• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 #include "sysdeps.h"
2 #include <windows.h>
3 #include <winsock2.h>
4 #include <stdio.h>
5 #include <errno.h>
6 #define  TRACE_TAG  TRACE_SYSDEPS
7 #include "adb.h"
8 
9 extern void fatal(const char *fmt, ...);
10 
11 #define assert(cond)  do { if (!(cond)) fatal( "assertion failed '%s' on %s:%ld\n", #cond, __FILE__, __LINE__ ); } while (0)
12 
13 /**************************************************************************/
14 /**************************************************************************/
15 /*****                                                                *****/
16 /*****      replaces libs/cutils/load_file.c                          *****/
17 /*****                                                                *****/
18 /**************************************************************************/
19 /**************************************************************************/
20 
load_file(const char * fn,unsigned * _sz)21 void *load_file(const char *fn, unsigned *_sz)
22 {
23     HANDLE    file;
24     char     *data;
25     DWORD     file_size;
26 
27     file = CreateFile( fn,
28                        GENERIC_READ,
29                        FILE_SHARE_READ,
30                        NULL,
31                        OPEN_EXISTING,
32                        0,
33                        NULL );
34 
35     if (file == INVALID_HANDLE_VALUE)
36         return NULL;
37 
38     file_size = GetFileSize( file, NULL );
39     data      = NULL;
40 
41     if (file_size > 0) {
42         data = (char*) malloc( file_size + 1 );
43         if (data == NULL) {
44             D("load_file: could not allocate %ld bytes\n", file_size );
45             file_size = 0;
46         } else {
47             DWORD  out_bytes;
48 
49             if ( !ReadFile( file, data, file_size, &out_bytes, NULL ) ||
50                  out_bytes != file_size )
51             {
52                 D("load_file: could not read %ld bytes from '%s'\n", file_size, fn);
53                 free(data);
54                 data      = NULL;
55                 file_size = 0;
56             }
57         }
58     }
59     CloseHandle( file );
60 
61     *_sz = (unsigned) file_size;
62     return  data;
63 }
64 
65 /**************************************************************************/
66 /**************************************************************************/
67 /*****                                                                *****/
68 /*****    common file descriptor handling                             *****/
69 /*****                                                                *****/
70 /**************************************************************************/
71 /**************************************************************************/
72 
73 typedef const struct FHClassRec_*   FHClass;
74 
75 typedef struct FHRec_*          FH;
76 
77 typedef struct EventHookRec_*  EventHook;
78 
79 typedef struct FHClassRec_
80 {
81     void (*_fh_init) ( FH  f );
82     int  (*_fh_close)( FH  f );
83     int  (*_fh_lseek)( FH  f, int  pos, int  origin );
84     int  (*_fh_read) ( FH  f, void*  buf, int  len );
85     int  (*_fh_write)( FH  f, const void*  buf, int  len );
86     void (*_fh_hook) ( FH  f, int  events, EventHook  hook );
87 
88 } FHClassRec;
89 
90 /* used to emulate unix-domain socket pairs */
91 typedef struct SocketPairRec_*  SocketPair;
92 
93 typedef struct FHRec_
94 {
95     FHClass    clazz;
96     int        used;
97     int        eof;
98     union {
99         HANDLE      handle;
100         SOCKET      socket;
101         SocketPair  pair;
102     } u;
103 
104     HANDLE    event;
105     int       mask;
106 
107     char  name[32];
108 
109 } FHRec;
110 
111 #define  fh_handle  u.handle
112 #define  fh_socket  u.socket
113 #define  fh_pair    u.pair
114 
115 #define  WIN32_FH_BASE    100
116 
117 #define  WIN32_MAX_FHS    128
118 
119 static adb_mutex_t   _win32_lock;
120 static  FHRec        _win32_fhs[ WIN32_MAX_FHS ];
121 static  int          _win32_fh_count;
122 
123 static FH
_fh_from_int(int fd)124 _fh_from_int( int   fd )
125 {
126     FH  f;
127 
128     fd -= WIN32_FH_BASE;
129 
130     if (fd < 0 || fd >= _win32_fh_count) {
131         D( "_fh_from_int: invalid fd %d\n", fd + WIN32_FH_BASE );
132         errno = EBADF;
133         return NULL;
134     }
135 
136     f = &_win32_fhs[fd];
137 
138     if (f->used == 0) {
139         D( "_fh_from_int: invalid fd %d\n", fd + WIN32_FH_BASE );
140         errno = EBADF;
141         return NULL;
142     }
143 
144     return f;
145 }
146 
147 
148 static int
_fh_to_int(FH f)149 _fh_to_int( FH  f )
150 {
151     if (f && f->used && f >= _win32_fhs && f < _win32_fhs + WIN32_MAX_FHS)
152         return (int)(f - _win32_fhs) + WIN32_FH_BASE;
153 
154     return -1;
155 }
156 
157 static FH
_fh_alloc(FHClass clazz)158 _fh_alloc( FHClass  clazz )
159 {
160     int  nn;
161     FH   f = NULL;
162 
163     adb_mutex_lock( &_win32_lock );
164 
165     if (_win32_fh_count < WIN32_MAX_FHS) {
166         f = &_win32_fhs[ _win32_fh_count++ ];
167         goto Exit;
168     }
169 
170     for (nn = 0; nn < WIN32_MAX_FHS; nn++) {
171         if ( _win32_fhs[nn].clazz == NULL) {
172             f = &_win32_fhs[nn];
173             goto Exit;
174         }
175     }
176     D( "_fh_alloc: no more free file descriptors\n" );
177 Exit:
178     if (f) {
179         f->clazz = clazz;
180         f->used  = 1;
181         f->eof   = 0;
182         clazz->_fh_init(f);
183     }
184     adb_mutex_unlock( &_win32_lock );
185     return f;
186 }
187 
188 
189 static int
_fh_close(FH f)190 _fh_close( FH   f )
191 {
192     if ( f->used ) {
193         f->clazz->_fh_close( f );
194         f->used = 0;
195         f->eof  = 0;
196         f->clazz = NULL;
197     }
198     return 0;
199 }
200 
201 /* forward definitions */
202 static const FHClassRec   _fh_file_class;
203 static const FHClassRec   _fh_socket_class;
204 
205 /**************************************************************************/
206 /**************************************************************************/
207 /*****                                                                *****/
208 /*****    file-based descriptor handling                              *****/
209 /*****                                                                *****/
210 /**************************************************************************/
211 /**************************************************************************/
212 
213 static void
_fh_file_init(FH f)214 _fh_file_init( FH  f )
215 {
216     f->fh_handle = INVALID_HANDLE_VALUE;
217 }
218 
219 static int
_fh_file_close(FH f)220 _fh_file_close( FH  f )
221 {
222     CloseHandle( f->fh_handle );
223     f->fh_handle = INVALID_HANDLE_VALUE;
224     return 0;
225 }
226 
227 static int
_fh_file_read(FH f,void * buf,int len)228 _fh_file_read( FH  f,  void*  buf, int   len )
229 {
230     DWORD  read_bytes;
231 
232     if ( !ReadFile( f->fh_handle, buf, (DWORD)len, &read_bytes, NULL ) ) {
233         D( "adb_read: could not read %d bytes from %s\n", len, f->name );
234         errno = EIO;
235         return -1;
236     } else if (read_bytes < (DWORD)len) {
237         f->eof = 1;
238     }
239     return (int)read_bytes;
240 }
241 
242 static int
_fh_file_write(FH f,const void * buf,int len)243 _fh_file_write( FH  f,  const void*  buf, int   len )
244 {
245     DWORD  wrote_bytes;
246 
247     if ( !WriteFile( f->fh_handle, buf, (DWORD)len, &wrote_bytes, NULL ) ) {
248         D( "adb_file_write: could not write %d bytes from %s\n", len, f->name );
249         errno = EIO;
250         return -1;
251     } else if (wrote_bytes < (DWORD)len) {
252         f->eof = 1;
253     }
254     return  (int)wrote_bytes;
255 }
256 
257 static int
_fh_file_lseek(FH f,int pos,int origin)258 _fh_file_lseek( FH  f, int  pos, int  origin )
259 {
260     DWORD  method;
261     DWORD  result;
262 
263     switch (origin)
264     {
265         case SEEK_SET:  method = FILE_BEGIN; break;
266         case SEEK_CUR:  method = FILE_CURRENT; break;
267         case SEEK_END:  method = FILE_END; break;
268         default:
269             errno = EINVAL;
270             return -1;
271     }
272 
273     result = SetFilePointer( f->fh_handle, pos, NULL, method );
274     if (result == INVALID_SET_FILE_POINTER) {
275         errno = EIO;
276         return -1;
277     } else {
278         f->eof = 0;
279     }
280     return (int)result;
281 }
282 
283 static void  _fh_file_hook( FH  f, int  event, EventHook  eventhook );  /* forward */
284 
285 static const FHClassRec  _fh_file_class =
286 {
287     _fh_file_init,
288     _fh_file_close,
289     _fh_file_lseek,
290     _fh_file_read,
291     _fh_file_write,
292     _fh_file_hook
293 };
294 
295 /**************************************************************************/
296 /**************************************************************************/
297 /*****                                                                *****/
298 /*****    file-based descriptor handling                              *****/
299 /*****                                                                *****/
300 /**************************************************************************/
301 /**************************************************************************/
302 
adb_open(const char * path,int options)303 int  adb_open(const char*  path, int  options)
304 {
305     FH  f;
306 
307     DWORD  desiredAccess       = 0;
308     DWORD  shareMode           = FILE_SHARE_READ | FILE_SHARE_WRITE;
309 
310     switch (options) {
311         case O_RDONLY:
312             desiredAccess = GENERIC_READ;
313             break;
314         case O_WRONLY:
315             desiredAccess = GENERIC_WRITE;
316             break;
317         case O_RDWR:
318             desiredAccess = GENERIC_READ | GENERIC_WRITE;
319             break;
320         default:
321             D("adb_open: invalid options (0x%0x)\n", options);
322             errno = EINVAL;
323             return -1;
324     }
325 
326     f = _fh_alloc( &_fh_file_class );
327     if ( !f ) {
328         errno = ENOMEM;
329         return -1;
330     }
331 
332     f->fh_handle = CreateFile( path, desiredAccess, shareMode, NULL, OPEN_EXISTING,
333                                0, NULL );
334 
335     if ( f->fh_handle == INVALID_HANDLE_VALUE ) {
336         _fh_close(f);
337         D( "adb_open: could not open '%s':", path );
338         switch (GetLastError()) {
339             case ERROR_FILE_NOT_FOUND:
340                 D( "file not found\n" );
341                 errno = ENOENT;
342                 return -1;
343 
344             case ERROR_PATH_NOT_FOUND:
345                 D( "path not found\n" );
346                 errno = ENOTDIR;
347                 return -1;
348 
349             default:
350                 D( "unknown error\n" );
351                 errno = ENOENT;
352                 return -1;
353         }
354     }
355 
356     snprintf( f->name, sizeof(f->name), "%d(%s)", _fh_to_int(f), path );
357     D( "adb_open: '%s' => fd %d\n", path, _fh_to_int(f) );
358     return _fh_to_int(f);
359 }
360 
361 /* ignore mode on Win32 */
adb_creat(const char * path,int mode)362 int  adb_creat(const char*  path, int  mode)
363 {
364     FH  f;
365 
366     f = _fh_alloc( &_fh_file_class );
367     if ( !f ) {
368         errno = ENOMEM;
369         return -1;
370     }
371 
372     f->fh_handle = CreateFile( path, GENERIC_WRITE, FILE_SHARE_READ | FILE_SHARE_WRITE,
373                                NULL, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL,
374                                NULL );
375 
376     if ( f->fh_handle == INVALID_HANDLE_VALUE ) {
377         _fh_close(f);
378         D( "adb_creat: could not open '%s':", path );
379         switch (GetLastError()) {
380             case ERROR_FILE_NOT_FOUND:
381                 D( "file not found\n" );
382                 errno = ENOENT;
383                 return -1;
384 
385             case ERROR_PATH_NOT_FOUND:
386                 D( "path not found\n" );
387                 errno = ENOTDIR;
388                 return -1;
389 
390             default:
391                 D( "unknown error\n" );
392                 errno = ENOENT;
393                 return -1;
394         }
395     }
396     snprintf( f->name, sizeof(f->name), "%d(%s)", _fh_to_int(f), path );
397     D( "adb_creat: '%s' => fd %d\n", path, _fh_to_int(f) );
398     return _fh_to_int(f);
399 }
400 
401 
adb_read(int fd,void * buf,int len)402 int  adb_read(int  fd, void* buf, int len)
403 {
404     FH     f = _fh_from_int(fd);
405 
406     if (f == NULL) {
407         return -1;
408     }
409 
410     return f->clazz->_fh_read( f, buf, len );
411 }
412 
413 
adb_write(int fd,const void * buf,int len)414 int  adb_write(int  fd, const void*  buf, int  len)
415 {
416     FH     f = _fh_from_int(fd);
417 
418     if (f == NULL) {
419         return -1;
420     }
421 
422     return f->clazz->_fh_write(f, buf, len);
423 }
424 
425 
adb_lseek(int fd,int pos,int where)426 int  adb_lseek(int  fd, int  pos, int  where)
427 {
428     FH     f = _fh_from_int(fd);
429 
430     if (!f) {
431         return -1;
432     }
433 
434     return f->clazz->_fh_lseek(f, pos, where);
435 }
436 
437 
adb_close(int fd)438 int  adb_close(int  fd)
439 {
440     FH   f = _fh_from_int(fd);
441 
442     if (!f) {
443         return -1;
444     }
445 
446     D( "adb_close: %s\n", f->name);
447     _fh_close(f);
448     return 0;
449 }
450 
451 /**************************************************************************/
452 /**************************************************************************/
453 /*****                                                                *****/
454 /*****    socket-based file descriptors                               *****/
455 /*****                                                                *****/
456 /**************************************************************************/
457 /**************************************************************************/
458 
459 static void
_socket_set_errno(void)460 _socket_set_errno( void )
461 {
462     switch (WSAGetLastError()) {
463     case 0:              errno = 0; break;
464     case WSAEWOULDBLOCK: errno = EAGAIN; break;
465     case WSAEINTR:       errno = EINTR; break;
466     default:
467         D( "_socket_set_errno: unhandled value %d\n", WSAGetLastError() );
468         errno = EINVAL;
469     }
470 }
471 
472 static void
_fh_socket_init(FH f)473 _fh_socket_init( FH  f )
474 {
475     f->fh_socket = INVALID_SOCKET;
476     f->event     = WSACreateEvent();
477     f->mask      = 0;
478 }
479 
480 static int
_fh_socket_close(FH f)481 _fh_socket_close( FH  f )
482 {
483     /* gently tell any peer that we're closing the socket */
484     shutdown( f->fh_socket, SD_BOTH );
485     closesocket( f->fh_socket );
486     f->fh_socket = INVALID_SOCKET;
487     CloseHandle( f->event );
488     f->mask = 0;
489     return 0;
490 }
491 
492 static int
_fh_socket_lseek(FH f,int pos,int origin)493 _fh_socket_lseek( FH  f, int pos, int origin )
494 {
495     errno = EPIPE;
496     return -1;
497 }
498 
499 static int
_fh_socket_read(FH f,void * buf,int len)500 _fh_socket_read( FH  f, void*  buf, int  len )
501 {
502     int  result = recv( f->fh_socket, buf, len, 0 );
503     if (result == SOCKET_ERROR) {
504         _socket_set_errno();
505         result = -1;
506     }
507     return  result;
508 }
509 
510 static int
_fh_socket_write(FH f,const void * buf,int len)511 _fh_socket_write( FH  f, const void*  buf, int  len )
512 {
513     int  result = send( f->fh_socket, buf, len, 0 );
514     if (result == SOCKET_ERROR) {
515         _socket_set_errno();
516         result = -1;
517     }
518     return result;
519 }
520 
521 static void  _fh_socket_hook( FH  f, int  event, EventHook  hook );  /* forward */
522 
523 static const FHClassRec  _fh_socket_class =
524 {
525     _fh_socket_init,
526     _fh_socket_close,
527     _fh_socket_lseek,
528     _fh_socket_read,
529     _fh_socket_write,
530     _fh_socket_hook
531 };
532 
533 /**************************************************************************/
534 /**************************************************************************/
535 /*****                                                                *****/
536 /*****    replacement for libs/cutils/socket_xxxx.c                   *****/
537 /*****                                                                *****/
538 /**************************************************************************/
539 /**************************************************************************/
540 
541 #include <winsock2.h>
542 
543 static int  _winsock_init;
544 
545 static void
_cleanup_winsock(void)546 _cleanup_winsock( void )
547 {
548     WSACleanup();
549 }
550 
551 static void
_init_winsock(void)552 _init_winsock( void )
553 {
554     if (!_winsock_init) {
555         WSADATA  wsaData;
556         int      rc = WSAStartup( MAKEWORD(2,2), &wsaData);
557         if (rc != 0) {
558             fatal( "adb: could not initialize Winsock\n" );
559         }
560         atexit( _cleanup_winsock );
561         _winsock_init = 1;
562     }
563 }
564 
socket_loopback_client(int port,int type)565 int socket_loopback_client(int port, int type)
566 {
567     FH  f = _fh_alloc( &_fh_socket_class );
568     struct sockaddr_in addr;
569     SOCKET  s;
570 
571     if (!f)
572         return -1;
573 
574     if (!_winsock_init)
575         _init_winsock();
576 
577     memset(&addr, 0, sizeof(addr));
578     addr.sin_family = AF_INET;
579     addr.sin_port = htons(port);
580     addr.sin_addr.s_addr = htonl(INADDR_LOOPBACK);
581 
582     s = socket(AF_INET, type, 0);
583     if(s == INVALID_SOCKET) {
584         D("socket_loopback_client: could not create socket\n" );
585         _fh_close(f);
586         return -1;
587     }
588 
589     f->fh_socket = s;
590     if(connect(s, (struct sockaddr *) &addr, sizeof(addr)) < 0) {
591         D("socket_loopback_client: could not connect to %s:%d\n", type != SOCK_STREAM ? "udp" : "tcp", port );
592         _fh_close(f);
593         return -1;
594     }
595     snprintf( f->name, sizeof(f->name), "%d(lo-client:%s%d)", _fh_to_int(f), type != SOCK_STREAM ? "udp:" : "", port );
596     D( "socket_loopback_client: port %d type %s => fd %d\n", port, type != SOCK_STREAM ? "udp" : "tcp", _fh_to_int(f) );
597     return _fh_to_int(f);
598 }
599 
600 #define LISTEN_BACKLOG 4
601 
socket_loopback_server(int port,int type)602 int socket_loopback_server(int port, int type)
603 {
604     FH   f = _fh_alloc( &_fh_socket_class );
605     struct sockaddr_in addr;
606     SOCKET  s;
607     int  n;
608 
609     if (!f) {
610         return -1;
611     }
612 
613     if (!_winsock_init)
614         _init_winsock();
615 
616     memset(&addr, 0, sizeof(addr));
617     addr.sin_family = AF_INET;
618     addr.sin_port = htons(port);
619     addr.sin_addr.s_addr = htonl(INADDR_LOOPBACK);
620 
621     s = socket(AF_INET, type, 0);
622     if(s == INVALID_SOCKET) return -1;
623 
624     f->fh_socket = s;
625 
626     n = 1;
627     setsockopt(s, SOL_SOCKET, SO_EXCLUSIVEADDRUSE, (const char*)&n, sizeof(n));
628 
629     if(bind(s, (struct sockaddr *) &addr, sizeof(addr)) < 0) {
630         _fh_close(f);
631         return -1;
632     }
633     if (type == SOCK_STREAM) {
634         int ret;
635 
636         ret = listen(s, LISTEN_BACKLOG);
637         if (ret < 0) {
638             _fh_close(f);
639             return -1;
640         }
641     }
642     snprintf( f->name, sizeof(f->name), "%d(lo-server:%s%d)", _fh_to_int(f), type != SOCK_STREAM ? "udp:" : "", port );
643     D( "socket_loopback_server: port %d type %s => fd %d\n", port, type != SOCK_STREAM ? "udp" : "tcp", _fh_to_int(f) );
644     return _fh_to_int(f);
645 }
646 
647 
socket_network_client(const char * host,int port,int type)648 int socket_network_client(const char *host, int port, int type)
649 {
650     FH  f = _fh_alloc( &_fh_socket_class );
651     struct hostent *hp;
652     struct sockaddr_in addr;
653     SOCKET s;
654 
655     if (!f)
656         return -1;
657 
658     if (!_winsock_init)
659         _init_winsock();
660 
661     hp = gethostbyname(host);
662     if(hp == 0) {
663         _fh_close(f);
664         return -1;
665     }
666 
667     memset(&addr, 0, sizeof(addr));
668     addr.sin_family = hp->h_addrtype;
669     addr.sin_port = htons(port);
670     memcpy(&addr.sin_addr, hp->h_addr, hp->h_length);
671 
672     s = socket(hp->h_addrtype, type, 0);
673     if(s == INVALID_SOCKET) {
674         _fh_close(f);
675         return -1;
676     }
677     f->fh_socket = s;
678 
679     if(connect(s, (struct sockaddr *) &addr, sizeof(addr)) < 0) {
680         _fh_close(f);
681         return -1;
682     }
683 
684     snprintf( f->name, sizeof(f->name), "%d(net-client:%s%d)", _fh_to_int(f), type != SOCK_STREAM ? "udp:" : "", port );
685     D( "socket_network_client: host '%s' port %d type %s => fd %d\n", host, port, type != SOCK_STREAM ? "udp" : "tcp", _fh_to_int(f) );
686     return _fh_to_int(f);
687 }
688 
689 
socket_inaddr_any_server(int port,int type)690 int socket_inaddr_any_server(int port, int type)
691 {
692     FH  f = _fh_alloc( &_fh_socket_class );
693     struct sockaddr_in addr;
694     SOCKET  s;
695     int n;
696 
697     if (!f)
698         return -1;
699 
700     if (!_winsock_init)
701         _init_winsock();
702 
703     memset(&addr, 0, sizeof(addr));
704     addr.sin_family = AF_INET;
705     addr.sin_port = htons(port);
706     addr.sin_addr.s_addr = htonl(INADDR_ANY);
707 
708     s = socket(AF_INET, type, 0);
709     if(s == INVALID_SOCKET) {
710         _fh_close(f);
711         return -1;
712     }
713 
714     f->fh_socket = s;
715     n = 1;
716     setsockopt(s, SOL_SOCKET, SO_EXCLUSIVEADDRUSE, (const char*)&n, sizeof(n));
717 
718     if(bind(s, (struct sockaddr *) &addr, sizeof(addr)) < 0) {
719         _fh_close(f);
720         return -1;
721     }
722 
723     if (type == SOCK_STREAM) {
724         int ret;
725 
726         ret = listen(s, LISTEN_BACKLOG);
727         if (ret < 0) {
728             _fh_close(f);
729             return -1;
730         }
731     }
732     snprintf( f->name, sizeof(f->name), "%d(any-server:%s%d)", _fh_to_int(f), type != SOCK_STREAM ? "udp:" : "", port );
733     D( "socket_inaddr_server: port %d type %s => fd %d\n", port, type != SOCK_STREAM ? "udp" : "tcp", _fh_to_int(f) );
734     return _fh_to_int(f);
735 }
736 
737 #undef accept
adb_socket_accept(int serverfd,struct sockaddr * addr,socklen_t * addrlen)738 int  adb_socket_accept(int  serverfd, struct sockaddr*  addr, socklen_t  *addrlen)
739 {
740     FH   serverfh = _fh_from_int(serverfd);
741     FH   fh;
742 
743     if ( !serverfh || serverfh->clazz != &_fh_socket_class ) {
744         D( "adb_socket_accept: invalid fd %d\n", serverfd );
745         return -1;
746     }
747 
748     fh = _fh_alloc( &_fh_socket_class );
749     if (!fh) {
750         D( "adb_socket_accept: not enough memory to allocate accepted socket descriptor\n" );
751         return -1;
752     }
753 
754     fh->fh_socket = accept( serverfh->fh_socket, addr, addrlen );
755     if (fh->fh_socket == INVALID_SOCKET) {
756         _fh_close( fh );
757         D( "adb_socket_accept: accept on fd %d return error %ld\n", serverfd, GetLastError() );
758         return -1;
759     }
760 
761     snprintf( fh->name, sizeof(fh->name), "%d(accept:%s)", _fh_to_int(fh), serverfh->name );
762     D( "adb_socket_accept on fd %d returns fd %d\n", serverfd, _fh_to_int(fh) );
763     return  _fh_to_int(fh);
764 }
765 
766 
disable_tcp_nagle(int fd)767 void  disable_tcp_nagle(int fd)
768 {
769     FH   fh = _fh_from_int(fd);
770     int  on;
771 
772     if ( !fh || fh->clazz != &_fh_socket_class )
773         return;
774 
775     setsockopt( fh->fh_socket, IPPROTO_TCP, TCP_NODELAY, (const char*)&on, sizeof(on) );
776 }
777 
778 /**************************************************************************/
779 /**************************************************************************/
780 /*****                                                                *****/
781 /*****    emulated socketpairs                                       *****/
782 /*****                                                                *****/
783 /**************************************************************************/
784 /**************************************************************************/
785 
786 /* we implement socketpairs directly in use space for the following reasons:
787  *   - it avoids copying data from/to the Nt kernel
788  *   - it allows us to implement fdevent hooks easily and cheaply, something
789  *     that is not possible with standard Win32 pipes !!
790  *
791  * basically, we use two circular buffers, each one corresponding to a given
792  * direction.
793  *
794  * each buffer is implemented as two regions:
795  *
796  *   region A which is (a_start,a_end)
797  *   region B which is (0, b_end)  with b_end <= a_start
798  *
799  * an empty buffer has:  a_start = a_end = b_end = 0
800  *
801  * a_start is the pointer where we start reading data
802  * a_end is the pointer where we start writing data, unless it is BUFFER_SIZE,
803  * then you start writing at b_end
804  *
805  * the buffer is full when  b_end == a_start && a_end == BUFFER_SIZE
806  *
807  * there is room when b_end < a_start || a_end < BUFER_SIZE
808  *
809  * when reading, a_start is incremented, it a_start meets a_end, then
810  * we do:  a_start = 0, a_end = b_end, b_end = 0, and keep going on..
811  */
812 
813 #define  BIP_BUFFER_SIZE   4096
814 
815 #if 0
816 #include <stdio.h>
817 #  define  BIPD(x)      D x
818 #  define  BIPDUMP   bip_dump_hex
819 
820 static void  bip_dump_hex( const unsigned char*  ptr, size_t  len )
821 {
822     int  nn, len2 = len;
823 
824     if (len2 > 8) len2 = 8;
825 
826     for (nn = 0; nn < len2; nn++)
827         printf("%02x", ptr[nn]);
828     printf("  ");
829 
830     for (nn = 0; nn < len2; nn++) {
831         int  c = ptr[nn];
832         if (c < 32 || c > 127)
833             c = '.';
834         printf("%c", c);
835     }
836     printf("\n");
837     fflush(stdout);
838 }
839 
840 #else
841 #  define  BIPD(x)        do {} while (0)
842 #  define  BIPDUMP(p,l)   BIPD(p)
843 #endif
844 
845 typedef struct BipBufferRec_
846 {
847     int                a_start;
848     int                a_end;
849     int                b_end;
850     int                fdin;
851     int                fdout;
852     int                closed;
853     int                can_write;  /* boolean */
854     HANDLE             evt_write;  /* event signaled when one can write to a buffer  */
855     int                can_read;   /* boolean */
856     HANDLE             evt_read;   /* event signaled when one can read from a buffer */
857     CRITICAL_SECTION  lock;
858     unsigned char      buff[ BIP_BUFFER_SIZE ];
859 
860 } BipBufferRec, *BipBuffer;
861 
862 static void
bip_buffer_init(BipBuffer buffer)863 bip_buffer_init( BipBuffer  buffer )
864 {
865     D( "bit_buffer_init %p\n", buffer );
866     buffer->a_start   = 0;
867     buffer->a_end     = 0;
868     buffer->b_end     = 0;
869     buffer->can_write = 1;
870     buffer->can_read  = 0;
871     buffer->fdin      = 0;
872     buffer->fdout     = 0;
873     buffer->closed    = 0;
874     buffer->evt_write = CreateEvent( NULL, TRUE, TRUE, NULL );
875     buffer->evt_read  = CreateEvent( NULL, TRUE, FALSE, NULL );
876     InitializeCriticalSection( &buffer->lock );
877 }
878 
879 static void
bip_buffer_close(BipBuffer bip)880 bip_buffer_close( BipBuffer  bip )
881 {
882     bip->closed = 1;
883 
884     if (!bip->can_read) {
885         SetEvent( bip->evt_read );
886     }
887     if (!bip->can_write) {
888         SetEvent( bip->evt_write );
889     }
890 }
891 
892 static void
bip_buffer_done(BipBuffer bip)893 bip_buffer_done( BipBuffer  bip )
894 {
895     BIPD(( "bip_buffer_done: %d->%d\n", bip->fdin, bip->fdout ));
896     CloseHandle( bip->evt_read );
897     CloseHandle( bip->evt_write );
898     DeleteCriticalSection( &bip->lock );
899 }
900 
901 static int
bip_buffer_write(BipBuffer bip,const void * src,int len)902 bip_buffer_write( BipBuffer  bip, const void* src, int  len )
903 {
904     int  avail, count = 0;
905 
906     if (len <= 0)
907         return 0;
908 
909     BIPD(( "bip_buffer_write: enter %d->%d len %d\n", bip->fdin, bip->fdout, len ));
910     BIPDUMP( src, len );
911 
912     EnterCriticalSection( &bip->lock );
913 
914     while (!bip->can_write) {
915         int  ret;
916         LeaveCriticalSection( &bip->lock );
917 
918         if (bip->closed) {
919             errno = EPIPE;
920             return -1;
921         }
922         /* spinlocking here is probably unfair, but let's live with it */
923         ret = WaitForSingleObject( bip->evt_write, INFINITE );
924         if (ret != WAIT_OBJECT_0) {  /* buffer probably closed */
925             D( "bip_buffer_write: error %d->%d WaitForSingleObject returned %d, error %ld\n", bip->fdin, bip->fdout, ret, GetLastError() );
926             return 0;
927         }
928         if (bip->closed) {
929             errno = EPIPE;
930             return -1;
931         }
932         EnterCriticalSection( &bip->lock );
933     }
934 
935     BIPD(( "bip_buffer_write: exec %d->%d len %d\n", bip->fdin, bip->fdout, len ));
936 
937     avail = BIP_BUFFER_SIZE - bip->a_end;
938     if (avail > 0)
939     {
940         /* we can append to region A */
941         if (avail > len)
942             avail = len;
943 
944         memcpy( bip->buff + bip->a_end, src, avail );
945         src   += avail;
946         count += avail;
947         len   -= avail;
948 
949         bip->a_end += avail;
950         if (bip->a_end == BIP_BUFFER_SIZE && bip->a_start == 0) {
951             bip->can_write = 0;
952             ResetEvent( bip->evt_write );
953             goto Exit;
954         }
955     }
956 
957     if (len == 0)
958         goto Exit;
959 
960     avail = bip->a_start - bip->b_end;
961     assert( avail > 0 );  /* since can_write is TRUE */
962 
963     if (avail > len)
964         avail = len;
965 
966     memcpy( bip->buff + bip->b_end, src, avail );
967     count += avail;
968     bip->b_end += avail;
969 
970     if (bip->b_end == bip->a_start) {
971         bip->can_write = 0;
972         ResetEvent( bip->evt_write );
973     }
974 
975 Exit:
976     assert( count > 0 );
977 
978     if ( !bip->can_read ) {
979         bip->can_read = 1;
980         SetEvent( bip->evt_read );
981     }
982 
983     BIPD(( "bip_buffer_write: exit %d->%d count %d (as=%d ae=%d be=%d cw=%d cr=%d\n",
984             bip->fdin, bip->fdout, count, bip->a_start, bip->a_end, bip->b_end, bip->can_write, bip->can_read ));
985     LeaveCriticalSection( &bip->lock );
986 
987     return count;
988  }
989 
990 static int
bip_buffer_read(BipBuffer bip,void * dst,int len)991 bip_buffer_read( BipBuffer  bip, void*  dst, int  len )
992 {
993     int  avail, count = 0;
994 
995     if (len <= 0)
996         return 0;
997 
998     BIPD(( "bip_buffer_read: enter %d->%d len %d\n", bip->fdin, bip->fdout, len ));
999 
1000     EnterCriticalSection( &bip->lock );
1001     while ( !bip->can_read )
1002     {
1003 #if 0
1004         LeaveCriticalSection( &bip->lock );
1005         errno = EAGAIN;
1006         return -1;
1007 #else
1008         int  ret;
1009         LeaveCriticalSection( &bip->lock );
1010 
1011         if (bip->closed) {
1012             errno = EPIPE;
1013             return -1;
1014         }
1015 
1016         ret = WaitForSingleObject( bip->evt_read, INFINITE );
1017         if (ret != WAIT_OBJECT_0) { /* probably closed buffer */
1018             D( "bip_buffer_read: error %d->%d WaitForSingleObject returned %d, error %ld\n", bip->fdin, bip->fdout, ret, GetLastError());
1019             return 0;
1020         }
1021         if (bip->closed) {
1022             errno = EPIPE;
1023             return -1;
1024         }
1025         EnterCriticalSection( &bip->lock );
1026 #endif
1027     }
1028 
1029     BIPD(( "bip_buffer_read: exec %d->%d len %d\n", bip->fdin, bip->fdout, len ));
1030 
1031     avail = bip->a_end - bip->a_start;
1032     assert( avail > 0 );  /* since can_read is TRUE */
1033 
1034     if (avail > len)
1035         avail = len;
1036 
1037     memcpy( dst, bip->buff + bip->a_start, avail );
1038     dst   += avail;
1039     count += avail;
1040     len   -= avail;
1041 
1042     bip->a_start += avail;
1043     if (bip->a_start < bip->a_end)
1044         goto Exit;
1045 
1046     bip->a_start = 0;
1047     bip->a_end   = bip->b_end;
1048     bip->b_end   = 0;
1049 
1050     avail = bip->a_end;
1051     if (avail > 0) {
1052         if (avail > len)
1053             avail = len;
1054         memcpy( dst, bip->buff, avail );
1055         count += avail;
1056         bip->a_start += avail;
1057 
1058         if ( bip->a_start < bip->a_end )
1059             goto Exit;
1060 
1061         bip->a_start = bip->a_end = 0;
1062     }
1063 
1064     bip->can_read = 0;
1065     ResetEvent( bip->evt_read );
1066 
1067 Exit:
1068     assert( count > 0 );
1069 
1070     if (!bip->can_write ) {
1071         bip->can_write = 1;
1072         SetEvent( bip->evt_write );
1073     }
1074 
1075     BIPDUMP( (const unsigned char*)dst - count, count );
1076     BIPD(( "bip_buffer_read: exit %d->%d count %d (as=%d ae=%d be=%d cw=%d cr=%d\n",
1077             bip->fdin, bip->fdout, count, bip->a_start, bip->a_end, bip->b_end, bip->can_write, bip->can_read ));
1078     LeaveCriticalSection( &bip->lock );
1079 
1080     return count;
1081 }
1082 
1083 typedef struct SocketPairRec_
1084 {
1085     BipBufferRec  a2b_bip;
1086     BipBufferRec  b2a_bip;
1087     FH            a_fd;
1088     int           used;
1089 
1090 } SocketPairRec;
1091 
_fh_socketpair_init(FH f)1092 void _fh_socketpair_init( FH  f )
1093 {
1094     f->fh_pair = NULL;
1095 }
1096 
1097 static int
_fh_socketpair_close(FH f)1098 _fh_socketpair_close( FH  f )
1099 {
1100     if ( f->fh_pair ) {
1101         SocketPair  pair = f->fh_pair;
1102 
1103         if ( f == pair->a_fd ) {
1104             pair->a_fd = NULL;
1105         }
1106 
1107         bip_buffer_close( &pair->b2a_bip );
1108         bip_buffer_close( &pair->a2b_bip );
1109 
1110         if ( --pair->used == 0 ) {
1111             bip_buffer_done( &pair->b2a_bip );
1112             bip_buffer_done( &pair->a2b_bip );
1113             free( pair );
1114         }
1115         f->fh_pair = NULL;
1116     }
1117     return 0;
1118 }
1119 
1120 static int
_fh_socketpair_lseek(FH f,int pos,int origin)1121 _fh_socketpair_lseek( FH  f, int pos, int  origin )
1122 {
1123     errno = ESPIPE;
1124     return -1;
1125 }
1126 
1127 static int
_fh_socketpair_read(FH f,void * buf,int len)1128 _fh_socketpair_read( FH  f, void* buf, int  len )
1129 {
1130     SocketPair  pair = f->fh_pair;
1131     BipBuffer   bip;
1132 
1133     if (!pair)
1134         return -1;
1135 
1136     if ( f == pair->a_fd )
1137         bip = &pair->b2a_bip;
1138     else
1139         bip = &pair->a2b_bip;
1140 
1141     return bip_buffer_read( bip, buf, len );
1142 }
1143 
1144 static int
_fh_socketpair_write(FH f,const void * buf,int len)1145 _fh_socketpair_write( FH  f, const void*  buf, int  len )
1146 {
1147     SocketPair  pair = f->fh_pair;
1148     BipBuffer   bip;
1149 
1150     if (!pair)
1151         return -1;
1152 
1153     if ( f == pair->a_fd )
1154         bip = &pair->a2b_bip;
1155     else
1156         bip = &pair->b2a_bip;
1157 
1158     return bip_buffer_write( bip, buf, len );
1159 }
1160 
1161 
1162 static void  _fh_socketpair_hook( FH  f, int  event, EventHook  hook );  /* forward */
1163 
1164 static const FHClassRec  _fh_socketpair_class =
1165 {
1166     _fh_socketpair_init,
1167     _fh_socketpair_close,
1168     _fh_socketpair_lseek,
1169     _fh_socketpair_read,
1170     _fh_socketpair_write,
1171     _fh_socketpair_hook
1172 };
1173 
1174 
adb_socketpair(int sv[2])1175 int  adb_socketpair( int  sv[2] )
1176 {
1177     FH          fa, fb;
1178     SocketPair  pair;
1179 
1180     fa = _fh_alloc( &_fh_socketpair_class );
1181     fb = _fh_alloc( &_fh_socketpair_class );
1182 
1183     if (!fa || !fb)
1184         goto Fail;
1185 
1186     pair = malloc( sizeof(*pair) );
1187     if (pair == NULL) {
1188         D("adb_socketpair: not enough memory to allocate pipes\n" );
1189         goto Fail;
1190     }
1191 
1192     bip_buffer_init( &pair->a2b_bip );
1193     bip_buffer_init( &pair->b2a_bip );
1194 
1195     fa->fh_pair = pair;
1196     fb->fh_pair = pair;
1197     pair->used  = 2;
1198     pair->a_fd  = fa;
1199 
1200     sv[0] = _fh_to_int(fa);
1201     sv[1] = _fh_to_int(fb);
1202 
1203     pair->a2b_bip.fdin  = sv[0];
1204     pair->a2b_bip.fdout = sv[1];
1205     pair->b2a_bip.fdin  = sv[1];
1206     pair->b2a_bip.fdout = sv[0];
1207 
1208     snprintf( fa->name, sizeof(fa->name), "%d(pair:%d)", sv[0], sv[1] );
1209     snprintf( fb->name, sizeof(fb->name), "%d(pair:%d)", sv[1], sv[0] );
1210     D( "adb_socketpair: returns (%d, %d)\n", sv[0], sv[1] );
1211     return 0;
1212 
1213 Fail:
1214     _fh_close(fb);
1215     _fh_close(fa);
1216     return -1;
1217 }
1218 
1219 /**************************************************************************/
1220 /**************************************************************************/
1221 /*****                                                                *****/
1222 /*****    fdevents emulation                                          *****/
1223 /*****                                                                *****/
1224 /*****   this is a very simple implementation, we rely on the fact    *****/
1225 /*****   that ADB doesn't use FDE_ERROR.                              *****/
1226 /*****                                                                *****/
1227 /**************************************************************************/
1228 /**************************************************************************/
1229 
1230 #define FATAL(x...) fatal(__FUNCTION__, x)
1231 
1232 #if DEBUG
dump_fde(fdevent * fde,const char * info)1233 static void dump_fde(fdevent *fde, const char *info)
1234 {
1235     fprintf(stderr,"FDE #%03d %c%c%c %s\n", fde->fd,
1236             fde->state & FDE_READ ? 'R' : ' ',
1237             fde->state & FDE_WRITE ? 'W' : ' ',
1238             fde->state & FDE_ERROR ? 'E' : ' ',
1239             info);
1240 }
1241 #else
1242 #define dump_fde(fde, info) do { } while(0)
1243 #endif
1244 
1245 #define FDE_EVENTMASK  0x00ff
1246 #define FDE_STATEMASK  0xff00
1247 
1248 #define FDE_ACTIVE     0x0100
1249 #define FDE_PENDING    0x0200
1250 #define FDE_CREATED    0x0400
1251 
1252 static void fdevent_plist_enqueue(fdevent *node);
1253 static void fdevent_plist_remove(fdevent *node);
1254 static fdevent *fdevent_plist_dequeue(void);
1255 
1256 static fdevent list_pending = {
1257     .next = &list_pending,
1258     .prev = &list_pending,
1259 };
1260 
1261 static fdevent **fd_table = 0;
1262 static int       fd_table_max = 0;
1263 
1264 typedef struct EventLooperRec_*  EventLooper;
1265 
1266 typedef struct EventHookRec_
1267 {
1268     EventHook    next;
1269     FH           fh;
1270     HANDLE       h;
1271     int          wanted;   /* wanted event flags */
1272     int          ready;    /* ready event flags  */
1273     void*        aux;
1274     void        (*prepare)( EventHook  hook );
1275     int         (*start)  ( EventHook  hook );
1276     void        (*stop)   ( EventHook  hook );
1277     int         (*check)  ( EventHook  hook );
1278     int         (*peek)   ( EventHook  hook );
1279 } EventHookRec;
1280 
1281 static EventHook  _free_hooks;
1282 
1283 static EventHook
event_hook_alloc(FH fh)1284 event_hook_alloc( FH  fh )
1285 {
1286     EventHook  hook = _free_hooks;
1287     if (hook != NULL)
1288         _free_hooks = hook->next;
1289     else {
1290         hook = malloc( sizeof(*hook) );
1291         if (hook == NULL)
1292             fatal( "could not allocate event hook\n" );
1293     }
1294     hook->next   = NULL;
1295     hook->fh     = fh;
1296     hook->wanted = 0;
1297     hook->ready  = 0;
1298     hook->h      = INVALID_HANDLE_VALUE;
1299     hook->aux    = NULL;
1300 
1301     hook->prepare = NULL;
1302     hook->start   = NULL;
1303     hook->stop    = NULL;
1304     hook->check   = NULL;
1305     hook->peek    = NULL;
1306 
1307     return hook;
1308 }
1309 
1310 static void
event_hook_free(EventHook hook)1311 event_hook_free( EventHook  hook )
1312 {
1313     hook->fh     = NULL;
1314     hook->wanted = 0;
1315     hook->ready  = 0;
1316     hook->next   = _free_hooks;
1317     _free_hooks  = hook;
1318 }
1319 
1320 
1321 static void
event_hook_signal(EventHook hook)1322 event_hook_signal( EventHook  hook )
1323 {
1324     FH        f   = hook->fh;
1325     int       fd  = _fh_to_int(f);
1326     fdevent*  fde = fd_table[ fd - WIN32_FH_BASE ];
1327 
1328     if (fde != NULL && fde->fd == fd) {
1329         if ((fde->state & FDE_PENDING) == 0) {
1330             fde->state |= FDE_PENDING;
1331             fdevent_plist_enqueue( fde );
1332         }
1333         fde->events |= hook->wanted;
1334     }
1335 }
1336 
1337 
1338 #define  MAX_LOOPER_HANDLES  WIN32_MAX_FHS
1339 
1340 typedef struct EventLooperRec_
1341 {
1342     EventHook    hooks;
1343     HANDLE       htab[ MAX_LOOPER_HANDLES ];
1344     int          htab_count;
1345 
1346 } EventLooperRec;
1347 
1348 static EventHook*
event_looper_find_p(EventLooper looper,FH fh)1349 event_looper_find_p( EventLooper  looper, FH  fh )
1350 {
1351     EventHook  *pnode = &looper->hooks;
1352     EventHook   node  = *pnode;
1353     for (;;) {
1354         if ( node == NULL || node->fh == fh )
1355             break;
1356         pnode = &node->next;
1357         node  = *pnode;
1358     }
1359     return  pnode;
1360 }
1361 
1362 static void
event_looper_hook(EventLooper looper,int fd,int events)1363 event_looper_hook( EventLooper  looper, int  fd, int  events )
1364 {
1365     FH          f = _fh_from_int(fd);
1366     EventHook  *pnode;
1367     EventHook   node;
1368 
1369     if (f == NULL)  /* invalid arg */ {
1370         D("event_looper_hook: invalid fd=%d\n", fd);
1371         return;
1372     }
1373 
1374     pnode = event_looper_find_p( looper, f );
1375     node  = *pnode;
1376     if ( node == NULL ) {
1377         node       = event_hook_alloc( f );
1378         node->next = *pnode;
1379         *pnode     = node;
1380     }
1381 
1382     if ( (node->wanted & events) != events ) {
1383         /* this should update start/stop/check/peek */
1384         D("event_looper_hook: call hook for %d (new=%x, old=%x)\n",
1385            fd, node->wanted, events);
1386         f->clazz->_fh_hook( f, events & ~node->wanted, node );
1387         node->wanted |= events;
1388     } else {
1389         D("event_looper_hook: ignoring events %x for %d wanted=%x)\n",
1390            events, fd, node->wanted);
1391     }
1392 }
1393 
1394 static void
event_looper_unhook(EventLooper looper,int fd,int events)1395 event_looper_unhook( EventLooper  looper, int  fd, int  events )
1396 {
1397     FH          fh    = _fh_from_int(fd);
1398     EventHook  *pnode = event_looper_find_p( looper, fh );
1399     EventHook   node  = *pnode;
1400 
1401     if (node != NULL) {
1402         int  events2 = events & node->wanted;
1403         if ( events2 == 0 ) {
1404             D( "event_looper_unhook: events %x not registered for fd %d\n", events, fd );
1405             return;
1406         }
1407         node->wanted &= ~events2;
1408         if (!node->wanted) {
1409             *pnode = node->next;
1410             event_hook_free( node );
1411         }
1412     }
1413 }
1414 
1415 static EventLooperRec  win32_looper;
1416 
fdevent_init(void)1417 static void fdevent_init(void)
1418 {
1419     win32_looper.htab_count = 0;
1420     win32_looper.hooks      = NULL;
1421 }
1422 
fdevent_connect(fdevent * fde)1423 static void fdevent_connect(fdevent *fde)
1424 {
1425     EventLooper  looper = &win32_looper;
1426     int          events = fde->state & FDE_EVENTMASK;
1427 
1428     if (events != 0)
1429         event_looper_hook( looper, fde->fd, events );
1430 }
1431 
fdevent_disconnect(fdevent * fde)1432 static void fdevent_disconnect(fdevent *fde)
1433 {
1434     EventLooper  looper = &win32_looper;
1435     int          events = fde->state & FDE_EVENTMASK;
1436 
1437     if (events != 0)
1438         event_looper_unhook( looper, fde->fd, events );
1439 }
1440 
fdevent_update(fdevent * fde,unsigned events)1441 static void fdevent_update(fdevent *fde, unsigned events)
1442 {
1443     EventLooper  looper  = &win32_looper;
1444     unsigned     events0 = fde->state & FDE_EVENTMASK;
1445 
1446     if (events != events0) {
1447         int  removes = events0 & ~events;
1448         int  adds    = events  & ~events0;
1449         if (removes) {
1450             D("fdevent_update: remove %x from %d\n", removes, fde->fd);
1451             event_looper_unhook( looper, fde->fd, removes );
1452         }
1453         if (adds) {
1454             D("fdevent_update: add %x to %d\n", adds, fde->fd);
1455             event_looper_hook  ( looper, fde->fd, adds );
1456         }
1457     }
1458 }
1459 
fdevent_process()1460 static void fdevent_process()
1461 {
1462     EventLooper  looper = &win32_looper;
1463     EventHook    hook;
1464     int          gotone = 0;
1465 
1466     /* if we have at least one ready hook, execute it/them */
1467     for (hook = looper->hooks; hook; hook = hook->next) {
1468         hook->ready = 0;
1469         if (hook->prepare) {
1470             hook->prepare(hook);
1471             if (hook->ready != 0) {
1472                 event_hook_signal( hook );
1473                 gotone = 1;
1474             }
1475         }
1476     }
1477 
1478     /* nothing's ready yet, so wait for something to happen */
1479     if (!gotone)
1480     {
1481         looper->htab_count = 0;
1482 
1483         for (hook = looper->hooks; hook; hook = hook->next)
1484         {
1485             if (hook->start && !hook->start(hook)) {
1486                 D( "fdevent_process: error when starting a hook\n" );
1487                 return;
1488             }
1489             if (hook->h != INVALID_HANDLE_VALUE) {
1490                 int  nn;
1491 
1492                 for (nn = 0; nn < looper->htab_count; nn++)
1493                 {
1494                     if ( looper->htab[nn] == hook->h )
1495                         goto DontAdd;
1496                 }
1497                 looper->htab[ looper->htab_count++ ] = hook->h;
1498             DontAdd:
1499                 ;
1500             }
1501         }
1502 
1503         if (looper->htab_count == 0) {
1504             D( "fdevent_process: nothing to wait for !!\n" );
1505             return;
1506         }
1507 
1508         do
1509         {
1510             int   wait_ret;
1511 
1512             D( "adb_win32: waiting for %d events\n", looper->htab_count );
1513             if (looper->htab_count > MAXIMUM_WAIT_OBJECTS) {
1514                 D("handle count %d exceeds MAXIMUM_WAIT_OBJECTS, aborting!\n", looper->htab_count);
1515                 abort();
1516             }
1517             wait_ret = WaitForMultipleObjects( looper->htab_count, looper->htab, FALSE, INFINITE );
1518             if (wait_ret == (int)WAIT_FAILED) {
1519                 D( "adb_win32: wait failed, error %ld\n", GetLastError() );
1520             } else {
1521                 D( "adb_win32: got one (index %d)\n", wait_ret );
1522 
1523                 /* according to Cygwin, some objects like consoles wake up on "inappropriate" events
1524                  * like mouse movements. we need to filter these with the "check" function
1525                  */
1526                 if ((unsigned)wait_ret < (unsigned)looper->htab_count)
1527                 {
1528                     for (hook = looper->hooks; hook; hook = hook->next)
1529                     {
1530                         if ( looper->htab[wait_ret] == hook->h       &&
1531                          (!hook->check || hook->check(hook)) )
1532                         {
1533                             D( "adb_win32: signaling %s for %x\n", hook->fh->name, hook->ready );
1534                             event_hook_signal( hook );
1535                             gotone = 1;
1536                             break;
1537                         }
1538                     }
1539                 }
1540             }
1541         }
1542         while (!gotone);
1543 
1544         for (hook = looper->hooks; hook; hook = hook->next) {
1545             if (hook->stop)
1546                 hook->stop( hook );
1547         }
1548     }
1549 
1550     for (hook = looper->hooks; hook; hook = hook->next) {
1551         if (hook->peek && hook->peek(hook))
1552                 event_hook_signal( hook );
1553     }
1554 }
1555 
1556 
fdevent_register(fdevent * fde)1557 static void fdevent_register(fdevent *fde)
1558 {
1559     int  fd = fde->fd - WIN32_FH_BASE;
1560 
1561     if(fd < 0) {
1562         FATAL("bogus negative fd (%d)\n", fde->fd);
1563     }
1564 
1565     if(fd >= fd_table_max) {
1566         int oldmax = fd_table_max;
1567         if(fde->fd > 32000) {
1568             FATAL("bogus huuuuge fd (%d)\n", fde->fd);
1569         }
1570         if(fd_table_max == 0) {
1571             fdevent_init();
1572             fd_table_max = 256;
1573         }
1574         while(fd_table_max <= fd) {
1575             fd_table_max *= 2;
1576         }
1577         fd_table = realloc(fd_table, sizeof(fdevent*) * fd_table_max);
1578         if(fd_table == 0) {
1579             FATAL("could not expand fd_table to %d entries\n", fd_table_max);
1580         }
1581         memset(fd_table + oldmax, 0, sizeof(int) * (fd_table_max - oldmax));
1582     }
1583 
1584     fd_table[fd] = fde;
1585 }
1586 
fdevent_unregister(fdevent * fde)1587 static void fdevent_unregister(fdevent *fde)
1588 {
1589     int  fd = fde->fd - WIN32_FH_BASE;
1590 
1591     if((fd < 0) || (fd >= fd_table_max)) {
1592         FATAL("fd out of range (%d)\n", fde->fd);
1593     }
1594 
1595     if(fd_table[fd] != fde) {
1596         FATAL("fd_table out of sync");
1597     }
1598 
1599     fd_table[fd] = 0;
1600 
1601     if(!(fde->state & FDE_DONT_CLOSE)) {
1602         dump_fde(fde, "close");
1603         adb_close(fde->fd);
1604     }
1605 }
1606 
fdevent_plist_enqueue(fdevent * node)1607 static void fdevent_plist_enqueue(fdevent *node)
1608 {
1609     fdevent *list = &list_pending;
1610 
1611     node->next = list;
1612     node->prev = list->prev;
1613     node->prev->next = node;
1614     list->prev = node;
1615 }
1616 
fdevent_plist_remove(fdevent * node)1617 static void fdevent_plist_remove(fdevent *node)
1618 {
1619     node->prev->next = node->next;
1620     node->next->prev = node->prev;
1621     node->next = 0;
1622     node->prev = 0;
1623 }
1624 
fdevent_plist_dequeue(void)1625 static fdevent *fdevent_plist_dequeue(void)
1626 {
1627     fdevent *list = &list_pending;
1628     fdevent *node = list->next;
1629 
1630     if(node == list) return 0;
1631 
1632     list->next = node->next;
1633     list->next->prev = list;
1634     node->next = 0;
1635     node->prev = 0;
1636 
1637     return node;
1638 }
1639 
fdevent_create(int fd,fd_func func,void * arg)1640 fdevent *fdevent_create(int fd, fd_func func, void *arg)
1641 {
1642     fdevent *fde = (fdevent*) malloc(sizeof(fdevent));
1643     if(fde == 0) return 0;
1644     fdevent_install(fde, fd, func, arg);
1645     fde->state |= FDE_CREATED;
1646     return fde;
1647 }
1648 
fdevent_destroy(fdevent * fde)1649 void fdevent_destroy(fdevent *fde)
1650 {
1651     if(fde == 0) return;
1652     if(!(fde->state & FDE_CREATED)) {
1653         FATAL("fde %p not created by fdevent_create()\n", fde);
1654     }
1655     fdevent_remove(fde);
1656 }
1657 
fdevent_install(fdevent * fde,int fd,fd_func func,void * arg)1658 void fdevent_install(fdevent *fde, int fd, fd_func func, void *arg)
1659 {
1660     memset(fde, 0, sizeof(fdevent));
1661     fde->state = FDE_ACTIVE;
1662     fde->fd = fd;
1663     fde->func = func;
1664     fde->arg = arg;
1665 
1666     fdevent_register(fde);
1667     dump_fde(fde, "connect");
1668     fdevent_connect(fde);
1669     fde->state |= FDE_ACTIVE;
1670 }
1671 
fdevent_remove(fdevent * fde)1672 void fdevent_remove(fdevent *fde)
1673 {
1674     if(fde->state & FDE_PENDING) {
1675         fdevent_plist_remove(fde);
1676     }
1677 
1678     if(fde->state & FDE_ACTIVE) {
1679         fdevent_disconnect(fde);
1680         dump_fde(fde, "disconnect");
1681         fdevent_unregister(fde);
1682     }
1683 
1684     fde->state = 0;
1685     fde->events = 0;
1686 }
1687 
1688 
fdevent_set(fdevent * fde,unsigned events)1689 void fdevent_set(fdevent *fde, unsigned events)
1690 {
1691     events &= FDE_EVENTMASK;
1692 
1693     if((fde->state & FDE_EVENTMASK) == (int)events) return;
1694 
1695     if(fde->state & FDE_ACTIVE) {
1696         fdevent_update(fde, events);
1697         dump_fde(fde, "update");
1698     }
1699 
1700     fde->state = (fde->state & FDE_STATEMASK) | events;
1701 
1702     if(fde->state & FDE_PENDING) {
1703             /* if we're pending, make sure
1704             ** we don't signal an event that
1705             ** is no longer wanted.
1706             */
1707         fde->events &= (~events);
1708         if(fde->events == 0) {
1709             fdevent_plist_remove(fde);
1710             fde->state &= (~FDE_PENDING);
1711         }
1712     }
1713 }
1714 
fdevent_add(fdevent * fde,unsigned events)1715 void fdevent_add(fdevent *fde, unsigned events)
1716 {
1717     fdevent_set(
1718         fde, (fde->state & FDE_EVENTMASK) | (events & FDE_EVENTMASK));
1719 }
1720 
fdevent_del(fdevent * fde,unsigned events)1721 void fdevent_del(fdevent *fde, unsigned events)
1722 {
1723     fdevent_set(
1724         fde, (fde->state & FDE_EVENTMASK) & (~(events & FDE_EVENTMASK)));
1725 }
1726 
fdevent_loop()1727 void fdevent_loop()
1728 {
1729     fdevent *fde;
1730 
1731     for(;;) {
1732 #if DEBUG
1733         fprintf(stderr,"--- ---- waiting for events\n");
1734 #endif
1735         fdevent_process();
1736 
1737         while((fde = fdevent_plist_dequeue())) {
1738             unsigned events = fde->events;
1739             fde->events = 0;
1740             fde->state &= (~FDE_PENDING);
1741             dump_fde(fde, "callback");
1742             fde->func(fde->fd, events, fde->arg);
1743         }
1744     }
1745 }
1746 
1747 /**  FILE EVENT HOOKS
1748  **/
1749 
_event_file_prepare(EventHook hook)1750 static void  _event_file_prepare( EventHook  hook )
1751 {
1752     if (hook->wanted & (FDE_READ|FDE_WRITE)) {
1753         /* we can always read/write */
1754         hook->ready |= hook->wanted & (FDE_READ|FDE_WRITE);
1755     }
1756 }
1757 
_event_file_peek(EventHook hook)1758 static int  _event_file_peek( EventHook  hook )
1759 {
1760     return (hook->wanted & (FDE_READ|FDE_WRITE));
1761 }
1762 
_fh_file_hook(FH f,int events,EventHook hook)1763 static void  _fh_file_hook( FH  f, int  events, EventHook  hook )
1764 {
1765     hook->h       = f->fh_handle;
1766     hook->prepare = _event_file_prepare;
1767     hook->peek    = _event_file_peek;
1768 }
1769 
1770 /** SOCKET EVENT HOOKS
1771  **/
1772 
_event_socket_verify(EventHook hook,WSANETWORKEVENTS * evts)1773 static void  _event_socket_verify( EventHook  hook, WSANETWORKEVENTS*  evts )
1774 {
1775     if ( evts->lNetworkEvents & (FD_READ|FD_ACCEPT|FD_CLOSE) ) {
1776         if (hook->wanted & FDE_READ)
1777             hook->ready |= FDE_READ;
1778         if ((evts->iErrorCode[FD_READ] != 0) && hook->wanted & FDE_ERROR)
1779             hook->ready |= FDE_ERROR;
1780     }
1781     if ( evts->lNetworkEvents & (FD_WRITE|FD_CONNECT|FD_CLOSE) ) {
1782         if (hook->wanted & FDE_WRITE)
1783             hook->ready |= FDE_WRITE;
1784         if ((evts->iErrorCode[FD_WRITE] != 0) && hook->wanted & FDE_ERROR)
1785             hook->ready |= FDE_ERROR;
1786     }
1787     if ( evts->lNetworkEvents & FD_OOB ) {
1788         if (hook->wanted & FDE_ERROR)
1789             hook->ready |= FDE_ERROR;
1790     }
1791 }
1792 
_event_socket_prepare(EventHook hook)1793 static void  _event_socket_prepare( EventHook  hook )
1794 {
1795     WSANETWORKEVENTS  evts;
1796 
1797     /* look if some of the events we want already happened ? */
1798     if (!WSAEnumNetworkEvents( hook->fh->fh_socket, NULL, &evts ))
1799         _event_socket_verify( hook, &evts );
1800 }
1801 
_socket_wanted_to_flags(int wanted)1802 static int  _socket_wanted_to_flags( int  wanted )
1803 {
1804     int  flags = 0;
1805     if (wanted & FDE_READ)
1806         flags |= FD_READ | FD_ACCEPT | FD_CLOSE;
1807 
1808     if (wanted & FDE_WRITE)
1809         flags |= FD_WRITE | FD_CONNECT | FD_CLOSE;
1810 
1811     if (wanted & FDE_ERROR)
1812         flags |= FD_OOB;
1813 
1814     return flags;
1815 }
1816 
_event_socket_start(EventHook hook)1817 static int _event_socket_start( EventHook  hook )
1818 {
1819     /* create an event which we're going to wait for */
1820     FH    fh    = hook->fh;
1821     long  flags = _socket_wanted_to_flags( hook->wanted );
1822 
1823     hook->h = fh->event;
1824     if (hook->h == INVALID_HANDLE_VALUE) {
1825         D( "_event_socket_start: no event for %s\n", fh->name );
1826         return 0;
1827     }
1828 
1829     if ( flags != fh->mask ) {
1830         D( "_event_socket_start: hooking %s for %x (flags %ld)\n", hook->fh->name, hook->wanted, flags );
1831         if ( WSAEventSelect( fh->fh_socket, hook->h, flags ) ) {
1832             D( "_event_socket_start: WSAEventSelect() for %s failed, error %d\n", hook->fh->name, WSAGetLastError() );
1833             CloseHandle( hook->h );
1834             hook->h = INVALID_HANDLE_VALUE;
1835             exit(1);
1836             return 0;
1837         }
1838         fh->mask = flags;
1839     }
1840     return 1;
1841 }
1842 
_event_socket_stop(EventHook hook)1843 static void _event_socket_stop( EventHook  hook )
1844 {
1845     hook->h = INVALID_HANDLE_VALUE;
1846 }
1847 
_event_socket_check(EventHook hook)1848 static int  _event_socket_check( EventHook  hook )
1849 {
1850     int               result = 0;
1851     FH                fh = hook->fh;
1852     WSANETWORKEVENTS  evts;
1853 
1854     if (!WSAEnumNetworkEvents( fh->fh_socket, hook->h, &evts ) ) {
1855         _event_socket_verify( hook, &evts );
1856         result = (hook->ready != 0);
1857         if (result) {
1858             ResetEvent( hook->h );
1859         }
1860     }
1861     D( "_event_socket_check %s returns %d\n", fh->name, result );
1862     return  result;
1863 }
1864 
_event_socket_peek(EventHook hook)1865 static int  _event_socket_peek( EventHook  hook )
1866 {
1867     WSANETWORKEVENTS  evts;
1868     FH                fh = hook->fh;
1869 
1870     /* look if some of the events we want already happened ? */
1871     if (!WSAEnumNetworkEvents( fh->fh_socket, NULL, &evts )) {
1872         _event_socket_verify( hook, &evts );
1873         if (hook->ready)
1874             ResetEvent( hook->h );
1875     }
1876 
1877     return hook->ready != 0;
1878 }
1879 
1880 
1881 
_fh_socket_hook(FH f,int events,EventHook hook)1882 static void  _fh_socket_hook( FH  f, int  events, EventHook  hook )
1883 {
1884     hook->prepare = _event_socket_prepare;
1885     hook->start   = _event_socket_start;
1886     hook->stop    = _event_socket_stop;
1887     hook->check   = _event_socket_check;
1888     hook->peek    = _event_socket_peek;
1889 
1890     _event_socket_start( hook );
1891 }
1892 
1893 /** SOCKETPAIR EVENT HOOKS
1894  **/
1895 
_event_socketpair_prepare(EventHook hook)1896 static void  _event_socketpair_prepare( EventHook  hook )
1897 {
1898     FH          fh   = hook->fh;
1899     SocketPair  pair = fh->fh_pair;
1900     BipBuffer   rbip = (pair->a_fd == fh) ? &pair->b2a_bip : &pair->a2b_bip;
1901     BipBuffer   wbip = (pair->a_fd == fh) ? &pair->a2b_bip : &pair->b2a_bip;
1902 
1903     if (hook->wanted & FDE_READ && rbip->can_read)
1904         hook->ready |= FDE_READ;
1905 
1906     if (hook->wanted & FDE_WRITE && wbip->can_write)
1907         hook->ready |= FDE_WRITE;
1908  }
1909 
_event_socketpair_start(EventHook hook)1910  static int  _event_socketpair_start( EventHook  hook )
1911  {
1912     FH          fh   = hook->fh;
1913     SocketPair  pair = fh->fh_pair;
1914     BipBuffer   rbip = (pair->a_fd == fh) ? &pair->b2a_bip : &pair->a2b_bip;
1915     BipBuffer   wbip = (pair->a_fd == fh) ? &pair->a2b_bip : &pair->b2a_bip;
1916 
1917     if (hook->wanted == FDE_READ)
1918         hook->h = rbip->evt_read;
1919 
1920     else if (hook->wanted == FDE_WRITE)
1921         hook->h = wbip->evt_write;
1922 
1923     else {
1924         D("_event_socketpair_start: can't handle FDE_READ+FDE_WRITE\n" );
1925         return 0;
1926     }
1927     D( "_event_socketpair_start: hook %s for %x wanted=%x\n",
1928        hook->fh->name, _fh_to_int(fh), hook->wanted);
1929     return 1;
1930 }
1931 
_event_socketpair_peek(EventHook hook)1932 static int  _event_socketpair_peek( EventHook  hook )
1933 {
1934     _event_socketpair_prepare( hook );
1935     return hook->ready != 0;
1936 }
1937 
_fh_socketpair_hook(FH fh,int events,EventHook hook)1938 static void  _fh_socketpair_hook( FH  fh, int  events, EventHook  hook )
1939 {
1940     hook->prepare = _event_socketpair_prepare;
1941     hook->start   = _event_socketpair_start;
1942     hook->peek    = _event_socketpair_peek;
1943 }
1944 
1945 
1946 void
adb_sysdeps_init(void)1947 adb_sysdeps_init( void )
1948 {
1949 #define  ADB_MUTEX(x)  InitializeCriticalSection( & x );
1950 #include "mutex_list.h"
1951     InitializeCriticalSection( &_win32_lock );
1952 }
1953 
1954