From 74f4304ee717d0f4b3a27e7fd4a64944749b8783 Mon Sep 17 00:00:00 2001 From: Wolfgang Denk Date: Sun, 25 Sep 2005 01:48:28 +0200 Subject: [PATCH] Add ARM946E cpu and core module targets; remap memory to 0x00000000 Patch by Peter Pearse, 2 Feb 2005 --- CHANGELOG | 3 + MAKEALL | 32 ++- Makefile | 175 ++++++++++++- board/integratorap/Makefile | 3 +- board/integratorap/integratorap.c | 137 ++++++++++ board/integratorap/memsetup.S | 30 +++ board/integratorap/platform.S | 12 + board/integratorcp/Makefile | 2 +- board/integratorcp/integratorcp.c | 185 +++++++++++++- board/integratorcp/memsetup.S | 30 +++ board/integratorcp/platform.S | 185 +++++++++++++- cpu/arm920t/cpu.c | 16 +- cpu/arm920t/interrupts.c | 8 +- cpu/arm926ejs/cpu.c | 13 +- cpu/arm926ejs/interrupts.c | 21 +- cpu/arm926ejs/start.S | 10 +- cpu/arm946es/Makefile | 44 ++++ cpu/arm946es/config.mk | 27 ++ cpu/arm946es/cpu.c | 164 ++++++++++++ cpu/arm946es/interrupts.c | 292 +++++++++++++++++++++ cpu/arm946es/start.S | 409 ++++++++++++++++++++++++++++++ cpu/arm_intcm/Makefile | 43 ++++ cpu/arm_intcm/config.mk | 27 ++ cpu/arm_intcm/cpu.c | 91 +++++++ cpu/arm_intcm/interrupts.c | 192 ++++++++++++++ cpu/arm_intcm/start.S | 370 +++++++++++++++++++++++++++ doc/README-integrator | 66 +++++ include/arm946es.h | 8 + include/configs/integratorap.h | 49 +++- include/configs/integratorcp.h | 102 ++++++-- 30 files changed, 2666 insertions(+), 80 deletions(-) create mode 100644 board/integratorap/memsetup.S create mode 100644 board/integratorcp/memsetup.S create mode 100644 cpu/arm946es/Makefile create mode 100644 cpu/arm946es/config.mk create mode 100644 cpu/arm946es/cpu.c create mode 100644 cpu/arm946es/interrupts.c create mode 100644 cpu/arm946es/start.S create mode 100644 cpu/arm_intcm/Makefile create mode 100644 cpu/arm_intcm/config.mk create mode 100644 cpu/arm_intcm/cpu.c create mode 100644 cpu/arm_intcm/interrupts.c create mode 100644 cpu/arm_intcm/start.S create mode 100644 doc/README-integrator create mode 100644 include/arm946es.h diff --git a/CHANGELOG b/CHANGELOG index 6c5c15c68..d0bef3005 100644 --- a/CHANGELOG +++ b/CHANGELOG @@ -2,6 +2,9 @@ Changes for U-Boot 1.1.4: ====================================================================== +* Add ARM946E cpu and core module targets; remap memory to 0x00000000 + Patch by Peter Pearse, 2 Feb 2005 + * Fix error handling in tools/env/fw_env.c Patch by Ara Avanesyan, 01 Feb 2005 diff --git a/MAKEALL b/MAKEALL index e146cd5bd..14bc37deb 100755 --- a/MAKEALL +++ b/MAKEALL @@ -160,24 +160,44 @@ LIST_SA="assabet dnp1110 gcplus lart shannon" ## ARM7 Systems ######################################################################### -LIST_ARM7="B2 ep7312 evb4510 impa7 modnet50" +LIST_ARM7=" \ + B2 ep7312 evb4510 impa7 \ + integratorap_CM720T integratorap_CM7TDMI \ + modnet50 \ +" ######################################################################### ## ARM9 Systems ######################################################################### LIST_ARM9=" \ - at91rm9200dk cmc_pu2 integratorcp integratorap \ + at91rm9200dk cmc_pu2 \ + integratorap_CM920T integratorap_CM920T_ETM \ + integratorap_CM922T_XA10 integratorap_CM926EJ_S \ + integratorap_CM940T integratorap_CM946E_S \ + integratorap_CM966E_S integratorcp_CM920T \ + integratorcp_CM920T_ETM integratorcp_CM922T_XA10 \ + integratorcp_CM926EJ_S integratorcp_CM940T \ + integratorcp_CM946E_S integratorcp_CM966E_S \ lpd7a400 mx1ads mx1fs2 omap1510inn \ omap1610h2 omap1610inn omap730p2 scb9328 \ smdk2400 smdk2410 trab VCMA9 \ versatile voiceblue \ " +######################################################################### +## ARM10 Systems +######################################################################### +LIST_ARM10=" \ + integratorcp_CM10220E integratorcp_CM1026EJ_S \ +" + ######################################################################### ## ARM11 Systems ######################################################################### -LIST_ARM11="omap2420h4" +LIST_ARM11=" \ + integratorcp_CM1136JF_S omap2420h4 \ +" ######################################################################### ## Xscale Systems @@ -186,7 +206,7 @@ LIST_ARM11="omap2420h4" LIST_pxa=" \ adsvix cerf250 cradle csb226 \ innokom lubbock wepep250 xaeniax \ - xm250 xsengine \ + xm250 xsengine \ " LIST_ixp="ixdp425" @@ -194,7 +214,7 @@ LIST_ixp="ixdp425" LIST_arm=" \ ${LIST_SA} \ - ${LIST_ARM7} ${LIST_ARM9} ${LIST_ARM11} \ + ${LIST_ARM7} ${LIST_ARM9} ${LIST_ARM10} ${LIST_ARM11} \ ${LIST_pxa} ${LIST_ixp} \ " @@ -276,7 +296,7 @@ for arg in $@ do case "$arg" in ppc|5xx|5xxx|8xx|8220|824x|8260|83xx|85xx|4xx|7xx|74xx| \ - arm|SA|ARM7|ARM9|ARM11|pxa|ixp| \ + arm|SA|ARM7|ARM9|ARM10|ARM11|pxa|ixp| \ microblaze| \ mips|mips_el| \ nios|nios2| \ diff --git a/Makefile b/Makefile index c43cb2e83..26fc73d85 100644 --- a/Makefile +++ b/Makefile @@ -1387,11 +1387,178 @@ at91rm9200dk_config : unconfig cmc_pu2_config : unconfig @./mkconfig $(@:_config=) arm arm920t cmc_pu2 NULL at91rm9200 -integratorap_config : unconfig - @./mkconfig $(@:_config=) arm arm926ejs integratorap +######################################################################## +## ARM Integrator boards +## There are two variants /AP && /CP +## - many different core modules (CMs) can be used +## - some share characteristics +## Those without specific cpu support can still use U-Boot +## provided the ARM boot monitor (or similar) runs before U-Boot +## to set up the platform e.g. map writeable memory to 0x00000000 +## setup MMU, setup caches etc. +## Ported cores are:- +## ARM926EJ-S +## ARM946E-S +## +######################################################################## +xtract_int_board = $(subst _$(subst integrator$1_,,$(subst _config,,$2)),,$(subst _config,,$2)) +xtract_int_cm = $(subst integrator$1_,,$(subst _config,,$2)) +######################################################################### +## Integrator/AP +######################################################################### +integratorap_config : unconfig + @echo -n "/* Integrator configuration implied " > tmp.fil; \ + echo " by Makefile target */" >> tmp.fil; \ + echo >> tmp.fil + @echo -n "#define CONFIG_INTEGRATOR 1" >> tmp.fil; \ + echo " /* Integrator board */" >> tmp.fil; \ + echo -n "#define CONFIG_ARCH_INTEGRATOR" >> tmp.fil; \ + echo " 1 /* Integrator/AP */" >> tmp.fil; \ + echo "/* Core module not defined */" >> tmp.fil; \ + echo -n "#define CONFIG_ARM_INTCM 1" >> tmp.fil; \ + echo -n " /* Integrator core module " >> tmp.fil; \ + echo "with unknown core */" >> tmp.fil; \ + cpu=arm_intcm; \ + mv tmp.fil ./include/config.h; \ + ubootlds=board/integratorap/u-boot.lds; \ + sed -e 's/cpu\/.*\/st/cpu\/'$$cpu'\/st/' \ + $$ubootlds > $$ubootlds.tmp; \ + mv -f $$ubootlds.tmp $$ubootlds; \ + ./mkconfig -a integratorap arm arm_intcm integratorap; -integratorcp_config : unconfig - @./mkconfig $(@:_config=) arm arm926ejs integratorcp +integratorap_CM720T_config integratorap_CM7TDMI_config \ +integratorap_CM920T_config integratorap_CM920T_ETM_config \ +integratorap_CM922T_XA10_config integratorap_CM926EJ_S_config \ +integratorap_CM940T_config integratorap_CM946E_S_config \ +integratorap_CM966E_S_config integratorap_CM10200E_config \ +integratorap_CM10220E_config integratorap_CM1026EJ_S_config \ +integratorap_CM1136JF_S_config : unconfig + @echo -n "/* Integrator configuration implied " > tmp.fil; \ + echo " by Makefile target */" >> tmp.fil; \ + echo >> tmp.fil + @echo -n "#define CONFIG_INTEGRATOR 1" >> tmp.fil; \ + echo " /* Integrator board */" >> tmp.fil; \ + echo -n "#define CONFIG_ARCH_INTEGRATOR" >> tmp.fil; \ + echo " 1 /* Integrator/AP */" >> tmp.fil; \ + cm=$(call xtract_int_cm,ap,$@); \ + echo -n "#define CONFIG_$$cm " >> tmp.fil; \ + echo " /* core module */" >> tmp.fil; \ + case $$cm in \ + CM920T) \ + echo -n "#define CONFIG_ARM920" >> tmp.fil; \ + echo -n "T 1 /* CPU" >> tmp.fil; \ + echo -n " core is ARM920T" >> tmp.fil; \ + echo " */" >> tmp.fil; \ + cpu=arm920t;; \ + CM926EJ_S) echo -n "#define CONFIG_ARM926" >> tmp.fil; \ + echo -n "EJ_S 1 /* CPU" >> tmp.fil; \ + echo -n " core is ARM926EJ-S" >> tmp.fil; \ + echo " */" >> tmp.fil; \ + cpu=arm926ejs;; \ + CM946E_S) echo -n "#define CONFIG_ARM946" >> tmp.fil; \ + echo -n "E_S 1 /* CPU" >> tmp.fil; \ + echo -n " core is ARM946E-S" >> tmp.fil; \ + echo " */" >> tmp.fil; \ + cpu=arm946es;; \ + *) echo -n "#define CONFIG_ARM_IN" >> tmp.fil; \ + echo -n "TCM 1 /* Int" >> tmp.fil; \ + echo -n "egrator core module w" >> tmp.fil; \ + echo -n "ith unported core" >> tmp.fil; \ + echo " */" >> tmp.fil; \ + cpu=arm_intcm;; \ + esac; \ + mv tmp.fil ./include/config.h; \ + ubootlds=board/$(call xtract_int_board,ap,$@)/u-boot.lds; \ + sed -e 's/cpu\/.*\/st/cpu\/'$$cpu'\/st/' \ + $$ubootlds > $$ubootlds.tmp; \ + mv -f $$ubootlds.tmp $$ubootlds; \ + ./mkconfig -a $(call xtract_int_board,ap,$@) arm $$cpu \ + $(call xtract_int_board,ap,$@); + +######################################################################### +## Integrator/CP +######################################################################### +integratorcp_config : unconfig + @echo -n "/* Integrator configuration implied " > tmp.fil; \ + echo " by Makefile target */" >> tmp.fil; \ + echo >> tmp.fil + @echo -n "#define CONFIG_INTEGRATOR 1" >> tmp.fil; \ + echo " /* Integrator board */" >> tmp.fil; \ + echo -n "#define CONFIG_ARCH_CINTEGRATOR" >> tmp.fil; \ + echo " 1 /* Integrator/CP */" >> tmp.fil; \ + echo "/* Core module not defined */" >> tmp.fil; \ + echo -n "#define CONFIG_ARM_INTCM 1" >> tmp.fil; \ + echo -n " /* Integrator core module " >> tmp.fil; \ + echo "with unknown core */" >> tmp.fil; \ + cpu=arm_intcm; \ + echo -n "#undef CONFIG_CM_MULTIPLE_SSRAM" >> tmp.fil; \ + echo -n " /* CM may not have " >> tmp.fil; \ + echo "multiple SSRAM mapping */" >> tmp.fil; \ + echo -n "#undef CONFIG_CM_SPD_DETECT " >> tmp.fil; \ + echo -n " /* CM may not support SPD " >> tmp.fil; \ + echo "query */" >> tmp.fil; \ + echo -n "#undef CONFIG_CM_REMAP " >> tmp.fil; \ + echo -n " /* CM may not support " >> tmp.fil; \ + echo "remapping */" >> tmp.fil; \ + echo -n "#undef CONFIG_CM_INIT " >> tmp.fil; \ + echo -n " /* CM may not have " >> tmp.fil; \ + echo "initialization reg */" >> tmp.fil; \ + echo -n "#undef CONFIG_CM_TCRAM " >> tmp.fil; \ + echo -n " /* CM may not have TCRAM */" >> tmp.fil; \ + mv tmp.fil ./include/config.h; \ + ubootlds=board/integratorcp/u-boot.lds; \ + sed -e 's/cpu\/.*\/st/cpu\/'$$cpu'\/st/' \ + $$ubootlds > $$ubootlds.tmp; \ + mv -f $$ubootlds.tmp $$ubootlds; \ + ./mkconfig -a integratorcp arm arm_intcm integratorcp; + +integratorcp_CM920T_config integratorcp_CM920T_ETM_config \ +integratorcp_CM922T_XA10_config integratorcp_CM926EJ_S_config \ +integratorcp_CM940T_config integratorcp_CM946E_S_config \ +integratorcp_CM966E_S_config integratorcp_CM10200E_config \ +integratorcp_CM10220E_config integratorcp_CM1026EJ_S_config \ +integratorcp_CM1136JF_S_config : unconfig + @echo -n "/* Integrator configuration implied " > tmp.fil; \ + echo " by Makefile target */" >> tmp.fil; \ + echo >> tmp.fil + @echo -n "#define CONFIG_INTEGRATOR 1" >> tmp.fil; \ + echo " /* Integrator board */" >> tmp.fil; \ + echo -n "#define CONFIG_ARCH_CINTEGRATOR" >> tmp.fil; \ + echo " 1 /* Integrator/CP */" >> tmp.fil; \ + cm=$(call xtract_int_cm,cp,$@); \ + echo -n "#define CONFIG_$$cm " >> tmp.fil; \ + echo " /* core module */" >> tmp.fil; \ + echo "/* $$cm core module */" >> tmp.fil; \ + case $$cm in \ + CM920T) echo -n "#define CONFIG_ARM920" >> tmp.fil; \ + echo -n "T 1 /* CPU" >> tmp.fil; \ + echo -n " core is ARM920T" >> tmp.fil; \ + echo " */" >> tmp.fil; \ + cpu=arm920t;; \ + CM946E_S) echo -n "#define CONFIG_ARM946" >> tmp.fil; \ + echo -n "E_S 1 /* CPU" >> tmp.fil; \ + echo -n " core is ARM946E-S" >> tmp.fil; \ + echo " */" >> tmp.fil; \ + cpu=arm946es;; \ + CM926EJ_S) echo -n "#define CONFIG_ARM926" >> tmp.fil; \ + echo -n "EJ_S 1 /* CPU" >> tmp.fil; \ + echo -n " core is ARM926EJ-S" >> tmp.fil; \ + echo " */" >> tmp.fil; \ + cpu=arm926ejs;; \ + *) echo -n "#define CONFIG_ARM_IN" >> tmp.fil; \ + echo -n "TCM 1 /* Int" >> tmp.fil; \ + echo -n "egrator core module w" >> tmp.fil; \ + echo -n "ith unported core" >> tmp.fil; \ + echo " */" >> tmp.fil; \ + cpu=arm_intcm;; \ + esac; \ + mv tmp.fil ./include/config.h; \ + ubootlds=board/$(call xtract_int_board,cp,$@)/u-boot.lds; \ + sed -e 's/cpu\/.*\/st/cpu\/'$$cpu'\/st/' \ + $$ubootlds > $$ubootlds.tmp; \ + mv -f $$ubootlds.tmp $$ubootlds; \ + ./mkconfig -a $(call xtract_int_board,cp,$@) arm $$cpu \ + $(call xtract_int_board,cp,$@); lpd7a400_config \ lpd7a404_config: unconfig diff --git a/board/integratorap/Makefile b/board/integratorap/Makefile index 00336aa77..154d1afed 100644 --- a/board/integratorap/Makefile +++ b/board/integratorap/Makefile @@ -30,7 +30,7 @@ include $(TOPDIR)/config.mk LIB = lib$(BOARD).a OBJS := integratorap.o flash.o -SOBJS := platform.o +SOBJS := platform.o memsetup.o $(LIB): $(OBJS) $(SOBJS) $(AR) crv $@ $^ @@ -49,3 +49,4 @@ distclean: clean -include .depend ######################################################################### + diff --git a/board/integratorap/integratorap.c b/board/integratorap/integratorap.c index fb83c82c1..6140a7a14 100644 --- a/board/integratorap/integratorap.c +++ b/board/integratorap/integratorap.c @@ -477,3 +477,140 @@ int dram_init (void) { return 0; } + +/* The Integrator/AP timer1 is clocked at 24MHz + * can be divided by 16 or 256 + * and is a 16-bit counter + */ +/* U-Boot expects a 32 bit timer running at CFG_HZ*/ +static ulong timestamp; /* U-Boot ticks since startup */ +static ulong total_count = 0; /* Total timer count */ +static ulong lastdec; /* Timer reading at last call */ +static ulong div_clock = 256; /* Divisor applied to the timer clock */ +static ulong div_timer = 1; /* Divisor to convert timer reading + * change to U-Boot ticks + */ +/* CFG_HZ = CFG_HZ_CLOCK/(div_clock * div_timer) */ + +#define TIMER_LOAD_VAL 0x0000FFFFL +#define READ_TIMER ((*(volatile ulong *)(CFG_TIMERBASE+4)) & 0x0000FFFFL) + +/* all function return values in U-Boot ticks i.e. (1/CFG_HZ) sec + * - unless otherwise stated + */ + +/* starts a counter + * - the Integrator/AP timer issues an interrupt + * each time it reaches zero + */ +int interrupt_init (void) +{ + /* Load timer with initial value */ + *(volatile ulong *)(CFG_TIMERBASE + 0) = TIMER_LOAD_VAL; + /* Set timer to be + * enabled 1 + * free-running 0 + * XX 00 + * divider 256 10 + * XX 00 + */ + *(volatile ulong *)(CFG_TIMERBASE + 8) = 0x00000088; + total_count = 0; + /* init the timestamp and lastdec value */ + reset_timer_masked(); + + div_timer = CFG_HZ_CLOCK / CFG_HZ; + div_timer /= div_clock; + + return (0); +} + +/* + * timer without interrupts + */ +void reset_timer (void) +{ + reset_timer_masked (); +} + +ulong get_timer (ulong base_ticks) +{ + return get_timer_masked () - base_ticks; +} + +void set_timer (ulong ticks) +{ + timestamp = ticks; + total_count = ticks * div_timer; + reset_timer_masked(); +} + +/* delay x useconds */ +void udelay (unsigned long usec) +{ + ulong tmo, tmp; + + /* Convert to U-Boot ticks */ + tmo = usec * CFG_HZ; + tmo /= (1000000L); + + tmp = get_timer_masked(); /* get current timestamp */ + tmo += tmp; /* wake up timestamp */ + + while (get_timer_masked () < tmo)/* loop till event */ + { + /*NOP*/; + } +} + +void reset_timer_masked (void) +{ + /* reset time */ + lastdec = READ_TIMER; /* capture current decrementer value */ + timestamp = 0; /* start "advancing" time stamp from 0 */ +} + +/* converts the timer reading to U-Boot ticks */ +/* the timestamp is the number of ticks since reset */ +/* This routine does not detect wraps unless called regularly + ASSUMES a call at least every 16 seconds to detect every reload */ +ulong get_timer_masked (void) +{ + ulong now = READ_TIMER; /* current count */ + + if(now > lastdec) + { + /* Must have wrapped */ + total_count += lastdec + TIMER_LOAD_VAL + 1 - now; + } else { + total_count += lastdec - now; + } + lastdec = now; + timestamp = total_count/div_timer; + + return timestamp; +} + +/* waits specified delay value and resets timestamp */ +void udelay_masked (unsigned long usec) +{ + udelay(usec); +} + +/* + * This function is derived from PowerPC code (read timebase as long long). + * On ARM it just returns the timer value. + */ +unsigned long long get_ticks(void) +{ + return get_timer(0); +} + +/* + * Return the timebase clock frequency + * i.e. how often the timer decrements + */ +ulong get_tbclk (void) +{ + return CFG_HZ_CLOCK/div_clock; +} diff --git a/board/integratorap/memsetup.S b/board/integratorap/memsetup.S new file mode 100644 index 000000000..bdf6af988 --- /dev/null +++ b/board/integratorap/memsetup.S @@ -0,0 +1,30 @@ +/* + * Memory setup for integratorAP + * + * 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 + */ +/* + * Memory setup + * - the reset defaults are assumed sufficient + */ + +.globl memsetup +memsetup: + mov pc,lr + diff --git a/board/integratorap/platform.S b/board/integratorap/platform.S index 480e040cd..e9b07178f 100644 --- a/board/integratorap/platform.S +++ b/board/integratorap/platform.S @@ -31,3 +31,15 @@ platformsetup: /* All done by Integrator's boot monitor! */ mov pc, lr + + /* Reset using CM control register */ +.global reset_cpu +reset_cpu: + mov r0, #CM_BASE + ldr r1,[r0,#OS_CTRL] + orr r1,r1,#CMMASK_RESET + str r1,[r0] + +reset_failed: + b reset_failed + diff --git a/board/integratorcp/Makefile b/board/integratorcp/Makefile index 9c97237e5..71532d113 100644 --- a/board/integratorcp/Makefile +++ b/board/integratorcp/Makefile @@ -26,7 +26,7 @@ include $(TOPDIR)/config.mk LIB = lib$(BOARD).a OBJS := integratorcp.o flash.o -SOBJS := platform.o +SOBJS := platform.o memsetup.o $(LIB): $(OBJS) $(SOBJS) $(AR) crv $@ $^ diff --git a/board/integratorcp/integratorcp.c b/board/integratorcp/integratorcp.c index 6fe8f05ba..db833f0c6 100644 --- a/board/integratorcp/integratorcp.c +++ b/board/integratorcp/integratorcp.c @@ -42,19 +42,12 @@ void peripheral_power_enable (void); #if defined(CONFIG_SHOW_BOOT_PROGRESS) void show_boot_progress(int progress) { - printf("Boot reached stage %d\n", progress); + printf("Boot reached stage %d\n", progress); } #endif #define COMP_MODE_ENABLE ((unsigned int)0x0000EAEF) -static inline void delay (unsigned long loops) -{ - __asm__ volatile ("1:\n" - "subs %0, %1, #1\n" - "bne 1b":"=r" (loops):"0" (loops)); -} - /* * Miscellaneous platform dependent initialisations */ @@ -71,6 +64,11 @@ int board_init (void) gd->flags = 0; +#ifdef CONFIG_CM_REMAP +extern void cm_remap(void); + cm_remap(); /* remaps writeable memory to 0x00000000 */ +#endif + icache_enable (); flash__init (); @@ -95,7 +93,7 @@ void flash__init (void) /************************************************************* Routine:ether__init Description: take the Ethernet controller out of reset and wait - for the EEPROM load to complete. + for the EEPROM load to complete. *************************************************************/ void ether__init (void) { @@ -107,5 +105,174 @@ void ether__init (void) ******************************/ int dram_init (void) { + DECLARE_GLOBAL_DATA_PTR; + + gd->bd->bi_dram[0].start = PHYS_SDRAM_1; + gd->bd->bi_dram[0].size = PHYS_SDRAM_1_SIZE; + +#ifdef CONFIG_CM_SPD_DETECT + { +extern void dram_query(void); + unsigned long cm_reg_sdram; + unsigned long sdram_shift; + + dram_query(); /* Assembler accesses to CM registers */ + /* Queries the SPD values */ + + /* Obtain the SDRAM size from the CM SDRAM register */ + + cm_reg_sdram = *(volatile ulong *)(CM_BASE + OS_SDRAM); + /* Register SDRAM size + * + * 0xXXXXXXbbb000bb 16 MB + * 0xXXXXXXbbb001bb 32 MB + * 0xXXXXXXbbb010bb 64 MB + * 0xXXXXXXbbb011bb 128 MB + * 0xXXXXXXbbb100bb 256 MB + * + */ + sdram_shift = ((cm_reg_sdram & 0x0000001C)/4)%4; + gd->bd->bi_dram[0].size = 0x01000000 << sdram_shift; + + } +#endif /* CM_SPD_DETECT */ + return 0; } + +/* The Integrator/CP timer1 is clocked at 1MHz + * can be divided by 16 or 256 + * and can be set up as a 32-bit timer + */ +/* U-Boot expects a 32 bit timer, running at CFG_HZ */ +/* Keep total timer count to avoid losing decrements < div_timer */ +static unsigned long long total_count = 0; +static unsigned long long lastdec; /* Timer reading at last call */ +static unsigned long long div_clock = 1; /* Divisor applied to timer clock */ +static unsigned long long div_timer = 1; /* Divisor to convert timer reading + * change to U-Boot ticks + */ +/* CFG_HZ = CFG_HZ_CLOCK/(div_clock * div_timer) */ +static ulong timestamp; /* U-Boot ticks since startup */ + +#define TIMER_LOAD_VAL ((ulong)0xFFFFFFFF) +#define READ_TIMER (*(volatile ulong *)(CFG_TIMERBASE+4)) + +/* all function return values in U-Boot ticks i.e. (1/CFG_HZ) sec + * - unless otherwise stated + */ + +/* starts up a counter + * - the Integrator/CP timer can be set up to issue an interrupt */ +int interrupt_init (void) +{ + /* Load timer with initial value */ + *(volatile ulong *)(CFG_TIMERBASE + 0) = TIMER_LOAD_VAL; + /* Set timer to be + * enabled 1 + * periodic 1 + * no interrupts 0 + * X 0 + * divider 1 00 == less rounding error + * 32 bit 1 + * wrapping 0 + */ + *(volatile ulong *)(CFG_TIMERBASE + 8) = 0x000000C2; + /* init the timestamp */ + total_count = 0ULL; + reset_timer_masked(); + + div_timer = (unsigned long long)(CFG_HZ_CLOCK / CFG_HZ); + div_timer /= div_clock; + + return (0); +} + +/* + * timer without interrupts + */ +void reset_timer (void) +{ + reset_timer_masked (); +} + +ulong get_timer (ulong base_ticks) +{ + return get_timer_masked () - base_ticks; +} + +void set_timer (ulong ticks) +{ + timestamp = ticks; + total_count = (unsigned long long)ticks * div_timer; +} + +/* delay usec useconds */ +void udelay (unsigned long usec) +{ + ulong tmo, tmp; + + /* Convert to U-Boot ticks */ + tmo = usec * CFG_HZ; + tmo /= (1000000L); + + tmp = get_timer_masked(); /* get current timestamp */ + tmo += tmp; /* form target timestamp */ + + while (get_timer_masked () < tmo)/* loop till event */ + { + /*NOP*/; + } +} + +void reset_timer_masked (void) +{ + /* capure current decrementer value */ + lastdec = (unsigned long long)READ_TIMER; + /* start "advancing" time stamp from 0 */ + timestamp = 0L; +} + +/* converts the timer reading to U-Boot ticks */ +/* the timestamp is the number of ticks since reset */ +ulong get_timer_masked (void) +{ + /* get current count */ + unsigned long long now = (unsigned long long)READ_TIMER; + + if(now > lastdec) + { + /* Must have wrapped */ + total_count += lastdec + TIMER_LOAD_VAL + 1 - now; + } else { + total_count += lastdec - now; + } + lastdec = now; + timestamp = (ulong)(total_count/div_timer); + + return timestamp; +} + +/* waits specified delay value and resets timestamp */ +void udelay_masked (unsigned long usec) +{ + udelay(usec); +} + +/* + * This function is derived from PowerPC code (read timebase as long long). + * On ARM it just returns the timer value. + */ +unsigned long long get_ticks(void) +{ + return (unsigned long long)get_timer(0); +} + +/* + * Return the timebase clock frequency + * i.e. how often the timer decrements + */ +ulong get_tbclk (void) +{ + return (ulong)(((unsigned long long)CFG_HZ_CLOCK)/div_clock); +} diff --git a/board/integratorcp/memsetup.S b/board/integratorcp/memsetup.S new file mode 100644 index 000000000..bdf6af988 --- /dev/null +++ b/board/integratorcp/memsetup.S @@ -0,0 +1,30 @@ +/* + * Memory setup for integratorAP + * + * 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 + */ +/* + * Memory setup + * - the reset defaults are assumed sufficient + */ + +.globl memsetup +memsetup: + mov pc,lr + diff --git a/board/integratorcp/platform.S b/board/integratorcp/platform.S index c02051b50..73d6922dd 100644 --- a/board/integratorcp/platform.S +++ b/board/integratorcp/platform.S @@ -26,8 +26,189 @@ #include #include +/* Reset using CM control register */ +.global reset_cpu +reset_cpu: + mov r0, #CM_BASE + ldr r1,[r0,#OS_CTRL] + orr r1,r1,#CMMASK_RESET + str r1,[r0] + +reset_failed: + b reset_failed + +/* set up the platform, once the cpu has been initialized */ .globl platformsetup platformsetup: + /* If U-Boot has been run after the ARM boot monitor + * then all the necessary actions have been done + * otherwise we are running from user flash mapped to 0x00000000 + * --- DO NOT REMAP BEFORE THE CODE HAS BEEN RELOCATED -- + * Changes to the (possibly soft) reset defaults of the processor + * itself should be performed in cpu/arm<>/start.S + * This function affects only the core module or board settings + */ + +#ifdef CONFIG_CM_INIT + /* CM has an initialization register + * - bits in it are wired into test-chip pins to force + * reset defaults + * - may need to change its contents for U-Boot + */ + + /* set the desired CM specific value */ + mov r2,#CMMASK_LOWVEC /* Vectors at 0x00000000 for all */ + +#if defined (CONFIG_CM10200E) || defined (CONFIG_CM10220E) + orr r2,r2,#CMMASK_INIT_102 +#else + +#if !defined (CONFIG_CM920T) && !defined (CONFIG_CM920T_ETM) && \ + !defined (CONFIG_CM940T) + +#ifdef CONFIG_CM_MULTIPLE_SSRAM + /* set simple mapping */ + and r2,r2,#CMMASK_MAP_SIMPLE +#endif /* #ifdef CONFIG_CM_MULTIPLE_SSRAM */ + +#ifdef CONFIG_CM_TCRAM + /* disable TCRAM */ + and r2,r2,#CMMASK_TCRAM_DISABLE +#endif /* #ifdef CONFIG_CM_TCRAM */ + +#if defined (CONFIG_CM926EJ_S) || defined (CONFIG_CM1026EJ_S) || \ + defined (CONFIG_CM1136JF_S) + + and r2,r2,#CMMASK_LE + +#endif /* cpu with little endian initialization */ + + orr r2,r2,#CMMASK_CMxx6_COMMON + +#endif /* CMxx6 code */ + +#endif /* ARM102xxE value */ + + /* read CM_INIT */ + mov r0, #CM_BASE + ldr r1, [r0, #OS_INIT] + /* check against desired bit setting */ + and r3,r1,r2 + cmp r3,r2 + beq init_reg_OK + + /* lock for change */ + mov r3, #CMVAL_LOCK + and r3,r3,#CMMASK_LOCK + str r3, [r0, #OS_LOCK] + /* set desired value */ + orr r1,r1,r2 + /* write & relock CM_INIT */ + str r1, [r0, #OS_INIT] + mov r1, #CMVAL_UNLOCK + str r1, [r0, #OS_LOCK] + + /* soft reset so new values used */ + b reset_cpu + +init_reg_OK: + +#endif /* CONFIG_CM_INIT */ + + mov pc, lr + +#ifdef CONFIG_CM_SPD_DETECT + /* Fast memory is available for the DRAM data + * - ensure it has been transferred, then summarize the data + * into a CM register + */ +.globl dram_query +dram_query: + stmfd r13!,{r4-r6,lr} + /* set up SDRAM info */ + /* - based on example code from the CM User Guide */ + mov r0, #CM_BASE + +readspdbit: + ldr r1, [r0, #OS_SDRAM] /* read the SDRAM register */ + and r1, r1, #0x20 /* mask SPD bit (5) */ + cmp r1, #0x20 /* test if set */ + bne readspdbit + +setupsdram: + add r0, r0, #OS_SPD /* address the copy of the SDP data */ + ldrb r1, [r0, #3] /* number of row address lines */ + ldrb r2, [r0, #4] /* number of column address lines */ + ldrb r3, [r0, #5] /* number of banks */ + ldrb r4, [r0, #31] /* module bank density */ + mul r5, r4, r3 /* size of SDRAM (MB divided by 4) */ + mov r5, r5, ASL#2 /* size in MB */ + mov r0, #CM_BASE /* reload for later code */ + cmp r5, #0x10 /* is it 16MB? */ + bne not16 + mov r6, #0x2 /* store size and CAS latency of 2 */ + b writesize + +not16: + cmp r5, #0x20 /* is it 32MB? */ + bne not32 + mov r6, #0x6 + b writesize + +not32: + cmp r5, #0x40 /* is it 64MB? */ + bne not64 + mov r6, #0xa + b writesize + +not64: + cmp r5, #0x80 /* is it 128MB? */ + bne not128 + mov r6, #0xe + b writesize + +not128: + /* if it is none of these sizes then it is either 256MB, or + * there is no SDRAM fitted so default to 256MB + */ + mov r6, #0x12 + +writesize: + mov r1, r1, ASL#8 /* row addr lines from SDRAM reg */ + orr r2, r1, r2, ASL#12 /* OR in column address lines */ + orr r3, r2, r3, ASL#16 /* OR in number of banks */ + orr r6, r6, r3 /* OR in size and CAS latency */ + str r6, [r0, #OS_SDRAM] /* store SDRAM parameters */ + +#endif /* #ifdef CONFIG_CM_SPD_DETECT */ + + ldmfd r13!,{r4-r6,pc} /* back to caller */ + +#ifdef CONFIG_CM_REMAP + /* CM remap bit is operational + * - use it to map writeable memory at 0x00000000, in place of flash + */ +.globl cm_remap +cm_remap: + stmfd r13!,{r4-r10,lr} + + mov r0, #CM_BASE + ldr r1, [r0, #OS_CTRL] + orr r1, r1, #CMMASK_REMAP /* set remap and led bits */ + str r1, [r0, #OS_CTRL] + + /* Now 0x00000000 is writeable, replace the vectors */ + ldr r0, =_start /* r0 <- start of vectors */ + ldr r2, =_armboot_start /* r2 <- past vectors */ + sub r1,r1,r1 /* destination 0x00000000 */ + +copy_vec: + ldmia r0!, {r3-r10} /* copy from source address [r0] */ + stmia r1!, {r3-r10} /* copy to target address [r1] */ + cmp r0, r2 /* until source end address [r2] */ + ble copy_vec + + ldmfd r13!,{r4-r10,pc} /* back to caller */ + +#endif /* #ifdef CONFIG_CM_REMAP */ - /* All done by IntegratorCP's boot monitor! */ - mov pc, lr diff --git a/cpu/arm920t/cpu.c b/cpu/arm920t/cpu.c index 718f25347..2f7963dcf 100644 --- a/cpu/arm920t/cpu.c +++ b/cpu/arm920t/cpu.c @@ -39,7 +39,7 @@ static unsigned long read_p15_c1 (void) unsigned long value; __asm__ __volatile__( - "mrc p15, 0, %0, c1, c0, 0 @ read control reg\n" + "mrc p15, 0, %0, c1, c0, 0 @ read control reg\n" : "=r" (value) : : "memory"); @@ -57,7 +57,7 @@ static void write_p15_c1 (unsigned long value) printf ("write %08lx to p15/c1\n", value); #endif __asm__ __volatile__( - "mcr p15, 0, %0, c1, c0, 0 @ write it back\n" + "mcr p15, 0, %0, c1, c0, 0 @ write it back\n" : : "r" (value) : "memory"); @@ -73,16 +73,17 @@ static void cp_delay (void) for (i = 0; i < 100; i++); } -/* See also ARM Ref. Man. */ +/* See also ARM920T Technical reference Manual */ #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_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_HIGH_VECTORS (1<<13) /* location of vectors: low/high addresses */ -#define RESERVED_1 (0xf << 3) /* must be 111b for R/W */ +#define C1_HIGH_VECTORS (1<<13) /* location of vectors: low/high addresses */ + int cpu_init (void) { @@ -119,6 +120,7 @@ int cleanup_before_linux (void) /* flush I/D-cache */ i = 0; asm ("mcr p15, 0, %0, c7, c7, 0": :"r" (i)); + return (0); } @@ -134,7 +136,7 @@ void icache_enable (void) { ulong reg; - reg = read_p15_c1 (); + reg = read_p15_c1 (); /* get control reg. */ cp_delay (); write_p15_c1 (reg | C1_IC); } diff --git a/cpu/arm920t/interrupts.c b/cpu/arm920t/interrupts.c index bfab51964..1d254c76d 100644 --- a/cpu/arm920t/interrupts.c +++ b/cpu/arm920t/interrupts.c @@ -30,7 +30,6 @@ */ #include - #include #include @@ -162,7 +161,14 @@ void do_fiq (struct pt_regs *pt_regs) void do_irq (struct pt_regs *pt_regs) { +#if defined (CONFIG_USE_IRQ) && defined (CONFIG_ARCH_INTEGRATOR) + /* ASSUMED to be a timer interrupt */ + /* Just clear it - count handled in */ + /* integratorap.c */ + *(volatile ulong *)(CFG_TIMERBASE + 0x0C) = 0; +#else printf ("interrupt request\n"); show_regs (pt_regs); bad_mode (); +#endif } diff --git a/cpu/arm926ejs/cpu.c b/cpu/arm926ejs/cpu.c index 2681f999c..f57c5a5d8 100644 --- a/cpu/arm926ejs/cpu.c +++ b/cpu/arm926ejs/cpu.c @@ -69,21 +69,21 @@ static void cp_delay (void) { volatile int i; - /* Many OMAP regs need at least 2 nops */ + /* copro seems to need some delay between reading and writing */ for (i = 0; i < 100; i++); } -/* See also ARM Ref. Man. */ +/* See also ARM926EJ-S Technical Reference Manual */ #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_WB (1<<3) /* merging write buffer on/off */ -#define C1_BIG_ENDIAN (1<<7) /* big endian 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_HIGH_VECTORS (1<<13) /* location of vectors: low/high addresses */ -#define RESERVED_1 (0xf << 3) /* must be 111b for R/W */ +#define C1_HIGH_VECTORS (1<<13) /* location of vectors: low/high addresses */ + int cpu_init (void) { @@ -120,6 +120,7 @@ int cleanup_before_linux (void) /* flush I/D-cache */ i = 0; asm ("mcr p15, 0, %0, c7, c7, 0": :"r" (i)); + return (0); } diff --git a/cpu/arm926ejs/interrupts.c b/cpu/arm926ejs/interrupts.c index ae8082d5c..0457bff96 100644 --- a/cpu/arm926ejs/interrupts.c +++ b/cpu/arm926ejs/interrupts.c @@ -36,8 +36,7 @@ */ #include -#include - +#include #include #define TIMER_LOAD_VAL 0xffffffff @@ -46,9 +45,6 @@ #ifdef CONFIG_OMAP #define READ_TIMER (*(volatile ulong *)(CFG_TIMERBASE+8)) #endif -#ifdef CONFIG_INTEGRATOR -#define READ_TIMER (*(volatile ulong *)(CFG_TIMERBASE+4)) -#endif #ifdef CONFIG_VERSATILE #define READ_TIMER (*(volatile ulong *)(CFG_TIMERBASE+4)) #endif @@ -186,6 +182,12 @@ void do_irq (struct pt_regs *pt_regs) bad_mode (); } +#ifdef CONFIG_INTEGRATOR + + /* Timer functionality supplied by Integrator board (AP or CP) */ + +#else + static ulong timestamp; static ulong lastdec; @@ -200,12 +202,7 @@ int interrupt_init (void) val = MPUTIM_ST | MPUTIM_AR | MPUTIM_CLOCK_ENABLE | (CFG_PVT << MPUTIM_PTV_BIT); *((int32_t *) (CFG_TIMERBASE + CNTL_TIMER)) = val; #endif /* CONFIG_OMAP */ -#ifdef CONFIG_INTEGRATOR - /* Load timer with initial value */ - *(volatile ulong *)(CFG_TIMERBASE + 0) = TIMER_LOAD_VAL; - /* Set timer to be enabled, free-running, no interrupts, 256 divider */ - *(volatile ulong *)(CFG_TIMERBASE + 8) = 0x8C; -#endif /* CONFIG_INTEGRATOR */ + #ifdef CONFIG_VERSATILE *(volatile ulong *)(CFG_TIMERBASE + 0) = CFG_TIMER_RELOAD; /* TimerLoad */ *(volatile ulong *)(CFG_TIMERBASE + 4) = CFG_TIMER_RELOAD; /* TimerValue */ @@ -332,3 +329,5 @@ ulong get_tbclk (void) tbclk = CFG_HZ; return tbclk; } + +#endif /* CONFIG_INTEGRATOR */ diff --git a/cpu/arm926ejs/start.S b/cpu/arm926ejs/start.S index d62940b07..dfa6e7fa3 100644 --- a/cpu/arm926ejs/start.S +++ b/cpu/arm926ejs/start.S @@ -393,6 +393,12 @@ fiq: #endif +# ifdef CONFIG_INTEGRATOR + + /* Satisfied by Integrator routine (AP or CP) */ + +#else + .align 5 .globl reset_cpu reset_cpu: @@ -404,6 +410,8 @@ reset_cpu: _loop_forever: b _loop_forever - rstctl1: .word 0xfffece10 + +#endif /* #ifdef CONFIG_INTEGRATOR */ + diff --git a/cpu/arm946es/Makefile b/cpu/arm946es/Makefile new file mode 100644 index 000000000..9a0e21795 --- /dev/null +++ b/cpu/arm946es/Makefile @@ -0,0 +1,44 @@ +# +# (C) Copyright 2000-2003 +# 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$(CPU).a + +START = start.o +OBJS = interrupts.o cpu.o + +all: .depend $(START) $(LIB) + +$(LIB): $(OBJS) + $(AR) crv $@ $(OBJS) + +######################################################################### + +.depend: Makefile $(START:.o=.S) $(OBJS:.o=.c) + $(CC) -M $(CFLAGS) $(START:.o=.S) $(OBJS:.o=.c) > $@ + +sinclude .depend + +######################################################################### + diff --git a/cpu/arm946es/config.mk b/cpu/arm946es/config.mk new file mode 100644 index 000000000..81ca2885e --- /dev/null +++ b/cpu/arm946es/config.mk @@ -0,0 +1,27 @@ +# +# (C) Copyright 2002 +# Gary Jennejohn, DENX Software Engineering, +# +# 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 +# + +PLATFORM_RELFLAGS += -fno-strict-aliasing -fno-common -ffixed-r8 \ + -msoft-float + +PLATFORM_CPPFLAGS += -march=armv4 diff --git a/cpu/arm946es/cpu.c b/cpu/arm946es/cpu.c new file mode 100644 index 000000000..ea75fe230 --- /dev/null +++ b/cpu/arm946es/cpu.c @@ -0,0 +1,164 @@ +/* + * (C) Copyright 2002 + * Sysgo Real-Time Solutions, GmbH + * Marius Groeger + * + * (C) Copyright 2002 + * Gary Jennejohn, DENX Software Engineering, + * + * 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 + */ + +/* + * CPU specific code + */ + +#include +#include +#include + +/* 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"); + +#ifdef MMU_DEBUG + printf ("p15/c1 is = %08lx\n", value); +#endif + return value; +} + +/* write to co-processor 15, register #1 (control register) */ +static void write_p15_c1 (unsigned long value) +{ +#ifdef MMU_DEBUG + 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 (); +} + +static void cp_delay (void) +{ + volatile int i; + + /* copro seems to need some delay between reading and writing */ + for (i = 0; i < 100; i++); +} + +/* See also ARM946E-S Technical Reference Manual */ +#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_HIGH_VECTORS (1<<13) /* location of vectors: low/high addresses */ + + +int cpu_init (void) +{ + /* + * setup up stacks if necessary + */ +#ifdef CONFIG_USE_IRQ + DECLARE_GLOBAL_DATA_PTR; + + IRQ_STACK_START = _armboot_start - CFG_MALLOC_LEN - CFG_GBL_DATA_SIZE - 4; + FIQ_STACK_START = IRQ_STACK_START - CONFIG_STACKSIZE_IRQ; +#endif + return 0; +} + +int cleanup_before_linux (void) +{ + /* + * this function is called just before we call linux + * it prepares the processor for linux + * + * we turn off caches etc ... + */ + + unsigned long i; + + disable_interrupts (); + + /* ARM926E-S needs the protection unit enabled for the icache to have + * been enabled - left for possible later use + * should turn off the protection unit as well.... + */ + /* 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, c5, 0": :"r" (i)); + asm ("mcr p15, 0, %0, c7, c6, 0": :"r" (i)); + return (0); +} + +int do_reset (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]) +{ + extern void reset_cpu (ulong addr); + + disable_interrupts (); + reset_cpu (0); + /*NOTREACHED*/ + return (0); +} +/* ARM926E-S needs the protection unit enabled for this to have any effect + - left for possible later use */ +void icache_enable (void) +{ + ulong reg; + + reg = read_p15_c1 (); /* get control reg. */ + cp_delay (); + write_p15_c1 (reg | C1_IC); +} + +void icache_disable (void) +{ + ulong reg; + + reg = read_p15_c1 (); + cp_delay (); + write_p15_c1 (reg & ~C1_IC); +} + +int icache_status (void) +{ + return (read_p15_c1 () & C1_IC) != 0; +} + diff --git a/cpu/arm946es/interrupts.c b/cpu/arm946es/interrupts.c new file mode 100644 index 000000000..5728c3a44 --- /dev/null +++ b/cpu/arm946es/interrupts.c @@ -0,0 +1,292 @@ +/* + * (C) Copyright 2003 + * Texas Instruments + * + * (C) Copyright 2002 + * Sysgo Real-Time Solutions, GmbH + * Marius Groeger + * + * (C) Copyright 2002 + * Sysgo Real-Time Solutions, GmbH + * Alex Zuepke + * + * (C) Copyright 2002-2004 + * Gary Jennejohn, DENX Software Engineering, + * + * (C) Copyright 2004 + * Philippe Robin, ARM Ltd. + * + * 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 +#include +#include + +#define TIMER_LOAD_VAL 0xffffffff +extern void reset_cpu(ulong addr); + +#ifdef CONFIG_USE_IRQ +/* enable IRQ interrupts */ +void enable_interrupts (void) +{ + unsigned long temp; + __asm__ __volatile__("mrs %0, cpsr\n" + "bic %0, %0, #0x80\n" + "msr cpsr_c, %0" + : "=r" (temp) + : + : "memory"); +} + + +/* + * disable IRQ/FIQ interrupts + * returns true if interrupts had been enabled before we disabled them + */ +int disable_interrupts (void) +{ + unsigned long old,temp; + __asm__ __volatile__("mrs %0, cpsr\n" + "orr %1, %0, #0xc0\n" + "msr cpsr_c, %1" + : "=r" (old), "=r" (temp) + : + : "memory"); + return (old & 0x80) == 0; +} +#else +void enable_interrupts (void) +{ + return; +} +int disable_interrupts (void) +{ + return 0; +} +#endif + + +void bad_mode (void) +{ + panic ("Resetting CPU ...\n"); + reset_cpu (0); +} + +void show_regs (struct pt_regs *regs) +{ + unsigned long flags; + const char *processor_modes[] = { + "USER_26", "FIQ_26", "IRQ_26", "SVC_26", + "UK4_26", "UK5_26", "UK6_26", "UK7_26", + "UK8_26", "UK9_26", "UK10_26", "UK11_26", + "UK12_26", "UK13_26", "UK14_26", "UK15_26", + "USER_32", "FIQ_32", "IRQ_32", "SVC_32", + "UK4_32", "UK5_32", "UK6_32", "ABT_32", + "UK8_32", "UK9_32", "UK10_32", "UND_32", + "UK12_32", "UK13_32", "UK14_32", "SYS_32", + }; + + flags = condition_codes (regs); + + printf ("pc : [<%08lx>] lr : [<%08lx>]\n" + "sp : %08lx ip : %08lx fp : %08lx\n", + instruction_pointer (regs), + regs->ARM_lr, regs->ARM_sp, regs->ARM_ip, regs->ARM_fp); + printf ("r10: %08lx r9 : %08lx r8 : %08lx\n", + regs->ARM_r10, regs->ARM_r9, regs->ARM_r8); + printf ("r7 : %08lx r6 : %08lx r5 : %08lx r4 : %08lx\n", + regs->ARM_r7, regs->ARM_r6, regs->ARM_r5, regs->ARM_r4); + printf ("r3 : %08lx r2 : %08lx r1 : %08lx r0 : %08lx\n", + regs->ARM_r3, regs->ARM_r2, regs->ARM_r1, regs->ARM_r0); + printf ("Flags: %c%c%c%c", + flags & CC_N_BIT ? 'N' : 'n', + flags & CC_Z_BIT ? 'Z' : 'z', + flags & CC_C_BIT ? 'C' : 'c', flags & CC_V_BIT ? 'V' : 'v'); + printf (" IRQs %s FIQs %s Mode %s%s\n", + interrupts_enabled (regs) ? "on" : "off", + fast_interrupts_enabled (regs) ? "on" : "off", + processor_modes[processor_mode (regs)], + thumb_mode (regs) ? " (T)" : ""); +} + +void do_undefined_instruction (struct pt_regs *pt_regs) +{ + printf ("undefined instruction\n"); + show_regs (pt_regs); + bad_mode (); +} + +void do_software_interrupt (struct pt_regs *pt_regs) +{ + printf ("software interrupt\n"); + show_regs (pt_regs); + bad_mode (); +} + +void do_prefetch_abort (struct pt_regs *pt_regs) +{ + printf ("prefetch abort\n"); + show_regs (pt_regs); + bad_mode (); +} + +void do_data_abort (struct pt_regs *pt_regs) +{ + printf ("data abort\n"); + show_regs (pt_regs); + bad_mode (); +} + +void do_not_used (struct pt_regs *pt_regs) +{ + printf ("not used\n"); + show_regs (pt_regs); + bad_mode (); +} + +void do_fiq (struct pt_regs *pt_regs) +{ + printf ("fast interrupt request\n"); + show_regs (pt_regs); + bad_mode (); +} + +void do_irq (struct pt_regs *pt_regs) +{ + printf ("interrupt request\n"); + show_regs (pt_regs); + bad_mode (); +} + +#ifdef CONFIG_INTEGRATOR + /* Timer functionality supplied by Integrator board (AP or CP) */ +#else + +static ulong timestamp; +static ulong lastdec; + +/* nothing really to do with interrupts, just starts up a counter. */ +int interrupt_init (void) +{ + /* init the timestamp and lastdec value */ + reset_timer_masked(); + + return (0); +} + +/* + * timer without interrupts + */ + +void reset_timer (void) +{ + reset_timer_masked (); +} + +ulong get_timer (ulong base) +{ + return get_timer_masked () - base; +} + +void set_timer (ulong t) +{ + timestamp = t; +} + +/* delay x useconds AND perserve advance timstamp value */ +void udelay(unsigned long usec) +{ + udelay_masked(usec); +} + +void reset_timer_masked (void) +{ + /* reset time */ + lastdec = READ_TIMER; /* capure current decrementer value time */ + timestamp = 0; /* start "advancing" time stamp from 0 */ +} + +ulong get_timer_raw (void) +{ + ulong now = READ_TIMER; /* current tick value */ + + if (lastdec >= now) { /* normal mode (non roll) */ + /* normal mode */ + timestamp += lastdec - now; /* move stamp fordward with absoulte diff ticks */ + } else { /* we have overflow of the count down timer */ + /* nts = ts + ld + (TLV - now) + * ts=old stamp, ld=time that passed before passing through -1 + * (TLV-now) amount of time after passing though -1 + * nts = new "advancing time stamp"...it could also roll and cause problems. + */ + timestamp += lastdec + TIMER_LOAD_VAL - now; + } + lastdec = now; + + return timestamp; +} + +ulong get_timer_masked (void) +{ + return get_timer_raw() / TIMER_LOAD_VAL; +} + +/* waits specified delay value and resets timestamp */ +void udelay_masked (unsigned long usec) +{ + ulong tmo; + + if(usec >= 1000){ /* if "big" number, spread normalization to seconds */ + tmo = usec / 1000; /* start to normalize for usec to ticks per sec */ + tmo *= CFG_HZ_CLOCK; /* find number of "ticks" to wait to achieve target */ + tmo /= 1000; /* finish normalize. */ + }else{ /* else small number, don't kill it prior to HZ multiply */ + tmo = usec * CFG_HZ_CLOCK; + tmo /= (1000*1000); + } + + reset_timer_masked (); /* set "advancing" timestamp to 0, set lastdec vaule */ + + while (get_timer_raw () < tmo) /* wait for time stamp to overtake tick number.*/ + /*NOP*/; +} + +/* + * This function is derived from PowerPC code (read timebase as long long). + * On ARM it just returns the timer value. + */ +unsigned long long get_ticks(void) +{ + return get_timer(0); +} + +/* + * This function is derived from PowerPC code (timebase clock frequency). + * On ARM it returns the number of timer ticks per second. + */ +ulong get_tbclk (void) +{ + ulong tbclk; + + tbclk = CFG_HZ; + return tbclk; +} + +#endif /* CONFIG_INTEGRATOR */ diff --git a/cpu/arm946es/start.S b/cpu/arm946es/start.S new file mode 100644 index 000000000..ef3be8ec9 --- /dev/null +++ b/cpu/arm946es/start.S @@ -0,0 +1,409 @@ +/* + * armboot - Startup Code for ARM926EJS CPU-core + * + * Copyright (c) 2003 Texas Instruments + * + * ----- Adapted for OMAP1610 OMAP730 from ARM925t code ------ + * + * Copyright (c) 2001 Marius Gröger + * Copyright (c) 2002 Alex Züpke + * Copyright (c) 2002 Gary Jennejohn + * Copyright (c) 2003 Richard Woodruff + * Copyright (c) 2003 Kshitij + * + * 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 +#include + +/* + ************************************************************************* + * + * Jump vector table as in table 3.1 in [1] + * + ************************************************************************* + */ + + +.globl _start +_start: + b reset + ldr pc, _undefined_instruction + ldr pc, _software_interrupt + ldr pc, _prefetch_abort + ldr pc, _data_abort + ldr pc, _not_used + ldr pc, _irq + ldr pc, _fiq + +_undefined_instruction: + .word undefined_instruction +_software_interrupt: + .word software_interrupt +_prefetch_abort: + .word prefetch_abort +_data_abort: + .word data_abort +_not_used: + .word not_used +_irq: + .word irq +_fiq: + .word fiq + + .balignl 16,0xdeadbeef + + +/* + ************************************************************************* + * + * Startup Code (reset vector) + * + * do important init only if we don't start from memory! + * setup Memory and board specific bits prior to relocation. + * relocate armboot to ram + * setup stack + * + ************************************************************************* + */ + +_TEXT_BASE: + .word TEXT_BASE + +.globl _armboot_start +_armboot_start: + .word _start + +/* + * These are defined in the board-specific linker script. + */ +.globl _bss_start +_bss_start: + .word __bss_start + +.globl _bss_end +_bss_end: + .word _end + +#ifdef CONFIG_USE_IRQ +/* IRQ stack memory (calculated at run-time) */ +.globl IRQ_STACK_START +IRQ_STACK_START: + .word 0x0badc0de + +/* IRQ stack memory (calculated at run-time) */ +.globl FIQ_STACK_START +FIQ_STACK_START: + .word 0x0badc0de +#endif + + +/* + * the actual reset code + */ + +reset: + /* + * set the cpu to SVC32 mode + */ + mrs r0,cpsr + bic r0,r0,#0x1f + orr r0,r0,#0xd3 + msr cpsr,r0 + + /* + * we do sys-critical inits only at reboot, + * not when booting from ram! + */ +#ifdef CONFIG_INIT_CRITICAL + bl cpu_init_crit +#endif + +relocate: /* relocate U-Boot to RAM */ + adr r0, _start /* r0 <- current position of code */ + ldr r1, _TEXT_BASE /* test if we run from flash or RAM */ + cmp r0, r1 /* don't reloc during debug */ + beq stack_setup + + ldr r2, _armboot_start + ldr r3, _bss_start + sub r2, r3, r2 /* r2 <- size of armboot */ + add r2, r0, r2 /* r2 <- source end address */ + +copy_loop: + ldmia r0!, {r3-r10} /* copy from source address [r0] */ + stmia r1!, {r3-r10} /* copy to target address [r1] */ + cmp r0, r2 /* until source end addreee [r2] */ + ble copy_loop + + /* Set up the stack */ +stack_setup: + ldr r0, _TEXT_BASE /* upper 128 KiB: relocated uboot */ + sub r0, r0, #CFG_MALLOC_LEN /* malloc area */ + sub r0, r0, #CFG_GBL_DATA_SIZE /* bdinfo */ +#ifdef CONFIG_USE_IRQ + sub r0, r0, #(CONFIG_STACKSIZE_IRQ+CONFIG_STACKSIZE_FIQ) +#endif + sub sp, r0, #12 /* leave 3 words for abort-stack */ + +clear_bss: + ldr r0, _bss_start /* find start of bss segment */ + ldr r1, _bss_end /* stop here */ + mov r2, #0x00000000 /* clear */ + +clbss_l:str r2, [r0] /* clear loop... */ + add r0, r0, #4 + cmp r0, r1 + bne clbss_l + + ldr pc, _start_armboot + +_start_armboot: + .word start_armboot + + +/* + ************************************************************************* + * + * CPU_init_critical registers + * + * setup important registers + * setup memory timing + * + ************************************************************************* + */ + + +cpu_init_crit: + /* + * flush v4 I/D caches + */ + mov r0, #0 + mcr p15, 0, r0, c7, c5, 0 /* flush v4 I-cache */ + mcr p15, 0, r0, c7, c6, 0 /* flush v4 D-cache */ + + /* + * disable MMU stuff and caches + */ + mrc p15, 0, r0, c1, c0, 0 + bic r0, r0, #0x00002300 /* clear bits 13, 9:8 (--V- --RS) */ + bic r0, r0, #0x00000087 /* clear bits 7, 2:0 (B--- -CAM) */ + orr r0, r0, #0x00000002 /* set bit 2 (A) Align */ + orr r0, r0, #0x00001000 /* set bit 12 (I) I-Cache */ + mcr p15, 0, r0, c1, c0, 0 + + /* + * Go setup Memory and board specific bits prior to relocation. + */ + mov ip, lr /* perserve link reg across call */ + bl platformsetup /* go setup memory */ + mov lr, ip /* restore link */ + mov pc, lr /* back to my caller */ +/* + ************************************************************************* + * + * Interrupt handling + * + ************************************************************************* + */ + +@ +@ IRQ stack frame. +@ +#define S_FRAME_SIZE 72 + +#define S_OLD_R0 68 +#define S_PSR 64 +#define S_PC 60 +#define S_LR 56 +#define S_SP 52 + +#define S_IP 48 +#define S_FP 44 +#define S_R10 40 +#define S_R9 36 +#define S_R8 32 +#define S_R7 28 +#define S_R6 24 +#define S_R5 20 +#define S_R4 16 +#define S_R3 12 +#define S_R2 8 +#define S_R1 4 +#define S_R0 0 + +#define MODE_SVC 0x13 +#define I_BIT 0x80 + +/* + * use bad_save_user_regs for abort/prefetch/undef/swi ... + * use irq_save_user_regs / irq_restore_user_regs for IRQ/FIQ handling + */ + + .macro bad_save_user_regs + @ carve out a frame on current user stack + sub sp, sp, #S_FRAME_SIZE + stmia sp, {r0 - r12} @ Save user registers (now in svc mode) r0-r12 + + ldr r2, _armboot_start + sub r2, r2, #(CONFIG_STACKSIZE+CFG_MALLOC_LEN) + sub r2, r2, #(CFG_GBL_DATA_SIZE+8) @ set base 2 words into abort stack + @ get values for "aborted" pc and cpsr (into parm regs) + ldmia r2, {r2 - r3} + add r0, sp, #S_FRAME_SIZE @ grab pointer to old stack + add r5, sp, #S_SP + mov r1, lr + stmia r5, {r0 - r3} @ save sp_SVC, lr_SVC, pc, cpsr + mov r0, sp @ save current stack into r0 (param register) + .endm + + .macro irq_save_user_regs + sub sp, sp, #S_FRAME_SIZE + stmia sp, {r0 - r12} @ Calling r0-r12 + @ !!!! R8 NEEDS to be saved !!!! a reserved stack spot would be good. + add r8, sp, #S_PC + stmdb r8, {sp, lr}^ @ Calling SP, LR + str lr, [r8, #0] @ Save calling PC + mrs r6, spsr + str r6, [r8, #4] @ Save CPSR + str r0, [r8, #8] @ Save OLD_R0 + mov r0, sp + .endm + + .macro irq_restore_user_regs + ldmia sp, {r0 - lr}^ @ Calling r0 - lr + mov r0, r0 + ldr lr, [sp, #S_PC] @ Get PC + add sp, sp, #S_FRAME_SIZE + subs pc, lr, #4 @ return & move spsr_svc into cpsr + .endm + + .macro get_bad_stack + ldr r13, _armboot_start @ setup our mode stack + sub r13, r13, #(CONFIG_STACKSIZE+CFG_MALLOC_LEN) + sub r13, r13, #(CFG_GBL_DATA_SIZE+8) @ reserved a couple spots in abort stack + + str lr, [r13] @ save caller lr in position 0 of saved stack + mrs lr, spsr @ get the spsr + str lr, [r13, #4] @ save spsr in position 1 of saved stack + mov r13, #MODE_SVC @ prepare SVC-Mode + @ msr spsr_c, r13 + msr spsr, r13 @ switch modes, make sure moves will execute + mov lr, pc @ capture return pc + movs pc, lr @ jump to next instruction & switch modes. + .endm + + .macro get_irq_stack @ setup IRQ stack + ldr sp, IRQ_STACK_START + .endm + + .macro get_fiq_stack @ setup FIQ stack + ldr sp, FIQ_STACK_START + .endm + +/* + * exception handlers + */ + .align 5 +undefined_instruction: + get_bad_stack + bad_save_user_regs + bl do_undefined_instruction + + .align 5 +software_interrupt: + get_bad_stack + bad_save_user_regs + bl do_software_interrupt + + .align 5 +prefetch_abort: + get_bad_stack + bad_save_user_regs + bl do_prefetch_abort + + .align 5 +data_abort: + get_bad_stack + bad_save_user_regs + bl do_data_abort + + .align 5 +not_used: + get_bad_stack + bad_save_user_regs + bl do_not_used + +#ifdef CONFIG_USE_IRQ + + .align 5 +irq: + get_irq_stack + irq_save_user_regs + bl do_irq + irq_restore_user_regs + + .align 5 +fiq: + get_fiq_stack + /* someone ought to write a more effiction fiq_save_user_regs */ + irq_save_user_regs + bl do_fiq + irq_restore_user_regs + +#else + + .align 5 +irq: + get_bad_stack + bad_save_user_regs + bl do_irq + + .align 5 +fiq: + get_bad_stack + bad_save_user_regs + bl do_fiq + +#endif + +# ifdef CONFIG_INTEGRATOR + + /* Satisfied by general board level routine */ + +#else + + .align 5 +.globl reset_cpu +reset_cpu: + + ldr r1, rstctl1 /* get clkm1 reset ctl */ + mov r3, #0x0 + strh r3, [r1] /* clear it */ + mov r3, #0x8 + strh r3, [r1] /* force dsp+arm reset */ +_loop_forever: + b _loop_forever + +rstctl1: + .word 0xfffece10 + +#endif /* #ifdef CONFIG_INTEGRATOR */ diff --git a/cpu/arm_intcm/Makefile b/cpu/arm_intcm/Makefile new file mode 100644 index 000000000..203278e9c --- /dev/null +++ b/cpu/arm_intcm/Makefile @@ -0,0 +1,43 @@ +# +# (C) Copyright 2000-2003 +# 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$(CPU).a + +START = start.o +OBJS = interrupts.o cpu.o + +all: .depend $(START) $(LIB) + +$(LIB): $(OBJS) + $(AR) crv $@ $(OBJS) + +######################################################################### + +.depend: Makefile $(START:.o=.S) $(OBJS:.o=.c) + $(CC) -M $(CFLAGS) $(START:.o=.S) $(OBJS:.o=.c) > $@ + +sinclude .depend + +######################################################################### diff --git a/cpu/arm_intcm/config.mk b/cpu/arm_intcm/config.mk new file mode 100644 index 000000000..81ca2885e --- /dev/null +++ b/cpu/arm_intcm/config.mk @@ -0,0 +1,27 @@ +# +# (C) Copyright 2002 +# Gary Jennejohn, DENX Software Engineering, +# +# 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 +# + +PLATFORM_RELFLAGS += -fno-strict-aliasing -fno-common -ffixed-r8 \ + -msoft-float + +PLATFORM_CPPFLAGS += -march=armv4 diff --git a/cpu/arm_intcm/cpu.c b/cpu/arm_intcm/cpu.c new file mode 100644 index 000000000..34cd5af82 --- /dev/null +++ b/cpu/arm_intcm/cpu.c @@ -0,0 +1,91 @@ +/* + * (C) Copyright 2002 + * Sysgo Real-Time Solutions, GmbH + * Marius Groeger + * + * (C) Copyright 2002 + * Gary Jennejohn, DENX Software Engineering, + * + * 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 + */ + +/* + * CPU specific code for an unknown cpu + * - hence fairly empty...... + */ + +#include +#include + +int cpu_init (void) +{ + /* + * setup up stacks if necessary + */ +#ifdef CONFIG_USE_IRQ + DECLARE_GLOBAL_DATA_PTR; + + IRQ_STACK_START = _armboot_start - CFG_MALLOC_LEN - CFG_GBL_DATA_SIZE - 4; + FIQ_STACK_START = IRQ_STACK_START - CONFIG_STACKSIZE_IRQ; +#endif + return 0; +} + +int cleanup_before_linux (void) +{ + /* + * this function is called just before we call linux + * it prepares the processor for linux + * + * we turn off caches etc ... + */ + + disable_interrupts (); + + /* Since the CM has unknown processor we do not support + * cache operations + */ + + return (0); +} + +int do_reset (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]) +{ + extern void reset_cpu (ulong addr); + + disable_interrupts (); + reset_cpu (0); + /*NOTREACHED*/ + return (0); +} + +/* May not be cahed processor on the CM - do nothing */ +void icache_enable (void) +{ +} + +void icache_disable (void) +{ +} + +/* return "disabled" */ +int icache_status (void) +{ + return 0; +} diff --git a/cpu/arm_intcm/interrupts.c b/cpu/arm_intcm/interrupts.c new file mode 100644 index 000000000..e41ac5ac5 --- /dev/null +++ b/cpu/arm_intcm/interrupts.c @@ -0,0 +1,192 @@ +/* + * (C) Copyright 2003 + * Texas Instruments + * + * (C) Copyright 2002 + * Sysgo Real-Time Solutions, GmbH + * Marius Groeger + * + * (C) Copyright 2002 + * Sysgo Real-Time Solutions, GmbH + * Alex Zuepke + * + * (C) Copyright 2002-2004 + * Gary Jennejohn, DENX Software Engineering, + * + * (C) Copyright 2004 + * Philippe Robin, ARM Ltd. + * + * 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 +#include + +#ifndef CONFIG_INTEGRATOR +/* Only to be used for integrator/AP or /CP */ +/* Allows U-Boot to be used with any ARM supplied core module (CM), + * provided the ARM boot monitor, or similar software, + * runs first to set up the platform e.g. map writeable memory to 0x00000000 + * - see Integrator User Guides + * Versatile has a supported cpu - arm926ejs + * Some integrator CMs cpus are supported + * CM926EJ-S, CM946E-S + * For platforms with supported cpus U-Boot can be used as the sole boot + * monitor/loader - it will configure the platform itself + * Also U-Boot may be faster/smaller in those cases since specific + * qualities of the cpu and/or CM can be used e.g i and/or d caches etc. + */ +#endif +extern void reset_cpu(ulong addr); + +#ifdef CONFIG_USE_IRQ +/* enable IRQ interrupts */ +void enable_interrupts (void) +{ + unsigned long temp; + __asm__ __volatile__("mrs %0, cpsr\n" + "bic %0, %0, #0x80\n" + "msr cpsr_c, %0" + : "=r" (temp) + : + : "memory"); +} + + +/* + * disable IRQ/FIQ interrupts + * returns true if interrupts had been enabled before we disabled them + */ +int disable_interrupts (void) +{ + unsigned long old,temp; + __asm__ __volatile__("mrs %0, cpsr\n" + "orr %1, %0, #0xc0\n" + "msr cpsr_c, %1" + : "=r" (old), "=r" (temp) + : + : "memory"); + return (old & 0x80) == 0; +} +#else +void enable_interrupts (void) +{ + return; +} +int disable_interrupts (void) +{ + return 0; +} +#endif + + +void bad_mode (void) +{ + panic ("Resetting CPU ...\n"); + reset_cpu (0); +} + +void show_regs (struct pt_regs *regs) +{ + unsigned long flags; + const char *processor_modes[] = { + "USER_26", "FIQ_26", "IRQ_26", "SVC_26", + "UK4_26", "UK5_26", "UK6_26", "UK7_26", + "UK8_26", "UK9_26", "UK10_26", "UK11_26", + "UK12_26", "UK13_26", "UK14_26", "UK15_26", + "USER_32", "FIQ_32", "IRQ_32", "SVC_32", + "UK4_32", "UK5_32", "UK6_32", "ABT_32", + "UK8_32", "UK9_32", "UK10_32", "UND_32", + "UK12_32", "UK13_32", "UK14_32", "SYS_32", + }; + + flags = condition_codes (regs); + + printf ("pc : [<%08lx>] lr : [<%08lx>]\n" + "sp : %08lx ip : %08lx fp : %08lx\n", + instruction_pointer (regs), + regs->ARM_lr, regs->ARM_sp, regs->ARM_ip, regs->ARM_fp); + printf ("r10: %08lx r9 : %08lx r8 : %08lx\n", + regs->ARM_r10, regs->ARM_r9, regs->ARM_r8); + printf ("r7 : %08lx r6 : %08lx r5 : %08lx r4 : %08lx\n", + regs->ARM_r7, regs->ARM_r6, regs->ARM_r5, regs->ARM_r4); + printf ("r3 : %08lx r2 : %08lx r1 : %08lx r0 : %08lx\n", + regs->ARM_r3, regs->ARM_r2, regs->ARM_r1, regs->ARM_r0); + printf ("Flags: %c%c%c%c", + flags & CC_N_BIT ? 'N' : 'n', + flags & CC_Z_BIT ? 'Z' : 'z', + flags & CC_C_BIT ? 'C' : 'c', flags & CC_V_BIT ? 'V' : 'v'); + printf (" IRQs %s FIQs %s Mode %s%s\n", + interrupts_enabled (regs) ? "on" : "off", + fast_interrupts_enabled (regs) ? "on" : "off", + processor_modes[processor_mode (regs)], + thumb_mode (regs) ? " (T)" : ""); +} + +void do_undefined_instruction (struct pt_regs *pt_regs) +{ + printf ("undefined instruction\n"); + show_regs (pt_regs); + bad_mode (); +} + +void do_software_interrupt (struct pt_regs *pt_regs) +{ + printf ("software interrupt\n"); + show_regs (pt_regs); + bad_mode (); +} + +void do_prefetch_abort (struct pt_regs *pt_regs) +{ + printf ("prefetch abort\n"); + show_regs (pt_regs); + bad_mode (); +} + +void do_data_abort (struct pt_regs *pt_regs) +{ + printf ("data abort\n"); + show_regs (pt_regs); + bad_mode (); +} + +void do_not_used (struct pt_regs *pt_regs) +{ + printf ("not used\n"); + show_regs (pt_regs); + bad_mode (); +} + +void do_fiq (struct pt_regs *pt_regs) +{ + printf ("fast interrupt request\n"); + show_regs (pt_regs); + bad_mode (); +} + +void do_irq (struct pt_regs *pt_regs) +{ + printf ("interrupt request\n"); + show_regs (pt_regs); + bad_mode (); +} + +/* The timer functionality is supplied by the Integrator board */ +/* - see board/integrator<>.c */ diff --git a/cpu/arm_intcm/start.S b/cpu/arm_intcm/start.S new file mode 100644 index 000000000..ccfd1815a --- /dev/null +++ b/cpu/arm_intcm/start.S @@ -0,0 +1,370 @@ +/* + * armboot - Startup Code for ARM926EJS CPU-core + * + * Copyright (c) 2003 Texas Instruments + * + * ----- Adapted for OMAP1610 OMAP730 from ARM925t code ------ + * + * Copyright (c) 2001 Marius Gröger + * Copyright (c) 2002 Alex Züpke + * Copyright (c) 2002 Gary Jennejohn + * Copyright (c) 2003 Richard Woodruff + * Copyright (c) 2003 Kshitij + * + * 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 +#include + +/* + ************************************************************************* + * + * Jump vector table + * + ************************************************************************* + */ + +.globl _start +_start: + b reset + ldr pc, _undefined_instruction + ldr pc, _software_interrupt + ldr pc, _prefetch_abort + ldr pc, _data_abort + ldr pc, _not_used + ldr pc, _irq + ldr pc, _fiq + +_undefined_instruction: + .word undefined_instruction +_software_interrupt: + .word software_interrupt +_prefetch_abort: + .word prefetch_abort +_data_abort: + .word data_abort +_not_used: + .word not_used +_irq: + .word irq +_fiq: + .word fiq + + .balignl 16,0xdeadbeef + +/* + ************************************************************************* + * + * Startup Code (reset vector) + * + * do important init only if we don't start from memory! + * setup memory and board specific bits prior to relocation. + * relocate armboot to ram + * setup stack + * + ************************************************************************* + */ + +_TEXT_BASE: + .word TEXT_BASE /* address of _start in the linked image */ + +.globl _armboot_start +_armboot_start: + .word _start + +/* + * These are defined in the board-specific linker script. + */ +.globl _bss_start +_bss_start: + .word __bss_start + +.globl _bss_end +_bss_end: + .word _end + +#ifdef CONFIG_USE_IRQ +/* IRQ stack memory (calculated at run-time) */ +.globl IRQ_STACK_START +IRQ_STACK_START: + .word 0x0badc0de + +/* IRQ stack memory (calculated at run-time) */ +.globl FIQ_STACK_START +FIQ_STACK_START: + .word 0x0badc0de +#endif + + +/* + * the actual reset code + */ +.globl reset +reset: + /* + * set the cpu to SVC32 mode + */ + mrs r0,cpsr + bic r0,r0,#0x1f + orr r0,r0,#0xd3 + msr cpsr,r0 + + /* + * we do sys-critical inits only at reboot, + * not when booting from ram! + */ +#ifdef CONFIG_INIT_CRITICAL + bl cpu_init_crit +#endif + +relocate: /* relocate U-Boot to RAM */ + adr r0, _start /* pc relative address of label */ + ldr r1, _TEXT_BASE /* linked image address of label */ + cmp r0, r1 /* test if we run from flash or RAM */ + beq stack_setup /* ifeq we are in the RAM copy */ + + ldr r2, _armboot_start + ldr r3, _bss_start + sub r2, r3, r2 /* r2 <- size of armboot */ + add r2, r0, r2 /* r2 <- source end address */ + +copy_loop: + ldmia r0!, {r3-r10} /* copy from source address [r0] */ + stmia r1!, {r3-r10} /* copy to target address [r1] */ + cmp r0, r2 /* until source end addreee [r2] */ + ble copy_loop + + /* Set up the stack */ +stack_setup: + ldr r0, _TEXT_BASE /* upper 128 KiB: relocated uboot */ + sub r0, r0, #CFG_MALLOC_LEN /* malloc area */ + sub r0, r0, #CFG_GBL_DATA_SIZE /* bdinfo */ +#ifdef CONFIG_USE_IRQ + sub r0, r0, #(CONFIG_STACKSIZE_IRQ+CONFIG_STACKSIZE_FIQ) +#endif + sub sp, r0, #12 /* leave 3 words for abort-stack */ + +clear_bss: + ldr r0, _bss_start /* find start of bss segment */ + ldr r1, _bss_end /* stop here */ + mov r2, #0x00000000 /* clear */ + +clbss_l:str r2, [r0] /* clear loop... */ + add r0, r0, #4 + cmp r0, r1 + ble clbss_l + + ldr pc, _start_armboot + +_start_armboot: + .word start_armboot + +/* + ************************************************************************* + * + * CPU_init_critical registers + * + * setup important registers + * setup memory timing + * + ************************************************************************* + */ + +cpu_init_crit: + /* arm_int_generic assumes the ARM boot monitor, or user software, + * has initialized the platform + */ + mov pc, lr /* back to my caller */ +/* + ************************************************************************* + * + * Interrupt handling + * + ************************************************************************* + */ + +@ +@ IRQ stack frame. +@ +#define S_FRAME_SIZE 72 + +#define S_OLD_R0 68 +#define S_PSR 64 +#define S_PC 60 +#define S_LR 56 +#define S_SP 52 + +#define S_IP 48 +#define S_FP 44 +#define S_R10 40 +#define S_R9 36 +#define S_R8 32 +#define S_R7 28 +#define S_R6 24 +#define S_R5 20 +#define S_R4 16 +#define S_R3 12 +#define S_R2 8 +#define S_R1 4 +#define S_R0 0 + +#define MODE_SVC 0x13 +#define I_BIT 0x80 + +/* + * use bad_save_user_regs for abort/prefetch/undef/swi ... + * use irq_save_user_regs / irq_restore_user_regs for IRQ/FIQ handling + */ + + .macro bad_save_user_regs + @ carve out a frame on current user stack + sub sp, sp, #S_FRAME_SIZE + stmia sp, {r0 - r12} @ Save user registers (now in svc mode) r0-r12 + + ldr r2, _armboot_start + sub r2, r2, #(CONFIG_STACKSIZE+CFG_MALLOC_LEN) + sub r2, r2, #(CFG_GBL_DATA_SIZE+8) @ set base 2 words into abort stack + @ get values for "aborted" pc and cpsr (into parm regs) + ldmia r2, {r2 - r3} + add r0, sp, #S_FRAME_SIZE @ grab pointer to old stack + add r5, sp, #S_SP + mov r1, lr + stmia r5, {r0 - r3} @ save sp_SVC, lr_SVC, pc, cpsr + mov r0, sp @ save current stack into r0 (param register) + .endm + + .macro irq_save_user_regs + sub sp, sp, #S_FRAME_SIZE + stmia sp, {r0 - r12} @ Calling r0-r12 + @ !!!! R8 NEEDS to be saved !!!! a reserved stack spot would be good. + add r8, sp, #S_PC + stmdb r8, {sp, lr}^ @ Calling SP, LR + str lr, [r8, #0] @ Save calling PC + mrs r6, spsr + str r6, [r8, #4] @ Save CPSR + str r0, [r8, #8] @ Save OLD_R0 + mov r0, sp + .endm + + .macro irq_restore_user_regs + ldmia sp, {r0 - lr}^ @ Calling r0 - lr + mov r0, r0 + ldr lr, [sp, #S_PC] @ Get PC + add sp, sp, #S_FRAME_SIZE + subs pc, lr, #4 @ return & move spsr_svc into cpsr + .endm + + .macro get_bad_stack + ldr r13, _armboot_start @ setup our mode stack + sub r13, r13, #(CONFIG_STACKSIZE+CFG_MALLOC_LEN) + sub r13, r13, #(CFG_GBL_DATA_SIZE+8) @ reserved a couple spots in abort stack + + str lr, [r13] @ save caller lr in position 0 of saved stack + mrs lr, spsr @ get the spsr + str lr, [r13, #4] @ save spsr in position 1 of saved stack + mov r13, #MODE_SVC @ prepare SVC-Mode + @ msr spsr_c, r13 + msr spsr, r13 @ switch modes, make sure moves will execute + mov lr, pc @ capture return pc + movs pc, lr @ jump to next instruction & switch modes. + .endm + + .macro get_irq_stack @ setup IRQ stack + ldr sp, IRQ_STACK_START + .endm + + .macro get_fiq_stack @ setup FIQ stack + ldr sp, FIQ_STACK_START + .endm + +/* + * exception handlers + */ + .align 5 +.globl undefined_instruction +undefined_instruction: + get_bad_stack + bad_save_user_regs + bl do_undefined_instruction + + .align 5 +.globl software_interrupt +software_interrupt: + get_bad_stack + bad_save_user_regs + bl do_software_interrupt + + .align 5 +.globl prefetch_abort +prefetch_abort: + get_bad_stack + bad_save_user_regs + bl do_prefetch_abort + + .align 5 +.globl data_abort +data_abort: + get_bad_stack + bad_save_user_regs + bl do_data_abort + + .align 5 +.globl not_used +not_used: + get_bad_stack + bad_save_user_regs + bl do_not_used + +#ifdef CONFIG_USE_IRQ + .align 5 +.globl irq +irq: + get_irq_stack + irq_save_user_regs + bl do_irq + irq_restore_user_regs + + .align 5 +.globl fiq +fiq: + get_fiq_stack + /* someone ought to write a more effiction fiq_save_user_regs */ + irq_save_user_regs + bl do_fiq + irq_restore_user_regs + +#else + + .align 5 +.globl irq +irq: + get_bad_stack + bad_save_user_regs + bl do_irq + + .align 5 +.globl fiq +fiq: + get_bad_stack + bad_save_user_regs + bl do_fiq + +#endif diff --git a/doc/README-integrator b/doc/README-integrator new file mode 100644 index 000000000..93d768838 --- /dev/null +++ b/doc/README-integrator @@ -0,0 +1,66 @@ + + U-Boot for ARM Integrator Development Platforms + + Peter Pearse, ARM Ltd. + peter.pearse@arm.com + www.arm.com + +Manuals available from :- +http://www.arm.com/products/DevTools/Hardware_Platforms.html + +Overview : +-------- +There are two Integrator variants - Integrator/AP and Integrator/CP. +Each may be fitted with a variety of core modules (CMs). +Each CM consists of a ARM processor core and associated hardware e.g + FPGA implementing various controllers and/or register + SSRAM + SDRAM + RAM controllers + clock generators etc. + +Boot Methods : +------------ +Integrator platforms can be configured to use U-Boot in at least three ways :- +a) Run ARM boot monitor, manually run U-Boot image from flash +b) Run ARM boot monitor, automatically run U-Boot image from flash +c) Run U-Boot image direct from flash. + +In cases a) and b) the ARM boot monitor will have configured the CM and mapped +writeable memory to 0x00000000 in the Integrator address space. +U-Boot has to carry out minimal configration before standard code is run. + +In case c) it may be necessary for U-Boot to perform CM dependent initialization. + +Configuring U-Boot : +------------------ + The makefile contains targets for Integrator platforms of both types +fitted with all current variants of CM. If these targets are to be used with +boot process c) above then CONFIG_INIT_CRITICAL may need to be defined to ensure +that the CM is correctly configured. + + There are also targets independent of CM. These may not be suitable for +boot process c) above. They have been preserved for backward compatibility with +existing build processes. + +Code Hierarchy Applied : +---------------------- +Code specific to initialization of a particular ARM processor has been placed in +cpu/arm<>/start.S so that it may be used by other boards. + +However, to avoid duplicating code through all processor files, a generic core +for ARM Integrator CMs has been added + + cpu/arm_intcm + +Otherwise. for example, the standard CM reset via the CM control register would +need placing in each CM processor file...... + +Code specific to the initialization of the CM, rather than the cpu, and initialization +of the Integrator board itself, has been placed in + + board/integrator<>/platform.S + board/integrator<>/integrator<>.c + + + diff --git a/include/arm946es.h b/include/arm946es.h new file mode 100644 index 000000000..c23f3e79c --- /dev/null +++ b/include/arm946es.h @@ -0,0 +1,8 @@ +/************************************************ + * NAME arm946es.h * + * $Version$ * + ************************************************/ +/* Currently empty */ +#ifndef __ARM946ES_H__ +#define __ARM946ES_H__ +#endif /*__ARM946ES_H__*/ diff --git a/include/configs/integratorap.h b/include/configs/integratorap.h index 2674b52bf..94c6c7753 100644 --- a/include/configs/integratorap.h +++ b/include/configs/integratorap.h @@ -27,23 +27,18 @@ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, * MA 02111-1307 USA */ - + #ifndef __CONFIG_H #define __CONFIG_H - /* * High Level Configuration Options * (easy to change) */ -#define CONFIG_ARM926EJS 1 /* This is an arm926ejs CPU core */ -#define CONFIG_INTEGRATOR 1 /* in an Integrator board */ -#define CONFIG_ARCH_CINTEGRATOR 1 /* Specifically, a CP */ - - -#define CFG_MEMTEST_START 0x100000 -#define CFG_MEMTEST_END 0x10000000 -#define CFG_HZ (1000000 / 256) /* Timer 1 is clocked at 1Mhz, with 256 divider */ -#define CFG_TIMERBASE 0x13000100 +#define CFG_MEMTEST_START 0x100000 +#define CFG_MEMTEST_END 0x10000000 +#define CFG_HZ 1000 +#define CFG_HZ_CLOCK 24000000 /* Timer 1 is clocked at 24Mhz */ +#define CFG_TIMERBASE 0x13000100 /* Timer1 */ #define CONFIG_CMDLINE_TAG 1 /* enable passing of ATAGs */ #define CONFIG_SETUP_MEMORY_TAGS 1 @@ -120,8 +115,8 @@ #define CFG_MAX_FLASH_BANKS 1 /* max number of memory banks */ #define PHYS_FLASH_SIZE 0x01000000 /* 16MB */ /* timeout values are in ticks */ -#define CFG_FLASH_ERASE_TOUT (20*CFG_HZ) /* Timeout for Flash Erase */ -#define CFG_FLASH_WRITE_TOUT (20*CFG_HZ) /* Timeout for Flash Write */ +#define CFG_FLASH_ERASE_TOUT (2*CFG_HZ) /* Timeout for Flash Erase */ +#define CFG_FLASH_WRITE_TOUT (2*CFG_HZ) /* Timeout for Flash Write */ #define CFG_MAX_FLASH_SECT 128 #define CFG_ENV_SIZE 32768 @@ -131,7 +126,7 @@ * PCI definitions */ -/*#define CONFIG_PCI /--* include pci support */ +/*#define CONFIG_PCI /--* include pci support */ #undef CONFIG_PCI_PNP #define CONFIG_PCI_SCAN_SHOW 1 /* show pci devices on startup */ #define DEBUG @@ -267,5 +262,31 @@ #define INTEGRATOR_SC_PCIENABLE \ (INTEGRATOR_SC_BASE + INTEGRATOR_SC_PCIENABLE_OFFSET) +/*----------------------------------------------------------------------- + * There are various dependencies on the core module (CM) fitted + * Users should refer to their CM user guide + * - when porting adjust u-boot/Makefile accordingly + * to define the necessary CONFIG_ s for the CM involved + * see e.g. integratorcp_CM926EJ-S_config + */ + +#define CM_BASE 0x10000000 + +/* CM registers common to all integrator/CP CMs */ +#define OS_CTRL 0x0000000C +#define CMMASK_REMAP 0x00000005 /* Set remap & led */ +#define CMMASK_RESET 0x00000008 +#define OS_LOCK 0x00000014 +#define CMVAL_LOCK 0x0000A000 /* Locking value */ +#define CMMASK_LOCK 0x0000005F /* Locking value */ +#define CMVAL_UNLOCK 0x00000000 /* Any value != CM_LOCKVAL */ +#define OS_SDRAM 0x00000020 +#define OS_INIT 0x00000024 +#define CMMASK_MAP_SIMPLE 0xFFFDFFFF /* simple mapping */ +#define CMMASK_TCRAM_DISABLE 0xFFFEFFFF /* TCRAM disabled */ + +#ifdef CONFIG_CM_SPD_DETECT +#define OS_SPD 0x00000100 /* The SDRAM SPD data is copied here */ +#endif #endif /* __CONFIG_H */ diff --git a/include/configs/integratorcp.h b/include/configs/integratorcp.h index 0b0ffd43c..0da3171de 100644 --- a/include/configs/integratorcp.h +++ b/include/configs/integratorcp.h @@ -35,23 +35,15 @@ * High Level Configuration Options * (easy to change) */ -#if 1 -#define CONFIG_ARM926EJS 1 /* This is an arm926ejs CPU core */ -#else -#define CONFIG_ARM946ES 1 /* This is an arm946es CPU core */ -#endif -#define CONFIG_INTEGRATOR 1 /* in an Integrator board */ -#define CONFIG_ARCH_CINTEGRATOR 1 /* Specifically, a CP */ +#define CFG_MEMTEST_START 0x100000 +#define CFG_MEMTEST_END 0x10000000 +#define CFG_HZ 1000 +#define CFG_HZ_CLOCK 1000000 /* Timer 1 is clocked at 1Mhz */ +#define CFG_TIMERBASE 0x13000100 - -#define CFG_MEMTEST_START 0x100000 -#define CFG_MEMTEST_END 0x10000000 -#define CFG_HZ (1000000 / 256) /* Timer 1 is clocked at 1Mhz, with 256 divider */ -#define CFG_TIMERBASE 0x13000100 - -#define CONFIG_CMDLINE_TAG 1 /* enable passing of ATAGs */ +#define CONFIG_CMDLINE_TAG 1 /* enable passing of ATAGs */ #define CONFIG_SETUP_MEMORY_TAGS 1 -#define CONFIG_MISC_INIT_R 1 /* call misc_init_r during start up */ +#define CONFIG_MISC_INIT_R 1 /* call misc_init_r during start up */ /* * Size of malloc() pool */ @@ -96,6 +88,16 @@ #define CONFIG_BOOTCOMMAND "bootp ; bootm" #endif +/* Flash loaded + - U-Boot + - u-linux + - system.cramfs +*/ +#define CONFIG_BOOTDELAY 2 +#define CONFIG_BOOTARGS "root=/dev/mtdblock2 mem=128M ip=dhcp netdev=27,0, \ +0xfc800000,0xfc800010,eth0 video=clcdfb:0" +#define CONFIG_BOOTCOMMAND "cp 0x24040000 0x7fc0 0x80000; bootm" + /* * Miscellaneous configurable options */ @@ -135,8 +137,8 @@ #define CFG_MAX_FLASH_SECT 64 #define CFG_MAX_FLASH_BANKS 1 /* max number of memory banks */ #define PHYS_FLASH_SIZE 0x01000000 /* 16MB */ -#define CFG_FLASH_ERASE_TOUT (20*CFG_HZ) /* Timeout for Flash Erase */ -#define CFG_FLASH_WRITE_TOUT (20*CFG_HZ) /* Timeout for Flash Write */ +#define CFG_FLASH_ERASE_TOUT (2*CFG_HZ) /* Timeout for Flash Erase */ +#define CFG_FLASH_WRITE_TOUT (2*CFG_HZ) /* Timeout for Flash Write */ #define CFG_MONITOR_BASE 0x24F40000 #define CFG_ENV_IS_IN_FLASH @@ -144,4 +146,70 @@ #define CFG_ENV_SECT_SIZE 0x40000 /* 256KB */ #define CFG_ENV_SIZE 8192 /* 8KB */ +/*----------------------------------------------------------------------- + * There are various dependencies on the core module (CM) fitted + * Users should refer to their CM user guide + * - when porting adjust u-boot/Makefile accordingly + * to define the necessary CONFIG_ s for the CM involved + * see e.g. integratorcp_CM926EJ-S_config + */ + +#define CM_BASE 0x10000000 + +/* CM registers common to all integrator/CP CMs */ +#define OS_CTRL 0x0000000C +#define CMMASK_REMAP 0x00000005 /* set remap & led */ +#define CMMASK_RESET 0x00000008 +#define OS_LOCK 0x00000014 +#define CMVAL_LOCK 0x0000A000 /* locking value */ +#define CMMASK_LOCK 0x0000005F /* locking value */ +#define CMVAL_UNLOCK 0x00000000 /* any value != CM_LOCKVAL */ +#define OS_SDRAM 0x00000020 +#define OS_INIT 0x00000024 +#define CMMASK_MAP_SIMPLE 0xFFFDFFFF /* simple mapping */ +#define CMMASK_TCRAM_DISABLE 0xFFFEFFFF /* TCRAM disabled */ +#define CMMASK_LOWVEC 0x00000004 /* vectors @ 0x00000000 */ +#if defined (CONFIG_CM10200E) || defined (CONFIG_CM10220E) +#define CMMASK_INIT_102 0x00000300 /* see CM102xx ref manual + * - PLL test clock bypassed + * - bus clock ratio 2 + * - little endian + * - vectors at zero + */ +#endif /* CM1022xx */ + +#define CMMASK_LE 0x00000008 /* little endian */ +#define CMMASK_CMxx6_COMMON 0x00000100 /* Common value for CMxx6 + * - divisor/ratio b00000001 + * bx + * - HCLKDIV b000 + * bxx + * - PLL BYPASS b00 + */ + +/* Determine CM characteristics */ + +#undef CONFIG_CM_MULTIPLE_SSRAM +#undef CONFIG_CM_SPD_DETECT +#undef CONFIG_CM_REMAP +#undef CONFIG_CM_INIT +#undef CONFIG_CM_TCRAM + +#if defined (CONFIG_CM946E_S) || defined (CONFIG_CM966E_S) +#define CONFIG_CM_MULTIPLE_SSRAM /* CM has multiple SSRAM mapping */ +#endif + +#ifndef CONFIG_CM922t_XA10 +#define CONFIG_CM_SPD_DETECT /* CM supports SPD query */ +#define OS_SPD 0x00000100 /* Address of SPD data */ +#define CONFIG_CM_REMAP /* CM supports remapping */ +#define CONFIG_CM_INIT /* CM has initialization reg */ +#endif + +#if defined(CONFIG_CM926EJ_S) || defined (CONFIG_CM946E_S) || \ + defined(CONFIG_CM966E_S) || defined (CONFIG_CM1026EJ_S) || \ + defined(CONFIG_CM1136JF_S) +#define CONFIG_CM_TCRAM /* CM has TCRAM */ +#endif + #endif /* __CONFIG_H */