[BACK]Return to scp.c CVS log [TXT][DIR] Up to [local] / src / usr.bin / ssh

Diff for /src/usr.bin/ssh/scp.c between version 1.125.2.2 and 1.126

version 1.125.2.2, 2006/10/06 03:19:33 version 1.126, 2005/09/13 23:40:07
Line 1 
Line 1 
 /* $OpenBSD$ */  
 /*  /*
  * scp - secure remote copy.  This is basically patched BSD rcp which   * scp - secure remote copy.  This is basically patched BSD rcp which
  * uses ssh to do the data transfer (instead of using rcmd).   * uses ssh to do the data transfer (instead of using rcmd).
Line 71 
Line 70 
  *   *
  */   */
   
 #include <sys/param.h>  #include "includes.h"
 #include <sys/types.h>  RCSID("$OpenBSD$");
 #include <sys/wait.h>  
 #include <sys/stat.h>  
 #include <sys/time.h>  
 #include <sys/uio.h>  
   
 #include <ctype.h>  
 #include <dirent.h>  
 #include <errno.h>  
 #include <fcntl.h>  
 #include <pwd.h>  
 #include <signal.h>  
 #include <stdarg.h>  
 #include <stdio.h>  
 #include <stdlib.h>  
 #include <string.h>  
 #include <time.h>  
 #include <unistd.h>  
   
 #include "xmalloc.h"  #include "xmalloc.h"
 #include "atomicio.h"  #include "atomicio.h"
 #include "pathnames.h"  #include "pathnames.h"
Line 98 
Line 80 
 #include "misc.h"  #include "misc.h"
 #include "progressmeter.h"  #include "progressmeter.h"
   
 int do_cmd(char *host, char *remuser, char *cmd, int *fdin, int *fdout);  int do_cmd(char *host, char *remuser, char *cmd, int *fdin, int *fdout, int argc);
   
 void bwlimit(int);  void bwlimit(int);
   
Line 136 
Line 118 
         exit(1);          exit(1);
 }  }
   
 static int  
 do_local_cmd(arglist *a)  
 {  
         u_int i;  
         int status;  
         pid_t pid;  
   
         if (a->num == 0)  
                 fatal("do_local_cmd: no arguments");  
   
         if (verbose_mode) {  
                 fprintf(stderr, "Executing:");  
                 for (i = 0; i < a->num; i++)  
                         fprintf(stderr, " %s", a->list[i]);  
                 fprintf(stderr, "\n");  
         }  
         if ((pid = fork()) == -1)  
                 fatal("do_local_cmd: fork: %s", strerror(errno));  
   
         if (pid == 0) {  
                 execvp(a->list[0], a->list);  
                 perror(a->list[0]);  
                 exit(1);  
         }  
   
         do_cmd_pid = pid;  
         signal(SIGTERM, killchild);  
         signal(SIGINT, killchild);  
         signal(SIGHUP, killchild);  
   
         while (waitpid(pid, &status, 0) == -1)  
                 if (errno != EINTR)  
                         fatal("do_local_cmd: waitpid: %s", strerror(errno));  
   
         do_cmd_pid = -1;  
   
         if (!WIFEXITED(status) || WEXITSTATUS(status) != 0)  
                 return (-1);  
   
         return (0);  
 }  
   
 /*  /*
  * This function executes the given command as the specified user on the   * This function executes the given command as the specified user on the
  * given host.  This returns < 0 if execution fails, and >= 0 otherwise. This   * given host.  This returns < 0 if execution fails, and >= 0 otherwise. This
Line 185 
Line 125 
  */   */
   
 int  int
 do_cmd(char *host, char *remuser, char *cmd, int *fdin, int *fdout)  do_cmd(char *host, char *remuser, char *cmd, int *fdin, int *fdout, int argc)
 {  {
         int pin[2], pout[2], reserved[2];          int pin[2], pout[2], reserved[2];
   
Line 199 
Line 139 
          * Reserve two descriptors so that the real pipes won't get           * Reserve two descriptors so that the real pipes won't get
          * descriptors 0 and 1 because that will screw up dup2 below.           * descriptors 0 and 1 because that will screw up dup2 below.
          */           */
         if (pipe(reserved) < 0)          pipe(reserved);
                 fatal("pipe: %s", strerror(errno));  
   
         /* Create a socket pair for communicating with ssh. */          /* Create a socket pair for communicating with ssh. */
         if (pipe(pin) < 0)          if (pipe(pin) < 0)
Line 223 
Line 162 
                 close(pin[0]);                  close(pin[0]);
                 close(pout[1]);                  close(pout[1]);
   
                 replacearg(&args, 0, "%s", ssh_program);                  args.list[0] = ssh_program;
                 if (remuser != NULL)                  if (remuser != NULL)
                         addargs(&args, "-l%s", remuser);                          addargs(&args, "-l%s", remuser);
                 addargs(&args, "%s", host);                  addargs(&args, "%s", host);
Line 253 
Line 192 
   
 BUF *allocbuf(BUF *, int, int);  BUF *allocbuf(BUF *, int, int);
 void lostconn(int);  void lostconn(int);
   void nospace(void);
 int okname(char *);  int okname(char *);
 void run_err(const char *,...);  void run_err(const char *,...);
 void verifydir(char *);  void verifydir(char *);
Line 276 
Line 216 
 int  int
 main(int argc, char **argv)  main(int argc, char **argv)
 {  {
         int ch, fflag, tflag, status, n;          int ch, fflag, tflag, status;
         double speed;          double speed;
         char *targ, *endp, **newargv;          char *targ, *endp;
         extern char *optarg;          extern char *optarg;
         extern int optind;          extern int optind;
   
         /* Ensure that fds 0, 1 and 2 are open or directed to /dev/null */          /* Ensure that fds 0, 1 and 2 are open or directed to /dev/null */
         sanitise_stdfd();          sanitise_stdfd();
   
         /* Copy argv, because we modify it */  
         newargv = xcalloc(MAX(argc + 1, 1), sizeof(*newargv));  
         for (n = 0; n < argc; n++)  
                 newargv[n] = xstrdup(argv[n]);  
         argv = newargv;  
   
         memset(&args, '\0', sizeof(args));  
         args.list = NULL;          args.list = NULL;
         addargs(&args, "%s", ssh_program);          addargs(&args, "ssh");          /* overwritten with ssh_program */
         addargs(&args, "-x");          addargs(&args, "-x");
         addargs(&args, "-oForwardAgent no");          addargs(&args, "-oForwardAgent no");
         addargs(&args, "-oPermitLocalCommand no");  
         addargs(&args, "-oClearAllForwardings yes");          addargs(&args, "-oClearAllForwardings yes");
   
         fflag = tflag = 0;          fflag = tflag = 0;
Line 402 
Line 334 
         if ((targ = colon(argv[argc - 1])))     /* Dest is remote host. */          if ((targ = colon(argv[argc - 1])))     /* Dest is remote host. */
                 toremote(targ, argc, argv);                  toremote(targ, argc, argv);
         else {          else {
                   tolocal(argc, argv);    /* Dest is local host. */
                 if (targetshouldbedirectory)                  if (targetshouldbedirectory)
                         verifydir(argv[argc - 1]);                          verifydir(argv[argc - 1]);
                 tolocal(argc, argv);    /* Dest is local host. */  
         }          }
         /*          /*
          * Finally check the exit status of the ssh process, if one was forked           * Finally check the exit status of the ssh process, if one was forked
Line 428 
Line 360 
 void  void
 toremote(char *targ, int argc, char **argv)  toremote(char *targ, int argc, char **argv)
 {  {
           int i, len;
         char *bp, *host, *src, *suser, *thost, *tuser, *arg;          char *bp, *host, *src, *suser, *thost, *tuser, *arg;
         arglist alist;  
         int i;  
   
         memset(&alist, '\0', sizeof(alist));  
         alist.list = NULL;  
   
         *targ++ = 0;          *targ++ = 0;
         if (*targ == 0)          if (*targ == 0)
                 targ = ".";                  targ = ".";
Line 451 
Line 379 
                 tuser = NULL;                  tuser = NULL;
         }          }
   
         if (tuser != NULL && !okname(tuser)) {  
                 xfree(arg);  
                 return;  
         }  
   
         for (i = 0; i < argc - 1; i++) {          for (i = 0; i < argc - 1; i++) {
                 src = colon(argv[i]);                  src = colon(argv[i]);
                 if (src) {      /* remote to remote */                  if (src) {      /* remote to remote */
                         freeargs(&alist);                          static char *ssh_options =
                         addargs(&alist, "%s", ssh_program);                              "-x -o'ClearAllForwardings yes'";
                         if (verbose_mode)  
                                 addargs(&alist, "-v");  
                         addargs(&alist, "-x");  
                         addargs(&alist, "-oClearAllForwardings yes");  
                         addargs(&alist, "-n");  
   
                         *src++ = 0;                          *src++ = 0;
                         if (*src == 0)                          if (*src == 0)
                                 src = ".";                                  src = ".";
                         host = strrchr(argv[i], '@');                          host = strrchr(argv[i], '@');
                           len = strlen(ssh_program) + strlen(argv[i]) +
                               strlen(src) + (tuser ? strlen(tuser) : 0) +
                               strlen(thost) + strlen(targ) +
                               strlen(ssh_options) + CMDNEEDS + 20;
                           bp = xmalloc(len);
                         if (host) {                          if (host) {
                                 *host++ = 0;                                  *host++ = 0;
                                 host = cleanhostname(host);                                  host = cleanhostname(host);
                                 suser = argv[i];                                  suser = argv[i];
                                 if (*suser == '\0')                                  if (*suser == '\0')
                                         suser = pwd->pw_name;                                          suser = pwd->pw_name;
                                 else if (!okname(suser))                                  else if (!okname(suser)) {
                                           xfree(bp);
                                         continue;                                          continue;
                                 addargs(&alist, "-l");                                  }
                                 addargs(&alist, "%s", suser);                                  if (tuser && !okname(tuser)) {
                                           xfree(bp);
                                           continue;
                                   }
                                   snprintf(bp, len,
                                       "%s%s %s -n "
                                       "-l %s %s %s %s '%s%s%s:%s'",
                                       ssh_program, verbose_mode ? " -v" : "",
                                       ssh_options, suser, host, cmd, src,
                                       tuser ? tuser : "", tuser ? "@" : "",
                                       thost, targ);
                         } else {                          } else {
                                 host = cleanhostname(argv[i]);                                  host = cleanhostname(argv[i]);
                                   snprintf(bp, len,
                                       "exec %s%s %s -n %s "
                                       "%s %s '%s%s%s:%s'",
                                       ssh_program, verbose_mode ? " -v" : "",
                                       ssh_options, host, cmd, src,
                                       tuser ? tuser : "", tuser ? "@" : "",
                                       thost, targ);
                         }                          }
                         addargs(&alist, "%s", host);                          if (verbose_mode)
                         addargs(&alist, "%s", cmd);                                  fprintf(stderr, "Executing: %s\n", bp);
                         addargs(&alist, "%s", src);                          if (system(bp) != 0)
                         addargs(&alist, "%s%s%s:%s",  
                             tuser ? tuser : "", tuser ? "@" : "",  
                             thost, targ);  
                         if (do_local_cmd(&alist) != 0)  
                                 errs = 1;                                  errs = 1;
                           (void) xfree(bp);
                 } else {        /* local to remote */                  } else {        /* local to remote */
                         if (remin == -1) {                          if (remin == -1) {
                                 xasprintf(&bp, "%s -t %s", cmd, targ);                                  len = strlen(targ) + CMDNEEDS + 20;
                                   bp = xmalloc(len);
                                   (void) snprintf(bp, len, "%s -t %s", cmd, targ);
                                 host = cleanhostname(thost);                                  host = cleanhostname(thost);
                                 if (do_cmd(host, tuser, bp, &remin,                                  if (do_cmd(host, tuser, bp, &remin,
                                     &remout) < 0)                                      &remout, argc) < 0)
                                         exit(1);                                          exit(1);
                                 if (response() < 0)                                  if (response() < 0)
                                         exit(1);                                          exit(1);
Line 507 
Line 445 
                         source(1, argv + i);                          source(1, argv + i);
                 }                  }
         }          }
         xfree(arg);  
 }  }
   
 void  void
 tolocal(int argc, char **argv)  tolocal(int argc, char **argv)
 {  {
           int i, len;
         char *bp, *host, *src, *suser;          char *bp, *host, *src, *suser;
         arglist alist;  
         int i;  
   
         memset(&alist, '\0', sizeof(alist));  
         alist.list = NULL;  
   
         for (i = 0; i < argc - 1; i++) {          for (i = 0; i < argc - 1; i++) {
                 if (!(src = colon(argv[i]))) {  /* Local to local. */                  if (!(src = colon(argv[i]))) {  /* Local to local. */
                         freeargs(&alist);                          len = strlen(_PATH_CP) + strlen(argv[i]) +
                         addargs(&alist, "%s", _PATH_CP);                              strlen(argv[argc - 1]) + 20;
                         if (iamrecursive)                          bp = xmalloc(len);
                                 addargs(&alist, "-r");                          (void) snprintf(bp, len, "exec %s%s%s %s %s", _PATH_CP,
                         if (pflag)                              iamrecursive ? " -r" : "", pflag ? " -p" : "",
                                 addargs(&alist, "-p");                              argv[i], argv[argc - 1]);
                         addargs(&alist, "%s", argv[i]);                          if (verbose_mode)
                         addargs(&alist, "%s", argv[argc-1]);                                  fprintf(stderr, "Executing: %s\n", bp);
                         if (do_local_cmd(&alist))                          if (system(bp))
                                 ++errs;                                  ++errs;
                           (void) xfree(bp);
                         continue;                          continue;
                 }                  }
                 *src++ = 0;                  *src++ = 0;
Line 547 
Line 481 
                                 suser = pwd->pw_name;                                  suser = pwd->pw_name;
                 }                  }
                 host = cleanhostname(host);                  host = cleanhostname(host);
                 xasprintf(&bp, "%s -f %s", cmd, src);                  len = strlen(src) + CMDNEEDS + 20;
                 if (do_cmd(host, suser, bp, &remin, &remout) < 0) {                  bp = xmalloc(len);
                   (void) snprintf(bp, len, "%s -f %s", cmd, src);
                   if (do_cmd(host, suser, bp, &remin, &remout, argc) < 0) {
                         (void) xfree(bp);                          (void) xfree(bp);
                         ++errs;                          ++errs;
                         continue;                          continue;
Line 630 
Line 566 
                 if (response() < 0)                  if (response() < 0)
                         goto next;                          goto next;
                 if ((bp = allocbuf(&buffer, fd, 2048)) == NULL) {                  if ((bp = allocbuf(&buffer, fd, 2048)) == NULL) {
 next:                   if (fd != -1) {  next:                   (void) close(fd);
                                 (void) close(fd);  
                                 fd = -1;  
                         }  
                         continue;                          continue;
                 }                  }
                 if (showprogress)                  if (showprogress)
Line 662 
Line 595 
                 if (showprogress)                  if (showprogress)
                         stop_progress_meter();                          stop_progress_meter();
   
                 if (fd != -1) {                  if (close(fd) < 0 && !haderr)
                         if (close(fd) < 0 && !haderr)                          haderr = errno;
                                 haderr = errno;  
                         fd = -1;  
                 }  
                 if (!haderr)                  if (!haderr)
                         (void) atomicio(vwrite, remout, "", 1);                          (void) atomicio(vwrite, remout, "", 1);
                 else                  else
Line 793 
Line 723 
         BUF *bp;          BUF *bp;
         off_t i;          off_t i;
         size_t j, count;          size_t j, count;
         int amt, exists, first, ofd;          int amt, exists, first, mask, mode, ofd, omode;
         mode_t mode, omode, mask;  
         off_t size, statbytes;          off_t size, statbytes;
         int setimes, targisdir, wrerrno = 0;          int setimes, targisdir, wrerrno = 0;
         char ch, *cp, *np, *targ, *why, *vect[1], buf[2048];          char ch, *cp, *np, *targ, *why, *vect[1], buf[2048];
Line 1106 
Line 1035 
         va_list ap;          va_list ap;
   
         ++errs;          ++errs;
         if (fp != NULL || (remout != -1 && (fp = fdopen(remout, "w")))) {          if (fp == NULL && !(fp = fdopen(remout, "w")))
                 (void) fprintf(fp, "%c", 0x01);                  return;
                 (void) fprintf(fp, "scp: ");          (void) fprintf(fp, "%c", 0x01);
                 va_start(ap, fmt);          (void) fprintf(fp, "scp: ");
                 (void) vfprintf(fp, fmt, ap);          va_start(ap, fmt);
                 va_end(ap);          (void) vfprintf(fp, fmt, ap);
                 (void) fprintf(fp, "\n");          va_end(ap);
                 (void) fflush(fp);          (void) fprintf(fp, "\n");
         }          (void) fflush(fp);
   
         if (!iamremote) {          if (!iamremote) {
                 va_start(ap, fmt);                  va_start(ap, fmt);
Line 1186 
Line 1115 
         if (bp->buf == NULL)          if (bp->buf == NULL)
                 bp->buf = xmalloc(size);                  bp->buf = xmalloc(size);
         else          else
                 bp->buf = xrealloc(bp->buf, 1, size);                  bp->buf = xrealloc(bp->buf, size);
         memset(bp->buf, 0, size);          memset(bp->buf, 0, size);
         bp->cnt = size;          bp->cnt = size;
         return (bp);          return (bp);

Legend:
Removed from v.1.125.2.2  
changed lines
  Added in v.1.126