/*
 *  dumpjffs2.c
 *
 *  Copyright (C) 2003 Thomas Gleixner (tglx@linutronix.de)
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License version 2 as
 * published by the Free Software Foundation.
 *
 * Overview:
 *   This utility dumps the contents of a binary JFFS2 image
 *
 *
 * Bug/ToDo:
 */

#include <errno.h>
#include <stdint.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <fcntl.h>
#include <time.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/param.h>
#include <asm/types.h>
#include <dirent.h>
#include <mtd/jffs2-user.h>
#include <endian.h>
#include <byteswap.h>
#include <getopt.h>
#include "crc32.h"
#include "summary.h"

#define PROGRAM "jffs2dump"
#define VERSION "$Revision: 1.10 $"

#define PAD(x) (((x)+3)&~3)

/* For outputting a byte-swapped version of the input image. */
#define cnv_e32(x) ((jint32_t){bswap_32(x.v32)})
#define cnv_e16(x) ((jint16_t){bswap_16(x.v16)})

#define t32_backwards(x) ({ uint32_t __b = (x); (target_endian==__BYTE_ORDER)?bswap_32(__b):__b; })
#define cpu_to_e32(x) ((jint32_t){t32_backwards(x)})

// Global variables
long	imglen;		// length of image
char	*data;		// image data

void display_help (void)
{
	printf("Usage: " PROGRAM " [OPTION]... INPUTFILE\n"
	       "Dump the contents of a binary JFFS2 image.\n\n"
	       "     --help                   display this help and exit\n"
	       "     --version                display version information and exit\n"
	       " -b, --bigendian              image is big endian\n"
	       " -l, --littleendian           image is little endian\n"
	       " -c, --content                dump image contents\n"
	       " -e, --endianconvert=FNAME    convert image endianness, output to file fname\n"
	       " -r, --recalccrc              recalc name and data crc on endian conversion\n"
	       " -d, --datsize=LEN            size of data chunks, when oob data in binary image (NAND only)\n"
	       " -o, --oobsize=LEN            size of oob data chunk in binary image (NAND only)\n"
	       " -v, --verbose                verbose output\n");
	exit(0);
}

void display_version (void)
{
	printf(PROGRAM " " VERSION "\n"
			"\n"
			"Copyright (C) 2003 Thomas Gleixner \n"
			"\n"
			PROGRAM " comes with NO WARRANTY\n"
			"to the extent permitted by law.\n"
			"\n"
			"You may redistribute copies of " PROGRAM "\n"
			"under the terms of the GNU General Public Licence.\n"
			"See the file `COPYING' for more information.\n");
	exit(0);
}

// Option variables

int 	verbose;		// verbose output
char 	*img;			// filename of image
int	dumpcontent;		// dump image content
int	target_endian = __BYTE_ORDER;	// image endianess
int	convertendian;		// convert endianness
int	recalccrc;		// recalc name and data crc's on endian conversion
char	cnvfile[256];		// filename for conversion output
int	datsize;		// Size of data chunks, when oob data is inside the binary image
int	oobsize;		// Size of oob chunks, when oob data is inside the binary image

void process_options (int argc, char *argv[])
{
	int error = 0;

	for (;;) {
		int option_index = 0;
		static const char *short_options = "blce:rd:o:v";
		static const struct option long_options[] = {
			{"help", no_argument, 0, 0},
			{"version", no_argument, 0, 0},
			{"bigendian", no_argument, 0, 'b'},
			{"littleendian", no_argument, 0, 'l'},
			{"content", no_argument, 0, 'c'},
			{"endianconvert", required_argument, 0, 'e'},
			{"datsize", required_argument, 0, 'd'},
			{"oobsize", required_argument, 0, 'o'},
			{"recalccrc", required_argument, 0, 'r'},
			{"verbose", no_argument, 0, 'v'},
			{0, 0, 0, 0},
		};

		int c = getopt_long(argc, argv, short_options,
				long_options, &option_index);
		if (c == EOF) {
			break;
		}

		switch (c) {
			case 0:
				switch (option_index) {
					case 0:
						display_help();
						break;
					case 1:
						display_version();
						break;
				}
				break;
			case 'v':
				verbose = 1;
				break;
			case 'b':
				target_endian = __BIG_ENDIAN;
				break;
			case 'l':
				target_endian = __LITTLE_ENDIAN;
				break;
			case 'c':
				dumpcontent = 1;
				break;
			case 'd':
				datsize = atoi(optarg);
				break;
			case 'o':
				oobsize = atoi(optarg);
				break;
			case 'e':
				convertendian = 1;
				strcpy (cnvfile, optarg);
				break;
			case 'r':
				recalccrc = 1;
				break;
			case '?':
				error = 1;
				break;
		}
	}

	if ((argc - optind) != 1 || error)
		display_help ();

	img = argv[optind];
}


/*
 *	Dump image contents
 */
void do_dumpcontent (void)
{
	char			*p = data, *p_free_begin;
	union jffs2_node_union 	*node;
	int			empty = 0, dirty = 0;
	char			name[256];
	uint32_t		crc;
	uint16_t		type;
	int			bitchbitmask = 0;
	int			obsolete;

	p_free_begin = NULL;
	while ( p < (data + imglen)) {
		node = (union jffs2_node_union*) p;

		/* Skip empty space */
		if (!p_free_begin)
			p_free_begin = p;
		if (je16_to_cpu (node->u.magic) == 0xFFFF && je16_to_cpu (node->u.nodetype) == 0xFFFF) {
			p += 4;
			empty += 4;
			continue;
		}

		if (p != p_free_begin)
			printf("Empty space found from 0x%08x to 0x%08x\n", p_free_begin-data, p-data);
		p_free_begin = NULL;

		if (je16_to_cpu (node->u.magic) != JFFS2_MAGIC_BITMASK)	{
			if (!bitchbitmask++)
				printf ("Wrong bitmask  at  0x%08x, 0x%04x\n", p - data, je16_to_cpu (node->u.magic));
			p += 4;
			dirty += 4;
			continue;
		}
		bitchbitmask = 0;

		type = je16_to_cpu(node->u.nodetype);
		if ((type & JFFS2_NODE_ACCURATE) != JFFS2_NODE_ACCURATE) {
			obsolete = 1;
			type |= JFFS2_NODE_ACCURATE;
		} else
			obsolete = 0;
		/* Set accurate for CRC check */
		node->u.nodetype = cpu_to_je16(type);

		crc = crc32 (0, node, sizeof (struct jffs2_unknown_node) - 4);
		if (crc != je32_to_cpu (node->u.hdr_crc)) {
			printf ("Wrong hdr_crc  at  0x%08x, 0x%08x instead of 0x%08x\n", p - data, je32_to_cpu (node->u.hdr_crc), crc);
			p += 4;
			dirty += 4;
			continue;
		}

		switch(je16_to_cpu(node->u.nodetype)) {

			case JFFS2_NODETYPE_INODE:
				printf ("%8s Inode      node at 0x%08x, totlen 0x%08x, #ino  %5d, version %5d, isize %8d, csize %8d, dsize %8d, offset %8d\n",
						obsolete ? "Obsolete" : "",
						p - data, je32_to_cpu (node->i.totlen), je32_to_cpu (node->i.ino),
						je32_to_cpu ( node->i.version), je32_to_cpu (node->i.isize),
						je32_to_cpu (node->i.csize), je32_to_cpu (node->i.dsize), je32_to_cpu (node->i.offset));

				crc = crc32 (0, node, sizeof (struct jffs2_raw_inode) - 8);
				if (crc != je32_to_cpu (node->i.node_crc)) {
					printf ("Wrong node_crc at  0x%08x, 0x%08x instead of 0x%08x\n", p - data, je32_to_cpu (node->i.node_crc), crc);
					p += PAD(je32_to_cpu (node->i.totlen));
					dirty += PAD(je32_to_cpu (node->i.totlen));;
					continue;
				}

				crc = crc32(0, p + sizeof (struct jffs2_raw_inode), je32_to_cpu(node->i.csize));
				if (crc != je32_to_cpu(node->i.data_crc)) {
					printf ("Wrong data_crc at  0x%08x, 0x%08x instead of 0x%08x\n", p - data, je32_to_cpu (node->i.data_crc), crc);
					p += PAD(je32_to_cpu (node->i.totlen));
					dirty += PAD(je32_to_cpu (node->i.totlen));;
					continue;
				}

				p += PAD(je32_to_cpu (node->i.totlen));
				break;

			case JFFS2_NODETYPE_DIRENT:
				memcpy (name, node->d.name, node->d.nsize);
				name [node->d.nsize] = 0x0;
				printf ("%8s Dirent     node at 0x%08x, totlen 0x%08x, #pino %5d, version %5d, #ino  %8d, nsize %8d, name %s\n",
						obsolete ? "Obsolete" : "",
						p - data, je32_to_cpu (node->d.totlen), je32_to_cpu (node->d.pino),
						je32_to_cpu ( node->d.version), je32_to_cpu (node->d.ino),
						node->d.nsize, name);

				crc = crc32 (0, node, sizeof (struct jffs2_raw_dirent) - 8);
				if (crc != je32_to_cpu (node->d.node_crc)) {
					printf ("Wrong node_crc at  0x%08x, 0x%08x instead of 0x%08x\n", p - data, je32_to_cpu (node->d.node_crc), crc);
					p += PAD(je32_to_cpu (node->d.totlen));
					dirty += PAD(je32_to_cpu (node->d.totlen));;
					continue;
				}

				crc = crc32(0, p + sizeof (struct jffs2_raw_dirent), node->d.nsize);
				if (crc != je32_to_cpu(node->d.name_crc)) {
					printf ("Wrong name_crc at  0x%08x, 0x%08x instead of 0x%08x\n", p - data, je32_to_cpu (node->d.name_crc), crc);
					p += PAD(je32_to_cpu (node->d.totlen));
					dirty += PAD(je32_to_cpu (node->d.totlen));;
					continue;
				}

				p += PAD(je32_to_cpu (node->d.totlen));
				break;

			case JFFS2_NODETYPE_SUMMARY: {

											 int i;
											 struct jffs2_sum_marker * sm;

											 printf("%8s Inode Sum  node at 0x%08x, totlen 0x%08x, sum_num  %5d, cleanmarker size %5d\n",
													 obsolete ? "Obsolete" : "",
													 p - data,
													 je32_to_cpu (node->s.totlen),
													 je32_to_cpu (node->s.sum_num),
													 je32_to_cpu (node->s.cln_mkr));

											 crc = crc32 (0, node, sizeof (struct jffs2_raw_summary) - 8);
											 if (crc != je32_to_cpu (node->s.node_crc)) {
												 printf ("Wrong node_crc at  0x%08x, 0x%08x instead of 0x%08x\n", p - data, je32_to_cpu (node->s.node_crc), crc);
												 p += PAD(je32_to_cpu (node->s.totlen));
												 dirty += PAD(je32_to_cpu (node->s.totlen));;
												 continue;
											 }

											 crc = crc32(0, p + sizeof (struct jffs2_raw_summary),  je32_to_cpu (node->s.totlen) - sizeof(struct jffs2_raw_summary));
											 if (crc != je32_to_cpu(node->s.sum_crc)) {
												 printf ("Wrong data_crc at  0x%08x, 0x%08x instead of 0x%08x\n", p - data, je32_to_cpu (node->s.sum_crc), crc);
												 p += PAD(je32_to_cpu (node->s.totlen));
												 dirty += PAD(je32_to_cpu (node->s.totlen));;
												 continue;
											 }

											 if (verbose) {
												 void *sp;
												 sp = (p + sizeof(struct jffs2_raw_summary));

												 for(i=0; i<je32_to_cpu(node->s.sum_num); i++) {

													 switch(je16_to_cpu(((struct jffs2_sum_unknown_flash *)sp)->nodetype)) {
														 case JFFS2_NODETYPE_INODE : {

																						 struct jffs2_sum_inode_flash *spi;
																						 spi = sp;

																						 printf ("%14s #ino  %5d,  version %5d, offset 0x%08x, totlen 0x%08x\n",
																								 "",
																								 je32_to_cpu (spi->inode),
																								 je32_to_cpu (spi->version),
																								 je32_to_cpu (spi->offset),
																								 je32_to_cpu (spi->totlen));

																						 sp += JFFS2_SUMMARY_INODE_SIZE;
																						 break;
																					 }

														 case JFFS2_NODETYPE_DIRENT : {

																						  char name[255];
																						  struct jffs2_sum_dirent_flash *spd;
																						  spd = sp;

																						  memcpy(name,spd->name,spd->nsize);
																						  name [spd->nsize] = 0x0;

																						  printf ("%14s dirent offset 0x%08x, totlen 0x%08x, #pino  %5d,  version %5d, #ino  %8d, nsize %8d, name %s \n",
																								  "",
																								  je32_to_cpu (spd->offset),
																								  je32_to_cpu (spd->totlen),
																								  je32_to_cpu (spd->pino),
																								  je32_to_cpu (spd->version),
																								  je32_to_cpu (spd->ino),
																								  spd->nsize,
																								  name);

																						  sp += JFFS2_SUMMARY_DIRENT_SIZE(spd->nsize);
																						  break;
																					  }

														 default :
																					  printf("Unknown summary node!\n");
																					  break;
													 }
												 }

												 sm = (struct jffs2_sum_marker *) ((char *)p + je32_to_cpu(node->s.totlen) - sizeof(struct jffs2_sum_marker));

												 printf("%14s Sum Node Offset  0x%08x, Magic 0x%08x, Padded size 0x%08x\n",
														 "",
														 je32_to_cpu(sm->offset),
														 je32_to_cpu(sm->magic),
														 je32_to_cpu(node->s.padded));
											 }

											 p += PAD(je32_to_cpu (node->s.totlen));
											 break;
										 }

			case JFFS2_NODETYPE_CLEANMARKER:
										 if (verbose) {
											 printf ("%8s Cleanmarker     at 0x%08x, totlen 0x%08x\n",
													 obsolete ? "Obsolete" : "",
													 p - data, je32_to_cpu (node->u.totlen));
										 }
										 p += PAD(je32_to_cpu (node->u.totlen));
										 break;

			case JFFS2_NODETYPE_PADDING:
										 if (verbose) {
											 printf ("%8s Padding    node at 0x%08x, totlen 0x%08x\n",
													 obsolete ? "Obsolete" : "",
													 p - data, je32_to_cpu (node->u.totlen));
										 }
										 p += PAD(je32_to_cpu (node->u.totlen));
										 break;

			case 0xffff:
										 p += 4;
										 empty += 4;
										 break;

			default:
										 if (verbose) {
											 printf ("%8s Unknown    node at 0x%08x, totlen 0x%08x\n",
													 obsolete ? "Obsolete" : "",
													 p - data, je32_to_cpu (node->u.totlen));
										 }
										 p += PAD(je32_to_cpu (node->u.totlen));
										 dirty += PAD(je32_to_cpu (node->u.totlen));

		}
	}

	if (verbose)
		printf ("Empty space: %d, dirty space: %d\n", empty, dirty);
}

/*
 *	Convert endianess
 */
void do_endianconvert (void)
{
	char			*p = data;
	union jffs2_node_union 	*node, newnode;
	int			fd, len;
	jint32_t		mode;
	uint32_t		crc;

	fd = open (cnvfile, O_WRONLY | O_CREAT, 0644);
	if (fd < 0) {
		fprintf (stderr, "Cannot open / create file: %s\n", cnvfile);
		return;
	}

	while ( p < (data + imglen)) {
		node = (union jffs2_node_union*) p;

		/* Skip empty space */
		if (je16_to_cpu (node->u.magic) == 0xFFFF && je16_to_cpu (node->u.nodetype) == 0xFFFF) {
			write (fd, p, 4);
			p += 4;
			continue;
		}

		if (je16_to_cpu (node->u.magic) != JFFS2_MAGIC_BITMASK)	{
			printf ("Wrong bitmask  at  0x%08x, 0x%04x\n", p - data, je16_to_cpu (node->u.magic));
			newnode.u.magic = cnv_e16 (node->u.magic);
			newnode.u.nodetype = cnv_e16 (node->u.nodetype);
			write (fd, &newnode, 4);
			p += 4;
			continue;
		}

		crc = crc32 (0, node, sizeof (struct jffs2_unknown_node) - 4);
		if (crc != je32_to_cpu (node->u.hdr_crc)) {
			printf ("Wrong hdr_crc  at  0x%08x, 0x%08x instead of 0x%08x\n", p - data, je32_to_cpu (node->u.hdr_crc), crc);
		}

		switch(je16_to_cpu(node->u.nodetype)) {

			case JFFS2_NODETYPE_INODE:

				newnode.i.magic = cnv_e16 (node->i.magic);
				newnode.i.nodetype = cnv_e16 (node->i.nodetype);
				newnode.i.totlen = cnv_e32 (node->i.totlen);
				newnode.i.hdr_crc = cpu_to_e32 (crc32 (0, &newnode, sizeof (struct jffs2_unknown_node) - 4));
				newnode.i.ino = cnv_e32 (node->i.ino);
				newnode.i.version = cnv_e32 (node->i.version);
				mode.v32 = node->i.mode.m;
				mode = cnv_e32 (mode);
				newnode.i.mode.m = mode.v32;
				newnode.i.uid = cnv_e16 (node->i.uid);
				newnode.i.gid = cnv_e16 (node->i.gid);
				newnode.i.isize = cnv_e32 (node->i.isize);
				newnode.i.atime = cnv_e32 (node->i.atime);
				newnode.i.mtime = cnv_e32 (node->i.mtime);
				newnode.i.ctime = cnv_e32 (node->i.ctime);
				newnode.i.offset = cnv_e32 (node->i.offset);
				newnode.i.csize = cnv_e32 (node->i.csize);
				newnode.i.dsize = cnv_e32 (node->i.dsize);
				newnode.i.compr = node->i.compr;
				newnode.i.usercompr = node->i.usercompr;
				newnode.i.flags = cnv_e16 (node->i.flags);
				if (recalccrc) {
					len = je32_to_cpu(node->i.csize);
					newnode.i.data_crc = cpu_to_e32 ( crc32(0, p + sizeof (struct jffs2_raw_inode), len));
				} else
					newnode.i.data_crc = cnv_e32 (node->i.data_crc);

				newnode.i.node_crc = cpu_to_e32 (crc32 (0, &newnode, sizeof (struct jffs2_raw_inode) - 8));

				write (fd, &newnode, sizeof (struct jffs2_raw_inode));
				write (fd, p + sizeof (struct jffs2_raw_inode), PAD (je32_to_cpu (node->i.totlen) -  sizeof (struct jffs2_raw_inode)));

				p += PAD(je32_to_cpu (node->i.totlen));
				break;

			case JFFS2_NODETYPE_DIRENT:
				newnode.d.magic = cnv_e16 (node->d.magic);
				newnode.d.nodetype = cnv_e16 (node->d.nodetype);
				newnode.d.totlen = cnv_e32 (node->d.totlen);
				newnode.d.hdr_crc = cpu_to_e32 (crc32 (0, &newnode, sizeof (struct jffs2_unknown_node) - 4));
				newnode.d.pino = cnv_e32 (node->d.pino);
				newnode.d.version = cnv_e32 (node->d.version);
				newnode.d.ino = cnv_e32 (node->d.ino);
				newnode.d.mctime = cnv_e32 (node->d.mctime);
				newnode.d.nsize = node->d.nsize;
				newnode.d.type = node->d.type;
				newnode.d.unused[0] = node->d.unused[0];
				newnode.d.unused[1] = node->d.unused[1];
				newnode.d.node_crc = cpu_to_e32 (crc32 (0, &newnode, sizeof (struct jffs2_raw_dirent) - 8));
				if (recalccrc)
					newnode.d.name_crc = cpu_to_e32 ( crc32(0, p + sizeof (struct jffs2_raw_dirent), node->d.nsize));
				else
					newnode.d.name_crc = cnv_e32 (node->d.name_crc);

				write (fd, &newnode, sizeof (struct jffs2_raw_dirent));
				write (fd, p + sizeof (struct jffs2_raw_dirent), PAD (je32_to_cpu (node->d.totlen) -  sizeof (struct jffs2_raw_dirent)));
				p += PAD(je32_to_cpu (node->d.totlen));
				break;

			case JFFS2_NODETYPE_CLEANMARKER:
			case JFFS2_NODETYPE_PADDING:
				newnode.u.magic = cnv_e16 (node->u.magic);
				newnode.u.nodetype = cnv_e16 (node->u.nodetype);
				newnode.u.totlen = cnv_e32 (node->u.totlen);
				newnode.u.hdr_crc = cpu_to_e32 (crc32 (0, &newnode, sizeof (struct jffs2_unknown_node) - 4));

				write (fd, &newnode, sizeof (struct jffs2_unknown_node));
				len = PAD(je32_to_cpu (node->u.totlen) - sizeof (struct jffs2_unknown_node));
				if (len > 0)
					write (fd, p + sizeof (struct jffs2_unknown_node), len);

				p += PAD(je32_to_cpu (node->u.totlen));
				break;

			case JFFS2_NODETYPE_SUMMARY : {
											  struct jffs2_sum_marker *sm_ptr;
											  int i,sum_len;
											  int counter = 0;

											  newnode.s.magic = cnv_e16 (node->s.magic);
											  newnode.s.nodetype = cnv_e16 (node->s.nodetype);
											  newnode.s.totlen = cnv_e32 (node->s.totlen);
											  newnode.s.hdr_crc = cpu_to_e32 (crc32 (0, &newnode, sizeof (struct jffs2_unknown_node) - 4));
											  newnode.s.sum_num = cnv_e32 (node->s.sum_num);
											  newnode.s.cln_mkr = cnv_e32 (node->s.cln_mkr);
											  newnode.s.padded = cnv_e32 (node->s.padded);

											  newnode.s.node_crc = cpu_to_e32 (crc32 (0, &newnode, sizeof (struct jffs2_raw_summary) - 8));

											  // summary header
											  p += sizeof (struct jffs2_raw_summary);

											  // summary data
											  sum_len = je32_to_cpu (node->s.totlen) - sizeof (struct jffs2_raw_summary) - sizeof (struct jffs2_sum_marker);

											  for (i=0; i<je32_to_cpu (node->s.sum_num); i++) {
												  union jffs2_sum_flash *fl_ptr;

												  fl_ptr = (union jffs2_sum_flash *) p;

												  switch (je16_to_cpu (fl_ptr->u.nodetype)) {
													  case JFFS2_NODETYPE_INODE:

														  fl_ptr->i.nodetype = cnv_e16 (fl_ptr->i.nodetype);
														  fl_ptr->i.inode = cnv_e32 (fl_ptr->i.inode);
														  fl_ptr->i.version = cnv_e32 (fl_ptr->i.version);
														  fl_ptr->i.offset = cnv_e32 (fl_ptr->i.offset);
														  fl_ptr->i.totlen = cnv_e32 (fl_ptr->i.totlen);
														  p += sizeof (struct jffs2_sum_inode_flash);
														  counter += sizeof (struct jffs2_sum_inode_flash);
														  break;

													  case JFFS2_NODETYPE_DIRENT:
														  fl_ptr->d.nodetype = cnv_e16 (fl_ptr->d.nodetype);
														  fl_ptr->d.totlen = cnv_e32 (fl_ptr->d.totlen);
														  fl_ptr->d.offset = cnv_e32 (fl_ptr->d.offset);
														  fl_ptr->d.pino = cnv_e32 (fl_ptr->d.pino);
														  fl_ptr->d.version = cnv_e32 (fl_ptr->d.version);
														  fl_ptr->d.ino = cnv_e32 (fl_ptr->d.ino);
														  p += sizeof (struct jffs2_sum_dirent_flash) + fl_ptr->d.nsize;
														  counter += sizeof (struct jffs2_sum_dirent_flash) + fl_ptr->d.nsize;
														  break;

													  default :
														  printf("Unknown node in summary information!!! nodetype(%x)\n", je16_to_cpu (fl_ptr->u.nodetype));
														  exit(EXIT_FAILURE);
														  break;
												  }

											  }

											  //pad
											  p += sum_len - counter;

											  // summary marker
											  sm_ptr = (struct jffs2_sum_marker *) p;
											  sm_ptr->offset = cnv_e32 (sm_ptr->offset);
											  sm_ptr->magic = cnv_e32 (sm_ptr->magic);
											  p += sizeof (struct jffs2_sum_marker);

											  // generate new crc on sum data
											  newnode.s.sum_crc = cpu_to_e32 ( crc32(0, ((char *) node) + sizeof (struct jffs2_raw_summary),
														  je32_to_cpu (node->s.totlen) - sizeof (struct jffs2_raw_summary)));

											  // write out new node header
											  write(fd, &newnode, sizeof (struct jffs2_raw_summary));
											  // write out new summary data
											  write(fd, &node->s.sum, sum_len + sizeof (struct jffs2_sum_marker));

											  break;
										  }

			case 0xffff:
										  write (fd, p, 4);
										  p += 4;
										  break;

			default:
										  printf ("Unknown node type: 0x%04x at 0x%08x, totlen 0x%08x\n", je16_to_cpu (node->u.nodetype), p - data, je32_to_cpu (node->u.totlen));
										  p += PAD(je32_to_cpu (node->u.totlen));

		}
	}

	close (fd);

}

/*
 * Main program
 */
int main(int argc, char **argv)
{
	int fd;

	process_options(argc, argv);

	/* Open the input file */
	if ((fd = open(img, O_RDONLY)) == -1) {
		perror("open input file");
		exit(1);
	}

	// get image length
	imglen = lseek(fd, 0, SEEK_END);
	lseek (fd, 0, SEEK_SET);

	data = malloc (imglen);
	if (!data) {
		perror("out of memory");
		close (fd);
		exit(1);
	}

	if (datsize && oobsize) {
		int  idx = 0;
		long len = imglen;
		uint8_t oob[oobsize];
		printf ("Peeling data out of combined data/oob image\n");
		while (len) {
			// read image data
			read (fd, &data[idx], datsize);
			read (fd, oob, oobsize);
			idx += datsize;
			imglen -= oobsize;
			len -= datsize + oobsize;
		}

	} else {
		// read image data
		read (fd, data, imglen);
	}
	// Close the input file
	close(fd);

	if (dumpcontent)
		do_dumpcontent ();

	if (convertendian)
		do_endianconvert ();

	// free memory
	free (data);

	// Return happy
	exit (0);
}
