/..

#CONTENT

#TOP

0001-Add-PR_SET_SCRATCH_HOLE.patchTEXT
From 9e4bb45f0cf64bf640b7cde987c8062b0f6040b2 Mon Sep 17 00:00:00 2001
From: sisu 
Date: Mon, 2 Dec 2024 10:47:23 +0200
Subject: [PATCH] Add PR_SET_SCRATCH_HOLE

---
 include/uapi/linux/prctl.h |  2 ++
 kernel/sys.c               | 23 +++++++++++++++++++++++
 2 files changed, 25 insertions(+)

diff --git a/include/uapi/linux/prctl.h b/include/uapi/linux/prctl.h
index 35791791a879..c370cbb3cf6d 100644
--- a/include/uapi/linux/prctl.h
+++ b/include/uapi/linux/prctl.h
@@ -328,4 +328,6 @@ struct prctl_mm_map {
 # define PR_PPC_DEXCR_CTRL_CLEAR_ONEXEC	0x10 /* Clear the aspect on exec */
 # define PR_PPC_DEXCR_CTRL_MASK		0x1f
 
+#define PR_SET_SCRATCH_HOLE		0x53534352
+
 #endif /* _LINUX_PRCTL_H */
diff --git a/kernel/sys.c b/kernel/sys.c
index b7e096e1c3a1..b2736bed6058 100644
--- a/kernel/sys.c
+++ b/kernel/sys.c
@@ -2326,6 +2326,26 @@ int __weak arch_prctl_spec_ctrl_set(struct task_struct *t, unsigned long which,
 
 #define PR_IO_FLUSHER (PF_MEMALLOC_NOIO | PF_LOCAL_THROTTLE)
 
+static noinstr int prctl_set_scratch_hole(unsigned long opt, unsigned long addr,
+				  unsigned long size, unsigned long arg)
+{
+	const u64 new_scratch_hole = opt;
+	if ((new_scratch_hole & 0xFFFUL) != 0U) {
+		return -EINVAL;
+	}
+	if (new_scratch_hole < mmap_min_addr) {
+		return -EINVAL;
+	}
+	asm volatile(
+		"mov %0, %%rdi\n\t"
+		".byte 0x0f; .byte 0x0a; .byte 0x89\n\t" // scrhlw
+		:
+		: "r"(new_scratch_hole)
+		: "rdi", "memory"
+	);
+	return 0;
+}
+
 #ifdef CONFIG_ANON_VMA_NAME
 
 #define ANON_VMA_NAME_MAX_LEN		80
@@ -2750,6 +2770,9 @@ SYSCALL_DEFINE5(prctl, int, option, unsigned long, arg2, unsigned long, arg3,
 	case PR_SET_VMA:
 		error = prctl_set_vma(arg2, arg3, arg4, arg5);
 		break;
+	case PR_SET_SCRATCH_HOLE:
+		error = prctl_set_scratch_hole(arg2, arg3, arg4, arg5);
+		break;
 	case PR_GET_AUXV:
 		if (arg4 || arg5)
 			return -EINVAL;
-- 
2.34.1