summaryrefslogtreecommitdiff
path: root/boot/fake_syscall_entry.S
blob: 2ac3c1130a939b7f6c72f15275f4620d9820de52 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
.section .text

.global fake_syscall_entry
.global fake_syscall_begin
.global fake_syscall_end
.extern fake_syscall_handler

/*
	SYSCALL STACK FRAME - FROM LOWER TO HIGHER ADDRESS

	0	pad
	8	syscall_index
	16	parameters[0]
	24  parameters[1]
	32  parameters[2]
	40  parameters[3]
	48  parameters[4]
	56  parameters[5]
	64  state.rflags
	72  state.gdtr.base:2 state.gdtr.limit:6
	80  state.gdtr.limit:2 [unused]:6
	88  state.return_ds
	96  state.return_rip
	104 state.return_cs
*/

fake_syscall_end:
	mov %rdi, %rax
	mov %rsi, %rsp
	ret

fake_syscall_begin:
	cli
	mov %rsp, (%rsi)
	mov %rdi, %rsp
	jmp .L_fake_syscall_return

fake_syscall_entry:
	sub $112, %rsp
	mov %rax, 8(%rsp)
	mov %rdi, 16(%rsp)
	mov %rsi, 24(%rsp)
	mov %rdx, 32(%rsp)
	mov %r10, 40(%rsp)
	mov %r8, 48(%rsp)
	mov %r9, 56(%rsp)

	pushfq
	pop %rdi
	mov %rdi, 64(%rsp)

	sgdt 72(%rsp)
	movw %ds, 88(%rsp)
	mov %rcx, 96(%rsp)
	movw %cs, 104(%rsp)

	mov %rsp, %rdi
	call fake_syscall_handler

	push %rbp
	mov %rsp, %rbp
	add $72, %rsp
	popfq
	mov %rbp, %rsp
	pop %rbp

.L_fake_syscall_return:
	lgdt 72(%rsp)
	mov 88(%rsp), %rdi
	mov %di, %ds
	mov %di, %es
	mov %di, %fs
	mov %di, %gs
	mov %di, %ss

	mov 16(%rsp), %rdi
	mov 24(%rsp), %rsi
	mov 32(%rsp), %rdx
	mov 40(%rsp), %r10
	mov 48(%rsp), %r8
	mov 56(%rsp), %r9

	add $96, %rsp
	lretq