TensorRT 6.x.x.x — kõrge jõudlusega inferents süvaõppemudelite (objekti tuvastamine ja segmentatsioon) jaoks

TensorRT 6.x.x.x — kõrge jõudlusega inferents süvaõppemudelite (objekti tuvastamine ja segmentatsioon) jaoks
Valutab ainult esmakordselt!

Tere kõigile! Kallid sõbrad, selles artiklis tahan jagada oma kogemust TensorRT ja RetinaNet'i kasutamise kohta, mis põhineb hoidla github.com/aidonchuk/retinanet-examples (see on ametliku reposti fork nvidia, mis võimaldab teil võimalikult lühikese aja jooksul alustada optimeeritud mudelite rakendamist tootmisse). Lugedes uudiseid kogukonna kanalites ods.ai, kohtan küsimusi TensorRT kasutamise kohta, ja peamiselt korduvad küsimused, seetõttu otsustasin kirjutada nii täieliku juhendi TensorRT, RetinaNet, Unet ja dockeri abil kiire inferentsi kasutamiseks.

Ülesande kirjeldus

Soovitan ülesande seada niimoodi: peame andmestiku struktureerima, treenima RetinaNet/Unet võrku Pytorch1.3+ peal, konverteerima saadud kaalusid ONNX-ks, seejärel konvertima need TensorRT engine'iks ja kõik see käivitama dockeris, soovitavalt Ubuntu 18 peal ja väga soovitavalt ARM(Jetson)* arhitektuuril, vähendades sellega keskkonna käsitsi seadistamist. Lõpuks saame konteineri, mis on valmis mitte ainult RetinaNet/Unet eksportimiseks ja treenimiseks, vaid ka täielikuks klassifitseerimise ja segmentatsiooni arenduseks ja treenimiseks koos kogu vajaliku ümbrikuga.

Etapp 1. Keskkonna ettevalmistamine

Siinkohal on oluline märkida, et viimasel ajal olen täielikult loobunud igasuguste raamatukogude kasutamisest ja seadistamisest desktop masinas, nagu ka devbox'il. Ainus, mida on vaja luua ja installida, on python virtuaalne keskkond ja cuda 10.2 (võib piirduda ainult nvidia draiveriga) deb-paketist.

Oletame, et teil on värskelt installitud Ubuntu 18. Installime cuda 10.2 (deb), ei hakka ma installimisprotsessile rohkem keskenduma, ametlikust dokumentatsioonist piisab täiesti.

Nüüd installime docker'i, juhendi docker'i installimiseks leiab kiiresti, siin on näide www.digitalocean.com/community/tutorials/docker-ubuntu-18-04-1-et, on nüüd saadaval versioon 19+ — paigaldame selle. Ja ärge unustage lubada dockerit kasutada ilma sudo' ta, nii on mugavam. Kui kõik on korras, teeme järgmist:

distribution=$(. /etc/os-release;echo $ID$VERSION_ID)
curl -s -L https://nvidia.github.io/nvidia-docker/gpgkey | sudo apt-key add -
curl -s -L https://nvidia.github.io/nvidia-docker/$distribution/nvidia-docker.list | sudo tee /etc/apt/sources.list.d/nvidia-docker.list

sudo apt-get update && sudo apt-get install -y nvidia-container-toolkit
sudo systemctl restart docker

Ja pole isegi vaja ametlikku hoidlast vaatama minna github.com/NVIDIA/nvidia-docker.

Nüüd teeme git clone github.com/aidonchuk/retinanet-examples.

Tegelikult on jäänud vaid väike osa, et alustada dockeriga nvidia-pildi kasutamist, peame registreerima NGC Cloudis ja sisse logima. Suunduge siia ngc.nvidia.com, registreerume ja pärast NGC Cloudi sisenemist klõpsame ekraani vasakus ülanurgas nuppu SETUP või läheme sellele lingile ngc.nvidia.com/setup/api-key. Klõpsame „genereeri võti“. Soovitan selle salvestada, vastasel juhul tuleb järgmisel külastusel see uuesti genereerida ja seega peame selle uuel seadmel uuesti sooritama.

Teeme:

docker login nvcr.io
Kasutajanimi: $oauthtoken
Parool:  - genereeritud võti

Kasutajanimi kopeerime lihtsalt. Niisiis, arva ära, keskkond on nüüd seadistatud!

Samm 2. Docker konteineri koostamine

Teises meie töö etapis koostame docker'i ja uurime selle sisemust.
Liigume projekti retina-examples juurekausta ja täidame

docker build --build-arg USER=$USER --build-arg UID=$UID --build-arg GID=$GID --build-arg PW=alex -t retinanet:latest retinanet/

Koostame docker'i, edastades sellele hetke kasutaja — see on väga kasulik, kui soovite midagi kirjutada monteeritud VOLUME'isse praeguse kasutaja õigustega, vastasel juhul on see root ja valus.

Kuni docker'i koostamine kestab, uurime Dockerfile'i:

FROM nvcr.io/nvidia/pytorch:19.10-py3

ARG USER=alex
ARG UID=1000
ARG GID=1000
ARG PW=alex
RUN useradd -m ${USER} --uid=${UID} && echo "${USER}:${PW}" | chpasswd

RUN apt-get -y update && apt-get -y upgrade && apt-get -y install curl && apt-get -y install wget && apt-get -y install git && apt-get -y install automake && apt-get install -y sudo && adduser ${USER} sudo
RUN pip install git+https://github.com/bonlime/pytorch-tools.git@master

COPY . retinanet/
RUN pip install --no-cache-dir -e retinanet/
RUN pip install /workspace/retinanet/extras/tensorrt-6.0.1.5-cp36-none-linux_x86_64.whl
RUN pip install tensorboardx
RUN pip install albumentations
RUN pip install setproctitle
RUN pip install paramiko
RUN pip install flask
RUN pip install mem_top
RUN pip install arrow
RUN pip install pycuda
RUN pip install torchvision
RUN pip install pretrainedmodels
RUN pip install efficientnet-pytorch
RUN pip install git+https://github.com/qubvel/segmentation_models.pytorch
RUN pip install pytorch_toolbelt

RUN chown -R ${USER}:${USER} retinanet/

RUN cd /workspace/retinanet/extras/cppapi && mkdir build && cd build && cmake -DCMAKE_CUDA_FLAGS="--expt-extended-lambda -std=c++14" .. && make && cd /workspace

RUN apt-get install -y openssh-server && apt install -y tmux && apt-get -y install bison flex && apt-cache search pcre && apt-get -y install net-tools && apt-get -y install nmap
RUN apt-get -y install libpcre3 libpcre3-dev && apt-get -y install iputils-ping

RUN mkdir /var/run/sshd
RUN echo 'root:pass' | chpasswd
RUN sed -i 's/PermitRootLogin prohibit-password/PermitRootLogin yes/' /etc/ssh/sshd_config
RUN sed 's@sessions*requireds*pam_loginuid.so@session optional pam_loginuid.so@g' -i /etc/pam.d/sshd

ENV NOTVISIBLE "in users profile"
RUN echo "export VISIBLE=now" >> /etc/profile
CMD ["/usr/sbin/sshd", "-D"]

Tekstist on näha, et kogume kõik meie lemmiklibid, kompileerime retinaneti, lisame mõned põhivahendid Ubuntu mugavamaks kasutamiseks ja seadistame openssh serveri. Esimeses reas toimub nvidia pildi pärimine, mille jaoks me logime sisse NGC Cloudi ja mis sisaldab Pytorch1.3, TensorRT6.x.x.x ja hulga teisi librarite, mis võimaldavad meie detektori cpp allikaid kompileerida.

Samm 3. Docker konteineri käivitamine ja tõrkeotsing

Liigume edasi konteineri ja arenduskeskkonna peamise kasutusjuhtumi juurde, alustuseks käivitame nvidia dockeri. Käitumine:

docker run --gpus all --net=host -v /home/:/workspace/mounted_vol -d -P --rm --ipc=host -it retinanet:latest

Nüüd on konteiner ssh kaudu saadaval @localhost. Pärast edukat käivitamist avame projekti PyCharmis. Jätkame avades

Settings->Project Interpreter->Add->Ssh Interpreter

Samm 1
TensorRT 6.x.x.x — kõrge jõudlusega inferents süvaõppemudelite (objekti tuvastamine ja segmentatsioon) jaoks

Samm 2
TensorRT 6.x.x.x — kõrge jõudlusega inferents süvaõppemudelite (objekti tuvastamine ja segmentatsioon) jaoks

Samm 3
TensorRT 6.x.x.x — kõrge jõudlusega inferents süvaõppemudelite (objekti tuvastamine ja segmentatsioon) jaoks

Valime kõik nagu ekraanipiltidel,

Interpreter -> /opt/conda/bin/python

— see on link Python3.6-le ja

Sync folder -> /workspace/retinanet

Klõpsame lõpetamisel, ootame indekseerimist, ja kõik, keskkond on kasutamiseks valmis!

OLULINE!!! Vahetult pärast indekseerimist tõmmake dockerist kokkupandud failid Retinanetile. Projekti juure kontekstimenüüs valime punkti

Deployment->Download

Ilmub üks fail ja kaks kausta build, retinanet.egg-info ja _С.so

TensorRT 6.x.x.x — kõrge jõudlusega inferents süvaõppemudelite (objekti tuvastamine ja segmentatsioon) jaoks

Kui teie projekt näeb välja selline, siis keskkond näeb kõiki vajalikke faile ja oleme valmis RetinaNet-i koolitamiseks.

Etapp 4. Andmete märgistus ja detektori koolitus

Kuna ma täiendavate andmete märgistamiseks kasutan peamiselt supervise.ly — meeldiv ja mugav tööriist, viimasel ajal on palju vigu parandatud ja see töötab oluliselt paremini.

Oletame, et olete andmestiku märgistanud ja selle alla laadinud, kuid ei saa seda otse meie RetinaNet-i sisestada, kuna see on oma formaadis ja selleks peame selle COCO-ks konvertima. Konverteerimise tööriist asub:

markup_utils/supervisly_to_coco.py

Pange tähele, et Category skriptis on näide ja peate sisestama oma (kategooriat background lisama ei pea)

categories = [{'id': 1, 'name': '1'}, 
                  {'id': 2, 'name': '2'}, 
                  {'id': 3, 'name': '3'},
                  {'id': 4, 'name': '4'}] 

Originaalrepo autorid otsustasid, et te ei koolita detekteerimiseks midagi muud peale COCO/VOC, seega tuli algfaili natuke redigeerida

retinanet/dataset.py

Lisades siia armastatud augmentatsioonid albumentations.readthedocs.io/en/latest ja eemaldada rangelt sisseehitatud kategooriad COCO-st. Samuti on võimalik kärpida suuri tuvastuspiirkondi, kui otsite suurtes piltides väikseid objekte, teil on väike andmestik =), ja mitte midagi ei tööta, aga sellest järgmine kord.

Üldiselt on treeningtsükkel ka nõrk, algselt ei salvestanud ta kontrollpunkte, kasutas mingit kohutavat ajastajat jne. Aga nüüd peate lihtsalt valima selgroo ja sooritama

/opt/conda/bin/python retinanet/main.py

parameetritega:

treeni retinanet_rn34fpn.pth
--selg ResNet34FPN
--klassid 12
--val-iters 10
--pildid /workspace/mounted_vol/dataset/train/images
--annotatsioonid /workspace/mounted_vol/dataset/train_12_class.json
--val-pildid /workspace/mounted_vol/dataset/test/images_small
--val-annotatsioonid /workspace/mounted_vol/dataset/val_10_class_cropped.json
--jitter 256 512
--max-suurus 512
--partii 32

Konsolis näete:

Mudeli algatamine...
     mudel: RetinaNet
  selgroog: ResNet18FPN
   klassid: 2, ankurded: 9
Valitud optimeerimise tase O0: Puhtad FP32 treeningud.

Selle optimeerimise taseme vaike seadistused on:
lubatud               : True
opt_tase              : O0
muuda_mudeli_tyyp        : torch.float32
patch_torch_functions  : False
hoia_batchnorm_fp32    : None
master_weights         : False
loss_scale             : 1.0
Kasutaja ülekirjutuste töötlemine (täiendavad kwargs, mis ei ole None)...
Üksuste töötlemise järel on optimeerimise valikud:
 lubatud               : True
 opt_tase             : O0
 muuda_mudeli_tyyp     : torch.float32
 patch_torch_functions : False
 hoia_batchnorm_fp32   : None
 master_weights        : False
 loss_scale            : 128.0
Andmekogumi ettevalmistamine...
    laadija: pytorch
    suurus: [1024, 1280], max: 1280
    seade: 4 gpu
    partii: 4, täpsus: segatud
Mudeli treenimine 20000 iteratsiooni jooksul...
[    1/20000] fookuskaotus: 0.95619, kastikaotus: 0.51584, 4-partii 4.042s (edasi: 0.698s, tagasi: 0.459s), 1.0 pilt/s, lr: 0.0001
[   12/20000] fookuskaotus: 0.76191, kastikaotus: 0.31794, 0.187s/4-partii (edasi: 0.055s, tagasi: 0.133s), 21.4 pilti/s, lr: 0.0001
[   24/20000] fookuskaotus: 0.65036, kastikaotus: 0.30269, 0.173s/4-partii (edasi: 0.045s, tagasi: 0.128s), 23.1 pilti/s, lr: 0.0001
[   36/20000] fookuskaotus: 0.46425, kastikaotus: 0.23141, 0.178s/4-partii (edasi: 0.047s, tagasi: 0.131s), 22.4 pilti/s, lr: 0.0001
[   48/20000] fookuskaotus: 0.45115, kastikaotus: 0.23505, 0.180s/4-partii (edasi: 0.047s, tagasi: 0.133s), 22.2 pilti/s, lr: 0.0001
[   59/20000] fookuskaotus: 0.38958, kastikaotus: 0.25373, 0.184s/4-partii (edasi: 0.049s, tagasi: 0.134s), 21.8 pilti/s, lr: 0.0001
[   71/20000] fookuskaotus: 0.37733, kastikaotus: 0.23988, 0.174s/4-partii (edasi: 0.049s, tagasi: 0.125s), 22.9 pilti/s, lr: 0.0001
[   83/20000] fookuskaotus: 0.39514, kastikaotus: 0.23878, 0.181s/4-partii (edasi: 0.048s, tagasi: 0.133s), 22.1 pilti/s, lr: 0.0001
[   94/20000] fookuskaotus: 0.39947, kastikaotus: 0.23817, 0.185s/4-partii (edasi: 0.050s, tagasi: 0.134s), 21.6 pilti/s, lr: 0.0001
[  105/20000] fookuskaotus: 0.37343, kastikaotus: 0.20238, 0.182s/4-partii (edasi: 0.048s, tagasi: 0.134s), 22.0 pilti/s, lr: 0.0001
[  116/20000] fookuskaotus: 0.19689, kastikaotus: 0.17371, 0.183s/4-partii (edasi: 0.050s, tagasi: 0.132s), 21.8 pilti/s, lr: 0.0001
[  128/20000] fookuskaotus: 0.20368, kastikaotus: 0.16538, 0.178s/4-partii (edasi: 0.046s, tagasi: 0.131s), 22.5 pilti/s, lr: 0.0001
[  140/20000] fookuskaotus: 0.22763, kastikaotus: 0.15772, 0.176s/4-partii (edasi: 0.050s, tagasi: 0.126s), 22.7 pilti/s, lr: 0.0001
[  148/20000] fookuskaotus: 0.21997, kastikaotus: 0.18400, 0.585s/4-partii (edasi: 0.047s, tagasi: 0.144s), 6.8 pilti/s, lr: 0.0001
 Keskmine täpsus (AP) @[ IoU=0.50:0.95 | ala=   kõik | maxDets=100 ] = 0.52674
 Keskmine täpsus (AP) @[ IoU=0.50      | ala=   kõik | maxDets=100 ] = 0.91450
 Keskmine täpsus (AP) @[ IoU=0.75      | ala=   kõik | maxDets=100 ] = 0.35172
 Keskmine täpsus (AP) @[ IoU=0.50:0.95 | ala= väike | maxDets=100 ] = 0.61881
 Keskmine täpsus (AP) @[ IoU=0.50:0.95 | ala=keskmine | maxDets=100 ] = -1.00000
 Keskmine täpsus (AP) @[ IoU=0.50:0.95 | ala= suur | maxDets=100 ] = -1.00000
 Keskmine tagasikutsumine (AR) @[ IoU=0.50:0.95 | ala=   kõik | maxDets=  1 ] = 0.58824
 Keskmine tagasikutsumine (AR) @[ IoU=0.50:0.95 | ala=   kõik | maxDets= 10 ] = 0.61765
 Keskmine tagasikutsumine (AR) @[ IoU=0.50:0.95 | ala=   kõik | maxDets=100 ] = 0.61765
 Keskmine tagasikutsumine (AR) @[ IoU=0.50:0.95 | ala= väike | maxDets=100 ] = 0.61765
 Keskmine tagasikutsumine (AR) @[ IoU=0.50:0.95 | ala=keskmine | maxDets=100 ] = -1.00000
 Keskmine tagasikutsumine (AR) @[ IoU=0.50:0.95 | ala= suur | maxDets=100 ] = -1.00000
Mudeli salvestamine: 148

Kogu parameetrite komplekti uurimiseks vaadake

retinanet/main.py

Üldiselt on need standartne detekteerimiseks ja neil on kirjeldus. Käivitage koolitus ja oodake tulemusi. Näide järeldusest on saadaval:

retinanet/infer_example.py

või käivitage käsk:

/opt/conda/bin/python retinanet/main.py infer retinanet_rn34fpn.pth 
--images /workspace/mounted_vol/dataset/test/images 
--annotations /workspace/mounted_vol/dataset/val.json 
--output result.json 
--resize 256 
--max-size 512 
--batch 32

Repozitooriumisse on juba integreeritud Focal Loss ja mitu backbone'i, samuti on lihtne lisada oma

retinanet/backbones/*.py

Tabelis toovad autorid välja mõned omadused:

TensorRT 6.x.x.x — kõrge jõudlusega inferents süvaõppemudelite (objekti tuvastamine ja segmentatsioon) jaoks

Seal on ka backbone ResNeXt50_32x4dFPN ja ResNeXt101_32x8dFPN, mis on võetud torchvisionist.
Loodan, et detekteerimise osas on natuke selgem, aga kindlasti tasub lugeda ametlikku dokumentatsiooni, et mõista eksportimise ja logimise režiime.

Etapp 5. Unet mudelite eksport ja järeldus Resnet'i kodeerijaga

Nagu te tõenäoliselt märkate, on Dockerfile'i sisse laaditud segmentatsiooni raamatukogud, sealhulgas suurepärane teek github.com/qubvel/segmentation_models.pytorch. Unet pakendis leiate näiteid järeldusest ja PyTorch'i kontrollpunktide eksportimisest TensorRT-sse.

Põhiprobleem Unet-like mudelite eksportimisel ONNX-ist TensorRT-sse on vajalik ühesuuruse Upample määramine või ConvTranspose2D kasutamine:

import torch.onnx.symbolic_opset9 as onnx_symbolic
        def upsample_nearest2d(g, input, output_size):
            # Hetkel TRT 5.1/6.0 ONNX parser ei toeta kõiki ONNX ops
            # vajalikud dünaamilise suurendamise ONNX formulatsiooniks
            # Siin kodeerime skaalad kõvaks väärtuseks 2 ajutise lahendusena
            scales = g.op("Constant", value_t=torch.tensor([1., 1., 2., 2.]))
            return g.op("Upsample", input, scales, mode_s="nearest")

        onnx_symbolic.upsample_nearest2d = upsample_nearest2d

Selle teisenduse abil on võimalik see automaatselt ONNX-i eksportimisel teha, kuid TensorRT 7 versioonis on see probleem lahendatud ja meil jääb oodata vaid natuke.

Kokkuvõte

Kui ma hakkasin Dockerit kasutama, siis olid mul kahtlused selle jõudluse osas minu ülesannete täitmiseks. Ühes minu agregaatidest genereeritakse hetkel üsna suur võrgu liiklus, mida toodab mitu kaamerat.

TensorRT 6.x.x.x — kõrge jõudlusega inferents süvaõppemudelite (objekti tuvastamine ja segmentatsioon) jaoks

Erinevad testid internetis räägivad suhteliselt suurest overheadist võrgu suhtluses ning salvestamises VOLUMEss, lisaks sellele tundmatu ja hirmutav GIL, ning kuna kaadrisalvestamine, draiveri töö ja kaadrise saatmine võrku on aatomilised toimingud režiimis hard real-time, võrgu viivitus on minu jaoks väga kriitiline.

Aga kõik läks hästi =)

P.S. Lisage oma lemmik treeningtsükkel segmentimiseks ja tooge see tootmisse!

Tänu

Aitäh kogukonnale ods.ai, ilma selleta ei ole võimalik areneda! Suur tänu n01z3, kes ajendas mind tegelema DL-iga, tema hindamatute nõuannete ja äärmise professionaalsuse eest!

Kasutage tootmises optimeeritud mudeleid!

TensorRT 6.x.x.x — kõrge jõudlusega inferents süvaõppemudelite (objekti tuvastamine ja segmentatsioon) jaoks Aurorai, llc

Allikas: habr.com

Osta usaldusväärne veebihosting DDoS kaitsega, VPS VDS serverid 🔥 Osta usaldusväärne veebihosting DDoS kaitsega, VPS VDS serverid | ProHoster