]> www.infradead.org Git - users/rw/ppcboot.git/commitdiff
Patch by Keith Outwate, 21 Aug 2002:
authorwdenk <wdenk>
Wed, 21 Aug 2002 23:00:30 +0000 (23:00 +0000)
committerwdenk <wdenk>
Wed, 21 Aug 2002 23:00:30 +0000 (23:00 +0000)
- fix/add debug messages in soft_i2c.c
- added better memory test (optional)
- added support for 3rd status LED
- Date & Time support (no alarms) for
  Dallas Semiconductor (now Maxim) DS1337 Real Time Clock
- README fixes / extensions
- FPGA device configuration driver (Rich Ireland)

40 files changed:
CHANGELOG
CREDITS
README
board/dnp1110/dnp1110.c
board/ep7312/ep7312.c
board/impa7/impa7.c
board/lart/lart.c
board/shannon/shannon.c
board/smdk2410/smdk2410.c
common/Makefile
common/altera.c [new file with mode: 0644]
common/cmd_fpga.c [new file with mode: 0644]
common/cmd_mem.c
common/cmd_nvedit.c
common/command.c
common/fpga.c [new file with mode: 0644]
common/soft_i2c.c
common/spartan2.c [new file with mode: 0644]
common/virtex2.c [new file with mode: 0644]
common/xilinx.c [new file with mode: 0644]
cpu/arm720t/cpu.c
cpu/arm920t/cpu.c
cpu/mpc8xx/status_led.c
cpu/sa1100/cpu.c
cpu/xscale/cpu.c
doc/README.commands
include/altera.h [new file with mode: 0644]
include/asm-arm/global_data.h
include/asm-arm/ppcboot-arm.h [new file with mode: 0644]
include/asm-arm/ppcboot.h
include/cmd_confdefs.h
include/cmd_fpga.h [new file with mode: 0644]
include/common.h
include/fpga.h [new file with mode: 0644]
include/spartan2.h [new file with mode: 0644]
include/virtex2.h [new file with mode: 0644]
include/xilinx.h [new file with mode: 0644]
lib_arm/armlinux.c
rtc/Makefile
rtc/ds1337.c [new file with mode: 0644]

index c6d258386b088d945838fef5c1f6fceb39e9d8b5..bdc0d0d602183d78e40a96ccba872565c6295a71 100644 (file)
--- a/CHANGELOG
+++ b/CHANGELOG
@@ -11,6 +11,14 @@ Modifications for 1.2.0:
 
 For details about the current modifications, please see README-WIP
 
+* Patch by Keith Outwate, 21 Aug 2002:
+  - fix/add debug messages in soft_i2c.c
+  - added better memory test (optional)
+  - added support for 3rd status LED
+  - Date & Time support (no alarms) for
+    Dallas Semiconductor (now Maxim) DS1337 Real Time Clock
+  - README fixes / extensions
+  - FPGA device configuration driver (Rich Ireland)
 
 * Patch by Scott McNutt,, 14 Aug 2002:
   IBM 440GP Ethernet support
diff --git a/CREDITS b/CREDITS
index f64d152bbdbcf03275cf1c8bd9dc00bb451b8caf..743114825207f6e02f06080f7b12b113eb5e0f31 100644 (file)
--- a/CREDITS
+++ b/CREDITS
@@ -36,7 +36,7 @@ D: PCMCIA, Ethernet, TFTP
 
 N: Jerry van Baren
 E: <vanbaren@cideas.com>
-D: BedBug port to 603e core (MPC82xx)
+D: BedBug port to 603e core (MPC82xx). Code for enhanced memory test.
 
 N: Raphael Bossek
 E: raphael.bossek@solutions4linux.de
@@ -122,6 +122,10 @@ H: Stuart Hughes
 E: stuarth@lineo.com
 D: Port to MPC8260ADS board
 
+H: Rich Ireland
+E: r.ireland@computer.org
+D: FPGA device configuration driver
+
 N: Murray Jensen
 E: Murray.Jensen@cmst.csiro.au
 D: Initial 8260 support; GDB support
diff --git a/README b/README
index f072820f9824a82ca56960b13e10de0e5a8c3410..bde093d9fe4d64a980aca26bfb134ae517ab91ff 100644 (file)
--- a/README
+++ b/README
@@ -792,6 +792,54 @@ The following options need to be configured:
                 Time to wait after FPGA configuration. The default is
                200 mS.
 
+- FPGA Support:        CONFIG_FPGA_COUNT
+               Specify the number of FPGA devices to support.
+               CONFIG_FPGA
+               Used to specify the types of FPGA devices.  For example,
+               #define CONFIG_FPGA  CFG_XILINX_VIRTEX2 
+               CFG_FPGA_PROG_FEEDBACK
+               Enable printing of hash marks during FPGA configuration.
+
+               CFG_FPGA_CHECK_BUSY
+
+               Enable checks on FPGA configuration interface busy status
+               by the configuration function.  This option will require 
+               a board or device specific function to be written.
+
+               CONFIG_FPGA_DELAY
+
+               If defined, a function that provides delays in the FPGA
+               configuration driver.
+
+               CFG_FPGA_CHECK_CTRLC
+               Allow Control-C to interrupt FPGA configuration
+
+               CFG_FPGA_CHECK_ERROR
+
+               Check for configuration errors during FPGA bitfile loading.
+               For example, abort during Virtex II configuration if the
+               INIT_B line goes low (which indicated a CRC error).
+
+               CFG_FPGA_WAIT_INIT
+
+               Maximum time to wait for the INIT_B line to deassert after
+               PROB_B has been deasserted during a Virtex II FPGA
+               configuration sequence.  The default time is 500 mS.
+
+               CFG_FPGA_WAIT_BUSY
+               
+               Maximum time to wait for BUSY to deassert during Virtex II
+               FPGA configuration.  The default is 5 mS.
+
+               CFG_FPGA_WAIT_CONFIG
+
+               Time to wait after FPGA configuration.  The default is 200 mS.
+
 - Configuration Management:
                CONFIG_IDENT_STRING
 
@@ -1224,6 +1272,26 @@ to save the current settings.
        - CFG_EEPROM_SIZE:
          The size in bytes of the EEPROM device.
 
+       - CFG_I2C_EEPROM_ADDR:
+         If defined, specified the chip address of the EEPROM device.
+         The default address is zero.
+
+       - CFG_EEPROM_PAGE_WRITE_BITS:
+         If defined, the number of bits used to address bytes in a 
+         single page in the EEPROM device.  A 64 byte page, for example
+         would require six bits.
+
+       - CFG_EEPROM_PAGE_WRITE_DELAY_MS:
+         If defined, the number of milliseconds to delay between
+         page writes.  The default is zero milliseconds.
+
+       - CFG_I2C_EEPROM_ADDR_LEN:
+         The length in bytes of the EEPROM memory array address.  Note
+         that this is NOT the chip address length!
+
+       - CFG_EEPROM_SIZE:
+         The size in bytes of the EEPROM device.
+
 - CFG_SPI_INIT_OFFSET
 
        Defines offset to the initial SPI buffer area in DPRAM. The
index 588febda8bba947d3e952f1592df3707beaf648b..e551b7bc51b074e46d13b4b6fea82baddd8b4424 100644 (file)
  * Miscelaneous platform dependent initialisations
  */
 
-int board_init(bd_t *bd)
+int board_init (gd_t *gd)
 {
-    /* memory and cpu-speed are setup before relocation */
-    /* so we do _nothing_ here */
+       /* memory and cpu-speed are setup before relocation */
+       /* so we do _nothing_ here */
 
-    /* arch number of DNP1110-Board */
-    bd->bi_arch_number = 255;
+       /* arch number of DNP1110-Board */
+       bd->bi_arch_number = 255;
 
-    /* adress of boot parameters */
-    bd->bi_boot_params = 0xc0000100;
+       /* adress of boot parameters */
+       bd->bi_boot_params = 0xc0000100;
 
-    return 1;
+       return 0;
 }
 
-int dram_init(bd_t *bd)
+int dram_init (gd_t *gd)
 {
-    bd->bi_dram[0].start = PHYS_SDRAM_1;
-    bd->bi_dram[0].size  = PHYS_SDRAM_1_SIZE;
-    return PHYS_SDRAM_1_SIZE;
+       bd->bi_dram[0].start = PHYS_SDRAM_1;
+       bd->bi_dram[0].size = PHYS_SDRAM_1_SIZE;
+
+       return PHYS_SDRAM_1_SIZE;
 }
index 2611190b783e6b5f0d70eca15fc9ad0b8588a166..7ea2a537aa4327224a9169fdc1acc4ffdabd1bad 100644 (file)
  * Miscelaneous platform dependent initialisations
  */
 
-int board_init(bd_t *bd)
+int board_init (gd_t *gd)
 {
-    /* Activate LED flasher */
-    IO_LEDFLSH = 0x40;
+       /* Activate LED flasher */
+       IO_LEDFLSH = 0x40;
 
-    /* arch number MACH_TYPE_EDB7312 */
-    bd->bi_arch_number = 131;
+       /* arch number MACH_TYPE_EDB7312 */
+       bd->bi_arch_number = 131;
 
-    /* location of boot parameters */
-    bd->bi_boot_params = 0xc0020100;
+       /* location of boot parameters */
+       bd->bi_boot_params = 0xc0020100;
 
-    return 1;
+       return 0;
 }
 
-int dram_init(bd_t *bd)
+int dram_init (gd_t *gd)
 {
-    bd->bi_dram[0].start = PHYS_SDRAM_1;
-    bd->bi_dram[0].size  = PHYS_SDRAM_1_SIZE;
+       bd->bi_dram[0].start = PHYS_SDRAM_1;
+       bd->bi_dram[0].size = PHYS_SDRAM_1_SIZE;
 
-    return PHYS_SDRAM_1_SIZE;
+       return PHYS_SDRAM_1_SIZE;
 }
index 6f8f74fa0c02f6c4049a453133302ddd342a1350..792ec07b63c00004f999ebf426840cd1d150ac2a 100644 (file)
  * Miscelaneous platform dependent initialisations
  */
 
-int board_init(bd_t *bd)
+int board_init (gd_t *gd)
 {
-    /* Activate LED flasher */
-    IO_LEDFLSH = 0x40;
+       /* Activate LED flasher */
+       IO_LEDFLSH = 0x40;
 
-    /* arch number of EP7111 */
-    bd->bi_arch_number = 50;
+       /* arch number of EP7111 */
+       bd->bi_arch_number = 50;
 
-    /* location of boot parameters for EP7111 */
-    bd->bi_boot_params = 0xc0020100;
+       /* location of boot parameters for EP7111 */
+       bd->bi_boot_params = 0xc0020100;
 
-    return 1;
+       return 0;
 }
 
-int dram_init(bd_t *bd)
+int dram_init (gd_t *gd)
 {
-    bd->bi_dram[0].start = PHYS_SDRAM_1;
-    bd->bi_dram[0].size  = PHYS_SDRAM_1_SIZE;
-    bd->bi_dram[1].start = PHYS_SDRAM_2;
-    bd->bi_dram[1].size  = PHYS_SDRAM_2_SIZE;
-    
-    return PHYS_SDRAM_1_SIZE + PHYS_SDRAM_2_SIZE;
+       bd->bi_dram[0].start = PHYS_SDRAM_1;
+       bd->bi_dram[0].size = PHYS_SDRAM_1_SIZE;
+       bd->bi_dram[1].start = PHYS_SDRAM_2;
+       bd->bi_dram[1].size = PHYS_SDRAM_2_SIZE;
+
+       return PHYS_SDRAM_1_SIZE + PHYS_SDRAM_2_SIZE;
 }
index d1d874bb940333d64275d614ffdcf9fcef58d0ff..30845adf2595dbf305af409927533898448ae277 100644 (file)
  * Miscelaneous platform dependent initialisations
  */
 
-int board_init(bd_t *bd)
+int board_init (gd_t *gd)
 {
-    /* memory and cpu-speed are setup before relocation */
-    /* so we do _nothing_ here */
+       /* memory and cpu-speed are setup before relocation */
+       /* so we do _nothing_ here */
 
-    /* arch number of LART-Board */
-    bd->bi_arch_number = 27;
+       /* arch number of LART-Board */
+       bd->bi_arch_number = 27;
 
-    /* adress of boot parameters */
-    bd->bi_boot_params = 0xc0000100;
+       /* adress of boot parameters */
+       bd->bi_boot_params = 0xc0000100;
 
-    return 1;
+       return 0;
 }
 
-int dram_init(bd_t *bd)
+int dram_init (gd_t *gd)
 {
-    bd->bi_dram[0].start = PHYS_SDRAM_1;
-    bd->bi_dram[0].size  = PHYS_SDRAM_1_SIZE;
-    bd->bi_dram[1].start = PHYS_SDRAM_2;
-    bd->bi_dram[1].size  = PHYS_SDRAM_2_SIZE;
-    bd->bi_dram[2].start = PHYS_SDRAM_3;
-    bd->bi_dram[2].size  = PHYS_SDRAM_3_SIZE;
-    bd->bi_dram[3].start = PHYS_SDRAM_4;
-    bd->bi_dram[3].size  = PHYS_SDRAM_4_SIZE;
-    return PHYS_SDRAM_1_SIZE + PHYS_SDRAM_2_SIZE + PHYS_SDRAM_3_SIZE + PHYS_SDRAM_4_SIZE;
+       bd->bi_dram[0].start = PHYS_SDRAM_1;
+       bd->bi_dram[0].size = PHYS_SDRAM_1_SIZE;
+       bd->bi_dram[1].start = PHYS_SDRAM_2;
+       bd->bi_dram[1].size = PHYS_SDRAM_2_SIZE;
+       bd->bi_dram[2].start = PHYS_SDRAM_3;
+       bd->bi_dram[2].size = PHYS_SDRAM_3_SIZE;
+       bd->bi_dram[3].start = PHYS_SDRAM_4;
+       bd->bi_dram[3].size = PHYS_SDRAM_4_SIZE;
+
+       return (PHYS_SDRAM_1_SIZE +
+               PHYS_SDRAM_2_SIZE +
+               PHYS_SDRAM_3_SIZE +
+               PHYS_SDRAM_4_SIZE );
 }
index e69656b4c2abf0005ccf6f17a5c9d77460735b2a..1a23ec4c21234e1d50059ae13fb99f8f6b846728 100644 (file)
  * Miscelaneous platform dependent initialisations
  */
 
-int board_init(bd_t *bd)
+int board_init (gd_t *gd)
 {
-    /* memory and cpu-speed are setup before relocation */
-    /* but if we use InfernoLoader, we must do some inits here */
+       /* memory and cpu-speed are setup before relocation */
+       /* but if we use InfernoLoader, we must do some inits here */
 
-    #ifdef CONFIG_INFERNO
-    {
+#ifdef CONFIG_INFERNO
+       {
         unsigned long temp;
         __asm__ __volatile__(/* disable MMU, enable icache */
                              "mrc p15, 0, %0, c1, c0\n"
@@ -57,43 +57,45 @@ int board_init(bd_t *bd)
         temp = 0xa0000018;
         *(unsigned long *)temp = 0x00060006;
 
-    }
-    #endif /* CONFIG_INIT_CRITICAL */
+       }
+#endif /* CONFIG_INIT_CRITICAL */
 
-    /* arch number for shannon */
-    bd->bi_arch_number = 97;
+       /* arch number for shannon */
+       bd->bi_arch_number = 97;
 
-    /* adress of boot parameters */
-    bd->bi_boot_params = 0xc0000100;
+       /* adress of boot parameters */
+       bd->bi_boot_params = 0xc0000100;
 
-    return 1;
+       return 0;
 }
 
-int dram_init(bd_t *bd)
+int dram_init (gd_t * gd)
 {
-    #ifdef PHYS_SDRAM_1
-    bd->bi_dram[0].start = PHYS_SDRAM_1;
-    bd->bi_dram[0].size  = PHYS_SDRAM_1_SIZE;
-    #endif
+#ifdef PHYS_SDRAM_1
+       bd->bi_dram[0].start = PHYS_SDRAM_1;
+       bd->bi_dram[0].size = PHYS_SDRAM_1_SIZE;
+#endif
 
-    #ifdef PHYS_SDRAM_2
-    bd->bi_dram[1].start = PHYS_SDRAM_2;
-    bd->bi_dram[1].size  = PHYS_SDRAM_2_SIZE;
-    #endif
+#ifdef PHYS_SDRAM_2
+       bd->bi_dram[1].start = PHYS_SDRAM_2;
+       bd->bi_dram[1].size = PHYS_SDRAM_2_SIZE;
+#endif
 
-    #ifdef PHYS_SDRAM_3
-    bd->bi_dram[2].start = PHYS_SDRAM_3;
-    bd->bi_dram[2].size  = PHYS_SDRAM_3_SIZE;
-    #endif
+#ifdef PHYS_SDRAM_3
+       bd->bi_dram[2].start = PHYS_SDRAM_3;
+       bd->bi_dram[2].size = PHYS_SDRAM_3_SIZE;
+#endif
 
-    #ifdef PHYS_SDRAM_4
-    bd->bi_dram[3].start = PHYS_SDRAM_4;
-    bd->bi_dram[3].size  = PHYS_SDRAM_4_SIZE;
-    #endif
+#ifdef PHYS_SDRAM_4
+       bd->bi_dram[3].start = PHYS_SDRAM_4;
+       bd->bi_dram[3].size = PHYS_SDRAM_4_SIZE;
+#endif
 
-    return PHYS_SDRAM_1_SIZE + PHYS_SDRAM_2_SIZE
-    #ifdef PHYS_SDRAM_4
-           + PHYS_SDRAM_3_SIZE + PHYS_SDRAM_4_SIZE
-    #endif
-    ;
+       return (  PHYS_SDRAM_1_SIZE
+               + PHYS_SDRAM_2_SIZE
+#ifdef PHYS_SDRAM_4
+               + PHYS_SDRAM_3_SIZE
+               + PHYS_SDRAM_4_SIZE
+#endif
+               );
 }
index 5944d948fb0dfa4ad79ec68ed9f139138b945798..2d124408f53d41e55c6dacb69a3a385f9c24d043 100644 (file)
 
 #define FCLK_SPEED 1
 
-#if FCLK_SPEED==0      /* Fout = 203MHz, Fin = 12MHz for Audio */
-    #define M_MDIV     0xC3
-    #define M_PDIV     0x4
-    #define M_SDIV     0x1
-#elif FCLK_SPEED==1    /* Fout = 202.8MHz */
-    #define M_MDIV     0xA1
-    #define M_PDIV     0x3
-    #define M_SDIV     0x1
+#if FCLK_SPEED==0              /* Fout = 203MHz, Fin = 12MHz for Audio */
+#define M_MDIV 0xC3
+#define M_PDIV 0x4
+#define M_SDIV 0x1
+#elif FCLK_SPEED==1            /* Fout = 202.8MHz */
+#define M_MDIV 0xA1
+#define M_PDIV 0x3
+#define M_SDIV 0x1
 #endif
 
 #define USB_CLOCK 1
 
 #if USB_CLOCK==0
-    #define U_M_MDIV   0xA1
-    #define U_M_PDIV   0x3
-    #define U_M_SDIV   0x1
+#define U_M_MDIV       0xA1
+#define U_M_PDIV       0x3
+#define U_M_SDIV       0x1
 #elif USB_CLOCK==1
-    #define U_M_MDIV   0x48
-    #define U_M_PDIV   0x3
-    #define U_M_SDIV   0x2
+#define U_M_MDIV       0x48
+#define U_M_PDIV       0x3
+#define U_M_SDIV       0x2
 #endif
 
-static inline
-void delay(unsigned long loops)
+static inline void delay (unsigned long loops)
 {
-    __asm__ volatile (
-       "1:\n"
-       "subs %0, %1, #1\n"
-       "bne 1b"
-        : "=r" (loops) : "0" (loops));
+       __asm__ volatile ("1:\n"
+         "subs %0, %1, #1\n"
+         "bne 1b":"=r" (loops):"0" (loops));
 }
 
 /*
  * Miscellaneous platform dependent initialisations
  */
 
-int board_init(bd_t *bd)
+int board_init (gd_t *gd)
 {
-    /* to reduce PLL lock time, adjust the LOCKTIME register */
-    rLOCKTIME = 0xFFFFFF;
-
-    /* configure MPLL */
-    rMPLLCON = ((M_MDIV << 12) + (M_PDIV << 4) + M_SDIV);
-
-    /* some delay between MPLL and UPLL */
-    delay(4000);
-
-    /* configure UPLL */
-    rUPLLCON = ((U_M_MDIV << 12) + (U_M_PDIV << 4) + U_M_SDIV);
-
-    /* some delay between MPLL and UPLL */
-    delay(8000);
-
-    /* set up the I/O ports */
-    rGPACON = 0x007FFFFF;
-    rGPBCON = 0x00044555;
-    rGPBUP  = 0x000007FF;
-    rGPCCON = 0xAAAAAAAA;
-    rGPCUP  = 0x0000FFFF;
-    rGPDCON = 0xAAAAAAAA;
-    rGPDUP  = 0x0000FFFF;
-    rGPECON = 0xAAAAAAAA;
-    rGPEUP  = 0x0000FFFF;
-    rGPFCON = 0x000055AA;
-    rGPFUP  = 0x000000FF;
-    rGPGCON = 0xFF95FFBA;
-    rGPGUP  = 0x0000FFFF;
-    rGPHCON = 0x002AFAAA;
-    rGPHUP  = 0x000007FF;
-
-    /* arch number of SMDK2410-Board */
-    bd->bi_arch_number = 193;
-
-    /* adress of boot parameters */
-    bd->bi_boot_params = 0x30000100;
-
-    return 1;
+       /* to reduce PLL lock time, adjust the LOCKTIME register */
+       rLOCKTIME = 0xFFFFFF;
+
+       /* configure MPLL */
+       rMPLLCON = ((M_MDIV << 12) + (M_PDIV << 4) + M_SDIV);
+
+       /* some delay between MPLL and UPLL */
+       delay (4000);
+
+       /* configure UPLL */
+       rUPLLCON = ((U_M_MDIV << 12) + (U_M_PDIV << 4) + U_M_SDIV);
+
+       /* some delay between MPLL and UPLL */
+       delay (8000);
+
+       /* set up the I/O ports */
+       rGPACON = 0x007FFFFF;
+       rGPBCON = 0x00044555;
+       rGPBUP = 0x000007FF;
+       rGPCCON = 0xAAAAAAAA;
+       rGPCUP = 0x0000FFFF;
+       rGPDCON = 0xAAAAAAAA;
+       rGPDUP = 0x0000FFFF;
+       rGPECON = 0xAAAAAAAA;
+       rGPEUP = 0x0000FFFF;
+       rGPFCON = 0x000055AA;
+       rGPFUP = 0x000000FF;
+       rGPGCON = 0xFF95FFBA;
+       rGPGUP = 0x0000FFFF;
+       rGPHCON = 0x002AFAAA;
+       rGPHUP = 0x000007FF;
+
+       /* arch number of SMDK2410-Board */
+       bd->bi_arch_number = 193;
+
+       /* adress of boot parameters */
+       bd->bi_boot_params = 0x30000100;
+
+       return 0;
 }
 
-int dram_init(bd_t *bd)
+int dram_init (gd_t *gd)
 {
-    bd->bi_dram[0].start = PHYS_SDRAM_1;
-    bd->bi_dram[0].size  = PHYS_SDRAM_1_SIZE;
-    return PHYS_SDRAM_1_SIZE;
+       bd->bi_dram[0].start = PHYS_SDRAM_1;
+       bd->bi_dram[0].size = PHYS_SDRAM_1_SIZE;
+       return PHYS_SDRAM_1_SIZE;
 }
-
index a29a891e9dee0815e18f22ae072c0135ab4618e3..e0a9cf5266125e19d5c057f6ccc549c45173a801 100644 (file)
@@ -26,18 +26,18 @@ include $(TOPDIR)/config.mk
 LIB    = libcommon.a
 
 AOBJS  =
-COBJS  = main.o command.o environment.o bedbug.o \
-         cmd_autoscript.o cmd_bedbug.o cmd_boot.o \
-         cmd_bootm.o cmd_cache.o cmd_console.o cmd_date.o \
-         cmd_dcr.o cmd_doc.o cmd_dtt.o cmd_eeprom.o cmd_elf.o \
-         cmd_fdc.o cmd_flash.o cmd_i2c.o cmd_ide.o \
-         cmd_immap.o cmd_jffs2.o cmd_mem.o cmd_mii.o \
-         cmd_misc.o cmd_net.o cmd_nvedit.o cmd_pcmcia.o \
-         cmd_reginfo.o cmd_scsi.o cmd_usb.o cmd_pci.o \
-         console.o devices.o dlmalloc.o docecc.o \
-         flash.o hush.o kgdb.o lists.o \
-         miiphybb.o miiphyutil.o s_record.o \
-         usb.o usb_kbd.o usb_storage.o soft_i2c.o
+COBJS  = main.o altera.o command.o environment.o bedbug.o \
+         cmd_autoscript.o cmd_bedbug.o cmd_boot.o cmd_bootm.o \
+         cmd_cache.o cmd_console.o cmd_date.o cmd_dcr.o cmd_doc.o \
+         cmd_dtt.o cmd_eeprom.o cmd_elf.o cmd_fdc.o cmd_flash.o \
+         cmd_fpga.o cmd_i2c.o cmd_ide.o cmd_immap.o cmd_jffs2.o \
+         cmd_mem.o cmd_mii.o cmd_misc.o cmd_net.o cmd_nvedit.o \
+         cmd_pcmcia.o cmd_reginfo.o cmd_scsi.o cmd_usb.o cmd_pci.o \
+         console.o devices.o dlmalloc.o docecc.o flash.o fpga.o \
+         hush.o kgdb.o lists.o miiphybb.o miiphyutil.o s_record.o \
+         soft_i2c.o spartan2.o usb.o usb_kbd.o usb_storage.o \
+         virtex2.o xilinx.o
+
 # Temporary hack to get ARM working quickly
 ifeq ($(ARCH),ppc)
 COBJS  += cmd_nvedit.o
diff --git a/common/altera.c b/common/altera.c
new file mode 100644 (file)
index 0000000..beb0147
--- /dev/null
@@ -0,0 +1,73 @@
+/*
+ * (C) Copyright 2002
+ * Rich Ireland, Enterasys Networks, rireland@enterasys.com.
+ *
+ * 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
+ *
+ */
+
+/*
+ * Note that this is just boilerplate - there is no Altera support yet.
+ */
+
+
+/*
+ *  Altera FPGA support
+ */
+#include <common.h>
+#include <fpga.h>                     /* Generic FPGA support  */
+#include <altera.h>                   /* Altera specific stuff */
+
+#if 0
+#define FPGA_DEBUG
+#endif
+
+#ifdef FPGA_DEBUG
+#define        PRINTF(fmt,args...)     printf (fmt ,##args)
+#else
+#define PRINTF(fmt,args...)
+#endif
+
+#if (CONFIG_FPGA & CFG_FPGA_ALTERA)
+
+/* ------------------------------------------------------------------------- */
+int altera_load( Altera_desc *desc, void *buf, size_t bsize )
+{
+       printf( "No support for Altera devices yet.\n" );
+       return FPGA_FAIL;
+}
+
+int altera_dump( Altera_desc *desc, void *buf, size_t bsize )
+{
+       printf( "No support for Altera devices yet.\n" );
+       return FPGA_FAIL;
+}
+
+int altera_info( Altera_desc *desc )
+{
+       printf( "No support for Altera devices yet.\n" );
+       return FPGA_FAIL;
+}
+
+/* ------------------------------------------------------------------------- */
+
+
+/* ------------------------------------------------------------------------- */
+
+#endif  /* CONFIG_FPGA & CFG_FPGA_ALTERA */
diff --git a/common/cmd_fpga.c b/common/cmd_fpga.c
new file mode 100644 (file)
index 0000000..3d8c79e
--- /dev/null
@@ -0,0 +1,158 @@
+/*
+ * (C) Copyright 2000, 2001
+ * Rich Ireland, Enterasys Networks, rireland@enterasys.com.
+ *
+ * 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
+ *
+ */
+
+/*
+ *  FPGA support
+ */
+#include <common.h>
+#include <command.h>
+#include <cmd_fpga.h>
+#include <fpga.h>
+#if (CONFIG_COMMANDS & CFG_CMD_NET)
+#include <net.h>
+#endif
+
+#if 0
+#define        FPGA_DEBUG
+#endif
+
+#ifdef FPGA_DEBUG
+#define        PRINTF(fmt,args...)     printf (fmt ,##args)
+#else
+#define PRINTF(fmt,args...)
+#endif
+
+#if defined (CONFIG_FPGA) && ( CONFIG_COMMANDS & CFG_CMD_FPGA )
+
+/* Local functions */
+static void fpga_usage ( cmd_tbl_t *cmdtp );
+static int fpga_get_op( char *opstr );
+
+/* Local defines */
+#define FPGA_NONE   -1
+#define FPGA_INFO   0
+#define FPGA_LOAD   1
+#define FPGA_DUMP   3
+
+/* ------------------------------------------------------------------------- */
+/* command form:
+ *   fpga <op> <device number> <data addr> <datasize>
+ * where op is 'load', 'dump', or 'info'
+ * If there is no device number field, the fpga environment variable is used.
+ * If there is no data addr field, the fpgadata environment variable is used.
+ * The info command requires no data address field.
+ */
+int
+do_fpga (cmd_tbl_t *cmdtp, gd_t *gd, int flag, int argc, char *argv[])
+{
+    int op, dev = FPGA_INVALID_DEVICE;
+    size_t data_size = 0;
+    void *fpga_data = NULL;
+    char *devstr = getenv("fpga");
+    char *datastr = getenv("fpgadata");
+
+       if ( devstr ) dev = (int)simple_strtoul( devstr, NULL, 16 );
+       if ( datastr ) fpga_data = (void *)simple_strtoul( datastr, NULL, 16 );
+
+    switch ( argc )
+    {
+           case 5: /* fpga <op> <dev> <data> <datasize> */
+                   data_size = simple_strtoul( argv[4], NULL, 16 );
+           case 4: /* fpga <op> <dev> <data> */
+                   fpga_data = (void *)simple_strtoul( argv[3], NULL, 16 );
+                       PRINTF(__FUNCTION__": fpga_data = 0x%x\n", (uint)fpga_data );
+           case 3: /* fpga <op> <dev | data addr> */
+                   dev = (int)simple_strtoul( argv[2], NULL, 16 );
+                       PRINTF(__FUNCTION__": device = %d\n", dev );
+                       /* FIXME - this is a really weak test */
+                   if (( argc == 3 ) && ( dev > fpga_count() )) { /* must be buffer ptr */
+                               PRINTF(__FUNCTION__": Assuming buffer pointer in arg 3\n");
+                           fpga_data = (void *)dev;
+                               PRINTF(__FUNCTION__": fpga_data = 0x%x\n", (uint)fpga_data );
+                           dev = FPGA_INVALID_DEVICE;  /* reset device num */
+                   }
+           case 2: /* fpga <op> */
+                   op = (int)fpga_get_op( argv[1] );
+                   break;
+           default:
+                       PRINTF(__FUNCTION__": Too many or too few args (%d)\n", argc );
+                   op = FPGA_NONE;    /* force usage display */
+                   break;
+    }
+
+    switch ( op ) {
+           case FPGA_NONE:
+                   fpga_usage( cmdtp );
+                   break;
+
+           case FPGA_INFO:
+                   fpga_info( dev );
+                   break;
+
+           case FPGA_LOAD:
+                       fpga_load( dev, fpga_data, data_size );
+                   break;
+
+           case FPGA_DUMP:
+                       fpga_dump( dev, fpga_data, data_size );
+                   break;
+
+           default:
+                   printf( "Unknown operation.\n" );
+                   fpga_usage( cmdtp );
+                   break;
+    }
+    return 0;
+}
+
+static void fpga_usage ( cmd_tbl_t *cmdtp )
+{
+       printf( "Usage:\n%s\n", cmdtp->usage );
+}
+
+/*
+ * Map op to supported operations.  We don't use a table since we
+ * would just have to relocate it from flash anyway.
+ */
+static int fpga_get_op( char *opstr )
+{
+       int op = FPGA_NONE;
+
+       if (!strcmp ("info", opstr)) {
+               op = FPGA_INFO;
+       }
+       else if (!strcmp ("load", opstr)) {
+               op = FPGA_LOAD;
+       }
+       else if (!strcmp ("dump", opstr)) {
+               op = FPGA_DUMP;
+       }
+
+       if ( op == FPGA_NONE ) {
+               printf ("Unknown fpga operation \"%s\"\n", opstr);
+       }
+       return op;
+}
+
+#endif /* CONFIG_FPGA && CONFIG_COMMANDS & CFG_CMD_FPGA */
index e395e25328bc9f9df0f5bc850bf8c187c3d37283..497dd798ff0879e02dd6d3cf80eae907e1a72f41 100644 (file)
@@ -39,11 +39,11 @@ int cmd_get_data_size(char* arg, int default_size)
        int len = strlen(arg);
        if (len > 2 && arg[len-2] == '.') {
                switch(arg[len-1]) {
-               case 'b': 
-                       return 1; 
-               case 'w': 
+               case 'b':
+                       return 1;
+               case 'w':
                        return 2;
-               case 'l': 
+               case 'l':
                        return 4;
                }
        }
@@ -52,6 +52,13 @@ int cmd_get_data_size(char* arg, int default_size)
 #endif
 
 #if (CONFIG_COMMANDS & CFG_CMD_MEMORY)
+
+#ifdef CMD_MEM_DEBUG
+#define        PRINTF(fmt,args...)     printf (fmt ,##args)
+#else
+#define PRINTF(fmt,args...)
+#endif
+
 static int mod_mem(cmd_tbl_t *, int, int, int, char *[]);
 
 /* Display values from last command.
@@ -157,7 +164,7 @@ int do_mem_md ( cmd_tbl_t *cmdtp, gd_t *gd,
 int do_mem_mm ( cmd_tbl_t *cmdtp, gd_t *gd,
                int flag, int argc, char *argv[])
 {
-       return mod_mem (cmdtp, 1, flag, argc, argv);
+       return mod_mem (cmdtp, 1, flag, argc, argv);
 }
 int do_mem_nm ( cmd_tbl_t *cmdtp, gd_t *gd,
                int flag, int argc, char *argv[])
@@ -417,16 +424,44 @@ int do_mem_loop (cmd_tbl_t *cmdtp, gd_t *gd,
        }
 }
 
-/* Just a quickie to walk through some memory.
+/*
+ * Perform a memory test. A more complete alternative test can be
+ * configured using CFG_ALT_MEMTEST. The complete test loops until
+ * interrupted by ctrl-c or by a failure of one of the sub-tests.
  */
-
-int do_mem_mtest (cmd_tbl_t *cmdtp, gd_t *gd,
-                 int flag, int argc, char *argv[])
+int do_mem_mtest (cmd_tbl_t *cmdtp, gd_t *gd, int flag, int argc, char *argv[])
 {
-       ulong   *addr, *start, *end;
+       vu_long *addr, *start, *end;
        ulong   val;
+       ulong   readback;
+
+#if defined(CFG_ALT_MEMTEST)
+       vu_long addr_mask;
+       vu_long offset;
+       vu_long test_offset;
+       vu_long pattern;
+       vu_long temp;
+       vu_long anti_pattern;
+       vu_long num_words;
+       vu_long *dummy = NULL;
+       int     j;
+       int iterations = 1;
+
+       static const ulong bitpattern[] = {
+               0x00000001,     /* single bit */
+               0x00000003,     /* two adjacent bits */
+               0x00000007,     /* three adjacent bits */
+               0x0000000F,     /* four adjacent bits */
+               0x00000005,     /* two non-adjacent bits */
+               0x00000015,     /* three non-adjacent bits */
+               0x00000055,     /* four non-adjacent bits */
+               0xaaaaaaaa,     /* alternating 1/0 */
+       };
+#else
+       ulong   incr;
        ulong   pattern;
        int     rcode = 0;
+#endif
 
        if (argc > 1) {
                start = (ulong *)simple_strtoul(argv[1], NULL, 16);
@@ -446,8 +481,207 @@ int do_mem_mtest (cmd_tbl_t *cmdtp, gd_t *gd,
                pattern = 0;
        }
 
+#if defined(CFG_ALT_MEMTEST)
        printf ("Testing %08x ... %08x:\n", (uint)start, (uint)end);
+       PRINTF("%s:%d: start 0x%p end 0x%p\n",
+               __FUNCTION__, __LINE__, start, end);
+
+       for (;;) {
+               if (ctrlc()) {
+                       putc ('\n');
+                       return 1;
+               }
+
+               printf("Iteration: %6d\r", iterations);
+               PRINTF("Iteration: %6d\n", iterations);
+               iterations++;
+
+               /*
+                * Data line test: write a pattern to the first
+                * location, write the 1's complement to a 'parking'
+                * address (changes the state of the data bus so a
+                * floating bus doen't give a false OK), and then
+                * read the value back. Note that we read it back
+                * into a variable because the next time we read it,
+                * it might be right (been there, tough to explain to
+                * the quality guys why it prints a failure when the
+                * "is" and "should be" are obviously the same in the
+                * error message).
+                *
+                * Rather than exhaustively testing, we test some
+                * patterns by shifting '1' bits through a field of
+                * '0's and '0' bits through a field of '1's (i.e.
+                * pattern and ~pattern).
+                */
+               addr = start;
+               for (j = 0; j < sizeof(bitpattern)/sizeof(bitpattern[0]); j++) {
+                   val = bitpattern[j];
+                   for(; val != 0; val <<= 1) {
+                       *addr  = val;
+                       *dummy  = ~val; /* clear the test data off of the bus */
+                       readback = *addr;
+                       if(readback != val) {
+                            printf ("FAILURE (data line): "
+                               "expected %08lx, actual %08lx\n",
+                                         val, readback);
+                       }
+                       *addr  = ~val;
+                       *dummy  = val;
+                       readback = *addr;
+                       if(readback != ~val) {
+                           printf ("FAILURE (data line): "
+                               "Is %08lx, should be %08lx\n",
+                                       val, readback);
+                       }
+                   }
+               }
+
+               /*
+                * Based on code whose Original Author and Copyright
+                * information follows: Copyright (c) 1998 by Michael
+                * Barr. This software is placed into the public
+                * domain and may be used for any purpose. However,
+                * this notice must not be changed or removed and no
+                * warranty is either expressed or implied by its
+                * publication or distribution.
+                */
+
+               /*
+                * Address line test
+                *
+                * Description: Test the address bus wiring in a
+                *              memory region by performing a walking
+                *              1's test on the relevant bits of the
+                *              address and checking for aliasing.
+                *              This test will find single-bit
+                *              address failures such as stuck -high,
+                *              stuck-low, and shorted pins. The base
+                *              address and size of the region are
+                *              selected by the caller.
+                *
+                * Notes:       For best results, the selected base
+                *              address should have enough LSB 0's to
+                *              guarantee single address bit changes.
+                *              For example, to test a 64-Kbyte
+                *              region, select a base address on a
+                *              64-Kbyte boundary. Also, select the
+                *              region size as a power-of-two if at
+                *              all possible.
+                *
+                * Returns:     0 if the test succeeds, 1 if the test fails.
+                *
+                * ## NOTE ##   Be sure to specify start and end
+                *              addresses such that addr_mask has
+                *              lots of bits set. For example an
+                *              address range of 01000000 02000000 is
+                *              bad while a range of 01000000
+                *              01ffffff is perfect.
+                */
+               addr_mask = ((ulong)end - (ulong)start)/sizeof(vu_long);
+               pattern = (vu_long) 0xaaaaaaaa;
+               anti_pattern = (vu_long) 0x55555555;
+
+               PRINTF("%s:%d: addr mask = 0x%.8lx\n",
+                       __FUNCTION__, __LINE__,
+                       addr_mask);
+               /*
+                * Write the default pattern at each of the
+                * power-of-two offsets.
+                */
+               for (offset = 1; (offset & addr_mask) != 0; offset <<= 1) {
+                       start[offset] = pattern;
+               }
+
+               /*
+                * Check for address bits stuck high.
+                */
+               test_offset = 0;
+               start[test_offset] = anti_pattern;
+
+               for (offset = 1; (offset & addr_mask) != 0; offset <<= 1) {
+                   temp = start[offset];
+                   if (temp != pattern) {
+                       printf ("\nFAILURE: Address bit stuck high @ 0x%.8lx:"
+                               " expected 0x%.8lx, actual 0x%.8lx\n",
+                               (ulong)&start[offset], pattern, temp);
+                       return 1;
+                   }
+               }
+               start[test_offset] = pattern;
 
+               /*
+                * Check for addr bits stuck low or shorted.
+                */
+               for (test_offset = 1; (test_offset & addr_mask) != 0; test_offset <<= 1) {
+                   start[test_offset] = anti_pattern;
+
+                   for (offset = 1; (offset & addr_mask) != 0; offset <<= 1) {
+                       temp = start[offset];
+                       if ((temp != pattern) && (offset != test_offset)) {
+                           printf ("\nFAILURE: Address bit stuck low or shorted @"
+                               " 0x%.8lx: expected 0x%.8lx, actual 0x%.8lx\n",
+                               (ulong)&start[offset], pattern, temp);
+                           return 1;
+                       }
+                   }
+                   start[test_offset] = pattern;
+               }
+
+               /*
+                * Description: Test the integrity of a physical
+                *              memory device by performing an
+                *              increment/decrement test over the
+                *              entire region. In the process every
+                *              storage bit in the device is tested
+                *              as a zero and a one. The base address
+                *              and the size of the region are
+                *              selected by the caller.
+                *
+                * Returns:     0 if the test succeeds, 1 if the test fails.
+                */
+               num_words = ((ulong)end - (ulong)start)/sizeof(vu_long) + 1;
+
+               /*
+                * Fill memory with a known pattern.
+                */
+               for (pattern = 1, offset = 0; offset < num_words; pattern++, offset++) {
+                       start[offset] = pattern;
+               }
+
+               /*
+                * Check each location and invert it for the second pass.
+                */
+               for (pattern = 1, offset = 0; offset < num_words; pattern++, offset++) {
+                   temp = start[offset];
+                   if (temp != pattern) {
+                       printf ("\nFAILURE (read/write) @ 0x%.8lx:"
+                               " expected 0x%.8lx, actual 0x%.8lx)\n",
+                               (ulong)&start[offset], pattern, temp);
+                       return 1;
+                   }
+
+                   anti_pattern = ~pattern;
+                   start[offset] = anti_pattern;
+               }
+
+               /*
+                * Check each location for the inverted pattern and zero it.
+                */
+               for (pattern = 1, offset = 0; offset < num_words; pattern++, offset++) {
+                   anti_pattern = ~pattern;
+                   temp = start[offset];
+                   if (temp != anti_pattern) {
+                       printf ("\nFAILURE (read/write): @ 0x%.8lx:"
+                               " expected 0x%.8lx, actual 0x%.8lx)\n",
+                               (ulong)&start[offset], anti_pattern, temp);
+                       return 1;
+                   }
+                   start[offset] = 0;
+               }
+       }
+
+#else /* The original, quickie test */
+       incr = 1;
        for (;;) {
                if (ctrlc()) {
                        putc ('\n');
@@ -460,31 +694,42 @@ int do_mem_mtest (cmd_tbl_t *cmdtp, gd_t *gd,
                        pattern, "");
 
                for (addr=start,val=pattern; addr<end; addr++) {
-                       *addr = val++;
+                       *addr = val;
+                       val  += incr;
                }
 
                printf("Reading...");
 
                for (addr=start,val=pattern; addr<end; addr++) {
-                       if (*addr != val) {
+                       readback = *addr;
+                       if (readback != val) {
                                printf ("\nMem error @ 0x%08X: "
-                                       "found %08lX, expected 0x%08lX\n",
-                                       (uint)addr, *addr, val);
+                                       "found %08lX, expected %08lX\n",
+                                       (uint)addr, readback, val);
                                rcode = 1;
                        }
-                       val++;
+                       val += incr;
                }
 
-               pattern++;
-
+               /*
+                * Flip the pattern each time to make lots of zeros and
+                * then, the next time, lots of ones.  We decrement
+                * the "negative" patterns and increment the "positive"
+                * patterns to preserve this feature.
+                */
+               if(pattern & 0x80000000) {
+                       pattern = -pattern;     /* complement & increment */
+               }
+               else {
+                       pattern = ~pattern;
+               }
+               incr = -incr;
        }
        return rcode;
-
+#endif
 }
 
 
-
-
 /* Modify memory.
  *
  * Syntax:
index c5e66a64f768b9f23f12b6d93c5b0b5a5a75601e..b14c7ddfbbf28d4d47afe92b1a0e76f53cf9d978 100644 (file)
@@ -33,7 +33,7 @@
  * '\0'. New entries are always added at the end. Deleting an entry
  * shifts the remaining entries to the front. Replacing an entry is a
  * combination of deleting the old value and adding the new one.
- * 
+ *
  * The environment is preceeded by a 32 bit CRC over the data part.
  *
  **************************************************************************
@@ -213,7 +213,7 @@ static uchar default_environment[] = {
 #endif
 #ifdef  CONFIG_EXTRA_ENV_SETTINGS
        CONFIG_EXTRA_ENV_SETTINGS
-#endif   
+#endif
        "\0"
 };
 
@@ -825,7 +825,7 @@ envmatch (uchar *s1, int i2)
        return(-1);
 }
 
-#define SAVESTR(type)  "Saving Enviroment to " #type "...\n"
+#define SAVESTR(type)  "Saving Environment to " #type "...\n"
 
 #ifdef CFG_ENV_IS_IN_NVRAM
 #define NVRAM_SAVESTR SAVESTR(NVRAM)
index 7a361607b68ab30b04f2e57ba4e755f6b8c1c62e..00740d331a20bbcc8fda77bcfec240b47fbd8e07 100644 (file)
@@ -57,6 +57,7 @@
 #include <cmd_dcr.h>           /* 4xx DCR register access */
 #include <cmd_doc.h>
 #include <cmd_jffs2.h>
+#include <cmd_fpga.h>
 
 #include <cmd_bsp.h>           /* board special functions */
 
@@ -246,6 +247,7 @@ cmd_tbl_t cmd_tbl[] = {
        CMD_TBL_FLERASE
        CMD_TBL_FDC
        CMD_TBL_FLINFO
+       CMD_TBL_FPGA
        CMD_TBL_GETDCR
        CMD_TBL_GO
        CMD_TBL_HELP
diff --git a/common/fpga.c b/common/fpga.c
new file mode 100644 (file)
index 0000000..9c7f76c
--- /dev/null
@@ -0,0 +1,351 @@
+/*
+ * (C) Copyright 2002
+ * Rich Ireland, Enterasys Networks, rireland@enterasys.com.
+ *
+ * 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
+ *
+ */
+
+/*
+ *  Generic FPGA support
+ */
+#include <common.h>             /* core ppcboot definitions */
+#include <xilinx.h>             /* xilinx specific definitions */
+#include <altera.h>             /* altera specific definitions */
+
+#if defined(CONFIG_FPGA)
+
+#if 0
+#define FPGA_DEBUG              /* define FPGA_DEBUG to get debug messages */
+#endif
+
+/* Local definitions */
+#ifndef CONFIG_MAX_FPGA_DEVICES
+#define CONFIG_MAX_FPGA_DEVICES                5
+#endif
+
+/* Enable/Disable debug console messages */
+#ifdef FPGA_DEBUG
+#define        PRINTF(fmt,args...)     printf (fmt ,##args)
+#else
+#define        PRINTF(fmt,args...)
+#endif
+
+/* Local static data */
+static ulong relocation_offset = 0;
+static int next_desc = FPGA_INVALID_DEVICE;
+static fpga_desc desc_table[CONFIG_MAX_FPGA_DEVICES];
+
+/* Local static functions */
+static const fpga_desc * const fpga_get_desc( int devnum );
+static const fpga_desc * const fpga_validate( int devnum, void *buf,
+                                         size_t bsize, char *fn );
+static int fpga_dev_info( int devnum );
+
+
+/* ------------------------------------------------------------------------- */
+
+/* fpga_no_sup
+ * 'no support' message function
+ */
+static void fpga_no_sup( char *fn, char *msg )
+{
+       if ( fn && msg ) {
+               printf( "%s: No support for %s.  CONFIG_FPGA defined as 0x%x.\n",
+                               fn, msg, CONFIG_FPGA );
+       } else if ( msg ) {
+               printf( "No support for %s. CONFIG_FPGA defined as 0x%x.\n",
+                               msg, CONFIG_FPGA );
+       } else {
+               printf( "No FPGA suport!  CONFIG_FPGA defined as 0x%x.\n",
+                               CONFIG_FPGA );
+       }
+}
+
+
+/* fpga_get_desc
+ *     map a device number to a descriptor
+ */
+static const fpga_desc * const fpga_get_desc( int devnum )
+{
+       fpga_desc *desc = (fpga_desc * )NULL;
+
+       if (( devnum >= 0 ) && (devnum < next_desc )) {
+               desc = &desc_table[devnum];
+               PRINTF( "%s: found fpga descriptor #%d @ 0x%p\n",
+                               __FUNCTION__, devnum, desc );
+       }
+
+       return desc;
+}
+
+
+/* fpga_validate
+ *     generic parameter checking code
+ */
+static const fpga_desc * const fpga_validate( int devnum, void *buf,
+                                         size_t bsize, char *fn )
+{
+       const fpga_desc * const desc = fpga_get_desc( devnum );
+
+       if ( !desc ) {
+               printf( "%s: Invalid device number %d\n", fn, devnum );
+       }
+
+       if ( !buf ) {
+               printf( "%s: Null buffer.\n", fn );
+               return (fpga_desc * const)NULL;
+       }
+       if ( !bsize ) {
+               printf( "%s: Null buffer size.\n", fn );
+               return (fpga_desc * const)NULL;
+       }
+
+       return desc;
+}
+
+
+/* fpga_dev_info
+ *     generic multiplexing code
+ */
+static int fpga_dev_info( int devnum )
+{
+       int ret_val = FPGA_FAIL;           /* assume failure */
+       const fpga_desc * const desc = fpga_get_desc( devnum );
+
+       if ( desc ) {
+               PRINTF( "%s: Device Descriptor @ 0x%p\n",
+                               __FUNCTION__, desc->devdesc );
+
+               switch ( desc->devtype ) {
+               case fpga_xilinx:
+#if CONFIG_FPGA & CFG_FPGA_XILINX
+                       printf( "Xilinx Device\nDescriptor @ 0x%p\n", desc );
+                       ret_val = xilinx_info( desc->devdesc );
+#else
+                       fpga_no_sup( __FUNCTION__, "Xilinx devices" );
+#endif
+                       break;
+               case fpga_altera:
+#if CONFIG_FPGA & CFG_FPGA_ALTERA
+                       printf( "Altera Device\nDescriptor @ 0x%p\n", desc );
+                       ret_val = altera_info( desc->devdesc );
+#else
+                       fpga_no_sup( __FUNCTION__, "Altera devices" );
+#endif
+                       break;
+               default:
+                       printf( "%s: Invalid or unsupported device type %d\n",
+                                       __FUNCTION__, desc->devtype );
+               }
+       } else {
+               printf( "%s: Invalid device number %d\n",
+                       __FUNCTION__, devnum );
+       }
+
+       return ret_val;
+}
+
+
+/* fpga_reloc
+ *     generic multiplexing code
+ */
+int fpga_reloc( fpga_type devtype, void *desc, ulong reloc_off )
+{
+       int ret_val = FPGA_FAIL;
+
+       PRINTF( "%s: Relocating Device of type %d @ 0x%p with offset %lx\n",
+                               __FUNCTION__, devtype, desc, reloc_off );
+
+       switch ( devtype ) {
+       case fpga_xilinx:
+#if CONFIG_FPGA & CFG_FPGA_XILINX
+               ret_val = xilinx_reloc( desc, reloc_off );
+#else
+               fpga_no_sup( __FUNCTION__, "Xilinx devices" );
+#endif
+               break;
+       case fpga_altera:
+#if CONFIG_FPGA & CFG_FPGA_ALTERA
+               ret_val = altera_reloc( desc, reloc_off );
+#else
+               fpga_no_sup( __FUNCTION__, "Altera devices" );
+#endif
+               break;
+       default:
+               printf( "%s: Invalid or unsupported device type %d\n",
+                       __FUNCTION__, devtype );
+       }
+
+       return ret_val;
+}
+
+/* ------------------------------------------------------------------------- */
+/* fgpa_init is usually called from misc_init_r() and MUST be called
+ * before any of the other fpga functions are used.
+ */
+void fpga_init( ulong reloc_off )
+{
+       relocation_offset = reloc_off;
+       next_desc = 0;
+       memset( desc_table, 0, sizeof(desc_table));
+
+       PRINTF( "%s: CONFIG_FPGA = 0x%x\n", __FUNCTION__, CONFIG_FPGA );
+#if 0
+       PRINTF( "%s: CFG_FPGA_XILINX = 0x%x\n", __FUNCTION__, CFG_FPGA_XILINX );
+       PRINTF( "%s: CFG_FPGA_ALTERA = 0x%x\n", __FUNCTION__, CFG_FPGA_ALTERA );
+#endif
+}
+
+/* fpga_count
+ * Basic interface function to get the current number of devices available.
+ */
+const int fpga_count( void )
+{
+       return next_desc;
+}
+
+/* fpga_add
+ *     Attempts to relocate the device/board specific interface code
+ *     to the proper RAM locations and adds the device descriptor to
+ *     the device table.
+ */
+int fpga_add( fpga_type devtype, void *desc )
+{
+       int devnum = FPGA_INVALID_DEVICE;
+
+       if ( next_desc  < 0 ) {
+               printf( "%s: FPGA support not initialized!\n", __FUNCTION__ );
+       } else if (( devtype > fpga_min_type ) && ( devtype < fpga_undefined )) {
+               if ( desc ) {
+                       if ( next_desc < CONFIG_MAX_FPGA_DEVICES ) {
+                               if ( fpga_reloc( devtype, desc, relocation_offset )
+                                 == FPGA_SUCCESS ) {
+                                       devnum = next_desc;
+                                       desc_table[next_desc].devtype = devtype;
+                                       desc_table[next_desc++].devdesc = desc;
+                               } else {
+                                       printf( "%s: Unable to relocate device interface table!\n",
+                                               __FUNCTION__ );
+                               }
+                       } else {
+                               printf( "%s: Exceeded Max FPGA device count\n", __FUNCTION__ );
+                       }
+               } else {
+                       printf( "%s: NULL device descriptor\n", __FUNCTION__ );
+               }
+       } else {
+               printf( "%s: Unsupported FPGA type %d\n", __FUNCTION__, devtype );
+       }
+
+       return devnum;
+}
+
+/*
+ *     Generic multiplexing code
+ */
+int fpga_load( int devnum, void *buf, size_t bsize )
+{
+       int ret_val = FPGA_FAIL;           /* assume failure */
+       const fpga_desc * const desc = fpga_validate( devnum, buf, bsize, __FUNCTION__ );
+
+       if ( desc ) {
+               switch ( desc->devtype ) {
+               case fpga_xilinx:
+#if CONFIG_FPGA & CFG_FPGA_XILINX
+                       ret_val = xilinx_load( desc->devdesc, buf, bsize );
+#else
+                       fpga_no_sup( __FUNCTION__, "Xilinx devices" );
+#endif
+                       break;
+               case fpga_altera:
+#if CONFIG_FPGA & CFG_FPGA_ALTERA
+                       ret_val = altera_load( desc->devdesc, buf, bsize );
+#else
+                       fpga_no_sup( __FUNCTION__, "Altera devices" );
+#endif
+                       break;
+               default:
+                       printf( "%s: Invalid or unsupported device type %d\n",
+                               __FUNCTION__, desc->devtype );
+               }
+       }
+
+       return ret_val;
+}
+
+/* fpga_dump
+ *     generic multiplexing code
+ */
+int fpga_dump( int devnum, void *buf, size_t bsize )
+{
+       int ret_val = FPGA_FAIL;           /* assume failure */
+       const fpga_desc * const desc = fpga_validate( devnum, buf, bsize, __FUNCTION__ );
+
+       if ( desc ) {
+               switch ( desc->devtype ) {
+               case fpga_xilinx:
+#if CONFIG_FPGA & CFG_FPGA_XILINX
+                       ret_val = xilinx_dump( desc->devdesc, buf, bsize );
+#else
+                       fpga_no_sup( __FUNCTION__, "Xilinx devices" );
+#endif
+                       break;
+               case fpga_altera:
+#if CONFIG_FPGA & CFG_FPGA_ALTERA
+                       ret_val = altera_dump( desc->devdesc, buf, bsize );
+#else
+                       fpga_no_sup( __FUNCTION__, "Altera devices" );
+#endif
+                       break;
+               default:
+                       printf( "%s: Invalid or unsupported device type %d\n",
+                               __FUNCTION__, desc->devtype );
+               }
+       }
+
+       return ret_val;
+}
+
+
+/* fpga_info
+ *     front end to fpga_dev_info.  If devnum is invalid, report on all
+ *     available devices.
+ */
+int fpga_info( int devnum )
+{
+       if ( devnum == FPGA_INVALID_DEVICE ) {
+               if ( next_desc > 0 ) {
+                       int dev;
+
+                       for ( dev = 0; dev < next_desc; dev++ ) {
+                               fpga_dev_info( dev );
+                       }
+                       return FPGA_SUCCESS;
+               } else {
+                       printf( "%s: No FPGA devices available.\n", __FUNCTION__ );
+                       return FPGA_FAIL;
+               }
+       }
+       else return fpga_dev_info( devnum );
+}
+
+/* ------------------------------------------------------------------------- */
+
+#endif  /* CONFIG_FPGA */
index 75aa49fd879c95db1996d214b320c152f9657e92..1c6da3ce5c9aed6cc910747a2d49eb034e784211 100644 (file)
@@ -298,7 +298,7 @@ int i2c_probe(uchar addr)
 int  i2c_read(uchar chip, uint addr, int alen, uchar *buffer, int len)
 {
        int shift;
-       PRINTD("i2c_read: chip %02X addr %02X alen %d buffer %p len%d\n",
+       PRINTD("i2c_read: chip %02X addr %02X alen %d buffer %p len %d\n",
                chip, addr, alen, buffer, len);
 
 #ifdef CFG_I2C_EEPROM_ADDR_OVERFLOW
@@ -362,6 +362,9 @@ int  i2c_read(uchar chip, uint addr, int alen, uchar *buffer, int len)
 int  i2c_write(uchar chip, uint addr, int alen, uchar *buffer, int len)
 {
        int shift, failures = 0;
+       
+       PRINTD("i2c_write: chip %02X addr %02X alen %d buffer %p len %d\n",
+               chip, addr, alen, buffer, len);
 
        send_start();
        if(write_byte(chip << 1)) {     /* write cycle */
diff --git a/common/spartan2.c b/common/spartan2.c
new file mode 100644 (file)
index 0000000..949c63c
--- /dev/null
@@ -0,0 +1,470 @@
+/*
+ * (C) Copyright 2002
+ * Rich Ireland, Enterasys Networks, rireland@enterasys.com.
+ *
+ * See file CREDITS for list of people who contributed to this
+ * project.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation; either version 2 of
+ * the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
+ * MA 02111-1307 USA
+ *
+ */
+
+#include <common.h>            /* core ppcboot definitions */
+#include <spartan2.h>           /* Spartan-II device family */
+
+#if (CONFIG_FPGA & (CFG_XILINX | CFG_SPARTAN2))
+
+/* Define FPGA_DEBUG to get debug printf's */
+#ifdef FPGA_DEBUG
+#define        PRINTF(fmt,args...)     printf (fmt ,##args)
+#else
+#define PRINTF(fmt,args...)
+#endif
+
+#undef CFG_FPGA_CHECK_BUSY
+#define CFG_FPGA_PROG_FEEDBACK
+
+/* Note: The assumption is that we cannot possibly run fast enough to
+ * overrun the device (the Slave Parallel mode can free run at 50MHz).
+ * If there is a need to operate slower, define CONFIG_FPGA_DELAY in
+ * the board config file to slow things down.
+ */
+#ifndef CONFIG_FPGA_DELAY
+#define CONFIG_FPGA_DELAY()
+#endif
+
+#ifndef CFG_FPGA_WAIT
+#define CFG_FPGA_WAIT 10
+#endif
+
+static int Spartan2_sp_load( Xilinx_desc *desc, void *buf, size_t bsize );
+static int Spartan2_sp_dump( Xilinx_desc *desc, void *buf, size_t bsize );
+/* static int Spartan2_sp_info( Xilinx_desc *desc ); */
+static int Spartan2_sp_reloc( Xilinx_desc *desc, ulong reloc_offset );
+
+static int Spartan2_ss_load( Xilinx_desc *desc, void *buf, size_t bsize );
+static int Spartan2_ss_dump( Xilinx_desc *desc, void *buf, size_t bsize );
+/* static int Spartan2_ss_info( Xilinx_desc *desc ); */
+static int Spartan2_ss_reloc( Xilinx_desc *desc, ulong reloc_offset );
+
+/* ------------------------------------------------------------------------- */
+/* Spartan-II Generic Implementation */
+int Spartan2_load (Xilinx_desc * desc, void *buf, size_t bsize)
+{
+       int ret_val = FPGA_FAIL;
+
+       switch (desc->iface) {
+       case slave_serial:
+               PRINTF ("%s: Launching Slave Serial Load\n", __FUNCTION__);
+               ret_val = Spartan2_ss_load (desc, buf, bsize);
+               break;
+
+       case slave_parallel:
+               PRINTF ("%s: Launching Slave Parallel Load\n", __FUNCTION__);
+               ret_val = Spartan2_sp_load (desc, buf, bsize);
+               break;
+
+       default:
+               printf ("%s: Unsupported interface type, %d\n",
+                               __FUNCTION__, desc->iface);
+       }
+
+       return ret_val;
+}
+
+int Spartan2_dump (Xilinx_desc * desc, void *buf, size_t bsize)
+{
+       int ret_val = FPGA_FAIL;
+
+       switch (desc->iface) {
+       case slave_serial:
+               PRINTF ("%s: Launching Slave Serial Dump\n", __FUNCTION__);
+               ret_val = Spartan2_ss_dump (desc, buf, bsize);
+               break;
+
+       case slave_parallel:
+               PRINTF ("%s: Launching Slave Parallel Dump\n", __FUNCTION__);
+               ret_val = Spartan2_sp_dump (desc, buf, bsize);
+               break;
+
+       default:
+               printf ("%s: Unsupported interface type, %d\n",
+                               __FUNCTION__, desc->iface);
+       }
+
+       return ret_val;
+}
+
+int Spartan2_info( Xilinx_desc *desc )
+{
+       return FPGA_SUCCESS;
+}
+
+
+int Spartan2_reloc (Xilinx_desc * desc, ulong reloc_offset)
+{
+       int ret_val = FPGA_FAIL;        /* assume a failure */
+
+       if (desc->family != Xilinx_Spartan2) {
+               printf ("%s: Unsupported family type, %d\n",
+                               __FUNCTION__, desc->family);
+               return FPGA_FAIL;
+       } else
+               switch (desc->iface) {
+               case slave_serial:
+                       ret_val = Spartan2_ss_reloc (desc, reloc_offset);
+                       break;
+
+               case slave_parallel:
+                       ret_val = Spartan2_sp_reloc (desc, reloc_offset);
+                       break;
+
+               default:
+                       printf ("%s: Unsupported interface type, %d\n",
+                                       __FUNCTION__, desc->iface);
+               }
+
+       return ret_val;
+}
+
+
+/* ------------------------------------------------------------------------- */
+/* Spartan-II Slave Parallel Generic Implementation */
+
+static int Spartan2_sp_load (Xilinx_desc * desc, void *buf, size_t bsize)
+{
+       int ret_val = FPGA_FAIL;        /* assume the worst */
+       Xilinx_Spartan2_Slave_Parallel_fns *fn = desc->iface_fns;
+
+       PRINTF ("%s: start with interface functions @ 0x%p\n",
+                       __FUNCTION__, fn);
+
+       if (fn) {
+               size_t bytecount = 0;
+               unsigned char *data = (unsigned char *) buf;
+               int cookie = desc->cookie;      /* make a local copy */
+               unsigned long ts;               /* timestamp */
+
+               PRINTF ("%s: Function Table:\n"
+                               "ptr:\t0x%p\n"
+                               "struct: 0x%p\n"
+                               "pre: 0x%p\n"
+                               "pgm:\t0x%p\n"
+                               "init:\t0x%p\n"
+                               "err:\t0x%p\n"
+                               "clk:\t0x%p\n"
+                               "cs:\t0x%p\n"
+                               "wr:\t0x%p\n"
+                               "read data:\t0x%p\n"
+                               "write data:\t0x%p\n"
+                               "busy:\t0x%p\n"
+                               "abort:\t0x%p\n",
+                               "post:\t0x%p\n\n",
+                               __FUNCTION__, &fn, fn, fn->pre, fn->pgm, fn->init, fn->err,
+                               fn->clk, fn->cs, fn->wr, fn->rdata, fn->wdata, fn->busy,
+                               fn->abort, fn->post);
+
+               /*
+                * This code is designed to emulate the "Express Style"
+                * Continuous Data Loading in Slave Parallel Mode for
+                * the Spartan-II Family.
+                */
+#ifdef CFG_FPGA_PROG_FEEDBACK
+               printf ("Loading FPGA Device %d...\n", cookie);
+#endif
+               /*
+                * Run the pre configuration function if there is one.
+                */
+               if (*fn->pre) {
+                       (*fn->pre) (cookie);
+               }
+
+               /* Establish the initial state */
+               (*fn->pgm) (TRUE, TRUE, cookie);        /* Assert the program, commit */
+
+               /* Get ready for the burn */
+               CONFIG_FPGA_DELAY ();
+               (*fn->pgm) (FALSE, TRUE, cookie);       /* Deassert the program, commit */
+
+               ts = get_timer (0);             /* get current time */
+               /* Now wait for INIT and BUSY to go high */
+               do {
+                       CONFIG_FPGA_DELAY ();
+                       if (get_timer (ts) > CFG_FPGA_WAIT) {   /* check the time */
+                               puts ("** Timeout waiting for INIT to clear.\n");
+                               (*fn->abort) (cookie);  /* abort the burn */
+                               return FPGA_FAIL;
+                       }
+               } while ((*fn->init) (cookie) && (*fn->busy) (cookie));
+
+               (*fn->wr) (TRUE, TRUE, cookie); /* Assert write, commit */
+               (*fn->cs) (TRUE, TRUE, cookie); /* Assert chip select, commit */
+               (*fn->clk) (TRUE, TRUE, cookie);        /* Assert the clock pin */
+
+               /* Load the data */
+               while (bytecount < bsize) {
+                       /* XXX - do we check for an Ctrl-C press in here ??? */
+                       /* XXX - Check the error bit? */
+
+                       (*fn->wdata) (data[bytecount++], TRUE, cookie); /* write the data */
+                       CONFIG_FPGA_DELAY ();
+                       (*fn->clk) (FALSE, TRUE, cookie);       /* Deassert the clock pin */
+                       CONFIG_FPGA_DELAY ();
+                       (*fn->clk) (TRUE, TRUE, cookie);        /* Assert the clock pin */
+
+#ifdef CFG_FPGA_CHECK_BUSY
+                       ts = get_timer (0);     /* get current time */
+                       while ((*fn->busy) (cookie)) {
+                               /* XXX - we should have a check in here somewhere to
+                                * make sure we aren't busy forever... */
+
+                               CONFIG_FPGA_DELAY ();
+                               (*fn->clk) (FALSE, TRUE, cookie);       /* Deassert the clock pin */
+                               CONFIG_FPGA_DELAY ();
+                               (*fn->clk) (TRUE, TRUE, cookie);        /* Assert the clock pin */
+
+                               if (get_timer (ts) > CFG_FPGA_WAIT) {   /* check the time */
+                                       puts ("** Timeout waiting for BUSY to clear.\n");
+                                       (*fn->abort) (cookie);  /* abort the burn */
+                                       return FPGA_FAIL;
+                               }
+                       }
+#endif
+
+#ifdef CFG_FPGA_PROG_FEEDBACK
+                       if (bytecount % (bsize / 40) == 0)
+                               putc ('.');             /* let them know we are alive */
+#endif
+               }
+
+               CONFIG_FPGA_DELAY ();
+               (*fn->cs) (FALSE, TRUE, cookie);        /* Deassert the chip select */
+               (*fn->wr) (FALSE, TRUE, cookie);        /* Deassert the write pin */
+
+#ifdef CFG_FPGA_PROG_FEEDBACK
+               putc ('\n');                    /* terminate the dotted line */
+#endif
+
+               /* now check for done signal */
+               ts = get_timer (0);             /* get current time */
+               ret_val = FPGA_SUCCESS;
+               while ((*fn->done) (cookie) == FPGA_FAIL) {
+                       /* XXX - we should have a check in here somewhere to
+                        * make sure we aren't busy forever... */
+
+                       CONFIG_FPGA_DELAY ();
+                       (*fn->clk) (FALSE, TRUE, cookie);       /* Deassert the clock pin */
+                       CONFIG_FPGA_DELAY ();
+                       (*fn->clk) (TRUE, TRUE, cookie);        /* Assert the clock pin */
+
+                       if (get_timer (ts) > CFG_FPGA_WAIT) {   /* check the time */
+                               puts ("** Timeout waiting for DONE to clear.\n");
+                               (*fn->abort) (cookie);  /* abort the burn */
+                               ret_val = FPGA_FAIL;
+                               break;
+                       }
+               }
+
+               if (ret_val == FPGA_SUCCESS) {
+#ifdef CFG_FPGA_PROG_FEEDBACK
+                       puts ("Done.\n");
+#endif
+               }
+               /*
+                * Run the post configuration function if there is one.
+                */
+               if (*fn->post) {
+                       (*fn->post) (cookie);
+               }
+
+               else {
+#ifdef CFG_FPGA_PROG_FEEDBACK
+                       puts ("Fail.\n");
+#endif
+               }
+
+       } else {
+               printf ("%s: NULL Interface function table!\n", __FUNCTION__);
+       }
+
+       return ret_val;
+}
+
+static int Spartan2_sp_dump (Xilinx_desc * desc, void *buf, size_t bsize)
+{
+       int ret_val = FPGA_FAIL;        /* assume the worst */
+       Xilinx_Spartan2_Slave_Parallel_fns *fn = desc->iface_fns;
+
+       if (fn) {
+               unsigned char *data = (unsigned char *) buf;
+               size_t bytecount = 0;
+               int cookie = desc->cookie;      /* make a local copy */
+
+               printf ("Starting Dump of FPGA Device %d...\n", cookie);
+
+               (*fn->cs) (TRUE, TRUE, cookie); /* Assert chip select, commit */
+               (*fn->clk) (TRUE, TRUE, cookie);        /* Assert the clock pin */
+
+               /* dump the data */
+               while (bytecount < bsize) {
+                       /* XXX - do we check for an Ctrl-C press in here ??? */
+
+                       (*fn->clk) (FALSE, TRUE, cookie);       /* Deassert the clock pin */
+                       (*fn->clk) (TRUE, TRUE, cookie);        /* Assert the clock pin */
+                       (*fn->rdata) (&(data[bytecount++]), cookie);    /* read the data */
+#ifdef CFG_FPGA_PROG_FEEDBACK
+                       if (bytecount % (bsize / 40) == 0)
+                               putc ('.');             /* let them know we are alive */
+#endif
+               }
+
+               (*fn->cs) (FALSE, FALSE, cookie);       /* Deassert the chip select */
+               (*fn->clk) (FALSE, TRUE, cookie);       /* Deassert the clock pin */
+               (*fn->clk) (TRUE, TRUE, cookie);        /* Assert the clock pin */
+
+#ifdef CFG_FPGA_PROG_FEEDBACK
+               putc ('\n');                    /* terminate the dotted line */
+#endif
+               puts ("Done.\n");
+
+               /* XXX - checksum the data? */
+       } else {
+               printf ("%s: NULL Interface function table!\n", __FUNCTION__);
+       }
+
+       return ret_val;
+}
+
+
+static int Spartan2_sp_reloc (Xilinx_desc * desc, ulong reloc_offset)
+{
+       int ret_val = FPGA_FAIL;        /* assume the worst */
+       Xilinx_Spartan2_Slave_Parallel_fns *fn_r, *fn =
+                       (Xilinx_Spartan2_Slave_Parallel_fns *) (desc->iface_fns);
+
+       if (fn) {
+               ulong addr;
+
+               /* Get the relocated table address */
+               addr = (ulong) fn + reloc_offset;
+               fn_r = (Xilinx_Spartan2_Slave_Parallel_fns *) addr;
+
+               if (!fn_r->relocated) {
+
+                       if (memcmp (fn_r, fn,
+                                               sizeof (Xilinx_Spartan2_Slave_Parallel_fns))
+                               == 0) {
+                               /* good copy of the table, fix the descriptor pointer */
+                               desc->iface_fns = fn_r;
+                       } else {
+                               PRINTF ("%s: Invalid function table at 0x%p\n",
+                                               __FUNCTION__, fn_r);
+                               return FPGA_FAIL;
+                       }
+
+                       PRINTF ("%s: Relocating descriptor at 0x%p\n", __FUNCTION__,
+                                       desc);
+
+                       addr = (ulong) (fn->pre) + reloc_offset;
+                       fn_r->pre = (Xilinx_pre_fn) addr;
+
+                       addr = (ulong) (fn->pgm) + reloc_offset;
+                       fn_r->pgm = (Xilinx_pgm_fn) addr;
+
+                       addr = (ulong) (fn->init) + reloc_offset;
+                       fn_r->init = (Xilinx_init_fn) addr;
+
+                       addr = (ulong) (fn->done) + reloc_offset;
+                       fn_r->done = (Xilinx_done_fn) addr;
+
+                       addr = (ulong) (fn->clk) + reloc_offset;
+                       fn_r->clk = (Xilinx_clk_fn) addr;
+
+                       addr = (ulong) (fn->err) + reloc_offset;
+                       fn_r->err = (Xilinx_err_fn) addr;
+
+                       addr = (ulong) (fn->cs) + reloc_offset;
+                       fn_r->cs = (Xilinx_cs_fn) addr;
+
+                       addr = (ulong) (fn->wr) + reloc_offset;
+                       fn_r->wr = (Xilinx_wr_fn) addr;
+
+                       addr = (ulong) (fn->rdata) + reloc_offset;
+                       fn_r->rdata = (Xilinx_rdata_fn) addr;
+
+                       addr = (ulong) (fn->wdata) + reloc_offset;
+                       fn_r->wdata = (Xilinx_wdata_fn) addr;
+
+                       addr = (ulong) (fn->busy) + reloc_offset;
+                       fn_r->busy = (Xilinx_busy_fn) addr;
+
+                       addr = (ulong) (fn->abort) + reloc_offset;
+                       fn_r->abort = (Xilinx_abort_fn) addr;
+
+                       addr = (ulong) (fn->post) + reloc_offset;
+                       fn_r->post = (Xilinx_post_fn) addr;
+
+                       fn_r->relocated = TRUE;
+
+               } else {
+                       /* this table has already been moved */
+                       /* XXX - should check to see if the descriptor is correct */
+                       desc->iface_fns = fn_r;
+               }
+
+               ret_val = FPGA_SUCCESS;
+       } else {
+               printf ("%s: NULL Interface function table!\n", __FUNCTION__);
+       }
+
+       return ret_val;
+
+}
+
+/* ------------------------------------------------------------------------- */
+
+static int Spartan2_ss_load (Xilinx_desc * desc, void *buf, size_t bsize)
+{
+       printf ("%s: Slave Serial Loading is still unsupported\n",
+                       __FUNCTION__);
+       return FPGA_FAIL;
+}
+
+static int Spartan2_ss_dump (Xilinx_desc * desc, void *buf, size_t bsize)
+{
+       printf ("%s: Slave Serial Dumping is still unsupported\n",
+                       __FUNCTION__);
+       return FPGA_FAIL;
+}
+
+static int Spartan2_ss_reloc (Xilinx_desc * desc, ulong reloc_offset)
+{
+       int ret_val = FPGA_FAIL;        /* assume the worst */
+       Xilinx_Spartan2_Slave_Serial_fns *fn =
+                       (Xilinx_Spartan2_Slave_Serial_fns *) (desc->iface_fns);
+
+       if (fn) {
+               printf ("%s: Slave Serial Loading is still unsupported\n",
+                               __FUNCTION__);
+       } else {
+               printf ("%s: NULL Interface function table!\n", __FUNCTION__);
+       }
+
+       return ret_val;
+
+}
+
+#endif
diff --git a/common/virtex2.c b/common/virtex2.c
new file mode 100644 (file)
index 0000000..b519be9
--- /dev/null
@@ -0,0 +1,543 @@
+/*
+ * (C) Copyright 2002
+ * Rich Ireland, Enterasys Networks, rireland@enterasys.com.
+ * Keith Outwater, keith_outwater@mvis.com
+ *
+ * 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
+ *
+ */
+
+/*
+ * Configuration support for Xilinx Virtex2 devices.  Based
+ * on spartan2.c (Rich Ireland, rireland@enterasys.com).
+ */
+
+#include <common.h>
+#include <virtex2.h>
+
+#if (CONFIG_FPGA & (CFG_XILINX | CFG_VIRTEX2))
+
+#ifdef FPGA_DEBUG
+#define        PRINTF(fmt,args...)     printf (fmt ,##args)
+#else
+#define PRINTF(fmt,args...)
+#endif
+
+/*
+ * If the SelectMap interface can be overrun by the processor, define
+ * CFG_FPGA_CHECK_BUSY and/or CONFIG_FPGA_DELAY in the board configuration
+ * file and add board-specific support for checking BUSY status. By default,
+ * assume that the SelectMap interface cannot be overrun.
+ */
+#ifndef CFG_FPGA_CHECK_BUSY
+#undef CFG_FPGA_CHECK_BUSY
+#endif
+
+#ifndef CONFIG_FPGA_DELAY
+#define CONFIG_FPGA_DELAY()
+#endif
+
+#ifndef CFG_FPGA_PROG_FEEDBACK
+#define CFG_FPGA_PROG_FEEDBACK
+#endif
+
+/*
+ * Don't allow config cycle to be interrupted
+ */
+#ifndef CFG_FPGA_CHECK_CTRLC
+#undef CFG_FPGA_CHECK_CTRLC
+#endif
+
+/*
+ * Check for errors during configuration by default
+ */
+#ifndef CFG_FPGA_CHECK_ERROR
+#define CFG_FPGA_CHECK_ERROR
+#endif
+
+/*
+ * The default timeout in mS for INIT_B to deassert after PROG_B has
+ * been deasserted. Per the latest Virtex II Handbook (page 347), the
+ * max time from PORG_B deassertion to INIT_B deassertion is 4uS per
+ * data frame for the XC2V8000.  The XC2V8000 has 2860 data frames
+ * which yields 11.44 mS.  So let's make it bigger in order to handle
+ * an XC2V1000, if anyone can ever get ahold of one.
+ */
+#ifndef CFG_FPGA_WAIT_INIT
+#define CFG_FPGA_WAIT_INIT     500     /* time in milliseconds */
+#endif
+
+/*
+ * The default timeout for waiting for BUSY to deassert during configuration.
+ * This is normally not necessary since for most reasonable configuration
+ * clock frequencies (i.e. 66 MHz or less), BUSY monitoring is unnecessary.
+ */
+#ifndef CFG_FPGA_WAIT_BUSY
+#define CFG_FPGA_WAIT_BUSY     5       /* time in milliseconds */
+#endif
+
+/* Default timeout for waiting for FPGA to enter operational mode after
+ * configuration data has been written.
+ */
+#ifndef        CFG_FPGA_WAIT_CONFIG
+#define CFG_FPGA_WAIT_CONFIG   200     /* time in milliseconds */
+#endif
+
+static int Virtex2_ssm_load (Xilinx_desc * desc, void *buf, size_t bsize);
+static int Virtex2_ssm_dump (Xilinx_desc * desc, void *buf, size_t bsize);
+static int Virtex2_ssm_reloc (Xilinx_desc * desc, ulong reloc_offset);
+
+static int Virtex2_ss_load (Xilinx_desc * desc, void *buf, size_t bsize);
+static int Virtex2_ss_dump (Xilinx_desc * desc, void *buf, size_t bsize);
+static int Virtex2_ss_reloc (Xilinx_desc * desc, ulong reloc_offset);
+
+int Virtex2_load (Xilinx_desc * desc, void *buf, size_t bsize)
+{
+       int ret_val = FPGA_FAIL;
+
+       switch (desc->iface) {
+       case slave_serial:
+               PRINTF ("%s: Launching Slave Serial Load\n", __FUNCTION__);
+               ret_val = Virtex2_ss_load (desc, buf, bsize);
+               break;
+
+       case slave_selectmap:
+               PRINTF ("%s: Launching Slave Parallel Load\n", __FUNCTION__);
+               ret_val = Virtex2_ssm_load (desc, buf, bsize);
+               break;
+
+       default:
+               printf ("%s: Unsupported interface type, %d\n",
+                               __FUNCTION__, desc->iface);
+       }
+       return ret_val;
+}
+
+int Virtex2_dump (Xilinx_desc * desc, void *buf, size_t bsize)
+{
+       int ret_val = FPGA_FAIL;
+
+       switch (desc->iface) {
+       case slave_serial:
+               PRINTF ("%s: Launching Slave Serial Dump\n", __FUNCTION__);
+               ret_val = Virtex2_ss_dump (desc, buf, bsize);
+               break;
+
+       case slave_parallel:
+               PRINTF ("%s: Launching Slave Parallel Dump\n", __FUNCTION__);
+               ret_val = Virtex2_ssm_dump (desc, buf, bsize);
+               break;
+
+       default:
+               printf ("%s: Unsupported interface type, %d\n",
+                               __FUNCTION__, desc->iface);
+       }
+       return ret_val;
+}
+
+int Virtex2_info (Xilinx_desc * desc)
+{
+       return FPGA_SUCCESS;
+}
+
+int Virtex2_reloc (Xilinx_desc * desc, ulong reloc_offset)
+{
+       int ret_val = FPGA_FAIL;
+
+       if (desc->family != Xilinx_Virtex2) {
+               printf ("%s: Unsupported family type, %d\n",
+                               __FUNCTION__, desc->family);
+               return FPGA_FAIL;
+       } else
+               switch (desc->iface) {
+               case slave_serial:
+                       ret_val = Virtex2_ss_reloc (desc, reloc_offset);
+                       break;
+
+               case slave_selectmap:
+                       ret_val = Virtex2_ssm_reloc (desc, reloc_offset);
+                       break;
+
+               default:
+                       printf ("%s: Unsupported interface type, %d\n",
+                                       __FUNCTION__, desc->iface);
+               }
+       return ret_val;
+}
+
+/*
+ * Virtex-II Slave SelectMap configuration loader. Configuration via
+ * SelectMap is as follows:
+ * 1. Set the FPGA's PROG_B line low.
+ * 2. Set the FPGA's PROG_B line high.  Wait for INIT_B to go high.
+ * 3. Write data to the SelectMap port.  If INIT_B goes low at any time
+ *    this process, a configuration error (most likely CRC failure) has
+ *    ocurred.  At this point a status word may be read from the
+ *    SelectMap interface to determine the source of the problem (You
+ *    could, for instance, put this in you 'abort' function handler).
+ * 4. After all data has been written, test the state of the FPGA
+ *    INIT_B and DONE lines.  If both are high, configuration has
+ *    succeeded. Congratulations!
+ */
+static int Virtex2_ssm_load (Xilinx_desc * desc, void *buf, size_t bsize)
+{
+       int ret_val = FPGA_FAIL;
+       Xilinx_Virtex2_Slave_SelectMap_fns *fn = desc->iface_fns;
+
+       PRINTF ("%s:%d: Start with interface functions @ 0x%p\n",
+                       __FUNCTION__, __LINE__, fn);
+
+       if (fn) {
+               size_t bytecount = 0;
+               unsigned char *data = (unsigned char *) buf;
+               int cookie = desc->cookie;
+               unsigned long ts;
+
+               /* Gotta split this one up (so the stack won't blow??) */
+               PRINTF ("%s:%d: Function Table:\n"
+                               "  base   0x%p\n"
+                               "  struct 0x%p\n"
+                               "  pre    0x%p\n"
+                               "  prog   0x%p\n"
+                               "  init   0x%p\n"
+                               "  error  0x%p\n",
+                               __FUNCTION__, __LINE__,
+                               &fn, fn, fn->pre, fn->pgm, fn->init, fn->err);
+               PRINTF ("  clock  0x%p\n"
+                               "  cs     0x%p\n"
+                               "  write  0x%p\n"
+                               "  rdata  0x%p\n"
+                               "  wdata  0x%p\n"
+                               "  busy   0x%p\n"
+                               "  abort  0x%p\n"
+                               "  post   0x%p\n\n",
+                               fn->clk, fn->cs, fn->wr, fn->rdata, fn->wdata,
+                               fn->busy, fn->abort, fn->post);
+
+#ifdef CFG_FPGA_PROG_FEEDBACK
+               printf ("Initializing FPGA Device %d...\n", cookie);
+#endif
+               /*
+                * Run the pre configuration function if there is one.
+                */
+               if (*fn->pre) {
+                       (*fn->pre) (cookie);
+               }
+
+               /*
+                * Assert the program line.  The minimum pulse width for
+                * Virtex II devices is 300 nS (Tprogram parameter in datasheet).
+                * There is no maximum value for the pulse width.  Check to make
+                * sure that INIT_B goes low after assertion of PROG_B
+                */
+               (*fn->pgm) (TRUE, TRUE, cookie);
+               udelay (10);
+               ts = get_timer (0);
+               do {
+                       if (get_timer (ts) > CFG_FPGA_WAIT_INIT) {
+                               printf ("%s:%d: ** Timeout after %d mS waiting for INIT"
+                                               " to assert.\n", __FUNCTION__, __LINE__,
+                                               CFG_FPGA_WAIT_INIT);
+                               (*fn->abort) (cookie);
+                               return FPGA_FAIL;
+                       }
+               } while (!(*fn->init) (cookie));
+
+               (*fn->pgm) (FALSE, TRUE, cookie);
+               CONFIG_FPGA_DELAY ();
+               (*fn->clk) (TRUE, TRUE, cookie);
+
+               /*
+                * Start a timer and wait for INIT_B to go high
+                */
+               ts = get_timer (0);
+               do {
+                       CONFIG_FPGA_DELAY ();
+                       if (get_timer (ts) > CFG_FPGA_WAIT_INIT) {
+                               printf ("%s:%d: ** Timeout after %d mS waiting for INIT"
+                                               " to deassert.\n", __FUNCTION__, __LINE__,
+                                               CFG_FPGA_WAIT_INIT);
+                               (*fn->abort) (cookie);
+                               return FPGA_FAIL;
+                       }
+               } while ((*fn->init) (cookie) && (*fn->busy) (cookie));
+
+               (*fn->wr) (TRUE, TRUE, cookie);
+               (*fn->cs) (TRUE, TRUE, cookie);
+
+               udelay (10000);
+
+               /*
+                * Load the data byte by byte
+                */
+               while (bytecount < bsize) {
+#ifdef CFG_FPGA_CHECK_CTRLC
+                       if (ctrlc ()) {
+                               (*fn->abort) (cookie);
+                               return FPGA_FAIL;
+                       }
+#endif
+#ifdef CFG_FPGA_CHECK_ERROR
+                       if ((*fn->init) (cookie)) {
+                               printf ("%s:%d:  ** Error: INIT asserted during"
+                                               " configuration\n", __FUNCTION__, __LINE__);
+                               (*fn->abort) (cookie);
+                               return FPGA_FAIL;
+                       }
+#endif
+                       (*fn->wdata) (data[bytecount++], TRUE, cookie);
+                       CONFIG_FPGA_DELAY ();
+
+                       /*
+                        * Cycle the clock pin
+                        */
+                       (*fn->clk) (FALSE, TRUE, cookie);
+                       CONFIG_FPGA_DELAY ();
+                       (*fn->clk) (TRUE, TRUE, cookie);
+
+#ifdef CFG_FPGA_CHECK_BUSY
+                       ts = get_timer (0);
+                       while ((*fn->busy) (cookie)) {
+                               if (get_timer (ts) > CFG_FPGA_WAIT_BUSY) {
+                                       printf ("%s:%d: ** Timeout after %d mS waiting for"
+                                                       " BUSY to deassert\n",
+                                                       __FUNCTION__, __LINE__, CFG_FPGA_WAIT_BUSY);
+                                       (*fn->abort) (cookie);
+                                       return FPGA_FAIL;
+                               }
+                       }
+#endif
+
+#ifdef CFG_FPGA_PROG_FEEDBACK
+                       if (bytecount % (bsize / 40) == 0)
+                               putc ('.');
+#endif
+               }
+
+               /*
+                * Finished writing the data; deassert FPGA CS_B and WRITE_B signals.
+                */
+               CONFIG_FPGA_DELAY ();
+               (*fn->cs) (FALSE, TRUE, cookie);
+               (*fn->wr) (FALSE, TRUE, cookie);
+
+#ifdef CFG_FPGA_PROG_FEEDBACK
+               putc ('\n');
+#endif
+
+               /*
+                * Check for successful configuration.  FPGA INIT_B and DONE should
+                * both be high upon successful configuration.
+                */
+               ts = get_timer (0);
+               ret_val = FPGA_SUCCESS;
+               while (((*fn->done) (cookie) == FPGA_FAIL) || (*fn->init) (cookie)) {
+                       if (get_timer (ts) > CFG_FPGA_WAIT_CONFIG) {
+                               printf ("%s:%d: ** Timeout after %d mS waiting for DONE to"
+                                               "assert and INIT to deassert\n",
+                                               __FUNCTION__, __LINE__, CFG_FPGA_WAIT_CONFIG);
+                               (*fn->abort) (cookie);
+                               ret_val = FPGA_FAIL;
+                               break;
+                       }
+               }
+
+               if (ret_val == FPGA_SUCCESS) {
+#ifdef CFG_FPGA_PROG_FEEDBACK
+                       printf ("Initialization of FPGA device %d complete\n", cookie);
+#endif
+                       /*
+                        * Run the post configuration function if there is one.
+                        */
+                       if (*fn->post) {
+                               (*fn->post) (cookie);
+                       }
+               } else {
+#ifdef CFG_FPGA_PROG_FEEDBACK
+                       printf ("** Initialization of FPGA device %d FAILED\n",
+                                       cookie);
+#endif
+               }
+       } else {
+               printf ("%s:%d: NULL Interface function table!\n",
+                               __FUNCTION__, __LINE__);
+       }
+       return ret_val;
+}
+
+/*
+ * Read the FPGA configuration data
+ */
+static int Virtex2_ssm_dump (Xilinx_desc * desc, void *buf, size_t bsize)
+{
+       int ret_val = FPGA_FAIL;
+       Xilinx_Virtex2_Slave_SelectMap_fns *fn = desc->iface_fns;
+
+       if (fn) {
+               unsigned char *data = (unsigned char *) buf;
+               size_t bytecount = 0;
+               int cookie = desc->cookie;
+
+               printf ("Starting Dump of FPGA Device %d...\n", cookie);
+
+               (*fn->cs) (TRUE, TRUE, cookie);
+               (*fn->clk) (TRUE, TRUE, cookie);
+
+               while (bytecount < bsize) {
+#ifdef CFG_FPGA_CHECK_CTRLC
+                       if (ctrlc ()) {
+                               (*fn->abort) (cookie);
+                               return FPGA_FAIL;
+                       }
+#endif
+                       /*
+                        * Cycle the clock and read the data
+                        */
+                       (*fn->clk) (FALSE, TRUE, cookie);
+                       (*fn->clk) (TRUE, TRUE, cookie);
+                       (*fn->rdata) (&(data[bytecount++]), cookie);
+#ifdef CFG_FPGA_PROG_FEEDBACK
+                       if (bytecount % (bsize / 40) == 0)
+                               putc ('.');
+#endif
+               }
+
+               /*
+                * Deassert CS_B and cycle the clock to deselect the device.
+                */
+               (*fn->cs) (FALSE, FALSE, cookie);
+               (*fn->clk) (FALSE, TRUE, cookie);
+               (*fn->clk) (TRUE, TRUE, cookie);
+
+#ifdef CFG_FPGA_PROG_FEEDBACK
+               putc ('\n');
+#endif
+               puts ("Done.\n");
+       } else {
+               printf ("%s:%d: NULL Interface function table!\n",
+                               __FUNCTION__, __LINE__);
+       }
+       return ret_val;
+}
+
+/*
+ * Relocate the addresses in the function table from FLASH (or ROM,
+ * or whatever) to RAM.
+ */
+static int Virtex2_ssm_reloc (Xilinx_desc * desc, ulong reloc_offset)
+{
+       ulong addr;
+       int ret_val = FPGA_FAIL;
+       Xilinx_Virtex2_Slave_SelectMap_fns *fn_r, *fn =
+                       (Xilinx_Virtex2_Slave_SelectMap_fns *) (desc->iface_fns);
+
+       if (fn) {
+               /*
+                * Get the relocated table address
+                */
+               addr = (ulong) fn + reloc_offset;
+               fn_r = (Xilinx_Virtex2_Slave_SelectMap_fns *) addr;
+
+               /*
+                * Check to see if the table has already been relocated.  If not, do
+                * a sanity check to make sure there is a faithful copy of the
+                * FLASH based function table in RAM, then adjust the table.
+                */
+               if (!fn_r->relocated) {
+                       if (memcmp
+                               (fn_r, fn, sizeof (Xilinx_Virtex2_Slave_SelectMap_fns))
+                               == 0) {
+                               desc->iface_fns = fn_r;
+                       } else {
+                               PRINTF ("%s:%d: Invalid function table at 0x%p\n",
+                                               __FUNCTION__, __LINE__, fn_r);
+                               return FPGA_FAIL;
+                       }
+
+                       PRINTF ("%s:%d: Relocating descriptor at 0x%p\n",
+                                       __FUNCTION__, __LINE__, desc);
+
+                       addr = (ulong) (fn->pre) + reloc_offset;
+                       fn_r->pre = (Xilinx_pre_fn) addr;
+                       addr = (ulong) (fn->pgm) + reloc_offset;
+                       fn_r->pgm = (Xilinx_pgm_fn) addr;
+                       addr = (ulong) (fn->init) + reloc_offset;
+                       fn_r->init = (Xilinx_init_fn) addr;
+                       addr = (ulong) (fn->done) + reloc_offset;
+                       fn_r->done = (Xilinx_done_fn) addr;
+                       addr = (ulong) (fn->err) + reloc_offset;
+                       fn_r->err = (Xilinx_err_fn) addr;
+                       addr = (ulong) (fn->clk) + reloc_offset;
+                       fn_r->clk = (Xilinx_clk_fn) addr;
+                       addr = (ulong) (fn->cs) + reloc_offset;
+                       fn_r->cs = (Xilinx_cs_fn) addr;
+                       addr = (ulong) (fn->wr) + reloc_offset;
+                       fn_r->wr = (Xilinx_wr_fn) addr;
+                       addr = (ulong) (fn->rdata) + reloc_offset;
+                       fn_r->rdata = (Xilinx_rdata_fn) addr;
+                       addr = (ulong) (fn->wdata) + reloc_offset;
+                       fn_r->wdata = (Xilinx_wdata_fn) addr;
+                       addr = (ulong) (fn->busy) + reloc_offset;
+                       fn_r->busy = (Xilinx_busy_fn) addr;
+                       addr = (ulong) (fn->abort) + reloc_offset;
+                       fn_r->abort = (Xilinx_abort_fn) addr;
+                       addr = (ulong) (fn->post) + reloc_offset;
+                       fn_r->post = (Xilinx_post_fn) addr;
+                       fn_r->relocated = TRUE;
+               } else {
+                       printf ("%s:%d: Function table @0x%p has already been relocated\n", __FUNCTION__, __LINE__, fn_r);
+                       desc->iface_fns = fn_r;
+               }
+               ret_val = FPGA_SUCCESS;
+       } else {
+               printf ("%s: NULL Interface function table!\n", __FUNCTION__);
+       }
+       return ret_val;
+}
+
+static int Virtex2_ss_load (Xilinx_desc * desc, void *buf, size_t bsize)
+{
+       printf ("%s: Slave Serial Loading is unsupported\n", __FUNCTION__);
+       return FPGA_FAIL;
+}
+
+static int Virtex2_ss_dump (Xilinx_desc * desc, void *buf, size_t bsize)
+{
+       printf ("%s: Slave Serial Dumping is unsupported\n", __FUNCTION__);
+       return FPGA_FAIL;
+}
+
+static int Virtex2_ss_reloc (Xilinx_desc * desc, ulong reloc_offset)
+{
+       int ret_val = FPGA_FAIL;
+       Xilinx_Virtex2_Slave_Serial_fns *fn =
+                       (Xilinx_Virtex2_Slave_Serial_fns *) (desc->iface_fns);
+
+       if (fn) {
+               printf ("%s:%d: Slave Serial Loading is unsupported\n",
+                               __FUNCTION__, __LINE__);
+       } else {
+               printf ("%s:%d: NULL Interface function table!\n",
+                               __FUNCTION__, __LINE__);
+       }
+       return ret_val;
+}
+#endif
+
+/* vim: set ts=4 tw=78: */
diff --git a/common/xilinx.c b/common/xilinx.c
new file mode 100644 (file)
index 0000000..cb153e1
--- /dev/null
@@ -0,0 +1,269 @@
+/*
+ * (C) Copyright 2002
+ * Rich Ireland, Enterasys Networks, rireland@enterasys.com.
+ * Keith Outwater, keith_outwater@mvis.com
+ *
+ * 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
+ *
+ */
+
+/*
+ *  Xilinx FPGA support
+ */
+
+#include <common.h>
+#include <virtex2.h>
+#include <spartan2.h>
+
+#if (CONFIG_FPGA & CFG_FPGA_XILINX)
+
+#if 0
+#define FPGA_DEBUG
+#endif
+
+/* Define FPGA_DEBUG to get debug printf's */
+#ifdef FPGA_DEBUG
+#define        PRINTF(fmt,args...)     printf (fmt ,##args)
+#else
+#define PRINTF(fmt,args...)
+#endif
+
+/* Local Static Functions */
+static int xilinx_validate (Xilinx_desc * desc, char *fn);
+
+/* ------------------------------------------------------------------------- */
+
+int xilinx_load (Xilinx_desc * desc, void *buf, size_t bsize)
+{
+       int ret_val = FPGA_FAIL;        /* assume a failure */
+
+       if (!xilinx_validate (desc, __FUNCTION__)) {
+               printf ("%s: Invalid device descriptor\n", __FUNCTION__);
+       } else
+               switch (desc->family) {
+               case Xilinx_Spartan2:
+#if (CONFIG_FPGA & CFG_SPARTAN2)
+                       PRINTF ("%s: Launching the Spartan-II Loader...\n",
+                                       __FUNCTION__);
+                       ret_val = Spartan2_load (desc, buf, bsize);
+#else
+                       printf ("%s: No support for Spartan-II devices.\n",
+                                       __FUNCTION__);
+#endif
+                       break;
+               case Xilinx_Virtex2:
+#if (CONFIG_FPGA & CFG_VIRTEX2)
+                       PRINTF ("%s: Launching the Virtex-II Loader...\n",
+                                       __FUNCTION__);
+                       ret_val = Virtex2_load (desc, buf, bsize);
+#else
+                       printf ("%s: No support for Virtex-II devices.\n",
+                                       __FUNCTION__);
+#endif
+                       break;
+
+               default:
+                       printf ("%s: Unsupported family type, %d\n",
+                                       __FUNCTION__, desc->family);
+               }
+
+       return ret_val;
+}
+
+int xilinx_dump (Xilinx_desc * desc, void *buf, size_t bsize)
+{
+       int ret_val = FPGA_FAIL;        /* assume a failure */
+
+       if (!xilinx_validate (desc, __FUNCTION__)) {
+               printf ("%s: Invalid device descriptor\n", __FUNCTION__);
+       } else
+               switch (desc->family) {
+               case Xilinx_Spartan2:
+#if (CONFIG_FPGA & CFG_SPARTAN2)
+                       PRINTF ("%s: Launching the Spartan-II Reader...\n",
+                                       __FUNCTION__);
+                       ret_val = Spartan2_dump (desc, buf, bsize);
+#else
+                       printf ("%s: No support for Spartan-II devices.\n",
+                                       __FUNCTION__);
+#endif
+                       break;
+               case Xilinx_Virtex2:
+#if (CONFIG_FPGA & CFG_VIRTEX2)
+                       PRINTF ("%s: Launching the Virtex-II Reader...\n",
+                                       __FUNCTION__);
+                       ret_val = Virtex2_dump (desc, buf, bsize);
+#else
+                       printf ("%s: No support for Virtex-II devices.\n",
+                                       __FUNCTION__);
+#endif
+                       break;
+
+               default:
+                       printf ("%s: Unsupported family type, %d\n",
+                                       __FUNCTION__, desc->family);
+               }
+
+       return ret_val;
+}
+
+int xilinx_info (Xilinx_desc * desc)
+{
+       int ret_val = FPGA_FAIL;
+
+       if (xilinx_validate (desc, __FUNCTION__)) {
+               printf ("Family:        \t");
+               switch (desc->family) {
+               case Xilinx_Spartan2:
+                       printf ("Spartan-II\n");
+                       break;
+               case Xilinx_Virtex2:
+                       printf ("Virtex-II\n");
+                       break;
+                       /* Add new family types here */
+               default:
+                       printf ("Unknown family type, %d\n", desc->family);
+               }
+
+               printf ("Interface type:\t");
+               switch (desc->iface) {
+               case slave_serial:
+                       printf ("Slave Serial\n");
+                       break;
+               case master_serial:     /* Not used */
+                       printf ("Master Serial\n");
+                       break;
+               case slave_parallel:
+                       printf ("Slave Parallel\n");
+                       break;
+               case jtag_mode:         /* Not used */
+                       printf ("JTAG Mode\n");
+                       break;
+               case slave_selectmap:
+                       printf ("Slave SelectMap Mode\n");
+                       break;
+               case master_selectmap:
+                       printf ("Master SelectMap Mode\n");
+                       break;
+                       /* Add new interface types here */
+               default:
+                       printf ("Unsupported interface type, %d\n", desc->iface);
+               }
+
+               printf ("Device Size:   \t%d bytes\n"
+                               "Cookie:        \t0x%x (%d)\n",
+                               desc->size, desc->cookie, desc->cookie);
+
+               if (desc->iface_fns) {
+                       printf ("Device Function Table @ 0x%p\n", desc->iface_fns);
+                       switch (desc->family) {
+                       case Xilinx_Spartan2:
+#if (CONFIG_FPGA & CFG_SPARTAN2)
+                               Spartan2_info (desc);
+#else
+                               /* just in case */
+                               printf ("%s: No support for Spartan-II devices.\n",
+                                               __FUNCTION__);
+#endif
+                               break;
+                       case Xilinx_Virtex2:
+#if (CONFIG_FPGA & CFG_VIRTEX2)
+                               Virtex2_info (desc);
+#else
+                               /* just in case */
+                               printf ("%s: No support for Virtex-II devices.\n",
+                                               __FUNCTION__);
+#endif
+                               break;
+                               /* Add new family types here */
+                       default:
+                               /* we don't need a message here - we give one up above */
+                       }
+               } else
+                       printf ("No Device Function Table.\n");
+
+               ret_val = FPGA_SUCCESS;
+       } else {
+               printf ("%s: Invalid device descriptor\n", __FUNCTION__);
+       }
+
+       return ret_val;
+}
+
+int xilinx_reloc (Xilinx_desc * desc, ulong reloc_offset)
+{
+       int ret_val = FPGA_FAIL;        /* assume a failure */
+
+       if (!xilinx_validate (desc, __FUNCTION__)) {
+               printf ("%s: Invalid device descriptor\n", __FUNCTION__);
+       } else
+               switch (desc->family) {
+               case Xilinx_Spartan2:
+#if (CONFIG_FPGA & CFG_SPARTAN2)
+                       ret_val = Spartan2_reloc (desc, reloc_offset);
+#else
+                       printf ("%s: No support for Spartan-II devices.\n",
+                                       __FUNCTION__);
+#endif
+                       break;
+               case Xilinx_Virtex2:
+#if (CONFIG_FPGA & CFG_VIRTEX2)
+                       ret_val = Virtex2_reloc (desc, reloc_offset);
+#else
+                       printf ("%s: No support for Virtex-II devices.\n",
+                                       __FUNCTION__);
+#endif
+                       break;
+                       /* Add new family types here */
+               default:
+                       printf ("%s: Unsupported family type, %d\n",
+                                       __FUNCTION__, desc->family);
+               }
+
+       return ret_val;
+}
+
+
+/* ------------------------------------------------------------------------- */
+
+static int xilinx_validate (Xilinx_desc * desc, char *fn)
+{
+       int ret_val = FALSE;
+
+       if (desc) {
+               if ((desc->family > min_xilinx_type) &&
+                       (desc->family < max_xilinx_type)) {
+                       if ((desc->iface > min_xilinx_iface_type) &&
+                               (desc->iface < max_xilinx_iface_type)) {
+                               if (desc->size) {
+                                       ret_val = TRUE;
+                               } else
+                                       printf ("%s: NULL part size\n", fn);
+                       } else
+                               printf ("%s: Invalid Interface type, %d\n",
+                                               fn, desc->iface);
+               } else
+                       printf ("%s: Invalid family type, %d\n", fn, desc->family);
+       } else
+               printf ("%s: NULL descriptor!\n", fn);
+
+       return ret_val;
+}
+
+#endif                                                 /* CONFIG_FPGA & CFG_FPGA_XILINX */
index c69cfd8ff317b9745ae7653009da91476f3e7185..d857834902c22cbf6b46e1ca3ccd054747e65223 100644 (file)
 /* read co-processor 15, register #1 (control register) */
 static unsigned long read_p15_c1(void)
 {
-    unsigned long value;
-
-    __asm__ __volatile__(
-       "mrc     p15, 0, %0, c1, c0, 0   @ read control reg\n"
-       : "=r" (value)
-       :
-       : "memory");
-    //printf("p15/c1 is = %08lx\n", value);
-    return value;
+       unsigned long value;
+
+       __asm__ __volatile__(
+               "mrc     p15, 0, %0, c1, c0, 0   @ read control reg\n"
+               : "=r" (value)
+               :
+               : "memory");
+       /* printf("p15/c1 is = %08lx\n", value); */
+       return value;
 }
 
 /* write to co-processor 15, register #1 (control register) */
 static void write_p15_c1(unsigned long value)
 {
-    //printf("write %08lx to p15/c1\n", value);
-    __asm__ __volatile__(
-        "mcr     p15, 0, %0, c1, c0, 0   @ write it back\n"
-       :
-       : "r" (value)
-       : "memory");
-
-    read_p15_c1();
+       /* printf("write %08lx to p15/c1\n", value); */
+       __asm__ __volatile__(
+               "mcr     p15, 0, %0, c1, c0, 0   @ write it back\n"
+               :
+               : "r" (value)
+               : "memory");
+
+       read_p15_c1();
 }
 
-static void cp_delay(void)
+static void cp_delay (void)
 {
-    volatile int i;
+       volatile int i;
 
-    /* copro seems to need some delay between reading and writing */
-    for (i=0; i<100; i++);
+       /* copro seems to need some delay between reading and writing */
+       for (i = 0; i < 100; i++);
 }
 
 /* See also ARM Ref. Man. */
@@ -79,96 +79,102 @@ static void cp_delay(void)
 #define C1_ROM_PROT    (1<<9)  /* ROM protection */
 #define C1_HIGH_VECTORS        (1<<13) /* location of vectors: low/high addresses */
 
-void cpu_init(bd_t *bd)
+int cpu_init (gd_t * gd)
 {
-    /*
-     * setup up stack if necessary
-     */
+       /*
+        * setup up stack if necessary
+        */
 #ifdef CONFIG_USE_IRQ
-    IRQ_STACK_START = _armboot_end +
-                       CONFIG_STACKSIZE + CONFIG_STACKSIZE_IRQ - 4;
-    FIQ_STACK_START = IRQ_STACK_START + CONFIG_STACKSIZE_FIQ;
-    _armboot_real_end = FIQ_STACK_START + 4;
+       IRQ_STACK_START   = _armboot_end + \
+                               CONFIG_STACKSIZE + \
+                               CONFIG_STACKSIZE_IRQ - 4;
+       FIQ_STACK_START = IRQ_STACK_START + CONFIG_STACKSIZE_FIQ;
+       _armboot_real_end = FIQ_STACK_START + 4;
 #else
-    _armboot_real_end = _armboot_end + CONFIG_STACKSIZE;
+       _armboot_real_end = _armboot_end + CONFIG_STACKSIZE;
 #endif
+       return (0);
 }
 
-void cleanup_before_linux(bd_t *bd)
+int cleanup_before_linux (gd_t *dummy)
 {
-    /*
-     * this function is called just before we call linux
-     * it prepares the processor for linux
-     *
-     * we turn off caches etc ...
-     * and we set the CPU-speed to 73 MHz - see start.S for details
-     */
+       /*
+        * this function is called just before we call linux
+        * it prepares the processor for linux
+        *
+        * we turn off caches etc ...
+        * and we set the CPU-speed to 73 MHz - see start.S for details
+        */
 
-    unsigned long i;
+       unsigned long i;
 
-    disable_interrupts();
+       disable_interrupts ();
 
-    /* turn off I-cache */
-    asm ("mrc p15, 0, %0, c1, c0, 0": "=r" (i));
-    i &= ~0x1000;
-    asm ("mcr p15, 0, %0, c1, c0, 0": : "r" (i));
+       /* turn off I-cache */
+       asm ("mrc p15, 0, %0, c1, c0, 0":"=r" (i));
+       i &= ~0x1000;
+       asm ("mcr p15, 0, %0, c1, c0, 0": :"r" (i));
 
-    /* flush I-cache */
-    asm ("mcr p15, 0, %0, c7, c5, 0": : "r" (i));
+       /* flush I-cache */
+       asm ("mcr p15, 0, %0, c7, c5, 0": :"r" (i));
 
 #ifdef CONFIG_ARM7_REVD
-    /* go to high speed */
-    IO_SYSCON3 = (IO_SYSCON3 & ~CLKCTL) | CLKCTL_73;
+       /* go to high speed */
+       IO_SYSCON3 = (IO_SYSCON3 & ~CLKCTL) | CLKCTL_73;
 #endif
+       return 0;
 }
 
-void do_reset (cmd_tbl_t *cmdtp, bd_t *bd, int flag, int argc, char *argv[])
+int do_reset (cmd_tbl_t *cmdtp, gd_t *gd, int flag, int argc, char *argv[])
 {
-    extern void reset_cpu(ulong addr);
+       extern void reset_cpu (ulong addr);
 
-    disable_interrupts();
-    reset_cpu(0);
-    /*NOTREACHED*/
-}
+       disable_interrupts ();
+       reset_cpu (0);
+ /*NOTREACHED*/}
 
-void icache_enable(void)
+void icache_enable (void)
 {
-    ulong reg;
-    reg = read_p15_c1();
-    cp_delay();
-    write_p15_c1(reg | C1_IDC);
+       ulong reg;
+
+       reg = read_p15_c1 ();
+       cp_delay ();
+       write_p15_c1 (reg | C1_IDC);
 }
 
-void icache_disable(void)
+void icache_disable (void)
 {
-    ulong reg;
-    reg = read_p15_c1();
-    cp_delay();
-    write_p15_c1(reg & ~C1_IDC);
+       ulong reg;
+
+       reg = read_p15_c1 ();
+       cp_delay ();
+       write_p15_c1 (reg & ~C1_IDC);
 }
 
-int icache_status(void)
+int icache_status (void)
 {
-    return (read_p15_c1() & C1_IDC) != 0;
+       return (read_p15_c1 () & C1_IDC) != 0;
 }
 
-void dcache_enable(void)
+void dcache_enable (void)
 {
-    ulong reg;
-    reg = read_p15_c1();
-    cp_delay();
-    write_p15_c1(reg | C1_IDC);
+       ulong reg;
+
+       reg = read_p15_c1 ();
+       cp_delay ();
+       write_p15_c1 (reg | C1_IDC);
 }
 
-void dcache_disable(void)
+void dcache_disable (void)
 {
-    ulong reg;
-    reg = read_p15_c1();
-    cp_delay();
-    write_p15_c1(reg & ~C1_IDC);
+       ulong reg;
+
+       reg = read_p15_c1 ();
+       cp_delay ();
+       write_p15_c1 (reg & ~C1_IDC);
 }
 
-int dcache_status(void)
+int dcache_status (void)
 {
-    return (read_p15_c1() & C1_IDC) != 0;
+       return (read_p15_c1 () & C1_IDC) != 0;
 }
index b2f5d69b237f9d87921fa66b92e6de5e32adfad8..d9944eb049024d14d4a3c44646e2aacf4047a4b2 100644 (file)
 /* it makes no sense to use the caches if the MMU also isn't used */
 #ifdef USE_920T_MMU
 /* read co-processor 15, register #1 (control register) */
-static unsigned long read_p15_c1(void)
+static unsigned long read_p15_c1 (void)
 {
-    unsigned long value;
+       unsigned long value;
+
+       __asm__ __volatile__(
+               "mrc     p15, 0, %0, c1, c0, 0   @ read control reg\n"
+               : "=r" (value)
+               :
+               : "memory");
 
-    __asm__ __volatile__(
-       "mrc     p15, 0, %0, c1, c0, 0   @ read control reg\n"
-       : "=r" (value)
-       :
-       : "memory");
 #ifdef MMU_DEBUG
-    printf("p15/c1 is = %08lx\n", value);
+       printf ("p15/c1 is = %08lx\n", value);
 #endif
-    return value;
+       return value;
 }
 
 /* write to co-processor 15, register #1 (control register) */
-static void write_p15_c1(unsigned long value)
+static void write_p15_c1 (unsigned long value)
 {
 #ifdef MMU_DEBUG
-    printf("write %08lx to p15/c1\n", value);
+       printf ("write %08lx to p15/c1\n", value);
 #endif
-    __asm__ __volatile__(
-        "mcr     p15, 0, %0, c1, c0, 0   @ write it back\n"
-       :
-       : "r" (value)
-       : "memory");
-    read_p15_c1();
+       __asm__ __volatile__(
+               "mcr     p15, 0, %0, c1, c0, 0   @ write it back\n"
+               :
+               : "r" (value)
+               : "memory");
+
+       read_p15_c1 ();
 }
 
-static void cp_delay(void)
+static void cp_delay (void)
 {
-    volatile int i;
+       volatile int i;
 
-    /* copro seems to need some delay between reading and writing */
-    for (i=0; i<100; i++);
+       /* copro seems to need some delay between reading and writing */
+       for (i = 0; i < 100; i++);
 }
 
 /* See also ARM Ref. Man. */
-#define C1_MMU         (1<<0)  /* mmu off/on */
-#define C1_ALIGN       (1<<1)  /* alignment faults off/on */
-#define C1_DC          (1<<2)  /* dcache off/on */
+#define C1_MMU         (1<<0)          /* mmu off/on */
+#define C1_ALIGN       (1<<1)          /* alignment faults off/on */
+#define C1_DC          (1<<2)          /* dcache off/on */
 #define C1_BIG_ENDIAN  (1<<7)  /* big endian off/on */
-#define C1_SYS_PROT    (1<<8)  /* system protection */
-#define C1_ROM_PROT    (1<<9)  /* ROM protection */
-#define C1_IC          (1<<12) /* icache off/on */
+#define C1_SYS_PROT    (1<<8)          /* system protection */
+#define C1_ROM_PROT    (1<<9)          /* ROM protection */
+#define C1_IC          (1<<12)         /* icache off/on */
 #define C1_HIGH_VECTORS        (1<<13) /* location of vectors: low/high addresses */
-#define RESERVED_1     (0xf << 3) /* must be 111b for R/W */
-#endif
+#define RESERVED_1     (0xf << 3)      /* must be 111b for R/W */
+#endif /* USE_920T_MMU */
 
-void cpu_init(bd_t *bd)
+int cpu_init (gd_t *gd)
 {
-    /*
-     * setup up stack if necessary
-     */
+       /*
+        * setup up stack if necessary
+        */
 #ifdef CONFIG_USE_IRQ
-    IRQ_STACK_START = _armboot_end +
-                       CONFIG_STACKSIZE + CONFIG_STACKSIZE_IRQ - 4;
-    FIQ_STACK_START = IRQ_STACK_START + CONFIG_STACKSIZE_FIQ;
-    _armboot_real_end = FIQ_STACK_START + 4;
+       IRQ_STACK_START = _armboot_end +
+                       CONFIG_STACKSIZE + CONFIG_STACKSIZE_IRQ - 4;
+       FIQ_STACK_START = IRQ_STACK_START + CONFIG_STACKSIZE_FIQ;
+       _armboot_real_end = FIQ_STACK_START + 4;
 #else
-    _armboot_real_end = _armboot_end + CONFIG_STACKSIZE;
+       _armboot_real_end = _armboot_end + CONFIG_STACKSIZE;
 #endif
+       return (0);
 }
 
-void cleanup_before_linux(bd_t *bd)
+int cleanup_before_linux (gd_t *dummy)
 {
-    /*
-     * this function is called just before we call linux
-     * it prepares the processor for linux
-     *
-     * we turn off caches etc ...
-     */
+       /*
+        * this function is called just before we call linux
+        * it prepares the processor for linux
+        *
+        * we turn off caches etc ...
+        */
 
 #ifdef USE_920T_MMU
-    unsigned long i;
+       unsigned long i;
 #endif
 
-    disable_interrupts();
+       disable_interrupts ();
 
 #ifdef USE_920T_MMU
-    /* turn off I/D-cache */
-    asm ("mrc p15, 0, %0, c1, c0, 0": "=r" (i));
-    i &= ~(C1_DC|C1_IC);
-    asm ("mcr p15, 0, %0, c1, c0, 0": : "r" (i));
-
-    /* flush I/D-cache */
-    i = 0;
-    asm ("mcr p15, 0, %0, c7, c7, 0": : "r" (i));
+       /* turn off I/D-cache */
+       asm ("mrc p15, 0, %0, c1, c0, 0":"=r" (i));
+       i &= ~(C1_DC | C1_IC);
+       asm ("mcr p15, 0, %0, c1, c0, 0": :"r" (i));
+
+       /* flush I/D-cache */
+       i = 0;
+       asm ("mcr p15, 0, %0, c7, c7, 0": :"r" (i));
 #endif
-
+       return (0);
 }
 
-void do_reset (cmd_tbl_t *cmdtp, bd_t *bd, int flag, int argc, char *argv[])
+int do_reset (cmd_tbl_t *cmdtp, gd_t *gd, int flag, int argc, char *argv[])
 {
-    extern void reset_cpu(ulong addr);
+       extern void reset_cpu (ulong addr);
 
-    disable_interrupts();
-    reset_cpu(0);
-    /*NOTREACHED*/
-}
+       disable_interrupts ();
+       reset_cpu (0);
+ /*NOTREACHED*/}
 
 #ifdef USE_920T_MMU
-void icache_enable(void)
+void icache_enable (void)
 {
-    ulong reg;
-    reg = read_p15_c1();
-    cp_delay();
-    write_p15_c1(reg | C1_IC);
+       ulong reg;
+
+       reg = read_p15_c1 ();
+       cp_delay ();
+       write_p15_c1 (reg | C1_IC);
 }
 
-void icache_disable(void)
+void icache_disable (void)
 {
-    ulong reg;
-    reg = read_p15_c1();
-    cp_delay();
-    write_p15_c1(reg & ~C1_IC);
+       ulong reg;
+
+       reg = read_p15_c1 ();
+       cp_delay ();
+       write_p15_c1 (reg & ~C1_IC);
 }
 
-int icache_status(void)
+int icache_status (void)
 {
-    return (read_p15_c1() & C1_IC) != 0;
+       return (read_p15_c1 () & C1_IC) != 0;
 }
 
-void dcache_enable(void)
+void dcache_enable (void)
 {
-    ulong reg;
-    reg = read_p15_c1();
-    cp_delay();
-    write_p15_c1(reg | C1_DC);
+       ulong reg;
+
+       reg = read_p15_c1 ();
+       cp_delay ();
+       write_p15_c1 (reg | C1_DC);
 }
 
-void dcache_disable(void)
+void dcache_disable (void)
 {
-    ulong reg;
-    reg = read_p15_c1();
-    cp_delay();
-    reg &= ~C1_DC;
-    write_p15_c1(reg);
+       ulong reg;
+
+       reg = read_p15_c1 ();
+       cp_delay ();
+       reg &= ~C1_DC;
+       write_p15_c1 (reg);
 }
 
-int dcache_status(void)
+int dcache_status (void)
 {
-    return (read_p15_c1() & C1_DC) != 0;
+       return (read_p15_c1 () & C1_DC) != 0;
 }
 #endif
index c21682d598d05768e8126ef6d1b281ef02085231..d8aaeec55d5b399f527ad7e4b2855e3f9205d00a 100644 (file)
@@ -65,6 +65,13 @@ led_dev_t led_dev[] = {
        0,
     },
 #endif
+#if defined(STATUS_LED_BIT3)
+    {  STATUS_LED_BIT3,
+       STATUS_LED_STATE3,
+       STATUS_LED_PERIOD3,
+       0,
+    },
+#endif
 };
 
 #define MAX_LED_DEV    (sizeof(led_dev)/sizeof(led_dev_t))
index 34850c255ee54c2e5dcf6b9b6ead0ecbb3e32750..2606862a37ad927eeb269e1f9b475f1dd8e32dee 100644 (file)
 #include <common.h>
 #include <command.h>
 
-void cpu_init(bd_t *bd)
+int cpu_init (gd_t *gd)
 {
-    /*
-     * setup up stack if necessary
-     */
+       /*
+        * setup up stack if necessary
+        */
 #ifdef CONFIG_USE_IRQ
-    IRQ_STACK_START = _armboot_end +
-                       CONFIG_STACKSIZE + CONFIG_STACKSIZE_IRQ - 4;
-    FIQ_STACK_START = IRQ_STACK_START + CONFIG_STACKSIZE_FIQ;
-    _armboot_real_end = FIQ_STACK_START + 4;
+       IRQ_STACK_START = _armboot_end +
+                       CONFIG_STACKSIZE + CONFIG_STACKSIZE_IRQ - 4;
+       FIQ_STACK_START = IRQ_STACK_START + CONFIG_STACKSIZE_FIQ;
+       _armboot_real_end = FIQ_STACK_START + 4;
 #else
-    _armboot_real_end = _armboot_end + CONFIG_STACKSIZE;
+       _armboot_real_end = _armboot_end + CONFIG_STACKSIZE;
 #endif
+       return (0);
 }
 
-void cleanup_before_linux(bd_t *bd)
+int cleanup_before_linux (gd_t * gd)
 {
-    /*
-     * this function is called just before we call linux
-     * it prepares the processor for linux
-     *
-     * just disable everything that can disturb booting linux
-     */
+       /*
+        * this function is called just before we call linux
+        * it prepares the processor for linux
+        *
+        * just disable everything that can disturb booting linux
+        */
 
-    unsigned long i;
+       unsigned long i;
 
-    disable_interrupts();
+       disable_interrupts ();
 
-    /* turn off I-cache */
-    asm ("mrc p15, 0, %0, c1, c0, 0": "=r" (i));
-    i &= ~0x1000;
-    asm ("mcr p15, 0, %0, c1, c0, 0": : "r" (i));
+       /* turn off I-cache */
+       asm ("mrc p15, 0, %0, c1, c0, 0":"=r" (i));
+       i &= ~0x1000;
+       asm ("mcr p15, 0, %0, c1, c0, 0": :"r" (i));
 
-    /* flush I-cache */
-    asm ("mcr p15, 0, %0, c7, c5, 0": : "r" (i));
+       /* flush I-cache */
+       asm ("mcr p15, 0, %0, c7, c5, 0": :"r" (i));
+
+       return (0);
 }
 
-void do_reset (cmd_tbl_t *cmdtp, bd_t *bd, int flag, int argc, char *argv[])
+int do_reset (cmd_tbl_t *cmdtp, gd_t *gd, int flag, int argc, char *argv[])
 {
-    extern void reset_cpu(ulong addr);
+       extern void reset_cpu (ulong addr);
+
+       printf ("resetting ...\n");
 
-    printf("reseting ...\n");
+       udelay (50000);                         /* wait 50 ms */
+       disable_interrupts ();
+       reset_cpu (0);
 
-    udelay(50000); /* wait 50 ms */
-    disable_interrupts();
-    reset_cpu(0);
-    /*NOTREACHED*/
+       /*NOTREACHED*/
+       return (0);
 }
 
 /* taken from blob */
-void icache_enable(void)
+void icache_enable (void)
 {
-    register u32 i;
+       register u32 i;
 
-    /* read control register */
-    asm ("mrc p15, 0, %0, c1, c0, 0": "=r" (i));
+       /* read control register */
+       asm ("mrc p15, 0, %0, c1, c0, 0":"=r" (i));
 
-    /* set i-cache */
-    i |= 0x1000;
+       /* set i-cache */
+       i |= 0x1000;
 
-    /* write back to control register */
-    asm ("mcr p15, 0, %0, c1, c0, 0": : "r" (i));
+       /* write back to control register */
+       asm ("mcr p15, 0, %0, c1, c0, 0": :"r" (i));
 }
 
-void icache_disable(void)
+void icache_disable (void)
 {
-    register u32 i;
+       register u32 i;
 
-    /* read control register */
-    asm ("mrc p15, 0, %0, c1, c0, 0": "=r" (i));
+       /* read control register */
+       asm ("mrc p15, 0, %0, c1, c0, 0":"=r" (i));
 
-    /* clear i-cache */
-    i &= ~0x1000;
+       /* clear i-cache */
+       i &= ~0x1000;
 
-    /* write back to control register */
-    asm ("mcr p15, 0, %0, c1, c0, 0": : "r" (i));
+       /* write back to control register */
+       asm ("mcr p15, 0, %0, c1, c0, 0": :"r" (i));
 
-    /* flush i-cache */
-    asm ("mcr p15, 0, %0, c7, c5, 0": : "r" (i));
+       /* flush i-cache */
+       asm ("mcr p15, 0, %0, c7, c5, 0": :"r" (i));
 }
 
-int icache_status(void)
+int icache_status (void)
 {
-    register u32 i;
+       register u32 i;
 
-    /* read control register */
-    asm ("mrc p15, 0, %0, c1, c0, 0": "=r" (i));
+       /* read control register */
+       asm ("mrc p15, 0, %0, c1, c0, 0":"=r" (i));
 
-    /* return bit */
-    return (i & 0x1000);
+       /* return bit */
+       return (i & 0x1000);
 }
 
 /* we will never enable dcache, because we have to setup MMU first */
-void dcache_enable(void)
+void dcache_enable (void)
 {
-    return;
+       return;
 }
 
-void dcache_disable(void)
+void dcache_disable (void)
 {
-    return;
+       return;
 }
 
-int dcache_status(void)
+int dcache_status (void)
 {
-    return 0; /* always off */
+       return 0;                                       /* always off */
 }
index 34850c255ee54c2e5dcf6b9b6ead0ecbb3e32750..11c9e003d5a100831f5fda8617ee665d30282ad4 100644 (file)
 #include <common.h>
 #include <command.h>
 
-void cpu_init(bd_t *bd)
+int cpu_init (gd_t *gd)
 {
-    /*
-     * setup up stack if necessary
-     */
+       /*
+        * setup up stack if necessary
+        */
 #ifdef CONFIG_USE_IRQ
-    IRQ_STACK_START = _armboot_end +
-                       CONFIG_STACKSIZE + CONFIG_STACKSIZE_IRQ - 4;
-    FIQ_STACK_START = IRQ_STACK_START + CONFIG_STACKSIZE_FIQ;
-    _armboot_real_end = FIQ_STACK_START + 4;
+       IRQ_STACK_START = _armboot_end +
+                       CONFIG_STACKSIZE + CONFIG_STACKSIZE_IRQ - 4;
+       FIQ_STACK_START = IRQ_STACK_START + CONFIG_STACKSIZE_FIQ;
+       _armboot_real_end = FIQ_STACK_START + 4;
 #else
-    _armboot_real_end = _armboot_end + CONFIG_STACKSIZE;
+       _armboot_real_end = _armboot_end + CONFIG_STACKSIZE;
 #endif
+       return (0);
 }
 
-void cleanup_before_linux(bd_t *bd)
+int cleanup_before_linux (gd_t *dummy)
 {
-    /*
-     * this function is called just before we call linux
-     * it prepares the processor for linux
-     *
-     * just disable everything that can disturb booting linux
-     */
+       /*
+        * this function is called just before we call linux
+        * it prepares the processor for linux
+        *
+        * just disable everything that can disturb booting linux
+        */
 
-    unsigned long i;
+       unsigned long i;
 
-    disable_interrupts();
+       disable_interrupts ();
 
-    /* turn off I-cache */
-    asm ("mrc p15, 0, %0, c1, c0, 0": "=r" (i));
-    i &= ~0x1000;
-    asm ("mcr p15, 0, %0, c1, c0, 0": : "r" (i));
+       /* turn off I-cache */
+       asm ("mrc p15, 0, %0, c1, c0, 0":"=r" (i));
+       i &= ~0x1000;
+       asm ("mcr p15, 0, %0, c1, c0, 0": :"r" (i));
 
-    /* flush I-cache */
-    asm ("mcr p15, 0, %0, c7, c5, 0": : "r" (i));
+       /* flush I-cache */
+       asm ("mcr p15, 0, %0, c7, c5, 0": :"r" (i));
+
+       return (0);
 }
 
-void do_reset (cmd_tbl_t *cmdtp, bd_t *bd, int flag, int argc, char *argv[])
+int do_reset (cmd_tbl_t *cmdtp, gd_t *gd, int flag, int argc, char *argv[])
 {
-    extern void reset_cpu(ulong addr);
+       extern void reset_cpu (ulong addr);
+
+       printf ("reseting ...\n");
 
-    printf("reseting ...\n");
+       udelay (50000);                         /* wait 50 ms */
+       disable_interrupts ();
+       reset_cpu (0);
 
-    udelay(50000); /* wait 50 ms */
-    disable_interrupts();
-    reset_cpu(0);
-    /*NOTREACHED*/
+       /*NOTREACHED*/
+       return (0);
 }
 
 /* taken from blob */
-void icache_enable(void)
+void icache_enable (void)
 {
-    register u32 i;
+       register u32 i;
 
-    /* read control register */
-    asm ("mrc p15, 0, %0, c1, c0, 0": "=r" (i));
+       /* read control register */
+       asm ("mrc p15, 0, %0, c1, c0, 0":"=r" (i));
 
-    /* set i-cache */
-    i |= 0x1000;
+       /* set i-cache */
+       i |= 0x1000;
 
-    /* write back to control register */
-    asm ("mcr p15, 0, %0, c1, c0, 0": : "r" (i));
+       /* write back to control register */
+       asm ("mcr p15, 0, %0, c1, c0, 0": :"r" (i));
 }
 
-void icache_disable(void)
+void icache_disable (void)
 {
-    register u32 i;
+       register u32 i;
 
-    /* read control register */
-    asm ("mrc p15, 0, %0, c1, c0, 0": "=r" (i));
+       /* read control register */
+       asm ("mrc p15, 0, %0, c1, c0, 0":"=r" (i));
 
-    /* clear i-cache */
-    i &= ~0x1000;
+       /* clear i-cache */
+       i &= ~0x1000;
 
-    /* write back to control register */
-    asm ("mcr p15, 0, %0, c1, c0, 0": : "r" (i));
+       /* write back to control register */
+       asm ("mcr p15, 0, %0, c1, c0, 0": :"r" (i));
 
-    /* flush i-cache */
-    asm ("mcr p15, 0, %0, c7, c5, 0": : "r" (i));
+       /* flush i-cache */
+       asm ("mcr p15, 0, %0, c7, c5, 0": :"r" (i));
 }
 
-int icache_status(void)
+int icache_status (void)
 {
-    register u32 i;
+       register u32 i;
 
-    /* read control register */
-    asm ("mrc p15, 0, %0, c1, c0, 0": "=r" (i));
+       /* read control register */
+       asm ("mrc p15, 0, %0, c1, c0, 0":"=r" (i));
 
-    /* return bit */
-    return (i & 0x1000);
+       /* return bit */
+       return (i & 0x1000);
 }
 
 /* we will never enable dcache, because we have to setup MMU first */
-void dcache_enable(void)
+void dcache_enable (void)
 {
-    return;
+       return;
 }
 
-void dcache_disable(void)
+void dcache_disable (void)
 {
-    return;
+       return;
 }
 
-int dcache_status(void)
+int dcache_status (void)
 {
-    return 0; /* always off */
+       return 0;                                       /* always off */
 }
index 58208c94f0b99703b33d664b147ed8288de9e460..4a7fecd18353e7018ebc4eb4728f8e97f63e6ed2 100644 (file)
@@ -40,6 +40,7 @@ erase         3
 fccinfo                3
 fdcboot                4
 flinfo         3
+fpga           4
 getdcr         6               # IBM 4XX DCR registers
 go             2
 help           1
diff --git a/include/altera.h b/include/altera.h
new file mode 100644 (file)
index 0000000..da18d73
--- /dev/null
@@ -0,0 +1,73 @@
+/*
+ * (C) Copyright 2002
+ * Rich Ireland, Enterasys Networks, rireland@enterasys.com.
+ *
+ * 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 <fpga.h>
+
+#ifndef _ALTERA_H_
+#define _ALTERA_H_
+
+/*
+ * Note that this is just  Altera FPGA interface boilerplate.
+ * There is no support for Altera devices yet.
+ *
+ * See include/xilinx.h for a working example.
+ */ 
+
+/* In your board's config.h file you should define CONFIG_FPGA as such:
+ *     #define CONFIG_FPGA     (CFG_ALTERA_xxx | CFG_ALTERA_IF_xxx )
+ */
+
+/* Altera Model definitions */
+#define CFG_ALTERA_xxxx                ( CFG_FPGA_ALTERA | CFG_FPGA_DEV( 0x1 ))
+/* Add new models here */
+
+/* Altera Interface definitions */
+#define CFG_ALTERA_IF_xxx              CFG_FPGA_IF( 0x1 )
+/* Add new interfaces here */
+
+typedef enum {                     /* typedef Altera_iface */
+    min_altera_iface_type,        /* insert all new types after this */
+/* Add new interfaces here */
+    max_altera_iface_type         /* insert all new types before this */
+} Altera_iface;                   /* end, typedef Altera_iface */
+
+typedef enum {                     /* typedef Altera_Family */  
+    min_altera_type,              /* insert all new types after this */
+/* Add new models here */
+    max_altera_type               /* insert all new types before this */
+} Altera_Family;                  /* end, typedef Altera_Family */     
+
+typedef struct {                   /* typedef Altera_desc */
+    Altera_Family    family;      /* part type */
+    Altera_iface     iface;       /* interface type */
+    size_t            size;        /* bytes of data part can accept */
+    void *            base;        /* base interface address */
+} Altera_desc;                    /* end, typedef Altera_desc */
+
+extern int altera_load( Altera_desc *desc, void *image, size_t size );
+extern int altera_dump( Altera_desc *desc, void *buf, size_t bsize );
+extern int altera_info( Altera_desc *desc );
+extern int altera_reloc( Altera_desc *desc, ulong reloc_off );
+
+#endif  /* _ALTERA_H_ */
index 109d309a2ce78517d4a36e070f174eb3b7fca46d..49d928612d5e6cbad13e80734a662d7d121a13a4 100644 (file)
  * Keep it *SMALL* and remember to set CFG_GBL_DATA_SIZE > sizeof(gd_t)
  */
 
+typedef        struct  global_data {
+       bd_t            *bd;
+       unsigned long   baudrate;
+#if 0
+       unsigned long   cpu_clk;        /* CPU clock in Hz!             */
+       unsigned long   bus_clk;
+       unsigned long   ram_size;       /* RAM size */
+       unsigned long   reloc_off;      /* Relocation Offset */
+       unsigned long   reset_status;   /* reset status register at boot */
+       unsigned long   env_addr;       /* Address  of Environment struct */
+       unsigned long   env_valid;      /* Checksum of Environment valid? */
+       unsigned long   have_console;   /* serial_init() was called */
+#endif
+} gd_t;
+
 #endif /* __ASM_GBL_DATA_H */
diff --git a/include/asm-arm/ppcboot-arm.h b/include/asm-arm/ppcboot-arm.h
new file mode 100644 (file)
index 0000000..f9d5b97
--- /dev/null
@@ -0,0 +1,195 @@
+/*
+ * (C) Copyright 2002
+ * Sysgo Real-Time Solutions, GmbH <www.elinos.com>
+ * Marius Groeger <mgroeger@sysgo.de>
+ * 
+ * (C) Copyright 2002
+ * Sysgo Real-Time Solutions, GmbH <www.elinos.com>
+ * Alex Zuepke <azu@sysgo.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 _PPCBOOT_ARM_H_
+#define _PPCBOOT_ARM_H_        1
+
+/* for the following variables, see start.S */
+extern ulong _armboot_start; /* code start */
+extern ulong _armboot_end;   /* code end */ 
+extern ulong IRQ_STACK_START; /* top of IRQ stack */
+extern ulong FIQ_STACK_START; /* top of FIQ stack */
+extern ulong _armboot_real_end; /* first usable RAM address */
+
+/* ------------------------------------------------------------ */
+/* Here is a list of some prototypes which are incompatible to */
+/* the PPCBoot implementation                                  */
+/* To be fixed!                                                        */
+/* ------------------------------------------------------------ */
+/* common/cmd_nvedit.c */
+int    env_init        (gd_t *);
+void   env_relocate    (gd_t *);
+char   *getenv         (bd_t *bd, uchar *);
+void   setenv          (bd_t *bd, char *, char *);
+
+/* cpu/.../cpu.c */
+void cpu_init(bd_t *bd);
+void cleanup_before_linux(bd_t *bd);
+
+/* board/.../... */
+int board_init(bd_t *);
+int dram_init(bd_t *bd);
+
+/* arm/display_options.c */
+void display_banner(bd_t *bd);
+void display_dram_config(bd_t *bd);
+void display_flash_config(bd_t *bd, ulong size);
+
+/* cpu/.../interrupt.c */
+void   reset_timer_masked      (void);
+ulong  get_timer_masked        (void);
+void   udelay_masked           (unsigned long usec);
+
+#if 0 /*------------------------------------------------------------*/
+/* arm/crc32.c */
+ulong  crc32           (ulong, const unsigned char *, uint);
+ulong  crc32_no_comp   (ulong crc, const unsigned char *, uint);
+
+/*
+ * Don't define some stuff private to armboot target code
+ */
+#ifndef HOST_TOOLS
+
+/* board/.../env.c */
+int    board_env_getchar(bd_t * bd, int index, uchar *c);
+int    board_env_save  (bd_t * bd, env_t *data, int size);
+int    board_env_copy  (bd_t * bd, env_t *data, int size);
+uchar *        board_env_getaddr(bd_t * bd, int index);
+
+
+/*
+ * Function Prototypes
+ */
+void   hang            (void);
+void   start_armboot   (void);
+void   main_loop       (bd_t *);
+int    run_command     (const char *cmd, bd_t *, int flag);
+int    readline        (const char *const prompt);
+void   reset_cmd_timeout(void);
+
+
+/* arm/string.c */
+char * strcpy          (char * dest,const char *src);
+char * strncpy         (char * dest,const char *src, size_t count);
+size_t strlen          (const char *);
+size_t strnlen         (const char * s, size_t count);
+int    strncmp         (const char * cs, const char * ct, size_t count);
+int    strcmp          (const char * cs, const char * ct);
+void * memcpy          (void * dest, const void *src, size_t count);
+int    memcmp          (const void * dest, const void *src, size_t count);
+void * memset          (void * s, char c, size_t count);
+void * memmove         (void * dest, const void *src, size_t count);
+char * strchr          (const char * s, int c);
+
+/* arm/vsprintf.c */
+ulong  simple_strtoul  (const char *cp,char **endp,unsigned int base);
+long   simple_strtol   (const char *cp,char **endp,unsigned int base);
+void   panic           (const char *fmt, ...);
+int    sprintf         (char * buf, const char *fmt, ...);
+int    vsprintf        (char *buf, const char *fmt, va_list args);
+
+void    udelay         (unsigned long);
+
+int    ctrlc           (void);
+int    had_ctrlc       (void);
+void   clear_ctrlc     (void);
+int    disable_ctrlc   (int);
+
+int    console_assign  (int file, char *devname);
+
+/* */
+int    icache_status (void);
+void   icache_enable (void);
+void   icache_disable(void);
+int    dcache_status (void);
+void   dcache_enable (void);
+void   dcache_disable(void);
+
+/* common/cmd_bootm.c */
+void print_image_hdr (image_header_t *hdr);
+
+/* cpu/.../interrupt.c */
+void   enable_interrupts       (void);
+int    disable_interrupts      (void);
+void   interrupt_init          (bd_t *bd);
+void   reset_timer             (void);
+ulong  get_timer               (ulong base);
+void   set_timer               (ulong t);
+
+extern ulong load_addr;
+
+/*
+ * STDIO based functions (can always be used)
+ */
+
+/* serial stuff */
+void   serial_printf (const char *fmt, ...);
+
+/* stdin */
+int    getc(void);
+int    tstc(void);
+
+/* stdout */
+void   putc(const char c);
+void   puts(const char *s);
+void   printf(const char *fmt, ...);
+
+/* stderr */
+#define eputc(c)               fputc(stderr, c)
+#define eputs(s)               fputs(stderr, s)
+#define eprintf(fmt,args...)   fprintf(stderr,fmt ,##args)
+
+/*
+ * FILE based functions (can only be used AFTER relocation!)
+ */
+
+#define stdin          0
+#define stdout         1
+#define stderr         2
+#define MAX_FILES      3
+
+void   fprintf(int file, const char *fmt, ...);
+void   fputs(int file, const char *s);
+void   fputc(int file, const char c);
+int    ftstc(int file);
+int    fgetc(int file);
+
+/* Byte swapping stuff */
+#define SWAP16(x)      ((((x) & 0xff) << 8) | ((x) >> 8))
+#define SWAP16c(x)     ((((x) & 0xff) << 8) | ((x) >> 8))
+#define SWAP32(x)       ( \
+                       (((x) >> 24) & 0x000000ff) | \
+                       (((x) >>  8) & 0x0000ff00) | \
+                       (((x) <<  8) & 0x00ff0000) | \
+                       (((x) << 24) & 0xff000000) )
+
+#endif /* HOST_TOOLS */
+#endif /* 0 ------------------------------------------------------------*/
+
+
+#endif /* _PPCBOOT_ARM_H_ */
index a704675a6bd2af7efb4aee9864de891580d582a0..259f4d763c09f13a285c7d96751f06a51acc23dc 100644 (file)
@@ -47,165 +47,4 @@ typedef struct bd_info {
 #define bi_env_data bi_env->data
 #define bi_env_crc  bi_env->crc
 
-/* for the following variables, see start.S */
-extern ulong _armboot_start; /* code start */
-extern ulong _armboot_end;   /* code end */ 
-extern ulong IRQ_STACK_START; /* top of IRQ stack */
-extern ulong FIQ_STACK_START; /* top of FIQ stack */
-extern ulong _armboot_real_end; /* first usable RAM address */
-
-/* ------------------------------------------------------------ */
-/* Here is a list of some prototypes which are incompatible to */
-/* the PPCBoot implementation                                  */
-/* To be fixed!                                                        */
-/* ------------------------------------------------------------ */
-/* common/cmd_nvedit.c */
-int    env_init        (gd_t *);
-void   env_relocate    (gd_t *);
-char   *getenv         (bd_t *bd, uchar *);
-void   setenv          (bd_t *bd, char *, char *);
-
-/* cpu/.../cpu.c */
-void cpu_init(bd_t *bd);
-void cleanup_before_linux(bd_t *bd);
-
-/* board/.../... */
-int board_init(bd_t *);
-int dram_init(bd_t *bd);
-
-/* arm/display_options.c */
-void display_banner(bd_t *bd);
-void display_dram_config(bd_t *bd);
-void display_flash_config(bd_t *bd, ulong size);
-
-/* cpu/.../interrupt.c */
-void   reset_timer_masked      (void);
-ulong  get_timer_masked        (void);
-void   udelay_masked           (unsigned long usec);
-
-#if 0 /*------------------------------------------------------------*/
-/* arm/crc32.c */
-ulong  crc32           (ulong, const unsigned char *, uint);
-ulong  crc32_no_comp   (ulong crc, const unsigned char *, uint);
-
-/*
- * Don't define some stuff private to armboot target code
- */
-#ifndef HOST_TOOLS
-
-/* board/.../env.c */
-int    board_env_getchar(bd_t * bd, int index, uchar *c);
-int    board_env_save  (bd_t * bd, env_t *data, int size);
-int    board_env_copy  (bd_t * bd, env_t *data, int size);
-uchar *        board_env_getaddr(bd_t * bd, int index);
-
-/*
- * Function Prototypes
- */
-void   hang            (void);
-void   start_armboot   (void);
-void   main_loop       (bd_t *);
-int    run_command     (const char *cmd, bd_t *, int flag);
-int    readline        (const char *const prompt);
-void   reset_cmd_timeout(void);
-
-
-/* arm/string.c */
-char * strcpy          (char * dest,const char *src);
-char * strncpy         (char * dest,const char *src, size_t count);
-size_t strlen          (const char *);
-size_t strnlen         (const char * s, size_t count);
-int    strncmp         (const char * cs, const char * ct, size_t count);
-int    strcmp          (const char * cs, const char * ct);
-void * memcpy          (void * dest, const void *src, size_t count);
-int    memcmp          (const void * dest, const void *src, size_t count);
-void * memset          (void * s, char c, size_t count);
-void * memmove         (void * dest, const void *src, size_t count);
-char * strchr          (const char * s, int c);
-
-/* arm/vsprintf.c */
-ulong  simple_strtoul  (const char *cp,char **endp,unsigned int base);
-long   simple_strtol   (const char *cp,char **endp,unsigned int base);
-void   panic           (const char *fmt, ...);
-int    sprintf         (char * buf, const char *fmt, ...);
-int    vsprintf        (char *buf, const char *fmt, va_list args);
-
-void    udelay         (unsigned long);
-
-int    ctrlc           (void);
-int    had_ctrlc       (void);
-void   clear_ctrlc     (void);
-int    disable_ctrlc   (int);
-
-int    console_assign  (int file, char *devname);
-
-/* */
-int    icache_status (void);
-void   icache_enable (void);
-void   icache_disable(void);
-int    dcache_status (void);
-void   dcache_enable (void);
-void   dcache_disable(void);
-
-/* common/cmd_bootm.c */
-void print_image_hdr (image_header_t *hdr);
-
-/* cpu/.../interrupt.c */
-void   enable_interrupts       (void);
-int    disable_interrupts      (void);
-void   interrupt_init          (bd_t *bd);
-void   reset_timer             (void);
-ulong  get_timer               (ulong base);
-void   set_timer               (ulong t);
-
-extern ulong load_addr;
-
-/*
- * STDIO based functions (can always be used)
- */
-
-/* serial stuff */
-void   serial_printf (const char *fmt, ...);
-
-/* stdin */
-int    getc(void);
-int    tstc(void);
-
-/* stdout */
-void   putc(const char c);
-void   puts(const char *s);
-void   printf(const char *fmt, ...);
-
-/* stderr */
-#define eputc(c)               fputc(stderr, c)
-#define eputs(s)               fputs(stderr, s)
-#define eprintf(fmt,args...)   fprintf(stderr,fmt ,##args)
-
-/*
- * FILE based functions (can only be used AFTER relocation!)
- */
-
-#define stdin          0
-#define stdout         1
-#define stderr         2
-#define MAX_FILES      3
-
-void   fprintf(int file, const char *fmt, ...);
-void   fputs(int file, const char *s);
-void   fputc(int file, const char c);
-int    ftstc(int file);
-int    fgetc(int file);
-
-/* Byte swapping stuff */
-#define SWAP16(x)      ((((x) & 0xff) << 8) | ((x) >> 8))
-#define SWAP16c(x)     ((((x) & 0xff) << 8) | ((x) >> 8))
-#define SWAP32(x)       ( \
-                       (((x) >> 24) & 0x000000ff) | \
-                       (((x) >>  8) & 0x0000ff00) | \
-                       (((x) <<  8) & 0x00ff0000) | \
-                       (((x) << 24) & 0xff000000) )
-
-#endif /* HOST_TOOLS */
-#endif /* 0 ------------------------------------------------------------*/
-
 #endif /* _PPCBOOT_H_ */
index 0688754e34c7b7911b0ecb46292d3d07e2b0f2da..0d91575762fd75f360359be3c0ad26b493528235 100644 (file)
@@ -71,6 +71,7 @@
 #define CFG_CMD_JFFS2  0x0000001000000000      /* JFFS2 Support                */
 #define CFG_CMD_DTT    0x0000002000000000      /* Digital Therm and Thermostat */
 #define CFG_CMD_SDRAM  0x0000004000000000      /* SDRAM DIMM SPD info printout */
+#define CFG_CMD_FPGA   0x0000080000000000      /* FPGA configuration Support   */
 
 #define CFG_CMD_ALL    0xFFFFFFFFFFFFFFFF      /* ALL commands                 */
 
diff --git a/include/cmd_fpga.h b/include/cmd_fpga.h
new file mode 100644 (file)
index 0000000..b34b3da
--- /dev/null
@@ -0,0 +1,52 @@
+/*
+ * (C) Copyright 2001
+ * Rich Ireland, Enterasys Networks, rireland@enterasys.com.
+ *
+ * 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
+ *
+ */
+
+/*
+ * FPGA support
+ */
+#ifndef        _CMD_FPGA_H
+#define        _CMD_FPGA_H
+
+#include <common.h>
+#include <command.h>
+
+#if defined(CONFIG_FPGA) && (CONFIG_COMMANDS & CFG_CMD_FPGA)
+
+#define        CMD_TBL_FPGA    MK_CMD_TBL_ENTRY(                               \
+       "fpga",      4,    6,     1,     do_fpga,                       \
+       "fpga   - loadable FPGA image support\n",                       \
+       "fpga [operation type] [device number] [image address] [image size]\n" \
+       "fpga operations:\n" \
+       "\tinfo\tlist known device information.\n" \
+       "\tload\tLoad device from memory buffer.\n" \
+       "\tdump\tLoad device to memory buffer.\n"  \
+),
+
+extern int do_fpga (cmd_tbl_t *cmdtp, gd_t *gd, int flag, int argc, char *argv[]);
+
+#else
+#define CMD_TBL_FPGA
+#endif  /* CONFIG_FPGA && CONFIG_COMMANDS & CFG_CMD_FPGA */
+
+#endif /* _CMD_FPGA_H */
index 6e4a8b5de7d6af3a499675e943e906ccf0adecd3..ef233e1d7e3307d28d289a2f50b3653920c24044 100644 (file)
@@ -115,7 +115,7 @@ void print_image_hdr (image_header_t *hdr);
 
 extern ulong load_addr;                /* Default Load Address */
 
-#ifdef CONFIG_PPC              /* ARM version in armboot.h - to be fixed! */
+#ifdef CONFIG_PPC              /* ARM version to be fixed! */
 /* common/cmd_nvedit.c */
 int    env_init     (gd_t *);
 void   env_relocate (gd_t *);
@@ -124,6 +124,9 @@ int getenv_r     (uchar *name, uchar *buf, unsigned len);
 int    saveenv      (void);
 void inline setenv   (char *, char *);
 #endif /* CONFIG_PPC */
+#ifdef CONFIG_ARM
+# include <asm/ppcboot-arm.h>  /* ARM version to be fixed! */
+#endif /* CONFIG_ARM */
 
 void    pci_init      (gd_t *);
 void    pciinfo       (int, int);
diff --git a/include/fpga.h b/include/fpga.h
new file mode 100644 (file)
index 0000000..782b58e
--- /dev/null
@@ -0,0 +1,81 @@
+/*
+ * (C) Copyright 2002
+ * Rich Ireland, Enterasys Networks, rireland@enterasys.com.
+ *
+ * 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 <linux/types.h>               /* for ulong typedef */
+
+#ifndef _FPGA_H_
+#define _FPGA_H_
+
+#ifndef CONFIG_MAX_FPGA_DEVICES
+#define CONFIG_MAX_FPGA_DEVICES                5
+#endif
+
+/* these probably belong somewhere else */
+#ifndef FALSE
+#define FALSE  (0)
+#endif
+#ifndef TRUE
+#define TRUE   (!FALSE)
+#endif
+
+/* CONFIG_FPGA bit assignments */
+#define CFG_FPGA_MAN(x)        (x)
+#define CFG_FPGA_DEV(x)        ((x) << 8 )
+#define CFG_FPGA_IF(x) ((x) << 16 )
+
+/* FPGA Manufacturer bits in CONFIG_FPGA */
+#define CFG_FPGA_XILINX                CFG_FPGA_MAN( 0x1 )
+#define CFG_FPGA_ALTERA                        CFG_FPGA_MAN( 0x2 )
+
+
+/* fpga_xxxx function return value definitions */
+#define FPGA_SUCCESS         0
+#define FPGA_FAIL           -1
+
+/* device numbers must be non-negative */
+#define FPGA_INVALID_DEVICE -1
+
+/* root data type defintions */
+typedef enum {                 /* typedef fpga_type */
+       fpga_min_type,             /* range check value */
+    fpga_xilinx,               /* Xilinx Family) */
+    fpga_altera,               /* unimplemented */
+    fpga_undefined             /* invalid range check value */
+} fpga_type;                   /* end, typedef fpga_type */
+
+typedef struct {               /* typedef fpga_desc */
+    fpga_type   devtype;       /* switch value to select sub-functions */
+    void *      devdesc;       /* real device descriptor */
+} fpga_desc;                   /* end, typedef fpga_desc */
+
+
+/* root function definitions */
+extern void fpga_init( ulong reloc_off );
+extern int fpga_add( fpga_type devtype, void *desc );
+extern const int fpga_count( void );
+extern int fpga_load( int devnum, void *buf, size_t bsize );
+extern int fpga_dump( int devnum, void *buf, size_t bsize );
+extern int fpga_info( int devnum );
+
+#endif /* _FPGA_H_ */
diff --git a/include/spartan2.h b/include/spartan2.h
new file mode 100644 (file)
index 0000000..2f98f96
--- /dev/null
@@ -0,0 +1,90 @@
+/*
+ * (C) Copyright 2002
+ * Rich Ireland, Enterasys Networks, rireland@enterasys.com.
+ *
+ * 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 _SPARTAN2_H_
+#define _SPARTAN2_H_
+
+#include <xilinx.h>
+
+extern int Spartan2_load( Xilinx_desc *desc, void *image, size_t size );
+extern int Spartan2_dump( Xilinx_desc *desc, void *buf, size_t bsize );
+extern int Spartan2_info( Xilinx_desc *desc );
+extern int Spartan2_reloc( Xilinx_desc *desc, ulong reloc_off );
+
+/* Slave Parallel Implementation function table */
+typedef struct {
+       Xilinx_pre_fn   pre;
+       Xilinx_pgm_fn   pgm;
+       Xilinx_init_fn  init;
+       Xilinx_err_fn   err;
+       Xilinx_done_fn  done;
+       Xilinx_clk_fn   clk;
+       Xilinx_cs_fn    cs;
+       Xilinx_wr_fn    wr;
+       Xilinx_rdata_fn rdata;
+       Xilinx_wdata_fn wdata;
+       Xilinx_busy_fn  busy;
+       Xilinx_abort_fn abort;
+       Xilinx_post_fn  post;
+       int             relocated;
+} Xilinx_Spartan2_Slave_Parallel_fns;
+
+/* Slave Serial Implementation function table */
+typedef struct {
+       Xilinx_pgm_fn   pgm;
+       Xilinx_clk_fn   clk;
+       Xilinx_rdata_fn rdata;
+       Xilinx_wdata_fn wdata;
+       int             relocated;
+} Xilinx_Spartan2_Slave_Serial_fns;
+
+/* Device Image Sizes
+ *********************************************************************/
+/* Spartan-II (2.5V) */
+#define XILINX_XC2S15_SIZE     197728/8
+#define XILINX_XC2S30_SIZE     336800/8
+#define XILINX_XC2S50_SIZE     559232/8
+#define XILINX_XC2S100_SIZE    781248/8
+#define XILINX_XC2S150_SIZE    1040128/8
+
+/* Descriptor Macros 
+ *********************************************************************/
+/* Spartan-II devices */
+#define XILINX_XC2S15_DESC(iface, fn_table, cookie) \
+{ Xilinx_Spartan2, iface, XILINX_XC2S15_SIZE, fn_table, cookie }
+
+#define XILINX_XC2S30_DESC(iface, fn_table, cookie) \
+{ Xilinx_Spartan2, iface, XILINX_XC2S30_SIZE, fn_table, cookie }
+
+#define XILINX_XC2S50_DESC(iface, fn_table, cookie) \
+{ Xilinx_Spartan2, iface, XILINX_XC2S50_SIZE, fn_table, cookie }
+
+#define XILINX_XC2S100_DESC(iface, fn_table, cookie) \
+{ Xilinx_Spartan2, iface, XILINX_XC2S100_SIZE, fn_table, cookie }
+
+#define XILINX_XC2S150_DESC(iface, fn_table, cookie) \
+{ Xilinx_Spartan2, iface, XILINX_XC2S150_SIZE, fn_table, cookie }
+
+#endif /* _SPARTAN2_H_ */
+
diff --git a/include/virtex2.h b/include/virtex2.h
new file mode 100644 (file)
index 0000000..8c0383e
--- /dev/null
@@ -0,0 +1,120 @@
+/*
+ * (C) Copyright 2002
+ * Rich Ireland, Enterasys Networks, rireland@enterasys.com.
+ * Keith Outwater, keith_outwater@mvis.com
+ *
+ * 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 _VIRTEX2_H_
+#define _VIRTEX2_H_
+
+#include <xilinx.h>
+
+extern int Virtex2_load( Xilinx_desc *desc, void *image, size_t size );
+extern int Virtex2_dump( Xilinx_desc *desc, void *buf, size_t bsize );
+extern int Virtex2_info( Xilinx_desc *desc );
+extern int Virtex2_reloc( Xilinx_desc *desc, ulong reloc_off );
+
+/*
+ * Slave SelectMap Implementation function table.
+ */
+typedef struct {
+       Xilinx_pre_fn   pre;
+       Xilinx_pgm_fn   pgm;
+       Xilinx_init_fn  init;
+       Xilinx_err_fn   err;
+       Xilinx_done_fn  done;
+       Xilinx_clk_fn   clk;
+       Xilinx_cs_fn    cs;
+       Xilinx_wr_fn    wr;
+       Xilinx_rdata_fn rdata;
+       Xilinx_wdata_fn wdata;
+       Xilinx_busy_fn  busy;
+       Xilinx_abort_fn abort;
+       Xilinx_post_fn  post;
+       int             relocated;
+} Xilinx_Virtex2_Slave_SelectMap_fns;
+
+/* Slave Serial Implementation function table */
+typedef struct {
+       Xilinx_pgm_fn   pgm;
+       Xilinx_clk_fn   clk;
+       Xilinx_rdata_fn rdata;
+       Xilinx_wdata_fn wdata;
+       int             relocated;
+} Xilinx_Virtex2_Slave_Serial_fns;
+
+/* Device Image Sizes (in bytes)
+ *********************************************************************/
+#define XILINX_XC2V40_SIZE             (338208 / 8)
+#define XILINX_XC2V80_SIZE             (597408 / 8)
+#define XILINX_XC2V250_SIZE            (1591584 / 8)
+#define XILINX_XC2V500_SIZE            (2557857 / 8)
+#define XILINX_XC2V1000_SIZE   (3749408 / 8)
+#define XILINX_XC2V1500_SIZE   (5166240 / 8)
+#define XILINX_XC2V2000_SIZE   (6808352 / 8)
+#define XILINX_XC2V3000_SIZE   (9589408 / 8)
+#define XILINX_XC2V4000_SIZE   (14220192 / 8)
+#define XILINX_XC2V6000_SIZE   (19752096 / 8)
+#define XILINX_XC2V8000_SIZE   (26185120 / 8)
+#define XILINX_XC2V10000_SIZE  (33519264 / 8)
+
+/* Descriptor Macros 
+ *********************************************************************/
+#define XILINX_XC2V40_DESC(iface, fn_table, cookie)    \
+{ Xilinx_Virtex2, iface, XILINX_XC2V40_SIZE, fn_table, cookie }
+
+#define XILINX_XC2V80_DESC(iface, fn_table, cookie) \
+{ Xilinx_Virtex2, iface, XILINX_XC2V80_SIZE, fn_table, cookie }
+
+#define XILINX_XC2V250_DESC(iface, fn_table, cookie) \
+{ Xilinx_Virtex2, iface, XILINX_XC2V250_SIZE, fn_table, cookie }
+
+#define XILINX_XC2V500_DESC(iface, fn_table, cookie) \
+{ Xilinx_Virtex2, iface, XILINX_XC2V500_SIZE, fn_table, cookie }
+
+#define XILINX_XC2V1000_DESC(iface, fn_table, cookie) \
+{ Xilinx_Virtex2, iface, XILINX_XC2V1000_SIZE, fn_table, cookie }
+
+#define XILINX_XC2V1500_DESC(iface, fn_table, cookie) \
+{ Xilinx_Virtex2, iface, XILINX_XC2V1500_SIZE, fn_table, cookie }
+
+#define XILINX_XC2V2000_DESC(iface, fn_table, cookie) \
+{ Xilinx_Virtex2, iface, XILINX_XC2V2000_SIZE, fn_table, cookie }
+
+#define XILINX_XC2V3000_DESC(iface, fn_table, cookie) \
+{ Xilinx_Virtex2, iface, XILINX_XC2V3000_SIZE, fn_table, cookie }
+
+#define XILINX_XC2V4000_DESC(iface, fn_table, cookie) \
+{ Xilinx_Virtex2, iface, XILINX_XC2V4000_SIZE, fn_table, cookie }
+
+#define XILINX_XC2V6000_DESC(iface, fn_table, cookie) \
+{ Xilinx_Virtex2, iface, XILINX_XC2V6000_SIZE, fn_table, cookie }
+
+#define XILINX_XC2V8000_DESC(iface, fn_table, cookie) \
+{ Xilinx_Virtex2, iface, XILINX_XC2V8000_SIZE, fn_table, cookie }
+
+#define XILINX_XC2V10000_DESC(iface, fn_table, cookie) \
+{ Xilinx_Virtex2, iface, XILINX_XC2V10000_SIZE, fn_table, cookie }
+
+#endif /* _VIRTEX2_H_ */
+
+/* vim: set ts=4 tw=78: */
diff --git a/include/xilinx.h b/include/xilinx.h
new file mode 100644 (file)
index 0000000..73d5434
--- /dev/null
@@ -0,0 +1,102 @@
+/*
+ * (C) Copyright 2002
+ * Rich Ireland, Enterasys Networks, rireland@enterasys.com.
+ *
+ * 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 <fpga.h>
+
+#ifndef _XILINX_H_
+#define _XILINX_H_
+
+/* Xilinx Model definitions
+ *********************************************************************/
+#define CFG_SPARTAN2                   CFG_FPGA_DEV( 0x1 )
+#define CFG_VIRTEX_E                   CFG_FPGA_DEV( 0x2 )
+#define CFG_VIRTEX2                            CFG_FPGA_DEV( 0x4 )
+#define CFG_XILINX_SPARTAN2    (CFG_FPGA_XILINX | CFG_SPARTAN2)
+#define CFG_XILINX_VIRTEX_E    (CFG_FPGA_XILINX | CFG_VIRTEX_E)
+#define CFG_XILINX_VIRTEX2             (CFG_FPGA_XILINX | CFG_VIRTEX2)
+/* XXX - Add new models here */
+
+
+/* Xilinx Interface definitions
+ *********************************************************************/
+#define CFG_XILINX_IF_SS       CFG_FPGA_IF( 0x1 )      /* slave serial         */
+#define CFG_XILINX_IF_MS       CFG_FPGA_IF( 0x2 )      /* master serial        */
+#define CFG_XILINX_IF_SP       CFG_FPGA_IF( 0x4 )      /* slave parallel       */
+#define CFG_XILINX_IF_JTAG     CFG_FPGA_IF( 0x8 )      /* jtag                         */
+#define CFG_XILINX_IF_MSM      CFG_FPGA_IF( 0x10 )     /* master selectmap     */
+#define CFG_XILINX_IF_SSM      CFG_FPGA_IF( 0x20 )     /* slave selectmap      */
+
+/* Xilinx types
+ *********************************************************************/
+typedef enum {                                 /* typedef Xilinx_iface */
+       min_xilinx_iface_type,          /* low range check value */
+    slave_serial,                              /* serial data and external clock */
+    master_serial,                             /* serial data w/ internal clock (not used) */
+    slave_parallel,                            /* parallel data w/ external latch */
+    jtag_mode,                                 /* jtag/tap serial (not used ) */
+       master_selectmap,                       /* master SelectMap (virtex2)           */
+       slave_selectmap,                        /* slave SelectMap (virtex2)            */
+    max_xilinx_iface_type              /* insert all new types before this */
+} Xilinx_iface;                                        /* end, typedef Xilinx_iface */
+
+typedef enum {                                 /* typedef Xilinx_Family */  
+       min_xilinx_type,                        /* low range check value */
+    Xilinx_Spartan2,                   /* Spartan-II Family */ 
+    Xilinx_VirtexE,                            /* Virtex-E Family */ 
+    Xilinx_Virtex2,                            /* Virtex2 Family */ 
+    max_xilinx_type                            /* insert all new types before this */
+} Xilinx_Family;                               /* end, typedef Xilinx_Family */        
+
+typedef struct {                               /* typedef Xilinx_desc */
+    Xilinx_Family    family;   /* part type */
+    Xilinx_iface     iface;            /* interface type */
+    size_t           size;             /* bytes of data part can accept */
+       void *           iface_fns;     /* interface function table */
+    int              cookie;   /* implementation specific cookie */
+} Xilinx_desc;                                 /* end, typedef Xilinx_desc */
+
+/* Generic Xilinx Functions
+ *********************************************************************/
+extern int xilinx_load( Xilinx_desc *desc, void *image, size_t size );
+extern int xilinx_dump( Xilinx_desc *desc, void *buf, size_t bsize );
+extern int xilinx_info( Xilinx_desc *desc );
+extern int xilinx_reloc( Xilinx_desc *desc, ulong reloc_offset );
+
+/* Board specific implementation specific function types
+ *********************************************************************/
+typedef int (*Xilinx_pgm_fn)( int assert_pgm, int flush, int cookie );
+typedef int (*Xilinx_init_fn)( int cookie );
+typedef int (*Xilinx_err_fn)( int cookie );
+typedef int (*Xilinx_done_fn)( int cookie );
+typedef int (*Xilinx_clk_fn)( int assert_clk, int flush, int cookie );
+typedef int (*Xilinx_cs_fn)( int assert_cs, int flush, int cookie );
+typedef int (*Xilinx_wr_fn)( int assert_write, int flush, int cookie );
+typedef int (*Xilinx_rdata_fn)( unsigned char *data, int cookie );
+typedef int (*Xilinx_wdata_fn)( unsigned char data, int flush, int cookie );
+typedef int (*Xilinx_busy_fn)( int cookie );
+typedef int (*Xilinx_abort_fn)( int cookie );
+typedef int (*Xilinx_pre_fn)( int cookie );
+typedef int (*Xilinx_post_fn)( int cookie );
+
+#endif  /* _XILINX_H_ */
index 75c884f179a7d4d2ed38d3b3412b7a1b124524b1..13e5e2ec682d9a3d4644553a47fa1ae741bd2f69 100644 (file)
@@ -63,6 +63,7 @@ void boot_linux(cmd_tbl_t *cmdtp,
     ulong data;
     void (*theKernel)(int zero, int arch);
     image_header_t *hdr = &header;
+    bd_t *bd = gd->bd;
 #ifdef CONFIG_CMDLINE_TAG
     char *commandline = getenv("bootargs");
 #endif
index 4119adbef4486a5da37f20c3ddaf21c93355d0a8..0e1fd0f0d51596bf71397b27d577b97c5ed8b3f1 100644 (file)
@@ -27,7 +27,7 @@ include $(TOPDIR)/config.mk
 
 LIB    = librtc.a
 
-OBJS   = date.o   ds1302.o ds174x.o ds1306.o ds1556.o \
+OBJS   = date.o   ds1302.o ds1306.o ds1337.o ds1556.o ds174x.o \
          m41t11.o m48t35ax.o mc146818.o mk48t59.o \
          mpc8xx.o pcf8563.o
 
diff --git a/rtc/ds1337.c b/rtc/ds1337.c
new file mode 100644 (file)
index 0000000..9f0c8c0
--- /dev/null
@@ -0,0 +1,191 @@
+/*
+ * (C) Copyright 2001, 2002
+ * Wolfgang Denk, DENX Software Engineering, wd@denx.de.
+ * Keith Outwater, keith_outwater@mvis.com`
+ *
+ * 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
+ */
+
+/*
+ * Date & Time support (no alarms) for Dallas Semiconductor (now Maxim)
+ * DS1337 Real Time Clock (RTC).
+ */
+
+#include <common.h>
+#include <command.h>
+#include <rtc.h>
+#include <i2c.h>
+
+#if defined(CONFIG_RTC_DS1337) && (CONFIG_COMMANDS & CFG_CMD_DATE)
+
+/*---------------------------------------------------------------------*/
+#undef DEBUG_RTC
+
+#ifdef DEBUG_RTC
+#define DEBUGR(fmt,args...) printf(fmt ,##args)
+#else
+#define DEBUGR(fmt,args...)
+#endif
+/*---------------------------------------------------------------------*/
+
+/*
+ * RTC register addresses
+ */
+#define RTC_SEC_REG_ADDR       0x0
+#define RTC_MIN_REG_ADDR       0x1
+#define RTC_HR_REG_ADDR                0x2
+#define RTC_DAY_REG_ADDR       0x3
+#define RTC_DATE_REG_ADDR      0x4
+#define RTC_MON_REG_ADDR       0x5
+#define RTC_YR_REG_ADDR                0x6
+#define RTC_CTL_REG_ADDR       0x0e
+#define RTC_STAT_REG_ADDR      0x0f
+
+/*
+ * RTC control register bits
+ */
+#define RTC_CTL_BIT_A1IE       0x1     /* Alarm 1 interrupt enable     */
+#define RTC_CTL_BIT_A2IE       0x2     /* Alarm 2 interrupt enable     */
+#define RTC_CTL_BIT_INTCN      0x4     /* Interrupt control            */
+#define RTC_CTL_BIT_RS1                0x8     /* Rate select 1                */
+#define RTC_CTL_BIT_RS2                0x10    /* Rate select 2                */
+#define RTC_CTL_BIT_DOSC       0x80    /* Disable Oscillator           */
+
+/*
+ * RTC status register bits
+ */
+#define RTC_STAT_BIT_A1F       0x1     /* Alarm 1 flag                 */
+#define RTC_STAT_BIT_A2F       0x2     /* Alarm 2 flag                 */
+#define RTC_STAT_BIT_OSF       0x80    /* Oscillator stop flag         */
+
+
+static uchar rtc_read (uchar reg);
+static void rtc_write (uchar reg, uchar val);
+static uchar bin2bcd (unsigned int n);
+static unsigned bcd2bin (uchar c);
+
+
+/*
+ * Get the current time from the RTC
+ */
+void rtc_get (struct rtc_time *tmp)
+{
+       uchar sec, min, hour, mday, wday, mon_cent, year, control, status;
+
+       control = rtc_read (RTC_CTL_REG_ADDR);
+       status = rtc_read (RTC_STAT_REG_ADDR);
+       sec = rtc_read (RTC_SEC_REG_ADDR);
+       min = rtc_read (RTC_MIN_REG_ADDR);
+       hour = rtc_read (RTC_HR_REG_ADDR);
+       wday = rtc_read (RTC_DAY_REG_ADDR);
+       mday = rtc_read (RTC_DATE_REG_ADDR);
+       mon_cent = rtc_read (RTC_MON_REG_ADDR);
+       year = rtc_read (RTC_YR_REG_ADDR);
+
+       DEBUGR ("Get RTC year: %02x mon/cent: %02x mday: %02x wday: %02x "
+               "hr: %02x min: %02x sec: %02x control: %02x status: %02x\n",
+               year, mon_cent, mday, wday, hour, min, sec, control, status);
+
+       if (status & RTC_STAT_BIT_OSF) {
+               printf ("### Warning: RTC oscillator has stopped\n");
+               /* clear the OSF flag */
+               rtc_write (RTC_STAT_REG_ADDR,
+                          rtc_read (RTC_STAT_REG_ADDR) & ~RTC_STAT_BIT_OSF);
+       }
+
+       tmp->tm_sec  = bcd2bin (sec & 0x7F);
+       tmp->tm_min  = bcd2bin (min & 0x7F);
+       tmp->tm_hour = bcd2bin (hour & 0x3F);
+       tmp->tm_mday = bcd2bin (mday & 0x3F);
+       tmp->tm_mon  = bcd2bin (mon_cent & 0x1F);
+       tmp->tm_year = bcd2bin (year) + ((mon_cent & 0x80) ? 2000 : 1900);
+       tmp->tm_wday = bcd2bin ((wday - 1) & 0x07);
+       tmp->tm_yday = 0;
+       tmp->tm_isdst= 0;
+
+       DEBUGR ("Get DATE: %4d-%02d-%02d (wday=%d)  TIME: %2d:%02d:%02d\n",
+               tmp->tm_year, tmp->tm_mon, tmp->tm_mday, tmp->tm_wday,
+               tmp->tm_hour, tmp->tm_min, tmp->tm_sec);
+}
+
+
+/*
+ * Set the RTC
+ */
+void rtc_set (struct rtc_time *tmp)
+{
+       uchar century;
+
+       DEBUGR ("Set DATE: %4d-%02d-%02d (wday=%d)  TIME: %2d:%02d:%02d\n",
+               tmp->tm_year, tmp->tm_mon, tmp->tm_mday, tmp->tm_wday,
+               tmp->tm_hour, tmp->tm_min, tmp->tm_sec);
+
+       rtc_write (RTC_YR_REG_ADDR, bin2bcd (tmp->tm_year % 100));
+
+       century = (tmp->tm_year >= 2000) ? 0x80 : 0;
+       rtc_write (RTC_MON_REG_ADDR, bin2bcd (tmp->tm_mon) | century);
+
+       rtc_write (RTC_DAY_REG_ADDR, bin2bcd (tmp->tm_wday + 1));
+       rtc_write (RTC_DATE_REG_ADDR, bin2bcd (tmp->tm_mday));
+       rtc_write (RTC_HR_REG_ADDR, bin2bcd (tmp->tm_hour));
+       rtc_write (RTC_MIN_REG_ADDR, bin2bcd (tmp->tm_min));
+       rtc_write (RTC_SEC_REG_ADDR, bin2bcd (tmp->tm_sec));
+}
+
+
+/*
+ * Reset the RTC.  We also enable the oscillator output on the
+ * SQW/INTB* pin and program it for 32,768 Hz output. Note that
+ * according to the datasheet, turning on the square wave output
+ * increases the current drain on the backup battery from about
+ * 600 nA to 2uA.
+ */
+void rtc_reset (void)
+{
+       rtc_write (RTC_CTL_REG_ADDR, RTC_CTL_BIT_RS1 | RTC_CTL_BIT_RS2);
+}
+
+
+/*
+ * Helper functions
+ */
+
+static
+uchar rtc_read (uchar reg)
+{
+       return (i2c_reg_read (CFG_I2C_RTC_ADDR, reg));
+}
+
+
+static void rtc_write (uchar reg, uchar val)
+{
+       i2c_reg_write (CFG_I2C_RTC_ADDR, reg, val);
+}
+
+static unsigned bcd2bin (uchar n)
+{
+       return ((((n >> 4) & 0x0F) * 10) + (n & 0x0F));
+}
+
+static unsigned char bin2bcd (unsigned int n)
+{
+       return (((n / 10) << 4) | (n % 10));
+}
+
+#endif /* CONFIG_RTC_DS1337 && (CFG_COMMANDS & CFG_CMD_DATE) */