1 |
|
/* |
2 |
|
* ether_unix.cpp - Ethernet device driver, Unix specific stuff (Linux and FreeBSD) |
3 |
|
* |
4 |
< |
* Basilisk II (C) 1997-2005 Christian Bauer |
4 |
> |
* Basilisk II (C) 1997-2008 Christian Bauer |
5 |
|
* |
6 |
|
* This program is free software; you can redistribute it and/or modify |
7 |
|
* it under the terms of the GNU General Public License as published by |
33 |
|
#define USE_POLL 1 |
34 |
|
#endif |
35 |
|
|
36 |
+ |
// Define to let the slirp library determine the right timeout for select() |
37 |
+ |
#define USE_SLIRP_TIMEOUT 1 |
38 |
+ |
|
39 |
|
#ifdef HAVE_SYS_POLL_H |
40 |
|
#include <sys/poll.h> |
41 |
|
#endif |
47 |
|
#include <semaphore.h> |
48 |
|
#include <errno.h> |
49 |
|
#include <stdio.h> |
50 |
+ |
#include <signal.h> |
51 |
|
#include <map> |
52 |
|
|
53 |
|
#if defined(__FreeBSD__) || defined(sgi) || (defined(__APPLE__) && defined(__MACH__)) |
125 |
|
// Prototypes |
126 |
|
static void *receive_func(void *arg); |
127 |
|
static void *slirp_receive_func(void *arg); |
124 |
– |
static int poll_fd(int fd); |
128 |
|
static int16 ether_do_add_multicast(uint8 *addr); |
129 |
|
static int16 ether_do_del_multicast(uint8 *addr); |
130 |
|
static int16 ether_do_write(uint32 arg); |
248 |
|
else |
249 |
|
net_if_type = NET_IF_SHEEPNET; |
250 |
|
|
251 |
+ |
// Don't raise SIGPIPE, let errno be set to EPIPE |
252 |
+ |
struct sigaction sigpipe_sa; |
253 |
+ |
if (sigaction(SIGPIPE, NULL, &sigpipe_sa) == 0) { |
254 |
+ |
assert(sigpipe_sa.sa_handler == SIG_DFL || sigpipe_sa.sa_handler == SIG_IGN); |
255 |
+ |
sigfillset(&sigpipe_sa.sa_mask); |
256 |
+ |
sigpipe_sa.sa_flags = 0; |
257 |
+ |
sigpipe_sa.sa_handler = SIG_IGN; |
258 |
+ |
sigaction(SIGPIPE, &sigpipe_sa, NULL); |
259 |
+ |
} |
260 |
+ |
|
261 |
|
#ifdef HAVE_SLIRP |
262 |
|
// Initialize slirp library |
263 |
|
if (net_if_type == NET_IF_SLIRP) { |
814 |
|
FD_ZERO(&rfds); |
815 |
|
FD_ZERO(&wfds); |
816 |
|
FD_ZERO(&xfds); |
817 |
< |
slirp_select_fill(&nfds, &rfds, &wfds, &xfds); |
817 |
> |
int timeout = slirp_select_fill(&nfds, &rfds, &wfds, &xfds); |
818 |
> |
#if ! USE_SLIRP_TIMEOUT |
819 |
> |
timeout = 10000; |
820 |
> |
#endif |
821 |
|
tv.tv_sec = 0; |
822 |
< |
tv.tv_usec = 10000; |
822 |
> |
tv.tv_usec = timeout; |
823 |
|
if (select(nfds + 1, &rfds, &wfds, &xfds, &tv) >= 0) |
824 |
|
slirp_select_poll(&rfds, &wfds, &xfds); |
825 |
|
|
881 |
|
// Wait for interrupt acknowledge by EtherInterrupt() |
882 |
|
sem_wait(&int_ack); |
883 |
|
} else |
884 |
< |
usleep(20000); |
884 |
> |
Delay_usec(20000); |
885 |
|
} |
886 |
|
return NULL; |
887 |
|
} |