OpusEncoder.cpp 8.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271
  1. //
  2. // libtgvoip is free and unencumbered public domain software.
  3. // For more information, see http://unlicense.org or the UNLICENSE file
  4. // you should have received with this source code distribution.
  5. //
  6. #include "OpusEncoder.h"
  7. #include "EchoCanceller.h"
  8. #include <assert.h>
  9. #include <algorithm>
  10. #include "logging.h"
  11. #include "VoIPServerConfig.h"
  12. #if TGVOIP_INCLUDE_OPUS_PACKAGE
  13. #include <opus/opus.h>
  14. #else
  15. #include <opus.h>
  16. #endif
  17. namespace{
  18. int serverConfigValueToBandwidth(int config){
  19. switch(config){
  20. case 0:
  21. return OPUS_BANDWIDTH_NARROWBAND;
  22. case 1:
  23. return OPUS_BANDWIDTH_MEDIUMBAND;
  24. case 2:
  25. return OPUS_BANDWIDTH_WIDEBAND;
  26. case 3:
  27. return OPUS_BANDWIDTH_SUPERWIDEBAND;
  28. case 4:
  29. default:
  30. return OPUS_BANDWIDTH_FULLBAND;
  31. }
  32. }
  33. }
  34. tgvoip::OpusEncoder::OpusEncoder(MediaStreamItf *source, bool needSecondary):queue(11), bufferPool(960*2, 10){
  35. this->source=source;
  36. source->SetCallback(tgvoip::OpusEncoder::Callback, this);
  37. enc=opus_encoder_create(48000, 1, OPUS_APPLICATION_VOIP, NULL);
  38. opus_encoder_ctl(enc, OPUS_SET_COMPLEXITY(10));
  39. opus_encoder_ctl(enc, OPUS_SET_PACKET_LOSS_PERC(1));
  40. opus_encoder_ctl(enc, OPUS_SET_INBAND_FEC(1));
  41. opus_encoder_ctl(enc, OPUS_SET_SIGNAL(OPUS_SIGNAL_VOICE));
  42. opus_encoder_ctl(enc, OPUS_SET_BANDWIDTH(OPUS_BANDWIDTH_FULLBAND));
  43. requestedBitrate=20000;
  44. currentBitrate=0;
  45. running=false;
  46. echoCanceller=NULL;
  47. complexity=10;
  48. frameDuration=20;
  49. levelMeter=NULL;
  50. vadNoVoiceBitrate=static_cast<uint32_t>(ServerConfig::GetSharedInstance()->GetInt("audio_vad_no_voice_bitrate", 6000));
  51. vadModeVoiceBandwidth=serverConfigValueToBandwidth(ServerConfig::GetSharedInstance()->GetInt("audio_vad_bandwidth", 3));
  52. vadModeNoVoiceBandwidth=serverConfigValueToBandwidth(ServerConfig::GetSharedInstance()->GetInt("audio_vad_no_voice_bandwidth", 0));
  53. secondaryEnabledBandwidth=serverConfigValueToBandwidth(ServerConfig::GetSharedInstance()->GetInt("audio_extra_ec_bandwidth", 2));
  54. secondaryEncoderEnabled=false;
  55. if(needSecondary){
  56. secondaryEncoder=opus_encoder_create(48000, 1, OPUS_APPLICATION_VOIP, NULL);
  57. opus_encoder_ctl(secondaryEncoder, OPUS_SET_COMPLEXITY(10));
  58. opus_encoder_ctl(secondaryEncoder, OPUS_SET_SIGNAL(OPUS_SIGNAL_VOICE));
  59. //opus_encoder_ctl(secondaryEncoder, OPUS_SET_VBR(0));
  60. opus_encoder_ctl(secondaryEncoder, OPUS_SET_BITRATE(8000));
  61. opus_encoder_ctl(secondaryEncoder, OPUS_SET_BANDWIDTH(secondaryEnabledBandwidth));
  62. }else{
  63. secondaryEncoder=NULL;
  64. }
  65. }
  66. tgvoip::OpusEncoder::~OpusEncoder(){
  67. opus_encoder_destroy(enc);
  68. if(secondaryEncoder)
  69. opus_encoder_destroy(secondaryEncoder);
  70. }
  71. void tgvoip::OpusEncoder::Start(){
  72. if(running)
  73. return;
  74. running=true;
  75. thread=new Thread(std::bind(&tgvoip::OpusEncoder::RunThread, this));
  76. thread->SetName("OpusEncoder");
  77. thread->Start();
  78. thread->SetMaxPriority();
  79. }
  80. void tgvoip::OpusEncoder::Stop(){
  81. if(!running)
  82. return;
  83. running=false;
  84. queue.Put(NULL);
  85. thread->Join();
  86. delete thread;
  87. }
  88. void tgvoip::OpusEncoder::SetBitrate(uint32_t bitrate){
  89. requestedBitrate=bitrate;
  90. }
  91. void tgvoip::OpusEncoder::Encode(int16_t* data, size_t len){
  92. if(requestedBitrate!=currentBitrate){
  93. opus_encoder_ctl(enc, OPUS_SET_BITRATE(requestedBitrate));
  94. currentBitrate=requestedBitrate;
  95. LOGV("opus_encoder: setting bitrate to %u", currentBitrate);
  96. }
  97. if(levelMeter)
  98. levelMeter->Update(data, len);
  99. if(secondaryEncoderEnabled!=wasSecondaryEncoderEnabled){
  100. wasSecondaryEncoderEnabled=secondaryEncoderEnabled;
  101. opus_encoder_ctl(enc, OPUS_SET_BANDWIDTH(secondaryEncoderEnabled ? secondaryEnabledBandwidth : OPUS_BANDWIDTH_FULLBAND));
  102. }
  103. int32_t r=opus_encode(enc, data, static_cast<int>(len), buffer, 4096);
  104. if(r<=0){
  105. LOGE("Error encoding: %d", r);
  106. }else if(r==1){
  107. LOGW("DTX");
  108. }else if(running){
  109. //LOGV("Packet size = %d", r);
  110. int32_t secondaryLen=0;
  111. unsigned char secondaryBuffer[128];
  112. if(secondaryEncoderEnabled && secondaryEncoder){
  113. secondaryLen=opus_encode(secondaryEncoder, data, static_cast<int>(len), secondaryBuffer, sizeof(secondaryBuffer));
  114. //LOGV("secondaryLen %d", secondaryLen);
  115. }
  116. InvokeCallback(buffer, (size_t)r, secondaryBuffer, (size_t)secondaryLen);
  117. }
  118. }
  119. size_t tgvoip::OpusEncoder::Callback(unsigned char *data, size_t len, void* param){
  120. OpusEncoder* e=(OpusEncoder*)param;
  121. unsigned char* buf=e->bufferPool.Get();
  122. if(buf){
  123. assert(len==960*2);
  124. memcpy(buf, data, 960*2);
  125. e->queue.Put(buf);
  126. }else{
  127. LOGW("opus_encoder: no buffer slots left");
  128. if(e->complexity>1){
  129. e->complexity--;
  130. opus_encoder_ctl(e->enc, OPUS_SET_COMPLEXITY(e->complexity));
  131. }
  132. }
  133. return 0;
  134. }
  135. uint32_t tgvoip::OpusEncoder::GetBitrate(){
  136. return requestedBitrate;
  137. }
  138. void tgvoip::OpusEncoder::SetEchoCanceller(EchoCanceller* aec){
  139. echoCanceller=aec;
  140. }
  141. void tgvoip::OpusEncoder::RunThread(){
  142. uint32_t bufferedCount=0;
  143. uint32_t packetsPerFrame=frameDuration/20;
  144. LOGV("starting encoder, packets per frame=%d", packetsPerFrame);
  145. int16_t* frame;
  146. if(packetsPerFrame>1)
  147. frame=(int16_t*) malloc(960*2*packetsPerFrame);
  148. else
  149. frame=NULL;
  150. bool frameHasVoice=false;
  151. bool wasVadMode=false;
  152. while(running){
  153. int16_t* packet=(int16_t*)queue.GetBlocking();
  154. if(packet){
  155. bool hasVoice=true;
  156. if(echoCanceller)
  157. echoCanceller->ProcessInput(packet, 960, hasVoice);
  158. if(!postProcEffects.empty()){
  159. for(effects::AudioEffect* effect:postProcEffects){
  160. effect->Process(packet, 960);
  161. }
  162. }
  163. if(packetsPerFrame==1){
  164. Encode(packet, 960);
  165. }else{
  166. memcpy(frame+(960*bufferedCount), packet, 960*2);
  167. frameHasVoice=frameHasVoice || hasVoice;
  168. bufferedCount++;
  169. if(bufferedCount==packetsPerFrame){
  170. if(vadMode){
  171. if(frameHasVoice){
  172. opus_encoder_ctl(enc, OPUS_SET_BITRATE(currentBitrate));
  173. opus_encoder_ctl(enc, OPUS_SET_BANDWIDTH(vadModeVoiceBandwidth));
  174. if(secondaryEncoder){
  175. opus_encoder_ctl(secondaryEncoder, OPUS_SET_BITRATE(currentBitrate));
  176. opus_encoder_ctl(secondaryEncoder, OPUS_SET_BANDWIDTH(vadModeVoiceBandwidth));
  177. }
  178. }else{
  179. opus_encoder_ctl(enc, OPUS_SET_BITRATE(vadNoVoiceBitrate));
  180. opus_encoder_ctl(enc, OPUS_SET_BANDWIDTH(vadModeNoVoiceBandwidth));
  181. if(secondaryEncoder){
  182. opus_encoder_ctl(secondaryEncoder, OPUS_SET_BITRATE(vadNoVoiceBitrate));
  183. opus_encoder_ctl(secondaryEncoder, OPUS_SET_BANDWIDTH(vadModeNoVoiceBandwidth));
  184. }
  185. }
  186. wasVadMode=true;
  187. }else if(wasVadMode){
  188. wasVadMode=false;
  189. opus_encoder_ctl(enc, OPUS_SET_BITRATE(currentBitrate));
  190. opus_encoder_ctl(enc, OPUS_SET_BANDWIDTH(secondaryEncoderEnabled ? secondaryEnabledBandwidth : OPUS_AUTO));
  191. if(secondaryEncoder){
  192. opus_encoder_ctl(secondaryEncoder, OPUS_SET_BITRATE(currentBitrate));
  193. opus_encoder_ctl(secondaryEncoder, OPUS_SET_BANDWIDTH(secondaryEnabledBandwidth));
  194. }
  195. }
  196. Encode(frame, 960*packetsPerFrame);
  197. bufferedCount=0;
  198. frameHasVoice=false;
  199. }
  200. }
  201. bufferPool.Reuse(reinterpret_cast<unsigned char *>(packet));
  202. }
  203. }
  204. if(frame)
  205. free(frame);
  206. }
  207. void tgvoip::OpusEncoder::SetOutputFrameDuration(uint32_t duration){
  208. frameDuration=duration;
  209. }
  210. void tgvoip::OpusEncoder::SetPacketLoss(int percent){
  211. packetLossPercent=std::min(20, percent);
  212. opus_encoder_ctl(enc, OPUS_SET_PACKET_LOSS_PERC(packetLossPercent));
  213. opus_encoder_ctl(enc, OPUS_SET_INBAND_FEC(percent>0 && !secondaryEncoderEnabled ? 1 : 0));
  214. }
  215. int tgvoip::OpusEncoder::GetPacketLoss(){
  216. return packetLossPercent;
  217. }
  218. void tgvoip::OpusEncoder::SetDTX(bool enable){
  219. opus_encoder_ctl(enc, OPUS_SET_DTX(enable ? 1 : 0));
  220. }
  221. void tgvoip::OpusEncoder::SetLevelMeter(tgvoip::AudioLevelMeter *levelMeter){
  222. this->levelMeter=levelMeter;
  223. }
  224. void tgvoip::OpusEncoder::SetCallback(void (*f)(unsigned char *, size_t, unsigned char *, size_t, void *), void *param){
  225. callback=f;
  226. callbackParam=param;
  227. }
  228. void tgvoip::OpusEncoder::InvokeCallback(unsigned char *data, size_t length, unsigned char *secondaryData, size_t secondaryLength){
  229. callback(data, length, secondaryData, secondaryLength, callbackParam);
  230. }
  231. void tgvoip::OpusEncoder::SetSecondaryEncoderEnabled(bool enabled){
  232. secondaryEncoderEnabled=enabled;
  233. }
  234. void tgvoip::OpusEncoder::SetVadMode(bool vad){
  235. vadMode=vad;
  236. }
  237. void tgvoip::OpusEncoder::AddAudioEffect(effects::AudioEffect *effect){
  238. postProcEffects.push_back(effect);
  239. }
  240. void tgvoip::OpusEncoder::RemoveAudioEffect(effects::AudioEffect *effect){
  241. std::vector<effects::AudioEffect*>::iterator i=std::find(postProcEffects.begin(), postProcEffects.end(), effect);
  242. if(i!=postProcEffects.end())
  243. postProcEffects.erase(i);
  244. }