summaryrefslogtreecommitdiff
path: root/arch/x86/machine/tcb_asm.S
diff options
context:
space:
mode:
Diffstat (limited to 'arch/x86/machine/tcb_asm.S')
-rw-r--r--arch/x86/machine/tcb_asm.S94
1 files changed, 94 insertions, 0 deletions
diff --git a/arch/x86/machine/tcb_asm.S b/arch/x86/machine/tcb_asm.S
new file mode 100644
index 00000000..0be93809
--- /dev/null
+++ b/arch/x86/machine/tcb_asm.S
@@ -0,0 +1,94 @@
+/*
+ * Copyright (c) 2012 Richard Braun.
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include <machine/asm.h>
+#include <machine/cpu.h>
+
+.text
+
+#ifdef __LP64__
+
+ASM_ENTRY(tcb_load)
+ movq 8(%rdi), %rax
+ movq (%rdi), %rsp
+ pushq %rax
+ pushq $CPU_EFL_ONE
+ popfq
+ ret
+ASM_END(tcb_load)
+
+ASM_ENTRY(tcb_context_switch)
+ pushfq
+ pushq %rbx
+ pushq %rbp
+ pushq %r12
+ pushq %r13
+ pushq %r14
+ pushq %r15
+ movq %rsp, (%rdi)
+ movq $1f, 8(%rdi)
+ movq (%rsi), %rsp
+ movq 8(%rsi), %rax
+ jmp *%rax
+
+1:
+ popq %r15
+ popq %r14
+ popq %r13
+ popq %r12
+ popq %rbp
+ popq %rbx
+ popfq
+ ret
+ASM_END(tcb_context_switch)
+
+#else /* __LP64__ */
+
+ASM_ENTRY(tcb_load)
+ movl 4(%esp), %eax
+ movl 4(%eax), %ecx
+ movl (%eax), %esp
+ pushl %ecx
+ pushl $CPU_EFL_ONE
+ popfl
+ ret
+ASM_END(tcb_load)
+
+ASM_ENTRY(tcb_context_switch)
+ movl 4(%esp), %eax
+ movl 8(%esp), %ecx
+ pushfl
+ pushl %ebx
+ pushl %ebp
+ pushl %edi
+ pushl %esi
+ movl %esp, (%eax)
+ movl $1f, 4(%eax)
+ movl (%ecx), %esp
+ movl 4(%ecx), %edx
+ jmp *%edx
+
+1:
+ popl %esi
+ popl %edi
+ popl %ebp
+ popl %ebx
+ popfl
+ ret
+ASM_END(tcb_context_switch)
+
+#endif /* __LP64__ */