linux一覧

DRM/KMS についてメモ

以下のメモは概要把握としては間違っていないようには心がけたつもりですが、
間違っている可能性が大いにありますので、鵜呑みにしないようご注意ください。

DRI, DRM, KMS の目的

昔は Xサーバーが描画を一手に引き受けていたため、描画に関するコードが X依存になってしまっていた。OpenGL など最近のグラフィックスを描画使用したいケースで問題になってしまう。また Xorg の設計が古くて現状耐えられない状況にきていたりもするようで。

LibDRM

DRMカーネルモジュールはユーザー空間に危険な(不安定な)APIを公開しているので、
アプリが直接この DRMのモジュールを使うべきではない。その代わりに libDRM が提供されているので、アプリはこちらを使用する。この libDRM は Xからも使用される。

DRM (DRMcore)

カーネルモジュールです。これはすべてのカードに適用されるモジュールです。
このモジュールがロードされるとカード固有の DRM ヘルパモジュールが動きだして、
機能ポインタのセットを含めた状態でシステムに登録される。
これにより /dev/dri/card0 などのデバイスファイルが作成・登録される

KMS (Kernel Mode Setting)

ユーザースペースではなくカーネル空間側でディスプレイの解像度・色深度を設定するモジュールです。他の利点としてシステムは素早くグラフィックスの機能を使用可能になったり、ちらつきの問題改善などがあるらしい。

DRM/KMS

これらをまとめて DRM/KMS という表記をしている模様。つまり KMS をサポートしたドライバがあるなら libDRM を直接叩いて描画コードを作れば、X11(Xorg) なしでも画面描画が可能になりそうな感じです。Xサーバーの実装さえ、この libDRM 経由っぽいですし。

これらの関係らをブロック的に表すとこういうことだろうかと思います。
libdrmkms


Linux で BonCasLink のクライアント側を実現

前回は BonCasLink のサーバー側の話だったので、今回は逆のクライアントをLinuxでやるお話です。Linuxで録画用のプログラムは recpt1 が標準的なようなのでこれについては既に使えている前提でここでは話を進めていきます。

必要なもの

  • PT3などLinuxでの録画環境が構築された環境
  • BonCasLinkのサーバーが動作している他PC

インストール

BCASに関しての部分をフックするようなプログラムを作成してくれた方がいるのでその成果物である b25-remote を使わせてもらいます。これは Rec10 というプロジェクトのサブプロジェクトという位置づけのようです。

まずはこの Rec10 のコードを取得してきます。こちらは現在 bitbucket 上にあるようです。

取得してきたコードの中に b25-remote というフォルダがあり、この中にソースコードが収められているのでライブラリを以下のようにして作成します。

これでインストールまで完了です。ここで出来る成果物のうち使うのは b25-client.so がキーとなります。

使い方

以下の環境変数を設定します。

  • LD_PRELOAD=”b25-client.so のフルパス”
  • B25_SERVER_IP=BonCasLinkのサーバーが動いているPCのアドレス
  • B25_SERVER_PORT=BonCasLinkのサーバーが動いているPCのポート番号

これらを設定した状態で、 recpt1 を –b25 オプション付きで動かして、うまく動作すれば(映像が見れるようであれば)OKだと思います。

参考

https://osdn.jp/projects/rec10/scm/svn/blobs/head/b25-remote/Readme.txt
のドキュメントを参考にしました。


Debian Jessie で RADEON のドライバを入れる

標準インストールで xfce が入った状態だったので気にもしていなかったのですが、glxinfo を実行してみたらレンダラが llvmpipe になっており、ドライバがちゃんと入っていないことに気づきました。

ちょっともったいないので RADEON 用のドライバを入れることにしました。KernelModeSetting のためにはファームを入れろ、と起動時のログにも出ているのを今更ながら発見しました。

まず DRIモジュールとファームウェアバイナリを入れるために、/etc/apt/sources.list を編集します。contrib, non-free がデフォルトのものに追加されたような感じになります。

編集したら更新してから、パッケージを入れます。

あとは再起動後に有効になっていると思います。glxinfo などで llvmpipe ではなく、今回インストールしたドライバが使用されているかと思います。

OpenGL バージョンは 3.3、 OpenGL ES は 3.0 あたりになりそうです。ハードウェアとしては 4.0 もいけるはずなのですが、オープンソースドライバですし仕方ないことなのかもしれません。

glxinfoなど

glxinfo は mesa-utils パッケージにあるようです。

ソフトウェアレンダラだとこのように表示されます。llvmpipe は従来と比べると出来の良いレンダラで割とまともに動作します。


PowerVR SGX*** のカーネルドライバのソースコード

結構触っていない期間が長くなってしまいましたが MIPS Creator CI20 の最近の様子はどうだろうと思って調べてみました。http://elinux.org/MIPS_Creator_CI20 にアクセスしてみたら、実は既にこのボードって3世代くらいになっているようです。形的には最新の世代の正方形に近いものがいいなぁと思ってます。しかし未だに日本の発売はなさそうで、残念。

今の最新では Debian 8 の環境開発が進んでいるようで、SGXドライバが使えないという話は昔の話となりつつあるような感じです。そして自分が使っていたシステムイメージなどは CI20_Distros_Legacy のページに行ってしまっていました。
そしてこのページには Debian 8 Jessie 部分で、”Graphics acceleration will not work (the powervr drivers currently don’t work with xorg 1.16).” なんて記載が残ってました。現行のページでは release note にもそんな話は見当たらないので、そこそこ使えたりするんじゃないでしょうか。そのうち時間できたら試してみるかもしれません。

その一方で驚いたのが CI20_Dev_Zone のページです。こちらは通常は覗くことがないかもしれません。自分もたまたま発見したのですが、このページの後半で Linux Kernel のビルドに関しての説明があるあたりで驚きました。
 それが “Building GPU Kernel Module from sources” という部分です。 PowerVR の SGX のドライバは今まではバイナリ提供でソース類を明かさなかったのですが、コレを見るとカーネル部分のドライバソースも公開されているようです。これらに関してはこちらの CI20-SGX_kernel_moduleのページのようです。ここでは 3.0.8 でも 3.18 カーネルでも対応してるっぽいです。

 ちょっと興味があったので中身を開けてみたら、 pvrsrv のソースっぽいものがあったり、各PowerVR のチップ(sgx530, sgx535, sgx543, sgx544, sgx540)といったもののレジスタのヘッダがあったりととてもおもしろい気がします。このあたりのチップは他の組込ボードでも使われているケースがあるので、割と使えるものな気がしています。

OpenGL も動くグラフィックスドライバがソースコード付きの公開というのは自分は初めて見た気がします。これはとても興味深いですね。(ただしOpenGLの解釈部分などはここじゃないようですが)


Ubuntu で USBシリアルケーブルを使う 続編

前回は minicom でつながるのを確認しました。あれからそもそも Raspberry Pi だったらシリアルコンソールで操作も可能だったことを思い出して、そちらでも確認をと思ったので今回のメモを書いてます。
Raspbery Pi は Raspberry Pi 2 のことをさしています。またシリアル出力を有効化する詳細な手順と、一般ユーザーでもシリアルを使えるようにする手順については今回省略させていただきます。一般ユーザーでも使えるようにする方法は以前の日記を参照してください。

ツール: gtkterm

GUIもあるターミナルソフトです。これをインストールしてみました。

デフォルト設定を作ることができ、ここでデバイスのパラメータを指定することができます。GUIから起動させる場合にはデフォルト設定を使った方が便利な気がします。
ubuntu-serial-1
コンソールであれば起動のオプションで指定も可能です。省略すればデフォルト設定が使われるようです。
ubuntu-serial-2

ツール: screen

コンソール作業では割とおなじみらしい screen です。

使い方はオプションにデバイスらのパラメータを入れます。

ubuntu-serial-3
screen の終了のさせ方は知らないとわからないので注意。
”Ctrl+a”, ”k”と押します。

終了確認が問われるので “y” をタイプして終了します。
ubuntu-serial-4

起動時のログなど

Raspberry Pi の起動時からシリアルをつないであったとき、以下のように動いてました。
ubuntu-serial-5


USBシリアルケーブルを買った(PL2303のやつ)

Raspberry Pi 2 との接続のためにお遊びで USB シリアル変換ケーブルを買ってみたのですが、 Windows 8.x 以降ではいろいろな問題のために使えないというシロモノでした。普段の環境は Windows7 だったりするので問題に直面しているわけではないですが、今後のことも考えて対策を考えてみました。
 その結果が Ubuntu で使用する!です。こちらならばドライバの問題はなさそうなので。今回はその設定についてメモしておこうと思います。 続きを読む


Jetson TK1をSDカード起動にする

Jetson TK1のシステムや作業領域としてSDカードを使用するように切り替えました。
容量の問題とか書き換え回数制限とか気にしてです。SDカードならシステム破壊するようなことをしても、交換可能ですし、バックアップもやりやすそうですし、メリットが多くあると思います。

準備

ここではVMware上の Ubuntu 14.04 で作業しました。
必要なファイル群をNVIDIAから入手します.

Tegra124_Linux_R19.3.0.armhf.tgz2
Tegra_Linux_Sample-Root-Filesystem_R19.3.0_armhf.tbz2

そしてこれを適当なところに展開して、コマンドを実行します。
これらの作業コマンドを以下に示しておきます。

$ wget https://developer.nvidia.com/sites/default/files/akamai/mobile/files/L4T/Tegra124_Linux_R19.3.0_armhf.tbz2
$ wget https://developer.nvidia.com/sites/default/files/akamai/mobile/files/L4T/Tegra_Linux_Sample-Root-Filesystem_R19.3.0_armhf.tbz2
$ tar xpf Tegra124_Linux_R19.3.0_armhf.tbz2
$ cd Linux_for_Tegra/rootfs
$ sudo tar xpf ../../Tegra_Linux_Sample-Root-Filesystem_R19.3.0_armhf.tbz2
$ cd ../
$ sudo ./apply_binaries.sh

書き込み

ファイル群が準備できたので、これをSDカードに書き込みます。
手元のカードリーダーでSDカードを装着して確認したところ、/dev/sdb として認識しているようでした。各自の環境ではこのあたりが変わると思いますので、適宜読み替えて下さい。

SDカードがフォーマットされたところで、データを書き込みます。

Jetson TK1をUSB(microUSBのほう)でLinux環境と繋いでリカバリーモード起動させます。
リカバリーモードに入るには、Recoveryスイッチを押しながら、Resetスイッチを押します。

リカバリーモードに入った後で、Linux環境で以下のコマンドを実行します。
念のため、認識できているか lsusb で確認しています。
リカバリーモードに入っているときには、画面に何も出力されないので…。

というように表示されて、正常に書き込まれるとJetson TK1が再起動されます。

fastboot.bin というバイナリが送られているようですし、方式としてはfastbootのほうでしょうか。
19.3バージョンからは、U-BOOTもサポートされたとありましたし、そのうち試してみたいところです。

再起動後、SDカードを挿さないままだと、起動が途中で止まるはずです。
止まったことを確認したら、SDカードを挿入してみます。
うまくいけば、ここから起動シーケンスが再開されていくと思います。
(画面が出ないようなら、リセットして試してみましょう)

初期設定など

Jetson TK1が無事にSDカードから起動できたら、初期設定をしておきます。
タイムゾーンは Asia/Tokyo を選択して時刻を合わせておきます
(実際にはRTCは、電源OFFでリセットされちゃうんですが・・・)
他にもリポジトリの設定とか。

コマンドが見つからなかった場合のヘルプ(どのパッケージに入ってるのか)を出すための設定.

最後に使用量を確認しておきます。
SDカードが16GBの物を使っているのでこんな感じでした。

デフォルトの eMMCに入っている時には 8GBほどのパーティションだったと思います。
上記のように15Gが表示されていますし、無事にSDカードのシステムが使われているように思います。

感想とか

最後に感じたことを1つ。
安物SDカードだとか、クラスの低いものを使っていると、操作に引っかかりをよく感じます。
気になる人は、ちゃんとした高速なものを使用するようにしましょう。

最後に

元の起動に戻す方法は、リカバリーモードにして以下のコマンドを実行します。


cygwinでクロスコンパイラのmake

ARM用クロスコンパイラのビルド(Windows8+Cygwin)
を参考にCygwinでクロスコンパイラのビルドをしてみました。
さすがに全部入りの状態なので、cygwinのインストールには時間がかかりました。

確かにgccのビルドまで成功までいけたのですが、thread modelがsingleに。
これをposix となるように –enable-threads=posix とするとgccのmake時にエラーとなってしまいうまくいかず…。

というエラー行が発端なので、pthread.hが正しく読み込めていないんだろうと思います。
(ファイルはあるけど中身がおかしい?)

Windowsでクロスコンパイラの準備から始めるのはちょっと大変なのがわかりました。


cygwinでcrosstool-ngのmake

クロスコンパイラなどのクロスツールチェインを作るためのツールとして、crosstool-ngが便利です。
Ubuntuなどではこれを利用してクロス環境を整えるのがとても手軽だと思っています。
今回はそのcrosstool-ngをWindowsのcygwinで生成できないかを試してみました。

そもそも、crosstool-ng は http://crosstool-ng.org/ で入手できます。
これを cygwin で使用するためには以下のパッチを適用します。このパッチはここで紹介されていましたが、パッチファイルがダウンロードできないようだったので、ここにテキストとして貼り付けておきます。

このパッチを適用してmakeする例としてはこんな感じで。

実際に動かす際には、Windowsのファイルシステムにおいて大文字小文字を区別するように変更する必要があるようです。
レジストリの次の場所を書き換えます。

実行とまとめ

/opt/cross/bin/ct-ng が実行可能状態になっていると思います。
あとはパスを通して実行できるように下上で、 ct-ng menuconfig や ct-ng build でツールチェインのビルドが可能だと思います。ただし、手元の環境ではどうもgccのmake途中でエラーになってしまいうまくいきませんでした。設定関連がわるい可能性があるので、それは調査中です


クロスコンパイラgccのビルド -成功編

ようやくクロスコンパイラ gccをmakeすることに成功しました。
JetsonTK1をターゲット想定なので、デフォルトで hard float を使用するようにしたかったので、その設定となるようにしています。
早速その手順をここに書いておきたいと思います。

makeinfoのバージョンが5以降だとエラーになるようなので、それ以前のものをインストールしておきます。

$ sudo apt-get install ncurses-dev gawk
$ tar xvzf texinfo-4.13a.tar.gz 
$ cd texinfo-4.13a
$ make
$ make install

gccに必要な他のライブラリを用意しておきます。

これらをとりあえず作業ディレクトリにダウンロードしておきます。

binutilsを準備

$ export CROSSTOOL=$HOME/cross-toolchains
$ export TARGET=arm-linux-gnueabi
$ export SYSROOT=$CROSSTOOL/$TARGET/sysroot

$ cd cross
$ tar xjf binutils-2.23.2.tar.bz2
$ mkdir -p binutils-2.23.2/build
$ cd binutils-2.23.2/build
$ ../configure --target=$TARGET --prefix=$CROSSTOOL --with-sysroot=$SYSROOT
$ make -j3 && make install

gmpの準備

$ cd ../..
$ tar xjf gmp-5.1.1.tar.bz2
$ mkdir -p gmp-5.1.1/build
$ cd gmp-5.1.1/build
$ ../configure --prefix=$CROSSTOOL
$ make -j3 &&  make install

mpfrの準備

$ cd ../..
$ tar xjf mpfr-3.1.2.tar.bz2
$ mkdir -p mpfr-3.1.2/build
$ cd mpfr-3.1.2/build
$ ../configure --prefix=$CROSSTOOL --with-gmp=$CROSSTOOL
$ make -j3 && make install

mpcの準備

$ cd ../..
$ tar xzf mpc-0.8.2.tar.gz
$ mkdir -p mpc-0.8.2/build
$ cd mpc-0.8.2/build
$ ../configure --prefix=$CROSSTOOL --with-gmp=$CROSSTOOL --with-mpfr=$CROSSTOOL
$ make -j3 
$ sudo make install

1st gccのmake

$ cd ../..
$ tar xjf gcc-4.8.2.tar.bz2
$ mkdir gcc-4.8.2/build1
$ cd gcc-4.8.2/build1
$ export CFLAGS_FP="--with-float=hard --with-fpu=vfp --with-arch=armv7-a"
$ ../configure --target=$TARGET --prefix=$CROSSTOOL \
  --without-headers \
  --without-ppl \
  --with-newlib \
  --disable-decimal-float \
  --disable-shared \
  --disable-threads --disable-libssp \
  --disable-libgomp --disable-libmudflap \
  --disable-libquadmath --disable-libatomic \
  --disable-sanitizer --disable-nls \
  --disable-libstdc++-v3 \
  --with-gmp=$CROSSTOOL \
  --with-mpfr=$CROSSTOOL \
  --with-mpc=$CROSSTOOL \
  --enable-languages=c \
  --with-mode=thumb \
  $CFLAGS_FP

$ make -j3
$ make install

2nd gccのための準備

1st gccが生成されている場所へパスを通しておきます。

$ export PATH=$PATH:$CROSSTOOL/bin

カーネルヘッダを準備します。

$ cd ../..
$ tar xjf linux-3.2.35.tar.bz2
$ cd linux-3.2.35
$ make mrproper
$ make headers_install ARCH=arm CROSS_COMPILE=${TARGET}- INSTALL_HDR_PATH=$SYSROOT/usr

glibcのヘッダの準備です。

$ cd ..
$ tar xzf eglibc-2_13.tar.gz
$ cd eglibc-2_13
$ cp -r ports libc
$ mkdir build
$ cd build
$ BUILD_CC=gcc CC=${TARGET}-gcc CXX=${TARGET}-g++ \
  AR=${TARGET}-ar \
  RANLIB=${TARGET}-ranlib \
  ../libc/configure \
    --prefix=/usr \
    --with-headers=${SYSROOT}/usr/include \
    --host=$TARGET \
    --disable-profile \
    --without-gd \
    --without-cvs \
    --enable-add-ons \
    --with-mode=thumb \
    $CFLAGS_FP

$ make install-headers install_root=$SYSROOT install-bootstrap-headers=yes
$ make csu/subdir_lib
$ mkdir -p ${SYSROOT}/usr/lib
$ cp csu/crt1.o csu/crti.o csu/crtn.o ${SYSROOT}/usr/lib
$ ${TARGET}-gcc -nostdlib -nostartfiles -shared -x c /dev/null -o ${SYSROOT}/usr/lib/libc.so
$ ln -sv ${CROSSTOOL}/lib/gcc/${TARGET}/4.8.2/libgcc.a ${CROSSTOOL}/lib/gcc/${TARGET}/4.8.2/libgcc_eh.a

2nd gccのmake

$ cd ../..
$ mkdir gcc-4.8.2/build2
$ cd gcc-4.8.2/build2 
$ ../configure \
  --target=${TARGET} \
  --prefix=${CROSSTOOL} \
  --with-sysroot=${SYSROOT} \
  --disable-libssp --disable-libgomp --disable-libmudflap \
  --disable-shared \
  --with-gmp=${CROSSTOOL} \
  --with-mpfr=${CROSSTOOL} \
  --with-mpc=${CROSSTOOL} \
  --enable-languages=c \
  --with-system-zlib \
  --with-mode=thumb \
  ${CFLAGS_FP}
$ make -j3 all-gcc
$ make install-gcc

これで作成したgccでglibcを作成することになります.

glibcのmake

$ cd ../..
$ rm -rf eglibc-2_13\build
$ mkdir -p eglibc-2_13\build
$ cd eglibc-2_13\build
$ BUILD_CC=gcc \
  CC=${TARGET}-gcc \
  CXX=${TARGET}-g++ \
  AR=${TARGET}-ar \
  RANLIB=${TARGET}-ranlib \
  ../libc/configure \
      --prefix=/usr \
      --with-headers=${SYSROOT}/usr/include \
        --host=${TARGET} \
        --disable-profile \
        --without-gd \
        --without-cvs \
        --enable-add-ons \
        --with-mode=thumb \
	${CFLAGS_FP}
$ make -j3
$ make install install_root=$SYSROOT

3rd gccのmake

作成したglibcを参照するようなgccをmakeしていきます

$ cd ../..
$ mkdir -p gcc-4.8.2/build3
$ cd gcc-4.8.2/build3
$ ../configure \
  --target=${TARGET} \
  --prefix=${CROSSTOOL} \
  --with-sysroot=${SYSROOT} \
  --disable-libssp --disable-libgomp --disable-libmudflap \
  --disable-libquadmath \
  --with-gmp=${CROSSTOOL} \
  --with-mpfr=${CROSSTOOL} \
  --with-mpc=${CROSSTOOL} \
  --enable-languages=c,c++ \
  --with-system-zlib \
  --enable-nls \
  --enable-threads=posix \
  --enable-multilib \
  --enable-c99 \
  --with-mode=thumb \
  ${CFLAGS_FP}
$ make -j3
$ make install

これで完成です。