/*******************************
*
*杂项设备驱动:miscdevice
*majior=10;
*
* *****************************/
#include <linux/kernel.h>
#include #include #include #include //#include //#include //---------ioctl------------ #include //---------misc_register---- #include //----------cdev-------------- #include //----------delay------------- #include //----------GPIO--------------- #include #include #include #define DEVICE_NAME 'leds' static int led_gpios[] = { S5PV210_MP04(4), S5PV210_MP04(5), S5PV210_MP04(6), S5PV210_MP04(7), };//4个LED #define LED_NUM ARRAY_SIZE(led_gpios) static long fl210_leds_ioctl(struct file *filp, unsigned int cmd, unsigned long arg) { switch(cmd) { case 0: case 1: if (arg > LED_NUM) { return -EINVAL; } gpio_set_value(led_gpios[arg], !cmd);//根据cmd设置LED的暗灭 printk(DEVICE_NAME': %ld %dn', arg, cmd); break; default: return -EINVAL; } return 0; } static struct file_operations fl210_led_dev_fops = { .owner = THIS_MODULE, .unlocked_ioctl = fl210_leds_ioctl, }; //----------------miscdevice------------------ static struct miscdevice fl210_led_dev = { .minor = MISC_DYNAMIC_MINOR, .name = DEVICE_NAME, .fops = &fl210_led_dev_fops, }; //-------------------------------------------- static int __init fl210_led_dev_init(void) { int ret; int i; for (i = 0; i < LED_NUM; i++) { ret = gpio_request(led_gpios[i], 'LED');//申请GPIO口 if (ret) { printk('%s: request GPIO %d for LED failed, ret = %dn', DEVICE_NAME, led_gpios[i], ret); return ret; } s3c_gpio_cfgpin(led_gpios[i], S3C_GPIO_OUTPUT);//设置GPIO口为输出 gpio_set_value(led_gpios[i], 1);//初始化GPIO口的值 } ret = misc_register(&fl210_led_dev);//注册杂项设备 printk(DEVICE_NAME'tinitializedn'); printk('led num is: %dn',LED_NUM); return ret; } static void __exit fl210_led_dev_exit(void) { int i; for (i = 0; i < LED_NUM; i++) { gpio_free(led_gpios[i]);//释放GPIO口 } misc_deregister(&fl210_led_dev);//注销设备 } module_init(fl210_led_dev_init); module_exit(fl210_led_dev_exit); MODULE_LICENSE('GPL'); MODULE_AUTHOR(''); S5PV210_MP04宏定义在linux/arch/arm/mach-s5pv210/include/mach/gpio.h #define S5PV210_MP04(_nr) (S5PV210_GPIO_MP04_START + (_nr)) S5PV210_GPIO_MP04_START = S5PV210_GPIO_NEXT(S5PV210_GPIO_MP03), #define S5PV210_GPIO_NEXT(__gpio) ((__gpio##_START) + (__gpio##_NR) + CONFIG_S3C_GPIO_SPACE + 1) //这里的CONFIG_S3C_GPIO_SPAC是内核配置选项,在.config中可以找到,我的配置为: CONFIG_S3C_GPIO_SPACE = 0 上述代码用到以下几个函数: gpio_set_value(); s3c_gpio_cfgpin(); gpio_request(); gpio_free(); misc_register(); misc_deregister(); 后面会逐个分析。 测试程序如下: #include //#include 'sys/types.h' #include #include #include //#include 'termios.h' //#include 'sys/stat.h' #include #define LED2_ON 0x1 #define LED2_OFF 0x0 main(int argc,char *argv[]) { int fd; if ((fd=open('/dev/leds',O_RDWR /*| O_NDELAY | O_NOCTTY*/)) < 0) { printf('Open Device failed.rn'); exit(1); } else { printf('Open Device successed.rn'); } if (argc<3) { /* code */ printf('Usage: %s exit(1); } if(!strcmp(argv[1],'on')) { printf('led1 will on!!n'); if(ioctl(fd,LED2_ON,atoi(argv[2]))<0) { printf('ioctl err!!n'); } } if(!strcmp(argv[1],'off')) { printf('led1 will off!!n'); if(ioctl(fd,LED2_OFF,atoi(argv[2]))<0) { printf('ioctl err!!n'); } } close(fd); }
上一篇:如何将驱动加入内核
下一篇:linux驱动(七)gpiolib库详解
推荐阅读最新更新时间:2026-03-21 10:56
- LM2904DMR2G 函数发生器运算放大器的典型应用
- DEMO9RS08KA2: DEMO9RS08KA2 Demonstration Board
- MCP73871EV,MCP73871 锂离子电池充电器评估板
- STEVAL-IHM039V1,采用 STM32F415 微控制器的双电机控制演示板
- LTC1606CG 演示板、16 位、250ksps ADC
- RT8086B 3.5A、1.2MHz、同步降压转换器的典型应用
- TS4999EIJT 典型应用 免滤波器立体声 2.8 W D 类音频功率放大器,可选择 3D 音效
- LTM4615,采用 15mm-15mm 封装的完整双路和三路输出负载点模块稳压器
- LTC2415-1IGN 24 位 ADC 的典型应用电路使用电阻器阵列在励磁放大器中提供精确匹配
- 使用 Analog Devices 的 LTC1450LIN 的参考设计

Linux技术手册
【2025 DigiKey创意大赛】 学伴智盒 - 代码
智能机械臂
现代雷达系统的信号设计
BFR340T






京公网安备 11010802033920号