]> Kevux Git Server - fll/commitdiff
Feature: Add missing mutex consistent and robust mutex attribute functions.
authorKevin Day <Kevin@kevux.org>
Wed, 13 Aug 2025 02:13:51 +0000 (21:13 -0500)
committerKevin Day <Kevin@kevux.org>
Wed, 13 Aug 2025 02:13:51 +0000 (21:13 -0500)
Add the following functions:
  - `f_thread_mutex_attribute_robust_get()`
  - `f_thread_mutex_attribute_robust_set()`
  - `f_thread_mutex_consistent()`

Add the new thread mutex group:
  - `f_thread_mutex_d`

Add the following status codes:
  - `F_consistent`
  - `F_consistent_not`
  - `F_robust`
  - `F_robust_not`

Add appropriate unit tests.

27 files changed:
build/disable/level_0/f_thread.h
build/stand_alone/byte_dump.config.h
build/stand_alone/example.config.h
build/stand_alone/fake.config.h
build/stand_alone/firewall.config.h
build/stand_alone/utf8.config.h
level_0/f_status/c/status.h
level_0/f_status_string/c/status_string.c
level_0/f_status_string/c/status_string.h
level_0/f_status_string/tests/unit/c/test-status_string-to.c
level_0/f_thread/c/thread.c
level_0/f_thread/c/thread.h
level_0/f_thread/c/thread/mutex.h
level_0/f_thread/data/build/settings-mocks
level_0/f_thread/data/build/settings-tests
level_0/f_thread/tests/unit/c/mock-thread.c
level_0/f_thread/tests/unit/c/mock-thread.h
level_0/f_thread/tests/unit/c/test-thread-mutex_attribute_robust_get.c [new file with mode: 0644]
level_0/f_thread/tests/unit/c/test-thread-mutex_attribute_robust_get.h [new file with mode: 0644]
level_0/f_thread/tests/unit/c/test-thread-mutex_attribute_robust_set.c [new file with mode: 0644]
level_0/f_thread/tests/unit/c/test-thread-mutex_attribute_robust_set.h [new file with mode: 0644]
level_0/f_thread/tests/unit/c/test-thread-mutex_consistent.c [new file with mode: 0644]
level_0/f_thread/tests/unit/c/test-thread-mutex_consistent.h [new file with mode: 0644]
level_0/f_thread/tests/unit/c/test-thread.c
level_0/f_thread/tests/unit/c/test-thread.h
level_1/fl_status_string/c/status_string.c
level_1/fl_status_string/tests/unit/c/test-status_string-from.c

index 2d23460ebd4b4719ff4a38e3043fe73c2e2429c9..176182e097be8581d885e012a02a0827f4e8846c 100644 (file)
 #define _di_f_thread_mutex_attribute_priority_ceiling_set_
 #define _di_f_thread_mutex_attribute_protocol_get_
 #define _di_f_thread_mutex_attribute_protocol_set_
+#define _di_f_thread_mutex_attribute_robust_get_
+#define _di_f_thread_mutex_attribute_robust_set_
 #define _di_f_thread_mutex_attribute_shared_get_
 #define _di_f_thread_mutex_attribute_shared_set_
 #define _di_f_thread_mutex_attribute_d_
 #define _di_f_thread_mutex_attributes_t_
 #define _di_f_thread_mutex_attributess_delete_callback_
 #define _di_f_thread_mutex_attributess_destroy_callback_
+#define _di_f_thread_mutex_consistent_
 #define _di_f_thread_mutex_create_
+#define _di_f_thread_mutex_d_
 #define _di_f_thread_mutex_delete_
 #define _di_f_thread_mutex_lock_
 #define _di_f_thread_mutex_lock_timed_
index 53265c60844e50ff334b5faca06089d1080d1a33..87c24393677f25a66d6ec29bd16e5bc274d9566c 100644 (file)
 #define _di_f_thread_mutex_attribute_priority_ceiling_set_
 #define _di_f_thread_mutex_attribute_protocol_get_
 #define _di_f_thread_mutex_attribute_protocol_set_
+#define _di_f_thread_mutex_attribute_robust_get_
+#define _di_f_thread_mutex_attribute_robust_set_
 #define _di_f_thread_mutex_attribute_shared_get_
 #define _di_f_thread_mutex_attribute_shared_set_
 #define _di_f_thread_mutex_attribute_d_
 #define _di_f_thread_mutex_attributes_t_
 #define _di_f_thread_mutex_attributess_delete_callback_
 #define _di_f_thread_mutex_attributess_destroy_callback_
+#define _di_f_thread_mutex_consistent_
 #define _di_f_thread_mutex_create_
+#define _di_f_thread_mutex_d_
 #define _di_f_thread_mutex_delete_
 #define _di_f_thread_mutex_lock_
 #define _di_f_thread_mutex_lock_timed_
index e96aa9732f62772cb109fa199f8338c1a595e037..0ee72a1ce5716188a61ec501cca941671c05d9cf 100644 (file)
 #define _di_f_thread_mutex_attribute_priority_ceiling_set_
 #define _di_f_thread_mutex_attribute_protocol_get_
 #define _di_f_thread_mutex_attribute_protocol_set_
+#define _di_f_thread_mutex_attribute_robust_get_
+#define _di_f_thread_mutex_attribute_robust_set_
 #define _di_f_thread_mutex_attribute_shared_get_
 #define _di_f_thread_mutex_attribute_shared_set_
 #define _di_f_thread_mutex_attribute_d_
 #define _di_f_thread_mutex_attributes_t_
 #define _di_f_thread_mutex_attributess_delete_callback_
 #define _di_f_thread_mutex_attributess_destroy_callback_
+#define _di_f_thread_mutex_consistent_
 #define _di_f_thread_mutex_create_
+#define _di_f_thread_mutex_d_
 #define _di_f_thread_mutex_delete_
 #define _di_f_thread_mutex_lock_
 #define _di_f_thread_mutex_lock_timed_
index 548463387a1ac098072e0eea9bf2aaafa06ff5be..df89551eaa2cbce3c766f417b40201cadc30761d 100644 (file)
 #define _di_f_thread_mutex_attribute_priority_ceiling_set_
 #define _di_f_thread_mutex_attribute_protocol_get_
 #define _di_f_thread_mutex_attribute_protocol_set_
+#define _di_f_thread_mutex_attribute_robust_get_
+#define _di_f_thread_mutex_attribute_robust_set_
 #define _di_f_thread_mutex_attribute_shared_get_
 #define _di_f_thread_mutex_attribute_shared_set_
 #define _di_f_thread_mutex_attribute_d_
 #define _di_f_thread_mutex_attributes_t_
 #define _di_f_thread_mutex_attributess_delete_callback_
 #define _di_f_thread_mutex_attributess_destroy_callback_
+#define _di_f_thread_mutex_consistent_
 #define _di_f_thread_mutex_create_
+#define _di_f_thread_mutex_d_
 #define _di_f_thread_mutex_delete_
 #define _di_f_thread_mutex_lock_
 #define _di_f_thread_mutex_lock_timed_
index 2e3c78b76a73435b64162fd1e772bac569025039..b288dc494d63f37acc1a39ef4827279dbd633176 100644 (file)
 #define _di_f_thread_mutex_attribute_priority_ceiling_set_
 #define _di_f_thread_mutex_attribute_protocol_get_
 #define _di_f_thread_mutex_attribute_protocol_set_
+#define _di_f_thread_mutex_attribute_robust_get_
+#define _di_f_thread_mutex_attribute_robust_set_
 #define _di_f_thread_mutex_attribute_shared_get_
 #define _di_f_thread_mutex_attribute_shared_set_
 #define _di_f_thread_mutex_attribute_d_
 #define _di_f_thread_mutex_attributes_t_
 #define _di_f_thread_mutex_attributess_delete_callback_
 #define _di_f_thread_mutex_attributess_destroy_callback_
+#define _di_f_thread_mutex_consistent_
 #define _di_f_thread_mutex_create_
+#define _di_f_thread_mutex_d_
 #define _di_f_thread_mutex_delete_
 #define _di_f_thread_mutex_lock_
 #define _di_f_thread_mutex_lock_timed_
index 421882f5e33211d4b529e3f86c3b9b69df02b78b..2ee95ea0149c0ce1c00fe3191d08432aed533881 100644 (file)
 #define _di_f_thread_mutex_attribute_priority_ceiling_set_
 #define _di_f_thread_mutex_attribute_protocol_get_
 #define _di_f_thread_mutex_attribute_protocol_set_
+#define _di_f_thread_mutex_attribute_robust_get_
+#define _di_f_thread_mutex_attribute_robust_set_
 #define _di_f_thread_mutex_attribute_shared_get_
 #define _di_f_thread_mutex_attribute_shared_set_
 #define _di_f_thread_mutex_attribute_d_
 #define _di_f_thread_mutex_attributes_t_
 #define _di_f_thread_mutex_attributess_delete_callback_
 #define _di_f_thread_mutex_attributess_destroy_callback_
+#define _di_f_thread_mutex_consistent_
 #define _di_f_thread_mutex_create_
+#define _di_f_thread_mutex_d_
 #define _di_f_thread_mutex_delete_
 #define _di_f_thread_mutex_lock_
 #define _di_f_thread_mutex_lock_timed_
index a129d886d46348a873856688c653c22da3066ba5..dba15b6b4182fdc9f7e44501872b6b01e239e405 100644 (file)
@@ -312,6 +312,8 @@ extern "C" {
     F_connect_not,
     F_connect_refuse,
     F_connect_reset,
+    F_consistent,
+    F_consistent_not,
     F_container,
     F_container_not,
     F_content,
@@ -705,6 +707,8 @@ extern "C" {
     F_restore_not,
     F_revert,
     F_revert_not,
+    F_robust,
+    F_robust_not,
     F_schedule,
     F_schedule_not,
     F_search,
index c4374d2ca5bf3849a2c88b5abf24958aebf54073..c1af84574782c0d1c038a7c686f76250be4adbc2 100644 (file)
@@ -180,6 +180,8 @@ extern "C" {
   const f_string_static_t f_status_connect_not_s = macro_f_string_static_t_initialize_1(F_status_connect_not_s, 0, F_status_connect_not_s_length);
   const f_string_static_t f_status_connect_refuse_s = macro_f_string_static_t_initialize_1(F_status_connect_refuse_s, 0, F_status_connect_refuse_s_length);
   const f_string_static_t f_status_connect_reset_s = macro_f_string_static_t_initialize_1(F_status_connect_reset_s, 0, F_status_connect_reset_s_length);
+  const f_string_static_t f_status_consistent_s = macro_f_string_static_t_initialize_1(F_status_consistent_s, 0, F_status_consistent_s_length);
+  const f_string_static_t f_status_consistent_not_s = macro_f_string_static_t_initialize_1(F_status_consistent_not_s, 0, F_status_consistent_not_s_length);
   const f_string_static_t f_status_container_s = macro_f_string_static_t_initialize_1(F_status_container_s, 0, F_status_container_s_length);
   const f_string_static_t f_status_container_not_s = macro_f_string_static_t_initialize_1(F_status_container_not_s, 0, F_status_container_not_s_length);
   const f_string_static_t f_status_content_s = macro_f_string_static_t_initialize_1(F_status_content_s, 0, F_status_content_s_length);
@@ -581,6 +583,8 @@ extern "C" {
   const f_string_static_t f_status_restore_not_s = macro_f_string_static_t_initialize_1(F_status_restore_not_s, 0, F_status_restore_not_s_length);
   const f_string_static_t f_status_revert_s = macro_f_string_static_t_initialize_1(F_status_revert_s, 0, F_status_revert_s_length);
   const f_string_static_t f_status_revert_not_s = macro_f_string_static_t_initialize_1(F_status_revert_not_s, 0, F_status_revert_not_s_length);
+  const f_string_static_t f_status_robust_s = macro_f_string_static_t_initialize_1(F_status_robust_s, 0, F_status_robust_s_length);
+  const f_string_static_t f_status_robust_not_s = macro_f_string_static_t_initialize_1(F_status_robust_not_s, 0, F_status_robust_not_s_length);
   const f_string_static_t f_status_schedule_s = macro_f_string_static_t_initialize_1(F_status_schedule_s, 0, F_status_schedule_s_length);
   const f_string_static_t f_status_schedule_not_s = macro_f_string_static_t_initialize_1(F_status_schedule_not_s, 0, F_status_schedule_not_s_length);
   const f_string_static_t f_status_search_s = macro_f_string_static_t_initialize_1(F_status_search_s, 0, F_status_search_s_length);
@@ -1570,6 +1574,26 @@ extern "C" {
 
         break;
 
+      case F_consistent:
+        *name = f_status_consistent_s;
+
+        break;
+
+      case F_consistent_not:
+        *name = f_status_consistent_not_s;
+
+        break;
+
+      case F_container:
+        *name = f_status_container_s;
+
+        break;
+
+      case F_container_not:
+        *name = f_status_container_not_s;
+
+        break;
+
       case F_content:
         *name = f_status_content_s;
 
@@ -1590,16 +1614,6 @@ extern "C" {
 
         break;
 
-      case F_container:
-        *name = f_status_container_s;
-
-        break;
-
-      case F_container_not:
-        *name = f_status_container_not_s;
-
-        break;
-
       case F_control:
         *name = f_status_control_s;
 
@@ -3536,6 +3550,16 @@ extern "C" {
 
         break;
 
+      case F_robust:
+        *name = f_status_robust_s;
+
+        break;
+
+      case F_robust_not:
+        *name = f_status_robust_not_s;
+
+        break;
+
       case F_schedule:
         *name = f_status_schedule_s;
 
index fbe0b3cb4b319602c678109766f4808fe92ee823..d8f9b3f681fbb38b4344648358f1601790e8e06c 100644 (file)
@@ -340,6 +340,8 @@ extern "C" {
   #define F_status_connect_not_s              "F_connect_not"
   #define F_status_connect_refuse_s           "F_connect_refuse"
   #define F_status_connect_reset_s            "F_connect_reset"
+  #define F_status_consistent_s                "F_consistent"
+  #define F_status_consistent_not_s            "F_consistent_not"
   #define F_status_container_s                "F_container"
   #define F_status_container_not_s            "F_container_not"
   #define F_status_content_s                  "F_content"
@@ -733,6 +735,8 @@ extern "C" {
   #define F_status_restore_not_s              "F_restore_not"
   #define F_status_revert_s                   "F_revert"
   #define F_status_revert_not_s               "F_revert_not"
+  #define F_status_robust_s                   "F_robust"
+  #define F_status_robust_not_s               "F_robust_not"
   #define F_status_schedule_s                 "F_schedule"
   #define F_status_schedule_not_s             "F_schedule_not"
   #define F_status_search_s                   "F_search"
@@ -942,6 +946,8 @@ extern "C" {
   #define F_status_connect_not_s_length              13
   #define F_status_connect_refuse_s_length           16
   #define F_status_connect_reset_s_length            15
+  #define F_status_consistent_s_length               12
+  #define F_status_consistent_not_s_length           16
   #define F_status_container_s_length                11
   #define F_status_container_not_s_length            15
   #define F_status_content_s_length                  9
@@ -1335,6 +1341,8 @@ extern "C" {
   #define F_status_restore_not_s_length              13
   #define F_status_revert_s_length                   8
   #define F_status_revert_not_s_length               12
+  #define F_status_robust_s_length                   8
+  #define F_status_robust_not_s_length               12
   #define F_status_schedule_s_length                 10
   #define F_status_schedule_not_s_length             14
   #define F_status_search_s_length                   8
@@ -1544,6 +1552,8 @@ extern "C" {
   extern const f_string_static_t f_status_connect_not_s;
   extern const f_string_static_t f_status_connect_refuse_s;
   extern const f_string_static_t f_status_connect_reset_s;
+  extern const f_string_static_t f_status_consistent_s;
+  extern const f_string_static_t f_status_consistent_not_s;
   extern const f_string_static_t f_status_container_s;
   extern const f_string_static_t f_status_container_not_s;
   extern const f_string_static_t f_status_content_s;
@@ -1939,6 +1949,8 @@ extern "C" {
   extern const f_string_static_t f_status_restore_not_s;
   extern const f_string_static_t f_status_revert_s;
   extern const f_string_static_t f_status_revert_not_s;
+  extern const f_string_static_t f_status_robust_s;
+  extern const f_string_static_t f_status_robust_not_s;
   extern const f_string_static_t f_status_schedule_s;
   extern const f_string_static_t f_status_schedule_not_s;
   extern const f_string_static_t f_status_search_s;
index 653add93ce4fc94d2a8687ab0a7e8c9ba0374463..70360f7ee3b4f35baa8a28a9facd1edaf323206b 100644 (file)
@@ -206,6 +206,8 @@ void test__f_status_string_to__works(void **state) {
     F_connect_not,
     F_connect_refuse,
     F_connect_reset,
+    F_consistent,
+    F_consistent_not,
     F_container,
     F_container_not,
     F_content,
@@ -599,6 +601,8 @@ void test__f_status_string_to__works(void **state) {
     F_restore_not,
     F_revert,
     F_revert_not,
+    F_robust,
+    F_robust_not,
     F_schedule,
     F_schedule_not,
     F_search,
@@ -877,6 +881,8 @@ void test__f_status_string_to__works(void **state) {
     f_status_connect_not_s,
     f_status_connect_refuse_s,
     f_status_connect_reset_s,
+    f_status_consistent_s,
+    f_status_consistent_not_s,
     f_status_container_s,
     f_status_container_not_s,
     f_status_content_s,
@@ -1270,6 +1276,8 @@ void test__f_status_string_to__works(void **state) {
     f_status_restore_not_s,
     f_status_revert_s,
     f_status_revert_not_s,
+    f_status_robust_s,
+    f_status_robust_not_s,
     f_status_schedule_s,
     f_status_schedule_not_s,
     f_status_search_s,
@@ -1371,7 +1379,7 @@ void test__f_status_string_to__works(void **state) {
     f_status_status_code_last_s,
   };
 
-  for (uint16_t i = 0; i < 664; ++i) {
+  for (uint16_t i = 0; i < 668; ++i) {
 
     f_string_static_t result = f_string_static_t_initialize;
 
index aeed44bab48b2a87361ac8f695b6f42f7fdc59ac..8ed74b20ce13aef62115cb967ac12fba45204939 100644 (file)
@@ -1469,6 +1469,41 @@ extern "C" {
   }
 #endif // _di_f_thread_mutex_attribute_protocol_set_
 
+#ifndef _di_f_thread_mutex_attribute_robust_get_
+  f_status_t f_thread_mutex_attribute_robust_get(f_thread_mutex_attribute_t * const attribute, int * const robust) {
+    #ifndef _di_level_0_parameter_checking_
+      if (!attribute) return F_status_set_error(F_parameter);
+      if (!robust) return F_status_set_error(F_parameter);
+    #endif // _di_level_0_parameter_checking_
+
+    const int error = pthread_mutexattr_getrobust(attribute, robust);
+
+    if (error) {
+      return F_status_set_error(F_failure);
+    }
+
+    return F_okay;
+  }
+#endif // _di_f_thread_mutex_attribute_robust_get_
+
+#ifndef _di_f_thread_mutex_attribute_robust_set_
+  f_status_t f_thread_mutex_attribute_robust_set(const int robust, f_thread_mutex_attribute_t * const attribute) {
+    #ifndef _di_level_0_parameter_checking_
+      if (!attribute) return F_status_set_error(F_parameter);
+    #endif // _di_level_0_parameter_checking_
+
+    const int error = pthread_mutexattr_setrobust(attribute, robust);
+
+    if (error) {
+      if (error == EINVAL) return F_status_set_error(F_parameter);
+
+      return F_status_set_error(F_failure);
+    }
+
+    return F_okay;
+  }
+#endif // _di_f_thread_mutex_attribute_robust_set_
+
 #ifndef _di_f_thread_mutex_attribute_shared_get_
   f_status_t f_thread_mutex_attribute_shared_get(const f_thread_mutex_attribute_t * const attribute, int * const shared) {
     #ifndef _di_level_0_parameter_checking_
@@ -1535,6 +1570,24 @@ extern "C" {
   }
 #endif // _di_f_thread_mutex_attribute_type_set_
 
+#ifndef _di_f_thread_mutex_consistent_
+  f_status_t f_thread_mutex_consistent(f_thread_mutex_t * const mutex) {
+    #ifndef _di_level_0_parameter_checking_
+      if (!mutex) return F_status_set_error(F_parameter);
+    #endif // _di_level_0_parameter_checking_
+
+    const int error = pthread_mutex_consistent(mutex);
+
+    if (error) {
+      if (error == EINVAL) return F_status_set_error(F_robust_not);
+
+      return F_status_set_error(F_failure);
+    }
+
+    return F_okay;
+  }
+#endif // _di_f_thread_mutex_consistent_
+
 #ifndef _di_f_thread_mutex_create_
   f_status_t f_thread_mutex_create(f_thread_mutex_attribute_t * const attribute, f_thread_mutex_t * const mutex) {
     #ifndef _di_level_0_parameter_checking_
index 334c7cfe490d36b461f2cbc574c23db7d842420f..58850b0ec195fbcdd99bab9983238d171eb9816f 100644 (file)
@@ -1974,6 +1974,54 @@ extern "C" {
 #endif // _di_f_thread_mutex_attribute_protocol_set_
 
 /**
+ * Get the robust mutex attribute.
+ *
+ * @param attribute
+ *   The mutex attributes to set the value of.
+ *
+ *   Must not be NULL.
+ * @param robust
+ *   The value to set to robust attribute to.
+ *   See f_thread_mutex_stalled_d and f_thread_mutex_robust_d.
+ *
+ *   Must not be NULL.
+ *
+ * @return
+ *   F_okay on success.
+ *
+ *   F_parameter (with error bit) if a parameter is invalid.
+ *   F_failure (with error bit) on any other error.
+ *
+ * @see pthread_mutexattr_setrobust()
+ */
+#ifndef _di_f_thread_mutex_attribute_robust_get_
+  extern f_status_t f_thread_mutex_attribute_robust_get(f_thread_mutex_attribute_t * const attribute, int * const robust);
+#endif // _di_f_thread_mutex_attribute_robust_get_
+
+/**
+ * Set the robust mutex attribute.
+ *
+ * @param robust
+ *   The value to set to robust attribute to.
+ *   See f_thread_mutex_stalled_d and f_thread_mutex_robust_d.
+ * @param attribute
+ *   The mutex attributes to set the value of.
+ *
+ *   Must not be NULL.
+ *
+ * @return
+ *   F_okay on success.
+ *
+ *   F_parameter (with error bit) if a parameter is invalid.
+ *   F_failure (with error bit) on any other error.
+ *
+ * @see pthread_mutexattr_setrobust()
+ */
+#ifndef _di_f_thread_mutex_attribute_robust_set_
+  extern f_status_t f_thread_mutex_attribute_robust_set(const int robust, f_thread_mutex_attribute_t * const attribute);
+#endif // _di_f_thread_mutex_attribute_robust_set_
+
+/**
  * Get the mutex attribute process shared thread attribute.
  *
  * @param attribute
@@ -2070,6 +2118,32 @@ extern "C" {
 #endif // _di_f_thread_mutex_attribute_type_set_
 
 /**
+ * Mark a robust mutex as consistent.
+ *
+ * Use this to re-mark a mutex that is no longer in a consistent state.
+ *
+ * This should be used to address mutex locks that return F_dead when attempting to acquire a lock.
+ *
+ * @param mutex
+ *   The thread mutex.
+ *
+ *   Must not be NULL.
+ *
+ * @return
+ *   F_okay on success.
+ *
+ *   F_parameter (with error bit) if a parameter is invalid.
+ *   F_robust (with error bit) if mutex is either not robust or it does not protect from an inconsistent state.
+ *
+ *   F_failure (with error bit) on any other error.
+ *
+ * @see pthread_mutex_consistent()
+ */
+#ifndef _di_f_thread_mutex_consistent_
+  extern f_status_t f_thread_mutex_consistent(f_thread_mutex_t * const mutex);
+#endif // _di_f_thread_mutex_consistent_
+
+/**
  * Create a thread mutex.
  *
  * @param attribute
index f77f17d546a3d78bdaed82de44592bc72000ce80..094a48cbda685f41bd87e6bab718a42a64f2521e 100644 (file)
@@ -17,6 +17,18 @@ extern "C" {
 #endif
 
 /**
+ * Mutex defines.
+ *
+ * f_thread_mutex_*_d:
+ *   - robust:  The mutex is in a robust state.
+ *   - stalled: The mutex is in a stalled state (non-robust), such as when F_dead is returned on lock attempts.
+ */
+#ifndef _di_f_thread_mutex_d_
+  #define f_thread_mutex_robust_d  PTHREAD_MUTEX_ROBUST
+  #define f_thread_mutex_stalled_d PTHREAD_MUTEX_STALLED
+#endif // _di_f_thread_mutex_d_
+
+/**
  * A typedef representing pthread_mutex_t.
  *
  * This variable cannot be cleared by setting value to 0, so there is no clear macro provided.
index bcef337f8ed2e76da51e717a896d0aa57e5df118..1f7f2f5c0c89768f587fecceb1de1d3372426650 100644 (file)
@@ -128,6 +128,7 @@ flags -Wl,--wrap=pthread_join
 flags -Wl,--wrap=pthread_key_create
 flags -Wl,--wrap=pthread_key_delete
 flags -Wl,--wrap=pthread_kill
+flags -Wl,--wrap=pthread_mutex_consistent
 flags -Wl,--wrap=pthread_mutex_destroy
 flags -Wl,--wrap=pthread_mutex_getprioceiling
 flags -Wl,--wrap=pthread_mutex_init
@@ -141,10 +142,12 @@ flags -Wl,--wrap=pthread_mutexattr_init
 flags -Wl,--wrap=pthread_mutexattr_getprioceiling
 flags -Wl,--wrap=pthread_mutexattr_getprotocol
 flags -Wl,--wrap=pthread_mutexattr_getpshared
+flags -Wl,--wrap=pthread_mutexattr_getrobust
 flags -Wl,--wrap=pthread_mutexattr_gettype
 flags -Wl,--wrap=pthread_mutexattr_setprioceiling
 flags -Wl,--wrap=pthread_mutexattr_setprotocol
 flags -Wl,--wrap=pthread_mutexattr_setpshared
+flags -Wl,--wrap=pthread_mutexattr_setrobust
 flags -Wl,--wrap=pthread_mutexattr_settype
 flags -Wl,--wrap=pthread_once
 flags -Wl,--wrap=pthread_rwlock_destroy
index c93065a1ea59dda4ad788c0b0045056966ffcd5a..5954e88c3cae1722e2f6908dd52d92a26745bd58 100644 (file)
@@ -82,9 +82,11 @@ build_sources_program test-thread-lock_read.c test-thread-lock_read_timed.c test
 build_sources_program test-thread-lock_write.c test-thread-lock_write_timed.c test-thread-lock_write_try.c
 build_sources_program test-thread-mutex_attribute_create.c test-thread-mutex_attribute_delete.c
 build_sources_program test-thread-mutex_attribute_priority_ceiling_get.c test-thread-mutex_attribute_priority_ceiling_set.c
+build_sources_program test-thread-mutex_attribute_robust_get.c test-thread-mutex_attribute_robust_set.c
 build_sources_program test-thread-mutex_attribute_shared_get.c test-thread-mutex_attribute_shared_set.c
 build_sources_program test-thread-mutex_attribute_type_get.c test-thread-mutex_attribute_type_set.c
 build_sources_program test-thread-mutex_attribute_protocol_get.c test-thread-mutex_attribute_protocol_set.c
+build_sources_program test-thread-mutex_consistent.c
 build_sources_program test-thread-mutex_create.c test-thread-mutex_delete.c
 build_sources_program test-thread-mutex_lock.c test-thread-mutex_lock_timed.c test-thread-mutex_lock_try.c
 build_sources_program test-thread-scheduler_parameter_get.c test-thread-scheduler_parameter_set.c
index 2935fcff316653044e31435a26af3de91d13636a..bab8a3a25977363bde892a5322428e7ce4b45e34 100644 (file)
@@ -607,6 +607,17 @@ int __wrap_pthread_kill(pthread_t thread, int sig) {
   return 0;
 }
 
+int __wrap_pthread_mutex_consistent(pthread_mutex_t *mutex) {
+
+  const bool failure = mock_type(bool);
+
+  if (failure) {
+    return mock_type(int);
+  }
+
+  return 0;
+}
+
 int __wrap_pthread_mutex_destroy(pthread_mutex_t *mutex) {
 
   const bool failure = mock_type(bool);
@@ -750,6 +761,28 @@ int __wrap_pthread_mutexattr_getpshared(const pthread_mutexattr_t *attr, int *ps
   return 0;
 }
 
+int __wrap_pthread_mutexattr_getrobust(const pthread_mutexattr_t *restrict attr, int *restrict robust) {
+
+  const bool failure = mock_type(bool);
+
+  if (failure) {
+    return mock_type(int);
+  }
+
+  return 0;
+}
+
+int __wrap_pthread_mutexattr_setrobust(pthread_mutexattr_t *attr, int robust) {
+
+  const bool failure = mock_type(bool);
+
+  if (failure) {
+    return mock_type(int);
+  }
+
+  return 0;
+}
+
 int __wrap_pthread_mutexattr_gettype(const pthread_mutexattr_t *attr, int *kind) {
 
   const bool failure = mock_type(bool);
index 1a59e3bf0a10160ef524ce5790b2dda0a846b01a..ff7793dda65c9e7c64054fa714300c93065ff5e2 100644 (file)
@@ -87,6 +87,7 @@ extern int __wrap_pthread_join(pthread_t pthread, void **value_ptr);
 extern int __wrap_pthread_key_create(pthread_key_t *key, void (*destructor)(void*));
 extern int __wrap_pthread_key_delete(pthread_key_t key);
 extern int __wrap_pthread_kill(pthread_t thread, int sig);
+extern int __wrap_pthread_mutex_consistent(pthread_mutex_t *mutex);
 extern int __wrap_pthread_mutex_destroy(pthread_mutex_t *mutex);
 extern int __wrap_pthread_mutex_getprioceiling(const pthread_mutex_t * restrict mutex, int *prioceiling);
 extern int __wrap_pthread_mutex_init(pthread_mutex_t *mutex, const pthread_mutexattr_t *attr);
@@ -100,6 +101,8 @@ extern int __wrap_pthread_mutexattr_init(pthread_mutexattr_t *attr);
 extern int __wrap_pthread_mutexattr_getprioceiling(const pthread_mutexattr_t *attr, int *prioceiling);
 extern int __wrap_pthread_mutexattr_getprotocol(const pthread_mutexattr_t *attr, int *protocol);
 extern int __wrap_pthread_mutexattr_getpshared(const pthread_mutexattr_t *attr, int *pshared);
+extern int __wrap_pthread_mutexattr_getrobust(const pthread_mutexattr_t *restrict attr, int *restrict robust);
+extern int __wrap_pthread_mutexattr_setrobust(pthread_mutexattr_t *attr, int robust);
 extern int __wrap_pthread_mutexattr_gettype(const pthread_mutexattr_t *attr, int *kind);
 extern int __wrap_pthread_mutexattr_setprioceiling(pthread_mutexattr_t *attr, int prioceiling);
 extern int __wrap_pthread_mutexattr_setprotocol(pthread_mutexattr_t *attr, int protocol);
diff --git a/level_0/f_thread/tests/unit/c/test-thread-mutex_attribute_robust_get.c b/level_0/f_thread/tests/unit/c/test-thread-mutex_attribute_robust_get.c
new file mode 100644 (file)
index 0000000..ebb61c7
--- /dev/null
@@ -0,0 +1,72 @@
+#include "test-thread.h"
+#include "test-thread-mutex_attribute_robust_get.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+void test__f_thread_mutex_attribute_robust_get__fails(void **state) {
+
+  f_thread_mutex_attribute_t attribute = f_thread_mutex_attribute_t_initialize;
+  int robust = 0;
+
+  int errnos[] = {
+    mock_errno_generic,
+  };
+
+  f_status_t statuss[] = {
+    F_failure,
+  };
+
+  for (uint8_t i = 0; i < 1; ++i) {
+
+    will_return(__wrap_pthread_mutexattr_getrobust, true);
+    will_return(__wrap_pthread_mutexattr_getrobust, errnos[i]);
+
+    const f_status_t status = f_thread_mutex_attribute_robust_get(&attribute, &robust);
+
+    assert_int_equal(status, F_status_set_error(statuss[i]));
+  } // for
+}
+
+void test__f_thread_mutex_attribute_robust_get__parameter_checking(void **state) {
+
+  f_thread_mutex_attribute_t attribute = f_thread_mutex_attribute_t_initialize;
+  int robust = 0;
+
+  {
+    const f_status_t status = f_thread_mutex_attribute_robust_get(0, 0);
+
+    assert_int_equal(status, F_status_set_error(F_parameter));
+  }
+
+  {
+    const f_status_t status = f_thread_mutex_attribute_robust_get(&attribute, 0);
+
+    assert_int_equal(status, F_status_set_error(F_parameter));
+  }
+
+  {
+    const f_status_t status = f_thread_mutex_attribute_robust_get(0, &robust);
+
+    assert_int_equal(status, F_status_set_error(F_parameter));
+  }
+}
+
+void test__f_thread_mutex_attribute_robust_get__works(void **state) {
+
+  f_thread_mutex_attribute_t attribute = f_thread_mutex_attribute_t_initialize;
+  int robust = 0;
+
+  {
+    will_return(__wrap_pthread_mutexattr_getrobust, false);
+
+    const f_status_t status = f_thread_mutex_attribute_robust_get(&attribute, &robust);
+
+    assert_int_equal(status, F_okay);
+  }
+}
+
+#ifdef __cplusplus
+} // extern "C"
+#endif
diff --git a/level_0/f_thread/tests/unit/c/test-thread-mutex_attribute_robust_get.h b/level_0/f_thread/tests/unit/c/test-thread-mutex_attribute_robust_get.h
new file mode 100644 (file)
index 0000000..9465400
--- /dev/null
@@ -0,0 +1,34 @@
+/**
+ * FLL - Level 0
+ *
+ * Project: Thread
+ * API Version: 0.7
+ * Licenses: lgpl-2.1-or-later
+ *
+ * Test the thread project.
+ */
+#ifndef _TEST__F_thread__mutex_attribute_robust_get_h
+#define _TEST__F_thread__mutex_attribute_robust_get_h
+
+/**
+ * Test that function fails.
+ *
+ * @see f_thread_mutex_attribute_robust_get()
+ */
+extern void test__f_thread_mutex_attribute_robust_get__fails(void **state);
+
+/**
+ * Test that parameter checking works as expected.
+ *
+ * @see f_thread_mutex_attribute_robust_get()
+ */
+extern void test__f_thread_mutex_attribute_robust_get__parameter_checking(void **state);
+
+/**
+ * Test that function works.
+ *
+ * @see f_thread_mutex_attribute_robust_get()
+ */
+extern void test__f_thread_mutex_attribute_robust_get__works(void **state);
+
+#endif // _TEST__F_thread__mutex_attribute_robust_get_h
diff --git a/level_0/f_thread/tests/unit/c/test-thread-mutex_attribute_robust_set.c b/level_0/f_thread/tests/unit/c/test-thread-mutex_attribute_robust_set.c
new file mode 100644 (file)
index 0000000..a54a505
--- /dev/null
@@ -0,0 +1,61 @@
+#include "test-thread.h"
+#include "test-thread-mutex_attribute_robust_set.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+void test__f_thread_mutex_attribute_robust_set__fails(void **state) {
+
+  f_thread_mutex_attribute_t attribute = f_thread_mutex_attribute_t_initialize;
+  int robust = 0;
+
+  int errnos[] = {
+    EINVAL,
+    mock_errno_generic,
+  };
+
+  f_status_t statuss[] = {
+    F_parameter,
+    F_failure,
+  };
+
+  for (uint8_t i = 0; i < 2; ++i) {
+
+    will_return(__wrap_pthread_mutexattr_setrobust, true);
+    will_return(__wrap_pthread_mutexattr_setrobust, errnos[i]);
+
+    const f_status_t status = f_thread_mutex_attribute_robust_set(robust, &attribute);
+
+    assert_int_equal(status, F_status_set_error(statuss[i]));
+  } // for
+}
+
+void test__f_thread_mutex_attribute_robust_set__parameter_checking(void **state) {
+
+  int robust = 0;
+
+  {
+    const f_status_t status = f_thread_mutex_attribute_robust_set(robust, 0);
+
+    assert_int_equal(status, F_status_set_error(F_parameter));
+  }
+}
+
+void test__f_thread_mutex_attribute_robust_set__works(void **state) {
+
+  f_thread_mutex_attribute_t attribute = f_thread_mutex_attribute_t_initialize;
+  int robust = 0;
+
+  {
+    will_return(__wrap_pthread_mutexattr_setrobust, false);
+
+    const f_status_t status = f_thread_mutex_attribute_robust_set(robust, &attribute);
+
+    assert_int_equal(status, F_okay);
+  }
+}
+
+#ifdef __cplusplus
+} // extern "C"
+#endif
diff --git a/level_0/f_thread/tests/unit/c/test-thread-mutex_attribute_robust_set.h b/level_0/f_thread/tests/unit/c/test-thread-mutex_attribute_robust_set.h
new file mode 100644 (file)
index 0000000..25bf82e
--- /dev/null
@@ -0,0 +1,34 @@
+/**
+ * FLL - Level 0
+ *
+ * Project: Thread
+ * API Version: 0.7
+ * Licenses: lgpl-2.1-or-later
+ *
+ * Test the thread project.
+ */
+#ifndef _TEST__F_thread__mutex_attribute_robust_set_h
+#define _TEST__F_thread__mutex_attribute_robust_set_h
+
+/**
+ * Test that function fails.
+ *
+ * @see f_thread_mutex_attribute_robust_set()
+ */
+extern void test__f_thread_mutex_attribute_robust_set__fails(void **state);
+
+/**
+ * Test that parameter checking works as expected.
+ *
+ * @see f_thread_mutex_attribute_robust_set()
+ */
+extern void test__f_thread_mutex_attribute_robust_set__parameter_checking(void **state);
+
+/**
+ * Test that function works.
+ *
+ * @see f_thread_mutex_attribute_robust_set()
+ */
+extern void test__f_thread_mutex_attribute_robust_set__works(void **state);
+
+#endif // _TEST__F_thread__mutex_attribute_robust_set_h
diff --git a/level_0/f_thread/tests/unit/c/test-thread-mutex_consistent.c b/level_0/f_thread/tests/unit/c/test-thread-mutex_consistent.c
new file mode 100644 (file)
index 0000000..b253ff2
--- /dev/null
@@ -0,0 +1,57 @@
+#include "test-thread.h"
+#include "test-thread-mutex_consistent.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+void test__f_thread_mutex_consistent__fails(void **state) {
+
+  f_thread_mutex_t mutex = f_thread_mutex_t_initialize;
+
+  int errnos[] = {
+    EINVAL,
+    mock_errno_generic,
+  };
+
+  f_status_t statuss[] = {
+    F_robust_not,
+    F_failure,
+  };
+
+  for (uint8_t i = 0; i < 2; ++i) {
+
+    will_return(__wrap_pthread_mutex_consistent, true);
+    will_return(__wrap_pthread_mutex_consistent, errnos[i]);
+
+    const f_status_t status = f_thread_mutex_consistent(&mutex);
+
+    assert_int_equal(status, F_status_set_error(statuss[i]));
+  } // for
+}
+
+void test__f_thread_mutex_consistent__parameter_checking(void **state) {
+
+  {
+    const f_status_t status = f_thread_mutex_consistent(0);
+
+    assert_int_equal(status, F_status_set_error(F_parameter));
+  }
+}
+
+void test__f_thread_mutex_consistent__works(void **state) {
+
+  f_thread_mutex_t mutex = f_thread_mutex_t_initialize;
+
+  {
+    will_return(__wrap_pthread_mutex_consistent, false);
+
+    const f_status_t status = f_thread_mutex_consistent(&mutex);
+
+    assert_int_equal(status, F_okay);
+  }
+}
+
+#ifdef __cplusplus
+} // extern "C"
+#endif
diff --git a/level_0/f_thread/tests/unit/c/test-thread-mutex_consistent.h b/level_0/f_thread/tests/unit/c/test-thread-mutex_consistent.h
new file mode 100644 (file)
index 0000000..10c17dd
--- /dev/null
@@ -0,0 +1,34 @@
+/**
+ * FLL - Level 0
+ *
+ * Project: Thread
+ * API Version: 0.7
+ * Licenses: lgpl-2.1-or-later
+ *
+ * Test the thread project.
+ */
+#ifndef _TEST__F_thread__mutex_consistent_h
+#define _TEST__F_thread__mutex_consistent_h
+
+/**
+ * Test that function fails.
+ *
+ * @see f_thread_mutex_consistent()
+ */
+extern void test__f_thread_mutex_consistent__fails(void **state);
+
+/**
+ * Test that parameter checking works as expected.
+ *
+ * @see f_thread_mutex_consistent()
+ */
+extern void test__f_thread_mutex_consistent__parameter_checking(void **state);
+
+/**
+ * Test that function works.
+ *
+ * @see f_thread_mutex_consistent()
+ */
+extern void test__f_thread_mutex_consistent__works(void **state);
+
+#endif // _TEST__F_thread__mutex_consistent_h
index d0a881320049c062d5f2a8418509769298f6c492..61208d5277005d94541118eb71590b15dcc29dd6 100644 (file)
@@ -301,6 +301,12 @@ int main(void) {
     cmocka_unit_test(test__f_thread_mutex_attribute_priority_ceiling_set__fails),
     cmocka_unit_test(test__f_thread_mutex_attribute_priority_ceiling_set__works),
 
+    cmocka_unit_test(test__f_thread_mutex_attribute_robust_get__fails),
+    cmocka_unit_test(test__f_thread_mutex_attribute_robust_get__works),
+
+    cmocka_unit_test(test__f_thread_mutex_attribute_robust_set__fails),
+    cmocka_unit_test(test__f_thread_mutex_attribute_robust_set__works),
+
     cmocka_unit_test(test__f_thread_mutex_attribute_shared_get__fails),
     cmocka_unit_test(test__f_thread_mutex_attribute_shared_get__works),
 
@@ -319,6 +325,9 @@ int main(void) {
     cmocka_unit_test(test__f_thread_mutex_attribute_protocol_set__fails),
     cmocka_unit_test(test__f_thread_mutex_attribute_protocol_set__works),
 
+    cmocka_unit_test(test__f_thread_mutex_consistent__fails),
+    cmocka_unit_test(test__f_thread_mutex_consistent__works),
+
     cmocka_unit_test(test__f_thread_mutex_create__fails),
     cmocka_unit_test(test__f_thread_mutex_create__works),
 
@@ -591,6 +600,10 @@ int main(void) {
 
       cmocka_unit_test(test__f_thread_mutex_attribute_priority_ceiling_set__parameter_checking),
 
+      cmocka_unit_test(test__f_thread_mutex_attribute_robust_get__parameter_checking),
+
+      cmocka_unit_test(test__f_thread_mutex_attribute_robust_set__parameter_checking),
+
       cmocka_unit_test(test__f_thread_mutex_attribute_shared_get__parameter_checking),
 
       cmocka_unit_test(test__f_thread_mutex_attribute_shared_set__parameter_checking),
index 87f712a7a2c4023f35187fcbcc1605a23b9d929c..c7d574fcf58a29de59952f0311be5e1ee33addc5 100644 (file)
 #include "test-thread-mutex_attribute_delete.h"
 #include "test-thread-mutex_attribute_priority_ceiling_get.h"
 #include "test-thread-mutex_attribute_priority_ceiling_set.h"
+#include "test-thread-mutex_attribute_robust_get.h"
+#include "test-thread-mutex_attribute_robust_set.h"
 #include "test-thread-mutex_attribute_shared_get.h"
 #include "test-thread-mutex_attribute_shared_set.h"
 #include "test-thread-mutex_attribute_type_get.h"
 #include "test-thread-mutex_attribute_type_set.h"
 #include "test-thread-mutex_attribute_protocol_get.h"
 #include "test-thread-mutex_attribute_protocol_set.h"
+#include "test-thread-mutex_consistent.h"
 #include "test-thread-mutex_create.h"
 #include "test-thread-mutex_delete.h"
 #include "test-thread-mutex_lock.h"
index 8cee17432c62c046cff3cf530e33e3a696c7b00d..975931a5e7635a471630fdf18d2ff23d9c68e7cf 100644 (file)
@@ -1094,6 +1094,18 @@ extern "C" {
       return F_okay;
     }
 
+    if (f_compare_dynamic(name, f_status_consistent_s) == F_equal_to) {
+      *code = F_consistent;
+
+      return F_okay;
+    }
+
+    if (f_compare_dynamic(name, f_status_consistent_not_s) == F_equal_to) {
+      *code = F_consistent_not;
+
+      return F_okay;
+    }
+
     if (f_compare_dynamic(name, f_status_container_s) == F_equal_to) {
       *code = F_container;
 
@@ -3450,6 +3462,18 @@ extern "C" {
       return F_okay;
     }
 
+    if (f_compare_dynamic(name, f_status_robust_s) == F_equal_to) {
+      *code = F_robust;
+
+      return F_okay;
+    }
+
+    if (f_compare_dynamic(name, f_status_robust_not_s) == F_equal_to) {
+      *code = F_robust_not;
+
+      return F_okay;
+    }
+
     if (f_compare_dynamic(name, f_status_schedule_s) == F_equal_to) {
       *code = F_schedule;
 
index 13b9e5bec85f2fe7dc80175ad010e32dfcd08ac4..f8142de2eebd4fe3931fd3f0e4358e0a202d2e11 100644 (file)
@@ -222,6 +222,8 @@ void test__fl_status_string_from__works(void **state) {
     F_connect_not,
     F_connect_refuse,
     F_connect_reset,
+    F_consistent,
+    F_consistent_not,
     F_container,
     F_container_not,
     F_content,
@@ -615,6 +617,8 @@ void test__fl_status_string_from__works(void **state) {
     F_restore_not,
     F_revert,
     F_revert_not,
+    F_robust,
+    F_robust_not,
     F_schedule,
     F_schedule_not,
     F_search,
@@ -893,6 +897,8 @@ void test__fl_status_string_from__works(void **state) {
     f_status_connect_not_s,
     f_status_connect_refuse_s,
     f_status_connect_reset_s,
+    f_status_consistent_s,
+    f_status_consistent_not_s,
     f_status_container_s,
     f_status_container_not_s,
     f_status_content_s,
@@ -1286,6 +1292,8 @@ void test__fl_status_string_from__works(void **state) {
     f_status_restore_not_s,
     f_status_revert_s,
     f_status_revert_not_s,
+    f_status_robust_s,
+    f_status_robust_not_s,
     f_status_schedule_s,
     f_status_schedule_not_s,
     f_status_search_s,
@@ -1387,7 +1395,7 @@ void test__fl_status_string_from__works(void **state) {
     f_status_status_code_last_s,
   };
 
-  for (uint16_t i = 0; i < 664; ++i) {
+  for (uint16_t i = 0; i < 668; ++i) {
 
     f_status_t result = F_okay;