2013년 6월 7일 금요일

Stellaris Launchpad SysTick Interrupt 사용하기

SysTick 인터럽트를 사용하여 LED를 점멸시켜 보도록 하겠다.


  1. #include "inc/hw_types.h"
  2. #include "inc/hw_memmap.h"
  3. #include "driverlib/systick.h"
  4. #include "driverlib/interrupt.h"
  5. #include "driverlib/sysctl.h"
  6. #include "driverlib/gpio.h"
  7. #include "driverlib/rom.h"
  8. #include "driverlib/pin_map.h"

  9. #define LED_RED GPIO_PIN_1
  10. #define LED_BLUE GPIO_PIN_2
  11. #define LED_GREEN GPIO_PIN_3

  12. const unsigned char color[] = {0x2, 0x6, 0x4, 0xc, 0x8, 0xa};
  13. unsigned char color_sz;

  14. void SysTickIntHandler(void);

  15. int main(void)
  16. {
  17. color_sz = sizeof(color);

  18. ROM_SysCtlClockSet(SYSCTL_SYSDIV_4|SYSCTL_USE_PLL|SYSCTL_XTAL_16MHZ|SYSCTL_OSC_MAIN);
  19. ROM_SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOF);
  20. ROM_GPIOPinTypeGPIOOutput(GPIO_PORTF_BASE, LED_RED|LED_BLUE|LED_GREEN);
  21. ROM_GPIOPinWrite(GPIO_PORTF_BASE, LED_RED|LED_GREEN|LED_BLUE, color[5]);

  22. ROM_SysTickPeriodSet(8000000-1);  // 0.5 sec
  23. ROM_SysTickEnable();
  24. ROM_SysTickIntEnable();
  25. ROM_IntMasterEnable();      // CPSIE instruction

  26. while (1) {
  27. }
  28.  }

  29. void SysTickIntHandler(void)
  30. {
  31. static unsigned char idx = 0;

  32. ROM_GPIOPinWrite(GPIO_PORTF_BASE, LED_RED | LED_GREEN | LED_BLUE, color[idx]);
  33. idx = (idx+1)%color_sz;
  34. }


코드는 위와 같다. 위의 코드에서 일정 시간마다 SysTick 인터럽트가 발생하면 37~43 라인의 SysTickIntHandler 함수가 호출되게 된다. 그러므로 main() 함수에서는 초기 설정을 제외하면 메인 루프(33~34라인)에서는 아무 것도 하지 않고 단순히 무한루프를 돌고 있게 된다.

28~31에서 SysTick 인터럽트를 사용하기 위한 설정을 하고 인터럽트를 활성화 시켜주게 되는데 실제 SysTick 인터럽트가 발생했을 때 SysTickIntHandler()를 호출하게 해 주기 위해서는 startup_gcc.c에 있는 인터럽트 벡터 테이블을 수정해 줘야만 한다.

startup_gcc.c는 이전 포스트(Stellaris Launchpad #1)에서 사용했던것과 동일한 startup_gcc.c (~/stellarisware/boards/ek-lm4f120xl/blinky/startup_gcc.c) 를 약간 수정해서 사용한다.


...
//*****************************************************************************
//
// The entry point for the application.
//
//*****************************************************************************
extern int main(void);

// External Interrupt handler declaration

void SysTickIntHandler(void);

//*****************************************************************************
//
// Reserve space for the system stack.
//
//*****************************************************************************
static unsigned long pulStack[64];
...
    IntDefaultHandler,                      // The PendSV handler
    SysTickIntHandler,                      // The SysTick handler
    IntDefaultHandler,                      // GPIO Port A
...


빨간색 라인을 추가하고 파란색 라인 부분은 원래 IntDefaultHandler,      // the SysTick handler 로 되어 있는데 IntDefaultHandler 대신 파란색 부분 같이 SysTick 인터럽트가 발생했을 때 실제 호출될 인터럽트 핸들러 함수 이름으로 바꿔주면 된다.

링커 스트립트 파일과 Makefile은 이전에 사용한것을 그대로 사용해 주면 된다.

정상적으로 바이너리 파일을 만들어 보드로 다운로드 하면 LED D1의 색깔이 주기적으로 바뀌는 걸 볼 수 있다.

댓글 없음:

댓글 쓰기