[Lazarus] EXC_BAD_ACCESS, Could not access memory

Martin Friebe lazarus at mfriebe.de
Fri Apr 24 15:33:34 CEST 2009


Roland Turcan wrote:
> Hello Bart and others,
>
> Thanks for your kindness to test my test case, which works fine in my
> case too, but I have found something what maybe more explain my
> problem.
>   
"maybe"? This does most certainly explain your problem, see below
> TYPE TSomeItem = RECORD
>                    First :single;
>                    Second:Single;
>                    Third :integer;
>
> TYPE TSomethingArr = ARRAY OF TSomeItem;
>
> TYPE TSomeHeader   =RECORD
>                       ...
>                     end;
>
> TYPE TMyObject =class
>                  private
>                    FHeader:TSomeHeader;
>                    FItems :TSomethingArr;
>
> ...
>
> FUNCTION TMyObject.LoadFromStream (Stream:TStream):BOOLEAN;
> ...
>   SetLength (FItems, 0); //!! for testing only -- this line works fine
>   Stream.Read (FHeader, HeaderLen);
>   SetLength (FItems, 0); //!! for testing only -- this line raises an exception
> END;
>
>
> If you see the declaration of TMyObject you will find that FHeader
> declaration is followed by FItems and the length of read memory block
> goes over size of FHeader and it affects FItems.
>
> Hm?
>   
Take a look of how thinks are organized in memory:

TMyObject allocates some memory. FHeaders (being a record) is embedded 
into the same memory, it is part of  TMyObjects memory.
But FItems (being an array) allocates it's own memory, somewhere 
completely different. It only stores a pointer inside TMyObject.

This means when you write past FHeaders, then you but a random value 
into the pointer. Next time you try to access the array it will try to 
follow this random value. This means you try to access memory that 
doesn't belong to the application. Even if the value pointed to an 
address inside the apps accessible mem, you would still override random 
other data and crash.

Best Regards
Martin

> TRoland;
>
> <<< 23.4.2009 17:19 - Bart "bartjunk64 at gmail.com" >>>
> B> This code works perfectly fine (at least it does not crash) with fpc 2.2.2
>
> B> constructor TMyObject.Create;
> B> begin
> B>   DebugLn('Create');
> B>   FItem := nil;
> B>   DebugLn('nil');
> B>   SetLength(FItem,3);
> B>   DebugLn('SetLength');
> B>   FItem[0].First:= 1.0;
> B>   DebugLn('FItem[0].First = ',DbgS(FItem[0].First));
> B> end;
>
> B> Bart
>
>
>
>
>   



More information about the Lazarus mailing list