[FFmpeg-soc] [soc]: r3418 - mlp/mlpenc.c
ramiro
subversion at mplayerhq.hu
Mon Aug 18 00:20:17 CEST 2008
Author: ramiro
Date: Mon Aug 18 00:20:17 2008
New Revision: 3418
Log:
Use LPC filter.
Modified:
mlp/mlpenc.c
Modified: mlp/mlpenc.c
==============================================================================
--- mlp/mlpenc.c (original)
+++ mlp/mlpenc.c Mon Aug 18 00:20:17 2008
@@ -23,9 +23,15 @@
#include "bitstream.h"
#include "libavutil/crc.h"
#include "mlp.h"
+#include "dsputil.h"
+#include "lpc.h"
#define MAJOR_HEADER_INTERVAL 16
+#define MLP_MIN_LPC_ORDER 0
+#define MLP_MAX_LPC_ORDER 8
+#define MLP_MAX_LPC_SHIFT 16
+
typedef struct {
//! The index of the first channel coded in this substream.
uint8_t min_channel;
@@ -92,6 +98,8 @@ typedef struct {
int32_t *big_sample_buffer;
int32_t *last_frame;
+ unsigned int lpc_frame_size;
+
int32_t *lossless_check_data;
uint8_t quant_step_size; ///< TODO This shouldn't be here.
@@ -115,6 +123,8 @@ typedef struct {
DecodingParams decoding_params[MAX_SUBSTREAMS];
RestartHeader restart_header[MAX_SUBSTREAMS];
+
+ DSPContext dsp;
} MLPEncodeContext;
#define SYNC_MAJOR 0xf8726f
@@ -381,6 +391,8 @@ static av_cold int mlp_encode_init(AVCod
default_decoding_params(ctx, ctx->decoding_params);
clear_channel_params(ctx->channel_params);
+ dsputil_init(&ctx->dsp, avctx);
+
return 0;
}
@@ -621,6 +633,7 @@ static void set_filter_params(MLPEncodeC
int restart_frame)
{
FilterParams *fp = &ctx->channel_params[channel].filter_params[filter];
+ unsigned int lpc_frame_size;
/* Restart frames must not depend on filter state from previous frames. */
if (restart_frame) {
@@ -628,10 +641,40 @@ static void set_filter_params(MLPEncodeC
return;
}
+ lpc_frame_size = ctx->frame_size[ctx->frame_index]
+ * ctx->major_header_interval;
+
+ if (ctx->frame_size[ctx->frame_index] >
+ ctx->frame_size[ctx->major_header_interval - 1])
+ lpc_frame_size -= ctx->frame_size[ctx->frame_index]
+ - ctx->frame_size[ctx->major_header_interval - 1];
+
+ ctx->lpc_frame_size = lpc_frame_size;
+
if (filter == FIR) {
- fp->order = 1;
- fp->shift = 0;
- fp->coeff[0] = 1;
+ int32_t *sample_buffer = ctx->sample_buffer + channel;
+ int32_t coefs[MAX_LPC_ORDER][MAX_LPC_ORDER];
+ int32_t samples[lpc_frame_size];
+ int32_t *lpc_samples = samples;
+ int shift[MLP_MAX_LPC_ORDER];
+ unsigned int i;
+ int order;
+
+ for (i = 0; i < lpc_frame_size; i++) {
+ *lpc_samples++ = *sample_buffer;
+ sample_buffer += ctx->num_channels;
+ }
+
+ order = ff_lpc_calc_coefs(&ctx->dsp, samples, lpc_frame_size,
+ MLP_MIN_LPC_ORDER, MLP_MAX_LPC_ORDER, 7,
+ coefs, shift, 1,
+ ORDER_METHOD_EST, MLP_MAX_LPC_SHIFT, 0);
+
+ fp->order = order;
+ fp->shift = shift[order-1];
+
+ for (i = 0; i < order; i++)
+ fp->coeff[i] = coefs[order-1][i];
} else { /* IIR */
fp->order = 0;
fp->shift = 0;
@@ -654,21 +697,22 @@ static int apply_filter(MLPEncodeContext
{
FilterParams *fp[NUM_FILTERS] = { &ctx->channel_params[channel].filter_params[FIR],
&ctx->channel_params[channel].filter_params[IIR], };
- int32_t filter_state_buffer[NUM_FILTERS][MAX_BLOCKSIZE + MAX_FILTER_ORDER];
+ int32_t filter_state_buffer[NUM_FILTERS][ctx->lpc_frame_size];
int32_t mask = MSB_MASK(ctx->decoding_params[0].quant_step_size[channel]);
int32_t *sample_buffer = ctx->sample_buffer + channel;
+ unsigned int lpc_frame_size = ctx->lpc_frame_size;
unsigned int filter_shift = fp[FIR]->shift;
- int index = MAX_BLOCKSIZE;
int filter;
int i;
- for (filter = 0; filter < NUM_FILTERS; filter++) {
- memcpy(&filter_state_buffer[filter][MAX_BLOCKSIZE],
- &fp[filter]->state[0],
- MAX_FILTER_ORDER * sizeof(int32_t));
+ for (i = 0; i < 8; i++) {
+ filter_state_buffer[FIR][i] = *sample_buffer;
+ filter_state_buffer[IIR][i] = *sample_buffer;
+
+ sample_buffer += ctx->num_channels;
}
- for (i = 0; i < ctx->frame_size[ctx->frame_index]; i++) {
+ for (i = 8; i < lpc_frame_size; i++) {
int32_t sample = *sample_buffer;
unsigned int order;
int64_t accum = 0;
@@ -676,7 +720,7 @@ static int apply_filter(MLPEncodeContext
for (filter = 0; filter < NUM_FILTERS; filter++)
for (order = 0; order < fp[filter]->order; order++)
- accum += (int64_t)filter_state_buffer[filter][index + order] *
+ accum += (int64_t)filter_state_buffer[filter][i - 1 - order] *
fp[filter]->coeff[order];
accum >>= filter_shift;
@@ -685,31 +729,19 @@ static int apply_filter(MLPEncodeContext
if (residual < INT24_MIN || residual > INT24_MAX)
return -1;
- --index;
-
- filter_state_buffer[FIR][index] = sample;
- filter_state_buffer[IIR][index] = residual;
+ filter_state_buffer[FIR][i] = sample;
+ filter_state_buffer[IIR][i] = residual;
sample_buffer += ctx->num_channels;
}
- index = MAX_BLOCKSIZE;
sample_buffer = ctx->sample_buffer + channel;
- for (i = 0; i < ctx->frame_size[ctx->frame_index]; i++) {
- int32_t residual = filter_state_buffer[IIR][--index];
-
- /* Store residual. */
- *sample_buffer = residual;
+ for (i = 0; i < lpc_frame_size; i++) {
+ *sample_buffer = filter_state_buffer[IIR][i];
sample_buffer += ctx->num_channels;
}
- for (filter = 0; filter < NUM_FILTERS; filter++) {
- memcpy(&fp[filter]->state[0],
- &filter_state_buffer[filter][index],
- MAX_FILTER_ORDER * sizeof(int32_t));
- }
-
return 0;
}
@@ -1113,15 +1145,15 @@ static void write_frame_headers(MLPEncod
/** Tries to determine a good prediction filter, and applies it to the samples
* buffer if the filter is good enough. Sets the filter data to be cleared if
- * this is a restart frame or no good filter was found.
+ * no good filter was found.
*/
-static void determine_filters(MLPEncodeContext *ctx, int restart_frame)
+static void determine_filters(MLPEncodeContext *ctx)
{
int channel, filter;
for (channel = 0; channel < ctx->avctx->channels; channel++) {
for (filter = 0; filter < NUM_FILTERS; filter++)
- set_filter_params(ctx, channel, filter, restart_frame);
+ set_filter_params(ctx, channel, filter, 0);
if (apply_filter(ctx, channel) < 0) {
/* Filter is horribly wrong.
* Clear filter params and update state. */
@@ -1306,6 +1338,8 @@ static int mlp_encode_frame(AVCodecConte
clear_decoding_params(decoding_params);
clear_channel_params (channel_params );
clear_channel_params(ctx->channel_params);
+
+ determine_filters(ctx);
} else {
memcpy(decoding_params, ctx->decoding_params, sizeof(decoding_params));
memcpy(channel_params, ctx->channel_params, sizeof(channel_params));
@@ -1327,8 +1361,6 @@ static int mlp_encode_frame(AVCodecConte
total_length = buf - buf0;
- determine_filters(ctx, restart_frame);
-
buf = write_substrs(ctx, buf, buf_size, restart_frame, decoding_params,
substream_data_len, channel_params);
More information about the FFmpeg-soc
mailing list