1N/A/*
1N/A * Copyright (c) 2005-2007 Sendmail, Inc. and its suppliers.
1N/A * All rights reserved.
1N/A *
1N/A * By using this file, you agree to the terms and conditions set
1N/A * forth in the LICENSE file which can be found at the top level of
1N/A * the sendmail distribution.
1N/A */
1N/A
1N/A#pragma ident "%Z%%M% %I% %E% SMI"
1N/A
1N/A#include <sm/gen.h>
1N/ASM_RCSID("@(#)$Id: memstat.c,v 1.6 2007/03/20 23:26:12 ca Exp $")
1N/A
1N/A#include <errno.h>
1N/A#include <sm/misc.h>
1N/A
1N/A#if USESWAPCTL
1N/A#include <sys/stat.h>
1N/A#include <sys/swap.h>
1N/A
1N/Astatic long sc_page_size;
1N/A
1N/A/*
1N/A** SM_MEMSTAT_OPEN -- open memory statistics
1N/A**
1N/A** Parameters:
1N/A** none
1N/A**
1N/A** Results:
1N/A** errno as error code, 0: ok
1N/A*/
1N/A
1N/Aint
1N/Asm_memstat_open()
1N/A{
1N/A sc_page_size = sysconf(_SC_PAGE_SIZE);
1N/A if (sc_page_size == -1)
1N/A return (errno != 0) ? errno : -1;
1N/A return 0;
1N/A}
1N/A
1N/A/*
1N/A** SM_MEMSTAT_CLOSE -- close memory statistics
1N/A**
1N/A** Parameters:
1N/A** none
1N/A**
1N/A** Results:
1N/A** errno as error code, 0: ok
1N/A*/
1N/A
1N/Aint
1N/Asm_memstat_close()
1N/A{
1N/A return 0;
1N/A}
1N/A
1N/A/*
1N/A** SM_MEMSTAT_GET -- get memory statistics
1N/A**
1N/A** Parameters:
1N/A** resource -- resource to look up
1N/A** pvalue -- (pointer to) memory statistics value (output)
1N/A**
1N/A** Results:
1N/A** 0: success
1N/A** !=0: error
1N/A*/
1N/A
1N/Aint
1N/Asm_memstat_get(resource, pvalue)
1N/A char *resource;
1N/A long *pvalue;
1N/A{
1N/A int r;
1N/A struct anoninfo ai;
1N/A
1N/A r = swapctl(SC_AINFO, &ai);
1N/A if (r == -1)
1N/A return (errno != 0) ? errno : -1;
1N/A r = ai.ani_max - ai.ani_resv;
1N/A r *= sc_page_size >> 10;
1N/A *pvalue = r;
1N/A return 0;
1N/A}
1N/A
1N/A#elif USEKSTAT
1N/A
1N/A#include <kstat.h>
1N/A#include <sys/sysinfo.h>
1N/A
1N/Astatic kstat_ctl_t *kc;
1N/Astatic kstat_t *kst;
1N/A
1N/A/*
1N/A** SM_MEMSTAT_OPEN -- open memory statistics
1N/A**
1N/A** Parameters:
1N/A** none
1N/A**
1N/A** Results:
1N/A** errno as error code, 0: ok
1N/A*/
1N/A
1N/Aint
1N/Asm_memstat_open()
1N/A{
1N/A kstat_named_t *kn;
1N/A
1N/A kc = kstat_open();
1N/A if (kc == NULL)
1N/A return (errno != 0) ? errno : -1;
1N/A kst = kstat_lookup(kc, "unix", 0,
1N/A (name != NULL) ? name : "system_pages");
1N/A if (kst == 0)
1N/A return (errno != 0) ? errno : -2;
1N/A return 0;
1N/A}
1N/A
1N/A/*
1N/A** SM_MEMSTAT_CLOSE -- close memory statistics
1N/A**
1N/A** Parameters:
1N/A** none
1N/A**
1N/A** Results:
1N/A** errno as error code, 0: ok
1N/A*/
1N/A
1N/Aint
1N/Asm_memstat_close()
1N/A{
1N/A int r;
1N/A
1N/A if (kc == NULL)
1N/A return 0;
1N/A r = kstat_close(kc);
1N/A if (r != 0)
1N/A return (errno != 0) ? errno : -1;
1N/A return 0;
1N/A}
1N/A
1N/A/*
1N/A** SM_MEMSTAT_GET -- get memory statistics
1N/A**
1N/A** Parameters:
1N/A** resource -- resource to look up
1N/A** pvalue -- (pointer to) memory statistics value (output)
1N/A**
1N/A** Results:
1N/A** 0: success
1N/A** !=0: error
1N/A*/
1N/A
1N/Aint
1N/Asm_memstat_get(resource, pvalue)
1N/A char *resource;
1N/A long *pvalue;
1N/A{
1N/A int r;
1N/A kstat_named_t *kn;
1N/A
1N/A if (kc == NULL || kst == NULL)
1N/A return -1;
1N/A if (kstat_read(kc, kst, NULL) == -1)
1N/A return (errno != 0) ? errno : -2;
1N/A kn = kstat_data_lookup(kst,
1N/A (resource != NULL) ? resource: "freemem");
1N/A if (kn == NULL)
1N/A return (errno != 0) ? errno : -3;
1N/A *pvalue = kn->value.ul;
1N/A return 0;
1N/A}
1N/A
1N/A#elif USEPROCMEMINFO
1N/A
1N/A/*
1N/A/proc/meminfo?
1N/A total: used: free: shared: buffers: cached:
1N/AMem: 261468160 252149760 9318400 0 3854336 109813760
1N/ASwap: 1052794880 62185472 990609408
1N/AMemTotal: 255340 kB
1N/AMemFree: 9100 kB
1N/AMemShared: 0 kB
1N/ABuffers: 3764 kB
1N/ACached: 107240 kB
1N/AActive: 104340 kB
1N/AInact_dirty: 4220 kB
1N/AInact_clean: 2444 kB
1N/AInact_target: 4092 kB
1N/AHighTotal: 0 kB
1N/AHighFree: 0 kB
1N/ALowTotal: 255340 kB
1N/ALowFree: 9100 kB
1N/ASwapTotal: 1028120 kB
1N/ASwapFree: 967392 kB
1N/A*/
1N/A
1N/A#include <stdio.h>
1N/A#include <string.h>
1N/Astatic FILE *fp;
1N/A
1N/A/*
1N/A** SM_MEMSTAT_OPEN -- open memory statistics
1N/A**
1N/A** Parameters:
1N/A** none
1N/A**
1N/A** Results:
1N/A** errno as error code, 0: ok
1N/A*/
1N/A
1N/Aint
1N/Asm_memstat_open()
1N/A{
1N/A fp = fopen("/proc/meminfo", "r");
1N/A return (fp != NULL) ? 0 : errno;
1N/A}
1N/A
1N/A/*
1N/A** SM_MEMSTAT_CLOSE -- close memory statistics
1N/A**
1N/A** Parameters:
1N/A** none
1N/A**
1N/A** Results:
1N/A** errno as error code, 0: ok
1N/A*/
1N/A
1N/Aint
1N/Asm_memstat_close()
1N/A{
1N/A if (fp != NULL)
1N/A {
1N/A fclose(fp);
1N/A fp = NULL;
1N/A }
1N/A return 0;
1N/A}
1N/A
1N/A/*
1N/A** SM_MEMSTAT_GET -- get memory statistics
1N/A**
1N/A** Parameters:
1N/A** resource -- resource to look up
1N/A** pvalue -- (pointer to) memory statistics value (output)
1N/A**
1N/A** Results:
1N/A** 0: success
1N/A** !=0: error
1N/A*/
1N/A
1N/Aint
1N/Asm_memstat_get(resource, pvalue)
1N/A char *resource;
1N/A long *pvalue;
1N/A{
1N/A int r;
1N/A size_t l;
1N/A char buf[80];
1N/A
1N/A if (resource == NULL)
1N/A return EINVAL;
1N/A if (pvalue == NULL)
1N/A return EINVAL;
1N/A if (fp == NULL)
1N/A return -1; /* try to reopen? */
1N/A rewind(fp);
1N/A l = strlen(resource);
1N/A if (l >= sizeof(buf))
1N/A return EINVAL;
1N/A while (fgets(buf, sizeof(buf), fp) != NULL)
1N/A {
1N/A if (strncmp(buf, resource, l) == 0 && buf[l] == ':')
1N/A {
1N/A r = sscanf(buf + l + 1, "%ld", pvalue);
1N/A return (r > 0) ? 0 : -1;
1N/A }
1N/A }
1N/A return 0;
1N/A}
1N/A
1N/A#else /* USEPROCMEMINFO */
1N/A
1N/A/*
1N/A** SM_MEMSTAT_OPEN -- open memory statistics
1N/A**
1N/A** Parameters:
1N/A** none
1N/A**
1N/A** Results:
1N/A** errno as error code, 0: ok
1N/A*/
1N/A
1N/Aint
1N/Asm_memstat_open()
1N/A{
1N/A return -1;
1N/A}
1N/A
1N/A/*
1N/A** SM_MEMSTAT_CLOSE -- close memory statistics
1N/A**
1N/A** Parameters:
1N/A** none
1N/A**
1N/A** Results:
1N/A** errno as error code, 0: ok
1N/A*/
1N/A
1N/Aint
1N/Asm_memstat_close()
1N/A{
1N/A return 0;
1N/A}
1N/A
1N/A/*
1N/A** SM_MEMSTAT_GET -- get memory statistics
1N/A**
1N/A** Parameters:
1N/A** resource -- resource to look up
1N/A** pvalue -- (pointer to) memory statistics value (output)
1N/A**
1N/A** Results:
1N/A** 0: success
1N/A** !=0: error
1N/A*/
1N/A
1N/Aint
1N/Asm_memstat_get(resource, pvalue)
1N/A char *resource;
1N/A long *pvalue;
1N/A{
1N/A return -1;
1N/A}
1N/A
1N/A#endif /* USEKSTAT */