Discussion:
Need help with inline version of findloc
Thomas Koenig
2018-10-21 10:42:01 UTC
Permalink
Hello world,

I have been busy in the last weeks implementing FINDLOC. It is almost
feature-complete; still missing is the library version for a character
version (that is easy, if a bit of work), handling scalar masks in
the inlined version (also easy, just look at other intrinsics for that),
but I have hit one snag.

The problem can be seen with the following test case.

program main
integer, dimension(0:5) :: a = [1,2,3,1,2,3]
logical, dimension(6) :: mask =
[.false.,.false.,.false.,.true.,.true.,.true.]
logical :: back

back = .false.
if (findloc(a,2,dim=1,mask=mask,back=back) /= 5) stop 1
if (findloc(a,2,dim=1,mask=mask,back=back) /= 5) stop 1
end program main


If I run this through the compiler, I hit a gimplification error.
This can be understood from the beginning of the tree dump:

MAIN__ ()
{
integer(kind=8) pos.4;
integer(kind=8) offset.5;
static integer(kind=4) a[6] = {1, 2, 3, 1, 2, 3};
logical(kind=4) back;
static logical(kind=4) mask[6] = {0, 0, 0, 1, 1, 1};

{
integer(kind=8) S.6;

back = 0;
{
integer(kind=8) S.3;

pos.0 = 0;

The declaration for pos.0 is missing, and I have no idea why.

Can anybody shed any light on this? I think this has
something to do with me generating two loops for the
single findloc statement (one for BACK=.false., one
for BACK=.true.). Also, this only occurs if BACK
is a variable.

Any ideas?

Regards

Thomas
Thomas Koenig
2018-10-21 13:43:12 UTC
Permalink
Hello world,
Post by Thomas Koenig
Can anybody shed any light on this?
Never mind, I found the problem -

+ gfc_start_block (&block);
+ }
+
+ /* If the condition matches then set the return value. */
+ gfc_start_block (&block);
+

is a bad idea :-)
Paul Richard Thomas
2018-10-21 14:42:34 UTC
Permalink
Hi Thomas,

I could see that there was a scope problem and had started working
backwards from the end of the function. You beat me to it by a matter
of minutes.

Adding the extra scope for 'block' twice is indeed a poor idea!

For reasons that are not evident to me, the other similar functions do this:
gfc_start_block (&block);
}
else
gfc_init_block (&block);
instead of a single gfc_start_block (&block) or, even, gfc_init_block (&block);.

I tried both and it doesn't matter as long as the declarations all
make their way to the parent scope.

I can see why you have been so quiet for the last week. Great work!

Cheers

Paul
Post by Thomas Koenig
Hello world,
Post by Thomas Koenig
Can anybody shed any light on this?
Never mind, I found the problem -
+ gfc_start_block (&block);
+ }
+
+ /* If the condition matches then set the return value. */
+ gfc_start_block (&block);
+
is a bad idea :-)
--
"If you can't explain it simply, you don't understand it well enough"
- Albert Einstein
Loading...