public inbox for linux-coco@lists.linux.dev
 help / color / mirror / Atom feed
From: Chao Gao <chao.gao@intel.com>
To: linux-coco@lists.linux.dev, linux-kernel@vger.kernel.org,
	kvm@vger.kernel.org, x86@kernel.org
Cc: reinette.chatre@intel.com, ira.weiny@intel.com,
	kai.huang@intel.com, dan.j.williams@intel.com,
	yilun.xu@linux.intel.com, sagis@google.com,
	vannapurve@google.com, paulmck@kernel.org, nik.borisov@suse.com,
	zhenzhong.duan@intel.com, seanjc@google.com,
	rick.p.edgecombe@intel.com, kas@kernel.org,
	dave.hansen@linux.intel.com, vishal.l.verma@intel.com,
	binbin.wu@linux.intel.com, tony.lindgren@linux.intel.com,
	Chao Gao <chao.gao@intel.com>, Thomas Gleixner <tglx@kernel.org>,
	Ingo Molnar <mingo@redhat.com>, Borislav Petkov <bp@alien8.de>,
	"H. Peter Anvin" <hpa@zytor.com>
Subject: [PATCH v4 01/24] x86/virt/tdx: Move low level SEAMCALL helpers out of <asm/tdx.h>
Date: Thu, 12 Feb 2026 06:35:04 -0800	[thread overview]
Message-ID: <20260212143606.534586-2-chao.gao@intel.com> (raw)
In-Reply-To: <20260212143606.534586-1-chao.gao@intel.com>

From: Kai Huang <kai.huang@intel.com>

TDX host core code implements three seamcall*() helpers to make SEAMCALL
to the TDX module.  Currently, they are implemented in <asm/tdx.h> and
are exposed to other kernel code which includes <asm/tdx.h>.

However, other than the TDX host core, seamcall*() are not expected to
be used by other kernel code directly.  For instance, for all SEAMCALLs
that are used by KVM, the TDX host core exports a wrapper function for
each of them.

Move seamcall*() and related code out of <asm/tdx.h> and make them only
visible to TDX host core.

Since TDX host core tdx.c is already very heavy, don't put low level
seamcall*() code there but to a new dedicated "seamcall.h".  Also,
currently tdx.c has seamcall_prerr*() helpers which additionally print
error message when calling seamcall*() fails.  Move them to "seamcall.h"
as well.  In such way all low level SEAMCALL helpers are in a dedicated
place, which is much more readable.

Copy the copyright notice from the original files and consolidate the
date ranges to:

	Copyright (C) 2021-2023 Intel Corporation

Signed-off-by: Kai Huang <kai.huang@intel.com>
Signed-off-by: Chao Gao <chao.gao@intel.com>
Reviewed-by: Zhenzhong Duan <zhenzhong.duan@intel.com>
Reviewed-by: Binbin Wu <binbin.wu@linux.intel.com>
Reviewed-by: Tony Lindgren <tony.lindgren@linux.intel.com>
Acked-by: Dave Hansen <dave.hansen@linux.intel.com>
---
v4:
 - Collect reviews
 - add "internal" to the new header file [Dave]
 - document the scope of the new header file [Dave]
 - correct the copyright notice [Dave]
v2:
 - new
---
 arch/x86/include/asm/tdx.h                |  47 ----------
 arch/x86/virt/vmx/tdx/seamcall_internal.h | 107 ++++++++++++++++++++++
 arch/x86/virt/vmx/tdx/tdx.c               |  47 +---------
 3 files changed, 109 insertions(+), 92 deletions(-)
 create mode 100644 arch/x86/virt/vmx/tdx/seamcall_internal.h

diff --git a/arch/x86/include/asm/tdx.h b/arch/x86/include/asm/tdx.h
index 6b338d7f01b7..cb2219302dfc 100644
--- a/arch/x86/include/asm/tdx.h
+++ b/arch/x86/include/asm/tdx.h
@@ -97,54 +97,7 @@ static inline long tdx_kvm_hypercall(unsigned int nr, unsigned long p1,
 #endif /* CONFIG_INTEL_TDX_GUEST && CONFIG_KVM_GUEST */
 
 #ifdef CONFIG_INTEL_TDX_HOST
-u64 __seamcall(u64 fn, struct tdx_module_args *args);
-u64 __seamcall_ret(u64 fn, struct tdx_module_args *args);
-u64 __seamcall_saved_ret(u64 fn, struct tdx_module_args *args);
 void tdx_init(void);
-
-#include <linux/preempt.h>
-#include <asm/archrandom.h>
-#include <asm/processor.h>
-
-typedef u64 (*sc_func_t)(u64 fn, struct tdx_module_args *args);
-
-static __always_inline u64 __seamcall_dirty_cache(sc_func_t func, u64 fn,
-						  struct tdx_module_args *args)
-{
-	lockdep_assert_preemption_disabled();
-
-	/*
-	 * SEAMCALLs are made to the TDX module and can generate dirty
-	 * cachelines of TDX private memory.  Mark cache state incoherent
-	 * so that the cache can be flushed during kexec.
-	 *
-	 * This needs to be done before actually making the SEAMCALL,
-	 * because kexec-ing CPU could send NMI to stop remote CPUs,
-	 * in which case even disabling IRQ won't help here.
-	 */
-	this_cpu_write(cache_state_incoherent, true);
-
-	return func(fn, args);
-}
-
-static __always_inline u64 sc_retry(sc_func_t func, u64 fn,
-			   struct tdx_module_args *args)
-{
-	int retry = RDRAND_RETRY_LOOPS;
-	u64 ret;
-
-	do {
-		preempt_disable();
-		ret = __seamcall_dirty_cache(func, fn, args);
-		preempt_enable();
-	} while (ret == TDX_RND_NO_ENTROPY && --retry);
-
-	return ret;
-}
-
-#define seamcall(_fn, _args)		sc_retry(__seamcall, (_fn), (_args))
-#define seamcall_ret(_fn, _args)	sc_retry(__seamcall_ret, (_fn), (_args))
-#define seamcall_saved_ret(_fn, _args)	sc_retry(__seamcall_saved_ret, (_fn), (_args))
 int tdx_cpu_enable(void);
 int tdx_enable(void);
 const char *tdx_dump_mce_info(struct mce *m);
diff --git a/arch/x86/virt/vmx/tdx/seamcall_internal.h b/arch/x86/virt/vmx/tdx/seamcall_internal.h
new file mode 100644
index 000000000000..70c3cf1f4adc
--- /dev/null
+++ b/arch/x86/virt/vmx/tdx/seamcall_internal.h
@@ -0,0 +1,107 @@
+/* SPDX-License-Identifier: GPL-2.0 */
+/*
+ * SEAMCALL utilities for TDX host-side operations.
+ *
+ * Provides convenient wrappers around SEAMCALL assembly with retry logic,
+ * error reporting and cache coherency tracking.
+ *
+ * Copyright (C) 2021-2023 Intel Corporation
+ */
+
+#ifndef _X86_VIRT_SEAMCALL_INTERNAL_H
+#define _X86_VIRT_SEAMCALL_INTERNAL_H
+
+#include <linux/printk.h>
+#include <linux/types.h>
+#include <asm/archrandom.h>
+#include <asm/processor.h>
+#include <asm/tdx.h>
+
+u64 __seamcall(u64 fn, struct tdx_module_args *args);
+u64 __seamcall_ret(u64 fn, struct tdx_module_args *args);
+u64 __seamcall_saved_ret(u64 fn, struct tdx_module_args *args);
+
+typedef u64 (*sc_func_t)(u64 fn, struct tdx_module_args *args);
+
+static __always_inline u64 __seamcall_dirty_cache(sc_func_t func, u64 fn,
+						  struct tdx_module_args *args)
+{
+	lockdep_assert_preemption_disabled();
+
+	/*
+	 * SEAMCALLs are made to the TDX module and can generate dirty
+	 * cachelines of TDX private memory.  Mark cache state incoherent
+	 * so that the cache can be flushed during kexec.
+	 *
+	 * This needs to be done before actually making the SEAMCALL,
+	 * because kexec-ing CPU could send NMI to stop remote CPUs,
+	 * in which case even disabling IRQ won't help here.
+	 */
+	this_cpu_write(cache_state_incoherent, true);
+
+	return func(fn, args);
+}
+
+static __always_inline u64 sc_retry(sc_func_t func, u64 fn,
+			   struct tdx_module_args *args)
+{
+	int retry = RDRAND_RETRY_LOOPS;
+	u64 ret;
+
+	do {
+		ret = func(fn, args);
+	} while (ret == TDX_RND_NO_ENTROPY && --retry);
+
+	return ret;
+}
+
+#define seamcall(_fn, _args)		sc_retry(__seamcall, (_fn), (_args))
+#define seamcall_ret(_fn, _args)	sc_retry(__seamcall_ret, (_fn), (_args))
+#define seamcall_saved_ret(_fn, _args)	sc_retry(__seamcall_saved_ret, (_fn), (_args))
+
+typedef void (*sc_err_func_t)(u64 fn, u64 err, struct tdx_module_args *args);
+
+static inline void seamcall_err(u64 fn, u64 err, struct tdx_module_args *args)
+{
+	pr_err("SEAMCALL (0x%016llx) failed: 0x%016llx\n", fn, err);
+}
+
+static inline void seamcall_err_ret(u64 fn, u64 err,
+				    struct tdx_module_args *args)
+{
+	seamcall_err(fn, err, args);
+	pr_err("RCX 0x%016llx RDX 0x%016llx R08 0x%016llx\n",
+			args->rcx, args->rdx, args->r8);
+	pr_err("R09 0x%016llx R10 0x%016llx R11 0x%016llx\n",
+			args->r9, args->r10, args->r11);
+}
+
+static __always_inline int sc_retry_prerr(sc_func_t func,
+					  sc_err_func_t err_func,
+					  u64 fn, struct tdx_module_args *args)
+{
+	u64 sret = sc_retry(func, fn, args);
+
+	if (sret == TDX_SUCCESS)
+		return 0;
+
+	if (sret == TDX_SEAMCALL_VMFAILINVALID)
+		return -ENODEV;
+
+	if (sret == TDX_SEAMCALL_GP)
+		return -EOPNOTSUPP;
+
+	if (sret == TDX_SEAMCALL_UD)
+		return -EACCES;
+
+	err_func(fn, sret, args);
+	return -EIO;
+}
+
+#define seamcall_prerr(__fn, __args)						\
+	sc_retry_prerr(__seamcall, seamcall_err, (__fn), (__args))
+
+#define seamcall_prerr_ret(__fn, __args)					\
+	sc_retry_prerr(__seamcall_ret, seamcall_err_ret, (__fn), (__args))
+
+#endif /* _X86_VIRT_SEAMCALL_INTERNAL_H */
diff --git a/arch/x86/virt/vmx/tdx/tdx.c b/arch/x86/virt/vmx/tdx/tdx.c
index 5ce4ebe99774..ddcc1a8c743f 100644
--- a/arch/x86/virt/vmx/tdx/tdx.c
+++ b/arch/x86/virt/vmx/tdx/tdx.c
@@ -39,6 +39,8 @@
 #include <asm/cpu_device_id.h>
 #include <asm/processor.h>
 #include <asm/mce.h>
+
+#include "seamcall_internal.h"
 #include "tdx.h"
 
 static u32 tdx_global_keyid __ro_after_init;
@@ -59,51 +61,6 @@ static LIST_HEAD(tdx_memlist);
 
 static struct tdx_sys_info tdx_sysinfo;
 
-typedef void (*sc_err_func_t)(u64 fn, u64 err, struct tdx_module_args *args);
-
-static inline void seamcall_err(u64 fn, u64 err, struct tdx_module_args *args)
-{
-	pr_err("SEAMCALL (0x%016llx) failed: 0x%016llx\n", fn, err);
-}
-
-static inline void seamcall_err_ret(u64 fn, u64 err,
-				    struct tdx_module_args *args)
-{
-	seamcall_err(fn, err, args);
-	pr_err("RCX 0x%016llx RDX 0x%016llx R08 0x%016llx\n",
-			args->rcx, args->rdx, args->r8);
-	pr_err("R09 0x%016llx R10 0x%016llx R11 0x%016llx\n",
-			args->r9, args->r10, args->r11);
-}
-
-static __always_inline int sc_retry_prerr(sc_func_t func,
-					  sc_err_func_t err_func,
-					  u64 fn, struct tdx_module_args *args)
-{
-	u64 sret = sc_retry(func, fn, args);
-
-	if (sret == TDX_SUCCESS)
-		return 0;
-
-	if (sret == TDX_SEAMCALL_VMFAILINVALID)
-		return -ENODEV;
-
-	if (sret == TDX_SEAMCALL_GP)
-		return -EOPNOTSUPP;
-
-	if (sret == TDX_SEAMCALL_UD)
-		return -EACCES;
-
-	err_func(fn, sret, args);
-	return -EIO;
-}
-
-#define seamcall_prerr(__fn, __args)						\
-	sc_retry_prerr(__seamcall, seamcall_err, (__fn), (__args))
-
-#define seamcall_prerr_ret(__fn, __args)					\
-	sc_retry_prerr(__seamcall_ret, seamcall_err_ret, (__fn), (__args))
-
 /*
  * Do the module global initialization once and return its result.
  * It can be done on any cpu.  It's always called with interrupts
-- 
2.47.3


  reply	other threads:[~2026-02-12 14:36 UTC|newest]

Thread overview: 115+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2026-02-12 14:35 [PATCH v4 00/24] Runtime TDX Module update support Chao Gao
2026-02-12 14:35 ` Chao Gao [this message]
2026-03-02 12:24   ` [PATCH v4 01/24] x86/virt/tdx: Move low level SEAMCALL helpers out of <asm/tdx.h> Chao Gao
2026-03-05  9:24   ` Binbin Wu
2026-02-12 14:35 ` [PATCH v4 02/24] coco/tdx-host: Introduce a "tdx_host" device Chao Gao
2026-02-20  0:15   ` Huang, Kai
2026-02-24  1:11     ` Chao Gao
2026-03-05  9:25   ` Binbin Wu
2026-03-06  2:13     ` Chao Gao
2026-03-06  4:17       ` Dave Hansen
2026-03-06  5:12         ` Chao Gao
2026-02-12 14:35 ` [PATCH v4 03/24] coco/tdx-host: Expose TDX Module version Chao Gao
2026-02-20  0:40   ` Huang, Kai
2026-02-24  2:02     ` Chao Gao
2026-02-24 10:18       ` Huang, Kai
2026-02-12 14:35 ` [PATCH v4 04/24] x86/virt/seamldr: Introduce a wrapper for P-SEAMLDR SEAMCALLs Chao Gao
2026-02-20  1:12   ` Huang, Kai
2026-02-24  2:31     ` Chao Gao
2026-02-24 10:25       ` Huang, Kai
2026-03-12 20:15         ` Dave Hansen
2026-03-05  9:51   ` Binbin Wu
2026-03-12 20:14   ` Dave Hansen
2026-03-13  8:02     ` Chao Gao
2026-02-12 14:35 ` [PATCH v4 05/24] x86/virt/seamldr: Retrieve P-SEAMLDR information Chao Gao
2026-02-20  9:36   ` Huang, Kai
2026-02-24  2:59     ` Chao Gao
2026-02-24 10:30       ` Huang, Kai
2026-02-12 14:35 ` [PATCH v4 06/24] coco/tdx-host: Expose P-SEAMLDR information via sysfs Chao Gao
2026-03-06  9:29   ` Binbin Wu
2026-02-12 14:35 ` [PATCH v4 07/24] coco/tdx-host: Implement firmware upload sysfs ABI for TDX Module updates Chao Gao
2026-02-27  3:30   ` Xu Yilun
2026-02-27  4:36   ` Xu Yilun
2026-03-10  2:31   ` Yan Zhao
2026-03-12 20:20   ` Dave Hansen
2026-03-13  8:28     ` Chao Gao
2026-02-12 14:35 ` [PATCH v4 08/24] x86/virt/seamldr: Block TDX Module updates if any CPU is offline Chao Gao
2026-03-05  7:02   ` Huang, Kai
2026-03-12 20:20   ` Dave Hansen
2026-03-13  8:17     ` Chao Gao
2026-02-12 14:35 ` [PATCH v4 09/24] x86/virt/seamldr: Check update limit before TDX Module updates Chao Gao
2026-03-05  4:09   ` Xu Yilun
2026-03-05  7:04   ` Huang, Kai
2026-03-12  2:35   ` Yan Zhao
2026-03-12 14:13     ` Chao Gao
2026-03-12 19:21   ` Edgecombe, Rick P
2026-03-12 20:23   ` Dave Hansen
2026-03-13  8:32     ` Chao Gao
2026-02-12 14:35 ` [PATCH v4 10/24] x86/virt/seamldr: Allocate and populate a module update request Chao Gao
2026-02-19 22:31   ` Huang, Kai
2026-02-24  5:15     ` Chao Gao
2026-02-24 10:46       ` Huang, Kai
2026-03-05  4:12   ` Xu Yilun
2026-03-12  2:32   ` Yan Zhao
2026-03-12 14:36     ` Chao Gao
2026-03-12 16:56       ` Edgecombe, Rick P
2026-03-13 12:16         ` Chao Gao
2026-02-12 14:35 ` [PATCH v4 11/24] x86/virt/seamldr: Introduce skeleton for TDX Module updates Chao Gao
2026-02-23  9:25   ` Huang, Kai
2026-02-24  6:00     ` Chao Gao
2026-02-24 10:49       ` Huang, Kai
2026-03-12  2:00   ` Edgecombe, Rick P
2026-03-12 14:09     ` Chao Gao
2026-03-12 18:05       ` Edgecombe, Rick P
2026-03-13 13:54         ` Chao Gao
2026-03-13 17:43           ` Edgecombe, Rick P
2026-03-12 20:40   ` Dave Hansen
2026-03-13 12:15     ` Chao Gao
2026-02-12 14:35 ` [PATCH v4 12/24] x86/virt/seamldr: Abort updates if errors occurred midway Chao Gao
2026-03-04 22:38   ` Huang, Kai
2026-02-12 14:35 ` [PATCH v4 13/24] x86/virt/seamldr: Shut down the current TDX module Chao Gao
2026-03-04 22:59   ` Huang, Kai
2026-03-06  8:14     ` Chao Gao
2026-03-12  2:34       ` Edgecombe, Rick P
2026-03-05  4:14   ` Xu Yilun
2026-03-12  2:17   ` Edgecombe, Rick P
2026-03-12  2:57     ` Chao Gao
2026-02-12 14:35 ` [PATCH v4 14/24] x86/virt/tdx: Reset software states during TDX Module shutdown Chao Gao
2026-03-04 23:06   ` Huang, Kai
2026-02-12 14:35 ` [PATCH v4 15/24] x86/virt/seamldr: Log TDX Module update failures Chao Gao
2026-03-04 23:08   ` Huang, Kai
2026-03-05  4:18   ` Xu Yilun
2026-02-12 14:35 ` [PATCH v4 16/24] x86/virt/seamldr: Install a new TDX Module Chao Gao
2026-03-04 23:17   ` Huang, Kai
2026-03-05  4:22     ` Xu Yilun
2026-02-12 14:35 ` [PATCH v4 17/24] x86/virt/seamldr: Do TDX per-CPU initialization after updates Chao Gao
2026-03-04 23:18   ` Huang, Kai
2026-02-12 14:35 ` [PATCH v4 18/24] x86/virt/tdx: Restore TDX Module state Chao Gao
2026-03-04 23:24   ` Huang, Kai
2026-02-12 14:35 ` [PATCH v4 19/24] x86/virt/tdx: Update tdx_sysinfo and check features post-update Chao Gao
2026-03-04 23:40   ` Huang, Kai
2026-03-06  8:32     ` Chao Gao
2026-03-06  9:35       ` Huang, Kai
2026-03-12 18:48   ` Edgecombe, Rick P
2026-02-12 14:35 ` [PATCH v4 20/24] x86/virt/tdx: Enable TDX Module runtime updates Chao Gao
2026-02-23  5:09   ` Huang, Kai
2026-02-24  6:02     ` Chao Gao
2026-02-12 14:35 ` [PATCH v4 21/24] x86/virt/tdx: Avoid updates during update-sensitive operations Chao Gao
2026-02-23  4:58   ` Huang, Kai
2026-02-26  3:02     ` Chao Gao
2026-02-26  6:34       ` dan.j.williams
2026-02-26 15:32         ` Chao Gao
2026-02-26 22:06           ` dan.j.williams
2026-02-12 14:35 ` [PATCH v4 22/24] coco/tdx-host: Document TDX Module update expectations Chao Gao
2026-02-12 21:59   ` dan.j.williams
2026-02-12 14:35 ` [PATCH v4 23/24] x86/virt/tdx: Document TDX Module updates Chao Gao
2026-03-04 23:49   ` Huang, Kai
2026-03-12  2:42   ` Edgecombe, Rick P
2026-02-12 14:35 ` [PATCH v4 24/24] [NOT-FOR-REVIEW] x86/virt/seamldr: Save and restore current VMCS Chao Gao
2026-03-11 12:50   ` Chao Gao
2026-03-11 22:06     ` Huang, Kai
2026-03-12  8:48       ` Chao Gao
2026-03-12  9:59         ` Huang, Kai
2026-03-12 15:26         ` Vishal Annapurve
2026-03-12 15:31           ` Dave Hansen
2026-02-12 14:46 ` [PATCH v4 00/24] Runtime TDX Module update support Chao Gao

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20260212143606.534586-2-chao.gao@intel.com \
    --to=chao.gao@intel.com \
    --cc=binbin.wu@linux.intel.com \
    --cc=bp@alien8.de \
    --cc=dan.j.williams@intel.com \
    --cc=dave.hansen@linux.intel.com \
    --cc=hpa@zytor.com \
    --cc=ira.weiny@intel.com \
    --cc=kai.huang@intel.com \
    --cc=kas@kernel.org \
    --cc=kvm@vger.kernel.org \
    --cc=linux-coco@lists.linux.dev \
    --cc=linux-kernel@vger.kernel.org \
    --cc=mingo@redhat.com \
    --cc=nik.borisov@suse.com \
    --cc=paulmck@kernel.org \
    --cc=reinette.chatre@intel.com \
    --cc=rick.p.edgecombe@intel.com \
    --cc=sagis@google.com \
    --cc=seanjc@google.com \
    --cc=tglx@kernel.org \
    --cc=tony.lindgren@linux.intel.com \
    --cc=vannapurve@google.com \
    --cc=vishal.l.verma@intel.com \
    --cc=x86@kernel.org \
    --cc=yilun.xu@linux.intel.com \
    --cc=zhenzhong.duan@intel.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox