mirror of the now-defunct rocklinux.org
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

275 lines
9.7 KiB

  1. --- ./doc/gzip.texi.orig 2007-02-06 00:29:04.000000000 +0100
  2. +++ ./doc/gzip.texi 2007-05-16 11:42:11.000000000 +0200
  3. @@ -350,6 +350,14 @@
  4. into the directory and compress all the files it finds there (or
  5. decompress them in the case of @command{gunzip}).
  6. +@item --rsyncable
  7. +While compressing, synchronize the output occasionally based on the
  8. +input. This reduces compression by about 1 percent most cases, but
  9. +means that the @code{rsync} program can take advantage of similarities
  10. +in the uncompressed input when syncronizing two files compressed with
  11. +this flag. @code{gunzip} cannot tell the difference between a
  12. +compressed file created with this option, and one created without it.
  13. +
  14. @item --suffix @var{suf}
  15. @itemx -S @var{suf}
  16. Use suffix @var{suf} instead of @samp{.gz}. Any suffix can be
  17. --- ./deflate.c.orig 2006-12-08 00:53:00.000000000 +0100
  18. +++ ./deflate.c 2007-05-16 11:43:55.000000000 +0200
  19. @@ -135,6 +135,14 @@
  20. #endif
  21. /* Matches of length 3 are discarded if their distance exceeds TOO_FAR */
  22. +#ifndef RSYNC_WIN
  23. +# define RSYNC_WIN 4096
  24. +#endif
  25. +/* Size of rsync window, must be < MAX_DIST */
  26. +
  27. +#define RSYNC_SUM_MATCH(sum) ((sum) % RSYNC_WIN == 0)
  28. +/* Whether window sum matches magic value */
  29. +
  30. /* ===========================================================================
  31. * Local data used by the "longest match" routines.
  32. */
  33. @@ -216,6 +224,8 @@
  34. unsigned near good_match;
  35. /* Use a faster search when the previous match is longer than this */
  36. +local ulg rsync_sum; /* rolling sum of rsync window */
  37. +local ulg rsync_chunk_end; /* next rsync sequence point */
  38. /* Values for max_lazy_match, good_match and max_chain_length, depending on
  39. * the desired pack level (0..9). The values given below have been tuned to
  40. @@ -314,6 +324,10 @@
  41. #endif
  42. /* prev will be initialized on the fly */
  43. + /* rsync params */
  44. + rsync_chunk_end = 0xFFFFFFFFUL;
  45. + rsync_sum = 0;
  46. +
  47. /* Set the default configuration parameters:
  48. */
  49. max_lazy_match = configuration_table[pack_level].max_lazy;
  50. @@ -550,6 +564,8 @@
  51. memcpy((char*)window, (char*)window+WSIZE, (unsigned)WSIZE);
  52. match_start -= WSIZE;
  53. strstart -= WSIZE; /* we now have strstart >= MAX_DIST: */
  54. + if (rsync_chunk_end != 0xFFFFFFFFUL)
  55. + rsync_chunk_end -= WSIZE;
  56. block_start -= (long) WSIZE;
  57. @@ -577,13 +593,46 @@
  58. }
  59. }
  60. +local void rsync_roll(start, num)
  61. + unsigned start;
  62. + unsigned num;
  63. +{
  64. + unsigned i;
  65. +
  66. + if (start < RSYNC_WIN) {
  67. + /* before window fills. */
  68. + for (i = start; i < RSYNC_WIN; i++) {
  69. + if (i == start + num) return;
  70. + rsync_sum += (ulg)window[i];
  71. + }
  72. + num -= (RSYNC_WIN - start);
  73. + start = RSYNC_WIN;
  74. + }
  75. +
  76. + /* buffer after window full */
  77. + for (i = start; i < start+num; i++) {
  78. + /* New character in */
  79. + rsync_sum += (ulg)window[i];
  80. + /* Old character out */
  81. + rsync_sum -= (ulg)window[i - RSYNC_WIN];
  82. + if (rsync_chunk_end == 0xFFFFFFFFUL && RSYNC_SUM_MATCH(rsync_sum))
  83. + rsync_chunk_end = i;
  84. + }
  85. +}
  86. +
  87. +/* ===========================================================================
  88. + * Set rsync_chunk_end if window sum matches magic value.
  89. + */
  90. +#define RSYNC_ROLL(s, n) \
  91. + do { if (rsync) rsync_roll((s), (n)); } while(0)
  92. +
  93. /* ===========================================================================
  94. * Flush the current block, with given end-of-file flag.
  95. * IN assertion: strstart is set to the end of the current match.
  96. */
  97. #define FLUSH_BLOCK(eof) \
  98. flush_block(block_start >= 0L ? (char*)&window[(unsigned)block_start] : \
  99. - (char*)NULL, (long)strstart - block_start, (eof))
  100. + (char*)NULL, (long)strstart - block_start, flush-1, (eof))
  101. /* ===========================================================================
  102. * Processes a new input file and return its compressed length. This
  103. @@ -594,7 +643,7 @@
  104. local off_t deflate_fast()
  105. {
  106. IPos hash_head; /* head of the hash chain */
  107. - int flush; /* set if current block must be flushed */
  108. + int flush; /* set if current block must be flushed, 2=>and padded */
  109. unsigned match_length = 0; /* length of best match */
  110. prev_length = MIN_MATCH-1;
  111. @@ -624,6 +673,7 @@
  112. lookahead -= match_length;
  113. + RSYNC_ROLL(strstart, match_length);
  114. /* Insert new strings in the hash table only if the match length
  115. * is not too large. This saves time but degrades compression.
  116. */
  117. @@ -652,9 +702,14 @@
  118. /* No match, output a literal byte */
  119. Tracevv((stderr,"%c",window[strstart]));
  120. flush = ct_tally (0, window[strstart]);
  121. + RSYNC_ROLL(strstart, 1);
  122. lookahead--;
  123. strstart++;
  124. }
  125. + if (rsync && strstart > rsync_chunk_end) {
  126. + rsync_chunk_end = 0xFFFFFFFFUL;
  127. + flush = 2;
  128. + }
  129. if (flush) FLUSH_BLOCK(0), block_start = strstart;
  130. /* Make sure that we always have enough lookahead, except
  131. @@ -728,6 +783,7 @@
  132. */
  133. lookahead -= prev_length-1;
  134. prev_length -= 2;
  135. + RSYNC_ROLL(strstart, prev_length+1);
  136. do {
  137. strstart++;
  138. INSERT_STRING(strstart, hash_head);
  139. @@ -740,24 +796,39 @@
  140. match_available = 0;
  141. match_length = MIN_MATCH-1;
  142. strstart++;
  143. - if (flush) FLUSH_BLOCK(0), block_start = strstart;
  144. + if (rsync && strstart > rsync_chunk_end) {
  145. + rsync_chunk_end = 0xFFFFFFFFUL;
  146. + flush = 2;
  147. + }
  148. + if (flush) FLUSH_BLOCK(0), block_start = strstart;
  149. } else if (match_available) {
  150. /* If there was no match at the previous position, output a
  151. * single literal. If there was a match but the current match
  152. * is longer, truncate the previous match to a single literal.
  153. */
  154. Tracevv((stderr,"%c",window[strstart-1]));
  155. - if (ct_tally (0, window[strstart-1])) {
  156. - FLUSH_BLOCK(0), block_start = strstart;
  157. - }
  158. + flush = ct_tally (0, window[strstart-1]);
  159. + if (rsync && strstart > rsync_chunk_end) {
  160. + rsync_chunk_end = 0xFFFFFFFFUL;
  161. + flush = 2;
  162. + }
  163. + if (flush) FLUSH_BLOCK(0), block_start = strstart;
  164. + RSYNC_ROLL(strstart, 1);
  165. strstart++;
  166. lookahead--;
  167. } else {
  168. /* There is no previous match to compare with, wait for
  169. * the next step to decide.
  170. */
  171. + if (rsync && strstart > rsync_chunk_end) {
  172. + /* Reset huffman tree */
  173. + rsync_chunk_end = 0xFFFFFFFFUL;
  174. + flush = 2;
  175. + FLUSH_BLOCK(0), block_start = strstart;
  176. + }
  177. match_available = 1;
  178. + RSYNC_ROLL(strstart, 1);
  179. strstart++;
  180. lookahead--;
  181. }
  182. --- ./gzip.c.orig 2007-02-05 21:54:26.000000000 +0100
  183. +++ ./gzip.c 2007-05-16 11:46:16.000000000 +0200
  184. @@ -238,6 +238,7 @@
  185. unsigned insize; /* valid bytes in inbuf */
  186. unsigned inptr; /* index of next byte to be processed in inbuf */
  187. unsigned outcnt; /* bytes in output buffer */
  188. +int rsync = 0; /* make ryncable chunks */
  189. struct option longopts[] =
  190. {
  191. @@ -267,6 +268,7 @@
  192. {"best", 0, 0, '9'}, /* compress better */
  193. {"lzw", 0, 0, 'Z'}, /* make output compatible with old compress */
  194. {"bits", 1, 0, 'b'}, /* max number of bits per code (implies -Z) */
  195. + {"rsyncable", 0, 0, 'R'}, /* make rsync-friendly archive */
  196. { 0, 0, 0, 0 }
  197. };
  198. @@ -348,6 +350,7 @@
  199. " -Z, --lzw produce output compatible with old compress",
  200. " -b, --bits=BITS max number of bits per code (implies -Z)",
  201. #endif
  202. + " --rsyncable Make rsync-friendly archive",
  203. "",
  204. "With no FILE, or when FILE is -, read standard input.",
  205. "",
  206. @@ -476,6 +479,9 @@
  207. recursive = 1;
  208. #endif
  209. break;
  210. + case 'R':
  211. + rsync = 1; break;
  212. +
  213. case 'S':
  214. #ifdef NO_MULTIPLE_DOTS
  215. if (*optarg == '.') optarg++;
  216. --- ./gzip.h.orig 2006-12-11 19:54:39.000000000 +0100
  217. +++ ./gzip.h 2007-05-16 11:41:41.000000000 +0200
  218. @@ -155,6 +155,7 @@
  219. extern unsigned insize; /* valid bytes in inbuf */
  220. extern unsigned inptr; /* index of next byte to be processed in inbuf */
  221. extern unsigned outcnt; /* bytes in output buffer */
  222. +extern int rsync; /* deflate into rsyncable chunks */
  223. extern off_t bytes_in; /* number of input bytes */
  224. extern off_t bytes_out; /* number of output bytes */
  225. @@ -303,7 +304,7 @@
  226. /* in trees.c */
  227. void ct_init OF((ush *attr, int *method));
  228. int ct_tally OF((int dist, int lc));
  229. -off_t flush_block OF((char *buf, ulg stored_len, int eof));
  230. +off_t flush_block OF((char *buf, ulg stored_len, int pad, int eof));
  231. /* in bits.c */
  232. void bi_init OF((file_t zipfile));
  233. --- ./trees.c.orig 2006-11-20 09:40:33.000000000 +0100
  234. +++ ./trees.c 2007-05-16 11:42:11.000000000 +0200
  235. @@ -860,9 +860,10 @@
  236. * trees or store, and output the encoded block to the zip file. This function
  237. * returns the total compressed length for the file so far.
  238. */
  239. -off_t flush_block(buf, stored_len, eof)
  240. +off_t flush_block(buf, stored_len, pad, eof)
  241. char *buf; /* input block, or NULL if too old */
  242. ulg stored_len; /* length of input block */
  243. + int pad; /* pad output to byte boundary */
  244. int eof; /* true if this is the last block for a file */
  245. {
  246. ulg opt_lenb, static_lenb; /* opt_len and static_len in bytes */
  247. @@ -955,6 +956,10 @@
  248. Assert (input_len == bytes_in, "bad input size");
  249. bi_windup();
  250. compressed_len += 7; /* align on byte boundary */
  251. + } else if (pad && (compressed_len % 8) != 0) {
  252. + send_bits((STORED_BLOCK<<1)+eof, 3); /* send block type */
  253. + compressed_len = (compressed_len + 3 + 7) & ~7L;
  254. + copy_block(buf, 0, 1); /* with header */
  255. }
  256. return compressed_len >> 3;