You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@subversion.apache.org by ju...@apache.org on 2013/11/04 20:42:00 UTC
svn commit: r1538734 - in /subversion/branches/1.7.x-r1426762/subversion:
libsvn_diff/diff_file.c tests/libsvn_diff/diff-diff3-test.c
Author: julianfoad
Date: Mon Nov 4 19:41:59 2013
New Revision: 1538734
URL: http://svn.apache.org/r1538734
Log:
On the 1.7.x-r1426762 branch, backport r1426762 from trunk.
Modified:
subversion/branches/1.7.x-r1426762/subversion/libsvn_diff/diff_file.c
subversion/branches/1.7.x-r1426762/subversion/tests/libsvn_diff/diff-diff3-test.c
Modified: subversion/branches/1.7.x-r1426762/subversion/libsvn_diff/diff_file.c
URL: http://svn.apache.org/viewvc/subversion/branches/1.7.x-r1426762/subversion/libsvn_diff/diff_file.c?rev=1538734&r1=1538733&r2=1538734&view=diff
==============================================================================
--- subversion/branches/1.7.x-r1426762/subversion/libsvn_diff/diff_file.c (original)
+++ subversion/branches/1.7.x-r1426762/subversion/libsvn_diff/diff_file.c Mon Nov 4 19:41:59 2013
@@ -860,17 +860,24 @@ datasource_get_next_token(apr_uint32_t *
last_chunk = offset_to_chunk(file->size);
- if (curp == endp
- && last_chunk == file->chunk)
+ /* Are we already at the end of a chunk? */
+ if (curp == endp)
{
- return SVN_NO_ERROR;
+ /* Are we at EOF */
+ if (last_chunk == file->chunk)
+ return SVN_NO_ERROR; /* EOF */
+
+ /* Or right before an identical suffix in the next chunk? */
+ if (file->chunk + 1 == file->suffix_start_chunk
+ && file->suffix_offset_in_chunk == 0)
+ return SVN_NO_ERROR;
}
/* Stop when we encounter the identical suffix. If suffix scanning was not
* performed, suffix_start_chunk will be -1, so this condition will never
* be true. */
if (file->chunk == file->suffix_start_chunk
- && curp - file->buffer == file->suffix_offset_in_chunk)
+ && (curp - file->buffer) == file->suffix_offset_in_chunk)
return SVN_NO_ERROR;
/* Allocate a new token, or fetch one from the "reusable tokens" list. */
@@ -939,6 +946,14 @@ datasource_get_next_token(apr_uint32_t *
endp += length;
file->endp = endp;
+ /* Issue #4283: Normally we should have checked for reaching the skipped
+ suffix here, but because we assume that a suffix always starts on a
+ line and token boundary we rely on catching the suffix earlier in this
+ function.
+
+ When changing things here, make sure the whitespace settings are
+ applied, or we mught not reach the exact suffix boundary as token
+ boundary. */
SVN_ERR(read_chunk(file->file, file->path,
curp, length,
chunk_to_offset(file->chunk),
Modified: subversion/branches/1.7.x-r1426762/subversion/tests/libsvn_diff/diff-diff3-test.c
URL: http://svn.apache.org/viewvc/subversion/branches/1.7.x-r1426762/subversion/tests/libsvn_diff/diff-diff3-test.c?rev=1538734&r1=1538733&r2=1538734&view=diff
==============================================================================
--- subversion/branches/1.7.x-r1426762/subversion/tests/libsvn_diff/diff-diff3-test.c (original)
+++ subversion/branches/1.7.x-r1426762/subversion/tests/libsvn_diff/diff-diff3-test.c Mon Nov 4 19:41:59 2013
@@ -2526,6 +2526,123 @@ test_token_compare(apr_pool_t *pool)
return SVN_NO_ERROR;
}
+/* A back-ported copy of the 1.8 public function of the same name. */
+static void
+svn_stringbuf_insert(svn_stringbuf_t *str,
+ apr_size_t pos,
+ const char *bytes,
+ apr_size_t count)
+{
+ if (bytes + count > str->data && bytes < str->data + str->blocksize)
+ {
+ /* special case: BYTES overlaps with this string -> copy the source */
+ const char *temp = apr_pstrndup(str->pool, bytes, count);
+ svn_stringbuf_insert(str, pos, temp, count);
+ }
+ else
+ {
+ if (pos > str->len)
+ pos = str->len;
+
+ svn_stringbuf_ensure(str, str->len + count);
+ memmove(str->data + pos + count, str->data + pos, str->len - pos + 1);
+ memcpy(str->data + pos, bytes, count);
+
+ str->len += count;
+ }
+}
+
+/* Issue #4283, 'When identical suffix started at a chunk boundary,
+ incorrect diff was generated'.
+ The magic number used in this test, (1<<17) and 50 are CHUNK_SIZE
+ and SUFFIX_LINES_TO_KEEP from ../../libsvn_diff/diff_file.c, respectively.
+ */
+#define ORIGINAL_CONTENTS_PATTERN "0123456789abcde\n"
+#define INSERTED_LINE "0123456789ABCDE\n"
+static svn_error_t *
+test_identical_suffix(apr_pool_t *pool)
+{
+ apr_size_t lines_in_chunk = (1 << 17)
+ / (sizeof(ORIGINAL_CONTENTS_PATTERN) - 1);
+ /* To let identical suffix start at a chunk boundary,
+ insert a line at before (SUFFIX_LINES_TO_KEEP + 1) lines
+ from tail of the previous chunk. */
+ apr_size_t insert_pos = lines_in_chunk
+#ifdef SUFFIX_LINES_TO_KEEP
+ - SUFFIX_LINES_TO_KEEP
+#else
+ - 50
+#endif
+ - 1;
+ apr_size_t i;
+ svn_stringbuf_t *original, *modified;
+
+ /* The original contents become like this.
+
+ $ hexdump -C identical-suffix-original
+ 00000000 30 31 32 33 34 35 36 37 38 39 61 62 63 64 65 0a |0123456789abcde.|
+ *
+ 00020400
+ */
+ original = svn_stringbuf_create_ensure((1 << 17) + 1024, pool);
+ for (i = 0; i < lines_in_chunk + 64; i++)
+ {
+ svn_stringbuf_appendbytes(original, ORIGINAL_CONTENTS_PATTERN,
+ sizeof(ORIGINAL_CONTENTS_PATTERN) - 1);
+ }
+
+ /* The modified contents become like this.
+
+ $ hexdump -C identical-suffix-modified
+ 00000000 30 31 32 33 34 35 36 37 38 39 61 62 63 64 65 0a |0123456789abcde.|
+ *
+ 00000400 30 31 32 33 34 35 36 37 38 39 41 42 43 44 45 0a |0123456789ABCDE.|
+ 00000410 30 31 32 33 34 35 36 37 38 39 61 62 63 64 65 0a |0123456789abcde.|
+ *
+ 0001fcd0 30 31 32 33 34 35 36 37 38 39 41 42 43 44 45 0a |0123456789ABCDE.|
+ 0001fce0 30 31 32 33 34 35 36 37 38 39 61 62 63 64 65 0a |0123456789abcde.|
+ *
+ 00020420
+ */
+ modified = svn_stringbuf_dup(original, pool);
+ svn_stringbuf_insert(modified,
+ 64 * (sizeof(ORIGINAL_CONTENTS_PATTERN) - 1),
+ INSERTED_LINE, sizeof(INSERTED_LINE) - 1);
+ svn_stringbuf_insert(modified,
+ insert_pos * (sizeof(ORIGINAL_CONTENTS_PATTERN) - 1),
+ INSERTED_LINE, sizeof(INSERTED_LINE) - 1);
+
+ SVN_ERR(two_way_diff("identical-suffix-original",
+ "identical-suffix-modified",
+ original->data, modified->data,
+ apr_psprintf(pool,
+ "--- identical-suffix-original" NL
+ "+++ identical-suffix-modified" NL
+ "@@ -62,6 +62,7 @@" NL
+ " " ORIGINAL_CONTENTS_PATTERN
+ " " ORIGINAL_CONTENTS_PATTERN
+ " " ORIGINAL_CONTENTS_PATTERN
+ "+" INSERTED_LINE
+ " " ORIGINAL_CONTENTS_PATTERN
+ " " ORIGINAL_CONTENTS_PATTERN
+ " " ORIGINAL_CONTENTS_PATTERN
+ "@@ -%u,6 +%u,7 @@" NL
+ " " ORIGINAL_CONTENTS_PATTERN
+ " " ORIGINAL_CONTENTS_PATTERN
+ " " ORIGINAL_CONTENTS_PATTERN
+ "+" INSERTED_LINE
+ " " ORIGINAL_CONTENTS_PATTERN
+ " " ORIGINAL_CONTENTS_PATTERN
+ " " ORIGINAL_CONTENTS_PATTERN,
+ 1 + (unsigned int)insert_pos - 3 - 1,
+ 1 + (unsigned int)insert_pos - 3),
+ NULL, pool));
+
+ return SVN_NO_ERROR;
+}
+#undef ORIGINAL_CONTENTS_PATTERN
+#undef INSERTED_LINE
+
/* ========================================================================== */
struct svn_test_descriptor_t test_funcs[] =
@@ -2559,5 +2676,7 @@ struct svn_test_descriptor_t test_funcs[
"offset of the normalized token"),
SVN_TEST_PASS2(test_token_compare,
"compare tokes at the chunk boundary"),
+ SVN_TEST_PASS2(test_identical_suffix,
+ "identical suffix starts at the boundary of a chunk"),
SVN_TEST_NULL
};