X-Git-Url: https://git.octo.it/?a=blobdiff_plain;f=src%2Fprocesses.c;h=1c5b96308eb8275d3b2213f3ee0be0923ebcb2f6;hb=e9e85b7ab4d0f303e61c6557fb76340ee95b8dee;hp=68f30a5a30e87737cc7c12a1855dbb5787e19645;hpb=ca316d91e178412604ea8462dc60a8bc32cbfc87;p=collectd.git diff --git a/src/processes.c b/src/processes.c index 68f30a5a..1c5b9630 100644 --- a/src/processes.c +++ b/src/processes.c @@ -112,7 +112,22 @@ /* #endif HAVE_PROCINFO_H */ #elif KERNEL_SOLARIS +/* Hack: Avoid #error when building a 32-bit binary with + * _FILE_OFFSET_BITS=64. There is a reason for this #error, as one + * of the structures in uses an off_t, but that + * isn't relevant to our usage of procfs. */ +#if !defined(_LP64) && _FILE_OFFSET_BITS == 64 +# define SAVE_FOB_64 +# undef _FILE_OFFSET_BITS +#endif + # include + +#ifdef SAVE_FOB_64 +# define _FILE_OFFSET_BITS 64 +# undef SAVE_FOB_64 +#endif + # include /* #endif KERNEL_SOLARIS */ @@ -790,8 +805,8 @@ static int ps_read_tasks (int pid) return ((count >= 1) ? count : 1); } /* int *ps_read_tasks */ -/* Read advanced virtual memory data from /proc/pid/status */ -static procstat_t *ps_read_vmem (int pid, procstat_t *ps) +/* Read data from /proc/pid/status */ +static procstat_t *ps_read_status (int pid, procstat_t *ps) { FILE *fh; char buffer[1024]; @@ -799,6 +814,7 @@ static procstat_t *ps_read_vmem (int pid, procstat_t *ps) unsigned long long lib = 0; unsigned long long exe = 0; unsigned long long data = 0; + unsigned long long threads = 0; char *fields[8]; int numfields; @@ -811,7 +827,8 @@ static procstat_t *ps_read_vmem (int pid, procstat_t *ps) long long tmp; char *endptr; - if (strncmp (buffer, "Vm", 2) != 0) + if (strncmp (buffer, "Vm", 2) != 0 + && strncmp (buffer, "Threads", 7) != 0) continue; numfields = strsplit (buffer, fields, @@ -837,6 +854,10 @@ static procstat_t *ps_read_vmem (int pid, procstat_t *ps) { exe = tmp; } + else if (strncmp(buffer, "Threads", 7) == 0) + { + threads = tmp; + } } } /* while (fgets) */ @@ -849,6 +870,7 @@ static procstat_t *ps_read_vmem (int pid, procstat_t *ps) ps->vmem_data = data * 1024; ps->vmem_code = (exe + lib) * 1024; + ps->num_lwp = threads; return (ps); } /* procstat_t *ps_read_vmem */ @@ -991,10 +1013,21 @@ int ps_read_process (int pid, procstat_t *ps, char *state) } else { - if ( (ps->num_lwp = ps_read_tasks (pid)) == -1 ) + if ( (ps_read_status(pid, ps)) == NULL) + { + /* No VMem data */ + ps->vmem_data = -1; + ps->vmem_code = -1; + ps->num_lwp = 0; + DEBUG("ps_read_process: did not get vmem data for pid %i",pid); + } + if ( ps->num_lwp <= 0) { - /* returns -1 => kernel 2.4 */ - ps->num_lwp = 1; + if ( (ps->num_lwp = ps_read_tasks (pid)) == -1 ) + { + /* returns -1 => kernel 2.4 */ + ps->num_lwp = 1; + } } ps->num_proc = 1; } @@ -1028,14 +1061,6 @@ int ps_read_process (int pid, procstat_t *ps, char *state) cpu_system_counter = cpu_system_counter * 1000000 / CONFIG_HZ; vmem_rss = vmem_rss * pagesize_g; - if ( (ps_read_vmem(pid, ps)) == NULL) - { - /* No VMem data */ - ps->vmem_data = -1; - ps->vmem_code = -1; - DEBUG("ps_read_process: did not get vmem data for pid %i",pid); - } - ps->cpu_user_counter = cpu_user_counter; ps->cpu_system_counter = cpu_system_counter; ps->vmem_size = (unsigned long) vmem_size; @@ -1199,17 +1224,17 @@ static int read_fork_rate () #endif /*KERNEL_LINUX */ #if KERNEL_SOLARIS -static const char *ps_get_cmdline (pid_t pid, /* {{{ */ +static const char *ps_get_cmdline (long pid, /* {{{ */ char *buffer, size_t buffer_size) { char path[PATH_MAX]; psinfo_t info; int status; - snprintf(path, sizeof (path), "/proc/%i/psinfo", pid); + snprintf(path, sizeof (path), "/proc/%li/psinfo", pid); status = read_file_contents (path, (void *) &info, sizeof (info)); - if (status != ((int) buffer_size)) + if (status != sizeof (info)) { ERROR ("processes plugin: Unexpected return value " "while reading \"%s\": " @@ -1230,7 +1255,7 @@ static const char *ps_get_cmdline (pid_t pid, /* {{{ */ * The values for input and ouput chars are calculated "by hand" * Added a few "solaris" specific process states as well */ -static int ps_read_process(int pid, procstat_t *ps, char *state) +static int ps_read_process(long pid, procstat_t *ps, char *state) { char filename[64]; char f_psinfo[64], f_usage[64]; @@ -1240,9 +1265,9 @@ static int ps_read_process(int pid, procstat_t *ps, char *state) psinfo_t *myInfo; prusage_t *myUsage; - snprintf(filename, sizeof (filename), "/proc/%i/status", pid); - snprintf(f_psinfo, sizeof (f_psinfo), "/proc/%i/psinfo", pid); - snprintf(f_usage, sizeof (f_usage), "/proc/%i/usage", pid); + snprintf(filename, sizeof (filename), "/proc/%li/status", pid); + snprintf(f_psinfo, sizeof (f_psinfo), "/proc/%li/psinfo", pid); + snprintf(f_usage, sizeof (f_usage), "/proc/%li/usage", pid); buffer = malloc(sizeof (pstatus_t)); @@ -1791,7 +1816,7 @@ static int ps_read (void) int wait = 0; kvm_t *kd; - char errbuf[1024]; + char errbuf[_POSIX2_LINE_MAX]; struct kinfo_proc *procs; /* array of processes */ struct kinfo_proc *proc_ptr = NULL; int count; /* returns number of processes */ @@ -1803,7 +1828,7 @@ static int ps_read (void) ps_list_reset (); /* Open the kvm interface, get a descriptor */ - kd = kvm_open (NULL, NULL, NULL, 0, errbuf); + kd = kvm_openfiles (NULL, "/dev/null", NULL, 0, errbuf); if (kd == NULL) { ERROR ("processes plugin: Cannot open kvm interface: %s", @@ -2224,14 +2249,16 @@ static int ps_read (void) while ((ent = readdir(proc)) != NULL) { - int pid; + long pid; struct procstat ps; procstat_entry_t pse; + char *endptr; if (!isdigit ((int) ent->d_name[0])) continue; - if ((pid = atoi (ent->d_name)) < 1) + pid = strtol (ent->d_name, &endptr, 10); + if (*endptr != 0) /* value didn't completely parse as a number */ continue; status = ps_read_process (pid, &ps, &state); @@ -2281,8 +2308,7 @@ static int ps_read (void) ps_list_add (ps.name, - ps_get_cmdline ((pid_t) pid, - cmdline, sizeof (cmdline)), + ps_get_cmdline (pid, cmdline, sizeof (cmdline)), &pse); } /* while(readdir) */ closedir (proc);