summaryrefslogtreecommitdiff
path: root/tests
diff options
context:
space:
mode:
authorIvan Maidanski <ivmai@mail.ru>2022-01-15 00:23:08 +0300
committerIvan Maidanski <ivmai@mail.ru>2022-02-22 12:18:34 +0300
commitbc01dc390e3e0d8ade52f8cd97992a2f8d5314d7 (patch)
tree6f2246865c8d0c91b643f2ee8eaf96456d8622a8 /tests
parentcb54e978347243af964b8b6f3a97f19b02f8904a (diff)
downloadbdwgc-bc01dc390e3e0d8ade52f8cd97992a2f8d5314d7.tar.gz
Workaround crash in FreeBSD rand() by avoiding its concurrent usage
(a cherry-pick of commit 84d42b8c5 from 'release-8_2') Issue #414 (bdwgc). The standard specifies rand() as not a thread-safe API function. Thus, the concurrent usage of libc rand() should be avoided. Redefine the standard rand() in disclaim_[weakmap_]test with a trivial (yet sufficient for the test purpose) implementation to avoid crashes inside rand() on some targets (e.g. FreeBSD 13.0). * tests/disclaim_test.c [LINT2] (GC_API_PRIV): Do not define. * tests/disclaim_weakmap_test.c [LINT2] (GC_API_PRIV): Likewise. * tests/disclaim_test.c [LINT2] (GC_random): Do not declare. * tests/disclaim_weakmap_test.c [LINT2] (GC_random): Likewise. * tests/disclaim_test.c [GC_PTHREADS || LINT2]: Include gc_priv.h. * tests/disclaim_test.c [GC_PTHREADS || LINT2] (GC_rand): New static function. * tests/disclaim_weakmap_test.c [GC_PTHREADS || LINT2] (GC_rand): Likewise. * tests/disclaim_test.c [GC_PTHREADS || LINT2] (rand): Define to GC_rand() (instead of (int)GC_random()); add comment. * tests/disclaim_weakmap_test.c [GC_PTHREADS || LINT2] (rand): Likewise. * tests/disclaim_weakmap_test.c [GC_PTHREADS || LINT2]: Include gc_priv.h before gc_mark.h; add comment.
Diffstat (limited to 'tests')
-rw-r--r--tests/disclaim_test.c32
-rw-r--r--tests/disclaim_weakmap_test.c35
2 files changed, 36 insertions, 31 deletions
diff --git a/tests/disclaim_test.c b/tests/disclaim_test.c
index 6af62f64..86e864df 100644
--- a/tests/disclaim_test.c
+++ b/tests/disclaim_test.c
@@ -28,21 +28,25 @@
#undef GC_NO_THREAD_REDIRECTS
#include "gc_disclaim.h"
-#ifdef LINT2
- /* Avoid include gc_priv.h. */
-# ifndef GC_API_PRIV
-# define GC_API_PRIV GC_API
-# endif
-# ifdef __cplusplus
- extern "C" {
-# endif
- GC_API_PRIV long GC_random(void);
-# ifdef __cplusplus
- } /* extern "C" */
-# endif
+#if defined(GC_PTHREADS) || defined(LINT2)
+# include "private/gc_priv.h"
+
+ GC_ATTR_NO_SANITIZE_THREAD
+ static int GC_rand(void) /* nearly identical to GC_random */
+ {
+ static unsigned seed; /* concurrent update does not hurt the test */
+
+ seed = (seed * 1103515245U + 12345) & (~0U >> 1);
+ return (int)seed;
+ }
+
+ /* Redefine the standard rand() with a trivial (yet sufficient for */
+ /* the test purpose) implementation to avoid crashes inside rand() */
+ /* on some targets (e.g. FreeBSD 13.0) when used concurrently. */
+ /* The standard specifies rand() as not a thread-safe API function. */
# undef rand
-# define rand() (int)GC_random()
-#endif /* LINT2 */
+# define rand() GC_rand()
+#endif /* GC_PTHREADS || LINT2 */
#define my_assert(e) \
if (!(e)) { \
diff --git a/tests/disclaim_weakmap_test.c b/tests/disclaim_weakmap_test.c
index 516a3fd7..fd811fef 100644
--- a/tests/disclaim_weakmap_test.c
+++ b/tests/disclaim_weakmap_test.c
@@ -24,7 +24,24 @@
#endif
#include "gc_disclaim.h" /* includes gc.h */
-#include "gc_mark.h"
+
+#if defined(GC_PTHREADS) || defined(LINT2)
+# include "private/gc_priv.h"
+
+ GC_ATTR_NO_SANITIZE_THREAD
+ static int GC_rand(void) /* same as in disclaim_test.c */
+ {
+ static unsigned seed; /* concurrent update does not hurt the test */
+
+ seed = (seed * 1103515245U + 12345) & (~0U >> 1);
+ return (int)seed;
+ }
+
+# undef rand
+# define rand() GC_rand()
+#endif /* GC_PTHREADS || LINT2 */
+
+#include "gc_mark.h" /* should not precede include gc_priv.h */
#ifdef GC_PTHREADS
# ifndef NTHREADS
@@ -39,22 +56,6 @@
# define AO_t GC_word
#endif
-#ifdef LINT2
- /* Avoid include gc_priv.h. */
-# ifndef GC_API_PRIV
-# define GC_API_PRIV GC_API
-# endif
-# ifdef __cplusplus
- extern "C" {
-# endif
- GC_API_PRIV long GC_random(void);
-# ifdef __cplusplus
- } /* extern "C" */
-# endif
-# undef rand
-# define rand() (int)GC_random()
-#endif /* LINT2 */
-
#define POP_SIZE 200
#define MUTATE_CNT (5000000 / NTHREADS)
#define GROW_LIMIT (MUTATE_CNT / 10)