gnatmem makes use of the output created by the special version of
allocation and deallocation routines that record call information. This
allows to obtain accurate dynamic memory usage history at a minimal cost to
the execution speed. Note however, that
gnatmem is not supported on
all platforms (currently, it is supported on AIX, HP-UX, GNU/Linux,
Solaris and Windows NT/2000/XP (x86).
gnatmem command has the form
$ gnatmem [switches] user_program
The program must have been linked with the instrumented version of the allocation and deallocation routines. This is done by linking with the libgmem.a library. For correct symbolic backtrace information, the user program should be compiled with debugging options (see Switches for gcc). For example to build my_program:
$ gnatmake -g my_program -largs -lgmem
As library libgmem.a contains an alternate body for package
System.Memory, s-memory.adb should not be compiled and linked
when an executable is linked with library libgmem.a. It is then not
recommended to use gnatmake with switch -a.
When my_program is executed, the file gmem.out is produced.
This file contains information about all allocations and deallocations
performed by the program. It is produced by the instrumented allocations and
deallocations routines and will be used by
In order to produce symbolic backtrace information for allocations and deallocations performed by the GNAT run-time library, you need to use a version of that library that has been compiled with the -g switch (see Rebuilding the GNAT Run-Time Library).
Gnatmem must be supplied with the gmem.out file and the executable to
examine. If the location of gmem.out file was not explicitly supplied by
-i switch, gnatmem will assume that this file can be found in the
current directory. For example, after you have executed my_program,
gmem.out can be analyzed by
gnatmem using the command:
$ gnatmem my_program
This will produce the output with the following format:
*************** debut cc
$ gnatmem my_program Global information ------------------ Total number of allocations : 45 Total number of deallocations : 6 Final Water Mark (non freed mem) : 11.29 Kilobytes High Water Mark : 11.40 Kilobytes . . . Allocation Root # 2 ------------------- Number of non freed allocations : 11 Final Water Mark (non freed mem) : 1.16 Kilobytes High Water Mark : 1.27 Kilobytes Backtrace : my_program.adb:23 my_program.alloc . . .
The first block of output gives general information. In this case, the Ada construct “new” was executed 45 times, and only 6 calls to an Unchecked_Deallocation routine occurred.
Subsequent paragraphs display information on all allocation roots. An allocation root is a specific point in the execution of the program that generates some dynamic allocation, such as a “new” construct. This root is represented by an execution backtrace (or subprogram call stack). By default the backtrace depth for allocations roots is 1, so that a root corresponds exactly to a source location. The backtrace can be made deeper, to make the root more specific.