summaryrefslogtreecommitdiff
path: root/board/pcippc2
diff options
context:
space:
mode:
Diffstat (limited to 'board/pcippc2')
-rwxr-xr-xboard/pcippc2/Makefile45
-rwxr-xr-xboard/pcippc2/config.mk30
-rwxr-xr-xboard/pcippc2/cpc710.h96
-rwxr-xr-xboard/pcippc2/cpc710_init_ram.c254
-rwxr-xr-xboard/pcippc2/cpc710_pci.c309
-rwxr-xr-xboard/pcippc2/cpc710_pci.h51
-rwxr-xr-xboard/pcippc2/flash.c573
-rwxr-xr-xboard/pcippc2/fpga_serial.c132
-rwxr-xr-xboard/pcippc2/fpga_serial.h34
-rwxr-xr-xboard/pcippc2/hardware.h48
-rwxr-xr-xboard/pcippc2/i2c.c257
-rwxr-xr-xboard/pcippc2/i2c.h36
-rwxr-xr-xboard/pcippc2/ns16550.h41
-rwxr-xr-xboard/pcippc2/pcippc2.c245
-rwxr-xr-xboard/pcippc2/pcippc2.h51
-rwxr-xr-xboard/pcippc2/pcippc2_fpga.c87
-rwxr-xr-xboard/pcippc2/pcippc2_fpga.h49
-rwxr-xr-xboard/pcippc2/sconsole.c141
-rwxr-xr-xboard/pcippc2/sconsole.h49
-rwxr-xr-xboard/pcippc2/u-boot.lds141
20 files changed, 2669 insertions, 0 deletions
diff --git a/board/pcippc2/Makefile b/board/pcippc2/Makefile
new file mode 100755
index 0000000..2998f23
--- /dev/null
+++ b/board/pcippc2/Makefile
@@ -0,0 +1,45 @@
+#
+# (C) Copyright 2002
+# Wolfgang Denk, DENX Software Engineering, wd@denx.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 $(TOPDIR)/config.mk
+
+LIB = lib$(BOARD).a
+
+COBJS = $(BOARD).o cpc710_pci.o flash.o sconsole.o \
+ fpga_serial.o pcippc2_fpga.o cpc710_init_ram.o i2c.o
+
+AOBJS =
+
+OBJS = $(COBJS) $(AOBJS)
+
+$(LIB): .depend $(OBJS)
+ $(AR) crv $@ $(OBJS)
+
+#########################################################################
+
+.depend: Makefile $(AOBJS:.o=.S) $(COBJS:.o=.c)
+ $(CC) -M $(CFLAGS) $(AOBJS:.o=.S) $(COBJS:.o=.c) > $@
+
+sinclude .depend
+
+#########################################################################
diff --git a/board/pcippc2/config.mk b/board/pcippc2/config.mk
new file mode 100755
index 0000000..92d37c9
--- /dev/null
+++ b/board/pcippc2/config.mk
@@ -0,0 +1,30 @@
+#
+# (C) Copyright 2002
+# Wolfgang Denk, DENX Software Engineering, wd@denx.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
+#
+
+#
+# PCIPPC-2 boards
+#
+
+TEXT_BASE = 0xfff00000
+
+PLATFORM_CPPFLAGS += -DTEXT_BASE=$(TEXT_BASE)
diff --git a/board/pcippc2/cpc710.h b/board/pcippc2/cpc710.h
new file mode 100755
index 0000000..8167270
--- /dev/null
+++ b/board/pcippc2/cpc710.h
@@ -0,0 +1,96 @@
+/*
+ * (C) Copyright 2002
+ * Wolfgang Denk, DENX Software Engineering, wd@denx.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
+ */
+
+#ifndef _CPC710_H_
+#define _CPC710_H_
+
+/* Revision */
+#define CPC710_TYPE_100 0x80
+#define CPC710_TYPE_100P 0x90
+
+/* System control area */
+#define HW_PHYS_SCA 0xff000000
+
+#define HW_SCA_CPC0 0x000000
+#define HW_SCA_SDRAM0 0x000000
+#define HW_SCA_DMA0 0x1C0000
+
+#define HW_PHYS_CPC0 (HW_PHYS_SCA + HW_SCA_CPC0)
+#define HW_PHYS_SDRAM0 (HW_PHYS_SCA + HW_SCA_SDRAM0)
+
+#define HW_CPC0_PCICNFR 0x000c
+#define HW_CPC0_RSTR 0x0010
+#define HW_CPC0_SPOR 0x00e8
+#define HW_CPC0_UCTL 0x1000
+#define HW_CPC0_SIOC0 0x1020
+#define HW_CPC0_ABCNTL 0x1030
+#define HW_CPC0_SESR 0x1060
+#define HW_CPC0_SEAR 0x1070
+#define HW_CPC0_PGCHP 0x1100
+#define HW_CPC0_RGBAN0 0x1110
+#define HW_CPC0_RGBAN1 0x1120
+
+#define HW_CPC0_GPDIR 0x1130
+#define HW_CPC0_GPIN 0x1140
+#define HW_CPC0_GPOUT 0x1150
+
+#define HW_CPC0_ATAS 0x1160
+
+#define HW_CPC0_PCIBAR 0x200018
+#define HW_CPC0_PCIENB 0x201000
+
+#define HW_SDRAM0_MCCR 0x1200
+#define HW_SDRAM0_MESR 0x1220
+#define HW_SDRAM0_MEAR 0x1230
+
+#define HW_SDRAM0_MCER0 0x1300
+#define HW_SDRAM0_MCER1 0x1310
+#define HW_SDRAM0_MCER2 0x1320
+#define HW_SDRAM0_MCER3 0x1330
+#define HW_SDRAM0_MCER4 0x1340
+#define HW_SDRAM0_MCER5 0x1350
+#define HW_SDRAM0_MCER6 0x1360
+#define HW_SDRAM0_MCER7 0x1370
+
+#define HW_BRIDGE_PCIDG 0xf6120
+#define HW_BRIDGE_INTACK 0xf7700
+#define HW_BRIDGE_PIBAR 0xf7800
+#define HW_BRIDGE_PMBAR 0xf7810
+#define HW_BRIDGE_CRR 0xf7ef0
+#define HW_BRIDGE_PR 0xf7f20
+#define HW_BRIDGE_ACR 0xf7f30
+#define HW_BRIDGE_MSIZE 0xf7f40
+#define HW_BRIDGE_IOSIZE 0xf7f60
+#define HW_BRIDGE_SMBAR 0xf7f80
+#define HW_BRIDGE_SIBAR 0xf7fc0
+#define HW_BRIDGE_CFGADDR 0xf8000
+#define HW_BRIDGE_CFGDATA 0xf8010
+#define HW_BRIDGE_PSSIZE 0xf8100
+#define HW_BRIDGE_BARPS 0xf8120
+#define HW_BRIDGE_PSBAR 0xf8140
+
+/* Configuration space registers */
+#define CPC710_BUS_NUMBER 0x40
+#define CPC710_SUB_BUS_NUMBER 0x41
+
+#endif
diff --git a/board/pcippc2/cpc710_init_ram.c b/board/pcippc2/cpc710_init_ram.c
new file mode 100755
index 0000000..57ed8f0
--- /dev/null
+++ b/board/pcippc2/cpc710_init_ram.c
@@ -0,0 +1,254 @@
+/*
+ * (C) Copyright 2002
+ * Wolfgang Denk, DENX Software Engineering, wd@denx.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 <config.h>
+#include <common.h>
+#include <asm/io.h>
+
+#include "pcippc2.h"
+#include "i2c.h"
+
+typedef struct cpc710_mem_org_s
+{
+ u8 rows;
+ u8 cols;
+ u8 banks2;
+ u8 org;
+} cpc710_mem_org_t;
+
+static int cpc710_compute_mcer (u32 * mcer,
+ unsigned long *
+ size,
+ unsigned int sdram);
+static int cpc710_eeprom_checksum (unsigned int sdram);
+static u8 cpc710_eeprom_read (unsigned int sdram,
+ unsigned int offset);
+
+static u32 cpc710_mcer_mem [] =
+{
+ 0x000003f3, /* 18 lines, 4 Mb */
+ 0x000003e3, /* 19 lines, 8 Mb */
+ 0x000003c3, /* 20 lines, 16 Mb */
+ 0x00000383, /* 21 lines, 32 Mb */
+ 0x00000303, /* 22 lines, 64 Mb */
+ 0x00000203, /* 23 lines, 128 Mb */
+ 0x00000003, /* 24 lines, 256 Mb */
+ 0x00000002, /* 25 lines, 512 Mb */
+ 0x00000001 /* 26 lines, 1024 Mb */
+};
+static cpc710_mem_org_t cpc710_mem_org [] =
+{
+ { 0x0c, 0x09, 0x02, 0x00 }, /* 0000: 12/ 9/2 */
+ { 0x0d, 0x09, 0x02, 0x00 }, /* 0000: 13/ 9/2 */
+ { 0x0d, 0x0a, 0x02, 0x00 }, /* 0000: 13/10/2 */
+ { 0x0d, 0x0b, 0x02, 0x00 }, /* 0000: 13/11/2 */
+ { 0x0d, 0x0c, 0x02, 0x00 }, /* 0000: 13/12/2 */
+ { 0x0e, 0x0c, 0x02, 0x00 }, /* 0000: 14/12/2 */
+ { 0x0b, 0x08, 0x02, 0x01 }, /* 0001: 11/ 8/2 */
+ { 0x0b, 0x09, 0x01, 0x02 }, /* 0010: 11/ 9/1 */
+ { 0x0b, 0x0a, 0x01, 0x03 }, /* 0011: 11/10/1 */
+ { 0x0c, 0x08, 0x02, 0x04 }, /* 0100: 12/ 8/2 */
+ { 0x0c, 0x0a, 0x02, 0x05 }, /* 0101: 12/10/2 */
+ { 0x0d, 0x08, 0x01, 0x06 }, /* 0110: 13/ 8/1 */
+ { 0x0d, 0x08, 0x02, 0x07 }, /* 0111: 13/ 8/2 */
+ { 0x0d, 0x09, 0x01, 0x08 }, /* 1000: 13/ 9/1 */
+ { 0x0d, 0x0a, 0x01, 0x09 }, /* 1001: 13/10/1 */
+ { 0x0b, 0x08, 0x01, 0x0a }, /* 1010: 11/ 8/1 */
+ { 0x0c, 0x08, 0x01, 0x0b }, /* 1011: 12/ 8/1 */
+ { 0x0c, 0x09, 0x01, 0x0c }, /* 1100: 12/ 9/1 */
+ { 0x0e, 0x09, 0x02, 0x0d }, /* 1101: 14/ 9/2 */
+ { 0x0e, 0x0a, 0x02, 0x0e }, /* 1110: 14/10/2 */
+ { 0x0e, 0x0b, 0x02, 0x0f } /* 1111: 14/11/2 */
+};
+
+unsigned long cpc710_ram_init (void)
+{
+ unsigned long memsize = 0;
+ unsigned long bank_size;
+ u32 mcer;
+
+#ifndef CFG_RAMBOOT
+ /* Clear memory banks
+ */
+ out32(REG(SDRAM0, MCER0), 0);
+ out32(REG(SDRAM0, MCER1), 0);
+ out32(REG(SDRAM0, MCER2), 0);
+ out32(REG(SDRAM0, MCER3), 0);
+ out32(REG(SDRAM0, MCER4), 0);
+ out32(REG(SDRAM0, MCER5), 0);
+ out32(REG(SDRAM0, MCER6), 0);
+ out32(REG(SDRAM0, MCER7), 0);
+ iobarrier_rw();
+
+ /* Disable memory
+ */
+ out32(REG(SDRAM0,MCCR), 0x13b06000);
+ iobarrier_rw();
+#endif
+
+ /* Only the first memory bank is initialised now
+ */
+ if (! cpc710_compute_mcer(& mcer, & bank_size, 0))
+ {
+ puts("Unsupported SDRAM type !\n");
+ hang();
+ }
+ memsize += bank_size;
+#ifndef CFG_RAMBOOT
+ /* Enable bank, zero start
+ */
+ out32(REG(SDRAM0, MCER0), mcer | 0x80000000);
+ iobarrier_rw();
+#endif
+
+#ifndef CFG_RAMBOOT
+ /* Enable memory
+ */
+ out32(REG(SDRAM0, MCCR), in32(REG(SDRAM0, MCCR)) | 0x80000000);
+
+ /* Wait until initialisation finished
+ */
+ while (! (in32 (REG(SDRAM0, MCCR)) & 0x20000000))
+ {
+ iobarrier_rw();
+ }
+
+ /* Clear Memory Error Status and Address registers
+ */
+ out32(REG(SDRAM0, MESR), 0);
+ out32(REG(SDRAM0, MEAR), 0);
+ iobarrier_rw();
+
+ /* ECC is not configured now
+ */
+#endif
+
+ /* Memory size counter
+ */
+ out32(REG(CPC0, RGBAN1), memsize);
+
+ return memsize;
+}
+
+static int cpc710_compute_mcer (
+ u32 * mcer,
+ unsigned long * size,
+ unsigned int sdram)
+{
+ u8 rows;
+ u8 cols;
+ u8 banks2;
+ unsigned int lines;
+ u32 mc = 0;
+ unsigned int i;
+ cpc710_mem_org_t * org = 0;
+
+
+ if (! i2c_reset())
+ {
+ puts("Can't reset I2C!\n");
+ hang();
+ }
+
+ if (! cpc710_eeprom_checksum(sdram))
+ {
+ puts("Invalid EEPROM checksum !\n");
+ hang();
+ }
+
+ rows = cpc710_eeprom_read(sdram, 3);
+ cols = cpc710_eeprom_read(sdram, 4);
+ /* Can be 2 or 4 banks; divide by 2
+ */
+ banks2 = cpc710_eeprom_read(sdram, 17) / 2;
+
+ lines = rows + cols + banks2;
+
+ if (lines < 18 || lines > 26)
+ {
+ /* Unsupported configuration
+ */
+ return 0;
+ }
+
+
+ mc |= cpc710_mcer_mem [lines - 18] << 6;
+
+ for (i = 0; i < sizeof(cpc710_mem_org) / sizeof(cpc710_mem_org_t); i++)
+ {
+ cpc710_mem_org_t * corg = cpc710_mem_org + i;
+
+ if (corg->rows == rows && corg->cols == cols && corg->banks2 == banks2)
+ {
+ org = corg;
+
+ break;
+ }
+ }
+
+ if (! org)
+ {
+ /* Unsupported configuration
+ */
+ return 0;
+ }
+
+ mc |= (u32) org->org << 2;
+
+ /* Supported configuration
+ */
+ *mcer = mc;
+ *size = 1l << (lines + 4);
+
+ return 1;
+}
+
+static int cpc710_eeprom_checksum (
+ unsigned int sdram)
+{
+ u8 sum = 0;
+ unsigned int i;
+
+ for (i = 0; i < 63; i++)
+ {
+ sum += cpc710_eeprom_read(sdram, i);
+ }
+
+ return sum == cpc710_eeprom_read(sdram, 63);
+}
+
+static u8 cpc710_eeprom_read (
+ unsigned int sdram,
+ unsigned int offset)
+{
+ u8 dev = (sdram << 1) | 0xa0;
+ u8 data;
+
+ if (! i2c_read_byte(& data, dev,offset))
+ {
+ puts("I2C error !\n");
+ hang();
+ }
+
+ return data;
+}
diff --git a/board/pcippc2/cpc710_pci.c b/board/pcippc2/cpc710_pci.c
new file mode 100755
index 0000000..bed8aea
--- /dev/null
+++ b/board/pcippc2/cpc710_pci.c
@@ -0,0 +1,309 @@
+/*
+ * (C) Copyright 2002
+ * Wolfgang Denk, DENX Software Engineering, wd@denx.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 <config.h>
+#include <common.h>
+#include <asm/io.h>
+#include <pci.h>
+
+#include "hardware.h"
+#include "pcippc2.h"
+
+struct pci_controller local_hose, cpci_hose;
+
+static u32 cpc710_mapped_ram;
+
+ /* Enable PCI retry timeouts
+ */
+void cpc710_pci_enable_timeout (void)
+{
+ out32(BRIDGE(LOCAL, CFGADDR), 0x50000080);
+ iobarrier_rw();
+ out32(BRIDGE(LOCAL, CFGDATA), 0x32000000);
+ iobarrier_rw();
+
+ out32(BRIDGE(CPCI, CFGADDR), 0x50000180);
+ iobarrier_rw();
+ out32(BRIDGE(CPCI, CFGDATA), 0x32000000);
+ iobarrier_rw();
+}
+
+void cpc710_pci_init (void)
+{
+ u32 sdram_size = pcippc2_sdram_size();
+
+ cpc710_mapped_ram = sdram_size < PCI_MEMORY_MAXSIZE ?
+ sdram_size : PCI_MEMORY_MAXSIZE;
+
+ /* Select the local PCI
+ */
+ out32(REG(CPC0, PCICNFR), 0x80000002);
+ iobarrier_rw();
+
+ out32(REG(CPC0, PCIBAR), BRIDGE_LOCAL_PHYS);
+ iobarrier_rw();
+
+ /* Enable PCI bridge address decoding
+ */
+ out32(REG(CPC0, PCIENB), 0x80000000);
+ iobarrier_rw();
+
+ /* Select the CPCI bridge
+ */
+ out32(REG(CPC0, PCICNFR), 0x80000003);
+ iobarrier_rw();
+
+ out32(REG(CPC0, PCIBAR), BRIDGE_CPCI_PHYS);
+ iobarrier_rw();
+
+ /* Enable PCI bridge address decoding
+ */
+ out32(REG(CPC0, PCIENB), 0x80000000);
+ iobarrier_rw();
+
+ /* Disable configuration accesses
+ */
+ out32(REG(CPC0, PCICNFR), 0x80000000);
+ iobarrier_rw();
+
+ /* Initialise the local PCI
+ */
+ out32(BRIDGE(LOCAL, CRR), 0x7c000000);
+ iobarrier_rw();
+ out32(BRIDGE(LOCAL, PCIDG), 0x40000000);
+ iobarrier_rw();
+ out32(BRIDGE(LOCAL, PIBAR), BRIDGE_LOCAL_IO_BUS);
+ out32(BRIDGE(LOCAL, SIBAR), BRIDGE_LOCAL_IO_PHYS);
+ out32(BRIDGE(LOCAL, IOSIZE), -BRIDGE_LOCAL_IO_SIZE);
+ iobarrier_rw();
+ out32(BRIDGE(LOCAL, PMBAR), BRIDGE_LOCAL_MEM_BUS);
+ out32(BRIDGE(LOCAL, SMBAR), BRIDGE_LOCAL_MEM_PHYS);
+ out32(BRIDGE(LOCAL, MSIZE), -BRIDGE_LOCAL_MEM_SIZE);
+ iobarrier_rw();
+ out32(BRIDGE(LOCAL, PR), 0x00ffe000);
+ iobarrier_rw();
+ out32(BRIDGE(LOCAL, ACR), 0xfe000000);
+ iobarrier_rw();
+ out32(BRIDGE(LOCAL, PSBAR), PCI_MEMORY_BUS >> 24);
+ out32(BRIDGE(LOCAL, BARPS), PCI_MEMORY_PHYS >> 24);
+ out32(BRIDGE(LOCAL, PSSIZE), 256 - (cpc710_mapped_ram >> 24));
+ iobarrier_rw();
+
+ /* Initialise the CPCI bridge
+ */
+ out32(BRIDGE(CPCI, CRR), 0x7c000000);
+ iobarrier_rw();
+ out32(BRIDGE(CPCI, PCIDG), 0xC0000000);
+ iobarrier_rw();
+ out32(BRIDGE(CPCI, PIBAR), BRIDGE_CPCI_IO_BUS);
+ out32(BRIDGE(CPCI, SIBAR), BRIDGE_CPCI_IO_PHYS);
+ out32(BRIDGE(CPCI, IOSIZE), -BRIDGE_CPCI_IO_SIZE);
+ iobarrier_rw();
+ out32(BRIDGE(CPCI, PMBAR), BRIDGE_CPCI_MEM_BUS);
+ out32(BRIDGE(CPCI, SMBAR), BRIDGE_CPCI_MEM_PHYS);
+ out32(BRIDGE(CPCI, MSIZE), -BRIDGE_CPCI_MEM_SIZE);
+ iobarrier_rw();
+ out32(BRIDGE(CPCI, PR), 0x80ffe000);
+ iobarrier_rw();
+ out32(BRIDGE(CPCI, ACR), 0xdf000000);
+ iobarrier_rw();
+ out32(BRIDGE(CPCI, PSBAR), PCI_MEMORY_BUS >> 24);
+ out32(BRIDGE(CPCI, BARPS), PCI_MEMORY_PHYS >> 24);
+ out32(BRIDGE(CPCI, PSSIZE), 256 - (cpc710_mapped_ram >> 24));
+ iobarrier_rw();
+
+ /* Local PCI
+ */
+
+ out32(BRIDGE(LOCAL, CFGADDR), 0x04000080);
+ iobarrier_rw();
+ out32(BRIDGE(LOCAL, CFGDATA), 0x56010000);
+ iobarrier_rw();
+
+ out32(BRIDGE(LOCAL, CFGADDR), 0x0c000080);
+ iobarrier_rw();
+ out32(BRIDGE(LOCAL, CFGDATA), PCI_LATENCY_TIMER_VAL << 16);
+ iobarrier_rw();
+
+ /* Set bus and subbus numbers
+ */
+ out32(BRIDGE(LOCAL, CFGADDR), 0x40000080);
+ iobarrier_rw();
+ out32(BRIDGE(LOCAL, CFGDATA), 0x00000000);
+ iobarrier_rw();
+
+ out32(BRIDGE(LOCAL, CFGADDR), 0x50000080);
+ iobarrier_rw();
+ /* PCI retry timeouts will be enabled later
+ */
+ out32(BRIDGE(LOCAL, CFGDATA), 0x00000000);
+ iobarrier_rw();
+
+ /* CPCI
+ */
+
+ /* Set bus and subbus numbers
+ */
+ out32(BRIDGE(CPCI, CFGADDR), 0x40000080);
+ iobarrier_rw();
+ out32(BRIDGE(CPCI, CFGDATA), 0x01010000);
+ iobarrier_rw();
+
+ out32(BRIDGE(CPCI, CFGADDR), 0x04000180);
+ iobarrier_rw();
+ out32(BRIDGE(CPCI, CFGDATA), 0x56010000);
+ iobarrier_rw();
+
+ out32(BRIDGE(CPCI, CFGADDR), 0x0c000180);
+ iobarrier_rw();
+ out32(BRIDGE(CPCI, CFGDATA), PCI_LATENCY_TIMER_VAL << 16);
+ iobarrier_rw();
+
+ /* Write to the PSBAR */
+ out32(BRIDGE(CPCI, CFGADDR), 0x10000180);
+ iobarrier_rw();
+ out32(BRIDGE(CPCI, CFGDATA), cpu_to_le32(PCI_MEMORY_BUS));
+ iobarrier_rw();
+
+ /* Set bus and subbus numbers
+ */
+ out32(BRIDGE(CPCI, CFGADDR), 0x40000180);
+ iobarrier_rw();
+ out32(BRIDGE(CPCI, CFGDATA), 0x01ff0000);
+ iobarrier_rw();
+
+ out32(BRIDGE(CPCI, CFGADDR), 0x50000180);
+ iobarrier_rw();
+ out32(BRIDGE(CPCI, CFGDATA), 0x32000000);
+ /* PCI retry timeouts will be enabled later
+ */
+ out32(BRIDGE(CPCI, CFGDATA), 0x00000000);
+ iobarrier_rw();
+
+ /* Remove reset on the PCI buses
+ */
+ out32(BRIDGE(LOCAL, CRR), 0xfc000000);
+ iobarrier_rw();
+ out32(BRIDGE(CPCI, CRR), 0xfc000000);
+ iobarrier_rw();
+
+ local_hose.first_busno = 0;
+ local_hose.last_busno = 0xff;
+
+ /* System memory space */
+ pci_set_region(local_hose.regions + 0,
+ PCI_MEMORY_BUS,
+ PCI_MEMORY_PHYS,
+ PCI_MEMORY_MAXSIZE,
+ PCI_REGION_MEM | PCI_REGION_MEMORY);
+
+ /* PCI memory space */
+ pci_set_region(local_hose.regions + 1,
+ BRIDGE_LOCAL_MEM_BUS,
+ BRIDGE_LOCAL_MEM_PHYS,
+ BRIDGE_LOCAL_MEM_SIZE,
+ PCI_REGION_MEM);
+
+ /* PCI I/O space */
+ pci_set_region(local_hose.regions + 2,
+ BRIDGE_LOCAL_IO_BUS,
+ BRIDGE_LOCAL_IO_PHYS,
+ BRIDGE_LOCAL_IO_SIZE,
+ PCI_REGION_IO);
+
+ local_hose.region_count = 3;
+
+ pci_setup_indirect(&local_hose,
+ BRIDGE_LOCAL_PHYS + HW_BRIDGE_CFGADDR,
+ BRIDGE_LOCAL_PHYS + HW_BRIDGE_CFGDATA);
+
+ pci_register_hose(&local_hose);
+
+ /* Initialize PCI32 bus registers */
+ pci_hose_write_config_byte(&local_hose,
+ PCI_BDF(local_hose.first_busno,0,0),
+ CPC710_BUS_NUMBER,
+ local_hose.first_busno);
+ pci_hose_write_config_byte(&local_hose,
+ PCI_BDF(local_hose.first_busno,0,0),
+ CPC710_SUB_BUS_NUMBER,
+ local_hose.last_busno);
+
+ local_hose.last_busno = pci_hose_scan(&local_hose);
+
+ /* Write out correct max subordinate bus number for local hose */
+ pci_hose_write_config_byte(&local_hose,
+ PCI_BDF(local_hose.first_busno,0,0),
+ CPC710_SUB_BUS_NUMBER,
+ local_hose.last_busno);
+
+ cpci_hose.first_busno = local_hose.last_busno + 1;
+ cpci_hose.last_busno = 0xff;
+
+ /* System memory space */
+ pci_set_region(cpci_hose.regions + 0,
+ PCI_MEMORY_BUS,
+ PCI_MEMORY_PHYS,
+ PCI_MEMORY_MAXSIZE,
+ PCI_REGION_MEMORY);
+
+ /* PCI memory space */
+ pci_set_region(cpci_hose.regions + 1,
+ BRIDGE_CPCI_MEM_BUS,
+ BRIDGE_CPCI_MEM_PHYS,
+ BRIDGE_CPCI_MEM_SIZE,
+ PCI_REGION_MEM);
+
+ /* PCI I/O space */
+ pci_set_region(cpci_hose.regions + 2,
+ BRIDGE_CPCI_IO_BUS,
+ BRIDGE_CPCI_IO_PHYS,
+ BRIDGE_CPCI_IO_SIZE,
+ PCI_REGION_IO);
+
+ cpci_hose.region_count = 3;
+
+ pci_setup_indirect(&cpci_hose,
+ BRIDGE_CPCI_PHYS + HW_BRIDGE_CFGADDR,
+ BRIDGE_CPCI_PHYS + HW_BRIDGE_CFGDATA);
+
+ pci_register_hose(&cpci_hose);
+
+ /* Initialize PCI64 bus registers */
+ pci_hose_write_config_byte(&cpci_hose,
+ PCI_BDF(cpci_hose.first_busno,0,0),
+ CPC710_BUS_NUMBER,
+ cpci_hose.first_busno);
+ pci_hose_write_config_byte(&cpci_hose,
+ PCI_BDF(cpci_hose.first_busno,0,0),
+ CPC710_SUB_BUS_NUMBER,
+ cpci_hose.last_busno);
+
+ cpci_hose.last_busno = pci_hose_scan(&cpci_hose);
+
+ /* Write out correct max subordinate bus number for cpci hose */
+ pci_hose_write_config_byte(&cpci_hose,
+ PCI_BDF(cpci_hose.first_busno,0,0),
+ CPC710_SUB_BUS_NUMBER,
+ cpci_hose.last_busno);
+}
diff --git a/board/pcippc2/cpc710_pci.h b/board/pcippc2/cpc710_pci.h
new file mode 100755
index 0000000..24d0db6
--- /dev/null
+++ b/board/pcippc2/cpc710_pci.h
@@ -0,0 +1,51 @@
+/*
+ * (C) Copyright 2002
+ * Wolfgang Denk, DENX Software Engineering, wd@denx.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
+ */
+
+#ifndef _CPC710_PCI_H_
+#define _CPC710_PCI_H_
+
+#define PCI_MEMORY_PHYS 0x00000000
+#define PCI_MEMORY_BUS 0x80000000
+#define PCI_MEMORY_MAXSIZE 0x20000000
+
+#define BRIDGE_CPCI_PHYS 0xff500000
+#define BRIDGE_CPCI_MEM_SIZE 0x08000000
+#define BRIDGE_CPCI_MEM_PHYS 0xf0000000
+#define BRIDGE_CPCI_MEM_BUS 0x00000000
+#define BRIDGE_CPCI_IO_SIZE 0x02000000
+#define BRIDGE_CPCI_IO_PHYS 0xfc000000
+#define BRIDGE_CPCI_IO_BUS 0x00000000
+
+#define BRIDGE_LOCAL_PHYS 0xff400000
+#define BRIDGE_LOCAL_MEM_SIZE 0x04000000
+#define BRIDGE_LOCAL_MEM_PHYS 0xf8000000
+#define BRIDGE_LOCAL_MEM_BUS 0x40000000
+#define BRIDGE_LOCAL_IO_SIZE 0x01000000
+#define BRIDGE_LOCAL_IO_PHYS 0xfe000000
+#define BRIDGE_LOCAL_IO_BUS 0x04000000
+
+#define BRIDGE(r, x) (BRIDGE_##r##_PHYS + HW_BRIDGE_##x)
+
+#define PCI_LATENCY_TIMER_VAL 0xff
+
+#endif
diff --git a/board/pcippc2/flash.c b/board/pcippc2/flash.c
new file mode 100755
index 0000000..8c01415
--- /dev/null
+++ b/board/pcippc2/flash.c
@@ -0,0 +1,573 @@
+/*
+ * (C) Copyright 2001
+ * Josh Huber <huber@mclx.com>, Mission Critical Linux, Inc.
+ *
+ * (C) Copyright 2002
+ * Wolfgang Denk, DENX Software Engineering, wd@denx.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 <config.h>
+#include <common.h>
+#include <flash.h>
+#include <asm/io.h>
+
+/*---------------------------------------------------------------------*/
+#undef DEBUG_FLASH
+
+#ifdef DEBUG_FLASH
+#define DEBUGF(fmt,args...) printf(fmt ,##args)
+#else
+#define DEBUGF(fmt,args...)
+#endif
+/*---------------------------------------------------------------------*/
+
+flash_info_t flash_info[CFG_MAX_FLASH_BANKS];
+
+static ulong flash_get_size (ulong addr, flash_info_t *info);
+static int flash_get_offsets (ulong base, flash_info_t *info);
+static int write_word (flash_info_t *info, ulong dest, ulong data);
+static void flash_reset (ulong addr);
+
+unsigned long flash_init (void)
+{
+ unsigned int i;
+ unsigned long flash_size = 0;
+
+ /* Init: no FLASHes known */
+ for (i=0; i<CFG_MAX_FLASH_BANKS; ++i) {
+ flash_info[i].flash_id = FLASH_UNKNOWN;
+ flash_info[i].sector_count = 0;
+ flash_info[i].size = 0;
+ }
+
+ DEBUGF("\n## Get flash size @ 0x%08x\n", CFG_FLASH_BASE);
+
+ flash_size = flash_get_size (CFG_FLASH_BASE, flash_info);
+
+ DEBUGF("## Flash bank size: %08lx\n", flash_size);
+
+ if (flash_size) {
+#if CFG_MONITOR_BASE >= CFG_FLASH_BASE && \
+ CFG_MONITOR_BASE < CFG_FLASH_BASE + CFG_FLASH_MAX_SIZE
+ /* monitor protection ON by default */
+ flash_protect(FLAG_PROTECT_SET,
+ CFG_MONITOR_BASE,
+ CFG_MONITOR_BASE + monitor_flash_len - 1,
+ &flash_info[0]);
+#endif
+
+#ifdef CFG_ENV_IS_IN_FLASH
+ /* ENV protection ON by default */
+ flash_protect(FLAG_PROTECT_SET,
+ CFG_ENV_ADDR,
+ CFG_ENV_ADDR + CFG_ENV_SECT_SIZE - 1,
+ &flash_info[0]);
+#endif
+
+ } else {
+ puts ("Warning: the BOOT Flash is not initialised !");
+ }
+
+ return flash_size;
+}
+
+/*
+ * The following code cannot be run from FLASH!
+ */
+static ulong flash_get_size (ulong addr, flash_info_t *info)
+{
+ short i;
+ uchar value;
+
+ /* Write auto select command: read Manufacturer ID */
+ out8(addr + 0x0555, 0xAA);
+ iobarrier_rw();
+ out8(addr + 0x02AA, 0x55);
+ iobarrier_rw();
+ out8(addr + 0x0555, 0x90);
+ iobarrier_rw();
+
+ value = in8(addr);
+ iobarrier_rw();
+
+ DEBUGF("Manuf. ID @ 0x%08lx: 0x%08x\n", (ulong)addr, value);
+
+ switch (value | (value << 16)) {
+ case AMD_MANUFACT:
+ info->flash_id = FLASH_MAN_AMD;
+ break;
+
+ case FUJ_MANUFACT:
+ info->flash_id = FLASH_MAN_FUJ;
+ break;
+
+ case STM_MANUFACT:
+ info->flash_id = FLASH_MAN_STM;
+ break;
+
+ default:
+ info->flash_id = FLASH_UNKNOWN;
+ info->sector_count = 0;
+ info->size = 0;
+ flash_reset (addr);
+ return 0;
+ }
+
+ value = in8(addr + 1); /* device ID */
+ iobarrier_rw();
+
+ DEBUGF("Device ID @ 0x%08lx: 0x%08x\n", addr+1, value);
+
+ switch ((ulong)value) {
+ case AMD_ID_F040B:
+ DEBUGF("Am29F040B\n");
+ info->flash_id += FLASH_AM040;
+ info->sector_count = 8;
+ info->size = 0x00080000;
+ break; /* => 512 kB */
+
+ case AMD_ID_LV040B:
+ DEBUGF("Am29LV040B\n");
+ info->flash_id += FLASH_AM040;
+ info->sector_count = 8;
+ info->size = 0x00080000;
+ break; /* => 512 kB */
+
+ case AMD_ID_LV400T:
+ DEBUGF("Am29LV400T\n");
+ info->flash_id += FLASH_AM400T;
+ info->sector_count = 11;
+ info->size = 0x00100000;
+ break; /* => 1 MB */
+
+ case AMD_ID_LV400B:
+ DEBUGF("Am29LV400B\n");
+ info->flash_id += FLASH_AM400B;
+ info->sector_count = 11;
+ info->size = 0x00100000;
+ break; /* => 1 MB */
+
+ case AMD_ID_LV800T:
+ DEBUGF("Am29LV800T\n");
+ info->flash_id += FLASH_AM800T;
+ info->sector_count = 19;
+ info->size = 0x00200000;
+ break; /* => 2 MB */
+
+ case AMD_ID_LV800B:
+ DEBUGF("Am29LV400B\n");
+ info->flash_id += FLASH_AM800B;
+ info->sector_count = 19;
+ info->size = 0x00200000;
+ break; /* => 2 MB */
+
+ case AMD_ID_LV160T:
+ DEBUGF("Am29LV160T\n");
+ info->flash_id += FLASH_AM160T;
+ info->sector_count = 35;
+ info->size = 0x00400000;
+ break; /* => 4 MB */
+
+ case AMD_ID_LV160B:
+ DEBUGF("Am29LV160B\n");
+ info->flash_id += FLASH_AM160B;
+ info->sector_count = 35;
+ info->size = 0x00400000;
+ break; /* => 4 MB */
+
+ case AMD_ID_LV320T:
+ DEBUGF("Am29LV320T\n");
+ info->flash_id += FLASH_AM320T;
+ info->sector_count = 67;
+ info->size = 0x00800000;
+ break; /* => 8 MB */
+
+#if 0
+ /* Has the same ID as AMD_ID_LV320T, to be fixed */
+ case AMD_ID_LV320B:
+ DEBUGF("Am29LV320B\n");
+ info->flash_id += FLASH_AM320B;
+ info->sector_count = 67;
+ info->size = 0x00800000;
+ break; /* => 8 MB */
+#endif
+
+ case AMD_ID_LV033C:
+ DEBUGF("Am29LV033C\n");
+ info->flash_id += FLASH_AM033C;
+ info->sector_count = 64;
+ info->size = 0x01000000;
+ break; /* => 16Mb */
+
+ case STM_ID_F040B:
+ DEBUGF("M29F040B\n");
+ info->flash_id += FLASH_AM040;
+ info->sector_count = 8;
+ info->size = 0x00080000;
+ break; /* => 512 kB */
+
+ default:
+ info->flash_id = FLASH_UNKNOWN;
+ flash_reset (addr);
+ return (0); /* => no or unknown flash */
+
+ }
+
+ if (info->sector_count > CFG_MAX_FLASH_SECT) {
+ printf ("** ERROR: sector count %d > max (%d) **\n",
+ info->sector_count, CFG_MAX_FLASH_SECT);
+ info->sector_count = CFG_MAX_FLASH_SECT;
+ }
+
+ if (! flash_get_offsets (addr, info)) {
+ flash_reset (addr);
+ return 0;
+ }
+
+ /* check for protected sectors */
+ for (i = 0; i < info->sector_count; i++) {
+ /* read sector protection at sector address, (A7 .. A0) = 0x02 */
+ /* D0 = 1 if protected */
+ value = in8(info->start[i] + 2);
+ iobarrier_rw();
+ info->protect[i] = (value & 1) != 0;
+ }
+
+ /*
+ * Reset bank to read mode
+ */
+ flash_reset (addr);
+
+ return (info->size);
+}
+
+static int flash_get_offsets (ulong base, flash_info_t *info)
+{
+ unsigned int i;
+
+ switch (info->flash_id & FLASH_TYPEMASK) {
+ case FLASH_AM040:
+ /* set sector offsets for uniform sector type */
+ for (i = 0; i < info->sector_count; i++) {
+ info->start[i] = base + i * info->size /
+ info->sector_count;
+ }
+ break;
+ default:
+ return 0;
+ }
+
+ return 1;
+}
+
+int flash_erase (flash_info_t *info, int s_first, int s_last)
+{
+ volatile ulong addr = info->start[0];
+ int flag, prot, sect, l_sect;
+ ulong start, now, last;
+
+ if (s_first < 0 || s_first > s_last) {
+ if (info->flash_id == FLASH_UNKNOWN) {
+ printf ("- missing\n");
+ } else {
+ printf ("- no sectors to erase\n");
+ }
+ return 1;
+ }
+
+ if (info->flash_id == FLASH_UNKNOWN) {
+ printf ("Can't erase unknown flash type %08lx - aborted\n",
+ info->flash_id);
+ return 1;
+ }
+
+ prot = 0;
+ for (sect=s_first; sect<=s_last; ++sect) {
+ if (info->protect[sect]) {
+ prot++;
+ }
+ }
+
+ if (prot) {
+ printf ("- Warning: %d protected sectors will not be erased!\n",
+ prot);
+ } else {
+ printf ("\n");
+ }
+
+ l_sect = -1;
+
+ /* Disable interrupts which might cause a timeout here */
+ flag = disable_interrupts();
+
+ out8(addr + 0x555, 0xAA);
+ iobarrier_rw();
+ out8(addr + 0x2AA, 0x55);
+ iobarrier_rw();
+ out8(addr + 0x555, 0x80);
+ iobarrier_rw();
+ out8(addr + 0x555, 0xAA);
+ iobarrier_rw();
+ out8(addr + 0x2AA, 0x55);
+ iobarrier_rw();
+
+ /* Start erase on unprotected sectors */
+ for (sect = s_first; sect<=s_last; sect++) {
+ if (info->protect[sect] == 0) { /* not protected */
+ addr = info->start[sect];
+ out8(addr, 0x30);
+ iobarrier_rw();
+ l_sect = sect;
+ }
+ }
+
+ /* re-enable interrupts if necessary */
+ if (flag)
+ enable_interrupts();
+
+ /* wait at least 80us - let's wait 1 ms */
+ udelay (1000);
+
+ /*
+ * We wait for the last triggered sector
+ */
+ if (l_sect < 0)
+ goto DONE;
+
+ start = get_timer (0);
+ last = start;
+ addr = info->start[l_sect];
+
+ DEBUGF ("Start erase timeout: %d\n", CFG_FLASH_ERASE_TOUT);
+
+ while ((in8(addr) & 0x80) != 0x80) {
+ if ((now = get_timer(start)) > CFG_FLASH_ERASE_TOUT) {
+ printf ("Timeout\n");
+ flash_reset (info->start[0]);
+ return 1;
+ }
+ /* show that we're waiting */
+ if ((now - last) > 1000) { /* every second */
+ putc ('.');
+ last = now;
+ }
+ iobarrier_rw();
+ }
+
+DONE:
+ /* reset to read mode */
+ flash_reset (info->start[0]);
+
+ printf (" done\n");
+ return 0;
+}
+
+/*
+ * Copy memory to flash, returns:
+ * 0 - OK
+ * 1 - write timeout
+ * 2 - Flash not erased
+ */
+int write_buff (flash_info_t *info, uchar *src, ulong addr, ulong cnt)
+{
+ ulong cp, wp, data;
+ int i, l, rc;
+
+ wp = (addr & ~3); /* get lower word aligned address */
+
+ /*
+ * handle unaligned start bytes
+ */
+ if ((l = addr - wp) != 0) {
+ data = 0;
+ for (i=0, cp=wp; i<l; ++i, ++cp) {
+ data = (data << 8) | (*(uchar *)cp);
+ }
+ for (; i<4 && cnt>0; ++i) {
+ data = (data << 8) | *src++;
+ --cnt;
+ ++cp;
+ }
+ for (; cnt==0 && i<4; ++i, ++cp) {
+ data = (data << 8) | (*(uchar *)cp);
+ }
+
+ if ((rc = write_word(info, wp, data)) != 0) {
+ return (rc);
+ }
+ wp += 4;
+ }
+
+ /*
+ * handle word aligned part
+ */
+ while (cnt >= 4) {
+ data = 0;
+ for (i=0; i<4; ++i) {
+ data = (data << 8) | *src++;
+ }
+ if ((rc = write_word(info, wp, data)) != 0) {
+ return (rc);
+ }
+ wp += 4;
+ cnt -= 4;
+ }
+
+ if (cnt == 0) {
+ return (0);
+ }
+
+ /*
+ * handle unaligned tail bytes
+ */
+ data = 0;
+ for (i=0, cp=wp; i<4 && cnt>0; ++i, ++cp) {
+ data = (data << 8) | *src++;
+ --cnt;
+ }
+ for (; i<4; ++i, ++cp) {
+ data = (data << 8) | (*(uchar *)cp);
+ }
+
+ return (write_word(info, wp, data));
+}
+
+/*
+ * Write a word to Flash, returns:
+ * 0 - OK
+ * 1 - write timeout
+ * 2 - Flash not erased
+ */
+static int write_word (flash_info_t *info, ulong dest, ulong data)
+{
+ volatile ulong addr = info->start[0];
+ ulong start;
+ int i;
+
+ /* Check if Flash is (sufficiently) erased */
+ if ((in32(dest) & data) != data) {
+ return (2);
+ }
+
+ /* write each byte out */
+ for (i = 0; i < 4; i++) {
+ char *data_ch = (char *)&data;
+ int flag = disable_interrupts();
+
+ out8(addr + 0x555, 0xAA);
+ iobarrier_rw();
+ out8(addr + 0x2AA, 0x55);
+ iobarrier_rw();
+ out8(addr + 0x555, 0xA0);
+ iobarrier_rw();
+ out8(dest+i, data_ch[i]);
+ iobarrier_rw();
+
+ /* re-enable interrupts if necessary */
+ if (flag)
+ enable_interrupts();
+
+ /* data polling for D7 */
+ start = get_timer (0);
+ while ((in8(dest+i) & 0x80) != (data_ch[i] & 0x80)) {
+ if (get_timer(start) > CFG_FLASH_WRITE_TOUT) {
+ flash_reset (addr);
+ return (1);
+ }
+ iobarrier_rw();
+ }
+ }
+
+ flash_reset (addr);
+ return (0);
+}
+
+/*
+ * Reset bank to read mode
+ */
+static void flash_reset (ulong addr)
+{
+ out8(addr, 0xF0); /* reset bank */
+ iobarrier_rw();
+}
+
+void flash_print_info (flash_info_t *info)
+{
+ int i;
+
+ if (info->flash_id == FLASH_UNKNOWN) {
+ printf ("missing or unknown FLASH type\n");
+ return;
+ }
+
+ switch (info->flash_id & FLASH_VENDMASK) {
+ case FLASH_MAN_AMD: printf ("AMD "); break;
+ case FLASH_MAN_FUJ: printf ("FUJITSU "); break;
+ case FLASH_MAN_BM: printf ("BRIGHT MICRO "); break;
+ case FLASH_MAN_STM: printf ("SGS THOMSON "); break;
+ default: printf ("Unknown Vendor "); break;
+ }
+
+ switch (info->flash_id & FLASH_TYPEMASK) {
+ case FLASH_AM040: printf ("29F040 or 29LV040 (4 Mbit, uniform sectors)\n");
+ break;
+ case FLASH_AM400B: printf ("AM29LV400B (4 Mbit, bottom boot sect)\n");
+ break;
+ case FLASH_AM400T: printf ("AM29LV400T (4 Mbit, top boot sector)\n");
+ break;
+ case FLASH_AM800B: printf ("AM29LV800B (8 Mbit, bottom boot sect)\n");
+ break;
+ case FLASH_AM800T: printf ("AM29LV800T (8 Mbit, top boot sector)\n");
+ break;
+ case FLASH_AM160B: printf ("AM29LV160B (16 Mbit, bottom boot sect)\n");
+ break;
+ case FLASH_AM160T: printf ("AM29LV160T (16 Mbit, top boot sector)\n");
+ break;
+ case FLASH_AM320B: printf ("AM29LV320B (32 Mbit, bottom boot sect)\n");
+ break;
+ case FLASH_AM320T: printf ("AM29LV320T (32 Mbit, top boot sector)\n");
+ break;
+ default: printf ("Unknown Chip Type\n");
+ break;
+ }
+
+ if (info->size % 0x100000 == 0) {
+ printf (" Size: %ld MB in %d Sectors\n",
+ info->size / 0x100000, info->sector_count);
+ } else if (info->size % 0x400 == 0) {
+ printf (" Size: %ld KB in %d Sectors\n",
+ info->size / 0x400, info->sector_count);
+ } else {
+ printf (" Size: %ld B in %d Sectors\n",
+ info->size, info->sector_count);
+ }
+
+ printf (" Sector Start Addresses:");
+ for (i=0; i<info->sector_count; ++i) {
+ if ((i % 5) == 0)
+ printf ("\n ");
+ printf (" %08lX%s",
+ info->start[i],
+ info->protect[i] ? " (RO)" : " "
+ );
+ }
+ printf ("\n");
+}
diff --git a/board/pcippc2/fpga_serial.c b/board/pcippc2/fpga_serial.c
new file mode 100755
index 0000000..579bfc7
--- /dev/null
+++ b/board/pcippc2/fpga_serial.c
@@ -0,0 +1,132 @@
+/*
+ * (C) Copyright 2002
+ * Wolfgang Denk, DENX Software Engineering, wd@denx.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 <config.h>
+#include <common.h>
+#include <asm/io.h>
+
+#include "fpga_serial.h"
+#include "hardware.h"
+#include "pcippc2.h"
+
+ /* 8 data, 1 stop, no parity
+ */
+#define LCRVAL 0x03
+ /* RTS/DTR
+ */
+#define MCRVAL 0x03
+ /* Clear & enable FIFOs
+ */
+#define FCRVAL 0x07
+
+static void fpga_serial_wait (void);
+static void fpga_serial_print (char c);
+
+void fpga_serial_init (int baudrate)
+{
+ int clock_divisor = 115200 / baudrate;
+
+ out8 (FPGA (INT, SERIAL_CONFIG), 0x24);
+ iobarrier_rw ();
+
+ fpga_serial_wait ();
+
+ out8 (UART (IER), 0);
+ out8 (UART (LCR), LCRVAL | 0x80);
+ iobarrier_rw ();
+ out8 (UART (DLL), clock_divisor & 0xff);
+ out8 (UART (DLM), clock_divisor >> 8);
+ iobarrier_rw ();
+ out8 (UART (LCR), LCRVAL);
+ iobarrier_rw ();
+ out8 (UART (MCR), MCRVAL);
+ out8 (UART (FCR), FCRVAL);
+ iobarrier_rw ();
+}
+
+void fpga_serial_putc (char c)
+{
+ if (c) {
+ fpga_serial_print (c);
+ }
+}
+
+void fpga_serial_puts (const char *s)
+{
+ while (*s) {
+ fpga_serial_print (*s++);
+ }
+}
+
+int fpga_serial_getc (void)
+{
+ while ((in8 (UART (LSR)) & 0x01) == 0);
+
+ return in8 (UART (RBR));
+}
+
+int fpga_serial_tstc (void)
+{
+ return (in8 (UART (LSR)) & 0x01) != 0;
+}
+
+void fpga_serial_setbrg (void)
+{
+ DECLARE_GLOBAL_DATA_PTR;
+
+ int clock_divisor = 115200 / gd->baudrate;
+
+ fpga_serial_wait ();
+
+ out8 (UART (LCR), LCRVAL | 0x80);
+ iobarrier_rw ();
+ out8 (UART (DLL), clock_divisor & 0xff);
+ out8 (UART (DLM), clock_divisor >> 8);
+ iobarrier_rw ();
+ out8 (UART (LCR), LCRVAL);
+ iobarrier_rw ();
+}
+
+static void fpga_serial_wait (void)
+{
+ while ((in8 (UART (LSR)) & 0x40) == 0);
+}
+
+static void fpga_serial_print (char c)
+{
+ if (c == '\n') {
+ while ((in8 (UART (LSR)) & 0x20) == 0);
+
+ out8 (UART (THR), '\r');
+ iobarrier_rw ();
+ }
+
+ while ((in8 (UART (LSR)) & 0x20) == 0);
+
+ out8 (UART (THR), c);
+ iobarrier_rw ();
+
+ if (c == '\n') {
+ fpga_serial_wait ();
+ }
+}
diff --git a/board/pcippc2/fpga_serial.h b/board/pcippc2/fpga_serial.h
new file mode 100755
index 0000000..92c9cdd
--- /dev/null
+++ b/board/pcippc2/fpga_serial.h
@@ -0,0 +1,34 @@
+/*
+ * (C) Copyright 2002
+ * Wolfgang Denk, DENX Software Engineering, wd@denx.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
+ */
+
+#ifndef _FPGA_SERIAL_H_
+#define _FPGA_SERIAL_H_
+
+extern void fpga_serial_init (int);
+extern void fpga_serial_putc (char);
+extern void fpga_serial_puts (const char *);
+extern int fpga_serial_getc (void);
+extern int fpga_serial_tstc (void);
+extern void fpga_serial_setbrg (void);
+
+#endif
diff --git a/board/pcippc2/hardware.h b/board/pcippc2/hardware.h
new file mode 100755
index 0000000..489929d
--- /dev/null
+++ b/board/pcippc2/hardware.h
@@ -0,0 +1,48 @@
+/*
+ * (C) Copyright 2002
+ * Wolfgang Denk, DENX Software Engineering, wd@denx.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
+ */
+
+#ifndef _HARDWARE_H_
+#define _HARDWARE_H_
+
+#include "cpc710.h"
+#include "cpc710_pci.h"
+#include "pcippc2_fpga.h"
+#include "ns16550.h"
+
+#define REG(r, x) (HW_PHYS_##r + HW_##r##_##x)
+
+ /* Address map:
+ *
+ * 0x00000000-0x20000000 SDRAM
+ * 0x40000000-0x00008000 Init RAM in the CPU DCache
+ * 0xf0000000-0xf8000000 CPCI MEM
+ * 0xf8000000-0xfc000000 Local PCI MEM
+ * 0xfc000000-0xfe000000 CPCI I/O
+ * 0xfe000000-0xff000000 Local PCI I/O
+ * 0xff000000-0xff201000 System configuration space
+ * 0xff400000-0xff500000 Local PCI bridge space
+ * 0xff500000-0xff600000 CPCI bridge space
+ * 0xfff00000-0xfff80000 Boot Flash
+ */
+
+#endif
diff --git a/board/pcippc2/i2c.c b/board/pcippc2/i2c.c
new file mode 100755
index 0000000..36b1d0f
--- /dev/null
+++ b/board/pcippc2/i2c.c
@@ -0,0 +1,257 @@
+/*
+ * (C) Copyright 2002
+ * Wolfgang Denk, DENX Software Engineering, wd@denx.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 <config.h>
+#include <common.h>
+#include <asm/io.h>
+
+#include "hardware.h"
+#include "i2c.h"
+
+static void i2c_start (void);
+static void i2c_stop (void);
+static int i2c_write (u8 data);
+static void i2c_read (u8 * data);
+
+static inline void i2c_port_start (void);
+static inline void i2c_clock (unsigned int val);
+static inline void i2c_data (unsigned int val);
+static inline unsigned int
+ i2c_in (void);
+static inline void i2c_write_bit (unsigned int val);
+static inline unsigned int
+ i2c_read_bit (void);
+
+static inline void i2c_udelay (unsigned int time);
+
+int i2c_read_byte (
+ u8 * data,
+ u8 dev,
+ u8 offset)
+{
+ int err = 0;
+
+ i2c_start();
+
+ err = ! i2c_write(dev);
+
+ if (! err)
+ {
+ err = ! i2c_write(offset);
+ }
+
+ if (! err)
+ {
+ i2c_start();
+ }
+
+ if (! err)
+ {
+ err = ! i2c_write(dev | 0x01);
+ }
+
+ if (! err)
+ {
+ i2c_read(data);
+ }
+
+ i2c_stop();
+
+ return ! err;
+}
+
+static inline void i2c_udelay (
+ unsigned int time)
+{
+ int v;
+
+ asm volatile("mtdec %0" : : "r" (time * ((CFG_BUS_CLK / 4) / 1000000)));
+
+ do
+ {
+ asm volatile("isync; mfdec %0" : "=r" (v));
+ } while (v >= 0);
+}
+
+ /* Low-level hardware access
+ */
+
+#define BIT_GPDATA 0x80000000
+#define BIT_GPCLK 0x40000000
+
+static inline void i2c_port_start (void)
+{
+ out32(REG(CPC0, GPDIR), in32(REG(CPC0, GPDIR)) & ~(BIT_GPCLK | BIT_GPDATA));
+ out32(REG(CPC0, GPOUT), in32(REG(CPC0, GPOUT)) & ~(BIT_GPCLK | BIT_GPDATA));
+ iobarrier_rw();
+
+ i2c_udelay(1);
+}
+
+static inline void i2c_clock (
+ unsigned int val)
+{
+ if (val)
+ {
+ out32(REG(CPC0, GPDIR), in32(REG(CPC0, GPDIR)) & ~BIT_GPCLK);
+ }
+ else
+ {
+ out32(REG(CPC0, GPDIR), in32(REG(CPC0, GPDIR)) | BIT_GPCLK);
+ }
+
+ iobarrier_rw();
+
+ i2c_udelay(1);
+}
+
+static inline void i2c_data (
+ unsigned int val)
+{
+ if (val)
+ {
+ out32(REG(CPC0, GPDIR), in32(REG(CPC0, GPDIR)) & ~BIT_GPDATA);
+ }
+ else
+ {
+ out32(REG(CPC0, GPDIR), in32(REG(CPC0, GPDIR)) | BIT_GPDATA);
+ }
+
+ iobarrier_rw();
+
+ i2c_udelay(1);
+}
+
+static inline unsigned int i2c_in (void)
+{
+ unsigned int val = ((in32(REG(CPC0, GPIN)) & BIT_GPDATA) != 0)?1:0;
+
+ iobarrier_rw();
+
+ return val;
+}
+
+
+ /* Protocol implementation
+ */
+
+static inline void i2c_write_bit (
+ unsigned int val)
+{
+ i2c_data(val);
+ i2c_udelay(10);
+ i2c_clock(1);
+ i2c_udelay(10);
+ i2c_clock(0);
+ i2c_udelay(10);
+}
+
+static inline unsigned int i2c_read_bit (void)
+{
+ unsigned int val;
+
+ i2c_data(1);
+ i2c_udelay(10);
+
+ i2c_clock(1);
+ i2c_udelay(10);
+
+ val = i2c_in();
+
+ i2c_clock(0);
+ i2c_udelay(10);
+
+ return val;
+}
+
+unsigned int i2c_reset (void)
+{
+ unsigned int val;
+ int i;
+
+ i2c_port_start();
+
+ i=0;
+ do {
+ i2c_udelay(10);
+ i2c_clock(0);
+ i2c_udelay(10);
+ i2c_clock(1);
+ i2c_udelay(10);
+ val = i2c_in();
+ i++;
+ } while ((i<9)&&(val==0));
+ return (val);
+}
+
+
+static void i2c_start (void)
+{
+ i2c_data(1);
+ i2c_clock(1);
+ i2c_udelay(10);
+ i2c_data(0);
+ i2c_udelay(10);
+ i2c_clock(0);
+ i2c_udelay(10);
+}
+
+static void i2c_stop (void)
+{
+ i2c_data(0);
+ i2c_udelay(10);
+ i2c_clock(1);
+ i2c_udelay(10);
+ i2c_data(1);
+ i2c_udelay(10);
+}
+
+static int i2c_write (
+ u8 data)
+{
+ unsigned int i;
+
+ for (i = 0; i < 8; i++)
+ {
+ i2c_write_bit(data >> 7);
+ data <<= 1;
+ }
+
+ return i2c_read_bit() == 0;
+}
+
+static void i2c_read (
+ u8 * data)
+{
+ unsigned int i;
+ u8 val = 0;
+
+ for (i = 0; i < 8; i++)
+ {
+ val <<= 1;
+ val |= i2c_read_bit();
+ }
+
+ *data = val;
+ i2c_write_bit(1); /* NoAck */
+}
diff --git a/board/pcippc2/i2c.h b/board/pcippc2/i2c.h
new file mode 100755
index 0000000..1224b42
--- /dev/null
+++ b/board/pcippc2/i2c.h
@@ -0,0 +1,36 @@
+/*
+ * (C) Copyright 2002
+ * Wolfgang Denk, DENX Software Engineering, wd@denx.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
+ */
+
+#ifndef _I2C_H_
+#define _I2C_H_
+
+#include <common.h>
+
+extern int i2c_read_byte (u8 * data,
+ u8 dev,
+ u8 offset);
+
+extern unsigned int i2c_reset (void);
+
+
+#endif
diff --git a/board/pcippc2/ns16550.h b/board/pcippc2/ns16550.h
new file mode 100755
index 0000000..7023f13
--- /dev/null
+++ b/board/pcippc2/ns16550.h
@@ -0,0 +1,41 @@
+/*
+ * (C) Copyright 2002
+ * Wolfgang Denk, DENX Software Engineering, wd@denx.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
+ */
+
+#ifndef _NS16550_H_
+#define _NS16550_H_
+
+#define NS16550_RBR 0x00
+#define NS16550_IER 0x01
+#define NS16550_FCR 0x02
+#define NS16550_LCR 0x03
+#define NS16550_MCR 0x04
+#define NS16550_LSR 0x05
+#define NS16550_MSR 0x06
+#define NS16550_SCR 0x07
+
+#define NS16550_THR NS16550_RBR
+#define NS16550_IIR NS16550_FCR
+#define NS16550_DLL NS16550_RBR
+#define NS16550_DLM NS16550_IER
+
+#endif
diff --git a/board/pcippc2/pcippc2.c b/board/pcippc2/pcippc2.c
new file mode 100755
index 0000000..231b505
--- /dev/null
+++ b/board/pcippc2/pcippc2.c
@@ -0,0 +1,245 @@
+/*
+ * (C) Copyright 2002
+ * Wolfgang Denk, DENX Software Engineering, wd@denx.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 <config.h>
+#include <common.h>
+#include <command.h>
+#include <asm/io.h>
+#include <linux/mtd/doc2000.h>
+#include <watchdog.h>
+#include <pci.h>
+
+#include "hardware.h"
+#include "pcippc2.h"
+#include "sconsole.h"
+#include "fpga_serial.h"
+
+#if defined(CONFIG_WATCHDOG)
+
+static int pcippc2_wdt_init_done = 0;
+
+void pcippc2_wdt_init (void);
+
+#endif
+
+ /* Check board identity
+ */
+int checkboard (void)
+{
+#ifdef CONFIG_PCIPPC2
+ puts ("Board: Gespac PCIPPC-2\n");
+#else
+ puts ("Board: Gespac PCIPPC-6\n");
+#endif
+ return 0;
+}
+
+ /* RAM size is stored in CPC0_RGBAN1
+ */
+u32 pcippc2_sdram_size (void)
+{
+ return in32 (REG (CPC0, RGBAN1));
+}
+
+long initdram (int board_type)
+{
+ return cpc710_ram_init ();
+}
+
+int do_reset (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
+{
+ out32 (REG (CPC0, SPOR), 0);
+ iobarrier_rw ();
+ while (1);
+ /* notreached */
+ return (-1);
+}
+
+int board_early_init_f (void)
+{
+ out32 (REG (CPC0, RSTR), 0xC0000000);
+ iobarrier_rw ();
+
+ out32 (REG (CPC0, RSTR), 0xF0000000);
+ iobarrier_rw ();
+
+ out32 (REG (CPC0, UCTL), 0x00F80000);
+
+ out32 (REG (CPC0, SIOC0), 0x30000000);
+
+ out32 (REG (CPC0, ABCNTL), 0x00000000);
+
+ out32 (REG (CPC0, SESR), 0x00000000);
+ out32 (REG (CPC0, SEAR), 0x00000000);
+
+ /* Detect IBM Avignon CPC710 Revision */
+ if ((in32 (REG (CPC0, UCTL)) & 0x000000F0) == CPC710_TYPE_100P)
+ out32 (REG (CPC0, PGCHP), 0xA0000040);
+ else
+ out32 (REG (CPC0, PGCHP), 0x80800040);
+
+
+ out32 (REG (CPC0, ATAS), 0x709C2508);
+
+ iobarrier_rw ();
+
+ return 0;
+}
+
+void after_reloc (ulong dest_addr)
+{
+ DECLARE_GLOBAL_DATA_PTR;
+
+ /* Jump to the main U-Boot board init code
+ */
+ board_init_r ((gd_t *)gd, dest_addr);
+}
+
+int misc_init_r (void)
+{
+ pcippc2_fpga_init ();
+
+ pcippc2_cpci3264_init ();
+
+#if defined(CONFIG_WATCHDOG)
+ pcippc2_wdt_init ();
+#endif
+
+ fpga_serial_init (sconsole_get_baudrate ());
+
+ sconsole_putc = fpga_serial_putc;
+ sconsole_puts = fpga_serial_puts;
+ sconsole_getc = fpga_serial_getc;
+ sconsole_tstc = fpga_serial_tstc;
+ sconsole_setbrg = fpga_serial_setbrg;
+
+ sconsole_flush ();
+ return (0);
+}
+
+void pci_init_board (void)
+{
+ cpc710_pci_init ();
+
+ /* FPGA requires no retry timeouts to be enabled
+ */
+ cpc710_pci_enable_timeout ();
+}
+
+void doc_init (void)
+{
+ doc_probe (pcippc2_fpga1_phys + HW_FPGA1_DOC);
+}
+
+void pcippc2_cpci3264_init (void)
+{
+ pci_dev_t bdf = pci_find_device(FPGA_VENDOR_ID, FPGA_DEVICE_ID, 0);
+
+ if (bdf == -1)
+ {
+ puts("Unable to find FPGA !\n");
+ hang();
+ }
+
+ if((in32(pcippc2_fpga0_phys + HW_FPGA0_BOARD) & 0x01000000) == 0x01000000)
+ /* 32-bits Compact PCI bus - LSB bit */
+ {
+ iobarrier_rw();
+ out32(BRIDGE(CPCI, PCIDG), 0x40000000); /* 32-bits bridge, Pipeline */
+ iobarrier_rw();
+ }
+}
+
+#if defined(CONFIG_WATCHDOG)
+
+void pcippc2_wdt_init (void)
+{
+ out16r (FPGA (WDT, PROG), 0xffff);
+ out8 (FPGA (WDT, CTRL), 0x1);
+
+ pcippc2_wdt_init_done = 1;
+}
+
+void pcippc2_wdt_done (void)
+{
+ out8 (FPGA (WDT, CTRL), 0x0);
+
+ pcippc2_wdt_init_done = 0;
+}
+
+void pcippc2_wdt_reset (void)
+{
+ if (pcippc2_wdt_init_done == 1)
+ out8 (FPGA (WDT, REFRESH), 0x56);
+}
+
+void watchdog_reset (void)
+{
+ int re_enable = disable_interrupts ();
+
+ pcippc2_wdt_reset ();
+ if (re_enable)
+ enable_interrupts ();
+}
+
+#if (CONFIG_COMMANDS & CFG_CMD_BSP)
+int do_wd (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
+{
+ switch (argc) {
+ case 1:
+ printf ("Watchdog timer status is %s\n",
+ pcippc2_wdt_init_done == 1 ? "on" : "off");
+
+ return 0;
+ case 2:
+ if (!strcmp(argv[1],"on")) {
+ pcippc2_wdt_init();
+ printf("Watchdog timer now is on\n");
+
+ return 0;
+
+ } else if (!strcmp(argv[1],"off")) {
+ pcippc2_wdt_done();
+ printf("Watchdog timer now is off\n");
+
+ return 0;
+
+ } else
+ break;
+ default:
+ break;
+ }
+ printf ("Usage:\n%s\n", cmdtp->usage);
+ return 1;
+}
+
+U_BOOT_CMD(
+ wd, 2, 1, do_wd,
+ "wd - check and set watchdog\n",
+ "on - switch watchDog on\n"
+ "wd off - switch watchdog off\n"
+ "wd - print current status\n"
+);
+
+#endif /* CFG_CMD_BSP */
+#endif /* CONFIG_WATCHDOG */
diff --git a/board/pcippc2/pcippc2.h b/board/pcippc2/pcippc2.h
new file mode 100755
index 0000000..3820bbe
--- /dev/null
+++ b/board/pcippc2/pcippc2.h
@@ -0,0 +1,51 @@
+/*
+ * (C) Copyright 2002
+ * Wolfgang Denk, DENX Software Engineering, wd@denx.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
+ */
+
+#ifndef _PCIPPC2_H_
+#define _PCIPPC2_H_
+
+#include <config.h>
+#include <common.h>
+
+#include "hardware.h"
+
+#define FPGA(r, p) (pcippc2_fpga0_phys + HW_FPGA0_##r##_##p)
+#define UART(r) (pcippc2_fpga0_phys + HW_FPGA0_UART1 + NS16550_##r * 4)
+#define RTC(r) (pcippc2_fpga1_phys + HW_FPGA1_RTC + r)
+
+extern u32 pcippc2_fpga0_phys;
+extern u32 pcippc2_fpga1_phys;
+
+extern u32 pcippc2_sdram_size (void);
+
+extern void pcippc2_fpga_init (void);
+
+extern void pcippc2_cpci3264_init (void);
+
+extern void cpc710_pci_init (void);
+extern void cpc710_pci_enable_timeout (void);
+
+extern unsigned long
+ cpc710_ram_init (void);
+
+#endif
diff --git a/board/pcippc2/pcippc2_fpga.c b/board/pcippc2/pcippc2_fpga.c
new file mode 100755
index 0000000..7f6739d
--- /dev/null
+++ b/board/pcippc2/pcippc2_fpga.c
@@ -0,0 +1,87 @@
+/*
+ * (C) Copyright 2002
+ * Wolfgang Denk, DENX Software Engineering, wd@denx.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 <config.h>
+#include <common.h>
+#include <asm/io.h>
+
+#include "pci.h"
+
+#include "hardware.h"
+#include "pcippc2.h"
+
+u32 pcippc2_fpga0_phys;
+u32 pcippc2_fpga1_phys;
+
+void pcippc2_fpga_init (void)
+{
+ pci_dev_t bdf = pci_find_device(FPGA_VENDOR_ID, FPGA_DEVICE_ID, 0);
+ unsigned int addr;
+ u16 cmd;
+
+ if (bdf == -1)
+ {
+ puts("Unable to find FPGA !\n");
+ hang();
+ }
+
+ pci_read_config_word(bdf, PCI_COMMAND, &cmd);
+ if ((cmd & (PCI_COMMAND_MEMORY | PCI_COMMAND_IO)) != (PCI_COMMAND_MEMORY | PCI_COMMAND_IO))
+ {
+ puts("FPGA is not configured !\n");
+ hang();
+ }
+
+ pci_read_config_dword(bdf, PCI_BASE_ADDRESS_0, &addr);
+ if (addr & 0x1)
+ {
+ /* IO space
+ */
+ pcippc2_fpga0_phys = pci_io_to_phys(bdf, addr & 0xfffffffc);
+ }
+ else
+ {
+ /* Memory space
+ */
+ pcippc2_fpga0_phys = pci_mem_to_phys(bdf, addr & 0xfffffff0);
+ }
+
+ pci_read_config_dword(bdf, PCI_BASE_ADDRESS_1, &addr);
+ if (addr & 0x1)
+ {
+ /* IO space
+ */
+ pcippc2_fpga1_phys = pci_io_to_phys(bdf, addr & 0xfffffffc);
+ }
+ else
+ {
+ /* Memory space
+ */
+ pcippc2_fpga1_phys = pci_mem_to_phys(bdf, addr & 0xfffffff0);
+ }
+
+ /* Interrupts are not used
+ */
+ out32(FPGA(INT, INTR_MASK), 0xffffffff);
+ iobarrier_rw();
+}
diff --git a/board/pcippc2/pcippc2_fpga.h b/board/pcippc2/pcippc2_fpga.h
new file mode 100755
index 0000000..850c331
--- /dev/null
+++ b/board/pcippc2/pcippc2_fpga.h
@@ -0,0 +1,49 @@
+/*
+ * (C) Copyright 2002
+ * Wolfgang Denk, DENX Software Engineering, wd@denx.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
+ */
+
+#ifndef _PCIPPC2_FPGA_H_
+#define _PCIPPC2_FPGA_H_
+
+#define FPGA_VENDOR_ID 0x1310
+#define FPGA_DEVICE_ID 0x000d
+
+#define HW_FPGA0_INT 0x0000
+#define HW_FPGA0_BOARD 0x0060
+#define HW_FPGA0_UART1 0x0080
+#define HW_FPGA0_UART2 0x0100
+#define HW_FPGA0_RTC 0x2000
+#define HW_FPGA0_DOC 0x4000
+#define HW_FPGA1_RTC 0x0000
+#define HW_FPGA1_DOC 0x4000
+
+#define HW_FPGA0_INT_INTR_MASK 0x30
+#define HW_FPGA0_INT_INTR_STATUS 0x34
+#define HW_FPGA0_INT_INTR_EOI 0x40
+#define HW_FPGA0_INT_SERIAL_CONFIG 0x5c
+
+#define HW_FPGA0_WDT_CTRL 0x44
+#define HW_FPGA0_WDT_PROG 0x48
+#define HW_FPGA0_WDT_VAL 0x4c
+#define HW_FPGA0_WDT_REFRESH 0x50
+
+#endif
diff --git a/board/pcippc2/sconsole.c b/board/pcippc2/sconsole.c
new file mode 100755
index 0000000..a9f2b29
--- /dev/null
+++ b/board/pcippc2/sconsole.c
@@ -0,0 +1,141 @@
+/*
+ * (C) Copyright 2002
+ * Wolfgang Denk, DENX Software Engineering, wd@denx.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 <config.h>
+#include <common.h>
+
+#include "sconsole.h"
+
+void (*sconsole_putc) (char) = 0;
+void (*sconsole_puts) (const char *) = 0;
+int (*sconsole_getc) (void) = 0;
+int (*sconsole_tstc) (void) = 0;
+void (*sconsole_setbrg) (void) = 0;
+
+int serial_init (void)
+{
+ DECLARE_GLOBAL_DATA_PTR;
+
+ sconsole_buffer_t *sb = SCONSOLE_BUFFER;
+
+ sb->pos = 0;
+ sb->size = 0;
+ sb->baud = gd->baudrate;
+ sb->max_size = CFG_SCONSOLE_SIZE - sizeof (sconsole_buffer_t);
+
+ return (0);
+}
+
+void serial_putc (char c)
+{
+ if (sconsole_putc) {
+ (*sconsole_putc) (c);
+ } else {
+ sconsole_buffer_t *sb = SCONSOLE_BUFFER;
+
+ if (c) {
+ sb->data[sb->pos++] = c;
+ if (sb->pos == sb->max_size) {
+ sb->pos = 0;
+ }
+ if (sb->size < sb->max_size) {
+ sb->size++;
+ }
+ }
+ }
+}
+
+void serial_puts (const char *s)
+{
+ if (sconsole_puts) {
+ (*sconsole_puts) (s);
+ } else {
+ sconsole_buffer_t *sb = SCONSOLE_BUFFER;
+
+ while (*s) {
+ sb->data[sb->pos++] = *s++;
+ if (sb->pos == sb->max_size) {
+ sb->pos = 0;
+ }
+ if (sb->size < sb->max_size) {
+ sb->size++;
+ }
+ }
+ }
+}
+
+int serial_getc (void)
+{
+ if (sconsole_getc) {
+ return (*sconsole_getc) ();
+ } else {
+ return 0;
+ }
+}
+
+int serial_tstc (void)
+{
+ if (sconsole_tstc) {
+ return (*sconsole_tstc) ();
+ } else {
+ return 0;
+ }
+}
+
+void serial_setbrg (void)
+{
+ DECLARE_GLOBAL_DATA_PTR;
+
+ if (sconsole_setbrg) {
+ (*sconsole_setbrg) ();
+ } else {
+ sconsole_buffer_t *sb = SCONSOLE_BUFFER;
+
+ sb->baud = gd->baudrate;
+ }
+}
+
+int sconsole_get_baudrate (void)
+{
+ sconsole_buffer_t *sb = SCONSOLE_BUFFER;
+
+ return sb->baud;
+}
+
+void sconsole_flush (void)
+{
+ if (sconsole_putc) {
+ sconsole_buffer_t *sb = SCONSOLE_BUFFER;
+ unsigned int end = sb->pos < sb->size
+ ? sb->pos + sb->max_size - sb->size
+ : sb->pos - sb->size;
+
+ while (sb->size) {
+ (*sconsole_putc) (sb->data[end++]);
+ if (end == sb->max_size) {
+ end = 0;
+ }
+ sb->size--;
+ }
+ }
+}
diff --git a/board/pcippc2/sconsole.h b/board/pcippc2/sconsole.h
new file mode 100755
index 0000000..40fd75b
--- /dev/null
+++ b/board/pcippc2/sconsole.h
@@ -0,0 +1,49 @@
+/*
+ * (C) Copyright 2002
+ * Wolfgang Denk, DENX Software Engineering, wd@denx.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
+ */
+
+#ifndef _SCONSOLE_H_
+#define _SCONSOLE_H_
+
+#include <config.h>
+
+typedef struct sconsole_buffer_s
+{
+ unsigned long size;
+ unsigned long max_size;
+ unsigned long pos;
+ unsigned long baud;
+ char data [1];
+} sconsole_buffer_t;
+
+#define SCONSOLE_BUFFER ((sconsole_buffer_t *) CFG_SCONSOLE_ADDR)
+
+extern void (* sconsole_putc) (char);
+extern void (* sconsole_puts) (const char *);
+extern int (* sconsole_getc) (void);
+extern int (* sconsole_tstc) (void);
+extern void (* sconsole_setbrg) (void);
+
+extern void sconsole_flush (void);
+extern int sconsole_get_baudrate (void);
+
+#endif
diff --git a/board/pcippc2/u-boot.lds b/board/pcippc2/u-boot.lds
new file mode 100755
index 0000000..5c8cd5a
--- /dev/null
+++ b/board/pcippc2/u-boot.lds
@@ -0,0 +1,141 @@
+/*
+ * (C) Copyright 2001
+ * Josh Huber <huber@mclx.com>, Mission Critical Linux, Inc.
+ *
+ * (C) Copyright 2002
+ * Wolfgang Denk, DENX Software Engineering, wd@denx.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
+ */
+
+/*
+ * u-boot.lds - linker script for U-Boot on the Galileo Eval Board.
+ */
+
+OUTPUT_ARCH(powerpc)
+SEARCH_DIR(/lib); SEARCH_DIR(/usr/lib); SEARCH_DIR(/usr/local/lib); SEARCH_DIR(/usr/local/powerpc-any-elf/lib);
+/* Do we need any of these for elf?
+ __DYNAMIC = 0; */
+SECTIONS
+{
+ /* Read-only sections, merged into text segment: */
+ . = + SIZEOF_HEADERS;
+ .interp : { *(.interp) }
+ .hash : { *(.hash) }
+ .dynsym : { *(.dynsym) }
+ .dynstr : { *(.dynstr) }
+ .rel.text : { *(.rel.text) }
+ .rela.text : { *(.rela.text) }
+ .rel.data : { *(.rel.data) }
+ .rela.data : { *(.rela.data) }
+ .rel.rodata : { *(.rel.rodata) }
+ .rela.rodata : { *(.rela.rodata) }
+ .rel.got : { *(.rel.got) }
+ .rela.got : { *(.rela.got) }
+ .rel.ctors : { *(.rel.ctors) }
+ .rela.ctors : { *(.rela.ctors) }
+ .rel.dtors : { *(.rel.dtors) }
+ .rela.dtors : { *(.rela.dtors) }
+ .rel.bss : { *(.rel.bss) }
+ .rela.bss : { *(.rela.bss) }
+ .rel.plt : { *(.rel.plt) }
+ .rela.plt : { *(.rela.plt) }
+ .init : { *(.init) }
+ .plt : { *(.plt) }
+ .text :
+ {
+ cpu/74xx_7xx/start.o (.text)
+
+/* store the environment in a seperate sector in the boot flash */
+/* . = env_offset; */
+/* common/environment.o(.text) */
+
+ *(.text)
+ *(.fixup)
+ *(.got1)
+ }
+ _etext = .;
+ PROVIDE (etext = .);
+ .rodata :
+ {
+ *(.rodata)
+ *(.rodata1)
+ *(.rodata.str1.4)
+ *(.eh_frame)
+ }
+ .fini : { *(.fini) } =0
+ .ctors : { *(.ctors) }
+ .dtors : { *(.dtors) }
+
+ /* Read-write section, merged into data segment: */
+ . = (. + 0x00FF) & 0xFFFFFF00;
+ _erotext = .;
+ PROVIDE (erotext = .);
+ .reloc :
+ {
+ *(.got)
+ _GOT2_TABLE_ = .;
+ *(.got2)
+ _FIXUP_TABLE_ = .;
+ *(.fixup)
+ }
+ __got2_entries = (_FIXUP_TABLE_ - _GOT2_TABLE_) >>2;
+ __fixup_entries = (. - _FIXUP_TABLE_)>>2;
+
+ .data :
+ {
+ *(.data)
+ *(.data1)
+ *(.sdata)
+ *(.sdata2)
+ *(.dynamic)
+ CONSTRUCTORS
+ }
+ _edata = .;
+ PROVIDE (edata = .);
+
+ . = .;
+ __u_boot_cmd_start = .;
+ .u_boot_cmd : { *(.u_boot_cmd) }
+ __u_boot_cmd_end = .;
+
+
+ . = .;
+ __start___ex_table = .;
+ __ex_table : { *(__ex_table) }
+ __stop___ex_table = .;
+
+ . = ALIGN(256);
+ __init_begin = .;
+ .text.init : { *(.text.init) }
+ .data.init : { *(.data.init) }
+ . = ALIGN(256);
+ __init_end = .;
+
+ __bss_start = .;
+ .bss :
+ {
+ *(.sbss) *(.scommon)
+ *(.dynbss)
+ *(.bss)
+ *(COMMON)
+ }
+ _end = . ;
+ PROVIDE (end = .);
+}