c语言 - 我正在尝试进行的新系统调用出现问题(Ubuntu 18.04.1 LTS 内核:4.17.4)



以下是我遵循的步骤。

1) 我运行的是4.15.0内核,所以我更新到了更新的内核。

wget https://www.kernel.org/pub/linux/kernel/v4.x/linux-4.17.4.tar.xz

2) 使用提取内核源代码

sudo tar -xvf linux-4.17.4.tar.xz -C/usr/src/

3) 在cd /usr/src/linux-4.17.4/中创建了一个名为的新目录

然后创建

subc

内部

目录。

在中

subc

我写的代码是从x中减去y if(y>x),否则返回0;这里x是整数,y是二重。

#include <linux/kernel.h>
asmlinkage int sys_sub(int x,double y)
{
printk("working...");
if(y>x){
return ((int)y-x);}
else
return 0;
}

4) 在同一子目录中创建了一个Makefile,并添加了obj-y := sub.o

5) 在中

/usr/src/linux-4.17.4

打开Makefile并将core-y行修改为

core-y += kernel/ mm/ fs/ ipc/ security/ crypto/ block/ sub/

6) 然后在中

cd arch/x86/entry/syscalls/

我打开了

gedit syscall_64.tbl

并且作为第548次系统调用,我进入

548       64        hello          sys_sub

7) 在中

cd include/linux/

我打开了

gedit系统调用.h

并添加

asmlinkage int sys_sub(int x,double y);

作为endif 前的最后一行

8) 我确保在中选择ext4

sudo使菜单配置

9)我使用编译了内核

sudo制作模块安装

10)执行

关闭-r现在

11)已检查

uname-r

以确保我正在运行

4.17.4

我确实是。

12) 我创建了一个C程序来检查系统调用

#include <stdio.h>
#include <linux/kernel.h>
#include <sys/syscall.h>
#include <unistd.h>
int main()
{
int res = syscall(548,10,44);
printf("System call sys_sub returned %d ", res);
return 0;

}

但它只返回

系统调用sys_sub返回0

dmesg

出于某种原因显示Hello World。请帮帮我。我做错了什么?

编辑:

我根据阅读的评论对代码进行了必要的更改。现在我的系统调用代码如下:

#include <linux/kernel.h>
asmlinkage long sys_sub(int a,int b)
{
printk("System call is working...n");
printk("Inputs are %d and %d",a,b);
if(b>a)
{
int c= b-a;
printk("Answer is %d",c);
return c;   
}
printk("Answer is 0");
return 0;
}

我添加了一些print语句,以确保正确调用系统调用。我重新编译了内核并再次运行,现在我得到了

dmesg

输出为

系统调用正在工作。。。输入为1114685272和111468527答案是0

看起来内核得到的是随机垃圾值,而不是我传递的参数,这使得它总是使if循环失败。两个参数的随机值似乎总是相同的!我不知道我现在哪里错了。

在一篇互联网文章中提到编译整个内核,然后编译modules_install。此外,系统调用的返回必须是长的,而不是int。unistd.h文件需要对新的系统调用进行一些更改。这篇文章适用于2.6内核,但可以在http://www.tldp.org/HOWTO/html_single/Implement-Sys-Call-Linux-2.6-i386/

最新更新