diff options
-rw-r--r-- | apps/codecs/libspeex/Makefile | 2 | ||||
-rw-r--r-- | apps/codecs/libspeex/SOURCES | 10 | ||||
-rw-r--r-- | apps/codecs/libspeex/bits.c | 2 | ||||
-rw-r--r-- | apps/codecs/libspeex/config-speex.h | 14 | ||||
-rw-r--r-- | apps/codecs/libspeex/rockbox.h | 5 | ||||
-rw-r--r-- | apps/codecs/libspeex/speex_header.c | 2 | ||||
-rw-r--r-- | tools/Makefile | 6 | ||||
-rw-r--r-- | tools/rbspeex/Makefile | 56 | ||||
-rw-r--r-- | tools/rbspeex/rbspeexenc.c | 239 |
9 files changed, 332 insertions, 4 deletions
diff --git a/apps/codecs/libspeex/Makefile b/apps/codecs/libspeex/Makefile index 35a8535369..3bda53dca7 100644 --- a/apps/codecs/libspeex/Makefile +++ b/apps/codecs/libspeex/Makefile | |||
@@ -14,7 +14,7 @@ ifdef APPEXTRA | |||
14 | INCLUDES += $(patsubst %,-I$(APPSDIR)/%,$(subst :, ,$(APPEXTRA))) | 14 | INCLUDES += $(patsubst %,-I$(APPSDIR)/%,$(subst :, ,$(APPEXTRA))) |
15 | endif | 15 | endif |
16 | 16 | ||
17 | SPEEXOPTS = -DHAVE_CONFIG_H -DSPEEX_DISABLE_ENCODER | 17 | SPEEXOPTS = -DHAVE_CONFIG_H -DSPEEX_DISABLE_ENCODER -DROCKBOX |
18 | 18 | ||
19 | # We're faster on ARM-targets with -O1 instead of -O2 | 19 | # We're faster on ARM-targets with -O1 instead of -O2 |
20 | ifeq ($(CPU),arm) | 20 | ifeq ($(CPU),arm) |
diff --git a/apps/codecs/libspeex/SOURCES b/apps/codecs/libspeex/SOURCES index 40ea5380b9..f036734589 100644 --- a/apps/codecs/libspeex/SOURCES +++ b/apps/codecs/libspeex/SOURCES | |||
@@ -24,12 +24,22 @@ speex.c | |||
24 | speex_callbacks.c | 24 | speex_callbacks.c |
25 | speex_header.c | 25 | speex_header.c |
26 | #ifndef ROCKBOX_VOICE_CODEC | 26 | #ifndef ROCKBOX_VOICE_CODEC |
27 | #ifndef ROCKBOX_VOICE_ENCODER | ||
27 | oggframing.c | 28 | oggframing.c |
29 | #endif | ||
28 | stereo.c | 30 | stereo.c |
29 | #endif | 31 | #endif |
32 | #ifdef ROCKBOX_VOICE_ENCODER | ||
33 | lpc.c | ||
34 | vbr.c | ||
35 | vq.c | ||
36 | window.c | ||
37 | resample.c | ||
38 | #else | ||
30 | #ifdef CPU_COLDFIRE | 39 | #ifdef CPU_COLDFIRE |
31 | filters_cf.S | 40 | filters_cf.S |
32 | ltp_cf.S | 41 | ltp_cf.S |
33 | #elif defined(CPU_ARM) | 42 | #elif defined(CPU_ARM) |
34 | filters_arm4.S | 43 | filters_arm4.S |
35 | #endif | 44 | #endif |
45 | #endif | ||
diff --git a/apps/codecs/libspeex/bits.c b/apps/codecs/libspeex/bits.c index d4b02a5a86..e460a39cf2 100644 --- a/apps/codecs/libspeex/bits.c +++ b/apps/codecs/libspeex/bits.c | |||
@@ -106,7 +106,7 @@ void speex_bits_rewind(SpeexBits *bits) | |||
106 | bits->overflow=0; | 106 | bits->overflow=0; |
107 | } | 107 | } |
108 | 108 | ||
109 | #if 0 | 109 | #ifndef SPEEX_VOICE_ENCODER |
110 | void speex_bits_read_from(SpeexBits *bits, char *chars, int len) | 110 | void speex_bits_read_from(SpeexBits *bits, char *chars, int len) |
111 | { | 111 | { |
112 | int i; | 112 | int i; |
diff --git a/apps/codecs/libspeex/config-speex.h b/apps/codecs/libspeex/config-speex.h index 1378fc2a69..ad1393fc60 100644 --- a/apps/codecs/libspeex/config-speex.h +++ b/apps/codecs/libspeex/config-speex.h | |||
@@ -1,8 +1,16 @@ | |||
1 | #ifndef ROCKBOX_VOICE_ENCODER | ||
1 | #include "../codec.h" | 2 | #include "../codec.h" |
2 | #include "autoconf.h" | 3 | #include "autoconf.h" |
4 | #else | ||
5 | #define ICODE_ATTR | ||
6 | #define IDATA_ATTR | ||
7 | #define IBSS_ATTR | ||
8 | #define ICONST_ATTR | ||
9 | #endif | ||
3 | /* config.h. Generated from config.h.in by configure. */ | 10 | /* config.h. Generated from config.h.in by configure. */ |
4 | /* config.h.in. Generated from configure.ac by autoheader. */ | 11 | /* config.h.in. Generated from configure.ac by autoheader. */ |
5 | 12 | ||
13 | #ifndef ROCKBOX_VOICE_ENCODER | ||
6 | /* Make use of ARM4E assembly optimizations */ | 14 | /* Make use of ARM4E assembly optimizations */ |
7 | #if defined(CPU_ARM) | 15 | #if defined(CPU_ARM) |
8 | #define ARM4_ASM | 16 | #define ARM4_ASM |
@@ -15,6 +23,7 @@ | |||
15 | 23 | ||
16 | /* Make use of Blackfin assembly optimizations */ | 24 | /* Make use of Blackfin assembly optimizations */ |
17 | /* #undef BFIN_ASM */ | 25 | /* #undef BFIN_ASM */ |
26 | #endif /* ROCKBOX_VOICE_ENCODER */ | ||
18 | 27 | ||
19 | /* Disable wideband codec */ | 28 | /* Disable wideband codec */ |
20 | /* #undef DISABLE_WIDEBAND */ | 29 | /* #undef DISABLE_WIDEBAND */ |
@@ -28,8 +37,13 @@ | |||
28 | /* Debug fixed-point implementation */ | 37 | /* Debug fixed-point implementation */ |
29 | /* #undef FIXED_DEBUG */ | 38 | /* #undef FIXED_DEBUG */ |
30 | 39 | ||
40 | #ifndef ROCKBOX_VOICE_ENCODER | ||
31 | /* Compile target codec as fixed point */ | 41 | /* Compile target codec as fixed point */ |
32 | #define FIXED_POINT | 42 | #define FIXED_POINT |
43 | #else | ||
44 | /* Compile voice clip encoder as floating point */ | ||
45 | #define FLOATING_POINT | ||
46 | #endif | ||
33 | 47 | ||
34 | /* Define to 1 if you have the <dlfcn.h> header file. */ | 48 | /* Define to 1 if you have the <dlfcn.h> header file. */ |
35 | /* #undef HAVE_DLFCN_H */ | 49 | /* #undef HAVE_DLFCN_H */ |
diff --git a/apps/codecs/libspeex/rockbox.h b/apps/codecs/libspeex/rockbox.h index 0f8c6d932f..0e0d3ed647 100644 --- a/apps/codecs/libspeex/rockbox.h +++ b/apps/codecs/libspeex/rockbox.h | |||
@@ -19,6 +19,9 @@ | |||
19 | #ifndef SPEEX_ROCKBOX_H | 19 | #ifndef SPEEX_ROCKBOX_H |
20 | #define SPEEX_ROCKBOX_H | 20 | #define SPEEX_ROCKBOX_H |
21 | 21 | ||
22 | /* We don't want all this stuff if we're building encoder */ | ||
23 | #ifndef ROCKBOX_VOICE_ENCODER | ||
24 | |||
22 | #include "../codec.h" | 25 | #include "../codec.h" |
23 | #include "../lib/codeclib.h" | 26 | #include "../lib/codeclib.h" |
24 | 27 | ||
@@ -106,5 +109,7 @@ static inline void _speex_putc(int ch, void *file) | |||
106 | //printf("%c", ch); | 109 | //printf("%c", ch); |
107 | } | 110 | } |
108 | 111 | ||
112 | #endif /* ROCKBOX_VOICE_ENCODER */ | ||
113 | |||
109 | #endif | 114 | #endif |
110 | 115 | ||
diff --git a/apps/codecs/libspeex/speex_header.c b/apps/codecs/libspeex/speex_header.c index eb4c199d46..30f47206c4 100644 --- a/apps/codecs/libspeex/speex_header.c +++ b/apps/codecs/libspeex/speex_header.c | |||
@@ -47,7 +47,7 @@ | |||
47 | /** Convert little endian */ | 47 | /** Convert little endian */ |
48 | static inline spx_int32_t le_int(spx_int32_t i) | 48 | static inline spx_int32_t le_int(spx_int32_t i) |
49 | { | 49 | { |
50 | #if 1 | 50 | #ifdef ROCKBOX |
51 | return letoh32(i); | 51 | return letoh32(i); |
52 | #elif !defined(__LITTLE_ENDIAN__) && ( defined(WORDS_BIGENDIAN) || defined(__BIG_ENDIAN__) ) | 52 | #elif !defined(__LITTLE_ENDIAN__) && ( defined(WORDS_BIGENDIAN) || defined(__BIG_ENDIAN__) ) |
53 | spx_uint32_t ui, ret; | 53 | spx_uint32_t ui, ret; |
diff --git a/tools/Makefile b/tools/Makefile index 4b72b4c638..50d05abda8 100644 --- a/tools/Makefile +++ b/tools/Makefile | |||
@@ -11,7 +11,7 @@ LDFLAGS := -g | |||
11 | 11 | ||
12 | CLEANALL := scramble descramble iriver sh2d bmp2rb rdf2binary convbdf \ | 12 | CLEANALL := scramble descramble iriver sh2d bmp2rb rdf2binary convbdf \ |
13 | generate_rocklatin mkboot ipod_fw codepages uclpack mi4 gigabeat database \ | 13 | generate_rocklatin mkboot ipod_fw codepages uclpack mi4 gigabeat database \ |
14 | lngdump telechips gigabeats mktccboot mknkboot | 14 | lngdump telechips gigabeats mktccboot mknkboot rbspeexenc |
15 | 15 | ||
16 | all: | 16 | all: |
17 | @echo "Run make in your build directory!" | 17 | @echo "Run make in your build directory!" |
@@ -76,6 +76,9 @@ player_unifont: player_unifont.c ../firmware/drivers/lcd-charset-player.c | |||
76 | uclpack: | 76 | uclpack: |
77 | $(SILENT)$(MAKE) -C ucl | 77 | $(SILENT)$(MAKE) -C ucl |
78 | 78 | ||
79 | rbspeexenc: | ||
80 | $(SILENT)$(MAKE) -C rbspeex | ||
81 | |||
79 | wavtrim: wavtrim.c | 82 | wavtrim: wavtrim.c |
80 | $(SILENT)$(CC) -g $+ -o $@ | 83 | $(SILENT)$(CC) -g $+ -o $@ |
81 | 84 | ||
@@ -86,4 +89,5 @@ clean: | |||
86 | @echo "Cleaning tools" | 89 | @echo "Cleaning tools" |
87 | $(SILENT)rm -f $(CLEANALL) $(shell for f in $(CLEANALL) ; do echo $$f.exe $$f.o $$f.obj ; done) *.ajf *~ | 90 | $(SILENT)rm -f $(CLEANALL) $(shell for f in $(CLEANALL) ; do echo $$f.exe $$f.o $$f.obj ; done) *.ajf *~ |
88 | $(SILENT)$(MAKE) -C ucl clean | 91 | $(SILENT)$(MAKE) -C ucl clean |
92 | $(SILENT)$(MAKE) -C rbspeex clean | ||
89 | 93 | ||
diff --git a/tools/rbspeex/Makefile b/tools/rbspeex/Makefile new file mode 100644 index 0000000000..4771fe4ea2 --- /dev/null +++ b/tools/rbspeex/Makefile | |||
@@ -0,0 +1,56 @@ | |||
1 | # __________ __ ___. | ||
2 | # Open \______ \ ____ ____ | | _\_ |__ _______ ___ | ||
3 | # Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / | ||
4 | # Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < | ||
5 | # Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ | ||
6 | # \/ \/ \/ \/ \/ | ||
7 | # $Id: Makefile,v 1.16 2006-09-02 22:34:13 bagder Exp $ | ||
8 | # | ||
9 | |||
10 | ifndef V | ||
11 | SILENT = @ | ||
12 | endif | ||
13 | |||
14 | SPEEXSRC = ../../apps/codecs/libspeex | ||
15 | |||
16 | INCLUDES = -I $(SPEEXSRC) -iquote $(SPEEXSRC) | ||
17 | SPEEXOPTS = -DHAVE_CONFIG_H -DROCKBOX_VOICE_ENCODER | ||
18 | |||
19 | CFLAGS = $(SPEEXOPTS) $(INCLUDES) -O3 -fomit-frame-pointer -Wno-unused-parameter | ||
20 | |||
21 | # This sets up 'SRC' based on the files mentioned in SOURCES | ||
22 | SRC := $(shell cat $(SPEEXSRC)/SOURCES | $(CC) $(CFLAGS) -E -P - | grep -v "^\#") | ||
23 | |||
24 | SOURCES = $(SRC:%.c=$(SPEEXSRC)/%.c) rbspeexenc.c | ||
25 | OBJS := $(SRC:%.c=%.o) rbspeexenc.o | ||
26 | DEPFILE = dep-speex | ||
27 | DIRS = | ||
28 | |||
29 | .PHONY : all | ||
30 | |||
31 | all: ../rbspeexenc | ||
32 | |||
33 | $(DEPFILE): $(SOURCES) | ||
34 | $(SILENT)rm -f $(DEPFILE) | ||
35 | $(SILENT)(for each in $(SOURCES) x; do \ | ||
36 | if test "x" != "$$each"; then \ | ||
37 | obj=`echo $$each | sed -e 's/\.[cS]/.o/' | sed -e 's/^.*\///' `; \ | ||
38 | $(CC) -MG -MM -MT "$$obj" $(CFLAGS) $$each 2>/dev/null; \ | ||
39 | fi; \ | ||
40 | if test -n "$$del"; then \ | ||
41 | rm $$del; \ | ||
42 | del=""; \ | ||
43 | fi \ | ||
44 | done > $(DEPFILE); \ | ||
45 | echo "oo" > /dev/null ) | ||
46 | |||
47 | ../rbspeexenc: $(OBJS) $(DEPFILE) | ||
48 | gcc -o ../rbspeexenc $(OBJS) -lm | ||
49 | |||
50 | %.o: | ||
51 | $(CC) $(CFLAGS) -c $< -o $@ | ||
52 | |||
53 | clean: | ||
54 | rm -f $(OBJS) dep-speex | ||
55 | |||
56 | -include $(DEPFILE) | ||
diff --git a/tools/rbspeex/rbspeexenc.c b/tools/rbspeex/rbspeexenc.c new file mode 100644 index 0000000000..5d301998da --- /dev/null +++ b/tools/rbspeex/rbspeexenc.c | |||
@@ -0,0 +1,239 @@ | |||
1 | /************************************************************************** | ||
2 | * __________ __ ___. | ||
3 | * Open \______ \ ____ ____ | | _\_ |__ _______ ___ | ||
4 | * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / | ||
5 | * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < | ||
6 | * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ | ||
7 | * \/ \/ \/ \/ \/ | ||
8 | * | ||
9 | * Copyright (C) 2007 Thom Johansen | ||
10 | * | ||
11 | * All files in this archive are subject to the GNU General Public License. | ||
12 | * See the file COPYING in the source tree root for full license agreement. | ||
13 | * | ||
14 | * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY | ||
15 | * KIND, either express or implied. | ||
16 | * | ||
17 | ***************************************************************************/ | ||
18 | |||
19 | #include <speex/speex.h> | ||
20 | #include <speex/speex_resampler.h> | ||
21 | #include <stdio.h> | ||
22 | #include <stdlib.h> | ||
23 | #include <string.h> | ||
24 | #include <stdbool.h> | ||
25 | |||
26 | /* Read an unaligned 32-bit little endian long from buffer. */ | ||
27 | unsigned int get_long_le(unsigned char *p) | ||
28 | { | ||
29 | return p[0] | (p[1] << 8) | (p[2] << 16) | (p[3] << 24); | ||
30 | } | ||
31 | |||
32 | bool get_wave_metadata(FILE *fd, int *numchan, int *bps, int *sr, int *numsamples) | ||
33 | { | ||
34 | unsigned char buf[1024]; | ||
35 | unsigned long totalsamples = 0; | ||
36 | unsigned long channels = 0; | ||
37 | unsigned long bitspersample = 0; | ||
38 | unsigned long numbytes = 0; | ||
39 | size_t read_bytes; | ||
40 | int i; | ||
41 | |||
42 | if ((read_bytes = fread(buf, 1, 12, fd)) < 12) | ||
43 | return false; | ||
44 | |||
45 | if ((memcmp(buf, "RIFF",4) != 0) || (memcmp(&buf[8], "WAVE", 4) != 0)) | ||
46 | return false; | ||
47 | |||
48 | /* iterate over WAVE chunks until 'data' chunk */ | ||
49 | while (1) { | ||
50 | /* get chunk header */ | ||
51 | if ((read_bytes = fread(buf, 1, 8, fd)) < 8) | ||
52 | return false; | ||
53 | |||
54 | /* chunkSize */ | ||
55 | i = get_long_le(&buf[4]); | ||
56 | |||
57 | if (memcmp(buf, "fmt ", 4) == 0) { | ||
58 | /* get rest of chunk */ | ||
59 | if ((read_bytes = fread(buf, 1, 16, fd)) < 16) | ||
60 | return false; | ||
61 | |||
62 | i -= 16; | ||
63 | |||
64 | channels = *numchan = buf[2] | (buf[3] << 8); | ||
65 | *sr = get_long_le(&buf[4]); | ||
66 | /* wBitsPerSample */ | ||
67 | bitspersample = *bps = buf[14] | (buf[15] << 8); | ||
68 | } else if (memcmp(buf, "data", 4) == 0) { | ||
69 | numbytes = i; | ||
70 | break; | ||
71 | } else if (memcmp(buf, "fact", 4) == 0) { | ||
72 | /* dwSampleLength */ | ||
73 | if (i >= 4) { | ||
74 | /* get rest of chunk */ | ||
75 | if ((read_bytes = read(buf, 1, 4, fd)) < 4) | ||
76 | return false; | ||
77 | |||
78 | i -= 4; | ||
79 | totalsamples = get_long_le(buf); | ||
80 | } | ||
81 | } | ||
82 | |||
83 | /* seek to next chunk (even chunk sizes must be padded) */ | ||
84 | if (i & 0x01) | ||
85 | i++; | ||
86 | |||
87 | if (fseek(fd, i, SEEK_CUR) < 0) | ||
88 | return false; | ||
89 | } | ||
90 | |||
91 | if ((numbytes == 0) || (channels == 0)) | ||
92 | return false; | ||
93 | |||
94 | if (totalsamples == 0) { | ||
95 | /* for PCM only */ | ||
96 | totalsamples = numbytes/((((bitspersample - 1) / 8) + 1)*channels); | ||
97 | } | ||
98 | *numsamples = totalsamples; | ||
99 | return true; | ||
100 | } | ||
101 | |||
102 | int main(int argc, char **argv) | ||
103 | { | ||
104 | FILE *fin, *fout; | ||
105 | spx_int16_t *in, *inpos; | ||
106 | spx_int16_t enc_buf[640]; /* Max frame size */ | ||
107 | char cbits[200]; | ||
108 | int nbytes; | ||
109 | void *st; | ||
110 | SpeexResamplerState *resampler = NULL; | ||
111 | SpeexBits bits; | ||
112 | int i, tmp; | ||
113 | float ftmp; | ||
114 | int numchan, bps, sr, numsamples; | ||
115 | int frame_size; | ||
116 | |||
117 | if (argc < 3) { | ||
118 | printf("Usage: rbspeexenc [options] infile outfile\n" | ||
119 | "Options:\n" | ||
120 | " -q x Quality, floating point number in the range [0-10]\n" | ||
121 | " -c x Complexity, affects quality and encoding time, where\n" | ||
122 | " both increase with increasing values, range [0-10]\n" | ||
123 | " Defaults are as in speexenc.\n" | ||
124 | "\nWARNING: This tool will create files that are only usable by Rockbox!\n" | ||
125 | ); | ||
126 | return 1; | ||
127 | } | ||
128 | |||
129 | /* We'll eat an entire WAV file here, and encode it with Speex, packing the | ||
130 | * bits as tightly as we can. Output is completely raw, with absolutely | ||
131 | * nothing to identify the contents. | ||
132 | */ | ||
133 | |||
134 | /* Wideband encoding */ | ||
135 | st = speex_encoder_init(&speex_wb_mode); | ||
136 | |||
137 | /* VBR */ | ||
138 | tmp = 1; | ||
139 | speex_encoder_ctl(st, SPEEX_SET_VBR, &tmp); | ||
140 | /* Quality, 0-10 */ | ||
141 | ftmp = 8.f; | ||
142 | for (i = 1; i < argc - 2; ++i) { | ||
143 | if (strncmp(argv[i], "-q", 2) == 0) { | ||
144 | ftmp = atof(argv[i + 1]); | ||
145 | break; | ||
146 | } | ||
147 | } | ||
148 | speex_encoder_ctl(st, SPEEX_SET_VBR_QUALITY, &ftmp); | ||
149 | /* Complexity, 0-10 */ | ||
150 | tmp = 3; | ||
151 | for (i = 1; i < argc - 2; ++i) { | ||
152 | if (strncmp(argv[i], "-c", 2) == 0) { | ||
153 | tmp = atoi(argv[i + 1]); | ||
154 | break; | ||
155 | } | ||
156 | } | ||
157 | speex_encoder_ctl(st, SPEEX_SET_COMPLEXITY, &tmp); | ||
158 | speex_encoder_ctl(st, SPEEX_GET_FRAME_SIZE, &frame_size); | ||
159 | |||
160 | fin = fopen(argv[argc - 2], "rb"); | ||
161 | if (!get_wave_metadata(fin, &numchan, &bps, &sr, &numsamples)) { | ||
162 | printf("invalid wave file!\n"); | ||
163 | return 1; | ||
164 | } | ||
165 | if (sr != 16000) { | ||
166 | resampler = speex_resampler_init(1, sr, 16000, 10, NULL); | ||
167 | speex_resampler_skip_zeros(resampler); | ||
168 | printf("Resampling from %i Hz to 16000 Hz\n", sr); | ||
169 | } | ||
170 | if (numchan != 1) { | ||
171 | printf("Error: input file must be mono\n"); | ||
172 | return 1; | ||
173 | } | ||
174 | if (bps != 16) { | ||
175 | printf("samples must be 16 bit!\n"); | ||
176 | return 1; | ||
177 | } | ||
178 | |||
179 | /* Read input samples into a buffer */ | ||
180 | in = malloc(numsamples*2); | ||
181 | if (malloc == NULL) { | ||
182 | printf("error on malloc\n"); | ||
183 | return 1; | ||
184 | } | ||
185 | fread(in, 2, numsamples, fin); | ||
186 | fclose(fin); | ||
187 | |||
188 | speex_bits_init(&bits); | ||
189 | inpos = in; | ||
190 | fout = fopen(argv[argc - 1], "wb"); | ||
191 | |||
192 | while (numsamples > 0) { | ||
193 | int samples = frame_size; | ||
194 | |||
195 | /* Check if we need to resample */ | ||
196 | if (sr != 16000) { | ||
197 | spx_uint32_t in_len = numsamples, out_len = frame_size; | ||
198 | |||
199 | /* Limit this or resampler will try to allocate it all on stack */ | ||
200 | if (in_len > 2000) | ||
201 | in_len = 2000; | ||
202 | speex_resampler_process_int(resampler, 0, inpos, &in_len, | ||
203 | enc_buf, &out_len); | ||
204 | inpos += in_len; | ||
205 | samples = out_len; | ||
206 | numsamples -= in_len; | ||
207 | } else { | ||
208 | if (samples > numsamples) | ||
209 | samples = numsamples; | ||
210 | memcpy(enc_buf, inpos, samples*2); | ||
211 | inpos += frame_size; | ||
212 | numsamples -= frame_size; | ||
213 | } | ||
214 | /* Pad out with zeros if we didn't fill all input */ | ||
215 | memset(enc_buf + samples, 0, (frame_size - samples)*2); | ||
216 | |||
217 | speex_encode_int(st, enc_buf, &bits); | ||
218 | |||
219 | /* Copy the bits to an array of char that can be written */ | ||
220 | nbytes = speex_bits_write_whole_bytes(&bits, cbits, 200); | ||
221 | |||
222 | /* Write the compressed data */ | ||
223 | fwrite(cbits, 1, nbytes, fout); | ||
224 | } | ||
225 | |||
226 | /* Squeeze out the last bits */ | ||
227 | nbytes = speex_bits_write(&bits, cbits, 200); | ||
228 | fwrite(cbits, 1, nbytes, fout); | ||
229 | |||
230 | /*Destroy the encoder state*/ | ||
231 | speex_encoder_destroy(st); | ||
232 | /*Destroy the bit-packing struct*/ | ||
233 | speex_bits_destroy(&bits); | ||
234 | if (resampler != NULL) | ||
235 | speex_resampler_destroy(resampler); | ||
236 | fclose(fout); | ||
237 | free(in); | ||
238 | return 0; | ||
239 | } | ||