Commit | Line | Data |
---|---|---|
1ee1e8e9 BJ |
1 | /* |
2 | * ps - process status | |
3 | * This is the augmented UCB ps for UCB/VM Unix (9/79) | |
4 | * examine and print certain things about processes | |
5 | * usage: ps [acgklrt#uvwx] [corefile] [swapfile] [system] | |
6 | */ | |
7 | ||
8 | #include <stdio.h> | |
9 | #include <a.out.h> | |
10 | #include <pwd.h> | |
11 | #include <sys/param.h> | |
12 | #include <sys/proc.h> | |
13 | #include <sys/tty.h> | |
14 | #include <sys/dir.h> | |
15 | #include <sys/user.h> | |
16 | #include <sys/pte.h> | |
17 | #include <sys/vm.h> | |
18 | #include <sys/text.h> | |
19 | #include <psout.h> | |
20 | ||
21 | struct nlist nl[] = { | |
22 | { "_proc" }, | |
23 | #define X_PROC 0 | |
24 | { "_swapdev" }, | |
25 | #define X_SWAPDEV 1 | |
26 | { "_swplo" }, | |
27 | #define X_SWPLO 2 | |
28 | { "_Usrptma" }, | |
29 | #define X_USRPTMA 3 | |
30 | { "_usrpt" }, | |
31 | #define X_USRPT 4 | |
32 | { "_text" }, | |
33 | #define X_TEXT 5 | |
34 | { "_nswap" }, | |
35 | #define X_NSWAP 6 | |
36 | { 0 }, | |
37 | }; | |
38 | ||
39 | struct proc mproc; | |
40 | struct text text[NTEXT]; | |
41 | ||
42 | #define INTPPG (NBPG/sizeof(int)) /* ints per page */ | |
43 | union { | |
44 | struct user yy; | |
45 | int xx[INTPPG][UPAGES]; | |
46 | } zz; | |
47 | #define clear(x) ((int)x & 0x7fffffff) | |
48 | #define u zz.yy | |
49 | int chkpid = 0; | |
50 | int aflg; /* -a: all processes, not just mine */ | |
51 | int cflg; /* -c: complete listing of args, not just comm. */ | |
52 | int gflg; /* -g: complete listing including group headers, etc */ | |
53 | int kflg; /* -k: read from core file instead of real memory */ | |
54 | int lflg; /* -l: long listing form */ | |
55 | int rflg; /* -r: raw output in style <psout.h> */ | |
56 | int sflg; /* -s: stack depth */ | |
57 | int uflg; /* -u: user name */ | |
58 | int vflg; /* -v: virtual memory statistics */ | |
59 | int wflg; /* -w[w]: wide terminal */ | |
60 | int xflg; /* -x: ALL processes, even those without ttys */ | |
61 | int login; /* -: this is a login shell */ | |
62 | char *tptr; | |
63 | char *gettty(); | |
64 | int pscomp(); | |
65 | struct pte pagetbl[NPTEPG]; | |
66 | int kmem; | |
67 | int mem; | |
68 | int swap; | |
69 | daddr_t swplo; | |
70 | int nswap; | |
71 | int Usrptma; | |
72 | int usrpt; | |
73 | ||
74 | int ndev; | |
75 | struct devl { | |
76 | char dname[DIRSIZ]; | |
77 | dev_t dev; | |
78 | } devl[256]; | |
79 | ||
80 | struct psout outargs[NPROC]; /* info for first npr processes */ | |
81 | int npr; /* number of processes found so far */ | |
82 | int argwidth; /* number of chars of args to print */ | |
83 | ||
84 | char *coref; | |
85 | ||
86 | main(argc, argv) | |
87 | char **argv; | |
88 | { | |
89 | int i; | |
90 | char *ap; | |
91 | int uid, puid; | |
92 | char obuf[BUFSIZ]; | |
93 | register struct nlist *nlp; | |
94 | ||
95 | setbuf(stdout, obuf); | |
96 | argc--, argv++; | |
97 | if (argc>0) { | |
98 | ap = argv[0]; | |
99 | while (*ap) switch (*ap++) { | |
100 | case '-': | |
101 | break; | |
102 | ||
103 | case 'a': | |
104 | aflg++; | |
105 | break; | |
106 | ||
107 | case 'c': | |
108 | cflg++; | |
109 | break; | |
110 | ||
111 | case 'g': | |
112 | gflg++; | |
113 | break; | |
114 | ||
115 | case 'k': | |
116 | kflg++; | |
117 | break; | |
118 | ||
119 | case 'l': | |
120 | lflg++; | |
121 | break; | |
122 | ||
123 | case 'r': | |
124 | rflg++; | |
125 | break; | |
126 | ||
127 | case 's': | |
128 | sflg++; | |
129 | break; | |
130 | ||
131 | case 't': | |
132 | if(*ap) | |
133 | tptr = ap; | |
134 | aflg++; | |
135 | gflg++; | |
136 | if (*tptr == '?') | |
137 | xflg++; | |
138 | while (*ap) | |
139 | ap++; | |
140 | break; | |
141 | ||
142 | case 'u': | |
143 | uflg++; | |
144 | break; | |
145 | ||
146 | case 'v': | |
147 | vflg++; | |
148 | break; | |
149 | ||
150 | case 'w': | |
151 | wflg++; | |
152 | break; | |
153 | ||
154 | case 'x': | |
155 | xflg++; | |
156 | break; | |
157 | ||
158 | default: | |
159 | chkpid=atoi(--ap); | |
160 | *ap = '\0'; | |
161 | aflg++; | |
162 | xflg++; | |
163 | break; | |
164 | } | |
165 | } | |
166 | coref = "/dev/kmem"; | |
167 | if(kflg) | |
168 | coref = argc > 1 ? argv[1] : "/vmcore"; | |
169 | ||
170 | if ((kmem = open(coref, 0)) < 0) { | |
171 | perror(coref); | |
172 | done(1); | |
173 | } | |
174 | if ((mem = open("/dev/mem", 0)) < 0) { | |
175 | fprintf(stderr, "No mem\n"); | |
176 | done(1); | |
177 | } | |
178 | if (kflg) | |
179 | mem = kmem; | |
180 | ||
181 | if ((swap = open(argc>2 ? argv[2]: "/dev/drum", 0)) < 0) { | |
182 | fprintf(stderr, "Can't open /dev/drum\n"); | |
183 | done(1); | |
184 | } | |
185 | ||
186 | nlist(argc>3 ? argv[3] : "/vmunix", nl); | |
187 | if (nl[0].n_type==0) { | |
188 | fprintf(stderr, "No namelist\n"); | |
189 | done(1); | |
190 | } | |
191 | ||
192 | if(chdir("/dev") < 0) { | |
193 | fprintf(stderr, "Can't change to /dev\n"); | |
194 | done(1); | |
195 | } | |
196 | if (kflg) | |
197 | for (nlp= nl; nlp < &nl[sizeof (nl)/sizeof (nl[0])]; nlp++) | |
198 | nlp->n_value &= 0x7ffffffff; | |
199 | Usrptma = nl[X_USRPTMA].n_value; | |
200 | usrpt = nl[X_USRPT].n_value; | |
201 | /* | |
202 | * read kmem to find swap dev. | |
203 | */ | |
204 | lseek(kmem, (long)nl[X_SWAPDEV].n_value, 0); | |
205 | read(kmem, &nl[X_SWAPDEV].n_value, sizeof(nl[X_SWAPDEV].n_value)); | |
206 | /* | |
207 | * Find base and size of swap | |
208 | */ | |
209 | lseek(kmem, (long)nl[X_SWPLO].n_value, 0); | |
210 | read(kmem, &swplo, sizeof(swplo)); | |
211 | lseek(kmem, (long)nl[X_NSWAP].n_value, 0); | |
212 | read(kmem, &nswap, sizeof (nswap)); | |
213 | /* | |
214 | * If v flag get text table | |
215 | */ | |
216 | if (vflg) { | |
217 | lseek(kmem, (long)nl[X_TEXT].n_value, 0); | |
218 | read(kmem, text, sizeof (text)); | |
219 | } | |
220 | if (kflg) | |
221 | swplo = 0; | |
222 | getdev(); | |
223 | uid = getuid(); | |
224 | if (sflg + lflg + vflg + uflg > 1) { | |
225 | printf("Cannot combine s, l, v, and/or u.\n"); | |
226 | exit(1); | |
227 | } | |
228 | /* different psout widths depending on how much printed & w flag */ | |
229 | if (wflg <= 1) { | |
230 | argwidth = 63; | |
231 | if (wflg) argwidth += 52; /* 132 col term */ | |
232 | if (lflg) argwidth -= 49; /* extra junk printed */ | |
233 | if (vflg) argwidth -= 48; /* extra junk for -v */ | |
234 | if (sflg) argwidth -= 4; /* 4 cols of stack size */ | |
235 | if (uflg) argwidth -= 27; /* user name */ | |
236 | } else argwidth = 127; | |
237 | if (rflg) | |
238 | ; /* No heading for raw output */ | |
239 | else if (lflg) | |
240 | printf(" F S UID PID PPID CPU PRI NICE ADDR SZ RSS WCHAN TTY TIME COMMAND\n"); | |
241 | else if (vflg) | |
242 | printf("F PID TT TIME TIM SL MINFLT MAJFLT SIZE RSS SRS TSIZ TRS PF COMMAND\n"); | |
243 | else if (uflg) | |
244 | printf("USER PID %%CPU NICE SZ RSS TTY TIME COMMAND\n"); | |
245 | else if (chkpid==0) { | |
246 | if (sflg) | |
247 | printf(" SSIZ"); | |
248 | printf(" PID TTY TIME COMMAND\n"); | |
249 | } | |
250 | fflush(stdout); | |
251 | for (i=0; i<NPROC; i++) { | |
252 | lseek(kmem, (long)(nl[X_PROC].n_value+i*(sizeof mproc)), 0); | |
253 | read(kmem, &mproc, sizeof mproc); | |
254 | /* skip processes that don't exist */ | |
255 | if (mproc.p_stat==0) | |
256 | continue; | |
257 | /* skip those without a tty unless -x */ | |
258 | if (mproc.p_pgrp==0 && xflg==0) | |
259 | continue; | |
260 | /* skip group leaders on a tty unless -g, -x, or -t.. */ | |
261 | if (!gflg && !xflg && !tptr && mproc.p_pid == mproc.p_pgrp) | |
262 | continue; | |
263 | /* -g also skips those where **argv is "-" - see savcom */ | |
264 | puid = mproc.p_uid; | |
265 | /* skip other peoples processes unless -a or a specific pid */ | |
266 | if ((uid != puid && aflg==0) || | |
267 | (chkpid!=0 && chkpid!=mproc.p_pid)) | |
268 | continue; | |
269 | if (savcom(puid)) | |
270 | npr++; | |
271 | } | |
272 | fixup(npr); | |
273 | for (i=0; i<npr; i++) | |
274 | if (prcom(&outargs[i])) { | |
275 | putchar('\n'); | |
276 | fflush(stdout); | |
277 | } | |
278 | done(!npr); | |
279 | } | |
280 | ||
281 | getdev() | |
282 | { | |
283 | #include <sys/stat.h> | |
284 | register FILE *df; | |
285 | struct stat sbuf; | |
286 | struct direct dbuf; | |
287 | ||
288 | if ((df = fopen("/dev", "r")) == NULL) { | |
289 | fprintf(stderr, "Can't open /dev\n"); | |
290 | done(1); | |
291 | } | |
292 | ndev = 0; | |
293 | while (fread(&dbuf, sizeof(dbuf), 1, df) == 1) { | |
294 | if(dbuf.d_ino == 0) | |
295 | continue; | |
296 | if(stat(dbuf.d_name, &sbuf) < 0) | |
297 | continue; | |
298 | if ((sbuf.st_mode&S_IFMT) != S_IFCHR) | |
299 | continue; | |
300 | strcpy(devl[ndev].dname, dbuf.d_name); | |
301 | devl[ndev].dev = sbuf.st_rdev; | |
302 | ndev++; | |
303 | } | |
304 | fclose(df); | |
305 | } | |
306 | ||
307 | savcom(puid) | |
308 | { | |
309 | int abuf[INTPPG]; | |
310 | long addr; | |
311 | register int *ip; | |
312 | register struct psout *a; | |
313 | register char *cp, *cp1; | |
314 | long tm; | |
315 | int cc, nbad; | |
316 | int szpt, p0br; | |
317 | register char *tp; | |
318 | struct dblock db; | |
319 | struct pte apte; | |
320 | ||
321 | /* skip long sleeping or dead processes if -v unless -g or -x */ | |
322 | if (!gflg && vflg && !xflg) { | |
323 | switch (mproc.p_stat) { | |
324 | ||
325 | case SSLEEP: | |
326 | case SSTOP: | |
327 | if (mproc.p_slptime > MAXSLP) | |
328 | return (0); | |
329 | break; | |
330 | ||
331 | case SRUN: | |
332 | case SIDL: | |
333 | break; | |
334 | ||
335 | case SZOMB: | |
336 | return (0); | |
337 | } | |
338 | } | |
339 | /* read in the user structure */ | |
340 | if ((mproc.p_flag& SLOAD ) == 0) { | |
341 | /* not loaded - get from swap */ | |
342 | addr = (mproc.p_swaddr+swplo)<<9; | |
343 | lseek(swap, addr, 0); | |
344 | if (read(swap, &u, sizeof(u)) != sizeof(u)) | |
345 | return(0); | |
346 | } else { | |
347 | /* loaded, get each page from memory separately */ | |
348 | for(cc=0; cc<UPAGES; cc++) { /* get u area */ | |
349 | int upage = ctob(mproc.p_addr[cc]); | |
350 | lseek(mem,upage,0); | |
351 | if (read(mem,((int *)&u)+INTPPG*cc,NBPG) != NBPG) | |
352 | return(0); | |
353 | } | |
354 | } | |
355 | tp = gettty(); | |
356 | if (tptr && strcmpn(tptr, tp, 2)) | |
357 | return(0); | |
358 | a = &outargs[npr]; | |
359 | /* saving com starts here */ | |
360 | a->o_uid = puid; | |
361 | a->o_pid = mproc.p_pid; | |
362 | a->o_flag = mproc.p_flag; | |
363 | a->o_ppid = mproc.p_ppid; | |
364 | a->o_cpu = mproc.p_cpu; | |
365 | a->o_pctcpu = 0.0; /* This needs to be fixed later */ | |
366 | a->o_pri = mproc.p_pri; | |
367 | a->o_nice = mproc.p_nice; | |
368 | a->o_addr0 = mproc.p_addr[0]; | |
369 | a->o_dsize = mproc.p_dsize; | |
370 | a->o_ssize = mproc.p_ssize; | |
371 | a->o_rssize = mproc.p_rssize; | |
372 | a->o_swrss = mproc.p_swrss; | |
373 | a->o_wchan = mproc.p_wchan; | |
374 | a->o_pgrp = mproc.p_pgrp; | |
375 | a->o_tty[0] = tp[0]; | |
376 | a->o_tty[1] = tp[1] ? tp[1] : ' '; | |
377 | a->o_ttyd = u.u_ttyd; | |
378 | a->o_stat = mproc.p_stat; | |
379 | a->o_flag = mproc.p_flag; | |
380 | if (a->o_stat==SZOMB) return(1); | |
381 | a->o_utime = u.u_utime; | |
382 | a->o_stime = u.u_stime; | |
383 | a->o_cutime = u.u_cutime; | |
384 | a->o_cstime = u.u_cstime; | |
385 | a->o_sigs = u.u_signal[SIGINT] + u.u_signal[SIGQUIT]; | |
386 | a->o_time = mproc.p_time; | |
387 | a->o_slptime = mproc.p_slptime; | |
388 | a->o_uname[0] = 0; | |
389 | if (sflg) { | |
390 | for (cp = (char *)u.u_stack; cp < (char *)&u + ctob(UPAGES); cp++) | |
391 | if (*cp) | |
392 | break; | |
393 | a->o_stksize = (int) ((char *)&u + ctob(UPAGES) - cp); | |
394 | } | |
395 | if (mproc.p_stat==SZOMB) return(1); | |
396 | if (vflg) { | |
397 | register struct text *xp; | |
398 | ||
399 | if (mproc.p_textp) { | |
400 | xp = &text[mproc.p_textp - (struct text *)nl[5].n_value]; | |
401 | a->o_xsize = xp->x_size; | |
402 | a->o_xrssize = xp->x_rssize; | |
403 | } else { | |
404 | a->o_xsize = 0; | |
405 | a->o_xrssize = 0; | |
406 | } | |
407 | a->o_aveflt = mproc.p_aveflt; | |
408 | a->o_minorflt = u.u_minorflt; | |
409 | a->o_majorflt = u.u_majorflt; | |
410 | } | |
411 | strcpy(a->o_comm, u.u_comm); | |
412 | if (cflg) | |
413 | return (1); | |
414 | a->o_args[0] = 0; /* in case of early return */ | |
415 | if ((mproc.p_flag & SLOAD) == 0) { | |
416 | vstodb(0, 1, &u.u_smap, &db, 1); | |
417 | addr = ctob(swplo + db.db_base); | |
418 | lseek(swap, addr, 0); | |
419 | if (read(swap, abuf, sizeof(abuf)) != sizeof(abuf)) | |
420 | goto garbage; | |
421 | } else { | |
422 | szpt = u.u_pcb.pcb_szpt; | |
423 | p0br = kflg ? clear((int)mproc.p_p0br) : (int)mproc.p_p0br; | |
424 | cc = Usrptma + (p0br + NBPG*(szpt-1) - usrpt)/NPTEPG; | |
425 | lseek(kmem, cc, 0); | |
426 | if (read(kmem, &apte, sizeof(apte)) != sizeof(apte)) | |
427 | goto garbage; | |
428 | lseek(mem, ctob(apte.pg_pfnum), 0); | |
429 | if (read(mem,pagetbl,sizeof(pagetbl)) != sizeof(pagetbl)) | |
430 | goto garbage; | |
431 | if (pagetbl[NPTEPG-1].pg_fod == 0 && pagetbl[NPTEPG-1].pg_pfnum) { | |
432 | lseek(mem,ctob((pagetbl[NPTEPG-1].pg_pfnum)),0); | |
433 | if (read(mem,abuf,sizeof(abuf)) != sizeof(abuf)) | |
434 | goto garbage; | |
435 | } else { | |
436 | vstodb(0, 1, &u.u_smap, &db, 1); | |
437 | addr = ctob(swplo + db.db_base); | |
438 | lseek(swap, addr, 0); | |
439 | if (read(swap, abuf, sizeof(abuf)) != sizeof(abuf)) | |
440 | goto garbage; | |
441 | } | |
442 | } | |
443 | abuf[INTPPG] = 0; | |
444 | for (ip = &abuf[INTPPG-2]; ip > abuf;) { | |
445 | if (*--ip == -1 || *ip == 0) { | |
446 | cp = (char *)(ip+1); | |
447 | if (*cp==0) | |
448 | cp++; | |
449 | nbad = 0; | |
450 | for (cp1 = cp; cp1 < (char *)&abuf[INTPPG]; cp1++) { | |
451 | cc = *cp1&0177; | |
452 | if (cc==0) | |
453 | *cp1 = ' '; | |
454 | else if (cc < ' ' || cc > 0176) { | |
455 | if (++nbad >= 5) { | |
456 | *cp1++ = ' '; | |
457 | break; | |
458 | } | |
459 | *cp1 = '?'; | |
460 | } else if (cc=='=') { | |
461 | *cp1 = 0; | |
462 | while (cp1>cp && *--cp1!=' ') | |
463 | *cp1 = 0; | |
464 | break; | |
465 | } | |
466 | } | |
467 | while (*--cp1==' ') | |
468 | *cp1 = 0; | |
469 | strcpy(a->o_args, cp); | |
470 | garbage: | |
471 | cp = a->o_args; | |
472 | if (cp[0]=='-'&&cp[1]<=' ' || cp[0]=='?' || cp[0]<=' ') { | |
473 | strcat(cp, " ("); | |
474 | strcat(cp, u.u_comm); | |
475 | strcat(cp, ")"); | |
476 | } | |
477 | cp[127] = 0; /* max room in psout is 128 chars */ | |
478 | if (xflg || gflg || tptr || cp[0]!='-') | |
479 | return(1); | |
480 | return(0); | |
481 | } | |
482 | } | |
483 | goto garbage; | |
484 | } | |
485 | ||
486 | prcom(a) | |
487 | register struct psout *a; | |
488 | { | |
489 | long tm; | |
490 | ||
491 | if (rflg) { | |
492 | write(1, a, sizeof (*a)); | |
493 | return(0); | |
494 | } | |
495 | if (lflg) { | |
496 | printf("%4x %c", 0xffff & a->o_flag, | |
497 | "0SWRIZT"[a->o_stat]); | |
498 | printf("%4d", a->o_uid); | |
499 | } else if (vflg) { | |
500 | switch (a->o_stat) { | |
501 | ||
502 | case SSLEEP: | |
503 | case SSTOP: | |
504 | if ((a->o_flag & SLOAD) == 0) | |
505 | printf("W"); | |
506 | else if (a->o_pri >= PZERO) | |
507 | printf("S"); | |
508 | else if (a->o_flag & SPAGE) | |
509 | printf("P"); | |
510 | else | |
511 | printf("D"); | |
512 | break; | |
513 | ||
514 | case SRUN: | |
515 | case SIDL: | |
516 | if (a->o_flag & SLOAD) | |
517 | printf("R"); | |
518 | else | |
519 | printf("W"); | |
520 | break; | |
521 | } | |
522 | if (a->o_nice > NZERO) | |
523 | printf("N"); | |
524 | else | |
525 | printf(" "); | |
526 | } else if (uflg) { | |
527 | printf("%-8.8s", a->o_uname); | |
528 | } | |
529 | if (sflg) { | |
530 | printf("%5d", a->o_stksize); | |
531 | } | |
532 | printf("%6u", a->o_pid); | |
533 | if (lflg) | |
534 | printf("%6u%4d%4d%4d%6x", a->o_ppid, a->o_cpu&0377, | |
535 | a->o_pri, a->o_nice, a->o_addr0); | |
536 | else if (uflg) | |
537 | printf("%5.1f%4d ", a->o_pctcpu, a->o_nice); | |
538 | if (lflg || uflg) | |
539 | printf("%4d%5d", a->o_dsize+a->o_ssize, a->o_rssize); | |
540 | if (lflg) | |
541 | if (a->o_wchan) | |
542 | printf("%6x", clear(a->o_wchan)); | |
543 | else | |
544 | printf(" "); | |
545 | printf(" %-2.2s", a->o_tty); | |
546 | if (a->o_stat==SZOMB) { | |
547 | printf(" <defunct>"); | |
548 | return(1); | |
549 | } | |
550 | tm = (a->o_utime + a->o_stime + 30)/60; | |
551 | printf("%3ld:", tm/60); | |
552 | tm %= 60; | |
553 | printf(tm<10?"0%ld":"%ld", tm); | |
554 | if (vflg) { | |
555 | /* | |
556 | tm = (a->o_stime + 30) / 60; | |
557 | printf(" %2ld:", tm/60); | |
558 | tm %= 60; | |
559 | printf(tm<10?"0%ld":"%ld", tm); | |
560 | */ | |
561 | printf("%4d%3d", a->o_time, a->o_slptime); | |
562 | } | |
563 | #ifdef notdef | |
564 | if (0 && lflg==0) { /* 0 == old tflg (print long times) */ | |
565 | tm = (a->o_cstime + 30)/60; | |
566 | printf(" %2ld:", tm/60); | |
567 | tm %= 60; | |
568 | printf(tm<10?"0%ld":"%ld", tm); | |
569 | tm = (a->o_cutime + 30)/60; | |
570 | printf(" %2ld:", tm/60); | |
571 | tm %= 60; | |
572 | printf(tm<10?"0%ld":"%ld", tm); | |
573 | } | |
574 | #endif | |
575 | if (vflg) { | |
576 | printf("%7d%7d",a->o_minorflt,a->o_majorflt); | |
577 | printf("%5d%4d%4d", a->o_dsize+a->o_ssize, a->o_rssize, a->o_swrss); | |
578 | printf("%5d%4d", a->o_xsize, a->o_xrssize); | |
579 | printf("%3d", a->o_aveflt); | |
580 | } | |
581 | if (a->o_pid == 0) { | |
582 | printf(" swapper"); | |
583 | return(1); | |
584 | } | |
585 | if (a->o_pid == 2) { | |
586 | printf(" pagedaemon"); | |
587 | return(1); | |
588 | } | |
589 | if (cflg) { | |
590 | printf(" %s", a->o_comm); | |
591 | return(1); | |
592 | } | |
593 | a -> o_args[argwidth] = 0; /* force it to quit early */ | |
594 | printf(" %s", a->o_args); | |
595 | return (1); | |
596 | } | |
597 | ||
598 | char * | |
599 | gettty() | |
600 | { | |
601 | register i; | |
602 | register char *p; | |
603 | ||
604 | if (u.u_ttyp==0) | |
605 | return("?"); | |
606 | for (i=0; i<ndev; i++) { | |
607 | if (devl[i].dev == u.u_ttyd) { | |
608 | p = devl[i].dname; | |
609 | if (p[0]=='t' && p[1]=='t' && p[2]=='y') | |
610 | p += 3; | |
611 | return(p); | |
612 | } | |
613 | } | |
614 | return("?"); | |
615 | } | |
616 | ||
617 | /* | |
618 | * Given a base/size pair in virtual swap area, | |
619 | * return a physical base/size pair which is the | |
620 | * (largest) initial, physically contiguous block. | |
621 | */ | |
622 | vstodb(vsbase, vssize, dmp, dbp, rev) | |
623 | register int vsbase; | |
624 | int vssize; | |
625 | struct dmap *dmp; | |
626 | register struct dblock *dbp; | |
627 | { | |
628 | register int blk = DMMIN; | |
629 | register swblk_t *ip = dmp->dm_map; | |
630 | ||
631 | if (vsbase < 0 || vsbase + vssize > dmp->dm_size) | |
632 | panic("vstodb"); | |
633 | while (vsbase >= blk) { | |
634 | vsbase -= blk; | |
635 | if (blk < DMMAX) | |
636 | blk *= 2; | |
637 | ip++; | |
638 | } | |
639 | if (*ip <= 0 || *ip + blk > nswap) | |
640 | panic("vstodb *ip"); | |
641 | dbp->db_size = min(vssize, blk - vsbase); | |
642 | dbp->db_base = *ip + (rev ? blk - (vsbase + dbp->db_size) : vsbase); | |
643 | } | |
644 | ||
645 | panic(cp) | |
646 | char *cp; | |
647 | { | |
648 | ||
649 | #ifdef DEBUG | |
650 | printf("%s\n", cp); | |
651 | #endif | |
652 | } | |
653 | ||
654 | min(a, b) | |
655 | { | |
656 | ||
657 | return (a < b ? a : b); | |
658 | } | |
659 | ||
660 | done(exitno) | |
661 | { | |
662 | if (login) { | |
663 | printf("Press return when done: "); | |
664 | getchar(); | |
665 | } | |
666 | exit(exitno); | |
667 | } | |
668 | ||
669 | /* | |
670 | * fixup figures out everybodys name and sorts into a nice order. | |
671 | */ | |
672 | fixup(np) int np; { | |
673 | register int i; | |
674 | register struct passwd *pw; | |
675 | struct passwd *getpwent(); | |
676 | ||
677 | if (uflg) { | |
678 | /* | |
679 | * If we want names, traverse the password file. For each | |
680 | * passwd entry, look for it in the processes. | |
681 | * In case of multiple entries in /etc/passwd, we believe | |
682 | * the first one (same thing ls does). | |
683 | */ | |
684 | while ((pw=getpwent()) != NULL) { | |
685 | for (i=0; i<np; i++) | |
686 | if (outargs[i].o_uid == pw -> pw_uid) { | |
687 | if (outargs[i].o_uname[0] == 0) | |
688 | strcpy(outargs[i].o_uname, pw -> pw_name); | |
689 | } | |
690 | } | |
691 | } | |
692 | ||
693 | qsort(outargs, np, sizeof(outargs[0]), pscomp); | |
694 | } | |
695 | ||
696 | pscomp(x1, x2) struct psout *x1, *x2; { | |
697 | register int c; | |
698 | ||
699 | c = (x1)->o_ttyd - (x2)->o_ttyd; | |
700 | if (c==0) c = (x1)->o_pid - (x2)->o_pid; | |
701 | return(c); | |
702 | } |