diff options
5 files changed, 35 insertions, 23 deletions
diff --git a/compiler-rt/lib/sanitizer_common/sanitizer_coverage_libcdep.cc b/compiler-rt/lib/sanitizer_common/sanitizer_coverage_libcdep.cc index 64861d0441a..e1fa05d5015 100644 --- a/compiler-rt/lib/sanitizer_common/sanitizer_coverage_libcdep.cc +++ b/compiler-rt/lib/sanitizer_common/sanitizer_coverage_libcdep.cc @@ -91,9 +91,9 @@ class CoverageData { static CoverageData coverage_data; void CoverageData::DirectInit() { - InternalScopedString path(64); - internal_snprintf((char *)path.data(), path.size(), "%zd.sancov.raw", - internal_getpid()); + InternalScopedString path(1024); + internal_snprintf((char *)path.data(), path.size(), "%s/%zd.sancov.raw", + common_flags()->coverage_dir, internal_getpid()); pc_fd = OpenFile(path.data(), true); if (internal_iserror(pc_fd)) { Report(" Coverage: failed to open %s for writing\n", path.data()); @@ -221,15 +221,17 @@ static int CovOpenFile(bool packed, const char* name) { InternalScopedBuffer<char> path(1024); if (!packed) { CHECK(name); - internal_snprintf((char *)path.data(), path.size(), "%s.%zd.sancov", - name, internal_getpid()); + Printf("%s\n", common_flags()->coverage_dir); + internal_snprintf((char *)path.data(), path.size(), "%s/%s.%zd.sancov", + common_flags()->coverage_dir, name, internal_getpid()); } else { if (!name) - internal_snprintf((char *)path.data(), path.size(), "%zd.sancov.packed", + internal_snprintf((char *)path.data(), path.size(), + "%s/%zd.sancov.packed", common_flags()->coverage_dir, internal_getpid()); else - internal_snprintf((char *)path.data(), path.size(), "%s.sancov.packed", - name); + internal_snprintf((char *)path.data(), path.size(), "%s/%s.sancov.packed", + common_flags()->coverage_dir, name); } uptr fd = OpenFile(path.data(), true); if (internal_iserror(fd)) { @@ -279,8 +281,9 @@ static void CovDump() { } } else { // One file per module per process. - internal_snprintf((char *)path.data(), path.size(), "%s.%zd.sancov", - module_name, internal_getpid()); + internal_snprintf((char *)path.data(), path.size(), "%s/%s.%zd.sancov", + common_flags()->coverage_dir, module_name, + internal_getpid()); int fd = CovOpenFile(false /* packed */, module_name); if (fd > 0) { internal_write(fd, offsets.data(), offsets.size() * sizeof(u32)); diff --git a/compiler-rt/lib/sanitizer_common/sanitizer_coverage_mapping_libcdep.cc b/compiler-rt/lib/sanitizer_common/sanitizer_coverage_mapping_libcdep.cc index 75f6162d185..e814c2e5e29 100644 --- a/compiler-rt/lib/sanitizer_common/sanitizer_coverage_mapping_libcdep.cc +++ b/compiler-rt/lib/sanitizer_common/sanitizer_coverage_mapping_libcdep.cc @@ -41,9 +41,12 @@ void CovUpdateMapping() { if (!common_flags()->coverage || !common_flags()->coverage_direct) return; int err; - InternalScopedString tmp_path(64); - internal_snprintf((char *)tmp_path.data(), tmp_path.size(), - "%zd.sancov.map.tmp", internal_getpid()); + InternalScopedString tmp_path(64 + + internal_strlen(common_flags()->coverage_dir)); + uptr res = internal_snprintf((char *)tmp_path.data(), tmp_path.size(), + "%s/%zd.sancov.map.tmp", common_flags()->coverage_dir, + internal_getpid()); + CHECK_LE(res, tmp_path.size()); uptr map_fd = OpenFile(tmp_path.data(), true); if (internal_iserror(map_fd)) { Report(" Coverage: failed to open %s for writing\n", tmp_path.data()); @@ -59,7 +62,7 @@ void CovUpdateMapping() { InternalScopedString line(4096); line.append("%d\n", sizeof(uptr) * 8); - uptr res = internal_write(map_fd, line.data(), line.length()); + res = internal_write(map_fd, line.data(), line.length()); if (internal_iserror(res, &err)) { Printf("sancov.map write failed: %d\n", err); Die(); @@ -84,9 +87,10 @@ void CovUpdateMapping() { internal_close(map_fd); - InternalScopedString path(64); - internal_snprintf((char *)path.data(), path.size(), "%zd.sancov.map", - internal_getpid()); + InternalScopedString path(64 + internal_strlen(common_flags()->coverage_dir)); + res = internal_snprintf((char *)path.data(), path.size(), "%s/%zd.sancov.map", + common_flags()->coverage_dir, internal_getpid()); + CHECK_LE(res, path.size()); res = internal_rename(tmp_path.data(), path.data()); if (internal_iserror(res, &err)) { Printf("sancov.map rename failed: %d\n", err); diff --git a/compiler-rt/lib/sanitizer_common/sanitizer_flags.cc b/compiler-rt/lib/sanitizer_common/sanitizer_flags.cc index 83bdb1cdabc..e8f288f62b8 100644 --- a/compiler-rt/lib/sanitizer_common/sanitizer_flags.cc +++ b/compiler-rt/lib/sanitizer_common/sanitizer_flags.cc @@ -56,6 +56,7 @@ void SetCommonFlagsDefaults(CommonFlags *f) { f->intercept_tls_get_addr = false; f->coverage = false; f->coverage_direct = false; + f->coverage_dir = "."; f->full_address_space = false; } @@ -132,6 +133,9 @@ void ParseCommonFlagsFromString(CommonFlags *f, const char *str) { "If set, coverage information will be dumped directly to a memory " "mapped file. This way data is not lost even if the process is " "suddenly killed."); + ParseFlag(str, &f->coverage_dir, "coverage_dir", + "Target directory for coverage dumps. Defaults to the current " + "directory."); ParseFlag(str, &f->full_address_space, "full_address_space", "Sanitize complete address space; " "by default kernel area on 32-bit platforms will not be sanitized"); diff --git a/compiler-rt/lib/sanitizer_common/sanitizer_flags.h b/compiler-rt/lib/sanitizer_common/sanitizer_flags.h index 1ad53dc6711..41dc2188844 100644 --- a/compiler-rt/lib/sanitizer_common/sanitizer_flags.h +++ b/compiler-rt/lib/sanitizer_common/sanitizer_flags.h @@ -55,6 +55,7 @@ struct CommonFlags { uptr mmap_limit_mb; bool coverage; bool coverage_direct; + const char *coverage_dir; bool full_address_space; }; diff --git a/compiler-rt/test/asan/TestCases/Linux/coverage-direct.cc b/compiler-rt/test/asan/TestCases/Linux/coverage-direct.cc index f6e7801cbff..7fe2514b315 100644 --- a/compiler-rt/test/asan/TestCases/Linux/coverage-direct.cc +++ b/compiler-rt/test/asan/TestCases/Linux/coverage-direct.cc @@ -4,13 +4,13 @@ // RUN: rm -rf %T/coverage-direct -// RUN: mkdir -p %T/coverage-direct/normal && cd %T/coverage-direct/normal -// RUN: ASAN_OPTIONS=coverage=1:coverage_direct=0:verbosity=1 %run %t -// RUN: %sancov print *.sancov >out.txt -// RUN: cd ../.. +// RUN: mkdir -p %T/coverage-direct/normal +// RUN: ASAN_OPTIONS=coverage=1:coverage_direct=0:coverage_dir=%T/coverage-direct/normal:verbosity=1 %run %t +// RUN: %sancov print %T/coverage-direct/normal/*.sancov >%T/coverage-direct/normal/out.txt -// RUN: mkdir -p %T/coverage-direct/direct && cd %T/coverage-direct/direct -// RUN: ASAN_OPTIONS=coverage=1:coverage_direct=1:verbosity=1 %run %t +// RUN: mkdir -p %T/coverage-direct/direct +// RUN: ASAN_OPTIONS=coverage=1:coverage_direct=1:coverage_dir=%T/coverage-direct/direct:verbosity=1 %run %t +// RUN: cd %T/coverage-direct/direct // RUN: %sancov rawunpack *.sancov.raw // RUN: %sancov print *.sancov >out.txt // RUN: cd ../.. |