BSD 3 development
[unix-history] / usr / src / cmd / net / mwrite.c
CommitLineData
557609a3
ES
1/*
2 Mwrite provides the "response" function in the network.
3 It sends its standard input to "toaddress", either by opening
4 his terminal and writing on it, or by mailing it to him.
5 It is executed by a remote machine from netdameon.c, either for a
6 response to be sent back or an errormsg to be sent back.
7 It excutes mmail locally if it needs to.
8
9Archaic Usage:
10 mwrite toaddress ttystr lutmptime fmach fuser [command ltimeSent]
11
12New Usage:
13 mwrite [-t toaddress] [-f fromaddress] [-x lutmptime]
14 [-c command] [-y ttystr] [-e ltimeSent] [-r rc]
15
16 fmach is a single letter.
17 ttystr is the full name, e.g. /dev/tty0
18 ltimeSent is number of secs since TIMEBASE in decimal.
19 lutmptime is the login time from utmp in OCTAL in the old protocol
20 and in decimal in the new protocol.
21 rc is the decimal return code (exit code>>8) of the command.
22 command and ltimeSent are optional.
23
24 There is duplication in this argument list.
25 See the note in mmail.c about this stuff.
26
27 Mwrite must be setuid bin or setuid root, to get in group 0,
28 on the CC machines, in order to write on the user's terminal.
29
30 Exit Codes:
31 Returns 0 if the writing on the terminal works.
32 Returns the return code of the mmail program if this is mailed.
33 Returns 101 if can't exec mail program.
34 Returns 102 if can't read the utmp file.
35*/
36# include "defs.h"
37jmp_buf env;
38main(argc,argv)
39 char **argv; {
40 long lutmptime, otime, ltimeSent, ltimeCur, ltimeElap;
41 int alarmint();
42 FILE *file;
43 int i;
44 struct utmp utmpstr;
45 char buf[BUFSIZ],*s;
46 char fromaddress[BUFSIZ], toaddress[BUFSIZ];
47 char ttynamestr[BUFSIZ], cmdstr[BUFSIZ], *stimeCur, stimeSent[20];
48 char src[10], stemp[BUFSIZ];
49 struct stat statbuf;
50
51 debugflg = DBV;
52 argv[argc] = 0;
53 otime = 0;
54 src[0] = 0;
55 errno = 0;
56
57 strcpy(toaddress,argv[1]);
58 strcpy(ttynamestr,argv[2]);
59 sscanf(argv[3],"%lo",&lutmptime);
60 sprintf(fromaddress,"%s:%s",longname(argv[4][0]),argv[5]);
61 if(argc > 6)strcpy(cmdstr,argv[6]);
62 else cmdstr[0] = 0;
63 if(argc > 7)strcpy(stimeSent,argv[7]);
64 else stimeSent[0] = 0;
65
66 /* parse arguments */
67 for(i = 1; i < argc; i++){
68 if(argv[i][0] == '-')
69 switch(argv[i][1]){
70 case 't':
71 strcpy(toaddress,argv[++i]);
72 break;
73 case 'y':
74 strcpy(ttynamestr,argv[++i]);
75 break;
76 case 'x':
77 lutmptime = atol(argv[++i]);
78 break;
79 case 'f':
80 strcpy(fromaddress,argv[++i]);
81 break;
82 case 'c':
83 strcpy(cmdstr,argv[++i]);
84 break;
85 case 'e':
86 strcpy(stimeSent,argv[++i]);
87 break;
88 case 'r':
89 strcpy(src,argv[++i]);
90 break;
91 }
92 /* it is important that this code ignore unknown flags
93 so that options can be added w/o recompiling */
94 }
95
96 ltimeSent=atol(stimeSent)+TIMEBASE;
97
98 setjmp(env);
99 alarm(0);
100 signal(SIGCLK,alarmint);
101 if(errno != 100 && ttynamestr[0] && ttynamestr[8] != 'x'){
102 alarm(100);
103 file = fopen("/etc/utmp","r");
104 if(file == NULL){
105 perror("/etc/utmp");
106 exit(201);
107 }
108 while(fread(&utmpstr,1,sizeof utmpstr,file) == sizeof utmpstr){
109# ifdef OLDTTY
110 if(utmpstr.ut_tty == ttynamestr[8]){
111# else
112 if(strcmp(utmpstr.ut_line,ttynamestr+5) == 0){
113# endif
114 otime = utmpstr.ut_time;
115 break;
116 }
117 }
118 fclose(file);
119 /*
120 debug("lutmptime %lo otime %lo",lutmptime,otime);
121 */
122 if(otime != 0 && otime == lutmptime) {
123 file = fopen(ttynamestr,"w");
124 if(file != NULL && fstat(fileno(file),&statbuf) != -1
125 && (statbuf.st_mode&02)){
126 if(src[0] != 0)sprintf(stemp,", R: %s",src);
127 else stemp[0] = 0;
128 ltimeCur = gettime();
129 stimeCur = ctime(&ltimeCur);
130 stimeCur += 11;
131 stimeCur[strlen(stimeCur)-9] = 0;
132 fprintf(file,
133 "\r\nMessage from %s at %s ...\r\n",
134 fromaddress, stimeCur);
135 if(cmdstr[0] != 0){
136 s = ctime(&ltimeSent);
137 s[strlen(s)-6] = 0;
138 ltimeElap = ltimeCur - ltimeSent;
139 fprintf(file,
140 "(command: %s%s, sent %s, took %s)\r\n",
141 cmdstr,stemp,s,comptime(ltimeElap));
142 }
143 while(fgets(buf,BUFSIZ,stdin) != NULL){
144 fputs(buf,file);
145 fputc('\r',file);
146 }
147 fprintf(file,"------\r\n");
148 exit(0);
149 }
150 }
151 }
152
153 /* well, couldn't write to him, so we'll mail to him on this mach */
154 /* mail to "toaddress", saying its from "fromaddress", about a command
155 "cmdstr", which was sent at time "stimeSent" */
156
157 sprintf(stimeSent,"%ld",ltimeSent);
158 if(cmdstr[0] != 0){
159 if(src[0] != 0)
160 mexecl(MMAILCMD,"mmail", "-r",src, "-c",cmdstr,
161 "-e",stimeSent,"-f",fromaddress,
162 "-t",toaddress,"-z",0);
163 else
164 mexecl(MMAILCMD,"mmail", "-c",cmdstr, "-e",stimeSent,
165 "-f",fromaddress, "-t",toaddress,"-z",0);
166 }
167 else
168 mexecl(MMAILCMD,"mmail", "-f",fromaddress, "-t",toaddress,
169 "-z", 0);
170 exit(101);
171}
172alarmint(){
173 errno = 100;
174 signal(SIGCLK,SIG_IGN); /* alarm off */
175 longjmp(env,0); /* ugh */
176 }