123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103 |
- /*
- *********************************************************************************************************
- *
- * 模块名称 : 数据观察点与跟踪(DWT)模块
- * 文件名称 : bsp_dwt.c
- * 版 本 : V1.0
- * 说 明 : 在CM3,CM4中可以有3种跟踪源:ETM, ITM 和DWT,本驱动主要实现
- * DWT中的时钟周期(CYCCNT)计数功能,此功能非常重要,可以很方便的
- * 计算程序执行的时钟周期个数。
- * 修改记录 :
- * 版本号 日期 作者 说明
- * V1.0 2015-08-18 Eric2013 正式发布
- *
- * Copyright (C), 2015-2020, 安富莱电子 www.armfly.com
- *
- *********************************************************************************************************
- */
- #include "dwt.h"
- /*
- *********************************************************************************************************
- * 寄存器
- *********************************************************************************************************
- */
- #define DWT_CYCCNT *(volatile unsigned int *)0xE0001004
- #define DWT_CR *(volatile unsigned int *)0xE0001000
- #define DEM_CR *(volatile unsigned int *)0xE000EDFC
- #define DBGMCU_CR *(volatile unsigned int *)0xE0042004
- #define DEM_CR_TRCENA (1 << 24)
- #define DWT_CR_CYCCNTENA (1 << 0)
- /*
- *********************************************************************************************************
- * 函 数 名: bsp_InitDWT
- * 功能说明: 初始化DWT. 该函数被 bsp_Init() 调用。
- * 形 参: 无
- * 返 回 值: 无
- *********************************************************************************************************
- */
- void dwt_init(void)
- {
- DEM_CR |= (unsigned int)DEM_CR_TRCENA; /* Enable Cortex-M4's DWT CYCCNT reg. */
- DWT_CYCCNT = (unsigned int)0u;
- DWT_CR |= (unsigned int)DWT_CR_CYCCNTENA;
- }
- /*
- *********************************************************************************************************
- * 函 数 名: bsp_DelayUS
- * 功能说明: 这里的延时采用CPU的内部计数实现,32位计数器
- * OSSchedLock(&err);
- * bsp_DelayUS(5);
- * OSSchedUnlock(&err); 根据实际情况看看是否需要加调度锁或选择关中断
- * 形 参: us_time 延迟长度,单位1 us
- * 返 回 值: 无
- * 说 明: 1. 主频168MHz的情况下,32位计数器计满是2^32/168000000 = 25.565秒
- * 建议使用本函数做延迟的话,延迟在1秒以下。
- * 2. 实际通过示波器测试,微妙延迟函数比实际设置实际多运行0.25us左右的时间。
- * 下面数据测试条件:
- * (1). MDK5.15,优化等级0, 不同的MDK优化等级对其没有影响。
- * (2). STM32F407IGT6
- * (3). 测试方法:
- * GPIOI->BSRRL = GPIO_Pin_8;
- * bsp_DelayUS(10);
- * GPIOI->BSRRH = GPIO_Pin_8;
- * -------------------------------------------
- * 测试 实际执行
- * bsp_DelayUS(1) 1.2360us
- * bsp_DelayUS(2) 2.256us
- * bsp_DelayUS(3) 3.256us
- * bsp_DelayUS(4) 4.256us
- * bsp_DelayUS(5) 5.276us
- * bsp_DelayUS(6) 6.276us
- * bsp_DelayUS(7) 7.276us
- * bsp_DelayUS(8) 8.276us
- * bsp_DelayUS(9) 9.276us
- * bsp_DelayUS(10) 10.28us
- * 3. 两个32位无符号数相减,获取的结果再赋值给32位无符号数依然可以正确的获取差值。
- * 假如A,B,C都是32位无符号数。
- * 如果A > B 那么A - B = C,这个很好理解,完全没有问题
- * 如果A < B 那么A - B = C, C的数值就是0xFFFFFFFF - B + A + 1。这一点要特别注意,正好用于本函数。
- *********************************************************************************************************
- */
- void delay_us(uint32_t us_time)
- {
- uint32_t tCnt, tDelayCnt;
- uint32_t tStart;
- tStart = DWT_CYCCNT; /* 刚进入时的计数器值 */
- tCnt = 0;
- tDelayCnt = us_time * (SystemCoreClock / 1000000); /* 需要的节拍数 */
- while (tCnt < tDelayCnt)
- {
- tCnt = DWT_CYCCNT - tStart; /* 求减过程中,如果发生第一次32位计数器重新计数,依然可以正确计算 */
- }
- }
- void delay_ms(uint32_t us_time)
- {
- delay_us(1000 * us_time);
- }
|