📄 nb_celp.c
字号:
pit_max = st->max_pitch;
} else {
pit_min = pit_max = ol_pitch;
}
} else {
pit_min = st->min_pitch;
pit_max = st->max_pitch;
}
/* Pitch synthesis */
SUBMODE(ltp_unquant)(exc, pit_min, pit_max, ol_pitch_coef, SUBMODE(ltp_params),
st->subframeSize, &pitch, &pitch_gain[0], bits, stack, st->count_lost, offset, st->last_pitch_gain);
/* If we had lost frames, check energy of last received frame */
if (st->count_lost && ol_gain < st->last_ol_gain)
{
float fact = ol_gain/(st->last_ol_gain+1);
for (i=0;i<st->subframeSize;i++)
exc[i]*=fact;
}
tmp = fabs(pitch_gain[0]+pitch_gain[1]+pitch_gain[2]);
tmp = fabs(pitch_gain[1]);
if (pitch_gain[0]>0)
tmp += pitch_gain[0];
else
tmp -= .5*pitch_gain[0];
if (pitch_gain[2]>0)
tmp += pitch_gain[2];
else
tmp -= .5*pitch_gain[0];
pitch_average += tmp;
if (tmp>best_pitch_gain)
{
best_pitch = pitch;
best_pitch_gain = tmp;
/* best_pitch_gain = tmp*.9;
if (best_pitch_gain>.85)
best_pitch_gain=.85;*/
}
} else {
speex_error("No pitch prediction, what's wrong");
}
/* Unquantize the innovation */
{
int q_energy;
float ener;
float *innov;
innov = st->innov+sub*st->subframeSize;
for (i=0;i<st->subframeSize;i++)
innov[i]=0;
/* Decode sub-frame gain correction */
if (SUBMODE(have_subframe_gain)==3)
{
q_energy = speex_bits_unpack_unsigned(bits, 3);
ener = ol_gain*exp(exc_gain_quant_scal3[q_energy]);
} else if (SUBMODE(have_subframe_gain)==1)
{
q_energy = speex_bits_unpack_unsigned(bits, 1);
ener = ol_gain*exp(exc_gain_quant_scal1[q_energy]);
} else {
ener = ol_gain;
}
if (SUBMODE(innovation_unquant))
{
/*Fixed codebook contribution*/
SUBMODE(innovation_unquant)(innov, SUBMODE(innovation_params), st->subframeSize, bits, stack);
} else {
speex_error("No fixed codebook");
}
/* De-normalize innovation and update excitation */
for (i=0;i<st->subframeSize;i++)
innov[i]*=ener;
/*Vocoder mode*/
if (st->submodeID==1)
{
float g=ol_pitch_coef;
for (i=0;i<st->subframeSize;i++)
exc[i]=0;
while (st->voc_offset<st->subframeSize)
{
if (st->voc_offset>=0)
exc[st->voc_offset]=sqrt(1.0*ol_pitch);
st->voc_offset+=ol_pitch;
}
st->voc_offset -= st->subframeSize;
g=.5+2*(g-.6);
if (g<0)
g=0;
if (g>1)
g=1;
for (i=0;i<st->subframeSize;i++)
{
float exci=exc[i];
exc[i]=.8*g*exc[i]*ol_gain + .6*g*st->voc_m1*ol_gain + .5*g*innov[i] - .5*g*st->voc_m2 + (1-g)*innov[i];
st->voc_m1 = exci;
st->voc_m2=innov[i];
st->voc_mean = .95*st->voc_mean + .05*exc[i];
exc[i]-=st->voc_mean;
}
} else {
for (i=0;i<st->subframeSize;i++)
exc[i]+=innov[i];
}
/* Decode second codebook (only for some modes) */
if (SUBMODE(double_codebook))
{
char *tmp_stack=stack;
float *innov2 = PUSH(tmp_stack, st->subframeSize, float);
for (i=0;i<st->subframeSize;i++)
innov2[i]=0;
SUBMODE(innovation_unquant)(innov2, SUBMODE(innovation_params), st->subframeSize, bits, tmp_stack);
for (i=0;i<st->subframeSize;i++)
innov2[i]*=ener*(1/2.2);
for (i=0;i<st->subframeSize;i++)
exc[i] += innov2[i];
}
}
for (i=0;i<st->subframeSize;i++)
sp[i]=exc[i];
/* Signal synthesis */
if (st->lpc_enh_enabled && SUBMODE(comb_gain)>0)
comb_filter(exc, sp, st->interp_qlpc, st->lpcSize, st->subframeSize,
pitch, pitch_gain, SUBMODE(comb_gain), st->comb_mem);
if (st->lpc_enh_enabled)
{
/* Use enhanced LPC filter */
filter_mem2(sp, awk2, awk1, sp, st->subframeSize, st->lpcSize,
st->mem_sp+st->lpcSize);
filter_mem2(sp, awk3, st->interp_qlpc, sp, st->subframeSize, st->lpcSize,
st->mem_sp);
} else {
/* Use regular filter */
for (i=0;i<st->lpcSize;i++)
st->mem_sp[st->lpcSize+i] = 0;
iir_mem2(sp, st->interp_qlpc, sp, st->subframeSize, st->lpcSize,
st->mem_sp);
}
}
/*Copy output signal*/
out[0] = st->frame[0] + st->preemph*st->pre_mem;
for (i=1;i<st->frameSize;i++)
out[i]=st->frame[i] + st->preemph*out[i-1];
st->pre_mem=out[st->frameSize-1];
/* Store the LSPs for interpolation in the next frame */
for (i=0;i<st->lpcSize;i++)
st->old_qlsp[i] = st->qlsp[i];
/* The next frame will not be the first (Duh!) */
st->first = 0;
st->count_lost=0;
st->last_pitch = best_pitch;
st->last_pitch_gain = .25*pitch_average;
st->pitch_gain_buf[st->pitch_gain_buf_idx++] = st->last_pitch_gain;
if (st->pitch_gain_buf_idx > 2) /* rollover */
st->pitch_gain_buf_idx = 0;
st->last_ol_gain = ol_gain;
return 0;
}
int nb_encoder_ctl(void *state, int request, void *ptr)
{
EncState *st;
st=(EncState*)state;
switch(request)
{
case SPEEX_GET_FRAME_SIZE:
(*(int*)ptr) = st->frameSize;
break;
case SPEEX_SET_LOW_MODE:
case SPEEX_SET_MODE:
st->submodeSelect = st->submodeID = (*(int*)ptr);
break;
case SPEEX_GET_LOW_MODE:
case SPEEX_GET_MODE:
(*(int*)ptr) = st->submodeID;
break;
case SPEEX_SET_VBR:
st->vbr_enabled = (*(int*)ptr);
break;
case SPEEX_GET_VBR:
(*(int*)ptr) = st->vbr_enabled;
break;
case SPEEX_SET_VAD:
st->vad_enabled = (*(int*)ptr);
break;
case SPEEX_GET_VAD:
(*(int*)ptr) = st->vad_enabled;
break;
case SPEEX_SET_DTX:
st->dtx_enabled = (*(int*)ptr);
break;
case SPEEX_GET_DTX:
(*(int*)ptr) = st->dtx_enabled;
break;
case SPEEX_SET_ABR:
st->abr_enabled = (*(int*)ptr);
st->vbr_enabled = 1;
{
int i=10, rate, target;
float vbr_qual;
target = (*(int*)ptr);
while (i>=0)
{
speex_encoder_ctl(st, SPEEX_SET_QUALITY, &i);
speex_encoder_ctl(st, SPEEX_GET_BITRATE, &rate);
if (rate <= target)
break;
i--;
}
vbr_qual=i;
if (vbr_qual<0)
vbr_qual=0;
speex_encoder_ctl(st, SPEEX_SET_VBR_QUALITY, &vbr_qual);
st->abr_count=0;
st->abr_drift=0;
st->abr_drift2=0;
}
break;
case SPEEX_GET_ABR:
(*(int*)ptr) = st->abr_enabled;
break;
case SPEEX_SET_VBR_QUALITY:
st->vbr_quality = (*(float*)ptr);
break;
case SPEEX_GET_VBR_QUALITY:
(*(float*)ptr) = st->vbr_quality;
break;
case SPEEX_SET_QUALITY:
{
int quality = (*(int*)ptr);
if (quality < 0)
quality = 0;
if (quality > 10)
quality = 10;
st->submodeSelect = st->submodeID = ((SpeexNBMode*)(st->mode->mode))->quality_map[quality];
}
break;
case SPEEX_SET_COMPLEXITY:
st->complexity = (*(int*)ptr);
if (st->complexity<1)
st->complexity=1;
break;
case SPEEX_GET_COMPLEXITY:
(*(int*)ptr) = st->complexity;
break;
case SPEEX_SET_BITRATE:
{
int i=10, rate, target;
target = (*(int*)ptr);
while (i>=0)
{
speex_encoder_ctl(st, SPEEX_SET_QUALITY, &i);
speex_encoder_ctl(st, SPEEX_GET_BITRATE, &rate);
if (rate <= target)
break;
i--;
}
}
break;
case SPEEX_GET_BITRATE:
if (st->submodes[st->submodeID])
(*(int*)ptr) = st->sampling_rate*SUBMODE(bits_per_frame)/st->frameSize;
else
(*(int*)ptr) = st->sampling_rate*(NB_SUBMODE_BITS+1)/st->frameSize;
break;
case SPEEX_SET_SAMPLING_RATE:
st->sampling_rate = (*(int*)ptr);
break;
case SPEEX_GET_SAMPLING_RATE:
(*(int*)ptr)=st->sampling_rate;
break;
case SPEEX_RESET_STATE:
{
int i;
st->bounded_pitch = 1;
st->first = 1;
for (i=0;i<st->lpcSize;i++)
st->lsp[i]=(M_PI*((float)(i+1)))/(st->lpcSize+1);
for (i=0;i<st->lpcSize;i++)
st->mem_sw[i]=st->mem_sw_whole[i]=st->mem_sp[i]=st->mem_exc[i]=0;
for (i=0;i<st->bufSize;i++)
st->excBuf[i]=st->swBuf[i]=st->inBuf[i]=st->exc2Buf[i]=0;
}
break;
case SPEEX_GET_PI_GAIN:
{
int i;
float *g = (float*)ptr;
for (i=0;i<st->nbSubframes;i++)
g[i]=st->pi_gain[i];
}
break;
case SPEEX_GET_EXC:
{
int i;
float *e = (float*)ptr;
for (i=0;i<st->frameSize;i++)
e[i]=st->exc[i];
}
break;
case SPEEX_GET_INNOV:
{
int i;
float *e = (float*)ptr;
for (i=0;i<st->frameSize;i++)
e[i]=st->innov[i];
}
break;
case SPEEX_GET_RELATIVE_QUALITY:
(*(float*)ptr)=st->relative_quality;
break;
default:
speex_warning_int("Unknown nb_ctl request: ", request);
return -1;
}
return 0;
}
int nb_decoder_ctl(void *state, int request, void *ptr)
{
DecState *st;
st=(DecState*)state;
switch(request)
{
case SPEEX_GET_LOW_MODE:
case SPEEX_GET_MODE:
(*(int*)ptr) = st->submodeID;
break;
case SPEEX_SET_ENH:
st->lpc_enh_enabled = *((int*)ptr);
break;
case SPEEX_GET_ENH:
*((int*)ptr) = st->lpc_enh_enabled;
break;
case SPEEX_GET_FRAME_SIZE:
(*(int*)ptr) = st->frameSize;
break;
case SPEEX_GET_BITRATE:
if (st->submodes[st->submodeID])
(*(int*)ptr) = st->sampling_rate*SUBMODE(bits_per_frame)/st->frameSize;
else
(*(int*)ptr) = st->sampling_rate*(NB_SUBMODE_BITS+1)/st->frameSize;
break;
case SPEEX_SET_SAMPLING_RATE:
st->sampling_rate = (*(int*)ptr);
break;
case SPEEX_GET_SAMPLING_RATE:
(*(int*)ptr)=st->sampling_rate;
break;
case SPEEX_SET_HANDLER:
{
SpeexCallback *c = (SpeexCallback*)ptr;
st->speex_callbacks[c->callback_id].func=c->func;
st->speex_callbacks[c->callback_id].data=c->data;
st->speex_callbacks[c->callback_id].callback_id=c->callback_id;
}
break;
case SPEEX_SET_USER_HANDLER:
{
SpeexCallback *c = (SpeexCallback*)ptr;
st->user_callback.func=c->func;
st->user_callback.data=c->data;
st->user_callback.callback_id=c->callback_id;
}
break;
case SPEEX_RESET_STATE:
{
int i;
for (i=0;i<2*st->lpcSize;i++)
st->mem_sp[i]=0;
for (i=0;i<st->bufSize;i++)
st->excBuf[i]=st->inBuf[i]=0;
}
break;
case SPEEX_GET_PI_GAIN:
{
int i;
float *g = (float*)ptr;
for (i=0;i<st->nbSubframes;i++)
g[i]=st->pi_gain[i];
}
break;
case SPEEX_GET_EXC:
{
int i;
float *e = (float*)ptr;
for (i=0;i<st->frameSize;i++)
e[i]=st->exc[i];
}
break;
case SPEEX_GET_INNOV:
{
int i;
float *e = (float*)ptr;
for (i=0;i<st->frameSize;i++)
e[i]=st->innov[i];
}
break;
case SPEEX_GET_DTX_STATUS:
*((int*)ptr) = st->dtx_enabled;
break;
default:
speex_warning_int("Unknown nb_ctl request: ", request);
return -1;
}
return 0;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -