paragraph for gnunet devs that don't know how to use the web
[oweals/gnunet.git] / src / transport / gnunet-helper-transport-bluetooth.c
1 /*
2    This file is part of GNUnet.
3    Copyright (C) 2010, 2011, 2012 GNUnet e.V.
4    Copyright (c) 2007, 2008, Andy Green <andy@warmcat.com>
5    Copyright Copyright (C) 2009 Thomas d'Otreppe
6
7    GNUnet is free software: you can redistribute it and/or modify it
8    under the terms of the GNU Affero General Public License as published
9    by the Free Software Foundation, either version 3 of the License,
10    or (at your option) any later version.
11
12    GNUnet is distributed in the hope that it will be useful, but
13    WITHOUT ANY WARRANTY; without even the implied warranty of
14    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
15    Affero General Public License for more details.
16   
17    You should have received a copy of the GNU Affero General Public License
18    along with this program.  If not, see <http://www.gnu.org/licenses/>.
19 */
20 #include "gnunet_config.h"
21
22 #ifdef MINGW
23   #include "platform.h"
24   #include "gnunet_util_lib.h"
25   #include <bthdef.h>
26   #include <ws2bth.h>
27 #else
28   #define SOCKTYPE int
29   #include <bluetooth/bluetooth.h>
30   #include <bluetooth/hci.h>
31   #include <bluetooth/hci_lib.h>
32   #include <bluetooth/rfcomm.h>
33   #include <bluetooth/sdp.h>
34   #include <bluetooth/sdp_lib.h>
35   #include <errno.h>
36   #include <linux/if.h>
37   #include <stdio.h>
38   #include <stdlib.h>
39   #include <sys/ioctl.h>
40   #include <sys/param.h>
41   #include <sys/socket.h>
42   #include <sys/stat.h>
43   #include <sys/types.h>
44   #include <unistd.h>
45 #endif
46
47 #include "plugin_transport_wlan.h"
48 #include "gnunet_protocols.h"
49
50
51 /**
52  * Maximum number of ports assignable for RFCOMMM protocol.
53  */
54 #define MAX_PORTS 30
55
56 /**
57  * Maximum size of a message allowed in either direction
58  * (used for our receive and sent buffers).
59  */
60 #define MAXLINE 4096
61
62
63 /**
64  * Maximum number of loops without inquiring for new devices.
65  */
66 #define MAX_LOOPS 5
67
68 #ifdef MINGW
69   /* Maximum size of the interface's name */
70   #define IFNAMSIZ 16
71
72   #ifndef NS_BTH
73     #define NS_BTH 16
74   #endif
75   /**
76    * A copy of the MAC Address.
77    */
78   struct GNUNET_TRANSPORT_WLAN_MacAddress_Copy
79   {
80     UINT8 mac[MAC_ADDR_SIZE];
81   };
82
83   /**
84    * The UUID used for the SDP service.
85    * {31191E56-FA7E-4517-870E-71B86BBCC52F}
86    */
87   #define GNUNET_BLUETOOTH_SDP_UUID \
88     { \
89       0x31, 0x19, 0x1E, 0x56, \
90       0xFA, 0x7E, \
91       0x45, 0x17, \
92       0x87, 0x0E, \
93       0x71, 0xB8, 0x6B, 0xBC, 0xC5, 0x2F \
94     }
95 #endif
96
97 /**
98  * In bluez library, the maximum name length of a device is 8
99  */
100 #define BLUEZ_DEVNAME_SIZE  8
101
102 /**
103  * struct for storing the information of the hardware.  There is only
104  * one of these.
105  */
106 struct HardwareInfos
107 {
108   /**
109    * Name of the interface, not necessarily 0-terminated (!).
110    */
111   char iface[IFNAMSIZ];
112
113  #ifdef MINGW
114   /**
115    * socket handle
116    */
117   struct GNUNET_NETWORK_Handle *handle;
118
119   /**
120    * MAC address of our own bluetooth interface.
121    */
122   struct GNUNET_TRANSPORT_WLAN_MacAddress_Copy pl_mac;
123  #else
124   /**
125    * file descriptor for the rfcomm socket
126    */
127   int fd_rfcomm;
128
129   /**
130    * MAC address of our own bluetooth interface.
131    */
132   struct GNUNET_TRANSPORT_WLAN_MacAddress pl_mac;
133
134   /**
135    * SDP session
136    */
137    sdp_session_t *session ;
138  #endif
139 };
140
141 /**
142  * IO buffer used for buffering data in transit (to wireless or to stdout).
143  */
144 struct SendBuffer
145 {
146   /**
147    * How many bytes of data are stored in 'buf' for transmission right now?
148    * Data always starts at offset 0 and extends to 'size'.
149    */
150   size_t size;
151
152   /**
153    * How many bytes that were stored in 'buf' did we already write to the
154    * destination?  Always smaller than 'size'.
155    */
156   size_t pos;
157
158   /**
159    * Buffered data; twice the maximum allowed message size as we add some
160    * headers.
161    */
162   char buf[MAXLINE * 2];
163 };
164
165 #ifdef LINUX
166  /**
167   * Devices buffer used to keep a list with all the discoverable devices in
168   * order to send them HELLO messages one by one when it receive a broadcast message.
169   */
170  struct BroadcastMessages
171  {
172    /* List with the discoverable devices' addresses */
173    bdaddr_t devices[MAX_PORTS];
174
175    /* List with the open sockets */
176    int fds[MAX_PORTS];
177
178
179    /* The number of the devices */
180    int size;
181
182    /* The current position */
183    int pos;
184
185    /* The device id */
186    int dev_id;
187  };
188
189  /**
190   * Address used to identify the broadcast messages.
191   */
192  static struct GNUNET_TRANSPORT_WLAN_MacAddress broadcast_address = {{255, 255, 255, 255, 255, 255}};
193
194  /**
195   * Buffer with the discoverable devices.
196   */
197  static struct BroadcastMessages neighbours;
198
199  static int searching_devices_count = 0;
200 #endif
201
202 /**
203  * Buffer for data read from stdin to be transmitted to the bluetooth device
204  */
205 static struct SendBuffer write_pout;
206
207 /**
208  * Buffer for data read from the bluetooth device to be transmitted to stdout.
209  */
210 static struct SendBuffer write_std;
211
212
213 /* ****** this are the same functions as the ones used in gnunet-helper-transport-wlan.c ****** */
214
215 /**
216  * To what multiple do we align messages?  8 byte should suffice for everyone
217  * for now.
218  */
219 #define ALIGN_FACTOR 8
220
221 /**
222  * Smallest supported message.
223  */
224 #define MIN_BUFFER_SIZE sizeof (struct GNUNET_MessageHeader)
225
226
227 /**
228  * Functions with this signature are called whenever a
229  * complete message is received by the tokenizer.
230  *
231  * @param cls closure
232  * @param message the actual message
233  */
234 typedef void (*MessageTokenizerCallback) (void *cls,
235             const struct
236             GNUNET_MessageHeader *
237             message);
238
239 /**
240  * Handle to a message stream tokenizer.
241  */
242 struct MessageStreamTokenizer
243 {
244
245   /**
246    * Function to call on completed messages.
247    */
248   MessageTokenizerCallback cb;
249
250   /**
251    * Closure for cb.
252    */
253   void *cb_cls;
254
255   /**
256    * Size of the buffer (starting at 'hdr').
257    */
258   size_t curr_buf;
259
260   /**
261    * How many bytes in buffer have we already processed?
262    */
263   size_t off;
264
265   /**
266    * How many bytes in buffer are valid right now?
267    */
268   size_t pos;
269
270   /**
271    * Beginning of the buffer.  Typed like this to force alignment.
272    */
273   struct GNUNET_MessageHeader *hdr;
274
275 };
276
277
278 /**
279  * Create a message stream tokenizer.
280  *
281  * @param cb function to call on completed messages
282  * @param cb_cls closure for cb
283  * @return handle to tokenizer
284  */
285 static struct MessageStreamTokenizer *
286 mst_create (MessageTokenizerCallback cb,
287       void *cb_cls)
288 {
289   struct MessageStreamTokenizer *ret;
290
291   ret = malloc (sizeof (struct MessageStreamTokenizer));
292   if (NULL == ret)
293   {
294     fprintf (stderr, "Failed to allocate buffer for tokenizer\n");
295     exit (1);
296   }
297   ret->hdr = malloc (MIN_BUFFER_SIZE);
298   if (NULL == ret->hdr)
299   {
300     fprintf (stderr, "Failed to allocate buffer for alignment\n");
301     exit (1);
302   }
303   ret->curr_buf = MIN_BUFFER_SIZE;
304   ret->cb = cb;
305   ret->cb_cls = cb_cls;
306   ret->pos = 0;
307
308   return ret;
309 }
310
311
312 /**
313  * Add incoming data to the receive buffer and call the
314  * callback for all complete messages.
315  *
316  * @param mst tokenizer to use
317  * @param buf input data to add
318  * @param size number of bytes in buf
319  * @return GNUNET_OK if we are done processing (need more data)
320  *         GNUNET_SYSERR if the data stream is corrupt
321  */
322 static int
323 mst_receive (struct MessageStreamTokenizer *mst,
324        const char *buf, size_t size)
325 {
326   const struct GNUNET_MessageHeader *hdr;
327   size_t delta;
328   uint16_t want;
329   char *ibuf;
330   int need_align;
331   unsigned long offset;
332   int ret;
333
334   ret = GNUNET_OK;
335   ibuf = (char *) mst->hdr;
336   while (mst->pos > 0)
337   {
338 do_align:
339     if (mst->pos < mst->off)
340     {
341       //fprintf (stderr, "We processed too many bytes!\n");
342       return GNUNET_SYSERR;
343     }
344     if ((mst->curr_buf - mst->off < sizeof (struct GNUNET_MessageHeader)) ||
345         (0 != (mst->off % ALIGN_FACTOR)))
346     {
347       /* need to align or need more space */
348       mst->pos -= mst->off;
349       memmove (ibuf, &ibuf[mst->off], mst->pos);
350       mst->off = 0;
351     }
352     if (mst->pos - mst->off < sizeof (struct GNUNET_MessageHeader))
353     {
354       delta =
355           GNUNET_MIN (sizeof (struct GNUNET_MessageHeader) -
356                       (mst->pos - mst->off), size);
357       GNUNET_memcpy (&ibuf[mst->pos], buf, delta);
358       mst->pos += delta;
359       buf += delta;
360       size -= delta;
361     }
362     if (mst->pos - mst->off < sizeof (struct GNUNET_MessageHeader))
363     {
364       //FIXME should I reset ??
365       // mst->off = 0;
366       // mst->pos = 0;
367       return GNUNET_OK;
368     }
369     hdr = (const struct GNUNET_MessageHeader *) &ibuf[mst->off];
370     want = ntohs (hdr->size);
371     if (want < sizeof (struct GNUNET_MessageHeader))
372     {
373       fprintf (stderr,
374          "Received invalid message from stdin\n");
375       return GNUNET_SYSERR;
376     }
377     if ((mst->curr_buf - mst->off < want) &&
378        (mst->off > 0))
379     {
380       /* need more space */
381       mst->pos -= mst->off;
382       memmove (ibuf, &ibuf[mst->off], mst->pos);
383       mst->off = 0;
384     }
385     if (want > mst->curr_buf)
386     {
387       if (mst->off != 0)
388       {
389         fprintf (stderr, "Error! We should proceeded 0 bytes\n");
390         return GNUNET_SYSERR;
391       }
392       mst->hdr = realloc (mst->hdr, want);
393       if (NULL == mst->hdr)
394       {
395   fprintf (stderr, "Failed to allocate buffer for alignment\n");
396   exit (1);
397       }
398       ibuf = (char *) mst->hdr;
399       mst->curr_buf = want;
400     }
401     hdr = (const struct GNUNET_MessageHeader *) &ibuf[mst->off];
402     if (mst->pos - mst->off < want)
403     {
404       delta = GNUNET_MIN (want - (mst->pos - mst->off), size);
405       if (mst->pos + delta > mst->curr_buf)
406       {
407         fprintf (stderr, "The size of the buffer will be exceeded!\n");
408         return GNUNET_SYSERR;
409       }
410       GNUNET_memcpy (&ibuf[mst->pos], buf, delta);
411       mst->pos += delta;
412       buf += delta;
413       size -= delta;
414     }
415     if (mst->pos - mst->off < want)
416     {
417       //FIXME should I use this?
418       // mst->off = 0;
419       // mst->pos = 0;
420       return GNUNET_OK;
421     }
422     mst->cb (mst->cb_cls, hdr);
423     mst->off += want;
424     if (mst->off == mst->pos)
425     {
426       /* reset to beginning of buffer, it's free right now! */
427       mst->off = 0;
428       mst->pos = 0;
429     }
430   }
431   if (0 != mst->pos)
432   {
433     fprintf (stderr, "There should some valid bytes in the buffer on this stage\n");
434     return GNUNET_SYSERR;
435   }
436   while (size > 0)
437   {
438     if (size < sizeof (struct GNUNET_MessageHeader))
439       break;
440     offset = (unsigned long) buf;
441     need_align = (0 != offset % ALIGN_FACTOR) ? GNUNET_YES : GNUNET_NO;
442     if (GNUNET_NO == need_align)
443     {
444       /* can try to do zero-copy and process directly from original buffer */
445       hdr = (const struct GNUNET_MessageHeader *) buf;
446       want = ntohs (hdr->size);
447       if (want < sizeof (struct GNUNET_MessageHeader))
448       {
449   fprintf (stderr,
450      "Received invalid message from stdin\n");
451   //exit (1);
452         mst->off = 0;
453         return GNUNET_SYSERR;
454       }
455       if (size < want)
456         break;                  /* or not, buffer incomplete, so copy to private buffer... */
457       mst->cb (mst->cb_cls, hdr);
458       buf += want;
459       size -= want;
460     }
461     else
462     {
463       /* need to copy to private buffer to align;
464        * yes, we go a bit more spagetti than usual here */
465       goto do_align;
466     }
467   }
468   if (size > 0)
469   {
470     if (size + mst->pos > mst->curr_buf)
471     {
472       mst->hdr = realloc (mst->hdr, size + mst->pos);
473       if (NULL == mst->hdr)
474       {
475   fprintf (stderr, "Failed to allocate buffer for alignment\n");
476   exit (1);
477       }
478       ibuf = (char *) mst->hdr;
479       mst->curr_buf = size + mst->pos;
480     }
481     if (mst->pos + size > mst->curr_buf)
482     {
483       fprintf (stderr,
484          "Assertion failed\n");
485       exit (1);
486     }
487     GNUNET_memcpy (&ibuf[mst->pos], buf, size);
488     mst->pos += size;
489   }
490   return ret;
491 }
492
493 /**
494  * Destroys a tokenizer.
495  *
496  * @param mst tokenizer to destroy
497  */
498 static void
499 mst_destroy (struct MessageStreamTokenizer *mst)
500 {
501   free (mst->hdr);
502   free (mst);
503 }
504
505 /**
506  * Calculate crc32, the start of the calculation
507  *
508  * @param buf buffer to calc the crc
509  * @param len len of the buffer
510  * @return crc sum
511  */
512 static unsigned long
513 calc_crc_osdep (const unsigned char *buf, size_t len)
514 {
515   static const unsigned long int crc_tbl_osdep[256] = {
516     0x00000000, 0x77073096, 0xEE0E612C, 0x990951BA, 0x076DC419, 0x706AF48F,
517     0xE963A535, 0x9E6495A3,
518     0x0EDB8832, 0x79DCB8A4, 0xE0D5E91E, 0x97D2D988, 0x09B64C2B, 0x7EB17CBD,
519     0xE7B82D07, 0x90BF1D91,
520     0x1DB71064, 0x6AB020F2, 0xF3B97148, 0x84BE41DE, 0x1ADAD47D, 0x6DDDE4EB,
521     0xF4D4B551, 0x83D385C7,
522     0x136C9856, 0x646BA8C0, 0xFD62F97A, 0x8A65C9EC, 0x14015C4F, 0x63066CD9,
523     0xFA0F3D63, 0x8D080DF5,
524     0x3B6E20C8, 0x4C69105E, 0xD56041E4, 0xA2677172, 0x3C03E4D1, 0x4B04D447,
525     0xD20D85FD, 0xA50AB56B,
526     0x35B5A8FA, 0x42B2986C, 0xDBBBC9D6, 0xACBCF940, 0x32D86CE3, 0x45DF5C75,
527     0xDCD60DCF, 0xABD13D59,
528     0x26D930AC, 0x51DE003A, 0xC8D75180, 0xBFD06116, 0x21B4F4B5, 0x56B3C423,
529     0xCFBA9599, 0xB8BDA50F,
530     0x2802B89E, 0x5F058808, 0xC60CD9B2, 0xB10BE924, 0x2F6F7C87, 0x58684C11,
531     0xC1611DAB, 0xB6662D3D,
532     0x76DC4190, 0x01DB7106, 0x98D220BC, 0xEFD5102A, 0x71B18589, 0x06B6B51F,
533     0x9FBFE4A5, 0xE8B8D433,
534     0x7807C9A2, 0x0F00F934, 0x9609A88E, 0xE10E9818, 0x7F6A0DBB, 0x086D3D2D,
535     0x91646C97, 0xE6635C01,
536     0x6B6B51F4, 0x1C6C6162, 0x856530D8, 0xF262004E, 0x6C0695ED, 0x1B01A57B,
537     0x8208F4C1, 0xF50FC457,
538     0x65B0D9C6, 0x12B7E950, 0x8BBEB8EA, 0xFCB9887C, 0x62DD1DDF, 0x15DA2D49,
539     0x8CD37CF3, 0xFBD44C65,
540     0x4DB26158, 0x3AB551CE, 0xA3BC0074, 0xD4BB30E2, 0x4ADFA541, 0x3DD895D7,
541     0xA4D1C46D, 0xD3D6F4FB,
542     0x4369E96A, 0x346ED9FC, 0xAD678846, 0xDA60B8D0, 0x44042D73, 0x33031DE5,
543     0xAA0A4C5F, 0xDD0D7CC9,
544     0x5005713C, 0x270241AA, 0xBE0B1010, 0xC90C2086, 0x5768B525, 0x206F85B3,
545     0xB966D409, 0xCE61E49F,
546     0x5EDEF90E, 0x29D9C998, 0xB0D09822, 0xC7D7A8B4, 0x59B33D17, 0x2EB40D81,
547     0xB7BD5C3B, 0xC0BA6CAD,
548     0xEDB88320, 0x9ABFB3B6, 0x03B6E20C, 0x74B1D29A, 0xEAD54739, 0x9DD277AF,
549     0x04DB2615, 0x73DC1683,
550     0xE3630B12, 0x94643B84, 0x0D6D6A3E, 0x7A6A5AA8, 0xE40ECF0B, 0x9309FF9D,
551     0x0A00AE27, 0x7D079EB1,
552     0xF00F9344, 0x8708A3D2, 0x1E01F268, 0x6906C2FE, 0xF762575D, 0x806567CB,
553     0x196C3671, 0x6E6B06E7,
554     0xFED41B76, 0x89D32BE0, 0x10DA7A5A, 0x67DD4ACC, 0xF9B9DF6F, 0x8EBEEFF9,
555     0x17B7BE43, 0x60B08ED5,
556     0xD6D6A3E8, 0xA1D1937E, 0x38D8C2C4, 0x4FDFF252, 0xD1BB67F1, 0xA6BC5767,
557     0x3FB506DD, 0x48B2364B,
558     0xD80D2BDA, 0xAF0A1B4C, 0x36034AF6, 0x41047A60, 0xDF60EFC3, 0xA867DF55,
559     0x316E8EEF, 0x4669BE79,
560     0xCB61B38C, 0xBC66831A, 0x256FD2A0, 0x5268E236, 0xCC0C7795, 0xBB0B4703,
561     0x220216B9, 0x5505262F,
562     0xC5BA3BBE, 0xB2BD0B28, 0x2BB45A92, 0x5CB36A04, 0xC2D7FFA7, 0xB5D0CF31,
563     0x2CD99E8B, 0x5BDEAE1D,
564     0x9B64C2B0, 0xEC63F226, 0x756AA39C, 0x026D930A, 0x9C0906A9, 0xEB0E363F,
565     0x72076785, 0x05005713,
566     0x95BF4A82, 0xE2B87A14, 0x7BB12BAE, 0x0CB61B38, 0x92D28E9B, 0xE5D5BE0D,
567     0x7CDCEFB7, 0x0BDBDF21,
568     0x86D3D2D4, 0xF1D4E242, 0x68DDB3F8, 0x1FDA836E, 0x81BE16CD, 0xF6B9265B,
569     0x6FB077E1, 0x18B74777,
570     0x88085AE6, 0xFF0F6A70, 0x66063BCA, 0x11010B5C, 0x8F659EFF, 0xF862AE69,
571     0x616BFFD3, 0x166CCF45,
572     0xA00AE278, 0xD70DD2EE, 0x4E048354, 0x3903B3C2, 0xA7672661, 0xD06016F7,
573     0x4969474D, 0x3E6E77DB,
574     0xAED16A4A, 0xD9D65ADC, 0x40DF0B66, 0x37D83BF0, 0xA9BCAE53, 0xDEBB9EC5,
575     0x47B2CF7F, 0x30B5FFE9,
576     0xBDBDF21C, 0xCABAC28A, 0x53B39330, 0x24B4A3A6, 0xBAD03605, 0xCDD70693,
577     0x54DE5729, 0x23D967BF,
578     0xB3667A2E, 0xC4614AB8, 0x5D681B02, 0x2A6F2B94, 0xB40BBE37, 0xC30C8EA1,
579     0x5A05DF1B, 0x2D02EF8D
580   };
581
582   unsigned long crc = 0xFFFFFFFF;
583
584   for (; len > 0; len--, buf++)
585     crc = crc_tbl_osdep[(crc ^ *buf) & 0xFF] ^ (crc >> 8);
586   return (~crc);
587 }
588
589
590 /**
591  * Calculate and check crc of the bluetooth packet
592  *
593  * @param buf buffer of the packet, with len + 4 bytes of data,
594  *            the last 4 bytes being the checksum
595  * @param len length of the payload in data
596  * @return 0 on success (checksum matches), 1 on error
597  */
598 static int
599 check_crc_buf_osdep (const unsigned char *buf, size_t len)
600 {
601   unsigned long crc;
602
603   crc = calc_crc_osdep (buf, len);
604   buf += len;
605   if (((crc) & 0xFF) == buf[0] && ((crc >> 8) & 0xFF) == buf[1] &&
606       ((crc >> 16) & 0xFF) == buf[2] && ((crc >> 24) & 0xFF) == buf[3])
607     return 0;
608   return 1;
609 }
610
611
612
613 /* ************** end of clone  ***************** */
614
615 #ifdef MINGW
616   /**
617    * Function used to get the code of last error and to print the type of error.
618    */
619   static void
620   print_last_error()
621   {
622     LPVOID lpMsgBuf = NULL;
623
624     if (FormatMessage (FORMAT_MESSAGE_ALLOCATE_BUFFER | FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS,
625                     NULL, GetLastError(), 0, (LPTSTR) &lpMsgBuf, 0, NULL))
626       fprintf (stderr, "%s\n", (char *)lpMsgBuf);
627     else
628       fprintf (stderr, "Failed to format the message for the last error! Error number : %d\n", GetLastError());
629   }
630
631   /**
632    * Function used to initialize the Windows Sockets
633    */
634   static void
635   initialize_windows_sockets()
636   {
637     WSADATA wsaData ;
638     WORD wVersionRequested = MAKEWORD (2, 0);
639     if (WSAStartup (wVersionRequested, &wsaData) != NO_ERROR)
640     {
641       fprintf (stderr , "Error initializing window sockets!\n");
642       print_last_error();
643       ExitProcess (2) ;
644     }
645   }
646
647   /**
648    * Function used to convert the GUID.
649    * @param bytes the GUID represented as a char array
650    * @param uuid pointer to the GUID
651    */
652   static void
653   convert_guid(char *bytes, GUID * uuid)
654   {
655     int i;
656     uuid->Data1 = ((bytes[0] << 24) & 0xff000000) | ((bytes[1] << 16) & 0x00ff0000) | ((bytes[2] << 8) & 0x0000ff00) | (bytes[3] & 0x000000ff);
657     uuid->Data2 = ((bytes[4] << 8) & 0xff00) | (bytes[5] & 0x00ff);
658     uuid->Data3 = ((bytes[6] << 8) & 0xff00) | (bytes[7] & 0x00ff);
659
660     for (i = 0; i < 8; i++)
661     {
662       uuid->Data4[i] = bytes[i + 8];
663     }
664   }
665 #endif
666
667 #ifdef LINUX
668   /**
669    * Function for assigning a port number
670    *
671    * @param socket the socket used to bind
672    * @param addr pointer to the rfcomm address
673    * @return 0 on success
674    */
675   static int
676   bind_socket (int socket, struct sockaddr_rc *addr)
677   {
678     int port, status;
679
680     /* Bind every possible port (from 0 to 30) and stop when binding doesn't fail */
681     //FIXME : it should start from port 1, but on my computer it doesn't work :)
682     for (port = 3; port <= 30; port++)
683     {
684       addr->rc_channel = port;
685       status = bind (socket, (struct sockaddr *) addr, sizeof (struct sockaddr_rc));
686       if (status == 0)
687         return 0;
688     }
689
690     return -1;
691   }
692 #endif
693
694 #ifdef MINGW
695   /**
696    * Function used for creating the service record and registering it.
697    *
698    * @param dev pointer to the device struct
699    * @return 0 on success
700    */
701   static int
702   register_service (struct HardwareInfos *dev)
703   {
704     /* advertise the service */
705     CSADDR_INFO addr_info;
706     WSAQUERYSET wqs;
707     GUID guid;
708     unsigned char uuid[] = GNUNET_BLUETOOTH_SDP_UUID;
709     SOCKADDR_BTH addr;
710     int addr_len = sizeof (SOCKADDR_BTH);
711     int fd;
712     /* get the port on which we are listening on */
713     memset (& addr, 0, sizeof (SOCKADDR_BTH));
714     fd = GNUNET_NETWORK_get_fd (dev->handle);
715     if (fd <= 0)
716     {
717       fprintf (stderr, "Failed to get the file descriptor\n");
718       return -1;
719     }
720     if (SOCKET_ERROR == getsockname (fd, (SOCKADDR*)&addr, &addr_len))
721     {
722       fprintf (stderr, "Failed to get the port on which we are listening on: \n");
723       print_last_error();
724       return -1;
725     }
726
727     /* save the device address */
728     GNUNET_memcpy (&dev->pl_mac, &addr.btAddr, sizeof (BTH_ADDR));
729
730     /* set the address information */
731     memset (&addr_info, 0, sizeof (CSADDR_INFO));
732     addr_info.iProtocol = BTHPROTO_RFCOMM;
733     addr_info.iSocketType = SOCK_STREAM;
734     addr_info.LocalAddr.lpSockaddr = (LPSOCKADDR)&addr;
735     addr_info.LocalAddr.iSockaddrLength = sizeof (addr);
736     addr_info.RemoteAddr.lpSockaddr = (LPSOCKADDR)&addr;
737     addr_info.RemoteAddr.iSockaddrLength = sizeof (addr);
738
739     convert_guid((char *) uuid, &guid);
740
741     /* register the service */
742     memset (&wqs, 0, sizeof (WSAQUERYSET));
743     wqs.dwSize = sizeof (WSAQUERYSET);
744     wqs.dwNameSpace = NS_BTH;
745     wqs.lpszServiceInstanceName = "GNUnet Bluetooth Service";
746     wqs.lpszComment = "This is the service used by the GNUnnet plugin transport";
747     wqs.lpServiceClassId = &guid;
748     wqs.dwNumberOfCsAddrs = 1;
749     wqs.lpcsaBuffer = &addr_info ;
750     wqs.lpBlob = 0;
751
752     if (SOCKET_ERROR == WSASetService (&wqs , RNRSERVICE_REGISTER, 0))
753     {
754       fprintf (stderr, "Failed to register the SDP service: ");
755       print_last_error();
756       return -1;
757     }
758     else
759     {
760       fprintf (stderr, "The SDP service was registered\n");
761     }
762
763     return 0;
764   }
765 #else
766   /**
767    * Function used for creating the service record and registering it.
768    *
769    * @param dev pointer to the device struct
770    * @param rc_channel the rfcomm channel
771    * @return 0 on success
772    */
773   static int
774   register_service (struct HardwareInfos *dev, int rc_channel)
775   {
776     /**
777      * 1. initializations
778      * 2. set the service ID, class, profile information
779      * 3. make the service record publicly browsable
780      * 4. register the RFCOMM channel
781      * 5. set the name, provider and description
782      * 6. register the service record to the local SDP server
783      * 7. cleanup
784      */
785     uint8_t svc_uuid_int[] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
786                               dev->pl_mac.mac[5], dev->pl_mac.mac[4], dev->pl_mac.mac[3],
787                               dev->pl_mac.mac[2], dev->pl_mac.mac[1], dev->pl_mac.mac[0]};
788     const char *service_dsc = "Bluetooth plugin services";
789     const char *service_prov = "GNUnet provider";
790     uuid_t root_uuid, rfcomm_uuid, svc_uuid;
791     sdp_list_t *root_list = 0, *rfcomm_list = 0, *proto_list = 0,
792        *access_proto_list = 0, *svc_list = 0;
793     sdp_record_t *record = 0;
794     sdp_data_t *channel = 0;
795
796     record = sdp_record_alloc();
797
798     /* Set the general service ID */
799     sdp_uuid128_create (&svc_uuid, &svc_uuid_int);
800     svc_list = sdp_list_append (0, &svc_uuid);
801     sdp_set_service_classes (record, svc_list);
802     sdp_set_service_id (record, svc_uuid);
803
804     /* Make the service record publicly browsable */
805     sdp_uuid16_create (&root_uuid, PUBLIC_BROWSE_GROUP);
806     root_list = sdp_list_append (0, &root_uuid);
807     sdp_set_browse_groups (record, root_list);
808
809     /* Register the RFCOMM channel */
810     sdp_uuid16_create (&rfcomm_uuid, RFCOMM_UUID);
811     channel = sdp_data_alloc (SDP_UINT8, &rc_channel);
812     rfcomm_list = sdp_list_append (0, &rfcomm_uuid);
813     sdp_list_append (rfcomm_list, channel);
814     proto_list = sdp_list_append (0, rfcomm_list);
815
816     /* Set protocol information */
817     access_proto_list = sdp_list_append (0, proto_list);
818     sdp_set_access_protos (record, access_proto_list);
819
820     /* Set the name, provider, and description */
821     sdp_set_info_attr (record, dev->iface, service_prov, service_dsc);
822
823     /* Connect to the local SDP server */
824     dev->session = sdp_connect (BDADDR_ANY, BDADDR_LOCAL, SDP_RETRY_IF_BUSY);
825
826     if (!dev->session)
827     {
828       fprintf (stderr, "Failed to connect to the SDP server on interface `%.*s': %s\n",
829                IFNAMSIZ, dev->iface, strerror (errno));
830       //FIXME exit?
831       return 1;
832     }
833
834     /* Register the service record */
835     if (sdp_record_register (dev->session, record, 0) < 0)
836     {
837       fprintf (stderr, "Failed to register a service record on interface `%.*s': %s\n",
838                IFNAMSIZ, dev->iface, strerror (errno));
839       //FIXME exit?
840       return 1;
841     }
842
843     /* Cleanup */
844     sdp_data_free (channel);
845     sdp_list_free (root_list, 0);
846     sdp_list_free (rfcomm_list, 0);
847     sdp_list_free (proto_list, 0);
848     sdp_list_free (access_proto_list, 0);
849     sdp_list_free (svc_list, 0);
850     sdp_record_free (record);
851
852     return 0;
853   }
854 #endif
855
856 #ifdef MINGW
857   /**
858    * Function for searching and browsing for a service. This will return the
859    * port number on which the service is running.
860    *
861    * @param dest target address
862    * @return channel
863    */
864   static int
865   get_channel(const char *dest)
866   {
867     HANDLE h;
868     WSAQUERYSET *wqs;
869     DWORD wqs_len = sizeof (WSAQUERYSET);
870     int done = 0;
871     int channel = -1;
872     GUID guid;
873     unsigned char uuid[] = GNUNET_BLUETOOTH_SDP_UUID;
874     convert_guid ((char *) uuid, &guid);
875
876     wqs = (WSAQUERYSET*)malloc (wqs_len);
877     ZeroMemory (wqs, wqs_len);
878
879     wqs->dwSize = sizeof (WSAQUERYSET) ;
880     wqs->lpServiceClassId = &guid;
881     wqs->dwNameSpace = NS_BTH;
882     wqs->dwNumberOfCsAddrs = 0;
883     wqs->lpszContext = (LPSTR)dest;
884
885     if (SOCKET_ERROR == WSALookupServiceBegin (wqs,  LUP_FLUSHCACHE | LUP_RETURN_ALL, &h))
886     {
887       if (GetLastError() == WSASERVICE_NOT_FOUND)
888       {
889         fprintf (stderr, "WARNING! The device with address %s wasn't found. Skipping the message!", dest);
890         return -1;
891       }
892       else
893       {
894         fprintf (stderr, "Failed to find the port number: ");
895         print_last_error();
896         ExitProcess (2);
897         return -1;
898       }
899     }
900
901     /* search the sdp service */
902     while (!done)
903     {
904       if (SOCKET_ERROR == WSALookupServiceNext (h, LUP_FLUSHCACHE | LUP_RETURN_ALL, &wqs_len, wqs))
905       {
906         int error = WSAGetLastError();
907
908         switch (error)
909         {
910         case WSAEFAULT:
911           free (wqs);
912           wqs = (WSAQUERYSET*)malloc (wqs_len);
913           break;
914         case WSANO_DATA:
915           fprintf (stderr, "Failed! The address was valid but there was no data record of requested type\n");
916           done = 1;
917           break;
918         case WSA_E_NO_MORE:
919           done = 1;
920           break;
921         default:
922           fprintf (stderr, "Failed to look over the services: ");
923           print_last_error();
924           WSALookupServiceEnd (h);
925           ExitProcess (2);
926         }
927       }
928       else
929       {
930         channel = ((SOCKADDR_BTH*)wqs->lpcsaBuffer->RemoteAddr.lpSockaddr)->port;
931       }
932     }
933
934     free (wqs) ;
935     WSALookupServiceEnd (h);
936
937     return channel;
938   }
939 #else
940   /**
941    * Function used for searching and browsing for a service. This will return the
942    * port number on which the service is running.
943    *
944    * @param dev pointer to the device struct
945    * @param dest target address
946    * @return channel
947    */
948   static int
949   get_channel(struct HardwareInfos *dev, bdaddr_t dest)
950   {
951     /**
952      * 1. detect all nearby devices
953      * 2. for each device:
954      * 2.1. connect to the SDP server running
955      * 2.2. get a list of service records with the specific UUID
956      * 2.3. for each service record get a list of the protocol sequences and get
957      *       the port number
958      */
959     uint8_t svc_uuid_int[] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
960                              dest.b[5], dest.b[4], dest.b[3],
961                              dest.b[2], dest.b[1], dest.b[0]};
962     sdp_session_t *session = 0;
963     sdp_list_t *search_list = 0, *attrid_list = 0, *response_list = 0, *it = 0;
964     uuid_t svc_uuid;
965     uint32_t range = 0x0000ffff;
966     int channel = -1;
967
968     /* Connect to the local SDP server */
969     session = sdp_connect (BDADDR_ANY, &dest, 0);
970     if (!session)
971     {
972      fprintf (stderr, "Failed to connect to the SDP server on interface `%.*s': %s\n",
973               IFNAMSIZ, dev->iface, strerror (errno));
974      return -1;
975     }
976
977     sdp_uuid128_create (&svc_uuid, &svc_uuid_int);
978     search_list = sdp_list_append (0, &svc_uuid);
979     attrid_list = sdp_list_append (0, &range);
980
981     if (sdp_service_search_attr_req (session, search_list,
982                     SDP_ATTR_REQ_RANGE, attrid_list, &response_list) == 0)
983     {
984       for (it = response_list; it; it = it->next)
985       {
986         sdp_record_t *record = (sdp_record_t*) it->data;
987         sdp_list_t *proto_list = 0;
988         if (sdp_get_access_protos (record, &proto_list) == 0)
989         {
990           channel = sdp_get_proto_port (proto_list, RFCOMM_UUID);
991           sdp_list_free (proto_list, 0);
992         }
993         sdp_record_free (record);
994       }
995     }
996
997     sdp_list_free (search_list, 0);
998     sdp_list_free (attrid_list, 0);
999     sdp_list_free (response_list, 0);
1000
1001     sdp_close (session);
1002
1003     if (-1 == channel)
1004       fprintf (stderr,
1005                "Failed to find the listening channel for interface `%.*s': %s\n",
1006                IFNAMSIZ,
1007                dev->iface,
1008                strerror (errno));
1009
1010     return channel;
1011   }
1012 #endif
1013
1014 /**
1015  * Read from the socket and put the result into the buffer for transmission to 'stdout'.
1016  *
1017  * @param sock file descriptor for reading
1018  * @param buf buffer to read to; first bytes will be the 'struct GNUNET_TRANSPORT_WLAN_Ieee80211Frame',
1019  *            followed by the actual payload
1020  * @param buf_size size of the buffer
1021  * @param ri where to write radiotap_rx info
1022  * @return number of bytes written to 'buf'
1023  */
1024 static ssize_t
1025 read_from_the_socket (void *sock,
1026       unsigned char *buf, size_t buf_size,
1027             struct GNUNET_TRANSPORT_WLAN_RadiotapReceiveMessage *ri)
1028 {
1029   unsigned char tmpbuf[buf_size];
1030   ssize_t count;
1031
1032   #ifdef MINGW
1033    count = GNUNET_NETWORK_socket_recv ((struct GNUNET_NETWORK_Handle *)sock, tmpbuf, buf_size);
1034   #else
1035    count = read (*((int *)sock), tmpbuf, buf_size);
1036   #endif
1037
1038   if (0 > count)
1039   {
1040     if (EAGAIN == errno)
1041       return 0;
1042     #if MINGW
1043      print_last_error();
1044     #else
1045      fprintf (stderr, "Failed to read from the HCI socket: %s\n", strerror (errno));
1046     #endif
1047
1048     return -1;
1049   }
1050
1051   #ifdef LINUX
1052    /* Get the channel used */
1053    int len;
1054    struct sockaddr_rc  rc_addr = { 0 };
1055
1056    memset (&rc_addr, 0, sizeof (rc_addr));
1057    len = sizeof (rc_addr);
1058    if (0 > getsockname (*((int *)sock), (struct sockaddr *) &rc_addr, (socklen_t *) &len))
1059    {
1060      fprintf (stderr, "getsockname() call failed : %s\n", strerror (errno));
1061      return -1;
1062    }
1063
1064    memset (ri, 0, sizeof (*ri));
1065    ri->ri_channel = rc_addr.rc_channel;
1066   #endif
1067
1068   /* Detect CRC32 at the end */
1069   if (0 == check_crc_buf_osdep (tmpbuf, count - sizeof (uint32_t)))
1070   {
1071     count -= sizeof(uint32_t);
1072   }
1073
1074   GNUNET_memcpy (buf, tmpbuf, count);
1075
1076   return count;
1077 }
1078
1079
1080 /**
1081  * Open the bluetooth interface for reading/writing
1082  *
1083  * @param dev pointer to the device struct
1084  * @return 0 on success, non-zero on error
1085  */
1086 static int
1087 open_device (struct HardwareInfos *dev)
1088 {
1089   #ifdef MINGW
1090     SOCKADDR_BTH addr;
1091
1092     /* bind the RFCOMM socket to the interface */
1093     addr.addressFamily = AF_BTH;
1094     addr.btAddr = 0;
1095     addr.port = BT_PORT_ANY;
1096
1097     if (GNUNET_OK !=
1098         GNUNET_NETWORK_socket_bind (dev->handle, (const SOCKADDR*)&addr, sizeof (SOCKADDR_BTH)))
1099     {
1100       fprintf (stderr, "Failed to bind the socket: ");
1101       if (GetLastError() == WSAENETDOWN)
1102       {
1103         fprintf (stderr, "Please make sure that your Bluetooth device is ON!\n");
1104         ExitProcess (2);
1105       }
1106       print_last_error();
1107       return -1;
1108     }
1109
1110     /* start listening on the socket */
1111     if (GNUNET_NETWORK_socket_listen (dev->handle, 4) != GNUNET_OK)
1112     {
1113       fprintf (stderr, "Failed to listen on the socket: ");
1114       print_last_error();
1115       return -1;
1116     }
1117
1118     /* register the sdp service */
1119     if (register_service(dev) != 0)
1120     {
1121       fprintf (stderr, "Failed to register a service: ");
1122       print_last_error();
1123       return 1;
1124     }
1125   #else
1126     int i, dev_id = -1, fd_hci;
1127     struct
1128     {
1129       struct hci_dev_list_req list;
1130       struct hci_dev_req dev[HCI_MAX_DEV];
1131     } request;                              //used for detecting the local devices
1132     struct sockaddr_rc rc_addr = { 0 };    //used for binding
1133
1134     /* Initialize the neighbour structure */
1135     neighbours.dev_id = -1;
1136     for (i = 0; i < MAX_PORTS; i++)
1137       neighbours.fds[i] = -1;
1138
1139     /* Open a HCI socket */
1140     fd_hci = socket (AF_BLUETOOTH, SOCK_RAW, BTPROTO_HCI);
1141
1142     if (fd_hci < 0)
1143     {
1144       fprintf (stderr,
1145                "Failed to create HCI socket: %s\n",
1146                strerror (errno));
1147       return -1;
1148     }
1149
1150     memset (&request, 0, sizeof(request));
1151     request.list.dev_num = HCI_MAX_DEV;
1152
1153     if (ioctl (fd_hci, HCIGETDEVLIST, (void *) &request) < 0)
1154     {
1155       fprintf (stderr,
1156                "ioctl(HCIGETDEVLIST) on interface `%.*s' failed: %s\n",
1157                IFNAMSIZ,
1158                dev->iface,
1159                strerror (errno));
1160       (void) close (fd_hci);
1161       return 1;
1162     }
1163
1164     /* Search for a device with dev->iface name */
1165     for (i = 0; i < request.list.dev_num; i++)
1166     {
1167       struct hci_dev_info dev_info;
1168
1169       memset (&dev_info, 0, sizeof(struct hci_dev_info));
1170       dev_info.dev_id = request.dev[i].dev_id;
1171       strncpy (dev_info.name, dev->iface, BLUEZ_DEVNAME_SIZE);
1172
1173       if (ioctl (fd_hci, HCIGETDEVINFO, (void *) &dev_info))
1174       {
1175         fprintf (stderr,
1176                  "ioctl(HCIGETDEVINFO) on interface `%.*s' failed: %s\n",
1177                  IFNAMSIZ,
1178                  dev->iface,
1179                  strerror (errno));
1180         (void) close (fd_hci);
1181         return 1;
1182       }
1183
1184       if (strncmp (dev_info.name, dev->iface, BLUEZ_DEVNAME_SIZE) == 0)
1185       {
1186
1187         dev_id = dev_info.dev_id; //the device was found
1188         /**
1189          * Copy the MAC address to the device structure
1190          */
1191         GNUNET_memcpy (&dev->pl_mac, &dev_info.bdaddr, sizeof (bdaddr_t));
1192
1193         /* Check if the interface is up */
1194         if (hci_test_bit (HCI_UP, (void *) &dev_info.flags) == 0)
1195         {
1196           /* Bring the interface up */
1197           if (ioctl (fd_hci, HCIDEVUP, dev_info.dev_id))
1198           {
1199             fprintf (stderr,
1200                      "ioctl(HCIDEVUP) on interface `%.*s' failed: %s\n",
1201                      IFNAMSIZ,
1202                      dev->iface,
1203                      strerror (errno));
1204             (void) close (fd_hci);
1205             return 1;
1206           }
1207         }
1208
1209         /* Check if the device is discoverable */
1210         if (hci_test_bit (HCI_PSCAN, (void *) &dev_info.flags) == 0 ||
1211             hci_test_bit (HCI_ISCAN, (void *) &dev_info.flags) == 0)
1212         {
1213           /* Set interface Page Scan and Inqury Scan ON */
1214           struct hci_dev_req dev_req;
1215
1216           memset (&dev_req, 0, sizeof (dev_req));
1217           dev_req.dev_id = dev_info.dev_id;
1218           dev_req.dev_opt = SCAN_PAGE | SCAN_INQUIRY;
1219
1220           if (ioctl (fd_hci, HCISETSCAN, (unsigned long) &dev_req))
1221           {
1222             fprintf (stderr,
1223                      "ioctl(HCISETSCAN) on interface `%.*s' failed: %s\n",
1224                      IFNAMSIZ,
1225                      dev->iface,
1226                      strerror (errno));
1227             (void) close (fd_hci);
1228             return 1;
1229           }
1230
1231         }
1232         break;
1233       }
1234
1235     }
1236
1237     /* Check if the interface was not found */
1238     if (-1 == dev_id)
1239     {
1240       fprintf (stderr,
1241                "The interface %s was not found\n",
1242                dev->iface);
1243       (void) close (fd_hci);
1244       return 1;
1245     }
1246
1247     /* Close the hci socket */
1248     (void) close(fd_hci);
1249
1250
1251
1252     /* Bind the rfcomm socket to the interface */
1253     memset (&rc_addr, 0, sizeof (rc_addr));
1254     rc_addr.rc_family = AF_BLUETOOTH;
1255     rc_addr.rc_bdaddr = *BDADDR_ANY;
1256
1257     if (bind_socket (dev->fd_rfcomm, &rc_addr) != 0)
1258     {
1259       fprintf (stderr,
1260                "Failed to bind interface `%.*s': %s\n",
1261                IFNAMSIZ,
1262                dev->iface,
1263                strerror (errno));
1264       return 1;
1265     }
1266
1267     /* Register a SDP service */
1268     if (register_service (dev, rc_addr.rc_channel) != 0)
1269     {
1270       fprintf (stderr,
1271                "Failed to register a service on interface `%.*s': %s\n",
1272                IFNAMSIZ,
1273                dev->iface, strerror (errno));
1274       return 1;
1275     }
1276
1277     /* Switch socket in listening mode */
1278     if (listen (dev->fd_rfcomm, 5) == -1) //FIXME: probably we need a bigger number
1279     {
1280       fprintf (stderr, "Failed to listen on socket for interface `%.*s': %s\n", IFNAMSIZ,
1281                dev->iface, strerror (errno));
1282       return 1;
1283     }
1284
1285   #endif
1286
1287   return 0;
1288 }
1289
1290
1291 /**
1292  * Set the header to sane values to make attacks more difficult
1293  *
1294  * @param taIeeeHeader pointer to the header of the packet
1295  * @param dev pointer to the Hardware_Infos struct
1296  *
1297  **** copy from gnunet-helper-transport-wlan.c ****
1298  */
1299 static void
1300 mac_set (struct GNUNET_TRANSPORT_WLAN_Ieee80211Frame *taIeeeHeader,
1301          const struct HardwareInfos *dev)
1302 {
1303   taIeeeHeader->frame_control = htons (IEEE80211_FC0_TYPE_DATA);
1304   taIeeeHeader->addr3 = mac_bssid_gnunet;
1305
1306   #ifdef MINGW
1307     GNUNET_memcpy (&taIeeeHeader->addr2, &dev->pl_mac, sizeof (struct GNUNET_TRANSPORT_WLAN_MacAddress));
1308   #else
1309     taIeeeHeader->addr2 = dev->pl_mac;
1310   #endif
1311 }
1312
1313 #ifdef LINUX
1314   /**
1315    * Test if the given interface name really corresponds to a bluetooth
1316    * device.
1317    *
1318    * @param iface name of the interface
1319    * @return 0 on success, 1 on error
1320    **** similar with the one from gnunet-helper-transport-wlan.c ****
1321    */
1322   static int
1323   test_bluetooth_interface (const char *iface)
1324   {
1325     char strbuf[512];
1326     struct stat sbuf;
1327     int ret;
1328
1329     ret = snprintf (strbuf, sizeof (strbuf),
1330         "/sys/class/bluetooth/%s/subsystem",
1331         iface);
1332     if ((ret < 0) || (ret >= sizeof (strbuf)) || (0 != stat (strbuf, &sbuf)))
1333     {
1334       fprintf (stderr,
1335          "Did not find 802.15.1 interface `%s'. Exiting.\n",
1336          iface);
1337       exit (1);
1338     }
1339     return 0;
1340   }
1341 #endif
1342
1343 /**
1344  * Test incoming packets mac for being our own.
1345  *
1346  * @param taIeeeHeader buffer of the packet
1347  * @param dev the Hardware_Infos struct
1348  * @return 0 if mac belongs to us, 1 if mac is for another target
1349  *
1350  **** same as the one from gnunet-helper-transport-wlan.c ****
1351  */
1352 static int
1353 mac_test (const struct GNUNET_TRANSPORT_WLAN_Ieee80211Frame *taIeeeHeader,
1354           const struct HardwareInfos *dev)
1355 {
1356   static struct GNUNET_TRANSPORT_WLAN_MacAddress all_zeros;
1357
1358   if ( (0 == memcmp (&taIeeeHeader->addr3, &all_zeros, MAC_ADDR_SIZE)) ||
1359        (0 == memcmp (&taIeeeHeader->addr1, &all_zeros, MAC_ADDR_SIZE)) )
1360     return 0; /* some drivers set no Macs, then assume it is all for us! */
1361
1362   if (0 != memcmp (&taIeeeHeader->addr3, &mac_bssid_gnunet, MAC_ADDR_SIZE))
1363     return 1; /* not a GNUnet ad-hoc package */
1364   if ( (0 == memcmp (&taIeeeHeader->addr1, &dev->pl_mac, MAC_ADDR_SIZE)) ||
1365        (0 == memcmp (&taIeeeHeader->addr1, &bc_all_mac, MAC_ADDR_SIZE)) )
1366     return 0; /* for us, or broadcast */
1367   return 1; /* not for us */
1368 }
1369
1370
1371 /**
1372  * Process data from the stdin. Takes the message, forces the sender MAC to be correct
1373  * and puts it into our buffer for transmission to the receiver.
1374  *
1375  * @param cls pointer to the device struct ('struct HardwareInfos*')
1376  * @param hdr pointer to the start of the packet
1377  *
1378  **** same as the one from gnunet-helper-transport-wlan.c ****
1379  */
1380 static void
1381 stdin_send_hw (void *cls, const struct GNUNET_MessageHeader *hdr)
1382 {
1383   struct HardwareInfos *dev = cls;
1384   const struct GNUNET_TRANSPORT_WLAN_RadiotapSendMessage *header;
1385   struct GNUNET_TRANSPORT_WLAN_Ieee80211Frame *blueheader;
1386   size_t sendsize;
1387
1388   sendsize = ntohs (hdr->size);
1389   if ( (sendsize <
1390   sizeof (struct GNUNET_TRANSPORT_WLAN_RadiotapSendMessage)) ||
1391        (GNUNET_MESSAGE_TYPE_WLAN_DATA_TO_HELPER != ntohs (hdr->type)) )
1392   {
1393     fprintf (stderr, "Received malformed message\n");
1394     exit (1);
1395   }
1396   sendsize -= (sizeof (struct GNUNET_TRANSPORT_WLAN_RadiotapSendMessage) -
1397                sizeof (struct GNUNET_TRANSPORT_WLAN_Ieee80211Frame));
1398   if (MAXLINE < sendsize)
1399   {
1400     fprintf (stderr, "Packet too big for buffer\n");
1401     exit (1);
1402   }
1403   header = (const struct GNUNET_TRANSPORT_WLAN_RadiotapSendMessage *) hdr;
1404   GNUNET_memcpy (&write_pout.buf, &header->frame, sendsize);
1405   blueheader = (struct GNUNET_TRANSPORT_WLAN_Ieee80211Frame *) &write_pout.buf;
1406
1407   /* payload contains MAC address, but we don't trust it, so we'll
1408   * overwrite it with OUR MAC address to prevent mischief */
1409   mac_set (blueheader, dev);
1410   GNUNET_memcpy (&blueheader->addr1, &header->frame.addr1,
1411           sizeof (struct GNUNET_TRANSPORT_WLAN_MacAddress));
1412   write_pout.size = sendsize;
1413 }
1414
1415 #ifdef LINUX
1416   /**
1417    * Broadcast a HELLO message for peer discovery
1418    *
1419    * @param dev pointer to the device struct
1420    * @param dev pointer to the socket which was added to the set
1421    * @return 0 on success
1422    */
1423   static int
1424   send_broadcast (struct HardwareInfos *dev, int *sendsocket)
1425   {
1426     int new_device = 0;
1427     int loops = 0;
1428
1429    search_for_devices:
1430     if ((neighbours.size == neighbours.pos && new_device == 1) || neighbours.size == 0)
1431     {
1432    inquiry_devices:   //skip the conditions and force a inquiry for new devices
1433       {
1434       /**
1435        * It means that I sent HELLO messages to all the devices from the list and I should search
1436        * for new ones or that this is the first time when I do a search.
1437        */
1438       inquiry_info *devices = NULL;
1439       int i, responses, max_responses = MAX_PORTS;
1440
1441       /* sanity checks */
1442       if (neighbours.size >= MAX_PORTS)
1443       {
1444         fprintf (stderr, "%.*s reached the top limit for the discovarable devices\n", IFNAMSIZ, dev->iface);
1445         return 2;
1446       }
1447
1448       /* Get the device id */
1449       if (neighbours.dev_id == -1)
1450       {
1451         char addr[19] = { 0 }; //the device MAC address
1452
1453         ba2str ((bdaddr_t *) &dev->pl_mac, addr);
1454         neighbours.dev_id = hci_devid (addr);
1455         if (neighbours.dev_id < 0)
1456         {
1457           fprintf (stderr, "Failed to get the device id for interface %.*s : %s\n", IFNAMSIZ,
1458                   dev->iface, strerror (errno));
1459           return 1;
1460         }
1461       }
1462
1463       devices = malloc (max_responses * sizeof (inquiry_info));
1464       if (devices == NULL)
1465       {
1466         fprintf (stderr, "Failed to allocate memory for inquiry info list on interface %.*s\n", IFNAMSIZ,
1467                 dev->iface);
1468         return 1;
1469       }
1470
1471       responses = hci_inquiry (neighbours.dev_id, 8, max_responses, NULL, &devices, IREQ_CACHE_FLUSH);
1472       if (responses < 0)
1473       {
1474         fprintf (stderr, "Failed to inquiry on interface %.*s\n", IFNAMSIZ, dev->iface);
1475         return 1;
1476       }
1477
1478       fprintf (stderr, "LOG : Found %d devices\n", responses); //FIXME delete it after debugging stage
1479
1480       if (responses == 0)
1481       {
1482         fprintf (stderr, "LOG : No devices discoverable\n");
1483         return 1;
1484       }
1485
1486       for (i = 0; i < responses; i++)
1487       {
1488         int j;
1489         int found = 0;
1490
1491         /* sanity check */
1492         if (i >= MAX_PORTS)
1493         {
1494           fprintf (stderr, "%.*s reached the top limit for the discoverable devices (after inquiry)\n", IFNAMSIZ,
1495                   dev->iface);
1496           return 2;
1497         }
1498
1499         /* Search if the address already exists on the list */
1500         for (j = 0; j < neighbours.size; j++)
1501         {
1502           if (memcmp (&(devices + i)->bdaddr, &(neighbours.devices[j]), sizeof (bdaddr_t)) == 0)
1503           {
1504             found = 1;
1505             fprintf (stderr, "LOG : the device already exists on the list\n"); //FIXME debugging message
1506             break;
1507           }
1508         }
1509
1510         if (found == 0)
1511         {
1512           char addr[19] = { 0 };
1513
1514           ba2str (&(devices +i)->bdaddr, addr);
1515           fprintf (stderr, "LOG : %s was added to the list\n", addr); //FIXME debugging message
1516           GNUNET_memcpy (&(neighbours.devices[neighbours.size++]), &(devices + i)->bdaddr, sizeof (bdaddr_t));
1517         }
1518       }
1519
1520       free (devices);
1521       }
1522     }
1523
1524     int connection_successful = 0;
1525     struct sockaddr_rc addr_rc = { 0 };
1526     int errno_copy = 0;
1527     addr_rc.rc_family = AF_BLUETOOTH;
1528
1529     /* Try to connect to a new device from the list */
1530     while (neighbours.pos < neighbours.size)
1531     {
1532       /* Check if we are already connected to this device */
1533       if (neighbours.fds[neighbours.pos] == -1)
1534       {
1535
1536         memset (&addr_rc.rc_bdaddr, 0, sizeof (addr_rc.rc_bdaddr));
1537         GNUNET_memcpy (&addr_rc.rc_bdaddr, &(neighbours.devices[neighbours.pos]), sizeof (addr_rc.rc_bdaddr));
1538
1539         addr_rc.rc_channel = get_channel (dev, addr_rc.rc_bdaddr);
1540
1541         *sendsocket = socket (AF_BLUETOOTH, SOCK_STREAM, BTPROTO_RFCOMM);
1542         if ( (-1 < *sendsocket) &&
1543              (0 == connect (*sendsocket,
1544                             (struct sockaddr *) &addr_rc,
1545                             sizeof (addr_rc))) )
1546         {
1547           neighbours.fds[neighbours.pos++] = *sendsocket;
1548           connection_successful = 1;
1549           char addr[19] = { 0 };
1550           ba2str (&(neighbours.devices[neighbours.pos - 1]), addr);
1551           fprintf (stderr, "LOG : Connected to %s\n", addr);
1552           break;
1553         }
1554         else
1555         {
1556           char addr[19] = { 0 };
1557           errno_copy = errno;  //Save a copy for later
1558
1559           if (-1 != *sendsocket)
1560           {
1561             (void) close (*sendsocket);
1562             *sendsocket = -1;
1563           }
1564           ba2str (&(neighbours.devices[neighbours.pos]), addr);
1565           fprintf (stderr,
1566                    "LOG : Couldn't connect on device %s, error : %s\n",
1567                    addr,
1568                    strerror (errno));
1569           if (errno != ECONNREFUSED) //FIXME be sure that this works
1570           {
1571             fprintf (stderr, "LOG : Removes %d device from the list\n", neighbours.pos);
1572             /* Remove the device from the list */
1573             GNUNET_memcpy (&neighbours.devices[neighbours.pos], &neighbours.devices[neighbours.size - 1], sizeof (bdaddr_t));
1574             memset (&neighbours.devices[neighbours.size - 1], 0, sizeof (bdaddr_t));
1575             neighbours.fds[neighbours.pos] = neighbours.fds[neighbours.size - 1];
1576             neighbours.fds[neighbours.size - 1] = -1;
1577             neighbours.size -= 1;
1578           }
1579
1580           neighbours.pos += 1;
1581
1582           if (neighbours.pos >= neighbours.size)
1583               neighbours.pos = 0;
1584
1585           loops += 1;
1586
1587           if (loops == MAX_LOOPS) //don't get stuck trying to connect to one device
1588             return 1;
1589         }
1590       }
1591       else
1592       {
1593         fprintf (stderr, "LOG : Search for a new device\n"); //FIXME debugging message
1594         neighbours.pos += 1;
1595       }
1596     }
1597
1598     /* Cycle on the list */
1599     if (neighbours.pos == neighbours.size)
1600     {
1601       neighbours.pos = 0;
1602       searching_devices_count += 1;
1603
1604       if (searching_devices_count == MAX_LOOPS)
1605       {
1606         fprintf (stderr, "LOG : Force to inquiry for new devices\n");
1607         searching_devices_count = 0;
1608         goto inquiry_devices;
1609       }
1610     }
1611    /* If a new device wasn't found, search an old one */
1612     if (connection_successful == 0)
1613     {
1614       int loop_check = neighbours.pos;
1615       while (neighbours.fds[neighbours.pos] == -1)
1616       {
1617         if (neighbours.pos == neighbours.size)
1618           neighbours.pos = 0;
1619
1620         if (neighbours.pos == loop_check)
1621         {
1622           if (errno_copy == ECONNREFUSED)
1623           {
1624             fprintf (stderr, "LOG : No device found. Go back and search again\n"); //FIXME debugging message
1625             new_device = 1;
1626             loops += 1;
1627             goto search_for_devices;
1628           }
1629           else
1630           {
1631             return 1; // Skip the broadcast message
1632           }
1633         }
1634
1635         neighbours.pos += 1;
1636       }
1637
1638       *sendsocket = neighbours.fds[neighbours.pos++];
1639     }
1640
1641     return 0;
1642   }
1643 #endif
1644
1645 /**
1646  * Main function of the helper.  This code accesses a bluetooth interface
1647  * forwards traffic in both directions between the bluetooth interface and
1648  * stdin/stdout of this process.  Error messages are written to stderr.
1649  *
1650  * @param argc number of arguments, must be 2
1651  * @param argv arguments only argument is the name of the interface (i.e. 'hci0')
1652  * @return 0 on success (never happens, as we don't return unless aborted), 1 on error
1653  *
1654  **** similar to gnunet-helper-transport-wlan.c ****
1655  */
1656 int
1657 main (int argc, char *argv[])
1658 {
1659 #ifdef LINUX
1660     struct HardwareInfos dev;
1661     char readbuf[MAXLINE];
1662     int maxfd;
1663     fd_set rfds;
1664     fd_set wfds;
1665     int stdin_open;
1666     struct MessageStreamTokenizer *stdin_mst;
1667     int raw_eno, i;
1668     int crt_rfds = 0, rfds_list[MAX_PORTS];
1669     int broadcast, sendsocket;
1670
1671     /* Assert privs so we can modify the firewall rules! */
1672     {
1673 #ifdef HAVE_SETRESUID
1674       uid_t uid = getuid ();
1675
1676       if (0 != setresuid (uid, 0, 0))
1677       {
1678         fprintf (stderr, 
1679                  "Failed to setresuid to root: %s\n",
1680                  strerror (errno));
1681         return 254;
1682       }
1683 #else
1684       if (0 != seteuid (0))
1685       {
1686         fprintf (stderr, 
1687                  "Failed to seteuid back to root: %s\n", strerror (errno));
1688         return 254;
1689       }
1690 #endif
1691     }
1692
1693     /* Make use of SGID capabilities on POSIX */
1694     memset (&dev, 0, sizeof (dev));
1695     dev.fd_rfcomm = socket (AF_BLUETOOTH, SOCK_STREAM, BTPROTO_RFCOMM);
1696     raw_eno = errno; /* remember for later */
1697
1698     /* Now that we've dropped root rights, we can do error checking */
1699     if (2 != argc)
1700     {
1701       fprintf (stderr, "You must specify the name of the interface as the first \
1702                         and only argument to this program.\n");
1703       if (-1 != dev.fd_rfcomm)
1704         (void) close (dev.fd_rfcomm);
1705       return 1;
1706     }
1707
1708     if (-1 == dev.fd_rfcomm)
1709     {
1710       fprintf (stderr, "Failed to create a RFCOMM socket: %s\n", strerror (raw_eno));
1711       return 1;
1712     }
1713     if (dev.fd_rfcomm >= FD_SETSIZE)
1714     {
1715       fprintf (stderr, "File descriptor too large for select (%d > %d)\n",
1716                dev.fd_rfcomm, FD_SETSIZE);
1717       (void) close (dev.fd_rfcomm);
1718       return 1;
1719     }
1720     if (0 != test_bluetooth_interface (argv[1]))
1721     {
1722       (void) close (dev.fd_rfcomm);
1723       return 1;
1724     }
1725     strncpy (dev.iface, argv[1], IFNAMSIZ);
1726     if (0 != open_device (&dev))
1727     {
1728       (void) close (dev.fd_rfcomm);
1729       return 1;
1730     }
1731
1732     /* Drop privs */
1733     {
1734       uid_t uid = getuid ();
1735   #ifdef HAVE_SETRESUID
1736       if (0 != setresuid (uid, uid, uid))
1737       {
1738         fprintf (stderr, "Failed to setresuid: %s\n", strerror (errno));
1739         if (-1 != dev.fd_rfcomm)
1740     (void) close (dev.fd_rfcomm);
1741         return 1;
1742       }
1743   #else
1744       if (0 != (setuid (uid) | seteuid (uid)))
1745       {
1746         fprintf (stderr, "Failed to setuid: %s\n", strerror (errno));
1747         if (-1 != dev.fd_rfcomm)
1748     (void) close (dev.fd_rfcomm);
1749         return 1;
1750       }
1751   #endif
1752     }
1753
1754    /* Send MAC address of the bluetooth interface to STDOUT first */
1755     {
1756       struct GNUNET_TRANSPORT_WLAN_HelperControlMessage macmsg;
1757
1758       macmsg.hdr.size = htons (sizeof (macmsg));
1759       macmsg.hdr.type = htons (GNUNET_MESSAGE_TYPE_WLAN_HELPER_CONTROL);
1760       GNUNET_memcpy (&macmsg.mac, &dev.pl_mac, sizeof (struct GNUNET_TRANSPORT_WLAN_MacAddress));
1761       GNUNET_memcpy (write_std.buf, &macmsg, sizeof (macmsg));
1762       write_std.size = sizeof (macmsg);
1763     }
1764
1765
1766     stdin_mst = mst_create (&stdin_send_hw, &dev);
1767     stdin_open = 1;
1768
1769    /**
1770     * TODO : I should make the time out of a mac endpoint smaller and check if the rate
1771     * from get_wlan_header (plugin_transport_bluetooth.c) is correct.
1772     */
1773    while (1)
1774     {
1775       maxfd = -1;
1776       broadcast = 0;
1777       sendsocket = -1;
1778
1779       FD_ZERO (&rfds);
1780       if ((0 == write_pout.size) && (1 == stdin_open))
1781       {
1782         FD_SET (STDIN_FILENO, &rfds);
1783         maxfd = MAX (maxfd, STDIN_FILENO);
1784       }
1785       if (0 == write_std.size)
1786       {
1787         FD_SET (dev.fd_rfcomm, &rfds);
1788         maxfd = MAX (maxfd, dev.fd_rfcomm);
1789       }
1790
1791       for (i = 0; i < crt_rfds; i++)  // it can receive messages from multiple devices
1792       {
1793         FD_SET (rfds_list[i], &rfds);
1794         maxfd = MAX (maxfd, rfds_list[i]);
1795       }
1796       FD_ZERO (&wfds);
1797       if (0 < write_std.size)
1798       {
1799         FD_SET (STDOUT_FILENO, &wfds);
1800         maxfd = MAX (maxfd, STDOUT_FILENO);
1801       }
1802       if (0 < write_pout.size) //it can send messages only to one device per loop
1803       {
1804         struct GNUNET_TRANSPORT_WLAN_Ieee80211Frame *frame;
1805         /* Get the destination address */
1806         frame = (struct GNUNET_TRANSPORT_WLAN_Ieee80211Frame *) write_pout.buf;
1807
1808         if (memcmp (&frame->addr1, &dev.pl_mac,
1809                     sizeof (struct GNUNET_TRANSPORT_WLAN_MacAddress)) == 0)
1810         {
1811           broadcast = 1;
1812           memset (&write_pout, 0, sizeof (write_pout)); //clear the buffer
1813         }
1814         else if (memcmp (&frame->addr1, &broadcast_address,
1815                   sizeof (struct GNUNET_TRANSPORT_WLAN_MacAddress)) == 0)
1816         {
1817           fprintf (stderr, "LOG : %s has a broadcast message (pos %d, size %d)\n", dev.iface, neighbours.pos, neighbours.size); //FIXME: debugging message
1818
1819           if (send_broadcast(&dev, &sendsocket) != 0) //if the searching wasn't successful don't get stuck on the select stage
1820           {
1821             broadcast = 1;
1822             memset (&write_pout, 0, sizeof (write_pout)); //remove the message
1823             fprintf (stderr, "LOG : Skipping the broadcast message (pos %d, size %d)\n", neighbours.pos, neighbours.size);
1824           }
1825           else
1826           {
1827             FD_SET (sendsocket, &wfds);
1828             maxfd = MAX (maxfd, sendsocket);
1829           }
1830         }
1831         else
1832         {
1833           int found = 0;
1834           int pos = 0;
1835           /* Search if the address already exists on the list */
1836           for (i = 0; i < neighbours.size; i++)
1837           {
1838             if (memcmp (&frame->addr1, &(neighbours.devices[i]), sizeof (bdaddr_t)) == 0)
1839             {
1840               pos = i;
1841               if (neighbours.fds[i] != -1)
1842               {
1843                 found = 1;  //save the position where it was found
1844                 FD_SET (neighbours.fds[i], &wfds);
1845                 maxfd = MAX (maxfd, neighbours.fds[i]);
1846                 sendsocket = neighbours.fds[i];
1847                 fprintf (stderr, "LOG: the address was found in the list\n");
1848                 break;
1849               }
1850             }
1851           }
1852           if (found == 0)
1853           {
1854             int status;
1855             struct sockaddr_rc addr = { 0 };
1856
1857             fprintf (stderr, "LOG : %s has a new message for %.2X:%.2X:%.2X:%.2X:%.2X:%.2X which isn't on the broadcast list\n", dev.iface,
1858                     frame->addr1.mac[5], frame->addr1.mac[4], frame->addr1.mac[3],
1859                     frame->addr1.mac[2], frame->addr1.mac[1], frame->addr1.mac[0]); //FIXME: debugging message
1860
1861             sendsocket = socket (AF_BLUETOOTH, SOCK_STREAM, BTPROTO_RFCOMM);
1862
1863             if (sendsocket < 0)
1864             {
1865               fprintf (stderr, "Failed to create a RFCOMM socket (sending stage): %s\n",
1866                       strerror (errno));
1867               return -1;
1868             }
1869
1870             GNUNET_memcpy (&addr.rc_bdaddr, &frame->addr1, sizeof (bdaddr_t));
1871             addr.rc_family = AF_BLUETOOTH;
1872             addr.rc_channel = get_channel (&dev, addr.rc_bdaddr);
1873
1874             int tries = 0;
1875             connect_retry:
1876             status = connect (sendsocket, (struct sockaddr *) &addr, sizeof (addr));
1877             if (0 != status && errno != EAGAIN)
1878             {
1879               if (errno == ECONNREFUSED && tries < 2)
1880               {
1881                 fprintf (stderr, "LOG : %.*s failed to connect. Trying again!\n", IFNAMSIZ, dev.iface);
1882                 tries++;
1883                 goto connect_retry;
1884               }
1885               else if (errno == EBADF)
1886               {
1887                 fprintf (stderr, "LOG : %s failed to connect : %s. Skip it!\n", dev.iface, strerror (errno));
1888                 memset (&write_pout, 0, sizeof (write_pout));
1889                 broadcast = 1;
1890               }
1891               else
1892               {
1893                 fprintf (stderr, "LOG : %s failed to connect : %s. Try again later!\n", dev.iface, strerror (errno));
1894                 memset (&write_pout, 0, sizeof (write_pout));
1895                 broadcast = 1;
1896               }
1897
1898             }
1899             else
1900             {
1901               FD_SET (sendsocket, &wfds);
1902               maxfd = MAX (maxfd, sendsocket);
1903               fprintf (stderr, "LOG : Connection successful\n");
1904               if (pos != 0) // save the socket
1905               {
1906                 neighbours.fds[pos] = sendsocket;
1907               }
1908               else
1909               {
1910                 /* Add the new device to the discovered devices list */
1911                 if (neighbours.size < MAX_PORTS)
1912                 {
1913                   neighbours.fds[neighbours.size] = sendsocket;
1914                   GNUNET_memcpy (&(neighbours.devices[neighbours.size++]), &addr.rc_bdaddr, sizeof (bdaddr_t));
1915                 }
1916                 else
1917                 {
1918                   fprintf (stderr, "The top limit for the discovarable devices' list was reached\n");
1919                 }
1920               }
1921             }
1922           }
1923         }
1924       }
1925
1926       if (broadcast == 0)
1927       {
1928         /* Select a fd which is ready for action :) */
1929         {
1930           int retval = select (maxfd + 1, &rfds, &wfds, NULL, NULL);
1931           if ((-1 == retval) && (EINTR == errno))
1932       continue;
1933           if (0 > retval && errno != EBADF)   // we handle BADF errors later
1934           {
1935       fprintf (stderr, "select failed: %s\n", strerror (errno));
1936       break;
1937           }
1938         }
1939         if (FD_ISSET (STDOUT_FILENO , &wfds))
1940         {
1941           ssize_t ret =
1942               write (STDOUT_FILENO, write_std.buf + write_std.pos,
1943                      write_std.size - write_std.pos);
1944           if (0 > ret)
1945           {
1946             fprintf (stderr, "Failed to write to STDOUT: %s\n", strerror (errno));
1947             break;
1948           }
1949           write_std.pos += ret;
1950           if (write_std.pos == write_std.size)
1951           {
1952             write_std.pos = 0;
1953             write_std.size = 0;
1954           }
1955           fprintf (stderr, "LOG : %s sends a message to STDOUT\n", dev.iface); //FIXME: debugging message
1956
1957         }
1958         if (-1 != sendsocket)
1959         {
1960           if (FD_ISSET (sendsocket , &wfds))
1961           {
1962             ssize_t ret = write (sendsocket,
1963                                  write_pout.buf + write_std.pos,
1964                                  write_pout.size - write_pout.pos);
1965             if (0 > ret) //FIXME should I first check the error type?
1966             {
1967               fprintf (stderr, "Failed to write to bluetooth device: %s. Closing the socket!\n",
1968                        strerror (errno));
1969               for (i = 0; i < neighbours.size; i++)
1970               {
1971                 if (neighbours.fds[i] == sendsocket)
1972                 {
1973                   (void) close(sendsocket);
1974                   neighbours.fds[i] = -1;
1975                   break;
1976                 }
1977               }
1978               /* Remove the message */
1979               memset (&write_pout.buf + write_std.pos, 0, (write_pout.size - write_pout.pos));
1980               write_pout.pos = 0 ;
1981               write_pout.size = 0;
1982             }
1983             else
1984             {
1985               write_pout.pos += ret;
1986               if ((write_pout.pos != write_pout.size) && (0 != ret))
1987               {
1988                 /* We should not get partial sends with packet-oriented devices... */
1989                 fprintf (stderr, "Write error, partial send: %u/%u\n",
1990                         (unsigned int) write_pout.pos,
1991                         (unsigned int) write_pout.size);
1992                 break;
1993               }
1994
1995               if (write_pout.pos == write_pout.size)
1996               {
1997                 write_pout.pos = 0;
1998                 write_pout.size = 0;
1999               }
2000               fprintf (stderr, "LOG : %s sends a message to a DEVICE\n", dev.iface); //FIXME: debugging message
2001             }
2002           }
2003         }
2004         for (i = 0; i <= maxfd; i++)
2005         {
2006           if (FD_ISSET (i, &rfds))
2007           {
2008             if (i == STDIN_FILENO)
2009             {
2010               ssize_t ret =
2011           read (i, readbuf, sizeof (readbuf));
2012               if (0 > ret)
2013               {
2014                 fprintf (stderr,
2015                          "Read error from STDIN: %s\n",
2016                          strerror (errno));
2017                 break;
2018               }
2019               if (0 == ret)
2020               {
2021                 /* stop reading... */
2022                 stdin_open = 0;
2023               }
2024               else
2025               {
2026                 mst_receive (stdin_mst, readbuf, ret);
2027                 fprintf (stderr, "LOG : %s receives a message from STDIN\n", dev.iface); //FIXME: debugging message
2028               }
2029             }
2030             else if (i == dev.fd_rfcomm)
2031             {
2032               int readsocket;
2033               struct sockaddr_rc addr = { 0 };
2034               unsigned int opt = sizeof (addr);
2035
2036               readsocket = accept (dev.fd_rfcomm, (struct sockaddr *) &addr, &opt);
2037               fprintf(stderr, "LOG : %s accepts a message\n", dev.iface); //FIXME: debugging message
2038               if (readsocket == -1)
2039               {
2040                 fprintf (stderr, "Failed to accept a connection on interface: %.*s\n", IFNAMSIZ,
2041                     strerror (errno));
2042                 break;
2043               }
2044               else
2045               {
2046                 FD_SET (readsocket, &rfds);
2047                 maxfd = MAX (maxfd, readsocket);
2048
2049                 if (crt_rfds < MAX_PORTS)
2050                   rfds_list[crt_rfds++] = readsocket;
2051                 else
2052                 {
2053                   fprintf (stderr, "The limit for the read file descriptors list was \
2054                                   reached\n");
2055                   break;
2056                 }
2057               }
2058
2059             }
2060             else
2061             {
2062               struct GNUNET_TRANSPORT_WLAN_RadiotapReceiveMessage *rrm;
2063               ssize_t ret;
2064               fprintf (stderr, "LOG : %s reads something from the socket\n", dev.iface);//FIXME : debugging message
2065               rrm = (struct GNUNET_TRANSPORT_WLAN_RadiotapReceiveMessage *) write_std.buf;
2066               ret =
2067                   read_from_the_socket ((void *)&i, (unsigned char *) &rrm->frame,
2068                               sizeof (write_std.buf)
2069                   - sizeof (struct GNUNET_TRANSPORT_WLAN_RadiotapReceiveMessage)
2070                   + sizeof (struct GNUNET_TRANSPORT_WLAN_Ieee80211Frame),
2071                   rrm);
2072               if (0 >= ret)
2073               {
2074                 int j;
2075                 FD_CLR (i, &rfds);
2076                 close (i);
2077                  /* Remove the socket from the list */
2078                 for (j = 0; j < crt_rfds; j++)
2079                 {
2080                   if (rfds_list[j] == i)
2081                   {
2082                     rfds_list[j] ^= rfds_list[crt_rfds - 1];
2083                     rfds_list[crt_rfds - 1] ^= rfds_list[j];
2084                     rfds_list[j] ^= rfds_list[crt_rfds - 1];
2085                     crt_rfds -= 1;
2086                     break;
2087                   }
2088                 }
2089
2090                 fprintf (stderr, "Read error from raw socket: %s\n", strerror (errno));
2091                 break;
2092               }
2093               if ((0 < ret) && (0 == mac_test (&rrm->frame, &dev)))
2094               {
2095                 write_std.size = ret
2096             + sizeof (struct GNUNET_TRANSPORT_WLAN_RadiotapReceiveMessage)
2097             - sizeof (struct GNUNET_TRANSPORT_WLAN_Ieee80211Frame);
2098                 rrm->header.size = htons (write_std.size);
2099                 rrm->header.type = htons (GNUNET_MESSAGE_TYPE_WLAN_DATA_FROM_HELPER);
2100               }
2101             }
2102           }
2103         }
2104       }
2105     }
2106     /* Error handling, try to clean up a bit at least */
2107     mst_destroy (stdin_mst);
2108     stdin_mst = NULL;
2109     sdp_close (dev.session);
2110     (void) close (dev.fd_rfcomm);
2111     if (-1 != sendsocket)
2112       (void) close (sendsocket);
2113
2114     for (i = 0; i < crt_rfds; i++)
2115       (void) close (rfds_list[i]);
2116
2117     for (i = 0; i < neighbours.size; i++)
2118       (void) close (neighbours.fds[i]);
2119   #else
2120     struct HardwareInfos dev;
2121     struct GNUNET_NETWORK_Handle *sendsocket;
2122     struct GNUNET_NETWORK_FDSet *rfds;
2123     struct GNUNET_NETWORK_FDSet *wfds;
2124     struct GNUNET_NETWORK_Handle *rfds_list[MAX_PORTS];
2125     char readbuf[MAXLINE] = { 0 };
2126     SOCKADDR_BTH acc_addr = { 0 };
2127     int addr_len = sizeof (SOCKADDR_BTH);
2128     int broadcast, i, stdin_open, crt_rfds = 0;
2129     HANDLE stdin_handle = GetStdHandle (STD_INPUT_HANDLE);
2130     HANDLE stdout_handle = GetStdHandle (STD_OUTPUT_HANDLE);
2131     struct MessageStreamTokenizer *stdin_mst;
2132
2133     /* check the handles */
2134     if (stdin_handle == INVALID_HANDLE_VALUE)
2135     {
2136       fprintf (stderr, "Failed to get the stdin handle\n");
2137       ExitProcess (2);
2138     }
2139
2140     if (stdout_handle == INVALID_HANDLE_VALUE)
2141     {
2142       fprintf (stderr, "Failed to get the stdout handle\n");
2143       ExitProcess (2);
2144     }
2145
2146     /* initialize windows sockets */
2147     initialize_windows_sockets();
2148
2149     // /* test bluetooth socket family support */ --> it return false because the GNUNET_NETWORK_test_pf should also receive the type of socket (BTHPROTO_RFCOMM)
2150     // if (GNUNET_NETWORK_test_pf (AF_BTH) != GNUNET_OK)
2151     // {
2152     //   fprintf (stderr, "AF_BTH family is not supported\n");
2153     //   ExitProcess (2);
2154     // }
2155
2156      /* create the socket */
2157     dev.handle = GNUNET_NETWORK_socket_create (AF_BTH, SOCK_STREAM, BTHPROTO_RFCOMM);
2158     if (dev.handle == NULL)
2159     {
2160       fprintf (stderr, "Failed to create RFCOMM socket: ");
2161       print_last_error();
2162       ExitProcess (2);
2163     }
2164
2165
2166     if (open_device (&dev) == -1)
2167     {
2168       fprintf (stderr, "Failed to open the device\n");
2169       print_last_error();
2170       if (GNUNET_NETWORK_socket_close (dev.handle) != GNUNET_OK)
2171       {
2172         fprintf (stderr, "Failed to close the socket!\n");
2173         print_last_error();
2174       }
2175       ExitProcess (2);
2176     }
2177
2178     if (GNUNET_OK != GNUNET_NETWORK_socket_set_blocking (dev.handle, 1) )
2179     {
2180       fprintf (stderr, "Failed to change the socket mode\n");
2181       ExitProcess (2);
2182     }
2183
2184     memset (&write_std, 0, sizeof (write_std));
2185     memset (&write_pout, 0, sizeof (write_pout));
2186     stdin_open = 1;
2187
2188     rfds = GNUNET_NETWORK_fdset_create ();
2189     wfds = GNUNET_NETWORK_fdset_create ();
2190
2191   /* Send MAC address of the bluetooth interface to STDOUT first */
2192     {
2193       struct GNUNET_TRANSPORT_WLAN_HelperControlMessage macmsg;
2194
2195       macmsg.hdr.size = htons (sizeof (macmsg));
2196       macmsg.hdr.type = htons (GNUNET_MESSAGE_TYPE_WLAN_HELPER_CONTROL);
2197       GNUNET_memcpy (&macmsg.mac, &dev.pl_mac, sizeof (struct GNUNET_TRANSPORT_WLAN_MacAddress_Copy));
2198       GNUNET_memcpy (write_std.buf, &macmsg, sizeof (macmsg));
2199       write_std.size = sizeof (macmsg);
2200     }
2201
2202
2203     stdin_mst = mst_create (&stdin_send_hw, &dev);
2204     stdin_open = 1;
2205
2206     int pos = 0;
2207     int stdin_pos = -1;
2208     int stdout_pos = -1;
2209     while (1)
2210     {
2211       broadcast = 0;
2212       pos = 0;
2213       stdin_pos = -1;
2214       stdout_pos = -1;
2215       sendsocket = NULL; //FIXME ???memleaks
2216
2217       GNUNET_NETWORK_fdset_zero (rfds);
2218       if ((0 == write_pout.size) && (1 == stdin_open))
2219       {
2220         stdin_pos = pos;
2221         pos +=1;
2222         GNUNET_NETWORK_fdset_handle_set (rfds, (struct GNUNET_DISK_FileHandle*) &stdin_handle);
2223       }
2224
2225       if (0 == write_std.size)
2226       {
2227         pos += 1;
2228         GNUNET_NETWORK_fdset_set (rfds, dev.handle);
2229       }
2230
2231       for (i = 0; i < crt_rfds; i++)
2232       {
2233         pos += 1;
2234         GNUNET_NETWORK_fdset_set (rfds, rfds_list[i]);
2235       }
2236
2237       GNUNET_NETWORK_fdset_zero (wfds);
2238       if (0 < write_std.size)
2239       {
2240         stdout_pos = pos;
2241         GNUNET_NETWORK_fdset_handle_set (wfds, (struct GNUNET_DISK_FileHandle*) &stdout_handle);
2242         // printf ("%s\n", write_std.buf);
2243         // memset (write_std.buf, 0, write_std.size);
2244         // write_std.size = 0;
2245       }
2246
2247       if (0 < write_pout.size)
2248       {
2249         if (strcmp (argv[1], "ff:ff:ff:ff:ff:ff") == 0) {
2250           fprintf(stderr, "LOG: BROADCAST! Skipping the message\n");
2251           // skip the message
2252           broadcast = 1;
2253           memset (write_pout.buf, 0, write_pout.size);
2254           write_pout.size = 0;
2255         }
2256         else
2257         {
2258           SOCKADDR_BTH addr;
2259           fprintf (stderr, "LOG : has a new message for %s\n", argv[1]);
2260           sendsocket = GNUNET_NETWORK_socket_create (AF_BTH, SOCK_STREAM, BTHPROTO_RFCOMM);
2261
2262           if (sendsocket == NULL)
2263           {
2264             fprintf (stderr, "Failed to create RFCOMM socket: \n");
2265             print_last_error();
2266             ExitProcess (2);
2267           }
2268
2269           memset (&addr, 0, sizeof (addr));
2270           //addr.addressFamily = AF_BTH;
2271           if (SOCKET_ERROR ==
2272              WSAStringToAddress (argv[1], AF_BTH, NULL, (LPSOCKADDR) &addr, &addr_len))
2273           {
2274             fprintf (stderr, "Failed to translate the address: ");
2275             print_last_error();
2276             ExitProcess ( 2 ) ;
2277           }
2278           addr.port = get_channel (argv[1]);
2279           if (addr.port == -1)
2280           {
2281             fprintf (stderr, "Couldn't find the sdp service for the address: %s\n", argv[1]);
2282             memset (write_pout.buf, 0, write_pout.size);
2283             write_pout.size = 0;
2284             broadcast = 1; //skipping the select part
2285           }
2286           else
2287           {
2288             if (GNUNET_OK != GNUNET_NETWORK_socket_connect (sendsocket, (LPSOCKADDR)&addr, addr_len))
2289             {
2290               fprintf (stderr, "Failed to connect: ");
2291               print_last_error();
2292               ExitProcess (2);
2293             }
2294
2295             if (GNUNET_OK != GNUNET_NETWORK_socket_set_blocking (sendsocket, 1) )
2296             {
2297               fprintf (stderr, "Failed to change the socket mode\n");
2298               ExitProcess (2);
2299             }
2300
2301             GNUNET_NETWORK_fdset_set (wfds, sendsocket);
2302           }
2303         }
2304       }
2305
2306       if (broadcast == 0)
2307       {
2308         int retval = GNUNET_NETWORK_socket_select (rfds, wfds, NULL, GNUNET_TIME_relative_get_forever_());
2309         if (retval < 0)
2310         {
2311           fprintf (stderr, "Select error\n");
2312           ExitProcess (2);
2313         }
2314         //if (GNUNET_NETWORK_fdset_isset (wfds, (struct GNUNET_NETWORK_Handle*)&stdout_handle))
2315         if (retval == stdout_pos)
2316         {
2317           fprintf(stderr, "LOG : sends a message to STDOUT\n"); //FIXME: debugging message
2318           //ssize_t ret;
2319           //ret = GNUNET_NETWORK_socket_send ((struct GNUNET_NETWORK_Handle *)&stdout_handle,  write_std.buf + write_std.pos, write_std.size - write_std.pos);
2320           //ret = write (STDOUT_FILENO, write_std.buf + write_std.pos,  write_std.size - write_std.pos);
2321           DWORD ret;
2322           if (FALSE == WriteFile (stdout_handle,  write_std.buf + write_std.pos, write_std.size - write_std.pos, &ret, NULL))
2323           {
2324             fprintf (stderr, "Failed to write to STDOUT: ");
2325             print_last_error();
2326             break;
2327           }
2328
2329           if (ret <= 0)
2330           {
2331             fprintf (stderr, "Failed to write to STDOUT\n");
2332             ExitProcess (2);
2333           }
2334
2335           write_std.pos += ret;
2336           if (write_std.pos == write_std.size)
2337           {
2338             write_std.pos = 0;
2339             write_std.size = 0;
2340           }
2341         }
2342         if (sendsocket != NULL)
2343         {
2344           if (GNUNET_NETWORK_fdset_isset (wfds, sendsocket))
2345           {
2346             ssize_t ret;
2347             ret = GNUNET_NETWORK_socket_send (sendsocket, write_pout.buf + write_pout.pos,
2348                  write_pout.size - write_pout.pos);
2349
2350             if (GNUNET_SYSERR == ret)
2351             {
2352               fprintf (stderr, "Failed to send to the socket. Closing the socket. Error: \n");
2353               print_last_error();
2354               if (GNUNET_NETWORK_socket_close (sendsocket) != GNUNET_OK)
2355               {
2356                 fprintf (stderr, "Failed to close the sendsocket!\n");
2357                 print_last_error();
2358               }
2359               ExitProcess (2);
2360             }
2361             else
2362             {
2363               write_pout.pos += ret;
2364               if ((write_pout.pos != write_pout.size) && (0 != ret))
2365               {
2366                 /* we should not get partial sends with packet-oriented devices... */
2367                 fprintf (stderr, "Write error, partial send: %u/%u\n",
2368                         (unsigned int) write_pout.pos,
2369                        (unsigned int) write_pout.size);
2370                 break;
2371               }
2372
2373               if (write_pout.pos == write_pout.size)
2374               {
2375                 write_pout.pos = 0;
2376                 write_pout.size = 0;
2377
2378               }
2379               fprintf(stderr, "LOG : sends a message to a DEVICE\n"); //FIXME: debugging message
2380             }
2381           }
2382         }
2383
2384         //if (GNUNET_NETWORK_fdset_isset (rfds, (struct GNUNET_NETWORK_Handle*)&stdin_handle))
2385         if (retval == stdin_pos)
2386         {
2387           //ssize_t ret;
2388           //ret = GNUNET_NETWORK_socket_recv ((struct GNUNET_NETWORK_Handle *)&stdin_handle, readbuf, sizeof (write_pout.buf));
2389           //ret = read (STDIN_FILENO, readbuf, sizeof (readbuf));
2390           DWORD ret;
2391           if (FALSE == ReadFile (stdin_handle, readbuf, sizeof (readbuf), &ret, NULL))  /* do nothing asynchronous */
2392           {
2393             fprintf (stderr, "Read error from STDIN: ");
2394             print_last_error();
2395             break;
2396           }
2397           if (0 == ret)
2398           {
2399             /* stop reading... */
2400             stdin_open = 0;
2401           } else {
2402             mst_receive (stdin_mst, readbuf, ret);
2403             fprintf (stderr, "LOG : receives a message from STDIN\n"); //FIXME: debugging message
2404           }
2405         }
2406         else
2407         if (GNUNET_NETWORK_fdset_isset (rfds, dev.handle))
2408         {
2409           fprintf (stderr, "LOG: accepting connection\n");
2410           struct GNUNET_NETWORK_Handle *readsocket;
2411           readsocket = GNUNET_NETWORK_socket_accept (dev.handle, (LPSOCKADDR)&acc_addr, &addr_len);
2412           if (readsocket == NULL)
2413           {
2414             fprintf (stderr, "Accept error %d: ", GetLastError());
2415             print_last_error();
2416             ExitProcess (2);
2417           }
2418           else
2419           {
2420             if (GNUNET_OK != GNUNET_NETWORK_socket_set_blocking (readsocket, 1) )
2421             {
2422               fprintf (stderr, "Failed to change the socket mode\n");
2423               ExitProcess (2);
2424             }
2425             GNUNET_NETWORK_fdset_set (rfds, readsocket);
2426
2427             if (crt_rfds < MAX_PORTS)
2428               rfds_list[crt_rfds++] = readsocket;
2429             else
2430             {
2431               fprintf (stderr, "The limit for the read file descriptors list was reached\n");
2432               break;
2433             }
2434           }
2435         }
2436         else
2437         for (i = 0; i < crt_rfds; i++)
2438         {
2439           if (GNUNET_NETWORK_fdset_isset (rfds, rfds_list[i]))
2440           {
2441             struct GNUNET_TRANSPORT_WLAN_RadiotapReceiveMessage *rrm;
2442             ssize_t ret;
2443             fprintf (stderr, "LOG: reading something from the socket\n");//FIXME : debugging message
2444             rrm = (struct GNUNET_TRANSPORT_WLAN_RadiotapReceiveMessage *) write_std.buf;
2445             ret = read_from_the_socket (rfds_list[i], (unsigned char *) &rrm->frame,
2446                               sizeof (write_std.buf)
2447                   - sizeof (struct GNUNET_TRANSPORT_WLAN_RadiotapReceiveMessage)
2448                   + sizeof (struct GNUNET_TRANSPORT_WLAN_Ieee80211Frame),
2449                   rrm);
2450             if (0 >= ret)
2451             {
2452
2453               //TODO remove the socket from the list
2454               if (GNUNET_NETWORK_socket_close (rfds_list[i]) != GNUNET_OK)
2455               {
2456                 fprintf (stderr, "Failed to close the sendsocket!\n");
2457                 print_last_error();
2458               }
2459
2460               fprintf (stderr, "Read error from raw socket: ");
2461               print_last_error();
2462               break;
2463
2464             }
2465             if ((0 < ret) && (0 == mac_test (&rrm->frame, &dev)))
2466             {
2467               write_std.size = ret
2468           + sizeof (struct GNUNET_TRANSPORT_WLAN_RadiotapReceiveMessage)
2469           - sizeof (struct GNUNET_TRANSPORT_WLAN_Ieee80211Frame);
2470               rrm->header.size = htons (write_std.size);
2471               rrm->header.type = htons (GNUNET_MESSAGE_TYPE_WLAN_DATA_FROM_HELPER);
2472             }
2473             break;
2474           }
2475         }
2476       }
2477     }
2478
2479     mst_destroy (stdin_mst);
2480     stdin_mst = NULL;
2481
2482     if (GNUNET_NETWORK_socket_close (dev.handle) != GNUNET_OK)
2483     {
2484       fprintf (stderr, "Failed to close the socket!\n");
2485       print_last_error();
2486     }
2487
2488     for (i = 0; i < crt_rfds; i++)
2489     {
2490       if (GNUNET_NETWORK_socket_close (rfds_list[i]) != GNUNET_OK)
2491       {
2492         fprintf (stderr, "Failed to close the socket!\n");
2493         print_last_error();
2494       }
2495     }
2496
2497     WSACleanup();
2498   #endif
2499   return 1;                     /* we never exit 'normally' */
2500 }