TMS320F28335之定时器
定時器系統原理介紹?
TMS320F28335的CPU Time有三個,分別為Timer0,Timer1,Timer2,其中Timer2是為操作系統DSP/BIOS保留的,當未移植操作系統時,可用來做普通的定時器。這三個定時器的中斷信號分別為TINT0, TINT1, TINT2,分別對應于中斷向量INT1,INT13,INT14。圖4-2為定時器的結構框圖,圖中TIMH:TIM為計數寄存器,PRDH:PRD為周期寄存器,形如AH格式:A的形式表示一個32位的寄存器,是由兩個16位的寄存器構成,AH是高16位,A是低16位。?
CPU定時器的計數復位時,計數寄存器TIMH:TIM加載周期寄存器PRDH:PRD所設定的值,經歷一個計數器時鐘后,TIMH:TIM內的值就減1,一直減到0,這時產生定時器周期中斷事件,并重新裝載PRDH:PRD所設定的值,重新開始計數。至于每隔多少時間,計數寄存器TIMH:TIM的值才會減1則由預分頻寄存器TPRH:TPR來決定。?
TPRH和TPR這兩個寄存器由兩部分組成,高8位為定時器預分頻計數器PSC,低8位是定時器分頻TDDR。也即是說,TPRH是由PSCH和TDDRH構成,而TDDR由PSC和TDDR構成。且其工作的原理與51系列單片機定時器計數器類似,復位時,PSCH:PSC加載TDDRH:TDDR所設定的值,然后經過一個CPU時鐘,PSCH:PSC的值減1,當PSCH:PSC的值減到0時,會再次裝載TDDRH:TDDR所設定的值,并且產生一個計數器時鐘,TIMH:TIM減1。CPU定時器0、1、2配置和控制寄存器如表4-1所示?
定時器定時時間的公式計算?
以上寄存器測值在配置函數ConfigCpuTimer(struct CPUTIMER_VARS *Timer, float Freq, float Period)中設置。形參Timer為第幾位定時器,Freq為定時頻率,Period為計時周期。?
假若Freq為15,Period為1000000,則時間t = 1*15*1000000/150M = 0.1s (系統時鐘頻率為150M)。不過這個算式的成立是有條件的,這個條件就是以下兩條語句:
Timer->RegsAddr->TPR.all = 0
Timer->RegsAddr->TPRH.all = 0
上文曾提及,定時器的計數時鐘是有預分頻寄存器TPRH:TPR決定的。CpuTimerxRegs.TPR.all = 0, CpuTimerxRegs.TPRH.all = 0這兩句話決定了1個時鐘源周期為定時器的時鐘周期(即一個SYSCLKOUT,TIMH:TIM減1),若CpuTimerxRegs.TPR.all = y,CpuTimerxRegs.TPRH.all = 0,則計y+1個時鐘周期為定時器的時鐘周期。X表示0,1,2中的任意值(任意定時器)。
因此,真正的定時時間為:time =TPRH:TPR/SYSCLKOUT*Freq*Peroid。只有當TPRH:TPR=0時,SYSCLKOUT直接作為TIMH:TIM的時鐘周期,time =Freq*Peroid/SYSCLKOUT。另外,在定時器配置函數中,
Timer->RegsAddr->TCR.bit.TSS = 1 表示停止定時器 ;
Timer->RegsAddr->TCR.bit.TRB = 1 表示重裝定時器;
Timer->RegsAddr->TCR.bit.FREE = 1 表示定時器自由運行;
Timer->RegsAddr->TCR.bit.TIE = 1 表示使能定時器中斷。
如果要利用定時器產生一定周期的時間中斷,別忘了在主函數中設置響應的中斷向量即可。
TI官方頭文件DSP2833x_CpuTimers.h程序如下:
// TI File $Revision: /main/4 $ // Checkin $Date: March 20, 2007 15:33:42 $ //########################################################################### // // FILE: DSP2833x_CpuTimers.h // // TITLE: DSP2833x CPU 32-bit 定時器寄存器定義. // // NOTES: CpuTimer1 and CpuTimer2 are reserved for use with DSP BIOS and // other realtime operating systems. // // Do not use these two timers in your application if you ever plan // on integrating DSP-BIOS or another realtime OS. // // For this reason, comment out the code to manipulate these two timers // if using DSP-BIOS or another realtime OS. // //########################################################################### // $TI Release: DSP2833x/DSP2823x C/C++ Header Files V1.31 $ // $Release Date: August 4, 2009 $ //############################################################################ifndef DSP2833x_CPU_TIMERS_H #define DSP2833x_CPU_TIMERS_H#ifdef __cplusplus extern "C" { #endif//--------------------------------------------------------------------------- // CPU 定時器寄存器位定義: // // // TCR: 定時器控制寄存器定義: struct TCR_BITS { // bits 描述Uint16 rsvd1:4; // 3:0 保留Uint16 TSS:1; // 4 定時器啟動/停止Uint16 TRB:1; // 5 定時器重載Uint16 rsvd2:4; // 9:6 保留Uint16 SOFT:1; // 10 運行模式Uint16 FREE:1; // 11 運行模式Uint16 rsvd3:2; // 12:13 保留Uint16 TIE:1; // 14 中斷使能Uint16 TIF:1; // 15 中斷標志位 }; //定時器控制寄存器 union TCR_REG {Uint16 all;struct TCR_BITS bit; //定時器控制寄存器定義 };// TPR: 預分頻低電平寄存器定義: struct TPR_BITS { // bits 描述Uint16 TDDR:8; // 7:0 定時計數寄存器Uint16 PSC:8; // 15:8 預分頻計數器低位 }; //預分頻低電平寄存器 union TPR_REG {Uint16 all;struct TPR_BITS bit; //預分頻低電平寄存器定義 };// TPRH: 預分頻高電平寄存器定義: struct TPRH_BITS { // bits 描述Uint16 TDDRH:8; // 7:0 定時計數器寄存器Uint16 PSCH:8; // 15:8 預分頻計數器高位 }; //預分頻寄存器高電平寄存器 union TPRH_REG {Uint16 all;struct TPRH_BITS bit; //預分頻高電平寄存器定義 };// TIM, TIMH: 計數器寄存器定義: struct TIM_REG {Uint16 LSW; //低位Uint16 MSW; //高位 }; //計數器寄存器 union TIM_GROUP {Uint32 all;struct TIM_REG half; //計數器寄存器定義 };// PRD, PRDH: 周期寄存器定義: struct PRD_REG {Uint16 LSW; //低位Uint16 MSW; //高位 }; //周期寄存器 union PRD_GROUP {Uint32 all;struct PRD_REG half; //周期寄存器定義 };//--------------------------------------------------------------------------- // CPU 定時器寄存器文件: // struct CPUTIMER_REGS {union TIM_GROUP TIM; // 計數器寄存器union PRD_GROUP PRD; // 周期寄存器union TCR_REG TCR; // 定時器控制寄存器Uint16 rsvd1; // 保留union TPR_REG TPR; // 預分頻低電平寄存器union TPRH_REG TPRH; // 預分頻高電平寄存器 };//--------------------------------------------------------------------------- // CPU 定時器支持的變量: // struct CPUTIMER_VARS {volatile struct CPUTIMER_REGS *RegsAddr; //定時器結構體Uint32 InterruptCount; //中斷計數器float CPUFreqInMHz; //頻率float PeriodInUSec; //周期 };//--------------------------------------------------------------------------- // 函數原型和外部定義: // extern void InitCpuTimers(void); //初始化定時器 void ConfigCpuTimer(struct CPUTIMER_VARS *Timer, float Freq, float Period); //定時器配置函數 extern volatile struct CPUTIMER_REGS CpuTimer0Regs; extern struct CPUTIMER_VARS CpuTimer0;//CpuTimer 1和CpuTimer2預留給DSP BIOS和其他操作系統 如果使用DSP BIOS或其他操作系統注釋掉CpuTimer1 CpuTimer2 extern volatile struct CPUTIMER_REGS CpuTimer1Regs; extern volatile struct CPUTIMER_REGS CpuTimer2Regs;extern struct CPUTIMER_VARS CpuTimer1; extern struct CPUTIMER_VARS CpuTimer2;//--------------------------------------------------------------------------- // 實用定時器操作: // // 啟動定時器0: #define StartCpuTimer0() CpuTimer0Regs.TCR.bit.TSS = 0// 停止定時器0: #define StopCpuTimer0() CpuTimer0Regs.TCR.bit.TSS = 1// 重載定時器周期值: #define ReloadCpuTimer0() CpuTimer0Regs.TCR.bit.TRB = 1// 讀取定時器0計數器寄存器的值: #define ReadCpuTimer0Counter() CpuTimer0Regs.TIM.all// 讀取定時器0周期寄存器的值: #define ReadCpuTimer0Period() CpuTimer0Regs.PRD.all// CpuTimer 1 and CpuTimer2 are reserved for DSP BIOS & other RTOS // Do not use these two timers if you ever plan on integrating // DSP-BIOS or another realtime OS. // // For this reason, comment out the code to manipulate these two timers // if using DSP-BIOS or another realtime OS.// 啟動定時器1、2: #define StartCpuTimer1() CpuTimer1Regs.TCR.bit.TSS = 0 #define StartCpuTimer2() CpuTimer2Regs.TCR.bit.TSS = 0// 停止定時器1、2: #define StopCpuTimer1() CpuTimer1Regs.TCR.bit.TSS = 1 #define StopCpuTimer2() CpuTimer2Regs.TCR.bit.TSS = 1// 重載定時器周期值1、2: #define ReloadCpuTimer1() CpuTimer1Regs.TCR.bit.TRB = 1 #define ReloadCpuTimer2() CpuTimer2Regs.TCR.bit.TRB = 1// 讀取定時器1、2計數器寄存器的值: #define ReadCpuTimer1Counter() CpuTimer1Regs.TIM.all #define ReadCpuTimer2Counter() CpuTimer2Regs.TIM.all// 讀取定時器1、2周期寄存器的值: #define ReadCpuTimer1Period() CpuTimer1Regs.PRD.all #define ReadCpuTimer2Period() CpuTimer2Regs.PRD.all#ifdef __cplusplus } #endif /* extern "C" */#endif // end of DSP2833x_CPU_TIMERS_H definition//=========================================================================== // End of file. //===========================================================================- ?
其中的實例程序如下:
// TI File $Revision: /main/4 $ // Checkin $Date: July 9, 2009 10:51:59 $ //########################################################################### // // FILE: DSP2833x_CpuTimers.c // // TITLE: CPU 32-bit Timers 初始化 & 支持功能. // // NOTES: CpuTimer2 is reserved for use with DSP BIOS and // other realtime operating systems. // // Do not use these this timer in your application if you ever plan // on integrating DSP-BIOS or another realtime OS. // //########################################################################### // $TI Release: DSP2833x/DSP2823x C/C++ Header Files V1.31 $ // $Release Date: August 4, 2009 $ //############################################################################include "DSP2833x_Device.h" // Headerfile Include File #include "DSP2833x_Examples.h" // Examples Include Filestruct CPUTIMER_VARS CpuTimer0;// 當使用DSP BIOS和其他操作系統,CPU定時器2的代碼注釋掉 struct CPUTIMER_VARS CpuTimer1; struct CPUTIMER_VARS CpuTimer2;//--------------------------------------------------------------------------- // InitCpuTimers: //--------------------------------------------------------------------------- // 改函數將三個CPU的定時器初始化到一個已知狀態. // void InitCpuTimers(void) //初始化定時器寄存器 {// CPU 定時器 0// 寄存器地址指針和各自計時器初始化:CpuTimer0.RegsAddr = &CpuTimer0Regs;// 定時器周期寄存器最大值初始化:CpuTimer0Regs.PRD.all = 0xFFFFFFFF;// 預分頻寄存器初始化為1 (SYSCLKOUT):CpuTimer0Regs.TPR.all = 0;CpuTimer0Regs.TPRH.all = 0;// 確保定時器0停止:CpuTimer0Regs.TCR.bit.TSS = 1;// 重加載計數器周期值:CpuTimer0Regs.TCR.bit.TRB = 1;// 復位中斷計時器:CpuTimer0.InterruptCount = 0;// CpuTimer2 is reserved for DSP BIOS & other RTOS // Do not use this timer if you ever plan on integrating // DSP-BIOS or another realtime OS.// 寄存器地址指針和各自計時器初始化:CpuTimer1.RegsAddr = &CpuTimer1Regs;CpuTimer2.RegsAddr = &CpuTimer2Regs;// 定時器1、2周期最大值初始化:CpuTimer1Regs.PRD.all = 0xFFFFFFFF;CpuTimer2Regs.PRD.all = 0xFFFFFFFF;// 確保定時器停止:CpuTimer1Regs.TCR.bit.TSS = 1;CpuTimer2Regs.TCR.bit.TSS = 1;// 重加載計數器周期值:CpuTimer1Regs.TCR.bit.TRB = 1;CpuTimer2Regs.TCR.bit.TRB = 1;// 復位中斷計時器:CpuTimer1.InterruptCount = 0;CpuTimer2.InterruptCount = 0;}//--------------------------------------------------------------------------- // 配置CpuTimer: //--------------------------------------------------------------------------- // 這個函數初始化,選擇定時器,周期參數指定“頻率”和“時間”參數. // 頻率為MHz,時間為us級,定時器配置后保存在停止狀態 // void ConfigCpuTimer(struct CPUTIMER_VARS *Timer, float Freq, float Period) {Uint32 temp;// 定時器周期參數初始化:Timer->CPUFreqInMHz = Freq; //頻率Timer->PeriodInUSec = Period; //周期temp = (long) (Freq * Period);Timer->RegsAddr->PRD.all = temp; //周期寄存器設定值為timer// 預分頻寄存器初始化為1 (SYSCLKOUT):Timer->RegsAddr->TPR.all = 0;Timer->RegsAddr->TPRH.all = 0;// 定時器控制寄存器初始化:Timer->RegsAddr->TCR.bit.TSS = 1; // 1 = 停止定時器, 0 = 啟動/重啟定時器Timer->RegsAddr->TCR.bit.TRB = 1; // 1 = 重載計時器Timer->RegsAddr->TCR.bit.SOFT = 1; // 定時器自由運行Timer->RegsAddr->TCR.bit.FREE = 1; // 定時器自由運行Timer->RegsAddr->TCR.bit.TIE = 1; // 0 = 禁止/ 1 = 定時器中斷使能// 復位中斷計數器:Timer->InterruptCount = 0; }//=========================================================================== // End of file. //===========================================================================- ?
參考資料
【TI博客大賽】TI C2000 TMS320F28335定時器配置簡介?
2.3 關于ConfigCpuTimer()函數的說明?
百度文庫-ConfigCpuTimer()函數
文章標簽:?操作系統
個人分類:?DSP_28335
總結
以上是生活随笔為你收集整理的TMS320F28335之定时器的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 【经典算法大全】
- 下一篇: 28335的CPU定时器解析