1 /***************************************************************************
3 * Open \______ \ ____ ____ | | _\_ |__ _______ ___
4 * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
5 * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
6 * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
10 * Copyright (C) 2002 Björn Stenberg
12 * This program is free software; you can redistribute it and/or
13 * modify it under the terms of the GNU General Public License
14 * as published by the Free Software Foundation; either version 2
15 * of the License, or (at your option) any later version.
17 * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
18 * KIND, either express or implied.
20 ****************************************************************************/
32 #include "backlight.h"
33 #include "sound_menu.h"
35 #include "powermgmt.h"
38 #include "option_select.h"
47 #ifdef HAVE_LCD_BITMAP
48 #include "scrollbar.h"
49 #include "peakmeter.h"
55 static unsigned char pluginbuf
[PLUGIN_BUFFER_SIZE
];
56 void *sim_plugin_load(char *plugin
, void **pd
);
57 void sim_plugin_close(void *pd
);
58 void sim_lcd_ex_init(int shades
, unsigned long (*getpixel
)(int, int));
59 void sim_lcd_ex_update_rect(int x
, int y
, int width
, int height
);
61 #define sim_plugin_close(x)
62 extern unsigned char pluginbuf
[];
66 /* for actual plugins only, not for codecs */
67 static bool plugin_loaded
= false;
68 static int plugin_size
= 0;
69 static bool (*pfn_tsr_exit
)(bool reenter
) = NULL
; /* TSR exit callback */
70 static char current_plugin
[MAX_PATH
];
72 char *plugin_get_current_filename(void);
74 extern struct thread_entry threads
[MAXTHREADS
];
76 static const struct plugin_api rockbox_api
= {
87 #ifdef HAVE_LCD_CHARCELLS
89 lcd_get_locked_pattern
,
97 &lcd_framebuffer
[0][0],
108 lcd_mono_bitmap_part
,
121 lcd_bitmap_transparent_part
,
122 lcd_bitmap_transparent
,
124 #if defined(TOSHIBA_GIGABEAT_F) || defined(SANSA_E200) || defined(SANSA_C200) \
125 || defined(IRIVER_H10) || defined(COWON_D2)
128 #elif (LCD_DEPTH < 4) && !defined(SIMULATOR)
131 #endif /* LCD_DEPTH */
133 lcd_puts_scroll_style
,
134 #ifdef HAVE_LCD_INVERT
135 lcd_set_invert_display
,
136 #endif /* HAVE_LCD_INVERT */
137 #if defined(HAVE_LCD_ENABLE) && defined(HAVE_LCD_COLOR)
149 #endif /* HAVE_LCD_BITMAP */
154 backlight_set_timeout
,
155 #ifdef HAVE_BACKLIGHT_BRIGHTNESS
156 backlight_set_brightness
,
157 #endif /* HAVE_BACKLIGHT_BRIGHTNESS */
160 backlight_set_timeout_plugged
,
166 #ifdef HAVE_REMOTE_LCD
168 lcd_remote_set_contrast
,
169 lcd_remote_clear_display
,
171 lcd_remote_puts_scroll
,
172 lcd_remote_stop_scroll
,
173 lcd_remote_set_drawmode
,
174 lcd_remote_get_drawmode
,
176 lcd_remote_getstringsize
,
177 lcd_remote_drawpixel
,
183 lcd_remote_mono_bitmap_part
,
184 lcd_remote_mono_bitmap
,
186 lcd_remote_puts_style
,
187 lcd_remote_puts_scroll_style
,
188 &lcd_remote_framebuffer
[0][0],
190 lcd_remote_update_rect
,
193 remote_backlight_off
,
194 remote_backlight_set_timeout
,
196 remote_backlight_set_timeout_plugged
,
198 #endif /* HAVE_REMOTE_LCD */
200 {&screens
[SCREEN_MAIN
], &screens
[SCREEN_REMOTE
]},
202 {&screens
[SCREEN_MAIN
]},
204 #if defined(HAVE_REMOTE_LCD) && (LCD_REMOTE_DEPTH > 1)
205 lcd_remote_set_foreground
,
206 lcd_remote_get_foreground
,
207 lcd_remote_set_background
,
208 lcd_remote_get_background
,
209 lcd_remote_bitmap_part
,
212 viewport_set_defaults
,
213 viewportmanager_set_statusbar
,
217 gui_synclist_set_nb_items
,
218 gui_synclist_set_icon_callback
,
219 gui_synclist_get_nb_items
,
220 gui_synclist_get_sel_pos
,
222 gui_synclist_select_item
,
223 gui_synclist_add_item
,
224 gui_synclist_del_item
,
225 gui_synclist_limit_scroll
,
226 gui_synclist_do_button
,
227 gui_synclist_set_title
,
229 simplelist_info_init
,
230 simplelist_show_list
,
236 #ifdef HAVE_BUTTON_DATA
241 #ifdef HAS_BUTTON_HOLD
244 #ifdef HAVE_TOUCHSCREEN
245 touchscreen_set_mode
,
248 #ifdef HAVE_BUTTON_LIGHT
249 buttonlight_set_timeout
,
252 #ifdef HAVE_BUTTONLIGHT_BRIGHTNESS
253 buttonlight_set_brightness
,
254 #endif /* HAVE_BUTTONLIGHT_BRIGHTNESS */
255 #endif /* HAVE_BUTTON_LIGHT */
258 (open_func
)PREFIX(open
),
260 (read_func
)PREFIX(read
),
262 (creat_func
)PREFIX(creat
),
263 (write_func
)PREFIX(write
),
274 #if USING_STORAGE_CALLBACK
275 register_storage_idle_func
,
276 unregister_storage_idle_func
,
277 #endif /* USING_STORAGE_CALLBACK */
279 create_numbered_filename
,
294 default_event_handler
,
295 default_event_handler_ex
,
300 #if (CONFIG_CODEC == SWCODEC)
307 reset_poweroff_timer
,
312 #ifdef HAVE_ADJUSTABLE_CPU_FREQ
313 #ifdef CPU_BOOST_LOGGING
318 #endif /* HAVE_ADJUSTABLE_CPU_FREQ */
319 #endif /* !SIMULATOR */
320 #ifdef HAVE_SCHEDULER_BOOSTCTRL
324 #ifdef CACHE_FUNCTIONS_AS_CALL
336 #if CONFIG_CODEC == SWCODEC
337 queue_enable_queue_send
,
347 __cyg_profile_func_enter
,
348 __cyg_profile_func_exit
,
352 /* special simulator hooks */
353 #if defined(HAVE_LCD_BITMAP) && LCD_DEPTH < 8
355 sim_lcd_ex_update_rect
,
359 /* strings and memory */
402 #if CONFIG_CODEC != SWCODEC
406 #if CONFIG_CODEC == SWCODEC
407 &audio_master_sampr_list
[0],
416 pcm_get_bytes_waiting
,
420 #ifdef HAVE_RECORDING
427 pcm_calculate_rec_peaks
,
428 audio_set_recording_gain
,
429 #endif /* HAVE_RECORDING */
430 #if INPUT_SRC_CAPS != 0
431 audio_set_output_source
,
432 audio_set_input_source
,
439 #endif /* CONFIG_CODEC == SWCODEC */
441 /* playback control */
454 audio_has_changed_track
,
456 audio_flush_and_reload_tracks
,
458 #if !defined(SIMULATOR) && (CONFIG_CODEC != SWCODEC)
459 mpeg_get_last_header
,
461 #if (CONFIG_CODEC == MAS3587F) || (CONFIG_CODEC == MAS3539F) || \
462 (CONFIG_CODEC == SWCODEC)
466 #if !defined(SIMULATOR) && (CONFIG_CODEC != SWCODEC)
467 /* MAS communication */
472 #if (CONFIG_CODEC == MAS3587F) || (CONFIG_CODEC == MAS3539F)
479 #endif /* !SIMULATOR && CONFIG_CODEC != SWCODEC */
485 gui_syncstatusbar_draw
,
494 #ifdef HAVE_LCD_COLOR
498 /* action handling */
512 # if CONFIG_CHARGING == CHARGING_MONITOR
516 #ifdef HAVE_USB_POWER
531 plugin_get_audio_buffer
,
533 plugin_get_current_filename
,
534 #ifdef PLUGIN_USE_IRAM
537 #if defined(DEBUG) || defined(SIMULATOR)
540 #ifdef ROCKBOX_HAS_LOGF
546 #if CONFIG_CODEC == SWCODEC
555 #if (CONFIG_CODEC == MAS3587F) || (CONFIG_CODEC == MAS3539F)
556 peak_meter_scale_value
,
557 peak_meter_set_use_dbfs
,
558 peak_meter_get_use_dbfs
,
560 #ifdef HAVE_LCD_BITMAP
562 screen_dump_set_hook
,
569 #ifdef HAVE_WHEEL_POSITION
574 #ifdef IRIVER_H100_SERIES
575 /* Routines for the iriver_flash -plugin. */
576 detect_original_firmware
,
577 detect_flashed_ramimage
,
578 detect_flashed_romimage
,
581 #if (CONFIG_CODEC == SWCODEC)
594 buf_request_buffer_handle
,
601 tagcache_search_set_uniqbuf
,
602 tagcache_search_add_filter
,
605 tagcache_search_finish
,
606 tagcache_get_numeric
,
611 search_albumart_files
,
616 #ifdef HAVE_SEMAPHORE_OBJECTS
623 /* new stuff at the end, sort into place next time
624 the API gets incompatible */
627 int plugin_load(const char* plugin
, const void* parameter
)
630 struct plugin_header
*hdr
;
633 #else /* !SIMULATOR */
639 #endif /* !SIMULATOR */
642 fb_data
* old_backdrop
;
645 if (pfn_tsr_exit
!= NULL
) /* if we have a resident old plugin: */
647 if (pfn_tsr_exit(!strcmp(current_plugin
, plugin
)) == false )
649 /* not allowing another plugin to load */
653 plugin_loaded
= false;
656 splash(0, ID2P(LANG_WAIT
));
657 strcpy(current_plugin
, plugin
);
660 hdr
= sim_plugin_load((char *)plugin
, &pd
);
662 splashf(HZ
*2, str(LANG_PLUGIN_CANT_OPEN
), plugin
);
666 || hdr
->magic
!= PLUGIN_MAGIC
667 || hdr
->target_id
!= TARGET_ID
) {
668 sim_plugin_close(pd
);
669 splash(HZ
*2, str(LANG_PLUGIN_WRONG_MODEL
));
672 if (hdr
->api_version
> PLUGIN_API_VERSION
673 || hdr
->api_version
< PLUGIN_MIN_API_VERSION
) {
674 sim_plugin_close(pd
);
675 splash(HZ
*2, str(LANG_PLUGIN_WRONG_VERSION
));
679 fd
= open(plugin
, O_RDONLY
);
681 splashf(HZ
*2, str(LANG_PLUGIN_CANT_OPEN
), plugin
);
685 /* Make sure COP cache is flushed and invalidated before loading */
686 my_core
= switch_core(CURRENT_CORE
^ 1);
688 switch_core(my_core
);
691 readsize
= read(fd
, pluginbuf
, PLUGIN_BUFFER_SIZE
);
695 splashf(HZ
*2, str(LANG_READ_FAILED
), plugin
);
698 hdr
= (struct plugin_header
*)pluginbuf
;
700 if ((unsigned)readsize
<= sizeof(struct plugin_header
)
701 || hdr
->magic
!= PLUGIN_MAGIC
702 || hdr
->target_id
!= TARGET_ID
703 || hdr
->load_addr
!= pluginbuf
704 || hdr
->end_addr
> pluginbuf
+ PLUGIN_BUFFER_SIZE
) {
705 splash(HZ
*2, str(LANG_PLUGIN_WRONG_MODEL
));
708 if (hdr
->api_version
> PLUGIN_API_VERSION
709 || hdr
->api_version
< PLUGIN_MIN_API_VERSION
) {
710 splash(HZ
*2, str(LANG_PLUGIN_WRONG_VERSION
));
713 plugin_size
= hdr
->end_addr
- pluginbuf
;
715 /* zero out bss area only, above guards end of pluginbuf */
716 if (plugin_size
> readsize
)
717 memset(pluginbuf
+ readsize
, 0, plugin_size
- readsize
);
720 plugin_loaded
= true;
723 #if defined HAVE_LCD_BITMAP && LCD_DEPTH > 1
724 old_backdrop
= lcd_get_backdrop();
729 #ifdef HAVE_REMOTE_LCD
730 lcd_remote_clear_display();
735 viewportmanager_set_statusbar(false);
737 rc
= hdr
->entry_point(&rockbox_api
, parameter
);
739 viewportmanager_set_statusbar(true);
741 button_clear_queue();
743 #ifdef HAVE_LCD_BITMAP
745 lcd_set_backdrop(old_backdrop
);
746 #ifdef HAVE_LCD_COLOR
747 lcd_set_drawinfo(DRMODE_SOLID
, global_settings
.fg_color
,
748 global_settings
.bg_color
);
750 lcd_set_drawinfo(DRMODE_SOLID
, LCD_DEFAULT_FG
, LCD_DEFAULT_BG
);
752 #else /* LCD_DEPTH == 1 */
753 lcd_set_drawmode(DRMODE_SOLID
);
754 #endif /* LCD_DEPTH */
755 #endif /* HAVE_LCD_BITMAP */
760 #ifdef HAVE_REMOTE_LCD
761 #if LCD_REMOTE_DEPTH > 1
762 lcd_remote_set_drawinfo(DRMODE_SOLID
, LCD_REMOTE_DEFAULT_FG
,
763 LCD_REMOTE_DEFAULT_BG
);
765 lcd_remote_set_drawmode(DRMODE_SOLID
);
767 lcd_remote_clear_display();
775 if (pfn_tsr_exit
== NULL
)
776 plugin_loaded
= false;
778 sim_plugin_close(pd
);
784 case PLUGIN_USB_CONNECTED
:
785 return PLUGIN_USB_CONNECTED
;
788 splash(HZ
*2, str(LANG_PLUGIN_ERROR
));
795 /* Returns a pointer to the portion of the plugin buffer that is not already
796 being used. If no plugin is loaded, returns the entire plugin buffer */
797 void* plugin_get_buffer(size_t *buffer_size
)
803 if (plugin_size
>= PLUGIN_BUFFER_SIZE
)
806 *buffer_size
= PLUGIN_BUFFER_SIZE
-plugin_size
;
807 buffer_pos
= plugin_size
;
811 *buffer_size
= PLUGIN_BUFFER_SIZE
;
815 return &pluginbuf
[buffer_pos
];
818 /* Returns a pointer to the mp3 buffer.
819 Playback gets stopped, to avoid conflicts.
820 Talk buffer is stolen as well.
822 void* plugin_get_audio_buffer(size_t *buffer_size
)
824 #if CONFIG_CODEC == SWCODEC
825 return audio_get_buffer(true, buffer_size
);
828 talk_buffer_steal(); /* we use the mp3 buffer, need to tell */
829 *buffer_size
= audiobufend
- audiobuf
;
834 #ifdef PLUGIN_USE_IRAM
835 /* Initializes plugin IRAM */
836 void plugin_iram_init(char *iramstart
, char *iramcopy
, size_t iram_size
,
837 char *iedata
, size_t iedata_size
)
839 /* We need to stop audio playback in order to use codec IRAM */
841 memcpy(iramstart
, iramcopy
, iram_size
);
842 memset(iedata
, 0, iedata_size
);
843 memset(iramcopy
, 0, iram_size
);
845 /* writeback cleared iedata and iramcopy areas */
849 #endif /* PLUGIN_USE_IRAM */
851 /* The plugin wants to stay resident after leaving its main function, e.g.
852 runs from timer or own thread. The callback is registered to later
853 instruct it to free its resources before a new plugin gets loaded. */
854 void plugin_tsr(bool (*exit_callback
)(bool))
856 pfn_tsr_exit
= exit_callback
; /* remember the callback for later */
859 char *plugin_get_current_filename(void)
861 return current_plugin
;