一个GPIO的驱动,输出高低电平 驱动源代码:GPIO_DRIVER.C #include <linux/fs.h> //#include <linux/iobuf.h> #include <linux/major.h> #include <linux/blkdev.h> #include <linux/capability.h> #include <linux/smp_lock.h> #include <asm/uaccess.h> #include <asm/hardware.h> #include <asm/arch/AT91RM9200.h> #include <linux/vmalloc.h> #include <linux/delay.h> #include <linux/kernel.h> #include <linux/init.h> #include <linux/config.h> #include <linux/module.h> #include <linux/fs.h> #include <linux/ioport.h> #include <linux/sched.h> #include <asm/io.h> #include <asm/arch/gpio.h> #include <linux/delay.h> MODULE_LICENSE("GPL"); #define IOPORT_MAJOR 220 //定义主设备号 typedef char ioport_device_t; static ioport_device_t gpio_devices[257]; #define IOWRITE 1; #define IOCLEAR 2; static int gpio_open(struct inode *inode,struct file *filp) { int minor; minor = MINOR(inode->i_rdev); at91_set_gpio_output(AT91_PIN_PB3,0 ); gpio_devices[minor]++; return 0; } static int gpio_release(struct inode *inode,struct file *filp) { int minor; minor = MINOR(inode->i_rdev); if(gpio_devices[minor]) gpio_devices[minor]--; return 0; } static int gpio_ctl_ioctl(struct inode *inode, struct file *filp, unsigned int command, unsigned long arg) { int err = 0; int minor = MINOR(inode->i_rdev); switch(command) { case IOWRITE: err = at91_set_gpio_value(AT91_PIN_PB3,1);//输出1高电平 break; case IOCLEAR: err = at91_set_gpio_value(AT91_PIN_PB3,0);//输出0低电平 break; } return err; } static struct file_operations gpio_ctl_fops={ owner: THIS_MODULE, ioctl: gpio_ctl_ioctl, open: gpio_open, release: gpio_release, }; static int __init gpio_init(void) { register_chrdev(IOPORT_MAJOR ,"gpiotest",&gpio_ctl_fops); return 0; } static void __exit gpio_exit(void) { unregister_chrdev(IOPORT_MAJOR,"gpiotest"); return 0; } module_init(gpio_init); module_exit(gpio_exit); 测试程序: #include <stdio.h> #include <stdlib.h> #include <sys/ioctl.h> #include <unistd.h> #include <sys/mman.h> #include <sys/types.h> #include <sys/stat.h> #include <fcntl.h> #define DEVICE_GPIOTEST "/dev/gpiotest" #define IOWRITE 1; #define IOCLEAR 2; int main() { int fd; int val=-1; if( (fd=open(DEVICE_GPIOTEST,O_WRITE | O_NONBLOCK)) < 0 ) { perror("can not open device"); exit(1); } while(1) { printf("0:set,1:clear,2:quit;"); scanf("%d",&val); if(val==0) ioctl(fd,IOWRITE,0); else if(val==1) ioctl(fd,IOCLEAR,0); else if(val==2) { close(fd); exit(1); } } } 把生成的驱动.KO和交叉编译的程序下载到板子的/tmp上,输入0的时候是低电平,输入1高电平。
|