Beispiel #1
0
static int
runtest(struct ieee80211vap *vap, struct ciphertest *t)
{
	struct ieee80211_key *key;
	struct sk_buff *skb = NULL;
	const struct ieee80211_cipher *cip;
	u_int8_t mac[IEEE80211_ADDR_LEN];
	struct tkip_ctx *ctx;
	int hdrlen;

	printk("%s: ", t->name);

	if (!ieee80211_crypto_available(vap, t->cipher)) {
		printk("FAIL: ieee80211_crypto_available failed\n");
		return 0;
	}

	/*
	 * Setup key.
	 */
	key = &vap->iv_nw_keys[t->keyix];
	key->wk_keyix = t->keyix;
	if (!ieee80211_crypto_newkey(vap, t->cipher,
				     IEEE80211_KEY_XMIT | IEEE80211_KEY_RECV,
				     key)) {
		printk("FAIL: ieee80211_crypto_newkey failed\n");
		goto bad;
	}

	memcpy(key->wk_key, t->key, t->key_len);
	key->wk_keylen = 128 / NBBY;
	memset(key->wk_keyrsc, 0, sizeof(key->wk_keyrsc));
	key->wk_keytsc = 0;
	if (!ieee80211_crypto_setkey(vap, key, mac, NULL)) {
		printk("FAIL: ieee80211_crypto_setkey failed\n");
		goto bad;
	}

	/*
	 * Craft frame from plaintext data.  Note that
	 * we leave the MIC off as we'll add it ourself
	 * and then check it against the reference data.
	 */
	cip = key->wk_cipher;
	skb = ieee80211_dev_alloc_skb(t->plaintext_len +
		cip->ic_miclen + cip->ic_header + cip->ic_trailer);
	if (skb == NULL) {
		printk("FAIL: unable to allocate skbuff\n");
		goto bad;
	}
	skb_reserve(skb, cip->ic_header);
	memcpy(skb_put(skb, t->plaintext_len - cip->ic_miclen),
		t->plaintext, t->plaintext_len - cip->ic_miclen);

	/*
	 * Add MIC.
	 */
	if (!ieee80211_crypto_enmic(vap, key, skb, 0)) {
		printk("FAIL: tkip enmic failed\n");
		goto bad;
	}
	/*
	 * Verify: frame length, frame contents.
	 */
	if (skb->len != t->plaintext_len) {
		printk("FAIL: enmic botch; length mismatch\n");
		cmpfail(skb->data, skb->len,
			t->plaintext, t->plaintext_len);
		goto bad;
	}
	if (memcmp(skb->data, t->plaintext, t->plaintext_len)) {
		printk("FAIL: enmic botch\n");
		cmpfail(skb->data, skb->len,
			t->plaintext, t->plaintext_len);
		goto bad;
	}
	/*
	 * Encrypt frame w/ MIC.
	 */
	if (!(*cip->ic_encap)(key, skb, t->keyix << 6)) {
		printk("FAIL: tkip encap failed\n");
		goto bad;
	}
	/*
	 * Verify: phase1, phase2, frame length, frame contents.
	 */
	ctx = key->wk_private;
	if (memcmp(ctx->tx_ttak, t->phase1, t->phase1_len)) {
		printk("FAIL: encrypt phase1 botch\n");
		cmpfail(ctx->tx_ttak, sizeof(ctx->tx_ttak),
			t->phase1, t->phase1_len);
		goto bad;
	} else if (memcmp(ctx->tx_rc4key, t->phase2, t->phase2_len)) {
		printf("FAIL: encrypt phase2 botch\n");
		cmpfail(ctx->tx_rc4key, sizeof(ctx->tx_rc4key),
			t->phase2, t->phase2_len);
		goto bad;
	} else if (skb->len != t->encrypted_len) {
		printk("FAIL: encrypt data length mismatch\n");
		cmpfail(skb->data, skb->len,
			t->encrypted, t->encrypted_len);
		goto bad;
	} else if (memcmp(skb->data, t->encrypted, skb->len)) {
		printk("FAIL: encrypt data does not compare\n");
		cmpfail(skb->data, skb->len,
			t->encrypted, t->encrypted_len);
		dumpdata("Plaintext", t->plaintext, t->plaintext_len);
		goto bad;
	}

	/*
	 * Decrypt frame.
	 */
	hdrlen = ieee80211_hdrspace(vap->iv_ic, skb->data);
	if (!(*cip->ic_decap)(key, skb, hdrlen)) {
		printk("FAIL: tkip decap failed\n");
		/*
		 * Check reason for failure: phase1, phase2, frame data (ICV).
		 */
		if (memcmp(ctx->rx_ttak, t->phase1, t->phase1_len)) {
			printk("decrypt phase1 botch\n");
			cmpfail(ctx->rx_ttak, sizeof(ctx->rx_ttak),
				t->phase1, t->phase1_len);
		} else if (memcmp(ctx->rx_rc4key, t->phase2, t->phase2_len)) {
			printf("decrypt phase2 botch\n");
			cmpfail(ctx->rx_rc4key, sizeof(ctx->rx_rc4key),
				t->phase2, t->phase2_len);
		} else {
			printk("decrypt data does not compare\n");
			cmpfail(skb->data, skb->len,
				t->plaintext, t->plaintext_len);
		}
		goto bad;
	}
	/*
	 * Verify: frame length, frame contents.
	 */
	if (skb->len != t->plaintext_len) {
		printk("FAIL: decap botch; length mismatch\n");
		cmpfail(skb->data, skb->len,
			t->plaintext, t->plaintext_len);
		goto bad;
	}
	if (memcmp(skb->data, t->plaintext, t->plaintext_len)) {
		printk("FAIL: decap botch; data does not compare\n");
		cmpfail(skb->data, skb->len,
			t->plaintext, t->plaintext_len);
		goto bad;
	}
	/*
	 * De-MIC decrypted frame.
	 */
	if (!ieee80211_crypto_demic(vap, key, skb, hdrlen, 0)) {
		printk("FAIL: tkip demic failed\n");
		goto bad;
	}
	/* XXX check frame length and contents... */
	ieee80211_dev_kfree_skb(&skb);
	ieee80211_crypto_delkey(vap, key, NULL);
	printk("PASS\n");
	return 1;
bad:
	if (skb != NULL)
		ieee80211_dev_kfree_skb(&skb);
	ieee80211_crypto_delkey(vap, key, NULL);
	return 0;
}
Beispiel #2
0
void
tkip_test(struct ieee80211com *ic)
{
	struct tkip_ctx *ctx;
	struct ieee80211_key key;
	struct sk_buff *skb = NULL;
	const struct ieee80211_cipher *cip;
	u_int8_t mac[IEEE80211_ADDR_LEN];

	/*
	 * Setup key.
	 */
	memset(&key, 0, sizeof(key));
	key.wk_flags = IEEE80211_KEY_XMIT | IEEE80211_KEY_RECV;
	key.wk_cipher = &ieee80211_cipher_none;
	if (!ieee80211_crypto_newkey(ic, IEEE80211_CIPHER_TKIP, &key)) {
		printk("ieee80211_crypto_newkey failed\n");
		goto bad;
	}

	memcpy(key.wk_key, ref_key, sizeof(ref_key));
	key.wk_keylen = 128 / NBBY;
	key.wk_keyrsc = 0;
	key.wk_keytsc = 0;
	if (!ieee80211_crypto_setkey(ic, &key, mac)) {
		printk("ieee80211_crypto_setkey failed\n");
		goto bad;
	}

	/*
	 * Craft frame from plaintext data.  Note that
	 * we leave the MIC off as we'll add it ourself
	 * and then check it against the reference data.
	 */
	cip = key.wk_cipher;
	skb = dev_alloc_skb(sizeof(ref_plaintext) +
		cip->ic_miclen + cip->ic_header + cip->ic_trailer);
	if (skb == NULL) {
		printk("unable to allocate skbuff\n");
		goto bad;
	}
	skb_reserve(skb, cip->ic_header);
	memcpy(skb_put(skb, sizeof(ref_plaintext) - cip->ic_miclen),
		ref_plaintext, sizeof(ref_plaintext) - cip->ic_miclen);

	/*
	 * Add MIC.
	 */
	if (!ieee80211_crypto_enmic(ic, &key, skb)) {
		printk("tkip enmic failed\n");
		goto bad;
	}
	/*
	 * Verify: frame length, frame contents.
	 */
	if (skb->len != sizeof(ref_plaintext)) {
		printk("enmic botch; length mismatch\n");
		cmpfail(skb->data, skb->len,
			ref_plaintext, sizeof(ref_plaintext));
		goto bad;
	}
	if (memcmp(skb->data, ref_plaintext, sizeof(ref_plaintext))) {
		printk("enmic botch\n");
		cmpfail(skb->data, skb->len,
			ref_plaintext, sizeof(ref_plaintext));
		goto bad;
	}
	/*
	 * Encrypt frame w/ MIC.
	 */
	if (!(*cip->ic_encap)(&key, skb, 0 << 6)) {
		printk("tkip encap failed\n");
		goto bad;
	}
	/*
	 * Verify: phase1, phase2, frame length, frame contents.
	 */
	ctx = key.wk_private;
	if (memcmp(ctx->tx_ttak, ref_phase1, sizeof(ref_phase1))) {
		printk("encrypt phase1 botch\n");
		cmpfail(ctx->tx_ttak, sizeof(ctx->tx_ttak),
			ref_phase1, sizeof(ref_phase1));
		goto bad;
	} else if (memcmp(ctx->tx_rc4key, ref_phase2, sizeof(ref_phase2))) {
		printf("encrypt phase2 botch\n");
		cmpfail(ctx->tx_rc4key, sizeof(ctx->tx_rc4key),
			ref_phase2, sizeof(ref_phase2));
		goto bad;
	} else if (skb->len != sizeof(ref_encrypted)) {
		printk("encrypt data length mismatch\n");
		cmpfail(skb->data, skb->len,
			ref_encrypted, sizeof(ref_encrypted));
		goto bad;
	} else if (memcmp(skb->data, ref_encrypted, skb->len)) {
		printk("encrypt data does not compare\n");
		cmpfail(skb->data, skb->len,
			ref_encrypted, sizeof(ref_encrypted));
		dumpdata("Plaintext", ref_plaintext, sizeof(ref_plaintext));
		goto bad;
	}

	/*
	 * Decrypt frame.
	 */
	if (!(*cip->ic_decap)(&key, skb)) {
		printk("tkip decap failed\n");
		/*
		 * Check reason for failure: phase1, phase2, frame data (ICV).
		 */
		if (memcmp(ctx->rx_ttak, ref_phase1, sizeof(ref_phase1))) {
			printk("decrypt phase1 botch\n");
			cmpfail(ctx->rx_ttak, sizeof(ctx->rx_ttak),
				ref_phase1, sizeof(ref_phase1));
		} else if (memcmp(ctx->rx_rc4key, ref_phase2, sizeof(ref_phase2))) {
			printf("decrypt phase2 botch\n");
			cmpfail(ctx->rx_rc4key, sizeof(ctx->rx_rc4key),
				ref_phase2, sizeof(ref_phase2));
		} else {
			printk("decrypt data does not compare\n");
			cmpfail(skb->data, skb->len,
				ref_plaintext, sizeof(ref_plaintext));
		}
		goto bad;
	}
	/*
	 * Verify: frame length, frame contents.
	 */
	if (skb->len != sizeof(ref_plaintext)) {
		printk("decap botch; length mismatch\n");
		cmpfail(skb->data, skb->len,
			ref_plaintext, sizeof(ref_plaintext));
		goto bad;
	}
	if (memcmp(skb->data, ref_plaintext, sizeof(ref_plaintext))) {
		printk("decap botch; data does not compare\n");
		cmpfail(skb->data, skb->len,
			ref_plaintext, sizeof(ref_plaintext));
		goto bad;
	}
	/*
	 * De-MIC decrypted frame.
	 */
	if (!ieee80211_crypto_demic(ic, &key, skb)) {
		printk("tkip demic failed\n");
		goto bad;
	}
	/* XXX check frame length and contents... */
	printk("802.11i TKIP test vectors passed\n");
bad:
	if (skb != NULL)
		dev_kfree_skb(skb);
	ieee80211_crypto_delkey(ic, &key);
}