1 /*
2  * Copyright (c) 2023-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 MODULES_MEDIA_CODEC_H
17 #define MODULES_MEDIA_CODEC_H
18 
19 #include <cstring>
20 #include "surface.h"
21 #include "meta/meta.h"
22 #include "buffer/avbuffer.h"
23 #include "buffer/avallocator.h"
24 #include "buffer/avbuffer_queue.h"
25 #include "buffer/avbuffer_queue_producer.h"
26 #include "buffer/avbuffer_queue_consumer.h"
27 #include "common/status.h"
28 #include "plugin/plugin_event.h"
29 #include "plugin/codec_plugin.h"
30 #include "osal/task/mutex.h"
31 #include "foundation/multimedia/drm_framework/services/drm_service/ipc/i_keysession_service.h"
32 #include "foundation/multimedia/av_codec/services/drm_decryptor/codec_drm_decrypt.h"
33 
34 namespace OHOS {
35 namespace Media {
36 enum class CodecState : int32_t {
37     UNINITIALIZED,
38     INITIALIZED,
39     CONFIGURED,
40     PREPARED,
41     RUNNING,
42     FLUSHED,
43     END_OF_STREAM,
44 
45     INITIALIZING, // RELEASED -> INITIALIZED
46     STARTING,     // INITIALIZED -> RUNNING
47     STOPPING,     // RUNNING -> INITIALIZED
48     FLUSHING,     // RUNNING -> FLUSHED
49     RESUMING,     // FLUSHED -> RUNNING
50     RELEASING,    // {ANY EXCEPT RELEASED} -> RELEASED
51 
52     ERROR,
53 };
54 
55 enum class CodecErrorType : int32_t {
56     CODEC_ERROR_INTERNAL,
57     CODEC_DRM_DECRYTION_FAILED,
58     CODEC_ERROR_EXTEND_START = 0X10000,
59 };
60 
61 class CodecCallback {
62 public:
63     virtual ~CodecCallback() = default;
64 
65     virtual void OnError(CodecErrorType errorType, int32_t errorCode) = 0;
66 
67     virtual void OnOutputFormatChanged(const std::shared_ptr<Meta> &format) = 0;
68 };
69 
70 class AudioBaseCodecCallback {
71 public:
72     virtual ~AudioBaseCodecCallback() = default;
73 
74     virtual void OnError(CodecErrorType errorType, int32_t errorCode) = 0;
75 
76     virtual void OnOutputBufferDone(const std::shared_ptr<AVBuffer> &outputBuffer) = 0;
77 };
78 
79 class MediaCodec : public Plugins::DataCallback {
80 public:
81     MediaCodec();
82 
83     ~MediaCodec() override;
84 
85     int32_t Init(const std::string &mime, bool isEncoder);
86 
87     int32_t Init(const std::string &name);
88 
89     int32_t Configure(const std::shared_ptr<Meta> &meta);
90 
91     int32_t SetOutputBufferQueue(const sptr<AVBufferQueueProducer> &bufferQueueProducer);
92 
93     int32_t SetCodecCallback(const std::shared_ptr<CodecCallback> &codecCallback);
94 
95     int32_t SetCodecCallback(const std::shared_ptr<AudioBaseCodecCallback> &codecCallback);
96 
97     int32_t SetOutputSurface(sptr<Surface> surface);
98 
99     int32_t Prepare();
100 
101     sptr<AVBufferQueueProducer> GetInputBufferQueue();
102 
103     sptr<Surface> GetInputSurface();
104 
105     int32_t Start();
106 
107     int32_t Stop();
108 
109     int32_t Flush();
110 
111     int32_t Reset();
112 
113     int32_t Release();
114 
115     int32_t NotifyEos();
116 
117     int32_t SetParameter(const std::shared_ptr<Meta> &parameter);
118 
119     int32_t GetOutputFormat(std::shared_ptr<Meta> &parameter);
120 
121     void ProcessInputBuffer();
122 
123     void SetDumpInfo(bool isDump, uint64_t instanceId);
124 
125     int32_t SetAudioDecryptionConfig(const sptr<DrmStandard::IMediaKeySessionService> &keySession,
126         const bool svpFlag);
127 
128     Status ChangePlugin(const std::string &mime, bool isEncoder, const std::shared_ptr<Meta> &meta);
129 
130     void OnDumpInfo(int32_t fd);
131 
132 private:
133     std::shared_ptr<Plugins::CodecPlugin> CreatePlugin(Plugins::PluginType pluginType);
134     std::shared_ptr<Plugins::CodecPlugin> CreatePlugin(const std::string &mime, Plugins::PluginType pluginType);
135     Status AttachBufffer();
136     Status AttachDrmBufffer(std::shared_ptr<AVBuffer> &drmInbuf, std::shared_ptr<AVBuffer> &drmOutbuf,
137         uint32_t size);
138     Status DrmAudioCencDecrypt(std::shared_ptr<AVBuffer> &filledInputBuffer);
139     Status HandleOutputBuffer(uint32_t eosStatus);
140 
141     int32_t PrepareInputBufferQueue();
142 
143     int32_t PrepareOutputBufferQueue();
144 
145     void OnInputBufferDone(const std::shared_ptr<AVBuffer> &inputBuffer) override;
146 
147     void OnOutputBufferDone(const std::shared_ptr<AVBuffer> &outputBuffer) override;
148 
149     void OnEvent(const std::shared_ptr<Plugins::PluginEvent> event) override;
150 
151     std::string StateToString(CodecState state);
152 
153     void ClearBufferQueue();
154 
155     void ClearInputBuffer();
156 
157     void HandleAudioCencDecryptError();
158 
159 private:
160     std::shared_ptr<Plugins::CodecPlugin> codecPlugin_;
161     std::shared_ptr<AVBufferQueue> inputBufferQueue_;
162     sptr<AVBufferQueueProducer> inputBufferQueueProducer_;
163     sptr<AVBufferQueueConsumer> inputBufferQueueConsumer_;
164     sptr<AVBufferQueueProducer> outputBufferQueueProducer_;
165     std::weak_ptr<CodecCallback> codecCallback_;
166     // callback from north interface(AudioCodec..)
167     std::weak_ptr<AudioBaseCodecCallback> mediaCodecCallback_;
168     AVBufferConfig outputBufferConfig_;
169     bool isEncoder_;
170     bool isSurfaceMode_;
171     bool isBufferMode_;
172     bool isDump_ = false;
173     std::string dumpPrefix_ = "";
174     int32_t outputBufferCapacity_;
175     std::string codecPluginName_;
176 
177     std::atomic<CodecState> state_;
178     std::shared_ptr<MediaAVCodec::CodecDrmDecrypt> drmDecryptor_ = nullptr;
179     std::vector<std::shared_ptr<AVBuffer>> inputBufferVector_;
180     std::vector<std::shared_ptr<AVBuffer>> outputBufferVector_;
181     Mutex stateMutex_;
182 };
183 } // namespace Media
184 } // namespace OHOS
185 #endif // MODULES_MEDIA_CODEC_H
186