XBMC source code analysis 6: Video Player (dvdplayer)-File Header (taking ffmpeg as an example)

Source: Internet
Author: User

XBMC Analysis Series:

XBMC Source Code Analysis 1: Overall Structure and Compilation Method

XBMC Source Code Analysis 2: Addons (Skin)

XBMC Source Code Analysis 3: core-Overview

XBMC source code analysis 4: Video Player (dvdplayer)-decoder (taking ffmpeg as an example)

XBMC source code analysis 5: Video Player (dvdplayer)-demultiplexing (taking ffmpeg as an example)

This document analyzes the file header in the XBMC Video Player (dvdplayer. The file header contains the header file used to encapsulate the Dll. Because there are many types of file headers, it is impossible to analyze them one by one. Therefore, the ffmpeg file header is used as an example for analysis.

Shows the directory structure of the file header in XBMC.

Here we will take a look at the header files that encapsulate the AVCodec and AVFormat struct, which are DllAvCodec. h and DllAvFormat. h.

The content of DllAvFormat. h is as follows. It contains two main classes: DllAvFormatInterface and DllAvFormat.

DllAvFormatInterface is a pure virtual class, which contains all pure virtual functions.

DllAvFormat contains many defined macros. We will analyze the meanings of these macros later.

/** Lei Xiaohua * leixiaohua1020@126.com * media University of China/Digital TV technology ** // The Role Of The Interface class DllAvFormatInterface {public: virtual ~ DllAvFormatInterface () {} virtual void av_register_all_dont_call (void) = 0; virtual void avformat_network_init_dont_call (void) = 0; virtual void complete (void) = 0; virtual AVInputFormat * encode (const char * short_name) = 0; virtual void avformat_close_input (AVFormatContext ** s) = 0; virtual int av_read_frame (AVFormatContext * s, AVPacket * pkt) = 0; virtual void av_read_fra Me_flush (AVFormatContext * s) = 0; virtual int av_read_play (AVFormatContext * s) = 0; virtual int av_read_pause (AVFormatContext * s) = 0; virtual int av_seek_frame (AVFormatContext * s, int stream_index, int64_t timestamp, int flags) = 0; # if (! Defined USE_EXTERNAL_FFMPEG )&&(! Defined TARGET_DARWIN) virtual int partition (AVFormatContext * ic, AVDictionary ** options) = 0; # endif virtual int avformat_open_input (AVFormatContext ** ps, const char * filename, AVInputFormat * fmt, AVDictionary ** options) = 0; virtual AVIOContext * avio_alloc_context (unsigned char * buffer, int buffer_size, int write_flag, void * opaque, int (* read_packet) (void * opaque, uint8_t * B Uf, int buf_size), int (* write_packet) (void * opaque, uint8_t * buf, int buf_size), offset_t (* seek) (void * opaque, offset_t offset, int whence) = 0; virtual AVInputFormat * av_probe_input_format (AVProbeData * pd, int is_opened) = 0; virtual AVInputFormat * partition (AVProbeData * pd, int is_opened, int * score_max) = 0; virtual int av_probe_input_buffer (AVIOContext * pb, AVInputFormat ** fmt, const Char * filename, void * logctx, unsigned int offset, unsigned int max_probe_size) = 0; virtual void av_dump_format (AVFormatContext * ic, int index, const char * url, int is_output) = 0; virtual int avio_open (AVIOContext ** s, const char * filename, int flags) = 0; virtual int avio_close (AVIOContext * s) = 0; virtual int avio_open_dyn_buf (AVIOContext ** s) = 0; virtual int avio_close_dyn_buf (AVIOContext * s, uint8_t ** Pbuffer) = 0; virtual offset_t avio_seek (AVIOContext * s, offset_t offset, int whence) = 0; virtual int avio_read (AVIOContext * s, unsigned char * buf, int size) = 0; virtual void avio_w8 (AVIOContext * s, int B) = 0; virtual void avio_write (AVIOContext * s, const unsigned char * buf, int size) = 0; virtual void avio_wb24 (AVIOContext * s, unsigned int val) = 0; virtual void avio_wb32 (AVIOContext * s, unsigned int v Al) = 0; virtual void avio_wb16 (AVIOContext * s, unsigned int val) = 0; virtual AVFormatContext * avformat_alloc_context (void) = 0; virtual int avformat_alloc_output_context2 (AVFormatContext * ctx, AVOutputFormat * oformat, const char * format_name, const char * filename) = 0; virtual AVStream * avformat_new_stream (AVFormatContext * s, AVCodec * c) = 0; virtual AVOutputFormat * av_guess_format (const char * short_na Me, const char * filename, const char * mime_type) = 0; virtual int avformat_write_header (AVFormatContext * s, AVDictionary ** options) = 0; virtual int av_write_trailer (AVFormatContext * s) = 0; virtual int av_write_frame (AVFormatContext * s, AVPacket * pkt) = 0; # if defined (SUCCESS) virtual AVRational av_stream_get_r_frame_rate (const AVStream * s) = 0; # endif }; // The encapsulated Dll inherits the DllDynamic And Interface class DllAvFormat: public DllDynamic, DllAvFormatInterface {extract (DllAvFormat, callback) LOAD_SYMBOLS () DEFINE_METHOD0 (void, callback) DEFINE_METHOD0 (void, callback) DEFINE_METHOD0 (void, callback) DEFINE_METHOD1 (AVInputFormat *, av_find_input_format, (const char * p1) DEFINE_METHOD1 (void, avformat_close_ I Nput, (AVFormatContext ** p1) DEFINE_METHOD1 (int, av_read_play, (AVFormatContext * p1) DEFINE_METHOD1 (int, av_read_pause, (AVFormatContext * p1) DEFINE_METHOD1 (void, complete, (AVFormatContext * p1) DEFINE_FUNC_ALIGNED2 (int, _ cdecl, av_read_frame, AVFormatContext *, AVPacket *) values (int, _ cdecl, av_seek_frame, AVFormatContext *, int, int64_t, int) DEFINE_FUNC_ALIGNED2 (I Nt, _ cdecl, delimiter, AVFormatContext *, AVDictionary **) DEFINE_FUNC_ALIGNED4 (int, _ cdecl, avformat_open_input, AVFormatContext **, const char *, AVInputFormat *, AVDictionary **) DEFINE_FUNC_ALIGNED2 (AVInputFormat *, _ cdecl, struct, AVProbeData *, int) DEFINE_FUNC_ALIGNED3 (AVInputFormat *, _ cdecl, struct, AVProbeData *, int, int *) DEFINE_F UNC_ALIGNED6 (int, _ cdecl, delimiter, AVIOContext *, AVInputFormat **, const char *, void *, unsigned int, unsigned int) DEFINE_FUNC_ALIGNED3 (int, _ cdecl, avio_read, AVIOContext *, unsigned char *, int) DEFINE_FUNC_ALIGNED2 (void, _ cdecl, avio_w8, AVIOContext *, int) terminate (void, _ cdecl, avio_write, AVIOContext *, const unsigned char *, int) DEFINE_FUNC_ALIGNED2 (void, _ cd Ecl, avio_wb24, AVIOContext *, unsigned int) values (void, _ cdecl, avio_wb32, AVIOContext *, unsigned int) values (void, _ cdecl, avio_wb16, AVIOContext *, unsigned int) DEFINE_METHOD7 (AVIOContext *, avio_alloc_context, (unsigned char * p1, int p2, int p3, void * p4, int (* p5) (void * opaque, uint8_t * buf, int buf_size), int (* p6) (void * opaque, uint8_t * buf, int buf_size), offs Et_t (* p7) (void * opaque, offset_t offset, int whence) DEFINE_METHOD4 (void, av_dump_format, (AVFormatContext * p1, int p2, const char * p3, int p4) DEFINE_METHOD3 (int, avio_open, (AVIOContext ** p1, const char * p2, int p3) DEFINE_METHOD1 (int, avio_close, (AVIOContext * p1 )) DEFINE_METHOD1 (int, avio_open_dyn_buf, (AVIOContext ** p1) DEFINE_METHOD2 (int, avio_close_dyn_buf, (AVIOContext * p1, uint8_t * * P2) DEFINE_METHOD3 (offset_t, avio_seek, (AVIOContext * p1, offset_t p2, int p3) DEFINE_METHOD0 (AVFormatContext *, avformat_alloc_context) DEFINE_METHOD4 (int, limit, (AVFormatContext ** p1, AVOutputFormat * p2, const char * p3, const char * p4) DEFINE_METHOD2 (AVStream *, avformat_new_stream, (AVFormatContext * p1, AVCodec * p2 )) DEFINE_METHOD3 (AVOutputFormat *, av_guess_format, (Const char * p1, const char * p2, const char * p3) DEFINE_METHOD2 (int, avformat_write_header, (AVFormatContext * p1, AVDictionary ** p2) DEFINE_METHOD1 (int, av_write_trailer, (AVFormatContext * p1) DEFINE_METHOD2 (int, av_write_frame, (AVFormatContext * p1, AVPacket * p2) # if defined (attributes) DEFINE_METHOD1 (AVRational, av_stream_get_r_frame_rate, (const AVStream * p1) # e Ndif Merge () Merge (partial, partial) Merge (avformat_network_init, partial) Merge (partial, partial) RESOLVE_METHOD (av_read_frame) RESOLVE_METHOD (av_read_play) Merge D (optional) RESOLVE_METHOD (optional) returns (optional, optional) RESOLVE_METHOD (optional) RESOLVE_METHOD (av_dump_format) RESOLVE_METHOD (Avio_open) Commit (avio_close) Commit (response) RESOLVE_METHOD (avio_read) RESOLVE_METHOD (response) Commit (avio_write) Commit (response) RESOLVE_METHOD (avio_wb16) RESOLVE_METHOD (avformat_alloc_context) RESOLVE_METHOD (avformat_alloc_output_context2) RESOLVE_METHOD (avformat_n Ew_stream) RESOLVE_METHOD (optional) RESOLVE_METHOD (avformat_write_header) RESOLVE_METHOD (optional) RESOLVE_METHOD (av_write_frame) # if defined (optional) RESOLVE_METHOD (optional) # endif Merge () /* dependencies of libavformat */DllAvCodec m_dllAvCodec; // DllAvUtil loaded implicitely by m_dllAvCodecpublic: void av_register_all () {CSingleLock lock (DllAvCodec: m_critSection); extract ();} int avformat_find_stream_info (AVFormatContext * ic, AVDictionary ** options) {CSingleLock lock (DllAvCodec: m_critSection ); return avformat_find_stream_info_dont_call (ic, options);} virtual bool Load () {if (! M_dllAvCodec.Load () return false; bool loaded = DllDynamic: Load (); CSingleLock lock (DllAvCodec: m_critSection); if (++ m_avformat_refcnt = 1 & loaded) callback (); return loaded;} virtual void Unload () {CSingleLock lock (DllAvCodec: m_critSection); if (-- m_avformat_refcnt = 0 & DllDynamic: IsLoaded ()) avformat_network_deinit_dont_call (); DllDynamic: Unload ();} protected: static int m_avformat_refcnt;}; # endif

These macros have the following meanings:

DEFINE_METHOD0 (result, name) defines a method (excluding parameters) DEFINE_METHOD1 (result, name, args) defines a method (one parameter) DEFINE_METHOD2 (result, name, args) define a method (two parameters) DEFINE_METHOD3 (result, name, args) define a method (three parameters) DEFINE_METHOD4 (result, name, args) define a method (four parameters) and so on... DEFINE_FUNC_ALIGNED0 (result, linkage, name) defines a method (excluding parameters) DEFINE_FUNC_ALIGNED1 (result, linkage, name, t1) defines a method (one parameter) DEFINE_FUNC_ALIGNED2 (result, linkage, name, t1, t2) defines a method (two parameters) and so on...

Let's take a look at the definition of these macros. After reading it for a while, I felt that there were too many macro definitions and they were messy. Here is only one example: RESOLVE_METHOD

#define RESOLVE_METHOD(method) \  if (!m_dll->ResolveExport( #method , & m_##method##_ptr )) \    return false;
From the definition, we can see that the m_dll method ResolveExport () is called (). But there is no m_dll variable in DllAvFormat. M_dll is actually located in the DllAvFormat parent class DllDynamic.

DllAvFormat inherits DllDynamic. DllDynamic is the class used to load Dll. Let's take a look at its definition:

// Dll dynamic loading class DllDynamic {public: DllDynamic (); DllDynamic (const CStdString & strDllName); virtual ~ DllDynamic (); virtual bool Load (); // Load virtual void Unload (); // uninstall virtual bool IsLoaded () const {return m_dll! = NULL;} // whether to load bool CanLoad (); bool EnableDelayedUnload (bool bOnOff); bool SetFile (const CStdString & strDllName); // set the file const CStdString & GetFile () const {return m_strDllName;} protected: virtual bool ResolveExports () = 0; virtual bool LoadSymbols () {return false;} bool m_DelayUnload; LibraryLoader * m_dll; CStdString m_strDllName ;};

There is a variable LibraryLoader * m_dll. Is used to load Dll.

You can see the main functions in DllDynamic to understand the role of this class.

// Load bool DllDynamic: Load () {if (m_dll) return true; if (! (M_dll = CSectionLoader: LoadDLL (m_strDllName, m_DelayUnload, LoadSymbols () return false; if (! ResolveExports () {CLog: Log (LOGERROR, "Unable to resolve exports from dll % s", m_strDllName.c_str (); Unload (); return false;} return true ;}

// Uninstall void DllDynamic: Unload () {if (m_dll) CSectionLoader: UnloadDLL (m_strDllName); m_dll = NULL ;}


Let's take a look at the definition of LibraryLoader. LibraryLoader itself is a pure virtual class, and the implementation of specific methods is in its subclass.

// Dll loading class LibraryLoader {public: LibraryLoader (const char * libraryFile); virtual ~ LibraryLoader (); virtual bool Load () = 0; virtual void Unload () = 0; virtual int ResolveExport (const char * symbol, void ** ptr, bool logging = true) = 0; virtual int ResolveOrdinal (unsigned long ordinal, void ** ptr); virtual bool IsSystemDll () = 0; virtual HMODULE GetHModule () = 0; virtual bool HasSymbols () = 0; char * GetName (); // eg "mplayer. dll "char * GetFileName (); //" special: // xbmcbin/system/mplayer/players/mplayer. dll "char * GetPath (); //" special: // xbmcbin/system/mplayer/players/"int IncrRef (); int DecrRef (); int GetRef (); private: LibraryLoader (const LibraryLoader &); LibraryLoader & operator = (const LibraryLoader &); char * m_sFileName; char * m_sPath; int m_iRefCount ;};
Shows the inheritance relationship of LibraryLoader.

Because your operating system is in Windows, you can see the definition of Win32DllLoader.

// Windows Dll loading class Win32DllLoader: public LibraryLoader {public: class Import {public: void * table; DWORD function ;}; Win32DllLoader (const char * dll );~ Win32DllLoader (); virtual bool Load (); // Load virtual void Unload (); // uninstall virtual int ResolveExport (const char * symbol, void ** ptr, bool logging = true); virtual bool IsSystemDll (); virtual HMODULE GetHModule (); virtual bool HasSymbols (); private: void OverrideImports (const CStdString & dll); void RestoreImports (); static bool ResolveImport (const char * dllName, const char * functionName, void ** fixup); static bool ResolveOrdinal (const char * dllName, unsigned long ordinal, void ** fixup ); bool NeedsHooking (const char * dllName); HMODULE m_dllHandle; bool bIsSystemDll; std: vector <Import> m_overriddenImports; std: vector <HMODULE> m_referencedDlls ;};
Load () is used to Load the Dll, and Unload () is used to uninstall the Dll (). Let's take a look at the specific code of these two functions.
// Load bool Win32DllLoader: Load () {if (m_dllHandle! = NULL) return true; // file path CStdString strFileName = GetFileName (); CStdStringW strDllW; substring (CSpecialProtocol: TranslatePath (strFileName), strDllW, false ); // load the library m_dllHandle = LoadLibraryExW (strDllW. c_str (), NULL, LOAD_WITH_ALTERED_SEARCH_PATH); if (! M_dllHandle) {LPVOID lpMsgBuf; DWORD dw = GetLastError (); FormatMessage (plaintext | FORMAT_MESSAGE_FROM_SYSTEM | delimiter, NULL, dw, 0, (LPTSTR) & lpMsgBuf, 0, NULL); CLog:: Log (LOGERROR, "% s: Failed to load % s with error % d: % s", _ FUNCTION __, CSpecialProtocol: TranslatePath (strFileName ). c_str (), dw, lpMsgBuf); LocalFree (lpMsgBuf); return false;} // handle Functions that the dll imports if (NeedsHooking (strFileName. c_str () OverrideImports (strFileName); else bIsSystemDll = true; return true;} // uninstall void Win32DllLoader: Unload () {// restore our imports RestoreImports (); // uninstall the library if (m_dllHandle) {if (! FreeLibrary (m_dllHandle) CLog: Log (LOGERROR, "% s Unable to unload % s", _ FUNCTION __, GetName ();} m_dllHandle = NULL ;}


Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.