@@ -1962,7 +1962,50 @@ transform_call(int std, int ast)
19621962 ARGT_ARG (newargt , newj ) = pghpf_type (ty );
19631963 ++ newj ;
19641964 } else if (SDSCG (sptr )) {
1965-
1965+ /*
1966+ * If the array descriptor comes from the parent subprogram (Fortran
1967+ * term, host subprogram), the INTERNREF flag of array descriptor must
1968+ * be set. The missing case here is when the array is a static member
1969+ * of derived type var and the derived type var is defined in parent
1970+ * routine, the array descriptor is not set. The following code is to
1971+ * detect such case.
1972+ */
1973+
1974+ SPTR sdsdsptr = SDSCG (sptr );
1975+
1976+ /* Condition gbl.internal > 1 is to make sure that the current
1977+ * function is a contained subprogram.
1978+ * gbl.internal = 0, there is no contained subprogram.
1979+ * gbl.internal = 1, the current routine at least has a contain
1980+ * statement.
1981+ * gbl.internal > 1, the current routine is contained subprogram.
1982+ * A_TYPEG(ele) == A_MEM && needdescr && gbl.internal > 1
1983+ * is to make sure that the descriptor is for an array
1984+ * member in a derived-type variable if it is not an array variable
1985+ * member in the derived-type, the INTERNREF flag of its descriptor
1986+ * should be set in routine set_internref_flag in semsym.c.
1987+ *
1988+ * SCOPEG(sdsdsptr) && STYPEG(SCOPEG(sdsdsptr)) != ST_MODULE &&
1989+ * SCOPEG(sdsdsptr) == SCOPEG(gbl.currsub) is to make sure that the
1990+ * sdsc is a reference from the parent routine.
1991+ *
1992+ * Note that the fortran can only contain one-level depth of
1993+ * subprogram. The contained subprogram cannot contain any
1994+ * subprograms.
1995+ */
1996+ if (gbl .internal > 1 && A_TYPEG (ele ) == A_MEM && needdescr &&
1997+ SCOPEG (sdsdsptr ) && STYPEG (SCOPEG (sdsdsptr )) != ST_MODULE &&
1998+ SCOPEG (sdsdsptr ) == SCOPEG (gbl .currsub )) {
1999+ /* Pointer to the section descriptor created by the front-end
2000+ * (or any phase before transform()). If the field is non-zero,
2001+ * the transformer uses the descriptor located by this field;
2002+ * the actual symbol located by this field is a based/allocatable
2003+ * array.
2004+ */
2005+ if (SECDSCG (sdsdsptr ))
2006+ sdsdsptr = SECDSCG (sdsdsptr );
2007+ INTERNREFP (sdsdsptr , TRUE);
2008+ }
19662009 ARGT_ARG (newargt , newj ) = check_member (ele , mk_id (SDSCG (sptr )));
19672010 DESCUSEDP (sptr , 1 );
19682011 NODESCP (sptr , 0 );
@@ -2007,6 +2050,20 @@ transform_call(int std, int ast)
20072050 handle_seq_section (entry , ele , i , std , & retval , & descr , 1 ,
20082051 inface_arg );
20092052 } else {
2053+ SPTR descr_sptr = DESCRG (sptr );
2054+ /* Set the INTERNREF flag of array descriptor to make sure host
2055+ subroutines' array descriptor is accessible for contained
2056+ subroutines.
2057+ */
2058+ if (gbl .internal > 1 && A_TYPEG (ele ) == A_MEM && needdescr &&
2059+ descr_sptr > NOSYM && SCOPEG (descr_sptr ) &&
2060+ STYPEG (SCOPEG (descr_sptr )) != ST_MODULE &&
2061+ SCOPEG (descr_sptr ) == SCOPEG (gbl .currsub )) {
2062+ if (SECDSCG (descr_sptr ))
2063+ descr_sptr = SECDSCG (descr_sptr );
2064+
2065+ INTERNREFP (descr_sptr , TRUE);
2066+ }
20102067 retval = ele ;
20112068 descr = check_member (retval , mk_id (DESCRG (sptr )));
20122069 }
@@ -3690,7 +3747,8 @@ is_desc_needed(int entry, int arr_ast, int loc)
36903747 /* only user procedure may not need descr */
36913748 if (iface && HCCSYMG (iface ))
36923749 return TRUE;
3693- if (iface && STYPEG (entry ) != ST_PROC && STYPEG (entry ) != ST_ENTRY )
3750+ if (iface && STYPEG (entry ) != ST_PROC && STYPEG (entry ) != ST_ENTRY
3751+ && (STYPEG (entry ) != ST_MEMBER || !VTABLEG (entry )) && !is_procedure_ptr (entry ))
36943752 return TRUE;
36953753 /* for F90, F77, C, need descriptor if copy-in is needed */
36963754 if (!dscptr )
0 commit comments