1 // Test __sanitizer_reset_coverage(). 2 3 // RUN: %clangxx_asan -fsanitize-coverage=func %s -o %t 4 // RUN: %env_asan_opts=coverage=1 %run %t 5 6 // https://github.com/google/sanitizers/issues/618 7 // UNSUPPORTED: android 8 9 #include <sanitizer/coverage_interface.h> 10 #include <stdio.h> 11 #include <assert.h> 12 static volatile int sink; bar()13__attribute__((noinline)) void bar() { sink = 2; } foo()14__attribute__((noinline)) void foo() { sink = 1; } 15 16 // In MSVC 2015, printf is an inline function, which causes this test to fail as 17 // it introduces an extra coverage point. Define away printf on that platform to 18 // avoid the issue. 19 #if _MSC_VER >= 1900 20 # define printf(arg, ...) 21 #endif 22 23 #define GET_AND_PRINT_COVERAGE() \ 24 bitset = 0; \ 25 for (size_t i = 0; i < n_guards; i++) \ 26 if (guards[i]) bitset |= 1U << i; \ 27 printf("line %d: bitset %zd total: %zd\n", __LINE__, bitset, \ 28 __sanitizer_get_total_unique_coverage()); 29 30 #define IS_POWER_OF_TWO(a) ((a & ((a) - 1)) == 0) 31 main()32int main() { 33 size_t *guards = 0; 34 size_t bitset; 35 size_t n_guards = __sanitizer_get_coverage_guards(&guards); 36 37 GET_AND_PRINT_COVERAGE(); 38 size_t main_bit = bitset; 39 assert(IS_POWER_OF_TWO(main_bit)); 40 41 foo(); 42 GET_AND_PRINT_COVERAGE(); 43 size_t foo_bit = bitset & ~main_bit; 44 assert(IS_POWER_OF_TWO(foo_bit)); 45 46 bar(); 47 GET_AND_PRINT_COVERAGE(); 48 size_t bar_bit = bitset & ~(main_bit | foo_bit); 49 assert(IS_POWER_OF_TWO(bar_bit)); 50 51 __sanitizer_reset_coverage(); 52 assert(__sanitizer_get_total_unique_coverage() == 0); 53 GET_AND_PRINT_COVERAGE(); 54 assert(bitset == 0); 55 56 foo(); 57 GET_AND_PRINT_COVERAGE(); 58 assert(bitset == foo_bit); 59 60 bar(); 61 GET_AND_PRINT_COVERAGE(); 62 assert(bitset == (foo_bit | bar_bit)); 63 } 64