单片机调试 — Event Recorder 的使用

在单片机的软件开发中,经常会遇到各种各样的问题,很多时候为了定位到出现bug的地方,我们可能会借助很多的手段或者工具。比如串口打印、MDK在线仿真、上位机调试工具等等的。

但是,有时候想要用串口打印输出某些结果,而硬件设计又没有预留串口,这种时候就感觉很不方便。我个人使用串口调试的频率还是蛮多的,主要是简单易操作,可以在想要观察运行结果的代码位置随便加调试输出,很方便定位问题。

在硬件上没有多余的串口预留的话,如果有外接仿真引脚出来的话,在MDK环境下就可以使用ST-LINK、J-LINK等的各种LINK进行调试,实现printf输出的功能,简直是不要太棒了!

在MDK的开发IDE环境下,支持仿真调试的组件有好几个,我这里使用的是Event Recorder。这个组件功能是在MDK5.22的版本是哪个开始增加的,所以想要使用这个组件功能,需要将自己的MDK开发工具升级到5.22以上,建议是当前最新的版本!

1、添加 Event Recorder 组件

1)打开你需要添加调试组件的项目工程,点击如下图所示的图标:
在这里插入图片描述

2)选择 “Compiler”,并按照如下勾选,勾选之后点击“ok”即可。如下图:
在这里插入图片描述

勾选之后可以看到工程目录上出现一个“Compiler”的选项,说明组件添加成功了,如下图:
在这里插入图片描述

3)检查组件的工程配置,如下:
在这里插入图片描述

说明如下:

Number of Records:表示 Event Recorder 缓冲可以记录的消息条数。
Time Stamp Source:表示时间戳来源

其中,Time Stamp Source 有如下四种可以选择,一般使用 DWT 时钟周期计数器。如下图:
在这里插入图片描述

至此,Event Record组件就已经添加完成了。

2、printf 重定向

在Event Recorder 实现printf输出需要使用MDK的 Debug 功能,输出的效果就跟串口调试工具上的显示效果是一样的。

Event Recorder 中的重定向代码如下:

int fputc (int c, FILE * stream) {
#if (!defined(RTE_Compiler_IO_STDOUT) && !defined(RTE_Compiler_IO_STDERR))
  (void)c;
  (void)stream;
#endif
 
#ifdef RTE_Compiler_IO_STDOUT
  if (stream == &__stdout) {
#if (STDOUT_CR_LF != 0)
    if (c == '\n') stdout_putchar('\r');
#endif
    return (stdout_putchar(c));
  }
#endif
 
#ifdef RTE_Compiler_IO_STDERR
  if (stream == &__stderr) {
#if (STDERR_CR_LF != 0)
    if (c == '\n') stderr_putchar('\r');
#endif
    return (stderr_putchar(c));
  }
#endif
 
  return (-1);
}

注意:使用 Event Recorder 实现printf重定向时,一定要取消掉自己的项目中原本的重定向!

1)进入仿真调试模式,如下:
在这里插入图片描述

2)选中 Debug(printf)Viewer 调试组件,如下图:
在这里插入图片描述

3)选择仿真时周期更新,如下图:
在这里插入图片描述

4)添加初始化代码,如下:

/* 初始化 EventRecorder 并开启 */
    EventRecorderInitialize(EventRecordAll, 1U);
    EventRecorderStart();

5)全速运行即可以看到结果。
在这里插入图片描述

示例:
测试代码如下:
在这里插入图片描述

仿真结果如下:
在这里插入图片描述

鼠标右键还可以对 Debug(printf)Viewer 进行设置,如下图:
在这里插入图片描述

3、简单方便的时间测量功能

Event Recorder 也可以测量代码运行的时间,时间测量功能简单易用,仅需一个起始函数,一个停止函数即可。

3.1、时间测量起始函数

EventStartG (slot) 
或者 
EventStartGv (slot, val1, val2)

函数说明:

1)函数中的字母 G 是表示分组 A,B,C,D,即实际调用函数为 EventStartA,EventStartB,EventStartC 和 EventStartD。

2)函数的第一个形参 slot 的范围是 0-15,也就是最大可以测量 16 路。

3)函数后面的两个形象 val1 和 val2 是 32 Bit变量,用户可以用这两个形参来传递变量数值给 Event Statistics 调试组件里面,用于图形化展示。

3.2、时间测量结束函数

EventStopG (slot) 
或者 
EventStopGv (slot, val1, val2)

函数说明:

1)函数中的字母G是表示分组A,B,C,D,即实际调用函数为EventStopA,EventStopB,EventStopC 和 EventStopD。

2)函数的第一个形参 slot 的范围是 0-15,也就是最大可以测量 16 路。

3)函数后面的两个形象 val1 和 val2 是 32 位变量,用户可以用这两个形参来传递变量数值给 Event Statistics 调试组件里面,用于图形化展示。

3.3、使用示例

1)添加初始化代码

/* 初始化 EventRecorder 并开启 */
EventRecorderInitialize(EventRecordAll, 1U);
EventRecorderStart();

2)在代码前后加上起始和结束时间的测量API函数,如下所示:
在这里插入图片描述

3)选择 Event Statistics 调试组件,如下:
在这里插入图片描述

4)全速运行,查看结果,如下:
在这里插入图片描述

从图中可以看出,开始测量的位置是在 149 行处,结束测量的位置是在152 行处,下方的红色方框处标出了测量的最大时间和最小时间。

对嵌入式技术感兴趣欢迎关注微信公众号“嵌入式之入坑笔记”,一起学习讨论啊!
在这里插入图片描述

  • 7
    点赞
  • 43
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 2
    评论
要在Vue中获取实时录音流,可以使用Web Audio API。你需要先创建一个MediaStream对象来捕获麦克风的音频输入。然后,使用MediaRecorder API来记录音频,并将其存储为Blob对象。下面是一个简单的示例代码: ``` <template> <div> <button @click="startRecording">Start Recording</button> <button @click="stopRecording">Stop Recording</button> </div> </template> <script> export default { data() { return { mediaRecorder: null, audioChunks: [] }; }, methods: { startRecording() { navigator.mediaDevices.getUserMedia({ audio: true }) .then(stream => { this.mediaRecorder = new MediaRecorder(stream); this.mediaRecorder.addEventListener("dataavailable", event => { this.audioChunks.push(event.data); }); this.mediaRecorder.start(); }); }, stopRecording() { this.mediaRecorder.stop(); const audioBlob = new Blob(this.audioChunks); const audioUrl = URL.createObjectURL(audioBlob); // do something with audioUrl, such as playing it back or sending it to a server } } }; </script> ``` 这个示例代码创建了一个包含“Start Recording”和“Stop Recording”按钮的组件。当用户点击“Start Recording”按钮时,它将请求访问麦克风,并在获取到MediaStream对象后创建一个MediaRecorder对象来记录音频。每当MediaRecorder对象生成新的数据块时,它都会将数据块添加到audioChunks数组中。当用户点击“Stop Recording”按钮时,它会停止MediaRecorder对象并将audioChunks数组中的所有数据块合并为一个Blob对象。最后,它使用URL.createObjectURL()方法将Blob对象转换为可播放的URL,并将其存储在audioUrl变量中。你可以将audioUrl用于播放录音或将其发送到服务器进行后续处理。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

嵌入式之入坑笔记

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值