1 /*
2  * Copyright (c) 2021-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 #ifndef HISTREAMER_VIDEO_FFMPEG_DECODER_PLUGIN_H
17 #define HISTREAMER_VIDEO_FFMPEG_DECODER_PLUGIN_H
18 
19 #if defined(RECORDER_SUPPORT) && defined(VIDEO_SUPPORT)
20 
21 #include <functional>
22 #include <map>
23 #include "foundation/osal/thread/task.h"
24 #include "foundation/utils/blocking_queue.h"
25 #include "plugin/interface/codec_plugin.h"
26 
27 #ifdef __cplusplus
28 extern "C" {
29 #endif
30 #include "libavcodec/avcodec.h"
31 #ifdef __cplusplus
32 };
33 #endif
34 
35 #ifdef DUMP_RAW_DATA
36 #include <cstdio>
37 #endif
38 
39 namespace OHOS {
40 namespace Media {
41 namespace Plugin {
42 namespace Ffmpeg {
43 class VideoFfmpegEncoderPlugin : public CodecPlugin {
44 public:
45     explicit VideoFfmpegEncoderPlugin(std::string name);
46     ~VideoFfmpegEncoderPlugin() override = default;
47 
48     Status Init() override;
49     Status Deinit() override;
50     Status Prepare() override;
51     Status Reset() override;
52     Status Start() override;
53     Status Stop() override;
54 
55     Status GetParameter(Tag tag, ValueType &value) override;
56     Status SetParameter(Tag tag, const ValueType &value) override;
57 
58     std::shared_ptr<Allocator> GetAllocator() override;
59 
SetCallback(Callback * cb)60     Status SetCallback(Callback* cb) override
61     {
62         return Status::OK;
63     }
64 
65     Status QueueInputBuffer(const std::shared_ptr<Buffer>& inputBuffer, int32_t timeoutMs) override;
66 
67     Status QueueOutputBuffer(const std::shared_ptr<Buffer>& outputBuffer, int32_t timeoutMs) override;
68 
69     Status Flush() override;
70 
SetDataCallback(DataCallback * dataCallback)71     Status SetDataCallback(DataCallback* dataCallback) override
72     {
73         dataCb_ = dataCallback;
74         return Status::OK;
75     }
76 
77 private:
78     Status CreateCodecContext();
79 
80     void InitCodecContext();
81 
82     void DeinitCodecContext();
83 
84     Status OpenCodecContext();
85 
86     Status CloseCodecContext();
87 
88     Status ResetLocked();
89 
90     template<typename T>
91     void FindInParameterMapThenAssignLocked(Tag tag, T &assign);
92 
93     Status FillAvFrame(const std::shared_ptr<Buffer>& inputBuffer);
94 
95     Status SendBufferLocked(const std::shared_ptr<Buffer> &inputBuffer);
96 
97     Status FillFrameBuffer(const std::shared_ptr<Buffer> &packetBuffer);
98 
99     Status ReceiveBufferLocked(const std::shared_ptr<Buffer> &packetBuffer);
100 
101     void ReceiveBuffer();
102 
103 #ifdef DUMP_RAW_DATA
104     std::FILE* dumpFd_ {nullptr};
105 #endif
106 
107     void NotifyInputBufferDone(const std::shared_ptr<Buffer> &input);
108 
109     void NotifyOutputBufferDone(const std::shared_ptr<Buffer> &output);
110 
111     std::shared_ptr<const AVCodec> avCodec_;
112     mutable OSAL::Mutex parameterMutex_ {};
113     std::map<Tag, ValueType> vencParams_ {};
114     std::shared_ptr<AVFrame> cachedFrame_;
115     std::shared_ptr<AVPacket> cachedPacket_;
116     DataCallback* dataCb_ {};
117 
118     uint32_t width_ {0};
119     uint32_t height_ {0};
120     uint32_t frameRate_ {0};
121     VideoPixelFormat pixelFormat_ {};
122 
123     mutable OSAL::Mutex avMutex_ {};
124     State state_ {State::CREATED};
125     std::shared_ptr<AVCodecContext> avCodecContext_ {};
126     OHOS::Media::BlockingQueue<std::shared_ptr<Buffer>> outBufferQ_;
127     std::shared_ptr<OSAL::Task> encodeTask_;
128 };
129 } // namespace Ffmpeg
130 } // namespace Plugin
131 } // namespace Media
132 } // namespace OHOS
133 #endif
134 #endif // HISTREAMER_VIDEO_FFMPEG_DECODER_PLUGIN_H
135