[fpc-devel] Dangerous optimization in CASE..OF
Florian Klämpfl
florian at freepascal.org
Sun Jul 2 19:39:30 CEST 2017
Am 02.07.2017 um 19:29 schrieb Martok:
> Addendum to this:
>
>> This was also always my intuition that the else block is also triggered for
>> invalid enum values (the docs even literally say that, "If none of the case
>> constants match the expression value") - and it *is* true in Delphi.
> There is a reason why this is true in Delphi: because this is the way it has
> been documented in Borland products for at least 25 years!
>
> I have checked with the TP7 language reference (it pays to keep books around),
> which defines the following things:
> - Enumeration element names are implicitly defined as typed constants of their
> enum type
> - The enum type is either Byte (<=256 elements) or Word.
> - Subrange types are defined as the smallest type that can contain their range
> - Case statements execute the statements of the matching case label, or the
> else block otherwise
>
> Note that they actually defined enumerations as what I called 'fancy constants'
> before.
>
>
> The Delphi 4 language reference (also in book form, which is a bit more detailed
> than what is in the .hlp files) uses more precise language:
> - Enumeration element names are implicitly defined as typed constants of their
> enum type
> - The enum type is either Byte, Word, or Longword, depending on $Z and element
> count
> - Subrange types are defined as the smallest type that can contain their range
> - it is legal to inc/dec outside of a subrange, example from the book:
> type Percentile = 1..99;
> var I: Percentile;
> begin
> I:= 99;
> inc(I); // I is now 100
> So if this is a legal statement, subrange types can contain values outside of
> their range. The description in the German version is "Die Variable wird in
> ihren Basistyp umgewandelt", the variable becomes its base type.
> - Case statements execute *precisely one* of their branches: the statements of
> the matching case label, or the else block otherwise
>
> So, in D4, we have enums as fancy constants, subrange-types are not safe (so
> enums can also never be), and case statements cannot fail.
>
>
> FPC's language reference has no formal definition of what enums or subranges
> really are, and the same language as TP7 regarding case statements.
>
>
> So at least in modes TP and DELPHI, the optimisation in question is formally wrong.
So this means:
var
b : boolean;
begin
b:=boolean(3);
if b then
writeln(true)
else if not(b) then
writeln(false)
else
writeln(ord(b));
end.
writes 3 in delphi?
More information about the fpc-devel
mailing list