Welcome to mirror list, hosted at ThFree Co, Russian Federation.

gitlab.xiph.org/xiph/opus.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
path: root/silk
diff options
context:
space:
mode:
authorJean-Marc Valin <jmvalin@amazon.com>2023-05-30 01:10:56 +0300
committerJean-Marc Valin <jmvalin@amazon.com>2023-06-16 20:02:19 +0300
commit9c137d493370cb195f0fb062f94b362c8bed481e (patch)
treeddbabc06b9d42cae27f186a786d386f5ca1d9948 /silk
parent4fbf6dcaf46bbc13ddd91a5762a486981fd0a14a (diff)
Add offset and quantization to DRED bitstream
Brings the DRED implementation in line with the -00 draft
Diffstat (limited to 'silk')
-rw-r--r--silk/dred_coding.c10
-rw-r--r--silk/dred_coding.h2
-rw-r--r--silk/dred_config.h2
-rw-r--r--silk/dred_decoder.c9
-rw-r--r--silk/dred_decoder.h1
-rw-r--r--silk/dred_encoder.c11
6 files changed, 32 insertions, 3 deletions
diff --git a/silk/dred_coding.c b/silk/dred_coding.c
index ff592e81..34829390 100644
--- a/silk/dred_coding.c
+++ b/silk/dred_coding.c
@@ -37,11 +37,21 @@
#include "celt/cwrs.h"
#include "celt/laplace.h"
#include "os_support.h"
+#include "dred_config.h"
#define LATENT_DIM 80
#define PVQ_DIM 24
#define PVQ_K 82
+int compute_quantizer(int q0, int dQ, int i) {
+ int quant;
+ static const int dQ_table[8] = {0, 2, 3, 4, 6, 8, 12, 16};
+ quant = 0;
+ quant = q0 + (dQ_table[dQ]*i + 8)/16;
+ return quant > 15 ? 15 : quant;
+ return (int) floor(0.5f + DRED_ENC_Q0 + 1.f * (DRED_ENC_Q1 - DRED_ENC_Q0) * i / (DRED_NUM_REDUNDANCY_FRAMES - 2));
+}
+
static void encode_pvq(const int *iy, int N, int K, ec_enc *enc) {
int fits;
celt_assert(N==24 || N==12 || N==6);
diff --git a/silk/dred_coding.h b/silk/dred_coding.h
index a36f93d9..662ba549 100644
--- a/silk/dred_coding.h
+++ b/silk/dred_coding.h
@@ -31,6 +31,8 @@
#include "opus_types.h"
#include "entcode.h"
+int compute_quantizer(int q0, int dQ, int i);
+
void dred_encode_state(ec_enc *enc, float *x);
void dred_encode_latents(ec_enc *enc, const float *x, const opus_uint16 *scale, const opus_uint16 *dzone, const opus_uint16 *r, const opus_uint16 *p0);
diff --git a/silk/dred_config.h b/silk/dred_config.h
index f396219f..ff9903ba 100644
--- a/silk/dred_config.h
+++ b/silk/dred_config.h
@@ -28,7 +28,7 @@
#ifndef DRED_CONFIG_H
#define DRED_CONFIG_H
-#define DRED_VERSION 0
+#define DRED_VERSION 1
#define DRED_MIN_BYTES 16
/* these are inpart duplicates to the values defined in dred_rdovae_constants.h */
diff --git a/silk/dred_decoder.c b/silk/dred_decoder.c
index 20eb98ec..dea53251 100644
--- a/silk/dred_decoder.c
+++ b/silk/dred_decoder.c
@@ -48,6 +48,8 @@ int dred_ec_decode(OpusDRED *dec, const opus_uint8 *bytes, int num_bytes, int mi
int q_level;
int i;
int offset;
+ int q0;
+ int dQ;
/* since features are decoded in quadruples, it makes no sense to go with an uneven number of redundancy frames */
@@ -55,6 +57,11 @@ int dred_ec_decode(OpusDRED *dec, const opus_uint8 *bytes, int num_bytes, int mi
/* decode initial state and initialize RDOVAE decoder */
ec_dec_init(&ec, (unsigned char*)bytes, num_bytes);
+ dec->dred_offset = ec_dec_uint(&ec, 32);
+ q0 = ec_dec_uint(&ec, 16);
+ dQ = ec_dec_uint(&ec, 8);
+ /*printf("%d %d %d\n", dred_offset, q0, dQ);*/
+
dred_decode_state(&ec, dec->state);
/* decode newest to oldest and store oldest to newest */
@@ -63,7 +70,7 @@ int dred_ec_decode(OpusDRED *dec, const opus_uint8 *bytes, int num_bytes, int mi
/* FIXME: Figure out how to avoid missing a last frame that would take up < 8 bits. */
if (8*num_bytes - ec_tell(&ec) <= 7)
break;
- q_level = (int) floor(.5 + DRED_ENC_Q0 + 1.f * (DRED_ENC_Q1 - DRED_ENC_Q0) * i / (DRED_NUM_REDUNDANCY_FRAMES - 2));
+ q_level = compute_quantizer(q0, dQ, i/2);
offset = q_level * DRED_LATENT_DIM;
dred_decode_latents(
&ec,
diff --git a/silk/dred_decoder.h b/silk/dred_decoder.h
index e2640964..c7355ed1 100644
--- a/silk/dred_decoder.h
+++ b/silk/dred_decoder.h
@@ -39,6 +39,7 @@ struct OpusDRED {
float latents[(DRED_NUM_REDUNDANCY_FRAMES/2)*DRED_LATENT_DIM];
int nb_latents;
int process_stage;
+ int dred_offset;
};
diff --git a/silk/dred_encoder.c b/silk/dred_encoder.c
index ffc24b7c..02f1eb9f 100644
--- a/silk/dred_encoder.c
+++ b/silk/dred_encoder.c
@@ -85,9 +85,18 @@ int dred_encode_silk_frame(DREDEnc *enc, unsigned char *buf, int max_chunks, int
int i;
int offset;
int ec_buffer_fill;
+ int dred_offset;
+ int q0;
+ int dQ;
/* entropy coding of state and latents */
ec_enc_init(&ec_encoder, buf, max_bytes);
+ dred_offset = 8; /* 20 ms */
+ q0 = DRED_ENC_Q0;
+ dQ = 3;
+ ec_enc_uint(&ec_encoder, dred_offset, 32);
+ ec_enc_uint(&ec_encoder, q0, 16);
+ ec_enc_uint(&ec_encoder, dQ, 8);
dred_encode_state(&ec_encoder, enc->state_buffer);
for (i = 0; i < IMIN(2*max_chunks, enc->latents_buffer_fill-1); i += 2)
@@ -95,7 +104,7 @@ int dred_encode_silk_frame(DREDEnc *enc, unsigned char *buf, int max_chunks, int
ec_enc ec_bak;
ec_bak = ec_encoder;
- q_level = (int) floor(0.5f + DRED_ENC_Q0 + 1.f * (DRED_ENC_Q1 - DRED_ENC_Q0) * i / (DRED_NUM_REDUNDANCY_FRAMES - 2));
+ q_level = compute_quantizer(q0, dQ, i/2);
offset = q_level * DRED_LATENT_DIM;
dred_encode_latents(