timer.c 2.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111
  1. /* ___INGO___ */
  2. #include <arm/NXP/LPC17xx/LPC17xx.h>
  3. #include "bits.h"
  4. #include "config.h"
  5. #include "timer.h"
  6. #include "clock.h"
  7. #include "uart.h"
  8. #include "sdnative.h"
  9. #include "snes.h"
  10. /* bit definitions */
  11. #define RITINT 0
  12. #define RITEN 3
  13. #define PCRIT 16
  14. extern volatile int sd_changed;
  15. extern volatile int reset_changed;
  16. volatile tick_t ticks;
  17. volatile int wokefromrit;
  18. void __attribute__((weak,noinline)) SysTick_Hook(void) {
  19. /* Empty function for hooking the systick handler */
  20. }
  21. /* Systick interrupt handler */
  22. void SysTick_Handler(void) {
  23. ticks++;
  24. static uint16_t sdch_state = 0;
  25. static uint16_t reset_state = 0;
  26. sdch_state = (sdch_state << 1) | SDCARD_DETECT | 0xe000;
  27. if((sdch_state == 0xf000) || (sdch_state == 0xefff)) {
  28. sd_changed = 1;
  29. }
  30. reset_state = (reset_state << 1) | get_snes_reset() | 0xe000;
  31. if((reset_state == 0xf000) || (reset_state == 0xefff)) {
  32. reset_changed = 1;
  33. }
  34. sdn_changed();
  35. SysTick_Hook();
  36. }
  37. void __attribute__((weak,noinline)) RIT_Hook(void) {
  38. }
  39. void RIT_IRQHandler(void) {
  40. LPC_RIT->RICTRL = BV(RITINT);
  41. NVIC_ClearPendingIRQ(RIT_IRQn);
  42. wokefromrit = 1;
  43. RIT_Hook();
  44. }
  45. void timer_init(void) {
  46. /* turn on power to RIT */
  47. BITBAND(LPC_SC->PCONP, PCRIT) = 1;
  48. /* clear RIT mask */
  49. LPC_RIT->RIMASK = 0; /*xffffffff;*/
  50. /* PCLK = CCLK */
  51. BITBAND(LPC_SC->PCLKSEL1, 26) = 1;
  52. BITBAND(LPC_SC->PCLKSEL1, PCLK_TIMER3) = 1;
  53. /* enable SysTick */
  54. SysTick_Config((SysTick->CALIB & SysTick_CALIB_TENMS_Msk));
  55. }
  56. void delay_us(unsigned int time) {
  57. /* Prepare RIT */
  58. LPC_RIT->RICOUNTER = 0;
  59. LPC_RIT->RICOMPVAL = (CONFIG_CPU_FREQUENCY / 1000000) * time;
  60. LPC_RIT->RICTRL = BV(RITEN) | BV(RITINT);
  61. /* Wait until RIT signals an interrupt */
  62. while (!(BITBAND(LPC_RIT->RICTRL, RITINT))) ;
  63. /* Disable RIT */
  64. LPC_RIT->RICTRL = 0;
  65. }
  66. void delay_ms(unsigned int time) {
  67. /* Prepare RIT */
  68. LPC_RIT->RICOUNTER = 0;
  69. LPC_RIT->RICOMPVAL = (CONFIG_CPU_FREQUENCY / 1000) * time;
  70. LPC_RIT->RICTRL = BV(RITEN) | BV(RITINT);
  71. /* Wait until RIT signals an interrupt */
  72. while (!(BITBAND(LPC_RIT->RICTRL, RITINT))) ;
  73. /* Disable RIT */
  74. LPC_RIT->RICTRL = 0;
  75. }
  76. void sleep_ms(unsigned int time) {
  77. wokefromrit = 0;
  78. /* Prepare RIT */
  79. LPC_RIT->RICOUNTER = 0;
  80. LPC_RIT->RICOMPVAL = (CONFIG_CPU_FREQUENCY / 1000) * time;
  81. LPC_RIT->RICTRL = BV(RITEN) | BV(RITINT);
  82. NVIC_EnableIRQ(RIT_IRQn);
  83. /* Wait until RIT signals an interrupt */
  84. //uart_putc(';');
  85. while(!wokefromrit) {
  86. __WFI();
  87. }
  88. NVIC_DisableIRQ(RIT_IRQn);
  89. /* Disable RIT */
  90. LPC_RIT->RICTRL = BV(RITINT);
  91. }