1 /* $NetBSD: wi.c,v 1.42 2002/02/18 14:45:56 yamt Exp $ */ 2 3 /* 4 * Copyright (c) 1997, 1998, 1999 5 * Bill Paul <wpaul@ctr.columbia.edu>. All rights reserved. 6 * 7 * Redistribution and use in source and binary forms, with or without 8 * modification, are permitted provided that the following conditions 9 * are met: 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. All advertising materials mentioning features or use of this software 16 * must display the following acknowledgement: 17 * This product includes software developed by Bill Paul. 18 * 4. Neither the name of the author nor the names of any co-contributors 19 * may be used to endorse or promote products derived from this software 20 * without specific prior written permission. 21 * 22 * THIS SOFTWARE IS PROVIDED BY Bill Paul AND CONTRIBUTORS ``AS IS'' AND 23 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 24 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 25 * ARE DISCLAIMED. IN NO EVENT SHALL Bill Paul OR THE VOICES IN HIS HEAD 26 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 27 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 28 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 29 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 30 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 31 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF 32 * THE POSSIBILITY OF SUCH DAMAGE. 33 */ 34 35 /* 36 * Lucent WaveLAN/IEEE 802.11 PCMCIA driver for NetBSD. 37 * 38 * Original FreeBSD driver written by Bill Paul <wpaul@ctr.columbia.edu> 39 * Electrical Engineering Department 40 * Columbia University, New York City 41 */ 42 43 /* 44 * The WaveLAN/IEEE adapter is the second generation of the WaveLAN 45 * from Lucent. Unlike the older cards, the new ones are programmed 46 * entirely via a firmware-driven controller called the Hermes. 47 * Unfortunately, Lucent will not release the Hermes programming manual 48 * without an NDA (if at all). What they do release is an API library 49 * called the HCF (Hardware Control Functions) which is supposed to 50 * do the device-specific operations of a device driver for you. The 51 * publically available version of the HCF library (the 'HCF Light') is 52 * a) extremely gross, b) lacks certain features, particularly support 53 * for 802.11 frames, and c) is contaminated by the GNU Public License. 54 * 55 * This driver does not use the HCF or HCF Light at all. Instead, it 56 * programs the Hermes controller directly, using information gleaned 57 * from the HCF Light code and corresponding documentation. 58 * 59 * This driver supports both the PCMCIA and ISA versions of the 60 * WaveLAN/IEEE cards. Note however that the ISA card isn't really 61 * anything of the sort: it's actually a PCMCIA bridge adapter 62 * that fits into an ISA slot, into which a PCMCIA WaveLAN card is 63 * inserted. Consequently, you need to use the pccard support for 64 * both the ISA and PCMCIA adapters. 65 */ 66 67 /* 68 * FreeBSD driver ported to NetBSD by Bill Sommerfeld in the back of the 69 * Oslo IETF plenary meeting. 70 */ 71 72 #include <sys/cdefs.h> 73 __KERNEL_RCSID(0, "$NetBSD: wi.c,v 1.42 2002/02/18 14:45:56 yamt Exp $"); 74 75 #define WI_HERMES_AUTOINC_WAR /* Work around data write autoinc bug. */ 76 #define WI_HERMES_STATS_WAR /* Work around stats counter bug. */ 77 78 #include "bpfilter.h" 79 80 #include <sys/param.h> 81 #include <sys/systm.h> 82 #include <sys/callout.h> 83 #include <sys/device.h> 84 #include <sys/socket.h> 85 #include <sys/mbuf.h> 86 #include <sys/ioctl.h> 87 #include <sys/kernel.h> /* for hz */ 88 #include <sys/proc.h> 89 90 #include <net/if.h> 91 #include <net/if_dl.h> 92 #include <net/if_media.h> 93 #include <net/if_ether.h> 94 #include <net/if_ieee80211.h> 95 96 #if NBPFILTER > 0 97 #include <net/bpf.h> 98 #include <net/bpfdesc.h> 99 #endif 100 101 #include <machine/bus.h> 102 103 #include <dev/ic/wi_ieee.h> 104 #include <dev/ic/wireg.h> 105 #include <dev/ic/wivar.h> 106 107 static void wi_reset __P((struct wi_softc *)); 108 static int wi_ioctl __P((struct ifnet *, u_long, caddr_t)); 109 static void wi_start __P((struct ifnet *)); 110 static void wi_watchdog __P((struct ifnet *)); 111 static int wi_init __P((struct ifnet *)); 112 static void wi_stop __P((struct ifnet *, int)); 113 static void wi_rxeof __P((struct wi_softc *)); 114 static void wi_txeof __P((struct wi_softc *, int)); 115 static void wi_update_stats __P((struct wi_softc *)); 116 static void wi_setmulti __P((struct wi_softc *)); 117 118 static int wi_cmd __P((struct wi_softc *, int, int)); 119 static int wi_read_record __P((struct wi_softc *, struct wi_ltv_gen *)); 120 static int wi_write_record __P((struct wi_softc *, struct wi_ltv_gen *)); 121 static int wi_read_data __P((struct wi_softc *, int, 122 int, caddr_t, int)); 123 static int wi_write_data __P((struct wi_softc *, int, 124 int, caddr_t, int)); 125 static int wi_seek __P((struct wi_softc *, int, int, int)); 126 static int wi_alloc_nicmem __P((struct wi_softc *, int, int *)); 127 static void wi_inquire __P((void *)); 128 static void wi_wait_scan __P((void *)); 129 static int wi_setdef __P((struct wi_softc *, struct wi_req *)); 130 static int wi_getdef __P((struct wi_softc *, struct wi_req *)); 131 static int wi_mgmt_xmit __P((struct wi_softc *, caddr_t, int)); 132 133 static int wi_media_change __P((struct ifnet *)); 134 static void wi_media_status __P((struct ifnet *, struct ifmediareq *)); 135 136 static void wi_get_id __P((struct wi_softc *)); 137 138 static int wi_set_ssid __P((struct ieee80211_nwid *, u_int8_t *, int)); 139 static void wi_request_fill_ssid __P((struct wi_req *, 140 struct ieee80211_nwid *)); 141 static int wi_write_ssid __P((struct wi_softc *, int, struct wi_req *, 142 struct ieee80211_nwid *)); 143 static int wi_set_nwkey __P((struct wi_softc *, struct ieee80211_nwkey *)); 144 static int wi_get_nwkey __P((struct wi_softc *, struct ieee80211_nwkey *)); 145 static int wi_sync_media __P((struct wi_softc *, int, int)); 146 static int wi_set_pm(struct wi_softc *, struct ieee80211_power *); 147 static int wi_get_pm(struct wi_softc *, struct ieee80211_power *); 148 149 int 150 wi_attach(sc) 151 struct wi_softc *sc; 152 { 153 struct ifnet *ifp = sc->sc_ifp; 154 struct wi_ltv_macaddr mac; 155 struct wi_ltv_gen gen; 156 static const u_int8_t empty_macaddr[ETHER_ADDR_LEN] = { 157 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 158 }; 159 int s; 160 161 s = splnet(); 162 163 callout_init(&sc->wi_inquire_ch); 164 callout_init(&sc->wi_scan_sh); 165 166 /* Make sure interrupts are disabled. */ 167 CSR_WRITE_2(sc, WI_INT_EN, 0); 168 CSR_WRITE_2(sc, WI_EVENT_ACK, 0xFFFF); 169 170 /* Reset the NIC. */ 171 wi_reset(sc); 172 173 memset(&mac, 0, sizeof(mac)); 174 /* Read the station address. */ 175 mac.wi_type = WI_RID_MAC_NODE; 176 mac.wi_len = 4; 177 wi_read_record(sc, (struct wi_ltv_gen *)&mac); 178 memcpy(sc->sc_macaddr, mac.wi_mac_addr, ETHER_ADDR_LEN); 179 180 /* 181 * Check if we got anything meaningful. 182 * 183 * Is it really enough just checking against null ethernet address? 184 * Or, check against possible vendor? XXX. 185 */ 186 if (memcmp(sc->sc_macaddr, empty_macaddr, ETHER_ADDR_LEN) == 0) { 187 printf("%s: could not get mac address, attach failed\n", 188 sc->sc_dev.dv_xname); 189 splx(s); 190 return 1; 191 } 192 193 printf(" 802.11 address %s\n", ether_sprintf(sc->sc_macaddr)); 194 195 /* Read NIC identification */ 196 wi_get_id(sc); 197 198 memcpy(ifp->if_xname, sc->sc_dev.dv_xname, IFNAMSIZ); 199 ifp->if_softc = sc; 200 ifp->if_start = wi_start; 201 ifp->if_ioctl = wi_ioctl; 202 ifp->if_watchdog = wi_watchdog; 203 ifp->if_init = wi_init; 204 ifp->if_stop = wi_stop; 205 ifp->if_flags = IFF_BROADCAST | IFF_SIMPLEX | IFF_MULTICAST; 206 #ifdef IFF_NOTRAILERS 207 ifp->if_flags |= IFF_NOTRAILERS; 208 #endif 209 IFQ_SET_READY(&ifp->if_snd); 210 211 (void)wi_set_ssid(&sc->wi_nodeid, WI_DEFAULT_NODENAME, 212 sizeof(WI_DEFAULT_NODENAME) - 1); 213 (void)wi_set_ssid(&sc->wi_netid, WI_DEFAULT_NETNAME, 214 sizeof(WI_DEFAULT_NETNAME) - 1); 215 (void)wi_set_ssid(&sc->wi_ibssid, WI_DEFAULT_IBSS, 216 sizeof(WI_DEFAULT_IBSS) - 1); 217 218 sc->wi_portnum = WI_DEFAULT_PORT; 219 sc->wi_ptype = WI_PORTTYPE_BSS; 220 sc->wi_ap_density = WI_DEFAULT_AP_DENSITY; 221 sc->wi_rts_thresh = WI_DEFAULT_RTS_THRESH; 222 sc->wi_tx_rate = WI_DEFAULT_TX_RATE; 223 sc->wi_max_data_len = WI_DEFAULT_DATALEN; 224 sc->wi_create_ibss = WI_DEFAULT_CREATE_IBSS; 225 sc->wi_pm_enabled = WI_DEFAULT_PM_ENABLED; 226 sc->wi_max_sleep = WI_DEFAULT_MAX_SLEEP; 227 sc->wi_roaming = WI_DEFAULT_ROAMING; 228 sc->wi_authtype = WI_DEFAULT_AUTHTYPE; 229 230 /* 231 * Read the default channel from the NIC. This may vary 232 * depending on the country where the NIC was purchased, so 233 * we can't hard-code a default and expect it to work for 234 * everyone. 235 */ 236 gen.wi_type = WI_RID_OWN_CHNL; 237 gen.wi_len = 2; 238 wi_read_record(sc, &gen); 239 sc->wi_channel = le16toh(gen.wi_val); 240 241 memset((char *)&sc->wi_stats, 0, sizeof(sc->wi_stats)); 242 243 /* AP info was filled with 0 */ 244 memset((char *)&sc->wi_aps, 0, sizeof(sc->wi_aps)); 245 sc->wi_scanning=0; 246 sc->wi_naps=0; 247 248 /* 249 * Find out if we support WEP on this card. 250 */ 251 gen.wi_type = WI_RID_WEP_AVAIL; 252 gen.wi_len = 2; 253 wi_read_record(sc, &gen); 254 sc->wi_has_wep = le16toh(gen.wi_val); 255 256 ifmedia_init(&sc->sc_media, 0, wi_media_change, wi_media_status); 257 #define IFM_AUTOADHOC \ 258 IFM_MAKEWORD(IFM_IEEE80211, IFM_AUTO, IFM_IEEE80211_ADHOC, 0) 259 #define ADD(m, c) ifmedia_add(&sc->sc_media, (m), (c), NULL) 260 ADD(IFM_MAKEWORD(IFM_IEEE80211, IFM_AUTO, 0, 0), 0); 261 ADD(IFM_AUTOADHOC, 0); 262 ADD(IFM_MAKEWORD(IFM_IEEE80211, IFM_IEEE80211_DS1, 0, 0), 0); 263 ADD(IFM_MAKEWORD(IFM_IEEE80211, IFM_IEEE80211_DS1, 264 IFM_IEEE80211_ADHOC, 0), 0); 265 ADD(IFM_MAKEWORD(IFM_IEEE80211, IFM_IEEE80211_DS2, 0, 0), 0); 266 ADD(IFM_MAKEWORD(IFM_IEEE80211, IFM_IEEE80211_DS2, 267 IFM_IEEE80211_ADHOC, 0), 0); 268 ADD(IFM_MAKEWORD(IFM_IEEE80211, IFM_IEEE80211_DS5, 0, 0), 0); 269 ADD(IFM_MAKEWORD(IFM_IEEE80211, IFM_IEEE80211_DS5, 270 IFM_IEEE80211_ADHOC, 0), 0); 271 ADD(IFM_MAKEWORD(IFM_IEEE80211, IFM_IEEE80211_DS11, 0, 0), 0); 272 ADD(IFM_MAKEWORD(IFM_IEEE80211, IFM_IEEE80211_DS11, 273 IFM_IEEE80211_ADHOC, 0), 0); 274 ADD(IFM_MAKEWORD(IFM_IEEE80211, IFM_MANUAL, 0, 0), 0); 275 #undef ADD 276 ifmedia_set(&sc->sc_media, IFM_AUTOADHOC); 277 278 /* 279 * Call MI attach routines. 280 */ 281 if_attach(ifp); 282 ether_ifattach(ifp, mac.wi_mac_addr); 283 284 ifp->if_baudrate = IF_Mbps(2); 285 286 /* Attach is successful. */ 287 sc->sc_attached = 1; 288 289 splx(s); 290 return 0; 291 } 292 293 static void wi_rxeof(sc) 294 struct wi_softc *sc; 295 { 296 struct ifnet *ifp; 297 struct ether_header *eh; 298 struct wi_frame rx_frame; 299 struct mbuf *m; 300 int id; 301 302 ifp = sc->sc_ifp; 303 304 id = CSR_READ_2(sc, WI_RX_FID); 305 306 /* First read in the frame header */ 307 if (wi_read_data(sc, id, 0, (caddr_t)&rx_frame, sizeof(rx_frame))) { 308 ifp->if_ierrors++; 309 return; 310 } 311 312 /* 313 * Drop undecryptable or packets with receive errors here 314 */ 315 if (le16toh(rx_frame.wi_status) & WI_STAT_ERRSTAT) { 316 ifp->if_ierrors++; 317 return; 318 } 319 320 MGETHDR(m, M_DONTWAIT, MT_DATA); 321 if (m == NULL) { 322 ifp->if_ierrors++; 323 return; 324 } 325 MCLGET(m, M_DONTWAIT); 326 if (!(m->m_flags & M_EXT)) { 327 m_freem(m); 328 ifp->if_ierrors++; 329 return; 330 } 331 332 /* Align the data after the ethernet header */ 333 m->m_data = (caddr_t) ALIGN(m->m_data + sizeof(struct ether_header)) 334 - sizeof(struct ether_header); 335 336 eh = mtod(m, struct ether_header *); 337 m->m_pkthdr.rcvif = ifp; 338 339 if (le16toh(rx_frame.wi_status) == WI_STAT_1042 || 340 le16toh(rx_frame.wi_status) == WI_STAT_TUNNEL || 341 le16toh(rx_frame.wi_status) == WI_STAT_WMP_MSG) { 342 if ((le16toh(rx_frame.wi_dat_len) + WI_SNAPHDR_LEN) > MCLBYTES) { 343 printf("%s: oversized packet received " 344 "(wi_dat_len=%d, wi_status=0x%x)\n", 345 sc->sc_dev.dv_xname, 346 le16toh(rx_frame.wi_dat_len), le16toh(rx_frame.wi_status)); 347 m_freem(m); 348 ifp->if_ierrors++; 349 return; 350 } 351 m->m_pkthdr.len = m->m_len = 352 le16toh(rx_frame.wi_dat_len) + WI_SNAPHDR_LEN; 353 354 memcpy((char *)&eh->ether_dhost, (char *)&rx_frame.wi_dst_addr, 355 ETHER_ADDR_LEN); 356 memcpy((char *)&eh->ether_shost, (char *)&rx_frame.wi_src_addr, 357 ETHER_ADDR_LEN); 358 memcpy((char *)&eh->ether_type, (char *)&rx_frame.wi_type, 359 sizeof(u_int16_t)); 360 361 if (wi_read_data(sc, id, WI_802_11_OFFSET, 362 mtod(m, caddr_t) + sizeof(struct ether_header), 363 m->m_len + 2)) { 364 m_freem(m); 365 ifp->if_ierrors++; 366 return; 367 } 368 } else { 369 if ((le16toh(rx_frame.wi_dat_len) + 370 sizeof(struct ether_header)) > MCLBYTES) { 371 printf("%s: oversized packet received " 372 "(wi_dat_len=%d, wi_status=0x%x)\n", 373 sc->sc_dev.dv_xname, 374 le16toh(rx_frame.wi_dat_len), le16toh(rx_frame.wi_status)); 375 m_freem(m); 376 ifp->if_ierrors++; 377 return; 378 } 379 m->m_pkthdr.len = m->m_len = 380 le16toh(rx_frame.wi_dat_len) + sizeof(struct ether_header); 381 382 if (wi_read_data(sc, id, WI_802_3_OFFSET, 383 mtod(m, caddr_t), m->m_len + 2)) { 384 m_freem(m); 385 ifp->if_ierrors++; 386 return; 387 } 388 } 389 390 ifp->if_ipackets++; 391 392 #if NBPFILTER > 0 393 /* Handle BPF listeners. */ 394 if (ifp->if_bpf) 395 bpf_mtap(ifp->if_bpf, m); 396 #endif 397 398 /* Receive packet. */ 399 (*ifp->if_input)(ifp, m); 400 } 401 402 static void wi_txeof(sc, status) 403 struct wi_softc *sc; 404 int status; 405 { 406 struct ifnet *ifp = sc->sc_ifp; 407 408 ifp->if_timer = 0; 409 ifp->if_flags &= ~IFF_OACTIVE; 410 411 if (status & WI_EV_TX_EXC) 412 ifp->if_oerrors++; 413 else 414 ifp->if_opackets++; 415 416 return; 417 } 418 419 void wi_inquire(xsc) 420 void *xsc; 421 { 422 struct wi_softc *sc; 423 struct ifnet *ifp; 424 int s; 425 426 sc = xsc; 427 ifp = &sc->sc_ethercom.ec_if; 428 429 if ((sc->sc_dev.dv_flags & DVF_ACTIVE) == 0) 430 return; 431 432 callout_reset(&sc->wi_inquire_ch, hz * 60, wi_inquire, sc); 433 434 /* Don't do this while we're transmitting */ 435 if (ifp->if_flags & IFF_OACTIVE) 436 return; 437 438 s = splnet(); 439 wi_cmd(sc, WI_CMD_INQUIRE, WI_INFO_COUNTERS); 440 splx(s); 441 } 442 443 void wi_wait_scan(xsc) 444 void *xsc; 445 { 446 struct wi_softc *sc; 447 struct ifnet *ifp; 448 int s, result; 449 450 sc = xsc; 451 ifp = &sc->sc_ethercom.ec_if; 452 453 /* If not scanning, ignore */ 454 if (!sc->wi_scanning) 455 return; 456 457 s = splnet(); 458 459 /* Wait for sending complete to make INQUIRE */ 460 if (ifp->if_flags & IFF_OACTIVE) { 461 callout_reset(&sc->wi_scan_sh, hz * 1, wi_wait_scan, sc); 462 splx(s); 463 return; 464 } 465 466 /* try INQUIRE */ 467 result = wi_cmd(sc, WI_CMD_INQUIRE, WI_INFO_SCAN_RESULTS); 468 if (result == ETIMEDOUT) 469 callout_reset(&sc->wi_scan_sh, hz * 1, wi_wait_scan, sc); 470 471 splx(s); 472 } 473 474 void wi_update_stats(sc) 475 struct wi_softc *sc; 476 { 477 struct wi_ltv_gen gen; 478 struct wi_scan_header ap2_header; /* Prism2 header */ 479 struct wi_scan_data_p2 ap2; /* Prism2 scantable*/ 480 struct wi_scan_data ap; /* Lucent scantable */ 481 struct wi_assoc assoc; /* Association Status */ 482 u_int16_t id; 483 struct ifnet *ifp; 484 u_int32_t *ptr; 485 int len, naps, i, j; 486 u_int16_t t; 487 488 ifp = &sc->sc_ethercom.ec_if; 489 490 id = CSR_READ_2(sc, WI_INFO_FID); 491 492 wi_read_data(sc, id, 0, (char *)&gen, 4); 493 494 switch (gen.wi_type) { 495 case WI_INFO_SCAN_RESULTS: 496 if (gen.wi_len <= 3) 497 break; 498 if (sc->sc_prism2) { /* Prism2 chip */ 499 naps = 2 * (gen.wi_len - 3) / sizeof(ap2); 500 naps = naps > MAXAPINFO ? MAXAPINFO : naps; 501 sc->wi_naps = naps; 502 /* Read Header */ 503 for(j=0; j < sizeof(ap2_header) / 2; j++) 504 ((u_int16_t *)&ap2_header)[j] = 505 CSR_READ_2(sc, WI_DATA1); 506 /* Read Data */ 507 for (i=0; i < naps; i++) { 508 for(j=0; j < sizeof(ap2) / 2; j++) 509 ((u_int16_t *)&ap2)[j] = 510 CSR_READ_2(sc, WI_DATA1); 511 sc->wi_aps[i].scanreason = ap2_header.wi_reason; 512 memcpy(sc->wi_aps[i].bssid, ap2.wi_bssid, 6); 513 sc->wi_aps[i].channel = ap2.wi_chid; 514 sc->wi_aps[i].signal = ap2.wi_signal; 515 sc->wi_aps[i].noise = ap2.wi_noise; 516 sc->wi_aps[i].quality = ap2.wi_signal - ap2.wi_noise; 517 sc->wi_aps[i].capinfo = ap2.wi_capinfo; 518 sc->wi_aps[i].interval = ap2.wi_interval; 519 sc->wi_aps[i].rate = ap2.wi_rate; 520 if (ap2.wi_namelen > 32) 521 ap2.wi_namelen = 32; 522 sc->wi_aps[i].namelen = ap2.wi_namelen; 523 memcpy(sc->wi_aps[i].name, ap2.wi_name, 524 ap2.wi_namelen); 525 } 526 } else { /* Lucent chip */ 527 naps = 2 * gen.wi_len / sizeof(ap); 528 naps = naps > MAXAPINFO ? MAXAPINFO : naps; 529 sc->wi_naps = naps; 530 /* Read Data*/ 531 for (i=0; i < naps; i++) { 532 for(j=0; j < sizeof(ap) / 2; j++) 533 ((u_int16_t *)&ap)[j] = 534 CSR_READ_2(sc, WI_DATA1); 535 memcpy(sc->wi_aps[i].bssid, ap.wi_bssid, 6); 536 sc->wi_aps[i].channel = ap.wi_chid; 537 sc->wi_aps[i].signal = ap.wi_signal; 538 sc->wi_aps[i].noise = ap.wi_noise; 539 sc->wi_aps[i].quality = ap.wi_signal - ap.wi_noise; 540 sc->wi_aps[i].capinfo = ap.wi_capinfo; 541 sc->wi_aps[i].interval = ap.wi_interval; 542 if (ap.wi_namelen > 32) 543 ap.wi_namelen = 32; 544 sc->wi_aps[i].namelen = ap.wi_namelen; 545 memcpy(sc->wi_aps[i].name, ap.wi_name, 546 ap.wi_namelen); 547 } 548 } 549 /* Done scanning */ 550 sc->wi_scanning = 0; 551 break; 552 553 case WI_INFO_COUNTERS: 554 /* some card versions have a larger stats structure */ 555 len = (gen.wi_len - 1 < sizeof(sc->wi_stats) / 4) ? 556 gen.wi_len - 1 : sizeof(sc->wi_stats) / 4; 557 ptr = (u_int32_t *)&sc->wi_stats; 558 559 for (i = 0; i < len; i++) { 560 t = CSR_READ_2(sc, WI_DATA1); 561 #ifdef WI_HERMES_STATS_WAR 562 if (t > 0xF000) 563 t = ~t & 0xFFFF; 564 #endif 565 ptr[i] += t; 566 } 567 568 ifp->if_collisions = sc->wi_stats.wi_tx_single_retries + 569 sc->wi_stats.wi_tx_multi_retries + 570 sc->wi_stats.wi_tx_retry_limit; 571 break; 572 573 case WI_INFO_LINK_STAT: { 574 static char *msg[] = { 575 "connected", 576 "disconnected", 577 "AP change", 578 "AP out of range", 579 "AP in range", 580 "Association Faild" 581 }; 582 583 if (gen.wi_len != 2) { 584 #ifdef WI_DEBUG 585 printf("WI_INFO_LINK_STAT: len=%d\n", gen.wi_len); 586 #endif 587 break; 588 } 589 t = CSR_READ_2(sc, WI_DATA1); 590 if ((t < 1) || (t > 6)) { 591 #ifdef WI_DEBUG 592 printf("WI_INFO_LINK_STAT: status %d\n", t); 593 #endif 594 break; 595 } 596 /* 597 * Some cards issue streams of "connected" messages while 598 * trying to find a peer. Don't bother the user with this 599 * unless he is debugging. 600 */ 601 if (ifp->if_flags & IFF_DEBUG) 602 printf("%s: %s\n", sc->sc_dev.dv_xname, msg[t - 1]); 603 break; 604 } 605 606 case WI_INFO_ASSOC_STAT: { 607 static char *msg[] = { 608 "STA Associated", 609 "STA Reassociated", 610 "STA Disassociated", 611 "Association Failure", 612 "Authentication Faild" 613 }; 614 if (gen.wi_len != 10) 615 break; 616 for (i=0; i < gen.wi_len - 1; i++) 617 ((u_int16_t *)&assoc)[i] = CSR_READ_2(sc, WI_DATA1); 618 switch (assoc.wi_assoc_stat) { 619 case ASSOC: 620 case DISASSOC: 621 case ASSOCFAIL: 622 case AUTHFAIL: 623 printf("%s: %s, AP = %x:%x:%x:%x:%x:%x\n", 624 sc->sc_dev.dv_xname, 625 msg[assoc.wi_assoc_stat - 1], 626 assoc.wi_assoc_sta[0]&0xff, assoc.wi_assoc_sta[1]&0xff, 627 assoc.wi_assoc_sta[2]&0xff, assoc.wi_assoc_sta[3]&0xff, 628 assoc.wi_assoc_sta[4]&0xff, assoc.wi_assoc_sta[5]&0xff); 629 break; 630 case REASSOC: 631 printf("%s: %s, AP = %x:%x:%x:%x:%x:%x, OldAP = %x:%x:%x:%x:%x:%x\n", 632 sc->sc_dev.dv_xname, msg[assoc.wi_assoc_stat - 1], 633 assoc.wi_assoc_sta[0]&0xff, assoc.wi_assoc_sta[1]&0xff, 634 assoc.wi_assoc_sta[2]&0xff, assoc.wi_assoc_sta[3]&0xff, 635 assoc.wi_assoc_sta[4]&0xff, assoc.wi_assoc_sta[5]&0xff, 636 assoc.wi_assoc_osta[0]&0xff, assoc.wi_assoc_osta[1]&0xff, 637 assoc.wi_assoc_osta[2]&0xff, assoc.wi_assoc_osta[3]&0xff, 638 assoc.wi_assoc_osta[4]&0xff, assoc.wi_assoc_osta[5]&0xff); 639 break; 640 } 641 } 642 default: 643 #if 0 644 printf("Got info type: %04x\n", gen.wi_type); 645 #endif 646 for (i = 0; i < gen.wi_len; i++) { 647 t = CSR_READ_2(sc, WI_DATA1); 648 #if 0 649 printf("[0x%02x] = 0x%04x\n", i, t); 650 #endif 651 } 652 break; 653 } 654 } 655 656 int wi_intr(arg) 657 void *arg; 658 { 659 struct wi_softc *sc = arg; 660 struct ifnet *ifp; 661 u_int16_t status; 662 663 if (sc->sc_enabled == 0 || 664 (sc->sc_dev.dv_flags & DVF_ACTIVE) == 0 || 665 (sc->sc_ethercom.ec_if.if_flags & IFF_RUNNING) == 0) 666 return (0); 667 668 ifp = &sc->sc_ethercom.ec_if; 669 670 if (!(ifp->if_flags & IFF_UP)) { 671 CSR_WRITE_2(sc, WI_EVENT_ACK, 0xFFFF); 672 CSR_WRITE_2(sc, WI_INT_EN, 0); 673 return 1; 674 } 675 676 /* Disable interrupts. */ 677 CSR_WRITE_2(sc, WI_INT_EN, 0); 678 679 status = CSR_READ_2(sc, WI_EVENT_STAT); 680 CSR_WRITE_2(sc, WI_EVENT_ACK, ~WI_INTRS); 681 682 if (status & WI_EV_RX) { 683 wi_rxeof(sc); 684 CSR_WRITE_2(sc, WI_EVENT_ACK, WI_EV_RX); 685 } 686 687 if (status & WI_EV_TX) { 688 wi_txeof(sc, status); 689 CSR_WRITE_2(sc, WI_EVENT_ACK, WI_EV_TX); 690 } 691 692 if (status & WI_EV_ALLOC) { 693 int id; 694 id = CSR_READ_2(sc, WI_ALLOC_FID); 695 CSR_WRITE_2(sc, WI_EVENT_ACK, WI_EV_ALLOC); 696 if (id == sc->wi_tx_data_id) 697 wi_txeof(sc, status); 698 } 699 700 if (status & WI_EV_INFO) { 701 wi_update_stats(sc); 702 CSR_WRITE_2(sc, WI_EVENT_ACK, WI_EV_INFO); 703 } 704 705 if (status & WI_EV_TX_EXC) { 706 wi_txeof(sc, status); 707 CSR_WRITE_2(sc, WI_EVENT_ACK, WI_EV_TX_EXC); 708 } 709 710 if (status & WI_EV_INFO_DROP) { 711 CSR_WRITE_2(sc, WI_EVENT_ACK, WI_EV_INFO_DROP); 712 } 713 714 /* Re-enable interrupts. */ 715 CSR_WRITE_2(sc, WI_INT_EN, WI_INTRS); 716 717 if (IFQ_IS_EMPTY(&ifp->if_snd) == 0) 718 wi_start(ifp); 719 720 return 1; 721 } 722 723 /* Must be called at proper protection level! */ 724 static int 725 wi_cmd(sc, cmd, val) 726 struct wi_softc *sc; 727 int cmd; 728 int val; 729 { 730 int i, s = 0; 731 732 /* wait for the busy bit to clear */ 733 for (i = 0; i < WI_TIMEOUT; i++) { 734 if (!(CSR_READ_2(sc, WI_COMMAND) & WI_CMD_BUSY)) 735 break; 736 } 737 738 if (i == WI_TIMEOUT) { 739 printf("%s: wi_cmd: BUSY did not clear, cmd=0x%x\n", 740 sc->sc_dev.dv_xname, cmd); 741 return EIO; 742 } 743 744 CSR_WRITE_2(sc, WI_PARAM0, val); 745 CSR_WRITE_2(sc, WI_PARAM1, 0); 746 CSR_WRITE_2(sc, WI_PARAM2, 0); 747 CSR_WRITE_2(sc, WI_COMMAND, cmd); 748 749 /* wait for the cmd completed bit */ 750 for (i = 0; i < WI_TIMEOUT; i++) { 751 if (CSR_READ_2(sc, WI_EVENT_STAT) & WI_EV_CMD) 752 break; 753 DELAY(1); 754 } 755 756 /* Ack the command */ 757 CSR_WRITE_2(sc, WI_EVENT_ACK, WI_EV_CMD); 758 759 s = CSR_READ_2(sc, WI_STATUS); 760 if (s & WI_STAT_CMD_RESULT) 761 return(EIO); 762 763 if (i == WI_TIMEOUT) { 764 if (!sc->wi_scanning) 765 printf("%s: command timed out, cmd=0x%x\n", 766 sc->sc_dev.dv_xname, cmd); 767 return(ETIMEDOUT); 768 } 769 770 return(0); 771 } 772 773 static void 774 wi_reset(sc) 775 struct wi_softc *sc; 776 { 777 DELAY(100*1000); /* 100 m sec */ 778 if (wi_cmd(sc, WI_CMD_INI, 0)) 779 printf("%s: init failed\n", sc->sc_dev.dv_xname); 780 CSR_WRITE_2(sc, WI_INT_EN, 0); 781 CSR_WRITE_2(sc, WI_EVENT_ACK, 0xFFFF); 782 783 /* Calibrate timer. */ 784 WI_SETVAL(WI_RID_TICK_TIME, 8); 785 786 return; 787 } 788 789 void 790 wi_pci_reset(sc) 791 struct wi_softc *sc; 792 { 793 bus_space_write_2(sc->sc_iot, sc->sc_ioh, 794 WI_PCI_COR, WI_PCI_SOFT_RESET); 795 DELAY(100*1000); /* 100 m sec */ 796 797 bus_space_write_2(sc->sc_iot, sc->sc_ioh, WI_PCI_COR, 0x0); 798 DELAY(100*1000); /* 100 m sec */ 799 800 return; 801 } 802 803 /* 804 * Read an LTV record from the NIC. 805 */ 806 static int wi_read_record(sc, ltv) 807 struct wi_softc *sc; 808 struct wi_ltv_gen *ltv; 809 { 810 u_int16_t *ptr; 811 int len, code; 812 struct wi_ltv_gen *oltv, p2ltv; 813 814 if (sc->sc_prism2) { 815 oltv = ltv; 816 switch (ltv->wi_type) { 817 case WI_RID_ENCRYPTION: 818 p2ltv.wi_type = WI_RID_P2_ENCRYPTION; 819 p2ltv.wi_len = 2; 820 ltv = &p2ltv; 821 break; 822 case WI_RID_TX_CRYPT_KEY: 823 p2ltv.wi_type = WI_RID_P2_TX_CRYPT_KEY; 824 p2ltv.wi_len = 2; 825 ltv = &p2ltv; 826 break; 827 } 828 } 829 830 /* Tell the NIC to enter record read mode. */ 831 if (wi_cmd(sc, WI_CMD_ACCESS|WI_ACCESS_READ, ltv->wi_type)) 832 return(EIO); 833 834 /* Seek to the record. */ 835 if (wi_seek(sc, ltv->wi_type, 0, WI_BAP1)) 836 return(EIO); 837 838 /* 839 * Read the length and record type and make sure they 840 * match what we expect (this verifies that we have enough 841 * room to hold all of the returned data). 842 */ 843 len = CSR_READ_2(sc, WI_DATA1); 844 if (len > ltv->wi_len) 845 return(ENOSPC); 846 code = CSR_READ_2(sc, WI_DATA1); 847 if (code != ltv->wi_type) 848 return(EIO); 849 850 ltv->wi_len = len; 851 ltv->wi_type = code; 852 853 /* Now read the data. */ 854 ptr = <v->wi_val; 855 if (ltv->wi_len > 1) 856 CSR_READ_MULTI_STREAM_2(sc, WI_DATA1, ptr, ltv->wi_len - 1); 857 858 if (sc->sc_prism2) { 859 int v; 860 861 switch (oltv->wi_type) { 862 case WI_RID_TX_RATE: 863 case WI_RID_CUR_TX_RATE: 864 switch (le16toh(ltv->wi_val)) { 865 case 1: v = 1; break; 866 case 2: v = 2; break; 867 case 3: v = 6; break; 868 case 4: v = 5; break; 869 case 7: v = 7; break; 870 case 8: v = 11; break; 871 case 15: v = 3; break; 872 default: v = 0x100 + le16toh(ltv->wi_val); break; 873 } 874 oltv->wi_val = htole16(v); 875 break; 876 case WI_RID_ENCRYPTION: 877 oltv->wi_len = 2; 878 if (le16toh(ltv->wi_val) & 0x01) 879 oltv->wi_val = htole16(1); 880 else 881 oltv->wi_val = htole16(0); 882 break; 883 case WI_RID_TX_CRYPT_KEY: 884 oltv->wi_len = 2; 885 oltv->wi_val = ltv->wi_val; 886 break; 887 case WI_RID_AUTH_CNTL: 888 oltv->wi_len = 2; 889 if (le16toh(ltv->wi_val) & 0x01) 890 oltv->wi_val = htole16(1); 891 else if (le16toh(ltv->wi_val) & 0x02) 892 oltv->wi_val = htole16(2); 893 break; 894 } 895 } 896 897 return(0); 898 } 899 900 /* 901 * Same as read, except we inject data instead of reading it. 902 */ 903 static int wi_write_record(sc, ltv) 904 struct wi_softc *sc; 905 struct wi_ltv_gen *ltv; 906 { 907 u_int16_t *ptr; 908 int i; 909 struct wi_ltv_gen p2ltv; 910 911 if (sc->sc_prism2) { 912 int v; 913 914 switch (ltv->wi_type) { 915 case WI_RID_TX_RATE: 916 p2ltv.wi_type = WI_RID_TX_RATE; 917 p2ltv.wi_len = 2; 918 switch (le16toh(ltv->wi_val)) { 919 case 1: v = 1; break; 920 case 2: v = 2; break; 921 case 3: v = 15; break; 922 case 5: v = 4; break; 923 case 6: v = 3; break; 924 case 7: v = 7; break; 925 case 11: v = 8; break; 926 default: return EINVAL; 927 } 928 p2ltv.wi_val = htole16(v); 929 ltv = &p2ltv; 930 break; 931 case WI_RID_ENCRYPTION: 932 p2ltv.wi_type = WI_RID_P2_ENCRYPTION; 933 p2ltv.wi_len = 2; 934 if (le16toh(ltv->wi_val)) 935 p2ltv.wi_val = htole16(0x03); 936 else 937 p2ltv.wi_val = htole16(0x90); 938 ltv = &p2ltv; 939 break; 940 case WI_RID_TX_CRYPT_KEY: 941 p2ltv.wi_type = WI_RID_P2_TX_CRYPT_KEY; 942 p2ltv.wi_len = 2; 943 p2ltv.wi_val = ltv->wi_val; 944 ltv = &p2ltv; 945 break; 946 case WI_RID_DEFLT_CRYPT_KEYS: 947 { 948 int error; 949 struct wi_ltv_str ws; 950 struct wi_ltv_keys *wk = (struct wi_ltv_keys *)ltv; 951 for (i = 0; i < 4; i++) { 952 memset(&ws, 0, sizeof(ws)); 953 if(wk->wi_keys[i].wi_keylen <= 5) { 954 /* 5 Octets WEP Keys */ 955 ws.wi_len = 4; 956 memcpy(ws.wi_str, &wk->wi_keys[i].wi_keydat, 5); 957 ws.wi_str[5] = '\0'; 958 } else { 959 /* 13 Octets WEP Keys */ 960 ws.wi_len = 8; 961 memcpy(ws.wi_str, &wk->wi_keys[i].wi_keydat, 13); 962 ws.wi_str[13] = '\0'; 963 } 964 ws.wi_type = WI_RID_P2_CRYPT_KEY0 + i; 965 966 if(wi_write_record(sc, (struct wi_ltv_gen *)&ws)) 967 return error; 968 } 969 return 0; 970 } 971 case WI_RID_AUTH_CNTL: 972 p2ltv.wi_type = WI_RID_AUTH_CNTL; 973 p2ltv.wi_len = 2; 974 if (le16toh(ltv->wi_val) == 1) 975 p2ltv.wi_val = htole16(0x01); 976 else if (le16toh(ltv->wi_val) == 2) 977 p2ltv.wi_val = htole16(0x02); 978 ltv = &p2ltv; 979 break; 980 } 981 } 982 983 if (wi_seek(sc, ltv->wi_type, 0, WI_BAP1)) 984 return(EIO); 985 986 CSR_WRITE_2(sc, WI_DATA1, ltv->wi_len); 987 CSR_WRITE_2(sc, WI_DATA1, ltv->wi_type); 988 989 /* Write data */ 990 ptr = <v->wi_val; 991 if (ltv->wi_len > 1) 992 CSR_WRITE_MULTI_STREAM_2(sc, WI_DATA1, ptr, ltv->wi_len - 1); 993 994 if (wi_cmd(sc, WI_CMD_ACCESS|WI_ACCESS_WRITE, ltv->wi_type)) 995 return(EIO); 996 997 return(0); 998 } 999 1000 static int wi_seek(sc, id, off, chan) 1001 struct wi_softc *sc; 1002 int id, off, chan; 1003 { 1004 int i; 1005 int selreg, offreg; 1006 int status; 1007 1008 switch (chan) { 1009 case WI_BAP0: 1010 selreg = WI_SEL0; 1011 offreg = WI_OFF0; 1012 break; 1013 case WI_BAP1: 1014 selreg = WI_SEL1; 1015 offreg = WI_OFF1; 1016 break; 1017 default: 1018 printf("%s: invalid data path: %x\n", 1019 sc->sc_dev.dv_xname, chan); 1020 return(EIO); 1021 } 1022 1023 CSR_WRITE_2(sc, selreg, id); 1024 CSR_WRITE_2(sc, offreg, off); 1025 1026 for (i = 0; i < WI_TIMEOUT; i++) { 1027 status = CSR_READ_2(sc, offreg); 1028 if (!(status & (WI_OFF_BUSY|WI_OFF_ERR))) 1029 break; 1030 } 1031 1032 if (i == WI_TIMEOUT) { 1033 printf("%s: timeout in wi_seek to %x/%x; last status %x\n", 1034 sc->sc_dev.dv_xname, id, off, status); 1035 return(ETIMEDOUT); 1036 } 1037 return(0); 1038 } 1039 1040 static int wi_read_data(sc, id, off, buf, len) 1041 struct wi_softc *sc; 1042 int id, off; 1043 caddr_t buf; 1044 int len; 1045 { 1046 u_int16_t *ptr; 1047 1048 if (wi_seek(sc, id, off, WI_BAP1)) 1049 return(EIO); 1050 1051 ptr = (u_int16_t *)buf; 1052 CSR_READ_MULTI_STREAM_2(sc, WI_DATA1, ptr, len / 2); 1053 1054 return(0); 1055 } 1056 1057 /* 1058 * According to the comments in the HCF Light code, there is a bug in 1059 * the Hermes (or possibly in certain Hermes firmware revisions) where 1060 * the chip's internal autoincrement counter gets thrown off during 1061 * data writes: the autoincrement is missed, causing one data word to 1062 * be overwritten and subsequent words to be written to the wrong memory 1063 * locations. The end result is that we could end up transmitting bogus 1064 * frames without realizing it. The workaround for this is to write a 1065 * couple of extra guard words after the end of the transfer, then 1066 * attempt to read then back. If we fail to locate the guard words where 1067 * we expect them, we preform the transfer over again. 1068 */ 1069 static int wi_write_data(sc, id, off, buf, len) 1070 struct wi_softc *sc; 1071 int id, off; 1072 caddr_t buf; 1073 int len; 1074 { 1075 u_int16_t *ptr; 1076 1077 #ifdef WI_HERMES_AUTOINC_WAR 1078 again: 1079 #endif 1080 1081 if (wi_seek(sc, id, off, WI_BAP0)) 1082 return(EIO); 1083 1084 ptr = (u_int16_t *)buf; 1085 CSR_WRITE_MULTI_STREAM_2(sc, WI_DATA0, ptr, len / 2); 1086 1087 #ifdef WI_HERMES_AUTOINC_WAR 1088 CSR_WRITE_2(sc, WI_DATA0, 0x1234); 1089 CSR_WRITE_2(sc, WI_DATA0, 0x5678); 1090 1091 if (wi_seek(sc, id, off + len, WI_BAP0)) 1092 return(EIO); 1093 1094 if (CSR_READ_2(sc, WI_DATA0) != 0x1234 || 1095 CSR_READ_2(sc, WI_DATA0) != 0x5678) 1096 goto again; 1097 #endif 1098 1099 return(0); 1100 } 1101 1102 /* 1103 * Allocate a region of memory inside the NIC and zero 1104 * it out. 1105 */ 1106 static int wi_alloc_nicmem(sc, len, id) 1107 struct wi_softc *sc; 1108 int len; 1109 int *id; 1110 { 1111 int i; 1112 1113 if (wi_cmd(sc, WI_CMD_ALLOC_MEM, len)) { 1114 printf("%s: failed to allocate %d bytes on NIC\n", 1115 sc->sc_dev.dv_xname, len); 1116 return(ENOMEM); 1117 } 1118 1119 for (i = 0; i < WI_TIMEOUT; i++) { 1120 if (CSR_READ_2(sc, WI_EVENT_STAT) & WI_EV_ALLOC) 1121 break; 1122 } 1123 1124 if (i == WI_TIMEOUT) { 1125 printf("%s: TIMED OUT in alloc\n", sc->sc_dev.dv_xname); 1126 return(ETIMEDOUT); 1127 } 1128 1129 CSR_WRITE_2(sc, WI_EVENT_ACK, WI_EV_ALLOC); 1130 *id = CSR_READ_2(sc, WI_ALLOC_FID); 1131 1132 if (wi_seek(sc, *id, 0, WI_BAP0)) { 1133 printf("%s: seek failed in alloc\n", sc->sc_dev.dv_xname); 1134 return(EIO); 1135 } 1136 1137 for (i = 0; i < len / 2; i++) 1138 CSR_WRITE_2(sc, WI_DATA0, 0); 1139 1140 return(0); 1141 } 1142 1143 static void wi_setmulti(sc) 1144 struct wi_softc *sc; 1145 { 1146 struct ifnet *ifp; 1147 int i = 0; 1148 struct wi_ltv_mcast mcast; 1149 struct ether_multi *enm; 1150 struct ether_multistep estep; 1151 struct ethercom *ec = &sc->sc_ethercom; 1152 1153 ifp = &sc->sc_ethercom.ec_if; 1154 1155 if ((ifp->if_flags & IFF_PROMISC) != 0) { 1156 allmulti: 1157 ifp->if_flags |= IFF_ALLMULTI; 1158 memset((char *)&mcast, 0, sizeof(mcast)); 1159 mcast.wi_type = WI_RID_MCAST_LIST; 1160 mcast.wi_len = ((ETHER_ADDR_LEN / 2) * 16) + 1; 1161 1162 wi_write_record(sc, (struct wi_ltv_gen *)&mcast); 1163 return; 1164 } 1165 1166 i = 0; 1167 ETHER_FIRST_MULTI(estep, ec, enm); 1168 while (enm != NULL) { 1169 /* Punt on ranges or too many multicast addresses. */ 1170 if (memcmp(enm->enm_addrlo, enm->enm_addrhi, 1171 ETHER_ADDR_LEN) != 0 || 1172 i >= 16) 1173 goto allmulti; 1174 1175 memcpy((char *)&mcast.wi_mcast[i], enm->enm_addrlo, 1176 ETHER_ADDR_LEN); 1177 i++; 1178 ETHER_NEXT_MULTI(estep, enm); 1179 } 1180 1181 ifp->if_flags &= ~IFF_ALLMULTI; 1182 mcast.wi_type = WI_RID_MCAST_LIST; 1183 mcast.wi_len = ((ETHER_ADDR_LEN / 2) * i) + 1; 1184 wi_write_record(sc, (struct wi_ltv_gen *)&mcast); 1185 } 1186 1187 static int 1188 wi_setdef(sc, wreq) 1189 struct wi_softc *sc; 1190 struct wi_req *wreq; 1191 { 1192 struct sockaddr_dl *sdl; 1193 struct ifnet *ifp; 1194 int error = 0; 1195 1196 ifp = &sc->sc_ethercom.ec_if; 1197 1198 switch(wreq->wi_type) { 1199 case WI_RID_MAC_NODE: 1200 sdl = (struct sockaddr_dl *)ifp->if_sadl; 1201 memcpy((char *)&sc->sc_macaddr, (char *)&wreq->wi_val, 1202 ETHER_ADDR_LEN); 1203 memcpy(LLADDR(sdl), (char *)&wreq->wi_val, ETHER_ADDR_LEN); 1204 break; 1205 case WI_RID_PORTTYPE: 1206 error = wi_sync_media(sc, le16toh(wreq->wi_val[0]), sc->wi_tx_rate); 1207 break; 1208 case WI_RID_TX_RATE: 1209 error = wi_sync_media(sc, sc->wi_ptype, le16toh(wreq->wi_val[0])); 1210 break; 1211 case WI_RID_MAX_DATALEN: 1212 sc->wi_max_data_len = le16toh(wreq->wi_val[0]); 1213 break; 1214 case WI_RID_RTS_THRESH: 1215 sc->wi_rts_thresh = le16toh(wreq->wi_val[0]); 1216 break; 1217 case WI_RID_SYSTEM_SCALE: 1218 sc->wi_ap_density = le16toh(wreq->wi_val[0]); 1219 break; 1220 case WI_RID_CREATE_IBSS: 1221 sc->wi_create_ibss = le16toh(wreq->wi_val[0]); 1222 break; 1223 case WI_RID_OWN_CHNL: 1224 sc->wi_channel = le16toh(wreq->wi_val[0]); 1225 break; 1226 case WI_RID_NODENAME: 1227 error = wi_set_ssid(&sc->wi_nodeid, 1228 (u_int8_t *)&wreq->wi_val[1], le16toh(wreq->wi_val[0])); 1229 break; 1230 case WI_RID_DESIRED_SSID: 1231 error = wi_set_ssid(&sc->wi_netid, 1232 (u_int8_t *)&wreq->wi_val[1], le16toh(wreq->wi_val[0])); 1233 break; 1234 case WI_RID_OWN_SSID: 1235 error = wi_set_ssid(&sc->wi_ibssid, 1236 (u_int8_t *)&wreq->wi_val[1], le16toh(wreq->wi_val[0])); 1237 break; 1238 case WI_RID_PM_ENABLED: 1239 sc->wi_pm_enabled = le16toh(wreq->wi_val[0]); 1240 break; 1241 case WI_RID_MICROWAVE_OVEN: 1242 sc->wi_mor_enabled = le16toh(wreq->wi_val[0]); 1243 break; 1244 case WI_RID_MAX_SLEEP: 1245 sc->wi_max_sleep = le16toh(wreq->wi_val[0]); 1246 break; 1247 case WI_RID_AUTH_CNTL: 1248 sc->wi_authtype = le16toh(wreq->wi_val[0]); 1249 break; 1250 case WI_RID_ROAMING_MODE: 1251 sc->wi_roaming = le16toh(wreq->wi_val[0]); 1252 break; 1253 case WI_RID_ENCRYPTION: 1254 sc->wi_use_wep = le16toh(wreq->wi_val[0]); 1255 break; 1256 case WI_RID_TX_CRYPT_KEY: 1257 sc->wi_tx_key = le16toh(wreq->wi_val[0]); 1258 break; 1259 case WI_RID_DEFLT_CRYPT_KEYS: 1260 memcpy((char *)&sc->wi_keys, (char *)wreq, 1261 sizeof(struct wi_ltv_keys)); 1262 break; 1263 default: 1264 error = EINVAL; 1265 break; 1266 } 1267 1268 return (error); 1269 } 1270 1271 static int 1272 wi_getdef(sc, wreq) 1273 struct wi_softc *sc; 1274 struct wi_req *wreq; 1275 { 1276 struct sockaddr_dl *sdl; 1277 struct ifnet *ifp; 1278 int error = 0; 1279 1280 ifp = &sc->sc_ethercom.ec_if; 1281 1282 wreq->wi_len = 2; /* XXX */ 1283 switch (wreq->wi_type) { 1284 case WI_RID_MAC_NODE: 1285 wreq->wi_len += ETHER_ADDR_LEN / 2 - 1; 1286 sdl = (struct sockaddr_dl *)ifp->if_sadl; 1287 memcpy(&wreq->wi_val, &sc->sc_macaddr, ETHER_ADDR_LEN); 1288 memcpy(&wreq->wi_val, LLADDR(sdl), ETHER_ADDR_LEN); 1289 break; 1290 case WI_RID_PORTTYPE: 1291 wreq->wi_val[0] = htole16(sc->wi_ptype); 1292 break; 1293 case WI_RID_TX_RATE: 1294 wreq->wi_val[0] = htole16(sc->wi_tx_rate); 1295 break; 1296 case WI_RID_MAX_DATALEN: 1297 wreq->wi_val[0] = htole16(sc->wi_max_data_len); 1298 break; 1299 case WI_RID_RTS_THRESH: 1300 wreq->wi_val[0] = htole16(sc->wi_rts_thresh); 1301 break; 1302 case WI_RID_SYSTEM_SCALE: 1303 wreq->wi_val[0] = htole16(sc->wi_ap_density); 1304 break; 1305 case WI_RID_CREATE_IBSS: 1306 wreq->wi_val[0] = htole16(sc->wi_create_ibss); 1307 break; 1308 case WI_RID_OWN_CHNL: 1309 wreq->wi_val[0] = htole16(sc->wi_channel); 1310 break; 1311 case WI_RID_NODENAME: 1312 wi_request_fill_ssid(wreq, &sc->wi_nodeid); 1313 break; 1314 case WI_RID_DESIRED_SSID: 1315 wi_request_fill_ssid(wreq, &sc->wi_netid); 1316 break; 1317 case WI_RID_OWN_SSID: 1318 wi_request_fill_ssid(wreq, &sc->wi_ibssid); 1319 break; 1320 case WI_RID_PM_ENABLED: 1321 wreq->wi_val[0] = htole16(sc->wi_pm_enabled); 1322 break; 1323 case WI_RID_MICROWAVE_OVEN: 1324 wreq->wi_val[0] = htole16(sc->wi_mor_enabled); 1325 break; 1326 case WI_RID_MAX_SLEEP: 1327 wreq->wi_val[0] = htole16(sc->wi_max_sleep); 1328 break; 1329 case WI_RID_AUTH_CNTL: 1330 wreq->wi_val[0] = htole16(sc->wi_authtype); 1331 break; 1332 case WI_RID_ROAMING_MODE: 1333 wreq->wi_val[0] = htole16(sc->wi_roaming); 1334 break; 1335 case WI_RID_WEP_AVAIL: 1336 wreq->wi_val[0] = htole16(sc->wi_has_wep); 1337 break; 1338 case WI_RID_ENCRYPTION: 1339 wreq->wi_val[0] = htole16(sc->wi_use_wep); 1340 break; 1341 case WI_RID_TX_CRYPT_KEY: 1342 wreq->wi_val[0] = htole16(sc->wi_tx_key); 1343 break; 1344 case WI_RID_DEFLT_CRYPT_KEYS: 1345 wreq->wi_len += sizeof(struct wi_ltv_keys) / 2 - 1; 1346 memcpy(wreq, &sc->wi_keys, sizeof(struct wi_ltv_keys)); 1347 break; 1348 default: 1349 #if 0 1350 error = EIO; 1351 #else 1352 #ifdef WI_DEBUG 1353 printf("%s: wi_getdef: unknown request %d\n", 1354 sc->sc_dev.dv_xname, wreq->wi_type); 1355 #endif 1356 #endif 1357 break; 1358 } 1359 1360 return (error); 1361 } 1362 1363 static int 1364 wi_ioctl(ifp, command, data) 1365 struct ifnet *ifp; 1366 u_long command; 1367 caddr_t data; 1368 { 1369 int s, error = 0; 1370 int len; 1371 struct wi_softc *sc = ifp->if_softc; 1372 struct wi_req wreq; 1373 struct ifreq *ifr; 1374 struct proc *p = curproc; 1375 struct ieee80211_nwid nwid; 1376 1377 if ((sc->sc_dev.dv_flags & DVF_ACTIVE) == 0) 1378 return (ENXIO); 1379 1380 s = splnet(); 1381 1382 ifr = (struct ifreq *)data; 1383 switch (command) { 1384 case SIOCSIFADDR: 1385 case SIOCGIFADDR: 1386 case SIOCSIFMTU: 1387 error = ether_ioctl(ifp, command, data); 1388 break; 1389 case SIOCSIFFLAGS: 1390 if (ifp->if_flags & IFF_UP) { 1391 if (ifp->if_flags & IFF_RUNNING && 1392 ifp->if_flags & IFF_PROMISC && 1393 !(sc->wi_if_flags & IFF_PROMISC)) { 1394 WI_SETVAL(WI_RID_PROMISC, 1); 1395 } else if (ifp->if_flags & IFF_RUNNING && 1396 !(ifp->if_flags & IFF_PROMISC) && 1397 sc->wi_if_flags & IFF_PROMISC) { 1398 WI_SETVAL(WI_RID_PROMISC, 0); 1399 } 1400 wi_init(ifp); 1401 } else { 1402 if (ifp->if_flags & IFF_RUNNING) { 1403 wi_stop(ifp, 0); 1404 } 1405 } 1406 sc->wi_if_flags = ifp->if_flags; 1407 1408 if (!(ifp->if_flags & IFF_UP)) { 1409 if (sc->sc_enabled) { 1410 if (sc->sc_disable) 1411 (*sc->sc_disable)(sc); 1412 sc->sc_enabled = 0; 1413 ifp->if_flags &= ~IFF_RUNNING; 1414 } 1415 } 1416 error = 0; 1417 break; 1418 case SIOCADDMULTI: 1419 case SIOCDELMULTI: 1420 error = (command == SIOCADDMULTI) ? 1421 ether_addmulti(ifr, &sc->sc_ethercom) : 1422 ether_delmulti(ifr, &sc->sc_ethercom); 1423 if (error == ENETRESET) { 1424 if (sc->sc_enabled != 0) { 1425 /* 1426 * Multicast list has changed. Set the 1427 * hardware filter accordingly. 1428 */ 1429 wi_setmulti(sc); 1430 } 1431 error = 0; 1432 } 1433 break; 1434 case SIOCSIFMEDIA: 1435 case SIOCGIFMEDIA: 1436 error = ifmedia_ioctl(ifp, ifr, &sc->sc_media, command); 1437 break; 1438 case SIOCGWAVELAN: 1439 error = copyin(ifr->ifr_data, &wreq, sizeof(wreq)); 1440 if (error) 1441 break; 1442 if (wreq.wi_type == WI_RID_IFACE_STATS) { 1443 wi_update_stats(sc); 1444 /* XXX native byte order */ 1445 memcpy((char *)&wreq.wi_val, (char *)&sc->wi_stats, 1446 sizeof(sc->wi_stats)); 1447 wreq.wi_len = (sizeof(sc->wi_stats) / 2) + 1; 1448 } else if (wreq.wi_type == WI_RID_READ_APS) { 1449 if (sc->wi_scanning) { 1450 error = EINVAL; 1451 break; 1452 } else { 1453 len = sc->wi_naps * sizeof(struct wi_apinfo); 1454 len = len > WI_MAX_DATALEN ? WI_MAX_DATALEN : len; 1455 len = len / sizeof(struct wi_apinfo); 1456 memcpy((char *)&wreq.wi_val, (char *)&len, sizeof(len)); 1457 memcpy((char *)&wreq.wi_val + sizeof(len), 1458 (char *)&sc->wi_aps, 1459 len * sizeof(struct wi_apinfo)); 1460 } 1461 } else if (wreq.wi_type == WI_RID_DEFLT_CRYPT_KEYS) { 1462 /* For non-root user, return all-zeroes keys */ 1463 if (suser(p->p_ucred, &p->p_acflag)) 1464 memset((char *)&wreq, 0, 1465 sizeof(struct wi_ltv_keys)); 1466 else 1467 memcpy((char *)&wreq, (char *)&sc->wi_keys, 1468 sizeof(struct wi_ltv_keys)); 1469 } else { 1470 if (sc->sc_enabled == 0) 1471 error = wi_getdef(sc, &wreq); 1472 else if (wi_read_record(sc, (struct wi_ltv_gen *)&wreq)) 1473 error = EINVAL; 1474 } 1475 if (error == 0) 1476 error = copyout(&wreq, ifr->ifr_data, sizeof(wreq)); 1477 break; 1478 case SIOCSWAVELAN: 1479 error = suser(p->p_ucred, &p->p_acflag); 1480 if (error) 1481 break; 1482 error = copyin(ifr->ifr_data, &wreq, sizeof(wreq)); 1483 if (error) 1484 break; 1485 if (wreq.wi_type == WI_RID_IFACE_STATS) { 1486 error = EINVAL; 1487 break; 1488 } else if (wreq.wi_type == WI_RID_MGMT_XMIT) { 1489 error = wi_mgmt_xmit(sc, (caddr_t)&wreq.wi_val, 1490 wreq.wi_len); 1491 } else if (wreq.wi_type == WI_RID_SCAN_APS) { 1492 if (wreq.wi_len != 4) { 1493 error = EINVAL; 1494 break; 1495 } 1496 if (!sc->wi_scanning) { 1497 if (sc->sc_prism2) { 1498 wreq.wi_type = WI_RID_SCAN_REQ; 1499 error = wi_write_record(sc, 1500 (struct wi_ltv_gen *)&wreq); 1501 } 1502 if (!error) { 1503 sc->wi_scanning = 1; 1504 callout_reset(&sc->wi_scan_sh, hz * 1, 1505 wi_wait_scan, sc); 1506 } 1507 } 1508 } else { 1509 if (sc->sc_enabled != 0) 1510 error = wi_write_record(sc, 1511 (struct wi_ltv_gen *)&wreq); 1512 if (error == 0) 1513 error = wi_setdef(sc, &wreq); 1514 if (error == 0 && sc->sc_enabled != 0) 1515 /* Reinitialize WaveLAN. */ 1516 wi_init(ifp); 1517 } 1518 break; 1519 case SIOCG80211NWID: 1520 if (sc->sc_enabled == 0) { 1521 /* Return the desired ID */ 1522 error = copyout(&sc->wi_netid, ifr->ifr_data, 1523 sizeof(sc->wi_netid)); 1524 } else { 1525 wreq.wi_type = WI_RID_CURRENT_SSID; 1526 wreq.wi_len = WI_MAX_DATALEN; 1527 if (wi_read_record(sc, (struct wi_ltv_gen *)&wreq) || 1528 le16toh(wreq.wi_val[0]) > IEEE80211_NWID_LEN) 1529 error = EINVAL; 1530 else { 1531 wi_set_ssid(&nwid, (u_int8_t *)&wreq.wi_val[1], 1532 le16toh(wreq.wi_val[0])); 1533 error = copyout(&nwid, ifr->ifr_data, 1534 sizeof(nwid)); 1535 } 1536 } 1537 break; 1538 case SIOCS80211NWID: 1539 error = copyin(ifr->ifr_data, &nwid, sizeof(nwid)); 1540 if (error != 0) 1541 break; 1542 if (nwid.i_len > IEEE80211_NWID_LEN) { 1543 error = EINVAL; 1544 break; 1545 } 1546 if (sc->wi_netid.i_len == nwid.i_len && 1547 memcmp(sc->wi_netid.i_nwid, nwid.i_nwid, nwid.i_len) == 0) 1548 break; 1549 wi_set_ssid(&sc->wi_netid, nwid.i_nwid, nwid.i_len); 1550 if (sc->sc_enabled != 0) 1551 /* Reinitialize WaveLAN. */ 1552 wi_init(ifp); 1553 break; 1554 case SIOCS80211NWKEY: 1555 error = wi_set_nwkey(sc, (struct ieee80211_nwkey *)data); 1556 break; 1557 case SIOCG80211NWKEY: 1558 error = wi_get_nwkey(sc, (struct ieee80211_nwkey *)data); 1559 break; 1560 case SIOCS80211POWER: 1561 error = wi_set_pm(sc, (struct ieee80211_power *)data); 1562 break; 1563 case SIOCG80211POWER: 1564 error = wi_get_pm(sc, (struct ieee80211_power *)data); 1565 break; 1566 1567 default: 1568 error = EINVAL; 1569 break; 1570 } 1571 1572 splx(s); 1573 return (error); 1574 } 1575 1576 static int 1577 wi_init(ifp) 1578 struct ifnet *ifp; 1579 { 1580 struct wi_softc *sc = ifp->if_softc; 1581 struct wi_req wreq; 1582 struct wi_ltv_macaddr mac; 1583 int error, id = 0; 1584 1585 if (!sc->sc_enabled) { 1586 if ((error = (*sc->sc_enable)(sc)) != 0) 1587 goto out; 1588 sc->sc_enabled = 1; 1589 } 1590 1591 wi_stop(ifp, 0); 1592 wi_reset(sc); 1593 1594 /* Program max data length. */ 1595 WI_SETVAL(WI_RID_MAX_DATALEN, sc->wi_max_data_len); 1596 1597 /* Enable/disable IBSS creation. */ 1598 WI_SETVAL(WI_RID_CREATE_IBSS, sc->wi_create_ibss); 1599 1600 /* Set the port type. */ 1601 WI_SETVAL(WI_RID_PORTTYPE, sc->wi_ptype); 1602 1603 /* Program the RTS/CTS threshold. */ 1604 WI_SETVAL(WI_RID_RTS_THRESH, sc->wi_rts_thresh); 1605 1606 /* Program the TX rate */ 1607 WI_SETVAL(WI_RID_TX_RATE, sc->wi_tx_rate); 1608 1609 /* Access point density */ 1610 WI_SETVAL(WI_RID_SYSTEM_SCALE, sc->wi_ap_density); 1611 1612 /* Power Management Enabled */ 1613 WI_SETVAL(WI_RID_PM_ENABLED, sc->wi_pm_enabled); 1614 1615 /* Power Managment Max Sleep */ 1616 WI_SETVAL(WI_RID_MAX_SLEEP, sc->wi_max_sleep); 1617 1618 /* Roaming type */ 1619 WI_SETVAL(WI_RID_ROAMING_MODE, sc->wi_roaming); 1620 1621 /* Specify the IBSS name */ 1622 wi_write_ssid(sc, WI_RID_OWN_SSID, &wreq, &sc->wi_ibssid); 1623 1624 /* Specify the network name */ 1625 wi_write_ssid(sc, WI_RID_DESIRED_SSID, &wreq, &sc->wi_netid); 1626 1627 /* Specify the frequency to use */ 1628 WI_SETVAL(WI_RID_OWN_CHNL, sc->wi_channel); 1629 1630 /* Program the nodename. */ 1631 wi_write_ssid(sc, WI_RID_NODENAME, &wreq, &sc->wi_nodeid); 1632 1633 /* Set our MAC address. */ 1634 mac.wi_len = 4; 1635 mac.wi_type = WI_RID_MAC_NODE; 1636 memcpy(&mac.wi_mac_addr, sc->sc_macaddr, ETHER_ADDR_LEN); 1637 wi_write_record(sc, (struct wi_ltv_gen *)&mac); 1638 1639 /* Initialize promisc mode. */ 1640 if (ifp->if_flags & IFF_PROMISC) { 1641 WI_SETVAL(WI_RID_PROMISC, 1); 1642 } else { 1643 WI_SETVAL(WI_RID_PROMISC, 0); 1644 } 1645 1646 /* Configure WEP. */ 1647 if (sc->wi_has_wep) { 1648 WI_SETVAL(WI_RID_ENCRYPTION, sc->wi_use_wep); 1649 WI_SETVAL(WI_RID_TX_CRYPT_KEY, sc->wi_tx_key); 1650 sc->wi_keys.wi_len = (sizeof(struct wi_ltv_keys) / 2) + 1; 1651 sc->wi_keys.wi_type = WI_RID_DEFLT_CRYPT_KEYS; 1652 wi_write_record(sc, (struct wi_ltv_gen *)&sc->wi_keys); 1653 if (sc->sc_prism2 && sc->wi_use_wep) { 1654 /* 1655 * ONLY HWB3163 EVAL-CARD Firmware version 1656 * less than 0.8 variant3 1657 * 1658 * If promiscuous mode disable, Prism2 chip 1659 * does not work with WEP . 1660 * It is under investigation for details. 1661 * (ichiro@netbsd.org) 1662 */ 1663 if (sc->sc_prism2_ver < 83 ) { 1664 /* firm ver < 0.8 variant 3 */ 1665 WI_SETVAL(WI_RID_PROMISC, 1); 1666 } 1667 WI_SETVAL(WI_RID_AUTH_CNTL, sc->wi_authtype); 1668 } 1669 } 1670 1671 /* Set multicast filter. */ 1672 wi_setmulti(sc); 1673 1674 /* Enable desired port */ 1675 wi_cmd(sc, WI_CMD_ENABLE | sc->wi_portnum, 0); 1676 1677 /* scanning variable is modal, therefore reinit to OFF, in case it was on. */ 1678 sc->wi_scanning=0; 1679 sc->wi_naps=0; 1680 1681 if ((error = wi_alloc_nicmem(sc, 1682 1518 + sizeof(struct wi_frame) + 8, &id)) != 0) { 1683 printf("%s: tx buffer allocation failed\n", 1684 sc->sc_dev.dv_xname); 1685 goto out; 1686 } 1687 sc->wi_tx_data_id = id; 1688 1689 if ((error = wi_alloc_nicmem(sc, 1690 1518 + sizeof(struct wi_frame) + 8, &id)) != 0) { 1691 printf("%s: mgmt. buffer allocation failed\n", 1692 sc->sc_dev.dv_xname); 1693 goto out; 1694 } 1695 sc->wi_tx_mgmt_id = id; 1696 1697 /* Enable interrupts */ 1698 CSR_WRITE_2(sc, WI_INT_EN, WI_INTRS); 1699 1700 ifp->if_flags |= IFF_RUNNING; 1701 ifp->if_flags &= ~IFF_OACTIVE; 1702 1703 callout_reset(&sc->wi_inquire_ch, hz * 60, wi_inquire, sc); 1704 1705 out: 1706 if (error) { 1707 ifp->if_flags &= ~(IFF_RUNNING | IFF_OACTIVE); 1708 ifp->if_timer = 0; 1709 printf("%s: interface not running\n", sc->sc_dev.dv_xname); 1710 } 1711 return (error); 1712 } 1713 1714 static void 1715 wi_start(ifp) 1716 struct ifnet *ifp; 1717 { 1718 struct wi_softc *sc; 1719 struct mbuf *m0; 1720 struct wi_frame tx_frame; 1721 struct ether_header *eh; 1722 int id; 1723 1724 sc = ifp->if_softc; 1725 1726 if (ifp->if_flags & IFF_OACTIVE) 1727 return; 1728 1729 IFQ_DEQUEUE(&ifp->if_snd, m0); 1730 if (m0 == NULL) 1731 return; 1732 1733 memset((char *)&tx_frame, 0, sizeof(tx_frame)); 1734 id = sc->wi_tx_data_id; 1735 eh = mtod(m0, struct ether_header *); 1736 1737 /* 1738 * Use RFC1042 encoding for IP and ARP datagrams, 1739 * 802.3 for anything else. 1740 */ 1741 if (ntohs(eh->ether_type) == ETHERTYPE_IP || 1742 ntohs(eh->ether_type) == ETHERTYPE_ARP || 1743 ntohs(eh->ether_type) == ETHERTYPE_REVARP || 1744 ntohs(eh->ether_type) == ETHERTYPE_IPV6) { 1745 memcpy((char *)&tx_frame.wi_addr1, (char *)&eh->ether_dhost, 1746 ETHER_ADDR_LEN); 1747 memcpy((char *)&tx_frame.wi_addr2, (char *)&eh->ether_shost, 1748 ETHER_ADDR_LEN); 1749 memcpy((char *)&tx_frame.wi_dst_addr, (char *)&eh->ether_dhost, 1750 ETHER_ADDR_LEN); 1751 memcpy((char *)&tx_frame.wi_src_addr, (char *)&eh->ether_shost, 1752 ETHER_ADDR_LEN); 1753 1754 tx_frame.wi_dat_len = htole16(m0->m_pkthdr.len - WI_SNAPHDR_LEN); 1755 tx_frame.wi_frame_ctl = htole16(WI_FTYPE_DATA); 1756 tx_frame.wi_dat[0] = htons(WI_SNAP_WORD0); 1757 tx_frame.wi_dat[1] = htons(WI_SNAP_WORD1); 1758 tx_frame.wi_len = htons(m0->m_pkthdr.len - WI_SNAPHDR_LEN); 1759 tx_frame.wi_type = eh->ether_type; 1760 1761 m_copydata(m0, sizeof(struct ether_header), 1762 m0->m_pkthdr.len - sizeof(struct ether_header), 1763 (caddr_t)&sc->wi_txbuf); 1764 1765 wi_write_data(sc, id, 0, (caddr_t)&tx_frame, 1766 sizeof(struct wi_frame)); 1767 wi_write_data(sc, id, WI_802_11_OFFSET, (caddr_t)&sc->wi_txbuf, 1768 (m0->m_pkthdr.len - sizeof(struct ether_header)) + 2); 1769 } else { 1770 tx_frame.wi_dat_len = htole16(m0->m_pkthdr.len); 1771 1772 m_copydata(m0, 0, m0->m_pkthdr.len, (caddr_t)&sc->wi_txbuf); 1773 1774 wi_write_data(sc, id, 0, (caddr_t)&tx_frame, 1775 sizeof(struct wi_frame)); 1776 wi_write_data(sc, id, WI_802_3_OFFSET, (caddr_t)&sc->wi_txbuf, 1777 m0->m_pkthdr.len + 2); 1778 } 1779 1780 #if NBPFILTER > 0 1781 /* 1782 * If there's a BPF listener, bounce a copy of 1783 * this frame to him. 1784 */ 1785 if (ifp->if_bpf) 1786 bpf_mtap(ifp->if_bpf, m0); 1787 #endif 1788 1789 m_freem(m0); 1790 1791 if (wi_cmd(sc, WI_CMD_TX|WI_RECLAIM, id)) 1792 printf("%s: xmit failed\n", sc->sc_dev.dv_xname); 1793 1794 ifp->if_flags |= IFF_OACTIVE; 1795 1796 /* 1797 * Set a timeout in case the chip goes out to lunch. 1798 */ 1799 ifp->if_timer = 5; 1800 1801 return; 1802 } 1803 1804 static int 1805 wi_mgmt_xmit(sc, data, len) 1806 struct wi_softc *sc; 1807 caddr_t data; 1808 int len; 1809 { 1810 struct wi_frame tx_frame; 1811 int id; 1812 struct wi_80211_hdr *hdr; 1813 caddr_t dptr; 1814 1815 hdr = (struct wi_80211_hdr *)data; 1816 dptr = data + sizeof(struct wi_80211_hdr); 1817 1818 memset((char *)&tx_frame, 0, sizeof(tx_frame)); 1819 id = sc->wi_tx_mgmt_id; 1820 1821 memcpy((char *)&tx_frame.wi_frame_ctl, (char *)hdr, 1822 sizeof(struct wi_80211_hdr)); 1823 1824 tx_frame.wi_dat_len = htole16(len - WI_SNAPHDR_LEN); 1825 tx_frame.wi_len = htons(len - WI_SNAPHDR_LEN); 1826 1827 wi_write_data(sc, id, 0, (caddr_t)&tx_frame, sizeof(struct wi_frame)); 1828 wi_write_data(sc, id, WI_802_11_OFFSET_RAW, dptr, 1829 (len - sizeof(struct wi_80211_hdr)) + 2); 1830 1831 if (wi_cmd(sc, WI_CMD_TX|WI_RECLAIM, id)) { 1832 printf("%s: xmit failed\n", sc->sc_dev.dv_xname); 1833 return(EIO); 1834 } 1835 1836 return(0); 1837 } 1838 1839 static void 1840 wi_stop(ifp, disable) 1841 struct ifnet *ifp; 1842 { 1843 struct wi_softc *sc = ifp->if_softc; 1844 1845 CSR_WRITE_2(sc, WI_INT_EN, 0); 1846 wi_cmd(sc, WI_CMD_DISABLE|sc->wi_portnum, 0); 1847 1848 callout_stop(&sc->wi_inquire_ch); 1849 callout_stop(&sc->wi_scan_sh); 1850 1851 if (disable) { 1852 if (sc->sc_enabled) { 1853 if (sc->sc_disable) 1854 (*sc->sc_disable)(sc); 1855 sc->sc_enabled = 0; 1856 } 1857 } 1858 1859 ifp->if_flags &= ~(IFF_OACTIVE | IFF_RUNNING); 1860 ifp->if_timer = 0; 1861 } 1862 1863 static void 1864 wi_watchdog(ifp) 1865 struct ifnet *ifp; 1866 { 1867 struct wi_softc *sc; 1868 1869 sc = ifp->if_softc; 1870 1871 printf("%s: device timeout\n", sc->sc_dev.dv_xname); 1872 1873 wi_init(ifp); 1874 1875 ifp->if_oerrors++; 1876 1877 return; 1878 } 1879 1880 void 1881 wi_shutdown(sc) 1882 struct wi_softc *sc; 1883 { 1884 int s; 1885 1886 s = splnet(); 1887 if (sc->sc_enabled) { 1888 if (sc->sc_disable) 1889 (*sc->sc_disable)(sc); 1890 sc->sc_enabled = 0; 1891 } 1892 splx(s); 1893 } 1894 1895 int 1896 wi_activate(self, act) 1897 struct device *self; 1898 enum devact act; 1899 { 1900 struct wi_softc *sc = (struct wi_softc *)self; 1901 int rv = 0, s; 1902 1903 s = splnet(); 1904 switch (act) { 1905 case DVACT_ACTIVATE: 1906 rv = EOPNOTSUPP; 1907 break; 1908 1909 case DVACT_DEACTIVATE: 1910 if_deactivate(&sc->sc_ethercom.ec_if); 1911 break; 1912 } 1913 splx(s); 1914 return (rv); 1915 } 1916 1917 static void 1918 wi_get_id(sc) 1919 struct wi_softc *sc; 1920 { 1921 struct wi_ltv_ver ver; 1922 1923 /* getting chip identity */ 1924 memset(&ver, 0, sizeof(ver)); 1925 ver.wi_type = WI_RID_CARD_ID; 1926 ver.wi_len = 5; 1927 wi_read_record(sc, (struct wi_ltv_gen *)&ver); 1928 printf("%s: using ", sc->sc_dev.dv_xname); 1929 switch (le16toh(ver.wi_ver[0])) { 1930 case WI_NIC_EVB2: 1931 printf("RF:PRISM2 MAC:HFA3841"); 1932 sc->sc_prism2 = 1; 1933 break; 1934 case WI_NIC_HWB3763: 1935 printf("RF:PRISM2 MAC:HFA3841 CARD:HWB3763 rev.B"); 1936 sc->sc_prism2 = 1; 1937 break; 1938 case WI_NIC_HWB3163: 1939 printf("RF:PRISM2 MAC:HFA3841 CARD:HWB3163 rev.A"); 1940 sc->sc_prism2 = 1; 1941 break; 1942 case WI_NIC_HWB3163B: 1943 printf("RF:PRISM2 MAC:HFA3841 CARD:HWB3163 rev.B"); 1944 sc->sc_prism2 = 1; 1945 break; 1946 case WI_NIC_EVB3: 1947 printf("RF:PRISM2 MAC:HFA3842"); 1948 sc->sc_prism2 = 1; 1949 break; 1950 case WI_NIC_HWB1153: 1951 printf("RF:PRISM1 MAC:HFA3841 CARD:HWB1153"); 1952 sc->sc_prism2 = 1; 1953 break; 1954 case WI_NIC_P2_SST: 1955 printf("RF:PRISM2 MAC:HFA3841 CARD:HWB3163-SST-flash"); 1956 sc->sc_prism2 = 1; 1957 break; 1958 case WI_NIC_PRISM2_5: 1959 printf("RF:PRISM2.5 MAC:ISL3873"); 1960 sc->sc_prism2 = 1; 1961 break; 1962 case WI_NIC_3874A: 1963 printf("RF:PRISM2.5 MAC:ISL3874A(PCI)"); 1964 sc->sc_prism2 = 1; 1965 break; 1966 default: 1967 printf("Lucent chip or unknown chip\n"); 1968 sc->sc_prism2 = 0; 1969 break; 1970 } 1971 1972 if (sc->sc_prism2) { 1973 /* try to get prism2 firm version */ 1974 memset(&ver, 0, sizeof(ver)); 1975 ver.wi_type = WI_RID_STA_IDENTITY; 1976 ver.wi_len = 5; 1977 wi_read_record(sc, (struct wi_ltv_gen *)&ver); 1978 LE16TOH(ver.wi_ver[1]); 1979 LE16TOH(ver.wi_ver[2]); 1980 LE16TOH(ver.wi_ver[3]); 1981 printf(", Firmware: %i.%i variant %i\n", ver.wi_ver[2], 1982 ver.wi_ver[3], ver.wi_ver[1]); 1983 sc->sc_prism2_ver = ver.wi_ver[2] * 100 + 1984 ver.wi_ver[3] * 10 + ver.wi_ver[1]; 1985 } 1986 1987 return; 1988 } 1989 1990 int 1991 wi_detach(sc) 1992 struct wi_softc *sc; 1993 { 1994 struct ifnet *ifp = sc->sc_ifp; 1995 int s; 1996 1997 if (!sc->sc_attached) 1998 return (0); 1999 2000 s = splnet(); 2001 callout_stop(&sc->wi_inquire_ch); 2002 2003 /* Delete all remaining media. */ 2004 ifmedia_delete_instance(&sc->sc_media, IFM_INST_ANY); 2005 2006 ether_ifdetach(ifp); 2007 if_detach(ifp); 2008 if (sc->sc_enabled) { 2009 if (sc->sc_disable) 2010 (*sc->sc_disable)(sc); 2011 sc->sc_enabled = 0; 2012 } 2013 splx(s); 2014 return (0); 2015 } 2016 2017 void 2018 wi_power(sc, why) 2019 struct wi_softc *sc; 2020 int why; 2021 { 2022 int s; 2023 2024 if (!sc->sc_enabled) 2025 return; 2026 2027 s = splnet(); 2028 switch (why) { 2029 case PWR_SUSPEND: 2030 case PWR_STANDBY: 2031 wi_stop(sc->sc_ifp, 0); 2032 if (sc->sc_enabled) { 2033 if (sc->sc_disable) 2034 (*sc->sc_disable)(sc); 2035 } 2036 break; 2037 case PWR_RESUME: 2038 sc->sc_enabled = 0; 2039 wi_init(sc->sc_ifp); 2040 (void)wi_intr(sc); 2041 break; 2042 case PWR_SOFTSUSPEND: 2043 case PWR_SOFTSTANDBY: 2044 case PWR_SOFTRESUME: 2045 break; 2046 } 2047 splx(s); 2048 } 2049 2050 static int 2051 wi_set_ssid(ws, id, len) 2052 struct ieee80211_nwid *ws; 2053 u_int8_t *id; 2054 int len; 2055 { 2056 2057 if (len > IEEE80211_NWID_LEN) 2058 return (EINVAL); 2059 ws->i_len = len; 2060 memcpy(ws->i_nwid, id, len); 2061 return (0); 2062 } 2063 2064 static void 2065 wi_request_fill_ssid(wreq, ws) 2066 struct wi_req *wreq; 2067 struct ieee80211_nwid *ws; 2068 { 2069 int len = ws->i_len; 2070 2071 memset(&wreq->wi_val[0], 0, sizeof(wreq->wi_val)); 2072 wreq->wi_val[0] = htole16(len); 2073 wreq->wi_len = roundup(len, 2) / 2 + 2; 2074 memcpy(&wreq->wi_val[1], ws->i_nwid, len); 2075 } 2076 2077 static int 2078 wi_write_ssid(sc, type, wreq, ws) 2079 struct wi_softc *sc; 2080 int type; 2081 struct wi_req *wreq; 2082 struct ieee80211_nwid *ws; 2083 { 2084 2085 wreq->wi_type = type; 2086 wi_request_fill_ssid(wreq, ws); 2087 return (wi_write_record(sc, (struct wi_ltv_gen *)wreq)); 2088 } 2089 2090 static int 2091 wi_sync_media(sc, ptype, txrate) 2092 struct wi_softc *sc; 2093 int ptype; 2094 int txrate; 2095 { 2096 int media = sc->sc_media.ifm_cur->ifm_media; 2097 int options = IFM_OPTIONS(media); 2098 int subtype; 2099 2100 switch (txrate) { 2101 case 1: 2102 subtype = IFM_IEEE80211_DS1; 2103 break; 2104 case 2: 2105 subtype = IFM_IEEE80211_DS2; 2106 break; 2107 case 3: 2108 subtype = IFM_AUTO; 2109 break; 2110 case 5: 2111 subtype = IFM_IEEE80211_DS5; 2112 break; 2113 case 11: 2114 subtype = IFM_IEEE80211_DS11; 2115 break; 2116 default: 2117 subtype = IFM_MANUAL; /* Unable to represent */ 2118 break; 2119 } 2120 switch (ptype) { 2121 case WI_PORTTYPE_ADHOC: 2122 options |= IFM_IEEE80211_ADHOC; 2123 break; 2124 case WI_PORTTYPE_BSS: 2125 options &= ~IFM_IEEE80211_ADHOC; 2126 break; 2127 default: 2128 subtype = IFM_MANUAL; /* Unable to represent */ 2129 break; 2130 } 2131 media = IFM_MAKEWORD(IFM_TYPE(media), subtype, options, 2132 IFM_INST(media)); 2133 if (ifmedia_match(&sc->sc_media, media, sc->sc_media.ifm_mask) == NULL) 2134 return (EINVAL); 2135 ifmedia_set(&sc->sc_media, media); 2136 sc->wi_ptype = ptype; 2137 sc->wi_tx_rate = txrate; 2138 return (0); 2139 } 2140 2141 static int 2142 wi_media_change(ifp) 2143 struct ifnet *ifp; 2144 { 2145 struct wi_softc *sc = ifp->if_softc; 2146 int otype = sc->wi_ptype; 2147 int orate = sc->wi_tx_rate; 2148 2149 if ((sc->sc_media.ifm_cur->ifm_media & IFM_IEEE80211_ADHOC) != 0) 2150 sc->wi_ptype = WI_PORTTYPE_ADHOC; 2151 else 2152 sc->wi_ptype = WI_PORTTYPE_BSS; 2153 2154 switch (IFM_SUBTYPE(sc->sc_media.ifm_cur->ifm_media)) { 2155 case IFM_IEEE80211_DS1: 2156 sc->wi_tx_rate = 1; 2157 break; 2158 case IFM_IEEE80211_DS2: 2159 sc->wi_tx_rate = 2; 2160 break; 2161 case IFM_AUTO: 2162 sc->wi_tx_rate = 3; 2163 break; 2164 case IFM_IEEE80211_DS5: 2165 sc->wi_tx_rate = 5; 2166 break; 2167 case IFM_IEEE80211_DS11: 2168 sc->wi_tx_rate = 11; 2169 break; 2170 } 2171 2172 if (sc->sc_enabled != 0) { 2173 if (otype != sc->wi_ptype || 2174 orate != sc->wi_tx_rate) 2175 wi_init(ifp); 2176 } 2177 2178 ifp->if_baudrate = ifmedia_baudrate(sc->sc_media.ifm_cur->ifm_media); 2179 2180 return (0); 2181 } 2182 2183 static void 2184 wi_media_status(ifp, imr) 2185 struct ifnet *ifp; 2186 struct ifmediareq *imr; 2187 { 2188 struct wi_softc *sc = ifp->if_softc; 2189 2190 if (sc->sc_enabled == 0) { 2191 imr->ifm_active = IFM_IEEE80211|IFM_NONE; 2192 imr->ifm_status = 0; 2193 return; 2194 } 2195 2196 imr->ifm_active = sc->sc_media.ifm_cur->ifm_media; 2197 imr->ifm_status = IFM_AVALID|IFM_ACTIVE; 2198 } 2199 2200 static int 2201 wi_set_nwkey(sc, nwkey) 2202 struct wi_softc *sc; 2203 struct ieee80211_nwkey *nwkey; 2204 { 2205 int i, error; 2206 size_t len; 2207 struct wi_req wreq; 2208 struct wi_ltv_keys *wk = (struct wi_ltv_keys *)&wreq; 2209 2210 if (!sc->wi_has_wep) 2211 return ENODEV; 2212 if (nwkey->i_defkid <= 0 || 2213 nwkey->i_defkid > IEEE80211_WEP_NKID) 2214 return EINVAL; 2215 memcpy(wk, &sc->wi_keys, sizeof(*wk)); 2216 for (i = 0; i < IEEE80211_WEP_NKID; i++) { 2217 if (nwkey->i_key[i].i_keydat == NULL) 2218 continue; 2219 len = nwkey->i_key[i].i_keylen; 2220 if (len > sizeof(wk->wi_keys[i].wi_keydat)) 2221 return EINVAL; 2222 error = copyin(nwkey->i_key[i].i_keydat, 2223 wk->wi_keys[i].wi_keydat, len); 2224 if (error) 2225 return error; 2226 wk->wi_keys[i].wi_keylen = htole16(len); 2227 } 2228 2229 wk->wi_len = (sizeof(*wk) / 2) + 1; 2230 wk->wi_type = WI_RID_DEFLT_CRYPT_KEYS; 2231 if (sc->sc_enabled != 0) { 2232 error = wi_write_record(sc, (struct wi_ltv_gen *)&wreq); 2233 if (error) 2234 return error; 2235 } 2236 error = wi_setdef(sc, &wreq); 2237 if (error) 2238 return error; 2239 2240 wreq.wi_len = 2; 2241 wreq.wi_type = WI_RID_TX_CRYPT_KEY; 2242 wreq.wi_val[0] = htole16(nwkey->i_defkid - 1); 2243 if (sc->sc_enabled != 0) { 2244 error = wi_write_record(sc, (struct wi_ltv_gen *)&wreq); 2245 if (error) 2246 return error; 2247 } 2248 error = wi_setdef(sc, &wreq); 2249 if (error) 2250 return error; 2251 2252 wreq.wi_type = WI_RID_ENCRYPTION; 2253 wreq.wi_val[0] = htole16(nwkey->i_wepon); 2254 if (sc->sc_enabled != 0) { 2255 error = wi_write_record(sc, (struct wi_ltv_gen *)&wreq); 2256 if (error) 2257 return error; 2258 } 2259 error = wi_setdef(sc, &wreq); 2260 if (error) 2261 return error; 2262 2263 if (sc->sc_enabled != 0) 2264 wi_init(&sc->sc_ethercom.ec_if); 2265 return 0; 2266 } 2267 2268 static int 2269 wi_get_nwkey(sc, nwkey) 2270 struct wi_softc *sc; 2271 struct ieee80211_nwkey *nwkey; 2272 { 2273 int i, len, error; 2274 struct wi_ltv_keys *wk = &sc->wi_keys; 2275 2276 if (!sc->wi_has_wep) 2277 return ENODEV; 2278 nwkey->i_wepon = sc->wi_use_wep; 2279 nwkey->i_defkid = sc->wi_tx_key + 1; 2280 2281 /* do not show any keys to non-root user */ 2282 error = suser(curproc->p_ucred, &curproc->p_acflag); 2283 for (i = 0; i < IEEE80211_WEP_NKID; i++) { 2284 if (nwkey->i_key[i].i_keydat == NULL) 2285 continue; 2286 /* error holds results of suser() for the first time */ 2287 if (error) 2288 return error; 2289 len = le16toh(wk->wi_keys[i].wi_keylen); 2290 if (nwkey->i_key[i].i_keylen < len) 2291 return ENOSPC; 2292 nwkey->i_key[i].i_keylen = len; 2293 error = copyout(wk->wi_keys[i].wi_keydat, 2294 nwkey->i_key[i].i_keydat, len); 2295 if (error) 2296 return error; 2297 } 2298 return 0; 2299 } 2300 2301 static int 2302 wi_set_pm(struct wi_softc *sc, struct ieee80211_power *power) 2303 { 2304 2305 sc->wi_pm_enabled = power->i_enabled; 2306 sc->wi_max_sleep = power->i_maxsleep; 2307 2308 if (sc->sc_enabled) 2309 return (wi_init(&sc->sc_ethercom.ec_if)); 2310 2311 return (0); 2312 } 2313 2314 static int 2315 wi_get_pm(struct wi_softc *sc, struct ieee80211_power *power) 2316 { 2317 2318 power->i_enabled = sc->wi_pm_enabled; 2319 power->i_maxsleep = sc->wi_max_sleep; 2320 2321 return (0); 2322 } 2323