/*
 * This file contains SFF related definitions
 */
#ifndef PRISM_SFF_H
#define PRISM_SFF_H

#include <common.h>
#include <command.h>
#include <environment.h>
#include <i2c.h>
#include <malloc.h>
#include <asm/byteorder.h>
#include "mvTypes.h"

/**************************************************
 * Definitions
 **************************************************/
#if defined(SFF_CMD_DBG)
	#if defined(PRISM_DBG)
		#undef PRISM_DBG
	#endif
	#define PRISM_DBG(format, args...)  \
		printf("%s: "format"\n", __func__, ## args)
#elif !defined(PRISM_DBG)
	#define PRISM_DBG(format, args...)
#endif

#define SFF_ADDR_A0    0x50      /* A0 = 10100000X   b7:1 address, b0 r/w bit */
#define SFF_ADDR_A2    0x51      /* A0 = 10100001X   b7:1 address, b0 r/w bit */

#define SFF_BUF_LEN    128
#define SFF_ADDR_LEN   1         /* SFF address length */
#define CC_BASE        "ccb"
#define CC_EXT         "cce"
#define CC_DMI         "ccd"

#if (defined(CONFIG_POST) && defined(CONFIG_SYS_POST_I2C))
	#define I2C_ADDR_LIST {						\
		SFF_ADDR_A0,						\
		SFF_ADDR_A2,						\
		0x64,							\
		CONFIG_SYS_I2C_RTC_ADDR,				\
	}

	#define SFF_LOG(format, args...)
	#define SFF_ERR_LOG(format, args...) \
		post_log("I2C: "format"\n", ## args)
#else
	#define SFF_LOG(format, args...)  printf(format"\n", ## args)
	#define SFF_ERR_LOG               SFF_LOG
#endif  /* end of CONFIG_POST & CONFIG_SYS_POST_I2C */

/* SFF field starting data address and data length */
/* A0 starting address per group */
#define SFF_A0_BASE_ID   0
#define SFF_A0_EXT_ID    64
#define SFF_A0_VEND_SPEC 96
#define SFF_A0_END       127
/* A0 group lengths */
#define A0_BASE_ID_L			(SFF_A0_EXT_ID - SFF_A0_BASE_ID)
#define A0_EXT_ID_L				(SFF_A0_VEND_SPEC - SFF_A0_EXT_ID)
#define A0_VEND_SPEC_L		(SFF_A0_END + 1 - SFF_A0_VEND_SPEC)

/* A0 checksum addresses */
#define SFF_A0_CC_BASE   63
#define SFF_A0_CC_EXT    95

/* A2 starting address per group */
#define SFF_A2_ALRM_WARN   0
#define SFF_A2_EXT_CONSTS  56
#define SFF_A2_RT_DIAG     96
#define SFF_A2_END         179
/* A2 group lengths */
#define A2_ALRM_WARN_L     (SFF_A2_EXT_CONSTS - SFF_A2_ALRM_WARN)
#define A2_CC_DMI_CHKSUM_L (SFF_A2_RT_DIAG - SFF_A2_ALRM_WARN)


/**************************************************
 * local data and function
 **************************************************/

/* SFF verify-checksum command entry */
typedef struct csum_vfy_func_entry_ {
	char *name;      /* cmd string */
	int chip;        /* SFF addr */
	int daddr;       /* data addr to access of the SFF addr */
	int nbytes;      /* number of bytes to access */
} csum_vfy_func_entry, sff_addr;

/* Command lookup table
 * - For verifying CCB_BASE and CC_EXC checksums, read in all of data in
 *   the range including checksum bytes.
 */
static const csum_vfy_func_entry sff_csum_vfy_sub_cmds[] = {
/* name,	chip,				daddr,					nbyte */
	{CC_BASE, SFF_ADDR_A0, SFF_A0_BASE_ID,   A0_BASE_ID_L},
	{CC_EXT,  SFF_ADDR_A0, SFF_A0_EXT_ID,    A0_EXT_ID_L},
	{CC_DMI,  SFF_ADDR_A2, SFF_A2_ALRM_WARN, A2_CC_DMI_CHKSUM_L},
};
#define SIZEOF_CSUM_VFY_SUB_CMD_TBL	(sizeof(sff_csum_vfy_sub_cmds)/sizeof(csum_vfy_func_entry))

/*
 * 8-bit checksum
 * (Copied the routine from mv_feroceon/mv_kw2_mv_cmd.c)
 */
static uchar checksum8(uchar *start, uchar len, uchar csum)
{
	uchar sum = csum;
	volatile uchar *startp = (volatile uchar *)start;

	do {
		sum += *startp;
		startp++;
	} while(--len);

	return (sum);
} /* end of checksum */


static int sff_read_verify_checksum(char *csum_name)
{
	int ret = 1;	/* default fail */
	int i;
	uchar sff_buf[SFF_BUF_LEN];
	uchar	csum = 0;
	csum_vfy_func_entry *ptable = (csum_vfy_func_entry *)sff_csum_vfy_sub_cmds;
	MV_BOOL	found = MV_FALSE;

	do {
		/* Lookup the command table and find the sub-cmd entry */
		for (i = 0; i < SIZEOF_CSUM_VFY_SUB_CMD_TBL; i++, ptable++) {
			PRISM_DBG("name=%s, len=%d\n", ptable->name, (int)strlen(ptable->name));
			if (!strncmp(csum_name, ptable->name, (int)strlen(ptable->name))) {
				/* Found the diag func, return entry address */
				found = MV_TRUE;
				break;
			}
		}
		if (found != MV_TRUE) {
			PRISM_DBG("Invalid command....\n");
			break;			/* not found. exit */
		}

		/* read and verify the checksum
		 * buffer all read data, so we can make sure data is read only once.
		 */
		ret = i2c_read(
		        ptable->chip, ptable->daddr, SFF_ADDR_LEN,
		        sff_buf, ptable->nbytes);
		if (ret != 0) {
			SFF_ERR_LOG("failed to access the sff chip addr (0x%02x).\n",
			            (ptable->chip<<1));
			break;
		}

		/* Calculate 8-bit checksum */
		csum = checksum8(sff_buf, (ptable->nbytes-1), 0);
		PRISM_DBG("calculated csum=0x%02X, csum=0x%02X",
		        csum, sff_buf[ptable->nbytes-1]);
		if (csum != sff_buf[ptable->nbytes-1]) {
			SFF_ERR_LOG("csum mismatched - chip=0x%02x, off= 0x%02x, csum=0x%02x, "
			        "calculated csum=0x%02x",
			        (ptable->chip<<1), (ptable->daddr +ptable->nbytes-1),
			        sff_buf[ptable->nbytes-1], csum);
			ret = 1;	/* fail */
		} else {
			SFF_LOG("csum matched - chip=0x%02x, off= 0x%02x, csum=0x%02x",
			        (ptable->chip<<1), (ptable->daddr+ptable->nbytes-1), csum);
			ret = 0;	/* success */
		}

	} while (0);

	return(ret);
} /* end of sff_read_print_group */

#endif /* end of PRISM_SFF_H */
