
// #ifdef __FreeBSD__
// 
// #include <sys/types.h>
// #include <sys/time.h>
// #include <sys/resource.h>
// 
// long get_os_heap_size (void)
// {
//     struct rusage r;
//     memset (&r, '\0', sizeof (r));
//     getrusage (RUSAGE_SELF, &r);
//     return r.ru_idrss;
// }
// 
// #else

#include <sys/types.h>
#include <sys/stat.h>
#include <unistd.h>
#include <fcntl.h>

long find_field (const char *field, const char *buf)
{
    const char *p;
    p = strstr (buf, field);
    if (!p)
        return -1;
    p += strlen (field);
    while (*p && *p <= ' ')
        p++;
    if (!*p)
        return -1;
    return atol (p);
}

long get_os_heap_size (void)
{
    char buf[65536];
    int buflen = 0;
#ifdef __FreeBSD__
    char dfw[256];
    FILE *p;
    snprintf (dfw, sizeof (dfw), "ps -o vsz %ld", (long) getpid ());
    p = popen (dfw, "r");
    assert (p);
    for (;;) {
        int r;
        r = fread (buf + buflen, 1, sizeof (buf) - buflen, p);
        if (r <= 0)
            break;
        buflen += r;
    }
    pclose (p);
    buf[sizeof (buf) - 1] = '\0';
    return find_field ("VSZ", buf);
#else
    char dfw[256];
    int fd;
    snprintf (dfw, sizeof (dfw), "/proc/%ld/status", (long) getpid ());
    fd = open (dfw, O_RDONLY);
    assert (fd >= 0);
    for (;;) {
        int r;
        r = read (fd, buf + buflen, sizeof (buf) - buflen);
        if (r <= 0)
            break;
        buflen += r;
    }
    close (fd);
    buf[sizeof (buf) - 1] = '\0';
    return find_field ("VmRSS:", buf);
#endif
}

// #endif

