You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@nuttx.apache.org by ac...@apache.org on 2024/03/26 16:53:45 UTC

(nuttx) branch master updated (86bb721d80 -> 075b0e5ac0)

This is an automated email from the ASF dual-hosted git repository.

acassis pushed a change to branch master
in repository https://gitbox.apache.org/repos/asf/nuttx.git


    from 86bb721d80 nuttx/mqueue: fix build break if disable posix message queue
     new 44e2e9011f esp32s3: Update libc stubs to properly acquire/release locks.
     new d56e6de628 esp32: Update libc stubs to properly acquire/release locks.
     new 075b0e5ac0 esp32s2: Update libc stubs to properly acquire/release locks.

The 3 revisions listed above as "new" are entirely new to this
repository and will be described in separate emails.  The revisions
listed as "add" were already present in the repository and have only
been added to this reference.


Summary of changes:
 arch/xtensa/src/common/espressif/Make.defs         |   2 +
 .../espressif/platform_include/sys/lock.h}         | 183 +++++++++------------
 arch/xtensa/src/esp32/esp32_libc_stubs.c           |  98 +++++++----
 arch/xtensa/src/esp32s2/esp32s2_libc_stubs.c       |  98 +++++++----
 arch/xtensa/src/esp32s3/Make.defs                  |   1 +
 arch/xtensa/src/esp32s3/esp32s3_libc_stubs.c       |  91 +++++++---
 arch/xtensa/src/esp32s3/rom/esp32s3_libc_stubs.h   |   3 +-
 7 files changed, 284 insertions(+), 192 deletions(-)
 copy arch/xtensa/src/{esp32/esp32_pm.h => common/espressif/platform_include/sys/lock.h} (57%)


(nuttx) 01/03: esp32s3: Update libc stubs to properly acquire/release locks.

Posted by ac...@apache.org.
This is an automated email from the ASF dual-hosted git repository.

acassis pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/nuttx.git

commit 44e2e9011f8ccaa3d3c0b15ccef23dc177fa3123
Author: Tiago Medicci Serrano <ti...@espressif.com>
AuthorDate: Thu Mar 7 15:48:55 2024 -0300

    esp32s3: Update libc stubs to properly acquire/release locks.
    
    Avoid using static mutex and recursive mutex as the resource to be
    acquired/release. Instead, create a specific lock for each call if
    it does not exist.
---
 arch/xtensa/src/common/espressif/Make.defs         |   2 +
 .../common/espressif/platform_include/sys/lock.h   | 213 +++++++++++++++++++++
 arch/xtensa/src/esp32s3/Make.defs                  |   1 +
 arch/xtensa/src/esp32s3/esp32s3_libc_stubs.c       |  91 ++++++---
 arch/xtensa/src/esp32s3/rom/esp32s3_libc_stubs.h   |   3 +-
 5 files changed, 283 insertions(+), 27 deletions(-)

diff --git a/arch/xtensa/src/common/espressif/Make.defs b/arch/xtensa/src/common/espressif/Make.defs
index 3a48c6b4a7..2034dbeebf 100644
--- a/arch/xtensa/src/common/espressif/Make.defs
+++ b/arch/xtensa/src/common/espressif/Make.defs
@@ -24,3 +24,5 @@ ifeq ($(CONFIG_WS2812_NON_SPI_DRIVER),y)
 CHIP_CSRCS += esp_ws2812.c
 endif
 endif
+
+INCLUDES += ${INCDIR_PREFIX}$(ARCH_SRCDIR)$(DELIM)common$(DELIM)espressif$(DELIM)platform_include
diff --git a/arch/xtensa/src/common/espressif/platform_include/sys/lock.h b/arch/xtensa/src/common/espressif/platform_include/sys/lock.h
new file mode 100644
index 0000000000..94e4809034
--- /dev/null
+++ b/arch/xtensa/src/common/espressif/platform_include/sys/lock.h
@@ -0,0 +1,213 @@
+/****************************************************************************
+ * arch/xtensa/src/common/espressif/platform_include/sys/lock.h
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.  The
+ * ASF licenses this file to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance with the
+ * License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.  See the
+ * License for the specific language governing permissions and limitations
+ * under the License.
+ *
+ ****************************************************************************/
+
+#pragma once
+
+/****************************************************************************
+ * Included Files
+ ****************************************************************************/
+
+#include_next <sys/lock.h>
+
+#ifdef _RETARGETABLE_LOCKING
+
+/****************************************************************************
+ * Public Type Definitions
+ ****************************************************************************/
+
+/* Actual platfrom-specific definition of struct __lock.
+ * The size here should be sufficient for a NuttX mutex and recursive mutex.
+ * This is checked by a static assertion in <chip>_libc_stubs.c
+ */
+
+struct __lock
+{
+  int reserved[4];
+};
+
+typedef _LOCK_T _lock_t;
+
+/****************************************************************************
+ * Public Function Prototypes
+ ****************************************************************************/
+
+/****************************************************************************
+ * Name: _lock_init
+ *
+ * Description:
+ *   Allocate lock related resources.
+ *
+ * Input Parameters:
+ *   plock - pointer to user defined lock object
+ *
+ * Returned Value:
+ *   None
+ *
+ ****************************************************************************/
+
+void _lock_init(_lock_t *plock);
+
+/****************************************************************************
+ * Name: _lock_init_recursive
+ *
+ * Description:
+ *   Allocate recursive lock related resources.
+ *
+ * Input Parameters:
+ *   plock - pointer to user defined lock object
+ *
+ * Returned Value:
+ *   None
+ *
+ ****************************************************************************/
+
+void _lock_init_recursive(_lock_t *plock);
+
+/****************************************************************************
+ * Name: _lock_close
+ *
+ * Description:
+ *   Free lock related resources.
+ *
+ * Input Parameters:
+ *   plock - pointer to user defined lock object
+ *
+ * Returned Value:
+ *   None
+ *
+ ****************************************************************************/
+
+void _lock_close(_lock_t *plock);
+
+/****************************************************************************
+ * Name: _lock_close_recursive
+ *
+ * Description:
+ *   Free recursive lock related resources.
+ *
+ * Input Parameters:
+ *   plock - pointer to user defined lock object
+ *
+ * Returned Value:
+ *   None
+ *
+ ****************************************************************************/
+
+void _lock_close_recursive(_lock_t *plock);
+
+/****************************************************************************
+ * Name: _lock_acquire
+ *
+ * Description:
+ *   Acquire lock immediately after the lock object is available.
+ *
+ * Input Parameters:
+ *   plock - pointer to user defined lock object
+ *
+ * Returned Value:
+ *   None
+ *
+ ****************************************************************************/
+
+void _lock_acquire(_lock_t *plock);
+
+/****************************************************************************
+ * Name: _lock_acquire_recursive
+ *
+ * Description:
+ *   Acquire recursive lock immediately after the lock object is available.
+ *
+ * Input Parameters:
+ *   plock - pointer to user defined lock object
+ *
+ * Returned Value:
+ *   None
+ *
+ ****************************************************************************/
+
+void _lock_acquire_recursive(_lock_t *plock);
+
+/****************************************************************************
+ * Name: _lock_try_acquire
+ *
+ * Description:
+ *   Acquire lock if the lock object is available.
+ *
+ * Input Parameters:
+ *   plock - pointer to user defined lock object
+ *
+ * Returned Value:
+ *   Zero for success and non-zero to indicate that the lock cannot be
+ *   acquired
+ *
+ ****************************************************************************/
+
+int _lock_try_acquire(_lock_t *plock);
+
+/****************************************************************************
+ * Name: _lock_try_acquire_recursive
+ *
+ * Description:
+ *   Acquire recursive lock if the lock object is available.
+ *
+ * Input Parameters:
+ *   plock - pointer to user defined lock object
+ *
+ * Returned Value:
+ *   Zero for success and non-zero to indicate that the lock cannot be
+ *   acquired
+ *
+ ****************************************************************************/
+
+int _lock_try_acquire_recursive(_lock_t *plock);
+
+/****************************************************************************
+ * Name: _lock_release
+ *
+ * Description:
+ *   Relinquish the lock ownership.
+ *
+ * Input Parameters:
+ *   plock - pointer to user defined lock object
+ *
+ * Returned Value:
+ *   None
+ *
+ ****************************************************************************/
+
+void _lock_release(_lock_t *plock);
+
+/****************************************************************************
+ * Name: _lock_release_recursive
+ *
+ * Description:
+ *   Relinquish the recursive lock ownership.
+ *
+ * Input Parameters:
+ *   plock - pointer to user defined lock object
+ *
+ * Returned Value:
+ *   None
+ *
+ ****************************************************************************/
+
+void _lock_release_recursive(_lock_t *plock);
+
+#endif // _RETARGETABLE_LOCKING
diff --git a/arch/xtensa/src/esp32s3/Make.defs b/arch/xtensa/src/esp32s3/Make.defs
index 1785c6bc21..da5838b851 100644
--- a/arch/xtensa/src/esp32s3/Make.defs
+++ b/arch/xtensa/src/esp32s3/Make.defs
@@ -207,6 +207,7 @@ chip/$(ESP_HAL_3RDPARTY_REPO):
 # Silent preprocessor warnings
 
 CFLAGS += -Wno-undef -Wno-unused-variable
+CFLAGS += ${DEFINE_PREFIX}_RETARGETABLE_LOCKING
 
 # Files that require the HAL recipe
 
diff --git a/arch/xtensa/src/esp32s3/esp32s3_libc_stubs.c b/arch/xtensa/src/esp32s3/esp32s3_libc_stubs.c
index 56528eb1cf..dd729389de 100644
--- a/arch/xtensa/src/esp32s3/esp32s3_libc_stubs.c
+++ b/arch/xtensa/src/esp32s3/esp32s3_libc_stubs.c
@@ -42,17 +42,12 @@
  * Pre-processor Definitions
  ****************************************************************************/
 
-#define _lock_t int
-
 #define ROM_MUTEX_MAGIC   0xbb10c433
 
 /****************************************************************************
  * Private Types
  ****************************************************************************/
 
-static mutex_t g_nxlock_common;
-static mutex_t g_nxlock_recursive;
-
 /* Forward declaration */
 
 struct _reent;
@@ -173,64 +168,108 @@ void _raise_r(struct _reent *r)
 
 void _lock_init(_lock_t *lock)
 {
-  nxmutex_init(&g_nxlock_common);
-  nxsem_get_value(&g_nxlock_common.sem, lock);
+  mutex_t *mutex = (mutex_t *)kmm_malloc(sizeof(mutex_t));
+
+  nxmutex_init(mutex);
+
+  *lock = (_lock_t)mutex;
 }
 
 void _lock_init_recursive(_lock_t *lock)
 {
-  nxmutex_init(&g_nxlock_recursive);
-  nxsem_get_value(&g_nxlock_recursive.sem, lock);
+  rmutex_t *rmutex = (rmutex_t *)kmm_malloc(sizeof(rmutex_t));
+
+  nxrmutex_init(rmutex);
+
+  *lock = (_lock_t)rmutex;
 }
 
 void _lock_close(_lock_t *lock)
 {
-  nxmutex_destroy(&g_nxlock_common);
+  mutex_t *mutex = (mutex_t *)(*lock);
+
+  nxmutex_destroy(mutex);
+  kmm_free(*lock);
   *lock = 0;
 }
 
 void _lock_close_recursive(_lock_t *lock)
 {
-  nxmutex_destroy(&g_nxlock_recursive);
+  rmutex_t *rmutex = (rmutex_t *)(*lock);
+
+  nxrmutex_destroy(rmutex);
+  kmm_free(*lock);
   *lock = 0;
 }
 
 void _lock_acquire(_lock_t *lock)
 {
-  nxmutex_lock(&g_nxlock_common);
-  nxsem_get_value(&g_nxlock_common.sem, lock);
+  if ((*lock) == NULL)
+    {
+      mutex_t *mutex = (mutex_t *)kmm_malloc(sizeof(mutex_t));
+
+      nxmutex_init(mutex);
+
+      *lock = (_lock_t)mutex;
+    }
+
+  nxmutex_lock((mutex_t *)(*lock));
 }
 
 void _lock_acquire_recursive(_lock_t *lock)
 {
-  nxmutex_lock(&g_nxlock_recursive);
-  nxsem_get_value(&g_nxlock_recursive.sem, lock);
+  if ((*lock) == NULL)
+    {
+      rmutex_t *rmutex = (rmutex_t *)kmm_malloc(sizeof(rmutex_t));
+
+      nxrmutex_init(rmutex);
+
+      *lock = (_lock_t)rmutex;
+    }
+
+  nxrmutex_lock((rmutex_t *)(*lock));
 }
 
 int _lock_try_acquire(_lock_t *lock)
 {
-  nxmutex_trylock(&g_nxlock_common);
-  nxsem_get_value(&g_nxlock_common.sem, lock);
-  return 0;
+  if ((*lock) == NULL)
+    {
+      mutex_t *mutex = (mutex_t *)kmm_malloc(sizeof(mutex_t));
+
+      nxmutex_init(mutex);
+
+      *lock = (_lock_t)mutex;
+    }
+
+  return nxmutex_trylock((mutex_t *)(*lock));
 }
 
 int _lock_try_acquire_recursive(_lock_t *lock)
 {
-  nxmutex_trylock(&g_nxlock_recursive);
-  nxsem_get_value(&g_nxlock_recursive.sem, lock);
-  return 0;
+  if ((*lock) == NULL)
+    {
+      rmutex_t *rmutex = (rmutex_t *)kmm_malloc(sizeof(rmutex_t));
+
+      nxrmutex_init(rmutex);
+
+      *lock = (_lock_t)rmutex;
+    }
+
+  return nxrmutex_trylock((rmutex_t *)(*lock));
 }
 
 void _lock_release(_lock_t *lock)
 {
-  nxmutex_unlock(&g_nxlock_common);
-  nxsem_get_value(&g_nxlock_common.sem, lock);
+  mutex_t *mutex = (mutex_t *)(*lock);
+
+  nxmutex_unlock(mutex);
 }
 
 void _lock_release_recursive(_lock_t *lock)
 {
-  nxmutex_unlock(&g_nxlock_recursive);
-  nxsem_get_value(&g_nxlock_recursive.sem, lock);
+  rmutex_t *rmutex = (rmutex_t *)(*lock);
+
+  nxrmutex_unlock(rmutex);
 }
 
 void __retarget_lock_init(_lock_t *lock)
@@ -376,6 +415,8 @@ static const struct syscall_stub_table g_stub_table =
 
 void esp_setup_syscall_table(void)
 {
+  static_assert(sizeof(struct __lock) >= sizeof(mutex_t));
+
   syscall_table_ptr = (struct syscall_stub_table *)&g_stub_table;
 
   /* Newlib 3.3.0 is used in ROM, built with _RETARGETABLE_LOCKING.
diff --git a/arch/xtensa/src/esp32s3/rom/esp32s3_libc_stubs.h b/arch/xtensa/src/esp32s3/rom/esp32s3_libc_stubs.h
index ffc0d0f3d1..c7cc0cb327 100644
--- a/arch/xtensa/src/esp32s3/rom/esp32s3_libc_stubs.h
+++ b/arch/xtensa/src/esp32s3/rom/esp32s3_libc_stubs.h
@@ -27,6 +27,7 @@
 
 #include <stdio.h>
 
+#include <sys/lock.h>
 #include <sys/time.h>
 #include <sys/times.h>
 #include <sys/types.h>
@@ -38,8 +39,6 @@
 
 #include <nuttx/mutex.h>
 
-#define _lock_t int
-
 /* Forward declaration */
 
 struct _reent;


(nuttx) 02/03: esp32: Update libc stubs to properly acquire/release locks.

Posted by ac...@apache.org.
This is an automated email from the ASF dual-hosted git repository.

acassis pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/nuttx.git

commit d56e6de62832c7613d276155f08c8dc06e79d07e
Author: Tiago Medicci Serrano <ti...@espressif.com>
AuthorDate: Thu Mar 21 17:57:01 2024 -0300

    esp32: Update libc stubs to properly acquire/release locks.
    
    Avoid using static mutex and recursive mutex as the resource to be
    acquired/release. Instead, create a specific lock for each call if
    it does not exist.
---
 arch/xtensa/src/esp32/esp32_libc_stubs.c | 98 +++++++++++++++++++++++---------
 1 file changed, 70 insertions(+), 28 deletions(-)

diff --git a/arch/xtensa/src/esp32/esp32_libc_stubs.c b/arch/xtensa/src/esp32/esp32_libc_stubs.c
index 66f8047230..2cd2bf0695 100644
--- a/arch/xtensa/src/esp32/esp32_libc_stubs.c
+++ b/arch/xtensa/src/esp32/esp32_libc_stubs.c
@@ -38,18 +38,12 @@
 
 #include "rom/esp32_libc_stubs.h"
 
-/****************************************************************************
- * Pre-processor Definitions
- ****************************************************************************/
-
-#define _lock_t int
-
 /****************************************************************************
  * Private Types
  ****************************************************************************/
 
-static mutex_t g_nxlock_common;
-static mutex_t g_nxlock_recursive;
+static mutex_t g_nxlock_common    = NXMUTEX_INITIALIZER;
+static mutex_t g_nxlock_recursive = NXMUTEX_INITIALIZER;
 
 /* Forward declaration */
 
@@ -171,64 +165,112 @@ void _raise_r(struct _reent *r)
 
 void _lock_init(_lock_t *lock)
 {
-  nxmutex_init(&g_nxlock_common);
-  nxsem_get_value(&g_nxlock_common.sem, lock);
+  *lock = 0;
+
+  mutex_t *mutex = (mutex_t *)kmm_malloc(sizeof(mutex_t));
+
+  nxmutex_init(mutex);
+
+  *lock = (_lock_t)mutex;
 }
 
 void _lock_init_recursive(_lock_t *lock)
 {
-  nxmutex_init(&g_nxlock_recursive);
-  nxsem_get_value(&g_nxlock_recursive.sem, lock);
+  *lock = 0;
+
+  rmutex_t *rmutex = (rmutex_t *)kmm_malloc(sizeof(rmutex_t));
+
+  nxrmutex_init(rmutex);
+
+  *lock = (_lock_t)rmutex;
 }
 
 void _lock_close(_lock_t *lock)
 {
-  nxmutex_destroy(&g_nxlock_common);
+  mutex_t *mutex = (mutex_t *)(*lock);
+
+  nxmutex_destroy(mutex);
+  kmm_free((void *)(*lock));
   *lock = 0;
 }
 
 void _lock_close_recursive(_lock_t *lock)
 {
-  nxmutex_destroy(&g_nxlock_recursive);
+  rmutex_t *rmutex = (rmutex_t *)(*lock);
+
+  nxrmutex_destroy(rmutex);
+  kmm_free((void *)(*lock));
   *lock = 0;
 }
 
 void _lock_acquire(_lock_t *lock)
 {
-  nxmutex_lock(&g_nxlock_common);
-  nxsem_get_value(&g_nxlock_common.sem, lock);
+  if ((*lock) == 0)
+    {
+      mutex_t *mutex = (mutex_t *)kmm_malloc(sizeof(mutex_t));
+
+      nxmutex_init(mutex);
+
+      *lock = (_lock_t)mutex;
+    }
+
+  nxmutex_lock((mutex_t *)(*lock));
 }
 
 void _lock_acquire_recursive(_lock_t *lock)
 {
-  nxmutex_lock(&g_nxlock_recursive);
-  nxsem_get_value(&g_nxlock_recursive.sem, lock);
+  if ((*lock) == 0)
+    {
+      rmutex_t *rmutex = (rmutex_t *)kmm_malloc(sizeof(rmutex_t));
+
+      nxrmutex_init(rmutex);
+
+      *lock = (_lock_t)rmutex;
+    }
+
+  nxrmutex_lock((rmutex_t *)(*lock));
 }
 
 int _lock_try_acquire(_lock_t *lock)
 {
-  nxmutex_trylock(&g_nxlock_common);
-  nxsem_get_value(&g_nxlock_common.sem, lock);
-  return 0;
+  if ((*lock) == 0)
+    {
+      mutex_t *mutex = (mutex_t *)kmm_malloc(sizeof(mutex_t));
+
+      nxmutex_init(mutex);
+
+      *lock = (_lock_t)mutex;
+    }
+
+  return nxmutex_trylock((mutex_t *)(*lock));
 }
 
 int _lock_try_acquire_recursive(_lock_t *lock)
 {
-  nxmutex_trylock(&g_nxlock_recursive);
-  nxsem_get_value(&g_nxlock_recursive.sem, lock);
-  return 0;
+  if ((*lock) == 0)
+    {
+      rmutex_t *rmutex = (rmutex_t *)kmm_malloc(sizeof(rmutex_t));
+
+      nxrmutex_init(rmutex);
+
+      *lock = (_lock_t)rmutex;
+    }
+
+  return nxrmutex_trylock((rmutex_t *)(*lock));
 }
 
 void _lock_release(_lock_t *lock)
 {
-  nxmutex_unlock(&g_nxlock_common);
-  nxsem_get_value(&g_nxlock_common.sem, lock);
+  mutex_t *mutex = (mutex_t *)(*lock);
+
+  nxmutex_unlock(mutex);
 }
 
 void _lock_release_recursive(_lock_t *lock)
 {
-  nxmutex_unlock(&g_nxlock_recursive);
-  nxsem_get_value(&g_nxlock_recursive.sem, lock);
+  rmutex_t *rmutex = (rmutex_t *)(*lock);
+
+  nxrmutex_unlock(rmutex);
 }
 
 struct _reent *__getreent(void)


(nuttx) 03/03: esp32s2: Update libc stubs to properly acquire/release locks.

Posted by ac...@apache.org.
This is an automated email from the ASF dual-hosted git repository.

acassis pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/nuttx.git

commit 075b0e5ac0bad0a93d316ea562abf09fd65a0041
Author: Tiago Medicci Serrano <ti...@espressif.com>
AuthorDate: Fri Mar 22 16:13:14 2024 -0300

    esp32s2: Update libc stubs to properly acquire/release locks.
    
    Avoid using static mutex and recursive mutex as the resource to be
    acquired/release. Instead, create a specific lock for each call if
    it does not exist.
---
 arch/xtensa/src/esp32s2/esp32s2_libc_stubs.c | 98 ++++++++++++++++++++--------
 1 file changed, 70 insertions(+), 28 deletions(-)

diff --git a/arch/xtensa/src/esp32s2/esp32s2_libc_stubs.c b/arch/xtensa/src/esp32s2/esp32s2_libc_stubs.c
index 2415d83109..49e353fc4b 100644
--- a/arch/xtensa/src/esp32s2/esp32s2_libc_stubs.c
+++ b/arch/xtensa/src/esp32s2/esp32s2_libc_stubs.c
@@ -38,18 +38,12 @@
 
 #include "rom/esp32s2_libc_stubs.h"
 
-/****************************************************************************
- * Pre-processor Definitions
- ****************************************************************************/
-
-#define _lock_t int
-
 /****************************************************************************
  * Private Types
  ****************************************************************************/
 
-static mutex_t g_nxlock_common;
-static mutex_t g_nxlock_recursive;
+static mutex_t g_nxlock_common    = NXMUTEX_INITIALIZER;
+static mutex_t g_nxlock_recursive = NXMUTEX_INITIALIZER;
 
 /* Forward declaration */
 
@@ -171,64 +165,112 @@ void _raise_r(struct _reent *r)
 
 void _lock_init(_lock_t *lock)
 {
-  nxmutex_init(&g_nxlock_common);
-  nxsem_get_value(&g_nxlock_common.sem, lock);
+  *lock = 0;
+
+  mutex_t *mutex = (mutex_t *)kmm_malloc(sizeof(mutex_t));
+
+  nxmutex_init(mutex);
+
+  *lock = (_lock_t)mutex;
 }
 
 void _lock_init_recursive(_lock_t *lock)
 {
-  nxmutex_init(&g_nxlock_recursive);
-  nxsem_get_value(&g_nxlock_recursive.sem, lock);
+  *lock = 0;
+
+  rmutex_t *rmutex = (rmutex_t *)kmm_malloc(sizeof(rmutex_t));
+
+  nxrmutex_init(rmutex);
+
+  *lock = (_lock_t)rmutex;
 }
 
 void _lock_close(_lock_t *lock)
 {
-  nxmutex_destroy(&g_nxlock_common);
+  mutex_t *mutex = (mutex_t *)(*lock);
+
+  nxmutex_destroy(mutex);
+  kmm_free((void *)(*lock));
   *lock = 0;
 }
 
 void _lock_close_recursive(_lock_t *lock)
 {
-  nxmutex_destroy(&g_nxlock_recursive);
+  rmutex_t *rmutex = (rmutex_t *)(*lock);
+
+  nxrmutex_destroy(rmutex);
+  kmm_free((void *)(*lock));
   *lock = 0;
 }
 
 void _lock_acquire(_lock_t *lock)
 {
-  nxmutex_lock(&g_nxlock_common);
-  nxsem_get_value(&g_nxlock_common.sem, lock);
+  if ((*lock) == 0)
+    {
+      mutex_t *mutex = (mutex_t *)kmm_malloc(sizeof(mutex_t));
+
+      nxmutex_init(mutex);
+
+      *lock = (_lock_t)mutex;
+    }
+
+  nxmutex_lock((mutex_t *)(*lock));
 }
 
 void _lock_acquire_recursive(_lock_t *lock)
 {
-  nxmutex_lock(&g_nxlock_recursive);
-  nxsem_get_value(&g_nxlock_recursive.sem, lock);
+  if ((*lock) == 0)
+    {
+      rmutex_t *rmutex = (rmutex_t *)kmm_malloc(sizeof(rmutex_t));
+
+      nxrmutex_init(rmutex);
+
+      *lock = (_lock_t)rmutex;
+    }
+
+  nxrmutex_lock((rmutex_t *)(*lock));
 }
 
 int _lock_try_acquire(_lock_t *lock)
 {
-  nxmutex_trylock(&g_nxlock_common);
-  nxsem_get_value(&g_nxlock_common.sem, lock);
-  return 0;
+  if ((*lock) == 0)
+    {
+      mutex_t *mutex = (mutex_t *)kmm_malloc(sizeof(mutex_t));
+
+      nxmutex_init(mutex);
+
+      *lock = (_lock_t)mutex;
+    }
+
+  return nxmutex_trylock((mutex_t *)(*lock));
 }
 
 int _lock_try_acquire_recursive(_lock_t *lock)
 {
-  nxmutex_trylock(&g_nxlock_recursive);
-  nxsem_get_value(&g_nxlock_recursive.sem, lock);
-  return 0;
+  if ((*lock) == 0)
+    {
+      rmutex_t *rmutex = (rmutex_t *)kmm_malloc(sizeof(rmutex_t));
+
+      nxrmutex_init(rmutex);
+
+      *lock = (_lock_t)rmutex;
+    }
+
+  return nxrmutex_trylock((rmutex_t *)(*lock));
 }
 
 void _lock_release(_lock_t *lock)
 {
-  nxmutex_unlock(&g_nxlock_common);
-  nxsem_get_value(&g_nxlock_common.sem, lock);
+  mutex_t *mutex = (mutex_t *)(*lock);
+
+  nxmutex_unlock(mutex);
 }
 
 void _lock_release_recursive(_lock_t *lock)
 {
-  nxmutex_unlock(&g_nxlock_recursive);
-  nxsem_get_value(&g_nxlock_recursive.sem, lock);
+  rmutex_t *rmutex = (rmutex_t *)(*lock);
+
+  nxrmutex_unlock(rmutex);
 }
 
 struct _reent *__getreent(void)