1 /*
2 * Copyright (c) 2022-2023 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 #ifndef LOG_TAG
16 #define LOG_TAG "FastAudioRendererSinkInner"
17 #endif
18
19 #include "fast_audio_renderer_sink.h"
20
21 #include <cinttypes>
22 #include <climits>
23 #include <cstdio>
24 #include <cstring>
25 #include <dlfcn.h>
26 #include <list>
27 #include <mutex>
28 #include <string>
29 #include <unistd.h>
30
31 #include <sys/mman.h>
32 #ifdef FEATURE_POWER_MANAGER
33 #include "power_mgr_client.h"
34 #include "running_lock.h"
35 #include "audio_running_lock_manager.h"
36 #endif
37 #include "securec.h"
38 #include "v4_0/iaudio_manager.h"
39
40 #include "audio_errors.h"
41 #include "audio_hdi_log.h"
42 #include "audio_utils.h"
43
44 using namespace std;
45
46 namespace OHOS {
47 namespace AudioStandard {
48 namespace {
49 const int32_t HALF_FACTOR = 2;
50 const uint32_t MAX_AUDIO_ADAPTER_NUM = 5;
51 const float DEFAULT_VOLUME_LEVEL = 1.0f;
52 const uint32_t AUDIO_CHANNELCOUNT = 2;
53 const uint32_t DEEP_BUFFER_RENDER_PERIOD_SIZE = 3840;
54 const uint32_t INT_32_MAX = 0x7fffffff;
55 const uint32_t PCM_8_BIT = 8;
56 const uint32_t PCM_16_BIT = 16;
57 const uint32_t PCM_24_BIT = 24;
58 const uint32_t PCM_32_BIT = 32;
59 const int64_t SECOND_TO_NANOSECOND = 1000000000;
60 const int INVALID_FD = -1;
61 const unsigned int XCOLLIE_TIME_OUT_SECONDS = 10;
62 }
63
64 class FastAudioRendererSinkInner : public FastAudioRendererSink {
65 public:
66 int32_t Init(const IAudioSinkAttr &attr) override;
67 bool IsInited(void) override;
68 void DeInit(void) override;
69
70 int32_t Start(void) override;
71 int32_t Stop(void) override;
72 int32_t Flush(void) override;
73 int32_t Reset(void) override;
74 int32_t Pause(void) override;
75 int32_t Resume(void) override;
76
77 int32_t SuspendRenderSink(void) override;
78 int32_t RestoreRenderSink(void) override;
79
80 int32_t RenderFrame(char &data, uint64_t len, uint64_t &writeLen) override;
81 int32_t SetVolume(float left, float right) override;
82 int32_t GetVolume(float &left, float &right) override;
83 int32_t SetVoiceVolume(float volume) override;
84 int32_t GetLatency(uint32_t *latency) override;
85 int32_t GetTransactionId(uint64_t *transactionId) override;
86 int32_t SetAudioScene(AudioScene audioScene, std::vector<DeviceType> &activeDevices) override;
87 int32_t SetOutputRoutes(std::vector<DeviceType> &outputDevices) override;
88 void ResetOutputRouteForDisconnect(DeviceType device) override;
89
90 void SetAudioParameter(const AudioParamKey key, const std::string &condition, const std::string &value) override;
91 std::string GetAudioParameter(const AudioParamKey key, const std::string &condition) override;
92 void RegisterParameterCallback(IAudioSinkCallback* callback) override;
93
94 void SetAudioMonoState(bool audioMono) override;
95 void SetAudioBalanceValue(float audioBalance) override;
96
97 int32_t GetPresentationPosition(uint64_t& frames, int64_t& timeSec, int64_t& timeNanoSec) override;
98
99 int32_t GetMmapBufferInfo(int &fd, uint32_t &totalSizeInframe, uint32_t &spanSizeInframe,
100 uint32_t &byteSizePerFrame) override;
101 int32_t GetMmapHandlePosition(uint64_t &frames, int64_t &timeSec, int64_t &timeNanoSec) override;
102 float GetMaxAmplitude() override;
103 int32_t SetPaPower(int32_t flag) override;
104 int32_t SetPriPaPower() override;
105
106 int32_t UpdateAppsUid(const int32_t appsUid[MAX_MIX_CHANNELS], const size_t size) final;
107 int32_t UpdateAppsUid(const std::vector<int32_t> &appsUid) final;
108
109 FastAudioRendererSinkInner();
110 ~FastAudioRendererSinkInner();
111
112 private:
113 #ifdef FEATURE_POWER_MANAGER
114 void KeepRunningLock();
115 void KeepRunningUnlock();
116 #endif
117 int32_t PrepareMmapBuffer();
118 void ReleaseMmapBuffer();
119
120 int32_t CheckPositionTime();
121 void PreparePosition();
122
123 void InitAttrs(struct AudioSampleAttributes &attrs);
124 AudioFormat ConvertToHdiFormat(HdiAdapterFormat format);
125 int32_t CreateRender(const struct AudioPort &renderPort);
126 int32_t InitAudioManager();
127
128 private:
129 IAudioSinkAttr attr_ = {};
130 bool rendererInited_ = false;
131 bool started_ = false;
132 bool paused_ = false;
133 float leftVolume_ = 0.0f;
134 float rightVolume_ = 0.0f;
135 int32_t routeHandle_ = -1;
136 std::string adapterNameCase_ = "";
137 struct IAudioManager *audioManager_ = nullptr;
138 struct IAudioAdapter *audioAdapter_ = nullptr;
139 struct IAudioRender *audioRender_ = nullptr;
140 struct AudioAdapterDescriptor adapterDesc_ = {};
141 struct AudioPort audioPort_ = {};
142 uint32_t renderId_ = 0;
143
144 size_t bufferSize_ = 0;
145 uint32_t bufferTotalFrameSize_ = 0;
146
147 int bufferFd_ = INVALID_FD;
148 uint32_t frameSizeInByte_ = 1;
149 uint32_t eachReadFrameSize_ = 0;
150 std::mutex mutex_;
151 #ifdef FEATURE_POWER_MANAGER
152 std::shared_ptr<AudioRunningLockManager<PowerMgr::RunningLock>> runningLockManager_;
153 #endif
154
155 #ifdef DEBUG_DIRECT_USE_HDI
156 char *bufferAddresss_ = nullptr;
157 bool isFirstWrite_ = true;
158 uint64_t alreadyReadFrames_ = 0;
159 uint32_t curReadPos_ = 0;
160 uint32_t curWritePos_ = 0;
161 uint32_t writeAheadPeriod_ = 1;
162
163 int privFd_ = INVALID_FD; // invalid fd
164 #endif
165 }; // FastAudioRendererSinkInner
166
FastAudioRendererSinkInner()167 FastAudioRendererSinkInner::FastAudioRendererSinkInner()
168 : rendererInited_(false), started_(false), paused_(false), leftVolume_(DEFAULT_VOLUME_LEVEL),
169 rightVolume_(DEFAULT_VOLUME_LEVEL), audioManager_(nullptr), audioAdapter_(nullptr),
170 audioRender_(nullptr)
171 {
172 attr_ = {};
173 }
174
~FastAudioRendererSinkInner()175 FastAudioRendererSinkInner::~FastAudioRendererSinkInner()
176 {
177 FastAudioRendererSinkInner::DeInit();
178 }
179
GetInstance()180 IMmapAudioRendererSink *FastAudioRendererSink::GetInstance()
181 {
182 static FastAudioRendererSinkInner audioRenderer;
183
184 return &audioRenderer;
185 }
186
GetVoipInstance()187 IMmapAudioRendererSink *FastAudioRendererSink::GetVoipInstance()
188 {
189 static FastAudioRendererSinkInner audioVoipRenderer;
190
191 return &audioVoipRenderer;
192 }
193
CreateFastRendererSink()194 std::shared_ptr<IMmapAudioRendererSink> FastAudioRendererSink::CreateFastRendererSink()
195 {
196 std::shared_ptr<IMmapAudioRendererSink> audioRenderer = std::make_shared<FastAudioRendererSinkInner>();
197
198 return audioRenderer;
199 }
200
IsInited()201 bool FastAudioRendererSinkInner::IsInited()
202 {
203 return rendererInited_;
204 }
205
DeInit()206 void FastAudioRendererSinkInner::DeInit()
207 {
208 #ifdef FEATURE_POWER_MANAGER
209 KeepRunningUnlock();
210
211 #endif
212
213 started_ = false;
214 rendererInited_ = false;
215 if ((audioRender_ != nullptr) && (audioAdapter_ != nullptr)) {
216 audioAdapter_->DestroyRender(audioAdapter_, renderId_);
217 }
218 audioRender_ = nullptr;
219
220 if ((audioManager_ != nullptr) && (audioAdapter_ != nullptr)) {
221 if (routeHandle_ != -1) {
222 audioAdapter_->ReleaseAudioRoute(audioAdapter_, routeHandle_);
223 }
224 audioManager_->UnloadAdapter(audioManager_, adapterDesc_.adapterName);
225 }
226 audioAdapter_ = nullptr;
227 audioManager_ = nullptr;
228
229 ReleaseMmapBuffer();
230 }
231
InitAttrs(struct AudioSampleAttributes & attrs)232 void FastAudioRendererSinkInner::InitAttrs(struct AudioSampleAttributes &attrs)
233 {
234 /* Initialization of audio parameters for playback */
235 attrs.channelCount = AUDIO_CHANNELCOUNT;
236 attrs.interleaved = true;
237 attrs.streamId = attr_.audioStreamFlag == AUDIO_FLAG_VOIP_FAST ?
238 static_cast<int32_t>(GenerateUniqueID(AUDIO_HDI_RENDER_ID_BASE, HDI_RENDER_OFFSET_VOIP_FAST)) :
239 static_cast<int32_t>(GenerateUniqueID(AUDIO_HDI_RENDER_ID_BASE, HDI_RENDER_OFFSET_FAST));
240 attrs.period = DEEP_BUFFER_RENDER_PERIOD_SIZE;
241 attrs.isBigEndian = false;
242 attrs.isSignedData = true;
243 attrs.stopThreshold = INT_32_MAX;
244 attrs.silenceThreshold = 0;
245 }
246
SwitchAdapterRender(struct AudioAdapterDescriptor * descs,string adapterNameCase,enum AudioPortDirection portFlag,struct AudioPort & renderPort,int32_t size)247 static int32_t SwitchAdapterRender(struct AudioAdapterDescriptor *descs, string adapterNameCase,
248 enum AudioPortDirection portFlag, struct AudioPort &renderPort, int32_t size)
249 {
250 if (descs == nullptr) {
251 return ERROR;
252 }
253 for (int32_t index = 0; index < size; index++) {
254 struct AudioAdapterDescriptor *desc = &descs[index];
255 if (desc == nullptr || desc->adapterName == nullptr) {
256 continue;
257 }
258 if (strcmp(desc->adapterName, adapterNameCase.c_str())) {
259 continue;
260 }
261 for (uint32_t port = 0; port < desc->portsLen; port++) {
262 // Only find out the port of out in the sound card
263 if (desc->ports[port].dir == portFlag) {
264 renderPort = desc->ports[port];
265 return index;
266 }
267 }
268 }
269 AUDIO_ERR_LOG("SwitchAdapterRender Fail");
270
271 return ERR_INVALID_INDEX;
272 }
273
InitAudioManager()274 int32_t FastAudioRendererSinkInner::InitAudioManager()
275 {
276 AUDIO_INFO_LOG("Initialize audio proxy manager");
277
278 audioManager_ = IAudioManagerGet(false);
279 if (audioManager_ == nullptr) {
280 return ERR_INVALID_HANDLE;
281 }
282
283 return 0;
284 }
285
PcmFormatToBits(HdiAdapterFormat format)286 uint32_t PcmFormatToBits(HdiAdapterFormat format)
287 {
288 switch (format) {
289 case SAMPLE_U8:
290 return PCM_8_BIT;
291 case SAMPLE_S16LE:
292 return PCM_16_BIT;
293 case SAMPLE_S24LE:
294 return PCM_24_BIT;
295 case SAMPLE_S32LE:
296 return PCM_32_BIT;
297 case SAMPLE_F32LE:
298 return PCM_32_BIT;
299 default:
300 return PCM_24_BIT;
301 }
302 }
303
GetMmapBufferInfo(int & fd,uint32_t & totalSizeInframe,uint32_t & spanSizeInframe,uint32_t & byteSizePerFrame)304 int32_t FastAudioRendererSinkInner::GetMmapBufferInfo(int &fd, uint32_t &totalSizeInframe, uint32_t &spanSizeInframe,
305 uint32_t &byteSizePerFrame)
306 {
307 CHECK_AND_RETURN_RET_LOG(bufferFd_ != INVALID_FD, ERR_INVALID_HANDLE, "buffer fd has been released!");
308 fd = bufferFd_;
309 totalSizeInframe = bufferTotalFrameSize_;
310 spanSizeInframe = eachReadFrameSize_;
311 byteSizePerFrame = PcmFormatToBits(attr_.format) * attr_.channel / PCM_8_BIT;
312 return SUCCESS;
313 }
314
GetMmapHandlePosition(uint64_t & frames,int64_t & timeSec,int64_t & timeNanoSec)315 int32_t FastAudioRendererSinkInner::GetMmapHandlePosition(uint64_t &frames, int64_t &timeSec, int64_t &timeNanoSec)
316 {
317 CHECK_AND_RETURN_RET_LOG(audioRender_ != nullptr, ERR_INVALID_HANDLE, "Audio render is null!");
318
319 struct AudioTimeStamp timestamp = {};
320 int32_t ret = audioRender_->GetMmapPosition(audioRender_, &frames, ×tamp);
321 CHECK_AND_RETURN_RET_LOG(ret == 0, ERR_OPERATION_FAILED, "Hdi GetMmapPosition filed, ret:%{public}d!", ret);
322 #ifdef DEBUG_DIRECT_USE_HDI
323 alreadyReadFrames_ = frames; // frames already read.
324 curReadPos_ = frameSizeInByte_ * (frames - bufferTotalFrameSize_ * (frames / bufferTotalFrameSize_));
325 CHECK_AND_RETURN_RET_LOG((curReadPos_ >= 0 && curReadPos_ < bufferSize_), ERR_INVALID_PARAM, "curReadPos invalid");
326 AUDIO_DEBUG_LOG("GetMmapHandlePosition frames[:%{public}" PRIu64 "] tvsec:%{public}" PRId64 " tvNSec:"
327 "%{public}" PRId64 " alreadyReadFrames:%{public}" PRId64 " curReadPos[%{public}d]",
328 frames, timestamp.tvSec, timestamp.tvNSec, alreadyReadFrames_, curReadPos_);
329 #endif
330
331 int64_t maxSec = 9223372036; // (9223372036 + 1) * 10^9 > INT64_MAX, seconds should not bigger than it.
332 CHECK_AND_RETURN_RET_LOG(timestamp.tvSec >= 0 && timestamp.tvSec <= maxSec && timestamp.tvNSec >= 0 &&
333 timestamp.tvNSec <= SECOND_TO_NANOSECOND, ERR_OPERATION_FAILED,
334 "Hdi GetMmapPosition get invaild second:%{public}" PRId64 " or nanosecond:%{public}" PRId64 " !",
335 timestamp.tvSec, timestamp.tvNSec);
336 timeSec = timestamp.tvSec;
337 timeNanoSec = timestamp.tvNSec;
338
339 return SUCCESS;
340 }
341
ReleaseMmapBuffer()342 void FastAudioRendererSinkInner::ReleaseMmapBuffer()
343 {
344 #ifdef DEBUG_DIRECT_USE_HDI
345 if (bufferAddresss_ != nullptr) {
346 munmap(bufferAddresss_, bufferSize_);
347 bufferAddresss_ = nullptr;
348 bufferSize_ = 0;
349 AUDIO_INFO_LOG("ReleaseMmapBuffer end.");
350 } else {
351 AUDIO_WARNING_LOG("ReleaseMmapBuffer buffer already null.");
352 }
353 if (privFd_ != INVALID_FD) {
354 close(privFd_);
355 privFd_ = INVALID_FD;
356 }
357 #endif
358 if (bufferFd_ != INVALID_FD) {
359 close(bufferFd_);
360 bufferFd_ = INVALID_FD;
361 }
362 }
363
PrepareMmapBuffer()364 int32_t FastAudioRendererSinkInner::PrepareMmapBuffer()
365 {
366 uint32_t totalBufferInMs = 40; // 5 * (6 + 2 * (1)) = 40ms, the buffer size, not latency.
367 frameSizeInByte_ = PcmFormatToBits(attr_.format) * attr_.channel / PCM_8_BIT;
368 uint32_t reqBufferFrameSize = totalBufferInMs * (attr_.sampleRate / 1000);
369
370 struct AudioMmapBufferDescriptor desc = {0};
371 int32_t ret = audioRender_->ReqMmapBuffer(audioRender_, reqBufferFrameSize, &desc);
372 CHECK_AND_RETURN_RET_LOG(ret == 0, ERR_OPERATION_FAILED, "ReqMmapBuffer failed, ret:%{public}d", ret);
373 AUDIO_INFO_LOG("AudioMmapBufferDescriptor memoryAddress[%{private}p] memoryFd[%{public}d] totalBufferFrames"
374 "[%{public}d] transferFrameSize[%{public}d] isShareable[%{public}d] offset[%{public}d]", desc.memoryAddress,
375 desc.memoryFd, desc.totalBufferFrames, desc.transferFrameSize, desc.isShareable, desc.offset);
376
377 bufferFd_ = desc.memoryFd; // fcntl(fd, 1030,3) after dup?
378 int32_t periodFrameMaxSize = 1920000; // 192khz * 10s
379 CHECK_AND_RETURN_RET_LOG(desc.totalBufferFrames >= 0 && desc.transferFrameSize >= 0 &&
380 desc.transferFrameSize <= periodFrameMaxSize, ERR_OPERATION_FAILED,
381 "ReqMmapBuffer invalid values: totalBufferFrames[%{public}d] transferFrameSize[%{public}d]",
382 desc.totalBufferFrames, desc.transferFrameSize);
383 bufferTotalFrameSize_ = static_cast<uint32_t>(desc.totalBufferFrames); // 1440 ~ 3840
384 eachReadFrameSize_ = static_cast<uint32_t>(desc.transferFrameSize); // 240
385
386 CHECK_AND_RETURN_RET_LOG(frameSizeInByte_ <= ULLONG_MAX / bufferTotalFrameSize_, ERR_OPERATION_FAILED,
387 "BufferSize will overflow!");
388 bufferSize_ = bufferTotalFrameSize_ * frameSizeInByte_;
389 #ifdef DEBUG_DIRECT_USE_HDI
390 privFd_ = dup(bufferFd_);
391 bufferAddresss_ = (char *)mmap(nullptr, bufferSize_, PROT_READ | PROT_WRITE, MAP_SHARED, privFd_, 0);
392 CHECK_AND_RETURN_RET_LOG(bufferAddresss_ != nullptr && bufferAddresss_ != MAP_FAILED, ERR_OPERATION_FAILED,
393 "mmap buffer failed!");
394 #endif
395 return SUCCESS;
396 }
397
ConvertToHdiFormat(HdiAdapterFormat format)398 AudioFormat FastAudioRendererSinkInner::ConvertToHdiFormat(HdiAdapterFormat format)
399 {
400 AudioFormat hdiFormat;
401 switch (format) {
402 case SAMPLE_U8:
403 hdiFormat = AUDIO_FORMAT_TYPE_PCM_8_BIT;
404 break;
405 case SAMPLE_S16:
406 hdiFormat = AUDIO_FORMAT_TYPE_PCM_16_BIT;
407 break;
408 case SAMPLE_S24:
409 hdiFormat = AUDIO_FORMAT_TYPE_PCM_24_BIT;
410 break;
411 case SAMPLE_S32:
412 hdiFormat = AUDIO_FORMAT_TYPE_PCM_32_BIT;
413 break;
414 default:
415 hdiFormat = AUDIO_FORMAT_TYPE_PCM_16_BIT;
416 break;
417 }
418
419 return hdiFormat;
420 }
421
CreateRender(const struct AudioPort & renderPort)422 int32_t FastAudioRendererSinkInner::CreateRender(const struct AudioPort &renderPort)
423 {
424 int32_t ret;
425 struct AudioSampleAttributes param;
426 InitAttrs(param);
427 param.type = attr_.audioStreamFlag == AUDIO_FLAG_VOIP_FAST ? AUDIO_MMAP_VOIP : AUDIO_MMAP_NOIRQ;
428 param.sampleRate = attr_.sampleRate;
429 param.channelCount = attr_.channel;
430 if (param.channelCount == MONO) {
431 param.channelLayout = CH_LAYOUT_MONO;
432 } else if (param.channelCount == STEREO) {
433 param.channelLayout = CH_LAYOUT_STEREO;
434 }
435 param.format = ConvertToHdiFormat(attr_.format);
436 param.frameSize = PcmFormatToBits(attr_.format) * param.channelCount / PCM_8_BIT;
437 param.startThreshold = DEEP_BUFFER_RENDER_PERIOD_SIZE / (param.frameSize); // not passed in hdi
438 AUDIO_INFO_LOG("Type: %{public}d, sampleRate: %{public}u, channel: %{public}d, format: %{public}d, "
439 "device:%{public}d", param.type, param.sampleRate, param.channelCount, param.format, attr_.deviceType);
440 struct AudioDeviceDescriptor deviceDesc;
441 deviceDesc.portId = renderPort.portId;
442 switch (static_cast<DeviceType>(attr_.deviceType)) {
443 case DEVICE_TYPE_EARPIECE:
444 deviceDesc.pins = PIN_OUT_EARPIECE;
445 break;
446 case DEVICE_TYPE_SPEAKER:
447 deviceDesc.pins = PIN_OUT_SPEAKER;
448 break;
449 case DEVICE_TYPE_WIRED_HEADSET:
450 deviceDesc.pins = PIN_OUT_HEADSET;
451 break;
452 case DEVICE_TYPE_USB_HEADSET:
453 deviceDesc.pins = PIN_OUT_USB_EXT;
454 break;
455 case DEVICE_TYPE_BLUETOOTH_SCO:
456 deviceDesc.pins = PIN_OUT_BLUETOOTH_SCO;
457 break;
458 default:
459 deviceDesc.pins = PIN_OUT_SPEAKER;
460 break;
461 }
462 char desc[] = "";
463 deviceDesc.desc = desc;
464 ret = audioAdapter_->CreateRender(audioAdapter_, &deviceDesc, ¶m, &audioRender_, &renderId_);
465 if (ret != 0 || audioRender_ == nullptr) {
466 AUDIO_ERR_LOG("AudioDeviceCreateRender failed, ret is :%{public}d", ret);
467 audioManager_->UnloadAdapter(audioManager_, adapterDesc_.adapterName);
468 return ERR_NOT_STARTED;
469 }
470
471 return SUCCESS;
472 }
473
Init(const IAudioSinkAttr & attr)474 int32_t FastAudioRendererSinkInner::Init(const IAudioSinkAttr &attr)
475 {
476 AUDIO_INFO_LOG("FastAudioRendererSinkInner::Init");
477 attr_ = attr;
478 adapterNameCase_ = attr_.adapterName; // Set sound card information
479 enum AudioPortDirection port = PORT_OUT; // Set port information
480
481 CHECK_AND_RETURN_RET_LOG(InitAudioManager() == 0, ERR_NOT_STARTED, "Init audio manager Fail");
482
483 uint32_t size = MAX_AUDIO_ADAPTER_NUM;
484 AudioAdapterDescriptor descs[MAX_AUDIO_ADAPTER_NUM];
485 if (audioManager_ == nullptr) {
486 AUDIO_ERR_LOG("The audioManager is nullptr!");
487 return ERROR;
488 }
489 int32_t ret = audioManager_->GetAllAdapters(audioManager_,
490 (struct AudioAdapterDescriptor *)&descs, &size);
491 CHECK_AND_RETURN_RET_LOG(size <= MAX_AUDIO_ADAPTER_NUM && size != 0 && ret == 0, ERR_NOT_STARTED,
492 "Get adapters Fail");
493
494 int32_t index = SwitchAdapterRender((struct AudioAdapterDescriptor *)&descs, adapterNameCase_, port, audioPort_,
495 size);
496 CHECK_AND_RETURN_RET_LOG(index >= 0, ERR_NOT_STARTED, "Switch Adapter Fail");
497
498 adapterDesc_ = descs[index];
499 int32_t result = audioManager_->LoadAdapter(audioManager_, &adapterDesc_, &audioAdapter_);
500 CHECK_AND_RETURN_RET_LOG(result == 0, ERR_NOT_STARTED, "Load Adapter Fail");
501 CHECK_AND_RETURN_RET_LOG(audioAdapter_ != nullptr, ERR_NOT_STARTED, "Load audio device failed");
502
503 // Initialization port information, can fill through mode and other parameters
504 ret = audioAdapter_->InitAllPorts(audioAdapter_);
505 CHECK_AND_RETURN_RET_LOG(ret == 0, ERR_NOT_STARTED, "InitAllPorts failed");
506
507 CHECK_AND_RETURN_RET_LOG(CreateRender(audioPort_) == SUCCESS && PrepareMmapBuffer() == SUCCESS,
508 ERR_NOT_STARTED, "Create render failed, Audio Port: %{public}d", audioPort_.portId);
509
510 rendererInited_ = true;
511
512 return SUCCESS;
513 }
514
PreparePosition()515 void FastAudioRendererSinkInner::PreparePosition()
516 {
517 #ifdef DEBUG_DIRECT_USE_HDI
518 isFirstWrite_ = false;
519 uint64_t frames = 0;
520 int64_t timeSec = 0;
521 int64_t timeNanoSec = 0;
522 GetMmapHandlePosition(frames, timeSec, timeNanoSec); // get first start position
523 int32_t periodByteSize = eachReadFrameSize_ * frameSizeInByte_;
524 CHECK_AND_RETURN_LOG(periodByteSize * writeAheadPeriod_ <= ULLONG_MAX - curReadPos_, "TempPos will overflow!");
525 size_t tempPos = curReadPos_ + periodByteSize * writeAheadPeriod_; // 1 period ahead
526 curWritePos_ = (tempPos < bufferSize_ ? tempPos : tempPos - bufferSize_);
527 AUDIO_INFO_LOG("First render frame start with curReadPos_[%{public}d] curWritePos_[%{public}d]", curReadPos_,
528 curWritePos_);
529 #endif
530 }
531
RenderFrame(char & data,uint64_t len,uint64_t & writeLen)532 int32_t FastAudioRendererSinkInner::RenderFrame(char &data, uint64_t len, uint64_t &writeLen)
533 {
534 #ifdef DEBUG_DIRECT_USE_HDI
535 int64_t stamp = ClockTime::GetCurNano();
536 CHECK_AND_RETURN_RET_LOG(audioRender_ != nullptr, ERR_INVALID_HANDLE, "Audio Render Handle is nullptr!");
537
538 if (len > (bufferSize_ - eachReadFrameSize_ * frameSizeInByte_ * writeAheadPeriod_)) {
539 writeLen = 0;
540 AUDIO_ERR_LOG("RenderFrame failed,too large len[%{public}" PRIu64 "]!", len);
541 return ERR_WRITE_FAILED;
542 }
543
544 if (isFirstWrite_) {
545 PreparePosition();
546 }
547
548 CHECK_AND_RETURN_RET_LOG((curWritePos_ >= 0 && curWritePos_ < bufferSize_), ERR_INVALID_PARAM,
549 "curWritePos_ invalid");
550 char *writePtr = bufferAddresss_ + curWritePos_;
551 uint64_t dataBefore = *(uint64_t *)writePtr;
552 uint64_t dataAfter = 0;
553 uint64_t tempPos = curWritePos_ + len;
554 if (tempPos <= bufferSize_) {
555 if (memcpy_s(writePtr, (bufferSize_ - curWritePos_), static_cast<void *>(&data), len)) {
556 AUDIO_ERR_LOG("copy failed");
557 return ERR_WRITE_FAILED;
558 }
559 dataAfter = *(uint64_t *)writePtr;
560 curWritePos_ = (tempPos == bufferSize_ ? 0 : tempPos);
561 } else {
562 AUDIO_DEBUG_LOG("(tempPos%{public}" PRIu64 ")curWritePos_ + len > bufferSize_", tempPos);
563 size_t writeableSize = bufferSize_ - curWritePos_;
564 if (memcpy_s(writePtr, writeableSize, static_cast<void *>(&data), writeableSize) ||
565 memcpy_s(bufferAddresss_, bufferSize_, static_cast<void *>((char *)&data + writeableSize),
566 (len - writeableSize))) {
567 AUDIO_ERR_LOG("copy failed");
568 return ERR_WRITE_FAILED;
569 }
570 curWritePos_ = len - writeableSize;
571 }
572 writeLen = len;
573
574 stamp = (ClockTime::GetCurNano() - stamp) / AUDIO_US_PER_SECOND;
575 AUDIO_DEBUG_LOG("Render len[%{public}" PRIu64 "] cost[%{public}" PRId64 "]ms curWritePos[%{public}d] dataBefore"
576 "<%{public}" PRIu64 "> dataAfter<%{public}" PRIu64 ">", len, stamp, curWritePos_, dataBefore, dataAfter);
577 return SUCCESS;
578 #else
579 AUDIO_WARNING_LOG("RenderFrame is not supported.");
580 return ERR_NOT_SUPPORTED;
581 #endif
582 }
583
GetMaxAmplitude()584 float FastAudioRendererSinkInner::GetMaxAmplitude()
585 {
586 AUDIO_WARNING_LOG("getMaxAmplitude in fast_audio_renderder_sink not support");
587 return 0;
588 }
589
SetPaPower(int32_t flag)590 int32_t FastAudioRendererSinkInner::SetPaPower(int32_t flag)
591 {
592 (void)flag;
593 return ERR_NOT_SUPPORTED;
594 }
595
SetPriPaPower()596 int32_t FastAudioRendererSinkInner::SetPriPaPower()
597 {
598 return ERR_NOT_SUPPORTED;
599 }
600
CheckPositionTime()601 int32_t FastAudioRendererSinkInner::CheckPositionTime()
602 {
603 int32_t tryCount = 50;
604 uint64_t frames = 0;
605 int64_t timeSec = 0;
606 int64_t timeNanoSec = 0;
607 int64_t maxHandleCost = 10000000; // ns
608 int64_t waitTime = 2000000; // 2ms
609 while (tryCount-- > 0) {
610 ClockTime::RelativeSleep(waitTime); // us
611 int32_t ret = GetMmapHandlePosition(frames, timeSec, timeNanoSec);
612 int64_t curTime = ClockTime::GetCurNano();
613 int64_t curSec = curTime / AUDIO_NS_PER_SECOND;
614 int64_t curNanoSec = curTime - curSec * AUDIO_NS_PER_SECOND;
615 if (ret != SUCCESS || curSec != timeSec || curNanoSec - timeNanoSec > maxHandleCost) {
616 AUDIO_WARNING_LOG("CheckPositionTime[%{public}d]:ret %{public}d", tryCount, ret);
617 continue;
618 } else {
619 AUDIO_INFO_LOG("CheckPositionTime end, position and time is ok.");
620 return SUCCESS;
621 }
622 }
623 return ERROR;
624 }
625
Start(void)626 int32_t FastAudioRendererSinkInner::Start(void)
627 {
628 std::lock_guard<std::mutex> lock(mutex_);
629 Trace trace("FastAudioRendererSinkInner::Start");
630 AudioXCollie sourceXCollie("FastAudioRendererSinkInner::Start", XCOLLIE_TIME_OUT_SECONDS);
631 AUDIO_INFO_LOG("FastAudioRendererSinkInner::Start");
632 int64_t stamp = ClockTime::GetCurNano();
633 int32_t ret;
634
635 CHECK_AND_RETURN_RET_LOG(audioRender_ != nullptr, ERR_INVALID_HANDLE,
636 "FastAudioRendererSink::Start audioRender_ null!");
637
638 if (!started_) {
639 ret = audioRender_->Start(audioRender_);
640 CHECK_AND_RETURN_RET_LOG(ret == 0, ERR_NOT_STARTED,
641 "FastAudioRendererSink::Start failed!");
642 int32_t err = CheckPositionTime();
643 CHECK_AND_RETURN_RET_LOG(err == SUCCESS, ERR_NOT_STARTED,
644 "FastAudioRendererSink::CheckPositionTime failed!");
645 }
646 #ifdef FEATURE_POWER_MANAGER
647 KeepRunningLock();
648 #endif
649 started_ = true;
650 AUDIO_DEBUG_LOG("Start cost[%{public}" PRId64 "]ms", (ClockTime::GetCurNano() - stamp) / AUDIO_US_PER_SECOND);
651 return SUCCESS;
652 }
653 #ifdef FEATURE_POWER_MANAGER
KeepRunningLock()654 void FastAudioRendererSinkInner::KeepRunningLock()
655 {
656 std::shared_ptr<PowerMgr::RunningLock> keepRunningLock;
657 if (runningLockManager_ == nullptr) {
658 keepRunningLock = PowerMgr::PowerMgrClient::GetInstance().CreateRunningLock("AudioFastBackgroundPlay",
659 PowerMgr::RunningLockType::RUNNINGLOCK_BACKGROUND_AUDIO);
660 if (keepRunningLock) {
661 runningLockManager_ = std::make_shared<AudioRunningLockManager<PowerMgr::RunningLock>> (keepRunningLock);
662 }
663 }
664
665 if (runningLockManager_ != nullptr) {
666 int32_t timeOut = -1; // -1 for lasting.
667 AUDIO_INFO_LOG("keepRunningLock lock result: %{public}d",
668 runningLockManager_->Lock(timeOut)); // -1 for lasting.
669 } else {
670 AUDIO_ERR_LOG("keepRunningLock is null, playback can not work well!");
671 }
672 }
673 #endif
674
675 #ifdef FEATURE_POWER_MANAGER
KeepRunningUnlock()676 void FastAudioRendererSinkInner::KeepRunningUnlock()
677 {
678 if (runningLockManager_ != nullptr) {
679 AUDIO_INFO_LOG("keepRunningLock unLock");
680 runningLockManager_->UnLock();
681 } else {
682 AUDIO_WARNING_LOG("keepRunningLock is null, playback can not work well!");
683 }
684 }
685 #endif
686
687
SetVolume(float left,float right)688 int32_t FastAudioRendererSinkInner::SetVolume(float left, float right)
689 {
690 int32_t ret;
691 float volume;
692
693 CHECK_AND_RETURN_RET_LOG(audioRender_ != nullptr, ERR_INVALID_HANDLE,
694 "FastAudioRendererSink::SetVolume failed audioRender_ null");
695
696 leftVolume_ = left;
697 rightVolume_ = right;
698 if ((leftVolume_ == 0) && (rightVolume_ != 0)) {
699 volume = rightVolume_;
700 } else if ((leftVolume_ != 0) && (rightVolume_ == 0)) {
701 volume = leftVolume_;
702 } else {
703 volume = (leftVolume_ + rightVolume_) / HALF_FACTOR;
704 }
705
706 AUDIO_INFO_LOG("Set hdi volume to %{public}f", volume);
707 ret = audioRender_->SetVolume(audioRender_, volume);
708 if (ret) {
709 AUDIO_ERR_LOG("FastAudioRendererSink::Set volume failed!");
710 }
711
712 return ret;
713 }
714
GetVolume(float & left,float & right)715 int32_t FastAudioRendererSinkInner::GetVolume(float &left, float &right)
716 {
717 left = leftVolume_;
718 right = rightVolume_;
719 return SUCCESS;
720 }
721
SetVoiceVolume(float volume)722 int32_t FastAudioRendererSinkInner::SetVoiceVolume(float volume)
723 {
724 AUDIO_ERR_LOG("FastAudioRendererSink SetVoiceVolume not supported.");
725 return ERR_NOT_SUPPORTED;
726 }
727
SetAudioScene(AudioScene audioScene,std::vector<DeviceType> & activeDevices)728 int32_t FastAudioRendererSinkInner::SetAudioScene(AudioScene audioScene, std::vector<DeviceType> &activeDevices)
729 {
730 AUDIO_ERR_LOG("FastAudioRendererSink SetAudioScene not supported.");
731 return ERR_NOT_SUPPORTED;
732 }
733
SetOutputRoutes(std::vector<DeviceType> & outputDevices)734 int32_t FastAudioRendererSinkInner::SetOutputRoutes(std::vector<DeviceType> &outputDevices)
735 {
736 AUDIO_ERR_LOG("SetOutputRoutes not supported.");
737 return ERR_NOT_SUPPORTED;
738 }
739
SetAudioParameter(const AudioParamKey key,const std::string & condition,const std::string & value)740 void FastAudioRendererSinkInner::SetAudioParameter(const AudioParamKey key, const std::string &condition,
741 const std::string &value)
742 {
743 AUDIO_ERR_LOG("FastAudioRendererSink SetAudioParameter not supported.");
744 return;
745 }
746
GetAudioParameter(const AudioParamKey key,const std::string & condition)747 std::string FastAudioRendererSinkInner::GetAudioParameter(const AudioParamKey key, const std::string &condition)
748 {
749 AUDIO_INFO_LOG("GetAudioParameter, key: %{public}d, condition: %{public}s",
750 key, condition.c_str());
751 AudioExtParamKey hdiKey = AudioExtParamKey(key);
752 char value[PARAM_VALUE_LENTH];
753 CHECK_AND_RETURN_RET_LOG(audioAdapter_ != nullptr, "",
754 "GetAudioParameter failed, audioAdapter_ is null");
755 int32_t ret = audioAdapter_->GetExtraParams(audioAdapter_, hdiKey, condition.c_str(),
756 value, PARAM_VALUE_LENTH);
757 CHECK_AND_RETURN_RET_LOG(ret == SUCCESS, "",
758 "FRSink GetAudioParameter failed, error code:%{public}d", ret);
759 return value;
760 }
761
RegisterParameterCallback(IAudioSinkCallback * callback)762 void FastAudioRendererSinkInner::RegisterParameterCallback(IAudioSinkCallback* callback)
763 {
764 AUDIO_ERR_LOG("FastAudioRendererSink RegisterParameterCallback not supported.");
765 }
766
SetAudioMonoState(bool audioMono)767 void FastAudioRendererSinkInner::SetAudioMonoState(bool audioMono)
768 {
769 AUDIO_ERR_LOG("FastAudioRendererSink SetAudioMonoState not supported.");
770 return;
771 }
772
SetAudioBalanceValue(float audioBalance)773 void FastAudioRendererSinkInner::SetAudioBalanceValue(float audioBalance)
774 {
775 AUDIO_ERR_LOG("FastAudioRendererSink SetAudioBalanceValue not supported.");
776 return;
777 }
778
GetPresentationPosition(uint64_t & frames,int64_t & timeSec,int64_t & timeNanoSec)779 int32_t FastAudioRendererSinkInner::GetPresentationPosition(uint64_t& frames, int64_t& timeSec, int64_t& timeNanoSec)
780 {
781 AUDIO_ERR_LOG("FastAudioRendererSink GetPresentationPosition not supported.");
782 return ERR_NOT_SUPPORTED;
783 }
784
GetTransactionId(uint64_t * transactionId)785 int32_t FastAudioRendererSinkInner::GetTransactionId(uint64_t *transactionId)
786 {
787 AUDIO_ERR_LOG("FastAudioRendererSink %{public}s", __func__);
788 *transactionId = 6; // 6 is the mmap device.
789 return ERR_NOT_SUPPORTED;
790 }
791
GetLatency(uint32_t * latency)792 int32_t FastAudioRendererSinkInner::GetLatency(uint32_t *latency)
793 {
794 Trace trace("FastAudioRendererSinkInner::GetLatency");
795 CHECK_AND_RETURN_RET_LOG(audioRender_ != nullptr, ERR_INVALID_HANDLE,
796 "GetLatency failed audio render null");
797
798 CHECK_AND_RETURN_RET_LOG(latency, ERR_INVALID_PARAM,
799 "GetLatency failed latency null");
800
801 uint32_t hdiLatency;
802 if (audioRender_->GetLatency(audioRender_, &hdiLatency) == 0) {
803 *latency = hdiLatency;
804 return SUCCESS;
805 } else {
806 return ERR_OPERATION_FAILED;
807 }
808 }
809
Stop(void)810 int32_t FastAudioRendererSinkInner::Stop(void)
811 {
812 std::lock_guard<std::mutex> lock(mutex_);
813 Trace trace("FastAudioRendererSinkInner::Stop");
814 AudioXCollie sourceXCollie("FastAudioRendererSinkInner::Stop", XCOLLIE_TIME_OUT_SECONDS);
815 AUDIO_INFO_LOG("Stop.");
816
817 CHECK_AND_RETURN_RET_LOG(audioRender_ != nullptr, ERR_INVALID_HANDLE,
818 "Stop failed audioRender_ null");
819 #ifdef FEATURE_POWER_MANAGER
820 KeepRunningUnlock();
821 #endif
822
823 if (started_) {
824 int32_t ret = audioRender_->Stop(audioRender_);
825 CHECK_AND_RETURN_RET_LOG(ret == 0, ERR_OPERATION_FAILED,
826 "Stop failed! ret: %{public}d.", ret);
827 }
828 started_ = false;
829
830 return SUCCESS;
831 }
832
Pause(void)833 int32_t FastAudioRendererSinkInner::Pause(void)
834 {
835 int32_t ret;
836
837 CHECK_AND_RETURN_RET_LOG(audioRender_ != nullptr, ERR_INVALID_HANDLE,
838 "Pause failed audioRender_ null");
839
840 CHECK_AND_RETURN_RET_LOG(started_, ERR_OPERATION_FAILED,
841 "Pause invalid state!");
842
843 if (!paused_) {
844 ret = audioRender_->Pause(audioRender_);
845 CHECK_AND_RETURN_RET_LOG(ret == 0, ERR_OPERATION_FAILED,
846 "Pause failed!");
847 }
848 paused_ = true;
849
850 return SUCCESS;
851 }
852
Resume(void)853 int32_t FastAudioRendererSinkInner::Resume(void)
854 {
855 Trace trace("FastAudioRendererSinkInner::Resume");
856 int32_t ret;
857
858 CHECK_AND_RETURN_RET_LOG(audioRender_ != nullptr, ERR_INVALID_HANDLE,
859 "Resume failed audioRender_ null");
860
861 CHECK_AND_RETURN_RET_LOG(started_, ERR_OPERATION_FAILED,
862 "Resume invalid state!");
863
864 if (paused_) {
865 ret = audioRender_->Resume(audioRender_);
866 CHECK_AND_RETURN_RET_LOG(ret == 0, ERR_OPERATION_FAILED,
867 "Resume failed!");
868 }
869 paused_ = false;
870
871 return SUCCESS;
872 }
873
SuspendRenderSink(void)874 int32_t FastAudioRendererSinkInner::SuspendRenderSink(void)
875 {
876 return SUCCESS;
877 }
878
RestoreRenderSink(void)879 int32_t FastAudioRendererSinkInner::RestoreRenderSink(void)
880 {
881 return SUCCESS;
882 }
883
Reset(void)884 int32_t FastAudioRendererSinkInner::Reset(void)
885 {
886 Trace trace("FastAudioRendererSinkInner::Reset");
887 int32_t ret;
888
889 if (started_ && audioRender_ != nullptr) {
890 ret = audioRender_->Flush(audioRender_);
891
892 CHECK_AND_RETURN_RET_LOG(ret == 0, ERR_OPERATION_FAILED,
893 "Reset failed!");
894 }
895
896 return SUCCESS;
897 }
898
Flush(void)899 int32_t FastAudioRendererSinkInner::Flush(void)
900 {
901 Trace trace("FastAudioRendererSinkInner::Flush");
902 int32_t ret;
903
904 if (started_ && audioRender_ != nullptr) {
905 ret = audioRender_->Flush(audioRender_);
906 CHECK_AND_RETURN_RET_LOG(ret == 0, ERR_OPERATION_FAILED,
907 "Flush failed!");
908 }
909
910 return SUCCESS;
911 }
912
ResetOutputRouteForDisconnect(DeviceType device)913 void FastAudioRendererSinkInner::ResetOutputRouteForDisconnect(DeviceType device)
914 {
915 }
916
UpdateAppsUid(const int32_t appsUid[MAX_MIX_CHANNELS],const size_t size)917 int32_t FastAudioRendererSinkInner::UpdateAppsUid(const int32_t appsUid[MAX_MIX_CHANNELS],
918 const size_t size)
919 {
920 return SUCCESS;
921 }
922
UpdateAppsUid(const std::vector<int32_t> & appsUid)923 int32_t FastAudioRendererSinkInner::UpdateAppsUid(const std::vector<int32_t> &appsUid)
924 {
925 #ifdef FEATURE_POWER_MANAGER
926 if (!runningLockManager_) {
927 return ERROR;
928 }
929
930 runningLockManager_->UpdateAppsUid(appsUid.cbegin(), appsUid.cend());
931 runningLockManager_->UpdateAppsUidToPowerMgr();
932 #endif
933
934 return SUCCESS;
935 }
936
937 } // namespace AudioStandard
938 } // namespace OHOS
939