Clean up multiple definitions of RAM size. Remove -DMEM (make) and MEM (code), use...
[maemo-rb.git] / apps / debug_menu.c
blob2d356ab573b938acd38e4e50d7d5572563101b20
1 /***************************************************************************
2 * __________ __ ___.
3 * Open \______ \ ____ ____ | | _\_ |__ _______ ___
4 * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
5 * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
6 * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
7 * \/ \/ \/ \/ \/
8 * $Id$
10 * Copyright (C) 2002 Heikki Hannikainen
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 ****************************************************************************/
22 #include "config.h"
23 #include <stdlib.h>
24 #include <stdio.h>
25 #include <stdbool.h>
26 #include <string.h>
27 #include "lcd.h"
28 #include "menu.h"
29 #include "debug_menu.h"
30 #include "kernel.h"
31 #include "structec.h"
32 #include "action.h"
33 #include "debug.h"
34 #include "thread.h"
35 #include "powermgmt.h"
36 #include "system.h"
37 #include "font.h"
38 #include "audio.h"
39 #include "mp3_playback.h"
40 #include "settings.h"
41 #include "list.h"
42 #include "statusbar.h"
43 #include "dir.h"
44 #include "panic.h"
45 #include "screens.h"
46 #include "misc.h"
47 #include "splash.h"
48 #include "dircache.h"
49 #include "viewport.h"
50 #ifdef HAVE_TAGCACHE
51 #include "tagcache.h"
52 #endif
53 #include "lcd-remote.h"
54 #include "crc32.h"
55 #include "logf.h"
56 #if (CONFIG_PLATFORM & PLATFORM_NATIVE)
57 #include "disk.h"
58 #include "adc.h"
59 #include "power.h"
60 #include "usb.h"
61 #include "rtc.h"
62 #include "storage.h"
63 #include "fat.h"
64 #include "eeprom_24cxx.h"
65 #if (CONFIG_STORAGE & STORAGE_MMC) || (CONFIG_STORAGE & STORAGE_SD)
66 #include "sdmmc.h"
67 #endif
68 #if (CONFIG_STORAGE & STORAGE_ATA)
69 #include "ata.h"
70 #endif
71 #if CONFIG_TUNER
72 #include "tuner.h"
73 #include "radio.h"
74 #endif
75 #endif
77 #ifdef HAVE_LCD_BITMAP
78 #include "scrollbar.h"
79 #include "peakmeter.h"
80 #endif
81 #include "logfdisp.h"
82 #if CONFIG_CODEC == SWCODEC
83 #include "pcmbuf.h"
84 #include "buffering.h"
85 #include "playback.h"
86 #if defined(HAVE_SPDIF_OUT) || defined(HAVE_SPDIF_IN)
87 #include "spdif.h"
88 #endif
89 #endif
90 #ifdef IRIVER_H300_SERIES
91 #include "pcf50606.h" /* for pcf50606_read */
92 #endif
93 #ifdef IAUDIO_X5
94 #include "ds2411.h"
95 #endif
96 #include "hwcompat.h"
97 #include "button.h"
98 #if CONFIG_RTC == RTC_PCF50605
99 #include "pcf50605.h"
100 #endif
101 #include "appevents.h"
102 #if (CONFIG_PLATFORM & PLATFORM_NATIVE)
103 #include "debug-target.h"
104 #endif
106 #if defined(SANSA_E200) || defined(SANSA_C200) || defined(PHILIPS_SA9200) \
107 || (CONFIG_CPU == AS3525 && defined(CONFIG_CHARGING)) \
108 || CONFIG_CPU == AS3525v2
109 #include "ascodec.h"
110 #include "as3514.h"
111 #endif
113 #ifdef IPOD_NANO2G
114 #include "pmu-target.h"
115 #endif
117 #ifdef HAVE_USBSTACK
118 #include "usb_core.h"
119 #endif
121 #if defined(IPOD_ACCESSORY_PROTOCOL)
122 #include "iap.h"
123 #endif
125 /*---------------------------------------------------*/
126 /* SPECIAL DEBUG STUFF */
127 /*---------------------------------------------------*/
128 extern struct thread_entry threads[MAXTHREADS];
130 static char thread_status_char(unsigned status)
132 static const char thread_status_chars[THREAD_NUM_STATES+1] =
134 [0 ... THREAD_NUM_STATES] = '?',
135 [STATE_RUNNING] = 'R',
136 [STATE_BLOCKED] = 'B',
137 [STATE_SLEEPING] = 'S',
138 [STATE_BLOCKED_W_TMO] = 'T',
139 [STATE_FROZEN] = 'F',
140 [STATE_KILLED] = 'K',
143 if (status > THREAD_NUM_STATES)
144 status = THREAD_NUM_STATES;
146 return thread_status_chars[status];
149 static const char* threads_getname(int selected_item, void *data,
150 char *buffer, size_t buffer_len)
152 (void)data;
153 struct thread_entry *thread;
154 char name[32];
156 #if NUM_CORES > 1
157 if (selected_item < (int)NUM_CORES)
159 snprintf(buffer, buffer_len, "Idle (%d): %2d%%", selected_item,
160 idle_stack_usage(selected_item));
161 return buffer;
164 selected_item -= NUM_CORES;
165 #endif
167 thread = &threads[selected_item];
169 if (thread->state == STATE_KILLED)
171 snprintf(buffer, buffer_len, "%2d: ---", selected_item);
172 return buffer;
175 thread_get_name(name, 32, thread);
177 snprintf(buffer, buffer_len,
178 "%2d: " IF_COP("(%d) ") "%c%c " IF_PRIO("%d %d ") "%2d%% %s",
179 selected_item,
180 IF_COP(thread->core,)
181 #ifdef HAVE_SCHEDULER_BOOSTCTRL
182 (thread->cpu_boost) ? '+' :
183 #endif
184 ((thread->state == STATE_RUNNING) ? '*' : ' '),
185 thread_status_char(thread->state),
186 IF_PRIO(thread->base_priority, thread->priority, )
187 thread_stack_usage(thread), name);
189 return buffer;
192 static int dbg_threads_action_callback(int action, struct gui_synclist *lists)
194 (void)lists;
195 #ifdef ROCKBOX_HAS_LOGF
196 if (action == ACTION_STD_OK)
198 int selpos = gui_synclist_get_sel_pos(lists);
199 #if NUM_CORES > 1
200 if (selpos >= NUM_CORES)
201 remove_thread(threads[selpos - NUM_CORES].id);
202 #else
203 remove_thread(threads[selpos].id);
204 #endif
205 return ACTION_REDRAW;
207 #endif /* ROCKBOX_HAS_LOGF */
208 if (action == ACTION_NONE)
209 action = ACTION_REDRAW;
210 return action;
212 /* Test code!!! */
213 static bool dbg_os(void)
215 struct simplelist_info info;
216 simplelist_info_init(&info, IF_COP("Core and ") "Stack usage:",
217 #if NUM_CORES == 1
218 MAXTHREADS,
219 #else
220 MAXTHREADS+NUM_CORES,
221 #endif
222 NULL);
223 #ifndef ROCKBOX_HAS_LOGF
224 info.hide_selection = true;
225 info.scroll_all = true;
226 #endif
227 info.action_callback = dbg_threads_action_callback;
228 info.get_name = threads_getname;
229 return simplelist_show_list(&info);
232 #ifdef HAVE_LCD_BITMAP
233 #if CONFIG_CODEC != SWCODEC
234 #ifndef SIMULATOR
235 static bool dbg_audio_thread(void)
237 struct audio_debug d;
239 lcd_setfont(FONT_SYSFIXED);
241 while(1)
243 if (action_userabort(HZ/5))
244 return false;
246 audio_get_debugdata(&d);
248 lcd_clear_display();
250 lcd_putsf(0, 0, "read: %x", d.audiobuf_read);
251 lcd_putsf(0, 1, "write: %x", d.audiobuf_write);
252 lcd_putsf(0, 2, "swap: %x", d.audiobuf_swapwrite);
253 lcd_putsf(0, 3, "playing: %d", d.playing);
254 lcd_putsf(0, 4, "playable: %x", d.playable_space);
255 lcd_putsf(0, 5, "unswapped: %x", d.unswapped_space);
257 /* Playable space left */
258 gui_scrollbar_draw(&screens[SCREEN_MAIN],0, 6*8, 112, 4, d.audiobuflen, 0,
259 d.playable_space, HORIZONTAL);
261 /* Show the watermark limit */
262 gui_scrollbar_draw(&screens[SCREEN_MAIN],0, 6*8+4, 112, 4, d.audiobuflen, 0,
263 d.low_watermark_level, HORIZONTAL);
265 lcd_putsf(0, 7, "wm: %x - %x",
266 d.low_watermark_level, d.lowest_watermark_level);
268 lcd_update();
270 lcd_setfont(FONT_UI);
271 return false;
273 #endif /* !SIMULATOR */
274 #else /* CONFIG_CODEC == SWCODEC */
275 static unsigned int ticks, freq_sum;
276 #ifndef CPU_MULTI_FREQUENCY
277 static unsigned int boost_ticks;
278 #endif
280 static void dbg_audio_task(void)
282 #ifdef CPUFREQ_NORMAL
283 #ifndef CPU_MULTI_FREQUENCY
284 if(FREQ > CPUFREQ_NORMAL)
285 boost_ticks++;
286 #endif
287 freq_sum += FREQ/1000000; /* in MHz */
288 #endif
289 ticks++;
292 static bool dbg_buffering_thread(void)
294 int button;
295 int line, i;
296 bool done = false;
297 size_t bufused;
298 size_t bufsize = pcmbuf_get_bufsize();
299 int pcmbufdescs = pcmbuf_descs();
300 struct buffering_debug d;
301 size_t filebuflen = audio_get_filebuflen();
302 /* This is a size_t, but call it a long so it puts a - when it's bad. */
304 #ifndef CPU_MULTI_FREQUENCY
305 boost_ticks = 0;
306 #endif
307 ticks = freq_sum = 0;
309 tick_add_task(dbg_audio_task);
311 FOR_NB_SCREENS(i)
312 screens[i].setfont(FONT_SYSFIXED);
314 while(!done)
316 button = get_action(CONTEXT_STD,HZ/5);
317 switch(button)
319 case ACTION_STD_NEXT:
320 audio_next();
321 break;
322 case ACTION_STD_PREV:
323 audio_prev();
324 break;
325 case ACTION_STD_CANCEL:
326 done = true;
327 break;
330 buffering_get_debugdata(&d);
331 bufused = bufsize - pcmbuf_free();
333 FOR_NB_SCREENS(i)
335 line = 0;
336 screens[i].clear_display();
339 screens[i].putsf(0, line++, "pcm: %6ld/%ld", (long) bufused, (long) bufsize);
341 gui_scrollbar_draw(&screens[i],0, line*8, screens[i].lcdwidth, 6,
342 bufsize, 0, bufused, HORIZONTAL);
343 line++;
345 screens[i].putsf(0, line++, "alloc: %6ld/%ld", audio_filebufused(),
346 (long) filebuflen);
348 #if LCD_HEIGHT > 80 || (defined(HAVE_REMOTE_LCD) && LCD_REMOTE_HEIGHT > 80)
349 if (screens[i].lcdheight > 80)
351 gui_scrollbar_draw(&screens[i],0, line*8, screens[i].lcdwidth, 6,
352 filebuflen, 0, audio_filebufused(), HORIZONTAL);
353 line++;
355 screens[i].putsf(0, line++, "real: %6ld/%ld", (long)d.buffered_data,
356 (long)filebuflen);
358 gui_scrollbar_draw(&screens[i],0, line*8, screens[i].lcdwidth, 6,
359 filebuflen, 0, (long)d.buffered_data, HORIZONTAL);
360 line++;
362 #endif
364 screens[i].putsf(0, line++, "usefl: %6ld/%ld", (long)(d.useful_data),
365 (long)filebuflen);
367 #if LCD_HEIGHT > 80 || (defined(HAVE_REMOTE_LCD) && LCD_REMOTE_HEIGHT > 80)
368 if (screens[i].lcdheight > 80)
370 gui_scrollbar_draw(&screens[i],0, line*8, screens[i].lcdwidth, 6,
371 filebuflen, 0, d.useful_data, HORIZONTAL);
372 line++;
374 #endif
376 screens[i].putsf(0, line++, "data_rem: %ld", (long)d.data_rem);
378 screens[i].putsf(0, line++, "track count: %2d", audio_track_count());
380 screens[i].putsf(0, line++, "handle count: %d", (int)d.num_handles);
382 #if (CONFIG_PLATFORM & PLATFORM_NATIVE)
383 screens[i].putsf(0, line++, "cpu freq: %3dMHz",
384 (int)((FREQ + 500000) / 1000000));
385 #endif
387 if (ticks > 0)
389 int avgclock = freq_sum * 10 / ticks; /* in 100 kHz */
390 #ifdef CPU_MULTI_FREQUENCY
391 int boostquota = (avgclock * 100 - CPUFREQ_NORMAL/1000) /
392 ((CPUFREQ_MAX - CPUFREQ_NORMAL) / 1000000); /* in 0.1 % */
393 #else
394 int boostquota = boost_ticks * 1000 / ticks; /* in 0.1 % */
395 #endif
396 screens[i].putsf(0, line++, "boost:%3d.%d%% (%d.%dMHz)",
397 boostquota/10, boostquota%10, avgclock/10, avgclock%10);
400 screens[i].putsf(0, line++, "pcmbufdesc: %2d/%2d",
401 pcmbuf_used_descs(), pcmbufdescs);
402 screens[i].putsf(0, line++, "watermark: %6d",
403 (int)(d.watermark));
405 screens[i].update();
409 tick_remove_task(dbg_audio_task);
411 FOR_NB_SCREENS(i)
412 screens[i].setfont(FONT_UI);
414 return false;
416 #endif /* CONFIG_CODEC */
417 #endif /* HAVE_LCD_BITMAP */
420 #if (CONFIG_CPU == SH7034 || defined(CPU_COLDFIRE))
421 /* Tool function to read the flash manufacturer and type, if available.
422 Only chips which could be reprogrammed in system will return values.
423 (The mode switch addresses vary between flash manufacturers, hence addr1/2) */
424 /* In IRAM to avoid problems when running directly from Flash */
425 static bool dbg_flash_id(unsigned* p_manufacturer, unsigned* p_device,
426 unsigned addr1, unsigned addr2)
427 ICODE_ATTR __attribute__((noinline));
428 static bool dbg_flash_id(unsigned* p_manufacturer, unsigned* p_device,
429 unsigned addr1, unsigned addr2)
432 unsigned not_manu, not_id; /* read values before switching to ID mode */
433 unsigned manu, id; /* read values when in ID mode */
435 #if CONFIG_CPU == SH7034
436 volatile unsigned char* flash = (unsigned char*)0x2000000; /* flash mapping */
437 #elif defined(CPU_COLDFIRE)
438 volatile unsigned short* flash = (unsigned short*)0; /* flash mapping */
439 #endif
440 int old_level; /* saved interrupt level */
442 not_manu = flash[0]; /* read the normal content */
443 not_id = flash[1]; /* should be 'A' (0x41) and 'R' (0x52) from the "ARCH" marker */
445 /* disable interrupts, prevent any stray flash access */
446 old_level = disable_irq_save();
448 flash[addr1] = 0xAA; /* enter command mode */
449 flash[addr2] = 0x55;
450 flash[addr1] = 0x90; /* ID command */
451 /* Atmel wants 20ms pause here */
452 /* sleep(HZ/50); no sleeping possible while interrupts are disabled */
454 manu = flash[0]; /* read the IDs */
455 id = flash[1];
457 flash[0] = 0xF0; /* reset flash (back to normal read mode) */
458 /* Atmel wants 20ms pause here */
459 /* sleep(HZ/50); no sleeping possible while interrupts are disabled */
461 restore_irq(old_level); /* enable interrupts again */
463 /* I assume success if the obtained values are different from
464 the normal flash content. This is not perfectly bulletproof, they
465 could theoretically be the same by chance, causing us to fail. */
466 if (not_manu != manu || not_id != id) /* a value has changed */
468 *p_manufacturer = manu; /* return the results */
469 *p_device = id;
470 return true; /* success */
472 return false; /* fail */
474 #endif /* (CONFIG_CPU == SH7034 || CPU_COLDFIRE) */
476 #if (CONFIG_PLATFORM & PLATFORM_NATIVE)
477 #ifdef CPU_PP
478 static int perfcheck(void)
480 int result;
482 asm (
483 "mrs r2, CPSR \n"
484 "orr r0, r2, #0xc0 \n" /* disable IRQ and FIQ */
485 "msr CPSR_c, r0 \n"
486 "mov %[res], #0 \n"
487 "ldr r0, [%[timr]] \n"
488 "add r0, r0, %[tmo] \n"
489 "1: \n"
490 "add %[res], %[res], #1 \n"
491 "ldr r1, [%[timr]] \n"
492 "cmp r1, r0 \n"
493 "bmi 1b \n"
494 "msr CPSR_c, r2 \n" /* reset IRQ and FIQ state */
496 [res]"=&r"(result)
498 [timr]"r"(&USEC_TIMER),
499 [tmo]"r"(
500 #if CONFIG_CPU == PP5002
501 16000
502 #else /* PP5020/5022/5024 */
503 10226
504 #endif
507 "r0", "r1", "r2"
509 return result;
511 #endif
513 #ifdef HAVE_LCD_BITMAP
514 static bool dbg_hw_info(void)
516 #if CONFIG_CPU == SH7034
517 int bitmask = HW_MASK;
518 int rom_version = ROM_VERSION;
519 unsigned manu, id; /* flash IDs */
520 bool got_id; /* flag if we managed to get the flash IDs */
521 unsigned rom_crc = 0xffffffff; /* CRC32 of the boot ROM */
522 bool has_bootrom; /* flag for boot ROM present */
523 int oldmode; /* saved memory guard mode */
525 oldmode = system_memory_guard(MEMGUARD_NONE); /* disable memory guard */
527 /* get flash ROM type */
528 got_id = dbg_flash_id(&manu, &id, 0x5555, 0x2AAA); /* try SST, Atmel, NexFlash */
529 if (!got_id)
530 got_id = dbg_flash_id(&manu, &id, 0x555, 0x2AA); /* try AMD, Macronix */
532 /* check if the boot ROM area is a flash mirror */
533 has_bootrom = (memcmp((char*)0, (char*)0x02000000, 64*1024) != 0);
534 if (has_bootrom) /* if ROM and Flash different */
536 /* calculate CRC16 checksum of boot ROM */
537 rom_crc = crc_32((unsigned char*)0x0000, 64*1024, 0xffffffff);
540 system_memory_guard(oldmode); /* re-enable memory guard */
542 lcd_setfont(FONT_SYSFIXED);
543 lcd_clear_display();
545 lcd_puts(0, 0, "[Hardware info]");
547 lcd_putsf(0, 1, "ROM: %d.%02d", rom_version/100, rom_version%100);
549 lcd_putsf(0, 2, "Mask: 0x%04x", bitmask);
551 if (got_id)
552 lcd_putsf(0, 3, "Flash: M=%02x D=%02x", manu, id);
553 else
554 lcd_puts(0, 3, "Flash: M=?? D=??"); /* unknown, sorry */
556 if (has_bootrom)
558 if (rom_crc == 0x56DBA4EE) /* known Version 1 */
559 lcd_puts(0, 4, "Boot ROM: V1");
560 else
561 lcd_putsf(0, 4, "ROMcrc: 0x%08x", rom_crc);
563 else
565 lcd_puts(0, 4, "Boot ROM: none");
568 lcd_update();
570 while (!(action_userabort(TIMEOUT_BLOCK)));
572 #elif CONFIG_CPU == MCF5249 || CONFIG_CPU == MCF5250
573 unsigned manu, id; /* flash IDs */
574 int got_id; /* flag if we managed to get the flash IDs */
575 int oldmode; /* saved memory guard mode */
576 int line = 0;
578 oldmode = system_memory_guard(MEMGUARD_NONE); /* disable memory guard */
580 /* get flash ROM type */
581 got_id = dbg_flash_id(&manu, &id, 0x5555, 0x2AAA); /* try SST, Atmel, NexFlash */
582 if (!got_id)
583 got_id = dbg_flash_id(&manu, &id, 0x555, 0x2AA); /* try AMD, Macronix */
585 system_memory_guard(oldmode); /* re-enable memory guard */
587 lcd_setfont(FONT_SYSFIXED);
588 lcd_clear_display();
590 lcd_puts(0, line++, "[Hardware info]");
592 if (got_id)
593 lcd_putsf(0, line++, "Flash: M=%04x D=%04x", manu, id);
594 else
595 lcd_puts(0, line++, "Flash: M=???? D=????"); /* unknown, sorry */
597 #ifdef IAUDIO_X5
599 struct ds2411_id id;
601 lcd_puts(0, ++line, "Serial Number:");
603 got_id = ds2411_read_id(&id);
605 if (got_id == DS2411_OK)
607 lcd_putsf(0, ++line, " FC=%02x", (unsigned)id.family_code);
608 lcd_putsf(0, ++line, " ID=%02X %02X %02X %02X %02X %02X",
609 (unsigned)id.uid[0], (unsigned)id.uid[1], (unsigned)id.uid[2],
610 (unsigned)id.uid[3], (unsigned)id.uid[4], (unsigned)id.uid[5]);
611 lcd_putsf(0, ++line, " CRC=%02X", (unsigned)id.crc);
613 else
615 lcd_putsf(0, ++line, "READ ERR=%d", got_id);
618 #endif
620 lcd_update();
622 while (!(action_userabort(TIMEOUT_BLOCK)));
624 #elif defined(CPU_PP502x)
625 int line = 0;
626 char pp_version[] = { (PP_VER2 >> 24) & 0xff, (PP_VER2 >> 16) & 0xff,
627 (PP_VER2 >> 8) & 0xff, (PP_VER2) & 0xff,
628 (PP_VER1 >> 24) & 0xff, (PP_VER1 >> 16) & 0xff,
629 (PP_VER1 >> 8) & 0xff, (PP_VER1) & 0xff, '\0' };
631 lcd_setfont(FONT_SYSFIXED);
632 lcd_clear_display();
634 lcd_puts(0, line++, "[Hardware info]");
636 #ifdef IPOD_ARCH
637 lcd_putsf(0, line++, "HW rev: 0x%08lx", IPOD_HW_REVISION);
638 #endif
640 #ifdef IPOD_COLOR
641 extern int lcd_type; /* Defined in lcd-colornano.c */
643 lcd_putsf(0, line++, "LCD type: %d", lcd_type);
644 #endif
646 lcd_putsf(0, line++, "PP version: %s", pp_version);
648 lcd_putsf(0, line++, "Est. clock (kHz): %d", perfcheck());
650 lcd_update();
652 while (!(action_userabort(TIMEOUT_BLOCK)));
654 #elif CONFIG_CPU == PP5002
655 int line = 0;
656 char pp_version[] = { (PP_VER4 >> 8) & 0xff, PP_VER4 & 0xff,
657 (PP_VER3 >> 8) & 0xff, PP_VER3 & 0xff,
658 (PP_VER2 >> 8) & 0xff, PP_VER2 & 0xff,
659 (PP_VER1 >> 8) & 0xff, PP_VER1 & 0xff, '\0' };
662 lcd_setfont(FONT_SYSFIXED);
663 lcd_clear_display();
665 lcd_puts(0, line++, "[Hardware info]");
667 #ifdef IPOD_ARCH
668 lcd_putsf(0, line++, "HW rev: 0x%08lx", IPOD_HW_REVISION);
669 #endif
671 lcd_putsf(0, line++, "PP version: %s", pp_version);
673 lcd_putsf(0, line++, "Est. clock (kHz): %d", perfcheck());
675 lcd_update();
677 while (!(action_userabort(TIMEOUT_BLOCK)));
679 #else
680 /* Define this function in your target tree */
681 return __dbg_hw_info();
682 #endif /* CONFIG_CPU */
683 lcd_setfont(FONT_UI);
684 return false;
686 #else /* !HAVE_LCD_BITMAP */
687 static bool dbg_hw_info(void)
689 int button;
690 int currval = 0;
691 int rom_version = ROM_VERSION;
692 unsigned manu, id; /* flash IDs */
693 bool got_id; /* flag if we managed to get the flash IDs */
694 unsigned rom_crc = 0xffffffff; /* CRC32 of the boot ROM */
695 bool has_bootrom; /* flag for boot ROM present */
696 int oldmode; /* saved memory guard mode */
698 oldmode = system_memory_guard(MEMGUARD_NONE); /* disable memory guard */
700 /* get flash ROM type */
701 got_id = dbg_flash_id(&manu, &id, 0x5555, 0x2AAA); /* try SST, Atmel, NexFlash */
702 if (!got_id)
703 got_id = dbg_flash_id(&manu, &id, 0x555, 0x2AA); /* try AMD, Macronix */
705 /* check if the boot ROM area is a flash mirror */
706 has_bootrom = (memcmp((char*)0, (char*)0x02000000, 64*1024) != 0);
707 if (has_bootrom) /* if ROM and Flash different */
709 /* calculate CRC16 checksum of boot ROM */
710 rom_crc = crc_32((unsigned char*)0x0000, 64*1024, 0xffffffff);
713 system_memory_guard(oldmode); /* re-enable memory guard */
715 lcd_clear_display();
717 lcd_puts(0, 0, "[HW Info]");
718 while(1)
720 switch(currval)
722 case 0:
723 lcd_putsf(0, 1, "ROM: %d.%02d",
724 rom_version/100, rom_version%100);
725 break;
726 case 1:
727 if (got_id)
728 lcd_putsf(0, 1, "Flash:%02x,%02x", manu, id);
729 else
730 lcd_puts(0, 1, "Flash:??,??"); /* unknown, sorry */
731 break;
732 case 2:
733 if (has_bootrom)
735 if (rom_crc == 0x56DBA4EE) /* known Version 1 */
736 lcd_puts(0, 1, "BootROM: V1");
737 else if (rom_crc == 0x358099E8)
738 lcd_puts(0, 1, "BootROM: V2");
739 /* alternative boot ROM found in one single player so far */
740 else
741 lcd_putsf(0, 1, "R: %08x", rom_crc);
743 else
744 lcd_puts(0, 1, "BootROM: no");
747 lcd_update();
749 button = get_action(CONTEXT_SETTINGS,TIMEOUT_BLOCK);
751 switch(button)
753 case ACTION_STD_CANCEL:
754 return false;
756 case ACTION_SETTINGS_DEC:
757 currval--;
758 if(currval < 0)
759 currval = 2;
760 break;
762 case ACTION_SETTINGS_INC:
763 currval++;
764 if(currval > 2)
765 currval = 0;
766 break;
769 return false;
771 #endif /* !HAVE_LCD_BITMAP */
772 #endif /* PLATFORM_NATIVE */
774 #if (CONFIG_PLATFORM & PLATFORM_NATIVE)
775 static const char* dbg_partitions_getname(int selected_item, void *data,
776 char *buffer, size_t buffer_len)
778 (void)data;
779 int partition = selected_item/2;
780 struct partinfo* p = disk_partinfo(partition);
781 if (selected_item%2)
783 snprintf(buffer, buffer_len, " T:%x %ld MB", p->type, p->size / ( 2048 / ( SECTOR_SIZE / 512 )));
785 else
787 snprintf(buffer, buffer_len, "P%d: S:%lx", partition, p->start);
789 return buffer;
792 bool dbg_partitions(void)
794 struct simplelist_info info;
795 simplelist_info_init(&info, "Partition Info", 4, NULL);
796 info.selection_size = 2;
797 info.hide_selection = true;
798 info.scroll_all = true;
799 info.get_name = dbg_partitions_getname;
800 return simplelist_show_list(&info);
802 #endif /* PLATFORM_NATIVE */
804 #if defined(CPU_COLDFIRE) && defined(HAVE_SPDIF_OUT)
805 static bool dbg_spdif(void)
807 int line;
808 unsigned int control;
809 int x;
810 char *s;
811 int category;
812 int generation;
813 unsigned int interruptstat;
814 bool valnogood, symbolerr, parityerr;
815 bool done = false;
816 bool spdif_src_on;
817 int spdif_source = spdif_get_output_source(&spdif_src_on);
818 spdif_set_output_source(AUDIO_SRC_SPDIF IF_SPDIF_POWER_(, true));
820 lcd_clear_display();
821 lcd_setfont(FONT_SYSFIXED);
823 #ifdef HAVE_SPDIF_POWER
824 spdif_power_enable(true); /* We need SPDIF power for both sending & receiving */
825 #endif
827 while (!done)
829 line = 0;
831 control = EBU1RCVCCHANNEL1;
832 interruptstat = INTERRUPTSTAT;
833 INTERRUPTCLEAR = 0x03c00000;
835 valnogood = (interruptstat & 0x01000000)?true:false;
836 symbolerr = (interruptstat & 0x00800000)?true:false;
837 parityerr = (interruptstat & 0x00400000)?true:false;
839 lcd_putsf(0, line++, "Val: %s Sym: %s Par: %s",
840 valnogood?"--":"OK",
841 symbolerr?"--":"OK",
842 parityerr?"--":"OK");
844 lcd_putsf(0, line++, "Status word: %08x", (int)control);
846 line++;
848 x = control >> 31;
849 lcd_putsf(0, line++, "PRO: %d (%s)",
850 x, x?"Professional":"Consumer");
852 x = (control >> 30) & 1;
853 lcd_putsf(0, line++, "Audio: %d (%s)",
854 x, x?"Non-PCM":"PCM");
856 x = (control >> 29) & 1;
857 lcd_putsf(0, line++, "Copy: %d (%s)",
858 x, x?"Permitted":"Inhibited");
860 x = (control >> 27) & 7;
861 switch(x)
863 case 0:
864 s = "None";
865 break;
866 case 1:
867 s = "50/15us";
868 break;
869 default:
870 s = "Reserved";
871 break;
873 lcd_putsf(0, line++, "Preemphasis: %d (%s)", x, s);
875 x = (control >> 24) & 3;
876 lcd_putsf(0, line++, "Mode: %d", x);
878 category = (control >> 17) & 127;
879 switch(category)
881 case 0x00:
882 s = "General";
883 break;
884 case 0x40:
885 s = "Audio CD";
886 break;
887 default:
888 s = "Unknown";
890 lcd_putsf(0, line++, "Category: 0x%02x (%s)", category, s);
892 x = (control >> 16) & 1;
893 generation = x;
894 if(((category & 0x70) == 0x10) ||
895 ((category & 0x70) == 0x40) ||
896 ((category & 0x78) == 0x38))
898 generation = !generation;
900 lcd_putsf(0, line++, "Generation: %d (%s)",
901 x, generation?"Original":"No ind.");
903 x = (control >> 12) & 15;
904 lcd_putsf(0, line++, "Source: %d", x);
907 x = (control >> 8) & 15;
908 switch(x)
910 case 0:
911 s = "Unspecified";
912 break;
913 case 8:
914 s = "A (Left)";
915 break;
916 case 4:
917 s = "B (Right)";
918 break;
919 default:
920 s = "";
921 break;
923 lcd_putsf(0, line++, "Channel: %d (%s)", x, s);
925 x = (control >> 4) & 15;
926 switch(x)
928 case 0:
929 s = "44.1kHz";
930 break;
931 case 0x4:
932 s = "48kHz";
933 break;
934 case 0xc:
935 s = "32kHz";
936 break;
938 lcd_putsf(0, line++, "Frequency: %d (%s)", x, s);
940 x = (control >> 2) & 3;
941 lcd_putsf(0, line++, "Clock accuracy: %d", x);
942 line++;
944 #if (CONFIG_PLATFORM & PLATFORM_NATIVE)
945 lcd_putsf(0, line++, "Measured freq: %ldHz",
946 spdif_measure_frequency());
947 #endif
949 lcd_update();
951 if (action_userabort(HZ/10))
952 break;
955 spdif_set_output_source(spdif_source IF_SPDIF_POWER_(, spdif_src_on));
957 #ifdef HAVE_SPDIF_POWER
958 spdif_power_enable(global_settings.spdif_enable);
959 #endif
961 lcd_setfont(FONT_UI);
962 return false;
964 #endif /* CPU_COLDFIRE */
966 #if (CONFIG_RTC == RTC_PCF50605) && (CONFIG_PLATFORM & PLATFORM_NATIVE)
967 static bool dbg_pcf(void)
969 int line;
971 #ifdef HAVE_LCD_BITMAP
972 lcd_setfont(FONT_SYSFIXED);
973 #endif
974 lcd_clear_display();
976 while(1)
978 line = 0;
980 lcd_putsf(0, line++, "DCDC1: %02x", pcf50605_read(0x1b));
981 lcd_putsf(0, line++, "DCDC2: %02x", pcf50605_read(0x1c));
982 lcd_putsf(0, line++, "DCDC3: %02x", pcf50605_read(0x1d));
983 lcd_putsf(0, line++, "DCDC4: %02x", pcf50605_read(0x1e));
984 lcd_putsf(0, line++, "DCDEC1: %02x", pcf50605_read(0x1f));
985 lcd_putsf(0, line++, "DCDEC2: %02x", pcf50605_read(0x20));
986 lcd_putsf(0, line++, "DCUDC1: %02x", pcf50605_read(0x21));
987 lcd_putsf(0, line++, "DCUDC2: %02x", pcf50605_read(0x22));
988 lcd_putsf(0, line++, "IOREGC: %02x", pcf50605_read(0x23));
989 lcd_putsf(0, line++, "D1REGC: %02x", pcf50605_read(0x24));
990 lcd_putsf(0, line++, "D2REGC: %02x", pcf50605_read(0x25));
991 lcd_putsf(0, line++, "D3REGC: %02x", pcf50605_read(0x26));
992 lcd_putsf(0, line++, "LPREG1: %02x", pcf50605_read(0x27));
993 lcd_update();
994 if (button_get_w_tmo(HZ/10) == (DEBUG_CANCEL|BUTTON_REL))
996 lcd_setfont(FONT_UI);
997 return false;
1001 lcd_setfont(FONT_UI);
1002 return false;
1004 #endif
1006 #ifdef HAVE_ADJUSTABLE_CPU_FREQ
1007 static bool dbg_cpufreq(void)
1009 int line;
1010 int button;
1012 #ifdef HAVE_LCD_BITMAP
1013 lcd_setfont(FONT_SYSFIXED);
1014 #endif
1015 lcd_clear_display();
1017 while(1)
1019 line = 0;
1021 lcd_putsf(0, line++, "Frequency: %ld", FREQ);
1022 lcd_putsf(0, line++, "boost_counter: %d", get_cpu_boost_counter());
1024 lcd_update();
1025 button = get_action(CONTEXT_STD,HZ/10);
1027 switch(button)
1029 case ACTION_STD_PREV:
1030 cpu_boost(true);
1031 break;
1033 case ACTION_STD_NEXT:
1034 cpu_boost(false);
1035 break;
1037 case ACTION_STD_OK:
1038 while (get_cpu_boost_counter() > 0)
1039 cpu_boost(false);
1040 set_cpu_frequency(CPUFREQ_DEFAULT);
1041 break;
1043 case ACTION_STD_CANCEL:
1044 lcd_setfont(FONT_UI);
1045 return false;
1048 lcd_setfont(FONT_UI);
1049 return false;
1051 #endif /* HAVE_ADJUSTABLE_CPU_FREQ */
1053 #if defined(HAVE_TSC2100) && (CONFIG_PLATFORM & PLATFORM_NATIVE)
1054 #include "tsc2100.h"
1055 static char *itob(int n, int len)
1057 static char binary[64];
1058 int i,j;
1059 for (i=1, j=0;i<=len;i++)
1061 binary[j++] = n&(1<<(len-i))?'1':'0';
1062 if (i%4 == 0)
1063 binary[j++] = ' ';
1065 binary[j] = '\0';
1066 return binary;
1069 static const char* tsc2100_debug_getname(int selected_item, void * data,
1070 char *buffer, size_t buffer_len)
1072 int *page = (int*)data;
1073 bool reserved = false;
1074 switch (*page)
1076 case 0:
1077 if ((selected_item > 0x0a) ||
1078 (selected_item == 0x04) ||
1079 (selected_item == 0x08))
1080 reserved = true;
1081 break;
1082 case 1:
1083 if ((selected_item > 0x05) ||
1084 (selected_item == 0x02))
1085 reserved = true;
1086 break;
1087 case 2:
1088 if (selected_item > 0x1e)
1089 reserved = true;
1090 break;
1092 if (reserved)
1093 snprintf(buffer, buffer_len, "%02x: RESERVED", selected_item);
1094 else
1095 snprintf(buffer, buffer_len, "%02x: %s", selected_item,
1096 itob(tsc2100_readreg(*page, selected_item)&0xffff,16));
1097 return buffer;
1099 static int tsc2100debug_action_callback(int action, struct gui_synclist *lists)
1101 int *page = (int*)lists->data;
1102 if (action == ACTION_STD_OK)
1104 *page = (*page+1)%3;
1105 snprintf(lists->title, 32,
1106 "tsc2100 registers - Page %d", *page);
1107 return ACTION_REDRAW;
1109 return action;
1111 static bool tsc2100_debug(void)
1113 int page = 0;
1114 char title[32] = "tsc2100 registers - Page 0";
1115 struct simplelist_info info;
1116 simplelist_info_init(&info, title, 32, &page);
1117 info.timeout = HZ/100;
1118 info.get_name = tsc2100_debug_getname;
1119 info.action_callback= tsc2100debug_action_callback;
1120 return simplelist_show_list(&info);
1122 #endif
1123 #if (CONFIG_PLATFORM & PLATFORM_NATIVE)
1124 #ifdef HAVE_LCD_BITMAP
1126 * view_battery() shows a automatically scaled graph of the battery voltage
1127 * over time. Usable for estimating battery life / charging rate.
1128 * The power_history array is updated in power_thread of powermgmt.c.
1131 #define BAT_LAST_VAL MIN(LCD_WIDTH, POWER_HISTORY_LEN)
1132 #define BAT_YSPACE (LCD_HEIGHT - 20)
1135 static bool view_battery(void)
1137 int view = 0;
1138 int i, x, y, y1, y2, grid, graph;
1139 unsigned short maxv, minv;
1141 lcd_setfont(FONT_SYSFIXED);
1143 while(1)
1145 lcd_clear_display();
1146 switch (view) {
1147 case 0: /* voltage history graph */
1148 /* Find maximum and minimum voltage for scaling */
1149 minv = power_history[0];
1150 maxv = minv + 1;
1151 for (i = 1; i < BAT_LAST_VAL && power_history[i]; i++) {
1152 if (power_history[i] > maxv)
1153 maxv = power_history[i];
1154 if (power_history[i] < minv)
1155 minv = power_history[i];
1158 /* adjust grid scale */
1159 if ((maxv - minv) > 50)
1160 grid = 50;
1161 else
1162 grid = 5;
1164 /* print header */
1165 lcd_putsf(0, 0, "battery %d.%03dV", power_history[0] / 1000,
1166 power_history[0] % 1000);
1167 lcd_putsf(0, 1, "%d.%03d-%d.%03dV (%2dmV)",
1168 minv / 1000, minv % 1000, maxv / 1000, maxv % 1000,
1169 grid);
1171 i = 1;
1172 while ((y = (minv - (minv % grid)+i*grid)) < maxv)
1174 graph = ((y-minv)*BAT_YSPACE)/(maxv-minv);
1175 graph = LCD_HEIGHT-1 - graph;
1177 /* draw dotted horizontal grid line */
1178 for (x=0; x<LCD_WIDTH;x=x+2)
1179 lcd_drawpixel(x,graph);
1181 i++;
1184 x = 0;
1185 /* draw plot of power history
1186 * skip empty entries
1188 for (i = BAT_LAST_VAL - 1; i > 0; i--)
1190 if (power_history[i] && power_history[i-1])
1192 y1 = (power_history[i] - minv) * BAT_YSPACE /
1193 (maxv - minv);
1194 y1 = MIN(MAX(LCD_HEIGHT-1 - y1, 20),
1195 LCD_HEIGHT-1);
1196 y2 = (power_history[i-1] - minv) * BAT_YSPACE /
1197 (maxv - minv);
1198 y2 = MIN(MAX(LCD_HEIGHT-1 - y2, 20),
1199 LCD_HEIGHT-1);
1201 lcd_set_drawmode(DRMODE_SOLID);
1203 /* make line thicker */
1204 lcd_drawline(((x*LCD_WIDTH)/(BAT_LAST_VAL)),
1205 y1,
1206 (((x+1)*LCD_WIDTH)/(BAT_LAST_VAL)),
1207 y2);
1208 lcd_drawline(((x*LCD_WIDTH)/(BAT_LAST_VAL))+1,
1209 y1+1,
1210 (((x+1)*LCD_WIDTH)/(BAT_LAST_VAL))+1,
1211 y2+1);
1212 x++;
1215 break;
1217 case 1: /* status: */
1218 #if CONFIG_CHARGING >= CHARGING_MONITOR
1219 lcd_putsf(0, 0, "Pwr status: %s",
1220 charging_state() ? "charging" : "discharging");
1221 #else
1222 lcd_puts(0, 0, "Power status:");
1223 #endif
1224 battery_read_info(&y, NULL);
1225 lcd_putsf(0, 1, "Battery: %d.%03d V", y / 1000, y % 1000);
1226 #ifdef ADC_EXT_POWER
1227 y = (adc_read(ADC_EXT_POWER) * EXT_SCALE_FACTOR) / 1000;
1228 lcd_putsf(0, 2, "External: %d.%03d V", y / 1000, y % 1000);
1229 #endif
1230 #if CONFIG_CHARGING
1231 #if defined ARCHOS_RECORDER
1232 lcd_putsf(0, 3, "Chgr: %s %s",
1233 charger_inserted() ? "present" : "absent",
1234 charger_enabled() ? "on" : "off");
1235 lcd_putsf(0, 5, "short delta: %d", short_delta);
1236 lcd_putsf(0, 6, "long delta: %d", long_delta);
1237 lcd_puts(0, 7, power_message);
1238 lcd_putsf(0, 8, "USB Inserted: %s",
1239 usb_inserted() ? "yes" : "no");
1240 #elif defined IPOD_NANO || defined IPOD_VIDEO
1241 int usb_pwr = (GPIOL_INPUT_VAL & 0x10)?true:false;
1242 int ext_pwr = (GPIOL_INPUT_VAL & 0x08)?false:true;
1243 int dock = (GPIOA_INPUT_VAL & 0x10)?true:false;
1244 int charging = (GPIOB_INPUT_VAL & 0x01)?false:true;
1245 int headphone= (GPIOA_INPUT_VAL & 0x80)?true:false;
1247 lcd_putsf(0, 3, "USB pwr: %s",
1248 usb_pwr ? "present" : "absent");
1249 lcd_putsf(0, 4, "EXT pwr: %s",
1250 ext_pwr ? "present" : "absent");
1251 lcd_putsf(0, 5, "Battery: %s",
1252 charging ? "charging" : (usb_pwr||ext_pwr) ? "charged" : "discharging");
1253 lcd_putsf(0, 6, "Dock mode: %s",
1254 dock ? "enabled" : "disabled");
1255 lcd_putsf(0, 7, "Headphone: %s",
1256 headphone ? "connected" : "disconnected");
1257 #ifdef IPOD_VIDEO
1258 if(probed_ramsize == 64)
1259 x = (adc_read(ADC_4066_ISTAT) * 2400) / (1024 * 2);
1260 else
1261 x = (adc_read(ADC_4066_ISTAT) * 2400) / (1024 * 3);
1262 lcd_putsf(0, 8, "Ibat: %d mA", x);
1263 lcd_putsf(0, 9, "Vbat * Ibat: %d mW", x * y / 1000);
1264 #endif
1265 #elif defined TOSHIBA_GIGABEAT_S
1266 int line = 3;
1267 unsigned int st;
1269 static const unsigned char * const chrgstate_strings[] =
1271 "Disabled",
1272 "Error",
1273 "Discharging",
1274 "Precharge",
1275 "Constant Voltage",
1276 "Constant Current",
1277 "<unknown>",
1280 lcd_putsf(0, line++, "Charger: %s",
1281 charger_inserted() ? "present" : "absent");
1283 st = power_input_status() &
1284 (POWER_INPUT_CHARGER | POWER_INPUT_BATTERY);
1285 lcd_putsf(0, line++, "%s%s",
1286 (st & POWER_INPUT_MAIN_CHARGER) ? " Main" : "",
1287 (st & POWER_INPUT_USB_CHARGER) ? " USB" : "");
1289 y = ARRAYLEN(chrgstate_strings) - 1;
1291 switch (charge_state)
1293 case CHARGE_STATE_DISABLED: y--;
1294 case CHARGE_STATE_ERROR: y--;
1295 case DISCHARGING: y--;
1296 case TRICKLE: y--;
1297 case TOPOFF: y--;
1298 case CHARGING: y--;
1299 default:;
1302 lcd_putsf(0, line++, "State: %s", chrgstate_strings[y]);
1304 lcd_putsf(0, line++, "Battery Switch: %s",
1305 (st & POWER_INPUT_BATTERY) ? "On" : "Off");
1307 y = chrgraw_adc_voltage();
1308 lcd_putsf(0, line++, "CHRGRAW: %d.%03d V",
1309 y / 1000, y % 1000);
1311 y = application_supply_adc_voltage();
1312 lcd_putsf(0, line++, "BP : %d.%03d V",
1313 y / 1000, y % 1000);
1315 y = battery_adc_charge_current();
1316 if (y < 0) x = '-', y = -y;
1317 else x = ' ';
1318 lcd_putsf(0, line++, "CHRGISN:%c%d mA", x, y);
1320 y = cccv_regulator_dissipation();
1321 lcd_putsf(0, line++, "P CCCV : %d mW", y);
1323 y = battery_charge_current();
1324 if (y < 0) x = '-', y = -y;
1325 else x = ' ';
1326 lcd_putsf(0, line++, "I Charge:%c%d mA", x, y);
1328 y = battery_adc_temp();
1330 if (y != INT_MIN) {
1331 lcd_putsf(0, line++, "T Battery: %dC (%dF)", y,
1332 (9*y + 160) / 5);
1333 } else {
1334 /* Conversion disabled */
1335 lcd_puts(0, line++, "T Battery: ?");
1338 #elif defined(SANSA_E200) || defined(SANSA_C200) || CONFIG_CPU == AS3525 || \
1339 CONFIG_CPU == AS3525v2
1340 static const char * const chrgstate_strings[] =
1342 [CHARGE_STATE_DISABLED - CHARGE_STATE_DISABLED]= "Disabled",
1343 [CHARGE_STATE_ERROR - CHARGE_STATE_DISABLED] = "Error",
1344 [DISCHARGING - CHARGE_STATE_DISABLED] = "Discharging",
1345 [CHARGING - CHARGE_STATE_DISABLED] = "Charging",
1347 const char *str = NULL;
1349 lcd_putsf(0, 3, "Charger: %s",
1350 charger_inserted() ? "present" : "absent");
1352 y = charge_state - CHARGE_STATE_DISABLED;
1353 if ((unsigned)y < ARRAYLEN(chrgstate_strings))
1354 str = chrgstate_strings[y];
1356 lcd_putsf(0, 4, "State: %s",
1357 str ? str : "<unknown>");
1359 lcd_putsf(0, 5, "CHARGER: %02X", ascodec_read_charger());
1360 #elif defined(IPOD_NANO2G)
1361 y = pmu_read_battery_voltage();
1362 lcd_putsf(17, 1, "RAW: %d.%03d V", y / 1000, y % 1000);
1363 y = pmu_read_battery_current();
1364 lcd_putsf(0, 2, "Battery current: %d mA", y);
1365 lcd_putsf(0, 3, "PWRCON: %08x %08x", PWRCON, PWRCONEXT);
1366 lcd_putsf(0, 4, "CLKCON: %08x %03x %03x", CLKCON, CLKCON2, CLKCON3);
1367 lcd_putsf(0, 5, "PLL: %06x %06x %06x", PLL0PMS, PLL1PMS, PLL2PMS);
1368 x = pmu_read(0x1b) & 0xf;
1369 y = pmu_read(0x1a) * 25 + 625;
1370 lcd_putsf(0, 6, "AUTO: %x / %d mV", x, y);
1371 x = pmu_read(0x1f) & 0xf;
1372 y = pmu_read(0x1e) * 25 + 625;
1373 lcd_putsf(0, 7, "DOWN1: %x / %d mV", x, y);
1374 x = pmu_read(0x23) & 0xf;
1375 y = pmu_read(0x22) * 25 + 625;
1376 lcd_putsf(0, 8, "DOWN2: %x / %d mV", x, y);
1377 x = pmu_read(0x27) & 0xf;
1378 y = pmu_read(0x26) * 100 + 900;
1379 lcd_putsf(0, 9, "MEMLDO: %x / %d mV", x, y);
1380 for (i = 0; i < 6; i++)
1382 x = pmu_read(0x2e + (i << 1)) & 0xf;
1383 y = pmu_read(0x2d + (i << 1)) * 100 + 900;
1384 lcd_putsf(0, 10 + i, "LDO%d: %x / %d mV", i + 1, x, y);
1386 #else
1387 lcd_putsf(0, 3, "Charger: %s",
1388 charger_inserted() ? "present" : "absent");
1389 #endif /* target type */
1390 #endif /* CONFIG_CHARGING */
1391 break;
1393 case 2: /* voltage deltas: */
1394 lcd_puts(0, 0, "Voltage deltas:");
1396 for (i = 0; i <= 6; i++) {
1397 y = power_history[i] - power_history[i+1];
1398 lcd_putsf(0, i+1, "-%d min: %s%d.%03d V", i,
1399 (y < 0) ? "-" : "", ((y < 0) ? y * -1 : y) / 1000,
1400 ((y < 0) ? y * -1 : y ) % 1000);
1402 break;
1404 case 3: /* remaining time estimation: */
1406 #ifdef ARCHOS_RECORDER
1407 lcd_putsf(0, 0, "charge_state: %d", charge_state);
1409 lcd_putsf(0, 1, "Cycle time: %d m", powermgmt_last_cycle_startstop_min);
1411 lcd_putsf(0, 2, "Lvl@cyc st: %d%%", powermgmt_last_cycle_level);
1413 lcd_putsf(0, 3, "P=%2d I=%2d", pid_p, pid_i);
1415 lcd_putsf(0, 4, "Trickle sec: %d/60", trickle_sec);
1416 #endif /* ARCHOS_RECORDER */
1418 lcd_putsf(0, 5, "Last PwrHist: %d.%03dV",
1419 power_history[0] / 1000,
1420 power_history[0] % 1000);
1422 lcd_putsf(0, 6, "battery level: %d%%", battery_level());
1424 lcd_putsf(0, 7, "Est. remain: %d m", battery_time());
1425 break;
1428 lcd_update();
1430 switch(get_action(CONTEXT_STD,HZ/2))
1432 case ACTION_STD_PREV:
1433 if (view)
1434 view--;
1435 break;
1437 case ACTION_STD_NEXT:
1438 if (view < 3)
1439 view++;
1440 break;
1442 case ACTION_STD_CANCEL:
1443 lcd_setfont(FONT_UI);
1444 return false;
1447 lcd_setfont(FONT_UI);
1448 return false;
1451 #endif /* HAVE_LCD_BITMAP */
1452 #endif
1454 #if (CONFIG_PLATFORM & PLATFORM_NATIVE)
1455 #if (CONFIG_STORAGE & STORAGE_MMC) || (CONFIG_STORAGE & STORAGE_SD)
1457 #if (CONFIG_STORAGE & STORAGE_MMC)
1458 #define CARDTYPE "MMC"
1459 #elif (CONFIG_STORAGE & STORAGE_SD)
1460 #define CARDTYPE "microSD"
1461 #endif
1463 static int disk_callback(int btn, struct gui_synclist *lists)
1465 tCardInfo *card;
1466 int *cardnum = (int*)lists->data;
1467 unsigned char card_name[6];
1468 unsigned char pbuf[32];
1469 char *title = lists->title;
1470 static const unsigned char i_vmin[] = { 0, 1, 5, 10, 25, 35, 60, 100 };
1471 static const unsigned char i_vmax[] = { 1, 5, 10, 25, 35, 45, 80, 200 };
1472 static const unsigned char * const kbit_units[] = { "kBit/s", "MBit/s", "GBit/s" };
1473 static const unsigned char * const nsec_units[] = { "ns", "µs", "ms" };
1474 #if (CONFIG_STORAGE & STORAGE_MMC)
1475 static const char * const mmc_spec_vers[] = { "1.0-1.2", "1.4", "2.0-2.2",
1476 "3.1-3.31", "4.0" };
1477 #endif
1479 if ((btn == ACTION_STD_OK) || (btn == SYS_FS_CHANGED) || (btn == ACTION_REDRAW))
1481 #ifdef HAVE_HOTSWAP
1482 if (btn == ACTION_STD_OK)
1484 *cardnum ^= 0x1; /* change cards */
1486 #endif
1488 simplelist_set_line_count(0);
1490 card = card_get_info(*cardnum);
1492 if (card->initialized > 0)
1494 unsigned i;
1495 for (i=0; i<sizeof(card_name); i++)
1497 card_name[i] = card_extract_bits(card->cid, (103-8*i), 8);
1499 strlcpy(card_name, card_name, sizeof(card_name));
1500 simplelist_addline(SIMPLELIST_ADD_LINE,
1501 "%s Rev %d.%d", card_name,
1502 (int) card_extract_bits(card->cid, 63, 4),
1503 (int) card_extract_bits(card->cid, 59, 4));
1504 simplelist_addline(SIMPLELIST_ADD_LINE,
1505 "Prod: %d/%d",
1506 #if (CONFIG_STORAGE & STORAGE_SD)
1507 (int) card_extract_bits(card->cid, 11, 4),
1508 (int) card_extract_bits(card->cid, 19, 8) + 2000
1509 #elif (CONFIG_STORAGE & STORAGE_MMC)
1510 (int) card_extract_bits(card->cid, 15, 4),
1511 (int) card_extract_bits(card->cid, 11, 4) + 1997
1512 #endif
1514 simplelist_addline(SIMPLELIST_ADD_LINE,
1515 #if (CONFIG_STORAGE & STORAGE_SD)
1516 "Ser#: 0x%08lx",
1517 card_extract_bits(card->cid, 55, 32)
1518 #elif (CONFIG_STORAGE & STORAGE_MMC)
1519 "Ser#: 0x%04lx",
1520 card_extract_bits(card->cid, 47, 16)
1521 #endif
1524 simplelist_addline(SIMPLELIST_ADD_LINE, "M=%02x, "
1525 #if (CONFIG_STORAGE & STORAGE_SD)
1526 "O=%c%c",
1527 (int) card_extract_bits(card->cid, 127, 8),
1528 card_extract_bits(card->cid, 119, 8),
1529 card_extract_bits(card->cid, 111, 8)
1530 #elif (CONFIG_STORAGE & STORAGE_MMC)
1531 "O=%04x",
1532 (int) card_extract_bits(card->cid, 127, 8),
1533 (int) card_extract_bits(card->cid, 119, 16)
1534 #endif
1537 #if (CONFIG_STORAGE & STORAGE_MMC)
1538 int temp = card_extract_bits(card->csd, 125, 4);
1539 simplelist_addline(SIMPLELIST_ADD_LINE,
1540 "MMC v%s", temp < 5 ?
1541 mmc_spec_vers[temp] : "?.?");
1542 #endif
1543 simplelist_addline(SIMPLELIST_ADD_LINE,
1544 "Blocks: 0x%08lx", card->numblocks);
1545 output_dyn_value(pbuf, sizeof pbuf, card->speed / 1000,
1546 kbit_units, false);
1547 simplelist_addline(SIMPLELIST_ADD_LINE,
1548 "Speed: %s", pbuf);
1549 output_dyn_value(pbuf, sizeof pbuf, card->taac,
1550 nsec_units, false);
1551 simplelist_addline(SIMPLELIST_ADD_LINE,
1552 "Taac: %s", pbuf);
1553 simplelist_addline(SIMPLELIST_ADD_LINE,
1554 "Nsac: %d clk", card->nsac);
1555 simplelist_addline(SIMPLELIST_ADD_LINE,
1556 "R2W: *%d", card->r2w_factor);
1557 simplelist_addline(SIMPLELIST_ADD_LINE,
1558 "IRmax: %d..%d mA",
1559 i_vmin[card_extract_bits(card->csd, 61, 3)],
1560 i_vmax[card_extract_bits(card->csd, 58, 3)]);
1561 simplelist_addline(SIMPLELIST_ADD_LINE,
1562 "IWmax: %d..%d mA",
1563 i_vmin[card_extract_bits(card->csd, 55, 3)],
1564 i_vmax[card_extract_bits(card->csd, 52, 3)]);
1566 else if (card->initialized == 0)
1568 simplelist_addline(SIMPLELIST_ADD_LINE, "Not Found!");
1570 #if (CONFIG_STORAGE & STORAGE_SD)
1571 else /* card->initialized < 0 */
1573 simplelist_addline(SIMPLELIST_ADD_LINE, "Init Error! (%d)", card->initialized);
1575 #endif
1576 snprintf(title, 16, "[" CARDTYPE " %d]", *cardnum);
1577 gui_synclist_set_title(lists, title, Icon_NOICON);
1578 gui_synclist_set_nb_items(lists, simplelist_get_line_count());
1579 gui_synclist_select_item(lists, 0);
1580 btn = ACTION_REDRAW;
1582 return btn;
1584 #elif (CONFIG_STORAGE & STORAGE_ATA)
1585 static int disk_callback(int btn, struct gui_synclist *lists)
1587 (void)lists;
1588 int i;
1589 char buf[128];
1590 unsigned short* identify_info = ata_get_identify();
1591 bool timing_info_present = false;
1592 (void)btn;
1594 simplelist_set_line_count(0);
1596 for (i=0; i < 20; i++)
1597 ((unsigned short*)buf)[i]=htobe16(identify_info[i+27]);
1598 buf[40]=0;
1599 /* kill trailing space */
1600 for (i=39; i && buf[i]==' '; i--)
1601 buf[i] = 0;
1602 simplelist_addline(SIMPLELIST_ADD_LINE, "Model: %s", buf);
1603 for (i=0; i < 4; i++)
1604 ((unsigned short*)buf)[i]=htobe16(identify_info[i+23]);
1605 buf[8]=0;
1606 simplelist_addline(SIMPLELIST_ADD_LINE,
1607 "Firmware: %s", buf);
1608 snprintf(buf, sizeof buf, "%ld MB",
1609 ((unsigned long)identify_info[61] << 16 |
1610 (unsigned long)identify_info[60]) / 2048 );
1611 simplelist_addline(SIMPLELIST_ADD_LINE,
1612 "Size: %s", buf);
1613 unsigned long free;
1614 fat_size( IF_MV2(0,) NULL, &free );
1615 simplelist_addline(SIMPLELIST_ADD_LINE,
1616 "Free: %ld MB", free / 1024);
1617 simplelist_addline(SIMPLELIST_ADD_LINE,
1618 "Spinup time: %d ms", storage_spinup_time() * (1000/HZ));
1619 i = identify_info[83] & (1<<3);
1620 simplelist_addline(SIMPLELIST_ADD_LINE,
1621 "Power mgmt: %s", i ? "enabled" : "unsupported");
1622 i = identify_info[83] & (1<<9);
1623 simplelist_addline(SIMPLELIST_ADD_LINE,
1624 "Noise mgmt: %s", i ? "enabled" : "unsupported");
1625 i = identify_info[82] & (1<<6);
1626 simplelist_addline(SIMPLELIST_ADD_LINE,
1627 "Read-ahead: %s", i ? "enabled" : "unsupported");
1628 timing_info_present = identify_info[53] & (1<<1);
1629 if(timing_info_present) {
1630 char pio3[2], pio4[2];pio3[1] = 0;
1631 pio4[1] = 0;
1632 pio3[0] = (identify_info[64] & (1<<0)) ? '3' : 0;
1633 pio4[0] = (identify_info[64] & (1<<1)) ? '4' : 0;
1634 simplelist_addline(SIMPLELIST_ADD_LINE,
1635 "PIO modes: 0 1 2 %s %s", pio3, pio4);
1637 else {
1638 simplelist_addline(SIMPLELIST_ADD_LINE,
1639 "No PIO mode info");
1641 timing_info_present = identify_info[53] & (1<<1);
1642 if(timing_info_present) {
1643 simplelist_addline(SIMPLELIST_ADD_LINE,
1644 "Cycle times %dns/%dns",
1645 identify_info[67],
1646 identify_info[68] );
1647 } else {
1648 simplelist_addline(SIMPLELIST_ADD_LINE,
1649 "No timing info");
1651 int sector_size = 512;
1652 if((identify_info[106] & 0xe000) == 0x6000)
1653 sector_size *= BIT_N(identify_info[106] & 0x000f);
1654 simplelist_addline(SIMPLELIST_ADD_LINE,
1655 "Physical sector size: %d", sector_size);
1656 #ifdef HAVE_ATA_DMA
1657 if (identify_info[63] & (1<<0)) {
1658 char mdma0[2], mdma1[2], mdma2[2];
1659 mdma0[1] = mdma1[1] = mdma2[1] = 0;
1660 mdma0[0] = (identify_info[63] & (1<<0)) ? '0' : 0;
1661 mdma1[0] = (identify_info[63] & (1<<1)) ? '1' : 0;
1662 mdma2[0] = (identify_info[63] & (1<<2)) ? '2' : 0;
1663 simplelist_addline(SIMPLELIST_ADD_LINE,
1664 "MDMA modes: %s %s %s", mdma0, mdma1, mdma2);
1665 simplelist_addline(SIMPLELIST_ADD_LINE,
1666 "MDMA Cycle times %dns/%dns",
1667 identify_info[65],
1668 identify_info[66] );
1670 else {
1671 simplelist_addline(SIMPLELIST_ADD_LINE,
1672 "No MDMA mode info");
1674 if (identify_info[53] & (1<<2)) {
1675 char udma0[2], udma1[2], udma2[2], udma3[2], udma4[2], udma5[2], udma6[2];
1676 udma0[1] = udma1[1] = udma2[1] = udma3[1] = udma4[1] = udma5[1] = udma6[1] = 0;
1677 udma0[0] = (identify_info[88] & (1<<0)) ? '0' : 0;
1678 udma1[0] = (identify_info[88] & (1<<1)) ? '1' : 0;
1679 udma2[0] = (identify_info[88] & (1<<2)) ? '2' : 0;
1680 udma3[0] = (identify_info[88] & (1<<3)) ? '3' : 0;
1681 udma4[0] = (identify_info[88] & (1<<4)) ? '4' : 0;
1682 udma5[0] = (identify_info[88] & (1<<5)) ? '5' : 0;
1683 udma6[0] = (identify_info[88] & (1<<6)) ? '6' : 0;
1684 simplelist_addline(SIMPLELIST_ADD_LINE,
1685 "UDMA modes: %s %s %s %s %s %s %s", udma0, udma1, udma2,
1686 udma3, udma4, udma5, udma6);
1688 else {
1689 simplelist_addline(SIMPLELIST_ADD_LINE,
1690 "No UDMA mode info");
1692 #endif /* HAVE_ATA_DMA */
1693 timing_info_present = identify_info[53] & (1<<1);
1694 if(timing_info_present) {
1695 i = identify_info[49] & (1<<11);
1696 simplelist_addline(SIMPLELIST_ADD_LINE,
1697 "IORDY support: %s", i ? "yes" : "no");
1698 i = identify_info[49] & (1<<10);
1699 simplelist_addline(SIMPLELIST_ADD_LINE,
1700 "IORDY disable: %s", i ? "yes" : "no");
1701 } else {
1702 simplelist_addline(SIMPLELIST_ADD_LINE,
1703 "No timing info");
1705 simplelist_addline(SIMPLELIST_ADD_LINE,
1706 "Cluster size: %d bytes", fat_get_cluster_size(IF_MV(0)));
1707 #ifdef HAVE_ATA_DMA
1708 i = ata_get_dma_mode();
1709 if (i == 0) {
1710 simplelist_addline(SIMPLELIST_ADD_LINE,
1711 "DMA not enabled");
1712 } else {
1713 simplelist_addline(SIMPLELIST_ADD_LINE,
1714 "DMA mode: %s %c",
1715 (i & 0x40) ? "UDMA" : "MDMA",
1716 '0' + (i & 7));
1718 #endif /* HAVE_ATA_DMA */
1719 return btn;
1721 #else /* No SD, MMC or ATA */
1722 static int disk_callback(int btn, struct gui_synclist *lists)
1724 (void)btn;
1725 (void)lists;
1726 struct storage_info info;
1727 storage_get_info(0,&info);
1728 simplelist_addline(SIMPLELIST_ADD_LINE, "Vendor: %s", info.vendor);
1729 simplelist_addline(SIMPLELIST_ADD_LINE, "Model: %s", info.product);
1730 simplelist_addline(SIMPLELIST_ADD_LINE, "Firmware: %s", info.revision);
1731 simplelist_addline(SIMPLELIST_ADD_LINE,
1732 "Size: %ld MB", info.num_sectors*(info.sector_size/512)/2024);
1733 unsigned long free;
1734 fat_size( IF_MV2(0,) NULL, &free );
1735 simplelist_addline(SIMPLELIST_ADD_LINE,
1736 "Free: %ld MB", free / 1024);
1737 simplelist_addline(SIMPLELIST_ADD_LINE,
1738 "Cluster size: %d bytes", fat_get_cluster_size(IF_MV(0)));
1739 return btn;
1741 #endif
1743 #if (CONFIG_STORAGE & STORAGE_ATA)
1744 static bool dbg_identify_info(void)
1746 int fd = creat("/identify_info.bin", 0666);
1747 if(fd >= 0)
1749 #ifdef ROCKBOX_LITTLE_ENDIAN
1750 ecwrite(fd, ata_get_identify(), SECTOR_SIZE/2, "s", true);
1751 #else
1752 write(fd, ata_get_identify(), SECTOR_SIZE);
1753 #endif
1754 close(fd);
1756 return false;
1758 #endif
1760 static bool dbg_disk_info(void)
1762 struct simplelist_info info;
1763 simplelist_info_init(&info, "Disk Info", 1, NULL);
1764 #if (CONFIG_STORAGE & STORAGE_MMC) || (CONFIG_STORAGE & STORAGE_SD)
1765 char title[16];
1766 int card = 0;
1767 info.callback_data = (void*)&card;
1768 info.title = title;
1769 #endif
1770 info.action_callback = disk_callback;
1771 info.hide_selection = true;
1772 info.scroll_all = true;
1773 return simplelist_show_list(&info);
1775 #endif /* PLATFORM_NATIVE */
1777 #ifdef HAVE_DIRCACHE
1778 static int dircache_callback(int btn, struct gui_synclist *lists)
1780 (void)btn; (void)lists;
1781 simplelist_set_line_count(0);
1782 simplelist_addline(SIMPLELIST_ADD_LINE, "Cache initialized: %s",
1783 dircache_is_enabled() ? "Yes" : "No");
1784 simplelist_addline(SIMPLELIST_ADD_LINE, "Cache size: %d B",
1785 dircache_get_cache_size());
1786 simplelist_addline(SIMPLELIST_ADD_LINE, "Last size: %d B",
1787 global_status.dircache_size);
1788 simplelist_addline(SIMPLELIST_ADD_LINE, "Limit: %d B",
1789 DIRCACHE_LIMIT);
1790 simplelist_addline(SIMPLELIST_ADD_LINE, "Reserve: %d/%d B",
1791 dircache_get_reserve_used(), DIRCACHE_RESERVE);
1792 simplelist_addline(SIMPLELIST_ADD_LINE, "Scanning took: %d s",
1793 dircache_get_build_ticks() / HZ);
1794 simplelist_addline(SIMPLELIST_ADD_LINE, "Entry count: %d",
1795 dircache_get_entry_count());
1796 return btn;
1799 static bool dbg_dircache_info(void)
1801 struct simplelist_info info;
1802 simplelist_info_init(&info, "Dircache Info", 7, NULL);
1803 info.action_callback = dircache_callback;
1804 info.hide_selection = true;
1805 info.scroll_all = true;
1806 return simplelist_show_list(&info);
1809 #endif /* HAVE_DIRCACHE */
1811 #ifdef HAVE_TAGCACHE
1812 static int database_callback(int btn, struct gui_synclist *lists)
1814 (void)lists;
1815 struct tagcache_stat *stat = tagcache_get_stat();
1816 static bool synced = false;
1818 simplelist_set_line_count(0);
1820 simplelist_addline(SIMPLELIST_ADD_LINE, "Initialized: %s",
1821 stat->initialized ? "Yes" : "No");
1822 simplelist_addline(SIMPLELIST_ADD_LINE, "DB Ready: %s",
1823 stat->ready ? "Yes" : "No");
1824 simplelist_addline(SIMPLELIST_ADD_LINE, "RAM Cache: %s",
1825 stat->ramcache ? "Yes" : "No");
1826 simplelist_addline(SIMPLELIST_ADD_LINE, "RAM: %d/%d B",
1827 stat->ramcache_used, stat->ramcache_allocated);
1828 simplelist_addline(SIMPLELIST_ADD_LINE, "Progress: %d%% (%d entries)",
1829 stat->progress, stat->processed_entries);
1830 simplelist_addline(SIMPLELIST_ADD_LINE, "Curfile: %s",
1831 stat->curentry ? stat->curentry : "---");
1832 simplelist_addline(SIMPLELIST_ADD_LINE, "Commit step: %d",
1833 stat->commit_step);
1834 simplelist_addline(SIMPLELIST_ADD_LINE, "Commit delayed: %s",
1835 stat->commit_delayed ? "Yes" : "No");
1837 simplelist_addline(SIMPLELIST_ADD_LINE, "Queue length: %d",
1838 stat->queue_length);
1840 if (synced)
1842 synced = false;
1843 tagcache_screensync_event();
1846 if (!btn && stat->curentry)
1848 synced = true;
1849 return ACTION_REDRAW;
1852 if (btn == ACTION_STD_CANCEL)
1853 tagcache_screensync_enable(false);
1855 return btn;
1857 static bool dbg_tagcache_info(void)
1859 struct simplelist_info info;
1860 simplelist_info_init(&info, "Database Info", 8, NULL);
1861 info.action_callback = database_callback;
1862 info.hide_selection = true;
1863 info.scroll_all = true;
1865 /* Don't do nonblock here, must give enough processing time
1866 for tagcache thread. */
1867 /* info.timeout = TIMEOUT_NOBLOCK; */
1868 info.timeout = 1;
1869 tagcache_screensync_enable(true);
1870 return simplelist_show_list(&info);
1872 #endif
1874 #if CONFIG_CPU == SH7034
1875 static bool dbg_save_roms(void)
1877 int fd;
1878 int oldmode = system_memory_guard(MEMGUARD_NONE);
1880 fd = creat("/internal_rom_0000-FFFF.bin", 0666);
1881 if(fd >= 0)
1883 write(fd, (void *)0, 0x10000);
1884 close(fd);
1887 fd = creat("/internal_rom_2000000-203FFFF.bin", 0666);
1888 if(fd >= 0)
1890 write(fd, (void *)0x2000000, 0x40000);
1891 close(fd);
1894 system_memory_guard(oldmode);
1895 return false;
1897 #elif defined CPU_COLDFIRE
1898 static bool dbg_save_roms(void)
1900 int fd;
1901 int oldmode = system_memory_guard(MEMGUARD_NONE);
1903 #if defined(IRIVER_H100_SERIES)
1904 fd = creat("/internal_rom_000000-1FFFFF.bin", 0666);
1905 #elif defined(IRIVER_H300_SERIES)
1906 fd = creat("/internal_rom_000000-3FFFFF.bin", 0666);
1907 #elif defined(IAUDIO_X5) || defined(IAUDIO_M5) || defined(IAUDIO_M3)
1908 fd = creat("/internal_rom_000000-3FFFFF.bin", 0666);
1909 #elif defined(MPIO_HD200) || defined(MPIO_HD300)
1910 fd = creat("/internal_rom_000000-1FFFFF.bin", 0666);
1911 #endif
1912 if(fd >= 0)
1914 write(fd, (void *)0, FLASH_SIZE);
1915 close(fd);
1917 system_memory_guard(oldmode);
1919 #ifdef HAVE_EEPROM
1920 fd = creat("/internal_eeprom.bin", 0666);
1921 if (fd >= 0)
1923 int old_irq_level;
1924 char buf[EEPROM_SIZE];
1925 int err;
1927 old_irq_level = disable_irq_save();
1929 err = eeprom_24cxx_read(0, buf, sizeof buf);
1931 restore_irq(old_irq_level);
1933 if (err)
1934 splashf(HZ*3, "Eeprom read failure (%d)", err);
1935 else
1937 write(fd, buf, sizeof buf);
1940 close(fd);
1942 #endif
1944 return false;
1946 #elif defined(CPU_PP) && !(CONFIG_STORAGE & STORAGE_SD)
1947 static bool dbg_save_roms(void)
1949 int fd;
1951 fd = creat("/internal_rom_000000-0FFFFF.bin", 0666);
1952 if(fd >= 0)
1954 write(fd, (void *)0x20000000, FLASH_SIZE);
1955 close(fd);
1958 return false;
1960 #elif CONFIG_CPU == IMX31L
1961 static bool dbg_save_roms(void)
1963 int fd;
1965 fd = creat("/flash_rom_A0000000-A01FFFFF.bin", 0666);
1966 if (fd >= 0)
1968 write(fd, (void*)0xa0000000, FLASH_SIZE);
1969 close(fd);
1972 return false;
1974 #elif defined(CPU_TCC780X)
1975 static bool dbg_save_roms(void)
1977 int fd;
1979 fd = creat("/eeprom_E0000000-E0001FFF.bin", 0666);
1980 if (fd >= 0)
1982 write(fd, (void*)0xe0000000, 0x2000);
1983 close(fd);
1986 return false;
1988 #endif /* CPU */
1990 #ifndef SIMULATOR
1991 #if CONFIG_TUNER
1993 #ifdef CONFIG_TUNER_MULTI
1994 static int tuner_type = 0;
1995 #define IF_TUNER_TYPE(type) if(tuner_type==type)
1996 #else
1997 #define IF_TUNER_TYPE(type)
1998 #endif
2000 static int radio_callback(int btn, struct gui_synclist *lists)
2002 (void)lists;
2003 if (btn == ACTION_STD_CANCEL)
2004 return btn;
2005 simplelist_set_line_count(1);
2007 #if (CONFIG_TUNER & LV24020LP)
2008 simplelist_addline(SIMPLELIST_ADD_LINE,
2009 "CTRL_STAT: %02X", lv24020lp_get(LV24020LP_CTRL_STAT) );
2010 simplelist_addline(SIMPLELIST_ADD_LINE,
2011 "RADIO_STAT: %02X", lv24020lp_get(LV24020LP_REG_STAT) );
2012 simplelist_addline(SIMPLELIST_ADD_LINE,
2013 "MSS_FM: %d kHz", lv24020lp_get(LV24020LP_MSS_FM) );
2014 simplelist_addline(SIMPLELIST_ADD_LINE,
2015 "MSS_IF: %d Hz", lv24020lp_get(LV24020LP_MSS_IF) );
2016 simplelist_addline(SIMPLELIST_ADD_LINE,
2017 "MSS_SD: %d Hz", lv24020lp_get(LV24020LP_MSS_SD) );
2018 simplelist_addline(SIMPLELIST_ADD_LINE,
2019 "if_set: %d Hz", lv24020lp_get(LV24020LP_IF_SET) );
2020 simplelist_addline(SIMPLELIST_ADD_LINE,
2021 "sd_set: %d Hz", lv24020lp_get(LV24020LP_SD_SET) );
2022 #endif /* LV24020LP */
2023 #if (CONFIG_TUNER & S1A0903X01)
2024 simplelist_addline(SIMPLELIST_ADD_LINE,
2025 "Samsung regs: %08X", s1a0903x01_get(RADIO_ALL));
2026 /* This one doesn't return dynamic data atm */
2027 #endif /* S1A0903X01 */
2028 #if (CONFIG_TUNER & TEA5767)
2029 struct tea5767_dbg_info nfo;
2030 tea5767_dbg_info(&nfo);
2031 simplelist_addline(SIMPLELIST_ADD_LINE, "Philips regs:");
2032 simplelist_addline(SIMPLELIST_ADD_LINE,
2033 " Read: %02X %02X %02X %02X %02X",
2034 (unsigned)nfo.read_regs[0], (unsigned)nfo.read_regs[1],
2035 (unsigned)nfo.read_regs[2], (unsigned)nfo.read_regs[3],
2036 (unsigned)nfo.read_regs[4]);
2037 simplelist_addline(SIMPLELIST_ADD_LINE,
2038 " Write: %02X %02X %02X %02X %02X",
2039 (unsigned)nfo.write_regs[0], (unsigned)nfo.write_regs[1],
2040 (unsigned)nfo.write_regs[2], (unsigned)nfo.write_regs[3],
2041 (unsigned)nfo.write_regs[4]);
2042 #endif /* TEA5767 */
2043 #if (CONFIG_TUNER & SI4700)
2044 IF_TUNER_TYPE(SI4700)
2046 struct si4700_dbg_info nfo;
2047 int i;
2048 si4700_dbg_info(&nfo);
2049 simplelist_addline(SIMPLELIST_ADD_LINE, "SI4700 regs:");
2050 for (i = 0; i < 16; i += 4) {
2051 simplelist_addline(SIMPLELIST_ADD_LINE,"%02X: %04X %04X %04X %04X",
2052 i, nfo.regs[i], nfo.regs[i+1], nfo.regs[i+2], nfo.regs[i+3]);
2055 #endif /* SI4700 */
2056 #if (CONFIG_TUNER & RDA5802)
2057 IF_TUNER_TYPE(RDA5802)
2059 struct rda5802_dbg_info nfo;
2060 int i;
2061 rda5802_dbg_info(&nfo);
2062 simplelist_addline(SIMPLELIST_ADD_LINE, "RDA5802 regs:");
2063 for (i = 0; i < 16; i += 4) {
2064 simplelist_addline(SIMPLELIST_ADD_LINE,"%02X: %04X %04X %04X %04X",
2065 i, nfo.regs[i], nfo.regs[i+1], nfo.regs[i+2], nfo.regs[i+3]);
2068 #endif /* RDA55802 */
2069 return ACTION_REDRAW;
2071 static bool dbg_fm_radio(void)
2073 struct simplelist_info info;
2074 #ifdef CONFIG_TUNER_MULTI
2075 tuner_type = tuner_detect_type();
2076 #endif
2077 info.scroll_all = true;
2078 simplelist_info_init(&info, "FM Radio", 1, NULL);
2079 simplelist_set_line_count(0);
2080 simplelist_addline(SIMPLELIST_ADD_LINE, "HW detected: %s",
2081 radio_hardware_present() ? "yes" : "no");
2083 info.action_callback = radio_hardware_present()?radio_callback : NULL;
2084 info.hide_selection = true;
2085 return simplelist_show_list(&info);
2087 #endif /* CONFIG_TUNER */
2088 #endif /* !SIMULATOR */
2090 #ifdef HAVE_LCD_BITMAP
2091 extern bool do_screendump_instead_of_usb;
2093 static bool dbg_screendump(void)
2095 do_screendump_instead_of_usb = !do_screendump_instead_of_usb;
2096 splashf(HZ, "Screendump %s",
2097 do_screendump_instead_of_usb?"enabled":"disabled");
2098 return false;
2100 #endif /* HAVE_LCD_BITMAP */
2102 extern bool write_metadata_log;
2104 static bool dbg_metadatalog(void)
2106 write_metadata_log = !write_metadata_log;
2107 splashf(HZ, "Metadata log %s",
2108 write_metadata_log?"enabled":"disabled");
2109 return false;
2112 #if CONFIG_CPU == SH7034 || defined(CPU_COLDFIRE)
2113 static bool dbg_set_memory_guard(void)
2115 static const struct opt_items names[MAXMEMGUARD] = {
2116 { "None", -1 },
2117 { "Flash ROM writes", -1 },
2118 { "Zero area (all)", -1 }
2120 int mode = system_memory_guard(MEMGUARD_KEEP);
2122 set_option( "Catch mem accesses", &mode, INT, names, MAXMEMGUARD, NULL);
2123 system_memory_guard(mode);
2125 return false;
2127 #endif /* CONFIG_CPU == SH7034 || defined(CPU_COLDFIRE) */
2129 #if defined(HAVE_EEPROM) && !defined(HAVE_EEPROM_SETTINGS)
2130 static bool dbg_write_eeprom(void)
2132 int fd;
2133 int rc;
2134 int old_irq_level;
2135 char buf[EEPROM_SIZE];
2136 int err;
2138 fd = open("/internal_eeprom.bin", O_RDONLY);
2140 if (fd >= 0)
2142 rc = read(fd, buf, EEPROM_SIZE);
2144 if(rc == EEPROM_SIZE)
2146 old_irq_level = disable_irq_save();
2148 err = eeprom_24cxx_write(0, buf, sizeof buf);
2149 if (err)
2150 splashf(HZ*3, "Eeprom write failure (%d)", err);
2151 else
2152 splash(HZ*3, "Eeprom written successfully");
2154 restore_irq(old_irq_level);
2156 else
2158 splashf(HZ*3, "File read error (%d)",rc);
2160 close(fd);
2162 else
2164 splash(HZ*3, "Failed to open 'internal_eeprom.bin'");
2167 return false;
2169 #endif /* defined(HAVE_EEPROM) && !defined(HAVE_EEPROM_SETTINGS) */
2170 #ifdef CPU_BOOST_LOGGING
2171 static bool cpu_boost_log(void)
2173 int i = 0,j=0;
2174 int count = cpu_boost_log_getcount();
2175 int lines = LCD_HEIGHT/SYSFONT_HEIGHT;
2176 char *str;
2177 bool done;
2178 lcd_setfont(FONT_SYSFIXED);
2179 str = cpu_boost_log_getlog_first();
2180 while (i < count)
2182 lcd_clear_display();
2183 for(j=0; j<lines; j++,i++)
2185 if (!str)
2186 str = cpu_boost_log_getlog_next();
2187 if (str)
2189 if(strlen(str) > LCD_WIDTH/SYSFONT_WIDTH)
2190 lcd_puts_scroll(0, j, str);
2191 else
2192 lcd_puts(0, j,str);
2194 str = NULL;
2196 lcd_update();
2197 done = false;
2198 while (!done)
2200 switch(get_action(CONTEXT_STD,TIMEOUT_BLOCK))
2202 case ACTION_STD_OK:
2203 case ACTION_STD_PREV:
2204 case ACTION_STD_NEXT:
2205 done = true;
2206 break;
2207 case ACTION_STD_CANCEL:
2208 i = count;
2209 done = true;
2210 break;
2214 lcd_stop_scroll();
2215 get_action(CONTEXT_STD,TIMEOUT_BLOCK);
2216 lcd_setfont(FONT_UI);
2217 return false;
2219 #endif
2221 #if (defined(HAVE_WHEEL_ACCELERATION) && (CONFIG_KEYPAD==IPOD_4G_PAD) \
2222 && !defined(IPOD_MINI) && !defined(SIMULATOR))
2223 extern bool wheel_is_touched;
2224 extern int old_wheel_value;
2225 extern int new_wheel_value;
2226 extern int wheel_delta;
2227 extern unsigned int accumulated_wheel_delta;
2228 extern unsigned int wheel_velocity;
2230 static bool dbg_scrollwheel(void)
2232 unsigned int speed;
2234 lcd_setfont(FONT_SYSFIXED);
2236 while (1)
2238 if (action_userabort(HZ/10))
2239 break;
2241 lcd_clear_display();
2243 /* show internal variables of scrollwheel driver */
2244 lcd_putsf(0, 0, "wheel touched: %s", (wheel_is_touched) ? "true" : "false");
2245 lcd_putsf(0, 1, "new position: %2d", new_wheel_value);
2246 lcd_putsf(0, 2, "old position: %2d", old_wheel_value);
2247 lcd_putsf(0, 3, "wheel delta: %2d", wheel_delta);
2248 lcd_putsf(0, 4, "accumulated delta: %2d", accumulated_wheel_delta);
2249 lcd_putsf(0, 5, "velo [deg/s]: %4d", (int)wheel_velocity);
2251 /* show effective accelerated scrollspeed */
2252 speed = button_apply_acceleration( (1<<31)|(1<<24)|wheel_velocity);
2253 lcd_putsf(0, 6, "accel. speed: %4d", speed);
2255 lcd_update();
2257 lcd_setfont(FONT_UI);
2258 return false;
2260 #endif
2262 #if defined (HAVE_USBSTACK)
2264 #if defined(ROCKBOX_HAS_LOGF) && defined(USB_ENABLE_SERIAL)
2265 static bool toggle_usb_core_driver(int driver, char *msg)
2267 bool enabled = !usb_core_driver_enabled(driver);
2269 usb_core_enable_driver(driver,enabled);
2270 splashf(HZ, "%s %s", msg, enabled?"enabled":"disabled");
2272 return false;
2275 static bool toggle_usb_serial(void)
2277 return toggle_usb_core_driver(USB_DRIVER_SERIAL,"USB Serial");
2279 #endif
2281 #endif
2283 #if CONFIG_USBOTG == USBOTG_ISP1583
2284 extern int dbg_usb_num_items(void);
2285 extern const char* dbg_usb_item(int selected_item, void *data,
2286 char *buffer, size_t buffer_len);
2288 static int isp1583_action_callback(int action, struct gui_synclist *lists)
2290 (void)lists;
2291 if (action == ACTION_NONE)
2292 action = ACTION_REDRAW;
2293 return action;
2296 static bool dbg_isp1583(void)
2298 struct simplelist_info isp1583;
2299 isp1583.scroll_all = true;
2300 simplelist_info_init(&isp1583, "ISP1583", dbg_usb_num_items(), NULL);
2301 isp1583.timeout = HZ/100;
2302 isp1583.hide_selection = true;
2303 isp1583.get_name = dbg_usb_item;
2304 isp1583.action_callback = isp1583_action_callback;
2305 return simplelist_show_list(&isp1583);
2307 #endif
2309 #if defined(CREATIVE_ZVx) && !defined(SIMULATOR)
2310 extern int pic_dbg_num_items(void);
2311 extern const char* pic_dbg_item(int selected_item, void *data,
2312 char *buffer, size_t buffer_len);
2314 static int pic_action_callback(int action, struct gui_synclist *lists)
2316 (void)lists;
2317 if (action == ACTION_NONE)
2318 action = ACTION_REDRAW;
2319 return action;
2322 static bool dbg_pic(void)
2324 struct simplelist_info pic;
2325 pic.scroll_all = true;
2326 simplelist_info_init(&pic, "PIC", pic_dbg_num_items(), NULL);
2327 pic.timeout = HZ/100;
2328 pic.hide_selection = true;
2329 pic.get_name = pic_dbg_item;
2330 pic.action_callback = pic_action_callback;
2331 return simplelist_show_list(&pic);
2333 #endif
2336 /****** The menu *********/
2337 struct the_menu_item {
2338 unsigned char *desc; /* string or ID */
2339 bool (*function) (void); /* return true if USB was connected */
2341 static const struct the_menu_item menuitems[] = {
2342 #if CONFIG_CPU == SH7034 || defined(CPU_COLDFIRE) || \
2343 (defined(CPU_PP) && !(CONFIG_STORAGE & STORAGE_SD)) || \
2344 CONFIG_CPU == IMX31L || defined(CPU_TCC780X)
2345 { "Dump ROM contents", dbg_save_roms },
2346 #endif
2347 #if CONFIG_CPU == SH7034 || defined(CPU_COLDFIRE) || defined(CPU_PP) \
2348 || CONFIG_CPU == S3C2440 || CONFIG_CPU == IMX31L || CONFIG_CPU == AS3525 \
2349 || CONFIG_CPU == DM320 || defined(CPU_S5L870X) || CONFIG_CPU == AS3525v2
2350 { "View I/O ports", dbg_ports },
2351 #endif
2352 #if (CONFIG_RTC == RTC_PCF50605) && (CONFIG_PLATFORM & PLATFORM_NATIVE)
2353 { "View PCF registers", dbg_pcf },
2354 #endif
2355 #if defined(HAVE_TSC2100) && (CONFIG_PLATFORM & PLATFORM_NATIVE)
2356 { "TSC2100 debug", tsc2100_debug },
2357 #endif
2358 #ifdef HAVE_ADJUSTABLE_CPU_FREQ
2359 { "CPU frequency", dbg_cpufreq },
2360 #endif
2361 #if CONFIG_CPU == IMX31L
2362 { "DVFS/DPTC", __dbg_dvfs_dptc },
2363 #endif
2364 #if defined(IRIVER_H100_SERIES) && !defined(SIMULATOR)
2365 { "S/PDIF analyzer", dbg_spdif },
2366 #endif
2367 #if CONFIG_CPU == SH7034 || defined(CPU_COLDFIRE)
2368 { "Catch mem accesses", dbg_set_memory_guard },
2369 #endif
2370 { "View OS stacks", dbg_os },
2371 #ifdef HAVE_LCD_BITMAP
2372 #if (CONFIG_PLATFORM & PLATFORM_NATIVE)
2373 { "View battery", view_battery },
2374 #endif
2375 { "Screendump", dbg_screendump },
2376 #endif
2377 #if (CONFIG_PLATFORM & PLATFORM_NATIVE)
2378 { "View HW info", dbg_hw_info },
2379 #endif
2380 #if (CONFIG_PLATFORM & PLATFORM_NATIVE)
2381 { "View partitions", dbg_partitions },
2382 #endif
2383 #if (CONFIG_PLATFORM & PLATFORM_NATIVE)
2384 { "View disk info", dbg_disk_info },
2385 #if (CONFIG_STORAGE & STORAGE_ATA)
2386 { "Dump ATA identify info", dbg_identify_info},
2387 #endif
2388 #endif
2389 { "Metadata log", dbg_metadatalog },
2390 #ifdef HAVE_DIRCACHE
2391 { "View dircache info", dbg_dircache_info },
2392 #endif
2393 #ifdef HAVE_TAGCACHE
2394 { "View database info", dbg_tagcache_info },
2395 #endif
2396 #ifdef HAVE_LCD_BITMAP
2397 #if CONFIG_CODEC == SWCODEC
2398 { "View buffering thread", dbg_buffering_thread },
2399 #elif !defined(SIMULATOR)
2400 { "View audio thread", dbg_audio_thread },
2401 #endif
2402 #ifdef PM_DEBUG
2403 { "pm histogram", peak_meter_histogram},
2404 #endif /* PM_DEBUG */
2405 #endif /* HAVE_LCD_BITMAP */
2406 #ifndef SIMULATOR
2407 #if CONFIG_TUNER
2408 { "FM Radio", dbg_fm_radio },
2409 #endif
2410 #endif
2411 #if defined(HAVE_EEPROM) && !defined(HAVE_EEPROM_SETTINGS)
2412 { "Write back EEPROM", dbg_write_eeprom },
2413 #endif
2414 #if CONFIG_USBOTG == USBOTG_ISP1583
2415 { "View ISP1583 info", dbg_isp1583 },
2416 #endif
2417 #if defined(CREATIVE_ZVx) && !defined(SIMULATOR)
2418 { "View PIC info", dbg_pic },
2419 #endif
2420 #ifdef ROCKBOX_HAS_LOGF
2421 {"Show Log File", logfdisplay },
2422 {"Dump Log File", logfdump },
2423 #endif
2424 #if defined(HAVE_USBSTACK)
2425 #if defined(ROCKBOX_HAS_LOGF) && defined(USB_ENABLE_SERIAL)
2426 {"USB Serial driver (logf)", toggle_usb_serial },
2427 #endif
2428 #endif /* HAVE_USBSTACK */
2429 #ifdef CPU_BOOST_LOGGING
2430 {"cpu_boost log",cpu_boost_log},
2431 #endif
2432 #if (defined(HAVE_WHEEL_ACCELERATION) && (CONFIG_KEYPAD==IPOD_4G_PAD) \
2433 && !defined(IPOD_MINI) && !defined(SIMULATOR))
2434 {"Debug scrollwheel", dbg_scrollwheel },
2435 #endif
2437 static int menu_action_callback(int btn, struct gui_synclist *lists)
2439 int i;
2440 if (btn == ACTION_STD_OK)
2442 FOR_NB_SCREENS(i)
2443 viewportmanager_theme_enable(i, false, NULL);
2444 menuitems[gui_synclist_get_sel_pos(lists)].function();
2445 btn = ACTION_REDRAW;
2446 FOR_NB_SCREENS(i)
2447 viewportmanager_theme_undo(i, false);
2449 return btn;
2452 static const char* dbg_menu_getname(int item, void * data,
2453 char *buffer, size_t buffer_len)
2455 (void)data; (void)buffer; (void)buffer_len;
2456 return menuitems[item].desc;
2459 bool debug_menu(void)
2461 struct simplelist_info info;
2463 simplelist_info_init(&info, "Debug Menu", ARRAYLEN(menuitems), NULL);
2464 info.action_callback = menu_action_callback;
2465 info.get_name = dbg_menu_getname;
2466 return simplelist_show_list(&info);