diff options
Diffstat (limited to 'board/ap325rxa/cpld-ap325rxa.c')
-rw-r--r-- | board/ap325rxa/cpld-ap325rxa.c | 206 |
1 files changed, 206 insertions, 0 deletions
diff --git a/board/ap325rxa/cpld-ap325rxa.c b/board/ap325rxa/cpld-ap325rxa.c new file mode 100644 index 0000000..16fadcb --- /dev/null +++ b/board/ap325rxa/cpld-ap325rxa.c @@ -0,0 +1,206 @@ +/*************************************************************** + * Project: + * CPLD SlaveSerial Configuration via embedded microprocessor. + * + * Copyright info: + * + * This is free software; you can redistribute it and/or modify + * it as you like. + * + * 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. + * + * Description: + * + * This is the main source file that will allow a microprocessor + * to configure Xilinx Virtex, Virtex-E, Virtex-EM, Virtex-II, + * and Spartan-II devices via the SlaveSerial Configuration Mode. + * This code is discussed in Xilinx Application Note, XAPP502. + * + * History: + * 3-October-2001 MN/MP - Created + * 20-August-2008 Renesas Solutions - Modified to SH7723 + ****************************************************************/ + +#include <common.h> + +/* Serial */ +#define SCIF_BASE 0xffe00000 /* SCIF0 */ +#define SCSMR (vu_short *)(SCIF_BASE + 0x00) +#define SCBRR (vu_char *)(SCIF_BASE + 0x04) +#define SCSCR (vu_short *)(SCIF_BASE + 0x08) +#define SC_TDR (vu_char *)(SCIF_BASE + 0x0C) +#define SC_SR (vu_short *)(SCIF_BASE + 0x10) +#define SCFCR (vu_short *)(SCIF_BASE + 0x18) +#define RFCR (vu_long *)0xFE400020 + +#define SCSCR_INIT 0x0038 +#define SCSCR_CLR 0x0000 +#define SCFCR_INIT 0x0006 +#define SCSMR_INIT 0x0080 +#define RFCR_CLR 0xA400 +#define SCI_TD_E 0x0020 +#define SCI_TDRE_CLEAR 0x00df + +#define BPS_SETTING_VALUE 1 /* 12.5MHz */ +#define WAIT_RFCR_COUNTER 500 + +/* CPLD data size */ +#define CPLD_DATA_SIZE 169216 + +/* out */ +#define CPLD_PFC_ADR ((vu_short *)0xA4050112) + +#define CPLD_PROG_ADR ((vu_char *)0xA4050132) +#define CPLD_PROG_DAT 0x80 + +/* in */ +#define CPLD_INIT_ADR ((vu_char *)0xA4050132) +#define CPLD_INIT_DAT 0x40 +#define CPLD_DONE_ADR ((vu_char *)0xA4050132) +#define CPLD_DONE_DAT 0x20 + +#define HIZCRB ((vu_short *)0xA405015A) + +/* data */ +#define CPLD_NOMAL_START 0xA0A80000 +#define CPLD_SAFE_START 0xA0AC0000 +#define MODE_SW (vu_char *)0xA405012A + +static void init_cpld_loader(void) +{ + + *SCSCR = SCSCR_CLR; + *SCFCR = SCFCR_INIT; + *SCSMR = SCSMR_INIT; + + *SCBRR = BPS_SETTING_VALUE; + + *RFCR = RFCR_CLR; /* Refresh counter clear */ + + while (*RFCR < WAIT_RFCR_COUNTER) + ; + + *SCFCR = 0x0; /* RTRG=00, TTRG=00 */ + /* MCE=0,TFRST=0,RFRST=0,LOOP=0 */ + *SCSCR = SCSCR_INIT; +} + +static int check_write_ready(void) +{ + u16 status = *SC_SR; + return status & SCI_TD_E; +} + +static void write_cpld_data(char ch) +{ + while (!check_write_ready()) + ; + + *SC_TDR = ch; + *SC_SR; + *SC_SR = SCI_TDRE_CLEAR; +} + +static int delay(void) +{ + int i; + int c = 0; + for (i = 0; i < 200; i++) { + c = *(volatile int *)0xa0000000; + } + return c; +} + +/*********************************************************************** + * + * Function: slave_serial + * + * Description: Initiates SlaveSerial Configuration. + * Calls ShiftDataOut() to output serial data + * + ***********************************************************************/ +static void slave_serial(void) +{ + int i; + unsigned char *flash; + + *CPLD_PROG_ADR |= CPLD_PROG_DAT; /* PROGRAM_OE HIGH */ + delay(); + + /* + * Toggle Program Pin by Toggling Program_OE bit + * This is accomplished by writing to the Program Register in the CPLD + * + * NOTE: The Program_OE bit should be driven high to bring the Virtex + * Program Pin low. Likewise, it should be driven low + * to bring the Virtex Program Pin to High-Z + */ + + *CPLD_PROG_ADR &= ~CPLD_PROG_DAT; /* PROGRAM_OE LOW */ + delay(); + + /* + * Bring Program High-Z + * (Drive Program_OE bit low to bring Virtex Program Pin to High-Z + */ + + /* Program_OE bit Low brings the Virtex Program Pin to High Z: */ + *CPLD_PROG_ADR |= CPLD_PROG_DAT; /* PROGRAM_OE HIGH */ + + while ((*CPLD_INIT_ADR & CPLD_INIT_DAT) == 0) + delay(); + + /* Begin Slave-Serial Configuration */ + flash = (unsigned char *)CPLD_NOMAL_START; + + for (i = 0; i < CPLD_DATA_SIZE; i++) + write_cpld_data(*flash++); +} + +/*********************************************************************** + * + * Function: check_done_bit + * + * Description: This function takes monitors the CPLD Input Register + * by checking the status of the DONE bit in that Register. + * By doing so, it monitors the Xilinx Virtex device's DONE + * Pin to see if configuration bitstream has been properly + * loaded + * + ***********************************************************************/ +static void check_done_bit(void) +{ + while (!(*CPLD_DONE_ADR & CPLD_DONE_DAT)) + ; +} + +/*********************************************************************** + * + * Function: init_cpld + * + * Description: Begins Slave Serial configuration of Xilinx FPGA + * + ***********************************************************************/ +void init_cpld(void) +{ + /* Init serial device */ + init_cpld_loader(); + + if (*CPLD_DONE_ADR & CPLD_DONE_DAT) /* Already DONE */ + return; + + *HIZCRB = 0x0000; + *CPLD_PFC_ADR = 0x7c00; /* FPGA PROG = OUTPUT */ + + /* write CPLD data from NOR flash to device */ + slave_serial(); + + /* + * Monitor the DONE bit in the CPLD Input Register to see if + * configuration successful + */ + + check_done_bit(); +} |