Skip to content

Commit eb00f20

Browse files
committed
Fixup to A-law encode and decode to match reference
Signed-off-by: Seppo Ingalsuo <seppo.ingalsuo@linux.intel.com>
1 parent d441803 commit eb00f20

1 file changed

Lines changed: 15 additions & 9 deletions

File tree

src/math/a_law.c

Lines changed: 15 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -8,9 +8,13 @@
88
#include <sof/math/a_law.h>
99
#include <stdint.h>
1010

11+
/* TODO: Some found encoders invert the sign bit, check this. */
12+
#define SOFM_ALAW_SIGN_BIT_POS 0x80
13+
#define SOFM_ALAW_SIGN_BIT_NEG 0x00
14+
#define SOFM_ALAW_SIGN_BIT 0x80
15+
1116
#define SOFM_ALAW_MAX 4095
1217
#define SOFM_ALAW_TOGGLE_EVEN_BITS 0x55
13-
#define SOFM_ALAW_SIGN_BIT 0x80
1418
#define SOFM_ALAW_MANTISSA_MASK 0x0f
1519
#define SOFM_ALAW_MANTISSA_BITS 4
1620
#define SOFM_ALAW_SHIFT_MASK 0x07
@@ -82,20 +86,22 @@ static uint8_t alaw_encode_shifts[128] = {
8286
*/
8387
uint8_t sofm_a_law_encode(int16_t sample)
8488
{
85-
int sign = 0;
89+
int32_t tmp;
90+
int sign = SOFM_ALAW_SIGN_BIT_POS;
8691
int shift = 0;
8792
int low_bits;
8893
uint8_t byte;
8994

90-
/* Round 16 bit Q1.15 to 13 bit Q1.12 */
91-
sample = ((sample >> 2) + 1) >> 1;
92-
9395
/* Convert to sign and magnitude */
94-
if (sample < 0) {
95-
sign = SOFM_ALAW_SIGN_BIT;
96-
sample = -sample;
96+
tmp = sample;
97+
if (tmp < 0) {
98+
sign = SOFM_ALAW_SIGN_BIT_NEG;
99+
tmp = -tmp;
97100
}
98101

102+
/* Convert to 13 bits with shift. Note: There is no rounding in references. */
103+
sample = (int16_t)(tmp >> 3);
104+
99105
if (sample > SOFM_ALAW_MAX)
100106
sample = SOFM_ALAW_MAX;
101107

@@ -138,7 +144,7 @@ int16_t sofm_a_law_decode(int8_t byte)
138144
else
139145
value = (low_bits << 1) | 1;
140146

141-
if (sign)
147+
if (!sign)
142148
value = -value;
143149

144150
/* Shift 13 bit Q1.12 to 16 bit Q1.15 */

0 commit comments

Comments
 (0)