commented out stuff; allocate block for binary transfer, based on st_blksize;
redo reply/lreply as taking multiple arguments -- this should be ripped out
at some point and made to use varargs/vsyslog.
SCCS-vsn: libexec/ftpd/ftpd.c 5.22
#endif /* not lint */
#ifndef lint
#endif /* not lint */
#ifndef lint
-static char sccsid[] = "@(#)ftpd.c 5.21 (Berkeley) %G%";
+static char sccsid[] = "@(#)ftpd.c 5.22 (Berkeley) %G%";
case 't':
timeout = atoi(++cp);
goto nextopt;
case 't':
timeout = atoi(++cp);
goto nextopt;
default:
fprintf(stderr, "ftpd: Unknown flag -%c ignored.\n",
default:
fprintf(stderr, "ftpd: Unknown flag -%c ignored.\n",
login_attempts = 0; /* this time successful */
(void) setegid((gid_t)pw->pw_gid);
(void) initgroups(pw->pw_name, pw->pw_gid);
login_attempts = 0; /* this time successful */
(void) setegid((gid_t)pw->pw_gid);
(void) initgroups(pw->pw_name, pw->pw_gid);
- if (chdir(pw->pw_dir)) {
- reply(530, "User %s: can't change directory to %s.",
- pw->pw_name, pw->pw_dir);
- goto bad;
- }
/* open wtmp before chroot */
(void)sprintf(ttyline, "ftp%d", getpid());
logwtmp(ttyline, pw->pw_name, remotehost);
logged_in = 1;
/* open wtmp before chroot */
(void)sprintf(ttyline, "ftp%d", getpid());
logwtmp(ttyline, pw->pw_name, remotehost);
logged_in = 1;
- if (guest && chroot(pw->pw_dir) < 0) {
- reply(550, "Can't set guest privileges.");
- goto bad;
+ if (guest) {
+ if (chroot(pw->pw_dir) < 0) {
+ reply(550, "Can't set guest privileges.");
+ goto bad;
+ }
+ else if (chdir(pw->pw_dir))
+ if (chdir("/")) {
+ reply(530, "User %s: can't change directory to %s.",
+ pw->pw_name, pw->pw_dir);
+ goto bad;
+ }
+ else
+ lreply(230, "No directory! Logging in with home=/");
if (seteuid((uid_t)pw->pw_uid) < 0) {
reply(550, "Can't set uid.");
goto bad;
if (seteuid((uid_t)pw->pw_uid) < 0) {
reply(550, "Can't set uid.");
goto bad;
struct stat st;
int (*closefunc)(), tmp;
struct stat st;
int (*closefunc)(), tmp;
- if (cmd == 0) {
-#ifdef notdef
- /* no remote command execution -- it's a security hole */
- if (*name == '|')
- fin = ftpd_popen(name + 1, "r"),
- closefunc = ftpd_pclose;
- else
-#endif
- fin = fopen(name, "r"), closefunc = fclose;
- } else {
+ if (cmd == 0)
+ fin = fopen(name, "r"), closefunc = fclose;
+ else {
char line[BUFSIZ];
(void) sprintf(line, cmd, name), name = line;
char line[BUFSIZ];
(void) sprintf(line, cmd, name), name = line;
dout = dataconn(name, st.st_size, "w");
if (dout == NULL)
goto done;
dout = dataconn(name, st.st_size, "w");
if (dout == NULL)
goto done;
- if ((tmp = send_data(fin, dout)) > 0 || ferror(dout) > 0) {
+ if ((tmp = send_data(fin, dout, st.st_blksize)) > 0 ||
+ ferror(dout) > 0) {
perror_reply(550, name);
}
else if (tmp == 0) {
perror_reply(550, name);
}
else if (tmp == 0) {
int unique;
{
FILE *fout, *din;
int unique;
{
FILE *fout, *din;
int (*closefunc)(), tmp;
char *gunique();
int (*closefunc)(), tmp;
char *gunique();
-#ifdef notdef
- /* no remote command execution -- it's a security hole */
- if (name[0] == '|')
- fout = ftpd_popen(&name[1], "w"), closefunc = ftpd_pclose;
- else
-#endif
- {
- struct stat st;
+ if (unique && stat(name, &st) == 0 &&
+ (name = gunique(name)) == NULL)
+ return;
- if (unique && stat(name, &st) == 0 &&
- (name = gunique(name)) == NULL)
- return;
- fout = fopen(name, mode), closefunc = fclose;
- }
+ fout = fopen(name, mode), closefunc = fclose;
if (fout == NULL) {
perror_reply(553, name);
return;
if (fout == NULL) {
perror_reply(553, name);
return;
*
* NB: Form isn't handled.
*/
*
* NB: Form isn't handled.
*/
-send_data(instr, outstr)
+send_data(instr, outstr, blksize)
- register int c;
- int netfd, filefd, cnt;
- char buf[BUFSIZ];
+ register int c, cnt;
+ register char *buf;
+ int netfd, filefd;
transflag++;
if (setjmp(urgcatch)) {
transflag++;
if (setjmp(urgcatch)) {
(void) putc('\r', outstr);
}
(void) putc(c, outstr);
(void) putc('\r', outstr);
}
(void) putc(c, outstr);
- /* if (c == '\r') */
- /* putc ('\0', outstr); */
}
transflag = 0;
if (ferror (instr) || ferror (outstr)) {
return (1);
}
return (0);
}
transflag = 0;
if (ferror (instr) || ferror (outstr)) {
return (1);
}
return (0);
case TYPE_I:
case TYPE_L:
case TYPE_I:
case TYPE_L:
+ if ((buf = malloc((u_int)blksize)) == NULL) {
+ transflag = 0;
+ return (1);
+ }
netfd = fileno(outstr);
filefd = fileno(instr);
netfd = fileno(outstr);
filefd = fileno(instr);
-
- while ((cnt = read(filefd, buf, sizeof (buf))) > 0) {
- if (write(netfd, buf, cnt) < 0) {
- transflag = 0;
- return (1);
- }
- }
+ while ((cnt = read(filefd, buf, sizeof(buf))) > 0 &&
+ write(netfd, buf, cnt) == cnt);
+ (void)free(buf);
+ return (cnt != 0);
}
reply(550, "Unimplemented TYPE %d in send_data", type);
transflag = 0;
}
reply(550, "Unimplemented TYPE %d in send_data", type);
transflag = 0;
+/* VARARGS2 */
+reply(n, fmt, p0, p1, p2, p3, p4, p5)
- char *s;
- va_list argp;
+ printf(fmt, p0, p1, p2, p3, p4, p5);
printf("\r\n");
(void)fflush(stdout);
if (debug) {
syslog(LOG_DEBUG, "<--- %d ", n);
printf("\r\n");
(void)fflush(stdout);
if (debug) {
syslog(LOG_DEBUG, "<--- %d ", n);
- syslog(LOG_DEBUG, s, argp);
+ syslog(LOG_DEBUG, fmt, p0, p1, p2, p3, p4, p5);
+/* VARARGS2 */
+lreply(n, fmt, p0, p1, p2, p3, p4, p5)
- printf("%d- %s\r\n", n, s);
+ printf("%d- ", n);
+ printf(fmt, p0, p1, p2, p3, p4, p5);
+ printf("\r\n");
- if (debug)
- syslog(LOG_DEBUG, "<--- %d- %s", n, s);
+ if (debug) {
+ syslog(LOG_DEBUG, "<--- %d- ", n);
+ syslog(LOG_DEBUG, fmt, p0, p1, p2, p3, p4, p5);
+ }