Skip to content

Commit f7fb7a3

Browse files
committed
sideband: mask control characters
The output of `git clone` is a vital component for understanding what has happened when things go wrong. However, these logs are partially under the control of the remote server (via the "sideband", which typically contains what the remote `git pack-objects` process sends to `stderr`), and is currently not sanitized by Git. This makes Git susceptible to ANSI escape sequence injection (see CWE-150, https://cwe.mitre.org/data/definitions/150.html), which allows attackers to corrupt terminal state, to hide information, and even to insert characters into the input buffer (i.e. as if the user had typed those characters). To plug this vulnerability, disallow any control character in the sideband, replacing them instead with the common `^<letter/symbol>` (e.g. `^[` for `\x1b`, `^A` for `\x01`). There is likely a need for more fine-grained controls instead of using a "heavy hammer" like this, which will be introduced subsequently. Signed-off-by: Johannes Schindelin <[email protected]>
1 parent e1fbebe commit f7fb7a3

File tree

2 files changed

+27
-2
lines changed

2 files changed

+27
-2
lines changed

sideband.c

Lines changed: 15 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -65,6 +65,19 @@ void list_config_color_sideband_slots(struct string_list *list, const char *pref
6565
list_config_item(list, prefix, keywords[i].keyword);
6666
}
6767

68+
static void strbuf_add_sanitized(struct strbuf *dest, const char *src, int n)
69+
{
70+
strbuf_grow(dest, n);
71+
for (; n && *src; src++, n--) {
72+
if (!iscntrl(*src) || *src == '\t' || *src == '\n')
73+
strbuf_addch(dest, *src);
74+
else {
75+
strbuf_addch(dest, '^');
76+
strbuf_addch(dest, 0x40 + *src);
77+
}
78+
}
79+
}
80+
6881
/*
6982
* Optionally highlight one keyword in remote output if it appears at the start
7083
* of the line. This should be called for a single line only, which is
@@ -80,7 +93,7 @@ static void maybe_colorize_sideband(struct strbuf *dest, const char *src, int n)
8093
int i;
8194

8295
if (!want_color_stderr(use_sideband_colors())) {
83-
strbuf_add(dest, src, n);
96+
strbuf_add_sanitized(dest, src, n);
8497
return;
8598
}
8699

@@ -113,7 +126,7 @@ static void maybe_colorize_sideband(struct strbuf *dest, const char *src, int n)
113126
}
114127
}
115128

116-
strbuf_add(dest, src, n);
129+
strbuf_add_sanitized(dest, src, n);
117130
}
118131

119132

t/t5409-colorize-remote-messages.sh

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -99,4 +99,16 @@ test_expect_success 'fallback to color.ui' '
9999
grep "<BOLD;RED>error<RESET>: error" decoded
100100
'
101101

102+
test_expect_success 'disallow (color) control sequences in sideband' '
103+
write_script .git/color-me-surprised <<-\EOF &&
104+
printf "error: Have you \\033[31mread\\033[m this?\\n" >&2
105+
exec "$@"
106+
EOF
107+
test_config_global uploadPack.packObjectshook ./color-me-surprised &&
108+
test_commit need-at-least-one-commit &&
109+
git clone --no-local . throw-away 2>stderr &&
110+
test_decode_color <stderr >decoded &&
111+
test_grep ! RED decoded
112+
'
113+
102114
test_done

0 commit comments

Comments
 (0)