Linux嵌入式学习-ds18b20驱动
ds18b20的时序图如下:
复位时序:
读写时序:
以下是程序代码:
#include <linux/module.h>
#include <linux/init.h>
#include <linux/miscdevice.h>
#include <linux/interrupt.h>
#include <linux/io.h>
#include <linux/fs.h>
#include <linux/slab.h>
#include <asm/irq.h>
#include <linux/random.h>
#include <linux/uaccess.h>
#include <linux/device.h>
#include <linux/delay.h>
#include <mach/gpio.h>
#include <linux/mutex.h>
#define GPH3_0CON 0xE0200C60
#define GPH3_0DAT 0xE0200C64
#define GPH3_0PUD 0xE0200C68
unsigned int *gpio_config;
unsigned char *gpio_data;
unsigned int *gpio_pud;
static struct class *fog_class; //´´½¨Àà
static struct class_device *fog_class_devs; //´´½¨Àà¶ÔÓ¦µÄÉ豸
int major;
struct mutex res_mutex;
void Ds18b20_Pin_Init(void)
{
unsigned int pin_val;
gpio_request(S5PV210_GPH3(0),"my_ds1802");
gpio_config = ioremap(GPH3_0CON,4);
gpio_data = ioremap(GPH3_0DAT,1);
gpio_pud = ioremap(GPH3_0PUD,2);
pin_val = readl(gpio_pud);
pin_val &=~(0x0003);
pin_val |= 0x2;
writel(pin_val,gpio_pud);
pin_val = readl(gpio_data);
writel(pin_val|0x1,gpio_data);
}
void DS18B20_OUT( unsigned char value)
{
if( value == 1)
{
gpio_direction_output( S5PV210_GPH3(0), 1);
}
else
{
gpio_direction_output( S5PV210_GPH3(0), 0);
}
}
unsigned char DS18B20_IN( void )
{
unsigned int pin_val;
gpio_direction_input( S5PV210_GPH3(0));
pin_val = readl(gpio_data);
return pin_val&0x1;
}
static void Init_DS18B20(void)
{
gpio_direction_output( S5PV210_GPH3(0), 1);
udelay(200);
gpio_direction_output( S5PV210_GPH3(0), 0);
udelay(600);
gpio_direction_output( S5PV210_GPH3(0), 1);
udelay(480);
}
static void WriteCode(unsigned char dat)
{
unsigned char temp,i;
for(i=0;i<8;i++)
{
temp = dat&0x01;
gpio_direction_output( S5PV210_GPH3(0), 1);
udelay(2);
gpio_direction_output( S5PV210_GPH3(0), 0);
if(temp == 0x01)
{
udelay(2);
gpio_direction_output( S5PV210_GPH3(0), 1);
udelay(100);
}else{
udelay(100);
gpio_direction_output( S5PV210_GPH3(0), 1);
udelay(3);
}
dat = dat>>1;
}
}
static void Reset_DS18B20( void )
{
gpio_direction_output( S5PV210_GPH3(0), 0);
udelay(500);
gpio_direction_output( S5PV210_GPH3(0), 1);
udelay(480);
}
static unsigned int ReadData(void)
{
unsigned int rec,data,i;
data = 0;
for(i=0;i<16;i++)
{
gpio_direction_output( S5PV210_GPH3(0), 0);
udelay(5);
udelay(3);
rec = DS18B20_IN();
udelay(20);
if(rec){
data |= 0x8000;
}else{
data &= 0x7fff;
}
if(i<15)
data >>=1;
udelay(20);
gpio_direction_output( S5PV210_GPH3(0), 1);
udelay(5);
}
return (data);
}
int ds18b20_open(struct inode *node, struct file *filp)
{
return 0;
}
static int ds18b20_read(struct file * file, char * buffer, size_t count, loff_t *ppos)
{
int tem;
int ds_value;
mutex_lock_interruptible(&res_mutex);
Ds18b20_Pin_Init();
Init_DS18B20();
WriteCode(0xcc);
WriteCode(0x44);
gpio_direction_input( S5PV210_GPH3(0));
udelay(100);
tem = DS18B20_IN();
if(tem)
{
gpio_direction_output( S5PV210_GPH3(0), 1);
Reset_DS18B20();
WriteCode(0xcc);
WriteCode(0xbe);
ds_value = ReadData();
}else{
udelay(50);
ds_value = 0xaaaa;
}
mutex_unlock(&res_mutex);
copy_to_user(buffer, &ds_value, 4);
return sizeof ds_value;
}
static struct file_operations ds18b20_fops =
{
.open = ds18b20_open,
.read = ds18b20_read,
};
static int Ds18b20_init(void)
{
major = register_chrdev( 0,"ds18b20_drv", &ds18b20_fops );
fog_class = class_create(THIS_MODULE,"ds18b20_class");
fog_class_devs = device_create(fog_class,NULL,MKDEV(major,0),NULL,"my_ds1802");
mutex_init(&res_mutex);
printk("install module successed\n");
return 0;
}
void Ds18b20_exit(void)
{
unregister_chrdev( major, "ds18b20_drv" );
device_unregister(fog_class_devs);
class_destroy(fog_class);
}
module_init(Ds18b20_init);
module_exit(Ds18b20_exit);
MODULE_LICENSE("GPL");
Linux嵌入式学习-ds18b20驱动的更多相关文章
- Linux嵌入式学习-烟雾传感器驱动-字符设备驱动-按键驱动
MQ-2烟雾气敏传感器模块在X210v3开发板上的驱动. 现在需要一个MQ-2烟雾气敏传感器模块的驱动.其检测烟雾超过一定的标准后,会返回一个不同的电平,和按键驱动差不多. 但是在编写驱动的时候,需要 ...
- Linux嵌入式学习-mount命令+nfs挂载失败原因【转】
NFS 挂载失败原因[待搜集] 1.挂载时若出现mount.nfs: Input/output error 解决:在客户端也需启动portmap服务 service portmap status[查看 ...
- Linux嵌入式学习-USB端口号绑定
由于ubuntu USB设备号为从零开始依次累加,所以多个设备每次开机后设备号不固定,机器人每次开机都要蛋疼的按顺序插, 在网上找到一种方法:udev的规则 udev的规则说明,可以参考博客说明:ht ...
- Linux嵌入式学习-交叉编译openssl
利用arm-none-linux-gnueabi-gcc交叉编译openssl,生成静态库文件libcrypto.a ,libssl.a 1.从openssl官网下载openssl最新版本,我下载的是 ...
- Linux嵌入式学习-远程过程调用-Binder系统
Binder系统的C程序使用示例IPC : Inter-Process Communication, 进程间通信RPC : Remote Procedure Call, 远程过程调用 这里我们直接只用 ...
- Linux嵌入式学习-网络配置-ping外网、主机和域名
之前用的nfs挂载的文件系统,今天用yaffs2制作的文件系统并写入到nandflash中.但是网络却无法使用了. 首先,我们配置网卡. ifconfig eth0 192.168.1.230 bro ...
- Linux嵌入式学习-Mplayer交叉编译-undefined reference to `clock_gettime' MPlayer
編譯Mplayera. 配置.configure# ./configure --host-cc=gcc --cc=arm-linux-gcc --target=arm --enable-static ...
- Linux嵌入式学习-交叉编译mplayer
http://bbs.gkong.com/archive.aspx?ID=286721
- Linux内核调用I2C驱动_驱动嵌套驱动方法
禁止转载!!!! Linux内核调用I2C驱动_以MPU6050为例 0. 导语 最近一段时间都在恶补数据结构和C++,加上导师的事情比较多,Linux内核驱动的学习进程总是被阻碍.不过,十一假期终于 ...
随机推荐
- 第6.2节 Python特色的动态可执行方法简介
一. 基本概念 动态可执行,是指在代码中通过外部输入或代码嵌入的常量字符串包含代码的方式提供Python代码,要求Python执行这些代码.这样就可以达到开放式运行的效果,提高程序的能力和灵活性 ...
- 第10.11节 Python模块和包小结
Python的模块就是一个独立的Python文件,Python的包是一些功能相关的Python文件放到一个目录下进行统一管理的文件管理结构,包本质上是模块,加载包就是加载包下特定的模块文件__init ...
- 第11.15节 Python正则表达式转义符定义的特殊序列
一. 引言 在前面<第11.13节 Python正则表达式的转义符"\"功能介绍>介绍了正则表达式转义符'\',只不过当时作为转义符主要是用于在正则表达式中表示元字符自 ...
- 混合云存储打开的正确姿势——腾讯云存储网关 CSG
近年来,随着云计算的发展,越来越多的企业选择将IT系统基础设施转移到云上,上云有助于推动企业加快信息化.数字化.智能化的转型,但是很多企业对传统的业务系统依赖程度较高,短时间内将业务迁移上云将会面临很 ...
- mock.js 和easy-mock使用
mock.js 1.项目中引入mock.js <script src="../static/js/mock.js" type="text/javascript&qu ...
- NOI2008 志愿者招聘
文化课 + 竞赛双废物又来水题解了. 首先,对于题干中的人,很像网络流中的流量,但是他有一个每天人数的下限,我从网上借鉴(chaoxi)到了两种思路: 把下界限制转化为一条边的流量下界,这样就是最小费 ...
- Kubernetes Python Client 初体验之node操作
今天讲一下k8s中对于各个实物节点node的操作. 首先是获取所有nodes信息: self.config.kube_config.load_kube_config(config_file=" ...
- Typora快捷使用方式
快捷使用: 1.一级标题 # + 空格 + 内容 2.六级标题 # + 空格 + 内容 3.有序序号 1. + 空格 + 内容 4.无序序号 -+ 空格.*+空格.++空格 5.代码块 ```pyth ...
- Jmeter(10)逻辑控制器
逻辑控制器可以控制采样器的执行顺序,所以控制器需要和采样器一起使用 Jmeter中的逻辑控制器分为两类 1.控制测试计划执行过程中节点的逻辑顺序,如循环控制器.If控制器 2.对测试计划中的脚本进行分 ...
- PDCA
Plan(规划) Do(执行) Check(验证) Adjust(调整)