|
|
1.1 root 1: static char *sccsid = "@(#)at.c 4.2 (Berkeley) 10/21/80";
2: /*
3: * at time mon day
4: * at time wday
5: * at time wday 'week'
6: *
7: */
8: #include <stdio.h>
9: #include <ctype.h>
10: #include <time.h>
11: #include <signal.h>
12:
13: #define HOUR 100
14: #define HALFDAY (12*HOUR)
15: #define DAY (24*HOUR)
16: #define THISDAY "/usr/spool/at"
17:
18: char *days[] = {
19: "sunday",
20: "monday",
21: "tuesday",
22: "wednesday",
23: "thursday",
24: "friday",
25: "saturday",
26: };
27:
28: struct monstr {
29: char *mname;
30: int mlen;
31: } months[] = {
32: { "january", 31 },
33: { "february", 28 },
34: { "march", 31 },
35: { "april", 30 },
36: { "may", 31 },
37: { "june", 30 },
38: { "july", 31 },
39: { "august", 31 },
40: { "september", 30 },
41: { "october", 31 },
42: { "november", 30 },
43: { "december", 31 },
44: { 0, 0 },
45: };
46:
47: char fname[100];
48: int utime; /* requested time in grains */
49: int now; /* when is it */
50: int uday; /* day of year to be done */
51: int uyear; /* year */
52: int today; /* day of year today */
53: FILE *file;
54: FILE *ifile;
55: char **environ;
56: char *prefix();
57: char *getenv();
58: FILE *popen();
59:
60: main(argc, argv)
61: char **argv;
62: {
63: extern onintr();
64: register c;
65: char pwbuf[100];
66: FILE *pwfil;
67: int larg;
68: char *tmp;
69:
70: /* argv[1] is the user's time: e.g., 3AM */
71: /* argv[2] is a month name or day of week */
72: /* argv[3] is day of month or 'week' */
73: /* another argument might be an input file */
74: if (argc < 2) {
75: fprintf(stderr, "at: arg count\n");
76: exit(1);
77: }
78: makeutime(argv[1]);
79: larg = makeuday(argc,argv)+1;
80: if (uday==today && larg<=2 && utime<=now)
81: uday++;
82: c = uyear%4==0? 366: 365;
83: if (uday >= c) {
84: uday -= c;
85: uyear++;
86: }
87: filename(THISDAY, uyear, uday, utime);
88: /* Create file, then change UIDS */
89: close(creat(fname,0644));
90: chown(fname,getuid(),getgid());
91: setuid(getuid());
92: ifile = stdin;
93: if (argc > larg)
94: ifile = fopen(argv[larg], "r");
95: if (ifile == NULL) {
96: fprintf(stderr, "at: cannot open input: %s\n", argv[larg]);
97: exit(1);
98: }
99: if (signal(SIGINT, SIG_IGN) != SIG_IGN)
100: signal(SIGINT, onintr);
101: file = fopen(fname, "w");
102: if (file == NULL) {
103: fprintf(stderr, "at: cannot open memo file\n");
104: exit(1);
105: }
106: if ((pwfil = popen("pwd", "r")) == NULL) {
107: fprintf(stderr, "at: can't execute pwd\n");
108: exit(1);
109: }
110: fgets(pwbuf, 100, pwfil);
111: pclose(pwfil);
112: fprintf(file, "cd %s", pwbuf);
113: c = umask(0);
114: umask(c);
115: fprintf(file, "umask %.1o\n", c);
116: if (environ) {
117: char **ep = environ;
118: while(*ep)
119: {
120: char *cp;
121: for (tmp = *ep, cp = "TERMCAP"; *tmp==*cp; tmp++,cp++);
122: if (*cp == 0 && *tmp== '=') {
123: ep++;
124: continue;
125: }
126: for(tmp = *ep ; *tmp != '=' ; tmp++) putc(*tmp,file);
127: putc('=', file);
128: putc('\'', file);
129: for (tmp++; *tmp; tmp++) {
130: if (*tmp == '\'')
131: putc('\\', file);
132: putc(*tmp, file);
133: }
134: putc('\'', file);
135: fprintf(file, "\nexport ");
136: for(tmp = *ep ; *tmp != '=' ; tmp++) putc(*tmp,file);
137: putc('\n',file);
138: ep++;
139: }
140: }
141: /*
142: * see if the SHELL variable in the current enviroment is /bin/csh
143: * and in that case, use the csh as the shell
144: */
145: tmp = getenv("SHELL");
146: if (strcmp(tmp+strlen(tmp)-3, "csh") == 0)
147: fprintf(file, "%s %s\n", tmp, "<< 'xxFUNNYxx'");
148: while((c = getc(ifile)) != EOF) {
149: putc(c, file);
150: }
151: if (strcmp(tmp+strlen(tmp)-3, "csh") == 0)
152: fprintf(file, "%s\n", "xxFUNNYxx");
153: exit(0);
154: }
155:
156: makeutime(pp)
157: char *pp;
158: {
159: register val;
160: register char *p;
161:
162: /* p points to a user time */
163: p = pp;
164: val = 0;
165: while(isdigit(*p)) {
166: val = val*10+(*p++ -'0');
167: }
168: if (p-pp < 3)
169: val *= HOUR;
170:
171: for (;;) {
172: switch(*p) {
173:
174: case ':':
175: ++p;
176: if (isdigit(*p)) {
177: if (isdigit(p[1])) {
178: val +=(10* *p + p[1] - 11*'0');
179: p += 2;
180: continue;
181: }
182: }
183: fprintf(stderr, "at: bad time format:\n");
184: exit(1);
185:
186: case 'A':
187: case 'a':
188: if (val >= HALFDAY+HOUR)
189: val = DAY+1; /* illegal */
190: if (val >= HALFDAY && val <(HALFDAY+HOUR))
191: val -= HALFDAY;
192: break;
193:
194: case 'P':
195: case 'p':
196: if (val >= HALFDAY+HOUR)
197: val = DAY+1; /* illegal */
198: if (val < HALFDAY)
199: val += HALFDAY;
200: break;
201:
202: case 'n':
203: case 'N':
204: val = HALFDAY;
205: break;
206:
207: case 'M':
208: case 'm':
209: val = 0;
210: break;
211:
212:
213: case '\0':
214: case ' ':
215: /* 24 hour time */
216: if (val == DAY)
217: val -= DAY;
218: break;
219:
220: default:
221: fprintf(stderr, "at: bad time format\n");
222: exit(1);
223:
224: }
225: break;
226: }
227: if (val < 0 || val >= DAY) {
228: fprintf(stderr, "at: time out of range\n");
229: exit(1);
230: }
231: if (val%HOUR >= 60) {
232: fprintf(stderr, "at: illegal minute field\n");
233: exit(1);
234: }
235: utime = val;
236: }
237:
238:
239: makeuday(argc,argv)
240: char **argv;
241: {
242: /* the presumption is that argv[2], argv[3] are either
243: month day OR weekday [week]. Returns either 2 or 3 as last
244: argument used */
245: /* first of all, what's today */
246: long tm;
247: int found = -1;
248: char **ps;
249: struct tm *detail, *localtime();
250: struct monstr *pt;
251:
252: time(&tm);
253: detail = localtime(&tm);
254: uday = today = detail->tm_yday;
255: uyear = detail->tm_year;
256: now = detail->tm_hour*100+detail->tm_min;
257: if (argc<=2)
258: return(1);
259: /* is the next argument a month name ? */
260: for (pt=months; pt->mname; pt++) {
261: if (prefix(argv[2], pt->mname)) {
262: if (found<0)
263: found = pt-months;
264: else {
265: fprintf(stderr, "at: ambiguous month\n");
266: exit(1);
267: }
268: }
269: }
270: if (found>=0) {
271: if (argc<=3)
272: return(2);
273: uday = atoi(argv[3]) - 1;
274: if (uday<0) {
275: fprintf(stderr, "at: illegal day\n");
276: exit(1);
277: }
278: while(--found>=0)
279: uday += months[found].mlen;
280: if (detail->tm_year%4==0 && uday>59)
281: uday += 1;
282: return(3);
283: }
284: /* not a month, try day of week */
285: found = -1;
286: for (ps=days; ps<days+7; ps++) {
287: if (prefix(argv[2], *ps)) {
288: if (found<0)
289: found = ps-days;
290: else {
291: fprintf(stderr, "at: ambiguous day of week\n");
292: exit(1);
293: }
294: }
295: }
296: if (found<0)
297: return(1);
298: /* find next day of this sort */
299: uday = found - detail->tm_wday;
300: if (uday<=0)
301: uday += 7;
302: uday += today;
303: if (argc>3 && strcmp("week", argv[3])==0) {
304: uday += 7;
305: return(3);
306: }
307: return(2);
308: }
309:
310: char *
311: prefix(begin, full)
312: char *begin, *full;
313: {
314: int c;
315: while (c = *begin++) {
316: if (isupper(c))
317: c = tolower(c);
318: if (*full != c)
319: return(0);
320: else
321: full++;
322: }
323: return(full);
324: }
325:
326: filename(dir, y, d, t)
327: char *dir;
328: {
329: register i;
330:
331: for (i=0; ; i += 53) {
332: sprintf(fname, "%s/%02d.%03d.%04d.%02d", dir, y, d, t,
333: (getpid()+i)%100);
334: if (access(fname, 0) == -1)
335: return;
336: }
337: }
338:
339: onintr()
340: {
341: unlink(fname);
342: exit(1);
343: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.