major rework; fixup netstat stuff; pull disk cmds into common file; change
[unix-history] / usr / src / usr.bin / systat / pigs.c
CommitLineData
1cd14d1e 1#ifndef lint
833d578b 2static char sccsid[] = "@(#)pigs.c 1.8 (Berkeley) %G%";
1cd14d1e
SL
3#endif
4
5#include "systat.h"
855ff304
KM
6#include <sys/dir.h>
7#include <sys/time.h>
8#include <sys/proc.h>
855ff304 9#include <pwd.h>
1cd14d1e 10
d830bff6
SL
11WINDOW *
12openpigs()
13{
d830bff6 14
b5eefd1e 15 return (subwin(stdscr, LINES-5-1, 0, 5, 0));
d830bff6
SL
16}
17
18closepigs(w)
19 WINDOW *w;
20{
21
22 if (w == NULL)
23 return;
d830bff6
SL
24 wclear(w);
25 wrefresh(w);
b5eefd1e 26 delwin(w);
d830bff6
SL
27}
28
855ff304
KM
29int maxind;
30int factor;
31float total;
32struct passwd *getpwuid();
33char pidname[30];
34
1cd14d1e
SL
35showpigs()
36{
37 register short auid;
38 register int i, j, y;
39 register float max;
40 register struct p_times *ptptr;
41 struct p_times temppt;
42 register struct users *knptr;
43 char *getpname(), *pnamp;
44
d830bff6
SL
45 if (pt == NULL)
46 return;
1cd14d1e
SL
47 /* Accumulate the percent of cpu per user. */
48 ptptr = pt;
49 numprocs = 0;
50 total = 0.0;
51 for (i = 0; i < nproc; i++) {
52 /* discard inactive processes */
53 if (ptptr->pt_uid == -1) {
54 ptptr++;
55 continue;
56 }
57 /* Accumulate the percentage. */
58 total += ptptr->pt_pctcpu;
59 numprocs++;
60 ptptr++;
61 }
62
63 pt[numprocs].pt_pctcpu = 1.0 - total;
64 pt[numprocs].pt_uid = -1;
65 pt[numprocs].pt_pid = -1;
66 pt[numprocs].pt_pp = NULL;
67
68 if (total < 1.0)
69 total = 1.0;
70 factor = 50.0/total;
71
b5eefd1e
SL
72 /* Find the top few by executing a "bubble pass" ten times. */
73 y = numprocs + 1;
74 if (y > wnd->_maxy-1)
75 y = wnd->_maxy-1;
1cd14d1e
SL
76 for (i = 0; i < y; i++) {
77 ptptr = &pt[i];
78 max = -10000.0;
79 maxind = i;
80 for (j = i; j < numprocs + 1; j++) {
81 if (ptptr->pt_pctcpu > max) {
82 max = ptptr->pt_pctcpu;
83 maxind = j;
84 }
85 ptptr++;
86 }
87 if (maxind != i) {
88 temppt = pt[i];
89 pt[i] = pt[maxind];
90 pt[maxind] = temppt;
91 }
92 }
b5eefd1e 93 y = 1;
1cd14d1e 94 ptptr = pt;
b5eefd1e
SL
95 i = numprocs + 1;
96 if (i > wnd->_maxy-1)
97 i = wnd->_maxy-1;
1cd14d1e
SL
98 for (; i > 0 && ptptr->pt_pctcpu > 0.01; i--) {
99 /* Find the user's name. */
100 knptr = known;
101 auid = ptptr->pt_uid;
102 for (j = numknown - 1; j >= 0; j--) {
103 if (knptr->k_uid == auid) {
104 namp = knptr->k_name;
105 break;
106 }
107 knptr++;
108 }
109 if (j < 0) {
110 if (numknown < 30) {
111 knptr = &known[numknown];
112 namp = strncpy(knptr->k_name,
113 getpwuid(auid)->pw_name, 15);
114 knptr->k_name[15] = '\0';
115 knptr->k_uid = auid;
116 numknown++;
117 } else
118 namp = getpwuid(auid)-> pw_name;
119 }
120 pnamp = getpname(ptptr->pt_pid, ptptr->pt_pp);
121 wmove(wnd, y, 0);
122 wclrtoeol(wnd);
123 mvwaddstr(wnd, y, 0, namp);
83e2d91b
SL
124 sprintf(pidname, "%10.10s", pnamp);
125 mvwaddstr(wnd, y, 9, pidname);
126 wmove(wnd, y++, 20);
1cd14d1e
SL
127 for (j = ptptr->pt_pctcpu*factor + 0.5; j > 0; j--)
128 waddch(wnd, 'X');
129 ptptr++;
130 }
b5eefd1e 131 wmove(wnd, y, 0); wclrtobot(wnd);
1cd14d1e
SL
132}
133
d830bff6 134static struct nlist nlst[] = {
1cd14d1e 135#define X_PROC 0
d830bff6 136 { "_proc" },
1cd14d1e 137#define X_NPROC 1
d830bff6
SL
138 { "_nproc" },
139#define X_USRPTMAP 2
140 { "_Usrptmap" },
141#define X_USRPT 3
142 { "_usrpt" },
143 { "" }
144};
1cd14d1e 145
852c7064 146initpigs()
1cd14d1e 147{
1cd14d1e 148
d830bff6
SL
149 if (nlst[X_PROC].n_type == 0) {
150 nlist("/vmunix", nlst);
151 if (nlst[X_PROC].n_type == 0) {
152 error("namelist on /vmunix failed");
153 return;
154 }
155 }
1cd14d1e
SL
156 if (procp == NULL) {
157 procp = getw(nlst[X_PROC].n_value);
158 nproc = getw(nlst[X_NPROC].n_value);
1cd14d1e 159 }
c6265927
SL
160 if (kprocp == NULL)
161 kprocp = (struct proc *)calloc(nproc, sizeof (struct proc));
852c7064
SL
162 if (usrpt != NULL)
163 return;
164 usrpt = (struct pte *)nlst[X_USRPT].n_value;
165 Usrptma = (struct pte *)nlst[X_USRPTMAP].n_value;
c6265927
SL
166 if (pt == NULL)
167 pt = (struct p_times *)calloc(nproc, sizeof (struct p_times));
852c7064
SL
168}
169
170fetchpigs()
171{
172 register int i;
173 register struct p_times *prt;
174 register float time;
175 register struct proc *pp;
176
d830bff6
SL
177 if (nlst[X_PROC].n_type == 0)
178 return;
c6265927
SL
179 if (kprocp == NULL) {
180 kprocp = (struct proc *)calloc(nproc, sizeof (struct proc));
181 if (kprocp == NULL)
182 return;
183 }
184 if (pt == NULL) {
185 pt = (struct p_times *)calloc(nproc, sizeof (struct p_times));
186 if (pt == NULL)
187 return;
188 }
1cd14d1e
SL
189 prt = pt;
190 lseek(kmem, procp, L_SET);
191 read(kmem, kprocp, sizeof (struct proc) * nproc);
192 for (i = 0, pp = kprocp; i < nproc; i++, pp++) {
193 time = pp->p_time;
194 if (time == 0 || (pp->p_flag & SLOAD) == 0)
195 continue;
196 prt->pt_pid = pp->p_pid;
197 prt->pt_pp = pp;
198 prt->pt_pctcpu = pp->p_pctcpu / (1.0 - exp(time * lccpu));
199 prt->pt_uid = pp->p_uid;
200 prt++;
201 }
202 for (; prt < &pt[nproc]; prt++)
203 prt->pt_uid = -1;
204}
205
206labelpigs()
207{
208
b5eefd1e
SL
209 wmove(wnd, 0, 0); wclrtoeol(wnd);
210 mvwaddstr(wnd, 0, 20,
1cd14d1e
SL
211 "/0 /10 /20 /30 /40 /50 /60 /70 /80 /90 /100");
212}