The Design and Implementation of the FreeBSD Operating System, Second Edition
Now available: The Design and Implementation of the FreeBSD Operating System (Second Edition)


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]

FreeBSD/Linux Kernel Cross Reference
sys/net80211/ieee80211_crypto_tkip.c

Version: -  FREEBSD  -  FREEBSD-13-STABLE  -  FREEBSD-13-0  -  FREEBSD-12-STABLE  -  FREEBSD-12-0  -  FREEBSD-11-STABLE  -  FREEBSD-11-0  -  FREEBSD-10-STABLE  -  FREEBSD-10-0  -  FREEBSD-9-STABLE  -  FREEBSD-9-0  -  FREEBSD-8-STABLE  -  FREEBSD-8-0  -  FREEBSD-7-STABLE  -  FREEBSD-7-0  -  FREEBSD-6-STABLE  -  FREEBSD-6-0  -  FREEBSD-5-STABLE  -  FREEBSD-5-0  -  FREEBSD-4-STABLE  -  FREEBSD-3-STABLE  -  FREEBSD22  -  l41  -  OPENBSD  -  linux-2.6  -  MK84  -  PLAN9  -  xnu-8792 
SearchContext: -  none  -  3  -  10 

    1 /*-
    2  * Copyright (c) 2002-2008 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  *
   14  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
   15  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
   16  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
   17  * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
   18  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
   19  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
   20  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
   21  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
   22  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
   23  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
   24  */
   25 
   26 #include <sys/cdefs.h>
   27 __FBSDID("$FreeBSD: releng/8.3/sys/net80211/ieee80211_crypto_tkip.c 204215 2010-02-22 17:10:47Z bschmidt $");
   28 
   29 /*
   30  * IEEE 802.11i TKIP crypto support.
   31  *
   32  * Part of this module is derived from similar code in the Host
   33  * AP driver. The code is used with the consent of the author and
   34  * it's license is included below.
   35  */
   36 #include "opt_wlan.h"
   37 
   38 #include <sys/param.h>
   39 #include <sys/systm.h> 
   40 #include <sys/mbuf.h>   
   41 #include <sys/malloc.h>
   42 #include <sys/kernel.h>
   43 #include <sys/module.h>
   44 #include <sys/endian.h>
   45 
   46 #include <sys/socket.h>
   47 
   48 #include <net/if.h>
   49 #include <net/if_media.h>
   50 #include <net/ethernet.h>
   51 
   52 #include <net80211/ieee80211_var.h>
   53 
   54 static  void *tkip_attach(struct ieee80211vap *, struct ieee80211_key *);
   55 static  void tkip_detach(struct ieee80211_key *);
   56 static  int tkip_setkey(struct ieee80211_key *);
   57 static  int tkip_encap(struct ieee80211_key *, struct mbuf *m, uint8_t keyid);
   58 static  int tkip_enmic(struct ieee80211_key *, struct mbuf *, int);
   59 static  int tkip_decap(struct ieee80211_key *, struct mbuf *, int);
   60 static  int tkip_demic(struct ieee80211_key *, struct mbuf *, int);
   61 
   62 static const struct ieee80211_cipher tkip  = {
   63         .ic_name        = "TKIP",
   64         .ic_cipher      = IEEE80211_CIPHER_TKIP,
   65         .ic_header      = IEEE80211_WEP_IVLEN + IEEE80211_WEP_KIDLEN +
   66                           IEEE80211_WEP_EXTIVLEN,
   67         .ic_trailer     = IEEE80211_WEP_CRCLEN,
   68         .ic_miclen      = IEEE80211_WEP_MICLEN,
   69         .ic_attach      = tkip_attach,
   70         .ic_detach      = tkip_detach,
   71         .ic_setkey      = tkip_setkey,
   72         .ic_encap       = tkip_encap,
   73         .ic_decap       = tkip_decap,
   74         .ic_enmic       = tkip_enmic,
   75         .ic_demic       = tkip_demic,
   76 };
   77 
   78 typedef uint8_t u8;
   79 typedef uint16_t u16;
   80 typedef uint32_t __u32;
   81 typedef uint32_t u32;
   82 
   83 struct tkip_ctx {
   84         struct ieee80211vap *tc_vap;    /* for diagnostics+statistics */
   85 
   86         u16     tx_ttak[5];
   87         int     tx_phase1_done;
   88         u8      tx_rc4key[16];          /* XXX for test module; make locals? */
   89 
   90         u16     rx_ttak[5];
   91         int     rx_phase1_done;
   92         u8      rx_rc4key[16];          /* XXX for test module; make locals? */
   93         uint64_t rx_rsc;                /* held until MIC verified */
   94 };
   95 
   96 static  void michael_mic(struct tkip_ctx *, const u8 *key,
   97                 struct mbuf *m, u_int off, size_t data_len,
   98                 u8 mic[IEEE80211_WEP_MICLEN]);
   99 static  int tkip_encrypt(struct tkip_ctx *, struct ieee80211_key *,
  100                 struct mbuf *, int hdr_len);
  101 static  int tkip_decrypt(struct tkip_ctx *, struct ieee80211_key *,
  102                 struct mbuf *, int hdr_len);
  103 
  104 /* number of references from net80211 layer */
  105 static  int nrefs = 0;
  106 
  107 static void *
  108 tkip_attach(struct ieee80211vap *vap, struct ieee80211_key *k)
  109 {
  110         struct tkip_ctx *ctx;
  111 
  112         ctx = (struct tkip_ctx *) malloc(sizeof(struct tkip_ctx),
  113                 M_80211_CRYPTO, M_NOWAIT | M_ZERO);
  114         if (ctx == NULL) {
  115                 vap->iv_stats.is_crypto_nomem++;
  116                 return NULL;
  117         }
  118 
  119         ctx->tc_vap = vap;
  120         nrefs++;                        /* NB: we assume caller locking */
  121         return ctx;
  122 }
  123 
  124 static void
  125 tkip_detach(struct ieee80211_key *k)
  126 {
  127         struct tkip_ctx *ctx = k->wk_private;
  128 
  129         free(ctx, M_80211_CRYPTO);
  130         KASSERT(nrefs > 0, ("imbalanced attach/detach"));
  131         nrefs--;                        /* NB: we assume caller locking */
  132 }
  133 
  134 static int
  135 tkip_setkey(struct ieee80211_key *k)
  136 {
  137         struct tkip_ctx *ctx = k->wk_private;
  138 
  139         if (k->wk_keylen != (128/NBBY)) {
  140                 (void) ctx;             /* XXX */
  141                 IEEE80211_DPRINTF(ctx->tc_vap, IEEE80211_MSG_CRYPTO,
  142                         "%s: Invalid key length %u, expecting %u\n",
  143                         __func__, k->wk_keylen, 128/NBBY);
  144                 return 0;
  145         }
  146         k->wk_keytsc = 1;               /* TSC starts at 1 */
  147         ctx->rx_phase1_done = 0;
  148         return 1;
  149 }
  150 
  151 /*
  152  * Add privacy headers and do any s/w encryption required.
  153  */
  154 static int
  155 tkip_encap(struct ieee80211_key *k, struct mbuf *m, uint8_t keyid)
  156 {
  157         struct tkip_ctx *ctx = k->wk_private;
  158         struct ieee80211vap *vap = ctx->tc_vap;
  159         struct ieee80211com *ic = vap->iv_ic;
  160         uint8_t *ivp;
  161         int hdrlen;
  162 
  163         /*
  164          * Handle TKIP counter measures requirement.
  165          */
  166         if (vap->iv_flags & IEEE80211_F_COUNTERM) {
  167 #ifdef IEEE80211_DEBUG
  168                 struct ieee80211_frame *wh = mtod(m, struct ieee80211_frame *);
  169 #endif
  170 
  171                 IEEE80211_NOTE_MAC(vap, IEEE80211_MSG_CRYPTO, wh->i_addr2,
  172                     "discard frame due to countermeasures (%s)", __func__);
  173                 vap->iv_stats.is_crypto_tkipcm++;
  174                 return 0;
  175         }
  176         hdrlen = ieee80211_hdrspace(ic, mtod(m, void *));
  177 
  178         /*
  179          * Copy down 802.11 header and add the IV, KeyID, and ExtIV.
  180          */
  181         M_PREPEND(m, tkip.ic_header, M_NOWAIT);
  182         if (m == NULL)
  183                 return 0;
  184         ivp = mtod(m, uint8_t *);
  185         memmove(ivp, ivp + tkip.ic_header, hdrlen);
  186         ivp += hdrlen;
  187 
  188         ivp[0] = k->wk_keytsc >> 8;             /* TSC1 */
  189         ivp[1] = (ivp[0] | 0x20) & 0x7f;        /* WEP seed */
  190         ivp[2] = k->wk_keytsc >> 0;             /* TSC0 */
  191         ivp[3] = keyid | IEEE80211_WEP_EXTIV;   /* KeyID | ExtID */
  192         ivp[4] = k->wk_keytsc >> 16;            /* TSC2 */
  193         ivp[5] = k->wk_keytsc >> 24;            /* TSC3 */
  194         ivp[6] = k->wk_keytsc >> 32;            /* TSC4 */
  195         ivp[7] = k->wk_keytsc >> 40;            /* TSC5 */
  196 
  197         /*
  198          * Finally, do software encrypt if neeed.
  199          */
  200         if (k->wk_flags & IEEE80211_KEY_SWENCRYPT) {
  201                 if (!tkip_encrypt(ctx, k, m, hdrlen))
  202                         return 0;
  203                 /* NB: tkip_encrypt handles wk_keytsc */
  204         } else
  205                 k->wk_keytsc++;
  206 
  207         return 1;
  208 }
  209 
  210 /*
  211  * Add MIC to the frame as needed.
  212  */
  213 static int
  214 tkip_enmic(struct ieee80211_key *k, struct mbuf *m, int force)
  215 {
  216         struct tkip_ctx *ctx = k->wk_private;
  217 
  218         if (force || (k->wk_flags & IEEE80211_KEY_SWENMIC)) {
  219                 struct ieee80211_frame *wh = mtod(m, struct ieee80211_frame *);
  220                 struct ieee80211vap *vap = ctx->tc_vap;
  221                 struct ieee80211com *ic = vap->iv_ic;
  222                 int hdrlen;
  223                 uint8_t mic[IEEE80211_WEP_MICLEN];
  224 
  225                 vap->iv_stats.is_crypto_tkipenmic++;
  226 
  227                 hdrlen = ieee80211_hdrspace(ic, wh);
  228 
  229                 michael_mic(ctx, k->wk_txmic,
  230                         m, hdrlen, m->m_pkthdr.len - hdrlen, mic);
  231                 return m_append(m, tkip.ic_miclen, mic);
  232         }
  233         return 1;
  234 }
  235 
  236 static __inline uint64_t
  237 READ_6(uint8_t b0, uint8_t b1, uint8_t b2, uint8_t b3, uint8_t b4, uint8_t b5)
  238 {
  239         uint32_t iv32 = (b0 << 0) | (b1 << 8) | (b2 << 16) | (b3 << 24);
  240         uint16_t iv16 = (b4 << 0) | (b5 << 8);
  241         return (((uint64_t)iv16) << 32) | iv32;
  242 }
  243 
  244 /*
  245  * Validate and strip privacy headers (and trailer) for a
  246  * received frame.  If necessary, decrypt the frame using
  247  * the specified key.
  248  */
  249 static int
  250 tkip_decap(struct ieee80211_key *k, struct mbuf *m, int hdrlen)
  251 {
  252         struct tkip_ctx *ctx = k->wk_private;
  253         struct ieee80211vap *vap = ctx->tc_vap;
  254         struct ieee80211_frame *wh;
  255         uint8_t *ivp, tid;
  256 
  257         /*
  258          * Header should have extended IV and sequence number;
  259          * verify the former and validate the latter.
  260          */
  261         wh = mtod(m, struct ieee80211_frame *);
  262         ivp = mtod(m, uint8_t *) + hdrlen;
  263         if ((ivp[IEEE80211_WEP_IVLEN] & IEEE80211_WEP_EXTIV) == 0) {
  264                 /*
  265                  * No extended IV; discard frame.
  266                  */
  267                 IEEE80211_NOTE_MAC(vap, IEEE80211_MSG_CRYPTO, wh->i_addr2,
  268                     "%s", "missing ExtIV for TKIP cipher");
  269                 vap->iv_stats.is_rx_tkipformat++;
  270                 return 0;
  271         }
  272         /*
  273          * Handle TKIP counter measures requirement.
  274          */
  275         if (vap->iv_flags & IEEE80211_F_COUNTERM) {
  276                 IEEE80211_NOTE_MAC(vap, IEEE80211_MSG_CRYPTO, wh->i_addr2,
  277                     "discard frame due to countermeasures (%s)", __func__);
  278                 vap->iv_stats.is_crypto_tkipcm++;
  279                 return 0;
  280         }
  281 
  282         tid = ieee80211_gettid(wh);
  283         ctx->rx_rsc = READ_6(ivp[2], ivp[0], ivp[4], ivp[5], ivp[6], ivp[7]);
  284         if (ctx->rx_rsc <= k->wk_keyrsc[tid]) {
  285                 /*
  286                  * Replay violation; notify upper layer.
  287                  */
  288                 ieee80211_notify_replay_failure(vap, wh, k, ctx->rx_rsc, tid);
  289                 vap->iv_stats.is_rx_tkipreplay++;
  290                 return 0;
  291         }
  292         /*
  293          * NB: We can't update the rsc in the key until MIC is verified.
  294          *
  295          * We assume we are not preempted between doing the check above
  296          * and updating wk_keyrsc when stripping the MIC in tkip_demic.
  297          * Otherwise we might process another packet and discard it as
  298          * a replay.
  299          */
  300 
  301         /*
  302          * Check if the device handled the decrypt in hardware.
  303          * If so we just strip the header; otherwise we need to
  304          * handle the decrypt in software.
  305          */
  306         if ((k->wk_flags & IEEE80211_KEY_SWDECRYPT) &&
  307             !tkip_decrypt(ctx, k, m, hdrlen))
  308                 return 0;
  309 
  310         /*
  311          * Copy up 802.11 header and strip crypto bits.
  312          */
  313         memmove(mtod(m, uint8_t *) + tkip.ic_header, mtod(m, void *), hdrlen);
  314         m_adj(m, tkip.ic_header);
  315         m_adj(m, -tkip.ic_trailer);
  316 
  317         return 1;
  318 }
  319 
  320 /*
  321  * Verify and strip MIC from the frame.
  322  */
  323 static int
  324 tkip_demic(struct ieee80211_key *k, struct mbuf *m, int force)
  325 {
  326         struct tkip_ctx *ctx = k->wk_private;
  327         struct ieee80211_frame *wh;
  328         uint8_t tid;
  329 
  330         wh = mtod(m, struct ieee80211_frame *);
  331         if ((k->wk_flags & IEEE80211_KEY_SWDEMIC) || force) {
  332                 struct ieee80211vap *vap = ctx->tc_vap;
  333                 int hdrlen = ieee80211_hdrspace(vap->iv_ic, wh);
  334                 u8 mic[IEEE80211_WEP_MICLEN];
  335                 u8 mic0[IEEE80211_WEP_MICLEN];
  336 
  337                 vap->iv_stats.is_crypto_tkipdemic++;
  338 
  339                 michael_mic(ctx, k->wk_rxmic, 
  340                         m, hdrlen, m->m_pkthdr.len - (hdrlen + tkip.ic_miclen),
  341                         mic);
  342                 m_copydata(m, m->m_pkthdr.len - tkip.ic_miclen,
  343                         tkip.ic_miclen, mic0);
  344                 if (memcmp(mic, mic0, tkip.ic_miclen)) {
  345                         /* NB: 802.11 layer handles statistic and debug msg */
  346                         ieee80211_notify_michael_failure(vap, wh,
  347                                 k->wk_rxkeyix != IEEE80211_KEYIX_NONE ?
  348                                         k->wk_rxkeyix : k->wk_keyix);
  349                         return 0;
  350                 }
  351         }
  352         /*
  353          * Strip MIC from the tail.
  354          */
  355         m_adj(m, -tkip.ic_miclen);
  356 
  357         /*
  358          * Ok to update rsc now that MIC has been verified.
  359          */
  360         tid = ieee80211_gettid(wh);
  361         k->wk_keyrsc[tid] = ctx->rx_rsc;
  362 
  363         return 1;
  364 }
  365 
  366 /*
  367  * Host AP crypt: host-based TKIP encryption implementation for Host AP driver
  368  *
  369  * Copyright (c) 2003-2004, Jouni Malinen <jkmaline@cc.hut.fi>
  370  *
  371  * This program is free software; you can redistribute it and/or modify
  372  * it under the terms of the GNU General Public License version 2 as
  373  * published by the Free Software Foundation. See README and COPYING for
  374  * more details.
  375  *
  376  * Alternatively, this software may be distributed under the terms of BSD
  377  * license.
  378  */
  379 
  380 static const __u32 crc32_table[256] = {
  381         0x00000000L, 0x77073096L, 0xee0e612cL, 0x990951baL, 0x076dc419L,
  382         0x706af48fL, 0xe963a535L, 0x9e6495a3L, 0x0edb8832L, 0x79dcb8a4L,
  383         0xe0d5e91eL, 0x97d2d988L, 0x09b64c2bL, 0x7eb17cbdL, 0xe7b82d07L,
  384         0x90bf1d91L, 0x1db71064L, 0x6ab020f2L, 0xf3b97148L, 0x84be41deL,
  385         0x1adad47dL, 0x6ddde4ebL, 0xf4d4b551L, 0x83d385c7L, 0x136c9856L,
  386         0x646ba8c0L, 0xfd62f97aL, 0x8a65c9ecL, 0x14015c4fL, 0x63066cd9L,
  387         0xfa0f3d63L, 0x8d080df5L, 0x3b6e20c8L, 0x4c69105eL, 0xd56041e4L,
  388         0xa2677172L, 0x3c03e4d1L, 0x4b04d447L, 0xd20d85fdL, 0xa50ab56bL,
  389         0x35b5a8faL, 0x42b2986cL, 0xdbbbc9d6L, 0xacbcf940L, 0x32d86ce3L,
  390         0x45df5c75L, 0xdcd60dcfL, 0xabd13d59L, 0x26d930acL, 0x51de003aL,
  391         0xc8d75180L, 0xbfd06116L, 0x21b4f4b5L, 0x56b3c423L, 0xcfba9599L,
  392         0xb8bda50fL, 0x2802b89eL, 0x5f058808L, 0xc60cd9b2L, 0xb10be924L,
  393         0x2f6f7c87L, 0x58684c11L, 0xc1611dabL, 0xb6662d3dL, 0x76dc4190L,
  394         0x01db7106L, 0x98d220bcL, 0xefd5102aL, 0x71b18589L, 0x06b6b51fL,
  395         0x9fbfe4a5L, 0xe8b8d433L, 0x7807c9a2L, 0x0f00f934L, 0x9609a88eL,
  396         0xe10e9818L, 0x7f6a0dbbL, 0x086d3d2dL, 0x91646c97L, 0xe6635c01L,
  397         0x6b6b51f4L, 0x1c6c6162L, 0x856530d8L, 0xf262004eL, 0x6c0695edL,
  398         0x1b01a57bL, 0x8208f4c1L, 0xf50fc457L, 0x65b0d9c6L, 0x12b7e950L,
  399         0x8bbeb8eaL, 0xfcb9887cL, 0x62dd1ddfL, 0x15da2d49L, 0x8cd37cf3L,
  400         0xfbd44c65L, 0x4db26158L, 0x3ab551ceL, 0xa3bc0074L, 0xd4bb30e2L,
  401         0x4adfa541L, 0x3dd895d7L, 0xa4d1c46dL, 0xd3d6f4fbL, 0x4369e96aL,
  402         0x346ed9fcL, 0xad678846L, 0xda60b8d0L, 0x44042d73L, 0x33031de5L,
  403         0xaa0a4c5fL, 0xdd0d7cc9L, 0x5005713cL, 0x270241aaL, 0xbe0b1010L,
  404         0xc90c2086L, 0x5768b525L, 0x206f85b3L, 0xb966d409L, 0xce61e49fL,
  405         0x5edef90eL, 0x29d9c998L, 0xb0d09822L, 0xc7d7a8b4L, 0x59b33d17L,
  406         0x2eb40d81L, 0xb7bd5c3bL, 0xc0ba6cadL, 0xedb88320L, 0x9abfb3b6L,
  407         0x03b6e20cL, 0x74b1d29aL, 0xead54739L, 0x9dd277afL, 0x04db2615L,
  408         0x73dc1683L, 0xe3630b12L, 0x94643b84L, 0x0d6d6a3eL, 0x7a6a5aa8L,
  409         0xe40ecf0bL, 0x9309ff9dL, 0x0a00ae27L, 0x7d079eb1L, 0xf00f9344L,
  410         0x8708a3d2L, 0x1e01f268L, 0x6906c2feL, 0xf762575dL, 0x806567cbL,
  411         0x196c3671L, 0x6e6b06e7L, 0xfed41b76L, 0x89d32be0L, 0x10da7a5aL,
  412         0x67dd4accL, 0xf9b9df6fL, 0x8ebeeff9L, 0x17b7be43L, 0x60b08ed5L,
  413         0xd6d6a3e8L, 0xa1d1937eL, 0x38d8c2c4L, 0x4fdff252L, 0xd1bb67f1L,
  414         0xa6bc5767L, 0x3fb506ddL, 0x48b2364bL, 0xd80d2bdaL, 0xaf0a1b4cL,
  415         0x36034af6L, 0x41047a60L, 0xdf60efc3L, 0xa867df55L, 0x316e8eefL,
  416         0x4669be79L, 0xcb61b38cL, 0xbc66831aL, 0x256fd2a0L, 0x5268e236L,
  417         0xcc0c7795L, 0xbb0b4703L, 0x220216b9L, 0x5505262fL, 0xc5ba3bbeL,
  418         0xb2bd0b28L, 0x2bb45a92L, 0x5cb36a04L, 0xc2d7ffa7L, 0xb5d0cf31L,
  419         0x2cd99e8bL, 0x5bdeae1dL, 0x9b64c2b0L, 0xec63f226L, 0x756aa39cL,
  420         0x026d930aL, 0x9c0906a9L, 0xeb0e363fL, 0x72076785L, 0x05005713L,
  421         0x95bf4a82L, 0xe2b87a14L, 0x7bb12baeL, 0x0cb61b38L, 0x92d28e9bL,
  422         0xe5d5be0dL, 0x7cdcefb7L, 0x0bdbdf21L, 0x86d3d2d4L, 0xf1d4e242L,
  423         0x68ddb3f8L, 0x1fda836eL, 0x81be16cdL, 0xf6b9265bL, 0x6fb077e1L,
  424         0x18b74777L, 0x88085ae6L, 0xff0f6a70L, 0x66063bcaL, 0x11010b5cL,
  425         0x8f659effL, 0xf862ae69L, 0x616bffd3L, 0x166ccf45L, 0xa00ae278L,
  426         0xd70dd2eeL, 0x4e048354L, 0x3903b3c2L, 0xa7672661L, 0xd06016f7L,
  427         0x4969474dL, 0x3e6e77dbL, 0xaed16a4aL, 0xd9d65adcL, 0x40df0b66L,
  428         0x37d83bf0L, 0xa9bcae53L, 0xdebb9ec5L, 0x47b2cf7fL, 0x30b5ffe9L,
  429         0xbdbdf21cL, 0xcabac28aL, 0x53b39330L, 0x24b4a3a6L, 0xbad03605L,
  430         0xcdd70693L, 0x54de5729L, 0x23d967bfL, 0xb3667a2eL, 0xc4614ab8L,
  431         0x5d681b02L, 0x2a6f2b94L, 0xb40bbe37L, 0xc30c8ea1L, 0x5a05df1bL,
  432         0x2d02ef8dL
  433 };
  434 
  435 static __inline u16 RotR1(u16 val)
  436 {
  437         return (val >> 1) | (val << 15);
  438 }
  439 
  440 static __inline u8 Lo8(u16 val)
  441 {
  442         return val & 0xff;
  443 }
  444 
  445 static __inline u8 Hi8(u16 val)
  446 {
  447         return val >> 8;
  448 }
  449 
  450 static __inline u16 Lo16(u32 val)
  451 {
  452         return val & 0xffff;
  453 }
  454 
  455 static __inline u16 Hi16(u32 val)
  456 {
  457         return val >> 16;
  458 }
  459 
  460 static __inline u16 Mk16(u8 hi, u8 lo)
  461 {
  462         return lo | (((u16) hi) << 8);
  463 }
  464 
  465 static __inline u16 Mk16_le(const u16 *v)
  466 {
  467         return le16toh(*v);
  468 }
  469 
  470 static const u16 Sbox[256] = {
  471         0xC6A5, 0xF884, 0xEE99, 0xF68D, 0xFF0D, 0xD6BD, 0xDEB1, 0x9154,
  472         0x6050, 0x0203, 0xCEA9, 0x567D, 0xE719, 0xB562, 0x4DE6, 0xEC9A,
  473         0x8F45, 0x1F9D, 0x8940, 0xFA87, 0xEF15, 0xB2EB, 0x8EC9, 0xFB0B,
  474         0x41EC, 0xB367, 0x5FFD, 0x45EA, 0x23BF, 0x53F7, 0xE496, 0x9B5B,
  475         0x75C2, 0xE11C, 0x3DAE, 0x4C6A, 0x6C5A, 0x7E41, 0xF502, 0x834F,
  476         0x685C, 0x51F4, 0xD134, 0xF908, 0xE293, 0xAB73, 0x6253, 0x2A3F,
  477         0x080C, 0x9552, 0x4665, 0x9D5E, 0x3028, 0x37A1, 0x0A0F, 0x2FB5,
  478         0x0E09, 0x2436, 0x1B9B, 0xDF3D, 0xCD26, 0x4E69, 0x7FCD, 0xEA9F,
  479         0x121B, 0x1D9E, 0x5874, 0x342E, 0x362D, 0xDCB2, 0xB4EE, 0x5BFB,
  480         0xA4F6, 0x764D, 0xB761, 0x7DCE, 0x527B, 0xDD3E, 0x5E71, 0x1397,
  481         0xA6F5, 0xB968, 0x0000, 0xC12C, 0x4060, 0xE31F, 0x79C8, 0xB6ED,
  482         0xD4BE, 0x8D46, 0x67D9, 0x724B, 0x94DE, 0x98D4, 0xB0E8, 0x854A,
  483         0xBB6B, 0xC52A, 0x4FE5, 0xED16, 0x86C5, 0x9AD7, 0x6655, 0x1194,
  484         0x8ACF, 0xE910, 0x0406, 0xFE81, 0xA0F0, 0x7844, 0x25BA, 0x4BE3,
  485         0xA2F3, 0x5DFE, 0x80C0, 0x058A, 0x3FAD, 0x21BC, 0x7048, 0xF104,
  486         0x63DF, 0x77C1, 0xAF75, 0x4263, 0x2030, 0xE51A, 0xFD0E, 0xBF6D,
  487         0x814C, 0x1814, 0x2635, 0xC32F, 0xBEE1, 0x35A2, 0x88CC, 0x2E39,
  488         0x9357, 0x55F2, 0xFC82, 0x7A47, 0xC8AC, 0xBAE7, 0x322B, 0xE695,
  489         0xC0A0, 0x1998, 0x9ED1, 0xA37F, 0x4466, 0x547E, 0x3BAB, 0x0B83,
  490         0x8CCA, 0xC729, 0x6BD3, 0x283C, 0xA779, 0xBCE2, 0x161D, 0xAD76,
  491         0xDB3B, 0x6456, 0x744E, 0x141E, 0x92DB, 0x0C0A, 0x486C, 0xB8E4,
  492         0x9F5D, 0xBD6E, 0x43EF, 0xC4A6, 0x39A8, 0x31A4, 0xD337, 0xF28B,
  493         0xD532, 0x8B43, 0x6E59, 0xDAB7, 0x018C, 0xB164, 0x9CD2, 0x49E0,
  494         0xD8B4, 0xACFA, 0xF307, 0xCF25, 0xCAAF, 0xF48E, 0x47E9, 0x1018,
  495         0x6FD5, 0xF088, 0x4A6F, 0x5C72, 0x3824, 0x57F1, 0x73C7, 0x9751,
  496         0xCB23, 0xA17C, 0xE89C, 0x3E21, 0x96DD, 0x61DC, 0x0D86, 0x0F85,
  497         0xE090, 0x7C42, 0x71C4, 0xCCAA, 0x90D8, 0x0605, 0xF701, 0x1C12,
  498         0xC2A3, 0x6A5F, 0xAEF9, 0x69D0, 0x1791, 0x9958, 0x3A27, 0x27B9,
  499         0xD938, 0xEB13, 0x2BB3, 0x2233, 0xD2BB, 0xA970, 0x0789, 0x33A7,
  500         0x2DB6, 0x3C22, 0x1592, 0xC920, 0x8749, 0xAAFF, 0x5078, 0xA57A,
  501         0x038F, 0x59F8, 0x0980, 0x1A17, 0x65DA, 0xD731, 0x84C6, 0xD0B8,
  502         0x82C3, 0x29B0, 0x5A77, 0x1E11, 0x7BCB, 0xA8FC, 0x6DD6, 0x2C3A,
  503 };
  504 
  505 static __inline u16 _S_(u16 v)
  506 {
  507         u16 t = Sbox[Hi8(v)];
  508         return Sbox[Lo8(v)] ^ ((t << 8) | (t >> 8));
  509 }
  510 
  511 #define PHASE1_LOOP_COUNT 8
  512 
  513 static void tkip_mixing_phase1(u16 *TTAK, const u8 *TK, const u8 *TA, u32 IV32)
  514 {
  515         int i, j;
  516 
  517         /* Initialize the 80-bit TTAK from TSC (IV32) and TA[0..5] */
  518         TTAK[0] = Lo16(IV32);
  519         TTAK[1] = Hi16(IV32);
  520         TTAK[2] = Mk16(TA[1], TA[0]);
  521         TTAK[3] = Mk16(TA[3], TA[2]);
  522         TTAK[4] = Mk16(TA[5], TA[4]);
  523 
  524         for (i = 0; i < PHASE1_LOOP_COUNT; i++) {
  525                 j = 2 * (i & 1);
  526                 TTAK[0] += _S_(TTAK[4] ^ Mk16(TK[1 + j], TK[0 + j]));
  527                 TTAK[1] += _S_(TTAK[0] ^ Mk16(TK[5 + j], TK[4 + j]));
  528                 TTAK[2] += _S_(TTAK[1] ^ Mk16(TK[9 + j], TK[8 + j]));
  529                 TTAK[3] += _S_(TTAK[2] ^ Mk16(TK[13 + j], TK[12 + j]));
  530                 TTAK[4] += _S_(TTAK[3] ^ Mk16(TK[1 + j], TK[0 + j])) + i;
  531         }
  532 }
  533 
  534 #ifndef _BYTE_ORDER
  535 #error "Don't know native byte order"
  536 #endif
  537 
  538 static void tkip_mixing_phase2(u8 *WEPSeed, const u8 *TK, const u16 *TTAK,
  539                                u16 IV16)
  540 {
  541         /* Make temporary area overlap WEP seed so that the final copy can be
  542          * avoided on little endian hosts. */
  543         u16 *PPK = (u16 *) &WEPSeed[4];
  544 
  545         /* Step 1 - make copy of TTAK and bring in TSC */
  546         PPK[0] = TTAK[0];
  547         PPK[1] = TTAK[1];
  548         PPK[2] = TTAK[2];
  549         PPK[3] = TTAK[3];
  550         PPK[4] = TTAK[4];
  551         PPK[5] = TTAK[4] + IV16;
  552 
  553         /* Step 2 - 96-bit bijective mixing using S-box */
  554         PPK[0] += _S_(PPK[5] ^ Mk16_le((const u16 *) &TK[0]));
  555         PPK[1] += _S_(PPK[0] ^ Mk16_le((const u16 *) &TK[2]));
  556         PPK[2] += _S_(PPK[1] ^ Mk16_le((const u16 *) &TK[4]));
  557         PPK[3] += _S_(PPK[2] ^ Mk16_le((const u16 *) &TK[6]));
  558         PPK[4] += _S_(PPK[3] ^ Mk16_le((const u16 *) &TK[8]));
  559         PPK[5] += _S_(PPK[4] ^ Mk16_le((const u16 *) &TK[10]));
  560 
  561         PPK[0] += RotR1(PPK[5] ^ Mk16_le((const u16 *) &TK[12]));
  562         PPK[1] += RotR1(PPK[0] ^ Mk16_le((const u16 *) &TK[14]));
  563         PPK[2] += RotR1(PPK[1]);
  564         PPK[3] += RotR1(PPK[2]);
  565         PPK[4] += RotR1(PPK[3]);
  566         PPK[5] += RotR1(PPK[4]);
  567 
  568         /* Step 3 - bring in last of TK bits, assign 24-bit WEP IV value
  569          * WEPSeed[0..2] is transmitted as WEP IV */
  570         WEPSeed[0] = Hi8(IV16);
  571         WEPSeed[1] = (Hi8(IV16) | 0x20) & 0x7F;
  572         WEPSeed[2] = Lo8(IV16);
  573         WEPSeed[3] = Lo8((PPK[5] ^ Mk16_le((const u16 *) &TK[0])) >> 1);
  574 
  575 #if _BYTE_ORDER == _BIG_ENDIAN
  576         {
  577                 int i;
  578                 for (i = 0; i < 6; i++)
  579                         PPK[i] = (PPK[i] << 8) | (PPK[i] >> 8);
  580         }
  581 #endif
  582 }
  583 
  584 static void
  585 wep_encrypt(u8 *key, struct mbuf *m0, u_int off, size_t data_len,
  586         uint8_t icv[IEEE80211_WEP_CRCLEN])
  587 {
  588         u32 i, j, k, crc;
  589         size_t buflen;
  590         u8 S[256];
  591         u8 *pos;
  592         struct mbuf *m;
  593 #define S_SWAP(a,b) do { u8 t = S[a]; S[a] = S[b]; S[b] = t; } while(0)
  594 
  595         /* Setup RC4 state */
  596         for (i = 0; i < 256; i++)
  597                 S[i] = i;
  598         j = 0;
  599         for (i = 0; i < 256; i++) {
  600                 j = (j + S[i] + key[i & 0x0f]) & 0xff;
  601                 S_SWAP(i, j);
  602         }
  603 
  604         /* Compute CRC32 over unencrypted data and apply RC4 to data */
  605         crc = ~0;
  606         i = j = 0;
  607         m = m0;
  608         pos = mtod(m, uint8_t *) + off;
  609         buflen = m->m_len - off;
  610         for (;;) {
  611                 if (buflen > data_len)
  612                         buflen = data_len;
  613                 data_len -= buflen;
  614                 for (k = 0; k < buflen; k++) {
  615                         crc = crc32_table[(crc ^ *pos) & 0xff] ^ (crc >> 8);
  616                         i = (i + 1) & 0xff;
  617                         j = (j + S[i]) & 0xff;
  618                         S_SWAP(i, j);
  619                         *pos++ ^= S[(S[i] + S[j]) & 0xff];
  620                 }
  621                 m = m->m_next;
  622                 if (m == NULL) {
  623                         KASSERT(data_len == 0,
  624                             ("out of buffers with data_len %zu\n", data_len));
  625                         break;
  626                 }
  627                 pos = mtod(m, uint8_t *);
  628                 buflen = m->m_len;
  629         }
  630         crc = ~crc;
  631 
  632         /* Append little-endian CRC32 and encrypt it to produce ICV */
  633         icv[0] = crc;
  634         icv[1] = crc >> 8;
  635         icv[2] = crc >> 16;
  636         icv[3] = crc >> 24;
  637         for (k = 0; k < IEEE80211_WEP_CRCLEN; k++) {
  638                 i = (i + 1) & 0xff;
  639                 j = (j + S[i]) & 0xff;
  640                 S_SWAP(i, j);
  641                 icv[k] ^= S[(S[i] + S[j]) & 0xff];
  642         }
  643 }
  644 
  645 static int
  646 wep_decrypt(u8 *key, struct mbuf *m, u_int off, size_t data_len)
  647 {
  648         u32 i, j, k, crc;
  649         u8 S[256];
  650         u8 *pos, icv[4];
  651         size_t buflen;
  652 
  653         /* Setup RC4 state */
  654         for (i = 0; i < 256; i++)
  655                 S[i] = i;
  656         j = 0;
  657         for (i = 0; i < 256; i++) {
  658                 j = (j + S[i] + key[i & 0x0f]) & 0xff;
  659                 S_SWAP(i, j);
  660         }
  661 
  662         /* Apply RC4 to data and compute CRC32 over decrypted data */
  663         crc = ~0;
  664         i = j = 0;
  665         pos = mtod(m, uint8_t *) + off;
  666         buflen = m->m_len - off;
  667         for (;;) {
  668                 if (buflen > data_len)
  669                         buflen = data_len;
  670                 data_len -= buflen;
  671                 for (k = 0; k < buflen; k++) {
  672                         i = (i + 1) & 0xff;
  673                         j = (j + S[i]) & 0xff;
  674                         S_SWAP(i, j);
  675                         *pos ^= S[(S[i] + S[j]) & 0xff];
  676                         crc = crc32_table[(crc ^ *pos) & 0xff] ^ (crc >> 8);
  677                         pos++;
  678                 }
  679                 m = m->m_next;
  680                 if (m == NULL) {
  681                         KASSERT(data_len == 0,
  682                             ("out of buffers with data_len %zu\n", data_len));
  683                         break;
  684                 }
  685                 pos = mtod(m, uint8_t *);
  686                 buflen = m->m_len;
  687         }
  688         crc = ~crc;
  689 
  690         /* Encrypt little-endian CRC32 and verify that it matches with the
  691          * received ICV */
  692         icv[0] = crc;
  693         icv[1] = crc >> 8;
  694         icv[2] = crc >> 16;
  695         icv[3] = crc >> 24;
  696         for (k = 0; k < 4; k++) {
  697                 i = (i + 1) & 0xff;
  698                 j = (j + S[i]) & 0xff;
  699                 S_SWAP(i, j);
  700                 if ((icv[k] ^ S[(S[i] + S[j]) & 0xff]) != *pos++) {
  701                         /* ICV mismatch - drop frame */
  702                         return -1;
  703                 }
  704         }
  705 
  706         return 0;
  707 }
  708 
  709 
  710 static __inline u32 rotl(u32 val, int bits)
  711 {
  712         return (val << bits) | (val >> (32 - bits));
  713 }
  714 
  715 
  716 static __inline u32 rotr(u32 val, int bits)
  717 {
  718         return (val >> bits) | (val << (32 - bits));
  719 }
  720 
  721 
  722 static __inline u32 xswap(u32 val)
  723 {
  724         return ((val & 0x00ff00ff) << 8) | ((val & 0xff00ff00) >> 8);
  725 }
  726 
  727 
  728 #define michael_block(l, r)     \
  729 do {                            \
  730         r ^= rotl(l, 17);       \
  731         l += r;                 \
  732         r ^= xswap(l);          \
  733         l += r;                 \
  734         r ^= rotl(l, 3);        \
  735         l += r;                 \
  736         r ^= rotr(l, 2);        \
  737         l += r;                 \
  738 } while (0)
  739 
  740 
  741 static __inline u32 get_le32_split(u8 b0, u8 b1, u8 b2, u8 b3)
  742 {
  743         return b0 | (b1 << 8) | (b2 << 16) | (b3 << 24);
  744 }
  745 
  746 static __inline u32 get_le32(const u8 *p)
  747 {
  748         return get_le32_split(p[0], p[1], p[2], p[3]);
  749 }
  750 
  751 
  752 static __inline void put_le32(u8 *p, u32 v)
  753 {
  754         p[0] = v;
  755         p[1] = v >> 8;
  756         p[2] = v >> 16;
  757         p[3] = v >> 24;
  758 }
  759 
  760 /*
  761  * Craft pseudo header used to calculate the MIC.
  762  */
  763 static void
  764 michael_mic_hdr(const struct ieee80211_frame *wh0, uint8_t hdr[16])
  765 {
  766         const struct ieee80211_frame_addr4 *wh =
  767                 (const struct ieee80211_frame_addr4 *) wh0;
  768 
  769         switch (wh->i_fc[1] & IEEE80211_FC1_DIR_MASK) {
  770         case IEEE80211_FC1_DIR_NODS:
  771                 IEEE80211_ADDR_COPY(hdr, wh->i_addr1); /* DA */
  772                 IEEE80211_ADDR_COPY(hdr + IEEE80211_ADDR_LEN, wh->i_addr2);
  773                 break;
  774         case IEEE80211_FC1_DIR_TODS:
  775                 IEEE80211_ADDR_COPY(hdr, wh->i_addr3); /* DA */
  776                 IEEE80211_ADDR_COPY(hdr + IEEE80211_ADDR_LEN, wh->i_addr2);
  777                 break;
  778         case IEEE80211_FC1_DIR_FROMDS:
  779                 IEEE80211_ADDR_COPY(hdr, wh->i_addr1); /* DA */
  780                 IEEE80211_ADDR_COPY(hdr + IEEE80211_ADDR_LEN, wh->i_addr3);
  781                 break;
  782         case IEEE80211_FC1_DIR_DSTODS:
  783                 IEEE80211_ADDR_COPY(hdr, wh->i_addr3); /* DA */
  784                 IEEE80211_ADDR_COPY(hdr + IEEE80211_ADDR_LEN, wh->i_addr4);
  785                 break;
  786         }
  787 
  788         if (wh->i_fc[0] & IEEE80211_FC0_SUBTYPE_QOS) {
  789                 const struct ieee80211_qosframe *qwh =
  790                         (const struct ieee80211_qosframe *) wh;
  791                 hdr[12] = qwh->i_qos[0] & IEEE80211_QOS_TID;
  792         } else
  793                 hdr[12] = 0;
  794         hdr[13] = hdr[14] = hdr[15] = 0; /* reserved */
  795 }
  796 
  797 static void
  798 michael_mic(struct tkip_ctx *ctx, const u8 *key,
  799         struct mbuf *m, u_int off, size_t data_len,
  800         u8 mic[IEEE80211_WEP_MICLEN])
  801 {
  802         uint8_t hdr[16];
  803         u32 l, r;
  804         const uint8_t *data;
  805         u_int space;
  806 
  807         michael_mic_hdr(mtod(m, struct ieee80211_frame *), hdr);
  808 
  809         l = get_le32(key);
  810         r = get_le32(key + 4);
  811 
  812         /* Michael MIC pseudo header: DA, SA, 3 x 0, Priority */
  813         l ^= get_le32(hdr);
  814         michael_block(l, r);
  815         l ^= get_le32(&hdr[4]);
  816         michael_block(l, r);
  817         l ^= get_le32(&hdr[8]);
  818         michael_block(l, r);
  819         l ^= get_le32(&hdr[12]);
  820         michael_block(l, r);
  821 
  822         /* first buffer has special handling */
  823         data = mtod(m, const uint8_t *) + off;
  824         space = m->m_len - off;
  825         for (;;) {
  826                 if (space > data_len)
  827                         space = data_len;
  828                 /* collect 32-bit blocks from current buffer */
  829                 while (space >= sizeof(uint32_t)) {
  830                         l ^= get_le32(data);
  831                         michael_block(l, r);
  832                         data += sizeof(uint32_t), space -= sizeof(uint32_t);
  833                         data_len -= sizeof(uint32_t);
  834                 }
  835                 /*
  836                  * NB: when space is zero we make one more trip around
  837                  * the loop to advance to the next mbuf where there is
  838                  * data.  This handles the case where there are 4*n
  839                  * bytes in an mbuf followed by <4 bytes in a later mbuf.
  840                  * By making an extra trip we'll drop out of the loop
  841                  * with m pointing at the mbuf with 3 bytes and space
  842                  * set as required by the remainder handling below.
  843                  */
  844                 if (data_len == 0 ||
  845                     (data_len < sizeof(uint32_t) && space != 0))
  846                         break;
  847                 m = m->m_next;
  848                 if (m == NULL) {
  849                         KASSERT(0, ("out of data, data_len %zu\n", data_len));
  850                         break;
  851                 }
  852                 if (space != 0) {
  853                         const uint8_t *data_next;
  854                         /*
  855                          * Block straddles buffers, split references.
  856                          */
  857                         data_next = mtod(m, const uint8_t *);
  858                         KASSERT(m->m_len >= sizeof(uint32_t) - space,
  859                                 ("not enough data in following buffer, "
  860                                 "m_len %u need %zu\n", m->m_len,
  861                                 sizeof(uint32_t) - space));
  862                         switch (space) {
  863                         case 1:
  864                                 l ^= get_le32_split(data[0], data_next[0],
  865                                         data_next[1], data_next[2]);
  866                                 data = data_next + 3;
  867                                 space = m->m_len - 3;
  868                                 break;
  869                         case 2:
  870                                 l ^= get_le32_split(data[0], data[1],
  871                                         data_next[0], data_next[1]);
  872                                 data = data_next + 2;
  873                                 space = m->m_len - 2;
  874                                 break;
  875                         case 3:
  876                                 l ^= get_le32_split(data[0], data[1],
  877                                         data[2], data_next[0]);
  878                                 data = data_next + 1;
  879                                 space = m->m_len - 1;
  880                                 break;
  881                         }
  882                         michael_block(l, r);
  883                         data_len -= sizeof(uint32_t);
  884                 } else {
  885                         /*
  886                          * Setup for next buffer.
  887                          */
  888                         data = mtod(m, const uint8_t *);
  889                         space = m->m_len;
  890                 }
  891         }
  892         /*
  893          * Catch degenerate cases like mbuf[4*n+1 bytes] followed by
  894          * mbuf[2 bytes].  I don't believe these should happen; if they
  895          * do then we'll need more involved logic.
  896          */
  897         KASSERT(data_len <= space,
  898             ("not enough data, data_len %zu space %u\n", data_len, space));
  899 
  900         /* Last block and padding (0x5a, 4..7 x 0) */
  901         switch (data_len) {
  902         case 0:
  903                 l ^= get_le32_split(0x5a, 0, 0, 0);
  904                 break;
  905         case 1:
  906                 l ^= get_le32_split(data[0], 0x5a, 0, 0);
  907                 break;
  908         case 2:
  909                 l ^= get_le32_split(data[0], data[1], 0x5a, 0);
  910                 break;
  911         case 3:
  912                 l ^= get_le32_split(data[0], data[1], data[2], 0x5a);
  913                 break;
  914         }
  915         michael_block(l, r);
  916         /* l ^= 0; */
  917         michael_block(l, r);
  918 
  919         put_le32(mic, l);
  920         put_le32(mic + 4, r);
  921 }
  922 
  923 static int
  924 tkip_encrypt(struct tkip_ctx *ctx, struct ieee80211_key *key,
  925         struct mbuf *m, int hdrlen)
  926 {
  927         struct ieee80211_frame *wh;
  928         uint8_t icv[IEEE80211_WEP_CRCLEN];
  929 
  930         ctx->tc_vap->iv_stats.is_crypto_tkip++;
  931 
  932         wh = mtod(m, struct ieee80211_frame *);
  933         if (!ctx->tx_phase1_done) {
  934                 tkip_mixing_phase1(ctx->tx_ttak, key->wk_key, wh->i_addr2,
  935                                    (u32)(key->wk_keytsc >> 16));
  936                 ctx->tx_phase1_done = 1;
  937         }
  938         tkip_mixing_phase2(ctx->tx_rc4key, key->wk_key, ctx->tx_ttak,
  939                 (u16) key->wk_keytsc);
  940 
  941         wep_encrypt(ctx->tx_rc4key,
  942                 m, hdrlen + tkip.ic_header,
  943                 m->m_pkthdr.len - (hdrlen + tkip.ic_header),
  944                 icv);
  945         (void) m_append(m, IEEE80211_WEP_CRCLEN, icv);  /* XXX check return */
  946 
  947         key->wk_keytsc++;
  948         if ((u16)(key->wk_keytsc) == 0)
  949                 ctx->tx_phase1_done = 0;
  950         return 1;
  951 }
  952 
  953 static int
  954 tkip_decrypt(struct tkip_ctx *ctx, struct ieee80211_key *key,
  955         struct mbuf *m, int hdrlen)
  956 {
  957         struct ieee80211_frame *wh;
  958         struct ieee80211vap *vap = ctx->tc_vap;
  959         u32 iv32;
  960         u16 iv16;
  961         u8 tid;
  962 
  963         vap->iv_stats.is_crypto_tkip++;
  964 
  965         wh = mtod(m, struct ieee80211_frame *);
  966         /* NB: tkip_decap already verified header and left seq in rx_rsc */
  967         iv16 = (u16) ctx->rx_rsc;
  968         iv32 = (u32) (ctx->rx_rsc >> 16);
  969 
  970         tid = ieee80211_gettid(wh);
  971         if (iv32 != (u32)(key->wk_keyrsc[tid] >> 16) || !ctx->rx_phase1_done) {
  972                 tkip_mixing_phase1(ctx->rx_ttak, key->wk_key,
  973                         wh->i_addr2, iv32);
  974                 ctx->rx_phase1_done = 1;
  975         }
  976         tkip_mixing_phase2(ctx->rx_rc4key, key->wk_key, ctx->rx_ttak, iv16);
  977 
  978         /* NB: m is unstripped; deduct headers + ICV to get payload */
  979         if (wep_decrypt(ctx->rx_rc4key,
  980                 m, hdrlen + tkip.ic_header,
  981                 m->m_pkthdr.len - (hdrlen + tkip.ic_header + tkip.ic_trailer))) {
  982                 if (iv32 != (u32)(key->wk_keyrsc[tid] >> 16)) {
  983                         /* Previously cached Phase1 result was already lost, so
  984                          * it needs to be recalculated for the next packet. */
  985                         ctx->rx_phase1_done = 0;
  986                 }
  987                 IEEE80211_NOTE_MAC(vap, IEEE80211_MSG_CRYPTO, wh->i_addr2,
  988                     "%s", "TKIP ICV mismatch on decrypt");
  989                 vap->iv_stats.is_rx_tkipicv++;
  990                 return 0;
  991         }
  992         return 1;
  993 }
  994 
  995 /*
  996  * Module glue.
  997  */
  998 IEEE80211_CRYPTO_MODULE(tkip, 1);

Cache object: ee4f30cbcdd6a3b162d8f10447dca04d


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]


This page is part of the FreeBSD/Linux Linux Kernel Cross-Reference, and was automatically generated using a modified version of the LXR engine.