forked from OSchip/llvm-project
[sanitizer] Implement include= option.
Allows loading sanitizer options from file. llvm-svn: 226175
This commit is contained in:
parent
13be264db2
commit
bc14dd46f2
|
@ -71,10 +71,7 @@ void FlagParser::parse_flag() {
|
|||
InternalFree((void *)value);
|
||||
}
|
||||
|
||||
void FlagParser::ParseString(const char *s) {
|
||||
if (!s) return;
|
||||
buf_ = s;
|
||||
pos_ = 0;
|
||||
void FlagParser::parse_flags() {
|
||||
while (true) {
|
||||
skip_whitespace();
|
||||
if (buf_[pos_] == 0) break;
|
||||
|
@ -86,6 +83,20 @@ void FlagParser::ParseString(const char *s) {
|
|||
common_flags_dont_use.malloc_context_size = 1;
|
||||
}
|
||||
|
||||
void FlagParser::ParseString(const char *s) {
|
||||
if (!s) return;
|
||||
// Backup current parser state to allow nested ParseString() calls.
|
||||
const char *old_buf_ = buf_;
|
||||
uptr old_pos_ = pos_;
|
||||
buf_ = s;
|
||||
pos_ = 0;
|
||||
|
||||
parse_flags();
|
||||
|
||||
buf_ = old_buf_;
|
||||
pos_ = old_pos_;
|
||||
}
|
||||
|
||||
bool FlagParser::run_handler(const char *name, const char *value) {
|
||||
for (int i = 0; i < n_flags_; ++i) {
|
||||
if (internal_strcmp(name, flags_[i].name) == 0)
|
||||
|
|
|
@ -101,6 +101,7 @@ class FlagParser {
|
|||
void fatal_error(const char *err);
|
||||
bool is_space(char c);
|
||||
void skip_whitespace();
|
||||
void parse_flags();
|
||||
void parse_flag();
|
||||
bool run_handler(const char *name, const char *value);
|
||||
};
|
||||
|
|
|
@ -45,11 +45,37 @@ void CommonFlags::CopyFrom(const CommonFlags &other) {
|
|||
internal_memcpy(this, &other, sizeof(*this));
|
||||
}
|
||||
|
||||
class FlagHandlerInclude : public FlagHandlerBase {
|
||||
static const uptr kMaxIncludeSize = 1 << 15;
|
||||
FlagParser *parser_;
|
||||
|
||||
public:
|
||||
explicit FlagHandlerInclude(FlagParser *parser) : parser_(parser) {}
|
||||
bool Parse(const char *value) {
|
||||
char *data;
|
||||
uptr data_mapped_size;
|
||||
uptr len =
|
||||
ReadFileToBuffer(value, &data, &data_mapped_size, kMaxIncludeSize);
|
||||
if (!len) {
|
||||
Printf("Failed to read options from '%s'\n", value);
|
||||
return false;
|
||||
}
|
||||
parser_->ParseString(data);
|
||||
UnmapOrDie(data, data_mapped_size);
|
||||
return true;
|
||||
}
|
||||
};
|
||||
|
||||
void RegisterCommonFlags(FlagParser *parser, CommonFlags *cf) {
|
||||
#define COMMON_FLAG(Type, Name, DefaultValue, Description) \
|
||||
RegisterFlag(parser, #Name, Description, &cf->Name);
|
||||
#include "sanitizer_flags.inc"
|
||||
#undef COMMON_FLAG
|
||||
|
||||
FlagHandlerInclude *fh_include =
|
||||
new (INTERNAL_ALLOC) FlagHandlerInclude(parser); // NOLINT
|
||||
parser->RegisterHandler("include", fh_include,
|
||||
"read more options from the given file");
|
||||
}
|
||||
|
||||
} // namespace __sanitizer
|
||||
|
|
|
@ -0,0 +1,16 @@
|
|||
// RUN: %clangxx_asan -O0 %s -o %t
|
||||
// RUN: echo "symbolize=1\ninclude='%t.options2.txt'" > %t.options1.txt
|
||||
// RUN: echo "verbosity=1" > %t.options2.txt
|
||||
// RUN: ASAN_OPTIONS="verbosity=0:include='%t.options2.txt'" %run %t 2>&1 | FileCheck %s --check-prefix=CHECK-VERBOSITY1
|
||||
// RUN: ASAN_OPTIONS="include='%t.options2.txt',verbosity=0" %run %t 2>&1 | FileCheck %s --check-prefix=CHECK-VERBOSITY0
|
||||
// RUN: ASAN_OPTIONS="include='%t.options-not-found.txt',verbosity=0" not %run %t 2>&1 | FileCheck %s --check-prefix=CHECK-NOT-FOUND
|
||||
|
||||
#include <stdio.h>
|
||||
|
||||
int main() {
|
||||
fprintf(stderr, "done\n");
|
||||
}
|
||||
|
||||
// CHECK-VERBOSITY1: Parsed ASAN_OPTIONS:
|
||||
// CHECK-VERBOSITY0-NOT: Parsed ASAN_OPTIONS:
|
||||
// CHECK-NOT-FOUND: Failed to read options from
|
Loading…
Reference in New Issue