* [PATCH] Bug-fixes to enable PV ticketlock to work under Xen PVHVM with Linux v3.12. (v2)
@ 2013-09-09 15:11 Konrad Rzeszutek Wilk
2013-09-09 15:11 ` [PATCH 1/5] xen/spinlock: Fix locking path engaging too soon under PVHVM Konrad Rzeszutek Wilk
` (5 more replies)
0 siblings, 6 replies; 7+ messages in thread
From: Konrad Rzeszutek Wilk @ 2013-09-09 15:11 UTC (permalink / raw)
To: linux-kernel, xen-devel, boris.ostrovsky, david.vrabel,
stefan.bader, stefano.stabellini, jeremy
Changelog since v1 (see https://lkml.org/lkml/2013/9/7/78)
- Added Reviewed-by tag.
- Fleshed out description of patches
- Ran some perf
- Used xen_smp_prepare_boot_cpu instead of xen_hvm_smp_init
After a bit of false starts, lots of debugging, and tons of help from Stefano and
David on how event mechanism is suppose to work I am happy to present a set
of bug-fixes that make PV ticketlocks work under Xen PVHVM with Linux v3.12.
v3.12 has now thanks to commit 816434ec4a674fcdb3c2221a6dffdc8f34020550
(Merge branch 'x86-spinlocks-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip)
PV ticketlocks. That means:
- Xen PV bytelock has been replaced by Xen PV ticketlock.
- Xen PVHVM is using ticketlock (not PV variant) - this patch makes it PV.
- baremetal is still using ticketlocks.
In other words everything in the kernel is ticketlock based with the virtualizations
having the 'PV' part to aid.
Please take a look at the patches. They are also available as a git tree
under:
git://git.kernel.org/pub/scm/linux/kernel/git/konrad/xen.git stable/pvticketlock.v7.1
I had run some light performance tests with two guests - each over subscribed by
2:1 and running a spinlock_hog wherein each CPU tries to get a lock. The machine
is a 4 CPU Intel, and each guest is running with 8 VCPUs.
It is not a perfect test-case - for that I have asked our internal performance
engineer to test it out with various workloads and guests.
However it does demonstrate that these patches do work and they do not
incur any performance regressions (and yes, they do show a performance
improvement).
arch/x86/xen/enlighten.c | 1 -
arch/x86/xen/smp.c | 28 +++++++++++++++++++++++-----
arch/x86/xen/spinlock.c | 45 ++++++++-------------------------------------
3 files changed, 31 insertions(+), 43 deletions(-)
Konrad Rzeszutek Wilk (5):
xen/spinlock: Fix locking path engaging too soon under PVHVM.
xen/spinlock: We don't need the old structure anymore
xen/smp: Update pv_lock_ops functions before alternative code starts under PVHVM
xen/spinlock: Don't setup xen spinlock IPI kicker if disabled.
Revert "xen/spinlock: Disable IRQ spinlock (PV) allocation on PVHVM"
^ permalink raw reply [flat|nested] 7+ messages in thread
* [PATCH 1/5] xen/spinlock: Fix locking path engaging too soon under PVHVM.
2013-09-09 15:11 [PATCH] Bug-fixes to enable PV ticketlock to work under Xen PVHVM with Linux v3.12. (v2) Konrad Rzeszutek Wilk
@ 2013-09-09 15:11 ` Konrad Rzeszutek Wilk
2013-09-09 15:11 ` [PATCH 2/5] xen/spinlock: We don't need the old structure anymore Konrad Rzeszutek Wilk
` (4 subsequent siblings)
5 siblings, 0 replies; 7+ messages in thread
From: Konrad Rzeszutek Wilk @ 2013-09-09 15:11 UTC (permalink / raw)
To: linux-kernel, xen-devel, boris.ostrovsky, david.vrabel,
stefan.bader, stefano.stabellini, jeremy
Cc: Konrad Rzeszutek Wilk
The xen_lock_spinning has a check for the kicker interrupts
and if it is not initialized it will spin normally (not enter
the slowpath).
But for PVHVM case we would initialize the kicker interrupt
before the CPU came online. This meant that if the booting
CPU used a spinlock and went in the slowpath - it would
enter the slowpath and block forever. The forever part because
during bootup: the spinlock would be taken _before_ the CPU
sets itself to be online (more on this further), and we enter
to poll on the event channel forever.
The bootup CPU (see commit fc78d343fa74514f6fd117b5ef4cd27e4ac30236
"xen/smp: initialize IPI vectors before marking CPU online"
for details) and the CPU that started the bootup consult
the cpu_online_mask to determine whether the booting CPU should
get an IPI. The booting CPU has to set itself in this mask via:
set_cpu_online(smp_processor_id(), true);
However, if the spinlock is taken before this (and it is) and
it polls on an event channel - it will never be woken up as
the kernel will never send an IPI to an offline CPU.
Note that the PVHVM logic in sending IPIs is using the HVM
path which has numerous checks using the cpu_online_mask
and cpu_active_mask. See above mention git commit for details.
Signed-off-by: Konrad Rzeszutek Wilk <konrad.wilk@oracle.com>
Reviewed-by: David Vrabel <david.vrabel@citrix.com>
---
arch/x86/xen/enlighten.c | 1 -
arch/x86/xen/smp.c | 9 +++++++++
2 files changed, 9 insertions(+), 1 deletion(-)
diff --git a/arch/x86/xen/enlighten.c b/arch/x86/xen/enlighten.c
index 2fc216d..fa6ade7 100644
--- a/arch/x86/xen/enlighten.c
+++ b/arch/x86/xen/enlighten.c
@@ -1692,7 +1692,6 @@ static int xen_hvm_cpu_notify(struct notifier_block *self, unsigned long action,
case CPU_UP_PREPARE:
xen_vcpu_setup(cpu);
if (xen_have_vector_callback) {
- xen_init_lock_cpu(cpu);
if (xen_feature(XENFEAT_hvm_safe_pvclock))
xen_setup_timer(cpu);
}
diff --git a/arch/x86/xen/smp.c b/arch/x86/xen/smp.c
index 9235842..c21b825 100644
--- a/arch/x86/xen/smp.c
+++ b/arch/x86/xen/smp.c
@@ -709,6 +709,15 @@ static int xen_hvm_cpu_up(unsigned int cpu, struct task_struct *tidle)
WARN_ON(rc);
if (!rc)
rc = native_cpu_up(cpu, tidle);
+
+ /*
+ * We must initialize the slowpath CPU kicker _after_ the native
+ * path has executed. If we initialized it before none of the
+ * unlocker IPI kicks would reach the booting CPU as the booting
+ * CPU had not set itself 'online' in cpu_online_mask. That mask
+ * is checked when IPIs are sent (on HVM at least).
+ */
+ xen_init_lock_cpu(cpu);
return rc;
}
--
1.8.3.1
^ permalink raw reply related [flat|nested] 7+ messages in thread
* [PATCH 2/5] xen/spinlock: We don't need the old structure anymore
2013-09-09 15:11 [PATCH] Bug-fixes to enable PV ticketlock to work under Xen PVHVM with Linux v3.12. (v2) Konrad Rzeszutek Wilk
2013-09-09 15:11 ` [PATCH 1/5] xen/spinlock: Fix locking path engaging too soon under PVHVM Konrad Rzeszutek Wilk
@ 2013-09-09 15:11 ` Konrad Rzeszutek Wilk
2013-09-09 15:11 ` [PATCH 3/5] xen/smp: Update pv_lock_ops functions before alternative code starts under PVHVM Konrad Rzeszutek Wilk
` (3 subsequent siblings)
5 siblings, 0 replies; 7+ messages in thread
From: Konrad Rzeszutek Wilk @ 2013-09-09 15:11 UTC (permalink / raw)
To: linux-kernel, xen-devel, boris.ostrovsky, david.vrabel,
stefan.bader, stefano.stabellini, jeremy
Cc: Konrad Rzeszutek Wilk
As we are using the generic ticketlock structs and these
old structures are not needed anymore.
Signed-off-by: Konrad Rzeszutek Wilk <konrad.wilk@oracle.com>
Reviewed-by: David Vrabel <david.vrabel@citrix.com>
---
arch/x86/xen/spinlock.c | 18 ------------------
1 file changed, 18 deletions(-)
diff --git a/arch/x86/xen/spinlock.c b/arch/x86/xen/spinlock.c
index 0438b93..71db82c 100644
--- a/arch/x86/xen/spinlock.c
+++ b/arch/x86/xen/spinlock.c
@@ -81,7 +81,6 @@ static inline void spin_time_accum_blocked(u64 start)
spinlock_stats.time_blocked += delta;
}
#else /* !CONFIG_XEN_DEBUG_FS */
-#define TIMEOUT (1 << 10)
static inline void add_stats(enum xen_contention_stat var, u32 val)
{
}
@@ -96,23 +95,6 @@ static inline void spin_time_accum_blocked(u64 start)
}
#endif /* CONFIG_XEN_DEBUG_FS */
-/*
- * Size struct xen_spinlock so it's the same as arch_spinlock_t.
- */
-#if NR_CPUS < 256
-typedef u8 xen_spinners_t;
-# define inc_spinners(xl) \
- asm(LOCK_PREFIX " incb %0" : "+m" ((xl)->spinners) : : "memory");
-# define dec_spinners(xl) \
- asm(LOCK_PREFIX " decb %0" : "+m" ((xl)->spinners) : : "memory");
-#else
-typedef u16 xen_spinners_t;
-# define inc_spinners(xl) \
- asm(LOCK_PREFIX " incw %0" : "+m" ((xl)->spinners) : : "memory");
-# define dec_spinners(xl) \
- asm(LOCK_PREFIX " decw %0" : "+m" ((xl)->spinners) : : "memory");
-#endif
-
struct xen_lock_waiting {
struct arch_spinlock *lock;
__ticket_t want;
--
1.8.3.1
^ permalink raw reply related [flat|nested] 7+ messages in thread
* [PATCH 3/5] xen/smp: Update pv_lock_ops functions before alternative code starts under PVHVM
2013-09-09 15:11 [PATCH] Bug-fixes to enable PV ticketlock to work under Xen PVHVM with Linux v3.12. (v2) Konrad Rzeszutek Wilk
2013-09-09 15:11 ` [PATCH 1/5] xen/spinlock: Fix locking path engaging too soon under PVHVM Konrad Rzeszutek Wilk
2013-09-09 15:11 ` [PATCH 2/5] xen/spinlock: We don't need the old structure anymore Konrad Rzeszutek Wilk
@ 2013-09-09 15:11 ` Konrad Rzeszutek Wilk
2013-09-09 15:11 ` [PATCH 4/5] xen/spinlock: Don't setup xen spinlock IPI kicker if disabled Konrad Rzeszutek Wilk
` (2 subsequent siblings)
5 siblings, 0 replies; 7+ messages in thread
From: Konrad Rzeszutek Wilk @ 2013-09-09 15:11 UTC (permalink / raw)
To: linux-kernel, xen-devel, boris.ostrovsky, david.vrabel,
stefan.bader, stefano.stabellini, jeremy
Cc: Konrad Rzeszutek Wilk
Before this patch we would patch all of the pv_lock_ops sites
using alternative assembler. Then later in the bootup cycle
change the unlock_kick and lock_spinning to the Xen specific -
without re patching.
That meant that for the core of the kernel we would be running
with the baremetal version of unlock_kick and lock_spinning while
for modules we would have the proper Xen specific slowpaths.
As most of the module uses some API from the core kernel that ended
up with slowpath lockers waiting forever to be kicked (b/c they
would be using the Xen specific slowpath logic). And the
kick never came b/c the unlock path that was taken was the
baremetal one.
On PV we do not have the problem as we initialise before the
alternative code kicks in.
The fix is to make the updating of the pv_lock_ops function
be done before the alternative code starts patching.
Note that this patch fixes issues discovered by commit
f10cd522c5fbfec9ae3cc01967868c9c2401ed23.
("xen: disable PV spinlocks on HVM") wherein it mentioned
PV spinlocks cannot possibly work with the current code because they are
enabled after pvops patching has already been done, and because PV
spinlocks use a different data structure than native spinlocks so we
cannot switch between them dynamically.
The first problem is solved by this patch.
The second problem has been solved by commit
816434ec4a674fcdb3c2221a6dffdc8f34020550
(Merge branch 'x86-spinlocks-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip)
P.S.
There is still the commit 70dd4998cb85f0ecd6ac892cc7232abefa432efb
(xen/spinlock: Disable IRQ spinlock (PV) allocation on PVHVM) to
revert but that can be done later after all other bugs have been
fixed.
Signed-off-by: Konrad Rzeszutek Wilk <konrad.wilk@oracle.com>
Reviewed-by: David Vrabel <david.vrabel@citrix.com>
---
arch/x86/xen/smp.c | 19 ++++++++++++++-----
1 file changed, 14 insertions(+), 5 deletions(-)
diff --git a/arch/x86/xen/smp.c b/arch/x86/xen/smp.c
index c21b825..d1e4777 100644
--- a/arch/x86/xen/smp.c
+++ b/arch/x86/xen/smp.c
@@ -273,12 +273,20 @@ static void __init xen_smp_prepare_boot_cpu(void)
BUG_ON(smp_processor_id() != 0);
native_smp_prepare_boot_cpu();
- /* We've switched to the "real" per-cpu gdt, so make sure the
- old memory can be recycled */
- make_lowmem_page_readwrite(xen_initial_gdt);
+ if (xen_pv_domain()) {
+ /* We've switched to the "real" per-cpu gdt, so make sure the
+ old memory can be recycled */
+ make_lowmem_page_readwrite(xen_initial_gdt);
- xen_filter_cpu_maps();
- xen_setup_vcpu_info_placement();
+ xen_filter_cpu_maps();
+ xen_setup_vcpu_info_placement();
+ }
+ /*
+ * The alternative logic (which patches the unlock/lock) runs before
+ * the smp bootup up code is activated. Hence we need to set this up
+ * the core kernel is being patched. Otherwise we will have only
+ * modules patched but not core code.
+ */
xen_init_spinlocks();
}
@@ -737,4 +745,5 @@ void __init xen_hvm_smp_init(void)
smp_ops.cpu_die = xen_hvm_cpu_die;
smp_ops.send_call_func_ipi = xen_smp_send_call_function_ipi;
smp_ops.send_call_func_single_ipi = xen_smp_send_call_function_single_ipi;
+ smp_ops.smp_prepare_boot_cpu = xen_smp_prepare_boot_cpu;
}
--
1.8.3.1
^ permalink raw reply related [flat|nested] 7+ messages in thread
* [PATCH 4/5] xen/spinlock: Don't setup xen spinlock IPI kicker if disabled.
2013-09-09 15:11 [PATCH] Bug-fixes to enable PV ticketlock to work under Xen PVHVM with Linux v3.12. (v2) Konrad Rzeszutek Wilk
` (2 preceding siblings ...)
2013-09-09 15:11 ` [PATCH 3/5] xen/smp: Update pv_lock_ops functions before alternative code starts under PVHVM Konrad Rzeszutek Wilk
@ 2013-09-09 15:11 ` Konrad Rzeszutek Wilk
2013-09-09 15:11 ` [PATCH 5/5] Revert "xen/spinlock: Disable IRQ spinlock (PV) allocation on PVHVM" Konrad Rzeszutek Wilk
2013-09-09 15:33 ` [Xen-devel] [PATCH] Bug-fixes to enable PV ticketlock to work under Xen PVHVM with Linux v3.12. (v2) David Vrabel
5 siblings, 0 replies; 7+ messages in thread
From: Konrad Rzeszutek Wilk @ 2013-09-09 15:11 UTC (permalink / raw)
To: linux-kernel, xen-devel, boris.ostrovsky, david.vrabel,
stefan.bader, stefano.stabellini, jeremy
Cc: Konrad Rzeszutek Wilk
There is no need to setup this kicker IPI if we are never going
to use the paravirtualized ticketlock mechanism.
Signed-off-by: Konrad Rzeszutek Wilk <konrad.wilk@oracle.com>
Reviewed-by: David Vrabel <david.vrabel@citrix.com>
---
arch/x86/xen/spinlock.c | 11 ++++++++++-
1 file changed, 10 insertions(+), 1 deletion(-)
diff --git a/arch/x86/xen/spinlock.c b/arch/x86/xen/spinlock.c
index 71db82c..e1bff87 100644
--- a/arch/x86/xen/spinlock.c
+++ b/arch/x86/xen/spinlock.c
@@ -105,6 +105,7 @@ static DEFINE_PER_CPU(char *, irq_name);
static DEFINE_PER_CPU(struct xen_lock_waiting, lock_waiting);
static cpumask_t waiting_cpus;
+static bool xen_pvspin __initdata = true;
static void xen_lock_spinning(struct arch_spinlock *lock, __ticket_t want)
{
int irq = __this_cpu_read(lock_kicker_irq);
@@ -223,6 +224,9 @@ void xen_init_lock_cpu(int cpu)
int irq;
char *name;
+ if (!xen_pvspin)
+ return;
+
WARN(per_cpu(lock_kicker_irq, cpu) >= 0, "spinlock on CPU%d exists on IRQ%d!\n",
cpu, per_cpu(lock_kicker_irq, cpu));
@@ -259,13 +263,15 @@ void xen_uninit_lock_cpu(int cpu)
if (xen_hvm_domain())
return;
+ if (!xen_pvspin)
+ return;
+
unbind_from_irqhandler(per_cpu(lock_kicker_irq, cpu), NULL);
per_cpu(lock_kicker_irq, cpu) = -1;
kfree(per_cpu(irq_name, cpu));
per_cpu(irq_name, cpu) = NULL;
}
-static bool xen_pvspin __initdata = true;
void __init xen_init_spinlocks(void)
{
@@ -305,6 +311,9 @@ static int __init xen_spinlock_debugfs(void)
if (d_xen == NULL)
return -ENOMEM;
+ if (!xen_pvspin)
+ return 0;
+
d_spin_debug = debugfs_create_dir("spinlocks", d_xen);
debugfs_create_u8("zero_stats", 0644, d_spin_debug, &zero_stats);
--
1.8.3.1
^ permalink raw reply related [flat|nested] 7+ messages in thread
* [PATCH 5/5] Revert "xen/spinlock: Disable IRQ spinlock (PV) allocation on PVHVM"
2013-09-09 15:11 [PATCH] Bug-fixes to enable PV ticketlock to work under Xen PVHVM with Linux v3.12. (v2) Konrad Rzeszutek Wilk
` (3 preceding siblings ...)
2013-09-09 15:11 ` [PATCH 4/5] xen/spinlock: Don't setup xen spinlock IPI kicker if disabled Konrad Rzeszutek Wilk
@ 2013-09-09 15:11 ` Konrad Rzeszutek Wilk
2013-09-09 15:33 ` [Xen-devel] [PATCH] Bug-fixes to enable PV ticketlock to work under Xen PVHVM with Linux v3.12. (v2) David Vrabel
5 siblings, 0 replies; 7+ messages in thread
From: Konrad Rzeszutek Wilk @ 2013-09-09 15:11 UTC (permalink / raw)
To: linux-kernel, xen-devel, boris.ostrovsky, david.vrabel,
stefan.bader, stefano.stabellini, jeremy
Cc: Konrad Rzeszutek Wilk
This reverts commit 70dd4998cb85f0ecd6ac892cc7232abefa432efb.
Now that the bugs have been resolved we can re-enable the
PV ticketlock implementation under PVHVM Xen guests.
Signed-off-by: Konrad Rzeszutek Wilk <konrad.wilk@oracle.com>
Reviewed-by: David Vrabel <david.vrabel@citrix.com>
---
arch/x86/xen/spinlock.c | 20 --------------------
1 file changed, 20 deletions(-)
diff --git a/arch/x86/xen/spinlock.c b/arch/x86/xen/spinlock.c
index e1bff87..b3c1ee8 100644
--- a/arch/x86/xen/spinlock.c
+++ b/arch/x86/xen/spinlock.c
@@ -230,13 +230,6 @@ void xen_init_lock_cpu(int cpu)
WARN(per_cpu(lock_kicker_irq, cpu) >= 0, "spinlock on CPU%d exists on IRQ%d!\n",
cpu, per_cpu(lock_kicker_irq, cpu));
- /*
- * See git commit f10cd522c5fbfec9ae3cc01967868c9c2401ed23
- * (xen: disable PV spinlocks on HVM)
- */
- if (xen_hvm_domain())
- return;
-
name = kasprintf(GFP_KERNEL, "spinlock%d", cpu);
irq = bind_ipi_to_irqhandler(XEN_SPIN_UNLOCK_VECTOR,
cpu,
@@ -256,13 +249,6 @@ void xen_init_lock_cpu(int cpu)
void xen_uninit_lock_cpu(int cpu)
{
- /*
- * See git commit f10cd522c5fbfec9ae3cc01967868c9c2401ed23
- * (xen: disable PV spinlocks on HVM)
- */
- if (xen_hvm_domain())
- return;
-
if (!xen_pvspin)
return;
@@ -275,12 +261,6 @@ void xen_uninit_lock_cpu(int cpu)
void __init xen_init_spinlocks(void)
{
- /*
- * See git commit f10cd522c5fbfec9ae3cc01967868c9c2401ed23
- * (xen: disable PV spinlocks on HVM)
- */
- if (xen_hvm_domain())
- return;
if (!xen_pvspin) {
printk(KERN_DEBUG "xen: PV spinlocks disabled\n");
--
1.8.3.1
^ permalink raw reply related [flat|nested] 7+ messages in thread
* Re: [Xen-devel] [PATCH] Bug-fixes to enable PV ticketlock to work under Xen PVHVM with Linux v3.12. (v2)
2013-09-09 15:11 [PATCH] Bug-fixes to enable PV ticketlock to work under Xen PVHVM with Linux v3.12. (v2) Konrad Rzeszutek Wilk
` (4 preceding siblings ...)
2013-09-09 15:11 ` [PATCH 5/5] Revert "xen/spinlock: Disable IRQ spinlock (PV) allocation on PVHVM" Konrad Rzeszutek Wilk
@ 2013-09-09 15:33 ` David Vrabel
5 siblings, 0 replies; 7+ messages in thread
From: David Vrabel @ 2013-09-09 15:33 UTC (permalink / raw)
To: Konrad Rzeszutek Wilk
Cc: linux-kernel, xen-devel, boris.ostrovsky, david.vrabel,
stefan.bader, stefano.stabellini, jeremy
On 09/09/13 16:11, Konrad Rzeszutek Wilk wrote:
>
> I had run some light performance tests with two guests - each over subscribed by
> 2:1 and running a spinlock_hog wherein each CPU tries to get a lock. The machine
> is a 4 CPU Intel, and each guest is running with 8 VCPUs.
>
> It is not a perfect test-case - for that I have asked our internal performance
> engineer to test it out with various workloads and guests.
>
> However it does demonstrate that these patches do work and they do not
> incur any performance regressions (and yes, they do show a performance
> improvement).
Good enough for me, let's get these into 3.12.
David
^ permalink raw reply [flat|nested] 7+ messages in thread
end of thread, other threads:[~2013-09-09 15:33 UTC | newest]
Thread overview: 7+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2013-09-09 15:11 [PATCH] Bug-fixes to enable PV ticketlock to work under Xen PVHVM with Linux v3.12. (v2) Konrad Rzeszutek Wilk
2013-09-09 15:11 ` [PATCH 1/5] xen/spinlock: Fix locking path engaging too soon under PVHVM Konrad Rzeszutek Wilk
2013-09-09 15:11 ` [PATCH 2/5] xen/spinlock: We don't need the old structure anymore Konrad Rzeszutek Wilk
2013-09-09 15:11 ` [PATCH 3/5] xen/smp: Update pv_lock_ops functions before alternative code starts under PVHVM Konrad Rzeszutek Wilk
2013-09-09 15:11 ` [PATCH 4/5] xen/spinlock: Don't setup xen spinlock IPI kicker if disabled Konrad Rzeszutek Wilk
2013-09-09 15:11 ` [PATCH 5/5] Revert "xen/spinlock: Disable IRQ spinlock (PV) allocation on PVHVM" Konrad Rzeszutek Wilk
2013-09-09 15:33 ` [Xen-devel] [PATCH] Bug-fixes to enable PV ticketlock to work under Xen PVHVM with Linux v3.12. (v2) David Vrabel
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox