2017-2018-1 20155208 实验四 外设驱动程序设计
2017-12-01 22:21
453 查看
2017-2018-120155208实验四外设驱动程序设计
实验目的
学习资源中全课中的“hqyj.嵌入式Linux应用程序开发标准教程.pdf”中的第十一章在Ubuntu完成资源中全课中的“hqyj.嵌入式Linux应用程序开发标准教程.pdf”中的第十一章的test试验
提交编译,加载模块,卸载模块,测试运行的截图
实验一:
实验要求:
学习资源中全课中的“hqyj.嵌入式Linux应用程序开发标准教程.pdf”中的第十一章提交康奈尔笔记的照片
实验二:
实验要求:
在Ubuntu完成资源中全课中的“hqyj.嵌入式Linux应用程序开发标准教程.pdf”中的第十一章的test试验提交编译,加载模块,卸载模块,测试运行的截图
实验过程:
源代码test_drv.c
#include<linux/module.h> #include<linux/init.h> #include<linux/fs.h> #include<linux/kernel.h> #include<linux/slab.h> #include<linux/types.h> #include<linux/errno.h> #include<linux/cdev.h> #include<asm/uaccess.h> #defineTEST_DEVICE_NAME"test_dev" #defineBUFF_SZ1024 staticstructcdevtest_dev; unsignedintmajor=0; staticchar*data=NULL; /*º¯ÊýÉùÃ÷*/ staticssize_ttest_read(structfile*file,char*buf,size_tcount,loff_t*f_pos); staticssize_ttest_write(structfile*file,constchar*buffer,size_tcount,loff_t*f_pos); staticinttest_open(structinode*inode,structfile*file); staticinttest_release(structinode*inode,structfile*file); staticssize_ttest_read(structfile*file,char*buf,size_tcount,loff_t*f_pos) { intlen; if(count<0) { return-EINVAL; } len=strlen(data); count=(len>count)?count:len; if(copy_to_user(buf,data,count)) { return-EFAULT; } returncount; } staticssize_ttest_write(structfile*file,constchar*buffer,size_tcount,loff_t*f_pos) { if(count<0) { return-EINVAL; } memset(data,0,BUFF_SZ); count=(BUFF_SZ>count)?count:BUFF_SZ; if(copy_from_user(data,buffer,count)) { return-EFAULT; } returncount; } staticinttest_open(structinode*inode,structfile*file) { printk("Thisisopenoperation\n"); data=(char*)kmalloc(sizeof(char)*BUFF_SZ,GFP_KERNEL); if(!data) { return-ENOMEM; } memset(data,0,BUFF_SZ); return0; } staticinttest_release(structinode*inode,structfile*file) { printk("Thisisreleaseoperation\n"); if(data) { kfree(data); data=NULL; } return0; } staticvoidtest_setup_cdev(structcdev*dev,intminor, structfile_operations*fops) { interr,devno=MKDEV(major,minor); cdev_init(dev,fops); dev->owner=THIS_MODULE; dev->ops=fops; err=cdev_add(dev,devno,1); if(err) { printk(KERN_NOTICE"Error%daddingtest%d",err,minor); } } staticstructfile_operationstest_fops= { .owner=THIS_MODULE, .read=test_read, .write=test_write, .open=test_open, .release=test_release, }; intinit_module(void) { intresult; dev_tdev=MKDEV(major,0); if(major) { result=register_chrdev_region(dev,1,TEST_DEVICE_NAME); } else { result=alloc_chrdev_region(&dev,0,1,TEST_DEVICE_NAME); major=MAJOR(dev); } if(result<0) { printk(KERN_WARNING"Testdevice:unabletogetmajor%d\n",major); returnresult; } test_setup_cdev(&test_dev,0,&test_fops); printk("Themajorofthetestdeviceis%d\n",major); return0; } voidcleanup_module(void) { cdev_del(&test_dev); unregister_chrdev_region(MKDEV(major,0),1); printk("Testdeviceuninstalled\n"); }
test.c:
#include<stdio.h> #include<stdlib.h> #include<string.h> #include<sys/stat.h> #include<sys/types.h> #include<unistd.h> #include<fcntl.h> #defineTEST_DEVICE_FILENAME"/dev/test_dev" #defineBUFF_SZ1024 intmain() { intfd,nwrite,nread; charbuff[BUFF_SZ]; fd=open(TEST_DEVICE_FILENAME,O_RDWR); if(fd<0) { perror("open"); exit(1); } do { printf("Inputsomewordstokernel(enter'quit'toexit):"); memset(buff,0,BUFF_SZ); if(fgets(buff,BUFF_SZ,stdin)==NULL) { perror("fgets"); break; } buff[strlen(buff)-1]='\0'; if(write(fd,buff,strlen(buff))<0) { perror("write"); break; } if(read(fd,buff,BUFF_SZ)<0) { perror("read"); break; } else { printf("Thereadstringisfromkernel:%s\n",buff); } }while(strncmp(buff,"quit",4)); close(fd); exit(0); }
Makefile内容:
ifeq($(KERNELRELEASE),) KERNELDIR?=/lib/modules/$(shelluname-r)/build PWD:=$(shellpwd) modules: $(MAKE)-C$(KERNELDIR)M=$(PWD)modules modules_install: $(MAKE)-C$(KERNELDIR)M=$(PWD)modules_install clean: rm-rf*.o*~core.depend.*.cmd*.ko*.mod.c.tmp_versions .PHONY:modulesmodules_installclean else obj-m:=test_drv.o endif
两个脚本:
test_drv_load脚本内容:
#!/bin/sh module="test_drv" device="test_dev" mode="664" group="david" #removestalenodes rm-f/dev/${device} #invokeinsmodwithallargumentswegot #anduseapathname,asnewermodutilsdon'tlookin.bydefault /sbin/insmod-f./$module.ko$*||exit1 major=`cat/proc/devices|awk"\\$2==\"$device\"{print\\$1}"` mknod/dev/${device}c$major0 #giveappropriategroup/permissions chgrp$group/dev/${device} chmod$mode/dev/${device}
test_drv_unload脚本内容:
#!/bin/sh module="test_drv" device="test_dev" #invokermmodwithallargumentswegot /sbin/rmmod$module$*||exit1 #removenodes rm-f/dev/${device} exit0
依次运行,勿忘
make之前要
makeclean
运行成功截图:
实验中的问题及解决过程
问题:第二次运行sudo./test_drv_load时不成功。
解决方式:通过重启虚拟机可以解决这一问题。
相关文章推荐
- 2017-2018-1 20155208 20155212 实验四 外设驱动程序设计
- 2017-2018-1 20155310 20155337《信息安全系统设计基础》实验四外设驱动程序设计
- 2017-2018-1 20155311 实验四 外设驱动程序设计
- 2017-2018-1 20155326 实验四 外设驱动程序设计
- 2017-2018-1 20155209 20155230 实验四 外设驱动程序设计
- 2017-2018-1 20155218 20155205 实验四 外设驱动程序设计
- 2017-2018-1 20155235 20155211 实验四 外设驱动程序设计
- 2017-2018-1 20155336 实验四 外设驱动程序设计
- 2017-2018-1 20155203 20155204 实验四 外设驱动程序设计
- 2017-2018-1 20155214&20155216 实验四:外设驱动程序设计
- 2017-2018-1 20155220实验四——外设驱动程序设计
- 2017-2018-1 20155321 20155330 《信息安全系统设计基础》实验四——外设驱动程序设计
- 2017-2018-1 20155213 实验四 外设驱动程序设计
- 2017-2018-1 20155225 实验四 外设驱动程序设计
- 2017-2018-1 20155201 实验四 外设驱动程序设计
- 2017-2018-1 20155305 实验四 外设驱动程序设计
- 2017-2018-1 20155306 实验四 外设驱动程序设计
- 20155312 20155325 2017-2018 1 实验四 外设驱动程序设计
- 2017-2018-1 20155304 20155332 实验四 外设驱动程序设计
- 2017-2018-1 20155317 实验四 外设驱动程序设计