x86 Ubuntu 交叉編譯 aarch64(ARM64, jetson) CUDA依賴程序


x86 Ubuntu 交叉編譯 aarch64(ARM64) CUDA依賴程序

0 文檔說明

該文檔用來記錄如何從零開始構建一個能夠編輯CUDA依賴程序的交叉編譯環境,並完成交叉編譯工作。

1 環境准備

1.1 操作系統及硬件

  • 安裝有ubuntu 18.04 x86的物理機或虛擬機:此處ubuntu系統版本的選擇和目標aarch64(jetson平台)相同(不相同的話沒試過);
  • 一台已有的jetson;(用於配置的aarch64 ubuntu環境安裝的庫異常的時候,需要在jetson上面進行安裝,並獲取對應的庫文件);

1.2 安裝軟件

1.2.1 配置aarch64 ubuntu運行環境

需要注意的是:此處配置aarch64 ubuntu運行環境,並不是直接在該環境下進行編譯工作,因為該環境下的編譯太慢了;配置該環境,主要是為了能夠更快速,更加便捷的獲取交叉編譯依賴的動態庫,和靜態庫,頭文件信息等。

這部分參考:從0開始使用QEMU模擬ARM開發環境之定制Ubuntu rootfs(根文件系統)_墨1024的博客-CSDN博客_qemu rootfs

QEMU是一套由法布里斯·貝拉(Fabrice Bellard)所編寫的以GPL許可證分發源碼的模擬處理器軟件,在GNU/Linux平台上使用廣泛。

整個配置的基本過程如下:

  • 下載文件:ubuntu-base-18.04.5-base-arm64.tar.gz,地址為Ubuntu官網

  • x84 ubuntu系統上新建rootfs目錄,並將上述壓縮包解壓到該目錄:
    $ mkdir ~/rootfs以及$ tar -zxf ubuntu-base-18.04.5-base-arm64.tar.gz -C ~/rootfs

  • 安裝qemu包:$ sudo apt-get install qemu qemu-user-static binfmt-support debootstrap

  • 注冊aarch64 ubuntu運行環境:$ sudo update-binfmts --enable qemu-aarch64

  • 為了能在x86 Ubuntuchroot~/rootfs並執行aarch64的程序,需要將qemu-aarch64-static拷貝到~/rootfs/usr/bin/
    $ cp -av /usr/bin/qemu-aarch64-static ~/rootfs/usr/bin/

  • 配置arrch64 Ubuntu的網關,與x86 Ubuntu共享網絡$ cp /etc/resolv.conf ~/rootfs/etc/resolv.conf

  • 編寫運行腳本$ gedit ~/mount.sh

    #!/bin/bash
    mnt() {
    	echo "MOUNTING"
    	sudo mount -t proc /proc ${2}proc
    	sudo mount -t sysfs /sys ${2}sys
    	sudo mount -o bind /dev ${2}dev
    	sudo mount -o bind /dev/pts ${2}dev/pts
    	sudo chroot ${2}
    }
    umnt() {
    	echo "UNMOUNTING"
    	sudo umount ${2}proc
    	sudo umount ${2}sys
    	sudo umount ${2}dev/pts
    	sudo umount ${2}dev
    }
    
    if [ "$1" == "-m" ] && [ -n "$2" ] ;
    then
    	mnt $1 $2
    elif [ "$1" == "-u" ] && [ -n "$2" ];
    then
    	umnt $1 $2
    else
    	echo ""
    	echo "Either 1'st, 2'nd or both parameters were missing"
    	echo ""
    	echo "1'st parameter can be one of these: -m(mount) OR -u(umount)"
    	echo "2'nd parameter is the full path of rootfs directory(with trailing '/')"
    	echo ""
    	echo "For example: ch-mount -m /media/sdcard/"
    	echo ""
    	echo 1st parameter : ${1}
    	echo 2nd parameter : ${2}
    fi
    
  • 設置權限:$ sudo chmod +x mount.sh

  • 進入aarch64 ubuntu系統:$ source mount.sh -m ~/rootfs/

  • 退出aarch64 ubuntu系統:$ source mount.sh -u ~/rootfs/注意:進入aarch64 Ubuntu后,不要直接關閉終端,必須先exit內部終端,然后外部終端執行退出命令,否則x86 Ubuntu終端不可用了

  • 進入aarch64 ubuntu之后,需要配置源,參見ubuntu arm/arm64搭建和更改為國內源_漢文修士的博客-CSDN博客_ubuntuarm64源

  • apt update之后可以用apt install安裝需要的庫;

1.2.2 利用SDK Manager安裝cuda

這里可以利用nvidia自帶的sdk manager安裝cuda環境。下載地址見:NVIDIA SDK Manager | NVIDIA Developer。安裝完sdk manager之后

在sdk manager中選擇如下安裝包,按照步驟進行安裝即可。

2 交叉編譯

2.1 安裝編譯工具

注意:關於自帶的cmake版本過低,可以自行到Download | CMake官網下載合適的版本即可。

x86 ubuntu中編譯aarch64架構的軟件,需要先安裝對應的編譯工具,如下:

$ sudo apt-get install gcc-aarch64-linux-gnu g++-aarch64-linux-gnu

安裝完之后,會在bin下多出兩個可執行文件,/usr/bin/aarch64-linux-gnu-gcc/usr/bin/aarch64-linux-gnu-g++。交叉編譯的工作就是需要這個執行文件完成。同時,在usr目錄下還會多出一個目錄,/usr/aarch64-linux-gnu,該目錄下面存儲了aarch64架構下的鏈接庫。

2.2 配置交叉編譯toolchain.cmake

改文件參考了:https://docs.nvidia.com/vpi/sample_cross_aarch64.html

# ref: https://docs.nvidia.com/vpi/sample_cross_aarch64.html
set(CMAKE_SYSTEM_NAME Linux)
set(CMAKE_SYSTEM_PROCESSOR aarch64)

set(CMAKE_C_COMPILER /usr/bin/aarch64-linux-gnu-gcc)
set(CMAKE_CXX_COMPILER /usr/bin/aarch64-linux-gnc-g++)

set(CMAKE_FIND_ROOT_PATH /usr/aarch64-linux-gnu)
set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE BOTH)
set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY ONLY)
set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM BOTH)

set(CMAKE_CUDA_FLAGS "-ccbin ${CMAKE_CXX_COMPILER} -Xcompiler -fPIC" CACHE STRING "" FORCE)

這里有個需要關注的點是配置了,CMAKE_CUDA_FLAGS,其中對ccbin參數設置為${CMAKE_CXX_COMPILER},這個目的是設置nvcc執行過程中回調用的編譯器,如果沒有這個,那么生成得到.o文件將是host 機器(x86)平台下面的。

參考中的set(CMAKE_TRY_COMPILER_TARGET_TYPE STATIC_LIBRARY)這句話可以不需要,加上的話cmake的時候cuda檢測會通不過。

2.3 執行編譯

cmake -DCMAKE_TOOLCHAIN_FILE=toolchain.cmake ../

是不是這樣就完事ok了。其實並不然。在編譯過程中會出現很多鏈接庫缺失的問題。這個時候就需要進入aarch64 ubuntu環境安裝對應的庫,並將安裝后的頭文件,庫文件拷貝到/usr/aarch64-linux-gnu/lib目錄下(或/usr/aarch64-linux-gnu/usr/lib,用於將后面拷貝的和原始帶的庫進行區分),頭文件放到/usr/aarch64-linux-gnu/include/中。當然我們的頭文件查找方式設置的是set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE BOTH),如果在host系統目錄下能夠找到,那么可以不用進行拷貝。另外還需要注意的是,在aarch64 ubuntu環境下安裝的庫存在異常的可能,那么可以在jetson上面進行安裝,然后將對應庫拷貝出來即可。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM