/*
 hole.c -- convert huge files with mostly NULs to/from source_hole
 Copyright (C) 2014-2017 Dieter Baron and Thomas Klausner

 This file is part of libzip, a library to manipulate ZIP archives.
 The authors can be contacted at <libzip@nih.at>

 Redistribution and use in source and binary forms, with or without
 modification, are permitted provided that the following conditions
 are met:
 1. Redistributions of source code must retain the above copyright
 notice, this list of conditions and the following disclaimer.
 2. Redistributions in binary form must reproduce the above copyright
 notice, this list of conditions and the following disclaimer in
 the documentation and/or other materials provided with the
 distribution.
 3. The names of the authors may not be used to endorse or promote
 products derived from this software without specific prior
 written permission.

 THIS SOFTWARE IS PROVIDED BY THE AUTHORS ``AS IS'' AND ANY EXPRESS
 OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
 WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
 ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY
 DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
 DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
 GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
 INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
 IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
 OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
 IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 */

#include "config.h"

#include <errno.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#ifdef HAVE_UNISTD_H
#include <unistd.h>
#endif

#ifndef HAVE_GETOPT
#include "getopt.h"
#endif

#include "zip.h"

/* public API */

zip_source_t *source_hole_create(const char *, int flags, zip_error_t *);

const char *prg;


static int
copy_source(zip_source_t *from, zip_source_t *to) {
    zip_uint8_t buf[8192];
    zip_int64_t n;

    if (zip_source_open(from) < 0) {
	fprintf(stderr, "%s: can't open source for reading: %s\n", prg, zip_error_strerror(zip_source_error(from)));
	return -1;
    }

    if (zip_source_begin_write(to) < 0) {
	fprintf(stderr, "%s: can't open source for writing: %s\n", prg, zip_error_strerror(zip_source_error(to)));
	zip_source_close(from);
	return -1;
    }

    while ((n = zip_source_read(from, buf, sizeof(buf))) > 0) {
	if (zip_source_write(to, buf, (zip_uint64_t)n) != n) {
	    fprintf(stderr, "%s: can't write to source: %s\n", prg, zip_error_strerror(zip_source_error(to)));
	    zip_source_close(from);
	    zip_source_rollback_write(to);
	    return -1;
	}
    }

    if (n < 0) {
	fprintf(stderr, "%s: can't read from source: %s\n", prg, zip_error_strerror(zip_source_error(from)));
	zip_source_close(from);
	zip_source_rollback_write(to);
	return -1;
    }

    zip_source_close(from);

    if (zip_source_commit_write(to) < 0) {
	fprintf(stderr, "%s: can't commit source: %s\n", prg, zip_error_strerror(zip_source_error(to)));
	zip_source_rollback_write(to);
	return -1;
    }

    return 0;
}


static zip_source_t *
open_compressed(const char *fname, int flags) {
    zip_error_t error;
    zip_source_t *src;

    zip_error_init(&error);

    if ((src = source_hole_create(fname, flags, &error)) == NULL) {
	fprintf(stderr, "%s: can't open compressed file %s: %s\n", prg, fname, zip_error_strerror(&error));
	zip_error_fini(&error);
	exit(1);
    }

    return src;
}


static zip_source_t *
open_file(const char *fname) {
    zip_error_t error;
    zip_source_t *src;

    zip_error_init(&error);

    if ((src = zip_source_file_create(fname, 0, 0, &error)) == NULL) {
	fprintf(stderr, "%s: can't open file %s: %s\n", prg, fname, zip_error_strerror(&error));
	zip_error_fini(&error);
	exit(1);
    }

    return src;
}


static void
usage(void) {
    fprintf(stderr, "usage: %s [-du] in out\n", prg);
    fprintf(stderr, "\nOptions:\n  -d  decompress in\n  -u  update in\n");
    exit(1);
}


int
main(int argc, char **argv) {
    zip_source_t *from;
    zip_source_t *to;
    int c, err;
    int compress = 1;
    int decompress = 0;

    prg = argv[0];

    while ((c = getopt(argc, argv, "du")) != -1) {
	switch (c) {
	case 'd':
	    compress = 0;
	    decompress = 1;
	    break;

	case 'u':
	    compress = 1;
	    decompress = 1;
	    break;

	default:
	    usage();
	    break;
	}
    }

    if (optind + 2 != argc) {
	usage();
    }

    if (decompress) {
	from = open_compressed(argv[optind], 0);
    }
    else {
	from = open_file(argv[optind]);
    }

    if (compress) {
	to = open_compressed(argv[optind + 1], ZIP_CREATE);
    }
    else {
	to = open_file(argv[optind + 1]);
    }

    err = copy_source(from, to);

    zip_source_free(from);
    zip_source_free(to);

    exit(err < 0 ? 1 : 0);
}
