[nvptx] Unify C/Fortran routine handling in nvptx_goacc_validate_dims
authorTom de Vries <tdevries@suse.de>
Mon, 17 Dec 2018 21:26:49 +0000 (21:26 +0000)
committerTom de Vries <vries@gcc.gnu.org>
Mon, 17 Dec 2018 21:26:49 +0000 (21:26 +0000)
The Fortran front-end has a bug (PR72741) that means what when
nvptx_goacc_validate_dims is called for a Fortran routine, the dims parameter
is not the same as it would have been if the function would have been called for
an equivalent C routine.

Work around this bug by overriding the dims parameter for routines, allowing the
function to handle routines in Fortran and C the same.

Build and reg-tested on x86_64 with nvptx accelerator.

2018-12-17  Tom de Vries  <tdevries@suse.de>

* config/nvptx/nvptx.c (nvptx_goacc_validate_dims): Work around Fortran
bug PR72741 by overriding dims parameter for routines.

From-SVN: r267213

gcc/ChangeLog
gcc/config/nvptx/nvptx.c

index 7281f42d6fd9ce58f951f5695e8ca10b40f24ef2..767e3f8eb6b95ff1118998d9c1c3ac570a4a73a4 100644 (file)
@@ -1,3 +1,8 @@
+2018-12-17  Tom de Vries  <tdevries@suse.de>
+
+       * config/nvptx/nvptx.c (nvptx_goacc_validate_dims): Work around Fortran
+       bug PR72741 by overriding dims parameter for routines.
+
 2018-12-17  Tom de Vries  <tdevries@suse.de>
 
        * config/nvptx/nvptx.c (nvptx_goacc_validate_dims): Rewrite using
index 746d8bfb1004217d418c081780ad7183be179102..24727ad592010988088625de5aaf45003448f20c 100644 (file)
@@ -5212,6 +5212,42 @@ nvptx_goacc_validate_dims (tree decl, int dims[], int fn_level)
   else
     gcc_unreachable ();
 
+  if (routine_p)
+    {
+      /* OpenACC routines in C arrive here with the following attributes
+        (omitting the 'omp declare target'):
+        seq   : __attribute__((oacc function (0 1, 0 1, 0 1)))
+        vector: __attribute__((oacc function (0 1, 0 1, 1 0)))
+        worker: __attribute__((oacc function (0 1, 1 0, 1 0)))
+        gang  : __attribute__((oacc function (1 0, 1 0, 1 0)))
+
+        If we take f.i. the oacc function attribute of the worker routine
+        (0 1, 1 0, 1 0), then:
+        - the slice (0, 1, 1) is interpreted by oacc_fn_attrib_level as
+          meaning: worker routine, that is:
+          - can't contain gang loop (0),
+          - can contain worker loop (1),
+          - can contain vector loop (1).
+        - the slice (1, 0, 0) is interpreted by oacc_validate_dims as the
+        dimensions: gang: 1, worker: 0, vector: 0.
+
+        OTOH, routines in Fortran arrive here with these attributes:
+        seq   : __attribute__((oacc function (0 0, 0 0, 0 0)))
+        vector: __attribute__((oacc function (0 0, 0 0, 1 0)))
+        worker: __attribute__((oacc function (0 0, 1 0, 1 0)))
+        gang  : __attribute__((oacc function (1 0, 1 0, 1 0)))
+        that is, the same as for C but with the dimensions set to 0.
+
+        This is due to a bug in the Fortran front-end: PR72741.  Work around
+        this bug by forcing the dimensions to be the same in Fortran as for C,
+        to be able to handle C and Fortran routines uniformly in this
+        function.  */
+      dims[GOMP_DIM_VECTOR] = fn_level > GOMP_DIM_VECTOR ? 1 : 0;
+      dims[GOMP_DIM_WORKER] = fn_level > GOMP_DIM_WORKER ? 1 : 0;
+      dims[GOMP_DIM_GANG] = fn_level > GOMP_DIM_GANG ? 1 : 0;
+      changed = true;
+    }
+
   /* The vector size must be 32, unless this is a SEQ routine.  */
   if ((offload_region_p || oacc_default_dims_p
        || (routine_p && !routine_seq_p))