OpenEdv-开源电子网

 找回密码
 立即注册
正点原子全套STM32/Linux/FPGA开发资料,上千讲STM32视频教程免费下载...
查看: 3993|回复: 4

利用DWT实现指定变量被改写的时候触发中断

[复制链接]

3

主题

238

帖子

0

精华

金牌会员

Rank: 6Rank: 6

积分
1366
金钱
1366
注册时间
2016-5-26
在线时间
1698 小时
发表于 2018-6-2 13:14:22 | 显示全部楼层 |阅读模式
最近发现了 DWT 的比较器(就是 debug 的时候实现 watchpoint 功能的模块)是可以由软件控制并触发 Debug Monitor 异常的,
由此可以实现“当某个变量/内存地址被改写的时候触发一个中断”这样的功能。

测试代码:
[mw_shl_code=c,true]
    uint_fast8_t i, j;

    /* 时钟和 printf 初始化略 */
    /* data[10] 是初始为 0 的全局整型数组 */

    /* Enable Trace and Debug Monitor exception */
    CoreDebug->DEMCR |= CoreDebug_DEMCR_TRCENA_Msk |
                        CoreDebug_DEMCR_MON_EN_Msk;

//    /* Number of comparators available */
//    dwt_numcomp = _FLD2VAL(DWT_CTRL_NUMCOMP, DWT->CTRL);
   
    /* Configure comparators */
    DWT->FUNCTION0 = 0;                 /* Disable */
    DWT->COMP0 = (uint32_t)&data[8];    /* Target address */
    DWT->MASK0 = 2;                     /* 0 - Byte; 1 - Halfword; 2 - Word */
    DWT->FUNCTION0 = 6;                 /* 5 - Read; 6 - Write; 7 - R & W */

    DWT->FUNCTION1 = 0;                 /* Disable */
    DWT->COMP1 = (uint32_t)&data[3];    /* Target address */
    DWT->MASK1 = 2;                     /* 0 - Byte; 1 - Halfword; 2 - Word */
    DWT->FUNCTION1 = 6;                 /* 5 - Read; 6 - Write; 7 - R & W */

    DWT->FUNCTION2 = 0;                 /* Disable */
    DWT->COMP2 = (uint32_t)&data[6];    /* Target address */
    DWT->MASK2 = 2;                     /* 0 - Byte; 1 - Halfword; 2 - Word */
    DWT->FUNCTION2 = 6;                 /* 5 - Read; 6 - Write; 7 - R & W */

    DWT->FUNCTION3 = 0;                 /* Disable */
    DWT->COMP3 = (uint32_t)&data[2];    /* Target address */
    DWT->MASK3 = 2;                     /* 0 - Byte; 1 - Halfword; 2 - Word */
    DWT->FUNCTION3 = 6;                 /* 5 - Read; 6 - Write; 7 - R & W */

    for (i = 0; i < 10; i++)
    {
        data = 1;

        for (j = 0; j < 10; j++)
        {
            printf("%d ", data[j]);
        }
        printf("\n\r");
        HAL_Delay(1000);
    }
[/mw_shl_code]

for 循环依次修改 data[10] 中的每一个数,DWT 的 4 个比较器分别在第 8、3、6、2 元素被修改时触发。

然后在 Debug Monitor 异常里面:
[mw_shl_code=c,true]
void DebugMon_Handler(void)
{
    if ((DWT->FUNCTION0 & DWT_FUNCTION_MATCHED_Msk) != 0)
    {
        printf("Interrupt from DWT Comparator 0.\n\r");
    }

    if ((DWT->FUNCTION1 & DWT_FUNCTION_MATCHED_Msk) != 0)
    {
        printf("Interrupt from DWT Comparator 1.\n\r");
    }

    if ((DWT->FUNCTION2 & DWT_FUNCTION_MATCHED_Msk) != 0)
    {
        printf("Interrupt from DWT Comparator 2.\n\r");
    }

    if ((DWT->FUNCTION3 & DWT_FUNCTION_MATCHED_Msk) != 0)
    {
        printf("Interrupt from DWT Comparator 3.\n\r");
    }
}
[/mw_shl_code]

运行结果:
DWT_CMP.png

局限:
只有 4 个比较器;
不能在 debug 状态下用(会变成断点);
实际上是在监测指定地址的读/写,所以相同数据重复写入的情况需要额外处理。
淘汰人的从来是工具而不是年龄
嵌入式的冷知识屋 blog.csdn.net/k_o_carnivist
正点原子逻辑分析仪DL16劲爆上市
回复

使用道具 举报

0

主题

33

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
303
金钱
303
注册时间
2014-11-23
在线时间
121 小时
发表于 2018-6-2 19:40:09 | 显示全部楼层
不错,挺有用的一个功能
回复 支持 反对

使用道具 举报

7

主题

185

帖子

0

精华

金牌会员

Rank: 6Rank: 6

积分
2729
金钱
2729
注册时间
2015-12-27
在线时间
469 小时
发表于 2018-7-13 09:32:57 | 显示全部楼层
哈哈,我在CSDN也看了你的这个帖子。
回复 支持 反对

使用道具 举报

7

主题

185

帖子

0

精华

金牌会员

Rank: 6Rank: 6

积分
2729
金钱
2729
注册时间
2015-12-27
在线时间
469 小时
发表于 2018-7-13 09:34:13 | 显示全部楼层
我有个疑问,在这么用的时候会影响调试。如果我只是用WDT来做延时使用时,会影响仿真调试吗?
回复 支持 反对

使用道具 举报

530

主题

11万

帖子

34

精华

管理员

Rank: 12Rank: 12Rank: 12

积分
165524
金钱
165524
注册时间
2010-12-1
在线时间
2116 小时
发表于 2020-4-24 17:48:33 | 显示全部楼层
不错
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则



关闭

原子哥极力推荐上一条 /2 下一条

正点原子公众号

QQ|手机版|OpenEdv-开源电子网 ( 粤ICP备12000418号-1 )

GMT+8, 2025-5-26 05:28

Powered by OpenEdv-开源电子网

© 2001-2030 OpenEdv-开源电子网

快速回复 返回顶部 返回列表