Fix many holes and bugs in an attempt to get my libpthread.so to export
the same set of symbols as the real one, which I now realise is crucial
for it to work at all.
git-svn-id: svn://svn.valgrind.org/valgrind/trunk@151 a5019735-40e9-0310-863c-91ae7b9d1cf9
diff --git a/vg_libpthread.c b/vg_libpthread.c
index 2715953..4644a0e 100644
--- a/vg_libpthread.c
+++ b/vg_libpthread.c
@@ -679,6 +679,90 @@
}
+/* ---------------------------------------------------
+ LIBC-PRIVATE SPECIFIC DATA
+ ------------------------------------------------ */
+
+/* Relies on assumption that initial private data is NULL. This
+ should be fixed somehow. */
+
+/* The allowable keys (indices) (all 2 of them).
+ From sysdeps/pthread/bits/libc-tsd.h
+*/
+enum __libc_tsd_key_t { _LIBC_TSD_KEY_MALLOC = 0,
+ _LIBC_TSD_KEY_DL_ERROR,
+ _LIBC_TSD_KEY_N };
+
+/* Auto-initialising subsystem. libc_specifics_inited is set
+ after initialisation. libc_specifics_inited_mx guards it. */
+static int libc_specifics_inited = 0;
+static pthread_mutex_t libc_specifics_inited_mx = PTHREAD_MUTEX_INITIALIZER;
+
+/* These are the keys we must initialise the first time. */
+static pthread_key_t libc_specifics_keys[_LIBC_TSD_KEY_N];
+
+/* Initialise the keys, if they are not already initialise. */
+static
+void init_libc_tsd_keys ( void )
+{
+ int res, i;
+ pthread_key_t k;
+
+ res = pthread_mutex_lock(&libc_specifics_inited_mx);
+ if (res != 0) barf("init_libc_tsd_keys: lock");
+
+ if (libc_specifics_inited == 0) {
+ /* printf("INIT libc specifics\n"); */
+ libc_specifics_inited = 1;
+ for (i = 0; i < _LIBC_TSD_KEY_N; i++) {
+ res = pthread_key_create(&k, NULL);
+ if (res != 0) barf("init_libc_tsd_keys: create");
+ libc_specifics_keys[i] = k;
+ }
+ }
+
+ res = pthread_mutex_unlock(&libc_specifics_inited_mx);
+ if (res != 0) barf("init_libc_tsd_keys: unlock");
+}
+
+
+static int
+libc_internal_tsd_set ( enum __libc_tsd_key_t key,
+ const void * pointer )
+{
+ int res;
+ /* printf("SET SET SET key %d ptr %p\n", key, pointer); */
+ if (key < _LIBC_TSD_KEY_MALLOC || key >= _LIBC_TSD_KEY_N)
+ barf("libc_internal_tsd_set: invalid key");
+ init_libc_tsd_keys();
+ res = pthread_setspecific(libc_specifics_keys[key], pointer);
+ if (res != 0) barf("libc_internal_tsd_set: setspecific failed");
+ return 0;
+}
+
+static void *
+libc_internal_tsd_get ( enum __libc_tsd_key_t key )
+{
+ void* v;
+ /* printf("GET GET GET key %d\n", key); */
+ if (key < _LIBC_TSD_KEY_MALLOC || key >= _LIBC_TSD_KEY_N)
+ barf("libc_internal_tsd_get: invalid key");
+ init_libc_tsd_keys();
+ v = pthread_getspecific(libc_specifics_keys[key]);
+ /* if (v == NULL) barf("libc_internal_tsd_set: getspecific failed"); */
+ return v;
+}
+
+
+
+
+int (*__libc_internal_tsd_set)(enum __libc_tsd_key_t key, const void * pointer)
+ = libc_internal_tsd_set;
+
+void* (*__libc_internal_tsd_get)(enum __libc_tsd_key_t key)
+ = libc_internal_tsd_get;
+
+
/* ---------------------------------------------------------------------
These are here (I think) because they are deemed cancellation
points by POSIX. For the moment we'll simply pass the call along
@@ -1214,6 +1298,26 @@
/*--------------------------------------------------*/
+int
+pthread_rwlock_rdlock (void* /* pthread_rwlock_t* */ rwlock)
+{
+ kludged("pthread_rwlock_rdlock");
+ return 0;
+}
+
+strong_alias(pthread_rwlock_rdlock, __pthread_rwlock_rdlock)
+
+
+int
+pthread_rwlock_unlock (void* /* pthread_rwlock_t* */ rwlock)
+{
+ kludged("pthread_rwlock_unlock");
+ return 0;
+}
+
+strong_alias(pthread_rwlock_unlock, __pthread_rwlock_unlock)
+
+
/* I've no idea what these are, but they get called quite a lot.
Anybody know? */