1. bread鸿运国际论坛/
  2. 厂商专区/
    1. 电子论坛综合区
    2. 嵌入式论坛
    3. 电源技术论坛
    4. 硬件设计论坛
    5. 测试测量论坛
    6. 检测技术与质量
    7. EDA设计论坛
    8. 综合技术与应用
    9. 开源硬件
    10. IC设计论坛
    11. 消费电子论坛
    12. 无线通信论坛
    13. 个人版区
    14. 厂商专区
    15. 论坛服务区
    16. 高校联盟
    17. 供求信息发布
  3. 盈鹏飞嵌入式
    1. 灵动微电子 MM32
    2. TI论坛
    3. TI Deyisupport社区
    4. 芯灵思嵌入式论坛
    5. Tisan
    6. 米尔科技
    7. 庆科社区
    8. 优易特电子
    9. WIZnet技术专区
    10. Cypress技术论坛
    11. 飞凌嵌入式
    12. Qualcomm技术论坛
    13. 英创嵌入式
    14. 机智云GoKit论坛
  4. / 【EVB-T335开发板试用体验】- 基于I2C的温度传感器项目 ...
    关闭提示

[作品] 【EVB-T335开发板试用体验】- 基于I2C的温度传感器项目(结项)

[复制链接]
实习生
发表于 2017-5-8 08:34:37   1103 查看 3 回复 只看该作者 倒序浏览
分享


本项目最终使用的是数字式温度传感器对温度数值进行探测,使用app对数据进行读取和反馈
数字式温度传感器通过I2C连接:
I2C(Inter-Integrated Circuit)总线是由PHILIPS公司开发的两线式串行总线,用于连接微控制器及其外围设备。是微电子通信控制领域广泛采用的一种总线标准。它是同步通信的一种特殊形式,具有接口线少,控制方式简单,器件封装形式小,通信速率较高等优点。I2C 总线支持任何IC 生产工艺(CMOS、双极型)。通过串行数据(SDA)线和串行时钟 (SCL)线在连接到总线的器件间传递信息。每个器件都有一个唯一的地址识别(无论是微控制器——MCU、LCD 驱动器、存储器或键盘接口),而且都可以作为一个发送器或接收器(由器件的功能决定)。LCD 驱动器只能作为接收器,而存储器则既可以接收又可以发送数据。除了发送器和接收器外,器件在执行数据传输时也可以被看作是主机或从机(见表1)。主机是初始化总线的数据传输并产生允许传输的时钟信号的器件。此时,任何被寻址的器件都被认为是从机。


温度传感器芯片介绍:
LM75A是一款内置带隙温度传感器和∑-Δ模数转换功能的温度数字转换器,它也是温度检测器,可提供过热输出功能。LM75A包含多个数据寄存器:配置寄存器(Conf)用来存储器件的某些设置,如器件的工作模式、OS工作模式、OS极性和OS错误队列等;温度寄存器(Temp)用来存储读取的数字温度;设定点寄存器(Tos & Thyst)用来存储可编程的过热关断和滞后限制,器件通过两线的串行I2C总线接口与控制器通信。LM75A还包含一个开漏输出(OS)管脚,当温度超过编程限制的值时该输出有效。LM75A有3个可选的逻辑地址管脚,使得同一总线上可同时连接8个器件而不发生地址冲突。
  LM75A可配置成不同的工作模式。它可设置成在正常工作模式下周期性地对环境温度进行监控,或进入关断模式来将器件功耗降至最低。OS输出有2种可选的工作模式:OS比较器模式和OS中断模式。OS输出可选择高电平或低电平有效。错误队列和设定点限制可编程,可以激活OS输出。
  温度寄存器通常存放着一个11位的二进制数的补码,用来实现0.125℃的精度,在需要精确地测量温度偏移或超出限制范围的应用中非常有用。当LM75A在转换过程中不产生中断(I2C总线部分与∑-Δ转换部分完全独立)或LM75A不断被访问时,器件将一直更新温度寄存器中的数据。
  正常工作模式下,当器件上电时,OS工作在比较器模式,温度阈值为80℃,滞后75℃,这时,LM75A就可用作独立的温度控制器,预定义温度设定点。
管脚号
符号
功能
1
SDA
串行数据线
2
SCL
串行时钟线
3
OS
过热关断输出,开漏
4
GND
5
A2
用户定义的地址位2
6
A1
用户定义的地址位1
7
A0
用户定义的地址位0
8
VCC
电源


其中温度寄存器0x00,配置寄存器0x01,滞后寄存器0x02,过温保护寄存器0x03,只要对对应寄存器读取特定的数值即可。

因为选择了linux 系统,所以我们将驱动与应用分开,下面就来看下我们的实际代码:

驱动代码,主要负责读取数据,与底层硬件通讯,在这里是负责与温度传感器的I2C进行交互,即直接对I2C的寄存器进行读取信息

  • #include <linux/module.h>
  • #include <linux/init.h>
  • #include <linux/fs.h>
  • #include <linux/device.h>
  • //#include <linux/leds.h>
  • #include <linux/gpio.h>
  • #include <linux/errno.h>
  • #include <linux/types.h>
  • #include <asm/uaccess.h>
  • #include <linux/miscdevice.h>
  • #include <linux/gpio.h>
  • #include <linux/poll.h>
  • #include <linux/cdev.h>
  • #include <linux/wait.h>
  • #include <linux/sched.h>
  • #include <linux/semaphore.h>
  • #include <linux/timer.h>
  • #include <linux/jiffies.h>
  • #include <linux/i2c.h>
  • #include <linux/slab.h>
  • #include <linux/miscdevice.h>


  • #define LM75A_ADDR 0x48
  • #define CMD_SET_ROM_ADRR 0x01

  • #define DEBUG 1
  • #ifdef DEBUG
  • #define DEV_DEBUG(...) printk(__VA_ARGS__);
  • #endif

  • #define LM75X_CONF_REG 0x01

  • static const u8 LM75X_REG_TEMP[3] = {
  •     00,
  •     02,
  •     03,
  • };


  • struct lm75x_data{
  •   struct i2c_client *i2c_client;
  •   struct device *dev;
  •   u8 old_config;
  •   u16 temp[3];  // 0 input / 1 max  / 2 hyst
  • };

  • struct lm75x_data *data;


  • static int lm75_read_value(struct i2c_client *client, u8 reg)
  • {
  •         if (reg == LM75X_CONF_REG)
  •                 return i2c_smbus_read_byte_data(client, reg);
  •         else
  •                 return i2c_smbus_read_word_swapped(client, reg);
  • }


  • static int lm75_write_value(struct i2c_client *client, u8 reg, u16 value)
  • {
  •         if (reg == LM75X_CONF_REG)
  •                 return i2c_smbus_write_byte_data(client, reg, value);
  •         else
  •                 return i2c_smbus_write_word_swapped(client, reg, value);
  • }

  • static u16 read_reg_value(struct i2c_client *client, u8 reg)
  • {
  •   u16 temp_state = 0;
  •   temp_state = lm75_read_value(client, reg);

  •   if (reg == 0x00){
  •       temp_state = temp_state >> 5;
  •      // temp_state && 0x1ff;
  •       return temp_state;
  •   }
  • }

  • static const struct i2c_device_id lm75x_id[] = {
  •   {"lm75a", 0},
  •   {"lm75b", 1},
  •   {}
  • };

  • MODULE_DEVICE_TABLE(i2c, lm75x_id);

  • long lm75x_ioctl(struct file *filp, unsigned int cmd, unsigned long args)
  • {
  •   int ret = 0;




  •    return ret;
  • }


  • ssize_t lm75x_write(struct file *filp, const char __user *buf, size_t count, loff_t *loff)
  • {
  •   int ret = 0;




  •    return ret;
  • }

  • ssize_t lm75x_read(struct file *filp, char __user *buf, size_t count, loff_t *loff)
  • {
  •   int ret = 0;
  •   u16 temp_state = 0;
  •   char temp[2];

  •   temp_state = read_reg_value(data->i2c_client, 0x00);
  •   //temp = (char)temp_state;
  •   temp[0] = (char)(temp_state & 0x00FF);
  •   temp[1] = (char)(temp_state >> 8);
  •   DEV_DEBUG("temp[0] = %x\n", temp[0]);
  • // DEV_DEBUG("temp_state = %x \n", temp_state);
  •   if (copy_to_user(buf, &temp, count)){
  •       ret = -EFAULT;
  •   }
  •   DEV_DEBUG("temp_state = %x \n", temp_state);
  •   DEV_DEBUG("buf = %x \n", temp);
  • //  /lm75_read_value();


  •   return ret;
  • }

  • int lm75x_oepn(struct inode *node , struct file *filp)
  • {

  •   return 0;
  • }

  • static const struct file_operations lm75x_fops ={
  •    .owner = THIS_MODULE,
  •   // .open = lm75x_oepn,
  •   // .release = lmx75x_remove,
  •    .read = lm75x_read,
  •    .write = lm75x_write,
  •    .unlocked_ioctl = lm75x_ioctl,
  • };


  • static struct miscdevice lm75x_misc = {
  •     .name = "lm75x_misc",
  •     .minor = 99,
  •     .fops = &lm75x_fops,
  • };


  • int lm75x_probe(struct i2c_client *i2c_client, const struct i2c_device_id *i2c_device_id)
  • {
  •   int err = 0;
  •   int conf_state, old_conf;
  •   data = kzalloc(sizeof(struct lm75x_data), GFP_KERNEL);
  •   if (!data)
  •     return -ENOMEM;
  •   data->i2c_client = i2c_client;
  •   dev_set_drvdata(&i2c_client->dev, data);

  •   if (!i2c_check_functionality(i2c_client->adapter,I2C_FUNC_SMBUS_BYTE_DATA | I2C_FUNC_SMBUS_WORD_DATA))
  •                   return -EIO;

  •   conf_state = lm75_read_value(i2c_client, LM75X_CONF_REG);
  •   DEV_DEBUG("conf_state = %02x \n", conf_state);
  •   if (!conf_state)
  •     data->old_config = conf_state;

  •   err = misc_register(&lm75x_misc);

  •   DEV_DEBUG("sizeof data = %d \n", sizeof(*data));
  •   if (err) {
  •       printk("miscdevice is fail\n");
  •       return err;
  •     }

  •   printk("i2c is detected \n");
  • #if 0
  •   data->temp[0] = lm75_read_value(i2c_client, 0x00);
  •   DEV_DEBUG("state-pre = %x \n", state);
  •   state = state >> 5;
  •   printk("state = %x \n", state);

  •   tys = lm75_read_value(i2c_client, 0x02);
  •   DEV_DEBUG("tys-pre = %x \n", tys);
  •   tys = tys >> 7;
  •   printk("tys = %x \n", tys);

  •   tos = lm75_read_value(i2c_client, 0x03);
  •   DEV_DEBUG("tos-pre = %x \n", tos);
  •   tos = tos >> 7;
  •   printk("tos = %x \n", tos);

  •   lm75_write_value(i2c_client, 0x03, 0xa1 << 7);

  •   tos = lm75_read_value(i2c_client, 0x03);
  •   DEV_DEBUG("tos-pre = %x \n", tos);
  •   tos = tos >> 7;
  •   printk("tos = %x \n", tos);


  • #endif
  •   return 0;
  • }


  • int lm75x_remove(struct i2c_client *i2c_client)
  • {
  •   struct lm75x_data *data = dev_get_drvdata(&i2c_client->dev);
  •   misc_deregister(&lm75x_misc);
  •   kfree(data);
  •   printk("remove the i2c \n");
  •   return 0;
  • }

  • static unsigned short normal_i2c[] = { 0x48, 0x49, 0x4a, 0x4b, 0x4c,
  •          0x4d, 0x4e, 0x4f, I2C_CLIENT_END };


  • static struct i2c_driver lm75x_driver = {
  •   .driver = {
  •       .name = "lm75a",
  •   },
  •   .probe = lm75x_probe,
  •   .remove = lm75x_remove,
  •   .id_table = lm75x_id,
  •   .address_list = normal_i2c,
  • };

  • static int __init lm75x_init(void)
  • {
  •   i2c_add_driver(&lm75x_driver);
  •   return 0;
  • }

  • static void __exit lm75x_exit(void)
  • {<div class="blockcode"><blockquote>
  • 复制代码

      i2c_del_driver(&lm75x_driver);
    }


    module_init(lm75x_init);
    module_exit(lm75x_exit);

    MODULE_LICENSE("GPL");
    应用程序,负责对驱动进行操作,比如何时读,何时配置等,这些我们一般都放在应用层来执行

  • #include <stdio.h>
  • #include <stdlib.h>
  • #include <unistd.h>
  • #include <syspes.h>
  • #include <sys/stat.h>
  • #include <fcntl.h>
  • #include <termios.h>
  • #include <errno.h>

  • #define I2C_DEV_NAME "/dev/lm75x_misc"

  • #define DATA_LEN 20

  • char buf[DATA_LEN];

  • int main(int arg,char*args[])
  • {
  • int fd;
  • float temp;

  • fd = open(I2C_DEV_NAME, O_RDWR);
  • if(fd < 0) {
  • printf("open %s failed\r\n", I2C_DEV_NAME);
  • return -1;
  • }
  • printf("success \n");

  • read(fd, buf, DATA_LEN);

  • //printf("temp = %s \n", buf);

  • temp = (float)buf[0] * 0.125;
  • printf("temp = %.03f \n", temp);



  • return 0;

  • }
  • 复制代码
    应用程序主要负责读取驱动的数值,在linux中使用sysfs 对设备进行操作。

    到这里我们就完成了对温度传感器的数据采集的效果。
    标签:温度传感器
    发表于 2017-5-10 10:37:44  

    PCB在线计价下单

    板子大小:

    cm
    X
    cm

    层数:

    2

    板子数量:

    10

    厚度:

    1.6
    lz有效果演示嘛?
    回复 点赞
    实习生
    发表于 2017-5-11 14:19:11    楼主|

    有的,就是执行./app 我效果
    回复 点赞
    技术员
    发表于 2017-6-14 14:03:20  
    驱动框架写的不错,就是功能太简单了。。就读个数就完事了啊?
    回复 点赞
    高级模式
    您需要登录后才可以回帖 登录 | 注册
    专家问答 查看更多>>
    1. 资深电源专家带你高效掌握PFC功率因素校正 松山归人 17个问题        11851个浏览 提问
    2. 研发这样省才靠谱,NI大牛教你挑战低成本极限 马力斯 21个问题        22828个浏览 提问
    3. 一线资深电机控制专家带你高级进阶 松山归人 69个问题        9125个浏览 提问
    关闭

    站长推荐 上一条 /7 下一条

    小黑屋|手机版|Archiver| 鸿运国际 ( 粤ICP备14022951号-2 )      GMT+8, 2017-6-28 06:35 , Processed in 0.109795 second(s), 17 queries , Memcache On.
    Powered by 鸿运国际网 © 2015 bbs.elecfans.com
    微信扫描
    快速回复 返回顶部 返回列表
    1. time最新主题
    2. recommend推荐主题
    3. hot热门主题
    4. post 我的帖子
    -

    推荐专区

    技术干货集中营

    专家问答

    用户帮助┃咨询与建议┃版主议事

    我的提问

    工程师杂谈

    工程师创意

    工程师职场

    论坛电子赛事

    社区活动专版

    发烧友活动

    -

    嵌入式论坛

    单片机/MCU论坛

    FPGA|CPLD|ASIC论坛

    DSP论坛

    嵌入式系统论坛

    -

    电源技术论坛

    电源技术论坛

    -

    硬件设计论坛

    电路设计论坛

    电子元器件论坛

    控制|传感

    总线技术|接口技术

    -

    测试测量论坛

    LabVIEW论坛

    Matlab论坛

    测试测量技术专区

    仪器仪表技术专区

    -

    EDA设计论坛

    multisim论坛

    PCB设计论坛

    proteus论坛|仿真论坛

    EasyEDA-中国人自已的EDA工具

    -

    综合技术与应用

    电机控制

    智能电网

    光电及显示

    参考设计中心

    汽车电子技术论坛

    医疗电子论坛

    -

    开源硬件

    DFRobot专区

    树莓派论坛

    智能硬件论坛

    开发快智能硬件开发平台

    Intel物联网开发者专区

    Waveshare

    乐美客SBC专区

    Arduino论坛

    BeagleBone论坛

    机器人论坛

    创客神器NanoPi

    小钢炮CANNON

    比派科技banana pi专区

    -

    无线通信论坛

    无线通信技术专区

    天线|RF射频|微波|雷达技术

    -

    IC设计论坛

    芯片测试与失效分析

    Mixed Signal/SOC[数模混合芯片设计]

    Analog/RF IC设计

    设计与制造封装测试

    -

    个人版区

    阿东Verilog技术专版

    直流马达驱动电路设计

    LabVIEW英雄联盟

    特权同学FPGA专区

    -

    厂商专区

    灵动微电子 MM32

    盈鹏飞嵌入式

    TI论坛

    TI Deyisupport社区

    芯灵思嵌入式论坛

    Tisan

    米尔科技

    庆科社区

    WIZnet技术专区

    Cypress技术论坛

    飞凌嵌入式

    Qualcomm技术论坛

    英创嵌入式

    机智云GoKit论坛

    -

    检测技术与质量

    电磁兼容(EMC)设计与整改

    安规知识论坛

    检测与认证

    -

    消费电子论坛

    手机技术论坛

    平板电脑/mid论坛

    音视/视频/机顶盒论坛

    -

    电子论坛综合区

    聚丰众筹官方社区

    新人报道区

    聚丰供应链

    -

    论坛服务区

    -

    供求信息发布

    供需广告

    招聘┃求职发布区

    电子展览展会专区

    鸿运国际手机欢迎你