From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from smtp-out2.suse.de (smtp-out2.suse.de [195.135.223.131]) (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 E561246DFE7 for ; Fri, 11 Sep 2026 08:43:33 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=195.135.223.131 ARC-Seal:i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1789116215; cv=none; b=KXvCOeDmAeonIs3S5hWEw1E72FiX0VUp8XFJrqe6HEeiENYTeGcpxdfwcuk4hktsPMxLrOzticfgfpq1T1UDwoHw2erQmY87XOlfO/GXZQux27rODpm7nIcZsUlMXg2HHGx9J7p7OmZAwvDcspEnKzFT26b1nq4oVQtUt183cxQ= ARC-Message-Signature:i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1789116215; c=relaxed/simple; bh=9c9+3pkCdeqW2mtW9uDcnpqV1QStmN2de+vjoVWPN0Y=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=HVVez+JG66q3pzu79SOp9jfA0yAc1KnE3zQ4aG6rFNc/kpEgcheeyHlinafIXiR6RIGSsHtbUkBRNhflEMgSfBEi46RARPrbeob31OzWdLylHn/PP4CQwagmYAKfxnf+qUf141Ar8SJVt4Qum9ayYYm5nXVJWid7RzXJ5KdbGGM= ARC-Authentication-Results:i=1; smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=suse.com; spf=pass smtp.mailfrom=suse.com; dkim=pass (1024-bit key) header.d=suse.com header.i=@suse.com header.b=K2ym+chd; dkim=pass (1024-bit key) header.d=suse.com header.i=@suse.com header.b=FbfwFv85; arc=none smtp.client-ip=195.135.223.131 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=suse.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=suse.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=suse.com header.i=@suse.com header.b="K2ym+chd"; dkim=pass (1024-bit key) header.d=suse.com header.i=@suse.com header.b="FbfwFv85" Received: from imap1.dmz-prg2.suse.org (unknown [10.150.64.97]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (4096 bits) server-digest SHA256) (No client certificate requested) by smtp-out2.suse.de (Postfix) with ESMTPS id 98F131FA79; Fri, 11 Sep 2026 08:43:23 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=suse.com; s=susede1; t=1789116207; h=from:from:reply-to:date:date:message-id:message-id:to:to:cc:cc: mime-version:mime-version: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references; bh=y/JsZQGyUXG2PbaQKxJnt1DssgKzKUnZGz0wBmIldJU=; b=K2ym+chdvp4AOLx7hkxPAOXGGkVqFjIwBO9J5eYiDHaqbG0tAeUekjwPw1enesmOmkvpbb 60J62JjW2kbAONrRWP2I4xEvPu2HolP1M+HFk/LKa50fHZp6nuQTkaBSMvDwaXGYKL+Mag GcRxrTsJHmSDk3XBZtwilU2ydL4nGmM= Authentication-Results: smtp-out2.suse.de; none DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=suse.com; s=susede1; t=1789116203; h=from:from:reply-to:date:date:message-id:message-id:to:to:cc:cc: mime-version:mime-version: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references; bh=y/JsZQGyUXG2PbaQKxJnt1DssgKzKUnZGz0wBmIldJU=; b=FbfwFv85BO4Lxu6VbQS451GwDDEmZSiFnVhP+ZEMXMkCC4ikbs9v0r/FjQR3mWFpjf0TmZ L7QidEp3rxrjzR1mcTx3zjxQjYzGnTk8S4X2HyKk3oxdwLdM0rUhIobEQUL6hT/voPzpLw GEhuzD1Hyktm7Yj3T5pIddq8QY0s1VQ= Received: from imap1.dmz-prg2.suse.org (localhost [127.0.0.1]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (4096 bits) server-digest SHA256) (No client certificate requested) by imap1.dmz-prg2.suse.org (Postfix) with ESMTPS id 11536132D3; Fri, 11 Sep 2026 08:43:23 +0000 (UTC) Received: from dovecot-director2.suse.de ([2a07:de40:b281:106:10:150:64:167]) by imap1.dmz-prg2.suse.org with ESMTPSA id tXzkAiu/o2odFgAAD6G6ig (envelope-from ); Fri, 11 Sep 2026 08:43:23 +0000 From: Juergen Gross To: linux-kernel@vger.kernel.org, x86@kernel.org, virtualization@lists.linux.dev Cc: Juergen Gross , Thomas Gleixner , Ingo Molnar , Borislav Petkov , Dave Hansen , "H. Peter Anvin" , Ajay Kaher , Alexey Makhalov , Broadcom internal kernel review list , Boris Ostrovsky , Josh Poimboeuf , Peter Zijlstra , xen-devel@lists.xenproject.org Subject: [PATCH v5 12/17] x86/paravirt: Split off MSR related hooks into new header Date: Fri, 11 Sep 2026 10:42:06 +0200 Message-ID: <20260911084211.3149957-13-jgross@suse.com> X-Mailer: git-send-email 2.55.0 In-Reply-To: <20260911084211.3149957-1-jgross@suse.com> References: <20260911084211.3149957-1-jgross@suse.com> Precedence: bulk X-Mailing-List: virtualization@lists.linux.dev List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Spam-Level: X-Spam-Score: -6.80 X-Spam-Flag: NO X-Spamd-Result: default: False [-6.80 / 50.00]; REPLY(-4.00)[]; BAYES_HAM(-3.00)[100.00%]; MID_CONTAINS_FROM(1.00)[]; NEURAL_HAM_LONG(-1.00)[-1.000]; R_MISSING_CHARSET(0.50)[]; NEURAL_HAM_SHORT(-0.20)[-0.997]; MIME_GOOD(-0.10)[text/plain]; RCVD_COUNT_TWO(0.00)[2]; MIME_TRACE(0.00)[0:+]; FROM_HAS_DN(0.00)[]; RCPT_COUNT_TWELVE(0.00)[16]; TO_DN_SOME(0.00)[]; TO_MATCH_ENVRCPT_ALL(0.00)[]; ARC_NA(0.00)[]; FROM_EQ_ENVFROM(0.00)[]; DKIM_SIGNED(0.00)[suse.com:s=susede1]; RCVD_VIA_SMTP_AUTH(0.00)[]; R_RATELIMIT(0.00)[to_ip_from(RLfdszjqhz8kzzb9uwpzdm8png)]; DBL_BLOCKED_OPENRESOLVER(0.00)[suse.com:email,suse.com:mid,imap1.dmz-prg2.suse.org:helo]; RCVD_TLS_ALL(0.00)[] Move the WRMSR, RDMSR and RDPMC related parts of paravirt.h and paravirt_types.h into a new header file paravirt-msr.h. Switch all moved helper functions to __always_inline. Signed-off-by: Juergen Gross --- V3: - new patch V4: - always use __always_inline --- arch/x86/include/asm/msr.h | 2 +- arch/x86/include/asm/paravirt-msr.h | 56 +++++++++++++++++++++++++++ arch/x86/include/asm/paravirt.h | 55 -------------------------- arch/x86/include/asm/paravirt_types.h | 13 ------- arch/x86/kernel/paravirt.c | 14 ++++--- arch/x86/xen/enlighten_pv.c | 11 +++--- tools/objtool/check.c | 1 + 7 files changed, 73 insertions(+), 79 deletions(-) create mode 100644 arch/x86/include/asm/paravirt-msr.h diff --git a/arch/x86/include/asm/msr.h b/arch/x86/include/asm/msr.h index fb1027dc7f64..f7ad6d25bb65 100644 --- a/arch/x86/include/asm/msr.h +++ b/arch/x86/include/asm/msr.h @@ -323,7 +323,7 @@ static inline u64 native_read_pmc(int counter) } #ifdef CONFIG_PARAVIRT_XXL -#include +#include #else static __always_inline u64 read_msr(u32 msr) { diff --git a/arch/x86/include/asm/paravirt-msr.h b/arch/x86/include/asm/paravirt-msr.h new file mode 100644 index 000000000000..3e31648316a8 --- /dev/null +++ b/arch/x86/include/asm/paravirt-msr.h @@ -0,0 +1,56 @@ +/* SPDX-License-Identifier: GPL-2.0-only */ +#ifndef _ASM_X86_PARAVIRT_MSR_H +#define _ASM_X86_PARAVIRT_MSR_H + +#include + +struct pv_msr_ops { + /* Unsafe MSR operations. These will warn or panic on failure. */ + u64 (*read_msr)(u32 msr); + void (*write_msr)(u32 msr, u64 val); + + /* Safe MSR operations. Returns 0 or -EIO. */ + int (*read_msr_safe)(u32 msr, u64 *val); + int (*write_msr_safe)(u32 msr, u64 val); + + u64 (*read_pmc)(int counter); +} __no_randomize_layout; + +extern struct pv_msr_ops pv_ops_msr; + +static __always_inline u64 read_msr(u32 msr) +{ + return PVOP_CALL1(u64, pv_ops_msr, read_msr, msr); +} + +static __always_inline void write_msr(u32 msr, u64 val) +{ + PVOP_VCALL2(pv_ops_msr, write_msr, msr, val); +} + +static __always_inline void write_msrns(u32 msr, u64 val) +{ + PVOP_VCALL2(pv_ops_msr, write_msr, msr, val); +} + +static __always_inline int read_msr_safe(u32 msr, u64 *val) +{ + return PVOP_CALL2(int, pv_ops_msr, read_msr_safe, msr, val); +} + +static __always_inline int write_msr_safe(u32 msr, u64 val) +{ + return PVOP_CALL2(int, pv_ops_msr, write_msr_safe, msr, val); +} + +static __always_inline int write_msrns_safe(u32 msr, u64 val) +{ + return PVOP_CALL2(int, pv_ops_msr, write_msr_safe, msr, val); +} + +static __always_inline u64 rdpmc(int counter) +{ + return PVOP_CALL1(u64, pv_ops_msr, read_pmc, counter); +} + +#endif /* _ASM_X86_PARAVIRT_MSR_H */ diff --git a/arch/x86/include/asm/paravirt.h b/arch/x86/include/asm/paravirt.h index b0c740316cf7..eb16d55f94d3 100644 --- a/arch/x86/include/asm/paravirt.h +++ b/arch/x86/include/asm/paravirt.h @@ -130,61 +130,6 @@ static inline void __write_cr4(unsigned long x) PVOP_VCALL1(pv_ops, cpu.write_cr4, x); } -static inline u64 paravirt_read_msr(u32 msr) -{ - return PVOP_CALL1(u64, pv_ops, cpu.read_msr, msr); -} - -static inline void paravirt_write_msr(u32 msr, u64 val) -{ - PVOP_VCALL2(pv_ops, cpu.write_msr, msr, val); -} - -static inline int paravirt_read_msr_safe(u32 msr, u64 *val) -{ - return PVOP_CALL2(int, pv_ops, cpu.read_msr_safe, msr, val); -} - -static inline int paravirt_write_msr_safe(u32 msr, u64 val) -{ - return PVOP_CALL2(int, pv_ops, cpu.write_msr_safe, msr, val); -} - -static __always_inline u64 read_msr(u32 msr) -{ - return paravirt_read_msr(msr); -} - -static inline void write_msr(u32 msr, u64 val) -{ - paravirt_write_msr(msr, val); -} - -static __always_inline void write_msrns(u32 msr, u64 val) -{ - paravirt_write_msr(msr, val); -} - -static inline int write_msr_safe(u32 msr, u64 val) -{ - return paravirt_write_msr_safe(msr, val); -} - -static __always_inline int write_msrns_safe(u32 msr, u64 val) -{ - return paravirt_write_msr_safe(msr, val); -} - -static __always_inline int read_msr_safe(u32 msr, u64 *p) -{ - return paravirt_read_msr_safe(msr, p); -} - -static __always_inline u64 rdpmc(int counter) -{ - return PVOP_CALL1(u64, pv_ops, cpu.read_pmc, counter); -} - static inline void paravirt_alloc_ldt(struct desc_struct *ldt, unsigned entries) { PVOP_VCALL2(pv_ops, cpu.alloc_ldt, ldt, entries); diff --git a/arch/x86/include/asm/paravirt_types.h b/arch/x86/include/asm/paravirt_types.h index b4c4a23e77a1..2459163fa196 100644 --- a/arch/x86/include/asm/paravirt_types.h +++ b/arch/x86/include/asm/paravirt_types.h @@ -58,19 +58,6 @@ struct pv_cpu_ops { void (*cpuid)(unsigned int *eax, unsigned int *ebx, unsigned int *ecx, unsigned int *edx); - /* Unsafe MSR operations. These will warn or panic on failure. */ - u64 (*read_msr)(u32 msr); - void (*write_msr)(u32 msr, u64 val); - - /* - * Safe MSR operations. - * Returns 0 or -EIO. - */ - int (*read_msr_safe)(u32 msr, u64 *val); - int (*write_msr_safe)(u32 msr, u64 val); - - u64 (*read_pmc)(int counter); - void (*start_context_switch)(struct task_struct *prev); void (*end_context_switch)(struct task_struct *next); #endif diff --git a/arch/x86/kernel/paravirt.c b/arch/x86/kernel/paravirt.c index 00b59d774389..739dbfd8aadf 100644 --- a/arch/x86/kernel/paravirt.c +++ b/arch/x86/kernel/paravirt.c @@ -110,11 +110,6 @@ struct paravirt_patch_template pv_ops = { .cpu.read_cr0 = native_read_cr0, .cpu.write_cr0 = native_write_cr0, .cpu.write_cr4 = native_write_cr4, - .cpu.read_msr = native_read_msr, - .cpu.write_msr = native_write_msr, - .cpu.read_msr_safe = native_read_msr_safe, - .cpu.write_msr_safe = native_write_msr_safe, - .cpu.read_pmc = native_read_pmc, .cpu.load_tr_desc = native_load_tr_desc, .cpu.set_ldt = native_set_ldt, .cpu.load_gdt = native_load_gdt, @@ -212,6 +207,15 @@ struct paravirt_patch_template pv_ops = { }; #ifdef CONFIG_PARAVIRT_XXL +struct pv_msr_ops pv_ops_msr = { + .read_msr = native_read_msr, + .write_msr = native_write_msr, + .read_msr_safe = native_read_msr_safe, + .write_msr_safe = native_write_msr_safe, + .read_pmc = native_read_pmc, +}; +EXPORT_SYMBOL(pv_ops_msr); + NOKPROBE_SYMBOL(native_load_idt); #endif diff --git a/arch/x86/xen/enlighten_pv.c b/arch/x86/xen/enlighten_pv.c index 2c64b388f616..bf81e84ff261 100644 --- a/arch/x86/xen/enlighten_pv.c +++ b/arch/x86/xen/enlighten_pv.c @@ -1360,11 +1360,6 @@ asmlinkage __visible void __init xen_start_kernel(struct start_info *si) pv_ops.cpu.read_cr0 = xen_read_cr0; pv_ops.cpu.write_cr0 = xen_write_cr0; pv_ops.cpu.write_cr4 = xen_write_cr4; - pv_ops.cpu.read_msr = xen_read_msr; - pv_ops.cpu.write_msr = xen_write_msr; - pv_ops.cpu.read_msr_safe = xen_read_msr_safe; - pv_ops.cpu.write_msr_safe = xen_write_msr_safe; - pv_ops.cpu.read_pmc = xen_read_pmc; pv_ops.cpu.load_tr_desc = paravirt_nop; pv_ops.cpu.set_ldt = xen_set_ldt; pv_ops.cpu.load_gdt = xen_load_gdt; @@ -1385,6 +1380,12 @@ asmlinkage __visible void __init xen_start_kernel(struct start_info *si) pv_ops.cpu.start_context_switch = xen_start_context_switch; pv_ops.cpu.end_context_switch = xen_end_context_switch; + pv_ops_msr.read_msr = xen_read_msr; + pv_ops_msr.write_msr = xen_write_msr; + pv_ops_msr.read_msr_safe = xen_read_msr_safe; + pv_ops_msr.write_msr_safe = xen_write_msr_safe; + pv_ops_msr.read_pmc = xen_read_pmc; + xen_init_irq_ops(); /* diff --git a/tools/objtool/check.c b/tools/objtool/check.c index 464f6c9d9ff0..6c47d650b20e 100644 --- a/tools/objtool/check.c +++ b/tools/objtool/check.c @@ -529,6 +529,7 @@ static struct { } pv_ops_tables[] = { { .name = "pv_ops", }, { .name = "pv_ops_lock", }, + { .name = "pv_ops_msr", }, { .name = NULL, .idx_off = -1 } }; -- 2.55.0