From 60f3cd803eb90c80538fe4936bb3e23955786d80 Mon Sep 17 00:00:00 2001 From: Rob Hague Date: Fri, 3 Jan 2025 11:12:21 +0100 Subject: [PATCH] Drop DSA (#1558) DSA is removed at compile time from OpenSSH 9.8 and higher. That means we can no longer test it in our integration tests. It seems like a good time to remove it. From the OpenSSH release notes: DSA, as specified in the SSHv2 protocol, is inherently weak - being limited to a 160 bit private key and use of the SHA1 digest. Its estimated security level is only 80 bits symmetric equivalent. OpenSSH has disabled DSA keys by default since 2015 but has retained run-time optional support for them. DSA was the only mandatory-to- implement algorithm in the SSHv2 RFCs, mostly because alternative algorithms were encumbered by patents when the SSHv2 protocol was specified. This has not been the case for decades at this point and better algorithms are well supported by all actively-maintained SSH implementations. We do not consider the costs of maintaining DSA in OpenSSH to be justified and hope that removing it from OpenSSH can accelerate its wider deprecation in supporting cryptography libraries. --- src/Renci.SshNet/ConnectionInfo.cs | 1 - src/Renci.SshNet/PrivateKeyFile.PKCS1.cs | 2 - src/Renci.SshNet/PrivateKeyFile.PKCS8.cs | 21 -- src/Renci.SshNet/PrivateKeyFile.PuTTY.cs | 12 +- src/Renci.SshNet/PrivateKeyFile.SSHCOM.cs | 15 -- src/Renci.SshNet/PrivateKeyFile.cs | 4 - src/Renci.SshNet/Security/Certificate.cs | 3 - .../Cryptography/DsaDigitalSignature.cs | 86 ------- .../Security/Cryptography/DsaKey.cs | 220 ------------------ ....DSA.PKCS8.Encrypted.Aes.256.CBC.12345.txt | 12 - test/Data/Key.DSA.PKCS8.txt | 9 - test/Data/Key.DSA.pub | 1 - test/Data/Key.DSA.txt | 12 - ...ey.PuTTY3.DSA.Encrypted.Argon2id.12345.ppk | 22 -- test/Data/Key.PuTTY3.DSA.ppk | 17 -- .../Key.SSH2.DSA.Encrypted.Des.CBC.12345.pub | 1 - .../Key.SSH2.DSA.Encrypted.Des.CBC.12345.txt | 12 - test/Data/Key.SSH2.DSA.pub | 1 - test/Data/Key.SSH2.DSA.txt | 13 -- .../HostKeyAlgorithmTests.cs | 6 - .../PrivateKeyAuthenticationTests.cs | 6 - .../Classes/PrivateKeyFileTest.cs | 7 - .../Classes/ScpClientTest.cs | 8 +- .../Cryptography/DsaDigitalSignatureTest.cs | 59 ----- .../Security/Cryptography/DsaKeyTest.cs | 205 ---------------- 25 files changed, 6 insertions(+), 749 deletions(-) delete mode 100644 src/Renci.SshNet/Security/Cryptography/DsaDigitalSignature.cs delete mode 100644 src/Renci.SshNet/Security/Cryptography/DsaKey.cs delete mode 100644 test/Data/Key.DSA.PKCS8.Encrypted.Aes.256.CBC.12345.txt delete mode 100644 test/Data/Key.DSA.PKCS8.txt delete mode 100644 test/Data/Key.DSA.pub delete mode 100644 test/Data/Key.DSA.txt delete mode 100644 test/Data/Key.PuTTY3.DSA.Encrypted.Argon2id.12345.ppk delete mode 100644 test/Data/Key.PuTTY3.DSA.ppk delete mode 100644 test/Data/Key.SSH2.DSA.Encrypted.Des.CBC.12345.pub delete mode 100644 test/Data/Key.SSH2.DSA.Encrypted.Des.CBC.12345.txt delete mode 100644 test/Data/Key.SSH2.DSA.pub delete mode 100644 test/Data/Key.SSH2.DSA.txt delete mode 100644 test/Renci.SshNet.Tests/Classes/Security/Cryptography/DsaDigitalSignatureTest.cs delete mode 100644 test/Renci.SshNet.Tests/Classes/Security/Cryptography/DsaKeyTest.cs diff --git a/src/Renci.SshNet/ConnectionInfo.cs b/src/Renci.SshNet/ConnectionInfo.cs index bedb5d9d..b7806a90 100644 --- a/src/Renci.SshNet/ConnectionInfo.cs +++ b/src/Renci.SshNet/ConnectionInfo.cs @@ -407,7 +407,6 @@ namespace Renci.SshNet hostAlgs.Add("rsa-sha2-512", data => { var key = new RsaKey(new SshKeyData(data)); return new KeyHostAlgorithm("rsa-sha2-512", key, new RsaDigitalSignature(key, HashAlgorithmName.SHA512)); }); hostAlgs.Add("rsa-sha2-256", data => { var key = new RsaKey(new SshKeyData(data)); return new KeyHostAlgorithm("rsa-sha2-256", key, new RsaDigitalSignature(key, HashAlgorithmName.SHA256)); }); hostAlgs.Add("ssh-rsa", data => new KeyHostAlgorithm("ssh-rsa", new RsaKey(new SshKeyData(data)))); - hostAlgs.Add("ssh-dss", data => new KeyHostAlgorithm("ssh-dss", new DsaKey(new SshKeyData(data)))); #pragma warning restore SA1107 // Code should not contain multiple statements on one line HostKeyAlgorithms = hostAlgs; diff --git a/src/Renci.SshNet/PrivateKeyFile.PKCS1.cs b/src/Renci.SshNet/PrivateKeyFile.PKCS1.cs index 606bb00f..f63fe05d 100644 --- a/src/Renci.SshNet/PrivateKeyFile.PKCS1.cs +++ b/src/Renci.SshNet/PrivateKeyFile.PKCS1.cs @@ -80,8 +80,6 @@ namespace Renci.SshNet { case "RSA PRIVATE KEY": return new RsaKey(decryptedData); - case "DSA PRIVATE KEY": - return new DsaKey(decryptedData); case "EC PRIVATE KEY": return new EcdsaKey(decryptedData); default: diff --git a/src/Renci.SshNet/PrivateKeyFile.PKCS8.cs b/src/Renci.SshNet/PrivateKeyFile.PKCS8.cs index ad458615..45ba357d 100644 --- a/src/Renci.SshNet/PrivateKeyFile.PKCS8.cs +++ b/src/Renci.SshNet/PrivateKeyFile.PKCS8.cs @@ -54,27 +54,6 @@ namespace Renci.SshNet return new RsaKey(key); } - if (algorithmOid.Equals(X9ObjectIdentifiers.IdDsa)) - { - var parameters = privateKeyInfo.PrivateKeyAlgorithm.Parameters.GetDerEncoded(); - var parametersReader = new AsnReader(parameters, AsnEncodingRules.BER); - var sequenceReader = parametersReader.ReadSequence(); - parametersReader.ThrowIfNotEmpty(); - - var p = sequenceReader.ReadInteger(); - var q = sequenceReader.ReadInteger(); - var g = sequenceReader.ReadInteger(); - sequenceReader.ThrowIfNotEmpty(); - - var keyReader = new AsnReader(key, AsnEncodingRules.BER); - var x = keyReader.ReadInteger(); - keyReader.ThrowIfNotEmpty(); - - var y = BigInteger.ModPow(g, x, p); - - return new DsaKey(p, q, g, y, x); - } - if (algorithmOid.Equals(X9ObjectIdentifiers.IdECPublicKey)) { var parameters = privateKeyInfo.PrivateKeyAlgorithm.Parameters.GetDerEncoded(); diff --git a/src/Renci.SshNet/PrivateKeyFile.PuTTY.cs b/src/Renci.SshNet/PrivateKeyFile.PuTTY.cs index 627fcb99..6b1f0ea8 100644 --- a/src/Renci.SshNet/PrivateKeyFile.PuTTY.cs +++ b/src/Renci.SshNet/PrivateKeyFile.PuTTY.cs @@ -184,20 +184,12 @@ namespace Renci.SshNet var prv = privateKeyReader.ReadBignum2(); parsedKey = new EcdsaKey(curve, pub, prv); break; - case "ssh-dss": - var p = publicKeyReader.ReadBignum(); - var q = publicKeyReader.ReadBignum(); - var g = publicKeyReader.ReadBignum(); - var y = publicKeyReader.ReadBignum(); - var x = privateKeyReader.ReadBignum(); - parsedKey = new DsaKey(p, q, g, y, x); - break; case "ssh-rsa": var exponent = publicKeyReader.ReadBignum(); // e var modulus = publicKeyReader.ReadBignum(); // n var d = privateKeyReader.ReadBignum(); // d - p = privateKeyReader.ReadBignum(); // p - q = privateKeyReader.ReadBignum(); // q + var p = privateKeyReader.ReadBignum(); // p + var q = privateKeyReader.ReadBignum(); // q var inverseQ = privateKeyReader.ReadBignum(); // iqmp parsedKey = new RsaKey(modulus, exponent, d, p, q, inverseQ); break; diff --git a/src/Renci.SshNet/PrivateKeyFile.SSHCOM.cs b/src/Renci.SshNet/PrivateKeyFile.SSHCOM.cs index 568170ee..da879c3c 100644 --- a/src/Renci.SshNet/PrivateKeyFile.SSHCOM.cs +++ b/src/Renci.SshNet/PrivateKeyFile.SSHCOM.cs @@ -83,21 +83,6 @@ namespace Renci.SshNet var p = reader.ReadBigIntWithBits(); // q return new RsaKey(modulus, exponent, d, p, q, inverseQ); } - else if (keyType.Contains("dsa")) - { - var zero = reader.ReadUInt32(); - if (zero != 0) - { - throw new SshException("Invalid private key"); - } - - var p = reader.ReadBigIntWithBits(); - var g = reader.ReadBigIntWithBits(); - var q = reader.ReadBigIntWithBits(); - var y = reader.ReadBigIntWithBits(); - var x = reader.ReadBigIntWithBits(); - return new DsaKey(p, q, g, y, x); - } throw new NotSupportedException(string.Format("Key type '{0}' is not supported.", keyType)); } diff --git a/src/Renci.SshNet/PrivateKeyFile.cs b/src/Renci.SshNet/PrivateKeyFile.cs index 7a130e0e..cbd03739 100644 --- a/src/Renci.SshNet/PrivateKeyFile.cs +++ b/src/Renci.SshNet/PrivateKeyFile.cs @@ -381,10 +381,6 @@ namespace Renci.SshNet _hostAlgorithms.Add(new KeyHostAlgorithm("rsa-sha2-256", _key, new RsaDigitalSignature(rsaKey, HashAlgorithmName.SHA256))); #pragma warning restore CA2000 // Dispose objects before losing scope } - else if (_key is DsaKey) - { - _hostAlgorithms.Add(new KeyHostAlgorithm("ssh-dss", _key)); - } else { _hostAlgorithms.Add(new KeyHostAlgorithm(_key.ToString(), _key)); diff --git a/src/Renci.SshNet/Security/Certificate.cs b/src/Renci.SshNet/Security/Certificate.cs index 788239c4..30f083c1 100644 --- a/src/Renci.SshNet/Security/Certificate.cs +++ b/src/Renci.SshNet/Security/Certificate.cs @@ -348,9 +348,6 @@ namespace Renci.SshNet.Security case "ssh-rsa-cert-v01@openssh.com": keyData = new SshKeyData("ssh-rsa", LoadPublicKeys(2)); return new RsaKey(keyData); - case "ssh-dss-cert-v01@openssh.com": - keyData = new SshKeyData("ssh-dss", LoadPublicKeys(4)); - return new DsaKey(keyData); case "ecdsa-sha2-nistp256-cert-v01@openssh.com": case "ecdsa-sha2-nistp384-cert-v01@openssh.com": case "ecdsa-sha2-nistp521-cert-v01@openssh.com": diff --git a/src/Renci.SshNet/Security/Cryptography/DsaDigitalSignature.cs b/src/Renci.SshNet/Security/Cryptography/DsaDigitalSignature.cs deleted file mode 100644 index b779d418..00000000 --- a/src/Renci.SshNet/Security/Cryptography/DsaDigitalSignature.cs +++ /dev/null @@ -1,86 +0,0 @@ -#nullable enable -using System; -using System.Security.Cryptography; - -using Renci.SshNet.Common; - -namespace Renci.SshNet.Security.Cryptography -{ - /// - /// Implements DSA digital signature algorithm. - /// - public class DsaDigitalSignature : DigitalSignature, IDisposable - { - private readonly DsaKey _key; - - /// - /// Initializes a new instance of the class. - /// - /// The DSA key. - /// is . - public DsaDigitalSignature(DsaKey key) - { - ThrowHelper.ThrowIfNull(key); - - _key = key; - } - - /// - public override bool Verify(byte[] input, byte[] signature) - { -#if NETSTANDARD2_1_OR_GREATER || NET - return _key.DSA.VerifyData(input, signature, HashAlgorithmName.SHA1); -#else - // VerifyData does not exist on netstandard2.0. - // It does exist on net462, but in order to keep the path tested, - // use it on netfx as well. - using (var sha1 = SHA1.Create()) - { - var hash = sha1.ComputeHash(input); - return _key.DSA.VerifySignature(hash, signature); - } -#endif - } - - /// - /// Creates the signature. - /// - /// The input. - /// - /// Signed input data. - /// - /// Invalid DSA key. - public override byte[] Sign(byte[] input) - { -#if NETSTANDARD2_1_OR_GREATER || NET - return _key.DSA.SignData(input, HashAlgorithmName.SHA1); -#else - // SignData does not exist on netstandard2.0. - // It does exist on net462, but in order to keep the path tested, - // use it on netfx as well. - using (var sha1 = SHA1.Create()) - { - var hash = sha1.ComputeHash(input); - return _key.DSA.CreateSignature(hash); - } -#endif - } - - /// - /// Performs application-defined tasks associated with freeing, releasing, or resetting unmanaged resources. - /// - public void Dispose() - { - Dispose(disposing: true); - GC.SuppressFinalize(this); - } - - /// - /// Releases unmanaged and - optionally - managed resources. - /// - /// to release both managed and unmanaged resources; to release only unmanaged resources. - protected virtual void Dispose(bool disposing) - { - } - } -} diff --git a/src/Renci.SshNet/Security/Cryptography/DsaKey.cs b/src/Renci.SshNet/Security/Cryptography/DsaKey.cs deleted file mode 100644 index 5335f20b..00000000 --- a/src/Renci.SshNet/Security/Cryptography/DsaKey.cs +++ /dev/null @@ -1,220 +0,0 @@ -#nullable enable -using System; -using System.Formats.Asn1; -using System.Numerics; -using System.Security.Cryptography; - -using Renci.SshNet.Common; -using Renci.SshNet.Security.Cryptography; - -namespace Renci.SshNet.Security -{ - /// - /// Contains DSA private and public key. - /// - public class DsaKey : Key, IDisposable - { - private DsaDigitalSignature? _digitalSignature; - - internal DSA DSA { get; } - - /// - /// Gets the P. - /// - public BigInteger P { get; } - - /// - /// Gets the Q. - /// - public BigInteger Q { get; } - - /// - /// Gets the G. - /// - public BigInteger G { get; } - - /// - /// Gets public key Y. - /// - public BigInteger Y { get; } - - /// - /// Gets private key X. - /// - public BigInteger X { get; } - - /// - public override int KeyLength - { - get - { - return (int)P.GetBitLength(); - } - } - - /// - /// Gets the digital signature. - /// - protected internal override DigitalSignature DigitalSignature - { - get - { - _digitalSignature ??= new DsaDigitalSignature(this); - return _digitalSignature; - } - } - - /// - /// Gets the DSA public key. - /// - /// - /// An array whose values are: - /// - /// 0 - /// 1 - /// 2 - /// 3 - /// - /// - public override BigInteger[] Public - { - get - { - return new[] { P, Q, G, Y }; - } - } - - /// - /// Initializes a new instance of the class. - /// - /// The encoded public key data. - public DsaKey(SshKeyData publicKeyData) - { - ThrowHelper.ThrowIfNull(publicKeyData); - - if (publicKeyData.Name != "ssh-dss" || publicKeyData.Keys.Length != 4) - { - throw new ArgumentException($"Invalid DSA public key data. ({publicKeyData.Name}, {publicKeyData.Keys.Length}).", nameof(publicKeyData)); - } - - P = publicKeyData.Keys[0]; - Q = publicKeyData.Keys[1]; - G = publicKeyData.Keys[2]; - Y = publicKeyData.Keys[3]; - - DSA = LoadDSA(); - } - - /// - /// Initializes a new instance of the class. - /// - /// DER encoded private key data. - public DsaKey(byte[] privateKeyData) - { - ThrowHelper.ThrowIfNull(privateKeyData); - - var keyReader = new AsnReader(privateKeyData, AsnEncodingRules.DER); - var sequenceReader = keyReader.ReadSequence(); - keyReader.ThrowIfNotEmpty(); - - _ = sequenceReader.ReadInteger(); // skip version - - P = sequenceReader.ReadInteger(); - Q = sequenceReader.ReadInteger(); - G = sequenceReader.ReadInteger(); - Y = sequenceReader.ReadInteger(); - X = sequenceReader.ReadInteger(); - - sequenceReader.ThrowIfNotEmpty(); - - DSA = LoadDSA(); - } - - /// - /// Initializes a new instance of the class. - /// - /// The p. - /// The q. - /// The g. - /// The y. - /// The x. - public DsaKey(BigInteger p, BigInteger q, BigInteger g, BigInteger y, BigInteger x) - { - P = p; - Q = q; - G = g; - Y = y; - X = x; - - DSA = LoadDSA(); - } - -#pragma warning disable CA1859 // Use concrete types when possible for improved performance -#pragma warning disable CA5384 // Do Not Use Digital Signature Algorithm (DSA) - private DSA LoadDSA() - { -#if NETFRAMEWORK - // On .NET Framework we use the concrete CNG type which is FIPS-186-3 - // compatible. The CryptoServiceProvider type returned by DSA.Create() - // is limited to FIPS-186-1 (max 1024 bit key). - var dsa = new DSACng(); -#else - var dsa = DSA.Create(); -#endif - dsa.ImportParameters(GetDSAParameters()); - - return dsa; - } -#pragma warning restore CA5384 // Do Not Use Digital Signature Algorithm (DSA) -#pragma warning restore CA1859 // Use concrete types when possible for improved performance - - internal DSAParameters GetDSAParameters() - { - // P, G, Y, Q are required. - // P, G, Y must have the same length. - // If X is present, it must have the same length as Q. - - // See https://github.com/dotnet/runtime/blob/fadd8313653f71abd0068c8bf914be88edb2c8d3/src/libraries/Common/src/System/Security/Cryptography/DSACng.ImportExport.cs#L23 - // and https://github.com/dotnet/runtime/blob/fadd8313653f71abd0068c8bf914be88edb2c8d3/src/libraries/Common/src/System/Security/Cryptography/DSAKeyFormatHelper.cs#L18 - // (and similar code in RsaKey.cs) - - var ret = new DSAParameters - { - P = P.ToByteArray(isUnsigned: true, isBigEndian: true), - Q = Q.ToByteArray(isUnsigned: true, isBigEndian: true), - }; - - ret.G = G.ExportKeyParameter(ret.P.Length); - ret.Y = Y.ExportKeyParameter(ret.P.Length); - - if (!X.IsZero) - { - ret.X = X.ExportKeyParameter(ret.Q.Length); - } - - return ret; - } - - /// - /// Performs application-defined tasks associated with freeing, releasing, or resetting unmanaged resources. - /// - public void Dispose() - { - Dispose(disposing: true); - GC.SuppressFinalize(this); - } - - /// - /// Releases unmanaged and - optionally - managed resources. - /// - /// to release both managed and unmanaged resources; to release only unmanaged resources. - protected virtual void Dispose(bool disposing) - { - if (disposing) - { - _digitalSignature?.Dispose(); - DSA.Dispose(); - } - } - } -} diff --git a/test/Data/Key.DSA.PKCS8.Encrypted.Aes.256.CBC.12345.txt b/test/Data/Key.DSA.PKCS8.Encrypted.Aes.256.CBC.12345.txt deleted file mode 100644 index 03773bbf..00000000 --- a/test/Data/Key.DSA.PKCS8.Encrypted.Aes.256.CBC.12345.txt +++ /dev/null @@ -1,12 +0,0 @@ ------BEGIN ENCRYPTED PRIVATE KEY----- -MIIBrTBXBgkqhkiG9w0BBQ0wSjApBgkqhkiG9w0BBQwwHAQIjn9BgD9X0loCAggA -MAwGCCqGSIb3DQIJBQAwHQYJYIZIAWUDBAEqBBB3Zthr23nQDulzKryFEUTFBIIB -UDW8/IR0K5DRScH4Cl7HOoK20aR+TmUOGczE027RL++iosgk5rYUpIKn0pxIKM0U -StFGTqLz3G+bEh/Bm2Vt03Qv0Q2QZoX2e1Vktt32X2cLBNzGWfEpLuCD4vG8QDRW -uGkE1NHxJKQTJWQt/gwGituyhMThGoE3ZcuqeLmRlhUSgRccO6WJ2HkNOW7TM5RB -QbeBXmYB1H5S3FjpRAvd2p9dEzDsyquQaltFM4kekIxGjwiw5WSd+KsCGXFLa2Y2 -OXvcjRIIqGBJr+xvEVA86TNTfad+sKGqGUFszRmnGXA+VxEZju2OCpVhxTLEMX4Q -2vYz9i8jE78tpx7C6PTKoJe5FTdlTatvWvYD5cvcbazPUjuZbraI9ha4XvNtERGC -J0voz/7yeuNkW1ofxTUOu+snGhySC4AXkC44eZG4wUPfuQAswP8dFiQi2BthgVyP -kA== ------END ENCRYPTED PRIVATE KEY----- diff --git a/test/Data/Key.DSA.PKCS8.txt b/test/Data/Key.DSA.PKCS8.txt deleted file mode 100644 index f5baf96e..00000000 --- a/test/Data/Key.DSA.PKCS8.txt +++ /dev/null @@ -1,9 +0,0 @@ ------BEGIN PRIVATE KEY----- -MIIBSgIBADCCASsGByqGSM44BAEwggEeAoGBALVl3fae2O4qwsAK95SUShX0KMUN -P+yl/uT3lGH9T/ZptnHSlrTxnTWXCl0g91KEeCaEnDDhLxm4aCv1Ag4B/yvcM4u3 -4qkmaNLy2LiAxiqdobZcNG61Pqwqd5IDkp38LBsn8tmb12xu9NalpUfOiSEB1cyC -r4zFZMrm0wtdyJQVAhUArvojZKn/2DgGI2Kx0ghxZlgHxGECgYAOVJ434UAR3Hn6 -lA5nWNfFOuUVH3W7nJaP0FQJiIPx7GUbdxO9qtDNTbWkWL3c9qx5+B7Ole4xM7cv -yXPrNQUYDHCFlS+Ue2x3IeJrkdfZkH9ePP25y5A0J4/c+8XXvQaj4zA5nfw13oy5 -Ptyd7d3Kq5tEDM8KiVdIhwkXjUA3PQQWAhQYRjs5PgIpnqG/euBPPh7EDZcnXg== ------END PRIVATE KEY----- diff --git a/test/Data/Key.DSA.pub b/test/Data/Key.DSA.pub deleted file mode 100644 index f32c6fae..00000000 --- a/test/Data/Key.DSA.pub +++ /dev/null @@ -1 +0,0 @@ -ssh-dss AAAAB3NzaC1kc3MAAACBALVl3fae2O4qwsAK95SUShX0KMUNP+yl/uT3lGH9T/ZptnHSlrTxnTWXCl0g91KEeCaEnDDhLxm4aCv1Ag4B/yvcM4u34qkmaNLy2LiAxiqdobZcNG61Pqwqd5IDkp38LBsn8tmb12xu9NalpUfOiSEB1cyCr4zFZMrm0wtdyJQVAAAAFQCu+iNkqf/YOAYjYrHSCHFmWAfEYQAAAIAOVJ434UAR3Hn6lA5nWNfFOuUVH3W7nJaP0FQJiIPx7GUbdxO9qtDNTbWkWL3c9qx5+B7Ole4xM7cvyXPrNQUYDHCFlS+Ue2x3IeJrkdfZkH9ePP25y5A0J4/c+8XXvQaj4zA5nfw13oy5Ptyd7d3Kq5tEDM8KiVdIhwkXjUA3PQAAAIEAm8IGZQatS7M6AfNITNWG4TI7Z2aRQjLb9/MWJIID7c/VQ4zdTZdG3kpk0Gj9n4xreopK5NmYAdj8rtFfPBgmXltsLqt+bBcXkpxW//7WC29WOXW3t90ySTh+cWuWfr9fV7mf4Ql/6u/ZIgpQNvnNYezazt3fK8EXjI1dAXEuQxE= diff --git a/test/Data/Key.DSA.txt b/test/Data/Key.DSA.txt deleted file mode 100644 index 6c84e0c6..00000000 --- a/test/Data/Key.DSA.txt +++ /dev/null @@ -1,12 +0,0 @@ ------BEGIN DSA PRIVATE KEY----- -MIIBuwIBAAKBgQC1Zd32ntjuKsLACveUlEoV9CjFDT/spf7k95Rh/U/2abZx0pa0 -8Z01lwpdIPdShHgmhJww4S8ZuGgr9QIOAf8r3DOLt+KpJmjS8ti4gMYqnaG2XDRu -tT6sKneSA5Kd/CwbJ/LZm9dsbvTWpaVHzokhAdXMgq+MxWTK5tMLXciUFQIVAK76 -I2Sp/9g4BiNisdIIcWZYB8RhAoGADlSeN+FAEdx5+pQOZ1jXxTrlFR91u5yWj9BU -CYiD8exlG3cTvarQzU21pFi93PasefgezpXuMTO3L8lz6zUFGAxwhZUvlHtsdyHi -a5HX2ZB/Xjz9ucuQNCeP3PvF170Go+MwOZ38Nd6MuT7cne3dyqubRAzPColXSIcJ -F41ANz0CgYEAm8IGZQatS7M6AfNITNWG4TI7Z2aRQjLb9/MWJIID7c/VQ4zdTZdG -3kpk0Gj9n4xreopK5NmYAdj8rtFfPBgmXltsLqt+bBcXkpxW//7WC29WOXW3t90y -STh+cWuWfr9fV7mf4Ql/6u/ZIgpQNvnNYezazt3fK8EXjI1dAXEuQxECFBhGOzk+ -Aimeob964E8+HsQNlyde ------END DSA PRIVATE KEY----- diff --git a/test/Data/Key.PuTTY3.DSA.Encrypted.Argon2id.12345.ppk b/test/Data/Key.PuTTY3.DSA.Encrypted.Argon2id.12345.ppk deleted file mode 100644 index a6205ded..00000000 --- a/test/Data/Key.PuTTY3.DSA.Encrypted.Argon2id.12345.ppk +++ /dev/null @@ -1,22 +0,0 @@ -PuTTY-User-Key-File-3: ssh-dss -Encryption: aes256-cbc -Comment: imported-openssh-key -Public-Lines: 10 -AAAAB3NzaC1kc3MAAACBALVl3fae2O4qwsAK95SUShX0KMUNP+yl/uT3lGH9T/Zp -tnHSlrTxnTWXCl0g91KEeCaEnDDhLxm4aCv1Ag4B/yvcM4u34qkmaNLy2LiAxiqd -obZcNG61Pqwqd5IDkp38LBsn8tmb12xu9NalpUfOiSEB1cyCr4zFZMrm0wtdyJQV -AAAAFQCu+iNkqf/YOAYjYrHSCHFmWAfEYQAAAIAOVJ434UAR3Hn6lA5nWNfFOuUV -H3W7nJaP0FQJiIPx7GUbdxO9qtDNTbWkWL3c9qx5+B7Ole4xM7cvyXPrNQUYDHCF -lS+Ue2x3IeJrkdfZkH9ePP25y5A0J4/c+8XXvQaj4zA5nfw13oy5Ptyd7d3Kq5tE -DM8KiVdIhwkXjUA3PQAAAIEAm8IGZQatS7M6AfNITNWG4TI7Z2aRQjLb9/MWJIID -7c/VQ4zdTZdG3kpk0Gj9n4xreopK5NmYAdj8rtFfPBgmXltsLqt+bBcXkpxW//7W -C29WOXW3t90ySTh+cWuWfr9fV7mf4Ql/6u/ZIgpQNvnNYezazt3fK8EXjI1dAXEu -QxE= -Key-Derivation: Argon2id -Argon2-Memory: 8192 -Argon2-Passes: 8 -Argon2-Parallelism: 1 -Argon2-Salt: 310d916da49faba22ba8d2745777e5c5 -Private-Lines: 1 -xMm0Tg+o7Yq6lAs6L33y2fy3fiDPl6p71iKxm8OAgj4= -Private-MAC: fc2aef48bf90b80b97d06c32c37491db614331c2551ab37865d8719ee6cb5f4f diff --git a/test/Data/Key.PuTTY3.DSA.ppk b/test/Data/Key.PuTTY3.DSA.ppk deleted file mode 100644 index abecad67..00000000 --- a/test/Data/Key.PuTTY3.DSA.ppk +++ /dev/null @@ -1,17 +0,0 @@ -PuTTY-User-Key-File-3: ssh-dss -Encryption: none -Comment: imported-openssh-key -Public-Lines: 10 -AAAAB3NzaC1kc3MAAACBALVl3fae2O4qwsAK95SUShX0KMUNP+yl/uT3lGH9T/Zp -tnHSlrTxnTWXCl0g91KEeCaEnDDhLxm4aCv1Ag4B/yvcM4u34qkmaNLy2LiAxiqd -obZcNG61Pqwqd5IDkp38LBsn8tmb12xu9NalpUfOiSEB1cyCr4zFZMrm0wtdyJQV -AAAAFQCu+iNkqf/YOAYjYrHSCHFmWAfEYQAAAIAOVJ434UAR3Hn6lA5nWNfFOuUV -H3W7nJaP0FQJiIPx7GUbdxO9qtDNTbWkWL3c9qx5+B7Ole4xM7cvyXPrNQUYDHCF -lS+Ue2x3IeJrkdfZkH9ePP25y5A0J4/c+8XXvQaj4zA5nfw13oy5Ptyd7d3Kq5tE -DM8KiVdIhwkXjUA3PQAAAIEAm8IGZQatS7M6AfNITNWG4TI7Z2aRQjLb9/MWJIID -7c/VQ4zdTZdG3kpk0Gj9n4xreopK5NmYAdj8rtFfPBgmXltsLqt+bBcXkpxW//7W -C29WOXW3t90ySTh+cWuWfr9fV7mf4Ql/6u/ZIgpQNvnNYezazt3fK8EXjI1dAXEu -QxE= -Private-Lines: 1 -AAAAFBhGOzk+Aimeob964E8+HsQNlyde -Private-MAC: 6c517ac5ede72c006b0115dd9d0830c8e699a1f4d72c708d41f68b6263d974ae diff --git a/test/Data/Key.SSH2.DSA.Encrypted.Des.CBC.12345.pub b/test/Data/Key.SSH2.DSA.Encrypted.Des.CBC.12345.pub deleted file mode 100644 index 3b07844b..00000000 --- a/test/Data/Key.SSH2.DSA.Encrypted.Des.CBC.12345.pub +++ /dev/null @@ -1 +0,0 @@ -ssh-dss AAAAB3NzaC1kc3MAAACBAI8gyHFchkVhkPiwkhkjFDqN6w2nFWTqVy9sLjFs38oEWLMpAw9+c132erUptAhNQ6JZUAVZGllv/3V5hksSDyChe9WY5IfsOlh6X0dcZCwBKysEzQlPyMFqAtbc9uv7oUWNzBfvEbtV6WN/VmcmXf7dyo3EBVXbBFdPl1NKC7W9AAAAFQDY1+bTt7s2iNmYoBE4C9hdWRCyeQAAAIAEtj09ugx/Tdl6bo7X6mX17hcgVgIxcYj5VNONg2k6IHmRFriLviYaS68mIB4SG3jmvvxbXAGqR1bWBUrv90n0wpxxcuuNoCFylJQyuqUkzSsUHb0WMcncZ/tBQt+NJnRB1Zp9sw8n20ocpg3WVPdaXTtc4pk83NYB6ywG6UFPvgAAAIAX+De5dwo33LMl9W8IvA4dY8Q1wshdycAGJzhy+qYF9dCcwD1Pg+4EbPjYPmzJopsVrK97v9QhxyYcXMr/iHhngGwd9nYNzzSKx665vkSjzyeJWpeQ+fvNV3CLItP01ypbUreM+s+Vz1wor5joLKcDS4X0oQ0RIVZNEHnekuLuFg== diff --git a/test/Data/Key.SSH2.DSA.Encrypted.Des.CBC.12345.txt b/test/Data/Key.SSH2.DSA.Encrypted.Des.CBC.12345.txt deleted file mode 100644 index e7d77584..00000000 --- a/test/Data/Key.SSH2.DSA.Encrypted.Des.CBC.12345.txt +++ /dev/null @@ -1,12 +0,0 @@ ----- BEGIN SSH2 ENCRYPTED PRIVATE KEY ---- -P2/56wAAAgoAAAAmZGwtbW9kcHtzaWdue2RzYS1uaXN0LXNoYTF9LGRoe3BsYWlufX0AAA -AIM2Rlcy1jYmMAAAHIxrKV3QJkISlRHox4JYLlWJG0ccdEfMmDF3IXW+up6nUQZeWyOS9/ -csXyclUtJ/adA0qkpH5hcaIIOr1jQgvPxjMy7o3I5WJ/MvKB7omSDYG82wKZAaZQeSCaqY -Cn1DYHz6Xou5BIle37f0y71tq3d7YFCh33BjbCM8KHsar3TgRf3oegaawZyZuLnnZRy0L+ -xdsdqgntc4fyhpmCmfwIYhWwD2R9P56FXTw59VuE0r/LxxLJW8Cq2R8i7bN0lb2ezb3qnU -SykSJ5PYvoW6e7HIZ3GEr9d+wDhqp0SKWHl+shed3e5xi1NF7fRR23bZ1xlAk3FdrBrH1b -aWYW4JFzdVc33Pg5oHLe+q5NQ3vQpMxXlN2IG9cdAigWKNJMdvLuxiYi+6lzNIGAH+yb01 -56ksXYgUs65Gqnj0GMYVmf//8NN0gRKXl5dT57LyuU42jRePwANMyO/n9QOi9OKeea8Tku -f6ZMRiHQLDiZx2ShEXEhHRwmv42jt2xjuHNMbY0dZTKZEkFMUGVFVbkl5MEmN8Fj59rHJn -0adWRPLH5smwM8WXbaYt+E0r628UNZbedXCcjZ5c5egpxCBxRrSJqnK1f0l899fulB ----- END SSH2 ENCRYPTED PRIVATE KEY ---- diff --git a/test/Data/Key.SSH2.DSA.pub b/test/Data/Key.SSH2.DSA.pub deleted file mode 100644 index 65440014..00000000 --- a/test/Data/Key.SSH2.DSA.pub +++ /dev/null @@ -1 +0,0 @@ -ssh-dss AAAAB3NzaC1kc3MAAACBAOCSGuOxxY/DQBowG7fkS30AJmwN4fDPXToyTaAaxwpOWnGJXFhgP4Il+GSKlpaxnUWkajKpMc1b1hhawPWN4sxoT8QRb6SAW30ErnT/pUtsxqoFlkFla4xvWSgNAuHAVkUBrgPsJ4sHehSbNFn3I6q8Rgle2jyHDHTOqPj2KEXhAAAAFQC740YkVJdVpTJRTxd9Myi0Nx3t4wAAAIArvP7AGh5jY+zxeQRb52zxcUamRBkVYL/ferdJNi9hoM8ZaO4++Xgs8wMbpmoEch9DsXdtufjqXWpk7ywlPjcdhhsb3MxJAeEeFtTRsu2/IUTKqKPHIOgoiPzs8q69AxWhV10aDDUdYWLkqPV/tMGl6S/jC7vTJLmhZum4BUv8MQAAAIEAt19oHPIPyv/8mbMaYpu8I6kvj1/97Ejw0neN7Cd9cGZLqIPBwTyUHEQvKSAm4BvNP0Le3JDn3RFayhRmf+8RrAmS4d1MjrCOs6fmeyLnk2kTpRPFZ2x0H1udIRAhzRehyfj6OsAHn7Jclr+mqDhoq7nIfC3tSgWxFH5g948+7ks= imported-openssh-key diff --git a/test/Data/Key.SSH2.DSA.txt b/test/Data/Key.SSH2.DSA.txt deleted file mode 100644 index a4dc6d07..00000000 --- a/test/Data/Key.SSH2.DSA.txt +++ /dev/null @@ -1,13 +0,0 @@ ----- BEGIN SSH2 ENCRYPTED PRIVATE KEY ---- -Comment: "imported-openssh-key" -P2/56wAAAgIAAAAmZGwtbW9kcHtzaWdue2RzYS1uaXN0LXNoYTF9LGRoe3BsYWlufX0AAA -AEbm9uZQAAAcQAAAHAAAAAAAAABADgkhrjscWPw0AaMBu35Et9ACZsDeHwz106Mk2gGscK -TlpxiVxYYD+CJfhkipaWsZ1FpGoyqTHNW9YYWsD1jeLMaE/EEW+kgFt9BK50/6VLbMaqBZ -ZBZWuMb1koDQLhwFZFAa4D7CeLB3oUmzRZ9yOqvEYJXto8hwx0zqj49ihF4QAAA/4rvP7A -Gh5jY+zxeQRb52zxcUamRBkVYL/ferdJNi9hoM8ZaO4++Xgs8wMbpmoEch9DsXdtufjqXW -pk7ywlPjcdhhsb3MxJAeEeFtTRsu2/IUTKqKPHIOgoiPzs8q69AxWhV10aDDUdYWLkqPV/ -tMGl6S/jC7vTJLmhZum4BUv8MQAAAKC740YkVJdVpTJRTxd9Myi0Nx3t4wAABAC3X2gc8g -/K//yZsxpim7wjqS+PX/3sSPDSd43sJ31wZkuog8HBPJQcRC8pICbgG80/Qt7ckOfdEVrK -FGZ/7xGsCZLh3UyOsI6zp+Z7IueTaROlE8VnbHQfW50hECHNF6HJ+Po6wAefslyWv6aoOG -iruch8Le1KBbEUfmD3jz7uSwAAAJ9mUEtdk3zSMZJ1umUnNSo5zC+UxA== ----- END SSH2 ENCRYPTED PRIVATE KEY ---- diff --git a/test/Renci.SshNet.IntegrationTests/HostKeyAlgorithmTests.cs b/test/Renci.SshNet.IntegrationTests/HostKeyAlgorithmTests.cs index 40049938..d37230ab 100644 --- a/test/Renci.SshNet.IntegrationTests/HostKeyAlgorithmTests.cs +++ b/test/Renci.SshNet.IntegrationTests/HostKeyAlgorithmTests.cs @@ -24,12 +24,6 @@ namespace Renci.SshNet.IntegrationTests _remoteSshdConfig?.Reset(); } - [TestMethod] - public void SshDss() - { - DoTest(HostKeyAlgorithm.SshDss, HostKeyFile.Dsa); - } - [TestMethod] public void SshRsa() { diff --git a/test/Renci.SshNet.IntegrationTests/PrivateKeyAuthenticationTests.cs b/test/Renci.SshNet.IntegrationTests/PrivateKeyAuthenticationTests.cs index 6a4a37cd..2fa7fc25 100644 --- a/test/Renci.SshNet.IntegrationTests/PrivateKeyAuthenticationTests.cs +++ b/test/Renci.SshNet.IntegrationTests/PrivateKeyAuthenticationTests.cs @@ -22,12 +22,6 @@ namespace Renci.SshNet.IntegrationTests _remoteSshdConfig?.Reset(); } - [TestMethod] - public void SshDss() - { - DoTest(PublicKeyAlgorithm.SshDss, "Data.Key.SSH2.DSA.Encrypted.Des.CBC.12345.txt", "12345"); - } - [TestMethod] public void SshRsa() { diff --git a/test/Renci.SshNet.Tests/Classes/PrivateKeyFileTest.cs b/test/Renci.SshNet.Tests/Classes/PrivateKeyFileTest.cs index 3e0935ff..2e5f64a3 100644 --- a/test/Renci.SshNet.Tests/Classes/PrivateKeyFileTest.cs +++ b/test/Renci.SshNet.Tests/Classes/PrivateKeyFileTest.cs @@ -311,9 +311,6 @@ namespace Renci.SshNet.Tests.Classes } [TestMethod] - [DataRow("Key.DSA.PKCS8.Encrypted.Aes.256.CBC.12345.txt", "12345", typeof(DsaKey))] - [DataRow("Key.DSA.PKCS8.txt", null, typeof(DsaKey))] - [DataRow("Key.DSA.txt", null, typeof(DsaKey))] [DataRow("Key.ECDSA.Encrypted.txt", "12345", typeof(EcdsaKey))] [DataRow("Key.ECDSA.PKCS8.Encrypted.Aes.256.CBC.12345.txt", "12345", typeof(EcdsaKey))] [DataRow("Key.ECDSA.PKCS8.txt", null, typeof(EcdsaKey))] @@ -348,8 +345,6 @@ namespace Renci.SshNet.Tests.Classes [DataRow("Key.PuTTY2.Ed25519.ppk", null, typeof(ED25519Key))] [DataRow("Key.PuTTY2.RSA.Encrypted.12345.ppk", "12345", typeof(RsaKey))] [DataRow("Key.PuTTY2.RSA.ppk", null, typeof(RsaKey))] - [DataRow("Key.PuTTY3.DSA.Encrypted.Argon2id.12345.ppk", "12345", typeof(DsaKey))] - [DataRow("Key.PuTTY3.DSA.ppk", null, typeof(DsaKey))] [DataRow("Key.PuTTY3.ECDSA.Encrypted.Argon2id.12345.ppk", "12345", typeof(EcdsaKey))] [DataRow("Key.PuTTY3.ECDSA.ppk", null, typeof(EcdsaKey))] [DataRow("Key.PuTTY3.Ed25519.Encrypted.Argon2i.12345.ppk", "12345", typeof(ED25519Key))] @@ -366,8 +361,6 @@ namespace Renci.SshNet.Tests.Classes [DataRow("Key.RSA.PKCS8.Encrypted.Aes.256.CBC.12345.txt", "12345", typeof(RsaKey))] [DataRow("Key.RSA.PKCS8.txt", null, typeof(RsaKey))] [DataRow("Key.RSA.txt", null, typeof(RsaKey))] - [DataRow("Key.SSH2.DSA.Encrypted.Des.CBC.12345.txt", "12345", typeof(DsaKey))] - [DataRow("Key.SSH2.DSA.txt", null, typeof(DsaKey))] [DataRow("Key.SSH2.RSA.Encrypted.Des.CBC.12345.txt", "12345", typeof(RsaKey))] [DataRow("Key.SSH2.RSA.txt", null, typeof(RsaKey))] public void Test_PrivateKey(string name, string passPhrase, Type expectedKeyType) diff --git a/test/Renci.SshNet.Tests/Classes/ScpClientTest.cs b/test/Renci.SshNet.Tests/Classes/ScpClientTest.cs index d44afb78..89be6801 100644 --- a/test/Renci.SshNet.Tests/Classes/ScpClientTest.cs +++ b/test/Renci.SshNet.Tests/Classes/ScpClientTest.cs @@ -121,7 +121,7 @@ namespace Renci.SshNet.Tests.Classes var host = _random.Next().ToString(); var port = _random.Next(1, 100); var userName = _random.Next().ToString(); - var privateKeys = new[] { GetRsaKey(), GetDsaKey() }; + var privateKeys = new[] { GetRsaKey(), GetEcdsaKey() }; var client = new ScpClient(host, port, userName, privateKeys); Assert.AreEqual(16 * 1024U, client.BufferSize); @@ -154,7 +154,7 @@ namespace Renci.SshNet.Tests.Classes { var host = _random.Next().ToString(); var userName = _random.Next().ToString(); - var privateKeys = new[] { GetRsaKey(), GetDsaKey() }; + var privateKeys = new[] { GetRsaKey(), GetEcdsaKey() }; var client = new ScpClient(host, userName, privateKeys); Assert.AreEqual(16 * 1024U, client.BufferSize); @@ -222,9 +222,9 @@ namespace Renci.SshNet.Tests.Classes } } - private PrivateKeyFile GetDsaKey() + private PrivateKeyFile GetEcdsaKey() { - using (var stream = GetData("Key.SSH2.DSA.txt")) + using (var stream = GetData("Key.ECDSA.txt")) { return new PrivateKeyFile(stream); } diff --git a/test/Renci.SshNet.Tests/Classes/Security/Cryptography/DsaDigitalSignatureTest.cs b/test/Renci.SshNet.Tests/Classes/Security/Cryptography/DsaDigitalSignatureTest.cs deleted file mode 100644 index 695ec7ab..00000000 --- a/test/Renci.SshNet.Tests/Classes/Security/Cryptography/DsaDigitalSignatureTest.cs +++ /dev/null @@ -1,59 +0,0 @@ -using System.Text; - -using Microsoft.VisualStudio.TestTools.UnitTesting; - -using Renci.SshNet.Abstractions; -#if !NET6_0_OR_GREATER -using Renci.SshNet.Common; -#endif -using Renci.SshNet.Security; -using Renci.SshNet.Security.Cryptography; -using Renci.SshNet.Tests.Common; - -namespace Renci.SshNet.Tests.Classes.Security.Cryptography -{ - [TestClass] - public class DsaDigitalSignatureTest : TestBase - { - [TestMethod] - public void Verify() - { - byte[] data = Encoding.UTF8.GetBytes("Hello, World!"); - - DsaKey dsaKey = GetDsaKey("Key.DSA.txt"); - - Assert.AreEqual(1024, dsaKey.P.GetBitLength()); - Assert.AreEqual(160, dsaKey.Q.GetBitLength()); - - var digitalSignature = new DsaDigitalSignature(dsaKey); - - byte[] signedBytes = digitalSignature.Sign(data); - - // We can't compare signatures for value equality because they have a source of randomness - Assert.AreEqual(40, signedBytes.Length); - Assert.IsTrue(digitalSignature.Verify(data, signedBytes)); - - byte[] signatureToVerify = new byte[] - { - // Generated with a previous DsaDigitalSignature implementation in order to confirm consistent - // behaviour. We can't seem to validate against openssl because openssl outputs a DER signature, - // where as we want IEEE P1363 (fixed size) format. - 0x07, 0x4c, 0x5e, 0x15, 0x53, 0x36, 0x21, 0xbe, 0x5a, 0x82, 0x35, 0xd5, 0xb6, 0xe6, 0x7d, 0x2f, - 0x01, 0x2a, 0x78, 0x9b, 0x16, 0x4a, 0xe5, 0x8d, 0x85, 0xa6, 0x34, 0x56, 0x9d, 0x38, 0xd6, 0x1a, - 0xa4, 0xa1, 0x5b, 0x98, 0x7d, 0xd5, 0x35, 0x40 - }; - - Assert.IsTrue(digitalSignature.Verify(data, signatureToVerify)); - - Assert.IsFalse(digitalSignature.Verify(data, CryptoAbstraction.GenerateRandom(40))); - } - - private static DsaKey GetDsaKey(string fileName, string passPhrase = null) - { - using (var stream = GetData(fileName)) - { - return (DsaKey)new PrivateKeyFile(stream, passPhrase).Key; - } - } - } -} diff --git a/test/Renci.SshNet.Tests/Classes/Security/Cryptography/DsaKeyTest.cs b/test/Renci.SshNet.Tests/Classes/Security/Cryptography/DsaKeyTest.cs deleted file mode 100644 index 4f08eae0..00000000 --- a/test/Renci.SshNet.Tests/Classes/Security/Cryptography/DsaKeyTest.cs +++ /dev/null @@ -1,205 +0,0 @@ -using System; -using System.IO; -using System.Security.Cryptography; -using System.Text; - -using Microsoft.VisualStudio.TestTools.UnitTesting; - -#if !NET6_0_OR_GREATER -using Renci.SshNet.Common; -#endif -using Renci.SshNet.Security; -using Renci.SshNet.Tests.Common; - -namespace Renci.SshNet.Tests.Classes.Security.Cryptography -{ - [TestClass] - public class DsaKeyTest : TestBase - { - private static DsaKey GetDsaKey(string fileName, string passPhrase = null) - { - using (var stream = GetData(fileName)) - { - return (DsaKey)new PrivateKeyFile(stream, passPhrase).Key; - } - } - - // This is just to line up any differences in the assertion message. - private static void AssertEqual(byte[] actualBytes, string expectedHex) - { -#if NET - string actualHex = Convert.ToHexString(actualBytes); -#else - string actualHex = BitConverter.ToString(actualBytes).Replace("-", ""); -#endif - - Assert.AreEqual(expectedHex, actualHex, - $"{Environment.NewLine}Expected: {expectedHex}{Environment.NewLine} Actual: {actualHex}"); - } - - // These tests generated by converting the keys to PKCS8, importing them to BCL DSA, - // and printing out the expected DSAParameter values. - - // Some useful commands: - - // Generate a new params file with specific parameters: - // openssl genpkey -genparam -algorithm dsa -pkeyopt pbits:1024 -pkeyopt qbits:160 -out dsa.1024.params - - // Generate PKCS8 key file from the params: - // openssl genpkey -paramfile dsa.1024.params -out dsa.1024.txt - - // Convert to PKCS1: - // openssl pkcs8 -in dsa.1024.txt -nocrypt -traditional -out dsa.1024.pkcs1.txt - - // Convert PKCS1 to ssh.com: - // puttygen dsa.1024.pkcs1.txt -O private-sshcom -o dsa.1024.ssh2.txt - - // Convert to PKCS8: - // openssl pkcs8 -topk8 -nocrypt -in Key.DSA.txt -out Key.DSA.PKCS8.txt - - /* - - using IndentedTextWriter tw = new(Console.Out); - - foreach (string filePath in Directory.EnumerateFiles(dir, "*.DSA.*txt")) - { - string pkFile = Path.GetFileNameWithoutExtension(filePath); - - tw.WriteLine("[TestMethod]"); - tw.WriteLine($"public void {pkFile.Replace('.', '_')}()"); - tw.WriteLine("{"); - tw.Indent++; - - tw.WriteLine($"DsaKey dsaKey = GetDsaKey(\"{pkFile}.txt\");"); - tw.WriteLine(); - tw.WriteLine("DSAParameters p = dsaKey.GetDSAParameters();"); - tw.WriteLine(); - - using DSA dsa = DSA.Create(); - - dsa.ImportFromPem(File.ReadAllText(filePath)); - - DSAParameters p = dsa.ExportParameters(true); - - WriteParamAssert(p.P); - WriteParamAssert(p.G); - WriteParamAssert(p.Y); - WriteParamAssert(p.Q); - WriteParamAssert(p.X); - - tw.Indent--; - tw.WriteLine("}"); - tw.WriteLine(); - } - - void WriteParamAssert(byte[] bytes, [CallerArgumentExpression(nameof(bytes))] string name = null) - { - tw.WriteLine($"AssertEqual({name}, \"{Convert.ToHexString(bytes)}\");"); - } - */ - - [TestMethod] - public void Key_DSA() - { - DsaKey dsaKey = GetDsaKey("Key.DSA.txt"); - - Assert.AreEqual(1024, dsaKey.P.GetBitLength()); - Assert.AreEqual(160, dsaKey.Q.GetBitLength()); - - DSAParameters p = dsaKey.GetDSAParameters(); - - AssertEqual(p.P, "B565DDF69ED8EE2AC2C00AF794944A15F428C50D3FECA5FEE4F79461FD4FF669B671D296B4F19D35970A5D20F752847826849C30E12F19B8682BF5020E01FF2BDC338BB7E2A92668D2F2D8B880C62A9DA1B65C346EB53EAC2A779203929DFC2C1B27F2D99BD76C6EF4D6A5A547CE892101D5CC82AF8CC564CAE6D30B5DC89415"); - AssertEqual(p.G, "0E549E37E14011DC79FA940E6758D7C53AE5151F75BB9C968FD054098883F1EC651B7713BDAAD0CD4DB5A458BDDCF6AC79F81ECE95EE3133B72FC973EB3505180C7085952F947B6C7721E26B91D7D9907F5E3CFDB9CB9034278FDCFBC5D7BD06A3E330399DFC35DE8CB93EDC9DEDDDCAAB9B440CCF0A8957488709178D40373D"); - AssertEqual(p.Y, "9BC2066506AD4BB33A01F3484CD586E1323B6766914232DBF7F316248203EDCFD5438CDD4D9746DE4A64D068FD9F8C6B7A8A4AE4D99801D8FCAED15F3C18265E5B6C2EAB7E6C1717929C56FFFED60B6F563975B7B7DD3249387E716B967EBF5F57B99FE1097FEAEFD9220A5036F9CD61ECDACEDDDF2BC1178C8D5D01712E4311"); - AssertEqual(p.Q, "AEFA2364A9FFD838062362B1D20871665807C461"); - AssertEqual(p.X, "18463B393E02299EA1BF7AE04F3E1EC40D97275E"); - } - - - [TestMethod] - public void Key_SSH2_DSA_Encrypted_Des_CBC_12345() - { - DsaKey dsaKey = GetDsaKey("Key.SSH2.DSA.Encrypted.Des.CBC.12345.txt", "12345"); - - Assert.AreEqual(1024, dsaKey.P.GetBitLength()); - Assert.AreEqual(160, dsaKey.Q.GetBitLength()); - - DSAParameters p = dsaKey.GetDSAParameters(); - - AssertEqual(p.P, "8F20C8715C86456190F8B0921923143A8DEB0DA71564EA572F6C2E316CDFCA0458B329030F7E735DF67AB529B4084D43A2595005591A596FFF7579864B120F20A17BD598E487EC3A587A5F475C642C012B2B04CD094FC8C16A02D6DCF6EBFBA1458DCC17EF11BB55E9637F5667265DFEDDCA8DC40555DB04574F97534A0BB5BD"); - AssertEqual(p.G, "04B63D3DBA0C7F4DD97A6E8ED7EA65F5EE17205602317188F954D38D83693A20799116B88BBE261A4BAF26201E121B78E6BEFC5B5C01AA4756D6054AEFF749F4C29C7172EB8DA02172949432BAA524CD2B141DBD1631C9DC67FB4142DF8D267441D59A7DB30F27DB4A1CA60DD654F75A5D3B5CE2993CDCD601EB2C06E9414FBE"); - AssertEqual(p.Y, "17F837B9770A37DCB325F56F08BC0E1D63C435C2C85DC9C006273872FAA605F5D09CC03D4F83EE046CF8D83E6CC9A29B15ACAF7BBFD421C7261C5CCAFF887867806C1DF6760DCF348AC7AEB9BE44A3CF27895A9790F9FBCD57708B22D3F4D72A5B52B78CFACF95CF5C28AF98E82CA7034B85F4A10D1121564D1079DE92E2EE16"); - AssertEqual(p.Q, "D8D7E6D3B7BB3688D998A011380BD85D5910B279"); - AssertEqual(p.X, "23FA5A574AF1197B185B88008A7A7527899FD092"); - } - - [TestMethod] - public void Key_SSH2_DSA() - { - DsaKey dsaKey = GetDsaKey("Key.SSH2.DSA.txt"); - - Assert.AreEqual(1024, dsaKey.P.GetBitLength()); - Assert.AreEqual(160, dsaKey.Q.GetBitLength()); - - DSAParameters p = dsaKey.GetDSAParameters(); - - AssertEqual(p.P, "E0921AE3B1C58FC3401A301BB7E44B7D00266C0DE1F0CF5D3A324DA01AC70A4E5A71895C58603F8225F8648A9696B19D45A46A32A931CD5BD6185AC0F58DE2CC684FC4116FA4805B7D04AE74FFA54B6CC6AA059641656B8C6F59280D02E1C0564501AE03EC278B077A149B3459F723AABC46095EDA3C870C74CEA8F8F62845E1"); - AssertEqual(p.G, "2BBCFEC01A1E6363ECF179045BE76CF17146A644191560BFDF7AB749362F61A0CF1968EE3EF9782CF3031BA66A04721F43B1776DB9F8EA5D6A64EF2C253E371D861B1BDCCC4901E11E16D4D1B2EDBF2144CAA8A3C720E82888FCECF2AEBD0315A1575D1A0C351D6162E4A8F57FB4C1A5E92FE30BBBD324B9A166E9B8054BFC31"); - AssertEqual(p.Y, "B75F681CF20FCAFFFC99B31A629BBC23A92F8F5FFDEC48F0D2778DEC277D70664BA883C1C13C941C442F292026E01BCD3F42DEDC90E7DD115ACA14667FEF11AC0992E1DD4C8EB08EB3A7E67B22E7936913A513C5676C741F5B9D211021CD17A1C9F8FA3AC0079FB25C96BFA6A83868ABB9C87C2DED4A05B1147E60F78F3EEE4B"); - AssertEqual(p.Q, "BBE34624549755A532514F177D3328B4371DEDE3"); - AssertEqual(p.X, "66504B5D937CD2319275BA6527352A39CC2F94C4"); - } - - [TestMethod] - public void Key_DSA_3072_256() - { - // Not supported by OpenSSH but easy enough to test here. - - var keyString = """ - -----BEGIN DSA PRIVATE KEY----- - MIIE1gIBAAKCAYEA6Rb9Cogx64CZcrnP35Nr8W9sjcUqoCpSfZrJdvIhTxgyAkEl - d9U868azCTZ1QGvUuPOCGB5Ll8nRQ6QSK9bicSQ3q3C69BcjzTfZcFuZEi533wEl - 9m9xZTbMAW8643jgARKszoNWIeTGsk2JcXQ2c6+VfPOml6F7yMv3KDIpqjUQlpK+ - RoZn5Eg5R2+2VqcNwwqbP8dyQGnGmgX2hlzbWx9Cld8NTG2b0B6Taaea4zqiMLHC - MeOUh+3WkbGM+aVQ7kthQbkhTEMmZeB/zyJrlEQGmKJl/cuvx69iO8nPSIZJDSEp - sZwg6p+Fqlm0+IyaFaxJMF+SuQirYLR+ee5oor5lcWS3Szaaikz0u1ONO3ndWAmO - eEHq7BL4vuHc/SDxfO5RouhEirCUFtGwtYq/Kf7x53ccd0Jmlj1FalubKHaiyYSg - baHrvN8rFv12XDMI0vPDeOxLVaxaB3zSJTz/ZwDjUcFx7PbuWsvOoSZeagd0sCm9 - aVNQoe7dy/5YCrM7AiEA1oznSuokVWnPt9GaBlmggzk9lMjZ/XVr9MFuDzWDycsC - ggGAYVSdm43WuonZQ40M9An5oBZuWsv22ZNXFnMXzcrKkvdslWGP+za/Ipa+tm+j - YE82vuqCdGjDuDJViJbrx2FProe4J/to2Gpd0jc0uV2c1PFO0B1hDk7tkglQyhmV - q9GAQatA4XUM5cIiInseF5JxHMmfgwEKmfIUDotWnpFQImMvehHxZfI29ngrB2ND - Ba4wBIj1Ua4UqsQi2beNfope7+XSsBQm98prswjvdR6n6wg9Xkvtn4ti3lLbEHzO - ZlwnxoRxFlNE/s2RaygGySRRYAe9TPriGWeMpWirYF3/SDAQyt5qDJsPQU0fWAuF - WsuxDlOsaLmJNJNnvySwx5Qmiw4e17U+6/IKptVbOHWowq05PxZKSVYmcP5+Jbt2 - eVzozKPNGkEw6aBy18l4t+ehx7fiUha7uCPaZ+VTPodLRZE6sKT1uiKOBtPqhrsp - bxKJ3zzmF1KZpoOG++1JHzqOPL+Npokd+K3ce9vNfU7eWTYP2DuiooyF9EktJt7w - AVilAoIBgBCpFSwJxhdAIQRefnQmweW+eXRbx8KL+8t53YsPS/fQhdzIEVEi5LWz - cJ0iAU2l2Mj43AC/6yehA8KF6vJEy4LWSXNwoGVqEoSA2LxBaomLxLARqlFyfCZN - yBlUVfXDiqFw2ajRaLQKUIxWbfC6ard69brWZuS61YQd8Jrk782VAa+sQO6Ca6Ii - vtyyRjNKxbeYwKLkZydi9JFdYYR6kmVG1ge7spemMHlozza6VvNcDU3hE4T4PwbY - Ns555ihK79EWGO2zCNjhPEIN34IjN2WjbUidCBWPGgXLhw9BYyEEREhfP1QUTe2q - S3gup/j8//v46O+OZFcB6g/MZB2IFpRRSw16qM2+pNZFKVTvXs/dUq5tEXylbMCg - +7jS5eLVAkDYFwSUai4Ht9VOHGASz7VyfPfngL8nx+KLNyegB12OLwr6ho5tc9dE - Rib63kEJnsK6CzIjg1+iFblWy4pQsHnKEgvBWxk4+sLyEZFTtjCe7KjigdH6WRDH - U5ejA3bnFQIhAIkT3ff8AjkByyJg1CRkpwDCvFag1fbPXEdg1Ru1E+l/ - -----END DSA PRIVATE KEY----- - """; - - using MemoryStream stream = new MemoryStream(Encoding.UTF8.GetBytes(keyString)); - - DsaKey dsaKey = (DsaKey)new PrivateKeyFile(stream).Key; - - Assert.AreEqual(3072, dsaKey.P.GetBitLength()); - Assert.AreEqual(256, dsaKey.Q.GetBitLength()); - - DSAParameters p = dsaKey.GetDSAParameters(); - - AssertEqual(p.P, "E916FD0A8831EB809972B9CFDF936BF16F6C8DC52AA02A527D9AC976F2214F183202412577D53CEBC6B3093675406BD4B8F382181E4B97C9D143A4122BD6E2712437AB70BAF41723CD37D9705B99122E77DF0125F66F716536CC016F3AE378E00112ACCE835621E4C6B24D8971743673AF957CF3A697A17BC8CBF7283229AA35109692BE468667E44839476FB656A70DC30A9B3FC7724069C69A05F6865CDB5B1F4295DF0D4C6D9BD01E9369A79AE33AA230B1C231E39487EDD691B18CF9A550EE4B6141B9214C432665E07FCF226B94440698A265FDCBAFC7AF623BC9CF4886490D2129B19C20EA9F85AA59B4F88C9A15AC49305F92B908AB60B47E79EE68A2BE657164B74B369A8A4CF4BB538D3B79DD58098E7841EAEC12F8BEE1DCFD20F17CEE51A2E8448AB09416D1B0B58ABF29FEF1E7771C774266963D456A5B9B2876A2C984A06DA1EBBCDF2B16FD765C3308D2F3C378EC4B55AC5A077CD2253CFF6700E351C171ECF6EE5ACBCEA1265E6A0774B029BD695350A1EEDDCBFE580AB33B"); - AssertEqual(p.G, "61549D9B8DD6BA89D9438D0CF409F9A0166E5ACBF6D99357167317CDCACA92F76C95618FFB36BF2296BEB66FA3604F36BEEA827468C3B832558896EBC7614FAE87B827FB68D86A5DD23734B95D9CD4F14ED01D610E4EED920950CA1995ABD18041AB40E1750CE5C222227B1E1792711CC99F83010A99F2140E8B569E915022632F7A11F165F236F6782B07634305AE300488F551AE14AAC422D9B78D7E8A5EEFE5D2B01426F7CA6BB308EF751EA7EB083D5E4BED9F8B62DE52DB107CCE665C27C68471165344FECD916B2806C924516007BD4CFAE219678CA568AB605DFF483010CADE6A0C9B0F414D1F580B855ACBB10E53AC68B989349367BF24B0C794268B0E1ED7B53EEBF20AA6D55B3875A8C2AD393F164A49562670FE7E25BB76795CE8CCA3CD1A4130E9A072D7C978B7E7A1C7B7E25216BBB823DA67E5533E874B45913AB0A4F5BA228E06D3EA86BB296F1289DF3CE6175299A68386FBED491F3A8E3CBF8DA6891DF8ADDC7BDBCD7D4EDE59360FD83BA2A28C85F4492D26DEF00158A5"); - AssertEqual(p.Y, "10A9152C09C6174021045E7E7426C1E5BE79745BC7C28BFBCB79DD8B0F4BF7D085DCC8115122E4B5B3709D22014DA5D8C8F8DC00BFEB27A103C285EAF244CB82D6497370A0656A128480D8BC416A898BC4B011AA51727C264DC8195455F5C38AA170D9A8D168B40A508C566DF0BA6AB77AF5BAD666E4BAD5841DF09AE4EFCD9501AFAC40EE826BA222BEDCB246334AC5B798C0A2E4672762F4915D61847A926546D607BBB297A6307968CF36BA56F35C0D4DE11384F83F06D836CE79E6284AEFD11618EDB308D8E13C420DDF82233765A36D489D08158F1A05CB870F4163210444485F3F54144DEDAA4B782EA7F8FCFFFBF8E8EF8E645701EA0FCC641D881694514B0D7AA8CDBEA4D6452954EF5ECFDD52AE6D117CA56CC0A0FBB8D2E5E2D50240D81704946A2E07B7D54E1C6012CFB5727CF7E780BF27C7E28B3727A0075D8E2F0AFA868E6D73D7444626FADE41099EC2BA0B3223835FA215B956CB8A50B079CA120BC15B1938FAC2F2119153B6309EECA8E281D1FA5910C75397A30376E715"); - AssertEqual(p.Q, "D68CE74AEA245569CFB7D19A0659A083393D94C8D9FD756BF4C16E0F3583C9CB"); - AssertEqual(p.X, "8913DDF7FC023901CB2260D42464A700C2BC56A0D5F6CF5C4760D51BB513E97F"); - } - } -}