1 /*
2  * Copyright (c) 2020-2021 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 #include "player_impl.h"
17 #include <cinttypes>
18 #include <climits>
19 #include <string>
20 #include <sys/prctl.h>
21 #include "unistd.h"
22 #include "securec.h"
23 #include "format_type.h"
24 #include "hi_liteplayer_err.h"
25 #include "hi_liteplayer.h"
26 #include "player_define.h"
27 #include "media_log.h"
28 extern "C"
29 {
30 #include "codec_interface.h"
31 }
32 
33 using namespace std;
34 using OHOS::Media::AdapterStreamCallback;
35 
36 namespace OHOS {
37 namespace Media {
38 const int32_t INVALID_MEDIA_POSITION = -1;
39 const int32_t DEFAULT_REWIND_TIME = 0;
40 const int32_t IDLE_QUEQUE_SLEEP_TIME_US = 5000;
41 const float MAX_MEDIA_VOLUME = 300.0f;
42 const int32_t POS_NOTIFY_INTERVAL_MS = 300;
43 
44 #define CHECK_FAILED_PRINT(value, target, printfString) \
45 do { \
46     if ((value) != (target)) { \
47         MEDIA_ERR_LOG("%s", printfString ? printfString : " "); \
48     } \
49 } while (0)
50 
51 #define CHECK_FAILED_RETURN(value, target, ret, printfString) \
52 do { \
53     if ((value) != (target)) { \
54         MEDIA_ERR_LOG("%s, ret:%d", printfString ? printfString : " ", ret); \
55         return ret; \
56     } \
57 } while (0)
58 
59 #define CHK_NULL_RETURN(ptr) \
60 do { \
61     if (ptr == nullptr) { \
62         MEDIA_ERR_LOG("ptr null"); \
63         return -1; \
64     } \
65 } while (0)
66 
PlayerImpl()67 PlayerImpl::PlayerImpl()
68     : player_(nullptr), speed_(1.0), playerControlState_(PLAY_STATUS_IDLE),
69       isSingleLoop_(false),
70       currentPosition_(0),
71       rewindPosition_(INVALID_MEDIA_POSITION),
72       surface_(nullptr),
73       currentState_(PLAYER_IDLE),
74       rewindMode_(PLAYER_SEEK_PREVIOUS_SYNC),
75       currentRewindMode_(PLAYER_SEEK_PREVIOUS_SYNC),
76       audioStreamType_(0),
77       callback_(nullptr),
78       inited_ (false),
79       released_(false),
80       isStreamSource_(false),
81       bufferSource_(nullptr),
82       streamCallback_(nullptr),
83       pauseAfterPlay_(false),
84       extraRewind_(false)
85 {
86     (void)memset_s(&formatFileInfo_, sizeof(formatFileInfo_), 0, sizeof(FormatFileInfo));
87     formatFileInfo_.s32UsedVideoStreamIndex = -1;
88     formatFileInfo_.s32UsedAudioStreamIndex = -1;
89     formatFileInfo_.s64Duration = -1;
90     buffer_.idx = -1;
91     buffer_.flag = 0;
92     buffer_.offset = 0;
93     buffer_.size = 0;
94     buffer_.timestamp = 0;
95     (void)memset_s(&mediaAttr_, sizeof(mediaAttr_), 0, sizeof(PlayerControlStreamAttr));
96 }
97 
Init(void)98 int32_t PlayerImpl::Init(void)
99 {
100     if (inited_ == true) {
101         return 0;
102     }
103     int ret = CodecInit();
104     if (ret != 0) {
105 		MEDIA_ERR_LOG("PlayerImpl::Init CodecInit err\n");
106         return ret;
107     }
108     if (memset_s(&buffer_, sizeof(QueBuffer), 0, sizeof(QueBuffer)) != EOK) {
109         MEDIA_ERR_LOG("PlayerImpl::Init memset err\n");
110     }
111     buffer_.idx = -1;
112     inited_ = true;
113     MEDIA_INFO_LOG("process success");
114     return 0;
115 }
116 
DeInit(void)117 int32_t PlayerImpl::DeInit(void)
118 {
119     if (inited_ != true) {
120         return 0;
121     }
122     if (released_ == false) {
123         Release();
124     }
125     inited_ = false;
126     return 0;
127 }
128 
~PlayerImpl()129 PlayerImpl::~PlayerImpl()
130 {
131     DeInit();
132     player_ = nullptr;
133     MEDIA_INFO_LOG("~PlayerImpl process");
134 }
135 
SetSource(const Source & source)136 int32_t PlayerImpl::SetSource(const Source &source)
137 {
138     Init();
139     std::lock_guard<std::mutex> valueLock(lock_);
140     MEDIA_INFO_LOG("process in");
141     CHECK_FAILED_RETURN(released_, false, -1, "have released or not create");
142     if (currentState_ != PLAYER_IDLE) {
143         MEDIA_ERR_LOG("failed, current state is:%u", currentState_);
144         return -1;
145     }
146 
147     SourceType sType = source.GetSourceType();
148     if (sType == SourceType::SOURCE_TYPE_FD) {
149         MEDIA_ERR_LOG("not support fdSource now");
150         return -1;
151     }
152 
153     GetPlayer();
154     CHK_NULL_RETURN(player_);
155 
156     int32_t ret = -1;
157     if (sType == SourceType::SOURCE_TYPE_URI) {
158         ret = SetUriSource(source);
159     } else if (sType == SourceType::SOURCE_TYPE_STREAM) {
160         ret = SetStreamSource(source);
161     } else {
162         MEDIA_ERR_LOG("SetSource failed, source type is %d", static_cast<int32_t>(sType));
163     }
164 
165     if (ret != 0) {
166         ResetInner();
167     }
168     return ret;
169 }
170 
ShowFileInfo(const FormatFileInfo * fileInfo)171 static void ShowFileInfo(const FormatFileInfo *fileInfo)
172 {
173     for (int i = 0; i < HI_DEMUXER_RESOLUTION_CNT; i++) {
174         const StreamResolution *resolution = &fileInfo->stSteamResolution[i];
175         if (resolution->u32Width == 0 || resolution->u32Height == 0) {
176             break;
177         }
178         MEDIA_INFO_LOG("video[%d],w=%u,h=%u,index=%d ", i, resolution->u32Width,
179             resolution->u32Height, resolution->s32VideoStreamIndex);
180     }
181     MEDIA_INFO_LOG("audio channel_cnt=%u,sampleRate=%u,AudioStreamIndex=%d videoIndex:%d",
182         fileInfo->u32AudioChannelCnt, fileInfo->u32SampleRate, fileInfo->s32UsedAudioStreamIndex,
183         fileInfo->s32UsedVideoStreamIndex);
184 }
185 
UpdateState(PlayerImpl * curPlayer,PlayerStatus state)186 void PlayerImpl::UpdateState(PlayerImpl *curPlayer, PlayerStatus state)
187 {
188     if (curPlayer == nullptr) {
189         return;
190     }
191 
192     curPlayer->playerControlState_ = state;
193     MEDIA_INFO_LOG("player UpdateState, state:%d", state);
194 }
195 
PlayerControlEventCb(void * pPlayer,PlayerControlEvent enEvent,const void * pData)196 void PlayerImpl::PlayerControlEventCb(void* pPlayer, PlayerControlEvent enEvent, const void* pData)
197 {
198     PlayerControlError subErr = PLAYERCONTROL_ERROR_BUTT;
199     PlayerImpl *curPlayer = (PlayerImpl *)pPlayer;
200 
201     if (curPlayer == nullptr) {
202         MEDIA_ERR_LOG("the handle is error");
203         return;
204     }
205     switch (enEvent) {
206         case PLAYERCONTROL_EVENT_STATE_CHANGED:
207             if (pData == nullptr) {
208                 return;
209             }
210             curPlayer->UpdateState(curPlayer, *reinterpret_cast<const PlayerStatus *>(pData));
211             break;
212         case PLAYERCONTROL_EVENT_EOF:
213             MEDIA_INFO_LOG("end of file");
214             curPlayer->NotifyPlaybackComplete(curPlayer);
215             break;
216         case PLAYERCONTROL_EVENT_SOF:
217             MEDIA_INFO_LOG("start of file");
218             break;
219         case PLAYERCONTROL_EVENT_ERROR:
220             if (pData == nullptr) {
221                 return;
222             }
223             subErr = *reinterpret_cast<const PlayerControlError *>(pData);
224             MEDIA_ERR_LOG("error: %d", subErr);
225             if (curPlayer->callback_ != nullptr) {
226                 curPlayer->callback_->OnError(0, subErr);
227             }
228             break;
229         case PLAYERCONTROL_EVENT_PROGRESS:
230             if (pData == nullptr) {
231                 return;
232             }
233             curPlayer->currentPosition_ = *reinterpret_cast<const int64_t *>(pData);
234             break;
235         case PLAYERCONTROL_EVENT_SEEK_END:
236             if (pData == nullptr) {
237                 return;
238             }
239             MEDIA_INFO_LOG("seek action end, time is %lld",  *reinterpret_cast<const int64_t *>(pData));
240             curPlayer->NotifySeekComplete(curPlayer, *reinterpret_cast<const int64_t *>(pData));
241             break;
242         case PLAYERCONTROL_FIRST_VIDEO_FRAME:
243             MEDIA_INFO_LOG("render FirstVideoFrame");
244             if (curPlayer->pauseAfterPlay_) {
245                 curPlayer->player_->Pause();
246             }
247             break;
248         case PLAYERCONTROL_FIRST_AUDIO_FRAME:
249             if (curPlayer->pauseAfterPlay_ && curPlayer->formatFileInfo_.s32UsedVideoStreamIndex == -1) {
250                 curPlayer->player_->Pause();
251             }
252             break;
253         default:
254             break;
255     }
256 }
257 
ReportVideoSizeChange(void)258 void PlayerImpl::ReportVideoSizeChange(void)
259 {
260     for (int i = 0; i < HI_DEMUXER_RESOLUTION_CNT; i++) {
261         if (formatFileInfo_.stSteamResolution[i].s32VideoStreamIndex == formatFileInfo_.s32UsedVideoStreamIndex) {
262             if (callback_ != nullptr) {
263                 callback_->OnVideoSizeChanged(formatFileInfo_.stSteamResolution[i].u32Width,
264                     formatFileInfo_.stSteamResolution[i].u32Height);
265             }
266             break;
267         }
268     }
269 }
270 
Prepare()271 int32_t PlayerImpl::Prepare()
272 {
273     std::lock_guard<std::mutex> valueLock(lock_);
274     MEDIA_INFO_LOG("process in");
275     CHECK_FAILED_RETURN(released_, false, -1, "have released or not create");
276     CHK_NULL_RETURN(player_);
277 
278     if (currentState_ == PLAYER_PREPARED) {
279         MEDIA_ERR_LOG("have operated prepare before");
280         return 0;
281     }
282     if (currentState_ != PLAYER_INITIALIZED) {
283         MEDIA_ERR_LOG("Can not Prepare, currentState_ is %u", currentState_);
284         return -1;
285     }
286 
287     PlayerCtrlCallbackParam param;
288     param.player = this;
289     param.callbackFun = PlayerControlEventCb;
290     int ret = player_->RegCallback(param);
291     if (ret != 0) {
292         MEDIA_ERR_LOG("RegCallback exec failed ");
293         return -1;
294     }
295 
296     currentState_ = PLAYER_PREPARING;
297     ret = player_->Prepare();
298     if (ret != 0) {
299         MEDIA_ERR_LOG("Prepare exec failed");
300         currentState_ = PLAYER_INITIALIZED;
301         return -1;
302     }
303     currentState_ = PLAYER_PREPARED;
304     (void)player_->SetAudioStreamType(audioStreamType_);
305 
306     ret = player_->GetFileInfo(formatFileInfo_);
307     if (ret != 0) {
308         MEDIA_ERR_LOG("GetFileInfo failed");
309         return ret;
310     }
311     ShowFileInfo(&formatFileInfo_);
312     if (formatFileInfo_.s32UsedVideoStreamIndex == -1) {
313         MEDIA_INFO_LOG("process out");
314         return 0;
315     }
316 
317     /* report video solution */
318     ReportVideoSizeChange();
319     MEDIA_INFO_LOG("process out");
320     return 0;
321 }
322 
SetMediaStream(void)323 int32_t PlayerImpl::SetMediaStream(void)
324 {
325     int32_t ret;
326 
327     mediaAttr_.s32VidStreamId = formatFileInfo_.s32UsedVideoStreamIndex;
328     mediaAttr_.s32AudStreamId = formatFileInfo_.s32UsedAudioStreamIndex;
329     ret = player_->SetMedia(mediaAttr_);
330     if (ret != 0) {
331         MEDIA_ERR_LOG("SetMedia  exec failed");
332         return  ret;
333     }
334 
335     for (int i = 0; i < HI_DEMUXER_RESOLUTION_CNT; i++) {
336         StreamResolution *resolution = &formatFileInfo_.stSteamResolution[i];
337         if (resolution->s32VideoStreamIndex == mediaAttr_.s32VidStreamId) {
338             MEDIA_INFO_LOG("used video w=%u,h=%u,index=%d",
339                 resolution->u32Width, resolution->u32Height, mediaAttr_.s32VidStreamId);
340             break;
341         }
342     }
343     return 0;
344 }
345 
Play()346 int32_t PlayerImpl::Play()
347 {
348     std::lock_guard<std::mutex> valueLock(lock_);
349     int ret;
350     MEDIA_INFO_LOG("process in");
351     CHECK_FAILED_RETURN(released_, false, -1, "have released or not create");
352     CHK_NULL_RETURN(player_);
353     if (currentState_ == PLAYER_STARTED) {
354         MEDIA_INFO_LOG("no need to repeat operation");
355         return 0;
356     }
357     if (currentState_ != PLAYER_PREPARED && currentState_ != PLAYER_PAUSED) {
358         MEDIA_ERR_LOG("Can not Play, currentState is %u", currentState_);
359         return -1;
360     }
361     if (currentState_ == PLAYER_PAUSED) {
362         goto play;
363     }
364 
365     ret = SetMediaStream();
366     CHECK_FAILED_RETURN(ret, 0, ret, "SetMeidaStream failed");
367 play:
368     ret = player_->Play();
369     if (ret != 0) {
370         MEDIA_ERR_LOG("Play exec failed %x", ret);
371         return -1;
372     }
373     currentState_ = PLAYER_STARTED;
374     MEDIA_INFO_LOG("process out");
375     return 0;
376 }
377 
IsPlaying()378 bool PlayerImpl::IsPlaying()
379 {
380     std::lock_guard<std::mutex> valueLock(lock_);
381     MEDIA_INFO_LOG("process in");
382     CHECK_FAILED_RETURN(released_, false, 0, "have released or not create");
383     bool isPlaying = false;
384     if (player_ != nullptr) {
385         isPlaying = (currentState_ != PLAYER_STARTED) ? false : true;
386     }
387     return isPlaying;
388 }
389 
Pause()390 int32_t PlayerImpl::Pause()
391 {
392     std::lock_guard<std::mutex> valueLock(lock_);
393     MEDIA_INFO_LOG("process in");
394     CHECK_FAILED_RETURN(released_, false, -1, "have released or not create");
395     CHK_NULL_RETURN(player_);
396     if (currentState_ == PLAYER_PAUSED) {
397         MEDIA_ERR_LOG("currentState_ is %d", currentState_);
398         return 0;
399     }
400     if (speed_ != 1.0) {
401         MEDIA_ERR_LOG("failed, currentState_ speed is %f", speed_);
402         return -1;
403     }
404     if (pauseAfterPlay_ && currentState_ == PLAYER_PREPARED) {
405         int32_t ret;
406         ret = SetMediaStream();
407         CHECK_FAILED_RETURN(ret, 0, ret, "SetMeidaStream failed");
408         ret = player_->Play();
409         CHECK_FAILED_RETURN(ret, 0, ret, "Play failed");
410         currentState_ = PLAYER_PAUSED;
411         return 0;
412     }
413     if (currentState_ != PLAYER_STARTED) {
414         MEDIA_ERR_LOG("Can not Pause, currentState_ is %u", currentState_);
415         return -1;
416     }
417 
418     player_->Pause();
419     currentState_ = PLAYER_PAUSED;
420     return 0;
421 }
422 
Stop()423 int32_t PlayerImpl::Stop()
424 {
425     std::lock_guard<std::mutex> valueLock(lock_);
426     MEDIA_INFO_LOG("process in");
427     CHECK_FAILED_RETURN(released_, false, -1, "have released or not create");
428     if (currentState_ == PLAYER_STOPPED) {
429         return 0;
430     }
431     if ((currentState_ != PLAYER_STARTED) && (currentState_ != PLAYER_PAUSED) &&
432         (currentState_ != PLAYER_PLAYBACK_COMPLETE) && (currentState_ != PLAYER_STATE_ERROR)) {
433         MEDIA_INFO_LOG("current state: %u, no need to do stop", currentState_);
434         return -1;
435     }
436 
437     if (player_ != nullptr) {
438         int32_t ret = player_->Stop();
439         if (ret != 0) {
440             MEDIA_ERR_LOG("Stop failed, ret is %d", ret);
441         }
442     }
443     currentState_ = PLAYER_STOPPED;
444     MEDIA_INFO_LOG("process out");
445     return 0;
446 }
447 
RewindInner(int64_t mSeconds,PlayerSeekMode mode)448 int32_t PlayerImpl::RewindInner(int64_t mSeconds, PlayerSeekMode mode)
449 {
450     MEDIA_INFO_LOG("process in");
451     CHK_NULL_RETURN(player_);
452     if (mSeconds < DEFAULT_REWIND_TIME) {
453         MEDIA_WARNING_LOG("Attempt to rewind to invalid position %lld", mSeconds);
454         mSeconds = DEFAULT_REWIND_TIME;
455     }
456     int32_t ret;
457     int64_t durationMs = -1;
458     GetDurationInner(durationMs);
459     if ((durationMs > DEFAULT_REWIND_TIME) && (mSeconds > durationMs)) {
460         MEDIA_WARNING_LOG("Attempt to rewind to past end of file, request is %lld, durationMs is %lld", mSeconds,
461             durationMs);
462         return -1;
463     }
464     currentRewindMode_ = mode;
465     if (rewindPosition_ >= DEFAULT_REWIND_TIME) {
466         rewindPosition_ = mSeconds;
467         MEDIA_WARNING_LOG("is deal last rewind time:%lld", mSeconds);
468         return 0;
469     }
470 
471     rewindPosition_ = mSeconds;
472     rewindMode_ = mode;
473     ret = player_->Seek(mSeconds);
474     if (ret != 0) {
475         MEDIA_ERR_LOG("do seek failed, ret is %d", ret);
476     }
477     MEDIA_INFO_LOG("process out");
478     return ret;
479 }
480 
IsValidRewindMode(PlayerSeekMode mode)481 bool PlayerImpl::IsValidRewindMode(PlayerSeekMode mode)
482 {
483     switch (mode) {
484         case PLAYER_SEEK_PREVIOUS_SYNC:
485         case PLAYER_SEEK_NEXT_SYNC:
486         case PLAYER_SEEK_CLOSEST_SYNC:
487         case PLAYER_SEEK_CLOSEST:
488             break;
489         default:
490             MEDIA_ERR_LOG("Unknown rewind mode %d", mode);
491             return false;
492     }
493     return true;
494 }
495 
Rewind(int64_t mSeconds,int32_t mode)496 int32_t PlayerImpl::Rewind(int64_t mSeconds, int32_t mode)
497 {
498     std::lock_guard<std::mutex> valueLock(lock_);
499     MEDIA_INFO_LOG("process in");
500     CHECK_FAILED_RETURN(released_, false, -1, "have released or not create");
501     if (currentState_ != PLAYER_STARTED && currentState_ != PLAYER_PAUSED && currentState_ != PLAYER_PREPARED) {
502         MEDIA_ERR_LOG("Can not Rewind, currentState_ is %u", currentState_);
503         return -1;
504     }
505     if (speed_ != 1.0) {
506         MEDIA_ERR_LOG("Can not Rewind, currentState_ speed is %f", speed_);
507         return -1;
508     }
509 
510     if (IsValidRewindMode((PlayerSeekMode)mode) != true) {
511         MEDIA_ERR_LOG("Rewind failed, msec is %lld, mode is %d", mSeconds, mode);
512         return -1;
513     }
514 
515     if (isStreamSource_ == true) {
516         MEDIA_ERR_LOG("Failed, streamsource not support Rewind");
517         return -1;
518     }
519 
520     std::lock_guard<std::mutex> rewindLock(rewindLock_);
521     int32_t ret = RewindInner(mSeconds, (PlayerSeekMode)mode);
522     if (ret != 0) {
523         MEDIA_ERR_LOG("ReWind failed, ret is %d", ret);
524     } else {
525         currentPosition_ = mSeconds;
526         extraRewind_ = true;
527     }
528     MEDIA_INFO_LOG("process out");
529     return ret;
530 }
531 
SetVolume(float leftVolume,float rightVolume)532 int32_t PlayerImpl::SetVolume(float leftVolume, float rightVolume)
533 {
534     std::lock_guard<std::mutex> valueLock(lock_);
535     MEDIA_INFO_LOG("process in");
536     VolumeAttr attr;
537     CHECK_FAILED_RETURN(released_, false, -1, "have released or not create");
538     CHK_NULL_RETURN(player_);
539     if ((currentState_ != PLAYER_STARTED) && (currentState_ != PLAYER_PAUSED) &&
540         (currentState_ != PLAYER_PREPARED) && (currentState_ != PLAYER_INITIALIZED)) {
541         MEDIA_ERR_LOG("SetVolume failed, currentState_ is %u", currentState_);
542         return -1;
543     }
544     if (leftVolume < 0 || leftVolume > MAX_MEDIA_VOLUME || rightVolume < 0 || rightVolume > MAX_MEDIA_VOLUME) {
545         MEDIA_ERR_LOG("SetVolume failed, the volume should be set to a value ranging from 0 to 300");
546         return -1;
547     }
548     attr.leftVolume = leftVolume;
549     attr.rightVolume = rightVolume;
550     int ret = player_->SetVolume(attr);
551     if (ret != 0) {
552         MEDIA_ERR_LOG("SetVolume failed %x", ret);
553     }
554     MEDIA_INFO_LOG("process out\n");
555     return ret;
556 }
557 
SetSurface(Surface * surface)558 int32_t PlayerImpl::SetSurface(Surface *surface)
559 {
560     std::lock_guard<std::mutex> valueLock(lock_);
561     MEDIA_INFO_LOG("process in");
562     CHECK_FAILED_RETURN(released_, false, -1, "have released or not create");
563     if ((currentState_ != PLAYER_PREPARED) && (currentState_ != PLAYER_INITIALIZED)) {
564         MEDIA_ERR_LOG("SetSurface failed, currentState_ is %u", currentState_);
565         return -1;
566     }
567     surface_ = surface;
568     player_->SetSurface(surface);
569     return 0;
570 }
571 
IsSingleLooping()572 bool PlayerImpl::IsSingleLooping()
573 {
574     std::lock_guard<std::mutex> valueLock(lock_);
575     CHECK_FAILED_RETURN(released_, false, false, "have released or not create");
576     bool isLoop = (player_ == nullptr) ? false : isSingleLoop_;
577     return isLoop;
578 }
579 
GetPlayerState(int32_t & state)580 int32_t PlayerImpl::GetPlayerState(int32_t &state)
581 {
582     std::lock_guard<std::mutex> valueLock(lock_);
583     CHECK_FAILED_RETURN(released_, false, -1, "have released or not create");
584     state = currentState_;
585     return 0;
586 }
587 
GetCurrentPosition(int64_t & position)588 int32_t PlayerImpl::GetCurrentPosition(int64_t &position)
589 {
590     std::lock_guard<std::mutex> valueLock(lock_);
591     CHECK_FAILED_RETURN(released_, false, -1, "have released or not create");
592     position = (currentPosition_ >= 0) ? currentPosition_ : 0;
593     return 0;
594 }
595 
GetDurationInner(int64_t & durationMs)596 void PlayerImpl::GetDurationInner(int64_t &durationMs)
597 {
598     durationMs = formatFileInfo_.s64Duration;
599 }
600 
GetDuration(int64_t & durationMs)601 int32_t PlayerImpl::GetDuration(int64_t &durationMs)
602 {
603     std::lock_guard<std::mutex> valueLock(lock_);
604     MEDIA_INFO_LOG("process in");
605     CHECK_FAILED_RETURN(released_, false, -1, "have released or not create");
606     if (currentState_ == PLAYER_IDLE || currentState_ == PLAYER_INITIALIZED) {
607         durationMs = 0;
608         return 0;
609     }
610     GetDurationInner(durationMs);
611     return 0;
612 }
613 
GetVideoWidth(int32_t & videoWidth)614 int32_t PlayerImpl::GetVideoWidth(int32_t &videoWidth)
615 {
616     std::lock_guard<std::mutex> valueLock(lock_);
617     MEDIA_INFO_LOG("process in");
618     CHECK_FAILED_RETURN(released_, false, -1, "have released or not create");
619 
620     videoWidth = 0;
621     if (currentState_ != PLAYER_PREPARED && currentState_ != PLAYER_STARTED && currentState_ != PLAYER_PAUSED &&
622         currentState_ != PLAYER_STOPPED && currentState_ != PLAYER_PLAYBACK_COMPLETE) {
623         MEDIA_ERR_LOG("Can not GetVideoWidth, currentState_ is %u", currentState_);
624         return -1;
625     }
626 
627     if (formatFileInfo_.s32UsedVideoStreamIndex == -1) {
628         return -1;
629     }
630     for (int i = 0; i < HI_DEMUXER_RESOLUTION_CNT; i++) {
631         if (formatFileInfo_.stSteamResolution[i].s32VideoStreamIndex == formatFileInfo_.s32UsedVideoStreamIndex) {
632             videoWidth = formatFileInfo_.stSteamResolution[i].u32Width;
633             break;
634         }
635     }
636     return 0;
637 }
638 
GetVideoHeight(int32_t & videoHeight)639 int32_t PlayerImpl::GetVideoHeight(int32_t &videoHeight)
640 {
641     std::lock_guard<std::mutex> valueLock(lock_);
642     MEDIA_INFO_LOG("process in");
643     CHECK_FAILED_RETURN(released_, false, -1, "have released or not create");
644 
645     videoHeight = 0;
646     if (currentState_ != PLAYER_PREPARED && currentState_ != PLAYER_STARTED && currentState_ != PLAYER_PAUSED &&
647         currentState_ != PLAYER_STOPPED && currentState_ != PLAYER_PLAYBACK_COMPLETE) {
648         MEDIA_ERR_LOG("Can not GetVideoHeight, currentState_ is %u", currentState_);
649         return -1;
650     }
651     if (formatFileInfo_.s32UsedVideoStreamIndex == -1) {
652         return -1;
653     }
654 
655     for (int i = 0; i < HI_DEMUXER_RESOLUTION_CNT; i++) {
656         if (formatFileInfo_.stSteamResolution[i].s32VideoStreamIndex == formatFileInfo_.s32UsedVideoStreamIndex) {
657             videoHeight = formatFileInfo_.stSteamResolution[i].u32Height;
658             break;
659         }
660     }
661     return 0;
662 }
663 
PlayerControlCheckTPlayAttr(const float speed,TplayDirect direction)664 static int32_t PlayerControlCheckTPlayAttr(const float speed, TplayDirect direction)
665 {
666     if ((direction != TPLAY_DIRECT_BACKWARD) && (direction != TPLAY_DIRECT_FORWARD)) {
667         return HI_FAILURE;
668     }
669 
670     if (speed != PLAY_SPEED_2X_FAST &&
671         speed != PLAY_SPEED_4X_FAST &&
672         speed != PLAY_SPEED_8X_FAST &&
673         speed != PLAY_SPEED_16X_FAST &&
674         speed != PLAY_SPEED_32X_FAST &&
675         speed != PLAY_SPEED_64X_FAST &&
676         speed != PLAY_SPEED_128X_FAST) {
677         return HI_FAILURE;
678     }
679 
680     return HI_SUCCESS;
681 }
682 
SetPlaybackSpeed(float speed)683 int32_t PlayerImpl::SetPlaybackSpeed(float speed)
684 {
685     std::lock_guard<std::mutex> valueLock(lock_);
686     CHECK_FAILED_RETURN(released_, false, -1, "have released or not create");
687     if (speed <= 0.f) {
688         return -1;
689     }
690     CHK_NULL_RETURN(player_);
691     if (currentState_ != PLAYER_STARTED) {
692         MEDIA_ERR_LOG("currentState_ is %u", currentState_);
693         return -1;
694     }
695     if (speed == speed_) {
696         return 0;
697     }
698     if ((isStreamSource_ == true) && (speed != 1.0f)) {
699         MEDIA_ERR_LOG("Failed, streamsource not support abnormal speed");
700         return -1;
701     }
702 
703     if (formatFileInfo_.s32UsedVideoStreamIndex == -1) {
704         MEDIA_ERR_LOG("audio movie not support abnormal speed");
705         return -1;
706     }
707 
708     if (speed_ > 1 && speed == 1) { // tplay  ---> play
709         CHECK_FAILED_PRINT(player_->Play(), 0, "player failed");
710     } else { // normal/tplay -->tplay
711         TplayAttr tplayAttr;
712         TplayDirect direction = (speed > 0) ? TPLAY_DIRECT_FORWARD : TPLAY_DIRECT_BACKWARD;
713         float speedTmp = (speed > 0) ? speed : -speed;
714         tplayAttr.direction = direction;
715         tplayAttr.speed = speedTmp;
716         if (PlayerControlCheckTPlayAttr(speedTmp, direction) != 0) {
717             MEDIA_ERR_LOG("not support speed:%f", speed);
718             return -1;
719         }
720         CHECK_FAILED_PRINT(player_->TPlay(tplayAttr), 0, "tplayer failed");
721     }
722 
723     if (speed == 0.f && currentState_ == PLAYER_STARTED) {
724         currentState_ = PLAYER_PAUSED;
725     } else if (speed != 0.f && (currentState_ == PLAYER_PREPARED || currentState_ == PLAYER_PAUSED)) {
726         currentState_ = PLAYER_STARTED;
727     }
728     speed_ = speed;
729     return 0;
730 }
731 
GetPlaybackSpeed(float & speed)732 int32_t PlayerImpl::GetPlaybackSpeed(float &speed)
733 {
734     std::lock_guard<std::mutex> valueLock(lock_);
735     CHECK_FAILED_RETURN(released_, false, -1, "have released or not create");
736     speed = (currentState_ != PLAYER_PAUSED) ? speed_ : 0;
737     return 0;
738 }
739 
SetAudioStreamType(int32_t type)740 int32_t PlayerImpl::SetAudioStreamType(int32_t type)
741 {
742     std::lock_guard<std::mutex> valueLock(lock_);
743     MEDIA_INFO_LOG("process in");
744     CHECK_FAILED_RETURN(released_, false, -1, "have released or not create");
745     if (currentState_ != PLAYER_IDLE && currentState_ != PLAYER_INITIALIZED) {
746         MEDIA_ERR_LOG("failed, state %u,type:%d", currentState_, type);
747         return -1;
748     }
749     audioStreamType_ = type;
750 
751     if (player_ != nullptr) {
752         player_->SetAudioStreamType(type);
753     }
754     return 0;
755 }
756 
GetAudioStreamType(int32_t & type)757 void PlayerImpl::GetAudioStreamType(int32_t &type)
758 {
759     std::lock_guard<std::mutex> valueLock(lock_);
760     if (released_) {
761         MEDIA_ERR_LOG("have released or not create");
762         return;
763     }
764     type = static_cast<int32_t>(audioStreamType_);
765 }
766 
ResetInner(void)767 void PlayerImpl::ResetInner(void)
768 {
769     isSingleLoop_ = false;
770     if (player_ != nullptr) {
771         if (currentState_ != PLAYER_IDLE && currentState_ != PLAYER_STOPPED) {
772             CHECK_FAILED_PRINT(player_->Stop(), HI_SUCCESS, "stop failed");
773         }
774         (void)player_->Deinit();
775         player_.reset();
776         player_ = nullptr;
777     }
778     if (bufferSource_ != nullptr) {
779         bufferSource_.reset();
780         bufferSource_ = nullptr;
781     }
782     if (streamCallback_ != nullptr) {
783         streamCallback_.reset();
784         streamCallback_ = nullptr;
785     }
786 
787     currentState_ = PLAYER_IDLE;
788     currentRewindMode_ = PLAYER_SEEK_PREVIOUS_SYNC;
789     rewindPosition_ = INVALID_MEDIA_POSITION;
790     rewindMode_ = PLAYER_SEEK_PREVIOUS_SYNC;
791     isSingleLoop_ = false;
792     speed_ = 1.0;
793     currentPosition_ = 0;
794     pauseAfterPlay_ = false;
795     extraRewind_ = false;
796     playerControlState_ = PLAY_STATUS_IDLE;
797     isStreamSource_ = false;
798     (void)memset_s(&formatFileInfo_, sizeof(FormatFileInfo), 0, sizeof(FormatFileInfo));
799     formatFileInfo_.s32UsedVideoStreamIndex = -1;
800     formatFileInfo_.s32UsedAudioStreamIndex = -1;
801     formatFileInfo_.s64Duration = -1;
802     (void)memset_s(&mediaAttr_, sizeof(PlayerControlStreamAttr), 0, sizeof(PlayerControlStreamAttr));
803     (void)memset_s(&buffer_, sizeof(QueBuffer), 0, sizeof(QueBuffer));
804     buffer_.idx = -1;
805 }
806 
Reset(void)807 int32_t PlayerImpl::Reset(void)
808 {
809     std::lock_guard<std::mutex> valueLock(lock_);
810     MEDIA_INFO_LOG("process in");
811     CHECK_FAILED_RETURN(released_, false, -1, "have released or not create");
812     if (currentState_ == PLAYER_IDLE) {
813         return 0;
814     }
815     ResetInner();
816     return 0;
817 }
818 
Release()819 int32_t PlayerImpl::Release()
820 {
821     std::lock_guard<std::mutex> valueLock(lock_);
822     MEDIA_INFO_LOG("process in");
823     CHECK_FAILED_RETURN(released_, false, 0, "have released or not create");
824     ResetInner();
825 
826     if (callback_ != nullptr) {
827         callback_.reset();
828         callback_ = nullptr;
829     }
830     currentState_ = PLAYER_STATE_ERROR;
831     released_ = true;
832     return 0;
833 }
834 
CreatePlayerParamCheck(PlayerControlParam & createParam)835 int PlayerImpl::CreatePlayerParamCheck(PlayerControlParam &createParam)
836 {
837     if (createParam.u32PlayPosNotifyIntervalMs < MIN_NOTIFY_INTERVAL_MS
838         && createParam.u32PlayPosNotifyIntervalMs > 0) {
839         MEDIA_ERR_LOG("notify interval small than min value %d", MIN_NOTIFY_INTERVAL_MS);
840         return HI_ERR_PLAYERCONTROL_ILLEGAL_PARAM;
841     }
842     if ((createParam.u32VideoEsBufSize < AV_ESBUF_SIZE_MIN && createParam.u32VideoEsBufSize > 0)
843         || createParam.u32VideoEsBufSize > VIDEO_ESBUF_SIZE_LIMIT) {
844         MEDIA_ERR_LOG("video esbuffer illegal %u", createParam.u32VideoEsBufSize);
845         return HI_ERR_PLAYERCONTROL_ILLEGAL_PARAM;
846     }
847     if ((createParam.u32AudioEsBufSize < AV_ESBUF_SIZE_MIN && createParam.u32AudioEsBufSize > 0)
848         || createParam.u32AudioEsBufSize > AUDIO_ESBUF_SIZE_LIMIT) {
849         MEDIA_ERR_LOG("audio esbuffer illegal %u", createParam.u32VideoEsBufSize);
850         return HI_ERR_PLAYERCONTROL_ILLEGAL_PARAM;
851     }
852     if ((createParam.u32VdecFrameBufCnt < VDEC_VBBUF_CONUT_MIN) &&
853         (createParam.u32VdecFrameBufCnt != 0)) {
854         MEDIA_ERR_LOG("VDEC vb buffer count %u small than %d", createParam.u32VdecFrameBufCnt, VDEC_VBBUF_CONUT_MIN);
855         return HI_ERR_PLAYERCONTROL_ILLEGAL_PARAM;
856     }
857     return 0;
858 }
859 
GetPlayer()860 int PlayerImpl::GetPlayer()
861 {
862     MEDIA_INFO_LOG("process in");
863     PlayerControlParam playerParam;
864     if (player_ != nullptr) {
865         return 0;
866     }
867     if (memset_s(&playerParam, sizeof(PlayerControlParam), 0x00, sizeof(playerParam)) != EOK) {
868         MEDIA_INFO_LOG("memset_s playerParam failed");
869         return -1;
870     }
871 
872     playerParam.u32PlayPosNotifyIntervalMs = POS_NOTIFY_INTERVAL_MS;
873     if (CreatePlayerParamCheck(playerParam) != 0) {
874         MEDIA_ERR_LOG("CreatePlayerParamCheck failed");
875         return -1;
876     }
877     player_ = std::make_shared<PlayerControl>();
878     if (player_ == nullptr || player_.get() == nullptr) {
879         MEDIA_ERR_LOG("playerControl new failed");
880         return HI_ERR_PLAYERCONTROL_MEM_MALLOC;
881     }
882     if (player_->Init(playerParam) != HI_SUCCESS) {
883         MEDIA_ERR_LOG("playerControl init failed");
884         return HI_ERR_PLAYERCONTROL_MEM_MALLOC;
885     }
886     currentState_ = PLAYER_INITIALIZED;
887     MEDIA_INFO_LOG("GetPlayer success");
888     return 0;
889 }
890 
SetPlayerCallback(const std::shared_ptr<PlayerCallback> & cb)891 void PlayerImpl::SetPlayerCallback(const std::shared_ptr<PlayerCallback> &cb)
892 {
893     std::lock_guard<std::mutex> valueLock(lock_);
894     MEDIA_INFO_LOG("process in");
895     if (released_) {
896         MEDIA_ERR_LOG("have released or not create");
897         return;
898     }
899     callback_ = cb;
900 }
901 
NotifyPlaybackComplete(PlayerImpl * curPlayer)902 void PlayerImpl::NotifyPlaybackComplete(PlayerImpl *curPlayer)
903 {
904     if (curPlayer == nullptr) {
905         MEDIA_ERR_LOG("curPlayer is nullptr");
906         return;
907     }
908     if (!isSingleLoop_) {
909         if (curPlayer->formatFileInfo_.s64Duration == -1) {
910             curPlayer->formatFileInfo_.s64Duration = curPlayer->currentPosition_;
911         }
912         curPlayer->currentState_ = PLAYER_PLAYBACK_COMPLETE;
913         MEDIA_INFO_LOG("OnPlayBackComplete, iscallbackNull:%d", (curPlayer->callback_ == nullptr));
914         if (curPlayer->callback_ != nullptr) {
915             curPlayer->callback_->OnPlaybackComplete();
916         }
917         return;
918     }
919     std::lock_guard<std::mutex> valueLock(curPlayer->rewindLock_);
920     (void)curPlayer->RewindInner(0, PLAYER_SEEK_PREVIOUS_SYNC);
921     curPlayer->currentPosition_ = 0;
922     curPlayer->extraRewind_ = false;
923 }
924 
NotifySeekComplete(PlayerImpl * curPlayer,int64_t seekToMs)925 void PlayerImpl::NotifySeekComplete(PlayerImpl *curPlayer, int64_t seekToMs)
926 {
927     std::lock_guard<std::mutex> valueLock(curPlayer->rewindLock_);
928 
929     if (curPlayer->rewindPosition_ != -1 && curPlayer->rewindPosition_ != seekToMs) {
930         int64_t seekTime = curPlayer->rewindPosition_;
931         curPlayer->rewindMode_ = PLAYER_SEEK_PREVIOUS_SYNC;
932         curPlayer->rewindPosition_ = -1;
933         curPlayer->RewindInner(seekTime, curPlayer->currentRewindMode_);
934         return;
935     }
936 
937     curPlayer->currentRewindMode_ = curPlayer->rewindMode_ = PLAYER_SEEK_PREVIOUS_SYNC;
938     curPlayer->rewindPosition_ = -1;
939     if (curPlayer->callback_ != nullptr && extraRewind_) {
940         extraRewind_ = false;
941         curPlayer->callback_->OnRewindToComplete();
942     }
943 }
944 
SetLoop(bool loop)945 int32_t PlayerImpl::SetLoop(bool loop)
946 {
947     std::lock_guard<std::mutex> valueLock(lock_);
948     CHECK_FAILED_RETURN(released_, false, -1, "have released or not create");
949     CHECK_FAILED_RETURN(isStreamSource_, false, -1, "stream source not support loop player");
950     if (currentState_ == PLAYER_STOPPED || currentState_ == PLAYER_PLAYBACK_COMPLETE || currentState_ == PLAYER_IDLE) {
951         MEDIA_ERR_LOG("currentState_ is %u", currentState_);
952         return -1;
953     }
954     isSingleLoop_ = loop;
955     return 0;
956 }
957 
SetUriSource(const Source & source)958 int32_t PlayerImpl::SetUriSource(const Source &source)
959 {
960     MEDIA_INFO_LOG("process in");
961     const std::string uri = source.GetSourceUri();
962     if (uri.empty() || uri.c_str() == nullptr) {
963         MEDIA_ERR_LOG("SetUriSource failed, uri source do not set uri parameter");
964         return -1;
965     }
966     char filePath[PATH_MAX];
967     if (realpath(uri.c_str(), filePath) == nullptr) {
968         MEDIA_ERR_LOG("Realpath input file failed");
969         return -1;
970     }
971     if (access(filePath, R_OK) == -1) {
972         MEDIA_ERR_LOG("No permission to read the file");
973         return -1;
974     }
975     int32_t ret = player_->SetDataSource(uri.c_str());
976     if (ret != 0) {
977         MEDIA_ERR_LOG("SetSource failed, ret is %d, uri is %s", ret, uri.c_str());
978         return ret;
979     }
980     return 0;
981 }
982 
AdapterStreamCallback(std::shared_ptr<StreamSource> & stream,std::shared_ptr<BufferSource> & buffer)983 AdapterStreamCallback::AdapterStreamCallback(std::shared_ptr<StreamSource> &stream,
984     std::shared_ptr<BufferSource> &buffer)
985     : streamProcess_(0),
986       isRunning_(false)
987 {
988     streamSource_ = stream;
989     bufferSource_ = buffer;
990     pthread_mutex_init(&mutex_, nullptr);
991 }
992 
~AdapterStreamCallback(void)993 AdapterStreamCallback::~AdapterStreamCallback(void)
994 {
995     DeInit();
996     MEDIA_INFO_LOG("process out");
997 }
998 
IdleBufferProcess(void * arg)999 void *AdapterStreamCallback::IdleBufferProcess(void *arg)
1000 {
1001     int ret;
1002     QueBuffer buffer;
1003     BufferInfo info;
1004     if (memset_s(&info, sizeof(info), 0x00, sizeof(info)) != EOK) {
1005         return nullptr;
1006     }
1007     AdapterStreamCallback *process = (AdapterStreamCallback*)arg;
1008     if (process == nullptr) {
1009         return nullptr;
1010     }
1011 
1012     prctl(PR_SET_NAME, "IdlbufProc", 0, 0, 0);
1013     MEDIA_INFO_LOG("process start");
1014     while (true) {
1015         pthread_mutex_lock(&process->mutex_);
1016         if (process->isRunning_ == false) {
1017             pthread_mutex_unlock(&process->mutex_);
1018             break;
1019         }
1020         pthread_mutex_unlock(&process->mutex_);
1021         if (process->bufferSource_ == nullptr) {
1022             MEDIA_ERR_LOG("bufferSource_ null break");
1023             break;
1024         }
1025         if (process->bufferSource_->GetIdleQueSize() == 0) {
1026             usleep(IDLE_QUEQUE_SLEEP_TIME_US);
1027             continue;
1028         }
1029         ret = process->bufferSource_->DequeIdleBuffer(&buffer, 0);
1030         if (ret == 0) {
1031             process->bufferSource_->GetBufferInfo(buffer.idx, &info);
1032             std::shared_ptr<StreamSource> stream = process->streamSource_.lock();
1033             if (stream == nullptr) {
1034                 MEDIA_ERR_LOG("stream not exist break");
1035                 break;
1036             }
1037             stream->OnBufferAvailable(buffer.idx, 0, info.bufLen);
1038         }
1039     };
1040     pthread_mutex_lock(&process->mutex_);
1041     process->isRunning_ = false;
1042     pthread_mutex_unlock(&process->mutex_);
1043     MEDIA_INFO_LOG("work end");
1044     return nullptr;
1045 }
1046 
Init(void)1047 int AdapterStreamCallback::Init(void)
1048 {
1049     MEDIA_INFO_LOG("process in");
1050     pthread_mutex_lock(&mutex_);
1051     isRunning_ = true;
1052     pthread_mutex_unlock(&mutex_);
1053     int32_t ret = pthread_create(&streamProcess_, nullptr, IdleBufferProcess, this);
1054     if (ret != 0) {
1055         MEDIA_ERR_LOG("pthread_create failed %d", ret);
1056         pthread_mutex_lock(&mutex_);
1057         isRunning_ = false;
1058         pthread_mutex_unlock(&mutex_);
1059         return -1;
1060     }
1061     return 0;
1062 }
1063 
DeInit(void)1064 void AdapterStreamCallback::DeInit(void)
1065 {
1066     MEDIA_INFO_LOG("process in");
1067     pthread_mutex_lock(&mutex_);
1068     isRunning_ = false;
1069     pthread_mutex_unlock(&mutex_);
1070     if (streamProcess_ != 0) {
1071         pthread_join(streamProcess_, nullptr);
1072     }
1073     pthread_mutex_destroy(&mutex_);
1074 }
1075 
GetBuffer(size_t index)1076 uint8_t *AdapterStreamCallback::GetBuffer(size_t index)
1077 {
1078     BufferInfo info;
1079     if (bufferSource_ == nullptr) {
1080         MEDIA_ERR_LOG("bufferSource null");
1081         return nullptr;
1082     }
1083     if (bufferSource_->GetBufferInfo(index, &info) != 0) {
1084         MEDIA_ERR_LOG("GetBufferInfo failed");
1085         return nullptr;
1086     }
1087     return (uint8_t*)info.virAddr;
1088 }
1089 
QueueBuffer(size_t index,size_t offset,size_t size,int64_t timestampUs,uint32_t flags)1090 void AdapterStreamCallback::QueueBuffer(size_t index, size_t offset, size_t size, int64_t timestampUs, uint32_t flags)
1091 {
1092     QueBuffer buffer;
1093     if (bufferSource_ == nullptr) {
1094         MEDIA_ERR_LOG("bufferSource null");
1095         return;
1096     }
1097 
1098     buffer.idx = index;
1099     buffer.flag = static_cast<int32_t>(flags);
1100     buffer.offset = offset;
1101     buffer.size = size;
1102     buffer.timestamp = timestampUs;
1103     if (bufferSource_->QueFilledBuffer(&buffer) != 0) {
1104         MEDIA_ERR_LOG("QueFilledBuffer failed");
1105     }
1106 }
1107 
SetParameters(const Format & params)1108 void AdapterStreamCallback::SetParameters(const Format &params)
1109 {
1110     MEDIA_ERR_LOG("process, not support");
1111 }
1112 
GetReadableSize(const void * handle)1113 int32_t PlayerImpl::GetReadableSize(const void *handle)
1114 {
1115     const PlayerImpl *playImpl = (const PlayerImpl*)handle;
1116     CHK_NULL_RETURN(playImpl);
1117     if (playImpl->bufferSource_ == nullptr) {
1118         MEDIA_ERR_LOG("bufferSource null");
1119         return -1;
1120     }
1121     return playImpl->bufferSource_->GetFilledQueDataSize();
1122 }
1123 
ReadDataPro(uint8_t * data,int32_t size,DataFlags & flags)1124 int32_t PlayerImpl::ReadDataPro(uint8_t *data, int32_t size, DataFlags &flags)
1125 {
1126     int readLen;
1127     BufferInfo info;
1128     if (bufferSource_->GetBufferInfo(buffer_.idx, &info) != 0) {
1129         return 0;
1130     }
1131     /* read all buffer data */
1132     if (buffer_.size <= size) {
1133         if (buffer_.size == 0 && buffer_.flag == BUFFER_FLAG_EOS) {
1134             buffer_.offset = 0;
1135             buffer_.size = info.size;
1136             bufferSource_->QueIdleBuffer(&buffer_);
1137             buffer_.idx = -1;
1138             flags = DATA_FLAG_EOS;
1139             return 0;
1140         }
1141         if (memcpy_s(data, size, (unsigned char*)(info.virAddr) + buffer_.offset, buffer_.size) != EOK) {
1142             return -1;
1143         }
1144         flags = (buffer_.flag == BUFFER_FLAG_EOS) ? DATA_FLAG_EOS : DATA_FLAG_PARTIAL_FRAME;
1145         readLen = buffer_.size;
1146         buffer_.offset = 0;
1147         buffer_.size = info.size;
1148         bufferSource_->QueIdleBuffer(&buffer_);
1149         buffer_.idx = -1;
1150     } else {
1151         if (memcpy_s(data, size, (unsigned char*)(info.virAddr) + buffer_.offset, size) != EOK) {
1152             return -1;
1153         }
1154         buffer_.offset += size;
1155         buffer_.size -= size;
1156         flags = DATA_FLAG_PARTIAL_FRAME;
1157         readLen = size;
1158     }
1159     return readLen;
1160 }
1161 
ReadData(void * handle,uint8_t * data,int32_t size,int32_t timeOutMs,DataFlags * flags)1162 int32_t PlayerImpl::ReadData(void *handle, uint8_t *data, int32_t size, int32_t timeOutMs, DataFlags *flags)
1163 {
1164     PlayerImpl *playImpl = (PlayerImpl*)handle;
1165 
1166     if (playImpl == nullptr || playImpl->bufferSource_ == nullptr) {
1167         MEDIA_ERR_LOG("bufferSource null");
1168         return -1;
1169     }
1170     if (data == nullptr || size < 0  || flags == nullptr) {
1171         MEDIA_ERR_LOG("data null or buffer size < 0");
1172         return -1;
1173     }
1174 
1175     if (playImpl->buffer_.idx != -1) {
1176         return playImpl->ReadDataPro(data, size, *flags);
1177     }
1178 
1179     if (playImpl->bufferSource_->GetFilledQueSize() <= 0) {
1180         return 0;
1181     }
1182     if (playImpl->bufferSource_->DequeFilledBuffer(&playImpl->buffer_, 0) != 0) {
1183         playImpl->buffer_.idx = -1;
1184         return 0;
1185     }
1186 
1187     return playImpl->ReadDataPro(data, size, *flags);
1188 }
1189 
SetStreamSource(const Source & source)1190 int32_t PlayerImpl::SetStreamSource(const Source &source)
1191 {
1192     MEDIA_INFO_LOG("process in");
1193 
1194     isStreamSource_ = true;
1195     isSingleLoop_ = false;
1196 
1197     bufferSource_ = std::make_shared<BufferSource>();
1198     if (bufferSource_ == nullptr) {
1199         MEDIA_ERR_LOG("new BufferSource failed");
1200         return -1;
1201     }
1202 
1203     bufferSource_->Init();
1204     std::shared_ptr<StreamSource> stream = source.GetSourceStream();
1205     if (stream.get() == nullptr) {
1206         MEDIA_ERR_LOG("GetSourceStream null");
1207         return -1;
1208     }
1209 
1210     streamCallback_ = std::make_shared<AdapterStreamCallback>(stream, bufferSource_);
1211     if (streamCallback_ == nullptr || streamCallback_.get() == nullptr) {
1212         MEDIA_ERR_LOG("new AdapterStreamCallback failed");
1213         return -1;
1214     }
1215     streamCallback_->Init();
1216     stream->SetStreamCallback(streamCallback_);
1217 
1218     BufferStream sourceTmp;
1219     sourceTmp.handle = this;
1220     sourceTmp.ReadData = ReadData;
1221     sourceTmp.GetReadableSize = GetReadableSize;
1222     int32_t ret = player_->SetDataSource(sourceTmp);
1223     if (ret != 0) {
1224         MEDIA_ERR_LOG("SetDataSource  exec failed");
1225         return -1;
1226     }
1227     return 0;
1228 }
1229 
EnablePauseAfterPlay(bool isPauseAfterPlay)1230 int32_t PlayerImpl::EnablePauseAfterPlay(bool isPauseAfterPlay)
1231 {
1232     if (currentState_ != PLAYER_IDLE && currentState_ != PLAYER_INITIALIZED) {
1233         MEDIA_ERR_LOG("currentState_ is %u", currentState_);
1234         return -1;
1235     }
1236     if (pauseAfterPlay_ == isPauseAfterPlay) {
1237         return 0;
1238     }
1239 
1240     pauseAfterPlay_ = isPauseAfterPlay;
1241     if (player_ != NULL) {
1242         return player_->Invoke(INVOKE_ENABLE_PAUSE_AFTER_PLAYER, &pauseAfterPlay_);
1243     }
1244     MEDIA_INFO_LOG("isPauseAfterPlay:%d", isPauseAfterPlay);
1245     return 0;
1246 }
1247 
SetParameter(const Format & params)1248 int32_t PlayerImpl::SetParameter(const Format &params)
1249 {
1250     int32_t value;
1251     std::lock_guard<std::mutex> valueLock(lock_);
1252 
1253     if (params.GetIntValue(PAUSE_AFTER_PLAY, value) != true) {
1254         MEDIA_ERR_LOG("get pause after play failed");
1255         return -1;
1256     }
1257     if (value != 0 && value != 1) {
1258         MEDIA_ERR_LOG("pause after play flag error:%d", value);
1259         return -1;
1260     }
1261 
1262     return EnablePauseAfterPlay(value);
1263 }
1264 }  // namespace Media
1265 }  // namespace OHOS