annotate libsanitizer/sanitizer_common/sanitizer_flag_parser.h @ 158:494b0b89df80 default tip

...
author Shinji KONO <kono@ie.u-ryukyu.ac.jp>
date Mon, 25 May 2020 18:13:55 +0900
parents 1830386684a0
children
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
111
kono
parents:
diff changeset
1 //===-- sanitizer_flag_parser.h ---------------------------------*- C++ -*-===//
kono
parents:
diff changeset
2 //
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 111
diff changeset
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
1830386684a0 gcc-9.2.0
anatofuz
parents: 111
diff changeset
4 // See https://llvm.org/LICENSE.txt for license information.
1830386684a0 gcc-9.2.0
anatofuz
parents: 111
diff changeset
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
111
kono
parents:
diff changeset
6 //
kono
parents:
diff changeset
7 //===----------------------------------------------------------------------===//
kono
parents:
diff changeset
8 //
kono
parents:
diff changeset
9 // This file is a part of ThreadSanitizer/AddressSanitizer runtime.
kono
parents:
diff changeset
10 //
kono
parents:
diff changeset
11 //===----------------------------------------------------------------------===//
kono
parents:
diff changeset
12
kono
parents:
diff changeset
13 #ifndef SANITIZER_FLAG_REGISTRY_H
kono
parents:
diff changeset
14 #define SANITIZER_FLAG_REGISTRY_H
kono
parents:
diff changeset
15
kono
parents:
diff changeset
16 #include "sanitizer_internal_defs.h"
kono
parents:
diff changeset
17 #include "sanitizer_libc.h"
kono
parents:
diff changeset
18 #include "sanitizer_common.h"
kono
parents:
diff changeset
19
kono
parents:
diff changeset
20 namespace __sanitizer {
kono
parents:
diff changeset
21
kono
parents:
diff changeset
22 class FlagHandlerBase {
kono
parents:
diff changeset
23 public:
kono
parents:
diff changeset
24 virtual bool Parse(const char *value) { return false; }
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 111
diff changeset
25
1830386684a0 gcc-9.2.0
anatofuz
parents: 111
diff changeset
26 protected:
1830386684a0 gcc-9.2.0
anatofuz
parents: 111
diff changeset
27 ~FlagHandlerBase() {}
111
kono
parents:
diff changeset
28 };
kono
parents:
diff changeset
29
kono
parents:
diff changeset
30 template <typename T>
kono
parents:
diff changeset
31 class FlagHandler : public FlagHandlerBase {
kono
parents:
diff changeset
32 T *t_;
kono
parents:
diff changeset
33
kono
parents:
diff changeset
34 public:
kono
parents:
diff changeset
35 explicit FlagHandler(T *t) : t_(t) {}
kono
parents:
diff changeset
36 bool Parse(const char *value) final;
kono
parents:
diff changeset
37 };
kono
parents:
diff changeset
38
kono
parents:
diff changeset
39 inline bool ParseBool(const char *value, bool *b) {
kono
parents:
diff changeset
40 if (internal_strcmp(value, "0") == 0 ||
kono
parents:
diff changeset
41 internal_strcmp(value, "no") == 0 ||
kono
parents:
diff changeset
42 internal_strcmp(value, "false") == 0) {
kono
parents:
diff changeset
43 *b = false;
kono
parents:
diff changeset
44 return true;
kono
parents:
diff changeset
45 }
kono
parents:
diff changeset
46 if (internal_strcmp(value, "1") == 0 ||
kono
parents:
diff changeset
47 internal_strcmp(value, "yes") == 0 ||
kono
parents:
diff changeset
48 internal_strcmp(value, "true") == 0) {
kono
parents:
diff changeset
49 *b = true;
kono
parents:
diff changeset
50 return true;
kono
parents:
diff changeset
51 }
kono
parents:
diff changeset
52 return false;
kono
parents:
diff changeset
53 }
kono
parents:
diff changeset
54
kono
parents:
diff changeset
55 template <>
kono
parents:
diff changeset
56 inline bool FlagHandler<bool>::Parse(const char *value) {
kono
parents:
diff changeset
57 if (ParseBool(value, t_)) return true;
kono
parents:
diff changeset
58 Printf("ERROR: Invalid value for bool option: '%s'\n", value);
kono
parents:
diff changeset
59 return false;
kono
parents:
diff changeset
60 }
kono
parents:
diff changeset
61
kono
parents:
diff changeset
62 template <>
kono
parents:
diff changeset
63 inline bool FlagHandler<HandleSignalMode>::Parse(const char *value) {
kono
parents:
diff changeset
64 bool b;
kono
parents:
diff changeset
65 if (ParseBool(value, &b)) {
kono
parents:
diff changeset
66 *t_ = b ? kHandleSignalYes : kHandleSignalNo;
kono
parents:
diff changeset
67 return true;
kono
parents:
diff changeset
68 }
kono
parents:
diff changeset
69 if (internal_strcmp(value, "2") == 0 ||
kono
parents:
diff changeset
70 internal_strcmp(value, "exclusive") == 0) {
kono
parents:
diff changeset
71 *t_ = kHandleSignalExclusive;
kono
parents:
diff changeset
72 return true;
kono
parents:
diff changeset
73 }
kono
parents:
diff changeset
74 Printf("ERROR: Invalid value for signal handler option: '%s'\n", value);
kono
parents:
diff changeset
75 return false;
kono
parents:
diff changeset
76 }
kono
parents:
diff changeset
77
kono
parents:
diff changeset
78 template <>
kono
parents:
diff changeset
79 inline bool FlagHandler<const char *>::Parse(const char *value) {
kono
parents:
diff changeset
80 *t_ = value;
kono
parents:
diff changeset
81 return true;
kono
parents:
diff changeset
82 }
kono
parents:
diff changeset
83
kono
parents:
diff changeset
84 template <>
kono
parents:
diff changeset
85 inline bool FlagHandler<int>::Parse(const char *value) {
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 111
diff changeset
86 const char *value_end;
111
kono
parents:
diff changeset
87 *t_ = internal_simple_strtoll(value, &value_end, 10);
kono
parents:
diff changeset
88 bool ok = *value_end == 0;
kono
parents:
diff changeset
89 if (!ok) Printf("ERROR: Invalid value for int option: '%s'\n", value);
kono
parents:
diff changeset
90 return ok;
kono
parents:
diff changeset
91 }
kono
parents:
diff changeset
92
kono
parents:
diff changeset
93 template <>
kono
parents:
diff changeset
94 inline bool FlagHandler<uptr>::Parse(const char *value) {
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 111
diff changeset
95 const char *value_end;
111
kono
parents:
diff changeset
96 *t_ = internal_simple_strtoll(value, &value_end, 10);
kono
parents:
diff changeset
97 bool ok = *value_end == 0;
kono
parents:
diff changeset
98 if (!ok) Printf("ERROR: Invalid value for uptr option: '%s'\n", value);
kono
parents:
diff changeset
99 return ok;
kono
parents:
diff changeset
100 }
kono
parents:
diff changeset
101
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 111
diff changeset
102 template <>
1830386684a0 gcc-9.2.0
anatofuz
parents: 111
diff changeset
103 inline bool FlagHandler<s64>::Parse(const char *value) {
1830386684a0 gcc-9.2.0
anatofuz
parents: 111
diff changeset
104 const char *value_end;
1830386684a0 gcc-9.2.0
anatofuz
parents: 111
diff changeset
105 *t_ = internal_simple_strtoll(value, &value_end, 10);
1830386684a0 gcc-9.2.0
anatofuz
parents: 111
diff changeset
106 bool ok = *value_end == 0;
1830386684a0 gcc-9.2.0
anatofuz
parents: 111
diff changeset
107 if (!ok) Printf("ERROR: Invalid value for s64 option: '%s'\n", value);
1830386684a0 gcc-9.2.0
anatofuz
parents: 111
diff changeset
108 return ok;
1830386684a0 gcc-9.2.0
anatofuz
parents: 111
diff changeset
109 }
1830386684a0 gcc-9.2.0
anatofuz
parents: 111
diff changeset
110
111
kono
parents:
diff changeset
111 class FlagParser {
kono
parents:
diff changeset
112 static const int kMaxFlags = 200;
kono
parents:
diff changeset
113 struct Flag {
kono
parents:
diff changeset
114 const char *name;
kono
parents:
diff changeset
115 const char *desc;
kono
parents:
diff changeset
116 FlagHandlerBase *handler;
kono
parents:
diff changeset
117 } *flags_;
kono
parents:
diff changeset
118 int n_flags_;
kono
parents:
diff changeset
119
kono
parents:
diff changeset
120 const char *buf_;
kono
parents:
diff changeset
121 uptr pos_;
kono
parents:
diff changeset
122
kono
parents:
diff changeset
123 public:
kono
parents:
diff changeset
124 FlagParser();
kono
parents:
diff changeset
125 void RegisterHandler(const char *name, FlagHandlerBase *handler,
kono
parents:
diff changeset
126 const char *desc);
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 111
diff changeset
127 void ParseString(const char *s, const char *env_name = 0);
1830386684a0 gcc-9.2.0
anatofuz
parents: 111
diff changeset
128 void ParseStringFromEnv(const char *env_name);
111
kono
parents:
diff changeset
129 bool ParseFile(const char *path, bool ignore_missing);
kono
parents:
diff changeset
130 void PrintFlagDescriptions();
kono
parents:
diff changeset
131
kono
parents:
diff changeset
132 static LowLevelAllocator Alloc;
kono
parents:
diff changeset
133
kono
parents:
diff changeset
134 private:
kono
parents:
diff changeset
135 void fatal_error(const char *err);
kono
parents:
diff changeset
136 bool is_space(char c);
kono
parents:
diff changeset
137 void skip_whitespace();
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 111
diff changeset
138 void parse_flags(const char *env_option_name);
1830386684a0 gcc-9.2.0
anatofuz
parents: 111
diff changeset
139 void parse_flag(const char *env_option_name);
111
kono
parents:
diff changeset
140 bool run_handler(const char *name, const char *value);
kono
parents:
diff changeset
141 char *ll_strndup(const char *s, uptr n);
kono
parents:
diff changeset
142 };
kono
parents:
diff changeset
143
kono
parents:
diff changeset
144 template <typename T>
kono
parents:
diff changeset
145 static void RegisterFlag(FlagParser *parser, const char *name, const char *desc,
kono
parents:
diff changeset
146 T *var) {
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 111
diff changeset
147 FlagHandler<T> *fh = new (FlagParser::Alloc) FlagHandler<T>(var);
111
kono
parents:
diff changeset
148 parser->RegisterHandler(name, fh, desc);
kono
parents:
diff changeset
149 }
kono
parents:
diff changeset
150
kono
parents:
diff changeset
151 void ReportUnrecognizedFlags();
kono
parents:
diff changeset
152
kono
parents:
diff changeset
153 } // namespace __sanitizer
kono
parents:
diff changeset
154
kono
parents:
diff changeset
155 #endif // SANITIZER_FLAG_REGISTRY_H