系列文章
- DW1000开发笔记(一)DW1000芯片概览
- DW1000开发笔记(二)使用STM32硬件SPI+STM32cubeMX+HAL库测试DW1000通信
- DW1000开发笔记(三)基于STM32 HAL库裸机工程移植DW1000官方驱动
- DW1000开发笔记(四)DW1000使用轮询方式发送数据
- DW1000开发笔记(五)DW1000使用轮询方式接收数据
一、移植发送数据并等待响应的代码
本文中使用基于STM32F103ZET6开发板+DW1000评估板作为发送数据并等待回应端。
1. 复制官方示例文件
将官方驱动库中example下的第三个示例 a 移植过来:
复制到之前移植的STM32CubeMX生成的工程文件中,并重命名文件为tx_wait_resp_example.c:
将其添加到MDK工程中:
将之前移植的发送demo取消工程构建(防止冲突):
2. 修改官方示例文件
① 修改替换头文件:
② 修改函数名
③ 修改打印和延时函数:
添加调试打印信息:
修改延时函数:
修改完成。
3. 调用示例代码
main.c保持原来第三节中的测试代码不变。
4. 移植结果
编译、下载程序,在串口助手中查看打印日志:
可以看到DW1000一直在循环发送,但没有收到应答。
三、移植接收数据并发送响应的代码
本文中使用基于STM32F103C8T6开发板+DW1000评估板作为接收数据并发送响应的一侧设备。
1. 复制官方示例文件
将官方驱动库中example下的第三个示例 b 移植过来:
复制到之前移植的STM32CubeMX生成的工程文件中,并重命名文件为rx_send_resp_example.c:
将其添加到MDK工程中:
将之前移植的接收demo取消工程构建(防止冲突):
2. 修改官方示例文件
① 修改替换头文件:
② 修改函数名
③ 修改打印函数:
再添加一些额外的调试信息:
修改完成。
3. 调用示例代码
main.c保持原来第四节中的测试代码不变。
4. 移植结果
编译、下载程序,在串口助手中查看打印日志:
可以看到这一侧没有问题 ,接收到数据之后并发送响应数据回去。
此时再看等待响应的一侧:
先发送数据出去,然后接收响应数据成功。
加入接收数据时间戳之后,两边放在一起的日志如下:
四、发送之后等待接收响应API分析
1. 发送并等待响应的流程
2. 发送并等待响应流程中需要设置的延时时间
在发生并等待响应端,延时时间有两个,设置API分别如下。
第一个是从发送完成开始,到自动打开接收模式的延时时间。使用下面的API进行设置:
void dwt_setrxaftertxdelay(uint32 rxDelayTime);
它的入参只有一个,表示设置的时间大小。
这个时间值的大小宽度为20bit,也就是最大为 2 20 − 1 = 1048575 2^{20}-1=1048575 220−1=1048575。这个时间值的单位是UWB ms,该单位与正常的时间关系为 1 U W B m s = 512 / 499.2 M h z u s = 1.0256 u s 1 UWB ms = 512/499.2Mhz us = 1.0256 us 1UWBms=512/499.2Mhzus=1.0256us。
这个值最小可以设置为0,设置为0的时候,则DW1000会在发送完成后立即打开接收模式,这个操作大概需要花费6.2us的时间。而且如果设置的值小于7us,则花费的时间依然会是6.2us。
第二个是设置接收数据超时时间,即接收端在RX启用命令之后保持开着多久,其API原型如下:
void dwt_setrxtimeout(uint16 time);
该函数的入参也有一个,是一个16位的值(最大65535),单位依然是UWB ms,也就是1.0256us。
如果设置最大,则大约是 1.0256 ∗ 65535 / 1000 = 65 m s 1.0256*65535/1000=65ms 1.0256∗65535/1000=65ms。
如果设置为0,则表示禁止该超时检测功能。
该函数没有返回值,但需要注意,该功能设置的是DW1000内部硬件定时器,如果发生超时,则直接置位SY_STAT_RFTO事件标志。
3. 发送数据并等待回应
写入数据到发送缓冲区和控制发送寄存器的操作和之前普通发送相同,无需赘述。
在启动发送的时候,除了设置立即发送模式(DWT_START_TX_IMMEDIATE),还要设置等待响应模式(DWT_RESPONSE_EXPECTED),如下:
dwt_starttx(DWT_START_TX_IMMEDIATE | DWT_RESPONSE_EXPECTED);
4. 轮询是否接收到响应数据
如果设置了接收超时时间,还应该在轮询的时间检测是否超时(SYS_STATUS_ALL_RX_TO),如下:
while (!((status_reg = dwt_read32bitreg(SYS_STATUS_ID)) & (SYS_STATUS_RXFCG | SYS_STATUS_ALL_RX_TO | SYS_STATUS_ALL_RX_ERR)))
{ };
其余的是成功接收到数据之后的操作,与普通数据接收没有区别。