Browse Source

Add couple more extended requests for future support

olegkap_cp 13 years ago
parent
commit
2c9928aa1e

+ 6 - 0
Renci.SshClient/Renci.SshNet.NET35/Renci.SshNet.NET35.csproj

@@ -639,6 +639,12 @@
     <Compile Include="..\Renci.SshNet\Sftp\Flags.cs">
       <Link>Sftp\Flags.cs</Link>
     </Compile>
+    <Compile Include="..\Renci.SshNet\Sftp\Requests\ExtendedRequests\FStatVfsRequest.cs">
+      <Link>Sftp\Requests\ExtendedRequests\FStatVfsRequest.cs</Link>
+    </Compile>
+    <Compile Include="..\Renci.SshNet\Sftp\Requests\ExtendedRequests\HardLinkRequest.cs">
+      <Link>Sftp\Requests\ExtendedRequests\HardLinkRequest.cs</Link>
+    </Compile>
     <Compile Include="..\Renci.SshNet\Sftp\Requests\ExtendedRequests\PosixRenameRequest.cs">
       <Link>Sftp\Requests\ExtendedRequests\PosixRenameRequest.cs</Link>
     </Compile>

+ 6 - 0
Renci.SshClient/Renci.SshNet.Silverlight/Renci.SshNet.Silverlight.csproj

@@ -606,6 +606,12 @@
     <Compile Include="..\Renci.SshNet\Sftp\Flags.cs">
       <Link>Sftp\Flags.cs</Link>
     </Compile>
+    <Compile Include="..\Renci.SshNet\Sftp\Requests\ExtendedRequests\FStatVfsRequest.cs">
+      <Link>Sftp\Requests\ExtendedRequests\FStatVfsRequest.cs</Link>
+    </Compile>
+    <Compile Include="..\Renci.SshNet\Sftp\Requests\ExtendedRequests\HardLinkRequest.cs">
+      <Link>Sftp\Requests\ExtendedRequests\HardLinkRequest.cs</Link>
+    </Compile>
     <Compile Include="..\Renci.SshNet\Sftp\Requests\ExtendedRequests\PosixRenameRequest.cs">
       <Link>Sftp\Requests\ExtendedRequests\PosixRenameRequest.cs</Link>
     </Compile>

+ 6 - 0
Renci.SshClient/Renci.SshNet.Silverlight5/Renci.SshNet.Silverlight5.csproj

@@ -612,6 +612,12 @@
     <Compile Include="..\Renci.SshNet\Sftp\Flags.cs">
       <Link>Sftp\Flags.cs</Link>
     </Compile>
+    <Compile Include="..\Renci.SshNet\Sftp\Requests\ExtendedRequests\FStatVfsRequest.cs">
+      <Link>Sftp\Requests\ExtendedRequests\FStatVfsRequest.cs</Link>
+    </Compile>
+    <Compile Include="..\Renci.SshNet\Sftp\Requests\ExtendedRequests\HardLinkRequest.cs">
+      <Link>Sftp\Requests\ExtendedRequests\HardLinkRequest.cs</Link>
+    </Compile>
     <Compile Include="..\Renci.SshNet\Sftp\Requests\ExtendedRequests\PosixRenameRequest.cs">
       <Link>Sftp\Requests\ExtendedRequests\PosixRenameRequest.cs</Link>
     </Compile>

+ 6 - 0
Renci.SshClient/Renci.SshNet.WindowsPhone/Renci.SshNet.WindowsPhone.csproj

@@ -610,6 +610,12 @@
     <Compile Include="..\Renci.SshNet\Sftp\Flags.cs">
       <Link>Sftp\Flags.cs</Link>
     </Compile>
+    <Compile Include="..\Renci.SshNet\Sftp\Requests\ExtendedRequests\FStatVfsRequest.cs">
+      <Link>Sftp\Requests\ExtendedRequests\FStatVfsRequest.cs</Link>
+    </Compile>
+    <Compile Include="..\Renci.SshNet\Sftp\Requests\ExtendedRequests\HardLinkRequest.cs">
+      <Link>Sftp\Requests\ExtendedRequests\HardLinkRequest.cs</Link>
+    </Compile>
     <Compile Include="..\Renci.SshNet\Sftp\Requests\ExtendedRequests\PosixRenameRequest.cs">
       <Link>Sftp\Requests\ExtendedRequests\PosixRenameRequest.cs</Link>
     </Compile>

+ 6 - 0
Renci.SshClient/Renci.SshNet.WindowsPhone8/Renci.SshNet.WindowsPhone8.csproj

@@ -653,6 +653,12 @@
     <Compile Include="..\Renci.SshNet\Sftp\Flags.cs">
       <Link>Sftp\Flags.cs</Link>
     </Compile>
+    <Compile Include="..\Renci.SshNet\Sftp\Requests\ExtendedRequests\FStatVfsRequest.cs">
+      <Link>Sftp\Requests\ExtendedRequests\FStatVfsRequest.cs</Link>
+    </Compile>
+    <Compile Include="..\Renci.SshNet\Sftp\Requests\ExtendedRequests\HardLinkRequest.cs">
+      <Link>Sftp\Requests\ExtendedRequests\HardLinkRequest.cs</Link>
+    </Compile>
     <Compile Include="..\Renci.SshNet\Sftp\Requests\ExtendedRequests\PosixRenameRequest.cs">
       <Link>Sftp\Requests\ExtendedRequests\PosixRenameRequest.cs</Link>
     </Compile>

+ 2 - 0
Renci.SshClient/Renci.SshNet/Renci.SshNet.csproj

@@ -358,6 +358,8 @@
     </Compile>
     <Compile Include="SftpClient.NET40.cs" />
     <Compile Include="Sftp\Flags.cs" />
+    <Compile Include="Sftp\Requests\ExtendedRequests\FStatVfsRequest.cs" />
+    <Compile Include="Sftp\Requests\ExtendedRequests\HardLinkRequest.cs" />
     <Compile Include="Sftp\Requests\SftpUnblockRequest.cs" />
     <Compile Include="Sftp\Requests\SftpBlockRequest.cs" />
     <Compile Include="Sftp\Requests\SftpExtendedRequest.cs" />

+ 33 - 0
Renci.SshClient/Renci.SshNet/Sftp/Requests/ExtendedRequests/FStatVfsRequest.cs

@@ -0,0 +1,33 @@
+using System;
+using Renci.SshNet.Sftp.Responses;
+
+namespace Renci.SshNet.Sftp.Requests
+{
+    internal class FStatVfsRequest : SftpExtendedRequest
+    {
+        public override SftpMessageTypes SftpMessageType
+        {
+            get { return SftpMessageTypes.Extended; }
+        }
+
+        public override string Name
+        {
+            get { return "fstatvfs@openssh.com"; }
+        }
+
+        public byte[] Handle { get; private set; }
+
+        public FStatVfsRequest(uint protocolVersion, uint requestId, byte[] handle, Action<SftpExtendedReplyResponse> extendedAction, Action<SftpStatusResponse> statusAction)
+            : base(protocolVersion, requestId, statusAction)
+        {
+            this.Handle = handle;
+            this.SetAction(extendedAction);
+        }
+
+        protected override void SaveData()
+        {
+            base.SaveData();
+            this.WriteBinaryString(this.Handle);
+        }
+    }
+}

+ 36 - 0
Renci.SshClient/Renci.SshNet/Sftp/Requests/ExtendedRequests/HardLinkRequest.cs

@@ -0,0 +1,36 @@
+using System;
+using Renci.SshNet.Sftp.Responses;
+
+namespace Renci.SshNet.Sftp.Requests
+{
+    internal class HardLinkRequest : SftpExtendedRequest
+    {
+        public override SftpMessageTypes SftpMessageType
+        {
+            get { return SftpMessageTypes.Extended; }
+        }
+        
+        public override string Name
+        {
+            get { return "hardlink@openssh.com"; }
+        }
+
+        public string OldPath { get; private set; }
+
+        public string NewPath { get; private set; }
+
+        public HardLinkRequest(uint protocolVersion, uint requestId, string oldPath, string newPath, Action<SftpStatusResponse> statusAction)
+            : base(protocolVersion, requestId, statusAction)
+        {
+            this.OldPath = oldPath;
+            this.NewPath = newPath;
+        }
+
+        protected override void SaveData()
+        {
+            base.SaveData();
+            this.Write(this.OldPath);
+            this.Write(this.NewPath);
+        }
+    }
+}

+ 0 - 1
Renci.SshClient/Renci.SshNet/Sftp/Requests/SftpUnblockRequest.cs

@@ -25,7 +25,6 @@ namespace Renci.SshNet.Sftp.Requests
             this.Handle = handle;
             this.Offset = offset;
             this.Length = length;
-            this.SetAction(dataAction);
         }
 
         protected override void LoadData()

+ 94 - 1
Renci.SshClient/Renci.SshNet/Sftp/SftpSession.cs

@@ -25,6 +25,8 @@ namespace Renci.SshNet.Sftp
 
         private EventWaitHandle _sftpVersionConfirmed = new AutoResetEvent(false);
 
+        private IDictionary<string, string> _supportedExtensions;
+
         /// <summary>
         /// Gets remote working directory.
         /// </summary>
@@ -217,6 +219,7 @@ namespace Renci.SshNet.Sftp
                     if (versionResponse != null)
                     {
                         this.ProtocolVersion = versionResponse.Version;
+                        this._supportedExtensions = versionResponse.Extentions;
 
                         this._sftpVersionConfirmed.Set();
                     }
@@ -862,7 +865,7 @@ namespace Renci.SshNet.Sftp
         }
 
         #endregion
-        
+
         #region SFTP Extended API functions
 
         /// <summary>
@@ -892,6 +895,9 @@ namespace Renci.SshNet.Sftp
                         }
                     });
 
+                if (!this._supportedExtensions.ContainsKey(request.Name))
+                    throw new NotSupportedException(string.Format(CultureInfo.CurrentCulture, "Extension method {0} currently not supported by the server.", request.Name));
+
                 this.SendRequest(request);
 
                 this.WaitHandle(wait, this._operationTimeout);
@@ -934,6 +940,57 @@ namespace Renci.SshNet.Sftp
 
                     });
 
+                if (!this._supportedExtensions.ContainsKey(request.Name))
+                    throw new NotSupportedException(string.Format(CultureInfo.CurrentCulture, "Extension method {0} currently not supported by the server.", request.Name));
+
+                this.SendRequest(request);
+
+                this.WaitHandle(wait, this._operationTimeout);
+            }
+
+            return information;
+        }
+
+        /// <summary>
+        /// Performs fstatvfs@openssh.com extended request.
+        /// </summary>
+        /// <param name="handle">The file handle.</param>
+        /// <param name="nullOnError">if set to <c>true</c> [null on error].</param>
+        /// <returns></returns>
+        /// <exception cref="System.NotSupportedException"></exception>
+        internal SftpFileSytemInformation RequestFStatVfs(byte[] handle, bool nullOnError = false)
+        {
+            if (this.ProtocolVersion < 3)
+            {
+                throw new NotSupportedException(string.Format(CultureInfo.CurrentCulture, "SSH_FXP_EXTENDED operation is not supported in {0} version that server operates in.", this.ProtocolVersion));
+            }
+
+            SftpFileSytemInformation information = null;
+            using (var wait = new AutoResetEvent(false))
+            {
+                var request = new FStatVfsRequest(this.ProtocolVersion, this.NextRequestId, handle,
+                    (response) =>
+                    {
+                        information = response.GetReply<StatVfsReplyInfo>().Information;
+
+                        wait.Set();
+                    },
+                    (response) =>
+                    {
+                        if (nullOnError)
+                        {
+                            wait.Set();
+                        }
+                        else
+                        {
+                            ThrowSftpException(response);
+                        }
+
+                    });
+
+                if (!this._supportedExtensions.ContainsKey(request.Name))
+                    throw new NotSupportedException(string.Format(CultureInfo.CurrentCulture, "Extension method {0} currently not supported by the server.", request.Name));
+
                 this.SendRequest(request);
 
                 this.WaitHandle(wait, this._operationTimeout);
@@ -942,6 +999,42 @@ namespace Renci.SshNet.Sftp
             return information;
         }
 
+        /// <summary>
+        /// Performs hardlink@openssh.com extended request.
+        /// </summary>
+        /// <param name="oldPath">The old path.</param>
+        /// <param name="newPath">The new path.</param>
+        internal void HardLink(string oldPath, string newPath)
+        {
+            if (this.ProtocolVersion < 3)
+            {
+                throw new NotSupportedException(string.Format(CultureInfo.CurrentCulture, "SSH_FXP_EXTENDED operation is not supported in {0} version that server operates in.", this.ProtocolVersion));
+            }
+
+            using (var wait = new AutoResetEvent(false))
+            {
+                var request = new HardLinkRequest(this.ProtocolVersion, this.NextRequestId, oldPath, newPath,
+                    (response) =>
+                    {
+                        if (response.StatusCode == StatusCodes.Ok)
+                        {
+                            wait.Set();
+                        }
+                        else
+                        {
+                            ThrowSftpException(response);
+                        }
+                    });
+
+                if (!this._supportedExtensions.ContainsKey(request.Name))
+                    throw new NotSupportedException(string.Format(CultureInfo.CurrentCulture, "Extension method {0} currently not supported by the server.", request.Name));
+
+                this.SendRequest(request);
+
+                this.WaitHandle(wait, this._operationTimeout);
+            }
+        }
+
         #endregion
 
         private void ThrowSftpException(SftpStatusResponse response)