Jelajahi Sumber

Fix SCP to handle root path

olegkap_cp 12 tahun lalu
induk
melakukan
e1b2d13a99

+ 3 - 0
Renci.SshClient/Renci.SshNet/ConnectionInfo.cs

@@ -264,6 +264,9 @@ namespace Renci.SshNet
             if (username.IsNullOrWhiteSpace())
                 throw new ArgumentException("username");
 
+            if (authenticationMethods == null || authenticationMethods.Length < 1)
+                throw new ArgumentException("authenticationMethods");
+
             //  Set default connection values
             this.Timeout = TimeSpan.FromSeconds(30);
             this.RetryAttempts = 10;

+ 32 - 14
Renci.SshClient/Renci.SshNet/ScpClient.NET.cs

@@ -17,6 +17,7 @@ namespace Renci.SshNet
     /// </summary>
     public partial class ScpClient
     {
+        private Regex _rootPath = new Regex(@"^(/|[A-Z][:])", RegexOptions.Compiled | RegexOptions.IgnoreCase);
         /// <summary>
         /// Uploads the specified file or directory to the remote host.
         /// </summary>
@@ -42,38 +43,55 @@ namespace Renci.SshNet
 
                 channel.Open();
 
-                var pathParts = path.Split('\\', '/');
+                var isRootPath = _rootPath.Match(path);
 
-                //  Send channel command request
-                channel.SendExecRequest(string.Format("scp -rt \"{0}\"", pathParts[0]));
-                this.CheckReturnCode(input);
+                var pathParts = path.Split('\\', '/');
+                var targetPath = path;
 
-                //  Prepare directory structure
-                for (int i = 0; i < pathParts.Length - 1; i++)
+                if (isRootPath.Success)
+                {
+                    //  Send channel command request
+                    channel.SendExecRequest(string.Format("scp -rt \"{0}\"", path));
+                    this.CheckReturnCode(input);
+                }
+                else
                 {
-                    this.InternalSetTimestamp(channel, input, fileSystemInfo.LastWriteTimeUtc, fileSystemInfo.LastAccessTimeUtc);
-                    this.SendData(channel, string.Format("D0755 0 {0}\n", pathParts[i]));
+                    targetPath = pathParts.Last();
+
+                    //  Send channel command request
+                    channel.SendExecRequest(string.Format("scp -rt \"{0}\"", pathParts[0]));
                     this.CheckReturnCode(input);
+
+                    //  Prepare directory structure
+                    for (int i = 0; i < pathParts.Length - 1; i++)
+                    {
+                        this.InternalSetTimestamp(channel, input, fileSystemInfo.LastWriteTimeUtc, fileSystemInfo.LastAccessTimeUtc);
+                        this.SendData(channel, string.Format("D0755 0 {0}\n", pathParts[i]));
+                        this.CheckReturnCode(input);
+                    }
                 }
 
                 if (fileSystemInfo is FileInfo)
                 {
-                    this.InternalUpload(channel, input, fileSystemInfo as FileInfo, pathParts.Last());
+                    this.InternalUpload(channel, input, fileSystemInfo as FileInfo, targetPath);
                 }
                 else if (fileSystemInfo is DirectoryInfo)
                 {
-                    this.InternalUpload(channel, input, fileSystemInfo as DirectoryInfo, pathParts.Last());
+                    this.InternalUpload(channel, input, fileSystemInfo as DirectoryInfo, targetPath);
                 }
                 else
                 {
                     throw new NotSupportedException(string.Format("Type '{0}' is not supported.", fileSystemInfo.GetType().FullName));
                 }
 
-                //  Finish directory structure
-                for (int i = 0; i < pathParts.Length - 1; i++)
+                if (!isRootPath.Success)
                 {
-                    this.SendData(channel, "E\n");
-                    this.CheckReturnCode(input);
+                    //  Finish directory structure
+                    for (int i = 0; i < pathParts.Length - 1; i++)
+                    {
+                        this.SendData(channel, "E\n");
+                        this.CheckReturnCode(input);
+                    }
                 }
 
                 channel.Close();

+ 1 - 1
Renci.SshClient/Renci.SshNet/ScpClient.cs

@@ -249,7 +249,7 @@ namespace Renci.SshNet
         {
             var length = source.Length;
 
-            this.SendData(channel, string.Format("C0644 {0} {1}\n", length, filename));
+            this.SendData(channel, string.Format("C0644 {0} {1}\n", length, Path.GetFileName(filename)));
 
             var buffer = new byte[this.BufferSize];