diff --git a/drivers/aic8800/aic8800_fdrv/Makefile b/drivers/aic8800/aic8800_fdrv/Makefile index 21ebf91..b2a3514 100644 --- a/drivers/aic8800/aic8800_fdrv/Makefile +++ b/drivers/aic8800/aic8800_fdrv/Makefile @@ -172,7 +172,7 @@ CONFIG_RWNX_BCMC ?= y # Enable Monitor+Data interface support (need FW support) CONFIG_RWNX_MON_DATA =n -CONFIG_RWNX_MON_XMIT ?= n +CONFIG_RWNX_MON_XMIT ?= y CONFIG_RWNX_MON_RXFILTER ?= n CONFIG_FILTER_TCP_ACK =y diff --git a/drivers/aic8800/aic8800_fdrv/rwnx_tx.c b/drivers/aic8800/aic8800_fdrv/rwnx_tx.c index 8d2ab4a..2cec672 100644 --- a/drivers/aic8800/aic8800_fdrv/rwnx_tx.c +++ b/drivers/aic8800/aic8800_fdrv/rwnx_tx.c @@ -1991,7 +1991,7 @@ free_use: netdev_tx_t rwnx_start_monitor_if_xmit(struct sk_buff *skb, struct net_device *dev) { - int rtap_len, ret, idx, tmp_len; + int rtap_len, ret, idx; struct ieee80211_radiotap_header *rtap_hdr; // net/ieee80211_radiotap.h struct ieee80211_radiotap_iterator iterator; // net/cfg80211.h u8_l *rtap_buf = (u8_l *)skb->data; @@ -2012,10 +2012,30 @@ netdev_tx_t rwnx_start_monitor_if_xmit(struct sk_buff *skb, struct net_device *d bool offchan = false; int nx_off_chan_txq_idx = NX_OFF_CHAN_TXQ_IDX; - rtap_hdr = (struct ieee80211_radiotap_header*)(rtap_buf); - rtap_len = ieee80211_get_radiotap_len(rtap_buf);//max_length frame_len = skb->len; + if (unlikely(skb->len < sizeof(*rtap_hdr))) { + AICWFDBG(LOGERROR, "%s radiotap header is truncated\n", __func__); + goto free_tag; + } + + rtap_hdr = (struct ieee80211_radiotap_header*)(rtap_buf); + if (unlikely(rtap_hdr->it_version)) { + AICWFDBG(LOGERROR, "%s itv \r\n", __func__); + goto free_tag; + } + + rtap_len = ieee80211_get_radiotap_len(rtap_buf);//max_length + if (unlikely(rtap_len < sizeof(*rtap_hdr))) { + AICWFDBG(LOGERROR, "%s rtap_len < sizeof(struct ieee80211_radiotap_header) \r\n", __func__); + goto free_tag; + } + + if (unlikely(skb->len < rtap_len)) { + AICWFDBG(LOGERROR, "%s skb->len < rtap_len \r\n", __func__); + goto free_tag; + } + AICWFDBG(LOGINFO, "rwnx_start_monitor_if_xmit, skb_len=%d, rtap_len=%d\n", skb->len, rtap_len); //rwnx_data_dump((char*)__func__, skb->data, skb->len); if((g_rwnx_plat->usbdev->chipid == PRODUCT_ID_AIC8801) || @@ -2023,23 +2043,6 @@ netdev_tx_t rwnx_start_monitor_if_xmit(struct sk_buff *skb, struct net_device *d g_rwnx_plat->usbdev->chipid == PRODUCT_ID_AIC8800DW) && chip_id < 3)){ nx_off_chan_txq_idx = NX_OFF_CHAN_TXQ_IDX_FOR_OLD_IC; } - - - if (unlikely(rtap_hdr->it_version)){ - AICWFDBG(LOGERROR, "%s itv \r\n", __func__); - goto free_tag; - } - - if (unlikely(skb->len < rtap_len)){ - AICWFDBG(LOGERROR, "%s skb->len < rtap_len \r\n", __func__); - goto free_tag; - } - - if (unlikely(rtap_len < sizeof(struct ieee80211_radiotap_header))){ - AICWFDBG(LOGERROR, "%s rtap_len < sizeof(struct ieee80211_radiotap_header) \r\n", __func__); - goto free_tag; - } - frame_len -= rtap_len; pframe = rtap_buf + rtap_len; diff --git a/drivers/aic8800/aic8800_fdrv/rwnx_tx.h b/drivers/aic8800/aic8800_fdrv/rwnx_tx.h index 772e2d1..532ffab 100644 --- a/drivers/aic8800/aic8800_fdrv/rwnx_tx.h +++ b/drivers/aic8800/aic8800_fdrv/rwnx_tx.h @@ -172,7 +172,8 @@ int rwnx_start_mgmt_xmit(struct rwnx_vif *vif, struct rwnx_sta *sta, u64 *cookie); #endif /* LINUX_VERSION_CODE >= KERNEL_VERSION(3, 14, 0) */ #ifdef CONFIG_RWNX_MON_XMIT -int rwnx_start_monitor_if_xmit(struct sk_buff *skb, struct net_device *dev); +netdev_tx_t rwnx_start_monitor_if_xmit(struct sk_buff *skb, + struct net_device *dev); #endif int rwnx_txdatacfm(void *pthis, void *host_id);