summaryrefslogtreecommitdiff
path: root/xdelta3
diff options
context:
space:
mode:
Diffstat (limited to 'xdelta3')
-rw-r--r--xdelta3/xdelta3-main.h175
-rw-r--r--xdelta3/xdelta3.c2
-rw-r--r--xdelta3/xdelta3.h4
3 files changed, 119 insertions, 62 deletions
diff --git a/xdelta3/xdelta3-main.h b/xdelta3/xdelta3-main.h
index d6b237f..964274b 100644
--- a/xdelta3/xdelta3-main.h
+++ b/xdelta3/xdelta3-main.h
@@ -273,7 +273,7 @@ struct _main_merge_list
273struct _main_merge 273struct _main_merge
274{ 274{
275 const char *filename; 275 const char *filename;
276 xoff_t source_size; 276 //xoff_t source_size;
277 main_merge_list link; 277 main_merge_list link;
278}; 278};
279 279
@@ -338,9 +338,12 @@ static int lru_filled = 0;
338/* Hacks for VCDIFF tools */ 338/* Hacks for VCDIFF tools */
339static int allow_fake_source = 0; 339static int allow_fake_source = 0;
340 340
341/* State for xdelta3 recode */ 341/* recode_stream is used by both recode/merge */
342static xd3_stream *recode_stream = NULL; 342static xd3_stream *recode_stream = NULL;
343 343
344/* used by merge command */
345static main_merge recode_merge;
346
344/* This array of compressor types is compiled even if EXTERNAL_COMPRESSION is 347/* This array of compressor types is compiled even if EXTERNAL_COMPRESSION is
345 * false just so the program knows the mapping of IDENT->NAME. */ 348 * false just so the program knows the mapping of IDENT->NAME. */
346static main_extcomp extcomp_types[] = 349static main_extcomp extcomp_types[] =
@@ -358,6 +361,8 @@ static main_extcomp extcomp_types[] =
358 361
359// }; 362// };
360 363
364static int main_input (xd3_cmd cmd, main_file *ifile,
365 main_file *ofile, main_file *sfile);
361static void main_get_appheader (xd3_stream *stream, main_file *ifile, 366static void main_get_appheader (xd3_stream *stream, main_file *ifile,
362 main_file *output, main_file *sfile); 367 main_file *output, main_file *sfile);
363 368
@@ -773,6 +778,8 @@ main_file_close (main_file *xfile)
773static void 778static void
774main_file_cleanup (main_file *xfile) 779main_file_cleanup (main_file *xfile)
775{ 780{
781 XD3_ASSERT (xfile != NULL);
782
776 if (main_file_isopen (xfile)) 783 if (main_file_isopen (xfile))
777 { 784 {
778 main_file_close (xfile); 785 main_file_close (xfile);
@@ -1587,6 +1594,43 @@ main_recode_func (xd3_stream* stream, main_file *ofile)
1587 ******************************************************************/ 1594 ******************************************************************/
1588 1595
1589#if XD3_ENCODER 1596#if XD3_ENCODER
1597/* Modifies static state. */
1598static int
1599main_init_recode_stream (void)
1600{
1601 int ret;
1602 int stream_flags = XD3_ADLER32_NOVER | XD3_SKIP_EMIT;
1603 int recode_flags;
1604 xd3_config recode_config;
1605
1606 XD3_ASSERT (recode_stream == NULL);
1607
1608 if ((recode_stream = (xd3_stream*)
1609 main_malloc(sizeof(xd3_stream))) == NULL)
1610 {
1611 return ENOMEM;
1612 }
1613
1614 recode_flags = (stream_flags & XD3_SEC_TYPE);
1615
1616 recode_config.alloc = main_alloc;
1617 recode_config.freef = main_free1;
1618
1619 xd3_init_config(&recode_config, recode_flags);
1620
1621 if ((ret = main_set_secondary_flags (&recode_config)) ||
1622 (ret = xd3_config_stream (recode_stream, &recode_config)) ||
1623 (ret = xd3_encode_init_buffers (recode_stream)))
1624 {
1625 XPR(NT XD3_LIB_ERRMSG (recode_stream, ret));
1626 xd3_free_stream (recode_stream);
1627 recode_stream = NULL;
1628 return ret;
1629 }
1630
1631 return 0;
1632}
1633
1590/* The first stream in merge order sets the source of the merged 1634/* The first stream in merge order sets the source of the merged
1591 * output. This is where we initialize the static merge_state 1635 * output. This is where we initialize the static merge_state
1592 * variable w/ the initial source information. */ 1636 * variable w/ the initial source information. */
@@ -1599,8 +1643,6 @@ main_init_merge_state (xd3_stream *stream, main_merge *merge)
1599 return XD3_INVALID; 1643 return XD3_INVALID;
1600 } 1644 }
1601 1645
1602 merge->source_size = stream->src->size;
1603
1604 return 0; 1646 return 0;
1605} 1647}
1606 1648
@@ -1609,7 +1651,7 @@ main_init_merge_state (xd3_stream *stream, main_merge *merge)
1609static int 1651static int
1610main_merge_arguments (main_merge_list* merges) 1652main_merge_arguments (main_merge_list* merges)
1611{ 1653{
1612/* int ret; */ 1654 int ret;
1613 main_merge *merge = NULL; 1655 main_merge *merge = NULL;
1614 1656
1615 if (main_merge_list_empty (merges)) 1657 if (main_merge_list_empty (merges))
@@ -1621,12 +1663,37 @@ main_merge_arguments (main_merge_list* merges)
1621 1663
1622 while (!main_merge_list_end (merges, merge)) 1664 while (!main_merge_list_end (merges, merge))
1623 { 1665 {
1624 DP(RINT "TODO MERGE FILE: %s\n", merge->filename); 1666 main_file mfile;
1667 main_file_init (& mfile);
1668 mfile.filename = merge->filename;
1669 mfile.flags = RD_NONEXTERNAL;
1670
1671 if ((ret = main_file_open (& mfile, merge->filename, XO_READ)))
1672 {
1673 return ret;
1674 }
1675
1676 ret = main_input (CMD_MERGE, &mfile, NULL, NULL);
1677
1678 main_file_cleanup (& mfile);
1625 1679
1626/* if ((ret = main_init_merge_state (NULL, NULL))) */ 1680 if (recode_stream != NULL)
1627/* { */ 1681 {
1628/* return ret; */ 1682 xd3_free_stream (recode_stream);
1629/* } */ 1683 main_free (recode_stream);
1684 recode_stream = NULL;
1685 }
1686
1687 if (main_bdata != NULL)
1688 {
1689 main_free (main_bdata);
1690 main_bdata = NULL;
1691 }
1692
1693 if (ret != 0)
1694 {
1695 return ret;
1696 }
1630 1697
1631 merge = main_merge_list_next (merge); 1698 merge = main_merge_list_next (merge);
1632 } 1699 }
@@ -1641,13 +1708,14 @@ main_merge_func (xd3_stream* stream, main_file *no_write)
1641{ 1708{
1642 int ret; 1709 int ret;
1643 1710
1644 if ((ret = main_init_merge_state (stream, NULL))) 1711 if ((ret = main_init_merge_state (stream, &recode_merge)))
1645 { 1712 {
1646 return ret; 1713 return ret;
1647 } 1714 }
1648 1715
1649 // TODO HERE YOU ARE 1716 // TODO HERE YOU ARE
1650 //if ((ret = xd3_n 1717 // Need a new in-memory representation for whole deltas
1718 // xd3_merge_decode()
1651 1719
1652 return 0; 1720 return 0;
1653} 1721}
@@ -2823,10 +2891,6 @@ main_input (xd3_cmd cmd,
2823 xoff_t last_total_out = 0; 2891 xoff_t last_total_out = 0;
2824 long start_time; 2892 long start_time;
2825 int stdout_only = 0; 2893 int stdout_only = 0;
2826#if VCDIFF_TOOLS
2827 int recode_flags;
2828 xd3_config recode_config;
2829#endif
2830 int (*input_func) (xd3_stream*); 2894 int (*input_func) (xd3_stream*);
2831 int (*output_func) (xd3_stream*, main_file *); 2895 int (*output_func) (xd3_stream*, main_file *);
2832 2896
@@ -2864,28 +2928,14 @@ main_input (xd3_cmd cmd,
2864 case CMD_MERGE: 2928 case CMD_MERGE:
2865 /* No source will be read */ 2929 /* No source will be read */
2866 stream_flags |= XD3_ADLER32_NOVER | XD3_SKIP_EMIT; 2930 stream_flags |= XD3_ADLER32_NOVER | XD3_SKIP_EMIT;
2931 ifile->flags |= RD_NONEXTERNAL;
2932 input_func = xd3_decode_input;
2867 2933
2868 XD3_ASSERT (recode_stream == NULL); 2934 if ((ret = main_init_recode_stream ()))
2869 recode_stream = (xd3_stream*) main_malloc(sizeof(xd3_stream)); 2935 {
2870
2871 recode_flags = (stream_flags & XD3_SEC_TYPE);
2872
2873 recode_config.alloc = main_alloc;
2874 recode_config.freef = main_free1;
2875
2876 xd3_init_config(&recode_config, recode_flags);
2877
2878 if ((ret = main_set_secondary_flags (&recode_config)) ||
2879 (ret = xd3_config_stream (recode_stream, &recode_config)) ||
2880 (ret = xd3_encode_init_buffers (recode_stream)))
2881 {
2882
2883 XPR(NT XD3_LIB_ERRMSG (recode_stream, ret));
2884 return EXIT_FAILURE; 2936 return EXIT_FAILURE;
2885 } 2937 }
2886 2938
2887 ifile->flags |= RD_NONEXTERNAL;
2888 input_func = xd3_decode_input;
2889 if (cmd == CMD_RECODE) { output_func = main_recode_func; } 2939 if (cmd == CMD_RECODE) { output_func = main_recode_func; }
2890 else { output_func = main_merge_func; } 2940 else { output_func = main_merge_func; }
2891 break; 2941 break;
@@ -3128,22 +3178,25 @@ main_input (xd3_cmd cmd,
3128 * windows, but I can't think of any reason not to delay 3178 * windows, but I can't think of any reason not to delay
3129 * open.) */ 3179 * open.) */
3130 3180
3131 if (! main_file_isopen (ofile) && 3181 if (ofile != NULL)
3132 (ret = main_open_output (& stream, ofile)) != 0) 3182 {
3133 { 3183 if ((! main_file_isopen (ofile) &&
3134 return EXIT_FAILURE; 3184 (ret = main_open_output (& stream, ofile)) != 0))
3135 } 3185 {
3136 if ((ret = output_func (& stream, ofile)) && 3186 return EXIT_FAILURE;
3137 (ret != PRINTHDR_SPECIAL)) 3187 }
3138 { 3188 if ((ret = output_func (& stream, ofile)) &&
3139 return EXIT_FAILURE; 3189 (ret != PRINTHDR_SPECIAL))
3140 } 3190 {
3141 if (ret == PRINTHDR_SPECIAL) 3191 return EXIT_FAILURE;
3142 { 3192 }
3143 xd3_abort_stream (& stream); 3193 if (ret == PRINTHDR_SPECIAL)
3144 ret = EXIT_SUCCESS; 3194 {
3145 goto done; 3195 xd3_abort_stream (& stream);
3146 } 3196 ret = EXIT_SUCCESS;
3197 goto done;
3198 }
3199 }
3147 ret = 0; 3200 ret = 0;
3148 } 3201 }
3149 3202
@@ -3231,14 +3284,17 @@ main_input (xd3_cmd cmd,
3231done: 3284done:
3232 /* Close the inputs. (ifile must be open, sfile may be open) */ 3285 /* Close the inputs. (ifile must be open, sfile may be open) */
3233 main_file_close (ifile); 3286 main_file_close (ifile);
3234 main_file_close (sfile); 3287 if (sfile != NULL)
3288 {
3289 main_file_close (sfile);
3290 }
3235 3291
3236 /* If output file is not open yet because of delayed-open, it means 3292 /* If output file is not open yet because of delayed-open, it means
3237 * we never encountered a window in the delta, but it could have had 3293 * we never encountered a window in the delta, but it could have had
3238 * a VCDIFF header? TODO: solve this elsewhere. For now, it prints 3294 * a VCDIFF header? TODO: solve this elsewhere. For now, it prints
3239 * "nothing to output" below, but the check doesn't happen in case 3295 * "nothing to output" below, but the check doesn't happen in case
3240 * of option_no_output. */ 3296 * of option_no_output. */
3241 if (! option_no_output) 3297 if (! option_no_output && ofile != NULL)
3242 { 3298 {
3243 if (!stdout_only && ! main_file_isopen (ofile)) 3299 if (!stdout_only && ! main_file_isopen (ofile))
3244 { 3300 {
@@ -3268,17 +3324,17 @@ done:
3268 return EXIT_FAILURE; 3324 return EXIT_FAILURE;
3269 } 3325 }
3270 3326
3271 if (option_verbose > 1) 3327 if (option_verbose > 1 && cmd == CMD_ENCODE)
3272 { 3328 {
3273 XPR(NT "scanner configuration: %s\n", stream.smatcher.name); 3329 XPR(NT "scanner configuration: %s\n", stream.smatcher.name);
3274 XPR(NT "target hash table size: %u\n", stream.small_hash.size); 3330 XPR(NT "target hash table size: %u\n", stream.small_hash.size);
3275 if (sfile->filename != NULL) 3331 if (sfile != NULL && sfile->filename != NULL)
3276 { 3332 {
3277 XPR(NT "source hash table size: %u\n", stream.large_hash.size); 3333 XPR(NT "source hash table size: %u\n", stream.large_hash.size);
3278 } 3334 }
3279 } 3335 }
3280 3336
3281 if (option_verbose > 2) 3337 if (option_verbose > 2 && cmd == CMD_ENCODE)
3282 { 3338 {
3283 XPR(NT "source copies: %"Q"u (%"Q"u bytes)\n", 3339 XPR(NT "source copies: %"Q"u (%"Q"u bytes)\n",
3284 stream.n_scpy, stream.l_scpy); 3340 stream.n_scpy, stream.l_scpy);
@@ -3294,10 +3350,11 @@ done:
3294 { 3350 {
3295 char tm[32]; 3351 char tm[32];
3296 long end_time = get_millisecs_now (); 3352 long end_time = get_millisecs_now ();
3297 XPR(NT "finished in %s; input %"Q"u output %"Q"u bytes (%0.2f%%)\n", 3353 xoff_t nwrite = ofile != NULL ? ofile->nwrite : 0;
3354
3355 XPR(NT "finished in %s; input %"Q"u output %"Q"u bytes (%0.2f%%)\n",
3298 main_format_millis (end_time - start_time, tm), 3356 main_format_millis (end_time - start_time, tm),
3299 ifile->nread, ofile->nwrite, 3357 ifile->nread, nwrite, 100.0 * nwrite / ifile->nread);
3300 100.0 * ofile->nwrite / ifile->nread);
3301 } 3358 }
3302 3359
3303 return EXIT_SUCCESS; 3360 return EXIT_SUCCESS;
diff --git a/xdelta3/xdelta3.c b/xdelta3/xdelta3.c
index fab806a..d38ba39 100644
--- a/xdelta3/xdelta3.c
+++ b/xdelta3/xdelta3.c
@@ -3575,7 +3575,7 @@ xd3_encode_init_buffers (xd3_stream *stream)
3575 } 3575 }
3576 3576
3577 return 0; 3577 return 0;
3578} 3578}
3579 3579
3580/* This function allocates all memory initially used by the encoder. */ 3580/* This function allocates all memory initially used by the encoder. */
3581int 3581int
diff --git a/xdelta3/xdelta3.h b/xdelta3/xdelta3.h
index 440ac17..8adc7ff 100644
--- a/xdelta3/xdelta3.h
+++ b/xdelta3/xdelta3.h
@@ -1065,8 +1065,8 @@ int xd3_config_stream (xd3_stream *stream,
1065 * resources it supplied. */ 1065 * resources it supplied. */
1066int xd3_close_stream (xd3_stream *stream); 1066int xd3_close_stream (xd3_stream *stream);
1067 1067
1068/* This unconditionally closes/frees the stream, future close() will 1068/* This arranges for closes the stream to succeed. Does not free the
1069 succeed. */ 1069 * stream.*/
1070void xd3_abort_stream (xd3_stream *stream); 1070void xd3_abort_stream (xd3_stream *stream);
1071 1071
1072/* xd3_free_stream frees all memory allocated for the stream. The 1072/* xd3_free_stream frees all memory allocated for the stream. The