bsp_audio.c 14 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417
  1. #include "include.h"
  2. void bt_aec_process(u8 *ptr, u32 samples, int ch_mode);
  3. void bt_sco_tx_process(u8 *ptr, u32 samples, int ch_mode);
  4. void bt_alc_process(u8 *ptr, u32 samples, int ch_mode);
  5. void aux_sdadc_process(u8 *ptr, u32 samples, int ch_mode);
  6. void speaker_sdadc_process(u8 *ptr, u32 samples, int ch_mode);
  7. void usbmic_sdadc_process(u8 *ptr, u32 samples, int ch_mode);
  8. void karaok_sdadc_process(u8 *ptr, u32 samples, int ch_mode);
  9. void voice_assistant_sdadc_process(u8 *ptr,u32 samples,int ch_mode);
  10. void ttp_sdadc_process(u8 *ptr, u32 samples, int ch_mode);
  11. void anc_alg_sdadc_process(u8* ptr, u32 samples, int ch_mode);
  12. u32 get_sysclk_nhz(void);
  13. void anc_alg_audio_path_cfg_set(sdadc_cfg_t* cfg);
  14. void opus_sdadc_process(u8 *ptr, u32 samples, int ch_mode);
  15. void usbmic_data_process(u8 *ptr, u32 samples, int ch_mode);
  16. #if FUNC_AUX_EN
  17. #define aux_sdadc_callback aux_sdadc_process
  18. #else
  19. #define aux_sdadc_callback sdadc_dummy
  20. #endif // FUNC_AUX_EN
  21. #if FUNC_SPEAKER_EN
  22. #define speaker_sdadc_callback speaker_sdadc_process
  23. #else
  24. #define speaker_sdadc_callback sdadc_dummy
  25. #endif // FUNC_SPEAKER_EN
  26. #if UDE_MIC_EN && USB_MIC_NR_EN
  27. #define usbmic_sdadc_callback usbmic_data_process
  28. #elif UDE_MIC_EN
  29. #define usbmic_sdadc_callback usbmic_sdadc_process
  30. #else
  31. #define usbmic_sdadc_callback sdadc_dummy
  32. #endif // UDE_MIC_EN
  33. #if BT_AEC_EN
  34. #define bt_sdadc_callback bt_aec_process
  35. #elif BT_SCO_SMIC_EN || BT_SCO_DMIC_EN
  36. #define bt_sdadc_callback bt_aec_process
  37. #else
  38. #define bt_sdadc_callback bt_sco_tx_process
  39. #endif
  40. #if SYS_KARAOK_EN
  41. #define karaok_sdadc_callback karaok_sdadc_process
  42. #else
  43. #define karaok_sdadc_callback sdadc_dummy
  44. #endif
  45. #if TINY_TRANSPARENCY_EN
  46. #define ttp_sdadc_callback ttp_sdadc_process
  47. #else
  48. #define ttp_sdadc_callback sdadc_dummy
  49. #endif
  50. #if LE_DUEROS_DMA_EN
  51. #define opus_sdadc_callback opus_sdadc_process
  52. #else
  53. #define opus_sdadc_callback sdadc_dummy
  54. #endif
  55. #if ANC_ALG_EN
  56. #define anc_alg_sdadc_callback anc_alg_sdadc_process
  57. #else
  58. #define anc_alg_sdadc_callback sdadc_dummy
  59. #endif
  60. #if IODM_TEST_EN
  61. #define iodm_test_sdadc_callback iodm_test_sdadc_process
  62. #else
  63. #define iodm_test_sdadc_callback sdadc_dummy
  64. #endif
  65. #if ASR_EN
  66. #define asr_sdadc_callback asr_sdadc_process
  67. #else
  68. #define asr_sdadc_callback sdadc_dummy
  69. #endif
  70. #if USBAUDIO_MIC_AINS4
  71. typedef struct {
  72. //s32 noise_db2;
  73. //s32 noise_db3;
  74. s16 denoiseBound;
  75. s32 overdrive;
  76. u8 smooth_en;
  77. u8 modelUpdatePars0;
  78. //u8 enlarge_v;
  79. s16 gainHB_rd;
  80. u8 delta_k_up;
  81. s16 denoiseBound_fix;
  82. u8 yuan_en;
  83. u16 enr_thres;
  84. //u16 pitch_filter_range;
  85. } ains4_cb_t;
  86. #if 0
  87. typedef struct {
  88. uint8_t *rptr;
  89. uint8_t *wptr;
  90. uint8_t *start;
  91. uint8_t *end;
  92. volatile uint16_t total;
  93. uint16_t trig;
  94. } ring_buf_t;
  95. #endif // 0
  96. ains4_cb_t ains4_cb AT(.ains4_buf);
  97. ring_buf_t ring_buf AT(.ains4_buf);
  98. void asr_kick_start(void);
  99. void ains4_init(ains4_cb_t *ains4_cb);
  100. int ains4_process(s16 *data, s32 *data_32bits, u8 in_24bits_en);
  101. #if 0
  102. void ring_buf_init(ring_buf_t *pbuf, void *start, uint16_t size, uint16_t trig);
  103. bool ring_buf_put(ring_buf_t *pbuf, uint8_t *ptr, uint16_t len);
  104. bool ring_buf_get(ring_buf_t *pbuf, void (*callback)(uint8_t *, uint16_t), uint16_t len);
  105. #endif // 0
  106. extern u32 __cram_ains4_comm_vma, __cram_ains4_comm_lma, __cram_ains4_comm_size;
  107. u8 usbmic_togle = 0;
  108. s16 usbmic_buffer[240 * 4] AT(.ains4_buf);
  109. s16 ains4_buffer[480] AT(.ains4_buf);
  110. AT(.ains4_text)
  111. void ring_buf_get_callback(uint8_t *buf, uint16_t len)
  112. {
  113. memcpy(ains4_buffer, buf, len);
  114. asr_kick_start();
  115. }
  116. AT(.ains4_text)
  117. void usbmic_ains_sdadc_callback(u8* ptr, u32 samples, int ch_mode)
  118. {
  119. ring_buf_put(&ring_buf, ptr, samples * 2);
  120. ring_buf_get(&ring_buf, ring_buf_get_callback, 480 * 2);
  121. }
  122. AT(.ains4_text)
  123. void asr_kws_process(void) //借用kws的线程接口
  124. {
  125. ains4_process(ains4_buffer, (s32*)ains4_buffer, 0);
  126. mic_eq_proc((u16*)ains4_buffer, 480);
  127. usbmic_sdadc_callback((u8*)ains4_buffer, 480, 0);
  128. }
  129. #endif // USBAUDIO_MIC_AINS4
  130. //MIC analog gain: 0~14(共15级), step 3DB (0db ~ +42db)
  131. //adadc digital gain: 0~63, step 0.5 DB, 保存在gain的低6bit
  132. const sdadc_cfg_t rec_cfg_tbl[] = {
  133. /* 通道, 采样率, 模拟增益, 数字增益, BITS, 通路控制, 样点数, 回调函数*/
  134. {AUX_CHANNEL_CFG, SPR_44100, 2, 0, 0xff, ADC2DAC_EN, 256, aux_sdadc_callback}, /* AUX */
  135. {MIC_CHANNEL_CFG, SPR_48000, 10, 0, 0xff, ADC2DAC_EN, 256, speaker_sdadc_callback}, /* SPEAKER */
  136. {MIC_CHANNEL_CFG, SPR_8000, 12, 0, 1, ADC2DAC_EN, 480, bt_sdadc_callback}, /* BTMIC */
  137. #if USBAUDIO_MIC_AINS4
  138. {MIC_CHANNEL_CFG, SPR_96000, 12, 0, 1, 0, 480, usbmic_ains_sdadc_callback}, /* USBMIC */
  139. #else
  140. {MIC_CHANNEL_CFG, SPR_48000, 12, 0, 1, 0, 256, usbmic_sdadc_callback}, /* USBMIC */
  141. #endif // USBAUDIO_MIC_AINS4
  142. {MIC_CHANNEL_CFG, SPR_44100, 12, 0, 0xff, ADC2SRC_EN, 256, karaok_sdadc_callback}, /* KARAOK */
  143. {MIC_CHANNEL_CFG, SPR_16000, 12, 0, 1, ADC2DAC_EN, 256, opus_sdadc_callback}, /* opus */
  144. {MIC_CHANNEL_CFG, SPR_44100, 6, 0, 1, ADC2SRC_EN, 128, ttp_sdadc_callback}, /* TRANSPARENCY */
  145. {MIC_CHANNEL_CFG, SPR_16000, 12, 0, 1, ADC2SANC_EN, 256, anc_alg_sdadc_callback}, /* ANC ALG */
  146. {MIC_CHANNEL_CFG, SPR_48000, 10, 0, 0xff, ADC2DAC_EN, 256, iodm_test_sdadc_callback}, /* IODM TEST */
  147. {MIC_CHANNEL_CFG, SPR_16000, 10, 0, 1, ADC2ASR_EN, 256, asr_sdadc_callback}, /* ASR */
  148. };
  149. #if FUNC_AUX_EN
  150. u16 bsp_aux_ch_getcfg(void);
  151. #endif
  152. /*****************************************************************************
  153. * 功能 : 根据Settings,获取mic通路
  154. * 输入 : audio_path_idx,用于判断是否为BT_MIC_PATH
  155. * 注意 : 若mic通路选取异常,会报err;BT_MIC_PATH可选单、双麦,其他模式只采用单麦即主麦
  156. * 返回 : 无
  157. *****************************************************************************/
  158. static u16 bsp_mic_ch_getcfg(u8 audio_path)
  159. {
  160. u8 mic_cnt = 0;
  161. u16 ch_sel = 0;
  162. u16 mic_list[2] = {xcfg_cb.bt_mmic_cfg, xcfg_cb.bt_smic_cfg};
  163. u8 mic_mapping_tbl[5] = {CH_MIC0, CH_MIC1, CH_MIC2, CH_MIC3, CH_MIC4};
  164. #if ANC_EN
  165. if (xcfg_cb.anc_en && xcfg_cb.anc_mode != MODE_HYBRID) { //如果打开anc,重定义mic->adc路径
  166. mic_mapping_tbl[0] = ADC2 << 4 | MIC0;
  167. mic_mapping_tbl[1] = ADC3 << 4 | MIC1;
  168. mic_mapping_tbl[2] = ADC0 << 4 | MIC2;
  169. mic_mapping_tbl[3] = ADC1 << 4 | MIC3;
  170. }
  171. #endif
  172. #if BT_SCO_DMIC_EN
  173. if (audio_path == AUDIO_PATH_BTMIC) {
  174. mic_cnt = 2;
  175. } else if (audio_path == AUDIO_PATH_ASR) {
  176. mic_cnt = 1;
  177. }
  178. #if HLW_UI
  179. else if(audio_path == AUDIO_PATH_USBMIC)
  180. {
  181. mic_cnt = 1;
  182. }
  183. #endif // HLW_UI
  184. printf("mic_cnt %d MMIC --> %d, SMIC --> %d\n", mic_cnt, mic_list[0], mic_list[1]);
  185. #else
  186. mic_cnt = 1;
  187. printf("MMIC --> %d\n", mic_list[0]);
  188. #endif
  189. #if USB_MIC_NR_EN
  190. if (audio_path == AUDIO_PATH_USBMIC) {
  191. mic_cnt = 2;
  192. }
  193. #endif
  194. for (u8 i = 0; i < mic_cnt; i++) {
  195. if ((mic_list[i] + 1) > MIC4) {
  196. continue;
  197. }
  198. ch_sel |= mic_mapping_tbl[mic_list[i]] << (8 * i);
  199. }
  200. return ch_sel;
  201. }
  202. /*****************************************************************************
  203. * 功能 : 初始化对应AUDIO_PATH
  204. * 输入 : audio_path_idx 对应不同功能使用的audio通路
  205. * 注意 : 区分bt_call和其他状态
  206. * 返回 : 无
  207. *****************************************************************************/
  208. void audio_path_init(u8 path_idx)
  209. {
  210. sdadc_cfg_t cfg;
  211. memcpy(&cfg, &rec_cfg_tbl[path_idx], sizeof(sdadc_cfg_t));
  212. #if HLW_UI
  213. if (path_idx == AUDIO_PATH_USBMIC)
  214. {
  215. sys_clk_req(INDEX_ENCODE, SYS_160M); //借用录音的index
  216. #if USBAUDIO_MIC_AINS4
  217. memcpy(&__cram_ains4_comm_vma, &__cram_ains4_comm_lma, (u32)&__cram_ains4_comm_size); //把代码load到指定的ram
  218. memset(&ains4_cb, 0, sizeof(ains4_cb_t));
  219. ring_buf_init(&ring_buf, usbmic_buffer, 240 * 4 * 2, 0);
  220. ains4_init(&ains4_cb);
  221. #endif // USBAUDIO_MIC_AINS4
  222. mic_set_eq_by_res(RES_BUF_EQ_USB_MIC_EQ, RES_LEN_EQ_USB_MIC_EQ);
  223. mic_set_post_gain(SOFT_DIG_P0DB);
  224. }
  225. #endif // HLW_UI
  226. #if FUNC_AUX_EN
  227. if (path_idx == AUDIO_PATH_AUX) {
  228. cfg.channel = bsp_aux_ch_getcfg();
  229. cfg.anl_gain = xcfg_cb.aux_anl_gain | xcfg_cb.aux_anl_gain<<6; //双声道模拟增益保持一致
  230. cfg.dig_gain = xcfg_cb.aux_dig_gain | xcfg_cb.aux_dig_gain<<6; //双声道数字增益保持一致
  231. }
  232. #endif // FUNC_AUX_EN
  233. if (path_idx == AUDIO_PATH_BTMIC || path_idx == AUDIO_PATH_KARAOK || path_idx == AUDIO_PATH_OPUS || path_idx == AUDIO_PATH_TTP || path_idx == AUDIO_PATH_SPEAKER || path_idx == AUDIO_PATH_USBMIC || path_idx == AUDIO_PATH_ASR) {
  234. if (path_idx == AUDIO_PATH_BTMIC) {
  235. if (sys_cb.hfp_karaok_en) {
  236. memcpy(&cfg, &rec_cfg_tbl[AUDIO_PATH_KARAOK], sizeof(sdadc_cfg_t));
  237. cfg.sample_rate = SPR_48000;
  238. } else {
  239. if (bt_sco_is_msbc() || bt_sco_dnn_en()) { //如果开了msbc或dnn,则采样率设为16k
  240. cfg.sample_rate = SPR_16000;
  241. }
  242. }
  243. }
  244. cfg.channel = bsp_mic_ch_getcfg(path_idx);
  245. cfg.anl_gain = ((xcfg_cb.mic0_anl_gain) |
  246. (xcfg_cb.mic1_anl_gain<<6) |
  247. (xcfg_cb.mic2_anl_gain<<12)|
  248. (xcfg_cb.mic3_anl_gain<<18)|
  249. (xcfg_cb.mic4_anl_gain<<24));
  250. cfg.dig_gain = ((xcfg_cb.bt_mic0_dig_gain) |
  251. (xcfg_cb.bt_mic1_dig_gain<<6) |
  252. (xcfg_cb.bt_mic2_dig_gain<<12)|
  253. (xcfg_cb.bt_mic3_dig_gain<<18)|
  254. (xcfg_cb.bt_mic4_dig_gain<<24));
  255. }
  256. #if ANC_ALG_EN
  257. if (path_idx == AUDIO_PATH_ANC_ALG) {
  258. anc_alg_audio_path_cfg_set(&cfg);
  259. }
  260. #endif // ANC_ALG_EN
  261. #if IODM_TEST_EN
  262. if (path_idx == AUDIO_PATH_IODM_MIC_TEST){
  263. iodm_test_loopback_set_mic_ch(&cfg.channel, &cfg.anl_gain, &cfg.dig_gain);
  264. }
  265. #endif
  266. #if FUNC_USBDEV_EN
  267. if (path_idx == AUDIO_PATH_USBMIC) {
  268. cfg.sample_rate = sys_cb.ude_mic_spr;
  269. #if USB_MIC_NR_EN
  270. cfg.sample_rate = SPR_16000;
  271. cfg.samples = 480;
  272. #endif
  273. }
  274. #endif
  275. sdadc_init(&cfg);
  276. #if BT_SCO_SMIC_AI_EN || BT_SCO_DMIC_AI_EN || BT_SCO_LDMIC_AI_EN || BT_SCO_AIAEC_DNN_EN || BT_SCO_SMIC_AI_PRO_EN
  277. if (path_idx == AUDIO_PATH_BTMIC) {
  278. if (!bt_sco_is_msbc() && bt_sco_dnn_en()) { //部分降噪算法窄带通话时,ADC为16K采样率,DAC为8K采样率
  279. dac_spr_set(SPR_8000);
  280. }
  281. }
  282. #endif
  283. #if SDADC_DRC_EN
  284. sdadc_drc_init((u8 *)RES_BUF_EQ_SDADC_DRC, RES_LEN_EQ_SDADC_DRC);
  285. #endif
  286. }
  287. /*****************************************************************************
  288. * 功能 : 启动AUDIO采集和DAC数据处理
  289. * 输入 : audio_path_idx 对应不同功能使用的audio通路
  290. * 注意 : channel需要和init时保持一致,否则通路会启动失败
  291. * 返回 : 无
  292. *****************************************************************************/
  293. void audio_path_start(u8 path_idx)
  294. {
  295. sdadc_cfg_t cfg;
  296. memcpy(&cfg, &rec_cfg_tbl[path_idx], sizeof(sdadc_cfg_t));
  297. #if FUNC_AUX_EN
  298. if (path_idx == AUDIO_PATH_AUX) {
  299. cfg.channel = bsp_aux_ch_getcfg();
  300. cfg.anl_gain = xcfg_cb.aux_anl_gain | xcfg_cb.aux_anl_gain<<6; //双声道模拟增益保持一致
  301. cfg.dig_gain = xcfg_cb.aux_dig_gain | xcfg_cb.aux_dig_gain<<6; //双声道数字增益保持一致
  302. }
  303. #endif // FUNC_AUX_EN
  304. if (path_idx == AUDIO_PATH_BTMIC || path_idx == AUDIO_PATH_KARAOK || path_idx == AUDIO_PATH_OPUS || path_idx == AUDIO_PATH_TTP || path_idx == AUDIO_PATH_SPEAKER || path_idx == AUDIO_PATH_USBMIC || path_idx == AUDIO_PATH_ASR) {
  305. cfg.channel = bsp_mic_ch_getcfg(path_idx);
  306. }
  307. #if ANC_ALG_EN
  308. if (path_idx == AUDIO_PATH_ANC_ALG) {
  309. anc_alg_audio_path_cfg_set(&cfg);
  310. }
  311. #endif // ANC_ALG_EN
  312. #if IODM_TEST_EN
  313. if (path_idx == AUDIO_PATH_IODM_MIC_TEST){
  314. iodm_test_loopback_set_mic_ch(&cfg.channel, &cfg.anl_gain, &cfg.dig_gain);
  315. }
  316. #endif
  317. sdadc_start(cfg.channel);
  318. }
  319. /*****************************************************************************
  320. * 功能 : 关闭对应AUDIO_PATH
  321. * 输入 : audio_path_idx 对应不同功能使用的audio通路
  322. * 注意 : 关闭audio后,功耗要和打开audio之前保持一致
  323. * 返回 : 无
  324. *****************************************************************************/
  325. void audio_path_exit(u8 path_idx)
  326. {
  327. sdadc_cfg_t cfg;
  328. memcpy(&cfg, &rec_cfg_tbl[path_idx], sizeof(sdadc_cfg_t));
  329. #if FUNC_AUX_EN
  330. if (path_idx == AUDIO_PATH_AUX) {
  331. cfg.channel = bsp_aux_ch_getcfg();
  332. }
  333. #endif // FUNC_AUX_EN
  334. if (path_idx == AUDIO_PATH_BTMIC || path_idx == AUDIO_PATH_KARAOK || path_idx == AUDIO_PATH_OPUS || path_idx == AUDIO_PATH_TTP || path_idx == AUDIO_PATH_SPEAKER || path_idx == AUDIO_PATH_ASR || path_idx == AUDIO_PATH_USBMIC) {
  335. cfg.channel = bsp_mic_ch_getcfg(path_idx);
  336. }
  337. #if ANC_ALG_EN
  338. if (path_idx == AUDIO_PATH_ANC_ALG) {
  339. anc_alg_audio_path_cfg_set(&cfg);
  340. }
  341. #endif // ANC_ALG_EN
  342. #if IODM_TEST_EN
  343. if (path_idx == AUDIO_PATH_IODM_MIC_TEST){
  344. iodm_test_loopback_set_mic_exit(&cfg.channel);
  345. }
  346. #endif
  347. sdadc_exit(cfg.channel);
  348. #if ANC_EN
  349. if (!sys_cb.anc_start)
  350. #endif
  351. {
  352. adpll_spr_set(DAC_OUT_SPR);
  353. }
  354. #if HLW_UI
  355. if (path_idx == AUDIO_PATH_USBMIC)
  356. {
  357. sys_clk_free(INDEX_ENCODE);
  358. delay_5ms(10);
  359. mic_eq_off();
  360. }
  361. #endif // HLW_UI
  362. }