Home | History | Annotate | Line # | Download | only in dist
      1 /*
      2  * Copyright (c) 1999 - 2005 NetGroup, Politecnico di Torino (Italy)
      3  * Copyright (c) 2005 - 2010 CACE Technologies, Davis (California)
      4  * All rights reserved.
      5  *
      6  * Redistribution and use in source and binary forms, with or without
      7  * modification, are permitted provided that the following conditions
      8  * are met:
      9  *
     10  * 1. Redistributions of source code must retain the above copyright
     11  * notice, this list of conditions and the following disclaimer.
     12  * 2. Redistributions in binary form must reproduce the above copyright
     13  * notice, this list of conditions and the following disclaimer in the
     14  * documentation and/or other materials provided with the distribution.
     15  * 3. Neither the name of the Politecnico di Torino, CACE Technologies
     16  * nor the names of its contributors may be used to endorse or promote
     17  * products derived from this software without specific prior written
     18  * permission.
     19  *
     20  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
     21  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
     22  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
     23  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
     24  * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
     25  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
     26  * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
     27  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
     28  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
     29  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
     30  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
     31  *
     32  */
     33 
     34 #include <config.h>
     35 
     36 #include "pcap-int.h"
     37 
     38 #include <airpcap.h>
     39 
     40 #include "pcap-airpcap.h"
     41 
     42 /* Default size of the buffer we allocate in userland. */
     43 #define	AIRPCAP_DEFAULT_USER_BUFFER_SIZE 256000
     44 
     45 /* Default size of the buffer for the AirPcap adapter. */
     46 #define	AIRPCAP_DEFAULT_KERNEL_BUFFER_SIZE 1000000
     47 
     48 //
     49 // We load the AirPcap DLL dynamically, so that the code will
     50 // work whether you have it installed or not, and there don't
     51 // have to be two different versions of the library, one linked
     52 // to the AirPcap library and one not linked to it.
     53 //
     54 static pcap_code_handle_t airpcap_lib;
     55 
     56 typedef PCHAR (*AirpcapGetLastErrorHandler)(PAirpcapHandle);
     57 typedef BOOL (*AirpcapGetDeviceListHandler)(PAirpcapDeviceDescription *, PCHAR);
     58 typedef VOID (*AirpcapFreeDeviceListHandler)(PAirpcapDeviceDescription);
     59 typedef PAirpcapHandle (*AirpcapOpenHandler)(PCHAR, PCHAR);
     60 typedef VOID (*AirpcapCloseHandler)(PAirpcapHandle);
     61 typedef BOOL (*AirpcapSetDeviceMacFlagsHandler)(PAirpcapHandle, UINT);
     62 typedef BOOL (*AirpcapSetLinkTypeHandler)(PAirpcapHandle, AirpcapLinkType);
     63 typedef BOOL (*AirpcapGetLinkTypeHandler)(PAirpcapHandle, PAirpcapLinkType);
     64 typedef BOOL (*AirpcapSetKernelBufferHandler)(PAirpcapHandle, UINT);
     65 typedef BOOL (*AirpcapSetFilterHandler)(PAirpcapHandle, PVOID, UINT);
     66 typedef BOOL (*AirpcapSetMinToCopyHandler)(PAirpcapHandle, UINT);
     67 typedef BOOL (*AirpcapGetReadEventHandler)(PAirpcapHandle, HANDLE *);
     68 typedef BOOL (*AirpcapReadHandler)(PAirpcapHandle, PBYTE, UINT, PUINT);
     69 typedef BOOL (*AirpcapWriteHandler)(PAirpcapHandle, PCHAR, ULONG);
     70 typedef BOOL (*AirpcapGetStatsHandler)(PAirpcapHandle, PAirpcapStats);
     71 
     72 static AirpcapGetLastErrorHandler p_AirpcapGetLastError;
     73 static AirpcapGetDeviceListHandler p_AirpcapGetDeviceList;
     74 static AirpcapFreeDeviceListHandler p_AirpcapFreeDeviceList;
     75 static AirpcapOpenHandler p_AirpcapOpen;
     76 static AirpcapCloseHandler p_AirpcapClose;
     77 static AirpcapSetDeviceMacFlagsHandler p_AirpcapSetDeviceMacFlags;
     78 static AirpcapSetLinkTypeHandler p_AirpcapSetLinkType;
     79 static AirpcapGetLinkTypeHandler p_AirpcapGetLinkType;
     80 static AirpcapSetKernelBufferHandler p_AirpcapSetKernelBuffer;
     81 static AirpcapSetFilterHandler p_AirpcapSetFilter;
     82 static AirpcapSetMinToCopyHandler p_AirpcapSetMinToCopy;
     83 static AirpcapGetReadEventHandler p_AirpcapGetReadEvent;
     84 static AirpcapReadHandler p_AirpcapRead;
     85 static AirpcapWriteHandler p_AirpcapWrite;
     86 static AirpcapGetStatsHandler p_AirpcapGetStats;
     87 
     88 typedef enum LONG
     89 {
     90 	AIRPCAP_API_UNLOADED = 0,
     91 	AIRPCAP_API_LOADED,
     92 	AIRPCAP_API_CANNOT_LOAD,
     93 	AIRPCAP_API_LOADING
     94 } AIRPCAP_API_LOAD_STATUS;
     95 
     96 static AIRPCAP_API_LOAD_STATUS	airpcap_load_status;
     97 
     98 /*
     99  * NOTE: this function should be called by the pcap functions that can
    100  *       theoretically deal with the AirPcap library for the first time,
    101  *       namely listing the adapters and creating a pcap_t for an adapter.
    102  *       All the other ones (activate, close, read, write, set parameters)
    103  *       work on a pcap_t for an AirPcap device, meaning we've already
    104  *       created the pcap_t and thus have loaded the functions, so we do
    105  *       not need to call this function.
    106  */
    107 static AIRPCAP_API_LOAD_STATUS
    108 load_airpcap_functions(void)
    109 {
    110 	AIRPCAP_API_LOAD_STATUS current_status;
    111 
    112 	/*
    113 	 * We don't use a mutex because there's no place that
    114 	 * we can guarantee we'll be called before any threads
    115 	 * other than the main thread exists.  (For example,
    116 	 * this might be a static library, so we can't arrange
    117 	 * to be called by DllMain(), and there's no guarantee
    118 	 * that the application called pcap_init() - which is
    119 	 * supposed to be called only from one thread - so
    120 	 * we can't arrange to be called from it.)
    121 	 *
    122 	 * If nobody's tried to load it yet, mark it as
    123 	 * loading; in any case, return the status before
    124 	 * we modified it.
    125 	 */
    126 	current_status = InterlockedCompareExchange((LONG *)&airpcap_load_status,
    127 	    AIRPCAP_API_LOADING, AIRPCAP_API_UNLOADED);
    128 
    129 	/*
    130 	 * If the status was AIRPCAP_API_UNLOADED, we've set it
    131 	 * to AIRPCAP_API_LOADING, because we're going to be
    132 	 * the ones to load the library but current_status is
    133 	 * AIRPCAP_API_UNLOADED.
    134 	 *
    135 	 * if it was AIRPCAP_API_LOADING, meaning somebody else
    136 	 * was trying to load it, spin until they finish and
    137 	 * set the status to a value reflecting whether they
    138 	 * succeeded.
    139 	 */
    140 	while (current_status == AIRPCAP_API_LOADING) {
    141 		current_status = InterlockedCompareExchange((LONG*)&airpcap_load_status,
    142 		    AIRPCAP_API_LOADING, AIRPCAP_API_LOADING);
    143 		Sleep(10);
    144 	}
    145 
    146 	/*
    147 	 * At this point, current_status is either:
    148 	 *
    149 	 *	AIRPCAP_API_LOADED, in which case another thread
    150 	 *	loaded the library, so we're done;
    151 	 *
    152 	 *	AIRPCAP_API_CANNOT_LOAD, in which another thread
    153 	 *	tried and failed to load the library, so we're
    154 	 *	done - we won't try it ourselves;
    155 	 *
    156 	 *	AIRPCAP_API_LOADING, in which case *we're* the
    157 	 *	ones loading it, and should now try to do so.
    158 	 */
    159 	if (current_status == AIRPCAP_API_LOADED)
    160 		return AIRPCAP_API_LOADED;
    161 
    162 	if (current_status == AIRPCAP_API_CANNOT_LOAD)
    163 		return AIRPCAP_API_CANNOT_LOAD;
    164 
    165 	/*
    166 	 * Start out assuming we can't load it.
    167 	 */
    168 	current_status = AIRPCAP_API_CANNOT_LOAD;
    169 
    170 	airpcap_lib = pcapint_load_code("airpcap.dll");
    171 	if (airpcap_lib != NULL) {
    172 		/*
    173 		 * OK, we've loaded the library; now try to find the
    174 		 * functions we need in it.
    175 		 */
    176 		p_AirpcapGetLastError = (AirpcapGetLastErrorHandler) pcapint_find_function(airpcap_lib, "AirpcapGetLastError");
    177 		p_AirpcapGetDeviceList = (AirpcapGetDeviceListHandler) pcapint_find_function(airpcap_lib, "AirpcapGetDeviceList");
    178 		p_AirpcapFreeDeviceList = (AirpcapFreeDeviceListHandler) pcapint_find_function(airpcap_lib, "AirpcapFreeDeviceList");
    179 		p_AirpcapOpen = (AirpcapOpenHandler) pcapint_find_function(airpcap_lib, "AirpcapOpen");
    180 		p_AirpcapClose = (AirpcapCloseHandler) pcapint_find_function(airpcap_lib, "AirpcapClose");
    181 		p_AirpcapSetDeviceMacFlags = (AirpcapSetDeviceMacFlagsHandler) pcapint_find_function(airpcap_lib, "AirpcapSetDeviceMacFlags");
    182 		p_AirpcapSetLinkType = (AirpcapSetLinkTypeHandler) pcapint_find_function(airpcap_lib, "AirpcapSetLinkType");
    183 		p_AirpcapGetLinkType = (AirpcapGetLinkTypeHandler) pcapint_find_function(airpcap_lib, "AirpcapGetLinkType");
    184 		p_AirpcapSetKernelBuffer = (AirpcapSetKernelBufferHandler) pcapint_find_function(airpcap_lib, "AirpcapSetKernelBuffer");
    185 		p_AirpcapSetFilter = (AirpcapSetFilterHandler) pcapint_find_function(airpcap_lib, "AirpcapSetFilter");
    186 		p_AirpcapSetMinToCopy = (AirpcapSetMinToCopyHandler) pcapint_find_function(airpcap_lib, "AirpcapSetMinToCopy");
    187 		p_AirpcapGetReadEvent = (AirpcapGetReadEventHandler) pcapint_find_function(airpcap_lib, "AirpcapGetReadEvent");
    188 		p_AirpcapRead = (AirpcapReadHandler) pcapint_find_function(airpcap_lib, "AirpcapRead");
    189 		p_AirpcapWrite = (AirpcapWriteHandler) pcapint_find_function(airpcap_lib, "AirpcapWrite");
    190 		p_AirpcapGetStats = (AirpcapGetStatsHandler) pcapint_find_function(airpcap_lib, "AirpcapGetStats");
    191 
    192 		//
    193 		// Make sure that we found everything
    194 		//
    195 		if (p_AirpcapGetLastError != NULL &&
    196 		    p_AirpcapGetDeviceList != NULL &&
    197 		    p_AirpcapFreeDeviceList != NULL &&
    198 		    p_AirpcapOpen != NULL &&
    199 		    p_AirpcapClose != NULL &&
    200 		    p_AirpcapSetDeviceMacFlags != NULL &&
    201 		    p_AirpcapSetLinkType != NULL &&
    202 		    p_AirpcapGetLinkType != NULL &&
    203 		    p_AirpcapSetKernelBuffer != NULL &&
    204 		    p_AirpcapSetFilter != NULL &&
    205 		    p_AirpcapSetMinToCopy != NULL &&
    206 		    p_AirpcapGetReadEvent != NULL &&
    207 		    p_AirpcapRead != NULL &&
    208 		    p_AirpcapWrite != NULL &&
    209 		    p_AirpcapGetStats != NULL) {
    210 			/*
    211 			 * We have all we need.
    212 			 */
    213 			current_status = AIRPCAP_API_LOADED;
    214 		}
    215 	}
    216 
    217 	if (current_status != AIRPCAP_API_LOADED) {
    218 		/*
    219 		 * We failed; if we found the DLL, close the
    220 		 * handle for it.
    221 		 */
    222 		if (airpcap_lib != NULL) {
    223 			FreeLibrary(airpcap_lib);
    224 			airpcap_lib = NULL;
    225 		}
    226 	}
    227 
    228 	/*
    229 	 * Now set the status appropriately - and atomically.
    230 	 */
    231 	InterlockedExchange((LONG *)&airpcap_load_status, current_status);
    232 
    233 	return current_status;
    234 }
    235 
    236 /*
    237  * Private data for capturing on AirPcap devices.
    238  */
    239 struct pcap_airpcap {
    240 	PAirpcapHandle adapter;
    241 	int filtering_in_kernel;
    242 	int nonblock;
    243 	int read_timeout;
    244 	HANDLE read_event;
    245 	struct pcap_stat stat;
    246 };
    247 
    248 static int
    249 airpcap_setfilter(pcap_t *p, struct bpf_program *fp)
    250 {
    251 	struct pcap_airpcap *pa = p->priv;
    252 
    253 	if (!p_AirpcapSetFilter(pa->adapter, fp->bf_insns,
    254 	    fp->bf_len * sizeof(struct bpf_insn))) {
    255 		/*
    256 		 * Kernel filter not installed.
    257 		 *
    258 		 * XXX - we don't know whether this failed because:
    259 		 *
    260 		 *  the kernel rejected the filter program as invalid,
    261 		 *  in which case we should fall back on userland
    262 		 *  filtering;
    263 		 *
    264 		 *  the kernel rejected the filter program as too big,
    265 		 *  in which case we should again fall back on
    266 		 *  userland filtering;
    267 		 *
    268 		 *  there was some other problem, in which case we
    269 		 *  should probably report an error;
    270 		 *
    271 		 * So we just fall back on userland filtering in
    272 		 * all cases.
    273 		 */
    274 
    275 		/*
    276 		 * pcapint_install_bpf_program() validates the program.
    277 		 *
    278 		 * XXX - what if we already have a filter in the kernel?
    279 		 */
    280 		if (pcapint_install_bpf_program(p, fp) < 0)
    281 			return (-1);
    282 		pa->filtering_in_kernel = 0;	/* filtering in userland */
    283 		return (0);
    284 	}
    285 
    286 	/*
    287 	 * It worked.
    288 	 */
    289 	pa->filtering_in_kernel = 1;	/* filtering in the kernel */
    290 
    291 	/*
    292 	 * Discard any previously-received packets, as they might have
    293 	 * passed whatever filter was formerly in effect, but might
    294 	 * not pass this filter (BIOCSETF discards packets buffered
    295 	 * in the kernel, so you can lose packets in any case).
    296 	 */
    297 	p->cc = 0;
    298 	return (0);
    299 }
    300 
    301 static int
    302 airpcap_set_datalink(pcap_t *p, int dlt)
    303 {
    304 	struct pcap_airpcap *pa = p->priv;
    305 	AirpcapLinkType type;
    306 
    307 	switch (dlt) {
    308 
    309 	case DLT_IEEE802_11_RADIO:
    310 		type = AIRPCAP_LT_802_11_PLUS_RADIO;
    311 		break;
    312 
    313 	case DLT_PPI:
    314 		type = AIRPCAP_LT_802_11_PLUS_PPI;
    315 		break;
    316 
    317 	case DLT_IEEE802_11:
    318 		type = AIRPCAP_LT_802_11;
    319 		break;
    320 
    321 	default:
    322 		/* This can't happen; just return. */
    323 		return (0);
    324 	}
    325 	if (!p_AirpcapSetLinkType(pa->adapter, type)) {
    326 		snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
    327 		    "AirpcapSetLinkType() failed: %s",
    328 		    p_AirpcapGetLastError(pa->adapter));
    329 		return (-1);
    330 	}
    331 	p->linktype = dlt;
    332 	return (0);
    333 }
    334 
    335 static int
    336 airpcap_getnonblock(pcap_t *p)
    337 {
    338 	struct pcap_airpcap *pa = p->priv;
    339 
    340 	return (pa->nonblock);
    341 }
    342 
    343 static int
    344 airpcap_setnonblock(pcap_t *p, int nonblock)
    345 {
    346 	struct pcap_airpcap *pa = p->priv;
    347 	int newtimeout;
    348 
    349 	if (nonblock) {
    350 		/*
    351 		 * Set the packet buffer timeout to -1 for non-blocking
    352 		 * mode.
    353 		 */
    354 		newtimeout = -1;
    355 	} else {
    356 		/*
    357 		 * Restore the timeout set when the device was opened.
    358 		 * (Note that this may be -1, in which case we're not
    359 		 * really leaving non-blocking mode.  However, although
    360 		 * the timeout argument to pcap_set_timeout() and
    361 		 * pcap_open_live() is an int, you're not supposed to
    362 		 * supply a negative value, so that "shouldn't happen".)
    363 		 */
    364 		newtimeout = p->opt.timeout;
    365 	}
    366 	pa->read_timeout = newtimeout;
    367 	pa->nonblock = (newtimeout == -1);
    368 	return (0);
    369 }
    370 
    371 static int
    372 airpcap_stats(pcap_t *p, struct pcap_stat *ps)
    373 {
    374 	struct pcap_airpcap *pa = p->priv;
    375 	AirpcapStats tas;
    376 
    377 	/*
    378 	 * Try to get statistics.
    379 	 */
    380 	if (!p_AirpcapGetStats(pa->adapter, &tas)) {
    381 		snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
    382 		    "AirpcapGetStats() failed: %s",
    383 		    p_AirpcapGetLastError(pa->adapter));
    384 		return (-1);
    385 	}
    386 
    387 	ps->ps_drop = tas.Drops;
    388 	ps->ps_recv = tas.Recvs;
    389 	ps->ps_ifdrop = tas.IfDrops;
    390 
    391 	return (0);
    392 }
    393 
    394 /*
    395  * Win32-only routine for getting statistics.
    396  *
    397  * This way is definitely safer than passing the pcap_stat * from the userland.
    398  * In fact, there could happen than the user allocates a variable which is not
    399  * big enough for the new structure, and the library will write in a zone
    400  * which is not allocated to this variable.
    401  *
    402  * In this way, we're pretty sure we are writing on memory allocated to this
    403  * variable.
    404  *
    405  * XXX - but this is the wrong way to handle statistics.  Instead, we should
    406  * have an API that returns data in a form like the Options section of a
    407  * pcapng Interface Statistics Block:
    408  *
    409  *    https://xml2rfc.tools.ietf.org/cgi-bin/xml2rfc.cgi?url=https://raw.githubusercontent.com/pcapng/pcapng/master/draft-tuexen-opsawg-pcapng.xml&modeAsFormat=html/ascii&type=ascii#rfc.section.4.6
    410  *
    411  * which would let us add new statistics straightforwardly and indicate which
    412  * statistics we are and are *not* providing, rather than having to provide
    413  * possibly-bogus values for statistics we can't provide.
    414  */
    415 static struct pcap_stat *
    416 airpcap_stats_ex(pcap_t *p, int *pcap_stat_size)
    417 {
    418 	struct pcap_airpcap *pa = p->priv;
    419 	AirpcapStats tas;
    420 
    421 	*pcap_stat_size = sizeof (p->stat);
    422 
    423 	/*
    424 	 * Try to get statistics.
    425 	 */
    426 	if (!p_AirpcapGetStats(pa->adapter, &tas)) {
    427 		snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
    428 		    "AirpcapGetStats() failed: %s",
    429 		    p_AirpcapGetLastError(pa->adapter));
    430 		return (NULL);
    431 	}
    432 
    433 	p->stat.ps_recv = tas.Recvs;
    434 	p->stat.ps_drop = tas.Drops;
    435 	p->stat.ps_ifdrop = tas.IfDrops;
    436 	/*
    437 	 * Just in case this is ever compiled for a target other than
    438 	 * Windows, which is extremely unlikely at best.
    439 	 */
    440 #ifdef _WIN32
    441 	p->stat.ps_capt = tas.Capt;
    442 #endif
    443 	return (&p->stat);
    444 }
    445 
    446 /* Set the dimension of the kernel-level capture buffer */
    447 static int
    448 airpcap_setbuff(pcap_t *p, int dim)
    449 {
    450 	struct pcap_airpcap *pa = p->priv;
    451 
    452 	if (!p_AirpcapSetKernelBuffer(pa->adapter, dim)) {
    453 		snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
    454 		    "AirpcapSetKernelBuffer() failed: %s",
    455 		    p_AirpcapGetLastError(pa->adapter));
    456 		return (-1);
    457 	}
    458 	return (0);
    459 }
    460 
    461 /* Set the driver working mode */
    462 static int
    463 airpcap_setmode(pcap_t *p, int mode)
    464 {
    465 	 if (mode != MODE_CAPT) {
    466 		snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
    467 		    "Only MODE_CAPT is supported on an AirPcap adapter");
    468 		return (-1);
    469 	 }
    470 	 return (0);
    471 }
    472 
    473 /*set the minimum amount of data that will release a read call*/
    474 static int
    475 airpcap_setmintocopy(pcap_t *p, int size)
    476 {
    477 	struct pcap_airpcap *pa = p->priv;
    478 
    479 	if (!p_AirpcapSetMinToCopy(pa->adapter, size)) {
    480 		snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
    481 		    "AirpcapSetMinToCopy() failed: %s",
    482 		    p_AirpcapGetLastError(pa->adapter));
    483 		return (-1);
    484 	}
    485 	return (0);
    486 }
    487 
    488 static HANDLE
    489 airpcap_getevent(pcap_t *p)
    490 {
    491 	struct pcap_airpcap *pa = p->priv;
    492 
    493 	return (pa->read_event);
    494 }
    495 
    496 static int
    497 airpcap_oid_get_request(pcap_t *p, bpf_u_int32 oid _U_, void *data _U_,
    498     size_t *lenp _U_)
    499 {
    500 	snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
    501 	    "Getting OID values is not supported on an AirPcap adapter");
    502 	return (PCAP_ERROR);
    503 }
    504 
    505 static int
    506 airpcap_oid_set_request(pcap_t *p, bpf_u_int32 oid _U_, const void *data _U_,
    507     size_t *lenp _U_)
    508 {
    509 	snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
    510 	    "Setting OID values is not supported on an AirPcap adapter");
    511 	return (PCAP_ERROR);
    512 }
    513 
    514 static u_int
    515 airpcap_sendqueue_transmit(pcap_t *p, pcap_send_queue *queue _U_, int sync _U_)
    516 {
    517 	snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
    518 	    "Cannot queue packets for transmission on an AirPcap adapter");
    519 	return (0);
    520 }
    521 
    522 static int
    523 airpcap_setuserbuffer(pcap_t *p, int size)
    524 {
    525 	unsigned char *new_buff;
    526 
    527 	if (size <= 0) {
    528 		/* Bogus parameter */
    529 		snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
    530 		    "Error: invalid size %d",size);
    531 		return (-1);
    532 	}
    533 
    534 	/* Allocate the buffer */
    535 	new_buff = (unsigned char *)malloc(sizeof(char)*size);
    536 
    537 	if (!new_buff) {
    538 		snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
    539 		    "Error: not enough memory");
    540 		return (-1);
    541 	}
    542 
    543 	free(p->buffer);
    544 
    545 	p->buffer = new_buff;
    546 	p->bufsize = size;
    547 
    548 	return (0);
    549 }
    550 
    551 static int
    552 airpcap_live_dump(pcap_t *p, char *filename _U_, int maxsize _U_,
    553     int maxpacks _U_)
    554 {
    555 	snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
    556 	    "AirPcap adapters don't support live dump");
    557 	return (-1);
    558 }
    559 
    560 static int
    561 airpcap_live_dump_ended(pcap_t *p, int sync _U_)
    562 {
    563 	snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
    564 	    "AirPcap adapters don't support live dump");
    565 	return (-1);
    566 }
    567 
    568 static PAirpcapHandle
    569 airpcap_get_airpcap_handle(pcap_t *p)
    570 {
    571 	struct pcap_airpcap *pa = p->priv;
    572 
    573 	return (pa->adapter);
    574 }
    575 
    576 static int
    577 airpcap_read(pcap_t *p, int cnt, pcap_handler callback, u_char *user)
    578 {
    579 	struct pcap_airpcap *pa = p->priv;
    580 	int cc;
    581 	int n;
    582 	register u_char *bp, *ep;
    583 	UINT bytes_read;
    584 	u_char *datap;
    585 
    586 	cc = p->cc;
    587 	if (cc == 0) {
    588 		/*
    589 		 * Has "pcap_breakloop()" been called?
    590 		 */
    591 		if (p->break_loop) {
    592 			/*
    593 			 * Yes - clear the flag that indicates that it
    594 			 * has, and return PCAP_ERROR_BREAK to indicate
    595 			 * that we were told to break out of the loop.
    596 			 */
    597 			p->break_loop = 0;
    598 			return (PCAP_ERROR_BREAK);
    599 		}
    600 
    601 		//
    602 		// If we're not in non-blocking mode, wait for data to
    603 		// arrive.
    604 		//
    605 		if (pa->read_timeout != -1) {
    606 			WaitForSingleObject(pa->read_event,
    607 			    (pa->read_timeout ==0 )? INFINITE: pa->read_timeout);
    608 		}
    609 
    610 		//
    611 		// Read the data.
    612 		// p_AirpcapRead doesn't block.
    613 		//
    614 		if (!p_AirpcapRead(pa->adapter, (PBYTE)p->buffer,
    615 		    p->bufsize, &bytes_read)) {
    616 			snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
    617 			    "AirpcapRead() failed: %s",
    618 			    p_AirpcapGetLastError(pa->adapter));
    619 			return (-1);
    620 		}
    621 		cc = bytes_read;
    622 		bp = (u_char *)p->buffer;
    623 	} else
    624 		bp = p->bp;
    625 
    626 	/*
    627 	 * Loop through each packet.
    628 	 *
    629 	 * This assumes that a single buffer of packets will have
    630 	 * <= INT_MAX packets, so the packet count doesn't overflow.
    631 	 */
    632 #define bhp ((AirpcapBpfHeader *)bp)
    633 	n = 0;
    634 	ep = bp + cc;
    635 	for (;;) {
    636 		register u_int caplen, hdrlen;
    637 
    638 		/*
    639 		 * Has "pcap_breakloop()" been called?
    640 		 * If so, return immediately - if we haven't read any
    641 		 * packets, clear the flag and return PCAP_ERROR_BREAK
    642 		 * to indicate that we were told to break out of the loop,
    643 		 * otherwise leave the flag set, so that the *next* call
    644 		 * will break out of the loop without having read any
    645 		 * packets, and return the number of packets we've
    646 		 * processed so far.
    647 		 */
    648 		if (p->break_loop) {
    649 			if (n == 0) {
    650 				p->break_loop = 0;
    651 				return (PCAP_ERROR_BREAK);
    652 			} else {
    653 				p->bp = bp;
    654 				p->cc = (int) (ep - bp);
    655 				return (n);
    656 			}
    657 		}
    658 		if (bp >= ep)
    659 			break;
    660 
    661 		caplen = bhp->Caplen;
    662 		hdrlen = bhp->Hdrlen;
    663 		datap = bp + hdrlen;
    664 		/*
    665 		 * Short-circuit evaluation: if using BPF filter
    666 		 * in the AirPcap adapter, no need to do it now -
    667 		 * we already know the packet passed the filter.
    668 		 */
    669 		if (pa->filtering_in_kernel ||
    670 		    p->fcode.bf_insns == NULL ||
    671 		    pcapint_filter(p->fcode.bf_insns, datap, bhp->Originallen, caplen)) {
    672 			struct pcap_pkthdr pkthdr;
    673 
    674 			pkthdr.ts.tv_sec = bhp->TsSec;
    675 			pkthdr.ts.tv_usec = bhp->TsUsec;
    676 			pkthdr.caplen = caplen;
    677 			pkthdr.len = bhp->Originallen;
    678 			(*callback)(user, &pkthdr, datap);
    679 			bp += AIRPCAP_WORDALIGN(caplen + hdrlen);
    680 			if (++n >= cnt && !PACKET_COUNT_IS_UNLIMITED(cnt)) {
    681 				p->bp = bp;
    682 				p->cc = (int)(ep - bp);
    683 				return (n);
    684 			}
    685 		} else {
    686 			/*
    687 			 * Skip this packet.
    688 			 */
    689 			bp += AIRPCAP_WORDALIGN(caplen + hdrlen);
    690 		}
    691 	}
    692 #undef bhp
    693 	p->cc = 0;
    694 	return (n);
    695 }
    696 
    697 static int
    698 airpcap_inject(pcap_t *p, const void *buf, int size)
    699 {
    700 	struct pcap_airpcap *pa = p->priv;
    701 
    702 	/*
    703 	 * XXX - the second argument to AirpcapWrite() *should* have
    704 	 * been declared as a const pointer - a write function that
    705 	 * stomps on what it writes is *extremely* rude - but such
    706 	 * is life.  We assume it is, in fact, not going to write on
    707 	 * our buffer.
    708 	 */
    709 	if (!p_AirpcapWrite(pa->adapter, (void *)buf, size)) {
    710 		snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
    711 		    "AirpcapWrite() failed: %s",
    712 		    p_AirpcapGetLastError(pa->adapter));
    713 		return (-1);
    714 	}
    715 
    716 	/*
    717 	 * We assume it all got sent if "AirpcapWrite()" succeeded.
    718 	 * "pcap_inject()" is expected to return the number of bytes
    719 	 * sent.
    720 	 */
    721 	return (size);
    722 }
    723 
    724 static void
    725 airpcap_cleanup(pcap_t *p)
    726 {
    727 	struct pcap_airpcap *pa = p->priv;
    728 
    729 	if (pa->adapter != NULL) {
    730 		p_AirpcapClose(pa->adapter);
    731 		pa->adapter = NULL;
    732 	}
    733 	pcapint_cleanup_live_common(p);
    734 }
    735 
    736 static void
    737 airpcap_breakloop(pcap_t *p)
    738 {
    739 	HANDLE read_event;
    740 
    741 	pcapint_breakloop_common(p);
    742 	struct pcap_airpcap *pa = p->priv;
    743 
    744 	/* XXX - what if either of these fail? */
    745 	/*
    746 	 * XXX - will SetEvent() force a wakeup and, if so, will
    747 	 * the AirPcap read code handle that sanely?
    748 	 */
    749 	if (!p_AirpcapGetReadEvent(pa->adapter, &read_event))
    750 		return;
    751 	SetEvent(read_event);
    752 }
    753 
    754 static int
    755 airpcap_activate(pcap_t *p)
    756 {
    757 	struct pcap_airpcap *pa = p->priv;
    758 	char *device = p->opt.device;
    759 	char airpcap_errbuf[AIRPCAP_ERRBUF_SIZE];
    760 	BOOL status;
    761 	AirpcapLinkType link_type;
    762 
    763 	pa->adapter = p_AirpcapOpen(device, airpcap_errbuf);
    764 	if (pa->adapter == NULL) {
    765 		snprintf(p->errbuf, PCAP_ERRBUF_SIZE, "%s", airpcap_errbuf);
    766 		return (PCAP_ERROR);
    767 	}
    768 
    769 	/*
    770 	 * Set monitor mode appropriately.
    771 	 * Always turn off the "ACK frames sent to the card" mode.
    772 	 */
    773 	if (p->opt.rfmon) {
    774 		status = p_AirpcapSetDeviceMacFlags(pa->adapter,
    775 		    AIRPCAP_MF_MONITOR_MODE_ON);
    776 	} else
    777 		status = p_AirpcapSetDeviceMacFlags(pa->adapter,
    778 		    AIRPCAP_MF_ACK_FRAMES_ON);
    779 	if (!status) {
    780 		p_AirpcapClose(pa->adapter);
    781 		snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
    782 		    "AirpcapSetDeviceMacFlags() failed: %s",
    783 		    p_AirpcapGetLastError(pa->adapter));
    784 		return (PCAP_ERROR);
    785 	}
    786 
    787 	/*
    788 	 * Turn a negative snapshot value (invalid), a snapshot value of
    789 	 * 0 (unspecified), or a value bigger than the normal maximum
    790 	 * value, into the maximum allowed value.
    791 	 *
    792 	 * If some application really *needs* a bigger snapshot
    793 	 * length, we should just increase MAXIMUM_SNAPLEN.
    794 	 */
    795 	if (p->snapshot <= 0 || p->snapshot > MAXIMUM_SNAPLEN)
    796 		p->snapshot = MAXIMUM_SNAPLEN;
    797 
    798 	/*
    799 	 * If the buffer size wasn't explicitly set, default to
    800 	 * AIRPCAP_DEFAULT_KERNEL_BUFFER_SIZE.
    801 	 */
    802 	if (p->opt.buffer_size == 0)
    803 		p->opt.buffer_size = AIRPCAP_DEFAULT_KERNEL_BUFFER_SIZE;
    804 
    805 	if (!p_AirpcapSetKernelBuffer(pa->adapter, p->opt.buffer_size)) {
    806 		snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
    807 		    "AirpcapSetKernelBuffer() failed: %s",
    808 		    p_AirpcapGetLastError(pa->adapter));
    809 		goto bad;
    810 	}
    811 
    812 	if(!p_AirpcapGetReadEvent(pa->adapter, &pa->read_event)) {
    813 		snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
    814 		    "AirpcapGetReadEvent() failed: %s",
    815 		    p_AirpcapGetLastError(pa->adapter));
    816 		goto bad;
    817 	}
    818 
    819 	/* Set the buffer size */
    820 	p->bufsize = AIRPCAP_DEFAULT_USER_BUFFER_SIZE;
    821 	p->buffer = malloc(p->bufsize);
    822 	if (p->buffer == NULL) {
    823 		pcapint_fmt_errmsg_for_errno(p->errbuf, PCAP_ERRBUF_SIZE,
    824 		    errno, "malloc");
    825 		goto bad;
    826 	}
    827 
    828 	if (p->opt.immediate) {
    829 		/* Tell the driver to copy the buffer as soon as data arrives. */
    830 		if (!p_AirpcapSetMinToCopy(pa->adapter, 0)) {
    831 			snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
    832 			    "AirpcapSetMinToCopy() failed: %s",
    833 			    p_AirpcapGetLastError(pa->adapter));
    834 			goto bad;
    835 		}
    836 	} else {
    837 		/*
    838 		 * Tell the driver to copy the buffer only if it contains
    839 		 * at least 16K.
    840 		 */
    841 		if (!p_AirpcapSetMinToCopy(pa->adapter, 16000)) {
    842 			snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
    843 			    "AirpcapSetMinToCopy() failed: %s",
    844 			    p_AirpcapGetLastError(pa->adapter));
    845 			goto bad;
    846 		}
    847 	}
    848 
    849 	/*
    850 	 * Find out what the default link-layer header type is,
    851 	 * and set p->datalink to that.
    852 	 *
    853 	 * We don't force it to another value because there
    854 	 * might be some programs using WinPcap/Npcap that,
    855 	 * when capturing on AirPcap devices, assume the
    856 	 * default value set with the AirPcap configuration
    857 	 * program is what you get.
    858 	 *
    859 	 * The out-of-the-box default appears to be radiotap.
    860 	 */
    861 	if (!p_AirpcapGetLinkType(pa->adapter, &link_type)) {
    862 		/* That failed. */
    863 		snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
    864 		    "AirpcapGetLinkType() failed: %s",
    865 		    p_AirpcapGetLastError(pa->adapter));
    866 		goto bad;
    867 	}
    868 	switch (link_type) {
    869 
    870 	case AIRPCAP_LT_802_11_PLUS_RADIO:
    871 		p->linktype = DLT_IEEE802_11_RADIO;
    872 		break;
    873 
    874 	case AIRPCAP_LT_802_11_PLUS_PPI:
    875 		p->linktype = DLT_PPI;
    876 		break;
    877 
    878 	case AIRPCAP_LT_802_11:
    879 		p->linktype = DLT_IEEE802_11;
    880 		break;
    881 
    882 	case AIRPCAP_LT_UNKNOWN:
    883 	default:
    884 		/* OK, what? */
    885 		snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
    886 		    "AirpcapGetLinkType() returned unknown link type %u",
    887 		    link_type);
    888 		goto bad;
    889 	}
    890 
    891 	/*
    892 	 * Now provide a list of all the supported types; we
    893 	 * assume they all work.  We put radiotap at the top,
    894 	 * followed by PPI, followed by "no radio metadata".
    895 	 */
    896 	p->dlt_list = (u_int *) malloc(sizeof(u_int) * 3);
    897 	if (p->dlt_list == NULL) {
    898 		pcapint_fmt_errmsg_for_errno(p->errbuf, PCAP_ERRBUF_SIZE,
    899 		    errno, "malloc");
    900 		goto bad;
    901 	}
    902 	p->dlt_list[0] = DLT_IEEE802_11_RADIO;
    903 	p->dlt_list[1] = DLT_PPI;
    904 	p->dlt_list[2] = DLT_IEEE802_11;
    905 	p->dlt_count = 3;
    906 
    907 	p->read_op = airpcap_read;
    908 	p->inject_op = airpcap_inject;
    909 	p->setfilter_op = airpcap_setfilter;
    910 	p->setdirection_op = NULL;	/* Not implemented. */
    911 	p->set_datalink_op = airpcap_set_datalink;
    912 	p->getnonblock_op = airpcap_getnonblock;
    913 	p->setnonblock_op = airpcap_setnonblock;
    914 	p->breakloop_op = airpcap_breakloop;
    915 	p->stats_op = airpcap_stats;
    916 	p->stats_ex_op = airpcap_stats_ex;
    917 	p->setbuff_op = airpcap_setbuff;
    918 	p->setmode_op = airpcap_setmode;
    919 	p->setmintocopy_op = airpcap_setmintocopy;
    920 	p->getevent_op = airpcap_getevent;
    921 	p->oid_get_request_op = airpcap_oid_get_request;
    922 	p->oid_set_request_op = airpcap_oid_set_request;
    923 	p->sendqueue_transmit_op = airpcap_sendqueue_transmit;
    924 	p->setuserbuffer_op = airpcap_setuserbuffer;
    925 	p->live_dump_op = airpcap_live_dump;
    926 	p->live_dump_ended_op = airpcap_live_dump_ended;
    927 	p->get_airpcap_handle_op = airpcap_get_airpcap_handle;
    928 	p->cleanup_op = airpcap_cleanup;
    929 
    930 	return (0);
    931  bad:
    932 	airpcap_cleanup(p);
    933 	return (PCAP_ERROR);
    934 }
    935 
    936 /*
    937  * Monitor mode is supported.
    938  */
    939 static int
    940 airpcap_can_set_rfmon(pcap_t *p)
    941 {
    942 	return (1);
    943 }
    944 
    945 int
    946 device_is_airpcap(const char *device, char *ebuf)
    947 {
    948 	static const char airpcap_prefix[] = "\\\\.\\airpcap";
    949 
    950 	/*
    951 	 * We don't determine this by calling AirpcapGetDeviceList()
    952 	 * and looking at the list, as that appears to be a costly
    953 	 * operation.
    954 	 *
    955 	 * Instead, we just check whether it begins with "\\.\airpcap".
    956 	 */
    957 	if (strncmp(device, airpcap_prefix, sizeof airpcap_prefix - 1) == 0) {
    958 		/*
    959 		 * Yes, it's an AirPcap device.
    960 		 */
    961 		return (1);
    962 	}
    963 
    964 	/*
    965 	 * No, it's not an AirPcap device.
    966 	 */
    967 	return (0);
    968 }
    969 
    970 pcap_t *
    971 airpcap_create(const char *device, char *ebuf, int *is_ours)
    972 {
    973 	int ret;
    974 	pcap_t *p;
    975 
    976 	/*
    977 	 * This can be called before we've tried loading the library,
    978 	 * so do so if we haven't already tried to do so.
    979 	 */
    980 	if (load_airpcap_functions() != AIRPCAP_API_LOADED) {
    981 		/*
    982 		 * We assume this means that we don't have the AirPcap
    983 		 * software installed, which probably means we don't
    984 		 * have an AirPcap device.
    985 		 *
    986 		 * Don't treat that as an error.
    987 		 */
    988 		*is_ours = 0;
    989 		return (NULL);
    990 	}
    991 
    992 	/*
    993 	 * Is this an AirPcap device?
    994 	 */
    995 	ret = device_is_airpcap(device, ebuf);
    996 	if (ret == 0) {
    997 		/* No. */
    998 		*is_ours = 0;
    999 		return (NULL);
   1000 	}
   1001 
   1002 	/*
   1003 	 * Yes.
   1004 	 */
   1005 	*is_ours = 1;
   1006 	p = PCAP_CREATE_COMMON(ebuf, struct pcap_airpcap);
   1007 	if (p == NULL)
   1008 		return (NULL);
   1009 
   1010 	p->activate_op = airpcap_activate;
   1011 	p->can_set_rfmon_op = airpcap_can_set_rfmon;
   1012 	return (p);
   1013 }
   1014 
   1015 /*
   1016  * Add all AirPcap devices.
   1017  */
   1018 int
   1019 airpcap_findalldevs(pcap_if_list_t *devlistp, char *errbuf)
   1020 {
   1021 	AirpcapDeviceDescription *airpcap_devices, *airpcap_device;
   1022 	char airpcap_errbuf[AIRPCAP_ERRBUF_SIZE];
   1023 
   1024 	/*
   1025 	 * This can be called before we've tried loading the library,
   1026 	 * so do so if we haven't already tried to do so.
   1027 	 */
   1028 	if (load_airpcap_functions() != AIRPCAP_API_LOADED) {
   1029 		/*
   1030 		 * XXX - unless the error is "no such DLL", report this
   1031 		 * as an error rather than as "no AirPcap devices"?
   1032 		 */
   1033 		return (0);
   1034 	}
   1035 
   1036 	if (!p_AirpcapGetDeviceList(&airpcap_devices, airpcap_errbuf)) {
   1037 		snprintf(errbuf, PCAP_ERRBUF_SIZE,
   1038 		    "AirpcapGetDeviceList() failed: %s", airpcap_errbuf);
   1039 		return (-1);
   1040 	}
   1041 
   1042 	for (airpcap_device = airpcap_devices; airpcap_device != NULL;
   1043 	    airpcap_device = airpcap_device->next) {
   1044 		if (pcapint_add_dev(devlistp, airpcap_device->Name, 0,
   1045 		    airpcap_device->Description, errbuf) == NULL) {
   1046 			/*
   1047 			 * Failure.
   1048 			 */
   1049 			p_AirpcapFreeDeviceList(airpcap_devices);
   1050 			return (-1);
   1051 		}
   1052 	}
   1053 	p_AirpcapFreeDeviceList(airpcap_devices);
   1054 	return (0);
   1055 }
   1056