linux/arch/h8300/include/asm/switch_to.h
<<
>>
Prefs
   1/* SPDX-License-Identifier: GPL-2.0 */
   2#ifndef _H8300_SWITCH_TO_H
   3#define _H8300_SWITCH_TO_H
   4
   5/*
   6 * switch_to(n) should switch tasks to task ptr, first checking that
   7 * ptr isn't the current task, in which case it does nothing.  This
   8 * also clears the TS-flag if the task we switched to has used the
   9 * math co-processor latest.
  10 */
  11/*
  12 * switch_to() saves the extra registers, that are not saved
  13 * automatically by SAVE_SWITCH_STACK in resume(), ie. d0-d5 and
  14 * a0-a1. Some of these are used by schedule() and its predecessors
  15 * and so we might get see unexpected behaviors when a task returns
  16 * with unexpected register values.
  17 *
  18 * syscall stores these registers itself and none of them are used
  19 * by syscall after the function in the syscall has been called.
  20 *
  21 * Beware that resume now expects *next to be in d1 and the offset of
  22 * tss to be in a1. This saves a few instructions as we no longer have
  23 * to push them onto the stack and read them back right after.
  24 *
  25 * 02/17/96 - Jes Sorensen (jds@kom.auc.dk)
  26 *
  27 * Changed 96/09/19 by Andreas Schwab
  28 * pass prev in a0, next in a1, offset of tss in d1, and whether
  29 * the mm structures are shared in d2 (to avoid atc flushing).
  30 *
  31 * H8/300 Porting 2002/09/04 Yoshinori Sato
  32 */
  33
  34asmlinkage void resume(void);
  35#define switch_to(prev, next, last) \
  36do {                         \
  37        void *_last;                                        \
  38        __asm__ __volatile__(                               \
  39                "mov.l  %1, er0\n\t"                        \
  40                "mov.l  %2, er1\n\t"                        \
  41                "mov.l  %3, er2\n\t"                        \
  42                "jsr @_resume\n\t"                          \
  43                "mov.l  er2,%0\n\t"                         \
  44                : "=r" (_last)                              \
  45                : "r" (&(prev->thread)),                    \
  46                  "r" (&(next->thread)),                    \
  47                  "g" (prev)                                \
  48                : "cc", "er0", "er1", "er2", "er3");        \
  49        (last) = _last;                                     \
  50} while (0)
  51
  52#endif /* _H8300_SWITCH_TO_H */
  53