• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright 2019 The libgav1 Authors
2 //
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 #include "src/gav1/decoder.h"
16 
17 #include <memory>
18 #include <new>
19 #include <vector>
20 
21 #include "src/decoder_impl.h"
22 
23 extern "C" {
24 
Libgav1DecoderCreate(const Libgav1DecoderSettings * settings,Libgav1Decoder ** decoder_out)25 Libgav1StatusCode Libgav1DecoderCreate(const Libgav1DecoderSettings* settings,
26                                        Libgav1Decoder** decoder_out) {
27   std::unique_ptr<libgav1::Decoder> cxx_decoder(new (std::nothrow)
28                                                     libgav1::Decoder());
29   if (cxx_decoder == nullptr) return kLibgav1StatusOutOfMemory;
30 
31   libgav1::DecoderSettings cxx_settings;
32   cxx_settings.threads = settings->threads;
33   cxx_settings.frame_parallel = settings->frame_parallel != 0;
34   cxx_settings.blocking_dequeue = settings->blocking_dequeue != 0;
35   cxx_settings.on_frame_buffer_size_changed =
36       settings->on_frame_buffer_size_changed;
37   cxx_settings.get_frame_buffer = settings->get_frame_buffer;
38   cxx_settings.release_frame_buffer = settings->release_frame_buffer;
39   cxx_settings.release_input_buffer = settings->release_input_buffer;
40   cxx_settings.callback_private_data = settings->callback_private_data;
41   cxx_settings.output_all_layers = settings->output_all_layers != 0;
42   cxx_settings.operating_point = settings->operating_point;
43   cxx_settings.post_filter_mask = settings->post_filter_mask;
44   cxx_settings.parse_only = settings->parse_only != 0;
45 
46   const Libgav1StatusCode status = cxx_decoder->Init(&cxx_settings);
47   if (status == kLibgav1StatusOk) {
48     *decoder_out = reinterpret_cast<Libgav1Decoder*>(cxx_decoder.release());
49   }
50   return status;
51 }
52 
Libgav1DecoderDestroy(Libgav1Decoder * decoder)53 void Libgav1DecoderDestroy(Libgav1Decoder* decoder) {
54   auto* cxx_decoder = reinterpret_cast<libgav1::Decoder*>(decoder);
55   delete cxx_decoder;
56 }
57 
Libgav1DecoderEnqueueFrame(Libgav1Decoder * decoder,const uint8_t * data,size_t size,int64_t user_private_data,void * buffer_private_data)58 Libgav1StatusCode Libgav1DecoderEnqueueFrame(Libgav1Decoder* decoder,
59                                              const uint8_t* data, size_t size,
60                                              int64_t user_private_data,
61                                              void* buffer_private_data) {
62   auto* cxx_decoder = reinterpret_cast<libgav1::Decoder*>(decoder);
63   return cxx_decoder->EnqueueFrame(data, size, user_private_data,
64                                    buffer_private_data);
65 }
66 
Libgav1DecoderDequeueFrame(Libgav1Decoder * decoder,const Libgav1DecoderBuffer ** out_ptr)67 Libgav1StatusCode Libgav1DecoderDequeueFrame(
68     Libgav1Decoder* decoder, const Libgav1DecoderBuffer** out_ptr) {
69   auto* cxx_decoder = reinterpret_cast<libgav1::Decoder*>(decoder);
70   return cxx_decoder->DequeueFrame(out_ptr);
71 }
72 
Libgav1DecoderSignalEOS(Libgav1Decoder * decoder)73 Libgav1StatusCode Libgav1DecoderSignalEOS(Libgav1Decoder* decoder) {
74   auto* cxx_decoder = reinterpret_cast<libgav1::Decoder*>(decoder);
75   return cxx_decoder->SignalEOS();
76 }
77 
Libgav1DecoderGetMaxBitdepth()78 int Libgav1DecoderGetMaxBitdepth() {
79   return libgav1::Decoder::GetMaxBitdepth();
80 }
81 
82 }  // extern "C"
83 
84 namespace libgav1 {
85 
86 Decoder::Decoder() = default;
87 
88 Decoder::~Decoder() = default;
89 
Init(const DecoderSettings * const settings)90 StatusCode Decoder::Init(const DecoderSettings* const settings) {
91   if (impl_ != nullptr) return kStatusAlready;
92   if (settings != nullptr) settings_ = *settings;
93   return DecoderImpl::Create(&settings_, &impl_);
94 }
95 
EnqueueFrame(const uint8_t * data,const size_t size,int64_t user_private_data,void * buffer_private_data)96 StatusCode Decoder::EnqueueFrame(const uint8_t* data, const size_t size,
97                                  int64_t user_private_data,
98                                  void* buffer_private_data) {
99   if (impl_ == nullptr) return kStatusNotInitialized;
100   return impl_->EnqueueFrame(data, size, user_private_data,
101                              buffer_private_data);
102 }
103 
DequeueFrame(const DecoderBuffer ** out_ptr)104 StatusCode Decoder::DequeueFrame(const DecoderBuffer** out_ptr) {
105   if (impl_ == nullptr) return kStatusNotInitialized;
106   StatusCode status = impl_->DequeueFrame(out_ptr);
107   if (settings_.parse_only) {
108     frame_mean_qps_ = impl_->GetFrameQps();
109   }
110   return status;
111 }
112 
SignalEOS()113 StatusCode Decoder::SignalEOS() {
114   if (impl_ == nullptr) return kStatusNotInitialized;
115   // In non-frame-parallel mode, we have to release all the references. This
116   // simply means replacing the |impl_| with a new instance so that all the
117   // existing references are released and the state is cleared.
118   impl_ = nullptr;
119   return DecoderImpl::Create(&settings_, &impl_);
120 }
121 
122 // static.
GetMaxBitdepth()123 int Decoder::GetMaxBitdepth() { return DecoderImpl::GetMaxBitdepth(); }
124 
GetFramesMeanQpInTemporalUnit()125 std::vector<int> Decoder::GetFramesMeanQpInTemporalUnit() {
126   return frame_mean_qps_;
127 }
128 
129 }  // namespace libgav1
130