
/*
 Copyright 1999 by Digi International (www.digi.com)

 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, EXPRESS OR IMPLIED; 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., 675 Mass Ave, Cambridge, MA 02139, USA.
*/

/*
 * Things that describe the LSI Logic RAP II xxxxxx chip.
 * (not the board, not the project, I said *chip*)
 * Things that describe the processor core don't go here, either.  They
 * live in libidt.
 *
 * $Id: rap2.h,v 1.27 2001/01/09 21:05:08 travisl Exp $
 */

#ifndef _RAP2_H_

#define _RAP2_H_

#ifndef	_RAPMMAP_
#include "rap2mmap.h"
#endif

#include "rap2sysreg.h"
#include "osconfig.h"

#ifdef __mips
#define	REGISTER_SECTION	__attribute__((section("register")))
#else
#define	REGISTER_SECTION
#endif


#if TEST
typedef unsigned int 	uint32 ;
typedef unsigned short 	uint16 ;
typedef unsigned char	uint8 ;
#endif

#define	PROCESSOR_HZ	80000000	/* 80 MHz */

extern uint32	brg_hz ;
#define BRG_HZ 		brg_hz		/* common uart freq */
extern uint32	rtc_hz ;
#define RTC_HZ 		rtc_hz		/* common rtc freq */
extern uint32	sysclk_hz ;
#define	SYSCLK_HZ	sysclk_hz

#define NSWCS 		9	/* RAP 2 has this many serial channels */
/*
 * If/When NMCDMACS changes from (9 + 1), the padding following the
 * DMAC structure member structures better be re-visited !!!
 */
#define	NMCDMACS	(NSWCS+1)	/* RAP 2 has NSWCS+1 MCDMAC ch. */
#define	SWC2DMAC(x)	((x)+1)
#define	SWC_DMAC_MASK(x)	(2<<(x))

typedef volatile uint32	RAP_SYSCTL;


/*
 *	Define RAP TinyRISC timers.
 */

typedef struct rap_timers
{
	/* WARNING:  Although these have to be accessed as 32 bit values
	 * the upper 16 bits are ignored! 
	 */
	volatile uint32	timer0_initial_count;
	volatile uint32	timer0_current_count;
	volatile uint32	timer1_initial_count;
	volatile uint32	timer1_current_count;

	#define	TIMER1_WATCHDOG_MODE	(1<<10)
/*	#define	TIMER1_OUTPUT_MODE	(1<<9) */
	#define	TIMER1_ENABLE		(1<<8)
/*	#define	TIMER0_OUTPUT_MODE	(1<<1) */
	#define	TIMER0_ENABLE		(1<<0)
	volatile uint32	timer_mode;

	#define	TIMER0_INT		(1<<1)
	#define	TIMER0_INT_ENABLE	(1<<0)
	volatile uint32	timer0_int_status;

	volatile uint32	padding[2];

	#define	TIMER2_INT		(1<<17)
	#define	TIMER2_ENABLE		(1<<16)

	#define	TIMER1_INT		(1<<11)
	#define	TIMER1_INT_ENABLE	(1<<10)

	#define TIMER1_CLK_SRC_SYS_CLK	(0<<8)
	#define TIMER1_CLK_SRC_RTC_CLK	(2<<8)
	#define TIMER1_CLK_SRC_RTC_128	(3<<8)
	#define TIMER1_CLK_SRC_MASK	(3<<8)

	#define TIMER0_CLK_SRC_SYS_CLK	(0<<0)
	#define TIMER0_CLK_SRC_RTC_CLK	(2<<0)
	#define TIMER0_CLK_SRC_RTC_128	(3<<0)
	#define TIMER0_CLK_SRC_MASK	(3<<0)

	volatile uint32	enhanced_config;

	volatile uint32	timer2_count;
	volatile uint32	timer2_compare;

} RAP_TIMER_REGS;


typedef struct rap_rtc_regs
{
	volatile uint32	rtc_config;
	#define RTC_INT_PENDING			(1<<1)
	#define RTC_ENABLED			(1<<0)

	/* These might make more sense as bitfields or something.  Since
	 * we're unlikely to have a sensible RTC clock source, I can't 
	 * imagine we'd use these anyway.
	 */
	volatile uint32	rtc_time;
	volatile uint32	rtc_alarm;
} RAP_RTC_REGS;




typedef struct rap_cpu_regs
{
	volatile uint32	int_remap;

		#define	INT_DMAC_BUS_ERR	(1<<0)
		#define	INT_PCI_BUS_ERR		(1<<1)
		#define	INT_RX_MBOX_OVR		(1<<2)
		#define	INT_DMAC_RX		(1<<3)
		#define	INT_DMAC_TX		(1<<4)
		#define	INT_PCI			(1<<5)
		#define	INT_SWC1		(1<<6)
		#define	INT_SWC2		(1<<7)
		#define	INT_SWC3		(1<<8)
		#define	INT_SWC4		(1<<9)
		#define	INT_SWC5		(1<<10)
		#define	INT_SWC6		(1<<11)
		#define	INT_SWC7		(1<<12)
		#define	INT_SWC8		(1<<13)
		#define	INT_SWC9		(1<<14)
		#define	INT_SWC10		(1<<15)
		#define	INT_SWC11		(1<<16)
		#define	INT_SWC12		(1<<17)
		#define	INT_RTC			(1<<18)
		#define	INT_ETHERNET		(1<<19)
		#define	INT_UTOPIA		(1<<20)
		#define	INT_TIMER0		(1<<21)
		#define	INT_TIMER1		(1<<22)
		#define	INT_TIMER2		(1<<23)
		#define	INT_TIMER3		(1<<24)
		#define	INT_UART		(1<<25)
		#define	INT_GPIO		(1<<26)
		#define	INT_MBOX_I2O		(1<<27)
		#define	INT_BIST		(1<<28)

		#define ALL_SWC_INTS					\
			(INT_SWC1|INT_SWC2|INT_SWC3|INT_SWC4 		\
			 INT_SWC5|INT_SWC6|INT_SWC7|INT_SWC8 		\
			 INT_SWC9|INT_SWC10|INT_SWC11|INT_SWC12)

		#define INT_SWC1to8					\
			(INT_SWC1|INT_SWC2|INT_SWC3|INT_SWC4|		\
			 INT_SWC5|INT_SWC6|INT_SWC7|INT_SWC8)

#define INT_SOURCE_COUNT	6	/* All possible interrupt sources */

	volatile uint32	int_pending;
	volatile uint32	int_enable;
	volatile uint32	reset_status;		/* 1 if warm reset */
	volatile uint32	memory_error_addr;	/* Address which caused error */
	volatile uint32	unused1;		/* 0x8414 */
	volatile uint32	unused2;		/* 0x8418 */
	volatile uint32	cpu_pc;			/* 4101 program counter */
} RAP_CPU_REGS;


typedef struct rap_gpio_regs
{
		#define	GPIO_ENABLE		(1<<0)
	volatile uint32		gpio_ctl;

		#define	GPIO_REGISTERED_INPUTS	0x0
		#define	GPIO_REGISTERED_OUTPUTS	0x1
		#define	GPIO_LOW_GOING_EDGE_INT	0x2
		#define	GPIO_ACT_LOW_LVL_INT	0x3
		#define	GPIO_HI_GOING_EDGE_INT	0x4
		#define	GPIO_ACT_HI_LVL_INT	0x5
		#define	GPIO_INT_TEST		0x6
		#define	GPIO1(x)		((x)<<0)
		#define	GPIO2(x)		((x)<<4)
		#define	GPIO3(x)		((x)<<8)
		#define	GPIO4(x)		((x)<<12)
		#define	GPIO5(x)		((x)<<16)
		#define	GPIO6(x)		((x)<<20)
	volatile uint32		gpio_config;
	volatile uint32		gpio_output;
	volatile uint32		gpio_input;
	volatile uint32		gpio_interrupt;
} RAP_GPIO_REGS;


/* FIXME: Right now, include these defines from LSI Logic until 
   we can get more civilized ones in place. */

#define SDRAM_LP_MODE_OFF               0x00000000


#define SDRAM_DP2                       0x00000000



typedef struct local_mem_regs
{
		#define REFRESH_RATE_FOR_1MHZ	0x00000010
		#define REFRESH_RATE_FOR_40MHZ	0x00000271
		#define REFRESH_RATE_FOR_80MHZ	0x000004E2
	volatile uint32	dram_refresh;
	volatile uint32	pad1;

		#define SDRAM_CAS_LATENCY	0x00300000
		#define	SDRAM_CAS(x)		((x)<<20)
		#define SDRAM_RC_1MHZ		0x00002000
		#define SDRAM_RC_40MHZ		0x00007000
		#define SDRAM_RC_80MHZ		0x0000A000
		#define	SDRAM_RC(x)		((x)<<12)
		#define SDRAM_RBS		0x00000100
		#define	SDRAM_16SDX4		(0<<8)
		#define	SDRAM_16SDX8		(1<<8)
		#define	SDRAM_16SDX16		(2<<8)
		#define	SDRAM_8SGX32		(3<<8)
		#define	SDRAM_64SDX4		(4<<8)
		#define	SDRAM_64SDX8		(5<<8)
		#define	SDRAM_64SDX16		(6<<8)
/*		#define	SDRAM_8SGX32		(7<<8) */
	volatile uint32	sdram_control;
	volatile uint32	pad2;
	volatile uint32	manual_precharge;
	volatile uint32	pad3;
	volatile uint32	mode_register;
	volatile uint32	pad4;
	volatile uint32	refresh_command;
	volatile uint32	pad5;

		#define	EPROM_READ_TIME(x)	(x)
		#define	EPROM_READ_RECOVERY(x)	((x)<<4)
		#define	EPROM_WRITE_LOW(x)	((x)<<16)
		#define	EPROM_WRITE_HIGH(x)	((x)<<20)
	volatile uint32	eprom_control;
	volatile uint32	pad6;

		#define	PHY_READ_TIME(x)	(x)
		#define	PHY_READ_RECOVERY(x)	((x)<<4)
		#define	PHY_WRITE_LOW(x)	((x)<<16)
		#define	PHY_WRITE_HIGH(x)	((x)<<20)
	volatile uint32	phy_control;
} RAP_LOCAL_MEM_REGS;


/* PCI DMAC registers */


typedef struct pci_bmd
{
		#define RAP_DMA_PCI2LCL 	(0) 	/* Pseudo OP */
		#define	PCIBMD_VALID		(1 << 0)
		#define RAP_DMA_LCL2PCI		(1 << 1)
		#define	PCIBMD_COMPLETE		(1 << 2)
	volatile uint16          	count;
	volatile uint16          	flags;
	volatile uint32          	pci_addr;
	volatile uint32          	local_addr;
        struct pci_bmd * volatile	next_bmd;
} RAP_PCI_BMD;


typedef struct rap_pci_dmac_regs
{
		#define PCIDMAC_LOCKOUT_REQ 	(1<<0)
		#define PCIDMAC_LOCKOUT_READY	(1<<1)
		#define	PCIDMAC_POLL		(1<<2)
		#define	PCIDMAC_ENABLE		(1<<3)
		#define	PCIDMAC_RESET		(1<<4)
	volatile uint32		dmac_control;			/* 8100 */
	volatile uint32		pad1;				/* 8104 */

		#define	PCIDMAC_INT_LIST_EN	(1<<1)
		#define	PCIDMAC_INT_BMD_EN	(1<<2)
		#define	PCIDMAC_INT_LIST	(1<<9)
		#define	PCIDMAC_INT_BMD		(1<<10)
		#define	PCIDMAC_INT_LIST_CLR	(1<<17)
		#define	PCIDMAC_INT_BMD_CLR	(1<<18)
	volatile uint32		interrupt;			/* 8108 */
	volatile uint32		pad2;				/* 810C */
	volatile uint32		poll_timer;			/* 8110 */
	volatile uint32		pad3;				/* 8114 */
	RAP_PCI_BMD * volatile	bmd_pointer;			/* 8118 */
}  RAP_PCI_DMAC_REGS;


/* PCI registers - at B000_8150 - 32-bit access only! */

typedef struct rap_pci_regs
{
	volatile uint32		serialeeprom_port;	/* 8150 */
	volatile uint32		notused1;		/* 8154 */
	volatile uint32		sys_rst_ctrl;		/* 8158 */
	volatile uint32		notused2;		/* 815C */
	volatile uint32		reg_acc_enable;		/* 8160 */
	volatile uint32		notused3;		/* 8164 */
	volatile uint32		pci_address_reg;	/* 8168 */
	volatile uint32		notused4;		/* 816C */

		#define	PCI_RAP_INT_EEPROM_ERR	(1<<0)
		#define	PCI_RAP_INT_DMA_MEM_ERR	(1<<1)
		#define	PCI_RAP_INT_MEM_ERR	(1<<2)
		#define	PCI_RAP_INT_PARITY_ERR	(1<<4)
		#define	PCI_RAP_INT_MASTER_FATAL_ERR	(1<<5)
		#define	PCI_RAP_INT_ILL_ACCESS_ERR	(1<<6)
		#define	PCI_RAP_INT_DMA_NOT_ENABLED_ERR	(1<<7)
		#define	PCI_RAP_INT_MASTER_NOT_ENABLED_ERR	(1<<8)
		#define	PCI_RAP_INT_RANDOM_BIT_ERR	(1<<9)
		#define	PCI_RAP_INT_CFG_BUSY	(1<<29)
		#define	PCI_RAP_INT_INIT_EE_BUSY	(1<<30)
		#define	PCI_RAP_INT_EEPROM_BUSY	(1<<31)
	volatile uint32		rap_int;		/* 8170 */
	volatile uint32		notused5;		/* 8174 */

		#define PCI_RAP_IO_READ		0x02
		#define PCI_RAP_IO_WRITE	0x03
		#define PCI_RAP_MEMORY_READ	0x06
		#define PCI_RAP_MEMORY_WRITE	0x07
		#define PCI_RAP_CONFIG_READ	0x0a
		#define PCI_RAP_CONFIG_WRTIE	0x0b
	volatile uint32		pci_cmd;		/* 8178 */
	volatile uint32		notused6;		/* 817C */
	volatile uint32		vendor_device_id;	/* 8180 */
	volatile uint32		command_status;		/* 8184 */
	volatile uint32		revision_classcode;	/* 8188 */
	volatile uint32		cache_latency_header_bist;	/* 818C */
	volatile uint32		bar1;			/* 8190 */
	volatile uint32		bar2;			/* 8194 */
	volatile uint32		unused1;		/* 8198 */
	volatile uint32		unused2;		/* 819C */
	volatile uint32		unused3;		/* 81A0 */
	volatile uint32		unused4;		/* 81A4 */
	volatile uint32		unused5;		/* 81A8 */
	volatile uint32		subsysvendor_subsys;	/* 81AC */
	volatile uint32		exprom_bar;		/* 81B0 */
	volatile uint32		capabilities;		/* 81B4 */
	volatile uint32		unused6;		/* 81B8 */
	volatile uint32		intline_intpin_mingnt_maxlat;	/* 81BC */
	volatile uint32		trdytimeout_retrytimeout;	/* 81C0 */
	volatile uint32		pm_capabilities;	/* 81C4 */
	volatile uint32		pm_control_status_bridge;	/* 81C8 */
	volatile uint32		vpd_id_ptr_addr;	/* 81CC */
	volatile uint32		vpd_data;		/* 81D0 */
	volatile uint32		bar1_size_select;	/* 81D4 */
	volatile uint32		exprom_size_select;	/* 81D8 */
} RAP_PCI_REGS;




typedef struct mc_bmd
{
	volatile uint16		buffer_bytes_used;

		#define	BMD_DMAC_OWNS		(1<<0)
		#define BMD_EOF			(1<<1)
		#define BMD_START		(1<<2)
		#define FRAME_ORUN		(1<<3)
		/* reserved */
		#define BMD_ENABLE_FREELIST	(1<<6)
		#define BMD_INT_ON_BUF_DONE	(1<<7)

		#define ERR_ABORT		(1<<8)
		#define ERR_FRAME		(1<<9)
		#define ERR_CRC			(1<<10)
		#define	ERR_PARITY		(1<<10)
		#define	FLAG_MATCH1		(1<<11)
		#define	FLAG_MATCH2		(1<<12)
		#define	FLAG_MATCH3		(1<<13)
		#define	FLAG_RX_COUNT		(1<<14)
		#define	FLAG_IDLE		(1<<15)
		/* reserved */
	volatile uint16		flags;
	volatile uint16		rx_frame_count;
	volatile uint16		buffer_size;
	volatile void *		buf;
	struct mc_bmd * volatile	next_bmd;
} RAP_MC_BMD;


typedef struct rap2_dmac_regs
{
	volatile uint32		_missing1;
	volatile uint32		pad1;
	volatile uint32		rx_ch_enable;		/* 0x08 */
	volatile uint32		pad2;
	volatile uint32		tx_ch_enable;		/* 0x10 */
	volatile uint32		pad3;
		#define MCDMAC_FREELIST_ENABLE		(1 << 7)
	volatile uint32		rx_int_enable;		/* 0x18 */
	volatile uint32		pad4;
	volatile uint32		tx_int_enable;		/* 0x20 */
	volatile uint32		pad5;

		#define	MCDMAC_RXINT_FREEEMPTY		(1<<15)
		#define SWC0_PENDING			(1<<1)
	volatile uint32		rx_int_pending;		/* 0x28 */
	volatile uint32		pad6;
	volatile uint32		tx_int_pending;		/* 0x30 */
	volatile uint32		pad7;
	volatile uint32		rx_transparent;		/* 0x38 */
	volatile uint32		pad8;
	volatile uint32		rx_suspend;		/* 0x40 */
	volatile uint32		pad9;
	volatile uint32		tx_suspend;		/* 0x48 */
	volatile uint32		pad10;
	RAP_MC_BMD	* volatile bmd_free;		/* 0x50 */
	volatile uint32		pad11[43];

	/*
	 * Physically there are 13 of these, Tigger only uses 9,
	 * starting at '1' not '0', through '9'.
	 * Yes, this is ugly, compared to earlier rap2.h versions,
	 * but a non-GNU enhanced ANSI compiler can grok it.
	 */

	struct tx_bmd				/* 0x100 - 0x160 */
	{
		RAP_MC_BMD * volatile 	reg;
		volatile uint32 	pad;
	} tx_bmd[13];

	volatile uint32		pad12[38];

	struct rx_bmd				/* 0x200 - 0x360 */
	{
		RAP_MC_BMD * volatile 	reg;
		volatile uint32 	pad;
	} rx_bmd[13];

	uint32		pad13[38];

	struct tx_int_status			/* 0x300 - 0x360 */
	{
			#define	MC_INT_BMD_COMPLETE	(1<<0)
			#define	MC_INT_BMD_NOTREADY	(1<<1)
			#define	MC_INT_ABNORMAL		(1<<2)
			#define	MC_INT_LIST_COMPLETE	(1<<3)
			#define	MC_INT_RXEOF		(1<<4)
			#define	MC_INT_BUSERROR		(1<<5)
			#define	MC_INT_BMD_HOST		(1<<6)

			#define	MC_INT_BMD_ENABLE	(1<<31)
		volatile uint32		reg;
		volatile uint32 	pad;
	} tx_int_status[13];

	volatile uint32		pad14[38];

	struct rx_int_status			/* 0x400 - 0x460 */
	{
		volatile uint32		reg;
		volatile uint32		pad;
	} rx_int_status[13];

	uint32		pad15[38];

	struct tx_bmd_next			/* 0x500 - 0x560 */
	{
		RAP_MC_BMD * volatile	reg;
		volatile uint32		pad;
	} tx_bmd_next[13];

	volatile uint32		pad16[38];

	struct rx_bmd_next			/* 0x600 - 0x660 */
	{
		RAP_MC_BMD * volatile	reg;
		volatile uint32		pad;
	} rx_bmd_next[13];
} RAP_DMAC_REGS;


typedef struct rap_swc_regs
{
		#define TX_CLK_IS_RX_CLK_INPUT	(0x00 << 6)
		#define TX_CLK_IS_BRG_DIV_16	(0x01 << 6)
		#define TX_CLK_IS_TX_CLK_INPUT	(0x02 << 6)
		#define TX_CLK_IS_DISABLED    	(0x03 << 6)
		#define TX_CLK_MASK 		(0x03 << 6)

		#define RX_CLK_IS_RX_CLK_INPUT	(0x00 << 4)
		#define RX_CLK_IS_BRG_DIV_16	(0x01 << 4)
		#define RX_CLK_IS_DPLL		(0x02 << 4)
		#define RX_CLK_IS_DISABLED    	(0x03 << 4)
		#define RX_CLK_MASK 		(0x03 << 4)

		#define BRG_IS_SYSTEM_CLK	(1<<3)
		#define	RTS_TIMER_ENABLE	(1<<1)
		#define SWC_LOOPBACK		(1<<0)
	volatile uint32	swc_config;

		#define BRG_COUNT_MASK		0xfffff
	volatile uint32	brg_count;

		#define SWC_RESET 		(1<<0)
		#define SWC_RX_HALT		(1<<1)
		#define SWC_TX_HALT		(1<<2)
		#define	SWC_RX_FIFO_FLUSH	(1<<3)
	volatile uint32	reset;

		#define	SWCINT_STS_RX_ORUN	(1<<0)
		#define	SWCINT_STS_TX_URUN	(1<<1)
		#define	SWCINT_STS_TX_ERR	(1<<2)
		#define	SWCINT_STS_INTVL	(1<<3)
		#define	SWCINT_STS_DCD_INT	(1<<8)
		#define	SWCINT_STS_CTS_INT	(1<<9)
		#define	SWCINT_STS_DSR_INT	(1<<10)
		#define	SWCINT_STS_RI_INT	(1<<11)
		#define	SWCINT_STS_LINE_CHG_INT	(1<<12)
		#define	SWCINT_STS_BREAK_INT	(1<<13)
		#define	SWCINT_STS_TX_IDLE	(1<<14)
		#define	SWCINT_STS_RX_IDLE	(1<<15)
		#define	SWCINT_STS_DCD		(1<<16)
		#define	SWCINT_STS_CTS		(1<<17)
		#define	SWCINT_STS_DSR		(1<<18)
		#define	SWCINT_STS_RI		(1<<19)
		#define	SWCINT_STS_LINE_CHG	(1<<20)
		#define	SWCINT_STS_BREAK	(1<<21)
	volatile uint32	int_status;

		#define	SWCINT_CTL_RX_ORUN_INT_EN	(1<<0)
		#define	SWCINT_CTL_TX_URUN_INT_EN	(1<<1)
		#define	SWCINT_CTL_TX_ERR_INT_EN	(1<<2)
		#define	SWCINT_CTL_DCD_INT_EN	(1<<8)
		#define	SWCINT_CTL_CTS_INT_EN	(1<<9)
		#define	SWCINT_CTL_DSR_INT_EN	(1<<10)
		#define	SWCINT_CTL_RI_INT_EN	(1<<11)
		#define	SWCINT_CTL_LINE_CHG_INT_EN	(1<<12)
		#define	SWCINT_CTL_BREAK_INT_EN	(1<<13)
		#define	SWCINT_CTL_RTS		(1<<14)
		#define	SWCINT_CTL_DTR		(1<<15)
		#define	SWCINT_CTL_DCD		(1<<16)
		#define	SWCINT_CTL_CTS		(1<<17)
		#define	SWCINT_CTL_DSR		(1<<18)
		#define	SWCINT_CTL_RI		(1<<19)
		#define	SWCINT_CTL_LINE_CHG	(1<<20)
	volatile uint32	int_control;

		#define	MATCH_CHAR_MASK		0xFF
		#define	MATCH_XON		(1<<8)
		#define	MATCH_EOF		(1<<9)
		#define	MATCH_XOFF		(1<<10)
	volatile uint32	match1;
	volatile uint32	match2;
	volatile uint32	match3;

		#define	TXFORCE_EMPTY		(1<<8)
	volatile uint32	tx_force;
	volatile uint32	async_rx_counter;

		#define	RXCNT_ENABLE		(1<<12)
	volatile uint32	async_rx_buffer_count;
	volatile uint32	rx_idle_count;

	volatile uint32	interval_timer;

		#define	ASYNC_DATABITS_5	(0 << 0)
		#define	ASYNC_DATABITS_6	(1 << 0)
		#define	ASYNC_DATABITS_7	(2 << 0)
		#define ASYNC_DATABITS_8	(3 << 0)
		#define	ASYNC_PARITY_EVEN	(0 << 2)
		#define	ASYNC_PARITY_ODD	(1 << 2)
		#define	ASYNC_PARITY_SPACE	(2 << 2)
		#define	ASYNC_PARITY_MARK	(3 << 2)
		#define	ASYNC_PARITY_ENABLE	(1<<4)
		#define	ASYNC_PARITY_MATCH	(1<<5)
		#define ASYNC_STOPBITS_2	(1<<6)
		#define	ASYNC_TX_BREAK		(1<<7)

		#define	HDLC_CRC32		(1<<0)
		#define	HDLC_CRC2MEM		(1<<1)
		#define	HDLC_RX_CRC_ENABLE	(1<<2)
		#define	HDLC_TX_CRC_ENABLE	(1<<3)
		#define	HDLC_TX_PREAMBLE	(1<<4)
		#define	HDLC_TX_MARK		(1<<5)
		#define	HDLC_TX_IDLE_FF		(1<<6)

		#define	TRANSP_TX_MARK		(1<<5)

		#define	ATM_TAG_LENGTH_MASK	3
		#define	ATM_STRIP_TAGS		(1<<2)
		#define	ATM_INSERT_HEC		(1<<3)
		#define	ATM_DISCARD_IDLES	(1<<4)
		#define	ATM_PASS_HEC		(1<<5)
		#define	ATM_SCRAMBLE		(1<<6)

		#define	FRAME_HDLC		(0 << 8)
		#define	FRAME_ASYNC		(1 << 8)
		#define	FRAME_TRANSPARENT	(2 << 8)
		#define	FRAME_ATM		(3 << 8)
		#define	CODE_NRZ		(0 << 10)
		#define	CODE_NRZI		(1 << 10)
		#define	CODE_FM0		(2 << 10)
		#define	CODE_FM1		(3 << 10)
		#define IGNORE_DCD		(1<<12)
		#define IGNORE_DSR		(1<<13)
		#define IGNORE_CTS		(1<<14)
		#define	SW_FLOW_ENABLE		(1<<15)
		#define	SW_FLOW			(1<<16)
		#define	INVERT_RXC		(1<<17)
		#define	PARITY_EOF		(1<<17)
		#define	I_STRIP			(1<<18)
	volatile uint32	chan_config;
	volatile uint32	tx_idle_count;
	volatile uint32	abrd_min_sample;
	volatile uint32	unused[112];
} RAP_SWC_REGS;

/* 232/422/485 Control registers.  There will be two of these structures
 * in memory, the first one is for ports 1-8, the second for 9-16 
 */
typedef struct rap_mpi_regs
{
#define MPI_PORT_MASK(X) (1 << (X))
	volatile uint8 port_mode;
	
	uint8 pad1[15];
	
	volatile uint8 two_wire;

	uint8 pad2[15];

	volatile uint8 rx_term;
	
	uint8 pad3[15];

	volatile uint8 tx_term;

	uint8 pad4[31];

	volatile uint8 rx_bias;

	uint8 pad5[175];

} RAP_MPI_REGS;


#define MPI_CSIZE_MASK		0x07
#define		MPI_CSIZE_7	0
#define		MPI_CSIZE_8	1
#define		MPI_CSIZE_9	2
#define		MPI_CSIZE_10	3
#define		MPI_CSIZE_11	4
#define		MPI_CSIZE_12	5

#define MPI_485_MODE		(1<<3)
#define MPI_TX_AUTO		(1<<4)
#define MPI_RX_AUTO		(1<<5)
#define MPI_TX_ENABLE		(1<<6)
#define MPI_RX_ENABLE		(1<<7)
typedef struct mpi_config_reg_int
{
  volatile uint8 reg;
  uint8 pad[15];
} MPI_CONFIG_REG_INT;

typedef struct rap_mpi_config_regs
{
	MPI_CONFIG_REG_INT config_reg[8];
	uint8 pad[143];
} RAP_MPI_CONFIG_REGS;

typedef struct rap_mbox_regs
{
	volatile uint32	tx_fifo;	/* 0x0000 */
	volatile uint32	unused1;
	volatile uint32	rx_fifo;	/* 0x0008 */
	volatile uint32	unused2;

	#define	MBOX_TX_EMPTY		(1<<0)
	#define	MBOX_TX_THLD		(1<<1)
	#define	MBOX_TX_FULL		(1<<2)
	#define MBOX_RX_EMPTY		(1<<3)
	#define	MBOX_RX_THLD		(1<<4)
	#define	MBOX_RX_FULL		(1<<5)
	#define	MBOX_CPU_WR_RX		(1<<8)
	#define	MBOX_CPU_RD_TX		(1<<9)
	#define	MBOX_PCI_WR_TX		(1<<10)
	#define	MBOX_PCI_RD_RX		(1<<11)
	#define MBOX_ENABLE_INT_TO_HOST	(1<<12)
	#define	MBOX_WR_FULL_RX		(1<<16)
	#define	MBOX_RD_EMPTY_RX	(1<<17)
	#define	MBOX_WR_FULL_TX		(1<<18)
	#define	MBOX_RD_EMPTY_TX	(1<<19)
	volatile uint32	xpci_ctrl;	/* 0x0010 */
	volatile uint32	unused3[7];

	#define MBOX_ENABLE	0x01
	volatile uint32	mbox_address;	/* 0x0030 */
	volatile uint32	unused4;

	#define MBOX_256_WORDS	0x80
	#define MBOX_128_WORDS	0x40
	#define MBOX_64_WORDS	0x20
	#define MBOX_32_WORDS	0x10
	volatile uint32	mbox_size;	/* 0x0038 */
	volatile uint32	unused5;
	volatile uint32	mbox_threshold;	/* 0x0040 */
	volatile uint32	unused6;
} RAP_MBOX_REGS;


typedef struct rap_wan_ctrl_regs
{
	#define	WAN_TSM1_ENABLE		(1<<0)
	#define	WAN_TSM2_ENABLE		(1<<1)
	#define	WAN_TSM3_ENABLE		(1<<2)
	#define	WAN_TSM4_ENABLE		(1<<3)
	#define	WAN_SELECT_RI0		(1<<4)
	#define	WAN_SELECT_RI1		(1<<5)
	#define	WAN_SELECT_RI2		(1<<6)
	#define	WAN_SELECT_RI3		(1<<7)
	#define	WAN_SELECT_RI4		(1<<8)
	#define	WAN_SELECT_RI5		(1<<9)
	#define	WAN_SELECT_RI6		(1<<10)
	#define	WAN_SELECT_RI7		(1<<11)
	#define	WAN_SELECT_RI8		(1<<12)
	volatile uint32	port_config;
	#define ALL_PORTS_USE_RI  ( \
		WAN_SELECT_RI0 | WAN_SELECT_RI1 | \
		WAN_SELECT_RI2 | WAN_SELECT_RI3 | \
		WAN_SELECT_RI4 | WAN_SELECT_RI5 | \
		WAN_SELECT_RI6 | WAN_SELECT_RI7 | \
		WAN_SELECT_RI8 )

} RAP_WAN_CTRL_REGS;


/* TODO: MPI CHANGES Add RAP2_MPI_REGS structures and defines */

/*
 *	Ethernet register definitions.
 */

typedef struct ethernet_regs
{
	#define	ETH_MAC_RST		(1<<6)
	#define	ETH_BKOFF_LIM_1023	(0 << 4)
	#define	ETH_BKOFF_LIM_255	(1 << 4)
	#define	ETH_BKOFF_LIM_15	(2 << 4)
	#define	ETH_BKOFF_LIM_1		(3 << 4)
	#define	ETH_STOP_BACKOFF	(1<<3)
	#define	ETH_CLK_DISABLE		(1<<2)
	#define	ETH_FULLDUPLEX		(1<<1)
	#define	ETH_CLK_SEL		(1<<0)
	volatile uint32	main_ctl;
	volatile uint32	mac_addr1;
	volatile uint32	mac_addr2;

	#define	ETH_MII_INVALID		(1<<5)
	#define	ETH_MII_LINK_FAILURE	(1<<4)
	#define	ETH_MII_SCAN		(1<<3)
	#define	ETH_MII_STATUS		(1<<2)
	#define	ETH_MII_LOAD_CONTROL	(1<<1)
	#define	ETH_MII_BUSY		(1<<0)
	volatile uint32	mii_ctl_stat;
	volatile uint32	mii_write;
	volatile uint32	mii_read;

	#define	ETH_RX_RESET		(1<<4)
	#define	ETH_RX_BAD_DROP		(1<<3)
	#define	ETH_RX_MULTI_BLOCK	(1<<2)
	#define	ETH_RX_BROAD_BLOCK	(1<<1)
	#define	ETH_RX_PROMISCUOUS	(1<<0)
	volatile uint32	rx_ctl;
	volatile uint32	rng_seed;

	#define	ETH_TX_PAD_ENABLE	(1<<3)
	#define	ETH_TX_NO_PREAMBLE	(1<<2)
	#define	ETH_TX_HUGE_ENABLE	(1<<1)
	#define	ETH_TX_CRC_ENABLE	(1<<0)
	volatile uint32	tx_ctl;
	volatile uint32	ipg1;
	volatile uint32	ipg2;
	volatile uint32	back2back_ipg;

	#define	ETH_FLOW_ENABLE		(1<<1)
	#define	ETH_FALSE_CARRIER_SENSE	(1<<0)
	volatile uint32	flow_ctl;

	#define	ETH_INT_TX_URUN		(1<<9)
	#define	ETH_INT_COL		(1<<8)
	#define	ETH_INT_DEF		(1<<7)
	#define	ETH_INT_LATE		(1<<6)
	#define	ETH_INT_HUGE		(1<<5)
	#define	ETH_INT_STAT_OVER_ENABLE	(1<<4)
	#define	ETH_INT_STAT_OVER	(1<<3)
	#define	ETH_INT_TXABT_ENABLE	(1<<2)
	#define	ETH_INT_TXABT		(1<<1)
	#define	ETH_INT_RX_OVER		(1<<0)
	volatile uint32	interrupt;
	/* Stats go here */
	volatile uint32	events_dropped_counter;
	volatile uint32	alignment_error_counter;
	volatile uint32	runt_counter;
	volatile uint32	giant_counter;
	volatile uint32	fragment_counter;
	volatile uint32	jabber_counter;
	volatile uint32	txunderrun_counter;
	volatile uint32	late_collision_counter;
	volatile uint32	carrier_loss_counter;
	volatile uint32	collision_histogram[15];
} ETHERNET_REGS;


/*
 *	Below, the __attribute__((section("register"))), produced
 *	by the REGISTER_SECTION macro when compiled for MIPS
 *	architecture, is enough to force non-GP-relative code
 *	to be emitted for accesses.
 */
extern RAP_CPU_REGS rap_cpu_regs REGISTER_SECTION;
extern RAP_LOCAL_MEM_REGS rap_lmc_regs REGISTER_SECTION;
extern RAP_PCI_DMAC_REGS rap_pci_dmac_regs REGISTER_SECTION;
extern RAP_PCI_REGS rap_pci_regs REGISTER_SECTION;
extern RAP_TIMER_REGS rap_timer_regs REGISTER_SECTION;
extern RAP_RTC_REGS rap_rtc_regs REGISTER_SECTION;
extern RAP_SWC_REGS rap_swc_regs[NSWCS] REGISTER_SECTION;
extern RAP_MPI_REGS rap_mpi_regs[2] REGISTER_SECTION;
extern RAP_MPI_CONFIG_REGS rap_mpi_config_regs[2] REGISTER_SECTION;
extern RAP_DMAC_REGS rap_dmac_regs REGISTER_SECTION;
extern RAP_MBOX_REGS rap_mbox_regs REGISTER_SECTION;
extern RAP_WAN_CTRL_REGS rap_wan_ctrl_regs REGISTER_SECTION;
extern RAP_GPIO_REGS rap_gpio_regs REGISTER_SECTION;
#undef	REGISTER_SECTION

#define V_OFF(a,b) offsetof(struct a, b)
#if 0
#define	CASSERT(x)	struct {char CASSERT_FAILED[2*(x)-1];}

union __asserts__
{
CASSERT(0x00 == V_OFF(rap_cpu_regs, int_remap)) int_remap;
CASSERT(0x04 == V_OFF(rap_cpu_regs, int_pending)) int_pending;
CASSERT(0x08 == V_OFF(rap_cpu_regs, int_enable)) int_enable;

CASSERT(0x00 == V_OFF(rap_gpio_regs, gpio_ctl)) gpio_ctl;
CASSERT(0x04 == V_OFF(rap_gpio_regs, gpio_config)) gpio_config;

CASSERT(0x00 == V_OFF(local_mem_regs, dram_refresh)) dram_refresh;
CASSERT(0x08 == V_OFF(local_mem_regs, sdram_control)) sdram_control;
CASSERT(0x30 == V_OFF(local_mem_regs, phy_control)) phy_control;

CASSERT(0x08 == V_OFF(rap_pci_dmac_regs, interrupt)) interrupt;
CASSERT(0x18 == V_OFF(rap_pci_dmac_regs, bmd_pointer)) bmd_pointer;

/*CASSERT(0x00 == V_OFF(rap_reset_ctrl_regs, cpu_reset_control)) */
/*	cpu_reset_control; */
/*CASSERT(0x18 == V_OFF(rap_reset_ctrl_regs, local_mem_size)) */
/*	local_mem_size; */
/*CASSERT(0x38 == V_OFF(rap_reset_ctrl_regs, rap_local_memory_addr)) */
/*	rap_local_memory_addr; */

CASSERT(0x08 == V_OFF(rap2_dmac_regs, rx_ch_enable)) rx_ch_enable;
CASSERT(0x38 == V_OFF(rap2_dmac_regs, rx_transparent)) rx_transparent;
CASSERT(0x50 == V_OFF(rap2_dmac_regs, bmd_free)) bmd_free;

CASSERT(0x100 == V_OFF(rap2_dmac_regs, tx_bmd[0].reg)) tx_bmd0;
CASSERT(0x108 == V_OFF(rap2_dmac_regs, tx_bmd[1].reg)) tx_bmd1;

CASSERT(0x200 == V_OFF(rap2_dmac_regs, rx_bmd[0].reg)) rx_bmd0;
CASSERT(0x208 == V_OFF(rap2_dmac_regs, rx_bmd[1].reg)) rx_bmd1;

CASSERT(0x300 == V_OFF(rap2_dmac_regs, tx_int_status[0].reg))
	tx_int_status0;
CASSERT(0x308 == V_OFF(rap2_dmac_regs, tx_int_status[1].reg))
	tx_int_status1;

CASSERT(0x400 == V_OFF(rap2_dmac_regs, rx_int_status[0].reg))
	rx_int_status0;
CASSERT(0x408 == V_OFF(rap2_dmac_regs, rx_int_status[1].reg))
	rx_int_status1;

CASSERT(16 == sizeof(struct pci_bmd)) pci_bmd;

CASSERT(16 == sizeof(struct mc_bmd)) mc_bmd;

CASSERT(0x3C == V_OFF(rap_swc_regs, abrd_min_sample))
	abrd_min_sample;
CASSERT(0x200 == sizeof(struct rap_swc_regs)) rap2_swc_regs;

CASSERT(0x30 == V_OFF(rap_mbox_regs, mbox_address)) mbox_address;
CASSERT(0x20 == V_OFF(rap_timers, enhanced_config)) enhanced_config;
CASSERT(0x8 == V_OFF(rap_rtc_regs, rtc_alarm)) rtc_alarm;

CASSERT(0x00 == V_OFF(rap_mpi_regs, port_mode)) port_mode0;
CASSERT(0X10 == V_OFF(rap_mpi_regs, two_wire)) two_wire0;
CASSERT(0X20 == V_OFF(rap_mpi_regs, rx_term)) rx_term0;
CASSERT(0X30 == V_OFF(rap_mpi_regs, tx_term)) tx_term0;
CASSERT(0X50 == V_OFF(rap_mpi_regs, rx_bias)) rx_bias0;

  /* These are here more as documentation than for testing, because of
   * the way V_OFF works I can't subscript rap_mpi_regs array. */
#if 0
CASSERT(0x100 == V_OFF(rap_mpi_regs, port_mode)) port_mode1;
CASSERT(0X110 == V_OFF(rap_mpi_regs, two_wire)) two_wire1;
CASSERT(0X120 == V_OFF(rap_mpi_regs, rx_term)) rx_term1;
CASSERT(0X130 == V_OFF(rap_mpi_regs, tx_term)) tx_term1;
CASSERT(0X150 == V_OFF(rap_mpi_regs, rx_bias)) rx_bias1;
#endif

CASSERT(0x00 == V_OFF(rap_phy_regs, Semaphore)) Semaphore;
CASSERT(0x10 == V_OFF(rap_phy_regs, Reset)) Reset;
CASSERT(0x20 == V_OFF(rap_phy_regs, Interrupt[0].Reg)) Int0;
CASSERT(0x30 == V_OFF(rap_phy_regs, Interrupt[1].Reg)) Int1;
CASSERT(0x40 == V_OFF(rap_phy_regs, Interrupt[2].Reg)) Int2;
CASSERT(0x50 == V_OFF(rap_phy_regs, Interrupt[3].Reg)) Int3;
CASSERT(0x60 == V_OFF(rap_phy_regs, Tuning)) Tuning;


  
};
#endif


#ifdef __mips
/*
 *	rap2_flush_wb - Flush write buffer on rap2.
 *
 *	This guarantees a write buffer flush even if read priority is turned on.
 *	Using a register uses fewer clocks than using ram for the purpose and
 *	keeps the cpu off of the memory bus.
 */

inline static volatile 
void
rap2_flush_wb(void)
{
	rap_cpu_regs.memory_error_addr = 0;	/* Write ignored to this register */
	rap_cpu_regs.memory_error_addr;		/* Read the register */
}
#endif	/* __mips */


#endif
