网中网 发表于 2015-10-2 13:43:37

修改WiFi beacon帧

  http://blog.iyunv.com/UsSam/article/details/18040871
  
  最近需要对OpenWRT内核中的beacon帧做修改
  要修改beacon帧,就需要了解帧的写入和发送的过程
  beacon帧发送机制:
    beacon帧的发送是通过tasklet机制实现的,tasklet是软中断实现的下半部处理机制,用于中断处理流程的下半部。核心函数是beacon.c中的ath9k_beacon_tasklet函数,(将该函数的指针传递给tasklet_init()即可实现tasklet_struct的动态创建,当tasklet被调度以后,ath9k_beacon_tasklet函数会被执行)。函数体如下所示:

[*]void ath9k_beacon_tasklet(unsigned long data)
[*]{
[*]    struct ath_softc *sc = (struct ath_softc *)data;
[*]    struct ath_hw *ah = sc->sc_ah;
[*]    struct ath_common *common = ath9k_hw_common(ah);
[*]    struct ath_buf *bf = NULL;
[*]    ...
[*]
[*]    bf = ath9k_beacon_generate(sc->hw, vif);
[*]
[*]    ...
[*]    if (bf) {
[*]      ath9k_reset_beacon_status(sc);
[*]
[*]
[*]      ath_dbg(common, BEACON, "Transmitting beacon for slot: %d\n", slot);
[*]
[*]
[*]      /* NB: cabq traffic should already be queued and primed */
[*]      ath9k_hw_puttxbuf(ah, sc->beacon.beaconq, bf->bf_daddr);
[*]
[*]      if (!edma)
[*]      {
[*]            ath9k_hw_txstart(ah, sc->beacon.beaconq);
[*]      }
[*]    }
[*]}
  研究收发机制是为了修改beacon帧,因此接下来我们看一看beacon帧是如何产生的。这就要研究刚才提到的ath9k_beacon_generate函数了。ath9k_beacon_generate函数体如下所示:

[*]static struct ath_buf *ath9k_beacon_generate(struct ieee80211_hw *hw, struct ieee80211_vif *vif)
[*]{
[*]    struct ath_softc *sc = hw->priv;
[*]    struct ath_common *common = ath9k_hw_common(sc->sc_ah);
[*]    struct ath_buf *bf;
[*]    struct ath_vif *avp = (void *)vif->drv_priv;
[*]    struct sk_buff *skb;
[*]    struct ath_txq *cabq = sc->beacon.cabq;
[*]    struct ieee80211_tx_info *info;
[*]    struct ieee80211_mgmt *mgmt_hdr;
[*]    int cabq_depth;
[*]
[*]
[*]    if (avp->av_bcbuf == NULL)
[*]      return NULL;
[*]
[*]
[*]    bf = avp->av_bcbuf;
[*]    skb = bf->bf_mpdu;
[*]    if (skb) {
[*]      dma_unmap_single(sc->dev, bf->bf_buf_addr, skb->len, DMA_TO_DEVICE);
[*]      dev_kfree_skb_any(skb);
[*]      bf->bf_buf_addr = 0;
[*]      bf->bf_mpdu = NULL;            /*清空缓存*/
[*]    }
[*]
[*]
[*]
[*]    skb = ieee80211_beacon_get(hw, vif);<strong>
[*]</strong>
[*]
[*]
[*]    if (skb == NULL)
[*]      return NULL;                  /*skb生成失败退出*/
[*]
[*]    bf->bf_mpdu = skb;                   /*将生成的beacon帧缓存赋给bf结构体,此处是指针赋值,可以只用任一指针对对象进行修改*/
[*]
[*]
[*]
[*]
[*]
[*]    mgmt_hdr = (struct ieee80211_mgmt *)skb->data;
[*]    mgmt_hdr->u.beacon.timestamp = avp->tsf_adjust;       /*用ieee80211_mgmt结构体将skb->data中的前面若干个字段提取出来(包括frame_control,duration,da,sa,bssid,seqctrl,以及beacon帧特有的timestamp,beacon interval,capability information,variable字段),并对其timestamp字段进行数据的写入*/
[*]
[*]
[*]    ...
[*]
[*]    return bf;
[*]}
  
页: [1]
查看完整版本: 修改WiFi beacon帧