Edited at

Ultra96 PYNQ Darknet Google-Colabo


Memo

フレームワークやDNNを使ったことがなく、いろんなことを試す中で解った事柄をメモしています。日を追うごとに、PYNQと関係なくなってきてますが。


PYNQ-DNN

OpenVINOは、Python記述から中間言語に変換し、HLSすることで実現しているらしい。OpenVINOについてはこちらで。

PYNQの場合は?

PYNQ

PYNQ sdbuild

Board files to build Ultra96 PYNQ image

Petalinux2018.2 BSP for Ultra96

BNN-PYNQ pip install package


BNN-PYNQ

$ sudo pip3 install git+https://github.com/Xilinx/BNN-PYNQ.git (on PYNQ v2.3)


QNN on PYNQ using a MO architecture


QNN-MO-PYNQ

$ sudo pip3 install git+https://github.com/Xilinx/QNN-MO-PYNQ.git


In Shimaharu's mind から勝手に引用。

恐らくだが、CNNやらPoolingやらの層はあらかじめHLSで生成したハードを使って、

層数とか特徴量のチャネル数はパラメータ(JSONに記述されている?)により

ネットワークが決まるようである。

確かにそんな感じがする。


tinier-yolo-layers.json

{

"network": "tinier-yolo",
"input_image": "../../tests/Test_image/tinier-yolo/input.bin",
"verification_image": "../../tests/Test_image/tinier-yolo/verification.bin",
"binparam": "binparam-tinier-yolo-nopool",
"use_binparams" : true,
"binparam_skip": 1,
"layer_skip": 0,
"layers": [{
"name": "conv1",
"func": "conv_layer",
"input_bits": 3,
"output_bits": 3,
"weight_bits": 1,
"threshold_bits": 16,
"kernel_shape": 3,
"kernel_stride": 1,
"input_channels": 16,
"input": [16, 208, 208],
"output_channels": 64,
"output": [64, 208, 208],
"padding": 1
},
{
"name": "pool1",
"func": "maxpool_layer",
"input_bits": 3,
"output_bits": 3,
"kernel_shape": 2,
"kernel_stride": 2,
"input_channels": 64,
"input": [64, 208, 208],
"output_channels": 64,
"output": [64, 104, 104],
"padding": 0
},

途中割愛

{
"name": "end",
"func": "none"
}
]
}


詳しくは、よくわからない・・・


Ultra96-PYNQを自分でビルドする

@okuhata さんの記事です。


ZCU102向けPYNQビルド備忘録

@jin0g さんの記事です。


PYNQ LinuxイメージのSDカードへの書き込み


SDカード

$ sudo mkfs -t vfat -F 32 /dev/sdb1

$ sudo mkfs -t ext4 /dev/sdb2

$ sudo mlabel -i /dev/sdb1 ::BOOT
$ sudo e2label /dev/sdb2 ROOTFS

$ sudo mount /dev/sdb1 /mnt
$ sudo cp BOOT.BIN image.ub /mnt
$ sudo sync
$ sudo umount /mnt

$ sudo dd if=rootfs.ext4 of=/dev/sdb2 bs=1M status=progress

$ sudo e2fsck -f /dev/sdb2
$ sudo resize2fs -p /dev/sdb2 {7G}


Darknet

FPGA Magazineを参考にして、Darknetを試してみる。


Pjreddie(本家?)Yolo v3


Pjreddie

$ git clone https://github.com/pjreddie/darknet


$ cd darknet

$ vi Makefile
OPENCV=1
CFLAGS = ... -pg

$ make



Pjreddie

$ wget https://pjreddie.com/media/files/yolov3.weights

$ ./darknet detect cfg/yolov3.cfg yolov3.weights data/people_dog.jpg

Input JPEG

Predictions JPG


Pjreddie(本家?)Yolo v3 Tiny


Pjreddie

$ wget https://pjreddie.com/media/files/yolov3-tiny.weights

$ ./darknet detect cfg/yolov3-tiny.cfg yolov3-tiny.weights data/people_dog.jpg

Predictions JPG



靴先を野球ボールとだと認識してる。


Giuliogamba(forked from Pjreddie)Yolo v2


Giuliogamba

$ git clone https://github.com/giuliogamba/darknet.git

$ wget https://pjreddie.com/media/files/yolov2-voc.weights
$ wget https://pjreddie.com/media/files/yolo-voc.weights


AlexeyAB(forked from Pjreddie)Yolo v3

このForkは、動画ファイル(mp4)やWebカメラでも動作した。


AlexeyAB

$ git clone https://github.com/AlexeyAB/darknet.git


GPU、cuDNNを有効にして


AlexeyAB

$ vi Makefile

OPENCV=1
GPU=1
CUDNN=1

$ make
$ ./darknet detect cfg/yolov3.cfg yolov3.weights data/people_dog.jpg


Predictions JPG



後ろの人やベンチも認識している。

CPUだけ、GPUを有効、cuDNNも有効にした場合の処理時間の違いを。

NVidiaボードは古~いQuadro。


AlexeyAB

$ ./darknetCPU detect cfg/yolov3.cfg yolov3.weights data/People_Dog.jpg 

data/People_Dog.jpg: Predicted in 19813.975000 milli-seconds.

$ ./darknetGPU detect cfg/yolov3.cfg yolov3.weights data/People_Dog.jpg
data/People_Dog.jpg: Predicted in 505.077000 milli-seconds.

$ ./darknetCUDNN detect cfg/yolov3.cfg yolov3.weights data/People_Dog.jpg
data/People_Dog.jpg: Predicted in 299.481000 milli-seconds.


40倍以上、高速になった。

澁谷のゾンビ行進の画像で試してみると、皆Personです、当然といえば当然。:wink:


動画ファイルを使うなら

./darknet detector demo cfg/coco.data cfg/yolov3.cfg yolov3.weights -dont_show data/hoge.mp4 -i 0 -out_filename res.avi


3fpsぐらいだったので、それならWebカメラでカクカク映像が見れるかも。


Webカメラを使うなら

./darknet detector demo cfg/coco.data cfg/yolov3.cfg yolov3.weights


準備中


Jupyter Notebook Viewer

GitのJupyter Notebookを手っ取り早く見るためには便利

Jupyter Notebook Viewer


Linux上で画像ファイルの表示

apt updateしてなかったからか、Ubuntuに入っていなかったので。


ImageMagick

$ sudo apt install imagemagick

$ display predictions.jpg


Ubuntu16.04にUSB Webカメラを繋ぐ

Webカメラからの映像を表示するアプリCheeseを起動しても、Webカメラにアクセスできませんでした。デバイスファイル/dev/video0へのアクセスにはroot権限が要るらしく、setfaclコマンドでアクセス制御を設定することで、表示できるようになりました。


Webカメラ

sudo chmod 660 /dev/video0

sudo chgrp video /dev/video0
sudo setfacl -m u:自分のアカウント:rw /dev/video0

setfaclコマンドなるものを、初めて知った・・・


Ubuntu16.04にNVidiaドライバとCUDA9.0をインストール

こちら


Google Colaboratoryで試してみる

作成中


Time

./People_Dog.jpg: Predicted in 281.701000 milli-seconds.



FPS_on_Google-Colabo

cvWriteFrame 

1;1H
FPS:16.4
Objects:

person: 100%
person: 100%
person: 99% Stream closed.

person: 99%
person: 98%
person: 96%
person: 75%
person: 74%
person: 69%
person: 68%
person: 45%



Darknetの処理時間の可視化

Interfaceの記事をたよりに、Darknetの処理時間のプロファイルを取ってみた。


Profile_on_Ubuntu_using_GPU

$ vi Makefile

OPENCV=1
GPU=1
CUDNN=1
CFLAGS = ... -pg

$ make
$ ./darknet detect cfg/yolov3.cfg yolov3.weights data/people_dog.jpg
$ gprof darknet | ./gprof2dot.py | dot -Tpng -o profile.png


gprof2dot.pyは以下からゲットする。


gprof2dot

$ git clone https://github.com/jrfonseca/gprof2dot



Ubuntu上でGPUを使った場合のプロファイルは


Google Colabo上でGPUを使った場合のプロファイルは


Ubuntu上でCPUを使った場合のプロファイルは


Ultra96のPSだけで処理した場合のプロファイルは

処理時間は、

$ ./darknet detect cfg/yolov3.cfg yolov3.weights data/People_Dog.jpg 

data/People_Dog.jpg: Predicted in 120869.165000 milli-seconds.

dotが入ってなかったのでインストールする。Ubuntuであれば、以下のようなaptでインストールできますが

$ sudo apt install graphviz

Ultra96のPetalinux BSPで作ったLinuxは、Ubuntuではないのでaptできず、ソースをダウンロードしてコンパイル、インストールする。

$ wget https://graphviz.gitlab.io/pub/graphviz/stable/SOURCES/graphviz.tar.gz

$ tar zxvf graphviz.tar.gz
$ cd graphviz-2.40.1
$ ./configure
$ make
$ sudo make install

わざわざUltra96上でdot変換する必要はないけど、Memoとして。


Ultra96のXwindowをPC上に表示

処理結果の画像を表示して確認するために、

わざわざディスプレイを繋ぐのが場所もとるし面倒なので、

SSHでloginし、XwindowアプリをPC上に表示できるようにした。

PC上ではCygwinを使っているので、

CygwinによるXWindowsの利用等を参考にしてXサーバーをインストールし、


まずCygwin上でDISPLAY変数を設定する

  $ echo $DISPLAY

localhost:0.0
$ export DISPLAY=:0.0
$ echo $DISPLAY
:0.0


Ultra96にsshするときのオプション-Yが重要

  $ ssh -l root -Y 192.168.3.11



Ultra96上のDISPLAY変数は

  root@ultra96:~ # echo $DISPLAY

localhost:10.0


xtermを起動すると、PCに表示される

  root@ultra96:~ # xterm


取り敢えずここまで。