Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
stenzek
GitHub Repository: stenzek/duckstation
Path: blob/master/src/common/fastjmp.cpp
4214 views
1
// SPDX-FileCopyrightText: 2019-2024 Connor McLaughlin <[email protected]>
2
// SPDX-License-Identifier: CC-BY-NC-ND-4.0
3
4
// Win32 uses Fastjmp.asm, because MSVC doesn't support inline asm.
5
#if !defined(_WIN32) || defined(_M_ARM64)
6
7
#include "fastjmp.h"
8
9
#if defined(__APPLE__)
10
#define PREFIX "_"
11
#else
12
#define PREFIX ""
13
#endif
14
15
// clang-format off
16
17
#if defined(__x86_64__)
18
19
asm("\t.global " PREFIX "fastjmp_set\n"
20
"\t.global " PREFIX "fastjmp_jmp\n"
21
"\t.text\n"
22
"\t" PREFIX "fastjmp_set:" R"(
23
movq 0(%rsp), %rax
24
movq %rsp, %rdx # fixup stack pointer, so it doesn't include the call to fastjmp_set
25
addq $8, %rdx
26
movq %rax, 0(%rdi) # actually rip
27
movq %rbx, 8(%rdi)
28
movq %rdx, 16(%rdi) # actually rsp
29
movq %rbp, 24(%rdi)
30
movq %r12, 32(%rdi)
31
movq %r13, 40(%rdi)
32
movq %r14, 48(%rdi)
33
movq %r15, 56(%rdi)
34
xorl %eax, %eax
35
ret
36
)"
37
"\t" PREFIX "fastjmp_jmp:" R"(
38
movl %esi, %eax
39
movq 0(%rdi), %rdx # actually rip
40
movq 8(%rdi), %rbx
41
movq 16(%rdi), %rsp # actually rsp
42
movq 24(%rdi), %rbp
43
movq 32(%rdi), %r12
44
movq 40(%rdi), %r13
45
movq 48(%rdi), %r14
46
movq 56(%rdi), %r15
47
jmp *%rdx
48
)");
49
50
#elif defined(__aarch64__)
51
52
asm(
53
"\t.global " PREFIX "fastjmp_set\n"
54
"\t.global " PREFIX "fastjmp_jmp\n"
55
"\t.text\n"
56
"\t.align 16\n"
57
"\t" PREFIX "fastjmp_set:" R"(
58
mov x16, sp
59
stp x16, x30, [x0]
60
stp x19, x20, [x0, #16]
61
stp x21, x22, [x0, #32]
62
stp x23, x24, [x0, #48]
63
stp x25, x26, [x0, #64]
64
stp x27, x28, [x0, #80]
65
str x29, [x0, #96]
66
stp d8, d9, [x0, #112]
67
stp d10, d11, [x0, #128]
68
stp d12, d13, [x0, #144]
69
stp d14, d15, [x0, #160]
70
mov w0, wzr
71
br x30
72
)"
73
".align 16\n"
74
"\t" PREFIX "fastjmp_jmp:" R"(
75
ldp x16, x30, [x0]
76
mov sp, x16
77
ldp x19, x20, [x0, #16]
78
ldp x21, x22, [x0, #32]
79
ldp x23, x24, [x0, #48]
80
ldp x25, x26, [x0, #64]
81
ldp x27, x28, [x0, #80]
82
ldr x29, [x0, #96]
83
ldp d8, d9, [x0, #112]
84
ldp d10, d11, [x0, #128]
85
ldp d12, d13, [x0, #144]
86
ldp d14, d15, [x0, #160]
87
mov w0, w1
88
br x30
89
)");
90
91
#elif defined(__arm__)
92
93
asm(
94
"\t.global " PREFIX "fastjmp_set\n"
95
"\t.global " PREFIX "fastjmp_jmp\n"
96
"\t.text\n"
97
"\t" PREFIX "fastjmp_set:" R"(
98
vstmia r0!, {d8-d15}
99
stmia r0!, {r4-r14}
100
fmrx r1, fpscr
101
str r1, [r0]
102
mov r0, #0
103
bx lr
104
)"
105
106
"\t" PREFIX "fastjmp_jmp:" R"(
107
vldmia r0!, {d8-d15}
108
ldmia r0!, {r4-r14}
109
ldr r0, [r0]
110
fmxr fpscr, r0
111
mov r0, r1
112
bx lr
113
)");
114
115
#elif defined(__riscv) && __riscv_xlen == 64
116
117
asm(
118
"\t.global " PREFIX "fastjmp_set\n"
119
"\t.global " PREFIX "fastjmp_jmp\n"
120
"\t.attribute arch, \"rv64gc\"\n"
121
"\t.text\n"
122
"\t.align 16\n"
123
"\t" PREFIX "fastjmp_set:" R"(
124
sd sp, 0(a0)
125
sd s0, 8(a0)
126
sd s1, 16(a0)
127
sd s2, 24(a0)
128
sd s3, 32(a0)
129
sd s4, 40(a0)
130
sd s5, 48(a0)
131
sd s6, 56(a0)
132
sd s7, 64(a0)
133
sd s8, 72(a0)
134
sd s9, 80(a0)
135
sd s10, 88(a0)
136
sd s11, 96(a0)
137
fsd fs0, 104(a0)
138
fsd fs1, 112(a0)
139
fsd fs2, 120(a0)
140
fsd fs3, 128(a0)
141
fsd fs4, 136(a0)
142
fsd fs5, 144(a0)
143
fsd fs6, 152(a0)
144
fsd fs7, 160(a0)
145
fsd fs8, 168(a0)
146
fsd fs9, 176(a0)
147
fsd fs10, 184(a0)
148
fsd fs11, 192(a0)
149
sd ra, 208(a0)
150
li a0, 0
151
jr ra
152
)"
153
".align 16\n"
154
"\t" PREFIX "fastjmp_jmp:" R"(
155
ld ra, 208(a0)
156
fld fs11, 192(a0)
157
fld fs10, 184(a0)
158
fld fs9, 176(a0)
159
fld fs8, 168(a0)
160
fld fs7, 160(a0)
161
fld fs6, 152(a0)
162
fld fs5, 144(a0)
163
fld fs4, 136(a0)
164
fld fs3, 128(a0)
165
fld fs2, 120(a0)
166
fld fs1, 112(a0)
167
fld fs0, 104(a0)
168
ld s11, 96(a0)
169
ld s10, 88(a0)
170
ld s9, 80(a0)
171
ld s8, 72(a0)
172
ld s7, 64(a0)
173
ld s6, 56(a0)
174
ld s5, 48(a0)
175
ld s4, 40(a0)
176
ld s3, 32(a0)
177
ld s2, 24(a0)
178
ld s1, 16(a0)
179
ld s0, 8(a0)
180
ld sp, 0(a0)
181
mv a0, a1
182
jr ra
183
)");
184
185
186
#else
187
188
#error Unknown platform.
189
190
#endif
191
192
// clang-format on
193
194
#endif // __WIN32
195
196