comp.lang.ada
 help / color / mirror / Atom feed
* GNAT 4.4.5 order of conditional processing?
@ 2011-11-15 20:30 awdorrin
  2011-11-15 20:54 ` Niklas Holsti
  2011-11-15 23:08 ` Jeffrey Carter
  0 siblings, 2 replies; 13+ messages in thread
From: awdorrin @ 2011-11-15 20:30 UTC (permalink / raw)


Given an IF statement such as the following:

if X = Y and not A and B

How does GNAT handle the processing of the conditional statements?
Will "X = Y" be processed first, and if false, will the rest be
skipped?

Reason I'm asking is I'm porting code, and it appears as if all of the
statements are being evaluated, even though the "X = Y" part is
already false.

I'm not sure if there is some optimization going on and if there is,
is there a compiler flag to disable it.

Guessing the best thing to do would be to rewrite the code to
something clearer like:

if X = Y then
  if not A then
   if B then ...

But I was curious since this is something that is probably a hundred
places through out this collection of source code.

Thanks
-Al



^ permalink raw reply	[flat|nested] 13+ messages in thread

* Re: GNAT 4.4.5 order of conditional processing?
  2011-11-15 20:30 GNAT 4.4.5 order of conditional processing? awdorrin
@ 2011-11-15 20:54 ` Niklas Holsti
  2011-11-15 21:07   ` awdorrin
  2011-11-15 23:08 ` Jeffrey Carter
  1 sibling, 1 reply; 13+ messages in thread
From: Niklas Holsti @ 2011-11-15 20:54 UTC (permalink / raw)


On 11-11-15 21:30 , awdorrin wrote:
> Given an IF statement such as the following:
>
> if X = Y and not A and B
>
> How does GNAT handle the processing of the conditional statements?
> Will "X = Y" be processed first, and if false, will the rest be
> skipped?

If you want to be sure that the later conjuncts are evaluated only if 
X=Y, use the "and then" form. The following first evaluates "X = Y", and 
then evaluates "not A and B" only if X = Y:

    if X = Y and then (not A and B) then
       do something
    end if;

Or, expand also the later "and" so that B is evaluated only if X = Y and 
A is false:

    if X = Y and then (not A) and then B then
       do something
    end if;

-- 
Niklas Holsti
Tidorum Ltd
niklas holsti tidorum fi
       .      @       .



^ permalink raw reply	[flat|nested] 13+ messages in thread

* Re: GNAT 4.4.5 order of conditional processing?
  2011-11-15 20:54 ` Niklas Holsti
@ 2011-11-15 21:07   ` awdorrin
  2011-11-15 21:23     ` Vinzent Hoefler
  0 siblings, 1 reply; 13+ messages in thread
From: awdorrin @ 2011-11-15 21:07 UTC (permalink / raw)


Thanks, I wasn't familiar with the 'and then' syntax.

So I am assuming by your response that there are no pragmas or GNAT
compiler flags to enforce the order of evaluation?




^ permalink raw reply	[flat|nested] 13+ messages in thread

* Re: GNAT 4.4.5 order of conditional processing?
  2011-11-15 21:07   ` awdorrin
@ 2011-11-15 21:23     ` Vinzent Hoefler
  2011-11-15 21:49       ` awdorrin
  0 siblings, 1 reply; 13+ messages in thread
From: Vinzent Hoefler @ 2011-11-15 21:23 UTC (permalink / raw)


awdorrin wrote:

> So I am assuming by your response that there are no pragmas or GNAT
> compiler flags to enforce the order of evaluation?

Nope. The compiler plays by the language rules only.


Vinzent.

-- 
f u cn rd ths, u cn gt a gd jb n cmptr prgrmmng.



^ permalink raw reply	[flat|nested] 13+ messages in thread

* Re: GNAT 4.4.5 order of conditional processing?
  2011-11-15 21:23     ` Vinzent Hoefler
@ 2011-11-15 21:49       ` awdorrin
  2011-11-16 21:31         ` Gautier write-only
  0 siblings, 1 reply; 13+ messages in thread
From: awdorrin @ 2011-11-15 21:49 UTC (permalink / raw)


On Nov 15, 4:23 pm, "Vinzent Hoefler"
<0439279208b62c95f1880bf0f8776...@t-domaingrabbing.de> wrote:
> awdorrin wrote:
> > So I am assuming by your response that there are no pragmas or GNAT
> > compiler flags to enforce the order of evaluation?
>
> Nope. The compiler plays by the language rules only.
>

Figured that was is, sloppy programming that just managed to work (for
20 years) due to a compiler implementation... ;-)

>
> --
> f u cn rd ths, u cn gt a gd jb n cmptr prgrmmng.

I love your signature! :-)



^ permalink raw reply	[flat|nested] 13+ messages in thread

* Re: GNAT 4.4.5 order of conditional processing?
  2011-11-15 20:30 GNAT 4.4.5 order of conditional processing? awdorrin
  2011-11-15 20:54 ` Niklas Holsti
@ 2011-11-15 23:08 ` Jeffrey Carter
  2011-11-16  1:18   ` Adam Beneschan
  1 sibling, 1 reply; 13+ messages in thread
From: Jeffrey Carter @ 2011-11-15 23:08 UTC (permalink / raw)


On 11/15/2011 01:30 PM, awdorrin wrote:
> Given an IF statement such as the following:
>
> if X = Y and not A and B
>
> How does GNAT handle the processing of the conditional statements?
> Will "X = Y" be processed first, and if false, will the rest be
> skipped?

The language specifies that all the conditions must be evaluated. A compiler 
that does differently isn't Ada.

To skip later conditions, use the "short-circuit" forms "and then" and "or else":

if P /= null and then P.all = Sentinel then

if P = null or else P.all = Sentinel then

Note that the short circuit forms should not be considered optimizations. With 
modern processors, unnecessary short-circuit forms may sometimes be slower than 
the regular equivalents.

-- 
Jeff Carter
"I feel as though somebody stepped on my tongue
with muddy feet."
Never Give a Sucker an Even Break
112



^ permalink raw reply	[flat|nested] 13+ messages in thread

* Re: GNAT 4.4.5 order of conditional processing?
  2011-11-15 23:08 ` Jeffrey Carter
@ 2011-11-16  1:18   ` Adam Beneschan
  2011-11-16  5:33     ` tmoran
  0 siblings, 1 reply; 13+ messages in thread
From: Adam Beneschan @ 2011-11-16  1:18 UTC (permalink / raw)


On Nov 15, 3:08 pm, Jeffrey Carter
<spam.jrcarter....@spam.not.acm.org> wrote:
>
> Note that the short circuit forms should not be considered optimizations. With
> modern processors, unnecessary short-circuit forms may sometimes be slower than
> the regular equivalents.

Yeah, but the compiler should be able to figure it out and generate
the best code.  No matter what the Ada language says, if you write "A
and then B" and A and B are Boolean variables, it's perfectly legal
for the compiler to generate an instruction that reads the register
that currently contains B.  (I mean a normal register, not a memory-
mapped I/O register.)  The only time it should be necessary to use
"and" instead of "and then" (on Boolean operands) is if the right side
contains a function call (or, perhaps, a read of a variable that's
mapped to some special hardware address) that you absolutely want to
take place regardless of the left side.

                              -- Adam



^ permalink raw reply	[flat|nested] 13+ messages in thread

* Re: GNAT 4.4.5 order of conditional processing?
  2011-11-16  1:18   ` Adam Beneschan
@ 2011-11-16  5:33     ` tmoran
  2011-11-16 17:52       ` awdorrin
  0 siblings, 1 reply; 13+ messages in thread
From: tmoran @ 2011-11-16  5:33 UTC (permalink / raw)


> > Note that the short circuit forms should not be considered optimizations.
> > With modern processors, unnecessary short-circuit forms may sometimes be
> > slower than the regular equivalents.
>
> Yeah, but the compiler should be able to figure it out and generate
> the best code.  No matter what the Ada language says, if you write "A
> and then B" and A and B are Boolean variables, it's perfectly legal
> for the compiler to generate an instruction that reads the register
> that currently contains B.  (I mean a normal register, not a memory-
> mapped I/O register.)  The only time it should be necessary to use
> "and" instead of "and then" (on Boolean operands) is if the right side
> contains a function call (or, perhaps, a read of a variable that's
> mapped to some special hardware address) that you absolutely want to
> take place regardless of the left side.


"Portability and Style in Ada" (1984) says:

Short-circuit control forms should not be used unless logically necessary.
 ...
If used to increase efficiency of execution, there should be a comment
to this effect.  Note that the short-circuit form forces a procedural view
(rather than a functional/static view) of the expression in which it
occurs, which is somewhat undesirable.

while "Ada Quality and Style" (1989) says:
Use short-circuit forms of the logical operators.
 ...
The use of short-circuit control forms prevents a class of data-dependent
errors or exceptions that can occur as a result of expression evaluation.

I would add that "if N > 0 and then Tally > 0 then ..."  may lead the
maintenance programmer to think N is somehow more important or primary
than Tally, which may not be the case.



^ permalink raw reply	[flat|nested] 13+ messages in thread

* Re: GNAT 4.4.5 order of conditional processing?
  2011-11-16  5:33     ` tmoran
@ 2011-11-16 17:52       ` awdorrin
  2011-11-16 20:01         ` Simon Wright
  0 siblings, 1 reply; 13+ messages in thread
From: awdorrin @ 2011-11-16 17:52 UTC (permalink / raw)


In this case, the short-circuit logic is necessary based on how the
code has been structured.

The first conditional, is to see if the simulation is done being
initialized, the second and third conditionals are variables that
won't be initialized with valid values until the initialization is
complete.

Before anyone jumps in to comment on how bad this approach is, I
already know ;) but I'm dealing with porting code originally written
20 years ago. First step is to get it functional, second step is to
fix/update it. :-)

Thanks!



^ permalink raw reply	[flat|nested] 13+ messages in thread

* Re: GNAT 4.4.5 order of conditional processing?
  2011-11-16 17:52       ` awdorrin
@ 2011-11-16 20:01         ` Simon Wright
  0 siblings, 0 replies; 13+ messages in thread
From: Simon Wright @ 2011-11-16 20:01 UTC (permalink / raw)


awdorrin <awdorrin@gmail.com> writes:

> In this case, the short-circuit logic is necessary based on how the
> code has been structured.
>
> The first conditional, is to see if the simulation is done being
> initialized, the second and third conditionals are variables that
> won't be initialized with valid values until the initialization is
> complete.
>
> Before anyone jumps in to comment on how bad this approach is, I
> already know ;) but I'm dealing with porting code originally written
> 20 years ago. First step is to get it functional, second step is to
> fix/update it. :-)

I for one don't think it's bad; it's the way the problem is.



^ permalink raw reply	[flat|nested] 13+ messages in thread

* Re: GNAT 4.4.5 order of conditional processing?
  2011-11-15 21:49       ` awdorrin
@ 2011-11-16 21:31         ` Gautier write-only
  2011-11-16 22:40           ` Adam Beneschan
  0 siblings, 1 reply; 13+ messages in thread
From: Gautier write-only @ 2011-11-16 21:31 UTC (permalink / raw)


On 15 nov, 22:49, awdorrin <awdor...@gmail.com> wrote:

> Figured that was is, sloppy programming that just managed to work (for
> 20 years) due to a compiler implementation... ;-)

Waw, so there was an Ada compiler doing (erroneously of course) a
silent short-circuit ?...
The only system I know doing that is Turbo Pascal (and descendants).
There was even a compiler switch {$B+(/-)} saying "after here, short-
circuit is off(/on)".
A pure mess, as you guess...
______________________________________________________________________________
Gautier's Ada programming -- http://gautiersblog.blogspot.com/search/label/Ada
NB: follow the above link for a valid e-mail address



^ permalink raw reply	[flat|nested] 13+ messages in thread

* Re: GNAT 4.4.5 order of conditional processing?
  2011-11-16 21:31         ` Gautier write-only
@ 2011-11-16 22:40           ` Adam Beneschan
  2011-11-17  0:00             ` Adam Beneschan
  0 siblings, 1 reply; 13+ messages in thread
From: Adam Beneschan @ 2011-11-16 22:40 UTC (permalink / raw)


On Nov 16, 1:31 pm, Gautier write-only <gautier_niou...@hotmail.com>
wrote:
> On 15 nov, 22:49, awdorrin <awdor...@gmail.com> wrote:
>
> > Figured that was is, sloppy programming that just managed to work (for
> > 20 years) due to a compiler implementation... ;-)
>
> Waw, so there was an Ada compiler doing (erroneously of course) a
> silent short-circuit ?...

Not necessarily... Later on, the poster said that the issue was with
uninitialized variables.  In an expression like this:

  if Expression-1 and Expression-2 then...

where Expression-1=FALSE means that some variables in Expression-2 are
uninitialized.  The fact is, though, that even if Expression-2
involves variables that contain unpredictable garbage, using them is
unlikely to cause any harm in most situations.  For instance:

  subtype Index_Subtype is Integer range 1 .. 10;
  Arr : array (Index_Subtype) of Float;
  Curr_Index : Index_Subtype;

  if Curr_Index_Initialized and Arr(Curr_Index) < -1.0 then ...

Suppose Curr_Index_Initialized is FALSE and Curr_Index has never been
initialized to anything.  The result is that if the right side is
evaluated, Curr_Index's uninitialized value may be a value outside the
range 1..10, and then the code will read an element of Arr that is
outside the bounds of Arr.  Big deal.  That's not likely to make a
program fail.  (Unless the bit pattern it reads happens to be a
Signaling NaN, maybe!!)

But I also want to point out that a "silent short-circuit" is NOT
necessarily erroneous.  In fact, it's probably not erroneous in most
cases.  The compiler doesn't have to evaluate both operands of "X and
Y" if X is false and evaluating Y cannot have any effect on anything.
Also, if the only possible effect of evaluating Y is to fail a
language check, then I think Y doesn't have to be evaluated by 11.6.
Thus, if you write:

  if (N in My_Array'Range) and (My_Array(N) = 0) then ...

If N is out of range, the language says this should raise
Constraint_Error when My_Array(N) is evaluated.  So that means that
the above code shouldn't be written like that.  But a compiler that
generates code that doesn't raise Constraint_Error is, I think, legal
by 11.6.  So a compiler that generates the exact same code for the
above example and for

  if (N in My_Array'Range) and then (My_Array(N) = 0) then ...

is OK.  Obviously, programmers shouldn't count on it.  (And there may
be some differences of opinion as to how 11.6 is to be interpreted.
It's caused arguments in the past.)

I believe the only time the compiler *must* generate code that always
evaluates both operands is if the right-hand side contains a function
call that could have a side-effect, or if it refers to an object where
reading the object could have some external effect (i.e. a memory-
mapped device address or the like).

So there's a couple of reasons why (in a correct implementation) using
"and" instead of "and then" could be erroneous but still not cause the
program to fail.

                             -- Adam




^ permalink raw reply	[flat|nested] 13+ messages in thread

* Re: GNAT 4.4.5 order of conditional processing?
  2011-11-16 22:40           ` Adam Beneschan
@ 2011-11-17  0:00             ` Adam Beneschan
  0 siblings, 0 replies; 13+ messages in thread
From: Adam Beneschan @ 2011-11-17  0:00 UTC (permalink / raw)


On Nov 16, 2:40 pm, Adam Beneschan <a...@irvine.com> wrote:
> For instance:
>
>   subtype Index_Subtype is Integer range 1 .. 10;
>   Arr : array (Index_Subtype) of Float;
>   Curr_Index : Index_Subtype;
>
>   if Curr_Index_Initialized and Arr(Curr_Index) < -1.0 then ...
>
> Suppose Curr_Index_Initialized is FALSE and Curr_Index has never been
> initialized to anything.  The result is that if the right side is
> evaluated, Curr_Index's uninitialized value may be a value outside the
> range 1..10, and then the code will read an element of Arr that is
> outside the bounds of Arr.  Big deal.  That's not likely to make a
> program fail.  (Unless the bit pattern it reads happens to be a
> Signaling NaN, maybe!!)

Clarification: Depending on how Curr_Index is represented (some
compilers would fit it into an 8-bit byte while others would make it
as big as an Integer), evaluating Arr(Curr_Index) could make the
program fail if Curr_Index is big enough to put the element's address
out of the program's memory space.  So it's more likely to fail than I
first claimed.  Keep in mind that this is just my example and I don't
know that the OP was doing any array indexing.

                           -- Adam




^ permalink raw reply	[flat|nested] 13+ messages in thread

end of thread, other threads:[~2011-11-17  0:02 UTC | newest]

Thread overview: 13+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2011-11-15 20:30 GNAT 4.4.5 order of conditional processing? awdorrin
2011-11-15 20:54 ` Niklas Holsti
2011-11-15 21:07   ` awdorrin
2011-11-15 21:23     ` Vinzent Hoefler
2011-11-15 21:49       ` awdorrin
2011-11-16 21:31         ` Gautier write-only
2011-11-16 22:40           ` Adam Beneschan
2011-11-17  0:00             ` Adam Beneschan
2011-11-15 23:08 ` Jeffrey Carter
2011-11-16  1:18   ` Adam Beneschan
2011-11-16  5:33     ` tmoran
2011-11-16 17:52       ` awdorrin
2011-11-16 20:01         ` Simon Wright

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox