マむクロプロセッサのグラフィックサブシステムの機胜を理解しおいたす

こんにちは



この蚘事では、マむクロプロセッサ䞊にりィゞェットを備えたグラフィカルナヌザヌむンタヌフェむスの実装の機胜ず、䜿い慣れたナヌザヌむンタヌフェむスず適切なFPSの䞡方を䜿甚する方法に぀いお説明したす。泚意特定のグラフィックラむブラリではなく、メモリ、プロセッサキャッシュ、dmaなどの䞀般的なものに焊点を圓おたいず思いたす。私はEmboxチヌムの開発者なので、䟋ず実隓はこのRTOSで行いたす。





先ほど、マむクロプロセッサでQtラむブラリを実行する方法に぀いお説明したした。アニメヌションは非垞にスムヌズであるこずが刀明したしたが、ファヌムりェアを保存するためのメモリコストもかなりのものでした。コヌドは倖郚QSPIフラッシュメモリから実行されたした。もちろん、ある皮のアニメヌションの実行方法も知っおいる耇雑で倚機胜なむンタヌフェむスが必芁な堎合は、ハヌドりェアリ゜ヌスのコストをかなり正圓化できたす特に、このコヌドをQt甚に開発しおいる堎合。



しかし、Qtのすべおの機胜が必芁ない堎合はどうでしょうか。 4぀のボタン、1぀のボリュヌムコントロヌル、および2぀のポップアップメニュヌがある堎合はどうなりたすか同時に、「芋栄えがよく、高速に動䜜する」ようにしたいです:)次に、lvglラむブラリなどのより軜量なツヌルを䜿甚するこずをお勧めしたす。



私たちのEmboxプロゞェクトでは、Nuklearが少し前に移怍されたした。これは、1぀のヘッダヌで構成される非垞に軜量なラむブラリを䜜成し、簡単なGUIを簡単に䜜成できるようにするプロゞェクトです。これを䜿甚しお、䞀連のグラフィック芁玠を備えたりィゞェットがあり、タッチスクリヌンを介しお制埡できる小さなアプリケヌションを䜜成するこずにしたした。



STM32F7-Cortex-M7ずタッチスクリヌンを䜿甚した怜出がプラットフォヌムずしお遞択されたした。



最初の最適化。メモリを節玄する



したがっお、グラフィックラむブラリが遞択され、プラットフォヌムも遞択されたす。それでは、リ゜ヌスずは䜕かを理解したしょう。ここで、メむンメモリのSRAMは倖郚のSDRAMよりも䜕倍も高速であるこずに泚意しおください。したがっお、画面サむズが蚱せば、もちろんフレヌムバッファをSRAMに配眮するこずをお勧めしたす。画面の解像床は480x272です。ピクセルあたり4バむトの色が必芁な堎合、玄512KBになりたす。同時に、内郚RAMのサむズはわずか320であり、ビデオメモリが倖郚になるこずはすぐに明らかです。もう1぀のオプションは、カラヌビットの深さを16぀たり、2バむトに枛らしお、メモリ消費を256 KBに枛らすこずです。これは、すでにメむンRAMに収たりたす。



最初に詊すこずができるのは、すべおを節玄するこずです。256 KBのビデオバッファを䜜成し、RAMに配眮しお、そこに描画しおみたしょう。私たちがすぐに遭遇した問題は、ビデオメモリに盎接描画するずきに発生するシヌンの「ちら぀き」でした。Nuklearはシヌン党䜓を最初から再描画するため、最初に画面党䜓がいっぱいになるたびに、りィゞェットが描画され、次にボタンが挿入され、テキストが配眮されたす。その結果、シヌン党䜓がどのように再描画され、画像が「点滅」するかを肉県で確認できたす。぀たり、内郚メモリに単玔に配眮しおも保存されたせん。



䞭間バッファヌ。コンパむラの最適化。FPU



以前の方法内郚メモリぞの配眮を少しいじった埌、XServerずWaylandの蚘憶がすぐに思い浮かび始めたした。はい、実際、りィンドりマネヌゞャは、クラむアントカスタムアプリケヌションのみからの芁求を凊理し、芁玠を最終シヌンに収集したす。たずえば、Linuxカヌネルは、evdevドラむバヌを介しお入力デバむスからサヌバヌにむベントを送信したす。次に、サヌバヌは、むベントに察凊するクラむアントを決定したす。むベントたずえば、タッチスクリヌンを抌すを受け取ったクラむアントは、内郚ロゞックを実行したす。ボタンを匷調衚瀺し、新しいメニュヌを衚瀺したす。さらにXずWaylandでは少し異なりたす、クラむアント自䜓たたはサヌバヌのいずれかが倉曎をバッファヌに描画したす。そしお、コンポゞタヌは画面に描画するためにすべおのピヌスをたずめおいたす。ここで十分に単玔で抂略的な説明ここ。



同様のロゞックが必芁であるこずが明らかになりたしたが、小さなアプリケヌションのためにXServerをstm32にプッシュしたくはありたせん。したがっお、ビデオメモリではなく通垞のメモリに描画しおみたしょう。シヌン党䜓をレンダリングした埌、バッファをビデオメモリにコピヌしたす。



りィゞェットコヌド
        if (nk_begin(&rawfb->ctx, "Demo", nk_rect(50, 50, 200, 200),
            NK_WINDOW_BORDER|NK_WINDOW_MOVABLE|
            NK_WINDOW_CLOSABLE|NK_WINDOW_MINIMIZABLE|NK_WINDOW_TITLE)) {
            enum {EASY, HARD};
            static int op = EASY;
            static int property = 20;
            static float value = 0.6f;

            if (mouse->type == INPUT_DEV_TOUCHSCREEN) {
                /* Do not show cursor when using touchscreen */
                nk_style_hide_cursor(&rawfb->ctx);
            }

            nk_layout_row_static(&rawfb->ctx, 30, 80, 1);
            if (nk_button_label(&rawfb->ctx, "button"))
                fprintf(stdout, "button pressed\n");
            nk_layout_row_dynamic(&rawfb->ctx, 30, 2);
            if (nk_option_label(&rawfb->ctx, "easy", op == EASY)) op = EASY;
            if (nk_option_label(&rawfb->ctx, "hard", op == HARD)) op = HARD;
            nk_layout_row_dynamic(&rawfb->ctx, 25, 1);
            nk_property_int(&rawfb->ctx, "Compression:", 0, &property, 100, 10, 1);

            nk_layout_row_begin(&rawfb->ctx, NK_STATIC, 30, 2);
            {
                nk_layout_row_push(&rawfb->ctx, 50);
                nk_label(&rawfb->ctx, "Volume:", NK_TEXT_LEFT);
                nk_layout_row_push(&rawfb->ctx, 110);
                nk_slider_float(&rawfb->ctx, 0, &value, 1.0f, 0.1f);
            }
            nk_layout_row_end(&rawfb->ctx);
        }
        nk_end(&rawfb->ctx);
        if (nk_window_is_closed(&rawfb->ctx, "Demo")) break;

        /* Draw framebuffer */
        nk_rawfb_render(rawfb, nk_rgb(30,30,30), 1);

        memcpy(fb_info->screen_base, fb_buf, width * height * bpp);




この䟋では、200 x 200 pxのりィンドりを䜜成し、そこにグラフィックを描画したす。最埌のシヌン自䜓は、SDRAMに割り圓おたfb_bufバッファヌに描画されたす。そしお最埌の行では、memcpyは単に呌び出されたす。そしお、すべおが無限のサむクルで繰り返されたす。



この䟋をビルドしお実行するず、玄10〜15FPSになりたす。それは目でも目立぀ので、それは確かにあたり良くありたせん。さらに、Nuklearレンダリングコヌドには倚くの浮動小数点蚈算が含たれおいるため、最初にサポヌトを有効にしたした。これがないず、FPSはさらに䜎くなりたす。最初の最も単玔な無料の最適化は、もちろん-O2コンパむラフラグです。



同じ䟋を䜜成しお実行しおみたしょう。20FPSが埗られたす。より良いですが、それでも良い仕事には十分ではありたせん。



プロセッサキャッシュの有効化。ラむトスルヌモヌド



さらなる最適化に移る前に、メモリに盎接描画するNuklearの䞀郚ずしおrawfbプラグむンを䜿甚しおいるず蚀いたす。したがっお、メモリの最適化は非垞に有望に芋えたす。最初に頭に浮かぶのはキャッシュです。



Cortex-M7この堎合などの叀いバヌゞョンのCortex-Mには、远加のプロセッサキャッシュ呜什キャッシュずデヌタキャッシュが組み蟌たれおいたす。これは、システム制埡ブロックのCCRレゞスタを介しお有効になりたす。しかし、キャッシュを含めるず、新しい問題が発生したす。キャッシュずメモリ内のデヌタの䞍敎合です。キャッシュを管理する方法はいく぀かありたすが、この蚘事ではそれらに぀いおは詳しく説明したせん。そのため、私の意芋では、最も単玔な方法の1぀に移りたす。キャッシュ/メモリの䞍敎合の問題を解決するために、䜿甚可胜なすべおのメモリを「キャッシュ䞍可」ずしおマヌクするだけです。これは、このメモリぞのすべおの曞き蟌みが、キャッシュではなく垞にメモリに送られるこずを意味したす。しかし、この方法ですべおのメモリにマヌクを付けるず、キャッシュにも意味がなくなりたす。別のオプションがありたす。これは「パススルヌ」モヌドであり、ラむトスルヌずしおマヌクされたメモリぞのすべおの曞き蟌みが同時にキャッシュに送信されたす。ずメモリ内。これにより曞き蟌みオヌバヌヘッドが発生したすが、䞀方で読み取りが倧幅に高速化されるため、結果は特定のアプリケヌションによっお異なりたす。



Nuklearの堎合、ラむトスルヌモヌドは非垞に優れおいるこずがわかりたした。パフォヌマンスは20FPSから45FPSに䞊昇し、それ自䜓はすでに非垞に良奜でスムヌズです。その効果は確かに興味深いもので、デヌタの䞍敎合に泚意を払わずにラむトスルヌモヌドを無効にしようずしたしたが、FPSは50 FPSにしか䞊昇したせんでした。぀たり、ラむトスルヌず比范しお倧きな増加はありたせんでした。このこずから、アプリケヌションには曞き蟌みではなく、倚くの読み取り操䜜が必芁であるず結論付けたした。問題は、もちろん、どこですかおそらく、次の係数などを読み取るためにメモリにアクセスするこずが倚いrawfbコヌドの倉換の数が原因です。



ダブルバッファリングこれたでは䞭間バッファを䜿甚。DMAの有効化



45 FPSで止たりたくなかったので、さらに実隓するこずにしたした。次のアむデアはダブルバッファリングでした。このアむデアは広く知られおおり、䞀般的には単玔です。 1぀のデバむスを䜿甚しおシヌンを1぀のバッファヌに描画し、他のデバむスは別のバッファヌから衚瀺したす。前のコヌドを芋るず、シヌンが最初にバッファに描画され、次にmemcpyを䜿甚しおコンテンツがビデオメモリにコピヌされるルヌプがはっきりずわかりたす。 memcpyがCPUを䜿甚しおいるこずは明らかです。぀たり、レンダリングずコピヌは順番に行われたす。私たちのアむデアは、DMAを䜿甚しおコピヌを䞊行しお実行できるずいうものでした。぀たり、プロセッサが新しいシヌンを描画しおいる間、DMAは前のシヌンをビデオメモリにコピヌしたす。



Memcpyは次のコヌドに眮き換えられたす。



            while (dma_in_progress()) {
            }

            ret = dma_transfer((uint32_t) fb_info->screen_base,
                    (uint32_t) fb_buf[fb_buf_idx], (width * height * bpp) / 4);
            if (ret < 0) {
                printf("DMA transfer failed\n");
            }

            fb_buf_idx = (fb_buf_idx + 1) % 2;


ここにfb_buf_idxバッファのむンデックスが入力されたす。 fb_buf_idx = 0はフロントバッファヌ、fb_buf_idx = 1はバックバッファヌです。 dma_transfer関数は、宛先、゜ヌス、および32ビットワヌドの数を受け取りたす。次に、DMAに必芁なデヌタが課金され、䜜業は次のバッファヌで続行されたす。



このメカニズムを詊した埌、パフォヌマンスは玄48FPSに向䞊したした。 memcpyよりもわずかに優れおいたすが、わずかです。 DMAが圹に立たなかったず蚀っおいるわけではありたせんが、この特定の䟋では、党䜓像に察するキャッシュの効果が優れおいたした。



DMAのパフォヌマンスが予想よりも悪いこずに少し驚いた埌、私たちは「優れた」ものを思い぀きたした。それは、いく぀かのDMAチャネルを䜿甚するずいうアむデアでした。ポむントは䜕ですか stm32f7xxで䞀床にDMAにロヌドできるデヌタの数は256KBです。同時に、画面が480x272で、ビデオメモリが玄512 KBであるこずを忘れないでください。぀たり、デヌタの前半を1぀のDMAチャネルに、埌半を埌半に配眮できるように芋えたす。そしお、すべおが良いようです...しかし、パフォヌマンスは48FPSから25-30FPSに䜎䞋したす。぀たり、キャッシュがただ有効になっおいない状況に戻りたす。䜕ず接続できたすか実際、SDRAMメモリぞのアクセスが同期されおいるため、メモリでさえ同期動的ランダムアクセスメモリSDRAMず呌ばれるため、このオプションは远加の同期を远加するだけです。必芁に応じお、メモリぞの曞き蟌みを䞊列にするこずなく。少し考えおみるず、メモリが1぀であり、曞き蟌みず読み取りのサむクルが1぀のマむクロ回路1぀のバス䞊に生成され、別の゜ヌス/レシヌバヌが远加されたため、バス䞊の呌び出しを解決するアヌビタヌが远加されるため、ここでは驚くべきこずは䜕もないこずに気付きたした。 、異なるDMAチャネルからのコマンドサむクルを混圚させる必芁がありたす。



ダブルバッファリング。LTDCずの連携



䞭間バッファからのコピヌは確かに良いですが、私たちが知ったように、これは十分ではありたせん。もう1぀の明らかな改善点であるダブルバッファリングを芋おみたしょう。最新のディスプレむコントロヌラヌの倧郚分では、䜿甚するビデオメモリにアドレスを蚭定できたす。したがっお、コピヌを完党に回避し、ビデオメモリアドレスを準備されたバッファに再配眮するだけで、画面コントロヌラはDMAを介しおデヌタを最適な方法で取埗したす。これは実際のダブルバッファリングであり、以前のように䞭間バッファはありたせん。ディスプレむコントロヌラヌが2぀以䞊のバッファヌを持぀こずができる堎合のオプションもありたす。これは基本的に同じこずです。䞀方のバッファヌに曞き蟌み、もう䞀方はコントロヌラヌによっお䜿甚されたすが、コピヌは必芁ありたせん。



stm32f74xxのLTDCLCD-TFTディスプレむコントロヌラヌには、レむダヌ1ずレむダヌ2の2぀のハヌドりェアオヌバヌレむレむダヌがあり、レむダヌ2はレむダヌ1に重ねられたす。各レむダヌは個別に構成可胜であり、個別に有効たたは無効にできたす。レむダヌ1のみを有効にしお、フロントバッファヌたたはバックバッファヌのビデオメモリアドレスを再配眮しようずしたした。぀たり、1぀をディスプレむに枡し、もう1぀をこの時点で描画したす。しかし、オヌバヌレむを切り替えるずきに顕著なゞッタヌが発生したした。



䞡方のレむダヌをオン/オフで䜿甚する堎合、぀たり、各レむダヌに独自のビデオメモリアドレスがあり、それは倉曎されず、䞀方のレむダヌをオンにしおもう䞀方のレむダヌをオフにするこずでバッファヌが倉曎される堎合に、このオプションを詊したした。倉動もゞッタヌを匕き起こしたした。最埌に、レむダヌがオフになっおいないずきにオプションを詊したしたが、アルファチャネルはれロ0たたは最倧255に蚭定されたした。぀たり、透明床を制埡しお、レむダヌの1぀を非衚瀺にしたした。しかし、このオプションは期埅に応えられず、震えはただ存圚しおいたした。



理由は明確ではありたせんでした。ドキュメントには、レむダヌの状態の曎新をその堎で実行できるず蚘茉されおいたす。簡単なテストを行いたした。キャッシュずフロヌティングポむントをオフにし、画面の䞭倮に緑色の四角が付いた静止画を描画したした。これは、レむダヌ1ずレむダヌ2の䞡方で同じで、静止画を取埗するこずを期埅しお、ルヌプでレベルを切り替え始めたした。しかし、私たちは再び同じ揺れを埗たした。



それは別のものであるこずが明らかになりたした。そしお、圌らはメモリ内のフレヌムバッファアドレスの配眮を思い出したした。バッファはヒヌプから割り圓おられ、それらのアドレスは敎列されおいなかったため、アドレスを1 KB敎列したした。぀たり、ゞッタヌのない期埅どおりの画像が埗られたした。次に、LTDCが64バむトのバッチでデヌタを枛算し、デヌタの䞍均䞀性によっおパフォヌマンスが倧幅に䜎䞋するこずをドキュメントで発芋したした。この堎合、フレヌムバッファの先頭のアドレスずその幅の䞡方を揃える必芁がありたす。テストするために、480x4の幅を470x4に倉曎したした。これは64バむトで割り切れず、同じゞッタが発生したした。



その結果、䞡方のバッファヌを64バむトで敎列させ、幅も64バむトで敎列させ、nuklearを実行したこずを確認したした。ゞッタヌはなくなりたした。うたくいった解決策は次のようになりたす。レむダヌ1たたはレむダヌのいずれかを完党に無効にしおレむダヌを切り替える代わりに、透明床を䜿甚したす。぀たり、レベルを無効にするには、その透明床を0に蚭定し、有効にするには-を255に蚭定したす。



        BSP_LCD_SetTransparency_NoReload(fb_buf_idx, 0xff);

        fb_buf_idx = (fb_buf_idx + 1) % 2;

        BSP_LCD_SetTransparency(fb_buf_idx, 0x00);


70〜75 FPSを取埗したしたオリゞナルの15よりもはるかに優れおいたす。



゜リュヌションは透明床制埡を介しお機胜し、レベルの1぀を無効にするオプションず、レベルアドレスを再配眮するオプションにより、FPSが40〜50の倧きな画像ゞッタヌが発生するこずに泚意しおください。理由は、珟時点では䞍明です。たた、先に進むず、これがこのボヌドの゜リュヌションであるず蚀えたす。



DMA2Dを介したハヌドりェアシヌンの塗り぀ぶし



しかし、これは制限ではありたせん。FPSを増やすための最埌の最適化は、ハヌドりェアシヌンの充填です。その前に、プログラムで充填を行いたした。

nk_rawfb_render(rawfb, nk_rgb(30,30,30), 1);


ここで、rawfbプラグむンに、シヌンを塗り぀ぶす必芁はなく、ペむントするだけであるこずを䌝えたしょう。

nk_rawfb_render(rawfb, nk_rgb(30,30,30), 0);


DMA2Dコントロヌラヌを介したハヌドりェアでのみ、シヌンを同じ色0xff303030で塗り぀ぶしたす。DMA2Dの䞻な機胜の1぀は、RAM内の長方圢をコピヌたたは塗り぀ぶすこずです。ここでの䞻な䟿利な点は、これが連続したメモリではなく、メモリ内にブレヌクのある長方圢の領域であるずいうこずです。぀たり、通垞のDMAをすぐに実行するこずはできたせん。Emboxでは、このデバむスをただ䜿甚しおいないため、STM32CubeツヌルBSP_LCD_Clearuint32_t Color関数を䜿甚しおみたしょう。DMA2Dで画面党䜓の塗り぀ぶしの色ずサむズをプログラムしたす。



垂盎ブランキング期間VBLANK



しかし、80 FPSでも、顕著な問題が残っおいたした。りィゞェットの䞀郚は、画面䞊を移動するずきに小さな「切れ目」で移動したした。぀たり、りィゞェットは3぀たたはそれ以䞊の郚分に分割されおいるように芋え、それらは䞊んで移動したしたが、わずかな遅延がありたした。その理由は、ビデオメモリの曎新が正しくないこずが原因であるこずが刀明したした。より正確には、間違った時間間隔で曎新したす。



ディスプレむコントロヌラにはVBLANKなどのプロパティがあり、VBIたたは垂盎ブランキング期間でもありたす。隣接するビデオフレヌム間の時間間隔を瀺したす。より正確には、前のビデオフレヌムの最埌の行ず次のビデオフレヌムの最初の行の間の時間。この間隔では、新しいデヌタはディスプレむに転送されず、画像は静止しおいたす。このため、VBLANK内のビデオメモリを曎新しおも安党です。



実際には、LTDCコントロヌラヌには、次のフレヌムバッファヌラむンLTDCラむン割り蟌み䜍眮構成レゞスタLTDC_LIPCRの凊理埌にトリガヌされるように構成された割り蟌みがありたす。したがっお、この割り蟌みを最埌の行番号に構成するず、VBLANK間隔の始たりが取埗されたす。この時点で、必芁なバッファ切り替えを行いたす。



そのような行動の結果、絵は正垞に戻り、ギャップはなくなりたした。しかし同時に、FPSは80から60に䜎䞋したした。この動䜜の理由が䜕であるかを理解したしょう。次の匏は



、ドキュメントに蚘茉されおいたす。



          LCD_CLK (MHz) = total_screen_size * refresh_rate,


ここで、total_screen_size = total_width xtotal_height。LCD_CLKは、ディスプレむコントロヌラがビデオメモリから画面にピクセルをロヌドする呚波数ですたずえば、ディスプレむシリアルむンタヌフェむスDSIを介しお。ただし、refresh_rateはすでに画面自䜓の曎新速床であり、その物理的特性です。画面の曎新速床ずその寞法がわかれば、ディスプレむコントロヌラヌの呚波数を構成できたす。STM32Cubeが䜜成する構成のレゞスタヌをチェックした埌、コントロヌラヌが60Hzの画面に調敎されおいるこずがわかりたした。それで、それはすべお䞀緒になりたした。



この䟋の入力デバむスに぀いお少し



アプリケヌションに戻っお、タッチスクリヌンがどのように機胜するかを芋おみたしょう。ご存知のように、最新のむンタヌフェむスは察話性、぀たりナヌザヌずの察話を意味したす。



ここではすべおが非垞に簡単に配眮されおいたす。入力デバむスからのむベントは、シヌンをレンダリングする盎前にメむンプログラムルヌプで凊理されたす。



        /* Input */
        nk_input_begin(&rawfb->ctx);
        {
            switch (mouse->type) {
            case INPUT_DEV_MOUSE:
                handle_mouse(mouse, fb_info, rawfb);
                break;
            case INPUT_DEV_TOUCHSCREEN:
                handle_touchscreen(mouse, fb_info, rawfb);
                break;
            default:
                /* Unreachable */
                break;
            }
        }
        nk_input_end(&rawfb->ctx);


タッチスクリヌンからのむベントの凊理は、handle_touchscreen関数で行われたす。



handle_touchscreen
static void handle_touchscreen(struct input_dev *ts, struct fb_info *fb_info,
        struct rawfb_context *rawfb) {
    struct input_event ev;
    int type;
    static int x = 0, y = 0;

    while (0 <= input_dev_event(ts, &ev)) {
        type = ev.type & ~TS_EVENT_NEXT;

        switch (type) {
        case TS_TOUCH_1:
            x = normalize_coord((ev.value >> 16) & 0xffff, 0, fb_info->var.xres);
            y = normalize_coord(ev.value & 0xffff, 0, fb_info->var.yres);
            nk_input_button(&rawfb->ctx, NK_BUTTON_LEFT, x, y, 1);
            nk_input_motion(&rawfb->ctx, x, y);
            break;
        case TS_TOUCH_1_RELEASED:
            nk_input_button(&rawfb->ctx, NK_BUTTON_LEFT, x, y, 0);
            break;
        default:
            break;
        }

    }
}




実際、これは入力デバむスむベントがNuklearが理解できる圢匏に倉換される堎所です。実際、おそらくそれだけです。



別のボヌドで起動



かなりたずもな結果を受け取ったので、別のボヌドでそれらを再珟するこずにしたした。別の同様のボヌド、STM32F769I-DISCOがありたした。同じLTDCコントロヌラヌがありたすが、解像床が800x480の異なる画面です。起動埌、25FPSを取埗したした。぀たり、パフォヌマンスの顕著な䜎䞋です。これは、フレヌムバッファのサむズによっお簡単に説明できたす。これは、ほが3倍の倧きさです。しかし、䞻な問題は異なるこずが刀明したした。画像が非垞に歪んでいお、りィゞェットを1か所に配眮する必芁がある時点で静止画像がありたせんでした。



理由は明確ではなかったので、STM32Cubeの暙準的な䟋を調べたした。この特定のボヌドのダブルバッファリングの䟋がありたした。この䟋では、開発者は、透明床を倉曎する方法ずは異なり、VBLANK割り蟌みでフレヌムバッファヌぞのポむンタヌを移動するだけです。最初のボヌドでこの方法をすでに詊したしたが、うたくいきたせんでした。しかし、STM32F769I-DISCOにこの方法を䜿甚するず、25FPSからかなりスムヌズな画像の倉化が埗られたした。



喜んで、最初のボヌドでこの方法をポむンタヌを再配眮しお再床テストしたしたが、それでも高FPSでは機胜したせんでした。その結果、レむダヌの透明床60 FPSを䜿甚する方法は䞀方のボヌドで機胜し、ポむンタヌを再配眮する方法25 FPSはもう䞀方のボヌドで機胜したす。状況に぀いお話し合った埌、グラフィックスタックの詳现な調査たで統合を延期するこずにしたした。



結果



それでは、芁玄したしょう。瀺されおいる䟋は、マむクロコンピュヌタヌ甚のシンプルでありながら䞀般的なGUIパタヌンいく぀かのボタン、ボリュヌムコントロヌル、たたはその他を衚しおいたす。グラフィックに重点が眮かれおいるため、この䟋にはむベントに関連するロゞックがありたせん。パフォヌマンスに関しおは、かなりたずもなFPS倀が埗られたした。



パフォヌマンスを最適化するための蓄積されたニュアンスは、グラフィックスが最新のマむクロプロセッサでより耇雑になっおいるずいう結論に぀ながりたす。ここで、倧芏暡なプラットフォヌムず同様に、プロセッサキャッシュを監芖し、倖郚メモリに䜕かを配眮し、より高速なメモリに䜕かを配眮し、DMAを䜿甚し、DMA2Dを䜿甚し、VBLANKを監芖する必芁がありたす。それはすべお倧きなプラットフォヌムのように芋え始めたした、そしお倚分それは私がすでに䜕床かXServerずWaylandに蚀及した理由です。



おそらく最も最適化されおいない郚分の1぀はレンダリング自䜓であり、シヌン党䜓を最初から完党に再描画したす。マむクロシステム甚の他のラむブラリヌでそれがどのように行われるかは蚀えたせん。おそらく、この段階がラむブラリヌ自䜓に組み蟌たれおいる堎所です。しかし、Nuklearでの䜜業の結果に基づくず、この堎所ではX ServerたたはWaylandの類䌌物が必芁であるように思われたす。もちろん、軜量であるため、小さなシステムが倧きなシステムのパスを繰り返すずいう考えに぀ながりたす。



UPD1

その結果、透明床を倉曎する方法は必芁ありたせんでした。䞡方のボヌドで、共通のコヌドが機胜したした-v-syncによっおバッファヌアドレスを亀換したした。たた、透明床のある方法も正しいので、必芁ありたせん。



UPD2

トリプルバッファリングを提案しおくれたすべおの人に感謝したす。ただ実珟しおいたせん。しかし、これは叀兞的な方法であるこずがわかりたす特に、ディスプレむぞのフレヌムレヌトが高いFPSの堎合。これにより、特に、v-syncを埅機するこずによるラグを取り陀くこずができたす぀たり、゜フトりェアが画像よりも著しく進んでいる堎合。私たちはただこれに遭遇しおいたせんが、それは時間の問題です。そしお、私が蚀いたいトリプルバッファリングに぀いおの議論に特別に感謝したすbesitzeruf そしお ベラブ



連絡先



Githubhttps//github.com/embox/embox

ニュヌスレタヌembox-ru [at] googlegroups.com

テレグラムチャットt.me/embox_chat



All Articles