|
|
|
@ -786,6 +786,93 @@ static void reset_codec(WmallDecodeCtx *s) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
static void mclms_update(WmallDecodeCtx *s, int icoef) |
|
|
|
|
{ |
|
|
|
|
int i, j, ich; |
|
|
|
|
int16_t pred_error; |
|
|
|
|
int order = s->mclms_order; |
|
|
|
|
int num_channels = s->num_channels; |
|
|
|
|
int16_t range = 1 << (s->bits_per_sample - 1); |
|
|
|
|
int bps = s->bits_per_sample > 16 ? 4 : 2; // bytes per sample
|
|
|
|
|
|
|
|
|
|
for (ich = 0; ich < num_channels; ich++) { |
|
|
|
|
pred_error = s->channel_coeffs[ich][icoef] - |
|
|
|
|
s->channel_residues[ich][icoef]; |
|
|
|
|
if (pred_error > 0) { |
|
|
|
|
for (i = 0; i < order * num_channels; i++) |
|
|
|
|
s->mclms_coeffs[i + ich * order * num_channels] += |
|
|
|
|
s->mclms_updates[s->mclms_recent + i]; |
|
|
|
|
for (j = 0; j < i; j++) { |
|
|
|
|
if (s->channel_coeffs[ich][icoef] > 0) |
|
|
|
|
s->mclms_coeffs_cur[ich * num_channels + j] += 1; |
|
|
|
|
else if (s->channel_coeffs[ich][icoef] < 0) |
|
|
|
|
s->mclms_coeffs_cur[ich * num_channels + j] -= 1; |
|
|
|
|
} |
|
|
|
|
} else if (pred_error < 0) { |
|
|
|
|
for (i = 0; i < order * num_channels; i++) |
|
|
|
|
s->mclms_coeffs[i + ich * order * num_channels] -= |
|
|
|
|
s->mclms_updates[s->mclms_recent + i]; |
|
|
|
|
for (j = 0; j < i; j++) { |
|
|
|
|
if (s->channel_coeffs[ich][icoef] > 0) |
|
|
|
|
s->mclms_coeffs_cur[ich * num_channels + j] -= 1; |
|
|
|
|
else if (s->channel_coeffs[ich][icoef] < 0) |
|
|
|
|
s->mclms_coeffs_cur[ich * num_channels + j] += 1; |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
for (ich = num_channels - 1; ich >= 0; ich--) { |
|
|
|
|
s->mclms_recent--; |
|
|
|
|
if (s->channel_coeffs[ich][icoef] > range - 1) |
|
|
|
|
s->mclms_prevvalues[s->mclms_recent] = range - 1; |
|
|
|
|
else if (s->channel_coeffs[ich][icoef] <= -range) |
|
|
|
|
s->mclms_prevvalues[s->mclms_recent] = -range; |
|
|
|
|
|
|
|
|
|
s->mclms_updates[s->mclms_recent] = |
|
|
|
|
av_clip(-1, s->channel_coeffs[ich][icoef], 1); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
if (s->mclms_recent == 0) { |
|
|
|
|
memcpy(s->mclms_prevvalues[order * num_channels], |
|
|
|
|
s->mclms_prevvalues, |
|
|
|
|
bps * order * num_channels); |
|
|
|
|
memcpy(s->mclms_updates[order * num_channels], |
|
|
|
|
s->mclms_updates, |
|
|
|
|
bps * order * num_channels); |
|
|
|
|
s->mclms_recent = num_channels * order; |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
static void mclms_predict(WmallDecodeCtx *s, int icoef) |
|
|
|
|
{ |
|
|
|
|
int ich, i; |
|
|
|
|
int16_t pred; |
|
|
|
|
int order = s->mclms_order; |
|
|
|
|
int num_channels = s->num_channels; |
|
|
|
|
|
|
|
|
|
for (ich = 0; ich < num_channels; ich++) { |
|
|
|
|
if (!s->is_channel_coded[ich]) |
|
|
|
|
continue; |
|
|
|
|
pred = 0; |
|
|
|
|
for (i = 0; i < order * num_channels; i++) |
|
|
|
|
pred += s->mclms_prevvalues[i] * |
|
|
|
|
s->mclms_coeffs[i + order * num_channels * ich]; |
|
|
|
|
for (i = 0; i < ich; i++) |
|
|
|
|
pred += s->channel_coeffs[ich][icoef] * |
|
|
|
|
s->mclms_coeffs_cur[i + order * num_channels * ich]; |
|
|
|
|
s->channel_coeffs[ich][icoef] = |
|
|
|
|
s->channel_residues[ich][icoef] + pred; |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
static void revert_mclms(WmallDecodeCtx *s, int tile_size) |
|
|
|
|
{ |
|
|
|
|
int icoef; |
|
|
|
|
for (icoef = 0; icoef < tile_size; icoef++) { |
|
|
|
|
mclms_predict(s, icoef); |
|
|
|
|
mclms_update(s, icoef); |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
static int lms_predict(WmallDecodeCtx *s, int ich, int ilms) |
|
|
|
|
{ |
|
|
|
|
int16_t pred = 0, icoef; |
|
|
|
|