Why have memory leak const record ? lazarus / 62-General ---------------------------------------------------------------------- Thausand · 2019-05-06 18:36 HI hello, I have try look why but no can find me and then no understand why have leak this program: Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i program test_const_rec; {$MODE OBJFPC}{$H+} Uses  SysUtils; type  TDataRecord = record    test : string;  end; procedure MakeMany(var DataRecord: TDataRecord);const  Count : integer = 0;begin  inc(count);  DataRecord.test := Count.ToString;end; procedure Have_leak;const  DataRecord : TDataRecord = (test : '');var  i : integer;begin  DataRecord := default(TDataRecord);   for i := 1 to 100 do  begin    MakeMany(DataRecord);    WriteLn(DataRecord.Test);  end;end; procedure Have_no_leak;var  i          : integer;  DataRecord : TDataRecord = (test : '');begin  DataRecord := default(TDataRecord);   for i := 1 to 100 do  begin    MakeMany(DataRecord);    WriteLn(DataRecord.Test);  end;end;  begin  Have_leak;//  Have_no_leak;end.  heap trace: Code: [Select]Heap dump by heaptrc unit 106 memory blocks allocated : 2574/2696 105 memory blocks freed     : 2558/2680 1 unfreed memory blocks : 16 True heap size : 393216 True free heap : 393120 Should be : 393136 Call trace for block $76F6E180 size 16   $00010284  HAVE_LEAK,  line 31 of test_const_rec.pas   $000103EC  main,  line 52 of test_const_rec.pas Maybe some one can help make better understand ? ---------------------------------------------------------------------- howardpc · 2019-05-06 18:58 If you make DataRecord a global const, you can ensure that its string field (managed memory) is finalized. Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i program test_const_rec; {$MODE OBJFPC}{$H+} Uses  SysUtils; type  TDataRecord = record    test : string;  end; const  DataRecord : TDataRecord = (test : ''); procedure MakeMany(var DataRecord: TDataRecord);const  Count : integer = 0;begin  inc(Count);  DataRecord.test := Count.ToString;end; procedure This_Now_Has_No_Leak;var  i : integer;begin  DataRecord := default(TDataRecord);  for i := 1 to 100 do  begin    MakeMany(DataRecord);    WriteLn(DataRecord.Test);  end;end; begin  This_Now_Has_No_Leak;  DataRecord.test := ''; // <- insert this  ReadLn;end. ---------------------------------------------------------------------- Thausand · 2019-05-06 19:15 Hi hello howardpc, Many thanksy for help. Quote from: howardpc on May 06, 2019, 08:58:14 pmIf you make DataRecord a global const, you can ensure that its string field (managed memory) is finalized. Yes. In producing program i have make global const and leak is go away. Is problem i no understand why  (and is smell code have global const) Ok. Then i read better your answer and i think you write give hint string field and memory finalize ? I have find that when no use record field type string (or have string short) then no have leak memory ..... i have more look help because i think i have read some thing "managed memory" and "finalize".... Thank howardpc. I think maybe is good for find answer why.... i try look ---------------------------------------------------------------------- Thausand · 2019-05-06 20:50 I have look and read "typed constants" https://www.freepascal.org/docs-html/ref/refse10.html#x22-210002.2 read: QuoteRemark: It should be stressed that typed constants are automatically initialized at program start. This is also true for local typed constants and initialized variables. Local typed constants are also initialized at program start. If their value was changed during previous invocations of the function, they will retain their changed value, i.e. they are not initialized each time the function is invoked. I think that say when program start for typed const is called "initialize". Is no help read "Finalize" typed const. Then i think have answer why and how can fix: Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i procedure Have_leak_stop;const  DataRecord : TDataRecord = (test : '');var  i : integer;begin  DataRecord := default(TDataRecord);   for i := 1 to 100 do  begin    MakeMany(DataRecord);    WriteLn(DataRecord.Test);  end;    // have auto call Initialize (program startup) and no Finalize. Then make self  Finalize(DataRecord);end;.... I think is little confuse if not know/understand Typed const example is like global variable and no act same global variable ... Thanksy more howardpc for make write hint. ---------------------------------------------------------------------- ASerge · 2019-05-07 01:42 A simpler example of a memory leak: Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i {$MODE OBJFPC}{$WRITEABLECONST ON}{$LONGSTRINGS ON} procedure Test;const  Leak: string = 'Some string';begin  UniqueString(Leak);end; begin  Test;end.In my opinion, this is a compiler bug. In Delphi, this code does not cause a memory leak. ---------------------------------------------------------------------- Thausand · 2019-05-07 02:07 Hi hello ASerge, Quote from: ASerge on May 07, 2019, 03:42:16 amA simpler example of a memory leak: ... Thanksy. Yes, that much more simple QuoteIn my opinion, this is a compiler bug. In Delphi, this code does not cause a memory leak. I think same. I read better: QuoteRemark: It should be stressed that typed constants are automatically initialized at program start. This is also true for local typed constants and initialized variables. Local typed constants are also initialized at program start. If their value was changed during previous invocations of the function, they will retain their changed value, i.e. they are not initialized each time the function is invoked. I think than can write sentence after: Local initialized variable are also initialized at program start. Then same intialize and no have leak memory when use intialized variable. Same program ASerge make variable then no leak. I no have find answer for why differ and need call finalize when use typed const Some one know ? ---------------------------------------------------------------------- Thaddy · 2019-05-07 06:54 Quote from: ASerge on May 07, 2019, 03:42:16 amA simpler example of a memory leak: Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i {$MODE OBJFPC}{$WRITEABLECONST ON}{$LONGSTRINGS ON} procedure Test;const  Leak: string = 'Some string';begin  UniqueString(Leak);end; begin  Test;end.In my opinion, this is a compiler bug. In Delphi, this code does not cause a memory leak. In my opinion too.. see also here: https://forum.lazarus.freepascal.org/index.php?topic=44552.0 Didn't one of us reported yet? Otherwise plz do... Uniquestring causes that problem and it is not fixed yet. (I made the mistake there, that I was not convinced because of sheer logic, but eventually I reached the same conclusion based on testing) With a const record I can not reproduce it with trunk 331-r42017 on armhf. ---------------------------------------------------------------------- PascalDragon · 2019-05-07 07:20 Hmm, it seems that the compiler does not generate the finalizer for the unit (or program) if there are only local constants. If I add a global constant then the finalizer is generated for both the global constant and the local one. Please file a bug, preferably with the example by ASerge. ---------------------------------------------------------------------- ASerge · 2019-05-07 16:31 This is true for all managed types: Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i procedure Test;const  Leak: TBoundArray = nil;begin  SetLength(Leak, 10);end;Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i procedure Test;const  Leak: IInterface = nil;begin  Leak := TInterfacedObject.Create as IInterface;end; ---------------------------------------------------------------------- Thausand · 2019-05-07 19:40 Quote from: PascalDragon on May 07, 2019, 09:20:58 amHmm, it seems that the compiler does not generate the finalizer for the unit (or program) if there are only local constants. If I add a global constant then the finalizer is generated for both the global constant and the local one. Maybe i no read correct (then i sorry). If make add: Code: [Select]const   SomeConst = 'some thing';   .... Then have leak no remove example my. Then you write no correct ? I write maybe important i test freepascal release 3.0.4 QuotePlease file a bug, preferably with the example by ASerge. If is bug then i can ask some one can maybe make report bug ? I make very bad english write. I make sure write: my program have leak use freepascal release 3.0.4 (install lazarus release 2) ---------------------------------------------------------------------- ASerge · 2019-05-07 20:38 https://bugs.freepascal.org/view.php?id=35536 ---------------------------------------------------------------------- Thausand · 2019-05-07 21:09 @ASerge: very many thank you ASerge  I not can have write me that many good report