ieee80211_crypto.c revision 167433
10SN/A/*- 216682Sserb * Copyright (c) 2001 Atsushi Onoe 30SN/A * Copyright (c) 2002-2005 Sam Leffler, Errno Consulting 40SN/A * All rights reserved. 50SN/A * 60SN/A * Redistribution and use in source and binary forms, with or without 72362SN/A * modification, are permitted provided that the following conditions 80SN/A * are met: 92362SN/A * 1. Redistributions of source code must retain the above copyright 100SN/A * notice, this list of conditions and the following disclaimer. 110SN/A * 2. Redistributions in binary form must reproduce the above copyright 120SN/A * notice, this list of conditions and the following disclaimer in the 130SN/A * documentation and/or other materials provided with the distribution. 140SN/A * 3. The name of the author may not be used to endorse or promote products 150SN/A * derived from this software without specific prior written permission. 160SN/A * 170SN/A * Alternatively, this software may be distributed under the terms of the 180SN/A * GNU General Public License ("GPL") version 2 as published by the Free 190SN/A * Software Foundation. 200SN/A * 212362SN/A * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 222362SN/A * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 232362SN/A * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 240SN/A * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 250SN/A * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 260SN/A * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 270SN/A * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 280SN/A * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 290SN/A * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 300SN/A * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 310SN/A */ 322859SN/A 332859SN/A#include <sys/cdefs.h> 342859SN/A__FBSDID("$FreeBSD: head/sys/net80211/ieee80211_crypto.c 167433 2007-03-11 06:38:26Z sam $"); 358979SN/A 361696SN/A/* 370SN/A * IEEE 802.11 generic crypto support. 380SN/A */ 390SN/A#include <sys/param.h> 400SN/A#include <sys/mbuf.h> 410SN/A 420SN/A#include <sys/socket.h> 430SN/A 440SN/A#include <net/if.h> 450SN/A#include <net/if_media.h> 460SN/A#include <net/ethernet.h> /* XXX ETHER_HDR_LEN */ 470SN/A 480SN/A#include <net80211/ieee80211_var.h> 490SN/A 500SN/A/* 510SN/A * Table of registered cipher modules. 520SN/A */ 530SN/Astatic const struct ieee80211_cipher *ciphers[IEEE80211_CIPHER_MAX]; 540SN/A 550SN/Astatic int _ieee80211_crypto_delkey(struct ieee80211com *, 560SN/A struct ieee80211_key *); 570SN/A 580SN/A/* 590SN/A * Default "null" key management routines. 602859SN/A */ 611696SN/Astatic int 620SN/Anull_key_alloc(struct ieee80211com *ic, const struct ieee80211_key *k, 630SN/A ieee80211_keyix *keyix, ieee80211_keyix *rxkeyix) 640SN/A{ 6516682Sserb if (!(&ic->ic_nw_keys[0] <= k && 6616682Sserb k < &ic->ic_nw_keys[IEEE80211_WEP_NKID])) { 6716682Sserb /* 680SN/A * Not in the global key table, the driver should handle this 6916682Sserb * by allocating a slot in the h/w key table/cache. In 700SN/A * lieu of that return key slot 0 for any unicast key 710SN/A * request. We disallow the request if this is a group key. 720SN/A * This default policy does the right thing for legacy hardware 730SN/A * with a 4 key table. It also handles devices that pass 7416682Sserb * packets through untouched when marked with the WEP bit 7516682Sserb * and key index 0. 7616682Sserb */ 770SN/A if (k->wk_flags & IEEE80211_KEY_GROUP) 7816682Sserb return 0; 790SN/A *keyix = 0; /* NB: use key index 0 for ucast key */ 800SN/A } else { 810SN/A *keyix = k - ic->ic_nw_keys; 820SN/A } 8316682Sserb *rxkeyix = IEEE80211_KEYIX_NONE; /* XXX maybe *keyix? */ 8416682Sserb return 1; 8516682Sserb} 860SN/Astatic int 8716682Sserbnull_key_delete(struct ieee80211com *ic, const struct ieee80211_key *k) 880SN/A{ 890SN/A return 1; 900SN/A} 910SN/Astatic int 9216682Sserbnull_key_set(struct ieee80211com *ic, const struct ieee80211_key *k, 9316682Sserb const u_int8_t mac[IEEE80211_ADDR_LEN]) 9416682Sserb{ 950SN/A return 1; 9616682Sserb} 970SN/Astatic void null_key_update(struct ieee80211com *ic) {} 980SN/A 990SN/A/* 1000SN/A * Write-arounds for common operations. 10116682Sserb */ 10216682Sserbstatic __inline void 10316682Sserbcipher_detach(struct ieee80211_key *key) 1040SN/A{ 10516682Sserb key->wk_cipher->ic_detach(key); 1060SN/A} 1070SN/A 1080SN/Astatic __inline void * 1090SN/Acipher_attach(struct ieee80211com *ic, struct ieee80211_key *key) 11016682Sserb{ 11116682Sserb return key->wk_cipher->ic_attach(ic, key); 11216682Sserb} 1130SN/A 11416682Sserb/* 1150SN/A * Wrappers for driver key management methods. 1160SN/A */ 1170SN/Astatic __inline int 1180SN/Adev_key_alloc(struct ieee80211com *ic, 11916682Sserb const struct ieee80211_key *key, 12016682Sserb ieee80211_keyix *keyix, ieee80211_keyix *rxkeyix) 12116682Sserb{ 12216682Sserb return ic->ic_crypto.cs_key_alloc(ic, key, keyix, rxkeyix); 1230SN/A} 12416682Sserb 1250SN/Astatic __inline int 1260SN/Adev_key_delete(struct ieee80211com *ic, 1270SN/A const struct ieee80211_key *key) 1280SN/A{ 12916682Sserb return ic->ic_crypto.cs_key_delete(ic, key); 13016682Sserb} 13116682Sserb 13216682Sserbstatic __inline int 1330SN/Adev_key_set(struct ieee80211com *ic, const struct ieee80211_key *key, 13416682Sserb const u_int8_t mac[IEEE80211_ADDR_LEN]) 1350SN/A{ 1360SN/A return ic->ic_crypto.cs_key_set(ic, key, mac); 1370SN/A} 1380SN/A 1390SN/A/* 1400SN/A * Setup crypto support. 1410SN/A */ 1420SN/Avoid 1430SN/Aieee80211_crypto_attach(struct ieee80211com *ic) 1440SN/A{ 1450SN/A struct ieee80211_crypto_state *cs = &ic->ic_crypto; 1460SN/A int i; 1470SN/A 1480SN/A /* NB: we assume everything is pre-zero'd */ 1490SN/A cs->cs_def_txkey = IEEE80211_KEYIX_NONE; 1500SN/A cs->cs_max_keyix = IEEE80211_WEP_NKID; 1510SN/A ciphers[IEEE80211_CIPHER_NONE] = &ieee80211_cipher_none; 1520SN/A for (i = 0; i < IEEE80211_WEP_NKID; i++) 1530SN/A ieee80211_crypto_resetkey(ic, &cs->cs_nw_keys[i], 1540SN/A IEEE80211_KEYIX_NONE); 1550SN/A /* 1560SN/A * Initialize the driver key support routines to noop entries. 1570SN/A * This is useful especially for the cipher test modules. 1580SN/A */ 1590SN/A cs->cs_key_alloc = null_key_alloc; 1600SN/A cs->cs_key_set = null_key_set; 1610SN/A cs->cs_key_delete = null_key_delete; 1620SN/A cs->cs_key_update_begin = null_key_update; 1630SN/A cs->cs_key_update_end = null_key_update; 1640SN/A} 1650SN/A 1660SN/A/* 1670SN/A * Teardown crypto support. 1680SN/A */ 1690SN/Avoid 1700SN/Aieee80211_crypto_detach(struct ieee80211com *ic) 1710SN/A{ 1720SN/A ieee80211_crypto_delglobalkeys(ic); 1730SN/A} 1740SN/A 1750SN/A/* 1760SN/A * Register a crypto cipher module. 1770SN/A */ 1780SN/Avoid 1790SN/Aieee80211_crypto_register(const struct ieee80211_cipher *cip) 1800SN/A{ 1810SN/A if (cip->ic_cipher >= IEEE80211_CIPHER_MAX) { 1820SN/A printf("%s: cipher %s has an invalid cipher index %u\n", 1830SN/A __func__, cip->ic_name, cip->ic_cipher); 1840SN/A return; 185870SN/A } 186870SN/A if (ciphers[cip->ic_cipher] != NULL && ciphers[cip->ic_cipher] != cip) { 18716682Sserb printf("%s: cipher %s registered with a different template\n", 1881224SN/A __func__, cip->ic_name); 1891224SN/A return; 19010071SN/A } 191870SN/A ciphers[cip->ic_cipher] = cip; 192870SN/A} 193870SN/A 194870SN/A/* 19510729Sserb * Unregister a crypto cipher module. 196870SN/A */ 197870SN/Avoid 198870SN/Aieee80211_crypto_unregister(const struct ieee80211_cipher *cip) 199870SN/A{ 200870SN/A if (cip->ic_cipher >= IEEE80211_CIPHER_MAX) { 201870SN/A printf("%s: cipher %s has an invalid cipher index %u\n", 2021224SN/A __func__, cip->ic_name, cip->ic_cipher); 2031224SN/A return; 2041224SN/A } 2051224SN/A if (ciphers[cip->ic_cipher] != NULL && ciphers[cip->ic_cipher] != cip) { 2061224SN/A printf("%s: cipher %s registered with a different template\n", 2071224SN/A __func__, cip->ic_name); 2081224SN/A return; 2091224SN/A } 2101224SN/A /* NB: don't complain about not being registered */ 2111224SN/A /* XXX disallow if references */ 212870SN/A ciphers[cip->ic_cipher] = NULL; 213870SN/A} 214870SN/A 21510071SN/Aint 216870SN/Aieee80211_crypto_available(u_int cipher) 217870SN/A{ 218870SN/A return cipher < IEEE80211_CIPHER_MAX && ciphers[cipher] != NULL; 219870SN/A} 220870SN/A 221870SN/A/* XXX well-known names! */ 222870SN/Astatic const char *cipher_modnames[] = { 223870SN/A "wlan_wep", /* IEEE80211_CIPHER_WEP */ 224870SN/A "wlan_tkip", /* IEEE80211_CIPHER_TKIP */ 225870SN/A "wlan_aes_ocb", /* IEEE80211_CIPHER_AES_OCB */ 226870SN/A "wlan_ccmp", /* IEEE80211_CIPHER_AES_CCM */ 227870SN/A "wlan_ckip", /* IEEE80211_CIPHER_CKIP */ 228870SN/A}; 229870SN/A 230870SN/A/* 231870SN/A * Establish a relationship between the specified key and cipher 232870SN/A * and, if necessary, allocate a hardware index from the driver. 233870SN/A * Note that when a fixed key index is required it must be specified 234870SN/A * and we blindly assign it w/o consulting the driver (XXX). 235870SN/A * 236870SN/A * This must be the first call applied to a key; all the other key 237870SN/A * routines assume wk_cipher is setup. 238870SN/A * 239870SN/A * Locking must be handled by the caller using: 240870SN/A * ieee80211_key_update_begin(ic); 241870SN/A * ieee80211_key_update_end(ic); 242870SN/A */ 243870SN/Aint 244870SN/Aieee80211_crypto_newkey(struct ieee80211com *ic, 245870SN/A int cipher, int flags, struct ieee80211_key *key) 246870SN/A{ 247870SN/A#define N(a) (sizeof(a) / sizeof(a[0])) 248870SN/A const struct ieee80211_cipher *cip; 249870SN/A ieee80211_keyix keyix, rxkeyix; 250870SN/A void *keyctx; 251870SN/A int oflags; 252870SN/A 253870SN/A /* 254870SN/A * Validate cipher and set reference to cipher routines. 255870SN/A */ 256870SN/A if (cipher >= IEEE80211_CIPHER_MAX) { 257870SN/A IEEE80211_DPRINTF(ic, IEEE80211_MSG_CRYPTO, 258870SN/A "%s: invalid cipher %u\n", __func__, cipher); 259870SN/A ic->ic_stats.is_crypto_badcipher++; 260870SN/A return 0; 2619048SN/A } 2629048SN/A cip = ciphers[cipher]; 263870SN/A if (cip == NULL) { 264870SN/A /* 26510071SN/A * Auto-load cipher module if we have a well-known name 266870SN/A * for it. It might be better to use string names rather 267870SN/A * than numbers and craft a module name based on the cipher 268870SN/A * name; e.g. wlan_cipher_<cipher-name>. 269870SN/A */ 270870SN/A if (cipher < N(cipher_modnames)) { 271870SN/A IEEE80211_DPRINTF(ic, IEEE80211_MSG_CRYPTO, 272870SN/A "%s: unregistered cipher %u, load module %s\n", 27310729Sserb __func__, cipher, cipher_modnames[cipher]); 274870SN/A ieee80211_load_module(cipher_modnames[cipher]); 275870SN/A /* 276870SN/A * If cipher module loaded it should immediately 277870SN/A * call ieee80211_crypto_register which will fill 2780SN/A * in the entry in the ciphers array. 2790SN/A */ 2800SN/A cip = ciphers[cipher]; 2810SN/A } 2820SN/A if (cip == NULL) { 2831224SN/A IEEE80211_DPRINTF(ic, IEEE80211_MSG_CRYPTO, 2840SN/A "%s: unable to load cipher %u, module %s\n", 2850SN/A __func__, cipher, 2860SN/A cipher < N(cipher_modnames) ? 2870SN/A cipher_modnames[cipher] : "<unknown>"); 2880SN/A ic->ic_stats.is_crypto_nocipher++; 2890SN/A return 0; 2900SN/A } 2910SN/A } 2920SN/A 2930SN/A oflags = key->wk_flags; 2940SN/A flags &= IEEE80211_KEY_COMMON; 2950SN/A /* 2960SN/A * If the hardware does not support the cipher then 2970SN/A * fallback to a host-based implementation. 2980SN/A */ 2990SN/A if ((ic->ic_caps & (1<<cipher)) == 0) { 3000SN/A IEEE80211_DPRINTF(ic, IEEE80211_MSG_CRYPTO, 3010SN/A "%s: no h/w support for cipher %s, falling back to s/w\n", 3020SN/A __func__, cip->ic_name); 3030SN/A flags |= IEEE80211_KEY_SWCRYPT; 3040SN/A } 3050SN/A /* 3060SN/A * Hardware TKIP with software MIC is an important 3070SN/A * combination; we handle it by flagging each key, 3080SN/A * the cipher modules honor it. 3090SN/A */ 3100SN/A if (cipher == IEEE80211_CIPHER_TKIP && 3110SN/A (ic->ic_caps & IEEE80211_C_TKIPMIC) == 0) { 3120SN/A IEEE80211_DPRINTF(ic, IEEE80211_MSG_CRYPTO, 3130SN/A "%s: no h/w support for TKIP MIC, falling back to s/w\n", 3140SN/A __func__); 3150SN/A flags |= IEEE80211_KEY_SWMIC; 3160SN/A } 3170SN/A 3180SN/A /* 3190SN/A * Bind cipher to key instance. Note we do this 3200SN/A * after checking the device capabilities so the 3212859SN/A * cipher module can optimize space usage based on 3222859SN/A * whether or not it needs to do the cipher work. 3232859SN/A */ 3242944SN/A if (key->wk_cipher != cip || key->wk_flags != flags) { 3252859SN/Aagain: 3269449SN/A /* 3279449SN/A * Fillin the flags so cipher modules can see s/w 3289449SN/A * crypto requirements and potentially allocate 3299449SN/A * different state and/or attach different method 33015526Salexsch * pointers. 33115526Salexsch * 33215526Salexsch * XXX this is not right when s/w crypto fallback 33315526Salexsch * fails and we try to restore previous state. 33415526Salexsch */ 33515526Salexsch key->wk_flags = flags; 3362859SN/A keyctx = cip->ic_attach(ic, key); 3370SN/A if (keyctx == NULL) { 3380SN/A IEEE80211_DPRINTF(ic, IEEE80211_MSG_CRYPTO, 3390SN/A "%s: unable to attach cipher %s\n", 3400SN/A __func__, cip->ic_name); 3410SN/A key->wk_flags = oflags; /* restore old flags */ 3420SN/A ic->ic_stats.is_crypto_attachfail++; 3430SN/A return 0; 3440SN/A } 3450SN/A cipher_detach(key); 3460SN/A key->wk_cipher = cip; /* XXX refcnt? */ 3470SN/A key->wk_private = keyctx; 348217SN/A } 34913629Savstepan /* 35013629Savstepan * Commit to requested usage so driver can see the flags. 3510SN/A */ 3520SN/A key->wk_flags = flags; 353217SN/A 354217SN/A /* 355217SN/A * Ask the driver for a key index if we don't have one. 356217SN/A * Note that entries in the global key table always have 357217SN/A * an index; this means it's safe to call this routine 358217SN/A * for these entries just to setup the reference to the 359217SN/A * cipher template. Note also that when using software 360217SN/A * crypto we also call the driver to give us a key index. 3615003SN/A */ 3625003SN/A if (key->wk_keyix == IEEE80211_KEYIX_NONE) { 3635003SN/A if (!dev_key_alloc(ic, key, &keyix, &rxkeyix)) { 3645003SN/A /* 3655003SN/A * Driver has no room; fallback to doing crypto 3665003SN/A * in the host. We change the flags and start the 3675003SN/A * procedure over. If we get back here then there's 3685003SN/A * no hope and we bail. Note that this can leave 3695003SN/A * the key in a inconsistent state if the caller 37013629Savstepan * continues to use it. 371217SN/A */ 372217SN/A if ((key->wk_flags & IEEE80211_KEY_SWCRYPT) == 0) { 373217SN/A ic->ic_stats.is_crypto_swfallback++; 374217SN/A IEEE80211_DPRINTF(ic, IEEE80211_MSG_CRYPTO, 3750SN/A "%s: no h/w resources for cipher %s, " 3760SN/A "falling back to s/w\n", __func__, 3770SN/A cip->ic_name); 3780SN/A oflags = key->wk_flags; 3790SN/A flags |= IEEE80211_KEY_SWCRYPT; 3800SN/A if (cipher == IEEE80211_CIPHER_TKIP) 3810SN/A flags |= IEEE80211_KEY_SWMIC; 3820SN/A goto again; 3830SN/A } 3840SN/A ic->ic_stats.is_crypto_keyfail++; 3850SN/A IEEE80211_DPRINTF(ic, IEEE80211_MSG_CRYPTO, 3860SN/A "%s: unable to setup cipher %s\n", 3870SN/A __func__, cip->ic_name); 3880SN/A return 0; 3890SN/A } 3908979SN/A key->wk_keyix = keyix; 3910SN/A key->wk_rxkeyix = rxkeyix; 3920SN/A } 3937387SN/A return 1; 3941696SN/A#undef N 3950SN/A} 3960SN/A 3970SN/A/* 3980SN/A * Remove the key (no locking, for internal use). 3990SN/A */ 4000SN/Astatic int 4010SN/A_ieee80211_crypto_delkey(struct ieee80211com *ic, struct ieee80211_key *key) 4020SN/A{ 4030SN/A ieee80211_keyix keyix; 4040SN/A 4050SN/A KASSERT(key->wk_cipher != NULL, ("No cipher!")); 4060SN/A 4079048SN/A IEEE80211_DPRINTF(ic, IEEE80211_MSG_CRYPTO, 4080SN/A "%s: %s keyix %u flags 0x%x rsc %ju tsc %ju len %u\n", 4090SN/A __func__, key->wk_cipher->ic_name, 41016682Sserb key->wk_keyix, key->wk_flags, 4110SN/A key->wk_keyrsc, key->wk_keytsc, key->wk_keylen); 4120SN/A 4130SN/A keyix = key->wk_keyix; 4140SN/A if (keyix != IEEE80211_KEYIX_NONE) { 4159048SN/A /* 4160SN/A * Remove hardware entry. 4170SN/A */ 41816682Sserb /* XXX key cache */ 4190SN/A if (!dev_key_delete(ic, key)) { 4200SN/A IEEE80211_DPRINTF(ic, IEEE80211_MSG_CRYPTO, 4210SN/A "%s: driver did not delete key index %u\n", 4220SN/A __func__, keyix); 4239048SN/A ic->ic_stats.is_crypto_delkey++; 4240SN/A /* XXX recovery? */ 4250SN/A } 42616682Sserb } 4270SN/A cipher_detach(key); 4280SN/A memset(key, 0, sizeof(*key)); 4290SN/A ieee80211_crypto_resetkey(ic, key, IEEE80211_KEYIX_NONE); 4300SN/A return 1; 4319048SN/A} 4320SN/A 4330SN/A/* 43416682Sserb * Remove the specified key. 4350SN/A */ 4360SN/Aint 4370SN/Aieee80211_crypto_delkey(struct ieee80211com *ic, struct ieee80211_key *key) 4380SN/A{ 4399048SN/A int status; 4400SN/A 4410SN/A ieee80211_key_update_begin(ic); 44216682Sserb status = _ieee80211_crypto_delkey(ic, key); 4430SN/A ieee80211_key_update_end(ic); 4440SN/A return status; 4450SN/A} 446217SN/A 447217SN/A/* 4489048SN/A * Clear the global key table. 4490SN/A */ 4500SN/Avoid 4510SN/Aieee80211_crypto_delglobalkeys(struct ieee80211com *ic) 4520SN/A{ 4530SN/A int i; 4540SN/A 4550SN/A ieee80211_key_update_begin(ic); 45616682Sserb for (i = 0; i < IEEE80211_WEP_NKID; i++) 4579048SN/A (void) _ieee80211_crypto_delkey(ic, &ic->ic_nw_keys[i]); 45816682Sserb ieee80211_key_update_end(ic); 45916682Sserb} 4600SN/A 46116682Sserb/* 4620SN/A * Set the contents of the specified key. 4630SN/A * 4640SN/A * Locking must be handled by the caller using: 4650SN/A * ieee80211_key_update_begin(ic); 4660SN/A * ieee80211_key_update_end(ic); 4670SN/A */ 4685003SN/Aint 4695003SN/Aieee80211_crypto_setkey(struct ieee80211com *ic, struct ieee80211_key *key, 4705003SN/A const u_int8_t macaddr[IEEE80211_ADDR_LEN]) 4715003SN/A{ 4720SN/A const struct ieee80211_cipher *cip = key->wk_cipher; 4730SN/A 4745003SN/A KASSERT(cip != NULL, ("No cipher!")); 4750SN/A 4760SN/A IEEE80211_DPRINTF(ic, IEEE80211_MSG_CRYPTO, 4770SN/A "%s: %s keyix %u flags 0x%x mac %s rsc %ju tsc %ju len %u\n", 4780SN/A __func__, cip->ic_name, key->wk_keyix, 4790SN/A key->wk_flags, ether_sprintf(macaddr), 48013629Savstepan key->wk_keyrsc, key->wk_keytsc, key->wk_keylen); 48113629Savstepan 48213629Savstepan /* 48313629Savstepan * Give cipher a chance to validate key contents. 48413629Savstepan * XXX should happen before modifying state. 48513629Savstepan */ 4860SN/A if (!cip->ic_setkey(key)) { 4870SN/A IEEE80211_DPRINTF(ic, IEEE80211_MSG_CRYPTO, 4880SN/A "%s: cipher %s rejected key index %u len %u flags 0x%x\n", 48913629Savstepan __func__, cip->ic_name, key->wk_keyix, 4900SN/A key->wk_keylen, key->wk_flags); 4910SN/A ic->ic_stats.is_crypto_setkey_cipher++; 4920SN/A return 0; 4930SN/A } 4940SN/A if (key->wk_keyix == IEEE80211_KEYIX_NONE) { 4958242SN/A /* XXX nothing allocated, should not happen */ 4960SN/A IEEE80211_DPRINTF(ic, IEEE80211_MSG_CRYPTO, 4970SN/A "%s: no key index; should not happen!\n", __func__); 4980SN/A ic->ic_stats.is_crypto_setkey_nokey++; 4990SN/A return 0; 5000SN/A } 5019048SN/A return dev_key_set(ic, key, macaddr); 5020SN/A} 5030SN/A 5040SN/A/* 5050SN/A * Add privacy headers appropriate for the specified key. 5060SN/A */ 5070SN/Astruct ieee80211_key * 5080SN/Aieee80211_crypto_encap(struct ieee80211com *ic, 5090SN/A struct ieee80211_node *ni, struct mbuf *m) 5100SN/A{ 5110SN/A struct ieee80211_key *k; 5120SN/A struct ieee80211_frame *wh; 5130SN/A const struct ieee80211_cipher *cip; 5140SN/A u_int8_t keyid; 5150SN/A 5160SN/A /* 5170SN/A * Multicast traffic always uses the multicast key. 5189048SN/A * Otherwise if a unicast key is set we use that and 5190SN/A * it is always key index 0. When no unicast key is 5200SN/A * set we fall back to the default transmit key. 5210SN/A */ 5220SN/A wh = mtod(m, struct ieee80211_frame *); 5230SN/A if (IEEE80211_IS_MULTICAST(wh->i_addr1) || 5240SN/A IEEE80211_KEY_UNDEFINED(&ni->ni_ucastkey)) { 5250SN/A if (ic->ic_def_txkey == IEEE80211_KEYIX_NONE) { 5260SN/A IEEE80211_DPRINTF(ic, IEEE80211_MSG_CRYPTO, 5270SN/A "[%s] no default transmit key (%s) deftxkey %u\n", 5280SN/A ether_sprintf(wh->i_addr1), __func__, 5290SN/A ic->ic_def_txkey); 5300SN/A ic->ic_stats.is_tx_nodefkey++; 5310SN/A return NULL; 53213629Savstepan } 533217SN/A keyid = ic->ic_def_txkey; 534217SN/A k = &ic->ic_nw_keys[ic->ic_def_txkey]; 535217SN/A } else { 536217SN/A keyid = 0; 537217SN/A k = &ni->ni_ucastkey; 5380SN/A } 5399048SN/A cip = k->wk_cipher; 5409048SN/A return (cip->ic_encap(k, m, keyid<<6) ? k : NULL); 5419048SN/A} 5420SN/A 543870SN/A/* 5440SN/A * Validate and strip privacy headers (and trailer) for a 5450SN/A * received frame that has the WEP/Privacy bit set. 5460SN/A */ 5470SN/Astruct ieee80211_key * 5480SN/Aieee80211_crypto_decap(struct ieee80211com *ic, 5490SN/A struct ieee80211_node *ni, struct mbuf *m, int hdrlen) 5500SN/A{ 5510SN/A#define IEEE80211_WEP_HDRLEN (IEEE80211_WEP_IVLEN + IEEE80211_WEP_KIDLEN) 5520SN/A#define IEEE80211_WEP_MINLEN \ 5530SN/A (sizeof(struct ieee80211_frame) + \ 5540SN/A IEEE80211_WEP_HDRLEN + IEEE80211_WEP_CRCLEN) 5550SN/A struct ieee80211_key *k; 5560SN/A struct ieee80211_frame *wh; 5570SN/A const struct ieee80211_cipher *cip; 5580SN/A const u_int8_t *ivp; 5590SN/A u_int8_t keyid; 5600SN/A 5610SN/A /* NB: this minimum size data frame could be bigger */ 5620SN/A if (m->m_pkthdr.len < IEEE80211_WEP_MINLEN) { 5630SN/A IEEE80211_DPRINTF(ic, IEEE80211_MSG_ANY, 5640SN/A "%s: WEP data frame too short, len %u\n", 5650SN/A __func__, m->m_pkthdr.len); 5660SN/A ic->ic_stats.is_rx_tooshort++; /* XXX need unique stat? */ 5670SN/A return NULL; 5680SN/A } 5690SN/A 5700SN/A /* 571870SN/A * Locate the key. If unicast and there is no unicast 572870SN/A * key then we fall back to the key id in the header. 573870SN/A * This assumes unicast keys are only configured when 574870SN/A * the key id in the header is meaningless (typically 0). 575870SN/A */ 576870SN/A wh = mtod(m, struct ieee80211_frame *); 577870SN/A ivp = mtod(m, const u_int8_t *) + hdrlen; /* XXX contig */ 578870SN/A keyid = ivp[IEEE80211_WEP_IVLEN]; 5790SN/A if (IEEE80211_IS_MULTICAST(wh->i_addr1) || 5800SN/A IEEE80211_KEY_UNDEFINED(&ni->ni_ucastkey)) 5810SN/A k = &ic->ic_nw_keys[keyid >> 6]; 5820SN/A else 5830SN/A k = &ni->ni_ucastkey; 5840SN/A 5850SN/A /* 586 * Insure crypto header is contiguous for all decap work. 587 */ 588 cip = k->wk_cipher; 589 if (m->m_len < hdrlen + cip->ic_header && 590 (m = m_pullup(m, hdrlen + cip->ic_header)) == NULL) { 591 IEEE80211_DPRINTF(ic, IEEE80211_MSG_CRYPTO, 592 "[%s] unable to pullup %s header\n", 593 ether_sprintf(wh->i_addr2), cip->ic_name); 594 ic->ic_stats.is_rx_wepfail++; /* XXX */ 595 return 0; 596 } 597 598 return (cip->ic_decap(k, m, hdrlen) ? k : NULL); 599#undef IEEE80211_WEP_MINLEN 600#undef IEEE80211_WEP_HDRLEN 601} 602