About GStreamer 1.0 application development for beginners

63
GStreamer 1.0 Atmark-techno Inc. Dev, ShotaTAMURA [email protected]

Transcript of About GStreamer 1.0 application development for beginners

Page 1: About GStreamer 1.0 application development for beginners

GStreamer 1.0

Atmark-techno Inc.Dev, ShotaTAMURA

[email protected]

Page 2: About GStreamer 1.0 application development for beginners

目標

- GStreamer の全体像と構成要素についてざっくり知ってもらう

- 私が半年間やって知ったことの 6, 7割くらいをこの1時間で知ってもらう

Page 3: About GStreamer 1.0 application development for beginners

目次

- 1. GStreamer 概要- 全体像- 構成要素

- 2. もう少し詳しいこと- 内部構造的なこと- 実践的なこと

- GStreamer Tips

Page 4: About GStreamer 1.0 application development for beginners

GStreamer とは

image from: http://gstreamer.freedesktop.org/data/doc/gstreamer/head/manual/html/chapter-gstreamer.html

Page 5: About GStreamer 1.0 application development for beginners

GStreamer とは

GStreamerは、オープンソースのマルチメディアフレームワークです。

小さなコアライブラリに様々な機能をプラグインとして追加できるようになっており、多彩な形式のデータを扱うことができます。

※ Armadillo-840 製品マニュアル引用

Page 6: About GStreamer 1.0 application development for beginners

ちなみに

GStreamer は- オブジェクト指向な C で書かれています- Linux, Windows, Android, iOS, OS X で使えます- バージョンは

- 偶数が stable (..., 1.2, 1.4, ...)- 奇数が unstable (..., 1.3, 1.5, ….)

2015/6/7 に 1.5.1 (unstable) がリリースされている、活発なライブラリです。

Page 7: About GStreamer 1.0 application development for beginners

全体像

image from: http://gstreamer.freedesktop.org/data/doc/gstreamer/head/manual/html/section-intro-basics-communication.html

Page 8: About GStreamer 1.0 application development for beginners

全体像

GStreamerが提供

Page 9: About GStreamer 1.0 application development for beginners

全体像

ユーザーが実装

Page 10: About GStreamer 1.0 application development for beginners

全体像: Thread

GStreamer Application は大きく分けて 2 種類の Thread から成る

Application thread

Streaming threads

Page 11: About GStreamer 1.0 application development for beginners

全体像: Bus

Application thread

Streaming threads

Page 12: About GStreamer 1.0 application development for beginners

2つの Thread をつなぐ Bus

GStreamer の bus は

Streaming threads が自らの Context をApplication thread に伝えるためのシステム

※翻訳が間違ってたらすいません

Page 13: About GStreamer 1.0 application development for beginners

Streaming thread について

Application thread

Streaming threads

Page 14: About GStreamer 1.0 application development for beginners

Pipeline

Top-level Bin

自分の bus を持っている image from: http://gstreamer.freedesktop.org/data/doc/gstreamer/head/manual/html/chapter-helloworld.html

Page 15: About GStreamer 1.0 application development for beginners

Bin

Element の集まり

自分の bus は持っていない

image from: http://gstreamer.freedesktop.org/data/doc/gstreamer/head/manual/html/chapter-helloworld.html

Page 16: About GStreamer 1.0 application development for beginners

Element

4種類のElement- Src element- Filter element- Filter element (Pad が3つ以上)- Sink element

Page 17: About GStreamer 1.0 application development for beginners

Pad

Element

srcsink

Pad

Page 18: About GStreamer 1.0 application development for beginners

Pad

Element

srcsink

PadPad は Element の外界へのインターフェース

- Element 同士では- 接続 (Link)- Buffer の受け渡し- Event の受け渡し- etc...

Page 19: About GStreamer 1.0 application development for beginners

State Change

NULL READY PAUSED PLAYING

NULL READY PAUSED PLAYING

詳しくはこちらを参照http://gstreamer.freedesktop.org/data/doc/gstreamer/head/manual/html/section-elements-states.html

Page 20: About GStreamer 1.0 application development for beginners

Preroll は State ではありません

Preroll を気にするのは Sink Element だけ ↓

ちなみに

NULL READY PAUSED PLAYING

http://gstreamer.freedesktop.org/data/doc/gstreamer/head/pwg/html/chapter-other-base.html#section-base-sink

Prerolling

Prerolled

Page 21: About GStreamer 1.0 application development for beginners

Communication

Page 22: About GStreamer 1.0 application development for beginners

まとめ

- GStreamer Application は2つ以上の Thread から成る

- Application thread - Streaming threads

- Bus は Application thread と Streaming threadの架け橋

- Pipeline- Bus を持っている Bin

- Bin- Element の集まり

- Pad- Element の外界への

インターフェース- Element States

- NULL, READYPAUSED, PLAYING

- Communication- Buffer, Event,

Message, Query

Page 23: About GStreamer 1.0 application development for beginners

2. もう少し詳しいことを

- 内部構造的なこと- Buffer / Event flow- Thread について

- 実践的なこと- 簡単な GStreamer アプリの作り方- Appsink の使い方

Page 24: About GStreamer 1.0 application development for beginners

Buffer flow

Page 25: About GStreamer 1.0 application development for beginners

Buffer flow: GstBufferstruct GstBuffer { GstMiniObject mini_object;

GstBufferPool *pool;

/* timestamp */ GstClockTime pts; GstClockTime dts; GstClockTime duration;

/* media specific offset */ guint64 offset; guint64 offset_end;};

Page 26: About GStreamer 1.0 application development for beginners

Buffer flow: GstBufferImpltypedef struct{ GstBuffer buffer; gsize slice_size;

/* the memory blocks */

guint len; GstMemory *mem[GST_BUFFER_MEM_MAX];

/* memory of the buffer when allocated from 1 chunk */ GstMemory *bufmem;

/* FIXME, make metadata allocation more efficient by usingpart of the * GstBufferImpl */ GstMetaItem *item;} GstBufferImpl;

GstBuffer は複数の不連続なメモリ領域を持つことがある

gst_buffer_map() でこれを連続領域にすることができる

Page 27: About GStreamer 1.0 application development for beginners

Buffer flow

filter element

srcsink

sink element

sink_chain ()

pad_push ()

Page 28: About GStreamer 1.0 application development for beginners

gst_XXXXX_chain () →省略→ _chain()

実際の名前は)- gst_video_encoder_chain ()- gst_queue_chain ()- gst_qtdemux_chain ()- etc...

なぜ _chain () ?

Page 29: About GStreamer 1.0 application development for beginners

Event flow

Page 30: About GStreamer 1.0 application development for beginners

Event flow

filter element

srcsink

sink element

sink_sink_event ()

pad_push_event ()

Page 31: About GStreamer 1.0 application development for beginners

Event flow

filter element

srcsink

sink element

sink_src_event ()

pad_push_event ()

Event は downstream から upstream へ行くこともある

Page 32: About GStreamer 1.0 application development for beginners

Event flow: _sink_event()switch (GST_EVENT_TYPE(event)) {case GST_EVENT_CAPS:

[..]

case GST_EVENT_EOS:

[..]case GST_EVENT_STREAM_START:

[..]

case GST_EVENT_SEGMENT:[..]

default:ret = GST_VIDEO_ENCODER_CLASS (parent_class)->sink_event(enc,

event);break;

}

Page 33: About GStreamer 1.0 application development for beginners

_chain (), _sink_event ()Pad に 何か が来た時の処理は、 Pad に登録する

gst_pad_set_chain_function (basesink->sinkpad,gst_base_sink_chain);

gst_pad_set_event_function (

qtdemux->sinkpad,

gst_qtdemux_handle_sink_event);

Page 34: About GStreamer 1.0 application development for beginners

ちなみに

gst-launch の -e オプションは pipeline に EOS Event を送ります

gst-launch

pipelinebin

filter element

srcsink

sink element

sink

src element

src

Page 35: About GStreamer 1.0 application development for beginners

Threadqueue は内部で GstTask を使っているのでThread が増える

GstTask は pthread の wrapper libraryimage from: http://gstreamer.freedesktop.org/data/doc/gstreamer/head/manual/html/section-threads-uses.html

Page 36: About GStreamer 1.0 application development for beginners

Thread を見る

GDBで

- queue を使わなくても、2 Thread- application thread : main()- streaming thread : _chain(), etc...

Page 37: About GStreamer 1.0 application development for beginners

もう少し詳しいことを

- 内部構造的なこと- Buffer / Event flow- Thread について

- 実践的なこと- 簡単な GStreamer アプリの作り方- Appsink の使い方

Page 38: About GStreamer 1.0 application development for beginners

絶対 に書くこと

#include <gst/gst.h>

int main (int argc, char *argv[])

{

gst_init (&argc, &argv);

return 0;

}

GStreamer App の作り方

Page 39: About GStreamer 1.0 application development for beginners

GStreamer App の作り方

xvimagesinksink

pipelinegst_pipeline_new ()

gst_element_factory_make ()

gst_element_factory_make ()videotestsrc

src

Page 40: About GStreamer 1.0 application development for beginners

GStreamer App の作り方

pipeline

videotestsrcsrc

videotestsrcsrc

xvimagesinksink

xvimagesinksink

gst_bin_add ()

gst_bin_add ()

Page 41: About GStreamer 1.0 application development for beginners

GStreamer App の作り方

pipeline

videotestsrcsrc

xvimagesinksink

gst_element_link ()

Page 42: About GStreamer 1.0 application development for beginners

GStreamer App の作り方

gst_element_set_state (pipeline, GST_STATE_PLAYING);

pipeline

videotestsrcsrc

xvimagesinksink

Page 43: About GStreamer 1.0 application development for beginners

GStreamer App の作り方

gst_element_get_bus (pipeline)

pipeline

videotestsrcsrc

xvimagesinksink

bus

Page 44: About GStreamer 1.0 application development for beginners

GStreamer App の作り方

gst_bus_timed_pop_filtered ()

pipeline

videotestsrcsrc

xvimagesinksink

bus

Application

Page 45: About GStreamer 1.0 application development for beginners

AppSink の使い方

AppSink (AppSrc) は

Plugin Element を作成せずとも、

Element 内の処理をユーザーが実装できる Element

“new-sample” や “eos” など用意されているコールバック関数に

自分で実装した関数 (処理) を登録するだけ

とっても簡単

Page 46: About GStreamer 1.0 application development for beginners

AppSink の使い方

用意されているコールバック関数は inspect で確認

$ gst-inspect-1.0 appsink[..]Element Signals: "eos" : void user_function (GstElement* object, gpointer user_data); "new-preroll" : GstFlowReturn user_function (GstElement* object, gpointer user_data); "new-sample" : GstFlowReturn user_function (GstElement* object, gpointer user_data);

Page 47: About GStreamer 1.0 application development for beginners

AppSink の使い方

例えば、new-sample を使う場合

$ gst-inspect-1.0 appsink[..]Element Signals: "eos" : void user_function (GstElement* object, gpointer user_data); "new-preroll" : GstFlowReturn user_function (GstElement* object, gpointer user_data); "new-sample" : GstFlowReturn user_function (GstElement* object, gpointer user_data);

Page 48: About GStreamer 1.0 application development for beginners

AppSink の使い方

GstFlowReturn cb_new_sample (GstAppSink *sink, gpointer data){ [..]}int main (int argc, char *argv[]){ GstElemet *appsink_element; [..] g_signal_connect ( appsink_element, "new-sample", G_CALLBACK (cb_new_sample), &data); [..]}

Page 49: About GStreamer 1.0 application development for beginners

GStreamer Tips公式サイト

- http://gstreamer.freedesktop.org/

公式ドキュメントはこちら

- http://gstreamer.freedesktop.org/documentation/

Page 50: About GStreamer 1.0 application development for beginners

GStreamer Tips欲しいプラグインがあるか調べるときは

- コマンドラインで- gst-inspect-1.0 | grep -i xxxxxxxx

- ウェブページで- http://gstreamer.freedesktop.org/documentation/plugins.html- ※ Windows 用の ksvideosrc などはここに無いので基本 inspect で!

Page 51: About GStreamer 1.0 application development for beginners

GStreamer TipsGStreamer のコードを読むなら

これらすべてを clone してタグを作ろう

- gstreamer- http://gstreamer.freedesktop.org/modules/

- glib-2.0 (大事)- https://git.gnome.org/browse/glib/

Page 52: About GStreamer 1.0 application development for beginners

GStreamer TipsGStreamer のコードを読むなら

Devhelp が 便利

$ sudo apt-get install devhelp \ gstreamer1.0-plugins-xxxxx-doc \ gstreamer1.0-doc \ libglib2.0-doc

Vim や Emacs に Devhelp への

サポートプラグインがあるのでそれも一緒に。

Page 53: About GStreamer 1.0 application development for beginners

GStreamer Tipsサンプルコードが欲しい時は

タグを作ったディレクトリで

$ find -type f | grep examples | grep -e '\.c'

結果

./gst-plugins-good/tests/examples/v4l2/camctrl.c ./gstreamer/tests/examples/queue/queue.c ./gst-plugins-base/tests/examples/app/appsrc_ex.c ./gst-plugins-base/tests/examples/app/appsink-src.c ./gst-plugins-base/tests/examples/app/appsrc-stream.c [..]

Page 54: About GStreamer 1.0 application development for beginners

GStreamer Tips自分でビルドした GStreamer ライブラリを使うには

- Element そのものをビルドした時- GST_PLUGIN_PATH_1_0=/set/lib/path/.lib gst-launch-1.0 ....

- Element が使う so をビルドした時- LD_LIBRARY_PATH=/home/atmark/src/gst-plugins-acm/gst-plugin/src/.libs gst-launch-1.0

Page 55: About GStreamer 1.0 application development for beginners

GStreamer Tipsplaybin や decodebin、rtpbin など既存の Bin の中で、

どの Element が動いているかを知りたい時

http://manual.atmark-techno.com/armadillo-840/armadillo-840_product_manual_ja-1.5.1/ch15.html#sct.acm.about_gst_pipeline_img

Page 56: About GStreamer 1.0 application development for beginners

GStreamer Tips個人的によく使うもの

- src element- filesrc, multifilesrc, videotestsrc, v4l2src

- filter element- capsfilter, queue, identity, videoconvert- avdec_h264, x264enc, h264parse, qtmux, qtdemux

- sink element- filesink, multifilesink, fakesink, ximagesink

PC 上で映像を確認したいときは xvimagesink (videoconvert + ximagesink)が便利!!

Page 57: About GStreamer 1.0 application development for beginners

GStreamer Tipsいちおしの 3つ

- multifilesrc

- identity

- fakesink

multifilesrc location=”hoge%02d.txt” num-buffers=100multifilesrc location=”piyo%d.txt” loop=true

identity datarate=1024 drop-probability=0.3

※ “handoff” シグナルがあるので、bufferが通過するごとになにか処理させることも可能

fakesink num-buffers=30 sync=true async=falsefakesink dump=true

Page 58: About GStreamer 1.0 application development for beginners

GStreamer Tipsgst-launch の Pipeline の読みやすい書き方

読みやすい :)gst-launch-1.0 \filesrc location=/mnt/big-buck-bunny-30sec-fullhd.mp4 ! qtdemux name=demux0 \demux0.audio_0 ! queue ! acmaacdec ! audioresample ! audio/x-raw,rate=48000,channels=2 ! alsasink \demux0.video_0 ! queue ! acmh264dec ! acmfbdevsink device=/dev/fb0

読みにくい :(gst-launch-1.0 filesrc location=/mnt/big-buck-bunny-30sec-fullhd.mp4 \! qtdemux name=demux0 demux0.audio_0 ! queue ! acmaacdec ! audioresample \! audio/x-raw,rate=48000,channels=2 ! alsasink demux0.video_0 ! queue \! acmh264dec ! acmfbdevsink device=/dev/fb0

Page 59: About GStreamer 1.0 application development for beginners

GstElementstruct GstElement { GRecMutex state_lock;

/* element state */ GCond state_cond; guint32 state_cookie; GstState target_state; GstState current_state; GstState next_state; GstState pending_state; GstStateChangeReturn last_return;

GstBus *bus;

/* allocated clock */ GstClock *clock; GstClockTimeDiff base_time; GstClockTime start_time;

guint16 numpads; GList *pads; guint16 numsrcpads; GList *srcpads; guint16 numsinkpads; GList *sinkpads; guint32 pads_cookie;};

Page 60: About GStreamer 1.0 application development for beginners

GstElementstruct GstElement { GRecMutex state_lock;

/* element state */ GCond state_cond; guint32 state_cookie; GstState target_state; GstState current_state; GstState next_state; GstState pending_state; GstStateChangeReturn last_return;

GstBus *bus;

/* allocated clock */ GstClock *clock; GstClockTimeDiff base_time; GstClockTime start_time;

guint16 numpads; GList *pads; guint16 numsrcpads; GList *srcpads; guint16 numsinkpads; GList *sinkpads; guint32 pads_cookie;};

Page 61: About GStreamer 1.0 application development for beginners

Object Hierarchy

GObject ╰── GInitiallyUnowned ╰── GstObject ╰── GstElement ╰── GstQueue

GObject ╰── GInitiallyUnowned ╰── GstObject ╰── GstElement ╰── GstBaseSink ╰── GstFileSink

GObject ╰── GInitiallyUnowned ╰── GstObject ╰── GstElement ╰── GstBaseSrc ╰── GstPushSrc ╰── GstUDPSrc

Page 62: About GStreamer 1.0 application development for beginners

Object HierarchyPipeline も Element

GObject ╰── GInitiallyUnowned ╰── GstObject ╰── GstElement ╰── GstBin ╰── GstPipeline

Page 63: About GStreamer 1.0 application development for beginners

Object HierarchyPad はインターフェースなので Element ではない

GObject ╰── GInitiallyUnowned ╰── GstObject ╰── GstPad