2 This file is part of GNUnet.
3 (C) 2010, 2011 Christian Grothoff (and other contributing authors)
4 Copyright (c) 2007, 2008, Andy Green <andy@warmcat.com>
5 Copyright (C) 2009 Thomas d'Otreppe
7 GNUnet is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published
9 by the Free Software Foundation; either version 3, or (at your
10 option) any later version.
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 General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with GNUnet; see the file COPYING. If not, write to the
19 Free Software Foundation, Inc., 59 Temple Place - Suite 330,
20 Boston, MA 02111-1307, USA.
23 * we use our local copy of ieee80211_radiotap.h
25 * - since we can't support extensions we don't understand
26 * - since linux does not include it in userspace headers
28 * Portions of this code were taken from the ieee80211_radiotap.h header,
31 * Copyright (c) 2003, 2004 David Young. All rights reserved.
33 * Redistribution and use in source and binary forms, with or without
34 * modification, are permitted provided that the following conditions
36 * 1. Redistributions of source code must retain the above copyright
37 * notice, this list of conditions and the following disclaimer.
38 * 2. Redistributions in binary form must reproduce the above copyright
39 * notice, this list of conditions and the following disclaimer in the
40 * documentation and/or other materials provided with the distribution.
41 * 3. The name of David Young may not be used to endorse or promote
42 * products derived from this software without specific prior
45 * THIS SOFTWARE IS PROVIDED BY DAVID YOUNG ``AS IS'' AND ANY
46 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
47 * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
48 * PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL DAVID
49 * YOUNG BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
50 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
51 * TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
52 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
53 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
54 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
55 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY
60 * Modifications to fit into the linux IEEE 802.11 stack,
61 * Mike Kershaw (dragorn@kismetwireless.net)
65 * @file src/transport/gnunet-transport-wlan-helper.c
66 * @brief wlan layer two server; must run as root (SUID will do)
67 * This code will work under GNU/Linux only.
68 * @author David Brodski
70 * This program serves as the mediator between the wlan interface and
75 * parts taken from aircrack-ng, parts changend.
78 #include <sys/socket.h>
79 #include <sys/ioctl.h>
80 #include <sys/types.h>
85 #include <netpacket/packet.h>
86 #include <linux/if_ether.h>
88 #include <linux/wireless.h>
89 #include <netinet/in.h>
90 #include <linux/if_tun.h>
98 #include <sys/param.h>
103 #include "gnunet_protocols.h"
104 #include "gnunet_server_lib.h"
105 #include "plugin_transport_wlan.h"
107 #define ARPHRD_IEEE80211 801
108 #define ARPHRD_IEEE80211_PRISM 802
109 #define ARPHRD_IEEE80211_FULL 803
112 * size of 802.11 address
114 #define IEEE80211_ADDR_LEN 6
118 #define IEEE80211_RADIOTAP_PRESENT_EXTEND_MASK 0x80000000
121 /* Name Data type Units
122 * ---- --------- -----
124 * IEEE80211_RADIOTAP_TSFT __le64 microseconds
126 * Value in microseconds of the MAC's 64-bit 802.11 Time
127 * Synchronization Function timer when the first bit of the
128 * MPDU arrived at the MAC. For received frames, only.
130 * IEEE80211_RADIOTAP_CHANNEL 2 x __le16 MHz, bitmap
132 * Tx/Rx frequency in MHz, followed by flags (see below).
134 * IEEE80211_RADIOTAP_FHSS __le16 see below
136 * For frequency-hopping radios, the hop set (first byte)
137 * and pattern (second byte).
139 * IEEE80211_RADIOTAP_RATE uint8_t 500kb/s
143 * IEEE80211_RADIOTAP_DBM_ANTSIGNAL s8 decibels from
144 * one milliwatt (dBm)
146 * RF signal power at the antenna, decibel difference from
149 * IEEE80211_RADIOTAP_DBM_ANTNOISE s8 decibels from
150 * one milliwatt (dBm)
152 * RF noise power at the antenna, decibel difference from one
155 * IEEE80211_RADIOTAP_DB_ANTSIGNAL uint8_t decibel (dB)
157 * RF signal power at the antenna, decibel difference from an
158 * arbitrary, fixed reference.
160 * IEEE80211_RADIOTAP_DB_ANTNOISE uint8_t decibel (dB)
162 * RF noise power at the antenna, decibel difference from an
163 * arbitrary, fixed reference point.
165 * IEEE80211_RADIOTAP_LOCK_QUALITY __le16 unitless
167 * Quality of Barker code lock. Unitless. Monotonically
168 * nondecreasing with "better" lock strength. Called "Signal
169 * Quality" in datasheets. (Is there a standard way to measure
172 * IEEE80211_RADIOTAP_TX_ATTENUATION __le16 unitless
174 * Transmit power expressed as unitless distance from max
175 * power set at factory calibration. 0 is max power.
176 * Monotonically nondecreasing with lower power levels.
178 * IEEE80211_RADIOTAP_DB_TX_ATTENUATION __le16 decibels (dB)
180 * Transmit power expressed as decibel distance from max power
181 * set at factory calibration. 0 is max power. Monotonically
182 * nondecreasing with lower power levels.
184 * IEEE80211_RADIOTAP_DBM_TX_POWER s8 decibels from
185 * one milliwatt (dBm)
187 * Transmit power expressed as dBm (decibels from a 1 milliwatt
188 * reference). This is the absolute power level measured at
191 * IEEE80211_RADIOTAP_FLAGS uint8_t bitmap
193 * Properties of transmitted and received frames. See flags
196 * IEEE80211_RADIOTAP_ANTENNA uint8_t antenna index
198 * Unitless indication of the Rx/Tx antenna for this packet.
199 * The first antenna is antenna 0.
201 * IEEE80211_RADIOTAP_RX_FLAGS __le16 bitmap
203 * Properties of received frames. See flags defined below.
205 * IEEE80211_RADIOTAP_TX_FLAGS __le16 bitmap
207 * Properties of transmitted frames. See flags defined below.
209 * IEEE80211_RADIOTAP_RTS_RETRIES uint8_t data
211 * Number of rts retries a transmitted frame used.
213 * IEEE80211_RADIOTAP_DATA_RETRIES uint8_t data
215 * Number of unicast retries a transmitted frame used.
218 enum ieee80211_radiotap_type
220 IEEE80211_RADIOTAP_TSFT = 0,
221 IEEE80211_RADIOTAP_FLAGS = 1,
222 IEEE80211_RADIOTAP_RATE = 2,
223 IEEE80211_RADIOTAP_CHANNEL = 3,
224 IEEE80211_RADIOTAP_FHSS = 4,
225 IEEE80211_RADIOTAP_DBM_ANTSIGNAL = 5,
226 IEEE80211_RADIOTAP_DBM_ANTNOISE = 6,
227 IEEE80211_RADIOTAP_LOCK_QUALITY = 7,
228 IEEE80211_RADIOTAP_TX_ATTENUATION = 8,
229 IEEE80211_RADIOTAP_DB_TX_ATTENUATION = 9,
230 IEEE80211_RADIOTAP_DBM_TX_POWER = 10,
231 IEEE80211_RADIOTAP_ANTENNA = 11,
232 IEEE80211_RADIOTAP_DB_ANTSIGNAL = 12,
233 IEEE80211_RADIOTAP_DB_ANTNOISE = 13,
234 IEEE80211_RADIOTAP_RX_FLAGS = 14,
235 IEEE80211_RADIOTAP_TX_FLAGS = 15,
236 IEEE80211_RADIOTAP_RTS_RETRIES = 16,
237 IEEE80211_RADIOTAP_DATA_RETRIES = 17,
238 IEEE80211_RADIOTAP_EXT = 31
241 /* For IEEE80211_RADIOTAP_FLAGS */
242 #define IEEE80211_RADIOTAP_F_CFP 0x01 /* sent/received
245 #define IEEE80211_RADIOTAP_F_SHORTPRE 0x02 /* sent/received
249 #define IEEE80211_RADIOTAP_F_WEP 0x04 /* sent/received
250 * with WEP encryption
252 #define IEEE80211_RADIOTAP_F_FRAG 0x08 /* sent/received
255 #define IEEE80211_RADIOTAP_F_FCS 0x10 /* frame includes FCS */
256 #define IEEE80211_RADIOTAP_F_DATAPAD 0x20 /* frame has padding between
257 * 802.11 header and payload
258 * (to 32-bit boundary)
260 /* For IEEE80211_RADIOTAP_RX_FLAGS */
261 #define IEEE80211_RADIOTAP_F_RX_BADFCS 0x0001 /* frame failed crc check */
263 /* For IEEE80211_RADIOTAP_TX_FLAGS */
264 #define IEEE80211_RADIOTAP_F_TX_FAIL 0x0001 /* failed due to excessive
266 #define IEEE80211_RADIOTAP_F_TX_CTS 0x0002 /* used cts 'protection' */
267 #define IEEE80211_RADIOTAP_F_TX_RTS 0x0004 /* used rts/cts handshake */
268 #define IEEE80211_RADIOTAP_F_TX_NOACK 0x0008 /* frame should not be ACKed */
269 #define IEEE80211_RADIOTAP_F_TX_NOSEQ 0x0010 /* sequence number handled
274 * A generic radio capture format is desirable. There is one for
275 * Linux, but it is neither rigidly defined (there were not even
276 * units given for some fields) nor easily extensible.
278 * I suggest the following extensible radio capture format. It is
279 * based on a bitmap indicating which fields are present.
281 * I am trying to describe precisely what the application programmer
282 * should expect in the following, and for that reason I tell the
283 * units and origin of each measurement (where it applies), or else I
284 * use sufficiently weaselly language ("is a monotonically nondecreasing
285 * function of...") that I cannot set false expectations for lawyerly
288 * The radio capture header precedes the 802.11 header.
289 * All data in the header is little endian on all platforms.
291 struct ieee80211_radiotap_header
294 * Version 0. Only increases for drastic changes, introduction of
295 * compatible new fields does not count.
301 * length of the whole header in bytes, including it_version,
302 * it_pad, it_len, and data fields.
307 * A bitmap telling which fields are present. Set bit 31
308 * (0x80000000) to extend the bitmap by another 32 bits. Additional
309 * extensions are made by setting bit 31.
314 struct RadioTapheader
316 struct ieee80211_radiotap_header header;
330 char buf[MAXLINE * 2];
335 * generic definitions for IEEE 802.11 frames
337 struct ieee80211_frame
341 uint8_t i_addr1[IEEE80211_ADDR_LEN];
342 uint8_t i_addr2[IEEE80211_ADDR_LEN];
343 uint8_t i_addr3[IEEE80211_ADDR_LEN];
345 /* possibly followed by addr4[IEEE80211_ADDR_LEN]; */
351 * struct for storing the information of the hardware
353 struct Hardware_Infos
359 struct sendbuf write_pout;
361 * file descriptor for the raw socket
368 * Name of the interface, not necessarily 0-terminated (!).
370 char iface[IFNAMSIZ];
372 struct MacAddress pl_mac;
379 #define ___my_swab16(x) \
381 (((u_int16_t)(x) & (u_int16_t)0x00ffU) << 8) | \
382 (((u_int16_t)(x) & (u_int16_t)0xff00U) >> 8) ))
384 #define ___my_swab32(x) \
386 (((u_int32_t)(x) & (u_int32_t)0x000000ffUL) << 24) | \
387 (((u_int32_t)(x) & (u_int32_t)0x0000ff00UL) << 8) | \
388 (((u_int32_t)(x) & (u_int32_t)0x00ff0000UL) >> 8) | \
389 (((u_int32_t)(x) & (u_int32_t)0xff000000UL) >> 24) ))
390 #define ___my_swab64(x) \
392 (u_int64_t)(((u_int64_t)(x) & (u_int64_t)0x00000000000000ffULL) << 56) | \
393 (u_int64_t)(((u_int64_t)(x) & (u_int64_t)0x000000000000ff00ULL) << 40) | \
394 (u_int64_t)(((u_int64_t)(x) & (u_int64_t)0x0000000000ff0000ULL) << 24) | \
395 (u_int64_t)(((u_int64_t)(x) & (u_int64_t)0x00000000ff000000ULL) << 8) | \
396 (u_int64_t)(((u_int64_t)(x) & (u_int64_t)0x000000ff00000000ULL) >> 8) | \
397 (u_int64_t)(((u_int64_t)(x) & (u_int64_t)0x0000ff0000000000ULL) >> 24) | \
398 (u_int64_t)(((u_int64_t)(x) & (u_int64_t)0x00ff000000000000ULL) >> 40) | \
399 (u_int64_t)(((u_int64_t)(x) & (u_int64_t)0xff00000000000000ULL) >> 56) ))
403 #if __BYTE_ORDER == __LITTLE_ENDIAN
404 #define htole16(x) (x)
405 #define le16toh(x) (x)
406 #define htole32(x) (x)
407 #define le32toh(x) (x)
408 #define htole64(x) (x)
409 #define le64toh(x) (x)
411 #define htole16(x) ___my_swab16 (x)
412 #define le16toh(x) ___my_swab16 (x)
413 #define htole32(x) ___my_swab32 (x)
414 #define le32toh(x) ___my_swab32 (x)
415 #define htole64(x) ___my_swab64 (x)
416 #define le64toh(x) ___my_swab64 (x)
422 * struct ieee80211_radiotap_iterator - tracks walk thru present radiotap args
423 * @rtheader: pointer to the radiotap header we are walking through
424 * @max_length: length of radiotap header in cpu byte ordering
425 * @this_arg_index: IEEE80211_RADIOTAP_... index of current arg
426 * @this_arg: pointer to current radiotap arg
427 * @arg_index: internal next argument index
428 * @arg: internal next argument pointer
429 * @next_bitmap: internal pointer to next present uint32_t
430 * @bitmap_shifter: internal shifter for curr uint32_t bitmap, b0 set == arg present
432 struct ieee80211_radiotap_iterator
434 struct ieee80211_radiotap_header *rtheader;
440 uint32_t *next_bitmap;
441 uint32_t bitmap_shifter;
446 * Radiotap header iteration
448 * call __ieee80211_radiotap_iterator_init() to init a semi-opaque iterator
449 * struct ieee80211_radiotap_iterator (no need to init the struct beforehand)
450 * then loop calling __ieee80211_radiotap_iterator_next()... it returns -1
451 * if there are no more args in the header, or the next argument type index
452 * that is present. The iterator's this_arg member points to the start of the
453 * argument associated with the current argument index that is present,
454 * which can be found in the iterator's this_arg_index member. This arg
455 * index corresponds to the IEEE80211_RADIOTAP_... defines.
458 ieee80211_radiotap_iterator_init (struct ieee80211_radiotap_iterator
460 struct ieee80211_radiotap_header
461 *radiotap_header, int max_length)
463 if (iterator == NULL)
466 if (radiotap_header == NULL)
468 /* Linux only supports version 0 radiotap format */
470 if (radiotap_header->it_version)
473 /* sanity check for allowed length and radiotap length field */
475 if (max_length < (le16toh (radiotap_header->it_len)))
478 iterator->rtheader = radiotap_header;
479 iterator->max_length = le16toh (radiotap_header->it_len);
480 iterator->arg_index = 0;
481 iterator->bitmap_shifter = le32toh (radiotap_header->it_present);
483 ((uint8_t *) radiotap_header) + sizeof (struct ieee80211_radiotap_header);
484 iterator->this_arg = 0;
486 /* find payload start allowing for extended bitmap(s) */
488 if ((iterator->bitmap_shifter & IEEE80211_RADIOTAP_PRESENT_EXTEND_MASK))
490 while (le32toh (*((uint32_t *) iterator->arg)) &
491 IEEE80211_RADIOTAP_PRESENT_EXTEND_MASK)
493 iterator->arg += sizeof (uint32_t);
496 * check for insanity where the present bitmaps
497 * keep claiming to extend up to or even beyond the
498 * stated radiotap header length
501 if ((((void *) iterator->arg) - ((void *) iterator->rtheader)) >
502 iterator->max_length)
507 iterator->arg += sizeof (uint32_t);
510 * no need to check again for blowing past stated radiotap
511 * header length, becuase ieee80211_radiotap_iterator_next
512 * checks it before it is dereferenced
517 /* we are all initialized happily */
523 * ieee80211_radiotap_iterator_next - return next radiotap parser iterator arg
524 * @iterator: radiotap_iterator to move to next arg (if any)
526 * Returns: next present arg index on success or negative if no more or error
528 * This function returns the next radiotap arg index (IEEE80211_RADIOTAP_...)
529 * and sets iterator->this_arg to point to the payload for the arg. It takes
530 * care of alignment handling and extended present fields. interator->this_arg
531 * can be changed by the caller. The args pointed to are in little-endian
535 ieee80211_radiotap_iterator_next (struct ieee80211_radiotap_iterator
540 * small length lookup table for all radiotap types we heard of
541 * starting from b0 in the bitmap, so we can walk the payload
542 * area of the radiotap header
544 * There is a requirement to pad args, so that args
545 * of a given length must begin at a boundary of that length
546 * -- but note that compound args are allowed (eg, 2 x uint16_t
547 * for IEEE80211_RADIOTAP_CHANNEL) so total arg length is not
548 * a reliable indicator of alignment requirement.
550 * upper nybble: content alignment for arg
551 * lower nybble: content length for arg
554 static const uint8_t rt_sizes[] = {
555 [IEEE80211_RADIOTAP_TSFT] = 0x88,
556 [IEEE80211_RADIOTAP_FLAGS] = 0x11,
557 [IEEE80211_RADIOTAP_RATE] = 0x11,
558 [IEEE80211_RADIOTAP_CHANNEL] = 0x24,
559 [IEEE80211_RADIOTAP_FHSS] = 0x22,
560 [IEEE80211_RADIOTAP_DBM_ANTSIGNAL] = 0x11,
561 [IEEE80211_RADIOTAP_DBM_ANTNOISE] = 0x11,
562 [IEEE80211_RADIOTAP_LOCK_QUALITY] = 0x22,
563 [IEEE80211_RADIOTAP_TX_ATTENUATION] = 0x22,
564 [IEEE80211_RADIOTAP_DB_TX_ATTENUATION] = 0x22,
565 [IEEE80211_RADIOTAP_DBM_TX_POWER] = 0x11,
566 [IEEE80211_RADIOTAP_ANTENNA] = 0x11,
567 [IEEE80211_RADIOTAP_DB_ANTSIGNAL] = 0x11,
568 [IEEE80211_RADIOTAP_DB_ANTNOISE] = 0x11,
569 [IEEE80211_RADIOTAP_TX_FLAGS] = 0x22,
570 [IEEE80211_RADIOTAP_RX_FLAGS] = 0x22,
571 [IEEE80211_RADIOTAP_RTS_RETRIES] = 0x11,
572 [IEEE80211_RADIOTAP_DATA_RETRIES] = 0x11
574 * add more here as they are defined in
575 * include/net/ieee80211_radiotap.h
580 * for every radiotap entry we can at
581 * least skip (by knowing the length)...
584 while (iterator->arg_index < (int) sizeof (rt_sizes))
588 if (!(iterator->bitmap_shifter & 1))
589 goto next_entry; /* arg not present */
592 * arg is present, account for alignment padding
593 * 8-bit args can be at any alignment
594 * 16-bit args must start on 16-bit boundary
595 * 32-bit args must start on 32-bit boundary
596 * 64-bit args must start on 64-bit boundary
598 * note that total arg size can differ from alignment of
599 * elements inside arg, so we use upper nybble of length
600 * table to base alignment on
602 * also note: these alignments are ** relative to the
603 * start of the radiotap header **. There is no guarantee
604 * that the radiotap header itself is aligned on any
608 if ((((void *) iterator->arg) -
609 ((void *) iterator->rtheader)) & ((rt_sizes[iterator->arg_index] >>
611 iterator->arg_index +=
612 (rt_sizes[iterator->arg_index] >> 4) -
613 ((((void *) iterator->arg) -
614 ((void *) iterator->rtheader)) & ((rt_sizes[iterator->arg_index]
618 * this is what we will return to user, but we need to
619 * move on first so next call has something fresh to test
622 iterator->this_arg_index = iterator->arg_index;
623 iterator->this_arg = iterator->arg;
626 /* internally move on the size of this arg */
628 iterator->arg += rt_sizes[iterator->arg_index] & 0x0f;
631 * check for insanity where we are given a bitmap that
632 * claims to have more arg content than the length of the
633 * radiotap section. We will normally end up equalling this
634 * max_length on the last arg, never exceeding it.
637 if ((((void *) iterator->arg) - ((void *) iterator->rtheader)) >
638 iterator->max_length)
643 iterator->arg_index++;
644 if (((iterator->arg_index & 31) == 0))
646 /* completed current uint32_t bitmap */
647 if (iterator->bitmap_shifter & 1)
649 /* b31 was set, there is more */
650 /* move to next uint32_t bitmap */
651 iterator->bitmap_shifter = le32toh (*iterator->next_bitmap);
652 iterator->next_bitmap++;
656 /* no more bitmaps: end */
657 iterator->arg_index = sizeof (rt_sizes);
661 { /* just try the next bit */
662 iterator->bitmap_shifter >>= 1;
665 /* if we found a valid arg earlier, return it now */
668 return (iterator->this_arg_index);
672 /* we don't know how to handle any more args, we're done */
679 * function to create GNUNET_MESSAGE_TYPE_WLAN_HELPER_CONTROL message for plugin
680 * @param buffer pointer to buffer for the message
681 * @param mac pointer to the mac address
682 * @return number of bytes written
685 send_mac_to_plugin (char *buffer, struct MacAddress *mac)
688 struct Wlan_Helper_Control_Message macmsg;
690 memcpy (&macmsg.mac, (char *) mac, sizeof (struct MacAddress));
691 macmsg.hdr.size = htons (sizeof (struct Wlan_Helper_Control_Message));
692 macmsg.hdr.type = htons (GNUNET_MESSAGE_TYPE_WLAN_HELPER_CONTROL);
694 memcpy (buffer, &macmsg, sizeof (struct Wlan_Helper_Control_Message));
695 return sizeof (struct Wlan_Helper_Control_Message);
700 * Return the channel from the frequency (in Mhz)
701 * @param frequency of the channel
702 * @return number of the channel
705 getChannelFromFrequency (int frequency)
707 if (frequency >= 2412 && frequency <= 2472)
708 return (frequency - 2407) / 5;
709 else if (frequency == 2484)
711 else if (frequency >= 5000 && frequency <= 6100)
712 return (frequency - 5000) / 5;
719 * function to calculate the crc, the start of the calculation
720 * @param buf buffer to calc the crc
721 * @param len len of the buffer
725 calc_crc_osdep (const unsigned char *buf, size_t len)
727 static const unsigned long int crc_tbl_osdep[256] = {
728 0x00000000, 0x77073096, 0xEE0E612C, 0x990951BA, 0x076DC419, 0x706AF48F,
729 0xE963A535, 0x9E6495A3,
730 0x0EDB8832, 0x79DCB8A4, 0xE0D5E91E, 0x97D2D988, 0x09B64C2B, 0x7EB17CBD,
731 0xE7B82D07, 0x90BF1D91,
732 0x1DB71064, 0x6AB020F2, 0xF3B97148, 0x84BE41DE, 0x1ADAD47D, 0x6DDDE4EB,
733 0xF4D4B551, 0x83D385C7,
734 0x136C9856, 0x646BA8C0, 0xFD62F97A, 0x8A65C9EC, 0x14015C4F, 0x63066CD9,
735 0xFA0F3D63, 0x8D080DF5,
736 0x3B6E20C8, 0x4C69105E, 0xD56041E4, 0xA2677172, 0x3C03E4D1, 0x4B04D447,
737 0xD20D85FD, 0xA50AB56B,
738 0x35B5A8FA, 0x42B2986C, 0xDBBBC9D6, 0xACBCF940, 0x32D86CE3, 0x45DF5C75,
739 0xDCD60DCF, 0xABD13D59,
740 0x26D930AC, 0x51DE003A, 0xC8D75180, 0xBFD06116, 0x21B4F4B5, 0x56B3C423,
741 0xCFBA9599, 0xB8BDA50F,
742 0x2802B89E, 0x5F058808, 0xC60CD9B2, 0xB10BE924, 0x2F6F7C87, 0x58684C11,
743 0xC1611DAB, 0xB6662D3D,
744 0x76DC4190, 0x01DB7106, 0x98D220BC, 0xEFD5102A, 0x71B18589, 0x06B6B51F,
745 0x9FBFE4A5, 0xE8B8D433,
746 0x7807C9A2, 0x0F00F934, 0x9609A88E, 0xE10E9818, 0x7F6A0DBB, 0x086D3D2D,
747 0x91646C97, 0xE6635C01,
748 0x6B6B51F4, 0x1C6C6162, 0x856530D8, 0xF262004E, 0x6C0695ED, 0x1B01A57B,
749 0x8208F4C1, 0xF50FC457,
750 0x65B0D9C6, 0x12B7E950, 0x8BBEB8EA, 0xFCB9887C, 0x62DD1DDF, 0x15DA2D49,
751 0x8CD37CF3, 0xFBD44C65,
752 0x4DB26158, 0x3AB551CE, 0xA3BC0074, 0xD4BB30E2, 0x4ADFA541, 0x3DD895D7,
753 0xA4D1C46D, 0xD3D6F4FB,
754 0x4369E96A, 0x346ED9FC, 0xAD678846, 0xDA60B8D0, 0x44042D73, 0x33031DE5,
755 0xAA0A4C5F, 0xDD0D7CC9,
756 0x5005713C, 0x270241AA, 0xBE0B1010, 0xC90C2086, 0x5768B525, 0x206F85B3,
757 0xB966D409, 0xCE61E49F,
758 0x5EDEF90E, 0x29D9C998, 0xB0D09822, 0xC7D7A8B4, 0x59B33D17, 0x2EB40D81,
759 0xB7BD5C3B, 0xC0BA6CAD,
760 0xEDB88320, 0x9ABFB3B6, 0x03B6E20C, 0x74B1D29A, 0xEAD54739, 0x9DD277AF,
761 0x04DB2615, 0x73DC1683,
762 0xE3630B12, 0x94643B84, 0x0D6D6A3E, 0x7A6A5AA8, 0xE40ECF0B, 0x9309FF9D,
763 0x0A00AE27, 0x7D079EB1,
764 0xF00F9344, 0x8708A3D2, 0x1E01F268, 0x6906C2FE, 0xF762575D, 0x806567CB,
765 0x196C3671, 0x6E6B06E7,
766 0xFED41B76, 0x89D32BE0, 0x10DA7A5A, 0x67DD4ACC, 0xF9B9DF6F, 0x8EBEEFF9,
767 0x17B7BE43, 0x60B08ED5,
768 0xD6D6A3E8, 0xA1D1937E, 0x38D8C2C4, 0x4FDFF252, 0xD1BB67F1, 0xA6BC5767,
769 0x3FB506DD, 0x48B2364B,
770 0xD80D2BDA, 0xAF0A1B4C, 0x36034AF6, 0x41047A60, 0xDF60EFC3, 0xA867DF55,
771 0x316E8EEF, 0x4669BE79,
772 0xCB61B38C, 0xBC66831A, 0x256FD2A0, 0x5268E236, 0xCC0C7795, 0xBB0B4703,
773 0x220216B9, 0x5505262F,
774 0xC5BA3BBE, 0xB2BD0B28, 0x2BB45A92, 0x5CB36A04, 0xC2D7FFA7, 0xB5D0CF31,
775 0x2CD99E8B, 0x5BDEAE1D,
776 0x9B64C2B0, 0xEC63F226, 0x756AA39C, 0x026D930A, 0x9C0906A9, 0xEB0E363F,
777 0x72076785, 0x05005713,
778 0x95BF4A82, 0xE2B87A14, 0x7BB12BAE, 0x0CB61B38, 0x92D28E9B, 0xE5D5BE0D,
779 0x7CDCEFB7, 0x0BDBDF21,
780 0x86D3D2D4, 0xF1D4E242, 0x68DDB3F8, 0x1FDA836E, 0x81BE16CD, 0xF6B9265B,
781 0x6FB077E1, 0x18B74777,
782 0x88085AE6, 0xFF0F6A70, 0x66063BCA, 0x11010B5C, 0x8F659EFF, 0xF862AE69,
783 0x616BFFD3, 0x166CCF45,
784 0xA00AE278, 0xD70DD2EE, 0x4E048354, 0x3903B3C2, 0xA7672661, 0xD06016F7,
785 0x4969474D, 0x3E6E77DB,
786 0xAED16A4A, 0xD9D65ADC, 0x40DF0B66, 0x37D83BF0, 0xA9BCAE53, 0xDEBB9EC5,
787 0x47B2CF7F, 0x30B5FFE9,
788 0xBDBDF21C, 0xCABAC28A, 0x53B39330, 0x24B4A3A6, 0xBAD03605, 0xCDD70693,
789 0x54DE5729, 0x23D967BF,
790 0xB3667A2E, 0xC4614AB8, 0x5D681B02, 0x2A6F2B94, 0xB40BBE37, 0xC30C8EA1,
791 0x5A05DF1B, 0x2D02EF8D
794 unsigned long crc = 0xFFFFFFFF;
796 for (; len > 0; len--, buf++)
797 crc = crc_tbl_osdep[(crc ^ *buf) & 0xFF] ^ (crc >> 8);
804 * Function to check crc of the wlan packet
805 * @param buf buffer of the packet
806 * @param len len of the data
807 * @return crc sum of the data
810 check_crc_buf_osdep (const unsigned char *buf, size_t len)
817 crc = calc_crc_osdep (buf, len);
819 return (((crc) & 0xFF) == buf[0] && ((crc >> 8) & 0xFF) == buf[1] &&
820 ((crc >> 16) & 0xFF) == buf[2] && ((crc >> 24) & 0xFF) == buf[3]);
825 * function to get the channel of a specific wlan card
826 * @param dev pointer to the dev struct of the card
827 * @return channel number
830 linux_get_channel (const struct Hardware_Infos *dev)
837 memset (&wrq, 0, sizeof (struct iwreq));
839 strncpy (wrq.ifr_name, dev->iface, IFNAMSIZ);
842 if (0 > ioctl (fd, SIOCGIWFREQ, &wrq))
845 frequency = wrq.u.freq.m;
846 if (100000000 < frequency)
848 else if (1000000 < frequency)
851 if (1000 < frequency)
852 chan = getChannelFromFrequency (frequency);
861 * function to read from a wlan card
862 * @param dev pointer to the struct of the wlan card
863 * @param buf buffer to read to
864 * @param buf_size size of the buffer
865 * @param ri radiotap_rx info
866 * @return size read from the buffer
869 linux_read (struct Hardware_Infos *dev, unsigned char *buf,
870 size_t buf_size, struct Radiotap_rx *ri)
872 unsigned char tmpbuf[buf_size];
874 int n, got_signal, got_noise, got_channel, fcs_removed;
876 n = got_signal = got_noise = got_channel = fcs_removed = 0;
878 caplen = read (dev->fd_raw, tmpbuf, buf_size);
883 fprintf (stderr, "Failed to read from RAW socket: %s\n",
888 memset (buf, 0, buf_size);
889 memset (ri, 0, sizeof (*ri));
891 switch (dev->arptype_in)
893 case ARPHRD_IEEE80211_PRISM:
895 /* skip the prism header */
896 if (tmpbuf[7] == 0x40)
898 /* prism54 uses a different format */
899 ri->ri_power = tmpbuf[0x33];
900 ri->ri_noise = *(unsigned int *) (tmpbuf + 0x33 + 12);
901 ri->ri_rate = (*(unsigned int *) (tmpbuf + 0x33 + 24)) * 500000;
908 ri->ri_mactime = *(uint64_t *) (tmpbuf + 0x5C - 48);
909 ri->ri_channel = *(unsigned int *) (tmpbuf + 0x5C - 36);
910 ri->ri_power = *(unsigned int *) (tmpbuf + 0x5C);
911 ri->ri_noise = *(unsigned int *) (tmpbuf + 0x5C + 12);
912 ri->ri_rate = (*(unsigned int *) (tmpbuf + 0x5C + 24)) * 500000;
916 n = *(int *) (tmpbuf + 4);
919 if (n < 8 || n >= caplen)
924 case ARPHRD_IEEE80211_FULL:
926 struct ieee80211_radiotap_iterator iterator;
927 struct ieee80211_radiotap_header *rthdr;
929 rthdr = (struct ieee80211_radiotap_header *) tmpbuf;
931 if (ieee80211_radiotap_iterator_init (&iterator, rthdr, caplen) < 0)
934 /* go through the radiotap arguments we have been given
938 while (ieee80211_radiotap_iterator_next (&iterator) >= 0)
941 switch (iterator.this_arg_index)
944 case IEEE80211_RADIOTAP_TSFT:
945 ri->ri_mactime = le64toh (*((uint64_t *) iterator.this_arg));
948 case IEEE80211_RADIOTAP_DBM_ANTSIGNAL:
951 if (*iterator.this_arg < 127)
952 ri->ri_power = *iterator.this_arg;
954 ri->ri_power = *iterator.this_arg - 255;
960 case IEEE80211_RADIOTAP_DB_ANTSIGNAL:
963 if (*iterator.this_arg < 127)
964 ri->ri_power = *iterator.this_arg;
966 ri->ri_power = *iterator.this_arg - 255;
972 case IEEE80211_RADIOTAP_DBM_ANTNOISE:
975 if (*iterator.this_arg < 127)
976 ri->ri_noise = *iterator.this_arg;
978 ri->ri_noise = *iterator.this_arg - 255;
984 case IEEE80211_RADIOTAP_DB_ANTNOISE:
987 if (*iterator.this_arg < 127)
988 ri->ri_noise = *iterator.this_arg;
990 ri->ri_noise = *iterator.this_arg - 255;
996 case IEEE80211_RADIOTAP_ANTENNA:
997 ri->ri_antenna = *iterator.this_arg;
1000 case IEEE80211_RADIOTAP_CHANNEL:
1001 ri->ri_channel = *iterator.this_arg;
1005 case IEEE80211_RADIOTAP_RATE:
1006 ri->ri_rate = (*iterator.this_arg) * 500000;
1009 case IEEE80211_RADIOTAP_FLAGS:
1010 /* is the CRC visible at the end?
1013 if (*iterator.this_arg & IEEE80211_RADIOTAP_F_FCS)
1019 if (*iterator.this_arg & IEEE80211_RADIOTAP_F_RX_BADFCS)
1025 n = le16toh (rthdr->it_len);
1026 if (n <= 0 || n >= caplen)
1030 case ARPHRD_IEEE80211:
1040 //detect fcs at the end, even if the flag wasn't set and remove it
1041 if ((0 == fcs_removed)
1042 && (1 == check_crc_buf_osdep (tmpbuf + n, caplen - 4)))
1046 memcpy (buf, tmpbuf + n, caplen);
1048 ri->ri_channel = linux_get_channel (dev);
1055 * function to open the device for read/write
1056 * @param dev pointer to the device struct
1057 * @return 0 on success
1060 openraw (struct Hardware_Infos *dev)
1064 struct packet_mreq mr;
1065 struct sockaddr_ll sll;
1067 /* find the interface index */
1068 memset (&ifr, 0, sizeof (ifr));
1069 strncpy (ifr.ifr_name, dev->iface, IFNAMSIZ);
1070 if (-1 == ioctl (dev->fd_raw, SIOCGIFINDEX, &ifr))
1073 "ioctl(SIOCGIFINDEX) on interface `%.*s' failed: %s\n",
1074 IFNAMSIZ, dev->iface, strerror (errno));
1078 /* lookup the hardware type */
1079 memset (&sll, 0, sizeof (sll));
1080 sll.sll_family = AF_PACKET;
1081 sll.sll_ifindex = ifr.ifr_ifindex;
1082 sll.sll_protocol = htons (ETH_P_ALL);
1083 if (-1 == ioctl (dev->fd_raw, SIOCGIFHWADDR, &ifr))
1086 "ioctl(SIOCGIFHWADDR) on interface `%.*s' failed: %s\n",
1087 IFNAMSIZ, dev->iface, strerror (errno));
1091 /* lookup iw mode */
1092 memset (&wrq, 0, sizeof (struct iwreq));
1093 strncpy (wrq.ifr_name, dev->iface, IFNAMSIZ);
1094 if (-1 == ioctl (dev->fd_raw, SIOCGIWMODE, &wrq))
1096 /* most probably not supported (ie for rtap ipw interface) *
1097 * so just assume its correctly set... */
1098 wrq.u.mode = IW_MODE_MONITOR;
1101 if (((ifr.ifr_hwaddr.sa_family != ARPHRD_IEEE80211) &&
1102 (ifr.ifr_hwaddr.sa_family != ARPHRD_IEEE80211_PRISM) &&
1103 (ifr.ifr_hwaddr.sa_family != ARPHRD_IEEE80211_FULL)) ||
1104 (wrq.u.mode != IW_MODE_MONITOR))
1107 "Error: interface `%.*s' is not in monitor mode\n",
1108 IFNAMSIZ, dev->iface);
1112 /* Is interface st to up, broadcast & running ? */
1113 if ((ifr.ifr_flags | IFF_UP | IFF_BROADCAST | IFF_RUNNING) != ifr.ifr_flags)
1115 /* Bring interface up */
1116 ifr.ifr_flags |= IFF_UP | IFF_BROADCAST | IFF_RUNNING;
1118 if (-1 == ioctl (dev->fd_raw, SIOCSIFFLAGS, &ifr))
1121 "ioctl(SIOCSIFFLAGS) on interface `%.*s' failed: %s\n",
1122 IFNAMSIZ, dev->iface, strerror (errno));
1127 /* bind the raw socket to the interface */
1128 if (-1 == bind (dev->fd_raw, (struct sockaddr *) &sll, sizeof (sll)))
1131 "Failed to bind interface `%.*s': %s\n", IFNAMSIZ,
1132 dev->iface, strerror (errno));
1136 /* lookup the hardware type */
1137 if (-1 == ioctl (dev->fd_raw, SIOCGIFHWADDR, &ifr))
1140 "ioctl(SIOCGIFHWADDR) on interface `%.*s' failed: %s\n",
1141 IFNAMSIZ, dev->iface, strerror (errno));
1145 memcpy (&dev->pl_mac, ifr.ifr_hwaddr.sa_data, MAC_ADDR_SIZE);
1146 dev->arptype_in = ifr.ifr_hwaddr.sa_family;
1147 if ((ifr.ifr_hwaddr.sa_family != ARPHRD_IEEE80211) &&
1148 (ifr.ifr_hwaddr.sa_family != ARPHRD_IEEE80211_PRISM) &&
1149 (ifr.ifr_hwaddr.sa_family != ARPHRD_IEEE80211_FULL))
1152 "Unsupported hardware link type %d on interface `%.*s'\n",
1153 ifr.ifr_hwaddr.sa_family, IFNAMSIZ, dev->iface);
1157 /* enable promiscuous mode */
1158 memset (&mr, 0, sizeof (mr));
1159 mr.mr_ifindex = sll.sll_ifindex;
1160 mr.mr_type = PACKET_MR_PROMISC;
1162 setsockopt (dev->fd_raw, SOL_PACKET, PACKET_ADD_MEMBERSHIP, &mr,
1166 "Failed to enable promiscuous mode on interface `%.*s'\n",
1167 IFNAMSIZ, dev->iface);
1176 * function to prepare the helper, e.g. sockets, device...
1177 * @param dev struct for the device
1178 * @param iface name of the interface
1179 * @return 0 on success
1182 wlaninit (struct Hardware_Infos *dev, const char *iface)
1188 dev->fd_raw = socket (PF_PACKET, SOCK_RAW, htons (ETH_P_ALL));
1189 if (0 > dev->fd_raw)
1191 fprintf (stderr, "Failed to create raw socket: %s\n", strerror (errno));
1194 if (dev->fd_raw >= FD_SETSIZE)
1197 "File descriptor too large for select (%d > %d)\n",
1198 dev->fd_raw, FD_SETSIZE);
1199 close (dev->fd_raw);
1203 /* mac80211 stack detection */
1206 sizeof (strbuf), "/sys/class/net/%s/phy80211/subsystem", iface);
1207 if ((ret < 0) || (ret >= sizeof (strbuf)) || (0 != stat (strbuf, &sbuf)))
1210 "Did not find 802.11 interface `%s'. Exiting.\n", iface);
1211 close (dev->fd_raw);
1214 strncpy (dev->iface, iface, IFNAMSIZ);
1215 if (0 != openraw (dev))
1217 close (dev->fd_raw);
1225 * Function to test incoming packets mac for being our own.
1227 * @param uint8_taIeeeHeader buffer of the packet
1228 * @param dev the Hardware_Infos struct
1229 * @return 0 if mac belongs to us, 1 if mac is for another target
1232 mac_test (const struct ieee80211_frame *uint8_taIeeeHeader,
1233 const struct Hardware_Infos *dev)
1235 if (0 != memcmp (uint8_taIeeeHeader->i_addr3, &mac_bssid, MAC_ADDR_SIZE))
1237 if (0 == memcmp (uint8_taIeeeHeader->i_addr1, &dev->pl_mac, MAC_ADDR_SIZE))
1239 if (0 == memcmp (uint8_taIeeeHeader->i_addr1, &bc_all_mac, MAC_ADDR_SIZE))
1246 * function to set the wlan header to make attacks more difficult
1247 * @param uint8_taIeeeHeader pointer to the header of the packet
1248 * @param dev pointer to the Hardware_Infos struct
1251 mac_set (struct ieee80211_frame *uint8_taIeeeHeader,
1252 const struct Hardware_Infos *dev)
1254 uint8_taIeeeHeader->i_fc[0] = 0x08;
1255 uint8_taIeeeHeader->i_fc[1] = 0x00;
1256 memcpy (uint8_taIeeeHeader->i_addr2, &dev->pl_mac, MAC_ADDR_SIZE);
1257 memcpy (uint8_taIeeeHeader->i_addr3, &mac_bssid, MAC_ADDR_SIZE);
1262 * function to process the data from the stdin
1263 * @param cls pointer to the device struct
1264 * @param client not used
1265 * @param hdr pointer to the start of the packet
1268 stdin_send_hw (void *cls, void *client,
1269 const struct GNUNET_MessageHeader *hdr)
1271 struct Hardware_Infos *dev = cls;
1272 struct sendbuf *write_pout = &dev->write_pout;
1273 struct Radiotap_Send *header = (struct Radiotap_Send *) &hdr[1];
1274 struct ieee80211_frame *wlanheader;
1276 struct RadioTapheader rtheader;
1278 rtheader.header.it_version = 0;
1279 rtheader.header.it_len = htole16 (0x0c);
1280 rtheader.header.it_present = htole32 (0x00008004);
1281 rtheader.rate = 0x00;
1282 rtheader.pad1 = 0x00;
1284 htole16 (IEEE80211_RADIOTAP_F_TX_NOACK | IEEE80211_RADIOTAP_F_TX_NOSEQ);
1286 /* { 0x00, 0x00, <-- radiotap version
1287 * 0x0c, 0x00, <- radiotap header length
1288 * 0x04, 0x80, 0x00, 0x00, <-- bitmap
1290 * 0x00, <-- padding for natural alignment
1291 * 0x18, 0x00, <-- TX flags
1294 sendsize = ntohs (hdr->size);
1296 sizeof (struct Radiotap_Send) + sizeof (struct GNUNET_MessageHeader))
1299 "Function stdin_send_hw: malformed packet (too small)\n");
1303 sizeof (struct Radiotap_Send) + sizeof (struct GNUNET_MessageHeader);
1305 if (MAXLINE < sendsize)
1307 fprintf (stderr, "Function stdin_send_hw: Packet too big for buffer\n");
1310 if (GNUNET_MESSAGE_TYPE_WLAN_HELPER_DATA != ntohs (hdr->type))
1312 fprintf (stderr, "Function stdin_send: wrong packet type\n");
1316 rtheader.header.it_len = htole16 (sizeof (rtheader));
1317 rtheader.rate = header->rate;
1318 memcpy (write_pout->buf, &rtheader, sizeof (rtheader));
1319 memcpy (write_pout->buf + sizeof (rtheader), &header[1], sendsize);
1320 /* payload contains MAC address, but we don't trust it, so we'll
1321 * overwrite it with OUR MAC address again to prevent mischief */
1323 (struct ieee80211_frame *) (write_pout->buf + sizeof (rtheader));
1324 mac_set (wlanheader, dev);
1325 write_pout->size = sendsize + sizeof (rtheader);
1330 * main function of the helper
1331 * @param argc number of arguments
1332 * @param argv arguments
1333 * @return 0 on success, 1 on error
1336 main (int argc, char *argv[])
1339 struct Hardware_Infos dev;
1340 char readbuf[MAXLINE];
1341 struct sendbuf write_std;
1348 struct GNUNET_SERVER_MessageStreamTokenizer *stdin_mst;
1353 "You must specify the name of the interface as the first and only argument to this program.\n");
1356 if (0 != wlaninit (&dev, argv[1]))
1359 if (0 != setresuid (uid, uid, uid))
1361 fprintf (stderr, "Failed to setresuid: %s\n", strerror (errno));
1362 /* not critical, continue anyway */
1365 dev.write_pout.size = 0;
1366 dev.write_pout.pos = 0;
1367 stdin_mst = GNUNET_SERVER_mst_create (&stdin_send_hw, &dev);
1369 /* send mac to STDOUT first */
1371 write_std.size = send_mac_to_plugin ((char *) &write_std.buf, &dev.pl_mac);
1378 if ((0 == dev.write_pout.size) && (1 == stdin_open))
1380 FD_SET (STDIN_FILENO, &rfds);
1381 maxfd = MAX (maxfd, STDIN_FILENO);
1383 if (0 == write_std.size)
1385 FD_SET (dev.fd_raw, &rfds);
1386 maxfd = MAX (maxfd, dev.fd_raw);
1389 if (0 < write_std.size)
1391 FD_SET (STDOUT_FILENO, &wfds);
1392 maxfd = MAX (maxfd, STDOUT_FILENO);
1394 if (0 < dev.write_pout.size)
1396 FD_SET (dev.fd_raw, &wfds);
1397 maxfd = MAX (maxfd, dev.fd_raw);
1399 retval = select (maxfd + 1, &rfds, &wfds, NULL, NULL);
1400 if ((-1 == retval) && (EINTR == errno))
1404 fprintf (stderr, "select failed: %s\n", strerror (errno));
1407 if (FD_ISSET (STDOUT_FILENO, &wfds))
1410 write (STDOUT_FILENO,
1411 write_std.buf + write_std.pos,
1412 write_std.size - write_std.pos);
1416 "Failed to write to STDOUT: %s\n", strerror (errno));
1419 write_std.pos += ret;
1420 if (write_std.pos == write_std.size)
1426 if (FD_ISSET (dev.fd_raw, &wfds))
1428 ret = write (dev.fd_raw, dev.write_pout.buf, dev.write_pout.size);
1432 "Failed to write to WLAN device: %s\n",
1436 dev.write_pout.pos += ret;
1437 if ((dev.write_pout.pos != dev.write_pout.size) && (ret != 0))
1439 /* we should not get partial sends with packet-oriented devices... */
1441 "Write error, partial send: %u/%u\n",
1442 dev.write_pout.pos, dev.write_pout.size);
1445 if (dev.write_pout.pos == dev.write_pout.size)
1447 dev.write_pout.pos = 0;
1448 dev.write_pout.size = 0;
1452 if (FD_ISSET (STDIN_FILENO, &rfds))
1454 ret = read (STDIN_FILENO, readbuf, sizeof (readbuf));
1458 "Read error from STDIN: %s\n", strerror (errno));
1463 /* stop reading... */
1466 GNUNET_SERVER_mst_receive (stdin_mst, NULL, readbuf, ret, GNUNET_NO,
1470 if (FD_ISSET (dev.fd_raw, &rfds))
1472 struct GNUNET_MessageHeader *header;
1473 struct Radiotap_rx *rxinfo;
1474 struct ieee80211_frame *datastart;
1476 header = (struct GNUNET_MessageHeader *) write_std.buf;
1477 rxinfo = (struct Radiotap_rx *) &header[1];
1478 datastart = (struct ieee80211_frame *) &rxinfo[1];
1480 linux_read (&dev, (unsigned char *) datastart,
1481 sizeof (write_std.buf) - sizeof (struct Radiotap_rx) -
1482 sizeof (struct GNUNET_MessageHeader), rxinfo);
1486 "Read error from raw socket: %s\n", strerror (errno));
1489 if ((0 < ret) && (0 == mac_test (datastart, &dev)))
1492 ret + sizeof (struct GNUNET_MessageHeader) +
1493 sizeof (struct Radiotap_rx);
1494 header->size = htons (write_std.size);
1495 header->type = htons (GNUNET_MESSAGE_TYPE_WLAN_HELPER_DATA);
1500 /* Error handling, try to clean up a bit at least */
1501 GNUNET_SERVER_mst_destroy (stdin_mst);
1503 return 1; /* we never exit 'normally' */
1506 /* end of gnunet-transport-wlan-helper.c */