树莓派——9、IO操控代码编程

article/2025/9/22 7:12:37

编写操控io的代码

关于树莓派的cpu型号:

使用pinout
在这里插入图片描述
使用cat /proc/cpuinfo
在这里插入图片描述
查阅资料:

查阅资料发现树莓派3b的CPU型号就是BCM2709,也就是pinout中的BCM2827
在这里插入图片描述

要先确定IO空间的起始地址(物理地址)

ps:树莓派3B的是cpu型号为bcm2709.
在这里插入图片描述

0x3F00 0000就是IO外围设备的起始物理地址

我们需要确定GPFSEL0的物理地址,就要找出偏移量
在这里插入图片描述
在这里插入图片描述
可以得到物理地址:0x3F00 0000+(0x7E20 0000- 0x7E00 0000)=0x3F20 0000

GPFSEL0的地址为:0x3F20 0000;
GPSET0的地址为: 0x3F20 001C;
GPCLR0的地址为: 0x3F20 0028;

我们得到的是物理地址是不可以直接操作的,我们需要转化成虚拟地址,通过调用函数:__ioremap

void __iomem * __ioremap(unsigned long phys_addr, size_t size, unsigned long flags);ioremap宏定义在asm/io.h内:#define ioremap(cookie,size)           __ioremap(cookie,size,0)

参数:
phys_addr:要映射的起始的IO地址

size:要映射的空间的大小

flags:要映射的IO空间和权限有关的标志

驱动代码编写

基于驱动框架的代码进行修改

php 从数据库提取二进制图片的处理代码

pdf正在上传…重新上传取消0星超过10%的资源28KB

下载

sed -ir ‘s/hello/pin4/g’ pin4_drv.c (把pin4_drv.c里面所有的hello替换成pin4)

sed -ir ‘s/关键字/目标关键字/g’ 文件在这里插入图片描述

先定义寄存器的地址

错误示范:
在这里插入图片描述
这样直接定义是不对的,linux中代码访问的是虚拟地址,所以我们需要在入口函数把物理地址转化为虚拟地址

寄存器地址先初始化为NULL
在这里插入图片描述

volatile的作用:防止编译器对代码优化,变量值是直接从变量地址中读取和存储的

驱动加载的时候在入口函数对寄存器地址赋值

在这里插入图片描述
在open的时候配置pin4为输出引脚

在这里插入图片描述

在write函数获取用户层的数据,根据这个数据来操作io口输出高电平或者低电平

在这里插入图片描述

copy_from_user(void *to, const void __user *from, unsigned long n)
//从用户空间拷贝数据到内核空间
*to    :将数据拷贝到内核的地址
*from  :需要拷贝数据的地址
n      :拷贝数据的长度(字节)
也就是将form地址中的数据拷贝到to地址中去,拷贝长度是n

data-channel:将数据通道转换为流

zip正在上传…重新上传取消0星超过10%的资源3KB

下载

并且在出口函数解除寄存器的地址映射(防止风险)
在这里插入图片描述

完整代码

#include <linux/fs.h>
#include <linux/module.h>
#include <linux/init.h>
#include <linux/device.h>
#include <linux/uaccess.h>
#include <linux/types.h>
#include <asm/io.h>static struct class *pin4_class;
static struct device *pin4_class_dev;static dev_t devno;	//设备号
static int major = 231; //主设备号
static int minor = 0;	//次设备号
static char *module_name = "pin4"; //模块名volatile unsigned int *GPFSEL0 = NULL;
//volatile的作用是作为指令关键字,确保本条指令不会因编译器的优化而省略,且要求每次直接读值。
volatile unsigned int *GPSET0 = NULL;
volatile unsigned int *GPCLR0 = NULL;//led open 函数
static int pin4_open(struct inode *inode,struct file *file)
{printk("pin4_open\n");*GPFSEL0 &= ~(0x6 << 12);//0x6用二进制表示是110 想左移12位在取反就可以保证 14-12位为001在用&(与运算)运算我们就可以保证 14,13位一定为0*GPFSEL0 |= (0x1 <<12);//0x1 用二进制表示是1 想左移12位在用|(或运算)就可以保证第12为一定为1return 0;
}static int pin4_write(struct file *file, const char __user *buf, size_t size, loff_t *ppos)
{int userCmd;printk("pin4_write\n");copy_form_user(&userCmd,buf,size);//这个函数是用于接收上层代码的,在内核源码中可以找到这个函数用法if (userCmd==1){printk("set 1\n");*GPSET0 |= (0x1 << 4);//0x1 左移四位就可以将第4引脚置1并且不影响其他位,并且将pin4设置为高电平}else if(userCmd==0){printk("set 0\n");*GPCLR0 |= (0x1 << 4);//原理上,但这边设置的是低电平}else{printk("undo\n");}return 0;}static int pin4_read(struct file *file1, char __user *buf, size_t size, loff_t *ppos)
{printk("pin4_read\n");return 0;
}static struct file_operations led_fops = {.owner = THIS_MODULE,.open  = pin4_open,.write = pin4_write,.read  = pin4_read,
};int __init pin4_drv_init(void)
{int ret;printk("pin4 insmod success\n");devno = MKDEV(major,minor);ret = register_chrdev(major,module_name, &led_fops);//注册驱动 告诉内核pin4_class = class_create( THIS_MODULE, "myfirstdemo");pin4_class_dev = device_create(pin4_class,NULL,devno,NULL,module_name);GPFSEL0 = (volatile unsigned int *)ioremap(0x3f200000,4);//ioremap():物理地址转换成虚拟地址,io口寄存器映射成普通内存单元进行访问,0x3f200000 GPFSL0的物理地址,在下面为大家介绍为什么这个//第二个参数表示映射的大小GPSET0  = (volatile unsigned int *)ioremap(0x3f20001c,4);//物理地址的映射要在创建之后GPCLR0  = (volatile unsigned int *)ioremap(0x3f200028,4);return 0;}void __exit pin4_drv_exit(void)
{iounmap(GPFSEL0 );//取消ioremap所映射的IO地址iounmap(GPSET0 );//取消隐射要在摧毁前iounmap(GPSET0);device_destroy(pin4_class,devno);class_destroy(pin4_class);unregister_chrdev(major,module_name);//卸载驱动printk("pin4 destroyed\n");}module_init(pin4_drv_init);
module_exit(pin4_drv_exit);
MODULE_LICENSE("GPL v2");

编译阶段

  1. 把写好的驱动文件拷贝到源码树目录的 /drivers/char 目录下
    在这里插入图片描述

  2. 修改Makefile(为了在编译的时候生成.ko文件)
    在这里插入图片描述

  3. 编译驱动代码(切回到源码树目录进行编译)
    ARCH=arm CROSS_COMPILE=arm-linux-gnueabihf- KERNEL=kernel7 make modules

在这里插入图片描述
在这里插入图片描述

测试阶段

  1. 把驱动文件拷贝到树莓派,并且安装驱动
    在这里插入图片描述
    安装驱动
    在这里插入图片描述
    驱动加载成功
    在这里插入图片描述

  2. 编写测试程序拷贝到树莓派
    测试程序:

#include<stdio.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <unistd.h>
#include <fcntl.h>
int main(){int fd;char cmd;fd=open("/dev/pin4_drv",O_RDWR);if(fd==-1){printf("open failed\n");perror("reason");}else{printf("open success\n");}printf("imput 1 or 0\n1:pin4 set 1\n0:pin4 set 0\n");scanf("%c",&cmd);if(cmd=='1'){write(fd,"1",1);}else if (cmd=='0'){write(fd,"0",1);}else{printf("imput error\n");}return 0;
}

在lUbuntu交叉编译后把程序拷贝到树莓派,然后在树莓派运行

在这里插入图片描述
测试结果:用dmesg查看内核打印信息
在这里插入图片描述
查看io口状态:
在这里插入图片描述


http://chatgpt.dhexx.cn/article/Afqv62mH.shtml

相关文章

PHP并发IO编程之路

并发IO问题一直是服务器端编程中的技术难题&#xff0c;从最早的同步阻塞直接Fork进程&#xff0c;到Worker进程池/线程池&#xff0c;到现在的异步IO、协程。PHP程序员因为有强大的LAMP框架&#xff0c;对这类底层方面的知识知之甚少&#xff0c;本文目的就是详细介绍PHP进行并…

几种 IO编程比较

参考&#xff1a; Netty权威指南第一版 Java 网络IO编程总结&#xff08;BIO、NIO、AIO均含完整实例代码&#xff09; 1. 传统的BIO模型 通常由一个独立的Acceptor线程负责监听客户端的连接&#xff0c;它接收到客户端连接请求之后为每个客户端创建一个新的线程进行处理&am…

Java实验报告(七)|IO编程

文章目录 题目一题目二题目三 题目一 &#xff08;一&#xff09;编程实现打印目录“C:/”下所有后缀为“.txt”文件名。 import java.io.File; import java.util.Scanner; public class ShowTxt {public static void main(String[] args) {System.out.println("请输入要…

Linux下C语言编程(1):IO编程

笔者今天来讲讲Linux下IO口的使用。用的硬件是三大开源器件之一的BeagleBone&#xff08;狗骨头&#xff09;。 &#xff08;PS 三大开源器件&#xff1a;树莓派、Arduino和Beagle Bone&#xff09; 硬件介绍 TI公司的AM3358 集成 1G MHz ARM Cortex™ A8 内核&#xff0c; 4G…

IO接口编程

IO接口编程 作者&#xff1a; Saint 掘金&#xff1a;https://juejin.im/user/5aa1f89b6fb9a028bb18966a 微博&#xff1a;https://weibo.com/5458277467/profile?topnav1&wvr6&is_all1 GitHub&#xff1a;github.com/saint-000 CSDN: https://me.csdn.net/qq_405319…

网络编程IO

文章目录 前言用户空间和内核空间系统调用一、同步IO模型1、阻塞式IO模型2、非阻塞式IO模型3、IO复用模型4、信号驱动IO模型 二、异步IO模型三、同步和异步 前言 IO操作由两个部分组成&#xff1a;发起IO请求、实际进行IO操作。 也就是下图所示的等待数据从磁盘拷贝到内核空间…

Linux 下文件IO编程进程控制实验

Linux 下文件IO编程&进程控制实验 一、基本I/O操作 (1).Linux的输入/输出&#xff08;I/O&#xff09;操作&#xff0c;通常为五个方面&#xff1a;打开&#xff0c;读取&#xff0c;写入&#xff0c;定位和关闭&#xff1b;对应的函数分别为&#xff1a;open&#xff08;…

文件IO(IO编程)

一、文件IO&#xff08;IO编程&#xff09; 系统IO&#xff1a;和系统有关的IO接口函数 标准IO: 标准库里面的IO接口函数 #include <stdio.h> 目录操作&#xff1a;操作目录相关的IO接口函数 LCD屏的操作&#xff1a;刷图 TS(touch screen)触摸屏的操作:点击、滑动 二、…

I/O编程

一、标准IO 1.1、概述 标准IO 是ANSI C提供的函数接口&#xff0c;在文件IO的基础上封装出来的。任何兼容标准C库的操作系统都可以使用接口&#xff0c;具有更好的移植性。标准IO在执行时也会用到系统调用&#xff0c;为了增加内核的工作效率&#xff0c;减少资源浪费&#…

小米平板2装win10(附驱动)

前段时间在折腾着怎么给米pad2装win10&#xff0c;结果驱动什么的折腾了好久。 给米pad2装win10&#xff0c;其实就和给普通的电脑装win10差不多的步骤。 第一步&#xff0c;制作U盘启动器。工具什么的就用官方的winPE就好&#xff0c;iso就随意吧。 第二步&#xff0c;给米…

小米笔记本系统win10家庭版升级为企业版(专业版)

一.背景 新入职一家IT公司,由于公司领导层是小米粉,基本新入职的员工人手一本小米笔记本.小米笔记本默认自带的是家庭版的,由于之前公司很多人用的都是家庭版的,在某些极为特殊的软件开发情况下,家庭版的配置给开发带来了极大的困难,后来经过查资料验证企业版是不会出现这种情…

小米mix2s刷win11和android双系统

在给电脑安装系统的过程中&#xff0c;可能会因为各种原因出现windows无法安装的情况&#xff0c;我在给小米mix2s安装win11时发现出现了“计算机意外地重新启动或遇到错误&#xff0c;windows无法安装”的情况&#xff0c;下面就来教一下大家两种解决方法&#xff0c;希望可以…

小米air13.3一代的win10系统重装

仅作为记录&#xff0c;大佬请跳过 小米air的系统重装在进入bios之后&#xff0c;选择u盘启动时&#xff08;需要设置一个密码&#xff0c;然后关闭secure boot&#xff09;有点跟神船不一样&#xff0c;作为记录。 参考大佬博主文章传送门

Win10 IPv6 远程桌面连接(小米路由器)

前排广告&#xff1a;2021金三银四&#xff0c;字节跳动招人季&#xff0c;平均反馈时间仅1天&#xff01;选择覆盖达6大城市&#xff01;——2021年字节跳动飞书团队内推活动正式开启&#xff0c;岗位列表见&#xff1a;https://job.toutiao.com/s/eNtDcGu。除了这个投递连接外…

小米4A千兆刷OpenWrt_Win10

在Linux上试了一下&#xff0c;最终telnet 196.168.31.1失败&#xff0c;网上找了一些教程&#xff0c;改到win10下刷成功了。 1 先安装Pthon3 和pip3&#xff0c;然后pip3 install requests&#xff0c;不然会报错 2 win10开启telnet&#xff0c;方法简单自行百度&#xff1…

小米平板2可以装鸿蒙系统,详细教程!教你小米平板2轻松刷Win10

众所周知&#xff0c;小米平板2拥有MIUI和Windows 10两个版本&#xff0c;这两个版本在硬件上是一致的(除了机身存储空间不同)&#xff0c;所以理论上存在通刷的可能。 现在&#xff0c;有网友在MIUI论坛中共享了小米平板2刷Windows 10的教程&#xff0c;有兴趣的不妨一起来看看…

win10 下载

win10 下载 https://www.microsoft.com/zh-cn/software-download/windows10 Windows 10 2022 更新 l 版本 22H2 选择版本 以下 Windows 10 版本对于 Windows 10 家庭版和 Windows 10 专业版都有效。 如果您想验证下载数据的完整性和真实性&#xff0c;请按照以下步骤操作&…

计算机连接小米usb驱动,win10系统安装小米usb驱动的详细步骤

随着电脑的使用率越来越高&#xff0c;我们有时候可能会遇到对win10系统安装小米usb驱动进行设置&#xff0c;如果我们需要对win7系统安装小米usb驱动进行设置时&#xff0c;要怎么处理win10系统安装小米usb驱动的设置方法非常简单。 设置方法&#xff1a; 1、首先先下载小米驱…

win10 android 手机驱动下载,小米手机驱动win10驱动

小米手机usb驱动win10驱动是Win10系统专用的小米手机USB连接驱动&#xff0c;Win10电脑想要通过USB数据线与小米手机连接&#xff0c;必需安装这个驱动&#xff0c;从而可以使用电脑管理手机中的文件&#xff0c;以及进行线刷、解锁等操作&#xff0c;支持32位以及64位的Win10系…

【日常技巧】小米手机投屏至win10笔记本

最近需要多次实现自己手机与电脑的投屏&#xff0c;却又不想安装其他第三方软件&#xff0c;最终找到方法&#xff0c;做以下记录。 系统说明 手机&#xff1a;MIUI12.0.2稳定版 电脑&#xff1a;win10 前提条件 手机与电脑同处于同一wifi下 操作步骤 1.打开win10电脑投屏…