我想使用 copy_to_user() 将平台网络设备的一些信息复制到用户空间中的缓冲区。但我不知道内核如何知道 copy_to_user() 使用的“to”指针。 驱动程序的 ioctl() 需要 struct ifreq 作为参数。我知道我可以初始化 ifreq.name 来找到驱动程序的 ioctl()。但是我如何将“to”指针传递给内核,恰好是驱动程序的 ioctl()?
最佳答案
结构 ifreq 看起来像这样:
struct ifreq {
char ifr_name[IFNAMSIZ];/* Interface name */
union {
struct sockaddrifr_addr;
struct sockaddrifr_dstaddr;
struct sockaddrifr_broadaddr;
struct sockaddrifr_netmask;
struct sockaddrifr_hwaddr;
short ifr_flags;
int ifr_ifindex;
int ifr_metric;
int ifr_mtu;
struct ifmapifr_map;
char ifr_slave[IFNAMSIZ];
char ifr_newname[IFNAMSIZ];
char * ifr_data;
};
};
如果您要实现现有的 ioctl 命令,则必须弄清楚您应该使用 union 体中的哪些成员,包括用户空间和内核。
如果您要实现自己的 ioctl 命令,则可以使用 ifr_data
。调用者(在用户空间中)将成员设置为指向本地缓冲区,您将在内核中使用 copy_to_user() 填充该缓冲区(即 ifr_data 是您要查找的 to。 )
即用户空间做
char buf[128];
struct ifreq req;
strcpy(req.ifr_name,"eth0");
req.ifr_data = buf;
ioctl(fd, SIOCMYIOCTL, &ifr);
这里的缓冲区只是一个固定大小的数组,如果您需要更大的灵 active ,您当然可以使用结构,只要用户空间和您的内核 ioctl() 同意 ifr_data
是什么。
struct my_ioctl_data {
int a, b, c;
};
struct my_ioctl_data data;
struct ifreq req;
strcpy(req.ifr_name,"eth0");
req.ifr_data = (char*)&data;
ioctl(fd, SIOCMYIOCTL, &ifr);
关于c - 如何将用户空间中缓冲区的地址传递给内核,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/25640944/