diff --git a/src/Renci.SshNet.NET35/Renci.SshNet.NET35.csproj b/src/Renci.SshNet.NET35/Renci.SshNet.NET35.csproj
index a6878d187..64ee419f3 100644
--- a/src/Renci.SshNet.NET35/Renci.SshNet.NET35.csproj
+++ b/src/Renci.SshNet.NET35/Renci.SshNet.NET35.csproj
@@ -18,7 +18,7 @@
     full
     false
     bin\Debug\
-    TRACE;DEBUG;FEATURE_REGEX_COMPILE;FEATURE_BINARY_SERIALIZATION;FEATURE_RNG_CREATE;FEATURE_SOCKET_SYNC;FEATURE_SOCKET_EAP;FEATURE_SOCKET_APM;FEATURE_SOCKET_SETSOCKETOPTION;FEATURE_SOCKET_POLL;FEATURE_STREAM_APM;FEATURE_DNS_SYNC;FEATURE_THREAD_THREADPOOL;FEATURE_THREAD_SLEEP;FEATURE_HASH_MD5;FEATURE_HASH_SHA1_CREATE;FEATURE_HASH_SHA256_CREATE;FEATURE_HASH_SHA384_CREATE;FEATURE_HASH_SHA512_CREATE;FEATURE_HASH_RIPEMD160_CREATE;FEATURE_HMAC_MD5;FEATURE_HMAC_SHA1;FEATURE_HMAC_SHA256;FEATURE_HMAC_SHA384;FEATURE_HMAC_SHA512;FEATURE_HMAC_RIPEMD160;FEATURE_MEMORYSTREAM_GETBUFFER;FEATURE_DIAGNOSTICS_TRACESOURCE;FEATURE_ENCODING_ASCII
+    TRACE;DEBUG;FEATURE_REGEX_COMPILE;FEATURE_BINARY_SERIALIZATION;FEATURE_RNG_CREATE;FEATURE_SOCKET_SYNC;FEATURE_SOCKET_EAP;FEATURE_SOCKET_APM;FEATURE_SOCKET_SETSOCKETOPTION;FEATURE_SOCKET_POLL;FEATURE_STREAM_APM;FEATURE_DNS_SYNC;FEATURE_THREAD_THREADPOOL;FEATURE_THREAD_SLEEP;FEATURE_HASH_MD5;FEATURE_HASH_SHA1_CREATE;FEATURE_HASH_SHA256_CREATE;FEATURE_HASH_SHA384_CREATE;FEATURE_HASH_SHA512_CREATE;FEATURE_HASH_RIPEMD160_CREATE;FEATURE_HMAC_MD5;FEATURE_HMAC_SHA1;FEATURE_HMAC_SHA256;FEATURE_HMAC_SHA384;FEATURE_HMAC_SHA512;FEATURE_HMAC_RIPEMD160;FEATURE_MEMORYSTREAM_GETBUFFER;FEATURE_DIAGNOSTICS_TRACESOURCE;FEATURE_ENCODING_ASCII;FEATURE_ECDSA
     prompt
     4
     true
@@ -29,7 +29,7 @@
     none
     true
     bin\Release\
-    TRACE;FEATURE_REGEX_COMPILE;FEATURE_BINARY_SERIALIZATION;FEATURE_RNG_CREATE;FEATURE_SOCKET_SYNC;FEATURE_SOCKET_EAP;FEATURE_SOCKET_APM;FEATURE_SOCKET_SETSOCKETOPTION;FEATURE_SOCKET_POLL;FEATURE_STREAM_APM;FEATURE_DNS_SYNC;FEATURE_THREAD_THREADPOOL;FEATURE_THREAD_SLEEP;FEATURE_HASH_MD5;FEATURE_HASH_SHA1_CREATE;FEATURE_HASH_SHA256_CREATE;FEATURE_HASH_SHA384_CREATE;FEATURE_HASH_SHA512_CREATE;FEATURE_HASH_RIPEMD160_CREATE;FEATURE_HMAC_MD5;FEATURE_HMAC_SHA1;FEATURE_HMAC_SHA256;FEATURE_HMAC_SHA384;FEATURE_HMAC_SHA512;FEATURE_HMAC_RIPEMD160;FEATURE_MEMORYSTREAM_GETBUFFER;FEATURE_DIAGNOSTICS_TRACESOURCE;FEATURE_ENCODING_ASCII
+    TRACE;FEATURE_REGEX_COMPILE;FEATURE_BINARY_SERIALIZATION;FEATURE_RNG_CREATE;FEATURE_SOCKET_SYNC;FEATURE_SOCKET_EAP;FEATURE_SOCKET_APM;FEATURE_SOCKET_SETSOCKETOPTION;FEATURE_SOCKET_POLL;FEATURE_STREAM_APM;FEATURE_DNS_SYNC;FEATURE_THREAD_THREADPOOL;FEATURE_THREAD_SLEEP;FEATURE_HASH_MD5;FEATURE_HASH_SHA1_CREATE;FEATURE_HASH_SHA256_CREATE;FEATURE_HASH_SHA384_CREATE;FEATURE_HASH_SHA512_CREATE;FEATURE_HASH_RIPEMD160_CREATE;FEATURE_HMAC_MD5;FEATURE_HMAC_SHA1;FEATURE_HMAC_SHA256;FEATURE_HMAC_SHA384;FEATURE_HMAC_SHA512;FEATURE_HMAC_RIPEMD160;FEATURE_MEMORYSTREAM_GETBUFFER;FEATURE_DIAGNOSTICS_TRACESOURCE;FEATURE_ENCODING_ASCII;FEATURE_ECDSA
     prompt
     4
     bin\Release\Renci.SshNet.xml
@@ -695,6 +695,12 @@
     
       Security\Cryptography\Key.cs
     
+    
+      Security\Cryptography\EcdsaDigitalSignature.cs
+    
+    
+      Security\Cryptography\EcdsaKey.cs
+    
     
       Security\Cryptography\RsaDigitalSignature.cs
     
diff --git a/src/Renci.SshNet.Tests.NET35/Renci.SshNet.Tests.NET35.csproj b/src/Renci.SshNet.Tests.NET35/Renci.SshNet.Tests.NET35.csproj
index a42cf8ec1..893a6fe0c 100644
--- a/src/Renci.SshNet.Tests.NET35/Renci.SshNet.Tests.NET35.csproj
+++ b/src/Renci.SshNet.Tests.NET35/Renci.SshNet.Tests.NET35.csproj
@@ -1737,6 +1737,26 @@
       Data\Key.SSH2.RSA.txt
     
   
+  
+    
+      Data\Key.ECDSA.txt
+    
+    
+      Data\Key.ECDSA384.txt
+    
+    
+      Data\Key.ECDSA521.txt
+    
+    
+      Data\Key.ECDSA.Encrypted.txt
+    
+    
+      Data\Key.ECDSA384.Encrypted.txt
+    
+    
+      Data\Key.ECDSA521.Encrypted.txt
+    
+  
   
   
     
diff --git a/src/Renci.SshNet.Tests/Classes/PrivateKeyFileTest.cs b/src/Renci.SshNet.Tests/Classes/PrivateKeyFileTest.cs
index 21bd97853..3c944c8d4 100644
--- a/src/Renci.SshNet.Tests/Classes/PrivateKeyFileTest.cs
+++ b/src/Renci.SshNet.Tests/Classes/PrivateKeyFileTest.cs
@@ -319,6 +319,72 @@ public void Test_PrivateKey_RSA_DES_EDE3_CFB()
             }
         }
 
+        [TestMethod]
+        [Owner("darinkes")]
+        [TestCategory("PrivateKey")]
+        public void Test_PrivateKey_ECDSA()
+        {
+            using (var stream = GetData("Key.ECDSA.txt"))
+            {
+                new PrivateKeyFile(stream);
+            }
+        }
+
+        [TestMethod]
+        [Owner("darinkes")]
+        [TestCategory("PrivateKey")]
+        public void Test_PrivateKey_ECDSA384()
+        {
+            using (var stream = GetData("Key.ECDSA384.txt"))
+            {
+                new PrivateKeyFile(stream);
+            }
+        }
+
+        [TestMethod]
+        [Owner("darinkes")]
+        [TestCategory("PrivateKey")]
+        public void Test_PrivateKey_ECDSA521()
+        {
+            using (var stream = GetData("Key.ECDSA521.txt"))
+            {
+                new PrivateKeyFile(stream);
+            }
+        }
+
+        [TestMethod]
+        [Owner("darinkes")]
+        [TestCategory("PrivateKey")]
+        public void Test_PrivateKey_ECDSA_Encrypted()
+        {
+            using (var stream = GetData("Key.ECDSA.Encrypted.txt"))
+            {
+                new PrivateKeyFile(stream, "12345");
+            }
+        }
+
+        [TestMethod]
+        [Owner("darinkes")]
+        [TestCategory("PrivateKey")]
+        public void Test_PrivateKey_ECDSA384_Encrypted()
+        {
+            using (var stream = GetData("Key.ECDSA384.Encrypted.txt"))
+            {
+                new PrivateKeyFile(stream, "12345");
+            }
+        }
+
+        [TestMethod]
+        [Owner("darinkes")]
+        [TestCategory("PrivateKey")]
+        public void Test_PrivateKey_ECDSA521_Encrypted()
+        {
+            using (var stream = GetData("Key.ECDSA521.Encrypted.txt"))
+            {
+                new PrivateKeyFile(stream, "12345");
+            }
+        }
+
         /// 
         ///A test for Dispose
         ///
diff --git a/src/Renci.SshNet.Tests/Data/Key.ECDSA.Encrypted.txt b/src/Renci.SshNet.Tests/Data/Key.ECDSA.Encrypted.txt
new file mode 100644
index 000000000..f0af5ba7d
--- /dev/null
+++ b/src/Renci.SshNet.Tests/Data/Key.ECDSA.Encrypted.txt
@@ -0,0 +1,8 @@
+-----BEGIN EC PRIVATE KEY-----
+Proc-Type: 4,ENCRYPTED
+DEK-Info: AES-128-CBC,54D46F498C989115AAE14FEA21E3AF11
+
+IQdFnndcbzz10d7YQIgEE1TzuzJrm7uYJr4Hvdfz/FshVxMRqxqaqtEgo2vAHHik
+BOcPkm+84ERlTNPslcJqLSkKzCdxb7Rz5hfwHuN3Y6Lf01qGakDlzAUEjEyDor+4
+zQtAne+f+gRUJnBvLLoVhH4xdeQFC55GECNUFQpEmos=
+-----END EC PRIVATE KEY-----
\ No newline at end of file
diff --git a/src/Renci.SshNet.Tests/Data/Key.ECDSA.txt b/src/Renci.SshNet.Tests/Data/Key.ECDSA.txt
new file mode 100644
index 000000000..13ac9fb49
--- /dev/null
+++ b/src/Renci.SshNet.Tests/Data/Key.ECDSA.txt
@@ -0,0 +1,5 @@
+-----BEGIN EC PRIVATE KEY-----
+MHcCAQEEIEdqaFKgJBIibVjyUh1v7Y35LwIQJrocdTaYFLwl7iB0oAoGCCqGSM49
+AwEHoUQDQgAEQD5MO/n9yqSDTszwzVpApLx5SQFecE5ZfDkgxqVdHQecm1BAPozZ
+4eKGNhKn72hT79mLlp9HXX+oNEcuVT83Hw==
+-----END EC PRIVATE KEY-----
\ No newline at end of file
diff --git a/src/Renci.SshNet.Tests/Data/Key.ECDSA384.Encrypted.txt b/src/Renci.SshNet.Tests/Data/Key.ECDSA384.Encrypted.txt
new file mode 100644
index 000000000..00072ce24
--- /dev/null
+++ b/src/Renci.SshNet.Tests/Data/Key.ECDSA384.Encrypted.txt
@@ -0,0 +1,9 @@
+-----BEGIN EC PRIVATE KEY-----
+Proc-Type: 4,ENCRYPTED
+DEK-Info: AES-128-CBC,1D64653C5E18C2AACB0B17E3FE43C219
+
+lCtRmcvKSeIACwqTtsf/ei1brtCZ386rsk/j7bSXdkZBpvzcmzbeo6w6CYm206Km
+hV9TMl2dIO/I1/ov5/2VIR3ZkaElyDOJD/+Be0e3aus4EZj1H1YM/Dv+4QJId+is
+Cw4ycWjfudYPPejGdiyjzt5qjaIJwrrEvGtMg7sWVAqDpjcAjS9KuaCu5nOgdItL
+s7oHuz+DTGdJQNfUHAlUnz1JaMRWzpP0MwtxdcaRY+w=
+-----END EC PRIVATE KEY-----
\ No newline at end of file
diff --git a/src/Renci.SshNet.Tests/Data/Key.ECDSA384.txt b/src/Renci.SshNet.Tests/Data/Key.ECDSA384.txt
new file mode 100644
index 000000000..f2d658ea4
--- /dev/null
+++ b/src/Renci.SshNet.Tests/Data/Key.ECDSA384.txt
@@ -0,0 +1,6 @@
+-----BEGIN EC PRIVATE KEY-----
+MIGkAgEBBDCQawHdHLR7NvKa2vPV0sVkbzOE8c0enp95iEysGcGV66RXE1EH//nh
+gu5UzeTR4KigBwYFK4EEACKhZANiAAQUk4rVvoOPI1hQzWpNx09Uo6qG+srGcbvB
+q15eFK0GnK/T0UBKxdbZ2+//KAYI6SeDHM9t3ORF1aX5EpjTEBI4d7ZY/lV9jX6M
+nJ4XuGteJselM2iMmy+p9ZYw83BYB1Y=
+-----END EC PRIVATE KEY-----
\ No newline at end of file
diff --git a/src/Renci.SshNet.Tests/Data/Key.ECDSA521.Encrypted.txt b/src/Renci.SshNet.Tests/Data/Key.ECDSA521.Encrypted.txt
new file mode 100644
index 000000000..381b30be8
--- /dev/null
+++ b/src/Renci.SshNet.Tests/Data/Key.ECDSA521.Encrypted.txt
@@ -0,0 +1,10 @@
+-----BEGIN EC PRIVATE KEY-----
+Proc-Type: 4,ENCRYPTED
+DEK-Info: AES-128-CBC,F995028237EBD79C928530CC6C3E957F
+
+wT+iajbte4MnpCipVy/7W9t2I8OgwbMjNBw9PB5xmXR1NQX+yWa81DXMTgjHi8++
+6tp+Vlftkr7mY1yvZCVo1Sy4VgcvZeMhtpVKtvYdMCmHJC6gaDOTYX3yee8DJ4FL
+fG+IQz0wFyZZ26NFrHiwbufW9z6pXhGNCQZK0KLbFxI9iKwVA0llc7uzTEcmBBpn
+0/Snp0CVvX+i6AP9Xj0bBdrFCsvcoT+ZHzS8YWJUfu3m6cpAJksCAy0PXR3ifvus
+edTfDpkMxd4/b+DtPB6SMekIAjnQyzbyaTwJCujm8iU=
+-----END EC PRIVATE KEY-----
\ No newline at end of file
diff --git a/src/Renci.SshNet.Tests/Data/Key.ECDSA521.txt b/src/Renci.SshNet.Tests/Data/Key.ECDSA521.txt
new file mode 100644
index 000000000..31abe917a
--- /dev/null
+++ b/src/Renci.SshNet.Tests/Data/Key.ECDSA521.txt
@@ -0,0 +1,7 @@
+-----BEGIN EC PRIVATE KEY-----
+MIHcAgEBBEIBn2DAme7AU8sCA+/sd6s3c2FNW26IiPvulGd3FC8k5q+fjBZ5LUWR
+iJMGrsf2rJLO8hXMGJYoF9tjZEGaabQ8KVagBwYFK4EEACOhgYkDgYYABABrpVjs
+ANqcvqMUo1wo0I1uVCXQ6xrauy4iU86FiOwFmkYRrle4w3oYdRJwniC3TwGMuBuM
+PMIoCTXr0UtUzn1vkQESNR/J/jAxVseLlVe+KDfZHKvsvk2+O4XaSa1qMfLwN3sp
+wlj08+ylKjlO6V3g0hbz4ZaSVwuiRS7Xsv8W2MV6rg==
+-----END EC PRIVATE KEY-----
\ No newline at end of file
diff --git a/src/Renci.SshNet.Tests/Renci.SshNet.Tests.csproj b/src/Renci.SshNet.Tests/Renci.SshNet.Tests.csproj
index d968dd27b..6f64c0048 100644
--- a/src/Renci.SshNet.Tests/Renci.SshNet.Tests.csproj
+++ b/src/Renci.SshNet.Tests/Renci.SshNet.Tests.csproj
@@ -709,6 +709,14 @@
       Renci.SshNet
     
   
+  
+    
+    
+    
+    
+    
+    
+  
   
   
-
\ No newline at end of file
+
diff --git a/src/Renci.SshNet/Security/Cryptography/EcdsaDigitalSignature.cs b/src/Renci.SshNet/Security/Cryptography/EcdsaDigitalSignature.cs
new file mode 100644
index 000000000..c6386b180
--- /dev/null
+++ b/src/Renci.SshNet/Security/Cryptography/EcdsaDigitalSignature.cs
@@ -0,0 +1,197 @@
+#if FEATURE_ECDSA
+using System;
+using Renci.SshNet.Common;
+using System.Globalization;
+
+namespace Renci.SshNet.Security.Cryptography
+{
+    /// 
+    /// Implements ECDSA digital signature algorithm.
+    /// 
+    public class EcdsaDigitalSignature : DigitalSignature, IDisposable
+    {
+        private readonly EcdsaKey _key;
+
+        /// 
+        /// Initializes a new instance of the  class.
+        /// 
+        /// The ECDSA key.
+        ///  is null.
+        public EcdsaDigitalSignature(EcdsaKey key)
+        {
+            if (key == null)
+                throw new ArgumentNullException("key");
+
+            _key = key;
+        }
+
+        /// 
+        /// Verifies the signature.
+        /// 
+        /// The input.
+        /// The signature.
+        /// 
+        /// true if signature was successfully verified; otherwise false.
+        /// 
+        public override bool Verify(byte[] input, byte[] signature)
+        {
+            // for 521 sig_size is 132
+            var sig_size = _key.dsa.KeySize == 521 ? 132 : _key.dsa.KeySize / 4;
+            var ssh_data = new SshDataSignature(signature, sig_size);
+            return _key.dsa.VerifyData(input, ssh_data.Signature);
+        }
+
+        /// 
+        /// Creates the signature.
+        /// 
+        /// The input.
+        /// 
+        /// Signed input data.
+        /// 
+        public override byte[] Sign(byte[] input)
+        {
+            var signed = _key.dsa.SignData(input);
+            var ssh_data = new SshDataSignature(signed.Length);
+            ssh_data.Signature = signed;
+            return ssh_data.GetBytes();
+        }
+
+        #region IDisposable Members
+
+        private bool _isDisposed;
+
+        /// 
+        /// Performs application-defined tasks associated with freeing, releasing, or resetting unmanaged resources.
+        /// 
+        public void Dispose()
+        {
+            Dispose(true);
+            GC.SuppressFinalize(this);
+        }
+
+        /// 
+        /// Releases unmanaged and - optionally - managed resources
+        /// 
+        /// true to release both managed and unmanaged resources; false to release only unmanaged resources.
+        protected virtual void Dispose(bool disposing)
+        {
+            if (_isDisposed)
+                return;
+
+            if (disposing)
+            {
+                _isDisposed = true;
+            }
+        }
+
+        /// 
+        /// Releases unmanaged resources and performs other cleanup operations before the
+        ///  is reclaimed by garbage collection.
+        /// 
+        ~EcdsaDigitalSignature()
+        {
+            Dispose(false);
+        }
+
+        #endregion
+    }
+
+    class SshDataSignature : SshData
+    {
+        private int _signature_size;
+
+        private byte[] _signature_r;
+        private byte[] _signature_s;
+
+        public byte[] Signature
+        {
+            get
+            {
+                var signature = new byte[_signature_size];
+                Buffer.BlockCopy(_signature_r, 0, signature, 0, _signature_r.Length);
+                Buffer.BlockCopy(_signature_s, 0, signature, _signature_r.Length, _signature_s.Length);
+                return signature;
+            }
+            set
+            {
+                var signed_r = new byte[_signature_size / 2];
+                Buffer.BlockCopy(value, 0, signed_r, 0, signed_r.Length);
+                _signature_r = BytesToSsh(signed_r);
+
+                var signed_s = new byte[_signature_size / 2];
+                Buffer.BlockCopy(value, signed_r.Length, signed_s, 0, signed_s.Length);
+                _signature_s = BytesToSsh(signed_s);
+            }
+        }
+
+        public SshDataSignature(int sig_size)
+        {
+            _signature_size = sig_size;
+        }
+
+        public SshDataSignature(byte[] data, int sig_size)
+        {
+            _signature_size = sig_size;
+            Load(data);
+        }
+
+        protected override void LoadData()
+        {
+            _signature_r = Padded(ReadBinary().TrimLeadingZeros(), _signature_size / 2);
+            _signature_s = Padded(ReadBinary().TrimLeadingZeros(), _signature_size / 2);
+        }
+
+        protected override void SaveData()
+        {
+            WriteBinaryString(BytesToSsh(_signature_r));
+            WriteBinaryString(BytesToSsh(_signature_s));
+        }
+
+        public new byte[] ReadBinary()
+        {
+            var length = ReadUInt32();
+
+            if (length > int.MaxValue)
+            {
+                throw new NotSupportedException(string.Format(CultureInfo.CurrentCulture, "Strings longer than {0} is not supported.", int.MaxValue));
+            }
+
+            return ReadBytes((int)length);
+        }
+
+        protected override int BufferCapacity
+        {
+            get
+            {
+                var capacity = base.BufferCapacity;
+                capacity += 4; // r length
+                capacity += _signature_r.Length; // signature r
+                capacity += 4; // s length
+                capacity += _signature_s.Length; // signature s
+                return capacity;
+            }
+        }
+
+        // Fill Data with Leading-Zeros if neccesary
+        private byte[] Padded(byte[] data, int length)
+        {
+            if (length <= data.Length)
+                return data;
+            var new_data = new byte[length];
+            Buffer.BlockCopy(data, 0, new_data, new_data.Length - data.Length, data.Length);
+            return new_data;
+        }
+
+        // Prepend a 0-Byte if neccesary
+        private byte[] BytesToSsh(byte[] data)
+        {
+            if ((data[0] & (1 << 7)) != 0) {
+                var buf = new byte[data.Length + 1];
+                Buffer.BlockCopy(data, 0, buf, 1, data.Length);
+                return buf;
+            }
+            return data;
+        }
+    }
+}
+#endif
\ No newline at end of file
diff --git a/src/Renci.SshNet/Security/Cryptography/EcdsaKey.cs b/src/Renci.SshNet/Security/Cryptography/EcdsaKey.cs
new file mode 100644
index 000000000..4c1f52dda
--- /dev/null
+++ b/src/Renci.SshNet/Security/Cryptography/EcdsaKey.cs
@@ -0,0 +1,360 @@
+#if FEATURE_ECDSA
+using System;
+using System.IO;
+using System.Text;
+using System.Runtime.InteropServices;
+using System.Security.Cryptography;
+using Renci.SshNet.Common;
+using Renci.SshNet.Security.Cryptography;
+
+namespace Renci.SshNet.Security
+{
+    /// 
+    /// Contains ECDSA (ecdsa-sha2-nistp{256,384,521}) private and public key
+    /// 
+    public class EcdsaKey : Key, IDisposable
+    {
+        internal enum KeyBlobMagicNumber : int
+        {
+            BCRYPT_ECDSA_PUBLIC_P256_MAGIC = 0x31534345,
+            BCRYPT_ECDSA_PRIVATE_P256_MAGIC = 0x32534345,
+            BCRYPT_ECDSA_PUBLIC_P384_MAGIC = 0x33534345,
+            BCRYPT_ECDSA_PRIVATE_P384_MAGIC = 0x34534345,
+            BCRYPT_ECDSA_PUBLIC_P521_MAGIC = 0x35534345,
+            BCRYPT_ECDSA_PRIVATE_P521_MAGIC = 0x36534345,
+
+            BCRYPT_ECDH_PUBLIC_P256_MAGIC = 0x314B4345,
+            BCRYPT_ECDH_PRIVATE_P256_MAGIC = 0x324B4345,
+            BCRYPT_ECDH_PUBLIC_P384_MAGIC = 0x334B4345,
+            BCRYPT_ECDH_PRIVATE_P384_MAGIC = 0x344B4345,
+            BCRYPT_ECDH_PUBLIC_P521_MAGIC = 0x354B4345,
+            BCRYPT_ECDH_PRIVATE_P521_MAGIC = 0x364B4345,
+
+            BCRYPT_ECDH_PUBLIC_GENERIC_MAGIC = 0x504B4345,
+            BCRYPT_ECDH_PRIVATE_GENERIC_MAGIC = 0x564B4345,
+        }
+
+        [StructLayout(LayoutKind.Sequential)]
+        internal struct BCRYPT_ECCKEY_BLOB
+        {
+            internal KeyBlobMagicNumber Magic;
+            internal int cbKey;
+        }
+
+        /// 
+        /// Gets dsa
+        /// 
+        public ECDsaCng dsa;
+
+        private CngKey key;
+
+        /// 
+        /// Gets the SSH name of the ECDSA Key
+        /// 
+        public override string ToString()
+        {
+            return string.Format("ecdsa-sha2-nistp{0}", KeyLength);
+        }
+
+        /// 
+        /// Gets the length of the key.
+        /// 
+        /// 
+        /// The length of the key.
+        /// 
+        public override int KeyLength
+        {
+            get
+            {
+                return key.KeySize;
+            }
+        }
+
+        /// 
+        /// Gets the digital signature.
+        /// 
+        protected override DigitalSignature DigitalSignature
+        {
+            get
+            {
+                if (_digitalSignature == null)
+                {
+                    _digitalSignature = new EcdsaDigitalSignature(this);
+                }
+                return _digitalSignature;
+            }
+        }
+
+        /// 
+        /// Gets or sets the public.
+        /// 
+        /// 
+        /// The public.
+        /// 
+        public override BigInteger[] Public
+        {
+            get
+            {
+                var blob = key.Export(CngKeyBlobFormat.EccPublicBlob);
+
+                byte[] qx;
+                byte[] qy;
+                KeyBlobMagicNumber magic;
+                using (var br = new BinaryReader(new MemoryStream(blob)))
+                {
+                    magic = (KeyBlobMagicNumber)br.ReadInt32();
+                    int cbKey = br.ReadInt32();
+                    qx = br.ReadBytes(cbKey);
+                    qy = br.ReadBytes(cbKey);
+                }
+
+                string curve = "";
+                switch (magic)
+                {
+                    case KeyBlobMagicNumber.BCRYPT_ECDSA_PUBLIC_P256_MAGIC:
+                        curve = "nistp256";
+                        break;
+                    case KeyBlobMagicNumber.BCRYPT_ECDSA_PUBLIC_P384_MAGIC:
+                        curve = "nistp384";
+                        break;
+                    case KeyBlobMagicNumber.BCRYPT_ECDSA_PUBLIC_P521_MAGIC:
+                        curve = "nistp521";
+                        break;
+                    default:
+                        throw new SshException("Unexpected Curve Magic: " + magic);
+                }
+                var curve_bn = new BigInteger(Encoding.ASCII.GetBytes(curve).Reverse());
+
+                // Make ECPoint from x and y
+                // Prepend 04 (uncompressed format) + qx-bytes + qy-bytes
+                var point_bn_bytes = new byte[1 + qx.Length + qy.Length];
+                Buffer.SetByte(point_bn_bytes, 0, 4);
+                Buffer.BlockCopy(qx, 0, point_bn_bytes, 1, qx.Length);
+                Buffer.BlockCopy(qy, 0, point_bn_bytes, qx.Length + 1, qy.Length);
+
+                // returns Curve-Name and x/y as ECPoint
+                return new[] { curve_bn, new BigInteger(point_bn_bytes.Reverse()) };
+            }
+            set
+            {
+                // value[0]:
+                // Curve Name as String
+                // nistp{256,384,521}
+                var value_0 = Encoding.ASCII.GetString(value[0].ToByteArray().Reverse()); // Curve Name as String
+
+                var curve_magic = KeyBlobMagicNumber.BCRYPT_ECDH_PRIVATE_GENERIC_MAGIC;
+                var hash_algo = CngAlgorithm.Sha256;
+                switch (value_0)
+                {
+                    case "nistp256":
+                        curve_magic = KeyBlobMagicNumber.BCRYPT_ECDSA_PUBLIC_P256_MAGIC;
+                        hash_algo = CngAlgorithm.Sha256;
+                        break;
+                    case "nistp384":
+                        curve_magic = KeyBlobMagicNumber.BCRYPT_ECDSA_PUBLIC_P384_MAGIC;
+                        hash_algo = CngAlgorithm.Sha384;
+                        break;
+                    case "nistp521":
+                        curve_magic = KeyBlobMagicNumber.BCRYPT_ECDSA_PUBLIC_P521_MAGIC;
+                        hash_algo = CngAlgorithm.Sha512;
+                        break;
+                    default:
+                        throw new SshException("Unexpected Curve Name: " + value_0);
+                }
+
+                // ECPoint as BigInteger(2)
+                var value_1 = value[1].ToByteArray().Reverse();
+
+                var cord_size = (value_1.Length - 1) / 2;
+                var value_1_x = new byte[cord_size];
+                Buffer.BlockCopy(value_1, 1, value_1_x, 0, value_1_x.Length); // first byte is format. should be checked?
+
+                var value_1_y = new byte[cord_size];
+                Buffer.BlockCopy(value_1, cord_size + 1, value_1_y, 0, value_1_y.Length);
+
+                int headerSize = Marshal.SizeOf(typeof(BCRYPT_ECCKEY_BLOB));
+                int blobSize = headerSize + (2 * cord_size);
+                byte[] blob = new byte[blobSize];
+
+                using (var bw = new BinaryWriter(new MemoryStream(blob)))
+                {
+                    bw.Write((int)curve_magic);
+                    bw.Write(cord_size);
+                    bw.Write(value_1_x); // q.x
+                    bw.Write(value_1_y); // q.y
+                }
+                key = CngKey.Import(blob, CngKeyBlobFormat.EccPublicBlob);
+                dsa = new ECDsaCng(key)
+                {
+                    HashAlgorithm = hash_algo
+                };
+            }
+        }
+
+        private EcdsaDigitalSignature _digitalSignature;
+
+        /// 
+        /// Initializes a new instance of the  class.
+        /// 
+        public EcdsaKey()
+        {
+        }
+
+        /// 
+        /// Initializes a new instance of the  class.
+        /// 
+        /// DER encoded private key data.
+        public EcdsaKey(byte[] data)
+        {
+            var der = new DerData(data);
+            var version = der.ReadBigInteger(); // skip version
+
+            // PrivateKey
+            var privatekey = der.ReadOctetString();
+
+            // Construct
+            var s0 = der.ReadByte();
+            if ((s0 & 0xe0) != 0xa0)
+                throw new SshException(string.Format("UnexpectedDER: wanted constructed tag (0xa0-0xbf), got: {0:X}", s0));
+            var tag = s0 & 0x1f;
+            if (tag != 0)
+                throw new SshException(string.Format("expected tag 0 in DER privkey, got: {0}", tag));
+            der.ReadByte(); // object length
+
+            // curve OID
+            var curve = der.ReadObject();
+
+            var pkcs8_data = PemToPkcs8(privatekey, curve, true);
+            key = ImportPkcs8(pkcs8_data, privatekey);
+            dsa = new ECDsaCng(key);
+
+            switch (dsa.KeySize)
+            {
+                case 256:
+                    dsa.HashAlgorithm = CngAlgorithm.Sha256;
+                    break;
+                case 384:
+                    dsa.HashAlgorithm = CngAlgorithm.Sha384;
+                    break;
+                case 521:
+                    dsa.HashAlgorithm = CngAlgorithm.Sha512;
+                    break;
+                default:
+                    throw new SshException("Unknown KeySize: " + dsa.KeySize);
+            }
+        }
+
+        private CngKey ImportPkcs8(byte[] pkcs8_data, byte[] privatekey)
+        {
+            // There was an issue in older .NET Versions which prevents
+            // the usage our keys. Was fixed with .NET 4.6.1. Workaround:
+            // Change KeyBlobMagicNumber from Key-exchange (ECDH) to Signing (ECDSA)
+            // See: https://stackoverflow.com/a/43982666
+            var key =CngKey.Import(pkcs8_data, CngKeyBlobFormat.Pkcs8PrivateBlob);
+
+            var blob = key.Export(CngKeyBlobFormat.EccPublicBlob);
+            key.Dispose();
+            byte[] qx;
+            byte[] qy;
+            KeyBlobMagicNumber magic;
+            int cbkey;
+            using (var br = new BinaryReader(new MemoryStream(blob)))
+            {
+                magic = (KeyBlobMagicNumber)br.ReadInt32();
+                cbkey = br.ReadInt32();
+                qx = br.ReadBytes(cbkey);
+                qy = br.ReadBytes(cbkey);
+            }
+
+            switch (magic)
+            {
+                case KeyBlobMagicNumber.BCRYPT_ECDH_PUBLIC_P256_MAGIC:
+                    magic = KeyBlobMagicNumber.BCRYPT_ECDSA_PRIVATE_P256_MAGIC;
+                    break;
+                case KeyBlobMagicNumber.BCRYPT_ECDH_PUBLIC_P384_MAGIC:
+                    magic = KeyBlobMagicNumber.BCRYPT_ECDSA_PRIVATE_P384_MAGIC;
+                    break;
+                case KeyBlobMagicNumber.BCRYPT_ECDH_PUBLIC_P521_MAGIC:
+                    magic = KeyBlobMagicNumber.BCRYPT_ECDSA_PRIVATE_P521_MAGIC;
+                    break;
+            }
+
+            int headerSize = Marshal.SizeOf(typeof(BCRYPT_ECCKEY_BLOB));
+            int blobSize = headerSize + qx.Length + qy.Length + privatekey.Length;
+            byte[] new_blob = new byte[blobSize];
+
+            using (var bw = new BinaryWriter(new MemoryStream(new_blob)))
+            {
+                bw.Write((int)magic);
+                bw.Write(cbkey);
+                bw.Write(qx); // q.x
+                bw.Write(qy); // q.y
+                bw.Write(privatekey); // d
+            }
+            return CngKey.Import(new_blob, CngKeyBlobFormat.EccPrivateBlob);
+        }
+
+        // Since Windows Crypto API is unable to parse/read our PEM format directly
+        // we have to convert it to PKCS#8 Format first
+        private byte[] PemToPkcs8(byte[] key, byte[] curve, bool isprivate)
+        {
+            var newdata = new DerData();
+            newdata.Write(new BigInteger(0));
+
+            // Create Infos about Content and our Curve
+            var objdata = new DerData();
+            // 1.2.840.10045.2.1 - ECDSA and ECDH Public Key.
+            var obj = new ObjectIdentifier(1, 2, 840, 10045, 2, 1);
+            objdata.Write(obj);
+            objdata.WriteObjectIdentifier(curve);
+            newdata.WriteBytes(objdata.Encode());
+
+            var keydata = new DerData();
+            keydata.Write(new BigInteger(isprivate ? 1: 0));
+            keydata.Write(key);
+
+            newdata.Write(keydata.Encode());
+
+            return newdata.Encode();
+        }
+        #region IDisposable Members
+
+        private bool _isDisposed;
+
+        /// 
+        /// Performs application-defined tasks associated with freeing, releasing, or resetting unmanaged resources.
+        /// 
+        public void Dispose()
+        {
+            Dispose(true);
+            GC.SuppressFinalize(this);
+        }
+
+        /// 
+        /// Releases unmanaged and - optionally - managed resources
+        /// 
+        /// true to release both managed and unmanaged resources; false to release only unmanaged resources.
+        protected virtual void Dispose(bool disposing)
+        {
+            if (_isDisposed)
+                return;
+
+            if (disposing)
+            {
+                _isDisposed = true;
+            }
+        }
+
+        /// 
+        /// Releases unmanaged resources and performs other cleanup operations before the
+        ///  is reclaimed by garbage collection.
+        /// 
+        ~EcdsaKey()
+        {
+            Dispose(false);
+        }
+
+        #endregion
+    }
+}
+#endif
\ No newline at end of file