X-Git-Url: http://andersk.mit.edu/gitweb/openssh.git/blobdiff_plain/2ceb8101cc5c68200b83966a4821c7bfe1f16123..c9ecc3c71562790fd69d7d595322e9eca55b875b:/sftp.c diff --git a/sftp.c b/sftp.c index a77be84c..a2e3f6aa 100644 --- a/sftp.c +++ b/sftp.c @@ -16,7 +16,7 @@ #include "includes.h" -RCSID("$OpenBSD: sftp.c,v 1.64 2005/06/17 02:44:33 djm Exp $"); +RCSID("$OpenBSD: sftp.c,v 1.70 2006/01/31 10:19:02 djm Exp $"); #ifdef USE_LIBEDIT #include @@ -697,6 +697,8 @@ do_ls_dir(struct sftp_conn *conn, char *path, char *strip_path, int lflag) } if (lflag & SORT_FLAGS) { + for (n = 0; d[n] != NULL; n++) + ; /* count entries */ sort_flag = lflag & (SORT_FLAGS|LS_REVERSE_SORT); qsort(d, n, sizeof(*d), sdirent_comp); } @@ -1237,7 +1239,7 @@ interactive_loop(int fd_in, int fd_out, char *file1, char *file2) char *dir = NULL; char cmd[2048]; struct sftp_conn *conn; - int err; + int err, interactive; EditLine *el = NULL; #ifdef USE_LIBEDIT History *hl = NULL; @@ -1295,14 +1297,15 @@ interactive_loop(int fd_in, int fd_out, char *file1, char *file2) xfree(dir); } -#if HAVE_SETVBUF +#if defined(HAVE_SETVBUF) && !defined(BROKEN_SETVBUF) setvbuf(stdout, NULL, _IOLBF, 0); setvbuf(infile, NULL, _IOLBF, 0); #else - setlinebuf(stdout); - setlinebuf(infile); + setlinebuf(stdout); + setlinebuf(infile); #endif + interactive = !batchmode && isatty(STDIN_FILENO); err = 0; for (;;) { char *cp; @@ -1310,20 +1313,28 @@ interactive_loop(int fd_in, int fd_out, char *file1, char *file2) signal(SIGINT, SIG_IGN); if (el == NULL) { - printf("sftp> "); + if (interactive) + printf("sftp> "); if (fgets(cmd, sizeof(cmd), infile) == NULL) { - printf("\n"); + if (interactive) + printf("\n"); break; } - if (batchmode) /* Echo command */ - printf("%s", cmd); + if (!interactive) { /* Echo command */ + printf("sftp> %s", cmd); + if (strlen(cmd) > 0 && + cmd[strlen(cmd) - 1] != '\n') + printf("\n"); + } } else { #ifdef USE_LIBEDIT const char *line; int count = 0; - if ((line = el_gets(el, &count)) == NULL || count <= 0) - break; + if ((line = el_gets(el, &count)) == NULL || count <= 0) { + printf("\n"); + break; + } history(hl, &hev, H_ENTER, line); if (strlcpy(cmd, line, sizeof(cmd)) >= sizeof(cmd)) { fprintf(stderr, "Error: input line too long\n"); @@ -1346,6 +1357,11 @@ interactive_loop(int fd_in, int fd_out, char *file1, char *file2) } xfree(pwd); +#ifdef USE_LIBEDIT + if (el != NULL) + el_end(el); +#endif /* USE_LIBEDIT */ + /* err == 1 signifies normal "quit" exit */ return (err >= 0 ? 0 : -1); } @@ -1433,11 +1449,16 @@ main(int argc, char **argv) extern int optind; extern char *optarg; + /* Ensure that fds 0, 1 and 2 are open or directed to /dev/null */ + sanitise_stdfd(); + __progname = ssh_get_progname(argv[0]); + memset(&args, '\0', sizeof(args)); args.list = NULL; - addargs(&args, "ssh"); /* overwritten with ssh_program */ + addargs(&args, ssh_program); addargs(&args, "-oForwardX11 no"); addargs(&args, "-oForwardAgent no"); + addargs(&args, "-oPermitLocalCommand no"); addargs(&args, "-oClearAllForwardings yes"); ll = SYSLOG_LEVEL_INFO; @@ -1469,6 +1490,7 @@ main(int argc, char **argv) break; case 'S': ssh_program = optarg; + replacearg(&args, 0, "%s", ssh_program); break; case 'b': if (batchmode) @@ -1476,7 +1498,7 @@ main(int argc, char **argv) /* Allow "-" as stdin */ if (strcmp(optarg, "-") != 0 && - (infile = fopen(optarg, "r")) == NULL) + (infile = fopen(optarg, "r")) == NULL) fatal("%s (%s).", strerror(errno), optarg); showprogress = 0; batchmode = 1; @@ -1545,7 +1567,6 @@ main(int argc, char **argv) addargs(&args, "%s", host); addargs(&args, "%s", (sftp_server != NULL ? sftp_server : "sftp")); - args.list[0] = ssh_program; if (!batchmode) fprintf(stderr, "Connecting to %s...\n", host); @@ -1558,12 +1579,13 @@ main(int argc, char **argv) fprintf(stderr, "Attaching to %s...\n", sftp_direct); connect_to_server(sftp_direct, args.list, &in, &out); } + freeargs(&args); err = interactive_loop(in, out, file1, file2); #if !defined(USE_PIPES) - shutdown(in, SHUT_RDWR); - shutdown(out, SHUT_RDWR); + shutdown(in, SHUT_RDWR); + shutdown(out, SHUT_RDWR); #endif close(in);