1. iwconfig代码框架

一、基本概念

iwconfig 作用域WLAN层,和ifconfig类似, 但仅作用于80211设备。
射频层不支持iwconfig。

二、主要接口

iw_sockets_open      //函数根据不同的协议创建对应的socket,以便和无线设备驱动进行交互。
iw_enum_devices      //当输入的一个参入时,则罗列出全部接口,如果是网络接口,则输出网络接口状态信息。
print_info		//获取参数信息传入后,打印出与参数对应的需求信息。
set_info		//设置参数输入后,进行ioctl操作,向无线设备驱动传参,并生效。

 三、数据结构体

/*
 * The structure to exchange data for ioctl.
 * This structure is the same as 'struct ifreq', but (re)defined for
 * convenience...
 * Do I need to remind you about structure size (32 octets) ?
 */
struct    iwreq 
{
    union
    {
        char    ifrn_name[IFNAMSIZ];    /* if name, e.g. "eth0" 接口名称*/
    } ifr_ifrn;

    /* Data part (defined just above) */
    union    iwreq_data    u; //存放数据的地方
};
/* ------------------------ IOCTL REQUEST ------------------------ */
/*
 * This structure defines the payload of an ioctl, and is used 
 * below.
 *
 * Note that this structure should fit on the memory footprint
 * of iwreq (which is the same as ifreq), which mean a max size of
 * 16 octets = 128 bits. Warning, pointers might be 64 bits wide...
 * You should check this when increasing the structures defined
 * above in this file...
 */
union    iwreq_data
{
    /* Config - generic */
    char        name[IFNAMSIZ];
    /* Name : used to verify the presence of  wireless extensions.
     * Name of the protocol/provider... */

    struct iw_point    essid;        /* Extended network name */
    struct iw_param    nwid;        /* network id (or domain - the cell) */
    struct iw_freq    freq;        /* frequency or channel :
                     * 0-1000 = channel
                     * > 1000 = frequency in Hz */

    struct iw_param    sens;        /* signal level threshold */
    struct iw_param    bitrate;    /* default bit rate */
    struct iw_param    txpower;    /* default transmit power */
    struct iw_param    rts;        /* RTS threshold threshold */
    struct iw_param    frag;        /* Fragmentation threshold */
    __u32        mode;        /* Operation mode */
    struct iw_param    retry;        /* Retry limits & lifetime */

    struct iw_point    encoding;    /* Encoding stuff : tokens */
    struct iw_param    power;        /* PM duration/timeout */
    struct iw_quality qual;        /* Quality part of statistics */

    struct sockaddr    ap_addr;    /* Access point address */
    struct sockaddr    addr;        /* Destination address (hw/mac) */

    struct iw_param    param;        /* Other small parameters */
    struct iw_point    data;        /* Other large parameters */
};

 

四、接口解析

1. iw_enum_device

 1 /*------------------------------------------------------------------*/
 2 /*
 3  * Enumerate devices and call specified routine
 4  * The new way just use /proc/net/wireless, so get all wireless interfaces,
 5  * whether configured or not. This is the default if available.
 6  * The old way use SIOCGIFCONF, so get only configured interfaces (wireless
 7  * or not).
 8  */
 9 void
10 iw_enum_devices(int        skfd,
11         iw_enum_handler    fn,
12         char *        args[],
13         int        count)
14 {
15   char        buff[1024];
16   FILE *    fh;
17   struct ifconf ifc;
18   struct ifreq *ifr;
19   int        i;
20 
21 #ifndef IW_RESTRIC_ENUM
22   /* Check if /proc/net/dev is available */
23   fh = fopen(PROC_NET_DEV, "r");
24 #else
25   /* Check if /proc/net/wireless is available */
26   fh = fopen(PROC_NET_WIRELESS, "r");
27 #endif
28 
29   if(fh != NULL)
30     {
31       /* Success : use data from /proc/net/wireless */
32 
33       /* Eat 2 lines of header 跳过2行开头 */
34       fgets(buff, sizeof(buff), fh);
35       fgets(buff, sizeof(buff), fh);
36 
37       /* Read each device line */
38       while(fgets(buff, sizeof(buff), fh))
39     {
40       char    name[IFNAMSIZ + 1];
41       char *s;
42 
43       /* Skip empty or almost empty lines. It seems that in some
44        * cases fgets return a line with only a newline. 跳过空行 */
45       if((buff[0] == '\0') || (buff[1] == '\0'))
46         continue;
47 
48       /* Extract interface name 获取接口名称 easy skip */
49       s = iw_get_ifname(name, sizeof(name), buff);
50 
51       if(!s)
52         {
53           /* Failed to parse, complain and continue */
54 #ifndef IW_RESTRIC_ENUM
55           fprintf(stderr, "Cannot parse " PROC_NET_DEV "\n");
56 #else
57           fprintf(stderr, "Cannot parse " PROC_NET_WIRELESS "\n");
58 #endif
59         }
60       else
61         /* Got it, print info about this interface */
62         (*fn)(skfd, name, args, count);
63     }
64 
65       fclose(fh);
66     }
67   else
68     {
69       /* Get list of configured devices using "traditional" way */
70       ifc.ifc_len = sizeof(buff);
71       ifc.ifc_buf = buff;
72       if(ioctl(skfd, SIOCGIFCONF, &ifc) < 0)
73     {
74       fprintf(stderr, "SIOCGIFCONF: %s\n", strerror(errno));
75       return;
76     }
77       ifr = ifc.ifc_req;
78 
79       /* Print them */
80       for(i = ifc.ifc_len / sizeof(struct ifreq); --i >= 0; ifr++)c
81     (*fn)(skfd, ifr->ifr_name, args, count);
82     }
83 }
iw_enum_device

 

 从代码和图片可以看到,iwconfig列出来的所有接口是从/proc/dev/net 这个文件中读出来的。

 

posted @ 2021-02-05 15:49  kmist  阅读(640)  评论(0编辑  收藏  举报