diff -ruN mercurial-2.6.2/mercurial/mpatch.c mercurial-2.6.2_patched/mercurial/mpatch.c --- mercurial-2.6.2/mercurial/mpatch.c 2019-10-10 12:04:17.473702325 +0100 +++ mercurial-2.6.2_patched/mercurial/mpatch.c 2019-10-10 12:03:55.538520431 +0100 @@ -285,6 +285,7 @@ struct flist *l; struct frag *lt; const char *data = bin + 12, *end = bin + len; + int pos = 0; /* assume worst case size, we won't have many of these lists */ l = lalloc(len / 12); @@ -293,25 +294,23 @@ lt = l->tail; - while (data <= end) { - lt->start = getbe32(bin); - lt->end = getbe32(bin + 4); - lt->len = getbe32(bin + 8); + while (pos >= 0 && pos < (len - 11)) { + lt->start = getbe32(bin + pos); + lt->end = getbe32(bin + pos + 4); + lt->len = getbe32(bin + pos + 8); if (lt->start < 0 || lt->start > lt->end || lt->len < 0) break; /* sanity check */ - bin = data; - if (!safeadd(lt->len, &bin)) { + if (!safeadd(12, &pos)) { break; /* big data + big (bogus) len can wrap around */ } - lt->data = data; - data = bin; - if (!safeadd(12, &data)) { + lt->data = bin + pos; + if (!safeadd(lt->len, &pos)) { break; } lt++; } - if (bin != end) { + if (pos != len) { if (!PyErr_Occurred()) PyErr_SetString(mpatch_Error, "patch cannot be decoded"); lfree(l);