From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from mga18.intel.com (mga18.intel.com [134.134.136.126]) by dpdk.org (Postfix) with ESMTP id 500E71D7 for ; Tue, 13 Nov 2018 18:27:49 +0100 (CET) X-Amp-Result: SKIPPED(no attachment in message) X-Amp-File-Uploaded: False Received: from orsmga004.jf.intel.com ([10.7.209.38]) by orsmga106.jf.intel.com with ESMTP/TLS/DHE-RSA-AES256-GCM-SHA384; 13 Nov 2018 09:27:48 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.56,228,1539673200"; d="scan'208";a="249395709" Received: from sivswdev08.ir.intel.com (HELO localhost.localdomain) ([10.237.217.47]) by orsmga004.jf.intel.com with ESMTP; 13 Nov 2018 09:27:47 -0800 From: Konstantin Ananyev To: dev@dpdk.org Cc: Konstantin Ananyev Date: Tue, 13 Nov 2018 17:27:40 +0000 Message-Id: <1542130061-3702-2-git-send-email-konstantin.ananyev@intel.com> X-Mailer: git-send-email 1.7.0.7 In-Reply-To: <1542130061-3702-1-git-send-email-konstantin.ananyev@intel.com> References: <1542130061-3702-1-git-send-email-konstantin.ananyev@intel.com> Subject: [dpdk-dev] [PATCH 1/2] rwlock: introduce 'try' semantics for RD and WR locking X-BeenThere: dev@dpdk.org X-Mailman-Version: 2.1.15 Precedence: list List-Id: DPDK patches and discussions List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Tue, 13 Nov 2018 17:27:49 -0000 This patch targets 19.02 release. Introduce rte_rwlock_read_trylock() and rte_rwlock_write_trylock(). Signed-off-by: Konstantin Ananyev --- .../common/include/generic/rte_rwlock.h | 54 +++++++++++++++++++ lib/librte_eal/rte_eal_version.map | 2 + 2 files changed, 56 insertions(+) diff --git a/lib/librte_eal/common/include/generic/rte_rwlock.h b/lib/librte_eal/common/include/generic/rte_rwlock.h index 5751a0e6d..7e395781e 100644 --- a/lib/librte_eal/common/include/generic/rte_rwlock.h +++ b/lib/librte_eal/common/include/generic/rte_rwlock.h @@ -75,6 +75,33 @@ rte_rwlock_read_lock(rte_rwlock_t *rwl) } } +/** + * try to take a read lock. + * + * @param rwl + * A pointer to a rwlock structure. + * @return + * - zero if the lock is successfully taken + * - -EBUSY if lock could not be acquired for reading because a + * writer holds the lock + */ +static inline __rte_experimental int +rte_rwlock_read_trylock(rte_rwlock_t *rwl) +{ + int32_t x; + int success = 0; + + while (success == 0) { + x = rwl->cnt; + /* write lock is held */ + if (x < 0) + return -EBUSY; + success = rte_atomic32_cmpset((volatile uint32_t *)&rwl->cnt, + (uint32_t)x, (uint32_t)(x + 1)); + } + return 0; +} + /** * Release a read lock. * @@ -87,6 +114,33 @@ rte_rwlock_read_unlock(rte_rwlock_t *rwl) rte_atomic32_dec((rte_atomic32_t *)(intptr_t)&rwl->cnt); } +/** + * try to take a write lock. + * + * @param rwl + * A pointer to a rwlock structure. + * @return + * - zero if the lock is successfully taken + * - -EBUSY if lock could not be acquired for writing because + * it was already locked for reading or writing + */ +static inline __rte_experimental int +rte_rwlock_write_trylock(rte_rwlock_t *rwl) +{ + int32_t x; + int success = 0; + + while (success == 0) { + x = rwl->cnt; + /* a lock is held */ + if (x != 0) + return -EBUSY; + success = rte_atomic32_cmpset((volatile uint32_t *)&rwl->cnt, + 0, (uint32_t)-1); + } + return 0; +} + /** * Take a write lock. Loop until the lock is held. * diff --git a/lib/librte_eal/rte_eal_version.map b/lib/librte_eal/rte_eal_version.map index 3fe78260d..8b1593dd8 100644 --- a/lib/librte_eal/rte_eal_version.map +++ b/lib/librte_eal/rte_eal_version.map @@ -355,6 +355,8 @@ EXPERIMENTAL { rte_mp_request_async; rte_mp_sendmsg; rte_option_register; + rte_rwlock_read_trylock; + rte_rwlock_write_trylock; rte_service_lcore_attr_get; rte_service_lcore_attr_reset_all; rte_service_may_be_active; -- 2.17.1