Clean up for lint; change some stderr to stdout; bug fix
[unix-history] / usr / src / usr.bin / ftp / ruserpass.c
CommitLineData
3a38a184
GM
1/*
2 * Copyright (c) 1985 Regents of the University of California.
3 * All rights reserved. The Berkeley software License Agreement
4 * specifies the terms and conditions for redistribution.
5 */
6
7#ifndef lint
04480325 8static char sccsid[] = "@(#)ruserpass.c 1.3 (Berkeley) %G%";
3a38a184
GM
9#endif not lint
10
11
12struct macel {
13 char mac_name[9]; /* macro name */
14 char *mac_start; /* start of macro in macbuf */
15 char *mac_end; /* end of macro in macbuf */
16};
17
18extern int macnum, proxy; /* number of defined macros */
19extern struct macel macros[16], *macpt;
20extern char macbuf[4096];
21
22#include <stdio.h>
23#include <utmp.h>
24#include <ctype.h>
25#include <sys/types.h>
26#include <sys/stat.h>
27#include <errno.h>
28
29char *renvlook(), *malloc(), *index(), *getenv(), *getpass(), *getlogin();
04480325 30char *strcpy();
3a38a184
GM
31struct utmp *getutmp();
32static FILE *cfile;
33
34ruserpass(host, aname, apass, aacct)
35 char *host, **aname, **apass, **aacct;
36{
37
38 /* renv(host, aname, apass, aacct);
39 if (*aname == 0 || *apass == 0) */
40 return(rnetrc(host, aname, apass, aacct));
41}
42
43#define DEFAULT 1
44#define LOGIN 2
45#define PASSWD 3
46#define ACCOUNT 4
47#define MACDEF 5
48#define ID 10
49#define MACHINE 11
50
51static char tokval[100];
52
53static struct toktab {
54 char *tokstr;
55 int tval;
56} toktab[]= {
57 "default", DEFAULT,
58 "login", LOGIN,
59 "password", PASSWD,
60 "account", ACCOUNT,
61 "machine", MACHINE,
62 "macdef", MACDEF,
63 0, 0
64};
65
66static
67rnetrc(host, aname, apass, aacct)
68 char *host, **aname, **apass, **aacct;
69{
04480325
GM
70 char *hdir, buf[BUFSIZ], *tmp;
71 int t, i, c;
3a38a184
GM
72 struct stat stb;
73 extern int errno;
74
75 hdir = getenv("HOME");
76 if (hdir == NULL)
77 hdir = ".";
04480325 78 (void) sprintf(buf, "%s/.netrc", hdir);
3a38a184
GM
79 cfile = fopen(buf, "r");
80 if (cfile == NULL) {
81 if (errno != ENOENT)
82 perror(buf);
83 return(0);
84 }
85next:
86 while ((t = token())) switch(t) {
87
88 case DEFAULT:
89 (void) token();
90 continue;
91
92 case MACHINE:
93 if (token() != ID || strcmp(host, tokval))
94 continue;
95 while ((t = token()) && t != MACHINE) switch(t) {
96
97 case LOGIN:
98 if (token())
99 if (*aname == 0) {
04480325
GM
100 *aname = malloc((unsigned) strlen(tokval) + 1);
101 (void) strcpy(*aname, tokval);
3a38a184
GM
102 } else {
103 if (strcmp(*aname, tokval))
104 goto next;
105 }
106 break;
107 case PASSWD:
108 if (fstat(fileno(cfile), &stb) >= 0
109 && (stb.st_mode & 077) != 0) {
e6be46b8 110 fprintf(stderr, "Error - .netrc file not correct mode.\n");
3a38a184
GM
111 fprintf(stderr, "Remove password or correct mode.\n");
112 return(-1);
113 }
114 if (token() && *apass == 0) {
04480325
GM
115 *apass = malloc((unsigned) strlen(tokval) + 1);
116 (void) strcpy(*apass, tokval);
3a38a184
GM
117 }
118 break;
119 case ACCOUNT:
120 if (fstat(fileno(cfile), &stb) >= 0
121 && (stb.st_mode & 077) != 0) {
e6be46b8 122 fprintf(stderr, "Error - .netrc file not correct mode.\n");
3a38a184
GM
123 fprintf(stderr, "Remove account or correct mode.\n");
124 return(-1);
125 }
126 if (token() && *aacct == 0) {
04480325
GM
127 *aacct = malloc((unsigned) strlen(tokval) + 1);
128 (void) strcpy(*aacct, tokval);
3a38a184
GM
129 }
130 break;
131 case MACDEF:
132 if (proxy) {
133 return(0);
134 }
135 while ((c=getc(cfile)) != EOF && c == ' ' || c == '\t');
136 if (c == EOF || c == '\n') {
137 printf("Missing macdef name argument.\n");
138 return(-1);
139 }
140 if (macnum == 16) {
141 printf("Limit of 16 macros have already been defined\n");
142 return(-1);
143 }
144 tmp = macros[macnum].mac_name;
145 *tmp++ = c;
146 for (i=0; i < 8 && (c=getc(cfile)) != EOF &&
147 !isspace(c); ++i) {
148 *tmp++ = c;
149 }
150 if (c == EOF) {
151 printf("Macro definition missing null line terminator.\n");
152 return(-1);
153 }
154 *tmp = '\0';
155 if (c != '\n') {
156 while ((c=getc(cfile)) != EOF && c != '\n');
157 }
158 if (c == EOF) {
159 printf("Macro definition missing null line terminator.\n");
160 return(-1);
161 }
162 if (macnum == 0) {
163 macros[macnum].mac_start = macbuf;
164 }
165 else {
166 macros[macnum].mac_start = macros[macnum-1].mac_end + 1;
167 }
168 tmp = macros[macnum].mac_start;
169 while (tmp != macbuf + 4096) {
170 if ((c=getc(cfile)) == EOF) {
171 printf("Macro definition missing null line terminator.\n");
172 return(-1);
173 }
174 *tmp = c;
175 if (*tmp == '\n') {
176 if (*(tmp-1) == '\0') {
177 macros[macnum++].mac_end = tmp - 1;
178 break;
179 }
180 *tmp = '\0';
181 }
182 tmp++;
183 }
184 if (tmp == macbuf + 4096) {
185 printf("4K macro buffer exceeded\n");
186 return(-1);
187 }
188 break;
189 default:
e6be46b8 190 fprintf(stderr, "Unknown .netrc keyword %s\n", tokval);
3a38a184
GM
191 break;
192 }
193 goto done;
194 }
195done:
04480325
GM
196 (void) fclose(cfile);
197 return(0);
3a38a184
GM
198}
199
200static
201token()
202{
203 char *cp;
204 int c;
205 struct toktab *t;
206
207 if (feof(cfile))
208 return (0);
209 while ((c = getc(cfile)) != EOF &&
210 (c == '\n' || c == '\t' || c == ' ' || c == ','))
211 continue;
212 if (c == EOF)
213 return (0);
214 cp = tokval;
215 if (c == '"') {
216 while ((c = getc(cfile)) != EOF && c != '"') {
217 if (c == '\\')
218 c = getc(cfile);
219 *cp++ = c;
220 }
221 } else {
222 *cp++ = c;
223 while ((c = getc(cfile)) != EOF
224 && c != '\n' && c != '\t' && c != ' ' && c != ',') {
225 if (c == '\\')
226 c = getc(cfile);
227 *cp++ = c;
228 }
229 }
230 *cp = 0;
231 if (tokval[0] == 0)
232 return (0);
233 for (t = toktab; t->tokstr; t++)
234 if (!strcmp(t->tokstr, tokval))
235 return (t->tval);
236 return (ID);
237}