[tip: x86/tdx] x86/virt/tdx: Clarify try_init_module_global() result caching

tip-bot2 for Chao Gao posted 1 patch 2 days, 8 hours ago
arch/x86/virt/vmx/tdx/tdx.c | 14 ++++++++++----
1 file changed, 10 insertions(+), 4 deletions(-)
[tip: x86/tdx] x86/virt/tdx: Clarify try_init_module_global() result caching
Posted by tip-bot2 for Chao Gao 2 days, 8 hours ago
The following commit has been merged into the x86/tdx branch of tip:

Commit-ID:     1ffa6a10253c417b281aff3cbd02bdf43b2b159d
Gitweb:        https://git.kernel.org/tip/1ffa6a10253c417b281aff3cbd02bdf43b2b159d
Author:        Chao Gao <chao.gao@intel.com>
AuthorDate:    Wed, 20 May 2026 15:28:46 -07:00
Committer:     Dave Hansen <dave.hansen@linux.intel.com>
CommitterDate: Wed, 03 Jun 2026 08:14:39 -07:00

x86/virt/tdx: Clarify try_init_module_global() result caching

TDX module global initialization is executed only once. The first call
caches both the return code and the "done" state in static function
variables.  Later callers read the variables. A lock protects the
saved state and serializes callers.

These variables will soon be moved to a global structure. Prepare for
that by treating the variables as a unit. Assign them together and
limit accesses to while the lock is held.

[ dhansen: mostly rewrite changelog ]

Signed-off-by: Chao Gao <chao.gao@intel.com>
Signed-off-by: Dave Hansen <dave.hansen@linux.intel.com>
Link: https://patch.msgid.link/20260520133909.409394-2-chao.gao@intel.com
---
 arch/x86/virt/vmx/tdx/tdx.c | 14 ++++++++++----
 1 file changed, 10 insertions(+), 4 deletions(-)

diff --git a/arch/x86/virt/vmx/tdx/tdx.c b/arch/x86/virt/vmx/tdx/tdx.c
index c0c6281..ad56f14 100644
--- a/arch/x86/virt/vmx/tdx/tdx.c
+++ b/arch/x86/virt/vmx/tdx/tdx.c
@@ -115,28 +115,34 @@ static int try_init_module_global(void)
 	static DEFINE_RAW_SPINLOCK(sysinit_lock);
 	static bool sysinit_done;
 	static int sysinit_ret;
+	int ret;
 
 	raw_spin_lock(&sysinit_lock);
 
-	if (sysinit_done)
+	/* Return the "cached" return code. */
+	if (sysinit_done) {
+		ret = sysinit_ret;
 		goto out;
+	}
 
 	/* RCX is module attributes and all bits are reserved */
 	args.rcx = 0;
-	sysinit_ret = seamcall_prerr(TDH_SYS_INIT, &args);
+	ret = seamcall_prerr(TDH_SYS_INIT, &args);
 
 	/*
 	 * The first SEAMCALL also detects the TDX module, thus
 	 * it can fail due to the TDX module is not loaded.
 	 * Dump message to let the user know.
 	 */
-	if (sysinit_ret == -ENODEV)
+	if (ret == -ENODEV)
 		pr_err("module not loaded\n");
 
+	/* Save the return code for later callers. */
 	sysinit_done = true;
+	sysinit_ret = ret;
 out:
 	raw_spin_unlock(&sysinit_lock);
-	return sysinit_ret;
+	return ret;
 }
 
 /**