blob: 65d13a37fbe208687e4f7055689089a17441ce45 [file] [log] [blame]
Jeff Browned07e002011-02-03 17:46:23 -08001/* Test data race detection between floating point variables. */
2
3
4#include <assert.h>
5#include <stdio.h> /* printf() */
6#include <pthread.h>
7#include <unistd.h> /* sleep() */
8
9
10/* Local functions declarations. */
11
12static void* thread_func(void*);
13
14
15/* Local variables. */
16
17/* s_mutex protects s_d3. */
18static pthread_mutex_t s_mutex;
19
20static double s_d1; /* accessed before thread creation and in the created */
21 /* thread (not a race). */
22static double s_d2; /* accessed in the created thread and after the join */
23 /* (not a race). */
24static double s_d3; /* accessed simultaneously from both threads (race). */
25static int s_debug = 0;
26static int s_do_printf = 0;
27static int s_use_mutex = 0;
28
29
30/* Function definitions. */
31
32int main(int argc, char** argv)
33{
34 int optchar;
35 pthread_t threadid;
36
37 while ((optchar = getopt(argc, argv, "dmp")) != EOF)
38 {
39 switch (optchar)
40 {
41 case 'd':
42 s_debug = 1;
43 break;
44 case 'm':
45 s_use_mutex = 1;
46 break;
47 case 'p':
48 s_do_printf = 1;
49 break;
50 default:
51 assert(0);
52 }
53 }
54
55 pthread_mutex_init(&s_mutex, 0);
56
57 /*
58 * Switch to line-buffered mode, such that timing information can be
59 * obtained for each printf() call with strace.
60 */
61 setlinebuf(stdout);
62
63 if (s_debug)
64 {
65 printf("&s_d1 = %p; &s_d2 = %p; &s_d3 = %p\n", &s_d1, &s_d2, &s_d3);
66 }
67
68 s_d1 = 1;
69 s_d3 = 3;
70
71 pthread_create(&threadid, 0, thread_func, 0);
72
73 sleep(1); /* Wait until thread_func() finished. */
74
75 {
76 if (s_use_mutex) pthread_mutex_lock(&s_mutex);
77 s_d3++;
78 if (s_use_mutex) pthread_mutex_unlock(&s_mutex);
79 }
80
81 /* Wait until the thread finished. */
82 pthread_join(threadid, 0);
83 if (s_do_printf) printf("s_d2 = %g (should be 2)\n", s_d2);
84 if (s_do_printf) printf("s_d3 = %g (should be 5)\n", s_d3);
85
86 pthread_mutex_destroy(&s_mutex);
87
88 return 0;
89}
90
91static void* thread_func(void* thread_arg)
92{
93 if (s_do_printf)
94 {
95 printf("s_d1 = %g (should be 1)\n", s_d1);
96 }
97 s_d2 = 2;
98 {
99 if (s_use_mutex) pthread_mutex_lock(&s_mutex);
100 s_d3++;
101 if (s_use_mutex) pthread_mutex_unlock(&s_mutex);
102 }
103 return 0;
104}