Sign in Join

Live chat for Free Pascal, Lazarus, Delphi and every Pascal programmer.

Mailing lists / fpc-devel / 2020-12

Different handling of try..except depending on OS?

13 messages · 5 people · –

Reply by email Subscribe to this list Your subscription

Read-only archive. Use j and k to move between messages.

Bart

Hi,

Consider this code:

program Test;
{$apptype console}
{$ifdef fpc}
{$mode objfpc}
{$endif fpc}
{$R+}
var
  Arr: array[1..2] of integer;
  i: Integer;
begin
  i:=5;
  try
    try
      Arr[i] := 1;
    except
      writeln('Except block');
    end;
  finally
    writeln('Finally block');
  end;
end.

Compiled with fpc 3.2.0 on Windows it will output (both 32 and 64 bit): Runtime error 201 at $004015F1
$004015F1
$00407307

Compiled with fpc 3.2.0 on linux X86_64 it will output Except block
Finally block

On Windows you need to include the sysutils unit to execute the except and finally block.

Note 1: fpc 3.0.4 on Windows generates the same outpus as 3.2.0 on Linux... Note 2: Delphi 7 behaves like 3.2.0

Is there any explanation for that?
Related forum discussion:
https://forum.lazarus.freepascal.org/index.php/topic,52469.0/topicseen.html

Bart

Reply by email

Sven Barth
to Bart
Bart wrote 11 lines
Compiled with fpc 3.2.0 on Windows it will output (both 32 and 64 bit): Runtime error 201 at $004015F1 $004015F1 $00407307 Compiled with fpc 3.2.0 on linux X86_64 it will output Except block Finally block On Windows you need to include the sysutils unit to execute the except and finally block.

That is correct, because without the SysUtils unit (which declared the Exception type) the RTL can't convert the triggered runtime error to an exception type that can be caught inside the try ... except ... end block.

Note 1: fpc 3.0.4 on Windows generates the same outpus as 3.2.0 on Linux... Note 2: Delphi 7 behaves like 3.2.0

Behaves like 3.2.0 on what platform? I assume Windows, cause Delphi 10.2 behaves the same as FPC 3.2.0 on Windows.

Is there any explanation for that? Related forum discussion: https://forum.lazarus.freepascal.org/index.php/topic,52469.0/topicseen.html

It's possibly related to FPC using SEH on Win32 and Win64 instead of the SetJump/LongJump based exception handling on other platforms. Slight differences are possible and we'd have to investigate why the later does not correctly trigger a runtime error.

Regards,
Sven

Reply by email

Bart
to Sven Barth
AM Sven Barth wrote
That is correct, because without the SysUtils unit (which declared the Exception type) the RTL can't convert the triggered runtime error to an exception type that can be caught inside the try ... except ... end block.

I would have expected that in that scenario (no sysutils) try..except or try..finally should raise a compilation error then. Since you teel the compiler to do things it cannot do? It would be Delphi incompatible of course ...

B.t.w. (cannot test now, am at work): does it catc exceptions if any other used unit in the main program uses sysutils? I.o.w.: is it enough if sysutils gets linked in, or must it be in the unit/prgram that actually has the try..except/try..finally code in it?

Behaves like 3.2.0 on what platform? I assume Windows, cause Delphi 10.2

Yes, on Windows.

It's possibly related to FPC using SEH on Win32 and Win64 instead of the SetJump/LongJump based exception handling on other platforms. Slight differences are possible and we'd have to investigate why the later does not correctly trigger a runtime error.

Ok.
Not a big problem for me (I don't think I have any usefull program that doesn't include the sysutils unit), it just made me curious.

Bart

Reply by email

Bart
to Sven Barth: That is correct, because without the SysUtils unit (which declared the Exception type)…
AM Sven Barth wrote
It's possibly related to FPC using SEH on Win32 and Win64 instead of the SetJump/LongJump based exception handling on other platforms. Slight differences are possible and we'd have to investigate why the later does not correctly trigger a runtime error.

Should I file a bugreport for that?
If so, someone should first confirm it with trunk (I don't have fpc trunk on my Linux VM).

Bart

Reply by email

Michael Van Canneyt
to Bart: On Thu, Dec 10, 2020 at 7:34 AM Sven Barth via fpc-devel I would have expected that in…
Bart wrote 10 lines
On Thu, Dec 10, 2020 at 7:34 AM Sven Barth via fpc-devel wrote: > That is correct, because without the SysUtils unit (which declared the > Exception type) the RTL can't convert the triggered runtime error to an > exception type that can be caught inside the try ... except ... end block. I would have expected that in that scenario (no sysutils) try..except or try..finally should raise a compilation error then. Since you teel the compiler to do things it cannot do?

No.

Sysutils is only needed to convert run-time errors to exceptions.

You can perfectly use exceptions without sysutils, but they can not descend from Exception, but from TObject. That exception classes descend from Exception is a convention, not a compiler-enforced rule.

If you change your code to this

   Except
     On O : TObject do
      Writeln('except block : ',O.ClassName)

You'll see there is no output, because there is no exception object.

The reason is as Sven surmised: the setjmp mechanism used on non-windows platforms.

Show quoted text 6 lines
It would be Delphi incompatible of course ... B.t.w. (cannot test now, am at work): does it catc exceptions if any other used unit in the main program uses sysutils? I.o.w.: is it enough if sysutils gets linked in, or must it be in the unit/prgram that actually has the try..except/try..finally code in it?

It is enough that sysutils gets linked in.

I checked that, the program you sent does not have sysutils linked in.

Michael.

Reply by email

Michael Van Canneyt
to Bart: On Thu, Dec 10, 2020 at 7:34 AM Sven Barth via fpc-devel Should I file a bugreport for…
Bart wrote 11 lines
On Thu, Dec 10, 2020 at 7:34 AM Sven Barth via fpc-devel wrote: > It's possibly related to FPC using SEH on Win32 and Win64 instead of the > SetJump/LongJump based exception handling on other platforms. Slight > differences are possible and we'd have to investigate why the later does > not correctly trigger a runtime error. Should I file a bugreport for that? If so, someone should first confirm it with trunk (I don't have fpc trunk on my Linux VM).

No fpc in your linux vm ? I'm shocked... ;-)

I confirmed it with trunk.

Michael.

Reply by email

Tomas Hajny
to Sven Barth: That is correct, because without the SysUtils unit (which declared the Exception type)…
Sven Barth wrote 18 lines
Am 09.12.2020 um 23:45 schrieb Bart via fpc-devel: > Compiled with fpc 3.2.0 on Windows it will output (both 32 and 64 > bit): > Runtime error 201 at $004015F1 > $004015F1 > $00407307 > > Compiled with fpc 3.2.0 on linux X86_64 it will output > Except block > Finally block > > On Windows you need to include the sysutils unit to execute the except > and finally block. That is correct, because without the SysUtils unit (which declared the Exception type) the RTL can't convert the triggered runtime error to an exception type that can be caught inside the try ... except ... end block.

.
.

Is the current behaviour on "other" (non-MS Windows) targets really correct (I checked under OS/2 for both 3.2.0 and trunk and it behaves the same way as Linux)? Including SysUtils should result in converting a run-time error to an exception. If SysUtils is not included, run-time error should be raised regardless from the try..except block (as it does under MS Windows, but not on other platforms at the moment), shouldn't it? Shouldn't the try..except construct by default (i.e. without using SysUtils) catch only explicitly raised exceptions?

Tomas

Reply by email

Michael Van Canneyt
to Tomas Hajny
Tomas Hajny wrote 30 lines
On 2020-12-10 07:34, Sven Barth via fpc-devel wrote: > Am 09.12.2020 um 23:45 schrieb Bart via fpc-devel: >> Compiled with fpc 3.2.0 on Windows it will output (both 32 and 64 >> bit): >> Runtime error 201 at $004015F1 >> $004015F1 >> $00407307 >> >> Compiled with fpc 3.2.0 on linux X86_64 it will output >> Except block >> Finally block >> >> On Windows you need to include the sysutils unit to execute the except >> and finally block. > > That is correct, because without the SysUtils unit (which declared the > Exception type) the RTL can't convert the triggered runtime error to > an exception type that can be caught inside the try ... except ... end > block. . . Is the current behaviour on "other" (non-MS Windows) targets really correct (I checked under OS/2 for both 3.2.0 and trunk and it behaves the same way as Linux)? Including SysUtils should result in converting a run-time error to an exception. If SysUtils is not included, run-time error should be raised regardless from the try..except block (as it does under MS Windows, but not on other platforms at the moment), shouldn't it? Shouldn't the try..except construct by default (i.e. without using SysUtils) catch only explicitly raised exceptions?

Yes, it should. it's definitely a bug.

Michael.

Reply by email

Sven Barth
to Bart: On Thu, Dec 10, 2020 at 7:34 AM Sven Barth via fpc-devel I would have expected that in…

Bart via fpc-devel schrieb am Do., 10.
Dez. 2020, 11:56:

Show quoted text 13 lines
On Thu, Dec 10, 2020 at 7:34 AM Sven Barth via fpc-devel wrote: > That is correct, because without the SysUtils unit (which declared the > Exception type) the RTL can't convert the triggered runtime error to an > exception type that can be caught inside the try ... except ... end block. I would have expected that in that scenario (no sysutils) try..except or try..finally should raise a compilation error then. Since you teel the compiler to do things it cannot do? It would be Delphi incompatible of course ...

The *compiler* handles it correctly. It's the *RTL* that's not setup in a way that it would work correctly in that case. And since in theory the user is completely free to provide their own RTL the compiler can't do any checks here.

Show quoted text 5 lines
B.t.w. (cannot test now, am at work): does it catc exceptions if any other used unit in the main program uses sysutils? I.o.w.: is it enough if sysutils gets linked in, or must it be in the unit/prgram that actually has the try..except/try..finally code in it?

The initialization section of the SysUtils unit needs to be executed, so as long as any other unit includes the SysUtils unit it will work.

Regards,
Sven

Reply by email

Bart
to Michael Van Canneyt: No fpc in your linux vm ? I'm shocked... ;-) I confirmed it with trunk. Michael.
No fpc in your linux vm ? I'm shocked... ;-)

Well, no trunk ;-)
On Windows I know how to easily switch between using compilers. 3.2.0 is in path and I have some batch files to change that for 3.0.4 and trunk respectively (only in the current console session). I never had the courage to figure out how to do that on linux (in such a way it does not interfere with my normal setup).

Bart

Reply by email

Sven Barth
to Bart
Bart wrote 7 lines
> No fpc in your linux vm ? I'm shocked... ;-) Well, no trunk ;-) On Windows I know how to easily switch between using compilers. 3.2.0 is in path and I have some batch files to change that for 3.0.4 and trunk respectively (only in the current console session). I never had the courage to figure out how to do that on linux (in such a way it does not interfere with my normal setup).

I use a script to change symlinks that are inside a directory that's in PATH.

Regards,
Sven

Reply by email

Marco van de Voort
to Sven Barth

Op 2020-12-10 om 21:57 schreef Sven Barth via fpc-devel:

Show quoted text 11 lines
Am 10.12.2020 um 20:54 schrieb Bart via fpc-devel: >> No fpc in your linux vm ? I'm shocked... ;-) > Well, no trunk ;-) > On Windows I know how to easily switch between using compilers. > 3.2.0 is in path and I have some batch files to change that for 3.0.4 > and trunk respectively (only in the current console session). > I never had the courage to figure out how to do that on linux (in such > a way it does not interfere with my normal setup). I use a script to change symlinks that are inside a directory that's in PATH.

In the past I used the -V parameter a lot.

 -V<x>  Append '-<x>' to the used compiler binary name (e.g. for version)

This allows to make symlinks like   e.g. ppcx64-3.0  to /usr/local/lib/fpc/3.0.4/ppcx64  and then compile with fpc -V3.0 etc.

Of course this meant that the fpc.cfg had to be carefully crafted with $FPCVERSION

The biggest drawback is that it only goes for the compiler not for the other binaries. AND it requires a parameter, but for a quick check with an old/release compiler that is enough.

Reply by email