嵌入式系统编程和调试技巧

嵌入式系统的开发,软件的运行稳定可靠是非常重要的。在芯片中,软件是没有质量的,但软件的质量可以决定一颗芯片的成败。芯片设计中,性能能否满足设计要求,除了硬件设计、软硬件配合的设计技巧,对于软件来说,编程的一些技术和技巧同样重要。

本文讲述我在芯片固件开发过程中使用的一些编程调试技巧。针对在嵌入式系统开发中常见的问题,如实时系统下的同步问题,动态内存分配的内存泄漏问题,如何在编程阶段预防BUG出现,调试阶段如何及时发现问题和定位问题。总结下经验,目的是开发一个稳定运行的固件,提高开发效率,提高运行性能。

一       编程调试技巧

(一)      动态内存分配还是静态内存分配?

嵌入式系统开发中,动态内存分配和静态内存分配各有利弊,动态内存分配灵活方便,但占用额外内存资源,调用时性能有损失,存在内存碎片问题。

在无线芯片固件开发中,在两者的使用上主要考虑一下几点:

  • CPU性能
  • 可用内存大小
  • 需要使用内存分配的调用频率
  •  性能影响
在实际设计中:
  • 考虑malloc函数调用的开销。所有的收发通路上对数据帧的处理、管理使用的数据结构都用静态内存分配的方式。目的是为了减少处理时间。
  • l站点管理,密钥管理,SDIO接口传递的外部命令,向上传送的SDIO事件管理采用动态内存分配的方式。这些调用和数据帧收发处理次数相比不是一个数量级,有的是偶尔调用。
  • 一次性分配,存在于软件整个生命周期的数据结构变量采用静态内存分配。

(二)      使用ARM C库还是自己写一个?

嵌入式系统开发中经常会使用到C库的一些函数,如malloc,free,memcpy,memset,printf,是自己写一个呢还是利用ARM开发工具提供的C库呢?

我的习惯和建议是最好使用ARM的C库。优势就是

  • 使用方便,减少开发周期
  • ARM的C库性能会更好。

我以memcpy为例,网上有篇分析arm memcpy汇编代码的文章,ARM公司写的代码为什么更优化,性能更好呢?它主要考虑了以下几点:

  • 源地址和目的地址的首地址的字节对齐问题
  •  拷贝字节长度
  • 末尾字节的对齐问题。
  • 尽量word拷贝
  • 尽量利用arm的批量拷贝汇编指令。

所以我不会去另外写个memcpy函数。使用memcpy时只要注意,4-8个长的采用赋值方式效率会高些。或者不影响性能的情况下怎么用都无所谓。

ARMC库有两种库:标准库和MicroC库。后者是非线程安全,在裸系统下使用。前者是线程安全的,可以在实时系统下使用。对malloc的使用用户需要实现一个保护和释放保护的函数,供C库使用。防止多线程调用malloc函数出现的同步问题。

(三)      如何预防和发现内存泄漏

使用动态内存分配,系统就可能出现内存泄漏,内存使用溢出,内存重复释放等问题,如果直接使用malloc和free,很难发现这样的BUG。在编程阶段,重定义malloc和free函数可以及时发现和定位这些问题。让程序去发现问题,而不是自己去找问题或者根本不知道有问题。

重定义的malloc采用双向链表管理所有动态分配的内存。下面是管理内存使用的数据结构:

 


每次内存分配分配如上大小的内存,包括三个部分,黄色部分为MEMORY_BLOCK数据结构,灰色部分为实际使用内存区,红色部分(4个字节)为尾部标记。

MEMORY_BLOCK保存了双向链表,分配的文件名指针和文件行号,分配的长度和头部标记。

  • 0
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值