/*
 * isosize.c - Andries Brouwer, 000608
 *
 * use header info to find size of iso9660 file system
 * output a number - useful in scripts
 *
 * Synopsis:
 *    isosize [-x] [-d <num>] <filename>
 *        where "-x" gives length in sectors and sector size while
 *              without this argument the size is given in bytes
 *        without "-x" gives length in bytes unless "-d <num>" is
 *		given. In the latter case the length in bytes divided
 *		by <num> is given
 *
 *  Version 2.03 2000/12/21
 *     - add "-d <num>" option and use long long to fix things > 2 GB
 *  Version 2.02 2000/10/11
 *     - error messages on IO failures [D. Gilbert]
 *
 */
#include <stdio.h>
#include <stdlib.h>
#include <getopt.h>
#include <fcntl.h>
#include <unistd.h>
#include <errno.h>

#include "nls.h"
#include "c.h"
#include "strutils.h"
#include "closestream.h"

#define ISODCL(from, to) (to - from + 1)

static int is_iso(int fd)
{
	char label[8];
	if (pread(fd, &label, 8, 0x8000) == -1)
		return 1;
	return memcmp(&label, &"\1CD001\1", 8);
}

static int isonum_721(unsigned char *p)
{
	return ((p[0] & 0xff)
		| ((p[1] & 0xff) << 8));
}

static int isonum_722(unsigned char *p)
{
	return ((p[1] & 0xff)
		| ((p[0] & 0xff) << 8));
}

static int isonum_723(unsigned char *p, int xflag)
{
	int le = isonum_721(p);
	int be = isonum_722(p + 2);
	if (xflag && le != be)
		/* translation is useless */
		warnx("723error: le=%d be=%d", le, be);
	return (le);
}

static int isonum_731(unsigned char *p)
{
	return ((p[0] & 0xff)
		| ((p[1] & 0xff) << 8)
		| ((p[2] & 0xff) << 16)
		| ((p[3] & 0xff) << 24));
}

static int isonum_732(unsigned char *p)
{
	return ((p[3] & 0xff)
		| ((p[2] & 0xff) << 8)
		| ((p[1] & 0xff) << 16)
		| ((p[0] & 0xff) << 24));
}

static int isonum_733(unsigned char *p, int xflag)
{
	int le = isonum_731(p);
	int be = isonum_732(p + 4);
	if (xflag && le != be)
		/* translation is useless */
		warnx("733error: le=%d be=%d", le, be);
	return (le);
}

struct iso_primary_descriptor
{
	unsigned char type			[ISODCL (   1,	  1)]; /* 711 */
	unsigned char id			[ISODCL (   2,	  6)];
	unsigned char version			[ISODCL (   7,	  7)]; /* 711 */
	unsigned char unused1			[ISODCL (   8,	  8)];
	unsigned char system_id			[ISODCL (   9,	 40)]; /* auchars */
	unsigned char volume_id			[ISODCL (  41,	 72)]; /* duchars */
	unsigned char unused2			[ISODCL (  73,	 80)];
	unsigned char volume_space_size		[ISODCL (  81,	 88)]; /* 733 */
	unsigned char unused3			[ISODCL (  89,	120)];
	unsigned char volume_set_size		[ISODCL ( 121,	124)]; /* 723 */
	unsigned char volume_sequence_number	[ISODCL ( 125,	128)]; /* 723 */
	unsigned char logical_block_size	[ISODCL ( 129,	132)]; /* 723 */
	unsigned char path_table_size		[ISODCL ( 133,	140)]; /* 733 */
	unsigned char type_l_path_table		[ISODCL ( 141,	144)]; /* 731 */
	unsigned char opt_type_l_path_table	[ISODCL ( 145,	148)]; /* 731 */
	unsigned char type_m_path_table		[ISODCL ( 149,	152)]; /* 732 */
	unsigned char opt_type_m_path_table	[ISODCL ( 153,	156)]; /* 732 */
	unsigned char root_directory_record	[ISODCL ( 157,	190)]; /* 9.1 */
	unsigned char volume_set_id		[ISODCL ( 191,	318)]; /* duchars */
	unsigned char publisher_id		[ISODCL ( 319,	446)]; /* achars */
	unsigned char preparer_id		[ISODCL ( 447,	574)]; /* achars */
	unsigned char application_id		[ISODCL ( 575,	702)]; /* achars */
	unsigned char copyright_file_id		[ISODCL ( 703,	739)]; /* 7.5 dchars */
	unsigned char abstract_file_id		[ISODCL ( 740,	776)]; /* 7.5 dchars */
	unsigned char bibliographic_file_id	[ISODCL ( 777,	813)]; /* 7.5 dchars */
	unsigned char creation_date		[ISODCL ( 814,	830)]; /* 8.4.26.1 */
	unsigned char modification_date		[ISODCL ( 831,	847)]; /* 8.4.26.1 */
	unsigned char expiration_date		[ISODCL ( 848,	864)]; /* 8.4.26.1 */
	unsigned char effective_date		[ISODCL ( 865,	881)]; /* 8.4.26.1 */
	unsigned char file_structure_version	[ISODCL ( 882,	882)]; /* 711 */
	unsigned char unused4			[ISODCL ( 883,	883)];
	unsigned char application_data		[ISODCL ( 884, 1395)];
	unsigned char unused5			[ISODCL (1396, 2048)];
};

static void isosize(int argc, char *filenamep, int xflag, long divisor)
{
	int fd, nsecs, ssize;
	struct iso_primary_descriptor ipd;

	if ((fd = open(filenamep, O_RDONLY)) < 0)
		err(EXIT_FAILURE, _("cannot open %s"), filenamep);
	if (is_iso(fd))
		warnx(_("%s: might not be an ISO filesystem"), filenamep);

	if (lseek(fd, 16 << 11, 0) == (off_t) - 1)
		err(EXIT_FAILURE, _("seek error on %s"), filenamep);

	if (read(fd, &ipd, sizeof(ipd)) <= 0)
		err(EXIT_FAILURE, _("read error on %s"), filenamep);

	nsecs = isonum_733(ipd.volume_space_size, xflag);
	/* isonum_723 returns nowadays always 2048 */
	ssize = isonum_723(ipd.logical_block_size, xflag);

	if (1 < argc)
		printf("%s: ", filenamep);
	if (xflag) {
		printf(_("sector count: %d, sector size: %d\n"), nsecs, ssize);
	} else {
		long long product = nsecs;

		if (divisor == 0)
			printf("%lld\n", product * ssize);
		else if (divisor == ssize)
			printf("%d\n", nsecs);
		else
			printf("%lld\n", (product * ssize) / divisor);
	}

	close(fd);
}

static void __attribute__((__noreturn__)) usage(FILE *out)
{
	fputs(USAGE_HEADER, out);
	fprintf(out,
		_(" %s [options] <iso9660_image_file>\n"),
		program_invocation_short_name);

	fputs(USAGE_SEPARATOR, out);
	fputs(_("Show the length of an ISO-9660 filesystem.\n"), out);

	fputs(USAGE_OPTIONS, out);
	fputs(_(" -d, --divisor=<number>  divide the amount of bytes by <number>\n"), out);
	fputs(_(" -x, --sectors           show sector count and size\n"), out);
	fputs(USAGE_SEPARATOR, out);
	fputs(USAGE_HELP, out);
	fputs(USAGE_VERSION, out);
	fprintf(out, USAGE_MAN_TAIL("isosize(8)"));

	exit(out == stderr ? EXIT_FAILURE : EXIT_SUCCESS);
}

int main(int argc, char **argv)
{
	int j, ct, opt, xflag = 0;
	long divisor = 0;

	static const struct option longopts[] = {
		{"divisor", required_argument, 0, 'd'},
		{"sectors", no_argument, 0, 'x'},
		{"version", no_argument, 0, 'V'},
		{"help", no_argument, 0, 'h'},
		{NULL, 0, 0, 0}
	};

	setlocale(LC_ALL, "");
	bindtextdomain(PACKAGE, LOCALEDIR);
	textdomain(PACKAGE);
	atexit(close_stdout);

	while ((opt = getopt_long(argc, argv, "d:xVh", longopts, NULL)) != -1)
		switch (opt) {
		case 'd':
			divisor =
			    strtol_or_err(optarg,
					  _("invalid divisor argument"));
			break;
		case 'x':
			xflag = 1;
			break;
		case 'V':
			printf(UTIL_LINUX_VERSION);
			return EXIT_SUCCESS;
		case 'h':
			usage(stdout);
		default:
			usage(stderr);
		}

	ct = argc - optind;

	if (ct <= 0)
		usage(stderr);

	for (j = optind; j < argc; j++)
		isosize(ct, argv[j], xflag, divisor);

	return EXIT_SUCCESS;
}
