uboot/arch/powerpc/cpu/mpc86xx/mp.c
<<
>>
Prefs
   1/*
   2 * Copyright 2008-2010 Freescale Semiconductor, Inc.
   3 *
   4 * See file CREDITS for list of people who contributed to this
   5 * project.
   6 *
   7 * This program is free software; you can redistribute it and/or
   8 * modify it under the terms of the GNU General Public License as
   9 * published by the Free Software Foundation; either version 2 of
  10 * the License, or (at your option) any later version.
  11 *
  12 * This program is distributed in the hope that it will be useful,
  13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
  14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  15 * GNU General Public License for more details.
  16 *
  17 * You should have received a copy of the GNU General Public License
  18 * along with this program; if not, write to the Free Software
  19 * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
  20 * MA 02111-1307 USA
  21 */
  22
  23#include <common.h>
  24#include <asm/processor.h>
  25#include <asm/mmu.h>
  26#include <ioports.h>
  27#include <lmb.h>
  28#include <asm/io.h>
  29#include <asm/mp.h>
  30
  31DECLARE_GLOBAL_DATA_PTR;
  32
  33int cpu_reset(int nr)
  34{
  35        /* dummy function so common/cmd_mp.c will build
  36         * should be implemented in the future, when cpu_release()
  37         * is supported.  Be aware there may be a similiar bug
  38         * as exists on MPC85xx w/its PIC having a timing window
  39         * associated to resetting the core */
  40        return 1;
  41}
  42
  43int cpu_status(int nr)
  44{
  45        /* dummy function so common/cmd_mp.c will build */
  46        return 0;
  47}
  48
  49int cpu_disable(int nr)
  50{
  51        volatile immap_t *immap = (immap_t *) CONFIG_SYS_CCSRBAR;
  52        volatile ccsr_gur_t *gur = &immap->im_gur;
  53
  54        switch (nr) {
  55        case 0:
  56                setbits_be32(&gur->devdisr, MPC86xx_DEVDISR_CPU0);
  57                break;
  58        case 1:
  59                setbits_be32(&gur->devdisr, MPC86xx_DEVDISR_CPU1);
  60                break;
  61        default:
  62                printf("Invalid cpu number for disable %d\n", nr);
  63                return 1;
  64        }
  65
  66        return 0;
  67}
  68
  69int is_core_disabled(int nr) {
  70        immap_t *immap = (immap_t *) CONFIG_SYS_CCSRBAR;
  71        ccsr_gur_t *gur = &immap->im_gur;
  72        u32 devdisr = in_be32(&gur->devdisr);
  73
  74        switch (nr) {
  75        case 0:
  76                return (devdisr & MPC86xx_DEVDISR_CPU0);
  77        case 1:
  78                return (devdisr & MPC86xx_DEVDISR_CPU1);
  79        default:
  80                printf("Invalid cpu number for disable %d\n", nr);
  81        }
  82
  83        return 0;
  84}
  85
  86int cpu_release(int nr, int argc, char * const argv[])
  87{
  88        /* dummy function so common/cmd_mp.c will build
  89         * should be implemented in the future */
  90        return 1;
  91}
  92
  93u32 determine_mp_bootpg(void)
  94{
  95        /* if we have 4G or more of memory, put the boot page at 4Gb-1M */
  96        if ((u64)gd->ram_size > 0xfffff000)
  97                return (0xfff00000);
  98
  99        return (gd->ram_size - (1024 * 1024));
 100}
 101
 102void cpu_mp_lmb_reserve(struct lmb *lmb)
 103{
 104        u32 bootpg = determine_mp_bootpg();
 105
 106        /* tell u-boot we stole a page */
 107        lmb_reserve(lmb, bootpg, 4096);
 108}
 109
 110/*
 111 * Copy the code for other cpus to execute into an
 112 * aligned location accessible via BPTR
 113 */
 114void setup_mp(void)
 115{
 116        extern ulong __secondary_start_page;
 117        ulong fixup = (ulong)&__secondary_start_page;
 118        u32 bootpg = determine_mp_bootpg();
 119        u32 bootpg_va;
 120
 121        if (bootpg >= CONFIG_SYS_MAX_DDR_BAT_SIZE) {
 122                /* We're not covered by the DDR mapping, set up BAT  */
 123                write_bat(DBAT7, CONFIG_SYS_SCRATCH_VA | BATU_BL_128K |
 124                          BATU_VS | BATU_VP,
 125                          bootpg | BATL_PP_RW | BATL_MEMCOHERENCE);
 126                bootpg_va = CONFIG_SYS_SCRATCH_VA;
 127        } else {
 128                bootpg_va = bootpg;
 129        }
 130
 131        memcpy((void *)bootpg_va, (void *)fixup, 4096);
 132        flush_cache(bootpg_va, 4096);
 133
 134        /* remove the temporary BAT mapping */
 135        if (bootpg >= CONFIG_SYS_MAX_DDR_BAT_SIZE)
 136                write_bat(DBAT7, 0, 0);
 137
 138        /* If the physical location of bootpg is not at fff00000, set BPTR */
 139        if (bootpg != 0xfff00000)
 140                out_be32((uint *)(CONFIG_SYS_CCSRBAR + 0x20), 0x80000000 |
 141                         (bootpg >> 12));
 142}
 143