7. NodeMCU上使用RTOS固件读取bh1750传感器数据的实践
来源:互联网 发布:js遍历json对象数组 编辑:程序博客网 时间:2024/05/01 04:00
NodeMCU上使用RTOS固件读取bh1750传感器数据的实践
本文主要是尝试在NodeMCU(硬件)上,使用RTOS(固件、OS)来控制bh1750光照传感器,
采集亮度数据。
关于RTOS固件的编译环境和编译方式的介绍,可参照之前的文章。
ESP8266固件的编译5(RTOS SDK固件)
但是在RTOS固件下,只内置了很少的传感器驱动,bh1750并没有被支持。
需要自己根据I2C协议实现简单的驱动。
(nodeMCU的lua固件预置了相当多的、也包含bh1750的传感器驱动,
作为参考,可参照lua版本的驱动实现 nodemcu-firmware/lua_modules)
bh1750通信通过I2C协议,关于I2C协议本身,可以参照如下文章,有清晰的解释。
http://blog.chinaunix.net/uid-25906157-id-3585430.html
1、I2C驱动库的编译
Esp8266没有硬件I2C接口,是用GPIO软件模拟的,坏处是性能差,好在模拟也不复杂。
RTOS固件开发环境下提供了一个Driver库,内置I2C、SPI、UART等通信实现。
第一步自然是编译这个库。
编译过程中,出现一些问题,应该是维护人员的粗心所致。要如下方法修改:
进入ESP8266_RTOS_SDK\driver_lib\driver目录,如下修正i2c_master.c文件。
1) 增加头文件
#include "c_types.h"#include "esp8266/ets_sys.h"#include "esp8266/eagle_soc.h" /* 新增加头文件 */#include "esp8266/gpio_register.h" /* 新增加头文件 */#include "gpio.h"
2) 修改宏/函数名
在i2c_master_gpio_init函数中,将
ETS_GPIO_INTR_DISABLE() ;ETS_GPIO_INTR_ENABLE() ;
修改为
ETS_INTR_LOCK(); ETS_INTR_UNLOCK();
3)默认的SDA和SCL管脚定义
默认的I2C的SDA和SCL管脚在i2c_master.h中定义,其默认值为
SDA -- GPIO2SCL -- GPIO4
需要变更的话,可修改此文件。
4)编译
在ESP8266_RTOS_SDK\driver_lib目录下,执行
$ make_lib.sh driver
成功编译成功后,在ESP8266_RTOS_SDK/lib目录下会生成新的libdriver.a。
执行如下命令,能找到i2c对应函数的符号信息。
$nm –A libdriver.a | grep i2c
2、 bh1750驱动的实现
仿照lua版,只实现了【连续 H 分辨率模式】下的数据读取。
Bh1750的I2C接口的说明:
A)Slave地址有 2 种形式,由 ADDR 端口决定。
ADDR=“H” ( ADDR ≧ 0.7VCC ) →“1011100”ADDR=“L” ( ADDR ≦ 0.3VCC ) →“0100011”
B)bh1750的I2C数据读取协议,如图
C)简单实现如下(错误处理等省略)
uint8 addr = 0x23; // bh1750 i2c地址(low) 00100011uint8 cmd = 0x10; // bh1750 高分辨率模式 00010000void init_bh1750(){ // 初始化i2c总线 i2c_master_gpio_init();}uint16 read_bh1750_data(void){ uint8 b1 = 0x00; uint8 b2 = 0x00; uint32 data = 0x00; // 设置高分辨率模式 i2c_master_start(); i2c_master_writeByte( (addr << 1) ); i2c_master_getAck(); i2c_master_writeByte(cmd); i2c_master_getAck(); i2c_master_stop(); // 采集等待时间要求120ms以上 os_delay_us(60000); os_delay_us(60000); os_delay_us(60000); // 读取数据 i2c_master_start(); i2c_master_writeByte( (addr << 1) | 0x01 ); i2c_master_getAck(); b1 = i2c_master_readByte(); i2c_master_send_ack(); b2 = i2c_master_readByte(); i2c_master_send_ack(); i2c_master_stop(); // 计算结果(取得亮度数据为2字节、除1.2的阈值) data = b1 * 256 + b2; return (uint16)(data / 1.2);}
3. 固件入口函数user_init的实现
修改ESP8266_RTOS_SDK\examples\project_template\user\ user_main.c文件
(上面的bh1750驱动实现也可放在此文件中)
因为RTOS不允许在user_init中进行while(1)循环和睡眠等待,
因此用定时器来定时读取lux数据(也可以创建task)。代码如下:
LOCAL void ICACHE_FLASH_ATTR print_data(void* data){ printf("lux: %d\n", read_bh1750_data());}void user_init(void){ int i = 0; // 设置串口为 115200 波特率。不设的情况,默认波特率为78400 UART_ConfigTypeDef uart_config; uart_config.baud_rate = BIT_RATE_115200; uart_config.data_bits = UART_WordLength_8b; uart_config.parity = USART_Parity_None; uart_config.stop_bits = USART_StopBits_1; uart_config.flow_ctrl = USART_HardwareFlowControl_None; uart_config.UART_RxFlowThresh = 120; uart_config.UART_InverseMask = UART_None_Inverse; UART_ParamConfig(UART0, &uart_config); printf("----------------------\n"); printf("bh1750 reader\n"); printf("----------------------\n"); // 初始化I2C init_bh1750(); // 设置定时器 os_timer_disarm(&timer); os_timer_setfn(&timer, (os_timer_func_t *)print_data, NULL); os_timer_arm(&timer, 2000, 1);}
4. 固件编译
进入ESP8266_RTOS_SDK\examples\project_template目录,执行
make COMPILE=gcc BOOT=none APP=0 SPI_SPEED=40 SPI_MODE=DIO SPI_SIZE_MAP=4
如编译成功,则在BIN_PATH下会生成固件。
5.结果验证
1)接线
esp8266默认的GPIO定义和nodemcu的D管脚定义是不同的体系,使用nodemcu硬件是要注意。
直接用esp8266模块的话,根据gpio号接线就可以。
可参照下图:
接线如下:
SDA(bh1750) ---- D4(nodeMCU) ---- GPIO2(esp8266)SCL(bh1750) ---- D2(nodeMCU) ---- GPIO4(esp8266)VCC(bh1750) ---- 3.3vGND(bh1750) ---- GND(nodeMCU)ADDR(bh1750) ---- GND (使用bh1750的0x23地址)
接线效果图
2)固件下载
可参照以前的文章
" target="_blank">ESP8266固件的编译6(固件的下载)
3) 效果
用串口工具115200波特率连接nodeMCU硬件,
可以看到bh1750的数据被正常采集,且亮度能随场景变化而不同。
- 7. NodeMCU上使用RTOS固件读取bh1750传感器数据的实践
- 2. ESP8266固件的编译(nodemcu固件)
- 自己编译NodeMCU固件 & 提交数据到服务器
- win7下使用docker编译Nodemcu固件
- 自己动手编译NodeMCU固件
- 使用安信可ESP8266IDE编辑工具使用最新的乐鑫RTOS固件
- 使用Arduino读取水位传感器数据
- Nodemcu上使用Mongoose OS的坑(1)
- 8. ESP8266使用Mongoose-os初体验(使用bh1750传感器)
- 9. ESP8266使用esp-open-rtos的实践
- NodeMCU文档中文翻译 3 构建固件
- NodeMCU-入门之在线固件构建
- NodeMCU-入门之下载固件
- NodeMCU之AT固件与NodeMCU固件任意刷
- 5. ESP8266固件的编译(RTOS SDK固件)
- 关于 RTOS 的选择 (上)
- 关于 RTOS 的选择 (上)
- 关于 RTOS 的选择 (上)
- Tkinter 学习笔记 —— 第一个应用程序
- Unity中Update和FixedUpdate的区别
- Floyd判圈算法
- linux下的几种进程间通信方式的特点
- 关于集成Bmob遇到的坑
- 7. NodeMCU上使用RTOS固件读取bh1750传感器数据的实践
- html,xml,json入门Ajax例子
- Establishing SSL connection without server's identity verification is not recommended
- 设计模式之代理模式
- <s:property>
- angularjs指令-控制器
- 大数据流式分析系统框架(日志处理系统)
- 安卓数据存储方式之SQLite
- 解决CentOS遇到Qt编译(error: cannot find -lGL)