0%

AirKiss Client 实现评估及 raw socket

原始套接字、wifi驱动支持及Airkiss Client实现

源码 AirKiss,依赖于libiw实现抓取数据链路层 packet 功能

常用网络协议栈

  • Linux
  • FreeBSD

SOCK_RAW常应用于packet sniffer,例如libpcap,结合接口混杂模式,监视本地电缆上流通的所有分组

Promiscuous vs Monitoring mode

这两种模式不是所有设备都支持的!!!
一般网卡都工作在非混杂模式下,只接受来自网络端口的目的地址指向自己的数据。
以下两种模式经常混淆,常用与捕捉数据,对比其特点与差异

Promiscuous 网卡混杂模式

混杂模式不是数据包捕获模式,它是以太网数据包捕获的一种选择option

  • 设备必须入网,可以是 wire/wireless
  • 所有流经网卡的数据
  • 协议 IEEE 802.3,Ethernet level
  • OSI 层次:Mac 层

在此模式下监听以太网内部的流量,这个时候网卡不会区分流经其的数据包的目标地址是不是本机,一股脑儿的都将其截下供协议栈上层进行调用查看。

命令开启

ifconfig wlan0 promisc  设置混杂模式
ifconfig wlan0 -promisc 取消混杂模式

Monitor 无线网卡监听模式

监听模式仅用于WIFI,用于在802.11 radio level捕捉数据包,而不是在Ethernet level,是一种数据包捕获模式

  • 设备不能入网,不能位于任何网络中
  • 仅用于 wireless
  • 协议 IEEE 802.11,radio level
  • OSI 层次:Physical (PHY) Layer + Data Link Layer (Mac)

在此模式下监听所有802.11数据包

命令开启

ifconfig wlan0 down
iwconfig wlan0 mode monitor
ifconfig wlan0 up

// 或者增加虚拟监听网卡 mon0
sudo iw dev wlan0 interface add mon0 type monitor
sudo ifconfig mon0 up

总结

  • 监听模式允许网卡不用连接AP就可以抓取特性频道的数据,就是在空中抓取某个波段的数据。可以用在破解密码
  • 混杂模式(连接 wifi)就是接收所有经过网卡的数据包,包括不是发给本机的包,即不验证 MAC 地址
  • 普通模式下网卡只接收发给本机的包

L2 vs L3 raw socket

见这篇文章了解原始套接字:Raw Socket L2 vs L3

Airkiss Client除了要求硬件具有Monitor能力之外,还需要系统提供L2 Raw Socket支持

而现阶段ecos系统使用的FreeBSD Network Stack不支持,因此ecos下不能实现。而Linux Network Stack下使用PF_PACKET协议簇下的SOCK_RAW来实现链路层数据处理

Commands

// down device
$ sudo ifconfig wlan0 down
// up device
$ sudo ifconfig wlan0 up
// check device modes
$ sudo iw list
// check device mode
$ sudo iwconfig wlan0
// set device monitor mode
$ sudo iwconfig wlan0 mode monitor
$ sudo iw wlan0 set type monitor
// kill some processes
$ sudo airmon-ng check kill
// add virtual monitor device
$ sudo iw dev wlan0 interface add mon0 type monitor
// set channel
$ sudo iw wlan0 set channel 5
$ sudo iwconfig wlan0 channel 6
// set freq
$ sudo iwconfig wlan0 freq 2.484G
$ sudo iw wlan0 set freq 2.484G
// tcpdump with special channel
$ sudo tcpdump -i mon0 -n -w file.cap
// set device managed mode for station
$ sudo ifconfig wlan0 down
$ sudo iwconfig wlan0 mode managed
$ sudo ifconfig wlan0 up
// scan APs in managed mode
$ sudo iwlist wlan0 scan

问题

1#

airkiss首先需要在各个channel上切换,以获取前导数据,在开源工程中使用如下命令来完成,有如下错误

$ iw wlan0 set channel 5
command failed: Device or resource busy (-16)
$ iwconfig wlan0 chan 2
Error for wireless request "Set Frequency" (8B04) :
    SET failed on device wlan0 ; Device or resource busy.

在主机环境下做如下测试

$ ifconfig
wlx00117f5bb7b4: flags=4099<UP,BROADCAST,MULTICAST>  mtu 1500
        ether 00:11:7f:5b:b7:b4  txqueuelen 1000  (Ethernet)
        RX packets 0  bytes 0 (0.0 B)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 0  bytes 0 (0.0 B)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0
$ iwconfig wlx00117f5bb7b4
wlx00117f5bb7b4  IEEE 802.11  ESSID:off/any
          Mode:Managed  Access Point: Not-Associated   Tx-Power=20 dBm
          Retry short  long limit:2   RTS thr:off   Fragment thr:off
          Power Management:off
$ sudo iw wlx00117f5bb7b4 set channel 10
command failed: Device or resource busy (-16)
$ sudo ifconfig wlx00117f5bb7b4 down
$ sudo iw wlx00117f5bb7b4 set channel 10
command failed: Device or resource busy (-16)
$ sudo ifconfig wlx00117f5bb7b4 up

$ sudo iw wlx00117f5bb7b4 set type monitor
command failed: Device or resource busy (-16)
$ sudo ifconfig wlx00117f5bb7b4 down
$ sudo iw wlx00117f5bb7b4 set type monitor
$ sudo ifconfig wlx00117f5bb7b4 up
$ iwconfig wlx00117f5bb7b4
wlx00117f5bb7b4  IEEE 802.11  Mode:Monitor  Frequency:2.412 GHz  Tx-Power=20 dBm
          Retry short  long limit:2   RTS thr:off   Fragment thr:off
          Power Management:off
$ sudo iw wlx00117f5bb7b4 set channel 10
$ iwconfig wlx00117f5bb7b4
wlx00117f5bb7b4  IEEE 802.11  Mode:Monitor  Frequency:2.457 GHz  Tx-Power=20 dBm
          Retry short  long limit:2   RTS thr:off   Fragment thr:off
          Power Management:off

通过以上命令系列猜想set channel对应SIOCSIWFREQ,在STATION下不起作用,在Monitor下才可以设置

在内核4.9.x中查找到如下代码,调用SIOCSIWFREQ会执行到文件net/wireless/wext-compat.c下函数cfg80211_wext_siwfreq

  20     case NL80211_IFTYPE_STATION:
  19         return cfg80211_mgd_wext_siwfreq(dev, info, wextfreq, extra);
  18     case NL80211_IFTYPE_ADHOC:
  17         return cfg80211_ibss_wext_siwfreq(dev, info, wextfreq, extra);
  16     case NL80211_IFTYPE_MONITOR:
  15         freq = cfg80211_wext_freq(wextfreq);
  14         if (freq < 0)
  13             return freq;
  12         if (freq == 0)
  11             return -EINVAL;
  10         chandef.center_freq1 = freq;
   9         chandef.chan = ieee80211_get_channel(&rdev->wiphy, freq);
   8         if (!chandef.chan)
   7             return -EINVAL;
   6         return cfg80211_set_monitor_channel(rdev, &chandef);

其中cfg80211_mgd_wext_siwfreq最终调用cfg80211_set_monitor_channel

857 int cfg80211_set_monitor_channel(struct cfg80211_registered_device *rdev,
  1                  struct cfg80211_chan_def *chandef)
  2 {
  3     if (!rdev->ops->set_monitor_channel)
  4         return -EOPNOTSUPP;
  5     if (!cfg80211_has_monitors_only(rdev))
  6         return -EBUSY;
  7
  8     return rdev_set_monitor_channel(rdev, chandef);
  9 }

得到证实,只有在monitor下才能执行成功

2#

接上面的问题,set channel失败是因为不是monitor,而set mode monitor遇到错误

原因是interface down之后被其他线程up,调整逻辑解决此问题

Airkiss 协议

底层协议

见这篇文章了解802.11帧结构:Radiotap、Prism 和 802.11 帧格式分析

涉及802.2802.11以及radiotap header

Airkiss协议数据是802.11 数据帧,在FC中的subtype可以确认

通过monitor获取的数据为802.11 plus Radiotap

因为网卡驱动及路由区别导致链路层头长度不定,因此需要使用连续前导码来确定链路层头长度

因为mac payload加密原因,只能分析到802.11这一层,更高层SNAP/UDP/IP看不到,全部在加密数据中封装

开源工程wicap地址 中将数据直接转换为如下结构

  18  struct ieee80211_hdr {
    1     unsigned short frame_control;
    2     unsigned short duration_id;
    3     unsigned char addr1[6];
    4     unsigned char addr2[6];
    5     unsigned char addr3[6];
    6     unsigned short seq_ctrl;
    7     unsigned short addr4[6];
    8 } __attribute__ ((packed));

airkiss 优化

  1. 使用802.11 FC只过滤data frame
  2. 匹配mac addr

Ref

  1. 浅谈原始套接字 SOCK_RAW 的内幕及其应用
  2. raw socket 的使用
  3. linux 数据链路访问之 ETH_P_ALL 等等
  4. 网卡的混杂模式
  5. linux Packet socket (1) 简介
  6. 第二十九章 数据链路访问
  7. A Guide to Using Raw Sockets
  8. 链路层套接字 PF_PACKET 简介
  9. RAW sockets programming in C
  10. Linux 网络编程:原始套接字编程及实例分析
  11. Promiscuous vs Monitoring mode
  12. What is wireless monitor and promiscuous mode ?
  13. What is the difference between Promiscuous and Monitor Mode in Wireless Networks?
  14. 无线网卡的 4 种工作模式
  15. linux 网卡混杂模式和监听模式
  16. 802.11 协议帧格式、Wi-Fi 连接交互过程、无线破解入门研究
  17. How to send both 802.11 management frames and data frames using RAW sockets in linux
  18. Sending raw packets over WiFi on Linux (C/C++)
  19. Packet Sniffer Code in C using Linux Sockets (BSD) – Part 2