Observed issues › cce-mapper-next-map-copy-back
ftn in copy mode: the map list item after a map clause with a mapper modifier is not copied back
Legality: contested. An independent adjudicating reading finds the result not required: Mapper decay is correct (to with tofrom gives to), so sv=1 is right. The host_flag difference is not required: default-device-var is implementation-defined and target regions may execute on the host when the device does not exist or is unsupported. How this is checked
Affected variants
| Compiler | MI300A gfx942 unified memory (XNACK 1) | MI300A gfx942 copy (XNACK 0) | MI250X gfx90a copy (XNACK 0) | MI300X gfx942 copy (XNACK 0) | MI350X gfx950 copy (XNACK 0) | A100 sm_80 separate memory | A100 sm_80 managed memory |
|---|---|---|---|---|---|---|---|
| AFAR 24.3.0 | correct | correct | correct | correct | correct | n/a | n/a |
| CCE 19.0.0 | correct | behaves incorrectly | behaves incorrectly | unknown not run | unknown not run | n/a | n/a |
| CCE 20.0.2 | correct | behaves incorrectly | behaves incorrectly | unknown not run | unknown not run | n/a | n/a |
| CCE 21.0.3 | correct | correct | correct | unknown not run | unknown not run | n/a | n/a |
| CCE 21.0.4 | correct | correct | correct | unknown not run | unknown not run | n/a | n/a |
| NVHPC 25.11 | n/a | n/a | n/a | n/a | n/a | fails another way | fails another way |
| NVHPC 26.9 | n/a | n/a | n/a | n/a | n/a | fails another way | fails another way |
| GCC 16.2.0 | fails another way | fails another way | fails another way | fails another way | fails another way | fails another way | n/a |
"behaves incorrectly" / "not supported": this issue, confirmed in up to four environments (another build directory, another node, a repeat). "fails another way": a different failure, not counted as this issue. "unknown": not run there, or the runs disagree.
Messages
| Result | Compiler and GPU | Message |
|---|---|---|
| behaves incorrectly | CCE 19.0.0, MI300A copy CCE 19.0.0, MI250X CCE 20.0.2, MI300A copy CCE 20.0.2, MI250X | showhost_flag= 1 b1= 3 sv= 1 |
| fails another way | NVHPC 25.11, A100 separate NVHPC 25.11, A100 managed NVHPC 26.9, A100 separate NVHPC 26.9, A100 managed | showNVFORTRAN-W-0287-Unrecognized OpenMP directive - declare (cce-mapper-next-map-copy-back.f90: 7) NVFORTRAN-S-0034-Syntax error at or near : (cce-mapper-next-map-copy-back.f90: 13) 0 inform, 1 warnings, 1 severes, 0 fatal for p |
| fails another way | GCC 16.2.0, MI300A unified GCC 16.2.0, MI300A copy GCC 16.2.0, MI250X GCC 16.2.0, MI300X GCC 16.2.0, MI350X GCC 16.2.0, A100 separate | showcce-mapper-next-map-copy-back.f90:7:9:
7 | !$omp declare mapper(mm: dt :: q) map(to: q%v)
| 1
Error: Unclassifiable OpenMP directive at (1)
cce-mapper-next-map-copy-back.f90:13:39:
13 | !$omp target map(from: b) map(mapper(mm), tofrom: s) map(tofrom: host_flag)
| 1
Error: Syntax error in OpenMP variable list at (1) |
Reproduce
CCE 19.0.0, MI300A copy
module load cce/19.0.0 craype-accel-amd-gfx942 rocm/6.4.3 module unload cray-mpich ftn -fopenmp -O2 repro.f90 -o repro HSA_XNACK=0 OMP_TARGET_OFFLOAD=mandatory ./repro
CCE 20.0.2, MI300A copy
module load cce/20.0.2 craype-accel-amd-gfx942 rocm/6.4.3 module unload cray-mpich ftn -fopenmp -O2 repro.f90 -o repro HSA_XNACK=0 OMP_TARGET_OFFLOAD=mandatory ./repro
AFAR 24.3.0, MI300A unified (runs correctly)
$AFAR/bin/amdflang -fopenmp --offload-arch=gfx942 -O2 repro.f90 -o repro HSA_XNACK=1 OMP_TARGET_OFFLOAD=mandatory ./repro
Program (43 lines)
! (copy mode for the whole catalog): CCE 19 and 20 lose the
! copy-back of the map list item that FOLLOWS a map clause with a mapper
! modifier, at HSA_XNACK=0 only (separate host and device memory).
! s is mapped through the user-defined mapper mm (map(to: q%v)); the
! final map type is to (5.2 §5.8.8 p.163, Table 5.3: mapper to, clause
! tofrom -> to), so s%v keeps its host value 1 in copy mode. host_flag is
! map(tofrom:) and is set to 0 on the device; it must come back (5.2 §5.8.3
! p.151: "the map-type is replaced with a final map type ... according to
! the rules of map-type decay" applies to the mapper's list item only).
! Expected (copy mode): host_flag= 0 b1= 3 sv= 1
! Observed (tuolumne, MI300A, 2026-10-22, 3 runs each, -O2,
! OMP_TARGET_OFFLOAD=mandatory):
! - CCE 19.0.0, 20.0.2 at HSA_XNACK=0: host_flag= 1 b1= 3 sv= 1 on every
! run: the region ran on the device (b came back, s%v was not copied
! back) but host_flag's copy-back is lost. With the host_flag clause
! BEFORE the mapper clause, host_flag= 0 (correct); without the mapper
! modifier correct. At HSA_XNACK=1 correct (host_flag= 0, sv= 7).
! - CCE 21.0.3 and AFAR 24.0.0git: correct in both modes.
! The catalog's map.mapper programs (5.0, 5.2) put host_flag after the
! mapper clause, so CCE 19/20 report them as "fell back to host"
! (ran_on_host=1) at HSA_XNACK=0.
! AFAR: amdflang -fopenmp --offload-arch=gfx942 -O2
! CCE: ftn -fopenmp -O2 (module load cce/<v> craype-accel-amd-gfx942 rocm)
! Run: OMP_TARGET_OFFLOAD=mandatory HSA_XNACK=0 ./a.out
program p
use omp_lib, only: omp_is_initial_device
implicit none
type :: dt
integer :: v
end type dt
!$omp declare mapper(mm: dt :: q) map(to: q%v)
integer :: host_flag, b(4)
type(dt) :: s
s%v = 1
host_flag = 1
b = 0
!$omp target map(from: b) map(mapper(mm), tofrom: s) map(tofrom: host_flag)
host_flag = merge(1, 0, omp_is_initial_device())
b = 2 + s%v
s%v = 7
!$omp end target
print *, 'host_flag=', host_flag, ' b1=', b(1), ' sv=', s%v
end program p
Something to add? Dispute its legality · Report it fixed in a newer release · Report a mistake on this page
Expected and observed
Expected
host_flag= 0 b1= 3 sv= 1
Observed where it behaves incorrectly
host_flag= 1 b1= 3 sv= 1
What the specification requires
The specification text this program relies on and the compiler is expected to support.
OpenMP 5.2 §5.8.8 p.163
OpenMP 5.2 §5.8.3 p.151
the map-type is replaced with a final map type ... according to the rules of map-type decay
Evidence
Same compiler, one change
- the map(tofrom: host_flag) clause written before the mapper clause: AFAR 24.3.0: correct; CCE 19.0.0: correct; CCE 20.0.2: correct; CCE 21.0.3: correct; CCE 21.0.4: correct
Control program
program p use omp_lib, only: omp_is_initial_device implicit none type :: dt integer :: v end type dt !$omp declare mapper(mm: dt :: q) map(to: q%v) integer :: host_flag, b(4) type(dt) :: s s%v = 1 host_flag = 1 b = 0 !$omp target map(tofrom: host_flag) map(from: b) map(mapper(mm), tofrom: s) host_flag = merge(1, 0, omp_is_initial_device()) b = 2 + s%v s%v = 7 !$omp end target print *, 'host_flag=', host_flag, ' b1=', b(1), ' sv=', s%v end program p
Other compilers run it correctly
AFAR 24.3.0