📄 hostap.c
字号:
/* * Description: * flush station nodes table. * * Parameters: * In: * pDevice - * Out: * * Return Value: * */ static void hostap_flush_sta(PSDevice pDevice){ // reserved node index =0 for multicast node. BSSvClearNodeDBTable(pDevice, 1); pDevice->uAssocCount = 0; return;}/* * Description: * set each stations encryption key * * Parameters: * In: * pDevice - * param - * Out: * * Return Value: * */ static int hostap_set_encryption(PSDevice pDevice, struct viawget_hostapd_param *param, int param_len){ PSMgmtObject pMgmt = &(pDevice->sMgmtObj); DWORD dwKeyIndex = 0; BYTE abyKey[MAX_KEY_LEN]; BYTE abySeq[MAX_KEY_LEN]; NDIS_802_11_KEY_RSC KeyRSC; BYTE byKeyDecMode = KEY_CTL_WEP; int ret = 0; int iNodeIndex = -1; int ii; BOOL bKeyTableFull = FALSE; WORD wKeyCtl = 0; param->u.crypt.err = 0;/* if (param_len != (int) ((char *) param->u.crypt.key - (char *) param) + param->u.crypt.key_len) return -EINVAL;*/ if (param->u.crypt.alg > WPA_ALG_CCMP) return -EINVAL; if ((param->u.crypt.idx > 3) || (param->u.crypt.key_len > MAX_KEY_LEN)) { param->u.crypt.err = HOSTAP_CRYPT_ERR_KEY_SET_FAILED; DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " HOSTAP_CRYPT_ERR_KEY_SET_FAILED\n"); return -EINVAL; } if (param->sta_addr[0] == 0xff && param->sta_addr[1] == 0xff && param->sta_addr[2] == 0xff && param->sta_addr[3] == 0xff && param->sta_addr[4] == 0xff && param->sta_addr[5] == 0xff) { if (param->u.crypt.idx >= MAX_GROUP_KEY) return -EINVAL; iNodeIndex = 0; } else { if (BSSbIsSTAInNodeDB(pDevice, param->sta_addr, &iNodeIndex) == FALSE) { param->u.crypt.err = HOSTAP_CRYPT_ERR_UNKNOWN_ADDR; DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " HOSTAP_CRYPT_ERR_UNKNOWN_ADDR\n"); return -EINVAL; } } DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " hostap_set_encryption: sta_index %d \n", iNodeIndex); DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " hostap_set_encryption: alg %d \n", param->u.crypt.alg); if (param->u.crypt.alg == WPA_ALG_NONE) { if (pMgmt->sNodeDBTable[iNodeIndex].bOnFly == TRUE) { if (KeybRemoveKey( pDevice, &(pDevice->sKey), param->sta_addr, pMgmt->sNodeDBTable[iNodeIndex].dwKeyIndex ) == FALSE) { DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "KeybRemoveKey fail \n"); } pMgmt->sNodeDBTable[iNodeIndex].bOnFly = FALSE; } pMgmt->sNodeDBTable[iNodeIndex].byKeyIndex = 0; pMgmt->sNodeDBTable[iNodeIndex].dwKeyIndex = 0; pMgmt->sNodeDBTable[iNodeIndex].uWepKeyLength = 0; pMgmt->sNodeDBTable[iNodeIndex].KeyRSC = 0; pMgmt->sNodeDBTable[iNodeIndex].dwTSC47_16 = 0; pMgmt->sNodeDBTable[iNodeIndex].wTSC15_0 = 0; pMgmt->sNodeDBTable[iNodeIndex].byCipherSuite = 0; memset(&pMgmt->sNodeDBTable[iNodeIndex].abyWepKey[0], 0, MAX_KEY_LEN ); return ret; } memcpy(abyKey, param->u.crypt.key, param->u.crypt.key_len); // copy to node key tbl pMgmt->sNodeDBTable[iNodeIndex].byKeyIndex = param->u.crypt.idx; pMgmt->sNodeDBTable[iNodeIndex].uWepKeyLength = param->u.crypt.key_len; memcpy(&pMgmt->sNodeDBTable[iNodeIndex].abyWepKey[0], param->u.crypt.key, param->u.crypt.key_len ); dwKeyIndex = (DWORD)(param->u.crypt.idx); if (param->u.crypt.flags & HOSTAP_CRYPT_FLAG_SET_TX_KEY) { pDevice->byKeyIndex = (BYTE)dwKeyIndex; pDevice->bTransmitKey = TRUE; dwKeyIndex |= (1 << 31); } if (param->u.crypt.alg == WPA_ALG_WEP) { if ((pDevice->bEnable8021x == FALSE) || (iNodeIndex == 0)) { KeybSetDefaultKey( pDevice, &(pDevice->sKey), dwKeyIndex & ~(BIT30 | USE_KEYRSC), param->u.crypt.key_len, NULL, abyKey, KEY_CTL_WEP ); } else { // 8021x enable, individual key dwKeyIndex |= (1 << 30); // set pairwise key if (KeybSetKey(pDevice, &(pDevice->sKey), ¶m->sta_addr[0], dwKeyIndex & ~(USE_KEYRSC), param->u.crypt.key_len, (PQWORD) &(KeyRSC), (PBYTE)abyKey, KEY_CTL_WEP ) == TRUE) { pMgmt->sNodeDBTable[iNodeIndex].bOnFly = TRUE; } else { // Key Table Full pMgmt->sNodeDBTable[iNodeIndex].bOnFly = FALSE; bKeyTableFull = TRUE; } } pDevice->eEncryptionStatus = Ndis802_11Encryption1Enabled; pDevice->bEncryptionEnable = TRUE; pMgmt->byCSSPK = KEY_CTL_WEP; pMgmt->byCSSGK = KEY_CTL_WEP; pMgmt->sNodeDBTable[iNodeIndex].byCipherSuite = KEY_CTL_WEP; pMgmt->sNodeDBTable[iNodeIndex].dwKeyIndex = dwKeyIndex; return ret; } if (param->u.crypt.seq) { memcpy(&abySeq, param->u.crypt.seq, 8); for (ii = 0 ; ii < 8 ; ii++) { KeyRSC |= (abySeq[ii] << (ii * 8)); } dwKeyIndex |= 1 << 29; pMgmt->sNodeDBTable[iNodeIndex].KeyRSC = KeyRSC; } if (param->u.crypt.alg == WPA_ALG_TKIP) { if (param->u.crypt.key_len != MAX_KEY_LEN) return -EINVAL; pDevice->eEncryptionStatus = Ndis802_11Encryption2Enabled; byKeyDecMode = KEY_CTL_TKIP; pMgmt->byCSSPK = KEY_CTL_TKIP; pMgmt->byCSSGK = KEY_CTL_TKIP; } if (param->u.crypt.alg == WPA_ALG_CCMP) { if ((param->u.crypt.key_len != AES_KEY_LEN) || (pDevice->byLocalID <= REV_ID_VT3253_A1)) return -EINVAL; pDevice->eEncryptionStatus = Ndis802_11Encryption3Enabled; byKeyDecMode = KEY_CTL_CCMP; pMgmt->byCSSPK = KEY_CTL_CCMP; pMgmt->byCSSGK = KEY_CTL_CCMP; } if (iNodeIndex == 0) { KeybSetDefaultKey( pDevice, &(pDevice->sKey), dwKeyIndex, param->u.crypt.key_len, (PQWORD) &(KeyRSC), abyKey, byKeyDecMode ); pMgmt->sNodeDBTable[iNodeIndex].bOnFly = TRUE; } else { dwKeyIndex |= (1 << 30); // set pairwise key if (KeybSetKey(pDevice, &(pDevice->sKey), ¶m->sta_addr[0], dwKeyIndex, param->u.crypt.key_len, (PQWORD) &(KeyRSC), (PBYTE)abyKey, byKeyDecMode ) == TRUE) { pMgmt->sNodeDBTable[iNodeIndex].bOnFly = TRUE; } else { // Key Table Full pMgmt->sNodeDBTable[iNodeIndex].bOnFly = FALSE; bKeyTableFull = TRUE; DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " Key Table Full\n"); } } if (bKeyTableFull == TRUE) { wKeyCtl &= 0x7F00; // clear all key control filed wKeyCtl |= (byKeyDecMode << 4); wKeyCtl |= (byKeyDecMode); wKeyCtl |= 0x0044; // use group key for all address wKeyCtl |= 0x4000; // disable KeyTable[MAX_KEY_TABLE-1] on-fly to genernate rx int // Todo.. xxxxxx //MACvSetDefaultKeyCtl(pDevice->PortOffset, wKeyCtl, MAX_KEY_TABLE-1, pDevice->byLocalID); } DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " Set key sta_index= %d \n", iNodeIndex); DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " tx_index=%d len=%d \n", param->u.crypt.idx, param->u.crypt.key_len ); DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO " key=%x-%x-%x-%x-%x-xxxxx \n", pMgmt->sNodeDBTable[iNodeIndex].abyWepKey[0], pMgmt->sNodeDBTable[iNodeIndex].abyWepKey[1], pMgmt->sNodeDBTable[iNodeIndex].abyWepKey[2], pMgmt->sNodeDBTable[iNodeIndex].abyWepKey[3], pMgmt->sNodeDBTable[iNodeIndex].abyWepKey[4] ); // set wep key pDevice->bEncryptionEnable = TRUE; pMgmt->sNodeDBTable[iNodeIndex].byCipherSuite = byKeyDecMode; pMgmt->sNodeDBTable[iNodeIndex].dwKeyIndex = dwKeyIndex; pMgmt->sNodeDBTable[iNodeIndex].dwTSC47_16 = 0; pMgmt->sNodeDBTable[iNodeIndex].wTSC15_0 = 0; return ret;}/* * Description: * get each stations encryption key * * Parameters: * In: * pDevice - * param - * Out: * * Return Value: * */ static int hostap_get_encryption(PSDevice pDevice, struct viawget_hostapd_param *param, int param_len){ PSMgmtObject pMgmt = &(pDevice->sMgmtObj); int ret = 0; int ii; int iNodeIndex =0; param->u.crypt.err = 0; if (param->sta_addr[0] == 0xff && param->sta_addr[1] == 0xff && param->sta_addr[2] == 0xff && param->sta_addr[3] == 0xff && param->sta_addr[4] == 0xff && param->sta_addr[5] == 0xff) { iNodeIndex = 0; } else { if (BSSbIsSTAInNodeDB(pDevice, param->sta_addr, &iNodeIndex) == FALSE) { param->u.crypt.err = HOSTAP_CRYPT_ERR_UNKNOWN_ADDR; DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "hostap_get_encryption: HOSTAP_CRYPT_ERR_UNKNOWN_ADDR\n"); return -EINVAL; } } DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "hostap_get_encryption: %d\n", iNodeIndex); memset(param->u.crypt.seq, 0, 8); for (ii = 0 ; ii < 8 ; ii++) { param->u.crypt.seq[ii] = (BYTE)pMgmt->sNodeDBTable[iNodeIndex].KeyRSC >> (ii * 8); } return ret;}/* * Description: * hostap_ioctl main function supported for hostap deamon. * * Parameters: * In: * pDevice - * iw_point - * Out: * * Return Value: * */ int hostap_ioctl(PSDevice pDevice, struct iw_point *p){ struct viawget_hostapd_param *param; int ret = 0; int ap_ioctl = 0; if (p->length < sizeof(struct viawget_hostapd_param) || p->length > VIAWGET_HOSTAPD_MAX_BUF_SIZE || !p->pointer) return -EINVAL; param = (struct viawget_hostapd_param *) kmalloc((int)p->length, (int)GFP_KERNEL); if (param == NULL) return -ENOMEM; if (copy_from_user(param, p->pointer, p->length)) { ret = -EFAULT; goto out; } switch (param->cmd) { case VIAWGET_HOSTAPD_SET_ENCRYPTION: DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "VIAWGET_HOSTAPD_SET_ENCRYPTION \n"); spin_lock_irq(&pDevice->lock); ret = hostap_set_encryption(pDevice, param, p->length); spin_unlock_irq(&pDevice->lock); break; case VIAWGET_HOSTAPD_GET_ENCRYPTION: DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "VIAWGET_HOSTAPD_GET_ENCRYPTION \n"); spin_lock_irq(&pDevice->lock); ret = hostap_get_encryption(pDevice, param, p->length); spin_unlock_irq(&pDevice->lock); break; case VIAWGET_HOSTAPD_SET_ASSOC_AP_ADDR: DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "VIAWGET_HOSTAPD_SET_ASSOC_AP_ADDR \n"); return -EOPNOTSUPP; break; case VIAWGET_HOSTAPD_FLUSH: DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "VIAWGET_HOSTAPD_FLUSH \n"); spin_lock_irq(&pDevice->lock); hostap_flush_sta(pDevice); spin_unlock_irq(&pDevice->lock); break; case VIAWGET_HOSTAPD_ADD_STA: DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "VIAWGET_HOSTAPD_ADD_STA \n"); spin_lock_irq(&pDevice->lock); ret = hostap_add_sta(pDevice, param); spin_unlock_irq(&pDevice->lock); break; case VIAWGET_HOSTAPD_REMOVE_STA: DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "VIAWGET_HOSTAPD_REMOVE_STA \n"); spin_lock_irq(&pDevice->lock); ret = hostap_remove_sta(pDevice, param); spin_unlock_irq(&pDevice->lock); break; case VIAWGET_HOSTAPD_GET_INFO_STA: DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "VIAWGET_HOSTAPD_GET_INFO_STA \n"); ret = hostap_get_info_sta(pDevice, param); ap_ioctl = 1; break; /* case VIAWGET_HOSTAPD_RESET_TXEXC_STA: DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "VIAWGET_HOSTAPD_RESET_TXEXC_STA \n"); ret = hostap_reset_txexc_sta(pDevice, param); break; */ case VIAWGET_HOSTAPD_SET_FLAGS_STA: DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "VIAWGET_HOSTAPD_SET_FLAGS_STA \n"); ret = hostap_set_flags_sta(pDevice, param); break; case VIAWGET_HOSTAPD_MLME: DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "VIAWGET_HOSTAPD_MLME \n"); return -EOPNOTSUPP; case VIAWGET_HOSTAPD_SET_GENERIC_ELEMENT: DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "VIAWGET_HOSTAPD_SET_GENERIC_ELEMENT \n"); ret = hostap_set_generic_element(pDevice, param); break; case VIAWGET_HOSTAPD_SCAN_REQ: DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "VIAWGET_HOSTAPD_SCAN_REQ \n"); return -EOPNOTSUPP; case VIAWGET_HOSTAPD_STA_CLEAR_STATS: DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "VIAWGET_HOSTAPD_STA_CLEAR_STATS \n"); return -EOPNOTSUPP; default: DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "hostap_ioctl: unknown cmd=%d\n", (int)param->cmd); return -EOPNOTSUPP; break; } if ((ret == 0) && ap_ioctl) { if (copy_to_user(p->pointer, param, p->length)) { ret = -EFAULT; goto out; } } out: if (param != NULL) kfree(param); return ret;}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -