summaryrefslogtreecommitdiff
path: root/match.c
diff options
context:
space:
mode:
authorWayne Davison <wayned@samba.org>2004-08-03 08:05:23 +0000
committerWayne Davison <wayned@samba.org>2004-08-03 08:05:23 +0000
commit7560c17adc73f1f1407f9453c00ddef185d1aad3 (patch)
treee85c8d836274df529edbaa45cc010b4c89dc1557 /match.c
parent9cd339eb39d4090a8b85f8dccd2a823ff563b93a (diff)
downloadrsync-7560c17adc73f1f1407f9453c00ddef185d1aad3.tar.gz
We call map_ptr() with a data range than includes any unmatched data
(which we might need to reference again) in addition to the current rolling-checksum block (this prevents the unmatched data from being lost when we slide the buffer and read more data).
Diffstat (limited to 'match.c')
-rw-r--r--match.c21
1 files changed, 14 insertions, 7 deletions
diff --git a/match.c b/match.c
index f3858e5b..c09a2223 100644
--- a/match.c
+++ b/match.c
@@ -141,11 +141,12 @@ static void matched(int f,struct sum_struct *s,struct map_struct *buf,
static void hash_search(int f,struct sum_struct *s,
struct map_struct *buf, OFF_T len)
{
- OFF_T offset, end;
+ OFF_T offset, end, backup;
unsigned int k;
size_t want_i;
char sum2[SUM_LENGTH];
uint32 s1, s2, sum;
+ int more;
schar *map;
/* want_i is used to encourage adjacent matches, allowing the RLL
@@ -271,14 +272,21 @@ static void hash_search(int f,struct sum_struct *s,
} while (++j < s->count && targets[j].t == t);
null_tag:
+ backup = offset - last_match;
+ /* We sometimes read 1 byte prior to last_match... */
+ if (backup < 0)
+ backup = 0;
+
/* Trim off the first byte from the checksum */
- map = (schar *)map_ptr(buf, offset, k+1);
+ more = offset + k < len;
+ map = (schar *)map_ptr(buf, offset - backup, k + more + backup)
+ + backup;
s1 -= map[0] + CHAR_OFFSET;
s2 -= k * (map[0]+CHAR_OFFSET);
/* Add on the next byte (if there is one) to the checksum */
- if (k < (len-offset)) {
- s1 += (map[k]+CHAR_OFFSET);
+ if (more) {
+ s1 += map[k] + CHAR_OFFSET;
s2 += s1;
} else
--k;
@@ -289,9 +297,8 @@ static void hash_search(int f,struct sum_struct *s,
match. The 3 reads are caused by the
running match, the checksum update and the
literal send. */
- if (offset > last_match
- && offset-last_match >= CHUNK_SIZE+s->blength
- && end-offset > CHUNK_SIZE) {
+ if (backup >= CHUNK_SIZE + s->blength
+ && end - offset > CHUNK_SIZE) {
matched(f,s,buf,offset - s->blength, -2);
}
} while (++offset < end);