An article teaches you how to check Net memory leak

Time:2022-6-17

preface

Memory leakage usually means that after an application completes its life cycle, some objects are accidentally referenced by other objects, resulting in subsequent GC failure to recycle them. In the long run, it will lead to program performance degradation and potential OutOfMemoryException.

In this article, we use a memory leak tool Net core program for memory leak analysis. If the program is running on windows, you can directly use visual studio for diagnosis.

Check managed memory usage

Before analyzing the memory leak, you must have evidence to prove that there is a memory leak. Here, you can use dotnet counters to check the various indicators of the application.

Run the program


dotnet run

Find the PID of the program,


dotnet-counters ps

4807 DiagnosticScena /home/user/git/samples/core/diagnostics/DiagnosticScenarios/bin/Debug/netcoreapp3.0/DiagnosticScenarios

Use monitor to start the monitor. Here –refresh interval means refresh interval


dotnet-counters monitor --refresh-interval 1 -p 4807
Press p to pause, r to resume, q to quit.
    Status: Running

[System.Runtime]
    # of Assemblies Loaded                           118
    % Time in GC (since last GC)                       0
    Allocation Rate (Bytes / sec)                 37,896
    CPU Usage (%)                                      0
    Exceptions / sec                                   0
    GC Heap Size (MB)                                  4
    Gen 0 GC / sec                                     0
    Gen 0 Size (B)                                     0
    Gen 1 GC / sec                                     0
    Gen 1 Size (B)                                     0
    Gen 2 GC / sec                                     0
    Gen 2 Size (B)                                     0
    LOH Size (B)                                       0
    Monitor Lock Contention Count / sec                0
    Number of Active Timers                            1
    ThreadPool Completed Work Items / sec             10
    ThreadPool Queue Length                            0
    ThreadPool Threads Count                           1
    Working Set (MB)                                  83

Focus on the GC heap size (MB) indicator. You can see that the current GC heap memory is 4m after the program is started. Open the link: https://localhost:5001/api/diagscenario/memleak/20000 Then look at the GC heap memory. You can see that it is 30m at once, as shown below:

  GC Heap Size (MB)                                 30

By comparing the use of memory, it can be said to confirm the memory leak.

Generate dump file

To analyze the memory leak of a program, you must first have access to the GC heap, so that you can analyze the heap memory and the relationship between objects, and then you can boldly guess why the memory has not been released? To generate Net core program dump file, with the help of dotnet dump tool.


dotnet-dump collect -p 4807
Writing minidump with heap to ./core_20190430_185145
Complete

Analyze core dump

Next, you can use dotnet dump analyze to analyze the generated dump file.


dotnet-dump analyze core_20190430_185145

Core here_ 20190430_ 185145 is the dump name you want to analyze. It is worth mentioning that if you encounter libdl So cannot be found error. It is recommended to install the libc6 dev package.

First, we use the SOS command to view the statistical list of all objects on the managed heap.


> dumpheap -stat

Statistics:
              MT    Count    TotalSize Class Name
...
00007f6c1eeefba8      576        59904 System.Reflection.RuntimeMethodInfo
00007f6c1dc021c8     1749        95696 System.SByte[]
00000000008c9db0     3847       116080      Free
00007f6c1e784a18      175       128640 System.Char[]
00007f6c1dbf5510      217       133504 System.Object[]
00007f6c1dc014c0      467       416464 System.Byte[]
00007f6c21625038        6      4063376 testwebapi.Controllers.Customer[]
00007f6c20a67498   200000      4800000 testwebapi.Controllers.Customer
00007f6c1dc00f90   206770     19494060 System.String
Total 428516 objects

 

From the output, most of them are string and customer objects. Then you can get all the instance objects under the method table through the MT parameter.


> dumpheap -mt 00007faddaa50f90

         Address               MT     Size
...
00007f6ad09421f8 00007faddaa50f90       94
...
00007f6ad0965b20 00007f6c1dc00f90       80
00007f6ad0965c10 00007f6c1dc00f90       80
00007f6ad0965d00 00007f6c1dc00f90       80
00007f6ad0965df0 00007f6c1dc00f90       80
00007f6ad0965ee0 00007f6c1dc00f90       80

Statistics:
              MT    Count    TotalSize Class Name
00007f6c1dc00f90   206770     19494060 System.String
Total 206770 objects

You can use it next! Gcroot checks who owns a string?


> gcroot -all 00007f6ad09421f8

Thread 3f68:
    00007F6795BB58A0 00007F6C1D7D0745 System.Diagnostics.Tracing.CounterGroup.PollForValues() [/_/src/System.Private.CoreLib/shared/System/Diagnostics/Tracing/CounterGroup.cs @ 260]
        rbx:  (interior)
            ->  00007F6BDFFFF038 System.Object[]
            ->  00007F69D0033570 testwebapi.Controllers.Processor
            ->  00007F69D0033588 testwebapi.Controllers.CustomerCache
            ->  00007F69D00335A0 System.Collections.Generic.List`1[[testwebapi.Controllers.Customer, DiagnosticScenarios]]
            ->  00007F6C000148A0 testwebapi.Controllers.Customer[]
            ->  00007F6AD0942258 testwebapi.Controllers.Customer
            ->  00007F6AD09421F8 System.String

HandleTable:
    00007F6C98BB15F8 (pinned handle)
    -> 00007F6BDFFFF038 System.Object[]
    -> 00007F69D0033570 testwebapi.Controllers.Processor
    -> 00007F69D0033588 testwebapi.Controllers.CustomerCache
    -> 00007F69D00335A0 System.Collections.Generic.List`1[[testwebapi.Controllers.Customer, DiagnosticScenarios]]
    -> 00007F6C000148A0 testwebapi.Controllers.Customer[]
    -> 00007F6AD0942258 testwebapi.Controllers.Customer
    -> 00007F6AD09421F8 System.String

Found 2 roots.

From the reference chain of string, it is held by customercache, and then you can find problems in the code.

Original link: https://docs.microsoft.com/en-us/dotnet/core/diagnostics/debug-memory-leak

summary

This is about how to check Net memory leak, more related troubleshooting Net memory leak content, please search the previous articles of developeppaer or continue to browse the related articles below. I hope you can support developeppaer in the future!

Recommended Today

JVM knowledge summary

This article is a summary of the study. The first is to sort out the knowledge points and summarize them. The second is to share and communicate. If there are mistakes, please point out them.[References] 1、https://blog.csdn.net/qq_41701956/article/details/81664921 2、https://blog.csdn.net/qq_41701956/article/details/80020103 3、https://mp.weixin.qq.com/s?__biz=MzI4NDY5Mjc1Mg==&mid=2247484038&idx=1&sn=e083cc8b248461c8916a819119b059c3&chksm=ebf6daf9dc8153ef27ecd857e6cc85372735e84042679c133892d0993074371a46dd2c28b8b3&scene=21#wechat_redirect JVM (Java virtual machine) The cross platform feature of Java programs mainly means that bytecode files can […]