2 * WPA Supplicant - Windows/NDIS driver interface - event processing
3 * Copyright (c) 2004-2005, Jouni Malinen <jkmaline@cc.hut.fi>
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License version 2 as
7 * published by the Free Software Foundation.
9 * Alternatively, this software may be distributed under the terms of BSD
12 * See README and COPYING for more details.
18 #include <sys/unistd.h>
19 #include <sys/types.h>
20 #ifndef CONFIG_NATIVE_WINDOWS
21 #include <sys/socket.h>
22 #include <netinet/in.h>
23 #endif /* CONFIG_NATIVE_WINDOWS */
27 #include "wpa_supplicant.h"
28 #include "l2_packet.h"
32 /* Keep this event processing in a separate file and without WinPcap headers to
33 * avoid conflicts with some of the header files. */
35 typedef struct _ADAPTER
* LPADAPTER
;
36 #include "driver_ndis.h"
39 void wpa_driver_ndis_event_connect(struct wpa_driver_ndis_data
*drv
);
40 void wpa_driver_ndis_event_disconnect(struct wpa_driver_ndis_data
*drv
);
41 void wpa_driver_ndis_event_media_specific(struct wpa_driver_ndis_data
*drv
,
42 const u8
*data
, size_t data_len
);
45 enum event_types
{ EVENT_CONNECT
, EVENT_DISCONNECT
,
46 EVENT_MEDIA_SPECIFIC
};
49 * enum event_types (as int, i.e., 4 octets)
50 * InstanceName length (1 octet)
51 * InstanceName (variable len)
52 * data length (1 octet, optional)
53 * data (variable len, optional)
57 static void wpa_driver_ndis_event_cb(int sock
, void *eloop_ctx
, void *sock_ctx
)
59 struct wpa_driver_ndis_data
*drv
= eloop_ctx
;
60 u8 buf
[512], *pos
, *data
= NULL
;
62 enum event_types type
;
63 unsigned char instance_len
;
67 res
= recv(sock
, buf
, sizeof(buf
), 0);
69 perror("wpa_driver_ndis_event_cb - recv");
72 wpa_hexdump(MSG_MSGDUMP
, "NDIS: received event data", buf
, res
);
73 if (res
< sizeof(int) + 1)
75 type
= *((int *) buf
);
76 pos
= buf
+ sizeof(int);
77 wpa_printf(MSG_DEBUG
, "NDIS: event - type %d", type
);
78 instance_len
= *pos
++;
79 if (instance_len
> buf
+ res
- pos
) {
80 wpa_printf(MSG_DEBUG
, "NDIS: event InstanceName overflow");
85 wpa_hexdump_ascii(MSG_MSGDUMP
, "NDIS: event InstanceName",
86 instance
, instance_len
);
88 if (buf
+ res
- pos
> 1) {
90 if (data_len
> buf
+ res
- pos
) {
91 wpa_printf(MSG_DEBUG
, "NDIS: event data overflow");
95 wpa_hexdump(MSG_MSGDUMP
, "NDIS: event data", data
, data_len
);
98 if (drv
->adapter_desc
) {
99 desc_len
= strlen(drv
->adapter_desc
);
100 if (instance_len
< desc_len
||
101 strncmp(drv
->adapter_desc
, instance
, desc_len
)) {
102 wpa_printf(MSG_DEBUG
, "NDIS: ignored event for "
108 * <driver desc> #<num>
109 * <driver desc> #<num> - <intermediate drv name> Miniport
111 for (i
= desc_len
+ 1; i
< instance_len
; i
++) {
112 if (instance
[i
] == '-') {
113 wpa_printf(MSG_DEBUG
, "NDIS: ignored event "
114 "for intermediate miniport");
122 wpa_driver_ndis_event_connect(drv
);
124 case EVENT_DISCONNECT
:
125 wpa_driver_ndis_event_disconnect(drv
);
127 case EVENT_MEDIA_SPECIFIC
:
128 wpa_driver_ndis_event_media_specific(drv
, data
, data_len
);
134 int wpa_driver_register_event_cb(struct wpa_driver_ndis_data
*drv
)
136 struct sockaddr_in addr
;
138 drv
->event_sock
= socket(PF_INET
, SOCK_DGRAM
, 0);
139 if (drv
->event_sock
< 0) {
144 /* These events are received from an external program, ndis_events,
145 * which is converting WMI events to more "UNIX-like" input for
146 * wpa_supplicant, i.e., UDP packets that can be received through the
147 * eloop mechanism. */
148 memset(&addr
, 0, sizeof(addr
));
149 addr
.sin_family
= AF_INET
;
150 addr
.sin_addr
.s_addr
= htonl((127 << 24) | 1);
151 addr
.sin_port
= htons(9876);
152 if (bind(drv
->event_sock
, (struct sockaddr
*) &addr
, sizeof(addr
)) < 0)
155 close(drv
->event_sock
);
156 drv
->event_sock
= -1;
160 eloop_register_read_sock(drv
->event_sock
, wpa_driver_ndis_event_cb
,