我试图在我的玩具文件系统模块中调用ioctl函数。我只想让这个ioctl设置一个由调用者传入的变量。到目前为止,我已经设置了ioctl基础设施,允许我进行ioctl调用。我在我的模块中有这个函数来处理ioctl。
int ospfs_ioctl(struct inode *inode, struct file *filp,
unsigned int cmd, unsigned long arg)
{
if(cmd == OSPFSIOCRASH)
{
eprintk("crash: %ld\n", arg);
return 0;
}
else
return -ENOTTY;
}
我的测试功能看起来像这样。
#include <stdio.h>
#include <fcntl.h>
#include <sys/ioctl.h>
#define OSPFSIOCRASH 42
int main()
{
int fd = open("/tmp/cs111/lab3-thief/test/hello.txt", O_RDWR);
printf("ioctl call: %d\n", ioctl(fd, OSPFSIOCRASH, 100));
close(fd);
}
我希望输出为
crash: 100
ioctl call: 0
但输出实际上是
crash: 0
ioctl call: 0
我打赌我做的事情很简单。有人可以帮忙指出问题是什么吗?谢谢你。
答案 0 :(得分:0)
这可能不是解决问题的解决方案,但基于您的问题和评论中的有限信息,我可以收集这些信息。
根据问题和评论,看起来您已经以这种方式定义了struct file_operations
结构:
struct file_operations fops = { .ioctl=ospfs_ioctl };
您ospfs_ioctl
的签名表明您正在使用较旧的ioctl。
使用最新的内核(至少在2.6.35+之后),建议使用.unlocked_ioctl
代替.ioctl
。
struct file_operations fops = { .unlocked_ioctl=ospfs_ioctl };
ospfs_ioctl
函数的定义将更改为:
long ospfs_ioctl(struct file *filp, unsigned int cmd, unsigned long arg)
可以找到unlocked_ioctl
与常规ioctl之间的差异here。简而言之,在调用ioctl之前不会使用可怕的BKL
。
根据Chris Dodd
的建议,你应该仔细检查你如何定义OSPFIOCRASH
。推荐的方法是使用_IO(magic, some_num_for_ioctl)
答案 1 :(得分:0)
根据克里斯·多德的建议,我将#define OSPFIOCRASH 42
更改为#define OSPFSIOCRASH _IO(magic, 0)
,从而获得了理想的行为。