Merge branches 'processes-fix' and 'solaris-fixes'
authorFlorian Forster <octo@leeloo.lan.home.verplant.org>
Sat, 17 Jun 2006 19:15:42 +0000 (21:15 +0200)
committerFlorian Forster <octo@leeloo.lan.home.verplant.org>
Sat, 17 Jun 2006 19:15:42 +0000 (21:15 +0200)
Conflicts:

src/swap.c

1  2  3 
src/swap.c

diff --cc src/swap.c
@@@@ -61,69 -61,69 -52,19 +61,69 @@@@ static char *ds_def[] 
   };
   static int ds_num = 4;
   
  -#ifdef KERNEL_SOLARIS
  +#if KERNEL_LINUX
  +/* No global variables */
  +/* #endif KERNEL_LINUX */
  +
  +#elif HAVE_LIBKSTAT
-- static int pagesize;
++ static unsigned long long pagesize;
   static kstat_t *ksp;
  -#endif /* KERNEL_SOLARIS */
  +/* #endif HAVE_LIBKSTAT */
  +
  +#elif defined(VM_SWAPUSAGE)
  +/* No global variables */
  +/* #endif defined(VM_SWAPUSAGE) */
  +
  +#elif HAVE_LIBKVM
  +static kvm_t *kvm_obj = NULL;
  +int kvm_pagesize;
  +/* #endif HAVE_LIBKVM */
  +
  +#elif HAVE_LIBSTATGRAB
  +/* No global variables */
  +#endif /* HAVE_LIBSTATGRAB */
   
   static void swap_init (void)
   {
  -#ifdef KERNEL_SOLARIS
  +#if KERNEL_LINUX
  +     /* No init stuff */
  +/* #endif KERNEL_LINUX */
  +
  +#elif HAVE_LIBKSTAT
        /* getpagesize(3C) tells me this does not fail.. */
--      pagesize = getpagesize ();
++      pagesize = (unsigned long long) getpagesize ();
        if (get_kstat (&ksp, "unix", 0, "system_pages"))
                ksp = NULL;
  -#endif /* KERNEL_SOLARIS */
  +/* #endif HAVE_LIBKSTAT */
  +
  +#elif defined(VM_SWAPUSAGE)
  +     /* No init stuff */
  +/* #endif defined(VM_SWAPUSAGE) */
  +
  +#elif HAVE_LIBKVM
  +     if (kvm_obj != NULL)
  +     {
  +             kvm_close (kvm_obj);
  +             kvm_obj = NULL;
  +     }
  +
  +     kvm_pagesize = getpagesize ();
  +
  +     if ((kvm_obj = kvm_open (NULL, /* execfile */
  +                                     NULL, /* corefile */
  +                                     NULL, /* swapfile */
  +                                     O_RDONLY, /* flags */
  +                                     NULL)) /* errstr */
  +                     == NULL)
  +     {
  +             syslog (LOG_ERR, "swap plugin: kvm_open failed.");
  +             return;
  +     }
  +/* #endif HAVE_LIBKVM */
  +
  +#elif HAVE_LIBSTATGRAB
  +     /* No init stuff */
  +#endif /* HAVE_LIBSTATGRAB */
   
        return;
   }
@@@@ -212,85 -212,85 -149,44 +208,91 @@@@ static void swap_read (void
        struct anoninfo ai;
   
        if (swapctl (SC_AINFO, &ai) == -1)
++      {
++              syslog (LOG_ERR, "swap plugin: swapctl failed: %s",
++                              strerror (errno));
                return;
++      }
   
--      availrmem      = get_kstat_value (ksp, "availrmem");
--      swapfs_minfree = get_kstat_value (ksp, "minfree");
-- 
--      if ((availrmem < 0LL) || (swapfs_minfree < 0LL))
--              return;
-- 
--      /* 
--       * Calculations learned by reading
--       * http://www.itworld.com/Comp/2377/UIR980701perf/
++      /*
++       * Calculations from:
++       * http://cvs.opensolaris.org/source/xref/on/usr/src/cmd/swap/swap.c
++       * Also see:
++       * http://www.itworld.com/Comp/2377/UIR980701perf/ (outdated?)
++       * /usr/include/vm/anon.h
++       *
++       * In short, swap -s shows: allocated + reserved = used, available
++       *
++       * However, Solaris does not allow to allocated/reserved more than the
++       * available swap (physical memory + disk swap), so the pedant may
++       * prefer: allocated + unallocated = reserved, available
++       * 
++       * We map the above to: used + resv = n/a, free
         *
--       * swap_resv += ani_resv
--       * swap_alloc += MAX(ani_resv, ani_max) - ani_free
--       * swap_avail += MAX(ani_max - ani_resv, 0) + (availrmem - swapfs_minfree)
--       * swap_free += ani_free + (availrmem - swapfs_minfree)
++       * Does your brain hurt yet?  - Christophe Kalt
         *
--       * To clear up the terminology a bit:
--       * resv  = reserved (but not neccessarily used)
--       * alloc = used     (neccessarily reserved)
--       * avail = not reserved  (neccessarily free)
--       * free  = not allocates (possibly reserved)
++       * Oh, and in case you wonder,
++       * swap_alloc = pagesize * ( ai.ani_max - ai.ani_free );
++       * can suffer from a 32bit overflow.
         */
--      swap_resv  = pagesize * ai.ani_resv;
--      swap_alloc = pagesize * (MAX(ai.ani_resv, ai.ani_max) - ai.ani_free);
--      swap_avail = pagesize * (MAX(ai.ani_max - ai.ani_resv, 0) + (availrmem - swapfs_minfree));
--      /* swap_free  = pagesize * (ai.ani_free + (availrmem - swapfs_minfree)); */
++      swap_alloc  = ai.ani_max - ai.ani_free;
++      swap_alloc *= pagesize;
++      swap_resv   = ai.ani_resv + ai.ani_free - ai.ani_max;
++      swap_resv  *= pagesize;
++      swap_avail  = ai.ani_max - ai.ani_resv;
++      swap_avail *= pagesize;
   
  -     swap_submit (swap_alloc, swap_avail, -1LL, swap_resv);
  -/* #endif defined(KERNEL_SOLARIS) */
  +     swap_submit (swap_alloc, swap_avail, -1LL, swap_resv - swap_alloc);
  +/* #endif HAVE_LIBKSTAT */
  +
  +#elif defined(VM_SWAPUSAGE)
  +     int              mib[3];
  +     size_t           mib_len;
  +     struct xsw_usage sw_usage;
  +     size_t           sw_usage_len;
  +     int              status;
  +
  +     mib_len = 2;
  +     mib[0]  = CTL_VM;
  +     mib[1]  = VM_SWAPUSAGE;
  +
  +     sw_usage_len = sizeof (struct xsw_usage);
  +
  +     if (sysctl (mib, mib_len, &sw_usage, &sw_usage_len, NULL, 0) != 0)
  +             return;
  +
  +     /* The returned values are bytes. */
  +     swap_submit (sw_usage.xsu_used, sw_usage.xsu_avail, -1LL, -1LL);
  +/* #endif VM_SWAPUSAGE */
  +
  +#elif HAVE_LIBKVM
  +     struct kvm_swap data_s;
  +     int             status;
  +
  +     unsigned long long used;
  +     unsigned long long free;
  +     unsigned long long total;
  +
  +     if (kvm_obj == NULL)
  +             return;
  +
  +     /* only one structure => only get the grand total, no details */
  +     status = kvm_getswapinfo (kvm_obj, &data_s, 1, 0);
  +     if (status == -1)
  +             return;
  +
  +     total = (unsigned long long) data_s.ksw_total;
  +     used  = (unsigned long long) data_s.ksw_used;
  +
  +     total *= (unsigned long long) kvm_pagesize;
  +     used  *= (unsigned long long) kvm_pagesize;
  +
  +     free = total - used;
  +
  +     swap_submit (used, free, -1LL, -1LL);
  +/* #endif HAVE_LIBKVM */
   
  -#elif defined(HAVE_LIBSTATGRAB)
  +#elif HAVE_LIBSTATGRAB
        sg_swap_stats *swap;
   
        if ((swap = sg_get_swap_stats ()) != NULL)