[FFmpeg-soc] [soc] G.723.1 Decoder 2420742873e9364b717e9cf298a7fb149c512b92
naufal11 at gmail.com
naufal11 at gmail.com
Thu Jul 8 17:06:40 CEST 2010
- Log -----------------------------------------------------------------
commit 2420742873e9364b717e9cf298a7fb149c512b92
Author: Naufal <naufal11 at gmail.com>
Date: Thu Jul 8 20:35:26 2010 +0530
Add error handling code
diff --git a/libavcodec/g723_1.c b/libavcodec/g723_1.c
index df861f4..40836c3 100755
--- a/libavcodec/g723_1.c
+++ b/libavcodec/g723_1.c
@@ -15,7 +15,9 @@ typedef struct g723_1_context {
FrameType past_frame_type;
Rate cur_rate;
+ int16_t random_seed;
int16_t interp_index;
+ int16_t interp_gain;
int16_t sid_gain;
int16_t cur_gain;
} G723_1_Context;
@@ -153,6 +155,12 @@ static inline int16_t abs_16(int16_t x)
return (v & INT16_MIN) ? INT16_MAX : v;
}
+static inline int16_t prand(int16_t *rseed)
+{
+ *rseed = *rseed * 521 + 259;
+ return *rseed;
+}
+
static inline int dot_product(const int16_t *v1, const int16_t *v2, int length)
{
int i, sum = 0;
@@ -647,6 +655,34 @@ static int16_t comp_interp_index(int16_t *buf, int16_t pitch_lag,
return 0;
}
+/*
+ * Peform residual interpolation based on frame classification.
+ *
+ * @param buf decoded excitation vector
+ * @prarm out output vector
+ * @param lag decoded pitch lag
+ * @param gain interpolated gain
+ * @param rseed seed for random number generator
+ */
+static void residual_interp(int16_t *buf, int16_t *out, int16_t lag,
+ int16_t gain, int16_t *rseed)
+{
+ int i;
+ if (lag) { // Voiced
+ int16_t *vector_ptr = buf + PITCH_MAX;
+ // Attenuate
+ for (i = 0; i < lag; i++)
+ vector_ptr[i - lag] = vector_ptr[i - lag] * 0x6000 >> 15;
+ for (i = 0; i < FRAME_LEN; i++)
+ vector_ptr[i] = vector_ptr[i - lag];
+ memcpy(out, vector_ptr, FRAME_LEN * sizeof(int16_t));
+ } else { // Unvoiced
+ for (i = 0; i < FRAME_LEN; i++)
+ out[i] = gain * prand(rseed) >> 15;
+ memset(buf, 0, (FRAME_LEN + PITCH_MAX) * sizeof(int16_t));
+ }
+}
+
static int g723_1_decode_frame(AVCodecContext *avctx, void *data,
int *data_size, AVPacket *avpkt)
{
@@ -661,7 +697,6 @@ static int g723_1_decode_frame(AVCodecContext *avctx, void *data,
int16_t excitation[FRAME_LEN + PITCH_MAX];
int16_t acb_vector[SUBFRAME_LEN];
int16_t *vector_ptr;
- int16_t interp_gain;
int bad_frame = 0, erased_frames = 0, i, j;
if (!buf_size || buf_size < frame_size[buf[0] & 3]) {
@@ -689,7 +724,7 @@ static int g723_1_decode_frame(AVCodecContext *avctx, void *data,
vector_ptr = excitation + PITCH_MAX;
if (!erased_frames) {
// Update interpolation gain memory
- interp_gain = fixed_cb_gain[(p->subframe[2].amp_index +
+ p->interp_gain = fixed_cb_gain[(p->subframe[2].amp_index +
p->subframe[3].amp_index) >> 1];
for (i = 0; i < SUBFRAMES; i++) {
gen_fcb_excitation(vector_ptr, p->subframe[i], p->cur_rate,
@@ -726,6 +761,17 @@ static int g723_1_decode_frame(AVCodecContext *avctx, void *data,
vector_ptr + i + ppf[j].index,
ppf[j].sc_gain, ppf[j].opt_gain,
1 << 14, 15, SUBFRAME_LEN);
+ } else {
+ p->interp_gain = (p->interp_gain * 3 + 2) >> 2;
+ if (erased_frames == 3) {
+ // Mute output
+ memset(excitation, 0, (FRAME_LEN + PITCH_MAX) * sizeof(int16_t));
+ memset(out, 0, FRAME_LEN * sizeof(int16_t));
+ } else {
+ // Regenerate frame
+ residual_interp(excitation, out, p->interp_index,
+ p->interp_gain, &p->random_seed);
+ }
}
}
commit 7662f5e1379373f827dcf623f2d39a1e53d25d99
Author: Naufal <naufal11 at gmail.com>
Date: Thu Jul 8 15:54:04 2010 +0530
Compute residual interpolation index
diff --git a/libavcodec/g723_1.c b/libavcodec/g723_1.c
index 435d668..df861f4 100755
--- a/libavcodec/g723_1.c
+++ b/libavcodec/g723_1.c
@@ -14,6 +14,10 @@ typedef struct g723_1_context {
FrameType cur_frame_type;
FrameType past_frame_type;
Rate cur_rate;
+
+ int16_t interp_index;
+ int16_t sid_gain;
+ int16_t cur_gain;
} G723_1_Context;
static av_cold int g723_1_decode_init(AVCodecContext *avctx)
@@ -595,6 +599,54 @@ static void comp_ppf_coeff(int16_t *buf, int16_t pitch_lag, PPFParam *ppf,
}
}
+/*
+ * Classify frames as voiced/unvoiced.
+ *
+ * @param buf decoded excitation vector
+ * @param exc_eng excitation energy estimation
+ * @param scale scaling factor of exc_eng
+ *
+ * @return residual interpolation index if voiced, 0 otherwise
+ */
+static int16_t comp_interp_index(int16_t *buf, int16_t pitch_lag,
+ int16_t *exc_eng, int16_t *scale)
+{
+ int16_t index;
+ int16_t *vector_ptr;
+ int ccr, tgt_eng, best_eng;
+ int temp;
+
+ *scale = scale_vector(buf, FRAME_LEN + PITCH_MAX);
+
+ pitch_lag = FFMIN(PITCH_MAX - 3, pitch_lag);
+ vector_ptr = buf + PITCH_MAX + 2 * SUBFRAME_LEN;
+ index = pitch_lag;
+
+ // Compute maximum backward cross-correlation
+ ccr = 0;
+ index = get_ppf_lag(vector_ptr, &ccr, pitch_lag, SUBFRAME_LEN * 2, -1);
+ ccr = av_clipl_int32((int64_t)ccr + (1 << 15)) >> 16;
+
+ // Compute target energy
+ tgt_eng = dot_product(vector_ptr, vector_ptr, SUBFRAME_LEN * 2);
+ *exc_eng = av_clipl_int32(tgt_eng + (1 << 15)) >> 16;
+
+ if (ccr <= 0)
+ return 0;
+
+ // Compute best energy
+ best_eng = dot_product(vector_ptr - index, vector_ptr - index,
+ SUBFRAME_LEN * 2);
+ best_eng = av_clipl_int32((int64_t)best_eng + (1 << 15)) >> 16;
+
+ temp = best_eng * tgt_eng >> 3;
+
+ if (temp < ccr * ccr)
+ return index;
+ else
+ return 0;
+}
+
static int g723_1_decode_frame(AVCodecContext *avctx, void *data,
int *data_size, AVPacket *avpkt)
{
@@ -655,6 +707,9 @@ static int g723_1_decode_frame(AVCodecContext *avctx, void *data,
// Save the excitation
memcpy(out, excitation + PITCH_MAX, FRAME_LEN);
+ p->interp_index = comp_interp_index(excitation, p->pitch_lag[1],
+ &p->sid_gain, &p->cur_gain);
+
vector_ptr = excitation + PITCH_MAX;
for (i = 0, j = 0; i < FRAME_LEN; i += SUBFRAME_LEN, j++)
-----------------------------------------------------------------------
Summary of changes:
libavcodec/g723_1.c | 105 ++++++++++++++++++++++++++++++++++++++++++++++++++-
1 files changed, 103 insertions(+), 2 deletions(-)
--
http://github.com/naufal/ffmpeg-soc
More information about the FFmpeg-soc
mailing list