diff options
Diffstat (limited to 'arch/m68k/cpu/cpu.c')
-rw-r--r-- | arch/m68k/cpu/cpu.c | 185 |
1 files changed, 185 insertions, 0 deletions
diff --git a/arch/m68k/cpu/cpu.c b/arch/m68k/cpu/cpu.c new file mode 100644 index 0000000000..5c48add8d9 --- /dev/null +++ b/arch/m68k/cpu/cpu.c @@ -0,0 +1,185 @@ +/* + * Copyright (c) 2008 Carsten Schlote <c.schlote@konzeptpark.de> + * See file CREDITS for list of people who contributed to this project. + * + * This file is part of U-Boot V2. + * + * U-Boot V2 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 3 of the License, or + * (at your option) any later version. + * + * U-Boot V2 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 U-Boot V2. If not, see <http://www.gnu.org/licenses/>. + */ + +/** @file + * A few helper functions for M6kK/Coldfire + */ +#include <common.h> +#include <command.h> +#include <init.h> +#include <asm/proc/processor.h> // FIXME -stup place +#include <asm/arch/mcf54xx-regs.h> + +static uint32_t CACR_shadow = MCF5XXX_CACR_BEC; + +/* + * Reset init value := 0x010C0100 + * MCF5XXX_CACR_DCINVA + * MCF5XXX_CACR_BEC + * MCF5XXX_CACR_BCINVA + * MCF5XXX_CACR_ICINVA + */ + +/** + * Enable processor's instruction cache + */ +void icache_enable (void) +{ + CACR_shadow |= MCF5XXX_CACR_IEC; + mcf5xxx_wr_cacr( CACR_shadow ); +} + +/** + * Disable processor's instruction cache + */ +void icache_disable (void) +{ + CACR_shadow &= ~MCF5XXX_CACR_IEC; + mcf5xxx_wr_cacr( CACR_shadow ); +} + +/** + * Detect processor's current instruction cache status + * @return 0=disabled, 1=enabled + */ +int icache_status (void) +{ + return (CACR_shadow & MCF5XXX_CACR_IEC)?1:0; +} + +/** + * Enable processor's data cache + */ +void dcache_enable (void) +{ + CACR_shadow |= MCF5XXX_CACR_DEC; + mcf5xxx_wr_cacr( CACR_shadow ); +} + +/** + * Disable processor's data cache + */ +void dcache_disable (void) +{ + CACR_shadow &= ~MCF5XXX_CACR_DEC; + mcf5xxx_wr_cacr( CACR_shadow ); +} + +/** + * Detect processor's current instruction cache status + * @return 0=disabled, 1=enabled + */ +int dcache_status (void) +{ + return (CACR_shadow & MCF5XXX_CACR_DEC)?1:0; +} + +/** + * Flush CPU caches to memory + */ +void cpu_cache_flush(void) +{ + uint32_t way, set; + void *addr; + + for ( way=0; way < 4; way++ ) { + addr = (void*)way; + for ( set=0; set < 512; set++ ) { + mcf5xxx_cpushl_bc ( addr ); + addr += 0x10; + } + } +} + +/** + * Flush CPU caches to memory and disable them. + */ +void cpu_cache_disable(void) +{ + uint32_t lastipl; + + lastipl = asm_set_ipl( 7 ); + + cpu_cache_flush(); + mcf5xxx_wr_acr0( 0 ); + mcf5xxx_wr_acr1( 0 ); + mcf5xxx_wr_acr2( 0 ); + mcf5xxx_wr_acr3( 0 ); + + CACR_shadow &= ~MCF5XXX_CACR_IEC; + CACR_shadow &= ~MCF5XXX_CACR_DEC; + mcf5xxx_wr_cacr( CACR_shadow | (MCF5XXX_CACR_DCINVA|MCF5XXX_CACR_ICINVA)); + + lastipl = asm_set_ipl( lastipl ); +} + +/** + * Prepare a "clean" CPU for Linux to run + * @return 0 (always) + * + * This function is called by the generic U-Boot part just before we call + * Linux. It prepares the processor for Linux. + */ +int cleanup_before_linux (void) +{ + /* + * we never enable dcache so we do not need to disable + * it. Linux can be called with icache enabled, so just + * do nothing here + */ + + /* flush I/D-cache */ + cpu_cache_disable(); + + /* reenable icache */ + icache_enable(); + return (0); +} +/** @page m68k_boot_preparation Linux Preparation on M68k/Coldfire + * + * For M68K we never enable data cache so we do not need to disable it again. + * + * Linux can be called with instruction cache enabled. As this is the + * default setting we are running in U-Boot, there's no special preparation + * required. + */ + + +/** Early init of Coldfire V4E CPU + */ +static int cpu_init (void) +{ + /* Enable ICache - branch cache is already on */ + icache_enable(); + + /* + * setup up stacks if necessary + * setup other CPU specifics here to prepare + * handling of exceptions and interrupts + */ +#ifdef CONFIG_USE_IRQ + printf("Prepare CPU interrupts for handlers\n"); + mcf_interrupts_initialize(); +#endif + + return 0; +} + +core_initcall(cpu_init); |