| <- Back | |
| How to enable MALLOC_STATS in OpenBSD's libc | |
| ============================================ | |
| If you want to write sane programs in C, it's a good idea to check your | |
| program for memory leaks. OpenBSD's libc covers a neat method for | |
| thisendeavor. But it's not enabled by default. | |
| It can be enabled by recompiling libc after commenting in one line of | |
| code. | |
| You'll have to recursively fetch the libc part of the OpenBSD | |
| source-tree. To begin with, you should add your user to the groups wsrc | |
| and wobj. | |
| # useradd -G wsrc,wobj $USER | |
| You can apply these changes by logging in again with your user. The | |
| following just works within the shell it's run on. | |
| # su - $USER | |
| After this is done you will have to write access to the directory /usr/src | |
| (and /usr/obj). | |
| Change directory to /usr/src and fetch OpenBSD's source via cvs. | |
| $ cd /usr | |
| $ cvs -qd [email protected]:/cvs get -rOPENBSD_6_1 -P | |
| src/lib/libc | |
| This may take a while. | |
| Afterwards you'll have to edit malloc.c. | |
| $ vi /usr/src/lib/libc/stdlib/malloc.c | |
| find this line and remove the commenting: | |
| /* #define MALLOC_STATS */ | |
| It should be around line 26. | |
| Next you have to compile libc. This needs to be done from the | |
| folder/usr/src/lib/libc. | |
| $ cd /usr/src/lib/libc | |
| $ make obj | |
| $ make depend | |
| $ make | |
| $ make install | |
| This may take a while. | |
| On successful compilation you will rewarded with a new, modified | |
| versionof malloc(). Programs that are now compiled with this | |
| modifiedmalloc()-function are able to dump their stats. | |
| In order to achieve this, you'll have to make sure the following two | |
| things. | |
| A writable file called malloc.out has to exist in the same directory | |
| ofthe executable. And the program has to be called with the | |
| environmentvariable MALLOC_OPTIONS=D set: | |
| $ MALLOC_OPTIONS=D ./my_executable | |
| After execution the stats will be dumped into malloc.out. The bottompart | |
| of the dump is most interesting, since it contains the actual leakage | |
| information. | |
| The following is an example of one of my own programs: | |
| ******** Start dump my_executable ******* MT=0 IRC=1 F=0 U=0 J=1 R=0 X=0 | |
| C=0 cache=64 G=0 Malloc dir of my_executable pool 0 at 0x1ef309d654a0 | |
| Region slots free 507/512 Finds 74/0 Inserts 13/0 Deletes 8/0 Cheap | |
| reallocs 0/0 In use 167936 Guarded 0 Free chunk structs: | |
| 4) 54 | |
| 4) 54 chunk 0x1ef3c4c5e000 0x0 16 255/256 | |
| 4) 54 chunk 0x1ef39f5fa000 0x0 16 255/256 | |
| 4) 54 | |
| 5) 73 | |
| 5) 73 | |
| 5) 73 | |
| 5) 73 | |
| 6) 85 | |
| 6) 85 | |
| 6) 85 | |
| 6) 85 | |
| 7) 85 | |
| 7) 85 | |
| 7) 85 | |
| 7) 85 Free pages cached: 8 | |
| 2) free at 0x1ef31c4b1000: 1 18) free at 0x1ef3e1e20000: 1 26) free at | |
| 0x1ef302d90000: 1 27) free at 0x1ef3ce263000: 1 29) free at | |
| 0x1ef32d2a8000: 1 40) free at 0x1ef3af85c000: 1 43) free at | |
| 0x1ef319cdb000: 1 53) free at 0x1ef3b6a71000: 1 slot) hash d type | |
| page f size [free/n] | |
| 1c) # 1c 0 pages 0x1ef371d9a000 0x1ef2f0fb2bbc 65536 | |
| 5d) # 5d 0 chunk 0x1ef3c4c5e000 0x0 16 255/256 | |
| a4) # a4 0 pages 0x1ef3e6c99000 0x1ef2f0fb2bbc 16384 | |
| 1be) # 1be 0 chunk 0x1ef39f5fa000 0x0 16 255/256 | |
| 1ff) # 1ff 0 pages 0x1ef3a7cba000 0x1ef2f0fb2bbc 16384 Leak | |
| report | |
| f sum # avg | |
| 0x0 32 2 16 | |
| 0x1ef2f0fb2bbc 98304 3 32768 | |
| ******** End dump my_executable ******* |