2021年8月16日 星期一

Gstreamer详细指南 HOW TO DEBUG

 Gstreamer 提供的各种工具


这篇文章主要介绍Gstreamer提供的各种工具和LOG系统。

对于Gstreamer提供的各种工具,将按照linux man page的方式进行书写。

gst-launch 命令
gst-launch - 创建和运行一条pipeline

Synopsis
gst-launch  [OPTION...] PIPELINE-DESCRIPTION

Notice
gst-launch命令是提供给用户的调试工具,不要在应用程序里直接调用gst-launch命令,gstreamer提供了API:

gst_parse_launch()供应用程序调用,该API根据输入的pipeline-description为用户创建pipeline(gst-launch在内

部也是调用这个API来创建pipeline);

Options
--help 这个不用解释了吧;

-v, --verbose 打印pipeline的一些运行时信息, 例如caps的值, property的值,elements, state等等;

-q, --quiet 不打印任何LOG;

-m, --messages 打印pipeline的bus上的一些message,例如EOS;

-t, --tags  打印metadata相关的信息,例如专辑名,风格之类的;

-o FILE, --output=FILE 将pipeline的结构以XML表的形式存到文件"FILE"中;

-f, --no_fault 如果设置了该参数,gst-launch将不会捕捉SIGSEGV和SIGQUIT信号;

-T, --trace 打印gst-launch在创建pipeline的时候动态分配的一些对象的地址;

Gstreamer Options
--gst-version  打印gstreamer core的版本;

--gst-fatal-warnings 在pipeline出现warning的时候,会导致程序abort;

--gst-debug=STRING
gstreamer的log可以按照类别等级进行打印,STRING就是由“category_name : level”这种二元组的列表组成,

多个二元组用逗号分开;用--gst-debug-help查询所有的category_name的信息,可以用通配符‘*’来指定多个

category name; level的值根据gstreamer版本的有所不同,例如gstreamer 0.10.36支持0~7,其中0不会打印任何

信息,7将打出来所有的信息;例如,--gst-debug=GST_ELEMENT_*:3,oggdemux:5 表示将category name中带

有”GST_ELEMENT_”字符串并且level等级小于等于3的LOG全部打印出来,同时还将category name是

oggdemux并且level小于等于5的LOG全部打印出来;
 
--gst-debug-level=LEVEL,
不区分category,将所有的等级小于等于LEVEL的log全部打印出来。 0.10.36 LEVEL的取值范围是0~7;

--gst-debug-no-color,
gstreamer默认输出的Log按照等级不同区分颜色,设置该参数则不区颜色,这样对不支持颜色字符的终端就不会输出乱

七八糟的框框;

--gst-debug-disable, 禁用debug功能;

--gst-debug-help, 打印所有的category_name 以及默认的等级;

--gst-plugin-spew, 输出一些加载gstreamer插件的时候的错误信息;

--gst-plugin-path=PATH,设置插件查找的路径,多个路径用“:“分开;

--gst-plugin-load=PLUGINS, 指定需要预加载的插件(目前没有用上过)

Pipeline Description
Pipeline description由elements, bins, caps, links组成,用来指定Pipeline的组织形式。Pipeline description既可

以用来传递给gst-launch,也可以传递给gst_parse_launch()函数。

Elements
ELEMENT_TYPE [PROPERTY1 ...]

Creates an element of type ELEMENT_TYPE and sets the PROPERTIES

可以用gst-inspect命令来查看一个element支持哪些property,每个 property的类型以及默认值等。所有的

property都用 PROPERTY= VALUE的格式赋值,多个property之间用空格分开即可, 例如:

gst-launch-0.10 filesrc location=MPEG4_V_ONLY.avi ! decodebin2 ! ffmpegcolorspace ! autovideosink

其中黑体字表示创建一个filesrc类型的element,并且给“location”这个property赋值。

Bins
[BINTYPE.] ( [PROPERTY1 ...] PIPELINE-DESCRIPTION )

创建BINTYPE类型的bin,同时给该bin设置一些property,小括号中的pipeline-description用来说明该bin内部结构

以及bin内部各个elements是如何连接的,请注意BINTYPE后面有个点号,在gst-launch命令中基本上用不到Bins,

在写自己的APP的时候,可以将Bins传递给gst_parse_launch函数,这样gst_parse_launch将为你创建一个Bin而

不是Pipeline.

Links
Link用来说明如何连接两个element,Link的格式比较复杂,因此我从最简单的格式开始讲:

1, link只包含 " !",既下面的范式所示

   SRC_ELEMENT_TYPE [PROPERTY1... ]  !  SINK_ELEMENT_TYPE [PROPERTY1...]

SRC_ELEMENT_TYPE [PROPERTY1... ] 和SINK_ELEMENT_TYPE [PROPERTY1...]按照上面关于Elements

绍的方式书写即可,例如:
 
gst-launch filesrc location=music.mp3 ! filesink location=music.mp3.bak

2,link包含" !" 和element name,既下面的范式所示

   [[SRC_ELEMENT_NAME].]  !  [[SINK_ELEMENT_NAME].]

Links the element with name SRC_ELEMENT_NAME to the element with name

SINK_ELEMENT_NAME,SRC_ELEMENT_NAME和SINK_ELEMENT_NAME是在创建element的时候通过

name property指定的,注意NAME后面的点号!例如:

gst-launch filesrc  name=filesrc1 location=music.mp3 filesrc1. ! filesink1.  filesink name=filesink1 location=music.mp3.bak

这个命令在开始的时候创建了一个filesrc插件,并且命名为filesrc1,这样我们就可以用filesrc1来建立连接,对比第一

个例子和第二个例子,不难看出第一个范式是第二个范式的退化形式,是不是觉得范式二是多余的?但是并不是所有的

element都像filesrc和filesink这么简单,这两个element每次都仅仅连接一个element。但是像demux, mux,

tee,textoverlay,multiqueue,inputselector等等很多element同时需要连接好几个其它的elemenet。这样范式

一就没有办法工作了,因为范式一每次都是创建新的element,范式二不会创建新的element。例如:

gst-launch filesrc location=movie.mpg ! mpegdemux name=demuxer demuxer. ! queue ! mpeg2dec !

ffmpegcolorspace ! sdlvideosink demuxer. ! queue ! mad ! audioconvert ! audioresample ! osssink

这个命令用来播放一个既有音频又有视频的多媒体文件,一路用来播放video,一路用来播放audio。

我们将上面的pipeline description拆成三段就非常好理解了:

创建filesrc和mpegdemux,并且给demux命名为demuxer

filesrc location=movie.mpg ! mpegdemux name=demuxer

创建播放video的一系列的element,然后按照范式二,将这些element连接到demuxer上;

demuxer. ! queue ! mpeg2dec ! ffmpegcolorspace ! sdlvideosink

创建播放audio的一系列的element,然后按照范式二,将这些element连接到demuxer上;

demuxer. ! queue ! mad ! audioconvert ! audioresample ! osssink

3,link包含" !",element name, pad name既下图所示范式

[[SRC_ELEMENT_NAME].[PAD1_NAME,...]]   !  [[SINK_ELEMENT_NAME].[PAD1_NAME,...]]

跟第二个范式类似,只不过显示的指定了element的PAD_NAME,PAD_NAME可以通过gst-inspect查看。一般情况

下我们都不需要指定PAD_NAME, 如果PAD_NAME没有指定,gst-launch会比对link两边的element的所有的

pad,如果找到可以匹配的PAD则连接成果,否则会报Internal data error,例如:

gst-launch textoverlay name=overlay ! ffmpegcolorspace ! videoscale ! autovideosink   filesrc location=movie.avi ! decodebin2 ! ffmpegcolorspace ! overlay.video_sink filesrc location=movie.srt !
subparse ! overlay.text_sink

textoverlay插件对video和字幕进行mix,然后输出到一个videosink插件中,我们可以将上面的pipeline

description拆成下面的三段:

创建textoverlay并命名,然后按照范式二连接到实际的videosink;
textoverlay name=overlay ! ffmpegcolorspace ! videoscale ! autovideosink

按照范式三将ffmpegcolorspace连接到overlay的video_sink pad上,
filesrc location=movie.avi ! decodebin2 ! ffmpegcolorspace ! overlay.video_sink

按照范式三将subparse连接到overlay的text_sink pad上。
filesrc location=movie.srt ! subparse ! overlay.text_sink

上面的pipeline没有将播放audio 的path加上,如果你完全读懂了这篇blog,应该能够自己加上audio path。

Caps

MIMETYPE [, PROPERTY[, PROPERTY ...]]] [; CAPS[; CAPS ...]]

Caps用来指定两个element之间传输数据的类型,一般都不需要指定,关于CAPS这一部分linux man page说的非常详

细。

Gstreamer 提供的各种工具


gst-inspect和 gst-typefind命令。

gstreamer 使用的插件机制,允许系统提供者更新插件而不影响应用程序,因此我在跟客户交流的时候都强调不要直接包

含插件提供的头文件,这会导致你的应用程序跟具体的 插件绑定。gstreamer所有的插件都有统一的格式,因此你的应用

程序只需要包含gstreamer 提供的一些标准的头文件即可。但是客户经常会问我:“那我该如何查看各个插件提供的详细

功能呢? 例如插件A提供了什么样的property, 提供了哪些signal? 支持哪些caps?”答案就是用gst-inspect命令。

gst-inspect

gst-inspect   用来查看Plugin和Elements的接口信息,例如在用gst-launch命令的时候,你可能需要查看property的name,

或者在写 基于gstreamer框架的应用程序的时候,你也需要用gst-inspect来查看property, signal, caps等等,甚至你在开发

自己的插件的时候不知道应该创建什么样的pad_templete,这些时候你都可以借助 gst-inspect命令。

Synopsis
gst-inspect [OPTION...] [PLUGIN|ELEMENT]

Options
gst-inspect accepts the following arguments and options:

PLUGIN
Name of a plugin.  一般来说你肯定不记得plugin name,不过gstreamer插件在Linux环境下以so的形式存放,因此你可



以直接将该so的名字作为gst-inspect的参数就好了,例 如:gst-inspect libgsttta.so. 将so的文件名前面的libgst和.so



去掉就是plugin 的名字。libgsttta.so对用的plugin 名字是tta。

ELEMENT
Name of an element. 例如qtdemux, 一般来说你也很难记住element的名字,但是你知道你想要的功能,例如demux,



这个时候只需要执行 gst-inspect | grep demux. gst-inspect如果不带任何参数,会将系统当前所有的插件和elemeent



的信息列举出来,这时再grep你想要的插件就好了。



gst-inspect不带任何参数的时候,输出的格式如下:



Plugin Name:   Element Name: Descriptions



例如:

avi: avidemux: Avi demuxer


--help
Print help synopsis and available FLAGS



-a, --print-all


打 印出所有的plugin和element的信息,上面说如果gst-inspect不带任何参数也会打印出所有的信息,不过这些信息



仅仅是一个简单的列 表,而gst-inspect -a将会打印非常详细的信息。自己试验下就知道了。我只用过一次-a参数,



就是在自己写插件的时候不知道该定义什么样的caps,这个时候用gst- inspect -a 然后用grep命令去检索各种Caps.


--print-plugin-auto-install-info
--gst-debug-mask=FLAGS
--gst-mask=FLAGS
--gst-plugin-spew
这四个参数,我做完一个完整的量产过的项目也没用上,因此就不做介绍;

--gst-plugin-path=PATH
添 加插件的搜索路径,多个路径用冒号分开;

gst-inspect element输出的格式如下:
Factory Details    //typefinder在根据caps查找对应的element的时候会参考这一项


Plugin Details  //


Object Hierarchy  //

...

Pad Templates  //在你开发自己平台的gstramer插件的时候,可以从这里抄caps

...

Element Flags:

...

Element Implementations:  //列出来该element重写了哪些方法

...

Pads:  //列举该element有哪些pad

...

Element Properties //列举出该element所有的properties

...

Element Signals   //列举出该element所有的signal.


至 此gst-inspect命令介绍这么多了。

gst-typefind
Find the file corresponding MIME type,你可以用这个工具帮你判断文件的类型,然后根据文类型编写caps信息。

沒有留言:

張貼留言