1/* 2 * Board setup routines for the Motorola PrPMC2800 3 * 4 * Author: Dale Farnsworth <dale@farnsworth.org> 5 * 6 * 2007 (c) MontaVista, Software, Inc. This file is licensed under 7 * the terms of the GNU General Public License version 2. This program 8 * is licensed "as is" without any warranty of any kind, whether express 9 * or implied. 10 */ 11 12#include <linux/stddef.h> 13#include <linux/kernel.h> 14#include <linux/delay.h> 15#include <linux/interrupt.h> 16#include <linux/seq_file.h> 17 18#include <asm/machdep.h> 19#include <asm/prom.h> 20#include <asm/system.h> 21#include <asm/time.h> 22 23#include <mm/mmu_decl.h> 24 25#include <sysdev/mv64x60.h> 26 27#define MV64x60_MPP_CNTL_0 0x0000 28#define MV64x60_MPP_CNTL_2 0x0008 29 30#define MV64x60_GPP_IO_CNTL 0x0000 31#define MV64x60_GPP_LEVEL_CNTL 0x0010 32#define MV64x60_GPP_VALUE_SET 0x0018 33 34#define PLATFORM_NAME_MAX 32 35 36static char prpmc2800_platform_name[PLATFORM_NAME_MAX]; 37 38static void __iomem *mv64x60_mpp_reg_base; 39static void __iomem *mv64x60_gpp_reg_base; 40 41static void __init prpmc2800_setup_arch(void) 42{ 43 struct device_node *np; 44 phys_addr_t paddr; 45 const unsigned int *reg; 46 47 /* 48 * ioremap mpp and gpp registers in case they are later 49 * needed by prpmc2800_reset_board(). 50 */ 51 np = of_find_compatible_node(NULL, NULL, "marvell,mv64360-mpp"); 52 reg = of_get_property(np, "reg", NULL); 53 paddr = of_translate_address(np, reg); 54 of_node_put(np); 55 mv64x60_mpp_reg_base = ioremap(paddr, reg[1]); 56 57 np = of_find_compatible_node(NULL, NULL, "marvell,mv64360-gpp"); 58 reg = of_get_property(np, "reg", NULL); 59 paddr = of_translate_address(np, reg); 60 of_node_put(np); 61 mv64x60_gpp_reg_base = ioremap(paddr, reg[1]); 62 63#ifdef CONFIG_PCI 64 mv64x60_pci_init(); 65#endif 66 67 printk("Motorola %s\n", prpmc2800_platform_name); 68} 69 70static void prpmc2800_reset_board(void) 71{ 72 u32 temp; 73 74 local_irq_disable(); 75 76 temp = in_le32(mv64x60_mpp_reg_base + MV64x60_MPP_CNTL_0); 77 temp &= 0xFFFF0FFF; 78 out_le32(mv64x60_mpp_reg_base + MV64x60_MPP_CNTL_0, temp); 79 80 temp = in_le32(mv64x60_gpp_reg_base + MV64x60_GPP_LEVEL_CNTL); 81 temp |= 0x00000004; 82 out_le32(mv64x60_gpp_reg_base + MV64x60_GPP_LEVEL_CNTL, temp); 83 84 temp = in_le32(mv64x60_gpp_reg_base + MV64x60_GPP_IO_CNTL); 85 temp |= 0x00000004; 86 out_le32(mv64x60_gpp_reg_base + MV64x60_GPP_IO_CNTL, temp); 87 88 temp = in_le32(mv64x60_mpp_reg_base + MV64x60_MPP_CNTL_2); 89 temp &= 0xFFFF0FFF; 90 out_le32(mv64x60_mpp_reg_base + MV64x60_MPP_CNTL_2, temp); 91 92 temp = in_le32(mv64x60_gpp_reg_base + MV64x60_GPP_LEVEL_CNTL); 93 temp |= 0x00080000; 94 out_le32(mv64x60_gpp_reg_base + MV64x60_GPP_LEVEL_CNTL, temp); 95 96 temp = in_le32(mv64x60_gpp_reg_base + MV64x60_GPP_IO_CNTL); 97 temp |= 0x00080000; 98 out_le32(mv64x60_gpp_reg_base + MV64x60_GPP_IO_CNTL, temp); 99 100 out_le32(mv64x60_gpp_reg_base + MV64x60_GPP_VALUE_SET, 0x00080004); 101} 102 103static void prpmc2800_restart(char *cmd) 104{ 105 volatile ulong i = 10000000; 106 107 prpmc2800_reset_board(); 108 109 while (i-- > 0); 110 panic("restart failed\n"); 111} 112 113#ifdef CONFIG_NOT_COHERENT_CACHE 114#define PPRPM2800_COHERENCY_SETTING "off" 115#else 116#define PPRPM2800_COHERENCY_SETTING "on" 117#endif 118 119void prpmc2800_show_cpuinfo(struct seq_file *m) 120{ 121 seq_printf(m, "Vendor\t\t: Motorola\n"); 122 seq_printf(m, "coherency\t: %s\n", PPRPM2800_COHERENCY_SETTING); 123} 124 125/* 126 * Called very early, device-tree isn't unflattened 127 */ 128static int __init prpmc2800_probe(void) 129{ 130 unsigned long root = of_get_flat_dt_root(); 131 unsigned long len = PLATFORM_NAME_MAX; 132 void *m; 133 134 if (!of_flat_dt_is_compatible(root, "motorola,PrPMC2800")) 135 return 0; 136 137 /* Update ppc_md.name with name from dt */ 138 m = of_get_flat_dt_prop(root, "model", &len); 139 if (m) 140 strncpy(prpmc2800_platform_name, m, 141 min((int)len, PLATFORM_NAME_MAX - 1)); 142 143 _set_L2CR(_get_L2CR() | L2CR_L2E); 144 return 1; 145} 146 147define_machine(prpmc2800){ 148 .name = prpmc2800_platform_name, 149 .probe = prpmc2800_probe, 150 .setup_arch = prpmc2800_setup_arch, 151 .init_early = mv64x60_init_early, 152 .show_cpuinfo = prpmc2800_show_cpuinfo, 153 .init_IRQ = mv64x60_init_irq, 154 .get_irq = mv64x60_get_irq, 155 .restart = prpmc2800_restart, 156 .calibrate_decr = generic_calibrate_decr, 157}; 158