This commit is contained in:
2026-09-20 05:27:41 +02:00
parent 831308b2ad
commit 77f228df11
38 changed files with 465 additions and 115 deletions
+52 -53
View File
@@ -1,6 +1,14 @@
#include <zinnia/compiler.h>
#include <arch/usercopy.h>
void arch_usercopy_allow(bool state) {
if (state) {
asm volatile("stac" ::: "memory");
} else {
asm volatile("clac" ::: "memory");
}
}
extern void x86_64_read_start();
extern void x86_64_read_end();
extern void x86_64_read_fault();
@@ -11,37 +19,34 @@ static const struct usercopy_region read_region = {
.fault_ip = x86_64_read_fault,
};
[[__naked]]
bool arch_usercopy_read(void* dst, const __user void* src, size_t len, struct usercopy_region** region) {
asm volatile(
"stac\n"
// Setup regs for `rep movsb`.
"xchg rcx, rdx\n"
"mov rax, [rip + %0]\n"
"xchg [rdx], rax\n"
" xchg rcx, rdx\n"
" mov rax, [rip + %0]\n"
" xchg [rdx], rax\n"
".global x86_64_read_start\n"
"x86_64_read_start:\n"
"rep movsb\n"
" x86_64_read_start:\n"
" rep movsb\n"
".global x86_64_read_end\n"
"x86_64_read_end:\n"
"xor rax, rax\n"
"xchg [rdx], rax\n"
"mov rax, 1\n"
"clac\n"
"ret\n"
" xor rax, rax\n"
" xchg [rdx], rax\n"
" mov rax, 1\n"
" ret\n"
".global x86_64_read_fault\n"
"x86_64_read_fault:\n"
"xor rax, rax\n"
"xchg [rdx], rax\n"
"clac\n"
"ret\n"
" xor rax, rax\n"
" xchg [rdx], rax\n"
" ret\n"
:
: "i"(&read_region)
: "memory"
);
return false;
}
extern void x86_64_write_start();
@@ -54,37 +59,34 @@ static const struct usercopy_region write_region = {
.fault_ip = x86_64_write_fault,
};
[[__naked]]
bool arch_usercopy_write(__user void* dst, const void* src, size_t len, struct usercopy_region** region) {
asm volatile(
"stac\n"
// Setup regs for `rep movsb`.
"xchg rcx, rdx\n"
"mov rax, [rip + %0]\n"
"mov [rdx], rax\n"
" xchg rcx, rdx\n"
" mov rax, [rip + %0]\n"
" mov [rdx], rax\n"
".global x86_64_write_start\n"
"x86_64_write_start:\n"
"rep movsb\n"
" x86_64_write_start:\n"
" rep movsb\n"
".global x86_64_write_end\n"
"x86_64_write_end:\n"
"xor rax, rax\n"
"xchg [rdx], rax\n"
"mov rax, 1\n"
"clac\n"
"ret\n"
" x86_64_write_end:\n"
" xor rax, rax\n"
" xchg [rdx], rax\n"
" mov rax, 1\n"
" ret\n"
".global x86_64_write_fault\n"
"x86_64_write_fault:\n"
"xor rax, rax\n"
"xchg [rdx], rax\n"
"clac\n"
"ret\n"
" xor rax, rax\n"
" xchg [rdx], rax\n"
" ret\n"
:
: "i"(&write_region)
: "memory"
);
return false;
}
extern void x86_64_strlen_start();
@@ -100,36 +102,33 @@ static const struct usercopy_region strlen_region = {
[[__naked]]
bool arch_usercopy_strlen(const __user char* str, size_t max, size_t* len, struct usercopy_region** region) {
asm volatile(
"stac\n"
"mov rax, [rip + %0]\n"
"xchg [rcx], rax\n"
" mov rax, [rip + %0]\n"
" xchg [rcx], rax\n"
".global x86_64_strlen_start\n"
"x86_64_strlen_start:\n"
"xor r8, r8\n"
" x86_64_strlen_start:\n"
" xor r8, r8\n"
".Lloop:\n"
"cmp byte ptr [rdi + r8], 0\n"
"je .Lleave\n"
"inc r8\n"
"cmp rsi, r8\n"
"jne .Lloop\n"
" cmp byte ptr [rdi + r8], 0\n"
" je .Lleave\n"
" inc r8\n"
" cmp rsi, r8\n"
" jne .Lloop\n"
".Lleave:\n"
"mov [rdx], r8\n"
" mov [rdx], r8\n"
".global x86_64_strlen_end\n"
"x86_64_strlen_end:\n"
"xor rax, rax\n"
"xchg [rcx], rax\n"
"mov rax, 1\n"
"clac\n"
"ret\n"
" xor rax, rax\n"
" xchg [rcx], rax\n"
" mov rax, 1\n"
" ret\n"
".global x86_64_strlen_fault\n"
"x86_64_strlen_fault:\n"
"xor rax, rax\n"
"xchg [rcx], rax\n"
"clac\n"
"ret\n"
" xor rax, rax\n"
" xchg [rcx], rax\n"
" ret\n"
:
: "i"(&strlen_region)
: "memory"