2023年7月4日 星期二 linux驱动作业

news2024/11/26 0:30:12

Linux内核驱动开发板的灯的实验

头文件


#ifndef __HEAD_H__
#define __HEAD_H__
 
#define PHY_LED1_MODER 0X50006000
#define PHY_LED1_ODR   0X50006014
#define PHY_RCC        0X50000A28


#define PHY_LED2_MODER 0X50007000
#define PHY_LED2_ODR 0x50007014
 
#define PHY_LED3_MODER 0X50006000
#define PHY_LED3_ODR 0x50006014

 
#endif

驱动程序

#include <linux/init.h>
#include <linux/module.h>
#include <linux/fs.h>
#include <linux/uaccess.h>
#include <linux/io.h>
#include "head.h"
int major; // 用于保存主设备号
char kbuf[128] = {0};
unsigned int *vir_led1_moder;
unsigned int *vir_led1_odr;
unsigned int *vir_rcc;
unsigned int *vir_led2_moder;
unsigned int *vir_led2_odr;
unsigned int *vir_led3_moder;
unsigned int *vir_led3_odr;
// 封装操作方法
int mycdev_open(struct inode *inode, struct file *file)
{
    printk("%s:%s:%d\n", __FILE__, __func__, __LINE__);
    return 0;
}
ssize_t mycdev_read(struct file *file, char *ubuf, size_t size, loff_t *lof)
{
    int ret;
    if (sizeof(kbuf) < size)
        size = sizeof(kbuf);
    ret = copy_to_user(ubuf, kbuf, size);
    if (ret)
    {
        printk("copy_tO_user filed\n");
        return -EIO;
    }
    printk("%s:%s:%d\n", __FILE__, __func__, __LINE__);
    return 0;
}
ssize_t mycdev_write(struct file *file, const char *ubuf, size_t size, loff_t *lof)
{
    int ret;
    if (sizeof(kbuf) < size) // 判断用户空间的需求是否能被驱动满足,满足不了就给能给的最好的
        size = sizeof(kbuf);
    ret = copy_from_user(kbuf, ubuf, size);
    if (ret)
    {
        printk("copy_from_user filed\n");
        return -EIO;
    }
    // led1
    if (kbuf[0] == '1') // 开灯
    {
        // 开灯逻辑
        (*vir_led1_odr) |= (0x1 << 10);
    }
    else if (kbuf[0] == '0') // 关灯
    {
        // 关灯
        (*vir_led1_odr) &= (~(0x1 << 10));
    }
    // led2
    if (kbuf[1] == '1') // 开灯
    {
        // 开灯逻辑
        (*vir_led2_odr) |= (0x1 << 10);
    }
    else if (kbuf[1] == '0') // 关灯
    {
        // 关灯
        (*vir_led2_odr) &= (~(0x1 << 10));
    }
    // led3
    if (kbuf[3] == '1') // 开灯
    {
        // 开灯逻辑
        (*vir_led3_odr) |= (0x1 << 8);
    }
    else if (kbuf[3] == '0') // 关灯
    {
        // 关灯
        (*vir_led3_odr) &= (~(0x1 << 8));
    }
    printk("%s:%s:%d\n", __FILE__, __func__, __LINE__);
    return 0;
}
int mycdev_close(struct inode *inode, struct file *file)
{
    printk("%s:%s:%d\n", __FILE__, __func__, __LINE__);
    return 0;
}
// 定义操作方法结构体变量并完成初始化
struct file_operations fops =
    {
        .open = mycdev_open,
        .read = mycdev_read,
        .write = mycdev_write,
        .release = mycdev_close,
};

static int __init mycdev_init(void)
{
    // 字符设备驱动注册
    major = register_chrdev(0, "mychrdev", &fops);
    if (major < 0)
    {
        printk("字符设备驱动注册失败\n");
        return major;
    }
    printk("字符设备驱动注册成功major=%d\n", major);
    // 映射物理寄存器
    vir_led1_moder = ioremap(PHY_LED1_MODER, 4);
    if (vir_led1_moder == NULL)
    {
        printk("MODER寄存器地址映射表失败\n");
        return -EFAULT;
    }
    vir_led1_odr = ioremap(PHY_LED1_ODR, 4);
    if (vir_led1_odr == NULL)
    {
        printk("ODR寄存器地址映射表失败\n");
        return -EFAULT;
    }
    vir_rcc = ioremap(PHY_RCC, 4);
    if (vir_rcc == NULL)
    {
        printk("RCC寄存器地址映射表失败\n");
        return -EFAULT;
    }
    vir_led2_moder = ioremap(PHY_LED2_MODER, 4);
    if (vir_led2_moder == NULL)
    {
        printk("MODER寄存器地址映射表失败\n");
        return -EFAULT;
    }
    vir_led2_odr = ioremap(PHY_LED2_ODR, 4);
    if (vir_led2_odr == NULL)
    {
        printk("ODR寄存器地址映射表失败\n");
        return -EFAULT;
    }
    vir_led3_moder = ioremap(PHY_LED3_MODER, 4);
    if (vir_led3_moder == NULL)
    {
        printk("MODER寄存器地址映射表失败\n");
        return -EFAULT;
    }
    vir_led3_odr = ioremap(PHY_LED3_ODR, 4);
    if (vir_led3_odr == NULL)
    {
        printk("ODR寄存器地址映射表失败\n");
        return -EFAULT;
    }
    printk("寄存器地址映射成功\n");
    // 寄存器初始化
    (*vir_rcc) |= (0x1 << 4); // rcc使能
    (*vir_rcc) |= (0x1 << 5);
    (*vir_led1_moder) &= (~(0X3 << 20)); // 设置为输出
    (*vir_led1_moder) |= (0x1 << 20);
    (*vir_led1_odr) &= (~(0x1 << 10));   // 灭灯
    (*vir_led2_moder) &= (~(0X3 << 20)); // 设置为输出
    (*vir_led2_moder) |= (0x1 << 20);
    (*vir_led2_odr) &= (~(0x1 << 10));   // 灭灯
    (*vir_led3_moder) &= (~(0X3 << 16)); // 设置为输出
    (*vir_led3_moder) |= (0x1 << 16);
    (*vir_led3_odr) &= (~(0x1 << 8)); // 灭灯
    printk("硬件寄存器初始化成功\n");
    return 0;
}
static void __exit mycdev_exit(void)
{
    // 取消寄存器地址映射
    iounmap(vir_led1_moder);
    iounmap(vir_led1_odr);
    iounmap(vir_led2_moder);
    iounmap(vir_led2_odr);
    iounmap(vir_led3_moder);
    iounmap(vir_led3_odr);
    iounmap(vir_rcc);
    // 字符设备驱动的注销
    unregister_chrdev(major, "mychrdev");
}
module_init(mycdev_init);
module_exit(mycdev_exit);
MODULE_LICENSE("GPL");

应用程序

#include <stdio.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <unistd.h>
#include <string.h>
int main(int argc, char const *argv[])
{
    char buf[128] = {0};
    int fd = open("/dev/mychrdev", O_RDWR);
    if (fd < 0)
    {
        printf("打开设备文件失败\n");
        exit(-1);
    }
    while (1)
    {
        printf("输入控制命令--->三位>");
        fgets(buf, sizeof(buf), stdin);
        buf[strlen(buf) - 1] = '\0';
        write(fd, buf, sizeof(buf));
    }
    close(fd);
    return 0;
}

开发板的结果

在这里插入图片描述

在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/724732.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

LK409.最长回文字符串

题目描述 给定一个包含大写字母和小写字母的字符串 s &#xff0c;返回 通过这些字母构造成的 最长的回文串 。 在构造过程中&#xff0c;请注意 区分大小写 。比如 “Aa” 不能当做一个回文字符串。 解题思路 有两种情况可以构成回文字符串: 1.全部字符呈偶数对出现 2.一…

simulink 仿真时间 求解器 数据类型 delay模块

仿真时间&#xff0c;模型运行的时长 显示数据类型&#xff0c;改完数据类型后要run一次才能正常显示更改后的类型 delay模块&#xff0c;延时步长 综合训练 搭建一个累加器&#xff0c;每次调用1 //c语言 static int a 0; a;

一次搞懂ArrayBuffer和Unit8Array(TypedArray)和Array!

实现入职第三天&#xff0c;用到了公司自研框架里面的网络请求&#xff0c;返回的数据会被自动改成ArrayBuffer类型&#xff0c;研究了半天没明白ArrayBuffer怎么转成字符串数据&#xff0c;看了mentor发来的示例代码&#xff0c;经过一番研究也是明白了ArrayBuffer和它相关的东…

Python基础教程:读写文件IO操作

Python 是一门优秀的开发语言&#xff0c;它不仅是一种动态的脚本语言&#xff0c;还支持多种应用场景。在 Python 中&#xff0c;我们可以使用文件和 I/O 操作来读取和写入文件。它比起其他编程语言&#xff0c;使用更加方便。 1.读写文本文件 在 Python 中&#xff0c;读写…

【轴承RUL预测代码】基于DRSN(深度残差收缩网络)

DRSN&#xff08;深度残差收缩网络&#xff09;和完整Transformer&#xff08;encoderdecoder&#xff09; DRSN&#xff08;深度残差收缩网络&#xff09;模型的代码模型的打印训练与预测训练集的可视化&#xff1a;测试集的可视化&#xff1a; DRSN-TCN的效果 DRSN&#xff0…

贝叶斯与认知——读《贝叶斯的博弈》有感

关于对贝叶斯与认知问题的相关思考 一、贝叶斯定理二、贝叶斯与认知的本质三、经验的偏见四、总结 自古以来&#xff0c;人们就在思考知识来自何处&#xff0c;“冯翼惟象&#xff0c;何以识之&#xff1f;”&#xff0c;对此的思考逐渐发展成哲学的认识论分支。德国哲学家康德…

二十三种设计模式第十六篇--观察者模式

观察者模式是一种行为型设计模式&#xff0c;它建立了一种对象间的一对多依赖关系&#xff0c;使得当一个对象的状态发生变化时&#xff0c;所有依赖于它的对象都会得到通知并自动更新。这种模式可以实现对象间的松耦合通信&#xff0c;提高系统的可扩展性和灵活性。 观察者模…

开源白盒 静态代码分析对比

背景 源代码安全检测是安全开发流程&#xff08;SDL&#xff09;中非常重要的一部分&#xff0c;在58集团的CI/CD流程里面临每天几千数量级的构建及发布&#xff0c;白盒检测的自动化能力显得极为重要。白盒扫描从漏洞发现的需求转变为了需要适应企业CI/CD流程的白盒建设需求&…

Win2008 IIS TLS1.0升级到TLS1.2或TLS1.3

最近chrome和Edege浏览器已经把TLS 1.0标记为不安全了。 如果是开发网站&#xff0c;而使用的TLS 1.0&#xff0c;则直接打开不网站&#xff0c;也没有醒目的提示&#xff0c;你很难知道问题所在&#xff0c;总以为是SSL安装失败了&#xff0c;其实是TSL版本太低了。 如果是开…

密码学学习笔记(六):Hash Functions - 哈希函数2

哈希函数是怎么构成的&#xff1f; Merkle–Damgrd结构 哈希函数需要能够处理任意长度的输入。许多散列函数&#xff0c;例如MD5、SHA-1、SHA-2&#xff0c;都是由构建块&#xff08;称为压缩函数&#xff09;组成的&#xff0c;这些构建块可以处理特定的块大小&#xff0c;并…

SSM 整合 Shiro 安全框架【快速入门】

一、搭建ssm工程&#x1f349; 1.创建工程&#x1f95d; 更改web路径 创建所需目录 2.引入依赖&#x1f95d; <project xmlns"http://maven.apache.org/POM/4.0.0" xmlns:xsi"http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation"h…

LVS+Keepalived负载均衡高可用群集

目录 一、Keepalived高可用详解 1.应用场景 2.介绍和原理简介 3.主要模块和作用 二、LVSkeepalived配置实例&#xff08;抢占模式&#xff09; 1.配置NFS共享存储器 2.配置节点web服务&#xff08;两台的配置相同&#xff09; 3.配置主备LVSkeepalived负载调度器 三、非…

JAVA判断当前时间是否为节假日、周末、工作日,简单有效!

JAVA判断当前时间是否为节假日、周末、工作日 需求 有这么个需求&#xff0c;需要判断拿到的这个日期是否为节假日&#xff0c;周末&#xff0c;工作日&#xff0c;然后做剩下的操作。 话不多说&#xff0c;上代码 1.首先需要拿到节假日api 节假日API地址 2.拿到接口&…

Open3d计算点云切片

computePlane()给出三个点计算平面方程参数 设通过P1&#xff0c;P2&#xff0c;P3三点的平面方程为A(x - x1) B(y - y1) C(z - z1) 0 。化简为一般式&#xff1a;Ax By Cz D 0。 将P1(x1,y1,z1)点数值代入方程Ax By Cz D 0。 即可得到&#xff1a;Ax1 By 1 Cz1 D…

css之文字宽度自适应、width、fit、content

文章目录 效果图htmlcss解析width 效果图 html <div><div class"width_600"><div class"d_f ai_c bc_1296db padding_7 radius_8 cursor_pointer" style"width: fit-content;"><img class"width_26 height_26" …

ps通道抠图

相信我们在抠图的时候都遇到过这种问题&#xff1a; 在扣取一些像树木、毛发等类似图像的时候&#xff0c;用魔棒或者快速选择工具根本抠不完整&#xff08;图1&#xff09;&#xff0c;而且就算抠出来也是毛毛刺刺的&#xff0c;使用效果很拉跨。而通道抠图&#xff08;图2&a…

真的不想知道文档翻译在线翻译怎么弄才简单吗

从前有一个小明&#xff0c;他是一名国际商人。他需要将公司的商业计划书翻译成多种语言&#xff0c;以便在海外市场推销。但是&#xff0c;他并不会所有需要的语言&#xff0c;于是他开始寻找一种方法来进行文档翻译。终于&#xff0c;他找到了一种文档翻译的有效方法&#xf…

Dynamsoft Barcode Reader crack

Dynamsoft Barcode Reader crack SDK经过重构&#xff0c;与DynamsoftCaptureVision(DCV)体系结构集成&#xff0c;该体系结构包括&#xff1a; ImageSourceAdapter(ISA)-标准输入接口&#xff0c;用于将来自不同来源的图像数据转换为标准输入图像数据。此外&#xff0c;ISA结合…

2023第七届河南省高等学校信息安全对抗大赛-御网杯-ISCC2023线下赛-misc(详解-思路-脚本)

芜湖~ 是真累呀 原本一天的时间 硬打了一天半 还是那句话 不评价 各位道友心中自有公论 我misc手又发现一个小小的非预期 哎 没想到线下也有这种情况 欧克 以下是我自己的一些思路和解析 有什么问题或者建议随时都可以联系我 2023第七届河南省高等学校信息安全对抗大赛-御…

医疗设备中的直线导轨使用哪种润滑脂?

直线导轨属于滚动功能部件&#xff0c;看似普通&#xff0c;却是大多数医疗设备的核心功能部件之一&#xff0c;也是保障医疗设备精度的基础&#xff0c;需要具备高精度、高耐磨、高顺畅等性能&#xff0c;对生产企业的研发实力、制造工艺及技术水平提出相当大的挑战&#xff0…