1//===-- tsan_flags_test.cc ------------------------------------------------===//
2//
3//                     The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9//
10// This file is a part of ThreadSanitizer (TSan), a race detector.
11//
12//===----------------------------------------------------------------------===//
13#include "tsan_flags.h"
14#include "tsan_rtl.h"
15#include "gtest/gtest.h"
16#include <string>
17
18namespace __tsan {
19
20TEST(Flags, Basic) {
21  // At least should not crash.
22  Flags f;
23  InitializeFlags(&f, 0);
24  InitializeFlags(&f, "");
25}
26
27TEST(Flags, DefaultValues) {
28  Flags f;
29
30  f.enable_annotations = false;
31  f.exitcode = -11;
32  InitializeFlags(&f, "");
33  EXPECT_EQ(66, f.exitcode);
34  EXPECT_EQ(true, f.enable_annotations);
35}
36
37static const char *options1 =
38  " enable_annotations=0"
39  " suppress_equal_stacks=0"
40  " suppress_equal_addresses=0"
41  " suppress_java=0"
42  " report_bugs=0"
43  " report_thread_leaks=0"
44  " report_destroy_locked=0"
45  " report_mutex_bugs=0"
46  " report_signal_unsafe=0"
47  " report_atomic_races=0"
48  " force_seq_cst_atomics=0"
49  " suppressions=qwerty"
50  " print_suppressions=0"
51  " print_benign=0"
52  " exitcode=111"
53  " halt_on_error=0"
54  " atexit_sleep_ms=222"
55  " profile_memory=qqq"
56  " flush_memory_ms=444"
57  " flush_symbolizer_ms=555"
58  " memory_limit_mb=666"
59  " stop_on_start=0"
60  " running_on_valgrind=0"
61  " history_size=5"
62  " io_sync=1"
63  " die_after_fork=true"
64
65  " symbolize=0"
66  " external_symbolizer_path=asdfgh"
67  " allow_addr2line=true"
68  " strip_path_prefix=zxcvb"
69  " fast_unwind_on_fatal=0"
70  " fast_unwind_on_malloc=0"
71  " handle_ioctl=0"
72  " malloc_context_size=777"
73  " log_path=aaa"
74  " verbosity=2"
75  " detect_leaks=0"
76  " leak_check_at_exit=0"
77  " allocator_may_return_null=0"
78  " print_summary=0"
79  " legacy_pthread_cond=0"
80  "";
81
82static const char *options2 =
83  " enable_annotations=true"
84  " suppress_equal_stacks=true"
85  " suppress_equal_addresses=true"
86  " suppress_java=true"
87  " report_bugs=true"
88  " report_thread_leaks=true"
89  " report_destroy_locked=true"
90  " report_mutex_bugs=true"
91  " report_signal_unsafe=true"
92  " report_atomic_races=true"
93  " force_seq_cst_atomics=true"
94  " suppressions=aaaaa"
95  " print_suppressions=true"
96  " print_benign=true"
97  " exitcode=222"
98  " halt_on_error=true"
99  " atexit_sleep_ms=123"
100  " profile_memory=bbbbb"
101  " flush_memory_ms=234"
102  " flush_symbolizer_ms=345"
103  " memory_limit_mb=456"
104  " stop_on_start=true"
105  " running_on_valgrind=true"
106  " history_size=6"
107  " io_sync=2"
108  " die_after_fork=false"
109
110  " symbolize=true"
111  " external_symbolizer_path=cccccc"
112  " allow_addr2line=false"
113  " strip_path_prefix=ddddddd"
114  " fast_unwind_on_fatal=true"
115  " fast_unwind_on_malloc=true"
116  " handle_ioctl=true"
117  " malloc_context_size=567"
118  " log_path=eeeeeee"
119  " verbosity=0"
120  " detect_leaks=true"
121  " leak_check_at_exit=true"
122  " allocator_may_return_null=true"
123  " print_summary=true"
124  " legacy_pthread_cond=true"
125  "";
126
127void VerifyOptions1(Flags *f) {
128  EXPECT_EQ(f->enable_annotations, 0);
129  EXPECT_EQ(f->suppress_equal_stacks, 0);
130  EXPECT_EQ(f->suppress_equal_addresses, 0);
131  EXPECT_EQ(f->suppress_java, 0);
132  EXPECT_EQ(f->report_bugs, 0);
133  EXPECT_EQ(f->report_thread_leaks, 0);
134  EXPECT_EQ(f->report_destroy_locked, 0);
135  EXPECT_EQ(f->report_mutex_bugs, 0);
136  EXPECT_EQ(f->report_signal_unsafe, 0);
137  EXPECT_EQ(f->report_atomic_races, 0);
138  EXPECT_EQ(f->force_seq_cst_atomics, 0);
139  EXPECT_EQ(f->suppressions, std::string("qwerty"));
140  EXPECT_EQ(f->print_suppressions, 0);
141  EXPECT_EQ(f->print_benign, 0);
142  EXPECT_EQ(f->exitcode, 111);
143  EXPECT_EQ(f->halt_on_error, 0);
144  EXPECT_EQ(f->atexit_sleep_ms, 222);
145  EXPECT_EQ(f->profile_memory, std::string("qqq"));
146  EXPECT_EQ(f->flush_memory_ms, 444);
147  EXPECT_EQ(f->flush_symbolizer_ms, 555);
148  EXPECT_EQ(f->memory_limit_mb, 666);
149  EXPECT_EQ(f->stop_on_start, 0);
150  EXPECT_EQ(f->running_on_valgrind, 0);
151  EXPECT_EQ(f->history_size, 5);
152  EXPECT_EQ(f->io_sync, 1);
153  EXPECT_EQ(f->die_after_fork, true);
154
155  EXPECT_EQ(f->symbolize, 0);
156  EXPECT_EQ(f->external_symbolizer_path, std::string("asdfgh"));
157  EXPECT_EQ(f->allow_addr2line, true);
158  EXPECT_EQ(f->strip_path_prefix, std::string("zxcvb"));
159  EXPECT_EQ(f->fast_unwind_on_fatal, 0);
160  EXPECT_EQ(f->fast_unwind_on_malloc, 0);
161  EXPECT_EQ(f->handle_ioctl, 0);
162  EXPECT_EQ(f->malloc_context_size, 777);
163  EXPECT_EQ(f->log_path, std::string("aaa"));
164  EXPECT_EQ(f->verbosity, 2);
165  EXPECT_EQ(f->detect_leaks, 0);
166  EXPECT_EQ(f->leak_check_at_exit, 0);
167  EXPECT_EQ(f->allocator_may_return_null, 0);
168  EXPECT_EQ(f->print_summary, 0);
169  EXPECT_EQ(f->legacy_pthread_cond, false);
170}
171
172void VerifyOptions2(Flags *f) {
173  EXPECT_EQ(f->enable_annotations, true);
174  EXPECT_EQ(f->suppress_equal_stacks, true);
175  EXPECT_EQ(f->suppress_equal_addresses, true);
176  EXPECT_EQ(f->suppress_java, true);
177  EXPECT_EQ(f->report_bugs, true);
178  EXPECT_EQ(f->report_thread_leaks, true);
179  EXPECT_EQ(f->report_destroy_locked, true);
180  EXPECT_EQ(f->report_mutex_bugs, true);
181  EXPECT_EQ(f->report_signal_unsafe, true);
182  EXPECT_EQ(f->report_atomic_races, true);
183  EXPECT_EQ(f->force_seq_cst_atomics, true);
184  EXPECT_EQ(f->suppressions, std::string("aaaaa"));
185  EXPECT_EQ(f->print_suppressions, true);
186  EXPECT_EQ(f->print_benign, true);
187  EXPECT_EQ(f->exitcode, 222);
188  EXPECT_EQ(f->halt_on_error, true);
189  EXPECT_EQ(f->atexit_sleep_ms, 123);
190  EXPECT_EQ(f->profile_memory, std::string("bbbbb"));
191  EXPECT_EQ(f->flush_memory_ms, 234);
192  EXPECT_EQ(f->flush_symbolizer_ms, 345);
193  EXPECT_EQ(f->memory_limit_mb, 456);
194  EXPECT_EQ(f->stop_on_start, true);
195  EXPECT_EQ(f->running_on_valgrind, true);
196  EXPECT_EQ(f->history_size, 6);
197  EXPECT_EQ(f->io_sync, 2);
198  EXPECT_EQ(f->die_after_fork, false);
199
200  EXPECT_EQ(f->symbolize, true);
201  EXPECT_EQ(f->external_symbolizer_path, std::string("cccccc"));
202  EXPECT_EQ(f->allow_addr2line, false);
203  EXPECT_EQ(f->strip_path_prefix, std::string("ddddddd"));
204  EXPECT_EQ(f->fast_unwind_on_fatal, true);
205  EXPECT_EQ(f->fast_unwind_on_malloc, true);
206  EXPECT_EQ(f->handle_ioctl, true);
207  EXPECT_EQ(f->malloc_context_size, 567);
208  EXPECT_EQ(f->log_path, std::string("eeeeeee"));
209  EXPECT_EQ(f->verbosity, 0);
210  EXPECT_EQ(f->detect_leaks, true);
211  EXPECT_EQ(f->leak_check_at_exit, true);
212  EXPECT_EQ(f->allocator_may_return_null, true);
213  EXPECT_EQ(f->print_summary, true);
214  EXPECT_EQ(f->legacy_pthread_cond, true);
215}
216
217static const char *test_default_options;
218extern "C" const char *__tsan_default_options() {
219  return test_default_options;
220}
221
222TEST(Flags, ParseDefaultOptions) {
223  Flags f;
224
225  test_default_options = options1;
226  InitializeFlags(&f, "");
227  VerifyOptions1(&f);
228
229  test_default_options = options2;
230  InitializeFlags(&f, "");
231  VerifyOptions2(&f);
232}
233
234TEST(Flags, ParseEnvOptions) {
235  Flags f;
236
237  InitializeFlags(&f, options1);
238  VerifyOptions1(&f);
239
240  InitializeFlags(&f, options2);
241  VerifyOptions2(&f);
242}
243
244TEST(Flags, ParsePriority) {
245  Flags f;
246
247  test_default_options = options2;
248  InitializeFlags(&f, options1);
249  VerifyOptions1(&f);
250
251  test_default_options = options1;
252  InitializeFlags(&f, options2);
253  VerifyOptions2(&f);
254}
255
256}  // namespace __tsan
257