annotate wmadec.c @ 4301:b43bd0c56eaa libavcodec

Bug fix for crashes when SSE is used on unaligned arrays. No measureable change in speed. This gave random crashes on Win32 and BeOS. The cause for this bug is that gcc doesn't align the stackframe. Linux and glibc always ensure this to be true thus this never affected Linux.
author banan
date Thu, 14 Dec 2006 17:50:23 +0000
parents c8c591fe26f8
children 0efc832d9102
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1 /*
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
2 * WMA compatible decoder
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
3 * Copyright (c) 2002 The FFmpeg Project.
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
4 *
3947
c8c591fe26f8 Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents: 3776
diff changeset
5 * This file is part of FFmpeg.
c8c591fe26f8 Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents: 3776
diff changeset
6 *
c8c591fe26f8 Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents: 3776
diff changeset
7 * FFmpeg is free software; you can redistribute it and/or
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
8 * modify it under the terms of the GNU Lesser General Public
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
9 * License as published by the Free Software Foundation; either
3947
c8c591fe26f8 Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents: 3776
diff changeset
10 * version 2.1 of the License, or (at your option) any later version.
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
11 *
3947
c8c591fe26f8 Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents: 3776
diff changeset
12 * FFmpeg is distributed in the hope that it will be useful,
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
15 * Lesser General Public License for more details.
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
16 *
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
17 * You should have received a copy of the GNU Lesser General Public
3947
c8c591fe26f8 Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents: 3776
diff changeset
18 * License along with FFmpeg; if not, write to the Free Software
3036
0b546eab515d Update licensing information: The FSF changed postal address.
diego
parents: 3022
diff changeset
19 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
20 */
1106
1e39f273ecd6 per file doxy
michaelni
parents: 1064
diff changeset
21
1e39f273ecd6 per file doxy
michaelni
parents: 1064
diff changeset
22 /**
1e39f273ecd6 per file doxy
michaelni
parents: 1064
diff changeset
23 * @file wmadec.c
1e39f273ecd6 per file doxy
michaelni
parents: 1064
diff changeset
24 * WMA compatible decoder.
1967
2b0fc6b25ab8 add the minimal documentation to make this decoder useful
melanson
parents: 1750
diff changeset
25 * This decoder handles Microsoft Windows Media Audio data, versions 1 & 2.
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
26 * WMA v1 is identified by audio format 0x160 in Microsoft media files
1967
2b0fc6b25ab8 add the minimal documentation to make this decoder useful
melanson
parents: 1750
diff changeset
27 * (ASF/AVI/WAV). WMA v2 is identified by audio format 0x161.
2b0fc6b25ab8 add the minimal documentation to make this decoder useful
melanson
parents: 1750
diff changeset
28 *
2b0fc6b25ab8 add the minimal documentation to make this decoder useful
melanson
parents: 1750
diff changeset
29 * To use this decoder, a calling application must supply the extra data
2b0fc6b25ab8 add the minimal documentation to make this decoder useful
melanson
parents: 1750
diff changeset
30 * bytes provided with the WMA data. These are the extra, codec-specific
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
31 * bytes at the end of a WAVEFORMATEX data structure. Transmit these bytes
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
32 * to the decoder using the extradata[_size] fields in AVCodecContext. There
1967
2b0fc6b25ab8 add the minimal documentation to make this decoder useful
melanson
parents: 1750
diff changeset
33 * should be 4 extra bytes for v1 data and 6 extra bytes for v2 data.
1106
1e39f273ecd6 per file doxy
michaelni
parents: 1064
diff changeset
34 */
1e39f273ecd6 per file doxy
michaelni
parents: 1064
diff changeset
35
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
36 #include "avcodec.h"
2398
582e635cfa08 common.c -> bitstream.c (and the single non bitstream func -> utils.c)
michael
parents: 2370
diff changeset
37 #include "bitstream.h"
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
38 #include "dsputil.h"
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
39
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
40 /* size of blocks */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
41 #define BLOCK_MIN_BITS 7
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
42 #define BLOCK_MAX_BITS 11
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
43 #define BLOCK_MAX_SIZE (1 << BLOCK_MAX_BITS)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
44
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
45 #define BLOCK_NB_SIZES (BLOCK_MAX_BITS - BLOCK_MIN_BITS + 1)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
46
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
47 /* XXX: find exact max size */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
48 #define HIGH_BAND_MAX_SIZE 16
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
49
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
50 #define NB_LSP_COEFS 10
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
51
817
97b71a72f087 reverse first hunk
nickols_k
parents: 816
diff changeset
52 /* XXX: is it a suitable value ? */
2775
f3cdd51c9e16 WMA MAX_CODED_SUPERFRAME_SIZE too small patch by (Mark Weaver: mark-clist, npsl co uk)
michael
parents: 2398
diff changeset
53 #define MAX_CODED_SUPERFRAME_SIZE 16384
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
54
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
55 #define MAX_CHANNELS 2
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
56
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
57 #define NOISE_TAB_SIZE 8192
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
58
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
59 #define LSP_POW_BITS 7
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
60
3022
d4080a510724 get_vlc -> get_vlc2 transition.
banan
parents: 2992
diff changeset
61 #define VLCBITS 9
3113
ab01ee59324f - fix insufficient code length for exp_vlc
henry
parents: 3089
diff changeset
62 #define VLCMAX ((22+VLCBITS-1)/VLCBITS)
ab01ee59324f - fix insufficient code length for exp_vlc
henry
parents: 3089
diff changeset
63
ab01ee59324f - fix insufficient code length for exp_vlc
henry
parents: 3089
diff changeset
64 #define EXPVLCBITS 8
ab01ee59324f - fix insufficient code length for exp_vlc
henry
parents: 3089
diff changeset
65 #define EXPMAX ((19+EXPVLCBITS-1)/EXPVLCBITS)
ab01ee59324f - fix insufficient code length for exp_vlc
henry
parents: 3089
diff changeset
66
ab01ee59324f - fix insufficient code length for exp_vlc
henry
parents: 3089
diff changeset
67 #define HGAINVLCBITS 9
ab01ee59324f - fix insufficient code length for exp_vlc
henry
parents: 3089
diff changeset
68 #define HGAINMAX ((13+HGAINVLCBITS-1)/HGAINVLCBITS)
3022
d4080a510724 get_vlc -> get_vlc2 transition.
banan
parents: 2992
diff changeset
69
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
70 typedef struct WMADecodeContext {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
71 GetBitContext gb;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
72 int sample_rate;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
73 int nb_channels;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
74 int bit_rate;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
75 int version; /* 1 = 0x160 (WMAV1), 2 = 0x161 (WMAV2) */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
76 int block_align;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
77 int use_bit_reservoir;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
78 int use_variable_block_len;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
79 int use_exp_vlc; /* exponent coding: 0 = lsp, 1 = vlc + delta */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
80 int use_noise_coding; /* true if perceptual noise is added */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
81 int byte_offset_bits;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
82 VLC exp_vlc;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
83 int exponent_sizes[BLOCK_NB_SIZES];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
84 uint16_t exponent_bands[BLOCK_NB_SIZES][25];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
85 int high_band_start[BLOCK_NB_SIZES]; /* index of first coef in high band */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
86 int coefs_start; /* first coded coef */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
87 int coefs_end[BLOCK_NB_SIZES]; /* max number of coded coefficients */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
88 int exponent_high_sizes[BLOCK_NB_SIZES];
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
89 int exponent_high_bands[BLOCK_NB_SIZES][HIGH_BAND_MAX_SIZE];
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
90 VLC hgain_vlc;
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
91
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
92 /* coded values in high bands */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
93 int high_band_coded[MAX_CHANNELS][HIGH_BAND_MAX_SIZE];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
94 int high_band_values[MAX_CHANNELS][HIGH_BAND_MAX_SIZE];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
95
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
96 /* there are two possible tables for spectral coefficients */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
97 VLC coef_vlc[2];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
98 uint16_t *run_table[2];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
99 uint16_t *level_table[2];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
100 /* frame info */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
101 int frame_len; /* frame length in samples */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
102 int frame_len_bits; /* frame_len = 1 << frame_len_bits */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
103 int nb_block_sizes; /* number of block sizes */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
104 /* block info */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
105 int reset_block_lengths;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
106 int block_len_bits; /* log2 of current block length */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
107 int next_block_len_bits; /* log2 of next block length */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
108 int prev_block_len_bits; /* log2 of prev block length */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
109 int block_len; /* block length in samples */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
110 int block_num; /* block number in current frame */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
111 int block_pos; /* current position in frame */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
112 uint8_t ms_stereo; /* true if mid/side stereo mode */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
113 uint8_t channel_coded[MAX_CHANNELS]; /* true if channel is coded */
3089
072dbc669253 MSVC-compatible __align8/__align16 declaration
diego
parents: 3036
diff changeset
114 DECLARE_ALIGNED_16(float, exponents[MAX_CHANNELS][BLOCK_MAX_SIZE]);
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
115 float max_exponent[MAX_CHANNELS];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
116 int16_t coefs1[MAX_CHANNELS][BLOCK_MAX_SIZE];
3089
072dbc669253 MSVC-compatible __align8/__align16 declaration
diego
parents: 3036
diff changeset
117 DECLARE_ALIGNED_16(float, coefs[MAX_CHANNELS][BLOCK_MAX_SIZE]);
4301
b43bd0c56eaa Bug fix for crashes when SSE is used on unaligned arrays.
banan
parents: 3947
diff changeset
118 DECLARE_ALIGNED_16(FFTSample, output[BLOCK_MAX_SIZE * 2]);
b43bd0c56eaa Bug fix for crashes when SSE is used on unaligned arrays.
banan
parents: 3947
diff changeset
119 DECLARE_ALIGNED_16(float, window[BLOCK_MAX_SIZE * 2]);
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
120 MDCTContext mdct_ctx[BLOCK_NB_SIZES];
1031
19de1445beb2 use av_malloc() functions - added av_strdup and av_realloc()
bellard
parents: 1025
diff changeset
121 float *windows[BLOCK_NB_SIZES];
3089
072dbc669253 MSVC-compatible __align8/__align16 declaration
diego
parents: 3036
diff changeset
122 DECLARE_ALIGNED_16(FFTSample, mdct_tmp[BLOCK_MAX_SIZE]); /* temporary storage for imdct */
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
123 /* output buffer for one frame and the last for IMDCT windowing */
3089
072dbc669253 MSVC-compatible __align8/__align16 declaration
diego
parents: 3036
diff changeset
124 DECLARE_ALIGNED_16(float, frame_out[MAX_CHANNELS][BLOCK_MAX_SIZE * 2]);
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
125 /* last frame info */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
126 uint8_t last_superframe[MAX_CODED_SUPERFRAME_SIZE + 4]; /* padding added */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
127 int last_bitoffset;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
128 int last_superframe_len;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
129 float noise_table[NOISE_TAB_SIZE];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
130 int noise_index;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
131 float noise_mult; /* XXX: suppress that and integrate it in the noise array */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
132 /* lsp_to_curve tables */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
133 float lsp_cos_table[BLOCK_MAX_SIZE];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
134 float lsp_pow_e_table[256];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
135 float lsp_pow_m_table1[(1 << LSP_POW_BITS)];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
136 float lsp_pow_m_table2[(1 << LSP_POW_BITS)];
3592
6a358dccf2ab SIMD vector optimizations. 3% faster overall decoding.
banan
parents: 3555
diff changeset
137 DSPContext dsp;
1343
1fd083c620d6 moved frame_count to wmadeccontext
al3x
parents: 1342
diff changeset
138
1fd083c620d6 moved frame_count to wmadeccontext
al3x
parents: 1342
diff changeset
139 #ifdef TRACE
1fd083c620d6 moved frame_count to wmadeccontext
al3x
parents: 1342
diff changeset
140 int frame_count;
1fd083c620d6 moved frame_count to wmadeccontext
al3x
parents: 1342
diff changeset
141 #endif
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
142 } WMADecodeContext;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
143
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
144 typedef struct CoefVLCTable {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
145 int n; /* total number of codes */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
146 const uint32_t *huffcodes; /* VLC bit values */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
147 const uint8_t *huffbits; /* VLC bit size */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
148 const uint16_t *levels; /* table to build run/level tables */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
149 } CoefVLCTable;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
150
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
151 static void wma_lsp_to_curve_init(WMADecodeContext *s, int frame_len);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
152
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
153 #include "wmadata.h"
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
154
1342
f574934c4219 uniformization (now it uses the same trace functions as h264, defined in common.h)
al3x
parents: 1303
diff changeset
155 #ifdef TRACE
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
156 static void dump_shorts(const char *name, const short *tab, int n)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
157 {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
158 int i;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
159
1342
f574934c4219 uniformization (now it uses the same trace functions as h264, defined in common.h)
al3x
parents: 1303
diff changeset
160 tprintf("%s[%d]:\n", name, n);
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
161 for(i=0;i<n;i++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
162 if ((i & 7) == 0)
1342
f574934c4219 uniformization (now it uses the same trace functions as h264, defined in common.h)
al3x
parents: 1303
diff changeset
163 tprintf("%4d: ", i);
f574934c4219 uniformization (now it uses the same trace functions as h264, defined in common.h)
al3x
parents: 1303
diff changeset
164 tprintf(" %5d.0", tab[i]);
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
165 if ((i & 7) == 7)
1342
f574934c4219 uniformization (now it uses the same trace functions as h264, defined in common.h)
al3x
parents: 1303
diff changeset
166 tprintf("\n");
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
167 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
168 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
169
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
170 static void dump_floats(const char *name, int prec, const float *tab, int n)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
171 {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
172 int i;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
173
1342
f574934c4219 uniformization (now it uses the same trace functions as h264, defined in common.h)
al3x
parents: 1303
diff changeset
174 tprintf("%s[%d]:\n", name, n);
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
175 for(i=0;i<n;i++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
176 if ((i & 7) == 0)
1342
f574934c4219 uniformization (now it uses the same trace functions as h264, defined in common.h)
al3x
parents: 1303
diff changeset
177 tprintf("%4d: ", i);
f574934c4219 uniformization (now it uses the same trace functions as h264, defined in common.h)
al3x
parents: 1303
diff changeset
178 tprintf(" %8.*f", prec, tab[i]);
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
179 if ((i & 7) == 7)
1342
f574934c4219 uniformization (now it uses the same trace functions as h264, defined in common.h)
al3x
parents: 1303
diff changeset
180 tprintf("\n");
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
181 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
182 if ((i & 7) != 0)
1342
f574934c4219 uniformization (now it uses the same trace functions as h264, defined in common.h)
al3x
parents: 1303
diff changeset
183 tprintf("\n");
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
184 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
185 #endif
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
186
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
187 /* XXX: use same run/length optimization as mpeg decoders */
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
188 static void init_coef_vlc(VLC *vlc,
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
189 uint16_t **prun_table, uint16_t **plevel_table,
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
190 const CoefVLCTable *vlc_table)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
191 {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
192 int n = vlc_table->n;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
193 const uint8_t *table_bits = vlc_table->huffbits;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
194 const uint32_t *table_codes = vlc_table->huffcodes;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
195 const uint16_t *levels_table = vlc_table->levels;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
196 uint16_t *run_table, *level_table;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
197 const uint16_t *p;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
198 int i, l, j, level;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
199
3113
ab01ee59324f - fix insufficient code length for exp_vlc
henry
parents: 3089
diff changeset
200 init_vlc(vlc, VLCBITS, n, table_bits, 1, 1, table_codes, 4, 4, 0);
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
201
1031
19de1445beb2 use av_malloc() functions - added av_strdup and av_realloc()
bellard
parents: 1025
diff changeset
202 run_table = av_malloc(n * sizeof(uint16_t));
19de1445beb2 use av_malloc() functions - added av_strdup and av_realloc()
bellard
parents: 1025
diff changeset
203 level_table = av_malloc(n * sizeof(uint16_t));
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
204 p = levels_table;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
205 i = 2;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
206 level = 1;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
207 while (i < n) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
208 l = *p++;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
209 for(j=0;j<l;j++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
210 run_table[i] = j;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
211 level_table[i] = level;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
212 i++;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
213 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
214 level++;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
215 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
216 *prun_table = run_table;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
217 *plevel_table = level_table;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
218 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
219
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
220 static int wma_decode_init(AVCodecContext * avctx)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
221 {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
222 WMADecodeContext *s = avctx->priv_data;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
223 int i, flags1, flags2;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
224 float *window;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
225 uint8_t *extradata;
3235
d3c05c7dabcd reverting 1.31->1.33
michael
parents: 3195
diff changeset
226 float bps1, high_freq;
d3c05c7dabcd reverting 1.31->1.33
michael
parents: 3195
diff changeset
227 volatile float bps;
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
228 int sample_rate1;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
229 int coef_vlc_table;
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
230
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
231 s->sample_rate = avctx->sample_rate;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
232 s->nb_channels = avctx->channels;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
233 s->bit_rate = avctx->bit_rate;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
234 s->block_align = avctx->block_align;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
235
3592
6a358dccf2ab SIMD vector optimizations. 3% faster overall decoding.
banan
parents: 3555
diff changeset
236 dsputil_init(&s->dsp, avctx);
6a358dccf2ab SIMD vector optimizations. 3% faster overall decoding.
banan
parents: 3555
diff changeset
237
808
e9bfaabcf07d fixed nb_block_sizes detection - fixed codec_id test (avctx->codec_id does not need to be initialized)
bellard
parents: 797
diff changeset
238 if (avctx->codec->id == CODEC_ID_WMAV1) {
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
239 s->version = 1;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
240 } else {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
241 s->version = 2;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
242 }
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
243
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
244 /* extract flag infos */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
245 flags1 = 0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
246 flags2 = 0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
247 extradata = avctx->extradata;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
248 if (s->version == 1 && avctx->extradata_size >= 4) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
249 flags1 = extradata[0] | (extradata[1] << 8);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
250 flags2 = extradata[2] | (extradata[3] << 8);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
251 } else if (s->version == 2 && avctx->extradata_size >= 6) {
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
252 flags1 = extradata[0] | (extradata[1] << 8) |
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
253 (extradata[2] << 16) | (extradata[3] << 24);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
254 flags2 = extradata[4] | (extradata[5] << 8);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
255 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
256 s->use_exp_vlc = flags2 & 0x0001;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
257 s->use_bit_reservoir = flags2 & 0x0002;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
258 s->use_variable_block_len = flags2 & 0x0004;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
259
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
260 /* compute MDCT block size */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
261 if (s->sample_rate <= 16000) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
262 s->frame_len_bits = 9;
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
263 } else if (s->sample_rate <= 22050 ||
795
55add0e7eafb avoid name clash - fixed again block size selection
bellard
parents: 785
diff changeset
264 (s->sample_rate <= 32000 && s->version == 1)) {
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
265 s->frame_len_bits = 10;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
266 } else {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
267 s->frame_len_bits = 11;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
268 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
269 s->frame_len = 1 << s->frame_len_bits;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
270 if (s->use_variable_block_len) {
808
e9bfaabcf07d fixed nb_block_sizes detection - fixed codec_id test (avctx->codec_id does not need to be initialized)
bellard
parents: 797
diff changeset
271 int nb_max, nb;
e9bfaabcf07d fixed nb_block_sizes detection - fixed codec_id test (avctx->codec_id does not need to be initialized)
bellard
parents: 797
diff changeset
272 nb = ((flags2 >> 3) & 3) + 1;
e9bfaabcf07d fixed nb_block_sizes detection - fixed codec_id test (avctx->codec_id does not need to be initialized)
bellard
parents: 797
diff changeset
273 if ((s->bit_rate / s->nb_channels) >= 32000)
e9bfaabcf07d fixed nb_block_sizes detection - fixed codec_id test (avctx->codec_id does not need to be initialized)
bellard
parents: 797
diff changeset
274 nb += 2;
e9bfaabcf07d fixed nb_block_sizes detection - fixed codec_id test (avctx->codec_id does not need to be initialized)
bellard
parents: 797
diff changeset
275 nb_max = s->frame_len_bits - BLOCK_MIN_BITS;
e9bfaabcf07d fixed nb_block_sizes detection - fixed codec_id test (avctx->codec_id does not need to be initialized)
bellard
parents: 797
diff changeset
276 if (nb > nb_max)
e9bfaabcf07d fixed nb_block_sizes detection - fixed codec_id test (avctx->codec_id does not need to be initialized)
bellard
parents: 797
diff changeset
277 nb = nb_max;
e9bfaabcf07d fixed nb_block_sizes detection - fixed codec_id test (avctx->codec_id does not need to be initialized)
bellard
parents: 797
diff changeset
278 s->nb_block_sizes = nb + 1;
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
279 } else {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
280 s->nb_block_sizes = 1;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
281 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
282
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
283 /* init rate dependant parameters */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
284 s->use_noise_coding = 1;
3235
d3c05c7dabcd reverting 1.31->1.33
michael
parents: 3195
diff changeset
285 high_freq = s->sample_rate * 0.5;
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
286
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
287 /* if version 2, then the rates are normalized */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
288 sample_rate1 = s->sample_rate;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
289 if (s->version == 2) {
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
290 if (sample_rate1 >= 44100)
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
291 sample_rate1 = 44100;
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
292 else if (sample_rate1 >= 22050)
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
293 sample_rate1 = 22050;
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
294 else if (sample_rate1 >= 16000)
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
295 sample_rate1 = 16000;
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
296 else if (sample_rate1 >= 11025)
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
297 sample_rate1 = 11025;
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
298 else if (sample_rate1 >= 8000)
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
299 sample_rate1 = 8000;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
300 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
301
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
302 bps = (float)s->bit_rate / (float)(s->nb_channels * s->sample_rate);
2992
f74ae8aff2a9 Fix wma2 audio decoder
rtognimp
parents: 2967
diff changeset
303 s->byte_offset_bits = av_log2((int)(bps * s->frame_len / 8.0 + 0.5)) + 2;
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
304
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
305 /* compute high frequency value and choose if noise coding should
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
306 be activated */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
307 bps1 = bps;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
308 if (s->nb_channels == 2)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
309 bps1 = bps * 1.6;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
310 if (sample_rate1 == 44100) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
311 if (bps1 >= 0.61)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
312 s->use_noise_coding = 0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
313 else
3235
d3c05c7dabcd reverting 1.31->1.33
michael
parents: 3195
diff changeset
314 high_freq = high_freq * 0.4;
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
315 } else if (sample_rate1 == 22050) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
316 if (bps1 >= 1.16)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
317 s->use_noise_coding = 0;
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
318 else if (bps1 >= 0.72)
3235
d3c05c7dabcd reverting 1.31->1.33
michael
parents: 3195
diff changeset
319 high_freq = high_freq * 0.7;
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
320 else
3235
d3c05c7dabcd reverting 1.31->1.33
michael
parents: 3195
diff changeset
321 high_freq = high_freq * 0.6;
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
322 } else if (sample_rate1 == 16000) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
323 if (bps > 0.5)
3235
d3c05c7dabcd reverting 1.31->1.33
michael
parents: 3195
diff changeset
324 high_freq = high_freq * 0.5;
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
325 else
3235
d3c05c7dabcd reverting 1.31->1.33
michael
parents: 3195
diff changeset
326 high_freq = high_freq * 0.3;
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
327 } else if (sample_rate1 == 11025) {
3235
d3c05c7dabcd reverting 1.31->1.33
michael
parents: 3195
diff changeset
328 high_freq = high_freq * 0.7;
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
329 } else if (sample_rate1 == 8000) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
330 if (bps <= 0.625) {
3235
d3c05c7dabcd reverting 1.31->1.33
michael
parents: 3195
diff changeset
331 high_freq = high_freq * 0.5;
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
332 } else if (bps > 0.75) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
333 s->use_noise_coding = 0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
334 } else {
3235
d3c05c7dabcd reverting 1.31->1.33
michael
parents: 3195
diff changeset
335 high_freq = high_freq * 0.65;
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
336 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
337 } else {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
338 if (bps >= 0.8) {
3235
d3c05c7dabcd reverting 1.31->1.33
michael
parents: 3195
diff changeset
339 high_freq = high_freq * 0.75;
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
340 } else if (bps >= 0.6) {
3235
d3c05c7dabcd reverting 1.31->1.33
michael
parents: 3195
diff changeset
341 high_freq = high_freq * 0.6;
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
342 } else {
3235
d3c05c7dabcd reverting 1.31->1.33
michael
parents: 3195
diff changeset
343 high_freq = high_freq * 0.5;
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
344 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
345 }
1342
f574934c4219 uniformization (now it uses the same trace functions as h264, defined in common.h)
al3x
parents: 1303
diff changeset
346 dprintf("flags1=0x%x flags2=0x%x\n", flags1, flags2);
f574934c4219 uniformization (now it uses the same trace functions as h264, defined in common.h)
al3x
parents: 1303
diff changeset
347 dprintf("version=%d channels=%d sample_rate=%d bitrate=%d block_align=%d\n",
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
348 s->version, s->nb_channels, s->sample_rate, s->bit_rate,
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
349 s->block_align);
3235
d3c05c7dabcd reverting 1.31->1.33
michael
parents: 3195
diff changeset
350 dprintf("bps=%f bps1=%f high_freq=%f bitoffset=%d\n",
d3c05c7dabcd reverting 1.31->1.33
michael
parents: 3195
diff changeset
351 bps, bps1, high_freq, s->byte_offset_bits);
1342
f574934c4219 uniformization (now it uses the same trace functions as h264, defined in common.h)
al3x
parents: 1303
diff changeset
352 dprintf("use_noise_coding=%d use_exp_vlc=%d nb_block_sizes=%d\n",
808
e9bfaabcf07d fixed nb_block_sizes detection - fixed codec_id test (avctx->codec_id does not need to be initialized)
bellard
parents: 797
diff changeset
353 s->use_noise_coding, s->use_exp_vlc, s->nb_block_sizes);
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
354
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
355 /* compute the scale factor band sizes for each MDCT block size */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
356 {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
357 int a, b, pos, lpos, k, block_len, i, j, n;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
358 const uint8_t *table;
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
359
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
360 if (s->version == 1) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
361 s->coefs_start = 3;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
362 } else {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
363 s->coefs_start = 0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
364 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
365 for(k = 0; k < s->nb_block_sizes; k++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
366 block_len = s->frame_len >> k;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
367
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
368 if (s->version == 1) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
369 lpos = 0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
370 for(i=0;i<25;i++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
371 a = wma_critical_freqs[i];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
372 b = s->sample_rate;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
373 pos = ((block_len * 2 * a) + (b >> 1)) / b;
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
374 if (pos > block_len)
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
375 pos = block_len;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
376 s->exponent_bands[0][i] = pos - lpos;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
377 if (pos >= block_len) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
378 i++;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
379 break;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
380 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
381 lpos = pos;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
382 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
383 s->exponent_sizes[0] = i;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
384 } else {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
385 /* hardcoded tables */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
386 table = NULL;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
387 a = s->frame_len_bits - BLOCK_MIN_BITS - k;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
388 if (a < 3) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
389 if (s->sample_rate >= 44100)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
390 table = exponent_band_44100[a];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
391 else if (s->sample_rate >= 32000)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
392 table = exponent_band_32000[a];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
393 else if (s->sample_rate >= 22050)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
394 table = exponent_band_22050[a];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
395 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
396 if (table) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
397 n = *table++;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
398 for(i=0;i<n;i++)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
399 s->exponent_bands[k][i] = table[i];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
400 s->exponent_sizes[k] = n;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
401 } else {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
402 j = 0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
403 lpos = 0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
404 for(i=0;i<25;i++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
405 a = wma_critical_freqs[i];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
406 b = s->sample_rate;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
407 pos = ((block_len * 2 * a) + (b << 1)) / (4 * b);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
408 pos <<= 2;
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
409 if (pos > block_len)
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
410 pos = block_len;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
411 if (pos > lpos)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
412 s->exponent_bands[k][j++] = pos - lpos;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
413 if (pos >= block_len)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
414 break;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
415 lpos = pos;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
416 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
417 s->exponent_sizes[k] = j;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
418 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
419 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
420
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
421 /* max number of coefs */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
422 s->coefs_end[k] = (s->frame_len - ((s->frame_len * 9) / 100)) >> k;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
423 /* high freq computation */
3235
d3c05c7dabcd reverting 1.31->1.33
michael
parents: 3195
diff changeset
424 s->high_band_start[k] = (int)((block_len * 2 * high_freq) /
d3c05c7dabcd reverting 1.31->1.33
michael
parents: 3195
diff changeset
425 s->sample_rate + 0.5);
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
426 n = s->exponent_sizes[k];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
427 j = 0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
428 pos = 0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
429 for(i=0;i<n;i++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
430 int start, end;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
431 start = pos;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
432 pos += s->exponent_bands[k][i];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
433 end = pos;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
434 if (start < s->high_band_start[k])
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
435 start = s->high_band_start[k];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
436 if (end > s->coefs_end[k])
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
437 end = s->coefs_end[k];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
438 if (end > start)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
439 s->exponent_high_bands[k][j++] = end - start;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
440 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
441 s->exponent_high_sizes[k] = j;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
442 #if 0
1342
f574934c4219 uniformization (now it uses the same trace functions as h264, defined in common.h)
al3x
parents: 1303
diff changeset
443 tprintf("%5d: coefs_end=%d high_band_start=%d nb_high_bands=%d: ",
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
444 s->frame_len >> k,
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
445 s->coefs_end[k],
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
446 s->high_band_start[k],
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
447 s->exponent_high_sizes[k]);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
448 for(j=0;j<s->exponent_high_sizes[k];j++)
1342
f574934c4219 uniformization (now it uses the same trace functions as h264, defined in common.h)
al3x
parents: 1303
diff changeset
449 tprintf(" %d", s->exponent_high_bands[k][j]);
f574934c4219 uniformization (now it uses the same trace functions as h264, defined in common.h)
al3x
parents: 1303
diff changeset
450 tprintf("\n");
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
451 #endif
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
452 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
453 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
454
1342
f574934c4219 uniformization (now it uses the same trace functions as h264, defined in common.h)
al3x
parents: 1303
diff changeset
455 #ifdef TRACE
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
456 {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
457 int i, j;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
458 for(i = 0; i < s->nb_block_sizes; i++) {
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
459 tprintf("%5d: n=%2d:",
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
460 s->frame_len >> i,
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
461 s->exponent_sizes[i]);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
462 for(j=0;j<s->exponent_sizes[i];j++)
1342
f574934c4219 uniformization (now it uses the same trace functions as h264, defined in common.h)
al3x
parents: 1303
diff changeset
463 tprintf(" %d", s->exponent_bands[i][j]);
f574934c4219 uniformization (now it uses the same trace functions as h264, defined in common.h)
al3x
parents: 1303
diff changeset
464 tprintf("\n");
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
465 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
466 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
467 #endif
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
468
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
469 /* init MDCT */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
470 for(i = 0; i < s->nb_block_sizes; i++)
795
55add0e7eafb avoid name clash - fixed again block size selection
bellard
parents: 785
diff changeset
471 ff_mdct_init(&s->mdct_ctx[i], s->frame_len_bits - i + 1, 1);
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
472
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
473 /* init MDCT windows : simple sinus window */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
474 for(i = 0; i < s->nb_block_sizes; i++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
475 int n, j;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
476 float alpha;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
477 n = 1 << (s->frame_len_bits - i);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
478 window = av_malloc(sizeof(float) * n);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
479 alpha = M_PI / (2.0 * n);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
480 for(j=0;j<n;j++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
481 window[n - j - 1] = sin((j + 0.5) * alpha);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
482 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
483 s->windows[i] = window;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
484 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
485
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
486 s->reset_block_lengths = 1;
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
487
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
488 if (s->use_noise_coding) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
489
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
490 /* init the noise generator */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
491 if (s->use_exp_vlc)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
492 s->noise_mult = 0.02;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
493 else
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
494 s->noise_mult = 0.04;
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
495
1342
f574934c4219 uniformization (now it uses the same trace functions as h264, defined in common.h)
al3x
parents: 1303
diff changeset
496 #ifdef TRACE
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
497 for(i=0;i<NOISE_TAB_SIZE;i++)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
498 s->noise_table[i] = 1.0 * s->noise_mult;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
499 #else
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
500 {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
501 unsigned int seed;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
502 float norm;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
503 seed = 1;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
504 norm = (1.0 / (float)(1LL << 31)) * sqrt(3) * s->noise_mult;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
505 for(i=0;i<NOISE_TAB_SIZE;i++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
506 seed = seed * 314159 + 1;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
507 s->noise_table[i] = (float)((int)seed) * norm;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
508 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
509 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
510 #endif
3113
ab01ee59324f - fix insufficient code length for exp_vlc
henry
parents: 3089
diff changeset
511 init_vlc(&s->hgain_vlc, HGAINVLCBITS, sizeof(hgain_huffbits),
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
512 hgain_huffbits, 1, 1,
2370
26560d4fdb1f Memory leak fix patch by (Burkhard Plaum <plaum >at< ipf.uni-stuttgart )dot( de>)
michael
parents: 2180
diff changeset
513 hgain_huffcodes, 2, 2, 0);
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
514 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
515
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
516 if (s->use_exp_vlc) {
3113
ab01ee59324f - fix insufficient code length for exp_vlc
henry
parents: 3089
diff changeset
517 init_vlc(&s->exp_vlc, EXPVLCBITS, sizeof(scale_huffbits),
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
518 scale_huffbits, 1, 1,
2370
26560d4fdb1f Memory leak fix patch by (Burkhard Plaum <plaum >at< ipf.uni-stuttgart )dot( de>)
michael
parents: 2180
diff changeset
519 scale_huffcodes, 4, 4, 0);
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
520 } else {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
521 wma_lsp_to_curve_init(s, s->frame_len);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
522 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
523
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
524 /* choose the VLC tables for the coefficients */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
525 coef_vlc_table = 2;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
526 if (s->sample_rate >= 32000) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
527 if (bps1 < 0.72)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
528 coef_vlc_table = 0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
529 else if (bps1 < 1.16)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
530 coef_vlc_table = 1;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
531 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
532
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
533 init_coef_vlc(&s->coef_vlc[0], &s->run_table[0], &s->level_table[0],
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
534 &coef_vlcs[coef_vlc_table * 2]);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
535 init_coef_vlc(&s->coef_vlc[1], &s->run_table[1], &s->level_table[1],
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
536 &coef_vlcs[coef_vlc_table * 2 + 1]);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
537 return 0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
538 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
539
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
540 /* interpolate values for a bigger or smaller block. The block must
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
541 have multiple sizes */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
542 static void interpolate_array(float *scale, int old_size, int new_size)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
543 {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
544 int i, j, jincr, k;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
545 float v;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
546
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
547 if (new_size > old_size) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
548 jincr = new_size / old_size;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
549 j = new_size;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
550 for(i = old_size - 1; i >=0; i--) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
551 v = scale[i];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
552 k = jincr;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
553 do {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
554 scale[--j] = v;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
555 } while (--k);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
556 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
557 } else if (new_size < old_size) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
558 j = 0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
559 jincr = old_size / new_size;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
560 for(i = 0; i < new_size; i++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
561 scale[i] = scale[j];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
562 j += jincr;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
563 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
564 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
565 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
566
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
567 /* compute x^-0.25 with an exponent and mantissa table. We use linear
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
568 interpolation to reduce the mantissa table size at a small speed
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
569 expense (linear interpolation approximately doubles the number of
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
570 bits of precision). */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
571 static inline float pow_m1_4(WMADecodeContext *s, float x)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
572 {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
573 union {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
574 float f;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
575 unsigned int v;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
576 } u, t;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
577 unsigned int e, m;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
578 float a, b;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
579
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
580 u.f = x;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
581 e = u.v >> 23;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
582 m = (u.v >> (23 - LSP_POW_BITS)) & ((1 << LSP_POW_BITS) - 1);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
583 /* build interpolation scale: 1 <= t < 2. */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
584 t.v = ((u.v << LSP_POW_BITS) & ((1 << 23) - 1)) | (127 << 23);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
585 a = s->lsp_pow_m_table1[m];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
586 b = s->lsp_pow_m_table2[m];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
587 return s->lsp_pow_e_table[e] * (a + b * t.f);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
588 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
589
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
590 static void wma_lsp_to_curve_init(WMADecodeContext *s, int frame_len)
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
591 {
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
592 float wdel, a, b;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
593 int i, e, m;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
594
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
595 wdel = M_PI / frame_len;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
596 for(i=0;i<frame_len;i++)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
597 s->lsp_cos_table[i] = 2.0f * cos(wdel * i);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
598
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
599 /* tables for x^-0.25 computation */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
600 for(i=0;i<256;i++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
601 e = i - 126;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
602 s->lsp_pow_e_table[i] = pow(2.0, e * -0.25);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
603 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
604
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
605 /* NOTE: these two tables are needed to avoid two operations in
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
606 pow_m1_4 */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
607 b = 1.0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
608 for(i=(1 << LSP_POW_BITS) - 1;i>=0;i--) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
609 m = (1 << LSP_POW_BITS) + i;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
610 a = (float)m * (0.5 / (1 << LSP_POW_BITS));
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
611 a = pow(a, -0.25);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
612 s->lsp_pow_m_table1[i] = 2 * a - b;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
613 s->lsp_pow_m_table2[i] = b - a;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
614 b = a;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
615 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
616 #if 0
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
617 for(i=1;i<20;i++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
618 float v, r1, r2;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
619 v = 5.0 / i;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
620 r1 = pow_m1_4(s, v);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
621 r2 = pow(v,-0.25);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
622 printf("%f^-0.25=%f e=%f\n", v, r1, r2 - r1);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
623 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
624 #endif
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
625 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
626
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
627 /* NOTE: We use the same code as Vorbis here */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
628 /* XXX: optimize it further with SSE/3Dnow */
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
629 static void wma_lsp_to_curve(WMADecodeContext *s,
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
630 float *out, float *val_max_ptr,
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
631 int n, float *lsp)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
632 {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
633 int i, j;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
634 float p, q, w, v, val_max;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
635
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
636 val_max = 0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
637 for(i=0;i<n;i++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
638 p = 0.5f;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
639 q = 0.5f;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
640 w = s->lsp_cos_table[i];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
641 for(j=1;j<NB_LSP_COEFS;j+=2){
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
642 q *= w - lsp[j - 1];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
643 p *= w - lsp[j];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
644 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
645 p *= p * (2.0f - w);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
646 q *= q * (2.0f + w);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
647 v = p + q;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
648 v = pow_m1_4(s, v);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
649 if (v > val_max)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
650 val_max = v;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
651 out[i] = v;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
652 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
653 *val_max_ptr = val_max;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
654 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
655
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
656 /* decode exponents coded with LSP coefficients (same idea as Vorbis) */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
657 static void decode_exp_lsp(WMADecodeContext *s, int ch)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
658 {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
659 float lsp_coefs[NB_LSP_COEFS];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
660 int val, i;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
661
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
662 for(i = 0; i < NB_LSP_COEFS; i++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
663 if (i == 0 || i >= 8)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
664 val = get_bits(&s->gb, 3);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
665 else
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
666 val = get_bits(&s->gb, 4);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
667 lsp_coefs[i] = lsp_codebook[i][val];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
668 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
669
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
670 wma_lsp_to_curve(s, s->exponents[ch], &s->max_exponent[ch],
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
671 s->block_len, lsp_coefs);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
672 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
673
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
674 /* decode exponents coded with VLC codes */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
675 static int decode_exp_vlc(WMADecodeContext *s, int ch)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
676 {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
677 int last_exp, n, code;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
678 const uint16_t *ptr, *band_ptr;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
679 float v, *q, max_scale, *q_end;
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
680
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
681 band_ptr = s->exponent_bands[s->frame_len_bits - s->block_len_bits];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
682 ptr = band_ptr;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
683 q = s->exponents[ch];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
684 q_end = q + s->block_len;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
685 max_scale = 0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
686 if (s->version == 1) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
687 last_exp = get_bits(&s->gb, 5) + 10;
3235
d3c05c7dabcd reverting 1.31->1.33
michael
parents: 3195
diff changeset
688 /* XXX: use a table */
d3c05c7dabcd reverting 1.31->1.33
michael
parents: 3195
diff changeset
689 v = pow(10, last_exp * (1.0 / 16.0));
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
690 max_scale = v;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
691 n = *ptr++;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
692 do {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
693 *q++ = v;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
694 } while (--n);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
695 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
696 last_exp = 36;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
697 while (q < q_end) {
3113
ab01ee59324f - fix insufficient code length for exp_vlc
henry
parents: 3089
diff changeset
698 code = get_vlc2(&s->gb, s->exp_vlc.table, EXPVLCBITS, EXPMAX);
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
699 if (code < 0)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
700 return -1;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
701 /* NOTE: this offset is the same as MPEG4 AAC ! */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
702 last_exp += code - 60;
3235
d3c05c7dabcd reverting 1.31->1.33
michael
parents: 3195
diff changeset
703 /* XXX: use a table */
d3c05c7dabcd reverting 1.31->1.33
michael
parents: 3195
diff changeset
704 v = pow(10, last_exp * (1.0 / 16.0));
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
705 if (v > max_scale)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
706 max_scale = v;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
707 n = *ptr++;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
708 do {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
709 *q++ = v;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
710 } while (--n);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
711 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
712 s->max_exponent[ch] = max_scale;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
713 return 0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
714 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
715
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
716 /* return 0 if OK. return 1 if last block of frame. return -1 if
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
717 unrecorrable error. */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
718 static int wma_decode_block(WMADecodeContext *s)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
719 {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
720 int n, v, a, ch, code, bsize;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
721 int coef_nb_bits, total_gain, parse_exponents;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
722 int nb_coefs[MAX_CHANNELS];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
723 float mdct_norm;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
724
1343
1fd083c620d6 moved frame_count to wmadeccontext
al3x
parents: 1342
diff changeset
725 #ifdef TRACE
1fd083c620d6 moved frame_count to wmadeccontext
al3x
parents: 1342
diff changeset
726 tprintf("***decode_block: %d:%d\n", s->frame_count - 1, s->block_num);
1fd083c620d6 moved frame_count to wmadeccontext
al3x
parents: 1342
diff changeset
727 #endif
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
728
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
729 /* compute current block length */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
730 if (s->use_variable_block_len) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
731 n = av_log2(s->nb_block_sizes - 1) + 1;
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
732
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
733 if (s->reset_block_lengths) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
734 s->reset_block_lengths = 0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
735 v = get_bits(&s->gb, n);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
736 if (v >= s->nb_block_sizes)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
737 return -1;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
738 s->prev_block_len_bits = s->frame_len_bits - v;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
739 v = get_bits(&s->gb, n);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
740 if (v >= s->nb_block_sizes)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
741 return -1;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
742 s->block_len_bits = s->frame_len_bits - v;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
743 } else {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
744 /* update block lengths */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
745 s->prev_block_len_bits = s->block_len_bits;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
746 s->block_len_bits = s->next_block_len_bits;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
747 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
748 v = get_bits(&s->gb, n);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
749 if (v >= s->nb_block_sizes)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
750 return -1;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
751 s->next_block_len_bits = s->frame_len_bits - v;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
752 } else {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
753 /* fixed block len */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
754 s->next_block_len_bits = s->frame_len_bits;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
755 s->prev_block_len_bits = s->frame_len_bits;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
756 s->block_len_bits = s->frame_len_bits;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
757 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
758
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
759 /* now check if the block length is coherent with the frame length */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
760 s->block_len = 1 << s->block_len_bits;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
761 if ((s->block_pos + s->block_len) > s->frame_len)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
762 return -1;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
763
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
764 if (s->nb_channels == 2) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
765 s->ms_stereo = get_bits(&s->gb, 1);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
766 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
767 v = 0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
768 for(ch = 0; ch < s->nb_channels; ch++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
769 a = get_bits(&s->gb, 1);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
770 s->channel_coded[ch] = a;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
771 v |= a;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
772 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
773 /* if no channel coded, no need to go further */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
774 /* XXX: fix potential framing problems */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
775 if (!v)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
776 goto next;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
777
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
778 bsize = s->frame_len_bits - s->block_len_bits;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
779
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
780 /* read total gain and extract corresponding number of bits for
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
781 coef escape coding */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
782 total_gain = 1;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
783 for(;;) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
784 a = get_bits(&s->gb, 7);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
785 total_gain += a;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
786 if (a != 127)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
787 break;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
788 }
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
789
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
790 if (total_gain < 15)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
791 coef_nb_bits = 13;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
792 else if (total_gain < 32)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
793 coef_nb_bits = 12;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
794 else if (total_gain < 40)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
795 coef_nb_bits = 11;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
796 else if (total_gain < 45)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
797 coef_nb_bits = 10;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
798 else
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
799 coef_nb_bits = 9;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
800
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
801 /* compute number of coefficients */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
802 n = s->coefs_end[bsize] - s->coefs_start;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
803 for(ch = 0; ch < s->nb_channels; ch++)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
804 nb_coefs[ch] = n;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
805
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
806 /* complex coding */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
807 if (s->use_noise_coding) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
808
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
809 for(ch = 0; ch < s->nb_channels; ch++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
810 if (s->channel_coded[ch]) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
811 int i, n, a;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
812 n = s->exponent_high_sizes[bsize];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
813 for(i=0;i<n;i++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
814 a = get_bits(&s->gb, 1);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
815 s->high_band_coded[ch][i] = a;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
816 /* if noise coding, the coefficients are not transmitted */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
817 if (a)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
818 nb_coefs[ch] -= s->exponent_high_bands[bsize][i];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
819 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
820 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
821 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
822 for(ch = 0; ch < s->nb_channels; ch++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
823 if (s->channel_coded[ch]) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
824 int i, n, val, code;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
825
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
826 n = s->exponent_high_sizes[bsize];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
827 val = (int)0x80000000;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
828 for(i=0;i<n;i++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
829 if (s->high_band_coded[ch][i]) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
830 if (val == (int)0x80000000) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
831 val = get_bits(&s->gb, 7) - 19;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
832 } else {
3113
ab01ee59324f - fix insufficient code length for exp_vlc
henry
parents: 3089
diff changeset
833 code = get_vlc2(&s->gb, s->hgain_vlc.table, HGAINVLCBITS, HGAINMAX);
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
834 if (code < 0)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
835 return -1;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
836 val += code - 18;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
837 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
838 s->high_band_values[ch][i] = val;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
839 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
840 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
841 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
842 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
843 }
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
844
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
845 /* exposant can be interpolated in short blocks. */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
846 parse_exponents = 1;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
847 if (s->block_len_bits != s->frame_len_bits) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
848 parse_exponents = get_bits(&s->gb, 1);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
849 }
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
850
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
851 if (parse_exponents) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
852 for(ch = 0; ch < s->nb_channels; ch++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
853 if (s->channel_coded[ch]) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
854 if (s->use_exp_vlc) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
855 if (decode_exp_vlc(s, ch) < 0)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
856 return -1;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
857 } else {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
858 decode_exp_lsp(s, ch);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
859 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
860 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
861 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
862 } else {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
863 for(ch = 0; ch < s->nb_channels; ch++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
864 if (s->channel_coded[ch]) {
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
865 interpolate_array(s->exponents[ch], 1 << s->prev_block_len_bits,
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
866 s->block_len);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
867 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
868 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
869 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
870
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
871 /* parse spectral coefficients : just RLE encoding */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
872 for(ch = 0; ch < s->nb_channels; ch++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
873 if (s->channel_coded[ch]) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
874 VLC *coef_vlc;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
875 int level, run, sign, tindex;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
876 int16_t *ptr, *eptr;
3776
1843a85123b7 fix some signedness warnings
mru
parents: 3700
diff changeset
877 const uint16_t *level_table, *run_table;
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
878
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
879 /* special VLC tables are used for ms stereo because
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
880 there is potentially less energy there */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
881 tindex = (ch == 1 && s->ms_stereo);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
882 coef_vlc = &s->coef_vlc[tindex];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
883 run_table = s->run_table[tindex];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
884 level_table = s->level_table[tindex];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
885 /* XXX: optimize */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
886 ptr = &s->coefs1[ch][0];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
887 eptr = ptr + nb_coefs[ch];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
888 memset(ptr, 0, s->block_len * sizeof(int16_t));
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
889 for(;;) {
3113
ab01ee59324f - fix insufficient code length for exp_vlc
henry
parents: 3089
diff changeset
890 code = get_vlc2(&s->gb, coef_vlc->table, VLCBITS, VLCMAX);
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
891 if (code < 0)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
892 return -1;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
893 if (code == 1) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
894 /* EOB */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
895 break;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
896 } else if (code == 0) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
897 /* escape */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
898 level = get_bits(&s->gb, coef_nb_bits);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
899 /* NOTE: this is rather suboptimal. reading
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
900 block_len_bits would be better */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
901 run = get_bits(&s->gb, s->frame_len_bits);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
902 } else {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
903 /* normal code */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
904 run = run_table[code];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
905 level = level_table[code];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
906 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
907 sign = get_bits(&s->gb, 1);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
908 if (!sign)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
909 level = -level;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
910 ptr += run;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
911 if (ptr >= eptr)
3361
bcaa5113e311 Ignore overrun in spectral RLE decoding, fixes
reimar
parents: 3235
diff changeset
912 {
bcaa5113e311 Ignore overrun in spectral RLE decoding, fixes
reimar
parents: 3235
diff changeset
913 av_log(NULL, AV_LOG_ERROR, "overflow in spectral RLE, ignoring\n");
bcaa5113e311 Ignore overrun in spectral RLE decoding, fixes
reimar
parents: 3235
diff changeset
914 break;
bcaa5113e311 Ignore overrun in spectral RLE decoding, fixes
reimar
parents: 3235
diff changeset
915 }
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
916 *ptr++ = level;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
917 /* NOTE: EOB can be omitted */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
918 if (ptr >= eptr)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
919 break;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
920 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
921 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
922 if (s->version == 1 && s->nb_channels >= 2) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
923 align_get_bits(&s->gb);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
924 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
925 }
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
926
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
927 /* normalize */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
928 {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
929 int n4 = s->block_len / 2;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
930 mdct_norm = 1.0 / (float)n4;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
931 if (s->version == 1) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
932 mdct_norm *= sqrt(n4);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
933 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
934 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
935
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
936 /* finally compute the MDCT coefficients */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
937 for(ch = 0; ch < s->nb_channels; ch++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
938 if (s->channel_coded[ch]) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
939 int16_t *coefs1;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
940 float *coefs, *exponents, mult, mult1, noise, *exp_ptr;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
941 int i, j, n, n1, last_high_band;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
942 float exp_power[HIGH_BAND_MAX_SIZE];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
943
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
944 coefs1 = s->coefs1[ch];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
945 exponents = s->exponents[ch];
3235
d3c05c7dabcd reverting 1.31->1.33
michael
parents: 3195
diff changeset
946 mult = pow(10, total_gain * 0.05) / s->max_exponent[ch];
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
947 mult *= mdct_norm;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
948 coefs = s->coefs[ch];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
949 if (s->use_noise_coding) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
950 mult1 = mult;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
951 /* very low freqs : noise */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
952 for(i = 0;i < s->coefs_start; i++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
953 *coefs++ = s->noise_table[s->noise_index] * (*exponents++) * mult1;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
954 s->noise_index = (s->noise_index + 1) & (NOISE_TAB_SIZE - 1);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
955 }
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
956
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
957 n1 = s->exponent_high_sizes[bsize];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
958
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
959 /* compute power of high bands */
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
960 exp_ptr = exponents +
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
961 s->high_band_start[bsize] -
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
962 s->coefs_start;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
963 last_high_band = 0; /* avoid warning */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
964 for(j=0;j<n1;j++) {
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
965 n = s->exponent_high_bands[s->frame_len_bits -
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
966 s->block_len_bits][j];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
967 if (s->high_band_coded[ch][j]) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
968 float e2, v;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
969 e2 = 0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
970 for(i = 0;i < n; i++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
971 v = exp_ptr[i];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
972 e2 += v * v;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
973 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
974 exp_power[j] = e2 / n;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
975 last_high_band = j;
1342
f574934c4219 uniformization (now it uses the same trace functions as h264, defined in common.h)
al3x
parents: 1303
diff changeset
976 tprintf("%d: power=%f (%d)\n", j, exp_power[j], n);
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
977 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
978 exp_ptr += n;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
979 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
980
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
981 /* main freqs and high freqs */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
982 for(j=-1;j<n1;j++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
983 if (j < 0) {
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
984 n = s->high_band_start[bsize] -
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
985 s->coefs_start;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
986 } else {
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
987 n = s->exponent_high_bands[s->frame_len_bits -
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
988 s->block_len_bits][j];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
989 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
990 if (j >= 0 && s->high_band_coded[ch][j]) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
991 /* use noise with specified power */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
992 mult1 = sqrt(exp_power[j] / exp_power[last_high_band]);
3235
d3c05c7dabcd reverting 1.31->1.33
michael
parents: 3195
diff changeset
993 /* XXX: use a table */
d3c05c7dabcd reverting 1.31->1.33
michael
parents: 3195
diff changeset
994 mult1 = mult1 * pow(10, s->high_band_values[ch][j] * 0.05);
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
995 mult1 = mult1 / (s->max_exponent[ch] * s->noise_mult);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
996 mult1 *= mdct_norm;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
997 for(i = 0;i < n; i++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
998 noise = s->noise_table[s->noise_index];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
999 s->noise_index = (s->noise_index + 1) & (NOISE_TAB_SIZE - 1);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1000 *coefs++ = (*exponents++) * noise * mult1;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1001 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1002 } else {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1003 /* coded values + small noise */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1004 for(i = 0;i < n; i++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1005 noise = s->noise_table[s->noise_index];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1006 s->noise_index = (s->noise_index + 1) & (NOISE_TAB_SIZE - 1);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1007 *coefs++ = ((*coefs1++) + noise) * (*exponents++) * mult;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1008 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1009 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1010 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1011
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1012 /* very high freqs : noise */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1013 n = s->block_len - s->coefs_end[bsize];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1014 mult1 = mult * exponents[-1];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1015 for(i = 0; i < n; i++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1016 *coefs++ = s->noise_table[s->noise_index] * mult1;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1017 s->noise_index = (s->noise_index + 1) & (NOISE_TAB_SIZE - 1);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1018 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1019 } else {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1020 /* XXX: optimize more */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1021 for(i = 0;i < s->coefs_start; i++)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1022 *coefs++ = 0.0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1023 n = nb_coefs[ch];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1024 for(i = 0;i < n; i++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1025 *coefs++ = coefs1[i] * exponents[i] * mult;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1026 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1027 n = s->block_len - s->coefs_end[bsize];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1028 for(i = 0;i < n; i++)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1029 *coefs++ = 0.0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1030 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1031 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1032 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1033
1342
f574934c4219 uniformization (now it uses the same trace functions as h264, defined in common.h)
al3x
parents: 1303
diff changeset
1034 #ifdef TRACE
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1035 for(ch = 0; ch < s->nb_channels; ch++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1036 if (s->channel_coded[ch]) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1037 dump_floats("exponents", 3, s->exponents[ch], s->block_len);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1038 dump_floats("coefs", 1, s->coefs[ch], s->block_len);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1039 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1040 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1041 #endif
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
1042
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1043 if (s->ms_stereo && s->channel_coded[1]) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1044 float a, b;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1045 int i;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1046
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1047 /* nominal case for ms stereo: we do it before mdct */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1048 /* no need to optimize this case because it should almost
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1049 never happen */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1050 if (!s->channel_coded[0]) {
1342
f574934c4219 uniformization (now it uses the same trace functions as h264, defined in common.h)
al3x
parents: 1303
diff changeset
1051 tprintf("rare ms-stereo case happened\n");
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1052 memset(s->coefs[0], 0, sizeof(float) * s->block_len);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1053 s->channel_coded[0] = 1;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1054 }
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
1055
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1056 for(i = 0; i < s->block_len; i++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1057 a = s->coefs[0][i];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1058 b = s->coefs[1][i];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1059 s->coefs[0][i] = a + b;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1060 s->coefs[1][i] = a - b;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1061 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1062 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1063
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1064 /* build the window : we ensure that when the windows overlap
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1065 their squared sum is always 1 (MDCT reconstruction rule) */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1066 /* XXX: merge with output */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1067 {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1068 int i, next_block_len, block_len, prev_block_len, n;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1069 float *wptr;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1070
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1071 block_len = s->block_len;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1072 prev_block_len = 1 << s->prev_block_len_bits;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1073 next_block_len = 1 << s->next_block_len_bits;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1074
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1075 /* right part */
4301
b43bd0c56eaa Bug fix for crashes when SSE is used on unaligned arrays.
banan
parents: 3947
diff changeset
1076 wptr = s->window + block_len;
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1077 if (block_len <= next_block_len) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1078 for(i=0;i<block_len;i++)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1079 *wptr++ = s->windows[bsize][i];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1080 } else {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1081 /* overlap */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1082 n = (block_len / 2) - (next_block_len / 2);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1083 for(i=0;i<n;i++)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1084 *wptr++ = 1.0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1085 for(i=0;i<next_block_len;i++)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1086 *wptr++ = s->windows[s->frame_len_bits - s->next_block_len_bits][i];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1087 for(i=0;i<n;i++)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1088 *wptr++ = 0.0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1089 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1090
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1091 /* left part */
4301
b43bd0c56eaa Bug fix for crashes when SSE is used on unaligned arrays.
banan
parents: 3947
diff changeset
1092 wptr = s->window + block_len;
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1093 if (block_len <= prev_block_len) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1094 for(i=0;i<block_len;i++)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1095 *--wptr = s->windows[bsize][i];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1096 } else {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1097 /* overlap */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1098 n = (block_len / 2) - (prev_block_len / 2);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1099 for(i=0;i<n;i++)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1100 *--wptr = 1.0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1101 for(i=0;i<prev_block_len;i++)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1102 *--wptr = s->windows[s->frame_len_bits - s->prev_block_len_bits][i];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1103 for(i=0;i<n;i++)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1104 *--wptr = 0.0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1105 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1106 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1107
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
1108
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1109 for(ch = 0; ch < s->nb_channels; ch++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1110 if (s->channel_coded[ch]) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1111 float *ptr;
3592
6a358dccf2ab SIMD vector optimizations. 3% faster overall decoding.
banan
parents: 3555
diff changeset
1112 int n4, index, n;
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1113
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1114 n = s->block_len;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1115 n4 = s->block_len / 2;
3555
5ea82888103e 3dnow2 implementation of imdct.
lorenm
parents: 3362
diff changeset
1116 s->mdct_ctx[bsize].fft.imdct_calc(&s->mdct_ctx[bsize],
4301
b43bd0c56eaa Bug fix for crashes when SSE is used on unaligned arrays.
banan
parents: 3947
diff changeset
1117 s->output, s->coefs[ch], s->mdct_tmp);
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1118
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1119 /* XXX: optimize all that by build the window and
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1120 multipying/adding at the same time */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1121
3592
6a358dccf2ab SIMD vector optimizations. 3% faster overall decoding.
banan
parents: 3555
diff changeset
1122 /* multiply by the window and add in the frame */
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1123 index = (s->frame_len / 2) + s->block_pos - n4;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1124 ptr = &s->frame_out[ch][index];
4301
b43bd0c56eaa Bug fix for crashes when SSE is used on unaligned arrays.
banan
parents: 3947
diff changeset
1125 s->dsp.vector_fmul_add_add(ptr,s->window,s->output,ptr,0,2*n,1);
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1126
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1127 /* specific fast case for ms-stereo : add to second
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1128 channel if it is not coded */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1129 if (s->ms_stereo && !s->channel_coded[1]) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1130 ptr = &s->frame_out[1][index];
4301
b43bd0c56eaa Bug fix for crashes when SSE is used on unaligned arrays.
banan
parents: 3947
diff changeset
1131 s->dsp.vector_fmul_add_add(ptr,s->window,s->output,ptr,0,2*n,1);
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1132 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1133 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1134 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1135 next:
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1136 /* update block number */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1137 s->block_num++;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1138 s->block_pos += s->block_len;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1139 if (s->block_pos >= s->frame_len)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1140 return 1;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1141 else
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1142 return 0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1143 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1144
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1145 /* decode a frame of frame_len samples */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1146 static int wma_decode_frame(WMADecodeContext *s, int16_t *samples)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1147 {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1148 int ret, i, n, a, ch, incr;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1149 int16_t *ptr;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1150 float *iptr;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1151
1343
1fd083c620d6 moved frame_count to wmadeccontext
al3x
parents: 1342
diff changeset
1152 #ifdef TRACE
1fd083c620d6 moved frame_count to wmadeccontext
al3x
parents: 1342
diff changeset
1153 tprintf("***decode_frame: %d size=%d\n", s->frame_count++, s->frame_len);
1fd083c620d6 moved frame_count to wmadeccontext
al3x
parents: 1342
diff changeset
1154 #endif
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1155
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1156 /* read each block */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1157 s->block_num = 0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1158 s->block_pos = 0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1159 for(;;) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1160 ret = wma_decode_block(s);
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
1161 if (ret < 0)
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1162 return -1;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1163 if (ret)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1164 break;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1165 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1166
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1167 /* convert frame to integer */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1168 n = s->frame_len;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1169 incr = s->nb_channels;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1170 for(ch = 0; ch < s->nb_channels; ch++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1171 ptr = samples + ch;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1172 iptr = s->frame_out[ch];
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1173
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1174 for(i=0;i<n;i++) {
797
308e973c3fda use lrintf to avoid double conversion
bellard
parents: 795
diff changeset
1175 a = lrintf(*iptr++);
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1176 if (a > 32767)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1177 a = 32767;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1178 else if (a < -32768)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1179 a = -32768;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1180 *ptr = a;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1181 ptr += incr;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1182 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1183 /* prepare for next block */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1184 memmove(&s->frame_out[ch][0], &s->frame_out[ch][s->frame_len],
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1185 s->frame_len * sizeof(float));
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1186 /* XXX: suppress this */
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
1187 memset(&s->frame_out[ch][s->frame_len], 0,
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1188 s->frame_len * sizeof(float));
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1189 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1190
1342
f574934c4219 uniformization (now it uses the same trace functions as h264, defined in common.h)
al3x
parents: 1303
diff changeset
1191 #ifdef TRACE
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1192 dump_shorts("samples", samples, n * s->nb_channels);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1193 #endif
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1194 return 0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1195 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1196
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
1197 static int wma_decode_superframe(AVCodecContext *avctx,
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1198 void *data, int *data_size,
1064
b32afefe7d33 * UINTX -> uintx_t INTX -> intx_t
kabi
parents: 1031
diff changeset
1199 uint8_t *buf, int buf_size)
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1200 {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1201 WMADecodeContext *s = avctx->priv_data;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1202 int nb_frames, bit_offset, i, pos, len;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1203 uint8_t *q;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1204 int16_t *samples;
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
1205
1342
f574934c4219 uniformization (now it uses the same trace functions as h264, defined in common.h)
al3x
parents: 1303
diff changeset
1206 tprintf("***decode_superframe:\n");
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1207
1750
610617f1dbd0 segfault fix
michael
parents: 1343
diff changeset
1208 if(buf_size==0){
610617f1dbd0 segfault fix
michael
parents: 1343
diff changeset
1209 s->last_superframe_len = 0;
610617f1dbd0 segfault fix
michael
parents: 1343
diff changeset
1210 return 0;
610617f1dbd0 segfault fix
michael
parents: 1343
diff changeset
1211 }
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
1212
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1213 samples = data;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1214
1025
1f9afd8b9131 GetBitContext.size is allways multiplied by 8 -> use size_in_bits to avoid useless *8 in a few inner loops
michaelni
parents: 972
diff changeset
1215 init_get_bits(&s->gb, buf, buf_size*8);
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
1216
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1217 if (s->use_bit_reservoir) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1218 /* read super frame header */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1219 get_bits(&s->gb, 4); /* super frame index */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1220 nb_frames = get_bits(&s->gb, 4) - 1;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1221
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1222 bit_offset = get_bits(&s->gb, s->byte_offset_bits + 3);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1223
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1224 if (s->last_superframe_len > 0) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1225 // printf("skip=%d\n", s->last_bitoffset);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1226 /* add bit_offset bits to last frame */
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
1227 if ((s->last_superframe_len + ((bit_offset + 7) >> 3)) >
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1228 MAX_CODED_SUPERFRAME_SIZE)
964
6e6773512288 oops : better error resilience - should fix most wma decoding problems
bellard
parents: 819
diff changeset
1229 goto fail;
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1230 q = s->last_superframe + s->last_superframe_len;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1231 len = bit_offset;
3362
c43fcf831f7c Do not read full byte when less than 8 bits are still to be read.
reimar
parents: 3361
diff changeset
1232 while (len > 7) {
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1233 *q++ = (get_bits)(&s->gb, 8);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1234 len -= 8;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1235 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1236 if (len > 0) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1237 *q++ = (get_bits)(&s->gb, len) << (8 - len);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1238 }
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
1239
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1240 /* XXX: bit_offset bits into last frame */
1025
1f9afd8b9131 GetBitContext.size is allways multiplied by 8 -> use size_in_bits to avoid useless *8 in a few inner loops
michaelni
parents: 972
diff changeset
1241 init_get_bits(&s->gb, s->last_superframe, MAX_CODED_SUPERFRAME_SIZE*8);
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1242 /* skip unused bits */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1243 if (s->last_bitoffset > 0)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1244 skip_bits(&s->gb, s->last_bitoffset);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1245 /* this frame is stored in the last superframe and in the
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1246 current one */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1247 if (wma_decode_frame(s, samples) < 0)
964
6e6773512288 oops : better error resilience - should fix most wma decoding problems
bellard
parents: 819
diff changeset
1248 goto fail;
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1249 samples += s->nb_channels * s->frame_len;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1250 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1251
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1252 /* read each frame starting from bit_offset */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1253 pos = bit_offset + 4 + 4 + s->byte_offset_bits + 3;
1025
1f9afd8b9131 GetBitContext.size is allways multiplied by 8 -> use size_in_bits to avoid useless *8 in a few inner loops
michaelni
parents: 972
diff changeset
1254 init_get_bits(&s->gb, buf + (pos >> 3), (MAX_CODED_SUPERFRAME_SIZE - (pos >> 3))*8);
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1255 len = pos & 7;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1256 if (len > 0)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1257 skip_bits(&s->gb, len);
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
1258
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1259 s->reset_block_lengths = 1;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1260 for(i=0;i<nb_frames;i++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1261 if (wma_decode_frame(s, samples) < 0)
964
6e6773512288 oops : better error resilience - should fix most wma decoding problems
bellard
parents: 819
diff changeset
1262 goto fail;
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1263 samples += s->nb_channels * s->frame_len;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1264 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1265
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1266 /* we copy the end of the frame in the last frame buffer */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1267 pos = get_bits_count(&s->gb) + ((bit_offset + 4 + 4 + s->byte_offset_bits + 3) & ~7);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1268 s->last_bitoffset = pos & 7;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1269 pos >>= 3;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1270 len = buf_size - pos;
819
ae89deb3a97d * avoid negative numbers as well
kabi
parents: 818
diff changeset
1271 if (len > MAX_CODED_SUPERFRAME_SIZE || len < 0) {
964
6e6773512288 oops : better error resilience - should fix most wma decoding problems
bellard
parents: 819
diff changeset
1272 goto fail;
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1273 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1274 s->last_superframe_len = len;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1275 memcpy(s->last_superframe, buf + pos, len);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1276 } else {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1277 /* single frame decode */
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1278 if (wma_decode_frame(s, samples) < 0)
964
6e6773512288 oops : better error resilience - should fix most wma decoding problems
bellard
parents: 819
diff changeset
1279 goto fail;
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1280 samples += s->nb_channels * s->frame_len;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1281 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1282 *data_size = (int8_t *)samples - (int8_t *)data;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1283 return s->block_align;
964
6e6773512288 oops : better error resilience - should fix most wma decoding problems
bellard
parents: 819
diff changeset
1284 fail:
6e6773512288 oops : better error resilience - should fix most wma decoding problems
bellard
parents: 819
diff changeset
1285 /* when error, we reset the bit reservoir */
6e6773512288 oops : better error resilience - should fix most wma decoding problems
bellard
parents: 819
diff changeset
1286 s->last_superframe_len = 0;
6e6773512288 oops : better error resilience - should fix most wma decoding problems
bellard
parents: 819
diff changeset
1287 return -1;
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1288 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1289
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1290 static int wma_decode_end(AVCodecContext *avctx)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1291 {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1292 WMADecodeContext *s = avctx->priv_data;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1293 int i;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1294
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1295 for(i = 0; i < s->nb_block_sizes; i++)
795
55add0e7eafb avoid name clash - fixed again block size selection
bellard
parents: 785
diff changeset
1296 ff_mdct_end(&s->mdct_ctx[i]);
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1297 for(i = 0; i < s->nb_block_sizes; i++)
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1298 av_free(s->windows[i]);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1299
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1300 if (s->use_exp_vlc) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1301 free_vlc(&s->exp_vlc);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1302 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1303 if (s->use_noise_coding) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1304 free_vlc(&s->hgain_vlc);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1305 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1306 for(i = 0;i < 2; i++) {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1307 free_vlc(&s->coef_vlc[i]);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1308 av_free(s->run_table[i]);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1309 av_free(s->level_table[i]);
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1310 }
2967
ef2149182f1c COSMETICS: Remove all trailing whitespace.
diego
parents: 2775
diff changeset
1311
783
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1312 return 0;
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1313 }
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1314
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1315 AVCodec wmav1_decoder =
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1316 {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1317 "wmav1",
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1318 CODEC_TYPE_AUDIO,
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1319 CODEC_ID_WMAV1,
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1320 sizeof(WMADecodeContext),
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1321 wma_decode_init,
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1322 NULL,
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1323 wma_decode_end,
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1324 wma_decode_superframe,
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1325 };
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1326
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1327 AVCodec wmav2_decoder =
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1328 {
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1329 "wmav2",
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1330 CODEC_TYPE_AUDIO,
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1331 CODEC_ID_WMAV2,
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1332 sizeof(WMADecodeContext),
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1333 wma_decode_init,
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1334 NULL,
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1335 wma_decode_end,
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1336 wma_decode_superframe,
b6eefd714bf3 added wma decoder
bellard
parents:
diff changeset
1337 };