NIX mode.
[akaros.git] / kern / arch / x86 / trap32.h
1 /* Copyright (c) 2009-13 The Regents of the University of California
2  * Barret Rhoden <brho@cs.berkeley.edu>
3  * See LICENSE for details.
4  *
5  * x86 trap.h bit-specific functions.  This is included by trap.h, do not
6  * include it directly.  Any function beginning with x86_ is internal to x86,
7  * and not to be called by the main kernel.  Other functions are part of the
8  * kernel-arch interface. */
9
10 #ifndef ROS_KERN_ARCH_TRAP32_H
11 #define ROS_KERN_ARCH_TRAP32_H
12
13 #ifndef ROS_KERN_ARCH_TRAP_H
14 #error "Do not include arch/trap32.h directly."
15 #endif
16
17 static inline bool in_kernel(struct hw_trapframe *hw_tf)
18 {
19         return (hw_tf->tf_cs & ~3) == GD_KT;
20 }
21
22 static inline uintptr_t get_hwtf_pc(struct hw_trapframe *hw_tf)
23 {
24         return hw_tf->tf_eip;
25 }
26
27 static inline uintptr_t get_hwtf_fp(struct hw_trapframe *hw_tf)
28 {
29         return hw_tf->tf_regs.reg_ebp;
30 }
31
32 static inline uintptr_t x86_get_ip_hw(struct hw_trapframe *hw_tf)
33 {
34         return hw_tf->tf_eip;
35 }
36
37 static inline void x86_advance_ip(struct hw_trapframe *hw_tf, size_t bytes)
38 {
39         hw_tf->tf_eip += bytes;
40 }
41
42 static inline void x86_fake_rdtscp(struct hw_trapframe *hw_tf)
43 {
44         uint64_t tsc_time = read_tsc();
45         hw_tf->tf_eip += 3;
46         hw_tf->tf_regs.reg_eax = tsc_time & 0xffffffff;
47         hw_tf->tf_regs.reg_edx = tsc_time >> 32;
48         hw_tf->tf_regs.reg_ecx = core_id();
49 }
50
51 static inline void x86_sysenter_init(uintptr_t stacktop)
52 {
53         write_msr(MSR_IA32_SYSENTER_CS, GD_KT);
54         write_msr(MSR_IA32_SYSENTER_ESP, stacktop);
55         write_msr(MSR_IA32_SYSENTER_EIP, (uintptr_t) &sysenter_handler);
56 }
57
58 static inline void x86_set_sysenter_stacktop(uintptr_t stacktop)
59 {
60         write_msr(MSR_IA32_SYSENTER_ESP, stacktop);
61 }
62
63 static inline long x86_get_sysenter_arg0(struct hw_trapframe *hw_tf)
64 {
65         return hw_tf->tf_regs.reg_eax;
66 }
67
68 static inline long x86_get_sysenter_arg1(struct hw_trapframe *hw_tf)
69 {
70         return hw_tf->tf_regs.reg_esi;
71 }
72
73 static inline long x86_get_systrap_arg0(struct hw_trapframe *hw_tf)
74 {
75         return hw_tf->tf_regs.reg_eax;
76 }
77
78 static inline long x86_get_systrap_arg1(struct hw_trapframe *hw_tf)
79 {
80         return hw_tf->tf_regs.reg_edx;
81 }
82
83 static inline uintptr_t x86_get_stacktop_tss(struct taskstate *tss)
84 {
85         return tss->ts_esp0;
86 }
87
88 static inline void x86_set_stacktop_tss(struct taskstate *tss, uintptr_t top)
89 {
90         tss->ts_esp0 = top;
91         tss->ts_ss0 = GD_KD;
92 }
93
94 #endif /* ROS_KERN_ARCH_TRAP32_H */