linux c 获取网络接口信息 ioct l函数 ifreq ifconf 结构体 简介
目录
ioctl
struct ifreq
struct ifconf
ioctl
原型如下:
#include <sys/ioctl.h>
int ioctl(int fd, int request, ...);
参数:
fd : 文件描述符
request: 表示要请求的信息。如IP地址、网络掩码等
... : 后面的可变参数根据request而定
比如我们请求所有网络接口的清单:
struct ifconf IoCtlReq;
...
ioctl( Sock, SIOCGIFCONF, &IoCtlReq )
与接口相关的request如下表所示
SIOCGIFCONF SIOCSIFADDR SIOCGIFADDR SIOCSIFFLAGS SIOCGIFFLAGS SIOCSIFDSTADDR SIOCGIFDSTADDR SIOCGIFBRDADDR SIOCSIFBRDADDR SIOCGIFNETMASK SIOCSIFNETMASK SIOCGIFMETRIC SIOCSIFMETRIC SIOCGIFMTU SIOCxxx |
获取所有接口的清单 设置接口地址 获取接口地址 设置接口标志 获取接口标志 设置点到点地址 获取点到点地址 获取广播地址 设置广播地址 获取子网掩码 设置子网掩码 获取接口的测度 设置接口的测度 获取接口MTU (还有很多取决于系统的实现) |
struct ifconf struct ifreq struct ifreq struct ifreq struct ifreq struct ifreq struct ifreq struct ifreq struct ifreq struct ifreq struct ifreq struct ifreq struct ifreq struct ifreq |
struct ifreq
结构体 struct ifreq用来保存某个接口的信息。
// if.h
/** Interface request structure used for socket* ioctl's. All interface ioctl's must have parameter* definitions which begin with ifr_name. The* remainder may be interface specific.*/
struct ifreq {
#define IFHWADDRLEN 6union{char ifrn_name[IFNAMSIZ]; /* if name, e.g. "en0" */} ifr_ifrn;union {struct sockaddr ifru_addr;struct sockaddr ifru_dstaddr;struct sockaddr ifru_broadaddr;struct sockaddr ifru_netmask;struct sockaddr ifru_hwaddr;short ifru_flags;int ifru_ivalue;int ifru_mtu;struct ifmap ifru_map;char ifru_slave[IFNAMSIZ]; /* Just fits the size */char ifru_newname[IFNAMSIZ];void __user * ifru_data;struct if_settings ifru_settings;} ifr_ifru;
};
#define ifr_name ifr_ifrn.ifrn_name /* interface name */
#define ifr_hwaddr ifr_ifru.ifru_hwaddr /* MAC address */
#define ifr_addr ifr_ifru.ifru_addr /* address */
#define ifr_dstaddr ifr_ifru.ifru_dstaddr /* other end of p-p lnk */
#define ifr_broadaddr ifr_ifru.ifru_broadaddr /* broadcast address */
#define ifr_netmask ifr_ifru.ifru_netmask /* interface net mask */
#define ifr_flags ifr_ifru.ifru_flags /* flags */
#define ifr_metric ifr_ifru.ifru_ivalue /* metric */
#define ifr_mtu ifr_ifru.ifru_mtu /* mtu */
#define ifr_map ifr_ifru.ifru_map /* device map */
#define ifr_slave ifr_ifru.ifru_slave /* slave device */
#define ifr_data ifr_ifru.ifru_data /* for use by interface */
#define ifr_ifindex ifr_ifru.ifru_ivalue /* interface index */
#define ifr_bandwidth ifr_ifru.ifru_ivalue /* link bandwidth */
#define ifr_qlen ifr_ifru.ifru_ivalue /* Queue length */
#define ifr_newname ifr_ifru.ifru_newname /* New name */
#define ifr_settings ifr_ifru.ifru_settings /* Device/proto settings*/
ifr_name 标识了某一接口。
可以通过ioctl获取该接口的信息。如:
ioctl(Sock, SIOCGIFNETMASK, &IfReq);//获取网络接口地址掩码
该代码需要先对IfReq->ifr_name赋值,然后获取与IfReq->ifr_name向匹配的网络接口 的地址掩码
struct ifconf
结构体struct ifconf通常用来保存所有接口信息
// if.h
/** Structure used in SIOCGIFCONF request.* Used to retrieve interface configuration* for machine (useful for programs which* must know all networks accessible).*/
struct ifconf {int ifc_len; /* size of buffer */union {char __user *ifcu_buf;struct ifreq __user *ifcu_req;} ifc_ifcu;
};
#define ifc_buf ifc_ifcu.ifcu_buf /* buffer address */
#define ifc_req ifc_ifcu.ifcu_req /* array of structures */
该结构体可以用来获取所哟网络接口的名字和信息(不是全部信息,是ip地址)
实例:
#include <sys/types.h>
#include <sys/ioctl.h>
#include <sys/socket.h>
#include <net/if.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <netdb.h>
#include <string.h>
#include <fcntl.h>
#include <string.h>
#include <errno.h>
typedef uint32_t uint32;
#define MAX_IF 10
int main()
{struct ifreq ifVec[MAX_IF];//用来保存所有接口int sock = -1;if ((sock = socket( AF_INET, SOCK_DGRAM, 0 )) < 0){fprintf(stderr, "Error:%d, cannot open RAM;\n");}// get if vectorstruct ifconf ioIfConf;ioIfConf.ifc_buf = (void *)ifVec;ioIfConf.ifc_len = sizeof(ifVec);printf("Len:%d\n", ioIfConf.ifc_len);if (ioctl(sock, SIOCGIFCONF, &ioIfConf) < 0) //获取所有网络接口信息{fprintf(stderr, "Error:%d ioctl IFCONF\n");}printf("Len:%d\n", ioIfConf.ifc_len); // 和前面到len对比,发现ioctl修改里len到大小//循环打印每个网络接口到信息{struct ifreq *ifPt;struct ifreq *ifEndPt;ifPt = ifVec;ifEndPt = (void *)((char *)ifVec + ioIfConf.ifc_len);for (ifPt = ifVec; ifPt < ifEndPt; ifPt++){struct ifreq ifReq;if (ifPt->ifr_addr.sa_family != AF_INET){continue;}// Temp keepers of interface params...uint32 u32_addr, u32_mask;/* 打印ip地址 */char ipDotBuf[16], subnetDotBuf[16], maskDotBuf[16]; // 保存点分十进制到ip地址u32_addr = ((struct sockaddr_in *)&ifPt->ifr_addr)->sin_addr.s_addr;inet_ntop(AF_INET, &u32_addr, ipDotBuf, (socklen_t )sizeof(ipDotBuf));printf("IP Address: %s\n", ipDotBuf);/* 打印地址掩码 */bzero(&ifReq, sizeof(struct ifreq));memcpy(ifReq.ifr_name, ifPt->ifr_name, sizeof(ifReq.ifr_name));if (ioctl(sock, SIOCGIFNETMASK, &ifReq ) < 0){fprintf(stderr, "Error: %d, cannot get mask\n", errno);}else{u32_mask = ((struct sockaddr_in *)&ifReq.ifr_addr)->sin_addr.s_addr;inet_ntop(AF_INET, &u32_mask, maskDotBuf, (socklen_t )sizeof(maskDotBuf));printf("Mask: %s\n", maskDotBuf);}/* 打印MTU */bzero(&ifReq, sizeof(struct ifreq));memcpy(ifReq.ifr_name, ifPt->ifr_name, sizeof(ifReq.ifr_name));if (ioctl(sock, SIOCGIFMTU, &ifReq ) < 0){fprintf(stderr, "Error: %d, cannot get MTU\n", errno);}else{printf("SIOCGIFMTU:%d\n", ifReq.ifr_mtu);}/* 其他信息的打印方式与掩码和MTU相同 */}}
}
运行结果:
windeal@ubuntu:~/Windeal/apue$ ./exe
Len:320
Len:64
IP Address: 127.0.0.1
Mask: 255.0.0.0
SIOCGIFMTU:16436
IP Address: 172.17.92.198
Mask: 255.255.254.0
SIOCGIFMTU:1500
windeal@ubuntu:~/Windeal/apue$
linux c 获取网络接口信息 ioct l函数 ifreq ifconf 结构体 简介相关推荐
- 获取网络接口信息——ioctl()函数与结构体struct ifreq、 struct ifconf
http://blog.csdn.net/windeal3203/article/details/39320605 Linux 下 可以使用ioctl()函数 以及 结构体 struct ifreq ...
- Linux编程获取网络信息总结
Linux下C获取所有可用网卡信息 在Linux下开发网络程序时,经常会遇到需要取本地网络接口名.IP.广播地址 .子网掩码或者MAC地址等信息的需求,最常见的办法是配合宏SIOCGIFHWADDR. ...
- 【☀️C语言函数传参の结构体数组篇☀️】
背景介绍 C语言中函数参数传递的两种方式("引用传递做函数参数"是C++的特性,C语言不支持.) (1)传值,就是把你的变量的值传递给函数的形式参数,实际就是用变量的值来新生成一个 ...
- Golang——结构体创建与初始化、结构体与数组、结构体与切片、结构体与map、结构体作为函数参数、结构体方法、结构体方法继承
结构体: 结构体是由一系列具有相同类型或不同类型的数据构成的数据集合 结构体可以很好的管理一批有联系的数据,使用结构体可以提高程序的易读性,类似于Java的类一样 不能在结构体直接赋值 字段名必须唯一 ...
- C语言试题五十二之学生的记录由学号和成绩组称个,n名大学生得数据已在主函数中放入结构体数组a中,请编写函数fun,它的功能时:按分数的高低排列学生的记录,高分在前。
1. 题目 请编写一个函数void function(Student a[], int n),其功能时:学生的记录由学号和成绩组称个,n名大学生得数据已在主函数中放入结构体数组a中,请编写函数fun, ...
- c语言 由函数组成的数组,学生的记录由学号和成绩组成,N名学生的数据已在主函数中放入结构体数组s中,请编写函数fun(),它的_考题宝...
学生的记录由学号和成绩组成,N名学生的数据已在主函数中放入结构体数组s中,请编写函数fun(),它的功能是按分数的高低排列学生的记录,低分在前. 注意:部分源程序给出如下. 请勿改动主函数main和其 ...
- 【Linux 内核 内存管理】内存映射相关数据结构 ③ ( vm_area_struct 结构体成员分析 | shared 成员 | anon_vma_chain 成员 | anon_vma 成员 )
文章目录 一.vm_area_struct 结构体成员分析 1.shared 成员 2.anon_vma_chain 成员 3.anon_vma 成员 二.vm_area_struct 结构体完整源码 ...
- 【C++】结构体 - 定义和使用,结构体数组,结构体指针,结构体嵌套结构体,结构体做函数参数,结构体 const
文章目录 1. 定义和使用 2. 结构体数组 3. 结构体指针 4. 结构体嵌套结构体 5. 结构体做函数参数 6. 结构体 const 1. 定义和使用 结构体属于用户自定义的数据类型,允许用户存储 ...
- 三菱R系列PLC程序 全部采用ST语言编写,内部使用函数块和结构体,程序思路清晰
三菱R系列PLC程序 全部采用ST语言编写,内部使用函数块和结构体,程序思路清晰,简洁明了. 通过结构体和函数块的使用,可以使您在程序编写水平得到很大提高. ST语言是PLC后续的主流语言,是日后编程 ...
最新文章
- 计算机科学和Python编程导论(一) 计算机相关理论
- 计算机视觉大规模爆发,6大细分领域将撑起725亿元市场
- nodejs使用redis数据库缓存数据
- 【 Markdown 】Markdown 编辑器语法常用格式 ( 整理中 ... )
- Spring Cloud Alibaba - 09 Ribbon 饥饿加载及其他配置参数解读
- maven——pom.xml
- html制作柱状图教程,基于Echarts的HTML5 Canvas折线图柱状图DEMO演示
- jQuery多选列表框插件Multiselect
- C++ Exercises(十六)---Ethernet帧包结构解析
- 时刻警戒当前终端目录
- context menu与submenu区别
- Mr.Panda and TubeMaster Gym - 101194J (二分染色有源汇上下界最大费用流)
- OpenNebula概述
- android app 嵌入广告,流氓来了!如何拯救手机中嵌入广告的应用
- 【机器学习】注意力机制
- 错觉图片生成实验 - 隐形的黑点
- c语言中余数恒等于1,恒等于符号怎么打就是“≡”符号在windows里怎么打出来具体到搜狗里怎么打,麻烦说细点儿...
- loj3059/bzoj5494/洛谷P5294 [HNOI2019]序列 单调栈+主席树
- 一种巧妙的解决方案,一键恢复Win11中消失不见的“Microsoft Store”微软应用商店
- Eclipse/Myeclipse自定义JSP模板