Download presentation
Presentation is loading. Please wait.
1
Androidの 画面描画機構を チューニングする!
Speaker: 日本システム開発株式会社 第2事業部 石原 正樹
2
会社紹介 日本システム開発株式会社 ソフトウェアの受託開発 業務システム、組込みソフト事業など 詳しくはこちら 組込み事業では
Linux、Android、iTronのソフト開発 開発経験を生かした技術者教育 etc... 詳しくはこちら
3
テーマ(1) Androidの特徴の1つに「オープンソース」であることが挙げられます。 誰でも自由に使えるという良い面がありますが、
誰かのために最適化されたものではありません。 要求を満たすことができない部分は自身で最適化を行う必要が出てきます。
4
テーマ(2) 特に画面描画はその要求が大きくなりやすい。
今回はAndroidの画面描画の中枢を担うSurfaceFlingerをターゲットに、 課題となりやすいポイント どのような解決方法があるのか を紹介します。
5
Agenda ①SurfaceFlingerとは? ②SurfaceFlingerのチューニングポイント
色深度 描画速度 1アプリケーションのメモリ ③Nativeアプリケーションでの描画
6
① SurfaceFlinger とは?
7
SurfaceFlingerとは? 画面描画ソフトウェアスタックの中心に位置し、描画の実行、管理を行うコンポーネント。
8
SurfaceFlingerとは? SurfaceFlinger Androidアプリケーション JavaVM (Dalvik)
描画エンジン(OpenGLなど) User Kernel Linux FrameBuffer Videoデバイス
9
SurfaceFlingerの構成詳細 SurfaceFlingerの周辺の構成を、もう少し詳しく説明します。
10
SurfaceFlingerの構成詳細(1)
SurfaceFlingerは各アプリケーションに対し描画領域(Surface)を割り当てます。
11
SurfaceFlingerの構成詳細(2)
SurfaceFlingerは各Surfaceを取りまとめ、 描画エンジンを利用してFrameBufferに書き出しを行います。 アプリ アプリ Surface Surface SurfaceFlinger 描画エンジン OpenGL Copybit FrameBuffer
12
② SurfaceFlinger のチューニング ポイント
13
SurfaceFlingerのチューニングポイント
色深度 描画速度 1アプリケーションのメモリ
14
色深度 Android は 16bit カラーのみをサポートしている
昨今は携帯電話をはじめ32bitカラー(24bit以上)が要求されることが多いが、その要求に答えることができない
15
16bitカラー以上にするには? どこに修正を入れればよいか? SurfaceFlingerのFrameBuffer設定
16
SurfaceFlingerのFrameBuffer設定
現在の設定手順 システムの起動時に下記のようなやり取りが行われている FB情報取得 FrameBuffer SurfaceFlinger FBIOGET_VSCREENINFO 16bitカラー に変更! FBIOPUT_VSCREENINFO 16bitカラー で動作する ように設定! FBIOGET_VSCREENINFO FB設定反映の確認
17
SurfaceFlingerのFrameBuffer設定
つまり... FrameBuffer を32bitで設定し、 SurfaceFlingerがFrameBufferを32bitとして認識 できれば、実現は出来る 32bitカラー化 (16bitカラー以上)は
18
SurfaceFlingerのFrameBuffer設定
SurfaceFlingerで設定できる FrameBuffreフォーマットは? PIXEL_FORMAT_RGB_565 (default) 16bit RGB (565) フォーマット PIXEL_FORMAT_BGRA_8888 32bit BGRA(8888) フォーマット PIXEL_FORMAT_ARGB_8888 32bit ARGB(8888) フォーマット SurfaceFlingerには32bitカラーの考慮有り
19
SurfaceFlingerのFrameBuffer設定
32bit化の方法 FrameBuffer を32bitに設定 SurfaceFlinger で FrameBufferのフォーマットをPIXEL_FORMAT_BGRA_8888 として設定する SurfaceFlinger FrameBuffer FBIOGET_VSCREENINFO 32bitカラー に変更! PIXEL_ FORMAT_ BGRA_8888 FBIOPUT_VSCREENINFO 32bitカラー で動作する ように設定! FBIOGET_VSCREENINFO
20
アプリの生成するSurface Surface 32bppバッファ割当て
Android フレームワークが割り当てるSurfaceバッファのデフォルトは16bitカラー
21
アプリの生成するSurface Surface 32bppバッファ割当て
アプリが16bitカラーでは、SurfaceFlinger → FrameBufferを32bit化しても真価が発揮できない 16bpp 16bpp ??? 32bpp
22
Surfaceバッファにも32bit化の考慮有り
OPAQUE (default) 16bit RGB(565)のバッファを確保 TRANSPARENT 16bit RGBA(5551)のバッファを確保 TRANSLUCENT 32bit ARGB(8888)のバッファを確保 Surfaceバッファにも32bit化の考慮有り
23
Surface 32bppバッファ化 アプリのSurface生成のデフォルト設定をOPAQUE(16bpp)からTRANSLUCENT (32bpp) に変更することで既存アプリのSurfaceも32bit化が可能 32bpp 32bpp 32bpp
24
描画速度 32bitカラー化により次の問題が発生した。 16bitカラーのときに比べて描画性能が 1/10 に低下!!
25
デモ
26
描画速度 なぜ? Androidの描画エンジンは16bitカラーを前提としている このため、32bitカラー時の性能まで考慮されていない
27
描画速度 描画速度の改善にはどのような方法があるか? ハードウェアアクセラレータを使用したCopybitライブラリの使用
OpenGL描画エンジンの改善
28
Copybitライブラリの使用 Copybitライブラリとは? ハードウェア・アクセラレータを使用した2D描画エンジン・ライブラリ
29
Copybitライブラリの使用 Copybitライブラリとは? 出力 アプリ アプリ Surface Surface
/system/lib/hw/copybit/ro.hardware があるか探す SurfaceFlinger 存在していたらCopybitエンジン呼び出し! 描画エンジン OpenGL Copybit 出力 FrameBuffer
30
Copybitライブラリの使用 しかし… Copybitライブラリがなかった場合は?
AndroidのオープンソースプロジェクトにはCopybitライブラリは含まれていない! Copybitライブラリがなかった場合は? OpenGL汎用描画エンジンを使用する (=2D描画でもOpenGLが使われる) OpenGLはAndroidオープンソースプロジェクトに含まれているため、どの環境でも使用可能
31
OpenGLの性能問題 1/10 に低下したのはOpenGLライブラリが原因 16bitカラーを想定した高速化ルートは存在するが・・・
32
OpenGL汎用ルートは何故遅い? 全ての描画パターンに対応しているため、ピクセル単位で条件判定が発生 Surface 32bpp(α無し)
FrameBuffer Surface 32bpp(α無し) OpenGL 汎用描画 関数 Surface 32bpp(α有り) ボトルネック Surface 16bpp
33
16bppの場合は? Surface の条件毎に専用のモジュールを設定している 16 bit 32bpp⇒16bpp 特化関数
FrameBuffer 16 bit Surface 32bpp(α無し) Surface 32bpp(α有り) 32bpp⇒16bpp α有り特化関数 Surface 16bpp 16bpp⇒16bpp 特化関数
34
さらに ARM アーキテクチャの場合は? アセンブラにして高速化している
35
OpenGLの高速化には? Surface 単位に条件に応じたモジュールを作成 アセンブラ化して無駄なロジックを削る 32 bit
32bpp⇒32bpp 特化関数 FrameBuffer 32 bit Surface 32bpp(α無し) Surface 32bpp(α有り) 32bpp⇒32bpp α有り特化関数 Surface 16bpp 16bpp⇒32bpp 特化関数
36
デモ
37
1アプリケーションのメモリ 既に紹介したとおり、各アプリケーションにはSurfaceという描画領域が割り当てられます。
そのSurfaceに割り当てられる描画メモリは1アプリ単位で最大で8MBとなっています。
38
1アプリケーションのメモリ と、いうことは? 8MBを超える描画領域を必要とするアプリケーションはメモリ確保が出来ず起動に失敗する
32bitカラー化した場合、描画領域が16bitカラーの倍必要となるため問題となる可能性が上がる
39
1アプリケーションのメモリ では、どうすればよいか? Surface バッファのメモリの上限を 8MB 以上にする
40
③ Nativeアプリケーションでの描画
41
Natvieアプリとは? C/C++で記述したLinuxアプリケーションのこと
42
Androidのアプリは… 通常、Javaで実装を行います。 勿論、APIはJavaのクラスとなります。
43
でも、Java内部では… C/C++のコードが呼び出されています。(JNI)
44
ということは… NativeアプリでもJavaと同じようにGUIを持たせて共存できるのでは?
JavaよりNatvieアプリのほうが実行速度が速いのでは? そういった理由から、NatvieアプリでもSurfaceFlingerを利用した画面描画を行ってみました。
45
Javaアプリで描画 (既に説明済みですが)既存のJavaアプリは下図の構成で描画を行っています。
46
では、Nativeアプリではどのように描画するのか?
Surface Javaアプリと同じくSurfaceを生成して描画してあげればOK!!
47
仕組みをもう少し詳しく… JavaアプリとSurfaceFlingerはサーバ/クライアントの形式で接続を行っています。 接続
User Kernel Java アプリ Surface Flinger Frame Buffer 接続 Surface生成要求 Surface Surface Surface受け取り
48
仕組みをもう少し詳しく… JavaアプリとSurfaceFlingerはサーバ/クライアントの形式で接続を行っています。 接続
User Kernel Java アプリ Surface Flinger Frame Buffer 接続 Surface生成要求 描画 データ Surface Surface受け取り 書き込み 集荷 出力 Surface
49
Nativeアプリでの実現 その仕組みを利用して、同じ手順で接続・要求を行うことで実現できる。 Native 接続 アプリ
User Kernel Native アプリ Java アプリ Surface Flinger Frame Buffer 接続 Surface生成要求 Surface Surface Surface受け取り
50
SurfaceFlingerからはJavaアプリと同じに見える。(GUI共存が可能!!)
Nativeアプリでの実現 その仕組みを利用して、同じ手順で接続・要求を行うことで実現できる。 SurfaceFlingerからはJavaアプリと同じに見える。(GUI共存が可能!!) User Kernel Native アプリ Java アプリ Surface Flinger Frame Buffer 接続 Surface生成要求 描画 データ Surface Surface受け取り 書き込み 集荷 出力 Surface
51
デモ
52
Nativeアプリでの注意・補足(1) Javaアプリで使用していたCanvasや SurfaceViewといった描画クラスは、 Nativeアプリ用には用意されていない。 Nativeアプリにとって、Surfaceバッファは FrameBufferのメモリを直接さわっている のと同じイメージ 現状、描画は全てドットでベタ塗り
53
Nativeアプリでの注意・補足(2) アプリケーションを表示するレイヤに注意 レイヤ情報は整数値で管理されている。
既存Javaアプリの持つレイヤ情報を意識して値を決定する必要がある。 性能がどれだけかわる…? Android アプリとNative アプリで、実際に どれだけ性能アップするかは未評価(今後の 課題)
54
Nativeアプリで描画ができると… Linuxの既存GUIアプリをAndroid上で共存させられる可能性も…
55
以上、 ご清聴ありがとう ございました。
Similar presentations
© 2024 slidesplayer.net Inc.
All rights reserved.