1 /***************************************************************************
3 * Open \______ \ ____ ____ | | _\_ |__ _______ ___
4 * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
5 * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
6 * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
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 ****************************************************************************/
27 #include "debug_menu.h"
37 #include "powermgmt.h"
42 #include "mp3_playback.h"
50 #ifdef HAVE_LCD_BITMAP
52 #include "peakmeter.h"
61 #if defined(IRIVER_H100_SERIES) && !defined(SIMULATOR)
62 extern bool pcm_rec_screen(void);
64 #if CONFIG_CODEC == SWCODEC
66 #include "pcm_playback.h"
69 /*---------------------------------------------------*/
70 /* SPECIAL DEBUG STUFF */
71 /*---------------------------------------------------*/
72 extern char ata_device
;
73 extern int ata_io_address
;
74 extern int num_threads
;
75 extern const char *thread_name
[];
77 #ifdef HAVE_LCD_BITMAP
87 lcd_setfont(FONT_SYSFIXED
);
92 lcd_puts(0, 0, "Stack usage:");
93 for(i
= 0; i
< num_threads
;i
++)
95 usage
= thread_stack_usage(i
);
96 snprintf(buf
, 32, "%s: %d%%", thread_name
[i
], usage
);
97 lcd_puts(0, 1+i
, buf
);
102 button
= button_get_w_tmo(HZ
/10);
106 case SETTINGS_CANCEL
:
112 #else /* !HAVE_LCD_BITMAP */
124 lcd_puts(0, 0, "Stack usage");
126 usage
= thread_stack_usage(currval
);
127 snprintf(buf
, 32, "%d: %d%% ", currval
, usage
);
130 button
= button_get_w_tmo(HZ
/10);
134 case SETTINGS_CANCEL
:
140 currval
= num_threads
-1;
145 if(currval
> num_threads
-1)
152 #endif /* !HAVE_LCD_BITMAP */
154 #ifdef HAVE_LCD_BITMAP
155 #if CONFIG_CODEC != SWCODEC
156 bool dbg_audio_thread(void)
160 struct audio_debug d
;
162 lcd_setmargins(0, 0);
163 lcd_setfont(FONT_SYSFIXED
);
167 button
= button_get_w_tmo(HZ
/5);
170 case SETTINGS_CANCEL
:
174 audio_get_debugdata(&d
);
178 snprintf(buf
, sizeof(buf
), "read: %x", d
.audiobuf_read
);
180 snprintf(buf
, sizeof(buf
), "write: %x", d
.audiobuf_write
);
182 snprintf(buf
, sizeof(buf
), "swap: %x", d
.audiobuf_swapwrite
);
184 snprintf(buf
, sizeof(buf
), "playing: %d", d
.playing
);
186 snprintf(buf
, sizeof(buf
), "playable: %x", d
.playable_space
);
188 snprintf(buf
, sizeof(buf
), "unswapped: %x", d
.unswapped_space
);
191 /* Playable space left */
192 scrollbar(0, 6*8, 112, 4, d
.audiobuflen
, 0,
193 d
.playable_space
, HORIZONTAL
);
195 /* Show the watermark limit */
196 scrollbar(0, 6*8+4, 112, 4, d
.audiobuflen
, 0,
197 d
.low_watermark_level
, HORIZONTAL
);
199 snprintf(buf
, sizeof(buf
), "wm: %x - %x",
200 d
.low_watermark_level
, d
.lowest_watermark_level
);
207 #else /* CONFIG_CODEC == SWCODEC */
208 extern size_t audiobuffer_free
;
209 extern int filebuflen
;
210 extern int filebufused
;
211 extern int track_count
;
213 static int ticks
, boost_ticks
;
215 void dbg_audio_task(void)
217 if(FREQ
> CPUFREQ_NORMAL
)
223 bool dbg_audio_thread(void)
229 int bufsize
= pcmbuf_get_bufsize();
231 ticks
= boost_ticks
= 0;
233 tick_add_task(dbg_audio_task
);
235 lcd_setmargins(0, 0);
236 lcd_setfont(FONT_SYSFIXED
);
240 button
= button_get_w_tmo(HZ
/5);
243 case SETTINGS_CANCEL
:
252 snprintf(buf
, sizeof(buf
), "pcm: %d/%d",
253 bufsize
-(int)audiobuffer_free
, bufsize
);
254 lcd_puts(0, line
++, buf
);
256 /* Playable space left */
257 scrollbar(0, line
*8, LCD_WIDTH
, 6, bufsize
, 0,
258 bufsize
-audiobuffer_free
, HORIZONTAL
);
261 snprintf(buf
, sizeof(buf
), "codec: %d/%d", filebufused
, filebuflen
);
262 lcd_puts(0, line
++, buf
);
264 /* Playable space left */
265 scrollbar(0, line
*8, LCD_WIDTH
, 6, filebuflen
, 0,
266 filebufused
, HORIZONTAL
);
269 snprintf(buf
, sizeof(buf
), "track count: %d", track_count
);
270 lcd_puts(0, line
++, buf
);
272 snprintf(buf
, sizeof(buf
), "cpu freq: %dMHz",
273 (int)((FREQ
+ 500000) / 1000000));
274 lcd_puts(0, line
++, buf
);
276 snprintf(buf
, sizeof(buf
), "boost ratio: %d%%",
277 boost_ticks
* 100 / ticks
);
278 lcd_puts(0, line
++, buf
);
283 tick_remove_task(dbg_audio_task
);
287 #endif /* CONFIG_CODEC */
288 #endif /* HAVE_LCD_BITMAP */
290 /* Tool function to calculate a CRC16 across some buffer */
291 unsigned short crc_16(const unsigned char* buf
, unsigned len
)
293 /* CCITT standard polynomial 0x1021 */
294 static const unsigned short crc16_lookup
[16] =
295 { /* lookup table for 4 bits at a time is affordable */
296 0x0000, 0x1021, 0x2042, 0x3063,
297 0x4084, 0x50A5, 0x60C6, 0x70E7,
298 0x8108, 0x9129, 0xA14A, 0xB16B,
299 0xC18C, 0xD1AD, 0xE1CE, 0xF1EF
301 unsigned short crc16
= 0xFFFF; /* initialise to 0xFFFF (CCITT specification) */
307 byte
= *buf
++; /* get one byte of data */
309 /* upper nibble of our data */
310 t
= crc16
>> 12; /* extract the 4 most significant bits */
311 t
^= byte
>> 4; /* XOR in 4 bits of the data into the extracted bits */
312 crc16
<<= 4; /* shift the CRC Register left 4 bits */
313 crc16
^= crc16_lookup
[t
]; /* do the table lookup and XOR the result */
315 /* lower nibble of our data */
316 t
= crc16
>> 12; /* extract the 4 most significant bits */
317 t
^= byte
& 0x0F; /* XOR in 4 bits of the data into the extracted bits */
318 crc16
<<= 4; /* shift the CRC Register left 4 bits */
319 crc16
^= crc16_lookup
[t
]; /* do the table lookup and XOR the result */
326 #if CONFIG_CPU == TCC730
327 static unsigned flash_word_temp
__attribute__ ((section (".idata")));
329 static void flash_write_word(unsigned addr
, unsigned value
) __attribute__ ((section(".icode")));
330 static void flash_write_word(unsigned addr
, unsigned value
) {
331 flash_word_temp
= value
;
333 long extAddr
= (long)addr
<< 1;
334 ddma_transfer(1, 1, &flash_word_temp
, extAddr
, 2);
337 static unsigned flash_read_word(unsigned addr
) __attribute__ ((section(".icode")));
338 static unsigned flash_read_word(unsigned addr
) {
339 long extAddr
= (long)addr
<< 1;
340 ddma_transfer(1, 1, &flash_word_temp
, extAddr
, 2);
341 return flash_word_temp
;
346 /* Tool function to read the flash manufacturer and type, if available.
347 Only chips which could be reprogrammed in system will return values.
348 (The mode switch addresses vary between flash manufacturers, hence addr1/2) */
349 /* In IRAM to avoid problems when running directly from Flash */
350 bool dbg_flash_id(unsigned* p_manufacturer
, unsigned* p_device
,
351 unsigned addr1
, unsigned addr2
)
352 __attribute__ ((section (".icode")));
353 bool dbg_flash_id(unsigned* p_manufacturer
, unsigned* p_device
,
354 unsigned addr1
, unsigned addr2
)
357 unsigned not_manu
, not_id
; /* read values before switching to ID mode */
358 unsigned manu
, id
; /* read values when in ID mode */
359 #if CONFIG_CPU == TCC730
360 #define FLASH(addr) (flash_read_word(addr))
361 #define SET_FLASH(addr, val) (flash_write_word((addr), (val)))
363 #else /* memory mapped */
364 #if CONFIG_CPU == SH7034
365 volatile unsigned char* flash
= (unsigned char*)0x2000000; /* flash mapping */
366 #elif CONFIG_CPU == MCF5249
367 volatile unsigned short* flash
= (unsigned short*)0; /* flash mapping */
369 #define FLASH(addr) (flash[addr])
370 #define SET_FLASH(addr, val) (flash[addr] = val)
372 int old_level
; /* saved interrupt level */
374 not_manu
= FLASH(0); /* read the normal content */
375 not_id
= FLASH(1); /* should be 'A' (0x41) and 'R' (0x52) from the "ARCH" marker */
377 /* disable interrupts, prevent any stray flash access */
378 old_level
= set_irq_level(HIGHEST_IRQ_LEVEL
);
380 SET_FLASH(addr1
, 0xAA); /* enter command mode */
381 SET_FLASH(addr2
, 0x55);
382 SET_FLASH(addr1
, 0x90); /* ID command */
383 /* Atmel wants 20ms pause here */
384 /* sleep(HZ/50); no sleeping possible while interrupts are disabled */
386 manu
= FLASH(0); /* read the IDs */
389 SET_FLASH(0, 0xF0); /* reset flash (back to normal read mode) */
390 /* Atmel wants 20ms pause here */
391 /* sleep(HZ/50); no sleeping possible while interrupts are disabled */
393 set_irq_level(old_level
); /* enable interrupts again */
395 /* I assume success if the obtained values are different from
396 the normal flash content. This is not perfectly bulletproof, they
397 could theoretically be the same by chance, causing us to fail. */
398 if (not_manu
!= manu
|| not_id
!= id
) /* a value has changed */
400 *p_manufacturer
= manu
; /* return the results */
402 return true; /* success */
404 return false; /* fail */
408 #ifdef HAVE_LCD_BITMAP
409 bool dbg_hw_info(void)
411 #if CONFIG_CPU == SH7034
416 int bitmask
= *(unsigned short*)0x20000fc;
417 int rom_version
= *(unsigned short*)0x20000fe;
418 unsigned manu
, id
; /* flash IDs */
419 bool got_id
; /* flag if we managed to get the flash IDs */
420 unsigned rom_crc
= 0xFFFF; /* CRC16 of the boot ROM */
421 bool has_bootrom
; /* flag for boot ROM present */
422 int oldmode
; /* saved memory guard mode */
424 #ifdef USB_ENABLE_ONDIOSTYLE
429 usb_polarity
= 0; /* Negative */
431 usb_polarity
= 1; /* Positive */
434 pr_polarity
= 0; /* Negative */
436 pr_polarity
= 1; /* Positive */
438 oldmode
= system_memory_guard(MEMGUARD_NONE
); /* disable memory guard */
440 /* get flash ROM type */
441 got_id
= dbg_flash_id(&manu
, &id
, 0x5555, 0x2AAA); /* try SST, Atmel, NexFlash */
443 got_id
= dbg_flash_id(&manu
, &id
, 0x555, 0x2AA); /* try AMD, Macronix */
445 /* check if the boot ROM area is a flash mirror */
446 has_bootrom
= (memcmp((char*)0, (char*)0x02000000, 64*1024) != 0);
447 if (has_bootrom
) /* if ROM and Flash different */
449 /* calculate CRC16 checksum of boot ROM */
450 rom_crc
= crc_16((unsigned char*)0x0000, 64*1024);
453 system_memory_guard(oldmode
); /* re-enable memory guard */
455 lcd_setmargins(0, 0);
456 lcd_setfont(FONT_SYSFIXED
);
459 lcd_puts(0, 0, "[Hardware info]");
461 snprintf(buf
, 32, "ROM: %d.%02d", rom_version
/100, rom_version
%100);
464 snprintf(buf
, 32, "Mask: 0x%04x", bitmask
);
467 snprintf(buf
, 32, "USB: %s", usb_polarity
?"positive":"negative");
470 snprintf(buf
, 32, "PR: %s", pr_polarity
?"positive":"negative");
474 snprintf(buf
, 32, "Flash: M=%02x D=%02x", manu
, id
);
476 snprintf(buf
, 32, "Flash: M=?? D=??"); /* unknown, sorry */
481 snprintf(buf
, 32-3, "ROM CRC: 0x%04x", rom_crc
);
482 if (rom_crc
== 0x222F) /* known Version 1 */
487 snprintf(buf
, 32, "Boot ROM: none");
491 #ifndef HAVE_MMC /* have ATA */
492 snprintf(buf
, 32, "ATA: 0x%x,%s", ata_io_address
,
493 ata_device
? "slave":"master");
500 button
= button_get(true);
501 if(button
== SETTINGS_CANCEL
)
504 #elif CONFIG_CPU == MCF5249
507 unsigned manu
, id
; /* flash IDs */
508 bool got_id
; /* flag if we managed to get the flash IDs */
509 int oldmode
; /* saved memory guard mode */
511 oldmode
= system_memory_guard(MEMGUARD_NONE
); /* disable memory guard */
513 /* get flash ROM type */
514 got_id
= dbg_flash_id(&manu
, &id
, 0x5555, 0x2AAA); /* try SST, Atmel, NexFlash */
516 got_id
= dbg_flash_id(&manu
, &id
, 0x555, 0x2AA); /* try AMD, Macronix */
518 system_memory_guard(oldmode
); /* re-enable memory guard */
520 lcd_setmargins(0, 0);
521 lcd_setfont(FONT_SYSFIXED
);
524 lcd_puts(0, 0, "[Hardware info]");
527 snprintf(buf
, 32, "Flash: M=%04x D=%04x", manu
, id
);
529 snprintf(buf
, 32, "Flash: M=???? D=????"); /* unknown, sorry */
536 button
= button_get(true);
537 if(button
== SETTINGS_CANCEL
)
540 #endif /* CONFIG_CPU */
543 #else /* !HAVE_LCD_BITMAP */
544 bool dbg_hw_info(void)
550 int bitmask
= *(unsigned short*)0x20000fc;
551 int rom_version
= *(unsigned short*)0x20000fe;
552 unsigned manu
, id
; /* flash IDs */
553 bool got_id
; /* flag if we managed to get the flash IDs */
554 unsigned rom_crc
= 0xFFFF; /* CRC16 of the boot ROM */
555 bool has_bootrom
; /* flag for boot ROM present */
556 int oldmode
; /* saved memory guard mode */
559 usb_polarity
= 0; /* Negative */
561 usb_polarity
= 1; /* Positive */
563 oldmode
= system_memory_guard(MEMGUARD_NONE
); /* disable memory guard */
565 /* get flash ROM type */
566 got_id
= dbg_flash_id(&manu
, &id
, 0x5555, 0x2AAA); /* try SST, Atmel, NexFlash */
568 got_id
= dbg_flash_id(&manu
, &id
, 0x555, 0x2AA); /* try AMD, Macronix */
570 /* check if the boot ROM area is a flash mirror */
571 has_bootrom
= (memcmp((char*)0, (char*)0x02000000, 64*1024) != 0);
572 if (has_bootrom
) /* if ROM and Flash different */
574 /* calculate CRC16 checksum of boot ROM */
575 rom_crc
= crc_16((unsigned char*)0x0000, 64*1024);
578 system_memory_guard(oldmode
); /* re-enable memory guard */
582 lcd_puts(0, 0, "[HW Info]");
588 snprintf(buf
, 32, "ROM: %d.%02d",
589 rom_version
/100, rom_version
%100);
592 snprintf(buf
, 32, "USB: %s",
593 usb_polarity
?"pos":"neg");
596 snprintf(buf
, 32, "ATA: 0x%x%s",
597 ata_io_address
, ata_device
? "s":"m");
600 snprintf(buf
, 32, "Mask: %04x", bitmask
);
604 snprintf(buf
, 32, "Flash:%02x,%02x", manu
, id
);
606 snprintf(buf
, 32, "Flash:??,??"); /* unknown, sorry */
610 snprintf(buf
, 32, "RomCRC:%04x", rom_crc
);
612 snprintf(buf
, 32, "BootROM: no");
618 button
= button_get(true);
622 case SETTINGS_CANCEL
:
640 #endif /* !HAVE_LCD_BITMAP */
642 bool dbg_partitions(void)
647 lcd_puts(0, 0, "Partition");
648 lcd_puts(0, 1, "list");
656 struct partinfo
* p
= disk_partinfo(partition
);
659 snprintf(buf
, sizeof buf
, "P%d: S:%lx", partition
, p
->start
);
661 snprintf(buf
, sizeof buf
, "T:%x %ld MB", p
->type
, p
->size
/ 2048);
665 button
= button_get(true);
670 case SETTINGS_CANCEL
:
686 if(default_event_handler(button
) == SYS_USB_CONNECTED
)
700 unsigned int control
;
705 unsigned int interruptstat
;
706 bool valnogood
, symbolerr
, parityerr
;
708 lcd_setmargins(0, 0);
710 lcd_setfont(FONT_SYSFIXED
);
716 control
= EBU1RCVCCHANNEL1
;
717 interruptstat
= INTERRUPTSTAT
;
718 INTERRUPTCLEAR
= 0x03c00000;
720 valnogood
= (interruptstat
& 0x01000000)?true:false;
721 symbolerr
= (interruptstat
& 0x00800000)?true:false;
722 parityerr
= (interruptstat
& 0x00400000)?true:false;
724 snprintf(buf
, sizeof(buf
), "Val: %s Sym: %s Par: %s",
727 parityerr
?"--":"OK");
728 lcd_puts(0, line
++, buf
);
730 snprintf(buf
, sizeof(buf
), "Status word: %08x", (int)control
);
731 lcd_puts(0, line
++, buf
);
736 snprintf(buf
, sizeof(buf
), "PRO: %d (%s)",
737 x
, x
?"Professional":"Consumer");
738 lcd_puts(0, line
++, buf
);
740 x
= (control
>> 30) & 1;
741 snprintf(buf
, sizeof(buf
), "Audio: %d (%s)",
742 x
, x
?"Non-PCM":"PCM");
743 lcd_puts(0, line
++, buf
);
745 x
= (control
>> 29) & 1;
746 snprintf(buf
, sizeof(buf
), "Copy: %d (%s)",
747 x
, x
?"Permitted":"Inhibited");
748 lcd_puts(0, line
++, buf
);
750 x
= (control
>> 27) & 7;
763 snprintf(buf
, sizeof(buf
), "Preemphasis: %d (%s)", x
, s
);
764 lcd_puts(0, line
++, buf
);
766 x
= (control
>> 24) & 3;
767 snprintf(buf
, sizeof(buf
), "Mode: %d", x
);
768 lcd_puts(0, line
++, buf
);
770 category
= (control
>> 17) & 127;
782 snprintf(buf
, sizeof(buf
), "Category: 0x%02x (%s)", category
, s
);
783 lcd_puts(0, line
++, buf
);
785 x
= (control
>> 16) & 1;
787 if(((category
& 0x70) == 0x10) ||
788 ((category
& 0x70) == 0x40) ||
789 ((category
& 0x78) == 0x38))
791 generation
= !generation
;
793 snprintf(buf
, sizeof(buf
), "Generation: %d (%s)",
794 x
, generation
?"Original":"No ind.");
795 lcd_puts(0, line
++, buf
);
797 x
= (control
>> 12) & 15;
798 snprintf(buf
, sizeof(buf
), "Source: %d", x
);
799 lcd_puts(0, line
++, buf
);
801 x
= (control
>> 8) & 15;
817 snprintf(buf
, sizeof(buf
), "Channel: %d (%s)", x
, s
);
818 lcd_puts(0, line
++, buf
);
820 x
= (control
>> 4) & 15;
833 snprintf(buf
, sizeof(buf
), "Frequency: %d (%s)", x
, s
);
834 lcd_puts(0, line
++, buf
);
836 x
= (control
>> 2) & 3;
837 snprintf(buf
, sizeof(buf
), "Clock accuracy: %d", x
);
838 lcd_puts(0, line
++, buf
);
841 button
= button_get_w_tmo(HZ
/10);
845 case SETTINGS_CANCEL
:
853 #endif /* CPU_COLDFIRE */
855 #ifdef HAVE_LCD_BITMAP
859 #if CONFIG_CPU == SH7034
860 unsigned short porta
;
861 unsigned short portb
;
866 int batt_int
, batt_frac
;
868 lcd_setfont(FONT_SYSFIXED
);
869 lcd_setmargins(0, 0);
878 snprintf(buf
, 32, "PADR: %04x", porta
);
880 snprintf(buf
, 32, "PBDR: %04x", portb
);
883 snprintf(buf
, 32, "AN0: %03x AN4: %03x", adc_read(0), adc_read(4));
885 snprintf(buf
, 32, "AN1: %03x AN5: %03x", adc_read(1), adc_read(5));
887 snprintf(buf
, 32, "AN2: %03x AN6: %03x", adc_read(2), adc_read(6));
889 snprintf(buf
, 32, "AN3: %03x AN7: %03x", adc_read(3), adc_read(7));
892 battery_voltage
= (adc_read(ADC_UNREG_POWER
) * BATTERY_SCALE_FACTOR
) / 10000;
893 batt_int
= battery_voltage
/ 100;
894 batt_frac
= battery_voltage
% 100;
896 snprintf(buf
, 32, "Batt: %d.%02dV %d%% ", batt_int
, batt_frac
,
899 #ifndef HAVE_MMC /* have ATA */
900 snprintf(buf
, 32, "ATA: %s, 0x%x",
901 ata_device
?"slave":"master", ata_io_address
);
905 button
= button_get_w_tmo(HZ
/10);
909 case SETTINGS_CANCEL
:
913 #elif defined(CPU_COLDFIRE)
914 unsigned int gpio_out
;
915 unsigned int gpio1_out
;
916 unsigned int gpio_read
;
917 unsigned int gpio1_read
;
918 unsigned int gpio_function
;
919 unsigned int gpio1_function
;
920 unsigned int gpio_enable
;
921 unsigned int gpio1_enable
;
922 int adc_buttons
, adc_remote
, adc_battery
;
927 int batt_int
, batt_frac
;
929 lcd_setmargins(0, 0);
931 lcd_setfont(FONT_SYSFIXED
);
936 gpio_read
= GPIO_READ
;
937 gpio1_read
= GPIO1_READ
;
939 gpio1_out
= GPIO1_OUT
;
940 gpio_function
= GPIO_FUNCTION
;
941 gpio1_function
= GPIO1_FUNCTION
;
942 gpio_enable
= GPIO_ENABLE
;
943 gpio1_enable
= GPIO1_ENABLE
;
945 snprintf(buf
, sizeof(buf
), "GPIO_READ: %08x", gpio_read
);
946 lcd_puts(0, line
++, buf
);
947 snprintf(buf
, sizeof(buf
), "GPIO_OUT: %08x", gpio_out
);
948 lcd_puts(0, line
++, buf
);
949 snprintf(buf
, sizeof(buf
), "GPIO_FUNCTION: %08x", gpio_function
);
950 lcd_puts(0, line
++, buf
);
951 snprintf(buf
, sizeof(buf
), "GPIO_ENABLE: %08x", gpio_enable
);
952 lcd_puts(0, line
++, buf
);
954 snprintf(buf
, sizeof(buf
), "GPIO1_READ: %08x", gpio1_read
);
955 lcd_puts(0, line
++, buf
);
956 snprintf(buf
, sizeof(buf
), "GPIO1_OUT: %08x", gpio1_out
);
957 lcd_puts(0, line
++, buf
);
958 snprintf(buf
, sizeof(buf
), "GPIO1_FUNCTION: %08x", gpio1_function
);
959 lcd_puts(0, line
++, buf
);
960 snprintf(buf
, sizeof(buf
), "GPIO1_ENABLE: %08x", gpio1_enable
);
961 lcd_puts(0, line
++, buf
);
963 adc_buttons
= adc_read(ADC_BUTTONS
);
964 adc_remote
= adc_read(ADC_REMOTE
);
965 adc_battery
= adc_read(ADC_BATTERY
);
967 snprintf(buf
, sizeof(buf
), "ADC_BUTTONS: %02x", adc_buttons
);
968 lcd_puts(0, line
++, buf
);
969 snprintf(buf
, sizeof(buf
), "ADC_REMOTE: %02x", adc_remote
);
970 lcd_puts(0, line
++, buf
);
971 snprintf(buf
, sizeof(buf
), "ADC_BATTERY: %02x", adc_battery
);
972 lcd_puts(0, line
++, buf
);
974 battery_voltage
= (adc_battery
* BATTERY_SCALE_FACTOR
) / 10000;
975 batt_int
= battery_voltage
/ 100;
976 batt_frac
= battery_voltage
% 100;
978 snprintf(buf
, 32, "Batt: %d.%02dV %d%% ", batt_int
, batt_frac
,
980 lcd_puts(0, line
++, buf
);
983 button
= button_get_w_tmo(HZ
/10);
987 case SETTINGS_CANCEL
:
995 #else /* !HAVE_LCD_BITMAP */
998 unsigned short porta
;
999 unsigned short portb
;
1000 unsigned char portc
;
1003 int battery_voltage
;
1004 int batt_int
, batt_frac
;
1007 lcd_clear_display();
1018 snprintf(buf
, 32, "PADR: %04x ", porta
);
1021 snprintf(buf
, 32, "PBDR: %04x ", portb
);
1024 snprintf(buf
, 32, "AN0: %03x ", adc_read(0));
1027 snprintf(buf
, 32, "AN1: %03x ", adc_read(1));
1030 snprintf(buf
, 32, "AN2: %03x ", adc_read(2));
1033 snprintf(buf
, 32, "AN3: %03x ", adc_read(3));
1036 snprintf(buf
, 32, "AN4: %03x ", adc_read(4));
1039 snprintf(buf
, 32, "AN5: %03x ", adc_read(5));
1042 snprintf(buf
, 32, "AN6: %03x ", adc_read(6));
1045 snprintf(buf
, 32, "AN7: %03x ", adc_read(7));
1048 snprintf(buf
, 32, "%s, 0x%x ",
1049 ata_device
?"slv":"mst", ata_io_address
);
1052 lcd_puts(0, 0, buf
);
1054 battery_voltage
= (adc_read(ADC_UNREG_POWER
) *
1055 BATTERY_SCALE_FACTOR
) / 10000;
1056 batt_int
= battery_voltage
/ 100;
1057 batt_frac
= battery_voltage
% 100;
1059 snprintf(buf
, 32, "Batt: %d.%02dV", batt_int
, batt_frac
);
1060 lcd_puts(0, 1, buf
);
1062 button
= button_get_w_tmo(HZ
/5);
1066 case SETTINGS_CANCEL
:
1084 #endif /* !HAVE_LCD_BITMAP */
1086 #ifdef HAVE_ADJUSTABLE_CPU_FREQ
1087 extern int boost_counter
;
1088 bool dbg_cpufreq(void)
1094 #ifdef HAVE_LCD_BITMAP
1095 lcd_setmargins(0, 0);
1096 lcd_setfont(FONT_SYSFIXED
);
1098 lcd_clear_display();
1104 snprintf(buf
, sizeof(buf
), "Frequency: %ld", FREQ
);
1105 lcd_puts(0, line
++, buf
);
1107 snprintf(buf
, sizeof(buf
), "boost_counter: %d", boost_counter
);
1108 lcd_puts(0, line
++, buf
);
1111 button
= button_get_w_tmo(HZ
/10);
1123 #if (CONFIG_KEYPAD == IRIVER_H100_PAD) || \
1124 (CONFIG_KEYPAD == IRIVER_H300_PAD)
1129 set_cpu_frequency(CPUFREQ_DEFAULT
);
1133 case SETTINGS_CANCEL
:
1141 #endif /* HAVE_ADJUSTABLE_CPU_FREQ */
1143 #ifdef HAVE_LCD_BITMAP
1145 * view_battery() shows a automatically scaled graph of the battery voltage
1146 * over time. Usable for estimating battery life / charging rate.
1147 * The power_history array is updated in power_thread of powermgmt.c.
1150 #define BAT_LAST_VAL MIN(LCD_WIDTH, POWER_HISTORY_LEN)
1151 #define BAT_YSPACE (LCD_HEIGHT - 20)
1153 bool view_battery(void)
1157 unsigned short maxv
, minv
;
1160 lcd_setmargins(0, 0);
1161 lcd_setfont(FONT_SYSFIXED
);
1166 case 0: /* voltage history graph */
1167 /* Find maximum and minimum voltage for scaling */
1170 for (i
= 0; i
< BAT_LAST_VAL
; i
++) {
1171 if (power_history
[i
] > maxv
)
1172 maxv
= power_history
[i
];
1173 if (power_history
[i
] && (power_history
[i
] < minv
))
1175 minv
= power_history
[i
];
1179 if ((minv
< 1) || (minv
>= 65535))
1184 lcd_clear_display();
1185 snprintf(buf
, 30, "Battery %d.%02d", power_history
[0] / 100,
1186 power_history
[0] % 100);
1187 lcd_puts(0, 0, buf
);
1188 snprintf(buf
, 30, "scale %d.%02d-%d.%02d V",
1189 minv
/ 100, minv
% 100, maxv
/ 100, maxv
% 100);
1190 lcd_puts(0, 1, buf
);
1193 for (i
= BAT_LAST_VAL
- 1; i
>= 0; i
--) {
1194 y
= (power_history
[i
] - minv
) * BAT_YSPACE
/ (maxv
- minv
);
1195 lcd_set_drawmode(DRMODE_SOLID
|DRMODE_INVERSEVID
);
1196 lcd_vline(x
, LCD_HEIGHT
-1, 20);
1197 lcd_set_drawmode(DRMODE_SOLID
);
1198 lcd_vline(x
, LCD_HEIGHT
-1,
1199 MIN(MAX(LCD_HEIGHT
-1 - y
, 20), LCD_HEIGHT
-1));
1205 case 1: /* status: */
1206 lcd_clear_display();
1207 lcd_puts(0, 0, "Power status:");
1209 y
= (adc_read(ADC_UNREG_POWER
) * BATTERY_SCALE_FACTOR
) / 10000;
1210 snprintf(buf
, 30, "Battery: %d.%02d V", y
/ 100, y
% 100);
1211 lcd_puts(0, 1, buf
);
1212 #ifdef ADC_EXT_POWER
1213 y
= (adc_read(ADC_EXT_POWER
) * EXT_SCALE_FACTOR
) / 10000;
1214 snprintf(buf
, 30, "External: %d.%02d V", y
/ 100, y
% 100);
1215 lcd_puts(0, 2, buf
);
1217 #ifdef HAVE_CHARGING
1218 snprintf(buf
, 30, "Charger: %s",
1219 charger_inserted() ? "present" : "absent");
1220 lcd_puts(0, 3, buf
);
1222 #ifdef HAVE_CHARGE_CTRL
1223 snprintf(buf
, 30, "Chgr: %s %s",
1224 charger_inserted() ? "present" : "absent",
1225 charger_enabled
? "on" : "off");
1226 lcd_puts(0, 3, buf
);
1227 snprintf(buf
, 30, "short delta: %d", short_delta
);
1228 lcd_puts(0, 5, buf
);
1229 snprintf(buf
, 30, "long delta: %d", long_delta
);
1230 lcd_puts(0, 6, buf
);
1231 lcd_puts(0, 7, power_message
);
1232 #endif /* HAVE_CHARGE_CTRL */
1235 case 2: /* voltage deltas: */
1236 lcd_clear_display();
1237 lcd_puts(0, 0, "Voltage deltas:");
1239 for (i
= 0; i
<= 6; i
++) {
1240 y
= power_history
[i
] - power_history
[i
+i
];
1241 snprintf(buf
, 30, "-%d min: %s%d.%02d V", i
,
1242 (y
< 0) ? "-" : "", ((y
< 0) ? y
* -1 : y
) / 100,
1243 ((y
< 0) ? y
* -1 : y
) % 100);
1244 lcd_puts(0, i
+1, buf
);
1248 case 3: /* remaining time estimation: */
1249 lcd_clear_display();
1251 #ifdef HAVE_CHARGE_CTRL
1252 snprintf(buf
, 30, "charge_state: %d", charge_state
);
1253 lcd_puts(0, 0, buf
);
1255 snprintf(buf
, 30, "Cycle time: %d m", powermgmt_last_cycle_startstop_min
);
1256 lcd_puts(0, 1, buf
);
1258 snprintf(buf
, 30, "Lvl@cyc st: %d%%", powermgmt_last_cycle_level
);
1259 lcd_puts(0, 2, buf
);
1261 snprintf(buf
, 30, "P=%2d I=%2d", pid_p
, pid_i
);
1262 lcd_puts(0, 3, buf
);
1264 snprintf(buf
, 30, "Trickle sec: %d/60", trickle_sec
);
1265 lcd_puts(0, 4, buf
);
1266 #endif /* HAVE_CHARGE_CTRL */
1268 snprintf(buf
, 30, "Last PwrHist: %d.%02d V",
1269 power_history
[0] / 100,
1270 power_history
[0] % 100);
1271 lcd_puts(0, 5, buf
);
1273 snprintf(buf
, 30, "battery level: %d%%", battery_level());
1274 lcd_puts(0, 6, buf
);
1276 snprintf(buf
, 30, "Est. remain: %d m", battery_time());
1277 lcd_puts(0, 7, buf
);
1283 switch(button_get_w_tmo(HZ
/2))
1296 case SETTINGS_CANCEL
:
1303 #endif /* HAVE_LCD_BITMAP */
1305 static bool view_runtime(void)
1316 lcd_clear_display();
1317 #ifdef HAVE_LCD_BITMAP
1318 lcd_puts(0, y
++, "Running time:");
1323 if (charger_inserted())
1325 global_settings
.runtime
= 0;
1329 global_settings
.runtime
+= ((current_tick
- lasttime
) / HZ
);
1331 lasttime
= current_tick
;
1333 t
= global_settings
.runtime
;
1334 lcd_puts(0, y
++, "Current time");
1337 t
= global_settings
.topruntime
;
1338 lcd_puts(0, y
++, "Top time");
1341 snprintf(s
, sizeof(s
), "%dh %dm %ds",
1342 t
/ 3600, (t
% 3600) / 60, t
% 60);
1343 lcd_puts(0, y
++, s
);
1346 /* Wait for a key to be pushed */
1347 key
= button_get_w_tmo(HZ
);
1349 case SETTINGS_CANCEL
:
1362 lcd_clear_display();
1363 lcd_puts(0,0,"Clear time?");
1364 lcd_puts(0,1,"PLAY = Yes");
1367 key
= button_get(true);
1368 if ( key
== SETTINGS_OK
) {
1370 global_settings
.runtime
= 0;
1372 global_settings
.topruntime
= 0;
1375 if (!(key
& BUTTON_REL
)) /* ignore button releases */
1386 bool dbg_mmc_info(void)
1391 unsigned char pbuf
[32], pbuf2
[32];
1392 unsigned char card_name
[7];
1394 static const unsigned char i_vmin
[] = { 0, 1, 5, 10, 25, 35, 60, 100 };
1395 static const unsigned char i_vmax
[] = { 1, 5, 10, 25, 35, 45, 80, 200 };
1396 static const unsigned char *kbit_units
[] = { "kBit/s", "MBit/s", "GBit/s" };
1397 static const unsigned char *nsec_units
[] = { "ns", "µs", "ms" };
1399 card_name
[6] = '\0';
1401 lcd_setmargins(0, 0);
1402 lcd_setfont(FONT_SYSFIXED
);
1406 card
= mmc_card_info(currval
/ 2);
1408 lcd_clear_display();
1409 snprintf(pbuf
, sizeof(pbuf
), "[MMC%d p%d]", currval
/ 2,
1411 lcd_puts(0, 0, pbuf
);
1413 if (card
->initialized
)
1415 if (!(currval
% 2)) /* General info */
1417 strncpy(card_name
, ((unsigned char*)card
->cid
) + 3, 6);
1418 snprintf(pbuf
, sizeof(pbuf
), "%s Rev %d.%d", card_name
,
1419 (int) mmc_extract_bits(card
->cid
, 72, 4),
1420 (int) mmc_extract_bits(card
->cid
, 76, 4));
1421 lcd_puts(0, 1, pbuf
);
1422 snprintf(pbuf
, sizeof(pbuf
), "Prod: %d/%d",
1423 (int) mmc_extract_bits(card
->cid
, 112, 4),
1424 (int) mmc_extract_bits(card
->cid
, 116, 4) + 1997);
1425 lcd_puts(0, 2, pbuf
);
1426 snprintf(pbuf
, sizeof(pbuf
), "Ser#: 0x%08lx",
1427 mmc_extract_bits(card
->cid
, 80, 32));
1428 lcd_puts(0, 3, pbuf
);
1429 snprintf(pbuf
, sizeof(pbuf
), "M=%02x, O=%04x",
1430 (int) mmc_extract_bits(card
->cid
, 0, 8),
1431 (int) mmc_extract_bits(card
->cid
, 8, 16));
1432 lcd_puts(0, 4, pbuf
);
1433 snprintf(pbuf
, sizeof(pbuf
), "Blocks: 0x%06lx", card
->numblocks
);
1434 lcd_puts(0, 5, pbuf
);
1435 snprintf(pbuf
, sizeof(pbuf
), "Blksz.: %d", card
->blocksize
);
1436 lcd_puts(0, 6, pbuf
);
1438 else /* Technical details */
1440 output_dyn_value(pbuf2
, sizeof pbuf2
, card
->speed
/ 1000,
1442 snprintf(pbuf
, sizeof pbuf
, "Speed: %s", pbuf2
);
1443 lcd_puts(0, 1, pbuf
);
1445 output_dyn_value(pbuf2
, sizeof pbuf2
, card
->tsac
,
1447 snprintf(pbuf
, sizeof pbuf
, "Tsac: %s", pbuf2
);
1448 lcd_puts(0, 2, pbuf
);
1450 snprintf(pbuf
, sizeof(pbuf
), "Nsac: %d clk", card
->nsac
);
1451 lcd_puts(0, 3, pbuf
);
1452 snprintf(pbuf
, sizeof(pbuf
), "R2W: *%d", card
->r2w_factor
);
1453 lcd_puts(0, 4, pbuf
);
1454 snprintf(pbuf
, sizeof(pbuf
), "IRmax: %d..%d mA",
1455 i_vmin
[mmc_extract_bits(card
->csd
, 66, 3)],
1456 i_vmax
[mmc_extract_bits(card
->csd
, 69, 3)]);
1457 lcd_puts(0, 5, pbuf
);
1458 snprintf(pbuf
, sizeof(pbuf
), "IWmax: %d..%d mA",
1459 i_vmin
[mmc_extract_bits(card
->csd
, 72, 3)],
1460 i_vmax
[mmc_extract_bits(card
->csd
, 75, 3)]);
1461 lcd_puts(0, 6, pbuf
);
1465 lcd_puts(0, 1, "Not found!");
1469 switch (button_get_w_tmo(HZ
/2))
1472 case SETTINGS_CANCEL
:
1492 #else /* !HAVE_MMC */
1493 static bool dbg_disk_info(void)
1499 const int max_page
= 11;
1500 unsigned short* identify_info
= ata_get_identify();
1501 bool timing_info_present
= false;
1502 char pio3
[2], pio4
[2];
1504 #ifdef HAVE_LCD_BITMAP
1505 lcd_setmargins(0, 0);
1512 lcd_clear_display();
1513 #ifdef HAVE_LCD_BITMAP
1514 lcd_puts(0, y
++, "Disk info:");
1520 for (i
=0; i
< 20; i
++)
1521 ((unsigned short*)buf
)[i
]=identify_info
[i
+27];
1523 /* kill trailing space */
1524 for (i
=39; i
&& buf
[i
]==' '; i
--)
1526 lcd_puts(0, y
++, "Model");
1527 lcd_puts_scroll(0, y
++, buf
);
1531 for (i
=0; i
< 4; i
++)
1532 ((unsigned short*)buf
)[i
]=identify_info
[i
+23];
1534 lcd_puts(0, y
++, "Firmware");
1535 lcd_puts(0, y
++, buf
);
1539 snprintf(buf
, sizeof buf
, "%ld MB",
1540 ((unsigned long)identify_info
[61] << 16 |
1541 (unsigned long)identify_info
[60]) / 2048 );
1542 lcd_puts(0, y
++, "Size");
1543 lcd_puts(0, y
++, buf
);
1548 fat_size( IF_MV2(0,) NULL
, &free
);
1549 snprintf(buf
, sizeof buf
, "%ld MB", free
/ 1024 );
1550 lcd_puts(0, y
++, "Free");
1551 lcd_puts(0, y
++, buf
);
1556 snprintf(buf
, sizeof buf
, "%d ms", ata_spinup_time
* (1000/HZ
));
1557 lcd_puts(0, y
++, "Spinup time");
1558 lcd_puts(0, y
++, buf
);
1562 i
= identify_info
[83] & (1<<3);
1563 lcd_puts(0, y
++, "Power mgmt:");
1564 lcd_puts(0, y
++, i
? "enabled" : "unsupported");
1568 i
= identify_info
[83] & (1<<9);
1569 lcd_puts(0, y
++, "Noise mgmt:");
1570 lcd_puts(0, y
++, i
? "enabled" : "unsupported");
1574 i
= identify_info
[82] & (1<<6);
1575 lcd_puts(0, y
++, "Read-ahead:");
1576 lcd_puts(0, y
++, i
? "enabled" : "unsupported");
1580 timing_info_present
= identify_info
[53] & (1<<1);
1581 if(timing_info_present
) {
1584 lcd_puts(0, y
++, "PIO modes:");
1585 pio3
[0] = (identify_info
[64] & (1<<0)) ? '3' : 0;
1586 pio4
[0] = (identify_info
[64] & (1<<1)) ? '4' : 0;
1587 snprintf(buf
, 128, "0 1 2 %s %s", pio3
, pio4
);
1588 lcd_puts(0, y
++, buf
);
1590 lcd_puts(0, y
++, "No PIO mode info");
1595 timing_info_present
= identify_info
[53] & (1<<1);
1596 if(timing_info_present
) {
1597 lcd_puts(0, y
++, "Cycle times");
1598 snprintf(buf
, 128, "%dns/%dns",
1601 lcd_puts(0, y
++, buf
);
1603 lcd_puts(0, y
++, "No timing info");
1608 timing_info_present
= identify_info
[53] & (1<<1);
1609 if(timing_info_present
) {
1610 i
= identify_info
[49] & (1<<11);
1611 snprintf(buf
, 128, "IORDY support: %s", i
? "yes" : "no");
1612 lcd_puts(0, y
++, buf
);
1613 i
= identify_info
[49] & (1<<10);
1614 snprintf(buf
, 128, "IORDY disable: %s", i
? "yes" : "no");
1615 lcd_puts(0, y
++, buf
);
1617 lcd_puts(0, y
++, "No timing info");
1622 lcd_puts(0, y
++, "Cluster size");
1623 snprintf(buf
, 128, "%d bytes", fat_get_cluster_size(IF_MV(0)));
1624 lcd_puts(0, y
++, buf
);
1629 /* Wait for a key to be pushed */
1630 key
= button_get_w_tmo(HZ
*5);
1632 case SETTINGS_CANCEL
:
1642 if (++page
> max_page
)
1648 audio_stop(); /* stop playback, to avoid disk access */
1649 lcd_clear_display();
1650 lcd_puts(0,0,"Scanning");
1651 lcd_puts(0,1,"disk...");
1653 fat_recalc_free(IF_MV(0));
1662 #endif /* !HAVE_MMC */
1664 #if CONFIG_CPU == SH7034
1665 bool dbg_save_roms(void)
1668 int oldmode
= system_memory_guard(MEMGUARD_NONE
);
1670 fd
= creat("/internal_rom_0000-FFFF.bin", O_WRONLY
);
1673 write(fd
, (void *)0, 0x10000);
1677 fd
= creat("/internal_rom_2000000-203FFFF.bin", O_WRONLY
);
1680 write(fd
, (void *)0x2000000, 0x40000);
1684 system_memory_guard(oldmode
);
1687 #elif defined CPU_COLDFIRE
1688 bool dbg_save_roms(void)
1691 int oldmode
= system_memory_guard(MEMGUARD_NONE
);
1693 #if defined(IRIVER_H100_SERIES)
1694 fd
= creat("/internal_rom_000000-1FFFFF.bin", O_WRONLY
);
1697 write(fd
, (void *)0, 0x200000);
1702 system_memory_guard(oldmode
);
1708 bool dbg_fm_radio(void)
1714 #ifdef HAVE_LCD_BITMAP
1715 lcd_setmargins(0, 0);
1720 lcd_clear_display();
1721 fm_detected
= radio_hardware_present();
1723 snprintf(buf
, sizeof buf
, "HW detected: %s", fm_detected
?"yes":"no");
1724 lcd_puts(0, 0, buf
);
1727 button
= button_get(true);
1731 case SETTINGS_CANCEL
:
1737 #endif /* CONFIG_TUNER */
1739 #ifdef HAVE_LCD_BITMAP
1740 extern bool do_screendump_instead_of_usb
;
1742 bool dbg_screendump(void)
1744 do_screendump_instead_of_usb
= !do_screendump_instead_of_usb
;
1745 splash(HZ
, true, "Screendump %s",
1746 do_screendump_instead_of_usb
?"enabled":"disabled");
1749 #endif /* HAVE_LCD_BITMAP */
1751 #if CONFIG_CPU == SH7034 || defined(CPU_COLDFIRE)
1752 bool dbg_set_memory_guard(void)
1754 static const struct opt_items names
[MAXMEMGUARD
] = {
1756 { "Flash ROM writes", -1 },
1757 { "Zero area (all)", -1 }
1759 int mode
= system_memory_guard(MEMGUARD_KEEP
);
1761 set_option( "Catch mem accesses", &mode
, INT
, names
, MAXMEMGUARD
, NULL
);
1762 system_memory_guard(mode
);
1766 #endif /* CONFIG_CPU == SH7034 || defined(CPU_COLDFIRE) */
1768 bool debug_menu(void)
1773 static const struct menu_item items
[] = {
1774 #if CONFIG_CPU == SH7034 || defined(CPU_COLDFIRE)
1775 { "Dump ROM contents", dbg_save_roms
},
1776 { "View I/O ports", dbg_ports
},
1778 #ifdef HAVE_ADJUSTABLE_CPU_FREQ
1779 { "CPU frequency", dbg_cpufreq
},
1781 #if defined(IRIVER_H100_SERIES) && !defined(SIMULATOR)
1782 { "PCM recording", pcm_rec_screen
},
1783 { "S/PDIF analyzer", dbg_spdif
},
1785 #if CONFIG_CPU == SH7034 || defined(CPU_COLDFIRE)
1786 { "Catch mem accesses", dbg_set_memory_guard
},
1788 { "View OS stacks", dbg_os
},
1789 #ifdef HAVE_LCD_BITMAP
1790 { "View battery", view_battery
},
1791 { "Screendump", dbg_screendump
},
1793 { "View HW info", dbg_hw_info
},
1794 { "View partitions", dbg_partitions
},
1796 { "View MMC info", dbg_mmc_info
},
1798 { "View disk info", dbg_disk_info
},
1800 #ifdef HAVE_LCD_BITMAP
1801 { "View audio thread", dbg_audio_thread
},
1803 { "pm histogram", peak_meter_histogram
},
1804 #endif /* PM_DEBUG */
1805 #endif /* HAVE_LCD_BITMAP */
1806 { "View runtime", view_runtime
},
1808 { "FM Radio", dbg_fm_radio
},
1810 #ifdef ROCKBOX_HAS_LOGF
1811 {"logf", logfdisplay
},
1812 {"logfdump", logfdump
},
1816 m
=menu_init( items
, sizeof items
/ sizeof(struct menu_item
), NULL
,
1818 result
= menu_run(m
);
1824 #endif /* SIMULATOR */