Machine Learning/Computer Vision

Jetson Nano에서 TensorRT 기반 yolov7 동영상 분석

코방코 2024. 1. 1. 22:59
728x90

 지난 번 글에서 TensorRT를 이용하여 yolov7 분석을 하기 위해 사전 환경을 구성하였습니다.

이번에는 실제로 Jetson Nano에서 TensorRT를 적용하여,

yolov7-tiny 모델로 동영상을 분석하는 과정에 대해 글을 쓰겠습니다.

약 17fps의 분석 속도가 획득됩니다.

 

아래 이전 글에서 이어지는 내용입니다.

 

Jetson Nano 에 yolov7 TensorRT 사전 환경 구성

Jetson Nano 4GB에서 yolov7-tiny 모델 기반으로 웹캠으로 들어온 실시간 영상 처리를 해보았습니다. 이 때 실시간 영상 처리 속도는 TensorRT를 사용하여 17fps 를 획득하였는데, 해당 과정에 대해서 설명

cobang.tistory.com

 

 

지난 글에서 필요한 환경을 구성하였습니다.

이 환경에서 yolov7-tiny.pt 모델을 사용해서 영상 분석을 해볼 수 있습니다.

 

우선 yolov7 설치가 필요합니다.

 

GitHub - WongKinYiu/yolov7: Implementation of paper - YOLOv7: Trainable bag-of-freebies sets new state-of-the-art for real-time

Implementation of paper - YOLOv7: Trainable bag-of-freebies sets new state-of-the-art for real-time object detectors - GitHub - WongKinYiu/yolov7: Implementation of paper - YOLOv7: Trainable bag-of...

github.com

 

How to Deploy YOLOv7 to a Jetson Nano

We'll be creating a dataset, training a YOLOv7 computer vision model, and deploying it to a Jetson Nano to perform real-time object detection.

blog.roboflow.com

위 글을 참조하여 yolov7 설치 과정을 수행했습니다.

위 페이지의 내용을 아래에 정리해두었습니다.

 

일단은 yolov7 github를 clone 시킵시다.

cd

git clone https://github.com/WongKinYiu/yolov7.git

 

그리고 여기에 yolov7-tiny.pt 모델을 다운로드 받습니다.

cd yolov7

wget "https://github.com/WongKinYiu/yolov7/releases/download/v0.1/yolov7-tiny.pt"

 

 

우선 requirements.txt 에서 필요한 내용을 다운받아줍시다. 

그 전에, 이미 설치했던 opencv와 torch, torchvision에는 다음과 같이 주석 처리를 합니다.

 

# Usage: pip install -r requirements.txt

# Base ----------------------------------------
matplotlib>=3.2.2
numpy>=1.18.5,<1.24.0
#opencv-python>=4.1.1
Pillow>=7.1.2
PyYAML>=5.3.1
requests>=2.23.0
scipy>=1.4.1
#torch>=1.7.0,!=1.12.0
#torchvision>=0.8.1,!=0.13.0
tqdm>=4.41.0
protobuf<4.21.3

# Logging -------------------------------------
tensorboard>=2.4.1
# wandb

# Plotting ------------------------------------
pandas>=1.1.4
seaborn>=0.11.0

# Export --------------------------------------
# coremltools>=4.1  # CoreML export
# onnx>=1.9.0  # ONNX export
# onnx-simplifier>=0.3.6  # ONNX simplifier
# scikit-learn==0.19.2  # CoreML quantization
# tensorflow>=2.4.1  # TFLite export
# tensorflowjs>=3.9.0  # TF.js export
# openvino-dev  # OpenVINO export

# Extras --------------------------------------
ipython  # interactive notebook
psutil  # system utilization
thop  # FLOPs computation
# albumentations>=1.0.3
# pycocotools>=2.0  # COCO mAP
# roboflow

 

그리고 다음 명령을 실행시켜 다운로드 합니다.

sudo apt-get install python3-pip libjpeg-dev libopenblas-dev libopenmpi-dev libomp-dev

python3 -m pip install -U pip

python3 -m pip install -r ./requirements.txt

 

 

이제 yolov7-tiny.pt 모델을 이용하여 분석이 이루어지는지 테스트해보겠습니다.

python detect.py --weights yolov7-tiny.pt --conf 0.25 --img-size 640 --source inference/images/horses.jpg

 

이 명령을 수행하면 다음과 같이 분석된 이미지가 저장됩니다.

yolov7 디렉토리의 runs/detect/exp 에서 확인할 수 있습니다. 

 

만약 USB 웹캠을 연결하셨다면,

dev/video0 로 연결되어있을 때 다음과 같은 명령어로 실시간 영상 분석이 가능합니다.

python detect.py --weights yolov7-tiny.pt --conf 0.25 --img-size 640 --source 0

 

아마도 굉장히 느린 속도로 분석이 될 것입니다.

저는 3~5fps 정도가 얻어졌습니다.

이제 이를 17fps 정도로 가속시켜보겠습니다.

이 과정이 굉장히 피곤했는데, 

여러 글을 뒤적거리다 아래 글을 참조해서 성공했습니다.

 

YOLOv7 with TensorRT on Jetson Nano (with Python script example)

At the end of 2022, I started working on a project where the goal was to count cars and pedestrians. Because of privacy issues and lower…

medium.com

 

 

그럼 제가 수행한 방법을 설명하겠습니다.

우선 .pt 모델을 .engine 모델 (trt 모델) 로 바꾸는 과정이 먼저 수행되어야 합니다.

이 과정을 수행해주는 github repository를 clone 하겠습니다.

cd

git clone https://github.com/wang-xinyu/tensorrtx

 

이제 여기서 gen_wts.py라는 파일을 저희가 가지고있는 yolov7 디렉토리로 옮기겠습니다.

cd tensorrtx/yolov7

cp cp gen_wts.py ~/yolov7

cd ~/yolov7

 

그리고 .wts 파일로 변환시키도록 하겠습니다.

이 과정은 시간이 조금 소요되며,

결과적으로 yolov7-tiny.wts 파일이 생성됩니다.

python gen_wts.py -w yolov7-tiny.pt

 

다시 tensorrtx 디렉토리로 이동해줍니다.

cd ~/tensorrtx/yolov7

 

이제 cmake build 과정을 수행합니다.

mkdir build

cd build

cp ~/yolov7/yolov7-tiny.wts ~/tensorrtx/yolov7/build

cmake ..

make

 

빌드를 이용해서 yolov7-tiny.wts 파일을 .engine 파일로 획득하겠습니다.

sudo ./yolov7 -s yolov7-tiny.wts yolov7-tiny.engine t

그러면 build 디렉토리 내에 yolov7-tiny.engine 파일이 생성될 것 입니다.

 

.engine 파일을 이용해서 sample 이미지를 분석해보겠습니다.

sudo ./yolov7 -d yolov7-tiny.engine ../images

 

상위 디렉토리의 images 폴더에서 bus.jpg와 zidane.jpg가 분석된 것을 확인하셨다면

성공적으로 .engine파일이 만들어진 것입니다.

 

만약 안된다면, 제가 빌드한 .engine 파일과 libmyplugins.so을 다운받으시기 바랍니다.

wget "https://github.com/cobang0111/Tracker_Capstone_Design_2023-2/blob/main/yolov7-tiny.engine"

wget "https://github.com/cobang0111/Tracker_Capstone_Design_2023-2/blob/main/libmyplugins.so"

 

저도 별도로 다운해서 해보진 않았는데, 아마도 가능하지 않을까 생각합니다.

위 테스트 과정을 다시 수행해보시면 확인하실 수 있을 것 입니다.

 

그럼 이제 pycuda를 설치하겠습니다.

ln -s /usr/include/locale.h /usr/include/xlocale.h

pip3 install --global-option=build_ext --global-option="-I/usr/local/cuda/include" --global-option="-L/usr/local/cuda/lib64" pycuda

 

 

그리고 bashrc 파일에 해당 설치 경로를 추가하겠습니다.

sudo nano ~/.bashrc

# Add this line to the end
export PYTHONPATH=/usr/lib/python3.6/dist-packages:$PYTHONPATH

# Save and exit
source ~/.bashrc

 

이제 준비가 완료되었습니다.

아래 링크에서 yolov7_trt_cam.py를 다운 받으시기 바랍니다.

 

GitHub - spehj/jetson-nano-yolov7-tensorrt

Contribute to spehj/jetson-nano-yolov7-tensorrt development by creating an account on GitHub.

github.com

 

 

이제 여기서 main 함수 내에서 아래 부분을 수정해줍니다.

PLUGIN_LIBRARY = "../plugins/libmyplugins.so"
engine_file_path = "../engines/yolov7-tiny.engine"

# 아래와 같이 수정합니다.

PLUGIN_LIBRARY = "~/tensorrtx/yolov7/build/libmyplugins.so"
engine_file_path = "~/tensorrtx/yolov7/build/yolov7-tiny.engine"

 

libmyplugins.so 파일과 yolov7-tiny.engine 파일을

yolov7_trt_cam.py 가 있는 디렉토리로 옮겨 다음과 같이 수정해 사용할 수도 있습니다.

PLUGIN_LIBRARY = "libmyplugins.so"
engine_file_path = "yolov7-tiny.engine"

 

이제 이 python 파일을 실행시키면,

python3 yolov7_trt_cam.py

 

아래와 같이 yolov7_trt_cam.py  의 inferThread class 에 존재하는 sample 비디오를 분석합니다.

class inferThread(threading.Thread):
    def __init__(self, yolov7_wrapper):
        threading.Thread.__init__(self)
        self.yolov7_wrapper = yolov7_wrapper

        self.cap = cv2.VideoCapture(
            "/opt/nvidia/deepstream/deepstream/samples/streams/sample_1080p_h264.mp4"
        )

        # Check if the video file was successfully loaded
        if not self.cap.isOpened():
            print("Error opening video file")

 

그럼 아래 사진과 같이 해당 sample 동영상 분석이 이루어질 것입니다.

 

이 순간이 여러분에게 얼마나 감격스러운 순간일지는 모르겠습니다.

적어도 저에게는 정말로 기분 좋고 뿌듯한 순간이었습니다.

정말로 얼마나 인터넷을 뒤지고, chatGPT와 대화했는지 모르겠습니다.

이 글을 쓰는 이유도 이 글을 읽는 분들이 너무 헤메지 않길 바라면서도,

다시 제가 이 과제를 수행할 때 너무 헤메지 않고 싶어서 정리해두는 이유도 있습니다.

 

그럼 이제 소스를 바꿔보겠습니다. 

기본 비디오 채널로 바꿔 USB 웹캠 기반으로 분석이 이루어지게 합니다.

class inferThread(threading.Thread):
    def __init__(self, yolov7_wrapper):
        threading.Thread.__init__(self)
        self.yolov7_wrapper = yolov7_wrapper

        self.cap = cv2.VideoCapture(0) #여기를 수정하였습니다.

        # Check if the video file was successfully loaded
        if not self.cap.isOpened():
            print("Error opening video file")

 

만약 CSI camera, gstreamer 를 통해 분석을 하신다면 아래 함수를 추가하시고,

(세부 사항들을 확인하시고 height width, framerate, flip method 등 수정하시면 됩니다.)

# gstreamer for camera module
def gstreamer_pipeline(
    sensor_id=0,
    capture_width=1280,
    capture_height=720,
    display_width=640,
    display_height=480,
    framerate_1=60,
    flip_method=0,
):
    return (
        "nvarguscamerasrc sensor-id=%d ! "
        "video/x-raw(memory:NVMM), width=(int)%d, height=(int)%d, framerate=(fraction)%d/1 ! "
        "nvvidconv flip-method=%d ! "
        "video/x-raw, width=(int)%d, height=(int)%d, format=(string)BGRx ! "
        "videoconvert ! "
        "video/x-raw, format=(string)BGR ! appsink"
        % (
            sensor_id,
            capture_width,
            capture_height,
            framerate_1,
            flip_method,
            display_width,
            display_height
        )
    )

 

inferThread class 에서

self.cap을 다음과 같이 수정합니다.

self.cap = cv2.VideoCapture(gstreamer_pipeline(flip_method=0), cv2.CAP_GSTREAMER)

 

앞 글에서도 설명드렸듯이 딜레이가 존재합니다.

 

성공적으로 위 과정들이 다 수행되면,

카메라를 통해 실시간 영상 분석이 이루어지면서

약 17fps가 획득됩니다.

 

다음 글에서는 TensorRT 모델이 아닌

yolov7-tiny.pt 파일에 대해 DeepSORT를 적용시켜, 

id 기반 추적을 수행한 과정에 대해 작성하겠습니다.

 

728x90
반응형