]> wimlib.net Git - wimlib/blobdiff - src/write.c
Win32: Do not create lookup table entries for 0 length streams
[wimlib] / src / write.c
index e0d898eea3c516ebb3a2f2b69a645a76dd3802af..8b09449036b2ac52ad016278fe6f0f4180a91700 100644 (file)
 
 #include <limits.h>
 
-#if defined(__WIN32__) && !defined(INVALID_HANDLE_VALUE)
-#  define INVALID_HANDLE_VALUE ((HANDLE)(-1))
-#endif
-
 /* Chunk table that's located at the beginning of each compressed resource in
  * the WIM.  (This is not the on-disk format; the on-disk format just has an
  * array of offsets.) */
@@ -98,6 +94,8 @@ begin_wim_resource_chunk_tab(const struct wim_lookup_table_entry *lte,
        size_t alloc_size = sizeof(struct chunk_table) + num_chunks * sizeof(u64);
        struct chunk_table *chunk_tab = CALLOC(1, alloc_size);
 
+       DEBUG("Begin chunk table for stream with size %"PRIu64, size);
+
        if (!chunk_tab) {
                ERROR("Failed to allocate chunk table for %"PRIu64" byte "
                      "resource", size);
@@ -172,16 +170,18 @@ get_compress_func(int out_ctype)
  * Returns 0 on success; nonzero on failure.
  */
 static int
-write_wim_resource_chunk(const void *chunk, unsigned chunk_size,
-                        FILE *out_fp, compress_func_t compress,
-                        struct chunk_table *chunk_tab)
+write_wim_resource_chunk(const void * restrict chunk,
+                        unsigned chunk_size,
+                        FILE * restrict out_fp,
+                        compress_func_t compress,
+                        struct chunk_table * restrict chunk_tab)
 {
-       const u8 *out_chunk;
+       const void *out_chunk;
        unsigned out_chunk_size;
        if (compress) {
-               u8 *compressed_chunk = alloca(chunk_size);
+               void *compressed_chunk = alloca(chunk_size);
 
-               out_chunk_size = compress(chunk, chunk_size, compressed_chunk);
+               out_chunk_size = (*compress)(chunk, chunk_size, compressed_chunk);
                if (out_chunk_size) {
                        /* Write compressed */
                        out_chunk = compressed_chunk;
@@ -212,8 +212,9 @@ write_wim_resource_chunk(const void *chunk, unsigned chunk_size,
  * @compressed_size_p.
  */
 static int
-finish_wim_resource_chunk_tab(struct chunk_table *chunk_tab,
-                             FILE *out_fp, u64 *compressed_size_p)
+finish_wim_resource_chunk_tab(struct chunk_table * restrict chunk_tab,
+                             FILE * restrict out_fp,
+                             u64 * restrict compressed_size_p)
 {
        size_t bytes_written;
        if (fseeko(out_fp, chunk_tab->file_offset, SEEK_SET) != 0) {
@@ -261,7 +262,8 @@ fflush_and_ftruncate(FILE *out_fp, off_t offset)
 }
 
 static int
-finalize_and_check_sha1(SHA_CTX *sha_ctx, struct wim_lookup_table_entry *lte)
+finalize_and_check_sha1(SHA_CTX * restrict sha_ctx,
+                       struct wim_lookup_table_entry * restrict lte)
 {
        u8 md[SHA1_HASH_SIZE];
        sha1_final(md, sha_ctx);
@@ -289,25 +291,16 @@ struct write_resource_ctx {
 };
 
 static int
-write_resource_cb(const void *chunk, size_t chunk_size, void *_ctx)
+write_resource_cb(const void *restrict chunk, size_t chunk_size,
+                 void *restrict _ctx)
 {
        struct write_resource_ctx *ctx = _ctx;
 
        if (ctx->doing_sha)
                sha1_update(&ctx->sha_ctx, chunk, chunk_size);
-
-       if (ctx->compress) {
-               return write_wim_resource_chunk(chunk, chunk_size,
-                                               ctx->out_fp, ctx->compress,
-                                               ctx->chunk_tab);
-       } else {
-               if (fwrite(chunk, 1, chunk_size, ctx->out_fp) != chunk_size) {
-                       ERROR_WITH_ERRNO("Error writing to output WIM");
-                       return WIMLIB_ERR_WRITE;
-               } else {
-                       return 0;
-               }
-       }
+       return write_wim_resource_chunk(chunk, chunk_size,
+                                       ctx->out_fp, ctx->compress,
+                                       ctx->chunk_tab);
 }
 
 /*
@@ -681,6 +674,7 @@ do_write_stream_list(struct list_head *stream_list,
                                         * just skip to the next stream. */
                                        DEBUG("Discarding duplicate stream of length %"PRIu64,
                                              wim_resource_size(lte));
+                                       lte->no_progress = 0;
                                        goto skip_to_progress;
                                }
                        }
@@ -695,6 +689,7 @@ do_write_stream_list(struct list_head *stream_list,
                 * the SHA1 message digest yet.  */
                wimlib_assert(lte->out_refcnt != 0);
                lte->deferred = 0;
+               lte->no_progress = 0;
                ret = (*write_stream_cb)(lte, write_stream_ctx);
                if (ret)
                        break;
@@ -708,7 +703,7 @@ do_write_stream_list(struct list_head *stream_list,
                        lte->unhashed = 0;
                }
        skip_to_progress:
-               if (progress_func) {
+               if (!lte->no_progress) {
                        do_write_streams_progress(progress,
                                                  progress_func,
                                                  wim_resource_size(lte));
@@ -742,8 +737,11 @@ do_write_stream_list_serial(struct list_head *stream_list,
 static inline int
 write_flags_to_resource_flags(int write_flags)
 {
-       return (write_flags & WIMLIB_WRITE_FLAG_RECOMPRESS) ?
-                       WIMLIB_RESOURCE_FLAG_RECOMPRESS : 0;
+       int resource_flags = 0;
+
+       if (write_flags & WIMLIB_WRITE_FLAG_RECOMPRESS)
+               resource_flags |= WIMLIB_RESOURCE_FLAG_RECOMPRESS;
+       return resource_flags;
 }
 
 static int
@@ -1185,6 +1183,7 @@ main_thread_process_next_stream(struct wim_lookup_table_entry *lte, void *_ctx)
        } else {
                ret = submit_stream_for_compression(lte, ctx);
        }
+       lte->no_progress = 1;
        return ret;
 }
 
@@ -1313,7 +1312,7 @@ write_stream_list_parallel(struct list_head *stream_list,
                goto out_join;
        ret = do_write_stream_list(stream_list, lookup_table,
                                   main_thread_process_next_stream,
-                                  &ctx, NULL, NULL);
+                                  &ctx, progress_func, progress);
        if (ret)
                goto out_destroy_ctx;