• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 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 
16 #ifndef FCODEC_H
17 #define FCODEC_H
18 
19 #include <atomic>
20 #include <list>
21 #include <map>
22 #include <shared_mutex>
23 #include <tuple>
24 #include <vector>
25 #include <optional>
26 #include "av_common.h"
27 #include "avcodec_common.h"
28 #include "avcodec_errors.h"
29 #include "avcodec_info.h"
30 #include "block_queue.h"
31 #include "codec_utils.h"
32 #include "codecbase.h"
33 #include "media_description.h"
34 #include "surface_memory.h"
35 #include "task_thread.h"
36 
37 namespace OHOS {
38 namespace MediaAVCodec {
39 namespace Codec {
40 class FCodec : public CodecBase {
41 public:
42     explicit FCodec(const std::string &name);
43     ~FCodec() override;
44     int32_t Configure(const Format &format) override;
45     int32_t Start() override;
46     int32_t Stop() override;
47     int32_t Flush() override;
48     int32_t Reset() override;
49     int32_t Release() override;
50     int32_t SetParameter(const Format &format) override;
51     int32_t GetOutputFormat(Format &format) override;
52     int32_t QueueInputBuffer(uint32_t index, const AVCodecBufferInfo &info, AVCodecBufferFlag flag) override;
53     int32_t ReleaseOutputBuffer(uint32_t index) override;
54     int32_t SetCallback(const std::shared_ptr<AVCodecCallback> &callback) override;
55     int32_t SetOutputSurface(sptr<Surface> surface) override;
56     int32_t RenderOutputBuffer(uint32_t index) override;
57     static int32_t GetCodecCapability(std::vector<CapabilityData> &capaArray);
58 
59     struct AVBuffer {
60     public:
61         AVBuffer() = default;
62         ~AVBuffer() = default;
63 
64         enum class Owner {
65             OWNED_BY_US,
66             OWNED_BY_CODEC,
67             OWNED_BY_USER,
68             OWNED_BY_SURFACE,
69         };
70 
71         std::shared_ptr<AVSharedMemory> memory_;
72         std::atomic<Owner> owner_ = Owner::OWNED_BY_US;
73         AVCodecBufferInfo bufferInfo_;
74         AVCodecBufferFlag bufferFlag_;
75         int32_t width_ = 0;
76         int32_t height_ = 0;
77     };
78 
79 private:
80     int32_t Init();
81 
82     enum struct State : int32_t {
83         Uninitialized,
84         Initialized,
85         Configured,
86         Stopping,
87         Running,
88         Flushed,
89         Flushing,
90         EOS,
91         Error,
92     };
93     bool IsActive() const;
94     void ResetContext(bool isFlush = false);
95     void CalculateBufferSize();
96     int32_t AllocateBuffers();
97     void InitBuffers();
98     void ResetBuffers();
99     void ResetData();
100     void ReleaseBuffers();
101     void StopThread();
102     int32_t UpdateBuffers(uint32_t index, int32_t bufferSize, uint32_t bufferType);
103     int32_t UpdateSurfaceMemory(uint32_t index);
104     void SendFrame();
105     void ReceiveFrame();
106     void RenderFrame();
107     void ConfigureSufrace(const Format &format, const std::string_view &formatKey, uint32_t FORMAT_TYPE);
108     void ConfigureDefaultVal(const Format &format, const std::string_view &formatKey, int32_t minVal = 0,
109                              int32_t maxVal = INT_MAX);
110     int32_t ConfigureContext(const Format &format);
111     void FramePostProcess(std::shared_ptr<AVBuffer> &frameBuffer, uint32_t index, int32_t status, int ret);
112     int32_t AllocateInputBuffer(int32_t bufferCnt, int32_t inBufferSize);
113     int32_t AllocateOutputBuffer(int32_t bufferCnt, int32_t outBufferSize);
114     int32_t FillFrameBuffer(const std::shared_ptr<AVBuffer> &frameBuffer);
115     int32_t CheckFormatChange(uint32_t index, int width, int height);
116     void SetSurfaceParameter(const Format &format, const std::string_view &formatKey, uint32_t FORMAT_TYPE);
117     int32_t FlushSurfaceMemory(std::shared_ptr<SurfaceMemory> &surfaceMemory, int64_t pts);
118 
119     std::string codecName_;
120     std::atomic<State> state_ = State::Uninitialized;
121     Format format_;
122     int32_t width_ = 0;
123     int32_t height_ = 0;
124     int32_t inputBufferSize_ = 0;
125     int32_t outputBufferSize_ = 0;
126     // INIT
127     std::shared_ptr<AVCodec> avCodec_ = nullptr;
128     // Config
129     std::shared_ptr<AVCodecContext> avCodecContext_ = nullptr;
130     // Start
131     std::shared_ptr<AVPacket> avPacket_ = nullptr;
132     std::shared_ptr<AVFrame> cachedFrame_ = nullptr;
133     // Receive frame
134     uint8_t *scaleData_[AV_NUM_DATA_POINTERS];
135     int32_t scaleLineSize_[AV_NUM_DATA_POINTERS];
136     std::shared_ptr<Scale> scale_ = nullptr;
137     bool isConverted_ = false;
138     bool isOutBufSetted_ = false;
139     VideoPixelFormat outputPixelFmt_ = VideoPixelFormat::UNKNOWN_FORMAT;
140     // Running
141     std::vector<std::shared_ptr<AVBuffer>> buffers_[2];
142     std::shared_ptr<BlockQueue<uint32_t>> inputAvailQue_;
143     std::shared_ptr<BlockQueue<uint32_t>> codecAvailQue_;
144     std::shared_ptr<BlockQueue<uint32_t>> renderAvailQue_;
145     std::optional<uint32_t> synIndex_ = std::nullopt;
146     sptr<Surface> surface_ = nullptr;
147     std::shared_ptr<TaskThread> sendTask_ = nullptr;
148     std::shared_ptr<TaskThread> receiveTask_ = nullptr;
149     std::shared_ptr<TaskThread> renderTask_ = nullptr;
150     std::mutex inputMutex_;
151     std::mutex outputMutex_;
152     std::mutex sendMutex_;
153     std::mutex recvMutex_;
154     std::mutex syncMutex_;
155     std::mutex surfaceMutex_;
156     std::condition_variable sendCv_;
157     std::condition_variable recvCv_;
158     std::shared_ptr<AVCodecCallback> callback_;
159     std::atomic<bool> isSendWait_ = false;
160     std::atomic<bool> isSendEos_ = false;
161     std::atomic<bool> isBufferAllocated_ = false;
162 };
163 } // namespace Codec
164 } // namespace MediaAVCodec
165 } // namespace OHOS
166 #endif // FCODEC_H