1 /* 2 * Copyright (c) 2003-2005 Sam Leffler, Errno Consulting 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions 7 * are met: 8 * 1. Redistributions of source code must retain the above copyright 9 * notice, this list of conditions and the following disclaimer. 10 * 2. Redistributions in binary form must reproduce the above copyright 11 * notice, this list of conditions and the following disclaimer in the 12 * documentation and/or other materials provided with the distribution. 13 * 3. The name of the author may not be used to endorse or promote products 14 * derived from this software without specific prior written permission. 15 * 16 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 17 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 18 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 19 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 20 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 21 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 22 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 23 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 24 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 25 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 26 * 27 * $FreeBSD: src/sys/net80211/ieee80211_freebsd.c,v 1.7.2.2 2005/12/22 19:22:51 sam Exp $ 28 * $DragonFly: src/sys/netproto/802_11/wlan/ieee80211_dragonfly.c,v 1.12 2007/09/15 07:19:23 sephe Exp $ 29 */ 30 31 /* 32 * IEEE 802.11 support (DragonFlyBSD-specific code) 33 */ 34 #include <sys/param.h> 35 #include <sys/kernel.h> 36 #include <sys/systm.h> 37 #include <sys/linker.h> 38 #include <sys/mbuf.h> 39 #include <sys/module.h> 40 #include <sys/proc.h> 41 #include <sys/sysctl.h> 42 43 #include <sys/socket.h> 44 45 #include <net/if.h> 46 #include <net/if_arp.h> 47 #include <net/if_media.h> 48 #include <net/ethernet.h> 49 #include <net/route.h> 50 51 #include <netproto/802_11/ieee80211_var.h> 52 53 SYSCTL_NODE(_net, OID_AUTO, wlan, CTLFLAG_RD, 0, "IEEE 80211 parameters"); 54 55 #ifdef IEEE80211_DEBUG 56 int ieee80211_debug = 0; 57 SYSCTL_INT(_net_wlan, OID_AUTO, debug, CTLFLAG_RW, &ieee80211_debug, 58 0, "debugging kprintfs"); 59 #endif 60 61 static int 62 ieee80211_sysctl_inact(SYSCTL_HANDLER_ARGS) 63 { 64 int inact = (*(int *)arg1) * IEEE80211_INACT_WAIT; 65 int error; 66 67 error = sysctl_handle_int(oidp, &inact, 0, req); 68 if (error || !req->newptr) 69 return error; 70 *(int *)arg1 = inact / IEEE80211_INACT_WAIT; 71 return 0; 72 } 73 74 static int 75 ieee80211_sysctl_parent(SYSCTL_HANDLER_ARGS) 76 { 77 struct ieee80211com *ic = arg1; 78 const char *name = ic->ic_ifp->if_xname; 79 80 return SYSCTL_OUT(req, name, strlen(name)); 81 } 82 83 void 84 ieee80211_sysctl_attach(struct ieee80211com *ic) 85 { 86 struct sysctl_ctx_list *ctx; 87 struct sysctl_oid *oid; 88 char num[14]; /* sufficient for 32 bits */ 89 90 ctx = kmalloc(sizeof(struct sysctl_ctx_list), M_DEVBUF, 91 M_WAITOK | M_ZERO); 92 sysctl_ctx_init(ctx); 93 94 ksnprintf(num, sizeof(num), "%u", ic->ic_vap); 95 oid = SYSCTL_ADD_NODE(ctx, &SYSCTL_NODE_CHILDREN(_net, wlan), 96 OID_AUTO, num, CTLFLAG_RD, NULL, ""); 97 if (oid == NULL) { 98 kprintf("add sysctl node net.wlan.%s failed\n", num); 99 kfree(ctx, M_DEVBUF); 100 return; 101 } 102 103 SYSCTL_ADD_PROC(ctx, SYSCTL_CHILDREN(oid), OID_AUTO, 104 "%parent", CTLFLAG_RD, ic, 0, ieee80211_sysctl_parent, "A", 105 "parent device"); 106 #ifdef IEEE80211_DEBUG 107 ic->ic_debug = ieee80211_debug; 108 SYSCTL_ADD_INT(ctx, SYSCTL_CHILDREN(oid), OID_AUTO, 109 "debug", CTLFLAG_RW, &ic->ic_debug, 0, 110 "control debugging kprintfs"); 111 #endif 112 /* XXX inherit from tunables */ 113 SYSCTL_ADD_PROC(ctx, SYSCTL_CHILDREN(oid), OID_AUTO, 114 "inact_run", CTLTYPE_INT | CTLFLAG_RW, &ic->ic_inact_run, 0, 115 ieee80211_sysctl_inact, "I", 116 "station inactivity timeout (sec)"); 117 SYSCTL_ADD_PROC(ctx, SYSCTL_CHILDREN(oid), OID_AUTO, 118 "inact_probe", CTLTYPE_INT | CTLFLAG_RW, &ic->ic_inact_probe, 0, 119 ieee80211_sysctl_inact, "I", 120 "station inactivity probe timeout (sec)"); 121 SYSCTL_ADD_PROC(ctx, SYSCTL_CHILDREN(oid), OID_AUTO, 122 "inact_auth", CTLTYPE_INT | CTLFLAG_RW, &ic->ic_inact_auth, 0, 123 ieee80211_sysctl_inact, "I", 124 "station authentication timeout (sec)"); 125 SYSCTL_ADD_PROC(ctx, SYSCTL_CHILDREN(oid), OID_AUTO, 126 "inact_init", CTLTYPE_INT | CTLFLAG_RW, &ic->ic_inact_init, 0, 127 ieee80211_sysctl_inact, "I", 128 "station initial state timeout (sec)"); 129 SYSCTL_ADD_INT(ctx, SYSCTL_CHILDREN(oid), OID_AUTO, 130 "driver_caps", CTLFLAG_RW, &ic->ic_caps, 0, 131 "driver capabilities"); 132 SYSCTL_ADD_INT(ctx, SYSCTL_CHILDREN(oid), OID_AUTO, 133 "bmiss_max", CTLFLAG_RW, &ic->ic_bmiss_max, 0, 134 "consecutive beacon misses before scanning"); 135 136 ic->ic_sysctl = ctx; 137 ic->ic_sysctl_oid = oid; 138 } 139 140 void 141 ieee80211_sysctl_detach(struct ieee80211com *ic) 142 { 143 if (ic->ic_sysctl != NULL) { 144 sysctl_ctx_free(ic->ic_sysctl); 145 kfree(ic->ic_sysctl, M_DEVBUF); 146 ic->ic_sysctl = NULL; 147 } 148 } 149 150 int 151 ieee80211_node_dectestref(struct ieee80211_node *ni) 152 { 153 /* XXX need equivalent of atomic_dec_and_test */ 154 atomic_subtract_int(&ni->ni_refcnt, 1); 155 return atomic_cmpset_int(&ni->ni_refcnt, 0, 1); 156 } 157 158 /* 159 * Allocate and setup a management frame of the specified 160 * size. We return the mbuf and a pointer to the start 161 * of the contiguous data area that's been reserved based 162 * on the packet length. The data area is forced to 32-bit 163 * alignment and the buffer length to a multiple of 4 bytes. 164 * This is done mainly so beacon frames (that require this) 165 * can use this interface too. 166 */ 167 struct mbuf * 168 ieee80211_getmgtframe(uint8_t **frm, int headroom, u_int pktlen) 169 { 170 struct mbuf *m; 171 u_int len; 172 173 /* 174 * NB: we know the mbuf routines will align the data area 175 * so we don't need to do anything special. 176 */ 177 /* XXX 4-address frame? */ 178 len = roundup(headroom + pktlen, 4); 179 KASSERT(len <= MCLBYTES, ("802.11 mgt frame too large: %u", len)); 180 if (len < MINCLSIZE) { 181 m = m_gethdr(MB_DONTWAIT, MT_HEADER); 182 /* 183 * Align the data in case additional headers are added. 184 * This should only happen when a WEP header is added 185 * which only happens for shared key authentication mgt 186 * frames which all fit in MHLEN. 187 */ 188 if (m != NULL) 189 MH_ALIGN(m, len); 190 } else 191 m = m_getcl(MB_DONTWAIT, MT_HEADER, M_PKTHDR); 192 if (m != NULL) { 193 m->m_data += headroom; 194 *frm = mtod(m, uint8_t *); 195 } 196 return m; 197 } 198 199 #include <sys/libkern.h> 200 201 void 202 get_random_bytes(void *p, size_t n) 203 { 204 uint8_t *dp = p; 205 206 while (n > 0) { 207 uint32_t v = karc4random(); 208 size_t nb = n > sizeof(uint32_t) ? sizeof(uint32_t) : n; 209 210 bcopy(&v, dp, n > sizeof(uint32_t) ? sizeof(uint32_t) : n); 211 dp += sizeof(uint32_t), n -= nb; 212 } 213 } 214 215 void 216 ieee80211_notify_node_join(struct ieee80211com *ic, struct ieee80211_node *ni, 217 int newassoc) 218 { 219 struct ifnet *ifp = ic->ic_ifp; 220 struct ieee80211_join_event iev; 221 222 memset(&iev, 0, sizeof(iev)); 223 if (ni == ic->ic_bss) { 224 IEEE80211_ADDR_COPY(iev.iev_addr, ni->ni_bssid); 225 rt_ieee80211msg(ifp, newassoc ? 226 RTM_IEEE80211_ASSOC : RTM_IEEE80211_REASSOC, 227 &iev, sizeof(iev)); 228 ifp->if_link_state = LINK_STATE_UP; 229 if_link_state_change(ifp); 230 } else { 231 IEEE80211_ADDR_COPY(iev.iev_addr, ni->ni_macaddr); 232 rt_ieee80211msg(ifp, newassoc ? 233 RTM_IEEE80211_JOIN : RTM_IEEE80211_REJOIN, 234 &iev, sizeof(iev)); 235 } 236 } 237 238 void 239 ieee80211_notify_node_leave(struct ieee80211com *ic, struct ieee80211_node *ni) 240 { 241 struct ifnet *ifp = ic->ic_ifp; 242 struct ieee80211_leave_event iev; 243 244 if (ni == ic->ic_bss) { 245 rt_ieee80211msg(ifp, RTM_IEEE80211_DISASSOC, NULL, 0); 246 ifp->if_link_state = LINK_STATE_DOWN; 247 if_link_state_change(ifp); 248 } else { 249 /* fire off wireless event station leaving */ 250 memset(&iev, 0, sizeof(iev)); 251 IEEE80211_ADDR_COPY(iev.iev_addr, ni->ni_macaddr); 252 rt_ieee80211msg(ifp, RTM_IEEE80211_LEAVE, &iev, sizeof(iev)); 253 } 254 } 255 256 void 257 ieee80211_notify_scan_done(struct ieee80211com *ic) 258 { 259 struct ifnet *ifp = ic->ic_ifp; 260 261 IEEE80211_DPRINTF(ic, IEEE80211_MSG_SCAN, "%s\n", "notify scan done"); 262 263 /* dispatch wireless event indicating scan completed */ 264 rt_ieee80211msg(ifp, RTM_IEEE80211_SCAN, NULL, 0); 265 } 266 267 void 268 ieee80211_notify_replay_failure(struct ieee80211com *ic, 269 const struct ieee80211_frame *wh, const struct ieee80211_key *k, 270 uint64_t rsc) 271 { 272 struct ifnet *ifp = ic->ic_ifp; 273 274 IEEE80211_DPRINTF(ic, IEEE80211_MSG_CRYPTO, 275 "[%6D] %s replay detected <rsc %ju, csc %ju, keyix %u rxkeyix %u>\n", 276 wh->i_addr2, ":", k->wk_cipher->ic_name, 277 (intmax_t) rsc, (intmax_t) k->wk_keyrsc, 278 k->wk_keyix, k->wk_rxkeyix); 279 280 if (ifp != NULL) { /* NB: for cipher test modules */ 281 struct ieee80211_replay_event iev; 282 283 IEEE80211_ADDR_COPY(iev.iev_dst, wh->i_addr1); 284 IEEE80211_ADDR_COPY(iev.iev_src, wh->i_addr2); 285 iev.iev_cipher = k->wk_cipher->ic_cipher; 286 if (k->wk_rxkeyix != IEEE80211_KEYIX_NONE) 287 iev.iev_keyix = k->wk_rxkeyix; 288 else 289 iev.iev_keyix = k->wk_keyix; 290 iev.iev_keyrsc = k->wk_keyrsc; 291 iev.iev_rsc = rsc; 292 rt_ieee80211msg(ifp, RTM_IEEE80211_REPLAY, &iev, sizeof(iev)); 293 } 294 } 295 296 void 297 ieee80211_notify_michael_failure(struct ieee80211com *ic, 298 const struct ieee80211_frame *wh, u_int keyix) 299 { 300 struct ifnet *ifp = ic->ic_ifp; 301 302 IEEE80211_DPRINTF(ic, IEEE80211_MSG_CRYPTO, 303 "[%6D] michael MIC verification failed <keyix %u>\n", 304 wh->i_addr2, ":", keyix); 305 ic->ic_stats.is_rx_tkipmic++; 306 307 if (ifp != NULL) { /* NB: for cipher test modules */ 308 struct ieee80211_michael_event iev; 309 310 IEEE80211_ADDR_COPY(iev.iev_dst, wh->i_addr1); 311 IEEE80211_ADDR_COPY(iev.iev_src, wh->i_addr2); 312 iev.iev_cipher = IEEE80211_CIPHER_TKIP; 313 iev.iev_keyix = keyix; 314 rt_ieee80211msg(ifp, RTM_IEEE80211_MICHAEL, &iev, sizeof(iev)); 315 } 316 } 317 318 void 319 ieee80211_load_module(const char *modname) 320 { 321 #ifdef notyet 322 struct thread *td = curthread; 323 324 if (suser(td) == 0 && securelevel_gt(td->td_ucred, 0) == 0) { 325 crit_enter(); /* NB: need BGL here */ 326 linker_load_module(modname, NULL, NULL, NULL, NULL); 327 crit_exit(); 328 } 329 #else 330 kprintf("%s: load the %s module by hand for now.\n", __func__, modname); 331 #endif 332 } 333 334 /* 335 * Append the specified data to the indicated mbuf chain, 336 * Extend the mbuf chain if the new data does not fit in 337 * existing space. 338 * 339 * Return 1 if able to complete the job; otherwise 0. 340 */ 341 int 342 ieee80211_mbuf_append(struct mbuf *m0, int len, const uint8_t *cp) 343 { 344 struct mbuf *m, *n; 345 int remainder, space; 346 347 for (m = m0; m->m_next != NULL; m = m->m_next) 348 ; 349 remainder = len; 350 space = M_TRAILINGSPACE(m); 351 if (space > 0) { 352 /* 353 * Copy into available space. 354 */ 355 if (space > remainder) 356 space = remainder; 357 bcopy(cp, mtod(m, caddr_t) + m->m_len, space); 358 m->m_len += space; 359 cp += space, remainder -= space; 360 } 361 while (remainder > 0) { 362 /* 363 * Allocate a new mbuf; could check space 364 * and allocate a cluster instead. 365 */ 366 n = m_get(MB_DONTWAIT, m->m_type); 367 if (n == NULL) 368 break; 369 n->m_len = min(MLEN, remainder); 370 bcopy(cp, mtod(n, caddr_t), n->m_len); 371 cp += n->m_len, remainder -= n->m_len; 372 m->m_next = n; 373 m = n; 374 } 375 if (m0->m_flags & M_PKTHDR) 376 m0->m_pkthdr.len += len - remainder; 377 return (remainder == 0); 378 } 379 380 /* 381 * Create a writable copy of the mbuf chain. While doing this 382 * we compact the chain with a goal of producing a chain with 383 * at most two mbufs. The second mbuf in this chain is likely 384 * to be a cluster. The primary purpose of this work is to create 385 * a writable packet for encryption, compression, etc. The 386 * secondary goal is to linearize the data so the data can be 387 * passed to crypto hardware in the most efficient manner possible. 388 */ 389 struct mbuf * 390 ieee80211_mbuf_clone(struct mbuf *m0, int how) 391 { 392 struct mbuf *m, *mprev; 393 struct mbuf *n, *mfirst, *mlast; 394 int len, off; 395 396 mprev = NULL; 397 for (m = m0; m != NULL; m = mprev->m_next) { 398 /* 399 * Regular mbufs are ignored unless there's a cluster 400 * in front of it that we can use to coalesce. We do 401 * the latter mainly so later clusters can be coalesced 402 * also w/o having to handle them specially (i.e. convert 403 * mbuf+cluster -> cluster). This optimization is heavily 404 * influenced by the assumption that we're running over 405 * Ethernet where MCLBYTES is large enough that the max 406 * packet size will permit lots of coalescing into a 407 * single cluster. This in turn permits efficient 408 * crypto operations, especially when using hardware. 409 */ 410 if ((m->m_flags & M_EXT) == 0) { 411 if (mprev && (mprev->m_flags & M_EXT) && 412 m->m_len <= M_TRAILINGSPACE(mprev)) { 413 /* XXX: this ignores mbuf types */ 414 memcpy(mtod(mprev, caddr_t) + mprev->m_len, 415 mtod(m, caddr_t), m->m_len); 416 mprev->m_len += m->m_len; 417 mprev->m_next = m->m_next; /* unlink from chain */ 418 m_free(m); /* reclaim mbuf */ 419 } else { 420 mprev = m; 421 } 422 continue; 423 } 424 /* 425 * Writable mbufs are left alone (for now). 426 */ 427 if (M_WRITABLE(m)) { 428 mprev = m; 429 continue; 430 } 431 432 /* 433 * Not writable, replace with a copy or coalesce with 434 * the previous mbuf if possible (since we have to copy 435 * it anyway, we try to reduce the number of mbufs and 436 * clusters so that future work is easier). 437 */ 438 KASSERT(m->m_flags & M_EXT, ("m_flags 0x%x", m->m_flags)); 439 /* NB: we only coalesce into a cluster or larger */ 440 if (mprev != NULL && (mprev->m_flags & M_EXT) && 441 m->m_len <= M_TRAILINGSPACE(mprev)) { 442 /* XXX: this ignores mbuf types */ 443 memcpy(mtod(mprev, caddr_t) + mprev->m_len, 444 mtod(m, caddr_t), m->m_len); 445 mprev->m_len += m->m_len; 446 mprev->m_next = m->m_next; /* unlink from chain */ 447 m_free(m); /* reclaim mbuf */ 448 continue; 449 } 450 451 /* 452 * Allocate new space to hold the copy... 453 */ 454 /* XXX why can M_PKTHDR be set past the first mbuf? */ 455 if (mprev == NULL && (m->m_flags & M_PKTHDR)) { 456 /* 457 * NB: if a packet header is present we must 458 * allocate the mbuf separately from any cluster 459 * because M_MOVE_PKTHDR will smash the data 460 * pointer and drop the M_EXT marker. 461 */ 462 MGETHDR(n, how, m->m_type); 463 if (n == NULL) { 464 m_freem(m0); 465 return (NULL); 466 } 467 M_MOVE_PKTHDR(n, m); 468 MCLGET(n, how); 469 if ((n->m_flags & M_EXT) == 0) { 470 m_free(n); 471 m_freem(m0); 472 return (NULL); 473 } 474 } else { 475 n = m_getcl(how, m->m_type, m->m_flags); 476 if (n == NULL) { 477 m_freem(m0); 478 return (NULL); 479 } 480 } 481 /* 482 * ... and copy the data. We deal with jumbo mbufs 483 * (i.e. m_len > MCLBYTES) by splitting them into 484 * clusters. We could just malloc a buffer and make 485 * it external but too many device drivers don't know 486 * how to break up the non-contiguous memory when 487 * doing DMA. 488 */ 489 len = m->m_len; 490 off = 0; 491 mfirst = n; 492 mlast = NULL; 493 for (;;) { 494 int cc = min(len, MCLBYTES); 495 memcpy(mtod(n, caddr_t), mtod(m, caddr_t) + off, cc); 496 n->m_len = cc; 497 if (mlast != NULL) 498 mlast->m_next = n; 499 mlast = n; 500 501 len -= cc; 502 if (len <= 0) 503 break; 504 off += cc; 505 506 n = m_getcl(how, m->m_type, m->m_flags); 507 if (n == NULL) { 508 m_freem(mfirst); 509 m_freem(m0); 510 return (NULL); 511 } 512 } 513 n->m_next = m->m_next; 514 if (mprev == NULL) 515 m0 = mfirst; /* new head of chain */ 516 else 517 mprev->m_next = mfirst; /* replace old mbuf */ 518 m_free(m); /* release old mbuf */ 519 mprev = mfirst; 520 } 521 return (m0); 522 } 523 524 void 525 ieee80211_drain_mgtq(struct ifqueue *ifq) 526 { 527 for (;;) { 528 struct ieee80211_node *ni; 529 struct mbuf *m; 530 531 IF_DEQUEUE(ifq, m); 532 if (m == NULL) 533 break; 534 535 ni = (struct ieee80211_node *)m->m_pkthdr.rcvif; 536 KKASSERT(ni != NULL); 537 ieee80211_free_node(ni); 538 539 m->m_pkthdr.rcvif = NULL; 540 m_freem(m); 541 } 542 } 543 544 /* 545 * Module glue. 546 * 547 * NB: the module name is "wlan" for compatibility with NetBSD. 548 */ 549 static int 550 wlan_modevent(module_t mod, int type, void *unused) 551 { 552 switch (type) { 553 case MOD_LOAD: 554 if (bootverbose) 555 kprintf("wlan: <802.11 Link Layer>\n"); 556 return 0; 557 case MOD_UNLOAD: 558 return 0; 559 } 560 return EINVAL; 561 } 562 563 static moduledata_t wlan_mod = { 564 "wlan", 565 wlan_modevent, 566 0 567 }; 568 DECLARE_MODULE(wlan, wlan_mod, SI_SUB_DRIVERS, SI_ORDER_FIRST); 569 MODULE_VERSION(wlan, 1); 570 MODULE_DEPEND(wlan, crypto, 1, 1, 1); 571