
/*
 *
 Copyright (c) Eicon Networks, 2002.
 *
 This source file is supplied for the use with
 Eicon Networks range of DIVA Server Adapters.
 *
 Eicon File Revision :    2.1
 *
 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, or (at your option)
 any later version.
 *
 This program is distributed in the hope that it will be useful,
 but WITHOUT ANY WARRANTY OF ANY KIND WHATSOEVER INCLUDING ANY
 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., 675 Mass Ave, Cambridge, MA 02139, USA.
 *
 */
#include "platform.h"
#include "di_defs.h"
#include "pc.h"
#include "pr_pc.h"
#include "di.h"
#include "mi_pc.h"
#include "pc_maint.h"
#include "divasync.h"
#include "pc_init.h"
#include "io.h"
#include "helpers.h"
#include "dsrv4bri.h"
#include "dsp_defs.h"
#include "sdp_hdr.h"

/*****************************************************************************/
#define	MAX_XLOG_SIZE	(64 * 1024)

/* --------------------------------------------------------------------------
   Recovery XLOG from QBRI Card
   -------------------------------------------------------------------------- */
static void qBri_cpu_trapped(PISDN_ADAPTER IoAdapter) {
	byte  __iomem *base;
	word *Xlog;
	dword   regs[4], TrapID, offset, size;
	Xdesc   xlogDesc;
	int factor = (IoAdapter->tasks == 1) ? 1 : 2;

/*
 *	check for trapped MIPS 46xx CPU, dump exception frame
 */

	base = DIVA_OS_MEM_ATTACH_CONTROL(IoAdapter);
	offset = IoAdapter->ControllerNumber * (IoAdapter->MemorySize >> factor);

	TrapID = READ_DWORD(&base[0x80]);

	if ((TrapID == 0x99999999) || (TrapID == 0x99999901))
	{
		dump_trap_frame(IoAdapter, &base[0x90]);
		IoAdapter->trapped = 1;
	}

	regs[0] = READ_DWORD((base + offset) + 0x70);
	regs[1] = READ_DWORD((base + offset) + 0x74);
	regs[2] = READ_DWORD((base + offset) + 0x78);
	regs[3] = READ_DWORD((base + offset) + 0x7c);
	regs[0] &= IoAdapter->MemorySize - 1;

	if ((regs[0] >= offset)
	    && (regs[0] < offset + (IoAdapter->MemorySize >> factor) - 1))
	{
		if (!(Xlog = (word *)diva_os_malloc(0, MAX_XLOG_SIZE))) {
			DIVA_OS_MEM_DETACH_CONTROL(IoAdapter, base);
			return;
		}

		size = offset + (IoAdapter->MemorySize >> factor) - regs[0];
		if (size > MAX_XLOG_SIZE)
			size = MAX_XLOG_SIZE;
		memcpy_fromio(Xlog, &base[regs[0]], size);
		xlogDesc.buf = Xlog;
		xlogDesc.cnt = READ_WORD(&base[regs[1] & (IoAdapter->MemorySize - 1)]);
		xlogDesc.out = READ_WORD(&base[regs[2] & (IoAdapter->MemorySize - 1)]);
		dump_xlog_buffer(IoAdapter, &xlogDesc);
		diva_os_free(0, Xlog);
		IoAdapter->trapped = 2;
	}
	DIVA_OS_MEM_DETACH_CONTROL(IoAdapter, base);
}

/* --------------------------------------------------------------------------
   Reset QBRI Hardware
   -------------------------------------------------------------------------- */
static void reset_qBri_hardware(PISDN_ADAPTER IoAdapter) {
	word volatile __iomem *qBriReset;
	byte  volatile __iomem *qBriCntrl;
	byte  volatile __iomem *p;

	qBriReset = (word volatile __iomem *)DIVA_OS_MEM_ATTACH_PROM(IoAdapter);
	WRITE_WORD(qBriReset, READ_WORD(qBriReset) | PLX9054_SOFT_RESET);
	diva_os_wait(1);
	WRITE_WORD(qBriReset, READ_WORD(qBriReset) & ~PLX9054_SOFT_RESET);
	diva_os_wait(1);
	WRITE_WORD(qBriReset, READ_WORD(qBriReset) | PLX9054_RELOAD_EEPROM);
	diva_os_wait(1);
	WRITE_WORD(qBriReset, READ_WORD(qBriReset) & ~PLX9054_RELOAD_EEPROM);
	diva_os_wait(1);
	DIVA_OS_MEM_DETACH_PROM(IoAdapter, qBriReset);

	qBriCntrl = DIVA_OS_MEM_ATTACH_CTLREG(IoAdapter);
	p = &qBriCntrl[DIVA_4BRI_REVISION(IoAdapter) ? (MQ2_BREG_RISC) : (MQ_BREG_RISC)];
	WRITE_DWORD(p, 0);
	DIVA_OS_MEM_DETACH_CTLREG(IoAdapter, qBriCntrl);

	DBG_TRC(("resetted board @ reset addr 0x%08lx", qBriReset))
		DBG_TRC(("resetted board @ cntrl addr 0x%08lx", p))
		}

/* --------------------------------------------------------------------------
   Start Card CPU
   -------------------------------------------------------------------------- */
void start_qBri_hardware(PISDN_ADAPTER IoAdapter) {
	byte volatile __iomem *qBriReset;
	byte volatile __iomem *p;

	p = DIVA_OS_MEM_ATTACH_CTLREG(IoAdapter);
	qBriReset = &p[(DIVA_4BRI_REVISION(IoAdapter)) ? (MQ2_BREG_RISC) : (MQ_BREG_RISC)];
	WRITE_DWORD(qBriReset, MQ_RISC_COLD_RESET_MASK);
	diva_os_wait(2);
	WRITE_DWORD(qBriReset, MQ_RISC_WARM_RESET_MASK | MQ_RISC_COLD_RESET_MASK);
	diva_os_wait(10);
	DIVA_OS_MEM_DETACH_CTLREG(IoAdapter, p);

	DBG_TRC(("started processor @ addr 0x%08lx", qBriReset))
		}

/* --------------------------------------------------------------------------
   Stop Card CPU
   -------------------------------------------------------------------------- */
static void stop_qBri_hardware(PISDN_ADAPTER IoAdapter) {
	byte volatile __iomem *p;
	dword volatile __iomem *qBriReset;
	dword volatile __iomem *qBriIrq;
	dword volatile __iomem *qBriIsacDspReset;
	int rev2 = DIVA_4BRI_REVISION(IoAdapter);
	int reset_offset = rev2 ? (MQ2_BREG_RISC)      : (MQ_BREG_RISC);
	int irq_offset   = rev2 ? (MQ2_BREG_IRQ_TEST)  : (MQ_BREG_IRQ_TEST);
	int hw_offset    = rev2 ? (MQ2_ISAC_DSP_RESET) : (MQ_ISAC_DSP_RESET);

	if (IoAdapter->ControllerNumber > 0)
		return;
	p = DIVA_OS_MEM_ATTACH_CTLREG(IoAdapter);
	qBriReset = (dword volatile __iomem *)&p[reset_offset];
	qBriIsacDspReset = (dword volatile __iomem *)&p[hw_offset];
/*
 *	clear interrupt line (reset Local Interrupt Test Register)
 */
	WRITE_DWORD(qBriReset, 0);
	WRITE_DWORD(qBriIsacDspReset, 0);
	DIVA_OS_MEM_DETACH_CTLREG(IoAdapter, p);

	p = DIVA_OS_MEM_ATTACH_RESET(IoAdapter);
	WRITE_BYTE(&p[PLX9054_INTCSR], 0x00);	/* disable PCI interrupts */
	DIVA_OS_MEM_DETACH_RESET(IoAdapter, p);

	p = DIVA_OS_MEM_ATTACH_CTLREG(IoAdapter);
	qBriIrq   = (dword volatile __iomem *)&p[irq_offset];
	WRITE_DWORD(qBriIrq, MQ_IRQ_REQ_OFF);
	DIVA_OS_MEM_DETACH_CTLREG(IoAdapter, p);

	DBG_TRC(("stopped processor @ addr 0x%08lx", qBriReset))

		}

/* --------------------------------------------------------------------------
   FPGA download
   -------------------------------------------------------------------------- */
#define FPGA_NAME_OFFSET         0x10

static byte *qBri_check_FPGAsrc(PISDN_ADAPTER IoAdapter, char *FileName,
				dword *Length, dword *code) {
	byte *File;
	char *fpgaFile, *fpgaType, *fpgaDate, *fpgaTime;
	dword fpgaFlen, fpgaTlen, fpgaDlen, cnt, year, i;

	if (!(File = (byte *)xdiLoadFile(FileName, Length, 0))) {
		return (NULL);
	}
/*
 *	 scan file until FF and put id string into buffer
 */
	for (i = 0; File[i] != 0xff;)
	{
		if (++i >= *Length)
		{
			DBG_FTL(("FPGA download: start of data header not found"))
				xdiFreeFile(File);
			return (NULL);
		}
	}
	*code = i++;

	if ((File[i] & 0xF0) != 0x20)
	{
		DBG_FTL(("FPGA download: data header corrupted"))
			xdiFreeFile(File);
		return (NULL);
	}
	fpgaFlen = (dword)File[FPGA_NAME_OFFSET - 1];
	if (fpgaFlen == 0)
		fpgaFlen = 12;
	fpgaFile = (char *)&File[FPGA_NAME_OFFSET];
	fpgaTlen = (dword)fpgaFile[fpgaFlen + 2];
	if (fpgaTlen == 0)
		fpgaTlen = 10;
	fpgaType = (char *)&fpgaFile[fpgaFlen + 3];
	fpgaDlen = (dword)  fpgaType[fpgaTlen + 2];
	if (fpgaDlen == 0)
		fpgaDlen = 11;
	fpgaDate = (char *)&fpgaType[fpgaTlen + 3];
	fpgaTime = (char *)&fpgaDate[fpgaDlen + 3];
	cnt = (dword)(((File[i] & 0x0F) << 20) + (File[i + 1] << 12)
		      + (File[i + 2] << 4) + (File[i + 3] >> 4));

	if ((dword)(i + (cnt / 8)) > *Length)
	{
		DBG_FTL(("FPGA download: '%s' file too small (%ld < %ld)",
			 FileName, *Length, code + ((cnt + 7) / 8)))
			xdiFreeFile(File);
		return (NULL);
	}
	i = 0;
	do
	{
		while ((fpgaDate[i] != '\0')
		       && ((fpgaDate[i] < '0') || (fpgaDate[i] > '9')))
		{
			i++;
		}
		year = 0;
		while ((fpgaDate[i] >= '0') && (fpgaDate[i] <= '9'))
			year = year * 10 + (fpgaDate[i++] - '0');
	} while ((year < 2000) && (fpgaDate[i] != '\0'));

	switch (IoAdapter->cardType) {
	case CARDTYPE_DIVASRV_B_2F_PCI:
		break;

	default:
		if (year >= 2001) {
			IoAdapter->fpga_features |= PCINIT_FPGA_PLX_ACCESS_SUPPORTED;
		}
	}

	DBG_LOG(("FPGA[%s] file %s (%s %s) len %d",
		 fpgaType, fpgaFile, fpgaDate, fpgaTime, cnt))
		return (File);
}

/******************************************************************************/

#define FPGA_PROG   0x0001		/* PROG enable low */
#define FPGA_BUSY   0x0002		/* BUSY high, DONE low */
#define	FPGA_CS     0x000C		/* Enable I/O pins */
#define FPGA_CCLK   0x0100
#define FPGA_DOUT   0x0400
#define FPGA_DIN    FPGA_DOUT   /* bidirectional I/O */

int qBri_FPGA_download(PISDN_ADAPTER IoAdapter) {
	int            bit;
	byte           *File;
	dword          code, FileLength;
	word volatile __iomem *addr = (word volatile __iomem *)DIVA_OS_MEM_ATTACH_PROM(IoAdapter);
	word           val, baseval = FPGA_CS | FPGA_PROG;



	if (DIVA_4BRI_REVISION(IoAdapter))
	{
		char *name;

		switch (IoAdapter->cardType) {
		case CARDTYPE_DIVASRV_B_2F_PCI:
			name = "dsbri2f.bit";
			break;

		case CARDTYPE_DIVASRV_B_2M_V2_PCI:
		case CARDTYPE_DIVASRV_VOICE_B_2M_V2_PCI:
			name = "dsbri2m.bit";
			break;

		default:
			name = "ds4bri2.bit";
		}

		File = qBri_check_FPGAsrc(IoAdapter, name,
					  &FileLength, &code);
	}
	else
	{
		File = qBri_check_FPGAsrc(IoAdapter, "ds4bri.bit",
					  &FileLength, &code);
	}
	if (!File) {
		DIVA_OS_MEM_DETACH_PROM(IoAdapter, addr);
		return (0);
	}
/*
 *	prepare download, pulse PROGRAM pin down.
 */
	WRITE_WORD(addr, baseval & ~FPGA_PROG); /* PROGRAM low pulse */
	WRITE_WORD(addr, baseval);              /* release */
	diva_os_wait(50);  /* wait until FPGA finished internal memory clear */
/*
 *	check done pin, must be low
 */
	if (READ_WORD(addr) & FPGA_BUSY)
	{
		DBG_FTL(("FPGA download: acknowledge for FPGA memory clear missing"))
			xdiFreeFile(File);
		DIVA_OS_MEM_DETACH_PROM(IoAdapter, addr);
		return (0);
	}
/*
 *	put data onto the FPGA
 */
	while (code < FileLength)
	{
		val = ((word)File[code++]) << 3;

		for (bit = 8; bit-- > 0; val <<= 1) /* put byte onto FPGA */
		{
			baseval &= ~FPGA_DOUT;             /* clr  data bit */
			baseval |= (val & FPGA_DOUT);      /* copy data bit */
			WRITE_WORD(addr, baseval);
			WRITE_WORD(addr, baseval | FPGA_CCLK);     /* set CCLK hi */
			WRITE_WORD(addr, baseval | FPGA_CCLK);     /* set CCLK hi */
			WRITE_WORD(addr, baseval);                 /* set CCLK lo */
		}
	}
	xdiFreeFile(File);
	diva_os_wait(100);
	val = READ_WORD(addr);

	DIVA_OS_MEM_DETACH_PROM(IoAdapter, addr);

	if (!(val & FPGA_BUSY))
	{
		DBG_FTL(("FPGA download: chip remains in busy state (0x%04x)", val))
			return (0);
	}

	return (1);
}

static int load_qBri_hardware(PISDN_ADAPTER IoAdapter) {
	return (0);
}

/* --------------------------------------------------------------------------
   Card ISR
   -------------------------------------------------------------------------- */
static int qBri_ISR(struct _ISDN_ADAPTER *IoAdapter) {
	dword volatile     __iomem *qBriIrq;

	PADAPTER_LIST_ENTRY QuadroList = IoAdapter->QuadroList;

	word			i;
	int			serviced = 0;
	byte __iomem *p;

	p = DIVA_OS_MEM_ATTACH_RESET(IoAdapter);

	if (!(READ_BYTE(&p[PLX9054_INTCSR]) & 0x80)) {
		DIVA_OS_MEM_DETACH_RESET(IoAdapter, p);
		return (0);
	}
	DIVA_OS_MEM_DETACH_RESET(IoAdapter, p);

/*
 *	clear interrupt line (reset Local Interrupt Test Register)
 */
	p = DIVA_OS_MEM_ATTACH_CTLREG(IoAdapter);
	qBriIrq = (dword volatile __iomem *)(&p[DIVA_4BRI_REVISION(IoAdapter) ? (MQ2_BREG_IRQ_TEST)  : (MQ_BREG_IRQ_TEST)]);
	WRITE_DWORD(qBriIrq, MQ_IRQ_REQ_OFF);
	DIVA_OS_MEM_DETACH_CTLREG(IoAdapter, p);

	for (i = 0; i < IoAdapter->tasks; ++i)
	{
		IoAdapter = QuadroList->QuadroAdapter[i];

		if (IoAdapter && IoAdapter->Initialized
		    && IoAdapter->tst_irq(&IoAdapter->a))
		{
			IoAdapter->IrqCount++;
			serviced = 1;
			diva_os_schedule_soft_isr(&IoAdapter->isr_soft_isr);
		}
	}

	return (serviced);
}

/* --------------------------------------------------------------------------
   Does disable the interrupt on the card
   -------------------------------------------------------------------------- */
static void disable_qBri_interrupt(PISDN_ADAPTER IoAdapter) {
	dword volatile __iomem *qBriIrq;
	byte __iomem *p;

	if (IoAdapter->ControllerNumber > 0)
		return;
/*
 *	clear interrupt line (reset Local Interrupt Test Register)
 */
	p = DIVA_OS_MEM_ATTACH_RESET(IoAdapter);
	WRITE_BYTE(&p[PLX9054_INTCSR], 0x00);	/* disable PCI interrupts */
	DIVA_OS_MEM_DETACH_RESET(IoAdapter, p);

	p = DIVA_OS_MEM_ATTACH_CTLREG(IoAdapter);
	qBriIrq = (dword volatile __iomem *)(&p[DIVA_4BRI_REVISION(IoAdapter) ? (MQ2_BREG_IRQ_TEST)  : (MQ_BREG_IRQ_TEST)]);
	WRITE_DWORD(qBriIrq, MQ_IRQ_REQ_OFF);
	DIVA_OS_MEM_DETACH_CTLREG(IoAdapter, p);
}

/* --------------------------------------------------------------------------
   Install Adapter Entry Points
   -------------------------------------------------------------------------- */
static void set_common_qBri_functions(PISDN_ADAPTER IoAdapter) {
	ADAPTER *a;

	a = &IoAdapter->a;

	a->ram_in           = mem_in;
	a->ram_inw          = mem_inw;
	a->ram_in_buffer    = mem_in_buffer;
	a->ram_look_ahead   = mem_look_ahead;
	a->ram_out          = mem_out;
	a->ram_outw         = mem_outw;
	a->ram_out_buffer   = mem_out_buffer;
	a->ram_inc          = mem_inc;

	IoAdapter->out = pr_out;
	IoAdapter->dpc = pr_dpc;
	IoAdapter->tst_irq = scom_test_int;
	IoAdapter->clr_irq  = scom_clear_int;
	IoAdapter->pcm  = (struct pc_maint *)MIPS_MAINT_OFFS;

	IoAdapter->load = load_qBri_hardware;

	IoAdapter->disIrq = disable_qBri_interrupt;
	IoAdapter->rstFnc = reset_qBri_hardware;
	IoAdapter->stop = stop_qBri_hardware;
	IoAdapter->trapFnc = qBri_cpu_trapped;

	IoAdapter->diva_isr_handler = qBri_ISR;

	IoAdapter->a.io = (void *)IoAdapter;
}

static void set_qBri_functions(PISDN_ADAPTER IoAdapter) {
	if (!IoAdapter->tasks) {
		IoAdapter->tasks = MQ_INSTANCE_COUNT;
	}
	IoAdapter->MemorySize = MQ_MEMORY_SIZE;
	set_common_qBri_functions(IoAdapter);
	diva_os_set_qBri_functions(IoAdapter);
}

static void set_qBri2_functions(PISDN_ADAPTER IoAdapter) {
	if (!IoAdapter->tasks) {
		IoAdapter->tasks = MQ_INSTANCE_COUNT;
	}
	IoAdapter->MemorySize = (IoAdapter->tasks == 1) ? BRI2_MEMORY_SIZE : MQ2_MEMORY_SIZE;
	set_common_qBri_functions(IoAdapter);
	diva_os_set_qBri2_functions(IoAdapter);
}

/******************************************************************************/

void prepare_qBri_functions(PISDN_ADAPTER IoAdapter) {

	set_qBri_functions(IoAdapter->QuadroList->QuadroAdapter[0]);
	set_qBri_functions(IoAdapter->QuadroList->QuadroAdapter[1]);
	set_qBri_functions(IoAdapter->QuadroList->QuadroAdapter[2]);
	set_qBri_functions(IoAdapter->QuadroList->QuadroAdapter[3]);

}

void prepare_qBri2_functions(PISDN_ADAPTER IoAdapter) {
	if (!IoAdapter->tasks) {
		IoAdapter->tasks = MQ_INSTANCE_COUNT;
	}

	set_qBri2_functions(IoAdapter->QuadroList->QuadroAdapter[0]);
	if (IoAdapter->tasks > 1) {
		set_qBri2_functions(IoAdapter->QuadroList->QuadroAdapter[1]);
		set_qBri2_functions(IoAdapter->QuadroList->QuadroAdapter[2]);
		set_qBri2_functions(IoAdapter->QuadroList->QuadroAdapter[3]);
	}

}

/* -------------------------------------------------------------------------- */
