lkml.org 
[lkml]   [2021]   [Feb]   [9]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
/
SubjectRe: [PATCH v2 06/28] locking/rwlocks: Add contention detection for rwlocks
From
Date
On 2/2/21 1:57 PM, Ben Gardon wrote:
> rwlocks do not currently have any facility to detect contention
> like spinlocks do. In order to allow users of rwlocks to better manage
> latency, add contention detection for queued rwlocks.
>
> CC: Ingo Molnar <mingo@redhat.com>
> CC: Will Deacon <will@kernel.org>
> Acked-by: Peter Zijlstra <peterz@infradead.org>
> Acked-by: Davidlohr Bueso <dbueso@suse.de>
> Acked-by: Waiman Long <longman@redhat.com>
> Acked-by: Paolo Bonzini <pbonzini@redhat.com>
> Signed-off-by: Ben Gardon <bgardon@google.com>
> ---
> include/asm-generic/qrwlock.h | 24 ++++++++++++++++++------
> include/linux/rwlock.h | 7 +++++++
> 2 files changed, 25 insertions(+), 6 deletions(-)
>
> diff --git a/include/asm-generic/qrwlock.h b/include/asm-generic/qrwlock.h
> index 84ce841ce735..0020d3b820a7 100644
> --- a/include/asm-generic/qrwlock.h
> +++ b/include/asm-generic/qrwlock.h
> @@ -14,6 +14,7 @@
> #include <asm/processor.h>
>
> #include <asm-generic/qrwlock_types.h>
> +#include <asm-generic/qspinlock.h>

As said in another thread, qspinlock and qrwlock can be independently
enabled for an architecture. So we shouldn't include qspinlock.h here.
Instead, just include the regular linux/spinlock.h file to make sure
that arch_spin_is_locked() is available.


>
> /*
> * Writer states & reader shift and bias.
> @@ -116,15 +117,26 @@ static inline void queued_write_unlock(struct qrwlock *lock)
> smp_store_release(&lock->wlocked, 0);
> }
>
> +/**
> + * queued_rwlock_is_contended - check if the lock is contended
> + * @lock : Pointer to queue rwlock structure
> + * Return: 1 if lock contended, 0 otherwise
> + */
> +static inline int queued_rwlock_is_contended(struct qrwlock *lock)
> +{
> + return arch_spin_is_locked(&lock->wait_lock);
> +}
> +
> /*
> * Remapping rwlock architecture specific functions to the corresponding
> * queue rwlock functions.
> */
> -#define arch_read_lock(l) queued_read_lock(l)
> -#define arch_write_lock(l) queued_write_lock(l)
> -#define arch_read_trylock(l) queued_read_trylock(l)
> -#define arch_write_trylock(l) queued_write_trylock(l)
> -#define arch_read_unlock(l) queued_read_unlock(l)
> -#define arch_write_unlock(l) queued_write_unlock(l)
> +#define arch_read_lock(l) queued_read_lock(l)
> +#define arch_write_lock(l) queued_write_lock(l)
> +#define arch_read_trylock(l) queued_read_trylock(l)
> +#define arch_write_trylock(l) queued_write_trylock(l)
> +#define arch_read_unlock(l) queued_read_unlock(l)
> +#define arch_write_unlock(l) queued_write_unlock(l)
> +#define arch_rwlock_is_contended(l) queued_rwlock_is_contended(l)
>
> #endif /* __ASM_GENERIC_QRWLOCK_H */
> diff --git a/include/linux/rwlock.h b/include/linux/rwlock.h
> index 3dcd617e65ae..7ce9a51ae5c0 100644
> --- a/include/linux/rwlock.h
> +++ b/include/linux/rwlock.h
> @@ -128,4 +128,11 @@ do { \
> 1 : ({ local_irq_restore(flags); 0; }); \
> })
>
> +#ifdef arch_rwlock_is_contended
> +#define rwlock_is_contended(lock) \
> + arch_rwlock_is_contended(&(lock)->raw_lock)
> +#else
> +#define rwlock_is_contended(lock) ((void)(lock), 0)
> +#endif /* arch_rwlock_is_contended */
> +
> #endif /* __LINUX_RWLOCK_H */

Cheers,
Longman

\
 
 \ /
  Last update: 2021-02-10 04:35    [W:0.291 / U:1.052 seconds]
©2003-2020 Jasper Spaans|hosted at Digital Ocean and TransIP|Read the blog|Advertise on this site