三星6410 led平台驱动
2016-10-13 13:55
260 查看
源程序
1、应用程序led.c
2、驱动程序led_dev.c
3、设备树配置
4、执行驱动的makefile
5、启动tftp和nfs执行程序
“`
执行sudo service tftpd-hpa restart命令,开启tftp服务
重新驱动nfs服务:sudo /etc/init.d/nfs-kernel-server restart
下载驱动,创建设备文件,执行应用程序,即可
1、应用程序led.c
#include <stdio.h> #include <fcntl.h> #include <unistd.h> #include <stdlib.h> #include <sys/ioctl.h> #define LED_MAGIC 'L' #define LED_ON _IOW(LED_MAGIC, 0, int) #define LED_OFF _IOW(LED_MAGIC, 1, int) int main(int argc, char **argv) { int fd; fd = open("/dev/led", O_RDWR); if (fd < 0) { perror("open"); exit(1); } while(1) { ioctl(fd, LED_ON); usleep(100000); ioctl(fd, LED_OFF); usleep(100000); } return 0; }
2、驱动程序led_dev.c
#include <linux/kernel.h> #include <linux/module.h> #include <linux/fs.h> #include <linux/cdev.h> #include <linux/platform_device.h> #include <linux/of_device.h> #include <asm/io.h> #include <asm/uaccess.h> MODULE_LICENSE("Dual BSD/GPL"); #define LED_MAGIC 'L' #define LED_ON _IOW(LED_MAGIC, 0, int) #define LED_OFF _IOW(LED_MAGIC, 1, int) #define LED_MA 500 #define LED_MI 0 #define LED_NUM 1 //#define FS4412_GPX2CON 0x11000C40 //#define FS4412_GPX2DAT 0x11000C44 static unsigned int *gpx2con; static unsigned int *gpx2dat; //存放映射的地址 struct cdev cdev; static int s5pv210_led_open(struct inode *inode, struct file *file) { return 0; } static int s5pv210_led_release(struct inode *inode, struct file *file) { return 0; } static long s5pv210_led_unlocked_ioctl(struct file *file, unsigned int cmd, unsigned long arg) { switch (cmd) { case LED_ON: writel(readl(gpx2dat) | 1 << 7, gpx2dat); break; case LED_OFF: writel(readl(gpx2dat) & ~(1 << 7), gpx2dat); break; } return 0; } struct file_operations s5pv210_led_fops = { .owner = THIS_MODULE, .open = s5pv210_led_open, .release = s5pv210_led_release, .unlocked_ioctl = s5pv210_led_unlocked_ioctl, }; static int led_init(struct platform_device *pdev) { /****************设备号初始化**********************************/ dev_t devno = MKDEV(LED_MA, LED_MI); int ret = register_chrdev_region(devno, LED_NUM, "led"); if (ret < 0) { printk("register_chrdev_region\n"); return ret; } cdev_init(&cdev, &s5pv210_led_fops); cdev.owner = THIS_MODULE; ret = cdev_add(&cdev, devno, LED_NUM); if (ret < 0) { printk("cdev_add\n"); goto err1; } **********************根据设备树获取地址***************************/ struct resource * p = platform_get_resource(pdev,IORESOURCE_MEM,0); gpx2con = ioremap(p->start, 4); if (gpx2con == NULL) { printk("ioremap gpx2con\n"); ret = -ENOMEM; goto err2; } struct resource * q = platform_get_resource(pdev,IORESOURCE_MEM,1); gpx2dat = ioremap(q->start, 4); if (gpx2dat == NULL) { printk("ioremap gpx2dat\n"); ret = -ENOMEM; goto err3; } writel((readl(gpx2con) & ~(0xf << 28)) | (0x1 << 28), gpx2con); writel(readl(gpx2dat) & ~(0x1<<7), gpx2dat); printk("Led init\n"); return 0; err3: iounmap(gpx2con); err2: cdev_del(&cdev); err1: unregister_chrdev_region(devno, LED_NUM); return ret; } static void led_exit(void) { dev_t devno = MKDEV(LED_MA, LED_MI); iounmap(gpx2dat); iounmap(gpx2con); cdev_del(&cdev); unregister_chrdev_region(devno, LED_NUM); printk("Led exit\n"); } //module_init(s5pv210_led_init); //module_exit(s5pv210_led_exit); static const struct of_device_id fs4412_dt_of_matches[] = { { .compatible = "led"}, //这个字符串 必须与设备树里的字符串一致 {}, }; MODULE_DEVICE_TABLE(of, fs4412_dt_of_matches); struct platform_driver led_platform_driver = { .driver = { .name = "led", .owner = THIS_MODULE, .of_match_table = of_match_ptr(fs4412_dt_of_matches), }, .probe = led_init, //对应初始化函数 .remove = led_exit, //对应退出函数 }; module_platform_driver(led_platform_driver); //驱动默认从该函数执行
3、设备树配置
在内核linux-3.14下执行 vim /arch/arm/boot/dts/exynos4412-fs4412.dts添加 重新编译设备树 make dtbs 复制设备树 cp /arch/arm/boot/dts/exynos4412-fs4412.dtb到tftp共享目录下替换了原先的设备树。
4、执行驱动的makefile
#module templet ifeq ($(KERNELRELEASE),) KERNELDIR ?= /home/farsight/remove/linux-3.14 PWD := $(shell pwd) all: $(MAKE) -C $(KERNELDIR) M=$(PWD) modules arm-none-linux-gnueabi-gcc led.c -o led cp -af *.ko /home/farsight/remove/rootfs cp led /home/farsight/remove/rootfs clean: rm -rf *.o *~ core .depend .*.cmd *.ko *.mod.c .tmp_versions Module* modules* a.out else obj-m := led_dev.o endif
5、启动tftp和nfs执行程序
“`
执行sudo service tftpd-hpa restart命令,开启tftp服务
重新驱动nfs服务:sudo /etc/init.d/nfs-kernel-server restart
下载驱动,创建设备文件,执行应用程序,即可
相关文章推荐
- Linux 驱动之 platform 驱动模型总结 (基于tiny210 平台 LED 驱动)
- Linux3.8.3在OK6410平台的移植LCD驱动
- OK6410 linux LED驱动
- 三星平台SD/MMC驱动分析
- Android 驱动Ok6410Led
- 和菜鸟一起学OK6410之Led字符驱动
- 字符设备驱动之LED-平台设备驱动(platform设备驱动)
- 三星s3c2410ARM平台下的按键驱动注释
- 三星 SMDKC210 开发板的最简单的LED驱动
- 基于全志A33的LED驱动开发,安卓6.0.1平台
- 基于platform总线的ok6410 LED 驱动
- 2440平台,LED驱动模块,成功加载,rmmod可以卸载,但是总是报错
- ok6410学习笔记(15.platform平台总线驱动模型之混杂设备驱动led)
- 和菜鸟一起学OK6410之Led字符驱动
- linux NAND驱动之三:6410平台上的NAND驱动加载
- 驱动实战-----OK6410驱动编程之led驱动1
- android平台led开发之内核硬件驱动层(一)
- 木其工作室(专业程序代写服务)[原]ok6410学习笔记(15.platform平台总线驱动模型之混杂设备驱动led)
- 我的led驱动OK6410 飞凌开发板
- Linux字符设备驱动之Tiny6410 LED驱动分析