port.c 7.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213
  1. /*
  2. * FreeRTOS Kernel <DEVELOPMENT BRANCH>
  3. * Copyright (C) 2021 Amazon.com, Inc. or its affiliates. All Rights Reserved.
  4. *
  5. * SPDX-License-Identifier: MIT
  6. *
  7. * Permission is hereby granted, free of charge, to any person obtaining a copy of
  8. * this software and associated documentation files (the "Software"), to deal in
  9. * the Software without restriction, including without limitation the rights to
  10. * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
  11. * the Software, and to permit persons to whom the Software is furnished to do so,
  12. * subject to the following conditions:
  13. *
  14. * The above copyright notice and this permission notice shall be included in all
  15. * copies or substantial portions of the Software.
  16. *
  17. * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  18. * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
  19. * FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
  20. * COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
  21. * IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
  22. * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  23. *
  24. * https://www.FreeRTOS.org
  25. * https://github.com/FreeRTOS
  26. *
  27. */
  28. /* Scheduler includes. */
  29. #include "FreeRTOS.h"
  30. #include "task.h"
  31. /* The critical nesting value is initialised to a non zero value to ensure
  32. * interrupts don't accidentally become enabled before the scheduler is started. */
  33. #define portINITIAL_CRITICAL_NESTING ( ( uint16_t ) 10 )
  34. /* Initial PSW value allocated to a newly created task.
  35. * 11000110
  36. * ||||||||-------------- Fill byte
  37. * |||||||--------------- Carry Flag cleared
  38. * |||||----------------- In-service priority Flags set to low level
  39. * ||||------------------ Register bank Select 0 Flag cleared
  40. * |||------------------- Auxiliary Carry Flag cleared
  41. * ||-------------------- Register bank Select 1 Flag cleared
  42. * |--------------------- Zero Flag set
  43. * ---------------------- Global Interrupt Flag set (enabled)
  44. */
  45. #define portPSW ( 0xc6UL )
  46. /* Each task maintains a count of the critical section nesting depth. Each time
  47. * a critical section is entered the count is incremented. Each time a critical
  48. * section is exited the count is decremented - with interrupts only being
  49. * re-enabled if the count is zero.
  50. *
  51. * usCriticalNesting will get set to zero when the scheduler starts, but must
  52. * not be initialised to zero as that could cause problems during the startup
  53. * sequence. */
  54. volatile uint16_t usCriticalNesting = portINITIAL_CRITICAL_NESTING;
  55. /*-----------------------------------------------------------*/
  56. /*
  57. * Sets up the periodic ISR used for the RTOS tick.
  58. */
  59. __attribute__( ( weak ) ) void vApplicationSetupTimerInterrupt( void );
  60. /*
  61. * Starts the scheduler by loading the context of the first task to run.
  62. * (defined in portasm.S).
  63. */
  64. extern void vPortStartFirstTask( void );
  65. /*-----------------------------------------------------------*/
  66. /*
  67. * Initialise the stack of a task to look exactly as if a call to
  68. * portSAVE_CONTEXT had been called.
  69. *
  70. * See the header file portable.h.
  71. */
  72. StackType_t * pxPortInitialiseStack( StackType_t * pxTopOfStack,
  73. TaskFunction_t pxCode,
  74. void * pvParameters )
  75. {
  76. uint32_t * pulLocal;
  77. /* Stack type and pointers to the stack type are both 2 bytes. */
  78. /* Parameters are passed in on the stack, and written using a 32bit value
  79. * hence a space is left for the second two bytes. */
  80. pxTopOfStack--;
  81. /* Write in the parameter value. */
  82. pulLocal = ( uint32_t * ) pxTopOfStack;
  83. *pulLocal = ( StackType_t ) pvParameters;
  84. pxTopOfStack--;
  85. /* The return address, leaving space for the first two bytes of the
  86. * 32-bit value. */
  87. pxTopOfStack--;
  88. pulLocal = ( uint32_t * ) pxTopOfStack;
  89. *pulLocal = ( uint32_t ) 0;
  90. pxTopOfStack--;
  91. /* The start address / PSW value is also written in as a 32bit value,
  92. * so leave a space for the second two bytes. */
  93. pxTopOfStack--;
  94. /* Task function start address combined with the PSW. */
  95. pulLocal = ( uint32_t * ) pxTopOfStack;
  96. *pulLocal = ( ( ( uint32_t ) pxCode ) | ( portPSW << 24UL ) );
  97. pxTopOfStack--;
  98. /* An initial value for the AX register. */
  99. *pxTopOfStack = ( StackType_t ) 0x1111;
  100. pxTopOfStack--;
  101. /* An initial value for the HL register. */
  102. *pxTopOfStack = ( StackType_t ) 0x2222;
  103. pxTopOfStack--;
  104. /* CS and ES registers. */
  105. *pxTopOfStack = ( StackType_t ) 0x0F00;
  106. pxTopOfStack--;
  107. /* The remaining general purpose registers bank 0 (DE and BC) and the other
  108. * two register banks...register bank 3 is dedicated for use by interrupts so
  109. * is not saved as part of the task context. */
  110. pxTopOfStack -= 10;
  111. /* Finally the critical section nesting count is set to zero when the task
  112. * first starts. */
  113. *pxTopOfStack = ( StackType_t ) portNO_CRITICAL_SECTION_NESTING;
  114. /* Return a pointer to the top of the stack that has been generated so it
  115. * can be stored in the task control block for the task. */
  116. return pxTopOfStack;
  117. }
  118. /*-----------------------------------------------------------*/
  119. BaseType_t xPortStartScheduler( void )
  120. {
  121. /* Setup the hardware to generate the tick. Interrupts are disabled when
  122. * this function is called. */
  123. vApplicationSetupTimerInterrupt();
  124. /* Restore the context of the first task that is going to run. */
  125. vPortStartFirstTask();
  126. /* Execution should not reach here as the tasks are now running! */
  127. return pdTRUE;
  128. }
  129. /*-----------------------------------------------------------*/
  130. void vPortEndScheduler( void )
  131. {
  132. /* It is unlikely that the RL78 port will get stopped. */
  133. }
  134. /*-----------------------------------------------------------*/
  135. __attribute__( ( weak ) ) void vApplicationSetupTimerInterrupt( void )
  136. {
  137. const uint16_t usClockHz = 15000UL; /* Internal clock. */
  138. const uint16_t usCompareMatch = ( usClockHz / configTICK_RATE_HZ ) + 1UL;
  139. /* Use the internal 15K clock. */
  140. OSMC = ( unsigned char ) 0x16;
  141. #ifdef RTCEN
  142. {
  143. /* Supply the interval timer clock. */
  144. RTCEN = ( unsigned char ) 1U;
  145. /* Disable INTIT interrupt. */
  146. ITMK = ( unsigned char ) 1;
  147. /* Disable ITMC operation. */
  148. ITMC = ( unsigned char ) 0x0000;
  149. /* Clear INIT interrupt. */
  150. ITIF = ( unsigned char ) 0;
  151. /* Set interval and enable interrupt operation. */
  152. ITMC = usCompareMatch | 0x8000U;
  153. /* Enable INTIT interrupt. */
  154. ITMK = ( unsigned char ) 0;
  155. }
  156. #endif /* ifdef RTCEN */
  157. #ifdef TMKAEN
  158. {
  159. /* Supply the interval timer clock. */
  160. TMKAEN = ( unsigned char ) 1U;
  161. /* Disable INTIT interrupt. */
  162. TMKAMK = ( unsigned char ) 1;
  163. /* Disable ITMC operation. */
  164. ITMC = ( unsigned char ) 0x0000;
  165. /* Clear INIT interrupt. */
  166. TMKAIF = ( unsigned char ) 0;
  167. /* Set interval and enable interrupt operation. */
  168. ITMC = usCompareMatch | 0x8000U;
  169. /* Enable INTIT interrupt. */
  170. TMKAMK = ( unsigned char ) 0;
  171. }
  172. #endif /* ifdef TMKAEN */
  173. }
  174. /*-----------------------------------------------------------*/