]>
Commit | Line | Data |
---|---|---|
3bccf403 AM |
1 | diff -u -p linux/include/linux/wireless.14.h linux/include/linux/wireless.h |
2 | --- linux/include/linux/wireless.14.h Thu Aug 15 19:31:40 2002 | |
3 | +++ linux/include/linux/wireless.h Thu Aug 15 19:42:22 2002 | |
4 | @@ -1,7 +1,7 @@ | |
5 | /* | |
6 | * This file define a set of standard wireless extensions | |
7 | * | |
8 | - * Version : 14 25.1.02 | |
9 | + * Version : 15 12.7.02 | |
10 | * | |
11 | * Authors : Jean Tourrilhes - HPL - <jt@hpl.hp.com> | |
12 | * Copyright (c) 1997-2002 Jean Tourrilhes, All Rights Reserved. | |
13 | @@ -80,7 +80,7 @@ | |
14 | * (there is some stuff that will be added in the future...) | |
15 | * I just plan to increment with each new version. | |
16 | */ | |
17 | -#define WIRELESS_EXT 14 | |
18 | +#define WIRELESS_EXT 15 | |
19 | ||
20 | /* | |
21 | * Changes : | |
22 | @@ -153,17 +153,32 @@ | |
23 | * - Define additional specific event numbers | |
24 | * - Add "addr" and "param" fields in union iwreq_data | |
25 | * - AP scanning stuff (SIOCSIWSCAN and friends) | |
26 | + * | |
27 | + * V14 to V15 | |
28 | + * ---------- | |
29 | + * - Add IW_PRIV_TYPE_ADDR for struct sockaddr private arg | |
30 | + * - Make struct iw_freq signed (both m & e), add explicit padding | |
31 | + * - Add IWEVCUSTOM for driver specific event/scanning token | |
32 | + * - Add IW_MAX_GET_SPY for driver returning a lot of addresses | |
33 | + * - Add IW_TXPOW_RANGE for range of Tx Powers | |
34 | + * - Add IWEVREGISTERED & IWEVEXPIRED events for Access Points | |
35 | + * - Add IW_MODE_MONITOR for passive monitor | |
36 | */ | |
37 | ||
38 | /**************************** CONSTANTS ****************************/ | |
39 | ||
40 | /* -------------------------- IOCTL LIST -------------------------- */ | |
41 | ||
42 | -/* Basic operations */ | |
43 | +/* Wireless Identification */ | |
44 | #define SIOCSIWCOMMIT 0x8B00 /* Commit pending changes to driver */ | |
45 | #define SIOCGIWNAME 0x8B01 /* get name == wireless protocol */ | |
46 | -#define SIOCSIWNWID 0x8B02 /* set network id (the cell) */ | |
47 | -#define SIOCGIWNWID 0x8B03 /* get network id */ | |
48 | +/* SIOCGIWNAME is used to verify the presence of Wireless Extensions. | |
49 | + * Common values : "IEEE 802.11-DS", "IEEE 802.11-FH", "IEEE 802.11b"... | |
50 | + * Don't put the name of your driver there, it's useless. */ | |
51 | + | |
52 | +/* Basic operations */ | |
53 | +#define SIOCSIWNWID 0x8B02 /* set network id (pre-802.11) */ | |
54 | +#define SIOCGIWNWID 0x8B03 /* get network id (the cell) */ | |
55 | #define SIOCSIWFREQ 0x8B04 /* set channel/frequency (Hz) */ | |
56 | #define SIOCGIWFREQ 0x8B05 /* get channel/frequency (Hz) */ | |
57 | #define SIOCSIWMODE 0x8B06 /* set operation mode */ | |
58 | @@ -178,16 +193,18 @@ | |
59 | #define SIOCGIWPRIV 0x8B0D /* get private ioctl interface info */ | |
60 | #define SIOCSIWSTATS 0x8B0E /* Unused */ | |
61 | #define SIOCGIWSTATS 0x8B0F /* Get /proc/net/wireless stats */ | |
62 | +/* SIOCGIWSTATS is strictly used between user space and the kernel, and | |
63 | + * is never passed to the driver (i.e. the driver will never see it). */ | |
64 | ||
65 | -/* Mobile IP support */ | |
66 | +/* Mobile IP support (statistics per MAC address) */ | |
67 | #define SIOCSIWSPY 0x8B10 /* set spy addresses */ | |
68 | #define SIOCGIWSPY 0x8B11 /* get spy info (quality of link) */ | |
69 | ||
70 | /* Access Point manipulation */ | |
71 | #define SIOCSIWAP 0x8B14 /* set access point MAC addresses */ | |
72 | #define SIOCGIWAP 0x8B15 /* get access point MAC addresses */ | |
73 | -#define SIOCGIWAPLIST 0x8B17 /* get list of access point in range */ | |
74 | -#define SIOCSIWSCAN 0x8B18 /* trigger scanning */ | |
75 | +#define SIOCGIWAPLIST 0x8B17 /* Deprecated in favor of scanning */ | |
76 | +#define SIOCSIWSCAN 0x8B18 /* trigger scanning (list cells) */ | |
77 | #define SIOCGIWSCAN 0x8B19 /* get scanning results */ | |
78 | ||
79 | /* 802.11 specific support */ | |
80 | @@ -197,9 +214,7 @@ | |
81 | #define SIOCGIWNICKN 0x8B1D /* get node name/nickname */ | |
82 | /* As the ESSID and NICKN are strings up to 32 bytes long, it doesn't fit | |
83 | * within the 'iwreq' structure, so we need to use the 'data' member to | |
84 | - * point to a string in user space, like it is done for RANGE... | |
85 | - * The "flags" member indicate if the ESSID is active or not (promiscuous). | |
86 | - */ | |
87 | + * point to a string in user space, like it is done for RANGE... */ | |
88 | ||
89 | /* Other parameters useful in 802.11 and some other devices */ | |
90 | #define SIOCSIWRATE 0x8B20 /* set default bit rate (bps) */ | |
91 | @@ -257,7 +272,10 @@ | |
92 | /* Most events use the same identifier as ioctl requests */ | |
93 | ||
94 | #define IWEVTXDROP 0x8C00 /* Packet dropped to excessive retry */ | |
95 | -#define IWEVQUAL 0x8C01 /* Quality part of statistics */ | |
96 | +#define IWEVQUAL 0x8C01 /* Quality part of statistics (scan) */ | |
97 | +#define IWEVCUSTOM 0x8C02 /* Driver specific ascii string */ | |
98 | +#define IWEVREGISTERED 0x8C03 /* Discovered a new node (AP mode) */ | |
99 | +#define IWEVEXPIRED 0x8C04 /* Expired a node (AP mode) */ | |
100 | ||
101 | #define IWEVFIRST 0x8C00 | |
102 | ||
103 | @@ -273,7 +291,8 @@ | |
104 | #define IW_PRIV_TYPE_BYTE 0x1000 /* Char as number */ | |
105 | #define IW_PRIV_TYPE_CHAR 0x2000 /* Char as character */ | |
106 | #define IW_PRIV_TYPE_INT 0x4000 /* 32 bits int */ | |
107 | -#define IW_PRIV_TYPE_FLOAT 0x5000 | |
108 | +#define IW_PRIV_TYPE_FLOAT 0x5000 /* struct iw_freq */ | |
109 | +#define IW_PRIV_TYPE_ADDR 0x6000 /* struct sockaddr */ | |
110 | ||
111 | #define IW_PRIV_SIZE_FIXED 0x0800 /* Variable or fixed nuber of args */ | |
112 | ||
113 | @@ -297,9 +316,12 @@ | |
114 | ||
115 | /* Maximum tx powers in the range struct */ | |
116 | #define IW_MAX_TXPOWER 8 | |
117 | +/* Note : if you more than 8 TXPowers, just set the max and min or | |
118 | + * a few of them in the struct iw_range. */ | |
119 | ||
120 | /* Maximum of address that you may set with SPY */ | |
121 | -#define IW_MAX_SPY 8 | |
122 | +#define IW_MAX_SPY 8 /* set */ | |
123 | +#define IW_MAX_GET_SPY 64 /* get */ | |
124 | ||
125 | /* Maximum of address that you may get in the | |
126 | list of access points in range */ | |
127 | @@ -315,6 +337,7 @@ | |
128 | #define IW_MODE_MASTER 3 /* Synchronisation master or Access Point */ | |
129 | #define IW_MODE_REPEAT 4 /* Wireless Repeater (forwarder) */ | |
130 | #define IW_MODE_SECOND 5 /* Secondary master/repeater (backup) */ | |
131 | +#define IW_MODE_MONITOR 6 /* Passive monitor (listen only) */ | |
132 | ||
133 | /* Maximum number of size of encoding token available | |
134 | * they are listed in the range structure */ | |
135 | @@ -350,8 +373,10 @@ | |
136 | #define IW_POWER_RELATIVE 0x0004 /* Value is not in seconds/ms/us */ | |
137 | ||
138 | /* Transmit Power flags available */ | |
139 | +#define IW_TXPOW_TYPE 0x00FF /* Type of value */ | |
140 | #define IW_TXPOW_DBM 0x0000 /* Value is in dBm */ | |
141 | #define IW_TXPOW_MWATT 0x0001 /* Value is in mW */ | |
142 | +#define IW_TXPOW_RANGE 0x1000 /* Range of value between min/max */ | |
143 | ||
144 | /* Retry limits and lifetime flags available */ | |
145 | #define IW_RETRY_ON 0x0000 /* No details... */ | |
146 | @@ -376,6 +401,9 @@ | |
147 | /* Maximum size of returned data */ | |
148 | #define IW_SCAN_MAX_DATA 4096 /* In bytes */ | |
149 | ||
150 | +/* Max number of char in custom event - use multiple of them if needed */ | |
151 | +#define IW_CUSTOM_MAX 256 /* In bytes */ | |
152 | + | |
153 | /****************************** TYPES ******************************/ | |
154 | ||
155 | /* --------------------------- SUBTYPES --------------------------- */ | |
156 | @@ -411,9 +439,10 @@ struct iw_point | |
157 | */ | |
158 | struct iw_freq | |
159 | { | |
160 | - __u32 m; /* Mantissa */ | |
161 | - __u16 e; /* Exponent */ | |
162 | + __s32 m; /* Mantissa */ | |
163 | + __s16 e; /* Exponent */ | |
164 | __u8 i; /* List index (when in range struct) */ | |
165 | + __u8 pad; /* Unused - just for alignement */ | |
166 | }; | |
167 | ||
168 | /* | |
169 | diff -u -p linux/include/net/iw_handler.14.h linux/include/net/iw_handler.h | |
170 | --- linux/include/net/iw_handler.14.h Thu Aug 15 19:31:52 2002 | |
171 | +++ linux/include/net/iw_handler.h Thu Aug 15 19:32:10 2002 | |
172 | @@ -1,7 +1,7 @@ | |
173 | /* | |
174 | * This file define the new driver API for Wireless Extensions | |
175 | * | |
176 | - * Version : 3 17.1.02 | |
177 | + * Version : 4 21.6.02 | |
178 | * | |
179 | * Authors : Jean Tourrilhes - HPL - <jt@hpl.hp.com> | |
180 | * Copyright (c) 2001-2002 Jean Tourrilhes, All Rights Reserved. | |
181 | @@ -206,7 +206,7 @@ | |
182 | * will be needed... | |
183 | * I just plan to increment with each new version. | |
184 | */ | |
185 | -#define IW_HANDLER_VERSION 3 | |
186 | +#define IW_HANDLER_VERSION 4 | |
187 | ||
188 | /* | |
189 | * Changes : | |
190 | @@ -217,6 +217,9 @@ | |
191 | * - Add Wireless Event support : | |
192 | * o wireless_send_event() prototype | |
193 | * o iwe_stream_add_event/point() inline functions | |
194 | + * V3 to V4 | |
195 | + * -------- | |
196 | + * - Reshuffle IW_HEADER_TYPE_XXX to map IW_PRIV_TYPE_XXX changes | |
197 | */ | |
198 | ||
199 | /**************************** CONSTANTS ****************************/ | |
200 | @@ -233,10 +236,10 @@ | |
201 | #define IW_HEADER_TYPE_CHAR 2 /* char [IFNAMSIZ] */ | |
202 | #define IW_HEADER_TYPE_UINT 4 /* __u32 */ | |
203 | #define IW_HEADER_TYPE_FREQ 5 /* struct iw_freq */ | |
204 | -#define IW_HEADER_TYPE_POINT 6 /* struct iw_point */ | |
205 | -#define IW_HEADER_TYPE_PARAM 7 /* struct iw_param */ | |
206 | -#define IW_HEADER_TYPE_ADDR 8 /* struct sockaddr */ | |
207 | -#define IW_HEADER_TYPE_QUAL 9 /* struct iw_quality */ | |
208 | +#define IW_HEADER_TYPE_ADDR 6 /* struct sockaddr */ | |
209 | +#define IW_HEADER_TYPE_POINT 8 /* struct iw_point */ | |
210 | +#define IW_HEADER_TYPE_PARAM 9 /* struct iw_param */ | |
211 | +#define IW_HEADER_TYPE_QUAL 10 /* struct iw_quality */ | |
212 | ||
213 | /* Handling flags */ | |
214 | /* Most are not implemented. I just use them as a reminder of some | |
215 | diff -u -p linux/net/core/wireless.14.c linux/net/core/wireless.c | |
216 | --- linux/net/core/wireless.14.c Thu Aug 15 19:32:03 2002 | |
217 | +++ linux/net/core/wireless.c Thu Aug 15 19:32:10 2002 | |
218 | @@ -33,8 +33,16 @@ | |
219 | * o Propagate events as rtnetlink IFLA_WIRELESS option | |
220 | * o Generate event on selected SET requests | |
221 | * | |
222 | - * v4 - 18.04.01 - Jean II | |
223 | + * v4 - 18.04.02 - Jean II | |
224 | * o Fix stupid off by one in iw_ioctl_description : IW_ESSID_MAX_SIZE + 1 | |
225 | + * | |
226 | + * v5 - 21.06.02 - Jean II | |
227 | + * o Add IW_PRIV_TYPE_ADDR in priv_type_size (+cleanup) | |
228 | + * o Reshuffle IW_HEADER_TYPE_XXX to map IW_PRIV_TYPE_XXX changes | |
229 | + * o Add IWEVCUSTOM for driver specific event/scanning token | |
230 | + * o Turn on WE_STRICT_WRITE by default + kernel warning | |
231 | + * o Fix WE_STRICT_WRITE in ioctl_export_private() (32 => iw_num) | |
232 | + * o Fix off-by-one in test (extra_size <= IFNAMSIZ) | |
233 | */ | |
234 | ||
235 | /***************************** INCLUDES *****************************/ | |
236 | @@ -50,8 +58,9 @@ | |
237 | ||
238 | /**************************** CONSTANTS ****************************/ | |
239 | ||
240 | -/* This will be turned on later on... */ | |
241 | -#undef WE_STRICT_WRITE /* Check write buffer size */ | |
242 | +/* Enough lenience, let's make sure things are proper... */ | |
243 | +#define WE_STRICT_WRITE /* Check write buffer size */ | |
244 | +/* I'll probably drop both the define and kernel message in the next version */ | |
245 | ||
246 | /* Debuging stuff */ | |
247 | #undef WE_IOCTL_DEBUG /* Debug IOCTL API */ | |
248 | @@ -106,7 +115,7 @@ static const struct iw_ioctl_description | |
249 | /* SIOCSIWSPY */ | |
250 | { IW_HEADER_TYPE_POINT, 0, sizeof(struct sockaddr), 0, IW_MAX_SPY, 0}, | |
251 | /* SIOCGIWSPY */ | |
252 | - { IW_HEADER_TYPE_POINT, 0, (sizeof(struct sockaddr) + sizeof(struct iw_quality)), 0, IW_MAX_SPY, 0}, | |
253 | + { IW_HEADER_TYPE_POINT, 0, (sizeof(struct sockaddr) + sizeof(struct iw_quality)), 0, IW_MAX_GET_SPY, 0}, | |
254 | /* -- hole -- */ | |
255 | { IW_HEADER_TYPE_NULL, 0, 0, 0, 0, 0}, | |
256 | /* -- hole -- */ | |
257 | @@ -176,25 +185,41 @@ static const struct iw_ioctl_description | |
258 | { IW_HEADER_TYPE_ADDR, 0, 0, 0, 0, 0}, | |
259 | /* IWEVQUAL */ | |
260 | { IW_HEADER_TYPE_QUAL, 0, 0, 0, 0, 0}, | |
261 | + /* IWEVCUSTOM */ | |
262 | + { IW_HEADER_TYPE_POINT, 0, 1, 0, IW_CUSTOM_MAX, 0}, | |
263 | + /* IWEVREGISTERED */ | |
264 | + { IW_HEADER_TYPE_ADDR, 0, 0, 0, 0, 0}, | |
265 | + /* IWEVEXPIRED */ | |
266 | + { IW_HEADER_TYPE_ADDR, 0, 0, 0, 0, 0}, | |
267 | }; | |
268 | static const int standard_event_num = (sizeof(standard_event) / | |
269 | sizeof(struct iw_ioctl_description)); | |
270 | ||
271 | /* Size (in bytes) of the various private data types */ | |
272 | -static const char priv_type_size[] = { 0, 1, 1, 0, 4, 4, 0, 0 }; | |
273 | +static const char priv_type_size[] = { | |
274 | + 0, /* IW_PRIV_TYPE_NONE */ | |
275 | + 1, /* IW_PRIV_TYPE_BYTE */ | |
276 | + 1, /* IW_PRIV_TYPE_CHAR */ | |
277 | + 0, /* Not defined */ | |
278 | + sizeof(__u32), /* IW_PRIV_TYPE_INT */ | |
279 | + sizeof(struct iw_freq), /* IW_PRIV_TYPE_FLOAT */ | |
280 | + sizeof(struct sockaddr), /* IW_PRIV_TYPE_ADDR */ | |
281 | + 0, /* Not defined */ | |
282 | +}; | |
283 | ||
284 | /* Size (in bytes) of various events */ | |
285 | static const int event_type_size[] = { | |
286 | - IW_EV_LCP_LEN, | |
287 | + IW_EV_LCP_LEN, /* IW_HEADER_TYPE_NULL */ | |
288 | + 0, | |
289 | + IW_EV_CHAR_LEN, /* IW_HEADER_TYPE_CHAR */ | |
290 | 0, | |
291 | - IW_EV_CHAR_LEN, | |
292 | + IW_EV_UINT_LEN, /* IW_HEADER_TYPE_UINT */ | |
293 | + IW_EV_FREQ_LEN, /* IW_HEADER_TYPE_FREQ */ | |
294 | + IW_EV_ADDR_LEN, /* IW_HEADER_TYPE_ADDR */ | |
295 | 0, | |
296 | - IW_EV_UINT_LEN, | |
297 | - IW_EV_FREQ_LEN, | |
298 | IW_EV_POINT_LEN, /* Without variable payload */ | |
299 | - IW_EV_PARAM_LEN, | |
300 | - IW_EV_ADDR_LEN, | |
301 | - IW_EV_QUAL_LEN, | |
302 | + IW_EV_PARAM_LEN, /* IW_HEADER_TYPE_PARAM */ | |
303 | + IW_EV_QUAL_LEN, /* IW_HEADER_TYPE_QUAL */ | |
304 | }; | |
305 | ||
306 | /************************ COMMON SUBROUTINES ************************/ | |
307 | @@ -440,8 +465,10 @@ static inline int ioctl_export_private(s | |
308 | return -EFAULT; | |
309 | #ifdef WE_STRICT_WRITE | |
310 | /* Check if there is enough buffer up there */ | |
311 | - if(iwr->u.data.length < (SIOCIWLASTPRIV - SIOCIWFIRSTPRIV + 1)) | |
312 | + if(iwr->u.data.length < dev->wireless_handlers->num_private_args) { | |
313 | + printk(KERN_ERR "%s (WE) : Buffer for request SIOCGIWPRIV too small (%d<%d)\n", dev->name, iwr->u.data.length, dev->wireless_handlers->num_private_args); | |
314 | return -E2BIG; | |
315 | + } | |
316 | #endif /* WE_STRICT_WRITE */ | |
317 | ||
318 | /* Set the number of available ioctls. */ | |
319 | @@ -471,6 +498,7 @@ static inline int ioctl_standard_call(st | |
320 | const struct iw_ioctl_description * descr; | |
321 | struct iw_request_info info; | |
322 | int ret = -EINVAL; | |
323 | + int user_size = 0; | |
324 | ||
325 | /* Get the description of the IOCTL */ | |
326 | if((cmd - SIOCIWFIRST) >= standard_ioctl_num) | |
327 | @@ -518,11 +546,8 @@ static inline int ioctl_standard_call(st | |
328 | /* Check NULL pointer */ | |
329 | if(iwr->u.data.pointer == NULL) | |
330 | return -EFAULT; | |
331 | -#ifdef WE_STRICT_WRITE | |
332 | - /* Check if there is enough buffer up there */ | |
333 | - if(iwr->u.data.length < descr->max_tokens) | |
334 | - return -E2BIG; | |
335 | -#endif /* WE_STRICT_WRITE */ | |
336 | + /* Save user space buffer size for checking */ | |
337 | + user_size = iwr->u.data.length; | |
338 | } | |
339 | ||
340 | #ifdef WE_IOCTL_DEBUG | |
341 | @@ -559,6 +584,15 @@ static inline int ioctl_standard_call(st | |
342 | ||
343 | /* If we have something to return to the user */ | |
344 | if (!ret && IW_IS_GET(cmd)) { | |
345 | +#ifdef WE_STRICT_WRITE | |
346 | + /* Check if there is enough buffer up there */ | |
347 | + if(user_size < iwr->u.data.length) { | |
348 | + printk(KERN_ERR "%s (WE) : Buffer for request %04X too small (%d<%d)\n", dev->name, cmd, user_size, iwr->u.data.length); | |
349 | + kfree(extra); | |
350 | + return -E2BIG; | |
351 | + } | |
352 | +#endif /* WE_STRICT_WRITE */ | |
353 | + | |
354 | err = copy_to_user(iwr->u.data.pointer, extra, | |
355 | iwr->u.data.length * | |
356 | descr->token_size); | |
357 | @@ -646,12 +680,18 @@ static inline int ioctl_private_call(str | |
358 | /* Compute the size of the set/get arguments */ | |
359 | if(descr != NULL) { | |
360 | if(IW_IS_SET(cmd)) { | |
361 | + int offset = 0; /* For sub-ioctls */ | |
362 | + /* Check for sub-ioctl handler */ | |
363 | + if(descr->name[0] == '\0') | |
364 | + /* Reserve one int for sub-ioctl index */ | |
365 | + offset = sizeof(__u32); | |
366 | + | |
367 | /* Size of set arguments */ | |
368 | extra_size = get_priv_size(descr->set_args); | |
369 | ||
370 | /* Does it fits in iwr ? */ | |
371 | if((descr->set_args & IW_PRIV_SIZE_FIXED) && | |
372 | - (extra_size < IFNAMSIZ)) | |
373 | + ((extra_size + offset) <= IFNAMSIZ)) | |
374 | extra_size = 0; | |
375 | } else { | |
376 | /* Size of set arguments */ | |
377 | @@ -659,7 +699,7 @@ static inline int ioctl_private_call(str | |
378 | ||
379 | /* Does it fits in iwr ? */ | |
380 | if((descr->get_args & IW_PRIV_SIZE_FIXED) && | |
381 | - (extra_size < IFNAMSIZ)) | |
382 | + (extra_size <= IFNAMSIZ)) | |
383 | extra_size = 0; | |
384 | } | |
385 | } | |
386 | @@ -925,7 +965,7 @@ void wireless_send_event(struct net_devi | |
387 | * The best the driver could do is to log an error message. | |
388 | * We will do it ourselves instead... | |
389 | */ | |
390 | - printk(KERN_ERR "%s (WE) : Invalid Wireless Event (0x%04X)\n", | |
391 | + printk(KERN_ERR "%s (WE) : Invalid/Unknown Wireless Event (0x%04X)\n", | |
392 | dev->name, cmd); | |
393 | return; | |
394 | } |