Re: [PATCH] Fortran: fix issue with impure elemental subroutine and interface [PR119656]

2025-04-09 Thread Harald Anlauf

Am 09.04.25 um 04:06 schrieb Jerry D:

On 4/8/25 1:43 PM, Harald Anlauf wrote:

Hi all,

the attached patch fixes a rather strange 12/13/14/15 regression.
When walking through the list of procedures in an interface to
find the matching one, the code could remember an inferred type
from a false module procedure within the same interface if and
only if optional arguments were in the procedure declarations,
and the procedure call did not provide an actual argument for
an optional one.  An inferred type could then leak into
gfc_conv_procedure_call and pretend a wrong type for the dummy.

(This bug appears to be related to a code refactoring during
12-development and is not present in 11-releases.)

The simple and obvious solution is to use the type of the formal,
as inferred types are only relevant when there is no explicit
interface.

Regtested on x86_64-pc-linux-gnu.  OK for mainline?

As this is a regression, I would like to backport this as
appropriate.

Thanks,
Harald



This looks OK Harold, thanks!


Thanks for the review!

Pushed as r15-9340-g334545194d9023.


Jerry


Harald



Re: Is ASSOCIATE implemented correctly in gfortran?

2025-04-09 Thread Mikael Morin

Hello,

Le 08/04/2025 à 15:29, Andre Vehreschild a écrit :

Hi all,

while working at teams stuff I encountered some issue with the ASSOCIATE
statement:

1. First of all: It does not open its namespace as it is expected to. I.e. the
associate-name (referring to the term as used in F2018 11.1.3.1 R1104) is put
into the parent namespace/scope and not into its own (overwriting values
possibly).

Yes, there are bugs unfortunately.  I thought ASSOCIATE were creating 
BLOCK constructs under the hood, but I may well be wrong.



2. Doing

associate(me => this_image(), num => num_images(), foo = MOD(me + 43, num))

produces a very unexpected value of foo. If it is computed at all! I got a
SigFPE for a long time, before I figured that the me and num in the expression
of foo are not the ones from the associate, but are not initialized variable of
the parent scope. I therefore worked to resolve this and found one test
(associate_1.f03), that check exactly this (IMO wrong) behavior. Testing with
Intel's latest Fortran compiler, the test fails, too. Intel also allows using
former associate-names in the later expr.


Not sure I understand; the test associate_1.f03 has:

  a = -2.0
  b = 3.0
...
  ASSOCIATE (a => 1 * b, b => 1 * a, x => 1, y => 2)
IF (ABS (a - 3.0) > 1.0e-3 .OR. ABS (b + 2.0) > 1.0e-3) STOP 9

So A has the value of B from the parent scope, and B has the value of A 
from the parent scope.  Are you saying this is wrong?



Therefore my question: Why is this implemented that way? When I read F2018
19.6.7 correctly, then it only means that recursive references are not allowed,
i.e. associate( v => f(v) ) or the like. But referencing an associate-name in a
latter expr is fine, because that is not recursive.

Any comments, insight or pointers to why a "defined" associate-name must not
occur in an associate expr, but may occur in an associate immediately
following, are very much appreciated!

I think that behaviour is correct.  While the cross-references don't 
seem to be explicitly prohibited, the ASSOCIATE construct execution is 
defined as follows (f2023, 11.1.3.2):



Execution of an ASSOCIATE construct causes evaluation of every expression 
within every selector that is a
variable designator and evaluation of every other selector, followed by 
execution of its block. During execution of
that block each associate name identifies an entity which is associated 
(19.5.1.6) with the corresponding selector.


This doesn't specify any evaluation order of selectors, and tells that 
the names are associated with the selectors during the execution of the 
block, but doesn't say anything about the names during the evaluation of 
selectors.  My conclusion is that the names are not defined/associated 
during the evaluation of selectors.


Hope it helps...
Mikael



Re: Is ASSOCIATE implemented correctly in gfortran?

2025-04-09 Thread Paul Richard Thomas
Hi Andre and Mikael,

The associate block is added *after* the associate statement is matched and
the associate_names added to the parent namespace; see
parse.cc(parse_associate).

nagfor and flang-new both behave in the same way as gfortran. So ifort and
ifx are the odd ones out.

In F2018 and F2013, the scope of the selector is clear enough:
19.4 Statement and construct entities
...
9 The associate names of an ASSOCIATE construct have the scope of the
block. ..

Then,
19.5.1.6 Construct association
...
3 If the selector is a variable other than an array section having a vector
subscript, the association is with the data object specified by the
selector; otherwise, the association is with the value of the selector
expression, *which is evaluated prior to execution of the block.*

Given this and Mikael's observation, "that the names are not
defined/associated during the evaluation of selectors", I conclude that
gfortran has the correct behaviour.

As I understand it, the associate construct was intended to provide a
convenient way of representing arbitrary expressions from the parent scope
and so I wouldn't describe the behaviour as odd. It is what it is :-)

Best regards

Paul


Re: Is ASSOCIATE implemented correctly in gfortran?

2025-04-09 Thread Andre Vehreschild
Hi Mikael,

thanks for your input. Meanwhile I checked the compiler explorer
https://godbolt.org/z/Ehbjefzab and got an in-decided picture of what could be
the way to go. First of all, most of the compilers in compiler explorer are
gfortran for different architectures. So I ignored them. 

I used this small test program:

integer :: me = 1, num = 1, n_ind = -1

associate(me => 2, num => 4, n_ind => mod(me + 13, num))
print *, me, num, n_ind
end associate
print *, me, num, n_ind
end

ifort 2021.11.0 emits:
   2   4   3
   1   1  -1

which is intuitive to me. I.e. as soon as an associate-name shadows a variable
from the parent scope the associate-name is referenced.

ifx (latest) gets to the same result.

LFortran 0.42.0 (never heard of it) computes:
240
11-1

So here `me` and `num` are taken from the parent scope.

flang-trunk does the same.
nvfortran 25.1 also. 

Those are all the different available compilers. So we have Intel which goes
for the early shadowing and three other compilers that evaluate the selector in
the parent scope. The latter seems to be the most common interpretation of the
issue.

One caveat is when one changes the example slightly:

integer :: me = 1, num = 1, n_ind = -1

associate(me => 2, num => 4)
associate (n_ind => mod(me + 13, num))
  print *, me, num, n_ind
end associate
end associate
print *, me, num, n_ind
end

Why should splitting the association-list into two associates be necessary? To
me this is not intuitive. But given that the others do the same, I will change
my patch to mimic that odd behavior.

Thanks for your time and regards,
Andre


On Wed, 9 Apr 2025 09:37:14 +0200
Mikael Morin  wrote:

> Hello,
> 
> Le 08/04/2025 à 15:29, Andre Vehreschild a écrit :
> > Hi all,
> > 
> > while working at teams stuff I encountered some issue with the ASSOCIATE
> > statement:
> > 
> > 1. First of all: It does not open its namespace as it is expected to. I.e.
> > the associate-name (referring to the term as used in F2018 11.1.3.1 R1104)
> > is put into the parent namespace/scope and not into its own (overwriting
> > values possibly).
> >   
> Yes, there are bugs unfortunately.  I thought ASSOCIATE were creating 
> BLOCK constructs under the hood, but I may well be wrong.
> 
> > 2. Doing
> > 
> > associate(me => this_image(), num => num_images(), foo = MOD(me + 43, num))
> > 
> > produces a very unexpected value of foo. If it is computed at all! I got a
> > SigFPE for a long time, before I figured that the me and num in the
> > expression of foo are not the ones from the associate, but are not
> > initialized variable of the parent scope. I therefore worked to resolve
> > this and found one test (associate_1.f03), that check exactly this (IMO
> > wrong) behavior. Testing with Intel's latest Fortran compiler, the test
> > fails, too. Intel also allows using former associate-names in the later
> > expr. 
> Not sure I understand; the test associate_1.f03 has:
> 
>a = -2.0
>b = 3.0
> ...
>ASSOCIATE (a => 1 * b, b => 1 * a, x => 1, y => 2)
>  IF (ABS (a - 3.0) > 1.0e-3 .OR. ABS (b + 2.0) > 1.0e-3) STOP 9
> 
> So A has the value of B from the parent scope, and B has the value of A 
> from the parent scope.  Are you saying this is wrong?
> 
> > Therefore my question: Why is this implemented that way? When I read F2018
> > 19.6.7 correctly, then it only means that recursive references are not
> > allowed, i.e. associate( v => f(v) ) or the like. But referencing an
> > associate-name in a latter expr is fine, because that is not recursive.
> > 
> > Any comments, insight or pointers to why a "defined" associate-name must not
> > occur in an associate expr, but may occur in an associate immediately
> > following, are very much appreciated!
> >   
> I think that behaviour is correct.  While the cross-references don't 
> seem to be explicitly prohibited, the ASSOCIATE construct execution is 
> defined as follows (f2023, 11.1.3.2):
> 
> > Execution of an ASSOCIATE construct causes evaluation of every expression
> > within every selector that is a variable designator and evaluation of every
> > other selector, followed by execution of its block. During execution of
> > that block each associate name identifies an entity which is associated
> > (19.5.1.6) with the corresponding selector.  
> 
> This doesn't specify any evaluation order of selectors, and tells that 
> the names are associated with the selectors during the execution of the 
> block, but doesn't say anything about the names during the evaluation of 
> selectors.  My conclusion is that the names are not defined/associated 
> during the evaluation of selectors.
> 
> Hope it helps...
> Mikael
> 


-- 
Andre Vehreschild * Email: vehre ad gmx dot de