树莓派3 Model B执行make命令编译内核模块报错求助
解决树莓派内核模块编译错误及代码修正方案
一、先解决make编译报错问题
错误核心是/lib/modules/6.1.21-v7+/build目录不存在,这是因为树莓派默认未安装对应内核版本的头文件,按以下步骤修复:
- 更新系统包列表:
sudo apt update - 安装匹配当前内核的头文件:
该包会自动适配你当前运行的sudo apt install raspberrypi-kernel-headers6.1.21-v7+内核,安装后/lib/modules/$(uname -r)/build会自动指向正确的头文件目录。 - 若安装后仍报错,手动创建软链接补全路径:
sudo ln -s /usr/src/linux-headers-6.1.21-v7+ /lib/modules/6.1.21-v7+/build
二、代码中的致命问题(编译通过后必现错误)
你的代码意图是拦截鼠标事件,但存在多处不符合内核模块规范的问题,必须修正才能正常工作:
- 重复定义
struct input_handler<linux/input.h>中已经定义了该结构体,删除代码中重复定义的这段:static struct input_handler { void (*event)(struct input_handler *, void *, struct input_event *); const char *name; const struct input_device_id *id_table; }; input_get_handler参数错误
该函数接收的是struct input_device指针,而非设备名,需先通过设备名获取设备指针:struct input_dev *dev = input_find_device_by_name(NULL, "mouse0"); if (!dev) { printk(KERN_ERR "Failed to find mouse0\n"); return -ENODEV; } old_handler = dev->handler; input_get_handler(old_handler);- 必须启用
MODULE_LICENSE
注释掉该行会导致内核拒绝加载模块,取消注释:MODULE_LICENSE("GPL"); - 事件拦截逻辑错误
返回0会让事件继续向下传递,达不到拦截效果,修改返回值:static int block_mouse_event(struct input_handler *handler, void *data, struct input_event *event) { // 返回非0值阻止事件传递 return -ENODEV; } id_table不能为空
需定义匹配鼠标设备的规则,否则自定义handler无法捕获鼠标事件:
同时在static const struct input_device_id block_mouse_ids[] = { { .evbit = BIT_MASK(EV_KEY) | BIT_MASK(EV_REL), .keybit = BIT_MASK(BTN_MOUSE), }, { } // 终止项 }; MODULE_DEVICE_TABLE(input, block_mouse_ids);block_handler中设置.id_table = block_mouse_ids,
三、修正后的完整代码
#include <linux/module.h> #include <linux/kernel.h> #include <linux/input.h> static struct input_handler *old_handler; static struct input_dev *mouse_dev; static int block_mouse_event(struct input_handler *handler, void *data, struct input_event *event) { // 拦截鼠标输入事件,阻止事件传递 return -ENODEV; } static const struct input_device_id block_mouse_ids[] = { { .evbit = BIT_MASK(EV_KEY) | BIT_MASK(EV_REL), .keybit = BIT_MASK(BTN_MOUSE), }, { } }; MODULE_DEVICE_TABLE(input, block_mouse_ids); static struct input_handler block_handler = { .event = block_mouse_event, .name = "block_mouse_handler", .id_table = block_mouse_ids, }; static int __init mouse_block_init(void) { printk(KERN_INFO "Mouse block module initialized\n"); // 查找mouse0设备 mouse_dev = input_find_device_by_name(NULL, "mouse0"); if (!mouse_dev) { printk(KERN_ERR "Failed to locate mouse0 device\n"); return -ENODEV; } // 保存原handler old_handler = mouse_dev->handler; if (old_handler) { input_get_handler(old_handler); } // 注册自定义handler return input_register_handler(&block_handler); } static void __exit mouse_block_exit(void) { printk(KERN_INFO "Mouse block module removed\n"); // 注销handler input_unregister_handler(&block_handler); // 释放原handler if (old_handler) { input_put_handler(old_handler); old_handler = NULL; } if (mouse_dev) { input_put_device(mouse_dev); mouse_dev = NULL; } } module_init(mouse_block_init); module_exit(mouse_block_exit); MODULE_LICENSE("GPL"); MODULE_DESCRIPTION("Mouse Event Block Module"); MODULE_AUTHOR("Your Name");
内容的提问来源于stack exchange,提问作者Jasmine58850_01
相关产品推荐
相关产品推荐

