Recent

Author Topic: Crash in Assign()  (Read 1760 times)

Steve Baxter

  • Newbie
  • Posts: 6
Crash in Assign()
« on: July 08, 2024, 06:23:04 pm »
We have a Pascal library that's used in a C++ application. We last compiled this library about 10 years ago when we moved from 32-bit to 64-bit on Mac. We now need to compile it again for ARM. My Pascal is rusty to say the least!

Everything compiles, but the library crashes with an access violation in Assign(). I've boiled it down to this code:

Code: Pascal  [Select][+][-]
  1. function Delphi_DLLInitDB(DllPathC:PChar):Int16; cdecl;
  2. var
  3.    f:File;
  4. begin
  5.     Assign(f,'Test');
  6. end;
  7.  

This is about as simple as it can get. The crash is in:

Code: Pascal  [Select][+][-]
  1. #0      0x0000000000000000 in 0x00000000 ()
  2. #1      0x000000010f37fd8a in fpc_ansistr_to_widechararray ()
  3. #2      0x000000010f393459 in SYSTEM_$$_ASSIGN$file$RAWBYTESTRING ()
  4. #3      0x000000010f5183a8 in $REDACTED$_Ld41 ()
  5. #4      0x000000010f32a438 in RedactedCCode() const
  6.  

I'm sure I must be missing something basic, does anyone have any idea what it might be?

Steve Baxter

  • Newbie
  • Posts: 6
Re: Crash in Assign()
« Reply #1 on: July 08, 2024, 06:25:13 pm »
In case it's important, this is how we're building:

Code: Pascal  [Select][+][-]
  1. # Compile the files for x64
  2. fpc -Px86_64 -FEbuild/x64 -FuUnits -gl -g -Cn src/Redacted.p
  3.  
  4. # Create a static x64 library
  5. libtool -static -o build/libRedacted-x64.a `grep "\.o$" build/x64/linkfiles*.res`
  6.  
  7. # Compile the files for ARM
  8. fpc -Paarch64 -FEbuild/arm -FuUnits -gl -g -Cn src/Redacted.p
  9.  
  10. # Create a static ARM library
  11. libtool -static -o build/libRedacted-arm.a `grep "\.o$" build/arm/linkfiles*.res`
  12.  
  13. # Combine the two libraries into a new one
  14. lipo -create -output lib/libRedacted.a build/libRedacted-arm.a build/libRedacted-x64.a
  15.  

Thaddy

  • Hero Member
  • *****
  • Posts: 16168
  • Censorship about opinions does not belong here.
Re: Crash in Assign()
« Reply #2 on: July 08, 2024, 06:28:54 pm »
In FreePascal a Console needs be assigned under Windows. I you do {$apptype console} then it works.  (you don't have to show the console}.
On other platforms, like on linux, your code should always work.
The very weird issue is that on Windows, stdin/out/error are not available as default.
In trunk, there are many fixes, also for Mac, but that is out of the question for production code of course. The problem I described is Windows only.
Can you maybe describe the setup a bit better? The part you showed is/starts with nil, the real nil, so something that should be there isn't there....
« Last Edit: July 08, 2024, 06:38:46 pm by Thaddy »
If I smell bad code it usually is bad code and that includes my own code.

cdbc

  • Hero Member
  • *****
  • Posts: 1655
    • http://www.cdbc.dk
Re: Crash in Assign()
« Reply #3 on: July 08, 2024, 06:46:45 pm »
Hi
Quote
fpc_ansistr_to_widechararray ()
Could it be as simple as changing params from 'PChar' to 'PWideChar' and recompiling?!?
...Just caught my eye...
Regards Benny
If it ain't broke, don't fix it ;)
PCLinuxOS(rolling release) 64bit -> KDE5 -> FPC 3.2.2 -> Lazarus 2.2.6 up until Jan 2024 from then on it's: KDE5/QT5 -> FPC 3.3.1 -> Lazarus 3.0

Zvoni

  • Hero Member
  • *****
  • Posts: 2741
Re: Crash in Assign()
« Reply #4 on: July 09, 2024, 08:23:49 am »
Is it possible, that the client is calling the "wrong" version?
AFAIU, TS is combining both architectures into one lib

And if i see this correctly, TS is going for static linking

btw: Untyped File?
One System to rule them all, One Code to find them,
One IDE to bring them all, and to the Framework bind them,
in the Land of Redmond, where the Windows lie
---------------------------------------------------------------------
Code is like a joke: If you have to explain it, it's bad

Thaddy

  • Hero Member
  • *****
  • Posts: 16168
  • Censorship about opinions does not belong here.
Re: Crash in Assign()
« Reply #5 on: July 09, 2024, 08:32:46 am »
Well it must be related to the string literal if fpc_ansistr_to_widechararray () is called. The literal itself should be an array type of ansichar, which is not a PChar..
I suggest you explicitly declare it as PAnsiChar. What does gettypekind return? Assign() on its own does very little until rewrite  or reset is called. It merely assigns, but not use, a file name 'test'  to be used later.
Find out what the string literal type is and change the code explicitly using either PAnsiChar or PWideChar. You may also have a look at if the calling convention is correct:
the code probably stems from 32 bit era. What happens if you remove the cdecl? I can test AARCH64, but not Apple hardware.

And where is the export modifier?
« Last Edit: July 09, 2024, 08:40:58 am by Thaddy »
If I smell bad code it usually is bad code and that includes my own code.

Steve Baxter

  • Newbie
  • Posts: 6
Re: Crash in Assign()
« Reply #6 on: July 09, 2024, 05:00:33 pm »
Thanks for the comments.

1. This is on Mac, so no console or anything should be needed
2. It's not possible for the client to call the wrong architecture (and it still crashes with a single architecture)
3. The PChar isn't involved - I'm calling Assign() with a literal

@Thaddy - what is the export modifier? This is code we have inherited, nobody on our team knows much at all about Pascal!

This is such an obvious crash that there must be something else going on. Is there some initialisation that needs to happen?

Thaddy

  • Hero Member
  • *****
  • Posts: 16168
  • Censorship about opinions does not belong here.
Re: Crash in Assign()
« Reply #7 on: July 09, 2024, 05:38:04 pm »
Assign() to a file does basically nothing until rewrite or reset is called. It just associates the handle with a recognizable file name.
From your code it seems, like Benny suspects too, that the string literal 'test' causes your issue. And that string literal should resolve to array of ansichar. Which is not a PChar. Pay attention to the string details when porting to a unicode 64 bit system.
« Last Edit: July 09, 2024, 06:07:25 pm by Thaddy »
If I smell bad code it usually is bad code and that includes my own code.

Steve Baxter

  • Newbie
  • Posts: 6
Re: Crash in Assign()
« Reply #8 on: July 09, 2024, 08:32:29 pm »
So I think this is an initialisation problem. It looks like `widestringmanager` isn't initialised, this is used in `fpc_ansistr_to_widechararray()`:

https://github.com/fpc/FPCSource/blob/main/rtl/inc/ustrings.inc#L828

It looks like this is supposed to be initialised automatically here:

https://github.com/fpc/FPCSource/blob/b1f0c504cc58d9441af5dd81229d54c84e74b162/rtl/objpas/fpwidestring.pp#L889

Possibly as this is a static library the runtime isn't getting initialised automatically. Does anyone know how to make that work?

PascalDragon

  • Hero Member
  • *****
  • Posts: 5755
  • Compiler Developer
Re: Crash in Assign()
« Reply #9 on: July 09, 2024, 10:49:19 pm »
Possibly as this is a static library the runtime isn't getting initialised automatically. Does anyone know how to make that work?

That is correct. FPC code is not designed to be usable as a static library. If you want to go this route you need to make sure that you call FPC_INITIALIZEUNITS (it's exported with that uppercase symbol name from the System unit (and thus its object file)).

Steve Baxter

  • Newbie
  • Posts: 6
Re: Crash in Assign()
« Reply #10 on: July 10, 2024, 11:45:18 am »
That doesn't work unfortunately:

Code: Pascal  [Select][+][-]
  1. TEST.P(2225,5) Error: Identifier not found "FPC_INITIALIZEUNITS"
  2. TEST.P(2254) Fatal: There were 1 errors compiling module, stopping
  3. Fatal: Compilation aborted
  4.  

I might have to rearrange this as a dynamic library.

Thaddy

  • Hero Member
  • *****
  • Posts: 16168
  • Censorship about opinions does not belong here.
Re: Crash in Assign()
« Reply #11 on: July 10, 2024, 03:57:55 pm »
How doesn't that work? did you actually link against system? Because that is what PascalDragon explained. If you leave that out, indeed, make it a shared library.
If I smell bad code it usually is bad code and that includes my own code.

Steve Baxter

  • Newbie
  • Posts: 6
Re: Crash in Assign()
« Reply #12 on: July 10, 2024, 04:11:06 pm »
I thought system was included always? Anyway I've moved this to be a dynamic lib which has fixed all the problems.

PascalDragon

  • Hero Member
  • *****
  • Posts: 5755
  • Compiler Developer
Re: Crash in Assign()
« Reply #13 on: July 14, 2024, 10:02:21 pm »
I thought system was included always? Anyway I've moved this to be a dynamic lib which has fixed all the problems.

You need to make sure that the system.o is indeed included in your static library.

 

TinyPortal © 2005-2018