SDK版本:TLSR8258_TuyaOS-3.8.0
低功耗设备("dev_role":"sleep_end_dev"),在使用硬件i2c时,通过drv_i2c_read_series读取aht20传感器温湿度,发现读取失败(读取缓存pst->ReadByte全是0),但是通过逻辑分析仪抓取波形,是正常的。并且在代码原封不动的情况下,将appconfig.json中"dev_role"配置从改为"router",读取就正常了,数据也是对的。请问低功耗设备如何使用硬件i2c设备(尝试在__tuya_post_sleep_cb中重新初始化i2c和gpio配置(具体如下,还是不行):
Code: Select all
VOID_T __tuya_post_sleep_cb(VOID_T)
{
tal_main_debug("post_sleep_cb!!!\r\n");
drv_i2c_master_init(100000);
drv_i2c_gpio_set(I2C_GPIO_GROUP_C0C1);
}
BOOL_T tkl_gpio_output_use_wakeup_mode(TUYA_GPIO_NUM_E pin_id)
{
if((TUYA_GPIO_NUM_16 == pin_id) || (TUYA_GPIO_NUM_17 == pin_id) || (GPIO_APP_NET_LED == pin_id)){
return TRUE;
}
else
{
return FALSE;
}
}
I2C代码主要摘录如下:
Code: Select all
#define AHT20_SAMPLE_PERIOD 5000 //单位:ms, 且不小于MinReadTim
/* I2C Clock */
#define I2C_CLOCK 100000//100K
/* I2C slave ID */
#define I2C_SLAVE_ID 0x38
#define I2C_SLAVE_ADDR_LEN 1
#define ATH20_ADDR 0x38
#define AHT20_STATUS_REG 0x00 //状态字 寄存器地址
#define AHT20_INIT_REG 0xBE //初始化 寄存器地址
#define AHT20_SOFTRESET_REG 0xBA //软复位 单指令
#define AHT20_MEASURE_REG 0xAC //触发测量 寄存器地址
#define SENSOR_IDLE 0 //
#define SENSOR_MEASURE 1 //
#define SENSOR_COMPLETE 2 //
//****************************************
// 定义 AHT20 内部地址
//****************************************
#define ATH20_ADDR 0x38
#define AHT20_STATUS_REG 0x00 //状态字 寄存器地址
#define AHT20_INIT_REG 0xBE //初始化 寄存器地址
#define AHT20_SOFTRESET_REG 0xBA //软复位 单指令
#define AHT20_MEASURE_REG 0xAC //触发测量 寄存器地址
/*----------------------------------------------------------------------------
Section: Type Definitions
----------------------------------------------------------------------------*/
typedef struct
{
unsigned char Adrr;
unsigned int timcnt;
unsigned char ErrFlag;
unsigned char Step;
unsigned int SetRTim;
unsigned char SendByte[16];
unsigned char ReadByte[16];
float RH;//湿度
float T;//温度
}MYI2C_Struct;
static MYI2C_Struct SENx;
static TIMER_ID aht20_etimerid;
static TIMER_ID aht20_sample_etimerid;
/*******************************************************************************
* Function Name :
* Description :
* Input :None
* Output :None
* Return :None
*******************************************************************************/
static void MYI2C_Handle(TIMER_ID timer_id, VOID_T *arg)
{
MYI2C_Struct *pst = (MYI2C_Struct *)arg;
pst->Step = SENSOR_IDLE;
tal_sw_timer_start(aht20_sample_etimerid, 10, TAL_TIMER_ONCE);
//tkl_cpu_force_wakeup();
}
static void aht20_measure_handle(TIMER_ID timer_id, VOID_T *arg)
{
unsigned char i;
unsigned long s32x;
MYI2C_Struct *pst = (MYI2C_Struct *)arg;
TAL_PR_DEBUG("[%s] step = %d", __FUNCTION__, pst->Step);
if(pst->Step == SENSOR_IDLE)
{
pst->SendByte[0]=0x33;
pst->SendByte[1]=0x00;
drv_i2c_write_series((I2C_SLAVE_ID<<1) | 0, AHT20_MEASURE_REG, I2C_SLAVE_ADDR_LEN, pst->SendByte, 2);
pst->Step = SENSOR_MEASURE;
//TODO: 开启定时器等待75ms测量完成
tal_sw_timer_start(aht20_sample_etimerid, 100, TAL_TIMER_ONCE);
}
else if(pst->Step == SENSOR_MEASURE)
{
pst->Step=SENSOR_COMPLETE;
drv_i2c_read_series((I2C_SLAVE_ID<<1)|1, 0,I2C_SLAVE_ADDR_LEN, pst->ReadByte, 7);
/* 换算温度和湿度 */
if(pst->ErrFlag==0)
{
//if((CheckCrc8(&pst->ReadByte[0],6)==pst->ReadByte[6])&&((pst->ReadByte[0]&0x98) == 0x18))
{
s32x=pst->ReadByte[1];s32x=s32x<<8;s32x+=pst->ReadByte[2];s32x=s32x<<8;s32x+=pst->ReadByte[3];s32x=s32x>>4;
pst->RH=s32x;
pst->RH=pst->RH*100/1048576;
s32x=pst->ReadByte[3]&0x0F;s32x=s32x<<8;s32x+=pst->ReadByte[4];s32x=s32x<<8;s32x+=pst->ReadByte[5];
pst->T=s32x;
pst->T=pst->T*200/1048576-50;
}
TAL_PR_DEBUG("pst->ReadByte: %02x-%02x-%02x-%02x-%02x-%02x-%02x", pst->ReadByte[0], pst->ReadByte[1], pst->ReadByte[2],\
pst->ReadByte[3], pst->ReadByte[4], pst->ReadByte[5], pst->ReadByte[6]);
TAL_PR_DEBUG("temp = %.2f, humi = %.2f", pst->T, pst->RH);
}
else
{
pst->RH=0;
pst->T=0;
}
//tkl_cpu_allow_sleep();
}
}
int app_aht20_init(void)
{
drv_i2c_master_init(I2C_CLOCK);
drv_i2c_gpio_set(I2C_GPIO_GROUP_C0C1);
SENx.Adrr = ATH20_ADDR;
SENx.Step = SENSOR_IDLE;
//SENx.SetRTim=AHT20_SAMPLE_PERIOD;
WaitMs(40);
/* 定时启动读取温湿度用 */
OPERATE_RET ret = tal_sw_timer_create(MYI2C_Handle, &SENx, &aht20_etimerid);
if(ret != OPRT_OK)
{
TAL_PR_DEBUG("[%s] timer create failed", __FUNCTION__);
return ret;
}
/* 温湿度采集时动作延迟用 */
ret = tal_sw_timer_create(aht20_measure_handle, &SENx, &aht20_sample_etimerid);
if(ret != OPRT_OK)
{
TAL_PR_DEBUG("[%s] timer create failed", __FUNCTION__);
return ret;
}
//
ret = tal_sw_timer_start(aht20_etimerid, AHT20_SAMPLE_PERIOD, TAL_TIMER_CYCLE);
if(ret != OPRT_OK)
{
TAL_PR_DEBUG("[%s] timer create failed", __FUNCTION__);
return ret;
}
return 0;
}
附件图片:
1.异常情况下,逻辑分析仪抓到的波形正常
2.router配置时正常读取
3. sleep_end_dev配置时,读取异常