/*
 * (C) Copyright 2002
 * Rich Ireland, Enterasys Networks, rireland@enterasys.com.
 * Keith Outwater, keith_outwater@mvis.com.
 *
 * (C) Copyright 2011
 * Andre Schwarz, Matrix Vision GmbH, andre.schwarz@matrix-vision.de
 * Michael Jones, Matrix Vision GmbH, michael.jones@matrix-vision.de
 *
 * See file CREDITS for list of people who contributed to this
 * project.
 *
 * This program is free software; you can redistribute it and/or
 * modify it under the terms of the GNU General Public License as
 * published by the Free Software Foundation; either version 2 of
 * the License, or (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
 * MA 02111-1307 USA
 *
 */

#include <common.h>
#include <ACEX1K.h>
#include <command.h>
#include <asm/gpio.h>
#include "fpga.h"

#ifdef FPGA_DEBUG
#define fpga_debug(fmt, args...)      printf("%s: "fmt, __func__, ##args)
#else
#define fpga_debug(fmt, args...)
#endif

Altera_CYC2_Passive_Serial_fns altera_fns = {
	fpga_null_fn,   /* Altera_pre_fn */
	fpga_config_fn,
	fpga_status_fn,
	fpga_done_fn,
	fpga_wr_fn,
	fpga_null_fn,
	fpga_null_fn,
};

Altera_desc cyclone2 = {
	Altera_CYC2,
	fast_passive_parallel,
	Altera_EP3C5_SIZE,
	(void *) &altera_fns,
	NULL,
	0
};

#define GPIO_RESET		43
#define GPIO_DCLK		65
#define GPIO_nSTATUS	157
#define GPIO_CONF_DONE	158
#define GPIO_nCONFIG	159
#define GPIO_DATA0		54
#define GPIO_DATA1		55
#define GPIO_DATA2		56
#define GPIO_DATA3		57
#define GPIO_DATA4		58
#define GPIO_DATA5		60
#define GPIO_DATA6		61
#define GPIO_DATA7		62

DECLARE_GLOBAL_DATA_PTR;

/* return FPGA_SUCCESS on success, else FPGA_FAIL
 */
int mvblx_init_fpga(void)
{
	fpga_debug("Initializing FPGA interface\n");
	fpga_init();
	fpga_add(fpga_altera, &cyclone2);

	if (gpio_request(GPIO_DCLK, "dclk") ||
			gpio_request(GPIO_nSTATUS, "nStatus") ||
#ifndef CONFIG_SYS_FPGA_DONT_USE_CONF_DONE
			gpio_request(GPIO_CONF_DONE, "conf_done") ||
#endif
			gpio_request(GPIO_nCONFIG, "nConfig") ||
			gpio_request(GPIO_DATA0, "data0") ||
			gpio_request(GPIO_DATA1, "data1") ||
			gpio_request(GPIO_DATA2, "data2") ||
			gpio_request(GPIO_DATA3, "data3") ||
			gpio_request(GPIO_DATA4, "data4") ||
			gpio_request(GPIO_DATA5, "data5") ||
			gpio_request(GPIO_DATA6, "data6") ||
			gpio_request(GPIO_DATA7, "data7")) {
		printf("%s: error requesting GPIOs.", __func__);
		return FPGA_FAIL;
	}

	/* set up outputs */
	gpio_direction_output(GPIO_DCLK,  0);
	gpio_direction_output(GPIO_nCONFIG, 0);
	gpio_direction_output(GPIO_DATA0, 0);
	gpio_direction_output(GPIO_DATA1, 0);
	gpio_direction_output(GPIO_DATA2, 0);
	gpio_direction_output(GPIO_DATA3, 0);
	gpio_direction_output(GPIO_DATA4, 0);
	gpio_direction_output(GPIO_DATA5, 0);
	gpio_direction_output(GPIO_DATA6, 0);
	gpio_direction_output(GPIO_DATA7, 0);

	/* NB omap_free_gpio() resets to an input, so we can't
	 * free ie. nCONFIG, or else the FPGA would reset
	 * Q: presumably gpio_free() has the same effect?
	 */

	/* set up inputs */
	gpio_direction_input(GPIO_nSTATUS);
#ifndef CONFIG_SYS_FPGA_DONT_USE_CONF_DONE
	gpio_direction_input(GPIO_CONF_DONE);
#endif

	fpga_config_fn(0, 1, 0);
	udelay(60);

	return FPGA_SUCCESS;
}

int fpga_null_fn(int cookie)
{
	return 0;
}

int fpga_config_fn(int assert, int flush, int cookie)
{
	fpga_debug("SET config : %s=%d\n", assert ? "low" : "high", assert);
	if (flush) {
		gpio_set_value(GPIO_nCONFIG, !assert);
		udelay(1);
		gpio_set_value(GPIO_nCONFIG, assert);
	}

	return assert;
}

int fpga_done_fn(int cookie)
{
	int result = 0;

	/* since revA of BLX, we will not get this signal. */
	udelay(10);
#ifdef CONFIG_SYS_FPGA_DONT_USE_CONF_DONE
	fpga_debug("not waiting for CONF_DONE.");
	result = 1;
#else
	fpga_debug("CONF_DONE check ... ");
	if (gpio_get_value(GPIO_CONF_DONE))  {
		fpga_debug("high\n");
		result = 1;
	} else
		fpga_debug("low\n");
	gpio_free(GPIO_CONF_DONE);
#endif

	return result;
}

int fpga_status_fn(int cookie)
{
	int result = 0;
	fpga_debug("STATUS check ... ");

	result = gpio_get_value(GPIO_nSTATUS);

	if (result < 0)
		fpga_debug("error\n");
	else if (result > 0)
		fpga_debug("high\n");
	else
		fpga_debug("low\n");

	return result;
}

static inline int _write_fpga(u8 byte)
{
	gpio_set_value(GPIO_DATA0, byte & 0x01);
	gpio_set_value(GPIO_DATA1, (byte >> 1) & 0x01);
	gpio_set_value(GPIO_DATA2, (byte >> 2) & 0x01);
	gpio_set_value(GPIO_DATA3, (byte >> 3) & 0x01);
	gpio_set_value(GPIO_DATA4, (byte >> 4) & 0x01);
	gpio_set_value(GPIO_DATA5, (byte >> 5) & 0x01);
	gpio_set_value(GPIO_DATA6, (byte >> 6) & 0x01);
	gpio_set_value(GPIO_DATA7, (byte >> 7) & 0x01);

	/* clock */
	gpio_set_value(GPIO_DCLK, 1);
	udelay(1);
	gpio_set_value(GPIO_DCLK, 0);
	udelay(1);

	return 0;
}

int fpga_wr_fn(const void *buf, size_t len, int flush, int cookie)
{
	unsigned char *data = (unsigned char *) buf;
	int i;

	fpga_debug("fpga_wr: buf %p / size %d\n", buf, len);
	for (i = 0; i < len; i++)
		_write_fpga(data[i]);
	fpga_debug("-%s\n", __func__);

	return FPGA_SUCCESS;
}
