X-Git-Url: http://git.tuebingen.mpg.de/?p=paraslash.git;a=blobdiff_plain;f=wmadec_filter.c;h=0565a14bfaac6e0353fd5eac89b23666c03a1282;hp=a548d04894040bb79b9d8247ad40200b58d917da;hb=5747192b26d313449964a735226136c12dc1c77e;hpb=f481eaddec671c3783cc098d65be29ea16ee81b1 diff --git a/wmadec_filter.c b/wmadec_filter.c index a548d048..0565a14b 100644 --- a/wmadec_filter.c +++ b/wmadec_filter.c @@ -19,7 +19,6 @@ #include #include -#include #include #include #include @@ -96,7 +95,6 @@ struct private_wmadec_data { int next_block_len_bits; ///< log2 of next block length int prev_block_len_bits; ///< log2 of prev block length int block_len; ///< block length in samples - int block_num; ///< block number in current frame int block_pos; ///< current position in frame uint8_t ms_stereo; ///< true if mid/side stereo mode uint8_t channel_coded[MAX_CHANNELS]; ///< true if channel is coded @@ -125,13 +123,34 @@ struct private_wmadec_data { }; #define EXPVLCBITS 8 -#define EXPMAX ((19+EXPVLCBITS-1)/EXPVLCBITS) +#define EXPMAX ((19 + EXPVLCBITS - 1) / EXPVLCBITS) #define HGAINVLCBITS 9 -#define HGAINMAX ((13+HGAINVLCBITS-1)/HGAINVLCBITS) +#define HGAINMAX ((13 + HGAINVLCBITS - 1) / HGAINVLCBITS) #define VLCBITS 9 -#define VLCMAX ((22+VLCBITS-1)/VLCBITS) +#define VLCMAX ((22 + VLCBITS - 1)/VLCBITS) + +DECLARE_ALIGNED(16, float, ff_sine_128[128]); +DECLARE_ALIGNED(16, float, ff_sine_256[256]); +DECLARE_ALIGNED(16, float, ff_sine_512[512]); +DECLARE_ALIGNED(16, float, ff_sine_1024[1024]); +DECLARE_ALIGNED(16, float, ff_sine_2048[2048]); +DECLARE_ALIGNED(16, float, ff_sine_4096[4096]); + +static float *ff_sine_windows[6] = { + ff_sine_128, ff_sine_256, ff_sine_512, ff_sine_1024, + ff_sine_2048, ff_sine_4096 +}; + +/* Generate a sine window. */ +static void sine_window_init(float *window, int n) +{ + int i; + + for (i = 0; i < n; i++) + window[i] = sinf((i + 0.5) * (M_PI / (2.0 * n))); +} static int wmadec_cleanup(struct private_wmadec_data *s) { @@ -168,9 +187,9 @@ static void init_coef_vlc(struct vlc *vlc, uint16_t **prun_table, init_vlc(vlc, VLCBITS, n, table_bits, 1, 1, table_codes, 4, 4); - run_table = para_malloc(n * sizeof (uint16_t)); - level_table = para_malloc(n * sizeof (uint16_t)); - int_table = para_malloc(n * sizeof (uint16_t)); + run_table = para_malloc(n * sizeof(uint16_t)); + level_table = para_malloc(n * sizeof(uint16_t)); + int_table = para_malloc(n * sizeof(uint16_t)); i = 2; level = 1; k = 0; @@ -446,14 +465,13 @@ static int wma_decode_init(char *initial_buf, int len, struct private_wmadec_dat struct private_wmadec_data *s; int ret, i; - if (len < 18) - return 0; - PARA_NOTICE_LOG("initial buf: %d bytes\n", len); s = para_calloc(sizeof(*s)); ret = read_asf_header(initial_buf, len, &s->ahi); - if (ret < 0) + if (ret <= 0) { + free(s); return ret; + } s->use_exp_vlc = s->ahi.flags2 & 0x0001; s->use_bit_reservoir = s->ahi.flags2 & 0x0002; @@ -464,21 +482,21 @@ static int wma_decode_init(char *initial_buf, int len, struct private_wmadec_dat return ret; /* init MDCT */ for (i = 0; i < s->nb_block_sizes; i++) { - ret = imdct_init(s->frame_len_bits - i + 1, 1, &s->mdct_ctx[i]); + ret = imdct_init(s->frame_len_bits - i + 1, &s->mdct_ctx[i]); if (ret < 0) return ret; } if (s->use_noise_coding) { PARA_INFO_LOG("using noise coding\n"); init_vlc(&s->hgain_vlc, HGAINVLCBITS, - sizeof (ff_wma_hgain_huffbits), ff_wma_hgain_huffbits, + sizeof(ff_wma_hgain_huffbits), ff_wma_hgain_huffbits, 1, 1, ff_wma_hgain_huffcodes, 2, 2); } if (s->use_exp_vlc) { PARA_INFO_LOG("using exp_vlc\n"); init_vlc(&s->exp_vlc, EXPVLCBITS, - sizeof (ff_wma_scale_huffbits), ff_wma_scale_huffbits, + sizeof(ff_wma_scale_huffbits), ff_wma_scale_huffbits, 1, 1, ff_wma_scale_huffcodes, 4, 4); } else { PARA_INFO_LOG("using curve\n"); @@ -611,18 +629,21 @@ static int decode_exp_vlc(struct private_wmadec_data *s, int ch) return 0; } -static void vector_fmul_add(float *dst, const float *src0, const float *src1, - const float *src2, int src3, int len, int step) +/* compute src0 * src1 + src2 */ +static inline void vector_mult_add(float *dst, const float *src0, const float *src1, + const float *src2, int len) { int i; + for (i = 0; i < len; i++) - dst[i * step] = src0[i] * src1[i] + src2[i] + src3; + dst[i] = src0[i] * src1[i] + src2[i]; } -static void vector_fmul_reverse_c(float *dst, const float *src0, +static inline void vector_mult_reverse(float *dst, const float *src0, const float *src1, int len) { int i; + src1 += len - 1; for (i = 0; i < len; i++) dst[i] = src0[i] * src1[-i]; @@ -643,43 +664,31 @@ static void wma_window(struct private_wmadec_data *s, float *out) if (s->block_len_bits <= s->prev_block_len_bits) { block_len = s->block_len; bsize = s->frame_len_bits - s->block_len_bits; - - vector_fmul_add(out, in, s->windows[bsize], - out, 0, block_len, 1); - + vector_mult_add(out, in, s->windows[bsize], out, block_len); } else { block_len = 1 << s->prev_block_len_bits; n = (s->block_len - block_len) / 2; bsize = s->frame_len_bits - s->prev_block_len_bits; - - vector_fmul_add(out + n, in + n, s->windows[bsize], - out + n, 0, block_len, 1); - + vector_mult_add(out + n, in + n, s->windows[bsize], out + n, + block_len); memcpy(out + n + block_len, in + n + block_len, - n * sizeof (float)); + n * sizeof(float)); } - out += s->block_len; in += s->block_len; - /* right part */ if (s->block_len_bits <= s->next_block_len_bits) { block_len = s->block_len; bsize = s->frame_len_bits - s->block_len_bits; - - vector_fmul_reverse_c(out, in, s->windows[bsize], block_len); - + vector_mult_reverse(out, in, s->windows[bsize], block_len); } else { block_len = 1 << s->next_block_len_bits; n = (s->block_len - block_len) / 2; bsize = s->frame_len_bits - s->next_block_len_bits; - - memcpy(out, in, n * sizeof (float)); - - vector_fmul_reverse_c(out + n, in + n, s->windows[bsize], - block_len); - - memset(out + n + block_len, 0, n * sizeof (float)); + memcpy(out, in, n * sizeof(float)); + vector_mult_reverse(out + n, in + n, s->windows[bsize], + block_len); + memset(out + n + block_len, 0, n * sizeof(float)); } } @@ -743,9 +752,8 @@ static int wma_decode_block(struct private_wmadec_data *s) if ((s->block_pos + s->block_len) > s->frame_len) return -E_INCOHERENT_BLOCK_LEN; - if (s->ahi.channels == 2) { + if (s->ahi.channels == 2) s->ms_stereo = get_bits1(&s->gb); - } v = 0; for (ch = 0; ch < s->ahi.channels; ch++) { int a = get_bits1(&s->gb); @@ -779,7 +787,6 @@ static int wma_decode_block(struct private_wmadec_data *s) /* complex coding */ if (s->use_noise_coding) { - for (ch = 0; ch < s->ahi.channels; ch++) { if (s->channel_coded[ch]) { int i, m, a; @@ -1091,7 +1098,7 @@ next: if (s->channel_coded[ch]) imdct(s->mdct_ctx[bsize], s->output, s->coefs[ch]); else if (!(s->ms_stereo && ch == 1)) - memset(s->output, 0, sizeof (s->output)); + memset(s->output, 0, sizeof(s->output)); /* multiply by the window and add in the frame */ index = (s->frame_len / 2) + s->block_pos - n4; @@ -1099,7 +1106,6 @@ next: } /* update block number */ - s->block_num++; s->block_pos += s->block_len; if (s->block_pos >= s->frame_len) return 1; @@ -1123,14 +1129,13 @@ static inline int16_t av_clip_int16(int a) } /* Decode a frame of frame_len samples. */ -static int wma_decode_frame(struct private_wmadec_data *s, int16_t * samples) +static int wma_decode_frame(struct private_wmadec_data *s, int16_t *samples) { int ret, i, n, ch, incr; int16_t *ptr; float *iptr; /* read each block */ - s->block_num = 0; s->block_pos = 0; for (;;) { ret = wma_decode_block(s); @@ -1153,7 +1158,7 @@ static int wma_decode_frame(struct private_wmadec_data *s, int16_t * samples) } /* prepare for next block */ memmove(&s->frame_out[ch][0], &s->frame_out[ch][s->frame_len], - s->frame_len * sizeof (float)); + s->frame_len * sizeof(float)); } return 0; } @@ -1199,9 +1204,8 @@ static int wma_decode_superframe(struct private_wmadec_data *s, void *data, *q++ = get_bits(&s->gb, 8); len -= 8; } - if (len > 0) { + if (len > 0) *q++ = get_bits(&s->gb, len) << (8 - len); - } /* XXX: bit_offset bits into last frame */ init_get_bits(&s->gb, s->last_superframe, @@ -1244,9 +1248,8 @@ static int wma_decode_superframe(struct private_wmadec_data *s, void *data, pos >>= 3; len = buf_size - pos; ret = -E_WMA_BAD_SUPERFRAME; - if (len > MAX_CODED_SUPERFRAME_SIZE || len < 0) { + if (len > MAX_CODED_SUPERFRAME_SIZE || len < 0) goto fail; - } s->last_superframe_len = len; memcpy(s->last_superframe, buf + pos, len); } else { @@ -1305,6 +1308,7 @@ static ssize_t wmadec_convert(char *inbuffer, size_t len, static void wmadec_close(struct filter_node *fn) { struct private_wmadec_data *pwd = fn->private_data; + if (!pwd) return; wmadec_cleanup(pwd);