[PYTHON] Essayez le Deep Learning avec FPGA

introduction

Avec la sortie d'un projet appelé BNN-PYNQ par Xilinx, même les débutants de FPGA peuvent facilement exécuter le Deep Learning sur FPGA. J'ai acheté une carte immédiatement et l'ai essayée jusqu'à ce que la démo soit exécutée.

Explication préalable

PYNQ Il semble que ce soit un projet open source Xilinx qui facilite l'utilisation de la logique FPGA implémentée dans le Zynq de Xilinx à partir de Python.

pynq-logo.png

Normalement, lorsqu'un programme est exécuté dans Zynq, il est divisé en PS (Processing System) qui est exécuté par CPU et PL (Programmable Logic) qui est exécuté par FPGA. En Deep Learning, est-ce une image d'implémentation d'une application qui utilise Deep Learning sur PS, et d'implémentation d'un traitement de convolution dont on peut s'attendre à ce qu'il accélère par parallélisation et traitement de calcul de chaque couche du réseau neuronal sur PL? PYNQ vous permet d'écrire PS en Python.

De plus, comme caractéristique majeure, il a l'idée de superposition. Overlay vous permet de changer dynamiquement la partie PL de Python en traitant le PL comme une bibliothèque de logiciels. Par exemple, lors de l'exécution de MNIST, chargez simplement la superposition MNIST en Python et le réseau MNIST sera étendu à PL.

Pour plus de détails sur PYNQ, veuillez consulter ce qui suit.

PYNQ-Z1 Board La carte qui soutient officiellement le projet PYNQ est la carte PYNQ-Z1. Il est équipé du Dual-Core ARM® Cortex®-A9. Il a également HDMI IN / OUT, il semble donc être utile pour le traitement d'image et vidéo.

pynq-z1-board.png PYNQ: PYTHON PRODUCTIVITY ON ZYNQ

Actuellement, il semble qu'il n'est pas possible d'acheter au Japon, je l'ai donc acheté sur le site Digilent. Le montant est d'environ 30000 yens, frais d'expédition inclus, et il est arrivé environ une semaine après la commande. La livraison était FedEx, mais j'ai reçu une facture fiscale (environ 1 500 yens) séparément du produit. J'ai pu payer la facture au dépanneur.

BNN-PYNQ BNN-PYNQ est un projet qui vous permet d'exécuter un réseau neuronal binarisé (BNN) sur PYNQ. Le Deep Learning consiste en l'inférence et l'apprentissage, mais seule l'inférence est publiée dans BNN-PYNQ.

algorithme

En FPGA, il semble qu'il soit courant d'utiliser un algorithme binarisé en raison de la limitation des ressources informatiques. De plus, en le binarisant, cela devient un calcul XNOR et il semble que l'on puisse s'attendre à une accélération. Dans BNN-PYNQ, CNV et LFC présentés dans l'article [FINN: A Framework for Fast, Scalable Binarized Neural Network Inference] sont publiés en tant que Overlay of PYNQ. Ça a été.

Pour plus d'informations sur BNN, je pense qu'il est préférable de lire l'article. En outre, en ce qui concerne l'algorithme de binarisation, ce qui suit sera utile.

la mise en oeuvre

BNN-PYNQ implémente le Deep Learning à l'aide d'une bibliothèque appelée xilinx-tiny-cnn. xilinx-tiny-cnn est basé sur tiny-dnn, et les points suivants ont été modifiés. BNN-PYNQ utilise tiny-dnn.

Le développeur de tiny-dnn semble être japonais. C'est incroyable. .. .. Introduction de Deep Learning, tiny-dnn uniquement avec en-tête C ++

Lancer la démo

environnement

Afin d'exécuter BNN-PYNQ, nous avons préparé ce qui suit.

Réglage initial de PYNQ

Suivez la documentation de mise en route (https://pynq.readthedocs.io/en/latest/1_getting_started.html).

Créer une image

Tout d'abord, téléchargez l'image. Téléchargez depuis Télécharger et l'image PYNQ-Z1 dans la procédure décrite dans le document ci-dessus. Vous pouvez également le télécharger depuis le site de Digilent. (Je ne connais pas la différence) Au moment de la rédaction de l'article, pynq_z1_image_2017_02_10.zip a été téléchargé.

Décompressez le fichier zip téléchargé PYNQ-Z1 Image.

$ tar zxvf pynq_z1_image_2017_02_10.zip
x pynq_z1_image_2017_02_10.img

Installez l'image décompressée sur la carte SD. Tout d'abord, vérifiez la carte SD sur laquelle vous souhaitez installer l'image.

$ df -ah
Filesystem      Size   Used  Avail Capacity   iused    ifree %iused  Mounted on
/dev/disk1s1    30Gi  2.5Mi   30Gi     1%         0        0  100%   /Volumes/UNTITLED

Formatez la carte SD avec FAT32.

$ diskutil eraseDisk FAT32 PYNQ /dev/disk1
Started erase on disk1
Unmounting disk
Creating the partition map
Waiting for the disks to reappear
Formatting disk1s2 as MS-DOS (FAT32) with name PYNQ
512 bytes per physical sector
/dev/rdisk1s2: 62501024 sectors in 1953157 FAT32 clusters (16384 bytes/cluster)
bps=512 spc=32 res=32 nft=2 mid=0xf8 spt=32 hds=255 hid=411648 drv=0x80 bsec=62531584 bspf=15260 rdcl=2 infs=1 bkbs=6
Mounting disk
Finished erase on disk1

Démontez la carte SD.

$ diskutil unmountDisk /dev/disk1
Unmount of all volumes on disk1 was successful

Écrivez l'image précédente sur la carte SD.

$ sudo dd bs=1024m if=pynq_z1_image_2017_02_10.img of=/dev/rdisk1
Password:

La carte SD est maintenant prête!

Commencez

Réglez la carte PYNQ selon l'image ci-dessous.

pynqz1_setup.jpg

⓪ Assurez-vous que l'interrupteur d'alimentation est éteint ① Réglez JP4 (à côté de USB HOST) sur SD ② Insérez la carte SD que vous avez créée précédemment ③ Connectez le câble USB (câble d'alimentation) ④ Connectez le câble LAN

Dans mon cas, j'ai changé JP5 (à côté de l'interrupteur d'alimentation) en USB en plus de ce qui précède car l'alimentation est tirée de l'USB. Après avoir tout réglé ...

⑤ Allumez le PYNQ

Jupyter Notebook / SSH Dans PYNQ, Jupyter Notebook est en cours d'exécution. Par conséquent, vous pouvez programmer Python sur Jupyter Notebook en accédant au lien ci-dessous.

http://[PYNQのIPアドレス]:9090

Lorsque vous y accédez pour la première fois, vous verrez la page de connexion ci-dessous. Le mot de passe est "xilinx".

jupyter-login.png

L'utilisation est la même que Jupyter normale.

Vous pouvez également accéder à PYNQ via SSH. Le nom du compte est "xilinx" et le mot de passe est "xilinx".

Exécutez la commande suivante pour mettre à jour PYNQ.

xilinx@pynq:~$ sudo /home/xilinx/scripts/update_pynq.sh
[sudo] password for xilinx: 
Info: This operation will overwrite all the example notebooks
Press any key to continue...

Github Repo Detected. Pulling latest changes from upstream..
fatal: A branch named 'master' already exists.
Already on 'master'
Your branch is up-to-date with 'origin/master'.
remote: Counting objects: 13, done.
remote: Compressing objects: 100% (13/13), done.
remote: Total 13 (delta 2), reused 0 (delta 0), pack-reused 0
Unpacking objects: 100% (13/13), done.
From https://github.com/Xilinx/PYNQ
   3ed304a..0309566  master     -> origin/master
Updating 3ed304a..0309566
Fast-forward
 python/pynq/gpio.py            | 210 ++++++++++++++++++++++++++++++++++++++----------------
 python/pynq/iop/iop.py         |  22 +++---
 python/pynq/tests/test_gpio.py |   1 +
 3 files changed, 161 insertions(+), 72 deletions(-)

checking out v1.4

Verifying current SDCard image supports this pynq release.
Completed

Build libsds_lib

cd /home/xilinx/pynq_git/scripts/xlnkutils && make && make install
make[1]: Entering directory '/home/xilinx/pynq_git/scripts/xlnkutils'
gcc wrapper.c -fPIC -shared -rdynamic -o libsds_lib.so -Wl,--whole-archive libsds_lib.a -l pthread  -Wl,--no-whole-archive
make[1]: Leaving directory '/home/xilinx/pynq_git/scripts/xlnkutils'
make[1]: Entering directory '/home/xilinx/pynq_git/scripts/xlnkutils'
cp -avf libsds_lib.so /usr/lib/
‘libsds_lib.so’ -> ‘/usr/lib/libsds_lib.so’
cp -arvf libxlnk_cma.h /usr/include/
‘libxlnk_cma.h’ -> ‘/usr/include/libxlnk_cma.h’
make[1]: Leaving directory '/home/xilinx/pynq_git/scripts/xlnkutils'

Pip install latest pynq python package

python3.6 /home/xilinx/scripts/stop_pl_server.py
rm -rf /opt/python3.6/lib/python3.6/site-packages/pynq/*
cp -rf /home/xilinx/pynq_git/Pynq-Z1/sdk/bin/*.bin /home/xilinx/pynq_git/python/pynq/iop/
cp -rf /home/xilinx/pynq_git/Pynq-Z1/bitstream /home/xilinx/pynq_git/python/pynq/
cd /home/xilinx/pynq_git/python ; sudo -H python3.6 -m pip install --upgrade .
Processing /home/xilinx/pynq_git/python
Installing collected packages: pynq
  Found existing installation: pynq 1.4
    Uninstalling pynq-1.4:
      Successfully uninstalled pynq-1.4
  Running setup.py install for pynq ... done
Successfully installed pynq-1.4
python3.6 /home/xilinx/scripts/start_pl_server.py &

Update scripts and notebooks

cp -arf /home/xilinx/pynq_git/Pynq-Z1/notebooks/* /home/xilinx/jupyter_notebooks
cp -f /home/xilinx/pynq_git/scripts/linux/rc.local /etc/
mkdir -p /home/xilinx/jupyter_notebooks/getting_started
mkdir -p /home/xilinx/jupyter_notebooks/getting_started/images
cp /home/xilinx/pynq_git/docs/source/3_jupyter_notebook.ipynb \
/home/xilinx/jupyter_notebooks/getting_started/1_jupyter_notebook.ipynb
cp /home/xilinx/pynq_git/docs/source/4_programming_python.ipynb \
/home/xilinx/jupyter_notebooks/getting_started/2_programming_python.ipynb
cp /home/xilinx/pynq_git/docs/source/5_programming_onboard.ipynb \
/home/xilinx/jupyter_notebooks/getting_started/3_programming_onboard.ipynb
cp /home/xilinx/pynq_git/docs/source/8_base_overlay_iop.ipynb \
/home/xilinx/jupyter_notebooks/getting_started/4_base_overlay_iop.ipynb
cp /home/xilinx/pynq_git/docs/source/9_base_overlay_video.ipynb \
/home/xilinx/jupyter_notebooks/getting_started/5_base_overlay_video.ipynb
cp /home/xilinx/pynq_git/docs/source/10_base_overlay_audio.ipynb \
/home/xilinx/jupyter_notebooks/getting_started/6_base_overlay_audio.ipynb
chown -R xilinx:xilinx /opt/python3.6/lib/python3.6/site-packages/pynq/*
chmod -R a+rw /home/xilinx/jupyter_notebooks /opt/python3.6/lib/python3.6/site-packages/pynq
chmod -R a+x /home/xilinx/scripts/*
chmod a+x /root/*.sh
chmod a+x /etc/rc.local
chown -R xilinx:xilinx /home/xilinx/jupyter_notebooks /home/xilinx/scripts /opt/python3.6/lib/python3.6/site-packages/pynq
Notebooks     folder is at: /home/xilinx/jupyter_notebooks
Scripts       folder is at: /home/xilinx/scripts

Completed PYNQ update.

xilinx@pynq:~$ 

Il est devenu PYNQ 1.4.

Installation du BNN-PYNQ

Installez BNN-PYNQ. Il est décrit dans [Démarrage rapide] de BNN-PYNQ (https://github.com/Xilinx/BNN-PYNQ#quick-start), mais vous pouvez l'installer avec la commande suivante.

xilinx@pynq:~$ sudo pip3.6 install git+https://github.com/Xilinx/BNN-PYNQ.git
[sudo] password for xilinx: 
The directory '/home/xilinx/.cache/pip/http' or its parent directory is not owned by the current user and the cache has been disabled. Please check the permissions and owner of that directory. If executing pip with sudo, you may want sudo's -H flag.
The directory '/home/xilinx/.cache/pip' or its parent directory is not owned by the current user and caching wheels has been disabled. check the permissions and owner of that directory. If executing pip with sudo, you may want sudo's -H flag.
Collecting git+https://github.com/Xilinx/BNN-PYNQ.git
  Cloning https://github.com/Xilinx/BNN-PYNQ.git to /tmp/pip-7pt0wn6t-build
Installing collected packages: bnn-pynq
  Running setup.py install for bnn-pynq ... done
Successfully installed bnn-pynq-0.1

Exécution de BNN-PYNQ

Lorsque l'installation est terminée, vous devriez avoir un dossier bnn sur Jupyter. Certains échantillons sont préparés dans ce dossier. jupyter-bnn-sample.png

À partir de là, je voudrais lancer Cifar10. Cifar10 est un exemple qui classe les images en 10 types. Pour le moment, essayez [Exécuter tout].

Tout était fait. Comme vous pouvez le voir en regardant le code source, Python charge simplement l'image déduite et appelle classify_image.

Le résultat de la comparaison de la vitesse par CPU et FPGA est affiché à l'endroit suivant.

pynq-cifar10-hw-sw.png

Le processeur de PYNQ peut être lent, mais la différence est plus de 360 fois.

 4.Lancement de BNN dans le matériel → Utiliser FPGA
    2223.00 microseconds
 5.Lancement de BNN dans le logiciel → Utiliser uniquement le processeur
    817744.00 microseconds

Code source

Jetons un coup d'œil à bnn.py de BNN-PYNQ installé par PIP.

Le premier est l'initialisation de la classe CnvClassifier.

class CnvClassifier:
    def __init__(self, params, runtime=RUNTIME_HW):
        self.bnn = PynqBNN(runtime, network=NETWORK_CNV)
        self.bnn.load_parameters(params)

Ici, nous chargeons les paramètres d'instanciation PynqBNN et d'apprentissage du réseau.

Vient ensuite l'initialisation de la classe PynqBNN.

class PynqBNN:
    
    def __init__(self, runtime=RUNTIME_HW, network=NETWORK_CNV, load_overlay=True):
        self.bitstream_name = None
        if runtime == RUNTIME_HW:
            self.bitstream_name="{0}-pynq.bit".format(network)
            self.bitstream_path=os.path.join(BNN_BIT_DIR, self.bitstream_name)
            if PL.bitfile_name != self.bitstream_path:
                if load_overlay:
                    Overlay(self.bitstream_path).download()
                else:
                    raise RuntimeError("Incorrect Overlay loaded")
        dllname = "{0}-{1}.so".format(runtime, network)
        if dllname not in _libraries:
            _libraries[dllname] = _ffi.dlopen(
		os.path.join(BNN_LIB_DIR, dllname))
        self.interface = _libraries[dllname]
        self.num_classes = 0

Ici, Overlay est chargé en fonction du réseau spécifié. Au fait, dans ʻOverlay (self.bitstream_path) .download () , il semble que le fichier bitstream soit lu et écrit dans le fichier de périphérique / dev / xdevcfg`. Lecture de la superposition PYNQ-Z1 et contrôle du FPGA PL à partir de Python

Il charge également la bibliothèque partagée pour accéder au FPGA. Dans BNN-PYNQ, en accédant à la bibliothèque partagée avec cffi.FFI.dlopen, vous utilisez FPGA via la bibliothèque partagée.

Enfin, l'inférence de la «classe PynqBNN».

    def inference(self, path):
        usecperimage = _ffi.new("float *") 
        result_ptr = self.interface.inference(path.encode(), _ffi.NULL, len(self.classes), usecperimage)
        print("Inference took %.2f microseconds" % (usecperimage[0]))
        print("Classification rate: %.2f images per second" % (1000000.0/usecperimage[0]))
        return result_ptr

J'appelle «self.interface.inference» pour en déduire. L'heure d'inférence qui était affichée précédemment semble avoir été `imprimée ici.

en conclusion

Actuellement, seule inférence, mais j'ai pu effectuer du Deep Learning sur FPGA. C'était beaucoup plus rapide que le processeur. De plus, comme il peut être utilisé avec Python (Jupyter Notebook), j'ai pensé qu'il serait facile de l'intégrer dans une application ou de le tester.

Cependant, comme je n'ai pas touché PL cette fois, je n'avais pas vraiment l'impression d'utiliser FPGA. Le Code source après la bibliothèque partagée est également ouvert au public, et la [Méthode de reconstruction](https: // github. com / Xilinx / BNN-PYNQ # hardware-design-rebuilt) est également répertorié, je voudrais donc jeter un coup d'œil.

PYNQ a été présenté et c'était un article très intéressant. Pourquoi les ingénieurs en logiciel devraient apprendre le FPGA en 2017 lorsque les emplois d'apprentissage automatique / Deep Learning augmentent

Recommended Posts

Essayez le Deep Learning avec FPGA
Essayez l'apprentissage en profondeur avec TensorFlow
Essayez le Deep Learning avec les concombres FPGA-Select
Essayez les prévisions de prix Bitcoin avec Deep Learning
Essayez avec Chainer Deep Q Learning - Lancement
Essayez l'apprentissage profond de la génomique avec Kipoi
Apprentissage profond du noyau avec Pyro
Essayez le machine learning à la légère avec Kaggle
Générez des Pokémon avec Deep Learning
L'apprentissage en profondeur
Identification de la race de chat avec Deep Learning
Renforcer l'apprentissage 13 Essayez Mountain_car avec ChainerRL.
Faites de l'art ASCII avec l'apprentissage en profondeur
SVM essayant l'apprentissage automatique avec scikit-learn
Vérifiez la forme de squat avec l'apprentissage en profondeur
Catégoriser les articles de presse grâce au Deep Learning
Prévisions des ventes de collations avec apprentissage en profondeur
Essayez l'apprentissage de la représentation commune avec le chainer
Faites sourire les gens avec le Deep Learning
[Evangelion] Essayez de générer automatiquement des lignes de type Asuka avec Deep Learning
Classez les visages d'anime avec l'apprentissage en profondeur avec Chainer
Apprentissage profond / Apprentissage profond à partir de zéro 2-Essayez de déplacer GRU
Mémorandum d'apprentissage profond
Analyse émotionnelle des tweets avec apprentissage en profondeur
Apprentissage en profondeur Python
Apprentissage profond × Python
Introduction au Deep Learning (2) - Essayez votre propre régression non linéaire avec Chainer-
Enquête sur PYNQ - Faisons du Deep Learning avec FPGA en utilisant Python -
Renforcer l'apprentissage 11 Essayez OpenAI acrobot avec ChainerRL.
99,78% de précision avec apprentissage en profondeur en reconnaissant les hiragana manuscrits
Essayez de gratter avec Python.
Premier apprentissage profond ~ Lutte ~
Apprendre Python avec ChemTHEATER 03
"Orienté objet" appris avec python
Apprendre Python avec ChemTHEATER 05-1
Python: pratique du Deep Learning
Fonctions d'apprentissage en profondeur / d'activation
Apprentissage profond à partir de zéro
Deep learning 1 Pratique du deep learning
Apprentissage profond / entropie croisée
Premier apprentissage profond ~ Préparation ~
Première solution d'apprentissage en profondeur ~
[AI] Apprentissage métrique profond
Apprendre Python avec ChemTHEATER 02
J'ai essayé le deep learning
Apprendre Python avec ChemTHEATER 01
Essayez SNN avec BindsNET
Python: réglage du Deep Learning
Technologie d'apprentissage en profondeur à grande échelle
Essayez la régression avec TensorFlow
Fonction d'apprentissage profond / softmax
Une histoire de prédiction du taux de change avec Deep Learning
Analyse d'images par apprentissage profond à partir de Kaggle et Keras
Essayez de prédire le taux de change (FX) avec un apprentissage automatique non approfondi
Prédire les tags en extrayant des fonctionnalités musicales avec Deep Learning
Classer les visages d'anime par suite / apprentissage profond avec Keras
Maintenant, essayons la reconnaissance faciale avec Chainer (phase d'apprentissage)
[Apprentissage automatique] Démarrez Spark avec iPython Notebook et essayez MLlib
L'apprentissage automatique appris avec Pokemon
Essayez de défier le sol par récursif