home *** CD-ROM | disk | FTP | other *** search
/ Usenet 1993 July / InfoMagic USENET CD-ROM July 1993.ISO / sources / unix / volume6 / bsd.ps.patch < prev    next >
Encoding:
Internet Message Format  |  1986-11-30  |  8.7 KB

  1. Subject: v06i083:  Speed, etc., patches for BSD ps (bsd.ps.patch)
  2. Newsgroups: mod.sources
  3. Approved: rs@mirror.UUCP
  4.  
  5. Submitted by: "Michael A. Callahan" <cca!uokvax!mikec>
  6. Mod.sources: Volume 6, Issue 83
  7. Archive-name: bsd.ps.patch
  8.  
  9. [  I ran this on a 4.2BSD 750, and it worked.  I took Mike's initial
  10.    comments, formatted them into the manpage, and published the diff
  11.    as part of the sharefile.  I also threw together the Makefile.
  12.    The technique of storing data that changes infrequently in a file in
  13.    order to speed up ps is probably a good one for any Un*x system,
  14.    and is in fact done in other versions of ps I've seen.  Sorry the
  15.    diffs aren't context; Mike's weren't, and I opted for consistency.
  16.    --r$  ]
  17.  
  18. The diff's that follow are speedup modifications for ps.c.  These mods
  19. cut the system time of ps by more than half, and trim back the user
  20. time a bit also.  The main difference is that the ttys in /dev are not
  21. stat'ed each time ps runs.  Instead a file is created in /etc when the
  22. machine boots via /etc/rc, and that file is used instead.  Also in this
  23. file is kept a name list of /vmunix.
  24.  
  25.                 Mike Callahan
  26.                 University of Oklahoma
  27.                 ihnp4!okstate!uokvax!mikec
  28.                 cbosgd!okstate!uokvax!mikec
  29.  
  30. #!/bin/sh
  31. # This is a shell archive.  Remove anything before this line,
  32. # then unpack it by saving it in a file and typing "sh file".
  33. # Wrapped by rs@mirror.UUCP on Fri Jul 25 19:38:44 EDT 1986
  34. # Contents:  Makefile ps.1.patch ps.c.patch
  35.  
  36. echo x - Makefile
  37. sed 's/^XX//' > "Makefile" <<'@//E*O*F Makefile//'
  38. XXCFLAGS=-O -DECN
  39. XXps:    ps.c
  40. XX    cc $(CFLAGS) -o ps ps.c -lm
  41. @//E*O*F Makefile//
  42. chmod u=rw,g=rw,o=rw Makefile
  43.  
  44. echo x - ps.1.patch
  45. sed 's/^XX//' > "ps.1.patch" <<'@//E*O*F ps.1.patch//'
  46. XX135,163d134
  47. XX< .TP 5
  48. XX< .B U
  49. XX< This flag instructs
  50. XX< .I ps
  51. XX< recreate its data files; all the files in
  52. XX< .I /etc/ttys
  53. XX< are stat'd, and the data is recorded in
  54. XX< .IR /etc/psdatabase ;
  55. XX< the namelist of
  56. XX< .I /vmunix
  57. XX< is stored in
  58. XX< .IR /etc/psdatabase .
  59. XX< This information changes only when the ttys are changed, or when a new
  60. XX< kernel is booted.
  61. XX< It is a good idea to put ``/bin/ps -U'' in
  62. XX< .IR /etc/rc.local .
  63. XX< .TP 5
  64. XX< .BI L login
  65. XX< This flag will do a ``ps x'' as the login name specified; i.e., is as
  66. XX< if the user with the indicated login name had run the command.
  67. XX< .TP 5
  68. XX< .B R
  69. XX< This will show the running processes in the system; it is faster than
  70. XX< .IR top (1L).
  71. XX< .TP 5
  72. XX< .BI N #
  73. XX< This flag will show all processes with a nice value greater than
  74. XX< or equal to #; e.g., ``ps lN4'' shows all the automatically-niced
  75. XX< processes.
  76. @//E*O*F ps.1.patch//
  77. chmod u=rw,g=rw,o=rw ps.1.patch
  78.  
  79. echo x - ps.c.patch
  80. sed 's/^XX//' > "ps.c.patch" <<'@//E*O*F ps.c.patch//'
  81. XX% diff ps.c.old ps.c
  82. XX21a22,24
  83. XX> #ifdef ECN
  84. XX> #include <sys/file.h>
  85. XX> #endif
  86. XX23a27
  87. XX> #ifdef ECN /* share nlist with w so keep fields same */
  88. XX48a53,58
  89. XX>     { "_swapdev" },
  90. XX> #define    X_SWAPDEV    12
  91. XX>     { "_avenrun" },
  92. XX> #define    X_AVENRUN    13
  93. XX>     { "_boottime" },
  94. XX> #define    X_BOOTTIME    14
  95. XX50a61,89
  96. XX> #else
  97. XX> struct nlist nl[] = {
  98. XX>     { "_proc" },
  99. XX> #define    X_PROC        0
  100. XX>     { "_Usrptmap" },
  101. XX> #define    X_USRPTMA    1
  102. XX>     { "_usrpt" },
  103. XX> #define    X_USRPT        2
  104. XX>     { "_text" },
  105. XX> #define    X_TEXT        3
  106. XX>     { "_nswap" },
  107. XX> #define    X_NSWAP        4
  108. XX>     { "_maxslp" },
  109. XX> #define    X_MAXSLP    5
  110. XX>     { "_ccpu" },
  111. XX> #define    X_CCPU        6
  112. XX>     { "_ecmx" },
  113. XX> #define    X_ECMX        7
  114. XX>     { "_nproc" },
  115. XX> #define    X_NPROC        8
  116. XX>     { "_ntext" },
  117. XX> #define    X_NTEXT        9
  118. XX>     { "_dmmin" },
  119. XX> #define    X_DMMIN        10
  120. XX>     { "_dmmax" },
  121. XX> #define    X_DMMAX        11
  122. XX>     { "" },
  123. XX> };
  124. XX> #endif
  125. XX91a131,133
  126. XX> #ifdef ECN
  127. XX> struct    proc proc[400];        /* 400 = a few, for less syscalls */
  128. XX> #else
  129. XX92a135
  130. XX> #endif
  131. XX106a150,153
  132. XX> #ifdef ECN
  133. XX> int    Rflg, Nflg, nvalue, Uflg;
  134. XX> char    *mylogin, *lptr;
  135. XX> #endif
  136. XX139a187,189
  137. XX> #ifdef ECN
  138. XX> char bigoutbuf[BUFSIZ];
  139. XX> #endif ECN
  140. XX150a201,203
  141. XX> #ifdef ECN
  142. XX>     setbuffer(stdout, bigoutbuf, BUFSIZ);
  143. XX> #endif ECN
  144. XX198a252,280
  145. XX> #ifdef ECN
  146. XX>         case 'R':
  147. XX>             Rflg++;
  148. XX>             xflg++;
  149. XX>             gflg++;
  150. XX>             aflg++;
  151. XX>             break;
  152. XX>         case 'L':
  153. XX>             if (*ap)
  154. XX>                 lptr = ap;
  155. XX>             xflg++;
  156. XX>             gflg++;
  157. XX>             while (*ap)
  158. XX>                 ap++;
  159. XX>             break;
  160. XX>         case 'N':
  161. XX>             if (*ap)
  162. XX>                 nvalue = atoi(ap) + 20;
  163. XX>             aflg++;
  164. XX>             gflg++;
  165. XX>             xflg++;
  166. XX>             Nflg++;
  167. XX>             while (*ap)
  168. XX>                 ap++;
  169. XX>             break;
  170. XX>         case 'U':
  171. XX>             Uflg++;
  172. XX>             break;
  173. XX> #endif
  174. XX231a314,325
  175. XX> #ifdef ECN
  176. XX>     if (lptr) {
  177. XX>         struct passwd *pw, *getpwnam();
  178. XX>         if ((pw = getpwnam(lptr)) == NULL) {
  179. XX>             fprintf(stderr, "Unknown user: %s\n", lptr);
  180. XX>             exit(1);
  181. XX>         } else {
  182. XX>             uid = pw->pw_uid;
  183. XX>         }
  184. XX>     } else
  185. XX>         uid = getuid();
  186. XX> #else
  187. XX232a327
  188. XX> #endif ECN
  189. XX236a332,334
  190. XX> #ifdef ECN
  191. XX>     for (i=0; i<nproc; i += 400) {
  192. XX> #else
  193. XX237a336
  194. XX> #endif
  195. XX240,241c339,345
  196. XX<         if (j > 8)
  197. XX<             j = 8;
  198. XX---
  199. XX> #ifdef ECN
  200. XX>         if (j > 400)
  201. XX>             j = 400;
  202. XX> #else
  203. XX>         if (j > 400)
  204. XX>             j = 400;
  205. XX> #endif
  206. XX252a357,367
  207. XX>             if (Rflg) {
  208. XX>                 if (mproc->p_stat == SRUN)
  209. XX>                     save();
  210. XX>                 continue;
  211. XX>             }
  212. XX>             if (Nflg) {
  213. XX>                 if ((int)mproc->p_nice >= nvalue) {
  214. XX>                     save();
  215. XX>                 }
  216. XX>                 continue;
  217. XX>             }
  218. XX358a474,490
  219. XX> #ifdef ECN
  220. XX>     register int fd;
  221. XX>     if (Uflg)
  222. XX>         return;
  223. XX>     else {
  224. XX>         if (argc > 1)
  225. XX>             nlist(argv[1],nl);
  226. XX>         else {
  227. XX>             if ((fd = open("/etc/psnlist", O_RDONLY)) < 0)
  228. XX>                 nlist("/vmunix", nl);
  229. XX>             else {
  230. XX>                 read(fd, nl, sizeof(nl));
  231. XX>                 close(fd);
  232. XX>             }
  233. XX>         }
  234. XX>     }
  235. XX> #else
  236. XX360a493
  237. XX> #endif ECN
  238. XX436a570,575
  239. XX> #ifdef ECN
  240. XX> #define MAXTTYS 150
  241. XX> struct ttys *hash_ttys[256]; /* 256 used to find minor */
  242. XX> struct ttys saved_tty_stat[MAXTTYS]; /* fixed sized used to quickly read in */
  243. XX> int next_stty = 0;
  244. XX> 
  245. XX438a578,667
  246. XX>     register int fd;
  247. XX> 
  248. XX>     if (Uflg) {
  249. XX>         if ((fd = open("/etc/psnlist", O_CREAT|O_RDWR, 0444)) >= 0) {
  250. XX>             nlist("/vmunix", nl);
  251. XX>             write(fd, nl, sizeof(nl));
  252. XX>             close(fd);
  253. XX>         } else {
  254. XX>             perror("/etc/psnlist");
  255. XX>             exit(1);
  256. XX>         }
  257. XX>         domanual();
  258. XX>         dosavettys();
  259. XX>     }
  260. XX> 
  261. XX>     if ((fd = open("/etc/psdatabase", O_RDONLY)) <= 0) {
  262. XX>         domanual();
  263. XX>         return;
  264. XX>     }
  265. XX>     read(fd, hash_ttys, sizeof(hash_ttys));
  266. XX>     read(fd, saved_tty_stat, sizeof(saved_tty_stat));
  267. XX>     close(fd);
  268. XX> }
  269. XX> 
  270. XX> dosavettys()
  271. XX> {
  272. XX>     register int fd;
  273. XX> 
  274. XX>     if ((fd = open("/etc/psdatabase", O_CREAT|O_RDWR, 0444)) <= 0)
  275. XX>         return;
  276. XX>     write(fd, hash_ttys, sizeof(hash_ttys));
  277. XX>     write(fd, saved_tty_stat, sizeof(saved_tty_stat));
  278. XX>     close(fd);
  279. XX>     exit(0);
  280. XX> }
  281. XX> 
  282. XX> domanual()
  283. XX> {
  284. XX>     register FILE *fp;
  285. XX>     register int i;
  286. XX>     register char c;
  287. XX>     struct stat sbuf;
  288. XX> 
  289. XX>     if ((fp = fopen("/etc/ttys", "r")) == NULL) {
  290. XX>         perror("/etc/ttys");
  291. XX>         exit(1);
  292. XX>     }
  293. XX>     i = 0;
  294. XX>     while((c = getc(fp)) != EOF) {
  295. XX>         if (c == '\n') {    /* jump the first 2 chars */
  296. XX>             saved_tty_stat[next_stty].name[i] = '\0';
  297. XX>             i = 0;
  298. XX>             if (stat(saved_tty_stat[next_stty].name,&sbuf)==0 &&
  299. XX>                 (sbuf.st_mode & S_IFMT) == S_IFCHR)
  300. XX>                 saved_tty_stat[next_stty].ttyd = sbuf.st_rdev;
  301. XX>             else
  302. XX>                 saved_tty_stat[next_stty].ttyd = -2;
  303. XX>             saved_tty_stat[next_stty].next =
  304. XX>                 hash_ttys[saved_tty_stat[next_stty].ttyd % 256];
  305. XX>             hash_ttys[saved_tty_stat[next_stty].ttyd % 256] =
  306. XX>                 &saved_tty_stat[next_stty];
  307. XX>             next_stty++;
  308. XX>             if ((c = getc(fp)) == EOF)
  309. XX>                 return;
  310. XX>             if ((c = getc(fp)) == EOF)
  311. XX>                 return;
  312. XX>         } else
  313. XX>             saved_tty_stat[next_stty].name[i++] = c;
  314. XX>     }
  315. XX> }
  316. XX> 
  317. XX> char *
  318. XX> gettty()
  319. XX> {
  320. XX>     register struct ttys *dp;
  321. XX>     register char *p;
  322. XX> 
  323. XX>     for(dp = hash_ttys[u.u_ttyd % 256]; dp; dp = dp->next)
  324. XX>         if (dp->ttyd == u.u_ttyd) {
  325. XX>             p = dp->name;
  326. XX>             if (p[0] == 't' && p[1] == 't' && p[2] == 'y')
  327. XX>                 p += 3;
  328. XX>             return(p);
  329. XX>         }
  330. XX>     return("?");
  331. XX> }
  332. XX> 
  333. XX> #else ECN
  334. XX> getdev()
  335. XX> {
  336. XX596a826
  337. XX> #endif ECN
  338. XX1103a1334,1336
  339. XX> #ifdef ECN
  340. XX>     struct passwd            *getpwuid();
  341. XX> #else
  342. XX1105a1339
  343. XX> #endif
  344. XX1118a1353,1359
  345. XX> #ifdef ECN
  346. XX>     if ((pw = getpwuid(uid)) == NULL)
  347. XX>         return((char *)NULL);
  348. XX>     strncpy(n->nt_name, pw->pw_name, NMAX);
  349. XX>     n->nt_uid = uid;
  350. XX>     return(n->nt_name);
  351. XX> #else
  352. XX1145a1387
  353. XX> #endif
  354. @//E*O*F ps.c.patch//
  355. chmod u=rw,g=rw,o=rw ps.c.patch
  356.  
  357. echo Inspecting for damage in transit...
  358. temp=/tmp/sharin$$; dtemp=/tmp/sharout$$
  359. trap "rm -f $temp $dtemp; exit" 0 1 2 3 15
  360. cat > $temp <<\!!!
  361.        3      10      54 Makefile
  362.       30     181     840 ps.1.patch
  363.      273     892    5101 ps.c.patch
  364.      306    1083    5995 total
  365. !!!
  366. wc  Makefile ps.1.patch ps.c.patch | sed 's=[^ ]*/==' | diff -b $temp - >$dtemp
  367. if test -s $dtemp
  368. then echo "Ouch [diff of wc output]:" ; cat $dtemp
  369. else echo "No problems found."
  370. fi
  371. exit 0
  372.