Skip to content

Commit 2541cba

Browse files
fajsgitster
authored andcommitted
wt-status: don't find scissors line beyond buf len
If (a) There is a "---" divider in a commit message, (b) At some point beyond that divider, there is a cut-line (that is, "# ------------------------ >8 ------------------------") in the commit message, (c) the user does not explicitly set the "no-divider" option, then "git interpret-trailers" will hang indefinitively. This is because when (a) is true, find_end_of_log_message() will invoke ignored_log_message_bytes() with a len that is intended to make it ignore the part of the commit message beyond the divider. However, ignored_log_message_bytes() calls wt_status_locate_end(), and that function ignores the length restriction when it tries to locate the cut line. If it manages to find one, the returned cutoff value is greater than len. At this point, ignored_log_message_bytes() goes into an infinite loop, because it won't advance the string parsing beyond len, but the exit condition expects to reach cutoff. Make wt_status_locate_end() honor the length parameter passed in, to fix this issue. In general, if wt_status_locate_end() is given a piece of the memory that lacks NUL at all, strstr() may continue across page boundaries and run into an unmapped page. For our current callers, this is not a problem, as all of them except one uses a memory owned by a strbuf (which guarantees an implicit NUL-termination after its payload), and the one exception in trailer.c:find_end_of_log_message() uses strlen() to compute the length before calling this function. Signed-off-by: Florian Schmidt <[email protected]> Reviewed-by: Jonathan Davies <[email protected]> [jc: tweaked the commit log message and the implementation a bit] Signed-off-by: Junio C Hamano <[email protected]>
1 parent 668f2d5 commit 2541cba

File tree

2 files changed

+19
-2
lines changed

2 files changed

+19
-2
lines changed

t/t7513-interpret-trailers.sh

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1476,4 +1476,18 @@ test_expect_success 'suppress --- handling' '
14761476
test_cmp expected actual
14771477
'
14781478

1479+
test_expect_success 'handling of --- lines in conjunction with cut-lines' '
1480+
echo "my-trailer: here" >expected &&
1481+
1482+
git interpret-trailers --parse >actual <<-\EOF &&
1483+
subject
1484+
1485+
my-trailer: here
1486+
---
1487+
# ------------------------ >8 ------------------------
1488+
EOF
1489+
1490+
test_cmp expected actual
1491+
'
1492+
14791493
test_done

wt-status.c

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1007,8 +1007,11 @@ size_t wt_status_locate_end(const char *s, size_t len)
10071007
strbuf_addf(&pattern, "\n%c %s", comment_line_char, cut_line);
10081008
if (starts_with(s, pattern.buf + 1))
10091009
len = 0;
1010-
else if ((p = strstr(s, pattern.buf)))
1011-
len = p - s + 1;
1010+
else if ((p = strstr(s, pattern.buf))) {
1011+
size_t newlen = p - s + 1;
1012+
if (newlen < len)
1013+
len = newlen;
1014+
}
10121015
strbuf_release(&pattern);
10131016
return len;
10141017
}

0 commit comments

Comments
 (0)