我正在使用i2c适配器(在主模式下)进行异步写入,或者读取从回调中发出的OS_EVENT等待的读取。然而,而不是永远等待我希望能够设置超时值,以便如果在总线上没有设备,则不会被卡住。但是,如果我尝试启动另一个异步读取或写入适配器的超时,因为存在未完成的待处理事务,所以读取或写入适配器挂起。我如何取消这些待处理的交易或更好,尚更良好,是正确的方式,以便我可以使用带有AD_I2C_ASYNC_READ或AD_I2C_ASYNC_WRITE的超时。
嗨rajames,
如果您使用SDK的ASYNCH函数启动异步事务,则API为您提供回调参数,应在完成事务时执行此回调。如果由于任何原因在尝试访问I2C设备时设备获取NACK,则交互将终止适当的错误,在设备侧HW_I2C_ABORT_7B_ADDR_NO_ACK中的NACK的情况下,您将能够知道在回调时。而不是拥有wait_for_event(事件)(我想这就是你的意思)你可以ommit是为了不阻止任务,但你不能取消已经开始的事务,并且你不能在之前使用第二个ASYNCH事务前一个返回,这在doxygen中清楚地说明了ad_i2c_asynch_read和写入函数的描述中。
谢谢mt_dialog.
嗨Dalog,
谢谢你的回复。
如果我正确理解,即使发生错误,应始终应始终执行回调。
我正在使用回调来发出任务,请参阅下面的伪代码:回调(Params){//处理参数os_signal(事件)}任务(){async_write(数据,回调)OS_EVENT_WAIT(事件,超时)//更多异步写入或以相同的方式读取}
回调(Params){//处理参数os_signal(事件)}
任务(){async_write(数据,回调)OS_EVENT_WAIT(事件,超时)//更多异步写入或以相同的方式读取}
我面临的问题是,如果在超时过期之前未执行回调,则无法取消任何挂起的事务。这就是为什么要使用OS_Event_forever。但并不总是执行回调。回调会在以下错误期间执行吗?例如,SCLK线在异步写入或读取开始之前由从设备保持低电平。回调仍然会用hw_i2c_abort_ *执行吗?在未触发回调时是否有其他情况?
如何防止以下序列阻止
master:ad_i2c_async_read.主机:启动读取请求奴隶:承认并保持SCLK线路奴隶:永远不会发送回复master:os_event_wait超时到期Master:启动另一个ad_i2c_async_read请求Master:块因为有待待处理的事务。
谢谢您的帮助
那么,你说有时操作永远不会完成,所以设备摊位并等待?从那以后,如果I2C HW看到的是时钟线路低电平,它不会传输任何数据,并且它不会返回错误(因为没有错误)它只等到时钟线释放并传出数据缓冲区。所以在这种情况下,不应该任何完成交易完成。但是你不能拥有一个奴隶,它会一直将CLK线保持低。如果发生这种情况并且线路保持低电平,则应更好地由从设备而不是主机处理,因为保持时钟线低电平将阻止对该总线上附加的所有设备的通信,即使存在取消程序以停止异步事务,如果从站继续保持低电平,则必须符合后续交易。在任何情况下,您可以尝试的是有类似以下代码段的东西,以取消程序(请注意,这没有测试,而不是官方SDK代码,我无法预测这可能对I2C交易的行为的任何副作用):
静态无效i2c\u释放\u解压缩\u事务处理(i2c\u设备开发){i2c_device_config * device =(i2c_device_config *)dev;i2c_bus_dynamic_data * data = device-> bus_data;if(数据 - > transaction_ix!= 0){data-> transaction_ix = 0;/ *只发布总线和设备* /AD_I2C_BUS_RELEASE(DEV);ad_i2c_device_release(dev);}}
因此,使用上面的函数,您可以在wait\u for\u EVENT()函数中设置一个超时,而不是永远使用OS\u EVENT\u,一旦超时结束,您就可以调用上面的函数来取消上一个事务并继续执行另一个事务。
嗨rajames,
如果您使用SDK的ASYNCH函数启动异步事务,则API为您提供回调参数,应在完成事务时执行此回调。如果由于任何原因在尝试访问I2C设备时设备获取NACK,则交互将终止适当的错误,在设备侧HW_I2C_ABORT_7B_ADDR_NO_ACK中的NACK的情况下,您将能够知道在回调时。而不是拥有wait_for_event(事件)(我想这就是你的意思)你可以ommit是为了不阻止任务,但你不能取消已经开始的事务,并且你不能在之前使用第二个ASYNCH事务前一个返回,这在doxygen中清楚地说明了ad_i2c_asynch_read和写入函数的描述中。
谢谢mt_dialog.
嗨Dalog,
谢谢你的回复。
如果我正确理解,即使发生错误,应始终应始终执行回调。
我正在使用回调来发出任务,请参阅下面的伪代码:
回调(Params){
//处理参数
os_signal(事件)
}
任务(){
async_write(数据,回调)
OS_EVENT_WAIT(事件,超时)
//更多异步写入或以相同的方式读取
}
我面临的问题是,如果在超时过期之前未执行回调,则无法取消任何挂起的事务。这就是为什么要使用OS_Event_forever。
但并不总是执行回调。回调会在以下错误期间执行吗?例如,SCLK线在异步写入或读取开始之前由从设备保持低电平。回调仍然会用hw_i2c_abort_ *执行吗?在未触发回调时是否有其他情况?
如何防止以下序列阻止
master:ad_i2c_async_read.
主机:启动读取请求
奴隶:承认并保持SCLK线路
奴隶:永远不会发送回复
master:os_event_wait超时到期
Master:启动另一个ad_i2c_async_read请求
Master:块因为有待待处理的事务。
谢谢您的帮助
嗨rajames,
那么,你说有时操作永远不会完成,所以设备摊位并等待?从那以后,如果I2C HW看到的是时钟线路低电平,它不会传输任何数据,并且它不会返回错误(因为没有错误)它只等到时钟线释放并传出数据缓冲区。所以在这种情况下,不应该任何完成交易完成。但是你不能拥有一个奴隶,它会一直将CLK线保持低。如果发生这种情况并且线路保持低电平,则应更好地由从设备而不是主机处理,因为保持时钟线低电平将阻止对该总线上附加的所有设备的通信,即使存在取消程序以停止异步事务,如果从站继续保持低电平,则必须符合后续交易。在任何情况下,您可以尝试的是有类似以下代码段的东西,以取消程序(请注意,这没有测试,而不是官方SDK代码,我无法预测这可能对I2C交易的行为的任何副作用):
静态无效i2c\u释放\u解压缩\u事务处理(i2c\u设备开发)
{
i2c_device_config * device =(i2c_device_config *)dev;
i2c_bus_dynamic_data * data = device-> bus_data;
if(数据 - > transaction_ix!= 0)
{
data-> transaction_ix = 0;
/ *只发布总线和设备* /
AD_I2C_BUS_RELEASE(DEV);
ad_i2c_device_release(dev);
}
}
因此,使用上面的函数,您可以在wait\u for\u EVENT()函数中设置一个超时,而不是永远使用OS\u EVENT\u,一旦超时结束,您就可以调用上面的函数来取消上一个事务并继续执行另一个事务。
谢谢mt_dialog.