OmxDataDecoder.h (6882B)
1 /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ 2 /* vim:set ts=2 sw=2 sts=2 et cindent: */ 3 /* This Source Code Form is subject to the terms of the Mozilla Public 4 * License, v. 2.0. If a copy of the MPL was not distributed with this 5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ 6 7 #if !defined(OmxDataDecoder_h_) 8 # define OmxDataDecoder_h_ 9 10 # include "AudioCompactor.h" 11 # include "ImageContainer.h" 12 # include "MediaInfo.h" 13 # include "OMX_Component.h" 14 # include "OmxPromiseLayer.h" 15 # include "PerformanceRecorder.h" 16 # include "PlatformDecoderModule.h" 17 # include "mozilla/Monitor.h" 18 # include "mozilla/StateWatching.h" 19 20 namespace mozilla { 21 22 class MediaDataHelper; 23 24 typedef OmxPromiseLayer::OmxCommandPromise OmxCommandPromise; 25 typedef OmxPromiseLayer::OmxBufferPromise OmxBufferPromise; 26 typedef OmxPromiseLayer::OmxBufferFailureHolder OmxBufferFailureHolder; 27 typedef OmxPromiseLayer::OmxCommandFailureHolder OmxCommandFailureHolder; 28 typedef OmxPromiseLayer::BufferData BufferData; 29 typedef OmxPromiseLayer::BUFFERLIST BUFFERLIST; 30 31 DDLoggedTypeDeclNameAndBase(OmxDataDecoder, MediaDataDecoder); 32 33 /* OmxDataDecoder is the major class which performs followings: 34 * 1. Translate PDM function into OMX commands. 35 * 2. Keeping the buffers between client and component. 36 * 3. Manage the OMX state. 37 * 38 * From the definition in OpenMax spec. "2.2.1", there are 3 major roles in 39 * OpenMax IL. 40 * 41 * IL client: 42 * "The IL client may be a layer below the GUI application, such as GStreamer, 43 * or may be several layers below the GUI layer." 44 * 45 * OmxDataDecoder acts as the IL client. 46 * 47 * OpenMAX IL component: 48 * "A component that is intended to wrap functionality that is required in the 49 * target system." 50 * 51 * OmxPromiseLayer acts as the OpenMAX IL component. 52 * 53 * OpenMAX IL core: 54 * "Platform-specific code that has the functionality necessary to locate and 55 * then load an OpenMAX IL component into main memory." 56 * 57 * OmxPlatformLayer acts as the OpenMAX IL core. 58 */ 59 class OmxDataDecoder final : public MediaDataDecoder, 60 public DecoderDoctorLifeLogger<OmxDataDecoder> { 61 protected: 62 virtual ~OmxDataDecoder(); 63 64 public: 65 NS_INLINE_DECL_THREADSAFE_REFCOUNTING(OmxDataDecoder, final); 66 67 OmxDataDecoder(const TrackInfo& aTrackInfo, 68 layers::ImageContainer* aImageContainer, 69 Maybe<TrackingId> aTrackingId); 70 71 RefPtr<InitPromise> Init() override; 72 RefPtr<DecodePromise> Decode(MediaRawData* aSample) override; 73 RefPtr<DecodePromise> Drain() override; 74 RefPtr<FlushPromise> Flush() override; 75 RefPtr<ShutdownPromise> Shutdown() override; 76 77 nsCString GetDescriptionName() const override { return "omx decoder"_ns; } 78 79 nsCString GetCodecName() const override { return "unknown"_ns; } 80 81 ConversionRequired NeedsConversion() const override { 82 return ConversionRequired::kNeedAnnexB; 83 } 84 85 // Return true if event is handled. 86 bool Event(OMX_EVENTTYPE aEvent, OMX_U32 aData1, OMX_U32 aData2); 87 88 protected: 89 void InitializationTask(); 90 91 void ResolveInitPromise(StaticString aMethodName); 92 93 void RejectInitPromise(MediaResult aError, StaticString aMethodName); 94 95 void OmxStateRunner(); 96 97 void FillAndEmptyBuffers(); 98 99 void FillBufferDone(BufferData* aData); 100 101 void FillBufferFailure(OmxBufferFailureHolder aFailureHolder); 102 103 void EmptyBufferDone(BufferData* aData); 104 105 void EmptyBufferFailure(OmxBufferFailureHolder aFailureHolder); 106 107 void NotifyError( 108 OMX_ERRORTYPE aOmxError, const char* aLine, 109 const MediaResult& aError = MediaResult(NS_ERROR_DOM_MEDIA_FATAL_ERR)); 110 111 // Configure audio/video codec. 112 // Some codec may just ignore this and rely on codec specific data in 113 // FillCodecConfigDataToOmx(). 114 void ConfigCodec(); 115 116 // Sending codec specific data to OMX component. OMX component could send a 117 // OMX_EventPortSettingsChanged back to client. And then client needs to 118 // disable port and reallocate buffer. 119 void FillCodecConfigDataToOmx(); 120 121 void SendEosBuffer(); 122 123 void EndOfStream(); 124 125 // It could be called after codec specific data is sent and component found 126 // the port format is changed due to different codec specific. 127 void PortSettingsChanged(); 128 129 void Output(BufferData* aData); 130 131 // Buffer can be released if its status is not OMX_COMPONENT or 132 // OMX_CLIENT_OUTPUT. 133 bool BuffersCanBeReleased(OMX_DIRTYPE aType); 134 135 OMX_DIRTYPE GetPortDirection(uint32_t aPortIndex); 136 137 RefPtr<ShutdownPromise> DoAsyncShutdown(); 138 139 RefPtr<FlushPromise> DoFlush(); 140 141 void FlushComplete(OMX_COMMANDTYPE aCommandType); 142 143 void FlushFailure(OmxCommandFailureHolder aFailureHolder); 144 145 BUFFERLIST* GetBuffers(OMX_DIRTYPE aType); 146 147 nsresult AllocateBuffers(OMX_DIRTYPE aType); 148 149 nsresult ReleaseBuffers(OMX_DIRTYPE aType); 150 151 BufferData* FindAvailableBuffer(OMX_DIRTYPE aType); 152 153 // aType could be OMX_DirMax for all types. 154 RefPtr<OmxPromiseLayer::OmxBufferPromise::AllPromiseType> 155 CollectBufferPromises(OMX_DIRTYPE aType); 156 157 // The Omx TaskQueue. 158 RefPtr<TaskQueue> mOmxTaskQueue; 159 160 nsCOMPtr<nsISerialEventTarget> mThread; 161 RefPtr<layers::ImageContainer> mImageContainer; 162 163 WatchManager<OmxDataDecoder> mWatchManager; 164 165 // It is accessed in omx TaskQueue. 166 Watchable<OMX_STATETYPE> mOmxState; 167 168 RefPtr<OmxPromiseLayer> mOmxLayer; 169 170 UniquePtr<TrackInfo> mTrackInfo; 171 172 // It is accessed in both omx and reader TaskQueue. 173 Atomic<bool> mFlushing; 174 175 // It is accessed in Omx/reader TaskQueue. 176 Atomic<bool> mShuttingDown; 177 178 // It is accessed in Omx TaskQeueu. 179 bool mCheckingInputExhausted; 180 181 // It is accessed in OMX TaskQueue. 182 MozPromiseHolder<InitPromise> mInitPromise; 183 MozPromiseHolder<DecodePromise> mDecodePromise; 184 MozPromiseHolder<DecodePromise> mDrainPromise; 185 MozPromiseHolder<FlushPromise> mFlushPromise; 186 MozPromiseHolder<ShutdownPromise> mShutdownPromise; 187 // Where decoded samples will be stored until the decode promise is resolved. 188 DecodedData mDecodedData; 189 190 void CompleteDrain(); 191 192 // It is written in Omx TaskQueue. Read in Omx TaskQueue. 193 // It value means the port index which port settings is changed. 194 // -1 means no port setting changed. 195 // 196 // Note: when port setting changed, there should be no buffer operations 197 // via EmptyBuffer or FillBuffer. 198 Watchable<int32_t> mPortSettingsChanged; 199 200 // It is access in Omx TaskQueue. 201 nsTArray<RefPtr<MediaRawData>> mMediaRawDatas; 202 203 BUFFERLIST mInPortBuffers; 204 205 BUFFERLIST mOutPortBuffers; 206 207 RefPtr<MediaDataHelper> mMediaDataHelper; 208 209 const Maybe<TrackingId> mTrackingId; 210 211 // Accessed on Omx TaskQueue 212 PerformanceRecorderMulti<DecodeStage> mPerformanceRecorder; 213 }; 214 215 template <class T> 216 void InitOmxParameter(T* aParam) { 217 PodZero(aParam); 218 aParam->nSize = sizeof(T); 219 aParam->nVersion.s.nVersionMajor = 1; 220 } 221 222 } // namespace mozilla 223 224 #endif /* OmxDataDecoder_h_ */