void _ips_enter(_adapter * padapter) { struct pwrctrl_priv *pwrpriv = &padapter->pwrctrlpriv; if (padapter->hw_init_completed == _FALSE) { DBG_871X("%s: hw_init_completed: %d\n", __func__, padapter->hw_init_completed); return; } pwrpriv->bips_processing = _TRUE; // syn ips_mode with request pwrpriv->ips_mode = pwrpriv->ips_mode_req; pwrpriv->ips_enter_cnts++; DBG_871X("==>ips_enter cnts:%d\n",pwrpriv->ips_enter_cnts); #ifdef CONFIG_BT_COEXIST BTDM_TurnOffBtCoexistBeforeEnterIPS(padapter); #endif if(rf_off == pwrpriv->change_rfpwrstate ) { pwrpriv->bpower_saving = _TRUE; DBG_871X_LEVEL(_drv_always_, "nolinked power save enter\n"); if(pwrpriv->ips_mode == IPS_LEVEL_2) pwrpriv->bkeepfwalive = _TRUE; rtw_ips_pwr_down(padapter); pwrpriv->rf_pwrstate = rf_off; } pwrpriv->bips_processing = _FALSE; }
int _ips_leave(_adapter * padapter) { struct pwrctrl_priv *pwrpriv = adapter_to_pwrctl(padapter); int result = _SUCCESS; if((pwrpriv->rf_pwrstate == rf_off) &&(!pwrpriv->bips_processing)) { pwrpriv->bips_processing = _TRUE; pwrpriv->change_rfpwrstate = rf_on; pwrpriv->ips_leave_cnts++; DBG_871X("==>ips_leave cnts:%d\n",pwrpriv->ips_leave_cnts); if ((result = rtw_ips_pwr_up(padapter)) == _SUCCESS) { pwrpriv->rf_pwrstate = rf_on; } DBG_871X_LEVEL(_drv_always_, "nolinked power save leave\n"); DBG_871X("==> ips_leave.....LED(0x%08x)...\n",rtw_read32(padapter,0x4c)); pwrpriv->bips_processing = _FALSE; pwrpriv->bkeepfwalive = _FALSE; pwrpriv->bpower_saving = _FALSE; } return result; }
void ips_enter(_adapter * padapter) { struct pwrctrl_priv *pwrpriv = &padapter->pwrctrlpriv; struct mlme_priv *pmlmepriv = &(padapter->mlmepriv); struct xmit_priv *pxmit_priv = &padapter->xmitpriv; #if (MP_DRIVER == 1) if (padapter->registrypriv.mp_mode == 1) return; #endif if (pxmit_priv->free_xmitbuf_cnt != NR_XMITBUFF || pxmit_priv->free_xmit_extbuf_cnt != NR_XMIT_EXTBUFF) { DBG_871X_LEVEL(_drv_always_, "There are some pkts to transmit\n"); DBG_871X_LEVEL(_drv_info_, "free_xmitbuf_cnt: %d, free_xmit_extbuf_cnt: %d\n", pxmit_priv->free_xmitbuf_cnt, pxmit_priv->free_xmit_extbuf_cnt); return; } _enter_pwrlock(&pwrpriv->lock); pwrpriv->bips_processing = _TRUE; // syn ips_mode with request pwrpriv->ips_mode = pwrpriv->ips_mode_req; pwrpriv->ips_enter_cnts++; DBG_871X("==>ips_enter cnts:%d\n",pwrpriv->ips_enter_cnts); #ifdef CONFIG_BT_COEXIST BTDM_TurnOffBtCoexistBeforeEnterIPS(padapter); #endif if(rf_off == pwrpriv->change_rfpwrstate ) { pwrpriv->bpower_saving = _TRUE; DBG_871X_LEVEL(_drv_always_, "nolinked power save enter\n"); if(pwrpriv->ips_mode == IPS_LEVEL_2) pwrpriv->bkeepfwalive = _TRUE; rtw_ips_pwr_down(padapter); pwrpriv->rf_pwrstate = rf_off; } pwrpriv->bips_processing = _FALSE; _exit_pwrlock(&pwrpriv->lock); }
/* * Description * Transmit xmitframe from queue * * Return * _SUCCESS ok * _FAIL something error */ s32 rtl8723bs_xmit_handler(PADAPTER padapter) { struct xmit_priv *pxmitpriv; s32 ret; _irqL irql; pxmitpriv = &padapter->xmitpriv; wait: ret = _rtw_down_sema(&pxmitpriv->SdioXmitSema); if (_FAIL == ret) { DBG_871X_LEVEL(_drv_emerg_, "%s: down sema fail!\n", __FUNCTION__); return _FAIL; } next: if ((padapter->bDriverStopped == _TRUE) || (padapter->bSurpriseRemoved == _TRUE)) { RT_TRACE(_module_hal_xmit_c_, _drv_notice_, ("%s: bDriverStopped(%d) bSurpriseRemoved(%d)\n", __FUNCTION__, padapter->bDriverStopped, padapter->bSurpriseRemoved)); return _FAIL; } _enter_critical_bh(&pxmitpriv->lock, &irql); ret = rtw_txframes_pending(padapter); _exit_critical_bh(&pxmitpriv->lock, &irql); if (ret == 0) { if(!padapter->registrypriv.wifi_spec) rtw_yield_os(); return _SUCCESS; } // dequeue frame and write to hardware ret = xmit_xmitframes(padapter, pxmitpriv); if (ret == -2) { //here sleep 1ms will cause big TP loss of TX //from 50+ to 40+ if(padapter->registrypriv.wifi_spec) rtw_msleep_os(1); else rtw_yield_os(); goto next; } _enter_critical_bh(&pxmitpriv->lock, &irql); ret = rtw_txframes_pending(padapter); _exit_critical_bh(&pxmitpriv->lock, &irql); if (ret == 1) { //rtw_msleep_os(1); goto next; } return _SUCCESS; }
/* * Description * Transmit xmitbuf to hardware tx fifo * * Return * _SUCCESS ok * _FAIL something error */ s32 rtl8723bs_xmit_buf_handler(PADAPTER padapter) { PHAL_DATA_TYPE phal; struct mlme_priv *pmlmepriv; struct xmit_priv *pxmitpriv; struct dvobj_priv *pdvobjpriv; struct xmit_buf *pxmitbuf; struct xmit_frame *pframe; u32 deviceId; u32 requiredPage; u8 PageIdx, queue_empty; _irqL irql; u32 n; s32 ret; phal = GET_HAL_DATA(padapter); pmlmepriv = &padapter->mlmepriv; pxmitpriv = &padapter->xmitpriv; pdvobjpriv = adapter_to_dvobj(padapter); ret = _rtw_down_sema(&pxmitpriv->xmit_sema); if (_FAIL == ret) { DBG_871X_LEVEL(_drv_emerg_, "%s: down SdioXmitBufSema fail!\n", __FUNCTION__); return _FAIL; } ret = (padapter->bDriverStopped == _TRUE) || (padapter->bSurpriseRemoved == _TRUE); if (ret) { RT_TRACE(_module_hal_xmit_c_, _drv_err_, ("%s: bDriverStopped(%d) bSurpriseRemoved(%d)!\n", __FUNCTION__, padapter->bDriverStopped, padapter->bSurpriseRemoved)); return _FAIL; } #ifdef CONFIG_LPS_LCLK ret = rtw_register_tx_alive(padapter); if (ret != _SUCCESS) { return _SUCCESS; } #endif do { queue_empty = rtl8723_dequeue_writeport(padapter); // dump secondary adapter xmitbuf #ifdef CONFIG_CONCURRENT_MODE if(rtw_buddy_adapter_up(padapter)) queue_empty &= rtl8723_dequeue_writeport(padapter->pbuddy_adapter); #endif } while ( !queue_empty); #ifdef CONFIG_LPS_LCLK rtw_unregister_tx_alive(padapter); #endif return _SUCCESS; }
static void __exit rtw_drv_halt(void) { DBG_871X_LEVEL(_drv_always_, "module exit start\n"); drvpriv.drv_registered = _FALSE; spi_unregister_driver(&rtw_spi_drv); rtw_wifi_gpio_wlan_ctrl(WLAN_PWDN_OFF); rtw_wifi_gpio_deinit(); rtw_suspend_lock_uninit(); rtw_drv_proc_deinit(); rtw_ndev_notifier_unregister(); DBG_871X_LEVEL(_drv_always_, "module exit success\n"); rtw_mstat_dump(RTW_DBGDUMP); }
static int rtw_cfgvendor_get_feature_set_matrix(struct wiphy *wiphy, struct wireless_dev *wdev, const void *data, int len) { int err = 0; struct sk_buff *skb; int *reply; int num, mem_needed, i; reply = rtw_dev_get_feature_set_matrix(wdev_to_ndev(wdev), &num); if (!reply) { DBG_871X_LEVEL(_drv_err_, FUNC_NDEV_FMT" Could not get feature list matrix\n" , FUNC_NDEV_ARG(wdev_to_ndev(wdev))); err = -EINVAL; return err; } mem_needed = VENDOR_REPLY_OVERHEAD + (ATTRIBUTE_U32_LEN * num) + ATTRIBUTE_U32_LEN; /* Alloc the SKB for vendor_event */ skb = rtw_cfg80211_vendor_cmd_alloc_reply_skb(wiphy, mem_needed); if (unlikely(!skb)) { DBG_871X_LEVEL(_drv_err_, FUNC_NDEV_FMT" skb alloc failed", FUNC_NDEV_ARG(wdev_to_ndev(wdev))); err = -ENOMEM; goto exit; } nla_put_u32(skb, ANDR_WIFI_ATTRIBUTE_NUM_FEATURE_SET, num); for (i = 0; i < num; i++) { nla_put_u32(skb, ANDR_WIFI_ATTRIBUTE_FEATURE_SET, reply[i]); } err = rtw_cfg80211_vendor_cmd_reply(skb); if (unlikely(err)) DBG_871X_LEVEL(_drv_err_, FUNC_NDEV_FMT" Vendor Command reply failed ret:%d \n" , FUNC_NDEV_ARG(wdev_to_ndev(wdev)), err); exit: rtw_mfree((u8*)reply, sizeof(int)*num); return err; }
u8 GetHalDefVar( struct adapter *adapter, enum HAL_DEF_VARIABLE variable, void *value ) { struct hal_com_data *hal_data = GET_HAL_DATA(adapter); DM_ODM_T *odm = &(hal_data->odmpriv); u8 bResult = _SUCCESS; switch (variable) { case HAL_DEF_UNDERCORATEDSMOOTHEDPWDB: { struct mlme_priv *pmlmepriv; struct sta_priv *pstapriv; struct sta_info *psta; pmlmepriv = &adapter->mlmepriv; pstapriv = &adapter->stapriv; psta = rtw_get_stainfo(pstapriv, pmlmepriv->cur_network.network.MacAddress); if (psta) *((int *)value) = psta->rssi_stat.UndecoratedSmoothedPWDB; } break; case HW_DEF_ODM_DBG_FLAG: *((u64 *)value) = odm->DebugComponents; break; case HW_DEF_ODM_DBG_LEVEL: *((u32 *)value) = odm->DebugLevel; break; case HAL_DEF_DBG_DM_FUNC: *((u32 *)value) = hal_data->odmpriv.SupportAbility; break; case HAL_DEF_DBG_DUMP_RXPKT: *((u8 *)value) = hal_data->bDumpRxPkt; break; case HAL_DEF_DBG_DUMP_TXPKT: *((u8 *)value) = hal_data->bDumpTxPkt; break; case HAL_DEF_ANT_DETECT: *((u8 *)value) = hal_data->AntDetection; break; case HAL_DEF_MACID_SLEEP: *(u8 *)value = false; break; case HAL_DEF_TX_PAGE_SIZE: *((u32 *)value) = PAGE_SIZE_128; break; default: DBG_871X_LEVEL(_drv_always_, "%s: [WARNING] HAL_DEF_VARIABLE(%d) not defined!\n", __func__, variable); bResult = _FAIL; break; } return bResult; }
/* * rtw_set_band - * @adapter: pointer to _adapter structure * @band: band to set * * Return _SUCCESS or _FAIL */ int rtw_set_band(_adapter *adapter, enum _BAND band) { if (rtw_band_valid(band)) { DBG_871X(FUNC_ADPT_FMT" band:%d\n", FUNC_ADPT_ARG(adapter), band); adapter->setband = band; return _SUCCESS; } DBG_871X_LEVEL(_drv_always_, FUNC_ADPT_FMT" band:%d fail\n", FUNC_ADPT_ARG(adapter), band); return _FAIL; }
void rtw_hal_set_chnl_bw(_adapter *padapter, u8 channel, CHANNEL_WIDTH Bandwidth, u8 Offset40, u8 Offset80) { PHAL_DATA_TYPE pHalData = GET_HAL_DATA(padapter); PDM_ODM_T pDM_Odm = &(pHalData->odmpriv); ODM_AcquireSpinLock( pDM_Odm, RT_IQK_SPINLOCK); if(pDM_Odm->RFCalibrateInfo.bIQKInProgress == _TRUE) DBG_871X_LEVEL(_drv_err_, "%s, %d, IQK may race condition\n", __func__,__LINE__); ODM_ReleaseSpinLock( pDM_Odm, RT_IQK_SPINLOCK); padapter->HalFunc.set_chnl_bw_handler(padapter, channel, Bandwidth, Offset40, Offset80); }
s32 rtw_hal_fill_h2c_cmd(PADAPTER padapter, u8 ElementID, u32 CmdLen, u8 *pCmdBuffer) { _adapter *pri_adapter = GET_PRIMARY_ADAPTER(padapter); if (pri_adapter->bFWReady == _TRUE) return padapter->HalFunc.fill_h2c_cmd(padapter, ElementID, CmdLen, pCmdBuffer); else if (padapter->registrypriv.mp_mode == 0) DBG_871X_LEVEL(_drv_always_, FUNC_ADPT_FMT" FW doesn't exit when no MP mode, by pass H2C id:0x%02x\n" , FUNC_ADPT_ARG(padapter), ElementID); return _FAIL; }
u8 SetHalDefVar(_adapter *adapter, HAL_DEF_VARIABLE variable, void *val) { HAL_DATA_TYPE *hal_data = GET_HAL_DATA(adapter); struct dm_priv *dm = &(hal_data->dmpriv); u8 bResult = _SUCCESS; switch(variable) { case HAL_DEF_DBG_DM_FUNC: { u8 dm_func = *((u8*)val); if (dm_func == 0){ //disable all dynamic func dm->DMFlag = DYNAMIC_FUNC_DISABLE; DBG_8192C("==> Disable all dynamic function...\n"); } else if (dm_func == 1){//disable DIG dm->DMFlag &= (~DYNAMIC_FUNC_DIG); DBG_8192C("==> Disable DIG...\n"); } else if (dm_func == 2){//disable High power dm->DMFlag &= (~DYNAMIC_FUNC_HP); } else if (dm_func == 3){//disable tx power tracking dm->DMFlag &= (~DYNAMIC_FUNC_SS); DBG_8192C("==> Disable tx power tracking...\n"); } else if (dm_func == 4){//disable BT coexistence dm->DMFlag &= (~DYNAMIC_FUNC_BT); } else if (dm_func == 5){//disable antenna diversity dm->DMFlag &= (~DYNAMIC_FUNC_ANT_DIV); } else if (dm_func == 6){//turn on all dynamic func if (!(dm->DMFlag & DYNAMIC_FUNC_DIG)) { DIG_T *pDigTable = &dm->DM_DigTable; pDigTable->PreIGValue = rtw_read8(adapter, 0xc50); } dm->DMFlag |= (DYNAMIC_FUNC_DIG|DYNAMIC_FUNC_HP|DYNAMIC_FUNC_SS| DYNAMIC_FUNC_BT|DYNAMIC_FUNC_ANT_DIV) ; DBG_8192C("==> Turn on all dynamic function...\n"); } } break; default: if(0) DBG_871X_LEVEL(_drv_always_, "%s: [WARNING] HAL_DEF_VARIABLE(%d) not defined!\n", __FUNCTION__, variable); bResult = _FAIL; break; } return bResult; }
/* * Description * Transmit xmitframe from queue * * Return * _SUCCESS ok * _FAIL something error */ static s32 rtl8723bs_xmit_handler(PADAPTER padapter) { struct xmit_priv *pxmitpriv; s32 ret; _irqL irql; pxmitpriv = &padapter->xmitpriv; if (down_interruptible(&pxmitpriv->SdioXmitSema)) { DBG_871X_LEVEL(_drv_emerg_, "%s: down sema fail!\n", __FUNCTION__); return _FAIL; } next: if ((padapter->bDriverStopped == true) || (padapter->bSurpriseRemoved == true)) { RT_TRACE(_module_hal_xmit_c_, _drv_notice_, ("%s: bDriverStopped(%d) bSurpriseRemoved(%d)\n", __FUNCTION__, padapter->bDriverStopped, padapter->bSurpriseRemoved)); return _FAIL; } spin_lock_bh(&pxmitpriv->lock); ret = rtw_txframes_pending(padapter); spin_unlock_bh(&pxmitpriv->lock); if (ret == 0) { return _SUCCESS; } // dequeue frame and write to hardware ret = xmit_xmitframes(padapter, pxmitpriv); if (ret == -2) { //here sleep 1ms will cause big TP loss of TX //from 50+ to 40+ if(padapter->registrypriv.wifi_spec) msleep(1); else yield(); goto next; } spin_lock_bh(&pxmitpriv->lock); ret = rtw_txframes_pending(padapter); spin_unlock_bh(&pxmitpriv->lock); if (ret == 1) { goto next; } return _SUCCESS; }
int *rtw_dev_get_feature_set_matrix(struct net_device *dev, int *num) { int feature_set_full, mem_needed; int *ret; *num = 0; mem_needed = sizeof(int) * MAX_FEATURE_SET_CONCURRRENT_GROUPS; ret = (int *)rtw_malloc(mem_needed); if (!ret) { DBG_871X_LEVEL(_drv_err_, FUNC_NDEV_FMT" failed to allocate %d bytes\n" , FUNC_NDEV_ARG(dev), mem_needed); return ret; } feature_set_full = rtw_dev_get_feature_set(dev); ret[0] = (feature_set_full & WIFI_FEATURE_INFRA) | (feature_set_full & WIFI_FEATURE_INFRA_5G) | (feature_set_full & WIFI_FEATURE_NAN) | (feature_set_full & WIFI_FEATURE_D2D_RTT) | (feature_set_full & WIFI_FEATURE_D2AP_RTT) | (feature_set_full & WIFI_FEATURE_PNO) | (feature_set_full & WIFI_FEATURE_BATCH_SCAN) | (feature_set_full & WIFI_FEATURE_GSCAN) | (feature_set_full & WIFI_FEATURE_HOTSPOT) | (feature_set_full & WIFI_FEATURE_ADDITIONAL_STA) | (feature_set_full & WIFI_FEATURE_EPR); ret[1] = (feature_set_full & WIFI_FEATURE_INFRA) | (feature_set_full & WIFI_FEATURE_INFRA_5G) | /* Not yet verified NAN with P2P */ /* (feature_set_full & WIFI_FEATURE_NAN) | */ (feature_set_full & WIFI_FEATURE_P2P) | (feature_set_full & WIFI_FEATURE_D2AP_RTT) | (feature_set_full & WIFI_FEATURE_D2D_RTT) | (feature_set_full & WIFI_FEATURE_EPR); ret[2] = (feature_set_full & WIFI_FEATURE_INFRA) | (feature_set_full & WIFI_FEATURE_INFRA_5G) | (feature_set_full & WIFI_FEATURE_NAN) | (feature_set_full & WIFI_FEATURE_D2D_RTT) | (feature_set_full & WIFI_FEATURE_D2AP_RTT) | (feature_set_full & WIFI_FEATURE_TDLS) | (feature_set_full & WIFI_FEATURE_TDLS_OFFCHANNEL) | (feature_set_full & WIFI_FEATURE_EPR); *num = MAX_FEATURE_SET_CONCURRRENT_GROUPS; return ret; }
void GetHwReg(_adapter *adapter, HW_VARIABLES variable, u8 *val) { HAL_DATA_TYPE *hal_data = GET_HAL_DATA(adapter); struct dm_priv *dm = &(hal_data->dmpriv); switch (variable) { case HW_VAR_DM_FLAG: *((u8*)val) = dm->DMFlag; break; default: if(0) DBG_871X_LEVEL(_drv_always_, "%s: [WARNING] HW_VARIABLES(%d) not defined!\n", __FUNCTION__, variable); break; } }
/* * Description *Transmit xmitbuf to hardware tx fifo * * Return *_SUCCESS ok *_FAIL something error */ s32 rtl8723bs_xmit_buf_handler(struct adapter *padapter) { struct xmit_priv *pxmitpriv; u8 queue_empty, queue_pending; s32 ret; pxmitpriv = &padapter->xmitpriv; if (down_interruptible(&pxmitpriv->xmit_sema)) { DBG_871X_LEVEL(_drv_emerg_, "%s: down SdioXmitBufSema fail!\n", __func__); return _FAIL; } ret = (padapter->bDriverStopped == true) || (padapter->bSurpriseRemoved == true); if (ret) { RT_TRACE( _module_hal_xmit_c_, _drv_err_, ( "%s: bDriverStopped(%d) bSurpriseRemoved(%d)!\n", __func__, padapter->bDriverStopped, padapter->bSurpriseRemoved ) ); return _FAIL; } queue_pending = check_pending_xmitbuf(pxmitpriv); if (queue_pending == false) return _SUCCESS; ret = rtw_register_tx_alive(padapter); if (ret != _SUCCESS) { return _SUCCESS; } do { queue_empty = rtl8723_dequeue_writeport(padapter); /* dump secondary adapter xmitbuf */ } while (!queue_empty); rtw_unregister_tx_alive(padapter); return _SUCCESS; }
int ips_leave(_adapter * padapter) { struct pwrctrl_priv *pwrpriv = &padapter->pwrctrlpriv; struct security_priv* psecuritypriv=&(padapter->securitypriv); struct mlme_priv *pmlmepriv = &(padapter->mlmepriv); int result = _SUCCESS; sint keyid; _enter_pwrlock(&pwrpriv->lock); if((pwrpriv->rf_pwrstate == rf_off) &&(!pwrpriv->bips_processing)) { pwrpriv->bips_processing = _TRUE; pwrpriv->change_rfpwrstate = rf_on; pwrpriv->ips_leave_cnts++; DBG_871X("==>ips_leave cnts:%d\n",pwrpriv->ips_leave_cnts); if ((result = rtw_ips_pwr_up(padapter)) == _SUCCESS) { pwrpriv->rf_pwrstate = rf_on; } DBG_871X_LEVEL(_drv_always_, "nolinked power save leave\n"); if((_WEP40_ == psecuritypriv->dot11PrivacyAlgrthm) ||(_WEP104_ == psecuritypriv->dot11PrivacyAlgrthm)) { DBG_871X("==>%s,channel(%d),processing(%x)\n",__FUNCTION__,padapter->mlmeextpriv.cur_channel,pwrpriv->bips_processing); set_channel_bwmode(padapter, padapter->mlmeextpriv.cur_channel, HAL_PRIME_CHNL_OFFSET_DONT_CARE, HT_CHANNEL_WIDTH_20); for(keyid=0;keyid<4;keyid++){ if(pmlmepriv->key_mask & BIT(keyid)){ if(keyid == psecuritypriv->dot11PrivacyKeyIndex) result=rtw_set_key(padapter,psecuritypriv, keyid, 1); else result=rtw_set_key(padapter,psecuritypriv, keyid, 0); } } } DBG_871X("==> ips_leave.....LED(0x%08x)...\n",rtw_read32(padapter,0x4c)); pwrpriv->bips_processing = _FALSE; pwrpriv->bkeepfwalive = _FALSE; pwrpriv->bpower_saving = _FALSE; } _exit_pwrlock(&pwrpriv->lock); return result; }
static int rtw_cfgvendor_get_feature_set(struct wiphy *wiphy, struct wireless_dev *wdev, const void *data, int len) { int err = 0; int reply; reply = rtw_dev_get_feature_set(wdev_to_ndev(wdev)); err = rtw_cfgvendor_send_cmd_reply(wiphy, wdev_to_ndev(wdev), &reply, sizeof(int)); if (unlikely(err)) DBG_871X_LEVEL(_drv_err_, FUNC_NDEV_FMT" Vendor Command reply failed ret:%d \n" , FUNC_NDEV_ARG(wdev_to_ndev(wdev)), err); return err; }
u8 _rtw_sd_f0_read8(_adapter *adapter, u32 addr) { u8 r_val = 0x00; struct io_priv *pio_priv = &adapter->iopriv; struct intf_hdl *pintfhdl = &(pio_priv->intf); u8 (*_sd_f0_read8)(struct intf_hdl *pintfhdl, u32 addr); _sd_f0_read8 = pintfhdl->io_ops._sd_f0_read8; if (_sd_f0_read8) r_val = _sd_f0_read8(pintfhdl, addr); else DBG_871X_LEVEL(_drv_warning_, FUNC_ADPT_FMT" _sd_f0_read8 callback is NULL\n", FUNC_ADPT_ARG(adapter)); return r_val; }
static int rtw_cfgvendor_send_cmd_reply(struct wiphy *wiphy, struct net_device *dev, const void *data, int len) { struct sk_buff *skb; /* Alloc the SKB for vendor_event */ skb = rtw_cfg80211_vendor_cmd_alloc_reply_skb(wiphy, len); if (unlikely(!skb)) { DBG_871X_LEVEL(_drv_err_, FUNC_NDEV_FMT" skb alloc failed", FUNC_NDEV_ARG(dev)); return -ENOMEM; } /* Push the data to the skb */ nla_put_nohdr(skb, len, data); return rtw_cfg80211_vendor_cmd_reply(skb); }
u8 GetHalDefVar(_adapter *adapter, HAL_DEF_VARIABLE variable, void *val) { HAL_DATA_TYPE *hal_data = GET_HAL_DATA(adapter); struct dm_priv *dm = &(hal_data->dmpriv); u8 bResult = _SUCCESS; switch(variable) { case HAL_DEF_DBG_DM_FUNC: *((u8*)val) = dm->DMFlag; break; default: if(0) DBG_871X_LEVEL(_drv_always_, "%s: [WARNING] HAL_DEF_VARIABLE(%d) not defined!\n", __FUNCTION__, variable); bResult = _FAIL; break; } return bResult; }
s32 rtw_hal_macid_wakeup(PADAPTER padapter, u8 macid) { struct dvobj_priv *dvobj = adapter_to_dvobj(padapter); struct macid_ctl_t *macid_ctl = dvobj_to_macidctl(dvobj); u8 support; support = _FALSE; rtw_hal_get_def_var(padapter, HAL_DEF_MACID_SLEEP, &support); if (_FALSE == support) return _FAIL; if (macid >= macid_ctl->num) { DBG_871X_LEVEL(_drv_err_, FUNC_ADPT_FMT": Invalid macid(%u)\n", FUNC_ADPT_ARG(padapter), macid); return _FAIL; } rtw_hal_set_hwreg(padapter, HW_VAR_MACID_WAKEUP, &macid); return _SUCCESS; }
/* * This API is to be used for asynchronous vendor events. This * shouldn't be used in response to a vendor command from its * do_it handler context (instead rtw_cfgvendor_send_cmd_reply should * be used). */ int rtw_cfgvendor_send_async_event(struct wiphy *wiphy, struct net_device *dev, int event_id, const void *data, int len) { u16 kflags; struct sk_buff *skb; kflags = in_atomic() ? GFP_ATOMIC : GFP_KERNEL; /* Alloc the SKB for vendor_event */ skb = rtw_cfg80211_vendor_event_alloc(wiphy, len, event_id, kflags); if (!skb) { DBG_871X_LEVEL(_drv_err_, FUNC_NDEV_FMT" skb alloc failed", FUNC_NDEV_ARG(dev)); return -ENOMEM; } /* Push the data to the skb */ nla_put_nohdr(skb, len, data); rtw_cfg80211_vendor_event(skb, kflags); return 0; }
u8 rtw_set_802_11_connect(struct adapter *padapter, u8 *bssid, struct ndis_802_11_ssid *ssid) { u8 status = _SUCCESS; bool bssid_valid = true; bool ssid_valid = true; struct mlme_priv *pmlmepriv = &padapter->mlmepriv; if (!ssid || rtw_validate_ssid(ssid) == false) ssid_valid = false; if (!bssid || rtw_validate_bssid(bssid) == false) bssid_valid = false; if (ssid_valid == false && bssid_valid == false) { DBG_871X(FUNC_ADPT_FMT" ssid:%p, ssid_valid:%d, bssid:%p, bssid_valid:%d\n", FUNC_ADPT_ARG(padapter), ssid, ssid_valid, bssid, bssid_valid); status = _FAIL; goto exit; } if (padapter->hw_init_completed == false) { RT_TRACE(_module_rtl871x_ioctl_set_c_, _drv_err_, ("set_ssid: hw_init_completed ==false =>exit!!!\n")); status = _FAIL; goto exit; } spin_lock_bh(&pmlmepriv->lock); DBG_871X_LEVEL(_drv_always_, FUNC_ADPT_FMT" fw_state = 0x%08x\n", FUNC_ADPT_ARG(padapter), get_fwstate(pmlmepriv)); if (check_fwstate(pmlmepriv, _FW_UNDER_SURVEY) == true) { goto handle_tkip_countermeasure; } else if (check_fwstate(pmlmepriv, _FW_UNDER_LINKING) == true) { goto release_mlme_lock; } handle_tkip_countermeasure: if (rtw_handle_tkip_countermeasure(padapter, __func__) == _FAIL) { status = _FAIL; goto release_mlme_lock; } if (ssid && ssid_valid) memcpy(&pmlmepriv->assoc_ssid, ssid, sizeof(struct ndis_802_11_ssid)); else memset(&pmlmepriv->assoc_ssid, 0, sizeof(struct ndis_802_11_ssid)); if (bssid && bssid_valid) { memcpy(&pmlmepriv->assoc_bssid, bssid, ETH_ALEN); pmlmepriv->assoc_by_bssid = true; } else { pmlmepriv->assoc_by_bssid = false; } if (check_fwstate(pmlmepriv, _FW_UNDER_SURVEY) == true) { pmlmepriv->to_join = true; } else { status = rtw_do_join(padapter); } release_mlme_lock: spin_unlock_bh(&pmlmepriv->lock); exit: return status; }
bool rtw_pwr_unassociated_idle(_adapter *adapter) { _adapter *buddy = adapter->pbuddy_adapter; struct mlme_priv *pmlmepriv = &(adapter->mlmepriv); struct xmit_priv *pxmit_priv = &adapter->xmitpriv; #ifdef CONFIG_P2P struct wifidirect_info *pwdinfo = &(adapter->wdinfo); #ifdef CONFIG_IOCTL_CFG80211 struct cfg80211_wifidirect_info *pcfg80211_wdinfo = &adapter->cfg80211_wdinfo; #endif #endif bool ret = _FALSE; if (adapter->pwrctrlpriv.ips_deny_time >= rtw_get_current_time()) { //DBG_871X("%s ips_deny_time\n", __func__); goto exit; } if (check_fwstate(pmlmepriv, WIFI_ASOC_STATE|WIFI_SITE_MONITOR) || check_fwstate(pmlmepriv, WIFI_UNDER_LINKING|WIFI_UNDER_WPS) || check_fwstate(pmlmepriv, WIFI_AP_STATE) || check_fwstate(pmlmepriv, WIFI_ADHOC_MASTER_STATE|WIFI_ADHOC_STATE) #if defined(CONFIG_P2P) && defined(CONFIG_IOCTL_CFG80211) && defined(CONFIG_P2P_IPS) || pcfg80211_wdinfo->is_ro_ch #elif defined(CONFIG_P2P) || !rtw_p2p_chk_state(pwdinfo, P2P_STATE_NONE) #endif ) { goto exit; } /* consider buddy, if exist */ if (buddy) { struct mlme_priv *b_pmlmepriv = &(buddy->mlmepriv); #ifdef CONFIG_P2P struct wifidirect_info *b_pwdinfo = &(buddy->wdinfo); #ifdef CONFIG_IOCTL_CFG80211 struct cfg80211_wifidirect_info *b_pcfg80211_wdinfo = &buddy->cfg80211_wdinfo; #endif #endif if (check_fwstate(b_pmlmepriv, WIFI_ASOC_STATE|WIFI_SITE_MONITOR) || check_fwstate(b_pmlmepriv, WIFI_UNDER_LINKING|WIFI_UNDER_WPS) || check_fwstate(b_pmlmepriv, WIFI_AP_STATE) || check_fwstate(b_pmlmepriv, WIFI_ADHOC_MASTER_STATE|WIFI_ADHOC_STATE) #if defined(CONFIG_P2P) && defined(CONFIG_IOCTL_CFG80211) && defined(CONFIG_P2P_IPS) || b_pcfg80211_wdinfo->is_ro_ch #elif defined(CONFIG_P2P) || !rtw_p2p_chk_state(b_pwdinfo, P2P_STATE_NONE) #endif ) { goto exit; } } #if (MP_DRIVER == 1) if (adapter->registrypriv.mp_mode == 1) goto exit; #endif #ifdef CONFIG_INTEL_PROXIM if(adapter->proximity.proxim_on==_TRUE){ return; } #endif if (pxmit_priv->free_xmitbuf_cnt != NR_XMITBUFF || pxmit_priv->free_xmit_extbuf_cnt != NR_XMIT_EXTBUFF) { DBG_871X_LEVEL(_drv_always_, "There are some pkts to transmit\n"); DBG_871X_LEVEL(_drv_info_, "free_xmitbuf_cnt: %d, free_xmit_extbuf_cnt: %d\n", pxmit_priv->free_xmitbuf_cnt, pxmit_priv->free_xmit_extbuf_cnt); goto exit; } ret = _TRUE; exit: return ret; }
/* * Description: * Aggregation packets and send to hardware * * Return: * 0 Success * -1 Hardware resource(TX FIFO) not ready * -2 Software resource(xmitbuf) not ready */ static s32 xmit_xmitframes(PADAPTER padapter, struct xmit_priv *pxmitpriv) { s32 err, ret; u32 k=0; struct hw_xmit *hwxmits, *phwxmit; u8 no_res, idx, hwentry; _irqL irql; struct tx_servq *ptxservq; _list *sta_plist, *sta_phead, *frame_plist, *frame_phead; struct xmit_frame *pxmitframe; _queue *pframe_queue; struct xmit_buf *pxmitbuf; u32 txlen; u8 txdesc_size = TXDESC_SIZE; int inx[4]; err = 0; no_res = _FALSE; hwxmits = pxmitpriv->hwxmits; hwentry = pxmitpriv->hwxmit_entry; ptxservq = NULL; pxmitframe = NULL; pframe_queue = NULL; pxmitbuf = NULL; if (padapter->registrypriv.wifi_spec == 1) { for(idx=0; idx<4; idx++) inx[idx] = pxmitpriv->wmm_para_seq[idx]; } else { inx[0] = 0; inx[1] = 1; inx[2] = 2; inx[3] = 3; } // 0(VO), 1(VI), 2(BE), 3(BK) for (idx = 0; idx < hwentry; idx++) { phwxmit = hwxmits + inx[idx]; if((check_pending_xmitbuf(pxmitpriv) == _TRUE) && (padapter->mlmepriv.LinkDetectInfo.bHigherBusyTxTraffic == _TRUE)) { if ((phwxmit->accnt > 0) && (phwxmit->accnt < 5)) { err = -2; break; } } _enter_critical_bh(&pxmitpriv->lock, &irql); sta_phead = get_list_head(phwxmit->sta_queue); sta_plist = get_next(sta_phead); //because stop_sta_xmit may delete sta_plist at any time //so we should add lock here, or while loop can not exit while (rtw_end_of_queue_search(sta_phead, sta_plist) == _FALSE) { ptxservq = LIST_CONTAINOR(sta_plist, struct tx_servq, tx_pending); sta_plist = get_next(sta_plist); #ifdef DBG_XMIT_BUF DBG_871X("%s idx:%d hwxmit_pkt_num:%d ptxservq_pkt_num:%d\n", __func__, idx, phwxmit->accnt, ptxservq->qcnt); DBG_871X("%s free_xmit_extbuf_cnt=%d free_xmitbuf_cnt=%d free_xmitframe_cnt=%d \n", __func__, pxmitpriv->free_xmit_extbuf_cnt, pxmitpriv->free_xmitbuf_cnt, pxmitpriv->free_xmitframe_cnt); #endif pframe_queue = &ptxservq->sta_pending; frame_phead = get_list_head(pframe_queue); while (rtw_is_list_empty(frame_phead) == _FALSE) { frame_plist = get_next(frame_phead); pxmitframe = LIST_CONTAINOR(frame_plist, struct xmit_frame, list); // check xmit_buf size enough or not txlen = txdesc_size + rtw_wlan_pkt_size(pxmitframe); if ((NULL == pxmitbuf) || ((pxmitbuf->ptail + txlen) > pxmitbuf->pend) #ifdef SDIO_TX_AGG_MAX || (k >= SDIO_TX_AGG_MAX) #endif ) { if (pxmitbuf) { //pxmitbuf->priv_data will be NULL, and will crash here if (pxmitbuf->len > 0 && pxmitbuf->priv_data) { struct xmit_frame *pframe; pframe = (struct xmit_frame*)pxmitbuf->priv_data; pframe->agg_num = k; pxmitbuf->agg_num = k; rtl8723b_update_txdesc(pframe, pframe->buf_addr); rtw_free_xmitframe(pxmitpriv, pframe); pxmitbuf->priv_data = NULL; enqueue_pending_xmitbuf(pxmitpriv, pxmitbuf); //can not yield under lock //rtw_yield_os(); } else { rtw_free_xmitbuf(pxmitpriv, pxmitbuf); } } pxmitbuf = rtw_alloc_xmitbuf(pxmitpriv); if (pxmitbuf == NULL) { #ifdef DBG_XMIT_BUF DBG_871X_LEVEL(_drv_err_, "%s: xmit_buf is not enough!\n", __FUNCTION__); #endif err = -2; break; } k = 0; } // ok to send, remove frame from queue #ifdef CONFIG_AP_MODE if (check_fwstate(&padapter->mlmepriv, WIFI_AP_STATE) == _TRUE) { if ((pxmitframe->attrib.psta->state & WIFI_SLEEP_STATE) && (pxmitframe->attrib.triggered == 0)) { DBG_871X("%s: one not triggered pkt in queue when this STA sleep," " break and goto next sta\n", __func__); break; } } #endif rtw_list_delete(&pxmitframe->list); ptxservq->qcnt--; phwxmit->accnt--; if (k == 0) { pxmitbuf->ff_hwaddr = rtw_get_ff_hwaddr(pxmitframe); pxmitbuf->priv_data = (u8*)pxmitframe; } // coalesce the xmitframe to xmitbuf pxmitframe->pxmitbuf = pxmitbuf; pxmitframe->buf_addr = pxmitbuf->ptail; ret = rtw_xmitframe_coalesce(padapter, pxmitframe->pkt, pxmitframe); if (ret == _FAIL) { DBG_871X_LEVEL(_drv_err_, "%s: coalesce FAIL!", __FUNCTION__); // Todo: error handler } else { k++; if (k != 1) rtl8723b_update_txdesc(pxmitframe, pxmitframe->buf_addr); rtw_count_tx_stats(padapter, pxmitframe, pxmitframe->attrib.last_txcmdsz); txlen = txdesc_size + pxmitframe->attrib.last_txcmdsz; pxmitframe->pg_num = (txlen + 127)/128; pxmitbuf->pg_num += (txlen + 127)/128; //if (k != 1) // ((struct xmit_frame*)pxmitbuf->priv_data)->pg_num += pxmitframe->pg_num; pxmitbuf->ptail += _RND(txlen, 8); // round to 8 bytes alignment pxmitbuf->len = _RND(pxmitbuf->len, 8) + txlen; } if (k != 1) rtw_free_xmitframe(pxmitpriv, pxmitframe); pxmitframe = NULL; } if (_rtw_queue_empty(pframe_queue) == _TRUE) rtw_list_delete(&ptxservq->tx_pending); if (err) break; } _exit_critical_bh(&pxmitpriv->lock, &irql); // dump xmit_buf to hw tx fifo if (pxmitbuf) { RT_TRACE(_module_hal_xmit_c_, _drv_info_, ("pxmitbuf->len=%d enqueue\n",pxmitbuf->len)); if (pxmitbuf->len > 0) { struct xmit_frame *pframe; pframe = (struct xmit_frame*)pxmitbuf->priv_data; pframe->agg_num = k; pxmitbuf->agg_num = k; rtl8723b_update_txdesc(pframe, pframe->buf_addr); rtw_free_xmitframe(pxmitpriv, pframe); pxmitbuf->priv_data = NULL; enqueue_pending_xmitbuf(pxmitpriv, pxmitbuf); rtw_yield_os(); } else rtw_free_xmitbuf(pxmitpriv, pxmitbuf); pxmitbuf = NULL; } if (err) break; } return err; }
u8 SetHalDefVar( struct adapter *adapter, enum HAL_DEF_VARIABLE variable, void *value ) { struct hal_com_data *hal_data = GET_HAL_DATA(adapter); DM_ODM_T *odm = &(hal_data->odmpriv); u8 bResult = _SUCCESS; switch (variable) { case HW_DEF_FA_CNT_DUMP: /* ODM_COMP_COMMON */ if (*((u8 *)value)) odm->DebugComponents |= (ODM_COMP_DIG | ODM_COMP_FA_CNT); else odm->DebugComponents &= ~(ODM_COMP_DIG | ODM_COMP_FA_CNT); break; case HAL_DEF_DBG_RX_INFO_DUMP: DBG_871X("============ Rx Info dump ===================\n"); DBG_871X("bLinked = %d, RSSI_Min = %d(%%)\n", odm->bLinked, odm->RSSI_Min); if (odm->bLinked) { DBG_871X("RxRate = %s, RSSI_A = %d(%%), RSSI_B = %d(%%)\n", HDATA_RATE(odm->RxRate), odm->RSSI_A, odm->RSSI_B); #ifdef DBG_RX_SIGNAL_DISPLAY_RAW_DATA rtw_dump_raw_rssi_info(adapter); #endif } break; case HW_DEF_ODM_DBG_FLAG: ODM_CmnInfoUpdate(odm, ODM_CMNINFO_DBG_COMP, *((u64 *)value)); break; case HW_DEF_ODM_DBG_LEVEL: ODM_CmnInfoUpdate(odm, ODM_CMNINFO_DBG_LEVEL, *((u32 *)value)); break; case HAL_DEF_DBG_DM_FUNC: { u8 dm_func = *((u8 *)value); struct dm_priv *dm = &hal_data->dmpriv; if (dm_func == 0) { /* disable all dynamic func */ odm->SupportAbility = DYNAMIC_FUNC_DISABLE; DBG_8192C("==> Disable all dynamic function...\n"); } else if (dm_func == 1) {/* disable DIG */ odm->SupportAbility &= (~DYNAMIC_BB_DIG); DBG_8192C("==> Disable DIG...\n"); } else if (dm_func == 2) {/* disable High power */ odm->SupportAbility &= (~DYNAMIC_BB_DYNAMIC_TXPWR); } else if (dm_func == 3) {/* disable tx power tracking */ odm->SupportAbility &= (~DYNAMIC_RF_CALIBRATION); DBG_8192C("==> Disable tx power tracking...\n"); } else if (dm_func == 4) {/* disable BT coexistence */ dm->DMFlag &= (~DYNAMIC_FUNC_BT); } else if (dm_func == 5) {/* disable antenna diversity */ odm->SupportAbility &= (~DYNAMIC_BB_ANT_DIV); } else if (dm_func == 6) {/* turn on all dynamic func */ if (!(odm->SupportAbility & DYNAMIC_BB_DIG)) { DIG_T *pDigTable = &odm->DM_DigTable; pDigTable->CurIGValue = rtw_read8(adapter, 0xc50); } dm->DMFlag |= DYNAMIC_FUNC_BT; odm->SupportAbility = DYNAMIC_ALL_FUNC_ENABLE; DBG_8192C("==> Turn on all dynamic function...\n"); } } break; case HAL_DEF_DBG_DUMP_RXPKT: hal_data->bDumpRxPkt = *((u8 *)value); break; case HAL_DEF_DBG_DUMP_TXPKT: hal_data->bDumpTxPkt = *((u8 *)value); break; case HAL_DEF_ANT_DETECT: hal_data->AntDetection = *((u8 *)value); break; default: DBG_871X_LEVEL(_drv_always_, "%s: [WARNING] HAL_DEF_VARIABLE(%d) not defined!\n", __func__, variable); bResult = _FAIL; break; } return bResult; }
void SetHwReg(struct adapter *adapter, u8 variable, u8 *val) { struct hal_com_data *hal_data = GET_HAL_DATA(adapter); DM_ODM_T *odm = &(hal_data->odmpriv); switch (variable) { case HW_VAR_PORT_SWITCH: hw_var_port_switch(adapter); break; case HW_VAR_INIT_RTS_RATE: rtw_warn_on(1); break; case HW_VAR_SEC_CFG: { u16 reg_scr; reg_scr = rtw_read16(adapter, REG_SECCFG); rtw_write16(adapter, REG_SECCFG, reg_scr|SCR_CHK_KEYID|SCR_RxDecEnable|SCR_TxEncEnable); } break; case HW_VAR_SEC_DK_CFG: { struct security_priv *sec = &adapter->securitypriv; u8 reg_scr = rtw_read8(adapter, REG_SECCFG); if (val) { /* Enable default key related setting */ reg_scr |= SCR_TXBCUSEDK; if (sec->dot11AuthAlgrthm != dot11AuthAlgrthm_8021X) reg_scr |= (SCR_RxUseDK|SCR_TxUseDK); } else /* Disable default key related setting */ reg_scr &= ~(SCR_RXBCUSEDK|SCR_TXBCUSEDK|SCR_RxUseDK|SCR_TxUseDK); rtw_write8(adapter, REG_SECCFG, reg_scr); } break; case HW_VAR_DM_FLAG: odm->SupportAbility = *((u32 *)val); break; case HW_VAR_DM_FUNC_OP: if (*((u8 *)val) == true) { /* save dm flag */ odm->BK_SupportAbility = odm->SupportAbility; } else { /* restore dm flag */ odm->SupportAbility = odm->BK_SupportAbility; } break; case HW_VAR_DM_FUNC_SET: if (*((u32 *)val) == DYNAMIC_ALL_FUNC_ENABLE) { struct dm_priv *dm = &hal_data->dmpriv; dm->DMFlag = dm->InitDMFlag; odm->SupportAbility = dm->InitODMFlag; } else { odm->SupportAbility |= *((u32 *)val); } break; case HW_VAR_DM_FUNC_CLR: /* * input is already a mask to clear function * don't invert it again! George, Lucas@20130513 */ odm->SupportAbility &= *((u32 *)val); break; case HW_VAR_AMPDU_MIN_SPACE: /* TODO - Is something needed here? */ break; case HW_VAR_WIRELESS_MODE: /* TODO - Is something needed here? */ break; default: DBG_871X_LEVEL( _drv_always_, FUNC_ADPT_FMT" variable(%d) not defined!\n", FUNC_ADPT_ARG(adapter), variable ); break; } }
u8 rtw_set_802_11_bssid(_adapter* padapter, u8 *bssid) { _irqL irqL; u8 status=_SUCCESS; u32 cur_time = 0; struct mlme_priv *pmlmepriv = &padapter->mlmepriv; _func_enter_; DBG_871X_LEVEL(_drv_always_, "set bssid:%pM\n", bssid); if ((bssid[0]==0x00 && bssid[1]==0x00 && bssid[2]==0x00 && bssid[3]==0x00 && bssid[4]==0x00 &&bssid[5]==0x00) || (bssid[0]==0xFF && bssid[1]==0xFF && bssid[2]==0xFF && bssid[3]==0xFF && bssid[4]==0xFF &&bssid[5]==0xFF)) { status = _FAIL; goto exit; } _enter_critical_bh(&pmlmepriv->lock, &irqL); DBG_871X("Set BSSID under fw_state=0x%08x\n", get_fwstate(pmlmepriv)); if (check_fwstate(pmlmepriv, _FW_UNDER_SURVEY) == _TRUE) { goto handle_tkip_countermeasure; } else if (check_fwstate(pmlmepriv, _FW_UNDER_LINKING) == _TRUE) { goto release_mlme_lock; } if (check_fwstate(pmlmepriv, _FW_LINKED|WIFI_ADHOC_MASTER_STATE) == _TRUE) { RT_TRACE(_module_rtl871x_ioctl_set_c_, _drv_info_, ("set_bssid: _FW_LINKED||WIFI_ADHOC_MASTER_STATE\n")); if (_rtw_memcmp(&pmlmepriv->cur_network.network.MacAddress, bssid, ETH_ALEN) == _TRUE) { if (check_fwstate(pmlmepriv, WIFI_STATION_STATE) == _FALSE) goto release_mlme_lock;//it means driver is in WIFI_ADHOC_MASTER_STATE, we needn't create bss again. } else { RT_TRACE(_module_rtl871x_ioctl_set_c_,_drv_info_,("Set BSSID not the same bssid\n")); RT_TRACE(_module_rtl871x_ioctl_set_c_,_drv_info_,("set_bssid="MAC_FMT"\n", MAC_ARG(bssid) )); RT_TRACE(_module_rtl871x_ioctl_set_c_,_drv_info_,("cur_bssid="MAC_FMT"\n", MAC_ARG(pmlmepriv->cur_network.network.MacAddress) )); rtw_disassoc_cmd(padapter); if (check_fwstate(pmlmepriv, _FW_LINKED) == _TRUE) rtw_indicate_disconnect(padapter); rtw_free_assoc_resources(padapter, 1); if ((check_fwstate(pmlmepriv, WIFI_ADHOC_MASTER_STATE) == _TRUE)) { _clr_fwstate_(pmlmepriv, WIFI_ADHOC_MASTER_STATE); set_fwstate(pmlmepriv, WIFI_ADHOC_STATE); } } } handle_tkip_countermeasure: //should we add something here...? #ifdef PLATFORM_LINUX if (padapter->securitypriv.btkip_countermeasure == _TRUE) { cur_time = rtw_get_current_time(); if( (cur_time - padapter->securitypriv.btkip_countermeasure_time) > 60 * HZ ) { padapter->securitypriv.btkip_countermeasure = _FALSE; padapter->securitypriv.btkip_countermeasure_time = 0; } else { status = _FAIL; goto release_mlme_lock; } } #endif _rtw_memcpy(&pmlmepriv->assoc_bssid, bssid, ETH_ALEN); pmlmepriv->assoc_by_bssid=_TRUE; if (check_fwstate(pmlmepriv, _FW_UNDER_SURVEY) == _TRUE) { pmlmepriv->to_join = _TRUE; } else { status = rtw_do_join(padapter); } release_mlme_lock: _exit_critical_bh(&pmlmepriv->lock, &irqL); exit: RT_TRACE(_module_rtl871x_ioctl_set_c_, _drv_err_, ("rtw_set_802_11_bssid: status=%d\n", status)); _func_exit_; return status; }
u8 rtw_set_802_11_ssid(_adapter* padapter, NDIS_802_11_SSID *ssid) { _irqL irqL; u8 status = _SUCCESS; u32 cur_time = 0; struct mlme_priv *pmlmepriv = &padapter->mlmepriv; struct wlan_network *pnetwork = &pmlmepriv->cur_network; _func_enter_; DBG_871X_LEVEL(_drv_always_, "set ssid [%s] fw_state=0x%08x\n", ssid->Ssid, get_fwstate(pmlmepriv)); if(padapter->hw_init_completed==_FALSE){ RT_TRACE(_module_rtl871x_ioctl_set_c_, _drv_err_, ("set_ssid: hw_init_completed==_FALSE=>exit!!!\n")); status = _FAIL; goto exit; } _enter_critical_bh(&pmlmepriv->lock, &irqL); DBG_871X("Set SSID under fw_state=0x%08x\n", get_fwstate(pmlmepriv)); if (check_fwstate(pmlmepriv, _FW_UNDER_SURVEY) == _TRUE) { goto handle_tkip_countermeasure; } else if (check_fwstate(pmlmepriv, _FW_UNDER_LINKING) == _TRUE) { goto release_mlme_lock; } if (check_fwstate(pmlmepriv, _FW_LINKED|WIFI_ADHOC_MASTER_STATE) == _TRUE) { RT_TRACE(_module_rtl871x_ioctl_set_c_, _drv_info_, ("set_ssid: _FW_LINKED||WIFI_ADHOC_MASTER_STATE\n")); if ((pmlmepriv->assoc_ssid.SsidLength == ssid->SsidLength) && (_rtw_memcmp(&pmlmepriv->assoc_ssid.Ssid, ssid->Ssid, ssid->SsidLength) == _TRUE)) { if((check_fwstate(pmlmepriv, WIFI_STATION_STATE) == _FALSE)) { RT_TRACE(_module_rtl871x_ioctl_set_c_, _drv_err_, ("Set SSID is the same ssid, fw_state=0x%08x\n", get_fwstate(pmlmepriv))); if(rtw_is_same_ibss(padapter, pnetwork) == _FALSE) { //if in WIFI_ADHOC_MASTER_STATE | WIFI_ADHOC_STATE, create bss or rejoin again rtw_disassoc_cmd(padapter); if (check_fwstate(pmlmepriv, _FW_LINKED) == _TRUE) rtw_indicate_disconnect(padapter); rtw_free_assoc_resources(padapter, 1); if (check_fwstate(pmlmepriv, WIFI_ADHOC_MASTER_STATE) == _TRUE) { _clr_fwstate_(pmlmepriv, WIFI_ADHOC_MASTER_STATE); set_fwstate(pmlmepriv, WIFI_ADHOC_STATE); } } else { goto release_mlme_lock;//it means driver is in WIFI_ADHOC_MASTER_STATE, we needn't create bss again. } } #ifdef CONFIG_LPS else { rtw_lps_ctrl_wk_cmd(padapter, LPS_CTRL_JOINBSS, 1); } #endif } else { RT_TRACE(_module_rtl871x_ioctl_set_c_,_drv_info_,("Set SSID not the same ssid\n")); RT_TRACE(_module_rtl871x_ioctl_set_c_,_drv_info_,("set_ssid=[%s] len=0x%x\n", ssid->Ssid, (unsigned int)ssid->SsidLength)); RT_TRACE(_module_rtl871x_ioctl_set_c_,_drv_info_,("assoc_ssid=[%s] len=0x%x\n", pmlmepriv->assoc_ssid.Ssid, (unsigned int)pmlmepriv->assoc_ssid.SsidLength)); rtw_disassoc_cmd(padapter); if (check_fwstate(pmlmepriv, _FW_LINKED) == _TRUE) rtw_indicate_disconnect(padapter); rtw_free_assoc_resources(padapter, 1); if (check_fwstate(pmlmepriv, WIFI_ADHOC_MASTER_STATE) == _TRUE) { _clr_fwstate_(pmlmepriv, WIFI_ADHOC_MASTER_STATE); set_fwstate(pmlmepriv, WIFI_ADHOC_STATE); } } } handle_tkip_countermeasure: #ifdef PLATFORM_WINDOWS if (padapter->securitypriv.btkip_countermeasure==_TRUE) { LARGE_INTEGER sys_time; u32 diff_time,cur_time ; RT_TRACE(_module_rtl871x_ioctl_set_c_,_drv_info_,("rtw_set_802_11_ssid:padapter->securitypriv.btkip_countermeasure==_TRUE\n")); NdisGetCurrentSystemTime(&sys_time); cur_time=(u32)(sys_time.QuadPart/10); // In micro-second. RT_TRACE(_module_rtl871x_ioctl_set_c_,_drv_info_,("rtw_set_802_11_ssid:cur_time=0x%x\n",cur_time)); RT_TRACE(_module_rtl871x_ioctl_set_c_,_drv_info_,("rtw_set_802_11_ssid:psecuritypriv->last_mic_err_time=0x%x\n",padapter->securitypriv.btkip_countermeasure_time)); diff_time = cur_time -padapter->securitypriv.btkip_countermeasure_time; // In micro-second. RT_TRACE(_module_rtl871x_ioctl_set_c_,_drv_info_,("rtw_set_802_11_ssid:diff_time=0x%x\n",diff_time)); if (diff_time > 60000000) { RT_TRACE(_module_rtl871x_ioctl_set_c_,_drv_info_,("rtw_set_802_11_ssid(): countermeasure time >60s.\n")); padapter->securitypriv.btkip_countermeasure=_FALSE; // Update MIC error time. padapter->securitypriv.btkip_countermeasure_time=0; } else { // can't join in 60 seconds. status = _FAIL; RT_TRACE(_module_rtl871x_ioctl_set_c_,_drv_info_,("rtw_set_802_11_ssid(): countermeasure time <60s.\n")); goto release_mlme_lock; } } #endif #ifdef PLATFORM_LINUX if (padapter->securitypriv.btkip_countermeasure == _TRUE) { cur_time = rtw_get_current_time(); if( (cur_time - padapter->securitypriv.btkip_countermeasure_time) > 60 * HZ ) { padapter->securitypriv.btkip_countermeasure = _FALSE; padapter->securitypriv.btkip_countermeasure_time = 0; } else { status = _FAIL; goto release_mlme_lock; } } #endif #ifdef CONFIG_VALIDATE_SSID if (rtw_validate_ssid(ssid) == _FALSE) { status = _FAIL; goto release_mlme_lock; } #endif _rtw_memcpy(&pmlmepriv->assoc_ssid, ssid, sizeof(NDIS_802_11_SSID)); pmlmepriv->assoc_by_bssid=_FALSE; if (check_fwstate(pmlmepriv, _FW_UNDER_SURVEY) == _TRUE) { pmlmepriv->to_join = _TRUE; } else { status = rtw_do_join(padapter); } release_mlme_lock: _exit_critical_bh(&pmlmepriv->lock, &irqL); exit: RT_TRACE(_module_rtl871x_ioctl_set_c_, _drv_err_, ("-rtw_set_802_11_ssid: status=%d\n", status)); _func_exit_; return status; }