? CLASS_DATA (sym)->attr.class_pointer : sym->attr.pointer;
for (ref = e->ref; ref && check_intentin; ref = ref->next)
{
- if (ptr_component && ref->type == REF_COMPONENT)
+ /* Associate-targets need special handling. Subobjects of an object with
+ the PROTECTED attribute inherit this attribute. */
+ if (ptr_component && ref->type == REF_COMPONENT
+ && !sym->assoc && !sym->attr.is_protected)
check_intentin = false;
if (ref->type == REF_COMPONENT)
{
}
}
+ /* See if the INTENT(IN) check should apply to an ASSOCIATE target. */
+ if (check_intentin
+ && sym->assoc
+ && sym->assoc->target
+ && sym->assoc->target->symtree
+ && sym->assoc->target->symtree->n.sym
+ && sym->assoc->target->symtree->n.sym->attr.dummy
+ && sym->assoc->target->symtree->n.sym->attr.intent != INTENT_IN)
+ check_intentin = false;
+
if (check_intentin
&& (sym->attr.intent == INTENT_IN
|| (sym->attr.select_type_temporary && sym->assoc
&& sym->assoc->target && sym->assoc->target->symtree
&& sym->assoc->target->symtree->n.sym->attr.intent == INTENT_IN)))
{
+ const char *name = (sym->attr.select_type_temporary
+ ? sym->assoc->target->symtree->name : sym->name);
if (pointer && is_pointer)
{
if (context)
gfc_error ("Dummy argument %qs with INTENT(IN) in pointer"
" association context (%s) at %L",
- sym->name, context, &e->where);
+ name, context, &e->where);
return false;
}
if (!pointer && !is_pointer && !sym->attr.pointer)
{
- const char *name = sym->attr.select_type_temporary
- ? sym->assoc->target->symtree->name : sym->name;
if (context)
gfc_error ("Dummy argument %qs with INTENT(IN) in variable"
" definition context (%s) at %L",
if (sym->attr.is_protected
&& (sym->attr.use_assoc
|| (sym->attr.used_in_submodule && !sym_is_from_ancestor (sym)))
- && check_intentin)
+ && !own_scope
+ && (check_intentin || !pointer))
{
if (pointer && is_pointer)
{
}
}
/* Check variable definition context for associate-names. */
- if (!pointer && sym->assoc && !sym->attr.select_rank_temporary)
+ if ((!pointer || check_intentin)
+ && sym->assoc && !sym->attr.select_rank_temporary)
{
const char* name;
gfc_association_list* assoc;
}
}
- /* Target must be allowed to appear in a variable definition context. */
- if (!gfc_check_vardef_context (assoc->target, pointer, false, false, NULL))
+ /* Target must be allowed to appear in a variable definition context.
+ Check valid assignment to pointers and invalid reassociations. */
+ if (!gfc_check_vardef_context (assoc->target, pointer, false, false, NULL)
+ && (!ptr_component || pointer))
{
if (context)
gfc_error ("Associate-name %qs cannot appear in a variable"
--- /dev/null
+! { dg-do compile }
+! PR fortran/71565 - INTENT(IN) polymorphic argument with pointer components
+!
+! Contributed by Marco Restelli.
+
+module m
+ implicit none
+
+ type, abstract :: t_a
+ end type t_a
+
+ type, extends(t_a), abstract :: t_b
+ integer, pointer :: i => null()
+ end type t_b
+
+contains
+
+ subroutine s1(var)
+ class(t_a), intent(in) :: var
+ select type(var)
+ class is(t_b)
+ var%i = 3
+ var%i => NULL() ! { dg-error "pointer association context" }
+ end select
+ end subroutine s1
+
+ subroutine s1a(var)
+ class(t_a), intent(in) :: var
+ select type(tmp => var) ! { dg-error "variable definition context" }
+ class is(t_b)
+ tmp%i = 3
+ tmp%i => NULL() ! { dg-error "variable definition context" }
+ end select
+ end subroutine s1a
+
+ subroutine s2(var)
+ class(t_b), intent(in) :: var
+ var%i = 3
+ var%i => NULL() ! { dg-error "pointer association context" }
+ end subroutine s2
+
+ subroutine s2a(var)
+ class(t_b), intent(in) :: var
+ associate (tmp => var) ! { dg-error "variable definition context" }
+ print *, associated (tmp%i)
+ tmp%i = 3
+ tmp%i => NULL() ! { dg-error "variable definition context" }
+ end associate
+ end subroutine s2a
+
+ subroutine s2b(var)
+ class(t_b), intent(in) :: var
+ associate (tmp => var%i)
+ tmp = 3
+ end associate
+ end subroutine s2b
+
+ subroutine s3(var)
+ class(t_a), intent(in) :: var
+ integer, pointer :: tmp
+ select type(var); class is(t_b)
+ tmp => var%i
+ tmp = 3
+ end select
+ end subroutine s3
+
+end module m