Linux 内核裁剪与功能扩展实验报告
Linux 内核裁剪与功能扩展实验报告
一、实验目的
- 熟悉 Linux 内核源码的结构与编译方法。
- 掌握内核裁剪的基本思想与方法。
- 本实验要求:禁止使用
menuconfig
等配置工具,只能通过修改内核源码实现裁剪。
- 本实验要求:禁止使用
- 学习如何扩展内核功能,以验证修改效果。
二、实验环境
- VMware Workstation / Fusion
- Ubuntu 22.04.5 LTS (Server,无图形界面)
- gcc、make、binutils、libncurses-dev、bison、flex、libssl-dev、libelf-dev
三、实验步骤
1. 内核源码准备
cd ~
wget https://cdn.kernel.org/pub/linux/kernel/v6.x/linux-6.1.101.tar.xz
tar -xvf linux-6.1.101.tar.xz
cd linux-6.1.101
复制当前内核配置作为基准:
cp /boot/config-$(uname -r) .config
yes "" | make oldconfig
2. 源码级内核裁剪(禁止使用 menuconfig)
实验要求:通过 直接修改 .config
文件或源码控制宏 来裁剪。
(1) 裁剪文件系统
打开 .config
,搜索并修改:
# CONFIG_REISERFS_FS is not set
# CONFIG_JFS_FS is not set
# CONFIG_HFS_FS is not set
# CONFIG_HFSPLUS_FS is not set
这些文件系统在 VM 实验环境中不需要。
(2) 裁剪网络协议
同样在 .config
中注释掉:
# CONFIG_IPDDP is not set
# CONFIG_APPLETALK is not set
# CONFIG_DECNET is not set
# CONFIG_BT is not set
(3) 裁剪驱动
若虚拟机仅需要 virtio 驱动,可关掉多余的硬件支持:
# CONFIG_NET_VENDOR_3COM is not set
# CONFIG_NET_VENDOR_ADAPTEC is not set
# CONFIG_NET_VENDOR_INTEL is not set
# CONFIG_WLAN is not set
(4) 通过修改 Kconfig/Makefile 禁用模块
例如:在 drivers/net/Kconfig
里直接注释不需要的驱动配置项;
或在 drivers/net/Makefile
去掉对应的 obj-$(CONFIG_xxx)
行。
3. 内核功能扩展(增加一个系统调用)
(1) 新增系统调用函数
编辑 kernel/sys.c
末尾添加:
#include <linux/kernel.h>
#include <linux/syscalls.h>SYSCALL_DEFINE0(hello_syscall)
{printk(KERN_INFO "Hello, Linux kernel is modified (by source editing)!\n");return 2025;
}
(2) 注册系统调用号
修改 arch/x86/entry/syscalls/syscall_64.tbl
:
找到未使用编号,例如 449:
449 common hello_syscall sys_hello_syscall
(3) 添加声明
在 include/linux/syscalls.h
中添加:
asmlinkage long sys_hello_syscall(void);
4. 编译与安装内核
make -j$(nproc)
sudo make modules_install
sudo make install
sudo update-grub
sudo reboot
5. 验证实验结果
(1) 验证裁剪成果:
进入新内核后,检查裁剪掉的特性不再存在:
zcat /proc/config.gz | grep REISERFS
输出应为空或未设置。
(2) 验证系统调用:
编写用户态测试程序:
// hello_test.c
#include <stdio.h>
#include <unistd.h>
#include <sys/syscall.h>#define __NR_hello_syscall 449int main() {long res = syscall(__NR_hello_syscall);printf("Syscall returned: %ld\n", res);return 0;
}
编译运行:
gcc hello_test.c -o hello_test
./hello_test
输出:
Syscall returned: 2025
同时内核日志:
dmesg | tail -n 5
应出现:
Hello, Linux kernel is modified (by source editing)!
四、实验结果与截图说明
- 内核配置文件中不再包含 ReiserFS 等裁剪项。
uname -r
显示新编译内核版本。- 用户态程序成功调用新增系统调用,返回值 2025。
dmesg
日志显示内核输出。
五、实验分析与思考
-
裁剪方法对比
- 使用
menuconfig
是最常见的方法,但本实验通过 直接编辑.config
与源码 达成效果,更加底层。 - 这种方式适合自动化脚本、批量裁剪场景。
- 使用
-
扩展功能的思考
- 我们通过新增系统调用验证了可以修改内核源代码。
- 实际上,更推荐通过 内核模块(LKM) 扩展功能,而不是直接修改内核源码,因为维护性更好。
-
安全性考虑
- 新增的系统调用默认对所有用户可见,如果涉及敏感功能,应增加访问权限检查。