summaryrefslogtreecommitdiff
path: root/apps/pcmbuf.c
diff options
context:
space:
mode:
authorMichael Sevakis <jethead71@rockbox.org>2007-02-07 00:51:50 +0000
committerMichael Sevakis <jethead71@rockbox.org>2007-02-07 00:51:50 +0000
commitaba6ca0881d1481b4047b2d7834d70ca2eb5c64b (patch)
tree6635b98840dcf4936b3c1ca641c00c32ea1b3e7f /apps/pcmbuf.c
parentdd50c863e60488662dee8f28f7292389ade42bac (diff)
downloadrockbox-aba6ca0881d1481b4047b2d7834d70ca2eb5c64b.tar.gz
rockbox-aba6ca0881d1481b4047b2d7834d70ca2eb5c64b.zip
Fix resampling clicking as much as possible at the moment. 1) Upsampling clicked because of size inaccuracies returned by DSP. Fix by simplifying audio system to use per-channel sample count from codec to pcm buffer. 2) Downsampling affected by 1) and was often starting passed the end of the data when not enough was available to generate an output sample. Fix by clamping input range to last sample in buffer and using the last sample value in the buffer. A perfect fix will require a double buffering scheme on the resampler to sufficient data during small data transients on both ends at all times of the down ratio on input and the up ratio on output.
git-svn-id: svn://svn.rockbox.org/rockbox/trunk@12218 a1c6a512-1295-4272-9138-f99709370657
Diffstat (limited to 'apps/pcmbuf.c')
-rw-r--r--apps/pcmbuf.c30
1 files changed, 15 insertions, 15 deletions
diff --git a/apps/pcmbuf.c b/apps/pcmbuf.c
index f9d60e9b58..e2b1d7f87b 100644
--- a/apps/pcmbuf.c
+++ b/apps/pcmbuf.c
@@ -791,21 +791,20 @@ static bool prepare_insert(size_t length)
791 return true; 791 return true;
792} 792}
793 793
794void* pcmbuf_request_buffer(size_t length, size_t *realsize) 794void* pcmbuf_request_buffer(int *count)
795{ 795{
796 if (crossfade_init) 796 if (crossfade_init)
797 crossfade_start(); 797 crossfade_start();
798 798
799 if (crossfade_active) { 799 if (crossfade_active) {
800 *realsize = MIN(length, PCMBUF_MIX_CHUNK); 800 *count = MIN(*count, PCMBUF_MIX_CHUNK/4);
801 return fadebuf; 801 return fadebuf;
802 } 802 }
803 else 803 else
804 { 804 {
805 if(prepare_insert(length)) 805 if(prepare_insert(*count << 2))
806 { 806 {
807 size_t audiobuffer_index = audiobuffer_pos + audiobuffer_fillpos; 807 size_t audiobuffer_index = audiobuffer_pos + audiobuffer_fillpos;
808 *realsize = length;
809 if (pcmbuf_size - audiobuffer_index >= PCMBUF_MIN_CHUNK) 808 if (pcmbuf_size - audiobuffer_index >= PCMBUF_MIN_CHUNK)
810 { 809 {
811 /* Usual case, there's space here */ 810 /* Usual case, there's space here */
@@ -821,34 +820,31 @@ void* pcmbuf_request_buffer(size_t length, size_t *realsize)
821 } 820 }
822 else 821 else
823 { 822 {
824 *realsize = 0;
825 return NULL; 823 return NULL;
826 } 824 }
827 } 825 }
828} 826}
829 827
830void* pcmbuf_request_voice_buffer(size_t length, size_t *realsize, bool mix) 828void* pcmbuf_request_voice_buffer(int *count, bool mix)
831{ 829{
832 if (mix) 830 if (mix)
833 { 831 {
834 if (pcmbuf_read == NULL) 832 if (pcmbuf_read == NULL)
835 { 833 {
836 *realsize = 0;
837 return NULL; 834 return NULL;
838 } 835 }
839 else if (pcmbuf_mix_chunk || pcmbuf_read->link) 836 else if (pcmbuf_mix_chunk || pcmbuf_read->link)
840 { 837 {
841 *realsize = MIN(length, PCMBUF_MIX_CHUNK); 838 *count = MIN(*count, PCMBUF_MIX_CHUNK/4);
842 return voicebuf; 839 return voicebuf;
843 } 840 }
844 else 841 else
845 { 842 {
846 *realsize = 0;
847 return NULL; 843 return NULL;
848 } 844 }
849 } 845 }
850 else 846 else
851 return pcmbuf_request_buffer(length, realsize); 847 return pcmbuf_request_buffer(count);
852} 848}
853 849
854bool pcmbuf_is_crossfade_active(void) 850bool pcmbuf_is_crossfade_active(void)
@@ -856,8 +852,10 @@ bool pcmbuf_is_crossfade_active(void)
856 return crossfade_active || crossfade_init; 852 return crossfade_active || crossfade_init;
857} 853}
858 854
859void pcmbuf_write_complete(size_t length) 855void pcmbuf_write_complete(int count)
860{ 856{
857 size_t length = (size_t)(unsigned int)count << 2;
858
861 if (crossfade_active) 859 if (crossfade_active)
862 { 860 {
863 flush_crossfade(fadebuf, length); 861 flush_crossfade(fadebuf, length);
@@ -874,8 +872,10 @@ void pcmbuf_write_complete(size_t length)
874} 872}
875 873
876#if 0 874#if 0
877bool pcmbuf_insert_buffer(char *buf, size_t length) 875bool pcmbuf_insert_buffer(char *buf, int count)
878{ 876{
877 size_t length = (size_t)(unsigned int)count << 2;
878
879 if (crossfade_active) 879 if (crossfade_active)
880 { 880 {
881 flush_crossfade(buf, length); 881 flush_crossfade(buf, length);
@@ -980,7 +980,7 @@ int pcmbuf_mix_free(void)
980 return 100; 980 return 100;
981} 981}
982 982
983void pcmbuf_mix_voice(size_t length) 983void pcmbuf_mix_voice(int count)
984{ 984{
985 short *ibuf = (short *)voicebuf; 985 short *ibuf = (short *)voicebuf;
986 short *obuf; 986 short *obuf;
@@ -998,9 +998,9 @@ void pcmbuf_mix_voice(size_t length)
998 obuf = (short *)pcmbuf_mix_chunk->addr; 998 obuf = (short *)pcmbuf_mix_chunk->addr;
999 chunk_samples = pcmbuf_mix_chunk->size / 2; 999 chunk_samples = pcmbuf_mix_chunk->size / 2;
1000 1000
1001 length /= 2; 1001 count <<= 1;
1002 1002
1003 while (length-- > 0) { 1003 while (count-- > 0) {
1004 int sample = *ibuf++; 1004 int sample = *ibuf++;
1005 if (pcmbuf_mix_sample >= chunk_samples) 1005 if (pcmbuf_mix_sample >= chunk_samples)
1006 { 1006 {