凡科免费建站陕西网站建设方案
2026/1/9 4:30:13 网站建设 项目流程
凡科免费建站,陕西网站建设方案,怎么自己在家做网站,西安市网站这个信号量实验是基于 Linux 内核模块的字符设备互斥访问实验#xff0c;核心是用信号量实现多进程对设备的互斥访问#xff0c;步骤如下#xff08;含代码修正、编译、测试全流程#xff09;#xff1a;一、环境准备工具链与内核源码#xff1a;安装对应架构的交叉编译工…这个信号量实验是基于 Linux 内核模块的字符设备互斥访问实验核心是用信号量实现多进程对设备的互斥访问步骤如下含代码修正、编译、测试全流程一、环境准备工具链与内核源码安装对应架构的交叉编译工具链比如实验中ARCHarm64需安装aarch64-linux-gnu-。准备开发板对应的Linux 内核源码并记录其路径后续Makefile中KDIR需填写此路径。二、代码准备修正实验中笔误将实验代码整理为 3 个文件1. 内核模块代码semaphore_test.c修正semaphpre→semaphore、slepp→sleep等笔误#include linux/init.h #include linux/module.h #include linux/fs.h #include linux/cdev.h #include linux/device.h #include linux/uaccess.h #include linux/delay.h #include linux/semaphore.h struct semaphore semaphore_test; // 定义信号量 static int open_test(struct inode *inode, struct file *file) { printk(this is open_test \n); down(semaphore_test); // 获取信号量值-1 return 0; } static ssize_t read_test(struct file *file, char __user *ubuf, size_t len, loff_t *off) { int ret; char kbuf[10] topeet; // 内核缓冲区 printk(read_test \n); ret copy_to_user(ubuf, kbuf, strlen(kbuf)); // 内核→用户空间 if (ret ! 0) { printk(copy_to_user is error \n); } printk(copy_to_user is ok \n); return 0; } static char kbuf[10] {0}; // 全局内核缓冲区 static ssize_t write_test(struct file *file, const char __user *ubuf, size_t len, loff_t *off) { int ret; ret copy_from_user(kbuf, ubuf, len); // 用户→内核空间 if (ret ! 0) { printk(copy_from_user is error\n); } if(strcmp(kbuf, topeet) 0) { // 传topeet则sleep4秒 sleep(4); } else if(strcmp(kbuf, te) 0) { // 传te则sleep2秒 sleep(2); } printk(copy_from_user buf is %s \n, kbuf); return 0; } static int release_test(struct inode *inode, struct file *file) { up(semaphore_test); // 释放信号量值1 printk(this is release_test \n); return 0; } // 字符设备结构 struct chrdrv_test { dev_t dev_num; // 设备号 int major, minor; // 主/次设备号 struct cdev cdev_test; // cdev结构 struct class *class_test; // 设备类 }; struct chrdrv_test devi; // 文件操作集合 static const struct file_operations fops_test { .owner THIS_MODULE, // 所属模块 .open open_test, // 打开设备 .read read_test, // 读设备 .write write_test, // 写设备 .release release_test // 释放设备 }; static int __init atomic_init(void) { sema_init(semaphore_test, 1); // 初始化信号量初始值1互斥信号量 // 自动分配设备号 if(alloc_chrdev_region(devi.dev_num, 0, 1, chrdrv_name) 0) { printk(alloc_chrdev_region is error \n); return -1; } printk(alloc chrdrv region is ok \n); devi.major MAJOR(devi.dev_num); devi.minor MINOR(devi.dev_num); printk(major is %d,minor is %d\n, devi.major, devi.minor); // 初始化cdev cdev_init(devi.cdev_test, fops_test); devi.cdev_test.owner THIS_MODULE; cdev_add(devi.cdev_test, devi.dev_num, 1); // 添加cdev到内核 // 创建设备类和设备文件 devi.class_test class_create(THIS_MODULE, class_test); device_create(devi.class_test, NULL, devi.dev_num, NULL, device_test); return 0; } static void __exit atomic_exit(void) { device_destroy(devi.class_test, devi.dev_num); class_destroy(devi.class_test); cdev_del(devi.cdev_test); unregister_chrdev_region(devi.dev_num, 1); } module_init(atomic_init); module_exit(atomic_exit); MODULE_LICENSE(GPL);2. Makefile编译内核模块makefileexport ARCHarm64 export CROSS_COMPILEaarch64-linux-gnu- obj-m semaphore_test.o KDIR : /path/to/your/linux-kernel-source # 替换为实际内核源码路径 PWD ? $(shell pwd) all: make -C $(KDIR) M$(PWD) modules # 编译模块 clean: make -C $(KDIR) M$(PWD) clean # 清理编译产物3. 应用层测试代码app.c#include stdio.h #include sys/types.h #include sys/stat.h #include fcntl.h #include string.h #include unistd.h int main(int argc, char *argv[]) { int fd; char str[16] {0}; // 打开设备文件argv[1]是设备路径如/dev/device_test fd open(argv[1], O_RDWR); if(fd 0) { printf(file open failed \n); return -1; } // 向设备写数据argv[2]是要写入的内容如test if (strcmp(argv[2], test) 0) { write(fd, topeet, 10); } else if (strcmp(argv[2], te) 0) { write(fd, te, 10); } close(fd); return 0; }三、编译编译内核模块在semaphore_test.c和Makefile所在目录执行make生成semaphore_test.ko内核模块文件。编译应用层程序用交叉编译器编译app.caarch64-linux-gnu-gcc app.c -o app四、部署与测试在开发板上操作上传文件将semaphore_test.ko和app传到开发板比如用scp。加载内核模块insmod semaphore_test.ko执行dmesg查看输出确认模块加载成功会显示major is xxx, minor is 0等信息。测试互斥访问打开2 个终端分别运行测试程序终端 1写 topeet会 sleep4 秒./app /dev/device_test test终端 2写 te会 sleep2 秒./app /dev/device_test te观察dmesg输出终端 2 的进程会等待终端 1 的进程执行release_test释放信号量后才会执行open_test获取信号量实现了多进程对设备的互斥访问。五、收尾测试完成后卸载内核模块rmmod semaphore_test

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询