ar9300_keycache.c (250008) | ar9300_keycache.c (278741) |
---|---|
1/* 2 * Copyright (c) 2013 Qualcomm Atheros, Inc. 3 * 4 * Permission to use, copy, modify, and/or distribute this software for any 5 * purpose with or without fee is hereby granted, provided that the above 6 * copyright notice and this permission notice appear in all copies. 7 * 8 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH --- 422 unchanged lines hidden (view full) --- 431#define AH_KEY_REG_SIZE 8 432 int i; 433 434 for (i = 0; i < AH_KEY_REG_SIZE; i++) { 435 entry[i] = OS_REG_READ(ah, AR_KEYTABLE_KEY0(n) + i * 4); 436 } 437#undef AH_KEY_REG_SIZE 438} | 1/* 2 * Copyright (c) 2013 Qualcomm Atheros, Inc. 3 * 4 * Permission to use, copy, modify, and/or distribute this software for any 5 * purpose with or without fee is hereby granted, provided that the above 6 * copyright notice and this permission notice appear in all copies. 7 * 8 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH --- 422 unchanged lines hidden (view full) --- 431#define AH_KEY_REG_SIZE 8 432 int i; 433 434 for (i = 0; i < AH_KEY_REG_SIZE; i++) { 435 entry[i] = OS_REG_READ(ah, AR_KEYTABLE_KEY0(n) + i * 4); 436 } 437#undef AH_KEY_REG_SIZE 438} |
439 440#if ATH_SUPPORT_KEYPLUMB_WAR 441/* 442 * Check the contents of the specified key cache entry 443 * and any associated MIC entry. 444 */ 445 HAL_BOOL 446ar9300_check_key_cache_entry(struct ath_hal *ah, u_int16_t entry, 447 const HAL_KEYVAL *k, int xorKey) 448{ 449 const HAL_CAPABILITIES *pCap = &AH_PRIVATE(ah)->ah_caps; 450 u_int32_t key0, key1, key2, key3, key4; 451 u_int32_t keyType; 452 u_int32_t xorMask = xorKey ? 453 (KEY_XOR << 24 | KEY_XOR << 16 | KEY_XOR << 8 | KEY_XOR) : 0; 454 struct ath_hal_9300 *ahp = AH9300(ah); 455 456 457 if (entry >= pCap->hal_key_cache_size) { 458 HALDEBUG(ah, HAL_DEBUG_KEYCACHE, 459 "%s: entry %u out of range\n", __func__, entry); 460 return AH_FALSE; 461 } 462 switch (k->kv_type) { 463 case HAL_CIPHER_AES_OCB: 464 keyType = AR_KEYTABLE_TYPE_AES; 465 break; 466 case HAL_CIPHER_AES_CCM: 467 if (!pCap->hal_cipher_aes_ccm_support) { 468 HALDEBUG(ah, HAL_DEBUG_KEYCACHE, "%s: AES-CCM not supported by " 469 "mac rev 0x%x\n", 470 __func__, AH_PRIVATE(ah)->ah_macRev); 471 return AH_FALSE; 472 } 473 keyType = AR_KEYTABLE_TYPE_CCM; 474 break; 475 case HAL_CIPHER_TKIP: 476 keyType = AR_KEYTABLE_TYPE_TKIP; 477 if (IS_MIC_ENABLED(ah) && entry + 64 >= pCap->hal_key_cache_size) { 478 HALDEBUG(ah, HAL_DEBUG_KEYCACHE, 479 "%s: entry %u inappropriate for TKIP\n", 480 __func__, entry); 481 return AH_FALSE; 482 } 483 break; 484 case HAL_CIPHER_WEP: 485 if (k->kv_len < 40 / NBBY) { 486 HALDEBUG(ah, HAL_DEBUG_KEYCACHE, "%s: WEP key length %u too small\n", 487 __func__, k->kv_len); 488 return AH_FALSE; 489 } 490 if (k->kv_len <= 40 / NBBY) { 491 keyType = AR_KEYTABLE_TYPE_40; 492 } else if (k->kv_len <= 104 / NBBY) { 493 keyType = AR_KEYTABLE_TYPE_104; 494 } else { 495 keyType = AR_KEYTABLE_TYPE_128; 496 } 497 break; 498 case HAL_CIPHER_CLR: 499 keyType = AR_KEYTABLE_TYPE_CLR; 500 return AH_TRUE; 501 default: 502 HALDEBUG(ah, HAL_DEBUG_KEYCACHE, "%s: cipher %u not supported\n", 503 __func__, k->kv_type); 504 return AH_TRUE; 505 } 506 507 key0 = LE_READ_4(k->kv_val + 0) ^ xorMask; 508 key1 = (LE_READ_2(k->kv_val + 4) ^ xorMask) & 0xffff; 509 key2 = LE_READ_4(k->kv_val + 6) ^ xorMask; 510 key3 = (LE_READ_2(k->kv_val + 10) ^ xorMask) & 0xffff; 511 key4 = LE_READ_4(k->kv_val + 12) ^ xorMask; 512 if (k->kv_len <= 104 / NBBY) { 513 key4 &= 0xff; 514 } 515 516 /* 517 * Note: key cache hardware requires that each double-word 518 * pair be written in even/odd order (since the destination is 519 * a 64-bit register). Don't reorder these writes w/o 520 * considering this! 521 */ 522 if (keyType == AR_KEYTABLE_TYPE_TKIP && IS_MIC_ENABLED(ah)) { 523 u_int16_t micentry = entry + 64; /* MIC goes at slot+64 */ 524 525 526 /* 527 * Invalidate the encrypt/decrypt key until the MIC 528 * key is installed so pending rx frames will fail 529 * with decrypt errors rather than a MIC error. 530 */ 531 if ((OS_REG_READ(ah, AR_KEYTABLE_KEY0(entry)) == key0) && 532 (OS_REG_READ(ah, AR_KEYTABLE_KEY1(entry)) == key1) && 533 (OS_REG_READ(ah, AR_KEYTABLE_KEY2(entry)) == key2) && 534 (OS_REG_READ(ah, AR_KEYTABLE_KEY3(entry)) == key3) && 535 (OS_REG_READ(ah, AR_KEYTABLE_KEY4(entry)) == key4) && 536 ((OS_REG_READ(ah, AR_KEYTABLE_TYPE(entry)) & AR_KEY_TYPE) == (keyType & AR_KEY_TYPE))) 537 { 538 539 /* 540 * since the AR_MISC_MODE register was written with the contents of 541 * ah_miscMode (if any) in ar9300Attach, just check ah_miscMode and 542 * save a pci read per key set. 543 */ 544 if (ahp->ah_misc_mode & AR_PCU_MIC_NEW_LOC_ENA) { 545 u_int32_t mic0,mic1,mic2,mic3,mic4; 546 /* 547 * both RX and TX mic values can be combined into 548 * one cache slot entry. 549 * 8*N + 800 31:0 RX Michael key 0 550 * 8*N + 804 15:0 TX Michael key 0 [31:16] 551 * 8*N + 808 31:0 RX Michael key 1 552 * 8*N + 80C 15:0 TX Michael key 0 [15:0] 553 * 8*N + 810 31:0 TX Michael key 1 554 * 8*N + 814 15:0 reserved 555 * 8*N + 818 31:0 reserved 556 * 8*N + 81C 14:0 reserved 557 * 15 key valid == 0 558 */ 559 /* RX mic */ 560 mic0 = LE_READ_4(k->kv_mic + 0); 561 mic2 = LE_READ_4(k->kv_mic + 4); 562 /* TX mic */ 563 mic1 = LE_READ_2(k->kv_txmic + 2) & 0xffff; 564 mic3 = LE_READ_2(k->kv_txmic + 0) & 0xffff; 565 mic4 = LE_READ_4(k->kv_txmic + 4); 566 if ((OS_REG_READ(ah, AR_KEYTABLE_KEY0(micentry)) == mic0) && 567 (OS_REG_READ(ah, AR_KEYTABLE_KEY1(micentry)) == mic1) && 568 (OS_REG_READ(ah, AR_KEYTABLE_KEY2(micentry)) == mic2) && 569 (OS_REG_READ(ah, AR_KEYTABLE_KEY3(micentry)) == mic3) && 570 (OS_REG_READ(ah, AR_KEYTABLE_KEY4(micentry)) == mic4) && 571 ((OS_REG_READ(ah, AR_KEYTABLE_TYPE(micentry)) & AR_KEY_TYPE) == (AR_KEYTABLE_TYPE_CLR & AR_KEY_TYPE))) { 572 return AH_TRUE; 573 } 574 575 } else { 576 return AH_TRUE; 577 } 578 } 579 } else { 580 if ((OS_REG_READ(ah, AR_KEYTABLE_KEY0(entry)) == key0) && 581 (OS_REG_READ(ah, AR_KEYTABLE_KEY1(entry)) == key1) && 582 (OS_REG_READ(ah, AR_KEYTABLE_KEY2(entry)) == key2) && 583 (OS_REG_READ(ah, AR_KEYTABLE_KEY3(entry)) == key3) && 584 (OS_REG_READ(ah, AR_KEYTABLE_KEY4(entry)) == key4) && 585 ((OS_REG_READ(ah, AR_KEYTABLE_TYPE(entry)) & AR_KEY_TYPE) == (keyType & AR_KEY_TYPE))) { 586 return AH_TRUE; 587 } 588 } 589 return AH_FALSE; 590} 591#endif |
|