forked from Mirrors/freeswitch
wip
git-svn-id: http://svn.freeswitch.org/svn/freeswitch/trunk@2448 d0543943-73ff-0310-b7d9-9358b9ac24b2
This commit is contained in:
parent
ebfa5d5733
commit
7de2d07626
@ -31,6 +31,7 @@
|
|||||||
*/
|
*/
|
||||||
#include "switch.h"
|
#include "switch.h"
|
||||||
#include "g72x.h"
|
#include "g72x.h"
|
||||||
|
#define BITS_IN_A_BYTE 8
|
||||||
|
|
||||||
static const char modname[] = "mod_g726";
|
static const char modname[] = "mod_g726";
|
||||||
|
|
||||||
@ -38,8 +39,14 @@ static const char modname[] = "mod_g726";
|
|||||||
typedef struct {
|
typedef struct {
|
||||||
g726_state context;
|
g726_state context;
|
||||||
uint8_t buf[5];
|
uint8_t buf[5];
|
||||||
|
uint8_t *ptr;
|
||||||
uint8_t bits_per_frame;
|
uint8_t bits_per_frame;
|
||||||
uint8_t bits;
|
uint8_t bits;
|
||||||
|
uint8_t bbits;
|
||||||
|
uint8_t d_bits;
|
||||||
|
uint8_t d_bbits;
|
||||||
|
uint8_t dcount;
|
||||||
|
uint8_t save;
|
||||||
} g726_handle_t;
|
} g726_handle_t;
|
||||||
|
|
||||||
static switch_status_t switch_g726_init(switch_codec_t *codec, switch_codec_flag_t flags,
|
static switch_status_t switch_g726_init(switch_codec_t *codec, switch_codec_flag_t flags,
|
||||||
@ -57,6 +64,7 @@ static switch_status_t switch_g726_init(switch_codec_t *codec, switch_codec_flag
|
|||||||
g726_init_state(&handle->context);
|
g726_init_state(&handle->context);
|
||||||
codec->private_info = handle;
|
codec->private_info = handle;
|
||||||
handle->bits_per_frame = codec->implementation->bits_per_second / (codec->implementation->samples_per_second);
|
handle->bits_per_frame = codec->implementation->bits_per_second / (codec->implementation->samples_per_second);
|
||||||
|
handle->ptr = handle->buf;
|
||||||
return SWITCH_STATUS_SUCCESS;
|
return SWITCH_STATUS_SUCCESS;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -117,19 +125,49 @@ static switch_status_t switch_g726_encode(switch_codec_t *codec,
|
|||||||
if (decoded_data_len % len == 0) {
|
if (decoded_data_len % len == 0) {
|
||||||
uint32_t new_len = 0;
|
uint32_t new_len = 0;
|
||||||
int16_t *ddp = decoded_data;
|
int16_t *ddp = decoded_data;
|
||||||
//int8_t *edp = encoded_data;
|
uint8_t *edp = encoded_data;
|
||||||
int x;
|
int x;
|
||||||
uint32_t loops = decoded_data_len / (sizeof(*ddp));
|
uint32_t loops = decoded_data_len / (sizeof(*ddp));
|
||||||
|
|
||||||
for (x = 0; x < loops && new_len < *encoded_data_len; x++) {
|
for (x = 0; x < loops && new_len < *encoded_data_len; x++) {
|
||||||
#if 0
|
int edata = encoder(*ddp, AUDIO_ENCODING_LINEAR, context);
|
||||||
if (handle->buf & 0x80) {
|
|
||||||
edp[new_len++] = ((handle->buf & 0xf) << handle->bits_per_frame) | encoder(*ddp, AUDIO_ENCODING_LINEAR, context);
|
if (!handle->bbits) {
|
||||||
handle->buf = 0;
|
*handle->ptr = edata;
|
||||||
|
} else if ((handle->bbits + handle->bits_per_frame) <= BITS_IN_A_BYTE) {
|
||||||
|
*handle->ptr <<= handle->bits_per_frame;
|
||||||
|
*handle->ptr |= edata;
|
||||||
} else {
|
} else {
|
||||||
handle->buf = 0x80 | encoder(*ddp, AUDIO_ENCODING_LINEAR, context);
|
int remain, next, rdata, ndata;
|
||||||
|
|
||||||
|
remain = BITS_IN_A_BYTE - handle->bits_per_frame;
|
||||||
|
next = handle->bits_per_frame - remain;
|
||||||
|
rdata = edata;
|
||||||
|
ndata = edata;
|
||||||
|
|
||||||
|
rdata >>= remain;
|
||||||
|
*handle->ptr <<= remain;
|
||||||
|
*handle->ptr |= rdata;
|
||||||
|
|
||||||
|
handle->ptr++;
|
||||||
|
|
||||||
|
ndata &= (1 << next) - 1;
|
||||||
|
*handle->ptr = ndata;
|
||||||
|
|
||||||
|
handle->bbits = 0;
|
||||||
|
}
|
||||||
|
handle->bits += handle->bits_per_frame;
|
||||||
|
handle->bbits += handle->bits_per_frame;
|
||||||
|
|
||||||
|
if ((handle->bits % BITS_IN_A_BYTE) == 0) {
|
||||||
|
int bytes = handle->bits / BITS_IN_A_BYTE, count;
|
||||||
|
for(count = 0; count < bytes; count++) {
|
||||||
|
edp[new_len++] = handle->buf[count];
|
||||||
|
}
|
||||||
|
handle->bits = handle->bbits = 0;
|
||||||
|
handle->ptr = handle->buf;
|
||||||
|
memset(handle->buf, 0, sizeof(handle->buf));
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
ddp++;
|
ddp++;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -159,26 +197,28 @@ static switch_status_t switch_g726_decode(switch_codec_t *codec,
|
|||||||
unsigned int *flag)
|
unsigned int *flag)
|
||||||
{
|
{
|
||||||
|
|
||||||
g726_state *context = codec->private_info;
|
g726_handle_t *handle = codec->private_info;
|
||||||
uint32_t len = codec->implementation->bytes_per_frame;
|
g726_state *context = &handle->context;
|
||||||
|
//uint32_t len = codec->implementation->bytes_per_frame;
|
||||||
uint32_t elen = codec->implementation->encoded_bytes_per_frame;
|
uint32_t elen = codec->implementation->encoded_bytes_per_frame;
|
||||||
decoder_t decoder;
|
decoder_t decoder;
|
||||||
|
|
||||||
|
|
||||||
switch(elen) {
|
switch(elen) {
|
||||||
case 40:
|
case 100:
|
||||||
decoder = g726_40_decoder;
|
decoder = g726_40_decoder;
|
||||||
break;
|
break;
|
||||||
case 32:
|
case 80:
|
||||||
decoder = g726_32_decoder;
|
decoder = g726_32_decoder;
|
||||||
break;
|
break;
|
||||||
case 24:
|
case 60:
|
||||||
decoder = g726_24_decoder;
|
decoder = g726_24_decoder;
|
||||||
break;
|
break;
|
||||||
case 16:
|
case 40:
|
||||||
decoder = g726_16_decoder;
|
decoder = g726_16_decoder;
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "invalid Encoding Size!\n");
|
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "invalid Encoding Size %d!\n", elen);
|
||||||
return SWITCH_STATUS_FALSE;
|
return SWITCH_STATUS_FALSE;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@ -189,18 +229,54 @@ static switch_status_t switch_g726_decode(switch_codec_t *codec,
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
if (encoded_data_len % elen == 0) {
|
{
|
||||||
int loops = (int) encoded_data_len / elen;
|
|
||||||
char *edp = encoded_data;
|
int loops = ((int)encoded_data_len * BITS_IN_A_BYTE) / handle->bits_per_frame;
|
||||||
|
int8_t *edp = encoded_data;
|
||||||
int16_t *ddp = decoded_data;
|
int16_t *ddp = decoded_data;
|
||||||
int x;
|
int x;
|
||||||
uint32_t new_len = 0;
|
uint32_t new_len = 0;
|
||||||
|
|
||||||
for (x = 0; x < loops && new_len < *decoded_data_len; x++) {
|
for (x = 0; x < loops && new_len < *decoded_data_len; x++) {
|
||||||
*(int16_t *)ddp = decoder(*(int *)edp, AUDIO_ENCODING_LINEAR, context);
|
int in = 0;
|
||||||
ddp += len;
|
int bits = 0;
|
||||||
edp += elen;
|
int8_t over = 0;
|
||||||
new_len += len;
|
int8_t under = 0;
|
||||||
|
|
||||||
|
if (handle->save) {
|
||||||
|
in = handle->save;
|
||||||
|
handle->save = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
handle->d_bits += handle->bits_per_frame;
|
||||||
|
bits = handle->d_bbits + handle->bits_per_frame;
|
||||||
|
|
||||||
|
if (bits > BITS_IN_A_BYTE) {
|
||||||
|
int tmp;
|
||||||
|
over = bits - BITS_IN_A_BYTE;
|
||||||
|
under = handle->bits_per_frame - over;
|
||||||
|
handle->dcount = 0;
|
||||||
|
tmp = *edp >> (BITS_IN_A_BYTE - (handle->bits_per_frame * handle->dcount));
|
||||||
|
in = tmp >> over;
|
||||||
|
handle->save = tmp;
|
||||||
|
handle->save &= (1 << under) - 1;
|
||||||
|
edp++;
|
||||||
|
} else if (bits == BITS_IN_A_BYTE) {
|
||||||
|
handle->d_bbits = 0;
|
||||||
|
in = *edp;
|
||||||
|
edp++;
|
||||||
|
handle->dcount = 0;
|
||||||
|
} else {
|
||||||
|
in |= *edp >> (BITS_IN_A_BYTE - (handle->bits_per_frame * handle->dcount));
|
||||||
|
handle->d_bbits = bits;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
handle->dcount++;
|
||||||
|
|
||||||
|
*ddp++ = decoder(in, AUDIO_ENCODING_LINEAR, context);
|
||||||
|
new_len += 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (new_len <= *decoded_data_len) {
|
if (new_len <= *decoded_data_len) {
|
||||||
@ -209,6 +285,7 @@ static switch_status_t switch_g726_decode(switch_codec_t *codec,
|
|||||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "buffer overflow!!!\n");
|
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "buffer overflow!!!\n");
|
||||||
return SWITCH_STATUS_FALSE;
|
return SWITCH_STATUS_FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return SWITCH_STATUS_SUCCESS;
|
return SWITCH_STATUS_SUCCESS;
|
||||||
|
Loading…
Reference in New Issue
Block a user