Transferred from: https://www.cnblogs.com/arnoldlu/p/10827884.html
Key words: MALLOC_CHECK_, mtrace(),muntrace(),MALLOC_TRACE, mprobe(), - lmcheck, and so on.
1. MALLOC_CHECK_ Environment variable (double free)
MALLOC_CHECK_ It provides functions similar to mcheck() and mprobe() functions, but there is no need to modify and recompile the program.
Setting different integer values can control how the program responds to memory allocation errors.
0 - no error messages are generated and the program is not aborted
1 - generates an error message, but does not abort the program
2 - no error message is generated, but the program is aborted
3 - generate an error message and abort the program
Here is a double free error program to verify:
#include <stdio.h> #include <malloc.h> void main(void) { char *s = NULL; s = malloc(32); free(s); free(s); }
env MALLOC_ CHECK_= 0 ./ The effect of dfree is similar to direct execution/ dfree.
env MALLOC_CHECK_=1 ./dfree generates the following error message:
*** Error in `./dfree': free(): invalid pointer: 0x0000000000e22010 ***
env MALLOC_CHECK_=2 ./dfree simply terminates the program and generates the coredump file.
Aborted (core dumped)
By analyzing the core file and bt full viewing the backtrace:
(gdb) bt full #0 0x00007fb4cd69c428 in __GI_raise (sig=sig@entry=6) at ../sysdeps/unix/sysv/linux/raise.c:54 resultvar = 0 pid = 3415 selftid = 3415 #1 0x00007fb4cd69e02a in __GI_abort () at abort.c:89 save_stage = 2 act = {__sigaction_handler = {sa_handler = 0x0, sa_sigaction = 0x0}, sa_mask = {__val = {0 <repeats 14 times>, 1095216660480, 0}}, sa_flags = 0, sa_restorer = 0x0} sigs = {__val = {32, 0 <repeats 15 times>}} #2 0x00007fb4cd6e6430 in malloc_printerr (ar_ptr=<optimized out>, ptr=<optimized out>, str=<optimized out>, action=<optimized out>) at malloc.c:5010 No locals. #3 free_check (mem=<optimized out>, caller=<optimized out>) at hooks.c:314 No locals. #4 0x00007fb4cd6eb5e7 in __GI___libc_free (mem=<optimized out>) at malloc.c:2942 ar_ptr = <optimized out> p = <optimized out> hook = <optimized out> #5 0x000000000040059c in main () No symbol table info available.
env MALLOC_CHECK_=3 ./dfree displays more information and coredump.
*** Error in `./dfree': free(): invalid pointer: 0x0000000000aa0010 *** ======= Backtrace: =========--------------------------------------------------------------------Problem point backtrace. /lib/x86_64-linux-gnu/libc.so.6(+0x777e5)[0x7f640d3447e5] /lib/x86_64-linux-gnu/libc.so.6(+0x7f72a)[0x7f640d34c72a] /lib/x86_64-linux-gnu/libc.so.6(cfree+0xf7)[0x7f640d3515e7] ./dfree[0x40059c] /lib/x86_64-linux-gnu/libc.so.6(__libc_start_main+0xf0)[0x7f640d2ed830] ./dfree[0x400499] ======= Memory map: ========---------------------------------------------------------------------Of the current process maps. 00400000-00401000 r-xp 00000000 08:11 33178794 /home/al/test/dfree 00600000-00601000 r--p 00000000 08:11 33178794 /home/al/test/dfree 00601000-00602000 rw-p 00001000 08:11 33178794 /home/al/test/dfree 00aa0000-00ac1000 rw-p 00000000 00:00 0 [heap] 7f640d0b7000-7f640d0cd000 r-xp 00000000 08:02 4199205 /lib/x86_64-linux-gnu/libgcc_s.so.1 7f640d0cd000-7f640d2cc000 ---p 00016000 08:02 4199205 /lib/x86_64-linux-gnu/libgcc_s.so.1 7f640d2cc000-7f640d2cd000 rw-p 00015000 08:02 4199205 /lib/x86_64-linux-gnu/libgcc_s.so.1 7f640d2cd000-7f640d48d000 r-xp 00000000 08:02 4199167 /lib/x86_64-linux-gnu/libc-2.23.so 7f640d48d000-7f640d68d000 ---p 001c0000 08:02 4199167 /lib/x86_64-linux-gnu/libc-2.23.so 7f640d68d000-7f640d691000 r--p 001c0000 08:02 4199167 /lib/x86_64-linux-gnu/libc-2.23.so 7f640d691000-7f640d693000 rw-p 001c4000 08:02 4199167 /lib/x86_64-linux-gnu/libc-2.23.so 7f640d693000-7f640d697000 rw-p 00000000 00:00 0 7f640d697000-7f640d6bd000 r-xp 00000000 08:02 4199139 /lib/x86_64-linux-gnu/ld-2.23.so 7f640d890000-7f640d893000 rw-p 00000000 00:00 0 7f640d8bb000-7f640d8bc000 rw-p 00000000 00:00 0 7f640d8bc000-7f640d8bd000 r--p 00025000 08:02 4199139 /lib/x86_64-linux-gnu/ld-2.23.so 7f640d8bd000-7f640d8be000 rw-p 00026000 08:02 4199139 /lib/x86_64-linux-gnu/ld-2.23.so 7f640d8be000-7f640d8bf000 rw-p 00000000 00:00 0 7ffc0fb27000-7ffc0fb49000 rw-p 00000000 00:00 0 [stack] 7ffc0fbb2000-7ffc0fbb5000 r--p 00000000 00:00 0 [vvar] 7ffc0fbb5000-7ffc0fbb7000 r-xp 00000000 00:00 0 [vdso] ffffffffff600000-ffffffffff601000 r-xp 00000000 00:00 0 [vsyscall] Aborted (core dumped)
The following is the detailed stack information:
#0 0x00007f640d302428 in __GI_raise (sig=sig@entry=6) at ../sysdeps/unix/sysv/linux/raise.c:54 resultvar = 0 pid = 3542 selftid = 3542 #1 0x00007f640d30402a in __GI_abort () at abort.c:89 save_stage = 2 act = {__sigaction_handler = {sa_handler = 0x2070782d72203030, sa_sigaction = 0x2070782d72203030}, sa_mask = {__val = {3472328296227680304, 3467824696768081952, 2314885530818453536, 2314885530818453536, 7166204968890474528, 3544385727815773281, 4048771456345059427, 4123381033782620218, 2314885530819966513, 2314885530818453536, 3395749441387372576, 6860733171187738988, 8679965255892022326, 7091318039360988973, 8299627453906824547, 7219327610922666607}}, sa_flags = 808532278, sa_restorer = 0x48} sigs = {__val = {32, 0 <repeats 15 times>}} #2 0x00007f640d3447ea in __libc_message (do_abort=do_abort@entry=2, fmt=fmt@entry=0x7f640d45ded8 "*** Error in `%s': %s: 0x%s ***\n") at ../sysdeps/posix/libc_fatal.c:175 ap = <error reading variable ap (Attempt to dereference a generic pointer.)> fd = 3 on_2 = <optimized out> list = <optimized out> nlist = <optimized out> cp = <optimized out> written = <optimized out> #3 0x00007f640d34c72a in malloc_printerr (ar_ptr=0x7f640d691b20 <main_arena>, ptr=<optimized out>, str=0x7f640d45acaf "free(): invalid pointer", action=<optimized out>) at malloc.c:5006 buf = "0000000000aa0010" cp = <optimized out> ar_ptr = 0x7f640d691b20 <main_arena> ptr = <optimized out> str = 0x7f640d45acaf "free(): invalid pointer" action = <optimized out> #4 free_check (mem=<optimized out>, caller=<optimized out>) at hooks.c:314 No locals. #5 0x00007f640d3515e7 in __GI___libc_free (mem=<optimized out>) at malloc.c:2942 ar_ptr = <optimized out> p = <optimized out> hook = <optimized out> #6 0x000000000040059c in main () No symbol table info available.
2. mtrace/muntrace/MALLOC_ Trace (repeated release, leakage)
The mtrace() and muntrace() functions turn on and off the function of tracking memory allocation calls in the program respectively.
These two functions are associated with the environment variable malloc_ Used with trace, this variable defines the file name to write trace information.
2.1 construct test cases
Scenarios that construct malloc() but do not release:
#include <stdlib.h> #include <stdio.h> #include <mcheck.h> int main(int argc, char **argv) { mtrace(); char * p = malloc(100); free(p); p = malloc(1000); muntrace(); return 0; }
2.2 mtrace() tracking result analysis
gcc mtrace.c -o mtrace -g compile with debug information.
export MALLOC_TRACE=/home/al/test/mtrace.log sets the mtrace() information output path.
Then execute/ mtrace will be in malloc_ Generate malloc()/free() track information under trace.
= Start @ ./mtrace:[0x400624] + 0x10b4450 0x64 @ ./mtrace:[0x400634] - 0x10b4450 @ ./mtrace:[0x40063e] + 0x10b44c0 0x3e8 = End
The above information format is: @ program name: [address of memory allocation release call] + / - memory address parameter of operation.
+Indicates malloc, - indicates free.
Or log of the following types:
@Program name: (function name + offset) [memory allocation release call address] + / / < / > operation memory address parameter.
+: corresponds to a malloc() operation.
-: corresponds to a free() operation.
< / >: corresponds to a realloc() operation, which appears in pairs< Indicates the memory before release, > indicates the resu lt after application. If realloc() applies for memory for the first time, it corresponds to a + sign.
@ /usr/lib/libglib-2.0.so.0:(g_malloc+0x2a)[0x2ac7c412] + 0x2b510f50 0x3------------------------g_malloc()Application 0 x3 Byte size memory, return address is 0 x2b510f50. @ /usr/lib/libglib-2.0.so.0:(g_realloc+0x38)[0x2ac7c4cc] + 0x2b510f60 0x20----------------------g_realloc()There is no corresponding memory before the pointer, so the corresponding+. Indicates request 0 x20 Byte size memory, return address is 0 x2b510f60. @ /usr/lib/libglib-2.0.so.0:(g_free+0x20)[0x2ac7c524] - 0x2b510f40 @ /usr/lib/libglib-2.0.so.0:(g_malloc+0x2a)[0x2ac7c412] + 0x2b510f40 0xc------------------------stay g_malloc()Application 0 xc Byte size memory, return address is 0 x2b510f40. @ /usr/lib/libglib-2.0.so.0:(g_malloc+0x2a)[0x2ac7c412] + 0x2b510f88 0xc @ /usr/lib/libglib-2.0.so.0:(g_realloc+0x38)[0x2ac7c4cc] < 0x2b510f60---------------------------g_realloc()The corresponding memory already exists, so release 0 first x2b510f60 Memory. @ /usr/lib/libglib-2.0.so.0:(g_realloc+0x38)[0x2ac7c4cc] > 0x2b510f98 0x40----------------------Then re apply for 0 x40 Size of memory, return address is 0 x2b50f98. @ /usr/lib/libglib-2.0.so.0:(g_free+0x20)[0x2ac7c524] - 0x2b510f40------------------------------stay g_free()The release address in is 0 x2b510f40 Memory. @ /usr/lib/libglib-2.0.so.0:(g_realloc+0x38)[0x2ac7c4cc] < 0x2b510f98---------------------------g_realoc()Corresponding memory already exists, release 0 x2b510f98 Corresponding memory. @ /usr/lib/libglib-2.0.so.0:(g_realloc+0x38)[0x2ac7c4cc] > 0x2b513660 0x80----------------------Then re apply for 0 x80 Memory size, return address is 0 x2b513660.
Via mtrace mtrace Log can provide more readable information. The first mtrace is to parse mtrace Log tool, and the second mtrace is the test program.
Memory not freed: ----------------- Address Size Caller 0x00000000010b44c0 0x3e8 at /home/al/test/mtrace.c:13
The normal malloc()/free() information will be filtered out, leaving the leaked memory.
Address indicates the leak address, Size indicates the leak Size, and Caller indicates the leak point code location.
2.3 repeated release
The following is the repeated release problem. How will mtrace() handle it?
#include <stdio.h> #include <malloc.h> #include <mcheck.h> void main(void) { char *s = NULL; mtrace(); s = malloc(32); free(s); free(s); muntrace(); }
Execution/ dfree results are as follows:
*** Error in `./dfree': double free or corruption (fasttop): 0x000000000188b450 ***
2.4 mtrace output interpretation
mtrace output results also have some hints that may not be exceptions.
= Start [0x8048209] - 0x8064cc8 [0x8048209] - 0x8064ce0 [0x8048209] - 0x8064cf8 [0x80481eb] + 0x8064c48 0x14 [0x80481eb] + 0x8064c60 0x14 [0x80481eb] + 0x8064c78 0x14 [0x80481eb] + 0x8064c90 0x14 = End
The output results are as follows:
- 0x08064cc8 Free 2 was never alloc'd /home/drepper/tst.c:39 - 0x08064ce0 Free 3 was never alloc'd /home/drepper/tst.c:39 - 0x08064cf8 Free 4 was never alloc'd /home/drepper/tst.c:39
(-express free abnormal) (free Memory corresponding pointer) Free (In the original log Line number in) was never alloc'd (free Function call point) Memory not freed: ----------------- Address Size Caller 0x08064c48 0x14 at /home/drepper/tst.c:33 0x08064c60 0x14 at /home/drepper/tst.c:33 0x08064c78 0x14 at /home/drepper/tst.c:33 0x08064c90 0x14 at /home/drepper/tst.c:33
References:< 3.2.4.4 Interpreting the traces>.
- 0x000000000002ba00 Realloc 1109 was never alloc'd 0x2af654bc
(-Indicates release) (free Corresponding memory address) Realloc (stay log Bank of China No) was never alloc'd (free point of release)
realloc() releases memory first and then re applies for memory, which means that the corresponding alloc() is not found when realloc() releases memory.
+ 0x000000000006ea48 Alloc 17136 duplicate: 0x2b2ef800 /lib/libstdc++.so.6:(_Znwj+0x24)[0x2b2ef800]
(+express alloc()) (alloc()Memory address) Alloc (stay log Bank of China No) duplicate: (alloc()Call point)
Indicates two allocs. The requested memory address is the same. There is no free between the previous alloc() and this alloc().
3. mcheck() check memory consistency (repeated release, out of bounds)
The mcheck() function allows the program to check the consistency of allocated memory blocks.
3.1 mcheck() Introduction
#include <mcheck.h> int mcheck(void (*abortfunc)(enum mcheck_status mstatus));
After calling this function, subsequent memory allocation and release will check the memory continuity and call abortfunc after the memory continuity check fails.
Enumerator mcheck_ The status is as follows:
enum mcheck_status { MCHECK_DISABLED = -1, /* Consistency checking is not turned on. */ MCHECK_OK, /* Block is fine. */ MCHECK_FREE, /* Block freed twice. */ MCHECK_HEAD, /* Memory before the block was clobbered. */ MCHECK_TAIL /* Memory after the block was clobbered. */ };
3.2 mcheck() instance
The following example creates the error capture function abortfun(), which has three types of errors: repeat release, header overwrite, and tail overwrite.
#include <stdio.h> #include <malloc.h> #include <mcheck.h> #include <errno.h> #include <string.h> void abortfun(enum mcheck_status mstatus) { if(mstatus == MCHECK_FREE) fprintf(stderr, "Block freed twice.\n"); else if(mstatus == MCHECK_HEAD) fprintf(stderr, "Memory before the block was clobbered.\n"); else if(mstatus == MCHECK_TAIL) fprintf(stderr, "Memory after the block was clobbered.\n"); else fprintf(stderr, "Block is fine.\n"); } void main(void) { char *s = NULL; if(mcheck(abortfun) != 0) { fprintf(stderr, "mcheck:%s\n", strerror(errno)); return; } s = malloc(32); *(s-1) = 3;--------------------------Head cover. *(s+32) = 3;-------------------------Tail cover. free(s); free(s);-----------------------------Repeat release. }
After execution, the results are as follows: tail coverage and repeated release are captured, while head coverage is not captured; However, individual header overrides can be captured.
And the coredump file is generated.
Memory after the block was clobbered. Block freed twice. *** Error in `./dfree': double free or corruption (fasttop): 0x0000000000957030 *** ======= Backtrace: ========= /lib/x86_64-linux-gnu/libc.so.6(+0x777e5)[0x7fc2eac267e5] /lib/x86_64-linux-gnu/libc.so.6(+0x8037a)[0x7fc2eac2f37a] /lib/x86_64-linux-gnu/libc.so.6(cfree+0x4c)[0x7fc2eac3353c] /lib/x86_64-linux-gnu/libc.so.6(+0x87fa0)[0x7fc2eac36fa0] /lib/x86_64-linux-gnu/libc.so.6(cfree+0xf7)[0x7fc2eac335e7] ./dfree[0x40084a] /lib/x86_64-linux-gnu/libc.so.6(__libc_start_main+0xf0)[0x7fc2eabcf830] ./dfree[0x400659] ======= Memory map: ======== 00400000-00401000 r-xp 00000000 08:11 33173251 /home/al/test/dfree 00600000-00601000 r--p 00000000 08:11 33173251 /home/al/test/dfree 00601000-00602000 rw-p 00001000 08:11 33173251 /home/al/test/dfree 00957000-00978000 rw-p 00000000 00:00 0 [heap] 7fc2e4000000-7fc2e4021000 rw-p 00000000 00:00 0 7fc2e4021000-7fc2e8000000 ---p 00000000 00:00 0 7fc2ea999000-7fc2ea9af000 r-xp 00000000 08:02 4199205 /lib/x86_64-linux-gnu/libgcc_s.so.1 7fc2ea9af000-7fc2eabae000 ---p 00016000 08:02 4199205 /lib/x86_64-linux-gnu/libgcc_s.so.1 7fc2eabae000-7fc2eabaf000 rw-p 00015000 08:02 4199205 /lib/x86_64-linux-gnu/libgcc_s.so.1 7fc2eabaf000-7fc2ead6f000 r-xp 00000000 08:02 4199167 /lib/x86_64-linux-gnu/libc-2.23.so 7fc2ead6f000-7fc2eaf6f000 ---p 001c0000 08:02 4199167 /lib/x86_64-linux-gnu/libc-2.23.so 7fc2eaf6f000-7fc2eaf73000 r--p 001c0000 08:02 4199167 /lib/x86_64-linux-gnu/libc-2.23.so 7fc2eaf73000-7fc2eaf75000 rw-p 001c4000 08:02 4199167 /lib/x86_64-linux-gnu/libc-2.23.so 7fc2eaf75000-7fc2eaf79000 rw-p 00000000 00:00 0 7fc2eaf79000-7fc2eaf9f000 r-xp 00000000 08:02 4199139 /lib/x86_64-linux-gnu/ld-2.23.so 7fc2eb172000-7fc2eb175000 rw-p 00000000 00:00 0 7fc2eb19d000-7fc2eb19e000 rw-p 00000000 00:00 0 7fc2eb19e000-7fc2eb19f000 r--p 00025000 08:02 4199139 /lib/x86_64-linux-gnu/ld-2.23.so 7fc2eb19f000-7fc2eb1a0000 rw-p 00026000 08:02 4199139 /lib/x86_64-linux-gnu/ld-2.23.so 7fc2eb1a0000-7fc2eb1a1000 rw-p 00000000 00:00 0 7ffcc5840000-7ffcc5862000 rw-p 00000000 00:00 0 [stack] 7ffcc58df000-7ffcc58e2000 r--p 00000000 00:00 0 [vvar] 7ffcc58e2000-7ffcc58e4000 r-xp 00000000 00:00 0 [vdso] ffffffffff600000-ffffffffff601000 r-xp 00000000 00:00 0 [vsyscall] Aborted (core dumped)
4. mprobe()
Introduction to function format:
#include <mcheck.h> enum mcheck_status mprobe(void *ptr);
mprobe() example:
#include <stdio.h> #include <malloc.h> #include <mcheck.h> #include <errno.h> #include <string.h> void abortfun(enum mcheck_status mstatus) { if(mstatus == MCHECK_FREE) fprintf(stderr, "Block freed twice.\n"); else if(mstatus == MCHECK_HEAD) fprintf(stderr, "Memory before the block was clobbered.\n"); else if(mstatus == MCHECK_TAIL) fprintf(stderr, "Memory after the block was clobbered.\n"); else fprintf(stderr, "Block is fine.\n"); } void main(void) { char *s = NULL; if(mcheck(abortfun) != 0) { fprintf(stderr, "mcheck:%s\n", strerror(errno)); return; } s = malloc(32); mprobe(s);------------------------------correct mprobe(s-1);----------------------------Error, return MCHECK_HEAD Error type. mprobe(s+32);---------------------------Error, return MCHECK_HEAD Error type. free(s); }
Return result:
Memory before the block was clobbered. Memory before the block was clobbered.
5. -lmcheck auto start check
Add - lmcheck during compilation to check malloc()/free() without modifying the code.
#include <stdio.h> #include <malloc.h> void main(void) { char *s = NULL; s = malloc(32); free(s); free(s); }
gcc dfree.c -o dfree -lmcheck is compiled and executed/ dfree.
block freed twice Aborted (core dumped)
View coredump bt full as follows:
#0 0x00007fdf1e826428 in __GI_raise (sig=sig@entry=6) at ../sysdeps/unix/sysv/linux/raise.c:54 resultvar = 0 pid = 5719 selftid = 5719 #1 0x00007fdf1e82802a in __GI_abort () at abort.c:89 save_stage = 2 act = {__sigaction_handler = {sa_handler = 0x3065383363666637, sa_sigaction = 0x3065383363666637}, sa_mask = {__val = {8659703141076316208, 3472328296227676272, 3472339291342909488, 2314885530818457632, 2314885530818453536, 2314885530818453536, 8314900945785856032, 7378697629477789039, 3472335126135203430, 7378697628523966512, 3474076752553600614, 8659703141076316209, 3472328296227676272, 3472339291342909488, 2314885530818457632, 2314885530818453536}}, sa_flags = 538976288, sa_restorer = 0x54} sigs = {__val = {32, 0 <repeats 15 times>}} #2 0x00007fdf1e8687ea in __libc_message (do_abort=do_abort@entry=2, fmt=fmt@entry=0x7fdf1e981ed8 "*** Error in `%s': %s: 0x%s ***\n") at ../sysdeps/posix/libc_fatal.c:175 ap = <error reading variable ap (Attempt to dereference a generic pointer.)> fd = 3 on_2 = <optimized out> list = <optimized out> nlist = <optimized out> cp = <optimized out> written = <optimized out> #3 0x00007fdf1e87137a in malloc_printerr (ar_ptr=<optimized out>, ptr=<optimized out>, str=0x7fdf1e981fa0 "double free or corruption (fasttop)", action=3) at malloc.c:5006 buf = "000000000186a010" cp = <optimized out> ar_ptr = <optimized out> str = 0x7fdf1e981fa0 "double free or corruption (fasttop)" action = 3 #4 _int_free (av=<optimized out>, p=<optimized out>, have_lock=0) at malloc.c:3867 size = <optimized out> fb = <optimized out> nextchunk = <optimized out> nextsize = <optimized out> nextinuse = <optimized out> prevsize = <optimized out> bck = <optimized out> fwd = <optimized out> errstr = <optimized out> locked = <optimized out> #5 0x00007fdf1e87553c in __GI___libc_free (mem=<optimized out>) at malloc.c:2968 ar_ptr = <optimized out> p = <optimized out> hook = <optimized out> #6 0x000000000040059c in register_tm_clones () No symbol table info available. #7 0x00007ffc38dc54c0 in ?? () No symbol table info available. #8 0x000000000186a010 in ?? () No symbol table info available. #9 0x00000000004005a0 in register_tm_clones () No symbol table info available. #10 0x00007fdf1e811830 in __libc_start_main (main=0x400566 <deregister_tm_clones+54>, argc=1, argv=0x7ffc38dc54c8, init=<optimized out>, fini=<optimized out>, rtld_fini=<optimized out>, stack_end=0x7ffc38dc54b8) at ../csu/libc-start.c:291 result = <optimized out> unwind_buf = {cancel_jmp_buf = {{jmp_buf = {0, 4770583698588052314, 4195440, 140721262449856, 0, 0, -4770167831151236262, -4788811728122270886}, mask_was_saved = 0}}, priv = {pad = {0x0, 0x0, 0x400610 <main+26>, 0x7fdf1ebcbab0 <_dl_fini>}, data = {prev = 0x0, cleanup = 0x0, canceltype = 4195856}}} not_first_call = <optimized out> #11 0x0000000000400499 in ?? () No symbol table info available. #12 0x00007ffc38dc54b8 in ?? () No symbol table info available. #13 0x000000000000001c in ?? () No symbol table info available. #14 0x0000000000000001 in ?? () No symbol table info available. #15 0x00007ffc38dc5fba in ?? () No symbol table info available. #16 0x0000000000000000 in ?? () No symbol table info available.
6. Summary
Compare the above memory check methods: MALLOC_CHECK_ The simplest is - lmcheck, followed by mtrace()/muntrace(), mcheck(), mprobe().
However, these technologies are not comprehensive enough. None of them can comprehensively check memory leakage, memory trampling and repeated release.
Valgrind technology is still needed for comprehensive inspection. Please refer to< How to use valgrind>.
Reference documents:< mtrace - memory usage tracking (memory)>,<mcheck function usage (glibc-3-memory)>