1/* 2 * arch/arm/mach-at91/at91sam9rl.c 3 * 4 * Copyright (C) 2005 SAN People 5 * Copyright (C) 2007 Atmel Corporation 6 * 7 * This file is subject to the terms and conditions of the GNU General Public 8 * License. See the file COPYING in the main directory of this archive for 9 * more details. 10 */ 11 12#include <linux/module.h> 13 14#include <asm/mach/arch.h> 15#include <asm/mach/map.h> 16#include <asm/arch/cpu.h> 17#include <asm/arch/at91sam9rl.h> 18#include <asm/arch/at91_pmc.h> 19#include <asm/arch/at91_rstc.h> 20 21#include "generic.h" 22#include "clock.h" 23 24static struct map_desc at91sam9rl_io_desc[] __initdata = { 25 { 26 .virtual = AT91_VA_BASE_SYS, 27 .pfn = __phys_to_pfn(AT91_BASE_SYS), 28 .length = SZ_16K, 29 .type = MT_DEVICE, 30 }, 31}; 32 33static struct map_desc at91sam9rl_sram_desc[] __initdata = { 34 { 35 .pfn = __phys_to_pfn(AT91SAM9RL_SRAM_BASE), 36 .type = MT_DEVICE, 37 } 38}; 39 40/* -------------------------------------------------------------------- 41 * Clocks 42 * -------------------------------------------------------------------- */ 43 44/* 45 * The peripheral clocks. 46 */ 47static struct clk pioA_clk = { 48 .name = "pioA_clk", 49 .pmc_mask = 1 << AT91SAM9RL_ID_PIOA, 50 .type = CLK_TYPE_PERIPHERAL, 51}; 52static struct clk pioB_clk = { 53 .name = "pioB_clk", 54 .pmc_mask = 1 << AT91SAM9RL_ID_PIOB, 55 .type = CLK_TYPE_PERIPHERAL, 56}; 57static struct clk pioC_clk = { 58 .name = "pioC_clk", 59 .pmc_mask = 1 << AT91SAM9RL_ID_PIOC, 60 .type = CLK_TYPE_PERIPHERAL, 61}; 62static struct clk pioD_clk = { 63 .name = "pioD_clk", 64 .pmc_mask = 1 << AT91SAM9RL_ID_PIOD, 65 .type = CLK_TYPE_PERIPHERAL, 66}; 67static struct clk usart0_clk = { 68 .name = "usart0_clk", 69 .pmc_mask = 1 << AT91SAM9RL_ID_US0, 70 .type = CLK_TYPE_PERIPHERAL, 71}; 72static struct clk usart1_clk = { 73 .name = "usart1_clk", 74 .pmc_mask = 1 << AT91SAM9RL_ID_US1, 75 .type = CLK_TYPE_PERIPHERAL, 76}; 77static struct clk usart2_clk = { 78 .name = "usart2_clk", 79 .pmc_mask = 1 << AT91SAM9RL_ID_US2, 80 .type = CLK_TYPE_PERIPHERAL, 81}; 82static struct clk usart3_clk = { 83 .name = "usart3_clk", 84 .pmc_mask = 1 << AT91SAM9RL_ID_US3, 85 .type = CLK_TYPE_PERIPHERAL, 86}; 87static struct clk mmc_clk = { 88 .name = "mci_clk", 89 .pmc_mask = 1 << AT91SAM9RL_ID_MCI, 90 .type = CLK_TYPE_PERIPHERAL, 91}; 92static struct clk twi0_clk = { 93 .name = "twi0_clk", 94 .pmc_mask = 1 << AT91SAM9RL_ID_TWI0, 95 .type = CLK_TYPE_PERIPHERAL, 96}; 97static struct clk twi1_clk = { 98 .name = "twi1_clk", 99 .pmc_mask = 1 << AT91SAM9RL_ID_TWI1, 100 .type = CLK_TYPE_PERIPHERAL, 101}; 102static struct clk spi_clk = { 103 .name = "spi_clk", 104 .pmc_mask = 1 << AT91SAM9RL_ID_SPI, 105 .type = CLK_TYPE_PERIPHERAL, 106}; 107static struct clk ssc0_clk = { 108 .name = "ssc0_clk", 109 .pmc_mask = 1 << AT91SAM9RL_ID_SSC0, 110 .type = CLK_TYPE_PERIPHERAL, 111}; 112static struct clk ssc1_clk = { 113 .name = "ssc1_clk", 114 .pmc_mask = 1 << AT91SAM9RL_ID_SSC1, 115 .type = CLK_TYPE_PERIPHERAL, 116}; 117static struct clk tc0_clk = { 118 .name = "tc0_clk", 119 .pmc_mask = 1 << AT91SAM9RL_ID_TC0, 120 .type = CLK_TYPE_PERIPHERAL, 121}; 122static struct clk tc1_clk = { 123 .name = "tc1_clk", 124 .pmc_mask = 1 << AT91SAM9RL_ID_TC1, 125 .type = CLK_TYPE_PERIPHERAL, 126}; 127static struct clk tc2_clk = { 128 .name = "tc2_clk", 129 .pmc_mask = 1 << AT91SAM9RL_ID_TC2, 130 .type = CLK_TYPE_PERIPHERAL, 131}; 132static struct clk pwmc_clk = { 133 .name = "pwmc_clk", 134 .pmc_mask = 1 << AT91SAM9RL_ID_PWMC, 135 .type = CLK_TYPE_PERIPHERAL, 136}; 137static struct clk tsc_clk = { 138 .name = "tsc_clk", 139 .pmc_mask = 1 << AT91SAM9RL_ID_TSC, 140 .type = CLK_TYPE_PERIPHERAL, 141}; 142static struct clk dma_clk = { 143 .name = "dma_clk", 144 .pmc_mask = 1 << AT91SAM9RL_ID_DMA, 145 .type = CLK_TYPE_PERIPHERAL, 146}; 147static struct clk udphs_clk = { 148 .name = "udphs_clk", 149 .pmc_mask = 1 << AT91SAM9RL_ID_UDPHS, 150 .type = CLK_TYPE_PERIPHERAL, 151}; 152static struct clk lcdc_clk = { 153 .name = "lcdc_clk", 154 .pmc_mask = 1 << AT91SAM9RL_ID_LCDC, 155 .type = CLK_TYPE_PERIPHERAL, 156}; 157static struct clk ac97_clk = { 158 .name = "ac97_clk", 159 .pmc_mask = 1 << AT91SAM9RL_ID_AC97C, 160 .type = CLK_TYPE_PERIPHERAL, 161}; 162 163static struct clk *periph_clocks[] __initdata = { 164 &pioA_clk, 165 &pioB_clk, 166 &pioC_clk, 167 &pioD_clk, 168 &usart0_clk, 169 &usart1_clk, 170 &usart2_clk, 171 &usart3_clk, 172 &mmc_clk, 173 &twi0_clk, 174 &twi1_clk, 175 &spi_clk, 176 &ssc0_clk, 177 &ssc1_clk, 178 &tc0_clk, 179 &tc1_clk, 180 &tc2_clk, 181 &pwmc_clk, 182 &tsc_clk, 183 &dma_clk, 184 &udphs_clk, 185 &lcdc_clk, 186 &ac97_clk, 187 // irq0 188}; 189 190/* 191 * The two programmable clocks. 192 * You must configure pin multiplexing to bring these signals out. 193 */ 194static struct clk pck0 = { 195 .name = "pck0", 196 .pmc_mask = AT91_PMC_PCK0, 197 .type = CLK_TYPE_PROGRAMMABLE, 198 .id = 0, 199}; 200static struct clk pck1 = { 201 .name = "pck1", 202 .pmc_mask = AT91_PMC_PCK1, 203 .type = CLK_TYPE_PROGRAMMABLE, 204 .id = 1, 205}; 206 207static void __init at91sam9rl_register_clocks(void) 208{ 209 int i; 210 211 for (i = 0; i < ARRAY_SIZE(periph_clocks); i++) 212 clk_register(periph_clocks[i]); 213 214 clk_register(&pck0); 215 clk_register(&pck1); 216} 217 218/* -------------------------------------------------------------------- 219 * GPIO 220 * -------------------------------------------------------------------- */ 221 222static struct at91_gpio_bank at91sam9rl_gpio[] = { 223 { 224 .id = AT91SAM9RL_ID_PIOA, 225 .offset = AT91_PIOA, 226 .clock = &pioA_clk, 227 }, { 228 .id = AT91SAM9RL_ID_PIOB, 229 .offset = AT91_PIOB, 230 .clock = &pioB_clk, 231 }, { 232 .id = AT91SAM9RL_ID_PIOC, 233 .offset = AT91_PIOC, 234 .clock = &pioC_clk, 235 }, { 236 .id = AT91SAM9RL_ID_PIOD, 237 .offset = AT91_PIOD, 238 .clock = &pioD_clk, 239 } 240}; 241 242static void at91sam9rl_reset(void) 243{ 244 at91_sys_write(AT91_RSTC_CR, AT91_RSTC_KEY | AT91_RSTC_PROCRST | AT91_RSTC_PERRST); 245} 246 247 248/* -------------------------------------------------------------------- 249 * AT91SAM9RL processor initialization 250 * -------------------------------------------------------------------- */ 251 252void __init at91sam9rl_initialize(unsigned long main_clock) 253{ 254 unsigned long cidr, sram_size; 255 256 /* Map peripherals */ 257 iotable_init(at91sam9rl_io_desc, ARRAY_SIZE(at91sam9rl_io_desc)); 258 259 cidr = at91_sys_read(AT91_DBGU_CIDR); 260 261 switch (cidr & AT91_CIDR_SRAMSIZ) { 262 case AT91_CIDR_SRAMSIZ_32K: 263 sram_size = 2 * SZ_16K; 264 break; 265 case AT91_CIDR_SRAMSIZ_16K: 266 default: 267 sram_size = SZ_16K; 268 } 269 270 at91sam9rl_sram_desc->virtual = AT91_IO_VIRT_BASE - sram_size; 271 at91sam9rl_sram_desc->length = sram_size; 272 273 /* Map SRAM */ 274 iotable_init(at91sam9rl_sram_desc, ARRAY_SIZE(at91sam9rl_sram_desc)); 275 276 at91_arch_reset = at91sam9rl_reset; 277 at91_extern_irq = (1 << AT91SAM9RL_ID_IRQ0); 278 279 /* Init clock subsystem */ 280 at91_clock_init(main_clock); 281 282 /* Register the processor-specific clocks */ 283 at91sam9rl_register_clocks(); 284 285 /* Register GPIO subsystem */ 286 at91_gpio_init(at91sam9rl_gpio, 4); 287} 288 289/* -------------------------------------------------------------------- 290 * Interrupt initialization 291 * -------------------------------------------------------------------- */ 292 293/* 294 * The default interrupt priority levels (0 = lowest, 7 = highest). 295 */ 296static unsigned int at91sam9rl_default_irq_priority[NR_AIC_IRQS] __initdata = { 297 7, /* Advanced Interrupt Controller */ 298 7, /* System Peripherals */ 299 1, /* Parallel IO Controller A */ 300 1, /* Parallel IO Controller B */ 301 1, /* Parallel IO Controller C */ 302 1, /* Parallel IO Controller D */ 303 5, /* USART 0 */ 304 5, /* USART 1 */ 305 5, /* USART 2 */ 306 5, /* USART 3 */ 307 0, /* Multimedia Card Interface */ 308 6, /* Two-Wire Interface 0 */ 309 6, /* Two-Wire Interface 1 */ 310 5, /* Serial Peripheral Interface */ 311 4, /* Serial Synchronous Controller 0 */ 312 4, /* Serial Synchronous Controller 1 */ 313 0, /* Timer Counter 0 */ 314 0, /* Timer Counter 1 */ 315 0, /* Timer Counter 2 */ 316 0, 317 0, /* Touch Screen Controller */ 318 0, /* DMA Controller */ 319 2, /* USB Device High speed port */ 320 2, /* LCD Controller */ 321 6, /* AC97 Controller */ 322 0, 323 0, 324 0, 325 0, 326 0, 327 0, 328 0, /* Advanced Interrupt Controller */ 329}; 330 331void __init at91sam9rl_init_interrupts(unsigned int priority[NR_AIC_IRQS]) 332{ 333 if (!priority) 334 priority = at91sam9rl_default_irq_priority; 335 336 /* Initialize the AIC interrupt controller */ 337 at91_aic_init(priority); 338 339 /* Enable GPIO interrupts */ 340 at91_gpio_irq_setup(); 341} 342