+ -
当前位置:首页 → 问答吧 →  模块问题

模块问题

时间:2003-05-30

来源:互联网

我抄写了一测试程序,以前好像还能成功,现在竟然不行了,谁帮我看看,这是哪里有问题,程序如下:
#include linux/kernel.h

#define __NO_VERSION__
#include linux/version.h
#include linux/module.h
#if CONFIG_MODVERSIONS==1
#define MODVERSIONS
#include linux/modversions.h
#endif

int init_module()
{
printk("Hello,world-this is the kernel speaking\n");
return 0;
}

void cleanup_module()
{
printk("Short is the life of a kernel module\n");
}
编译结果如下:
#gcc -Wall -DMODULE -D__KERNEL__ -DLINUX -o start.o start.c
start.c: In function `init_module':
start.c:13: warning: implicit declaration of function `printk'
/usr/lib/gcc-lib/i386-redhat-linux/3.2.2/../../../crt1.o(.text+0x18): In function `_start':
../sysdeps/i386/elf/start.S:77: undefined reference to `main'
/tmp/ccM33akw.o(.text+0xf): In function `init_module':
: undefined reference to `printk'
/tmp/ccM33akw.o(.text+0x2c): In function `cleanup_module':
: undefined reference to `printk'
collect2: ld returned 1 exit status

implicit declaration是怎么回事啊?
模块的版本不匹配该怎么解决啊?我用的是redhat9.0,编译时说该程序是被内核版本4.2.20编译的,但现在的版本是4.2.20-8,可我就是在这个系统上编译的啊?
附带问一下:怎么把gcc编译输出的内容重定向到文件中去啊?

作者: Lazybones   发布时间: 2003-05-30

u need -I/usr/src/linux. make sure u have ../linux dir.


gcc .... &>s (s is u filename, no space between & and >)

作者: cheungming   发布时间: 2003-05-31

[root@Lazybones root]# gcc -Wall -O2 -DMODULE -D__KERNEL__ -c -I/usr/src/linux-2.4.20-8 -o start.o start.c
start.c: In function `init_module':
start.c:11: warning: implicit declaration of function `printk'
[root@Lazybones root]# insmod start.o
start.o: kernel-module version mismatch
start.o was compiled for kernel version 2.4.20
while this kernel is version 2.4.20-8.

还是有这样的问题啊(我的是redhat9.0)?cheungming老兄,你说的是解决哪个问题的啊,就是包括那个linux文件夹的?原来文件有问题,现在改正如下:
#include <linux/kernel.h>

#include <linux/module.h>
#if CONFIG_MODVERSIONS==1
#define MODVERSIONS
#include <linux/modversions.h>
#endif

int init_module()
{
printk("<1>Hello,world-this is the kernel speaking\n");
return 0;
}

void cleanup_module()
{
printk("<1>Short is the life of a kernel module\n");
}

编译就出上面的错,但是能够强制安装成功,不知版本匹配错误该怎么解决?

附带问题我终于知道了,非常感谢,真是大好人啊

作者: Lazybones   发布时间: 2003-05-31

我在其它模块中也遇到这两种问题,如menmen,read等函数等
这些函数在9.0中是包含在哪些头文件里啊?

作者: Lazybones   发布时间: 2003-05-31

第一个问题,gcc的-I参数加错了:你用的是-I/usr/src/linux-2.4.20-8,这样会导致gcc直接到/usr/src/linux-2.4.20-8下面找头文件,比如去找/usr/src/linux-2.4.20-8/linux/version.h,这样当然找不到,于是就又到系统默认目录/usr/include下面找,结果找到了/usr/include/linux/version.h。但是两个version.h是不一样的,前面那个说版本是2.4.20-8,后面那个说版本是2.4.20,于是就出现了版本不一致的问题。正确的做法应该是-I/usr/src/linux-2.4.20-8/include,不要忘了后面的/include。

作者: zhuangsihua   发布时间: 2003-07-20

第二个问题,头文件顺序错误:
modversion.h的作用是通过宏定义,把所有需要校验和的内核符号加上校验和,比如它会#define printk printk_R12345678,这样,在include了modversion.h之后出现的所有printk(包括函数声明和函数调用)就会自动变成带校验和的版本了。而你原来是先include了kernel.h再include modversion.h,于是kernel.h中只是声明了printk,没有声明printk_R12345678,这就是出现“隐含声明”的原因。正确的做法是先include modversion.h再include kernel.h和module.h。
另外,还要在一开始include config.h,这样CONFIG_MODVERSIONS才会有意义。

作者: zhuangsihua   发布时间: 2003-07-20

源码:
代码:
//#define __NO_VERSION__
#include <linux/version.h>
#include <linux/config.h>
#if CONFIG_MODVERSIONS==1
#define MODVERSIONS
#include <linux/modversions.h>
#endif
#include <linux/module.h>
#include <linux/kernel.h>

int init_module()
{
 printk("Hello,world-this is the kernel speaking\n");
 return 0;
}

void cleanup_module()
{
 printk("Short is the life of a kernel module\n");
}
编译命令:
gcc -Wall -DMODULE -D__KERNEL__ -DLINUX -c -o start.o start.c -I /usr/src/linux-2.4/include/
另外,__NO_VERSION__宏好像已经不用了,反正编译出来的结果和有没有这个宏没有关系。不知哪位大侠帮忙解释一下这个问题?谢谢了。

作者: zhuangsihua   发布时间: 2003-07-20