diff options
author | Michael Sevakis <jethead71@rockbox.org> | 2012-05-02 17:22:28 -0400 |
---|---|---|
committer | Michael Sevakis <jethead71@rockbox.org> | 2012-05-02 17:22:28 -0400 |
commit | da6cebb6b0b17b4a75a2bd4f51b7cf70b5dafe40 (patch) | |
tree | df0eb18120c38ec7b08d3ae1e0837f0781065e87 /apps/talk.c | |
parent | 3d3a144cf68186fd34f7bf11181b7757c7a6018d (diff) | |
download | rockbox-da6cebb6b0b17b4a75a2bd4f51b7cf70b5dafe40.tar.gz rockbox-da6cebb6b0b17b4a75a2bd4f51b7cf70b5dafe40.tar.bz2 rockbox-da6cebb6b0b17b4a75a2bd4f51b7cf70b5dafe40.zip |
Use buflib for the allocation of voice PCM resources.
Buffers are not allocated and thread is not created until the first
call where voice is required.
Adds a different callback (sync_callback) to buflib so that other
sorts of synchonization are possible, such as briefly locking-out the
PCM callback for a buffer move. It's sort of a messy addition but it
is needed so voice decoding won't have to be stopped when its buffer
is moved.
Change-Id: I4d4d8c35eed5dd15fb7ee7df9323af3d036e92b3
Diffstat (limited to 'apps/talk.c')
-rw-r--r-- | apps/talk.c | 58 |
1 files changed, 41 insertions, 17 deletions
diff --git a/apps/talk.c b/apps/talk.c index 4b0975083d..f3ca967d3a 100644 --- a/apps/talk.c +++ b/apps/talk.c @@ -31,7 +31,11 @@ #include "kernel.h" #include "settings.h" #include "settings_list.h" +#if CONFIG_CODEC == SWCODEC +#include "voice_thread.h" +#else #include "mp3_playback.h" +#endif #include "audio.h" #include "lang.h" #include "talk.h" @@ -43,7 +47,6 @@ #include "plugin.h" /* plugin_get_buffer() */ #include "debug.h" - /* Memory layout varies between targets because the Archos (MASCODEC) devices cannot mix voice and audio playback @@ -589,7 +592,6 @@ static void queue_clip(unsigned char* buf, long size, bool enqueue) return; } - static void alloc_thumbnail_buf(void) { /* use the audio buffer now, need to release before loading a voice */ @@ -614,8 +616,22 @@ static void reset_state(void) #endif p_silence = NULL; /* pause clip not accessible */ - voicebuf = NULL; + voicebuf = NULL; /* voice buffer is gone */ +} + +#if CONFIG_CODEC == SWCODEC +static bool restore_state(void) +{ + if (!voicebuf) + { + size_t size; + audio_restore_playback(AUDIO_WANT_VOICE); + voicebuf = audio_get_buffer(false, &size); + } + + return !!voicebuf; } +#endif /* CONFIG_CODEC == SWCODEC */ /***************** Public implementation *****************/ @@ -655,7 +671,7 @@ void talk_init(void) voicefile_size = filesize(filehandle); - audio_get_buffer(false, NULL); /* Must tell audio to reinitialize */ + audio_get_buffer(false, NULL); /* Must tell audio to reinitialize */ reset_state(); /* use this for most of our inits */ #ifdef TALK_PARTIAL_LOAD @@ -693,9 +709,14 @@ void talk_init(void) voicefile_size = 0; } - alloc_thumbnail_buf(); close(filehandle); /* close again, this was just to detect presence */ filehandle = -1; + +#if CONFIG_CODEC == SWCODEC + /* Safe to init voice playback engine now since we now know if talk is + required or not */ + voice_thread_init(); +#endif } #if CONFIG_CODEC == SWCODEC @@ -709,7 +730,7 @@ bool talk_voice_required(void) #endif /* return size of voice file */ -static int talk_get_buffer(void) +static size_t talk_get_buffer_size(void) { #if CONFIG_CODEC == SWCODEC return voicefile_size + MAX_THUMBNAIL_BUFSIZE; @@ -726,10 +747,11 @@ size_t talkbuf_init(char *bufstart) if (changed) /* must reload voice file */ reset_state(); + if (bufstart) voicebuf = bufstart; - return talk_get_buffer(); + return talk_get_buffer_size(); } /* somebody else claims the mp3 buffer, e.g. for regular play/record */ @@ -748,29 +770,27 @@ void talk_buffer_steal(void) reset_state(); } - /* play a voice ID from voicefile */ int talk_id(int32_t id, bool enqueue) { long clipsize; - int temp = talk_get_buffer(); unsigned char* clipbuf; int32_t unit; int decimals; if (talk_temp_disable_count > 0) return -1; /* talking has been disabled */ -#if CONFIG_CODEC != SWCODEC +#if CONFIG_CODEC == SWCODEC + /* If talk buffer was stolen, it must be restored for voicefile's sake */ + if (!restore_state()) + return -1; /* cannot get any space */ +#else if (audio_status()) /* busy, buffer in use */ return -1; #endif - /* try to get audio buffer until talkbuf_init() is called */ - if (!voicebuf) - voicebuf = audio_get_buffer(true, (size_t*)&temp); - - if (p_voicefile == NULL && has_voicefile) - load_voicefile(false, voicebuf, MIN(talk_get_buffer(),temp)); /* reload needed */ + if (p_voicefile == NULL && has_voicefile) /* reload needed? */ + load_voicefile(false, voicebuf, talk_get_buffer_size()); if (p_voicefile == NULL) /* still no voices? */ return -1; @@ -842,7 +862,11 @@ static int _talk_file(const char* filename, if (talk_temp_disable_count > 0) return -1; /* talking has been disabled */ -#if CONFIG_CODEC != SWCODEC +#if CONFIG_CODEC == SWCODEC + /* If talk buffer was stolen, it must be restored for thumbnail's sake */ + if (!restore_state()) + return -1; /* cannot get any space */ +#else if (audio_status()) /* busy, buffer in use */ return -1; #endif |