Hi Paul-Antoine! On 2024-12-16T19:35:01+0100, Paul-Antoine Arras <par...@baylibre.com> wrote: > On 15/11/2024 14:59, Tobias Burnus wrote: >> Paul-Antoine Arras wrote: >>> This patch adds support for the `dispatch` construct and the >>> `adjust_args` clause to the Fortran front-end. >>> >>> Handling of `adjust_args` across translation units is missing due >>> to PR115271. >> >> >> First, can you add a run-time test? >> >> [I think it helps to have at least one run-time test feature for every >> major feature - as we had in the past e.g. C runtime tests and Fortran >> compile time tests - but it turned out that some flags was not set, >> causing the middle to ignore the feature completely ...] > > Added libgomp/testsuite/libgomp.fortran/dispatch-1.f90.
I see this new test case FAIL (execution test SIGSEGV) for most (but not all) offloading configurations, both GCN and nvptx: +PASS: libgomp.fortran/dispatch-1.f90 -O (test for excess errors) +FAIL: libgomp.fortran/dispatch-1.f90 -O execution test For example: [...] Thread 1 "a.out" received signal SIGSEGV, Segmentation fault. 0x00000000004022fc in procedures::bar (d_bv=0x7fffc7002040, d_av=0x7fffc7000000, n=1024) at source-gcc/libgomp/testsuite/libgomp.fortran/dispatch-1.f90:59 59 fp_bv(i) = fp_av(i) * i (gdb) bt #0 0x00000000004022fc in procedures::bar (d_bv=0x7fffc7002040, d_av=0x7fffc7000000, n=1024) at source-gcc/libgomp/testsuite/libgomp.fortran/dispatch-1.f90:59 #1 0x0000000000401c41 in procedures::test (n=1024) at source-gcc/libgomp/testsuite/libgomp.fortran/dispatch-1.f90:86 #2 0x0000000000402b1e in MAIN__ () at source-gcc/libgomp/testsuite/libgomp.fortran/dispatch-1.f90:115 (gdb) print i $1 = 1 (gdb) print fp_bv $2 = (0, <repeats 200 times>, ...) (gdb) print fp_av $3 = (0, <repeats 200 times>, ...) (gdb) print fp_bv(1) $4 = 0 (gdb) print fp_av(1) $5 = 0 (gdb) ptype fp_bv type = real(kind=8) (1024) (gdb) ptype fp_av type = real(kind=8) (1024) (gdb) up #1 0x0000000000401c41 in procedures::test (n=1024) at source-gcc/libgomp/testsuite/libgomp.fortran/dispatch-1.f90:86 86 !$omp dispatch nocontext(n > 1024) novariants(n < 1024) device(last_dev) (gdb) print last_dev $6 = 0 Grüße Thomas > --- /dev/null > +++ libgomp/testsuite/libgomp.fortran/dispatch-1.f90 > @@ -0,0 +1,120 @@ > +module procedures > + use iso_c_binding, only: c_ptr, c_f_pointer > + use omp_lib > + implicit none > + > + contains > + > + function foo(bv, av, n) result(res) > + implicit none > + integer :: res, n, i > + type(c_ptr) :: bv > + type(c_ptr) :: av > + real(8), pointer :: fp_bv(:), fp_av(:) ! Fortran pointers for array > access > + !$omp declare variant(bar) match(construct={dispatch}) > adjust_args(need_device_ptr: bv, av) > + !$omp declare variant(baz) match(implementation={vendor(gnu)}) > + > + ! Associate C pointers with Fortran pointers > + call c_f_pointer(bv, fp_bv, [n]) > + call c_f_pointer(av, fp_av, [n]) > + > + ! Perform operations using Fortran pointers > + do i = 1, n > + fp_bv(i) = fp_av(i) * i > + end do > + res = -1 > + end function foo > + > + function baz(d_bv, d_av, n) result(res) > + implicit none > + integer :: res, n, i > + type(c_ptr) :: d_bv > + type(c_ptr) :: d_av > + real(8), pointer :: fp_bv(:), fp_av(:) ! Fortran pointers for array > access > + > + ! Associate C pointers with Fortran pointers > + call c_f_pointer(d_bv, fp_bv, [n]) > + call c_f_pointer(d_av, fp_av, [n]) > + > + !$omp distribute parallel do > + do i = 1, n > + fp_bv(i) = fp_av(i) * i > + end do > + res = -3 > + end function baz > + > + function bar(d_bv, d_av, n) result(res) > + implicit none > + integer :: res, n, i > + type(c_ptr) :: d_bv > + type(c_ptr) :: d_av > + real(8), pointer :: fp_bv(:), fp_av(:) ! Fortran pointers for array > access > + > + ! Associate C pointers with Fortran pointers > + call c_f_pointer(d_bv, fp_bv, [n]) > + call c_f_pointer(d_av, fp_av, [n]) > + > + ! Perform operations on target > + do i = 1, n > + fp_bv(i) = fp_av(i) * i > + end do > + res = -2 > + end function bar > + > + function test(n) result(res) > + use iso_c_binding, only: c_ptr, c_loc > + implicit none > + integer :: n, res, i, f, ff, last_dev > + real(8), allocatable, target :: av(:), bv(:), d_bv(:) > + real(8), parameter :: e = 2.71828d0 > + type(c_ptr) :: c_av, c_bv, c_d_bv > + > + allocate(av(n), bv(n), d_bv(n)) > + > + ! Initialize arrays > + do i = 1, n > + av(i) = e * i > + bv(i) = 0.0d0 > + d_bv(i) = 0.0d0 > + end do > + > + last_dev = omp_get_num_devices() - 1 > + > + c_av = c_loc(av) > + c_d_bv = c_loc(d_bv) > + !$omp target data map(to: av(:n)) map(from: d_bv(:n)) device(last_dev) > if(n == 1024) > + !$omp dispatch nocontext(n > 1024) novariants(n < 1024) > device(last_dev) > + f = foo(c_d_bv, c_av, n) > + !$omp end target data > + > + c_bv = c_loc(bv) > + ff = foo(c_bv, c_loc(av), n) > + > + ! Verify results > + do i = 1, n > + if (d_bv(i) /= bv(i)) then > + write(0,*) 'ERROR at ', i, ': ', d_bv(i), ' (act) != ', bv(i), ' > (exp)' > + res = 1 > + return > + end if > + end do > + > + res = f > + deallocate(av, bv, d_bv) > + end function test > +end module procedures > + > +program main > + use procedures > + implicit none > + integer :: ret > + > + ret = test(1023) > + if (ret /= -1) stop 1 > + > + ret = test(1024) > + if (ret /= -2) stop 1 > + > + ret = test(1025) > + if (ret /= -3) stop 1 > +end program main