From nobody Fri May  2 23:18:30 2025
Received: from mail-wm1-f73.google.com (mail-wm1-f73.google.com
 [209.85.128.73])
	(using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits))
	(No client certificate requested)
	by smtp.subspace.kernel.org (Postfix) with ESMTPS id F19C9204C06
	for <linux-kernel@vger.kernel.org>; Tue,  1 Apr 2025 13:34:40 +0000 (UTC)
Authentication-Results: smtp.subspace.kernel.org;
 arc=none smtp.client-ip=209.85.128.73
ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116;
	t=1743514483; cv=none;
 b=tPD4dvzFLecGZ2mOr/Ywavm6nxwCANpGGllqev3Nm62jhfCFhimE1pe0xrOHhgfdY/91sMAui44czOHFQf68tqwV7tQ/RjZU5Pn6xZKgrUCOjkSO+gPRVbgParqvW4/sEWv3RHw/WTrDPwJKVfF3krtrGEHZFl20cVrFdyxulp4=
ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org;
	s=arc-20240116; t=1743514483; c=relaxed/simple;
	bh=13dN6LyMDIRJPZtbLc4Qnlwfujaf8mnCxnGVXar+9i0=;
	h=Date:In-Reply-To:Mime-Version:References:Message-ID:Subject:From:
	 To:Cc:Content-Type;
 b=pazcEQkQJYUhlPAOz3fwPg49FrPTTAfpzltGZE62FI2LGEEx0HdTG8RcejraeT/WKz1xw/EYqA+cjIX1GnjGyIRcI9kAzl0mlwCPIqO8PGNHjssQokUDMyYzvUd6fukDRA4gXHorogudobW7YKPwkLQGJDES6n0HL2K3qMAAQag=
ARC-Authentication-Results: i=1; smtp.subspace.kernel.org;
 dmarc=pass (p=reject dis=none) header.from=google.com;
 spf=pass smtp.mailfrom=flex--ardb.bounces.google.com;
 dkim=pass (2048-bit key) header.d=google.com header.i=@google.com
 header.b=QwueR8CX; arc=none smtp.client-ip=209.85.128.73
Authentication-Results: smtp.subspace.kernel.org;
 dmarc=pass (p=reject dis=none) header.from=google.com
Authentication-Results: smtp.subspace.kernel.org;
 spf=pass smtp.mailfrom=flex--ardb.bounces.google.com
Authentication-Results: smtp.subspace.kernel.org;
	dkim=pass (2048-bit key) header.d=google.com header.i=@google.com
 header.b="QwueR8CX"
Received: by mail-wm1-f73.google.com with SMTP id
 5b1f17b1804b1-43ceb011ea5so39710685e9.2
        for <linux-kernel@vger.kernel.org>;
 Tue, 01 Apr 2025 06:34:40 -0700 (PDT)
DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
        d=google.com; s=20230601; t=1743514479; x=1744119279;
 darn=vger.kernel.org;
        h=cc:to:from:subject:message-id:references:mime-version:in-reply-to
         :date:from:to:cc:subject:date:message-id:reply-to;
        bh=iwpNwL234IC9yWIvSwlZhIgKkylOGfUY/NpW29/ZOa0=;
        b=QwueR8CXE1SHDXlMcssYhXj9RaibADn4mGnqJICY/KwI20FhSua7niARSlPKhVvhZp
         zAUMeZC49YZ/KUhutUZDXFdMnk0Ekl3uKt1wsMctwtl/LUYQwD//quAS4M8JhFBU9Oqu
         /yY+yoEu0T41n0gqQs/ZA+OFvUV7PS2REsLmpAmB6MO4AUSiljQ6raRsH2fhbakaY+Vz
         45uehrYRKMmAWFBQUjtFviYl2AXZwsVwQVoe0bfCjiZnhhY6riwnd0BV6iamCN1meiPC
         vAT98+qM6SkvENKDLrepy23uT40hksxvVdsj60/HCGNIG+FKLGXkNWcVduZnIOJ90LUJ
         f2sA==
X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
        d=1e100.net; s=20230601; t=1743514479; x=1744119279;
        h=cc:to:from:subject:message-id:references:mime-version:in-reply-to
         :date:x-gm-message-state:from:to:cc:subject:date:message-id:reply-to;
        bh=iwpNwL234IC9yWIvSwlZhIgKkylOGfUY/NpW29/ZOa0=;
        b=u28vQaBIYy0Ta4IzxY9nLqHZiOfhZiAdLqgqBqgXET2/z7LoaWgnJdJS1gKW3aadev
         783/9ChXQKpbovn7IK3GnahNqZqGtVY4szcAx6D+Z5kuPICITYZTuBv+khT6h81w4KOA
         3eV+nNkc4Jt1fwYJ0tzOQZu6lpqatiahlOeotTX1O7Lv6Xmh4vZHsm6t+ikmHsd6WhAn
         cwUt4oN1tbhVSslIfWKCbt1H+ggnVVZZDlp9gzfR9yY551nH5YuV3zMABr3xyX/h3jCA
         ARCoutZgpBJtkZiZ+8nm1mnItWh3Nmee/TIBIX+kb6ks0JiDKhx1BJPVH/vl6iMJxVDc
         mLNQ==
X-Gm-Message-State: AOJu0YwdssF5c3oJjkEM5u3NXnYYg6lGCx9DjSOC75shXykwTNjbDyQn
	1WP6vEGN7G00cx4M3VXrD/Mkm4LlQU/K68eDtcKMfsF00sP/VSJdNAVMKYvIULMw7JwLcA==
X-Google-Smtp-Source: 
 AGHT+IG4QK2ZXVU8OaDJZrpd4jbGOh2SrGi1jhRE/dSVG0kTZPTHVEXeqFIKnFD0vg8+XQ7RAPuxGyya
X-Received: from wmbhc8.prod.google.com
 ([2002:a05:600c:8708:b0:43d:8244:7f6d])
 (user=ardb job=prod-delivery.src-stubby-dispatcher) by
 2002:a05:600c:3c8a:b0:43d:45a:8fca
 with SMTP id 5b1f17b1804b1-43db62bf4e4mr119197335e9.30.1743514479363; Tue, 01
 Apr 2025 06:34:39 -0700 (PDT)
Date: Tue,  1 Apr 2025 15:34:21 +0200
In-Reply-To: <20250401133416.1436741-8-ardb+git@google.com>
Precedence: bulk
X-Mailing-List: linux-kernel@vger.kernel.org
List-Id: <linux-kernel.vger.kernel.org>
List-Subscribe: <mailto:linux-kernel+subscribe@vger.kernel.org>
List-Unsubscribe: <mailto:linux-kernel+unsubscribe@vger.kernel.org>
Mime-Version: 1.0
References: <20250401133416.1436741-8-ardb+git@google.com>
X-Developer-Key: i=ardb@kernel.org; a=openpgp;
 fpr=F43D03328115A198C90016883D200E9CA6329909
X-Developer-Signature: v=1; a=openpgp-sha256; l=7788; i=ardb@kernel.org;
 h=from:subject; bh=7CqWOqUn0owfJx93vqlZ0MaFHl2+UzXGIVwFFUz3Lwk=;
 b=owGbwMvMwCFmkMcZplerG8N4Wi2JIf3167hzdUZKs0sL7l6c+eF38RwBCUHBG/u/zop/KD77r
 c38xTwMHaUsDGIcDLJiiiwCs/++23l6olSt8yxZmDmsTCBDGLg4BWAiJxgZ/qnz/Ft1teKvVpBB
 YjCn2DvGlkkRuyR2btO1Nw99bLdoyQ6Gf1oK/bUCaofNbidkMIkt6b2Wtmy5vc02t19T3QVfyxy
 +wgEA
X-Mailer: git-send-email 2.49.0.472.ge94155a9ec-goog
Message-ID: <20250401133416.1436741-12-ardb+git@google.com>
Subject: [RFC PATCH 4/6] x86/boot: Move early GDT/IDT setup code into startup/
From: Ard Biesheuvel <ardb+git@google.com>
To: linux-efi@vger.kernel.org
Cc: linux-kernel@vger.kernel.org, x86@kernel.org,
	Ard Biesheuvel <ardb@kernel.org>, Tom Lendacky <thomas.lendacky@amd.com>,
	Dionna Amalie Glaze <dionnaglaze@google.com>,
 Kevin Loughlin <kevinloughlin@google.com>
Content-Transfer-Encoding: quoted-printable
Content-Type: text/plain; charset="utf-8"

From: Ard Biesheuvel <ardb@kernel.org>

Move the early GDT/IDT setup code that runs long before the kernel
virtual mapping is up into arch/x86/boot/startup/, and build it in a way
that ensures that the code tolerates being called from the 1:1 mapping
of memory.

This allows the RIP_REL_REF() macro uses to be dropped, and removes the
need for emitting the code into the special .head.text section.

Also tweak the sed symbol matching pattern in the decompressor to match
on lower case 't' or 'b', as these will be emitted by Clang for symbols
with hidden linkage.

Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
---
 arch/x86/boot/compressed/Makefile |  2 +-
 arch/x86/boot/startup/Makefile    | 15 ++++
 arch/x86/boot/startup/gdt_idt.c   | 82 ++++++++++++++++++++
 arch/x86/kernel/head64.c          | 74 ------------------
 4 files changed, 98 insertions(+), 75 deletions(-)

diff --git a/arch/x86/boot/compressed/Makefile b/arch/x86/boot/compressed/M=
akefile
index 468e135de88e..48541cf54790 100644
--- a/arch/x86/boot/compressed/Makefile
+++ b/arch/x86/boot/compressed/Makefile
@@ -74,7 +74,7 @@ LDFLAGS_vmlinux +=3D -T
 hostprogs	:=3D mkpiggy
 HOST_EXTRACFLAGS +=3D -I$(srctree)/tools/include
=20
-sed-voffset :=3D -e 's/^\([0-9a-fA-F]*\) [ABCDGRSTVW] \(_text\|__start_rod=
ata\|__bss_start\|_end\)$$/\#define VO_\2 _AC(0x\1,UL)/p'
+sed-voffset :=3D -e 's/^\([0-9a-fA-F]*\) [ABbCDGRSTtVW] \(_text\|__start_r=
odata\|__bss_start\|_end\)$$/\#define VO_\2 _AC(0x\1,UL)/p'
=20
 quiet_cmd_voffset =3D VOFFSET $@
       cmd_voffset =3D $(NM) $< | sed -n $(sed-voffset) > $@
diff --git a/arch/x86/boot/startup/Makefile b/arch/x86/boot/startup/Makefile
index 73946a3f6b3b..34b324cbd5a4 100644
--- a/arch/x86/boot/startup/Makefile
+++ b/arch/x86/boot/startup/Makefile
@@ -1,6 +1,21 @@
 # SPDX-License-Identifier: GPL-2.0
=20
 KBUILD_AFLAGS		+=3D -D__DISABLE_EXPORTS
+KBUILD_CFLAGS		+=3D -D__DISABLE_EXPORTS -mcmodel=3Dsmall -fPIC \
+			   -Os -DDISABLE_BRANCH_PROFILING \
+			   $(DISABLE_STACKLEAK_PLUGIN) \
+			   -fno-stack-protector -D__NO_FORTIFY \
+			   -include $(srctree)/include/linux/hidden.h
+
+# disable ftrace hooks
+KBUILD_CFLAGS	:=3D $(subst $(CC_FLAGS_FTRACE),,$(KBUILD_CFLAGS))
+KASAN_SANITIZE	:=3D n
+KCSAN_SANITIZE	:=3D n
+KMSAN_SANITIZE	:=3D n
+UBSAN_SANITIZE	:=3D n
+KCOV_INSTRUMENT	:=3D n
+
+obj-$(CONFIG_X86_64)		+=3D gdt_idt.o
=20
 lib-$(CONFIG_X86_64)		+=3D la57toggle.o
 lib-$(CONFIG_EFI_MIXED)		+=3D efi-mixed.o
diff --git a/arch/x86/boot/startup/gdt_idt.c b/arch/x86/boot/startup/gdt_id=
t.c
new file mode 100644
index 000000000000..b382d5db2586
--- /dev/null
+++ b/arch/x86/boot/startup/gdt_idt.c
@@ -0,0 +1,82 @@
+// SPDX-License-Identifier: GPL-2.0
+
+#include <linux/linkage.h>
+#include <linux/types.h>
+
+#include <asm/desc.h>
+#include <asm/setup.h>
+#include <asm/sev.h>
+#include <asm/trapnr.h>
+
+/*
+ * Data structures and code used for IDT setup in head_64.S. The bringup-I=
DT is
+ * used until the idt_table takes over. On the boot CPU this happens in
+ * x86_64_start_kernel(), on secondary CPUs in start_secondary(). In both =
cases
+ * this happens in the functions called from head_64.S.
+ *
+ * The idt_table can't be used that early because all the code modifying i=
t is
+ * in idt.c and can be instrumented by tracing or KASAN, which both don't =
work
+ * during early CPU bringup. Also the idt_table has the runtime vectors
+ * configured which require certain CPU state to be setup already (like TS=
S),
+ * which also hasn't happened yet in early CPU bringup.
+ */
+static gate_desc bringup_idt_table[NUM_EXCEPTION_VECTORS] __page_aligned_d=
ata;
+
+/* This may run while still in the direct mapping */
+static void startup_64_load_idt(void *vc_handler)
+{
+	struct desc_ptr desc =3D {
+		.address =3D (unsigned long)bringup_idt_table,
+		.size    =3D sizeof(bringup_idt_table) - 1,
+	};
+	struct idt_data data;
+	gate_desc idt_desc;
+
+	/* @vc_handler is set only for a VMM Communication Exception */
+	if (vc_handler) {
+		init_idt_data(&data, X86_TRAP_VC, vc_handler);
+		idt_init_desc(&idt_desc, &data);
+		native_write_idt_entry((gate_desc *)desc.address, X86_TRAP_VC, &idt_desc=
);
+	}
+
+	native_load_idt(&desc);
+}
+
+/* This is used when running on kernel addresses */
+void early_setup_idt(void)
+{
+	void *handler =3D NULL;
+
+	if (IS_ENABLED(CONFIG_AMD_MEM_ENCRYPT)) {
+		setup_ghcb();
+		handler =3D vc_boot_ghcb;
+	}
+
+	startup_64_load_idt(handler);
+}
+
+/*
+ * Setup boot CPU state needed before kernel switches to virtual addresses.
+ */
+void __init startup_64_setup_gdt_idt(void)
+{
+	void *handler =3D NULL;
+
+	struct desc_ptr startup_gdt_descr =3D {
+		.address =3D (__force unsigned long)gdt_page.gdt,
+		.size    =3D GDT_SIZE - 1,
+	};
+
+	/* Load GDT */
+	native_load_gdt(&startup_gdt_descr);
+
+	/* New GDT is live - reload data segment registers */
+	asm volatile("movl %%eax, %%ds\n"
+		     "movl %%eax, %%ss\n"
+		     "movl %%eax, %%es\n" : : "a"(__KERNEL_DS) : "memory");
+
+	if (IS_ENABLED(CONFIG_AMD_MEM_ENCRYPT))
+		handler =3D vc_no_ghcb;
+
+	startup_64_load_idt(handler);
+}
diff --git a/arch/x86/kernel/head64.c b/arch/x86/kernel/head64.c
index fa9b6339975f..5b993b545c7e 100644
--- a/arch/x86/kernel/head64.c
+++ b/arch/x86/kernel/head64.c
@@ -512,77 +512,3 @@ void __init __noreturn x86_64_start_reservations(char =
*real_mode_data)
=20
 	start_kernel();
 }
-
-/*
- * Data structures and code used for IDT setup in head_64.S. The bringup-I=
DT is
- * used until the idt_table takes over. On the boot CPU this happens in
- * x86_64_start_kernel(), on secondary CPUs in start_secondary(). In both =
cases
- * this happens in the functions called from head_64.S.
- *
- * The idt_table can't be used that early because all the code modifying i=
t is
- * in idt.c and can be instrumented by tracing or KASAN, which both don't =
work
- * during early CPU bringup. Also the idt_table has the runtime vectors
- * configured which require certain CPU state to be setup already (like TS=
S),
- * which also hasn't happened yet in early CPU bringup.
- */
-static gate_desc bringup_idt_table[NUM_EXCEPTION_VECTORS] __page_aligned_d=
ata;
-
-/* This may run while still in the direct mapping */
-static void __head startup_64_load_idt(void *vc_handler)
-{
-	struct desc_ptr desc =3D {
-		.address =3D (unsigned long)&RIP_REL_REF(bringup_idt_table),
-		.size    =3D sizeof(bringup_idt_table) - 1,
-	};
-	struct idt_data data;
-	gate_desc idt_desc;
-
-	/* @vc_handler is set only for a VMM Communication Exception */
-	if (vc_handler) {
-		init_idt_data(&data, X86_TRAP_VC, vc_handler);
-		idt_init_desc(&idt_desc, &data);
-		native_write_idt_entry((gate_desc *)desc.address, X86_TRAP_VC, &idt_desc=
);
-	}
-
-	native_load_idt(&desc);
-}
-
-/* This is used when running on kernel addresses */
-void early_setup_idt(void)
-{
-	void *handler =3D NULL;
-
-	if (IS_ENABLED(CONFIG_AMD_MEM_ENCRYPT)) {
-		setup_ghcb();
-		handler =3D vc_boot_ghcb;
-	}
-
-	startup_64_load_idt(handler);
-}
-
-/*
- * Setup boot CPU state needed before kernel switches to virtual addresses.
- */
-void __head startup_64_setup_gdt_idt(void)
-{
-	struct desc_struct *gdt =3D (void *)(__force unsigned long)gdt_page.gdt;
-	void *handler =3D NULL;
-
-	struct desc_ptr startup_gdt_descr =3D {
-		.address =3D (unsigned long)&RIP_REL_REF(*gdt),
-		.size    =3D GDT_SIZE - 1,
-	};
-
-	/* Load GDT */
-	native_load_gdt(&startup_gdt_descr);
-
-	/* New GDT is live - reload data segment registers */
-	asm volatile("movl %%eax, %%ds\n"
-		     "movl %%eax, %%ss\n"
-		     "movl %%eax, %%es\n" : : "a"(__KERNEL_DS) : "memory");
-
-	if (IS_ENABLED(CONFIG_AMD_MEM_ENCRYPT))
-		handler =3D &RIP_REL_REF(vc_no_ghcb);
-
-	startup_64_load_idt(handler);
-}
--=20
2.49.0.472.ge94155a9ec-goog