Process list/table area blank on MP machines running 2.6 kernel.
I've developed a patch for this problema, it is attached. I tested it
on UP and MP 2.6 machines, and on MP and UP 2.4 machines. No problems
that I could see, with the options that I had set. I also fixed a
couple of compile time warnings caused by having slightly incorrect
format specifiers in s.sprintf calls.
Cheers,
a
diff -Naur qps-1.9.7.0/proc.C qps-1.9.7.0,fixed/proc.C
--- qps-1.9.7.0/proc.C 2000-05-02 09:38:59.000000000 -0700
+++ qps-1.9.7.0,fixed/proc.C 2005-08-13 13:16:18.387318272 -0700
@@ -29,6 +29,8 @@
#include <limits.h>
#endif
+extern int kernel_version_2_6;
+
//#define FAKE_SMP 4 // for SMP debugging on UP machines
// socket states, from <linux/net.h> and touched to avoid name collisions
@@ -147,6 +149,7 @@
char buf[256];
char sbuf[4096]; // should be enough to acommodate /proc/X/stat
char cmdbuf[MAX_CMD_LEN];
+ int da_cpu = 0;
pid = proc_pid;
@@ -198,17 +201,19 @@
long stime, cstime;
sscanf(p + 2, "%c %d %d %d %d %d %lu %lu %lu %lu %lu "
"%ld %ld %ld %ld %d %d %*s %*s %lu %*s %*s %*s %*s %*s %*s %*s %*s "
- "%*s %*s %*s %*s %lu",
+ "%*s %*s %*s %*s %lu %*s %*s %*s %d",
&state, &ppid, &pgrp, &session, &tty, &tpgid,
&flags, &minflt, &cminflt, &majflt, &cmajflt,
&utime, &stime, &cutime, &cstime, &priority, &nice,
- /* timeout, itrealvalue */
+ /* numthreads, itrealvalue */
&starttime,
/* vsize */
/* rss */
/* rlim, startcode, endcode, startstack kstkesp kstkeip,
signal, blocked, sigignore, sigcatch */
- &wchan);
+ &wchan,
+ /* 2.6: 0UL, 0UL, exit_sig, cpu, rt_priority, policy */
+ &da_cpu);
utime += stime; // we make no user/system time distinction
cutime += cstime;
@@ -243,30 +248,30 @@
strcpy(buf, path);
strcat(buf, "/cantmove");
if((statlen = read_file(buf, sbuf, sizeof(sbuf) - 1)) > 0) {
- sbuf[statlen] = '\0';
- p = strchr(sbuf, '\n');
- if(p) {
- *p = '\0';
- cantmove = sbuf;
- }
+ sbuf[statlen] = '\0';
+ p = strchr(sbuf, '\n');
+ if(p) {
+ *p = '\0';
+ cantmove = sbuf;
+ }
}
// Read /proc/XX/nmigs
strcpy(buf, path);
strcat(buf, "/nmigs");
if((statlen = read_file(buf, sbuf, sizeof(sbuf) - 1)) <= 0)
- nmigs = -1;
+ nmigs = -1;
else {
- sbuf[statlen] = '\0';
- sscanf(sbuf, "%d", &nmigs);
+ sbuf[statlen] = '\0';
+ sscanf(sbuf, "%d", &nmigs);
}
// Read /proc/XX/lock
strcpy(buf, path);
strcat(buf, "/lock");
if((statlen = read_file(buf, sbuf, sizeof(sbuf) - 1)) <= 0)
- locked = -1;
+ locked = -1;
else {
- sbuf[statlen] = '\0';
- sscanf(sbuf, "%d", &locked);
+ sbuf[statlen] = '\0';
+ sscanf(sbuf, "%d", &locked);
}
// See if this is a remote job
@@ -278,7 +283,7 @@
strcpy(buf, path2);
strcat(buf, "/stats");
if((statlen = read_file(buf, sbuf, sizeof(sbuf) - 1)) > 0) {
- isremote = TRUE; // This process is a visitor
+ isremote = TRUE; // This process is a visitor
// The following variables are available, but are not used at the
// moment, so they are merely placeholders right now.
@@ -297,20 +302,20 @@
sbuf[statlen] = '\0';
if(sscanf(sbuf, "%d", &from) != 1) return -1;
- // comm is parsed wrong (contains "remote(xx)")
- sscanf(comm, "remote(%d)", &remotepid);
- comm = cmdline; // grab comm from there...
+ // comm is parsed wrong (contains "remote(xx)")
+ sscanf(comm, "remote(%d)", &remotepid);
+ comm = cmdline; // grab comm from there...
} else {
- isremote = FALSE;
- remotepid = -1;
- from = -1;
+ isremote = FALSE;
+ remotepid = -1;
+ from = -1;
}
if(from > 0)
- sprintf(buf, "%d>", from);
+ sprintf(buf, "%d>", from);
else if(where > 0)
- sprintf(buf, ">%d", where);
+ sprintf(buf, ">%d", where);
else
- strcpy(buf, "-");
+ strcpy(buf, "-");
migr = buf;
#endif // MOSIX
@@ -320,8 +325,7 @@
strcat(buf, "/status");
if((statlen = read_file(buf, sbuf, sizeof(sbuf) - 1)) <= 0) return -1;
sbuf[statlen] = '\0';
- if(!(p = strstr(sbuf, "Uid:")))
- return -1;
+ if(!(p = strstr(sbuf, "Uid:"))) return -1;
sscanf(p, "Uid: %d %d %d %d Gid: %d %d %d %d",
&uid, &euid, &suid, &fsuid,
&gid, &egid, &sgid, &fsgid);
@@ -329,26 +333,30 @@
which_cpu = 0;
per_cpu_times = 0;
if(num_cpus > 1) {
- strcpy(buf, path);
- strcat(buf, "/cpu");
- if( (statlen = read_file(buf, sbuf, sizeof(sbuf) - 1)) <= 0)
- return -1;
- sbuf[statlen] = '\0';
- per_cpu_times = new unsigned long[num_cpus];
- p = sbuf;
- for(unsigned cpu = 0; cpu < num_cpus; cpu++) {
- p = strchr(p, '\n');
- if (!p) {
- for(cpu = 0; cpu < num_cpus; cpu++)
- per_cpu_times[cpu] = 0;
- break;
- }
- p++;
- unsigned long utime, stime;
- sscanf(p, "%*s %lu %lu", &utime, &stime);
- per_cpu_times[cpu] = utime + stime;
+ if (!kernel_version_2_6) {
+ strcpy(buf, path);
+ strcat(buf, "/cpu");
+ if( (statlen = read_file(buf, sbuf, sizeof(sbuf) - 1))
<= 0)
+ return -1;
+ sbuf[statlen] = '\0';
+ per_cpu_times = new unsigned long[num_cpus];
+ p = sbuf;
+ for(unsigned cpu = 0; cpu < num_cpus; cpu++) {
+ p = strchr(p, '\n');
+ if (!p) {
+ for(cpu = 0; cpu < num_cpus; cpu++)
+ per_cpu_times[cpu] = 0;
+ break;
+ }
+ p++;
+ unsigned long utime, stime;
+ sscanf(p, "%*s %lu %lu", &utime, &stime);
+ per_cpu_times[cpu] = utime + stime;
+ }
+ } else {
+ which_cpu = da_cpu;
+ }
}
- }
gettimeofday(&tv, 0);
policy = -1; // will get it when needed
@@ -746,7 +754,7 @@
// a TCP or UDP socket
sock_inodes->add(SockInode(fdnum, ino));
QString s;
- s.sprintf("%sp socket %d",
+ s.sprintf("%sp socket %ld",
si->proto == Sockinfo::TCP ? "tc" : "ud", ino);
fd_files->add(new Fileinfo(fdnum, s, mode));
return;
@@ -768,7 +776,7 @@
case SSCONNECTED: st = "connected"; break;
case SSDISCONNECTING: st = "disconn"; break;
}
- s.sprintf("unix domain socket %d (%s, %s) ",
+ s.sprintf("unix domain socket %ld (%s, %s) ",
ino, tp, st);
s.append(us->name);
fd_files->add(new Fileinfo(fdnum, s, mode));
@@ -1711,19 +1719,21 @@
#ifdef LINUX
if(Procinfo::num_cpus > 1) {
- // SMP: see which processor was used the most
- int best_cpu = -1;
- unsigned long most = 0;
- for(unsigned cpu = 0; cpu < Procinfo::num_cpus; cpu++) {
- unsigned long delta =
- p->per_cpu_times[cpu] - oldp->per_cpu_times[cpu];
- if(delta > most) {
- most = delta;
- best_cpu = cpu;
+ if (!kernel_version_2_6) {
+ // SMP: see which processor was used the most
+ int best_cpu = -1;
+ unsigned long most = 0;
+ for(unsigned cpu = 0; cpu < Procinfo::num_cpus; cpu++) {
+ unsigned long delta =
+ p->per_cpu_times[cpu] -
oldp->per_cpu_times[cpu];
+ if(delta > most) {
+ most = delta;
+ best_cpu = cpu;
+ }
+ // if no cpu time has been spent, use previous value
+ p->which_cpu = (best_cpu >= 0) ? best_cpu :
oldp->which_cpu;
+ }
}
- // if no cpu time has been spent, use previous value
- p->which_cpu = (best_cpu >= 0) ? best_cpu : oldp->which_cpu;
- }
}
#endif
oldp->deref();
@@ -1744,15 +1754,17 @@
#ifdef LINUX
if(Procinfo::num_cpus > 1) {
- // first tick: count times from 0
- unsigned long most = 0;
- for(unsigned cpu = 0; cpu < Procinfo::num_cpus; cpu++) {
- unsigned long t = p->per_cpu_times[cpu];
- if(t > most) {
- most = t;
- p->which_cpu = cpu;
+ if (!kernel_version_2_6) {
+ // first tick: count times from 0
+ unsigned long most = 0;
+ for(unsigned cpu = 0; cpu < Procinfo::num_cpus; cpu++) {
+ unsigned long t = p->per_cpu_times[cpu];
+ if(t > most) {
+ most = t;
+ p->which_cpu = cpu;
+ }
+ }
}
- }
}
#endif
}
diff -Naur qps-1.9.7.0/qps.C qps-1.9.7.0,fixed/qps.C
--- qps-1.9.7.0/qps.C 2000-05-02 15:14:19.000000000 -0700
+++ qps-1.9.7.0,fixed/qps.C 2005-08-13 13:19:22.267125940 -0700
@@ -12,9 +12,11 @@
#include <sys/time.h>
#include <sys/resource.h>
#include <sys/utsname.h>
+#include <sys/stat.h>
#include <signal.h>
#include <errno.h>
#include <sched.h>
+#include <fcntl.h>
#include "qps.h"
#include "dialogs.h"
@@ -128,6 +130,12 @@
yellow, black // selected process: bg, fg
};
+#ifdef LINUX
+//the modifications to make this work on 2.6 MP machines are the fault of
+//Andrew Sharp <[EMAIL PROTECTED]>
+int kernel_version_2_6 = 0; //set to 1 if running on a 2.6 kernel
+#endif
+
const char *Qps::color_name[NUM_COLORS] = {
"cpu-user",
#ifdef LINUX
@@ -1758,6 +1766,8 @@
int saved_argc = argc;
char **saved_argv = (char **)malloc(sizeof(char *) * (argc + 1));
memcpy(saved_argv, argv, sizeof(char *) * (argc + 1));
+ char buf[1024];
+ int kv;
bool start_iconic = FALSE;
for(int i = 1; i < argc; i++) {
@@ -1776,6 +1786,21 @@
if(!getenv("LANG"))
putenv("LANG=C");
+#ifdef LINUX
+ // what kind of stinkin linux kernel are we on, anyway
+ kv = open("/proc/version", O_RDONLY);
+ if (kv < 0) {
+ fprintf(stderr, "can't get kernel version: open(/proc/version)"
+ " returned %d\n", kv);
+ exit(1);
+ }
+ read(kv, buf, 1023);
+ if (!strncmp("2.6", &buf[14], 3)) {
+ kernel_version_2_6 = 1;
+ }
+ close(kv);
+#endif
+
QApplication app(argc, argv);
// gross hack: if the font is too wide, then it's probably a 100dpi font