31 #ifndef CPU_X86_MM_MULTI_SEGMENT_H_
32 #define CPU_X86_MM_MULTI_SEGMENT_H_
37 #include "ldt-layout.h"
41 #define __seg_fs __attribute__((address_space(257)))
43 #define __seg_gs __attribute__((address_space(256)))
47 #define ATTR_MMIO_ADDR_SPACE __seg_fs
48 #define ATTR_KERN_ADDR_SPACE __seg_fs
50 #define ATTR_KERN_ADDR_SPACE
53 #define ATTR_META_ADDR_SPACE __seg_gs
56 void prot_domains_reg_multi_seg(
volatile struct dom_kern_data ATTR_KERN_ADDR_SPACE *dkd,
57 uintptr_t mmio,
size_t mmio_sz,
58 uintptr_t meta,
size_t meta_sz);
59 void multi_segment_launch_kernel(
void);
61 #define MULTI_SEGMENT_ENTER_ISR(exc) \
62 "mov $" EXP_STRINGIFY(GDT_SEL_DATA) ", %%eax\n\t" \
64 "mov %%eax, %%ds\n\t" \
65 "mov %%eax, %%es\n\t" \
67 "mov $" EXP_STRINGIFY(LDT_SEL_KERN) ", %%eax\n\t" \
68 "mov %%eax, %%" SEG_KERN "s\n\t" \
73 "mov %%" SEG_MMIO "s, %%ebp\n\t" \
74 "mov $" EXP_STRINGIFY(GDT_SEL_DATA_KERN_EXC) ", %%eax\n\t" \
75 "mov %%eax, %%" SEG_KERN "s\n\t" \
77 #define MULTI_SEGMENT_LEAVE_ISR(exc) \
79 "mov %%ebp, %%" SEG_MMIO "s\n\t" \
86 #define PROT_DOMAINS_MMIO(dcd) 0
91 #define PROT_DOMAINS_META(dcd) 0
97 #define _SEG_READL(seg, dst, src) \
98 __asm__ __volatile__ ( \
99 "movl %%" seg "s:%[src_], %[dst_]" : [dst_]"=r"(dst) : [src_]"m"(src))
101 #define _SEG_READW(seg, dst, src) \
102 __asm__ __volatile__ ( \
103 "movw %%" seg "s:%[src_], %[dst_]" : [dst_]"=r"(dst) : [src_]"m"(src))
105 #define _SEG_READB(seg, dst, src) \
106 __asm__ __volatile__ ( \
107 "movb %%" seg "s:%[src_], %[dst_]" : [dst_]"=q"(dst) : [src_]"m"(src))
109 #define _SEG_WRITEL(seg, dst, src) \
110 __asm__ __volatile__ ( \
111 "movl %[src_], %%" seg "s:%[dst_]" \
112 : [dst_]"=m"(dst) : [src_]"r"((uint32_t)(src)))
114 #define _SEG_WRITEW(seg, dst, src) \
115 __asm__ __volatile__ ( \
116 "movw %[src_], %%" seg "s:%[dst_]" \
117 : [dst_]"=m"(dst) : [src_]"r"((uint16_t)(src)))
119 #define _SEG_WRITEB(seg, dst, src) \
120 __asm__ __volatile__ ( \
121 "movb %[src_], %%" seg "s:%[dst_]" \
122 : [dst_]"=m"(dst) : [src_]"q"((uint8_t)(src)))
125 #define MMIO_READL(dst, src) _SEG_READL(SEG_MMIO, dst, src)
126 #define MMIO_READW(dst, src) _SEG_READW(SEG_MMIO, dst, src)
127 #define MMIO_READB(dst, src) _SEG_READB(SEG_MMIO, dst, src)
128 #define MMIO_WRITEL(dst, src) _SEG_WRITEL(SEG_MMIO, dst, src)
129 #define MMIO_WRITEW(dst, src) _SEG_WRITEW(SEG_MMIO, dst, src)
130 #define MMIO_WRITEB(dst, src) _SEG_WRITEB(SEG_MMIO, dst, src)
132 #define KERN_READL(dst, src) _SEG_READL(SEG_KERN, dst, src)
133 #define KERN_READW(dst, src) _SEG_READW(SEG_KERN, dst, src)
134 #define KERN_READB(dst, src) _SEG_READB(SEG_KERN, dst, src)
135 #define KERN_WRITEL(dst, src) _SEG_WRITEL(SEG_KERN, dst, src)
136 #define KERN_WRITEW(dst, src) _SEG_WRITEW(SEG_KERN, dst, src)
137 #define KERN_WRITEB(dst, src) _SEG_WRITEB(SEG_KERN, dst, src)
141 #define META_READL(dst, src) _SEG_READL(SEG_META, dst, src)
142 #define META_READW(dst, src) _SEG_READW(SEG_META, dst, src)
143 #define META_READB(dst, src) _SEG_READB(SEG_META, dst, src)
144 #define META_WRITEL(dst, src) _SEG_WRITEL(SEG_META, dst, src)
145 #define META_WRITEW(dst, src) _SEG_WRITEW(SEG_META, dst, src)
146 #define META_WRITEB(dst, src) _SEG_WRITEB(SEG_META, dst, src)
149 #define MEMCPY_FROM_META(dst, src, sz) \
151 uintptr_t __dst = (uintptr_t)(dst); \
152 uintptr_t __src = (uintptr_t)(src); \
153 size_t __sz = (size_t)(sz); \
154 __asm__ __volatile__ ( \
155 "rep movsb %%" SEG_META "s:(%%esi), %%es:(%%edi)\n\t" \
156 : "+D"(__dst), "+S"(__src), "+c"(__sz)); \
159 #define MEMCPY_TO_META(dst, src, sz) \
161 uintptr_t __dst = (uintptr_t)(dst); \
162 uintptr_t __src = (uintptr_t)(src); \
163 size_t __sz = (size_t)(sz); \
164 __asm__ __volatile__ ( \
166 "push %%" SEG_META "s\n\t" \
170 : "+D"(__dst), "+S"(__src), "+c"(__sz)); \
174 #define KERN_DATA_OFF_TO_PHYS_ADDR(x) \
175 (((uintptr_t)&_sbss_kern_addr) + (uintptr_t)(x))
177 #define DATA_OFF_TO_PHYS_ADDR(x) \
178 (((uintptr_t)&_sdata_addr) + (uintptr_t)(x))
180 #define PHYS_ADDR_TO_KERN_DATA_OFF(x) \
181 (((uintptr_t)(x)) - (uintptr_t)&_sbss_kern_addr)
190 #define PROT_DOMAINS_CHECK_INCOMING_PTR PROT_DOMAINS_CHECK_INCOMING_PTR_EBP
192 void prot_domains_enable_mmio(
void);
193 void prot_domains_disable_mmio(
void);