全志linux led驱动程序,芯灵思Sinlinx A64 linux通过设备树写LED驱动(附参考代码,未测试)...
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#define MY_DEVICE_NAME "my_LED_device"
// 获取到设备树中到节点
static int gpio = -1;
int get_irqno_from_node(void)
{
struct gpio_config config;
struct device_node *np = of_find_node_by_path("/leds");
IF(np){
printk("find node ok\n");
}
else{
printk("find node failed\n");
}
gpio = of_get_named_gpio_flags(nd, "gpios", i, (enum of_gpio_flags *)&config);// 从设备树中读取gpios的GPIO配置编号和标志
if(!gpio_is_valid(gpio)){
//判断该 GPIO 编号是否有效,有效gpio_request 则申请占用该 GPIO。如果初始化过程出错,需要调用 gpio_free 来释放之前申请过且成功的 GPIO
printk("gpio isn't valid\n");
return -1;
}
if(gpio_request(gpio, "leds") < 0)
printk("gpio request failed %d\n", gpio);
gpio_direction_output(gpio, 1); //关灯
return 0;
}
static int my_open (struct inode *node, struct file *filp)
{
if(gpio)
{
printk("open ok\n");
}
else
{
return -EINVAL;
}
return 0;
}
static ssize_t my_write (struct file *filp, const char __user *buf, size_t size, loff_t *off)
{
unsigned char val;
copy_from_user(&val, buf, 1);
printk(" gpl_dat address 0x%x\n",gpl_dat);
if (val)
{
gpio_direction_output(gpio, 0); //关灯
printk("led on\n");
}
else
{
gpio_direction_output(gpio, 1); //关灯
printk("led off\n");
}
return 1;
}
static const struct file_operations my_led_fops = {
//step 1 :定义file_operations结构体
.open = my_open,
.write = my_write,
};
//step 1 :
static struct class *led_class;
static struct cdev *pcdev; //定义一个cdev指针
static dev_t n_dev; //第一个设备号(包含了主和次)
static int __init led_device_init(void)
{//step 2 :注册
int ret = -1;
pcdev = cdev_alloc();//分配cdev结构空间
if(pcdev == NULL) {
printk(KERN_EMERG" cdev_alloc error\n");
ret = -ENOMEM; /* 分配失败 */
return ret;
}
//2. 动态申请设备号
ret = alloc_chrdev_region(&n_dev, 0 , 2, MY_DEVICE_NAME);
if(ret < 0 ) {
//释放前面成功的资源
kfree(pcdev); /*释放cdev结构空间 */
printk(KERN_EMERG"alloc_chrdev_region error\n");
return ret;
}
cdev_init(pcdev, &my_led_fops); //初始化cdev结构 /* 建立cdev和file_operations之间的连接 */
/*
或这样初始化cdev结构
pcdev->owner = THIS_MODULE;
pcdev->ops = &my_led_fops;
*/
ret = cdev_add(pcdev, n_dev, 2) ;// 向内核里面添加一个驱动,注册驱动
if(ret < 0 ) {
//释放前面成功的资源
unregister_chrdev_region(n_dev, 2); /* 释放前面申请的调和号*/
kfree(pcdev); /* 释放cdev结构空间 */
printk(KERN_EMERG"alloc_chrdev_region error\n");
return ret;
}
/*自动创建设备节点/dev/SinlinxA64_LED*/
led_class = class_create(THIS_MODULE, "myled");
device_create(led_class, NULL, n_dev, NULL, "SinlinxA64_LED");
get_irqno_from_node();
printk(KERN_EMERG"cdev ok\n");
return 0;
}
static void __exit led_device_exit(void)
{ //step 2 :注销
//注销cdev结构
cdev_del(pcdev);
//释放设备号
unregister_chrdev_region(n_dev, 2); /*起始设备号(主、次) 连续的次设备号数量*/
//释放cdev结构空间
kfree(pcdev);
device_destroy(led_class, n_dev);
class_destroy(led_class);
gpio_free(gpio);
printk(KERN_EMERG"cdev_del ok\n");
}
module_init(led_device_init);
module_exit(led_device_exit);
MODULE_LICENSE("GPL");
全志linux led驱动程序,芯灵思Sinlinx A64 linux通过设备树写LED驱动(附参考代码,未测试)...相关推荐
- 全志a64linux内核编译,芯灵思Sinlinx A64 Linuxqt编译安装
开发平台 芯灵思Sinlinx A64 内存: 1GB 存储: 4GB 开发板交流 641395230 前提条件搭建好CentOS环境 光盘目录 :芯灵思SIN-A64光盘资料\Linux & ...
- 芯灵思Sinlinx A64开发板 Linux内核等待队列p
阻塞:阻塞调用是指调用结果返回之前,当前进程程会被挂起(休眠).函数只有在得到结果之后才会返回.默认情况下,文件都是以这种方式打开. 非阻塞:指在不能立刻得到结果之前,该函数不会阻塞当前进程程,而会立 ...
- Linux设备树led,linux设备树下LED灯控制
linux设备树下LED灯控制 linux设备树下LED灯控制 原理图: 所以在设备树下子节点下插入gpioled节点: gpioled { #address-cells = <1>; # ...
- Linux驱动_设备树下LED驱动
前言 学习完设备树基础知识后,完成设备树下LED驱动实验 一.修改设备树文件 在设备书根/节点下添加子节点led信息: alphaled {status = "okay";comp ...
- 【基于Linux系统设备树的SPI驱动编写方法】
文章目录 前言 一.SPI驱动编写 1.修改设备树 a.设备树文件是什么? b.设备树怎么改? 2.编写驱动 二.完善和测试 1.编译和应用程序 a.编译 && 拷贝到开发板命令 ...
- Linux利用platform_driver和设备树实现PWM驱动
Linux利用platform_driver和设备树实现PWM驱动 字符设备PWM驱动 一.PWM驱动的硬件资源 1.PWM工作原理 2.PWM电路原理 3.PWM内部结构 二.具体代码 1.设备树 ...
- Linux dts设备树和platform驱动详解
概念 小麦大叔 2019-05-06 22:56:31 12603 收藏 135 什么是设备树 dts(device tree)? 设备树(Device Tree)是描述计算机的特定硬件设备信息的数据 ...
- linux设备和驱动匹配的方法,Linux使用设备树的i2c驱动与设备匹配方式
Linux使用设备树的i2c驱动与设备匹配有3种方式: of_driver_match_device acpi_driver_match_device i2c_match_id 源码: static ...
- linux u 驱动程序,在uClinux中增加自己的设备驱动程序
驱动程序的使用可以按照两种方式编译,一种是静态编译进内核,另一种是编译成模块以供动态加载.由于 uClinux不支持模块动态加载,而且嵌入式Linux不能够象桌面Linux那样灵活的使用insmod/ ...
最新文章
- 搜索引擎中的URL散列
- 【解决方法】java.lang.ClassNotFoundException:
- python decorator ssh_Python库现后门 可窃取用户SSH信息
- 2016福州大学软件工程第四次团队作业-系统设计成绩汇总
- 时隔一年俺又回来了..
- Nutanix企业云助力嘉里大通提升核心竞争力
- FreeEIM 是班级的学习委员
- (7)UART接收verilog与Systemverilog编码
- Excel如何批量根据身份证号码查询出地址
- NX的尺寸控制与半径补偿(重要)
- 用Cocos Creator 模拟书本翻页效果
- 计算机应用技术一班班徽,1班班徽设计图片大全欣赏
- ClickHouse表引擎到底怎么选
- 移动端自动轮播可滑动轮播图
- 颜色综述何为三原色?配色原理?
- meshgrid()函数
- python实现md5和sha1加密
- 干货分享:智慧工厂时代下大数据 + 智能的深度实践
- gson线上环境解析日期时报错JsonSyntaxException
- oracle创建带blob字段的表,ORACLE 还有BLOB及CLOB等类型字段的表的导出导入
热门文章
- windows平台一个高性能、通用型的C++生产者/消费者架构模板
- 论文笔记:PRIN: Pointwise Rotation-Invariant Networks
- 论文笔记:Image Caption(Show and Tell)
- html 设置视频尺寸,如何使用CSS控制视频的宽高?
- 团队作业第二次—项目选题报告(追光的人)
- Nginx 实现AJAX跨域请求
- CSS Dock Menu:JS+CSS 仿苹果MAC机桌面导航菜单
- Oh-My-Zsh 操作 Git 的快捷键
- Leaflet实现地图分屏联动
- U盘安装openSuse