blob: 5b28d6728c2bb52b997ac835d43e863ab0b21f08 [file] [log] [blame]
sewardjaf44c822007-11-25 14:01:38 +00001
2/*--------------------------------------------------------------------*/
sewardj85642922008-01-14 11:54:56 +00003/*--- Client-space code for drd. drd_intercepts.c ---*/
sewardjaf44c822007-11-25 14:01:38 +00004/*--------------------------------------------------------------------*/
5
6/*
7 This file is part of drd, a data race detector.
8
sewardj85642922008-01-14 11:54:56 +00009 Copyright (C) 2006-2008 Bart Van Assche
sewardjaf44c822007-11-25 14:01:38 +000010 bart.vanassche@gmail.com
11
12 This program is free software; you can redistribute it and/or
13 modify it under the terms of the GNU General Public License as
14 published by the Free Software Foundation; either version 2 of the
15 License, or (at your option) any later version.
16
17 This program is distributed in the hope that it will be useful, but
18 WITHOUT ANY WARRANTY; without even the implied warranty of
19 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
20 General Public License for more details.
21
22 You should have received a copy of the GNU General Public License
23 along with this program; if not, write to the Free Software
24 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
25 02111-1307, USA.
26
27 The GNU General Public License is contained in the file COPYING.
28*/
29
30/* ---------------------------------------------------------------------
31 ALL THE CODE IN THIS FILE RUNS ON THE SIMULATED CPU.
32
33 These functions are not called directly - they're the targets of code
34 redirection or load notifications (see pub_core_redir.h for info).
35 They're named weirdly so that the intercept code can find them when the
36 shared object is initially loaded.
37
38 Note that this filename has the "drd_" prefix because it can appear
39 in stack traces, and the "drd_" makes it a little clearer that it
40 originates from Valgrind.
41 ------------------------------------------------------------------ */
42
bart5e85d262008-03-01 10:49:37 +000043// Make sure pthread_spinlock_t is available when compiling with older glibc
44// versions (2.3 or before).
sewardjaf44c822007-11-25 14:01:38 +000045#ifndef _GNU_SOURCE
46#define _GNU_SOURCE
47#endif
48
49#include <assert.h>
bart4501d5c2008-03-04 18:36:23 +000050#include <inttypes.h> // uintptr_t
sewardj85642922008-01-14 11:54:56 +000051#include <pthread.h>
52#include <semaphore.h>
sewardjaf44c822007-11-25 14:01:38 +000053#include <stdio.h>
bart0d063002008-03-01 07:25:13 +000054#include <stdlib.h>
bart4501d5c2008-03-04 18:36:23 +000055#include <unistd.h> // confstr()
bart5e389f12008-04-05 12:53:15 +000056#include "config.h"
sewardjaf44c822007-11-25 14:01:38 +000057#include "drd_clientreq.h"
sewardj85642922008-01-14 11:54:56 +000058#include "pub_tool_redir.h"
sewardjaf44c822007-11-25 14:01:38 +000059
60
61// Defines.
62
bart3772a982008-03-15 08:11:03 +000063#define PTH_FUNC(ret_ty, f, args...) \
64 ret_ty VG_WRAP_FUNCTION_ZZ(libpthreadZdsoZd0,f)(args); \
65 ret_ty VG_WRAP_FUNCTION_ZZ(libpthreadZdsoZd0,f)(args)
sewardjaf44c822007-11-25 14:01:38 +000066
67
bart6f07b252008-04-04 16:45:20 +000068/* Local data structures. */
sewardjaf44c822007-11-25 14:01:38 +000069
70typedef struct
71{
bart3772a982008-03-15 08:11:03 +000072 void* (*start)(void*);
73 void* arg;
74 int detachstate;
sewardjaf44c822007-11-25 14:01:38 +000075#if 0
bart3772a982008-03-15 08:11:03 +000076 pthread_mutex_t mutex;
77 pthread_cond_t cond;
sewardjaf44c822007-11-25 14:01:38 +000078#else
bart3772a982008-03-15 08:11:03 +000079 int wrapper_started;
sewardjaf44c822007-11-25 14:01:38 +000080#endif
81} VgPosixThreadArgs;
82
83
bart6f07b252008-04-04 16:45:20 +000084/* Function declarations. */
sewardjaf44c822007-11-25 14:01:38 +000085
bart44ceea22008-04-16 18:19:45 +000086static void init(void) __attribute__((constructor));
bart6f07b252008-04-04 16:45:20 +000087static void check_threading_library(void);
88static void vg_set_main_thread_state(void);
sewardjaf44c822007-11-25 14:01:38 +000089
90
bart6f07b252008-04-04 16:45:20 +000091/* Function definitions. */
92
93/** Shared library initialization function: the _init() function is called
94 * after dlopen() has loaded the shared library. This function must not
95 * be declared static.
96 */
bart44ceea22008-04-16 18:19:45 +000097static void init(void)
bart6f07b252008-04-04 16:45:20 +000098{
99 check_threading_library();
bart0baacb32008-05-03 09:00:40 +0000100 vg_set_main_thread_state();
bart25d30032008-04-06 07:51:24 +0000101 /* glibc up to and including version 2.7 triggers conflicting accesses */
102 /* on stdout and stderr when sending output to one of these streams from */
103 /* more than one thread. Suppress data race reports on these objects. */
104 DRD_IGNORE_VAR(*stdout);
105 DRD_IGNORE_VAR(*stderr);
bart6f07b252008-04-04 16:45:20 +0000106}
sewardjaf44c822007-11-25 14:01:38 +0000107
bart5357fcb2008-02-27 15:46:00 +0000108static MutexT pthread_to_drd_mutex_type(const int kind)
109{
bart3772a982008-03-15 08:11:03 +0000110 switch (kind)
111 {
112 /* PTHREAD_MUTEX_RECURSIVE_NP */
113 case PTHREAD_MUTEX_RECURSIVE:
114 return mutex_type_recursive_mutex;
115 /* PTHREAD_MUTEX_ERRORCHECK_NP */
116 case PTHREAD_MUTEX_ERRORCHECK:
117 return mutex_type_errorcheck_mutex;
118 /* PTHREAD_MUTEX_TIMED_NP */
119 /* PTHREAD_MUTEX_NORMAL */
120 case PTHREAD_MUTEX_DEFAULT:
sewardj7cf4e6b2008-05-01 20:24:26 +0000121# if !defined(VGP_ppc32_aix5) && !defined(VGP_ppc64_aix5)
bart3772a982008-03-15 08:11:03 +0000122 case PTHREAD_MUTEX_ADAPTIVE_NP:
sewardj7cf4e6b2008-05-01 20:24:26 +0000123# endif
bart3772a982008-03-15 08:11:03 +0000124 return mutex_type_default_mutex;
125 }
126 return mutex_type_invalid_mutex;
bart5357fcb2008-02-27 15:46:00 +0000127}
128
129static MutexT mutex_type(pthread_mutex_t* mutex)
130{
bart5e389f12008-04-05 12:53:15 +0000131#if defined(HAVE_PTHREAD_MUTEX_T__M_KIND)
132 /* LinuxThreads. */
bart3772a982008-03-15 08:11:03 +0000133 const int kind = mutex->__m_kind;
bart5e389f12008-04-05 12:53:15 +0000134#elif defined(HAVE_PTHREAD_MUTEX_T__DATA__KIND)
135 /* NPTL. */
bart3772a982008-03-15 08:11:03 +0000136 const int kind = mutex->__data.__kind;
bartc9463c42008-02-28 07:36:04 +0000137#else
bart5e389f12008-04-05 12:53:15 +0000138 /* Another POSIX threads implementation. Regression tests will fail. */
bart3772a982008-03-15 08:11:03 +0000139 const int kind = PTHREAD_MUTEX_DEFAULT;
bart5e389f12008-04-05 12:53:15 +0000140 fprintf(stderr,
141 "Did not recognize your POSIX threads implementation. Giving up.\n");
142 assert(0);
bartc9463c42008-02-28 07:36:04 +0000143#endif
bart3772a982008-03-15 08:11:03 +0000144 return pthread_to_drd_mutex_type(kind);
bart5357fcb2008-02-27 15:46:00 +0000145}
146
sewardjaf44c822007-11-25 14:01:38 +0000147static void vg_start_suppression(const void* const p, size_t const size)
148{
bart3772a982008-03-15 08:11:03 +0000149 int res;
150 VALGRIND_DO_CLIENT_REQUEST(res, 0, VG_USERREQ__DRD_START_SUPPRESSION,
bartf5bb46a2008-03-29 13:18:02 +0000151 p, size, 0, 0, 0);
sewardjaf44c822007-11-25 14:01:38 +0000152}
153
154static void vg_set_joinable(const pthread_t tid, const int joinable)
155{
bart3772a982008-03-15 08:11:03 +0000156 int res;
157 assert(joinable == 0 || joinable == 1);
158 VALGRIND_DO_CLIENT_REQUEST(res, 0, VG_USERREQ__SET_JOINABLE,
159 tid, joinable, 0, 0, 0);
sewardjaf44c822007-11-25 14:01:38 +0000160}
161
162static void* vg_thread_wrapper(void* arg)
163{
bart3772a982008-03-15 08:11:03 +0000164 int res;
bart0d063002008-03-01 07:25:13 +0000165
bart3772a982008-03-15 08:11:03 +0000166 VALGRIND_DO_CLIENT_REQUEST(res, 0, VG_USERREQ__DRD_SUPPRESS_CURRENT_STACK,
167 0, 0, 0, 0, 0);
sewardjaf44c822007-11-25 14:01:38 +0000168
bart3772a982008-03-15 08:11:03 +0000169 {
170 VgPosixThreadArgs* const arg_ptr = (VgPosixThreadArgs*)arg;
171 VgPosixThreadArgs const arg_copy = *arg_ptr;
172 void* result;
sewardjaf44c822007-11-25 14:01:38 +0000173
174#if 0
bart3772a982008-03-15 08:11:03 +0000175 pthread_mutex_lock(arg_ptr->mutex);
176 pthread_cond_signal(arg_ptr->cond);
177 pthread_mutex_unlock(arg_ptr->mutex);
sewardjaf44c822007-11-25 14:01:38 +0000178#else
bart3772a982008-03-15 08:11:03 +0000179 arg_ptr->wrapper_started = 1;
sewardjaf44c822007-11-25 14:01:38 +0000180#endif
181
bart3772a982008-03-15 08:11:03 +0000182 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__SET_PTHREADID,
183 pthread_self(), 0, 0, 0, 0);
184 vg_set_joinable(pthread_self(),
185 arg_copy.detachstate == PTHREAD_CREATE_JOINABLE);
186 result = (arg_copy.start)(arg_copy.arg);
187 return result;
188 }
sewardjaf44c822007-11-25 14:01:38 +0000189}
190
bart6f07b252008-04-04 16:45:20 +0000191/** Return 1 if LinuxThread has been detected, and 0 otherwise. */
bart4501d5c2008-03-04 18:36:23 +0000192static int detected_linuxthreads(void)
193{
194#if defined(linux)
195#if defined(_CS_GNU_LIBPTHREAD_VERSION)
bart3772a982008-03-15 08:11:03 +0000196 /* Linux with a recent glibc. */
197 char buffer[256];
198 unsigned len;
199 len = confstr(_CS_GNU_LIBPTHREAD_VERSION, buffer, sizeof(buffer));
200 assert(len <= sizeof(buffer));
201 return len > 0 && buffer[0] == 'l';
bart4501d5c2008-03-04 18:36:23 +0000202#else
bart3772a982008-03-15 08:11:03 +0000203 /* Linux without _CS_GNU_LIBPTHREAD_VERSION: most likely LinuxThreads. */
204 return 1;
bart4501d5c2008-03-04 18:36:23 +0000205#endif
206#else
bart3772a982008-03-15 08:11:03 +0000207 /* Another OS than Linux, hence no LinuxThreads. */
208 return 0;
bart4501d5c2008-03-04 18:36:23 +0000209#endif
210}
211
bart6f07b252008-04-04 16:45:20 +0000212/** Stop and print an error message in case a non-supported threading
213 * library (LinuxThreads) has been detected.
214 */
215static void check_threading_library(void)
sewardjaf44c822007-11-25 14:01:38 +0000216{
bart3772a982008-03-15 08:11:03 +0000217 if (detected_linuxthreads())
218 {
219 if (getenv("LD_ASSUME_KERNEL"))
220 {
221 fprintf(stderr,
222 "Detected the LinuxThreads threading library. Sorry, but DRD only supports\n"
223 "the newer NPTL (Native POSIX Threads Library). Please try to rerun DRD\n"
224 "after having unset the environment variable LD_ASSUME_KERNEL. Giving up.\n"
225 );
226 }
227 else
228 {
229 fprintf(stderr,
230 "Detected the LinuxThreads threading library. Sorry, but DRD only supports\n"
231 "the newer NPTL (Native POSIX Threads Library). Please try to rerun DRD\n"
232 "after having upgraded to a newer version of your Linux distribution.\n"
233 "Giving up.\n"
234 );
235 }
236 abort();
237 }
bart6f07b252008-04-04 16:45:20 +0000238}
239
240static void vg_set_main_thread_state(void)
241{
242 int res;
bart0d063002008-03-01 07:25:13 +0000243
bart3772a982008-03-15 08:11:03 +0000244 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__DRD_SUPPRESS_CURRENT_STACK,
245 0, 0, 0, 0, 0);
sewardjaf44c822007-11-25 14:01:38 +0000246
bart3772a982008-03-15 08:11:03 +0000247 // Make sure that DRD knows about the main thread's POSIX thread ID.
248 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__SET_PTHREADID,
249 pthread_self(), 0, 0, 0, 0);
sewardjaf44c822007-11-25 14:01:38 +0000250
251}
252
253// pthread_create
sewardj347eeba2008-01-21 14:19:07 +0000254PTH_FUNC(int, pthreadZucreateZa, // pthread_create*
bart3772a982008-03-15 08:11:03 +0000255 pthread_t *thread, const pthread_attr_t *attr,
256 void *(*start) (void *), void *arg)
sewardjaf44c822007-11-25 14:01:38 +0000257{
bartbf3a60c2008-04-04 19:10:21 +0000258 int res;
bart3772a982008-03-15 08:11:03 +0000259 int ret;
260 OrigFn fn;
261 VgPosixThreadArgs vgargs;
sewardjaf44c822007-11-25 14:01:38 +0000262
bart3772a982008-03-15 08:11:03 +0000263 VALGRIND_GET_ORIG_FN(fn);
sewardjaf44c822007-11-25 14:01:38 +0000264
bart3772a982008-03-15 08:11:03 +0000265 vg_start_suppression(&vgargs.wrapper_started,
266 sizeof(vgargs.wrapper_started));
267 vgargs.start = start;
268 vgargs.arg = arg;
269 vgargs.wrapper_started = 0;
270 vgargs.detachstate = PTHREAD_CREATE_JOINABLE;
271 if (attr)
272 {
273 if (pthread_attr_getdetachstate(attr, &vgargs.detachstate) != 0)
274 {
275 assert(0);
276 }
277 }
278 assert(vgargs.detachstate == PTHREAD_CREATE_JOINABLE
279 || vgargs.detachstate == PTHREAD_CREATE_DETACHED);
sewardjaf44c822007-11-25 14:01:38 +0000280#if 0
bart3772a982008-03-15 08:11:03 +0000281 pthread_mutex_init(&vgargs.mutex, 0);
282 pthread_cond_init(&vgargs.cond, 0);
283 pthread_mutex_lock(&vgargs.mutex);
sewardjaf44c822007-11-25 14:01:38 +0000284#endif
bartbf3a60c2008-04-04 19:10:21 +0000285 /* Suppress NPTL-specific conflicts between creator and created thread. */
286 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__DRD_STOP_RECORDING,
287 0, 0, 0, 0, 0);
bart3772a982008-03-15 08:11:03 +0000288 CALL_FN_W_WWWW(ret, fn, thread, attr, vg_thread_wrapper, &vgargs);
bartbf3a60c2008-04-04 19:10:21 +0000289 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__DRD_START_RECORDING,
290 0, 0, 0, 0, 0);
sewardjaf44c822007-11-25 14:01:38 +0000291#if 0
bart3772a982008-03-15 08:11:03 +0000292 pthread_cond_wait(&vgargs.cond, &vgargs.mutex);
293 pthread_mutex_unlock(&vgargs.mutex);
294 pthread_cond_destroy(&vgargs.cond);
295 pthread_mutex_destroy(&vgargs.mutex);
sewardjaf44c822007-11-25 14:01:38 +0000296#else
bart3772a982008-03-15 08:11:03 +0000297 // Yes, you see it correctly, busy waiting ... The problem is that
298 // POSIX threads functions cannot be called here -- the functions defined
299 // in this file (drd_intercepts.c) would be called instead of those in
300 // libpthread.so. This loop is necessary because vgargs is allocated on the
301 // stack, and the created thread reads it.
302 if (ret == 0)
303 {
304 while (! vgargs.wrapper_started)
305 {
306 sched_yield();
307 }
308 }
sewardjaf44c822007-11-25 14:01:38 +0000309#endif
bart3772a982008-03-15 08:11:03 +0000310 return ret;
sewardjaf44c822007-11-25 14:01:38 +0000311}
312
313// pthread_join
314PTH_FUNC(int, pthreadZujoin, // pthread_join
bart3772a982008-03-15 08:11:03 +0000315 pthread_t pt_joinee, void **thread_return)
sewardjaf44c822007-11-25 14:01:38 +0000316{
bart3772a982008-03-15 08:11:03 +0000317 int ret;
318 int res;
319 OrigFn fn;
sewardjaf44c822007-11-25 14:01:38 +0000320
bart3772a982008-03-15 08:11:03 +0000321 VALGRIND_GET_ORIG_FN(fn);
322 CALL_FN_W_WW(ret, fn, pt_joinee, thread_return);
323 if (ret == 0)
324 {
325 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_THREAD_JOIN,
326 pt_joinee, 0, 0, 0, 0);
327 }
328 return ret;
sewardjaf44c822007-11-25 14:01:38 +0000329}
330
331// pthread_detach
332PTH_FUNC(int, pthreadZudetach, pthread_t pt_thread)
333{
bart3772a982008-03-15 08:11:03 +0000334 int ret;
335 OrigFn fn;
336 VALGRIND_GET_ORIG_FN(fn);
337 {
338 CALL_FN_W_W(ret, fn, pt_thread);
339 if (ret == 0)
340 {
341 vg_set_joinable(pt_thread, 0);
342 }
343 }
344 return ret;
sewardjaf44c822007-11-25 14:01:38 +0000345}
346
347// pthread_mutex_init
348PTH_FUNC(int, pthreadZumutexZuinit,
bart3772a982008-03-15 08:11:03 +0000349 pthread_mutex_t *mutex,
350 const pthread_mutexattr_t* attr)
sewardjaf44c822007-11-25 14:01:38 +0000351{
bart3772a982008-03-15 08:11:03 +0000352 int ret;
353 int res;
354 OrigFn fn;
355 int mt;
356 VALGRIND_GET_ORIG_FN(fn);
357 mt = PTHREAD_MUTEX_DEFAULT;
358 if (attr)
359 pthread_mutexattr_gettype(attr, &mt);
360 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__PRE_MUTEX_INIT,
361 mutex, pthread_to_drd_mutex_type(mt), 0, 0, 0);
362 CALL_FN_W_WW(ret, fn, mutex, attr);
363 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_MUTEX_INIT,
364 mutex, 0, 0, 0, 0);
365 return ret;
sewardjaf44c822007-11-25 14:01:38 +0000366}
367
368// pthread_mutex_destroy
369PTH_FUNC(int, pthreadZumutexZudestroy,
bart3772a982008-03-15 08:11:03 +0000370 pthread_mutex_t *mutex)
sewardjaf44c822007-11-25 14:01:38 +0000371{
bart3772a982008-03-15 08:11:03 +0000372 int ret;
373 int res;
374 OrigFn fn;
375 VALGRIND_GET_ORIG_FN(fn);
376 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__PRE_MUTEX_DESTROY,
377 mutex, 0, 0, 0, 0);
378 CALL_FN_W_W(ret, fn, mutex);
379 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_MUTEX_DESTROY,
380 mutex, mutex_type(mutex), 0, 0, 0);
381 return ret;
sewardjaf44c822007-11-25 14:01:38 +0000382}
383
384// pthread_mutex_lock
385PTH_FUNC(int, pthreadZumutexZulock, // pthread_mutex_lock
bart3772a982008-03-15 08:11:03 +0000386 pthread_mutex_t *mutex)
sewardjaf44c822007-11-25 14:01:38 +0000387{
bart3772a982008-03-15 08:11:03 +0000388 int ret;
389 int res;
390 OrigFn fn;
391 VALGRIND_GET_ORIG_FN(fn);
392 VALGRIND_DO_CLIENT_REQUEST(res, 0, VG_USERREQ__PRE_MUTEX_LOCK,
393 mutex, mutex_type(mutex), 0, 0, 0);
394 CALL_FN_W_W(ret, fn, mutex);
395 VALGRIND_DO_CLIENT_REQUEST(res, 0, VG_USERREQ__POST_MUTEX_LOCK,
396 mutex, ret == 0, 0, 0, 0);
397 return ret;
sewardjaf44c822007-11-25 14:01:38 +0000398}
399
400// pthread_mutex_trylock
401PTH_FUNC(int, pthreadZumutexZutrylock, // pthread_mutex_trylock
bart3772a982008-03-15 08:11:03 +0000402 pthread_mutex_t *mutex)
sewardjaf44c822007-11-25 14:01:38 +0000403{
bart3772a982008-03-15 08:11:03 +0000404 int ret;
405 int res;
406 OrigFn fn;
407 VALGRIND_GET_ORIG_FN(fn);
408 VALGRIND_DO_CLIENT_REQUEST(res, 0, VG_USERREQ__PRE_MUTEX_LOCK,
bart2e3a3c12008-03-24 08:33:47 +0000409 mutex, mutex_type(mutex), 1, 0, 0);
bart3772a982008-03-15 08:11:03 +0000410 CALL_FN_W_W(ret, fn, mutex);
411 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_MUTEX_LOCK,
412 mutex, ret == 0, 0, 0, 0);
413 return ret;
sewardjaf44c822007-11-25 14:01:38 +0000414}
415
sewardj85642922008-01-14 11:54:56 +0000416// pthread_mutex_timedlock
417PTH_FUNC(int, pthreadZumutexZutimedlock, // pthread_mutex_timedlock
bart3772a982008-03-15 08:11:03 +0000418 pthread_mutex_t *mutex,
419 const struct timespec *abs_timeout)
sewardj85642922008-01-14 11:54:56 +0000420{
bart3772a982008-03-15 08:11:03 +0000421 int ret;
422 int res;
423 OrigFn fn;
424 VALGRIND_GET_ORIG_FN(fn);
425 VALGRIND_DO_CLIENT_REQUEST(res, 0, VG_USERREQ__PRE_MUTEX_LOCK,
426 mutex, mutex_type(mutex), 0, 0, 0);
427 CALL_FN_W_WW(ret, fn, mutex, abs_timeout);
428 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_MUTEX_LOCK,
429 mutex, ret == 0, 0, 0, 0);
430 return ret;
sewardj85642922008-01-14 11:54:56 +0000431}
432
sewardjaf44c822007-11-25 14:01:38 +0000433// pthread_mutex_unlock
434PTH_FUNC(int, pthreadZumutexZuunlock, // pthread_mutex_unlock
bart3772a982008-03-15 08:11:03 +0000435 pthread_mutex_t *mutex)
sewardjaf44c822007-11-25 14:01:38 +0000436{
bart3772a982008-03-15 08:11:03 +0000437 int ret;
438 int res;
439 OrigFn fn;
440 VALGRIND_GET_ORIG_FN(fn);
441 VALGRIND_DO_CLIENT_REQUEST(res, -1,
442 VG_USERREQ__PRE_MUTEX_UNLOCK,
443 mutex, mutex_type(mutex), 0, 0, 0);
444 CALL_FN_W_W(ret, fn, mutex);
445 VALGRIND_DO_CLIENT_REQUEST(res, -1,
446 VG_USERREQ__POST_MUTEX_UNLOCK,
447 mutex, 0, 0, 0, 0);
448 return ret;
sewardjaf44c822007-11-25 14:01:38 +0000449}
450
451// pthread_cond_init
sewardj347eeba2008-01-21 14:19:07 +0000452PTH_FUNC(int, pthreadZucondZuinitZa, // pthread_cond_init*
bart3772a982008-03-15 08:11:03 +0000453 pthread_cond_t* cond,
454 const pthread_condattr_t* attr)
sewardjaf44c822007-11-25 14:01:38 +0000455{
bart3772a982008-03-15 08:11:03 +0000456 int ret;
457 int res;
458 OrigFn fn;
459 VALGRIND_GET_ORIG_FN(fn);
460 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__PRE_COND_INIT,
461 cond, 0, 0, 0, 0);
462 CALL_FN_W_WW(ret, fn, cond, attr);
463 return ret;
sewardjaf44c822007-11-25 14:01:38 +0000464}
465
466// pthread_cond_destroy
sewardj347eeba2008-01-21 14:19:07 +0000467PTH_FUNC(int, pthreadZucondZudestroyZa, // pthread_cond_destroy*
bart3772a982008-03-15 08:11:03 +0000468 pthread_cond_t* cond)
sewardjaf44c822007-11-25 14:01:38 +0000469{
bart3772a982008-03-15 08:11:03 +0000470 int ret;
471 int res;
472 OrigFn fn;
473 VALGRIND_GET_ORIG_FN(fn);
474 CALL_FN_W_W(ret, fn, cond);
475 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_COND_DESTROY,
476 cond, 0, 0, 0, 0);
477 return ret;
sewardjaf44c822007-11-25 14:01:38 +0000478}
479
480// pthread_cond_wait
sewardj347eeba2008-01-21 14:19:07 +0000481PTH_FUNC(int, pthreadZucondZuwaitZa, // pthread_cond_wait*
bart3772a982008-03-15 08:11:03 +0000482 pthread_cond_t *cond,
483 pthread_mutex_t *mutex)
sewardjaf44c822007-11-25 14:01:38 +0000484{
bart3772a982008-03-15 08:11:03 +0000485 int ret;
486 int res;
487 OrigFn fn;
488 VALGRIND_GET_ORIG_FN(fn);
489 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__PRE_COND_WAIT,
490 cond, mutex, mutex_type(mutex), 0, 0);
491 CALL_FN_W_WW(ret, fn, cond, mutex);
492 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_COND_WAIT,
bart1b7a8302008-03-30 08:39:51 +0000493 cond, mutex, 1, 0, 0);
bart3772a982008-03-15 08:11:03 +0000494 return ret;
sewardjaf44c822007-11-25 14:01:38 +0000495}
496
497// pthread_cond_timedwait
sewardj347eeba2008-01-21 14:19:07 +0000498PTH_FUNC(int, pthreadZucondZutimedwaitZa, // pthread_cond_timedwait*
bart3772a982008-03-15 08:11:03 +0000499 pthread_cond_t *cond,
500 pthread_mutex_t *mutex,
501 const struct timespec* abstime)
sewardjaf44c822007-11-25 14:01:38 +0000502{
bart3772a982008-03-15 08:11:03 +0000503 int ret;
504 int res;
505 OrigFn fn;
506 VALGRIND_GET_ORIG_FN(fn);
507 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__PRE_COND_WAIT,
508 cond, mutex, mutex_type(mutex), 0, 0);
509 CALL_FN_W_WWW(ret, fn, cond, mutex, abstime);
510 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_COND_WAIT,
bart1b7a8302008-03-30 08:39:51 +0000511 cond, mutex, 1, 0, 0);
bart3772a982008-03-15 08:11:03 +0000512 return ret;
sewardjaf44c822007-11-25 14:01:38 +0000513}
514
515// pthread_cond_signal
sewardj347eeba2008-01-21 14:19:07 +0000516PTH_FUNC(int, pthreadZucondZusignalZa, // pthread_cond_signal*
bart3772a982008-03-15 08:11:03 +0000517 pthread_cond_t* cond)
sewardjaf44c822007-11-25 14:01:38 +0000518{
bart3772a982008-03-15 08:11:03 +0000519 int ret;
520 int res;
521 OrigFn fn;
522 VALGRIND_GET_ORIG_FN(fn);
523 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__PRE_COND_SIGNAL,
524 cond, 0, 0, 0, 0);
525 CALL_FN_W_W(ret, fn, cond);
526 return ret;
sewardjaf44c822007-11-25 14:01:38 +0000527}
528
529// pthread_cond_broadcast
sewardj347eeba2008-01-21 14:19:07 +0000530PTH_FUNC(int, pthreadZucondZubroadcastZa, // pthread_cond_broadcast*
bart3772a982008-03-15 08:11:03 +0000531 pthread_cond_t* cond)
sewardjaf44c822007-11-25 14:01:38 +0000532{
bart3772a982008-03-15 08:11:03 +0000533 int ret;
534 int res;
535 OrigFn fn;
536 VALGRIND_GET_ORIG_FN(fn);
537 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__PRE_COND_BROADCAST,
538 cond, 0, 0, 0, 0);
539 CALL_FN_W_W(ret, fn, cond);
540 return ret;
sewardjaf44c822007-11-25 14:01:38 +0000541}
542
543
544// pthread_spin_init
545PTH_FUNC(int, pthreadZuspinZuinit, // pthread_spin_init
bart3772a982008-03-15 08:11:03 +0000546 pthread_spinlock_t *spinlock,
547 int pshared)
sewardjaf44c822007-11-25 14:01:38 +0000548{
bart3772a982008-03-15 08:11:03 +0000549 int ret;
550 int res;
551 OrigFn fn;
552 VALGRIND_GET_ORIG_FN(fn);
553 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__SPIN_INIT_OR_UNLOCK,
554 spinlock, mutex_type_spinlock, 0, 0, 0);
555 CALL_FN_W_WW(ret, fn, spinlock, pshared);
556 return ret;
sewardjaf44c822007-11-25 14:01:38 +0000557}
558
559// pthread_spin_destroy
560PTH_FUNC(int, pthreadZuspinZudestroy, // pthread_spin_destroy
bart3772a982008-03-15 08:11:03 +0000561 pthread_spinlock_t *spinlock)
sewardjaf44c822007-11-25 14:01:38 +0000562{
bart3772a982008-03-15 08:11:03 +0000563 int ret;
564 int res;
565 OrigFn fn;
566 VALGRIND_GET_ORIG_FN(fn);
567 CALL_FN_W_W(ret, fn, spinlock);
568 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_MUTEX_DESTROY,
569 spinlock, mutex_type_spinlock, 0, 0, 0);
570 return ret;
sewardjaf44c822007-11-25 14:01:38 +0000571}
572
573// pthread_spin_lock
574PTH_FUNC(int, pthreadZuspinZulock, // pthread_spin_lock
bart3772a982008-03-15 08:11:03 +0000575 pthread_spinlock_t *spinlock)
sewardjaf44c822007-11-25 14:01:38 +0000576{
bart3772a982008-03-15 08:11:03 +0000577 int ret;
578 int res;
579 OrigFn fn;
580 VALGRIND_GET_ORIG_FN(fn);
581 VALGRIND_DO_CLIENT_REQUEST(res, 0, VG_USERREQ__PRE_MUTEX_LOCK,
582 spinlock, mutex_type_spinlock, 0, 0, 0);
583 CALL_FN_W_W(ret, fn, spinlock);
584 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_MUTEX_LOCK,
585 spinlock, ret == 0, 0, 0, 0);
586 return ret;
sewardjaf44c822007-11-25 14:01:38 +0000587}
588
589// pthread_spin_trylock
590PTH_FUNC(int, pthreadZuspinZutrylock, // pthread_spin_trylock
bart3772a982008-03-15 08:11:03 +0000591 pthread_spinlock_t *spinlock)
sewardjaf44c822007-11-25 14:01:38 +0000592{
bart3772a982008-03-15 08:11:03 +0000593 int ret;
594 int res;
595 OrigFn fn;
596 VALGRIND_GET_ORIG_FN(fn);
597 VALGRIND_DO_CLIENT_REQUEST(res, 0, VG_USERREQ__PRE_MUTEX_LOCK,
598 spinlock, mutex_type_spinlock, 0, 0, 0);
599 CALL_FN_W_W(ret, fn, spinlock);
600 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_MUTEX_LOCK,
601 spinlock, ret == 0, 0, 0, 0);
602 return ret;
sewardjaf44c822007-11-25 14:01:38 +0000603}
604
605// pthread_spin_unlock
606PTH_FUNC(int, pthreadZuspinZuunlock, // pthread_spin_unlock
bart3772a982008-03-15 08:11:03 +0000607 pthread_spinlock_t *spinlock)
sewardjaf44c822007-11-25 14:01:38 +0000608{
bart3772a982008-03-15 08:11:03 +0000609 int ret;
610 int res;
611 OrigFn fn;
612 VALGRIND_GET_ORIG_FN(fn);
613 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__SPIN_INIT_OR_UNLOCK,
614 spinlock, mutex_type_spinlock, 0, 0, 0);
615 CALL_FN_W_W(ret, fn, spinlock);
616 return ret;
sewardjaf44c822007-11-25 14:01:38 +0000617}
618
sewardj85642922008-01-14 11:54:56 +0000619// pthread_barrier_init
620PTH_FUNC(int, pthreadZubarrierZuinit, // pthread_barrier_init
bart3772a982008-03-15 08:11:03 +0000621 pthread_barrier_t* barrier,
622 const pthread_barrierattr_t* attr,
623 unsigned count)
sewardj85642922008-01-14 11:54:56 +0000624{
bart3772a982008-03-15 08:11:03 +0000625 int ret;
626 int res;
627 OrigFn fn;
628 VALGRIND_GET_ORIG_FN(fn);
629 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__PRE_BARRIER_INIT,
630 barrier, pthread_barrier, count, 0, 0);
631 CALL_FN_W_WWW(ret, fn, barrier, attr, count);
632 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_BARRIER_INIT,
633 barrier, pthread_barrier, 0, 0, 0);
634 return ret;
sewardj85642922008-01-14 11:54:56 +0000635}
636
637// pthread_barrier_destroy
638PTH_FUNC(int, pthreadZubarrierZudestroy, // pthread_barrier_destroy
bart3772a982008-03-15 08:11:03 +0000639 pthread_barrier_t* barrier)
sewardj85642922008-01-14 11:54:56 +0000640{
bart3772a982008-03-15 08:11:03 +0000641 int ret;
642 int res;
643 OrigFn fn;
644 VALGRIND_GET_ORIG_FN(fn);
645 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__PRE_BARRIER_DESTROY,
646 barrier, pthread_barrier, 0, 0, 0);
647 CALL_FN_W_W(ret, fn, barrier);
648 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_BARRIER_DESTROY,
649 barrier, pthread_barrier, 0, 0, 0);
650 return ret;
sewardj85642922008-01-14 11:54:56 +0000651}
652
653// pthread_barrier_wait
654PTH_FUNC(int, pthreadZubarrierZuwait, // pthread_barrier_wait
bart3772a982008-03-15 08:11:03 +0000655 pthread_barrier_t* barrier)
sewardj85642922008-01-14 11:54:56 +0000656{
bart3772a982008-03-15 08:11:03 +0000657 int ret;
658 int res;
659 OrigFn fn;
660 VALGRIND_GET_ORIG_FN(fn);
661 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__PRE_BARRIER_WAIT,
662 barrier, pthread_barrier, 0, 0, 0);
663 CALL_FN_W_W(ret, fn, barrier);
664 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_BARRIER_WAIT,
665 barrier, pthread_barrier,
666 ret == 0 || ret == PTHREAD_BARRIER_SERIAL_THREAD,
667 0, 0);
668 return ret;
sewardj85642922008-01-14 11:54:56 +0000669}
670
671
sewardj85642922008-01-14 11:54:56 +0000672// sem_init
bart368ec982008-03-11 20:39:01 +0000673PTH_FUNC(int, semZuinitZa, // sem_init*
bart3772a982008-03-15 08:11:03 +0000674 sem_t *sem,
675 int pshared,
676 unsigned int value)
sewardj85642922008-01-14 11:54:56 +0000677{
bart3772a982008-03-15 08:11:03 +0000678 int ret;
679 int res;
680 OrigFn fn;
681 VALGRIND_GET_ORIG_FN(fn);
682 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__PRE_SEM_INIT,
683 sem, pshared, value, 0, 0);
684 CALL_FN_W_WWW(ret, fn, sem, pshared, value);
685 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_SEM_INIT,
686 sem, 0, 0, 0, 0);
687 return ret;
sewardj85642922008-01-14 11:54:56 +0000688}
689
690// sem_destroy
bart00344642008-03-01 15:27:41 +0000691PTH_FUNC(int, semZudestroyZa, // sem_destroy*
bart3772a982008-03-15 08:11:03 +0000692 sem_t *sem)
sewardj85642922008-01-14 11:54:56 +0000693{
bart3772a982008-03-15 08:11:03 +0000694 int ret;
695 int res;
696 OrigFn fn;
697 VALGRIND_GET_ORIG_FN(fn);
698 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__PRE_SEM_DESTROY,
699 sem, 0, 0, 0, 0);
700 CALL_FN_W_W(ret, fn, sem);
701 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_SEM_DESTROY,
702 sem, 0, 0, 0, 0);
703 return ret;
sewardj85642922008-01-14 11:54:56 +0000704}
705
706// sem_wait
bart368ec982008-03-11 20:39:01 +0000707PTH_FUNC(int, semZuwaitZa, // sem_wait*
bart3772a982008-03-15 08:11:03 +0000708 sem_t *sem)
sewardj85642922008-01-14 11:54:56 +0000709{
bart3772a982008-03-15 08:11:03 +0000710 int ret;
711 int res;
712 OrigFn fn;
713 VALGRIND_GET_ORIG_FN(fn);
714 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__PRE_SEM_WAIT,
715 sem, 0, 0, 0, 0);
716 CALL_FN_W_W(ret, fn, sem);
717 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_SEM_WAIT,
718 sem, ret == 0, 0, 0, 0);
719 return ret;
sewardj85642922008-01-14 11:54:56 +0000720}
721
722// sem_trywait
bart00344642008-03-01 15:27:41 +0000723PTH_FUNC(int, semZutrywaitZa, // sem_trywait*
bart3772a982008-03-15 08:11:03 +0000724 sem_t *sem)
sewardj85642922008-01-14 11:54:56 +0000725{
bart3772a982008-03-15 08:11:03 +0000726 int ret;
727 int res;
728 OrigFn fn;
729 VALGRIND_GET_ORIG_FN(fn);
730 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__PRE_SEM_WAIT,
731 sem, 0, 0, 0, 0);
732 CALL_FN_W_W(ret, fn, sem);
733 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_SEM_WAIT,
734 sem, ret == 0, 0, 0, 0);
735 return ret;
sewardj85642922008-01-14 11:54:56 +0000736}
737
738// sem_timedwait
bart00344642008-03-01 15:27:41 +0000739PTH_FUNC(int, semZutimedwait, // sem_timedwait
bart3772a982008-03-15 08:11:03 +0000740 sem_t *sem, const struct timespec *abs_timeout)
sewardj85642922008-01-14 11:54:56 +0000741{
bart3772a982008-03-15 08:11:03 +0000742 int ret;
743 int res;
744 OrigFn fn;
745 VALGRIND_GET_ORIG_FN(fn);
746 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__PRE_SEM_WAIT,
747 sem, 0, 0, 0, 0);
748 CALL_FN_W_WW(ret, fn, sem, abs_timeout);
749 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_SEM_WAIT,
750 sem, ret == 0, 0, 0, 0);
751 return ret;
sewardj85642922008-01-14 11:54:56 +0000752}
753
754// sem_post
bart368ec982008-03-11 20:39:01 +0000755PTH_FUNC(int, semZupostZa, // sem_post*
bart3772a982008-03-15 08:11:03 +0000756 sem_t *sem)
sewardj85642922008-01-14 11:54:56 +0000757{
bart3772a982008-03-15 08:11:03 +0000758 int ret;
759 int res;
760 OrigFn fn;
761 VALGRIND_GET_ORIG_FN(fn);
762 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__PRE_SEM_POST,
763 sem, 0, 0, 0, 0);
764 CALL_FN_W_W(ret, fn, sem);
765 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_SEM_POST,
766 sem, ret == 0, 0, 0, 0);
767 return ret;
sewardj85642922008-01-14 11:54:56 +0000768}
769
bart00344642008-03-01 15:27:41 +0000770// pthread_rwlock_init
771PTH_FUNC(int,
772 pthreadZurwlockZuinitZa, // pthread_rwlock_init*
773 pthread_rwlock_t* rwlock,
774 const pthread_rwlockattr_t* attr)
775{
bart3772a982008-03-15 08:11:03 +0000776 int ret;
777 int res;
778 OrigFn fn;
779 VALGRIND_GET_ORIG_FN(fn);
780 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__PRE_RWLOCK_INIT,
781 rwlock, 0, 0, 0, 0);
782 CALL_FN_W_WW(ret, fn, rwlock, attr);
783 return ret;
bart00344642008-03-01 15:27:41 +0000784}
785
786// pthread_rwlock_destroy
787PTH_FUNC(int,
788 pthreadZurwlockZudestroyZa, // pthread_rwlock_destroy*
789 pthread_rwlock_t* rwlock)
790{
bart3772a982008-03-15 08:11:03 +0000791 int ret;
792 int res;
793 OrigFn fn;
794 VALGRIND_GET_ORIG_FN(fn);
795 CALL_FN_W_W(ret, fn, rwlock);
796 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_RWLOCK_DESTROY,
797 rwlock, 0, 0, 0, 0);
798 return ret;
bart00344642008-03-01 15:27:41 +0000799}
800
801// pthread_rwlock_rdlock
802PTH_FUNC(int,
803 pthreadZurwlockZurdlockZa, // pthread_rwlock_rdlock*
804 pthread_rwlock_t* rwlock)
805{
bart3772a982008-03-15 08:11:03 +0000806 int ret;
807 int res;
808 OrigFn fn;
809 VALGRIND_GET_ORIG_FN(fn);
810 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__PRE_RWLOCK_RDLOCK,
811 rwlock, 0, 0, 0, 0);
812 CALL_FN_W_W(ret, fn, rwlock);
813 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_RWLOCK_RDLOCK,
814 rwlock, ret == 0, 0, 0, 0);
815 return ret;
bart00344642008-03-01 15:27:41 +0000816}
817
818// pthread_rwlock_wrlock
819PTH_FUNC(int,
820 pthreadZurwlockZuwrlockZa, // pthread_rwlock_wrlock*
821 pthread_rwlock_t* rwlock)
822{
bart3772a982008-03-15 08:11:03 +0000823 int ret;
824 int res;
825 OrigFn fn;
826 VALGRIND_GET_ORIG_FN(fn);
827 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__PRE_RWLOCK_WRLOCK,
828 rwlock, 0, 0, 0, 0);
829 CALL_FN_W_W(ret, fn, rwlock);
830 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_RWLOCK_WRLOCK,
831 rwlock, ret == 0, 0, 0, 0);
832 return ret;
bart00344642008-03-01 15:27:41 +0000833}
834
835// pthread_rwlock_timedrdlock
836PTH_FUNC(int,
837 pthreadZurwlockZutimedrdlockZa, // pthread_rwlock_timedrdlock*
838 pthread_rwlock_t* rwlock)
839{
bart3772a982008-03-15 08:11:03 +0000840 int ret;
841 int res;
842 OrigFn fn;
843 VALGRIND_GET_ORIG_FN(fn);
844 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__PRE_RWLOCK_RDLOCK,
845 rwlock, 0, 0, 0, 0);
846 CALL_FN_W_W(ret, fn, rwlock);
847 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_RWLOCK_RDLOCK,
848 rwlock, ret == 0, 0, 0, 0);
849 return ret;
bart00344642008-03-01 15:27:41 +0000850}
851
852// pthread_rwlock_timedwrlock
853PTH_FUNC(int,
854 pthreadZurwlockZutimedwrlockZa, // pthread_rwlock_timedwrlock*
855 pthread_rwlock_t* rwlock)
856{
bart3772a982008-03-15 08:11:03 +0000857 int ret;
858 int res;
859 OrigFn fn;
860 VALGRIND_GET_ORIG_FN(fn);
861 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__PRE_RWLOCK_WRLOCK,
862 rwlock, 0, 0, 0, 0);
863 CALL_FN_W_W(ret, fn, rwlock);
864 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_RWLOCK_WRLOCK,
865 rwlock, ret == 0, 0, 0, 0);
866 return ret;
bart00344642008-03-01 15:27:41 +0000867}
868
869// pthread_rwlock_tryrdlock
870PTH_FUNC(int,
871 pthreadZurwlockZutryrdlockZa, // pthread_rwlock_tryrdlock*
872 pthread_rwlock_t* rwlock)
873{
bart3772a982008-03-15 08:11:03 +0000874 int ret;
875 int res;
876 OrigFn fn;
877 VALGRIND_GET_ORIG_FN(fn);
878 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__PRE_RWLOCK_RDLOCK,
879 rwlock, 0, 0, 0, 0);
880 CALL_FN_W_W(ret, fn, rwlock);
881 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_RWLOCK_RDLOCK,
882 rwlock, ret == 0, 0, 0, 0);
883 return ret;
bart00344642008-03-01 15:27:41 +0000884}
885
886// pthread_rwlock_trywrlock
887PTH_FUNC(int,
888 pthreadZurwlockZutrywrlockZa, // pthread_rwlock_trywrlock*
889 pthread_rwlock_t* rwlock)
890{
bart3772a982008-03-15 08:11:03 +0000891 int ret;
892 int res;
893 OrigFn fn;
894 VALGRIND_GET_ORIG_FN(fn);
895 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__PRE_RWLOCK_WRLOCK,
896 rwlock, 0, 0, 0, 0);
897 CALL_FN_W_W(ret, fn, rwlock);
898 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_RWLOCK_WRLOCK,
899 rwlock, ret == 0, 0, 0, 0);
900 return ret;
bart00344642008-03-01 15:27:41 +0000901}
902
903// pthread_rwlock_unlock
904PTH_FUNC(int,
905 pthreadZurwlockZuunlockZa, // pthread_rwlock_unlock*
906 pthread_rwlock_t* rwlock)
907{
bart3772a982008-03-15 08:11:03 +0000908 int ret;
909 int res;
910 OrigFn fn;
911 VALGRIND_GET_ORIG_FN(fn);
912 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__PRE_RWLOCK_UNLOCK,
913 rwlock, 0, 0, 0, 0);
914 CALL_FN_W_W(ret, fn, rwlock);
915 VALGRIND_DO_CLIENT_REQUEST(res, -1, VG_USERREQ__POST_RWLOCK_UNLOCK,
916 rwlock, ret == 0, 0, 0, 0);
917 return ret;
bart00344642008-03-01 15:27:41 +0000918}