View Issue Details

IDProjectCategoryView StatusLast Update
0038877FPCCompilerpublic2021-05-13 04:29
Reporter440bx Assigned To 
PrioritynormalSeverityminorReproducibilityalways
Status newResolutionopen 
Product Version3.0.4 
Summary0038877: FPC allows writing to non-writeable constant
Descriptionthe title says it all.
Steps To ReproduceCompile the following program :

{$APPTYPE CONSOLE}
 
{$TYPEDADDRESS ON}
 
{$LONGSTRINGS OFF}
{$WRITEABLECONST OFF}
 
{ --------------------------------------------------------------------------- }
 
program _writeableconst;
 
const
  ArrayConst : array[0..1] of
               record
                 t : pchar;
                 l : DWORD
               end =
  (
   (t: 'some text'; l: 0),
   (t: 'more text'; l: 0)
  );
 
  v : DWORD = 0;
 
var
  i : integer;
 
begin
  for i := low(ArrayConst) to high(ArrayConst) do
  begin
    with ArrayConst[i] do
    begin
      { assign to a non writeable constant, yet NO compiler error emitted }
      { BUT, you get an access violation at runtime (as there should be) }
 
      l := i + 10; { set to any value }
    end;
  end;
 
  { this statement causes a compile time error - as it should }
 
  v := 1; { compile error - as expected }
end.

the line l := i + 10; should be rejected by the compiler.
TagsNo tags attached.
Fixed in Revision
FPCOldBugId
FPCTarget
Attached Files

Activities

runewalsh

2021-05-12 13:43

reporter   ~0130827

You can also take a pointer to a constant and get SIGSEGV when trying to write it. Not sure about the 'with' scenario, but with pointers this can hardly be fixed at all. Even if there were CV-qualifications for types, you'd need a way to circumvent them for compatibility or specific needs, as with C++'s "mutable" and "const_cast".

J. Gareth Moreton

2021-05-12 18:11

developer   ~0130838

Last edited: 2021-05-12 18:11

View 2 revisions

On a similar note, under x86_64-win64, the test test/tarray15.pp fails if you specify TEST_OPT="-a" for the assembly dumps. The failure is because the code writes to a constant and doesn't raise an exception while doing so.

440bx

2021-05-13 04:29

reporter   ~0130842

@runewalsh,

When taking a pointer to a constant, the compiler has to be able to determine that the pointer is an alias for the constant, something which is not always possible.

In the example I presented, the reference to the non-writeable constant is direct, the compiler should complain because it "knows" that the assignment is being done to a non-writeable constant (as it does when it encounters "v := 1")

There is no difference at all between that "v := 1" and "l := i + 10". Both are direct references to a non-writeable constant and, the compiler should reject _both_.

Issue History

Date Modified Username Field Change
2021-05-12 08:25 440bx New Issue
2021-05-12 13:43 runewalsh Note Added: 0130827
2021-05-12 18:11 J. Gareth Moreton Note Added: 0130838
2021-05-12 18:11 J. Gareth Moreton Note Edited: 0130838 View Revisions
2021-05-13 04:29 440bx Note Added: 0130842