Xen Test Framework
main.c
Go to the documentation of this file.
1
18#include <xtf.h>
19
20const char test_title[] = "Test Long Mode #TS";
21
22#ifdef __i386__
23# define COND(_32, _64) _32
24#else
25# define COND(_32, _64) _64
26#endif
27
28static bool check_ts(struct cpu_regs *regs, const struct extable_entry *ex)
29{
30 exinfo_t got = EXINFO(regs->entry_vector, regs->error_code);
31 exinfo_t exp = EXINFO_SYM(TS, SEL_EC_SYM(TSS_SEL, GDT));
32
33 if ( got == exp )
34 {
35 printk(" Got %pe as expected\n", _p(got));
36 regs->ip = ex->fixup;
37 return true;
38 }
39
40 return false;
41}
42
43static void __user_text user(void)
44{
45 asm volatile ("1: int $"STR(X86_VEC_AVAIL)";"
46 "2:"
47 _ASM_EXTABLE_HANDLER(1b, 2b, %P[check])
48 :
49 : [check] "p" (check_ts)
50 : "memory");
51}
52
53void test_main(void)
54{
55 /*
56 * Edit the TSS descriptor in place. Reset Busy to Available, and reduce
57 * limit to exclude the Ring1 stack.
58 */
59 gdt[GDTE_TSS].type = 0x9;
60 gdt[GDTE_TSS].limit0 = offsetof(env_tss, COND(esp1, rsp1)) - 1;
61
62 /* Reload %tr */
63 ltr(TSS_SEL);
64
65#ifdef __i386__
66 tss.ss1 = __KERN_CS;
67#endif
68
69 /* Ring1 code segment. */
70 gdt[GDTE_AVAIL0] = GDTE_SYM(0, 0xfffff, COMMON, DPL1, CODE, COND(D, L));
71
72 /*
73 * DPL3 RPL1 gate to allow userspace to invoke Ring 1. It will fault as
74 * %tr->{e,r}sp1 can't be accessed.
75 */
76 pack_intr_gate(&idt[X86_VEC_AVAIL], (GDTE_AVAIL0 * 8) | 1, 0, 3, 0);
77
79
81}
82
83/*
84 * Local variables:
85 * mode: C
86 * c-file-style: "BSD"
87 * c-basic-offset: 4
88 * tab-width: 4
89 * indent-tabs-mode: nil
90 * End:
91 */
static void ltr(unsigned int sel)
Definition: lib.h:342
#define __user_text
Definition: compiler.h:33
void printk(const char *fmt,...)
Definition: console.c:134
void test_main(void)
To be implemented by each test, as its entry point.
Definition: main.c:110
const char test_title[]
The title of the test.
Definition: main.c:24
user_desc gdt[NR_GDT_ENTRIES]
#define EXINFO(vec, ec)
Definition: exinfo.h:26
#define EXINFO_SYM(exc, ec)
Definition: exinfo.h:29
unsigned int exinfo_t
Packed exception and error code information.
Definition: exinfo.h:19
env_tss tss
Definition: traps.c:35
#define X86_VEC_AVAIL
Available for test use.
Definition: idt.h:20
#define _ASM_EXTABLE_HANDLER(fault, fixup, handler)
Create an exception table entry with custom handler.
Definition: extable.h:38
static void exec_user_void(void(*fn)(void))
Definition: lib.h:70
static void user(void)
Definition: main.c:43
static bool check_ts(struct cpu_regs *regs, const struct extable_entry *ex)
Definition: main.c:28
#define COND(_32, _64)
Definition: main.c:25
#define STR(x)
Stringise an expression, expanding preprocessor tokens.
Definition: macro_magic.h:17
#define _p(v)
Express an abitrary integer v as void *.
Definition: numbers.h:48
void xtf_success(const char *fmt,...)
Report test success.
Definition: report.c:38
#define GDTE_AVAIL0
Definition: segment.h:37
#define GDTE_TSS
Definition: segment.h:34
#define NULL
Definition: stddef.h:12
#define offsetof(t, m)
Definition: stddef.h:14
Exception table entry.
Definition: extable.h:65
unsigned long fixup
Fixup address.
Definition: extable.h:67
#define SEL_EC_SYM(sel,...)
Create a selector based error code using X86_EC_ mnemonics.
#define GDTE_SYM(base, limit,...)
As INIT_GDTE_SYM(), but creates a user_desc object.
void check(const char *func, exinfo_t got, exinfo_t exp)
Compare an expectation against what really happenend, printing human-readable information in case of ...
Definition: util.c:37
static void pack_intr_gate(env_gate *g, unsigned int sel, unsigned long offset, unsigned int dpl, unsigned int other)
Definition: x86-gate.h:117