• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2025 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #ifndef LOG_TAG
17 #define LOG_TAG "HpaeCaptureEffectNode"
18 #endif
19 
20 #include "hpae_capture_effect_node.h"
21 #include <iostream>
22 #include "hpae_pcm_buffer.h"
23 #include "audio_errors.h"
24 #include "hpae_format_convert.h"
25 #include "audio_enhance_chain_manager.h"
26 #include "audio_effect_map.h"
27 #include "audio_utils.h"
28 #include "audio_effect_log.h"
29 
30 namespace OHOS {
31 namespace AudioStandard {
32 namespace HPAE {
HpaeCaptureEffectNode(HpaeNodeInfo & nodeInfo)33 HpaeCaptureEffectNode::HpaeCaptureEffectNode(HpaeNodeInfo &nodeInfo)
34     : HpaeNode(nodeInfo), HpaePluginNode(nodeInfo)
35 {
36     const std::unordered_map<AudioEnhanceScene, std::string> &audioEnhanceSupportedSceneTypes =
37         GetEnhanceSupportedSceneType();
38     auto item = audioEnhanceSupportedSceneTypes.find(nodeInfo.effectInfo.enhanceScene);
39     if (item != audioEnhanceSupportedSceneTypes.end()) {
40         sceneType_ = item->second;
41         AUDIO_INFO_LOG("HpaeCaptureEffectNode created scenetype: [%{public}s]", sceneType_.c_str());
42     } else {
43         AUDIO_ERR_LOG("scenetype: %{public}u not supported", nodeInfo.effectInfo.enhanceScene);
44     }
45 #ifdef ENABLE_HIDUMP_DFX
46     SetNodeName("hpaeCaptureEffectNode");
47 #endif
48 }
49 
~HpaeCaptureEffectNode()50 HpaeCaptureEffectNode::~HpaeCaptureEffectNode()
51 {
52 #ifdef ENABLE_HIDUMP_DFX
53     AUDIO_INFO_LOG("NodeId: %{public}u NodeName: %{public}s destructed.",
54         GetNodeId(), GetNodeName().c_str());
55 #endif
56 }
57 
Reset()58 bool HpaeCaptureEffectNode::Reset()
59 {
60     return HpaePluginNode::Reset();
61 }
62 
SignalProcess(const std::vector<HpaePcmBuffer * > & inputs)63 HpaePcmBuffer *HpaeCaptureEffectNode::SignalProcess(const std::vector<HpaePcmBuffer *> &inputs)
64 {
65     Trace trace("[" + sceneType_ + "]HpaeRenderEffectNode::SignalProcess inputs num[" +
66         std::to_string(inputs.size()) + "]");
67     if (inputs.empty()) {
68         AUDIO_WARNING_LOG("HpaeCaptureEffectNode inputs size is empty, SessionId:%{public}d", GetSessionId());
69         return nullptr;
70     }
71 
72     AudioEnhanceChainManager *audioEnhanceChainManager = AudioEnhanceChainManager::GetInstance();
73     EnhanceTransBuffer transBuf = {};
74     uint32_t processLength = 0;
75     for (uint32_t i = 0; i < inputs.size(); i++) {
76         if (inputs[i]->GetSourceBufferType() == HPAE_SOURCE_BUFFER_TYPE_MIC) {
77             ConvertFromFloat(SAMPLE_S16LE, micBufferLength_ / GetSizeFromFormat(SAMPLE_S16LE),
78                 inputs[i]->GetPcmDataBuffer(), static_cast<void *>(micCache_.data()));
79             transBuf.micData = static_cast<void *>(micCache_.data());
80             transBuf.micDataLen = micCache_.size();
81             processLength = micBufferLength_;
82             AUDIO_DEBUG_LOG("CopyToEnhanceBuffer size:%{public}u", processLength);
83         } else if (inputs[i]->GetSourceBufferType() == HPAE_SOURCE_BUFFER_TYPE_EC) {
84             ConvertFromFloat(SAMPLE_S16LE, ecBufferLength_ / GetSizeFromFormat(SAMPLE_S16LE),
85                 inputs[i]->GetPcmDataBuffer(), static_cast<void *>(ecCache_.data()));
86             transBuf.ecData = static_cast<void *>(ecCache_.data());
87             transBuf.ecDataLen = ecCache_.size();
88             AUDIO_DEBUG_LOG("CopyEcToEnhanceBuffer size:%{public}u", ecBufferLength_);
89         } else if (inputs[i]->GetSourceBufferType() == HPAE_SOURCE_BUFFER_TYPE_MICREF) {
90             ConvertFromFloat(SAMPLE_S16LE, micrefBufferLength_ / GetSizeFromFormat(SAMPLE_S16LE),
91                 inputs[i]->GetPcmDataBuffer(), static_cast<void *>(micRefCache_.data()));
92             transBuf.micRefData = static_cast<void *>(micRefCache_.data());
93             transBuf.micRefDataLen = micRefCache_.size();
94             AUDIO_DEBUG_LOG("CopyMicRefToEnhanceBuffer size:%{public}u", micrefBufferLength_);
95         }
96     }
97 
98     outPcmBuffer_->SetBufferValid(processLength != 0);
99     CHECK_AND_RETURN_RET(processLength != 0, outPcmBuffer_.get(), "error, main mic data is null");
100 
101     int32_t ret = audioEnhanceChainManager->ApplyEnhanceChainById(sceneKeyCode_, transBuf);
102     CHECK_AND_RETURN_RET_LOG(ret == SUCCESS, outPcmBuffer_.get(), "effect apply failed, ret:%{public}d", ret);
103     audioEnhanceChainManager->GetChainOutputDataById(sceneKeyCode_, static_cast<void *>(cacheDataOut_.data()),
104         static_cast<size_t>(processLength));
105     ConvertToFloat(SAMPLE_S16LE, micBufferLength_ / GetSizeFromFormat(SAMPLE_S16LE),
106         static_cast<void *>(cacheDataOut_.data()), outPcmBuffer_->GetPcmDataBuffer());
107     return outPcmBuffer_.get();
108 }
109 
ConnectWithInfo(const std::shared_ptr<OutputNode<HpaePcmBuffer * >> & preNode,HpaeNodeInfo & nodeInfo)110 void HpaeCaptureEffectNode::ConnectWithInfo(const std::shared_ptr<OutputNode<HpaePcmBuffer*>> &preNode,
111     HpaeNodeInfo &nodeInfo)
112 {
113     std::shared_ptr<HpaeNode> realPreNode = preNode->GetSharedInstance(nodeInfo);
114     CHECK_AND_RETURN_LOG(realPreNode != nullptr, "realPreNode is nullptr");
115     inputStream_.Connect(realPreNode, preNode->GetOutputPort(nodeInfo));
116 #ifdef ENABLE_HIDUMP_DFX
117     if (auto callback = GetNodeStatusCallback().lock()) {
118         callback->OnNotifyDfxNodeInfo(true, realPreNode->GetNodeId(), GetNodeInfo());
119     }
120 #endif
121 }
122 
DisConnectWithInfo(const std::shared_ptr<OutputNode<HpaePcmBuffer * >> & preNode,HpaeNodeInfo & nodeInfo)123 void HpaeCaptureEffectNode::DisConnectWithInfo(const std::shared_ptr<OutputNode<HpaePcmBuffer*>>& preNode,
124     HpaeNodeInfo &nodeInfo)
125 {
126     CHECK_AND_RETURN_LOG(!inputStream_.CheckIfDisConnected(preNode->GetOutputPort(nodeInfo)),
127         "HpaeCaptureEffectNode[%{public}u] has disconnected with preNode", GetNodeId());
128     inputStream_.DisConnect(preNode->GetOutputPort(nodeInfo, true));
129 #ifdef ENABLE_HIDUMP_DFX
130     if (auto callback = GetNodeStatusCallback().lock()) {
131         callback->OnNotifyDfxNodeInfo(false, GetNodeId(), GetNodeInfo());
132     }
133 #endif
134 }
135 
GetCapturerEffectConfig(HpaeNodeInfo & nodeInfo,HpaeSourceBufferType type)136 bool HpaeCaptureEffectNode::GetCapturerEffectConfig(HpaeNodeInfo& nodeInfo, HpaeSourceBufferType type)
137 {
138     CHECK_AND_RETURN_RET_LOG(capturerEffectConfigMap_.find(type) != capturerEffectConfigMap_.end(),
139         false, "not need resample node, type:%{public}u", type);
140     nodeInfo = capturerEffectConfigMap_[type];
141     return true;
142 }
143 
SetCapturerEffectConfig(AudioBufferConfig micConfig,AudioBufferConfig ecConfig,AudioBufferConfig micrefConfig)144 void HpaeCaptureEffectNode::SetCapturerEffectConfig(AudioBufferConfig micConfig, AudioBufferConfig ecConfig,
145     AudioBufferConfig micrefConfig)
146 {
147     HpaeNodeInfo micInfo = {};
148     HpaeNodeInfo ecInfo = {};
149     HpaeNodeInfo micrefInfo = {};
150     micInfo.sourceBufferType = HPAE_SOURCE_BUFFER_TYPE_MIC;
151     micInfo.frameLen = FRAME_LEN * (micConfig.samplingRate / MILLISECOND_PER_SECOND);
152     micInfo.samplingRate = static_cast<AudioSamplingRate>(micConfig.samplingRate);
153     micInfo.channels = static_cast<AudioChannel>(micConfig.channels);
154     micInfo.format = static_cast<AudioSampleFormat>(micConfig.format / BITLENGTH - 1);
155     ecInfo.sourceBufferType = HPAE_SOURCE_BUFFER_TYPE_EC;
156     ecInfo.frameLen = FRAME_LEN * (ecConfig.samplingRate / MILLISECOND_PER_SECOND);
157     ecInfo.samplingRate = static_cast<AudioSamplingRate>(ecConfig.samplingRate);
158     ecInfo.channels = static_cast<AudioChannel>(ecConfig.channels);
159     ecInfo.format = static_cast<AudioSampleFormat>(ecConfig.format / BITLENGTH - 1);
160     micrefInfo.sourceBufferType = HPAE_SOURCE_BUFFER_TYPE_MICREF;
161     micrefInfo.frameLen = FRAME_LEN * (micrefConfig.samplingRate / MILLISECOND_PER_SECOND);
162     micrefInfo.samplingRate = static_cast<AudioSamplingRate>(micrefConfig.samplingRate);
163     micrefInfo.channels = static_cast<AudioChannel>(micrefConfig.channels);
164     micrefInfo.format = static_cast<AudioSampleFormat>(micrefConfig.format / BITLENGTH - 1);
165     capturerEffectConfigMap_.emplace(HPAE_SOURCE_BUFFER_TYPE_MIC, micInfo);
166     capturerEffectConfigMap_.emplace(HPAE_SOURCE_BUFFER_TYPE_EC, ecInfo);
167     capturerEffectConfigMap_.emplace(HPAE_SOURCE_BUFFER_TYPE_MICREF, micrefInfo);
168 }
169 
CaptureEffectCreate(uint64_t sceneKeyCode,CaptureEffectAttr attr)170 int32_t HpaeCaptureEffectNode::CaptureEffectCreate(uint64_t sceneKeyCode, CaptureEffectAttr attr)
171 {
172     sceneKeyCode_ = sceneKeyCode;
173     AudioEnhanceChainManager *audioEnhanceChainManager = AudioEnhanceChainManager::GetInstance();
174     CHECK_AND_RETURN_RET_LOG(audioEnhanceChainManager, ERR_ILLEGAL_STATE, "audioEnhanceChainManager is nullptr");
175     AudioEnhanceDeviceAttr enhanceAttr = {};
176     enhanceAttr.micChannels = attr.micChannels;
177     enhanceAttr.ecChannels = attr.ecChannels;
178     enhanceAttr.micRefChannels = attr.micRefChannels;
179     int32_t ret = audioEnhanceChainManager->CreateAudioEnhanceChainDynamic(sceneKeyCode, enhanceAttr);
180     CHECK_AND_RETURN_RET_LOG(ret == SUCCESS, ERROR, "CreateAudioEnhanceChainDynamic failed, ret:%{public}d", ret);
181 
182     AudioBufferConfig micConfig = {};
183     AudioBufferConfig ecConfig = {};
184     AudioBufferConfig micrefConfig = {};
185     ret = audioEnhanceChainManager->AudioEnhanceChainGetAlgoConfig(sceneKeyCode, micConfig, ecConfig, micrefConfig);
186     CHECK_AND_RETURN_RET_LOG(ret == 0 && micConfig.samplingRate != 0, ERROR,
187         "get algo config failed, ret:%{public}d", ret);
188     SetCapturerEffectConfig(micConfig, ecConfig, micrefConfig);
189     micBufferLength_ = FRAME_LEN * micConfig.channels * (micConfig.samplingRate / MILLISECOND_PER_SECOND) *
190         (micConfig.format / BITLENGTH);
191     ecBufferLength_ = FRAME_LEN * ecConfig.channels * (ecConfig.samplingRate / MILLISECOND_PER_SECOND) *
192         (ecConfig.format / BITLENGTH);
193     micrefBufferLength_ = FRAME_LEN * micrefConfig.channels * (micrefConfig.samplingRate / MILLISECOND_PER_SECOND) *
194         (micrefConfig.format / BITLENGTH);
195     uint32_t maxLength = (micBufferLength_ > ecBufferLength_) ?
196         (micBufferLength_ > micrefBufferLength_ ? micBufferLength_ : micrefBufferLength_) :
197         (ecBufferLength_ > micrefBufferLength_ ? ecBufferLength_ : micrefBufferLength_);
198     AUDIO_INFO_LOG("micLength: %{public}u, ecLength: %{public}u, micrefLength: %{public}u, maxLength:%{public}u",
199         micBufferLength_, ecBufferLength_, micrefBufferLength_, maxLength);
200     ecCache_.resize(ecBufferLength_);
201     micCache_.resize(micBufferLength_);
202     micRefCache_.resize(micrefBufferLength_);
203     cacheDataOut_.resize(maxLength);
204     PcmBufferInfo pcmBufferInfo(micConfig.channels, FRAME_LEN * (micConfig.samplingRate / MILLISECOND_PER_SECOND),
205         micConfig.samplingRate);
206     outPcmBuffer_ = std::make_unique<HpaePcmBuffer>(pcmBufferInfo);
207     if (outPcmBuffer_ == nullptr) {
208         AUDIO_ERR_LOG("create effect out pcm buffer fail");
209         return ERROR;
210     }
211 
212     return ret;
213 }
214 
CaptureEffectRelease(uint64_t sceneKeyCode)215 int32_t HpaeCaptureEffectNode::CaptureEffectRelease(uint64_t sceneKeyCode)
216 {
217     AudioEnhanceChainManager *audioEnhanceChainManager = AudioEnhanceChainManager::GetInstance();
218     CHECK_AND_RETURN_RET_LOG(audioEnhanceChainManager, ERR_ILLEGAL_STATE, "audioEnhanceChainManager is nullptr");
219     return audioEnhanceChainManager->ReleaseAudioEnhanceChainDynamic(sceneKeyCode);
220 }
221 
222 }  // namespace HPAE
223 }  // namespace AudioStandard
224 }  // namespace OHOS
225