/****************************************************************************** 版权所有: 文件名称: aht20.c 文件版本: 01.01 创建作者: Ewen 创建日期: 2025-11-10 功能说明: aht20驱动程序。 其它说明: 修改记录: /*------------------------------ 头文件 --------------------------------------- */ #include #include #include #include #include #include "head.h" #ifdef TMP_CHIP_AHT20 /*------------------------------ 宏定义 --------------------------------------- */ #define I2C_DEV "/dev/i2c-5" // 以下定义见AHT20 datasheet // AHT20 设备地址 #define AHT20_I2C_ADDR 0x38 // AHT20 命令字 #define AHT20_CMD_INIT 0xBE #define AHT20_CMD_MEAS 0xAC #define AHT20_CMD_RESET 0xBA /*------------------------------ 全局变量 ------------------------------------- */ struct aht20 aht20; int g_aht20_fd; /*------------------------------ 函数声明 ------------------------------------- */ // AHT20 初始化 static int _aht20_init(int fd) { uint8_t init_cmd[3] = {AHT20_CMD_INIT, 0x08, 0x00}; if (write(fd, init_cmd, sizeof(init_cmd)) != sizeof(init_cmd)) { printf("Failed to send init command: %s\n", strerror(errno)); return -1; } return 0; } // AHT20 软复位 static int _aht20_soft_reset(int fd) { uint8_t reset_cmd = AHT20_CMD_RESET; if (write(fd, &reset_cmd, sizeof(reset_cmd)) != sizeof(reset_cmd)) { printf("Failed to send reset command: %s\n", strerror(errno)); return -1; } return 0; } // 读取温湿度数据 static int _aht20_read_data(int fd, float* temperature, float* humidity) { uint8_t cmd[3] = {AHT20_CMD_MEAS, 0x33, 0x00}; uint8_t data[6] = {0}; uint32_t temp_raw = 0, humi_raw = 0; // 发送测量命令 if (write(fd, cmd, sizeof(cmd)) != sizeof(cmd)) { printf("Failed to send measure command: %s\n", strerror(errno)); return -1; } // 等待测量完成(最多100ms) int timeout = 0; while (timeout < 100) { msleep(1); if (read(fd, data, 1) == 1) { if (!(data[0] & 0x80)) { // 检查忙标志位 break; } } timeout++; } if (timeout >= 100) { printf("AHT20 measurement timeout\r\n"); return -1; } // 读取测量数据 if (read(fd, data, sizeof(data)) != sizeof(data)) { printf("Failed to read measurement data: %s\r\n", strerror(errno)); return -1; } // 检查数据状态位 if ((data[0] & 0x68) != 0x08) { printf("AHT20 data not ready or invalid\r\n"); return -1; } // 解析湿度数据(20位) humi_raw = ((uint32_t)data[1] << 12) | ((uint32_t)data[2] << 4) | ((uint32_t)data[3] >> 4); // 解析温度数据(20位) temp_raw = (((uint32_t)data[3] & 0x0F) << 16) | ((uint32_t)data[4] << 8) | data[5]; // 转换为实际值 *humidity = (float)humi_raw * 100.0 / (1 << 20); *temperature = (float)temp_raw * 200.0 / (1 << 20) - 50.0; return 0; } int aht20_init(void) { memset(&aht20, 0, sizeof(aht20)); // 打开I2C设备 g_aht20_fd = open(I2C_DEV, O_RDWR); if (g_aht20_fd < 0) { printf("Failed to open I2C device %s: %s\n", I2C_DEV, strerror(errno)); return -1; } // 设置从设备地址 if (ioctl(g_aht20_fd, I2C_SLAVE, AHT20_I2C_ADDR) < 0) { printf("Failed to set I2C slave address: %s\n", strerror(errno)); close(g_aht20_fd); return -1; } _aht20_soft_reset(g_aht20_fd); msleep(100); if(_aht20_init(g_aht20_fd) == 0) { printf("aht20 init success!\r\n"); } else { printf("aht20 init failed!\r\n"); close(g_aht20_fd); g_aht20_fd = -1; return -1; } aht20.us0 = bsp_ustimer_get_origin(); return 0; } int aht20_exit(void) { if(g_aht20_fd >= 0) { close(g_aht20_fd); g_aht20_fd = -1; } return 0; } void aht20_task(void) { if(bsp_ustimer_get_duration(aht20.us0) < USTIMER_SEC*5 || g_aht20_fd < 0) { return; } aht20.us0 = bsp_ustimer_get_origin(); _aht20_read_data(g_aht20_fd, &aht20.temp, &aht20.humi); // printf("aht20.temp=%.3f ℃, aht20.humi=%.3f %%RH\r\n", aht20.temp, aht20.humi); } float aht20_get_temp(void) { if(g_aht20_fd < 0) { // 校准系数判断 温度低于-85℃时为异常状态,温度补偿系数默认改为1.0, // 因此此处在初始化失败时返回-100.0℃ return -100.0; } return aht20.temp; } float aht20_get_humi(void) { return aht20.humi; } #endif /* TMP_CHIP_AHT20 */