don't save mountpoint using native separators in the configuration. Makes things...
[Rockbox.git] / apps / debug_menu.c
blobe198bfa18dbb2f8ffd80732798dbc39eacd0a6c3
1 /***************************************************************************
2 * __________ __ ___.
3 * Open \______ \ ____ ____ | | _\_ |__ _______ ___
4 * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
5 * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
6 * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
7 * \/ \/ \/ \/ \/
8 * $Id$
10 * Copyright (C) 2002 Heikki Hannikainen
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.
15 * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
16 * KIND, either express or implied.
18 ****************************************************************************/
20 #include "config.h"
21 #include <stdio.h>
22 #include <stdbool.h>
23 #include <string.h>
24 #include "lcd.h"
25 #include "menu.h"
26 #include "debug_menu.h"
27 #include "kernel.h"
28 #include "sprintf.h"
29 #include "structec.h"
30 #include "action.h"
31 #include "debug.h"
32 #include "thread.h"
33 #include "powermgmt.h"
34 #include "system.h"
35 #include "font.h"
36 #include "audio.h"
37 #include "mp3_playback.h"
38 #include "settings.h"
39 #include "list.h"
40 #include "statusbar.h"
41 #include "dir.h"
42 #include "panic.h"
43 #include "screens.h"
44 #include "misc.h"
45 #include "splash.h"
46 #include "dircache.h"
47 #ifdef HAVE_TAGCACHE
48 #include "tagcache.h"
49 #endif
50 #include "lcd-remote.h"
51 #include "crc32.h"
52 #include "logf.h"
53 #ifndef SIMULATOR
54 #include "disk.h"
55 #include "adc.h"
56 #include "power.h"
57 #include "usb.h"
58 #include "rtc.h"
59 #include "ata.h"
60 #include "fat.h"
61 #include "mas.h"
62 #include "eeprom_24cxx.h"
63 #if defined(HAVE_MMC) || defined(HAVE_ATA_SD)
64 #include "hotswap.h"
65 #endif
66 #if CONFIG_TUNER
67 #include "tuner.h"
68 #include "radio.h"
69 #endif
70 #endif
72 #ifdef HAVE_LCD_BITMAP
73 #include "scrollbar.h"
74 #include "peakmeter.h"
75 #endif
76 #include "logfdisp.h"
77 #if CONFIG_CODEC == SWCODEC
78 #include "pcmbuf.h"
79 #include "buffering.h"
80 #include "playback.h"
81 #if defined(HAVE_SPDIF_OUT) || defined(HAVE_SPDIF_IN)
82 #include "spdif.h"
83 #endif
84 #endif
85 #ifdef IRIVER_H300_SERIES
86 #include "pcf50606.h" /* for pcf50606_read */
87 #endif
88 #ifdef IAUDIO_X5
89 #include "ds2411.h"
90 #endif
91 #include "hwcompat.h"
92 #include "button.h"
93 #if CONFIG_RTC == RTC_PCF50605
94 #include "pcf50605.h"
95 #endif
97 #if CONFIG_CPU == DM320 || CONFIG_CPU == S3C2440 || CONFIG_CPU == TCC7801 \
98 || CONFIG_CPU == IMX31L
99 #include "debug-target.h"
100 #endif
102 #if defined(SANSA_E200)
103 #include "i2c-pp.h"
104 #include "as3514.h"
105 #endif
107 #if defined(HAVE_USBSTACK)
108 #include "usb_core.h"
109 #endif
110 #ifdef USB_STORAGE
111 #include "../firmware/usbstack/usb_storage.h"
112 #endif
114 /*---------------------------------------------------*/
115 /* SPECIAL DEBUG STUFF */
116 /*---------------------------------------------------*/
117 extern struct thread_entry threads[MAXTHREADS];
119 static char thread_status_char(unsigned status)
121 static const char thread_status_chars[THREAD_NUM_STATES+1] =
123 [0 ... THREAD_NUM_STATES] = '?',
124 [STATE_RUNNING] = 'R',
125 [STATE_BLOCKED] = 'B',
126 [STATE_SLEEPING] = 'S',
127 [STATE_BLOCKED_W_TMO] = 'T',
128 [STATE_FROZEN] = 'F',
129 [STATE_KILLED] = 'K',
132 if (status > THREAD_NUM_STATES)
133 status = THREAD_NUM_STATES;
135 return thread_status_chars[status];
138 static char* threads_getname(int selected_item, void *data,
139 char *buffer, size_t buffer_len)
141 (void)data;
142 struct thread_entry *thread;
143 char name[32];
145 #if NUM_CORES > 1
146 if (selected_item < (int)NUM_CORES)
148 snprintf(buffer, buffer_len, "Idle (%d): %2d%%", selected_item,
149 idle_stack_usage(selected_item));
150 return buffer;
153 selected_item -= NUM_CORES;
154 #endif
156 thread = &threads[selected_item];
158 if (thread->state == STATE_KILLED)
160 snprintf(buffer, buffer_len, "%2d: ---", selected_item);
161 return buffer;
164 thread_get_name(name, 32, thread);
166 snprintf(buffer, buffer_len,
167 "%2d: " IF_COP("(%d) ") "%c%c " IF_PRIO("%d %d ") "%2d%% %s",
168 selected_item,
169 IF_COP(thread->core,)
170 #ifdef HAVE_SCHEDULER_BOOSTCTRL
171 (thread->cpu_boost) ? '+' :
172 #endif
173 ((thread->state == STATE_RUNNING) ? '*' : ' '),
174 thread_status_char(thread->state),
175 IF_PRIO(thread->base_priority, thread->priority, )
176 thread_stack_usage(thread), name);
178 return buffer;
180 static int dbg_threads_action_callback(int action, struct gui_synclist *lists)
182 (void)lists;
183 #ifdef ROCKBOX_HAS_LOGF
184 if (action == ACTION_STD_OK)
186 int selpos = gui_synclist_get_sel_pos(lists);
187 #if NUM_CORES > 1
188 if (selpos >= NUM_CORES)
189 remove_thread(&threads[selpos - NUM_CORES]);
190 #else
191 remove_thread(&threads[selpos]);
192 #endif
193 return ACTION_REDRAW;
195 #endif /* ROCKBOX_HAS_LOGF */
196 if (action == ACTION_NONE)
197 action = ACTION_REDRAW;
198 return action;
200 /* Test code!!! */
201 static bool dbg_os(void)
203 struct simplelist_info info;
204 simplelist_info_init(&info, IF_COP("Core and ") "Stack usage:",
205 #if NUM_CORES == 1
206 MAXTHREADS,
207 #else
208 MAXTHREADS+NUM_CORES,
209 #endif
210 NULL);
211 #ifndef ROCKBOX_HAS_LOGF
212 info.hide_selection = true;
213 info.scroll_all = true;
214 #endif
215 info.action_callback = dbg_threads_action_callback;
216 info.get_name = threads_getname;
217 return simplelist_show_list(&info);
220 #ifdef HAVE_LCD_BITMAP
221 #if CONFIG_CODEC != SWCODEC
222 #ifndef SIMULATOR
223 static bool dbg_audio_thread(void)
225 char buf[32];
226 struct audio_debug d;
228 lcd_setmargins(0, 0);
229 lcd_setfont(FONT_SYSFIXED);
231 while(1)
233 if (action_userabort(HZ/5))
234 return false;
236 audio_get_debugdata(&d);
238 lcd_clear_display();
240 snprintf(buf, sizeof(buf), "read: %x", d.audiobuf_read);
241 lcd_puts(0, 0, buf);
242 snprintf(buf, sizeof(buf), "write: %x", d.audiobuf_write);
243 lcd_puts(0, 1, buf);
244 snprintf(buf, sizeof(buf), "swap: %x", d.audiobuf_swapwrite);
245 lcd_puts(0, 2, buf);
246 snprintf(buf, sizeof(buf), "playing: %d", d.playing);
247 lcd_puts(0, 3, buf);
248 snprintf(buf, sizeof(buf), "playable: %x", d.playable_space);
249 lcd_puts(0, 4, buf);
250 snprintf(buf, sizeof(buf), "unswapped: %x", d.unswapped_space);
251 lcd_puts(0, 5, buf);
253 /* Playable space left */
254 gui_scrollbar_draw(&screens[SCREEN_MAIN],0, 6*8, 112, 4, d.audiobuflen, 0,
255 d.playable_space, HORIZONTAL);
257 /* Show the watermark limit */
258 gui_scrollbar_draw(&screens[SCREEN_MAIN],0, 6*8+4, 112, 4, d.audiobuflen, 0,
259 d.low_watermark_level, HORIZONTAL);
261 snprintf(buf, sizeof(buf), "wm: %x - %x",
262 d.low_watermark_level, d.lowest_watermark_level);
263 lcd_puts(0, 7, buf);
265 lcd_update();
267 return false;
269 #endif /* !SIMULATOR */
270 #else /* CONFIG_CODEC == SWCODEC */
271 extern size_t filebuflen;
272 /* This is a size_t, but call it a long so it puts a - when it's bad. */
274 static unsigned int ticks, boost_ticks, freq_sum;
276 static void dbg_audio_task(void)
278 #ifndef SIMULATOR
279 if(FREQ > CPUFREQ_NORMAL)
280 boost_ticks++;
281 freq_sum += FREQ/1000000; /* in MHz */
282 #endif
283 ticks++;
286 static bool dbg_buffering_thread(void)
288 char buf[32];
289 int button;
290 int line;
291 bool done = false;
292 size_t bufused;
293 size_t bufsize = pcmbuf_get_bufsize();
294 int pcmbufdescs = pcmbuf_descs();
295 struct buffering_debug d;
297 ticks = boost_ticks = freq_sum = 0;
299 tick_add_task(dbg_audio_task);
301 lcd_setmargins(0, 0);
302 lcd_setfont(FONT_SYSFIXED);
303 while(!done)
305 button = get_action(CONTEXT_STD,HZ/5);
306 switch(button)
308 case ACTION_STD_NEXT:
309 audio_next();
310 break;
311 case ACTION_STD_PREV:
312 audio_prev();
313 break;
314 case ACTION_STD_CANCEL:
315 done = true;
316 break;
319 buffering_get_debugdata(&d);
321 line = 0;
322 lcd_clear_display();
324 bufused = bufsize - pcmbuf_free();
326 snprintf(buf, sizeof(buf), "pcm: %7ld/%7ld", (long) bufused, (long) bufsize);
327 lcd_puts(0, line++, buf);
329 gui_scrollbar_draw(&screens[SCREEN_MAIN],0, line*8, LCD_WIDTH, 6,
330 bufsize, 0, bufused, HORIZONTAL);
331 line++;
333 snprintf(buf, sizeof(buf), "alloc: %8ld/%8ld", audio_filebufused(),
334 (long) filebuflen);
335 lcd_puts(0, line++, buf);
337 #if LCD_HEIGHT > 80
338 gui_scrollbar_draw(&screens[SCREEN_MAIN],0, line*8, LCD_WIDTH, 6,
339 filebuflen, 0, audio_filebufused(), HORIZONTAL);
340 line++;
342 snprintf(buf, sizeof(buf), "real: %8ld/%8ld", (long)d.buffered_data,
343 (long)filebuflen);
344 lcd_puts(0, line++, buf);
346 gui_scrollbar_draw(&screens[SCREEN_MAIN],0, line*8, LCD_WIDTH, 6,
347 filebuflen, 0, (long)d.buffered_data, HORIZONTAL);
348 line++;
349 #endif
351 snprintf(buf, sizeof(buf), "usefl: %8ld/%8ld", (long)(d.useful_data),
352 (long)filebuflen);
353 lcd_puts(0, line++, buf);
355 #if LCD_HEIGHT > 80
356 gui_scrollbar_draw(&screens[SCREEN_MAIN],0, line*8, LCD_WIDTH, 6,
357 filebuflen, 0, d.useful_data, HORIZONTAL);
358 line++;
359 #endif
361 snprintf(buf, sizeof(buf), "data_rem: %ld", (long)d.data_rem);
362 lcd_puts(0, line++, buf);
364 snprintf(buf, sizeof(buf), "track count: %2d", audio_track_count());
365 lcd_puts(0, line++, buf);
367 snprintf(buf, sizeof(buf), "handle count: %d", (int)d.num_handles);
368 lcd_puts(0, line++, buf);
370 #ifndef SIMULATOR
371 snprintf(buf, sizeof(buf), "cpu freq: %3dMHz",
372 (int)((FREQ + 500000) / 1000000));
373 lcd_puts(0, line++, buf);
374 #endif
376 if (ticks > 0)
378 int boostquota = boost_ticks * 1000 / ticks; /* in 0.1 % */
379 int avgclock = freq_sum * 10 / ticks; /* in 100 kHz */
380 snprintf(buf, sizeof(buf), "boost ratio: %3d.%d%% (%2d.%dMHz)",
381 boostquota/10, boostquota%10, avgclock/10, avgclock%10);
382 lcd_puts(0, line++, buf);
385 snprintf(buf, sizeof(buf), "pcmbufdesc: %2d/%2d",
386 pcmbuf_used_descs(), pcmbufdescs);
387 lcd_puts(0, line++, buf);
389 lcd_update();
392 tick_remove_task(dbg_audio_task);
394 return false;
396 #endif /* CONFIG_CODEC */
397 #endif /* HAVE_LCD_BITMAP */
400 #if (CONFIG_CPU == SH7034 || defined(CPU_COLDFIRE))
401 /* Tool function to read the flash manufacturer and type, if available.
402 Only chips which could be reprogrammed in system will return values.
403 (The mode switch addresses vary between flash manufacturers, hence addr1/2) */
404 /* In IRAM to avoid problems when running directly from Flash */
405 static bool dbg_flash_id(unsigned* p_manufacturer, unsigned* p_device,
406 unsigned addr1, unsigned addr2)
407 ICODE_ATTR __attribute__((noinline));
408 static bool dbg_flash_id(unsigned* p_manufacturer, unsigned* p_device,
409 unsigned addr1, unsigned addr2)
412 unsigned not_manu, not_id; /* read values before switching to ID mode */
413 unsigned manu, id; /* read values when in ID mode */
415 #if CONFIG_CPU == SH7034
416 volatile unsigned char* flash = (unsigned char*)0x2000000; /* flash mapping */
417 #elif defined(CPU_COLDFIRE)
418 volatile unsigned short* flash = (unsigned short*)0; /* flash mapping */
419 #endif
420 int old_level; /* saved interrupt level */
422 not_manu = flash[0]; /* read the normal content */
423 not_id = flash[1]; /* should be 'A' (0x41) and 'R' (0x52) from the "ARCH" marker */
425 /* disable interrupts, prevent any stray flash access */
426 old_level = disable_irq_save();
428 flash[addr1] = 0xAA; /* enter command mode */
429 flash[addr2] = 0x55;
430 flash[addr1] = 0x90; /* ID command */
431 /* Atmel wants 20ms pause here */
432 /* sleep(HZ/50); no sleeping possible while interrupts are disabled */
434 manu = flash[0]; /* read the IDs */
435 id = flash[1];
437 flash[0] = 0xF0; /* reset flash (back to normal read mode) */
438 /* Atmel wants 20ms pause here */
439 /* sleep(HZ/50); no sleeping possible while interrupts are disabled */
441 restore_irq(old_level); /* enable interrupts again */
443 /* I assume success if the obtained values are different from
444 the normal flash content. This is not perfectly bulletproof, they
445 could theoretically be the same by chance, causing us to fail. */
446 if (not_manu != manu || not_id != id) /* a value has changed */
448 *p_manufacturer = manu; /* return the results */
449 *p_device = id;
450 return true; /* success */
452 return false; /* fail */
454 #endif /* (CONFIG_CPU == SH7034 || CPU_COLDFIRE) */
456 #ifndef SIMULATOR
457 #ifdef CPU_PP
458 static int perfcheck(void)
460 int result;
462 asm (
463 "mrs r2, CPSR \n"
464 "orr r0, r2, #0xc0 \n" /* disable IRQ and FIQ */
465 "msr CPSR_c, r0 \n"
466 "mov %[res], #0 \n"
467 "ldr r0, [%[timr]] \n"
468 "add r0, r0, %[tmo] \n"
469 "1: \n"
470 "add %[res], %[res], #1 \n"
471 "ldr r1, [%[timr]] \n"
472 "cmp r1, r0 \n"
473 "bmi 1b \n"
474 "msr CPSR_c, r2 \n" /* reset IRQ and FIQ state */
476 [res]"=&r"(result)
478 [timr]"r"(&USEC_TIMER),
479 [tmo]"r"(
480 #if CONFIG_CPU == PP5002
481 16000
482 #else /* PP5020/5022/5024 */
483 10226
484 #endif
487 "r0", "r1", "r2"
489 return result;
491 #endif
493 #ifdef HAVE_LCD_BITMAP
494 static bool dbg_hw_info(void)
496 #if CONFIG_CPU == SH7034
497 char buf[32];
498 int bitmask = HW_MASK;
499 int rom_version = ROM_VERSION;
500 unsigned manu, id; /* flash IDs */
501 bool got_id; /* flag if we managed to get the flash IDs */
502 unsigned rom_crc = 0xffffffff; /* CRC32 of the boot ROM */
503 bool has_bootrom; /* flag for boot ROM present */
504 int oldmode; /* saved memory guard mode */
506 oldmode = system_memory_guard(MEMGUARD_NONE); /* disable memory guard */
508 /* get flash ROM type */
509 got_id = dbg_flash_id(&manu, &id, 0x5555, 0x2AAA); /* try SST, Atmel, NexFlash */
510 if (!got_id)
511 got_id = dbg_flash_id(&manu, &id, 0x555, 0x2AA); /* try AMD, Macronix */
513 /* check if the boot ROM area is a flash mirror */
514 has_bootrom = (memcmp((char*)0, (char*)0x02000000, 64*1024) != 0);
515 if (has_bootrom) /* if ROM and Flash different */
517 /* calculate CRC16 checksum of boot ROM */
518 rom_crc = crc_32((unsigned char*)0x0000, 64*1024, 0xffffffff);
521 system_memory_guard(oldmode); /* re-enable memory guard */
523 lcd_setmargins(0, 0);
524 lcd_setfont(FONT_SYSFIXED);
525 lcd_clear_display();
527 lcd_puts(0, 0, "[Hardware info]");
529 snprintf(buf, 32, "ROM: %d.%02d", rom_version/100, rom_version%100);
530 lcd_puts(0, 1, buf);
532 snprintf(buf, 32, "Mask: 0x%04x", bitmask);
533 lcd_puts(0, 2, buf);
535 if (got_id)
536 snprintf(buf, 32, "Flash: M=%02x D=%02x", manu, id);
537 else
538 snprintf(buf, 32, "Flash: M=?? D=??"); /* unknown, sorry */
539 lcd_puts(0, 3, buf);
541 if (has_bootrom)
543 if (rom_crc == 0x56DBA4EE) /* known Version 1 */
544 snprintf(buf, 32, "Boot ROM: V1");
545 else
546 snprintf(buf, 32, "ROMcrc: 0x%08x", rom_crc);
548 else
550 snprintf(buf, 32, "Boot ROM: none");
552 lcd_puts(0, 4, buf);
554 lcd_update();
556 while (!(action_userabort(TIMEOUT_BLOCK)));
558 #elif CONFIG_CPU == MCF5249 || CONFIG_CPU == MCF5250
559 char buf[32];
560 unsigned manu, id; /* flash IDs */
561 int got_id; /* flag if we managed to get the flash IDs */
562 int oldmode; /* saved memory guard mode */
563 int line = 0;
565 oldmode = system_memory_guard(MEMGUARD_NONE); /* disable memory guard */
567 /* get flash ROM type */
568 got_id = dbg_flash_id(&manu, &id, 0x5555, 0x2AAA); /* try SST, Atmel, NexFlash */
569 if (!got_id)
570 got_id = dbg_flash_id(&manu, &id, 0x555, 0x2AA); /* try AMD, Macronix */
572 system_memory_guard(oldmode); /* re-enable memory guard */
574 lcd_setmargins(0, 0);
575 lcd_setfont(FONT_SYSFIXED);
576 lcd_clear_display();
578 lcd_puts(0, line++, "[Hardware info]");
580 if (got_id)
581 snprintf(buf, 32, "Flash: M=%04x D=%04x", manu, id);
582 else
583 snprintf(buf, 32, "Flash: M=???? D=????"); /* unknown, sorry */
584 lcd_puts(0, line++, buf);
586 #ifdef IAUDIO_X5
588 struct ds2411_id id;
590 lcd_puts(0, ++line, "Serial Number:");
592 got_id = ds2411_read_id(&id);
594 if (got_id == DS2411_OK)
596 snprintf(buf, 32, " FC=%02x", (unsigned)id.family_code);
597 lcd_puts(0, ++line, buf);
598 snprintf(buf, 32, " ID=%02X %02X %02X %02X %02X %02X",
599 (unsigned)id.uid[0], (unsigned)id.uid[1], (unsigned)id.uid[2],
600 (unsigned)id.uid[3], (unsigned)id.uid[4], (unsigned)id.uid[5]);
601 lcd_puts(0, ++line, buf);
602 snprintf(buf, 32, " CRC=%02X", (unsigned)id.crc);
604 else
606 snprintf(buf, 32, "READ ERR=%d", got_id);
609 lcd_puts(0, ++line, buf);
611 #endif
613 lcd_update();
615 while (!(action_userabort(TIMEOUT_BLOCK)));
617 #elif defined(CPU_PP502x)
618 int line = 0;
619 char buf[32];
620 char pp_version[] = { (PP_VER2 >> 24) & 0xff, (PP_VER2 >> 16) & 0xff,
621 (PP_VER2 >> 8) & 0xff, (PP_VER2) & 0xff,
622 (PP_VER1 >> 24) & 0xff, (PP_VER1 >> 16) & 0xff,
623 (PP_VER1 >> 8) & 0xff, (PP_VER1) & 0xff, '\0' };
625 lcd_setmargins(0, 0);
626 lcd_setfont(FONT_SYSFIXED);
627 lcd_clear_display();
629 lcd_puts(0, line++, "[Hardware info]");
631 #ifdef IPOD_ARCH
632 snprintf(buf, sizeof(buf), "HW rev: 0x%08lx", IPOD_HW_REVISION);
633 lcd_puts(0, line++, buf);
634 #endif
636 #ifdef IPOD_COLOR
637 extern int lcd_type; /* Defined in lcd-colornano.c */
639 snprintf(buf, sizeof(buf), "LCD type: %d", lcd_type);
640 lcd_puts(0, line++, buf);
641 #endif
643 snprintf(buf, sizeof(buf), "PP version: %s", pp_version);
644 lcd_puts(0, line++, buf);
646 snprintf(buf, sizeof(buf), "Est. clock (kHz): %d", perfcheck());
647 lcd_puts(0, line++, buf);
649 lcd_update();
651 while (!(action_userabort(TIMEOUT_BLOCK)));
653 #elif CONFIG_CPU == PP5002
654 int line = 0;
655 char buf[32];
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_setmargins(0, 0);
663 lcd_setfont(FONT_SYSFIXED);
664 lcd_clear_display();
666 lcd_puts(0, line++, "[Hardware info]");
668 #ifdef IPOD_ARCH
669 snprintf(buf, sizeof(buf), "HW rev: 0x%08lx", IPOD_HW_REVISION);
670 lcd_puts(0, line++, buf);
671 #endif
673 snprintf(buf, sizeof(buf), "PP version: %s", pp_version);
674 lcd_puts(0, line++, buf);
676 snprintf(buf, sizeof(buf), "Est. clock (kHz): %d", perfcheck());
677 lcd_puts(0, line++, buf);
679 lcd_update();
681 while (!(action_userabort(TIMEOUT_BLOCK)));
682 #else
683 /* Define this function in your target tree */
684 return __dbg_hw_info();
685 #endif /* CONFIG_CPU */
686 return false;
688 #else /* !HAVE_LCD_BITMAP */
689 static bool dbg_hw_info(void)
691 char buf[32];
692 int button;
693 int currval = 0;
694 int rom_version = ROM_VERSION;
695 unsigned manu, id; /* flash IDs */
696 bool got_id; /* flag if we managed to get the flash IDs */
697 unsigned rom_crc = 0xffffffff; /* CRC32 of the boot ROM */
698 bool has_bootrom; /* flag for boot ROM present */
699 int oldmode; /* saved memory guard mode */
701 oldmode = system_memory_guard(MEMGUARD_NONE); /* disable memory guard */
703 /* get flash ROM type */
704 got_id = dbg_flash_id(&manu, &id, 0x5555, 0x2AAA); /* try SST, Atmel, NexFlash */
705 if (!got_id)
706 got_id = dbg_flash_id(&manu, &id, 0x555, 0x2AA); /* try AMD, Macronix */
708 /* check if the boot ROM area is a flash mirror */
709 has_bootrom = (memcmp((char*)0, (char*)0x02000000, 64*1024) != 0);
710 if (has_bootrom) /* if ROM and Flash different */
712 /* calculate CRC16 checksum of boot ROM */
713 rom_crc = crc_32((unsigned char*)0x0000, 64*1024, 0xffffffff);
716 system_memory_guard(oldmode); /* re-enable memory guard */
718 lcd_clear_display();
720 lcd_puts(0, 0, "[HW Info]");
721 while(1)
723 switch(currval)
725 case 0:
726 snprintf(buf, 32, "ROM: %d.%02d",
727 rom_version/100, rom_version%100);
728 break;
729 case 1:
730 if (got_id)
731 snprintf(buf, 32, "Flash:%02x,%02x", manu, id);
732 else
733 snprintf(buf, 32, "Flash:??,??"); /* unknown, sorry */
734 break;
735 case 2:
736 if (has_bootrom)
738 if (rom_crc == 0x56DBA4EE) /* known Version 1 */
739 snprintf(buf, 32, "BootROM: V1");
740 else if (rom_crc == 0x358099E8)
741 snprintf(buf, 32, "BootROM: V2");
742 /* alternative boot ROM found in one single player so far */
743 else
744 snprintf(buf, 32, "R: %08x", rom_crc);
746 else
747 snprintf(buf, 32, "BootROM: no");
750 lcd_puts(0, 1, buf);
751 lcd_update();
753 button = get_action(CONTEXT_SETTINGS,TIMEOUT_BLOCK);
755 switch(button)
757 case ACTION_STD_CANCEL:
758 return false;
760 case ACTION_SETTINGS_DEC:
761 currval--;
762 if(currval < 0)
763 currval = 2;
764 break;
766 case ACTION_SETTINGS_INC:
767 currval++;
768 if(currval > 2)
769 currval = 0;
770 break;
773 return false;
775 #endif /* !HAVE_LCD_BITMAP */
776 #endif /* !SIMULATOR */
778 #ifndef SIMULATOR
779 static char* dbg_partitions_getname(int selected_item, void *data,
780 char *buffer, size_t buffer_len)
782 (void)data;
783 int partition = selected_item/2;
784 struct partinfo* p = disk_partinfo(partition);
785 if (selected_item%2)
787 snprintf(buffer, buffer_len, " T:%x %ld MB", p->type, p->size / 2048);
789 else
791 snprintf(buffer, buffer_len, "P%d: S:%lx", partition, p->start);
793 return buffer;
796 bool dbg_partitions(void)
798 struct simplelist_info info;
799 simplelist_info_init(&info, "Partition Info", 4, NULL);
800 info.selection_size = 2;
801 info.hide_selection = true;
802 info.scroll_all = true;
803 info.get_name = dbg_partitions_getname;
804 return simplelist_show_list(&info);
806 #endif
808 #if defined(CPU_COLDFIRE) && defined(HAVE_SPDIF_OUT)
809 static bool dbg_spdif(void)
811 char buf[128];
812 int line;
813 unsigned int control;
814 int x;
815 char *s;
816 int category;
817 int generation;
818 unsigned int interruptstat;
819 bool valnogood, symbolerr, parityerr;
820 bool done = false;
821 bool spdif_src_on;
822 int spdif_source = spdif_get_output_source(&spdif_src_on);
823 spdif_set_output_source(AUDIO_SRC_SPDIF IF_SPDIF_POWER_(, true));
825 lcd_setmargins(0, 0);
826 lcd_clear_display();
827 lcd_setfont(FONT_SYSFIXED);
829 #ifdef HAVE_SPDIF_POWER
830 spdif_power_enable(true); /* We need SPDIF power for both sending & receiving */
831 #endif
833 while (!done)
835 line = 0;
837 control = EBU1RCVCCHANNEL1;
838 interruptstat = INTERRUPTSTAT;
839 INTERRUPTCLEAR = 0x03c00000;
841 valnogood = (interruptstat & 0x01000000)?true:false;
842 symbolerr = (interruptstat & 0x00800000)?true:false;
843 parityerr = (interruptstat & 0x00400000)?true:false;
845 snprintf(buf, sizeof(buf), "Val: %s Sym: %s Par: %s",
846 valnogood?"--":"OK",
847 symbolerr?"--":"OK",
848 parityerr?"--":"OK");
849 lcd_puts(0, line++, buf);
851 snprintf(buf, sizeof(buf), "Status word: %08x", (int)control);
852 lcd_puts(0, line++, buf);
854 line++;
856 x = control >> 31;
857 snprintf(buf, sizeof(buf), "PRO: %d (%s)",
858 x, x?"Professional":"Consumer");
859 lcd_puts(0, line++, buf);
861 x = (control >> 30) & 1;
862 snprintf(buf, sizeof(buf), "Audio: %d (%s)",
863 x, x?"Non-PCM":"PCM");
864 lcd_puts(0, line++, buf);
866 x = (control >> 29) & 1;
867 snprintf(buf, sizeof(buf), "Copy: %d (%s)",
868 x, x?"Permitted":"Inhibited");
869 lcd_puts(0, line++, buf);
871 x = (control >> 27) & 7;
872 switch(x)
874 case 0:
875 s = "None";
876 break;
877 case 1:
878 s = "50/15us";
879 break;
880 default:
881 s = "Reserved";
882 break;
884 snprintf(buf, sizeof(buf), "Preemphasis: %d (%s)", x, s);
885 lcd_puts(0, line++, buf);
887 x = (control >> 24) & 3;
888 snprintf(buf, sizeof(buf), "Mode: %d", x);
889 lcd_puts(0, line++, buf);
891 category = (control >> 17) & 127;
892 switch(category)
894 case 0x00:
895 s = "General";
896 break;
897 case 0x40:
898 s = "Audio CD";
899 break;
900 default:
901 s = "Unknown";
903 snprintf(buf, sizeof(buf), "Category: 0x%02x (%s)", category, s);
904 lcd_puts(0, line++, buf);
906 x = (control >> 16) & 1;
907 generation = x;
908 if(((category & 0x70) == 0x10) ||
909 ((category & 0x70) == 0x40) ||
910 ((category & 0x78) == 0x38))
912 generation = !generation;
914 snprintf(buf, sizeof(buf), "Generation: %d (%s)",
915 x, generation?"Original":"No ind.");
916 lcd_puts(0, line++, buf);
918 x = (control >> 12) & 15;
919 snprintf(buf, sizeof(buf), "Source: %d", x);
920 lcd_puts(0, line++, buf);
922 x = (control >> 8) & 15;
923 switch(x)
925 case 0:
926 s = "Unspecified";
927 break;
928 case 8:
929 s = "A (Left)";
930 break;
931 case 4:
932 s = "B (Right)";
933 break;
934 default:
935 s = "";
936 break;
938 snprintf(buf, sizeof(buf), "Channel: %d (%s)", x, s);
939 lcd_puts(0, line++, buf);
941 x = (control >> 4) & 15;
942 switch(x)
944 case 0:
945 s = "44.1kHz";
946 break;
947 case 0x4:
948 s = "48kHz";
949 break;
950 case 0xc:
951 s = "32kHz";
952 break;
954 snprintf(buf, sizeof(buf), "Frequency: %d (%s)", x, s);
955 lcd_puts(0, line++, buf);
957 x = (control >> 2) & 3;
958 snprintf(buf, sizeof(buf), "Clock accuracy: %d", x);
959 lcd_puts(0, line++, buf);
960 line++;
962 #ifndef SIMULATOR
963 snprintf(buf, sizeof(buf), "Measured freq: %ldHz",
964 spdif_measure_frequency());
965 lcd_puts(0, line++, buf);
966 #endif
968 lcd_update();
970 if (action_userabort(HZ/10))
971 break;
974 spdif_set_output_source(spdif_source IF_SPDIF_POWER_(, spdif_src_on));
976 #ifdef HAVE_SPDIF_POWER
977 spdif_power_enable(global_settings.spdif_enable);
978 #endif
980 return false;
982 #endif /* CPU_COLDFIRE */
984 #ifndef SIMULATOR
985 #ifdef HAVE_LCD_BITMAP
986 /* button definitions */
987 #if (CONFIG_KEYPAD == IRIVER_H100_PAD) || \
988 (CONFIG_KEYPAD == IRIVER_H300_PAD)
989 # define DEBUG_CANCEL BUTTON_OFF
991 #elif CONFIG_KEYPAD == RECORDER_PAD
992 # define DEBUG_CANCEL BUTTON_OFF
994 #elif CONFIG_KEYPAD == ONDIO_PAD
995 # define DEBUG_CANCEL BUTTON_MENU
997 #elif (CONFIG_KEYPAD == IPOD_1G2G_PAD) || \
998 (CONFIG_KEYPAD == IPOD_3G_PAD) || \
999 (CONFIG_KEYPAD == IPOD_4G_PAD)
1000 # define DEBUG_CANCEL BUTTON_MENU
1002 #elif CONFIG_KEYPAD == IRIVER_IFP7XX_PAD
1003 # define DEBUG_CANCEL BUTTON_PLAY
1005 #elif CONFIG_KEYPAD == IAUDIO_X5M5_PAD
1006 # define DEBUG_CANCEL BUTTON_REC
1008 #elif (CONFIG_KEYPAD == IAUDIO_M3_PAD)
1009 # define DEBUG_CANCEL BUTTON_RC_REC
1011 #elif (CONFIG_KEYPAD == IRIVER_H10_PAD)
1012 # define DEBUG_CANCEL BUTTON_REW
1014 #elif (CONFIG_KEYPAD == MROBE100_PAD)
1015 # define DEBUG_CANCEL BUTTON_MENU
1017 #elif (CONFIG_KEYPAD == SANSA_E200_PAD) || \
1018 (CONFIG_KEYPAD == SANSA_C200_PAD)
1019 # define DEBUG_CANCEL BUTTON_LEFT
1020 #endif /* key definitions */
1022 /* Test code!!! */
1023 bool dbg_ports(void)
1025 #if CONFIG_CPU == SH7034
1026 char buf[32];
1027 int adc_battery_voltage, adc_battery_level;
1029 lcd_setfont(FONT_SYSFIXED);
1030 lcd_setmargins(0, 0);
1031 lcd_clear_display();
1033 while(1)
1035 snprintf(buf, 32, "PADR: %04x", (unsigned short)PADR);
1036 lcd_puts(0, 0, buf);
1037 snprintf(buf, 32, "PBDR: %04x", (unsigned short)PBDR);
1038 lcd_puts(0, 1, buf);
1040 snprintf(buf, 32, "AN0: %03x AN4: %03x", adc_read(0), adc_read(4));
1041 lcd_puts(0, 2, buf);
1042 snprintf(buf, 32, "AN1: %03x AN5: %03x", adc_read(1), adc_read(5));
1043 lcd_puts(0, 3, buf);
1044 snprintf(buf, 32, "AN2: %03x AN6: %03x", adc_read(2), adc_read(6));
1045 lcd_puts(0, 4, buf);
1046 snprintf(buf, 32, "AN3: %03x AN7: %03x", adc_read(3), adc_read(7));
1047 lcd_puts(0, 5, buf);
1049 battery_read_info(&adc_battery_voltage, &adc_battery_level);
1050 snprintf(buf, 32, "Batt: %d.%03dV %d%% ", adc_battery_voltage / 1000,
1051 adc_battery_voltage % 1000, adc_battery_level);
1052 lcd_puts(0, 6, buf);
1054 lcd_update();
1055 if (button_get_w_tmo(HZ/10) == (DEBUG_CANCEL|BUTTON_REL))
1056 return false;
1058 #elif defined(CPU_COLDFIRE)
1059 unsigned int gpio_out;
1060 unsigned int gpio1_out;
1061 unsigned int gpio_read;
1062 unsigned int gpio1_read;
1063 unsigned int gpio_function;
1064 unsigned int gpio1_function;
1065 unsigned int gpio_enable;
1066 unsigned int gpio1_enable;
1067 int adc_buttons, adc_remote;
1068 int adc_battery_voltage, adc_battery_level;
1069 char buf[128];
1070 int line;
1072 lcd_setmargins(0, 0);
1073 lcd_clear_display();
1074 lcd_setfont(FONT_SYSFIXED);
1076 while(1)
1078 line = 0;
1079 gpio_read = GPIO_READ;
1080 gpio1_read = GPIO1_READ;
1081 gpio_out = GPIO_OUT;
1082 gpio1_out = GPIO1_OUT;
1083 gpio_function = GPIO_FUNCTION;
1084 gpio1_function = GPIO1_FUNCTION;
1085 gpio_enable = GPIO_ENABLE;
1086 gpio1_enable = GPIO1_ENABLE;
1088 snprintf(buf, sizeof(buf), "GPIO_READ: %08x", gpio_read);
1089 lcd_puts(0, line++, buf);
1090 snprintf(buf, sizeof(buf), "GPIO_OUT: %08x", gpio_out);
1091 lcd_puts(0, line++, buf);
1092 snprintf(buf, sizeof(buf), "GPIO_FUNC: %08x", gpio_function);
1093 lcd_puts(0, line++, buf);
1094 snprintf(buf, sizeof(buf), "GPIO_ENA: %08x", gpio_enable);
1095 lcd_puts(0, line++, buf);
1097 snprintf(buf, sizeof(buf), "GPIO1_READ: %08x", gpio1_read);
1098 lcd_puts(0, line++, buf);
1099 snprintf(buf, sizeof(buf), "GPIO1_OUT: %08x", gpio1_out);
1100 lcd_puts(0, line++, buf);
1101 snprintf(buf, sizeof(buf), "GPIO1_FUNC: %08x", gpio1_function);
1102 lcd_puts(0, line++, buf);
1103 snprintf(buf, sizeof(buf), "GPIO1_ENA: %08x", gpio1_enable);
1104 lcd_puts(0, line++, buf);
1106 adc_buttons = adc_read(ADC_BUTTONS);
1107 adc_remote = adc_read(ADC_REMOTE);
1108 battery_read_info(&adc_battery_voltage, &adc_battery_level);
1109 #if defined(IAUDIO_X5) || defined(IAUDIO_M5) || defined(IRIVER_H300_SERIES)
1110 snprintf(buf, sizeof(buf), "ADC_BUTTONS (%c): %02x",
1111 button_scan_enabled() ? '+' : '-', adc_buttons);
1112 #else
1113 snprintf(buf, sizeof(buf), "ADC_BUTTONS: %02x", adc_buttons);
1114 #endif
1115 lcd_puts(0, line++, buf);
1116 #if defined(IAUDIO_X5) || defined(IAUDIO_M5)
1117 snprintf(buf, sizeof(buf), "ADC_REMOTE (%c): %02x",
1118 remote_detect() ? '+' : '-', adc_remote);
1119 #else
1120 snprintf(buf, sizeof(buf), "ADC_REMOTE: %02x", adc_remote);
1121 #endif
1122 lcd_puts(0, line++, buf);
1123 #if defined(IRIVER_H100_SERIES) || defined(IRIVER_H300_SERIES)
1124 snprintf(buf, sizeof(buf), "ADC_REMOTEDETECT: %02x",
1125 adc_read(ADC_REMOTEDETECT));
1126 lcd_puts(0, line++, buf);
1127 #endif
1129 snprintf(buf, 32, "Batt: %d.%03dV %d%% ", adc_battery_voltage / 1000,
1130 adc_battery_voltage % 1000, adc_battery_level);
1131 lcd_puts(0, line++, buf);
1133 #if defined(IRIVER_H100_SERIES) || defined(IRIVER_H300_SERIES)
1134 snprintf(buf, sizeof(buf), "remotetype: %d", remote_type());
1135 lcd_puts(0, line++, buf);
1136 #endif
1138 lcd_update();
1139 if (button_get_w_tmo(HZ/10) == (DEBUG_CANCEL|BUTTON_REL))
1140 return false;
1143 #elif defined(CPU_PP502x)
1145 char buf[128];
1146 int line;
1148 lcd_setmargins(0, 0);
1149 lcd_clear_display();
1150 lcd_setfont(FONT_SYSFIXED);
1152 while(1)
1154 line = 0;
1155 lcd_puts(0, line++, "GPIO STATES:");
1156 snprintf(buf, sizeof(buf), "A: %02x E: %02x I: %02x",
1157 (unsigned int)GPIOA_INPUT_VAL,
1158 (unsigned int)GPIOE_INPUT_VAL,
1159 (unsigned int)GPIOI_INPUT_VAL);
1160 lcd_puts(0, line++, buf);
1161 snprintf(buf, sizeof(buf), "B: %02x F: %02x J: %02x",
1162 (unsigned int)GPIOB_INPUT_VAL,
1163 (unsigned int)GPIOF_INPUT_VAL,
1164 (unsigned int)GPIOJ_INPUT_VAL);
1165 lcd_puts(0, line++, buf);
1166 snprintf(buf, sizeof(buf), "C: %02x G: %02x K: %02x",
1167 (unsigned int)GPIOC_INPUT_VAL,
1168 (unsigned int)GPIOG_INPUT_VAL,
1169 (unsigned int)GPIOK_INPUT_VAL);
1170 lcd_puts(0, line++, buf);
1171 snprintf(buf, sizeof(buf), "D: %02x H: %02x L: %02x",
1172 (unsigned int)GPIOD_INPUT_VAL,
1173 (unsigned int)GPIOH_INPUT_VAL,
1174 (unsigned int)GPIOL_INPUT_VAL);
1175 lcd_puts(0, line++, buf);
1176 line++;
1177 snprintf(buf, sizeof(buf), "GPO32_VAL: %08lx", GPO32_VAL);
1178 lcd_puts(0, line++, buf);
1179 snprintf(buf, sizeof(buf), "GPO32_EN: %08lx", GPO32_ENABLE);
1180 lcd_puts(0, line++, buf);
1181 snprintf(buf, sizeof(buf), "DEV_EN: %08lx", DEV_EN);
1182 lcd_puts(0, line++, buf);
1183 snprintf(buf, sizeof(buf), "DEV_EN2: %08lx", DEV_EN2);
1184 lcd_puts(0, line++, buf);
1185 snprintf(buf, sizeof(buf), "DEV_EN3: %08lx", inl(0x60006044));
1186 lcd_puts(0, line++, buf); /* to be verified */
1187 snprintf(buf, sizeof(buf), "DEV_INIT1: %08lx", DEV_INIT1);
1188 lcd_puts(0, line++, buf);
1189 snprintf(buf, sizeof(buf), "DEV_INIT2: %08lx", DEV_INIT2);
1190 lcd_puts(0, line++, buf);
1192 #if defined(IRIVER_H10) || defined(IRIVER_H10_5GB)
1193 line++;
1194 snprintf(buf, sizeof(buf), "BATT: %03x UNK1: %03x",
1195 adc_read(ADC_BATTERY), adc_read(ADC_UNKNOWN_1));
1196 lcd_puts(0, line++, buf);
1197 snprintf(buf, sizeof(buf), "REM: %03x PAD: %03x",
1198 adc_read(ADC_REMOTE), adc_read(ADC_SCROLLPAD));
1199 lcd_puts(0, line++, buf);
1200 #elif defined(SANSA_E200)
1201 snprintf(buf, sizeof(buf), "ADC_BVDD: %4d", adc_read(ADC_BVDD));
1202 lcd_puts(0, line++, buf);
1203 snprintf(buf, sizeof(buf), "ADC_RTCSUP: %4d", adc_read(ADC_RTCSUP));
1204 lcd_puts(0, line++, buf);
1205 snprintf(buf, sizeof(buf), "ADC_UVDD: %4d", adc_read(ADC_UVDD));
1206 lcd_puts(0, line++, buf);
1207 snprintf(buf, sizeof(buf), "ADC_CHG_IN: %4d", adc_read(ADC_CHG_IN));
1208 lcd_puts(0, line++, buf);
1209 snprintf(buf, sizeof(buf), "ADC_CVDD: %4d", adc_read(ADC_CVDD));
1210 lcd_puts(0, line++, buf);
1211 snprintf(buf, sizeof(buf), "ADC_BATTEMP: %4d", adc_read(ADC_BATTEMP));
1212 lcd_puts(0, line++, buf);
1213 snprintf(buf, sizeof(buf), "ADC_MICSUP1: %4d", adc_read(ADC_MICSUP1));
1214 lcd_puts(0, line++, buf);
1215 snprintf(buf, sizeof(buf), "ADC_MICSUP2: %4d", adc_read(ADC_MICSUP2));
1216 lcd_puts(0, line++, buf);
1217 snprintf(buf, sizeof(buf), "ADC_VBE1: %4d", adc_read(ADC_VBE1));
1218 lcd_puts(0, line++, buf);
1219 snprintf(buf, sizeof(buf), "ADC_VBE2: %4d", adc_read(ADC_VBE2));
1220 lcd_puts(0, line++, buf);
1221 snprintf(buf, sizeof(buf), "ADC_I_MICSUP1:%4d", adc_read(ADC_I_MICSUP1));
1222 lcd_puts(0, line++, buf);
1223 snprintf(buf, sizeof(buf), "ADC_I_MICSUP2:%4d", adc_read(ADC_I_MICSUP2));
1224 lcd_puts(0, line++, buf);
1225 snprintf(buf, sizeof(buf), "ADC_VBAT: %4d", adc_read(ADC_VBAT));
1226 lcd_puts(0, line++, buf);
1227 snprintf(buf, sizeof(buf), "CHARGER: %02X/%02X", i2c_readbyte(AS3514_I2C_ADDR, AS3514_CHARGER), i2c_readbyte(AS3514_I2C_ADDR, AS3514_IRQ_ENRD0));
1228 lcd_puts(0, line++, buf);
1229 #endif
1230 lcd_update();
1231 if (button_get_w_tmo(HZ/10) == (DEBUG_CANCEL|BUTTON_REL))
1232 return false;
1235 #elif CONFIG_CPU == PP5002
1236 char buf[128];
1237 int line;
1239 lcd_setmargins(0, 0);
1240 lcd_clear_display();
1241 lcd_setfont(FONT_SYSFIXED);
1243 while(1)
1245 line = 0;
1246 snprintf(buf, sizeof(buf), "GPIO_A: %02x GPIO_B: %02x",
1247 (unsigned int)GPIOA_INPUT_VAL, (unsigned int)GPIOB_INPUT_VAL);
1248 lcd_puts(0, line++, buf);
1249 snprintf(buf, sizeof(buf), "GPIO_C: %02x GPIO_D: %02x",
1250 (unsigned int)GPIOC_INPUT_VAL, (unsigned int)GPIOD_INPUT_VAL);
1251 lcd_puts(0, line++, buf);
1253 snprintf(buf, sizeof(buf), "DEV_EN: %08lx", DEV_EN);
1254 lcd_puts(0, line++, buf);
1255 snprintf(buf, sizeof(buf), "CLOCK_ENABLE: %08lx", CLOCK_ENABLE);
1256 lcd_puts(0, line++, buf);
1257 snprintf(buf, sizeof(buf), "CLOCK_SOURCE: %08lx", CLOCK_SOURCE);
1258 lcd_puts(0, line++, buf);
1259 snprintf(buf, sizeof(buf), "PLL_CONTROL: %08lx", PLL_CONTROL);
1260 lcd_puts(0, line++, buf);
1261 snprintf(buf, sizeof(buf), "PLL_DIV: %08lx", PLL_DIV);
1262 lcd_puts(0, line++, buf);
1263 snprintf(buf, sizeof(buf), "PLL_MULT: %08lx", PLL_MULT);
1264 lcd_puts(0, line++, buf);
1265 snprintf(buf, sizeof(buf), "TIMING1_CTL: %08lx", TIMING1_CTL);
1266 lcd_puts(0, line++, buf);
1267 snprintf(buf, sizeof(buf), "TIMING2_CTL: %08lx", TIMING2_CTL);
1268 lcd_puts(0, line++, buf);
1270 lcd_update();
1271 if (button_get_w_tmo(HZ/10) == (DEBUG_CANCEL|BUTTON_REL))
1272 return false;
1274 #else
1275 return __dbg_ports();
1276 #endif /* CPU */
1277 return false;
1279 #else /* !HAVE_LCD_BITMAP */
1280 bool dbg_ports(void)
1282 char buf[32];
1283 int button;
1284 int adc_battery_voltage;
1285 int currval = 0;
1287 lcd_clear_display();
1289 while(1)
1291 switch(currval)
1293 case 0:
1294 snprintf(buf, 32, "PADR: %04x", (unsigned short)PADR);
1295 break;
1296 case 1:
1297 snprintf(buf, 32, "PBDR: %04x", (unsigned short)PBDR);
1298 break;
1299 case 2:
1300 snprintf(buf, 32, "AN0: %03x", adc_read(0));
1301 break;
1302 case 3:
1303 snprintf(buf, 32, "AN1: %03x", adc_read(1));
1304 break;
1305 case 4:
1306 snprintf(buf, 32, "AN2: %03x", adc_read(2));
1307 break;
1308 case 5:
1309 snprintf(buf, 32, "AN3: %03x", adc_read(3));
1310 break;
1311 case 6:
1312 snprintf(buf, 32, "AN4: %03x", adc_read(4));
1313 break;
1314 case 7:
1315 snprintf(buf, 32, "AN5: %03x", adc_read(5));
1316 break;
1317 case 8:
1318 snprintf(buf, 32, "AN6: %03x", adc_read(6));
1319 break;
1320 case 9:
1321 snprintf(buf, 32, "AN7: %03x", adc_read(7));
1322 break;
1323 break;
1325 lcd_puts(0, 0, buf);
1327 battery_read_info(&adc_battery_voltage, NULL);
1328 snprintf(buf, 32, "Batt: %d.%03dV", adc_battery_voltage / 1000,
1329 adc_battery_voltage % 1000);
1330 lcd_puts(0, 1, buf);
1331 lcd_update();
1333 button = get_action(CONTEXT_SETTINGS,HZ/5);
1335 switch(button)
1337 case ACTION_STD_CANCEL:
1338 return false;
1340 case ACTION_SETTINGS_DEC:
1341 currval--;
1342 if(currval < 0)
1343 currval = 9;
1344 break;
1346 case ACTION_SETTINGS_INC:
1347 currval++;
1348 if(currval > 9)
1349 currval = 0;
1350 break;
1353 return false;
1355 #endif /* !HAVE_LCD_BITMAP */
1356 #endif /* !SIMULATOR */
1358 #if (CONFIG_RTC == RTC_PCF50605) && !defined(SIMULATOR)
1359 static bool dbg_pcf(void)
1361 char buf[128];
1362 int line;
1364 #ifdef HAVE_LCD_BITMAP
1365 lcd_setmargins(0, 0);
1366 lcd_setfont(FONT_SYSFIXED);
1367 #endif
1368 lcd_clear_display();
1370 while(1)
1372 line = 0;
1374 snprintf(buf, sizeof(buf), "DCDC1: %02x", pcf50605_read(0x1b));
1375 lcd_puts(0, line++, buf);
1376 snprintf(buf, sizeof(buf), "DCDC2: %02x", pcf50605_read(0x1c));
1377 lcd_puts(0, line++, buf);
1378 snprintf(buf, sizeof(buf), "DCDC3: %02x", pcf50605_read(0x1d));
1379 lcd_puts(0, line++, buf);
1380 snprintf(buf, sizeof(buf), "DCDC4: %02x", pcf50605_read(0x1e));
1381 lcd_puts(0, line++, buf);
1382 snprintf(buf, sizeof(buf), "DCDEC1: %02x", pcf50605_read(0x1f));
1383 lcd_puts(0, line++, buf);
1384 snprintf(buf, sizeof(buf), "DCDEC2: %02x", pcf50605_read(0x20));
1385 lcd_puts(0, line++, buf);
1386 snprintf(buf, sizeof(buf), "DCUDC1: %02x", pcf50605_read(0x21));
1387 lcd_puts(0, line++, buf);
1388 snprintf(buf, sizeof(buf), "DCUDC2: %02x", pcf50605_read(0x22));
1389 lcd_puts(0, line++, buf);
1390 snprintf(buf, sizeof(buf), "IOREGC: %02x", pcf50605_read(0x23));
1391 lcd_puts(0, line++, buf);
1392 snprintf(buf, sizeof(buf), "D1REGC: %02x", pcf50605_read(0x24));
1393 lcd_puts(0, line++, buf);
1394 snprintf(buf, sizeof(buf), "D2REGC: %02x", pcf50605_read(0x25));
1395 lcd_puts(0, line++, buf);
1396 snprintf(buf, sizeof(buf), "D3REGC: %02x", pcf50605_read(0x26));
1397 lcd_puts(0, line++, buf);
1398 snprintf(buf, sizeof(buf), "LPREG1: %02x", pcf50605_read(0x27));
1399 lcd_puts(0, line++, buf);
1401 lcd_update();
1402 if (button_get_w_tmo(HZ/10) == (DEBUG_CANCEL|BUTTON_REL))
1404 return false;
1408 return false;
1410 #endif
1412 #ifdef HAVE_ADJUSTABLE_CPU_FREQ
1413 static bool dbg_cpufreq(void)
1415 char buf[128];
1416 int line;
1417 int button;
1419 #ifdef HAVE_LCD_BITMAP
1420 lcd_setmargins(0, 0);
1421 lcd_setfont(FONT_SYSFIXED);
1422 #endif
1423 lcd_clear_display();
1425 while(1)
1427 line = 0;
1429 snprintf(buf, sizeof(buf), "Frequency: %ld", FREQ);
1430 lcd_puts(0, line++, buf);
1432 snprintf(buf, sizeof(buf), "boost_counter: %d", get_cpu_boost_counter());
1433 lcd_puts(0, line++, buf);
1435 lcd_update();
1436 button = get_action(CONTEXT_STD,HZ/10);
1438 switch(button)
1440 case ACTION_STD_PREV:
1441 cpu_boost(true);
1442 break;
1444 case ACTION_STD_NEXT:
1445 cpu_boost(false);
1446 break;
1448 case ACTION_STD_OK:
1449 while (get_cpu_boost_counter() > 0)
1450 cpu_boost(false);
1451 set_cpu_frequency(CPUFREQ_DEFAULT);
1452 break;
1454 case ACTION_STD_CANCEL:
1455 return false;
1459 return false;
1461 #endif /* HAVE_ADJUSTABLE_CPU_FREQ */
1463 #if defined(HAVE_TSC2100) && !defined(SIMULATOR)
1464 #include "tsc2100.h"
1465 char *itob(int n, int len)
1467 static char binary[64];
1468 int i,j;
1469 for (i=1, j=0;i<=len;i++)
1471 binary[j++] = n&(1<<(len-i))?'1':'0';
1472 if (i%4 == 0)
1473 binary[j++] = ' ';
1475 binary[j] = '\0';
1476 return binary;
1478 static char* tsc2100_debug_getname(int selected_item, void * data,
1479 char *buffer, size_t buffer_len)
1481 int *page = (int*)data;
1482 bool reserved = false;
1483 switch (*page)
1485 case 0:
1486 if ((selected_item > 0x0a) ||
1487 (selected_item == 0x04) ||
1488 (selected_item == 0x08))
1489 reserved = true;
1490 break;
1491 case 1:
1492 if ((selected_item > 0x05) ||
1493 (selected_item == 0x02))
1494 reserved = true;
1495 break;
1496 case 2:
1497 if (selected_item > 0x1e)
1498 reserved = true;
1499 break;
1501 if (reserved)
1502 snprintf(buffer, buffer_len, "%02x: RESERVED", selected_item);
1503 else
1504 snprintf(buffer, buffer_len, "%02x: %s", selected_item,
1505 itob(tsc2100_readreg(*page, selected_item)&0xffff,16));
1506 return buffer;
1508 static int tsc2100debug_action_callback(int action, struct gui_synclist *lists)
1510 int *page = (int*)lists->data;
1511 if (action == ACTION_STD_OK)
1513 *page = (*page+1)%3;
1514 snprintf(lists->title, 32,
1515 "tsc2100 registers - Page %d", *page);
1516 return ACTION_REDRAW;
1518 return action;
1520 bool tsc2100_debug(void)
1522 int page = 0;
1523 char title[32] = "tsc2100 registers - Page 0";
1524 struct simplelist_info info;
1525 simplelist_info_init(&info, title, 32, &page);
1526 info.timeout = HZ/100;
1527 info.get_name = tsc2100_debug_getname;
1528 info.action_callback= tsc2100debug_action_callback;
1529 return simplelist_show_list(&info);
1531 #endif
1532 #ifndef SIMULATOR
1533 #ifdef HAVE_LCD_BITMAP
1535 * view_battery() shows a automatically scaled graph of the battery voltage
1536 * over time. Usable for estimating battery life / charging rate.
1537 * The power_history array is updated in power_thread of powermgmt.c.
1540 #define BAT_LAST_VAL MIN(LCD_WIDTH, POWER_HISTORY_LEN)
1541 #define BAT_YSPACE (LCD_HEIGHT - 20)
1543 static bool view_battery(void)
1545 int view = 0;
1546 int i, x, y;
1547 unsigned short maxv, minv;
1548 char buf[32];
1550 lcd_setmargins(0, 0);
1551 lcd_setfont(FONT_SYSFIXED);
1553 while(1)
1555 lcd_clear_display();
1556 switch (view) {
1557 case 0: /* voltage history graph */
1558 /* Find maximum and minimum voltage for scaling */
1559 minv = power_history[0];
1560 maxv = minv + 1;
1561 for (i = 1; i < BAT_LAST_VAL && power_history[i]; i++) {
1562 if (power_history[i] > maxv)
1563 maxv = power_history[i];
1564 if (power_history[i] < minv)
1565 minv = power_history[i];
1568 snprintf(buf, 30, "Battery %d.%03d", power_history[0] / 1000,
1569 power_history[0] % 1000);
1570 lcd_puts(0, 0, buf);
1571 snprintf(buf, 30, "scale %d.%03d-%d.%03dV",
1572 minv / 1000, minv % 1000, maxv / 1000, maxv % 1000);
1573 lcd_puts(0, 1, buf);
1575 x = 0;
1576 for (i = BAT_LAST_VAL - 1; i >= 0; i--) {
1577 y = (power_history[i] - minv) * BAT_YSPACE / (maxv - minv);
1578 lcd_set_drawmode(DRMODE_SOLID|DRMODE_INVERSEVID);
1579 lcd_vline(x, LCD_HEIGHT-1, 20);
1580 lcd_set_drawmode(DRMODE_SOLID);
1581 lcd_vline(x, LCD_HEIGHT-1,
1582 MIN(MAX(LCD_HEIGHT-1 - y, 20), LCD_HEIGHT-1));
1583 x++;
1586 break;
1588 case 1: /* status: */
1589 lcd_puts(0, 0, "Power status:");
1591 battery_read_info(&y, NULL);
1592 snprintf(buf, 30, "Battery: %d.%03d V", y / 1000, y % 1000);
1593 lcd_puts(0, 1, buf);
1594 #ifdef ADC_EXT_POWER
1595 y = (adc_read(ADC_EXT_POWER) * EXT_SCALE_FACTOR) / 1000;
1596 snprintf(buf, 30, "External: %d.%03d V", y / 1000, y % 1000);
1597 lcd_puts(0, 2, buf);
1598 #endif
1599 #if CONFIG_CHARGING
1600 #if CONFIG_CHARGING == CHARGING_CONTROL
1601 snprintf(buf, 30, "Chgr: %s %s",
1602 charger_inserted() ? "present" : "absent",
1603 charger_enabled ? "on" : "off");
1604 lcd_puts(0, 3, buf);
1605 snprintf(buf, 30, "short delta: %d", short_delta);
1606 lcd_puts(0, 5, buf);
1607 snprintf(buf, 30, "long delta: %d", long_delta);
1608 lcd_puts(0, 6, buf);
1609 lcd_puts(0, 7, power_message);
1610 snprintf(buf, 30, "USB Inserted: %s",
1611 usb_inserted() ? "yes" : "no");
1612 lcd_puts(0, 8, buf);
1613 #if defined IRIVER_H300_SERIES
1614 snprintf(buf, 30, "USB Charging Enabled: %s",
1615 usb_charging_enabled() ? "yes" : "no");
1616 lcd_puts(0, 9, buf);
1617 #endif
1618 #else /* CONFIG_CHARGING != CHARGING_CONTROL */
1619 #if defined IPOD_NANO || defined IPOD_VIDEO
1620 int usb_pwr = (GPIOL_INPUT_VAL & 0x10)?true:false;
1621 int ext_pwr = (GPIOL_INPUT_VAL & 0x08)?false:true;
1622 int dock = (GPIOA_INPUT_VAL & 0x10)?true:false;
1623 int charging = (GPIOB_INPUT_VAL & 0x01)?false:true;
1624 int headphone= (GPIOA_INPUT_VAL & 0x80)?true:false;
1626 snprintf(buf, 30, "USB pwr: %s",
1627 usb_pwr ? "present" : "absent");
1628 lcd_puts(0, 3, buf);
1629 snprintf(buf, 30, "EXT pwr: %s",
1630 ext_pwr ? "present" : "absent");
1631 lcd_puts(0, 4, buf);
1632 snprintf(buf, 30, "Battery: %s",
1633 charging ? "charging" : (usb_pwr||ext_pwr) ? "charged" : "discharging");
1634 lcd_puts(0, 5, buf);
1635 snprintf(buf, 30, "Dock mode: %s",
1636 dock ? "enabled" : "disabled");
1637 lcd_puts(0, 6, buf);
1638 snprintf(buf, 30, "Headphone: %s",
1639 headphone ? "connected" : "disconnected");
1640 lcd_puts(0, 7, buf);
1641 #else
1642 snprintf(buf, 30, "Charger: %s",
1643 charger_inserted() ? "present" : "absent");
1644 lcd_puts(0, 3, buf);
1645 #endif
1646 #endif /* CONFIG_CHARGING != CHARGING_CONTROL */
1647 #endif /* CONFIG_CHARGING */
1648 break;
1650 case 2: /* voltage deltas: */
1651 lcd_puts(0, 0, "Voltage deltas:");
1653 for (i = 0; i <= 6; i++) {
1654 y = power_history[i] - power_history[i+1];
1655 snprintf(buf, 30, "-%d min: %s%d.%03d V", i,
1656 (y < 0) ? "-" : "", ((y < 0) ? y * -1 : y) / 1000,
1657 ((y < 0) ? y * -1 : y ) % 1000);
1658 lcd_puts(0, i+1, buf);
1660 break;
1662 case 3: /* remaining time estimation: */
1664 #if CONFIG_CHARGING == CHARGING_CONTROL
1665 snprintf(buf, 30, "charge_state: %d", charge_state);
1666 lcd_puts(0, 0, buf);
1668 snprintf(buf, 30, "Cycle time: %d m", powermgmt_last_cycle_startstop_min);
1669 lcd_puts(0, 1, buf);
1671 snprintf(buf, 30, "Lvl@cyc st: %d%%", powermgmt_last_cycle_level);
1672 lcd_puts(0, 2, buf);
1674 snprintf(buf, 30, "P=%2d I=%2d", pid_p, pid_i);
1675 lcd_puts(0, 3, buf);
1677 snprintf(buf, 30, "Trickle sec: %d/60", trickle_sec);
1678 lcd_puts(0, 4, buf);
1679 #endif /* CONFIG_CHARGING == CHARGING_CONTROL */
1681 snprintf(buf, 30, "Last PwrHist: %d.%03dV",
1682 power_history[0] / 1000,
1683 power_history[0] % 1000);
1684 lcd_puts(0, 5, buf);
1686 snprintf(buf, 30, "battery level: %d%%", battery_level());
1687 lcd_puts(0, 6, buf);
1689 snprintf(buf, 30, "Est. remain: %d m", battery_time());
1690 lcd_puts(0, 7, buf);
1691 break;
1694 lcd_update();
1696 switch(get_action(CONTEXT_STD,HZ/2))
1698 case ACTION_STD_PREV:
1699 if (view)
1700 view--;
1701 break;
1703 case ACTION_STD_NEXT:
1704 if (view < 3)
1705 view++;
1706 break;
1708 case ACTION_STD_CANCEL:
1709 return false;
1712 return false;
1715 #endif /* HAVE_LCD_BITMAP */
1716 #endif
1718 #ifndef SIMULATOR
1719 #if defined(HAVE_MMC) || defined(HAVE_ATA_SD)
1720 #if defined(HAVE_MMC)
1721 #define CARDTYPE "MMC"
1722 #else
1723 #define CARDTYPE "microSD"
1724 #endif
1725 static int disk_callback(int btn, struct gui_synclist *lists)
1727 tCardInfo *card;
1728 int *cardnum = (int*)lists->data;
1729 unsigned char card_name[7];
1730 unsigned char pbuf[32];
1731 char *title = lists->title;
1732 static const unsigned char i_vmin[] = { 0, 1, 5, 10, 25, 35, 60, 100 };
1733 static const unsigned char i_vmax[] = { 1, 5, 10, 25, 35, 45, 80, 200 };
1734 static const unsigned char *kbit_units[] = { "kBit/s", "MBit/s", "GBit/s" };
1735 static const unsigned char *nsec_units[] = { "ns", "µs", "ms" };
1736 static const char *spec_vers[] = { "1.0-1.2", "1.4", "2.0-2.2",
1737 "3.1-3.31", "4.0" };
1738 if ((btn == ACTION_STD_OK) || (btn == SYS_FS_CHANGED) || (btn == ACTION_REDRAW))
1740 #ifdef HAVE_HOTSWAP
1741 if (btn == ACTION_STD_OK)
1743 *cardnum ^= 0x1; /* change cards */
1745 #endif
1747 simplelist_set_line_count(0);
1749 card = card_get_info(*cardnum);
1751 if (card->initialized > 0)
1753 card_name[6] = '\0';
1754 strncpy(card_name, ((unsigned char*)card->cid) + 3, 6);
1755 simplelist_addline(SIMPLELIST_ADD_LINE,
1756 "%s Rev %d.%d", card_name,
1757 (int) card_extract_bits(card->cid, 72, 4),
1758 (int) card_extract_bits(card->cid, 76, 4));
1759 simplelist_addline(SIMPLELIST_ADD_LINE,
1760 "Prod: %d/%d",
1761 (int) card_extract_bits(card->cid, 112, 4),
1762 (int) card_extract_bits(card->cid, 116, 4) + 1997);
1763 simplelist_addline(SIMPLELIST_ADD_LINE,
1764 "Ser#: 0x%08lx",
1765 card_extract_bits(card->cid, 80, 32));
1766 simplelist_addline(SIMPLELIST_ADD_LINE,
1767 "M=%02x, O=%04x",
1768 (int) card_extract_bits(card->cid, 0, 8),
1769 (int) card_extract_bits(card->cid, 8, 16));
1770 int temp = card_extract_bits(card->csd, 2, 4);
1771 simplelist_addline(SIMPLELIST_ADD_LINE,
1772 CARDTYPE " v%s", temp < 5 ?
1773 spec_vers[temp] : "?.?");
1774 simplelist_addline(SIMPLELIST_ADD_LINE,
1775 "Blocks: 0x%06lx", card->numblocks);
1776 simplelist_addline(SIMPLELIST_ADD_LINE,
1777 "Blksz.: %d P:%c%c", card->blocksize,
1778 card_extract_bits(card->csd, 48, 1) ? 'R' : '-',
1779 card_extract_bits(card->csd, 106, 1) ? 'W' : '-');
1780 output_dyn_value(pbuf, sizeof pbuf, card->speed / 1000,
1781 kbit_units, false);
1782 simplelist_addline(SIMPLELIST_ADD_LINE,
1783 "Speed: %s", pbuf);
1784 output_dyn_value(pbuf, sizeof pbuf, card->tsac,
1785 nsec_units, false);
1786 simplelist_addline(SIMPLELIST_ADD_LINE,
1787 "Tsac: %s", pbuf);
1788 simplelist_addline(SIMPLELIST_ADD_LINE,
1789 "Nsac: %d clk", card->nsac);
1790 simplelist_addline(SIMPLELIST_ADD_LINE,
1791 "R2W: *%d", card->r2w_factor);
1792 simplelist_addline(SIMPLELIST_ADD_LINE,
1793 "IRmax: %d..%d mA",
1794 i_vmin[card_extract_bits(card->csd, 66, 3)],
1795 i_vmax[card_extract_bits(card->csd, 69, 3)]);
1796 simplelist_addline(SIMPLELIST_ADD_LINE,
1797 "IWmax: %d..%d mA",
1798 i_vmin[card_extract_bits(card->csd, 72, 3)],
1799 i_vmax[card_extract_bits(card->csd, 75, 3)]);
1801 else if (card->initialized == 0)
1803 simplelist_addline(SIMPLELIST_ADD_LINE, "Not Found!");
1805 #ifndef HAVE_MMC
1806 else /* card->initialized < 0 */
1808 simplelist_addline(SIMPLELIST_ADD_LINE, "Init Error! (%d)", card->initialized);
1810 #endif
1811 snprintf(title, 16, "[" CARDTYPE " %d]", *cardnum);
1812 gui_synclist_set_title(lists, title, Icon_NOICON);
1813 gui_synclist_set_nb_items(lists, simplelist_get_line_count());
1814 gui_synclist_select_item(lists, 0);
1815 btn = ACTION_REDRAW;
1817 return btn;
1819 #else /* !defined(HAVE_MMC) && !defined(HAVE_ATA_SD) */
1820 static int disk_callback(int btn, struct gui_synclist *lists)
1822 (void)lists;
1823 int i;
1824 char buf[128];
1825 unsigned short* identify_info = ata_get_identify();
1826 bool timing_info_present = false;
1827 (void)btn;
1829 simplelist_set_line_count(0);
1831 for (i=0; i < 20; i++)
1832 ((unsigned short*)buf)[i]=htobe16(identify_info[i+27]);
1833 buf[40]=0;
1834 /* kill trailing space */
1835 for (i=39; i && buf[i]==' '; i--)
1836 buf[i] = 0;
1837 simplelist_addline(SIMPLELIST_ADD_LINE, "Model: %s", buf);
1838 for (i=0; i < 4; i++)
1839 ((unsigned short*)buf)[i]=htobe16(identify_info[i+23]);
1840 buf[8]=0;
1841 simplelist_addline(SIMPLELIST_ADD_LINE,
1842 "Firmware: %s", buf);
1843 snprintf(buf, sizeof buf, "%ld MB",
1844 ((unsigned long)identify_info[61] << 16 |
1845 (unsigned long)identify_info[60]) / 2048 );
1846 simplelist_addline(SIMPLELIST_ADD_LINE,
1847 "Size: %s", buf);
1848 unsigned long free;
1849 fat_size( IF_MV2(0,) NULL, &free );
1850 simplelist_addline(SIMPLELIST_ADD_LINE,
1851 "Free: %ld MB", free / 1024);
1852 simplelist_addline(SIMPLELIST_ADD_LINE,
1853 "Spinup time: %d ms", ata_spinup_time * (1000/HZ));
1854 i = identify_info[83] & (1<<3);
1855 simplelist_addline(SIMPLELIST_ADD_LINE,
1856 "Power mgmt: %s", i ? "enabled" : "unsupported");
1857 i = identify_info[83] & (1<<9);
1858 simplelist_addline(SIMPLELIST_ADD_LINE,
1859 "Noise mgmt: %s", i ? "enabled" : "unsupported");
1860 i = identify_info[82] & (1<<6);
1861 simplelist_addline(SIMPLELIST_ADD_LINE,
1862 "Read-ahead: %s", i ? "enabled" : "unsupported");
1863 timing_info_present = identify_info[53] & (1<<1);
1864 if(timing_info_present) {
1865 char pio3[2], pio4[2];pio3[1] = 0;
1866 pio4[1] = 0;
1867 pio3[0] = (identify_info[64] & (1<<0)) ? '3' : 0;
1868 pio4[0] = (identify_info[64] & (1<<1)) ? '4' : 0;
1869 simplelist_addline(SIMPLELIST_ADD_LINE,
1870 "PIO modes: 0 1 2 %s %s", pio3, pio4);
1872 else {
1873 simplelist_addline(SIMPLELIST_ADD_LINE,
1874 "No PIO mode info");
1876 timing_info_present = identify_info[53] & (1<<1);
1877 if(timing_info_present) {
1878 simplelist_addline(SIMPLELIST_ADD_LINE,
1879 "Cycle times %dns/%dns",
1880 identify_info[67],
1881 identify_info[68] );
1882 } else {
1883 simplelist_addline(SIMPLELIST_ADD_LINE,
1884 "No timing info");
1886 #if defined (TOSHIBA_GIGABEAT_F) || defined (TOSHIBA_GIGABEAT_S)
1887 if (identify_info[63] & (1<<0)) {
1888 char mdma0[2], mdma1[2], mdma2[2];
1889 mdma0[1] = mdma1[1] = mdma2[1] = 0;
1890 mdma0[0] = (identify_info[63] & (1<<0)) ? '0' : 0;
1891 mdma1[0] = (identify_info[63] & (1<<1)) ? '1' : 0;
1892 mdma2[0] = (identify_info[63] & (1<<2)) ? '2' : 0;
1893 simplelist_addline(SIMPLELIST_ADD_LINE,
1894 "MDMA modes: %s %s %s", mdma0, mdma1, mdma2);
1895 simplelist_addline(SIMPLELIST_ADD_LINE,
1896 "MDMA Cycle times %dns/%dns",
1897 identify_info[65],
1898 identify_info[66] );
1900 else {
1901 simplelist_addline(SIMPLELIST_ADD_LINE,
1902 "No MDMA mode info");
1904 if (identify_info[88] & (1<<0)) {
1905 char udma0[2], udma1[2], udma2[2], udma3[2], udma4[2], udma5[2];
1906 udma0[1] = udma1[1] = udma2[1] = udma3[1] = udma4[1] = udma5[1] = 0;
1907 udma0[0] = (identify_info[88] & (1<<0)) ? '0' : 0;
1908 udma1[0] = (identify_info[88] & (1<<1)) ? '1' : 0;
1909 udma2[0] = (identify_info[88] & (1<<2)) ? '2' : 0;
1910 udma3[0] = (identify_info[88] & (1<<3)) ? '3' : 0;
1911 udma4[0] = (identify_info[88] & (1<<4)) ? '4' : 0;
1912 udma5[0] = (identify_info[88] & (1<<5)) ? '5' : 0;
1913 simplelist_addline(SIMPLELIST_ADD_LINE,
1914 "UDMA modes: %s %s %s %s %s %s", udma0, udma1, udma2,
1915 udma3, udma4, udma5);
1917 else {
1918 simplelist_addline(SIMPLELIST_ADD_LINE,
1919 "No UDMA mode info");
1921 #endif /* defined (TOSHIBA_GIGABEAT_F) || defined (TOSHIBA_GIGABEAT_S) */
1922 timing_info_present = identify_info[53] & (1<<1);
1923 if(timing_info_present) {
1924 i = identify_info[49] & (1<<11);
1925 simplelist_addline(SIMPLELIST_ADD_LINE,
1926 "IORDY support: %s", i ? "yes" : "no");
1927 i = identify_info[49] & (1<<10);
1928 simplelist_addline(SIMPLELIST_ADD_LINE,
1929 "IORDY disable: %s", i ? "yes" : "no");
1930 } else {
1931 simplelist_addline(SIMPLELIST_ADD_LINE,
1932 "No timing info");
1934 simplelist_addline(SIMPLELIST_ADD_LINE,
1935 "Cluster size: %d bytes", fat_get_cluster_size(IF_MV(0)));
1936 return btn;
1939 static bool dbg_identify_info(void)
1941 int fd = creat("/identify_info.bin");
1942 if(fd >= 0)
1944 #ifdef ROCKBOX_LITTLE_ENDIAN
1945 ecwrite(fd, ata_get_identify(), SECTOR_SIZE/2, "s", true);
1946 #else
1947 write(fd, ata_get_identify(), SECTOR_SIZE);
1948 #endif
1949 close(fd);
1951 return false;
1953 #endif /* !defined(HAVE_MMC) && !defined(HAVE_ATA_SD) */
1955 static bool dbg_disk_info(void)
1957 struct simplelist_info info;
1958 simplelist_info_init(&info, "Disk Info", 1, NULL);
1959 #if defined(HAVE_MMC) || defined(HAVE_ATA_SD)
1960 char title[16];
1961 int card = 0;
1962 info.callback_data = (void*)&card;
1963 info.title = title;
1964 #endif
1965 info.action_callback = disk_callback;
1966 info.hide_selection = true;
1967 info.scroll_all = true;
1968 return simplelist_show_list(&info);
1970 #endif /* !SIMULATOR */
1972 #ifdef HAVE_DIRCACHE
1973 static int dircache_callback(int btn, struct gui_synclist *lists)
1975 (void)btn; (void)lists;
1976 simplelist_set_line_count(0);
1977 simplelist_addline(SIMPLELIST_ADD_LINE, "Cache initialized: %s",
1978 dircache_is_enabled() ? "Yes" : "No");
1979 simplelist_addline(SIMPLELIST_ADD_LINE, "Cache size: %d B",
1980 dircache_get_cache_size());
1981 simplelist_addline(SIMPLELIST_ADD_LINE, "Last size: %d B",
1982 global_status.dircache_size);
1983 simplelist_addline(SIMPLELIST_ADD_LINE, "Limit: %d B",
1984 DIRCACHE_LIMIT);
1985 simplelist_addline(SIMPLELIST_ADD_LINE, "Reserve: %d/%d B",
1986 dircache_get_reserve_used(), DIRCACHE_RESERVE);
1987 simplelist_addline(SIMPLELIST_ADD_LINE, "Scanning took: %d s",
1988 dircache_get_build_ticks() / HZ);
1989 simplelist_addline(SIMPLELIST_ADD_LINE, "Entry count: %d",
1990 dircache_get_entry_count());
1991 return btn;
1994 static bool dbg_dircache_info(void)
1996 struct simplelist_info info;
1997 simplelist_info_init(&info, "Dircache Info", 7, NULL);
1998 info.action_callback = dircache_callback;
1999 info.hide_selection = true;
2000 info.scroll_all = true;
2001 return simplelist_show_list(&info);
2004 #endif /* HAVE_DIRCACHE */
2006 #ifdef HAVE_TAGCACHE
2007 static int database_callback(int btn, struct gui_synclist *lists)
2009 (void)lists;
2010 struct tagcache_stat *stat = tagcache_get_stat();
2011 static bool synced = false;
2013 simplelist_set_line_count(0);
2015 simplelist_addline(SIMPLELIST_ADD_LINE, "Initialized: %s",
2016 stat->initialized ? "Yes" : "No");
2017 simplelist_addline(SIMPLELIST_ADD_LINE, "DB Ready: %s",
2018 stat->ready ? "Yes" : "No");
2019 simplelist_addline(SIMPLELIST_ADD_LINE, "RAM Cache: %s",
2020 stat->ramcache ? "Yes" : "No");
2021 simplelist_addline(SIMPLELIST_ADD_LINE, "RAM: %d/%d B",
2022 stat->ramcache_used, stat->ramcache_allocated);
2023 simplelist_addline(SIMPLELIST_ADD_LINE, "Progress: %d%% (%d entries)",
2024 stat->progress, stat->processed_entries);
2025 simplelist_addline(SIMPLELIST_ADD_LINE, "Curfile: %s",
2026 stat->curentry ? stat->curentry : "---");
2027 simplelist_addline(SIMPLELIST_ADD_LINE, "Commit step: %d",
2028 stat->commit_step);
2029 simplelist_addline(SIMPLELIST_ADD_LINE, "Commit delayed: %s",
2030 stat->commit_delayed ? "Yes" : "No");
2032 simplelist_addline(SIMPLELIST_ADD_LINE, "Queue length: %d",
2033 stat->queue_length);
2035 if (synced)
2037 synced = false;
2038 tagcache_screensync_event();
2041 if (!btn && stat->curentry)
2043 synced = true;
2044 return ACTION_REDRAW;
2047 if (btn == ACTION_STD_CANCEL)
2048 tagcache_screensync_enable(false);
2050 return btn;
2052 static bool dbg_tagcache_info(void)
2054 struct simplelist_info info;
2055 simplelist_info_init(&info, "Database Info", 8, NULL);
2056 info.action_callback = database_callback;
2057 info.hide_selection = true;
2058 info.scroll_all = true;
2060 /* Don't do nonblock here, must give enough processing time
2061 for tagcache thread. */
2062 /* info.timeout = TIMEOUT_NOBLOCK; */
2063 info.timeout = 1;
2064 tagcache_screensync_enable(true);
2065 return simplelist_show_list(&info);
2067 #endif
2069 #if CONFIG_CPU == SH7034
2070 static bool dbg_save_roms(void)
2072 int fd;
2073 int oldmode = system_memory_guard(MEMGUARD_NONE);
2075 fd = creat("/internal_rom_0000-FFFF.bin");
2076 if(fd >= 0)
2078 write(fd, (void *)0, 0x10000);
2079 close(fd);
2082 fd = creat("/internal_rom_2000000-203FFFF.bin");
2083 if(fd >= 0)
2085 write(fd, (void *)0x2000000, 0x40000);
2086 close(fd);
2089 system_memory_guard(oldmode);
2090 return false;
2092 #elif defined CPU_COLDFIRE
2093 static bool dbg_save_roms(void)
2095 int fd;
2096 int oldmode = system_memory_guard(MEMGUARD_NONE);
2098 #if defined(IRIVER_H100_SERIES)
2099 fd = creat("/internal_rom_000000-1FFFFF.bin");
2100 #elif defined(IRIVER_H300_SERIES)
2101 fd = creat("/internal_rom_000000-3FFFFF.bin");
2102 #elif defined(IAUDIO_X5) || defined(IAUDIO_M5) || defined(IAUDIO_M3)
2103 fd = creat("/internal_rom_000000-3FFFFF.bin");
2104 #endif
2105 if(fd >= 0)
2107 write(fd, (void *)0, FLASH_SIZE);
2108 close(fd);
2110 system_memory_guard(oldmode);
2112 #ifdef HAVE_EEPROM
2113 fd = creat("/internal_eeprom.bin");
2114 if (fd >= 0)
2116 int old_irq_level;
2117 char buf[EEPROM_SIZE];
2118 int err;
2120 old_irq_level = disable_irq_save();
2122 err = eeprom_24cxx_read(0, buf, sizeof buf);
2124 restore_irq(old_irq_level);
2126 if (err)
2127 gui_syncsplash(HZ*3, "Eeprom read failure (%d)",err);
2128 else
2130 write(fd, buf, sizeof buf);
2133 close(fd);
2135 #endif
2137 return false;
2139 #elif defined(CPU_PP) && !(defined(SANSA_E200) || defined(SANSA_C200))
2140 static bool dbg_save_roms(void)
2142 int fd;
2144 fd = creat("/internal_rom_000000-0FFFFF.bin");
2145 if(fd >= 0)
2147 write(fd, (void *)0x20000000, FLASH_SIZE);
2148 close(fd);
2151 return false;
2153 #endif /* CPU */
2155 #ifndef SIMULATOR
2156 #if CONFIG_TUNER
2157 static int radio_callback(int btn, struct gui_synclist *lists)
2159 (void)lists;
2160 if (btn == ACTION_STD_CANCEL)
2161 return btn;
2162 simplelist_set_line_count(1);
2164 #if (CONFIG_TUNER & LV24020LP)
2165 simplelist_addline(SIMPLELIST_ADD_LINE,
2166 "CTRL_STAT: %02X", lv24020lp_get(LV24020LP_CTRL_STAT) );
2167 simplelist_addline(SIMPLELIST_ADD_LINE,
2168 "RADIO_STAT: %02X", lv24020lp_get(LV24020LP_REG_STAT) );
2169 simplelist_addline(SIMPLELIST_ADD_LINE,
2170 "MSS_FM: %d kHz", lv24020lp_get(LV24020LP_MSS_FM) );
2171 simplelist_addline(SIMPLELIST_ADD_LINE,
2172 "MSS_IF: %d Hz", lv24020lp_get(LV24020LP_MSS_IF) );
2173 simplelist_addline(SIMPLELIST_ADD_LINE,
2174 "MSS_SD: %d Hz", lv24020lp_get(LV24020LP_MSS_SD) );
2175 simplelist_addline(SIMPLELIST_ADD_LINE,
2176 "if_set: %d Hz", lv24020lp_get(LV24020LP_IF_SET) );
2177 simplelist_addline(SIMPLELIST_ADD_LINE,
2178 "sd_set: %d Hz", lv24020lp_get(LV24020LP_SD_SET) );
2179 #endif
2180 #if (CONFIG_TUNER & S1A0903X01)
2181 simplelist_addline(SIMPLELIST_ADD_LINE,
2182 "Samsung regs: %08X", s1a0903x01_get(RADIO_ALL));
2183 /* This one doesn't return dynamic data atm */
2184 #endif
2185 #if (CONFIG_TUNER & TEA5767)
2186 struct tea5767_dbg_info nfo;
2187 tea5767_dbg_info(&nfo);
2188 simplelist_addline(SIMPLELIST_ADD_LINE, "Philips regs:");
2189 simplelist_addline(SIMPLELIST_ADD_LINE,
2190 " Read: %02X %02X %02X %02X %02X",
2191 (unsigned)nfo.read_regs[0], (unsigned)nfo.read_regs[1],
2192 (unsigned)nfo.read_regs[2], (unsigned)nfo.read_regs[3],
2193 (unsigned)nfo.read_regs[4]);
2194 simplelist_addline(SIMPLELIST_ADD_LINE,
2195 " Write: %02X %02X %02X %02X %02X",
2196 (unsigned)nfo.write_regs[0], (unsigned)nfo.write_regs[1],
2197 (unsigned)nfo.write_regs[2], (unsigned)nfo.write_regs[3],
2198 (unsigned)nfo.write_regs[4]);
2199 #endif
2200 return ACTION_REDRAW;
2202 static bool dbg_fm_radio(void)
2204 struct simplelist_info info;
2205 info.scroll_all = true;
2206 simplelist_info_init(&info, "FM Radio", 1, NULL);
2207 simplelist_set_line_count(0);
2208 simplelist_addline(SIMPLELIST_ADD_LINE, "HW detected: %s",
2209 radio_hardware_present() ? "yes" : "no");
2211 info.action_callback = radio_hardware_present()?radio_callback : NULL;
2212 info.hide_selection = true;
2213 return simplelist_show_list(&info);
2215 #endif /* CONFIG_TUNER */
2216 #endif /* !SIMULATOR */
2218 #ifdef HAVE_LCD_BITMAP
2219 extern bool do_screendump_instead_of_usb;
2221 static bool dbg_screendump(void)
2223 do_screendump_instead_of_usb = !do_screendump_instead_of_usb;
2224 gui_syncsplash(HZ, "Screendump %s",
2225 do_screendump_instead_of_usb?"enabled":"disabled");
2226 return false;
2228 #endif /* HAVE_LCD_BITMAP */
2230 #if CONFIG_CPU == SH7034 || defined(CPU_COLDFIRE)
2231 static bool dbg_set_memory_guard(void)
2233 static const struct opt_items names[MAXMEMGUARD] = {
2234 { "None", -1 },
2235 { "Flash ROM writes", -1 },
2236 { "Zero area (all)", -1 }
2238 int mode = system_memory_guard(MEMGUARD_KEEP);
2240 set_option( "Catch mem accesses", &mode, INT, names, MAXMEMGUARD, NULL);
2241 system_memory_guard(mode);
2243 return false;
2245 #endif /* CONFIG_CPU == SH7034 || defined(CPU_COLDFIRE) */
2247 #if defined(HAVE_EEPROM) && !defined(HAVE_EEPROM_SETTINGS)
2248 static bool dbg_write_eeprom(void)
2250 int fd;
2251 int rc;
2252 int old_irq_level;
2253 char buf[EEPROM_SIZE];
2254 int err;
2256 fd = open("/internal_eeprom.bin", O_RDONLY);
2258 if (fd >= 0)
2260 rc = read(fd, buf, EEPROM_SIZE);
2262 if(rc == EEPROM_SIZE)
2264 old_irq_level = disable_irq_save();
2266 err = eeprom_24cxx_write(0, buf, sizeof buf);
2267 if (err)
2268 gui_syncsplash(HZ*3, "Eeprom write failure (%d)",err);
2269 else
2270 gui_syncsplash(HZ*3, "Eeprom written successfully");
2272 restore_irq(old_irq_level);
2274 else
2276 gui_syncsplash(HZ*3, "File read error (%d)",rc);
2278 close(fd);
2280 else
2282 gui_syncsplash(HZ*3, "Failed to open 'internal_eeprom.bin'");
2285 return false;
2287 #endif /* defined(HAVE_EEPROM) && !defined(HAVE_EEPROM_SETTINGS) */
2288 #ifdef CPU_BOOST_LOGGING
2289 static bool cpu_boost_log(void)
2291 int i = 0,j=0;
2292 int count = cpu_boost_log_getcount();
2293 int lines = LCD_HEIGHT/SYSFONT_HEIGHT;
2294 char *str;
2295 bool done;
2296 lcd_setmargins(0, 0);
2297 lcd_setfont(FONT_SYSFIXED);
2298 str = cpu_boost_log_getlog_first();
2299 while (i < count)
2301 lcd_clear_display();
2302 for(j=0; j<lines; j++,i++)
2304 if (!str)
2305 str = cpu_boost_log_getlog_next();
2306 if (str)
2308 lcd_puts(0, j,str);
2310 str = NULL;
2312 lcd_update();
2313 done = false;
2314 while (!done)
2316 switch(get_action(CONTEXT_STD,TIMEOUT_BLOCK))
2318 case ACTION_STD_OK:
2319 case ACTION_STD_PREV:
2320 case ACTION_STD_NEXT:
2321 done = true;
2322 break;
2323 case ACTION_STD_CANCEL:
2324 i = count;
2325 done = true;
2326 break;
2330 get_action(CONTEXT_STD,TIMEOUT_BLOCK);
2331 lcd_setfont(FONT_UI);
2332 return false;
2334 #endif
2336 #if (defined(HAVE_SCROLLWHEEL) && (CONFIG_KEYPAD==IPOD_4G_PAD) && !defined(SIMULATOR))
2337 extern bool wheel_is_touched;
2338 extern int old_wheel_value;
2339 extern int new_wheel_value;
2340 extern int wheel_delta;
2341 extern unsigned int accumulated_wheel_delta;
2342 extern unsigned int wheel_velocity;
2344 static bool dbg_scrollwheel(void)
2346 char buf[64];
2347 unsigned int speed;
2349 lcd_setmargins(0, 0);
2350 lcd_setfont(FONT_SYSFIXED);
2352 while (1)
2354 if (action_userabort(HZ/10))
2355 return false;
2357 lcd_clear_display();
2359 /* show internal variables of scrollwheel driver */
2360 snprintf(buf, sizeof(buf), "wheel touched: %s", (wheel_is_touched) ? "true" : "false");
2361 lcd_puts(0, 0, buf);
2362 snprintf(buf, sizeof(buf), "new position: %2d", new_wheel_value);
2363 lcd_puts(0, 1, buf);
2364 snprintf(buf, sizeof(buf), "old position: %2d", old_wheel_value);
2365 lcd_puts(0, 2, buf);
2366 snprintf(buf, sizeof(buf), "wheel delta: %2d", wheel_delta);
2367 lcd_puts(0, 3, buf);
2368 snprintf(buf, sizeof(buf), "accumulated delta: %2d", accumulated_wheel_delta);
2369 lcd_puts(0, 4, buf);
2370 snprintf(buf, sizeof(buf), "velo [deg/s]: %4d", (int)wheel_velocity);
2371 lcd_puts(0, 5, buf);
2373 /* show effective accelerated scrollspeed */
2374 speed = button_apply_acceleration( (1<<31)|(1<<24)|wheel_velocity);
2375 snprintf(buf, sizeof(buf), "accel. speed: %4d", speed);
2376 lcd_puts(0, 6, buf);
2378 lcd_update();
2380 return false;
2382 #endif
2384 #if defined(HAVE_USBSTACK) && defined(ROCKBOX_HAS_LOGF) && defined(USB_SERIAL)
2385 static bool logf_usb_serial(void)
2387 bool serial_enabled = !usb_core_driver_enabled(USB_DRIVER_SERIAL);
2388 usb_core_enable_driver(USB_DRIVER_SERIAL,serial_enabled);
2389 gui_syncsplash(HZ, "USB logf %s",
2390 serial_enabled?"enabled":"disabled");
2391 return false;
2393 #endif
2395 #if defined(HAVE_USBSTACK) && defined(USB_STORAGE)
2396 static bool usb_reconnect(void)
2398 gui_syncsplash(HZ, "Reconnect mass storage");
2399 usb_storage_reconnect();
2400 return false;
2402 #endif
2404 #if CONFIG_USBOTG == USBOTG_ISP1583
2405 extern int dbg_usb_num_items(void);
2406 extern char* dbg_usb_item(int selected_item, void *data, char *buffer, size_t buffer_len);
2408 static int isp1583_action_callback(int action, struct gui_synclist *lists)
2410 (void)lists;
2411 if (action == ACTION_NONE)
2412 action = ACTION_REDRAW;
2413 return action;
2416 static bool dbg_isp1583(void)
2418 struct simplelist_info isp1583;
2419 isp1583.scroll_all = true;
2420 simplelist_info_init(&isp1583, "ISP1583", dbg_usb_num_items(), NULL);
2421 isp1583.timeout = HZ/100;
2422 isp1583.hide_selection = true;
2423 isp1583.get_name = dbg_usb_item;
2424 isp1583.action_callback = isp1583_action_callback;
2425 return simplelist_show_list(&isp1583);
2427 #endif
2429 #if defined(CREATIVE_ZVx) && !defined(SIMULATOR)
2430 extern int pic_dbg_num_items(void);
2431 extern char* pic_dbg_item(int selected_item, void *data, char *buffer, size_t buffer_len);
2433 static int pic_action_callback(int action, struct gui_synclist *lists)
2435 (void)lists;
2436 if (action == ACTION_NONE)
2437 action = ACTION_REDRAW;
2438 return action;
2441 static bool dbg_pic(void)
2443 struct simplelist_info pic;
2444 pic.scroll_all = true;
2445 simplelist_info_init(&pic, "PIC", pic_dbg_num_items(), NULL);
2446 pic.timeout = HZ/100;
2447 pic.hide_selection = true;
2448 pic.get_name = pic_dbg_item;
2449 pic.action_callback = pic_action_callback;
2450 return simplelist_show_list(&pic);
2452 #endif
2455 /****** The menu *********/
2456 struct the_menu_item {
2457 unsigned char *desc; /* string or ID */
2458 bool (*function) (void); /* return true if USB was connected */
2460 static const struct the_menu_item menuitems[] = {
2461 #if CONFIG_CPU == SH7034 || defined(CPU_COLDFIRE) || \
2462 (defined(CPU_PP) && !(defined(SANSA_E200) || defined(SANSA_C200)))
2463 { "Dump ROM contents", dbg_save_roms },
2464 #endif
2465 #if CONFIG_CPU == SH7034 || defined(CPU_COLDFIRE) || defined(CPU_PP) \
2466 || CONFIG_CPU == S3C2440 || CONFIG_CPU == IMX31L
2467 { "View I/O ports", dbg_ports },
2468 #endif
2469 #if (CONFIG_RTC == RTC_PCF50605) && !defined(SIMULATOR)
2470 { "View PCF registers", dbg_pcf },
2471 #endif
2472 #if defined(HAVE_TSC2100) && !defined(SIMULATOR)
2473 { "TSC2100 debug", tsc2100_debug },
2474 #endif
2475 #ifdef HAVE_ADJUSTABLE_CPU_FREQ
2476 { "CPU frequency", dbg_cpufreq },
2477 #endif
2478 #if defined(IRIVER_H100_SERIES) && !defined(SIMULATOR)
2479 { "S/PDIF analyzer", dbg_spdif },
2480 #endif
2481 #if CONFIG_CPU == SH7034 || defined(CPU_COLDFIRE)
2482 { "Catch mem accesses", dbg_set_memory_guard },
2483 #endif
2484 { "View OS stacks", dbg_os },
2485 #ifdef HAVE_LCD_BITMAP
2486 #ifndef SIMULATOR
2487 { "View battery", view_battery },
2488 #endif
2489 { "Screendump", dbg_screendump },
2490 #endif
2491 #ifndef SIMULATOR
2492 { "View HW info", dbg_hw_info },
2493 #endif
2494 #ifndef SIMULATOR
2495 { "View partitions", dbg_partitions },
2496 #endif
2497 #ifndef SIMULATOR
2498 { "View disk info", dbg_disk_info },
2499 #if !defined(HAVE_MMC) && !defined(HAVE_ATA_SD)
2500 { "Dump ATA identify info", dbg_identify_info},
2501 #endif
2502 #endif
2503 #ifdef HAVE_DIRCACHE
2504 { "View dircache info", dbg_dircache_info },
2505 #endif
2506 #ifdef HAVE_TAGCACHE
2507 { "View database info", dbg_tagcache_info },
2508 #endif
2509 #ifdef HAVE_LCD_BITMAP
2510 #if CONFIG_CODEC == SWCODEC
2511 { "View buffering thread", dbg_buffering_thread },
2512 #elif !defined(SIMULATOR)
2513 { "View audio thread", dbg_audio_thread },
2514 #endif
2515 #ifdef PM_DEBUG
2516 { "pm histogram", peak_meter_histogram},
2517 #endif /* PM_DEBUG */
2518 #endif /* HAVE_LCD_BITMAP */
2519 #ifndef SIMULATOR
2520 #if CONFIG_TUNER
2521 { "FM Radio", dbg_fm_radio },
2522 #endif
2523 #endif
2524 #if defined(HAVE_EEPROM) && !defined(HAVE_EEPROM_SETTINGS)
2525 { "Write back EEPROM", dbg_write_eeprom },
2526 #endif
2527 #if CONFIG_USBOTG == USBOTG_ISP1583
2528 { "View ISP1583 info", dbg_isp1583 },
2529 #endif
2530 #if defined(CREATIVE_ZVx) && !defined(SIMULATOR)
2531 { "View PIC info", dbg_pic },
2532 #endif
2533 #ifdef ROCKBOX_HAS_LOGF
2534 {"logf", logfdisplay },
2535 {"logfdump", logfdump },
2536 #endif
2537 #if defined(HAVE_USBSTACK) && defined(ROCKBOX_HAS_LOGF) && defined(USB_SERIAL)
2538 {"logf over usb",logf_usb_serial },
2539 #endif
2540 #if defined(HAVE_USBSTACK) && defined(USB_STORAGE)
2541 {"reconnect usb storage",usb_reconnect},
2542 #endif
2543 #ifdef CPU_BOOST_LOGGING
2544 {"cpu_boost log",cpu_boost_log},
2545 #endif
2546 #if (defined(HAVE_SCROLLWHEEL) && (CONFIG_KEYPAD==IPOD_4G_PAD) && !defined(SIMULATOR))
2547 {"Debug scrollwheel", dbg_scrollwheel},
2548 #endif
2550 static int menu_action_callback(int btn, struct gui_synclist *lists)
2552 if (btn == ACTION_STD_OK)
2554 menuitems[gui_synclist_get_sel_pos(lists)].function();
2555 btn = ACTION_REDRAW;
2557 return btn;
2559 static char* dbg_menu_getname(int item, void * data,
2560 char *buffer, size_t buffer_len)
2562 (void)data; (void)buffer; (void)buffer_len;
2563 return menuitems[item].desc;
2565 bool debug_menu(void)
2567 struct simplelist_info info;
2569 simplelist_info_init(&info, "Debug Menu", ARRAYLEN(menuitems), NULL);
2570 info.action_callback = menu_action_callback;
2571 info.get_name = dbg_menu_getname;
2573 return simplelist_show_list(&info);