http://hi.baidu.com/lianghu3124/blog/item/4bcff0029aa25deb08fa9331.html
在DSP的寄存器头文件中使用到VOLATILE(TMS320F2812)
2009-02-26 14:28
在链接器配置文件中的SECTIONS段中为各种外设的寄存器结构映射了他们在dsp内部存储器中的地址。例如tms320f2812的链接器配置文件中有下面部分:(以CPU定时器0为例)
MEMORY中:
PAGE 1 :
/* Peripheral Frame 0: */
CPU_TIMER0 : origin = 0x000C00, length = 0x000008
SECTIONS中:
/* Allocate Peripheral Frame 0 Register Structures: */
CpuTimer0RegsFile : > CPU_TIMER0 PAGE = 1
如此一来就将
CpuTimer0RegsFile 定位到片内rom中特定的位置。接下来就是要将这些位置的寄存器一一指定:
在DSP281x_GlobalVariableDefs.c中有如下内容:
#ifdef __cplusplus
#pragma DATA_SECTION("
CpuTimer0RegsFile")
#else
#pragma DATA_SECTION(
CpuTimer0Regs,"
CpuTimer0RegsFile");
#endif
****** ******
volatile struct CPUTIMER_REGS
CpuTimer0Regs;//在此处定义timer0的结构体
#define
CPUTimer0Regs CpuTimer0Regs
在DSP281x_CpuTimers.h中有如下内容:
extern volatile struct CPUTIMER_REGS
CpuTimer0Regs; //声明外部变量
extern struct CPUTIMER_VARS CpuTimer0; //声明外部变量
其中CPUTIMER_VARS与CPUTIMER_REGS是包含关系:
struct CPUTIMER_REGS {
union TIM_GROUP TIM; // Timer counter register
union PRD_GROUP PRD; // Period register
union TCR_REG TCR; // Timer control register
Uint16 rsvd1; // reserved
union TPR_REG TPR; // Timer pre-scale low
union TPRH_REG TPRH; // Timer pre-scale high
};//定时器寄存器结构体
struct CPUTIMER_VARS {
volatile struct CPUTIMER_REGS *RegsAddr;
Uint32 InterruptCount;
float CPUFreqInMHz;
float PeriodInUSec;
};//定时器0组合结构体,包含寄存器结构体、中断次数、CPU主频、周期
CpuTimer0则是在DSP281x_CpuTimers.c中定义的供用户使用的CPU定时器0组合结构体:
struct CPUTIMER_VARS CpuTimer0; //timer0包含中断次数、寄存器组等的组合结构体。
CpuTimer0.RegsAddr = &CpuTimer0Regs; //将timer0寄存器结构体赋值给组合结构体
如此经过以上几层映射关系,我们在向CpuTimer0. CpuTimer0Regs. TIM.all写数据时就可以准确的写入DSP内部寄存器所在的存储器的位置。并且在读取寄存器的值时由于有 volatile 的作用,每次都是从源地址读取出来的值,保证了数据的正确性。