]> sourceware.org Git - valgrind.git/commitdiff
FreeBSD support, patch 4
authorPaul Floyd <pjfloyd@wanadoo.fr>
Sun, 3 Oct 2021 17:49:08 +0000 (19:49 +0200)
committerPaul Floyd <pjfloyd@wanadoo.fr>
Wed, 6 Oct 2021 19:50:49 +0000 (21:50 +0200)
DRD code
Mainly just intercepts, but also a hairy fix for early acces to
pthread_self()

drd/drd_main.c [changed mode: 0644->0755]
drd/drd_pthread_intercepts.c

old mode 100644 (file)
new mode 100755 (executable)
index 2f2279e..4a71eeb
@@ -744,7 +744,7 @@ void drd__atfork_child(ThreadId tid)
 
 static void DRD_(post_clo_init)(void)
 {
-#if defined(VGO_linux) || defined(VGO_darwin) || defined(VGO_solaris)
+#if defined(VGO_linux) || defined(VGO_darwin) || defined(VGO_solaris) || defined(VGO_freebsd)
    /* fine */
 #else
    VG_(printf)("\nWARNING: DRD has not yet been tested on this operating system.\n\n");
index 28c0de78bc83ad1949ba2412e5c2d25ef1271979..8b44543645f9bd6e62e34a77a188eaa27b626854 100644 (file)
 #include "drd_clientreq.h"
 #include "pub_tool_redir.h" /* VG_WRAP_FUNCTION_ZZ() */
 
+#if defined(VGO_freebsd)
+#include <dlfcn.h>
+#endif
+
 #if defined(VGO_solaris)
 /*
  * Solaris usually provides pthread_* functions on top of Solaris threading
@@ -168,6 +172,11 @@ static int never_true;
         fflush(stdout);                                                \
       return pth_func_result;                                          \
    }
+#elif defined(VG_WRAP_THREAD_FUNCTION_LIBPTHREAD_ONLY)
+#define PTH_FUNC(ret_ty, zf, implf, argl_decl, argl)                    \
+ret_ty VG_WRAP_FUNCTION_ZZ(VG_Z_LIBPTHREAD_SONAME,zf) argl_decl;        \
+ret_ty VG_WRAP_FUNCTION_ZZ(VG_Z_LIBPTHREAD_SONAME,zf) argl_decl         \
+{      return implf argl; }
 #elif defined(VG_WRAP_THREAD_FUNCTION_LIBC_ONLY)
 #define PTH_FUNC(ret_ty, zf, implf, argl_decl, argl)                    \
    ret_ty VG_WRAP_FUNCTION_ZZ(VG_Z_LIBC_SONAME,zf) argl_decl;           \
@@ -185,6 +194,13 @@ static int never_true;
 #  error "Unknown platform/thread wrapping"
 #endif
 
+#if defined(VGO_freebsd)
+#define LIBC_FUNC(ret_ty, zf, implf, argl_decl, argl)                    \
+   ret_ty VG_WRAP_FUNCTION_ZZ(VG_Z_LIBC_SONAME,zf) argl_decl;           \
+   ret_ty VG_WRAP_FUNCTION_ZZ(VG_Z_LIBC_SONAME,zf) argl_decl            \
+   { return implf argl; }
+#endif
+
 /**
  * Macro for generating three Valgrind interception functions: one with the
  * Z-encoded name zf, one with ZAZa ("@*") appended to the name zf and one
@@ -252,6 +268,27 @@ static void DRD_(sema_up)(DrdSema* sema);
  */
 static void DRD_(init)(void)
 {
+#if defined(VGO_freebsd)
+   {
+      /*
+       * On FreeBSD, pthead functions are all in libthr.so
+       * However libc.so contains stubs. In this ctor function,
+       * calling DRD_(set_pthread_id)() results in a call to
+       * pthread_self() resolving to the libc.so stub which
+       * returns a junk value for the tid. Subsequent calls
+       * to pthread_create() then also cause calls to
+       * DRD_(set_pthread_id)(), but this time with pthread_self()
+       * resolving to the good libthr.so version (since this is later
+       * and libthr.so has been loaded). That causes an assert
+       * since we expect the tid to either be INVALID_POSIX_THREADID
+       * or the same as the current tid, and the junk value
+       * is neither. So we force loading of libthr.so, which
+       * avoids this junk tid value.
+       */
+      dlclose(dlopen("/lib/libthr.so.3", RTLD_NOW|RTLD_GLOBAL|RTLD_NODELETE));
+   }
+#endif
+
    DRD_(check_threading_library)();
    DRD_(set_pthread_id)();
 #if defined(VGO_solaris)
@@ -1352,8 +1389,13 @@ int sem_init_intercept(sem_t *sem, int pshared, unsigned int value)
    return ret;
 }
 
+#if defined(VGO_freebsd)
+LIBC_FUNC(int, semZuinit, sem_init_intercept,
+          (sem_t *sem, int pshared, unsigned int value), (sem, pshared, value));
+#else
 PTH_FUNCS(int, semZuinit, sem_init_intercept,
           (sem_t *sem, int pshared, unsigned int value), (sem, pshared, value));
+#endif
 
 #if defined(VGO_solaris)
 static __always_inline
@@ -1390,7 +1432,12 @@ int sem_destroy_intercept(sem_t *sem)
    return ret;
 }
 
+#if defined(VGO_freebsd)
+LIBC_FUNC(int, semZudestroy, sem_destroy_intercept, (sem_t *sem), (sem));
+#else
 PTH_FUNCS(int, semZudestroy, sem_destroy_intercept, (sem_t *sem), (sem));
+#endif
+
 #if defined(VGO_solaris)
 PTH_FUNCS(int, semaZudestroy, sem_destroy_intercept, (sem_t *sem), (sem));
 #endif /* VGO_solaris */
@@ -1414,9 +1461,15 @@ sem_t* sem_open_intercept(const char *name, int oflag, mode_t mode,
    return ret;
 }
 
+#if defined(VGO_freebsd)
+LIBC_FUNC(sem_t *, semZuopen, sem_open_intercept,
+          (const char *name, int oflag, mode_t mode, unsigned int value),
+          (name, oflag, mode, value));
+#else
 PTH_FUNCS(sem_t *, semZuopen, sem_open_intercept,
           (const char *name, int oflag, mode_t mode, unsigned int value),
           (name, oflag, mode, value));
+#endif
 
 static __always_inline int sem_close_intercept(sem_t *sem)
 {
@@ -1431,7 +1484,11 @@ static __always_inline int sem_close_intercept(sem_t *sem)
    return ret;
 }
 
+#if defined(VGO_freebsd)
+LIBC_FUNC(int, semZuclose, sem_close_intercept, (sem_t *sem), (sem));
+#else
 PTH_FUNCS(int, semZuclose, sem_close_intercept, (sem_t *sem), (sem));
+#endif
 
 static __always_inline int sem_wait_intercept(sem_t *sem)
 {
@@ -1446,7 +1503,12 @@ static __always_inline int sem_wait_intercept(sem_t *sem)
    return ret;
 }
 
+#if defined(VGO_freebsd)
+LIBC_FUNC(int, semZuwait, sem_wait_intercept, (sem_t *sem), (sem));
+#else
 PTH_FUNCS(int, semZuwait, sem_wait_intercept, (sem_t *sem), (sem));
+#endif
+
 #if defined(VGO_solaris)
 PTH_FUNCS(int, semaZuwait, sem_wait_intercept, (sem_t *sem), (sem));
 #endif /* VGO_solaris */
@@ -1464,7 +1526,11 @@ static __always_inline int sem_trywait_intercept(sem_t *sem)
    return ret;
 }
 
+#if defined(VGO_freebsd)
+LIBC_FUNC(int, semZutrywait, sem_trywait_intercept, (sem_t *sem), (sem));
+#else
 PTH_FUNCS(int, semZutrywait, sem_trywait_intercept, (sem_t *sem), (sem));
+#endif
 #if defined(VGO_solaris)
 PTH_FUNCS(int, semaZutrywait, sem_trywait_intercept, (sem_t *sem), (sem));
 #endif /* VGO_solaris */
@@ -1483,9 +1549,15 @@ int sem_timedwait_intercept(sem_t *sem, const struct timespec *abs_timeout)
    return ret;
 }
 
+#if defined(VGO_freebsd)
+LIBC_FUNC(int, semZutimedwait, sem_timedwait_intercept,
+          (sem_t *sem, const struct timespec *abs_timeout),
+          (sem, abs_timeout));
+#else
 PTH_FUNCS(int, semZutimedwait, sem_timedwait_intercept,
           (sem_t *sem, const struct timespec *abs_timeout),
           (sem, abs_timeout));
+#endif
 #if defined(VGO_solaris)
 PTH_FUNCS(int, semaZutimedwait, sem_timedwait_intercept,
           (sem_t *sem, const struct timespec *timeout),
@@ -1508,7 +1580,11 @@ static __always_inline int sem_post_intercept(sem_t *sem)
    return ret;
 }
 
+#if defined(VGO_freebsd)
+LIBC_FUNC(int, semZupost, sem_post_intercept, (sem_t *sem), (sem));
+#else
 PTH_FUNCS(int, semZupost, sem_post_intercept, (sem_t *sem), (sem));
+#endif
 #if defined(VGO_solaris)
 PTH_FUNCS(int, semaZupost, sem_post_intercept, (sem_t *sem), (sem));
 #endif /* VGO_solaris */
This page took 0.03577 seconds and 5 git commands to generate.