trace2: use system/global config for default trace2 settings

Teach git to read the system and global config files for default Trace2 settings. This allows system-wide Trace2 settings to be installed and inherited to make it easier to manage a collection of systems. The original GIT_TR2* environment variables are loaded afterwards and can be used to override the system settings. Only the system and global config files are used. Repo and worktree local config files are ignored. Likewise, the "-c" command line arguments are also ignored. These limits are for performance reasons. (1) For users not using Trace2, there should be minimal overhead to detect that Trace2 is not enabled. In particular, Trace2 should not allocate lots of otherwise unused data strucutres. (2) For accurate performance measurements, Trace2 should be initialized as early in the git process as possible, and before most of the normal git process initialization (which involves discovering the .git directory and reading a hierarchy of config files). Signed-off-by: Jeff Hostetler <jeffhost@microsoft.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>

Jeff Hostetler committed Apr 15, 2019 at 13:39 UTC bce9db6de97c95882a7c46836bb6cc90acf0fef0
14 files changed +340 -76
Makefile
+1
@@ -1005,6 +1005,7 @@ LIB_OBJS += trace2/tr2_cfg.o
1005 LIB_OBJS += trace2/tr2_cmd_name.o
1006 LIB_OBJS += trace2/tr2_dst.o
1007 LIB_OBJS += trace2/tr2_sid.o
1008 +LIB_OBJS += trace2/tr2_sysenv.o
1009 LIB_OBJS += trace2/tr2_tbuf.o
1010 LIB_OBJS += trace2/tr2_tgt_event.o
1011 LIB_OBJS += trace2/tr2_tgt_normal.o
t/t0210-trace2-normal.sh
+44 -5
@@ -3,6 +3,11 @@
3 test_description='test trace2 facility (normal target)'
4 . ./test-lib.sh
5
6 +# Turn off any inherited trace2 settings for this test.
7 +sane_unset GIT_TR2 GIT_TR2_PERF GIT_TR2_EVENT
8 +sane_unset GIT_TR2_BRIEF
9 +sane_unset GIT_TR2_CONFIG_PARAMS
10 +
11 # Add t/helper directory to PATH so that we can use a relative
12 # path to run nested instances of test-tool.exe (see 004child).
13 # This helps with HEREDOC comparisons later.
@@ -15,11 +20,6 @@ PATH="$TTDIR:$PATH" && export PATH
20 # Warning: So you may see extra lines in artifact files when
21 # Warning: interactively debugging.
22
18 -# Turn off any inherited trace2 settings for this test.
19 -unset GIT_TR2 GIT_TR2_PERF GIT_TR2_EVENT
20 -unset GIT_TR2_BRIEF
21 -unset GIT_TR2_CONFIG_PARAMS
22 -
23 V=$(git version | sed -e 's/^git version //') && export V
24
25 # There are multiple trace2 targets: normal, perf, and event.
@@ -132,4 +132,43 @@ test_expect_success 'normal stream, error event' '
132 test_cmp expect actual
133 '
134
135 +sane_unset GIT_TR2_BRIEF
136 +
137 +# Now test without environment variables and get all Trace2 settings
138 +# from the global config.
139 +
140 +test_expect_success 'using global config, normal stream, return code 0' '
141 + test_when_finished "rm trace.normal actual expect" &&
142 + test_config_global trace2.normalBrief 1 &&
143 + test_config_global trace2.normalTarget "$(pwd)/trace.normal" &&
144 + test-tool trace2 001return 0 &&
145 + perl "$TEST_DIRECTORY/t0210/scrub_normal.perl" <trace.normal >actual &&
146 + cat >expect <<-EOF &&
147 + version $V
148 + start _EXE_ trace2 001return 0
149 + cmd_name trace2 (trace2)
150 + exit elapsed:_TIME_ code:0
151 + atexit elapsed:_TIME_ code:0
152 + EOF
153 + test_cmp expect actual
154 +'
155 +
156 +test_expect_success 'using global config with include' '
157 + test_when_finished "rm trace.normal actual expect real.gitconfig" &&
158 + test_config_global trace2.normalBrief 1 &&
159 + test_config_global trace2.normalTarget "$(pwd)/trace.normal" &&
160 + mv "$(pwd)/.gitconfig" "$(pwd)/real.gitconfig" &&
161 + test_config_global include.path "$(pwd)/real.gitconfig" &&
162 + test-tool trace2 001return 0 &&
163 + perl "$TEST_DIRECTORY/t0210/scrub_normal.perl" <trace.normal >actual &&
164 + cat >expect <<-EOF &&
165 + version $V
166 + start _EXE_ trace2 001return 0
167 + cmd_name trace2 (trace2)
168 + exit elapsed:_TIME_ code:0
169 + atexit elapsed:_TIME_ code:0
170 + EOF
171 + test_cmp expect actual
172 +'
173 +
174 test_done
t/t0211-trace2-perf.sh
+26 -5
@@ -3,6 +3,11 @@
3 test_description='test trace2 facility (perf target)'
4 . ./test-lib.sh
5
6 +# Turn off any inherited trace2 settings for this test.
7 +sane_unset GIT_TR2 GIT_TR2_PERF GIT_TR2_EVENT
8 +sane_unset GIT_TR2_PERF_BRIEF
9 +sane_unset GIT_TR2_CONFIG_PARAMS
10 +
11 # Add t/helper directory to PATH so that we can use a relative
12 # path to run nested instances of test-tool.exe (see 004child).
13 # This helps with HEREDOC comparisons later.
@@ -15,11 +20,6 @@ PATH="$TTDIR:$PATH" && export PATH
20 # Warning: So you may see extra lines in artifact files when
21 # Warning: interactively debugging.
22
18 -# Turn off any inherited trace2 settings for this test.
19 -unset GIT_TR2 GIT_TR2_PERF GIT_TR2_EVENT
20 -unset GIT_TR2_PERF_BRIEF
21 -unset GIT_TR2_CONFIG_PARAMS
22 -
23 V=$(git version | sed -e 's/^git version //') && export V
24
25 # There are multiple trace2 targets: normal, perf, and event.
@@ -150,4 +150,25 @@ test_expect_success 'perf stream, child processes' '
150 test_cmp expect actual
151 '
152
153 +sane_unset GIT_TR2_PERF_BRIEF
154 +
155 +# Now test without environment variables and get all Trace2 settings
156 +# from the global config.
157 +
158 +test_expect_success 'using global config, perf stream, return code 0' '
159 + test_when_finished "rm trace.perf actual expect" &&
160 + test_config_global trace2.perfBrief 1 &&
161 + test_config_global trace2.perfTarget "$(pwd)/trace.perf" &&
162 + test-tool trace2 001return 0 &&
163 + perl "$TEST_DIRECTORY/t0211/scrub_perf.perl" <trace.perf >actual &&
164 + cat >expect <<-EOF &&
165 + d0|main|version|||||$V
166 + d0|main|start||_T_ABS_|||_EXE_ trace2 001return 0
167 + d0|main|cmd_name|||||trace2 (trace2)
168 + d0|main|exit||_T_ABS_|||code:0
169 + d0|main|atexit||_T_ABS_|||code:0
170 + EOF
171 + test_cmp expect actual
172 +'
173 +
174 test_done
t/t0212-trace2-event.sh
+37 -5
@@ -3,6 +3,11 @@
3 test_description='test trace2 facility'
4 . ./test-lib.sh
5
6 +# Turn off any inherited trace2 settings for this test.
7 +sane_unset GIT_TR2 GIT_TR2_PERF GIT_TR2_EVENT
8 +sane_unset GIT_TR2_BARE
9 +sane_unset GIT_TR2_CONFIG_PARAMS
10 +
11 perl -MJSON::PP -e 0 >/dev/null 2>&1 && test_set_prereq JSON_PP
12
13 # Add t/helper directory to PATH so that we can use a relative
@@ -17,11 +22,6 @@ PATH="$TTDIR:$PATH" && export PATH
22 # Warning: So you may see extra lines in artifact files when
23 # Warning: interactively debugging.
24
20 -# Turn off any inherited trace2 settings for this test.
21 -unset GIT_TR2 GIT_TR2_PERF GIT_TR2_EVENT
22 -unset GIT_TR2_BARE
23 -unset GIT_TR2_CONFIG_PARAMS
24 -
25 V=$(git version | sed -e 's/^git version //') && export V
26
27 # There are multiple trace2 targets: normal, perf, and event.
@@ -233,4 +233,36 @@ test_expect_success JSON_PP 'basic trace2_data' '
233 test_cmp expect actual
234 '
235
236 +# Now test without environment variables and get all Trace2 settings
237 +# from the global config.
238 +
239 +test_expect_success JSON_PP 'using global config, event stream, error event' '
240 + test_when_finished "rm trace.event actual expect" &&
241 + test_config_global trace2.eventTarget "$(pwd)/trace.event" &&
242 + test-tool trace2 003error "hello world" "this is a test" &&
243 + perl "$TEST_DIRECTORY/t0212/parse_events.perl" <trace.event >actual &&
244 + sed -e "s/^|//" >expect <<-EOF &&
245 + |VAR1 = {
246 + | "_SID0_":{
247 + | "argv":[
248 + | "_EXE_",
249 + | "trace2",
250 + | "003error",
251 + | "hello world",
252 + | "this is a test"
253 + | ],
254 + | "errors":[
255 + | "%s",
256 + | "%s"
257 + | ],
258 + | "exit_code":0,
259 + | "hierarchy":"trace2",
260 + | "name":"trace2",
261 + | "version":"$V"
262 + | }
263 + |};
264 + EOF
265 + test_cmp expect actual
266 +'
267 +
268 test_done
trace2.c
+4
@@ -10,6 +10,7 @@
10 #include "trace2/tr2_cmd_name.h"
11 #include "trace2/tr2_dst.h"
12 #include "trace2/tr2_sid.h"
13 +#include "trace2/tr2_sysenv.h"
14 #include "trace2/tr2_tgt.h"
15 #include "trace2/tr2_tls.h"
16
@@ -120,6 +121,7 @@ static void tr2main_atexit_handler(void)
121 tr2_sid_release();
122 tr2_cmd_name_release();
123 tr2_cfg_free_patterns();
124 + tr2_sysenv_release();
125
126 trace2_enabled = 0;
127 }
@@ -155,6 +157,8 @@ void trace2_initialize_fl(const char *file, int line)
157 if (trace2_enabled)
158 return;
159
160 + tr2_sysenv_load();
161 +
162 if (!tr2_tgt_want_builtins())
163 return;
164 trace2_enabled = 1;
trace2.h
+7 -5
@@ -38,7 +38,8 @@ void trace2_initialize_clock(void);
38
39 /*
40 * Initialize TRACE2 tracing facility if any of the builtin TRACE2
41 - * targets are enabled in the environment. Emits a 'version' event.
41 + * targets are enabled in the system config or the environment.
42 + * Emits a 'version' event.
43 *
44 * Cleanup/Termination is handled automatically by a registered
45 * atexit() routine.
@@ -125,10 +126,11 @@ void trace2_cmd_alias_fl(const char *file, int line, const char *alias,
126 * Emit one or more 'def_param' events for "interesting" configuration
127 * settings.
128 *
128 - * The environment variable "GIT_TR2_CONFIG_PARAMS" can be set to a
129 - * list of patterns considered important. For example:
130 - *
131 - * GIT_TR2_CONFIG_PARAMS="core.*,remote.*.url"
129 + * Use the TR2_SYSENV_CFG_PARAM setting to register a comma-separated
130 + * list of patterns configured important. For example:
131 + * git config --system trace2.configParams 'core.*,remote.*.url'
132 + * or:
133 + * GIT_TR2_CONFIG_PARAMS=core.*,remote.*.url"
134 *
135 * Note: this routine does a read-only iteration on the config data
136 * (using read_early_config()), so it must not be called until enough
trace2/tr2_cfg.c
+3 -4
@@ -1,8 +1,7 @@
1 #include "cache.h"
2 #include "config.h"
3 -#include "tr2_cfg.h"
4 -
5 -#define TR2_ENVVAR_CFG_PARAM "GIT_TR2_CONFIG_PARAMS"
3 +#include "trace2/tr2_cfg.h"
4 +#include "trace2/tr2_sysenv.h"
5
6 static struct strbuf **tr2_cfg_patterns;
7 static int tr2_cfg_count_patterns;
@@ -21,7 +20,7 @@ static int tr2_cfg_load_patterns(void)
20 return tr2_cfg_count_patterns;
21 tr2_cfg_loaded = 1;
22
24 - envvar = getenv(TR2_ENVVAR_CFG_PARAM);
23 + envvar = tr2_sysenv_get(TR2_SYSENV_CFG_PARAM);
24 if (!envvar || !*envvar)
25 return tr2_cfg_count_patterns;
26
trace2/tr2_dst.c
+14 -12
@@ -1,5 +1,6 @@
1 #include "cache.h"
2 #include "trace2/tr2_dst.h"
3 +#include "trace2/tr2_sysenv.h"
4
5 /*
6 * If a Trace2 target cannot be opened for writing, we should issue a
@@ -7,17 +8,13 @@
8 * or socket and beyond the user's control -- especially since every
9 * git command (and sub-command) will print the message. So we silently
10 * eat these warnings and just discard the trace data.
10 - *
11 - * Enable the following environment variable to see these warnings.
11 */
13 -#define TR2_ENVVAR_DST_DEBUG "GIT_TR2_DST_DEBUG"
14 -
12 static int tr2_dst_want_warning(void)
13 {
14 static int tr2env_dst_debug = -1;
15
16 if (tr2env_dst_debug == -1) {
20 - const char *env_value = getenv(TR2_ENVVAR_DST_DEBUG);
17 + const char *env_value = tr2_sysenv_get(TR2_SYSENV_DST_DEBUG);
18 if (!env_value || !*env_value)
19 tr2env_dst_debug = 0;
20 else
@@ -42,7 +39,9 @@ static int tr2_dst_try_path(struct tr2_dst *dst, const char *tgt_value)
39 if (fd == -1) {
40 if (tr2_dst_want_warning())
41 warning("trace2: could not open '%s' for '%s' tracing: %s",
45 - tgt_value, dst->env_var_name, strerror(errno));
42 + tgt_value,
43 + tr2_sysenv_display_name(dst->sysenv_var),
44 + strerror(errno));
45
46 tr2_dst_trace_disable(dst);
47 return 0;
@@ -116,7 +115,8 @@ static int tr2_dst_try_unix_domain_socket(struct tr2_dst *dst,
115 if (!path || !*path) {
116 if (tr2_dst_want_warning())
117 warning("trace2: invalid AF_UNIX value '%s' for '%s' tracing",
119 - tgt_value, dst->env_var_name);
118 + tgt_value,
119 + tr2_sysenv_display_name(dst->sysenv_var));
120
121 tr2_dst_trace_disable(dst);
122 return 0;
@@ -126,7 +126,7 @@ static int tr2_dst_try_unix_domain_socket(struct tr2_dst *dst,
126 strlen(path) >= sizeof(((struct sockaddr_un *)0)->sun_path)) {
127 if (tr2_dst_want_warning())
128 warning("trace2: invalid AF_UNIX path '%s' for '%s' tracing",
129 - path, dst->env_var_name);
129 + path, tr2_sysenv_display_name(dst->sysenv_var));
130
131 tr2_dst_trace_disable(dst);
132 return 0;
@@ -148,7 +148,8 @@ static int tr2_dst_try_unix_domain_socket(struct tr2_dst *dst,
148 error:
149 if (tr2_dst_want_warning())
150 warning("trace2: could not connect to socket '%s' for '%s' tracing: %s",
151 - path, dst->env_var_name, strerror(e));
151 + path, tr2_sysenv_display_name(dst->sysenv_var),
152 + strerror(e));
153
154 tr2_dst_trace_disable(dst);
155 return 0;
@@ -168,7 +169,7 @@ static void tr2_dst_malformed_warning(struct tr2_dst *dst,
169 struct strbuf buf = STRBUF_INIT;
170
171 strbuf_addf(&buf, "trace2: unknown value for '%s': '%s'",
171 - dst->env_var_name, tgt_value);
172 + tr2_sysenv_display_name(dst->sysenv_var), tgt_value);
173 warning("%s", buf.buf);
174
175 strbuf_release(&buf);
@@ -184,7 +185,7 @@ int tr2_dst_get_trace_fd(struct tr2_dst *dst)
185
186 dst->initialized = 1;
187
187 - tgt_value = getenv(dst->env_var_name);
188 + tgt_value = tr2_sysenv_get(dst->sysenv_var);
189
190 if (!tgt_value || !strcmp(tgt_value, "") || !strcmp(tgt_value, "0") ||
191 !strcasecmp(tgt_value, "false")) {
@@ -246,7 +247,8 @@ void tr2_dst_write_line(struct tr2_dst *dst, struct strbuf *buf_line)
247 return;
248
249 if (tr2_dst_want_warning())
249 - warning("unable to write trace to '%s': %s", dst->env_var_name,
250 + warning("unable to write trace to '%s': %s",
251 + tr2_sysenv_display_name(dst->sysenv_var),
252 strerror(errno));
253 tr2_dst_trace_disable(dst);
254 }
trace2/tr2_dst.h
+2 -1
@@ -2,9 +2,10 @@
2 #define TR2_DST_H
3
4 struct strbuf;
5 +#include "trace2/tr2_sysenv.h"
6
7 struct tr2_dst {
7 - const char *const env_var_name;
8 + enum tr2_sysenv_variable sysenv_var;
9 int fd;
10 unsigned int initialized : 1;
11 unsigned int need_close : 1;
trace2/tr2_sysenv.c new
+127
@@ -0,0 +1,127 @@
1 +#include "cache.h"
2 +#include "config.h"
3 +#include "dir.h"
4 +#include "tr2_sysenv.h"
5 +
6 +/*
7 + * Each entry represents a trace2 setting.
8 + * See Documentation/technical/api-trace2.txt
9 + */
10 +struct tr2_sysenv_entry {
11 + const char *env_var_name;
12 + const char *git_config_name;
13 +
14 + char *value;
15 + unsigned int getenv_called : 1;
16 +};
17 +
18 +/*
19 + * This table must match "enum tr2_sysenv_variable" in tr2_sysenv.h.
20 + *
21 + * The strings in this table are constant and must match the published
22 + * config and environment variable names as described in the documentation.
23 + *
24 + * We do not define entries for the GIT_TR2_PARENT_* environment
25 + * variables because they are transient and used to pass information
26 + * from parent to child git processes, rather than settings.
27 + */
28 +/* clang-format off */
29 +static struct tr2_sysenv_entry tr2_sysenv_settings[] = {
30 + [TR2_SYSENV_CFG_PARAM] = { "GIT_TR2_CONFIG_PARAMS",
31 + "trace2.configparams" },
32 +
33 + [TR2_SYSENV_DST_DEBUG] = { "GIT_TR2_DST_DEBUG",
34 + "trace2.destinationdebug" },
35 +
36 + [TR2_SYSENV_NORMAL] = { "GIT_TR2",
37 + "trace2.normaltarget" },
38 + [TR2_SYSENV_NORMAL_BRIEF] = { "GIT_TR2_BRIEF",
39 + "trace2.normalbrief" },
40 +
41 + [TR2_SYSENV_EVENT] = { "GIT_TR2_EVENT",
42 + "trace2.eventtarget" },
43 + [TR2_SYSENV_EVENT_BRIEF] = { "GIT_TR2_EVENT_BRIEF",
44 + "trace2.eventbrief" },
45 + [TR2_SYSENV_EVENT_NESTING] = { "GIT_TR2_EVENT_NESTING",
46 + "trace2.eventnesting" },
47 +
48 + [TR2_SYSENV_PERF] = { "GIT_TR2_PERF",
49 + "trace2.perftarget" },
50 + [TR2_SYSENV_PERF_BRIEF] = { "GIT_TR2_PERF_BRIEF",
51 + "trace2.perfbrief" },
52 +};
53 +/* clang-format on */
54 +
55 +static int tr2_sysenv_cb(const char *key, const char *value, void *d)
56 +{
57 + int k;
58 +
59 + if (!starts_with(key, "trace2."))
60 + return 0;
61 +
62 + for (k = 0; k < ARRAY_SIZE(tr2_sysenv_settings); k++) {
63 + if (!strcmp(key, tr2_sysenv_settings[k].git_config_name)) {
64 + free(tr2_sysenv_settings[k].value);
65 + tr2_sysenv_settings[k].value = xstrdup(value);
66 + return 0;
67 + }
68 + }
69 +
70 + return 0;
71 +}
72 +
73 +/*
74 + * Load Trace2 settings from the system config (usually "/etc/gitconfig"
75 + * unless we were built with a runtime-prefix). These are intended to
76 + * define the default values for Trace2 as requested by the administrator.
77 + *
78 + * Then override with the Trace2 settings from the global config.
79 + */
80 +void tr2_sysenv_load(void)
81 +{
82 + if (ARRAY_SIZE(tr2_sysenv_settings) != TR2_SYSENV_MUST_BE_LAST)
83 + BUG("tr2_sysenv_settings size is wrong");
84 +
85 + read_very_early_config(tr2_sysenv_cb, NULL);
86 +}
87 +
88 +/*
89 + * Return the value for the requested Trace2 setting from these sources:
90 + * the system config, the global config, and the environment.
91 + */
92 +const char *tr2_sysenv_get(enum tr2_sysenv_variable var)
93 +{
94 + if (var >= TR2_SYSENV_MUST_BE_LAST)
95 + BUG("tr2_sysenv_get invalid var '%d'", var);
96 +
97 + if (!tr2_sysenv_settings[var].getenv_called) {
98 + const char *v = getenv(tr2_sysenv_settings[var].env_var_name);
99 + if (v && *v) {
100 + free(tr2_sysenv_settings[var].value);
101 + tr2_sysenv_settings[var].value = xstrdup(v);
102 + }
103 + tr2_sysenv_settings[var].getenv_called = 1;
104 + }
105 +
106 + return tr2_sysenv_settings[var].value;
107 +}
108 +
109 +/*
110 + * Return a friendly name for this setting that is suitable for printing
111 + * in an error messages.
112 + */
113 +const char *tr2_sysenv_display_name(enum tr2_sysenv_variable var)
114 +{
115 + if (var >= TR2_SYSENV_MUST_BE_LAST)
116 + BUG("tr2_sysenv_get invalid var '%d'", var);
117 +
118 + return tr2_sysenv_settings[var].env_var_name;
119 +}
120 +
121 +void tr2_sysenv_release(void)
122 +{
123 + int k;
124 +
125 + for (k = 0; k < ARRAY_SIZE(tr2_sysenv_settings); k++)
126 + free(tr2_sysenv_settings[k].value);
127 +}
trace2/tr2_sysenv.h new
+36
@@ -0,0 +1,36 @@
1 +#ifndef TR2_SYSENV_H
2 +#define TR2_SYSENV_H
3 +
4 +/*
5 + * The Trace2 settings that can be loaded from /etc/gitconfig
6 + * and/or user environment variables.
7 + *
8 + * Note that this set does not contain any of the transient
9 + * environment variables used to pass information from parent
10 + * to child git processes, such "GIT_TR2_PARENT_SID".
11 + */
12 +enum tr2_sysenv_variable {
13 + TR2_SYSENV_CFG_PARAM = 0,
14 +
15 + TR2_SYSENV_DST_DEBUG,
16 +
17 + TR2_SYSENV_NORMAL,
18 + TR2_SYSENV_NORMAL_BRIEF,
19 +
20 + TR2_SYSENV_EVENT,
21 + TR2_SYSENV_EVENT_BRIEF,
22 + TR2_SYSENV_EVENT_NESTING,
23 +
24 + TR2_SYSENV_PERF,
25 + TR2_SYSENV_PERF_BRIEF,
26 +
27 + TR2_SYSENV_MUST_BE_LAST
28 +};
29 +
30 +void tr2_sysenv_load(void);
31 +
32 +const char *tr2_sysenv_get(enum tr2_sysenv_variable);
33 +const char *tr2_sysenv_display_name(enum tr2_sysenv_variable var);
34 +void tr2_sysenv_release(void);
35 +
36 +#endif /* TR2_SYSENV_H */
trace2/tr2_tgt_event.c
+23 -23
@@ -6,10 +6,11 @@
6 #include "trace2/tr2_dst.h"
7 #include "trace2/tr2_tbuf.h"
8 #include "trace2/tr2_sid.h"
9 +#include "trace2/tr2_sysenv.h"
10 #include "trace2/tr2_tgt.h"
11 #include "trace2/tr2_tls.h"
12
12 -static struct tr2_dst tr2dst_event = { "GIT_TR2_EVENT", 0, 0, 0 };
13 +static struct tr2_dst tr2dst_event = { TR2_SYSENV_EVENT, 0, 0, 0 };
14
15 /*
16 * The version number of the JSON data generated by the EVENT target
@@ -28,37 +29,36 @@ static struct tr2_dst tr2dst_event = { "GIT_TR2_EVENT", 0, 0, 0 };
29 * are primarily intended for the performance target during debugging.
30 *
31 * Some of the outer-most messages, however, may be of interest to the
31 - * event target. Set this environment variable to a larger integer for
32 - * more detail in the event target.
32 + * event target. Use the TR2_SYSENV_EVENT_NESTING setting to increase
33 + * region details in the event target.
34 */
34 -#define TR2_ENVVAR_EVENT_NESTING "GIT_TR2_EVENT_NESTING"
35 -static int tr2env_event_nesting_wanted = 2;
35 +static int tr2env_event_max_nesting_levels = 2;
36
37 /*
38 - * Set this environment variable to true to omit the <time>, <file>, and
38 + * Use the TR2_SYSENV_EVENT_BRIEF to omit the <time>, <file>, and
39 * <line> fields from most events.
40 */
41 -#define TR2_ENVVAR_EVENT_BRIEF "GIT_TR2_EVENT_BRIEF"
42 -static int tr2env_event_brief;
41 +static int tr2env_event_be_brief;
42
43 static int fn_init(void)
44 {
45 int want = tr2_dst_trace_want(&tr2dst_event);
47 - int want_nesting;
46 + int max_nesting;
47 int want_brief;
49 - char *nesting;
50 - char *brief;
48 + const char *nesting;
49 + const char *brief;
50
51 if (!want)
52 return want;
53
55 - nesting = getenv(TR2_ENVVAR_EVENT_NESTING);
56 - if (nesting && ((want_nesting = atoi(nesting)) > 0))
57 - tr2env_event_nesting_wanted = want_nesting;
54 + nesting = tr2_sysenv_get(TR2_SYSENV_EVENT_NESTING);
55 + if (nesting && *nesting && ((max_nesting = atoi(nesting)) > 0))
56 + tr2env_event_max_nesting_levels = max_nesting;
57
59 - brief = getenv(TR2_ENVVAR_EVENT_BRIEF);
60 - if (brief && ((want_brief = atoi(brief)) > 0))
61 - tr2env_event_brief = want_brief;
58 + brief = tr2_sysenv_get(TR2_SYSENV_EVENT_BRIEF);
59 + if (brief && *brief &&
60 + ((want_brief = git_parse_maybe_bool(brief)) != -1))
61 + tr2env_event_be_brief = want_brief;
62
63 return want;
64 }
@@ -92,13 +92,13 @@ static void event_fmt_prepare(const char *event_name, const char *file,
92 /*
93 * In brief mode, only emit <time> on these 2 event types.
94 */
95 - if (!tr2env_event_brief || !strcmp(event_name, "version") ||
95 + if (!tr2env_event_be_brief || !strcmp(event_name, "version") ||
96 !strcmp(event_name, "atexit")) {
97 tr2_tbuf_utc_time(&tb_now);
98 jw_object_string(jw, "time", tb_now.buf);
99 }
100
101 - if (!tr2env_event_brief && file && *file) {
101 + if (!tr2env_event_be_brief && file && *file) {
102 jw_object_string(jw, "file", file);
103 jw_object_intmax(jw, "line", line);
104 }
@@ -459,7 +459,7 @@ static void fn_region_enter_printf_va_fl(const char *file, int line,
459 {
460 const char *event_name = "region_enter";
461 struct tr2tls_thread_ctx *ctx = tr2tls_get_self();
462 - if (ctx->nr_open_regions <= tr2env_event_nesting_wanted) {
462 + if (ctx->nr_open_regions <= tr2env_event_max_nesting_levels) {
463 struct json_writer jw = JSON_WRITER_INIT;
464
465 jw_object_begin(&jw, 0);
@@ -484,7 +484,7 @@ static void fn_region_leave_printf_va_fl(
484 {
485 const char *event_name = "region_leave";
486 struct tr2tls_thread_ctx *ctx = tr2tls_get_self();
487 - if (ctx->nr_open_regions <= tr2env_event_nesting_wanted) {
487 + if (ctx->nr_open_regions <= tr2env_event_max_nesting_levels) {
488 struct json_writer jw = JSON_WRITER_INIT;
489 double t_rel = (double)us_elapsed_region / 1000000.0;
490
@@ -511,7 +511,7 @@ static void fn_data_fl(const char *file, int line, uint64_t us_elapsed_absolute,
511 {
512 const char *event_name = "data";
513 struct tr2tls_thread_ctx *ctx = tr2tls_get_self();
514 - if (ctx->nr_open_regions <= tr2env_event_nesting_wanted) {
514 + if (ctx->nr_open_regions <= tr2env_event_max_nesting_levels) {
515 struct json_writer jw = JSON_WRITER_INIT;
516 double t_abs = (double)us_elapsed_absolute / 1000000.0;
517 double t_rel = (double)us_elapsed_region / 1000000.0;
@@ -539,7 +539,7 @@ static void fn_data_json_fl(const char *file, int line,
539 {
540 const char *event_name = "data_json";
541 struct tr2tls_thread_ctx *ctx = tr2tls_get_self();
542 - if (ctx->nr_open_regions <= tr2env_event_nesting_wanted) {
542 + if (ctx->nr_open_regions <= tr2env_event_max_nesting_levels) {
543 struct json_writer jw = JSON_WRITER_INIT;
544 double t_abs = (double)us_elapsed_absolute / 1000000.0;
545 double t_rel = (double)us_elapsed_region / 1000000.0;
trace2/tr2_tgt_normal.c
+8 -8
@@ -4,20 +4,20 @@
4 #include "quote.h"
5 #include "version.h"
6 #include "trace2/tr2_dst.h"
7 +#include "trace2/tr2_sysenv.h"
8 #include "trace2/tr2_tbuf.h"
9 #include "trace2/tr2_tgt.h"
10 #include "trace2/tr2_tls.h"
11
11 -static struct tr2_dst tr2dst_normal = { "GIT_TR2", 0, 0, 0 };
12 +static struct tr2_dst tr2dst_normal = { TR2_SYSENV_NORMAL, 0, 0, 0 };
13
14 /*
14 - * Set this environment variable to true to omit the "<time> <file>:<line>"
15 + * Use the TR2_SYSENV_NORMAL_BRIEF setting to omit the "<time> <file>:<line>"
16 * fields from each line written to the builtin normal target.
17 *
18 * Unit tests may want to use this to help with testing.
19 */
19 -#define TR2_ENVVAR_NORMAL_BRIEF "GIT_TR2_BRIEF"
20 -static int tr2env_normal_brief;
20 +static int tr2env_normal_be_brief;
21
22 #define TR2FMT_NORMAL_FL_WIDTH (50)
23
@@ -25,15 +25,15 @@ static int fn_init(void)
25 {
26 int want = tr2_dst_trace_want(&tr2dst_normal);
27 int want_brief;
28 - char *brief;
28 + const char *brief;
29
30 if (!want)
31 return want;
32
33 - brief = getenv(TR2_ENVVAR_NORMAL_BRIEF);
33 + brief = tr2_sysenv_get(TR2_SYSENV_NORMAL_BRIEF);
34 if (brief && *brief &&
35 ((want_brief = git_parse_maybe_bool(brief)) != -1))
36 - tr2env_normal_brief = want_brief;
36 + tr2env_normal_be_brief = want_brief;
37
38 return want;
39 }
@@ -47,7 +47,7 @@ static void normal_fmt_prepare(const char *file, int line, struct strbuf *buf)
47 {
48 strbuf_setlen(buf, 0);
49
50 - if (!tr2env_normal_brief) {
50 + if (!tr2env_normal_be_brief) {
51 struct tr2_tbuf tb_now;
52
53 tr2_tbuf_local_time(&tb_now);
trace2/tr2_tgt_perf.c
+8 -8
@@ -6,20 +6,20 @@
6 #include "json-writer.h"
7 #include "trace2/tr2_dst.h"
8 #include "trace2/tr2_sid.h"
9 +#include "trace2/tr2_sysenv.h"
10 #include "trace2/tr2_tbuf.h"
11 #include "trace2/tr2_tgt.h"
12 #include "trace2/tr2_tls.h"
13
13 -static struct tr2_dst tr2dst_perf = { "GIT_TR2_PERF", 0, 0, 0 };
14 +static struct tr2_dst tr2dst_perf = { TR2_SYSENV_PERF, 0, 0, 0 };
15
16 /*
16 - * Set this environment variable to true to omit the "<time> <file>:<line>"
17 + * Use TR2_SYSENV_PERF_BRIEF to omit the "<time> <file>:<line>"
18 * fields from each line written to the builtin performance target.
19 *
20 * Unit tests may want to use this to help with testing.
21 */
21 -#define TR2_ENVVAR_PERF_BRIEF "GIT_TR2_PERF_BRIEF"
22 -static int tr2env_perf_brief;
22 +static int tr2env_perf_be_brief;
23
24 #define TR2FMT_PERF_FL_WIDTH (50)
25 #define TR2FMT_PERF_MAX_EVENT_NAME (12)
@@ -36,17 +36,17 @@ static int fn_init(void)
36 {
37 int want = tr2_dst_trace_want(&tr2dst_perf);
38 int want_brief;
39 - char *brief;
39 + const char *brief;
40
41 if (!want)
42 return want;
43
44 strbuf_addchars(&dots, '.', TR2_DOTS_BUFFER_SIZE);
45
46 - brief = getenv(TR2_ENVVAR_PERF_BRIEF);
46 + brief = tr2_sysenv_get(TR2_SYSENV_PERF_BRIEF);
47 if (brief && *brief &&
48 ((want_brief = git_parse_maybe_bool(brief)) != -1))
49 - tr2env_perf_brief = want_brief;
49 + tr2env_perf_be_brief = want_brief;
50
51 return want;
52 }
@@ -77,7 +77,7 @@ static void perf_fmt_prepare(const char *event_name,
77
78 strbuf_setlen(buf, 0);
79
80 - if (!tr2env_perf_brief) {
80 + if (!tr2env_perf_be_brief) {
81 struct tr2_tbuf tb_now;
82
83 tr2_tbuf_local_time(&tb_now);