VLCSourceCodeNote


数据结构


(1) 宏定义的超级父类-VLC_COMMON_MEMBERS:

/*****************************************************************************
 * Common structure members
 *****************************************************************************/

/* VLC_COMMON_MEMBERS : members common to all basic vlc objects */
#define VLC_COMMON_MEMBERS                                                  \
/** \name VLC_COMMON_MEMBERS                                                \
 * these members are common for all vlc objects                             \
 */                                                                         \
/**@{*/                                                                     \
    const char *psz_object_type;                                            \
                                                                            \
    /* Messages header */                                                   \
    char *psz_header;                                                       \
    int  i_flags;                                                           \
                                                                            \
    /* Object properties */                                                 \
    bool b_force;      /**< set by the outside (eg. module_need()) */ \
                                                                            \
    /* Stuff related to the libvlc structure */                             \
    libvlc_int_t *p_libvlc;                  /** (root of all evil) - 1 */ \
                                                                            \
    vlc_object_t *  p_parent;                            /**> our parent */ \
                                                                            \
/**@}*/                            

(2)  vlc_object_t : 主要的一个数据结构

/** The main vlc_object_t structure */
struct vlc_object_t
{
    VLC_COMMON_MEMBERS
};


typedef struct vlc_object_t vlc_object_t;


(3) vlc_value_t : 
/**
 * VLC value structure
 */
typedef union
{
    int64_t         i_int;
    bool            b_bool;
    float           f_float;
    char *          psz_string;
    void *          p_address;
    vlc_object_t *  p_object;
    vlc_list_t *    p_list;
    mtime_t         i_time;
    struct { int32_t x; int32_t y; } coords;

} vlc_value_t;

	----------
	关于Union: 这个数据结构。本质上讲与结构体相近,但从包装角度来看有所差异:
	Union中可以定义多个成员,union的大小由最大的成员大小决定。
	Union成员共享一块大小的内存,一次只能使用其中的一个成员。
	对某一个成员赋值,会覆盖掉其他成员的值(也不奇怪,因为Union中的成员共享一块内存。但前提是成员所占字节数相同。当成员所占字节数不同时,仅仅会覆盖掉相应字节上的值。
	,比如char成员赋值就不会把整个int成员覆盖掉,因为char只占一个字节,而int只占四个字节)。
	联合体union的存放顺序是所有成员都从低地址开始存放。

	再扯点关于Static关键字
	在C语言中,static的字面意思很容易把我们导入歧途,其实它的作用有三条。
	(1)第一个作用:隐藏。
	当我们同时编译多个文件时,所有未加static前缀的全局变量和函数都具有全局可见性。为理解这句话,我举例来说明。我们要同时编译两个源文件,一个是a.c,另一个是main.c。
	下面是a.c的内容
	#include增加这条语句
	char a = ‘A‘; // global variable
	void msg() 
	{	
     	printf("Hello\n"); 
	}	
	你可能会问:为什么在a.c中定义的全局变量a和函数msg能在main.c中使用?前面说过,所有未加static前缀的全局变量和函数都具有全局可见性,其它的源文件也能访问。
	此例中,a是全局变量,msg是函数,并且都没有加static前缀,因此对于另外的源文件main.c是可见的。
	如果加了static,就会对其它源文件隐藏。例如在a和msg的定义前加上static,main.c就看不到它们了。利用这一特性可以在不同的文件中定义同名函数和同名变量,而不必担心命名冲突。
	Static可以用作函数和变量的前缀,对于函数来讲,static的作用仅限于隐藏,而对于变量,static还有下面两个作用。
	(2)static的第二个作用是保持变量内容的持久。存储在静态数据区的变量会在程序刚开始运行时就完成初始化,也是唯一的一次初始化
	共有两种变量存储在静态存储区:全局变量和static变量,只不过和全局变量比起来,static可以控制变量的可见范围,说到底static还是用来隐藏的。
	(3)static的第三个作用是默认初始化为0。其实全局变量也具备这一属性,因为全局变量也存储在静态数据区。在静态数据区,内存中所有的字节默认值都是0x00,某些时候这一特点可以减少程序员的工作量。
	最后对static的三条作用做一句话总结。首先static的最主要功能是隐藏,其次因为static变量存放在静态存储区,所以它具备持久性和默认值0。
	下面是main.c的内容
	除了头文件,需要声明函数:void msg();
	int main(void)
	{    
	    extern char a;    // extern variable must be declared before use
	     printf("%c ", a);
	     (void)msg();
	    return 0;
	}

(4) input_thread_t : 
/**
 * Main structure representing an input thread. This structure is mostly
 * private. The only public fields are READ-ONLY. You must use the helpers
 * to modify them
 */
struct input_thread_t
{
    VLC_COMMON_MEMBERS

    bool b_error;
    bool b_eof;
    bool b_preparsing;
    bool b_dead;

    /* All other data is input_thread is PRIVATE. You can't access it
     * outside of src/input */
    input_thread_private_t *p;
};

--> input_thread_private_t *p:
/** Private input fields */
struct input_thread_private_t
{
    /* Global properties */
    double      f_fps;
    int         i_state;
    bool        b_can_pause;
    bool        b_can_rate_control;
    bool        b_can_pace_control;

    /* Current state */
    bool        b_recording;
    int         i_rate;

    /* Playtime configuration and state */
    int64_t     i_start;    /* :start-time,0 by default */
    int64_t     i_stop;     /* :stop-time, 0 if none */
    int64_t     i_run;      /* :run-time, 0 if none */
    int64_t     i_time;     /* Current time */
    bool        b_fast_seek;/* :input-fast-seek */

    /* Output */
    bool            b_out_pace_control; /* XXX Move it ot es_sout ? */
    sout_instance_t *p_sout;            /* Idem ? */
    es_out_t        *p_es_out;
    es_out_t        *p_es_out_display;

    /* Title infos FIXME multi-input (not easy) ? */
    int          i_title;
    input_title_t **title;

    int i_title_offset;
    int i_seekpoint_offset;

    /* User bookmarks FIXME won't be easy with multiples input */
    seekpoint_t bookmark;
    int         i_bookmark;
    seekpoint_t **pp_bookmark;

    /* Input attachment */
    int i_attachment;
    input_attachment_t **attachment;
    demux_t **attachment_demux;

    /* Main input properties */

    /* Input item */
    input_item_t   *p_item;

    /* Main source */
    input_source_t input;
    /* Slave sources (subs, and others) */
    int            i_slave;
    input_source_t **slave;

    /* Resources */
    input_resource_t *p_resource;
    input_resource_t *p_resource_private;

    /* Stats counters */
    struct {
        counter_t *p_read_packets;
        counter_t *p_read_bytes;
        counter_t *p_input_bitrate;
        counter_t *p_demux_read;
        counter_t *p_demux_bitrate;
        counter_t *p_demux_corrupted;
        counter_t *p_demux_discontinuity;
        counter_t *p_decoded_audio;
        counter_t *p_decoded_video;
        counter_t *p_decoded_sub;
        counter_t *p_sout_sent_packets;
        counter_t *p_sout_sent_bytes;
        counter_t *p_sout_send_bitrate;
        counter_t *p_played_abuffers;
        counter_t *p_lost_abuffers;
        counter_t *p_displayed_pictures;
        counter_t *p_lost_pictures;
        vlc_mutex_t counters_lock;
    } counters;

    /* Buffer of pending actions */
    vlc_mutex_t lock_control;
    vlc_cond_t  wait_control;
    int i_control;
    input_control_t control[INPUT_CONTROL_FIFO_SIZE];

    bool b_abort;
    bool is_running;
    vlc_thread_t thread;
};
	
-------> sout_instance_t

/** Stream output instance (FIXME: should be private to src/ to avoid
* invalid unsynchronized access) */
struct sout_instance_t
{
    VLC_COMMON_MEMBERS

    char *psz_sout;

    /** count of output that can't control the space */
    int                 i_out_pace_nocontrol;

    vlc_mutex_t         lock;
    sout_stream_t       *p_stream;
};


----------------------------------------> vlc_mutex_t 互斥对象

typedef struct vlc_thread *vlc_thread_t;
typedef struct
{
    bool dynamic;
    union
    {
        struct
        {
            bool locked;
            unsigned long contention;
        };
        CRITICAL_SECTION mutex;
    };
} vlc_mutex_t;




---------------------------------------> sout_stream_t

/** Stream output instance (FIXME: should be private to src/ to avoid
 * invalid unsynchronized access) */
struct sout_instance_t
{
    VLC_COMMON_MEMBERS

    char *psz_sout;

    /** count of output that can't control the space */
    int                 i_out_pace_nocontrol;

    vlc_mutex_t         lock;
    sout_stream_t       *p_stream;
};

-------------> es_out_t 
一系列函数指针
struct es_out_t
{
    es_out_id_t *(*pf_add)    ( es_out_t *, const es_format_t * );
    int          (*pf_send)   ( es_out_t *, es_out_id_t *, block_t * );
    void         (*pf_del)    ( es_out_t *, es_out_id_t * );
    int          (*pf_control)( es_out_t *, int i_query, va_list );
    void         (*pf_destroy)( es_out_t * );

    es_out_sys_t    *p_sys;
};

------------>input_item_t

struct input_item_t
{
    int        i_id;                 /**< Identifier of the item */

    char       *psz_name;            /**< text describing this item */
    char       *psz_uri;             /**< mrl of this item */

    int        i_options;            /**< Number of input options */
    char       **ppsz_options;       /**< Array of input options */
    uint8_t    *optflagv;            /**< Some flags of input options */
    unsigned   optflagc;

    mtime_t    i_duration;           /**< Duration in microseconds */


    int        i_categories;         /**< Number of info categories */
    info_category_t **pp_categories; /**< Pointer to the first info category */

    int         i_es;                /**< Number of es format descriptions */
    es_format_t **es;                /**< Es formats */

    input_stats_t *p_stats;          /**< Statistics */

    vlc_meta_t *p_meta;

    int         i_epg;               /**< Number of EPG entries */
    vlc_epg_t   **pp_epg;            /**< EPG entries */

    vlc_event_manager_t event_manager;

    vlc_mutex_t lock;                 /**< Lock for the item */

    uint8_t     i_type;              /**< Type (file, disc, ... see input_item_type_e) */
    bool        b_error_when_reading;/**< Error When Reading */
};

------------->input_source_t

/* input_source_t: gathers all information per input source */
typedef struct
{
    demux_t  *p_demux; /**< Demux plugin instance */

    /* Title infos for that input */
    bool         b_title_demux; /* Titles/Seekpoints provided by demux */
    int          i_title;
    input_title_t **title;

    int i_title_offset;
    int i_seekpoint_offset;

    int i_title_start;
    int i_title_end;
    int i_seekpoint_start;
    int i_seekpoint_end;

    /* Properties */
    bool b_can_pause;
    bool b_can_pace_control;
    bool b_can_rate_control;
    bool b_can_stream_record;
    bool b_rescale_ts;

    /* */
    int64_t i_pts_delay;

    bool       b_eof;   /* eof of demuxer */

} input_source_t;


------------->counter_t

typedef struct counter_t
{
    int                 i_compute_type;
    int                 i_samples;
    counter_sample_t ** pp_samples;

    mtime_t             last_update;
} counter_t;