Thu Sep 7 01:03:26 2017

Asterisk developer's documentation


codec_adpcm.c File Reference

codec_adpcm.c - translate between signed linear and Dialogic ADPCM More...

#include "asterisk.h"
#include "asterisk/lock.h"
#include "asterisk/linkedlists.h"
#include "asterisk/module.h"
#include "asterisk/config.h"
#include "asterisk/translate.h"
#include "asterisk/utils.h"
#include "asterisk/slin.h"
#include "ex_adpcm.h"

Go to the source code of this file.

Data Structures

struct  adpcm_decoder_pvt
 Workspace for translating ADPCM signals to signed linear. More...
struct  adpcm_encoder_pvt
 Workspace for translating signed linear signals to ADPCM. More...
struct  adpcm_state

Defines

#define BUFFER_SAMPLES   8096

Functions

static int adpcm (short csig, struct adpcm_state *state)
static int adpcmtolin_framein (struct ast_trans_pvt *pvt, struct ast_frame *f)
 decode 4-bit adpcm frame data and store in output buffer
 AST_MODULE_INFO (ASTERISK_GPL_KEY, AST_MODFLAG_DEFAULT,"Adaptive Differential PCM Coder/Decoder",.load=load_module,.unload=unload_module,.reload=reload,)
static short decode (int encoded, struct adpcm_state *state)
static int lintoadpcm_framein (struct ast_trans_pvt *pvt, struct ast_frame *f)
 fill input buffer with 16-bit signed linear PCM values.
static struct ast_framelintoadpcm_frameout (struct ast_trans_pvt *pvt)
 convert inbuf and store into frame
static int load_module (void)
static int reload (void)
 standard module glue
static int unload_module (void)

Variables

static struct ast_translator adpcmtolin
static int indsft [8] = { -1, -1, -1, -1, 2, 4, 6, 8 }
static struct ast_translator lintoadpcm
static int stpsz [49]

Detailed Description

codec_adpcm.c - translate between signed linear and Dialogic ADPCM

Definition in file codec_adpcm.c.


Define Documentation

#define BUFFER_SAMPLES   8096

Definition at line 48 of file codec_adpcm.c.


Function Documentation

static int adpcm ( short  csig,
struct adpcm_state state 
) [inline, static]

Definition at line 166 of file codec_adpcm.c.

References decode(), adpcm_state::signal, and adpcm_state::ssindex.

Referenced by lintoadpcm_frameout().

00167 {
00168    int diff;
00169    int step;
00170    int encoded;
00171 
00172    /* 
00173     * Clip csig if too large or too small
00174     */
00175    csig >>= 4;
00176 
00177    step = stpsz[state->ssindex];
00178    diff = csig - state->signal;
00179 
00180 #ifdef NOT_BLI
00181    if (diff < 0) {
00182       encoded = (-diff << 2) / step;
00183       if (encoded > 7)
00184          encoded = 7;
00185       encoded |= 0x08;
00186    } else {
00187       encoded = (diff << 2) / step;
00188       if (encoded > 7)
00189          encoded = 7;
00190    }
00191 #else /* BLI code */
00192    if (diff < 0) {
00193       encoded = 8;
00194       diff = -diff;
00195    } else
00196       encoded = 0;
00197    if (diff >= step) {
00198       encoded |= 4;
00199       diff -= step;
00200    }
00201    step >>= 1;
00202    if (diff >= step) {
00203       encoded |= 2;
00204       diff -= step;
00205    }
00206    step >>= 1;
00207    if (diff >= step)
00208       encoded |= 1;
00209 #endif /* NOT_BLI */
00210 
00211    /* feedback to state */
00212    decode(encoded, state);
00213    
00214    return encoded;
00215 }

static int adpcmtolin_framein ( struct ast_trans_pvt pvt,
struct ast_frame f 
) [static]

decode 4-bit adpcm frame data and store in output buffer

Definition at line 231 of file codec_adpcm.c.

References ast_frame::data, ast_trans_pvt::datalen, ast_frame::datalen, decode(), ast_trans_pvt::i16, ast_trans_pvt::outbuf, ast_frame::ptr, ast_trans_pvt::pvt, ast_frame::samples, ast_trans_pvt::samples, and adpcm_decoder_pvt::state.

00232 {
00233    struct adpcm_decoder_pvt *tmp = pvt->pvt;
00234    int x = f->datalen;
00235    unsigned char *src = f->data.ptr;
00236    int16_t *dst = pvt->outbuf.i16 + pvt->samples;
00237 
00238    while (x--) {
00239       *dst++ = decode((*src >> 4) & 0xf, &tmp->state);
00240       *dst++ = decode(*src++ & 0x0f, &tmp->state);
00241    }
00242    pvt->samples += f->samples;
00243    pvt->datalen += 2*f->samples;
00244    return 0;
00245 }

AST_MODULE_INFO ( ASTERISK_GPL_KEY  ,
AST_MODFLAG_DEFAULT  ,
"Adaptive Differential PCM Coder/Decoder"  ,
load = load_module,
unload = unload_module,
reload = reload 
)
static short decode ( int  encoded,
struct adpcm_state state 
) [inline, static]

Definition at line 93 of file codec_adpcm.c.

References adpcm_state::next_flag, adpcm_state::signal, adpcm_state::ssindex, and adpcm_state::zero_count.

Referenced by adpcm(), and adpcmtolin_framein().

00094 {
00095    int diff;
00096    int step;
00097    int sign;
00098 
00099    step = stpsz[state->ssindex];
00100 
00101    sign = encoded & 0x08;
00102    encoded &= 0x07;
00103 #ifdef NOT_BLI
00104    diff = (((encoded << 1) + 1) * step) >> 3;
00105 #else /* BLI code */
00106    diff = step >> 3;
00107    if (encoded & 4)
00108       diff += step;
00109    if (encoded & 2)
00110       diff += step >> 1;
00111    if (encoded & 1)
00112       diff += step >> 2;
00113    if ((encoded >> 1) & step & 0x1)
00114       diff++;
00115 #endif
00116    if (sign)
00117       diff = -diff;
00118 
00119    if (state->next_flag & 0x1)
00120       state->signal -= 8;
00121    else if (state->next_flag & 0x2)
00122       state->signal += 8;
00123 
00124    state->signal += diff;
00125 
00126    if (state->signal > 2047)
00127       state->signal = 2047;
00128    else if (state->signal < -2047)
00129       state->signal = -2047;
00130 
00131    state->next_flag = 0;
00132 
00133 #ifdef AUTO_RETURN
00134    if (encoded)
00135       state->zero_count = 0;
00136    else if (++(state->zero_count) == 24) {
00137       state->zero_count = 0;
00138       if (state->signal > 0)
00139          state->next_flag = 0x1;
00140       else if (state->signal < 0)
00141          state->next_flag = 0x2;
00142    }
00143 #endif
00144 
00145    state->ssindex += indsft[encoded];
00146    if (state->ssindex < 0)
00147       state->ssindex = 0;
00148    else if (state->ssindex > 48)
00149       state->ssindex = 48;
00150 
00151    return state->signal << 4;
00152 }

static int lintoadpcm_framein ( struct ast_trans_pvt pvt,
struct ast_frame f 
) [static]

fill input buffer with 16-bit signed linear PCM values.

Definition at line 248 of file codec_adpcm.c.

References ast_frame::data, ast_frame::datalen, adpcm_encoder_pvt::inbuf, ast_frame::ptr, ast_trans_pvt::pvt, ast_frame::samples, and ast_trans_pvt::samples.

00249 {
00250    struct adpcm_encoder_pvt *tmp = pvt->pvt;
00251 
00252    memcpy(&tmp->inbuf[pvt->samples], f->data.ptr, f->datalen);
00253    pvt->samples += f->samples;
00254    return 0;
00255 }

static struct ast_frame* lintoadpcm_frameout ( struct ast_trans_pvt pvt  )  [static, read]

convert inbuf and store into frame

Definition at line 258 of file codec_adpcm.c.

References adpcm(), ast_trans_frameout(), ast_trans_pvt::c, f, adpcm_encoder_pvt::inbuf, ast_trans_pvt::outbuf, ast_trans_pvt::pvt, ast_trans_pvt::samples, ast_frame::samples, and adpcm_encoder_pvt::state.

00259 {
00260    struct adpcm_encoder_pvt *tmp = pvt->pvt;
00261    struct ast_frame *f;
00262    int i;
00263    int samples = pvt->samples;   /* save original number */
00264   
00265    if (samples < 2)
00266       return NULL;
00267 
00268    pvt->samples &= ~1; /* atomic size is 2 samples */
00269 
00270    for (i = 0; i < pvt->samples; i += 2) {
00271       pvt->outbuf.c[i/2] =
00272          (adpcm(tmp->inbuf[i  ], &tmp->state) << 4) |
00273          (adpcm(tmp->inbuf[i+1], &tmp->state)     );
00274    };
00275 
00276    f = ast_trans_frameout(pvt, pvt->samples/2, 0);
00277 
00278    /*
00279     * If there is a left over sample, move it to the beginning
00280     * of the input buffer.
00281     */
00282 
00283    if (samples & 1) {   /* move the leftover sample at beginning */
00284       tmp->inbuf[0] = tmp->inbuf[samples - 1];
00285       pvt->samples = 1;
00286    }
00287    return f;
00288 }

static int load_module ( void   )  [static]

Definition at line 330 of file codec_adpcm.c.

References AST_MODULE_LOAD_FAILURE, AST_MODULE_LOAD_SUCCESS, ast_register_translator, and ast_unregister_translator().

00331 {
00332    int res;
00333 
00334    res = ast_register_translator(&adpcmtolin);
00335    if (!res)
00336       res = ast_register_translator(&lintoadpcm);
00337    else
00338       ast_unregister_translator(&adpcmtolin);
00339    if (res)
00340       return AST_MODULE_LOAD_FAILURE;
00341    return AST_MODULE_LOAD_SUCCESS;
00342 }

static int reload ( void   )  [static]

standard module glue

Definition at line 315 of file codec_adpcm.c.

References AST_MODULE_LOAD_SUCCESS.

00316 {
00317    return AST_MODULE_LOAD_SUCCESS;
00318 }

static int unload_module ( void   )  [static]

Definition at line 320 of file codec_adpcm.c.

References ast_unregister_translator().

00321 {
00322    int res;
00323 
00324    res = ast_unregister_translator(&lintoadpcm);
00325    res |= ast_unregister_translator(&adpcmtolin);
00326 
00327    return res;
00328 }


Variable Documentation

struct ast_translator adpcmtolin [static]

Definition at line 291 of file codec_adpcm.c.

int indsft[8] = { -1, -1, -1, -1, 2, 4, 6, 8 } [static]

Definition at line 58 of file codec_adpcm.c.

struct ast_translator lintoadpcm [static]

Definition at line 302 of file codec_adpcm.c.

int stpsz[49] [static]

Definition at line 64 of file codec_adpcm.c.


Generated on 7 Sep 2017 for Asterisk - The Open Source Telephony Project by  doxygen 1.6.1