[Date Prev][Date Next] [Thread Prev][Thread Next] [Date Index] [Thread Index]

Bug#48057: scp -r follows symlinks



I wrote a patch to fix this problem. I has not been toroughly tested
and it may not apply anymore but it may help some people.

It has been marked as WONTFIX in the OpenSSH Bugzilla.

http://bugzilla.mindrot.org/show_bug.cgi?id=1059
http://openssh.org/faq.html#2.10

Of course nobody is supposed to use scp anymore :)
# Adds an -s option to scp(1) to ignore symlinks.
# Applies to scp.c 1.124 (that's -current from 17 June 2005)
# Patch submitted as part of bugreport #1059 (attachment #933) on 1 July 2005,
# rejected on 12 July 2006.
# http://bugzilla.mindrot.org/show_bug.cgi?id=1059
diff -ur ssh.old/scp.1 ssh/scp.1
--- ssh.old/scp.1	2005-06-30 18:40:29.116463608 +0200
+++ ssh/scp.1	2005-06-30 18:41:12.493869240 +0200
@@ -20,7 +20,7 @@
 .Sh SYNOPSIS
 .Nm scp
 .Bk -words
-.Op Fl 1246BCpqrv
+.Op Fl 1246BCpqrsv
 .Op Fl c Ar cipher
 .Op Fl F Ar ssh_config
 .Op Fl i Ar identity_file
@@ -180,6 +180,8 @@
 Disables the progress meter.
 .It Fl r
 Recursively copy entire directories.
+.It Fl s
+Ignore symbolic links.
 .It Fl S Ar program
 Name of
 .Ar program
@@ -218,3 +220,4 @@
 .Sh AUTHORS
 .An Timo Rinne Aq tri@iki.fi
 .An Tatu Ylonen Aq ylo@cs.hut.fi
+.An Adrien Kunysz (for the -s option) Aq a_kunysz@yahoo.com 
diff -ur ssh.old/scp.c ssh/scp.c
--- ssh.old/scp.c	2005-06-30 18:40:29.117463456 +0200
+++ ssh/scp.c	2005-06-30 18:41:12.532863312 +0200
@@ -200,10 +200,10 @@
 struct passwd *pwd;
 uid_t userid;
 int errs, remin, remout;
-int pflag, iamremote, iamrecursive, targetshouldbedirectory;
+int pflag, iamremote, iamrecursive, targetshouldbedirectory, ignorelinks;
 
 #define	CMDNEEDS	64
-char cmd[CMDNEEDS];		/* must hold "rcp -r -p -d\0" */
+char cmd[CMDNEEDS];		/* must hold "scp -v -r -p -s -d\0" */
 
 int response(void);
 void rsource(char *, struct stat *);
@@ -229,7 +229,7 @@
 	addargs(&args, "-oClearAllForwardings yes");
 
 	fflag = tflag = 0;
-	while ((ch = getopt(argc, argv, "dfl:prtvBCc:i:P:q1246S:o:F:")) != -1)
+	while ((ch = getopt(argc, argv, "dfl:prstvBCc:i:P:q1246S:o:F:")) != -1)
 		switch (ch) {
 		/* User-visible flags. */
 		case '1':
@@ -263,6 +263,9 @@
 		case 'r':
 			iamrecursive = 1;
 			break;
+		case 's':
+			ignorelinks = 1;
+			break;
 		case 'S':
 			ssh_program = xstrdup(optarg);
 			break;
@@ -321,9 +324,10 @@
 	remin = remout = -1;
 	do_cmd_pid = -1;
 	/* Command to be executed on remote system using "ssh". */
-	(void) snprintf(cmd, sizeof cmd, "scp%s%s%s%s",
+	(void) snprintf(cmd, sizeof cmd, "scp%s%s%s%s%s",
 	    verbose_mode ? " -v" : "",
-	    iamrecursive ? " -r" : "", pflag ? " -p" : "",
+	    iamrecursive ? " -r" : "", ignorelinks ? " -s" : "",
+	    pflag ? " -p" : "",
 	    targetshouldbedirectory ? " -d" : "");
 
 	(void) signal(SIGPIPE, lostconn);
@@ -455,8 +459,9 @@
 			len = strlen(_PATH_CP) + strlen(argv[i]) +
 			    strlen(argv[argc - 1]) + 20;
 			bp = xmalloc(len);
-			(void) snprintf(bp, len, "exec %s%s%s %s %s", _PATH_CP,
-			    iamrecursive ? " -r" : "", pflag ? " -p" : "",
+			(void)snprintf(bp, len, "exec %s%s%s%s %s %s", _PATH_CP,
+			    iamrecursive ? " -r" : "", ignorelinks ? " -s" : "",
+			    pflag ? " -p" : "",
 			    argv[i], argv[argc - 1]);
 			if (verbose_mode)
 				fprintf(stderr, "Executing: %s\n", bp);
@@ -516,6 +521,12 @@
 			    name);
 			goto next;
 		}
+		if (ignorelinks) {
+			if (lstat(name, &stb) < 0)
+				goto syserr;
+			if (S_ISLNK(stb.st_mode))
+				goto next;
+		}
 		if ((fd = open(name, O_RDONLY, 0)) < 0)
 			goto syserr;
 		if (fstat(fd, &stb) < 0) {
@@ -1019,7 +1030,7 @@
 usage(void)
 {
 	(void) fprintf(stderr,
-	    "usage: scp [-1246BCpqrv] [-c cipher] [-F ssh_config] [-i identity_file]\n"
+	    "usage: scp [-1246BCpqrsv] [-c cipher] [-F ssh_config] [-i identity_file]\n"
 	    "           [-l limit] [-o ssh_option] [-P port] [-S program]\n"
 	    "           [[user@]host1:]file1 [...] [[user@]host2:]file2\n");
 	exit(1);

Reply to: