/*
 * (C) Copyright 2003-2004
 * Gary Jennejohn, DENX Software Engineering, garyj@denx.de.
 * Stefan Roese, esd gmbh germany, stefan.roese@esd-electronics.com
 *
 * SPDX-License-Identifier:	GPL-2.0+
 */

#include <common.h>

#include <command.h>
#include <image.h>
#include <asm/byteorder.h>
#include <fat.h>
#include <flash.h>
#include <part.h>

#include "auto_update.h"

#ifdef CONFIG_AUTO_UPDATE

#if !defined(CONFIG_CMD_FAT)
#error "must define CONFIG_CMD_FAT"
#endif

extern au_image_t au_image[];
extern int N_AU_IMAGES;

/* where to load files into memory */
#define LOAD_ADDR ((unsigned char *)0x100000)
#define MAX_LOADSZ 0x1c00000

/* externals */
long do_fat_read (const char *filename, void *buffer,
		  unsigned long maxsize, int dols);

extern block_dev_desc_t ide_dev_desc[CONFIG_SYS_IDE_MAXDEVICE];

int au_check_cksum_valid(int i, long nbytes)
{
	image_header_t *hdr;

	hdr = (image_header_t *)LOAD_ADDR;
#if defined(CONFIG_FIT)
	if (genimg_get_format ((void *)hdr) != IMAGE_FORMAT_LEGACY) {
		puts ("Non legacy image format not supported\n");
		return -1;
	}
#endif

	if ((au_image[i].type == AU_FIRMWARE) &&
	    (au_image[i].size != image_get_data_size (hdr))) {
		printf ("Image %s has wrong size\n", au_image[i].name);
		return -1;
	}

	if (nbytes != (image_get_image_size (hdr))) {
		printf ("Image %s bad total SIZE\n", au_image[i].name);
		return -1;
	}

	/* check the data CRC */
	if (!image_check_dcrc (hdr)) {
		printf ("Image %s bad data checksum\n", au_image[i].name);
		return -1;
	}
	return 0;
}

int au_check_header_valid(int i, long nbytes)
{
	image_header_t *hdr;

	hdr = (image_header_t *)LOAD_ADDR;
#if defined(CONFIG_FIT)
	if (genimg_get_format ((void *)hdr) != IMAGE_FORMAT_LEGACY) {
		puts ("Non legacy image format not supported\n");
		return -1;
	}
#endif

	/* check the easy ones first */
	if (nbytes < image_get_header_size ()) {
		printf ("Image %s bad header SIZE\n", au_image[i].name);
		return -1;
	}
	if (!image_check_magic (hdr) || !image_check_arch (hdr, IH_ARCH_PPC)) {
		printf ("Image %s bad MAGIC or ARCH\n", au_image[i].name);
		return -1;
	}
	if (!image_check_hcrc (hdr)) {
		printf ("Image %s bad header checksum\n", au_image[i].name);
		return -1;
	}

	/* check the type - could do this all in one gigantic if() */
	if (((au_image[i].type & AU_TYPEMASK) == AU_FIRMWARE) &&
	    !image_check_type (hdr, IH_TYPE_FIRMWARE)) {
		printf ("Image %s wrong type\n", au_image[i].name);
		return -1;
	}
	if (((au_image[i].type & AU_TYPEMASK) == AU_SCRIPT) &&
	    !image_check_type (hdr, IH_TYPE_SCRIPT)) {
		printf ("Image %s wrong type\n", au_image[i].name);
		return -1;
	}

	return 0;
}

int au_do_update(int i, long sz)
{
	image_header_t *hdr;
	char *addr;
	long start, end;
	int off, rc;
	uint nbytes;
	int k;

	hdr = (image_header_t *)LOAD_ADDR;
#if defined(CONFIG_FIT)
	if (genimg_get_format ((void *)hdr) != IMAGE_FORMAT_LEGACY) {
		puts ("Non legacy image format not supported\n");
		return -1;
	}
#endif

	switch (au_image[i].type & AU_TYPEMASK) {
	case AU_SCRIPT:
		printf("Executing script %s\n", au_image[i].name);

		/* execute a script */
		if (image_check_type (hdr, IH_TYPE_SCRIPT)) {
			addr = (char *)((char *)hdr + image_get_header_size ());
			/* stick a NULL at the end of the script, otherwise */
			/* parse_string_outer() runs off the end. */
			addr[image_get_data_size (hdr)] = 0;
			addr += 8;

			/*
			 * Replace cr/lf with ;
			 */
			k = 0;
			while (addr[k] != 0) {
				if ((addr[k] == 10) || (addr[k] == 13)) {
					addr[k] = ';';
				}
				k++;
			}

			run_command(addr, 0);
			return 0;
		}

		break;

	case AU_FIRMWARE:
	case AU_NOR:
	case AU_NAND:
		start = au_image[i].start;
		end = au_image[i].start + au_image[i].size - 1;

		/*
		 * do not update firmware when image is already in flash.
		 */
		if (au_image[i].type == AU_FIRMWARE) {
			char *orig = (char*)start;
			char *new  = (char *)((char *)hdr +
					      image_get_header_size ());
			nbytes = image_get_data_size (hdr);

			while (--nbytes) {
				if (*orig++ != *new++) {
					break;
				}
			}
			if (!nbytes) {
				printf ("Skipping firmware update - "
					"images are identical\n");
				break;
			}
		}

		/* unprotect the address range */
		if (((au_image[i].type & AU_FLAGMASK) == AU_PROTECT) ||
		    (au_image[i].type == AU_FIRMWARE)) {
			flash_sect_protect (0, start, end);
		}

		/*
		 * erase the address range.
		 */
		if (au_image[i].type != AU_NAND) {
			printf ("Updating NOR FLASH with image %s\n",
				au_image[i].name);
			debug ("flash_sect_erase(%lx, %lx);\n", start, end);
			flash_sect_erase (start, end);
		}

		udelay(10000);

		/* strip the header - except for the kernel and ramdisk */
		if (au_image[i].type != AU_FIRMWARE) {
			addr = (char *)hdr;
			off = image_get_header_size ();
			nbytes = image_get_image_size (hdr);
		} else {
			addr = (char *)((char *)hdr + image_get_header_size ());
			off = 0;
			nbytes = image_get_data_size (hdr);
		}

		/*
		 * copy the data from RAM to FLASH
		 */
		if (au_image[i].type != AU_NAND) {
			debug ("flash_write(%p, %lx, %x)\n",
			       addr, start, nbytes);
			rc = flash_write ((char *)addr, start,
					  (nbytes + 1) & ~1);
		} else {
			rc = -1;
		}
		if (rc != 0) {
			printf ("Flashing failed due to error %d\n", rc);
			return -1;
		}

		/*
		 * check the dcrc of the copy
		 */
		if (au_image[i].type != AU_NAND) {
			rc = crc32 (0, (uchar *)(start + off),
				    image_get_data_size (hdr));
		}
		if (rc != image_get_dcrc (hdr)) {
			printf ("Image %s Bad Data Checksum After COPY\n",
				au_image[i].name);
			return -1;
		}

		/* protect the address range */
		/* this assumes that ONLY the firmware is protected! */
		if (((au_image[i].type & AU_FLAGMASK) == AU_PROTECT) ||
		    (au_image[i].type == AU_FIRMWARE)) {
			flash_sect_protect (1, start, end);
		}

		break;

	default:
		printf("Wrong image type selected!\n");
	}

	return 0;
}

static void process_macros (const char *input, char *output)
{
	char c, prev;
	const char *varname_start = NULL;
	int inputcnt  = strlen (input);
	int outputcnt = CONFIG_SYS_CBSIZE;
	int state = 0;	/* 0 = waiting for '$'	*/
			/* 1 = waiting for '(' or '{' */
			/* 2 = waiting for ')' or '}' */
			/* 3 = waiting for '''  */
#ifdef DEBUG_PARSER
	char *output_start = output;

	printf ("[PROCESS_MACROS] INPUT len %d: \"%s\"\n",
		strlen(input), input);
#endif

	prev = '\0';			/* previous character */

	while (inputcnt && outputcnt) {
	    c = *input++;
	    inputcnt--;

	    if (state != 3) {
	    /* remove one level of escape characters */
	    if ((c == '\\') && (prev != '\\')) {
		if (inputcnt-- == 0)
			break;
		prev = c;
		c = *input++;
	    }
	    }

	    switch (state) {
	    case 0:			/* Waiting for (unescaped) $ */
		if ((c == '\'') && (prev != '\\')) {
			state = 3;
			break;
		}
		if ((c == '$') && (prev != '\\')) {
			state++;
		} else {
			*(output++) = c;
			outputcnt--;
		}
		break;
	    case 1:			/* Waiting for ( */
		if (c == '(' || c == '{') {
			state++;
			varname_start = input;
		} else {
			state = 0;
			*(output++) = '$';
			outputcnt--;

			if (outputcnt) {
				*(output++) = c;
				outputcnt--;
			}
		}
		break;
	    case 2:			/* Waiting for )	*/
		if (c == ')' || c == '}') {
			int i;
			char envname[CONFIG_SYS_CBSIZE], *envval;
			/* Varname # of chars */
			int envcnt = input - varname_start - 1;

			/* Get the varname */
			for (i = 0; i < envcnt; i++) {
				envname[i] = varname_start[i];
			}
			envname[i] = 0;

			/* Get its value */
			envval = getenv (envname);

			/* Copy into the line if it exists */
			if (envval != NULL)
				while ((*envval) && outputcnt) {
					*(output++) = *(envval++);
					outputcnt--;
				}
			/* Look for another '$' */
			state = 0;
		}
		break;
	    case 3:			/* Waiting for '	*/
		if ((c == '\'') && (prev != '\\')) {
			state = 0;
		} else {
			*(output++) = c;
			outputcnt--;
		}
		break;
	    }
	    prev = c;
	}

	if (outputcnt)
		*output = 0;

#ifdef DEBUG_PARSER
	printf ("[PROCESS_MACROS] OUTPUT len %d: \"%s\"\n",
		strlen (output_start), output_start);
#endif
}

/*
 * this is called from board_init() after the hardware has been set up
 * and is usable. That seems like a good time to do this.
 * Right now the return value is ignored.
 */
int do_auto_update(void)
{
	block_dev_desc_t *stor_dev = NULL;
	long sz;
	int i, res, old_ctrlc;
	char buffer[32];
	char str[80];
	int n;

	if  (ide_dev_desc[0].type != DEV_TYPE_UNKNOWN) {
		stor_dev = get_dev ("ide", 0);
		if (stor_dev == NULL) {
			debug ("ide: unknown device\n");
			return -1;
		}
	}

	if (fat_register_device (stor_dev, 1) != 0) {
		debug ("Unable to register ide disk 0:1\n");
		return -1;
	}

	/*
	 * Check if magic file is present
	 */
	if ((n = do_fat_read (AU_MAGIC_FILE, buffer,
			      sizeof(buffer), LS_NO)) <= 0) {
		debug ("No auto_update magic file (n=%d)\n", n);
		return -1;
	}

#ifdef CONFIG_AUTO_UPDATE_SHOW
	board_auto_update_show (1);
#endif
	puts("\nAutoUpdate Disk detected! Trying to update system...\n");

	/* make sure that we see CTRL-C and save the old state */
	old_ctrlc = disable_ctrlc (0);

	/* just loop thru all the possible files */
	for (i = 0; i < N_AU_IMAGES; i++) {
		/*
		 * Try to expand the environment var in the fname
		 */
		process_macros (au_image[i].name, str);
		strcpy (au_image[i].name, str);

		printf("Reading %s ...", au_image[i].name);
		/* just read the header */
		sz = do_fat_read (au_image[i].name, LOAD_ADDR,
				  image_get_header_size (), LS_NO);
		debug ("read %s sz %ld hdr %d\n",
			au_image[i].name, sz, image_get_header_size ());
		if (sz <= 0 || sz < image_get_header_size ()) {
			puts(" not found\n");
			continue;
		}
		if (au_check_header_valid (i, sz) < 0) {
			puts(" header not valid\n");
			continue;
		}
		sz = do_fat_read (au_image[i].name, LOAD_ADDR,
				  MAX_LOADSZ, LS_NO);
		debug ("read %s sz %ld hdr %d\n",
			au_image[i].name, sz, image_get_header_size ());
		if (sz <= 0 || sz <= image_get_header_size ()) {
			puts(" not found\n");
			continue;
		}
		if (au_check_cksum_valid (i, sz) < 0) {
			puts(" checksum not valid\n");
			continue;
		}
		puts(" done\n");

		do {
			res = au_do_update (i, sz);
			/* let the user break out of the loop */
			if (ctrlc() || had_ctrlc ()) {
				clear_ctrlc ();
				break;
			}
		} while (res < 0);
	}

	/* restore the old state */
	disable_ctrlc (old_ctrlc);

	puts("AutoUpdate finished\n\n");
#ifdef CONFIG_AUTO_UPDATE_SHOW
	board_auto_update_show (0);
#endif

	return 0;
}

int auto_update(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
{
	do_auto_update();

	return 0;
}
U_BOOT_CMD(
	autoupd,	1,	1,	auto_update,
	"Automatically update images",
	""
);
#endif /* CONFIG_AUTO_UPDATE */
