/*
 *  Copyright (C) 2003 Glenn L. McGrath
 *  Copyright (C) 2003-2004 Erik Andersen
 *
 *  This program is free software; you can redistribute it and/or modify
 *  it under the terms of the GNU General Public License as published by
 *  the Free Software Foundation; either version 2 of the License, or
 *  (at your option) any later version.
 *
 *  This program is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *  GNU General Public License for more details.
 *
 *  You should have received a copy of the GNU General Public License
 *  along with this program; if not, write to the Free Software
 *  Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
 */

#include <fcntl.h>
#include <limits.h>
#include <stdio.h>
#include <stdint.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>

#include "busybox.h"


#define FLAG_SILENT	1
#define FLAG_CHECK	2
#define FLAG_WARN	4

/* This might be useful elsewhere */
static unsigned char *hash_bin_to_hex(unsigned char *hash_value,
									  unsigned char hash_length)
{
	int x, len, max;
	unsigned char *hex_value;

	max = (hash_length * 2) + 2;
	hex_value = xmalloc(max);
	for (x = len = 0; x < hash_length; x++) {
		len += snprintf(hex_value + len, max - len, "%02x", hash_value[x]);
	}
	return (hex_value);
}

static uint8_t *hash_file(const char *filename, uint8_t hash_algo)
{
	uint8_t *hash_value_bin;
	uint8_t *hash_value = NULL;
	uint8_t hash_length;
	int src_fd;

	if (strcmp(filename, "-") == 0) {
		src_fd = STDIN_FILENO;
	} else {
		src_fd = open(filename, O_RDONLY);
	}

	if (hash_algo == HASH_MD5) {
		hash_length = 16;
	} else {
		hash_length = 20;
	}

	hash_value_bin = xmalloc(hash_length);

	if ((src_fd != -1) && (hash_fd(src_fd, -1, hash_algo, hash_value_bin) != -2)) {
		hash_value = hash_bin_to_hex(hash_value_bin, hash_length);
	} else {
		bb_perror_msg("%s", filename);
	}

	close(src_fd);

	return(hash_value);
}

/* This could become a common function for md5 as well, by using md5_stream */
extern int hash_files(int argc, char **argv, const uint8_t hash_algo)
{
	int return_value = EXIT_SUCCESS;
	uint8_t *hash_value;

#ifdef CONFIG_FEATURE_MD5_SHA1_SUM_CHECK
	unsigned int flags;

	flags = bb_getopt_ulflags(argc, argv, "scw");
#endif

#ifdef CONFIG_FEATURE_MD5_SHA1_SUM_CHECK
	if (!(flags & FLAG_CHECK)) {
		if (flags & FLAG_SILENT) {
			bb_error_msg_and_die
				("the -s option is meaningful only when verifying checksums");
		} else if (flags & FLAG_WARN) {
			bb_error_msg_and_die
				("the -w option is meaningful only when verifying checksums");
		}
	}
#endif

	if (argc == optind) {
		argv[argc++] = "-";
	}
#ifdef CONFIG_FEATURE_MD5_SHA1_SUM_CHECK
	if (flags & FLAG_CHECK) {
		FILE *pre_computed_stream;
		int count_total = 0;
		int count_failed = 0;
		unsigned char *file_ptr = argv[optind];
		char *line;

		if (optind + 1 != argc) {
			bb_error_msg_and_die
				("only one argument may be specified when using -c");
		}

		if (strcmp(file_ptr, "-") == 0) {
			pre_computed_stream = stdin;
		} else {
			pre_computed_stream = bb_xfopen(file_ptr, "r");
		}

		while ((line = bb_get_chomped_line_from_file(pre_computed_stream)) != NULL) {
			char *filename_ptr;

			count_total++;
			filename_ptr = strstr(line, "  ");
			if (filename_ptr == NULL) {
				if (flags & FLAG_WARN) {
					bb_error_msg("Invalid format");
				}
				free(line);
				continue;
			}
			*filename_ptr = '\0';
			filename_ptr += 2;

			hash_value = hash_file(filename_ptr, hash_algo);

			if (hash_value && (strcmp(hash_value, line) == 0)) {
				if (!(flags & FLAG_SILENT))
					printf("%s: OK\n", filename_ptr);
			} else {
				if (!(flags & FLAG_SILENT))
					printf("%s: FAILED\n", filename_ptr);
				count_failed++;
				return_value = EXIT_FAILURE;
			}
			/* possible free(NULL) */
			free(hash_value);
			free(line);
		}
		if (count_failed && !(flags & FLAG_SILENT)) {
			bb_error_msg("WARNING: %d of %d computed checksums did NOT match",
						 count_failed, count_total);
		}
		if (bb_fclose_nonstdin(pre_computed_stream) == EOF) {
			bb_perror_msg_and_die("Couldnt close file %s", file_ptr);
		}
	} else
#endif
	{
		uint8_t hash_length;

		if (hash_algo == HASH_MD5) {
			hash_length = 16;
		} else {
			hash_length = 20;
		}
		hash_value = xmalloc(hash_length);

		while (optind < argc) {
			unsigned char *file_ptr = argv[optind++];

			hash_value = hash_file(file_ptr, hash_algo);
			if (hash_value == NULL) {
				return_value = EXIT_FAILURE;
			} else {
				printf("%s  %s\n", hash_value, file_ptr);
				free(hash_value);
			}
		}
	}
	return (return_value);
}

#ifdef CONFIG_MD5SUM
extern int md5sum_main(int argc, char **argv)
{
	return(hash_files(argc, argv, HASH_MD5));
}
#endif

#ifdef CONFIG_SHA1SUM
extern int sha1sum_main(int argc, char **argv)
{
	return(hash_files(argc, argv, HASH_SHA1));
}
#endif
