Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

Scope question (gfortran odd-man out)

5 views
Skip to first unread message

awgre...@earthlink.net

unread,
Jul 2, 2007, 4:50:25 PM7/2/07
to
Consider the following code fragment:

subroutine main
:
call internal
:
contains
subroutine internal
do i=...
if (...) return
enddo
end subroutine
end

Should the undeclared variable "i" be in the scope of "main", i.e.
should it have the right do loop value in "main" after the call?

Admittedly this is somewhat "sloppy" coding, but all the Fortran-95
compilers I use except Gfortran answer "yes" to the question.
Gfortran requires me to put an "integer i" declaration at the top of
main.

Al Greynolds

Richard Maine

unread,
Jul 2, 2007, 5:07:20 PM7/2/07
to
<awgre...@earthlink.net> wrote:

You didn't show all the code. It matters. A lot. In particular...

If there is literally nothing but the code shown, then i is in the scope
of the internal pricedure, not in the main program. It becomes udefined
on return to the main program.

But... how did you detect this? If you do *ANYTHING*, and I mean that
"anything" at all with an i in the main program, then that changes the
answer. Then the i is in the main program and the internal procedure
gets it by host association. That "anything" includes such things as
printing the value of i to check.

Heissenburg comes to mind.

--
Richard Maine | Good judgement comes from experience;
email: last name at domain . net | experience comes from bad judgement.
domain: summertriangle | -- Mark Twain

Steven G. Kargl

unread,
Jul 2, 2007, 5:15:39 PM7/2/07
to
In article <1183409425....@d30g2000prg.googlegroups.com>,

I think you'll need to show actual code because it works for
me (for some definition of 'works').

troutmask:kargl[233] cat k.f90
program a
call internal
print '(A,I0)', '6 --> ', i
contains
subroutine internal
do i = 1, 5
print '(A4,I0)', 'i = ', i
end do
end subroutine internal
end program a
troutmask:kargl[234] gfc -o z k.f90
troutmask:kargl[235] ./z
i = 1
i = 2
i = 3
i = 4
i = 5
6 --> 6

--
Steve
http://troutmask.apl.washington.edu/~kargl/

awgre...@earthlink.net

unread,
Jul 2, 2007, 5:35:31 PM7/2/07
to
On Jul 2, 2:07 pm, nos...@see.signature (Richard Maine) wrote:
>
> But... how did you detect this? If you do *ANYTHING*, and I mean that
> "anything" at all with an i in the main program, then that changes the
> answer. Then the i is in the main program and the internal procedure
> gets it by host association. That "anything" includes such things as
> printing the value of i to check.
>

You're right, I did forget that "i" was assigned and used for other
purposes in "main" and therefore must be in its scope. I'll have to
do some more investigation with the full (1000 line subroutine) source
to see why inserting the "integer i" declaration makes the gfortran
results agree with everyone else.

Al

awgre...@earthlink.net

unread,
Jul 2, 2007, 5:50:10 PM7/2/07
to
OK, the problem is a bug in gfortran as illustrated by the following
simple but complete code that should obviously print 4 (not 8)

program main
call something
end

subroutine something
i=1; n=7
call internal(5)
write(*,*) i
contains
subroutine internal(j)
intent(in) j
do i=j,n
if (i==4) return
enddo
end subroutine
end


awgre...@earthlink.net

unread,
Jul 2, 2007, 5:55:25 PM7/2/07
to

Nevermind, this has not been a lucid day for me. The above example is
crap! I'll get back to you guys when I have something REAL to report.

glen herrmannsfeldt

unread,
Jul 2, 2007, 7:15:07 PM7/2/07
to
awgre...@earthlink.net wrote:

> OK, the problem is a bug in gfortran as illustrated by the following
> simple but complete code that should obviously print 4 (not 8)

> subroutine something


> i=1; n=7
> call internal(5)
> write(*,*) i
> contains
> subroutine internal(j)
> intent(in) j
> do i=j,n
> if (i==4) return
> enddo
> end subroutine
> end

8 looks right to me. I don't see how it could be 4.

-- glen

awgre...@earthlink.net

unread,
Jul 2, 2007, 6:35:44 PM7/2/07
to
Finally, here's the code that gfortran has problems with:

program main
call something
end

subroutine something
! integer i !correct results from gfortran depend on this statement
character lit*1,line*100
lit(i)=line(i:i)
i=1; n=5; line='PZ0R1'
if (internal(4)) stop
write(*,*) i
contains
logical function internal(j)
intent(in) j
do i=j,n
k=index('RE',lit(i)); if (k==0) cycle
if (i+1==n) exit
enddo
internal=k==0
end function
end

glen herrmannsfeldt

unread,
Jul 2, 2007, 7:57:24 PM7/2/07
to
awgre...@earthlink.net wrote:

> Finally, here's the code that gfortran has problems with:

> program main
> call something
> end

> subroutine something
> ! integer i !correct results from gfortran depend on this statement
> character lit*1,line*100
> lit(i)=line(i:i)
> i=1; n=5; line='PZ0R1'
> if (internal(4)) stop
> write(*,*) i
> contains
> logical function internal(j)
> intent(in) j
> do i=j,n

At this point, j=4, i=4, n=5

> k=index('RE',lit(i)); if (k==0) cycle

now k=1, i=4, n=5, the following exit is done.

> if (i+1==n) exit
> enddo

Now k=1, i=4

> internal=k==0

internal=.FALSE.

> end function
> end

The function returns .FALSE., stop is not executed, and i
(still 4) is printed, with or without the integer i statement.

Looks fine to me.

-- glen

Paul van Delst

unread,
Jul 2, 2007, 7:10:51 PM7/2/07
to

lnx:scratch : gfortran blah.f90
lnx:scratch : a.out
4
lnx:scratch :

what do you see when you run your example? What do you expect to see?

FWIW:

lnx:scratch : g95 blah.f90
lnx:scratch : a.out
4
lnx:scratch : lf95 blah.f90
Encountered 0 errors, 0 warnings in file blah.f90.
lnx:scratch : a.out
4
lnx:scratch : pgf90 blah.f90
lnx:scratch : a.out
4


cheers,

paulv

p.s. I assume the lit(i)=line(i:i) is an oversight since i isn't set yet?

--
Paul van Delst Ride lots.
CIMSS @ NOAA/NCEP/EMC Eddy Merckx

James Giles

unread,
Jul 2, 2007, 7:12:02 PM7/2/07
to
glen herrmannsfeldt wrote:
> awgre...@earthlink.net wrote:
...

> The function returns .FALSE., stop is not executed, and i
> (still 4) is printed, with or without the integer i statement.
>
> Looks fine to me.

That's what I came up with too. But he doesn't say what
*he* expects. Nor does he say what gfortran does with
or without the explicit declaration. I can well believe that
gfortran might have problems. For such a small code
fragment it manages to use a awful lot of less common
features (CYCLE, statement functions, host association
of statement functions, and so on). Especially when
two or more uncommon features interact, compilers
are known to have bugs.

--
J. Giles

"I conclude that there are two ways of constructing a software
design: One way is to make it so simple that there are obviously
no deficiencies and the other way is to make it so complicated
that there are no obvious deficiencies." -- C. A. R. Hoare


awgre...@earthlink.net

unread,
Jul 2, 2007, 7:12:42 PM7/2/07
to
On Jul 2, 4:57 pm, glen herrmannsfeldt <g...@ugcs.caltech.edu> wrote:
>> Looks fine to me.
>
> -- glen- Hide quoted text -
>
> - Show quoted text -

I'm using the June 28 MacOSX Intel binary of gfortran 4.3 and I'm
definitely seeing a difference depending on whether "integer i" is
present. I think I'll shelf this until a newer Window's binary becomes
available.

Al


awgre...@earthlink.net

unread,
Jul 2, 2007, 7:14:23 PM7/2/07
to
On Jul 2, 4:10 pm, Paul van Delst <Paul.vanDe...@noaa.gov> wrote:
> p.s. I assume the lit(i)=line(i:i) is an oversight since i isn't set yet?
>
> --
> Paul van Delst Ride lots.
> CIMSS @ NOAA/NCEP/EMC Eddy Merckx- Hide quoted text -

>
> - Show quoted text -

"lit" is a statement function!

Al

James Giles

unread,
Jul 2, 2007, 7:15:05 PM7/2/07
to
Paul van Delst wrote:
...

> p.s. I assume the lit(i)=line(i:i) is an oversight since i isn't set
> yet?


I kind of like statement functions. But they're getting so rare
that people no longer even recognize them.

Steven G. Kargl

unread,
Jul 2, 2007, 7:18:01 PM7/2/07
to
In article <1183415744.3...@z28g2000prd.googlegroups.com>,

Can you submit a bug report? The code works fine with gfortran
4.2.0 20070214, and fails with 4.3.0 20070630. It looks like a
possible problem with the statement function.

--
Steve
http://troutmask.apl.washington.edu/~kargl/

Paul van Delst

unread,
Jul 2, 2007, 7:21:43 PM7/2/07
to

D'oh. Yeah, I realized that after I posted.

cheers,

paulv

Paul van Delst

unread,
Jul 2, 2007, 7:29:19 PM7/2/07
to
James Giles wrote:
> Paul van Delst wrote:
> ...
>> p.s. I assume the lit(i)=line(i:i) is an oversight since i isn't set
>> yet?
>
>
> I kind of like statement functions. But they're getting so rare
> that people no longer even recognize them.

Yep - count me in that group. I wouldn't even have worried more about it all except for
the explicit output from the Lahey compiler stating that it "Encountered 0 errors, 0
warnings...". That got me thinking since when I compile using that compiler I look for the
"variable <x> used but not set" warning output.

Sigh.

cheers,

paulv

awgre...@earthlink.net

unread,
Jul 2, 2007, 7:32:25 PM7/2/07
to
On Jul 2, 4:18 pm, k...@troutmask.apl.washington.edu (Steven G. Kargl)
wrote:

> Can you submit a bug report? The code works fine with gfortran
> 4.2.0 20070214, and fails with 4.3.0 20070630. It looks like a
> possible problem with the statement function.
>
> --
> Stevehttp://troutmask.apl.washington.edu/~kargl/- Hide quoted text -


Will do.

I'm pretty hard on the latest Fortran compilers (just ask Andy Vaught
or Steve Lionel) because there are old features, e.g. statements
functions, ENTRY, etc., that I (James too) still like. I also tend
tend to mix them freely with newer Fortran features. Until today,
Gfortran could not even completely compile my 3 year old application
without ICEs. At least now its down to getting it to execute properly
like the several other compilers I use.

Al

glen herrmannsfeldt

unread,
Jul 2, 2007, 8:38:36 PM7/2/07
to
James Giles wrote:

> glen herrmannsfeldt wrote:
>>awgre...@earthlink.net wrote:

>>The function returns .FALSE., stop is not executed, and i
>>(still 4) is printed, with or without the integer i statement.

>>Looks fine to me.

> That's what I came up with too. But he doesn't say what
> *he* expects. Nor does he say what gfortran does with
> or without the explicit declaration.

As I didn't note it before, I have the x86-64 version 4.2.0

> I can well believe that
> gfortran might have problems. For such a small code
> fragment it manages to use a awful lot of less common
> features (CYCLE, statement functions, host association
> of statement functions, and so on). Especially when
> two or more uncommon features interact, compilers
> are known to have bugs.

I did wonder about host association of statement functions,
but if that didn't work it would fail pretty hard.

-- glen

Message has been deleted

Wade Ward

unread,
Jul 2, 2007, 7:36:30 PM7/2/07
to

"James Giles" <james...@worldnet.att.net> wrote in message
news:ZFfii.140021$Sa4....@bgtnsc05-news.ops.worldnet.att.net...

> Paul van Delst wrote:
> ...
>> p.s. I assume the lit(i)=line(i:i) is an oversight since i isn't set
>> yet?
>
>
> I kind of like statement functions. But they're getting so rare
> that people no longer even recognize them.
And what could be wrong with a function looking like just another executable
statement? A statement function guarantees a pratfall for someone new to
the language.
--
WW


glen herrmannsfeldt

unread,
Jul 2, 2007, 8:45:58 PM7/2/07
to
James Giles wrote:

> Paul van Delst wrote:

>>p.s. I assume the lit(i)=line(i:i) is an oversight since i isn't set
>>yet?

> I kind of like statement functions. But they're getting so rare
> that people no longer even recognize them.

Someone posted a program with one a few days ago, or it might
have taken me longer to recognize it.

I got used to them many years ago when I was translating
BASIC programs to Fortran. The only user defined functions
in BASIC are like statement functions.

My favorite statement function story was many years ago about
a benchmark program that did a lot of complicated math using
statement functions and then printed the result. Compiled with
the IBM Fortran H compiler, which expands statement functions
inline and evaluates constant expressions, it compiled very
slow and ran very fast. The whole calculation was done at
compile time!

-- glen

James Giles

unread,
Jul 2, 2007, 8:30:04 PM7/2/07
to

I didn't say I was *overjoyed* with the feature. I just kind of
like it. Yes it's true that there are problems with the current
form of the feature. And because of backward compatibility
constraints you can't even fix those problems. But, the
feature has advantages too. Sure, the declaration should
probably look something like:

Statement_function :: square(x) = x * x

It should not be required (or even possible) to declare
the result type. The function should be inherently generic.

The scope of the dummy argument(s) should be the statement
function only. That is, in the above, the dummy argument X
is just that: a dummy argument. The declaration of X in the
host scope (or lack thereof) should mean nothing to the
use of X here.

All other entities referenced in the function should be host
associated. Finally something Fortran's version of the feature
actually does.

Those (and a few others) are properties statement functions
should have. They already have some of the desired properties.
The use of, say, internal procedures instead is awfully verbose
if all you want is a parameterized abstraction for an expression.
Macros (which some people might regard as similar) don't
do the job at all well (mainly because macro arguments are
"name associated").

So, I kind of like even Fortran's version of the feature. It's
not at all uniformly dismal.

John Harper

unread,
Jul 3, 2007, 6:00:56 PM7/3/07
to
In article <G6adnSvheo6mERTb...@comcast.com>,

I find them convenient sometimes but I always put ! stmt function
at the end of the line defining one, or ! statement functions
on a line by itself before several, to reduce the chance of misleading
human readers including myself.

-- John Harper, School of Mathematics, Statistics and Computer Science,
Victoria University, PO Box 600, Wellington 6140, New Zealand
e-mail john....@vuw.ac.nz phone (+64)(4)463 5341 fax (+64)(4)463 5045

John Harper

unread,
Jul 3, 2007, 6:13:43 PM7/3/07
to
In article <gMgii.264764$p47....@bgtnsc04-news.ops.worldnet.att.net>,

James Giles <james...@worldnet.att.net> wrote:
>
> Sure, the declaration should probably look something like:
>
> Statement_function :: square(x) = x * x
>
>It should not be required (or even possible) to declare
>the result type. The function should be inherently generic.
>
>The scope of the dummy argument(s) should be the statement
>function only. That is, in the above, the dummy argument X
>is just that: a dummy argument. The declaration of X in the
>host scope (or lack thereof) should mean nothing to the
>use of X here.

So how would I tell the compiler that either the result or an
argument was of type character (and of what length), or logical,
or complex, and how would IMPLICIT NONE work?

James Giles

unread,
Jul 3, 2007, 9:11:16 PM7/3/07
to
John Harper wrote:
> In article
> <gMgii.264764$p47....@bgtnsc04-news.ops.worldnet.att.net>, James
> Giles <james...@worldnet.att.net> wrote:
>>
>> Sure, the declaration should probably look something like:
>>
>> Statement_function :: square(x) = x * x
>>
>> It should not be required (or even possible) to declare
>> the result type. The function should be inherently generic.
>>
>> The scope of the dummy argument(s) should be the statement
>> function only. That is, in the above, the dummy argument X
>> is just that: a dummy argument. The declaration of X in the
>> host scope (or lack thereof) should mean nothing to the
>> use of X here.
>
> So how would I tell the compiler that either the result or an
> argument was of type character (and of what length), or logical,
> or complex, and how would IMPLICIT NONE work?

How do you presently tell the compiler that J*J has the same
type as J? Or that P.le.Q has type logical? You don't. They
are defined that way from the language's definition. Given
the above, the type of SQUARE(T) is whatever the type of
T*T would be. If T has an intrinsic numeric type, the result
is the same type as T. If T has some derived type on which
you have overloaded the "*" operator, the result has whatever
type that operator returns. That's what a generic function
does.

John Harper

unread,
Jul 3, 2007, 11:19:03 PM7/3/07
to
In article <UsCii.143164$Sa4....@bgtnsc05-news.ops.worldnet.att.net>,

James Giles <james...@worldnet.att.net> wrote:
>John Harper wrote:
>> In article
>> <gMgii.264764$p47....@bgtnsc04-news.ops.worldnet.att.net>, James
>> Giles <james...@worldnet.att.net> wrote:
>>>
>>> Sure, the declaration should probably look something like:
>>>
>>> Statement_function :: square(x) = x * x
>>>
>>> It should not be required (or even possible) to declare
>>> the result type. The function should be inherently generic.
>>>
>>> The scope of the dummy argument(s) should be the statement
>>> function only. That is, in the above, the dummy argument X
>>> is just that: a dummy argument. The declaration of X in the
>>> host scope (or lack thereof) should mean nothing to the
>>> use of X here.
>>
>> So how would I tell the compiler that either the result or an
>> argument was of type character (and of what length), or logical,
>> or complex, and how would IMPLICIT NONE work?
>
> If T has an intrinsic numeric type, the result
>is the same type as T.

So if your proposal were to be implemented, then would sqmod given by
Statement_function :: sqmod(z) = abs(z)**2
return a complex value if z was complex? Surely it ought to be real
and of the same kind as z if z is complex or real, and integer if z is.

I presume transformational intrinsics would remain forbidden in
statement functions (f95 or f2003 12.5.4 first constraint) for if

Statement_function :: trimconcat(a,b) = trim(trim(a)//b)

were allowed, the length would depend on the actual arguments.

James Giles

unread,
Jul 4, 2007, 12:06:48 AM7/4/07
to
John Harper wrote:
> In article
...

>> If T has an intrinsic numeric type, the result
>> is the same type as T.
>
> So if your proposal were to be implemented, then would sqmod given by
> Statement_function :: sqmod(z) = abs(z)**2
> return a complex value if z was complex? Surely it ought to be real
> and of the same kind as z if z is complex or real, and integer if z
> is.

The result type is that which would be expected by applying
the expression defining the statement to the actual argument.
If Z is complex, isn't ABS(Z) REAL? So, isn't that pretty
obviously what would be expected?

This is much why I explicitly mentioned the case of a derived
type argument last time. Given:

Statement_function :: square(x) = x*x

If called as SQUARE(T) the result is whatever the "*" operator
returns when applied to arguments of the type of T.

> I presume transformational intrinsics would remain forbidden in
> statement functions (f95 or f2003 12.5.4 first constraint) for if
>
> Statement_function :: trimconcat(a,b) = trim(trim(a)//b)
>
> were allowed, the length would depend on the actual arguments.

Looks alright to me. The feature is a named, parameterized abstraction
for an expression. The result type, type attributes, and other properties
are whatever that expression would produce if applied to the actual
argument(s). If you wrote:

result = trim(trim(a)//b)

Why would you even remotely suspect the answer to be different
than:

result = trimconcat(a,b)

Why would you *want* the answer to be different than that?

You seem to want some fixed data type, type parameters, and other
attributes to be inherent properties of the function. But that's not the
case with expressions. So why would it be expected to be the case
for named abstractions of expressions? The expression (T*T) doesn't
have some predefined type independent of the type of T. Nor is it
*necessarily* the same as the type of T. It is for intrinsic numeric
types (as I mentioned previously). But not necessarily for all types.

glen herrmannsfeldt

unread,
Jul 4, 2007, 3:01:41 AM7/4/07
to
James Giles wrote:
(snip, someone wrote)

>>So if your proposal were to be implemented, then would sqmod given by
>> Statement_function :: sqmod(z) = abs(z)**2
>>return a complex value if z was complex? Surely it ought to be real
>>and of the same kind as z if z is complex or real, and integer if z
>>is.

> The result type is that which would be expected by applying
> the expression defining the statement to the actual argument.
> If Z is complex, isn't ABS(Z) REAL? So, isn't that pretty
> obviously what would be expected?

It could be more like C's #define where

#define sq(x) ((x)*(x))

will square any quantity, independent of type.

Then again, if the compiler will run cpp, then you can always
use #define instead of statement functions.

-- glen

James Giles

unread,
Jul 4, 2007, 2:23:54 AM7/4/07
to
glen herrmannsfeldt wrote:
> James Giles wrote:
...

>> The result type is that which would be expected by applying
>> the expression defining the statement to the actual argument.
>> If Z is complex, isn't ABS(Z) REAL? So, isn't that pretty
>> obviously what would be expected?
>
> It could be more like C's #define where
>
> #define sq(x) ((x)*(x))
>
> will square any quantity, independent of type.
>
> Then again, if the compiler will run cpp, then you can always
> use #define instead of statement functions.

As I've already pointed out, macros work not at all well for
this purpose. Consider your version of sq(x) and the following:

answer = sq(f(t))

Using the macro this turns out to be:

answer = ((f(t))*(f(t)))

If the function F has side effects then this most likely violates
the Fortran standard. The evaluation of an entity in a statement
is not allowed to alter the interpretation of any other entity
in the same statement (with some caveates about staements
that have separate control expressions). That hardly works
like functions ought. Just the excessive parenthesis required
are an error prone, easily forgot precaution. As I said, these
problem are mostly due to the fact that macro arguments are
sort of like "name associated" arguments. Genuine function
call semantics are a better choice.

glen herrmannsfeldt

unread,
Jul 4, 2007, 4:38:06 AM7/4/07
to
James Giles wrote:

(I wrote)

>>#define sq(x) ((x)*(x))
(snip)

> As I've already pointed out, macros work not at all well for
> this purpose. Consider your version of sq(x) and the following:

> answer = sq(f(t))

> Using the macro this turns out to be:

> answer = ((f(t))*(f(t)))

> If the function F has side effects then this most likely violates
> the Fortran standard.

It violates the standard if you try to use it as an implementation
of statement functions. If it is done explicitly, that is, instead
of statement functions, then the user is expected to worry about
side effects.

> The evaluation of an entity in a statement
> is not allowed to alter the interpretation of any other entity
> in the same statement (with some caveates about staements
> that have separate control expressions). That hardly works
> like functions ought. Just the excessive parenthesis required
> are an error prone, easily forgot precaution. As I said, these
> problem are mostly due to the fact that macro arguments are
> sort of like "name associated" arguments. Genuine function
> call semantics are a better choice.

Some things work better with one, some with the other.

If you do something like:

#define WRITE(x,y) if(debug.or.x.eq.6) WRITE(x,y)

there is no equivalent in terms of functions. There are
even stories of C programs with

#define BEGIN {
#define END }

-- glen

James Giles

unread,
Jul 4, 2007, 4:06:59 AM7/4/07
to
glen herrmannsfeldt wrote:
...

> It violates the standard if you try to use it as an implementation
> of statement functions. [...

But statement functions were what you were recommending
that macros replace.

> ...] If it is done explicitly, that is, instead


> of statement functions, then the user is expected to worry about
> side effects.

And so, constitutes bad language design.

> Some things work better with one, some with the other.
>
> If you do something like:
>
> #define WRITE(x,y) if(debug.or.x.eq.6) WRITE(x,y)
>
> there is no equivalent in terms of functions. There are
> even stories of C programs with
>
> #define BEGIN {
> #define END }

Yes macros have their uses. A substitute for statement functions
should *never* be one of them.

John Harper

unread,
Jul 4, 2007, 5:59:36 PM7/4/07
to
In article <s1Fii.143518$Sa4....@bgtnsc05-news.ops.worldnet.att.net>,

James Giles <james...@worldnet.att.net> wrote:
>John Harper wrote:
>> I presume transformational intrinsics would remain forbidden in
>> statement functions (f95 or f2003 12.5.4 first constraint) for if
>>
>> Statement_function :: trimconcat(a,b) = trim(trim(a)//b)
>>
>> were allowed, the length would depend on the actual arguments.
>
>Looks alright to me. The feature is a named, parameterized abstraction
>for an expression. The result type, type attributes, and other properties
>are whatever that expression would produce if applied to the actual
>argument(s). If you wrote:
>
> result = trim(trim(a)//b)
>
>Why would you even remotely suspect the answer to be different
>than:
>
> result = trimconcat(a,b)

Ah. I had misunderstood your intentions - sorry. My remote suspicion
arose because in ordinary f95 one must declare the length of a statement
function result in advance, so

print *,'"'//trim(trim(a)//b)//'"'

could give different output from

print *,'"'//trimconcat(a,b)//'"'

But of course trim isn't allowed in a statement function in f95
though it is allowed in an internal function. I tried this test
program getting as near as I could to the above, using both a
statement function and an internal function:

PROGRAM teststmtfunclen

CHARACTER(8):: foo = 'foo', bar = 'bar', trimconcat1, a, b
trimconcat1(a,b) = a(1:len_trim(a))//b ! stmt function
print *, '"'//trim(trim(foo)//bar)//'"'
print *, '"'//trimconcat1(foo,bar)//'"'
print *, '"'//trimconcat2(foo,bar)//'"'

CONTAINS

FUNCTION trimconcat2( a,b)
CHARACTER(*),INTENT(IN)::a,b
CHARACTER(len_trim(trim(a)//b)) trimconcat2
trimconcat2 = trim(trim(a)//b)
END FUNCTION trimconcat2

END PROGRAM teststmtfunclen

Of 5 compilers, one crashed at compile time (I'll send a bug report
because that shouldn't happen even with a non-standard program),
three printed

"foobar"
"foobar "
"foobar"

and one printed

"foobar"
"foobar "
"foobar"

That makes me ask: is my program standard-conforming?

James Giles

unread,
Jul 4, 2007, 6:27:45 PM7/4/07
to
John Harper wrote:
...

> But of course trim isn't allowed in a statement function in f95
> though it is allowed in an internal function. I tried this test
> program getting as near as I could to the above, using both a
> statement function and an internal function:
>
> PROGRAM teststmtfunclen
>
> CHARACTER(8):: foo = 'foo', bar = 'bar', trimconcat1, a, b
> trimconcat1(a,b) = a(1:len_trim(a))//b ! stmt function
> print *, '"'//trim(trim(foo)//bar)//'"'
> print *, '"'//trimconcat1(foo,bar)//'"'
> print *, '"'//trimconcat2(foo,bar)//'"'
>
> CONTAINS
>
> FUNCTION trimconcat2( a,b)
> CHARACTER(*),INTENT(IN)::a,b
> CHARACTER(len_trim(trim(a)//b)) trimconcat2
> trimconcat2 = trim(trim(a)//b)
> END FUNCTION trimconcat2
>
> END PROGRAM teststmtfunclen


This looks legal to me on superficial examination. Fortran does
sometimes have rules against things that don't make much sense
(well, like not allowing TRIM in a statement function), so you
might be in violation of some arcane requirment that I don't
know or remember. :-(

> Of 5 compilers, one crashed at compile time (I'll send a bug report
> because that shouldn't happen even with a non-standard program),
> three printed
>
> "foobar"
> "foobar "
> "foobar"
>
> and one printed
>
> "foobar"
> "foobar "
> "foobar"

Since the declared length of the statement function is 8
returning 11 characters doesn't seem right. Of course,
11 is the length of the variable BAR plus the length of
the trimmed part of the variable FOO, so my guess is
that the compiler is making some mistake along those
lines.

paul.rich...@gmail.com

unread,
Jul 5, 2007, 3:03:54 AM7/5/07
to
On Jul 3, 12:35 am, awgreyno...@earthlink.net wrote:
> Finally, here's the code that gfortran has problems with:

This is now fixed on 4.3.0. Thanks for the report and for the
Bugzilla entry (pr32613).

We really appreciate the time that people take to file problem
reports. Depending on volunteer effort as we do, we might not be the
quickest but once in Bugzilla they, dare I say it, bug us until they
are done. Being a regression for which I was responsible, I responded
asap.

Thanks

Paul

Wade Ward

unread,
Jul 5, 2007, 4:40:33 PM7/5/07
to

"Steven G. Kargl" <ka...@troutmask.apl.washington.edu> wrote in message
news:f6c139$po7$1...@gnus01.u.washington.edu...
Could you post the bug report or if this is it, explain what those largeish
numbers are after the 4.x.0 ?
--
Wade Ward


Steven G. Kargl

unread,
Jul 5, 2007, 4:57:55 PM7/5/07
to
In article <wLWdnfX2ZqsfyhDb...@comcast.com>,

"Wade Ward" <inv...@invalid.nyet> writes:
>
> "Steven G. Kargl" <ka...@troutmask.apl.washington.edu> wrote in message
> news:f6c139$po7$1...@gnus01.u.washington.edu...
>>
>> Can you submit a bug report? The code works fine with gfortran
>> 4.2.0 20070214, and fails with 4.3.0 20070630. It looks like a
>> possible problem with the statement function.
> Could you post the bug report or if this is it, explain what those largeish
> numbers are after the 4.x.0 ?

gfortran 4.2.0 compiled from source dated 20070214 (aka Feb 14 2007).
gfortran 4.3.0 compiled from source dated 20070630 (aka Jun 30 2007).

The problem was fixed yesterday by Paul Thomas

2007-07-05 Paul Thomas <pa...@gcc.gnu.org>

PR fortran/32613
* match.c (gfc_match_do): Reset the implied_index attribute.

You can read the audit trail at

http://gcc.gnu.org/bugzilla/show_bug.cgi?id=32613

--
Steve
http://troutmask.apl.washington.edu/~kargl/

dpb

unread,
Jul 5, 2007, 4:57:05 PM7/5/07
to
Wade Ward wrote:
> "Steven G. Kargl" <ka...@troutmask.apl.washington.edu> wrote in message
> news:f6c139$po7$1...@gnus01.u.washington.edu...
...

>> Can you submit a bug report? The code works fine with gfortran
>> 4.2.0 20070214, and fails with 4.3.0 20070630. It looks like a
>> possible problem with the statement function.
> Could you post the bug report or if this is it, explain what those largeish
> numbers are after the 4.x.0 ?

Certainly look like a build date yyyymmdd to me...

--

Wade Ward

unread,
Jul 5, 2007, 5:13:12 PM7/5/07
to

"dpb" <no...@non.net> wrote in message news:f6jm21$8gc$4...@aioe.org...
If I were any blinder I'd need a different tip on my cane:-)
--


paul.rich...@gmail.com

unread,
Jul 6, 2007, 7:28:18 AM7/6/07
to
Dear All,

Just for the record, I committed the patch for Al's problem to the
development branch. Overnight binaries of gcc-4.3.0 are fixed.

Paul

David Thompson

unread,
Jul 22, 2007, 3:43:08 PM7/22/07
to
On Mon, 02 Jul 2007 16:45:58 -0800, glen herrmannsfeldt
<g...@ugcs.caltech.edu> wrote:

> James Giles wrote:
<snip>


> > I kind of like statement functions. But they're getting so rare
> > that people no longer even recognize them.

<snip>


> I got used to them many years ago when I was translating
> BASIC programs to Fortran. The only user defined functions
> in BASIC are like statement functions.

Although BASIC uses the keyword 'DEF' making them easier to recognize.
- formerly david.thompson1 || achar(64) || worldnet.att.net

0 new messages