revert between 56095 -> 55830 in arch
[AROS.git] / arch / ppc-sam440 / kernel / kernel_cpu.c
blob82aeb6c9bd776e4aa6d0efd51c4c93964f42c6ee
1 /*
2 Copyright © 1995-2012, The AROS Development Team. All rights reserved.
3 $Id$
4 */
6 #include <aros/debug.h>
8 #include <asm/amcc440.h>
9 #include <aros/kernel.h>
10 #include <aros/libcall.h>
11 #include <exec/execbase.h>
12 #include <hardware/intbits.h>
14 #include "etask.h"
16 #include "kernel_intern.h"
17 #include "kernel_cpu.h"
18 #include "kernel_syscall.h"
19 #include "kernel_scheduler.h"
20 #include "kernel_intr.h"
22 #include <strings.h>
25 * Task dispatcher. Basically it may be the same one no matter what scheduling algorithm is used
27 void cpu_Dispatch(context_t *regs)
29 struct Task *task;
30 uint64_t idle;
31 extern uint64_t idle_time;
33 __asm__ __volatile__("wrteei 0;");
34 idle = mftbu();
36 /*
37 * Is the list of ready tasks empty? Well, increment the idle switch cound and halt CPU.
38 * It should be extended by some plugin mechanism which would put CPU and whole machine
39 * into some more sophisticated sleep states (ACPI?)
42 /* Break Disable() if needed */
43 if (SysBase->IDNestCnt >= 0) {
44 SysBase->IDNestCnt = -1;
45 /* Enable selected external interrupts */
46 wrdcr(UIC0_ER, uic_er[0]);
49 while (!(task = core_Dispatch())) {
50 wrmsr(rdmsr() | MSR_POW | MSR_EE);
51 __asm__ __volatile__("sync; isync;");
52 __asm__ __volatile__("wrteei 0");
53 idle_time += mftbu() - idle;
55 if (SysBase->SysFlags & SFF_SoftInt)
56 core_Cause(INTB_SOFTINT, 1l << INTB_SOFTINT);
59 /* Restore the task's state */
60 CopyMem(task->tc_UnionETask.tc_ETask->et_RegFrame, regs, sizeof(regs_t));
61 regs->cpu.gpr[1] = (IPTR)task->tc_SPReg;
63 /* Handle tasks's flags */
64 if (task->tc_Flags & TF_EXCEPT)
65 Exception();
67 /* Store the launch time */
68 GetIntETask(task)->iet_private1 = mftbu();
70 if (task->tc_Flags & TF_LAUNCH)
72 AROS_UFC1(void, task->tc_Launch,
73 AROS_UFCA(struct ExecBase *, SysBase, A6));
76 /* Copy the fpu, mmx, xmm state */
77 // FIXME: Change to the lazy saving of the FPU state!!!!
79 regs->cpu.srr1 |= MSR_EE;
82 void cpu_Switch(context_t *regs)
84 struct Task *task;
86 /* Disable interrupts until the task switch */
87 __asm__ __volatile__("wrteei 0");
89 task = SysBase->ThisTask;
91 /* Copy current task's context into the ETask structure */
92 memmove(task->tc_UnionETask.tc_ETask->et_RegFrame, regs, sizeof(context_t));
94 /* Copy the fpu, mmx, xmm state */
95 // FIXME: Change to the lazy saving of the FPU state!!!!
97 task->tc_SPReg = (APTR)regs->cpu.gpr[1];
99 core_Switch();