[sancov] introducing SANCOV_OPTIONS

Reintroducing https://reviews.llvm.org/rL291068
Define options function everywhere but linux.

llvm-svn: 291267
This commit is contained in:
Mike Aizatsky 2017-01-06 19:22:50 +00:00
parent 258b847c4f
commit fb96e04efb
6 changed files with 169 additions and 4 deletions

View File

@ -52,6 +52,7 @@ set(SANITIZER_NOLIBC_SOURCES
set(SANITIZER_LIBCDEP_SOURCES
sanitizer_common_libcdep.cc
sancov_flags.cc
sanitizer_coverage_libcdep.cc
sanitizer_coverage_libcdep_new.cc
sanitizer_coverage_mapping_libcdep.cc

View File

@ -0,0 +1,60 @@
//===-- sancov_flags.cc -----------------------------------------*- C++ -*-===//
//
// The LLVM Compiler Infrastructure
//
// This file is distributed under the University of Illinois Open Source
// License. See LICENSE.TXT for details.
//
//===----------------------------------------------------------------------===//
//
// Sanitizer Coverage runtime flags.
//
//===----------------------------------------------------------------------===//
#include "sancov_flags.h"
#include "sanitizer_flag_parser.h"
#include "sanitizer_platform.h"
#if !SANITIZER_LINUX
// other platforms do not have weak symbols out of the box.
extern "C" const char* __sancov_default_options() { return ""; }
#endif
using namespace __sanitizer;
namespace __sancov {
SancovFlags sancov_flags_dont_use_directly; // use via flags();
void SancovFlags::SetDefaults() {
#define SANCOV_FLAG(Type, Name, DefaultValue, Description) Name = DefaultValue;
#include "sancov_flags.inc"
#undef SANCOV_FLAG
}
static void RegisterSancovFlags(FlagParser *parser, SancovFlags *f) {
#define SANCOV_FLAG(Type, Name, DefaultValue, Description) \
RegisterFlag(parser, #Name, Description, &f->Name);
#include "sancov_flags.inc"
#undef SANCOV_FLAG
}
static const char *MaybeCallSancovDefaultOptions() {
return (&__sancov_default_options) ? __sancov_default_options() : "";
}
void InitializeSancovFlags() {
SancovFlags *f = sancov_flags();
f->SetDefaults();
FlagParser parser;
RegisterSancovFlags(&parser, f);
parser.ParseString(MaybeCallSancovDefaultOptions());
parser.ParseString(GetEnv("SANCOV_OPTIONS"));
ReportUnrecognizedFlags();
if (f->help) parser.PrintFlagDescriptions();
}
} // namespace __sancov

View File

@ -0,0 +1,40 @@
//===-- sancov_flags.h ------------------------------------------*- C++ -*-===//
//
// The LLVM Compiler Infrastructure
//
// This file is distributed under the University of Illinois Open Source
// License. See LICENSE.TXT for details.
//
//===----------------------------------------------------------------------===//
//
// Sanitizer Coverage runtime flags.
//
//===----------------------------------------------------------------------===//
#ifndef SANCOV_FLAGS_H
#define SANCOV_FLAGS_H
#include "sanitizer_flag_parser.h"
#include "sanitizer_internal_defs.h"
namespace __sancov {
struct SancovFlags {
#define SANCOV_FLAG(Type, Name, DefaultValue, Description) Type Name;
#include "sancov_flags.inc"
#undef SANCOV_FLAG
void SetDefaults();
};
extern SancovFlags sancov_flags_dont_use_directly;
inline SancovFlags* sancov_flags() { return &sancov_flags_dont_use_directly; }
void InitializeSancovFlags();
extern "C" SANITIZER_INTERFACE_ATTRIBUTE SANITIZER_WEAK_ATTRIBUTE const char*
__sancov_default_options();
} // namespace __sancov
#endif

View File

@ -0,0 +1,21 @@
//===-- sancov_flags.inc ----------------------------------------*- C++ -*-===//
//
// The LLVM Compiler Infrastructure
//
// This file is distributed under the University of Illinois Open Source
// License. See LICENSE.TXT for details.
//
//===----------------------------------------------------------------------===//
//
// Sanitizer Coverage runtime flags.
//
//===----------------------------------------------------------------------===//
#ifndef SANCOV_FLAG
#error "Defnine SANCOV_FLAG prior to including this file!"
#endif
SANCOV_FLAG(bool, symbolize, true,
"If set, converage information will be symbolized by sancov tool "
"after dumping.")
SANCOV_FLAG(bool, help, false, "Print flags help.")

View File

@ -8,6 +8,7 @@
//===----------------------------------------------------------------------===//
// Sanitizer Coverage Controller for Trace PC Guard.
#include "sancov_flags.h"
#include "sanitizer_allocator_internal.h"
#include "sanitizer_atomic.h"
#include "sanitizer_common.h"
@ -17,6 +18,7 @@ using namespace __sanitizer;
using AddressRange = LoadedModule::AddressRange;
namespace __sancov {
namespace {
static const u64 Magic64 = 0xC0BFFFFFFFFFFF64ULL;
@ -96,6 +98,10 @@ static void SanitizerDumpCoverage(const uptr* unsorted_pcs, uptr len) {
InternalFree(file_path);
InternalFree(module_name);
InternalFree(pcs);
if (sancov_flags()->symbolize) {
Printf("TODO(aizatsky): call sancov to symbolize\n");
}
}
// Collects trace-pc guard coverage.
@ -106,6 +112,8 @@ class TracePcGuardController {
CHECK(!initialized);
initialized = true;
InitializeSancovFlags();
pc_vector.Initialize(0);
}
@ -140,26 +148,27 @@ class TracePcGuardController {
static TracePcGuardController pc_guard_controller;
} // namespace
} // namespace __sancov
extern "C" {
SANITIZER_INTERFACE_ATTRIBUTE void __sanitizer_dump_coverage( // NOLINT
const uptr* pcs, uptr len) {
return SanitizerDumpCoverage(pcs, len);
return __sancov::SanitizerDumpCoverage(pcs, len);
}
SANITIZER_INTERFACE_ATTRIBUTE SANITIZER_WEAK_ATTRIBUTE void
__sanitizer_cov_trace_pc_guard(u32* guard) {
if (!*guard) return;
pc_guard_controller.TracePcGuard(guard, GET_CALLER_PC() - 1);
__sancov::pc_guard_controller.TracePcGuard(guard, GET_CALLER_PC() - 1);
}
SANITIZER_INTERFACE_ATTRIBUTE SANITIZER_WEAK_ATTRIBUTE void
__sanitizer_cov_trace_pc_guard_init(u32* start, u32* end) {
if (start == end || *start) return;
pc_guard_controller.InitTracePcGuard(start, end);
__sancov::pc_guard_controller.InitTracePcGuard(start, end);
}
SANITIZER_INTERFACE_ATTRIBUTE void __sanitizer_dump_trace_pc_guard_coverage() {
pc_guard_controller.Dump();
__sancov::pc_guard_controller.Dump();
}
} // extern "C"

View File

@ -0,0 +1,34 @@
// Tests trace pc guard coverage collection.
//
// REQUIRES: x86_64-linux
// XFAIL: tsan
//
// RUN: DIR=%t_workdir
// RUN: rm -rf $DIR
// RUN: mkdir -p $DIR
// RUN: cd $DIR
// RUN: %clangxx -O0 -fsanitize-coverage=trace-pc-guard %s -ldl -o %t
// RUN: %env_tool_opts=coverage=1 %t 2>&1 | FileCheck %s
// RUN: %env_tool_opts=coverage=1 SANCOV_OPTIONS=symbolize=0 %t 2>&1 | FileCheck %s --check-prefix=CHECK-NOSYM
// RUN: rm -rf $DIR
#include <stdio.h>
int foo() {
fprintf(stderr, "foo\n");
return 1;
}
int main() {
fprintf(stderr, "main\n");
foo();
foo();
}
// CHECK: main
// CHECK: SanitizerCoverage: ./sanitizer_coverage_symbolize.{{.*}}.sancov 2 PCs written
// CHECK: call sancov
// CHECK-NOSYM: main
// CHECK-NOSYM: SanitizerCoverage: ./sanitizer_coverage_symbolize.{{.*}}.sancov 2 PCs written
// CHECK-NOSYM-NOT: call sancov