In debugging a fortran problem compiled with gfortran 4.3.0 in mingw,
I foucsed on the following code
------------------------------------------------------------------------
IF( LTYPE==5 ) THEN
.......
COEFX=VAL*PHX
COEFY=VAL*PHY
print *,COEFX,COEFY
END IF
........
------------------------------------------------------------------------
I added a print statement here because the value of COEFX and COEFY
seems not correct. But after doing that, I go a right answer. Then
after I deleted the print statement, I got a wrong answer.
It is strange that a print statement may change the final anwer. Do
you have any idea about this problem?
Your anwer is much appreciated.
That is a typical symptom of something going wrong elsewhere in the
program. For instance: an erroneous array index or an incorrect
argument list.
Print-statements seem to cause a reorganisation of the memory
locations,
so that all of a sudden the program is doing things quite differently
if you have such bugs as described above.
Regards,
Arjen
Thank you for your kindly reply. I checked other part as you
suggested. It DOES have a problem of out of range in array dimension!
Although the problem is solved, I am still quiter nervous about those
problems related to memory management. Do you have any suggestion to
avoid such probelms? In my case, I turned on debug option -g, but it
seems not works. Maybe I should recompile all my program (it is a big
project) turning all debug options on.
Much thanks for your help.
>
> That is a typical symptom of something going wrong elsewhere in the
> program. For instance: an erroneous array index or an incorrect
> argument list.
>
> Print-statements seem to cause a reorganisation of the memory
> locations,
> so that all of a sudden the program is doing things quite differently
> if you have such bugs as described above.
>
> Regards,
>
> Arjen-
When developing, I tend to use as much checks as possible. Enabling all
warnings avoids problems with certain deprecated constructions and I
find myself writing better code taking these suggestions into account.
To avoid out-of-bound indexing, the "-fbounds-check" is the thing you're
looking for. It enables at-runtime checks on the bounds of arrays and
will report if an index isn't within the correct range. Note that this
should not be used in release versions because it affects the runtime.
Best regards
Koen
> hill wrote:
> > Although the problem is solved, I am still quiter nervous about those
> > problems related to memory management. Do you have any suggestion to
> > avoid such problems?
>
> When developing, I tend to use as much checks as possible....
That's one thing (and is a good and common sugggestion).
Another is to develop an awareness of the potential for this kind of
problem and to use that awareness as you code. Every time you write an
array element or slice reference, you should think about whether it is
possible for that reference to be out of bounds. Eventually, that kind
of self-check should become second nature, along with a host of other
checks (such as whether a referenced variable might be undefined).
Yes, thinking about all these things can slow down writing the code. But
they make up for that many times over in lowering the time subsequently
spent in debugging.
--
Richard Maine | Good judgment comes from experience;
email: last name at domain . net | experience comes from bad judgment.
domain: summertriangle | -- Mark Twain
I agree that -fbounds-check should always be used when developing new
code, and like you I *used* to suggest like you that you should turn
this off when the program is tested. Now I'm not so sure. My
experience is that it only makes a program a bit slower, maybe 20 to 30%
slower. Now that computers are so fast, applications where getting the
last bit of speed is important are fairly uncommon.
If you are forecasting tomorrow's weather, and it takes 24 hours with
checks, and 20 hours without, then maybe you have to do without
checking. In most other situations I'd say keep the checking enabled
permanently. Even in programs that have been fairly well tested, some
circumstance might arise, such as an input file or zero length or one
much longer than you anticipated, which causes a "tested" program
suddenly to access an out-of-range array element in some obscure corner
of some routine. I prefer to know about such things by having an error
message come up, rather than risk the program continuing silently and
produce an incorrect result. Your opinions may vary.
--
Clive Page
It depends some on how it is implemented. Consider:
real x(10),y(10)
integer i
(do something with x and y here)
do i=1,10
x(i)=x(i)+y(i)
enddo
In this case, the compiler can determine that i will be
in bounds, assuming that 1 and 10 don't change.
Should bounds checking still check each, just in case the
constants are accidentally modified?
do i=1,j
x(i)=x(i)+y(i)
enddo
In this case, the checks can be done outside the loop.
Again, that assumes certain illegal operations don't
happen that could modify i within the loop.
Also, the compiler better check for:
equivalence (i,x(2))
I don't know how many compilers move bounds checking
outside the loop in cases like this.
-- glen
It's probably a good idea to check for things like this and give a
compile time warning or error message. In this particular case,
j must be less than 2. The loop index is NOT allowed to be
changed during the execution of a loop.
Dick Hendrickson
They're still quite common in certain problem domains. That is,
applications where a 20% to 30% speed hit is totally unacceptable are
still quite common in certain problem domains. I wouldn't kill myself
to improve by 1%, but 20% on a run that would take a week is pretty
substantial.
Leaving switches on that send messages to stdout is not always a good
idea.
I recently had to supply a computational engine in a Fortran .dll to a
company who has a fancy front-end written in C. Unfortunately, the
first time they called my .dll, they made a mistake in the calling
arguments and my program returned an error code and also did a write
(*,*) to inform anyone watching what was wrong. It turns out that C
doesn't like such messages to stdout. In fact, it caused a
catastrophic failure, to the extent that my routine managed to bring
the whole system down. When they told me what happened I laughed, but
they didn't think it was funny.
Whenever inserting or deleting a statement in a program
causes results to change or produce other strange effects
such as a program crash,
you have to suspect an array out-of-bounds condition.
Therefore, turn on all checks.