Sunday, March 01, 2009


The ru_maxrss field in struct rusage provides a convenient way to measure peak memory usage of a program (via getrusage, wait4, or simply `/usr/bin/time -p') on BSD systems, including Mac OS X. According the man page, ru_maxrss represents `the maximum resident set size utilized (in kilobytes)'.

Let's try it on Mac OS X (Leopard, 10.5.6).
$ /usr/bin/time -l uname -v
Darwin Kernel Version 9.6.0: Mon Nov 24 17:37:00 PST 2008; root:xnu-1228.9.59~1/RELEASE_I386
0.00 real 0.00 user 0.00 sys
385024 maximum resident set size

Do you really think the simple `uname' could take 385,024 KB (376 MB) memory ? It also reports 282624 maxrss for a small C program that only contains an empty main and is compiled by `gcc -O2'.

Here is a comparison.

FreeBSD 7.1, kern_clock.c
 527 rss = pgtok(vmspace_resident_count(vm));
528 if (ru->ru_maxrss < rss)
529 ru->ru_maxrss = rss;
Note pgtok is often defined as follows.
#define pgtok(x) ((unsigned long)(x) * (PAGE_SIZE / 1024))

Mac OS X 10.5.6, kern_exit.c
 612 p->p_ru->ru_maxrss = tinfo.resident_size;
1205 if (flavor == TASK_BASIC2_INFO_32) {
1210 basic_info->resident_size = pmap_resident_max(...);
1211 } else {
1212 basic_info->resident_size = pmap_resident_count(...);
1213 }
1214 basic_info->resident_size *= PAGE_SIZE;

Does Apple forget `/ 1024' or something? Hope Linux would not give a strange number.


eugenek said...
This comment has been removed by the author.
eugenek said...

Is this still an issue? I am getting crazy results for ru_maxrss, even under kernel 10.4.0. Dividing by 1024 does seem to produce more reasonable numbers.

Andy Fingerhut said...

According to this is a bug in the documentation. The number is in units of bytes, not kilobytes, on Mac OS X.