|
|
1.1 root 1:
2: # line 7 "ftpcmd.y"
3:
4: #ifndef lint
5: static char sccsid[] = "@(#)ftpcmd.y 4.11 83/06/22";
6: #endif
7:
8: #include <sys/types.h>
9:
10: #include <sys/inet/in.h>
11:
12: #include "ftp.h"
13:
14: #include <stdio.h>
15: #include <signal.h>
16: #include <ctype.h>
17: #include <pwd.h>
18: #include <setjmp.h>
19:
20: struct socket {
21: unsigned short sport;
22: long saddr;
23: };
24: char dest[128];
25: extern int logged_in;
26: extern struct passwd *pw;
27: extern int logging;
28: extern int type;
29: extern int form;
30: extern int debug;
31: extern int timeout;
32: extern char hostname[];
33: extern char *globerr;
34: extern int usedefault;
35: extern int pasv;
36: char **glob();
37:
38: static int cmd_type;
39: static int cmd_form;
40: static int cmd_bytesz;
41:
42: char *strchr();
43: # define A 257
44: # define B 258
45: # define C 259
46: # define E 260
47: # define F 261
48: # define I 262
49: # define L 263
50: # define N 264
51: # define P 265
52: # define R 266
53: # define S 267
54: # define T 268
55: # define SP 269
56: # define CRLF 270
57: # define COMMA 271
58: # define STRING 272
59: # define NUMBER 273
60: # define USER 274
61: # define PASS 275
62: # define ACCT 276
63: # define REIN 277
64: # define QUIT 278
65: # define PORT 279
66: # define PASV 280
67: # define TYPE 281
68: # define STRU 282
69: # define MODE 283
70: # define RETR 284
71: # define STOR 285
72: # define APPE 286
73: # define MLFL 287
74: # define MAIL 288
75: # define MSND 289
76: # define MSOM 290
77: # define MSAM 291
78: # define MRSQ 292
79: # define MRCP 293
80: # define ALLO 294
81: # define REST 295
82: # define RNFR 296
83: # define RNTO 297
84: # define ABOR 298
85: # define DELE 299
86: # define CWD 300
87: # define LIST 301
88: # define NLST 302
89: # define SITE 303
90: # define STAT 304
91: # define HELP 305
92: # define NOOP 306
93: # define XMKD 307
94: # define XRMD 308
95: # define XPWD 309
96: # define XCUP 310
97: # define OPEN 311
98: # define CLOS 312
99: # define READ 313
100: # define WRIT 314
101: # define SEEK 315
102: # define LEXERR 316
103: #define yyclearin yychar = -1
104: #define yyerrok yyerrflag = 0
105: extern int yychar;
106: extern short yyerrflag;
107: #ifndef YYMAXDEPTH
108: #define YYMAXDEPTH 150
109: #endif
110: #ifndef YYSTYPE
111: #define YYSTYPE int
112: #endif
113: YYSTYPE yylval, yyval;
114: # define YYERRCODE 256
115:
116: # line 430 "ftpcmd.y"
117:
118:
119: extern jmp_buf errcatch;
120:
121: #define CMD 0 /* beginniAg of command */
122: #define ARGS 1 /* expect miscellaneous arguments */
123: #define STR1 2 /* expect SP followed by STRING */
124: #define STR2 3 /* expect STRING */
125: #define OSTR 4 /* optional STRING */
126:
127: struct tab {
128: char *name;
129: short token;
130: short state;
131: short implemented; /* 1 if command is implemented */
132: char *help;
133: };
134:
135: struct tab cmdtab[] = { /* In order defined in RFC 765 */
136: { "USER", USER, STR1, 1, "<sp> username" },
137: { "PASS", PASS, STR1, 1, "<sp> password" },
138: { "ACCT", ACCT, STR1, 0, "(specify account)" },
139: { "REIN", REIN, ARGS, 0, "(reinitialize server state)" },
140: { "QUIT", QUIT, ARGS, 1, "(terminate service)", },
141: { "PORT", PORT, ARGS, 1, "<sp> b0, b1, b2, b3, b4" },
142: { "PASV", PASV, ARGS, 1, "(set server in passive mode)" },
143: { "TYPE", TYPE, ARGS, 1, "<sp> [ A | E | I | L ]" },
144: { "STRU", STRU, ARGS, 1, "(specify file structure)" },
145: { "MODE", MODE, ARGS, 1, "(specify transfer mode)" },
146: { "RETR", RETR, STR1, 1, "<sp> file-name" },
147: { "STOR", STOR, STR1, 1, "<sp> file-name" },
148: { "APPE", APPE, STR1, 1, "<sp> file-name" },
149: { "MLFL", MLFL, OSTR, 0, "(mail file)" },
150: { "MAIL", MAIL, OSTR, 0, "(mail to user)" },
151: { "MSND", MSND, OSTR, 0, "(mail send to terminal)" },
152: { "MSOM", MSOM, OSTR, 0, "(mail send to terminal or mailbox)" },
153: { "MSAM", MSAM, OSTR, 0, "(mail send to terminal and mailbox)" },
154: { "MRSQ", MRSQ, OSTR, 0, "(mail recipient scheme question)" },
155: { "MRCP", MRCP, STR1, 0, "(mail recipient)" },
156: { "ALLO", ALLO, ARGS, 1, "allocate storage (vacuously)" },
157: { "REST", REST, STR1, 0, "(restart command)" },
158: { "RNFR", RNFR, STR1, 1, "<sp> file-name" },
159: { "RNTO", RNTO, STR1, 1, "<sp> file-name" },
160: { "ABOR", ABOR, ARGS, 0, "(abort operation)" },
161: { "DELE", DELE, STR1, 1, "<sp> file-name" },
162: { "CWD", CWD, OSTR, 1, "[ <sp> directory-name]" },
163: { "XCWD", CWD, OSTR, 1, "[ <sp> directory-name ]" },
164: { "LIST", LIST, OSTR, 1, "[ <sp> path-name ]" },
165: { "NLST", NLST, OSTR, 1, "[ <sp> path-name ]" },
166: { "SITE", SITE, STR1, 0, "(get site parameters)" },
167: { "STAT", STAT, OSTR, 0, "(get server status)" },
168: { "HELP", HELP, OSTR, 1, "[ <sp> <string> ]" },
169: { "NOOP", NOOP, ARGS, 1, "" },
170: { "XMKD", XMKD, STR1, 1, "<sp> path-name" },
171: { "XRMD", XRMD, STR1, 1, "<sp> path-name" },
172: { "XPWD", XPWD, ARGS, 1, "(return current directory)" },
173: { "XCUP", XCUP, ARGS, 1, "(change to parent directory)" },
174: { "OPEN", OPEN, STR1, 1, "[ <sp> path-name ]" },
175: { "CLOS", CLOS, ARGS, 1, "(close file)" },
176: { "READ", READ, ARGS, 1, "(read from file)" },
177: { "WRIT", WRIT, ARGS, 1, "(writ from file)" },
178: { "SEEK", SEEK, ARGS, 1, "(seek in file)" },
179: { NULL, 0, 0, 0, 0 }
180: };
181:
182: struct tab *
183: lookup(cmd)
184: char *cmd;
185: {
186: register struct tab *p;
187:
188: for (p = cmdtab; p->name != NULL; p++)
189: if (strcmp(cmd, p->name) == 0)
190: return (p);
191: return (0);
192: }
193:
194: #include "telnet.h"
195:
196: /*
197: * getline - a hacked up version of fgets to ignore TELNET escape codes.
198: */
199: char *
200: getline(s, n, iop)
201: char *s;
202: register FILE *iop;
203: {
204: register c;
205: register char *cs;
206:
207: cs = s;
208: while (--n > 0 && (c = getc(iop)) >= 0) {
209: while (c == IAC) {
210: c = getc(iop); /* skip command */
211: c = getc(iop); /* try next char */
212: }
213: *cs++ = c;
214: if (c=='\n')
215: break;
216: }
217: if (c < 0 && cs == s)
218: return (NULL);
219: *cs++ = '\0';
220: if (debug) {
221: fprintf(stderr, "FTPD: command: %s", s);
222: if (c != '\n')
223: putc('\n', stderr);
224: fflush(stderr);
225: }
226: return (s);
227: }
228:
229: static int
230: toolong()
231: {
232: long now;
233: extern char *ctime();
234:
235: reply(421,
236: "Timeout (%d seconds): closing control connection.", timeout);
237: time(&now);
238: if (logging) {
239: fprintf(stderr,
240: "FTPD: User %s timed out after %d seconds at %s",
241: (pw ? pw -> pw_name : "unknown"), timeout, ctime(&now));
242: fflush(stderr);
243: }
244: dologout(1);
245: }
246:
247: yylex()
248: {
249: static char cbuf[512];
250: static int cpos, state;
251: register char *cp;
252: register struct tab *p;
253: int n;
254: char c;
255:
256: for (;;) {
257: switch (state) {
258:
259: case CMD:
260: signal(SIGALRM, toolong);
261: alarm(timeout);
262: if (getline(cbuf, sizeof(cbuf)-1, stdin) == NULL) {
263: reply(221, "You could at least say goodbye.");
264: dologout(0);
265: }
266: alarm(0);
267: if (strchr(cbuf, '\r')) {
268: cp = strchr(cbuf, '\r');
269: cp[0] = '\n'; cp[1] = 0;
270: }
271: if (strchr(cbuf, ' '))
272: cpos = strchr(cbuf, ' ') - cbuf;
273: else
274: cpos = 4;
275: c = cbuf[cpos];
276: cbuf[cpos] = '\0';
277: upper(cbuf);
278: p = lookup(cbuf);
279: cbuf[cpos] = c;
280: if (p != 0) {
281: if (p->implemented == 0) {
282: nack(p->name);
283: longjmp(errcatch);
284: /* NOTREACHED */
285: }
286: state = p->state;
287: yylval = (int) p->name;
288: return (p->token);
289: }
290: break;
291:
292: case OSTR:
293: if (cbuf[cpos] == '\n') {
294: state = CMD;
295: return (CRLF);
296: }
297: /* FALL THRU */
298:
299: case STR1:
300: if (cbuf[cpos] == ' ') {
301: cpos++;
302: state = STR2;
303: return (SP);
304: }
305: break;
306:
307: case STR2:
308: cp = &cbuf[cpos];
309: n = strlen(cp);
310: cpos += n - 1;
311: /*
312: * Make sure the string is nonempty and \n terminated.
313: */
314: if (n > 1 && cbuf[cpos] == '\n') {
315: cbuf[cpos] = '\0';
316: yylval = copy(cp);
317: cbuf[cpos] = '\n';
318: state = ARGS;
319: return (STRING);
320: }
321: break;
322:
323: case ARGS:
324: if (isdigit(cbuf[cpos])) {
325: cp = &cbuf[cpos];
326: while (isdigit(cbuf[++cpos]))
327: ;
328: c = cbuf[cpos];
329: cbuf[cpos] = '\0';
330: yylval = atoi(cp);
331: cbuf[cpos] = c;
332: return (NUMBER);
333: }
334: switch (cbuf[cpos++]) {
335:
336: case '\n':
337: state = CMD;
338: return (CRLF);
339:
340: case ' ':
341: return (SP);
342:
343: case ',':
344: return (COMMA);
345:
346: case 'A':
347: case 'a':
348: return (A);
349:
350: case 'B':
351: case 'b':
352: return (B);
353:
354: case 'C':
355: case 'c':
356: return (C);
357:
358: case 'E':
359: case 'e':
360: return (E);
361:
362: case 'F':
363: case 'f':
364: return (F);
365:
366: case 'I':
367: case 'i':
368: return (I);
369:
370: case 'L':
371: case 'l':
372: return (L);
373:
374: case 'N':
375: case 'n':
376: return (N);
377:
378: case 'P':
379: case 'p':
380: return (P);
381:
382: case 'R':
383: case 'r':
384: return (R);
385:
386: case 'S':
387: case 's':
388: return (S);
389:
390: case 'T':
391: case 't':
392: return (T);
393:
394: }
395: break;
396:
397: default:
398: fatal("Unknown state in scanner.");
399: }
400: yyerror();
401: state = CMD;
402: longjmp(errcatch);
403: }
404: }
405:
406: upper(s)
407: char *s;
408: {
409: while (*s != '\0') {
410: if (islower(*s))
411: *s = toupper(*s);
412: s++;
413: }
414: }
415:
416: copy(s)
417: char *s;
418: {
419: char *p;
420: extern char *malloc();
421:
422: p = malloc(strlen(s) + 1);
423: if (p == NULL)
424: fatal("Ran out of memory.");
425: strcpy(p, s);
426: return ((int)p);
427: }
428:
429: help(s)
430: char *s;
431: {
432: register struct tab *c;
433: register int width, NCMDS;
434:
435: width = 0, NCMDS = 0;
436: for (c = cmdtab; c->name != NULL; c++) {
437: int len = strlen(c->name);
438:
439: if (c->implemented == 0)
440: len++;
441: if (len > width)
442: width = len;
443: NCMDS++;
444: }
445: width = (width + 8) &~ 7;
446: if (s == 0) {
447: register int i, j, w;
448: int columns, lines;
449:
450: lreply(214,
451: "The following commands are recognized (* =>'s unimplemented).");
452: columns = 76 / width;
453: if (columns == 0)
454: columns = 1;
455: lines = (NCMDS + columns - 1) / columns;
456: for (i = 0; i < lines; i++) {
457: printf(" ");
458: for (j = 0; j < columns; j++) {
459: c = cmdtab + j * lines + i;
460: printf("%s%c", c->name,
461: c->implemented ? ' ' : '*');
462: if (c + lines >= &cmdtab[NCMDS])
463: break;
464: w = strlen(c->name);
465: while (w < width) {
466: putchar(' ');
467: w++;
468: }
469: }
470: printf("\r\n");
471: }
472: fflush(stdout);
473: reply(214, "Direct comments to ftp-bugs@%s.", hostname);
474: return;
475: }
476: upper(s);
477: c = lookup(s);
478: if (c == (struct tab *)0) {
479: reply(504, "Unknown command %s.", s);
480: return;
481: }
482: if (c->implemented)
483: reply(214, "Syntax: %s %s", c->name, c->help);
484: else
485: reply(214, "%-*s\t%s; unimplemented.", width, c->name, c->help);
486: }
487: short yyexca[] ={
488: -1, 1,
489: 0, -1,
490: -2, 0,
491: };
492: # define YYNPROD 59
493: # define YYLAST 215
494: short yyact[]={
495:
496: 27, 56, 103, 150, 148, 146, 105, 144, 105, 124,
497: 77, 63, 111, 89, 61, 59, 149, 147, 3, 4,
498: 145, 143, 26, 5, 21, 6, 7, 8, 10, 12,
499: 13, 99, 88, 87, 85, 84, 83, 82, 9, 142,
500: 29, 46, 45, 16, 17, 15, 14, 141, 140, 19,
501: 20, 22, 23, 24, 25, 11, 139, 138, 137, 136,
502: 135, 134, 133, 132, 131, 128, 119, 108, 107, 106,
503: 126, 100, 98, 97, 127, 96, 109, 93, 92, 54,
504: 53, 48, 47, 102, 101, 95, 94, 91, 90, 86,
505: 81, 80, 79, 78, 75, 76, 36, 35, 34, 33,
506: 32, 31, 30, 74, 70, 104, 37, 65, 72, 71,
507: 66, 125, 67, 68, 55, 28, 110, 18, 38, 39,
508: 40, 41, 42, 43, 44, 73, 69, 64, 62, 49,
509: 50, 51, 52, 60, 58, 2, 57, 1, 0, 0,
510: 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
511: 0, 0, 0, 0, 0, 0, 112, 113, 114, 0,
512: 115, 0, 116, 117, 0, 118, 0, 120, 121, 0,
513: 0, 122, 123, 0, 0, 0, 0, 0, 0, 0,
514: 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
515: 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
516: 0, 0, 0, 0, 0, 0, 0, 0, 0, 130,
517: 0, 0, 0, 0, 129 };
518: short yypact[]={
519:
520: -1000,-256,-1000,-167,-168,-169,-170,-171,-172,-173,
521: -1000,-1000,-1000,-1000,-1000,-1000,-1000,-1000,-1000,-228,
522: -188,-189,-1000,-1000,-1000,-1000,-190,-191,-296,-1000,
523: -257,-258,-262,-150,-157,-164,-263,-176,-177,-178,
524: -179,-233,-235,-180,-237,-1000,-259,-1000,-1000,-181,
525: -182,-192,-193,-1000,-1000,-1000,-183,-184,-195,-1000,
526: -197,-1000,-198,-240,-199,-185,-186,-1000,-267,-201,
527: -1000,-1000,-1000,-202,-1000,-1000,-1000,-203,-260,-260,
528: -260,-260,-1000,-260,-1000,-260,-260,-1000,-260,-204,
529: -260,-260,-1000,-1000,-260,-260,-1000,-1000,-1000,-264,
530: -1000,-194,-194,-265,-1000,-1000,-1000,-1000,-1000,-206,
531: -1000,-1000,-207,-208,-209,-210,-211,-212,-213,-1000,
532: -214,-222,-223,-231,-250,-1000,-1000,-1000,-1000,-1000,
533: -1000,-1000,-1000,-1000,-1000,-1000,-1000,-1000,-1000,-1000,
534: -1000,-1000,-1000,-266,-251,-268,-254,-269,-255,-270,
535: -1000 };
536: short yypgo[]={
537:
538: 0, 137, 135, 134, 133, 128, 127, 126, 125, 106,
539: 76, 117, 105, 111, 116, 115, 114 };
540: short yyr1[]={
541:
542: 0, 1, 1, 2, 2, 2, 2, 2, 2, 2,
543: 2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
544: 2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
545: 2, 2, 3, 4, 12, 5, 13, 13, 13, 6,
546: 6, 6, 6, 6, 6, 6, 6, 7, 7, 7,
547: 8, 8, 8, 10, 14, 11, 15, 16, 9 };
548: short yyr2[]={
549:
550: 0, 0, 2, 4, 4, 4, 4, 4, 4, 4,
551: 5, 5, 5, 5, 3, 5, 3, 5, 5, 3,
552: 5, 1, 2, 4, 2, 2, 5, 5, 3, 3,
553: 2, 2, 1, 1, 1, 11, 1, 1, 1, 1,
554: 3, 1, 3, 1, 1, 3, 2, 1, 1, 1,
555: 1, 1, 1, 1, 1, 2, 5, 4, 0 };
556: short yychk[]={
557:
558: -1000, -1, -2, 274, 275, 279, 281, 282, 283, 294,
559: 284, 311, 285, 286, 302, 301, 299, 300, -11, 305,
560: 306, 280, 307, 308, 309, 310, 278, 256, -15, 296,
561: 269, 269, 269, 269, 269, 269, 269, -9, -9, -9,
562: -9, -9, -9, -9, -9, 270, 269, 270, 270, -9,
563: -9, -9, -9, 270, 270, -16, 297, -9, -3, 272,
564: -4, 272, -5, 273, -6, 257, 260, 262, 263, -7,
565: 261, 266, 265, -8, 267, 258, 259, 273, 269, 269,
566: 269, 269, 270, 269, 270, 269, 269, 270, 269, 272,
567: 269, 269, 270, 270, 269, 269, 270, 270, 270, 271,
568: 270, 269, 269, 269, -12, 273, 270, 270, 270, -10,
569: -14, 272, -10, -10, -10, -10, -10, -10, -10, 270,
570: -10, -10, -10, -10, 273, -13, 264, 268, 259, -13,
571: -12, 270, 270, 270, 270, 270, 270, 270, 270, 270,
572: 270, 270, 270, 271, 273, 271, 273, 271, 273, 271,
573: 273 };
574: short yydef[]={
575:
576: 1, -2, 2, 0, 0, 0, 0, 0, 0, 0,
577: 58, 58, 58, 58, 58, 58, 58, 58, 21, 0,
578: 0, 0, 58, 58, 58, 58, 0, 0, 0, 58,
579: 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
580: 0, 0, 0, 0, 0, 22, 0, 24, 25, 0,
581: 0, 0, 0, 30, 31, 55, 0, 0, 0, 32,
582: 0, 33, 0, 0, 0, 39, 41, 43, 44, 0,
583: 47, 48, 49, 0, 50, 51, 52, 0, 0, 0,
584: 0, 0, 14, 0, 16, 0, 0, 19, 0, 0,
585: 0, 0, 28, 29, 0, 0, 3, 4, 5, 0,
586: 6, 0, 0, 0, 46, 34, 7, 8, 9, 0,
587: 53, 54, 0, 0, 0, 0, 0, 0, 0, 23,
588: 0, 0, 0, 0, 0, 40, 36, 37, 38, 42,
589: 45, 10, 11, 12, 13, 15, 17, 18, 20, 26,
590: 27, 57, 56, 0, 0, 0, 0, 0, 0, 0,
591: 35 };
592: # ifdef YYDEBUG
593: # include "y.debug"
594: # endif
595:
596: # define YYFLAG -1000
597: # define YYERROR goto yyerrlab
598: # define YYACCEPT return(0)
599: # define YYABORT return(1)
600:
601: /* parser for yacc output */
602:
603: #ifdef YYDEBUG
604: int yydebug = 0; /* 1 for debugging */
605: #endif
606: YYSTYPE yyv[YYMAXDEPTH]; /* where the values are stored */
607: int yychar = -1; /* current input token number */
608: int yynerrs = 0; /* number of errors */
609: short yyerrflag = 0; /* error recovery flag */
610:
611: yyparse()
612: { short yys[YYMAXDEPTH];
613: int yyj, yym;
614: register YYSTYPE *yypvt;
615: register int yystate, yyn;
616: register short *yyps;
617: register YYSTYPE *yypv;
618: register short *yyxi;
619:
620: yystate = 0;
621: yychar = -1;
622: yynerrs = 0;
623: yyerrflag = 0;
624: yyps= &yys[-1];
625: yypv= &yyv[-1];
626:
627: yystack: /* put a state and value onto the stack */
628: #ifdef YYDEBUG
629: if(yydebug >= 3)
630: if(yychar < 0 || yytoknames[yychar] == 0)
631: printf("char %d in %s", yychar, yystates[yystate]);
632: else
633: printf("%s in %s", yytoknames[yychar], yystates[yystate]);
634: #endif
635: if( ++yyps >= &yys[YYMAXDEPTH] ) {
636: yyerror( "yacc stack overflow" );
637: return(1);
638: }
639: *yyps = yystate;
640: ++yypv;
641: *yypv = yyval;
642: yynewstate:
643: yyn = yypact[yystate];
644: if(yyn <= YYFLAG) goto yydefault; /* simple state */
645: if(yychar<0) {
646: yychar = yylex();
647: #ifdef YYDEBUG
648: if(yydebug >= 2) {
649: if(yychar <= 0)
650: printf("lex EOF\n");
651: else if(yytoknames[yychar])
652: printf("lex %s\n", yytoknames[yychar]);
653: else
654: printf("lex (%c)\n", yychar);
655: }
656: #endif
657: if(yychar < 0)
658: yychar = 0;
659: }
660: if((yyn += yychar) < 0 || yyn >= YYLAST)
661: goto yydefault;
662: if( yychk[ yyn=yyact[ yyn ] ] == yychar ){ /* valid shift */
663: yychar = -1;
664: yyval = yylval;
665: yystate = yyn;
666: if( yyerrflag > 0 ) --yyerrflag;
667: goto yystack;
668: }
669: yydefault:
670: /* default state action */
671: if( (yyn=yydef[yystate]) == -2 ) {
672: if(yychar < 0) {
673: yychar = yylex();
674: #ifdef YYDEBUG
675: if(yydebug >= 2)
676: if(yychar < 0)
677: printf("lex EOF\n");
678: else
679: printf("lex %s\n", yytoknames[yychar]);
680: #endif
681: if(yychar < 0)
682: yychar = 0;
683: }
684: /* look through exception table */
685: for(yyxi=yyexca; (*yyxi!= (-1)) || (yyxi[1]!=yystate);
686: yyxi += 2 ) ; /* VOID */
687: while( *(yyxi+=2) >= 0 ){
688: if( *yyxi == yychar ) break;
689: }
690: if( (yyn = yyxi[1]) < 0 ) return(0); /* accept */
691: }
692: if( yyn == 0 ){ /* error */
693: /* error ... attempt to resume parsing */
694: switch( yyerrflag ){
695: case 0: /* brand new error */
696: #ifdef YYDEBUG
697: yyerror("syntax error\n%s", yystates[yystate]);
698: if(yytoknames[yychar])
699: yyerror("saw %s\n", yytoknames[yychar]);
700: else if(yychar >= ' ' && yychar < '\177')
701: yyerror("saw `%c'\n", yychar);
702: else if(yychar == 0)
703: yyerror("saw EOF\n");
704: else
705: yyerror("saw char 0%o\n", yychar);
706: #else
707: yyerror( "syntax error" );
708: #endif
709: yyerrlab:
710: ++yynerrs;
711: case 1:
712: case 2: /* incompletely recovered error ... try again */
713: yyerrflag = 3;
714: /* find a state where "error" is a legal shift action */
715: while ( yyps >= yys ) {
716: yyn = yypact[*yyps] + YYERRCODE;
717: if( yyn>= 0 && yyn < YYLAST && yychk[yyact[yyn]] == YYERRCODE ){
718: yystate = yyact[yyn]; /* simulate a shift of "error" */
719: goto yystack;
720: }
721: yyn = yypact[*yyps];
722: /* the current yyps has no shift onn "error", pop stack */
723: #ifdef YYDEBUG
724: if( yydebug ) printf( "error recovery pops state %d, uncovers %d\n", *yyps, yyps[-1] );
725: #endif
726: --yyps;
727: --yypv;
728: }
729: /* there is no state on the stack with an error shift ... abort */
730: yyabort:
731: return(1);
732: case 3: /* no shift yet; clobber input char */
733: #ifdef YYDEBUG
734: if( yydebug ) {
735: printf("error recovery discards ");
736: if(yytoknames[yychar])
737: printf("%s\n", yytoknames[yychar]);
738: else if(yychar >= ' ' && yychar < '\177')
739: printf("`%c'\n", yychar);
740: else if(yychar == 0)
741: printf("EOF\n");
742: else
743: printf("char 0%o\n", yychar);
744: }
745: #endif
746: if( yychar == 0 ) goto yyabort; /* don't discard EOF, quit */
747: yychar = -1;
748: goto yynewstate; /* try again in the same state */
749: }
750: }
751: /* reduction by production yyn */
752: #ifdef YYDEBUG
753: if(yydebug) { char *s;
754: printf("reduce %d in:\n\t", yyn);
755: for(s = yystates[yystate]; *s; s++) {
756: putchar(*s);
757: if(*s == '\n' && *(s+1))
758: putchar('\t');
759: }
760: }
761: #endif
762: yyps -= yyr2[yyn];
763: yypvt = yypv;
764: yypv -= yyr2[yyn];
765: yyval = yypv[1];
766: yym=yyn;
767: /* consult goto table to find next state */
768: yyn = yyr1[yyn];
769: yyj = yypgo[yyn] + *yyps + 1;
770: if( yyj>=YYLAST || yychk[ yystate = yyact[yyj] ] != -yyn ) yystate = yyact[yypgo[yyn]];
771: switch(yym){
772:
773: case 3:
774: # line 74 "ftpcmd.y"
775: {
776: extern struct passwd *getpwnam();
777:
778: pw = getpwnam(yypvt[-1]);
779: reply(331, "Password required for %s.", yypvt[-1]);
780: if (pw->pw_uid==0)
781: pw = NULL;
782: if (pw == NULL)
783: reply(530, "User %s unknown.", yypvt[-1]);
784: free(yypvt[-1]);
785: } break;
786: case 4:
787: # line 86 "ftpcmd.y"
788: {
789: pass(yypvt[-1]);
790: free(yypvt[-1]);
791: } break;
792: case 5:
793: # line 91 "ftpcmd.y"
794: {
795: usedefault = 0;
796: ack(yypvt[-3]);
797: } break;
798: case 6:
799: # line 96 "ftpcmd.y"
800: {
801: switch (cmd_type) {
802:
803: case TYPE_A:
804: if (cmd_form == FORM_N) {
805: reply(200, "Type set to A.");
806: type = cmd_type;
807: form = cmd_form;
808: } else
809: reply(504, "Form must be N.");
810: break;
811:
812: case TYPE_E:
813: reply(504, "Type E not implemented.");
814: break;
815:
816: case TYPE_I:
817: reply(200, "Type set to I.");
818: type = cmd_type;
819: break;
820:
821: case TYPE_L:
822: if (cmd_bytesz == 8) {
823: reply(200,
824: "Type set to L (byte size 8).");
825: type = cmd_type;
826: } else
827: reply(504, "Byte size must be 8.");
828: }
829: } break;
830: case 7:
831: # line 127 "ftpcmd.y"
832: {
833: switch (yypvt[-1]) {
834:
835: case STRU_F:
836: reply(200, "STRU F ok.");
837: break;
838:
839: default:
840: reply(502, "Unimplemented STRU type.");
841: }
842: } break;
843: case 8:
844: # line 139 "ftpcmd.y"
845: {
846: switch (yypvt[-1]) {
847:
848: case MODE_S:
849: reply(200, "MODE S ok.");
850: break;
851:
852: default:
853: reply(502, "Unimplemented MODE type.");
854: }
855: } break;
856: case 9:
857: # line 151 "ftpcmd.y"
858: {
859: ack(yypvt[-3]);
860: } break;
861: case 10:
862: # line 155 "ftpcmd.y"
863: {
864: if (yypvt[-3] && yypvt[-1] != NULL)
865: retrieve(0, yypvt[-1]);
866: if (yypvt[-1] != NULL)
867: free(yypvt[-1]);
868: } break;
869: case 11:
870: # line 162 "ftpcmd.y"
871: {
872: if (yypvt[-3] && yypvt[-1] != NULL)
873: openfile(yypvt[-1]);
874: if (yypvt[-1] != NULL)
875: free(yypvt[-1]);
876: } break;
877: case 12:
878: # line 169 "ftpcmd.y"
879: {
880: if (yypvt[-3] && yypvt[-1] != NULL)
881: store(yypvt[-1], "w");
882: if (yypvt[-1] != NULL)
883: free(yypvt[-1]);
884: } break;
885: case 13:
886: # line 176 "ftpcmd.y"
887: {
888: if (yypvt[-3] && yypvt[-1] != NULL)
889: store(yypvt[-1], "a");
890: if (yypvt[-1] != NULL)
891: free(yypvt[-1]);
892: } break;
893: case 14:
894: # line 183 "ftpcmd.y"
895: {
896: if (yypvt[-1])
897: retrieve("/bin/ls", "");
898: } break;
899: case 15:
900: # line 188 "ftpcmd.y"
901: {
902: if (yypvt[-3] && yypvt[-1] != NULL)
903: retrieve("/bin/ls %s", yypvt[-1]);
904: if (yypvt[-1] != NULL)
905: free(yypvt[-1]);
906: } break;
907: case 16:
908: # line 195 "ftpcmd.y"
909: {
910: if (yypvt[-1])
911: retrieve("/bin/ls -lg", "");
912: } break;
913: case 17:
914: # line 200 "ftpcmd.y"
915: {
916: if (yypvt[-3] && yypvt[-1] != NULL)
917: retrieve("/bin/ls -lg %s", yypvt[-1]);
918: if (yypvt[-1] != NULL)
919: free(yypvt[-1]);
920: } break;
921: case 18:
922: # line 207 "ftpcmd.y"
923: {
924: if (yypvt[-3] && yypvt[-1] != NULL)
925: delete(yypvt[-1]);
926: if (yypvt[-1] != NULL)
927: free(yypvt[-1]);
928: } break;
929: case 19:
930: # line 214 "ftpcmd.y"
931: {
932: if (yypvt[-1])
933: cwd(pw->pw_dir);
934: } break;
935: case 20:
936: # line 219 "ftpcmd.y"
937: {
938: if (yypvt[-3] && yypvt[-1] != NULL)
939: cwd(yypvt[-1]);
940: if (yypvt[-1] != NULL)
941: free(yypvt[-1]);
942: } break;
943: case 22:
944: # line 227 "ftpcmd.y"
945: {
946: help(0);
947: } break;
948: case 23:
949: # line 231 "ftpcmd.y"
950: {
951: help(yypvt[-1]);
952: } break;
953: case 24:
954: # line 235 "ftpcmd.y"
955: {
956: ack(yypvt[-1]);
957: } break;
958: case 25:
959: # line 239 "ftpcmd.y"
960: {
961: pasv++;
962: ack(yypvt[-1]);
963: } break;
964: case 26:
965: # line 244 "ftpcmd.y"
966: {
967: if (yypvt[-3] && yypvt[-1] != NULL)
968: makedir(yypvt[-1]);
969: if (yypvt[-1] != NULL)
970: free(yypvt[-1]);
971: } break;
972: case 27:
973: # line 251 "ftpcmd.y"
974: {
975: if (yypvt[-3] && yypvt[-1] != NULL)
976: removedir(yypvt[-1]);
977: if (yypvt[-1] != NULL)
978: free(yypvt[-1]);
979: } break;
980: case 28:
981: # line 258 "ftpcmd.y"
982: {
983: if (yypvt[-1])
984: pwd();
985: } break;
986: case 29:
987: # line 263 "ftpcmd.y"
988: {
989: if (yypvt[-1])
990: cwd("..");
991: } break;
992: case 30:
993: # line 268 "ftpcmd.y"
994: {
995: reply(221, "Goodbye.");
996: dologout(0);
997: } break;
998: case 31:
999: # line 273 "ftpcmd.y"
1000: {
1001: yyerrok;
1002: } break;
1003: case 35:
1004: # line 289 "ftpcmd.y"
1005: {
1006: sprintf(dest, "tcp!%d.%d.%d.%d!%d",
1007: yypvt[-10], yypvt[-8], yypvt[-6], yypvt[-4], yypvt[-2] * 256 + yypvt[-0]);
1008: } break;
1009: case 36:
1010: # line 296 "ftpcmd.y"
1011: {
1012: yyval = FORM_N;
1013: } break;
1014: case 37:
1015: # line 300 "ftpcmd.y"
1016: {
1017: yyval = FORM_T;
1018: } break;
1019: case 38:
1020: # line 304 "ftpcmd.y"
1021: {
1022: yyval = FORM_C;
1023: } break;
1024: case 39:
1025: # line 310 "ftpcmd.y"
1026: {
1027: cmd_type = TYPE_A;
1028: cmd_form = FORM_N;
1029: } break;
1030: case 40:
1031: # line 315 "ftpcmd.y"
1032: {
1033: cmd_type = TYPE_A;
1034: cmd_form = yypvt[-0];
1035: } break;
1036: case 41:
1037: # line 320 "ftpcmd.y"
1038: {
1039: cmd_type = TYPE_E;
1040: cmd_form = FORM_N;
1041: } break;
1042: case 42:
1043: # line 325 "ftpcmd.y"
1044: {
1045: cmd_type = TYPE_E;
1046: cmd_form = yypvt[-0];
1047: } break;
1048: case 43:
1049: # line 330 "ftpcmd.y"
1050: {
1051: cmd_type = TYPE_I;
1052: } break;
1053: case 44:
1054: # line 334 "ftpcmd.y"
1055: {
1056: cmd_type = TYPE_L;
1057: cmd_bytesz = 8;
1058: } break;
1059: case 45:
1060: # line 339 "ftpcmd.y"
1061: {
1062: cmd_type = TYPE_L;
1063: cmd_bytesz = yypvt[-0];
1064: } break;
1065: case 46:
1066: # line 345 "ftpcmd.y"
1067: {
1068: cmd_type = TYPE_L;
1069: cmd_bytesz = yypvt[-0];
1070: } break;
1071: case 47:
1072: # line 352 "ftpcmd.y"
1073: {
1074: yyval = STRU_F;
1075: } break;
1076: case 48:
1077: # line 356 "ftpcmd.y"
1078: {
1079: yyval = STRU_R;
1080: } break;
1081: case 49:
1082: # line 360 "ftpcmd.y"
1083: {
1084: yyval = STRU_P;
1085: } break;
1086: case 50:
1087: # line 366 "ftpcmd.y"
1088: {
1089: yyval = MODE_S;
1090: } break;
1091: case 51:
1092: # line 370 "ftpcmd.y"
1093: {
1094: yyval = MODE_B;
1095: } break;
1096: case 52:
1097: # line 374 "ftpcmd.y"
1098: {
1099: yyval = MODE_C;
1100: } break;
1101: case 53:
1102: # line 380 "ftpcmd.y"
1103: {
1104: yyval = yypvt[-0];
1105: } break;
1106: case 55:
1107: # line 389 "ftpcmd.y"
1108: {
1109: if (yypvt[-1] && yypvt[-0])
1110: renamecmd(yypvt[-1], yypvt[-0]);
1111: else
1112: reply(503, "Bad sequence of commands.");
1113: if (yypvt[-1])
1114: free(yypvt[-1]);
1115: if (yypvt[-0])
1116: free(yypvt[-0]);
1117: } break;
1118: case 56:
1119: # line 402 "ftpcmd.y"
1120: {
1121: char *from = 0, *renamefrom();
1122:
1123: if (yypvt[-3] && yypvt[-1])
1124: from = renamefrom(yypvt[-1]);
1125: if (from == 0 && yypvt[-1])
1126: free(yypvt[-1]);
1127: yyval = (int)from;
1128: } break;
1129: case 57:
1130: # line 414 "ftpcmd.y"
1131: {
1132: yyval = yypvt[-1];
1133: } break;
1134: case 58:
1135: # line 420 "ftpcmd.y"
1136: {
1137: if (logged_in)
1138: yyval = 1;
1139: else {
1140: reply(530, "Please login with USER and PASS.");
1141: yyval = 0;
1142: }
1143: } break;
1144: }
1145: goto yystack; /* stack new state and value */
1146: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.