View Issue Details

IDProjectCategoryView StatusLast Update
0016006FPCCompilerpublic2020-07-14 21:30
ReporterAdriaan van Os Assigned ToJonas Maebe  
PrioritynormalSeveritymajorReproducibilityalways
Status closedResolutionwon't fix 
Platformi386-apple-darwinOSMac OS X 
Product Version2.5.1 
Summary0016006: Dead code mistake
DescriptionThe following program

program testdeadcode;
type
  range = 1..96;
var
  i: integer;
  r: range;
begin
  i:= 100;
  r:= range( i);
  if r > 96
    then writeln( 'r out of range')
    else writeln( 'r = ', r)
end.

gives a warning

testdeadcode.pas(11,10) Warning: unreachable code

and then produces the following wrong output

r = 100

TagsNo tags attached.
Fixed in Revision
FPCOldBugId
FPCTarget
Attached Files

Relationships

has duplicate 0024421 resolvedJonas Maebe Comparing variable with out of range value yields false without typecast 
has duplicate 0029147 closedJonas Maebe Don't get I/O error as expected by Array of [Enumrange] 
has duplicate 0032079 resolvedJonas Maebe Jumptables for case..of may jump into invalid memory 
has duplicate 0030423 resolvedJonas Maebe Range checks missing at runtime on type casts using sub ranges 
has duplicate 0034100 resolvedJonas Maebe compiler doesn't generate range check code for boolean array 
related to 0022179 closedFlorian FPC trunk revision 21455 have major bug at Math units Max-procedure when using subranged type. 
related to 0034140 closed compiler removes code it wrongly believes to be unreachable 
related to 0035753 resolvedJonas Maebe Delphi allows dereferencing a pointer to a [0..0] static array and accessing it with indices > 0, however 0035671 breaks this. 
related to 0037342 resolvedJonas Maebe Regression: range check warning 

Activities

Jonas Maebe

2010-03-16 12:13

manager   ~0035634

If you explicitly disable the compiler's type checking, you can do anything. I think it is completely correct for the compiler to assume that variables of a particular type indeed only contain values that are valid for that type. Otherwise having a type system has little use.

Adriaan van Os

2010-09-21 10:46

developer   ~0041258

The test program proves that the compile-time assumption that "variables of a particular type indeed only contain values that are valid for that type" is wrong. Worse, this assumption makes it impossible to check for the same at run-time.

Jonas Maebe

2010-09-21 11:32

manager   ~0041259

Last edited: 2010-09-21 11:49

> The test program proves that the compile-time assumption that
> "variables of a particular type indeed only contain values that are
> valid for that type" is wrong.

Even in ADA you can perform unchecked type casts ( http://en.wikibooks.org/wiki/Ada_Programming/Subtypes#Unchecked_conversion ) and then the result is undefined "when the destination type can not hold the source value".

I stand by my opinion that if the program explicitly says that the compiler must not check a particular conversion, that the compiler is entitled to assume that it is valid (and hence that the result is also valid).

Florian

2010-09-21 17:04

administrator   ~0041264

I think the type cast is not the point. The important point is imo that r is declared 1..96 so the compiler can assume that r contains no other values. If it contains other values, the behaviour is implementation specific.

Adriaan van Os

2010-10-10 16:22

developer   ~0041688

I agree with Florian that the type cast is not the point. But I disagree with the compiler assumption that the value of of a variable is always in the declared range. That is very optimistic ....

There are many reasons why the runtime value of a variable can be outside its compile-time declared range. I mention: untyped pointers, blockmoves, typecasts, blockreads, calling external code, calling system software, variant parts of a case record, etcetera.

Only a language that forbids all those operations (and running on fault-tolerant hardware) can safely make the above assumption. And therefore a well-written program builds-in value checks at runtime. And therefore it doesn't like the compiler optimizing away those checks ....

Jonas Maebe

2010-10-10 17:01

manager   ~0041690

The typecast actually is the whole point for the example program, see the Ada explanation: that expression means that any further operation on that value is undefined if the original value was out of range.

Optimising based on type inference is done in every single compiler for every single typed language I know of, regardless of the platform or hardware you run on (from Java to C to Ada, even though in all cases you can corrupt values via assembler code or due to running on buggy hardware, cosmic rays, and except for Java due to uninitialised values).

If you don't want the compiler to take into account particular type information, then you cannot give it any such information and must perform the corresponding checks manually.

Jonas Maebe

2010-10-10 17:04

manager   ~0041691

You can always write "if longint(r) > 96 then" if you want the compiler to ignore the type information in that statement as well.

Issue History

Date Modified Username Field Change
2010-03-16 09:27 Adriaan van Os New Issue
2010-03-16 12:13 Jonas Maebe Status new => resolved
2010-03-16 12:13 Jonas Maebe Resolution open => no change required
2010-03-16 12:13 Jonas Maebe Assigned To => Jonas Maebe
2010-03-16 12:13 Jonas Maebe Note Added: 0035634
2010-09-21 10:46 Adriaan van Os Status resolved => feedback
2010-09-21 10:46 Adriaan van Os Resolution no change required => reopened
2010-09-21 10:46 Adriaan van Os Note Added: 0041258
2010-09-21 11:32 Jonas Maebe Status feedback => resolved
2010-09-21 11:32 Jonas Maebe Resolution reopened => no change required
2010-09-21 11:32 Jonas Maebe Note Added: 0041259
2010-09-21 11:49 Jonas Maebe Note Edited: 0041259
2010-09-21 17:04 Florian Note Added: 0041264
2010-10-10 16:22 Adriaan van Os Status resolved => feedback
2010-10-10 16:22 Adriaan van Os Resolution no change required => reopened
2010-10-10 16:22 Adriaan van Os Note Added: 0041688
2010-10-10 17:01 Jonas Maebe Status feedback => resolved
2010-10-10 17:01 Jonas Maebe Resolution reopened => won't fix
2010-10-10 17:01 Jonas Maebe Note Added: 0041690
2010-10-10 17:04 Jonas Maebe Note Added: 0041691
2012-06-03 11:40 Jonas Maebe Relationship added related to 0022179
2013-05-13 13:57 Jonas Maebe Relationship added has duplicate 0024421
2013-11-28 21:53 Jonas Maebe Status resolved => closed
2015-12-07 23:33 Jonas Maebe Relationship added has duplicate 0029147
2017-06-29 20:03 Jonas Maebe Relationship added has duplicate 0032079
2018-08-08 19:18 Jonas Maebe Relationship added has duplicate 0030423
2018-08-08 19:19 Jonas Maebe Relationship added has duplicate 0034100
2018-08-17 17:53 Jonas Maebe Relationship added related to 0034140
2019-06-22 21:52 Jonas Maebe Relationship added related to 0035753
2020-07-14 21:30 Jonas Maebe Relationship added related to 0037342