g723原始碼詳細分析 18 丟包補償

2021-06-03 06:25:48 字數 3280 閱讀 2489

g723對網路丟包行為了一些處理

涉及的函式為comp_info regen

comp_info:負責計算插值依據

它的四個引數

word16 *buff:激勵陣列,包含之前的145個激勵

word16 olp:當前幀的基音週期

word16 *gain:輸入增益(歸一化的)

word16 *shgain:輸出增益的縮放位移

返回值是激勵插值的延後

現在來看comp_info函式

道先做乙個歸一化處理,得到能量的歸一化所需要位移位數

/* normalize the excitation */

*shgain = vec_norm( buff, (word16) (pitchmax+frame) ) ;

**片段如下:

acc0 = (word32) 0 ;

for ( j = 0 ; j < 2*subfrlen ; j ++ )

acc0 = l_mac( acc0, buff[pitchmax+frame-2*subfrlen+j],

buff[pitchmax+frame-2*subfrlen-i+j] ) ;

if ( acc0 > acc1 )

}找出來的基音延後序列我們記錄 x[n-indx]

計算最後120個樣點的能量 tenr 這個是x[n]的能量(最後120個樣點)

/* compute target energy */ //lsc 計算最後120個樣點的能量

acc0 = (word32) 0 ;

for ( j = 0 ; j < 2*subfrlen ; j ++ )

acc0 = l_mac( acc0, buff[pitchmax+frame-2*subfrlen+j],

buff[pitchmax+frame-2*subfrlen+j] ) ;

tenr = round( acc0 ) ;

*gain = tenr;

計算最佳基音延後的能量 enr 這個是x[n-indx]的能量(連續120個)

/* compute best energy */ //lsc 計算基音週期延後的能量acc0

acc0 = (word32) 0 ;

for ( j = 0 ; j < 2*subfrlen ; j ++ )

acc0 = l_mac( acc0, buff[pitchmax+frame-2*subfrlen-(int)indx+j],

buff[pitchmax+frame-2*subfrlen-(int)indx+j] ) ;

得到能量以相基音延後的自相關之後,

就可以判斷x[n-indx] x[n]的相似度了

x[n-indx] x[n]相關,在**中是ccr

(enr * tenr)/16 < ccr^2 就認為這兩個序列是相關的,

當丟包時,插值依據就是x[n-indx],否則取x[n]

**片段:

ccr = round( acc1 ) ;

if ( ccr <= (word16) 0 )

return (word16) 0 ;

enr = round( acc0 ) ;

acc0 = l_mult( enr, tenr ) ;//lsc enr 為基音週期最佳延後的能量 tenr為最後120個樣點的能量

acc0 = l_shr( acc0, (word16) 3 ) ;

acc0 = l_msu( acc0, ccr, ccr ) ;//lsc ccr為最佳基音延遲自相關

if ( acc0 < (word32) 0 )//lsc acc0小 說明相關性大 可能會作為插值的依據,否則插值的依據就是前面的120個點

return indx ;

else

return (word16) 0 ;

再來看regen,它負責在出現丟包時,做插值

是否丟包,是由呼叫decod時傳的乙個引數crc來觸發

regen( databuff, temp, decstat.interindx, decstat.intergain,

decstat.ecount, &decstat.rseed ) ;

decstat.interindx就是comp_info計算得到的基音延後temp儲存145個歷史解碼激勵,

databuff為輸出的插值激勵

其中decstat.intergain是由以前幀得到的

如果沒有丟包,取中間兩子幀的平均,

丟包則按0.75的衰減取值

/** in case of no erasure, update the interpolation gain memory.

* otherwise compute the interpolation gain (text: section 3.10)

*/if ( decstat.ecount == (word16) 0 )

else

decstat.intergain = mult_r( decstat.intergain, (word16) 0x6000 ) ;//lsc 丟包時,按0.75衰減

regen的函式過程

如果錯誤次數超為6,則不做插值

錯誤次數小於6,按decstat.interindx是否為0,

decstat.interindx不為0,取相應的基音延後歷史激勵插值

/* voiced case */

for ( i = 0 ; i < frame ; i ++ )

buff[pitchmax+i] = buff[pitchmax-(int)lag+i] ;//lsc 利用基音延後,構造乙個週期激勵

for ( i = 0 ; i < frame ; i ++ )

databuff[i] = buff[pitchmax+i] = mult( buff[pitchmax+i],

(word16) 0x6000 ) ;//lsc 做乙個0.75的衰減

如果為0,認為處於清音段,用隨機激勵插值

/* unvoiced case */

for ( i = 0 ; i < frame ; i ++ )

databuff[i] = mult( gain, rand_lbc( sd ) ) ;//lsc 模擬乙個隨機激勵

/* clear buffer to reset memory */

for ( i = 0 ; i < frame+pitchmax ; i ++ )

buff[i] = (word16) 0 ;

下一章節將分析基音後置濾波與共振峰後置濾波

林紹川2012.01.16於杭州

g723原始碼詳細分析 三 lsp量化

4 lsp系數量化 現在來分析這個 10 lsp係數已經計算出來了,由於lsp的性質,可以將它們分成若干段,分別量化 它們將會被分成 3,3,4這三個分向量 每個向量都會有乙個256的碼本表 大概是這麼多的,可以直接計算一下那個陣列的大小 lsp qnt 這個函式,執行lsp量化的過程,會形成乙個l...

g723原始碼詳細分析 17 舒適雜訊解碼

dec cng舒適雜訊解碼 知道舒適雜訊如何生成,解碼就簡單了.sid會傳遞濾波引數 在濾波器相似度不高時,sid報文會被傳送 解出報文裡的lpc引數與增益估值 片段 sid frame decoding deccng.sidgain dec sidgain line sfs 0 mamp inve...

g723原始碼詳細分析 19 基音後置濾波器

現在來分析g723基音後置濾波器 根據基音周期間,激勵訊號的相關性,來對激勵訊號做乙個增強處理 相應的函式分別是 comp lpf filt lpf comp lpf 負責計算最佳的基音延後,具體地說,是在基音週期延遲附近,找出最匹配當前子幀激勵的60個連繼激勵e i 使用的方法自然找自相關最大的....