/****************************************************************************
 *  SPI flash driver for M25P64
 ****************************************************************************/
#include <common.h>
#include <linux/ctype.h>
#include <asm/io.h>

#if defined(CONFIG_SPI)

/* Application definitions */

#define	NUM_SECTORS 	128	/* number of sectors */
#define SECTOR_SIZE	0x10000
#define NOP_NUM		1000

#define COMMON_SPI_SETTINGS (SPE|MSTR|CPHA|CPOL) /* Settings to the SPI_CTL */
#define TIMOD01 (0x01)	/* stes the SPI to work with core instructions */

/* Flash commands */
#define	SPI_WREN	(0x06)	/*Set Write Enable Latch */
#define	SPI_WRDI	(0x04)	/*Reset Write Enable Latch */
#define	SPI_RDSR	(0x05)	/*Read Status Register */
#define	SPI_WRSR	(0x01)	/*Write Status Register */
#define	SPI_READ	(0x03)	/*Read data from memory */
#define	SPI_FAST_READ	(0x0B)	/*Read data from memory */
#define	SPI_PP		(0x02)	/*Program Data into memory */
#define	SPI_SE		(0xD8)	/*Erase one sector in memory */
#define	SPI_BE		(0xC7)	/*Erase all memory */
#define	WIP		(0x1)	/*Check the write in progress bit of the SPI status register */
#define	WEL		(0x2)	/*Check the write enable bit of the SPI status register */

#define	TIMEOUT		350000000

typedef enum {
	NO_ERR,
	POLL_TIMEOUT,
	INVALID_SECTOR,
	INVALID_BLOCK,
} ERROR_CODE;

void spi_init_f(void);
void spi_init_r(void);
ssize_t spi_read(uchar *, int, uchar *, int);
ssize_t spi_write(uchar *, int, uchar *, int);

char ReadStatusRegister(void);
void Wait_For_SPIF(void);
void SetupSPI(const int spi_setting);
void SPI_OFF(void);
void SendSingleCommand(const int iCommand);

ERROR_CODE GetSectorNumber(unsigned long ulOffset, int *pnSector);
ERROR_CODE EraseBlock(int nBlock);
ERROR_CODE ReadData(unsigned long ulStart, long lCount, int *pnData);
ERROR_CODE WriteData(unsigned long ulStart, long lCount, int *pnData);
ERROR_CODE Wait_For_Status(char Statusbit);
ERROR_CODE Wait_For_WEL(void);

/*
 * Function:    spi_init_f
 * Description: Init SPI-Controller (ROM part)
 * return:      ---
 */
void spi_init_f(void)
{
}

/*
 * Function:    spi_init_r
 * Description: Init SPI-Controller (RAM part) -
 *		 The malloc engine is ready and we can move our buffers to
 *		 normal RAM
 *  return:      ---
 */
void spi_init_r(void)
{
	return;
}

/*
 * Function:    spi_write
 */
ssize_t spi_write(uchar * addr, int alen, uchar * buffer, int len)
{
	unsigned long offset;
	int start_block, end_block;
	int start_byte, end_byte;
	ERROR_CODE result = NO_ERR;
	uchar temp[SECTOR_SIZE];
	int i, num;

	offset = addr[0] << 16 | addr[1] << 8 | addr[2];
	/* Get the start block number */
	result = GetSectorNumber(offset, &start_block);
	if (result == INVALID_SECTOR) {
		printf("Invalid sector! ");
		return 0;
	}
	/* Get the end block number */
	result = GetSectorNumber(offset + len - 1, &end_block);
	if (result == INVALID_SECTOR) {
		printf("Invalid sector! ");
		return 0;
	}

	for (num = start_block; num <= end_block; num++) {
		ReadData(num * SECTOR_SIZE, SECTOR_SIZE, (int *)temp);
		start_byte = num * SECTOR_SIZE;
		end_byte = (num + 1) * SECTOR_SIZE - 1;
		if (start_byte < offset)
			start_byte = offset;
		if (end_byte > (offset + len))
			end_byte = (offset + len - 1);
		for (i = start_byte; i <= end_byte; i++)
			temp[i - num * SECTOR_SIZE] = buffer[i - offset];
		EraseBlock(num);
		result = WriteData(num * SECTOR_SIZE, SECTOR_SIZE, (int *)temp);
		if (result != NO_ERR)
			return 0;
		printf(".");
	}
	return len;
}

/*
 * Function: spi_read
 */
ssize_t spi_read(uchar * addr, int alen, uchar * buffer, int len)
{
	unsigned long offset;
	offset = addr[0] << 16 | addr[1] << 8 | addr[2];
	ReadData(offset, len, (int *)buffer);
	return len;
}

void SendSingleCommand(const int iCommand)
{
	unsigned short dummy;

	/* turns on the SPI in single write mode */
	SetupSPI((COMMON_SPI_SETTINGS | TIMOD01));

	/* sends the actual command to the SPI TX register */
	*pSPI_TDBR = iCommand;
	sync();

	/* The SPI status register will be polled to check the SPIF bit */
	Wait_For_SPIF();

	dummy = *pSPI_RDBR;

	/* The SPI will be turned off */
	SPI_OFF();

}

void SetupSPI(const int spi_setting)
{

	if (icache_status() || dcache_status())
		udelay(CONFIG_CCLK_HZ / 50000000);
	/*sets up the PF10 to be the slave select of the SPI */
	*pPORTF_FER |= (PF10 | PF11 | PF12 | PF13);
	*pSPI_FLG = 0xFF02;
	*pSPI_BAUD = CONFIG_SPI_BAUD;
	*pSPI_CTL = spi_setting;
	sync();

	*pSPI_FLG = 0xFD02;
	sync();
}

void SPI_OFF(void)
{

	*pSPI_CTL = 0x0400;	/* disable SPI */
	*pSPI_FLG = 0;
	*pSPI_BAUD = 0;
	sync();
	udelay(CONFIG_CCLK_HZ / 50000000);

}

void Wait_For_SPIF(void)
{
	unsigned short dummyread;
	while ((*pSPI_STAT & TXS)) ;
	while (!(*pSPI_STAT & SPIF)) ;
	while (!(*pSPI_STAT & RXS)) ;
	/* Read dummy to empty the receive register */
	dummyread = *pSPI_RDBR;
}

ERROR_CODE Wait_For_WEL(void)
{
	int i;
	char status_register = 0;
	ERROR_CODE ErrorCode = NO_ERR;

	for (i = 0; i < TIMEOUT; i++) {
		status_register = ReadStatusRegister();
		if ((status_register & WEL)) {
			ErrorCode = NO_ERR;
			break;
		}
		ErrorCode = POLL_TIMEOUT;	/* Time out error */
	};

	return ErrorCode;
}

ERROR_CODE Wait_For_Status(char Statusbit)
{
	int i;
	char status_register = 0xFF;
	ERROR_CODE ErrorCode = NO_ERR;

	for (i = 0; i < TIMEOUT; i++) {
		status_register = ReadStatusRegister();
		if (!(status_register & Statusbit)) {
			ErrorCode = NO_ERR;
			break;
		}
		ErrorCode = POLL_TIMEOUT;	/* Time out error */
	};

	return ErrorCode;
}

char ReadStatusRegister(void)
{
	char status_register = 0;

	SetupSPI((COMMON_SPI_SETTINGS | TIMOD01));	/* Turn on the SPI */

	*pSPI_TDBR = SPI_RDSR;	/* send instruction to read status register */
	sync();
	Wait_For_SPIF();	/*wait until the instruction has been sent */
	*pSPI_TDBR = 0;		/*send dummy to receive the status register */
	sync();
	Wait_For_SPIF();	/*wait until the data has been sent */
	status_register = *pSPI_RDBR;	/*read the status register */

	SPI_OFF();		/* Turn off the SPI */

	return status_register;
}

ERROR_CODE GetSectorNumber(unsigned long ulOffset, int *pnSector)
{
	int nSector = 0;
	ERROR_CODE ErrorCode = NO_ERR;

	if (ulOffset > (NUM_SECTORS * 0x10000 - 1)) {
		ErrorCode = INVALID_SECTOR;
		return ErrorCode;
	}

	nSector = (int)ulOffset / 0x10000;
	*pnSector = nSector;

	return ErrorCode;
}

ERROR_CODE EraseBlock(int nBlock)
{
	unsigned long ulSectorOff = 0x0, ShiftValue;
	ERROR_CODE ErrorCode = NO_ERR;

	/* if the block is invalid just return */
	if ((nBlock < 0) || (nBlock > NUM_SECTORS)) {
		ErrorCode = INVALID_BLOCK;
		return ErrorCode;
	}
	/* figure out the offset of the block in flash */
	if ((nBlock >= 0) && (nBlock < NUM_SECTORS)) {
		ulSectorOff = (nBlock * SECTOR_SIZE);

	} else {
		ErrorCode = INVALID_BLOCK;
		return ErrorCode;
	}

	/* A write enable instruction must previously have been executed */
	SendSingleCommand(SPI_WREN);

	/* The status register will be polled to check the write enable latch "WREN" */
	ErrorCode = Wait_For_WEL();

	if (POLL_TIMEOUT == ErrorCode) {
		printf("SPI Erase block error\n");
		return ErrorCode;
	} else

	/* Turn on the SPI to send single commands */
	SetupSPI((COMMON_SPI_SETTINGS | TIMOD01));

	/*
	 * Send the erase block command to the flash followed by the 24 address
	 * to point to the start of a sector
	 */
	*pSPI_TDBR = SPI_SE;
	sync();
	Wait_For_SPIF();
	/* Send the highest byte of the 24 bit address at first */
	ShiftValue = (ulSectorOff >> 16);
	*pSPI_TDBR = ShiftValue;
	sync();
	/* Wait until the instruction has been sent */
	Wait_For_SPIF();
	/* Send the middle byte of the 24 bit address  at second */
	ShiftValue = (ulSectorOff >> 8);
	*pSPI_TDBR = ShiftValue;
	sync();
	/* Wait until the instruction has been sent */
	Wait_For_SPIF();
	/* Send the lowest byte of the 24 bit address finally */
	*pSPI_TDBR = ulSectorOff;
	sync();
	/* Wait until the instruction has been sent */
	Wait_For_SPIF();

	/* Turns off the SPI */
	SPI_OFF();

	/* Poll the status register to check the Write in Progress bit */
	/* Sector erase takes time */
	ErrorCode = Wait_For_Status(WIP);

	/* block erase should be complete */
	return ErrorCode;
}

/*
 * ERROR_CODE ReadData()
 * Read a value from flash for verify purpose
 * Inputs:	unsigned long ulStart - holds the SPI start address
 *			int pnData - pointer to store value read from flash
 *			long lCount - number of elements to read
 */
ERROR_CODE ReadData(unsigned long ulStart, long lCount, int *pnData)
{
	unsigned long ShiftValue;
	char *cnData;
	int i;

	/* Pointer cast to be able to increment byte wise */

	cnData = (char *)pnData;
	/* Start SPI interface */
	SetupSPI((COMMON_SPI_SETTINGS | TIMOD01));

#ifdef CONFIG_SPI_FLASH_FAST_READ
	/* Send the read command to SPI device */
	*pSPI_TDBR = SPI_FAST_READ;
#else
	/* Send the read command to SPI device */
	*pSPI_TDBR = SPI_READ;
#endif
	sync();
	/* Wait until the instruction has been sent */
	Wait_For_SPIF();
	/* Send the highest byte of the 24 bit address at first */
	ShiftValue = (ulStart >> 16);
	/* Send the byte to the SPI device */
	*pSPI_TDBR = ShiftValue;
	sync();
	/* Wait until the instruction has been sent */
	Wait_For_SPIF();
	/* Send the middle byte of the 24 bit address  at second */
	ShiftValue = (ulStart >> 8);
	/* Send the byte to the SPI device */
	*pSPI_TDBR = ShiftValue;
	sync();
	/* Wait until the instruction has been sent */
	Wait_For_SPIF();
	/* Send the lowest byte of the 24 bit address finally */
	*pSPI_TDBR = ulStart;
	sync();
	/* Wait until the instruction has been sent */
	Wait_For_SPIF();

#ifdef CONFIG_SPI_FLASH_FAST_READ
	/* Send dummy for FAST_READ */
	*pSPI_TDBR = 0;
	sync();
	/* Wait until the instruction has been sent */
	Wait_For_SPIF();
#endif

	/* After the SPI device address has been placed on the MOSI pin the data can be */
	/* received on the MISO pin. */
	for (i = 0; i < lCount; i++) {
		*pSPI_TDBR = 0;
		sync();
		while (!(*pSPI_STAT & RXS)) ;
		*cnData++ = *pSPI_RDBR;

		if ((i >= SECTOR_SIZE) && (i % SECTOR_SIZE == 0))
			printf(".");
	}

	/* Turn off the SPI */
	SPI_OFF();

	return NO_ERR;
}

ERROR_CODE WriteFlash(unsigned long ulStartAddr, long lTransferCount,
		      int *iDataSource, long *lWriteCount)
{

	unsigned long ulWAddr;
	long lWTransferCount = 0;
	int i;
	char iData;
	char *temp = (char *)iDataSource;
	ERROR_CODE ErrorCode = NO_ERR;

	/* First, a Write Enable Command must be sent to the SPI. */
	SendSingleCommand(SPI_WREN);

	/*
	 * Second, the SPI Status Register will be tested whether the
	 * Write Enable Bit has been set
	 */
	ErrorCode = Wait_For_WEL();
	if (POLL_TIMEOUT == ErrorCode) {
		printf("SPI Write Time Out\n");
		return ErrorCode;
	} else
		/* Third, the 24 bit address will be shifted out
		 * the SPI MOSI bytewise.
		 * Turns the SPI on
		 */
		SetupSPI((COMMON_SPI_SETTINGS | TIMOD01));
	*pSPI_TDBR = SPI_PP;
	sync();
	/*wait until the instruction has been sent */
	Wait_For_SPIF();
	ulWAddr = (ulStartAddr >> 16);
	*pSPI_TDBR = ulWAddr;
	sync();
	/*wait until the instruction has been sent */
	Wait_For_SPIF();
	ulWAddr = (ulStartAddr >> 8);
	*pSPI_TDBR = ulWAddr;
	sync();
	/*wait until the instruction has been sent */
	Wait_For_SPIF();
	ulWAddr = ulStartAddr;
	*pSPI_TDBR = ulWAddr;
	sync();
	/*wait until the instruction has been sent */
	Wait_For_SPIF();
	/*
	 * Fourth, maximum number of 256 bytes will be taken from the Buffer
	 * and sent to the SPI device.
	 */
	for (i = 0; (i < lTransferCount) && (i < 256); i++, lWTransferCount++) {
		iData = *temp;
		*pSPI_TDBR = iData;
		sync();
		/*wait until the instruction has been sent */
		Wait_For_SPIF();
		temp++;
	}

	/* Turns the SPI off */
	SPI_OFF();

	/*
	 * Sixth, the SPI Write in Progress Bit must be toggled to ensure the
	 * programming is done before start of next transfer
	 */
	ErrorCode = Wait_For_Status(WIP);

	if (POLL_TIMEOUT == ErrorCode) {
		printf("SPI Program Time out!\n");
		return ErrorCode;
	} else

		*lWriteCount = lWTransferCount;

	return ErrorCode;
}

ERROR_CODE WriteData(unsigned long ulStart, long lCount, int *pnData)
{

	unsigned long ulWStart = ulStart;
	long lWCount = lCount, lWriteCount;
	long *pnWriteCount = &lWriteCount;

	ERROR_CODE ErrorCode = NO_ERR;

	while (lWCount != 0) {
		ErrorCode = WriteFlash(ulWStart, lWCount, pnData, pnWriteCount);

		/*
		 * After each function call of WriteFlash the counter
		 * must be adjusted
		 */
		lWCount -= *pnWriteCount;

		/* Also, both address pointers must be recalculated. */
		ulWStart += *pnWriteCount;
		pnData += *pnWriteCount / 4;
	}

	/* return the appropriate error code */
	return ErrorCode;
}

#endif				/* CONFIG_SPI */
