fix off-by-one error when reading spi data
[kugel-rb.git] / bootloader / telechips.c
blob7f9a3556c0589bd944907d789b15ce109a0bc7a3
1 /***************************************************************************
2 * __________ __ ___.
3 * Open \______ \ ____ ____ | | _\_ |__ _______ ___
4 * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
5 * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
6 * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
7 * \/ \/ \/ \/ \/
8 * $Id$
10 * Copyright (C) 2007 by Dave Chapman
12 * Based on Rockbox iriver bootloader by Linus Nielsen Feltzing
14 * This program is free software; you can redistribute it and/or
15 * modify it under the terms of the GNU General Public License
16 * as published by the Free Software Foundation; either version 2
17 * of the License, or (at your option) any later version.
19 * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
20 * KIND, either express or implied.
22 ****************************************************************************/
23 #include "config.h"
25 #include <stdlib.h>
26 #include <stdio.h>
27 #include <string.h>
28 #include "cpu.h"
29 #include "system.h"
30 #include "lcd.h"
31 #include "kernel.h"
32 #include "thread.h"
33 #include "ata.h"
34 #include "fat.h"
35 #include "disk.h"
36 #include "font.h"
37 #include "button.h"
38 #include "adc.h"
39 #include "adc-target.h"
40 #include "backlight.h"
41 #include "backlight-target.h"
42 #include "panic.h"
43 #include "power.h"
44 #include "file.h"
45 #include "common.h"
47 #if defined(COWON_D2) || defined(IAUDIO_7) && defined(TCCBOOT)
48 # define REAL_BOOT
49 #endif
51 #ifdef REAL_BOOT
52 # if defined(COWON_D2) || defined(IAUDIO_7)
53 # include "pcf50606.h"
54 # endif
55 # define LOAD_ADDRESS 0x20000000 /* DRAM_START */
56 #endif
58 char version[] = APPSVERSION;
60 extern int line;
62 #define MAX_LOAD_SIZE (8*1024*1024) /* Arbitrary, but plenty. */
64 /* The following function is just test/development code */
65 #ifdef CPU_TCC77X
66 void show_debug_screen(void)
68 int button;
69 int power_count = 0;
70 int count = 0;
71 bool do_power_off = false;
73 /*lcd_puts_scroll(0,0,"this is a very long line to test scrolling");*/
74 while(!do_power_off) {
76 line = 1;
77 button = button_get(false);
79 /* Power-off if POWER button has been held for a time
80 This loop is currently running at about 100 iterations/second
82 if (button & POWEROFF_BUTTON) {
83 power_count++;
84 if (power_count > 100)
85 do_power_off = true;
86 } else {
87 power_count = 0;
89 #ifdef BUTTON_SELECT
90 if (button & BUTTON_SELECT){
91 _backlight_off();
93 else{
94 _backlight_on();
96 #endif
97 /*printf("Btn: 0x%08x",button);
98 printf("Tick: %d",current_tick);
99 printf("GPIOA: 0x%08x",GPIOA);
100 printf("GPIOB: 0x%08x",GPIOB);
101 printf("GPIOC: 0x%08x",GPIOC);
102 printf("GPIOD: 0x%08x",GPIOD);
103 printf("GPIOE: 0x%08x",GPIOE);*/
105 #if 0
106 int i;
107 for (i = 1; i<4; i++)
109 printf("ADC%d: 0x%04x",i,adc_read(i));
111 #endif
112 count++;
113 printf("Count: %d",count);
114 sleep(HZ/10);
118 lcd_clear_display();
119 line = 0;
120 printf("POWER-OFF");
122 /* Power-off */
123 power_off();
125 printf("(NOT) POWERED OFF");
126 while (true);
129 #else /* !CPU_TCC77X */
130 void show_debug_screen(void)
132 int button;
133 int power_count = 0;
134 int count = 0;
135 bool do_power_off = false;
136 #ifdef HAVE_BUTTON_DATA
137 unsigned int data;
138 #endif
140 while(!do_power_off) {
141 line = 0;
142 printf("Hello World!");
144 #ifdef HAVE_BUTTON_DATA
145 button = button_read_device(&data);
146 #else
147 button = button_read_device();
148 #endif
150 /* Power-off if POWER button has been held for a long time
151 This loop is currently running at about 100 iterations/second
153 if (button & POWEROFF_BUTTON) {
154 power_count++;
155 if (power_count > 200)
156 do_power_off = true;
157 } else {
158 power_count = 0;
161 printf("Btn: 0x%08x",button);
163 count++;
164 printf("Count: %d",count);
167 lcd_clear_display();
168 line = 0;
169 printf("POWER-OFF");
171 /* Power-off */
172 power_off();
174 printf("(NOT) POWERED OFF");
175 while (true);
177 #endif
179 void* main(void)
181 #ifdef REAL_BOOT
182 int rc;
183 unsigned char* loadbuffer = (unsigned char*)LOAD_ADDRESS;
184 #endif
186 system_init();
187 power_init();
188 #ifndef COWON_D2
189 /* The D2 doesn't enable threading or interrupts */
190 kernel_init();
191 enable_irq();
192 #endif
193 lcd_init();
195 adc_init();
196 button_init();
197 backlight_init();
199 font_init();
200 lcd_setfont(FONT_SYSFIXED);
202 _backlight_on();
204 /* Only load the firmware if TCCBOOT is defined - this ensures SDRAM_START is
205 available for loading the firmware. Otherwise display the debug screen. */
206 #ifdef REAL_BOOT
207 printf("Rockbox boot loader");
208 printf("Version %s", version);
210 printf("ATA");
211 rc = ata_init();
212 if(rc)
214 reset_screen();
215 error(EATA, rc);
218 printf("mount");
219 rc = disk_mount_all();
220 if (rc<=0)
222 error(EDISK,rc);
225 rc = load_firmware(loadbuffer, BOOTFILE, MAX_LOAD_SIZE);
227 if (rc < 0)
229 error(EBOOTFILE,rc);
231 else if (rc == EOK)
233 int(*kernel_entry)(void);
235 kernel_entry = (void*) loadbuffer;
236 rc = kernel_entry();
238 #else
239 show_debug_screen();
240 #endif
242 return 0;
245 /* These functions are present in the firmware library, but we reimplement
246 them here because the originals do a lot more than we want */
247 void usb_acknowledge(void)
251 void usb_wait_for_disconnect(void)