diff options
Diffstat (limited to 'os')
| -rw-r--r-- | os/ports/GCC/PPC/chcore.c | 14 | ||||
| -rw-r--r-- | os/ports/GCC/PPC/chcore.h | 23 | 
2 files changed, 31 insertions, 6 deletions
| diff --git a/os/ports/GCC/PPC/chcore.c b/os/ports/GCC/PPC/chcore.c index 8403e0171..c3170c6cf 100644 --- a/os/ports/GCC/PPC/chcore.c +++ b/os/ports/GCC/PPC/chcore.c @@ -67,11 +67,11 @@ void port_halt(void) {   * @param[in] ntp       the thread to be switched in
   * @param[in] otp       the thread to be switched out
   */
 -void port_switch(Thread *ntp, Thread *otp) {
 -
 -  (void)otp;
 -  (void)ntp;
 +__attribute__((naked))
 +void port_dummy1(void) {
 +  asm (".global _port_switch");
 +  asm ("_port_switch:");
    asm ("subi        %sp, %sp, 80");     /* Size of the intctx structure.    */
    asm ("mflr        %r0");
    asm ("stw         %r0, 84(%sp)");     /* LR into the caller frame.        */
 @@ -88,6 +88,7 @@ void port_switch(Thread *ntp, Thread *otp) {    asm ("lwz         %r0, 84(%sp)");     /* LR from the caller frame.        */
    asm ("mtlr        %r0");
    asm ("addi        %sp, %sp, 80");     /* Size of the intctx structure.    */
 +  asm ("blr");
  }
  /**
 @@ -95,8 +96,11 @@ void port_switch(Thread *ntp, Thread *otp) {   * @details If the work function returns @p chThdExit() is automatically
   *          invoked.
   */
 -void _port_thread_start(void) {
 +__attribute__((naked))
 +void port_dummy2(void) {
 +  asm (".global _port_thread_start");
 +  asm ("_port_thread_start:");
    chSysUnlock();
    asm ("mr          %r3, %r31");        /* Thread parameter.                */
    asm ("mtctr       %r30");
 diff --git a/os/ports/GCC/PPC/chcore.h b/os/ports/GCC/PPC/chcore.h index c64737c67..0f78b3b9b 100644 --- a/os/ports/GCC/PPC/chcore.h +++ b/os/ports/GCC/PPC/chcore.h @@ -342,6 +342,27 @@ struct context {  #define port_enable() asm volatile ("wrteei  1" : : : "memory")
  /**
 + * @brief   Performs a context switch between two threads.
 + * @details This is the most critical code in any port, this function
 + *          is responsible for the context switch between 2 threads.
 + * @note    The implementation of this code affects <b>directly</b> the context
 + *          switch performance so optimize here as much as you can.
 + *
 + * @param[in] ntp       the thread to be switched in
 + * @param[in] otp       the thread to be switched out
 + */
 +#if !CH_DBG_ENABLE_STACK_CHECK || defined(__DOXYGEN__)
 +#define port_switch(ntp, otp) _port_switch(ntp, otp)
 +#else
 +#define port_switch(ntp, otp) {                                             \
 +  register struct intctx *sp asm ("%r1");                                   \
 +  if ((stkalign_t *)(sp - 1) < otp->p_stklimit)                             \
 +    chDbgPanic("stack overflow");                                           \
 +  _port_switch(ntp, otp);                                                   \
 +}
 +#endif
 +
 +/**
   * @brief   Writes to a special register.
   *
   * @param[in] spr       special register number
 @@ -369,7 +390,7 @@ extern "C" {  #endif
    void port_init(void);
    void port_halt(void);
 -  void port_switch(Thread *ntp, Thread *otp);
 +  void _port_switch(Thread *ntp, Thread *otp);
    void _port_thread_start(void);
  #ifdef __cplusplus
  }
 | 
