Во-первых, мои исходные программы отображаются следующим образом:
call_fun.f90
program call_fun
use omp_lib
implicit none
integer, parameter :: N = 100
integer a(N), b(N), c(N)
integer i
do i = 1, N
a(i) = i
b(i) = i+1
end do
!$omp target
!$omp parallel do
do i = 1, N
call vec_add(a(i), b(i), c(i))
end do
!$omp end target
write(*,10) N, c(N)
10 format('c[', I4, ']=', I6)
end program
vec_add.f90
subroutine vec_add(a, b, c)
implicit none
integer a, b, c
c = a + b
end
Очевидно, что эти две программы просты, и я просто для тестирования. Затем я использую следующие команды для компиляции и компоновки программ:
gfortran -fopenmp -foffload=nvptx-none -c vec_add.f90 call_fun.f90
gfortran -fopenmp -foffload=nvptx-none call_fun.o vec_add.o -o call.x
наконец, я получил следующие сообщения об ошибках:
unresolved symbol vec_add_
collect2: 错误:ld 返回 1
mkoffload: fatal error: x86_64-pc-linux-gnu-accel-nvptx-none-gcc returned 1
exit status
compilation terminated.
lto-wrapper: 致命错误:/home/gjh/software/offload/install/libexec/gcc/x86_64-
pc-linux-gnu/9.0.0//accel/nvptx-none/mkoffload 以返回值 1 退出
编译中断。
/usr/bin/x86_64-linux-gnu-ld: error: lto-wrapper failed
collect2: 错误:ld 返回 1
Кажется, что компоновщик не может найти vec_add_, но я не знаю, как это исправить. Моя версия GCC - 9.0.0 (20180605), а соответствующая версия OpenMP - 4.5. Я не знаю, если он не поддерживает вызов функции в конструкции задачи, или некоторые другие причины. Кто-нибудь сталкивался с такой проблемой?
Более подробно, я использовал следующий скрипт для настройки среды:
#!/bin/sh
#
# Build GCC with support for offloading to NVIDIA GPUs
#
work_dir=$HOME/software/offload
install_dir=$work_dir/install
# Location of the installed CUDA toolkit
cuda=/usr/local/cuda
# Build assembler and linking tools
cd $work_dir
git clone https://github.com/MentorEmbedded/nvptx-tools
cd nvptx-tools
./configure \
--with-cuda-driver-include=$cuda/include \
--with-cuda-driver-lib=$cuda/lib64 \
--enable-languages="c,c++,fortran,lto" \
--prefix=$install_dir
make clean
make
make install
cd ../
# Set up the GCC source tree
git clone https://github.com/MentorEmbedded/nvptx-newlib
svn co svn://gcc.gnu.org/svn/gcc/trunk gcc
cd gcc
contrib/download_prerequistes
ln -s ../nvptx-newlib/newlib newlib
cd ..
target=$(gcc/config.guess)
# Build nvptx GCC
mkdir build-nvptx-gcc
cd build-nvptx-gcc
../gcc/configure \
--target=nvptx-none --with-build-time-tools=$install_dir/nvptx-none/bin \
--enable-as-accelerator-for=$target \
--disable-sjlj-exceptions \
--enable-newlib-io-long-long \
--enable-languages="c,c++,fortran,lto" \
--prefix=$install_dir
make clean
make -j4
make install
cd ..
# Build host GCC
mkdir build-host-gcc
cd build-host-gcc
../gcc/configure \
--enable-offload-targets=nvptx-none \
--with-cuda-driver-include=$cuda/include \
--with-cuda-driver-lib=$cuda/lib64 \
--disable-bootstrap \
--disable-multilib \
--enable-languages="c,c++,fortran,lto" \
--prefix=$install_dir
make clean
make -j4
make install
cd ..
этот сценарий был написан другими людьми, и я ссылался на него. Кроме того, я устанавливаю переменные среды следующим образом.
export LD_LIBRARY_PATH=/usr/local/cuda-9.2/lib64:/home/gjh/software/offload/install/lib64:$LD_LIBRARY_PATH
export PATH=/usr/local/cuda-9.2/bin:/home/gjh/software/offload/install/bin:$PATH