Merge branch 'jc/apply-ws-fix-expands'
"git apply --whitespace=fix" used to under-allocate the memory when the fix resulted in a longer text than the original patch. * jc/apply-ws-fix-expands: apply: count the size of postimage correctly apply: make update_pre_post_images() sanity check the given postlen apply.c: typofix
This commit is contained in:
commit
38459ee6af
@ -2230,6 +2230,12 @@ static void update_pre_post_images(struct image *preimage,
|
|||||||
ctx++;
|
ctx++;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (postlen
|
||||||
|
? postlen < new - postimage->buf
|
||||||
|
: postimage->len < new - postimage->buf)
|
||||||
|
die("BUG: caller miscounted postlen: asked %d, orig = %d, used = %d",
|
||||||
|
(int)postlen, (int) postimage->len, (int)(new - postimage->buf));
|
||||||
|
|
||||||
/* Fix the length of the whole thing */
|
/* Fix the length of the whole thing */
|
||||||
postimage->len = new - postimage->buf;
|
postimage->len = new - postimage->buf;
|
||||||
postimage->nr -= reduced;
|
postimage->nr -= reduced;
|
||||||
@ -2385,10 +2391,27 @@ static int match_fragment(struct image *img,
|
|||||||
|
|
||||||
/*
|
/*
|
||||||
* The hunk does not apply byte-by-byte, but the hash says
|
* The hunk does not apply byte-by-byte, but the hash says
|
||||||
* it might with whitespace fuzz. We haven't been asked to
|
* it might with whitespace fuzz. We weren't asked to
|
||||||
* ignore whitespace, we were asked to correct whitespace
|
* ignore whitespace, we were asked to correct whitespace
|
||||||
* errors, so let's try matching after whitespace correction.
|
* errors, so let's try matching after whitespace correction.
|
||||||
*
|
*
|
||||||
|
* While checking the preimage against the target, whitespace
|
||||||
|
* errors in both fixed, we count how large the corresponding
|
||||||
|
* postimage needs to be. The postimage prepared by
|
||||||
|
* apply_one_fragment() has whitespace errors fixed on added
|
||||||
|
* lines already, but the common lines were propagated as-is,
|
||||||
|
* which may become longer when their whitespace errors are
|
||||||
|
* fixed.
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* First count added lines in postimage */
|
||||||
|
postlen = 0;
|
||||||
|
for (i = 0; i < postimage->nr; i++) {
|
||||||
|
if (!(postimage->line[i].flag & LINE_COMMON))
|
||||||
|
postlen += postimage->line[i].len;
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
* The preimage may extend beyond the end of the file,
|
* The preimage may extend beyond the end of the file,
|
||||||
* but in this loop we will only handle the part of the
|
* but in this loop we will only handle the part of the
|
||||||
* preimage that falls within the file.
|
* preimage that falls within the file.
|
||||||
@ -2396,7 +2419,6 @@ static int match_fragment(struct image *img,
|
|||||||
strbuf_init(&fixed, preimage->len + 1);
|
strbuf_init(&fixed, preimage->len + 1);
|
||||||
orig = preimage->buf;
|
orig = preimage->buf;
|
||||||
target = img->buf + try;
|
target = img->buf + try;
|
||||||
postlen = 0;
|
|
||||||
for (i = 0; i < preimage_limit; i++) {
|
for (i = 0; i < preimage_limit; i++) {
|
||||||
size_t oldlen = preimage->line[i].len;
|
size_t oldlen = preimage->line[i].len;
|
||||||
size_t tgtlen = img->line[try_lno + i].len;
|
size_t tgtlen = img->line[try_lno + i].len;
|
||||||
@ -2424,6 +2446,9 @@ static int match_fragment(struct image *img,
|
|||||||
match = (tgtfix.len == fixed.len - fixstart &&
|
match = (tgtfix.len == fixed.len - fixstart &&
|
||||||
!memcmp(tgtfix.buf, fixed.buf + fixstart,
|
!memcmp(tgtfix.buf, fixed.buf + fixstart,
|
||||||
fixed.len - fixstart));
|
fixed.len - fixstart));
|
||||||
|
|
||||||
|
/* Add the length if this is common with the postimage */
|
||||||
|
if (preimage->line[i].flag & LINE_COMMON)
|
||||||
postlen += tgtfix.len;
|
postlen += tgtfix.len;
|
||||||
|
|
||||||
strbuf_release(&tgtfix);
|
strbuf_release(&tgtfix);
|
||||||
|
121
t/t4138-apply-ws-expansion.sh
Executable file
121
t/t4138-apply-ws-expansion.sh
Executable file
@ -0,0 +1,121 @@
|
|||||||
|
#!/bin/sh
|
||||||
|
#
|
||||||
|
# Copyright (C) 2015 Kyle J. McKay
|
||||||
|
#
|
||||||
|
|
||||||
|
test_description='git apply test patches with whitespace expansion.'
|
||||||
|
|
||||||
|
. ./test-lib.sh
|
||||||
|
|
||||||
|
test_expect_success setup '
|
||||||
|
#
|
||||||
|
## create test-N, patchN.patch, expect-N files
|
||||||
|
#
|
||||||
|
|
||||||
|
# test 1
|
||||||
|
printf "\t%s\n" 1 2 3 4 5 6 >before &&
|
||||||
|
printf "\t%s\n" 1 2 3 >after &&
|
||||||
|
printf "%64s\n" a b c >>after &&
|
||||||
|
printf "\t%s\n" 4 5 6 >>after &&
|
||||||
|
git diff --no-index before after |
|
||||||
|
sed -e "s/before/test-1/" -e "s/after/test-1/" >patch1.patch &&
|
||||||
|
printf "%64s\n" 1 2 3 4 5 6 >test-1 &&
|
||||||
|
printf "%64s\n" 1 2 3 a b c 4 5 6 >expect-1 &&
|
||||||
|
|
||||||
|
# test 2
|
||||||
|
printf "\t%s\n" a b c d e f >before &&
|
||||||
|
printf "\t%s\n" a b c >after &&
|
||||||
|
n=10 &&
|
||||||
|
x=1 &&
|
||||||
|
while test $x -lt $n
|
||||||
|
do
|
||||||
|
printf "%63s%d\n" "" $x >>after
|
||||||
|
x=$(( $x + 1 ))
|
||||||
|
done &&
|
||||||
|
printf "\t%s\n" d e f >>after &&
|
||||||
|
git diff --no-index before after |
|
||||||
|
sed -e "s/before/test-2/" -e "s/after/test-2/" >patch2.patch &&
|
||||||
|
printf "%64s\n" a b c d e f >test-2 &&
|
||||||
|
printf "%64s\n" a b c >expect-2 &&
|
||||||
|
x=1 &&
|
||||||
|
while test $x -lt $n
|
||||||
|
do
|
||||||
|
printf "%63s%d\n" "" $x >>expect-2
|
||||||
|
x=$(( $x + 1 ))
|
||||||
|
done &&
|
||||||
|
printf "%64s\n" d e f >>expect-2 &&
|
||||||
|
|
||||||
|
# test 3
|
||||||
|
printf "\t%s\n" a b c d e f >before &&
|
||||||
|
printf "\t%s\n" a b c >after &&
|
||||||
|
n=100 &&
|
||||||
|
x=0 &&
|
||||||
|
while test $x -lt $n
|
||||||
|
do
|
||||||
|
printf "%63s%02d\n" "" $x >>after
|
||||||
|
x=$(( $x + 1 ))
|
||||||
|
done &&
|
||||||
|
printf "\t%s\n" d e f >>after &&
|
||||||
|
git diff --no-index before after |
|
||||||
|
sed -e "s/before/test-3/" -e "s/after/test-3/" >patch3.patch &&
|
||||||
|
printf "%64s\n" a b c d e f >test-3 &&
|
||||||
|
printf "%64s\n" a b c >expect-3 &&
|
||||||
|
x=0 &&
|
||||||
|
while test $x -lt $n
|
||||||
|
do
|
||||||
|
printf "%63s%02d\n" "" $x >>expect-3
|
||||||
|
x=$(( $x + 1 ))
|
||||||
|
done &&
|
||||||
|
printf "%64s\n" d e f >>expect-3 &&
|
||||||
|
|
||||||
|
# test 4
|
||||||
|
>before &&
|
||||||
|
x=0 &&
|
||||||
|
while test $x -lt 50
|
||||||
|
do
|
||||||
|
printf "\t%02d\n" $x >>before
|
||||||
|
x=$(( $x + 1 ))
|
||||||
|
done &&
|
||||||
|
cat before >after &&
|
||||||
|
printf "%64s\n" a b c >>after &&
|
||||||
|
while test $x -lt 100
|
||||||
|
do
|
||||||
|
printf "\t%02d\n" $x >>before
|
||||||
|
printf "\t%02d\n" $x >>after
|
||||||
|
x=$(( $x + 1 ))
|
||||||
|
done &&
|
||||||
|
git diff --no-index before after |
|
||||||
|
sed -e "s/before/test-4/" -e "s/after/test-4/" >patch4.patch &&
|
||||||
|
>test-4 &&
|
||||||
|
x=0 &&
|
||||||
|
while test $x -lt 50
|
||||||
|
do
|
||||||
|
printf "%63s%02d\n" "" $x >>test-4
|
||||||
|
x=$(( $x + 1 ))
|
||||||
|
done &&
|
||||||
|
cat test-4 >expect-4 &&
|
||||||
|
printf "%64s\n" a b c >>expect-4 &&
|
||||||
|
while test $x -lt 100
|
||||||
|
do
|
||||||
|
printf "%63s%02d\n" "" $x >>test-4
|
||||||
|
printf "%63s%02d\n" "" $x >>expect-4
|
||||||
|
x=$(( $x + 1 ))
|
||||||
|
done &&
|
||||||
|
|
||||||
|
git config core.whitespace tab-in-indent,tabwidth=63 &&
|
||||||
|
git config apply.whitespace fix
|
||||||
|
|
||||||
|
'
|
||||||
|
|
||||||
|
# Note that `patch` can successfully apply all patches when run
|
||||||
|
# with the --ignore-whitespace option.
|
||||||
|
|
||||||
|
for t in 1 2 3 4
|
||||||
|
do
|
||||||
|
test_expect_success 'apply with ws expansion (t=$t)' '
|
||||||
|
git apply patch$t.patch &&
|
||||||
|
test_cmp test-$t expect-$t
|
||||||
|
'
|
||||||
|
done
|
||||||
|
|
||||||
|
test_done
|
Loading…
Reference in New Issue
Block a user