[PATCH] Support cloning packed repo from dumb http servers.
[gitweb.git] / diff-delta.c
index 480f03cd16841945352c176b50300613fbf71175..b2ae7b5e6c3b4aa409ccfa60f67d5c8eb1690504 100644 (file)
@@ -203,7 +203,8 @@ static void delta_cleanup(bdfile_t *bdf)
 
 void *diff_delta(void *from_buf, unsigned long from_size,
                 void *to_buf, unsigned long to_size,
-                unsigned long *delta_size)
+                unsigned long *delta_size,
+                unsigned long max_size)
 {
        int i, outpos, outsize, inscnt, csize, msize, moff;
        unsigned int fp;
@@ -227,28 +228,22 @@ void *diff_delta(void *from_buf, unsigned long from_size,
        top = to_buf + to_size;
 
        /* store reference buffer size */
-       orig = out + outpos++;
-       *orig = i = 0;
-       do {
-               if (from_size & 0xff) {
-                       *orig |= (1 << i);
-                       out[outpos++] = from_size;
-               }
-               i++;
-               from_size >>= 8;
-       } while (from_size);
+       out[outpos++] = from_size;
+       from_size >>= 7;
+       while (from_size) {
+               out[outpos - 1] |= 0x80;
+               out[outpos++] = from_size;
+               from_size >>= 7;
+       }
 
        /* store target buffer size */
-       orig = out + outpos++;
-       *orig = i = 0;
-       do {
-               if (to_size & 0xff) {
-                       *orig |= (1 << i);
-                       out[outpos++] = to_size;
-               }
-               i++;
-               to_size >>= 8;
-       } while (to_size);
+       out[outpos++] = to_size;
+       to_size >>= 7;
+       while (to_size) {
+               out[outpos - 1] |= 0x80;
+               out[outpos++] = to_size;
+               to_size >>= 7;
+       }
 
        inscnt = 0;
        moff = 0;
@@ -311,6 +306,12 @@ void *diff_delta(void *from_buf, unsigned long from_size,
                        *orig = i;
                }
 
+               if (max_size && outpos > max_size) {
+                       free(out);
+                       delta_cleanup(&bdf);
+                       return NULL;
+               }
+
                /* next time around the largest possible output is 1 + 4 + 3 */
                if (outpos > outsize - 8) {
                        void *tmp = out;