Currently, failures of pthread_* functions are printed to stderr
only and then OVS aborts.  These error messages are hard to find
and may be even just lost.

Use VLOG_ABORT() instead.  It will do the same thing, but will try
to log the error to the log file and syslog first, if configured.

Using VLOG_ABORT() instead of VLOG_FATAL() to preserve the abort()
logic and not just exit with a failure code, because it's likely
we want a core dump if one of these function failed.  For example,
we would like to have a stack trace in a core dump in case a mutex
lock failed with 'deadlock avoided'.

Signed-off-by: Ilya Maximets <[email protected]>
---

Another thing we can do to improve debugability is to also dump
the stack trace on ovs_abort.  It will also help with debugging
assertions on systems where coredumps are disabled for some reason.
But it's a separate topic.

 lib/ovs-thread.c | 42 +++++++++++++++++++++++++-----------------
 1 file changed, 25 insertions(+), 17 deletions(-)

diff --git a/lib/ovs-thread.c b/lib/ovs-thread.c
index ac5d2c3d0..f80008061 100644
--- a/lib/ovs-thread.c
+++ b/lib/ovs-thread.c
@@ -63,13 +63,14 @@ static bool multithreaded;
  \
         /* Verify that 'l' was initialized. */ \
         if (OVS_UNLIKELY(!l->where)) { \
-            ovs_abort(0, "%s: %s() passed uninitialized ovs_"#TYPE, \
-                      where, __func__); \
+            VLOG_ABORT("%s: %s() passed uninitialized ovs_"#TYPE, \
+                       where, __func__); \
         } \
  \
         error = pthread_##TYPE##_##FUN(&l->lock); \
         if (OVS_UNLIKELY(error)) { \
-            ovs_abort(error, "%s: pthread_%s_%s failed", where, #TYPE, #FUN); \
+            VLOG_ABORT("%s: pthread_%s_%s failed: %s", where, #TYPE, #FUN, \
+                       ovs_strerror(error)); \
         } \
         l->where = where; \
  }
@@ -91,13 +92,14 @@ LOCK_FUNCTION(spin, lock);
  \
         /* Verify that 'l' was initialized. */ \
         if (OVS_UNLIKELY(!l->where)) { \
-            ovs_abort(0, "%s: %s() passed uninitialized ovs_"#TYPE, \
-                      where, __func__); \
+            VLOG_ABORT("%s: %s() passed uninitialized ovs_"#TYPE, \
+                       where, __func__); \
         } \
  \
         error = pthread_##TYPE##_##FUN(&l->lock); \
         if (OVS_UNLIKELY(error) && error != EBUSY) { \
-            ovs_abort(error, "%s: pthread_%s_%s failed", where, #TYPE, #FUN); \
+            VLOG_ABORT("%s: pthread_%s_%s failed: %s", where, #TYPE, #FUN, \
+                       ovs_strerror(error)); \
         } \
         if (!error) { \
             l->where = where; \
@@ -125,7 +127,8 @@ TRY_LOCK_FUNCTION(spin, trylock);
         l->where = WHERE; \
         error = pthread_##TYPE##_##FUN(&l->lock); \
         if (OVS_UNLIKELY(error)) { \
-            ovs_abort(error, "pthread_%s_%s failed", #TYPE, #FUN); \
+            VLOG_ABORT("%s: pthread_%s_%s failed: %s", l->where, #TYPE, #FUN, \
+                       ovs_strerror(error)); \
         } \
     }
 UNLOCK_FUNCTION(mutex, unlock, "<unlocked>");
@@ -143,7 +146,8 @@ UNLOCK_FUNCTION(spin, destroy, NULL);
     {                                                   \
         int error = FUNCTION(arg1);                     \
         if (OVS_UNLIKELY(error)) {                      \
-            ovs_abort(error, "%s failed", #FUNCTION);   \
+            VLOG_ABORT("%s failed: %s", #FUNCTION,      \
+                       ovs_strerror(error));            \
         }                                               \
     }
 #define XPTHREAD_FUNC2(FUNCTION, PARAM1, PARAM2)        \
@@ -152,7 +156,8 @@ UNLOCK_FUNCTION(spin, destroy, NULL);
     {                                                   \
         int error = FUNCTION(arg1, arg2);               \
         if (OVS_UNLIKELY(error)) {                      \
-            ovs_abort(error, "%s failed", #FUNCTION);   \
+            VLOG_ABORT("%s failed: %s", #FUNCTION,      \
+                       ovs_strerror(error));            \
         }                                               \
     }
 #define XPTHREAD_FUNC3(FUNCTION, PARAM1, PARAM2, PARAM3)\
@@ -161,7 +166,8 @@ UNLOCK_FUNCTION(spin, destroy, NULL);
     {                                                   \
         int error = FUNCTION(arg1, arg2, arg3);         \
         if (OVS_UNLIKELY(error)) {                      \
-            ovs_abort(error, "%s failed", #FUNCTION);   \
+            VLOG_ABORT("%s failed: %s", #FUNCTION,      \
+                       ovs_strerror(error));            \
         }                                               \
     }
 
@@ -204,7 +210,7 @@ ovs_mutex_init__(const struct ovs_mutex *l_, int type)
     xpthread_mutexattr_settype(&attr, type);
     error = pthread_mutex_init(&l->lock, &attr);
     if (OVS_UNLIKELY(error)) {
-        ovs_abort(error, "pthread_mutex_init failed");
+        VLOG_ABORT("pthread_mutex_init failed: %s", ovs_strerror(error));
     }
     xpthread_mutexattr_destroy(&attr);
 }
@@ -257,7 +263,7 @@ ovs_rwlock_init(const struct ovs_rwlock *l_)
 #endif
 
     if (OVS_UNLIKELY(error)) {
-        ovs_abort(error, "pthread_rwlock_init failed");
+        VLOG_ABORT("pthread_rwlock_init failed: %s", ovs_strerror(error));
     }
 }
 
@@ -275,7 +281,7 @@ ovs_mutex_cond_wait(pthread_cond_t *cond, const struct 
ovs_mutex *mutex_)
     error = pthread_cond_wait(cond, &mutex->lock);
 
     if (OVS_UNLIKELY(error)) {
-        ovs_abort(error, "pthread_cond_wait failed");
+        VLOG_ABORT("pthread_cond_wait failed: %s", ovs_strerror(error));
     }
 }
 
@@ -289,7 +295,7 @@ ovs_spin_init__(const struct ovs_spin *l_, int pshared)
     l->where = "<unlocked>";
     error = pthread_spin_init(&l->lock, pshared);
     if (OVS_UNLIKELY(error)) {
-        ovs_abort(error, "pthread_spin_init failed");
+        VLOG_ABORT("pthread_spin_init failed: %s", ovs_strerror(error));
     }
 }
 
@@ -431,13 +437,15 @@ set_min_stack_size(pthread_attr_t *attr, size_t 
min_stacksize)
 
     error = pthread_attr_getstacksize(attr, &stacksize);
     if (error) {
-        ovs_abort(error, "pthread_attr_getstacksize failed");
+        VLOG_ABORT("pthread_attr_getstacksize failed: %s",
+                   ovs_strerror(error));
     }
 
     if (stacksize < min_stacksize) {
         error = pthread_attr_setstacksize(attr, min_stacksize);
         if (error) {
-            ovs_abort(error, "pthread_attr_setstacksize failed");
+            VLOG_ABORT("pthread_attr_setstacksize failed: %s",
+                       ovs_strerror(error));
         }
     }
 }
@@ -486,7 +494,7 @@ ovs_thread_create(const char *name, void *(*start)(void *), 
void *arg)
 
     error = pthread_create(&thread, &attr, ovsthread_wrapper, aux);
     if (error) {
-        ovs_abort(error, "pthread_create failed");
+        VLOG_ABORT("pthread_create failed: %s", ovs_strerror(error));
     }
     pthread_attr_destroy(&attr);
     return thread;
-- 
2.43.0

_______________________________________________
dev mailing list
[email protected]
https://mail.openvswitch.org/mailman/listinfo/ovs-dev

Reply via email to