* [PATCH 0/2] x86/svm: Add support for Bus Lock Threshold
@ 2026-01-20 9:53 Alejandro Vallejo
2026-01-20 9:53 ` [PATCH 1/2] x86/svm: Add infrastructure " Alejandro Vallejo
` (2 more replies)
0 siblings, 3 replies; 26+ messages in thread
From: Alejandro Vallejo @ 2026-01-20 9:53 UTC (permalink / raw)
To: xen-devel
Cc: Alejandro Vallejo, Jan Beulich, Andrew Cooper,
Roger Pau Monné, Jason Andryuk, Stefano Stabellini
Bus Locks are very costly and a VM left unchecked spamming instructions that
lock the memory bus (e.g: unaligned atomic CAS) makes system perf take a
nosedive. This patch is similar to BLD of VMX, but for SVM. It configures all
VMRUNs so they automatically exit at the first encounter of a buslock event,
effectively rate-limiting them.
Cheers,
Alejandro
Alejandro Vallejo (2):
x86/svm: Add infrastructure for Bus Lock Threshold
x86/svm: Intercept Bus Locks for HVM guests
xen/arch/x86/hvm/svm/svm.c | 5 +++++
xen/arch/x86/hvm/svm/vmcb.c | 6 ++++++
xen/arch/x86/hvm/svm/vmcb.h | 15 +++++++++++++--
xen/arch/x86/include/asm/hvm/svm.h | 2 ++
xen/arch/x86/include/asm/perfc_defn.h | 2 +-
5 files changed, 27 insertions(+), 3 deletions(-)
base-commit: 7b3e1b4e848d34c9a5b6634009959a7b9dd42104
--
2.43.0
^ permalink raw reply [flat|nested] 26+ messages in thread
* [PATCH 1/2] x86/svm: Add infrastructure for Bus Lock Threshold
2026-01-20 9:53 [PATCH 0/2] x86/svm: Add support for Bus Lock Threshold Alejandro Vallejo
@ 2026-01-20 9:53 ` Alejandro Vallejo
2026-01-20 13:12 ` Andrew Cooper
2026-01-20 13:19 ` Teddy Astie
2026-01-20 9:53 ` [PATCH 2/2] x86/svm: Intercept Bus Locks for HVM guests Alejandro Vallejo
2026-01-20 11:22 ` [PATCH 0/2] x86/svm: Add support for Bus Lock Threshold Alejandro Vallejo
2 siblings, 2 replies; 26+ messages in thread
From: Alejandro Vallejo @ 2026-01-20 9:53 UTC (permalink / raw)
To: xen-devel
Cc: Alejandro Vallejo, Jan Beulich, Andrew Cooper,
Roger Pau Monné, Jason Andryuk, Stefano Stabellini
Add missing scaffolding to enable BusLock Threshold. That is:
* Add general_intercepts_3.
* Add missing VMEXIT
* Adjust NPF perf counter base to immediately after the buslock counter
Signed-off-by: Alejandro Vallejo <alejandro.garciavallejo@amd.com>
---
xen/arch/x86/hvm/svm/svm.c | 1 +
xen/arch/x86/hvm/svm/vmcb.h | 15 +++++++++++++--
xen/arch/x86/include/asm/hvm/svm.h | 2 ++
xen/arch/x86/include/asm/perfc_defn.h | 2 +-
4 files changed, 17 insertions(+), 3 deletions(-)
diff --git a/xen/arch/x86/hvm/svm/svm.c b/xen/arch/x86/hvm/svm/svm.c
index 5d23603fc1..9748df87d8 100644
--- a/xen/arch/x86/hvm/svm/svm.c
+++ b/xen/arch/x86/hvm/svm/svm.c
@@ -2524,6 +2524,7 @@ const struct hvm_function_table * __init start_svm(void)
P(cpu_has_tsc_ratio, "TSC Rate MSR");
P(cpu_has_svm_sss, "NPT Supervisor Shadow Stack");
P(cpu_has_svm_spec_ctrl, "MSR_SPEC_CTRL virtualisation");
+ P(cpu_has_bus_lock_thresh, "BusLock-Intercept Filter");
#undef P
if ( !printed )
diff --git a/xen/arch/x86/hvm/svm/vmcb.h b/xen/arch/x86/hvm/svm/vmcb.h
index ba554a9644..85e194f247 100644
--- a/xen/arch/x86/hvm/svm/vmcb.h
+++ b/xen/arch/x86/hvm/svm/vmcb.h
@@ -65,6 +65,11 @@ enum GenericIntercept2bits
GENERAL2_INTERCEPT_RDPRU = 1 << 14,
};
+/* general 2 intercepts */
+enum GenericIntercept3bits
+{
+ GENERAL3_INTERCEPT_BUS_LOCK_THRESH = 1 << 5,
+};
/* control register intercepts */
enum CRInterceptBits
@@ -289,6 +294,7 @@ enum VMEXIT_EXITCODE
VMEXIT_MWAIT_CONDITIONAL= 140, /* 0x8c */
VMEXIT_XSETBV = 141, /* 0x8d */
VMEXIT_RDPRU = 142, /* 0x8e */
+ VMEXIT_BUSLOCK = 165, /* 0xa5 */
/* Remember to also update VMEXIT_NPF_PERFC! */
VMEXIT_NPF = 1024, /* 0x400, nested paging fault */
/* Remember to also update SVM_PERF_EXIT_REASON_SIZE! */
@@ -405,7 +411,8 @@ struct vmcb_struct {
u32 _exception_intercepts; /* offset 0x08 - cleanbit 0 */
u32 _general1_intercepts; /* offset 0x0C - cleanbit 0 */
u32 _general2_intercepts; /* offset 0x10 - cleanbit 0 */
- u32 res01[10];
+ u32 _general3_intercepts; /* offset 0x14 - cleanbit 0 */
+ u32 res01[9];
u16 _pause_filter_thresh; /* offset 0x3C - cleanbit 0 */
u16 _pause_filter_count; /* offset 0x3E - cleanbit 0 */
u64 _iopm_base_pa; /* offset 0x40 - cleanbit 1 */
@@ -489,7 +496,10 @@ struct vmcb_struct {
u64 nextrip; /* offset 0xC8 */
u8 guest_ins_len; /* offset 0xD0 */
u8 guest_ins[15]; /* offset 0xD1 */
- u64 res10a[100]; /* offset 0xE0 pad to save area */
+ u64 res10a[8]; /* offset 0xE0 */
+ u16 bus_lock_thresh; /* offset 0x120 */
+ u16 res10b[3]; /* offset 0x122 */
+ u64 res10c[91]; /* offset 0x128 pad to save area */
union {
struct segment_register sreg[6];
@@ -583,6 +593,7 @@ VMCB_ACCESSORS(dr_intercepts, intercepts)
VMCB_ACCESSORS(exception_intercepts, intercepts)
VMCB_ACCESSORS(general1_intercepts, intercepts)
VMCB_ACCESSORS(general2_intercepts, intercepts)
+VMCB_ACCESSORS(general3_intercepts, intercepts)
VMCB_ACCESSORS(pause_filter_count, intercepts)
VMCB_ACCESSORS(pause_filter_thresh, intercepts)
VMCB_ACCESSORS(tsc_offset, intercepts)
diff --git a/xen/arch/x86/include/asm/hvm/svm.h b/xen/arch/x86/include/asm/hvm/svm.h
index a6d7e4aed3..14fe4abf96 100644
--- a/xen/arch/x86/include/asm/hvm/svm.h
+++ b/xen/arch/x86/include/asm/hvm/svm.h
@@ -37,6 +37,7 @@ extern u32 svm_feature_flags;
#define SVM_FEATURE_VGIF 16 /* Virtual GIF */
#define SVM_FEATURE_SSS 19 /* NPT Supervisor Shadow Stacks */
#define SVM_FEATURE_SPEC_CTRL 20 /* MSR_SPEC_CTRL virtualisation */
+#define SVM_FEATURE_BUS_LOCK_THRESH 29 /* Bus Lock Threshold */
static inline bool cpu_has_svm_feature(unsigned int feat)
{
@@ -56,6 +57,7 @@ static inline bool cpu_has_svm_feature(unsigned int feat)
#define cpu_has_svm_vloadsave cpu_has_svm_feature(SVM_FEATURE_VLOADSAVE)
#define cpu_has_svm_sss cpu_has_svm_feature(SVM_FEATURE_SSS)
#define cpu_has_svm_spec_ctrl cpu_has_svm_feature(SVM_FEATURE_SPEC_CTRL)
+#define cpu_has_bus_lock_thresh cpu_has_svm_feature(SVM_FEATURE_BUS_LOCK_THRESH)
#define MSR_INTERCEPT_NONE 0
#define MSR_INTERCEPT_READ 1
diff --git a/xen/arch/x86/include/asm/perfc_defn.h b/xen/arch/x86/include/asm/perfc_defn.h
index d6127cb91e..ac7439b992 100644
--- a/xen/arch/x86/include/asm/perfc_defn.h
+++ b/xen/arch/x86/include/asm/perfc_defn.h
@@ -7,7 +7,7 @@ PERFCOUNTER_ARRAY(exceptions, "exceptions", 32)
#ifdef CONFIG_HVM
#define VMX_PERF_EXIT_REASON_SIZE 76
-#define VMEXIT_NPF_PERFC 143
+#define VMEXIT_NPF_PERFC 166
#define SVM_PERF_EXIT_REASON_SIZE (VMEXIT_NPF_PERFC + 1)
PERFCOUNTER_ARRAY(vmexits, "vmexits",
MAX(VMX_PERF_EXIT_REASON_SIZE, SVM_PERF_EXIT_REASON_SIZE))
--
2.43.0
^ permalink raw reply related [flat|nested] 26+ messages in thread
* [PATCH 2/2] x86/svm: Intercept Bus Locks for HVM guests
2026-01-20 9:53 [PATCH 0/2] x86/svm: Add support for Bus Lock Threshold Alejandro Vallejo
2026-01-20 9:53 ` [PATCH 1/2] x86/svm: Add infrastructure " Alejandro Vallejo
@ 2026-01-20 9:53 ` Alejandro Vallejo
2026-01-20 13:11 ` Teddy Astie
2026-01-20 13:18 ` Andrew Cooper
2026-01-20 11:22 ` [PATCH 0/2] x86/svm: Add support for Bus Lock Threshold Alejandro Vallejo
2 siblings, 2 replies; 26+ messages in thread
From: Alejandro Vallejo @ 2026-01-20 9:53 UTC (permalink / raw)
To: xen-devel
Cc: Alejandro Vallejo, Jan Beulich, Andrew Cooper,
Roger Pau Monné, Jason Andryuk, Stefano Stabellini
With the threshold initialised to 1 the guest exits at the first
buslock. Initialising as zero is invalid and causes an immediate exit.
Signed-off-by: Alejandro Vallejo <alejandro.garciavallejo@amd.com>
---
xen/arch/x86/hvm/svm/svm.c | 4 ++++
xen/arch/x86/hvm/svm/vmcb.c | 6 ++++++
2 files changed, 10 insertions(+)
diff --git a/xen/arch/x86/hvm/svm/svm.c b/xen/arch/x86/hvm/svm/svm.c
index 9748df87d8..dbb7f99d5e 100644
--- a/xen/arch/x86/hvm/svm/svm.c
+++ b/xen/arch/x86/hvm/svm/svm.c
@@ -3087,6 +3087,10 @@ void asmlinkage svm_vmexit_handler(void)
hvm_descriptor_access_intercept(0, 0, desc, write);
break;
}
+ case VMEXIT_BUSLOCK:
+ perfc_incr(buslock);
+ vmcb->bus_lock_thresh = 1;
+ break;
default:
unexpected_exit_type:
diff --git a/xen/arch/x86/hvm/svm/vmcb.c b/xen/arch/x86/hvm/svm/vmcb.c
index cbee10d046..7a19b1ab61 100644
--- a/xen/arch/x86/hvm/svm/vmcb.c
+++ b/xen/arch/x86/hvm/svm/vmcb.c
@@ -66,6 +66,12 @@ static int construct_vmcb(struct vcpu *v)
GENERAL2_INTERCEPT_XSETBV | GENERAL2_INTERCEPT_ICEBP |
GENERAL2_INTERCEPT_RDPRU;
+ if ( cpu_has_bus_lock_thresh )
+ {
+ vmcb->_general3_intercepts = GENERAL3_INTERCEPT_BUS_LOCK_THRESH;
+ vmcb->bus_lock_thresh = 1; /* trigger immediately */
+ }
+
/* Intercept all debug-register writes. */
vmcb->_dr_intercepts = ~0u;
--
2.43.0
^ permalink raw reply related [flat|nested] 26+ messages in thread
* Re: [PATCH 0/2] x86/svm: Add support for Bus Lock Threshold
2026-01-20 9:53 [PATCH 0/2] x86/svm: Add support for Bus Lock Threshold Alejandro Vallejo
2026-01-20 9:53 ` [PATCH 1/2] x86/svm: Add infrastructure " Alejandro Vallejo
2026-01-20 9:53 ` [PATCH 2/2] x86/svm: Intercept Bus Locks for HVM guests Alejandro Vallejo
@ 2026-01-20 11:22 ` Alejandro Vallejo
2026-01-20 13:21 ` Andrew Cooper
2 siblings, 1 reply; 26+ messages in thread
From: Alejandro Vallejo @ 2026-01-20 11:22 UTC (permalink / raw)
To: Alejandro Vallejo, xen-devel
Cc: Jan Beulich, Andrew Cooper, Roger Pau Monné, Jason Andryuk,
Stefano Stabellini
On Tue Jan 20, 2026 at 10:53 AM CET, Alejandro Vallejo wrote:
> Bus Locks are very costly and a VM left unchecked spamming instructions that
> lock the memory bus (e.g: unaligned atomic CAS) makes system perf take a
> nosedive. This patch is similar to BLD of VMX, but for SVM. It configures all
> VMRUNs so they automatically exit at the first encounter of a buslock event,
> effectively rate-limiting them.
Does this warrant an entry in the CHANGELOG?
Cheers,
Alejandro
>
> Cheers,
> Alejandro
>
> Alejandro Vallejo (2):
> x86/svm: Add infrastructure for Bus Lock Threshold
> x86/svm: Intercept Bus Locks for HVM guests
>
> xen/arch/x86/hvm/svm/svm.c | 5 +++++
> xen/arch/x86/hvm/svm/vmcb.c | 6 ++++++
> xen/arch/x86/hvm/svm/vmcb.h | 15 +++++++++++++--
> xen/arch/x86/include/asm/hvm/svm.h | 2 ++
> xen/arch/x86/include/asm/perfc_defn.h | 2 +-
> 5 files changed, 27 insertions(+), 3 deletions(-)
>
>
> base-commit: 7b3e1b4e848d34c9a5b6634009959a7b9dd42104
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PATCH 2/2] x86/svm: Intercept Bus Locks for HVM guests
2026-01-20 9:53 ` [PATCH 2/2] x86/svm: Intercept Bus Locks for HVM guests Alejandro Vallejo
@ 2026-01-20 13:11 ` Teddy Astie
2026-01-20 13:29 ` Jan Beulich
2026-01-20 13:18 ` Andrew Cooper
1 sibling, 1 reply; 26+ messages in thread
From: Teddy Astie @ 2026-01-20 13:11 UTC (permalink / raw)
To: Alejandro Vallejo, xen-devel
Cc: Jan Beulich, Andrew Cooper, Roger Pau Monné, Jason Andryuk,
Stefano Stabellini
Hello, some questions
Le 20/01/2026 à 10:56, Alejandro Vallejo a écrit :
> With the threshold initialised to 1 the guest exits at the first
> buslock. Initialising as zero is invalid and causes an immediate exit.
>
> Signed-off-by: Alejandro Vallejo <alejandro.garciavallejo@amd.com>
> ---
> xen/arch/x86/hvm/svm/svm.c | 4 ++++
> xen/arch/x86/hvm/svm/vmcb.c | 6 ++++++
> 2 files changed, 10 insertions(+)
>
> diff --git a/xen/arch/x86/hvm/svm/svm.c b/xen/arch/x86/hvm/svm/svm.c
> index 9748df87d8..dbb7f99d5e 100644
> --- a/xen/arch/x86/hvm/svm/svm.c
> +++ b/xen/arch/x86/hvm/svm/svm.c
> @@ -3087,6 +3087,10 @@ void asmlinkage svm_vmexit_handler(void)
> hvm_descriptor_access_intercept(0, 0, desc, write);
> break;
> }
> + case VMEXIT_BUSLOCK:
> + perfc_incr(buslock);
> + vmcb->bus_lock_thresh = 1;
> + break;
>
> default:
> unexpected_exit_type:
> diff --git a/xen/arch/x86/hvm/svm/vmcb.c b/xen/arch/x86/hvm/svm/vmcb.c
> index cbee10d046..7a19b1ab61 100644
> --- a/xen/arch/x86/hvm/svm/vmcb.c
> +++ b/xen/arch/x86/hvm/svm/vmcb.c
> @@ -66,6 +66,12 @@ static int construct_vmcb(struct vcpu *v)
> GENERAL2_INTERCEPT_XSETBV | GENERAL2_INTERCEPT_ICEBP |
> GENERAL2_INTERCEPT_RDPRU;
>
> + if ( cpu_has_bus_lock_thresh )
> + {
> + vmcb->_general3_intercepts = GENERAL3_INTERCEPT_BUS_LOCK_THRESH;
> + vmcb->bus_lock_thresh = 1; /* trigger immediately */
> + }
> +
> /* Intercept all debug-register writes. */
> vmcb->_dr_intercepts = ~0u;
>
According to APM,
INTERCEPT_BUS_LOCK_THRESH does
> Intercept bus lock operations when Bus Lock Threshold Counter is 0
I assume that when set to 0, we intercept all bus locks, so if set to 1,
every 2 bus lock (since we first go from 1 to 0, then at 0 we intercept
the next one) ?
I think we want that to be tunable, as intercepting all bus locks may be
too extreme we probably want to intercept every few ones instead.
Teddy
--
Teddy Astie | Vates XCP-ng Developer
XCP-ng & Xen Orchestra - Vates solutions
web: https://vates.tech
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PATCH 1/2] x86/svm: Add infrastructure for Bus Lock Threshold
2026-01-20 9:53 ` [PATCH 1/2] x86/svm: Add infrastructure " Alejandro Vallejo
@ 2026-01-20 13:12 ` Andrew Cooper
2026-01-20 13:57 ` Alejandro Vallejo
2026-01-20 13:19 ` Teddy Astie
1 sibling, 1 reply; 26+ messages in thread
From: Andrew Cooper @ 2026-01-20 13:12 UTC (permalink / raw)
To: Alejandro Vallejo, xen-devel
Cc: Andrew Cooper, Jan Beulich, Roger Pau Monné, Jason Andryuk,
Stefano Stabellini
On 20/01/2026 9:53 am, Alejandro Vallejo wrote:
> diff --git a/xen/arch/x86/hvm/svm/vmcb.h b/xen/arch/x86/hvm/svm/vmcb.h
> index ba554a9644..85e194f247 100644
> --- a/xen/arch/x86/hvm/svm/vmcb.h
> +++ b/xen/arch/x86/hvm/svm/vmcb.h
> @@ -65,6 +65,11 @@ enum GenericIntercept2bits
> GENERAL2_INTERCEPT_RDPRU = 1 << 14,
> };
>
> +/* general 2 intercepts */
> +enum GenericIntercept3bits
> +{
> + GENERAL3_INTERCEPT_BUS_LOCK_THRESH = 1 << 5,
> +};
Abbreviating thresh like this not great.
For the intercept, it can probably just be called BUS_LOCK. There's no
other form of such intercept.
>
> /* control register intercepts */
> enum CRInterceptBits
> @@ -289,6 +294,7 @@ enum VMEXIT_EXITCODE
> VMEXIT_MWAIT_CONDITIONAL= 140, /* 0x8c */
> VMEXIT_XSETBV = 141, /* 0x8d */
> VMEXIT_RDPRU = 142, /* 0x8e */
> + VMEXIT_BUSLOCK = 165, /* 0xa5 */
VMEXIT_BUS_LOCK for consistency.
> /* Remember to also update VMEXIT_NPF_PERFC! */
> VMEXIT_NPF = 1024, /* 0x400, nested paging fault */
> /* Remember to also update SVM_PERF_EXIT_REASON_SIZE! */
> @@ -405,7 +411,8 @@ struct vmcb_struct {
> u32 _exception_intercepts; /* offset 0x08 - cleanbit 0 */
> u32 _general1_intercepts; /* offset 0x0C - cleanbit 0 */
> u32 _general2_intercepts; /* offset 0x10 - cleanbit 0 */
> - u32 res01[10];
> + u32 _general3_intercepts; /* offset 0x14 - cleanbit 0 */
> + u32 res01[9];
> u16 _pause_filter_thresh; /* offset 0x3C - cleanbit 0 */
> u16 _pause_filter_count; /* offset 0x3E - cleanbit 0 */
> u64 _iopm_base_pa; /* offset 0x40 - cleanbit 1 */
> @@ -489,7 +496,10 @@ struct vmcb_struct {
> u64 nextrip; /* offset 0xC8 */
> u8 guest_ins_len; /* offset 0xD0 */
> u8 guest_ins[15]; /* offset 0xD1 */
> - u64 res10a[100]; /* offset 0xE0 pad to save area */
> + u64 res10a[8]; /* offset 0xE0 */
> + u16 bus_lock_thresh; /* offset 0x120 */
bus_lock_count, which is basically it's APM name anyway.
> diff --git a/xen/arch/x86/include/asm/hvm/svm.h b/xen/arch/x86/include/asm/hvm/svm.h
> index a6d7e4aed3..14fe4abf96 100644
> --- a/xen/arch/x86/include/asm/hvm/svm.h
> +++ b/xen/arch/x86/include/asm/hvm/svm.h
> @@ -37,6 +37,7 @@ extern u32 svm_feature_flags;
> #define SVM_FEATURE_VGIF 16 /* Virtual GIF */
> #define SVM_FEATURE_SSS 19 /* NPT Supervisor Shadow Stacks */
> #define SVM_FEATURE_SPEC_CTRL 20 /* MSR_SPEC_CTRL virtualisation */
> +#define SVM_FEATURE_BUS_LOCK_THRESH 29 /* Bus Lock Threshold */
>
> static inline bool cpu_has_svm_feature(unsigned int feat)
> {
> @@ -56,6 +57,7 @@ static inline bool cpu_has_svm_feature(unsigned int feat)
> #define cpu_has_svm_vloadsave cpu_has_svm_feature(SVM_FEATURE_VLOADSAVE)
> #define cpu_has_svm_sss cpu_has_svm_feature(SVM_FEATURE_SSS)
> #define cpu_has_svm_spec_ctrl cpu_has_svm_feature(SVM_FEATURE_SPEC_CTRL)
> +#define cpu_has_bus_lock_thresh cpu_has_svm_feature(SVM_FEATURE_BUS_LOCK_THRESH)
We actually discussed this on the x86 call just yesterday. This wants
an svm infix to match the others, and the thresh suffix can be dropped.
I can fix all of these on commit.
~Andrew
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PATCH 2/2] x86/svm: Intercept Bus Locks for HVM guests
2026-01-20 9:53 ` [PATCH 2/2] x86/svm: Intercept Bus Locks for HVM guests Alejandro Vallejo
2026-01-20 13:11 ` Teddy Astie
@ 2026-01-20 13:18 ` Andrew Cooper
2026-01-20 13:27 ` Jan Beulich
1 sibling, 1 reply; 26+ messages in thread
From: Andrew Cooper @ 2026-01-20 13:18 UTC (permalink / raw)
To: Alejandro Vallejo, xen-devel
Cc: Andrew Cooper, Jan Beulich, Roger Pau Monné, Jason Andryuk,
Stefano Stabellini
On 20/01/2026 9:53 am, Alejandro Vallejo wrote:
> With the threshold initialised to 1 the guest exits at the first
> buslock. Initialising as zero is invalid and causes an immediate exit.
What do you mean by this? A VMRUN failure, or a livelock?
>
> Signed-off-by: Alejandro Vallejo <alejandro.garciavallejo@amd.com>
> ---
> xen/arch/x86/hvm/svm/svm.c | 4 ++++
> xen/arch/x86/hvm/svm/vmcb.c | 6 ++++++
> 2 files changed, 10 insertions(+)
>
> diff --git a/xen/arch/x86/hvm/svm/svm.c b/xen/arch/x86/hvm/svm/svm.c
> index 9748df87d8..dbb7f99d5e 100644
> --- a/xen/arch/x86/hvm/svm/svm.c
> +++ b/xen/arch/x86/hvm/svm/svm.c
> @@ -3087,6 +3087,10 @@ void asmlinkage svm_vmexit_handler(void)
> hvm_descriptor_access_intercept(0, 0, desc, write);
> break;
> }
Blank line.
> + case VMEXIT_BUSLOCK:
> + perfc_incr(buslock);
> + vmcb->bus_lock_thresh = 1;
> + break;
>
> default:
> unexpected_exit_type:
> diff --git a/xen/arch/x86/hvm/svm/vmcb.c b/xen/arch/x86/hvm/svm/vmcb.c
> index cbee10d046..7a19b1ab61 100644
> --- a/xen/arch/x86/hvm/svm/vmcb.c
> +++ b/xen/arch/x86/hvm/svm/vmcb.c
> @@ -66,6 +66,12 @@ static int construct_vmcb(struct vcpu *v)
> GENERAL2_INTERCEPT_XSETBV | GENERAL2_INTERCEPT_ICEBP |
> GENERAL2_INTERCEPT_RDPRU;
>
> + if ( cpu_has_bus_lock_thresh )
> + {
> + vmcb->_general3_intercepts = GENERAL3_INTERCEPT_BUS_LOCK_THRESH;
|=
> + vmcb->bus_lock_thresh = 1; /* trigger immediately */
Really? The APM states:
On processors that support Bus Lock Threshold (indicated by CPUID
Fn8000_000A_EDX[29] BusLockThreshold=1), the VMCB provides a Bus Lock
Threshold enable bit and an unsigned 16-bit Bus Lock Threshold count. On
VMRUN, this value is loaded into an internal count register. Before the
processor executes a bus lock in the guest, it checks the value of this
register. If the value is greater than 0, the processor executes the bus
lock successfully and decrements the count. If the value is 0, the bus
lock is not executed and a #VMEXIT to the VMM is taken.
So according to the APM, setting the count to 1 will permit one bus lock
then exit (fault style) immediately before the next. This also says
that a count of 0 is a legal state.
~Andrew
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PATCH 1/2] x86/svm: Add infrastructure for Bus Lock Threshold
2026-01-20 9:53 ` [PATCH 1/2] x86/svm: Add infrastructure " Alejandro Vallejo
2026-01-20 13:12 ` Andrew Cooper
@ 2026-01-20 13:19 ` Teddy Astie
2026-01-20 13:30 ` Jan Beulich
2026-01-20 13:58 ` Alejandro Vallejo
1 sibling, 2 replies; 26+ messages in thread
From: Teddy Astie @ 2026-01-20 13:19 UTC (permalink / raw)
To: Alejandro Vallejo, xen-devel
Cc: Jan Beulich, Andrew Cooper, Roger Pau Monné, Jason Andryuk,
Stefano Stabellini
Hello,
Le 20/01/2026 à 10:56, Alejandro Vallejo a écrit :
> Add missing scaffolding to enable BusLock Threshold. That is:
>
> * Add general_intercepts_3.
> * Add missing VMEXIT
> * Adjust NPF perf counter base to immediately after the buslock counter
>
> Signed-off-by: Alejandro Vallejo <alejandro.garciavallejo@amd.com>
> ---
> xen/arch/x86/hvm/svm/svm.c | 1 +
> xen/arch/x86/hvm/svm/vmcb.h | 15 +++++++++++++--
> xen/arch/x86/include/asm/hvm/svm.h | 2 ++
> xen/arch/x86/include/asm/perfc_defn.h | 2 +-
> 4 files changed, 17 insertions(+), 3 deletions(-)
>
> diff --git a/xen/arch/x86/hvm/svm/svm.c b/xen/arch/x86/hvm/svm/svm.c
> index 5d23603fc1..9748df87d8 100644
> --- a/xen/arch/x86/hvm/svm/svm.c
> +++ b/xen/arch/x86/hvm/svm/svm.c
> @@ -2524,6 +2524,7 @@ const struct hvm_function_table * __init start_svm(void)
> P(cpu_has_tsc_ratio, "TSC Rate MSR");
> P(cpu_has_svm_sss, "NPT Supervisor Shadow Stack");
> P(cpu_has_svm_spec_ctrl, "MSR_SPEC_CTRL virtualisation");
> + P(cpu_has_bus_lock_thresh, "BusLock-Intercept Filter");
> #undef P
>
> if ( !printed )
> diff --git a/xen/arch/x86/hvm/svm/vmcb.h b/xen/arch/x86/hvm/svm/vmcb.h
> index ba554a9644..85e194f247 100644
> --- a/xen/arch/x86/hvm/svm/vmcb.h
> +++ b/xen/arch/x86/hvm/svm/vmcb.h
> @@ -65,6 +65,11 @@ enum GenericIntercept2bits
> GENERAL2_INTERCEPT_RDPRU = 1 << 14,
> };
>
> +/* general 2 intercepts */
nit, you want to says general 3 intercepts
> +enum GenericIntercept3bits
> +{
> + GENERAL3_INTERCEPT_BUS_LOCK_THRESH = 1 << 5,
> +};
>
> /* control register intercepts */
> enum CRInterceptBits
> @@ -289,6 +294,7 @@ enum VMEXIT_EXITCODE
> VMEXIT_MWAIT_CONDITIONAL= 140, /* 0x8c */
> VMEXIT_XSETBV = 141, /* 0x8d */
> VMEXIT_RDPRU = 142, /* 0x8e */
> + VMEXIT_BUSLOCK = 165, /* 0xa5 */
> /* Remember to also update VMEXIT_NPF_PERFC! */
> VMEXIT_NPF = 1024, /* 0x400, nested paging fault */
> /* Remember to also update SVM_PERF_EXIT_REASON_SIZE! */
> @@ -405,7 +411,8 @@ struct vmcb_struct {
> u32 _exception_intercepts; /* offset 0x08 - cleanbit 0 */
> u32 _general1_intercepts; /* offset 0x0C - cleanbit 0 */
> u32 _general2_intercepts; /* offset 0x10 - cleanbit 0 */
> - u32 res01[10];
> + u32 _general3_intercepts; /* offset 0x14 - cleanbit 0 */
> + u32 res01[9];
> u16 _pause_filter_thresh; /* offset 0x3C - cleanbit 0 */
> u16 _pause_filter_count; /* offset 0x3E - cleanbit 0 */
> u64 _iopm_base_pa; /* offset 0x40 - cleanbit 1 */
> @@ -489,7 +496,10 @@ struct vmcb_struct {
> u64 nextrip; /* offset 0xC8 */
> u8 guest_ins_len; /* offset 0xD0 */
> u8 guest_ins[15]; /* offset 0xD1 */
> - u64 res10a[100]; /* offset 0xE0 pad to save area */
> + u64 res10a[8]; /* offset 0xE0 */
> + u16 bus_lock_thresh; /* offset 0x120 */
> + u16 res10b[3]; /* offset 0x122 */
> + u64 res10c[91]; /* offset 0x128 pad to save area */
>
> union {
> struct segment_register sreg[6];
> @@ -583,6 +593,7 @@ VMCB_ACCESSORS(dr_intercepts, intercepts)
> VMCB_ACCESSORS(exception_intercepts, intercepts)
> VMCB_ACCESSORS(general1_intercepts, intercepts)
> VMCB_ACCESSORS(general2_intercepts, intercepts)
> +VMCB_ACCESSORS(general3_intercepts, intercepts)
> VMCB_ACCESSORS(pause_filter_count, intercepts)
> VMCB_ACCESSORS(pause_filter_thresh, intercepts)
> VMCB_ACCESSORS(tsc_offset, intercepts)
> diff --git a/xen/arch/x86/include/asm/hvm/svm.h b/xen/arch/x86/include/asm/hvm/svm.h
> index a6d7e4aed3..14fe4abf96 100644
> --- a/xen/arch/x86/include/asm/hvm/svm.h
> +++ b/xen/arch/x86/include/asm/hvm/svm.h
> @@ -37,6 +37,7 @@ extern u32 svm_feature_flags;
> #define SVM_FEATURE_VGIF 16 /* Virtual GIF */
> #define SVM_FEATURE_SSS 19 /* NPT Supervisor Shadow Stacks */
> #define SVM_FEATURE_SPEC_CTRL 20 /* MSR_SPEC_CTRL virtualisation */
> +#define SVM_FEATURE_BUS_LOCK_THRESH 29 /* Bus Lock Threshold */
>
> static inline bool cpu_has_svm_feature(unsigned int feat)
> {
> @@ -56,6 +57,7 @@ static inline bool cpu_has_svm_feature(unsigned int feat)
> #define cpu_has_svm_vloadsave cpu_has_svm_feature(SVM_FEATURE_VLOADSAVE)
> #define cpu_has_svm_sss cpu_has_svm_feature(SVM_FEATURE_SSS)
> #define cpu_has_svm_spec_ctrl cpu_has_svm_feature(SVM_FEATURE_SPEC_CTRL)
> +#define cpu_has_bus_lock_thresh cpu_has_svm_feature(SVM_FEATURE_BUS_LOCK_THRESH)
>
> #define MSR_INTERCEPT_NONE 0
> #define MSR_INTERCEPT_READ 1
> diff --git a/xen/arch/x86/include/asm/perfc_defn.h b/xen/arch/x86/include/asm/perfc_defn.h
> index d6127cb91e..ac7439b992 100644
> --- a/xen/arch/x86/include/asm/perfc_defn.h
> +++ b/xen/arch/x86/include/asm/perfc_defn.h
> @@ -7,7 +7,7 @@ PERFCOUNTER_ARRAY(exceptions, "exceptions", 32)
> #ifdef CONFIG_HVM
>
> #define VMX_PERF_EXIT_REASON_SIZE 76
> -#define VMEXIT_NPF_PERFC 143
> +#define VMEXIT_NPF_PERFC 166
> #define SVM_PERF_EXIT_REASON_SIZE (VMEXIT_NPF_PERFC + 1)
> PERFCOUNTER_ARRAY(vmexits, "vmexits",
> MAX(VMX_PERF_EXIT_REASON_SIZE, SVM_PERF_EXIT_REASON_SIZE))
With that changed, Reviewed-by: Teddy Astie <teddy.astie@vates.tech>
--
Teddy Astie | Vates XCP-ng Developer
XCP-ng & Xen Orchestra - Vates solutions
web: https://vates.tech
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PATCH 0/2] x86/svm: Add support for Bus Lock Threshold
2026-01-20 11:22 ` [PATCH 0/2] x86/svm: Add support for Bus Lock Threshold Alejandro Vallejo
@ 2026-01-20 13:21 ` Andrew Cooper
0 siblings, 0 replies; 26+ messages in thread
From: Andrew Cooper @ 2026-01-20 13:21 UTC (permalink / raw)
To: Alejandro Vallejo, xen-devel
Cc: Andrew Cooper, Jan Beulich, Roger Pau Monné, Jason Andryuk,
Stefano Stabellini
On 20/01/2026 11:22 am, Alejandro Vallejo wrote:
> On Tue Jan 20, 2026 at 10:53 AM CET, Alejandro Vallejo wrote:
>> Bus Locks are very costly and a VM left unchecked spamming instructions that
>> lock the memory bus (e.g: unaligned atomic CAS) makes system perf take a
>> nosedive. This patch is similar to BLD of VMX, but for SVM. It configures all
>> VMRUNs so they automatically exit at the first encounter of a buslock event,
>> effectively rate-limiting them.
> Does this warrant an entry in the CHANGELOG?
The Intel side got one (back in 4.18 and in the section about Sapphire
Rapids).
~Andrew
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PATCH 2/2] x86/svm: Intercept Bus Locks for HVM guests
2026-01-20 13:18 ` Andrew Cooper
@ 2026-01-20 13:27 ` Jan Beulich
2026-01-20 13:29 ` Andrew Cooper
0 siblings, 1 reply; 26+ messages in thread
From: Jan Beulich @ 2026-01-20 13:27 UTC (permalink / raw)
To: Andrew Cooper
Cc: Roger Pau Monné, Jason Andryuk, Alejandro Vallejo, xen-devel,
Stefano Stabellini
On 20.01.2026 14:18, Andrew Cooper wrote:
> On 20/01/2026 9:53 am, Alejandro Vallejo wrote:
>> --- a/xen/arch/x86/hvm/svm/vmcb.c
>> +++ b/xen/arch/x86/hvm/svm/vmcb.c
>> @@ -66,6 +66,12 @@ static int construct_vmcb(struct vcpu *v)
>> GENERAL2_INTERCEPT_XSETBV | GENERAL2_INTERCEPT_ICEBP |
>> GENERAL2_INTERCEPT_RDPRU;
>>
>> + if ( cpu_has_bus_lock_thresh )
>> + {
>> + vmcb->_general3_intercepts = GENERAL3_INTERCEPT_BUS_LOCK_THRESH;
>
> |=
>
>> + vmcb->bus_lock_thresh = 1; /* trigger immediately */
>
> Really? The APM states:
>
> On processors that support Bus Lock Threshold (indicated by CPUID
> Fn8000_000A_EDX[29] BusLockThreshold=1), the VMCB provides a Bus Lock
> Threshold enable bit and an unsigned 16-bit Bus Lock Threshold count. On
> VMRUN, this value is loaded into an internal count register. Before the
> processor executes a bus lock in the guest, it checks the value of this
> register. If the value is greater than 0, the processor executes the bus
> lock successfully and decrements the count. If the value is 0, the bus
> lock is not executed and a #VMEXIT to the VMM is taken.
>
> So according to the APM, setting the count to 1 will permit one bus lock
> then exit (fault style) immediately before the next. This also says
> that a count of 0 is a legal state.
But then you'd livelock the guest as soon as it uses a bus lock. Are you
suggesting to set to 1 in response to a bus lock exit, and keep at 0 at
all other times?
Jan
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PATCH 2/2] x86/svm: Intercept Bus Locks for HVM guests
2026-01-20 13:11 ` Teddy Astie
@ 2026-01-20 13:29 ` Jan Beulich
2026-01-20 14:41 ` Alejandro Vallejo
0 siblings, 1 reply; 26+ messages in thread
From: Jan Beulich @ 2026-01-20 13:29 UTC (permalink / raw)
To: Teddy Astie
Cc: Andrew Cooper, Roger Pau Monné, Jason Andryuk,
Stefano Stabellini, Alejandro Vallejo, xen-devel
On 20.01.2026 14:11, Teddy Astie wrote:
> Le 20/01/2026 à 10:56, Alejandro Vallejo a écrit :
>> --- a/xen/arch/x86/hvm/svm/vmcb.c
>> +++ b/xen/arch/x86/hvm/svm/vmcb.c
>> @@ -66,6 +66,12 @@ static int construct_vmcb(struct vcpu *v)
>> GENERAL2_INTERCEPT_XSETBV | GENERAL2_INTERCEPT_ICEBP |
>> GENERAL2_INTERCEPT_RDPRU;
>>
>> + if ( cpu_has_bus_lock_thresh )
>> + {
>> + vmcb->_general3_intercepts = GENERAL3_INTERCEPT_BUS_LOCK_THRESH;
>> + vmcb->bus_lock_thresh = 1; /* trigger immediately */
>> + }
>> +
>> /* Intercept all debug-register writes. */
>> vmcb->_dr_intercepts = ~0u;
>>
>
> According to APM,
>
> INTERCEPT_BUS_LOCK_THRESH does
> > Intercept bus lock operations when Bus Lock Threshold Counter is 0
>
> I assume that when set to 0, we intercept all bus locks, so if set to 1,
> every 2 bus lock (since we first go from 1 to 0, then at 0 we intercept
> the next one) ?
>
> I think we want that to be tunable, as intercepting all bus locks may be
> too extreme we probably want to intercept every few ones instead.
Otoh bus locks (as opposed to cache locks) would better be rare, or else
perhaps such a guest deserves some extra slowing down?
Jan
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PATCH 2/2] x86/svm: Intercept Bus Locks for HVM guests
2026-01-20 13:27 ` Jan Beulich
@ 2026-01-20 13:29 ` Andrew Cooper
2026-01-20 13:34 ` Jan Beulich
0 siblings, 1 reply; 26+ messages in thread
From: Andrew Cooper @ 2026-01-20 13:29 UTC (permalink / raw)
To: Jan Beulich
Cc: Andrew Cooper, Roger Pau Monné, Jason Andryuk,
Alejandro Vallejo, xen-devel, Stefano Stabellini
On 20/01/2026 1:27 pm, Jan Beulich wrote:
> On 20.01.2026 14:18, Andrew Cooper wrote:
>> On 20/01/2026 9:53 am, Alejandro Vallejo wrote:
>>> --- a/xen/arch/x86/hvm/svm/vmcb.c
>>> +++ b/xen/arch/x86/hvm/svm/vmcb.c
>>> @@ -66,6 +66,12 @@ static int construct_vmcb(struct vcpu *v)
>>> GENERAL2_INTERCEPT_XSETBV | GENERAL2_INTERCEPT_ICEBP |
>>> GENERAL2_INTERCEPT_RDPRU;
>>>
>>> + if ( cpu_has_bus_lock_thresh )
>>> + {
>>> + vmcb->_general3_intercepts = GENERAL3_INTERCEPT_BUS_LOCK_THRESH;
>> |=
>>
>>> + vmcb->bus_lock_thresh = 1; /* trigger immediately */
>> Really? The APM states:
>>
>> On processors that support Bus Lock Threshold (indicated by CPUID
>> Fn8000_000A_EDX[29] BusLockThreshold=1), the VMCB provides a Bus Lock
>> Threshold enable bit and an unsigned 16-bit Bus Lock Threshold count. On
>> VMRUN, this value is loaded into an internal count register. Before the
>> processor executes a bus lock in the guest, it checks the value of this
>> register. If the value is greater than 0, the processor executes the bus
>> lock successfully and decrements the count. If the value is 0, the bus
>> lock is not executed and a #VMEXIT to the VMM is taken.
>>
>> So according to the APM, setting the count to 1 will permit one bus lock
>> then exit (fault style) immediately before the next. This also says
>> that a count of 0 is a legal state.
> But then you'd livelock the guest as soon as it uses a bus lock. Are you
> suggesting to set to 1 in response to a bus lock exit, and keep at 0 at
> all other times?
I should have been clearer. I'm complaining at the "trigger
immediately" comment, because I don't think that's a correct statement
of how hardware behaves.
Simply dropping the comment would be ok, but I'd also like to understand
hardware behaviour if it differs from what the APM says.
~Andrew
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PATCH 1/2] x86/svm: Add infrastructure for Bus Lock Threshold
2026-01-20 13:19 ` Teddy Astie
@ 2026-01-20 13:30 ` Jan Beulich
2026-01-21 12:40 ` Alejandro Vallejo
2026-01-20 13:58 ` Alejandro Vallejo
1 sibling, 1 reply; 26+ messages in thread
From: Jan Beulich @ 2026-01-20 13:30 UTC (permalink / raw)
To: Teddy Astie, Alejandro Vallejo
Cc: Andrew Cooper, Roger Pau Monné, Jason Andryuk,
Stefano Stabellini, xen-devel
On 20.01.2026 14:19, Teddy Astie wrote:
> Le 20/01/2026 à 10:56, Alejandro Vallejo a écrit :
>> --- a/xen/arch/x86/hvm/svm/vmcb.h
>> +++ b/xen/arch/x86/hvm/svm/vmcb.h
>> @@ -65,6 +65,11 @@ enum GenericIntercept2bits
>> GENERAL2_INTERCEPT_RDPRU = 1 << 14,
>> };
>>
>> +/* general 2 intercepts */
>
> nit, you want to says general 3 intercepts
And then, further nit, also get comment style right.
Jan
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PATCH 2/2] x86/svm: Intercept Bus Locks for HVM guests
2026-01-20 13:29 ` Andrew Cooper
@ 2026-01-20 13:34 ` Jan Beulich
2026-01-20 14:11 ` Andrew Cooper
0 siblings, 1 reply; 26+ messages in thread
From: Jan Beulich @ 2026-01-20 13:34 UTC (permalink / raw)
To: Andrew Cooper
Cc: Roger Pau Monné, Jason Andryuk, Alejandro Vallejo, xen-devel,
Stefano Stabellini
On 20.01.2026 14:29, Andrew Cooper wrote:
> On 20/01/2026 1:27 pm, Jan Beulich wrote:
>> On 20.01.2026 14:18, Andrew Cooper wrote:
>>> On 20/01/2026 9:53 am, Alejandro Vallejo wrote:
>>>> --- a/xen/arch/x86/hvm/svm/vmcb.c
>>>> +++ b/xen/arch/x86/hvm/svm/vmcb.c
>>>> @@ -66,6 +66,12 @@ static int construct_vmcb(struct vcpu *v)
>>>> GENERAL2_INTERCEPT_XSETBV | GENERAL2_INTERCEPT_ICEBP |
>>>> GENERAL2_INTERCEPT_RDPRU;
>>>>
>>>> + if ( cpu_has_bus_lock_thresh )
>>>> + {
>>>> + vmcb->_general3_intercepts = GENERAL3_INTERCEPT_BUS_LOCK_THRESH;
>>> |=
>>>
>>>> + vmcb->bus_lock_thresh = 1; /* trigger immediately */
>>> Really? The APM states:
>>>
>>> On processors that support Bus Lock Threshold (indicated by CPUID
>>> Fn8000_000A_EDX[29] BusLockThreshold=1), the VMCB provides a Bus Lock
>>> Threshold enable bit and an unsigned 16-bit Bus Lock Threshold count. On
>>> VMRUN, this value is loaded into an internal count register. Before the
>>> processor executes a bus lock in the guest, it checks the value of this
>>> register. If the value is greater than 0, the processor executes the bus
>>> lock successfully and decrements the count. If the value is 0, the bus
>>> lock is not executed and a #VMEXIT to the VMM is taken.
>>>
>>> So according to the APM, setting the count to 1 will permit one bus lock
>>> then exit (fault style) immediately before the next. This also says
>>> that a count of 0 is a legal state.
>> But then you'd livelock the guest as soon as it uses a bus lock. Are you
>> suggesting to set to 1 in response to a bus lock exit, and keep at 0 at
>> all other times?
>
> I should have been clearer. I'm complaining at the "trigger
> immediately" comment, because I don't think that's a correct statement
> of how hardware behaves.
In turn I should have looked at the patch itself before commenting. The
other setting to 1 is what makes sense, and what ought to prevent a
livelock. The one here indeed raises questions.
Jan
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PATCH 1/2] x86/svm: Add infrastructure for Bus Lock Threshold
2026-01-20 13:12 ` Andrew Cooper
@ 2026-01-20 13:57 ` Alejandro Vallejo
0 siblings, 0 replies; 26+ messages in thread
From: Alejandro Vallejo @ 2026-01-20 13:57 UTC (permalink / raw)
To: Andrew Cooper, xen-devel
Cc: Jan Beulich, Roger Pau Monné, Jason Andryuk,
Stefano Stabellini
On Tue Jan 20, 2026 at 2:12 PM CET, Andrew Cooper wrote:
> On 20/01/2026 9:53 am, Alejandro Vallejo wrote:
>> diff --git a/xen/arch/x86/hvm/svm/vmcb.h b/xen/arch/x86/hvm/svm/vmcb.h
>> index ba554a9644..85e194f247 100644
>> --- a/xen/arch/x86/hvm/svm/vmcb.h
>> +++ b/xen/arch/x86/hvm/svm/vmcb.h
>> @@ -65,6 +65,11 @@ enum GenericIntercept2bits
>> GENERAL2_INTERCEPT_RDPRU = 1 << 14,
>> };
>>
>> +/* general 2 intercepts */
>> +enum GenericIntercept3bits
>> +{
>> + GENERAL3_INTERCEPT_BUS_LOCK_THRESH = 1 << 5,
>> +};
>
> Abbreviating thresh like this not great.
>
> For the intercept, it can probably just be called BUS_LOCK. There's no
> other form of such intercept.
>
>>
>> /* control register intercepts */
>> enum CRInterceptBits
>> @@ -289,6 +294,7 @@ enum VMEXIT_EXITCODE
>> VMEXIT_MWAIT_CONDITIONAL= 140, /* 0x8c */
>> VMEXIT_XSETBV = 141, /* 0x8d */
>> VMEXIT_RDPRU = 142, /* 0x8e */
>> + VMEXIT_BUSLOCK = 165, /* 0xa5 */
>
> VMEXIT_BUS_LOCK for consistency.
>
>> /* Remember to also update VMEXIT_NPF_PERFC! */
>> VMEXIT_NPF = 1024, /* 0x400, nested paging fault */
>> /* Remember to also update SVM_PERF_EXIT_REASON_SIZE! */
>> @@ -405,7 +411,8 @@ struct vmcb_struct {
>> u32 _exception_intercepts; /* offset 0x08 - cleanbit 0 */
>> u32 _general1_intercepts; /* offset 0x0C - cleanbit 0 */
>> u32 _general2_intercepts; /* offset 0x10 - cleanbit 0 */
>> - u32 res01[10];
>> + u32 _general3_intercepts; /* offset 0x14 - cleanbit 0 */
>> + u32 res01[9];
>> u16 _pause_filter_thresh; /* offset 0x3C - cleanbit 0 */
>> u16 _pause_filter_count; /* offset 0x3E - cleanbit 0 */
>> u64 _iopm_base_pa; /* offset 0x40 - cleanbit 1 */
>> @@ -489,7 +496,10 @@ struct vmcb_struct {
>> u64 nextrip; /* offset 0xC8 */
>> u8 guest_ins_len; /* offset 0xD0 */
>> u8 guest_ins[15]; /* offset 0xD1 */
>> - u64 res10a[100]; /* offset 0xE0 pad to save area */
>> + u64 res10a[8]; /* offset 0xE0 */
>> + u16 bus_lock_thresh; /* offset 0x120 */
>
> bus_lock_count, which is basically it's APM name anyway.
>
>> diff --git a/xen/arch/x86/include/asm/hvm/svm.h b/xen/arch/x86/include/asm/hvm/svm.h
>> index a6d7e4aed3..14fe4abf96 100644
>> --- a/xen/arch/x86/include/asm/hvm/svm.h
>> +++ b/xen/arch/x86/include/asm/hvm/svm.h
>> @@ -37,6 +37,7 @@ extern u32 svm_feature_flags;
>> #define SVM_FEATURE_VGIF 16 /* Virtual GIF */
>> #define SVM_FEATURE_SSS 19 /* NPT Supervisor Shadow Stacks */
>> #define SVM_FEATURE_SPEC_CTRL 20 /* MSR_SPEC_CTRL virtualisation */
>> +#define SVM_FEATURE_BUS_LOCK_THRESH 29 /* Bus Lock Threshold */
>>
>> static inline bool cpu_has_svm_feature(unsigned int feat)
>> {
>> @@ -56,6 +57,7 @@ static inline bool cpu_has_svm_feature(unsigned int feat)
>> #define cpu_has_svm_vloadsave cpu_has_svm_feature(SVM_FEATURE_VLOADSAVE)
>> #define cpu_has_svm_sss cpu_has_svm_feature(SVM_FEATURE_SSS)
>> #define cpu_has_svm_spec_ctrl cpu_has_svm_feature(SVM_FEATURE_SPEC_CTRL)
>> +#define cpu_has_bus_lock_thresh cpu_has_svm_feature(SVM_FEATURE_BUS_LOCK_THRESH)
>
> We actually discussed this on the x86 call just yesterday. This wants
> an svm infix to match the others, and the thresh suffix can be dropped.
>
> I can fix all of these on commit.
Fine by me. Is that an implicit R-by?
Cheers,
Alejandro
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PATCH 1/2] x86/svm: Add infrastructure for Bus Lock Threshold
2026-01-20 13:19 ` Teddy Astie
2026-01-20 13:30 ` Jan Beulich
@ 2026-01-20 13:58 ` Alejandro Vallejo
1 sibling, 0 replies; 26+ messages in thread
From: Alejandro Vallejo @ 2026-01-20 13:58 UTC (permalink / raw)
To: Teddy Astie, xen-devel
Cc: Jan Beulich, Andrew Cooper, Roger Pau Monné, Jason Andryuk,
Stefano Stabellini
On Tue Jan 20, 2026 at 2:18 PM CET, Teddy Astie wrote:
> Hello,
>
> Le 20/01/2026 à 10:56, Alejandro Vallejo a écrit :
>> Add missing scaffolding to enable BusLock Threshold. That is:
>>
>> * Add general_intercepts_3.
>> * Add missing VMEXIT
>> * Adjust NPF perf counter base to immediately after the buslock counter
>>
>> Signed-off-by: Alejandro Vallejo <alejandro.garciavallejo@amd.com>
>> ---
>> xen/arch/x86/hvm/svm/svm.c | 1 +
>> xen/arch/x86/hvm/svm/vmcb.h | 15 +++++++++++++--
>> xen/arch/x86/include/asm/hvm/svm.h | 2 ++
>> xen/arch/x86/include/asm/perfc_defn.h | 2 +-
>> 4 files changed, 17 insertions(+), 3 deletions(-)
>>
>> diff --git a/xen/arch/x86/hvm/svm/svm.c b/xen/arch/x86/hvm/svm/svm.c
>> index 5d23603fc1..9748df87d8 100644
>> --- a/xen/arch/x86/hvm/svm/svm.c
>> +++ b/xen/arch/x86/hvm/svm/svm.c
>> @@ -2524,6 +2524,7 @@ const struct hvm_function_table * __init start_svm(void)
>> P(cpu_has_tsc_ratio, "TSC Rate MSR");
>> P(cpu_has_svm_sss, "NPT Supervisor Shadow Stack");
>> P(cpu_has_svm_spec_ctrl, "MSR_SPEC_CTRL virtualisation");
>> + P(cpu_has_bus_lock_thresh, "BusLock-Intercept Filter");
>> #undef P
>>
>> if ( !printed )
>> diff --git a/xen/arch/x86/hvm/svm/vmcb.h b/xen/arch/x86/hvm/svm/vmcb.h
>> index ba554a9644..85e194f247 100644
>> --- a/xen/arch/x86/hvm/svm/vmcb.h
>> +++ b/xen/arch/x86/hvm/svm/vmcb.h
>> @@ -65,6 +65,11 @@ enum GenericIntercept2bits
>> GENERAL2_INTERCEPT_RDPRU = 1 << 14,
>> };
>>
>> +/* general 2 intercepts */
>
> nit, you want to says general 3 intercepts
I do. Well spotted
>
>> +enum GenericIntercept3bits
>> +{
>> + GENERAL3_INTERCEPT_BUS_LOCK_THRESH = 1 << 5,
>> +};
>>
>> /* control register intercepts */
>> enum CRInterceptBits
>> @@ -289,6 +294,7 @@ enum VMEXIT_EXITCODE
>> VMEXIT_MWAIT_CONDITIONAL= 140, /* 0x8c */
>> VMEXIT_XSETBV = 141, /* 0x8d */
>> VMEXIT_RDPRU = 142, /* 0x8e */
>> + VMEXIT_BUSLOCK = 165, /* 0xa5 */
>> /* Remember to also update VMEXIT_NPF_PERFC! */
>> VMEXIT_NPF = 1024, /* 0x400, nested paging fault */
>> /* Remember to also update SVM_PERF_EXIT_REASON_SIZE! */
>> @@ -405,7 +411,8 @@ struct vmcb_struct {
>> u32 _exception_intercepts; /* offset 0x08 - cleanbit 0 */
>> u32 _general1_intercepts; /* offset 0x0C - cleanbit 0 */
>> u32 _general2_intercepts; /* offset 0x10 - cleanbit 0 */
>> - u32 res01[10];
>> + u32 _general3_intercepts; /* offset 0x14 - cleanbit 0 */
>> + u32 res01[9];
>> u16 _pause_filter_thresh; /* offset 0x3C - cleanbit 0 */
>> u16 _pause_filter_count; /* offset 0x3E - cleanbit 0 */
>> u64 _iopm_base_pa; /* offset 0x40 - cleanbit 1 */
>> @@ -489,7 +496,10 @@ struct vmcb_struct {
>> u64 nextrip; /* offset 0xC8 */
>> u8 guest_ins_len; /* offset 0xD0 */
>> u8 guest_ins[15]; /* offset 0xD1 */
>> - u64 res10a[100]; /* offset 0xE0 pad to save area */
>> + u64 res10a[8]; /* offset 0xE0 */
>> + u16 bus_lock_thresh; /* offset 0x120 */
>> + u16 res10b[3]; /* offset 0x122 */
>> + u64 res10c[91]; /* offset 0x128 pad to save area */
>>
>> union {
>> struct segment_register sreg[6];
>> @@ -583,6 +593,7 @@ VMCB_ACCESSORS(dr_intercepts, intercepts)
>> VMCB_ACCESSORS(exception_intercepts, intercepts)
>> VMCB_ACCESSORS(general1_intercepts, intercepts)
>> VMCB_ACCESSORS(general2_intercepts, intercepts)
>> +VMCB_ACCESSORS(general3_intercepts, intercepts)
>> VMCB_ACCESSORS(pause_filter_count, intercepts)
>> VMCB_ACCESSORS(pause_filter_thresh, intercepts)
>> VMCB_ACCESSORS(tsc_offset, intercepts)
>> diff --git a/xen/arch/x86/include/asm/hvm/svm.h b/xen/arch/x86/include/asm/hvm/svm.h
>> index a6d7e4aed3..14fe4abf96 100644
>> --- a/xen/arch/x86/include/asm/hvm/svm.h
>> +++ b/xen/arch/x86/include/asm/hvm/svm.h
>> @@ -37,6 +37,7 @@ extern u32 svm_feature_flags;
>> #define SVM_FEATURE_VGIF 16 /* Virtual GIF */
>> #define SVM_FEATURE_SSS 19 /* NPT Supervisor Shadow Stacks */
>> #define SVM_FEATURE_SPEC_CTRL 20 /* MSR_SPEC_CTRL virtualisation */
>> +#define SVM_FEATURE_BUS_LOCK_THRESH 29 /* Bus Lock Threshold */
>>
>> static inline bool cpu_has_svm_feature(unsigned int feat)
>> {
>> @@ -56,6 +57,7 @@ static inline bool cpu_has_svm_feature(unsigned int feat)
>> #define cpu_has_svm_vloadsave cpu_has_svm_feature(SVM_FEATURE_VLOADSAVE)
>> #define cpu_has_svm_sss cpu_has_svm_feature(SVM_FEATURE_SSS)
>> #define cpu_has_svm_spec_ctrl cpu_has_svm_feature(SVM_FEATURE_SPEC_CTRL)
>> +#define cpu_has_bus_lock_thresh cpu_has_svm_feature(SVM_FEATURE_BUS_LOCK_THRESH)
>>
>> #define MSR_INTERCEPT_NONE 0
>> #define MSR_INTERCEPT_READ 1
>> diff --git a/xen/arch/x86/include/asm/perfc_defn.h b/xen/arch/x86/include/asm/perfc_defn.h
>> index d6127cb91e..ac7439b992 100644
>> --- a/xen/arch/x86/include/asm/perfc_defn.h
>> +++ b/xen/arch/x86/include/asm/perfc_defn.h
>> @@ -7,7 +7,7 @@ PERFCOUNTER_ARRAY(exceptions, "exceptions", 32)
>> #ifdef CONFIG_HVM
>>
>> #define VMX_PERF_EXIT_REASON_SIZE 76
>> -#define VMEXIT_NPF_PERFC 143
>> +#define VMEXIT_NPF_PERFC 166
>> #define SVM_PERF_EXIT_REASON_SIZE (VMEXIT_NPF_PERFC + 1)
>> PERFCOUNTER_ARRAY(vmexits, "vmexits",
>> MAX(VMX_PERF_EXIT_REASON_SIZE, SVM_PERF_EXIT_REASON_SIZE))
>
> With that changed, Reviewed-by: Teddy Astie <teddy.astie@vates.tech>
Cheers,
Alejandro
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PATCH 2/2] x86/svm: Intercept Bus Locks for HVM guests
2026-01-20 13:34 ` Jan Beulich
@ 2026-01-20 14:11 ` Andrew Cooper
2026-01-20 14:16 ` Jan Beulich
0 siblings, 1 reply; 26+ messages in thread
From: Andrew Cooper @ 2026-01-20 14:11 UTC (permalink / raw)
To: Jan Beulich
Cc: Andrew Cooper, Roger Pau Monné, Jason Andryuk,
Alejandro Vallejo, xen-devel, Stefano Stabellini
On 20/01/2026 1:34 pm, Jan Beulich wrote:
> On 20.01.2026 14:29, Andrew Cooper wrote:
>> On 20/01/2026 1:27 pm, Jan Beulich wrote:
>>> On 20.01.2026 14:18, Andrew Cooper wrote:
>>>> On 20/01/2026 9:53 am, Alejandro Vallejo wrote:
>>>>> --- a/xen/arch/x86/hvm/svm/vmcb.c
>>>>> +++ b/xen/arch/x86/hvm/svm/vmcb.c
>>>>> @@ -66,6 +66,12 @@ static int construct_vmcb(struct vcpu *v)
>>>>> GENERAL2_INTERCEPT_XSETBV | GENERAL2_INTERCEPT_ICEBP |
>>>>> GENERAL2_INTERCEPT_RDPRU;
>>>>>
>>>>> + if ( cpu_has_bus_lock_thresh )
>>>>> + {
>>>>> + vmcb->_general3_intercepts = GENERAL3_INTERCEPT_BUS_LOCK_THRESH;
>>>> |=
>>>>
>>>>> + vmcb->bus_lock_thresh = 1; /* trigger immediately */
>>>> Really? The APM states:
>>>>
>>>> On processors that support Bus Lock Threshold (indicated by CPUID
>>>> Fn8000_000A_EDX[29] BusLockThreshold=1), the VMCB provides a Bus Lock
>>>> Threshold enable bit and an unsigned 16-bit Bus Lock Threshold count. On
>>>> VMRUN, this value is loaded into an internal count register. Before the
>>>> processor executes a bus lock in the guest, it checks the value of this
>>>> register. If the value is greater than 0, the processor executes the bus
>>>> lock successfully and decrements the count. If the value is 0, the bus
>>>> lock is not executed and a #VMEXIT to the VMM is taken.
>>>>
>>>> So according to the APM, setting the count to 1 will permit one bus lock
>>>> then exit (fault style) immediately before the next. This also says
>>>> that a count of 0 is a legal state.
>>> But then you'd livelock the guest as soon as it uses a bus lock. Are you
>>> suggesting to set to 1 in response to a bus lock exit, and keep at 0 at
>>> all other times?
>> I should have been clearer. I'm complaining at the "trigger
>> immediately" comment, because I don't think that's a correct statement
>> of how hardware behaves.
> In turn I should have looked at the patch itself before commenting. The
> other setting to 1 is what makes sense, and what ought to prevent a
> livelock. The one here indeed raises questions.
Setting it to 1 here is fine. This is the constructor for VMCBs, and
*something* needs to make the state consistent with the setting we chose
at runtime.
~Andrew
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PATCH 2/2] x86/svm: Intercept Bus Locks for HVM guests
2026-01-20 14:11 ` Andrew Cooper
@ 2026-01-20 14:16 ` Jan Beulich
2026-01-20 14:26 ` Andrew Cooper
0 siblings, 1 reply; 26+ messages in thread
From: Jan Beulich @ 2026-01-20 14:16 UTC (permalink / raw)
To: Andrew Cooper
Cc: Roger Pau Monné, Jason Andryuk, Alejandro Vallejo, xen-devel,
Stefano Stabellini
On 20.01.2026 15:11, Andrew Cooper wrote:
> On 20/01/2026 1:34 pm, Jan Beulich wrote:
>> On 20.01.2026 14:29, Andrew Cooper wrote:
>>> On 20/01/2026 1:27 pm, Jan Beulich wrote:
>>>> On 20.01.2026 14:18, Andrew Cooper wrote:
>>>>> On 20/01/2026 9:53 am, Alejandro Vallejo wrote:
>>>>>> --- a/xen/arch/x86/hvm/svm/vmcb.c
>>>>>> +++ b/xen/arch/x86/hvm/svm/vmcb.c
>>>>>> @@ -66,6 +66,12 @@ static int construct_vmcb(struct vcpu *v)
>>>>>> GENERAL2_INTERCEPT_XSETBV | GENERAL2_INTERCEPT_ICEBP |
>>>>>> GENERAL2_INTERCEPT_RDPRU;
>>>>>>
>>>>>> + if ( cpu_has_bus_lock_thresh )
>>>>>> + {
>>>>>> + vmcb->_general3_intercepts = GENERAL3_INTERCEPT_BUS_LOCK_THRESH;
>>>>> |=
>>>>>
>>>>>> + vmcb->bus_lock_thresh = 1; /* trigger immediately */
>>>>> Really? The APM states:
>>>>>
>>>>> On processors that support Bus Lock Threshold (indicated by CPUID
>>>>> Fn8000_000A_EDX[29] BusLockThreshold=1), the VMCB provides a Bus Lock
>>>>> Threshold enable bit and an unsigned 16-bit Bus Lock Threshold count. On
>>>>> VMRUN, this value is loaded into an internal count register. Before the
>>>>> processor executes a bus lock in the guest, it checks the value of this
>>>>> register. If the value is greater than 0, the processor executes the bus
>>>>> lock successfully and decrements the count. If the value is 0, the bus
>>>>> lock is not executed and a #VMEXIT to the VMM is taken.
>>>>>
>>>>> So according to the APM, setting the count to 1 will permit one bus lock
>>>>> then exit (fault style) immediately before the next. This also says
>>>>> that a count of 0 is a legal state.
>>>> But then you'd livelock the guest as soon as it uses a bus lock. Are you
>>>> suggesting to set to 1 in response to a bus lock exit, and keep at 0 at
>>>> all other times?
>>> I should have been clearer. I'm complaining at the "trigger
>>> immediately" comment, because I don't think that's a correct statement
>>> of how hardware behaves.
>> In turn I should have looked at the patch itself before commenting. The
>> other setting to 1 is what makes sense, and what ought to prevent a
>> livelock. The one here indeed raises questions.
>
> Setting it to 1 here is fine. This is the constructor for VMCBs, and
> *something* needs to make the state consistent with the setting we chose
> at runtime.
But the setting at runtime is generally going to be 0: When the guest exits
for an intercepted bus lock, we'll set the threshold to 1, re-enter the
guest, it'll retry the bus-locking insn, the counter will be decremented to
0, and the guest will continue to run with that value being zero. Until the
next insn taking a bus lock. So starting with 0 would overall be more
consistent.
Jan
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PATCH 2/2] x86/svm: Intercept Bus Locks for HVM guests
2026-01-20 14:16 ` Jan Beulich
@ 2026-01-20 14:26 ` Andrew Cooper
2026-01-20 14:32 ` Jan Beulich
0 siblings, 1 reply; 26+ messages in thread
From: Andrew Cooper @ 2026-01-20 14:26 UTC (permalink / raw)
To: Jan Beulich
Cc: Andrew Cooper, Roger Pau Monné, Jason Andryuk,
Alejandro Vallejo, xen-devel, Stefano Stabellini
On 20/01/2026 2:16 pm, Jan Beulich wrote:
> On 20.01.2026 15:11, Andrew Cooper wrote:
>> On 20/01/2026 1:34 pm, Jan Beulich wrote:
>>> On 20.01.2026 14:29, Andrew Cooper wrote:
>>>> On 20/01/2026 1:27 pm, Jan Beulich wrote:
>>>>> On 20.01.2026 14:18, Andrew Cooper wrote:
>>>>>> On 20/01/2026 9:53 am, Alejandro Vallejo wrote:
>>>>>>> --- a/xen/arch/x86/hvm/svm/vmcb.c
>>>>>>> +++ b/xen/arch/x86/hvm/svm/vmcb.c
>>>>>>> @@ -66,6 +66,12 @@ static int construct_vmcb(struct vcpu *v)
>>>>>>> GENERAL2_INTERCEPT_XSETBV | GENERAL2_INTERCEPT_ICEBP |
>>>>>>> GENERAL2_INTERCEPT_RDPRU;
>>>>>>>
>>>>>>> + if ( cpu_has_bus_lock_thresh )
>>>>>>> + {
>>>>>>> + vmcb->_general3_intercepts = GENERAL3_INTERCEPT_BUS_LOCK_THRESH;
>>>>>> |=
>>>>>>
>>>>>>> + vmcb->bus_lock_thresh = 1; /* trigger immediately */
>>>>>> Really? The APM states:
>>>>>>
>>>>>> On processors that support Bus Lock Threshold (indicated by CPUID
>>>>>> Fn8000_000A_EDX[29] BusLockThreshold=1), the VMCB provides a Bus Lock
>>>>>> Threshold enable bit and an unsigned 16-bit Bus Lock Threshold count. On
>>>>>> VMRUN, this value is loaded into an internal count register. Before the
>>>>>> processor executes a bus lock in the guest, it checks the value of this
>>>>>> register. If the value is greater than 0, the processor executes the bus
>>>>>> lock successfully and decrements the count. If the value is 0, the bus
>>>>>> lock is not executed and a #VMEXIT to the VMM is taken.
>>>>>>
>>>>>> So according to the APM, setting the count to 1 will permit one bus lock
>>>>>> then exit (fault style) immediately before the next. This also says
>>>>>> that a count of 0 is a legal state.
>>>>> But then you'd livelock the guest as soon as it uses a bus lock. Are you
>>>>> suggesting to set to 1 in response to a bus lock exit, and keep at 0 at
>>>>> all other times?
>>>> I should have been clearer. I'm complaining at the "trigger
>>>> immediately" comment, because I don't think that's a correct statement
>>>> of how hardware behaves.
>>> In turn I should have looked at the patch itself before commenting. The
>>> other setting to 1 is what makes sense, and what ought to prevent a
>>> livelock. The one here indeed raises questions.
>> Setting it to 1 here is fine. This is the constructor for VMCBs, and
>> *something* needs to make the state consistent with the setting we chose
>> at runtime.
> But the setting at runtime is generally going to be 0
First, we need clarity on what "Initialising as zero is invalid and
causes an immediate exit." means.
> : When the guest exits
> for an intercepted bus lock, we'll set the threshold to 1, re-enter the
> guest, it'll retry the bus-locking insn, the counter will be decremented to
> 0, and the guest will continue to run with that value being zero. Until the
> next insn taking a bus lock. So starting with 0 would overall be more
> consistent.
Assuming we can set 0, then yes we could drive SVM like this. However,
we cannot do the same for PV or VT-x guests, both of which are strictly
trap behaviour.
So for that reason alone, we probably wouldn't want to drive SVM
differently to other guest types.
~Andrew
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PATCH 2/2] x86/svm: Intercept Bus Locks for HVM guests
2026-01-20 14:26 ` Andrew Cooper
@ 2026-01-20 14:32 ` Jan Beulich
2026-01-20 15:28 ` Alejandro Vallejo
0 siblings, 1 reply; 26+ messages in thread
From: Jan Beulich @ 2026-01-20 14:32 UTC (permalink / raw)
To: Andrew Cooper
Cc: Roger Pau Monné, Jason Andryuk, Alejandro Vallejo, xen-devel,
Stefano Stabellini
On 20.01.2026 15:26, Andrew Cooper wrote:
> On 20/01/2026 2:16 pm, Jan Beulich wrote:
>> On 20.01.2026 15:11, Andrew Cooper wrote:
>>> On 20/01/2026 1:34 pm, Jan Beulich wrote:
>>>> On 20.01.2026 14:29, Andrew Cooper wrote:
>>>>> On 20/01/2026 1:27 pm, Jan Beulich wrote:
>>>>>> On 20.01.2026 14:18, Andrew Cooper wrote:
>>>>>>> On 20/01/2026 9:53 am, Alejandro Vallejo wrote:
>>>>>>>> --- a/xen/arch/x86/hvm/svm/vmcb.c
>>>>>>>> +++ b/xen/arch/x86/hvm/svm/vmcb.c
>>>>>>>> @@ -66,6 +66,12 @@ static int construct_vmcb(struct vcpu *v)
>>>>>>>> GENERAL2_INTERCEPT_XSETBV | GENERAL2_INTERCEPT_ICEBP |
>>>>>>>> GENERAL2_INTERCEPT_RDPRU;
>>>>>>>>
>>>>>>>> + if ( cpu_has_bus_lock_thresh )
>>>>>>>> + {
>>>>>>>> + vmcb->_general3_intercepts = GENERAL3_INTERCEPT_BUS_LOCK_THRESH;
>>>>>>> |=
>>>>>>>
>>>>>>>> + vmcb->bus_lock_thresh = 1; /* trigger immediately */
>>>>>>> Really? The APM states:
>>>>>>>
>>>>>>> On processors that support Bus Lock Threshold (indicated by CPUID
>>>>>>> Fn8000_000A_EDX[29] BusLockThreshold=1), the VMCB provides a Bus Lock
>>>>>>> Threshold enable bit and an unsigned 16-bit Bus Lock Threshold count. On
>>>>>>> VMRUN, this value is loaded into an internal count register. Before the
>>>>>>> processor executes a bus lock in the guest, it checks the value of this
>>>>>>> register. If the value is greater than 0, the processor executes the bus
>>>>>>> lock successfully and decrements the count. If the value is 0, the bus
>>>>>>> lock is not executed and a #VMEXIT to the VMM is taken.
>>>>>>>
>>>>>>> So according to the APM, setting the count to 1 will permit one bus lock
>>>>>>> then exit (fault style) immediately before the next. This also says
>>>>>>> that a count of 0 is a legal state.
>>>>>> But then you'd livelock the guest as soon as it uses a bus lock. Are you
>>>>>> suggesting to set to 1 in response to a bus lock exit, and keep at 0 at
>>>>>> all other times?
>>>>> I should have been clearer. I'm complaining at the "trigger
>>>>> immediately" comment, because I don't think that's a correct statement
>>>>> of how hardware behaves.
>>>> In turn I should have looked at the patch itself before commenting. The
>>>> other setting to 1 is what makes sense, and what ought to prevent a
>>>> livelock. The one here indeed raises questions.
>>> Setting it to 1 here is fine. This is the constructor for VMCBs, and
>>> *something* needs to make the state consistent with the setting we chose
>>> at runtime.
>> But the setting at runtime is generally going to be 0
>
> First, we need clarity on what "Initialising as zero is invalid and
> causes an immediate exit." means.
+1
>> : When the guest exits
>> for an intercepted bus lock, we'll set the threshold to 1, re-enter the
>> guest, it'll retry the bus-locking insn, the counter will be decremented to
>> 0, and the guest will continue to run with that value being zero. Until the
>> next insn taking a bus lock. So starting with 0 would overall be more
>> consistent.
>
> Assuming we can set 0, then yes we could drive SVM like this. However,
> we cannot do the same for PV or VT-x guests, both of which are strictly
> trap behaviour.
>
> So for that reason alone, we probably wouldn't want to drive SVM
> differently to other guest types.
Yet we can't abstract away the fault vs trap behavioral difference. I'd
take a different position: To have behavior as similar as possible, we'd
want it to be uniform how many bus locks we allow to be used without us
noticing. If we trap after the first one for VMX, we ought to fault on
the first one for SVM (provided that's possible in practice).
Jan
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PATCH 2/2] x86/svm: Intercept Bus Locks for HVM guests
2026-01-20 13:29 ` Jan Beulich
@ 2026-01-20 14:41 ` Alejandro Vallejo
0 siblings, 0 replies; 26+ messages in thread
From: Alejandro Vallejo @ 2026-01-20 14:41 UTC (permalink / raw)
To: Jan Beulich, Teddy Astie
Cc: Andrew Cooper, Roger Pau Monné, Jason Andryuk,
Stefano Stabellini, xen-devel
On Tue Jan 20, 2026 at 2:29 PM CET, Jan Beulich wrote:
> On 20.01.2026 14:11, Teddy Astie wrote:
>> Le 20/01/2026 à 10:56, Alejandro Vallejo a écrit :
>>> --- a/xen/arch/x86/hvm/svm/vmcb.c
>>> +++ b/xen/arch/x86/hvm/svm/vmcb.c
>>> @@ -66,6 +66,12 @@ static int construct_vmcb(struct vcpu *v)
>>> GENERAL2_INTERCEPT_XSETBV | GENERAL2_INTERCEPT_ICEBP |
>>> GENERAL2_INTERCEPT_RDPRU;
>>>
>>> + if ( cpu_has_bus_lock_thresh )
>>> + {
>>> + vmcb->_general3_intercepts = GENERAL3_INTERCEPT_BUS_LOCK_THRESH;
>>> + vmcb->bus_lock_thresh = 1; /* trigger immediately */
>>> + }
>>> +
>>> /* Intercept all debug-register writes. */
>>> vmcb->_dr_intercepts = ~0u;
>>>
>>
>> According to APM,
>>
>> INTERCEPT_BUS_LOCK_THRESH does
>> > Intercept bus lock operations when Bus Lock Threshold Counter is 0
>>
>> I assume that when set to 0, we intercept all bus locks, so if set to 1,
>> every 2 bus lock (since we first go from 1 to 0, then at 0 we intercept
>> the next one) ?
Correct
>>
>> I think we want that to be tunable, as intercepting all bus locks may be
>> too extreme we probably want to intercept every few ones instead.
>
> Otoh bus locks (as opposed to cache locks) would better be rare, or else
> perhaps such a guest deserves some extra slowing down?
>
> Jan
I agree with Jan. buslock operations are so rare it's not worth being lenient
about them. They ought to be more expensive than they currently are for the
caller, in fact, so they notice and not do it because there's rarely a rationale
for them to exist at all. I'd be happier if the ISA didn't allow them at all.
Cheers,
Alejandro
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PATCH 2/2] x86/svm: Intercept Bus Locks for HVM guests
2026-01-20 14:32 ` Jan Beulich
@ 2026-01-20 15:28 ` Alejandro Vallejo
2026-01-20 15:41 ` Alejandro Vallejo
0 siblings, 1 reply; 26+ messages in thread
From: Alejandro Vallejo @ 2026-01-20 15:28 UTC (permalink / raw)
To: Jan Beulich, Andrew Cooper
Cc: Roger Pau Monné, Jason Andryuk, xen-devel,
Stefano Stabellini
On Tue Jan 20, 2026 at 3:32 PM CET, Jan Beulich wrote:
> On 20.01.2026 15:26, Andrew Cooper wrote:
>> On 20/01/2026 2:16 pm, Jan Beulich wrote:
>>> On 20.01.2026 15:11, Andrew Cooper wrote:
>>>> On 20/01/2026 1:34 pm, Jan Beulich wrote:
>>>>> On 20.01.2026 14:29, Andrew Cooper wrote:
>>>>>> On 20/01/2026 1:27 pm, Jan Beulich wrote:
>>>>>>> On 20.01.2026 14:18, Andrew Cooper wrote:
>>>>>>>> On 20/01/2026 9:53 am, Alejandro Vallejo wrote:
>>>>>>>>> --- a/xen/arch/x86/hvm/svm/vmcb.c
>>>>>>>>> +++ b/xen/arch/x86/hvm/svm/vmcb.c
>>>>>>>>> @@ -66,6 +66,12 @@ static int construct_vmcb(struct vcpu *v)
>>>>>>>>> GENERAL2_INTERCEPT_XSETBV | GENERAL2_INTERCEPT_ICEBP |
>>>>>>>>> GENERAL2_INTERCEPT_RDPRU;
>>>>>>>>>
>>>>>>>>> + if ( cpu_has_bus_lock_thresh )
>>>>>>>>> + {
>>>>>>>>> + vmcb->_general3_intercepts = GENERAL3_INTERCEPT_BUS_LOCK_THRESH;
>>>>>>>> |=
>>>>>>>>
>>>>>>>>> + vmcb->bus_lock_thresh = 1; /* trigger immediately */
>>>>>>>> Really? The APM states:
>>>>>>>>
>>>>>>>> On processors that support Bus Lock Threshold (indicated by CPUID
>>>>>>>> Fn8000_000A_EDX[29] BusLockThreshold=1), the VMCB provides a Bus Lock
>>>>>>>> Threshold enable bit and an unsigned 16-bit Bus Lock Threshold count. On
>>>>>>>> VMRUN, this value is loaded into an internal count register. Before the
>>>>>>>> processor executes a bus lock in the guest, it checks the value of this
>>>>>>>> register. If the value is greater than 0, the processor executes the bus
>>>>>>>> lock successfully and decrements the count. If the value is 0, the bus
>>>>>>>> lock is not executed and a #VMEXIT to the VMM is taken.
>>>>>>>>
>>>>>>>> So according to the APM, setting the count to 1 will permit one bus lock
>>>>>>>> then exit (fault style) immediately before the next. This also says
>>>>>>>> that a count of 0 is a legal state.
>>>>>>> But then you'd livelock the guest as soon as it uses a bus lock. Are you
>>>>>>> suggesting to set to 1 in response to a bus lock exit, and keep at 0 at
>>>>>>> all other times?
>>>>>> I should have been clearer. I'm complaining at the "trigger
>>>>>> immediately" comment, because I don't think that's a correct statement
>>>>>> of how hardware behaves.
>>>>> In turn I should have looked at the patch itself before commenting. The
>>>>> other setting to 1 is what makes sense, and what ought to prevent a
>>>>> livelock. The one here indeed raises questions.
>>>> Setting it to 1 here is fine. This is the constructor for VMCBs, and
>>>> *something* needs to make the state consistent with the setting we chose
>>>> at runtime.
>>> But the setting at runtime is generally going to be 0
>>
>> First, we need clarity on what "Initialising as zero is invalid and
>> causes an immediate exit." means.
>
> +1
The exit is not an VMEXIT_INVALID, if that's your fear. Let me clarify:
The TL;DR is that the commit message is the unfortunate side effect of trying
to remember why I did something a while ago and not remembering very well.
Initialy I had zero at both the initialiser and the reset. That doesn't get
very far until you notice the behaviour is a fault and not a trap, which the APM
states as:
```
If the value is 0, the bus lock is not executed and a #VMEXIT to the VMM is
taken
```
Then in order to go past that boundary the reset must be set at 1, or the guest
loops. The initialisation may start at either (though zero would be more
consistent).
I guess over time I just internalised a bit too much "I can't exec vmrun with
a counter of 0".
I'll send a v2 with the initialiser set to zero and an amended commit message.
Cheers,
Alejandro
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PATCH 2/2] x86/svm: Intercept Bus Locks for HVM guests
2026-01-20 15:28 ` Alejandro Vallejo
@ 2026-01-20 15:41 ` Alejandro Vallejo
0 siblings, 0 replies; 26+ messages in thread
From: Alejandro Vallejo @ 2026-01-20 15:41 UTC (permalink / raw)
To: Alejandro Vallejo, Jan Beulich, Andrew Cooper
Cc: Roger Pau Monné, Jason Andryuk, xen-devel,
Stefano Stabellini, Xen-devel
On Tue Jan 20, 2026 at 4:28 PM CET, Alejandro Vallejo wrote:
> On Tue Jan 20, 2026 at 3:32 PM CET, Jan Beulich wrote:
>> On 20.01.2026 15:26, Andrew Cooper wrote:
>>> On 20/01/2026 2:16 pm, Jan Beulich wrote:
>>>> On 20.01.2026 15:11, Andrew Cooper wrote:
>>>>> On 20/01/2026 1:34 pm, Jan Beulich wrote:
>>>>>> On 20.01.2026 14:29, Andrew Cooper wrote:
>>>>>>> On 20/01/2026 1:27 pm, Jan Beulich wrote:
>>>>>>>> On 20.01.2026 14:18, Andrew Cooper wrote:
>>>>>>>>> On 20/01/2026 9:53 am, Alejandro Vallejo wrote:
>>>>>>>>>> --- a/xen/arch/x86/hvm/svm/vmcb.c
>>>>>>>>>> +++ b/xen/arch/x86/hvm/svm/vmcb.c
>>>>>>>>>> @@ -66,6 +66,12 @@ static int construct_vmcb(struct vcpu *v)
>>>>>>>>>> GENERAL2_INTERCEPT_XSETBV | GENERAL2_INTERCEPT_ICEBP |
>>>>>>>>>> GENERAL2_INTERCEPT_RDPRU;
>>>>>>>>>>
>>>>>>>>>> + if ( cpu_has_bus_lock_thresh )
>>>>>>>>>> + {
>>>>>>>>>> + vmcb->_general3_intercepts = GENERAL3_INTERCEPT_BUS_LOCK_THRESH;
>>>>>>>>> |=
>>>>>>>>>
>>>>>>>>>> + vmcb->bus_lock_thresh = 1; /* trigger immediately */
>>>>>>>>> Really? The APM states:
>>>>>>>>>
>>>>>>>>> On processors that support Bus Lock Threshold (indicated by CPUID
>>>>>>>>> Fn8000_000A_EDX[29] BusLockThreshold=1), the VMCB provides a Bus Lock
>>>>>>>>> Threshold enable bit and an unsigned 16-bit Bus Lock Threshold count. On
>>>>>>>>> VMRUN, this value is loaded into an internal count register. Before the
>>>>>>>>> processor executes a bus lock in the guest, it checks the value of this
>>>>>>>>> register. If the value is greater than 0, the processor executes the bus
>>>>>>>>> lock successfully and decrements the count. If the value is 0, the bus
>>>>>>>>> lock is not executed and a #VMEXIT to the VMM is taken.
>>>>>>>>>
>>>>>>>>> So according to the APM, setting the count to 1 will permit one bus lock
>>>>>>>>> then exit (fault style) immediately before the next. This also says
>>>>>>>>> that a count of 0 is a legal state.
>>>>>>>> But then you'd livelock the guest as soon as it uses a bus lock. Are you
>>>>>>>> suggesting to set to 1 in response to a bus lock exit, and keep at 0 at
>>>>>>>> all other times?
>>>>>>> I should have been clearer. I'm complaining at the "trigger
>>>>>>> immediately" comment, because I don't think that's a correct statement
>>>>>>> of how hardware behaves.
>>>>>> In turn I should have looked at the patch itself before commenting. The
>>>>>> other setting to 1 is what makes sense, and what ought to prevent a
>>>>>> livelock. The one here indeed raises questions.
>>>>> Setting it to 1 here is fine. This is the constructor for VMCBs, and
>>>>> *something* needs to make the state consistent with the setting we chose
>>>>> at runtime.
>>>> But the setting at runtime is generally going to be 0
>>>
>>> First, we need clarity on what "Initialising as zero is invalid and
>>> causes an immediate exit." means.
>>
>> +1
>
> The exit is not an VMEXIT_INVALID, if that's your fear. Let me clarify:
>
> The TL;DR is that the commit message is the unfortunate side effect of trying
> to remember why I did something a while ago and not remembering very well.
>
> Initialy I had zero at both the initialiser and the reset. That doesn't get
> very far until you notice the behaviour is a fault and not a trap, which the APM
> states as:
>
> ```
> If the value is 0, the bus lock is not executed and a #VMEXIT to the VMM is
> taken
> ```
>
> Then in order to go past that boundary the reset must be set at 1, or the guest
> loops. The initialisation may start at either (though zero would be more
> consistent).
>
> I guess over time I just internalised a bit too much "I can't exec vmrun with
> a counter of 0".
>
> I'll send a v2 with the initialiser set to zero and an amended commit message.
... pending a hardware test, because the board I have with me ATM doesn't
support the feature and need to get ahold of one.
>
> Cheers,
> Alejandro
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PATCH 1/2] x86/svm: Add infrastructure for Bus Lock Threshold
2026-01-20 13:30 ` Jan Beulich
@ 2026-01-21 12:40 ` Alejandro Vallejo
2026-01-21 13:07 ` Jan Beulich
0 siblings, 1 reply; 26+ messages in thread
From: Alejandro Vallejo @ 2026-01-21 12:40 UTC (permalink / raw)
To: Jan Beulich, Teddy Astie
Cc: Andrew Cooper, Roger Pau Monné, Jason Andryuk,
Stefano Stabellini, xen-devel
On Tue Jan 20, 2026 at 2:30 PM CET, Jan Beulich wrote:
> On 20.01.2026 14:19, Teddy Astie wrote:
>> Le 20/01/2026 à 10:56, Alejandro Vallejo a écrit :
>>> --- a/xen/arch/x86/hvm/svm/vmcb.h
>>> +++ b/xen/arch/x86/hvm/svm/vmcb.h
>>> @@ -65,6 +65,11 @@ enum GenericIntercept2bits
>>> GENERAL2_INTERCEPT_RDPRU = 1 << 14,
>>> };
>>>
>>> +/* general 2 intercepts */
>>
>> nit, you want to says general 3 intercepts
>
> And then, further nit, also get comment style right.
>
> Jan
What do you mean by comment style? it's a /* ... */ oneliner that matches
what the other general intercepts say. What am I missing?
Cheers,
Alejandro
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PATCH 1/2] x86/svm: Add infrastructure for Bus Lock Threshold
2026-01-21 12:40 ` Alejandro Vallejo
@ 2026-01-21 13:07 ` Jan Beulich
2026-01-21 15:10 ` Alejandro Vallejo
0 siblings, 1 reply; 26+ messages in thread
From: Jan Beulich @ 2026-01-21 13:07 UTC (permalink / raw)
To: Alejandro Vallejo
Cc: Andrew Cooper, Roger Pau Monné, Jason Andryuk,
Stefano Stabellini, xen-devel, Teddy Astie
On 21.01.2026 13:40, Alejandro Vallejo wrote:
> On Tue Jan 20, 2026 at 2:30 PM CET, Jan Beulich wrote:
>> On 20.01.2026 14:19, Teddy Astie wrote:
>>> Le 20/01/2026 à 10:56, Alejandro Vallejo a écrit :
>>>> --- a/xen/arch/x86/hvm/svm/vmcb.h
>>>> +++ b/xen/arch/x86/hvm/svm/vmcb.h
>>>> @@ -65,6 +65,11 @@ enum GenericIntercept2bits
>>>> GENERAL2_INTERCEPT_RDPRU = 1 << 14,
>>>> };
>>>>
>>>> +/* general 2 intercepts */
>>>
>>> nit, you want to says general 3 intercepts
>>
>> And then, further nit, also get comment style right.
>
> What do you mean by comment style? it's a /* ... */ oneliner that matches
> what the other general intercepts say. What am I missing?
Quote from ./CODING_STYLE:
"Multi-word comments should begin with a capital letter."
Jan
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PATCH 1/2] x86/svm: Add infrastructure for Bus Lock Threshold
2026-01-21 13:07 ` Jan Beulich
@ 2026-01-21 15:10 ` Alejandro Vallejo
0 siblings, 0 replies; 26+ messages in thread
From: Alejandro Vallejo @ 2026-01-21 15:10 UTC (permalink / raw)
To: Jan Beulich
Cc: Andrew Cooper, Roger Pau Monné, Jason Andryuk,
Stefano Stabellini, xen-devel, Teddy Astie
On Wed Jan 21, 2026 at 2:07 PM CET, Jan Beulich wrote:
> On 21.01.2026 13:40, Alejandro Vallejo wrote:
>> On Tue Jan 20, 2026 at 2:30 PM CET, Jan Beulich wrote:
>>> On 20.01.2026 14:19, Teddy Astie wrote:
>>>> Le 20/01/2026 à 10:56, Alejandro Vallejo a écrit :
>>>>> --- a/xen/arch/x86/hvm/svm/vmcb.h
>>>>> +++ b/xen/arch/x86/hvm/svm/vmcb.h
>>>>> @@ -65,6 +65,11 @@ enum GenericIntercept2bits
>>>>> GENERAL2_INTERCEPT_RDPRU = 1 << 14,
>>>>> };
>>>>>
>>>>> +/* general 2 intercepts */
>>>>
>>>> nit, you want to says general 3 intercepts
>>>
>>> And then, further nit, also get comment style right.
>>
>> What do you mean by comment style? it's a /* ... */ oneliner that matches
>> what the other general intercepts say. What am I missing?
>
> Quote from ./CODING_STYLE:
>
> "Multi-word comments should begin with a capital letter."
>
> Jan
Ack. Though also from CODING_STYLE:
"In general you should copy the style of the surrounding code."
and intercept groups 1 and 2 also start in lowercase. I'll correct both as well.
Cheers,
Alejandro
^ permalink raw reply [flat|nested] 26+ messages in thread
end of thread, other threads:[~2026-01-21 15:10 UTC | newest]
Thread overview: 26+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-01-20 9:53 [PATCH 0/2] x86/svm: Add support for Bus Lock Threshold Alejandro Vallejo
2026-01-20 9:53 ` [PATCH 1/2] x86/svm: Add infrastructure " Alejandro Vallejo
2026-01-20 13:12 ` Andrew Cooper
2026-01-20 13:57 ` Alejandro Vallejo
2026-01-20 13:19 ` Teddy Astie
2026-01-20 13:30 ` Jan Beulich
2026-01-21 12:40 ` Alejandro Vallejo
2026-01-21 13:07 ` Jan Beulich
2026-01-21 15:10 ` Alejandro Vallejo
2026-01-20 13:58 ` Alejandro Vallejo
2026-01-20 9:53 ` [PATCH 2/2] x86/svm: Intercept Bus Locks for HVM guests Alejandro Vallejo
2026-01-20 13:11 ` Teddy Astie
2026-01-20 13:29 ` Jan Beulich
2026-01-20 14:41 ` Alejandro Vallejo
2026-01-20 13:18 ` Andrew Cooper
2026-01-20 13:27 ` Jan Beulich
2026-01-20 13:29 ` Andrew Cooper
2026-01-20 13:34 ` Jan Beulich
2026-01-20 14:11 ` Andrew Cooper
2026-01-20 14:16 ` Jan Beulich
2026-01-20 14:26 ` Andrew Cooper
2026-01-20 14:32 ` Jan Beulich
2026-01-20 15:28 ` Alejandro Vallejo
2026-01-20 15:41 ` Alejandro Vallejo
2026-01-20 11:22 ` [PATCH 0/2] x86/svm: Add support for Bus Lock Threshold Alejandro Vallejo
2026-01-20 13:21 ` Andrew Cooper
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.