Update commands bc, egrep, expr, iostat, mail, ps, su, vmstat, wall, write.

This commit is contained in:
Serge
2022-07-10 22:14:32 -07:00
parent edde805980
commit ba2871aa34
11 changed files with 893 additions and 895 deletions

View File

@@ -156,6 +156,7 @@ int symlink(const char *target, const char *linkpath);
int vhangup(void); int vhangup(void);
int mknod(const char *, mode_t, dev_t); int mknod(const char *, mode_t, dev_t);
int reboot(int howto); int reboot(int howto);
int ttyslot(void);
#ifndef _VA_LIST_ #ifndef _VA_LIST_
# ifdef __GNUC__ # ifdef __GNUC__

View File

@@ -1,5 +1,8 @@
%{ %{
int *getout(); int *getout(void);
int getch(void);
int cpeek(int c, int yes, int no);
void yyerror(char *s);
%} %}
%right '=' %right '='
%left '+' '-' %left '+' '-'
@@ -39,12 +42,12 @@ int *pre, *post;
%% %%
start : start :
| start stat tail | start stat tail
= output( $2 ); = output( (int*) $2 );
| start def dargs ')' '{' dlist slist '}' | start def dargs ')' '{' dlist slist '}'
={ bundle( 6,pre, $7, post ,"0",numb[lev],"Q"); ={ bundle(6, pre, $7, post, "0", numb[lev], "Q");
conout( $$, $2 ); conout( (int*) $$, (char*) $2 );
rcrs = crs; rcrs = crs;
output( "" ); output( (int*) "" );
lev = bindx = 0; lev = bindx = 0;
} }
; ;
@@ -62,11 +65,11 @@ stat : e
| LETTER '=' e | LETTER '=' e
={ bundle(3, $3, "s", $1 ); } ={ bundle(3, $3, "s", $1 ); }
| LETTER '[' e ']' '=' e | LETTER '[' e ']' '=' e
={ bundle(4, $6, $3, ":", geta($1)); } ={ bundle(4, $6, $3, ":", geta((char*) $1)); }
| LETTER EQOP e | LETTER EQOP e
={ bundle(6, "l", $1, $3, $2, "s", $1 ); } ={ bundle(6, "l", $1, $3, $2, "s", $1 ); }
| LETTER '[' e ']' EQOP e | LETTER '[' e ']' EQOP e
={ bundle(8,$3, ";", geta($1), $6, $5, $3, ":", geta($1));} ={ bundle(8,$3, ";", geta((char*) $1), $6, $5, $3, ":", geta((char*) $1));}
| _BREAK | _BREAK
={ bundle(2, numb[lev-bstack[bindx-1]], "Q" ); } ={ bundle(2, numb[lev-bstack[bindx-1]], "Q" ); }
| _RETURN '(' e ')' | _RETURN '(' e ')'
@@ -94,17 +97,17 @@ stat : e
| error | error
={ bundle(1,"c"); } ={ bundle(1,"c"); }
| _IF CRS BLEV '(' re ')' stat | _IF CRS BLEV '(' re ')' stat
={ conout( $7, $2 ); ={ conout( (int*) $7, (char*) $2 );
bundle(3, $5, $2, " " ); bundle(3, $5, $2, " " );
} }
| _WHILE CRS '(' re ')' stat BLEV | _WHILE CRS '(' re ')' stat BLEV
={ bundle(3, $6, $4, $2 ); ={ bundle(3, $6, $4, $2 );
conout( $$, $2 ); conout( (int*) $$, (char*) $2 );
bundle(3, $4, $2, " " ); bundle(3, $4, $2, " " );
} }
| fprefix CRS re ';' e ')' stat BLEV | fprefix CRS re ';' e ')' stat BLEV
={ bundle(5, $7, $5, "s.", $3, $2 ); ={ bundle(5, $7, $5, "s.", $3, $2 );
conout( $$, $2 ); conout( (int*) $$, (char*) $2 );
bundle(5, $1, "s.", $3, $2, " " ); bundle(5, $1, "s.", $3, $2, " " );
} }
| '~' LETTER '=' e | '~' LETTER '=' e
@@ -174,7 +177,7 @@ e : e '+' e
| e '^' e | e '^' e
= bundle(3, $1, $3, "^" ); = bundle(3, $1, $3, "^" );
| LETTER '[' e ']' | LETTER '[' e ']'
={ bundle(3,$3, ";", geta($1)); } ={ bundle(3,$3, ";", geta((char*) $1)); }
| LETTER INCR | LETTER INCR
= bundle(4, "l", $1, "d1+s", $1 ); = bundle(4, "l", $1, "d1+s", $1 );
| INCR LETTER | INCR LETTER
@@ -184,13 +187,13 @@ e : e '+' e
| LETTER DECR | LETTER DECR
= bundle(4, "l", $1, "d1-s", $1 ); = bundle(4, "l", $1, "d1-s", $1 );
| LETTER '[' e ']' INCR | LETTER '[' e ']' INCR
= bundle(7,$3,";",geta($1),"d1+",$3,":",geta($1)); = bundle(7,$3,";",geta((char*) $1),"d1+",$3,":",geta((char*) $1));
| INCR LETTER '[' e ']' | INCR LETTER '[' e ']'
= bundle(7,$4,";",geta($2),"1+d",$4,":",geta($2)); = bundle(7,$4,";",geta((char*) $2),"1+d",$4,":",geta((char*) $2));
| LETTER '[' e ']' DECR | LETTER '[' e ']' DECR
= bundle(7,$3,";",geta($1),"d1-",$3,":",geta($1)); = bundle(7,$3,";",geta((char*) $1),"d1-",$3,":",geta((char*) $1));
| DECR LETTER '[' e ']' | DECR LETTER '[' e ']'
= bundle(7,$4,";",geta($2),"1-d",$4,":",geta($2)); = bundle(7,$4,";",geta((char*) $2),"1-d",$4,":",geta((char*) $2));
| SCALE INCR | SCALE INCR
= bundle(1,"Kd1+k"); = bundle(1,"Kd1+k");
| INCR SCALE | INCR SCALE
@@ -216,9 +219,9 @@ e : e '+' e
| DECR OBASE | DECR OBASE
= bundle(1,"O1-do"); = bundle(1,"O1-do");
| LETTER '(' cargs ')' | LETTER '(' cargs ')'
= bundle(4, $3, "l", getf($1), "x" ); = bundle(4, $3, "l", getf((char*) $1), "x" );
| LETTER '(' ')' | LETTER '(' ')'
= bundle(3, "l", getf($1), "x" ); = bundle(3, "l", getf((char*) $1), "x" );
| cons | cons
={ bundle(2, " ", $1 ); } ={ bundle(2, " ", $1 ); }
| DOT cons | DOT cons
@@ -236,9 +239,9 @@ e : e '+' e
| LETTER EQOP e %prec '=' | LETTER EQOP e %prec '='
={ bundle(6, "l", $1, $3, $2, "ds", $1 ); } ={ bundle(6, "l", $1, $3, $2, "ds", $1 ); }
| LETTER '[' e ']' '=' e | LETTER '[' e ']' '=' e
= { bundle(5,$6,"d",$3,":",geta($1)); } = { bundle(5,$6,"d",$3,":",geta((char*) $1)); }
| LETTER '[' e ']' EQOP e | LETTER '[' e ']' EQOP e
= { bundle(9,$3,";",geta($1),$6,$5,"d",$3,":",geta($1)); } = { bundle(9,$3,";",geta((char*) $1),$6,$5,"d",$3,":",geta((char*) $1)); }
| LENGTH '(' e ')' | LENGTH '(' e ')'
= bundle(2,$3,"Z"); = bundle(2,$3,"Z");
| SCALE '(' e ')' | SCALE '(' e ')'
@@ -277,7 +280,7 @@ cargs : eora
; ;
eora: e eora: e
| LETTER '[' ']' | LETTER '[' ']'
=bundle(2,"l",geta($1)); =bundle(2,"l",geta((char*) $1));
; ;
cons : constant cons : constant
@@ -303,7 +306,7 @@ CRS :
; ;
def : _DEFINE LETTER '(' def : _DEFINE LETTER '('
={ $$ = (int) getf($2); ={ $$ = (int) getf((char*) $2);
pre = (int*) ""; pre = (int*) "";
post = (int*) ""; post = (int*) "";
lev = 1; lev = 1;
@@ -313,19 +316,19 @@ def : _DEFINE LETTER '('
dargs : dargs :
| lora | lora
={ pp( $1 ); } ={ pp((char*) $1); }
| dargs ',' lora | dargs ',' lora
={ pp( $3 ); } ={ pp((char*) $3); }
; ;
dlets : lora dlets : lora
={ tp($1); } ={ tp((char*) $1); }
| dlets ',' lora | dlets ',' lora
={ tp($3); } ={ tp((char*) $3); }
; ;
lora : LETTER lora : LETTER
| LETTER '[' ']' | LETTER '[' ']'
={ $$ = (int) geta($1); } ={ $$ = (int) geta((char*) $1); }
; ;
%% %%
@@ -348,7 +351,9 @@ char *letr[26] = {
"k","l","m","n","o","p","q","r","s","t", "k","l","m","n","o","p","q","r","s","t",
"u","v","w","x","y","z" } ; "u","v","w","x","y","z" } ;
char *dot = { "." }; char *dot = { "." };
yylex(){
int yylex()
{
int c, ch; int c, ch;
restart: restart:
c = getch(); c = getch();
@@ -445,7 +450,8 @@ restart:
} }
} }
cpeek( c, yes, no ){ int cpeek(int c, int yes, int no)
{
if( (peekc=getch()) != c ) return( no ); if( (peekc=getch()) != c ) return( no );
else { else {
peekc = -1; peekc = -1;
@@ -453,7 +459,8 @@ cpeek( c, yes, no ){
} }
} }
getch(){ int getch()
{
int ch; int ch;
loop: loop:
ch = (peekc < 0) ? getc(in) : peekc; ch = (peekc < 0) ? getc(in) : peekc;
@@ -472,13 +479,18 @@ loop:
goto loop; goto loop;
} }
yyerror("cannot open input file"); yyerror("cannot open input file");
return EOF;
} }
# define b_sp_max 3000 # define b_sp_max 3000
int b_space [ b_sp_max ]; int b_space [ b_sp_max ];
int * b_sp_nxt = { b_space }; int * b_sp_nxt = { b_space };
int bdebug = 0; int bdebug = 0;
bundle(a){
int bundle(int a, ...)
{
int i, *p, *q; int i, *p, *q;
p = &a; p = &a;
@@ -494,16 +506,18 @@ bundle(a){
return( (int) q ); return( (int) q );
} }
routput(p) int *p; { void routput(int *p)
{
if( bdebug ) printf("routput(%p)\n", p ); if( bdebug ) printf("routput(%p)\n", p );
if( p >= &b_space[0] && p < &b_space[b_sp_max]){ if( p >= &b_space[0] && p < &b_space[b_sp_max]){
/* part of a bundle */ /* part of a bundle */
while( *p != 0 ) routput( *p++ ); while( *p != 0 ) routput( (int*) *p++ );
} }
else printf( "%s", (char*) p ); /* character string */ else printf( "%s", (char*) p ); /* character string */
} }
output( p ) int *p; { void output(int *p)
{
routput( p ); routput( p );
b_sp_nxt = & b_space[0]; b_sp_nxt = & b_space[0];
printf( "\n" ); printf( "\n" );
@@ -512,7 +526,8 @@ output( p ) int *p; {
crs = rcrs; crs = rcrs;
} }
conout( p, s ) int *p; char *s; { void conout(int *p, char *s)
{
printf("["); printf("[");
routput( p ); routput( p );
printf("]s%s\n", s ); printf("]s%s\n", s );
@@ -520,7 +535,8 @@ conout( p, s ) int *p; char *s; {
lev--; lev--;
} }
yyerror( s ) char *s; { void yyerror(char *s)
{
if(ifile > sargc)ss="teletype"; if(ifile > sargc)ss="teletype";
printf("c[%s on line %d, %s]pc\n", s ,ln+1,ss); printf("c[%s on line %d, %s]pc\n", s ,ln+1,ss);
fflush(stdout); fflush(stdout);
@@ -531,7 +547,8 @@ yyerror( s ) char *s; {
b_sp_nxt = &b_space[0]; b_sp_nxt = &b_space[0];
} }
pp( s ) char *s; { void pp(char *s)
{
/* puts the relevant stuff on pre and post for the letter s */ /* puts the relevant stuff on pre and post for the letter s */
bundle(3, "S", s, pre ); bundle(3, "S", s, pre );
@@ -540,14 +557,17 @@ pp( s ) char *s; {
post = (int*) yyval; post = (int*) yyval;
} }
tp( s ) char *s; { /* same as pp, but for temps */ /* same as pp, but for temps */
void tp(char *s)
{
bundle(3, "0S", s, pre ); bundle(3, "0S", s, pre );
pre = (int*) yyval; pre = (int*) yyval;
bundle(4, post, "L", s, "s." ); bundle(4, post, "L", s, "s." );
post = (int*) yyval; post = (int*) yyval;
} }
yyinit(argc,argv) int argc; char *argv[];{ void yyinit(int argc, char *argv[])
{
signal( 2, SIG_IGN ); /* ignore all interrupts */ signal( 2, SIG_IGN ); /* ignore all interrupts */
sargv=argv; sargv=argv;
sargc= -- argc; sargc= -- argc;
@@ -560,24 +580,25 @@ yyinit(argc,argv) int argc; char *argv[];{
ln = 0; ln = 0;
ss = sargv[1]; ss = sargv[1];
} }
int *getout(){
int *getout()
{
printf("q"); printf("q");
fflush(stdout); fflush(stdout);
exit(0); exit(0);
} }
int * int *getf(char *p)
getf(p) char *p;{ {
return (int*) &funtab[2 * (*p - 0141)]; return (int*) &funtab[2 * (*p - 0141)];
} }
int * int *geta(char *p)
geta(p) char *p;{ {
return (int*) &atab[2 * (*p - 0141)]; return (int*) &atab[2 * (*p - 0141)];
} }
main(argc, argv) int main(int argc, char **argv)
char **argv;
{ {
int p[2]; int p[2];

View File

@@ -15,6 +15,8 @@
%{ %{
#include <stdio.h> #include <stdio.h>
#include <stdlib.h> #include <stdlib.h>
#include <unistd.h>
#include <fcntl.h>
#include <sys/types.h> #include <sys/types.h>
#include <sys/stat.h> #include <sys/stat.h>
@@ -24,6 +26,7 @@
#define NCHARS 128 #define NCHARS 128
#define NSTATES 128 #define NSTATES 128
#define FINAL -1 #define FINAL -1
char gotofn[NSTATES][NCHARS]; char gotofn[NSTATES][NCHARS];
int state[NSTATES]; int state[NSTATES];
char out[NSTATES]; char out[NSTATES];
@@ -62,6 +65,16 @@ int nsucc;
int f; int f;
char *fname; char *fname;
int nextch(void);
void synerror(void);
void overflo(void);
void follow(int v);
void add(int *array, int n);
int cstate(int v);
int member(int symb, int set, int torf);
int notin(int n);
void execute(char *file);
%} %}
%% %%
@@ -109,15 +122,18 @@ r: r OR r
; ;
%% %%
yyerror(s) { void yyerror(char *s)
{
fprintf(stderr, "egrep: %s\n", s); fprintf(stderr, "egrep: %s\n", s);
exit(2); exit(2);
} }
yylex() { int yylex()
{
extern int yylval; extern int yylval;
int cclcnt, x; int cclcnt, x;
register char c, d; char c, d;
switch(c = nextch()) { switch(c = nextch()) {
case '$': case '$':
case '^': c = '\n'; case '^': c = '\n';
@@ -140,32 +156,39 @@ yylex() {
c = nextch(); c = nextch();
} }
do { do {
if (c == '\0') synerror(); if (c == '\0')
synerror();
if (c == '-' && cclcnt > 0 && chars[nxtchar-1] != 0) { if (c == '-' && cclcnt > 0 && chars[nxtchar-1] != 0) {
if ((d = nextch()) != 0) { if ((d = nextch()) != 0) {
c = chars[nxtchar-1]; c = chars[nxtchar-1];
while (c < d) { while (c < d) {
if (nxtchar >= MAXLIN) overflo(); if (nxtchar >= MAXLIN)
overflo();
chars[nxtchar++] = ++c; chars[nxtchar++] = ++c;
cclcnt++; cclcnt++;
} }
continue; continue;
} }
} }
if (nxtchar >= MAXLIN) overflo(); if (nxtchar >= MAXLIN)
overflo();
chars[nxtchar++] = c; chars[nxtchar++] = c;
cclcnt++; cclcnt++;
} while ((c = nextch()) != ']'); } while ((c = nextch()) != ']');
chars[count] = cclcnt; chars[count] = cclcnt;
return (x); return (x);
case '\\': case '\\':
if ((c = nextch()) == '\0') synerror(); if ((c = nextch()) == '\0')
synerror();
defchar: defchar:
default: yylval = c; return (CHAR); default: yylval = c; return (CHAR);
} }
} }
nextch() {
register char c; int nextch()
{
char c;
if (fflag) { if (fflag) {
if ((c = getc(exprfile)) == EOF) { if ((c = getc(exprfile)) == EOF) {
fclose(exprfile); fclose(exprfile);
@@ -176,28 +199,35 @@ nextch() {
return(c); return(c);
} }
synerror() { void synerror()
{
fprintf(stderr, "egrep: syntax error\n"); fprintf(stderr, "egrep: syntax error\n");
exit(2); exit(2);
} }
enter(x) int x; { int enter(int x)
if(line >= MAXLIN) overflo(); {
if(line >= MAXLIN)
overflo();
name[line] = x; name[line] = x;
left[line] = 0; left[line] = 0;
right[line] = 0; right[line] = 0;
return(line++); return(line++);
} }
cclenter(x) int x; { int cclenter(int x)
register linno; {
int linno;
linno = enter(x); linno = enter(x);
right[linno] = count; right[linno] = count;
return (linno); return (linno);
} }
node(x, l, r) { int node(int x, int l, int r)
if(line >= MAXLIN) overflo(); {
if(line >= MAXLIN)
overflo();
name[line] = x; name[line] = x;
left[line] = l; left[line] = l;
right[line] = r; right[line] = r;
@@ -206,21 +236,27 @@ node(x, l, r) {
return(line++); return(line++);
} }
unary(x, d) { int unary(int x, int d)
if(line >= MAXLIN) overflo(); {
if(line >= MAXLIN)
overflo();
name[line] = x; name[line] = x;
left[line] = d; left[line] = d;
right[line] = 0; right[line] = 0;
parent[d] = line; parent[d] = line;
return(line++); return(line++);
} }
overflo() {
void overflo()
{
fprintf(stderr, "egrep: regular expression too long\n"); fprintf(stderr, "egrep: regular expression too long\n");
exit(2); exit(2);
} }
cfoll(v) { void cfoll(int v)
register i; {
int i;
if (left[v] == 0) { if (left[v] == 0) {
count = 0; count = 0;
for (i=1; i<=line; i++) tmpstat[i] = 0; for (i=1; i<=line; i++) tmpstat[i] = 0;
@@ -233,8 +269,10 @@ cfoll(v) {
cfoll(right[v]); cfoll(right[v]);
} }
} }
cgotofn() {
register c, i, k; void cgotofn()
{
int c, i, k;
int n, s; int n, s;
char symbol[NCHARS]; char symbol[NCHARS];
int j, nc, pc, pos; int j, nc, pc, pos;
@@ -242,7 +280,7 @@ cgotofn() {
int number, newpos; int number, newpos;
count = 0; count = 0;
for (n=3; n<=line; n++) tmpstat[n] = 0; for (n=3; n<=line; n++) tmpstat[n] = 0;
if (cstate(line-1)==0) { if (cstate(line-1) == 0) {
tmpstat[line] = 1; tmpstat[line] = 1;
count++; count++;
out[0] = 1; out[0] = 1;
@@ -327,8 +365,10 @@ cgotofn() {
} }
} }
cstate(v) { int cstate(int v)
register b; {
int b;
if (left[v] == 0) { if (left[v] == 0) {
if (tmpstat[v] != 1) { if (tmpstat[v] != 1) {
tmpstat[v] = 1; tmpstat[v] = 1;
@@ -352,9 +392,10 @@ cstate(v) {
} }
} }
int member(int symb, int set, int torf)
{
int i, num, pos;
member(symb, set, torf) {
register i, num, pos;
num = chars[set]; num = chars[set];
pos = set + 1; pos = set + 1;
for (i=0; i<num; i++) for (i=0; i<num; i++)
@@ -362,8 +403,10 @@ member(symb, set, torf) {
return (!torf); return (!torf);
} }
notin(n) { int notin(int n)
register i, j, pos; {
int i, j, pos;
for (i=0; i<=n; i++) { for (i=0; i<=n; i++) {
if (positions[state[i]] == count) { if (positions[state[i]] == count) {
pos = state[i] + 1; pos = state[i] + 1;
@@ -377,9 +420,12 @@ notin(n) {
return (1); return (1);
} }
add(array, n) int *array; { void add(int *array, int n)
register i; {
if (nxtpos + count > MAXPOS) overflo(); int i;
if (nxtpos + count > MAXPOS)
overflo();
array[n] = nxtpos; array[n] = nxtpos;
positions[nxtpos++] = count; positions[nxtpos++] = count;
for (i=3; i <= line; i++) { for (i=3; i <= line; i++) {
@@ -389,7 +435,8 @@ add(array, n) int *array; {
} }
} }
follow(v) int v; { void follow(int v)
{
int p; int p;
if (v == line) return; if (v == line) return;
p = parent[v]; p = parent[v];
@@ -419,9 +466,7 @@ follow(v) int v; {
} }
} }
int main(int argc, char **argv)
main(argc, argv)
char **argv;
{ {
while (--argc > 0 && (++argv)[0][0]=='-') while (--argc > 0 && (++argv)[0][0]=='-')
switch (argv[0][1]) { switch (argv[0][1]) {
@@ -498,12 +543,11 @@ out:
exit(retcode != 0 ? retcode : nsucc == 0); exit(retcode != 0 ? retcode : nsucc == 0);
} }
execute(file) void execute(char *file)
char *file;
{ {
register char *p; char *p;
register cstat; int cstat;
register ccount; int ccount;
static char *buf; static char *buf;
static int blksize; static int blksize;
struct stat stb; struct stat stb;
@@ -541,7 +585,8 @@ char *file;
for (;;) { for (;;) {
cstat = gotofn[cstat][*p&0377]; /* all input chars made positive */ cstat = gotofn[cstat][*p&0377]; /* all input chars made positive */
if (out[cstat]) { if (out[cstat]) {
found: for(;;) { found:
for(;;) {
if (*p++ == '\n') { if (*p++ == '\n') {
if (vflag == 0) { if (vflag == 0) {
succeed: nsucc = 1; succeed: nsucc = 1;
@@ -592,7 +637,7 @@ char *file;
if (out[(cstat=istat)]) goto cfound; if (out[(cstat=istat)]) goto cfound;
} }
} }
brk2: brk2:
if (--ccount <= 0) { if (--ccount <= 0) {
if (p <= &buf[blksize]) { if (p <= &buf[blksize]) {
if ((ccount = read(f, p, blksize)) <= 0) break; if ((ccount = read(f, p, blksize)) <= 0) break;
@@ -607,7 +652,8 @@ char *file;
blkno += ccount / 512; blkno += ccount / 512;
} }
} }
done: close(f); done:
close(f);
if (cflag) { if (cflag) {
if (nfile > 1) if (nfile > 1)
printf("%s:", file); printf("%s:", file);

View File

@@ -1,3 +1,12 @@
%{
int ematch(char *s, char *p);
void yyerror(char *s);
int advance(char *lp, char *ep);
char *compile(char *instring, char *ep, char *endbuf, int seof);
void getrnge(char *str);
int ecmp(char *a, char *b, int count);
%}
/* Yacc productions for "expr" command: */ /* Yacc productions for "expr" command: */
%token OR AND ADD SUBT MULT DIV REM EQ GT GEQ LT LEQ NEQ %token OR AND ADD SUBT MULT DIV REM EQ GT GEQ LT LEQ NEQ
@@ -18,7 +27,7 @@
/* a single `expression' is evaluated and printed: */ /* a single `expression' is evaluated and printed: */
expression: expr NOARG = { expression: expr NOARG = {
printf("%s\n", $1); printf("%s\n", (char*) $1);
exit((! strcmp((char*) $1, "0") || exit((! strcmp((char*) $1, "0") ||
! strcmp((char*) $1, "\0")) ? 1 : 0); ! strcmp((char*) $1, "\0")) ? 1 : 0);
} }
@@ -26,24 +35,24 @@ expression: expr NOARG = {
expr: '(' expr ')' = { $$ = (int) $2; } expr: '(' expr ')' = { $$ = (int) $2; }
| expr OR expr = { $$ = (int) conju(OR, $1, $3); } | expr OR expr = { $$ = (int) conju(OR, (char*) $1, (char*) $3); }
| expr AND expr = { $$ = (int) conju(AND, $1, $3); } | expr AND expr = { $$ = (int) conju(AND, (char*) $1, (char*) $3); }
| expr EQ expr = { $$ = (int) rel(EQ, $1, $3); } | expr EQ expr = { $$ = (int) rel(EQ, (char*) $1, (char*) $3); }
| expr GT expr = { $$ = (int) rel(GT, $1, $3); } | expr GT expr = { $$ = (int) rel(GT, (char*) $1, (char*) $3); }
| expr GEQ expr = { $$ = (int) rel(GEQ, $1, $3); } | expr GEQ expr = { $$ = (int) rel(GEQ, (char*) $1, (char*) $3); }
| expr LT expr = { $$ = (int) rel(LT, $1, $3); } | expr LT expr = { $$ = (int) rel(LT, (char*) $1, (char*) $3); }
| expr LEQ expr = { $$ = (int) rel(LEQ, $1, $3); } | expr LEQ expr = { $$ = (int) rel(LEQ, (char*) $1, (char*) $3); }
| expr NEQ expr = { $$ = (int) rel(NEQ, $1, $3); } | expr NEQ expr = { $$ = (int) rel(NEQ, (char*) $1, (char*) $3); }
| expr ADD expr = { $$ = (int) arith(ADD, $1, $3); } | expr ADD expr = { $$ = (int) arith(ADD, (char*) $1, (char*) $3); }
| expr SUBT expr = { $$ = (int) arith(SUBT, $1, $3); } | expr SUBT expr = { $$ = (int) arith(SUBT, (char*) $1, (char*) $3); }
| expr MULT expr = { $$ = (int) arith(MULT, $1, $3); } | expr MULT expr = { $$ = (int) arith(MULT, (char*) $1, (char*) $3); }
| expr DIV expr = { $$ = (int) arith(DIV, $1, $3); } | expr DIV expr = { $$ = (int) arith(DIV, (char*) $1, (char*) $3); }
| expr REM expr = { $$ = (int) arith(REM, $1, $3); } | expr REM expr = { $$ = (int) arith(REM, (char*) $1, (char*) $3); }
| expr MCH expr = { $$ = (int) match($1, $3); } | expr MCH expr = { $$ = (int) match((char*) $1, (char*) $3); }
| MATCH expr expr = { $$ = (int) match($2, $3); } | MATCH expr expr = { $$ = (int) match((char*) $2, (char*) $3); }
| SUBSTR expr expr expr = { $$ = (int) substr($2, $3, $4); } | SUBSTR expr expr expr = { $$ = (int) substr((char*) $2, (char*) $3, (char*) $4); }
| LENGTH expr = { $$ = (int) length($2); } | LENGTH expr = { $$ = (int) length((char*) $2); }
| INDEX expr expr = { $$ = (int) cindex($2, $3); } | INDEX expr expr = { $$ = (int) cindex((char*) $2, (char*) $3); }
| A_STRING | A_STRING
; ;
%% %%
@@ -55,7 +64,7 @@ expr: '(' expr ')' = { $$ = (int) $2; }
#define ESIZE 256 #define ESIZE 256
#define error(c) errxx(c) #define error(c) errxx(c)
#define EQL(x,y) !strcmp(x,y) #define EQL(x,y) !strcmp(x,y)
long atol();
char **Av; char **Av;
int Ac; int Ac;
int Argi; int Argi;
@@ -63,47 +72,53 @@ int Argi;
char Mstring[1][128]; char Mstring[1][128];
extern int nbra; extern int nbra;
main(argc, argv) char **argv; { int main(int argc, char **argv)
{
Ac = argc; Ac = argc;
Argi = 1; Argi = 1;
Av = argv; Av = argv;
yyparse(); yyparse();
} }
char *operators[] = { "|", "&", "+", "-", "*", "/", "%", ":", char *operators[] = {
"|", "&", "+", "-", "*", "/", "%", ":",
"=", "==", "<", "<=", ">", ">=", "!=", "=", "==", "<", "<=", ">", ">=", "!=",
"match", "substr", "length", "index", "\0" }; "match", "substr", "length", "index", "\0"
int op[] = { OR, AND, ADD, SUBT, MULT, DIV, REM, MCH, };
int op[] = {
OR, AND, ADD, SUBT, MULT, DIV, REM, MCH,
EQ, EQ, LT, LEQ, GT, GEQ, NEQ, EQ, EQ, LT, LEQ, GT, GEQ, NEQ,
MATCH, SUBSTR, LENGTH, INDEX }; MATCH, SUBSTR, LENGTH, INDEX
};
yylex() int yylex()
{ {
register char *p; char *p;
register i; int i;
if(Argi >= Ac) return NOARG; if (Argi >= Ac) return NOARG;
p = Av[Argi++]; p = Av[Argi++];
if(*p == '(' || *p == ')') if (*p == '(' || *p == ')')
return (int)*p; return (int)*p;
for(i = 0; *operators[i]; ++i) for (i = 0; *operators[i]; ++i)
if(EQL(operators[i], p)) if (EQL(operators[i], p))
return op[i]; return op[i];
yylval = (int) p; yylval = (int) p;
return A_STRING; return A_STRING;
} }
char *rel(op, r1, r2) register char *r1, *r2; char *rel(int op, char *r1, char *r2)
{ {
register long i; long i;
if(ematch(r1, "-*[0-9]*$") && ematch(r2, "[0-9]*$")) if (ematch(r1, "-*[0-9]*$") && ematch(r2, "[0-9]*$"))
i = atol(r1) - atol(r2); i = atol(r1) - atol(r2);
else else
i = strcmp(r1, r2); i = strcmp(r1, r2);
switch(op) { switch (op) {
case EQ: i = i==0; break; case EQ: i = i==0; break;
case GT: i = i>0; break; case GT: i = i>0; break;
case GEQ: i = i>=0; break; case GEQ: i = i>=0; break;
@@ -114,17 +129,17 @@ char *rel(op, r1, r2) register char *r1, *r2;
return i? "1": "0"; return i? "1": "0";
} }
char *arith(op, r1, r2) char *r1, *r2; char *arith(int op, char *r1, char *r2)
{ {
long i1, i2; long i1, i2;
register char *rv; char *rv;
if(!(ematch(r1, "[0-9]*$") && ematch(r2, "[0-9]*$"))) if (!(ematch(r1, "[0-9]*$") && ematch(r2, "[0-9]*$")))
yyerror("non-numeric argument"); yyerror("non-numeric argument");
i1 = atol(r1); i1 = atol(r1);
i2 = atol(r2); i2 = atol(r2);
switch(op) { switch (op) {
case ADD: i1 = i1 + i2; break; case ADD: i1 = i1 + i2; break;
case SUBT: i1 = i1 - i2; break; case SUBT: i1 = i1 - i2; break;
case MULT: i1 = i1 * i2; break; case MULT: i1 = i1 * i2; break;
@@ -132,20 +147,20 @@ char *arith(op, r1, r2) char *r1, *r2;
case REM: i1 = i1 % i2; break; case REM: i1 = i1 % i2; break;
} }
rv = malloc(16); rv = malloc(16);
sprintf(rv, "%D", i1); sprintf(rv, "%ld", i1);
return rv; return rv;
} }
char *conju(op, r1, r2) char *r1, *r2; char *conju(int op, char *r1, char *r2)
{ {
register char *rv; char *rv;
switch(op) { switch (op) {
case OR: case OR:
if(EQL(r1, "0") if (EQL(r1, "0")
|| EQL(r1, "")) || EQL(r1, ""))
if(EQL(r2, "0") if (EQL(r2, "0")
|| EQL(r2, "")) || EQL(r2, ""))
rv = "0"; rv = "0";
else else
@@ -154,10 +169,10 @@ char *conju(op, r1, r2) char *r1, *r2;
rv = r1; rv = r1;
break; break;
case AND: case AND:
if(EQL(r1, "0") if (EQL(r1, "0")
|| EQL(r1, "")) || EQL(r1, ""))
rv = "0"; rv = "0";
else if(EQL(r2, "0") else if (EQL(r2, "0")
|| EQL(r2, "")) || EQL(r2, ""))
rv = "0"; rv = "0";
else else
@@ -167,94 +182,89 @@ char *conju(op, r1, r2) char *r1, *r2;
return rv; return rv;
} }
char *substr(v, s, w) char *v, *s, *w; char *substr(char *v, char *s, char *w)
{ {
register si, wi; int si, wi;
register char *res; char *res;
si = atol(s); si = atol(s);
wi = atol(w); wi = atol(w);
while(--si) if(*v) ++v; while (--si) if (*v) ++v;
res = v; res = v;
while(wi--) if(*v) ++v; while (wi--) if (*v) ++v;
*v = '\0'; *v = '\0';
return res; return res;
} }
char *length(s) register char *s; char *length(char *s)
{ {
register i = 0; int i = 0;
register char *rv; char *rv;
while(*s++) ++i; while (*s++) ++i;
rv = malloc(8); rv = malloc(8);
sprintf(rv, "%d", i); sprintf(rv, "%d", i);
return rv; return rv;
} }
char *cindex(s, t) char *s, *t; char *cindex(char *s, char *t)
{ {
register i, j; int i, j;
register char *rv; char *rv;
for(i = 0; s[i] ; ++i) for (i = 0; s[i] ; ++i)
for(j = 0; t[j] ; ++j) for (j = 0; t[j] ; ++j)
if(s[i]==t[j]) { if (s[i]==t[j]) {
sprintf(rv = malloc(8), "%d", ++i); sprintf(rv = malloc(8), "%d", ++i);
return rv; return rv;
} }
return "0"; return "0";
} }
char *match(s, p) char *match(char *s, char *p)
{ {
register char *rv; char *rv = malloc(8);
sprintf(rv = malloc(8), "%d", ematch(s, p)); sprintf(rv, "%d", ematch(s, p));
if(nbra) { if (nbra) {
rv = malloc(strlen(Mstring[0])+1); rv = malloc(strlen(Mstring[0])+1);
strcpy(rv, Mstring[0]); strcpy(rv, Mstring[0]);
} }
return rv; return rv;
} }
#define INIT register char *sp = instring; #define INIT char *sp = instring;
#define GETC() (*sp++) #define GETC() (*sp++)
#define PEEKC() (*sp) #define PEEKC() (*sp)
#define UNGETC(c) (--sp) #define UNGETC(c) (--sp)
#define RETURN(c) return
#define ERROR(c) errxx(c) #define ERROR(c) errxx(c)
int ematch(char *s, char *p)
ematch(s, p)
char *s;
register char *p;
{ {
static char expbuf[ESIZE]; static char expbuf[ESIZE];
char *compile(); int num;
register num;
extern char *braslist[], *braelist[], *loc2; extern char *braslist[], *braelist[], *loc2;
compile(p, expbuf, &expbuf[ESIZE], 0); compile(p, expbuf, &expbuf[ESIZE], 0);
if(nbra > 1) if (nbra > 1)
yyerror("Too many '\\('s"); yyerror("Too many '\\('s");
if(advance(s, expbuf)) { if (advance(s, expbuf)) {
if(nbra == 1) { if (nbra == 1) {
p = braslist[0]; p = braslist[0];
num = braelist[0] - p; num = braelist[0] - p;
strncpy(Mstring[0], p, num); strncpy(Mstring[0], p, num);
Mstring[0][num] = '\0'; Mstring[0][num] = '\0';
} }
return(loc2-s); return loc2-s;
} }
return(0); return 0;
} }
errxx(c) void errxx(c)
{ {
yyerror("RE error"); yyerror("RE error");
} }
@@ -276,8 +286,8 @@ errxx(c)
#define PLACE(c) ep[c >> 3] |= bittab[c & 07] #define PLACE(c) ep[c >> 3] |= bittab[c & 07]
#define ISTHERE(c) (ep[c >> 3] & bittab[c & 07]) #define ISTHERE(c) (ep[c >> 3] & bittab[c & 07])
char *braslist[NBRA]; char *braslist[NBRA];
char *braelist[NBRA]; char *braelist[NBRA];
int nbra; int nbra;
char *loc1, *loc2, *locs; char *loc1, *loc2, *locs;
int sed; int sed;
@@ -286,7 +296,7 @@ int circf;
int low; int low;
int size; int size;
char bittab[] = { char bittab[] = {
1, 1,
2, 2,
4, 4,
@@ -297,14 +307,11 @@ char bittab[] = {
128 128
}; };
char * char *compile(char *instring, char *ep, char *endbuf, int seof)
compile(instring, ep, endbuf, seof)
register char *ep;
char *instring, *endbuf;
{ {
INIT /* Dependent declarations and initializations */ INIT /* Dependent declarations and initializations */
register c; int c;
register eof = seof; int eof = seof;
char *lastep = instring; char *lastep = instring;
int cclcnt; int cclcnt;
char bracket[NBRA], *bracketp; char bracket[NBRA], *bracketp;
@@ -314,10 +321,10 @@ char *instring, *endbuf;
int i, cflg; int i, cflg;
lastep = 0; lastep = 0;
if((c = GETC()) == eof) { if ((c = GETC()) == eof) {
if(*ep == 0 && !sed) if (*ep == 0 && !sed)
ERROR(41); ERROR(41);
RETURN(ep); return ep;
} }
bracketp = bracket; bracketp = bracket;
circf = closed = nbra = 0; circf = closed = nbra = 0;
@@ -328,11 +335,11 @@ char *instring, *endbuf;
for (;;) { for (;;) {
if (ep >= endbuf) if (ep >= endbuf)
ERROR(50); ERROR(50);
if((c = GETC()) != '*' && ((c != '\\') || (PEEKC() != '{'))) if ((c = GETC()) != '*' && ((c != '\\') || (PEEKC() != '{')))
lastep = ep; lastep = ep;
if (c == eof) { if (c == eof) {
*ep++ = CEOF; *ep++ = CEOF;
RETURN(ep); return ep;
} }
switch (c) { switch (c) {
@@ -349,44 +356,44 @@ char *instring, *endbuf;
continue; continue;
case '$': case '$':
if(PEEKC() != eof) if (PEEKC() != eof)
goto defchar; goto defchar;
*ep++ = CDOL; *ep++ = CDOL;
continue; continue;
case '[': case '[':
if(&ep[17] >= endbuf) if (&ep[17] >= endbuf)
ERROR(50); ERROR(50);
*ep++ = CCL; *ep++ = CCL;
lc = 0; lc = 0;
for(i = 0; i < 16; i++) for (i = 0; i < 16; i++)
ep[i] = 0; ep[i] = 0;
neg = 0; neg = 0;
if((c = GETC()) == '^') { if ((c = GETC()) == '^') {
neg = 1; neg = 1;
c = GETC(); c = GETC();
} }
do { do {
if(c == '\0' || c == '\n') if (c == '\0' || c == '\n')
ERROR(49); ERROR(49);
if(c == '-' && lc != 0) { if (c == '-' && lc != 0) {
if ((c = GETC()) == ']') { if ((c = GETC()) == ']') {
PLACE('-'); PLACE('-');
break; break;
} }
while(lc < c) { while (lc < c) {
PLACE(lc); PLACE(lc);
lc++; lc++;
} }
} }
lc = c; lc = c;
PLACE(c); PLACE(c);
} while((c = GETC()) != ']'); } while ((c = GETC()) != ']');
if(neg) { if (neg) {
for(cclcnt = 0; cclcnt < 16; cclcnt++) for (cclcnt = 0; cclcnt < 16; cclcnt++)
ep[cclcnt] ^= -1; ep[cclcnt] ^= -1;
ep[0] &= 0376; ep[0] &= 0376;
} }
@@ -396,10 +403,10 @@ char *instring, *endbuf;
continue; continue;
case '\\': case '\\':
switch(c = GETC()) { switch (c = GETC()) {
case '(': case '(':
if(nbra >= NBRA) if (nbra >= NBRA)
ERROR(43); ERROR(43);
*bracketp++ = nbra; *bracketp++ = nbra;
*ep++ = CBRA; *ep++ = CBRA;
@@ -407,7 +414,7 @@ char *instring, *endbuf;
continue; continue;
case ')': case ')':
if(bracketp <= bracket) if (bracketp <= bracket)
ERROR(42); ERROR(42);
*ep++ = CKET; *ep++ = CKET;
*ep++ = *--bracketp; *ep++ = *--bracketp;
@@ -415,7 +422,7 @@ char *instring, *endbuf;
continue; continue;
case '{': case '{':
if(lastep == (char *) (0)) if (lastep == (char *) (0))
goto defchar; goto defchar;
*lastep |= RNGE; *lastep |= RNGE;
cflg = 0; cflg = 0;
@@ -427,25 +434,25 @@ char *instring, *endbuf;
i = 10 * i + c - '0'; i = 10 * i + c - '0';
else else
ERROR(16); ERROR(16);
} while(((c = GETC()) != '\\') && (c != ',')); } while (((c = GETC()) != '\\') && (c != ','));
if (i > 255) if (i > 255)
ERROR(11); ERROR(11);
*ep++ = i; *ep++ = i;
if (c == ',') { if (c == ',') {
if(cflg++) if (cflg++)
ERROR(44); ERROR(44);
if((c = GETC()) == '\\') if ((c = GETC()) == '\\')
*ep++ = 255; *ep++ = '\377';
else { else {
UNGETC(c); UNGETC(c);
goto nlim; /* get 2'nd number */ goto nlim; /* get 2'nd number */
} }
} }
if(GETC() != '}') if (GETC() != '}')
ERROR(45); ERROR(45);
if(!cflg) /* one number */ if (!cflg) /* one number */
*ep++ = i; *ep++ = i;
else if((ep[-1] & 0377) < (ep[-2] & 0377)) else if ((ep[-1] & 0377) < (ep[-2] & 0377))
ERROR(46); ERROR(46);
continue; continue;
@@ -457,8 +464,8 @@ char *instring, *endbuf;
goto defchar; goto defchar;
default: default:
if(c >= '1' && c <= '9') { if (c >= '1' && c <= '9') {
if((c -= '1') >= closed) if ((c -= '1') >= closed)
ERROR(25); ERROR(25);
*ep++ = CBACK; *ep++ = CBACK;
*ep++ = c; *ep++ = c;
@@ -476,14 +483,13 @@ char *instring, *endbuf;
} }
} }
step(p1, p2) int step(char *p1, char *p2)
register char *p1, *p2;
{ {
register c; int c;
if (circf) { if (circf) {
loc1 = p1; loc1 = p1;
return(advance(p1, p2)); return advance(p1, p2);
} }
/* fast check for first character */ /* fast check for first character */
if (*p2==CCHR) { if (*p2==CCHR) {
@@ -493,25 +499,24 @@ register char *p1, *p2;
continue; continue;
if (advance(p1, p2)) { if (advance(p1, p2)) {
loc1 = p1; loc1 = p1;
return(1); return 1;
} }
} while (*p1++); } while (*p1++);
return(0); return 0;
} }
/* regular algorithm */ /* regular algorithm */
do { do {
if (advance(p1, p2)) { if (advance(p1, p2)) {
loc1 = p1; loc1 = p1;
return(1); return 1;
} }
} while (*p1++); } while (*p1++);
return(0); return 0;
} }
advance(lp, ep) int advance(char *lp, char *ep)
register char *lp, *ep;
{ {
register char *curlp; char *curlp;
char c; char c;
char *bbeg; char *bbeg;
int ct; int ct;
@@ -521,29 +526,29 @@ register char *lp, *ep;
case CCHR: case CCHR:
if (*ep++ == *lp++) if (*ep++ == *lp++)
continue; continue;
return(0); return 0;
case CDOT: case CDOT:
if (*lp++) if (*lp++)
continue; continue;
return(0); return 0;
case CDOL: case CDOL:
if (*lp==0) if (*lp==0)
continue; continue;
return(0); return 0;
case CEOF: case CEOF:
loc2 = lp; loc2 = lp;
return(1); return 1;
case CCL: case CCL:
c = *lp++ & 0177; c = *lp++ & 0177;
if(ISTHERE(c)) { if (ISTHERE(c)) {
ep += 16; ep += 16;
continue; continue;
} }
return(0); return 0;
case CBRA: case CBRA:
braslist[*ep++] = lp; braslist[*ep++] = lp;
continue; continue;
@@ -555,46 +560,46 @@ register char *lp, *ep;
case CCHR|RNGE: case CCHR|RNGE:
c = *ep++; c = *ep++;
getrnge(ep); getrnge(ep);
while(low--) while (low--)
if(*lp++ != c) if (*lp++ != c)
return(0); return 0;
curlp = lp; curlp = lp;
while(size--) while (size--)
if(*lp++ != c) if (*lp++ != c)
break; break;
if(size < 0) if (size < 0)
lp++; lp++;
ep += 2; ep += 2;
goto star; goto star;
case CDOT|RNGE: case CDOT|RNGE:
getrnge(ep); getrnge(ep);
while(low--) while (low--)
if(*lp++ == '\0') if (*lp++ == '\0')
return(0); return 0;
curlp = lp; curlp = lp;
while(size--) while (size--)
if(*lp++ == '\0') if (*lp++ == '\0')
break; break;
if(size < 0) if (size < 0)
lp++; lp++;
ep += 2; ep += 2;
goto star; goto star;
case CCL|RNGE: case CCL|RNGE:
getrnge(ep + 16); getrnge(ep + 16);
while(low--) { while (low--) {
c = *lp++ & 0177; c = *lp++ & 0177;
if(!ISTHERE(c)) if (!ISTHERE(c))
return(0); return 0;
} }
curlp = lp; curlp = lp;
while(size--) { while (size--) {
c = *lp++ & 0177; c = *lp++ & 0177;
if(!ISTHERE(c)) if (!ISTHERE(c))
break; break;
} }
if(size < 0) if (size < 0)
lp++; lp++;
ep += 18; /* 16 + 2 */ ep += 18; /* 16 + 2 */
goto star; goto star;
@@ -603,24 +608,24 @@ register char *lp, *ep;
bbeg = braslist[*ep]; bbeg = braslist[*ep];
ct = braelist[*ep++] - bbeg; ct = braelist[*ep++] - bbeg;
if(ecmp(bbeg, lp, ct)) { if (ecmp(bbeg, lp, ct)) {
lp += ct; lp += ct;
continue; continue;
} }
return(0); return 0;
case CBACK|STAR: case CBACK|STAR:
bbeg = braslist[*ep]; bbeg = braslist[*ep];
ct = braelist[*ep++] - bbeg; ct = braelist[*ep++] - bbeg;
curlp = lp; curlp = lp;
while(ecmp(bbeg, lp, ct)) while (ecmp(bbeg, lp, ct))
lp += ct; lp += ct;
while(lp >= curlp) { while (lp >= curlp) {
if(advance(lp, ep)) return(1); if (advance(lp, ep)) return 1;
lp -= ct; lp -= ct;
} }
return(0); return 0;
case CDOT|STAR: case CDOT|STAR:
@@ -638,43 +643,39 @@ register char *lp, *ep;
curlp = lp; curlp = lp;
do { do {
c = *lp++ & 0177; c = *lp++ & 0177;
} while(ISTHERE(c)); } while (ISTHERE(c));
ep += 16; ep += 16;
goto star; goto star;
star: star:
do { do {
if(--lp == locs) if (--lp == locs)
break; break;
if (advance(lp, ep)) if (advance(lp, ep))
return(1); return 1;
} while (lp > curlp); } while (lp > curlp);
return(0); return 0;
} }
} }
getrnge(str) void getrnge(char *str)
register char *str;
{ {
low = *str++ & 0377; low = *str++ & 0377;
size = *str == 255 ? 20000 : (*str &0377) - low; size = *str == '\377' ? 20000 : (*str & 0377) - low;
} }
ecmp(a, b, count) int ecmp(char *a, char *b, int count)
register char *a, *b;
register count;
{ {
if(a == b) /* should have been caught in compile() */ if (a == b) /* should have been caught in compile() */
error(51); error(51);
while(count--) while (count--)
if(*a++ != *b++) if (*a++ != *b++)
return(0); return 0;
return(1); return 1;
} }
yyerror(s) void yyerror(char *s)
char *s;
{ {
fprintf(stderr, "%s\n", s); fprintf(stderr, "%s\n", s);
exit(2); exit(2);

View File

@@ -1,44 +1,43 @@
/* /*
* iostat * iostat
*/ */
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h> #include <ctype.h>
#include <nlist.h> #include <nlist.h>
#include <signal.h> #include <signal.h>
#include <stdio.h>
#include <sys/types.h> #include <stdlib.h>
#include <sys/file.h> #include <string.h>
#include <sys/buf.h> #include <unistd.h>
#include <fcntl.h>
#include <sys/dk.h> #include <sys/dk.h>
#include <sys/file.h>
struct nlist nl[] = { struct nlist nl[] = {
{ "_dk_busy" }, { "_dk_busy" },
#define X_DK_BUSY 0 #define X_DK_BUSY 0
{ "_dk_xfer" }, { "_dk_xfer" },
#define X_DK_XFER 1 #define X_DK_XFER 1
{ "_dk_bytes" }, { "_dk_bytes" },
#define X_DK_BYTES 2 #define X_DK_BYTES 2
{ "_tk_nin" }, { "_tk_nin" },
#define X_TK_NIN 3 #define X_TK_NIN 3
{ "_tk_nout" }, { "_tk_nout" },
#define X_TK_NOUT 4 #define X_TK_NOUT 4
{ "_cp_time" }, { "_cp_time" },
#define X_CP_TIME 5 #define X_CP_TIME 5
{ "_hz" }, { "_hz" },
#define X_HZ 6 #define X_HZ 6
{ "_dk_ndrive" }, { "_dk_ndrive" },
#define X_DK_NDRIVE 7 #define X_DK_NDRIVE 7
{ "_dk_name" }, { "_dk_name" },
#define X_DK_NAME 8 #define X_DK_NAME 8
{ "_dk_unit" }, { "_dk_unit" },
#define X_DK_UNIT 9 #define X_DK_UNIT 9
{ 0 }, { 0 },
}; };
char **dr_name; char **dr_name;
char **dk_name; char **dk_name;
int *dr_select; int *dr_select;
int *dk_unit; int *dk_unit;
int dk_ndrive; int dk_ndrive;
@@ -46,22 +45,25 @@ int ndrives = 0;
struct { struct {
int dk_busy; int dk_busy;
long cp_time[CPUSTATES]; long cp_time[CPUSTATES];
long *dk_bytes; long *dk_bytes;
long *dk_xfer; long *dk_xfer;
long tk_nin; long tk_nin;
long tk_nout; long tk_nout;
} s, s1; } s, s1;
int mf; int mf;
int hz; int hz;
double etime; double etime;
int tohdr = 1; int tohdr = 1;
void printhdr(sig) static void read_names(void);
int sig; static void stats(int dn);
static void stat1(int o);
void printhdr(int sig)
{ {
register int i; int i;
printf("---tty---"); printf("---tty---");
for (i = 0; i < dk_ndrive; i++) for (i = 0; i < dk_ndrive; i++)
@@ -77,23 +79,21 @@ void printhdr(sig)
tohdr = 19; tohdr = 19;
} }
main(argc, argv) int main(int argc, char *argv[])
char *argv[];
{ {
extern char *ctime(); int i;
register i;
int iter; int iter;
double f1, f2; double f1, f2;
long t; long t;
char *arg, **cp, name[6], buf[BUFSIZ]; char *arg, **cp, name[6], buf[BUFSIZ];
knlist(nl); knlist(nl);
if(nl[X_DK_BUSY].n_value == 0) { if (nl[X_DK_BUSY].n_value == 0) {
printf("dk_busy not found in /vmunix namelist\n"); printf("dk_busy not found in /vmunix namelist\n");
exit(1); exit(1);
} }
mf = open("/dev/kmem", 0); mf = open("/dev/kmem", 0);
if(mf < 0) { if (mf < 0) {
printf("cannot open /dev/kmem\n"); printf("cannot open /dev/kmem\n");
exit(1); exit(1);
} }
@@ -105,19 +105,19 @@ main(argc, argv)
exit(1); exit(1);
} }
lseek(mf, (long)nl[X_DK_NDRIVE].n_value, L_SET); lseek(mf, (long)nl[X_DK_NDRIVE].n_value, L_SET);
read(mf, &dk_ndrive, sizeof (dk_ndrive)); read(mf, &dk_ndrive, sizeof(dk_ndrive));
if (dk_ndrive <= 0) { if (dk_ndrive <= 0) {
printf("dk_ndrive %d\n", dk_ndrive); printf("dk_ndrive %d\n", dk_ndrive);
exit(1); exit(1);
} }
dr_select = (int *)calloc(dk_ndrive, sizeof (int)); dr_select = (int *)calloc(dk_ndrive, sizeof(int));
dr_name = (char **)calloc(dk_ndrive, sizeof (char *)); dr_name = (char **)calloc(dk_ndrive, sizeof(char *));
dk_name = (char **)calloc(dk_ndrive, sizeof (char *)); dk_name = (char **)calloc(dk_ndrive, sizeof(char *));
dk_unit = (int *)calloc(dk_ndrive, sizeof (int)); dk_unit = (int *)calloc(dk_ndrive, sizeof(int));
s.dk_bytes = (long *)calloc(dk_ndrive, sizeof (long)); s.dk_bytes = (long *)calloc(dk_ndrive, sizeof(long));
s1.dk_bytes = (long *)calloc(dk_ndrive, sizeof (long)); s1.dk_bytes = (long *)calloc(dk_ndrive, sizeof(long));
s.dk_xfer = (long *)calloc(dk_ndrive, sizeof (long)); s.dk_xfer = (long *)calloc(dk_ndrive, sizeof(long));
s1.dk_xfer = (long *)calloc(dk_ndrive, sizeof (long)); s1.dk_xfer = (long *)calloc(dk_ndrive, sizeof(long));
for (arg = buf, i = 0; i < dk_ndrive; i++) { for (arg = buf, i = 0; i < dk_ndrive; i++) {
dr_name[i] = arg; dr_name[i] = arg;
sprintf(dr_name[i], "dk%d", i); sprintf(dr_name[i], "dk%d", i);
@@ -155,15 +155,15 @@ main(argc, argv)
signal(SIGCONT, printhdr); signal(SIGCONT, printhdr);
loop: loop:
if (--tohdr == 0) if (--tohdr == 0)
printhdr(); printhdr(0);
lseek(mf, (long)nl[X_DK_BUSY].n_value, L_SET); lseek(mf, (long)nl[X_DK_BUSY].n_value, L_SET);
read(mf, &s.dk_busy, sizeof s.dk_busy); read(mf, &s.dk_busy, sizeof s.dk_busy);
lseek(mf, (long)nl[X_DK_XFER].n_value, L_SET); lseek(mf, (long)nl[X_DK_XFER].n_value, L_SET);
read(mf, s.dk_xfer, dk_ndrive*sizeof (long)); read(mf, s.dk_xfer, dk_ndrive * sizeof(long));
lseek(mf, (long)nl[X_DK_BYTES].n_value, L_SET); lseek(mf, (long)nl[X_DK_BYTES].n_value, L_SET);
read(mf, s.dk_bytes, dk_ndrive*sizeof (long)); read(mf, s.dk_bytes, dk_ndrive * sizeof(long));
lseek(mf, (long)nl[X_TK_NIN].n_value, L_SET); lseek(mf, (long)nl[X_TK_NIN].n_value, L_SET);
read(mf, &s.tk_nin, sizeof s.tk_nin); read(mf, &s.tk_nin, sizeof s.tk_nin);
@@ -175,26 +175,34 @@ loop:
read(mf, s.cp_time, sizeof s.cp_time); read(mf, s.cp_time, sizeof s.cp_time);
for (i = 0; i < dk_ndrive; i++) { for (i = 0; i < dk_ndrive; i++) {
if (! dr_select[i]) if (!dr_select[i])
continue; continue;
#define X(fld) t = s.fld[i]; s.fld[i] -= s1.fld[i]; s1.fld[i] = t #define X(fld) \
X(dk_xfer); X(dk_bytes); t = s.fld[i]; \
s.fld[i] -= s1.fld[i]; \
s1.fld[i] = t
X(dk_xfer);
X(dk_bytes);
} }
t = s.tk_nin; s.tk_nin -= s1.tk_nin; s1.tk_nin = t; t = s.tk_nin;
t = s.tk_nout; s.tk_nout -= s1.tk_nout; s1.tk_nout = t; s.tk_nin -= s1.tk_nin;
s1.tk_nin = t;
t = s.tk_nout;
s.tk_nout -= s1.tk_nout;
s1.tk_nout = t;
etime = 0; etime = 0;
for(i=0; i<CPUSTATES; i++) { for (i = 0; i < CPUSTATES; i++) {
X(cp_time); X(cp_time);
etime += s.cp_time[i]; etime += s.cp_time[i];
} }
if (etime == 0.0) if (etime == 0.0)
etime = 1.0; etime = 1.0;
etime /= (float) hz; etime /= (float)hz;
printf("%4.0f%5.0f", s.tk_nin/etime, s.tk_nout/etime); printf("%4.0f%5.0f", s.tk_nin / etime, s.tk_nout / etime);
for (i=0; i<dk_ndrive; i++) for (i = 0; i < dk_ndrive; i++)
if (dr_select[i]) if (dr_select[i])
stats(i); stats(i);
for (i=0; i<CPUSTATES; i++) for (i = 0; i < CPUSTATES; i++)
stat1(i); stat1(i);
printf("\n"); printf("\n");
fflush(stdout); fflush(stdout);
@@ -205,42 +213,41 @@ contin:
} }
} }
stats(dn) void stats(int dn)
{ {
/* number of bytes transferred */ /* number of bytes transferred */
printf("%5.0f", (double) s.dk_bytes[dn] / 1024 / etime); printf("%5.0f", (double)s.dk_bytes[dn] / 1024 / etime);
/* number of transfers */ /* number of transfers */
printf("%4.0f", (double) s.dk_xfer[dn] / etime); printf("%4.0f", (double)s.dk_xfer[dn] / etime);
} }
stat1(o) void stat1(int o)
{ {
register i; int i;
double time; double time;
time = 0; time = 0;
for(i=0; i<CPUSTATES; i++) for (i = 0; i < CPUSTATES; i++)
time += s.cp_time[i]; time += s.cp_time[i];
if (time == 0.0) if (time == 0.0)
time = 1.0; time = 1.0;
printf(" %3.0f", 100.0 * s.cp_time[o] / time); printf(" %3.0f", 100.0 * s.cp_time[o] / time);
} }
read_names() void read_names()
{ {
char name[2]; char name[2];
register int i; int i;
lseek(mf, (long)nl[X_DK_NAME].n_value, L_SET); lseek(mf, (long)nl[X_DK_NAME].n_value, L_SET);
read(mf, dk_name, dk_ndrive * sizeof (char *)); read(mf, dk_name, dk_ndrive * sizeof(char *));
lseek(mf, (long)nl[X_DK_UNIT].n_value, L_SET); lseek(mf, (long)nl[X_DK_UNIT].n_value, L_SET);
read(mf, dk_unit, dk_ndrive * sizeof (int)); read(mf, dk_unit, dk_ndrive * sizeof(int));
for(i = 0; dk_name[i]; i++) { for (i = 0; dk_name[i]; i++) {
lseek(mf, (long)dk_name[i], L_SET); lseek(mf, (long)dk_name[i], L_SET);
read(mf, name, sizeof name); read(mf, name, sizeof name);
sprintf(dr_name[i], "%c%c%d", name[0], name[1], sprintf(dr_name[i], "%c%c%d", name[0], name[1], dk_unit[i]);
dk_unit[i]);
} }
} }

View File

@@ -1,52 +1,55 @@
#include <ctype.h>
#include <paths.h>
#include <pwd.h>
#include <setjmp.h>
#include <signal.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stdarg.h>
#include <sys/file.h>
#include <sys/param.h> #include <sys/param.h>
#include <sys/stat.h> #include <sys/stat.h>
#include <sys/file.h> #include <sys/wait.h>
#include <ctype.h>
#include <stdio.h>
#include <pwd.h>
#include <utmp.h>
#include <signal.h>
#include <setjmp.h>
#include <string.h>
#include <sysexits.h> #include <sysexits.h>
#include <paths.h>
#include <stdlib.h>
#include <time.h> #include <time.h>
#include <unistd.h> #include <unistd.h>
#include <utmp.h>
#include <fcntl.h>
/* copylet flags */ /* copylet flags */
#define REMOTE 1 /* remote mail, add rmtmsg */ #define REMOTE 1 /* remote mail, add rmtmsg */
#define ORDINARY 2 #define ORDINARY 2
#define ZAP 3 /* zap header and trailing empty line */ #define ZAP 3 /* zap header and trailing empty line */
#define FORWARD 4 #define FORWARD 4
#define LSIZE 256 #define LSIZE 256
#define MAXLET 300 /* maximum number of letters */ #define MAXLET 300 /* maximum number of letters */
#define MAILMODE 0600 /* mode of created mail */ #define MAILMODE 0600 /* mode of created mail */
char line[LSIZE];
char resp[LSIZE];
char line[LSIZE];
char resp[LSIZE];
struct let { struct let {
long adr; long adr;
char change; char change;
} let[MAXLET]; } let[MAXLET];
int nlet = 0;
char lfil[50]; int nlet = 0;
long iop; char lfil[50];
char lettmp[] = "/tmp/maXXXXX"; long iop;
char maildir[] = _PATH_MAIL; char lettmp[] = "/tmp/maXXXXX";
char mailfile[] = _PATH_MAIL "xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"; char maildir[] = _PATH_MAIL;
char dead[] = "dead.letter"; char mailfile[] = _PATH_MAIL "xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx";
char forwmsg[] = " forwarded\n"; char dead[] = "dead.letter";
FILE *tmpf; char forwmsg[] = " forwarded\n";
FILE *malf; FILE *tmpf;
char my_name[60]; FILE *malf;
char my_name[60];
int error; int error;
int changed; int changed;
int forward; int forward;
char from[] = "From "; char from[] = "From ";
int delex();
int flgf; int flgf;
int flgp; int flgp;
int delflg = 1; int delflg = 1;
@@ -54,20 +57,35 @@ int hseqno;
jmp_buf sjbuf; jmp_buf sjbuf;
int rmail; int rmail;
main(argc, argv) static void done(void);
char **argv; static void setsig(int i, sig_t f);
static void delex(int i);
static void panic(char *msg, ...);
static int any(int c, char *str);
static void printmail(int argc, char **argv);
static void bulkmail(int argc, char **argv);
static void cat(char *to, char *from1, char *from2);
static void copymt(FILE *f1, FILE *f2);
static void copylet(int n, FILE *f, int type);
static char *getarg(char *s, char *p);
static int sendmail(int n, char *name, char *fromaddr);
static void copyback(void);
static int isfrom(char *lp);
static void usage(void);
static int safefile(char *f);
int main(int argc, char **argv)
{ {
register int i; int i;
char *name; char *name;
struct passwd *pwent; struct passwd *pwent;
if (!(name = getlogin()) || !*name || !(pwent = getpwnam(name)) || if (!(name = getlogin()) || !*name || !(pwent = getpwnam(name)) || getuid() != pwent->pw_uid)
getuid() != pwent->pw_uid)
pwent = getpwuid(getuid()); pwent = getpwuid(getuid());
strncpy(my_name, pwent ? pwent->pw_name : "???", sizeof(my_name)-1); strncpy(my_name, pwent ? pwent->pw_name : "???", sizeof(my_name) - 1);
if (setjmp(sjbuf)) if (setjmp(sjbuf))
done(); done();
for (i=SIGHUP; i<=SIGTERM; i++) for (i = SIGHUP; i <= SIGTERM; i++)
setsig(i, delex); setsig(i, delex);
i = mkstemp(lettmp); i = mkstemp(lettmp);
tmpf = fdopen(i, "r+w"); tmpf = fdopen(i, "r+w");
@@ -80,38 +98,32 @@ char **argv;
unlink(lettmp); unlink(lettmp);
if (argv[0][0] == 'r') if (argv[0][0] == 'r')
rmail++; rmail++;
if (argv[0][0] != 'r' && /* no favors for rmail*/ if (argv[0][0] != 'r' && /* no favors for rmail*/
(argc == 1 || argv[1][0] == '-' && !any(argv[1][1], "rhd"))) (argc == 1 || argv[1][0] == '-' && !any(argv[1][1], "rhd")))
printmail(argc, argv); printmail(argc, argv);
else else
bulkmail(argc, argv); bulkmail(argc, argv);
done(); done();
} }
setsig(i, f) void setsig(int i, sig_t f)
int i;
sig_t f;
{ {
if (signal(i, SIG_IGN) != SIG_IGN) if (signal(i, SIG_IGN) != SIG_IGN)
signal(i, f); signal(i, f);
} }
any(c, str) int any(int c, char *str)
register int c;
register char *str;
{ {
while (*str) while (*str)
if (c == *str++) if (c == *str++)
return(1); return (1);
return(0); return (0);
} }
printmail(argc, argv) void printmail(int argc, char **argv)
char **argv;
{ {
int flg, i, j, print; int flg, i, j, print;
char *p, *getarg(); char *p;
struct stat statb; struct stat statb;
setuid(getuid()); setuid(getuid());
@@ -120,7 +132,6 @@ printmail(argc, argv)
if (argv[1][0] != '-') if (argv[1][0] != '-')
break; break;
switch (argv[1][1]) { switch (argv[1][1]) {
case 'p': case 'p':
flgp++; flgp++;
/* fall thru... */ /* fall thru... */
@@ -151,12 +162,12 @@ printmail(argc, argv)
} }
flock(fileno(malf), LOCK_SH); flock(fileno(malf), LOCK_SH);
copymt(malf, tmpf); copymt(malf, tmpf);
fclose(malf); /* implicit unlock */ fclose(malf); /* implicit unlock */
fseek(tmpf, 0L, L_SET); fseek(tmpf, 0L, L_SET);
changed = 0; changed = 0;
print = 1; print = 1;
for (i = 0; i < nlet; ) { for (i = 0; i < nlet;) {
j = forward ? i : nlet - i - 1; j = forward ? i : nlet - i - 1;
if (setjmp(sjbuf)) { if (setjmp(sjbuf)) {
print = 0; print = 0;
@@ -175,7 +186,6 @@ printmail(argc, argv)
if (fgets(resp, LSIZE, stdin) == NULL) if (fgets(resp, LSIZE, stdin) == NULL)
break; break;
switch (resp[0]) { switch (resp[0]) {
default: default:
printf("usage\n"); printf("usage\n");
case '?': case '?':
@@ -221,19 +231,18 @@ printmail(argc, argv)
if (resp[1] == '\n' || resp[1] == '\0') { if (resp[1] == '\n' || resp[1] == '\0') {
p = getenv("HOME"); p = getenv("HOME");
if (p != 0) if (p != 0)
cat(resp+1, p, "/mbox"); cat(resp + 1, p, "/mbox");
else else
cat(resp+1, "", "mbox"); cat(resp + 1, "", "mbox");
} }
for (p = resp+1; (p = getarg(lfil, p)) != NULL; ) { for (p = resp + 1; (p = getarg(lfil, p)) != NULL;) {
malf = fopen(lfil, "a"); malf = fopen(lfil, "a");
if (malf == NULL) { if (malf == NULL) {
printf("mail: %s: cannot append\n", printf("mail: %s: cannot append\n", lfil);
lfil);
flg++; flg++;
continue; continue;
} }
copylet(j, malf, resp[0]=='w'? ZAP: ORDINARY); copylet(j, malf, resp[0] == 'w' ? ZAP : ORDINARY);
fclose(malf); fclose(malf);
} }
if (flg) if (flg)
@@ -256,7 +265,7 @@ printmail(argc, argv)
print = 0; print = 0;
continue; continue;
} }
for (p = resp+1; (p = getarg(lfil, p)) != NULL; ) for (p = resp + 1; (p = getarg(lfil, p)) != NULL;)
if (!sendmail(j, lfil, my_name)) if (!sendmail(j, lfil, my_name))
flg++; flg++;
if (flg) if (flg)
@@ -268,7 +277,7 @@ printmail(argc, argv)
} }
break; break;
case '!': case '!':
system(resp+1); system(resp + 1);
printf("!\n"); printf("!\n");
print = 0; print = 0;
break; break;
@@ -281,15 +290,15 @@ printmail(argc, argv)
break; break;
} }
} }
donep: donep:
if (changed) if (changed)
copyback(); copyback();
} }
/* copy temp or whatever back to /var/mail */ /* copy temp or whatever back to /var/mail */
copyback() void copyback()
{ {
register int i, c; int i, c;
sigset_t set; sigset_t set;
int fd, new = 0; int fd, new = 0;
struct stat stbuf; struct stat stbuf;
@@ -307,7 +316,7 @@ copyback()
if (fd < 0 || malf == NULL) if (fd < 0 || malf == NULL)
panic("can't rewrite %s", lfil); panic("can't rewrite %s", lfil);
fstat(fd, &stbuf); fstat(fd, &stbuf);
if (stbuf.st_size != let[nlet].adr) { /* new mail has arrived */ if (stbuf.st_size != let[nlet].adr) { /* new mail has arrived */
fseek(malf, let[nlet].adr, L_SET); fseek(malf, let[nlet].adr, L_SET);
fseek(tmpf, let[nlet].adr, L_SET); fseek(tmpf, let[nlet].adr, L_SET);
while ((c = getc(malf)) != EOF) while ((c = getc(malf)) != EOF)
@@ -320,15 +329,14 @@ copyback()
for (i = 0; i < nlet; i++) for (i = 0; i < nlet; i++)
if (let[i].change != 'd') if (let[i].change != 'd')
copylet(i, malf, ORDINARY); copylet(i, malf, ORDINARY);
fclose(malf); /* implict unlock */ fclose(malf); /* implict unlock */
if (new) if (new)
printf("New mail has arrived.\n"); printf("New mail has arrived.\n");
(void)sigprocmask(SIG_UNBLOCK, &set, NULL); (void)sigprocmask(SIG_UNBLOCK, &set, NULL);
} }
/* copy mail (f1) to temp (f2) */ /* copy mail (f1) to temp (f2) */
copymt(f1, f2) void copymt(FILE *f1, FILE *f2)
FILE *f1, *f2;
{ {
long nextadr; long nextadr;
@@ -340,25 +348,23 @@ copymt(f1, f2)
nextadr += strlen(line); nextadr += strlen(line);
fputs(line, f2); fputs(line, f2);
} }
let[nlet].adr = nextadr; /* last plus 1 */ let[nlet].adr = nextadr; /* last plus 1 */
} }
copylet(n, f, type) void copylet(int n, FILE *f, int type)
FILE *f;
{ {
int ch; int ch;
long k; long k;
char hostname[MAXHOSTNAMELEN]; char hostname[MAXHOSTNAMELEN];
fseek(tmpf, let[n].adr, L_SET); fseek(tmpf, let[n].adr, L_SET);
k = let[n+1].adr - let[n].adr; k = let[n + 1].adr - let[n].adr;
while (k-- > 1 && (ch = getc(tmpf)) != '\n') while (k-- > 1 && (ch = getc(tmpf)) != '\n')
if (type != ZAP) if (type != ZAP)
putc(ch, f); putc(ch, f);
switch (type) { switch (type) {
case REMOTE: case REMOTE:
gethostname(hostname, sizeof (hostname)); gethostname(hostname, sizeof(hostname));
fprintf(f, " remote from %s\n", hostname); fprintf(f, " remote from %s\n", hostname);
break; break;
@@ -384,26 +390,24 @@ copylet(n, f, type)
putc(getc(tmpf), f); putc(getc(tmpf), f);
} }
isfrom(lp) int isfrom(char *lp)
register char *lp;
{ {
register char *p; char *p;
for (p = from; *p; ) for (p = from; *p;)
if (*lp++ != *p++) if (*lp++ != *p++)
return(0); return (0);
return(1); return (1);
} }
bulkmail(argc, argv) void bulkmail(int argc, char **argv)
char **argv;
{ {
char *truename; char *truename;
int first; int first;
register char *cp; char *cp;
char *newargv[1000]; char *newargv[1000];
register char **ap; char **ap;
register char **vp; char **vp;
int dflag; int dflag;
dflag = 0; dflag = 0;
@@ -418,7 +422,7 @@ char **argv;
if (!dflag) { if (!dflag) {
/* give it to sendmail, rah rah! */ /* give it to sendmail, rah rah! */
unlink(lettmp); unlink(lettmp);
ap = newargv+1; ap = newargv + 1;
if (rmail) if (rmail)
*ap-- = "-s"; *ap-- = "-s";
*ap = "-sendmail"; *ap = "-sendmail";
@@ -514,56 +518,53 @@ char **argv;
fclose(tmpf); fclose(tmpf);
} }
sendrmt(n, name) int sendrmt(int n, char *name)
char *name;
{ {
FILE *rmf, *popen(); FILE *rmf, *popen();
register char *p; char *p;
char rsys[64], cmd[64]; char rsys[64], cmd[64];
register pid; int pid;
int sts; int sts;
for (p=rsys; *name!='!'; *p++ = *name++) for (p = rsys; *name != '!'; *p++ = *name++)
if (*name=='\0') if (*name == '\0')
return(0); /* local address, no '!' */ return (0); /* local address, no '!' */
*p = '\0'; *p = '\0';
if (name[1]=='\0') { if (name[1] == '\0') {
printf("null name\n"); printf("null name\n");
return(0); return (0);
} }
skip: skip:
if ((pid = fork()) == -1) { if ((pid = fork()) == -1) {
fprintf(stderr, "mail: can't create proc for remote\n"); fprintf(stderr, "mail: can't create proc for remote\n");
return(0); return (0);
} }
if (pid) { if (pid) {
while (wait(&sts) != pid) { while (wait(&sts) != pid) {
if (wait(&sts)==-1) if (wait(&sts) == -1)
return(0); return (0);
} }
return(!sts); return (!sts);
} }
setuid(getuid()); setuid(getuid());
if (any('!', name+1)) if (any('!', name + 1))
(void)sprintf(cmd, "uux - %s!rmail \\(%s\\)", rsys, name+1); (void)sprintf(cmd, "uux - %s!rmail \\(%s\\)", rsys, name + 1);
else else
(void)sprintf(cmd, "uux - %s!rmail %s", rsys, name+1); (void)sprintf(cmd, "uux - %s!rmail %s", rsys, name + 1);
if ((rmf=popen(cmd, "w")) == NULL) if ((rmf = popen(cmd, "w")) == NULL)
exit(1); exit(1);
copylet(n, rmf, REMOTE); copylet(n, rmf, REMOTE);
exit(pclose(rmf) != 0); exit(pclose(rmf) != 0);
} }
usage() void usage()
{ {
fprintf(stderr, "Usage: mail [ -f ] people . . .\n"); fprintf(stderr, "Usage: mail [ -f ] people . . .\n");
error = EX_USAGE; error = EX_USAGE;
done(); done();
} }
sendmail(n, name, fromaddr) int sendmail(int n, char *name, char *fromaddr)
int n;
char *name, *fromaddr;
{ {
char file[256]; char file[256];
int fd; int fd;
@@ -571,30 +572,30 @@ sendmail(n, name, fromaddr)
char buf[128]; char buf[128];
off_t oldsize; off_t oldsize;
if (*name=='!') if (*name == '!')
name++; name++;
if (any('!', name)) if (any('!', name))
return (sendrmt(n, name)); return (sendrmt(n, name));
if ((pw = getpwnam(name)) == NULL) { if ((pw = getpwnam(name)) == NULL) {
printf("mail: can't send to %s\n", name); printf("mail: can't send to %s\n", name);
return(0); return (0);
} }
cat(file, maildir, name); cat(file, maildir, name);
if (!safefile(file)) if (!safefile(file))
return(0); return (0);
fd = open(file, O_WRONLY | O_CREAT | O_EXLOCK, MAILMODE); fd = open(file, O_WRONLY | O_CREAT | O_EXLOCK, MAILMODE);
if (fd >= 0) if (fd >= 0)
malf = fdopen(fd, "a"); malf = fdopen(fd, "a");
if (fd < 0 || malf == NULL) { if (fd < 0 || malf == NULL) {
close(fd); close(fd);
printf("mail: %s: cannot append\n", file); printf("mail: %s: cannot append\n", file);
return(0); return (0);
} }
fchown(fd, pw->pw_uid, pw->pw_gid); fchown(fd, pw->pw_uid, pw->pw_gid);
oldsize = ftell(malf); oldsize = ftell(malf);
(void)sprintf(buf, "%s@%ld\n", name, oldsize); (void)sprintf(buf, "%s@%ld\n", name, oldsize);
copylet(n, malf, ORDINARY); /* Try to deliver the message */ copylet(n, malf, ORDINARY); /* Try to deliver the message */
/* If there is any error during the delivery of the message, /* If there is any error during the delivery of the message,
* the mail file may be corrupted (incomplete last line) and * the mail file may be corrupted (incomplete last line) and
@@ -610,13 +611,13 @@ sendmail(n, name, fromaddr)
printf("mail: %s: cannot append\n", file); printf("mail: %s: cannot append\n", file);
ftruncate(fd, oldsize); ftruncate(fd, oldsize);
fclose(malf); fclose(malf);
return(0); return (0);
} }
fclose(malf); fclose(malf);
return(1); return (1);
} }
delex(i) void delex(int i)
{ {
sigset_t sigt; sigset_t sigt;
@@ -634,60 +635,56 @@ delex(i)
done(); done();
} }
done() void done()
{ {
unlink(lettmp); unlink(lettmp);
exit(error); exit(error);
} }
cat(to, from1, from2) void cat(char *to, char *from1, char *from2)
char *to, *from1, *from2;
{ {
register char *cp, *dp; char *cp, *dp;
cp = to; cp = to;
for (dp = from1; *cp = *dp++; cp++) for (dp = from1; (*cp = *dp++); cp++)
; ;
for (dp = from2; *cp++ = *dp++; ) for (dp = from2; (*cp++ = *dp++);)
; ;
} }
/* copy p... into s, update p */ /* copy p... into s, update p */
char * char *getarg(char *s, char *p)
getarg(s, p)
register char *s, *p;
{ {
while (*p == ' ' || *p == '\t') while (*p == ' ' || *p == '\t')
p++; p++;
if (*p == '\n' || *p == '\0') if (*p == '\n' || *p == '\0')
return(NULL); return (NULL);
while (*p != ' ' && *p != '\t' && *p != '\n' && *p != '\0') while (*p != ' ' && *p != '\t' && *p != '\n' && *p != '\0')
*s++ = *p++; *s++ = *p++;
*s = '\0'; *s = '\0';
return(p); return (p);
} }
safefile(f) int safefile(char *f)
char *f;
{ {
struct stat statb; struct stat statb;
if (lstat(f, &statb) < 0) if (lstat(f, &statb) < 0)
return (1); return (1);
if (statb.st_nlink != 1 || (statb.st_mode & S_IFMT) == S_IFLNK) { if (statb.st_nlink != 1 || (statb.st_mode & S_IFMT) == S_IFLNK) {
fprintf(stderr, fprintf(stderr, "mail: %s has more than one link or is a symbolic link\n", f);
"mail: %s has more than one link or is a symbolic link\n",
f);
return (0); return (0);
} }
return (1); return (1);
} }
panic(msg, a1, a2, a3) void panic(char *msg, ...)
char *msg;
{ {
va_list args;
va_start(args, msg);
fprintf(stderr, "mail: "); fprintf(stderr, "mail: ");
fprintf(stderr, msg, a1, a2, a3); vfprintf(stderr, msg, args);
fprintf(stderr, "\n"); fprintf(stderr, "\n");
va_end(args);
done(); done();
} }

View File

@@ -133,11 +133,9 @@ struct psout *outargs; /* info for first npr processes */
* know that r(hp|up|mt) are unlikely as are different mem's, * know that r(hp|up|mt) are unlikely as are different mem's,
* floppy, null, tty, etc. * floppy, null, tty, etc.
*/ */
void void maybetty(char *cp)
maybetty(cp)
register char *cp;
{ {
register struct ttys *dp; struct ttys *dp;
struct stat stb; struct stat stb;
/* Allow only terminal devices. */ /* Allow only terminal devices. */
@@ -167,11 +165,10 @@ maybetty(cp)
dp->ttyd = -1; dp->ttyd = -1;
} }
void void getdev()
getdev()
{ {
register DIR *df; DIR *df;
register struct direct *dbuf; struct direct *dbuf;
if (chdir("/dev") < 0) { if (chdir("/dev") < 0) {
perror("/dev"); perror("/dev");
@@ -186,11 +183,10 @@ getdev()
closedir(df); closedir(df);
} }
char * char *gettty()
gettty()
{ {
register int tty_step; int tty_step;
register char *p; char *p;
if (u.u_ttyp) { if (u.u_ttyp) {
for (tty_step = 0; tty_step < nttys; ++tty_step) { for (tty_step = 0; tty_step < nttys; ++tty_step) {
@@ -205,9 +201,7 @@ gettty()
return("?"); return("?");
} }
unsigned unsigned getptr(off_t adr)
getptr(adr)
off_t adr;
{ {
unsigned ptr = 0; unsigned ptr = 0;
@@ -217,21 +211,16 @@ getptr(adr)
return ptr; return ptr;
} }
int int getbyte(off_t adr)
getbyte(adr)
register char *adr;
{ {
char b; char b;
if (lseek(file, (off_t) adr, 0) == (off_t) -1 || read (file, &b, 1) < 1) if (lseek(file, adr, 0) == (off_t) -1 || read (file, &b, 1) < 1)
return(0); return(0);
return((unsigned) b); return((unsigned) b);
} }
int int getcmd(struct psout *a, off_t addr)
getcmd(a, addr)
off_t addr;
register struct psout *a;
{ {
/* amount of top of stack to examine for args */ /* amount of top of stack to examine for args */
#define ARGLIST (DEV_BSIZE * 2) #define ARGLIST (DEV_BSIZE * 2)
@@ -337,16 +326,14 @@ getcmd(a, addr)
* Save command data to outargs[]. * Save command data to outargs[].
* Return 1 on success. * Return 1 on success.
*/ */
int int savcom(int puid)
savcom(puid)
int puid;
{ {
char *tp; char *tp;
off_t addr; off_t addr;
off_t daddr, saddr; off_t daddr, saddr;
register struct psout *a; struct psout *a;
register struct proc *procp = mproc; struct proc *procp = mproc;
register struct user *up = &u; struct user *up = &u;
long txtsiz, datsiz, stksiz; long txtsiz, datsiz, stksiz;
if (procp->p_flag & SLOAD) { if (procp->p_flag & SLOAD) {
@@ -409,11 +396,11 @@ savcom(puid)
return getcmd(a, saddr); return getcmd(a, saddr);
} }
int int pscomp(const void *a1, const void *a2)
pscomp(x1, x2)
register struct psout *x1, *x2;
{ {
register int c; const struct psout *x1 = a1;
const struct psout *x2 = a2;
int c;
c = (x1)->o_ttyd - (x2)->o_ttyd; c = (x1)->o_ttyd - (x2)->o_ttyd;
if (c == 0) if (c == 0)
@@ -424,12 +411,10 @@ pscomp(x1, x2)
/* /*
* fixup figures out everybodys name and sorts into a nice order. * fixup figures out everybodys name and sorts into a nice order.
*/ */
void void fixup(int np)
fixup(np)
register int np;
{ {
register int i; int i;
register struct passwd *pw; struct passwd *pw;
if (uflg) { if (uflg) {
setpwent(); setpwent();
@@ -451,10 +436,11 @@ fixup(np)
qsort(outargs, np, sizeof (outargs[0]), pscomp); qsort(outargs, np, sizeof (outargs[0]), pscomp);
} }
int int wchancomp(const void *a1, const void *a2)
wchancomp(x1, x2)
register WCHAN *x1, *x2;
{ {
const WCHAN *x1 = a1;
const WCHAN *x2 = a2;
if (x1->caddr > x2->caddr) if (x1->caddr > x2->caddr)
return(1); return(1);
else if (x1->caddr == x2->caddr) else if (x1->caddr == x2->caddr)
@@ -463,13 +449,10 @@ wchancomp(x1, x2)
return(-1); return(-1);
} }
void void addchan(char *name, unsigned caddr)
addchan(name, caddr)
char *name;
unsigned caddr;
{ {
static int left = 0; static int left = 0;
register WCHAN *wp; WCHAN *wp;
if (left == 0) { if (left == 0) {
if (wchand) { if (wchand) {
@@ -493,17 +476,15 @@ addchan(name, caddr)
wp->caddr = caddr; wp->caddr = caddr;
} }
char * char *getchan(caddr_t chan)
getchan(chan)
register unsigned int chan;
{ {
register int i; int i;
register char *prevsym; char *prevsym;
prevsym = ""; prevsym = "";
if (chan) { if (chan) {
for (i = 0; i < nchans; i++) { for (i = 0; i < nchans; i++) {
if (wchand[i].caddr > chan) if (wchand[i].caddr > (unsigned) chan)
return (prevsym); return (prevsym);
prevsym = wchand[i].cname; prevsym = wchand[i].cname;
} }
@@ -511,17 +492,13 @@ getchan(chan)
return(prevsym); return(prevsym);
} }
void void perrexit(char *msg)
perrexit(msg)
char *msg;
{ {
perror(msg); perror(msg);
exit(1); exit(1);
} }
void void openfiles(int argc, char **argv)
openfiles(argc, argv)
char **argv;
{ {
if (kflg) if (kflg)
kmemf = argc > 1 ? argv[1] : _PATH_CORE; kmemf = argc > 1 ? argv[1] : _PATH_CORE;
@@ -541,10 +518,7 @@ openfiles(argc, argv)
perrexit(swapf); perrexit(swapf);
} }
void void getkvars(int argc, char **argv)
getkvars(argc,argv)
int argc;
char **argv;
{ {
knlist(nl); knlist(nl);
if (! nflg) { if (! nflg) {
@@ -581,9 +555,7 @@ getkvars(argc,argv)
read(kmem, (char *)&hz, sizeof(hz)); read(kmem, (char *)&hz, sizeof(hz));
} }
void void ptime(struct psout *a)
ptime(a)
struct psout *a;
{ {
time_t tm; time_t tm;
@@ -595,9 +567,7 @@ ptime(a)
char *uhdr = "USER PID NICE SZ TTY TIME"; char *uhdr = "USER PID NICE SZ TTY TIME";
void void upr(struct psout *a)
upr(a)
register struct psout *a;
{ {
printf("%-8.8s%6u%4d%4d %-3.3s",a->o_uname,a->o_pid,a->o_nice,a->o_size,a->o_tty); printf("%-8.8s%6u%4d%4d %-3.3s",a->o_uname,a->o_pid,a->o_nice,a->o_size,a->o_tty);
ptime(a); ptime(a);
@@ -605,9 +575,7 @@ upr(a)
char *shdr = " PID TTY TIME"; char *shdr = " PID TTY TIME";
void void spr(struct psout *a)
spr (a)
register struct psout *a;
{ {
printf("%6u %-3.3s",a->o_pid,a->o_tty); printf("%6u %-3.3s",a->o_pid,a->o_tty);
ptime(a); ptime(a);
@@ -615,9 +583,7 @@ spr (a)
char *lhdr = " F S UID PID PPID CPU PRI NICE ADDR SZ WCHAN TTY TIME"; char *lhdr = " F S UID PID PPID CPU PRI NICE ADDR SZ WCHAN TTY TIME";
void void lpr(struct psout *a)
lpr(a)
register struct psout *a;
{ {
static char clist[] = "0SWRIZT"; static char clist[] = "0SWRIZT";
@@ -636,10 +602,9 @@ lpr(a)
ptime(a); ptime(a);
} }
void void printhdr()
printhdr()
{ {
register char *hdr, *cmdstr = " COMMAND"; char *hdr, *cmdstr = " COMMAND";
if (rflg) if (rflg)
return; return;
@@ -656,14 +621,12 @@ printhdr()
fflush(stdout); fflush(stdout);
} }
int int main(int argc, char **argv)
main (argc, argv)
char **argv;
{ {
int uid, euid, puid, nread; int uid, euid, puid, nread;
register int i, j; int i, j;
char *ap; char *ap;
register struct proc *procp; struct proc *procp;
if ((ioctl(fileno(stdout), TIOCGWINSZ, &ws) != -1 && if ((ioctl(fileno(stdout), TIOCGWINSZ, &ws) != -1 &&
ioctl(fileno(stderr), TIOCGWINSZ, &ws) != -1 && ioctl(fileno(stderr), TIOCGWINSZ, &ws) != -1 &&
@@ -803,8 +766,8 @@ main (argc, argv)
} }
fixup(npr); fixup(npr);
for (i = 0; i < npr; i++) { for (i = 0; i < npr; i++) {
register int cmdwidth = twidth - cmdstart - 2; int cmdwidth = twidth - cmdstart - 2;
register struct psout *a = &outargs[i]; struct psout *a = &outargs[i];
if (rflg) { if (rflg) {
if (write(1, (char *) a, sizeof (*a)) != sizeof (*a)) if (write(1, (char *) a, sizeof (*a)) != sizeof (*a))

View File

@@ -3,41 +3,39 @@
* All rights reserved. The Berkeley software License Agreement * All rights reserved. The Berkeley software License Agreement
* specifies the terms and conditions for redistribution. * specifies the terms and conditions for redistribution.
*/ */
#include <stdio.h>
#include <string.h>
#include <pwd.h>
#include <syslog.h>
#include <stdlib.h>
#include <unistd.h>
#include <paths.h>
#include <sys/types.h> #include <sys/types.h>
#include <sys/time.h> #include <sys/time.h>
#include <sys/resource.h> #include <sys/resource.h>
#include <grp.h> #include <grp.h>
#include <paths.h>
#include <pwd.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <syslog.h>
#include <unistd.h>
char userbuf[64] = "USER="; char userbuf[64] = "USER=";
char homebuf[128] = "HOME="; char homebuf[128] = "HOME=";
char shellbuf[128] = "SHELL="; char shellbuf[128] = "SHELL=";
char pathbuf[128] = "PATH=" _PATH_STDPATH; char pathbuf[128] = "PATH=" _PATH_STDPATH;
char *cleanenv[] = { userbuf, homebuf, shellbuf, pathbuf, 0, 0 }; char *cleanenv[] = { userbuf, homebuf, shellbuf, pathbuf, 0, 0 };
char *user = "root"; char *user = "root";
char *shell = _PATH_BSHELL; char *shell = _PATH_BSHELL;
int fulllogin; int fulllogin;
int fastlogin; int fastlogin;
extern char **environ; struct passwd *pwd;
struct passwd *pwd;
setenvv(ename, eval, buf) void setenvv(char *ename, char *eval, char *buf)
char *ename, *eval, *buf;
{ {
register char *cp, *dp; char *cp, *dp;
register char **ep = environ; char **ep = environ;
/* /*
* this assumes an environment variable "ename" already exists * this assumes an environment variable "ename" already exists
*/ */
while (dp = *ep++) { while ((dp = *ep++)) {
for (cp = ename; *cp == *dp && *cp; cp++, dp++) for (cp = ename; *cp == *dp && *cp; cp++, dp++)
continue; continue;
if (*cp == 0 && (*dp == '=' || *dp == 0)) { if (*cp == 0 && (*dp == '=' || *dp == 0)) {
@@ -48,14 +46,12 @@ setenvv(ename, eval, buf)
} }
} }
char * char *getenvv(char *ename)
getenvv(ename)
char *ename;
{ {
register char *cp, *dp; char *cp, *dp;
register char **ep = environ; char **ep = environ;
while (dp = *ep++) { while ((dp = *ep++)) {
for (cp = ename; *cp == *dp && *cp; cp++, dp++) for (cp = ename; *cp == *dp && *cp; cp++, dp++)
continue; continue;
if (*cp == 0 && (*dp == '=' || *dp == 0)) if (*cp == 0 && (*dp == '=' || *dp == 0))
@@ -64,14 +60,12 @@ getenvv(ename)
return ((char *)0); return ((char *)0);
} }
main(argc,argv) int main(int argc, char *argv[])
int argc;
char *argv[];
{ {
char *password; char *password;
char buf[1000]; char buf[1000];
FILE *fp; FILE *fp;
register char *p; char *p;
openlog("su", LOG_ODELAY, LOG_AUTH); openlog("su", LOG_ODELAY, LOG_AUTH);
@@ -103,30 +97,28 @@ again:
* Only allow those in group zero to su to root. * Only allow those in group zero to su to root.
*/ */
if (pwd->pw_uid == 0) { if (pwd->pw_uid == 0) {
struct group *gr; struct group *gr;
int i; int i;
if ((gr = getgrgid(0)) != NULL) { if ((gr = getgrgid(0)) != NULL) {
for (i = 0; gr->gr_mem[i] != NULL; i++) for (i = 0; gr->gr_mem[i] != NULL; i++)
if (strcmp(buf, gr->gr_mem[i]) == 0) if (strcmp(buf, gr->gr_mem[i]) == 0)
goto userok; goto userok;
fprintf(stderr, "You do not have permission to su %s\n", fprintf(stderr, "You do not have permission to su %s\n", user);
user);
exit(1); exit(1);
} }
userok: userok:
setpriority(PRIO_PROCESS, 0, -2); setpriority(PRIO_PROCESS, 0, -2);
} }
#define Getlogin() (((p = getlogin()) && *p) ? p : buf) #define Getlogin() (((p = getlogin()) && *p) ? p : buf)
if (pwd->pw_passwd[0] == '\0' || getuid() == 0) if (pwd->pw_passwd[0] == '\0' || getuid() == 0)
goto ok; goto ok;
password = getpass("Password:"); password = getpass("Password:");
if (strcmp(pwd->pw_passwd, crypt(password, pwd->pw_passwd)) != 0) { if (strcmp(pwd->pw_passwd, crypt(password, pwd->pw_passwd)) != 0) {
fprintf(stderr, "Sorry\n"); fprintf(stderr, "Sorry\n");
if (pwd->pw_uid == 0) { if (pwd->pw_uid == 0) {
syslog(LOG_CRIT, "BAD SU %s on %s", syslog(LOG_CRIT, "BAD SU %s on %s", Getlogin(), ttyname(2));
Getlogin(), ttyname(2));
} }
exit(2); exit(2);
} }

View File

@@ -3,93 +3,98 @@
* All rights reserved. The Berkeley software License Agreement * All rights reserved. The Berkeley software License Agreement
* specifies the terms and conditions for redistribution. * specifies the terms and conditions for redistribution.
*/ */
#include <ctype.h>
#include <nlist.h>
#include <stdio.h> #include <stdio.h>
#include <stdlib.h> #include <stdlib.h>
#include <string.h> #include <string.h>
#include <ctype.h> #include <unistd.h>
#include <nlist.h> #include <fcntl.h>
#include <time.h>
#include <sys/param.h> #include <signal.h>
#include <sys/file.h>
#include <sys/vm.h>
#include <sys/dk.h>
#include <sys/buf.h>
#include <sys/dir.h> #include <sys/dir.h>
#include <sys/inode.h> #include <sys/dk.h>
#include <sys/file.h>
#include <sys/namei.h> #include <sys/namei.h>
#include <sys/vm.h>
#include <machine/machparam.h>
struct nlist nl[] = { struct nlist nl[] = {
#define X_CPTIME 0 #define X_CPTIME 0
{ "_cp_time" }, { "_cp_time" },
#define X_RATE 1 #define X_RATE 1
{ "_rate" }, { "_rate" },
#define X_TOTAL 2 #define X_TOTAL 2
{ "_total" }, { "_total" },
#define X_FORKSTAT 3 #define X_FORKSTAT 3
{ "_forkstat" }, { "_forkstat" },
#define X_SUM 4 #define X_SUM 4
{ "_sum" }, { "_sum" },
#define X_BOOTTIME 5 #define X_BOOTTIME 5
{ "_boottime" }, { "_boottime" },
#define X_DKXFER 6 #define X_DKXFER 6
{ "_dk_xfer" }, { "_dk_xfer" },
#define X_HZ 7 #define X_HZ 7
{ "_hz" }, { "_hz" },
#define X_NCHSTATS 8 #define X_NCHSTATS 8
{ "_nchstats" }, { "_nchstats" },
#define X_DK_NDRIVE 9 #define X_DK_NDRIVE 9
{ "_dk_ndrive" }, { "_dk_ndrive" },
#define X_DK_NAME 10 #define X_DK_NAME 10
{ "_dk_name" }, { "_dk_name" },
#define X_DK_UNIT 11 #define X_DK_UNIT 11
{ "_dk_unit" }, { "_dk_unit" },
#define X_FREEMEM 12 #define X_FREEMEM 12
{ "_freemem" }, { "_freemem" },
{ "" }, { "" },
}; };
char **dk_name; char **dk_name;
int *dk_unit; int *dk_unit;
size_t pfree; size_t pfree;
int pflag; int pflag;
char **dr_name; char **dr_name;
int *dr_select; int *dr_select;
int dk_ndrive; int dk_ndrive;
int ndrives = 0; int ndrives = 0;
char *defdrives[] = { "sd0", 0 }; char *defdrives[] = { "sd0", 0 };
double stat1(); double stat1();
int hz; int hz;
struct { struct {
int busy; int busy;
long time[CPUSTATES]; long time[CPUSTATES];
long *xfer; long *xfer;
struct vmrate Rate; struct vmrate Rate;
struct vmtotal Total; struct vmtotal Total;
struct vmsum Sum; struct vmsum Sum;
struct forkstat Forkstat; struct forkstat Forkstat;
unsigned rectime; unsigned rectime;
unsigned pgintime; unsigned pgintime;
} s, s1, z; } s, s1, z;
#define rate s.Rate
#define total s.Total
#define sum s.Sum
#define forkstat s.Forkstat
struct vmsum osum; #define rate s.Rate
double etime; #define total s.Total
int mf; #define sum s.Sum
time_t now, boottime; #define forkstat s.Forkstat
struct vmsum osum;
double etime;
int mf;
time_t now, boottime;
int lines = 1; int lines = 1;
void printhdr(sig) static void dotimes(void);
int sig; static void doforkst(void);
static void dosum(void);
static void read_names(void);
static void dointr(long nintv);
static void stats(int dn);
void printhdr(int sig)
{ {
register int i, j; int i, j;
if (pflag) if (pflag)
printf("-procs- -----memory----- -swap- "); printf("-procs- -----memory----- -swap- ");
@@ -108,8 +113,7 @@ void printhdr(sig)
for (i = 0; i < dk_ndrive; i++) for (i = 0; i < dk_ndrive; i++)
if (dr_select[i]) if (dr_select[i])
printf("%c%c%c ", printf("%c%c%c ", dr_name[i][0], dr_name[i][1], dr_name[i][2]);
dr_name[i][0], dr_name[i][1], dr_name[i][2]);
printf(" in sy"); printf(" in sy");
if (pflag) if (pflag)
printf(" tr"); printf(" tr");
@@ -120,65 +124,61 @@ void printhdr(sig)
lines = 19; lines = 19;
} }
main(argc, argv) int main(int argc, char **argv)
int argc;
char **argv;
{ {
extern char *ctime(); int i;
register i;
int iter, iflag = 0; int iter, iflag = 0;
long nintv, t; long nintv, t;
char *arg, **cp, buf[BUFSIZ]; char *arg, **cp, buf[BUFSIZ];
knlist(nl); knlist(nl);
if(nl[0].n_value == 0) { if (nl[0].n_value == 0) {
fprintf(stderr, "no /vmunix namelist\n"); fprintf(stderr, "no /vmunix namelist\n");
exit(1); exit(1);
} }
mf = open("/dev/kmem", 0); mf = open("/dev/kmem", 0);
if(mf < 0) { if (mf < 0) {
fprintf(stderr, "cannot open /dev/kmem\n"); fprintf(stderr, "cannot open /dev/kmem\n");
exit(1); exit(1);
} }
iter = 0; iter = 0;
argc--, argv++; argc--, argv++;
while (argc>0 && argv[0][0]=='-') { while (argc > 0 && argv[0][0] == '-') {
char *cp = *argv++; char *cp = *argv++;
argc--; argc--;
while (*++cp) switch (*cp) { while (*++cp)
switch (*cp) {
case 't':
dotimes();
exit(0);
case 't': case 'z':
dotimes(); close(mf);
exit(0); mf = open("/dev/kmem", 2);
lseek(mf, (long)nl[X_SUM].n_value, L_SET);
write(mf, &z.Sum, sizeof z.Sum);
exit(0);
case 'z': case 'f':
close(mf); doforkst();
mf = open("/dev/kmem", 2); exit(0);
lseek(mf, (long)nl[X_SUM].n_value, L_SET);
write(mf, &z.Sum, sizeof z.Sum);
exit(0);
case 'f': case 's':
doforkst(); dosum();
exit(0); exit(0);
case 's': case 'i':
dosum(); iflag++;
exit(0); break;
case 'i': case 'p':
iflag++; pflag++;
break; break;
case 'p': default:
pflag++; fprintf(stderr, "usage: vmstat [ -fsiptz ] [ interval ] [ count]\n");
break; exit(1);
}
default:
fprintf(stderr,
"usage: vmstat [ -fsiptz ] [ interval ] [ count]\n");
exit(1);
}
} }
lseek(mf, (long)nl[X_BOOTTIME].n_value, L_SET); lseek(mf, (long)nl[X_BOOTTIME].n_value, L_SET);
read(mf, &boottime, sizeof boottime); read(mf, &boottime, sizeof boottime);
@@ -189,18 +189,18 @@ main(argc, argv)
exit(1); exit(1);
} }
lseek(mf, (long)nl[X_DK_NDRIVE].n_value, L_SET); lseek(mf, (long)nl[X_DK_NDRIVE].n_value, L_SET);
read(mf, &dk_ndrive, sizeof (dk_ndrive)); read(mf, &dk_ndrive, sizeof(dk_ndrive));
if (dk_ndrive <= 0) { if (dk_ndrive <= 0) {
fprintf(stderr, "dk_ndrive %d\n", dk_ndrive); fprintf(stderr, "dk_ndrive %d\n", dk_ndrive);
exit(1); exit(1);
} }
dr_select = (int *)calloc(dk_ndrive, sizeof (int)); dr_select = (int *)calloc(dk_ndrive, sizeof(int));
dr_name = (char **)calloc(dk_ndrive, sizeof (char *)); dr_name = (char **)calloc(dk_ndrive, sizeof(char *));
dk_name = (char **)calloc(dk_ndrive, sizeof (char *)); dk_name = (char **)calloc(dk_ndrive, sizeof(char *));
dk_unit = (int *)calloc(dk_ndrive, sizeof (int)); dk_unit = (int *)calloc(dk_ndrive, sizeof(int));
#define allocate(e, t) \ #define allocate(e, t) \
s./**/e = (t *)calloc(dk_ndrive, sizeof (t)); \ s./**/ e = (t *)calloc(dk_ndrive, sizeof(t)); \
s1./**/e = (t *)calloc(dk_ndrive, sizeof (t)); s1./**/ e = (t *)calloc(dk_ndrive, sizeof(t));
allocate(xfer, long); allocate(xfer, long);
for (arg = buf, i = 0; i < dk_ndrive; i++) { for (arg = buf, i = 0; i < dk_ndrive; i++) {
dr_name[i] = arg; dr_name[i] = arg;
@@ -210,9 +210,8 @@ main(argc, argv)
read_names(); read_names();
time(&now); time(&now);
nintv = now - boottime; nintv = now - boottime;
if (nintv <= 0 || nintv > 60L*60L*24L*365L*10L) { if (nintv <= 0 || nintv > 60L * 60L * 24L * 365L * 10L) {
fprintf(stderr, fprintf(stderr, "Time makes no sense... namelist must be wrong.\n");
"Time makes no sense... namelist must be wrong.\n");
exit(1); exit(1);
} }
if (iflag) { if (iflag) {
@@ -257,11 +256,11 @@ main(argc, argv)
signal(SIGCONT, printhdr); signal(SIGCONT, printhdr);
loop: loop:
if (--lines == 0) if (--lines == 0)
printhdr(); printhdr(0);
lseek(mf, (long)nl[X_CPTIME].n_value, L_SET); lseek(mf, (long)nl[X_CPTIME].n_value, L_SET);
read(mf, s.time, sizeof s.time); read(mf, s.time, sizeof s.time);
lseek(mf, (long)nl[X_DKXFER].n_value, L_SET); lseek(mf, (long)nl[X_DKXFER].n_value, L_SET);
read(mf, s.xfer, dk_ndrive * sizeof (long)); read(mf, s.xfer, dk_ndrive * sizeof(long));
if (nintv != 1) { if (nintv != 1) {
lseek(mf, (long)nl[X_SUM].n_value, L_SET); lseek(mf, (long)nl[X_SUM].n_value, L_SET);
@@ -287,18 +286,18 @@ loop:
lseek(mf, (long)nl[X_SUM].n_value, L_SET); lseek(mf, (long)nl[X_SUM].n_value, L_SET);
read(mf, &sum, sizeof sum); read(mf, &sum, sizeof sum);
etime = 0; etime = 0;
for (i=0; i < dk_ndrive; i++) { for (i = 0; i < dk_ndrive; i++) {
t = s.xfer[i]; t = s.xfer[i];
s.xfer[i] -= s1.xfer[i]; s.xfer[i] -= s1.xfer[i];
s1.xfer[i] = t; s1.xfer[i] = t;
} }
for (i=0; i < CPUSTATES; i++) { for (i = 0; i < CPUSTATES; i++) {
t = s.time[i]; t = s.time[i];
s.time[i] -= s1.time[i]; s.time[i] -= s1.time[i];
s1.time[i] = t; s1.time[i] = t;
etime += s.time[i]; etime += s.time[i];
} }
if(etime == 0.) if (etime == 0.)
etime = 1.; etime = 1.;
printf("%2d%2d%2d", total.t_rq, total.t_dw, total.t_sw); printf("%2d%2d%2d", total.t_rq, total.t_dw, total.t_sw);
@@ -306,14 +305,13 @@ loop:
* We don't use total.t_free because it slops around too much * We don't use total.t_free because it slops around too much
* within this kernel * within this kernel
*/ */
printf("%7d", total.t_avm); printf("%7ld", total.t_avm);
if (pflag) if (pflag)
printf("%4d", printf("%4ld", total.t_avm ? (total.t_avmtxt * 100) / total.t_avm : 0);
total.t_avm ? (total.t_avmtxt * 100) / total.t_avm : 0);
printf("%6d", pfree); printf("%6d", pfree);
if (pflag) { if (pflag) {
printf("%4d%3d ", rate.v_swpin / nintv, rate.v_swpout / nintv); printf("%4ld%3ld ", rate.v_swpin / nintv, rate.v_swpout / nintv);
} }
etime /= (float)hz; etime /= (float)hz;
@@ -321,14 +319,14 @@ loop:
if (dr_select[i]) if (dr_select[i])
stats(i); stats(i);
} }
printf("%5d%4d", rate.v_intr/nintv, rate.v_syscall/nintv); printf("%5ld%4ld", rate.v_intr / nintv, rate.v_syscall / nintv);
if (pflag) if (pflag)
printf("%4d", rate.v_trap / nintv); printf("%4ld", rate.v_trap / nintv);
printf("%4d", rate.v_swtch / nintv); printf("%4ld", rate.v_swtch / nintv);
for(i=0; i<CPUSTATES; i++) { for (i = 0; i < CPUSTATES; i++) {
float f = stat1(i); float f = stat1(i);
if (! pflag && i == 0) { /* US+NI */ if (!pflag && i == 0) { /* US+NI */
i++; i++;
f += stat1(i); f += stat1(i);
} }
@@ -337,108 +335,104 @@ loop:
printf("\n"); printf("\n");
fflush(stdout); fflush(stdout);
nintv = 1; nintv = 1;
if (--iter &&argc > 0) { if (--iter && argc > 0) {
sleep(atoi(argv[0])); sleep(atoi(argv[0]));
goto loop; goto loop;
} }
} }
dotimes() void dotimes()
{ {
printf("page in/out/reclamation is not applicable to 2.11BSD\n"); printf("page in/out/reclamation is not applicable to 2.11BSD\n");
} }
dosum() void dosum()
{ {
struct nchstats nchstats; struct nchstats nchstats;
long nchtotal; long nchtotal;
lseek(mf, (long)nl[X_SUM].n_value, L_SET); lseek(mf, (long)nl[X_SUM].n_value, L_SET);
read(mf, &sum, sizeof sum); read(mf, &sum, sizeof sum);
printf("%9d swap ins\n", sum.v_swpin); printf("%9ld swap ins\n", sum.v_swpin);
printf("%9d swap outs\n", sum.v_swpout); printf("%9ld swap outs\n", sum.v_swpout);
printf("%9d kbytes swapped in\n", sum.v_kbin); printf("%9ld kbytes swapped in\n", sum.v_kbin);
printf("%9d kbytes swapped out\n", sum.v_kbout); printf("%9ld kbytes swapped out\n", sum.v_kbout);
printf("%9d cpu context switches\n", sum.v_swtch); printf("%9ld cpu context switches\n", sum.v_swtch);
printf("%9d device interrupts\n", sum.v_intr); printf("%9ld device interrupts\n", sum.v_intr);
printf("%9d software interrupts\n", sum.v_soft); printf("%9ld software interrupts\n", sum.v_soft);
printf("%9d traps\n", sum.v_trap); printf("%9ld traps\n", sum.v_trap);
printf("%9d system calls\n", sum.v_syscall); printf("%9ld system calls\n", sum.v_syscall);
#define nz(x) ((x) ? (x) : 1) #define nz(x) ((x) ? (x) : 1)
lseek(mf, (long)nl[X_NCHSTATS].n_value, 0); lseek(mf, (long)nl[X_NCHSTATS].n_value, 0);
read(mf, &nchstats, sizeof nchstats); read(mf, &nchstats, sizeof nchstats);
nchtotal = nchstats.ncs_goodhits + nchstats.ncs_badhits + nchtotal = nchstats.ncs_goodhits + nchstats.ncs_badhits + nchstats.ncs_falsehits +
nchstats.ncs_falsehits + nchstats.ncs_miss + nchstats.ncs_long; nchstats.ncs_miss + nchstats.ncs_long;
printf("%9d total name lookups", nchtotal); printf("%9ld total name lookups", nchtotal);
printf(" (cache hits %d%% system %d%% per-process)\n", printf(" (cache hits %ld%% system %ld%% per-process)\n",
nchstats.ncs_goodhits * 100 / nz(nchtotal), nchstats.ncs_goodhits * 100 / nz(nchtotal), nchstats.ncs_pass2 * 100 / nz(nchtotal));
nchstats.ncs_pass2 * 100 / nz(nchtotal)); printf("%9s badhits %ld, falsehits %ld, toolong %ld\n", "", nchstats.ncs_badhits,
printf("%9s badhits %d, falsehits %d, toolong %d\n", "", nchstats.ncs_falsehits, nchstats.ncs_long);
nchstats.ncs_badhits, nchstats.ncs_falsehits, nchstats.ncs_long);
} }
doforkst() void doforkst()
{ {
lseek(mf, (long)nl[X_FORKSTAT].n_value, L_SET); lseek(mf, (long)nl[X_FORKSTAT].n_value, L_SET);
read(mf, &forkstat, sizeof forkstat); read(mf, &forkstat, sizeof forkstat);
if (forkstat.cntfork != 0) if (forkstat.cntfork != 0)
printf("%d forks, %d kbytes, average=%.2f\n", printf("%ld forks, %ld kbytes, average=%.2f\n", forkstat.cntfork, forkstat.sizfork,
forkstat.cntfork, forkstat.sizfork, (float)forkstat.sizfork / forkstat.cntfork);
(float) forkstat.sizfork / forkstat.cntfork);
if (forkstat.cntvfork != 0) if (forkstat.cntvfork != 0)
printf("%d vforks, %d kbytes, average=%.2f\n", printf("%ld vforks, %ld kbytes, average=%.2f\n", forkstat.cntvfork, forkstat.sizvfork,
forkstat.cntvfork, forkstat.sizvfork, (float)forkstat.sizvfork / forkstat.cntvfork);
(float) forkstat.sizvfork / forkstat.cntvfork);
} }
stats(dn) void stats(int dn)
{ {
if (dn >= dk_ndrive) { if (dn >= dk_ndrive) {
printf(" 0"); printf(" 0");
return; return;
} }
printf("%4.0f", s.xfer[dn]/etime); printf("%4.0f", s.xfer[dn] / etime);
} }
double double stat1(row)
stat1(row)
{ {
double t; double t;
register i; int i;
t = 0; t = 0;
for(i=0; i<CPUSTATES; i++) for (i = 0; i < CPUSTATES; i++)
t += s.time[i]; t += s.time[i];
if(t == 0.) if (t == 0.)
t = 1.; t = 1.;
return(s.time[row]*100./t); return (s.time[row] * 100. / t);
} }
dointr(nintv) void dointr(long nintv)
long nintv;
{ {
printf("Device interrupt statistics are not applicable to 2.11BSD\n"); printf("Device interrupt statistics are not applicable to 2.11BSD\n");
} }
#define steal(where, var) \ #define steal(where, var) \
lseek(mf, where, L_SET); read(mf, &var, sizeof var); lseek(mf, where, L_SET); \
read(mf, &var, sizeof var);
/* /*
* Read the drive names out of kmem. * Read the drive names out of kmem.
*/ */
read_names() void read_names()
{ {
char two_char[2]; char two_char[2];
register int i; int i;
lseek(mf, (long)nl[X_DK_NAME].n_value, L_SET); lseek(mf, (long)nl[X_DK_NAME].n_value, L_SET);
read(mf, dk_name, dk_ndrive * sizeof (char *)); read(mf, dk_name, dk_ndrive * sizeof(char *));
lseek(mf, (long)nl[X_DK_UNIT].n_value, L_SET); lseek(mf, (long)nl[X_DK_UNIT].n_value, L_SET);
read(mf, dk_unit, dk_ndrive * sizeof (int)); read(mf, dk_unit, dk_ndrive * sizeof(int));
for(i = 0; dk_name[i]; i++) { for (i = 0; dk_name[i]; i++) {
lseek(mf, (long)dk_name[i], L_SET); lseek(mf, (long)dk_name[i], L_SET);
read(mf, two_char, sizeof two_char); read(mf, two_char, sizeof two_char);
sprintf(dr_name[i], "%c%c%d", two_char[0], two_char[1], sprintf(dr_name[i], "%c%c%d", two_char[0], two_char[1], dk_unit[i]);
dk_unit[i]);
} }
} }

View File

@@ -8,62 +8,55 @@
* All rights reserved. The Berkeley software License Agreement * All rights reserved. The Berkeley software License Agreement
* specifies the terms and conditions for redistribution. * specifies the terms and conditions for redistribution.
*/ */
#include <errno.h>
#include <fcntl.h>
#include <paths.h>
#include <signal.h>
#include <stdio.h> #include <stdio.h>
#include <stdlib.h> #include <stdlib.h>
#include <string.h> #include <string.h>
#include <utmp.h>
#include <paths.h>
#include <errno.h>
#include <signal.h>
#include <sys/time.h>
#include <fcntl.h>
#include <sys/types.h>
#include <sys/stat.h> #include <sys/stat.h>
#include <sys/wait.h>
#include <utmp.h>
#include <unistd.h>
#define IGNOREUSER "sleeper" #define IGNOREUSER "sleeper"
char hostname[32]; char hostname[32];
char mesg[3000]; char mesg[3000];
int msize,sline; int msize, sline;
struct utmp *utmp; struct utmp *utmp;
char who[UT_NAMESIZE + 1] = "???"; char who[UT_NAMESIZE + 1] = "???";
long clock; long clock;
struct tm *localclock; struct tm *localclock;
extern errno; static void sendmes(char *tty);
main(argc, argv) int main(int argc, char *argv[])
char *argv[];
{ {
register int i, c; int i, c;
register struct utmp *p; struct utmp *p;
int f; int f;
struct stat statb; struct stat statb;
(void) gethostname(hostname, sizeof (hostname)); (void)gethostname(hostname, sizeof(hostname));
if ((f = open(_PATH_UTMP, O_RDONLY, 0)) < 0) { if ((f = open(_PATH_UTMP, O_RDONLY, 0)) < 0) {
fprintf(stderr, "Cannot open %s\n", _PATH_UTMP); fprintf(stderr, "Cannot open %s\n", _PATH_UTMP);
exit(1); exit(1);
} }
clock = time( 0 ); clock = time(0);
localclock = localtime( &clock ); localclock = localtime(&clock);
sline = ttyslot(); /* 'utmp' slot no. of sender */ sline = ttyslot(); /* 'utmp' slot no. of sender */
(void) fstat(f, &statb); (void)fstat(f, &statb);
utmp = (struct utmp *)malloc((unsigned)statb.st_size); utmp = (struct utmp *)malloc((unsigned)statb.st_size);
c = read(f, (char *)utmp, (int)statb.st_size); c = read(f, (char *)utmp, (int)statb.st_size);
(void) close(f); (void)close(f);
c /= sizeof(struct utmp); c /= sizeof(struct utmp);
if (sline) if (sline)
strncpy(who, utmp[sline].ut_name, sizeof(utmp[sline].ut_name)); strncpy(who, utmp[sline].ut_name, sizeof(utmp[sline].ut_name));
sprintf(mesg, sprintf(mesg, "\n\007\007Broadcast Message from %s@%s (%.*s) at %d:%02d ...\r\n\n", who,
"\n\007\007Broadcast Message from %s@%s (%.*s) at %d:%02d ...\r\n\n" hostname, sizeof(utmp[sline].ut_line), utmp[sline].ut_line, localclock->tm_hour,
, who localclock->tm_min);
, hostname
, sizeof(utmp[sline].ut_line)
, utmp[sline].ut_line
, localclock -> tm_hour
, localclock -> tm_min
);
msize = strlen(mesg); msize = strlen(mesg);
if (argc >= 2) { if (argc >= 2) {
/* take message from unix file instead of standard input */ /* take message from unix file instead of standard input */
@@ -82,26 +75,24 @@ char *argv[];
mesg[msize++] = i; mesg[msize++] = i;
} }
fclose(stdin); fclose(stdin);
for (i=0; i<c; i++) { for (i = 0; i < c; i++) {
p = &utmp[i]; p = &utmp[i];
if (p->ut_name[0] == 0 || if (p->ut_name[0] == 0 || strncmp(p->ut_name, IGNOREUSER, sizeof(p->ut_name)) == 0)
strncmp(p->ut_name, IGNOREUSER, sizeof(p->ut_name)) == 0)
continue; continue;
sendmes(p->ut_line); sendmes(p->ut_line);
} }
exit(0); exit(0);
} }
sendmes(tty) void sendmes(char *tty)
char *tty;
{ {
register f, flags; int f, flags;
static char t[50] = "/dev/"; static char t[50] = "/dev/";
int e, i; int e, i;
strcpy(t + 5, tty); strcpy(t + 5, tty);
if ((f = open(t, O_WRONLY|O_NDELAY)) < 0) { if ((f = open(t, O_WRONLY | O_NDELAY)) < 0) {
if (errno != EWOULDBLOCK) if (errno != EWOULDBLOCK)
perror(t); perror(t);
return; return;
@@ -114,15 +105,15 @@ char *tty;
goto oldway; goto oldway;
i = write(f, mesg, msize); i = write(f, mesg, msize);
e = errno; e = errno;
(void) fcntl(f, F_SETFL, flags); (void)fcntl(f, F_SETFL, flags);
if (i == msize) { if (i == msize) {
(void) close(f); (void)close(f);
return; return;
} }
if (e != EWOULDBLOCK) { if (e != EWOULDBLOCK) {
errno = e; errno = e;
perror(t); perror(t);
(void) close(f); (void)close(f);
return; return;
} }
oldway: oldway:
@@ -132,10 +123,10 @@ oldway:
return; return;
} }
if (i) { if (i) {
(void) close(f); (void)close(f);
return; return;
} }
(void) write(f, mesg, msize); (void)write(f, mesg, msize);
exit(0); exit(0);
} }

View File

@@ -1,59 +1,87 @@
/* /*
* write to another user * write to another user
*/ */
#include <stdio.h>
#include <ctype.h> #include <ctype.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <signal.h>
#include <utmp.h>
#include <paths.h>
#include <errno.h> #include <errno.h>
#include <string.h> #include <paths.h>
#include <unistd.h> #include <signal.h>
#include <stdio.h>
#include <stdlib.h> #include <stdlib.h>
#include <string.h>
#include <sys/stat.h>
#include <sys/wait.h>
#include <time.h> #include <time.h>
#include <unistd.h>
#include <utmp.h>
#define NMAX sizeof(ubuf.ut_name) #define NMAX sizeof(ubuf.ut_name)
#define LMAX sizeof(ubuf.ut_line) #define LMAX sizeof(ubuf.ut_line)
struct utmp ubuf; struct utmp ubuf;
int signum[] = {SIGHUP, SIGINT, SIGQUIT, 0}; int signum[] = { SIGHUP, SIGINT, SIGQUIT, 0 };
char me[NMAX + 1] = "???"; char me[NMAX + 1] = "???";
char *him; char *him;
char *mytty; char *mytty;
char histty[32]; char histty[32];
char ttybuf[32]; char ttybuf[32];
char *histtya; char *histtya;
int logcnt; int logcnt;
FILE *tf; FILE *tf;
void timout(sig) void timout(int sig)
int sig;
{ {
fprintf(stderr, "write: Timeout opening their tty\n"); fprintf(stderr, "write: Timeout opening their tty\n");
exit(1); exit(1);
} }
void eof(sig) void eof(int sig)
int sig;
{ {
fprintf(tf, "EOF\r\n"); fprintf(tf, "EOF\r\n");
exit(0); exit(0);
} }
main(argc, argv) void sigs(sig_t sig)
int argc; {
char *argv[]; int i;
for (i = 0; signum[i]; i++)
signal(signum[i], sig);
}
void ex(char *bp)
{
int i;
sigs(SIG_IGN);
i = fork();
if (i < 0) {
printf("Try again\n");
goto out;
}
if (i == 0) {
fclose(tf); /* Close his terminal */
setgid(getgid()); /* Give up effective group privs */
sigs((sig_t)0);
execl(getenv("SHELL") ? getenv("SHELL") : "/bin/sh", "sh", "-c", bp + 1, 0);
exit(0);
}
while (wait((int *)NULL) != i)
;
printf("!\n");
out:
sigs(eof);
}
int main(int argc, char *argv[])
{ {
struct stat stbuf; struct stat stbuf;
register i; int i;
register FILE *uf; FILE *uf;
int c1, c2; int c1, c2;
time_t clock = time(0); time_t clock = time(0);
int suser = getuid() == 0; int suser = getuid() == 0;
int nomesg = 0; int nomesg = 0;
struct tm *localclock = localtime( &clock ); struct tm *localclock = localtime(&clock);
if (argc < 2) { if (argc < 2) {
fprintf(stderr, "Usage: write user [ttyname]\n"); fprintf(stderr, "Usage: write user [ttyname]\n");
@@ -77,9 +105,8 @@ main(argc, argv)
perror("write: Can't stat your tty"); perror("write: Can't stat your tty");
exit(1); exit(1);
} }
if ((stbuf.st_mode&020) == 0) { if ((stbuf.st_mode & 020) == 0) {
fprintf(stderr, fprintf(stderr, "write: You have write permission turned off\n");
"write: You have write permission turned off\n");
if (!suser) if (!suser)
exit(1); exit(1);
} }
@@ -91,8 +118,8 @@ main(argc, argv)
while (fread((char *)&ubuf, sizeof(ubuf), 1, uf) == 1) { while (fread((char *)&ubuf, sizeof(ubuf), 1, uf) == 1) {
if (ubuf.ut_name[0] == '\0') if (ubuf.ut_name[0] == '\0')
continue; continue;
if (strcmp(ubuf.ut_line, mytty)==0) { if (strcmp(ubuf.ut_line, mytty) == 0) {
for (i=0; i<NMAX; i++) { for (i = 0; i < NMAX; i++) {
c1 = ubuf.ut_name[i]; c1 = ubuf.ut_name[i];
if (c1 == ' ') if (c1 == ' ')
c1 = 0; c1 = 0;
@@ -103,7 +130,7 @@ main(argc, argv)
} }
if (him[0] == '-' && him[1] == 0) if (him[0] == '-' && him[1] == 0)
goto nomat; goto nomat;
for (i=0; i<NMAX; i++) { for (i = 0; i < NMAX; i++) {
c1 = him[i]; c1 = him[i];
c2 = ubuf.ut_name[i]; c2 = ubuf.ut_name[i];
if (c1 == 0) if (c1 == 0)
@@ -112,36 +139,30 @@ main(argc, argv)
if (c1 != c2) if (c1 != c2)
goto nomat; goto nomat;
} }
if (histtya && strncmp(histtya, ubuf.ut_line, if (histtya && strncmp(histtya, ubuf.ut_line, sizeof(ubuf.ut_line)))
sizeof(ubuf.ut_line)))
continue; continue;
logcnt++; logcnt++;
if (histty[0]==0 || nomesg && histtya == 0) { if (histty[0] == 0 || nomesg && histtya == 0) {
strcpy(ttybuf, "/dev/"); strcpy(ttybuf, "/dev/");
strcat(ttybuf, ubuf.ut_line); strcat(ttybuf, ubuf.ut_line);
if (histty[0]==0) if (histty[0] == 0)
strcpy(histty, ttybuf); strcpy(histty, ttybuf);
if (access(ttybuf, 0) < 0 || stat(ttybuf, &stbuf) < 0 || if (access(ttybuf, 0) < 0 || stat(ttybuf, &stbuf) < 0 || (stbuf.st_mode & 020) == 0)
(stbuf.st_mode&020) == 0)
nomesg++; nomesg++;
else { else {
strcpy(histty, ttybuf); strcpy(histty, ttybuf);
nomesg = 0; nomesg = 0;
} }
} }
nomat: nomat:;
;
} }
fclose(uf); fclose(uf);
if (logcnt==0) { if (logcnt == 0) {
fprintf(stderr, "write: %s not logged in%s\n", him, fprintf(stderr, "write: %s not logged in%s\n", him, histtya ? " on that tty" : "");
histtya ? " on that tty" : "");
exit(1); exit(1);
} }
if (histtya==0 && logcnt > 1) { if (histtya == 0 && logcnt > 1) {
fprintf(stderr, fprintf(stderr, "write: %s logged in more than once ... writing to %s\n", him, histty + 5);
"write: %s logged in more than once ... writing to %s\n",
him, histty+5);
} }
cont: cont:
if (access(histty, 0) < 0) { if (access(histty, 0) < 0) {
@@ -156,19 +177,20 @@ cont:
} }
alarm(0); alarm(0);
sigs(eof); sigs(eof);
{ char hostname[32]; {
gethostname(hostname, sizeof (hostname)); char hostname[32];
fprintf(tf, gethostname(hostname, sizeof(hostname));
"\r\nMessage from %s@%s on %s at %d:%02d ...\r\n\007\007\007", fprintf(tf, "\r\nMessage from %s@%s on %s at %d:%02d ...\r\n\007\007\007", me, hostname,
me, hostname, mytty, localclock->tm_hour, localclock->tm_min); mytty, localclock->tm_hour, localclock->tm_min);
fflush(tf); fflush(tf);
} }
for (;;) { for (;;) {
char buf[BUFSIZ]; char buf[BUFSIZ];
register char *bp; char *bp;
i = read(0, buf, sizeof buf); i = read(0, buf, sizeof buf);
if (i <= 0) if (i <= 0)
eof(); eof(0);
if (buf[0] == '!') { if (buf[0] == '!') {
buf[i] = 0; buf[i] = 0;
ex(buf); ex(buf);
@@ -184,8 +206,7 @@ cont:
*bp = toascii(*bp); *bp = toascii(*bp);
} }
if (isprint(*bp) || if (isprint(*bp) || *bp == ' ' || *bp == '\t' || *bp == '\n') {
*bp == ' ' || *bp == '\t' || *bp == '\n') {
putc(*bp, tf); putc(*bp, tf);
} else { } else {
putc('^', tf); putc('^', tf);
@@ -196,45 +217,9 @@ cont:
fflush(tf); fflush(tf);
if (ferror(tf) || feof(tf)) { if (ferror(tf) || feof(tf)) {
printf("\n\007Write failed (%s logged out?)\n", printf("\n\007Write failed (%s logged out?)\n", him);
him);
exit(1); exit(1);
} }
} }
} }
} }
ex(bp)
char *bp;
{
register i;
sigs(SIG_IGN);
i = fork();
if (i < 0) {
printf("Try again\n");
goto out;
}
if (i == 0) {
fclose(tf); /* Close his terminal */
setgid(getgid()); /* Give up effective group privs */
sigs((sig_t) 0);
execl(getenv("SHELL") ?
getenv("SHELL") : "/bin/sh", "sh", "-c", bp+1, 0);
exit(0);
}
while (wait((int *)NULL) != i)
;
printf("!\n");
out:
sigs(eof);
}
sigs(sig)
sig_t sig;
{
register i;
for (i=0; signum[i]; i++)
signal(signum[i], sig);
}