예제 #1
0
int
S3_helper(char *whitelist, char *blacklist, int yes, int no, char *keyword,
	char *behavior, int *didyes, int suppress)
{
	int oflags = SMB_O_NOCKSUM | SMB_O_NOVERS;
	smbios_hdl_t *shp;
	smbios_system_t sys;
	id_t id;
	int ret;
	kstat_ctl_t *kc;
	kstat_t *ksp;
	kstat_named_t *dp;
	smbios_info_t info;
	int preferred_pm_profile = 0;
	char yesstr[32], nostr[32];	/* DEBUG */

	*didyes = 0;

	(void) strncpy(yesstr, pm_map(yes), sizeof (yesstr));
	(void) strncpy(nostr, pm_map(no), sizeof (nostr));
	mesg(MDEBUG, "S3_helper(%s, %s, %s, %s, %s, %s)\n", whitelist,
	    blacklist, yesstr, nostr, keyword, behavior);
	if ((kc = kstat_open()) == NULL) {
		mesg(MDEBUG, "kstat_open failed\n");
		return (OKUP);
	}
	ksp = kstat_lookup(kc, "acpi", -1, "acpi");
	if (ksp == NULL) {
		mesg(MDEBUG, "kstat_lookup 'acpi', -1, 'acpi' failed\n");
		(void) kstat_close(kc);
		return (OKUP);
	}
	(void) kstat_read(kc, ksp,  NULL);
	dp = kstat_data_lookup(ksp, "S3");
	if (dp == NULL || dp->value.l == 0) {
		mesg(MDEBUG, "kstat_data_lookup 'S3' fails\n");
		if (dp != NULL)
			mesg(MDEBUG, "value.l %lx\n", dp->value.l);
		(void) kstat_close(kc);
		return (do_ioctl(no, keyword, behavior, suppress));
	}
	mesg(MDEBUG, "kstat indicates S3 support (%lx)\n", dp->value.l);

	if (!whitelist_only) {
		/*
		 * We still have an ACPI ksp, search it again for
		 * 'preferred_pm_profile' (needs to be valid if we don't
		 * aren't only using a whitelist).
		 */
		dp = kstat_data_lookup(ksp, "preferred_pm_profile");
		if (dp == NULL) {
			mesg(MDEBUG, "kstat_data_lookup 'ppmp fails\n");
			(void) kstat_close(kc);
			return (do_ioctl(no, keyword, behavior, suppress));
		}
		mesg(MDEBUG, "kstat indicates preferred_pm_profile is %lx\n",
		    dp->value.l);
		preferred_pm_profile = dp->value.l;
	}
	(void) kstat_close(kc);

	if ((shp = smbios_open(NULL,
	    SMB_VERSION, oflags, &ret)) == NULL) {
		/* we promised not to complain */
		/* we bail leaving it to the kernel default */
		mesg(MDEBUG, "smbios_open failed %d\n", errno);
		return (OKUP);
	}
	if ((id = smbios_info_system(shp, &sys)) == SMB_ERR) {
		mesg(MDEBUG, "smbios_info_system failed %d\n", errno);
		smbios_close(shp);
		return (OKUP);
	}
	if (smbios_info_common(shp, id, &info) == SMB_ERR) {
		mesg(MDEBUG, "smbios_info_common failed %d\n", errno);
		smbios_close(shp);
		return (OKUP);
	}
	mesg(MDEBUG, "Manufacturer: %s\n", info.smbi_manufacturer);
	mesg(MDEBUG, "Product: %s\n", info.smbi_product);
	smbios_close(shp);

	if (!whitelist_only) {
#define	PPP_DESKTOP 1
#define	PPP_WORKSTATION 3
		if (strcmp(info.smbi_manufacturer, "Sun Microsystems") == 0 &&
		    (preferred_pm_profile == PPP_DESKTOP ||
		    preferred_pm_profile == PPP_WORKSTATION)) {
			if (isonlist(blacklist,
			    info.smbi_manufacturer, info.smbi_product)) {
				return (do_ioctl(no, keyword, behavior,
				    suppress));
			} else {
				ret = do_ioctl(yes, keyword, behavior,
				    suppress);
				*didyes = (ret == OKUP);
				return (ret);
			}
		}
	}
	if (isonlist(whitelist,
	    info.smbi_manufacturer, info.smbi_product)) {
		ret = do_ioctl(yes, keyword, behavior, suppress);
		*didyes = (ret == OKUP);
		return (ret);
	} else {
		return (do_ioctl(no, keyword, behavior, suppress));
	}
}
예제 #2
0
파일: aggcpu.c 프로젝트: sax/nad
int main(int argc, char **argv) {
  kstat_ctl_t   *kc;  
  kstat_t       *ksp;  
  kstat_io_t     kio;  
  kstat_named_t *knp;  
  cpu_stat_t sum;
  cpu_stat_t cpu;
 
  memset(&sum, 0, sizeof(sum)); 
  kc = kstat_open();  
  ksp = kstat_lookup(kc, "cpu_stat", -1, NULL);
  for (; ksp != NULL; ksp = ksp->ks_next) { 
    if(!strcmp(ksp->ks_module, "cpu_stat")) {
      kstat_read(kc,ksp,&cpu);
      CSSUM(cpu[CPU_IDLE]);
      CSSUM(cpu[CPU_USER]);
      CSSUM(cpu[CPU_KERNEL]);
      CSSUM(cpu[CPU_WAIT]);
      CSSUM(wait[W_IO]);
      CSSUM(wait[W_SWAP]);
      CSSUM(wait[W_PIO]);
      CSSUM(bread);
      CSSUM(bwrite);
      CSSUM(lread);
      CSSUM(lwrite);
      CSSUM(phread);
      CSSUM(phwrite);
      CSSUM(pswitch);
      CSSUM(trap);
      CSSUM(intr);
      CSSUM(syscall);
      CSSUM(sysread);
      CSSUM(syswrite);
      CSSUM(sysfork);
      CSSUM(sysvfork);
      CSSUM(sysexec);
      CSSUM(readch);
      CSSUM(writech);
      CSSUM(rcvint);
      CSSUM(xmtint);
      CSSUM(mdmint);
      CSSUM(rawch);
      CSSUM(canch);
      CSSUM(outch);
      CSSUM(msg);
      CSSUM(sema);
      CSSUM(namei);
      CSSUM(ufsiget);
      CSSUM(ufsdirblk);
      CSSUM(ufsipage);
      CSSUM(ufsinopage);
      CSSUM(inodeovf);
      CSSUM(fileovf);
      CSSUM(procovf);
      CSSUM(intrthread);
      CSSUM(intrblk);
      CSSUM(idlethread);
      CSSUM(inv_swtch);
      CSSUM(nthreads);
      CSSUM(cpumigrate);
      CSSUM(xcalls);
      CSSUM(mutex_adenters);
      CSSUM(rw_rdfails);
      CSSUM(rw_wrfails);
      CSSUM(modload);
      CSSUM(modunload);
      CSSUM(bawrite);
      CVSUM(pgrec);
      CVSUM(pgfrec);
      CVSUM(pgin);
      CVSUM(pgpgin);
      CVSUM(pgout);
      CVSUM(pgpgout);
      CVSUM(swapin);
      CVSUM(pgswapin);
      CVSUM(swapout);
      CVSUM(pgswapout);
      CVSUM(zfod);
      CVSUM(dfree);
      CVSUM(scan);
      CVSUM(rev);
      CVSUM(hat_fault);
      CVSUM(as_fault);
      CVSUM(maj_fault);
      CVSUM(cow_fault);
      CVSUM(prot_fault);
      CVSUM(softlock);
      CVSUM(kernel_asflt);
      CVSUM(pgrrun);
      CVSUM(execpgin);
      CVSUM(execpgout);
      CVSUM(execfree);
      CVSUM(anonpgin);
      CVSUM(anonpgout);
      CVSUM(anonfree);
      CVSUM(fspgin);
      CVSUM(fspgout);
      CVSUM(fsfree);
    }
  }

  PRINTN_CSSUM(cpu_idle, cpu[CPU_IDLE]);
  PRINTN_CSSUM(cpu_user, cpu[CPU_USER]);
  PRINTN_CSSUM(cpu_kernel, cpu[CPU_KERNEL]);
  PRINTN_CSSUM(cpu_wait, cpu[CPU_WAIT]);
  PRINTN_CSSUM(wait_io, wait[W_IO]);
  PRINTN_CSSUM(wait_swap, wait[W_SWAP]);
  PRINTN_CSSUM(wait_pio, wait[W_PIO]);
  PRINT_CSSUM(bread);
  PRINT_CSSUM(bwrite);
  PRINT_CSSUM(lread);
  PRINT_CSSUM(lwrite);
  PRINT_CSSUM(phread);
  PRINT_CSSUM(phwrite);
  PRINT_CSSUM(pswitch);
  PRINT_CSSUM(trap);
  PRINT_CSSUM(intr);
  PRINT_CSSUM(syscall);
  PRINT_CSSUM(sysread);
  PRINT_CSSUM(syswrite);
  PRINT_CSSUM(sysfork);
  PRINT_CSSUM(sysvfork);
  PRINT_CSSUM(sysexec);
  PRINT_CSSUM(readch);
  PRINT_CSSUM(writech);
  PRINT_CSSUM(rcvint);
  PRINT_CSSUM(xmtint);
  PRINT_CSSUM(mdmint);
  PRINT_CSSUM(rawch);
  PRINT_CSSUM(canch);
  PRINT_CSSUM(outch);
  PRINT_CSSUM(msg);
  PRINT_CSSUM(sema);
  PRINT_CSSUM(namei);
  PRINT_CSSUM(ufsiget);
  PRINT_CSSUM(ufsdirblk);
  PRINT_CSSUM(ufsipage);
  PRINT_CSSUM(ufsinopage);
  PRINT_CSSUM(inodeovf);
  PRINT_CSSUM(fileovf);
  PRINT_CSSUM(procovf);
  PRINT_CSSUM(intrthread);
  PRINT_CSSUM(intrblk);
  PRINT_CSSUM(idlethread);
  PRINT_CSSUM(inv_swtch);
  PRINT_CSSUM(nthreads);
  PRINT_CSSUM(cpumigrate);
  PRINT_CSSUM(xcalls);
  PRINT_CSSUM(mutex_adenters);
  PRINT_CSSUM(rw_rdfails);
  PRINT_CSSUM(rw_wrfails);
  PRINT_CSSUM(modload);
  PRINT_CSSUM(modunload);
  PRINT_CSSUM(bawrite);
  PRINT_CVSUM(pgrec);
  PRINT_CVSUM(pgfrec);
  PRINT_CVSUM(pgin);
  PRINT_CVSUM(pgpgin);
  PRINT_CVSUM(pgout);
  PRINT_CVSUM(pgpgout);
  PRINT_CVSUM(swapin);
  PRINT_CVSUM(pgswapin);
  PRINT_CVSUM(swapout);
  PRINT_CVSUM(pgswapout);
  PRINT_CVSUM(zfod);
  PRINT_CVSUM(dfree);
  PRINT_CVSUM(scan);
  PRINT_CVSUM(rev);
  PRINT_CVSUM(hat_fault);
  PRINT_CVSUM(as_fault);
  PRINT_CVSUM(maj_fault);
  PRINT_CVSUM(cow_fault);
  PRINT_CVSUM(prot_fault);
  PRINT_CVSUM(softlock);
  PRINT_CVSUM(kernel_asflt);
  PRINT_CVSUM(pgrrun);
  PRINT_CVSUM(execpgin);
  PRINT_CVSUM(execpgout);
  PRINT_CVSUM(execfree);
  PRINT_CVSUM(anonpgin);
  PRINT_CVSUM(anonpgout);
  PRINT_CVSUM(anonfree);
  PRINT_CVSUM(fspgin);
  PRINT_CVSUM(fspgout);
  PRINT_CVSUM(fsfree);
}  
예제 #3
0
static u_char  *
var_extensible_mem(struct variable *vp,
                   oid * name,
                   size_t * length,
                   int exact,
                   size_t * var_len, WriteMethod ** write_method)
{
    static long     long_ret;

    /*
     * Initialize the return value to 0 
     */
    long_ret = 0;

    if (header_generic(vp, name, length, exact, var_len, write_method))
        return (NULL);

    switch (vp->magic) {
    case MIBINDEX:
        long_ret = 0;
        return ((u_char *) (&long_ret));
    case ERRORNAME:            /* dummy name */
        sprintf(errmsg, "swap");
        *var_len = strlen(errmsg);
        return ((u_char *) (errmsg));
    case MEMTOTALSWAP:
        long_ret = getTotalSwap() * (getpagesize() / 1024);
        return ((u_char *) (&long_ret));
    case MEMAVAILSWAP:
        long_ret = getFreeSwap() * (getpagesize() / 1024);
        return ((u_char *) (&long_ret));
    case MEMSWAPMINIMUM:
        long_ret = minimumswap;
        return ((u_char *) (&long_ret));
    case MEMTOTALREAL:
#ifdef _SC_PHYS_PAGES
        long_ret = sysconf(_SC_PHYS_PAGES) * (getpagesize()/1024);
#else
        ksp1 = kstat_lookup(kstat_fd, "unix", 0, "system_pages");
        kstat_read(kstat_fd, ksp1, 0);
        kn = kstat_data_lookup(ksp1, "physmem");

        long_ret = kn->value.ul * (getpagesize() / 1024);
#endif
        return ((u_char *) (&long_ret));
    case MEMAVAILREAL:
#ifdef _SC_AVPHYS_PAGES
        long_ret = sysconf(_SC_AVPHYS_PAGES) * (getpagesize()/1024);
#else
        long_ret =
            (getTotalFree() - getFreeSwap()) * (getpagesize() / 1024);
#endif
        return ((u_char *) (&long_ret));
    case MEMTOTALFREE:
        long_ret = getTotalFree() * (getpagesize() / 1024);
        return ((u_char *) (&long_ret));

    case ERRORFLAG:
        long_ret = getTotalFree() * (getpagesize() / 1024);
        long_ret = (long_ret > minimumswap) ? 0 : 1;
        return ((u_char *) (&long_ret));

    case ERRORMSG:
        long_ret = getTotalFree() * (getpagesize() / 1024);
        if ((long_ret > minimumswap) ? 0 : 1)
            sprintf(errmsg, "Running out of swap space (%ld)", long_ret);
        else
            errmsg[0] = 0;
        *var_len = strlen(errmsg);
        return ((u_char *) (errmsg));

    }

    return (NULL);
}
예제 #4
0
static void get_cpu_counters(int cpu_num, cpu_time_counters_t * counters)
{

	kstat_t *ksp;
	int found = 0;
	kid_t nkcid;
	kstat_named_t *knp;
	int i;

	ksp = kstat_lookup(kc, "cpu", lib_cpu_map[cpu_num], "sys");
	if ((ksp) && (ksp->ks_type == KSTAT_TYPE_NAMED)) {
		/* happiness and joy, keep going */
		nkcid = kstat_read(kc, ksp, NULL);
		if (nkcid != -1) {
			/* happiness and joy, keep going. we could consider adding a
			   "found < 3" to the end conditions, but then we wouldn't
			   search to the end and find that Sun added some nsec. we
			   probably want to see if they add an nsec. raj 2005-01-28 */
			for (i = ksp->ks_ndata, knp = ksp->ks_data; i > 0; knp++, i--) {
				/* we would be hosed if the same name could appear twice */
				if (!strcmp("cpu_nsec_idle", knp->name)) {
					found++;
					counters[cpu_num].idle = knp->value.ui64;
				} else if (!strcmp("cpu_nsec_user", knp->name)) {
					found++;
					counters[cpu_num].user = knp->value.ui64;
				} else if (!strcmp("cpu_nsec_kernel", knp->name)) {
					found++;
					counters[cpu_num].kernel = knp->value.ui64;
				} else if (!strcmp("cpu_nsec_intr", knp->name)) {
					if (debug >= 2) {
						fprintf(where,
								"Found a cpu_nsec_intr but it doesn't do what we want\n");
						fflush(where);
					}
				} else if (strstr(knp->name, "nsec")) {
					/* finding another nsec here means Sun have changed
					   something and we need to warn the user. raj 2005-01-28 */
					print_unexpected_statistic_warning("get_cpu_counters",
													   knp->name, "nsec");
				} else if (debug >= 2) {

					/* might want to tell people about what we are skipping.
					   however, only display other names debug >=2. raj
					   2005-01-28  */

					print_unexpected_statistic_warning("get_cpu_counters",
													   knp->name, NULL);
				}
			}
			if (3 == found) {
				/* happiness and joy */
				return;
			} else {
				fprintf(where,
						"get_cpu_counters could not find one or more of the expected counters!\n");
				fflush(where);
				exit(-1);
			}
		} else {
			/* the kstat_read returned an error or the chain changed */
			fprintf(where,
					"get_cpu_counters: kstat_read failed or chain id changed %d %s\n",
					errno, strerror(errno));
			fflush(where);
			exit(-1);
		}
	} else {
		/* the lookup failed or found the wrong type */
		fprintf(where,
				"get_cpu_counters: kstat_lookup failed for module 'cpu' number %d instance %d name 'sys' and KSTAT_TYPE_NAMED: errno %d %s\n",
				cpu_num, lib_cpu_map[cpu_num], errno, strerror(errno));
		fflush(where);
		exit(-1);
	}
}
예제 #5
0
파일: uptime.c 프로젝트: Shmuma/z
int	SYSTEM_UPTIME(const char *cmd, const char *param, unsigned flags, AGENT_RESULT *result)
{
#ifdef HAVE_SYSINFO_UPTIME
	struct sysinfo info;

	assert(result);

        init_result(result);

	if( 0 == sysinfo(&info))
	{
		SET_UI64_RESULT(result, info.uptime);
		return SYSINFO_RET_OK;
	}
	else
	{
		return SYSINFO_RET_FAIL;
	}
#else
#ifdef HAVE_FUNCTION_SYSCTL_KERN_BOOTTIME
	int	mib[2],len;
	struct timeval	uptime;
	int	now;

	assert(result);

        init_result(result);

	mib[0]=CTL_KERN;
	mib[1]=KERN_BOOTTIME;

	len=sizeof(uptime);

	if(sysctl(mib,2,&uptime,(size_t *)&len,NULL,0) != 0)
	{
		return	SYSINFO_RET_FAIL;
/*		printf("Errno [%m]\n");*/
	}

	now=time(NULL);
	
	SET_UI64_RESULT(result, now-uptime.tv_sec);
	return SYSINFO_RET_OK;
#else
/* Solaris */
#ifdef HAVE_KSTAT_H
	kstat_ctl_t   *kc;
	kstat_t       *kp;
	kstat_named_t *kn;

	long          hz;
	long          secs;

        assert(result);

        init_result(result);
	
	hz = sysconf(_SC_CLK_TCK);

	/* open kstat */
	kc = kstat_open();
	if (0 == kc)
	{
		return SYSINFO_RET_FAIL;
	}

	/* read uptime counter */
	kp = kstat_lookup(kc, "unix", 0, "system_misc");
	if (0 == kp)
	{
		kstat_close(kc);
		return SYSINFO_RET_FAIL;
	}

	if(-1 == kstat_read(kc, kp, 0))
	{
		kstat_close(kc);
		return SYSINFO_RET_FAIL;
	}
	kn = (kstat_named_t*)kstat_data_lookup(kp, "clk_intr");
	secs = kn->value.ul / hz;

	/* close kstat */
	kstat_close(kc);

	SET_UI64_RESULT(result, secs);
	return SYSINFO_RET_OK;
#else
        assert(result);

        init_result(result);

	return	SYSINFO_RET_FAIL;
#endif
#endif
#endif
}
예제 #6
0
/*
 * sdbc_discover() - looks for new statistics to be monitored.
 * Verifies that any statistics found are now already being
 * monitored.
 *
 */
int
sdbc_discover(kstat_ctl_t *kc)
{
	static int validated = 0;

	kstat_t *ksp;

	for (ksp = kc->kc_chain; ksp; ksp = ksp->ks_next) {
		int kinst;
		char kname[KSTAT_STRLEN + 1];
		sdbcstat_t *cur;
		sdbcstat_t *sdbcstat = NULL;
		kstat_t *io_ksp;

		if (strcmp(ksp->ks_module, SDBC_KSTAT_MODULE) != 0 ||
		    strncmp(ksp->ks_name, SDBC_KSTAT_CDSTATS, 2) != 0)
			continue;

		if (kstat_read(kc, ksp, NULL) == -1)
			continue;

		/*
		 * Validate kstat structure
		 */
		if (! validated) {
			if (sdbc_validate(ksp))
				return (EINVAL);

			validated++;
		}

		/*
		 * Duplicate check
		 */
		for (cur = sdbc_top; cur; cur = cur->next) {
			char *cur_vname, *tst_vname;

			cur_vname = kstat_value(cur->pre_set,
			    SDBC_CDKSTAT_VOL_NAME);

			tst_vname = kstat_value(ksp,
			    SDBC_CDKSTAT_VOL_NAME);

			if (strncmp(cur_vname, tst_vname, NAMED_LEN) == 0)
				goto next;
		}

		/*
		 * Initialize new record
		 */
		sdbcstat = (sdbcstat_t *)calloc(1, sizeof (sdbcstat_t));

		kinst = ksp->ks_instance;

		/*
		 * Set kstat
		 */
		sdbcstat->pre_set = kstat_retrieve(kc, ksp);

		if (sdbcstat->pre_set == NULL)
			goto next;

		sdbcstat->collected |= GOT_SET_KSTAT;

		/*
		 * I/O kstat
		 */
		sprintf(kname, "%s%d",  SDBC_IOKSTAT_CDSTATS, kinst);

		io_ksp = kstat_lookup(kc, SDBC_KSTAT_MODULE, kinst, kname);
		sdbcstat->pre_io = kstat_retrieve(kc, io_ksp);

		if (sdbcstat->pre_io == NULL)
			goto next;

		sdbcstat->collected |= GOT_IO_KSTAT;

next:
		/*
		 * Check if we got a complete set of stats
		 */
		if (sdbcstat == NULL)
			continue;

		if (SDBC_COMPLETE(sdbcstat->collected)) {
			(void) sdbc_delstat(sdbcstat);
			continue;
		}

		sdbc_addstat(sdbcstat);
	}

	if (sdbc_top == NULL)
		return (EAGAIN);

	return (0);
}
예제 #7
0
/*
 * Return information about system virtual memory.
 */
static PyObject *
psutil_swap_mem(PyObject *self, PyObject *args) {
// XXX (arghhh!)
// total/free swap mem: commented out as for some reason I can't
// manage to get the same results shown by "swap -l", despite the
// code below is exactly the same as:
// http://cvs.opensolaris.org/source/xref/onnv/onnv-gate/usr/src/
//    cmd/swap/swap.c
// We're going to parse "swap -l" output from Python (sigh!)

/*
    struct swaptable     *st;
    struct swapent    *swapent;
    int    i;
    struct stat64 statbuf;
    char *path;
    char fullpath[MAXPATHLEN+1];
    int    num;

    if ((num = swapctl(SC_GETNSWP, NULL)) == -1) {
        PyErr_SetFromErrno(PyExc_OSError);
        return NULL;
    }
    if (num == 0) {
        PyErr_SetString(PyExc_RuntimeError, "no swap devices configured");
        return NULL;
    }
    if ((st = malloc(num * sizeof(swapent_t) + sizeof (int))) == NULL) {
        PyErr_SetString(PyExc_RuntimeError, "malloc failed");
        return NULL;
    }
    if ((path = malloc(num * MAXPATHLEN)) == NULL) {
        PyErr_SetString(PyExc_RuntimeError, "malloc failed");
        return NULL;
    }
    swapent = st->swt_ent;
    for (i = 0; i < num; i++, swapent++) {
        swapent->ste_path = path;
        path += MAXPATHLEN;
    }
    st->swt_n = num;
    if ((num = swapctl(SC_LIST, st)) == -1) {
        PyErr_SetFromErrno(PyExc_OSError);
        return NULL;
    }

    swapent = st->swt_ent;
    long t = 0, f = 0;
    for (i = 0; i < num; i++, swapent++) {
        int diskblks_per_page =(int)(sysconf(_SC_PAGESIZE) >> DEV_BSHIFT);
        t += (long)swapent->ste_pages;
        f += (long)swapent->ste_free;
    }

    free(st);
    return Py_BuildValue("(kk)", t, f);
*/

    kstat_ctl_t *kc;
    kstat_t     *k;
    cpu_stat_t  *cpu;
    int         cpu_count = 0;
    int         flag = 0;
    uint_t      sin = 0;
    uint_t      sout = 0;

    kc = kstat_open();
    if (kc == NULL)
        return PyErr_SetFromErrno(PyExc_OSError);;

    k = kc->kc_chain;
    while (k != NULL) {
        if ((strncmp(k->ks_name, "cpu_stat", 8) == 0) && \
                (kstat_read(kc, k, NULL) != -1) )
        {
            flag = 1;
            cpu = (cpu_stat_t *) k->ks_data;
            sin += cpu->cpu_vminfo.pgswapin;    // num pages swapped in
            sout += cpu->cpu_vminfo.pgswapout;  // num pages swapped out
        }
        cpu_count += 1;
        k = k->ks_next;
    }
    kstat_close(kc);
    if (!flag) {
        PyErr_SetString(PyExc_RuntimeError, "no swap device was found");
        return NULL;
    }
    return Py_BuildValue("(II)", sin, sout);
}
예제 #8
0
파일: Memory.c 프로젝트: KDE/kde-workspace
int updateSwap( int upd ) {
	long			swaptotal;
	long			swapfree;
	long			swapused;
#ifdef HAVE_KSTAT
	kstat_ctl_t		*kctl;
	kstat_t			*ksp;
	struct timeval 		sampling;
	vminfo_t		vmi;

	uint64_t _swap_resv = 0;
	uint64_t _swap_free = 0;
	uint64_t _swap_avail = 0;
	uint64_t _swap_alloc = 0;

#endif /* HAVE_KSTAT */
	swaptotal = swapused = swapfree = 0L;

#ifndef HAVE_KSTAT
	/*
	 *  Retrieve overall swap information from anonymous memory structure -
	 *  which is the same way "swap -s" retrieves it's statistics.
	 *
	 *  swapctl(SC_LIST, void *arg) does not return what we are looking for.
	 */

	if (swapctl(SC_AINFO, &am_swap) == -1)
		return(0);

	swaptotal = am_swap.ani_max;
	swapused = am_swap.ani_resv;
	swapfree = swaptotal - swapused;

	usedswap = pagetok(swapused);
	freeswap = pagetok(swapfree);

#else /* HAVE_KSTAT */
	/*
	 *  get a kstat handle and update the user's kstat chain
	 */
	if( (kctl = kstat_open()) == NULL )
		return( 0 );
	while( kstat_chain_update( kctl ) != 0 )
		;

	totalmem = pagetok( sysconf( _SC_PHYS_PAGES ));

	if( (ksp = kstat_lookup( kctl, "unix", -1, "vminfo" )) == NULL ) {
		goto done;
	}

	if( kstat_read( kctl, ksp, &vmi ) == -1 ) {
                goto done;
        }

	_swap_resv = vmi.swap_resv - swap_resv;
	if (_swap_resv)
		swap_resv = vmi.swap_resv;

	_swap_free = vmi.swap_free - swap_free;
	if (_swap_free)
		swap_free = vmi.swap_free;

	_swap_avail = vmi.swap_avail - swap_avail;
	if (_swap_avail)
		swap_avail = vmi.swap_avail;

	_swap_alloc = vmi.swap_alloc - swap_alloc;
	if (_swap_alloc)
		swap_alloc = vmi.swap_alloc;

	if (upd) {
		long timeInterval;

		gettimeofday(&sampling, 0);
		timeInterval = sampling.tv_sec - lastSampling.tv_sec +
		    ( sampling.tv_usec - lastSampling.tv_usec ) / 1000000.0;
		lastSampling = sampling;
		timeInterval = timeInterval > 0 ? timeInterval : 1;

		_swap_resv = _swap_resv / timeInterval;
		_swap_free = _swap_free / timeInterval;
		_swap_avail = _swap_avail / timeInterval;
		_swap_alloc = _swap_alloc / timeInterval;

		if (_swap_alloc)
			usedswap = pagetok((unsigned long)(_swap_alloc + _swap_free - _swap_avail));

		/*
		 * Assume minfree = totalmem / 8, i.e. it has not been tuned
		 */
		if (_swap_avail)
			freeswap = pagetok((unsigned long)(_swap_avail + totalmem / 8));
	}
done:
	kstat_close( kctl );
#endif /* ! HAVE_KSTAT */

	return( 0 );
}
/* ******** end of picld sensor procedures * */

#endif /* solaris2 */
static int
_sensor_load(time_t t)
{
#ifdef solaris2
    int i,j;
    int typ;
    int temp=0; /* do not reset this later, more than one typ has temperatures*/
    int other=0;
    const char *fantypes[]={"CPU","PWR","AFB"};
    kstat_ctl_t *kc;
    kstat_t *kp;
    envctrl_fan_t *fan_info;
    envctrl_ps_t *power_info;
    envctrl_encl_t *enc_info;

/* DEBUGMSG(("ucd-snmp/lmSensors", "Reading the sensors\n")); */

/* initialize the array */
    for (i = 0; i < N_TYPES; i++){
        sensor_array[i].n = 0;
        for (j=0; j < MAX_SENSORS; j++){
            sensor_array[i].sensor[j].name[0] = '\0';
            sensor_array[i].sensor[j].value = 0;
             }
        } /*end for i*/

/* try picld (if supported), if that doesn't work, try kstat */
#ifdef HAVE_PICL_H 

/* some more declarations */

    int er_code;
    picl_errno_t     error_code;
    int level=0;
    picl_nodehdl_t  rooth;

er_code = picl_initialize();

if (er_code == PICL_SUCCESS) {

    error_code = picl_get_root(&rooth);

    if (error_code != PICL_SUCCESS) {
        DEBUGMSG(("ucd-snmp/lmSensors", "picld couldn't get root error code->%d\n",error_code));
        }
    else{
        DEBUGMSGTL(("ucd-snmp/lmSensors", "found root\n"));
        error_code = process_sensors(level,rooth);
        if (error_code != 255) 
            if (error_code != 7)
                DEBUGMSG(("ucd-snmp/lmSensors", "picld had an internal problem error code->%d\n",error_code));
        } /* end else */

    picl_shutdown();

}  /* end if err_code for picl_initialize */

else {  
    DEBUGMSG(("ucd-snmp/lmSensors", "picld couldn't initialize picld because error code->%d\n",er_code));

} /*end else picl_initialize */

#endif  /* end of picld section */
/* initialize kstat */

kc = kstat_open();
if (kc == 0) {
    DEBUGMSG(("ucd-snmp/lmSensors", "couldn't open kstat"));
    } /* endif kc */
else{
    temp = 0;
    kp = kstat_lookup(kc, ENVCTRL_MODULE_NAME, 0, ENVCTRL_KSTAT_FANSTAT);
    if (kp == 0) {
        DEBUGMSGTL(("ucd-snmp/lmSensors", "couldn't lookup fan kstat\n"));
        } /* endif lookup fans */
    else{
        if (kstat_read(kc, kp, 0) == -1) {
            DEBUGMSGTL(("ucd-snmp/lmSensors", "couldn't read fan kstat"));
            } /* endif kstatread fan */
        else{
            typ = 1;
            fan_info = (envctrl_fan_t *) kp->ks_data;
            sensor_array[typ].n = kp->ks_ndata;
            for (i=0; i < kp->ks_ndata; i++){
                DEBUGMSG(("ucd-snmp/lmSensors", "found instance %d fan type %d speed %d OK %d bustedfan %d\n",
                    fan_info->instance, fan_info->type,fan_info->fanspeed,fan_info->fans_ok,fan_info->fanflt_num));
                sensor_array[typ].sensor[i].value = fan_info->fanspeed;
                snprintf(sensor_array[typ].sensor[i].name,(MAX_NAME - 1),
                   "fan type %s number %d",fantypes[fan_info->type],fan_info->instance);
                sensor_array[typ].sensor[i].name[MAX_NAME - 1] = '\0';
                fan_info++;
                } /* end for fan_info */
            } /* end else kstatread fan */
        } /* end else lookup fans*/


    kp = kstat_lookup(kc, ENVCTRL_MODULE_NAME, 0, ENVCTRL_KSTAT_PSNAME);
    if (kp == 0) {
        DEBUGMSGTL(("ucd-snmp/lmSensors", "couldn't lookup power supply kstat\n"));
        } /* endif lookup power supply */
    else{
        if (kstat_read(kc, kp, 0) == -1) {
            DEBUGMSGTL(("ucd-snmp/lmSensors", "couldn't read power supply kstat\n"));
            } /* endif kstatread fan */
        else{
            typ = 0; /* this is a power supply temperature, not a voltage*/
            power_info = (envctrl_ps_t *) kp->ks_data;
            sensor_array[typ].n = kp->ks_ndata;
            for (i=0; i < kp->ks_ndata; i++){
                DEBUGMSG(("ucd-snmp/lmSensors", "found instance %d psupply temp mC %d %dW OK %d share %d limit %d\n",
                    power_info->instance, power_info->ps_tempr*1000,power_info->ps_rating,
                    power_info->ps_ok,power_info->curr_share_ok,power_info->limit_ok));
                sensor_array[typ].sensor[temp].value = power_info->ps_tempr*1000;
                snprintf(sensor_array[typ].sensor[temp].name,(MAX_NAME-1),
                         "power supply %d",power_info->instance);
                sensor_array[typ].sensor[temp].name[MAX_NAME - 1] = '\0';
                power_info++; /* increment the data structure */
                temp++; /* increment the temperature sensor array element */
                } /* end for power_info */
            } /* end else kstatread power supply */
        } /* end else lookup power supplies*/

    kp = kstat_lookup(kc, ENVCTRL_MODULE_NAME, 0, ENVCTRL_KSTAT_ENCL);
    if (kp == 0) {
        DEBUGMSGTL(("ucd-snmp/lmSensors", "couldn't lookup enclosure kstat\n"));
        } /* endif lookup enclosure */
    else{
        if (kstat_read(kc, kp, 0) == -1) {
            DEBUGMSGTL(("ucd-snmp/lmSensors", "couldn't read enclosure kstat\n"));
            } /* endif kstatread enclosure */
        else{
            enc_info = (envctrl_encl_t *) kp->ks_data; 
            other = 0;
            for (i=0; i < kp->ks_ndata; i++){
               switch (enc_info->type){
               case ENVCTRL_ENCL_FSP:
                   DEBUGMSG(("ucd-snmp/lmSensors", "front panel value %d\n",enc_info->value));
                   typ = 3; /* misc */
                   sensor_array[typ].sensor[other].value = enc_info->value;
                   strncpy(sensor_array[typ].sensor[other].name,"FSP",MAX_NAME-1);
                   sensor_array[typ].sensor[other].name[MAX_NAME-1]='\0'; /* null terminate */
                   other++;
                   break;
               case ENVCTRL_ENCL_AMBTEMPR:
                   DEBUGMSG(("ucd-snmp/lmSensors", "ambient temp mC %d\n",enc_info->value*1000));
                   typ = 0; /* temperature sensor */
                   sensor_array[typ].sensor[temp].value = enc_info->value*1000;
                   strncpy(sensor_array[typ].sensor[temp].name,"Ambient",MAX_NAME-1);
                   sensor_array[typ].sensor[temp].name[MAX_NAME-1]='\0'; /* null terminate */
                   temp++;
                   break;
               case ENVCTRL_ENCL_BACKPLANE4:
                   DEBUGMSG(("ucd-snmp/lmSensors", "There is a backplane4\n"));
                   typ = 3; /* misc */
                   sensor_array[typ].sensor[other].value = enc_info->value;
                   strncpy(sensor_array[typ].sensor[other].name,"Backplane4",MAX_NAME-1);
                   sensor_array[typ].sensor[other].name[MAX_NAME-1]='\0'; /* null terminate */
                   other++;
                   break;
               case ENVCTRL_ENCL_BACKPLANE8:
                   DEBUGMSG(("ucd-snmp/lmSensors", "There is a backplane8\n"));
                   typ = 3; /* misc */
                   sensor_array[typ].sensor[other].value = enc_info->value;
                   strncpy(sensor_array[typ].sensor[other].name,"Backplane8",MAX_NAME-1);
                   sensor_array[typ].sensor[other].name[MAX_NAME-1]='\0'; /* null terminate */
                   other++;
                   break;
               case ENVCTRL_ENCL_CPUTEMPR:
                   DEBUGMSG(("ucd-snmp/lmSensors", "CPU%d temperature mC %d\n",enc_info->instance,enc_info->value*1000));
                   typ = 0; /* temperature sensor */
                   sensor_array[typ].sensor[temp].value = enc_info->value*1000;
                   snprintf(sensor_array[typ].sensor[temp].name,MAX_NAME,"CPU%d",enc_info->instance);
                   sensor_array[typ].sensor[temp].name[MAX_NAME-1]='\0'; /* null terminate */
                   temp++;
                   break;
               default:
                   DEBUGMSG(("ucd-snmp/lmSensors", "unknown element instance &d type &d value %d\n",
                       enc_info->instance, enc_info->type, enc_info->value));
                   break;
               } /* end switch */
               enc_info++;
               } /* end for enc_info */
               sensor_array[3].n = other;
               sensor_array[0].n = temp;
            } /* end else kstatread enclosure */
        } /* end else lookup enclosure*/

    kstat_close(kc);

} /* end else kstat */
#else /* end solaris2 only ie. ifdef everything else */

    const sensors_chip_name *chip;
    const sensors_feature_data *data;
    int             chip_nr = 0;
    int             rc = 0;
    unsigned int    i = 0;

    for (i = 0; i < N_TYPES; i++)
    {
        sensor_array[i].n = 0;
        sensor_array[i].current_len = 0;

        /* Malloc the default number of sensors. */
        sensor_array[i].sensor = (_sensor*)malloc(sizeof(_sensor) * DEFAULT_SENSORS);
        if (sensor_array[i].sensor == NULL)
        {
           /* Continuing would be unsafe */
           snmp_log(LOG_ERR, "Cannot malloc sensor array!"); 
           return (rc = 1);
        } /* end if */
        sensor_array[i].current_len = DEFAULT_SENSORS;
    } /* end for */

    while ((chip = sensors_get_detected_chips(&chip_nr))) {
	int             a = 0;
	int             b = 0;

        while ((data = sensors_get_all_features(*chip, &a, &b))) {
            char           *label = NULL;
            double          val;

            if ((data->mode & SENSORS_MODE_R) &&
                (data->mapping == SENSORS_NO_MAPPING) &&
                !sensors_get_label(*chip, data->number, &label) &&
                !sensors_get_feature(*chip, data->number, &val)) {
                int             type = -1;
                float           mul;
                _sensor_array  *array;

                /* The label, as determined for a given chip in sensors.conf,
                 * is used to place each sensor in the appropriate bucket.
                 * Volt, Fan, Temp, and Misc.  If the text being looked for below
                 * is not in the label of a given sensor (e.g., the temp1 sensor
                 * has been labeled 'CPU' and not 'CPU temp') it will end up being
                 * lumped in the MISC bucket. */

                if (strstr(label, "V")) {
                    type = VOLT_TYPE;
                    mul = 1000.0;
                }
                if (strstr(label, "fan") || strstr(label, "Fan")) {
                    type = FAN_TYPE;
                    mul = 1.0;
                }
                if (strstr(label, "temp") || strstr(label, "Temp")) {
                    type = TEMP_TYPE;
                    mul = 1000.0;
                }
                if (type == -1) {
                    type = MISC_TYPE;
                    mul = 1000.0;
                }

                array = &sensor_array[type];
                if ( array->current_len <= array->n) {
                    _sensor* old_buffer = array->sensor;
                    size_t new_size = (sizeof(_sensor) * array->current_len) + (sizeof(_sensor) * DEFAULT_SENSORS);
                    array->sensor = (_sensor*)realloc(array->sensor, new_size);
                    if (array->sensor == NULL)
                    {
                       /* Continuing would be unsafe */
                       snmp_log(LOG_ERR, "too many sensors to fit, and failed to alloc more, failing on %s\n", label);
                       free(old_buffer);
                       old_buffer = NULL;
                       if (label) {
                           free(label);
                           label = NULL;
                       } /* end if label */
                       return (rc=1);
                    } /* end if array->sensor */
                    array->current_len = new_size / sizeof(_sensor);
                    DEBUGMSG(("ucd-snmp/lmSensors", "type #%d increased to %d elements\n", type, array->current_len));
                } /* end if array->current */
                strncpy(array->sensor[array->n].name, label, MAX_NAME);
                array->sensor[array->n].value = (int) (val * mul);
                DEBUGMSGTL(("sensors","sensor %d, value %d\n",
                            array->sensor[array->n].name,
                            array->sensor[array->n].value));
                array->n++;
            } /* end if data-mode */
	    if (label) {
		free(label);
		label = NULL;
	    } /* end if label */
        } /* end while data */
    } /* end while chip */
    return rc;
#endif  /* end else ie. ifdef everything else */
    /* Update the timestamp after a load. */
    timestamp = t;
}
예제 #10
0
int
getloadavg (double loadavg[], int nelem)
{
  int elem = 0;			/* Return value.  */

# ifdef NO_GET_LOAD_AVG
#  define LDAV_DONE
  /* Set errno to zero to indicate that there was no particular error;
     this function just can't work at all on this system.  */
  errno = 0;
  elem = -1;
# endif

# if !defined (LDAV_DONE) && defined (HAVE_LIBKSTAT)
/* Use libkstat because we don't have to be root.  */
#  define LDAV_DONE
  kstat_ctl_t *kc;
  kstat_t *ksp;
  kstat_named_t *kn;

  kc = kstat_open ();
  if (kc == 0)
    return -1;
  ksp = kstat_lookup (kc, "unix", 0, "system_misc");
  if (ksp == 0 )
    return -1;
  if (kstat_read (kc, ksp, 0) == -1)
    return -1;


  kn = kstat_data_lookup (ksp, "avenrun_1min");
  if (kn == 0)
    {
      /* Return -1 if no load average information is available.  */
      nelem = 0;
      elem = -1;
    }

  if (nelem >= 1)
    loadavg[elem++] = (double) kn->value.ul/FSCALE;

  if (nelem >= 2)
    {
      kn = kstat_data_lookup (ksp, "avenrun_5min");
      if (kn != 0)
	{
	  loadavg[elem++] = (double) kn->value.ul/FSCALE;

	  if (nelem >= 3)
	    {
	      kn = kstat_data_lookup (ksp, "avenrun_15min");
	      if (kn != 0)
		loadavg[elem++] = (double) kn->value.ul/FSCALE;
	    }
	}
    }

  kstat_close (kc);
# endif /* HAVE_LIBKSTAT */

# if !defined (LDAV_DONE) && defined (hpux) && defined (HAVE_PSTAT_GETDYNAMIC)
/* Use pstat_getdynamic() because we don't have to be root.  */
#  define LDAV_DONE
#  undef LOAD_AVE_TYPE

  struct pst_dynamic dyn_info;
  if (pstat_getdynamic (&dyn_info, sizeof (dyn_info), 0, 0) < 0)
    return -1;
  if (nelem > 0)
    loadavg[elem++] = dyn_info.psd_avg_1_min;
  if (nelem > 1)
    loadavg[elem++] = dyn_info.psd_avg_5_min;
  if (nelem > 2)
    loadavg[elem++] = dyn_info.psd_avg_15_min;

# endif /* hpux && HAVE_PSTAT_GETDYNAMIC */

# if !defined (LDAV_DONE) && defined (__linux__)
#  define LDAV_DONE
#  undef LOAD_AVE_TYPE

#  ifndef LINUX_LDAV_FILE
#   define LINUX_LDAV_FILE "/proc/loadavg"
#  endif

  char ldavgbuf[40];
  double load_ave[3];
  int fd, count;

  fd = open (LINUX_LDAV_FILE, O_RDONLY);
  if (fd == -1)
    return -1;
  count = read (fd, ldavgbuf, 40);
  (void) close (fd);
  if (count <= 0)
    return -1;

  /* The following sscanf must use the C locale.  */
  setlocale (LC_NUMERIC, "C");
  count = sscanf (ldavgbuf, "%lf %lf %lf",
		  &load_ave[0], &load_ave[1], &load_ave[2]);
  setlocale (LC_NUMERIC, "");
  if (count < 1)
    return -1;

  for (elem = 0; elem < nelem && elem < count; elem++)
    loadavg[elem] = load_ave[elem];

  return elem;

# endif /* __linux__ */

# if !defined (LDAV_DONE) && defined (__NetBSD__)
#  define LDAV_DONE
#  undef LOAD_AVE_TYPE

#  ifndef NETBSD_LDAV_FILE
#   define NETBSD_LDAV_FILE "/kern/loadavg"
#  endif

  unsigned long int load_ave[3], scale;
  int count;
  FILE *fp;

  fp = fopen (NETBSD_LDAV_FILE, "r");
  if (fp == NULL)
    return -1;
  count = fscanf (fp, "%lu %lu %lu %lu\n",
		  &load_ave[0], &load_ave[1], &load_ave[2],
		  &scale);
  (void) fclose (fp);
  if (count != 4)
    return -1;

  for (elem = 0; elem < nelem; elem++)
    loadavg[elem] = (double) load_ave[elem] / (double) scale;

  return elem;

# endif /* __NetBSD__ */

# if !defined (LDAV_DONE) && defined (NeXT)
#  define LDAV_DONE
  /* The NeXT code was adapted from iscreen 3.2.  */

  host_t host;
  struct processor_set_basic_info info;
  unsigned info_count;

  /* We only know how to get the 1-minute average for this system,
     so even if the caller asks for more than 1, we only return 1.  */

  if (!getloadavg_initialized)
    {
      if (processor_set_default (host_self (), &default_set) == KERN_SUCCESS)
	getloadavg_initialized = 1;
    }

  if (getloadavg_initialized)
    {
      info_count = PROCESSOR_SET_BASIC_INFO_COUNT;
      if (processor_set_info (default_set, PROCESSOR_SET_BASIC_INFO, &host,
			      (processor_set_info_t) &info, &info_count)
	  != KERN_SUCCESS)
	getloadavg_initialized = 0;
      else
	{
	  if (nelem > 0)
	    loadavg[elem++] = (double) info.load_average / LOAD_SCALE;
	}
    }

  if (!getloadavg_initialized)
    return -1;
# endif /* NeXT */

# if !defined (LDAV_DONE) && defined (UMAX)
#  define LDAV_DONE
/* UMAX 4.2, which runs on the Encore Multimax multiprocessor, does not
   have a /dev/kmem.  Information about the workings of the running kernel
   can be gathered with inq_stats system calls.
   We only know how to get the 1-minute average for this system.  */

  struct proc_summary proc_sum_data;
  struct stat_descr proc_info;
  double load;
  register unsigned int i, j;

  if (cpus == 0)
    {
      register unsigned int c, i;
      struct cpu_config conf;
      struct stat_descr desc;

      desc.sd_next = 0;
      desc.sd_subsys = SUBSYS_CPU;
      desc.sd_type = CPUTYPE_CONFIG;
      desc.sd_addr = (char *) &conf;
      desc.sd_size = sizeof conf;

      if (inq_stats (1, &desc))
	return -1;

      c = 0;
      for (i = 0; i < conf.config_maxclass; ++i)
	{
	  struct class_stats stats;
	  bzero ((char *) &stats, sizeof stats);

	  desc.sd_type = CPUTYPE_CLASS;
	  desc.sd_objid = i;
	  desc.sd_addr = (char *) &stats;
	  desc.sd_size = sizeof stats;

	  if (inq_stats (1, &desc))
	    return -1;

	  c += stats.class_numcpus;
	}
      cpus = c;
      samples = cpus < 2 ? 3 : (2 * cpus / 3);
    }

  proc_info.sd_next = 0;
  proc_info.sd_subsys = SUBSYS_PROC;
  proc_info.sd_type = PROCTYPE_SUMMARY;
  proc_info.sd_addr = (char *) &proc_sum_data;
  proc_info.sd_size = sizeof (struct proc_summary);
  proc_info.sd_sizeused = 0;

  if (inq_stats (1, &proc_info) != 0)
    return -1;

  load = proc_sum_data.ps_nrunnable;
  j = 0;
  for (i = samples - 1; i > 0; --i)
    {
      load += proc_sum_data.ps_nrun[j];
      if (j++ == PS_NRUNSIZE)
	j = 0;
    }

  if (nelem > 0)
    loadavg[elem++] = load / samples / cpus;
# endif /* UMAX */

# if !defined (LDAV_DONE) && defined (DGUX)
#  define LDAV_DONE
  /* This call can return -1 for an error, but with good args
     it's not supposed to fail.  The first argument is for no
     apparent reason of type `long int *'.  */
  dg_sys_info ((long int *) &load_info,
	       DG_SYS_INFO_LOAD_INFO_TYPE,
	       DG_SYS_INFO_LOAD_VERSION_0);

  if (nelem > 0)
    loadavg[elem++] = load_info.one_minute;
  if (nelem > 1)
    loadavg[elem++] = load_info.five_minute;
  if (nelem > 2)
    loadavg[elem++] = load_info.fifteen_minute;
# endif /* DGUX */

# if !defined (LDAV_DONE) && defined (apollo)
#  define LDAV_DONE
/* Apollo code from [email protected] (Ray Lischner).

   This system call is not documented.  The load average is obtained as
   three long integers, for the load average over the past minute,
   five minutes, and fifteen minutes.  Each value is a scaled integer,
   with 16 bits of integer part and 16 bits of fraction part.

   I'm not sure which operating system first supported this system call,
   but I know that SR10.2 supports it.  */

  extern void proc1_$get_loadav ();
  unsigned long load_ave[3];

  proc1_$get_loadav (load_ave);

  if (nelem > 0)
    loadavg[elem++] = load_ave[0] / 65536.0;
  if (nelem > 1)
    loadavg[elem++] = load_ave[1] / 65536.0;
  if (nelem > 2)
    loadavg[elem++] = load_ave[2] / 65536.0;
# endif /* apollo */

# if !defined (LDAV_DONE) && defined (OSF_MIPS)
#  define LDAV_DONE

  struct tbl_loadavg load_ave;
  table (TBL_LOADAVG, 0, &load_ave, 1, sizeof (load_ave));
  loadavg[elem++]
    = (load_ave.tl_lscale == 0
       ? load_ave.tl_avenrun.d[0]
       : (load_ave.tl_avenrun.l[0] / (double) load_ave.tl_lscale));
# endif	/* OSF_MIPS */

# if !defined (LDAV_DONE) && (defined (__MSDOS__) || defined (WINDOWS32))
#  define LDAV_DONE

  /* A faithful emulation is going to have to be saved for a rainy day.  */
  for ( ; elem < nelem; elem++)
    {
      loadavg[elem] = 0.0;
    }
# endif  /* __MSDOS__ || WINDOWS32 */

# if !defined (LDAV_DONE) && defined (OSF_ALPHA)
#  define LDAV_DONE

  struct tbl_loadavg load_ave;
  table (TBL_LOADAVG, 0, &load_ave, 1, sizeof (load_ave));
  for (elem = 0; elem < nelem; elem++)
    loadavg[elem]
      = (load_ave.tl_lscale == 0
       ? load_ave.tl_avenrun.d[elem]
       : (load_ave.tl_avenrun.l[elem] / (double) load_ave.tl_lscale));
# endif /* OSF_ALPHA */

# if !defined (LDAV_DONE) && defined (VMS)
  /* VMS specific code -- read from the Load Ave driver.  */

  LOAD_AVE_TYPE load_ave[3];
  static int getloadavg_initialized = 0;
#  ifdef eunice
  struct
  {
    int dsc$w_length;
    char *dsc$a_pointer;
  } descriptor;
#  endif

  /* Ensure that there is a channel open to the load ave device.  */
  if (!getloadavg_initialized)
    {
      /* Attempt to open the channel.  */
#  ifdef eunice
      descriptor.dsc$w_length = 18;
      descriptor.dsc$a_pointer = "$$VMS_LOAD_AVERAGE";
#  else
      $DESCRIPTOR (descriptor, "LAV0:");
#  endif
      if (sys$assign (&descriptor, &channel, 0, 0) & 1)
	getloadavg_initialized = 1;
    }

  /* Read the load average vector.  */
  if (getloadavg_initialized
      && !(sys$qiow (0, channel, IO$_READVBLK, 0, 0, 0,
		     load_ave, 12, 0, 0, 0, 0) & 1))
    {
      sys$dassgn (channel);
      getloadavg_initialized = 0;
    }

  if (!getloadavg_initialized)
    return -1;
# endif /* VMS */

# if !defined (LDAV_DONE) && defined(LOAD_AVE_TYPE) && !defined(VMS)

  /* UNIX-specific code -- read the average from /dev/kmem.  */

#  define LDAV_PRIVILEGED		/* This code requires special installation.  */

  LOAD_AVE_TYPE load_ave[3];

  /* Get the address of LDAV_SYMBOL.  */
  if (offset == 0)
    {
#  ifndef sgi
#   ifndef NLIST_STRUCT
      strcpy (nl[0].n_name, LDAV_SYMBOL);
      strcpy (nl[1].n_name, "");
#   else /* NLIST_STRUCT */
#    ifdef HAVE_STRUCT_NLIST_N_UN_N_NAME
      nl[0].n_un.n_name = LDAV_SYMBOL;
      nl[1].n_un.n_name = 0;
#    else /* not HAVE_STRUCT_NLIST_N_UN_N_NAME */
      nl[0].n_name = LDAV_SYMBOL;
      nl[1].n_name = 0;
#    endif /* not HAVE_STRUCT_NLIST_N_UN_N_NAME */
#   endif /* NLIST_STRUCT */

#   ifndef SUNOS_5
      if (
#    if !(defined (_AIX) && !defined (ps2))
	  nlist (KERNEL_FILE, nl)
#    else  /* _AIX */
	  knlist (nl, 1, sizeof (nl[0]))
#    endif
	  >= 0)
	  /* Omit "&& nl[0].n_type != 0 " -- it breaks on Sun386i.  */
	  {
#    ifdef FIXUP_KERNEL_SYMBOL_ADDR
	    FIXUP_KERNEL_SYMBOL_ADDR (nl);
#    endif
	    offset = nl[0].n_value;
	  }
#   endif /* !SUNOS_5 */
#  else  /* sgi */
      int ldav_off;

      ldav_off = sysmp (MP_KERNADDR, MPKA_AVENRUN);
      if (ldav_off != -1)
	offset = (long) ldav_off & 0x7fffffff;
#  endif /* sgi */
    }

  /* Make sure we have /dev/kmem open.  */
  if (!getloadavg_initialized)
    {
#  ifndef SUNOS_5
      channel = open ("/dev/kmem", 0);
      if (channel >= 0)
	{
	  /* Set the channel to close on exec, so it does not
	     litter any child's descriptor table.  */
#   ifdef F_SETFD
#    ifndef FD_CLOEXEC
#     define FD_CLOEXEC 1
#    endif
	  (void) fcntl (channel, F_SETFD, FD_CLOEXEC);
#   endif
	  getloadavg_initialized = 1;
	}
#  else /* SUNOS_5 */
      /* We pass 0 for the kernel, corefile, and swapfile names
	 to use the currently running kernel.  */
      kd = kvm_open (0, 0, 0, O_RDONLY, 0);
      if (kd != 0)
	{
	  /* nlist the currently running kernel.  */
	  kvm_nlist (kd, nl);
	  offset = nl[0].n_value;
	  getloadavg_initialized = 1;
	}
#  endif /* SUNOS_5 */
    }

  /* If we can, get the load average values.  */
  if (offset && getloadavg_initialized)
    {
      /* Try to read the load.  */
#  ifndef SUNOS_5
      if (lseek (channel, offset, 0) == -1L
	  || read (channel, (char *) load_ave, sizeof (load_ave))
	  != sizeof (load_ave))
	{
	  close (channel);
	  getloadavg_initialized = 0;
	}
#  else  /* SUNOS_5 */
      if (kvm_read (kd, offset, (char *) load_ave, sizeof (load_ave))
	  != sizeof (load_ave))
        {
          kvm_close (kd);
          getloadavg_initialized = 0;
	}
#  endif /* SUNOS_5 */
    }

  if (offset == 0 || !getloadavg_initialized)
    return -1;
# endif /* LOAD_AVE_TYPE and not VMS */

# if !defined (LDAV_DONE) && defined (LOAD_AVE_TYPE) /* Including VMS.  */
  if (nelem > 0)
    loadavg[elem++] = LDAV_CVT (load_ave[0]);
  if (nelem > 1)
    loadavg[elem++] = LDAV_CVT (load_ave[1]);
  if (nelem > 2)
    loadavg[elem++] = LDAV_CVT (load_ave[2]);

#  define LDAV_DONE
# endif /* !LDAV_DONE && LOAD_AVE_TYPE */

# ifdef LDAV_DONE
  return elem;
# else
  /* Set errno to zero to indicate that there was no particular error;
     this function just can't work at all on this system.  */
  errno = 0;
  return -1;
# endif
}
예제 #11
0
파일: cpu.c 프로젝트: Shmuma/z
static int get_cpu_data(
	const char* cpuname,
	unsigned long long *idle,
	unsigned long long *system,
	unsigned long long *user,
	unsigned long long *iowait)
{
	kstat_ctl_t	*kc;
	kstat_t		*k;
	cpu_stat_t	*cpu;

	static int			first_run = 1;
	static unsigned long long	old_cpu[CPU_STATES];
	unsigned long long		new_cpu[CPU_STATES];

	char ks_name[MAX_STRING_LEN];

	int cpu_count = 0, i;

	assert(cpuname);
	assert(idle);
	assert(system);
	assert(user);
	assert(iowait);

	if(first_run)    for(i = 0; i < CPU_STATES; old_cpu[i++] = 0LL);

	for(i = 0; i < CPU_STATES; new_cpu[i++] = 0LL);

        zbx_snprintf(ks_name, sizeof(ks_name), "cpu_stat%s", cpuname);

	kc = kstat_open();
	if (kc)
	{
		k = kc->kc_chain;
		while (k)
		{
			if ((strncmp(k->ks_name, ks_name, strlen(ks_name)) == 0)
				&& (kstat_read(kc, k, NULL) != -1)
				)
			{
				cpu = (cpu_stat_t *) k->ks_data;

				for(i = 0; i < CPU_STATES; i++)
					new_cpu[i] += cpu->cpu_sysinfo.cpu[i];

				cpu_count += 1;
			}
			k = k->ks_next;
		}
		kstat_close(kc);
	}
    
	if(first_run)
	{
		*idle = *system = *iowait = *user = 0LL;
		first_run = 0;
	}
	else
	{
		*idle	=  new_cpu[CPU_IDLE]	- old_cpu[CPU_IDLE];
		*system =  new_cpu[CPU_KERNEL]	- old_cpu[CPU_KERNEL];
		*iowait =  new_cpu[CPU_WAIT]	- old_cpu[CPU_WAIT];
		*user	=  new_cpu[CPU_USER]	- old_cpu[CPU_USER];
	}
	
	for(i = 0; i < CPU_STATES; i++)	old_cpu[i] = new_cpu[i];
	
	return cpu_count;
}
예제 #12
0
    /*
     * Load the latest CPU usage statistics
     */
int netsnmp_cpu_arch_load( netsnmp_cache *cache, void *magic ) {
    int               i=1;
    kstat_t          *ksp;
    cpu_stat_t        cs;
    netsnmp_cpu_info *cpu = netsnmp_cpu_get_byIdx( -1, 0 );
    netsnmp_cpu_info *cpu2;

        /* Clear overall stats, ready for summing individual CPUs */
    cpu->user_ticks = 0;
    cpu->idle_ticks = 0;
    cpu->kern_ticks = 0;
    cpu->wait_ticks = 0;
    cpu->sys2_ticks = 0;
    cpu->swapIn       = 0;
    cpu->swapOut      = 0;
    cpu->nInterrupts  = 0;
    cpu->nCtxSwitches = 0;

    kstat_chain_update( kstat_fd );
    DEBUGMSGTL(("cpu", "cpu_kstat load\n "));
    for (ksp = kstat_fd->kc_chain; ksp != NULL; ksp = ksp->ks_next) {
        if (ksp->ks_flags & KSTAT_FLAG_INVALID)
            continue;
        if (strcmp(ksp->ks_module, "cpu_stat") == 0) {
            i    = ksp->ks_instance;
            cpu2 = netsnmp_cpu_get_byIdx( i, 0 );
            if ( !cpu2 )  
                break;   /* or continue ? */  /* Skip new CPUs */
            if ((ksp->ks_type != KSTAT_TYPE_RAW) ||
                (ksp->ks_data_size != sizeof(cs))||
                (kstat_read(kstat_fd, ksp, &cs) == -1)) {
                DEBUGMSGTL(("cpu", "cpu_kstat load failed (%d)\n ", i));
                break;   /* or continue ? */
            }

            cpu2->user_ticks = (unsigned long long)cs.cpu_sysinfo.cpu[CPU_USER];
            cpu2->idle_ticks = (unsigned long long)cs.cpu_sysinfo.cpu[CPU_IDLE];
            cpu2->kern_ticks = (unsigned long long)cs.cpu_sysinfo.cpu[CPU_KERNEL];
            cpu2->wait_ticks = (unsigned long long)cs.cpu_sysinfo.cpu[CPU_WAIT];
              /* or cs.cpu_sysinfo.wait[W_IO]+cs.cpu_sysinfo.wait[W_PIO] */
            cpu2->sys2_ticks = (unsigned long long)cpu2->kern_ticks+cpu2->wait_ticks;
                /* nice_ticks, intrpt_ticks, sirq_ticks unused */

                /* sum these for the overall stats */
            cpu->user_ticks += (unsigned long long)cs.cpu_sysinfo.cpu[CPU_USER];
            cpu->idle_ticks += (unsigned long long)cs.cpu_sysinfo.cpu[CPU_IDLE];
            cpu->kern_ticks += (unsigned long long)cs.cpu_sysinfo.cpu[CPU_KERNEL];
            cpu->wait_ticks += (unsigned long long)cs.cpu_sysinfo.cpu[CPU_WAIT];
              /* or cs.cpu_sysinfo.wait[W_IO]+cs.cpu_sysinfo.wait[W_PIO] */
            cpu->sys2_ticks += (unsigned long long)cpu2->kern_ticks+cpu2->wait_ticks;

                /*
                 * Interrupt/Context Switch statistics
                 *   XXX - Do these really belong here ?
                 */
            cpu->swapIn       += (unsigned long long)cs.cpu_vminfo.swapin;
            cpu->swapOut      += (unsigned long long)cs.cpu_vminfo.swapout;
            cpu->pageIn       += (unsigned long long)cs.cpu_sysinfo.bread;
            cpu->pageOut      += (unsigned long long)cs.cpu_sysinfo.bwrite;
            cpu->nInterrupts  += (unsigned long long)cs.cpu_sysinfo.intr;
            cpu->nCtxSwitches += (unsigned long long)cs.cpu_sysinfo.pswitch;
        }
    }
    return 0;
}
예제 #13
0
uv_err_t uv_cpu_info(uv_cpu_info_t** cpu_infos, int* count) {
  int           lookup_instance;
  kstat_ctl_t   *kc;
  kstat_t       *ksp;
  kstat_named_t *knp;
  uv_cpu_info_t* cpu_info;

  if ((kc = kstat_open()) == NULL) {
    return uv__new_sys_error(errno);
  }

  /* Get count of cpus */
  lookup_instance = 0;
  while ((ksp = kstat_lookup(kc, (char *)"cpu_info", lookup_instance, NULL))) {
    lookup_instance++;
  }

  *cpu_infos = (uv_cpu_info_t*)
    malloc(lookup_instance * sizeof(uv_cpu_info_t));
  if (!(*cpu_infos)) {
    return uv__new_artificial_error(UV_ENOMEM);
  }

  *count = lookup_instance;

  cpu_info = *cpu_infos;
  lookup_instance = 0;
  while ((ksp = kstat_lookup(kc, (char *)"cpu_info", lookup_instance, NULL))) {
    if (kstat_read(kc, ksp, NULL) == -1) {
      /*
       * It is deeply annoying, but some kstats can return errors
       * under otherwise routine conditions.  (ACPI is one
       * offender; there are surely others.)  To prevent these
       * fouled kstats from completely ruining our day, we assign
       * an "error" member to the return value that consists of
       * the strerror().
       */
      cpu_info->speed = 0;
      cpu_info->model = NULL;
    } else {
      knp = (kstat_named_t *) kstat_data_lookup(ksp, (char *)"clock_MHz");
      assert(knp->data_type == KSTAT_DATA_INT32);
      cpu_info->speed = knp->value.i32;

      knp = (kstat_named_t *) kstat_data_lookup(ksp, (char *)"brand");
      assert(knp->data_type == KSTAT_DATA_STRING);
      cpu_info->model = KSTAT_NAMED_STR_PTR(knp);
    }

    lookup_instance++;
    cpu_info++;
  }

  cpu_info = *cpu_infos;
  lookup_instance = 0;
  while ((ksp = kstat_lookup(kc, (char *)"cpu", lookup_instance, (char *)"sys"))){

    if (kstat_read(kc, ksp, NULL) == -1) {
      cpu_info->cpu_times.user = 0;
      cpu_info->cpu_times.nice = 0;
      cpu_info->cpu_times.sys = 0;
      cpu_info->cpu_times.idle = 0;
      cpu_info->cpu_times.irq = 0;
    } else {
      knp = (kstat_named_t *) kstat_data_lookup(ksp, (char *)"cpu_ticks_user");
      assert(knp->data_type == KSTAT_DATA_UINT64);
      cpu_info->cpu_times.user = knp->value.ui64;

      knp = (kstat_named_t *) kstat_data_lookup(ksp, (char *)"cpu_ticks_kernel");
      assert(knp->data_type == KSTAT_DATA_UINT64);
      cpu_info->cpu_times.sys = knp->value.ui64;

      knp = (kstat_named_t *) kstat_data_lookup(ksp, (char *)"cpu_ticks_idle");
      assert(knp->data_type == KSTAT_DATA_UINT64);
      cpu_info->cpu_times.idle = knp->value.ui64;

      knp = (kstat_named_t *) kstat_data_lookup(ksp, (char *)"intr");
      assert(knp->data_type == KSTAT_DATA_UINT64);
      cpu_info->cpu_times.irq = knp->value.ui64;
      cpu_info->cpu_times.nice = 0;
    }

    lookup_instance++;
    cpu_info++;
  }

  kstat_close(kc);

  return uv_ok_;
}
예제 #14
0
    void
    CPU_Load_Monitor::access_kstats (unsigned long *which_idle)
    {
      this->kstats_ = kstat_open ();

      if (this->kstats_ == 0)
        {
          ACE_ERROR ((LM_ERROR,
                      ACE_TEXT ("opening kstats file failed\n")));
          return;
        }

      this->kstat_id_ = this->kstats_->kc_chain_id;

      while (true)
        {
          this->kernel_ = 0UL;
          this->wait_ = 0UL;
          this->user_ = 0UL;
          (*which_idle) = 0UL;

          /// Unlike Linux's "/proc/stat", there is no entry for total CPU
          /// stats, so we have to sum them manually.
          for (this->kstat_ = this->kstats_->kc_chain;
               this->kstat_ != 0;
               this->kstat_ = this->kstat_->ks_next)
            {
              int result = ACE_OS::strncmp (this->kstat_->ks_name,
                                            "cpu_stat",
                                            ACE_OS::strlen ("cpu_stat"));

              if (result == 0)
                {
                  /// Because the kstat chain can change dynamically,
                  /// watch the chain ID and restart the walk if the ID
                  /// differs from what we saw during the walk. The restart
                  /// is done by breaking from the cycle with kstat_ not 0.

                  kid_t kstat_id = kstat_read (this->kstats_, this->kstat_, 0);

                  if (kstat_id != this->kstat_id_)
                    {
                      break;
                    }

                  cpu_stat_t &kstat_cpu =
                    *((cpu_stat_t *) this->kstat_->ks_data);

                  this->kernel_ += kstat_cpu.cpu_sysinfo.cpu[CPU_KERNEL];
                  this->wait_ += kstat_cpu.cpu_sysinfo.cpu[CPU_WAIT];
                  this->user_ += kstat_cpu.cpu_sysinfo.cpu[CPU_USER];
                  (*which_idle) += kstat_cpu.cpu_sysinfo.cpu[CPU_IDLE];
                }
            }

          if (this->kstat_ != 0)
            {
              /// The ID changed underneath us, so get the new one and
              /// start again.
              this->kstat_id_ = kstat_chain_update (this->kstats_);

              if (! this->kstat_id_ > 0)
                {
                  ACE_ERROR ((LM_ERROR,
                              ACE_TEXT ("kstat chain update ")
                              ACE_TEXT ("returned null id\n")));
                  return;
                }
            }
          else
            {
              /// Clean run, exit the WHILE loop.
              break;
            }
        }

      int status = kstat_close (this->kstats_);

      if (status != 0)
        {
          ACE_ERROR ((LM_ERROR,
                      ACE_TEXT ("closing kstats file failed\n")));
        }
    }
예제 #15
0
sg_page_stats *sg_get_page_stats() {
#ifdef SOLARIS
    kstat_ctl_t *kc;
    kstat_t *ksp;
    cpu_stat_t cs;
#endif
#if defined(LINUX) || defined(CYGWIN)
    FILE *f;
    char *line_ptr;
#endif
#if defined(FREEBSD) || defined(DFBSD)
    size_t size;
#endif
#if defined(NETBSD) || defined(OPENBSD)
    struct uvmexp *uvm;
#endif

    page_stats.systime = time(NULL);
    page_stats.pages_pagein=0;
    page_stats.pages_pageout=0;

#ifdef SOLARIS
    if ((kc = kstat_open()) == NULL) {
        sg_set_error(SG_ERROR_KSTAT_OPEN, NULL);
        return NULL;
    }
    for (ksp = kc->kc_chain; ksp!=NULL; ksp = ksp->ks_next) {
        if ((strcmp(ksp->ks_module, "cpu_stat")) != 0) continue;
        if (kstat_read(kc, ksp, &cs) == -1) {
            continue;
        }

        page_stats.pages_pagein+=(long long)cs.cpu_vminfo.pgpgin;
        page_stats.pages_pageout+=(long long)cs.cpu_vminfo.pgpgout;
    }

    kstat_close(kc);
#endif
#if defined(LINUX) || defined(CYGWIN)
    if ((f = fopen("/proc/vmstat", "r")) != NULL) {
        while ((line_ptr = sg_f_read_line(f, "")) != NULL) {
            long long value;

            if (sscanf(line_ptr, "%*s %lld", &value) != 1) {
                continue;
            }

            if (strncmp(line_ptr, "pgpgin ", 7) == 0) {
                page_stats.pages_pagein = value;
            } else if (strncmp(line_ptr, "pgpgout ", 8) == 0) {
                page_stats.pages_pageout = value;
            }
        }

        fclose(f);
    } else if ((f = fopen("/proc/stat", "r")) != NULL) {
        if ((line_ptr = sg_f_read_line(f, "page")) == NULL) {
            sg_set_error(SG_ERROR_PARSE, "page");
            fclose(f);
            return NULL;
        }

        if (sscanf(line_ptr, "page %lld %lld", &page_stats.pages_pagein, &page_stats.pages_pageout) != 2) {
            sg_set_error(SG_ERROR_PARSE, "page");
            fclose(f);
            return NULL;
        }

        fclose(f);
    } else {
        sg_set_error(SG_ERROR_OPEN, "/proc/stat");
        return NULL;
    }
#endif
#if defined(FREEBSD) || defined(DFBSD)
    size = sizeof page_stats.pages_pagein;
    if (sysctlbyname("vm.stats.vm.v_swappgsin", &page_stats.pages_pagein, &size, NULL, 0) < 0) {
        sg_set_error(SG_ERROR_SYSCTLBYNAME, "vm.stats.vm.v_swappgsin");
        return NULL;
    }
    size = sizeof page_stats.pages_pageout;
    if (sysctlbyname("vm.stats.vm.v_swappgsout", &page_stats.pages_pageout, &size, NULL, 0) < 0) {
        sg_set_error(SG_ERROR_SYSCTLBYNAME, "vm.stats.vm.v_swappgsout");
        return NULL;
    }
#endif
#if defined(NETBSD) || defined(OPENBSD)
    if ((uvm = sg_get_uvmexp()) == NULL) {
        return NULL;
    }

    page_stats.pages_pagein = uvm->pgswapin;
    page_stats.pages_pageout = uvm->pgswapout;
#endif

    return &page_stats;
}
예제 #16
0
파일: disk.c 프로젝트: Civil/collectd
static int disk_read (void)
{
#if HAVE_IOKIT_IOKITLIB_H
	io_registry_entry_t	disk;
	io_registry_entry_t	disk_child;
	io_iterator_t		disk_list;
	CFDictionaryRef		props_dict;
	CFDictionaryRef		stats_dict;
	CFDictionaryRef		child_dict;
	CFStringRef		tmp_cf_string_ref;
	kern_return_t		status;

	signed long long read_ops;
	signed long long read_byt;
	signed long long read_tme;
	signed long long write_ops;
	signed long long write_byt;
	signed long long write_tme;

	int  disk_major;
	int  disk_minor;
	char disk_name[DATA_MAX_NAME_LEN];
	char disk_name_bsd[DATA_MAX_NAME_LEN];

	/* Get the list of all disk objects. */
	if (IOServiceGetMatchingServices (io_master_port,
				IOServiceMatching (kIOBlockStorageDriverClass),
				&disk_list) != kIOReturnSuccess)
	{
		ERROR ("disk plugin: IOServiceGetMatchingServices failed.");
		return (-1);
	}

	while ((disk = IOIteratorNext (disk_list)) != 0)
	{
		props_dict = NULL;
		stats_dict = NULL;
		child_dict = NULL;

		/* `disk_child' must be released */
		if ((status = IORegistryEntryGetChildEntry (disk, kIOServicePlane, &disk_child))
			       	!= kIOReturnSuccess)
		{
			/* This fails for example for DVD/CD drives.. */
			DEBUG ("IORegistryEntryGetChildEntry (disk) failed: 0x%08x", status);
			IOObjectRelease (disk);
			continue;
		}

		/* We create `props_dict' => we need to release it later */
		if (IORegistryEntryCreateCFProperties (disk,
					(CFMutableDictionaryRef *) &props_dict,
					kCFAllocatorDefault,
					kNilOptions)
				!= kIOReturnSuccess)
		{
			ERROR ("disk-plugin: IORegistryEntryCreateCFProperties failed.");
			IOObjectRelease (disk_child);
			IOObjectRelease (disk);
			continue;
		}

		if (props_dict == NULL)
		{
			DEBUG ("IORegistryEntryCreateCFProperties (disk) failed.");
			IOObjectRelease (disk_child);
			IOObjectRelease (disk);
			continue;
		}

		/* tmp_cf_string_ref doesn't need to be released. */
		tmp_cf_string_ref = (CFStringRef) CFDictionaryGetValue (props_dict,
				CFSTR(kIOBSDNameKey));
		if (!tmp_cf_string_ref)
		{
			DEBUG ("disk plugin: CFDictionaryGetValue("
					"kIOBSDNameKey) failed.");
			CFRelease (props_dict);
			IOObjectRelease (disk_child);
			IOObjectRelease (disk);
			continue;
		}
		assert (CFGetTypeID (tmp_cf_string_ref) == CFStringGetTypeID ());

		memset (disk_name_bsd, 0, sizeof (disk_name_bsd));
		CFStringGetCString (tmp_cf_string_ref,
				disk_name_bsd, sizeof (disk_name_bsd),
				kCFStringEncodingUTF8);
		if (disk_name_bsd[0] == 0)
		{
			ERROR ("disk plugin: CFStringGetCString() failed.");
			CFRelease (props_dict);
			IOObjectRelease (disk_child);
			IOObjectRelease (disk);
			continue;
		}
		DEBUG ("disk plugin: disk_name_bsd = \"%s\"", disk_name_bsd);

		stats_dict = (CFDictionaryRef) CFDictionaryGetValue (props_dict,
				CFSTR (kIOBlockStorageDriverStatisticsKey));

		if (stats_dict == NULL)
		{
			DEBUG ("disk plugin: CFDictionaryGetValue ("
					"%s) failed.",
				       	kIOBlockStorageDriverStatisticsKey);
			CFRelease (props_dict);
			IOObjectRelease (disk_child);
			IOObjectRelease (disk);
			continue;
		}

		if (IORegistryEntryCreateCFProperties (disk_child,
					(CFMutableDictionaryRef *) &child_dict,
					kCFAllocatorDefault,
					kNilOptions)
				!= kIOReturnSuccess)
		{
			DEBUG ("disk plugin: IORegistryEntryCreateCFProperties ("
					"disk_child) failed.");
			IOObjectRelease (disk_child);
			CFRelease (props_dict);
			IOObjectRelease (disk);
			continue;
		}

		/* kIOBSDNameKey */
		disk_major = (int) dict_get_value (child_dict,
			       	kIOBSDMajorKey);
		disk_minor = (int) dict_get_value (child_dict,
			       	kIOBSDMinorKey);
		read_ops  = dict_get_value (stats_dict,
				kIOBlockStorageDriverStatisticsReadsKey);
		read_byt  = dict_get_value (stats_dict,
				kIOBlockStorageDriverStatisticsBytesReadKey);
		read_tme  = dict_get_value (stats_dict,
				kIOBlockStorageDriverStatisticsTotalReadTimeKey);
		write_ops = dict_get_value (stats_dict,
				kIOBlockStorageDriverStatisticsWritesKey);
		write_byt = dict_get_value (stats_dict,
				kIOBlockStorageDriverStatisticsBytesWrittenKey);
		/* This property describes the number of nanoseconds spent
		 * performing writes since the block storage driver was
		 * instantiated. It is one of the statistic entries listed
		 * under the top-level kIOBlockStorageDriverStatisticsKey
		 * property table. It has an OSNumber value. */
		write_tme = dict_get_value (stats_dict,
				kIOBlockStorageDriverStatisticsTotalWriteTimeKey);

		if (use_bsd_name)
			sstrncpy (disk_name, disk_name_bsd, sizeof (disk_name));
		else
			ssnprintf (disk_name, sizeof (disk_name), "%i-%i",
					disk_major, disk_minor);
		DEBUG ("disk plugin: disk_name = \"%s\"", disk_name);

		if ((read_byt != -1LL) || (write_byt != -1LL))
			disk_submit (disk_name, "disk_octets", read_byt, write_byt);
		if ((read_ops != -1LL) || (write_ops != -1LL))
			disk_submit (disk_name, "disk_ops", read_ops, write_ops);
		if ((read_tme != -1LL) || (write_tme != -1LL))
			disk_submit (disk_name, "disk_time",
					read_tme / 1000,
					write_tme / 1000);

		CFRelease (child_dict);
		IOObjectRelease (disk_child);
		CFRelease (props_dict);
		IOObjectRelease (disk);
	}
	IOObjectRelease (disk_list);
/* #endif HAVE_IOKIT_IOKITLIB_H */

#elif KERNEL_LINUX
	FILE *fh;
	char buffer[1024];
	
	char *fields[32];
	int numfields;
	int fieldshift = 0;

	int minor = 0;

	derive_t read_sectors  = 0;
	derive_t write_sectors = 0;

	derive_t read_ops      = 0;
	derive_t read_merged   = 0;
	derive_t read_time     = 0;
	derive_t write_ops     = 0;
	derive_t write_merged  = 0;
	derive_t write_time    = 0;
	gauge_t in_progress    = NAN;
	int is_disk = 0;

	diskstats_t *ds, *pre_ds;

	if ((fh = fopen ("/proc/diskstats", "r")) == NULL)
	{
		fh = fopen ("/proc/partitions", "r");
		if (fh == NULL)
		{
			ERROR ("disk plugin: fopen (/proc/{diskstats,partitions}) failed.");
			return (-1);
		}

		/* Kernel is 2.4.* */
		fieldshift = 1;
	}

#if HAVE_LIBUDEV
	handle_udev = udev_new();
#endif

	while (fgets (buffer, sizeof (buffer), fh) != NULL)
	{
		char *disk_name;
		char *output_name;
		char *alt_name;

		numfields = strsplit (buffer, fields, 32);

		if ((numfields != (14 + fieldshift)) && (numfields != 7))
			continue;

		minor = atoll (fields[1]);

		disk_name = fields[2 + fieldshift];

		for (ds = disklist, pre_ds = disklist; ds != NULL; pre_ds = ds, ds = ds->next)
			if (strcmp (disk_name, ds->name) == 0)
				break;

		if (ds == NULL)
		{
			if ((ds = (diskstats_t *) calloc (1, sizeof (diskstats_t))) == NULL)
				continue;

			if ((ds->name = strdup (disk_name)) == NULL)
			{
				free (ds);
				continue;
			}

			if (pre_ds == NULL)
				disklist = ds;
			else
				pre_ds->next = ds;
		}

		is_disk = 0;
		if (numfields == 7)
		{
			/* Kernel 2.6, Partition */
			read_ops      = atoll (fields[3]);
			read_sectors  = atoll (fields[4]);
			write_ops     = atoll (fields[5]);
			write_sectors = atoll (fields[6]);
		}
		else if (numfields == (14 + fieldshift))
		{
			read_ops  =  atoll (fields[3 + fieldshift]);
			write_ops =  atoll (fields[7 + fieldshift]);

			read_sectors  = atoll (fields[5 + fieldshift]);
			write_sectors = atoll (fields[9 + fieldshift]);

			if ((fieldshift == 0) || (minor == 0))
			{
				is_disk = 1;
				read_merged  = atoll (fields[4 + fieldshift]);
				read_time    = atoll (fields[6 + fieldshift]);
				write_merged = atoll (fields[8 + fieldshift]);
				write_time   = atoll (fields[10+ fieldshift]);

				in_progress = atof (fields[11 + fieldshift]);
			}
		}
		else
		{
			DEBUG ("numfields = %i; => unknown file format.", numfields);
			continue;
		}

		{
			derive_t diff_read_sectors;
			derive_t diff_write_sectors;

		/* If the counter wraps around, it's only 32 bits.. */
			if (read_sectors < ds->read_sectors)
				diff_read_sectors = 1 + read_sectors
					+ (UINT_MAX - ds->read_sectors);
			else
				diff_read_sectors = read_sectors - ds->read_sectors;
			if (write_sectors < ds->write_sectors)
				diff_write_sectors = 1 + write_sectors
					+ (UINT_MAX - ds->write_sectors);
			else
				diff_write_sectors = write_sectors - ds->write_sectors;

			ds->read_bytes += 512 * diff_read_sectors;
			ds->write_bytes += 512 * diff_write_sectors;
			ds->read_sectors = read_sectors;
			ds->write_sectors = write_sectors;
		}

		/* Calculate the average time an io-op needs to complete */
		if (is_disk)
		{
			derive_t diff_read_ops;
			derive_t diff_write_ops;
			derive_t diff_read_time;
			derive_t diff_write_time;

			if (read_ops < ds->read_ops)
				diff_read_ops = 1 + read_ops
					+ (UINT_MAX - ds->read_ops);
			else
				diff_read_ops = read_ops - ds->read_ops;
			DEBUG ("disk plugin: disk_name = %s; read_ops = %"PRIi64"; "
					"ds->read_ops = %"PRIi64"; diff_read_ops = %"PRIi64";",
					disk_name,
					read_ops, ds->read_ops, diff_read_ops);

			if (write_ops < ds->write_ops)
				diff_write_ops = 1 + write_ops
					+ (UINT_MAX - ds->write_ops);
			else
				diff_write_ops = write_ops - ds->write_ops;

			if (read_time < ds->read_time)
				diff_read_time = 1 + read_time
					+ (UINT_MAX - ds->read_time);
			else
				diff_read_time = read_time - ds->read_time;

			if (write_time < ds->write_time)
				diff_write_time = 1 + write_time
					+ (UINT_MAX - ds->write_time);
			else
				diff_write_time = write_time - ds->write_time;

			if (diff_read_ops != 0)
				ds->avg_read_time += disk_calc_time_incr (
						diff_read_time, diff_read_ops);
			if (diff_write_ops != 0)
				ds->avg_write_time += disk_calc_time_incr (
						diff_write_time, diff_write_ops);

			ds->read_ops = read_ops;
			ds->read_time = read_time;
			ds->write_ops = write_ops;
			ds->write_time = write_time;
		} /* if (is_disk) */

		/* Don't write to the RRDs if we've just started.. */
		ds->poll_count++;
		if (ds->poll_count <= 2)
		{
			DEBUG ("disk plugin: (ds->poll_count = %i) <= "
					"(min_poll_count = 2); => Not writing.",
					ds->poll_count);
			continue;
		}

		if ((read_ops == 0) && (write_ops == 0))
		{
			DEBUG ("disk plugin: ((read_ops == 0) && "
					"(write_ops == 0)); => Not writing.");
			continue;
		}

		output_name = disk_name;

#if HAVE_LIBUDEV
		alt_name = disk_udev_attr_name (handle_udev, disk_name,
				conf_udev_name_attr);
#else
		alt_name = NULL;
#endif
		if (alt_name != NULL)
			output_name = alt_name;

		if ((ds->read_bytes != 0) || (ds->write_bytes != 0))
			disk_submit (output_name, "disk_octets",
					ds->read_bytes, ds->write_bytes);

		if ((ds->read_ops != 0) || (ds->write_ops != 0))
			disk_submit (output_name, "disk_ops",
					read_ops, write_ops);

		if ((ds->avg_read_time != 0) || (ds->avg_write_time != 0))
			disk_submit (output_name, "disk_time",
					ds->avg_read_time, ds->avg_write_time);

		if (is_disk)
		{
			disk_submit (output_name, "disk_merged",
					read_merged, write_merged);
			submit_in_progress (output_name, in_progress);
		} /* if (is_disk) */

		/* release udev-based alternate name, if allocated */
		free(alt_name);
	} /* while (fgets (buffer, sizeof (buffer), fh) != NULL) */

#if HAVE_LIBUDEV
	udev_unref(handle_udev);
#endif

	fclose (fh);
/* #endif defined(KERNEL_LINUX) */

#elif HAVE_LIBKSTAT
# if HAVE_KSTAT_IO_T_WRITES && HAVE_KSTAT_IO_T_NWRITES && HAVE_KSTAT_IO_T_WTIME
#  define KIO_ROCTETS reads
#  define KIO_WOCTETS writes
#  define KIO_ROPS    nreads
#  define KIO_WOPS    nwrites
#  define KIO_RTIME   rtime
#  define KIO_WTIME   wtime
# elif HAVE_KSTAT_IO_T_NWRITTEN && HAVE_KSTAT_IO_T_WRITES && HAVE_KSTAT_IO_T_WTIME
#  define KIO_ROCTETS nread
#  define KIO_WOCTETS nwritten
#  define KIO_ROPS    reads
#  define KIO_WOPS    writes
#  define KIO_RTIME   rtime
#  define KIO_WTIME   wtime
# else
#  error "kstat_io_t does not have the required members"
# endif
	static kstat_io_t kio;
	int i;

	if (kc == NULL)
		return (-1);

	for (i = 0; i < numdisk; i++)
	{
		if (kstat_read (kc, ksp[i], &kio) == -1)
			continue;

		if (strncmp (ksp[i]->ks_class, "disk", 4) == 0)
		{
			disk_submit (ksp[i]->ks_name, "disk_octets",
					kio.KIO_ROCTETS, kio.KIO_WOCTETS);
			disk_submit (ksp[i]->ks_name, "disk_ops",
					kio.KIO_ROPS, kio.KIO_WOPS);
			/* FIXME: Convert this to microseconds if necessary */
			disk_submit (ksp[i]->ks_name, "disk_time",
					kio.KIO_RTIME, kio.KIO_WTIME);
		}
		else if (strncmp (ksp[i]->ks_class, "partition", 9) == 0)
		{
			disk_submit (ksp[i]->ks_name, "disk_octets",
					kio.KIO_ROCTETS, kio.KIO_WOCTETS);
			disk_submit (ksp[i]->ks_name, "disk_ops",
					kio.KIO_ROPS, kio.KIO_WOPS);
		}
	}
/* #endif defined(HAVE_LIBKSTAT) */

#elif defined(HAVE_LIBSTATGRAB)
	sg_disk_io_stats *ds;
	int disks, counter;
	char name[DATA_MAX_NAME_LEN];
	
	if ((ds = sg_get_disk_io_stats(&disks)) == NULL)
		return (0);
		
	for (counter=0; counter < disks; counter++) {
		strncpy(name, ds->disk_name, sizeof(name));
		name[sizeof(name)-1] = '\0'; /* strncpy doesn't terminate longer strings */
		disk_submit (name, "disk_octets", ds->read_bytes, ds->write_bytes);
		ds++;
	}
/* #endif defined(HAVE_LIBSTATGRAB) */

#elif defined(HAVE_PERFSTAT)
	derive_t read_sectors;
	derive_t write_sectors;
	derive_t read_time;
	derive_t write_time;
	derive_t read_ops;
	derive_t write_ops;
	perfstat_id_t firstpath;
	int rnumdisk;
	int i;

	if ((numdisk = perfstat_disk(NULL, NULL, sizeof(perfstat_disk_t), 0)) < 0) 
	{
		char errbuf[1024];
		WARNING ("disk plugin: perfstat_disk: %s",
				sstrerror (errno, errbuf, sizeof (errbuf)));
		return (-1);
	}

	if (numdisk != pnumdisk || stat_disk==NULL) {
		if (stat_disk!=NULL) 
			free(stat_disk);
		stat_disk = (perfstat_disk_t *)calloc(numdisk, sizeof(perfstat_disk_t));
	} 
	pnumdisk = numdisk;

	firstpath.name[0]='\0';
	if ((rnumdisk = perfstat_disk(&firstpath, stat_disk, sizeof(perfstat_disk_t), numdisk)) < 0) 
	{
		char errbuf[1024];
		WARNING ("disk plugin: perfstat_disk : %s",
				sstrerror (errno, errbuf, sizeof (errbuf)));
		return (-1);
	}

	for (i = 0; i < rnumdisk; i++) 
	{
		read_sectors = stat_disk[i].rblks*stat_disk[i].bsize;
		write_sectors = stat_disk[i].wblks*stat_disk[i].bsize;
		disk_submit (stat_disk[i].name, "disk_octets", read_sectors, write_sectors);

		read_ops = stat_disk[i].xrate;
		write_ops = stat_disk[i].xfers - stat_disk[i].xrate;
		disk_submit (stat_disk[i].name, "disk_ops", read_ops, write_ops);

		read_time = stat_disk[i].rserv;
		read_time *= ((double)(_system_configuration.Xint)/(double)(_system_configuration.Xfrac)) / 1000000.0;
		write_time = stat_disk[i].wserv;
		write_time *= ((double)(_system_configuration.Xint)/(double)(_system_configuration.Xfrac)) / 1000000.0;
		disk_submit (stat_disk[i].name, "disk_time", read_time, write_time);
	}
#endif /* defined(HAVE_PERFSTAT) */

	return (0);
} /* int disk_read */
예제 #17
0
static int
hwloc_look_kstat(struct hwloc_topology *topology)
{
  /* FIXME this assumes that all packages are identical */
  char *CPUType = hwloc_solaris_get_chip_type();
  char *CPUModel = hwloc_solaris_get_chip_model();

  kstat_ctl_t *kc = kstat_open();
  kstat_t *ksp;
  kstat_named_t *stat;
  unsigned look_cores = 1, look_chips = 1;

  unsigned Pproc_max = 0;
  unsigned Pproc_alloc = 256;
  struct hwloc_solaris_Pproc {
    unsigned Lpkg, Ppkg, Lcore, Lproc;
  } * Pproc = malloc(Pproc_alloc * sizeof(*Pproc));

  unsigned Lproc_num = 0;
  unsigned Lproc_alloc = 256;
  struct hwloc_solaris_Lproc {
    unsigned Pproc;
  } * Lproc = malloc(Lproc_alloc * sizeof(*Lproc));

  unsigned Lcore_num = 0;
  unsigned Lcore_alloc = 256;
  struct hwloc_solaris_Lcore {
    unsigned Pcore, Ppkg;
  } * Lcore = malloc(Lcore_alloc * sizeof(*Lcore));

  unsigned Lpkg_num = 0;
  unsigned Lpkg_alloc = 256;
  struct hwloc_solaris_Lpkg {
    unsigned Ppkg;
  } * Lpkg = malloc(Lpkg_alloc * sizeof(*Lpkg));

  unsigned pkgid, coreid, cpuid;
  unsigned i;

  for (i = 0; i < Pproc_alloc; i++) {
    Pproc[i].Lproc = -1;
    Pproc[i].Lpkg = -1;
    Pproc[i].Ppkg = -1;
    Pproc[i].Lcore = -1;
  }

  if (!kc) {
    hwloc_debug("kstat_open failed: %s\n", strerror(errno));
    free(Pproc);
    free(Lproc);
    free(Lcore);
    free(Lpkg);
    return 0;
  }

  for (ksp = kc->kc_chain; ksp; ksp = ksp->ks_next)
    {
      if (strncmp("cpu_info", ksp->ks_module, 8))
	continue;

      cpuid = ksp->ks_instance;

      if (kstat_read(kc, ksp, NULL) == -1)
	{
	  fprintf(stderr, "kstat_read failed for CPU%u: %s\n", cpuid, strerror(errno));
	  continue;
	}

      hwloc_debug("cpu%u\n", cpuid);

      if (cpuid >= Pproc_alloc) {
	struct hwloc_solaris_Pproc *tmp = realloc(Pproc, 2*Pproc_alloc * sizeof(*Pproc));
	if (!tmp)
	  goto err;
	Pproc = tmp;
	Pproc_alloc *= 2;
	for(i = Pproc_alloc/2; i < Pproc_alloc; i++) {
	  Pproc[i].Lproc = -1;
	  Pproc[i].Lpkg = -1;
	  Pproc[i].Ppkg = -1;
	  Pproc[i].Lcore = -1;
	}
      }
      Pproc[cpuid].Lproc = Lproc_num;

      if (Lproc_num >= Lproc_alloc) {
	struct hwloc_solaris_Lproc *tmp = realloc(Lproc, 2*Lproc_alloc * sizeof(*Lproc));
	if (!tmp)
	  goto err;
	Lproc = tmp;
	Lproc_alloc *= 2;
      }
      Lproc[Lproc_num].Pproc = cpuid;
      Lproc_num++;

      if (cpuid >= Pproc_max)
        Pproc_max = cpuid + 1;

      stat = (kstat_named_t *) kstat_data_lookup(ksp, "state");
      if (!stat)
          hwloc_debug("could not read state for CPU%u: %s\n", cpuid, strerror(errno));
      else if (stat->data_type != KSTAT_DATA_CHAR)
          hwloc_debug("unknown kstat type %d for cpu state\n", stat->data_type);
      else
        {
          hwloc_debug("cpu%u's state is %s\n", cpuid, stat->value.c);
          if (strcmp(stat->value.c, "on-line"))
            /* not online */
            hwloc_bitmap_clr(topology->levels[0][0]->online_cpuset, cpuid);
        }

      if (look_chips) do {
	/* Get Chip ID */
	stat = (kstat_named_t *) kstat_data_lookup(ksp, "chip_id");
	if (!stat)
	  {
	    if (Lpkg_num)
	      fprintf(stderr, "could not read package id for CPU%u: %s\n", cpuid, strerror(errno));
	    else
	      hwloc_debug("could not read package id for CPU%u: %s\n", cpuid, strerror(errno));
	    look_chips = 0;
	    continue;
	  }
	switch (stat->data_type) {
	  case KSTAT_DATA_INT32:
	    pkgid = stat->value.i32;
	    break;
	  case KSTAT_DATA_UINT32:
	    pkgid = stat->value.ui32;
	    break;
#ifdef _INT64_TYPE
	  case KSTAT_DATA_UINT64:
	    pkgid = stat->value.ui64;
	    break;
	  case KSTAT_DATA_INT64:
	    pkgid = stat->value.i64;
	    break;
#endif
	  default:
	    fprintf(stderr, "chip_id type %d unknown\n", stat->data_type);
	    look_chips = 0;
	    continue;
	}
	Pproc[cpuid].Ppkg = pkgid;
	for (i = 0; i < Lpkg_num; i++)
	  if (pkgid == Lpkg[i].Ppkg)
	    break;
	Pproc[cpuid].Lpkg = i;
	hwloc_debug("%u on package %u (%u)\n", cpuid, i, pkgid);
	if (i == Lpkg_num) {
	  if (Lpkg_num == Lpkg_alloc) {
	    struct hwloc_solaris_Lpkg *tmp = realloc(Lpkg, 2*Lpkg_alloc * sizeof(*Lpkg));
	    if (!tmp)
	      goto err;
	    Lpkg = tmp;
	    Lpkg_alloc *= 2;
	  }
	  Lpkg[Lpkg_num++].Ppkg = pkgid;
	}
      } while(0);

      if (look_cores) do {
	/* Get Core ID */
	stat = (kstat_named_t *) kstat_data_lookup(ksp, "core_id");
	if (!stat)
	  {
	    if (Lcore_num)
	      fprintf(stderr, "could not read core id for CPU%u: %s\n", cpuid, strerror(errno));
	    else
	      hwloc_debug("could not read core id for CPU%u: %s\n", cpuid, strerror(errno));
	    look_cores = 0;
	    continue;
	  }
	switch (stat->data_type) {
	  case KSTAT_DATA_INT32:
	    coreid = stat->value.i32;
	    break;
	  case KSTAT_DATA_UINT32:
	    coreid = stat->value.ui32;
	    break;
#ifdef _INT64_TYPE
	  case KSTAT_DATA_UINT64:
	    coreid = stat->value.ui64;
	    break;
	  case KSTAT_DATA_INT64:
	    coreid = stat->value.i64;
	    break;
#endif
	  default:
	    fprintf(stderr, "core_id type %d unknown\n", stat->data_type);
	    look_cores = 0;
	    continue;
	}
	for (i = 0; i < Lcore_num; i++)
	  if (coreid == Lcore[i].Pcore && Pproc[cpuid].Ppkg == Lcore[i].Ppkg)
	    break;
	Pproc[cpuid].Lcore = i;
	hwloc_debug("%u on core %u (%u)\n", cpuid, i, coreid);
	if (i == Lcore_num) {
	  if (Lcore_num == Lcore_alloc) {
	    struct hwloc_solaris_Lcore *tmp = realloc(Lcore, 2*Lcore_alloc * sizeof(*Lcore));
	    if (!tmp)
	      goto err;
	    Lcore = tmp;
	    Lcore_alloc *= 2;
	  }
	  Lcore[Lcore_num].Ppkg = Pproc[cpuid].Ppkg;
	  Lcore[Lcore_num++].Pcore = coreid;
	}
      } while(0);

      /* Note: there is also clog_id for the Thread ID (not unique) and
       * pkg_core_id for the core ID (not unique).  They are not useful to us
       * however. */
    }

  if (look_chips) {
    struct hwloc_obj *obj;
    unsigned j,k;
    hwloc_debug("%d Packages\n", Lpkg_num);
    for (j = 0; j < Lpkg_num; j++) {
      obj = hwloc_alloc_setup_object(HWLOC_OBJ_PACKAGE, Lpkg[j].Ppkg);
      if (CPUType)
	hwloc_obj_add_info(obj, "CPUType", CPUType);
      if (CPUModel)
	hwloc_obj_add_info(obj, "CPUModel", CPUModel);
      obj->cpuset = hwloc_bitmap_alloc();
      for(k=0; k<Pproc_max; k++)
	if (Pproc[k].Lpkg == j)
	  hwloc_bitmap_set(obj->cpuset, k);
      hwloc_debug_1arg_bitmap("Package %d has cpuset %s\n", j, obj->cpuset);
      hwloc_insert_object_by_cpuset(topology, obj);
    }
    hwloc_debug("%s", "\n");
  }

  if (look_cores) {
    struct hwloc_obj *obj;
    unsigned j,k;
    hwloc_debug("%d Cores\n", Lcore_num);
    for (j = 0; j < Lcore_num; j++) {
      obj = hwloc_alloc_setup_object(HWLOC_OBJ_CORE, Lcore[j].Pcore);
      obj->cpuset = hwloc_bitmap_alloc();
      for(k=0; k<Pproc_max; k++)
	if (Pproc[k].Lcore == j)
	  hwloc_bitmap_set(obj->cpuset, k);
      hwloc_debug_1arg_bitmap("Core %d has cpuset %s\n", j, obj->cpuset);
      hwloc_insert_object_by_cpuset(topology, obj);
    }
    hwloc_debug("%s", "\n");
  }
  if (Lproc_num) {
    struct hwloc_obj *obj;
    unsigned j,k;
    hwloc_debug("%d PUs\n", Lproc_num);
    for (j = 0; j < Lproc_num; j++) {
      obj = hwloc_alloc_setup_object(HWLOC_OBJ_PU, Lproc[j].Pproc);
      obj->cpuset = hwloc_bitmap_alloc();
      for(k=0; k<Pproc_max; k++)
	if (Pproc[k].Lproc == j)
	  hwloc_bitmap_set(obj->cpuset, k);
      hwloc_debug_1arg_bitmap("PU %d has cpuset %s\n", j, obj->cpuset);
      hwloc_insert_object_by_cpuset(topology, obj);
    }
    hwloc_debug("%s", "\n");
  }

  kstat_close(kc);

  free(Pproc);
  free(Lproc);
  free(Lcore);
  free(Lpkg);
  return Lproc_num > 0;

 err:
  kstat_close(kc);

  free(Pproc);
  free(Lproc);
  free(Lcore);
  free(Lpkg);
  return 0;
}
예제 #18
0
파일: xcpuinfo.c 프로젝트: IFCA/slurm
				  /* Note: file static for qsort/_compare_cpus*/
extern int
get_cpuinfo(uint16_t *p_cpus, uint16_t *p_boards,
	    uint16_t *p_sockets, uint16_t *p_cores, uint16_t *p_threads,
	    uint16_t *p_block_map_size,
	    uint16_t **p_block_map, uint16_t **p_block_map_inv)
{
	int retval;

	uint16_t numproc;
	uint16_t numcpu	   = 0;		/* number of cpus seen */
	uint16_t numphys   = 0;		/* number of unique "physical id"s */
	uint16_t numcores  = 0;		/* number of unique "cores id"s */

	uint16_t maxsibs   = 0;		/* maximum value of "siblings" */
	uint16_t maxcores  = 0;		/* maximum value of "cores" */
	uint16_t minsibs   = 0xffff;	/* minimum value of "siblings" */
	uint16_t mincores  = 0xffff;	/* minimum value of "cores" */

	uint32_t maxcpuid  = 0;		/* maximum CPU ID ("processor") */
	uint32_t maxphysid = 0;		/* maximum "physical id" */
	uint32_t maxcoreid = 0;		/* maximum "core id" */
	uint32_t mincpuid  = 0xffffffff;/* minimum CPU ID ("processor") */
	uint32_t minphysid = 0xffffffff;/* minimum "physical id" */
	uint32_t mincoreid = 0xffffffff;/* minimum "core id" */
	int i;
#if defined (__sun)
#if defined (_LP64)
	int64_t curcpu, val, sockets, cores, threads;
#else
	int32_t curcpu, val, sockets, cores, threads;
#endif
	int32_t chip_id, core_id, ncore_per_chip, ncpu_per_chip;
#else
	FILE *cpu_info_file;
	char buffer[128];
	uint16_t curcpu, sockets, cores, threads;
#endif

	get_procs(&numproc);
	*p_cpus = numproc;
	*p_boards = 1;		/* Boards not identified from /proc/cpuinfo */
	*p_sockets = numproc;	/* initially all single core/thread */
	*p_cores   = 1;
	*p_threads = 1;
	*p_block_map_size = 0;
	*p_block_map      = NULL;
	*p_block_map_inv  = NULL;

#if defined (__sun)
	kstat_ctl_t   *kc;
	kstat_t       *ksp;
	kstat_named_t *knp;

	kc = kstat_open();
	if (kc == NULL) {
		error ("get speed: kstat error %d", errno);
		return errno;
	}
#else
	cpu_info_file = fopen(_cpuinfo_path, "r");
	if (cpu_info_file == NULL) {
		error ("get_cpuinfo: error %d opening %s",
			errno, _cpuinfo_path);
		return errno;
	}
#endif

	/* Note: assumes all processor IDs are within [0:numproc-1] */
	/*       treats physical/core IDs as tokens, not indices */
	if (cpuinfo)
		memset(cpuinfo, 0, numproc * sizeof(cpuinfo_t));
	else
		cpuinfo = xmalloc(numproc * sizeof(cpuinfo_t));

#if defined (__sun)
	ksp = kstat_lookup(kc, "cpu_info", -1, NULL);
	for (; ksp != NULL; ksp = ksp->ks_next) {
		if (strcmp(ksp->ks_module, "cpu_info"))
			continue;

		numcpu++;
		kstat_read(kc, ksp, NULL);

		knp = kstat_data_lookup(ksp, "chip_id");
		chip_id = knp->value.l;
		knp = kstat_data_lookup(ksp, "core_id");
		core_id = knp->value.l;
		knp = kstat_data_lookup(ksp, "ncore_per_chip");
		ncore_per_chip = knp->value.l;
		knp = kstat_data_lookup(ksp, "ncpu_per_chip");
		ncpu_per_chip = knp->value.l;

		if (chip_id >= numproc) {
			debug("cpuid is %ld (> %d), ignored", curcpu, numproc);
			continue;
		}

		cpuinfo[chip_id].seen = 1;
		cpuinfo[chip_id].cpuid = chip_id;

		maxcpuid = MAX(maxcpuid, chip_id);
		mincpuid = MIN(mincpuid, chip_id);

		for (i = 0; i < numproc; i++) {
			if ((cpuinfo[i].coreid == core_id) &&
			    (cpuinfo[i].corecnt))
				break;
		}

		if (i == numproc) {
			numcores++;
		} else {
			cpuinfo[i].corecnt++;
		}

		if (chip_id < numproc) {
			cpuinfo[chip_id].corecnt++;
			cpuinfo[chip_id].coreid = core_id;
		}

		maxcoreid = MAX(maxcoreid, core_id);
		mincoreid = MIN(mincoreid, core_id);

		if (ncore_per_chip > numproc) {
			debug("cores is %u (> %d), ignored",
			      ncore_per_chip, numproc);
				continue;
		}

		if (chip_id < numproc)
			cpuinfo[chip_id].cores = ncore_per_chip;

		maxcores = MAX(maxcores, ncore_per_chip);
		mincores = MIN(mincores, ncore_per_chip);
	}
#else

	curcpu = 0;
	while (fgets(buffer, sizeof(buffer), cpu_info_file) != NULL) {
		uint32_t val;
		if (_chk_cpuinfo_uint32(buffer, "processor", &val)) {
			numcpu++;
			curcpu = val;
		    	if (val >= numproc) {	/* out of bounds, ignore */
				debug("cpuid is %u (> %d), ignored",
					val, numproc);
				continue;
			}
			cpuinfo[val].seen = 1;
			cpuinfo[val].cpuid = val;
			maxcpuid = MAX(maxcpuid, val);
			mincpuid = MIN(mincpuid, val);
		} else if (_chk_cpuinfo_uint32(buffer, "physical id", &val)) {
			/* see if the ID has already been seen */
			for (i=0; i<numproc; i++) {
				if ((cpuinfo[i].physid == val)
				&&  (cpuinfo[i].physcnt))
					break;
			}

			if (i == numproc) {		/* new ID... */
				numphys++;		/* ...increment total */
			} else {			/* existing ID... */
				cpuinfo[i].physcnt++;	/* ...update ID cnt */
			}

			if (curcpu < numproc) {
				cpuinfo[curcpu].physcnt++;
				cpuinfo[curcpu].physid = val;
			}

			maxphysid = MAX(maxphysid, val);
			minphysid = MIN(minphysid, val);
		} else if (_chk_cpuinfo_uint32(buffer, "core id", &val)) {
			/* see if the ID has already been seen */
			for (i = 0; i < numproc; i++) {
				if ((cpuinfo[i].coreid == val)
				&&  (cpuinfo[i].corecnt))
					break;
			}

			if (i == numproc) {		/* new ID... */
				numcores++;		/* ...increment total */
			} else {			/* existing ID... */
				cpuinfo[i].corecnt++;	/* ...update ID cnt */
			}

			if (curcpu < numproc) {
				cpuinfo[curcpu].corecnt++;
				cpuinfo[curcpu].coreid = val;
			}

			maxcoreid = MAX(maxcoreid, val);
			mincoreid = MIN(mincoreid, val);
		} else if (_chk_cpuinfo_uint32(buffer, "siblings", &val)) {
			/* Note: this value is a count, not an index */
		    	if (val > numproc) {	/* out of bounds, ignore */
				debug("siblings is %u (> %d), ignored",
					val, numproc);
				continue;
			}
			if (curcpu < numproc)
				cpuinfo[curcpu].siblings = val;
			maxsibs = MAX(maxsibs, val);
			minsibs = MIN(minsibs, val);
		} else if (_chk_cpuinfo_uint32(buffer, "cpu cores", &val)) {
			/* Note: this value is a count, not an index */
		    	if (val > numproc) {	/* out of bounds, ignore */
				debug("cores is %u (> %d), ignored",
					val, numproc);
				continue;
			}
			if (curcpu < numproc)
				cpuinfo[curcpu].cores = val;
			maxcores = MAX(maxcores, val);
			mincores = MIN(mincores, val);
		}
	}

	fclose(cpu_info_file);
#endif

	/*** Sanity check ***/
	if (minsibs == 0) minsibs = 1;		/* guaranteee non-zero */
	if (maxsibs == 0) {
	    	minsibs = 1;
	    	maxsibs = 1;
	}
	if (maxcores == 0) {			/* no core data */
	    	mincores = 0;
	    	maxcores = 0;
	}

	/*** Compute Sockets/Cores/Threads ***/
	if ((minsibs == maxsibs) &&		/* homogeneous system */
	    (mincores == maxcores)) {
		sockets = numphys; 		/* unique "physical id" */
		if (sockets <= 1) {		/* verify single socket */
			sockets = numcpu / maxsibs; /* maximum "siblings" */
		}
		if (sockets == 0)
			sockets = 1;		/* guarantee non-zero */

		cores = numcores / sockets;	/* unique "core id" */
		cores = MAX(maxcores, cores);	/* maximum "cpu cores" */

		if (cores == 0) {
			cores = numcpu / sockets;	/* assume multi-core */
			if (cores > 1) {
				debug3("Warning: cpuinfo missing 'core id' or "
					"'cpu cores' but assuming multi-core");
			}
		}
		if (cores == 0)
			cores = 1;	/* guarantee non-zero */

		threads = numcpu / (sockets * cores); /* solve for threads */
		if (threads == 0)
			threads = 1;	/* guarantee non-zero */
	} else {				/* heterogeneous system */
		sockets = numcpu;
		cores   = 1;			/* one core per socket */
		threads = 1;			/* one core per core */
	}

	*p_sockets = sockets;		/* update output parameters */
	*p_cores   = cores;
	*p_threads = threads;

#if DEBUG_DETAIL
	/*** Display raw data ***/
	debug3("");
	debug3("numcpu:     %u", numcpu);
	debug3("numphys:    %u", numphys);
	debug3("numcores:   %u", numcores);

	debug3("cores:      %u->%u", mincores, maxcores);
	debug3("sibs:       %u->%u", minsibs,  maxsibs);

	debug3("cpuid:      %u->%u", mincpuid,  maxcpuid);
	debug3("physid:     %u->%u", minphysid, maxphysid);
	debug3("coreid:     %u->%u", mincoreid, maxcoreid);

	for (i = 0; i <= maxcpuid; i++) {
		debug3("CPU %d:", i);
		debug3(" seen:     %u", cpuinfo[i].seen);
		debug3(" physid:   %u", cpuinfo[i].physid);
		debug3(" physcnt:  %u", cpuinfo[i].physcnt);
		debug3(" siblings: %u", cpuinfo[i].siblings);
		debug3(" cores:    %u", cpuinfo[i].cores);
		debug3(" coreid:   %u", cpuinfo[i].coreid);
		debug3(" corecnt:  %u", cpuinfo[i].corecnt);
		debug3("");
	}

	debug3("");
	debug3("Sockets:          %u", sockets);
	debug3("Cores per socket: %u", cores);
	debug3("Threads per core: %u", threads);
#endif

	*p_block_map_size = numcpu;
	retval = _compute_block_map(*p_block_map_size, p_block_map,
				    p_block_map_inv);

	xfree(cpuinfo);		/* done with raw cpuinfo data */

	return retval;
}
예제 #19
0
/*
 * Return stats about a particular network
 * interface.  References:
 * https://github.com/dpaleino/wicd/blob/master/wicd/backends/be-ioctl.py
 * http://www.i-scream.org/libstatgrab/
 */
static PyObject*
psutil_net_if_stats(PyObject* self, PyObject* args) {
    kstat_ctl_t *kc = NULL;
    kstat_t *ksp;
    kstat_named_t *knp;
    int ret;
    int sock = -1;
    int duplex;
    int speed;

    PyObject *py_retdict = PyDict_New();
    PyObject *py_ifc_info = NULL;
    PyObject *py_is_up = NULL;

    if (py_retdict == NULL)
        return NULL;
    kc = kstat_open();
    if (kc == NULL)
        goto error;
    sock = socket(AF_INET, SOCK_DGRAM, 0);
    if (sock == -1) {
        PyErr_SetFromErrno(PyExc_OSError);
        goto error;
    }

    for (ksp = kc->kc_chain; ksp; ksp = ksp->ks_next) {
        if (strcmp(ksp->ks_class, "net") == 0) {
            struct lifreq ifr;

            kstat_read(kc, ksp, NULL);
            if (ksp->ks_type != KSTAT_TYPE_NAMED)
                continue;
            if (strcmp(ksp->ks_class, "net") != 0)
                continue;

            strncpy(ifr.lifr_name, ksp->ks_name, sizeof(ifr.lifr_name));
            ret = ioctl(sock, SIOCGLIFFLAGS, &ifr);
            if (ret == -1)
                continue;  // not a network interface

            // is up?
            if ((ifr.lifr_flags & IFF_UP) != 0) {
                if ((knp = kstat_data_lookup(ksp, "link_up")) != NULL) {
                    if (knp->value.ui32 != 0u)
                        py_is_up = Py_True;
                    else
                        py_is_up = Py_False;
                }
                else {
                    py_is_up = Py_True;
                }
            }
            else {
                py_is_up = Py_False;
            }
            Py_INCREF(py_is_up);

            // duplex
            duplex = 0;  // unknown
            if ((knp = kstat_data_lookup(ksp, "link_duplex")) != NULL) {
                if (knp->value.ui32 == 1)
                    duplex = 1;  // half
                else if (knp->value.ui32 == 2)
                    duplex = 2;  // full
            }

            // speed
            if ((knp = kstat_data_lookup(ksp, "ifspeed")) != NULL)
                // expressed in bits per sec, we want mega bits per sec
                speed = (int)knp->value.ui64 / 1000000;
            else
                speed = 0;

            // mtu
            ret = ioctl(sock, SIOCGLIFMTU, &ifr);
            if (ret == -1)
                goto error;

            py_ifc_info = Py_BuildValue("(Oiii)", py_is_up, duplex, speed,
                                        ifr.lifr_mtu);
            if (!py_ifc_info)
                goto error;
            if (PyDict_SetItemString(py_retdict, ksp->ks_name, py_ifc_info))
                goto error;
            Py_DECREF(py_ifc_info);
        }
    }

    close(sock);
    kstat_close(kc);
    return py_retdict;

error:
    Py_XDECREF(py_is_up);
    Py_XDECREF(py_ifc_info);
    Py_DECREF(py_retdict);
    if (sock != -1)
        close(sock);
    if (kc != NULL)
        kstat_close(kc);
    PyErr_SetFromErrno(PyExc_OSError);
    return NULL;
}
예제 #20
0
/*
* Iterate over all kernel statistics and save matches.
*/
static void
ks_instances_read(kstat_ctl_t *kc)
{
kstat_raw_reader_t save_raw = NULL;
kid_t		id;
ks_selector_t	*selector;
ks_instance_t	*ksi;
ks_instance_t	*tmp;
kstat_t		*kp;
boolean_t	skip;

for (kp = kc->kc_chain; kp != NULL; kp = kp->ks_next) {
	/* Don't bother storing the kstat headers */
	if (strncmp(kp->ks_name, "kstat_", 6) == 0) {
		continue;
	}

	/* Don't bother storing raw stats we don't understand */
	if (kp->ks_type == KSTAT_TYPE_RAW) {
		save_raw = lookup_raw_kstat_fn(kp->ks_module,
				kp->ks_name);
		if (save_raw == NULL) {
#ifdef REPORT_UNKNOWN
			(void) fprintf(stderr,
					"Unknown kstat type %s:%d:%s - "
					"%d of size %d\n", kp->ks_module,
					kp->ks_instance, kp->ks_name,
					kp->ks_ndata, kp->ks_data_size);
#endif
			continue;
		}
	}

	/*
	 * Iterate over the list of selectors and skip
	 * instances we dont want. We filter for statistics
	 * later, as we dont know them yet.
	 */
	skip = B_TRUE;
	selector = list_head(&selector_list);
	while (selector != NULL) {
		if (ks_match(kp->ks_module, &selector->ks_module) &&
				ks_match(kp->ks_name, &selector->ks_name)) {
			skip = B_FALSE;
			break;
		}
		selector = list_next(&selector_list, selector);
	}

	if (skip) {
		continue;
	}

	/*
	 * Allocate a new instance and fill in the values
	 * we know so far.
	 */
	ksi = (ks_instance_t *)malloc(sizeof (ks_instance_t));
	if (ksi == NULL) {
		perror("malloc");
		exit(3);
	}

	list_link_init(&ksi->ks_next);

	(void) strlcpy(ksi->ks_zone, "global", KSTAT_STRLEN);
	(void) strlcpy(ksi->ks_module, kp->ks_module, KSTAT_STRLEN);
	(void) strlcpy(ksi->ks_name, kp->ks_name, KSTAT_STRLEN);
	(void) strlcpy(ksi->ks_class, kp->ks_class, KSTAT_STRLEN);

	ksi->ks_instance = kp->ks_instance;
	ksi->ks_snaptime = kp->ks_snaptime;
	ksi->ks_type = kp->ks_type;

	list_create(&ksi->ks_nvlist, sizeof (ks_nvpair_t),
			offsetof(ks_nvpair_t, nv_next));

	SAVE_HRTIME_X(ksi, "crtime", kp->ks_crtime);
	SAVE_HRTIME_X(ksi, "snaptime", kp->ks_snaptime);
	if (g_pflg) {
		SAVE_STRING_X(ksi, "class", kp->ks_class);
	}

	/* Insert this instance into a sorted list */
	tmp = list_head(&instances_list);
	while (tmp != NULL && compare_instances(ksi, tmp) > 0)
		tmp = list_next(&instances_list, tmp);

	list_insert_before(&instances_list, tmp, ksi);

	/* Read the actual statistics */
	id = kstat_read(kc, kp, NULL);
	if (id == -1) {
#ifdef REPORT_UNKNOWN
		perror("kstat_read");
#endif
		continue;
	}

	switch (kp->ks_type) {
	case KSTAT_TYPE_RAW:
		save_raw(kp, ksi);
		break;
	case KSTAT_TYPE_NAMED:
		save_named(kp, ksi);
		break;
	case KSTAT_TYPE_INTR:
		save_intr(kp, ksi);
		break;
	case KSTAT_TYPE_IO:
		save_io(kp, ksi);
		break;
	case KSTAT_TYPE_TIMER:
		save_timer(kp, ksi);
		break;
	default:
		assert(B_FALSE); /* Invalid type */
		break;
	}
}
}
예제 #21
0
/*
 * Return a list of tuples for network I/O statistics.
 */
static PyObject *
psutil_net_io_counters(PyObject *self, PyObject *args) {
    kstat_ctl_t    *kc = NULL;
    kstat_t *ksp;
    kstat_named_t *rbytes, *wbytes, *rpkts, *wpkts, *ierrs, *oerrs;
    int ret;
    int sock = -1;
    struct lifreq ifr;

    PyObject *py_retdict = PyDict_New();
    PyObject *py_ifc_info = NULL;

    if (py_retdict == NULL)
        return NULL;
    kc = kstat_open();
    if (kc == NULL)
        goto error;

    sock = socket(AF_INET, SOCK_DGRAM, 0);
    if (sock == -1) {
        PyErr_SetFromErrno(PyExc_OSError);
        goto error;
    }

    ksp = kc->kc_chain;
    while (ksp != NULL) {
        if (ksp->ks_type != KSTAT_TYPE_NAMED)
            goto next;
        if (strcmp(ksp->ks_class, "net") != 0)
            goto next;
        // skip 'lo' (localhost) because it doesn't have the statistics we need
        // and it makes kstat_data_lookup() fail
        if (strcmp(ksp->ks_module, "lo") == 0)
            goto next;

        // check if this is a network interface by sending a ioctl
        strncpy(ifr.lifr_name, ksp->ks_name, sizeof(ifr.lifr_name));
        ret = ioctl(sock, SIOCGLIFFLAGS, &ifr);
        if (ret == -1)
            goto next;

        if (kstat_read(kc, ksp, NULL) == -1) {
            errno = 0;
            goto next;
        }

        rbytes = (kstat_named_t *)kstat_data_lookup(ksp, "rbytes");
        wbytes = (kstat_named_t *)kstat_data_lookup(ksp, "obytes");
        rpkts = (kstat_named_t *)kstat_data_lookup(ksp, "ipackets");
        wpkts = (kstat_named_t *)kstat_data_lookup(ksp, "opackets");
        ierrs = (kstat_named_t *)kstat_data_lookup(ksp, "ierrors");
        oerrs = (kstat_named_t *)kstat_data_lookup(ksp, "oerrors");

        if ((rbytes == NULL) || (wbytes == NULL) || (rpkts == NULL) ||
                (wpkts == NULL) || (ierrs == NULL) || (oerrs == NULL))
        {
            PyErr_SetString(PyExc_RuntimeError, "kstat_data_lookup() failed");
            goto error;
        }

        if (rbytes->data_type == KSTAT_DATA_UINT64)
        {
            py_ifc_info = Py_BuildValue("(KKKKIIii)",
                                        wbytes->value.ui64,
                                        rbytes->value.ui64,
                                        wpkts->value.ui64,
                                        rpkts->value.ui64,
                                        ierrs->value.ui32,
                                        oerrs->value.ui32,
                                        0,  // dropin not supported
                                        0   // dropout not supported
                                       );
        }
        else
        {
            py_ifc_info = Py_BuildValue("(IIIIIIii)",
                                        wbytes->value.ui32,
                                        rbytes->value.ui32,
                                        wpkts->value.ui32,
                                        rpkts->value.ui32,
                                        ierrs->value.ui32,
                                        oerrs->value.ui32,
                                        0,  // dropin not supported
                                        0   // dropout not supported
                                       );
        }
        if (!py_ifc_info)
            goto error;
        if (PyDict_SetItemString(py_retdict, ksp->ks_name, py_ifc_info))
            goto error;
        Py_DECREF(py_ifc_info);
        goto next;

next:
        ksp = ksp->ks_next;
    }

    kstat_close(kc);
    close(sock);
    return py_retdict;

error:
    Py_XDECREF(py_ifc_info);
    Py_DECREF(py_retdict);
    if (kc != NULL)
        kstat_close(kc);
    if (sock != -1) {
        close(sock);
    }
    return NULL;
}
예제 #22
0
int
getloadavg (double loadavg[], int nelem)
{
  int elem = 0;                 /* Return value.  */

# ifdef NO_GET_LOAD_AVG
#  define LDAV_DONE
  errno = ENOSYS;
  elem = -1;
# endif

# if !defined (LDAV_DONE) && defined (HAVE_LIBKSTAT)       /* Solaris <= 2.6 */
/* Use libkstat because we don't have to be root.  */
#  define LDAV_DONE
  kstat_ctl_t *kc;
  kstat_t *ksp;
  kstat_named_t *kn;
  int saved_errno;

  kc = kstat_open ();
  if (kc == 0)
    return -1;
  ksp = kstat_lookup (kc, "unix", 0, "system_misc");
  if (ksp == 0)
    return -1;
  if (kstat_read (kc, ksp, 0) == -1)
    return -1;


  kn = kstat_data_lookup (ksp, "avenrun_1min");
  if (kn == 0)
    {
      /* Return -1 if no load average information is available.  */
      nelem = 0;
      elem = -1;
    }

  if (nelem >= 1)
    loadavg[elem++] = (double) kn->value.ul / FSCALE;

  if (nelem >= 2)
    {
      kn = kstat_data_lookup (ksp, "avenrun_5min");
      if (kn != 0)
        {
          loadavg[elem++] = (double) kn->value.ul / FSCALE;

          if (nelem >= 3)
            {
              kn = kstat_data_lookup (ksp, "avenrun_15min");
              if (kn != 0)
                loadavg[elem++] = (double) kn->value.ul / FSCALE;
            }
        }
    }

  saved_errno = errno;
  kstat_close (kc);
  errno = saved_errno;
# endif /* HAVE_LIBKSTAT */

# if !defined (LDAV_DONE) && defined (hpux) && defined (HAVE_PSTAT_GETDYNAMIC)
                                                           /* HP-UX */
/* Use pstat_getdynamic() because we don't have to be root.  */
#  define LDAV_DONE
#  undef LOAD_AVE_TYPE

  struct pst_dynamic dyn_info;
  if (pstat_getdynamic (&dyn_info, sizeof (dyn_info), 0, 0) < 0)
    return -1;
  if (nelem > 0)
    loadavg[elem++] = dyn_info.psd_avg_1_min;
  if (nelem > 1)
    loadavg[elem++] = dyn_info.psd_avg_5_min;
  if (nelem > 2)
    loadavg[elem++] = dyn_info.psd_avg_15_min;

# endif /* hpux && HAVE_PSTAT_GETDYNAMIC */

# if ! defined LDAV_DONE && defined HAVE_LIBPERFSTAT       /* AIX */
#  define LDAV_DONE
#  undef LOAD_AVE_TYPE
/* Use perfstat_cpu_total because we don't have to be root. */
  {
    perfstat_cpu_total_t cpu_stats;
    int result = perfstat_cpu_total (NULL, &cpu_stats, sizeof cpu_stats, 1);
    if (result == -1)
      return result;
    loadavg[0] = cpu_stats.loadavg[0] / (double)(1 << SBITS);
    loadavg[1] = cpu_stats.loadavg[1] / (double)(1 << SBITS);
    loadavg[2] = cpu_stats.loadavg[2] / (double)(1 << SBITS);
    elem = 3;
  }
# endif

# if !defined (LDAV_DONE) && (defined (__linux__) || defined (__CYGWIN__))
                                              /* Linux without glibc, Cygwin */
#  define LDAV_DONE
#  undef LOAD_AVE_TYPE

#  ifndef LINUX_LDAV_FILE
#   define LINUX_LDAV_FILE "/proc/loadavg"
#  endif

  char ldavgbuf[3 * (INT_STRLEN_BOUND (int) + sizeof ".00 ")];
  char const *ptr = ldavgbuf;
  int fd, count, saved_errno;

  fd = open (LINUX_LDAV_FILE, O_RDONLY);
  if (fd == -1)
    return -1;
  count = read (fd, ldavgbuf, sizeof ldavgbuf - 1);
  saved_errno = errno;
  (void) close (fd);
  errno = saved_errno;
  if (count <= 0)
    return -1;
  ldavgbuf[count] = '\0';

  for (elem = 0; elem < nelem; elem++)
    {
      double numerator = 0;
      double denominator = 1;

      while (*ptr == ' ')
        ptr++;

      /* Finish if this number is missing, and report an error if all
         were missing.  */
      if (! ('0' <= *ptr && *ptr <= '9'))
        {
          if (elem == 0)
            {
              errno = ENOTSUP;
              return -1;
            }
          break;
        }

      while ('0' <= *ptr && *ptr <= '9')
        numerator = 10 * numerator + (*ptr++ - '0');

      if (*ptr == '.')
        for (ptr++; '0' <= *ptr && *ptr <= '9'; ptr++)
          numerator = 10 * numerator + (*ptr - '0'), denominator *= 10;

      loadavg[elem++] = numerator / denominator;
    }

  return elem;

# endif /* __linux__ || __CYGWIN__ */

# if !defined (LDAV_DONE) && defined (__NetBSD__)          /* NetBSD < 0.9 */
#  define LDAV_DONE
#  undef LOAD_AVE_TYPE

#  ifndef NETBSD_LDAV_FILE
#   define NETBSD_LDAV_FILE "/kern/loadavg"
#  endif

  unsigned long int load_ave[3], scale;
  int count;
  FILE *fp;

  fp = fopen (NETBSD_LDAV_FILE, "r");
  if (fp == NULL)
    return -1;
  count = fscanf (fp, "%lu %lu %lu %lu\n",
                  &load_ave[0], &load_ave[1], &load_ave[2],
                  &scale);
  (void) fclose (fp);
  if (count != 4)
    {
      errno = ENOTSUP;
      return -1;
    }

  for (elem = 0; elem < nelem; elem++)
    loadavg[elem] = (double) load_ave[elem] / (double) scale;

  return elem;

# endif /* __NetBSD__ */

# if !defined (LDAV_DONE) && defined (NeXT)                /* NeXTStep */
#  define LDAV_DONE
  /* The NeXT code was adapted from iscreen 3.2.  */

  host_t host;
  struct processor_set_basic_info info;
  unsigned int info_count;

  /* We only know how to get the 1-minute average for this system,
     so even if the caller asks for more than 1, we only return 1.  */

  if (!getloadavg_initialized)
    {
      if (processor_set_default (host_self (), &default_set) == KERN_SUCCESS)
        getloadavg_initialized = true;
    }

  if (getloadavg_initialized)
    {
      info_count = PROCESSOR_SET_BASIC_INFO_COUNT;
      if (processor_set_info (default_set, PROCESSOR_SET_BASIC_INFO, &host,
                              (processor_set_info_t) &info, &info_count)
          != KERN_SUCCESS)
        getloadavg_initialized = false;
      else
        {
          if (nelem > 0)
            loadavg[elem++] = (double) info.load_average / LOAD_SCALE;
        }
    }

  if (!getloadavg_initialized)
    {
      errno = ENOTSUP;
      return -1;
    }
# endif /* NeXT */

# if !defined (LDAV_DONE) && defined (UMAX)
#  define LDAV_DONE
/* UMAX 4.2, which runs on the Encore Multimax multiprocessor, does not
   have a /dev/kmem.  Information about the workings of the running kernel
   can be gathered with inq_stats system calls.
   We only know how to get the 1-minute average for this system.  */

  struct proc_summary proc_sum_data;
  struct stat_descr proc_info;
  double load;
  register unsigned int i, j;

  if (cpus == 0)
    {
      register unsigned int c, i;
      struct cpu_config conf;
      struct stat_descr desc;

      desc.sd_next = 0;
      desc.sd_subsys = SUBSYS_CPU;
      desc.sd_type = CPUTYPE_CONFIG;
      desc.sd_addr = (char *) &conf;
      desc.sd_size = sizeof conf;

      if (inq_stats (1, &desc))
        return -1;

      c = 0;
      for (i = 0; i < conf.config_maxclass; ++i)
        {
          struct class_stats stats;
          memset (&stats, 0, sizeof stats);

          desc.sd_type = CPUTYPE_CLASS;
          desc.sd_objid = i;
          desc.sd_addr = (char *) &stats;
          desc.sd_size = sizeof stats;

          if (inq_stats (1, &desc))
            return -1;

          c += stats.class_numcpus;
        }
      cpus = c;
      samples = cpus < 2 ? 3 : (2 * cpus / 3);
    }

  proc_info.sd_next = 0;
  proc_info.sd_subsys = SUBSYS_PROC;
  proc_info.sd_type = PROCTYPE_SUMMARY;
  proc_info.sd_addr = (char *) &proc_sum_data;
  proc_info.sd_size = sizeof (struct proc_summary);
  proc_info.sd_sizeused = 0;

  if (inq_stats (1, &proc_info) != 0)
    return -1;

  load = proc_sum_data.ps_nrunnable;
  j = 0;
  for (i = samples - 1; i > 0; --i)
    {
      load += proc_sum_data.ps_nrun[j];
      if (j++ == PS_NRUNSIZE)
        j = 0;
    }

  if (nelem > 0)
    loadavg[elem++] = load / samples / cpus;
# endif /* UMAX */

# if !defined (LDAV_DONE) && defined (DGUX)
#  define LDAV_DONE
  /* This call can return -1 for an error, but with good args
     it's not supposed to fail.  The first argument is for no
     apparent reason of type 'long int *'.  */
  dg_sys_info ((long int *) &load_info,
               DG_SYS_INFO_LOAD_INFO_TYPE,
               DG_SYS_INFO_LOAD_VERSION_0);

  if (nelem > 0)
    loadavg[elem++] = load_info.one_minute;
  if (nelem > 1)
    loadavg[elem++] = load_info.five_minute;
  if (nelem > 2)
    loadavg[elem++] = load_info.fifteen_minute;
# endif /* DGUX */

# if !defined (LDAV_DONE) && defined (apollo)
#  define LDAV_DONE
/* Apollo code from [email protected] (Ray Lischner).

   This system call is not documented.  The load average is obtained as
   three long integers, for the load average over the past minute,
   five minutes, and fifteen minutes.  Each value is a scaled integer,
   with 16 bits of integer part and 16 bits of fraction part.

   I'm not sure which operating system first supported this system call,
   but I know that SR10.2 supports it.  */

  extern void proc1_$get_loadav ();
  unsigned long load_ave[3];

  proc1_$get_loadav (load_ave);

  if (nelem > 0)
    loadavg[elem++] = load_ave[0] / 65536.0;
  if (nelem > 1)
    loadavg[elem++] = load_ave[1] / 65536.0;
  if (nelem > 2)
    loadavg[elem++] = load_ave[2] / 65536.0;
# endif /* apollo */

# if !defined (LDAV_DONE) && defined (OSF_MIPS)
#  define LDAV_DONE

  struct tbl_loadavg load_ave;
  table (TBL_LOADAVG, 0, &load_ave, 1, sizeof (load_ave));
  loadavg[elem++]
    = (load_ave.tl_lscale == 0
       ? load_ave.tl_avenrun.d[0]
       : (load_ave.tl_avenrun.l[0] / (double) load_ave.tl_lscale));
# endif /* OSF_MIPS */

# if !defined (LDAV_DONE) && (defined (__MSDOS__) || defined (WINDOWS32))
                                                           /* DJGPP */
#  define LDAV_DONE

  /* A faithful emulation is going to have to be saved for a rainy day.  */
  for ( ; elem < nelem; elem++)
    {
      loadavg[elem] = 0.0;
    }
# endif  /* __MSDOS__ || WINDOWS32 */

# if !defined (LDAV_DONE) && defined (OSF_ALPHA)           /* OSF/1 */
#  define LDAV_DONE

  struct tbl_loadavg load_ave;
  table (TBL_LOADAVG, 0, &load_ave, 1, sizeof (load_ave));
  for (elem = 0; elem < nelem; elem++)
    loadavg[elem]
      = (load_ave.tl_lscale == 0
         ? load_ave.tl_avenrun.d[elem]
         : (load_ave.tl_avenrun.l[elem] / (double) load_ave.tl_lscale));
# endif /* OSF_ALPHA */

# if ! defined LDAV_DONE && defined __VMS                  /* VMS */
  /* VMS specific code -- read from the Load Ave driver.  */

  LOAD_AVE_TYPE load_ave[3];
  static bool getloadavg_initialized;
#  ifdef eunice
  struct
  {
    int dsc$w_length;
    char *dsc$a_pointer;
  } descriptor;
#  endif

  /* Ensure that there is a channel open to the load ave device.  */
  if (!getloadavg_initialized)
    {
      /* Attempt to open the channel.  */
#  ifdef eunice
      descriptor.dsc$w_length = 18;
      descriptor.dsc$a_pointer = "$$VMS_LOAD_AVERAGE";
#  else
      $DESCRIPTOR (descriptor, "LAV0:");
#  endif
      if (sys$assign (&descriptor, &channel, 0, 0) & 1)
        getloadavg_initialized = true;
    }

  /* Read the load average vector.  */
  if (getloadavg_initialized
      && !(sys$qiow (0, channel, IO$_READVBLK, 0, 0, 0,
                     load_ave, 12, 0, 0, 0, 0) & 1))
    {
      sys$dassgn (channel);
      getloadavg_initialized = false;
    }

  if (!getloadavg_initialized)
    {
      errno = ENOTSUP;
      return -1;
    }
# endif /* ! defined LDAV_DONE && defined __VMS */

# if ! defined LDAV_DONE && defined LOAD_AVE_TYPE && ! defined __VMS
                                                  /* IRIX, other old systems */

  /* UNIX-specific code -- read the average from /dev/kmem.  */

#  define LDAV_PRIVILEGED               /* This code requires special installation.  */

  LOAD_AVE_TYPE load_ave[3];

  /* Get the address of LDAV_SYMBOL.  */
  if (offset == 0)
    {
#  ifndef sgi
#   if ! defined NLIST_STRUCT || ! defined N_NAME_POINTER
      strcpy (name_list[0].n_name, LDAV_SYMBOL);
      strcpy (name_list[1].n_name, "");
#   else /* NLIST_STRUCT */
#    ifdef HAVE_STRUCT_NLIST_N_UN_N_NAME
      name_list[0].n_un.n_name = LDAV_SYMBOL;
      name_list[1].n_un.n_name = 0;
#    else /* not HAVE_STRUCT_NLIST_N_UN_N_NAME */
      name_list[0].n_name = LDAV_SYMBOL;
      name_list[1].n_name = 0;
#    endif /* not HAVE_STRUCT_NLIST_N_UN_N_NAME */
#   endif /* NLIST_STRUCT */

#   ifndef SUNOS_5
      if (
#    if !(defined (_AIX) && !defined (ps2))
          nlist (KERNEL_FILE, name_list)
#    else  /* _AIX */
          knlist (name_list, 1, sizeof (name_list[0]))
#    endif
          >= 0)
          /* Omit "&& name_list[0].n_type != 0 " -- it breaks on Sun386i.  */
          {
#    ifdef FIXUP_KERNEL_SYMBOL_ADDR
            FIXUP_KERNEL_SYMBOL_ADDR (name_list);
#    endif
            offset = name_list[0].n_value;
          }
#   endif /* !SUNOS_5 */
#  else  /* sgi */
      ptrdiff_t ldav_off = sysmp (MP_KERNADDR, MPKA_AVENRUN);
      if (ldav_off != -1)
        offset = (long int) ldav_off & 0x7fffffff;
#  endif /* sgi */
    }

  /* Make sure we have /dev/kmem open.  */
  if (!getloadavg_initialized)
    {
#  ifndef SUNOS_5
      /* Set the channel to close on exec, so it does not
         litter any child's descriptor table.  */
#   ifndef O_CLOEXEC
#    define O_CLOEXEC 0
#   endif
      int fd = open ("/dev/kmem", O_RDONLY | O_CLOEXEC);
      if (0 <= fd)
        {
#   if F_DUPFD_CLOEXEC
          if (fd <= STDERR_FILENO)
            {
              int fd1 = fcntl (fd, F_DUPFD_CLOEXEC, STDERR_FILENO + 1);
              close (fd);
              fd = fd1;
            }
#   endif
          if (0 <= fd)
            {
              channel = fd;
              getloadavg_initialized = true;
            }
        }
#  else /* SUNOS_5 */
      /* We pass 0 for the kernel, corefile, and swapfile names
         to use the currently running kernel.  */
      kd = kvm_open (0, 0, 0, O_RDONLY, 0);
      if (kd != 0)
        {
          /* nlist the currently running kernel.  */
          kvm_nlist (kd, name_list);
          offset = name_list[0].n_value;
          getloadavg_initialized = true;
        }
#  endif /* SUNOS_5 */
    }

  /* If we can, get the load average values.  */
  if (offset && getloadavg_initialized)
    {
      /* Try to read the load.  */
#  ifndef SUNOS_5
      if (lseek (channel, offset, 0) == -1L
          || read (channel, (char *) load_ave, sizeof (load_ave))
          != sizeof (load_ave))
        {
          close (channel);
          getloadavg_initialized = false;
        }
#  else  /* SUNOS_5 */
      if (kvm_read (kd, offset, (char *) load_ave, sizeof (load_ave))
          != sizeof (load_ave))
        {
          kvm_close (kd);
          getloadavg_initialized = false;
        }
#  endif /* SUNOS_5 */
    }

  if (offset == 0 || !getloadavg_initialized)
    {
      errno = ENOTSUP;
      return -1;
    }
# endif /* ! defined LDAV_DONE && defined LOAD_AVE_TYPE && ! defined __VMS */

# if !defined (LDAV_DONE) && defined (LOAD_AVE_TYPE) /* Including VMS.  */
  if (nelem > 0)
    loadavg[elem++] = LDAV_CVT (load_ave[0]);
  if (nelem > 1)
    loadavg[elem++] = LDAV_CVT (load_ave[1]);
  if (nelem > 2)
    loadavg[elem++] = LDAV_CVT (load_ave[2]);

#  define LDAV_DONE
# endif /* !LDAV_DONE && LOAD_AVE_TYPE */

# if !defined LDAV_DONE
  errno = ENOSYS;
  elem = -1;
# endif
  return elem;
}
예제 #23
0
static void get_interrupt_counters(int cpu_num, cpu_time_counters_t * counters)
{
	kstat_t *ksp;
	int found = 0;
	kid_t nkcid;
	kstat_named_t *knp;
	int i;

	ksp = kstat_lookup(kc, "cpu", lib_cpu_map[cpu_num], "intrstat");

	counters[cpu_num].interrupt = 0;
	if ((ksp) && (ksp->ks_type == KSTAT_TYPE_NAMED)) {
		/* happiness and joy, keep going */
		nkcid = kstat_read(kc, ksp, NULL);
		if (nkcid != -1) {
			/* happiness and joy, keep going. we could consider adding a
			   "found < 15" to the end conditions, but then we wouldn't
			   search to the end and find that Sun added some "time." we
			   probably want to see if they add a "nsec." raj 2005-01-28 */
			for (i = ksp->ks_ndata, knp = ksp->ks_data; i > 0; knp++, i--) {
				if (strstr(knp->name, "time")) {
					found++;
					counters[cpu_num].interrupt += knp->value.ui64;
				} else if (debug >= 2) {

					/* might want to tell people about what we are skipping.
					   however, only display other names debug >=2. raj
					   2005-01-28
					 */

					print_unexpected_statistic_warning("get_cpu_counters",
													   knp->name, NULL);
				}
			}
			if (15 == found) {
				/* happiness and joy */
				return;
			} else {
				fprintf(where,
						"get_cpu_counters could not find one or more of the expected counters!\n");
				fflush(where);
				exit(-1);
			}
		} else {
			/* the kstat_read returned an error or the chain changed */
			fprintf(where,
					"get_cpu_counters: kstat_read failed or chain id changed %d %s\n",
					errno, strerror(errno));
			fflush(where);
			exit(-1);
		}
	} else {
		/* the lookup failed or found the wrong type */
		fprintf(where,
				"get_cpu_counters: kstat_lookup failed for module 'cpu' %d instance %d class 'intrstat' and KSTAT_TYPE_NAMED: errno %d %s\n",
				cpu_num, lib_cpu_map[cpu_num], errno, strerror(errno));
		fflush(where);
		exit(-1);
	}

}
예제 #24
0
void KMemoryWidget::update() {

	kstat_ctl_t	*kctl;
	kstat_t		*ksp;
	kstat_named_t	*kdata;

	/*
	 *  get a kstat handle first and update the user's kstat chain
	 */
	if( (kctl = kstat_open()) == NULL )
		return;
	while( kstat_chain_update( kctl ) != 0 )
		;

	/*
	 *  traverse the kstat chain to find the appropriate kstat
	 */
	if( (ksp = kstat_lookup( kctl, "unix", 0, "system_pages" )) == NULL )
		return;

	if( kstat_read( kctl, ksp, NULL ) == -1 )
		return;

	/*
	 *  lookup the data
	 */
#if 0
	kdata = (kstat_named_t *) kstat_data_lookup( ksp, "physmem" );
	if( kdata != NULL ) {
		Memory_Info[TOTAL_MEM] = PAGETOK(kdata->value.ui32);
	}
#endif
	Memory_Info[TOTAL_MEM] = PAGETOK(sysconf(_SC_PHYS_PAGES));

	kdata = (kstat_named_t *) kstat_data_lookup( ksp, "freemem" );
	if( kdata != NULL )
		Memory_Info[FREE_MEM] = PAGETOK(kdata->value.ui32);
#ifdef __GNUC__
#warning "FIXME: Memory_Info[CACHED_MEM]"
#endif	
	Memory_Info[CACHED_MEM] = NO_MEMORY_INFO; // cached memory in ram
	  
	kstat_close( kctl );

	/*
	 *  Swap Info
	 */

	struct anoninfo		am_swap;
	long			swaptotal;
	long			swapfree;
	long			swapused;

	swaptotal = swapused = swapfree = 0L;

	/*
	 *  Retrieve overall swap information from anonymous memory structure -
	 *  which is the same way "swap -s" retrieves it's statistics.
	 *
	 *  swapctl(SC_LIST, void *arg) does not return what we are looking for.
	 */

	if (swapctl(SC_AINFO, &am_swap) == -1)
		return;

	swaptotal = am_swap.ani_max;
	swapused = am_swap.ani_resv;
	swapfree = swaptotal - swapused;

	Memory_Info[SWAP_MEM]     = PAGETOK(swaptotal);
	Memory_Info[FREESWAP_MEM] = PAGETOK(swapfree);
}
예제 #25
0
int kupdate(int avenrun[3])
{
   kstat_t *ks;
   kid_t nkcid;
   int i;
   int changed = 0;
   static int ncpu = 0;
   static kid_t kcid = 0;
   kstat_named_t *kn;

   /*
   * 0. kstat_open
   */
   if (!kc) {
      kc = kstat_open();
      if (!kc) {
         perror("kstat_open ");
         return -1;
      }
      changed = 1;
      kcid = kc->kc_chain_id;
   }


   /* keep doing it until no more changes */
   kcid_changed:

   /*
   * 1.  kstat_chain_update
   */
   nkcid = kstat_chain_update(kc);
   if (nkcid) {
      /* UPDKCID will abort if nkcid is -1, so no need to check */
      changed = 1;
      kcid = nkcid;
   }
   UPDKCID(nkcid,0);

   ks = kstat_lookup(kc, "unix", 0, "system_misc");
   if (kstat_read(kc, ks, 0) == -1) {
      perror("kstat_read");
      return -1;
   }

#if 0
   /* load average */
   kn = kstat_data_lookup(ks, "avenrun_1min");
   if (kn)
      avenrun[0] = kn->value.ui32;
   kn = kstat_data_lookup(ks, "avenrun_5min");
   if (kn)
      avenrun[1] = kn->value.ui32;
   kn = kstat_data_lookup(ks, "avenrun_15min");
   if (kn)
      avenrun[2] = kn->value.ui32;

   /* nproc */
   kn = kstat_data_lookup(ks, "nproc");
   if (kn) {
      nproc = kn->value.ui32;
#ifdef NO_NPROC
      if (nproc > maxprocs)
      reallocproc(2 * nproc);
#endif
   }
#endif

   if (changed) {
      int ncpus = 0;

      /*
      * 2. get data addresses
      */

      ncpu = 0;

      kn = kstat_data_lookup(ks, "ncpus");
      if (kn && kn->value.ui32 > ncpus) {
         ncpus = kn->value.ui32;
         cpu_ks = (kstat_t **)sge_realloc(cpu_ks, ncpus * sizeof(kstat_t *), 1);
         cpu_stat = (cpu_stat_t *)sge_realloc(cpu_stat, ncpus * sizeof(cpu_stat_t), 1);
      }

      for (ks = kc->kc_chain; ks; ks = ks->ks_next) {
         if (strncmp(ks->ks_name, "cpu_stat", 8) == 0) {
            nkcid = kstat_read(kc, ks, NULL);
            /* if kcid changed, pointer might be invalid */
            UPDKCID(nkcid, kcid);

            cpu_ks[ncpu] = ks;
            ncpu++;
            if (ncpu >= ncpus) {
               break;
            }
         }
      }
      /* note that ncpu could be less than ncpus, but that's okay */
      changed = 0;
   }


   /*
   * 3. get data
   */

   for (i = 0; i < ncpu; i++) {
      nkcid = kstat_read(kc, cpu_ks[i], &cpu_stat[i]);
      /* if kcid changed, pointer might be invalid */
      UPDKCID(nkcid, kcid);
   }

   /* return the number of cpus found */
   return(ncpu);
}
예제 #26
0
파일: fstype.c 프로젝트: HPCKP/gridengine
int main(int argc, char *argv[]) {

   int ret=1;

   if (argc < 2) {
      printf("Usage: fstype <directory>\n");
      return 1;
   } else {
#if defined(LINUX)
   struct statfs buf;
   FILE *fd = NULL;
   char buffer[BUF_SIZE];
   ret = statfs(argv[1], &buf);
#elif defined(DARWIN) || defined(FREEBSD) || (defined(NETBSD) && !defined(ST_RDONLY))
   struct statfs buf;
   ret = statfs(argv[1], &buf);
#elif defined(INTERIX)
   struct statvfs buf;
   ret = wl_statvfs(argv[1], &buf);
#elif defined(SOLARIS)
   struct statvfs buf;
   struct mntinfo_kstat mnt_info;
   minor_t fsid;
   kstat_ctl_t    *kc = NULL;
   kstat_t        *ksp;
   kstat_named_t  *knp;

   ret = statvfs(argv[1], &buf);
   /*
      statfs returns dev_t (32bit - 14bit major + 18bit minor number)
      the kstat_instance is the minor number
   */
   fsid = (minor_t)(buf.f_fsid & 0x3ffff);

   if (strcmp(buf.f_basetype, "nfs") == 0) {
            kc = kstat_open();
            for (ksp = kc->kc_chain; ksp; ksp = ksp->ks_next) {
               if (ksp->ks_type != KSTAT_TYPE_RAW)
			         continue;
		         if (strcmp(ksp->ks_module, "nfs") != 0)
			         continue;
		         if (strcmp(ksp->ks_name, "mntinfo") != 0)
			         continue;
               if (kstat_read(kc, ksp, &mnt_info) == -1) {
                  kstat_close(kc);
                  printf("error\n");
                  return 2;
               }
               if (fsid  == ksp->ks_instance) {
                  if ( mnt_info.mik_vers >= 4 ) {
                     sprintf(buf.f_basetype, "%s%i", buf.f_basetype, mnt_info.mik_vers);
                  }
                  break;
               }
            }
            ret = kstat_close(kc);
   }
#else
   struct statvfs buf;
   ret = statvfs(argv[1], &buf);
#endif

   if(ret!=0) {
      printf("Error: %s\n", strerror(errno));
      return 2;
   }

#if defined (DARWIN) || defined(FREEBSD) || defined(NETBSD)
   printf("%s\n", buf.f_fstypename);
#elif defined(LINUX)
   /* 0x6969 is NFS_SUPER_MAGIC (see statfs(2) man page) */
   if (buf.f_type == 0x6969) {
      /*
       * Linux is not able to detect the right nfs version form the statfs struct.
       * f_type always returns nfs, even when it's a nfs4. We are looking into
       * the /etc/mtab file until we found a better solution to do this.
       */
      fd = fopen("/etc/mtab", "r");
      if (fd == NULL) {
         fprintf(stderr, "file system type could not be detected\n");
         printf("unknown fs\n");
         return 1;
      } else {
         bool found_line = false;
         sge_strip_white_space_at_eol(argv[1]);
         sge_strip_slash_at_eol(argv[1]);

         while (fgets(buffer, sizeof(buffer), fd) != NULL) {
            char* export = NULL; /* where is the nfs exported*/
            char* mountpoint = NULL; /*where is it mounted to */
            char* fstype = NULL; /*type of exported file system */

            export = sge_strtok(buffer, " \t");
            mountpoint = sge_strtok(NULL, " \t");
            fstype = sge_strtok(NULL, " \t");

            /* search only in valid lines that contain NFS4 mounts */
            if (mountpoint != NULL && fstype != NULL && strcmp(fstype, "nfs4") == 0) {
               /* search mountpoint in given path */
               char *pos = strstr(argv[1], mountpoint);
               if (pos == argv[1]) {
                  /* we found the mountpoint at the start of the given path, this is it! */
                  found_line = true;
                  printf ("%s\n", fstype);
                  break;
               }
            }
         }

         fclose(fd);
         if (found_line == false) { /*if type could not be detected via /etc/mtab, then we have to print out "nfs"*/
            printf("nfs\n");
         }
      }
   } else {
예제 #27
0
파일: load_stats.c 프로젝트: ancrux/cpp-ex
sg_load_stats *sg_get_load_stats(){

#if !defined(CYGWIN) && !defined(WIN32)
	static sg_load_stats load_stat;

#ifdef HPUX
	struct pst_dynamic pstat_dynamic;
#else
	double loadav[3];
#endif
#endif /* not CYGWIN or WIN32 */

#ifdef CYGWIN
	sg_set_error(SG_ERROR_UNSUPPORTED, "Cygwin");
	return NULL;
#elif defined(WIN32)
	sg_set_error(SG_ERROR_UNSUPPORTED, "Win32");
	return NULL;
#else

#if defined(SOLARIS) && !defined(HAVE_SYS_LOADAVG_H)

	kstat_ctl_t *kc;	
	kstat_t *ksp;
	kstat_named_t *kn;

	if ((kc = kstat_open()) == NULL) {
		sg_set_error(SG_ERROR_KSTAT_OPEN, NULL);
		return NULL;
	}

	if((ksp=kstat_lookup(kc, "unix", 0, "system_misc")) == NULL){
		sg_set_error(SG_ERROR_KSTAT_LOOKUP, "unix,0,system_misc");
		kstat_close(kc);
		return NULL;
	}

	if (kstat_read(kc, ksp, 0) == -1) {
		sg_set_error(SG_ERROR_KSTAT_READ, NULL);
		kstat_close(kc);
		return NULL;
	}

	kstat_close(kc);

	if((kn=kstat_data_lookup(ksp, "avenrun_1min")) == NULL){
		sg_set_error(SG_ERROR_KSTAT_DATA_LOOKUP, "avenrun_1min");
		return NULL;
	}
	load_stat.min1 = (double)kn->value.ui32 / (double)256;

	if((kn=kstat_data_lookup(ksp, "avenrun_5min")) == NULL){
		sg_set_error(SG_ERROR_KSTAT_DATA_LOOKUP, "avenrun_5min");
		return NULL;
	}
	load_stat.min5 = (double)kn->value.ui32 / (double)256;

	if((kn=kstat_data_lookup(ksp, "avenrun_15min")) == NULL){
		sg_set_error(SG_ERROR_KSTAT_DATA_LOOKUP, "avenrun_15min");
		return NULL;
	}
	load_stat.min15 = (double)kn->value.ui32 / (double)256;
#elif defined(HPUX)
	if (pstat_getdynamic(&pstat_dynamic, sizeof(pstat_dynamic), 1, 0) == -1) {
		sg_set_error_with_errno(SG_ERROR_PSTAT, "pstat_dynamic");
		return NULL;
	}

	load_stat.min1=pstat_dynamic.psd_avg_1_min;
	load_stat.min5=pstat_dynamic.psd_avg_5_min;
	load_stat.min15=pstat_dynamic.psd_avg_15_min;
#else
	getloadavg(loadav,3);

	load_stat.min1=loadav[0];
	load_stat.min5=loadav[1];
	load_stat.min15=loadav[2];
#endif

	return &load_stat;
#endif
}
예제 #28
0
파일: sunos.c 프로젝트: 353355756/node
int uv_cpu_info(uv_cpu_info_t** cpu_infos, int* count) {
  int           lookup_instance;
  kstat_ctl_t   *kc;
  kstat_t       *ksp;
  kstat_named_t *knp;
  uv_cpu_info_t* cpu_info;

  kc = kstat_open();
  if (kc == NULL)
    return -EPERM;

  /* Get count of cpus */
  lookup_instance = 0;
  while ((ksp = kstat_lookup(kc, (char*) "cpu_info", lookup_instance, NULL))) {
    lookup_instance++;
  }

  *cpu_infos =  malloc(lookup_instance * sizeof(**cpu_infos));
  if (!(*cpu_infos)) {
    kstat_close(kc);
    return -ENOMEM;
  }

  *count = lookup_instance;

  cpu_info = *cpu_infos;
  lookup_instance = 0;
  while ((ksp = kstat_lookup(kc, (char*) "cpu_info", lookup_instance, NULL))) {
    if (kstat_read(kc, ksp, NULL) == -1) {
      cpu_info->speed = 0;
      cpu_info->model = NULL;
    } else {
      knp = kstat_data_lookup(ksp, (char*) "clock_MHz");
      assert(knp->data_type == KSTAT_DATA_INT32 ||
             knp->data_type == KSTAT_DATA_INT64);
      cpu_info->speed = (knp->data_type == KSTAT_DATA_INT32) ? knp->value.i32
                                                             : knp->value.i64;

      knp = kstat_data_lookup(ksp, (char*) "brand");
      assert(knp->data_type == KSTAT_DATA_STRING);
      cpu_info->model = strdup(KSTAT_NAMED_STR_PTR(knp));
    }

    lookup_instance++;
    cpu_info++;
  }

  cpu_info = *cpu_infos;
  lookup_instance = 0;
  for (;;) {
    ksp = kstat_lookup(kc, (char*) "cpu", lookup_instance, (char*) "sys");

    if (ksp == NULL)
      break;

    if (kstat_read(kc, ksp, NULL) == -1) {
      cpu_info->cpu_times.user = 0;
      cpu_info->cpu_times.nice = 0;
      cpu_info->cpu_times.sys = 0;
      cpu_info->cpu_times.idle = 0;
      cpu_info->cpu_times.irq = 0;
    } else {
      knp = kstat_data_lookup(ksp, (char*) "cpu_ticks_user");
      assert(knp->data_type == KSTAT_DATA_UINT64);
      cpu_info->cpu_times.user = knp->value.ui64;

      knp = kstat_data_lookup(ksp, (char*) "cpu_ticks_kernel");
      assert(knp->data_type == KSTAT_DATA_UINT64);
      cpu_info->cpu_times.sys = knp->value.ui64;

      knp = kstat_data_lookup(ksp, (char*) "cpu_ticks_idle");
      assert(knp->data_type == KSTAT_DATA_UINT64);
      cpu_info->cpu_times.idle = knp->value.ui64;

      knp = kstat_data_lookup(ksp, (char*) "intr");
      assert(knp->data_type == KSTAT_DATA_UINT64);
      cpu_info->cpu_times.irq = knp->value.ui64;
      cpu_info->cpu_times.nice = 0;
    }

    lookup_instance++;
    cpu_info++;
  }

  kstat_close(kc);

  return 0;
}
예제 #29
0
/*
 * Retrieves the statistics for a specified port.phy on an adapter
 */
HBA_STATUS Sun_sasGetPhyStatistics(HBA_HANDLE handle,
    HBA_UINT32 port, HBA_UINT32 phy, SMHBA_PHYSTATISTICS *pStatistics) {
	const char	ROUTINE[] = "Sun_sasGetPhyStatistics";
	HBA_STATUS		status = HBA_STATUS_OK;
	struct sun_sas_hba	*hba_ptr;
	struct sun_sas_port	*hba_port_ptr;
	struct phy_info		*phy_ptr;
	PSMHBA_SASPHYSTATISTICS	psas;
	kstat_ctl_t		*kc;
	kstat_t			*ksp;
	kstat_named_t		*kname;
	char			*charptr, path[MAXPATHLEN + 1];
	char			*driver_name, kstat_name[256];
	di_node_t		node;
	int			instance = 0;
	int			i;
	uint64_t		iport_wwn;

	/* Validate the arguments */
	if (pStatistics == NULL) {
		log(LOG_DEBUG, ROUTINE,
		    "NULL Phy Statistics buffer of phyIndex: %08lx", phy);
		return (HBA_STATUS_ERROR_ARG);
	}
	psas = pStatistics->SASPhyStatistics;
	if (psas == NULL) {
		log(LOG_DEBUG, ROUTINE,
		    "NULL SAS Phy Statistics buffer of phyIndex: %08lx", phy);
		return (HBA_STATUS_ERROR_ARG);
	}

	lock(&all_hbas_lock);

	if ((hba_ptr = Retrieve_Sun_sasHandle(handle)) == NULL) {
		log(LOG_DEBUG, ROUTINE,
		    "Invalid HBA handler %08lx of phyIndex: %08lx",
		    handle, phy);
		unlock(&all_hbas_lock);
		return (HBA_STATUS_ERROR_INVALID_HANDLE);
	}

	/* Check for stale data */
	status = verifyAdapter(hba_ptr);
	if (status != HBA_STATUS_OK) {
		log(LOG_DEBUG, ROUTINE,
		    "Verify Adapter failed for phyIndex: %08lx", phy);
		unlock(&all_hbas_lock);
		return (status);
	}

	for (hba_port_ptr = hba_ptr->first_port;
	    hba_port_ptr != NULL;
	    hba_port_ptr = hba_port_ptr->next) {
		if (hba_port_ptr->index == port) {
			break;
		}
	}

	if (hba_port_ptr == NULL) {
		log(LOG_DEBUG, ROUTINE,
		    "Invalid port index of phyIndex: %08lx", phy);
		unlock(&all_hbas_lock);
		return (HBA_STATUS_ERROR_ILLEGAL_INDEX);
	}

	if (phy >= hba_port_ptr->port_attributes.PortSpecificAttribute.
	    SASPort->NumberofPhys) {
		log(LOG_DEBUG, ROUTINE, "Invalid phy index %08lx", phy);
		unlock(&all_hbas_lock);
		return (HBA_STATUS_ERROR_ILLEGAL_INDEX);
	}

	/* We need to find out the phy identifier. */
	for (phy_ptr = hba_port_ptr->first_phy;
	    phy_ptr != NULL;
	    phy_ptr = phy_ptr->next) {
		if (phy == phy_ptr->index)
			break;
	}

	if (phy_ptr == NULL) {
		log(LOG_DEBUG, ROUTINE, "Invalid phy index %08lx", phy);
		unlock(&all_hbas_lock);
		return (HBA_STATUS_ERROR_ILLEGAL_INDEX);
	}

	/*
	 * for statistics that are not supported, its bits should all be
	 * set to -1
	 */
	(void) memset(pStatistics->SASPhyStatistics, 0xff,
	    sizeof (SMHBA_SASPHYSTATISTICS));


	/* First, we need the deivce path to locate the devinfo node. */
	(void *) strlcpy(path, hba_port_ptr->device_path,
	    sizeof (path));
	charptr = strrchr(path, ':');
	if (charptr) {
		*charptr = '\0';
	}

	errno = 0;

	(void *) memset(kstat_name, 0, sizeof (kstat_name));
	node = di_init(path, DINFOCPYONE);
	if (node == DI_NODE_NIL) {
		di_fini(node);
		log(LOG_DEBUG, ROUTINE,
		    "Unable to take devinfo snapshot on HBA \"%s\" "
		    "for phyIndex: %08lx due to %s",
		    path, phy, strerror(errno));
		unlock(&all_hbas_lock);
		return (HBA_STATUS_ERROR);
	}

	/*
	 * Then we could fetch the instance number and driver name of this
	 * device.
	 */
	instance = di_instance(node);
	if (instance == -1) {
		di_fini(node);
		log(LOG_DEBUG, ROUTINE,
		    "An instance number has not been assigned to the "
		    "device \"%s\" when get phyIndex: %08lx", path, phy);
		unlock(&all_hbas_lock);
		return (HBA_STATUS_ERROR);
	}

	driver_name = di_driver_name(node);
	if (driver_name == NULL) {
		di_fini(node);
		log(LOG_DEBUG, ROUTINE,
		    "No driver bound to this device \"%s\" "
		    "when get phyIndex: %08lx",
		    path, phy);
		unlock(&all_hbas_lock);
		return (HBA_STATUS_ERROR);
	}

	di_fini(node);

	iport_wwn = wwnConversion(hba_port_ptr->port_attributes.\
	    PortSpecificAttribute.SASPort->LocalSASAddress.wwn);

	/*
	 * Construct the kstat name here.
	 */
	(void) snprintf(kstat_name, sizeof (kstat_name), "%s.%016llx.%u.%u",
	    driver_name, iport_wwn, instance, phy_ptr->phy.PhyIdentifier);

	/* retrieve all the statistics from kstat. */
	kc = kstat_open();
	if (kc == NULL) {
		log(LOG_DEBUG, ROUTINE,
		    "kstat_open failed due to \"%s\" of phyIndex: %08lx",
		    strerror(errno), phy);
		unlock(&all_hbas_lock);
		return (HBA_STATUS_ERROR);
	}
	ksp = kstat_lookup(kc, NULL, -1, kstat_name);
	if (ksp == NULL) {
		log(LOG_DEBUG, ROUTINE,
		    "No matching kstat name found for \"%s\" "
		    "of phyIndex: %08lx",
		    kstat_name, phy);
		unlock(&all_hbas_lock);
		(void) kstat_close(kc);
		return (HBA_STATUS_ERROR);
	}
	/* Found the phy we're looking for. */
	if (kstat_read(kc, ksp, NULL) == -1) {
		log(LOG_DEBUG, ROUTINE,
		    "error reading kstat data due to \"%s\" "
		    "of phyIndex: %08lx",
		    strerror(errno), phy);
		unlock(&all_hbas_lock);
		(void) kstat_close(kc);
		return (HBA_STATUS_ERROR);
	}

	kname = (kstat_named_t *)ksp->ks_data;
	for (i = 0; i < ksp->ks_ndata; i++, kname++) {
		if (strcmp(kname->name,
		    "SecondsSinceLastReset") == 0) {
		    psas->SecondsSinceLastReset = kname->value.ull;
			continue;
		}
		if (strcmp(kname->name, "TxFrames") == 0) {
			psas->TxFrames = kname->value.ull;
			continue;
		}
		if (strcmp(kname->name, "RxFrames") == 0) {
			psas->RxFrames = kname->value.ull;
			continue;
		}
		if (strcmp(kname->name, "TxWords") == 0) {
			psas->TxWords = kname->value.ull;
			continue;
		}
		if (strcmp(kname->name, "RxWords") == 0) {
			psas->RxWords = kname->value.ull;
			continue;
		}
		if (strcmp(kname->name, "InvalidDwordCount") == 0) {
			psas->InvalidDwordCount = kname->value.ull;
			continue;
		}
		if (strcmp(kname->name, "RunningDisparityErrorCount") == 0) {
			psas->RunningDisparityErrorCount = kname->value.ull;
			continue;
		}
		if (strcmp(kname->name, "LossofDwordSyncCount") == 0) {
			psas->LossofDwordSyncCount = kname->value.ull;
			continue;
		}
		if (strcmp(kname->name, "PhyResetProblemCount") == 0) {
			psas->PhyResetProblemCount = kname->value.ull;
		}
	}
	unlock(&all_hbas_lock);
	(void) kstat_close(kc);

	return (HBA_STATUS_OK);
}
예제 #30
0
/**
 * Returns the system uptime in centiseconds.
 *
 * @note The value returned by this function is not identical to sysUpTime
 *   defined in RFC 1213. get_uptime() returns the system uptime while
 *   sysUpTime represents the time that has elapsed since the most recent
 *   restart of the network manager (snmpd).
 *
 * @see See also netsnmp_get_agent_uptime().
 */
long
get_uptime(void)
{
#if defined(aix4) || defined(aix5) || defined(aix6) || defined(aix7)
    struct nlist nl;
    int kmem;
    time_t lbolt;
    nl.n_name = "lbolt";
    if(knlist(&nl, 1, sizeof(struct nlist)) != 0) return(0);
    if(nl.n_type == 0 || nl.n_value == 0) return(0);
    if((kmem = open("/dev/mem", 0)) < 0) return 0;
    lseek(kmem, (long) nl.n_value, L_SET);
    read(kmem, &lbolt, sizeof(lbolt));
    close(kmem);
    return(lbolt);
#elif defined(solaris2)
    kstat_ctl_t    *ksc = kstat_open();
    kstat_t        *ks;
    kid_t           kid;
    kstat_named_t  *named;
    u_long          lbolt = 0;

    if (ksc) {
        ks = kstat_lookup(ksc, "unix", -1, "system_misc");
        if (ks) {
            kid = kstat_read(ksc, ks, NULL);
            if (kid != -1) {
                named = kstat_data_lookup(ks, "lbolt");
                if (named) {
#ifdef KSTAT_DATA_UINT32
                    lbolt = named->value.ui32;
#else
                    lbolt = named->value.ul;
#endif
                }
            }
        }
        kstat_close(ksc);
    }
    return lbolt;
#elif defined(linux) || defined(cygwin)
    FILE           *in = fopen("/proc/uptime", "r");
    long            uptim = 0, a, b;
    if (in) {
        if (2 == fscanf(in, "%ld.%ld", &a, &b))
            uptim = a * 100 + b;
        fclose(in);
    }
    return uptim;
#else
    struct timeval  now;
    long            boottime_csecs, nowtime_csecs;

    boottime_csecs = get_boottime();
    if (boottime_csecs == 0)
        return 0;
    gettimeofday(&now, (struct timezone *) 0);
    nowtime_csecs = (now.tv_sec * 100) + (now.tv_usec / 10000);

    return (nowtime_csecs - boottime_csecs);
#endif
}