[PATCH 29/38] Optional POSIX Keys initialization

Sebastian Huber sebastian.huber at embedded-brains.de
Tue Jan 26 15:37:55 UTC 2016


Update #2408.
---
 cpukit/posix/Makefile.am                   |  2 +-
 cpukit/posix/include/rtems/posix/keyimpl.h | 27 +---------
 cpukit/posix/src/key.c                     | 69 +++++++++++++++++++++++-
 cpukit/posix/src/keyrundestructors.c       | 84 ------------------------------
 cpukit/rtems/src/tasks.c                   |  6 ---
 cpukit/sapi/src/posixapi.c                 |  3 --
 cpukit/score/include/rtems/sysinit.h       |  1 +
 testsuites/sptests/spsysinit01/init.c      | 17 ++++++
 8 files changed, 89 insertions(+), 120 deletions(-)
 delete mode 100644 cpukit/posix/src/keyrundestructors.c

diff --git a/cpukit/posix/Makefile.am b/cpukit/posix/Makefile.am
index 54a298a..40bc153 100644
--- a/cpukit/posix/Makefile.am
+++ b/cpukit/posix/Makefile.am
@@ -154,7 +154,7 @@ endif
 
 ## KEY_C_FILES
 libposix_a_SOURCES += src/key.c src/keycreate.c src/keydelete.c \
-    src/keygetspecific.c src/keyfreememory.c src/keyrundestructors.c \
+    src/keygetspecific.c src/keyfreememory.c \
     src/keysetspecific.c
 
 ## ONCE_C_FILES
diff --git a/cpukit/posix/include/rtems/posix/keyimpl.h b/cpukit/posix/include/rtems/posix/keyimpl.h
index 6fd4d13..1addb1e 100644
--- a/cpukit/posix/include/rtems/posix/keyimpl.h
+++ b/cpukit/posix/include/rtems/posix/keyimpl.h
@@ -38,7 +38,7 @@ extern "C" {
 /**
  * @brief The information control block used to manage this class of objects.
  */
-POSIX_EXTERN Objects_Information  _POSIX_Keys_Information;
+extern Objects_Information _POSIX_Keys_Information;
 
 /**
  * @brief The rbtree control block used to manage all key values
@@ -48,19 +48,12 @@ extern RBTree_Control _POSIX_Keys_Key_value_lookup_tree;
 /**
  * @brief This freechain is used as a memory pool for POSIX_Keys_Key_value_pair.
  */
-POSIX_EXTERN Freechain_Control _POSIX_Keys_Keypool;
+extern Freechain_Control _POSIX_Keys_Keypool;
 
 #define POSIX_KEYS_RBTREE_NODE_TO_KEY_VALUE_PAIR( node ) \
   RTEMS_CONTAINER_OF( node, POSIX_Keys_Key_value_pair, Key_value_lookup_node )
 
 /**
- * @brief POSIX key manager initialization.
- *
- * This routine performs the initialization necessary for this manager.
- */
-void _POSIX_Key_Manager_initialization(void);
-
-/**
  * @brief POSIX keys Red-Black tree node comparison.
  *
  * This routine compares the rbtree node
@@ -71,22 +64,6 @@ RBTree_Compare_result _POSIX_Keys_Key_value_compare(
 );
 
 /**
- * @brief Create thread-specific data POSIX key.
- *
- * This function executes all the destructors associated with the thread's
- * keys.  This function will execute until all values have been set to NULL.
- *
- * @param[in] thread is a pointer to the thread whose keys should have
- *            all their destructors run.
- *
- * NOTE: This is the routine executed when a thread exits to
- *       run through all the keys and do the destructor action.
- */
-void _POSIX_Keys_Run_destructors(
-  Thread_Control *thread
-);
-
-/**
  * @brief Free a POSIX key table memory.
  *
  * This memory frees the key table memory associated with @a the_key.
diff --git a/cpukit/posix/src/key.c b/cpukit/posix/src/key.c
index 55c65900..5a0886b 100644
--- a/cpukit/posix/src/key.c
+++ b/cpukit/posix/src/key.c
@@ -20,14 +20,20 @@
 #endif
 
 #include <rtems/config.h>
+#include <rtems/sysinit.h>
 
 #include <rtems/posix/keyimpl.h>
 #include <rtems/score/chainimpl.h>
 #include <rtems/score/objectimpl.h>
+#include <rtems/score/userextimpl.h>
 #include <rtems/score/wkspace.h>
 
+Objects_Information _POSIX_Keys_Information;
+
 RBTREE_DEFINE_EMPTY( _POSIX_Keys_Key_value_lookup_tree );
 
+Freechain_Control _POSIX_Keys_Keypool;
+
 /**
  * @brief This routine compares the rbtree node by comparing POSIX key first
  * and comparing thread id second.
@@ -112,10 +118,63 @@ POSIX_Keys_Key_value_pair * _POSIX_Keys_Key_value_pair_allocate( void )
   );
 }
 
+static void _POSIX_Keys_Run_destructors( Thread_Control *thread )
+{
+  Chain_Control *chain;
+  POSIX_Keys_Key_value_pair *iter, *next;
+  void *value;
+  void (*destructor) (void *);
+  POSIX_Keys_Control *the_key;
+  Objects_Locations location;
+
+  chain = &thread->Key_Chain;
+  iter = (POSIX_Keys_Key_value_pair *) _Chain_First( chain );
+  while ( !_Chain_Is_tail( chain, &iter->Key_values_per_thread_node ) ) {
+    next = (POSIX_Keys_Key_value_pair *)
+      _Chain_Next( &iter->Key_values_per_thread_node );
+
+    the_key = _POSIX_Keys_Get( iter->key, &location );
+    _Assert( location == OBJECTS_LOCAL );
+
+    /**
+     * remove key from rbtree and chain.
+     * here Chain_Node *iter can be convert to POSIX_Keys_Key_value_pair *,
+     * because Chain_Node is the first member of POSIX_Keys_Key_value_pair
+     * structure.
+     */
+    _RBTree_Extract(
+        &_POSIX_Keys_Key_value_lookup_tree,
+        &iter->Key_value_lookup_node
+    );
+    _Chain_Extract_unprotected( &iter->Key_values_per_thread_node );
+
+    destructor = the_key->destructor;
+    value = iter->value;
+
+    _POSIX_Keys_Key_value_pair_free( iter );
+
+    _Objects_Put( &the_key->Object );
+
+    /**
+     * run key value's destructor if destructor and value are both non-null.
+     */
+    if ( destructor != NULL && value != NULL )
+      (*destructor)( value );
+
+    iter = next;
+  }
+}
+
+static User_extensions_Control _POSIX_Keys_Extensions = {
+  .Callouts = {
+    .thread_terminate = _POSIX_Keys_Run_destructors
+  }
+};
+
 /**
  * @brief This routine performs the initialization necessary for this manager.
  */
-void _POSIX_Key_Manager_initialization(void)
+static void _POSIX_Keys_Manager_initialization(void)
 {
   _Objects_Initialize_information(
     &_POSIX_Keys_Information,   /* object information table */
@@ -135,4 +194,12 @@ void _POSIX_Key_Manager_initialization(void)
   );
 
   _POSIX_Keys_Initialize_keypool();
+
+  _User_extensions_Add_API_set( &_POSIX_Keys_Extensions );
 }
+
+RTEMS_SYSINIT_ITEM(
+  _POSIX_Keys_Manager_initialization,
+  RTEMS_SYSINIT_POSIX_KEYS,
+  RTEMS_SYSINIT_ORDER_MIDDLE
+);
diff --git a/cpukit/posix/src/keyrundestructors.c b/cpukit/posix/src/keyrundestructors.c
deleted file mode 100644
index 96147a5..0000000
--- a/cpukit/posix/src/keyrundestructors.c
+++ /dev/null
@@ -1,84 +0,0 @@
-/**
- * @file
- *
- * @brief Thread-Specific Data Key Create
- * @ingroup POSIX_KEY Key
- */
-
-/*
- * Copyright (c) 2012 Zhongwei Yao.
- * Copyright (c) 2010-2014 embedded brains GmbH.
- *
- * COPYRIGHT (c) 1989-2014.
- * On-Line Applications Research Corporation (OAR).
- *
- * The license and distribution terms for this file may be
- * found in the file LICENSE in this distribution or at
- * http://www.rtems.org/license/LICENSE.
- */
-
-#if HAVE_CONFIG_H
-#include "config.h"
-#endif
-
-#include <rtems/posix/keyimpl.h>
-#include <rtems/score/assert.h>
-#include <rtems/score/chainimpl.h>
-#include <rtems/score/thread.h>
-
-/*
- *  _POSIX_Keys_Run_destructors
- *
- *  17.1.1 Thread-Specific Data Key Create, P1003.1c/Draft 10, p. 163
- *
- *  NOTE:  This is the routine executed when a thread exits to
- *         run through all the keys and do the destructor action.
- */
-void _POSIX_Keys_Run_destructors(
-  Thread_Control *thread
-)
-{
-  Chain_Control *chain;
-  POSIX_Keys_Key_value_pair *iter, *next;
-  void *value;
-  void (*destructor) (void *);
-  POSIX_Keys_Control *the_key;
-  Objects_Locations location;
-
-  chain = &thread->Key_Chain;
-  iter = (POSIX_Keys_Key_value_pair *) _Chain_First( chain );
-  while ( !_Chain_Is_tail( chain, &iter->Key_values_per_thread_node ) ) {
-    next = (POSIX_Keys_Key_value_pair *)
-      _Chain_Next( &iter->Key_values_per_thread_node );
-
-    the_key = _POSIX_Keys_Get( iter->key, &location );
-    _Assert( location == OBJECTS_LOCAL );
-
-    /**
-     * remove key from rbtree and chain.
-     * here Chain_Node *iter can be convert to POSIX_Keys_Key_value_pair *,
-     * because Chain_Node is the first member of POSIX_Keys_Key_value_pair
-     * structure.
-     */
-    _RBTree_Extract(
-        &_POSIX_Keys_Key_value_lookup_tree,
-        &iter->Key_value_lookup_node
-    );
-    _Chain_Extract_unprotected( &iter->Key_values_per_thread_node );
-
-    destructor = the_key->destructor;
-    value = iter->value;
-
-    _POSIX_Keys_Key_value_pair_free( iter );
-
-    _Objects_Put( &the_key->Object );
-
-    /**
-     * run key value's destructor if destructor and value are both non-null.
-     */
-    if ( destructor != NULL && value != NULL )
-      (*destructor)( value );
-
-    iter = next;
-  }
-}
diff --git a/cpukit/rtems/src/tasks.c b/cpukit/rtems/src/tasks.c
index 8852999..2a5c5da 100644
--- a/cpukit/rtems/src/tasks.c
+++ b/cpukit/rtems/src/tasks.c
@@ -28,7 +28,6 @@
 #include <rtems/rtems/support.h>
 #include <rtems/rtems/modes.h>
 #include <rtems/rtems/tasksimpl.h>
-#include <rtems/posix/keyimpl.h>
 #include <rtems/score/stack.h>
 #include <rtems/score/threadimpl.h>
 #include <rtems/score/userextimpl.h>
@@ -121,11 +120,6 @@ static void _RTEMS_tasks_Terminate_extension(
     } while (0);
     #pragma GCC diagnostic pop
   #endif
-
-  /*
-   *  Run all the key destructors
-   */
-  _POSIX_Keys_Run_destructors( executing );
 }
 
 #if !defined(RTEMS_SMP)
diff --git a/cpukit/sapi/src/posixapi.c b/cpukit/sapi/src/posixapi.c
index 08b47de..b3839dd 100644
--- a/cpukit/sapi/src/posixapi.c
+++ b/cpukit/sapi/src/posixapi.c
@@ -24,7 +24,6 @@
 #include <rtems/system.h>    /* include this before checking RTEMS_POSIX_API */
 
 #include <rtems/config.h>
-#include <rtems/posix/keyimpl.h>
 #include <rtems/posix/posixapi.h>
 
 #ifdef RTEMS_POSIX_API
@@ -51,6 +50,4 @@ void _POSIX_API_Initialize(void)
    *
    * Currently, there are no none type size assumptions.
    */
-
-  _POSIX_Key_Manager_initialization();
 }
diff --git a/cpukit/score/include/rtems/sysinit.h b/cpukit/score/include/rtems/sysinit.h
index 39e551f..72b21e8 100644
--- a/cpukit/score/include/rtems/sysinit.h
+++ b/cpukit/score/include/rtems/sysinit.h
@@ -54,6 +54,7 @@ extern "C" {
 #define RTEMS_SYSINIT_POSIX_RWLOCK               000368
 #define RTEMS_SYSINIT_POSIX_SPINLOCK             000369
 #define RTEMS_SYSINIT_POSIX_CLEANUP              00036a
+#define RTEMS_SYSINIT_POSIX_KEYS                 00036b
 #define RTEMS_SYSINIT_IDLE_THREADS               000380
 #define RTEMS_SYSINIT_BSP_LIBC                   000400
 #define RTEMS_SYSINIT_BEFORE_DRIVERS             000500
diff --git a/testsuites/sptests/spsysinit01/init.c b/testsuites/sptests/spsysinit01/init.c
index 916ae6c..d72cefe 100644
--- a/testsuites/sptests/spsysinit01/init.c
+++ b/testsuites/sptests/spsysinit01/init.c
@@ -39,6 +39,7 @@
 #include <rtems/posix/spinlockimpl.h>
 #include <rtems/posix/timerimpl.h>
 #endif /* RTEMS_POSIX_API */
+#include <rtems/posix/keyimpl.h>
 #include <rtems/rtems/barrierimpl.h>
 #include <rtems/rtems/dpmemimpl.h>
 #include <rtems/rtems/messageimpl.h>
@@ -115,6 +116,8 @@ typedef enum {
   POSIX_CLEANUP_PRE,
   POSIX_CLEANUP_POST,
 #endif /* RTEMS_POSIX_API */
+  POSIX_KEYS_PRE,
+  POSIX_KEYS_POST,
   IDLE_THREADS_PRE,
   IDLE_THREADS_POST,
   BSP_LIBC_PRE,
@@ -515,6 +518,18 @@ LAST(RTEMS_SYSINIT_POSIX_CLEANUP)
 
 #endif /* RTEMS_POSIX_API */
 
+FIRST(RTEMS_SYSINIT_POSIX_KEYS)
+{
+  assert(_POSIX_Keys_Information.maximum == 0);
+  next_step(POSIX_KEYS_PRE);
+}
+
+LAST(RTEMS_SYSINIT_POSIX_KEYS)
+{
+  assert(_POSIX_Keys_Information.maximum != 0);
+  next_step(POSIX_KEYS_POST);
+}
+
 FIRST(RTEMS_SYSINIT_IDLE_THREADS)
 {
   assert(_System_state_Is_before_initialization(_System_state_Get()));
@@ -644,6 +659,8 @@ static void Init(rtems_task_argument arg)
 
 #endif /* RTEMS_POSIX_API */
 
+#define CONFIGURE_MAXIMUM_POSIX_KEYS 1
+
 #define CONFIGURE_RTEMS_INIT_TASKS_TABLE
 
 #define CONFIGURE_STACK_CHECKER_ENABLED
-- 
1.8.4.5




More information about the devel mailing list