TObjectList memory leak?












1














I have this code in Delphi 7:



var
Form1: TForm1;
T: TObjectList;

implementation

{$R *.dfm}

procedure TForm1.Button1Click(Sender: TObject);
var
I: Integer;
begin
T := TObjectList.Create(True);
for i := 1 to 10000 do begin
T.Add(TPersistent.Create);
end;
end;

procedure TForm1.Button2Click(Sender: TObject);
begin
FreeAndNil(T);
end;


And this in Delphi 2009:



var
Form1: TForm1;
T: TObjectList<TPersistent>;

implementation

{$R *.dfm}

procedure TForm1.Button1Click(Sender: TObject);
var
I: Integer;
begin
T := TObjectList<TPersistent>.Create(True);
for i := 1 to 10000 do begin
T.Add(TPersistent.Create);
end;
end;

procedure TForm1.Button2Click(Sender: TObject);
begin
FreeAndNil(T);
end;


According to the Task Manager, when i free T in Delphi 7, all the memory that it used is freed, but in Delphi 2009, the memory is not free and even adds extra 30 kb. Am i missing something? or is there a memory leak in TObjectList in Delphi 2009?










share|improve this question


















  • 1




    Ugh, Delphi 2009... not for this issue which obviously is none but for 100 other reasons. Get off that version as soon as you can. Especially if you want to use generics. They are terribly broken so are many other things.
    – Stefan Glienke
    Nov 22 '18 at 18:02
















1














I have this code in Delphi 7:



var
Form1: TForm1;
T: TObjectList;

implementation

{$R *.dfm}

procedure TForm1.Button1Click(Sender: TObject);
var
I: Integer;
begin
T := TObjectList.Create(True);
for i := 1 to 10000 do begin
T.Add(TPersistent.Create);
end;
end;

procedure TForm1.Button2Click(Sender: TObject);
begin
FreeAndNil(T);
end;


And this in Delphi 2009:



var
Form1: TForm1;
T: TObjectList<TPersistent>;

implementation

{$R *.dfm}

procedure TForm1.Button1Click(Sender: TObject);
var
I: Integer;
begin
T := TObjectList<TPersistent>.Create(True);
for i := 1 to 10000 do begin
T.Add(TPersistent.Create);
end;
end;

procedure TForm1.Button2Click(Sender: TObject);
begin
FreeAndNil(T);
end;


According to the Task Manager, when i free T in Delphi 7, all the memory that it used is freed, but in Delphi 2009, the memory is not free and even adds extra 30 kb. Am i missing something? or is there a memory leak in TObjectList in Delphi 2009?










share|improve this question


















  • 1




    Ugh, Delphi 2009... not for this issue which obviously is none but for 100 other reasons. Get off that version as soon as you can. Especially if you want to use generics. They are terribly broken so are many other things.
    – Stefan Glienke
    Nov 22 '18 at 18:02














1












1








1







I have this code in Delphi 7:



var
Form1: TForm1;
T: TObjectList;

implementation

{$R *.dfm}

procedure TForm1.Button1Click(Sender: TObject);
var
I: Integer;
begin
T := TObjectList.Create(True);
for i := 1 to 10000 do begin
T.Add(TPersistent.Create);
end;
end;

procedure TForm1.Button2Click(Sender: TObject);
begin
FreeAndNil(T);
end;


And this in Delphi 2009:



var
Form1: TForm1;
T: TObjectList<TPersistent>;

implementation

{$R *.dfm}

procedure TForm1.Button1Click(Sender: TObject);
var
I: Integer;
begin
T := TObjectList<TPersistent>.Create(True);
for i := 1 to 10000 do begin
T.Add(TPersistent.Create);
end;
end;

procedure TForm1.Button2Click(Sender: TObject);
begin
FreeAndNil(T);
end;


According to the Task Manager, when i free T in Delphi 7, all the memory that it used is freed, but in Delphi 2009, the memory is not free and even adds extra 30 kb. Am i missing something? or is there a memory leak in TObjectList in Delphi 2009?










share|improve this question













I have this code in Delphi 7:



var
Form1: TForm1;
T: TObjectList;

implementation

{$R *.dfm}

procedure TForm1.Button1Click(Sender: TObject);
var
I: Integer;
begin
T := TObjectList.Create(True);
for i := 1 to 10000 do begin
T.Add(TPersistent.Create);
end;
end;

procedure TForm1.Button2Click(Sender: TObject);
begin
FreeAndNil(T);
end;


And this in Delphi 2009:



var
Form1: TForm1;
T: TObjectList<TPersistent>;

implementation

{$R *.dfm}

procedure TForm1.Button1Click(Sender: TObject);
var
I: Integer;
begin
T := TObjectList<TPersistent>.Create(True);
for i := 1 to 10000 do begin
T.Add(TPersistent.Create);
end;
end;

procedure TForm1.Button2Click(Sender: TObject);
begin
FreeAndNil(T);
end;


According to the Task Manager, when i free T in Delphi 7, all the memory that it used is freed, but in Delphi 2009, the memory is not free and even adds extra 30 kb. Am i missing something? or is there a memory leak in TObjectList in Delphi 2009?







delphi






share|improve this question













share|improve this question











share|improve this question




share|improve this question










asked Nov 21 '18 at 22:17









IroncrossIroncross

184




184








  • 1




    Ugh, Delphi 2009... not for this issue which obviously is none but for 100 other reasons. Get off that version as soon as you can. Especially if you want to use generics. They are terribly broken so are many other things.
    – Stefan Glienke
    Nov 22 '18 at 18:02














  • 1




    Ugh, Delphi 2009... not for this issue which obviously is none but for 100 other reasons. Get off that version as soon as you can. Especially if you want to use generics. They are terribly broken so are many other things.
    – Stefan Glienke
    Nov 22 '18 at 18:02








1




1




Ugh, Delphi 2009... not for this issue which obviously is none but for 100 other reasons. Get off that version as soon as you can. Especially if you want to use generics. They are terribly broken so are many other things.
– Stefan Glienke
Nov 22 '18 at 18:02




Ugh, Delphi 2009... not for this issue which obviously is none but for 100 other reasons. Get off that version as soon as you can. Especially if you want to use generics. They are terribly broken so are many other things.
– Stefan Glienke
Nov 22 '18 at 18:02












3 Answers
3






active

oldest

votes


















3














Both versions do not leak. Your confusion stems from using the wrong tool to detect leaks. Memory managers tend to hang on to memory blocks that were recently used, and hope that they can be reused.



If you wish to detect memory leaks use the full FastMM library. That will show you that your code does not leak.






share|improve this answer

















  • 2




    AFAIK, in one of the latest versions, FastMM's ReportMemoryLeaksOnShutDown was moved to System.pas, and can now be used without the explicit use of the FastMM unit.
    – Rudy Velthuis
    Nov 21 '18 at 23:20










  • That's true but there is no information beyond the number of blocks leaked. Using FastMM allows you to obtain stack traces at the point of allocoof each leaked block and many other powerful debugging tools.
    – David Heffernan
    Nov 22 '18 at 7:40










  • sure, with the explicit fastMM you get much better diagnostics. But I find it useful for a quick check.
    – Rudy Velthuis
    Nov 22 '18 at 7:47



















3














Task Manager only reports the memory requested by the application through the Windows API. Delphi (just like every other compiler) has its own memory allocator that requests memory from Windows in chunks and then suballocates it as necessary. When you free a Delphi object, or a chunk of memory, it does not necessarily go back to Windows - Delphi's memory allocator simply marks the memory as free so it can be reused in subsequent memory requests. Windows knows nothing about that.



Try to create your own object and override its destructor - you can then put a breakpoint there to check that it indeed gets called.






share|improve this answer



















  • 1




    Also note that modern Delphi versions have ReportMemoryLeaksOnShutdown to detect true memory leaks from Delphi's memory allocator, as only it can know what actually constitutes a leak or not. In Delphi 7, you would have to manually install FastMM to get that same behavior.
    – Remy Lebeau
    Nov 22 '18 at 2:31





















0














There are no memory leaks. I tested both methods on Delphi XE6 and 10.2.3. I used: "ReportMemoryLeaksOnShutdown := DebugHook <> 0;" and to read memory GetProcessMemoryInfo -> WorkingSetSize.






share|improve this answer























    Your Answer






    StackExchange.ifUsing("editor", function () {
    StackExchange.using("externalEditor", function () {
    StackExchange.using("snippets", function () {
    StackExchange.snippets.init();
    });
    });
    }, "code-snippets");

    StackExchange.ready(function() {
    var channelOptions = {
    tags: "".split(" "),
    id: "1"
    };
    initTagRenderer("".split(" "), "".split(" "), channelOptions);

    StackExchange.using("externalEditor", function() {
    // Have to fire editor after snippets, if snippets enabled
    if (StackExchange.settings.snippets.snippetsEnabled) {
    StackExchange.using("snippets", function() {
    createEditor();
    });
    }
    else {
    createEditor();
    }
    });

    function createEditor() {
    StackExchange.prepareEditor({
    heartbeatType: 'answer',
    autoActivateHeartbeat: false,
    convertImagesToLinks: true,
    noModals: true,
    showLowRepImageUploadWarning: true,
    reputationToPostImages: 10,
    bindNavPrevention: true,
    postfix: "",
    imageUploader: {
    brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
    contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
    allowUrls: true
    },
    onDemand: true,
    discardSelector: ".discard-answer"
    ,immediatelyShowMarkdownHelp:true
    });


    }
    });














    draft saved

    draft discarded


















    StackExchange.ready(
    function () {
    StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53421218%2ftobjectlistt-memory-leak%23new-answer', 'question_page');
    }
    );

    Post as a guest















    Required, but never shown

























    3 Answers
    3






    active

    oldest

    votes








    3 Answers
    3






    active

    oldest

    votes









    active

    oldest

    votes






    active

    oldest

    votes









    3














    Both versions do not leak. Your confusion stems from using the wrong tool to detect leaks. Memory managers tend to hang on to memory blocks that were recently used, and hope that they can be reused.



    If you wish to detect memory leaks use the full FastMM library. That will show you that your code does not leak.






    share|improve this answer

















    • 2




      AFAIK, in one of the latest versions, FastMM's ReportMemoryLeaksOnShutDown was moved to System.pas, and can now be used without the explicit use of the FastMM unit.
      – Rudy Velthuis
      Nov 21 '18 at 23:20










    • That's true but there is no information beyond the number of blocks leaked. Using FastMM allows you to obtain stack traces at the point of allocoof each leaked block and many other powerful debugging tools.
      – David Heffernan
      Nov 22 '18 at 7:40










    • sure, with the explicit fastMM you get much better diagnostics. But I find it useful for a quick check.
      – Rudy Velthuis
      Nov 22 '18 at 7:47
















    3














    Both versions do not leak. Your confusion stems from using the wrong tool to detect leaks. Memory managers tend to hang on to memory blocks that were recently used, and hope that they can be reused.



    If you wish to detect memory leaks use the full FastMM library. That will show you that your code does not leak.






    share|improve this answer

















    • 2




      AFAIK, in one of the latest versions, FastMM's ReportMemoryLeaksOnShutDown was moved to System.pas, and can now be used without the explicit use of the FastMM unit.
      – Rudy Velthuis
      Nov 21 '18 at 23:20










    • That's true but there is no information beyond the number of blocks leaked. Using FastMM allows you to obtain stack traces at the point of allocoof each leaked block and many other powerful debugging tools.
      – David Heffernan
      Nov 22 '18 at 7:40










    • sure, with the explicit fastMM you get much better diagnostics. But I find it useful for a quick check.
      – Rudy Velthuis
      Nov 22 '18 at 7:47














    3












    3








    3






    Both versions do not leak. Your confusion stems from using the wrong tool to detect leaks. Memory managers tend to hang on to memory blocks that were recently used, and hope that they can be reused.



    If you wish to detect memory leaks use the full FastMM library. That will show you that your code does not leak.






    share|improve this answer












    Both versions do not leak. Your confusion stems from using the wrong tool to detect leaks. Memory managers tend to hang on to memory blocks that were recently used, and hope that they can be reused.



    If you wish to detect memory leaks use the full FastMM library. That will show you that your code does not leak.







    share|improve this answer












    share|improve this answer



    share|improve this answer










    answered Nov 21 '18 at 22:49









    David HeffernanDavid Heffernan

    515k348151207




    515k348151207








    • 2




      AFAIK, in one of the latest versions, FastMM's ReportMemoryLeaksOnShutDown was moved to System.pas, and can now be used without the explicit use of the FastMM unit.
      – Rudy Velthuis
      Nov 21 '18 at 23:20










    • That's true but there is no information beyond the number of blocks leaked. Using FastMM allows you to obtain stack traces at the point of allocoof each leaked block and many other powerful debugging tools.
      – David Heffernan
      Nov 22 '18 at 7:40










    • sure, with the explicit fastMM you get much better diagnostics. But I find it useful for a quick check.
      – Rudy Velthuis
      Nov 22 '18 at 7:47














    • 2




      AFAIK, in one of the latest versions, FastMM's ReportMemoryLeaksOnShutDown was moved to System.pas, and can now be used without the explicit use of the FastMM unit.
      – Rudy Velthuis
      Nov 21 '18 at 23:20










    • That's true but there is no information beyond the number of blocks leaked. Using FastMM allows you to obtain stack traces at the point of allocoof each leaked block and many other powerful debugging tools.
      – David Heffernan
      Nov 22 '18 at 7:40










    • sure, with the explicit fastMM you get much better diagnostics. But I find it useful for a quick check.
      – Rudy Velthuis
      Nov 22 '18 at 7:47








    2




    2




    AFAIK, in one of the latest versions, FastMM's ReportMemoryLeaksOnShutDown was moved to System.pas, and can now be used without the explicit use of the FastMM unit.
    – Rudy Velthuis
    Nov 21 '18 at 23:20




    AFAIK, in one of the latest versions, FastMM's ReportMemoryLeaksOnShutDown was moved to System.pas, and can now be used without the explicit use of the FastMM unit.
    – Rudy Velthuis
    Nov 21 '18 at 23:20












    That's true but there is no information beyond the number of blocks leaked. Using FastMM allows you to obtain stack traces at the point of allocoof each leaked block and many other powerful debugging tools.
    – David Heffernan
    Nov 22 '18 at 7:40




    That's true but there is no information beyond the number of blocks leaked. Using FastMM allows you to obtain stack traces at the point of allocoof each leaked block and many other powerful debugging tools.
    – David Heffernan
    Nov 22 '18 at 7:40












    sure, with the explicit fastMM you get much better diagnostics. But I find it useful for a quick check.
    – Rudy Velthuis
    Nov 22 '18 at 7:47




    sure, with the explicit fastMM you get much better diagnostics. But I find it useful for a quick check.
    – Rudy Velthuis
    Nov 22 '18 at 7:47













    3














    Task Manager only reports the memory requested by the application through the Windows API. Delphi (just like every other compiler) has its own memory allocator that requests memory from Windows in chunks and then suballocates it as necessary. When you free a Delphi object, or a chunk of memory, it does not necessarily go back to Windows - Delphi's memory allocator simply marks the memory as free so it can be reused in subsequent memory requests. Windows knows nothing about that.



    Try to create your own object and override its destructor - you can then put a breakpoint there to check that it indeed gets called.






    share|improve this answer



















    • 1




      Also note that modern Delphi versions have ReportMemoryLeaksOnShutdown to detect true memory leaks from Delphi's memory allocator, as only it can know what actually constitutes a leak or not. In Delphi 7, you would have to manually install FastMM to get that same behavior.
      – Remy Lebeau
      Nov 22 '18 at 2:31


















    3














    Task Manager only reports the memory requested by the application through the Windows API. Delphi (just like every other compiler) has its own memory allocator that requests memory from Windows in chunks and then suballocates it as necessary. When you free a Delphi object, or a chunk of memory, it does not necessarily go back to Windows - Delphi's memory allocator simply marks the memory as free so it can be reused in subsequent memory requests. Windows knows nothing about that.



    Try to create your own object and override its destructor - you can then put a breakpoint there to check that it indeed gets called.






    share|improve this answer



















    • 1




      Also note that modern Delphi versions have ReportMemoryLeaksOnShutdown to detect true memory leaks from Delphi's memory allocator, as only it can know what actually constitutes a leak or not. In Delphi 7, you would have to manually install FastMM to get that same behavior.
      – Remy Lebeau
      Nov 22 '18 at 2:31
















    3












    3








    3






    Task Manager only reports the memory requested by the application through the Windows API. Delphi (just like every other compiler) has its own memory allocator that requests memory from Windows in chunks and then suballocates it as necessary. When you free a Delphi object, or a chunk of memory, it does not necessarily go back to Windows - Delphi's memory allocator simply marks the memory as free so it can be reused in subsequent memory requests. Windows knows nothing about that.



    Try to create your own object and override its destructor - you can then put a breakpoint there to check that it indeed gets called.






    share|improve this answer














    Task Manager only reports the memory requested by the application through the Windows API. Delphi (just like every other compiler) has its own memory allocator that requests memory from Windows in chunks and then suballocates it as necessary. When you free a Delphi object, or a chunk of memory, it does not necessarily go back to Windows - Delphi's memory allocator simply marks the memory as free so it can be reused in subsequent memory requests. Windows knows nothing about that.



    Try to create your own object and override its destructor - you can then put a breakpoint there to check that it indeed gets called.







    share|improve this answer














    share|improve this answer



    share|improve this answer








    edited Nov 22 '18 at 2:28









    Remy Lebeau

    332k18251443




    332k18251443










    answered Nov 21 '18 at 22:32









    Dmitry StreblechenkoDmitry Streblechenko

    42.4k32760




    42.4k32760








    • 1




      Also note that modern Delphi versions have ReportMemoryLeaksOnShutdown to detect true memory leaks from Delphi's memory allocator, as only it can know what actually constitutes a leak or not. In Delphi 7, you would have to manually install FastMM to get that same behavior.
      – Remy Lebeau
      Nov 22 '18 at 2:31
















    • 1




      Also note that modern Delphi versions have ReportMemoryLeaksOnShutdown to detect true memory leaks from Delphi's memory allocator, as only it can know what actually constitutes a leak or not. In Delphi 7, you would have to manually install FastMM to get that same behavior.
      – Remy Lebeau
      Nov 22 '18 at 2:31










    1




    1




    Also note that modern Delphi versions have ReportMemoryLeaksOnShutdown to detect true memory leaks from Delphi's memory allocator, as only it can know what actually constitutes a leak or not. In Delphi 7, you would have to manually install FastMM to get that same behavior.
    – Remy Lebeau
    Nov 22 '18 at 2:31






    Also note that modern Delphi versions have ReportMemoryLeaksOnShutdown to detect true memory leaks from Delphi's memory allocator, as only it can know what actually constitutes a leak or not. In Delphi 7, you would have to manually install FastMM to get that same behavior.
    – Remy Lebeau
    Nov 22 '18 at 2:31













    0














    There are no memory leaks. I tested both methods on Delphi XE6 and 10.2.3. I used: "ReportMemoryLeaksOnShutdown := DebugHook <> 0;" and to read memory GetProcessMemoryInfo -> WorkingSetSize.






    share|improve this answer




























      0














      There are no memory leaks. I tested both methods on Delphi XE6 and 10.2.3. I used: "ReportMemoryLeaksOnShutdown := DebugHook <> 0;" and to read memory GetProcessMemoryInfo -> WorkingSetSize.






      share|improve this answer


























        0












        0








        0






        There are no memory leaks. I tested both methods on Delphi XE6 and 10.2.3. I used: "ReportMemoryLeaksOnShutdown := DebugHook <> 0;" and to read memory GetProcessMemoryInfo -> WorkingSetSize.






        share|improve this answer














        There are no memory leaks. I tested both methods on Delphi XE6 and 10.2.3. I used: "ReportMemoryLeaksOnShutdown := DebugHook <> 0;" and to read memory GetProcessMemoryInfo -> WorkingSetSize.







        share|improve this answer














        share|improve this answer



        share|improve this answer








        edited Nov 22 '18 at 0:04

























        answered Nov 21 '18 at 23:58









        janeks3janeks3

        354




        354






























            draft saved

            draft discarded




















































            Thanks for contributing an answer to Stack Overflow!


            • Please be sure to answer the question. Provide details and share your research!

            But avoid



            • Asking for help, clarification, or responding to other answers.

            • Making statements based on opinion; back them up with references or personal experience.


            To learn more, see our tips on writing great answers.




            draft saved


            draft discarded














            StackExchange.ready(
            function () {
            StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53421218%2ftobjectlistt-memory-leak%23new-answer', 'question_page');
            }
            );

            Post as a guest















            Required, but never shown





















































            Required, but never shown














            Required, but never shown












            Required, but never shown







            Required, but never shown

































            Required, but never shown














            Required, but never shown












            Required, but never shown







            Required, but never shown







            Popular posts from this blog

            404 Error Contact Form 7 ajax form submitting

            How to know if a Active Directory user can login interactively

            TypeError: fit_transform() missing 1 required positional argument: 'X'