dsp学习杂谈

最近在准备电赛中,我们的方向是信号与测量题,一个小队三个人分别负责硬件PCB、FPGA和dsp三个方向,我主要是负责dsp、单片机和人机交互这方面的内容。老师给我的板子主控芯片是TI的TMS320F2812,它属于C2000系列,板子是hellodsp(傅立叶电子)出品的,所以拿到板子我就去他们公司官网寻找资料,寻觅有果但不全,又去他们官方淘宝网店要资料(好厚的脸皮),有幸淘到了顾卫钢老师写的《一起学2812教程》和他们公司给的板子例程,摩拳擦掌开始学习。
另外,我的学习方式是根据例程顺序来的,先看所需要的教程文档,再看例程具体内容,最后会小改一下例程以练习实践。

在学习dsp前你需要知道的

dsp是什么?

DSP(Digital Signal Processing)即数字信号处理技术,DSP芯片即指能够实现数字信号处理技术的芯片。DSP芯片与CPU相比,如果说CPU是大而通用的处理器,那么DSP就是小而精于数字信号处理的芯片。在电赛中,dsp常常用于波形的采样和转换。

仿真器是什么?

仿真器应该与目标MCU在电气及物理上等价,并能在开发系统中替代MCU。目标系统的操作可由调试工具得以控制及观察。在开发初期,开发系统依靠仿真器工作,当目标功能完善后,仿真器将被真正的MCU取代。

说人话,拿以前接触过的STM32举例:
STM32有两种程序下载方式,仿真器下载和串口下载。在调试的时候用仿真器,不用忍受串口下载速度之苦,在error频报时还可以打断点,看寄存器的值,变量的值,下一步程序跳到哪个地方执行,学会这些调试手段,快速定位问题,可以提高查错效率。
但是仿真器对于单片机来说不是必需的。

DSP仿真器为什么是必需的?

前面说到仿真器应当可替代MCU,但是DSP的仿真器中没有DSP,只能提供IEEE标准的JTAG口对DSP进行仿真调试,所以仿真器必须有仿真对象,及目标系统(就是必须用JTAG连接板子的意思)。
DSP仿真器是在程序开发和调试阶段连接开发板与CCS开发环境/visual DSP++环境的桥梁。主要有两种用途,分别是下载程序和调试程序。

dsp和单片机的不同?

除了上面说到的仿真器的不同,dsp和单片机还有很多不同之处。
以前往单片机里下载好程序,掉电重启之后程序还在,但往DSP里写程序有两种方式,分别是RAM和flash,普通的RAM方式在掉电重启之后就找不回程序了,flash方式较麻烦但“真正写入了芯片”。
DSP还多了一个CMD文件。单片机或者ARM根本就没这么一说,这破东西到底干啥的?CMD文件主要作用就是用来做内存分配,其实就是把你代码中的这些一块一块的东西和具体的硬件存储对应起来。你可以随你需要任意来配置,比如我有一个数据表格,普通的单片机你定义好了之后会有编译器来帮你存放到一个地方,但是DSP里面你可以通过配置CMD把它放在你认为合适的地方。再比如堆栈空间的大小,以前从来没关心过堆栈大小,但是开辟的太大的话可能浪费内存空间。当然,每个芯片都有一个标准的CMD文件,初学者完全可以不用去修改它。

dsp芯片的常用编程软件是什么?

CCS,英文全称是Code Composer Studio,它是美国德州仪器公司(Texas Instrument,TI)出品的代码开发和调试套件。
它的C/C++内核是eclipse,UI看起来也像是eclipse魔改而成的。话不多说先下载一个。

ccs如何安装

目前最新的版本是ccs11,但是教程上给的版本是ccs3.3,所以在后面我会根据最新的版本把每个实验的例程跑一遍。
首先要说一个大坑:无论是软件安装路径、工作空间路径还是项目打开路径都!不!要!有!中!文!!!
官网下载地址:Code Composer Studio Downloads
你可能会需要的教程:CCS软件安装教程
关于安装时该选择哪个系列SDK的问题:我的2812属于C2000系列,所以只需要勾选C2000就好,当然MSP430也是常用的型号,可以顺便勾选上。

ccs使用

CCS11用户界面介绍1
CCS11用户界面介绍2
CCS11用户界面介绍3

一个项目的构成

头文件和源文件

同我们熟悉的C/C++项目一样,ccs中的项目也有着头文件(.h)和源文件(.c)。不同的是,在硬件工程项目中,头文件一般说明的是板子内部寄存器的数据结构,所以非必要不修改头文件。我们也可以把一些全局变量的声明放在同一个头文件里,以确保所有全局变量都能被所有源文件使用。
这里我们复习一下C/C++的知识,假设在main.c文件中定义了一个全局int变量a,我们还有另外一个源文件other.c,这两个源文件都包含了头文件all.h。如果我们想在other.c中使用这个变量a,那么就要在它的最前面写上“extern int a;”,这告诉编译器这个变量a并没有在此文件中定义,你去别的地方找找。但是如果我们有很多源文件都要使用a,那还是在统一包含的all.h中写这条语句比较省事。

库文件和CMD文件

除了头文件和源文件,还有库文件(.lib)和CMD文件。库文件就是C语言系统的库文件,CMD则要好好说道说道。
和其他普普通通的单片机不同,DSP需要使用CMD文件来帮助自己管理内存空间。由于DSP的编译结果是未定位的,也没有操作系统了来定位执行代码,DSP系统配置也不尽相同,因此我们要根据实际的需求来配置CMD文件。这个配置的过程就好像把板子的内存空间比作大仓库,我们来决定把什么类型的货物存放到哪里。对于货物不多的情况(程序和数据占用内存不大),我们可以制定一套通用规则来存放,所以普通程序都会直接把现成的CMD文件拿过来用。但像FFT这种需要大内存空间的算法程序,我们就要好好规划仓库了(重新安排CMD文件),必要时还需扩充片外RAM。

源文件名的玄机

由于项目开发者的编程风格不尽相同,我们有时可以看到不同的项目结构和不同的文件命名,这里我用比较常见的外设命名法举例说明每个源文件是干嘛的。
拿我所使用的例程来看:
DSP28_ADC.C ——外设AD的初始化函数,与外设AD相关
DSP28_CpuTimers.C——CPU定时器的初始化和配置函数,与CPU的定时器相关
DSP28_DefaultIsr.C——这个文件很重要,包含了2812所有的中断函数,写中断时,只要将程序写在对应的函数内就可以,大大保证了中断的成功率。
DSP28_ECan.C——外设CAN的初始化函数,与外设CAN相关。
DSP28_Ev.C——外设EV的初始化函数,与外设EV相关。
DSP28_GlobalVariableDefs.C——全局变量的定义,这个文件也很重要,定义了2812的寄存器,中断向量表等内容。
DSP28_Gpio.C——GPIO的初始化函数,只和GPIO相关。
DSP28_InitPeripherals.C——所有外设的初始化函数,函数的内容是调用了 2812 各个外设的初始化函数。
DSP28_Mcbsp.C——Mcbsp的初始化函数,只和Mcbsp相关。
DSP28_PieCtrl.C——PIE初始化函数,和中断相关,很重要。
DSP28_PieVect.C——PIE中断向量表定义以及初始化,很重要。
DSP28_Sci.C——外设 SCI的初始化函数,只和外设SCI相关。
DSP28_Spi.C——外设SPI的初始化函数,只和外设SPI相关。
DSP28_SysCtrl.C——系统初始化,主要对开门狗,时钟等模块进行初始化,以保证 2812 正常工作,非常重要。
DSP28_Xintf.C——外部接口的初始化函数。
DSP28_XIntrupt.C——外部中断的初始化函数。
Example_28xGpio.C——main函数所在的文件,但是各个工程的Main函数一般都是不一样的。
通过上面的分析我们可以看到几个文件非常重要,DSP28_DefaultIsr.C,DSP28_GlobalVariableDefs.C,DSP28_PieCtrl.C,DSP28_PieVect.C,DSP28_SysCtrl.C,因此每次新建工程的时候,就先把这些未编辑过的文件复制过来。其他的外设相关的文件,您这个工程中涉及到哪个外设,就把这个外设相关的源文件复制过来,一起加入工程。

本篇笔记到这里就结束啦,主要说了一些DSP初印象以及CCS编译器入门的内容,下篇(咕)会说存储器映射和中断的相关知识,敬请期待捏(咕)。