Observed issues › nested/gcc-acc-c-struct-and-member-array-one-directive
GCC OpenACC: structure and member array in one data directive stops at run time
Legality: independently confirmed. 2 independent readings find the program legal and the result required. How this is checked
GCC stops with "outer struct not mapped for attach" at a data directive naming a structure and its pointee array.
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 | n/a | n/a | n/a | n/a | n/a | n/a | n/a |
| CCE 19.0.0 | n/a | n/a | unknown not run | unknown not run | unknown not run | n/a | n/a |
| CCE 20.0.2 | n/a | n/a | unknown not run | unknown not run | unknown not run | n/a | n/a |
| CCE 21.0.3 | n/a | n/a | unknown not run | unknown not run | unknown not run | n/a | n/a |
| CCE 21.0.4 | n/a | n/a | unknown not run | unknown not run | unknown not run | n/a | n/a |
| NVHPC 25.11 | n/a | n/a | n/a | n/a | n/a | correct | correct |
| NVHPC 26.9 | n/a | n/a | n/a | n/a | n/a | correct | correct |
| GCC 16.2.0 | behaves incorrectly | behaves incorrectly | behaves incorrectly | behaves incorrectly | behaves incorrectly | behaves incorrectly | 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 | 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 | showlibgomp: outer struct not mapped for attach |
Reproduce
GCC 16.2.0, MI300A unified
export LD_LIBRARY_PATH=$GCC_16_2/lib64:/opt/rocm-7.2.1/lib $GCC_16_2/bin/gcc -fopenacc -foffload=amdgcn-amdhsa -foffload-options=amdgcn-amdhsa=-march=gfx942 -O2 repro.c -o repro HSA_XNACK=1 ./repro
GCC 16.2.0, A100 separate
export PATH=/usr/local/cuda/bin:$PATH export LD_LIBRARY_PATH=$GCC_16_2/lib64 $GCC_16_2/bin/gcc -fopenacc -foffload=nvptx-none -foffload-options=nvptx-none=-march=sm_80 -foffload-options=nvptx-none=-latomic -O2 repro.c -o repro ./repro
NVHPC 25.11, A100 separate (runs correctly)
export LD_LIBRARY_PATH=$NVHPC_25_11/compilers/lib nvc -acc=gpu -gpu=cc80 -gpu=mem:separate -O2 repro.c -o repro ./repro
Program (77 lines)
// # Finding (nested-data): GCC OpenACC: copyin of a structure and of the array its pointer member points to in one data
// # directive stops at run time: "outer struct not mapped for attach"
//
// - toolchains and modes that fail: gcc_g90 (GCC 16.2.0), gcc_sm80 (GCC 16.2.0); modes: copy; -O2
// - build: gcc -fopenacc -foffload=amdgcn-amdhsa -foffload-options=amdgcn-amdhsa=-march=gfx90a -O2 (gcc_g90); gcc -fopenacc
// -foffload=nvptx-none -foffload-options=nvptx-none=-march=sm_80 -foffload-options=nvptx-none=-latomic -O2 (gcc_sm80)
// - failure: wrong_answer (check=fail)
// - observed: `libgomp: outer struct not mapped for attach`; identical signature on 2 of 2 failing cells
// - expected: compiles and prints `tot= 15` with `check=pass`
// - rule: OpenACC 3.4 §2.7.8 p.55 l.1902-1903: "If var is a pointer reference, an attach pointer action is performed
// followed by an increment counter action"; the attach actions of a directive are scheduled after its transfers: "The
// implementation schedules pointer updates after any data transfers due to transfer in actions that are performed for
// the same directive." (§2.7.2 p.52 l.1785-1786), so the structure and the array its member points to may be mapped by
// one directive
// - same-compiler control: controls/c3-ctl-nested-data.c (one change from this file; correct on gcc_g90 (GCC 16.2.0), gcc_sm80 (GCC
// 16.2.0); rows results/nested/red/red6.jsonl, results/nested/red/wgs.jsonl, results/nested/red/wnv.jsonl);
// controls/c5-acc-serial-struct-and-array.c (one change from this file; correct on gcc_g90 (GCC 16.2.0), gcc_sm80 (GCC 16.2.0);
// rows results/nested/red/red6.jsonl, results/nested/red/wgs.jsonl, results/nested/red/wnv.jsonl)
// - other families: nvhpc (NVHPC 25.11), nvhpc269 (NVHPC 26.9) run the file correctly (rows results/nested/red/wnv.jsonl, site
// rows, check case site-nested--gcc-acc-c-struct-and-member-array-one-directive)
// - gate and confirmer: campaign gate of the programs below: 82 cells, 82 confirmed in the four environments (a-d; (c) on another
// node or GPU; rows results/nested/big/gate_reruns.part.<host>.1371141.jsonl,
// results/nested/big/gate_reruns.part.<host>.517665.jsonl,
// results/nested/big/gate_reruns.part.wingtip.501872.jsonl,
// results/nested/big/gate_reruns.part.wingtip.501873.jsonl,
// results/nested/big/gate_reruns.part.wingtip.711615.jsonl,
// results/nested/big/gate_reruns.part.wingtip.724122.jsonl, results/nested/big/rows.part.<host>.397000.jsonl,
// results/nested/big/rows.part.wingtip.3886921.jsonl,
// results/nested/main/gate_reruns.part.<host>.2711328.jsonl, results/nested/main/gate_reruns.part.<host>.351539.jsonl,
// results/nested/main/gate_reruns.part.wingtip.3582436.jsonl,
// results/nested/main/gate_reruns.part.wingtip.3582437.jsonl,
// results/nested/main/gate_reruns.part.wingtip.3637854.jsonl,
// results/nested/main/gate_reruns.part.wingtip.3639010.jsonl,
// results/nested/main/rows.part.<host>.2691037.jsonl, results/nested/main/rows.part.wingtip.3363229.jsonl,
// results/nested/main/rows.part.wingtip.3363230.jsonl)
// - programs (41): nd-c-acc-tdata-alias-d2-20ae973e, nd-c-acc-tdata-alias-d2-23c00982, nd-c-acc-tdata-alias-d2-72a1d7e8,
// nd-c-acc-tdata-alias-d2-af2ec241, nd-c-acc-tdata-chain-d1-0ed1bf12, nd-c-acc-tdata-chain-d1-9886a523,
// nd-c-acc-tdata-chain-d2-085c13be, nd-c-acc-tdata-chain-d2-1a584322, nd-c-acc-tdata-chain-d2-25c6c4d8,
// nd-c-acc-tdata-chain-d2-361ca0f9, nd-c-acc-tdata-chain-d2-36b0e127, nd-c-acc-tdata-chain-d2-43985434,
// nd-c-acc-tdata-chain-d2-462abe25, nd-c-acc-tdata-chain-d2-5e7728c0, nd-c-acc-tdata-chain-d2-85f2a830,
// nd-c-acc-tdata-chain-d2-a3760a7a, nd-c-acc-tdata-chain-d2-af1ca1e6, nd-c-acc-tdata-chain-d2-d9e6a839,
// nd-c-acc-tdata-chain-d2-f585dbe8, nd-c-acc-tdata-chain-d2-f85f821b, nd-c-acc-tdata-chain-d3-474c8b58,
// nd-c-acc-tdata-chain-d3-475cfe44, nd-c-acc-tdata-chain-d3-4bf0e2c8, nd-c-acc-tdata-chain-d3-5c2aa78e,
// nd-c-acc-tdata-chain-d3-63c6d8ed, nd-c-acc-tdata-chain-d3-8fa68caf, nd-c-acc-tdata-chain-d3-99924776,
// nd-c-acc-tdata-chain-d3-9d855631, nd-c-acc-tdata-chain-d3-f891fd7c, nd-c-acc-tdata-diamond-d3-6974fab3,
// nd-c-acc-tdata-diamond-d3-6fe9454b, nd-c-acc-tdata-diamond-d3-87e0b9a8, nd-c-acc-tdata-list-d2-1ab29ba9,
// nd-c-acc-tdata-list-d2-cc8507d1, nd-c-acc-tdata-list-d3-367465a3, nd-c-acc-tdata-tree-d2-12d76b63,
// nd-c-acc-tdata-tree-d2-87d4954e, nd-c-acc-tdata-tree-d2-aedfe6ab, nd-c-acc-tdata-tree-d2-fdcb2b5a,
// nd-c-acc-tdata-tree-d3-335e85bb, nd-c-acc-tdata-tree-d3-98389330
// - legality: the rules (offload.engine.rules) accept it; both NVHPC releases compile and run the reduction correctly (a
// compiler of another family; the registry has no OpenACC C clause checker, so this is acceptance and execution, not a
// clause check)
#include <stdio.h>
#include <stdlib.h>
#include <openacc.h>
struct s0 { int v; int *a; };
int main(void)
{
int hf = 1, i, tot = 0, ok;
struct s0 r;
r.v = 5; r.a = malloc(4 * sizeof(int));
for (i = 0; i < 4; i++) r.a[i] = i + 1;
#pragma acc serial copy(hf)
hf = acc_on_device(acc_device_host) ? 1 : 0;
#pragma acc data copyin(r, r.a[0:4])
{
#pragma acc serial copy(tot) present(r)
{
tot = r.v;
for (int q = 0; q < 4; q++) tot += r.a[q];
}
}
ok = tot == 15;
printf("tot= %d\n", tot);
printf("RESULT ran_on_host=%d check=%s\n", hf, ok ? "pass" : "fail");
return 0;
}
Something to add? Dispute its legality · Report it fixed in a newer release · Report a mistake on this page
Expected and observed
Observed where it behaves incorrectly
libgomp: outer struct not mapped for attach
What the specification requires
The specification text this program relies on and the compiler is expected to support.
OpenACC 3.4 §2.7.8 p.55 l.1902-1903
If var is a pointer reference, an attach pointer action is performed followed by an increment counter action
OpenACC 3.4 §2.7.2 p.52 l.1785-1786
The implementation schedules pointer updates after any data transfers due to transfer in actions that are performed for the same directive.
Evidence
Same compiler, one change
- one change from the finding; correct on gcc_g90, gcc_sm80: not run yet
Control program
// control: two nested data constructs #include <stdio.h> #include <stdlib.h> #include <openacc.h> struct s0 { int v; int *a; }; int main(void) { int hf = 1, i, tot = 0, ok; struct s0 r; r.v = 5; r.a = malloc(4 * sizeof(int)); for (i = 0; i < 4; i++) r.a[i] = i + 1; #pragma acc serial copy(hf) hf = acc_on_device(acc_device_host) ? 1 : 0; #pragma acc data copyin(r) #pragma acc data copyin(r.a[0:4]) { #pragma acc serial copy(tot) present(r) { tot = r.v; for (int q = 0; q < 4; q++) tot += r.a[q]; } } ok = tot == 15; printf("tot= %d\n", tot); printf("RESULT ran_on_host=%d check=%s\n", hf, ok ? "pass" : "fail"); return 0; } - one change from the finding; correct on gcc_g90, gcc_sm80: not run yet
Control program
// OpenACC compute construct copyin(r, r.a[0:4]) #include <stdio.h> #include <stdlib.h> #include <openacc.h> struct s0 { int v; int *a; }; int main(void) { int hf = 1, i, tot = 0, ok; struct s0 r; r.v = 5; r.a = malloc(4 * sizeof(int)); for (i = 0; i < 4; i++) r.a[i] = i + 1; #pragma acc serial copy(hf) hf = acc_on_device(acc_device_host) ? 1 : 0; { #pragma acc serial copy(tot) copyin(r, r.a[0:4]) { tot = r.v; for (int q = 0; q < 4; q++) tot += r.a[q]; } } ok = tot == 15; printf("tot= %d\n", tot); printf("RESULT ran_on_host=%d check=%s\n", hf, ok ? "pass" : "fail"); return 0; }
Other compilers run it correctly
NVHPC 25.11, NVHPC 26.9