1 /***************************************************************************
3 * Open \______ \ ____ ____ | | _\_ |__ _______ ___
4 * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
5 * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
6 * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
10 * Copyright (C) 2007 by Michael Sevakis
12 * This program is free software; you can redistribute it and/or
13 * modify it under the terms of the GNU General Public License
14 * as published by the Free Software Foundation; either version 2
15 * of the License, or (at your option) any later version.
17 * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
18 * KIND, either express or implied.
20 ****************************************************************************/
27 #define default_interrupt(name) \
28 extern __attribute__((weak,alias("UIRQ"))) void name (void)
30 default_interrupt(EINT0
);
31 default_interrupt(EINT1
);
32 default_interrupt(EINT2
);
33 default_interrupt(EINT3
);
34 default_interrupt(EINT4_7
);
35 default_interrupt(EINT8_23
);
36 default_interrupt(CAM
);
37 default_interrupt(nBATT_FLT
);
38 default_interrupt(TICK
);
39 default_interrupt(WDT_AC97
);
40 default_interrupt(TIMER0
);
41 default_interrupt(TIMER1
);
42 default_interrupt(TIMER2
);
43 default_interrupt(TIMER3
);
44 default_interrupt(TIMER4
);
45 default_interrupt(UART2
);
46 default_interrupt(LCD
);
47 default_interrupt(DMA0
);
48 default_interrupt(DMA1
);
49 default_interrupt(DMA2
);
50 default_interrupt(DMA3
);
51 default_interrupt(SDI
);
52 default_interrupt(SPI0
);
53 default_interrupt(UART1
);
54 default_interrupt(NFCON
);
55 default_interrupt(USBD
);
56 default_interrupt(USBH
);
57 default_interrupt(IIC
);
58 default_interrupt(UART0
);
59 default_interrupt(SPI1
);
60 default_interrupt(RTC
);
61 default_interrupt(ADC
);
63 static void (* const irqvector
[32])(void) __attribute__((__used__
)) =
65 EINT0
, EINT1
, EINT2
, EINT3
,
66 EINT4_7
, EINT8_23
, CAM
, nBATT_FLT
, TICK
, WDT_AC97
,
67 TIMER0
, TIMER1
, TIMER2
, TIMER3
, TIMER4
, UART2
,
68 LCD
, DMA0
, DMA1
, DMA2
, DMA3
, SDI
,
69 SPI0
, UART1
, NFCON
, USBD
, USBH
, IIC
,
70 UART0
, SPI1
, RTC
, ADC
,
73 static const char * const irqname
[32] =
75 "EINT0", "EINT1", "EINT2", "EINT3",
76 "EINT4_7", "EINT8_23", "CAM", "nBATT_FLT", "TICK", "WDT_AC97",
77 "TIMER0", "TIMER1", "TIMER2", "TIMER3", "TIMER4", "UART2",
78 "LCD", "DMA0", "DMA1", "DMA2", "DMA3", "SDI",
79 "SPI0", "UART1", "NFCON", "USBD", "USBH", "IIC",
80 "UART0", "SPI1", "RTC", "ADC"
83 static void UIRQ(void)
85 unsigned int offset
= INTOFFSET
;
86 panicf("Unhandled IRQ %02X: %s", offset
, irqname
[offset
]);
89 void irq_handler(void) __attribute__((interrupt ("IRQ"), naked
));
90 void irq_handler(void)
94 "stmfd sp!, {r0-r3, ip, lr} \r\n"
95 "mov r0, #0x4a000000 \r\n" /* INTOFFSET = 0x4a000014 */
96 "ldr r0, [r0, #0x14] \r\n"
97 "ldr r1, =irqvector \r\n"
98 "ldr r1, [r1, r0, lsl #2] \r\n"
101 "ldmfd sp!, {r0-r3, ip, pc}^ \r\n"
105 void system_reboot(void)
114 void system_exception_wait(void)
117 while ((GPGDAT
& (1 << 0)) == 0); /* Wait for power button */
120 static void set_page_tables(void)
122 /* map every memory region to itself */
123 map_section(0, 0, 0x1000, CACHE_NONE
);
125 /* map RAM to 0 and enable caching for it */
126 map_section(0x30000000, 0, MEMORYSIZE
, CACHE_ALL
);
128 /* enable buffered writing for the framebuffer */
129 map_section((int)FRAME
, (int)FRAME
, 1, BUFFERED
);
132 void memory_init(void)
139 void s3c_regmod32(volatile unsigned long *reg
, unsigned long bits
,
142 int oldstatus
= disable_interrupt_save(IRQ_FIQ_STATUS
);
143 *reg
= (*reg
& ~mask
) | (bits
& mask
);
144 restore_interrupt(oldstatus
);
147 void s3c_regset32(volatile unsigned long *reg
, unsigned long bits
)
149 s3c_regmod32(reg
, bits
, bits
);
152 void s3c_regclr32(volatile unsigned long *reg
, unsigned long bits
)
154 s3c_regmod32(reg
, 0, bits
);
158 void system_prepare_fw_start(void)
161 disable_interrupt(IRQ_FIQ_STATUS
);
166 void system_init(void)
173 INTSUBMSK
= 0xFFFFFFFF;
174 SUBSRCPND
= 0xFFFFFFFF;
180 /* Take care of flash related pins */
189 GPFCON
|= 0x00000AAA;
192 GPGCON
|= 0x01001000;
198 /* TODO: do something with PRIORITY */
200 /* Turn off currently-not or never-needed devices.
201 * Be careful here, it is possible to freeze the device by disabling
202 * clocks at the wrong time.
204 * Turn off AC97, Camera, SPI, IIS, I2C, UARTS, MMC/SD/SDIO Controller
205 * USB device, USB host, NAND flash controller.
207 * IDLE, Sleep, LCDC, PWM timer, GPIO, RTC, and ADC are untouched (on)
212 #elif defined(MINI2440)
213 /* TODO: anything? */
215 #error Unknown target
219 int system_memory_guard(int newmode
)
225 #ifdef HAVE_ADJUSTABLE_CPU_FREQ
227 void set_cpu_frequency(long frequency
)
229 if (frequency
== CPUFREQ_MAX
)
231 asm volatile("mov r0, #0\n"
232 "mrc p15, 0, r0, c1, c0, 0\n"
233 "orr r0, r0, #3<<30\n" /* set to Asynchronous mode*/
234 "mcr p15, 0, r0, c1, c0, 0" : : : "r0");
240 asm volatile("mov r0, #0\n"
241 "mrc p15, 0, r0, c1, c0, 0\n"
242 "bic r0, r0, #3<<30\n" /* set to FastBus mode*/
243 "mcr p15, 0, r0, c1, c0, 0" : : : "r0");
245 FREQ
= CPUFREQ_NORMAL
;