#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <math.h>

#define INT8    char
#define INT16   short
#define INT32   long
#define UINT8   unsigned char
#define UINT16  unsigned short
#define UINT32  unsigned long
#define INT     int
#define UINT    unsigned int
#define FLOAT32 float
#define FLOAT64 double

#define SDRAM_BASE			0x40000000
#define	FLASH_OFFSET		0x00000000

// --------------------------------------------------------------
typedef struct _sflash_img_hdr_t
{
	UINT8 magic[4];
	UINT32 target_addr;
	UINT32 img_offset;
	UINT32 img_size;
	UINT32 hdr_next;
	UINT8 img_name[128];
	UINT8 res[108];

} flash_img_hdr_t;

// --------------------------------------------------------------
void basename(char *pSrc, char *pDst)
{
	int i, size;

	size = strlen(pSrc);

	while(pSrc[size] != '.')
		size--;

	for (i=0; i < size; i++)
		pDst[i] = pSrc[i];

	pDst[i] = 0;

}

// --------------------------------------------------------------
int main(int argc, char *argv[])
{
	char *pFilenameIn;
	char name_flash[1024];
	char name_prj[1024];
	char *pBuf;
	flash_img_hdr_t img_hdr = {0};

	FILE *pFile;
	int filesize;
	long start, end;
	int i;

	if (argc < 2)
	{
		fprintf(stderr, "Usage: flashgen <input file>\n");
		return 1;
	}

	pFilenameIn = argv[1];
	pFile = fopen(pFilenameIn, "rb");
	if (!pFile)
	{
		fprintf(stderr, "Error opening file %s\n", pFilenameIn);
		return 1;
	}

	basename(pFilenameIn, name_prj);
	sprintf(name_flash, "%s.flash.bin", name_prj);

	// determine filesize
	fseek(pFile, 0, SEEK_SET);
	start = ftell(pFile);
	fseek(pFile, 0, SEEK_END);
	end = ftell(pFile);
	fseek(pFile, 0, SEEK_SET);
	filesize = (end-start);

	pBuf = (char*)malloc(filesize);
	fread(pBuf, 1, filesize, pFile);

	fclose(pFile);

	pFile = fopen(name_flash, "wb");
	if (!pFile)
	{
		fprintf(stderr, "Error opening file %s\n", name_flash);
		return 1;
	}

	img_hdr.magic[0] = 'J';
	img_hdr.magic[1] = 'F';
	img_hdr.magic[2] = 'I';
	img_hdr.magic[3] = '1';
	img_hdr.target_addr = SDRAM_BASE;
	img_hdr.img_size = filesize;
	img_hdr.img_offset = FLASH_OFFSET + sizeof(flash_img_hdr_t);
	img_hdr.hdr_next = FLASH_OFFSET;

	fwrite(&img_hdr, sizeof(flash_img_hdr_t), 1, pFile);
	fwrite(pBuf, 1, filesize, pFile);

	fclose(pFile);

	return 0;
}

