[fpc-devel] double free of internal temp string with fpc 3.2.0
baldzhang
baldzhang at 163.com
Fri Jan 8 23:13:44 CET 2021
I have the same problem after upgrade to 3.2.0, 3.0.4 is all good.
In my program, when free a TStringList that used in a thread, exception occurs in 80%~90% time.
I try to finger out what happening and got fpc_ansistr_decr_ref calling FreeMem then got wrong memory.
The program was x86-64 on Windows 10.
I haven't dig so deep like Martin has done, but I think it's the same problem.
At 2021-01-09 00:11:19, "Martin Frb via fpc-devel" <fpc-devel at lists.freepascal.org> wrote:
>I only tested with 3.2.0 so far. Maybe someone recalls if this is fixed
>or not.
>
>Also because it seems to happen only in very rare conditions, it may be
>that trunk does not cause it in this place even if the bug is not yet
>fixed. (as other code changes could simply change the context enough to
>mitigate it)
>
>
>Using fpc 3.2.0
>compiling lazarus SVN 64346 at trunk with -gw -gl -gt -Criot -Sa -O-1 -gh -gv
>(this also happened at -O3 / but I could not trace it as valgrinds
>reported stack was unreadable / The attached valgrind is with -O-1)
>
>unit MaskEdit
>procedure TCustomMaskEdit.SetMask(Value : String);
>
> From the generated ASM
>
># Temps allocated between rbp-696 and rbp-296
>
># [575] for I := 1 To Utf8Length(S) do
> leaq -400(%rbp),%rdi
> call fpc_ansistr_decr_ref at PLT
> leaq -408(%rbp),%rdi
> call fpc_ansistr_decr_ref at PLT
> leaq -272(%rbp),%rsi
> xorl %edx,%edx
> leaq -408(%rbp),%rdi
> call fpc_shortstr_to_ansistr at PLT
> movq -408(%rbp),%rsi //////
><<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
> movq %rsi,-400(%rbp)
> testq %rsi,%rsi
> je .Lj156
> movq -8(%rsi),%rsi
>.Lj156:
> movq -400(%rbp),%rdi
> testq %rdi,%rdi
> jne .Lj157
> movq FPC_EMPTYCHAR at GOTPCREL(%rip),%rdi
>.Lj157:
> call LAZUTF8_$$_UTF8LENGTH$PCHAR$INT64$$INT64 at PLT
>
>On the marked line, the string (ref) in temp(-408) is copied to temp(-400).
>But the refcount is NOT increased
>
>*****
>Temp(-408) is later passed as "var param Result" to
>
># [741] FTextOnEnter := inherited RealGetText;
> movq -16(%rbp),%rdi
> leaq -408(%rbp),%rsi
> call STDCTRLS$_$TCUSTOMEDIT_$__$$_REALGETTEXT$$TTRANSLATESTRING at PLT
>
>This will assign an empty string (in this case), and free the memory
>(apparently the refcount happens to be 1 at that time)
>
>*****
>in the autogenerated code for the procedures "end" statement:
>
># [743] end;
> leaq -408(%rbp),%rdi
> call fpc_ansistr_decr_ref at PLT
> leaq -400(%rbp),%rdi
> call fpc_ansistr_decr_ref at PLT
>
>Temp-408 is already free (or may have a new value that gets correctly freed)
>
>Temp-400 still points to the already freed string => double free.
>
>
>
>
>
>
More information about the fpc-devel
mailing list