栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 系统运维 > 运维 > Linux

Linux学习

Linux 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

Linux学习

        在设备树下创建IO子节点,方便一点在根节点/,把寄存器的复用以及电气属性追加在IOMUX(目前学到的引脚)。记得编译设备树,linux内核重新启动。

点灯大法:

        编写驱动和编写APP

需要注意失败时的处理cdev和device分配了内存需要释放,设备号要注销,class要销毁。

注册设备号
if(beep.major){
        beep.devid = MKDEV(beep.major, beep.minor);
        register_chrdev_region(beep.devid,DEV_NUMBER,DEV_NAME);
    }else {
        alloc_chrdev_region(&beep.devid,0,DEV_NUMBER,DEV_NAME);
        beep.major = MAJOR(beep.devid);
        beep.minor = MINOR(beep.devid);
    }printk("beep major = %d, minor = %drn",beep.major, beep.minor);
初始化c_dev并add上(将*ops与其绑定)
beep.cdev.owner = THIS_MODULE;
    cdev_init(&beep.cdev,&beep_ops);
    cdev_add(&beep.cdev,beep.devid,DEV_NUMBER);
创建class类(入口参数MODULE和注册名,感觉不太重要,作为device入口参数)
beep.class = class_create(THIS_MODULE,DEV_NAME);
    if(IS_ERR(beep.class)){
        return PTR_ERR(beep.class);
    }
创建device设备
beep.device = device_create(beep.class,NULL,beep.devid,NULL,DEV_NAME);
    if(IS_ERR(beep.device)){
        return PTR_ERR(beep.device);
    }
    beep.nd = of_find_node_by_path("/beep");
    if(beep.nd == NULL){
        ret = -EINVAL;
        goto failed_find_node;
    }
    beep.beep_gpio = of_get_named_gpio(beep.nd,"beep-gpios",0); 
    if(beep.beep_gpio < 0 ){
        printk("can't find BEEP rn");
        ret = -EINVAL;
        goto failed_find_node;
    }printk("beep gpio number = %drn",beep.beep_gpio);
    ret = gpio_request(beep.beep_gpio,"beep-gpios");
    if(ret){
        printk("beep_gpio request failedrn");
        ret = -EINVAL;
        goto failed_find_node;
    }

        终于不用在像之前学习操作寄存器了, 通过获取节点对应IO号操作,记得向内核申请防止IO正在被使用。

    ret = gpio_direction_output(beep.beep_gpio,1);
    if(ret){
        ret = -EINVAL;
        goto failed_setoutput;
    }
    gpio_set_value(beep.beep_gpio,1);

file_operations指针

static const struct file_operations beep_ops = {
    .owner = THIS_MODULE,
    .write = beep_write,
    .open = beep_open,
    .release = beep_release,
};

static ssize_t beep_write(struct file *filp, const char __user *buf,
                size_t count, loff_t *ppos)
{
    int ret;
    unsigned char databuf[1];
    struct beep_dev *dev = filp->private_data;
    ret = copy_from_user(databuf, buf, count);
    if(ret < 0){
        return -EFAULT;
    }
    gpio_set_value(dev->beep_gpio,databuf[0]);
    return 0;
}

数据由用户到内核空间write->beep_write

编写APP

#include 
#include 
#include 
#include 
#include 
#include 
#include 

#define LEDOFF 0
#define LEDON 1

int main(int argc, char *argv[])
{
    int fd;
    char *filename = argv[1];
    unsigned char databuf[1];
    int retval = 0;

    if(argc != 3){
        printf("Usage:Errorrn");
        return -1;
    }

    fd = open(filename, O_RDWR);
    if(fd < 0){
        printf("Error openingrn");
        return -1;
    }

    databuf[0] = atoi(argv[2]);
    retval = write(fd, databuf, sizeof(databuf));
    if(retval < 0)
    {
        printf("LED write Errorrn");
        close(fd);
        return -1;
    }
    close(fd);
    return 0;
}

转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/333415.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号