Fix TQM8560 DDR boot issue
v2 cover Fix TQM8560 DDR boot issue
Series to fix the TQM85xx issue reported by Wolfgang.... the problem turned out to be that those boards use get_ram_size(), which requires that a TLB entry be set up for the DDR region. My earlier patches changed the way this was done and broke this.
I've created a new function, clear_ddr_tlbs(), so that there is now a setup_ddr_tlbs() and a matching clear_ddr_tlbs() that boards can use if they need to temporarily set up a TLB entry for this purpose. The tqm85xx ddr init code now uses this and the board is able to boot.
NOTE: There was another patch in this series that changed some include logic in the TQM85xx.h header file. I have dropped that patch as it was screwed up and not needed.
Cheers,
Becky
arch/powerpc/cpu/mpc85xx/cpu.c | 14 +++----------- arch/powerpc/cpu/mpc85xx/tlb.c | 29 +++++++++++++++++++++++++++++ arch/powerpc/include/asm/mmu.h | 1 + board/tqc/tqm85xx/sdram.c | 7 +++++++ include/configs/TQM85xx.h | 6 ++++++ 5 files changed, 46 insertions(+), 11 deletions(-)
PATCH v2 1/2 powerpc/mpc85xx: Add clear_ddr_tlbs function
This is useful when we just want to wipe out the TLBs. There's currently a function that resets the ddr tlbs to a different value; it is changed to utilize this function. The new function can be used in conjunction with setup_ddr_tlbs() for a board to temporarily map/unmap the DDR address range as needed.
--- arch/powerpc/cpu/mpc85xx/cpu.c | 14 +++----------- arch/powerpc/cpu/mpc85xx/tlb.c | 29 +++++++++++++++++++++++++++++ arch/powerpc/include/asm/mmu.h | 1 + 3 files changed, 33 insertions(+), 11 deletions(-)
arch/powerpc/cpu/mpc85xx/cpu.c +3 -11
@@ -374,6 +374,8 @@ void read_tlbcam_entry(int idx, u32 *valid, u32 *tsize, unsigned long *epn,unsigned int setup_ddr_tlbs_phys (phys_addr_t p_addr,unsigned int memsize_in_meg); +void clear_ddr_tlbs_phys (phys_addr_t p_addr,unsigned int memsize_in_meg); +static void dump_spd_ddr_reg (void ) {int i, j, k, m;
@@ -460,19 +462,9 @@ static int reset_tlb(phys_addr_t p_addr, u32 size, phys_addr_t *phys_offset)u32 vstart =CONFIG_SYS_DDR_SDRAM_BASE ;unsigned long epn;u32 tsize, valid, ptr; -phys_addr_t rpn =0 ;int ddr_esel; - ptr = vstart; - -while (ptr < (vstart + size)) { - ddr_esel =find_tlb_idx ((void *)ptr,1 ); -if (ddr_esel !=-1 ) { -read_tlbcam_entry (ddr_esel, &valid, &tsize, &epn, &rpn); -disable_tlb (ddr_esel); - } - ptr +=TSIZE_TO_BYTES (tsize); - } +clear_ddr_tlbs_phys (p_addr, size>>20 );/* Setup new tlb to cover the physical address */ setup_ddr_tlbs_phys (p_addr, size>>20 );
arch/powerpc/cpu/mpc85xx/tlb.c +29 -0
@@ -300,4 +300,33 @@ unsigned int setup_ddr_tlbs(unsigned int memsize_in_meg)return setup_ddr_tlbs_phys(CONFIG_SYS_DDR_SDRAM_BASE, memsize_in_meg); } + +/* Invalidate the DDR TLBs for the requested size */ +void clear_ddr_tlbs_phys (phys_addr_t p_addr,unsigned int memsize_in_meg) +{ +u32 vstart =CONFIG_SYS_DDR_SDRAM_BASE ; +unsigned long epn; +u32 tsize, valid, ptr; +phys_addr_t rpn =0 ; +int ddr_esel; +u64 memsize = (u64 )memsize_in_meg <<20 ; + + ptr = vstart; + +while (ptr < (vstart + memsize)) { + ddr_esel =find_tlb_idx ((void *)ptr,1 ); +if (ddr_esel !=-1 ) { +read_tlbcam_entry (ddr_esel, &valid, &tsize, &epn, &rpn); +disable_tlb (ddr_esel); + } + ptr +=TSIZE_TO_BYTES (tsize); + } +} + +void clear_ddr_tlbs (unsigned int memsize_in_meg) +{ +clear_ddr_tlbs_phys (CONFIG_SYS_DDR_SDRAM_BASE , memsize_in_meg); +} + +#endif /* !CONFIG_NAND_SPL */
arch/powerpc/include/asm/mmu.h +1 -0
@@ -489,6 +489,7 @@ extern int find_free_tlbcam(void);extern void print_tlbcam (void );extern unsigned int setup_ddr_tlbs (unsigned int memsize_in_meg); +extern void clear_ddr_tlbs (unsigned int memsize_in_meg);extern void write_tlb (u32 _mas0,u32 _mas1,u32 _mas2,u32 _mas3,u32 _mas7);
Signature · 1 line
1.5.6.5
PATCH v2 2/2 board/tqm85xx: Create and tear down TLB for get_ram_size()
We need a TLB entry to call get_ram_size(); the common code doesn't create one until *after* fixed_sdram() has determined the size. So we set up tlbs for the max possible size and tear them down once we're done with get_ram_size(); the common 85xx code will then set up a final set of tlb entries for the *actual* detected size of ddr.
This prevents us from having TLB entries that are larger than DDR sitting around for very long, which is not a recommended scenario.
--- board/tqc/tqm85xx/sdram.c | 7 +++++++ include/configs/TQM85xx.h | 6 ++++++ 2 files changed, 13 insertions(+), 0 deletions(-)
board/tqc/tqm85xx/sdram.c +7 -0
@@ -363,6 +363,12 @@ static phys_size_t sdram_setup(int casl)udelay (1000 );#endif /* CONFIG_TQM8548 */ +/* +* get_ram_size() depends on having tlbs for the DDR, but they are +* not yet setup because we don't know the size. Set up a temp +* mapping and delete it when done. +*/ +setup_ddr_tlbs (CONFIG_SYS_DDR_EARLY_SIZE_MB );for (i =0 ; i <N_DDR_CS_CONF ; i++) { ddr->cs0_config = ddr_cs_conf[i].reg;
@@ -376,6 +382,7 @@ static phys_size_t sdram_setup(int casl)break ; } } +clear_ddr_tlbs (CONFIG_SYS_DDR_EARLY_SIZE_MB );#ifdef CONFIG_TQM8548 if (i <N_DDR_CS_CONF ) {
include/configs/TQM85xx.h +6 -0
@@ -147,10 +147,16 @@* DDR Setup */ #define CONFIG_SYS_DDR_SDRAM_BASE 0x00000000/* DDR is system memory */ +#if defined(CONFIG_TQM_BIGFLASH ) || \ (!defined(CONFIG_TQM8548_AG ) && !defined(CONFIG_TQM8548_BE ))#define CONFIG_SYS_PPC_DDR_WIMGE (MAS2_I | MAS2_G) +#define CONFIG_SYS_DDR_EARLY_SIZE_MB (512) +#else +#define CONFIG_SYS_PPC_DDR_WIMGE (0) +#define CONFIG_SYS_DDR_EARLY_SIZE_MB (2 * 1024)#endif +#define CONFIG_SYS_SDRAM_BASE CONFIG_SYS_DDR_SDRAM_BASE#ifdef CONFIG_TQM8548_AG #define CONFIG_VERY_BIG_RAM
Signature · 1 line
1.5.6.5
Kumar Gala
AppliedPATCH v2 2/2 board/tqm85xx: Create and tear down TLB for get_ram_size()
Quoted 11 lines · Becky Bruce
We need a TLB entry to call
get_ram_size(); the common code doesn't create one until *after*fixed_sdram()has determined the size. So we set up tlbs for the max possible size and tear them down once we're done withget_ram_size(); the common 85xx code will then set up a final set of tlb entries for the *actual* detected size of ddr.This prevents us from having TLB entries that are larger than DDR sitting around for very long, which is not a recommended scenario.
Quoted 5 lines
Signed-off-by Becky Bruce <[email protected]>---
board/tqc/tqm85xx/sdram.c | 7 +++++++ include/configs/TQM85xx.h | 6 ++++++ 2 files changed, 13 insertions(+), 0 deletions(-)
applied to 85xx
- k
PATCH v2 2/2 board/tqm85xx: Create and tear down TLB for get_ram_size()
In reply to Becky BruceDear Becky Bruce,
Quoted 11 lines · In message <[email protected]> you wrote:
We need a TLB entry to call
get_ram_size(); the common code doesn't create one until *after*fixed_sdram()has determined the size. So we set up tlbs for the max possible size and tear them down once we're done withget_ram_size(); the common 85xx code will then set up a final set of tlb entries for the *actual* detected size of ddr.This prevents us from having TLB entries that are larger than DDR sitting around for very long, which is not a recommended scenario.
Quoted 5 lines
Signed-off-by Becky Bruce <[email protected]>--- board/tqc/tqm85xx/sdram.c | 7 +++++++ include/configs/TQM85xx.h | 6 ++++++ 2 files changed, 13 insertions(+), 0 deletions(-)
Tested on TQM8555 / TQM8560.
Best regards,
Wolfgang Denk
Signature · 6 lines
DENX Software Engineering GmbH, MD: Wolfgang Denk & Detlev Zundel HRB 165235 Munich, Office: Kirchenstr.5, D-82194 Groebenzell, Germany Phone: (+49)-8142-66989-10 Fax: (+49)-8142-66989-80 Email: wd at denx.de If a man had a child who'd gone anti-social, killed perhaps, he'd still tend to protect that child. -- McCoy, "The Ultimate Computer", stardate 4731.3
Kumar Gala
AppliedPATCH v2 1/2 powerpc/mpc85xx: Add clear_ddr_tlbs function
In reply to Becky BruceQuoted 6 lines · Becky Bruce
This is useful when we just want to wipe out the TLBs. There's currently a function that resets the ddr tlbs to a different value; it is changed to utilize this function. The new function can be used in conjunction with
setup_ddr_tlbs()for a board to temporarily map/unmap the DDR address range as needed.
Quoted 6 lines
Signed-off-by Becky Bruce <[email protected]>---
arch/powerpc/cpu/mpc85xx/cpu.c | 14 +++----------- arch/powerpc/cpu/mpc85xx/tlb.c | 29 +++++++++++++++++++++++++++++ arch/powerpc/include/asm/mmu.h | 1 + 3 files changed, 33 insertions(+), 11 deletions(-)
applied to 85xx
- k
PATCH v2 1/2 powerpc/mpc85xx: Add clear_ddr_tlbs function
In reply to Becky BruceDear Becky Bruce,
Quoted 6 lines · In message <[email protected]> you wrote:
This is useful when we just want to wipe out the TLBs. There's currently a function that resets the ddr tlbs to a different value; it is changed to utilize this function. The new function can be used in conjunction with
setup_ddr_tlbs()for a board to temporarily map/unmap the DDR address range as needed.
Quoted 6 lines
Signed-off-by Becky Bruce <[email protected]>--- arch/powerpc/cpu/mpc85xx/cpu.c | 14 +++----------- arch/powerpc/cpu/mpc85xx/tlb.c | 29 +++++++++++++++++++++++++++++ arch/powerpc/include/asm/mmu.h | 1 + 3 files changed, 33 insertions(+), 11 deletions(-)
Tested on TQM8555 / TQM8560.
Best regards,
Wolfgang Denk
Signature · 6 lines
DENX Software Engineering GmbH, MD: Wolfgang Denk & Detlev Zundel
HRB 165235 Munich, Office: Kirchenstr.5, D-82194 Groebenzell, Germany
Phone: (+49)-8142-66989-10 Fax: (+49)-8142-66989-80 Email: wd at denx.de
The use of COBOL cripples the mind; its teaching should, therefore,
be regarded as a criminal offence.
-- Edsger W. Dijkstra, SIGPLAN Notices, Volume 17, Number 5