EE251: Tuesday October 23 Higher Frequency Clock via Phase Locked Loop TIMER MODULE: SysTick-Basis of next week s lab Section 12.4 and 18 in text describes our SysTick Section 2.5 of Valvano s Real Time Interfacing text Several SysTick slides are from Dr. Jonathan Valvano, University of Texas SysTick Use of Interrupts Lab 5 Due This Week Lab 6 (AtoD Conversion) This Week. Homework #5 Due Thursday Lab 7 (SysTick Timer) Next Week Lecture #19 1
PLL: Phase-Locked Loop External crystal Main Osc 16 MHz Internal Osc /4 30 khz Internal Osc Ref Clk OSCSRC 00 Mux 01 10* 11* Phase/ Freq Detector Phase-Lock-Loop Up Down * can't drive the PLL /m Charge Pump/ LPF VCO 400 MHz /2 DIV400 1 Mux 0 200 MHz BYPASS USESYSDIV 1 Mux 0 0 Mux /n SYSDIV 1 XTAL Internal oscillator requires minimal power but is imprecise External crystal provides stable bus clock TM4C is equipped with 16 MHz crystal and bus clock can be set to a maximum of 80 MHz See Wikipedia s entry on Phase-Locked Loop for explanation Lecture #19 2
Phase-Locked Loop Software to enable the phase-lock loop is not worth the effort to explain in this course. Example source code to enable changing the system clock frequency is available in Code Files on our lab web page. We have tested this code. PLL.s subroutine to enable PLL PLL_main.s program to demonstrate its use Used with Precision Clock Lecture #19 3
SysTick Timer Timer/Counter operation 24-bit counter decrements at system clock frequency (or precision clock frequency 4) 16 MHz system clock 62.5 ns decrements 16 MHz precision clock ns decrements Counting is from n 0 Setting n appropriately will make the counter a modulo n+1 counter. That is: next_value = (current_value-1) mod (n+1) Sequence: n,n-1,n-2,n-3 2,1,0,n,n-1 E.g. Find n for a 1 ms. count to 0 at 16 MHz? For system clock: 1ms/62.5ns = 16,000 = n+1 or n = 15,999 Will this fit in 24 bits? How big can n be? How much time is this? Lecture #19 4
SysTick Registers Initialization (4 steps) SysTick Timer Address 31-24 23-17 16 15-3 2 1 0 Name $E000E010 0 0 COUNT 0 CLK_SRC INTEN ENABLE NVIC_ST_CTRL_R $E000E014 0 24-bit RELOAD value NVIC_ST_RELOAD_R $E000E018 0 24-bit CURRENT value of SysTick counter NVIC_ST_CURRENT_R Step1: Clear ENABLE bit to stop counter Step2: Specify the RELOAD value n (from previous slide) Step3: Clear the counter by writing to register NVIC_ST_CURRENT_R Step4: Set CLK_SRC=1 (system) or 0 (precision) and specify whether interrupt action via INTEN in NVIC_ST_CTRL_R For details, see the Tiva TM4C123GH6PM Microcontroller Data Sheet, Sect. 3.1.1, p. 123 and Section 3.3, pp. 137-141 Lecture #19 5
SysTick Status Lecture #19 6
SysTick Control Lecture #19 7
Lecture #19 8
Lecture #19 9
SysTick Timer Setup Subroutine SysTick_Init ; disable SysTick during setup LDR R1, =NVIC_ST_CTRL_R MOV R0, #0 ; Clear Enable STR R0, [R1] ; set reload to maximum reload value LDR R1, =NVIC_ST_RELOAD_R LDR R0, =0x00FFFFFF; ; Specify RELOAD value 2 24-1 STR R0, [R1] ; reload at maximum ; writing any value to CURRENT clears it LDR R1, =NVIC_ST_CURRENT_R STR R0, [R1] ; clear counter ; enable SysTick with core clock LDR R1, =NVIC_ST_CTRL_R MOV R0, #0x0005 ; Enable but no interrupts (later) STR R0, [R1] ; ENABLE with System Clock BX LR ; Return from subroutine Lecture #19 10
Time Delay Subroutine (Polling) ;------------SysTick_Wait------------ ; Time delay using busy wait. ; Input: R0 delay parameter in ticks of the core clock ; At 16 MHz, tick is 62.5 nsec ; Output: none ; Modifies: R1 SysTick_Wait SUB R0, R0, #1 ; delay-1 LDR R1, =NVIC_ST_RELOAD_R STR R0, [R1] ; time to wait LDR R1, =NVIC_ST_CURRENT_R STR R0, [R1] ; any value written to CURRENT clears LDR R1, =NVIC_ST_CTRL_R SysTick_Wait_loop LDR R0, [R1] ; read status ANDS R0, R0, #0x00010000 ; bit 16 is COUNT flag BEQ SysTick_Wait_loop ; repeat until flag set BX LR ; flag set, so return from sub Lecture #19 11
Delay Using SysTick_Wait ;------------SysTick_Wait10ms------------ ; Call this routine to wait for R0*10 ms ; Time delay using busy wait. This assumes 16 MHz clock ; Input: R0 number of times to wait 10 ms before returning ; Output: none ; Modifies: R0 DELAY10MS EQU 160000 ; clock cycles for 10 ms delay SysTick_Wait10ms PUSH {R4, LR} ; save R4 and LR MOVS R4, R0 ; R4 = R0 = remainingwaits BEQ SysTick_Wait10ms_done ; R4 == 0, done ; SysTick_Wait10ms_loop LDR R0, =DELAY10MS ; R0 = DELAY10MS BL SysTick_Wait ; wait 10 ms SUBS R4, R4, #1 ; remainingwaits-- BHI SysTick_Wait10ms_loop ; if(r4>0), wait another 10 ms ; SysTick_Wait10ms_done POP {R4, PC} ; pop R4 and Return Lecture #19 12
SysTick Timer Methods Method just shown uses polling. When would using polling be appropriate? Will show how to initiate and use interrupts Frees up processor for other tasks Basis for Real-Time systems SysTick Interrupts will be used in Lab 7 Also Precision Clock, but no PLL Lecture #19 13
Lab 7 Fig. 7.5- Data Structures NVIC_ST_CTRL NVIC_ST_RELOAD NVIC_ST_CURRENT SHP_SYSPRI3 RELOAD_VALUE Stack EQU 0xE000E010 EQU 0xE000E014 EQU 0xE000E018 EQU 0xE000ED20 EQU 0x00300000 EQU 0x00000400 EXTERN OutStr ; Stack area AREA STACK, NOINIT, READWRITE, ALIGN=3 StackMem SPACE Stack ; Reset area AREA RESET, CODE, READONLY THUMB EXPORT Vectors Vectors DCD StackMem + Stack ; Top of Stack DCD Reset_Handler ; Reset Handler... DCD SysTick_Handler ; SysTick Handler Lecture #19 14
Lab 7 Fig. 7.5 - Setup/Main ; Program area AREA.text, CODE, READONLY, ALIGN=2 THUMB EXPORT Reset_Handler Reset_Handler LDR R1, =NVIC_ST_CTRL ; Systick Setup MOV R0, #0 STR R0, [R1] LDR R1, =NVIC_ST_RELOAD LDR R0, =RELOAD_VALUE STR R0, [R1] LDR R1, =NVIC_ST_CURRENT MOV R0, #0 STR R0, [R1] LDR R1, =SHP_SYSPRI3 MOV R0, #0x40000000 STR R0, [R1] LDR R1, =NVIC_ST_CTRL MOV R0, #0x03 STR R0, [R1] ; End of Systick Setup. Main follows CPSIE I ; Systick Main Program wait WFI B wait Lecture #19 15
Lab 7 Fig. 7.5 SysTick ISR ; SysTick ISR EXPORT SysTick_Handler SysTick_Handler ; Systick Interrupt Service Routine (ISR) PUSH {LR} ; Save whatever was in LR since BL Outstr will change this! LDR R0,=hello ; Address of message to Termite in R0 BL OutStr POP {LR} BX LR ; Data area hello DCB "Hello from SysTick",13,4 ALIGN END Lecture #19 16
Enable SysTick Interrupts SysTickInts.s enables interrupts in SysTick (from TI/Texas U) ; **************SysTick_Init********************* ; Initialize SysTick periodic interrupts, priority 2 ; Input: R0 interrupt period Units of period are 1/clockfreq ; Maximum is 2^24-1 Minimum is determined by length of ISR ; Output: none Modifies: R0, R1, R2, R3 SysTick_Init ; start critical section MRS R3, PRIMASK ; save old status CPSID I ; mask all interrupts(except faults) ; disable SysTick during setup LDR R1, =NVIC_ST_CTRL_R MOV R2, #0 STR R2, [R1] ; maximum reload value LDR R1, =NVIC_ST_RELOAD_R ; R1 is pointer to NVIC_ST_CTRL_R ; disable SysTick ; R1 is pointer to NVIC_ST_RELOAD_R SUB R0, R0, #1 ; counts down from RELOAD to 0 STR R0, [R1] ; establish interrupt period ; any write to CURRENT_R clears it LDR R1, =NVIC_ST_CURRENT_R ; R1 is pointer to NVIC_ST_CURRENT_R STR R2, [R1] ; writing to counter clears it Lecture #19 17
Enable SysTick Interrupts SysTickInts.s continued ; set NVIC system interrupt 15 to priority 2 LDR R1, =NVIC_SYS_PRI3_R LDR R2, [R1] ; R1 = &NVIC_SYS_PRI3_R (pointer) ; friendly access AND R2, R2, #0x00FFFFFF ; R2 = R2&0x00FFFFFF (clear interrupt 15 ORR R2, R2, #0x40000000 ; priority) ; R2 = R2 0x40000000 (interrupt 15 priority ; is in bits 31-29) STR R2, [R1] ; set SysTick to priority 2 ; enable SysTick with core clock LDR R1, =NVIC_ST_CTRL_R ; R1 = &NVIC_ST_CTRL_R ; ENABLE SysTick (bit 0), INTEN enable interrupts (bit 1), and ; CLK_SRC (bit 2) is internal MOV R2, #(NVIC_ST_CTRL_ENABLE+NVIC_ST_CTRL_INTEN+NVIC_ST_CTRL_CLK_SRC) STR R2, [R1] ; end critical section ; store a 7 to NVIC_ST_CTRL_R MSR PRIMASK, R3 ; restore old status BX LR ; return Lecture #19 18
SysTick Interrupt Handler PeriodicSysTickInts.s SysTick Interrupt Handler from TI/Texas U EXPORT SysTick_Handler SysTick_Handler ; increment Counts LDR R2, =Counts LDR R3, [R2] ; SysTick Interrupt Service Routine ; R2 = &Counts (pointer) ADD R3, R3, #1 ; R3 = R3 + 1 (Counts = Counts + 1) STR R3, [R2] ; Change LED LDR R2, =GPIO_PORTF_DATA_R AND R3, #0x0000000E ; (overflows after 49 days) ; R2 = &GPIO_PORTF_DATA_R (pointer) ; Keep LED bits only BX LR STR R3, [R2] ; Store back into Port F Data Register ; return from interrupt ; Is this just a regular subroutine return??? Lecture #19 19
SysTick Main Program PeriodicSysTickInts.s Skeleton of main program from TI/ Texas U Start BL PLL_Init ; activate clock for Port F ; set direction register ; regular port function ; enable digital port ; configure as GPIO ; disable analog functionality ; initialize Counts loop WFI LDR R1, =Counts ; 50 MHz clock MOV R0, #0 ; R0 = 0 ; R1 = &Counts (pointer) STR R0, [R1] ; [R1] = R0 (Counts = 0) ; enable SysTick MOV R0, #0x00FFFFFF BL SysTick_Init CPSIE I ; initialize SysTick timer for slow interrupts ; enable SysTick ; enable interrupts and configurable fault ; handlers (clear PRIMASK) ; wait for interrupt B loop ; unconditional branch to 'loop' Lecture #19 20
SysTick Summary SysTick can be used as a time delay It is most powerful as method for creating interrupts on a fixed interval Programming SysTick is straightforward Creating a real-time system based on it is a bit more complex, but fixed-time interrupts is required in many real system environments See both Lecture and Lab Examples Next topic: Timer Module, a Major Topic and basis for Lab #8. Lecture #19 21