summaryrefslogtreecommitdiff
path: root/firmware/target/arm
diff options
context:
space:
mode:
Diffstat (limited to 'firmware/target/arm')
-rw-r--r--firmware/target/arm/imx31/crt0.S422
-rw-r--r--firmware/target/arm/imx31/gigabeat-s/avic-imx31.c305
-rw-r--r--firmware/target/arm/imx31/gigabeat-s/avic-imx31.h124
-rw-r--r--firmware/target/arm/imx31/gigabeat-s/kernel-imx31.c55
-rw-r--r--firmware/target/arm/imx31/gigabeat-s/lcd-as-imx31.S222
-rw-r--r--firmware/target/arm/imx31/gigabeat-s/lcd-imx31.c224
-rw-r--r--firmware/target/arm/imx31/gigabeat-s/mmu-imx31.c4
-rw-r--r--firmware/target/arm/imx31/gigabeat-s/pcm-imx31.c8
-rw-r--r--firmware/target/arm/imx31/gigabeat-s/system-imx31.c18
-rw-r--r--firmware/target/arm/imx31/gigabeat-s/system-target.h20
10 files changed, 528 insertions, 874 deletions
diff --git a/firmware/target/arm/imx31/crt0.S b/firmware/target/arm/imx31/crt0.S
index 2be2510bbd..9d50888536 100644
--- a/firmware/target/arm/imx31/crt0.S
+++ b/firmware/target/arm/imx31/crt0.S
@@ -24,7 +24,7 @@
24 .global start 24 .global start
25start: 25start:
26 b newstart 26 b newstart
27 .space 4*16 27 .space 4*12 /* Space for low vectors */
28 28
29 29
30/* Arm bootloader and startup code based on startup.s from the iPodLinux loader 30/* Arm bootloader and startup code based on startup.s from the iPodLinux loader
@@ -35,86 +35,53 @@ start:
35 */ 35 */
36 36
37newstart: 37newstart:
38 msr cpsr, #0xd3 /* enter supervisor mode, disable IRQ */ 38 msr cpsr_c, #0xd3 /* enter supervisor mode, disable IRQ/FIQ */
39 39
40#if !defined(BOOTLOADER) 40#ifdef BOOTLOADER
41#if !defined(DEBUG) 41 ldr r2, =remap_start
42 /* Copy exception handler code to address 0 */ 42 ldr r3, =remap_end
43 ldr r2, =_vectorsstart 43 ldr r5, =TTB_BASE_ADDR /* TTB pointer */
44 ldr r3, =_vectorsend 44 ldr r6, =IRAM_BASE_ADDR
45 ldr r4, =_vectorscopy 45 mov r1, r6
461: 46
47 cmp r3, r2 471:
48 ldrhi r5, [r4], #4 48 cmp r3, r2
49 strhi r5, [r2], #4 49 ldrhi r4, [r2], #4
50 bhi 1b 50 strhi r4, [r1], #4
51#else 51 bhi 1b
52 ldr r1, =vectors 52
53 ldr r0, =irq_handler 53 mov pc, r6
54 str r0, [r1, #24]
55 ldr r0, =fiq_handler
56 str r0, [r1, #28]
57#endif
58
59 /* Zero out IBSS */
60 ldr r2, =_iedata
61 ldr r3, =_iend
62 mov r4, #0
631:
64 cmp r3, r2
65 strhi r4, [r2], #4
66 bhi 1b
67
68 /* Copy the IRAM */
69 ldr r2, =_iramcopy
70 ldr r3, =_iramstart
71 ldr r4, =_iramend
721:
73 cmp r4, r3
74 ldrhi r5, [r2], #4
75 strhi r5, [r3], #4
76 bhi 1b
77#endif /* !BOOTLOADER */
78
79 /* Initialise bss section to zero */
80 ldr r2, =_edata
81 ldr r3, =_end
82 mov r4, #0
831:
84 cmp r3, r2
85 strhi r4, [r2], #4
86 bhi 1b
87 54
88 /* Set up some stack and munge it with 0xdeadbeef */ 55remap_start:
89 ldr sp, =stackend 56 mrc p15, 0, r3, c1, c0, 0 /* perform writeback if D cache is enabled */
90 mov r3, sp 57 tst r3, #(1 << 2)
91 ldr r2, =stackbegin 58 tsteq r3, #(1 << 12)
92 ldr r4, =0xdeadbeef 59 mcrne p15, 0, r0, c7, c10, 0 /* clean dcache */
931: 60 mov r0, #0
94 cmp r3, r2 61 mcrne p15, 0, r0, c7, c7, 0 /* invalidate I cache and D cache */
95 strhi r4, [r2], #4 62 mcr p15, 0, r0, c8, c7, 0 /* invalidate TLBs */
96 bhi 1b 63 mcr p15, 0, r0, c7, c10, 4 /* Drain the write buffer */
97 64
98#ifdef BOOTLOADER 65 mcr p15, 0, r0, c13, c0, 0
99/* Code for ARM bootloader targets other than iPod go here */ 66 mcr p15, 0, r0, c13, c0, 1
100
101 mov r0, #0
102 mcr 15, 0, r0, c7, c7, 0 /* invalidate I cache and D cache */
103 mcr 15, 0, r0, c8, c7, 0 /* invalidate TLBs */
104 mcr 15, 0, r0, c7, c10, 4 /* Drain the write buffer */
105 67
106 /* Also setup the Peripheral Port Remap register inside the core */ 68 /* Also setup the Peripheral Port Remap register inside the core */
107 ldr r0, =0x40000015 /* start from AIPS 2GB region */ 69 mov r0, #0x40000000 /* start from AIPS 2GB region */
108 mcr p15, 0, r0, c15, c2, 4 70 add r0, r0, #0x15
71 mcr p15, 0, r0, c15, c2, 4
109 72
110 /*** L2 Cache setup/invalidation/disable ***/ 73 /*** L2 Cache setup/invalidation/disable ***/
111 /* Disable L2 cache first */ 74 /* Disable L2 cache first */
112 ldr r0, =L2CC_BASE_ADDR 75 mov r0, #L2CC_BASE_ADDR
113 ldr r2, [r0, #L2_CACHE_CTL_REG] 76 mov r1, #0
114 bic r2, r2, #0x1 77 str r1, [r0, #L2_CACHE_CTL_REG]
115 str r2, [r0, #L2_CACHE_CTL_REG] 78
116 79 /* Disble L1 caches and memory manager */
117 80 bic r3, r3, #(1 << 1)
81 bic r3, r3, #(1 << 2)
82 bic r3, r3, #(1 << 12)
83 mcr p15, 0, r3, c1, c0, 0
84
118 /* 85 /*
119 * Configure L2 Cache: 86 * Configure L2 Cache:
120 * - 128k size(16k way) 87 * - 128k size(16k way)
@@ -122,42 +89,21 @@ newstart:
122 * - 0 ws TAG/VALID/DIRTY 89 * - 0 ws TAG/VALID/DIRTY
123 * - 4 ws DATA R/W 90 * - 4 ws DATA R/W
124 */ 91 */
125 ldr r1, [r0, #L2_CACHE_AUX_CTL_REG] 92 mov r1, #0x00130000
126 and r1, r1, #0xFE000000 93 orr r1, r1, #0x24
127 ldr r2, =0x00030024 94 str r1, [r0, #L2_CACHE_AUX_CTL_REG]
128 orr r1, r1, r2
129 str r1, [r0, #L2_CACHE_AUX_CTL_REG]
130 95
131 /* Invalidate L2 */ 96 /* Invalidate L2 */
132 ldr r1, =0x000000FF 97 mov r1, #0x000000FF
133 str r1, [r0, #L2_CACHE_INV_WAY_REG] 98 str r1, [r0, #L2_CACHE_INV_WAY_REG]
134L2_loop: 99L2_loop:
135 /* Poll Invalidate By Way register */ 100 /* Poll Invalidate By Way register */
136 ldr r2, [r0, #L2_CACHE_INV_WAY_REG] 101 ldr r2, [r0, #L2_CACHE_INV_WAY_REG]
137 cmp r2, #0 102 cmp r2, #0
138 bne L2_loop 103 bne L2_loop
104
139 /*** End of L2 operations ***/ 105 /*** End of L2 operations ***/
140 /* Set up stack for IRQ mode */
141 mov r0,#0xd2
142 msr cpsr, r0
143 ldr sp, =irq_stack
144 /* Set up stack for FIQ mode */
145 mov r0,#0xd1
146 msr cpsr, r0
147 ldr sp, =fiq_stack
148 106
149 /* Let abort and undefined modes use IRQ stack */
150 mov r0,#0xd7
151 msr cpsr, r0
152 ldr sp, =irq_stack
153 mov r0,#0xdb
154 msr cpsr, r0
155 ldr sp, =irq_stack
156 /* Switch to supervisor mode */
157 mov r0,#0xd3
158 msr cpsr, r0
159 ldr sp, =stackend
160
161 /*remap memory as well as exception vectors*/ 107 /*remap memory as well as exception vectors*/
162 /*for now this will be done in bootloader, especially 108 /*for now this will be done in bootloader, especially
163 if usb will be needed within the bootloader to load the 109 if usb will be needed within the bootloader to load the
@@ -165,172 +111,155 @@ L2_loop:
165 (whether they be swi or irq)*/ 111 (whether they be swi or irq)*/
166 112
167 /* TTB Initialisation */ 113 /* TTB Initialisation */
168 ldr r3, =(0x80000000+64*1024*1024-TTB_SIZE) 114 mov r3, r5
169 mov r1, #0 115 add r2, r3, #TTB_SIZE
170 ldr r2, =(0x80000000+64*1024*1024) 116 mov r1, #0
171ttbloop: 117ttbloop:
172 str r1, [r3], #4 118 str r1, [r3], #4
173 cmp r3, r2 119 cmp r3, r2
174 bne ttbloop 120 bne ttbloop
175 121
176 /* Set TTB base address */ 122 /* Set TTB base address */
177 ldr r3, =(0x80000000+64*1024*1024-TTB_SIZE) 123 mov r3, r5
178 mcr 15, 0 ,r3, cr2, cr0, 0 124 mcr p15, 0, r3, c2, c0, 0
179 /* Set all domains to manager status */ 125 /* Set all domains to manager status */
180 mvn r3, #0 126 mvn r3, #0
181 mcr 15, 0, r3, cr3, cr0, 0 127 mcr p15, 0, r3, c3, c0, 0
182 128
183 /* Set page tables */ 129 /* Set page tables */
184 130
185 /* Map each memory loc to itself, no cache */ 131 /* Map each memory loc to itself, no cache */
186 mov r1, #0 /* Physical address */ 132 mov r1, #0 /* Physical address */
187 ldr r3, =(0x80000000+64*1024*1024-TTB_SIZE) /* TTB pointer */ 133 mov r3, r5
188 ldr r4, =(0x80000000+64*1024*1024-TTB_SIZE+0x4000) /* End position */ 134 add r4, r3, #TTB_SIZE /* End position */
189maploop1: 135maploop1:
190 mov r2, r1 136 mov r2, r1
191 orr r2, r2, #(1<<10) /* superuser - r/w, user - no access */ 137 orr r2, r2, #(1<<10) /* superuser - r/w, user - no access */
192 //orr r2, r2, #(0<<5) /* domain 0th */ 138 //orr r2, r2, #(0<<5) /* domain 0th */
193 orr r2, r2, #(1<<4) /* should be "1" */ 139 orr r2, r2, #(1<<4) /* should be "1" */
194 orr r2, r2, #(1<<1) /* Section signature */ 140 orr r2, r2, #(1<<1) /* Section signature */
195 str r2, [r3], #4 141 str r2, [r3], #4
196 add r1, r1, #(1<<20) 142 add r1, r1, #(1<<20)
197 cmp r3, r4 143 cmp r3, r4
198 bne maploop1 144 bne maploop1
199 145
200 /* Map 0x80000000 -> 0x0, cached */ 146 /* Map 0x80000000 -> 0x0, cached */
201 mov r1, #0x80000000 /* Physical address */ 147 mov r1, #0x80000000 /* Physical address */
202 ldr r3, =(0x80000000+64*1024*1024-TTB_SIZE) /* TTB pointer */ 148 mov r3, r5 /* TTB pointer */
203 ldr r4, =(0x80000000+64*1024*1024-TTB_SIZE+256) /* End position */ 149 add r4, r3, #64*4 /* End position */
204maploop2: 150maploop2:
205 mov r2, r1 151 mov r2, r1
206 orr r2, r2, #(1<<10) /* superuser - r/w, user - no access */ 152 orr r2, r2, #(1<<10) /* superuser - r/w, user - no access */
207 //orr r2, r2, #(0<<5) /* domain 0th */ 153 //orr r2, r2, #(0<<5) /* domain 0th */
208 orr r2, r2, #(1<<4) /* should be "1" */ 154 orr r2, r2, #(1<<4) /* should be "1" */
209 orr r2, r2, #(1<<3) /* cache flags */ 155 orr r2, r2, #(1<<3) /* cache flags */
210 orr r2, r2, #(1<<2) /* more cache stuff */ 156 orr r2, r2, #(1<<2) /* more cache stuff */
211 orr r2, r2, #(1<<1) /* Section signature */ 157 orr r2, r2, #(1<<1) /* Section signature */
212 str r2, [r3], #4 158 str r2, [r3], #4
213 add r1, r1, #(1<<20) 159 add r1, r1, #(1<<20)
214 cmp r3, r4 160 bic r6, r1, #0xf0000000
215 bne maploop2 161 cmp r6, #0x00100000 /* Skip framebuffer */
162 addeq r1, r1, #(1<<20)
163 cmp r3, r4
164 bne maploop2
216 165
217 /* Enable MMU */ 166 /* Enable MMU */
218 mrc 15, 0, r3, cr1, cr0, 0 167
219 tst r3, #0x4 168 mov r0, #0
220 bleq clean_dcache 169 mcr p15, 0, r0, c8, c7, 0 /* Invalidate TLB */
221 tst r3, #0x1000 170 mcr p15, 0, r0, c7, c7, 0 /* Invalidate icache and dcache */
222 bleq clean_dcache 171#if 1
223 mov r0, #0 172 mrc p15, 0, r0, c1, c0, 1
224 173 bic r0, r0, #0x70
225 mcr 15, 0, r0, cr8, cr7, 0 /* Invalidate TLB */ 174 bic r0, r0, #0x07
226 mcr 15, 0, r0, cr7, cr7, 0 /* Invalidate icache and dcache */ 175 mcr p15, 0, r0, c1, c0, 1
227 mrc 15, 0, r0, cr1, cr0, 0 176#endif
228 orr r0, r0, #1 /* enable mmu bit */ 177 mrc p15, 0, r0, c1, c0, 0
229 orr r0, r0, #(1<<2) /* enable dcache */ 178 orr r0, r0, #(1 << 0) /* enable mmu bit */
230 orr r0, r0, #(1<<12) /* enable icache */ 179 orr r0, r0, #(1 << 2) /* enable dcache */
231 mcr 15, 0, r0, cr1, cr0, 0 180 bic r0, r0, #(1 << 11) /* no program flow prediction */
181 orr r0, r0, #(1 << 12) /* enable icache */
182 bic r0, r0, #(1 << 13) /* low vectors */
183 orr r0, r0, #(1 << 14) /* Round-robin */
184 bic r0, r0, #(1 << 21) /* No low latency interrupt */
185 mcr p15, 0, r0, c1, c0, 0
232 nop 186 nop
233 nop 187 nop
234 nop 188 nop
235 nop 189 nop
190 ldr pc, L_post_remap
191L_post_remap:
192 .word remap_end
193remap_end:
236 194
237 mov r0,#0 195#endif /* BOOTLOADER */
238 ldr r1,=_vectorstart
239 mov r2,#0
240
241lp: ldr r3,[r1]
242 add r1,r1,#4
243 str r3,[r0]
244 add r0,r0,#4
245 add r2,r2,#1
246 cmp r2,#16
247 bne lp
248 bl main
249
250.section .vectors,"aw"
251_vectorstart:
252 ldr pc, [pc, #24]
253 ldr pc, [pc, #24]
254 ldr pc, [pc, #24]
255 ldr pc, [pc, #24]
256 ldr pc, [pc, #24]
257 ldr pc, [pc, #24]
258 ldr pc, [pc, #24]
259 ldr pc, [pc, #24]
260
261 /* Exception vectors */
262 .global vectors
263vectors:
264 .word start
265 .word undef_instr_handler
266 .word software_int_handler
267 .word prefetch_abort_handler
268 .word data_abort_handler
269 .word reserved_handler
270 .word irqz
271 .word fiqz
272
273 .text
274 .global irq
275 .global fiq
276 .global UIE
277
278undef_instr_handler:
279 mov r0, lr
280 mov r1, #0
281 b UIE
282
283software_int_handler:
284reserved_handler:
285 bl irq_handler
286 movs pc, lr
287
288prefetch_abort_handler:
289 sub r0, lr, #4
290 mov r1, #1
291 b UIE
292
293data_abort_handler:
294 sub r0, lr, #8
295 mov r1, #2
296 b UIE
297
298/*not working....if we get here, let someone
299know....*/
300irqz: bl irq_handler
301fiqz: bl fiq_handler
302
303UIE:
304 b UIE
305 196
306/* 256 words of IRQ stack */ 197#ifndef BOOTLOADER
307 .space 256*4 198 /* Copy exception handler code to address 0 */
308irq_stack: 199 ldr r2, =_vectorsstart
200 ldr r3, =_vectorsend
201 ldr r4, =_vectorscopy
2021:
203 cmp r3, r2
204 ldrhi r5, [r4], #4
205 strhi r5, [r2], #4
206 bhi 1b
309 207
310/* 256 words of FIQ stack */ 208 /* Zero out IBSS */
311 .space 256*4 209 ldr r2, =_iedata
312fiq_stack: 210 ldr r3, =_iend
211 mov r4, #0
2121:
213 cmp r3, r2
214 strhi r4, [r2], #4
215 bhi 1b
313 216
217 /* Copy the IRAM */
218 ldr r2, =_iramcopy
219 ldr r3, =_iramstart
220 ldr r4, =_iramend
2211:
222 cmp r4, r3
223 ldrhi r5, [r2], #4
224 strhi r5, [r3], #4
225 bhi 1b
226#endif /* BOOTLOADER */
314 227
315#else /* BOOTLOADER */ 228 /* Initialise bss section to zero */
229 ldr r2, =_edata
230 ldr r3, =_end
231 mov r4, #0
2321:
233 cmp r3, r2
234 strhi r4, [r2], #4
235 bhi 1b
236
237 /* Set up some stack and munge it with 0xdeadbeef */
238 ldr sp, =stackend
239 ldr r2, =stackbegin
240 ldr r3, =0xdeadbeef
2411:
242 cmp sp, r2
243 strhi r3, [r2], #4
244 bhi 1b
245
246 /* Set up stack for IRQ mode */
247 msr cpsr_c, #0xd2
248 ldr sp, =irq_stack
316 249
317 /* Set up stack for IRQ mode */
318 msr cpsr_c, #0xd2
319 ldr sp, =irq_stack
320 /* Set up stack for FIQ mode */ 250 /* Set up stack for FIQ mode */
321 msr cpsr_c, #0xd1 251 msr cpsr_c, #0xd1
322 ldr sp, =fiq_stack 252 ldr sp, =fiq_stack
323 253
324 /* Let abort and undefined modes use IRQ stack */ 254 /* Let abort and undefined modes use IRQ stack */
325 msr cpsr_c, #0xd7 255 msr cpsr_c, #0xd7
326 ldr sp, =irq_stack 256 ldr sp, =irq_stack
327 msr cpsr_c, #0xdb 257 msr cpsr_c, #0xdb
328 ldr sp, =irq_stack 258 ldr sp, =irq_stack
329 /* Switch to supervisor mode */ 259
330 msr cpsr_c, #0xd3 260 /* Switch back to supervisor mode */
331 ldr sp, =stackend 261 msr cpsr_c, #0xd3
332 bl main 262 bl main
333 /* main() should never return */
334 263
335/* Exception handlers. Will be copied to address 0 after memory remapping */ 264/* Exception handlers. Will be copied to address 0 after memory remapping */
336_vectorstart: 265_vectorstart:
@@ -358,8 +287,6 @@ vectors:
358 287
359 .text 288 .text
360 289
361 .global irq
362 .global fiq
363 .global UIE 290 .global UIE
364 291
365/* All illegal exceptions call into UIE with exception address as first 292/* All illegal exceptions call into UIE with exception address as first
@@ -389,6 +316,11 @@ data_abort_handler:
389 mov r1, #2 316 mov r1, #2
390 b UIE 317 b UIE
391 318
319#ifdef BOOTLOADER
320UIE:
321 b UIE
322#endif
323
392/* 256 words of IRQ stack */ 324/* 256 words of IRQ stack */
393 .space 256*4 325 .space 256*4
394irq_stack: 326irq_stack:
@@ -396,5 +328,3 @@ irq_stack:
396/* 256 words of FIQ stack */ 328/* 256 words of FIQ stack */
397 .space 256*4 329 .space 256*4
398fiq_stack: 330fiq_stack:
399
400#endif /* BOOTLOADER */
diff --git a/firmware/target/arm/imx31/gigabeat-s/avic-imx31.c b/firmware/target/arm/imx31/gigabeat-s/avic-imx31.c
index 8236a38014..99a52e56d5 100644
--- a/firmware/target/arm/imx31/gigabeat-s/avic-imx31.c
+++ b/firmware/target/arm/imx31/gigabeat-s/avic-imx31.c
@@ -20,204 +20,161 @@
20#include "system.h" 20#include "system.h"
21#include "imx31l.h" 21#include "imx31l.h"
22#include "avic-imx31.h" 22#include "avic-imx31.h"
23#include "panic.h"
23#include "debug.h" 24#include "debug.h"
24 25
26static const char * avic_int_names[64] =
27{
28 "RESERVED0", "RESERVED1", "RESERVED2", "I2C3",
29 "I2C2", "MPEG4_ENCODER", "RTIC", "FIR",
30 "MMC/SDHC2", "MMC/SDHC1", "I2C1", "SSI2",
31 "SSI1", "CSPI2", "CSPI1", "ATA",
32 "MBX", "CSPI3", "UART3", "IIM",
33 "SIM1", "SIM2", "RNGA", "EVTMON",
34 "KPP", "RTC", "PWN", "EPIT2",
35 "EPIT1", "GPT", "PWR_FAIL", "CCM_DVFS",
36 "UART2", "NANDFC", "SDMA", "USB_HOST1",
37 "USB_HOST2", "USB_OTG", "RESERVED3", "MSHC1",
38 "MSHC2", "IPU_ERR", "IPU", "RESERVED4",
39 "RESERVED5", "UART1", "UART4", "UART5",
40 "ETC_IRQ", "SCC_SCM", "SCC_SMN", "GPIO2",
41 "GPIO1", "CCM_CLK", "PCMCIA", "WDOG",
42 "GPIO3", "RESERVED6", "EXT_PWMG", "EXT_TEMP",
43 "EXT_SENS1", "EXT_SENS2", "EXT_WDOG", "EXT_TV"
44};
45
46static void UIE_VECTOR(void)
47{
48 set_interrupt_status(IRQ_FIQ_DISABLED, IRQ_FIQ_STATUS);
49 long offset = FIVECSR;
50 long offsetn = (long)NIVECSR >> 16;
51
52 if (offsetn == -1)
53 offset = offsetn; /* Could be FIQ */
54
55 panicf("Unhandled %s %ld: %s",
56 offsetn >= 0 ? "IRQ" : "FIQ", offset,
57 offset >= 0 ? avic_int_names[offset] : "");
58}
59
60/* We use the AVIC */
61void __attribute__((naked)) irq_handler(void)
62{
63 panicf("Unhandled IRQ");
64}
65
66/* Accoring to section 9.3.5 of the UM, the AVIC doesn't accelerate
67 * fast interrupts and they must be dispatched */
68void __attribute__((naked)) fiq_handler(void)
69{
70 asm volatile (
71 "mov r10, #0x6c000000 \n" /* load AVIC base address */
72 "ldr r9, [r10, #0x44] \n" /* read FIVECSR of AVIC */
73 "add r10, r10, #100 \n" /* move pointer to base of VECTOR table */
74 "ldr r8, [r10, r9, lsl #2] \n" /* read FIQ vector from VECTOR table */
75 "bx r8 \n" /* jump to FIQ service routine */
76 );
77}
78
25void avic_init(void) 79void avic_init(void)
26{ 80{
27 /*following the steps in the AVIC setup in imx31 man*/ 81 /* Disable all interrupts and set to unhandled */
82 avic_disable_int(ALL);
28 83
29 /*Initialize interrupt structures*/ 84 /* Init all interrupts to type IRQ */
30 int i,avicstart; 85 avic_set_int_type(ALL, IRQ);
31 /*get start of avic_init section for address calculation*/
32 __asm__ ("ldr %0,=_avicstart\n\t"
33 :"=r"(avicstart):);
34 86
35 for(i=0; i < 64;i++) 87 /* Set NM bit to enable VIC */
36 { 88 INTCNTL |= INTCNTL_NM;
37 imx31_int[i].name = (char *)&imx31_int_names[i];
38 imx31_int[i].int_type=IRQ;
39 /*integer i MUST be multiplied by 8 b/c gnu as
40 generates 2 instructions for each vector instruction
41 in vector_init(). Hence the value of 8 byte intervals
42 between each vector start address*/
43 imx31_int[i].addr=(avicstart+(i*8));
44 imx31_int[i].priority=0;
45 imx31_int[i].pInt_Handler=Unhandled_Int;
46 }
47
48 /*enable all Interrupts*/
49 avic_enable_int(ALL,IRQ,0);
50
51 /*Setup all interrupt type IRQ*/
52 avic_set_int_type(ALL,IRQ);
53
54 /*Set NM bit to enable VIC*/
55 INTCNTL |= (1 << 18);
56 89
57 /*Setup Registers Vector0-Vector63 for interrupt handler functions*/ 90 /* Enable IRQ/FIQ in imx31 INTCNTL reg */
58 for(i=0; i < 64;i++) 91 INTCNTL &= ~(INTCNTL_ABFEN | INTCNTL_NIDIS | INTCNTL_FIDIS);
59 writel(imx31_int[i].addr,(VECTOR_BASE_ADDR+(i*8))); 92
60 93 /* Enable VE bit in CP15 Control reg to enable VIC */
61 /*disable FIQ for now until the interrupt handlers are more mature...*/ 94 asm volatile (
62 disable_fiq(); 95 "mrc p15, 0, r0, c1, c0, 0 \n"
63 /*enable_fiq();*/ 96 "orr r0, r0, #(1 << 24) \n"
64 97 "mcr p15, 0, r0, c1, c0, 0 \n"
65 /*enable IRQ in imx31 INTCNTL reg*/ 98 : : : "r0");
66 INTCNTL &= ~(NIDIS); 99
67 /*disable FIQ in imx31 INTCNTL reg*/ 100 /* Enable normal interrupts at all priorities */
68 INTCNTL |= FIDIS; 101 NIMASK = 16;
69
70 /*enable IRQ in ARM11 core, enable VE bit in CP15 Control reg to enable VIC*/
71 __asm__ ("mrs r0,cpsr\t\n"
72 "bic r0,r0,#0x80\t\n"
73 "msr cpsr,r0\t\n"
74 "mrc p15,0,r0,c1,c0,0\n\t"
75 "orr r0,r0,#0x1000000\n\t"
76 "mcr p15,0,r0,c1,c0,0\n\t":::
77 "r0");
78} 102}
79 103
80void avic_enable_int(enum IMX31_INT_LIST ints, enum INT_TYPE intstype, 104void avic_enable_int(enum IMX31_INT_LIST ints, enum INT_TYPE intstype,
81 void (*pInt_Handler) (void)) 105 void (*handler)(void))
82{ 106{
83 int i; 107 int oldstatus = set_interrupt_status(IRQ_FIQ_DISABLED,
108 IRQ_FIQ_STATUS);
84 109
85 if(ints == ALL) 110 if (ints != ALL) /* No mass-enable allowed */
86 { 111 {
87 avic_set_int_type(ALL,intstype); 112 avic_set_int_type(ints, intstype);
88 for(i=0;i<64;i++) 113 VECTOR(ints) = (long)handler;
89 INTENNUM= (long)i; 114 INTENNUM = ints;
90 if(!(*pInt_Handler)) 115 }
91 pInt_Handler=Unhandled_Int; 116
92 return; 117 set_interrupt_status(oldstatus, IRQ_FIQ_STATUS);
93 }
94
95 imx31_int[ints].int_type=intstype;
96 imx31_int[ints].pInt_Handler=pInt_Handler;
97 avic_set_int_type(ints,intstype);
98 INTENNUM=(long)ints;
99} 118}
100 119
101void avic_disable_int(enum IMX31_INT_LIST ints) 120void avic_disable_int(enum IMX31_INT_LIST ints)
102{ 121{
103 int i; 122 long i;
104 123
105 if(ints == ALL) 124 if (ints == ALL)
106 { 125 {
107 for(i=0;i<64;i++) 126 for (i = 0; i < 64; i++)
108 INTDISNUM=(long)i; 127 {
109 imx31_int[ints].pInt_Handler=Unhandled_Int; 128 INTDISNUM = i;
110 return; 129 VECTOR(i) = (long)UIE_VECTOR;
130 }
111 } 131 }
112 132 else
113 INTDISNUM=(long)ints; 133 {
134 INTDISNUM = ints;
135 VECTOR(ints) = (long)UIE_VECTOR;
136 }
114} 137}
115 138
116void avic_set_int_type(enum IMX31_INT_LIST ints, enum INT_TYPE intstype) 139static void set_int_type(int i, enum INT_TYPE intstype)
117{ 140{
118 int i; 141 volatile unsigned long *reg;
119 if(ints == ALL) 142 long val;
120 {
121 imx31_int[ints].int_type=intstype;
122 for(i=0;i<64;i++)
123 {
124 if(intstype > CCM_DVFS)
125 INTTYPEH=(long)(intstype-32);
126 else INTTYPEL=(long)intstype;
127 }
128 return;
129 }
130
131 imx31_int[ints].int_type=intstype;
132 if(intstype > CCM_DVFS)
133 INTTYPEH=(long)(intstype-32);
134 else INTTYPEL=(long)intstype;
135}
136 143
137void Unhandled_Int(void) 144 if (i >= 32)
138{ 145 {
139 enum IMX31_INT_LIST ints = 0; 146 reg = &INTTYPEH;
140 DEBUGF("Unhandled Interrupt:\n"); 147 val = 1L << (i - 32);
141 DEBUGF("Name : %s\n",imx31_int[ints].name); 148 }
142 DEBUGF("Interrupt Type : "); 149 else
143 if(imx31_int[ints].int_type==IRQ) 150 {
144 DEBUGF("IRQ\n"); 151 reg = &INTTYPEL;
145 else DEBUGF("FIQ\n"); 152 val = 1L << i;
146 DEBUGF("Handler Address : 0x%x\n",imx31_int[ints].addr); 153 }
147 DEBUGF("Priority : %d",imx31_int[ints].priority); 154
155 if (intstype == IRQ)
156 val = *reg & ~val;
157 else
158 val = *reg | val;
159
160 *reg = val;
148} 161}
149 162
150void vector_init(void) 163void avic_set_int_type(enum IMX31_INT_LIST ints, enum INT_TYPE intstype)
151{ 164{
152 165 int oldstatus = set_interrupt_status(IRQ_FIQ_DISABLED,
153 /*64 branch instructions, one for every vector in avic 166 IRQ_FIQ_STATUS);
154 A better idea would to calculate the shellcode for each of these 167
155 instructions...*/ 168 if (ints == ALL)
156 169 {
157 170 int i;
158 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[RESERVED0].pInt_Handler)); 171 for (i = 0; i < 64; i++)
159 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[RESERVED1].pInt_Handler)); 172 set_int_type(i, intstype);
160 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[RESERVED2].pInt_Handler)); 173 }
161 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[I2C3].pInt_Handler)); 174 else
162 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[I2C2].pInt_Handler)); 175 {
163 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[MPEG4_ENCODER].pInt_Handler)); 176 set_int_type(ints, intstype);
164 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[RTIC].pInt_Handler)); 177 }
165 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[FIR].pInt_Handler)); 178
166 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[MMC_SDHC2].pInt_Handler)); 179 set_interrupt_status(oldstatus, IRQ_FIQ_STATUS);
167 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[MMC_SDHC1].pInt_Handler));
168 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[I2C1].pInt_Handler));
169 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[SSI2].pInt_Handler));
170 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[SSI1].pInt_Handler));
171 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[CSPI2].pInt_Handler));
172 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[CSPI1].pInt_Handler));
173 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[ATA].pInt_Handler));
174 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[MBX].pInt_Handler));
175 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[CSPI3].pInt_Handler));
176 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[UART3].pInt_Handler));
177 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[IIM].pInt_Handler));
178 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[SIM1].pInt_Handler));
179 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[SIM2].pInt_Handler));
180 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[RNGA].pInt_Handler));
181 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[EVTMON].pInt_Handler));
182 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[KPP].pInt_Handler));
183 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[RTC].pInt_Handler));
184 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[PWN].pInt_Handler));
185 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[EPIT2].pInt_Handler));
186 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[EPIT1].pInt_Handler));
187 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[GPT].pInt_Handler));
188 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[PWR_FAIL].pInt_Handler));
189 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[CCM_DVFS].pInt_Handler));
190 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[UART2].pInt_Handler));
191 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[NANDFC].pInt_Handler));
192 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[SDMA].pInt_Handler));
193 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[USB_HOST1].pInt_Handler));
194 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[USB_HOST2].pInt_Handler));
195 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[USB_OTG].pInt_Handler));
196 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[RESERVED3].pInt_Handler));
197 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[MSHC1].pInt_Handler));
198 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[MSHC2].pInt_Handler));
199 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[IPU_ERR].pInt_Handler));
200 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[IPU].pInt_Handler));
201 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[RESERVED4].pInt_Handler));
202 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[RESERVED5].pInt_Handler));
203 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[UART1].pInt_Handler));
204 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[UART4].pInt_Handler));
205 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[UART5].pInt_Handler));
206 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[ETC_IRQ].pInt_Handler));
207 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[SCC_SCM].pInt_Handler));
208 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[SCC_SMN].pInt_Handler));
209 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[GPIO2].pInt_Handler));
210 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[GPIO1].pInt_Handler));
211 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[CCM_CLK].pInt_Handler));
212 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[PCMCIA].pInt_Handler));
213 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[WDOG].pInt_Handler));
214 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[GPIO3].pInt_Handler));
215 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[RESERVED6].pInt_Handler));
216 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[EXT_PWMG].pInt_Handler));
217 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[EXT_TEMP].pInt_Handler));
218 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[EXT_SENS1].pInt_Handler));
219 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[EXT_SENS2].pInt_Handler));
220 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[EXT_WDOG].pInt_Handler));
221 __asm__("ldr pc, %0\n\t"::"g"(imx31_int[EXT_TV].pInt_Handler));
222
223} 180}
diff --git a/firmware/target/arm/imx31/gigabeat-s/avic-imx31.h b/firmware/target/arm/imx31/gigabeat-s/avic-imx31.h
index 53a37b353b..29a3ec8dd0 100644
--- a/firmware/target/arm/imx31/gigabeat-s/avic-imx31.h
+++ b/firmware/target/arm/imx31/gigabeat-s/avic-imx31.h
@@ -19,107 +19,37 @@
19#ifndef AVIC_IMX31_H 19#ifndef AVIC_IMX31_H
20#define AVIC_IMX31_H 20#define AVIC_IMX31_H
21 21
22 22enum INT_TYPE
23enum INT_TYPE {IRQ=0,FIQ}; 23{
24 24 IRQ = 0,
25struct int_names { 25 FIQ
26 char name[16];
27}; 26};
28 27
29static const struct int_names imx31_int_names[64] = 28enum IMX31_INT_LIST
30{ {"RESERVED0"}, 29{
31 {"RESERVED1"}, 30 __IMX31_INT_FIRST = -1,
32 {"RESERVED2"}, 31 RESERVED0, RESERVED1, RESERVED2, I2C3,
33 {"I2C3"}, 32 I2C2, MPEG4_ENCODER, RTIC, FIR,
34 {"I2C2"}, 33 MMC_SDHC2, MMC_SDHC1, I2C1, SSI2,
35 {"MPEG4_ENCODER"}, 34 SSI1, CSPI2, CSPI1, ATA,
36 {"RTIC"}, 35 MBX, CSPI3, UART3, IIM,
37 {"FIR"}, 36 SIM1, SIM2, RNGA, EVTMON,
38 {"MMC/SDHC2"}, 37 KPP, RTC, PWN, EPIT2,
39 {"MMC/SDHC1"}, 38 EPIT1, GPT, PWR_FAIL, CCM_DVFS,
40 {"I2C1"}, 39 UART2, NANDFC, SDMA, USB_HOST1,
41 {"SSI2"}, 40 USB_HOST2, USB_OTG, RESERVED3, MSHC1,
42 {"SSI1"}, 41 MSHC2, IPU_ERR, IPU, RESERVED4,
43 {"CSPI2"}, 42 RESERVED5, UART1, UART4, UART5,
44 {"CSPI1"}, 43 ETC_IRQ, SCC_SCM, SCC_SMN, GPIO2,
45 {"ATA"}, 44 GPIO1, CCM_CLK, PCMCIA, WDOG,
46 {"MBX"}, 45 GPIO3, RESERVED6, EXT_PWMG, EXT_TEMP,
47 {"CSPI3"}, 46 EXT_SENS1, EXT_SENS2, EXT_WDOG, EXT_TV,
48 {"UART3"}, 47 ALL
49 {"IIM"}, 48};
50 {"SIM1"},
51 {"SIM2"},
52 {"RNGA"},
53 {"EVTMON"},
54 {"KPP"},
55 {"RTC"},
56 {"PWN"},
57 {"EPIT2"},
58 {"EPIT1"},
59 {"GPT"},
60 {"PWR_FAIL"},
61 {"CCM_DVFS"},
62 {"UART2"},
63 {"NANDFC"},
64 {"SDMA"},
65 {"USB_HOST1"},
66 {"USB_HOST2"},
67 {"USB_OTG"},
68 {"RESERVED3"},
69 {"MSHC1"},
70 {"MSHC2"},
71 {"IPU_ERR"},
72 {"IPU"},
73 {"RESERVED4"},
74 {"RESERVED5"},
75 {"UART1"},
76 {"UART4"},
77 {"UART5"},
78 {"ETC_IRQ"},
79 {"SCC_SCM"},
80 {"SCC_SMN"},
81 {"GPIO2"},
82 {"GPIO1"},
83 {"CCM_CLK"},
84 {"PCMCIA"},
85 {"WDOG"},
86 {"GPIO3"},
87 {"RESERVED6"},
88 {"EXT_PWMG"},
89 {"EXT_TEMP"},
90 {"EXT_SENS1"},
91 {"EXT_SENS2"},
92 {"EXT_WDOG"},
93 {"EXT_TV"} };
94
95enum IMX31_INT_LIST {
96 RESERVED0 = 0,RESERVED1,RESERVED2,I2C3,
97 I2C2,MPEG4_ENCODER,RTIC,FIR,MMC_SDHC2,
98 MMC_SDHC1,I2C1,SSI2,SSI1,CSPI2,CSPI1,
99 ATA,MBX,CSPI3,UART3,IIM,SIM1,SIM2,
100 RNGA,EVTMON,KPP,RTC,PWN,EPIT2,EPIT1,
101 GPT,PWR_FAIL,CCM_DVFS,UART2,NANDFC,
102 SDMA,USB_HOST1,USB_HOST2,USB_OTG,
103 RESERVED3,MSHC1,MSHC2,IPU_ERR,IPU,
104 RESERVED4,RESERVED5,UART1,UART4,UART5,
105 ETC_IRQ,SCC_SCM,SCC_SMN,GPIO2,GPIO1,
106 CCM_CLK,PCMCIA,WDOG,GPIO3,RESERVED6,
107 EXT_PWMG,EXT_TEMP,EXT_SENS1,EXT_SENS2,
108 EXT_WDOG,EXT_TV,ALL };
109
110static struct avic_int {
111 char * name;
112 enum INT_TYPE int_type;
113 unsigned int addr;
114 unsigned int priority;
115 void (*pInt_Handler) (void);
116} imx31_int[64];
117 49
118void avic_init(void); 50void avic_init(void);
119void avic_enable_int(enum IMX31_INT_LIST ints, enum INT_TYPE intstype, 51void avic_enable_int(enum IMX31_INT_LIST ints, enum INT_TYPE intstype,
120 void (*pInt_Handler) (void)); 52 void (*handler)(void));
121void avic_disable_int(enum IMX31_INT_LIST ints) ; 53void avic_disable_int(enum IMX31_INT_LIST ints);
122void avic_set_int_type(enum IMX31_INT_LIST ints, enum INT_TYPE intstype); 54void avic_set_int_type(enum IMX31_INT_LIST ints, enum INT_TYPE intstype);
123void Unhandled_Int(void);
124void vector_init(void) __attribute__ ((section(".avic_int"),naked));
125#endif 55#endif
diff --git a/firmware/target/arm/imx31/gigabeat-s/kernel-imx31.c b/firmware/target/arm/imx31/gigabeat-s/kernel-imx31.c
index 9df90a2344..7f882405a5 100644
--- a/firmware/target/arm/imx31/gigabeat-s/kernel-imx31.c
+++ b/firmware/target/arm/imx31/gigabeat-s/kernel-imx31.c
@@ -1,25 +1,60 @@
1#include "config.h"
2#include "system.h"
3#include "avic-imx31.h"
1#include "kernel.h" 4#include "kernel.h"
2#include "thread.h" 5#include "thread.h"
3
4#include <stdio.h> 6#include <stdio.h>
5#include "lcd.h"
6 7
7extern void (*tick_funcs[MAX_NUM_TICK_TASKS])(void); 8extern void (*tick_funcs[MAX_NUM_TICK_TASKS])(void);
8 9
9void timer4(void) { 10#ifndef BOOTLOADER
10 int i; 11static __attribute__((interrupt("IRQ"))) void EPIT1_HANDLER(void)
12{
13 int i;
14
15 EPITSR1 = 1; /* Clear the pending status */
16
11 /* Run through the list of tick tasks */ 17 /* Run through the list of tick tasks */
12 for(i = 0; i < MAX_NUM_TICK_TASKS; i++) 18 for(i = 0;i < MAX_NUM_TICK_TASKS;i++)
13 { 19 {
14 if(tick_funcs[i]) 20 if(tick_funcs[i])
15 {
16 tick_funcs[i](); 21 tick_funcs[i]();
17 }
18 } 22 }
19 23
20 current_tick++; 24 current_tick++;
21
22 /* following needs to be fixed. */
23 /*wake_up_thread();*/
24} 25}
26#endif
27
28void tick_start(unsigned int interval_in_ms)
29{
30 EPITCR1 &= ~(1 << 0); /* Disable the counter */
31 EPITCR1 |= (1 << 16); /* Reset */
25 32
33 CLKCTL_CGR0 |= (0x3 << 6); /* Clock ON */
34 CLKCTL_WIMR0 &= ~(1 << 23); /* Clear wakeup mask */
35
36 /* NOTE: This isn't really accurate yet but it's close enough to work
37 * with for the moment */
38
39 /* CLKSRC=32KHz, EPIT Output Disconnected, Enabled
40 * prescale 1/32, Reload from modulus register, Compare interrupt enabled,
41 * Count from load value */
42 EPITCR1 = (0x3 << 24) | (1 << 19) | (32 << 4) |
43 (1 << 3) | (1 << 2) | (1 << 1);
44 EPITSR1 = 1; /* Clear any pending interrupt */
45#ifndef BOOTLOADER
46 EPITLR1 = interval_in_ms;
47 EPITCMPR1 = 0; /* Event when counter reaches 0 */
48 avic_enable_int(EPIT1, IRQ, EPIT1_HANDLER);
49#else
50 (void)interval_in_ms;
51#endif
52
53 EPITCR1 |= (1 << 0); /* Enable the counter */
54
55 /* Why does only this trigger the counter? Remove when we find out. */
56 asm volatile (
57 "mcr p15, 0, %0, c7, c0, 4 \n"
58 : : "r" (0)
59 );
60}
diff --git a/firmware/target/arm/imx31/gigabeat-s/lcd-as-imx31.S b/firmware/target/arm/imx31/gigabeat-s/lcd-as-imx31.S
deleted file mode 100644
index d431c95f29..0000000000
--- a/firmware/target/arm/imx31/gigabeat-s/lcd-as-imx31.S
+++ /dev/null
@@ -1,222 +0,0 @@
1/***************************************************************************
2 * __________ __ ___.
3 * Open \______ \ ____ ____ | | _\_ |__ _______ ___
4 * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
5 * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
6 * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
7 * \/ \/ \/ \/ \/
8 * $Id$
9 *
10 * Copyright (C) 2007 by Michael Sevakis
11 *
12 * All files in this archive are subject to the GNU General Public License.
13 * See the file COPYING in the source tree root for full license agreement.
14 *
15 * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
16 * KIND, either express or implied.
17 *
18 ****************************************************************************/
19
20#include "config.h"
21#include "cpu.h"
22
23/****************************************************************************
24 * void lcd_write_yuv_420_lines(fb_data *dst,
25 * unsigned char chroma_buf[LCD_HEIGHT/2*3],
26 unsigned char const * const src[3],
27 * int width,
28 * int stride);
29 *
30 * |R| |1.000000 -0.000001 1.402000| |Y'|
31 * |G| = |1.000000 -0.334136 -0.714136| |Pb|
32 * |B| |1.000000 1.772000 0.000000| |Pr|
33 * Scaled, normalized, rounded and tweaked to yield RGB 565:
34 * |R| |74 0 101| |Y' - 16| >> 9
35 * |G| = |74 -24 -51| |Cb - 128| >> 8
36 * |B| |74 128 0| |Cr - 128| >> 9
37 */
38 .section .icode, "ax", %progbits
39 .align 2
40 .global lcd_write_yuv420_lines
41 .type lcd_write_yuv420_lines, %function
42lcd_write_yuv420_lines:
43 @ r0 = dst
44 @ r1 = chroma_buf
45 @ r2 = yuv_src
46 @ r3 = width
47 @ [sp] = stride
48 stmdb sp!, { r4-r12, lr } @ save non-scratch
49 stmdb sp!, { r0, r3 } @ save dst and width
50 mov r14, #74 @ r14 = Y factor
51 ldmia r2, { r4, r5, r6 } @ r4 = yuv_src[0] = Y'_p
52 @ r5 = yuv_src[1] = Cb_p
53 @ r6 = yuv_src[2] = Cr_p
5410: @ loop line 1 @
55 ldrb r2, [r4], #1 @ r2 = *Y'_p++;
56 ldrb r8, [r5], #1 @ r8 = *Cb_p++;
57 ldrb r11, [r6], #1 @ r11 = *Cr_p++;
58 @
59 @ compute Y
60 sub r2, r2, #16 @ r7 = Y = (Y' - 16)*74
61 mul r7, r2, r14 @
62 @
63 sub r8, r8, #128 @ Cb -= 128
64 sub r11, r11, #128 @ Cr -= 128
65 @
66 mvn r2, #24 @ compute guv
67 mul r10, r2, r8 @ r10 = Cb*-24
68 mvn r2, #51 @
69 mla r10, r2, r11, r10 @ r10 = r10 + Cr*-51
70 @
71 mov r2, #101 @ compute rv
72 mul r9, r11, r2 @ r9 = rv = Cr*101
73 @
74 @ store chromas in line buffer
75 add r8, r8, #2 @ bu = (Cb + 2) >> 2
76 mov r8, r8, asr #2 @
77 strb r8, [r1], #1 @
78 add r9, r9, #256 @ rv = (Cr + 256) >> 9
79 mov r9, r9, asr #9 @
80 strb r9, [r1], #1 @
81 mov r10, r10, asr #8 @ guv >>= 8
82 strb r10, [r1], #1 @
83 @ compute R, G, and B
84 add r2, r8, r7, asr #9 @ r2 = b = (Y >> 9) + bu
85 add r11, r9, r7, asr #9 @ r11 = r = (Y >> 9) + rv
86 add r7, r10, r7, asr #8 @ r7 = g = (Y >> 8) + guv
87 @
88 orr r12, r2, r11 @ check if clamping is needed...
89 orr r12, r12, r7, asr #1 @ ...at all
90 cmp r12, #31 @
91 bls 15f @ no clamp @
92 mov r12, #31 @
93 cmp r12, r2 @ clamp b
94 andlo r2, r12, r2, asr #31 @
95 eorlo r2, r2, r12 @
96 cmp r12, r11 @ clamp r
97 andlo r11, r12, r11, asr #31 @
98 eorlo r11, r11, r12 @
99 cmp r12, r7, asr #1 @ clamp g
100 andlo r7, r12, r7, asr #31 @
101 eorlo r7, r7, r12 @
102 orrlo r7, r7, r7, asl #1 @
10315: @ no clamp @
104 @
105 orr r12, r2, r7, lsl #5 @ r4 |= (g << 5)
106 ldrb r2, [r4], #1 @ r2 = Y' = *Y'_p++
107 orr r12, r12, r11, lsl #11 @ r4 = b | (r << 11)
108 strh r12, [r0], #240 @ store pixel
109 @
110 sub r2, r2, #16 @ r7 = Y = (Y' - 16)*74
111 mul r7, r2, r14 @ next Y
112 @ compute R, G, and B
113 add r2, r8, r7, asr #9 @ r2 = b = (Y >> 9) + bu
114 add r11, r9, r7, asr #9 @ r11 = r = (Y >> 9) + rv
115 add r7, r10, r7, asr #8 @ r7 = g = (Y >> 8) + guv
116 @
117 orr r12, r2, r11 @ check if clamping is needed...
118 orr r12, r12, r7, asr #1 @ ...at all
119 cmp r12, #31 @
120 bls 15f @ no clamp @
121 mov r12, #31 @
122 cmp r12, r2 @ clamp b
123 andlo r2, r12, r2, asr #31 @
124 eorlo r2, r2, r12 @
125 cmp r12, r11 @ clamp r
126 andlo r11, r12, r11, asr #31 @
127 eorlo r11, r11, r12 @
128 cmp r12, r7, asr #1 @ clamp g
129 andlo r7, r12, r7, asr #31 @
130 eorlo r7, r7, r12 @
131 orrlo r7, r7, r7, asl #1 @
13215: @ no clamp @
133 @
134 orr r12, r2, r11, lsl #11 @ r4 = b | (r << 11)
135 orr r12, r12, r7, lsl #5 @ r4 |= (g << 5)
136 strh r12, [r0, #240]! @ store pixel
137 add r0, r0, #2*240 @
138 @
139 subs r3, r3, #2 @
140 bgt 10b @ loop line 1 @
141 @ do second line
142 @
143 ldmia sp!, { r0, r3 } @ pop dst and width
144 sub r0, r0, #2 @ set dst to start of next line
145 sub r1, r1, r3, asl #1 @ rewind chroma pointer...
146 ldr r2, [sp, #40] @ r2 = stride
147 add r1, r1, r3, asr #1 @ ... (r1 -= width/2*3)
148 @ move sources to start of next line
149 sub r2, r2, r3 @ r2 = skip = stride - width
150 add r4, r4, r2 @ r4 = Y'_p + skip
151 @
15220: @ loop line 2 @
153 ldrb r2, [r4], #1 @ r7 = Y' = *Y'_p++
154 ldrsb r8, [r1], #1 @ reload saved chromas
155 ldrsb r9, [r1], #1 @
156 ldrsb r10, [r1], #1 @
157 @
158 sub r2, r2, #16 @ r2 = Y = (Y' - 16)*74
159 mul r7, r2, r14 @
160 @ compute R, G, and B
161 add r2, r8, r7, asr #9 @ r2 = b = (Y >> 9) + bu
162 add r11, r9, r7, asr #9 @ r11 = r = (Y >> 9) + rv
163 add r7, r10, r7, asr #8 @ r7 = g = (Y >> 8) + guv
164 @
165 orr r12, r2, r11 @ check if clamping is needed...
166 orr r12, r12, r7, asr #1 @ ...at all
167 cmp r12, #31 @
168 bls 25f @ no clamp @
169 mov r12, #31 @
170 cmp r12, r2 @ clamp b
171 andlo r2, r12, r2, asr #31 @
172 eorlo r2, r2, r12 @
173 cmp r12, r11 @ clamp r
174 andlo r11, r12, r11, asr #31 @
175 eorlo r11, r11, r12 @
176 cmp r12, r7, asr #1 @ clamp g
177 andlo r7, r12, r7, asr #31 @
178 eorlo r7, r7, r12 @
179 orrlo r7, r7, r7, asl #1 @
18025: @ no clamp @
181 @
182 orr r12, r2, r11, lsl #11 @ r4 = b | (r << 11)
183 ldrb r2, [r4], #1 @ r2 = Y' = *Y'_p++
184 orr r12, r12, r7, lsl #5 @ r4 |= (g << 5)
185 strh r12, [r0], #240 @ store pixel
186 @
187 @ do second pixel
188 @
189 sub r2, r2, #16 @ r2 = Y = (Y' - 16)*74
190 mul r7, r2, r14 @
191 @ compute R, G, and B
192 add r2, r8, r7, asr #9 @ r2 = b = (Y >> 9) + bu
193 add r11, r9, r7, asr #9 @ r11 = r = (Y >> 9) + rv
194 add r7, r10, r7, asr #8 @ r7 = g = (Y >> 8) + guv
195 @
196 orr r12, r2, r11 @ check if clamping is needed...
197 orr r12, r12, r7, asr #1 @ ...at all
198 cmp r12, #31 @
199 bls 25f @ no clamp @
200 mov r12, #31 @
201 cmp r12, r2 @ clamp b
202 andlo r2, r12, r2, asr #31 @
203 eorlo r2, r2, r12 @
204 cmp r12, r11 @ clamp r
205 andlo r11, r12, r11, asr #31 @
206 eorlo r11, r11, r12 @
207 cmp r12, r7, asr #1 @ clamp g
208 andlo r7, r12, r7, asr #31 @
209 eorlo r7, r7, r12 @
210 orrlo r7, r7, r7, asl #1 @
21125: @ no clamp @
212 @
213 orr r12, r2, r11, lsl #11 @ r4 = b | (r << 11)
214 orr r12, r12, r7, lsl #5 @ r4 |= (g << 5)
215 strh r12, [r0, #240]! @ store pixel
216 add r0, r0, #2*240 @
217 @
218 subs r3, r3, #2 @
219 bgt 20b @ loop line 2 @
220 @
221 ldmia sp!, { r4-r12, pc } @ restore registers and return
222 .size lcd_write_yuv420_lines, .-lcd_write_yuv420_lines
diff --git a/firmware/target/arm/imx31/gigabeat-s/lcd-imx31.c b/firmware/target/arm/imx31/gigabeat-s/lcd-imx31.c
index c9cce6d653..b39ddbe77d 100644
--- a/firmware/target/arm/imx31/gigabeat-s/lcd-imx31.c
+++ b/firmware/target/arm/imx31/gigabeat-s/lcd-imx31.c
@@ -9,12 +9,15 @@
9 9
10static volatile bool lcd_on = true; 10static volatile bool lcd_on = true;
11volatile bool lcd_poweroff = false; 11volatile bool lcd_poweroff = false;
12static unsigned lcd_yuv_options = 0;
12/* 13/*
13** These are imported from lcd-16bit.c 14** These are imported from lcd-16bit.c
14*/ 15*/
15extern unsigned fg_pattern; 16extern unsigned fg_pattern;
16extern unsigned bg_pattern; 17extern unsigned bg_pattern;
17 18
19extern struct viewport* current_vp;
20
18#if 0 21#if 0
19bool lcd_enabled() 22bool lcd_enabled()
20{ 23{
@@ -22,68 +25,60 @@ bool lcd_enabled()
22} 25}
23#endif 26#endif
24 27
25void printscreen(unsigned int colour) { 28void printscreen(unsigned int colour)
29{
26 int i; 30 int i;
27 int base = 0x84100000; 31 char * base = (char *)FRAME;
28 for(i=0;i<(320*240*2);i++) { 32 for(i = 0; i < (320*240*2); i++)
29 writel(colour,base); 33 {
34 writel(colour, base);
30 base++; 35 base++;
31 } 36 }
32} 37}
33 38
34unsigned int LCDBANK(unsigned int address)
35{
36 return ((address >> 22) & 0xff);
37}
38
39unsigned int LCDBASEU(unsigned int address)
40{
41 return (address & ((1 << 22)-1)) >> 1;
42}
43
44unsigned int LCDBASEL(unsigned int address)
45{
46 address += 320*240*2;
47 return (address & ((1 << 22)-1)) >> 1;
48}
49
50
51/* LCD init */ 39/* LCD init */
52void lcd_init_device(void) 40void lcd_init_device(void)
53{ 41{
54 int i;
55#ifdef BOOTLOADER
56 /* When the Rockbox bootloader starts, we are changing framebuffer address,
57 but we don't want what's shown on the LCD to change until we do an
58 lcd_update(), so copy the data from the old framebuffer to the new one */
59 unsigned short *buf = (unsigned short*)FRAME1;
60
61 memcpy(FRAME1, (short *)((LCDSADDR1)<<1), 320*240*2);
62
63 /* The Rockbox bootloader is transitioning from RGB555I to RGB565 mode
64 so convert the frambuffer data accordingly */
65 for(i=0; i< 320*240; i++){
66 *buf = ((*buf>>1) & 0x1F) | (*buf & 0xffc0);
67 buf++;
68 }
69 return;
70#endif
71} 42}
72 43
73/* Update a fraction of the display. */ 44/* Update a fraction of the display. */
74void lcd_update_rect(int x, int y, int width, int height) 45void lcd_update_rect(int x, int y, int width, int height)
75{ 46{
76 (void)x; 47 fb_data *dst, *src;
77 (void)width;
78 (void)y;
79 (void)height;
80 48
81 if(!lcd_on) 49 if (!lcd_on)
82 {
83 sleep(200);
84 return; 50 return;
51
52 if (x + width > LCD_WIDTH)
53 width = LCD_WIDTH - x; /* Clip right */
54 if (x < 0)
55 width += x, x = 0; /* Clip left */
56 if (width <= 0)
57 return; /* nothing left to do */
58
59 if (y + height > LCD_HEIGHT)
60 height = LCD_HEIGHT - y; /* Clip bottom */
61 if (y < 0)
62 height += y, y = 0; /* Clip top */
63 if (height <= 0)
64 return; /* nothing left to do */
65
66 /* TODO: It may be faster to swap the addresses of lcd_driver_framebuffer
67 * and lcd_framebuffer */
68 dst = (fb_data *)FRAME + LCD_WIDTH*y + x;
69 src = &lcd_framebuffer[y][x];
70
71 /* Copy part of the Rockbox framebuffer to the second framebuffer */
72 if (width < LCD_WIDTH)
73 {
74 /* Not full width - do line-by-line */
75 lcd_copy_buffer_rect(dst, src, width, height);
76 }
77 else
78 {
79 /* Full width - copy as one line */
80 lcd_copy_buffer_rect(dst, src, LCD_WIDTH*height, 1);
85 } 81 }
86 memcpy(((char*)FRAME2) + (y * sizeof(fb_data) * LCD_WIDTH), ((char *)&lcd_framebuffer) + (y * sizeof(fb_data) * LCD_WIDTH), ((height * sizeof(fb_data) * LCD_WIDTH)));
87} 82}
88 83
89void lcd_enable(bool state) 84void lcd_enable(bool state)
@@ -100,68 +95,82 @@ bool lcd_enabled(void)
100 This must be called after all other LCD functions that change the display. */ 95 This must be called after all other LCD functions that change the display. */
101void lcd_update(void) 96void lcd_update(void)
102{ 97{
103 lcd_update_rect(0, 0, LCD_WIDTH, LCD_HEIGHT); 98 if (!lcd_on)
99 return;
100
101 lcd_copy_buffer_rect((fb_data *)FRAME, &lcd_framebuffer[0][0],
102 LCD_WIDTH*LCD_HEIGHT, 1);
104} 103}
105 104
106void lcd_bitmap_transparent_part(const fb_data *src, int src_x, int src_y, 105void lcd_bitmap_transparent_part(const fb_data *src, int src_x, int src_y,
107 int stride, int x, int y, int width, 106 int stride, int x, int y, int width,
108 int height) 107 int height)
109{ 108{
110 fb_data *dst, *dst_end; 109#if 0
111 unsigned int transcolor; 110 int w, px;
112 111 fb_data *dst;
113 /* nothing to draw? */
114 if ((width <= 0) || (height <= 0) || (x >= LCD_WIDTH) || (y >= LCD_HEIGHT)
115 || (x + width <= 0) || (y + height <= 0))
116 return;
117 112
118 /* clipping */
119 if (x < 0)
120 {
121 width += x;
122 src_x -= x;
123 x = 0;
124 }
125 if (y < 0)
126 {
127 height += y;
128 src_y -= y;
129 y = 0;
130 }
131 if (x + width > LCD_WIDTH) 113 if (x + width > LCD_WIDTH)
132 width = LCD_WIDTH - x; 114 width = LCD_WIDTH - x; /* Clip right */
115 if (x < 0)
116 width += x, x = 0; /* Clip left */
117 if (width <= 0)
118 return; /* nothing left to do */
119
133 if (y + height > LCD_HEIGHT) 120 if (y + height > LCD_HEIGHT)
134 height = LCD_HEIGHT - y; 121 height = LCD_HEIGHT - y; /* Clip bottom */
122 if (y < 0)
123 height += y, y = 0; /* Clip top */
124 if (height <= 0)
125 return; /* nothing left to do */
135 126
136 src += stride * src_y + src_x; /* move starting point */ 127 src += stride * src_y + src_x; /* move starting point */
137 dst = &lcd_framebuffer[(y)][(x)]; 128 dst = &lcd_framebuffer[y][x];
138 dst_end = dst + height * LCD_WIDTH; 129
139 width *= 2; 130 asm volatile (
140 stride *= 2; 131 ".rowstart: \r\n"
141 transcolor = TRANSPARENT_COLOR; 132 "mov %[w], %[width] \r\n" /* Load width for inner loop */
142 asm volatile( 133 ".nextpixel: \r\n"
143 "rowstart: \n" 134 "ldrh %[px], [%[s]], #2 \r\n" /* Load src pixel */
144 "mov r0, #0 \n" 135 "add %[d], %[d], #2 \r\n" /* Uncoditionally increment dst */
145 "nextpixel: \n" 136 "cmp %[px], %[fgcolor] \r\n" /* Compare to foreground color */
146 "ldrh r1, [%0, r0] \n" /* Load word src+r0 */ 137 "streqh %[fgpat], [%[d], #-2] \r\n" /* Store foregroud if match */
147 "cmp r1, %5 \n" /* Compare to transparent color */ 138 "cmpne %[px], %[transcolor] \r\n" /* Compare to transparent color */
148 "strneh r1, [%1, r0] \n" /* Store dst+r0 if not transparent */ 139 "strneh %[px], [%[d], #-2] \r\n" /* Store dst if not transparent */
149 "add r0, r0, #2 \n" 140 "subs %[w], %[w], #1 \r\n" /* Width counter has run down? */
150 "cmp r0, %2 \n" /* r0 == width? */ 141 "bgt .nextpixel \r\n" /* More in this row? */
151 "bne nextpixel \n" /* More in this row? */ 142 "add %[s], %[s], %[sstp], lsl #1 \r\n" /* Skip over to start of next line */
152 "add %0, %0, %4 \n" /* src += stride */ 143 "add %[d], %[d], %[dstp], lsl #1 \r\n"
153 "add %1, %1, #480 \n" /* dst += LCD_WIDTH (x2) */ 144 "subs %[h], %[h], #1 \r\n" /* Height counter has run down? */
154 "cmp %1, %3 \n" 145 "bgt .rowstart \r\n" /* More rows? */
155 "bne rowstart \n" /* if(dst != dst_end), keep going */ 146 : [w]"=&r"(w), [h]"+&r"(height), [px]"=&r"(px),
156 : : "r" (src), "r" (dst), "r" (width), "r" (dst_end), "r" (stride), "r" (transcolor) : "r0", "r1" ); 147 [s]"+&r"(src), [d]"+&r"(dst)
148 : [width]"r"(width),
149 [sstp]"r"(stride - width),
150 [dstp]"r"(LCD_WIDTH - width),
151 [transcolor]"r"(TRANSPARENT_COLOR),
152 [fgcolor]"r"(REPLACEWITHFG_COLOR),
153 [fgpat]"r"(current_vp->fg_pattern)
154 );
155#endif
156}
157
158void lcd_yuv_set_options(unsigned options)
159{
160 lcd_yuv_options = options;
157} 161}
158 162
159/* Line write helper function for lcd_yuv_blit. Write two lines of yuv420. */ 163/* Line write helper function for lcd_yuv_blit. Write two lines of yuv420. */
160extern void lcd_write_yuv420_lines(fb_data *dst, 164extern void lcd_write_yuv420_lines(fb_data *dst,
161 unsigned char chroma_buf[LCD_HEIGHT/2*3],
162 unsigned char const * const src[3], 165 unsigned char const * const src[3],
163 int width, 166 int width,
164 int stride); 167 int stride);
168extern void lcd_write_yuv420_lines_odither(fb_data *dst,
169 unsigned char const * const src[3],
170 int width,
171 int stride,
172 int x_screen, /* To align dither pattern */
173 int y_screen);
165/* Performance function to blit a YUV bitmap directly to the LCD */ 174/* Performance function to blit a YUV bitmap directly to the LCD */
166/* For the Gigabeat - show it rotated */ 175/* For the Gigabeat - show it rotated */
167/* So the LCD_WIDTH is now the height */ 176/* So the LCD_WIDTH is now the height */
@@ -171,7 +180,6 @@ void lcd_yuv_blit(unsigned char * const src[3],
171{ 180{
172 /* Caches for chroma data so it only need be recaculated every other 181 /* Caches for chroma data so it only need be recaculated every other
173 line */ 182 line */
174 unsigned char chroma_buf[LCD_HEIGHT/2*3]; /* 480 bytes */
175 unsigned char const * yuv_src[3]; 183 unsigned char const * yuv_src[3];
176 off_t z; 184 off_t z;
177 185
@@ -182,23 +190,39 @@ void lcd_yuv_blit(unsigned char * const src[3],
182 width &= ~1; 190 width &= ~1;
183 height >>= 1; 191 height >>= 1;
184 192
185 fb_data *dst = (fb_data*)FRAME1 + x * LCD_WIDTH + (LCD_WIDTH - y) - 1; 193 y = LCD_WIDTH - 1 - y;
194 fb_data *dst = (fb_data*)FRAME + x * LCD_WIDTH + y;
186 195
187 z = stride*src_y; 196 z = stride*src_y;
188 yuv_src[0] = src[0] + z + src_x; 197 yuv_src[0] = src[0] + z + src_x;
189 yuv_src[1] = src[1] + (z >> 2) + (src_x >> 1); 198 yuv_src[1] = src[1] + (z >> 2) + (src_x >> 1);
190 yuv_src[2] = src[2] + (yuv_src[1] - src[1]); 199 yuv_src[2] = src[2] + (yuv_src[1] - src[1]);
191 200
192 do 201 if (lcd_yuv_options & LCD_YUV_DITHER)
202 {
203 do
204 {
205 lcd_write_yuv420_lines_odither(dst, yuv_src, width, stride, y, x);
206 yuv_src[0] += stride << 1; /* Skip down two luma lines */
207 yuv_src[1] += stride >> 1; /* Skip down one chroma line */
208 yuv_src[2] += stride >> 1;
209 dst -= 2;
210 y -= 2;
211 }
212 while (--height > 0);
213 }
214 else
193 { 215 {
194 lcd_write_yuv420_lines(dst, chroma_buf, yuv_src, width, 216 do
195 stride); 217 {
196 yuv_src[0] += stride << 1; /* Skip down two luma lines */ 218 lcd_write_yuv420_lines(dst, yuv_src, width, stride);
197 yuv_src[1] += stride >> 1; /* Skip down one chroma line */ 219 yuv_src[0] += stride << 1; /* Skip down two luma lines */
198 yuv_src[2] += stride >> 1; 220 yuv_src[1] += stride >> 1; /* Skip down one chroma line */
199 dst -= 2; 221 yuv_src[2] += stride >> 1;
222 dst -= 2;
223 }
224 while (--height > 0);
200 } 225 }
201 while (--height > 0);
202} 226}
203 227
204void lcd_set_contrast(int val) { 228void lcd_set_contrast(int val) {
diff --git a/firmware/target/arm/imx31/gigabeat-s/mmu-imx31.c b/firmware/target/arm/imx31/gigabeat-s/mmu-imx31.c
index e8ec495449..e116439217 100644
--- a/firmware/target/arm/imx31/gigabeat-s/mmu-imx31.c
+++ b/firmware/target/arm/imx31/gigabeat-s/mmu-imx31.c
@@ -21,16 +21,20 @@
21#include "mmu-arm.h" 21#include "mmu-arm.h"
22 22
23void memory_init(void) { 23void memory_init(void) {
24#if 0
24 ttb_init(); 25 ttb_init();
25 set_page_tables(); 26 set_page_tables();
26 enable_mmu(); 27 enable_mmu();
28#endif
27} 29}
28 30
29void set_page_tables() { 31void set_page_tables() {
32#if 0
30 map_section(0, 0, 0x1000, CACHE_NONE); /* map every memory region to itself */ 33 map_section(0, 0, 0x1000, CACHE_NONE); /* map every memory region to itself */
31 /*This pa *might* change*/ 34 /*This pa *might* change*/
32 map_section(0x80000000, 0, 64, CACHE_ALL); /* map RAM to 0 and enable caching for it */ 35 map_section(0x80000000, 0, 64, CACHE_ALL); /* map RAM to 0 and enable caching for it */
33 map_section((int)FRAME1, (int)FRAME1, 1, BUFFERED); /* enable buffered writing for the framebuffer */ 36 map_section((int)FRAME1, (int)FRAME1, 1, BUFFERED); /* enable buffered writing for the framebuffer */
34 map_section((int)FRAME2, (int)FRAME2, 1, BUFFERED); 37 map_section((int)FRAME2, (int)FRAME2, 1, BUFFERED);
38#endif
35} 39}
36 40
diff --git a/firmware/target/arm/imx31/gigabeat-s/pcm-imx31.c b/firmware/target/arm/imx31/gigabeat-s/pcm-imx31.c
index b62051e41d..8485679aa4 100644
--- a/firmware/target/arm/imx31/gigabeat-s/pcm-imx31.c
+++ b/firmware/target/arm/imx31/gigabeat-s/pcm-imx31.c
@@ -27,8 +27,6 @@
27 27
28static int pcm_freq = HW_SAMPR_DEFAULT; /* 44.1 is default */ 28static int pcm_freq = HW_SAMPR_DEFAULT; /* 44.1 is default */
29 29
30void fiq_handler(void) __attribute__((naked));
31
32void pcm_play_lock(void) 30void pcm_play_lock(void)
33{ 31{
34} 32}
@@ -77,12 +75,6 @@ void pcm_play_dma_pause(bool pause)
77{ 75{
78} 76}
79 77
80/* Get more samples to play out - call pcm_play_dma_stop and
81 pcm_play_dma_stopped_callback if the data runs out */
82void fiq_handler(void)
83{
84}
85
86/* Set the pcm frequency hardware will use when play is next started or 78/* Set the pcm frequency hardware will use when play is next started or
87 when pcm_apply_settings is called. Do not apply the setting to the 79 when pcm_apply_settings is called. Do not apply the setting to the
88 hardware here but simply cache it. */ 80 hardware here but simply cache it. */
diff --git a/firmware/target/arm/imx31/gigabeat-s/system-imx31.c b/firmware/target/arm/imx31/gigabeat-s/system-imx31.c
index 544ae3afe6..ed5a26cd6e 100644
--- a/firmware/target/arm/imx31/gigabeat-s/system-imx31.c
+++ b/firmware/target/arm/imx31/gigabeat-s/system-imx31.c
@@ -13,27 +13,15 @@ int system_memory_guard(int newmode)
13 return 0; 13 return 0;
14} 14}
15 15
16extern void timer4(void);
17extern void dma0(void); /* free */
18extern void dma1(void);
19extern void dma3(void);
20
21void irq_handler(void)
22{
23}
24
25#ifdef BOOTLOADER
26void fiq_handler(void)
27{
28}
29#endif
30
31void system_reboot(void) 16void system_reboot(void)
32{ 17{
33} 18}
34 19
35void system_init(void) 20void system_init(void)
36{ 21{
22#ifndef BOOTLOADER
23 avic_init();
24#endif
37} 25}
38 26
39inline void dumpregs(void) 27inline void dumpregs(void)
diff --git a/firmware/target/arm/imx31/gigabeat-s/system-target.h b/firmware/target/arm/imx31/gigabeat-s/system-target.h
index e87b93b13a..1f7a2475af 100644
--- a/firmware/target/arm/imx31/gigabeat-s/system-target.h
+++ b/firmware/target/arm/imx31/gigabeat-s/system-target.h
@@ -19,15 +19,15 @@
19#ifndef SYSTEM_TARGET_H 19#ifndef SYSTEM_TARGET_H
20#define SYSTEM_TARGET_H 20#define SYSTEM_TARGET_H
21 21
22#include "mmu-imx31.h"
23#include "system-arm.h" 22#include "system-arm.h"
23#include "mmu-arm.h"
24 24
25#define CPUFREQ_NORMAL 532000000 25#define CPUFREQ_NORMAL 532000000
26 26
27static inline void udelay(unsigned int usecs) 27static inline void udelay(unsigned int usecs)
28{ 28{
29 volatile signed int stop = EPITCNT1 - usecs; 29 volatile signed int stop = EPITCNT1 - usecs;
30 while (EPITCNT1 > stop); 30 while ((signed int)EPITCNT1 > stop);
31} 31}
32 32
33#define __dbg_hw_info(...) 0 33#define __dbg_hw_info(...) 0
@@ -36,6 +36,22 @@ static inline void udelay(unsigned int usecs)
36#define HAVE_INVALIDATE_ICACHE 36#define HAVE_INVALIDATE_ICACHE
37static inline void invalidate_icache(void) 37static inline void invalidate_icache(void)
38{ 38{
39 long rd = 0;
40 asm volatile(
41 "mcr p15, 0, %0, c7, c10, 0 \n"
42 "mcr p15, 0, %0, c7, c5, 0 \n"
43 : : "r"(rd)
44 );
45}
46
47#define HAVE_FLUSH_ICACHE
48static inline void flush_icache(void)
49{
50 long rd = 0;
51 asm volatile (
52 "mcr p15, 0, %0, c7, c10, 0 \n"
53 : : "r"(rd)
54 );
39} 55}
40 56
41struct ARM_REGS { 57struct ARM_REGS {