例程代码微妙延时事宜请教
在跑freertos的例程中有个I2C延时函数:*********************************************************************************************************
* 函 数 名: i2c_Delay
* 功能说明: I2C总线位延迟,最快400KHz
* 形 参:无
* 返 回 值: 无
*********************************************************************************************************
*/
static void i2c_Delay(void)
{
uint8_t i;
/*
CPU主频168MHz时,在内部Flash运行, MDK工程不优化。用台式示波器观测波形。
循环次数为5时,SCL频率 = 1.78MHz (读耗时: 92ms, 读写正常,但是用示波器探头碰上就读写失败。时序接近临界)
循环次数为10时,SCL频率 = 1.1MHz (读耗时: 138ms, 读速度: 118724B/s)
循环次数为30时,SCL频率 = 440KHz, SCL高电平时间1.0us,SCL低电平时间1.2us
上拉电阻选择2.2K欧时,SCL上升沿时间约0.5us,如果选4.7K欧,则上升沿约1us
实际应用选择400KHz左右的速率即可
*/
for (i = 0; i < 30; i++);
}
为什么不用下面这个延时函数更准确?
*********************************************************************************************************
* 函 数 名: bsp_DelayUS
* 功能说明: us级延迟。 必须在systick定时器启动后才能调用此函数。
* 形 参:n : 延迟长度,单位1 us
* 返 回 值: 无
*********************************************************************************************************
*/
void bsp_DelayUS(uint32_t n)
{
uint32_t ticks;
uint32_t told;
uint32_t tnow;
uint32_t tcnt = 0;
uint32_t reload;
reload = SysTick->LOAD;
ticks = n * (SystemCoreClock / 1000000); /* 需要的节拍数 */
tcnt = 0;
told = SysTick->VAL; /* 刚进入时的计数器值 */
while (1)
{
tnow = SysTick->VAL;
if (tnow != told)
{
/* SYSTICK是一个递减的计数器 */
if (tnow < told)
{
tcnt += told - tnow;
}
/* 重新装载递减 */
else
{
tcnt += reload - tnow + told;
}
told = tnow;
/* 时间超过/等于要延迟的时间,则退出 */
if (tcnt >= ticks)
{
break;
}
}
}
} 应该可以的吧,cube里面systick中断里面就包含了两个,一个是freertos的心跳一个是hal的延时 和楼主说的很类似
回 shouyuxinyan 的帖子
shouyuxinyan:应该可以的吧,cube里面systick中断里面就包含了两个,一个是freertos的心跳一个是hal的延时 和楼主说的很类似 (2015-11-18 17:03) images/back.gif那个延时函数用宏定义限制了只在非freertos中使用 楼主问题解决了吗?我也遇到了这个问题 woaiwm 发表于 2021-5-19 14:54
楼主问题解决了吗?我也遇到了这个问题
这两个用那个都一样,区别不大,只是用for循环更灵活,方便修改。bsp_DelayUS并不准确,有抖动
用下面这个是最优
DWT实现一个精确微秒延迟的参考例程
http://www.armbbs.cn/forum.php?m ... id=89128&fromuid=58
(出处: 硬汉嵌入式论坛)
页:
[1]