diff options
Diffstat (limited to 'board/siemens/SCM')
-rwxr-xr-x | board/siemens/SCM/Makefile | 42 | ||||
-rwxr-xr-x | board/siemens/SCM/config.mk | 34 | ||||
-rwxr-xr-x | board/siemens/SCM/flash.c | 488 | ||||
-rwxr-xr-x | board/siemens/SCM/fpga_scm.c | 104 | ||||
-rwxr-xr-x | board/siemens/SCM/scm.c | 540 | ||||
-rwxr-xr-x | board/siemens/SCM/scm.h | 87 | ||||
-rwxr-xr-x | board/siemens/SCM/u-boot.lds | 126 |
7 files changed, 1421 insertions, 0 deletions
diff --git a/board/siemens/SCM/Makefile b/board/siemens/SCM/Makefile new file mode 100755 index 0000000..af646e4 --- /dev/null +++ b/board/siemens/SCM/Makefile @@ -0,0 +1,42 @@ +# +# (C) Copyright 2001 +# Wolfgang Denk, DENX Software Engineering, wd@denx.de. +# +# See file CREDITS for list of people who contributed to this +# project. +# +# This program is free software; you can redistribute it and/or +# modify it under the terms of the GNU General Public License as +# published by the Free Software Foundation; either version 2 of +# the License, or (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software +# Foundation, Inc., 59 Temple Place, Suite 330, Boston, +# MA 02111-1307 USA +# + +include $(TOPDIR)/config.mk + +LIB = lib$(BOARD).a + +OBJS = scm.o flash.o fpga_scm.o ../common/fpga.o \ + ../../tqm8xx/load_sernum_ethaddr.o + + +$(LIB): .depend $(OBJS) + $(AR) crv $@ $(OBJS) + +######################################################################### + +.depend: Makefile $(SOBJS:.o=.S) $(OBJS:.o=.c) + $(CC) -M $(CFLAGS) $(SOBJS:.o=.S) $(OBJS:.o=.c) > $@ + +sinclude .depend + +######################################################################### diff --git a/board/siemens/SCM/config.mk b/board/siemens/SCM/config.mk new file mode 100755 index 0000000..855ae38 --- /dev/null +++ b/board/siemens/SCM/config.mk @@ -0,0 +1,34 @@ +# +# (C) Copyright 2001 +# Wolfgang Denk, DENX Software Engineering, wd@denx.de. +# +# See file CREDITS for list of people who contributed to this +# project. +# +# This program is free software; you can redistribute it and/or +# modify it under the terms of the GNU General Public License as +# published by the Free Software Foundation; either version 2 of +# the License, or (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software +# Foundation, Inc., 59 Temple Place, Suite 330, Boston, +# MA 02111-1307 USA +# + +# +# Siemens SCM boards +# + +# This should be equal to the CFG_FLASH_BASE define in config_SCM.h +# for the "final" configuration, with U-Boot in flash, or the address +# in RAM where U-Boot is loaded at for debugging. +# +TEXT_BASE = 0x40000000 + +PLATFORM_CPPFLAGS += -DTEXT_BASE=$(TEXT_BASE) -I$(TOPDIR) diff --git a/board/siemens/SCM/flash.c b/board/siemens/SCM/flash.c new file mode 100755 index 0000000..056fe81 --- /dev/null +++ b/board/siemens/SCM/flash.c @@ -0,0 +1,488 @@ +/* + * (C) Copyright 2001, 2002 + * Wolfgang Denk, DENX Software Engineering, wd@denx.de. + * + * Flash Routines for AMD devices on the TQM8260 board + * + *-------------------------------------------------------------------- + * 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> +#include <mpc8xx.h> + +#define V_ULONG(a) (*(volatile unsigned long *)( a )) +#define V_BYTE(a) (*(volatile unsigned char *)( a )) + + +flash_info_t flash_info[CFG_MAX_FLASH_BANKS]; + + +/*----------------------------------------------------------------------- + */ +void flash_reset (void) +{ + if (flash_info[0].flash_id != FLASH_UNKNOWN) { + V_ULONG (flash_info[0].start[0]) = 0x00F000F0; + V_ULONG (flash_info[0].start[0] + 4) = 0x00F000F0; + } +} + +/*----------------------------------------------------------------------- + */ +ulong flash_get_size (ulong baseaddr, flash_info_t * info) +{ + short i; + unsigned long flashtest_h, flashtest_l; + + /* Write auto select command sequence and test FLASH answer */ + V_ULONG (baseaddr + ((ulong) 0x0555 << 3)) = 0x00AA00AA; + V_ULONG (baseaddr + ((ulong) 0x02AA << 3)) = 0x00550055; + V_ULONG (baseaddr + ((ulong) 0x0555 << 3)) = 0x00900090; + V_ULONG (baseaddr + 4 + ((ulong) 0x0555 << 3)) = 0x00AA00AA; + V_ULONG (baseaddr + 4 + ((ulong) 0x02AA << 3)) = 0x00550055; + V_ULONG (baseaddr + 4 + ((ulong) 0x0555 << 3)) = 0x00900090; + + flashtest_h = V_ULONG (baseaddr); /* manufacturer ID */ + flashtest_l = V_ULONG (baseaddr + 4); + + switch ((int) flashtest_h) { + case AMD_MANUFACT: + info->flash_id = FLASH_MAN_AMD; + break; + case FUJ_MANUFACT: + info->flash_id = FLASH_MAN_FUJ; + break; + default: + info->flash_id = FLASH_UNKNOWN; + info->sector_count = 0; + info->size = 0; + return (0); /* no or unknown flash */ + } + + flashtest_h = V_ULONG (baseaddr + 8); /* device ID */ + flashtest_l = V_ULONG (baseaddr + 12); + if (flashtest_h != flashtest_l) { + info->flash_id = FLASH_UNKNOWN; + } else { + switch (flashtest_h) { + case AMD_ID_LV800T: + info->flash_id += FLASH_AM800T; + info->sector_count = 19; + info->size = 0x00400000; + break; /* 4 * 1 MB = 4 MB */ + case AMD_ID_LV800B: + info->flash_id += FLASH_AM800B; + info->sector_count = 19; + info->size = 0x00400000; + break; /* 4 * 1 MB = 4 MB */ + case AMD_ID_LV160T: + info->flash_id += FLASH_AM160T; + info->sector_count = 35; + info->size = 0x00800000; + break; /* 4 * 2 MB = 8 MB */ + case AMD_ID_LV160B: + info->flash_id += FLASH_AM160B; + info->sector_count = 35; + info->size = 0x00800000; + break; /* 4 * 2 MB = 8 MB */ + case AMD_ID_DL322T: + info->flash_id += FLASH_AMDL322T; + info->sector_count = 71; + info->size = 0x01000000; + break; /* 4 * 4 MB = 16 MB */ + case AMD_ID_DL322B: + info->flash_id += FLASH_AMDL322B; + info->sector_count = 71; + info->size = 0x01000000; + break; /* 4 * 4 MB = 16 MB */ + case AMD_ID_DL323T: + info->flash_id += FLASH_AMDL323T; + info->sector_count = 71; + info->size = 0x01000000; + break; /* 4 * 4 MB = 16 MB */ + case AMD_ID_DL323B: + info->flash_id += FLASH_AMDL323B; + info->sector_count = 71; + info->size = 0x01000000; + break; /* 4 * 4 MB = 16 MB */ + case AMD_ID_LV640U: + info->flash_id += FLASH_AM640U; + info->sector_count = 128; + info->size = 0x02000000; + break; /* 4 * 8 MB = 32 MB */ + default: + info->flash_id = FLASH_UNKNOWN; + return (0); /* no or unknown flash */ + } + } + + if (flashtest_h == AMD_ID_LV640U) { + + /* set up sector start adress table (uniform sector type) */ + for (i = 0; i < info->sector_count; i++) + info->start[i] = baseaddr + (i * 0x00040000); + + } else if (info->flash_id & FLASH_BTYPE) { + + /* set up sector start adress table (bottom sector type) */ + info->start[0] = baseaddr + 0x00000000; + info->start[1] = baseaddr + 0x00010000; + info->start[2] = baseaddr + 0x00018000; + info->start[3] = baseaddr + 0x00020000; + for (i = 4; i < info->sector_count; i++) { + info->start[i] = baseaddr + (i * 0x00040000) - 0x000C0000; + } + + } else { + + /* set up sector start adress table (top sector type) */ + i = info->sector_count - 1; + info->start[i--] = baseaddr + info->size - 0x00010000; + info->start[i--] = baseaddr + info->size - 0x00018000; + info->start[i--] = baseaddr + info->size - 0x00020000; + for (; i >= 0; i--) { + info->start[i] = baseaddr + i * 0x00040000; + } + } + + /* check for protected sectors */ + for (i = 0; i < info->sector_count; i++) { + /* read sector protection at sector address, (A7 .. A0) = 0x02 */ + if ((V_ULONG (info->start[i] + 16) & 0x00010001) || + (V_ULONG (info->start[i] + 20) & 0x00010001)) { + info->protect[i] = 1; /* D0 = 1 if protected */ + } else { + info->protect[i] = 0; + } + } + + flash_reset (); + return (info->size); +} + +/*----------------------------------------------------------------------- + */ +unsigned long flash_init (void) +{ + unsigned long size_b0 = 0; + int i; + + /* Init: no FLASHes known */ + for (i = 0; i < CFG_MAX_FLASH_BANKS; ++i) { + flash_info[i].flash_id = FLASH_UNKNOWN; + } + + /* Static FLASH Bank configuration here (only one bank) */ + + size_b0 = flash_get_size (CFG_FLASH0_BASE, &flash_info[0]); + if (flash_info[0].flash_id == FLASH_UNKNOWN || size_b0 == 0) { + printf ("## Unknown FLASH on Bank 0 - Size = 0x%08lx = %ld MB\n", + size_b0, size_b0 >> 20); + } + + /* + * protect monitor and environment sectors + */ + +#if CFG_MONITOR_BASE >= CFG_FLASH0_BASE + flash_protect (FLAG_PROTECT_SET, + CFG_MONITOR_BASE, + CFG_MONITOR_BASE + monitor_flash_len - 1, &flash_info[0]); +#endif + +#if (CFG_ENV_IS_IN_FLASH == 1) && defined(CFG_ENV_ADDR) +# ifndef CFG_ENV_SIZE +# define CFG_ENV_SIZE CFG_ENV_SECT_SIZE +# endif + flash_protect (FLAG_PROTECT_SET, + CFG_ENV_ADDR, + CFG_ENV_ADDR + CFG_ENV_SIZE - 1, &flash_info[0]); +#endif + + return (size_b0); +} + +/*----------------------------------------------------------------------- + */ +void flash_print_info (flash_info_t * info) +{ + int i; + + if (info->flash_id == FLASH_UNKNOWN) { + printf ("missing or unknown FLASH type\n"); + return; + } + + switch (info->flash_id & FLASH_VENDMASK) { + case FLASH_MAN_AMD: + printf ("AMD "); + break; + case FLASH_MAN_FUJ: + printf ("FUJITSU "); + break; + default: + printf ("Unknown Vendor "); + break; + } + + switch (info->flash_id & FLASH_TYPEMASK) { + case FLASH_AM800T: + printf ("29LV800T (8 M, top sector)\n"); + break; + case FLASH_AM800B: + printf ("29LV800T (8 M, bottom sector)\n"); + break; + case FLASH_AM160T: + printf ("29LV160T (16 M, top sector)\n"); + break; + case FLASH_AM160B: + printf ("29LV160B (16 M, bottom sector)\n"); + break; + case FLASH_AMDL322T: + printf ("29DL322T (32 M, top sector)\n"); + break; + case FLASH_AMDL322B: + printf ("29DL322B (32 M, bottom sector)\n"); + break; + case FLASH_AMDL323T: + printf ("29DL323T (32 M, top sector)\n"); + break; + case FLASH_AMDL323B: + printf ("29DL323B (32 M, bottom sector)\n"); + break; + case FLASH_AM640U: + printf ("29LV640D (64 M, uniform sector)\n"); + break; + default: + printf ("Unknown Chip Type\n"); + break; + } + + printf (" Size: %ld MB in %d Sectors\n", + info->size >> 20, info->sector_count); + + printf (" Sector Start Addresses:"); + for (i = 0; i < info->sector_count; ++i) { + if ((i % 5) == 0) + printf ("\n "); + printf (" %08lX%s", + info->start[i], + info->protect[i] ? " (RO)" : " " + ); + } + printf ("\n"); + return; +} + +/*----------------------------------------------------------------------- + */ +int flash_erase (flash_info_t * info, int s_first, int s_last) +{ + int flag, prot, sect, l_sect; + ulong start, now, last; + + if ((s_first < 0) || (s_first > s_last)) { + if (info->flash_id == FLASH_UNKNOWN) { + printf ("- missing\n"); + } else { + printf ("- no sectors to erase\n"); + } + return 1; + } + + prot = 0; + for (sect = s_first; sect <= s_last; sect++) { + if (info->protect[sect]) + prot++; + } + + if (prot) { + printf ("- Warning: %d protected sectors will not be erased!\n", + prot); + } else { + printf ("\n"); + } + + l_sect = -1; + + /* Disable interrupts which might cause a timeout here */ + flag = disable_interrupts (); + + V_ULONG (info->start[0] + (0x0555 << 3)) = 0x00AA00AA; + V_ULONG (info->start[0] + (0x02AA << 3)) = 0x00550055; + V_ULONG (info->start[0] + (0x0555 << 3)) = 0x00800080; + V_ULONG (info->start[0] + (0x0555 << 3)) = 0x00AA00AA; + V_ULONG (info->start[0] + (0x02AA << 3)) = 0x00550055; + V_ULONG (info->start[0] + 4 + (0x0555 << 3)) = 0x00AA00AA; + V_ULONG (info->start[0] + 4 + (0x02AA << 3)) = 0x00550055; + V_ULONG (info->start[0] + 4 + (0x0555 << 3)) = 0x00800080; + V_ULONG (info->start[0] + 4 + (0x0555 << 3)) = 0x00AA00AA; + V_ULONG (info->start[0] + 4 + (0x02AA << 3)) = 0x00550055; + udelay (1000); + + /* Start erase on unprotected sectors */ + for (sect = s_first; sect <= s_last; sect++) { + if (info->protect[sect] == 0) { /* not protected */ + V_ULONG (info->start[sect]) = 0x00300030; + V_ULONG (info->start[sect] + 4) = 0x00300030; + l_sect = sect; + } + } + + /* re-enable interrupts if necessary */ + if (flag) + enable_interrupts (); + + /* wait at least 80us - let's wait 1 ms */ + udelay (1000); + + /* + * We wait for the last triggered sector + */ + if (l_sect < 0) + goto DONE; + + start = get_timer (0); + last = start; + while ((V_ULONG (info->start[l_sect]) & 0x00800080) != 0x00800080 || + (V_ULONG (info->start[l_sect] + 4) & 0x00800080) != 0x00800080) + { + if ((now = get_timer (start)) > CFG_FLASH_ERASE_TOUT) { + printf ("Timeout\n"); + return 1; + } + /* show that we're waiting */ + if ((now - last) > 1000) { /* every second */ + serial_putc ('.'); + last = now; + } + } + + DONE: + /* reset to read mode */ + flash_reset (); + + printf (" done\n"); + return 0; +} + +static int write_dword (flash_info_t *, ulong, unsigned char *); + +/*----------------------------------------------------------------------- + * Copy memory to flash, returns: + * 0 - OK + * 1 - write timeout + * 2 - Flash not erased + */ + +int write_buff (flash_info_t * info, uchar * src, ulong addr, ulong cnt) +{ + ulong dp; + static unsigned char bb[8]; + int i, l, rc, cc = cnt; + + dp = (addr & ~7); /* get lower dword aligned address */ + + /* + * handle unaligned start bytes + */ + if ((l = addr - dp) != 0) { + for (i = 0; i < 8; i++) + bb[i] = (i < l || (i - l) >= cc) ? V_BYTE (dp + i) : *src++; + if ((rc = write_dword (info, dp, bb)) != 0) { + return (rc); + } + dp += 8; + cc -= 8 - l; + } + + /* + * handle word aligned part + */ + while (cc >= 8) { + if ((rc = write_dword (info, dp, src)) != 0) { + return (rc); + } + dp += 8; + src += 8; + cc -= 8; + } + + if (cc <= 0) { + return (0); + } + + /* + * handle unaligned tail bytes + */ + for (i = 0; i < 8; i++) { + bb[i] = (i < cc) ? *src++ : V_BYTE (dp + i); + } + return (write_dword (info, dp, bb)); +} + +/*----------------------------------------------------------------------- + * Write a dword to Flash, returns: + * 0 - OK + * 1 - write timeout + * 2 - Flash not erased + */ +static int write_dword (flash_info_t * info, ulong dest, unsigned char *pdata) +{ + ulong start, cl, ch; + int flag, i; + + for (ch = 0, i = 0; i < 4; i++) + ch = (ch << 8) + *pdata++; /* high word */ + for (cl = 0, i = 0; i < 4; i++) + cl = (cl << 8) + *pdata++; /* low word */ + + /* Check if Flash is (sufficiently) erased */ + if ((*((vu_long *) dest) & ch) != ch + || (*((vu_long *) (dest + 4)) & cl) != cl) { + return (2); + } + + /* Disable interrupts which might cause a timeout here */ + flag = disable_interrupts (); + + V_ULONG (info->start[0] + (0x0555 << 3)) = 0x00AA00AA; + V_ULONG (info->start[0] + (0x02AA << 3)) = 0x00550055; + V_ULONG (info->start[0] + (0x0555 << 3)) = 0x00A000A0; + V_ULONG (dest) = ch; + V_ULONG (info->start[0] + 4 + (0x0555 << 3)) = 0x00AA00AA; + V_ULONG (info->start[0] + 4 + (0x02AA << 3)) = 0x00550055; + V_ULONG (info->start[0] + 4 + (0x0555 << 3)) = 0x00A000A0; + V_ULONG (dest + 4) = cl; + + /* re-enable interrupts if necessary */ + if (flag) + enable_interrupts (); + + /* data polling for D7 */ + start = get_timer (0); + while (((V_ULONG (dest) & 0x00800080) != (ch & 0x00800080)) || + ((V_ULONG (dest + 4) & 0x00800080) != (cl & 0x00800080))) { + if (get_timer (start) > CFG_FLASH_WRITE_TOUT) { + return (1); + } + } + return (0); +} diff --git a/board/siemens/SCM/fpga_scm.c b/board/siemens/SCM/fpga_scm.c new file mode 100755 index 0000000..661bf66 --- /dev/null +++ b/board/siemens/SCM/fpga_scm.c @@ -0,0 +1,104 @@ +/* + * (C) Copyright 2002 + * Wolfgang Grandegger, DENX Software Engineering, wg@denx.de. + * + * See file CREDITS for list of people who contributed to this + * project. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License as + * published by the Free Software Foundation; either version 2 of + * the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, + * MA 02111-1307 USA + */ + + +#include <common.h> +#include <mpc8260.h> +#include <common.h> +#include "../common/fpga.h" + +fpga_t fpga_list[] = { + {"FIOX", CFG_FIOX_BASE, + CFG_PD_FIOX_INIT, CFG_PD_FIOX_PROG, CFG_PD_FIOX_DONE} + , + {"FDOHM", CFG_FDOHM_BASE, + CFG_PD_FDOHM_INIT, CFG_PD_FDOHM_PROG, CFG_PD_FDOHM_DONE} +}; +int fpga_count = sizeof (fpga_list) / sizeof (fpga_t); + + +ulong fpga_control (fpga_t * fpga, int cmd) +{ + volatile immap_t *immr = (immap_t *) CFG_IMMR; + + switch (cmd) { + case FPGA_INIT_IS_HIGH: + immr->im_ioport.iop_pdird &= ~fpga->init_mask; /* input */ + return (immr->im_ioport.iop_pdatd & fpga->init_mask) ? 1 : 0; + + case FPGA_INIT_SET_LOW: + immr->im_ioport.iop_pdird |= fpga->init_mask; /* output */ + immr->im_ioport.iop_pdatd &= ~fpga->init_mask; + break; + + case FPGA_INIT_SET_HIGH: + immr->im_ioport.iop_pdird |= fpga->init_mask; /* output */ + immr->im_ioport.iop_pdatd |= fpga->init_mask; + break; + + case FPGA_PROG_SET_LOW: + immr->im_ioport.iop_pdatd &= ~fpga->prog_mask; + break; + + case FPGA_PROG_SET_HIGH: + immr->im_ioport.iop_pdatd |= fpga->prog_mask; + break; + + case FPGA_DONE_IS_HIGH: + return (immr->im_ioport.iop_pdatd & fpga->done_mask) ? 1 : 0; + + case FPGA_READ_MODE: + break; + + case FPGA_LOAD_MODE: + break; + + case FPGA_GET_ID: + if (fpga->conf_base == CFG_FIOX_BASE) { + ulong ver = + *(volatile ulong *) (fpga->conf_base + 0x10); + return ((ver >> 10) & 0xf) + ((ver >> 2) & 0xf0); + } else if (fpga->conf_base == CFG_FDOHM_BASE) { + return (*(volatile ushort *) fpga->conf_base) & 0xff; + } else { + return *(volatile ulong *) fpga->conf_base; + } + + case FPGA_INIT_PORTS: + immr->im_ioport.iop_ppard &= ~fpga->init_mask; /* INIT I/O */ + immr->im_ioport.iop_psord &= ~fpga->init_mask; + immr->im_ioport.iop_pdird &= ~fpga->init_mask; + + immr->im_ioport.iop_ppard &= ~fpga->prog_mask; /* PROG Output */ + immr->im_ioport.iop_psord &= ~fpga->prog_mask; + immr->im_ioport.iop_pdird |= fpga->prog_mask; + + immr->im_ioport.iop_ppard &= ~fpga->done_mask; /* DONE Input */ + immr->im_ioport.iop_psord &= ~fpga->done_mask; + immr->im_ioport.iop_pdird &= ~fpga->done_mask; + + break; + + } + return 0; +} diff --git a/board/siemens/SCM/scm.c b/board/siemens/SCM/scm.c new file mode 100755 index 0000000..d20688d --- /dev/null +++ b/board/siemens/SCM/scm.c @@ -0,0 +1,540 @@ +/* + * (C) Copyright 2001 + * Wolfgang Denk, DENX Software Engineering, wd@denx.de. + * + * See file CREDITS for list of people who contributed to this + * project. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License as + * published by the Free Software Foundation; either version 2 of + * the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, + * MA 02111-1307 USA + */ + +#include <common.h> +#include <ioports.h> +#include <mpc8260.h> + +#include "scm.h" + +static void config_scoh_cs(void); +extern int fpga_init(void); + +#if 0 +#define DEBUGF(fmt,args...) printf (fmt ,##args) +#else +#define DEBUGF(fmt,args...) +#endif + +/* + * I/O Port configuration table + * + * if conf is 1, then that port pin will be configured at boot time + * according to the five values podr/pdir/ppar/psor/pdat for that entry + */ + +const iop_conf_t iop_conf_tab[4][32] = { + + /* Port A configuration */ + { /* conf ppar psor pdir podr pdat */ + /* PA31 */ { 1, 1, 1, 0, 0, 0 }, /* FCC1 MII COL */ + /* PA30 */ { 1, 1, 1, 0, 0, 0 }, /* FCC1 MII CRS */ + /* PA29 */ { 1, 1, 1, 1, 0, 0 }, /* FCC1 MII TX_ER */ + /* PA28 */ { 1, 1, 1, 1, 0, 0 }, /* FCC1 MII TX_EN */ + /* PA27 */ { 1, 1, 1, 0, 0, 0 }, /* FCC1 MII RX_DV */ + /* PA26 */ { 1, 1, 1, 0, 0, 0 }, /* FCC1 MII RX_ER */ + /* PA25 */ { 0, 0, 0, 1, 0, 0 }, + /* PA24 */ { 0, 0, 0, 1, 0, 0 }, + /* PA23 */ { 0, 0, 0, 1, 0, 0 }, + /* PA22 */ { 0, 0, 0, 1, 0, 0 }, + /* PA21 */ { 1, 1, 0, 1, 0, 0 }, /* FCC1 MII TxD[3] */ + /* PA20 */ { 1, 1, 0, 1, 0, 0 }, /* FCC1 MII TxD[2] */ + /* PA19 */ { 1, 1, 0, 1, 0, 0 }, /* FCC1 MII TxD[1] */ + /* PA18 */ { 1, 1, 0, 1, 0, 0 }, /* FCC1 MII TxD[0] */ + /* PA17 */ { 1, 1, 0, 0, 0, 0 }, /* FCC1 MII RxD[0] */ + /* PA16 */ { 1, 1, 0, 0, 0, 0 }, /* FCC1 MII RxD[1]*/ + /* PA15 */ { 1, 1, 0, 0, 0, 0 }, /* FCC1 MII RxD[2] */ + /* PA14 */ { 1, 1, 0, 0, 0, 0 }, /* FCC1 MII RxD[3] */ + /* PA13 */ { 0, 0, 0, 1, 0, 0 }, + /* PA12 */ { 0, 0, 0, 1, 0, 0 }, + /* PA11 */ { 0, 0, 0, 1, 0, 0 }, + /* PA10 */ { 0, 0, 0, 1, 0, 0 }, + /* PA9 */ { 1, 1, 1, 1, 0, 0 }, /* TDM_A1 L1TXD0 */ + /* PA8 */ { 1, 1, 1, 0, 0, 0 }, /* TDM_A1 L1RXD0 */ + /* PA7 */ { 1, 1, 1, 0, 0, 0 }, /* TDM_A1 L1TSYNC */ + /* PA6 */ { 1, 1, 1, 0, 0, 0 }, /* TDM_A1 L1RSYNC */ + /* PA5 */ { 1, 0, 0, 0, 0, 0 }, /* FIOX_FPGA_PR */ + /* PA4 */ { 1, 0, 0, 0, 0, 0 }, /* DOHM_FPGA_PR */ + /* PA3 */ { 1, 1, 0, 0, 0, 0 }, /* TDM RXCLK4 */ + /* PA2 */ { 1, 1, 0, 0, 0, 0 }, /* TDM TXCLK4 */ + /* PA1 */ { 0, 0, 0, 1, 0, 0 }, + /* PA0 */ { 1, 0, 0, 0, 0, 0 } /* BUSY */ + }, + + /* Port B configuration */ + { /* conf ppar psor pdir podr pdat */ + /* PB31 */ { 1, 0, 0, 1, 0, 0 }, /* EQ_ALARM_MIN */ + /* PB30 */ { 1, 0, 0, 1, 0, 0 }, /* EQ_ALARM_MAJ */ + /* PB29 */ { 1, 0, 0, 1, 0, 0 }, /* COM_ALARM_MIN */ + /* PB28 */ { 1, 0, 0, 1, 0, 0 }, /* COM_ALARM_MAJ */ + /* PB27 */ { 0, 1, 0, 0, 0, 0 }, + /* PB26 */ { 0, 1, 0, 0, 0, 0 }, + /* PB25 */ { 1, 0, 0, 1, 0, 0 }, /* LED_GREEN_L */ + /* PB24 */ { 1, 0, 0, 1, 0, 0 }, /* LED_RED_L */ + /* PB23 */ { 1, 1, 1, 0, 0, 0 }, /* TDM_D2 L1TXD */ + /* PB22 */ { 1, 1, 1, 0, 0, 0 }, /* TDM_D2 L1RXD */ + /* PB21 */ { 1, 1, 1, 0, 0, 0 }, /* TDM_D2 L1TSYNC */ + /* PB20 */ { 1, 1, 1, 0, 0, 0 }, /* TDM_D2 L1RSYNC */ + /* PB19 */ { 1, 0, 0, 0, 0, 0 }, /* UID */ + /* PB18 */ { 0, 1, 0, 0, 0, 0 }, + /* PB17 */ { 1, 1, 0, 0, 0, 0 }, /* FCC3 MII RX_DV */ + /* PB16 */ { 1, 1, 0, 0, 0, 0 }, /* FCC3 MII RX_ER */ + /* PB15 */ { 1, 1, 0, 1, 0, 0 }, /* FCC3 MII TX_ER */ + /* PB14 */ { 1, 1, 0, 1, 0, 0 }, /* FCC3 MII TX_EN */ + /* PB13 */ { 1, 1, 0, 0, 0, 0 }, /* FCC3 MII COL */ + /* PB12 */ { 1, 1, 0, 0, 0, 0 }, /* FCC3 MII CRS */ + /* PB11 */ { 1, 1, 0, 0, 0, 0 }, /* FCC3 MII RxD[3] */ + /* PB10 */ { 1, 1, 0, 0, 0, 0 }, /* FCC3 MII RxD[2] */ + /* PB9 */ { 1, 1, 0, 0, 0, 0 }, /* FCC3 MII RxD[1] */ + /* PB8 */ { 1, 1, 0, 0, 0, 0 }, /* FCC3 MII RxD[0] */ + /* PB7 */ { 1, 1, 0, 1, 0, 0 }, /* FCC3 MII TxD[3] */ + /* PB6 */ { 1, 1, 0, 1, 0, 0 }, /* FCC3 MII TxD[2] */ + /* PB5 */ { 1, 1, 0, 1, 0, 0 }, /* FCC3 MII TxD[1] */ + /* PB4 */ { 1, 1, 0, 1, 0, 0 }, /* FCC3 MII TxD[0] */ + /* PB3 */ { 0, 0, 0, 0, 0, 0 }, /* pin doesn't exist */ + /* PB2 */ { 0, 0, 0, 0, 0, 0 }, /* pin doesn't exist */ + /* PB1 */ { 0, 0, 0, 0, 0, 0 }, /* pin doesn't exist */ + /* PB0 */ { 0, 0, 0, 0, 0, 0 } /* pin doesn't exist */ + }, + + /* Port C configuration */ + { /* conf ppar psor pdir podr pdat */ + /* PC31 */ { 1, 1, 0, 0, 0, 0 }, /* TDM RXCLK1 */ + /* PC30 */ { 1, 1, 0, 0, 0, 0 }, /* TDM TXCLK1 */ + /* PC29 */ { 1, 1, 0, 0, 0, 0 }, /* TDM RXCLK3 */ + /* PC28 */ { 1, 1, 0, 0, 0, 0 }, /* TDM TXCLK3 */ + /* PC27 */ { 1, 1, 0, 0, 0, 0 }, /* TDM RXCLK2 */ + /* PC26 */ { 1, 1, 0, 0, 0, 0 }, /* TDM TXCLK2 */ + /* PC25 */ { 0, 0, 0, 1, 0, 0 }, + /* PC24 */ { 0, 0, 0, 1, 0, 0 }, + /* PC23 */ { 0, 1, 0, 1, 0, 0 }, + /* PC22 */ { 0, 1, 0, 0, 0, 0 }, + /* PC21 */ { 1, 1, 0, 0, 0, 0 }, /* FCC1 MII TX_CLK */ + /* PC20 */ { 1, 1, 0, 0, 0, 0 }, /* FCC1 MII RX_CLK */ + /* PC19 */ { 0, 1, 0, 0, 0, 0 }, + /* PC18 */ { 0, 1, 0, 0, 0, 0 }, + /* PC17 */ { 1, 1, 0, 0, 0, 0 }, /* FCC3 MII RX_CLK */ + /* PC16 */ { 1, 1, 0, 0, 0, 0 }, /* FCC3 MII TX_CLK */ + /* PC15 */ { 0, 0, 0, 1, 0, 0 }, + /* PC14 */ { 0, 1, 0, 0, 0, 0 }, + /* PC13 */ { 0, 0, 0, 1, 0, 0 }, /* RES_PHY_L */ + /* PC12 */ { 0, 0, 0, 1, 0, 0 }, + /* PC11 */ { 0, 0, 0, 1, 0, 0 }, + /* PC10 */ { 0, 0, 0, 1, 0, 0 }, + /* PC9 */ { 0, 1, 1, 0, 0, 0 }, /* TDM_A2 L1TSYNC */ + /* PC8 */ { 0, 0, 0, 0, 0, 0 }, /* FEP_RDY */ + /* PC7 */ { 0, 0, 0, 0, 0, 0 }, + /* PC6 */ { 0, 0, 0, 0, 0, 0 }, /* UC4_ALARM_L */ + /* PC5 */ { 0, 0, 0, 0, 0, 0 }, /* UC3_ALARM_L */ + /* PC4 */ { 0, 0, 0, 0, 0, 0 }, /* UC2_ALARM_L */ + /* PC3 */ { 0, 0, 0, 1, 0, 0 }, /* RES_MISC_L */ + /* PC2 */ { 0, 0, 0, 1, 0, 0 }, /* RES_OH_L */ + /* PC1 */ { 0, 0, 0, 1, 0, 0 }, /* RES_DOHM_L */ + /* PC0 */ { 0, 0, 0, 1, 0, 0 }, /* RES_FIOX_L */ + }, + + /* Port D configuration */ + { /* conf ppar psor pdir podr pdat */ + /* PD31 */ { 1, 1, 0, 0, 0, 0 }, /* SCC1 EN RxD */ + /* PD30 */ { 1, 1, 1, 1, 0, 0 }, /* SCC1 EN TxD */ + /* PD29 */ { 0, 0, 0, 0, 0, 0 }, /* INIT_F */ + /* PD28 */ { 0, 0, 0, 1, 0, 0 }, /* DONE_F */ + /* PD27 */ { 0, 0, 0, 0, 0, 0 }, /* INIT_D */ + /* PD26 */ { 0, 0, 0, 1, 0, 0 }, /* DONE_D */ + /* PD25 */ { 0, 0, 0, 1, 0, 0 }, + /* PD24 */ { 0, 0, 0, 1, 0, 0 }, + /* PD23 */ { 0, 0, 0, 1, 0, 0 }, + /* PD22 */ { 1, 1, 1, 0, 0, 0 }, /* TDM_A2 L1TXD */ + /* PD21 */ { 1, 1, 1, 0, 0, 0 }, /* TDM_A2 L1RXD */ + /* PD20 */ { 1, 1, 1, 0, 0, 0 }, /* TDM_A2 L1RSYNC */ + /* PD19 */ { 1, 1, 1, 0, 0, 0 }, /* SPI SPISEL */ + /* PD18 */ { 1, 1, 1, 0, 0, 0 }, /* SPI SPICLK */ + /* PD17 */ { 1, 1, 1, 0, 0, 0 }, /* SPI SPIMOSI */ + /* PD16 */ { 1, 1, 1, 0, 0, 0 }, /* SPI SPIMOSO */ +#if defined(CONFIG_SOFT_I2C) + /* PD15 */ { 1, 0, 0, 1, 1, 1 }, /* I2C SDA */ + /* PD14 */ { 1, 0, 0, 1, 1, 1 }, /* I2C SCL */ +#else +#if defined(CONFIG_HARD_I2C) + /* PD15 */ { 1, 1, 1, 0, 1, 0 }, /* I2C SDA */ + /* PD14 */ { 1, 1, 1, 0, 1, 0 }, /* I2C SCL */ +#else /* normal I/O port pins */ + /* PD15 */ { 0, 1, 1, 0, 1, 0 }, /* I2C SDA */ + /* PD14 */ { 0, 1, 1, 0, 1, 0 }, /* I2C SCL */ +#endif +#endif + /* PD13 */ { 1, 1, 1, 0, 0, 0 }, /* TDM_B1 L1TXD */ + /* PD12 */ { 1, 1, 1, 0, 0, 0 }, /* TDM_B1 L1RXD */ + /* PD11 */ { 1, 1, 1, 0, 0, 0 }, /* TDM_B1 L1TSYNC */ + /* PD10 */ { 1, 1, 1, 0, 0, 0 }, /* TDM_B1 L1RSYNC */ + /* PD9 */ { 1, 1, 0, 1, 0, 0 }, /* SMC1 TXD */ + /* PD8 */ { 1, 1, 0, 0, 0, 0 }, /* SMC1 RXD */ + /* PD7 */ { 0, 0, 0, 1, 0, 1 }, + /* PD6 */ { 0, 0, 0, 1, 0, 1 }, + /* PD5 */ { 0, 0, 0, 1, 0, 0 }, /* PROG_F */ + /* PD4 */ { 0, 0, 0, 1, 0, 0 }, /* PROG_D */ + /* PD3 */ { 0, 0, 0, 0, 0, 0 }, /* pin doesn't exist */ + /* PD2 */ { 0, 0, 0, 0, 0, 0 }, /* pin doesn't exist */ + /* PD1 */ { 0, 0, 0, 0, 0, 0 }, /* pin doesn't exist */ + /* PD0 */ { 0, 0, 0, 0, 0, 0 } /* pin doesn't exist */ + } +}; + +/* ------------------------------------------------------------------------- */ + +/* Check Board Identity: + */ +int checkboard (void) +{ + char str[64]; + int i = getenv_r ("serial#", str, sizeof (str)); + + puts ("Board: "); + + if (!i || strncmp (str, "TQM8260", 7)) { + puts ("### No HW ID - assuming TQM8260\n"); + return (0); + } + + puts (str); + putc ('\n'); + + return 0; +} + +/* ------------------------------------------------------------------------- */ + +/* Try SDRAM initialization with P/LSDMR=sdmr and ORx=orx + * + * This routine performs standard 8260 initialization sequence + * and calculates the available memory size. It may be called + * several times to try different SDRAM configurations on both + * 60x and local buses. + */ +static long int try_init (volatile memctl8260_t * memctl, ulong sdmr, + ulong orx, volatile uchar * base) +{ + volatile uchar c = 0xff; + volatile uint *sdmr_ptr; + volatile uint *orx_ptr; + ulong maxsize, size; + int i; + + /* We must be able to test a location outsize the maximum legal size + * to find out THAT we are outside; but this address still has to be + * mapped by the controller. That means, that the initial mapping has + * to be (at least) twice as large as the maximum expected size. + */ + maxsize = (1 + (~orx | 0x7fff)) / 2; + + /* Since CFG_SDRAM_BASE is always 0 (??), we assume that + * we are configuring CS1 if base != 0 + */ + sdmr_ptr = base ? &memctl->memc_lsdmr : &memctl->memc_psdmr; + orx_ptr = base ? &memctl->memc_or2 : &memctl->memc_or1; + + *orx_ptr = orx; + + /* + * Quote from 8260 UM (10.4.2 SDRAM Power-On Initialization, 10-35): + * + * "At system reset, initialization software must set up the + * programmable parameters in the memory controller banks registers + * (ORx, BRx, P/LSDMR). After all memory parameters are configured, + * system software should execute the following initialization sequence + * for each SDRAM device. + * + * 1. Issue a PRECHARGE-ALL-BANKS command + * 2. Issue eight CBR REFRESH commands + * 3. Issue a MODE-SET command to initialize the mode register + * + * The initial commands are executed by setting P/LSDMR[OP] and + * accessing the SDRAM with a single-byte transaction." + * + * The appropriate BRx/ORx registers have already been set when we + * get here. The SDRAM can be accessed at the address CFG_SDRAM_BASE. + */ + + *sdmr_ptr = sdmr | PSDMR_OP_PREA; + *base = c; + + *sdmr_ptr = sdmr | PSDMR_OP_CBRR; + for (i = 0; i < 8; i++) + *base = c; + + *sdmr_ptr = sdmr | PSDMR_OP_MRW; + *(base + CFG_MRS_OFFS) = c; /* setting MR on address lines */ + + *sdmr_ptr = sdmr | PSDMR_OP_NORM | PSDMR_RFEN; + *base = c; + + size = get_ram_size((long *)base, maxsize); + + *orx_ptr = orx | ~(size - 1); + + return (size); +} + +/* + * Test Power-On-Reset. + */ +int power_on_reset (void) +{ + DECLARE_GLOBAL_DATA_PTR; + + /* Test Reset Status Register */ + return gd->reset_status & RSR_CSRS ? 0 : 1; +} + +long int initdram (int board_type) +{ + volatile immap_t *immap = (immap_t *) CFG_IMMR; + volatile memctl8260_t *memctl = &immap->im_memctl; + +#ifndef CFG_RAMBOOT + long size8, size9; +#endif + long psize, lsize; + + psize = 16 * 1024 * 1024; + lsize = 0; + + memctl->memc_psrt = CFG_PSRT; + memctl->memc_mptpr = CFG_MPTPR; + +#if 0 /* Just for debugging */ +#define prt_br_or(brX,orX) do { \ + ulong start = memctl->memc_ ## brX & 0xFFFF8000; \ + ulong sizem = ~memctl->memc_ ## orX | 0x00007FFF; \ + printf ("\n" \ + #brX " 0x%08x " #orX " 0x%08x " \ + "==> 0x%08lx ... 0x%08lx = %ld MB\n", \ + memctl->memc_ ## brX, memctl->memc_ ## orX, \ + start, start+sizem, (sizem+1)>>20); \ + } while (0) + prt_br_or (br0, or0); + prt_br_or (br1, or1); + prt_br_or (br2, or2); + prt_br_or (br3, or3); +#endif + +#ifndef CFG_RAMBOOT + /* 60x SDRAM setup: + */ + size8 = try_init (memctl, CFG_PSDMR_8COL, CFG_OR1_8COL, + (uchar *) CFG_SDRAM_BASE); + size9 = try_init (memctl, CFG_PSDMR_9COL, CFG_OR1_9COL, + (uchar *) CFG_SDRAM_BASE); + + if (size8 < size9) { + psize = size9; + printf ("(60x:9COL - %ld MB, ", psize >> 20); + } else { + psize = try_init (memctl, CFG_PSDMR_8COL, CFG_OR1_8COL, + (uchar *) CFG_SDRAM_BASE); + printf ("(60x:8COL - %ld MB, ", psize >> 20); + } + + /* Local SDRAM setup: + */ +#ifdef CFG_INIT_LOCAL_SDRAM + memctl->memc_lsrt = CFG_LSRT; + size8 = try_init (memctl, CFG_LSDMR_8COL, CFG_OR2_8COL, + (uchar *) SDRAM_BASE2_PRELIM); + size9 = try_init (memctl, CFG_LSDMR_9COL, CFG_OR2_9COL, + (uchar *) SDRAM_BASE2_PRELIM); + + if (size8 < size9) { + lsize = size9; + printf ("Local:9COL - %ld MB) using ", lsize >> 20); + } else { + lsize = try_init (memctl, CFG_LSDMR_8COL, CFG_OR2_8COL, + (uchar *) SDRAM_BASE2_PRELIM); + printf ("Local:8COL - %ld MB) using ", lsize >> 20); + } + +#if 0 + /* Set up BR2 so that the local SDRAM goes + * right after the 60x SDRAM + */ + memctl->memc_br2 = (CFG_BR2_PRELIM & ~BRx_BA_MSK) | + (CFG_SDRAM_BASE + psize); +#endif +#endif /* CFG_INIT_LOCAL_SDRAM */ +#endif /* CFG_RAMBOOT */ + + icache_enable (); + + config_scoh_cs (); + + return (psize); +} + +/* ------------------------------------------------------------------------- */ + +static void config_scoh_cs (void) +{ + volatile immap_t *immr = (immap_t *) CFG_IMMR; + volatile memctl8260_t *memctl = &immr->im_memctl; + volatile can_reg_t *can = (volatile can_reg_t *) CFG_CAN0_BASE; + volatile uint tmp, i; + + /* Initialize OR3 / BR3 for CAN Bus Controller 0 */ + memctl->memc_or3 = CFG_CAN0_OR3; + memctl->memc_br3 = CFG_CAN0_BR3; + /* Initialize OR4 / BR4 for CAN Bus Controller 1 */ + memctl->memc_or4 = CFG_CAN1_OR4; + memctl->memc_br4 = CFG_CAN1_BR4; + + /* Initialize MAMR to write in the array at address 0x0 */ + memctl->memc_mamr = 0x00 | MxMR_OP_WARR | MxMR_GPL_x4DIS; + + /* Initialize UPMA for CAN: single read */ + memctl->memc_mdr = 0xcffeec00; + udelay (1); /* Necessary to have the data correct in the UPM array!!!! */ + /* The read on the CAN controller write the data of mdr in UPMA array. */ + /* The index to the array will be incremented automatically + through this read */ + tmp = can->cpu_interface; + + memctl->memc_mdr = 0x0ffcec00; + udelay (1); + tmp = can->cpu_interface; + + memctl->memc_mdr = 0x0ffcec00; + udelay (1); + tmp = can->cpu_interface; + + memctl->memc_mdr = 0x0ffcec00; + udelay (1); + tmp = can->cpu_interface; + + memctl->memc_mdr = 0x0ffcec00; + udelay (1); + tmp = can->cpu_interface; + + memctl->memc_mdr = 0x0ffcfc00; + udelay (1); + tmp = can->cpu_interface; + + memctl->memc_mdr = 0x0ffcfc00; + udelay (1); + tmp = can->cpu_interface; + + memctl->memc_mdr = 0xfffdec07; + udelay (1); + tmp = can->cpu_interface; + + + /* Initialize MAMR to write in the array at address 0x18 */ + memctl->memc_mamr = 0x18 | MxMR_OP_WARR | MxMR_GPL_x4DIS; + + /* Initialize UPMA for CAN: single write */ + memctl->memc_mdr = 0xfcffec00; + udelay (1); + tmp = can->cpu_interface; + + memctl->memc_mdr = 0x00ffec00; + udelay (1); + tmp = can->cpu_interface; + + memctl->memc_mdr = 0x00ffec00; + udelay (1); + tmp = can->cpu_interface; + + memctl->memc_mdr = 0x00ffec00; + udelay (1); + tmp = can->cpu_interface; + + memctl->memc_mdr = 0x00ffec00; + udelay (1); + tmp = can->cpu_interface; + + memctl->memc_mdr = 0x00fffc00; + udelay (1); + tmp = can->cpu_interface; + + memctl->memc_mdr = 0x00fffc00; + udelay (1); + tmp = can->cpu_interface; + + memctl->memc_mdr = 0x30ffec07; + udelay (1); + tmp = can->cpu_interface; + + /* Initialize MAMR */ + memctl->memc_mamr = MxMR_GPL_x4DIS; /* GPL_B4 ouput line Disable */ + + + /* Initialize OR5 / BR5 for the extended EEPROM Bank0 */ + memctl->memc_or5 = CFG_EXTPROM_OR5; + memctl->memc_br5 = CFG_EXTPROM_BR5; + /* Initialize OR6 / BR6 for the extended EEPROM Bank1 */ + memctl->memc_or6 = CFG_EXTPROM_OR6; + memctl->memc_br6 = CFG_EXTPROM_BR6; + + /* Initialize OR7 / BR7 for the Glue Logic */ + memctl->memc_or7 = CFG_FIOX_OR7; + memctl->memc_br7 = CFG_FIOX_BR7; + + /* Initialize OR8 / BR8 for the DOH Logic */ + memctl->memc_or8 = CFG_FDOHM_OR8; + memctl->memc_br8 = CFG_FDOHM_BR8; + + DEBUGF ("OR0 %08x BR0 %08x\n", memctl->memc_or0, memctl->memc_br0); + DEBUGF ("OR1 %08x BR1 %08x\n", memctl->memc_or1, memctl->memc_br1); + DEBUGF ("OR2 %08x BR2 %08x\n", memctl->memc_or2, memctl->memc_br2); + DEBUGF ("OR3 %08x BR3 %08x\n", memctl->memc_or3, memctl->memc_br3); + DEBUGF ("OR4 %08x BR4 %08x\n", memctl->memc_or4, memctl->memc_br4); + DEBUGF ("OR5 %08x BR5 %08x\n", memctl->memc_or5, memctl->memc_br5); + DEBUGF ("OR6 %08x BR6 %08x\n", memctl->memc_or6, memctl->memc_br6); + DEBUGF ("OR7 %08x BR7 %08x\n", memctl->memc_or7, memctl->memc_br7); + DEBUGF ("OR8 %08x BR8 %08x\n", memctl->memc_or8, memctl->memc_br8); + + DEBUGF ("UPMA addr 0x0\n"); + memctl->memc_mamr = 0x00 | MxMR_OP_RARR | MxMR_GPL_x4DIS; + for (i = 0; i < 0x8; i++) { + tmp = can->cpu_interface; + udelay (1); + DEBUGF (" %08x ", memctl->memc_mdr); + } + DEBUGF ("\nUPMA addr 0x18\n"); + memctl->memc_mamr = 0x18 | MxMR_OP_RARR | MxMR_GPL_x4DIS; + for (i = 0; i < 0x8; i++) { + tmp = can->cpu_interface; + udelay (1); + DEBUGF (" %08x ", memctl->memc_mdr); + } + DEBUGF ("\n"); + memctl->memc_mamr = MxMR_GPL_x4DIS; +} + +/* ------------------------------------------------------------------------- */ + +int misc_init_r (void) +{ + fpga_init (); + return (0); +} + +/* ------------------------------------------------------------------------- */ diff --git a/board/siemens/SCM/scm.h b/board/siemens/SCM/scm.h new file mode 100755 index 0000000..70c12e6 --- /dev/null +++ b/board/siemens/SCM/scm.h @@ -0,0 +1,87 @@ +/* + * (C) Copyright 2001 + * Wolfgang Denk, DENX Software Engineering, wd@denx.de. + * + * See file CREDITS for list of people who contributed to this + * project. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License as + * published by the Free Software Foundation; either version 2 of + * the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, + * MA 02111-1307 USA + */ + +#ifndef __SCM_H +#define __SCM_H + +/*----------------*/ +/* CAN Structures */ +/*----------------*/ + +/* Message */ +typedef struct can_msg { + uchar ctrl_0; + uchar ctrl_1; + uchar arbit_0; + uchar arbit_1; + uchar arbit_2; + uchar arbit_3; + uchar config; + uchar data[8]; +} can_msg_t; + +/* CAN Register */ +typedef struct can_reg { + uchar ctrl; + uchar status; + uchar cpu_interface; + uchar resv0; + ushort high_speed_rd; + ushort gbl_mask_std; + uint gbl_mask_extd; + uint msg15_mask; + can_msg_t msg1 __attribute__ ((packed)); + uchar clkout; + can_msg_t msg2 __attribute__ ((packed)); + uchar bus_config; + can_msg_t msg3 __attribute__ ((packed)); + uchar bit_timing_0; + can_msg_t msg4 __attribute__ ((packed)); + uchar bit_timing_1; + can_msg_t msg5 __attribute__ ((packed)); + uchar interrupt; + can_msg_t msg6 __attribute__ ((packed)); + uchar resv1; + can_msg_t msg7 __attribute__ ((packed)); + uchar resv2; + can_msg_t msg8 __attribute__ ((packed)); + uchar resv3; + can_msg_t msg9 __attribute__ ((packed)); + uchar p1conf; + can_msg_t msg10 __attribute__ ((packed)); + uchar p2conf; + can_msg_t msg11 __attribute__ ((packed)); + uchar p1in; + can_msg_t msg12 __attribute__ ((packed)); + uchar p2in; + can_msg_t msg13 __attribute__ ((packed)); + uchar p1out; + can_msg_t msg14 __attribute__ ((packed)); + uchar p2out; + can_msg_t msg15 __attribute__ ((packed)); + uchar ser_res_addr; + uchar resv_cs[0x8000-0x100]; /* 0x8000 is the min size for CS */ +} can_reg_t; + + +#endif /* __SCM_H */ diff --git a/board/siemens/SCM/u-boot.lds b/board/siemens/SCM/u-boot.lds new file mode 100755 index 0000000..05f29c6 --- /dev/null +++ b/board/siemens/SCM/u-boot.lds @@ -0,0 +1,126 @@ +/* + * (C) Copyright 2001 + * Wolfgang Denk, DENX Software Engineering, wd@denx.de. + * + * See file CREDITS for list of people who contributed to this + * project. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License as + * published by the Free Software Foundation; either version 2 of + * the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, + * MA 02111-1307 USA + */ + +OUTPUT_ARCH(powerpc) +SEARCH_DIR(/lib); SEARCH_DIR(/usr/lib); SEARCH_DIR(/usr/local/lib); SEARCH_DIR(/usr/local/powerpc-any-elf/lib); +/* Do we need any of these for elf? + __DYNAMIC = 0; */ +SECTIONS +{ + /* Read-only sections, merged into text segment: */ + . = + SIZEOF_HEADERS; + .interp : { *(.interp) } + .hash : { *(.hash) } + .dynsym : { *(.dynsym) } + .dynstr : { *(.dynstr) } + .rel.text : { *(.rel.text) } + .rela.text : { *(.rela.text) } + .rel.data : { *(.rel.data) } + .rela.data : { *(.rela.data) } + .rel.rodata : { *(.rel.rodata) } + .rela.rodata : { *(.rela.rodata) } + .rel.got : { *(.rel.got) } + .rela.got : { *(.rela.got) } + .rel.ctors : { *(.rel.ctors) } + .rela.ctors : { *(.rela.ctors) } + .rel.dtors : { *(.rel.dtors) } + .rela.dtors : { *(.rela.dtors) } + .rel.bss : { *(.rel.bss) } + .rela.bss : { *(.rela.bss) } + .rel.plt : { *(.rel.plt) } + .rela.plt : { *(.rela.plt) } + .init : { *(.init) } + .plt : { *(.plt) } + .text : + { + cpu/mpc8260/start.o (.text) + *(.text) + common/environment.o(.text) + *(.fixup) + *(.got1) + . = ALIGN(16); + *(.rodata) + *(.rodata1) + *(.rodata.str1.4) + *(.eh_frame) + } + .fini : { *(.fini) } =0 + .ctors : { *(.ctors) } + .dtors : { *(.dtors) } + + /* Read-write section, merged into data segment: */ + . = (. + 0x0FFF) & 0xFFFFF000; + _erotext = .; + PROVIDE (erotext = .); + .reloc : + { + *(.got) + _GOT2_TABLE_ = .; + *(.got2) + _FIXUP_TABLE_ = .; + *(.fixup) + } + __got2_entries = (_FIXUP_TABLE_ - _GOT2_TABLE_) >> 2; + __fixup_entries = (. - _FIXUP_TABLE_) >> 2; + + .data : + { + *(.data) + *(.data1) + *(.sdata) + *(.sdata2) + *(.dynamic) + CONSTRUCTORS + } + _edata = .; + PROVIDE (edata = .); + + . = .; + __u_boot_cmd_start = .; + .u_boot_cmd : { *(.u_boot_cmd) } + __u_boot_cmd_end = .; + + + . = .; + __start___ex_table = .; + __ex_table : { *(__ex_table) } + __stop___ex_table = .; + + . = ALIGN(4096); + __init_begin = .; + .text.init : { *(.text.init) } + .data.init : { *(.data.init) } + . = ALIGN(4096); + __init_end = .; + + __bss_start = .; + .bss : + { + *(.sbss) *(.scommon) + *(.dynbss) + *(.bss) + *(COMMON) + } + _end = . ; + PROVIDE (end = .); +} |