diff options
author | Peter Dettman <peter.dettman@gmail.com> | 2022-06-21 19:34:30 +0700 |
---|---|---|
committer | Peter Dettman <peter.dettman@gmail.com> | 2022-06-21 19:34:30 +0700 |
commit | 28616776b548f3b68425a0e481a62c08de28d837 (patch) | |
tree | 8869d32d58251f4a4416558847957e6e2181657b /crypto/src | |
parent | ObsoleteAttribute cleanup (diff) | |
download | BouncyCastle.NET-ed25519-28616776b548f3b68425a0e481a62c08de28d837.tar.xz |
Remove legacy TLS
Diffstat (limited to 'crypto/src')
166 files changed, 2 insertions, 22278 deletions
diff --git a/crypto/src/cms/CMSSignedHelper.cs b/crypto/src/cms/CMSSignedHelper.cs index 6d17200d0..07a3a92d1 100644 --- a/crypto/src/cms/CMSSignedHelper.cs +++ b/crypto/src/cms/CMSSignedHelper.cs @@ -4,8 +4,6 @@ using System.Collections; using Org.BouncyCastle.Asn1; using Org.BouncyCastle.Asn1.CryptoPro; using Org.BouncyCastle.Asn1.Eac; -using Org.BouncyCastle.Asn1.Iana; -using Org.BouncyCastle.Asn1.Misc; using Org.BouncyCastle.Asn1.Nist; using Org.BouncyCastle.Asn1.Oiw; using Org.BouncyCastle.Asn1.Pkcs; @@ -13,14 +11,12 @@ using Org.BouncyCastle.Asn1.TeleTrust; using Org.BouncyCastle.Asn1.X509; using Org.BouncyCastle.Asn1.X9; using Org.BouncyCastle.Crypto; +using Org.BouncyCastle.Crypto.Parameters; using Org.BouncyCastle.Security; -using Org.BouncyCastle.Security.Certificates; using Org.BouncyCastle.Utilities; +using Org.BouncyCastle.Utilities.Collections; using Org.BouncyCastle.X509; using Org.BouncyCastle.X509.Store; -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Utilities.Collections; -using Org.BouncyCastle.Crypto.Tls; namespace Org.BouncyCastle.Cms { diff --git a/crypto/src/crypto/tls/AbstractTlsAgreementCredentials.cs b/crypto/src/crypto/tls/AbstractTlsAgreementCredentials.cs deleted file mode 100644 index 2d7af80e8..000000000 --- a/crypto/src/crypto/tls/AbstractTlsAgreementCredentials.cs +++ /dev/null @@ -1,12 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class AbstractTlsAgreementCredentials - : AbstractTlsCredentials, TlsAgreementCredentials - { - /// <exception cref="IOException"></exception> - public abstract byte[] GenerateAgreement(AsymmetricKeyParameter peerPublicKey); - } -} diff --git a/crypto/src/crypto/tls/AbstractTlsCipherFactory.cs b/crypto/src/crypto/tls/AbstractTlsCipherFactory.cs deleted file mode 100644 index 141ee6507..000000000 --- a/crypto/src/crypto/tls/AbstractTlsCipherFactory.cs +++ /dev/null @@ -1,15 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class AbstractTlsCipherFactory - : TlsCipherFactory - { - /// <exception cref="IOException"></exception> - public virtual TlsCipher CreateCipher(TlsContext context, int encryptionAlgorithm, int macAlgorithm) - { - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } -} diff --git a/crypto/src/crypto/tls/AbstractTlsClient.cs b/crypto/src/crypto/tls/AbstractTlsClient.cs deleted file mode 100644 index 356aab8d2..000000000 --- a/crypto/src/crypto/tls/AbstractTlsClient.cs +++ /dev/null @@ -1,266 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class AbstractTlsClient - : AbstractTlsPeer, TlsClient - { - protected TlsCipherFactory mCipherFactory; - - protected TlsClientContext mContext; - - protected IList mSupportedSignatureAlgorithms; - protected int[] mNamedCurves; - protected byte[] mClientECPointFormats, mServerECPointFormats; - - protected int mSelectedCipherSuite; - protected short mSelectedCompressionMethod; - - public AbstractTlsClient() - : this(new DefaultTlsCipherFactory()) - { - } - - public AbstractTlsClient(TlsCipherFactory cipherFactory) - { - this.mCipherFactory = cipherFactory; - } - - protected virtual bool AllowUnexpectedServerExtension(int extensionType, byte[] extensionData) - { - switch (extensionType) - { - case ExtensionType.supported_groups: - /* - * Exception added based on field reports that some servers do send this, although the - * Supported Elliptic Curves Extension is clearly intended to be client-only. If - * present, we still require that it is a valid EllipticCurveList. - */ - TlsEccUtilities.ReadSupportedEllipticCurvesExtension(extensionData); - return true; - - case ExtensionType.ec_point_formats: - /* - * Exception added based on field reports that some servers send this even when they - * didn't negotiate an ECC cipher suite. If present, we still require that it is a valid - * ECPointFormatList. - */ - TlsEccUtilities.ReadSupportedPointFormatsExtension(extensionData); - return true; - - default: - return false; - } - } - - protected virtual void CheckForUnexpectedServerExtension(IDictionary serverExtensions, int extensionType) - { - byte[] extensionData = TlsUtilities.GetExtensionData(serverExtensions, extensionType); - if (extensionData != null && !AllowUnexpectedServerExtension(extensionType, extensionData)) - { - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - } - - public virtual void Init(TlsClientContext context) - { - this.mContext = context; - } - - public virtual TlsSession GetSessionToResume() - { - return null; - } - - public virtual ProtocolVersion ClientHelloRecordLayerVersion - { - get - { - // "{03,00}" - //return ProtocolVersion.SSLv3; - - // "the lowest version number supported by the client" - //return MinimumVersion; - - // "the value of ClientHello.client_version" - return ClientVersion; - } - } - - public virtual ProtocolVersion ClientVersion - { - get { return ProtocolVersion.TLSv12; } - } - - public virtual bool IsFallback - { - /* - * RFC 7507 4. The TLS_FALLBACK_SCSV cipher suite value is meant for use by clients that - * repeat a connection attempt with a downgraded protocol (perform a "fallback retry") in - * order to work around interoperability problems with legacy servers. - */ - get { return false; } - } - - public virtual IDictionary GetClientExtensions() - { - IDictionary clientExtensions = null; - - ProtocolVersion clientVersion = mContext.ClientVersion; - - /* - * RFC 5246 7.4.1.4.1. Note: this extension is not meaningful for TLS versions prior to 1.2. - * Clients MUST NOT offer it if they are offering prior versions. - */ - if (TlsUtilities.IsSignatureAlgorithmsExtensionAllowed(clientVersion)) - { - // TODO Provide a way for the user to specify the acceptable hash/signature algorithms. - - this.mSupportedSignatureAlgorithms = TlsUtilities.GetDefaultSupportedSignatureAlgorithms(); - - clientExtensions = TlsExtensionsUtilities.EnsureExtensionsInitialised(clientExtensions); - - TlsUtilities.AddSignatureAlgorithmsExtension(clientExtensions, mSupportedSignatureAlgorithms); - } - - if (TlsEccUtilities.ContainsEccCipherSuites(GetCipherSuites())) - { - /* - * RFC 4492 5.1. A client that proposes ECC cipher suites in its ClientHello message - * appends these extensions (along with any others), enumerating the curves it supports - * and the point formats it can parse. Clients SHOULD send both the Supported Elliptic - * Curves Extension and the Supported Point Formats Extension. - */ - /* - * TODO Could just add all the curves since we support them all, but users may not want - * to use unnecessarily large fields. Need configuration options. - */ - this.mNamedCurves = new int[]{ NamedCurve.secp256r1, NamedCurve.secp384r1 }; - this.mClientECPointFormats = new byte[]{ ECPointFormat.uncompressed, - ECPointFormat.ansiX962_compressed_prime, ECPointFormat.ansiX962_compressed_char2, }; - - clientExtensions = TlsExtensionsUtilities.EnsureExtensionsInitialised(clientExtensions); - - TlsEccUtilities.AddSupportedEllipticCurvesExtension(clientExtensions, mNamedCurves); - TlsEccUtilities.AddSupportedPointFormatsExtension(clientExtensions, mClientECPointFormats); - } - - return clientExtensions; - } - - public virtual ProtocolVersion MinimumVersion - { - get { return ProtocolVersion.TLSv10; } - } - - public virtual void NotifyServerVersion(ProtocolVersion serverVersion) - { - if (!MinimumVersion.IsEqualOrEarlierVersionOf(serverVersion)) - throw new TlsFatalAlert(AlertDescription.protocol_version); - } - - public abstract int[] GetCipherSuites(); - - public virtual byte[] GetCompressionMethods() - { - return new byte[]{ CompressionMethod.cls_null }; - } - - public virtual void NotifySessionID(byte[] sessionID) - { - // Currently ignored - } - - public virtual void NotifySelectedCipherSuite(int selectedCipherSuite) - { - this.mSelectedCipherSuite = selectedCipherSuite; - } - - public virtual void NotifySelectedCompressionMethod(byte selectedCompressionMethod) - { - this.mSelectedCompressionMethod = selectedCompressionMethod; - } - - public virtual void ProcessServerExtensions(IDictionary serverExtensions) - { - /* - * TlsProtocol implementation validates that any server extensions received correspond to - * client extensions sent. By default, we don't send any, and this method is not called. - */ - if (serverExtensions != null) - { - /* - * RFC 5246 7.4.1.4.1. Servers MUST NOT send this extension. - */ - CheckForUnexpectedServerExtension(serverExtensions, ExtensionType.signature_algorithms); - - CheckForUnexpectedServerExtension(serverExtensions, ExtensionType.supported_groups); - - if (TlsEccUtilities.IsEccCipherSuite(this.mSelectedCipherSuite)) - { - this.mServerECPointFormats = TlsEccUtilities.GetSupportedPointFormatsExtension(serverExtensions); - } - else - { - CheckForUnexpectedServerExtension(serverExtensions, ExtensionType.ec_point_formats); - } - - /* - * RFC 7685 3. The server MUST NOT echo the extension. - */ - CheckForUnexpectedServerExtension(serverExtensions, ExtensionType.padding); - } - } - - public virtual void ProcessServerSupplementalData(IList serverSupplementalData) - { - if (serverSupplementalData != null) - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - - public abstract TlsKeyExchange GetKeyExchange(); - - public abstract TlsAuthentication GetAuthentication(); - - public virtual IList GetClientSupplementalData() - { - return null; - } - - public override TlsCompression GetCompression() - { - switch (mSelectedCompressionMethod) - { - case CompressionMethod.cls_null: - return new TlsNullCompression(); - - case CompressionMethod.DEFLATE: - return new TlsDeflateCompression(); - - default: - /* - * Note: internal error here; the TlsProtocol implementation verifies that the - * server-selected compression method was in the list of client-offered compression - * methods, so if we now can't produce an implementation, we shouldn't have offered it! - */ - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } - - public override TlsCipher GetCipher() - { - int encryptionAlgorithm = TlsUtilities.GetEncryptionAlgorithm(mSelectedCipherSuite); - int macAlgorithm = TlsUtilities.GetMacAlgorithm(mSelectedCipherSuite); - - return mCipherFactory.CreateCipher(mContext, encryptionAlgorithm, macAlgorithm); - } - - public virtual void NotifyNewSessionTicket(NewSessionTicket newSessionTicket) - { - } - } -} diff --git a/crypto/src/crypto/tls/AbstractTlsContext.cs b/crypto/src/crypto/tls/AbstractTlsContext.cs deleted file mode 100644 index bbcdb5ebc..000000000 --- a/crypto/src/crypto/tls/AbstractTlsContext.cs +++ /dev/null @@ -1,166 +0,0 @@ -using System; -using System.Threading; - -using Org.BouncyCastle.Crypto.Prng; -using Org.BouncyCastle.Crypto.Utilities; -using Org.BouncyCastle.Security; -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - internal abstract class AbstractTlsContext - : TlsContext - { - private static long counter = Times.NanoTime(); - -#if NETCF_1_0 - private static object counterLock = new object(); - private static long NextCounterValue() - { - lock (counterLock) - { - return ++counter; - } - } -#else - private static long NextCounterValue() - { - return Interlocked.Increment(ref counter); - } -#endif - - private static IRandomGenerator CreateNonceRandom(SecureRandom secureRandom, int connectionEnd) - { - byte[] additionalSeedMaterial = new byte[16]; - Pack.UInt64_To_BE((ulong)NextCounterValue(), additionalSeedMaterial, 0); - Pack.UInt64_To_BE((ulong)Times.NanoTime(), additionalSeedMaterial, 8); - additionalSeedMaterial[0] &= 0x7F; - additionalSeedMaterial[0] |= (byte)(connectionEnd << 7); - - IDigest digest = TlsUtilities.CreateHash(HashAlgorithm.sha256); - - byte[] seed = new byte[digest.GetDigestSize()]; - secureRandom.NextBytes(seed); - - IRandomGenerator nonceRandom = new DigestRandomGenerator(digest); - nonceRandom.AddSeedMaterial(additionalSeedMaterial); - nonceRandom.AddSeedMaterial(seed); - return nonceRandom; - } - - private readonly IRandomGenerator mNonceRandom; - private readonly SecureRandom mSecureRandom; - private readonly SecurityParameters mSecurityParameters; - - private ProtocolVersion mClientVersion = null; - private ProtocolVersion mServerVersion = null; - private TlsSession mSession = null; - private object mUserObject = null; - - internal AbstractTlsContext(SecureRandom secureRandom, SecurityParameters securityParameters) - { - this.mSecureRandom = secureRandom; - this.mSecurityParameters = securityParameters; - this.mNonceRandom = CreateNonceRandom(secureRandom, securityParameters.Entity); - } - - public virtual IRandomGenerator NonceRandomGenerator - { - get { return mNonceRandom; } - } - - public virtual SecureRandom SecureRandom - { - get { return mSecureRandom; } - } - - public virtual SecurityParameters SecurityParameters - { - get { return mSecurityParameters; } - } - - public abstract bool IsServer { get; } - - public virtual ProtocolVersion ClientVersion - { - get { return mClientVersion; } - } - - internal virtual void SetClientVersion(ProtocolVersion clientVersion) - { - this.mClientVersion = clientVersion; - } - - public virtual ProtocolVersion ServerVersion - { - get { return mServerVersion; } - } - - internal virtual void SetServerVersion(ProtocolVersion serverVersion) - { - this.mServerVersion = serverVersion; - } - - public virtual TlsSession ResumableSession - { - get { return mSession; } - } - - internal virtual void SetResumableSession(TlsSession session) - { - this.mSession = session; - } - - public virtual object UserObject - { - get { return mUserObject; } - set { this.mUserObject = value; } - } - - public virtual byte[] ExportKeyingMaterial(string asciiLabel, byte[] context_value, int length) - { - if (context_value != null && !TlsUtilities.IsValidUint16(context_value.Length)) - throw new ArgumentException("must have length less than 2^16 (or be null)", "context_value"); - - SecurityParameters sp = SecurityParameters; - if (!sp.IsExtendedMasterSecret) - { - /* - * RFC 7627 5.4. If a client or server chooses to continue with a full handshake without - * the extended master secret extension, [..] the client or server MUST NOT export any - * key material based on the new master secret for any subsequent application-level - * authentication. In particular, it MUST disable [RFC5705] [..]. - */ - throw new InvalidOperationException("cannot export keying material without extended_master_secret"); - } - - byte[] cr = sp.ClientRandom, sr = sp.ServerRandom; - - int seedLength = cr.Length + sr.Length; - if (context_value != null) - { - seedLength += (2 + context_value.Length); - } - - byte[] seed = new byte[seedLength]; - int seedPos = 0; - - Array.Copy(cr, 0, seed, seedPos, cr.Length); - seedPos += cr.Length; - Array.Copy(sr, 0, seed, seedPos, sr.Length); - seedPos += sr.Length; - if (context_value != null) - { - TlsUtilities.WriteUint16(context_value.Length, seed, seedPos); - seedPos += 2; - Array.Copy(context_value, 0, seed, seedPos, context_value.Length); - seedPos += context_value.Length; - } - - if (seedPos != seedLength) - throw new InvalidOperationException("error in calculation of seed for export"); - - return TlsUtilities.PRF(this, sp.MasterSecret, asciiLabel, seed, length); - } - } -} diff --git a/crypto/src/crypto/tls/AbstractTlsCredentials.cs b/crypto/src/crypto/tls/AbstractTlsCredentials.cs deleted file mode 100644 index 6411b811c..000000000 --- a/crypto/src/crypto/tls/AbstractTlsCredentials.cs +++ /dev/null @@ -1,10 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class AbstractTlsCredentials - : TlsCredentials - { - public abstract Certificate Certificate { get; } - } -} diff --git a/crypto/src/crypto/tls/AbstractTlsEncryptionCredentials.cs b/crypto/src/crypto/tls/AbstractTlsEncryptionCredentials.cs deleted file mode 100644 index 05b129c60..000000000 --- a/crypto/src/crypto/tls/AbstractTlsEncryptionCredentials.cs +++ /dev/null @@ -1,12 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class AbstractTlsEncryptionCredentials - : AbstractTlsCredentials, TlsEncryptionCredentials - { - /// <exception cref="IOException"></exception> - public abstract byte[] DecryptPreMasterSecret(byte[] encryptedPreMasterSecret); - } -} diff --git a/crypto/src/crypto/tls/AbstractTlsKeyExchange.cs b/crypto/src/crypto/tls/AbstractTlsKeyExchange.cs deleted file mode 100644 index 294b24929..000000000 --- a/crypto/src/crypto/tls/AbstractTlsKeyExchange.cs +++ /dev/null @@ -1,177 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class AbstractTlsKeyExchange - : TlsKeyExchange - { - protected readonly int mKeyExchange; - protected IList mSupportedSignatureAlgorithms; - - protected TlsContext mContext; - - protected AbstractTlsKeyExchange(int keyExchange, IList supportedSignatureAlgorithms) - { - this.mKeyExchange = keyExchange; - this.mSupportedSignatureAlgorithms = supportedSignatureAlgorithms; - } - - protected virtual DigitallySigned ParseSignature(Stream input) - { - DigitallySigned signature = DigitallySigned.Parse(mContext, input); - SignatureAndHashAlgorithm signatureAlgorithm = signature.Algorithm; - if (signatureAlgorithm != null) - { - TlsUtilities.VerifySupportedSignatureAlgorithm(mSupportedSignatureAlgorithms, signatureAlgorithm); - } - return signature; - } - - public virtual void Init(TlsContext context) - { - this.mContext = context; - - ProtocolVersion clientVersion = context.ClientVersion; - - if (TlsUtilities.IsSignatureAlgorithmsExtensionAllowed(clientVersion)) - { - /* - * RFC 5246 7.4.1.4.1. If the client does not send the signature_algorithms extension, - * the server MUST do the following: - * - * - If the negotiated key exchange algorithm is one of (RSA, DHE_RSA, DH_RSA, RSA_PSK, - * ECDH_RSA, ECDHE_RSA), behave as if client had sent the value {sha1,rsa}. - * - * - If the negotiated key exchange algorithm is one of (DHE_DSS, DH_DSS), behave as if - * the client had sent the value {sha1,dsa}. - * - * - If the negotiated key exchange algorithm is one of (ECDH_ECDSA, ECDHE_ECDSA), - * behave as if the client had sent value {sha1,ecdsa}. - */ - if (this.mSupportedSignatureAlgorithms == null) - { - switch (mKeyExchange) - { - case KeyExchangeAlgorithm.DH_DSS: - case KeyExchangeAlgorithm.DHE_DSS: - case KeyExchangeAlgorithm.SRP_DSS: - { - this.mSupportedSignatureAlgorithms = TlsUtilities.GetDefaultDssSignatureAlgorithms(); - break; - } - - case KeyExchangeAlgorithm.ECDH_ECDSA: - case KeyExchangeAlgorithm.ECDHE_ECDSA: - { - this.mSupportedSignatureAlgorithms = TlsUtilities.GetDefaultECDsaSignatureAlgorithms(); - break; - } - - case KeyExchangeAlgorithm.DH_RSA: - case KeyExchangeAlgorithm.DHE_RSA: - case KeyExchangeAlgorithm.ECDH_RSA: - case KeyExchangeAlgorithm.ECDHE_RSA: - case KeyExchangeAlgorithm.RSA: - case KeyExchangeAlgorithm.RSA_PSK: - case KeyExchangeAlgorithm.SRP_RSA: - { - this.mSupportedSignatureAlgorithms = TlsUtilities.GetDefaultRsaSignatureAlgorithms(); - break; - } - - case KeyExchangeAlgorithm.DHE_PSK: - case KeyExchangeAlgorithm.ECDHE_PSK: - case KeyExchangeAlgorithm.PSK: - case KeyExchangeAlgorithm.SRP: - break; - - default: - throw new InvalidOperationException("unsupported key exchange algorithm"); - } - } - - } - else if (this.mSupportedSignatureAlgorithms != null) - { - throw new InvalidOperationException("supported_signature_algorithms not allowed for " + clientVersion); - } - } - - public abstract void SkipServerCredentials(); - - public virtual void ProcessServerCertificate(Certificate serverCertificate) - { - if (mSupportedSignatureAlgorithms == null) - { - /* - * TODO RFC 2246 7.4.2. Unless otherwise specified, the signing algorithm for the - * certificate must be the same as the algorithm for the certificate key. - */ - } - else - { - /* - * TODO RFC 5246 7.4.2. If the client provided a "signature_algorithms" extension, then - * all certificates provided by the server MUST be signed by a hash/signature algorithm - * pair that appears in that extension. - */ - } - } - - public virtual void ProcessServerCredentials(TlsCredentials serverCredentials) - { - ProcessServerCertificate(serverCredentials.Certificate); - } - - public virtual bool RequiresServerKeyExchange - { - get { return false; } - } - - public virtual byte[] GenerateServerKeyExchange() - { - if (RequiresServerKeyExchange) - throw new TlsFatalAlert(AlertDescription.internal_error); - - return null; - } - - public virtual void SkipServerKeyExchange() - { - if (RequiresServerKeyExchange) - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - - public virtual void ProcessServerKeyExchange(Stream input) - { - if (!RequiresServerKeyExchange) - { - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - } - - public abstract void ValidateCertificateRequest(CertificateRequest certificateRequest); - - public virtual void SkipClientCredentials() - { - } - - public abstract void ProcessClientCredentials(TlsCredentials clientCredentials); - - public virtual void ProcessClientCertificate(Certificate clientCertificate) - { - } - - public abstract void GenerateClientKeyExchange(Stream output); - - public virtual void ProcessClientKeyExchange(Stream input) - { - // Key exchange implementation MUST support client key exchange - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - public abstract byte[] GeneratePremasterSecret(); - } -} diff --git a/crypto/src/crypto/tls/AbstractTlsPeer.cs b/crypto/src/crypto/tls/AbstractTlsPeer.cs deleted file mode 100644 index e7bfc1742..000000000 --- a/crypto/src/crypto/tls/AbstractTlsPeer.cs +++ /dev/null @@ -1,75 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class AbstractTlsPeer - : TlsPeer - { - private volatile TlsCloseable mCloseHandle; - - /// <exception cref="IOException"/> - public virtual void Cancel() - { - TlsCloseable closeHandle = this.mCloseHandle; - if (null != closeHandle) - { - closeHandle.Close(); - } - } - - public virtual void NotifyCloseHandle(TlsCloseable closeHandle) - { - this.mCloseHandle = closeHandle; - } - - public virtual int GetHandshakeTimeoutMillis() - { - return 0; - } - - public virtual bool RequiresExtendedMasterSecret() - { - return false; - } - - public virtual bool ShouldUseGmtUnixTime() - { - /* - * draft-mathewson-no-gmtunixtime-00 2. For the reasons we discuss above, we recommend that - * TLS implementors MUST by default set the entire value the ClientHello.Random and - * ServerHello.Random fields, including gmt_unix_time, to a cryptographically random - * sequence. - */ - return false; - } - - public virtual void NotifySecureRenegotiation(bool secureRenegotiation) - { - if (!secureRenegotiation) - { - /* - * RFC 5746 3.4/3.6. In this case, some clients/servers may want to terminate the handshake instead - * of continuing; see Section 4.1/4.3 for discussion. - */ - throw new TlsFatalAlert(AlertDescription.handshake_failure); - } - } - - public abstract TlsCompression GetCompression(); - - public abstract TlsCipher GetCipher(); - - public virtual void NotifyAlertRaised(byte alertLevel, byte alertDescription, string message, Exception cause) - { - } - - public virtual void NotifyAlertReceived(byte alertLevel, byte alertDescription) - { - } - - public virtual void NotifyHandshakeComplete() - { - } - } -} diff --git a/crypto/src/crypto/tls/AbstractTlsServer.cs b/crypto/src/crypto/tls/AbstractTlsServer.cs deleted file mode 100644 index 52a79c9d8..000000000 --- a/crypto/src/crypto/tls/AbstractTlsServer.cs +++ /dev/null @@ -1,351 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class AbstractTlsServer - : AbstractTlsPeer, TlsServer - { - protected TlsCipherFactory mCipherFactory; - - protected TlsServerContext mContext; - - protected ProtocolVersion mClientVersion; - protected int[] mOfferedCipherSuites; - protected byte[] mOfferedCompressionMethods; - protected IDictionary mClientExtensions; - - protected bool mEncryptThenMacOffered; - protected short mMaxFragmentLengthOffered; - protected bool mTruncatedHMacOffered; - protected IList mSupportedSignatureAlgorithms; - protected bool mEccCipherSuitesOffered; - protected int[] mNamedCurves; - protected byte[] mClientECPointFormats, mServerECPointFormats; - - protected ProtocolVersion mServerVersion; - protected int mSelectedCipherSuite; - protected byte mSelectedCompressionMethod; - protected IDictionary mServerExtensions; - - public AbstractTlsServer() - : this(new DefaultTlsCipherFactory()) - { - } - - public AbstractTlsServer(TlsCipherFactory cipherFactory) - { - this.mCipherFactory = cipherFactory; - } - - protected virtual bool AllowEncryptThenMac - { - get { return true; } - } - - protected virtual bool AllowTruncatedHMac - { - get { return false; } - } - - protected virtual IDictionary CheckServerExtensions() - { - return this.mServerExtensions = TlsExtensionsUtilities.EnsureExtensionsInitialised(this.mServerExtensions); - } - - protected abstract int[] GetCipherSuites(); - - protected byte[] GetCompressionMethods() - { - return new byte[] { CompressionMethod.cls_null }; - } - - protected virtual ProtocolVersion MaximumVersion - { - get { return ProtocolVersion.TLSv11; } - } - - protected virtual ProtocolVersion MinimumVersion - { - get { return ProtocolVersion.TLSv10; } - } - - protected virtual bool SupportsClientEccCapabilities(int[] namedCurves, byte[] ecPointFormats) - { - // NOTE: BC supports all the current set of point formats so we don't check them here - - if (namedCurves == null) - { - /* - * RFC 4492 4. A client that proposes ECC cipher suites may choose not to include these - * extensions. In this case, the server is free to choose any one of the elliptic curves - * or point formats [...]. - */ - return TlsEccUtilities.HasAnySupportedNamedCurves(); - } - - for (int i = 0; i < namedCurves.Length; ++i) - { - int namedCurve = namedCurves[i]; - if (NamedCurve.IsValid(namedCurve) - && (!NamedCurve.RefersToASpecificNamedCurve(namedCurve) || TlsEccUtilities.IsSupportedNamedCurve(namedCurve))) - { - return true; - } - } - - return false; - } - - public virtual void Init(TlsServerContext context) - { - this.mContext = context; - } - - public virtual void NotifyClientVersion(ProtocolVersion clientVersion) - { - this.mClientVersion = clientVersion; - } - - public virtual void NotifyFallback(bool isFallback) - { - /* - * RFC 7507 3. If TLS_FALLBACK_SCSV appears in ClientHello.cipher_suites and the highest - * protocol version supported by the server is higher than the version indicated in - * ClientHello.client_version, the server MUST respond with a fatal inappropriate_fallback - * alert [..]. - */ - if (isFallback && MaximumVersion.IsLaterVersionOf(mClientVersion)) - throw new TlsFatalAlert(AlertDescription.inappropriate_fallback); - } - - public virtual void NotifyOfferedCipherSuites(int[] offeredCipherSuites) - { - this.mOfferedCipherSuites = offeredCipherSuites; - this.mEccCipherSuitesOffered = TlsEccUtilities.ContainsEccCipherSuites(this.mOfferedCipherSuites); - } - - public virtual void NotifyOfferedCompressionMethods(byte[] offeredCompressionMethods) - { - this.mOfferedCompressionMethods = offeredCompressionMethods; - } - - public virtual void ProcessClientExtensions(IDictionary clientExtensions) - { - this.mClientExtensions = clientExtensions; - - if (clientExtensions != null) - { - this.mEncryptThenMacOffered = TlsExtensionsUtilities.HasEncryptThenMacExtension(clientExtensions); - - this.mMaxFragmentLengthOffered = TlsExtensionsUtilities.GetMaxFragmentLengthExtension(clientExtensions); - if (mMaxFragmentLengthOffered >= 0 && !MaxFragmentLength.IsValid((byte)mMaxFragmentLengthOffered)) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - - this.mTruncatedHMacOffered = TlsExtensionsUtilities.HasTruncatedHMacExtension(clientExtensions); - - this.mSupportedSignatureAlgorithms = TlsUtilities.GetSignatureAlgorithmsExtension(clientExtensions); - if (this.mSupportedSignatureAlgorithms != null) - { - /* - * RFC 5246 7.4.1.4.1. Note: this extension is not meaningful for TLS versions prior - * to 1.2. Clients MUST NOT offer it if they are offering prior versions. - */ - if (!TlsUtilities.IsSignatureAlgorithmsExtensionAllowed(mClientVersion)) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - - this.mNamedCurves = TlsEccUtilities.GetSupportedEllipticCurvesExtension(clientExtensions); - this.mClientECPointFormats = TlsEccUtilities.GetSupportedPointFormatsExtension(clientExtensions); - } - - /* - * RFC 4429 4. The client MUST NOT include these extensions in the ClientHello message if it - * does not propose any ECC cipher suites. - * - * NOTE: This was overly strict as there may be ECC cipher suites that we don't recognize. - * Also, draft-ietf-tls-negotiated-ff-dhe will be overloading the 'elliptic_curves' - * extension to explicitly allow FFDHE (i.e. non-ECC) groups. - */ - //if (!this.mEccCipherSuitesOffered && (this.mNamedCurves != null || this.mClientECPointFormats != null)) - // throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - - public virtual ProtocolVersion GetServerVersion() - { - if (MinimumVersion.IsEqualOrEarlierVersionOf(mClientVersion)) - { - ProtocolVersion maximumVersion = MaximumVersion; - if (mClientVersion.IsEqualOrEarlierVersionOf(maximumVersion)) - { - return mServerVersion = mClientVersion; - } - if (mClientVersion.IsLaterVersionOf(maximumVersion)) - { - return mServerVersion = maximumVersion; - } - } - throw new TlsFatalAlert(AlertDescription.protocol_version); - } - - public virtual int GetSelectedCipherSuite() - { - /* - * RFC 5246 7.4.3. In order to negotiate correctly, the server MUST check any candidate - * cipher suites against the "signature_algorithms" extension before selecting them. This is - * somewhat inelegant but is a compromise designed to minimize changes to the original - * cipher suite design. - */ - IList sigAlgs = TlsUtilities.GetUsableSignatureAlgorithms(this.mSupportedSignatureAlgorithms); - - /* - * RFC 4429 5.1. A server that receives a ClientHello containing one or both of these - * extensions MUST use the client's enumerated capabilities to guide its selection of an - * appropriate cipher suite. One of the proposed ECC cipher suites must be negotiated only - * if the server can successfully complete the handshake while using the curves and point - * formats supported by the client [...]. - */ - bool eccCipherSuitesEnabled = SupportsClientEccCapabilities(this.mNamedCurves, this.mClientECPointFormats); - - int[] cipherSuites = GetCipherSuites(); - for (int i = 0; i < cipherSuites.Length; ++i) - { - int cipherSuite = cipherSuites[i]; - - if (Arrays.Contains(this.mOfferedCipherSuites, cipherSuite) - && (eccCipherSuitesEnabled || !TlsEccUtilities.IsEccCipherSuite(cipherSuite)) - && TlsUtilities.IsValidCipherSuiteForVersion(cipherSuite, mServerVersion) - && TlsUtilities.IsValidCipherSuiteForSignatureAlgorithms(cipherSuite, sigAlgs)) - { - return this.mSelectedCipherSuite = cipherSuite; - } - } - throw new TlsFatalAlert(AlertDescription.handshake_failure); - } - - public virtual byte GetSelectedCompressionMethod() - { - byte[] compressionMethods = GetCompressionMethods(); - for (int i = 0; i < compressionMethods.Length; ++i) - { - if (Arrays.Contains(mOfferedCompressionMethods, compressionMethods[i])) - { - return this.mSelectedCompressionMethod = compressionMethods[i]; - } - } - throw new TlsFatalAlert(AlertDescription.handshake_failure); - } - - // IDictionary is (Int32 -> byte[]) - public virtual IDictionary GetServerExtensions() - { - if (this.mEncryptThenMacOffered && AllowEncryptThenMac) - { - /* - * RFC 7366 3. If a server receives an encrypt-then-MAC request extension from a client - * and then selects a stream or Authenticated Encryption with Associated Data (AEAD) - * ciphersuite, it MUST NOT send an encrypt-then-MAC response extension back to the - * client. - */ - if (TlsUtilities.IsBlockCipherSuite(this.mSelectedCipherSuite)) - { - TlsExtensionsUtilities.AddEncryptThenMacExtension(CheckServerExtensions()); - } - } - - if (this.mMaxFragmentLengthOffered >= 0 - && TlsUtilities.IsValidUint8(mMaxFragmentLengthOffered) - && MaxFragmentLength.IsValid((byte)mMaxFragmentLengthOffered)) - { - TlsExtensionsUtilities.AddMaxFragmentLengthExtension(CheckServerExtensions(), (byte)mMaxFragmentLengthOffered); - } - - if (this.mTruncatedHMacOffered && AllowTruncatedHMac) - { - TlsExtensionsUtilities.AddTruncatedHMacExtension(CheckServerExtensions()); - } - - if (this.mClientECPointFormats != null && TlsEccUtilities.IsEccCipherSuite(this.mSelectedCipherSuite)) - { - /* - * RFC 4492 5.2. A server that selects an ECC cipher suite in response to a ClientHello - * message including a Supported Point Formats Extension appends this extension (along - * with others) to its ServerHello message, enumerating the point formats it can parse. - */ - this.mServerECPointFormats = new byte[]{ ECPointFormat.uncompressed, - ECPointFormat.ansiX962_compressed_prime, ECPointFormat.ansiX962_compressed_char2, }; - - TlsEccUtilities.AddSupportedPointFormatsExtension(CheckServerExtensions(), mServerECPointFormats); - } - - return mServerExtensions; - } - - public virtual IList GetServerSupplementalData() - { - return null; - } - - public abstract TlsCredentials GetCredentials(); - - public virtual CertificateStatus GetCertificateStatus() - { - return null; - } - - public abstract TlsKeyExchange GetKeyExchange(); - - public virtual CertificateRequest GetCertificateRequest() - { - return null; - } - - public virtual void ProcessClientSupplementalData(IList clientSupplementalData) - { - if (clientSupplementalData != null) - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - - public virtual void NotifyClientCertificate(Certificate clientCertificate) - { - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - public override TlsCompression GetCompression() - { - switch (mSelectedCompressionMethod) - { - case CompressionMethod.cls_null: - return new TlsNullCompression(); - - default: - /* - * Note: internal error here; we selected the compression method, so if we now can't - * produce an implementation, we shouldn't have chosen it! - */ - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } - - public override TlsCipher GetCipher() - { - int encryptionAlgorithm = TlsUtilities.GetEncryptionAlgorithm(mSelectedCipherSuite); - int macAlgorithm = TlsUtilities.GetMacAlgorithm(mSelectedCipherSuite); - - return mCipherFactory.CreateCipher(mContext, encryptionAlgorithm, macAlgorithm); - } - - public virtual NewSessionTicket GetNewSessionTicket() - { - /* - * RFC 5077 3.3. If the server determines that it does not want to include a ticket after it - * has included the SessionTicket extension in the ServerHello, then it sends a zero-length - * ticket in the NewSessionTicket handshake message. - */ - return new NewSessionTicket(0L, TlsUtilities.EmptyBytes); - } - } -} diff --git a/crypto/src/crypto/tls/AbstractTlsSigner.cs b/crypto/src/crypto/tls/AbstractTlsSigner.cs deleted file mode 100644 index 1f4aabf74..000000000 --- a/crypto/src/crypto/tls/AbstractTlsSigner.cs +++ /dev/null @@ -1,50 +0,0 @@ -using System; - -using Org.BouncyCastle.Crypto; -using Org.BouncyCastle.Crypto.Parameters; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class AbstractTlsSigner - : TlsSigner - { - protected TlsContext mContext; - - public virtual void Init(TlsContext context) - { - this.mContext = context; - } - - public virtual byte[] GenerateRawSignature(AsymmetricKeyParameter privateKey, byte[] md5AndSha1) - { - return GenerateRawSignature(null, privateKey, md5AndSha1); - } - - public abstract byte[] GenerateRawSignature(SignatureAndHashAlgorithm algorithm, - AsymmetricKeyParameter privateKey, byte[] hash); - - public virtual bool VerifyRawSignature(byte[] sigBytes, AsymmetricKeyParameter publicKey, byte[] md5AndSha1) - { - return VerifyRawSignature(null, sigBytes, publicKey, md5AndSha1); - } - - public abstract bool VerifyRawSignature(SignatureAndHashAlgorithm algorithm, byte[] sigBytes, - AsymmetricKeyParameter publicKey, byte[] hash); - - public virtual ISigner CreateSigner(AsymmetricKeyParameter privateKey) - { - return CreateSigner(null, privateKey); - } - - public abstract ISigner CreateSigner(SignatureAndHashAlgorithm algorithm, AsymmetricKeyParameter privateKey); - - public virtual ISigner CreateVerifyer(AsymmetricKeyParameter publicKey) - { - return CreateVerifyer(null, publicKey); - } - - public abstract ISigner CreateVerifyer(SignatureAndHashAlgorithm algorithm, AsymmetricKeyParameter publicKey); - - public abstract bool IsValidPublicKey(AsymmetricKeyParameter publicKey); - } -} diff --git a/crypto/src/crypto/tls/AbstractTlsSignerCredentials.cs b/crypto/src/crypto/tls/AbstractTlsSignerCredentials.cs deleted file mode 100644 index 886c46c6e..000000000 --- a/crypto/src/crypto/tls/AbstractTlsSignerCredentials.cs +++ /dev/null @@ -1,20 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class AbstractTlsSignerCredentials - : AbstractTlsCredentials, TlsSignerCredentials - { - /// <exception cref="IOException"></exception> - public abstract byte[] GenerateCertificateSignature(byte[] hash); - - public virtual SignatureAndHashAlgorithm SignatureAndHashAlgorithm - { - get - { - throw new InvalidOperationException("TlsSignerCredentials implementation does not support (D)TLS 1.2+"); - } - } - } -} diff --git a/crypto/src/crypto/tls/AlertDescription.cs b/crypto/src/crypto/tls/AlertDescription.cs deleted file mode 100644 index 4e2464b50..000000000 --- a/crypto/src/crypto/tls/AlertDescription.cs +++ /dev/null @@ -1,304 +0,0 @@ -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary> - /// RFC 5246 7.2 - /// </summary> - public abstract class AlertDescription - { - /** - * This message notifies the recipient that the sender will not send any more messages on this - * connection. Note that as of TLS 1.1, failure to properly close a connection no longer - * requires that a session not be resumed. This is a change from TLS 1.0 ("The session becomes - * unresumable if any connection is terminated without proper close_notify messages with level - * equal to warning.") to conform with widespread implementation practice. - */ - public const byte close_notify = 0; - - /** - * An inappropriate message was received. This alert is always fatal and should never be - * observed in communication between proper implementations. - */ - public const byte unexpected_message = 10; - - /** - * This alert is returned if a record is received with an incorrect MAC. This alert also MUST be - * returned if an alert is sent because a TLSCiphertext decrypted in an invalid way: either it - * wasn't an even multiple of the block length, or its padding values, when checked, weren't - * correct. This message is always fatal and should never be observed in communication between - * proper implementations (except when messages were corrupted in the network). - */ - public const byte bad_record_mac = 20; - - /** - * This alert was used in some earlier versions of TLS, and may have permitted certain attacks - * against the CBC mode [CBCATT]. It MUST NOT be sent by compliant implementations. - */ - public const byte decryption_failed = 21; - - /** - * A TLSCiphertext record was received that had a length more than 2^14+2048 bytes, or a record - * decrypted to a TLSCompressed record with more than 2^14+1024 bytes. This message is always - * fatal and should never be observed in communication between proper implementations (except - * when messages were corrupted in the network). - */ - public const byte record_overflow = 22; - - /** - * The decompression function received improper input (e.g., data that would expand to excessive - * length). This message is always fatal and should never be observed in communication between - * proper implementations. - */ - public const byte decompression_failure = 30; - - /** - * Reception of a handshake_failure alert message indicates that the sender was unable to - * negotiate an acceptable set of security parameters given the options available. This is a - * fatal error. - */ - public const byte handshake_failure = 40; - - /** - * This alert was used in SSLv3 but not any version of TLS. It MUST NOT be sent by compliant - * implementations. - */ - public const byte no_certificate = 41; - - /** - * A certificate was corrupt, contained signatures that did not verify correctly, etc. - */ - public const byte bad_certificate = 42; - - /** - * A certificate was of an unsupported type. - */ - public const byte unsupported_certificate = 43; - - /** - * A certificate was revoked by its signer. - */ - public const byte certificate_revoked = 44; - - /** - * A certificate has expired or is not currently valid. - */ - public const byte certificate_expired = 45; - - /** - * Some other (unspecified) issue arose in processing the certificate, rendering it - * unacceptable. - */ - public const byte certificate_unknown = 46; - - /** - * A field in the handshake was out of range or inconsistent with other fields. This message is - * always fatal. - */ - public const byte illegal_parameter = 47; - - /** - * A valid certificate chain or partial chain was received, but the certificate was not accepted - * because the CA certificate could not be located or couldn't be matched with a known, trusted - * CA. This message is always fatal. - */ - public const byte unknown_ca = 48; - - /** - * A valid certificate was received, but when access control was applied, the sender decided not - * to proceed with negotiation. This message is always fatal. - */ - public const byte access_denied = 49; - - /** - * A message could not be decoded because some field was out of the specified range or the - * length of the message was incorrect. This message is always fatal and should never be - * observed in communication between proper implementations (except when messages were corrupted - * in the network). - */ - public const byte decode_error = 50; - - /** - * A handshake cryptographic operation failed, including being unable to correctly verify a - * signature or validate a Finished message. This message is always fatal. - */ - public const byte decrypt_error = 51; - - /** - * This alert was used in some earlier versions of TLS. It MUST NOT be sent by compliant - * implementations. - */ - public const byte export_restriction = 60; - - /** - * The protocol version the client has attempted to negotiate is recognized but not supported. - * (For example, old protocol versions might be avoided for security reasons.) This message is - * always fatal. - */ - public const byte protocol_version = 70; - - /** - * Returned instead of handshake_failure when a negotiation has failed specifically because the - * server requires ciphers more secure than those supported by the client. This message is - * always fatal. - */ - public const byte insufficient_security = 71; - - /** - * An internal error unrelated to the peer or the correctness of the protocol (such as a memory - * allocation failure) makes it impossible to continue. This message is always fatal. - */ - public const byte internal_error = 80; - - /** - * This handshake is being canceled for some reason unrelated to a protocol failure. If the user - * cancels an operation after the handshake is complete, just closing the connection by sending - * a close_notify is more appropriate. This alert should be followed by a close_notify. This - * message is generally a warning. - */ - public const byte user_canceled = 90; - - /** - * Sent by the client in response to a hello request or by the server in response to a client - * hello after initial handshaking. Either of these would normally lead to renegotiation; when - * that is not appropriate, the recipient should respond with this alert. At that point, the - * original requester can decide whether to proceed with the connection. One case where this - * would be appropriate is where a server has spawned a process to satisfy a request; the - * process might receive security parameters (key length, authentication, etc.) at startup, and - * it might be difficult to communicate changes to these parameters after that point. This - * message is always a warning. - */ - public const byte no_renegotiation = 100; - - /** - * Sent by clients that receive an extended server hello containing an extension that they did - * not put in the corresponding client hello. This message is always fatal. - */ - public const byte unsupported_extension = 110; - - /* - * RFC 3546 - */ - - /** - * This alert is sent by servers who are unable to retrieve a certificate chain from the URL - * supplied by the client (see Section 3.3). This message MAY be fatal - for example if client - * authentication is required by the server for the handshake to continue and the server is - * unable to retrieve the certificate chain, it may send a fatal alert. - */ - public const byte certificate_unobtainable = 111; - - /** - * This alert is sent by servers that receive a server_name extension request, but do not - * recognize the server name. This message MAY be fatal. - */ - public const byte unrecognized_name = 112; - - /** - * This alert is sent by clients that receive an invalid certificate status response (see - * Section 3.6). This message is always fatal. - */ - public const byte bad_certificate_status_response = 113; - - /** - * This alert is sent by servers when a certificate hash does not match a client provided - * certificate_hash. This message is always fatal. - */ - public const byte bad_certificate_hash_value = 114; - - /* - * RFC 4279 - */ - - /** - * If the server does not recognize the PSK identity, it MAY respond with an - * "unknown_psk_identity" alert message. - */ - public const byte unknown_psk_identity = 115; - - /* - * RFC 7507 - */ - - /** - * If TLS_FALLBACK_SCSV appears in ClientHello.cipher_suites and the highest protocol version - * supported by the server is higher than the version indicated in ClientHello.client_version, - * the server MUST respond with a fatal inappropriate_fallback alert [..]. - */ - public const byte inappropriate_fallback = 86; - - public static string GetName(byte alertDescription) - { - switch (alertDescription) - { - case close_notify: - return "close_notify"; - case unexpected_message: - return "unexpected_message"; - case bad_record_mac: - return "bad_record_mac"; - case decryption_failed: - return "decryption_failed"; - case record_overflow: - return "record_overflow"; - case decompression_failure: - return "decompression_failure"; - case handshake_failure: - return "handshake_failure"; - case no_certificate: - return "no_certificate"; - case bad_certificate: - return "bad_certificate"; - case unsupported_certificate: - return "unsupported_certificate"; - case certificate_revoked: - return "certificate_revoked"; - case certificate_expired: - return "certificate_expired"; - case certificate_unknown: - return "certificate_unknown"; - case illegal_parameter: - return "illegal_parameter"; - case unknown_ca: - return "unknown_ca"; - case access_denied: - return "access_denied"; - case decode_error: - return "decode_error"; - case decrypt_error: - return "decrypt_error"; - case export_restriction: - return "export_restriction"; - case protocol_version: - return "protocol_version"; - case insufficient_security: - return "insufficient_security"; - case internal_error: - return "internal_error"; - case user_canceled: - return "user_canceled"; - case no_renegotiation: - return "no_renegotiation"; - case unsupported_extension: - return "unsupported_extension"; - case certificate_unobtainable: - return "certificate_unobtainable"; - case unrecognized_name: - return "unrecognized_name"; - case bad_certificate_status_response: - return "bad_certificate_status_response"; - case bad_certificate_hash_value: - return "bad_certificate_hash_value"; - case unknown_psk_identity: - return "unknown_psk_identity"; - case inappropriate_fallback: - return "inappropriate_fallback"; - default: - return "UNKNOWN"; - } - } - - public static string GetText(byte alertDescription) - { - return GetName(alertDescription) + "(" + alertDescription + ")"; - } - } -} diff --git a/crypto/src/crypto/tls/AlertLevel.cs b/crypto/src/crypto/tls/AlertLevel.cs deleted file mode 100644 index 9461a0b58..000000000 --- a/crypto/src/crypto/tls/AlertLevel.cs +++ /dev/null @@ -1,29 +0,0 @@ -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary> - /// RFC 5246 7.2 - /// </summary> - public abstract class AlertLevel - { - public const byte warning = 1; - public const byte fatal = 2; - - public static string GetName(byte alertDescription) - { - switch (alertDescription) - { - case warning: - return "warning"; - case fatal: - return "fatal"; - default: - return "UNKNOWN"; - } - } - - public static string GetText(byte alertDescription) - { - return GetName(alertDescription) + "(" + alertDescription + ")"; - } - } -} diff --git a/crypto/src/crypto/tls/BasicTlsPskIdentity.cs b/crypto/src/crypto/tls/BasicTlsPskIdentity.cs deleted file mode 100644 index 7a3bbe72e..000000000 --- a/crypto/src/crypto/tls/BasicTlsPskIdentity.cs +++ /dev/null @@ -1,43 +0,0 @@ -using System; - -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class BasicTlsPskIdentity - : TlsPskIdentity - { - protected byte[] mIdentity; - protected byte[] mPsk; - - public BasicTlsPskIdentity(byte[] identity, byte[] psk) - { - this.mIdentity = Arrays.Clone(identity); - this.mPsk = Arrays.Clone(psk); - } - - public BasicTlsPskIdentity(string identity, byte[] psk) - { - this.mIdentity = Strings.ToUtf8ByteArray(identity); - this.mPsk = Arrays.Clone(psk); - } - - public virtual void SkipIdentityHint() - { - } - - public virtual void NotifyIdentityHint(byte[] psk_identity_hint) - { - } - - public virtual byte[] GetPskIdentity() - { - return mIdentity; - } - - public virtual byte[] GetPsk() - { - return Arrays.Clone(mPsk); - } - } -} diff --git a/crypto/src/crypto/tls/BulkCipherAlgorithm.cs b/crypto/src/crypto/tls/BulkCipherAlgorithm.cs deleted file mode 100644 index 07ff8dc07..000000000 --- a/crypto/src/crypto/tls/BulkCipherAlgorithm.cs +++ /dev/null @@ -1,25 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary>RFC 2246</summary> - /// <remarks> - /// Note that the values here are implementation-specific and arbitrary. It is recommended not to - /// depend on the particular values (e.g. serialization). - /// </remarks> - public abstract class BulkCipherAlgorithm - { - public const int cls_null = 0; - public const int rc4 = 1; - public const int rc2 = 2; - public const int des = 3; - public const int cls_3des = 4; - public const int des40 = 5; - - /* - * RFC 4346 - */ - public const int aes = 6; - public const int idea = 7; - } -} diff --git a/crypto/src/crypto/tls/ByteQueue.cs b/crypto/src/crypto/tls/ByteQueue.cs deleted file mode 100644 index b4df6850e..000000000 --- a/crypto/src/crypto/tls/ByteQueue.cs +++ /dev/null @@ -1,211 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <remarks> - /// A queue for bytes. - /// <p> - /// This file could be more optimized. - /// </p> - /// </remarks> - public class ByteQueue - { - /// <returns>The smallest number which can be written as 2^x which is bigger than i.</returns> - public static int NextTwoPow( - int i) - { - /* - * This code is based of a lot of code I found on the Internet - * which mostly referenced a book called "Hacking delight". - * - */ - i |= (i >> 1); - i |= (i >> 2); - i |= (i >> 4); - i |= (i >> 8); - i |= (i >> 16); - return i + 1; - } - - /** - * The initial size for our buffer. - */ - private const int DefaultCapacity = 1024; - - /** - * The buffer where we store our data. - */ - private byte[] databuf; - - /** - * How many bytes at the beginning of the buffer are skipped. - */ - private int skipped = 0; - - /** - * How many bytes in the buffer are valid data. - */ - private int available = 0; - - private bool readOnlyBuf = false; - - public ByteQueue() - : this(DefaultCapacity) - { - } - - public ByteQueue(int capacity) - { - this.databuf = capacity == 0 ? TlsUtilities.EmptyBytes : new byte[capacity]; - } - - public ByteQueue(byte[] buf, int off, int len) - { - this.databuf = buf; - this.skipped = off; - this.available = len; - this.readOnlyBuf = true; - } - - /// <summary>Add some data to our buffer.</summary> - /// <param name="data">A byte-array to read data from.</param> - /// <param name="offset">How many bytes to skip at the beginning of the array.</param> - /// <param name="len">How many bytes to read from the array.</param> - public void AddData( - byte[] data, - int offset, - int len) - { - if (readOnlyBuf) - throw new InvalidOperationException("Cannot add data to read-only buffer"); - - if ((skipped + available + len) > databuf.Length) - { - int desiredSize = ByteQueue.NextTwoPow(available + len); - if (desiredSize > databuf.Length) - { - byte[] tmp = new byte[desiredSize]; - Array.Copy(databuf, skipped, tmp, 0, available); - databuf = tmp; - } - else - { - Array.Copy(databuf, skipped, databuf, 0, available); - } - skipped = 0; - } - - Array.Copy(data, offset, databuf, skipped + available, len); - available += len; - } - - /// <summary>The number of bytes which are available in this buffer.</summary> - public int Available - { - get { return available; } - } - - /// <summary>Copy some bytes from the beginning of the data to the provided <c cref="Stream">Stream</c>.</summary> - /// <param name="output">The <c cref="Stream">Stream</c> to copy the bytes to.</param> - /// <param name="length">How many bytes to copy.</param> - /// <exception cref="InvalidOperationException">If insufficient data is available.</exception> - /// <exception cref="IOException">If there is a problem copying the data.</exception> - public void CopyTo(Stream output, int length) - { - if (length > available) - throw new InvalidOperationException("Cannot copy " + length + " bytes, only got " + available); - - output.Write(databuf, skipped, length); - } - - /// <summary>Read data from the buffer.</summary> - /// <param name="buf">The buffer where the read data will be copied to.</param> - /// <param name="offset">How many bytes to skip at the beginning of buf.</param> - /// <param name="len">How many bytes to read at all.</param> - /// <param name="skip">How many bytes from our data to skip.</param> - public void Read( - byte[] buf, - int offset, - int len, - int skip) - { - if ((buf.Length - offset) < len) - { - throw new ArgumentException("Buffer size of " + buf.Length + " is too small for a read of " + len + " bytes"); - } - if ((available - skip) < len) - { - throw new InvalidOperationException("Not enough data to read"); - } - Array.Copy(databuf, skipped + skip, buf, offset, len); - } - - /// <summary>Return a <c cref="MemoryStream">MemoryStream</c> over some bytes at the beginning of the data.</summary> - /// <param name="length">How many bytes will be readable.</param> - /// <returns>A <c cref="MemoryStream">MemoryStream</c> over the data.</returns> - /// <exception cref="InvalidOperationException">If insufficient data is available.</exception> - public MemoryStream ReadFrom(int length) - { - if (length > available) - throw new InvalidOperationException("Cannot read " + length + " bytes, only got " + available); - - int position = skipped; - - available -= length; - skipped += length; - - return new MemoryStream(databuf, position, length, false); - } - - /// <summary>Remove some bytes from our data from the beginning.</summary> - /// <param name="i">How many bytes to remove.</param> - public void RemoveData( - int i) - { - if (i > available) - { - throw new InvalidOperationException("Cannot remove " + i + " bytes, only got " + available); - } - - /* - * Skip the data. - */ - available -= i; - skipped += i; - } - - public void RemoveData(byte[] buf, int off, int len, int skip) - { - Read(buf, off, len, skip); - RemoveData(skip + len); - } - - public byte[] RemoveData(int len, int skip) - { - byte[] buf = new byte[len]; - RemoveData(buf, 0, len, skip); - return buf; - } - - public void Shrink() - { - if (available == 0) - { - databuf = TlsUtilities.EmptyBytes; - skipped = 0; - } - else - { - int desiredSize = ByteQueue.NextTwoPow(available); - if (desiredSize < databuf.Length) - { - byte[] tmp = new byte[desiredSize]; - Array.Copy(databuf, skipped, tmp, 0, available); - databuf = tmp; - skipped = 0; - } - } - } - } -} diff --git a/crypto/src/crypto/tls/ByteQueueStream.cs b/crypto/src/crypto/tls/ByteQueueStream.cs deleted file mode 100644 index 249e6099b..000000000 --- a/crypto/src/crypto/tls/ByteQueueStream.cs +++ /dev/null @@ -1,110 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class ByteQueueStream - : Stream - { - private readonly ByteQueue buffer; - - public ByteQueueStream() - { - this.buffer = new ByteQueue(); - } - - public virtual int Available - { - get { return buffer.Available; } - } - - public override bool CanRead - { - get { return true; } - } - - public override bool CanSeek - { - get { return false; } - } - - public override bool CanWrite - { - get { return true; } - } - - public override void Flush() - { - } - - public override long Length - { - get { throw new NotSupportedException(); } - } - - public virtual int Peek(byte[] buf) - { - int bytesToRead = System.Math.Min(buffer.Available, buf.Length); - buffer.Read(buf, 0, bytesToRead, 0); - return bytesToRead; - } - - public override long Position - { - get { throw new NotSupportedException(); } - set { throw new NotSupportedException(); } - } - - public virtual int Read(byte[] buf) - { - return Read(buf, 0, buf.Length); - } - - public override int Read(byte[] buf, int off, int len) - { - int bytesToRead = System.Math.Min(buffer.Available, len); - buffer.RemoveData(buf, off, bytesToRead, 0); - return bytesToRead; - } - - public override int ReadByte() - { - if (buffer.Available == 0) - return -1; - - return buffer.RemoveData(1, 0)[0] & 0xFF; - } - - public override long Seek(long offset, SeekOrigin origin) - { - throw new NotSupportedException(); - } - - public override void SetLength(long value) - { - throw new NotSupportedException(); - } - - public virtual int Skip(int n) - { - int bytesToSkip = System.Math.Min(buffer.Available, n); - buffer.RemoveData(bytesToSkip); - return bytesToSkip; - } - - public virtual void Write(byte[] buf) - { - buffer.AddData(buf, 0, buf.Length); - } - - public override void Write(byte[] buf, int off, int len) - { - buffer.AddData(buf, off, len); - } - - public override void WriteByte(byte b) - { - buffer.AddData(new byte[]{ b }, 0, 1); - } - } -} diff --git a/crypto/src/crypto/tls/CertChainType.cs b/crypto/src/crypto/tls/CertChainType.cs deleted file mode 100644 index cbb183441..000000000 --- a/crypto/src/crypto/tls/CertChainType.cs +++ /dev/null @@ -1,18 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /* - * RFC 3546 3.3. - */ - public abstract class CertChainType - { - public const byte individual_certs = 0; - public const byte pkipath = 1; - - public static bool IsValid(byte certChainType) - { - return certChainType >= individual_certs && certChainType <= pkipath; - } - } -} diff --git a/crypto/src/crypto/tls/Certificate.cs b/crypto/src/crypto/tls/Certificate.cs deleted file mode 100644 index e0479997a..000000000 --- a/crypto/src/crypto/tls/Certificate.cs +++ /dev/null @@ -1,136 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Asn1; -using Org.BouncyCastle.Asn1.X509; -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /** - * Parsing and encoding of a <i>Certificate</i> struct from RFC 4346. - * <p/> - * <pre> - * opaque ASN.1Cert<2^24-1>; - * - * struct { - * ASN.1Cert certificate_list<0..2^24-1>; - * } Certificate; - * </pre> - * - * @see Org.BouncyCastle.Asn1.X509.X509CertificateStructure - */ - public class Certificate - { - public static readonly Certificate EmptyChain = new Certificate(new X509CertificateStructure[0]); - - /** - * The certificates. - */ - protected readonly X509CertificateStructure[] mCertificateList; - - public Certificate(X509CertificateStructure[] certificateList) - { - if (certificateList == null) - throw new ArgumentNullException("certificateList"); - - this.mCertificateList = certificateList; - } - - /** - * @return an array of {@link org.bouncycastle.asn1.x509.Certificate} representing a certificate - * chain. - */ - public virtual X509CertificateStructure[] GetCertificateList() - { - return CloneCertificateList(); - } - - public virtual X509CertificateStructure GetCertificateAt(int index) - { - return mCertificateList[index]; - } - - public virtual int Length - { - get { return mCertificateList.Length; } - } - - /** - * @return <code>true</code> if this certificate chain contains no certificates, or - * <code>false</code> otherwise. - */ - public virtual bool IsEmpty - { - get { return mCertificateList.Length == 0; } - } - - /** - * Encode this {@link Certificate} to a {@link Stream}. - * - * @param output the {@link Stream} to encode to. - * @throws IOException - */ - public virtual void Encode(Stream output) - { - IList derEncodings = Platform.CreateArrayList(mCertificateList.Length); - - int totalLength = 0; - foreach (Asn1Encodable asn1Cert in mCertificateList) - { - byte[] derEncoding = asn1Cert.GetEncoded(Asn1Encodable.Der); - derEncodings.Add(derEncoding); - totalLength += derEncoding.Length + 3; - } - - TlsUtilities.CheckUint24(totalLength); - TlsUtilities.WriteUint24(totalLength, output); - - foreach (byte[] derEncoding in derEncodings) - { - TlsUtilities.WriteOpaque24(derEncoding, output); - } - } - - /** - * Parse a {@link Certificate} from a {@link Stream}. - * - * @param input the {@link Stream} to parse from. - * @return a {@link Certificate} object. - * @throws IOException - */ - public static Certificate Parse(Stream input) - { - int totalLength = TlsUtilities.ReadUint24(input); - if (totalLength == 0) - { - return EmptyChain; - } - - byte[] certListData = TlsUtilities.ReadFully(totalLength, input); - - MemoryStream buf = new MemoryStream(certListData, false); - - IList certificate_list = Platform.CreateArrayList(); - while (buf.Position < buf.Length) - { - byte[] berEncoding = TlsUtilities.ReadOpaque24(buf); - Asn1Object asn1Cert = TlsUtilities.ReadAsn1Object(berEncoding); - certificate_list.Add(X509CertificateStructure.GetInstance(asn1Cert)); - } - - X509CertificateStructure[] certificateList = new X509CertificateStructure[certificate_list.Count]; - for (int i = 0; i < certificate_list.Count; ++i) - { - certificateList[i] = (X509CertificateStructure)certificate_list[i]; - } - return new Certificate(certificateList); - } - - protected virtual X509CertificateStructure[] CloneCertificateList() - { - return (X509CertificateStructure[])mCertificateList.Clone(); - } - } -} diff --git a/crypto/src/crypto/tls/CertificateRequest.cs b/crypto/src/crypto/tls/CertificateRequest.cs deleted file mode 100644 index f3dcb3bbd..000000000 --- a/crypto/src/crypto/tls/CertificateRequest.cs +++ /dev/null @@ -1,156 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Asn1; -using Org.BouncyCastle.Asn1.X509; -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /** - * Parsing and encoding of a <i>CertificateRequest</i> struct from RFC 4346. - * <p/> - * <pre> - * struct { - * ClientCertificateType certificate_types<1..2^8-1>; - * DistinguishedName certificate_authorities<3..2^16-1> - * } CertificateRequest; - * </pre> - * - * @see ClientCertificateType - * @see X509Name - */ - public class CertificateRequest - { - protected readonly byte[] mCertificateTypes; - protected readonly IList mSupportedSignatureAlgorithms; - protected readonly IList mCertificateAuthorities; - - /** - * @param certificateTypes see {@link ClientCertificateType} for valid constants. - * @param certificateAuthorities an {@link IList} of {@link X509Name}. - */ - public CertificateRequest(byte[] certificateTypes, IList supportedSignatureAlgorithms, - IList certificateAuthorities) - { - this.mCertificateTypes = certificateTypes; - this.mSupportedSignatureAlgorithms = supportedSignatureAlgorithms; - this.mCertificateAuthorities = certificateAuthorities; - } - - /** - * @return an array of certificate types - * @see {@link ClientCertificateType} - */ - public virtual byte[] CertificateTypes - { - get { return mCertificateTypes; } - } - - /** - * @return an {@link IList} of {@link SignatureAndHashAlgorithm} (or null before TLS 1.2). - */ - public virtual IList SupportedSignatureAlgorithms - { - get { return mSupportedSignatureAlgorithms; } - } - - /** - * @return an {@link IList} of {@link X509Name} - */ - public virtual IList CertificateAuthorities - { - get { return mCertificateAuthorities; } - } - - /** - * Encode this {@link CertificateRequest} to a {@link Stream}. - * - * @param output the {@link Stream} to encode to. - * @throws IOException - */ - public virtual void Encode(Stream output) - { - if (mCertificateTypes == null || mCertificateTypes.Length == 0) - { - TlsUtilities.WriteUint8(0, output); - } - else - { - TlsUtilities.WriteUint8ArrayWithUint8Length(mCertificateTypes, output); - } - - if (mSupportedSignatureAlgorithms != null) - { - // TODO Check whether SignatureAlgorithm.anonymous is allowed here - TlsUtilities.EncodeSupportedSignatureAlgorithms(mSupportedSignatureAlgorithms, false, output); - } - - if (mCertificateAuthorities == null || mCertificateAuthorities.Count < 1) - { - TlsUtilities.WriteUint16(0, output); - } - else - { - IList derEncodings = Platform.CreateArrayList(mCertificateAuthorities.Count); - - int totalLength = 0; - foreach (Asn1Encodable certificateAuthority in mCertificateAuthorities) - { - byte[] derEncoding = certificateAuthority.GetEncoded(Asn1Encodable.Der); - derEncodings.Add(derEncoding); - totalLength += derEncoding.Length + 2; - } - - TlsUtilities.CheckUint16(totalLength); - TlsUtilities.WriteUint16(totalLength, output); - - foreach (byte[] derEncoding in derEncodings) - { - TlsUtilities.WriteOpaque16(derEncoding, output); - } - } - } - - /** - * Parse a {@link CertificateRequest} from a {@link Stream}. - * - * @param context - * the {@link TlsContext} of the current connection. - * @param input - * the {@link Stream} to parse from. - * @return a {@link CertificateRequest} object. - * @throws IOException - */ - public static CertificateRequest Parse(TlsContext context, Stream input) - { - int numTypes = TlsUtilities.ReadUint8(input); - byte[] certificateTypes = new byte[numTypes]; - for (int i = 0; i < numTypes; ++i) - { - certificateTypes[i] = TlsUtilities.ReadUint8(input); - } - - IList supportedSignatureAlgorithms = null; - if (TlsUtilities.IsTlsV12(context)) - { - // TODO Check whether SignatureAlgorithm.anonymous is allowed here - supportedSignatureAlgorithms = TlsUtilities.ParseSupportedSignatureAlgorithms(false, input); - } - - IList certificateAuthorities = Platform.CreateArrayList(); - byte[] certAuthData = TlsUtilities.ReadOpaque16(input); - MemoryStream bis = new MemoryStream(certAuthData, false); - while (bis.Position < bis.Length) - { - byte[] derEncoding = TlsUtilities.ReadOpaque16(bis); - Asn1Object asn1 = TlsUtilities.ReadDerObject(derEncoding); - // TODO Switch to X500Name when available - certificateAuthorities.Add(X509Name.GetInstance(asn1)); - } - - return new CertificateRequest(certificateTypes, supportedSignatureAlgorithms, certificateAuthorities); - } - } -} diff --git a/crypto/src/crypto/tls/CertificateStatus.cs b/crypto/src/crypto/tls/CertificateStatus.cs deleted file mode 100644 index bc4128722..000000000 --- a/crypto/src/crypto/tls/CertificateStatus.cs +++ /dev/null @@ -1,102 +0,0 @@ -using System; -using System.IO; - -using Org.BouncyCastle.Asn1; -using Org.BouncyCastle.Asn1.Ocsp; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class CertificateStatus - { - protected readonly byte mStatusType; - protected readonly object mResponse; - - public CertificateStatus(byte statusType, object response) - { - if (!IsCorrectType(statusType, response)) - throw new ArgumentException("not an instance of the correct type", "response"); - - this.mStatusType = statusType; - this.mResponse = response; - } - - public virtual byte StatusType - { - get { return mStatusType; } - } - - public virtual object Response - { - get { return mResponse; } - } - - public virtual OcspResponse GetOcspResponse() - { - if (!IsCorrectType(CertificateStatusType.ocsp, mResponse)) - throw new InvalidOperationException("'response' is not an OcspResponse"); - - return (OcspResponse)mResponse; - } - - /** - * Encode this {@link CertificateStatus} to a {@link Stream}. - * - * @param output - * the {@link Stream} to encode to. - * @throws IOException - */ - public virtual void Encode(Stream output) - { - TlsUtilities.WriteUint8(mStatusType, output); - - switch (mStatusType) - { - case CertificateStatusType.ocsp: - byte[] derEncoding = ((OcspResponse)mResponse).GetEncoded(Asn1Encodable.Der); - TlsUtilities.WriteOpaque24(derEncoding, output); - break; - default: - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } - - /** - * Parse a {@link CertificateStatus} from a {@link Stream}. - * - * @param input - * the {@link Stream} to parse from. - * @return a {@link CertificateStatus} object. - * @throws IOException - */ - public static CertificateStatus Parse(Stream input) - { - byte status_type = TlsUtilities.ReadUint8(input); - object response; - - switch (status_type) - { - case CertificateStatusType.ocsp: - { - byte[] derEncoding = TlsUtilities.ReadOpaque24(input); - response = OcspResponse.GetInstance(TlsUtilities.ReadDerObject(derEncoding)); - break; - } - default: - throw new TlsFatalAlert(AlertDescription.decode_error); - } - - return new CertificateStatus(status_type, response); - } - - protected static bool IsCorrectType(byte statusType, object response) - { - switch (statusType) - { - case CertificateStatusType.ocsp: - return response is OcspResponse; - default: - throw new ArgumentException("unsupported CertificateStatusType", "statusType"); - } - } - } -} diff --git a/crypto/src/crypto/tls/CertificateStatusRequest.cs b/crypto/src/crypto/tls/CertificateStatusRequest.cs deleted file mode 100644 index 24ce37655..000000000 --- a/crypto/src/crypto/tls/CertificateStatusRequest.cs +++ /dev/null @@ -1,95 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class CertificateStatusRequest - { - protected readonly byte mStatusType; - protected readonly object mRequest; - - public CertificateStatusRequest(byte statusType, Object request) - { - if (!IsCorrectType(statusType, request)) - throw new ArgumentException("not an instance of the correct type", "request"); - - this.mStatusType = statusType; - this.mRequest = request; - } - - public virtual byte StatusType - { - get { return mStatusType; } - } - - public virtual object Request - { - get { return mRequest; } - } - - public virtual OcspStatusRequest GetOcspStatusRequest() - { - if (!IsCorrectType(CertificateStatusType.ocsp, mRequest)) - throw new InvalidOperationException("'request' is not an OCSPStatusRequest"); - - return (OcspStatusRequest)mRequest; - } - - /** - * Encode this {@link CertificateStatusRequest} to a {@link Stream}. - * - * @param output - * the {@link Stream} to encode to. - * @throws IOException - */ - public virtual void Encode(Stream output) - { - TlsUtilities.WriteUint8(mStatusType, output); - - switch (mStatusType) - { - case CertificateStatusType.ocsp: - ((OcspStatusRequest)mRequest).Encode(output); - break; - default: - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } - - /** - * Parse a {@link CertificateStatusRequest} from a {@link Stream}. - * - * @param input - * the {@link Stream} to parse from. - * @return a {@link CertificateStatusRequest} object. - * @throws IOException - */ - public static CertificateStatusRequest Parse(Stream input) - { - byte status_type = TlsUtilities.ReadUint8(input); - object result; - - switch (status_type) - { - case CertificateStatusType.ocsp: - result = OcspStatusRequest.Parse(input); - break; - default: - throw new TlsFatalAlert(AlertDescription.decode_error); - } - - return new CertificateStatusRequest(status_type, result); - } - - protected static bool IsCorrectType(byte statusType, object request) - { - switch (statusType) - { - case CertificateStatusType.ocsp: - return request is OcspStatusRequest; - default: - throw new ArgumentException("unsupported CertificateStatusType", "statusType"); - } - } - } -} diff --git a/crypto/src/crypto/tls/CertificateStatusType.cs b/crypto/src/crypto/tls/CertificateStatusType.cs deleted file mode 100644 index 54b741b42..000000000 --- a/crypto/src/crypto/tls/CertificateStatusType.cs +++ /dev/null @@ -1,12 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class CertificateStatusType - { - /* - * RFC 3546 3.6 - */ - public const byte ocsp = 1; - } -} diff --git a/crypto/src/crypto/tls/CertificateType.cs b/crypto/src/crypto/tls/CertificateType.cs deleted file mode 100644 index 47ec05c80..000000000 --- a/crypto/src/crypto/tls/CertificateType.cs +++ /dev/null @@ -1,18 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /** - * RFC 6091 - */ - public class CertificateType - { - public const byte X509 = 0; - public const byte OpenPGP = 1; - - /* - * RFC 7250 - */ - public const byte RawPublicKey = 2; - } -} diff --git a/crypto/src/crypto/tls/CertificateUrl.cs b/crypto/src/crypto/tls/CertificateUrl.cs deleted file mode 100644 index aff999551..000000000 --- a/crypto/src/crypto/tls/CertificateUrl.cs +++ /dev/null @@ -1,125 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Utilities; -using Org.BouncyCastle.Utilities.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /* - * RFC 3546 3.3 - */ - public class CertificateUrl - { - protected readonly byte mType; - protected readonly IList mUrlAndHashList; - - /** - * @param type - * see {@link CertChainType} for valid constants. - * @param urlAndHashList - * a {@link IList} of {@link UrlAndHash}. - */ - public CertificateUrl(byte type, IList urlAndHashList) - { - if (!CertChainType.IsValid(type)) - throw new ArgumentException("not a valid CertChainType value", "type"); - if (urlAndHashList == null || urlAndHashList.Count < 1) - throw new ArgumentException("must have length > 0", "urlAndHashList"); - - this.mType = type; - this.mUrlAndHashList = urlAndHashList; - } - - /** - * @return {@link CertChainType} - */ - public virtual byte Type - { - get { return mType; } - } - - /** - * @return an {@link IList} of {@link UrlAndHash} - */ - public virtual IList UrlAndHashList - { - get { return mUrlAndHashList; } - } - - /** - * Encode this {@link CertificateUrl} to a {@link Stream}. - * - * @param output the {@link Stream} to encode to. - * @throws IOException - */ - public virtual void Encode(Stream output) - { - TlsUtilities.WriteUint8(this.mType, output); - - ListBuffer16 buf = new ListBuffer16(); - foreach (UrlAndHash urlAndHash in this.mUrlAndHashList) - { - urlAndHash.Encode(buf); - } - buf.EncodeTo(output); - } - - /** - * Parse a {@link CertificateUrl} from a {@link Stream}. - * - * @param context - * the {@link TlsContext} of the current connection. - * @param input - * the {@link Stream} to parse from. - * @return a {@link CertificateUrl} object. - * @throws IOException - */ - public static CertificateUrl parse(TlsContext context, Stream input) - { - byte type = TlsUtilities.ReadUint8(input); - if (!CertChainType.IsValid(type)) - throw new TlsFatalAlert(AlertDescription.decode_error); - - int totalLength = TlsUtilities.ReadUint16(input); - if (totalLength < 1) - throw new TlsFatalAlert(AlertDescription.decode_error); - - byte[] urlAndHashListData = TlsUtilities.ReadFully(totalLength, input); - - MemoryStream buf = new MemoryStream(urlAndHashListData, false); - - IList url_and_hash_list = Platform.CreateArrayList(); - while (buf.Position < buf.Length) - { - UrlAndHash url_and_hash = UrlAndHash.Parse(context, buf); - url_and_hash_list.Add(url_and_hash); - } - - return new CertificateUrl(type, url_and_hash_list); - } - - // TODO Could be more generally useful - internal class ListBuffer16 - : MemoryStream - { - internal ListBuffer16() - { - // Reserve space for length - TlsUtilities.WriteUint16(0, this); - } - - internal void EncodeTo(Stream output) - { - // Patch actual length back in - long length = Length - 2; - TlsUtilities.CheckUint16(length); - this.Position = 0; - TlsUtilities.WriteUint16((int)length, this); - Streams.WriteBufTo(this, output); - Platform.Dispose(this); - } - } - } -} diff --git a/crypto/src/crypto/tls/Chacha20Poly1305.cs b/crypto/src/crypto/tls/Chacha20Poly1305.cs deleted file mode 100644 index 8687803b4..000000000 --- a/crypto/src/crypto/tls/Chacha20Poly1305.cs +++ /dev/null @@ -1,199 +0,0 @@ -using System; -using System.IO; - -using Org.BouncyCastle.Crypto.Engines; -using Org.BouncyCastle.Crypto.Generators; -using Org.BouncyCastle.Crypto.Macs; -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Crypto.Utilities; -using Org.BouncyCastle.Security; -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /** - * draft-ietf-tls-chacha20-poly1305-04 - */ - public class Chacha20Poly1305 - : TlsCipher - { - private static readonly byte[] Zeroes = new byte[15]; - - protected readonly TlsContext context; - - protected readonly ChaCha7539Engine encryptCipher, decryptCipher; - protected readonly byte[] encryptIV, decryptIV; - - /// <exception cref="IOException"></exception> - public Chacha20Poly1305(TlsContext context) - { - if (!TlsUtilities.IsTlsV12(context)) - throw new TlsFatalAlert(AlertDescription.internal_error); - - this.context = context; - - int cipherKeySize = 32; - // TODO SecurityParameters.fixed_iv_length - int fixed_iv_length = 12; - // TODO SecurityParameters.record_iv_length = 0 - - int key_block_size = (2 * cipherKeySize) + (2 * fixed_iv_length); - - byte[] key_block = TlsUtilities.CalculateKeyBlock(context, key_block_size); - - int offset = 0; - - KeyParameter client_write_key = new KeyParameter(key_block, offset, cipherKeySize); - offset += cipherKeySize; - KeyParameter server_write_key = new KeyParameter(key_block, offset, cipherKeySize); - offset += cipherKeySize; - byte[] client_write_IV = Arrays.CopyOfRange(key_block, offset, offset + fixed_iv_length); - offset += fixed_iv_length; - byte[] server_write_IV = Arrays.CopyOfRange(key_block, offset, offset + fixed_iv_length); - offset += fixed_iv_length; - - if (offset != key_block_size) - throw new TlsFatalAlert(AlertDescription.internal_error); - - this.encryptCipher = new ChaCha7539Engine(); - this.decryptCipher = new ChaCha7539Engine(); - - KeyParameter encryptKey, decryptKey; - if (context.IsServer) - { - encryptKey = server_write_key; - decryptKey = client_write_key; - this.encryptIV = server_write_IV; - this.decryptIV = client_write_IV; - } - else - { - encryptKey = client_write_key; - decryptKey = server_write_key; - this.encryptIV = client_write_IV; - this.decryptIV = server_write_IV; - } - - this.encryptCipher.Init(true, new ParametersWithIV(encryptKey, encryptIV)); - this.decryptCipher.Init(false, new ParametersWithIV(decryptKey, decryptIV)); - } - - public virtual int GetPlaintextLimit(int ciphertextLimit) - { - return ciphertextLimit - 16; - } - - /// <exception cref="IOException"></exception> - public virtual byte[] EncodePlaintext(long seqNo, byte type, byte[] plaintext, int offset, int len) - { - KeyParameter macKey = InitRecord(encryptCipher, true, seqNo, encryptIV); - - byte[] output = new byte[len + 16]; - encryptCipher.ProcessBytes(plaintext, offset, len, output, 0); - - byte[] additionalData = GetAdditionalData(seqNo, type, len); - byte[] mac = CalculateRecordMac(macKey, additionalData, output, 0, len); - Array.Copy(mac, 0, output, len, mac.Length); - - return output; - } - - /// <exception cref="IOException"></exception> - public virtual byte[] DecodeCiphertext(long seqNo, byte type, byte[] ciphertext, int offset, int len) - { - if (GetPlaintextLimit(len) < 0) - throw new TlsFatalAlert(AlertDescription.decode_error); - - KeyParameter macKey = InitRecord(decryptCipher, false, seqNo, decryptIV); - - int plaintextLength = len - 16; - - byte[] additionalData = GetAdditionalData(seqNo, type, plaintextLength); - byte[] calculatedMac = CalculateRecordMac(macKey, additionalData, ciphertext, offset, plaintextLength); - byte[] receivedMac = Arrays.CopyOfRange(ciphertext, offset + plaintextLength, offset + len); - - if (!Arrays.ConstantTimeAreEqual(calculatedMac, receivedMac)) - throw new TlsFatalAlert(AlertDescription.bad_record_mac); - - byte[] output = new byte[plaintextLength]; - decryptCipher.ProcessBytes(ciphertext, offset, plaintextLength, output, 0); - return output; - } - - protected virtual KeyParameter InitRecord(IStreamCipher cipher, bool forEncryption, long seqNo, byte[] iv) - { - byte[] nonce = CalculateNonce(seqNo, iv); - cipher.Init(forEncryption, new ParametersWithIV(null, nonce)); - return GenerateRecordMacKey(cipher); - } - - protected virtual byte[] CalculateNonce(long seqNo, byte[] iv) - { - byte[] nonce = new byte[12]; - TlsUtilities.WriteUint64(seqNo, nonce, 4); - - for (int i = 0; i < 12; ++i) - { - nonce[i] ^= iv[i]; - } - - return nonce; - } - - protected virtual KeyParameter GenerateRecordMacKey(IStreamCipher cipher) - { - byte[] firstBlock = new byte[64]; - cipher.ProcessBytes(firstBlock, 0, firstBlock.Length, firstBlock, 0); - - KeyParameter macKey = new KeyParameter(firstBlock, 0, 32); - Arrays.Fill(firstBlock, (byte)0); - return macKey; - } - - protected virtual byte[] CalculateRecordMac(KeyParameter macKey, byte[] additionalData, byte[] buf, int off, int len) - { - IMac mac = new Poly1305(); - mac.Init(macKey); - - UpdateRecordMacText(mac, additionalData, 0, additionalData.Length); - UpdateRecordMacText(mac, buf, off, len); - UpdateRecordMacLength(mac, additionalData.Length); - UpdateRecordMacLength(mac, len); - - return MacUtilities.DoFinal(mac); - } - - protected virtual void UpdateRecordMacLength(IMac mac, int len) - { - byte[] longLen = Pack.UInt64_To_LE((ulong)len); - mac.BlockUpdate(longLen, 0, longLen.Length); - } - - protected virtual void UpdateRecordMacText(IMac mac, byte[] buf, int off, int len) - { - mac.BlockUpdate(buf, off, len); - - int partial = len % 16; - if (partial != 0) - { - mac.BlockUpdate(Zeroes, 0, 16 - partial); - } - } - - /// <exception cref="IOException"></exception> - protected virtual byte[] GetAdditionalData(long seqNo, byte type, int len) - { - /* - * additional_data = seq_num + TLSCompressed.type + TLSCompressed.version + - * TLSCompressed.length - */ - byte[] additional_data = new byte[13]; - TlsUtilities.WriteUint64(seqNo, additional_data, 0); - TlsUtilities.WriteUint8(type, additional_data, 8); - TlsUtilities.WriteVersion(context.ServerVersion, additional_data, 9); - TlsUtilities.WriteUint16(len, additional_data, 11); - - return additional_data; - } - } -} diff --git a/crypto/src/crypto/tls/ChangeCipherSpec.cs b/crypto/src/crypto/tls/ChangeCipherSpec.cs deleted file mode 100644 index 323de9162..000000000 --- a/crypto/src/crypto/tls/ChangeCipherSpec.cs +++ /dev/null @@ -1,9 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class ChangeCipherSpec - { - public const byte change_cipher_spec = 1; - } -} diff --git a/crypto/src/crypto/tls/CipherSuite.cs b/crypto/src/crypto/tls/CipherSuite.cs deleted file mode 100644 index 5aa556389..000000000 --- a/crypto/src/crypto/tls/CipherSuite.cs +++ /dev/null @@ -1,361 +0,0 @@ -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary> - /// RFC 2246 A.5 - /// </summary> - public abstract class CipherSuite - { - public const int TLS_NULL_WITH_NULL_NULL = 0x0000; - public const int TLS_RSA_WITH_NULL_MD5 = 0x0001; - public const int TLS_RSA_WITH_NULL_SHA = 0x0002; - public const int TLS_RSA_EXPORT_WITH_RC4_40_MD5 = 0x0003; - public const int TLS_RSA_WITH_RC4_128_MD5 = 0x0004; - public const int TLS_RSA_WITH_RC4_128_SHA = 0x0005; - public const int TLS_RSA_EXPORT_WITH_RC2_CBC_40_MD5 = 0x0006; - public const int TLS_RSA_WITH_IDEA_CBC_SHA = 0x0007; - public const int TLS_RSA_EXPORT_WITH_DES40_CBC_SHA = 0x0008; - public const int TLS_RSA_WITH_DES_CBC_SHA = 0x0009; - public const int TLS_RSA_WITH_3DES_EDE_CBC_SHA = 0x000A; - public const int TLS_DH_DSS_EXPORT_WITH_DES40_CBC_SHA = 0x000B; - public const int TLS_DH_DSS_WITH_DES_CBC_SHA = 0x000C; - public const int TLS_DH_DSS_WITH_3DES_EDE_CBC_SHA = 0x000D; - public const int TLS_DH_RSA_EXPORT_WITH_DES40_CBC_SHA = 0x000E; - public const int TLS_DH_RSA_WITH_DES_CBC_SHA = 0x000F; - public const int TLS_DH_RSA_WITH_3DES_EDE_CBC_SHA = 0x0010; - public const int TLS_DHE_DSS_EXPORT_WITH_DES40_CBC_SHA = 0x0011; - public const int TLS_DHE_DSS_WITH_DES_CBC_SHA = 0x0012; - public const int TLS_DHE_DSS_WITH_3DES_EDE_CBC_SHA = 0x0013; - public const int TLS_DHE_RSA_EXPORT_WITH_DES40_CBC_SHA = 0x0014; - public const int TLS_DHE_RSA_WITH_DES_CBC_SHA = 0x0015; - public const int TLS_DHE_RSA_WITH_3DES_EDE_CBC_SHA = 0x0016; - public const int TLS_DH_anon_EXPORT_WITH_RC4_40_MD5 = 0x0017; - public const int TLS_DH_anon_WITH_RC4_128_MD5 = 0x0018; - public const int TLS_DH_anon_EXPORT_WITH_DES40_CBC_SHA = 0x0019; - public const int TLS_DH_anon_WITH_DES_CBC_SHA = 0x001A; - public const int TLS_DH_anon_WITH_3DES_EDE_CBC_SHA = 0x001B; - - /* - * Note: The cipher suite values { 0x00, 0x1C } and { 0x00, 0x1D } are reserved to avoid - * collision with Fortezza-based cipher suites in SSL 3. - */ - - /* - * RFC 3268 - */ - public const int TLS_RSA_WITH_AES_128_CBC_SHA = 0x002F; - public const int TLS_DH_DSS_WITH_AES_128_CBC_SHA = 0x0030; - public const int TLS_DH_RSA_WITH_AES_128_CBC_SHA = 0x0031; - public const int TLS_DHE_DSS_WITH_AES_128_CBC_SHA = 0x0032; - public const int TLS_DHE_RSA_WITH_AES_128_CBC_SHA = 0x0033; - public const int TLS_DH_anon_WITH_AES_128_CBC_SHA = 0x0034; - public const int TLS_RSA_WITH_AES_256_CBC_SHA = 0x0035; - public const int TLS_DH_DSS_WITH_AES_256_CBC_SHA = 0x0036; - public const int TLS_DH_RSA_WITH_AES_256_CBC_SHA = 0x0037; - public const int TLS_DHE_DSS_WITH_AES_256_CBC_SHA = 0x0038; - public const int TLS_DHE_RSA_WITH_AES_256_CBC_SHA = 0x0039; - public const int TLS_DH_anon_WITH_AES_256_CBC_SHA = 0x003A; - - /* - * RFC 5932 - */ - public const int TLS_RSA_WITH_CAMELLIA_128_CBC_SHA = 0x0041; - public const int TLS_DH_DSS_WITH_CAMELLIA_128_CBC_SHA = 0x0042; - public const int TLS_DH_RSA_WITH_CAMELLIA_128_CBC_SHA = 0x0043; - public const int TLS_DHE_DSS_WITH_CAMELLIA_128_CBC_SHA = 0x0044; - public const int TLS_DHE_RSA_WITH_CAMELLIA_128_CBC_SHA = 0x0045; - public const int TLS_DH_anon_WITH_CAMELLIA_128_CBC_SHA = 0x0046; - - public const int TLS_RSA_WITH_CAMELLIA_256_CBC_SHA = 0x0084; - public const int TLS_DH_DSS_WITH_CAMELLIA_256_CBC_SHA = 0x0085; - public const int TLS_DH_RSA_WITH_CAMELLIA_256_CBC_SHA = 0x0086; - public const int TLS_DHE_DSS_WITH_CAMELLIA_256_CBC_SHA = 0x0087; - public const int TLS_DHE_RSA_WITH_CAMELLIA_256_CBC_SHA = 0x0088; - public const int TLS_DH_anon_WITH_CAMELLIA_256_CBC_SHA = 0x0089; - - public const int TLS_RSA_WITH_CAMELLIA_128_CBC_SHA256 = 0x00BA; - public const int TLS_DH_DSS_WITH_CAMELLIA_128_CBC_SHA256 = 0x00BB; - public const int TLS_DH_RSA_WITH_CAMELLIA_128_CBC_SHA256 = 0x00BC; - public const int TLS_DHE_DSS_WITH_CAMELLIA_128_CBC_SHA256 = 0x00BD; - public const int TLS_DHE_RSA_WITH_CAMELLIA_128_CBC_SHA256 = 0x00BE; - public const int TLS_DH_anon_WITH_CAMELLIA_128_CBC_SHA256 = 0x00BF; - - public const int TLS_RSA_WITH_CAMELLIA_256_CBC_SHA256 = 0x00C0; - public const int TLS_DH_DSS_WITH_CAMELLIA_256_CBC_SHA256 = 0x00C1; - public const int TLS_DH_RSA_WITH_CAMELLIA_256_CBC_SHA256 = 0x00C2; - public const int TLS_DHE_DSS_WITH_CAMELLIA_256_CBC_SHA256 = 0x00C3; - public const int TLS_DHE_RSA_WITH_CAMELLIA_256_CBC_SHA256 = 0x00C4; - public const int TLS_DH_anon_WITH_CAMELLIA_256_CBC_SHA256 = 0x00C5; - - /* - * RFC 4162 - */ - public const int TLS_RSA_WITH_SEED_CBC_SHA = 0x0096; - public const int TLS_DH_DSS_WITH_SEED_CBC_SHA = 0x0097; - public const int TLS_DH_RSA_WITH_SEED_CBC_SHA = 0x0098; - public const int TLS_DHE_DSS_WITH_SEED_CBC_SHA = 0x0099; - public const int TLS_DHE_RSA_WITH_SEED_CBC_SHA = 0x009A; - public const int TLS_DH_anon_WITH_SEED_CBC_SHA = 0x009B; - - /* - * RFC 4279 - */ - public const int TLS_PSK_WITH_RC4_128_SHA = 0x008A; - public const int TLS_PSK_WITH_3DES_EDE_CBC_SHA = 0x008B; - public const int TLS_PSK_WITH_AES_128_CBC_SHA = 0x008C; - public const int TLS_PSK_WITH_AES_256_CBC_SHA = 0x008D; - public const int TLS_DHE_PSK_WITH_RC4_128_SHA = 0x008E; - public const int TLS_DHE_PSK_WITH_3DES_EDE_CBC_SHA = 0x008F; - public const int TLS_DHE_PSK_WITH_AES_128_CBC_SHA = 0x0090; - public const int TLS_DHE_PSK_WITH_AES_256_CBC_SHA = 0x0091; - public const int TLS_RSA_PSK_WITH_RC4_128_SHA = 0x0092; - public const int TLS_RSA_PSK_WITH_3DES_EDE_CBC_SHA = 0x0093; - public const int TLS_RSA_PSK_WITH_AES_128_CBC_SHA = 0x0094; - public const int TLS_RSA_PSK_WITH_AES_256_CBC_SHA = 0x0095; - - /* - * RFC 4492 - */ - public const int TLS_ECDH_ECDSA_WITH_NULL_SHA = 0xC001; - public const int TLS_ECDH_ECDSA_WITH_RC4_128_SHA = 0xC002; - public const int TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA = 0xC003; - public const int TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA = 0xC004; - public const int TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA = 0xC005; - public const int TLS_ECDHE_ECDSA_WITH_NULL_SHA = 0xC006; - public const int TLS_ECDHE_ECDSA_WITH_RC4_128_SHA = 0xC007; - public const int TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA = 0xC008; - public const int TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA = 0xC009; - public const int TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA = 0xC00A; - public const int TLS_ECDH_RSA_WITH_NULL_SHA = 0xC00B; - public const int TLS_ECDH_RSA_WITH_RC4_128_SHA = 0xC00C; - public const int TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA = 0xC00D; - public const int TLS_ECDH_RSA_WITH_AES_128_CBC_SHA = 0xC00E; - public const int TLS_ECDH_RSA_WITH_AES_256_CBC_SHA = 0xC00F; - public const int TLS_ECDHE_RSA_WITH_NULL_SHA = 0xC010; - public const int TLS_ECDHE_RSA_WITH_RC4_128_SHA = 0xC011; - public const int TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA = 0xC012; - public const int TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA = 0xC013; - public const int TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA = 0xC014; - public const int TLS_ECDH_anon_WITH_NULL_SHA = 0xC015; - public const int TLS_ECDH_anon_WITH_RC4_128_SHA = 0xC016; - public const int TLS_ECDH_anon_WITH_3DES_EDE_CBC_SHA = 0xC017; - public const int TLS_ECDH_anon_WITH_AES_128_CBC_SHA = 0xC018; - public const int TLS_ECDH_anon_WITH_AES_256_CBC_SHA = 0xC019; - - /* - * RFC 4785 - */ - public const int TLS_PSK_WITH_NULL_SHA = 0x002C; - public const int TLS_DHE_PSK_WITH_NULL_SHA = 0x002D; - public const int TLS_RSA_PSK_WITH_NULL_SHA = 0x002E; - - /* - * RFC 5054 - */ - public const int TLS_SRP_SHA_WITH_3DES_EDE_CBC_SHA = 0xC01A; - public const int TLS_SRP_SHA_RSA_WITH_3DES_EDE_CBC_SHA = 0xC01B; - public const int TLS_SRP_SHA_DSS_WITH_3DES_EDE_CBC_SHA = 0xC01C; - public const int TLS_SRP_SHA_WITH_AES_128_CBC_SHA = 0xC01D; - public const int TLS_SRP_SHA_RSA_WITH_AES_128_CBC_SHA = 0xC01E; - public const int TLS_SRP_SHA_DSS_WITH_AES_128_CBC_SHA = 0xC01F; - public const int TLS_SRP_SHA_WITH_AES_256_CBC_SHA = 0xC020; - public const int TLS_SRP_SHA_RSA_WITH_AES_256_CBC_SHA = 0xC021; - public const int TLS_SRP_SHA_DSS_WITH_AES_256_CBC_SHA = 0xC022; - - /* - * RFC 5246 - */ - public const int TLS_RSA_WITH_NULL_SHA256 = 0x003B; - public const int TLS_RSA_WITH_AES_128_CBC_SHA256 = 0x003C; - public const int TLS_RSA_WITH_AES_256_CBC_SHA256 = 0x003D; - public const int TLS_DH_DSS_WITH_AES_128_CBC_SHA256 = 0x003E; - public const int TLS_DH_RSA_WITH_AES_128_CBC_SHA256 = 0x003F; - public const int TLS_DHE_DSS_WITH_AES_128_CBC_SHA256 = 0x0040; - public const int TLS_DHE_RSA_WITH_AES_128_CBC_SHA256 = 0x0067; - public const int TLS_DH_DSS_WITH_AES_256_CBC_SHA256 = 0x0068; - public const int TLS_DH_RSA_WITH_AES_256_CBC_SHA256 = 0x0069; - public const int TLS_DHE_DSS_WITH_AES_256_CBC_SHA256 = 0x006A; - public const int TLS_DHE_RSA_WITH_AES_256_CBC_SHA256 = 0x006B; - public const int TLS_DH_anon_WITH_AES_128_CBC_SHA256 = 0x006C; - public const int TLS_DH_anon_WITH_AES_256_CBC_SHA256 = 0x006D; - - /* - * RFC 5288 - */ - public const int TLS_RSA_WITH_AES_128_GCM_SHA256 = 0x009C; - public const int TLS_RSA_WITH_AES_256_GCM_SHA384 = 0x009D; - public const int TLS_DHE_RSA_WITH_AES_128_GCM_SHA256 = 0x009E; - public const int TLS_DHE_RSA_WITH_AES_256_GCM_SHA384 = 0x009F; - public const int TLS_DH_RSA_WITH_AES_128_GCM_SHA256 = 0x00A0; - public const int TLS_DH_RSA_WITH_AES_256_GCM_SHA384 = 0x00A1; - public const int TLS_DHE_DSS_WITH_AES_128_GCM_SHA256 = 0x00A2; - public const int TLS_DHE_DSS_WITH_AES_256_GCM_SHA384 = 0x00A3; - public const int TLS_DH_DSS_WITH_AES_128_GCM_SHA256 = 0x00A4; - public const int TLS_DH_DSS_WITH_AES_256_GCM_SHA384 = 0x00A5; - public const int TLS_DH_anon_WITH_AES_128_GCM_SHA256 = 0x00A6; - public const int TLS_DH_anon_WITH_AES_256_GCM_SHA384 = 0x00A7; - - /* - * RFC 5289 - */ - public const int TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256 = 0xC023; - public const int TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384 = 0xC024; - public const int TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA256 = 0xC025; - public const int TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA384 = 0xC026; - public const int TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256 = 0xC027; - public const int TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384 = 0xC028; - public const int TLS_ECDH_RSA_WITH_AES_128_CBC_SHA256 = 0xC029; - public const int TLS_ECDH_RSA_WITH_AES_256_CBC_SHA384 = 0xC02A; - public const int TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256 = 0xC02B; - public const int TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384 = 0xC02C; - public const int TLS_ECDH_ECDSA_WITH_AES_128_GCM_SHA256 = 0xC02D; - public const int TLS_ECDH_ECDSA_WITH_AES_256_GCM_SHA384 = 0xC02E; - public const int TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256 = 0xC02F; - public const int TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 = 0xC030; - public const int TLS_ECDH_RSA_WITH_AES_128_GCM_SHA256 = 0xC031; - public const int TLS_ECDH_RSA_WITH_AES_256_GCM_SHA384 = 0xC032; - - /* - * RFC 5487 - */ - public const int TLS_PSK_WITH_AES_128_GCM_SHA256 = 0x00A8; - public const int TLS_PSK_WITH_AES_256_GCM_SHA384 = 0x00A9; - public const int TLS_DHE_PSK_WITH_AES_128_GCM_SHA256 = 0x00AA; - public const int TLS_DHE_PSK_WITH_AES_256_GCM_SHA384 = 0x00AB; - public const int TLS_RSA_PSK_WITH_AES_128_GCM_SHA256 = 0x00AC; - public const int TLS_RSA_PSK_WITH_AES_256_GCM_SHA384 = 0x00AD; - public const int TLS_PSK_WITH_AES_128_CBC_SHA256 = 0x00AE; - public const int TLS_PSK_WITH_AES_256_CBC_SHA384 = 0x00AF; - public const int TLS_PSK_WITH_NULL_SHA256 = 0x00B0; - public const int TLS_PSK_WITH_NULL_SHA384 = 0x00B1; - public const int TLS_DHE_PSK_WITH_AES_128_CBC_SHA256 = 0x00B2; - public const int TLS_DHE_PSK_WITH_AES_256_CBC_SHA384 = 0x00B3; - public const int TLS_DHE_PSK_WITH_NULL_SHA256 = 0x00B4; - public const int TLS_DHE_PSK_WITH_NULL_SHA384 = 0x00B5; - public const int TLS_RSA_PSK_WITH_AES_128_CBC_SHA256 = 0x00B6; - public const int TLS_RSA_PSK_WITH_AES_256_CBC_SHA384 = 0x00B7; - public const int TLS_RSA_PSK_WITH_NULL_SHA256 = 0x00B8; - public const int TLS_RSA_PSK_WITH_NULL_SHA384 = 0x00B9; - - /* - * RFC 5489 - */ - public const int TLS_ECDHE_PSK_WITH_RC4_128_SHA = 0xC033; - public const int TLS_ECDHE_PSK_WITH_3DES_EDE_CBC_SHA = 0xC034; - public const int TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA = 0xC035; - public const int TLS_ECDHE_PSK_WITH_AES_256_CBC_SHA = 0xC036; - public const int TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA256 = 0xC037; - public const int TLS_ECDHE_PSK_WITH_AES_256_CBC_SHA384 = 0xC038; - public const int TLS_ECDHE_PSK_WITH_NULL_SHA = 0xC039; - public const int TLS_ECDHE_PSK_WITH_NULL_SHA256 = 0xC03A; - public const int TLS_ECDHE_PSK_WITH_NULL_SHA384 = 0xC03B; - - /* - * RFC 5746 - */ - public const int TLS_EMPTY_RENEGOTIATION_INFO_SCSV = 0x00FF; - - /* - * RFC 6367 - */ - public const int TLS_ECDHE_ECDSA_WITH_CAMELLIA_128_CBC_SHA256 = 0xC072; - public const int TLS_ECDHE_ECDSA_WITH_CAMELLIA_256_CBC_SHA384 = 0xC073; - public const int TLS_ECDH_ECDSA_WITH_CAMELLIA_128_CBC_SHA256 = 0xC074; - public const int TLS_ECDH_ECDSA_WITH_CAMELLIA_256_CBC_SHA384 = 0xC075; - public const int TLS_ECDHE_RSA_WITH_CAMELLIA_128_CBC_SHA256 = 0xC076; - public const int TLS_ECDHE_RSA_WITH_CAMELLIA_256_CBC_SHA384 = 0xC077; - public const int TLS_ECDH_RSA_WITH_CAMELLIA_128_CBC_SHA256 = 0xC078; - public const int TLS_ECDH_RSA_WITH_CAMELLIA_256_CBC_SHA384 = 0xC079; - - public const int TLS_RSA_WITH_CAMELLIA_128_GCM_SHA256 = 0xC07A; - public const int TLS_RSA_WITH_CAMELLIA_256_GCM_SHA384 = 0xC07B; - public const int TLS_DHE_RSA_WITH_CAMELLIA_128_GCM_SHA256 = 0xC07C; - public const int TLS_DHE_RSA_WITH_CAMELLIA_256_GCM_SHA384 = 0xC07D; - public const int TLS_DH_RSA_WITH_CAMELLIA_128_GCM_SHA256 = 0xC07E; - public const int TLS_DH_RSA_WITH_CAMELLIA_256_GCM_SHA384 = 0xC07F; - public const int TLS_DHE_DSS_WITH_CAMELLIA_128_GCM_SHA256 = 0xC080; - public const int TLS_DHE_DSS_WITH_CAMELLIA_256_GCM_SHA384 = 0xC081; - public const int TLS_DH_DSS_WITH_CAMELLIA_128_GCM_SHA256 = 0xC082; - public const int TLS_DH_DSS_WITH_CAMELLIA_256_GCM_SHA384 = 0xC083; - public const int TLS_DH_anon_WITH_CAMELLIA_128_GCM_SHA256 = 0xC084; - public const int TLS_DH_anon_WITH_CAMELLIA_256_GCM_SHA384 = 0xC085; - public const int TLS_ECDHE_ECDSA_WITH_CAMELLIA_128_GCM_SHA256 = 0xC086; - public const int TLS_ECDHE_ECDSA_WITH_CAMELLIA_256_GCM_SHA384 = 0xC087; - public const int TLS_ECDH_ECDSA_WITH_CAMELLIA_128_GCM_SHA256 = 0xC088; - public const int TLS_ECDH_ECDSA_WITH_CAMELLIA_256_GCM_SHA384 = 0xC089; - public const int TLS_ECDHE_RSA_WITH_CAMELLIA_128_GCM_SHA256 = 0xC08A; - public const int TLS_ECDHE_RSA_WITH_CAMELLIA_256_GCM_SHA384 = 0xC08B; - public const int TLS_ECDH_RSA_WITH_CAMELLIA_128_GCM_SHA256 = 0xC08C; - public const int TLS_ECDH_RSA_WITH_CAMELLIA_256_GCM_SHA384 = 0xC08D; - - public const int TLS_PSK_WITH_CAMELLIA_128_GCM_SHA256 = 0xC08E; - public const int TLS_PSK_WITH_CAMELLIA_256_GCM_SHA384 = 0xC08F; - public const int TLS_DHE_PSK_WITH_CAMELLIA_128_GCM_SHA256 = 0xC090; - public const int TLS_DHE_PSK_WITH_CAMELLIA_256_GCM_SHA384 = 0xC091; - public const int TLS_RSA_PSK_WITH_CAMELLIA_128_GCM_SHA256 = 0xC092; - public const int TLS_RSA_PSK_WITH_CAMELLIA_256_GCM_SHA384 = 0xC093; - public const int TLS_PSK_WITH_CAMELLIA_128_CBC_SHA256 = 0xC094; - public const int TLS_PSK_WITH_CAMELLIA_256_CBC_SHA384 = 0xC095; - public const int TLS_DHE_PSK_WITH_CAMELLIA_128_CBC_SHA256 = 0xC096; - public const int TLS_DHE_PSK_WITH_CAMELLIA_256_CBC_SHA384 = 0xC097; - public const int TLS_RSA_PSK_WITH_CAMELLIA_128_CBC_SHA256 = 0xC098; - public const int TLS_RSA_PSK_WITH_CAMELLIA_256_CBC_SHA384 = 0xC099; - public const int TLS_ECDHE_PSK_WITH_CAMELLIA_128_CBC_SHA256 = 0xC09A; - public const int TLS_ECDHE_PSK_WITH_CAMELLIA_256_CBC_SHA384 = 0xC09B; - - /* - * RFC 6655 - */ - public const int TLS_RSA_WITH_AES_128_CCM = 0xC09C; - public const int TLS_RSA_WITH_AES_256_CCM = 0xC09D; - public const int TLS_DHE_RSA_WITH_AES_128_CCM = 0xC09E; - public const int TLS_DHE_RSA_WITH_AES_256_CCM = 0xC09F; - public const int TLS_RSA_WITH_AES_128_CCM_8 = 0xC0A0; - public const int TLS_RSA_WITH_AES_256_CCM_8 = 0xC0A1; - public const int TLS_DHE_RSA_WITH_AES_128_CCM_8 = 0xC0A2; - public const int TLS_DHE_RSA_WITH_AES_256_CCM_8 = 0xC0A3; - public const int TLS_PSK_WITH_AES_128_CCM = 0xC0A4; - public const int TLS_PSK_WITH_AES_256_CCM = 0xC0A5; - public const int TLS_DHE_PSK_WITH_AES_128_CCM = 0xC0A6; - public const int TLS_DHE_PSK_WITH_AES_256_CCM = 0xC0A7; - public const int TLS_PSK_WITH_AES_128_CCM_8 = 0xC0A8; - public const int TLS_PSK_WITH_AES_256_CCM_8 = 0xC0A9; - public const int TLS_PSK_DHE_WITH_AES_128_CCM_8 = 0xC0AA; - public const int TLS_PSK_DHE_WITH_AES_256_CCM_8 = 0xC0AB; - - /* - * RFC 7251 - */ - public const int TLS_ECDHE_ECDSA_WITH_AES_128_CCM = 0xC0AC; - public const int TLS_ECDHE_ECDSA_WITH_AES_256_CCM = 0xC0AD; - public const int TLS_ECDHE_ECDSA_WITH_AES_128_CCM_8 = 0xC0AE; - public const int TLS_ECDHE_ECDSA_WITH_AES_256_CCM_8 = 0xC0AF; - - /* - * RFC 7507 - */ - public const int TLS_FALLBACK_SCSV = 0x5600; - - /* - * draft-ietf-tls-chacha20-poly1305-04 - */ - public const int DRAFT_TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256 = 0xCCA8; - public const int DRAFT_TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256 = 0xCCA9; - public const int DRAFT_TLS_DHE_RSA_WITH_CHACHA20_POLY1305_SHA256 = 0xCCAA; - public const int DRAFT_TLS_PSK_WITH_CHACHA20_POLY1305_SHA256 = 0xCCAB; - public const int DRAFT_TLS_ECDHE_PSK_WITH_CHACHA20_POLY1305_SHA256 = 0xCCAC; - public const int DRAFT_TLS_DHE_PSK_WITH_CHACHA20_POLY1305_SHA256 = 0xCCAD; - public const int DRAFT_TLS_RSA_PSK_WITH_CHACHA20_POLY1305_SHA256 = 0xCCAE; - - public static bool IsScsv(int cipherSuite) - { - switch (cipherSuite) - { - case TLS_EMPTY_RENEGOTIATION_INFO_SCSV: - case TLS_FALLBACK_SCSV: - return true; - default: - return false; - } - } - } -} diff --git a/crypto/src/crypto/tls/CipherType.cs b/crypto/src/crypto/tls/CipherType.cs deleted file mode 100644 index b2ad7d8e1..000000000 --- a/crypto/src/crypto/tls/CipherType.cs +++ /dev/null @@ -1,20 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary>RFC 2246</summary> - /// <remarks> - /// Note that the values here are implementation-specific and arbitrary. It is recommended not to - /// depend on the particular values (e.g. serialization). - /// </remarks> - public abstract class CipherType - { - public const int stream = 0; - public const int block = 1; - - /* - * RFC 5246 - */ - public const int aead = 2; - } -} diff --git a/crypto/src/crypto/tls/ClientAuthenticationType.cs b/crypto/src/crypto/tls/ClientAuthenticationType.cs deleted file mode 100644 index dd248f3df..000000000 --- a/crypto/src/crypto/tls/ClientAuthenticationType.cs +++ /dev/null @@ -1,14 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class ClientAuthenticationType - { - /* - * RFC 5077 4 - */ - public const byte anonymous = 0; - public const byte certificate_based = 1; - public const byte psk = 2; - } -} diff --git a/crypto/src/crypto/tls/ClientCertificateType.cs b/crypto/src/crypto/tls/ClientCertificateType.cs deleted file mode 100644 index a291a46e6..000000000 --- a/crypto/src/crypto/tls/ClientCertificateType.cs +++ /dev/null @@ -1,23 +0,0 @@ -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class ClientCertificateType - { - /* - * RFC 4346 7.4.4 - */ - public const byte rsa_sign = 1; - public const byte dss_sign = 2; - public const byte rsa_fixed_dh = 3; - public const byte dss_fixed_dh = 4; - public const byte rsa_ephemeral_dh_RESERVED = 5; - public const byte dss_ephemeral_dh_RESERVED = 6; - public const byte fortezza_dms_RESERVED = 20; - - /* - * RFC 4492 5.5 - */ - public const byte ecdsa_sign = 64; - public const byte rsa_fixed_ecdh = 65; - public const byte ecdsa_fixed_ecdh = 66; - } -} diff --git a/crypto/src/crypto/tls/CombinedHash.cs b/crypto/src/crypto/tls/CombinedHash.cs deleted file mode 100644 index 74a52d598..000000000 --- a/crypto/src/crypto/tls/CombinedHash.cs +++ /dev/null @@ -1,133 +0,0 @@ -using System; - -using Org.BouncyCastle.Security; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /** - * A combined hash, which implements md5(m) || sha1(m). - */ - internal class CombinedHash - : TlsHandshakeHash - { - protected TlsContext mContext; - protected IDigest mMd5; - protected IDigest mSha1; - - internal CombinedHash() - { - this.mMd5 = TlsUtilities.CreateHash(HashAlgorithm.md5); - this.mSha1 = TlsUtilities.CreateHash(HashAlgorithm.sha1); - } - - internal CombinedHash(CombinedHash t) - { - this.mContext = t.mContext; - this.mMd5 = TlsUtilities.CloneHash(HashAlgorithm.md5, t.mMd5); - this.mSha1 = TlsUtilities.CloneHash(HashAlgorithm.sha1, t.mSha1); - } - - public virtual void Init(TlsContext context) - { - this.mContext = context; - } - - public virtual TlsHandshakeHash NotifyPrfDetermined() - { - return this; - } - - public virtual void TrackHashAlgorithm(byte hashAlgorithm) - { - throw new InvalidOperationException("CombinedHash only supports calculating the legacy PRF for handshake hash"); - } - - public virtual void SealHashAlgorithms() - { - } - - public virtual TlsHandshakeHash StopTracking() - { - return new CombinedHash(this); - } - - public virtual IDigest ForkPrfHash() - { - return new CombinedHash(this); - } - - public virtual byte[] GetFinalHash(byte hashAlgorithm) - { - throw new InvalidOperationException("CombinedHash doesn't support multiple hashes"); - } - - public virtual string AlgorithmName - { - get { return mMd5.AlgorithmName + " and " + mSha1.AlgorithmName; } - } - - public virtual int GetByteLength() - { - return System.Math.Max(mMd5.GetByteLength(), mSha1.GetByteLength()); - } - - public virtual int GetDigestSize() - { - return mMd5.GetDigestSize() + mSha1.GetDigestSize(); - } - - public virtual void Update(byte input) - { - mMd5.Update(input); - mSha1.Update(input); - } - - /** - * @see org.bouncycastle.crypto.Digest#update(byte[], int, int) - */ - public virtual void BlockUpdate(byte[] input, int inOff, int len) - { - mMd5.BlockUpdate(input, inOff, len); - mSha1.BlockUpdate(input, inOff, len); - } - - /** - * @see org.bouncycastle.crypto.Digest#doFinal(byte[], int) - */ - public virtual int DoFinal(byte[] output, int outOff) - { - if (mContext != null && TlsUtilities.IsSsl(mContext)) - { - Ssl3Complete(mMd5, Ssl3Mac.IPAD, Ssl3Mac.OPAD, 48); - Ssl3Complete(mSha1, Ssl3Mac.IPAD, Ssl3Mac.OPAD, 40); - } - - int i1 = mMd5.DoFinal(output, outOff); - int i2 = mSha1.DoFinal(output, outOff + i1); - return i1 + i2; - } - - /** - * @see org.bouncycastle.crypto.Digest#reset() - */ - public virtual void Reset() - { - mMd5.Reset(); - mSha1.Reset(); - } - - protected virtual void Ssl3Complete(IDigest d, byte[] ipad, byte[] opad, int padLength) - { - byte[] master_secret = mContext.SecurityParameters.masterSecret; - - d.BlockUpdate(master_secret, 0, master_secret.Length); - d.BlockUpdate(ipad, 0, padLength); - - byte[] tmp = DigestUtilities.DoFinal(d); - - d.BlockUpdate(master_secret, 0, master_secret.Length); - d.BlockUpdate(opad, 0, padLength); - d.BlockUpdate(tmp, 0, tmp.Length); - } - } -} diff --git a/crypto/src/crypto/tls/CompressionMethod.cs b/crypto/src/crypto/tls/CompressionMethod.cs deleted file mode 100644 index 89c1f5ff4..000000000 --- a/crypto/src/crypto/tls/CompressionMethod.cs +++ /dev/null @@ -1,22 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary> - /// RFC 2246 6.1 - /// </summary> - public abstract class CompressionMethod - { - public const byte cls_null = 0; - - /* - * RFC 3749 2 - */ - public const byte DEFLATE = 1; - - /* - * Values from 224 decimal (0xE0) through 255 decimal (0xFF) - * inclusive are reserved for private use. - */ - } -} diff --git a/crypto/src/crypto/tls/ConnectionEnd.cs b/crypto/src/crypto/tls/ConnectionEnd.cs deleted file mode 100644 index afc9460f2..000000000 --- a/crypto/src/crypto/tls/ConnectionEnd.cs +++ /dev/null @@ -1,15 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary>RFC 2246</summary> - /// <remarks> - /// Note that the values here are implementation-specific and arbitrary. It is recommended not to - /// depend on the particular values (e.g. serialization). - /// </remarks> - public abstract class ConnectionEnd - { - public const int server = 0; - public const int client = 1; - } -} diff --git a/crypto/src/crypto/tls/ContentType.cs b/crypto/src/crypto/tls/ContentType.cs deleted file mode 100644 index d6ab43857..000000000 --- a/crypto/src/crypto/tls/ContentType.cs +++ /dev/null @@ -1,14 +0,0 @@ -namespace Org.BouncyCastle.Crypto.Tls -{ - /** - * RFC 2246 6.2.1 - */ - public abstract class ContentType - { - public const byte change_cipher_spec = 20; - public const byte alert = 21; - public const byte handshake = 22; - public const byte application_data = 23; - public const byte heartbeat = 24; - } -} diff --git a/crypto/src/crypto/tls/DatagramTransport.cs b/crypto/src/crypto/tls/DatagramTransport.cs deleted file mode 100644 index 42f958d46..000000000 --- a/crypto/src/crypto/tls/DatagramTransport.cs +++ /dev/null @@ -1,21 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public interface DatagramTransport - : TlsCloseable - { - /// <exception cref="IOException"/> - int GetReceiveLimit(); - - /// <exception cref="IOException"/> - int GetSendLimit(); - - /// <exception cref="IOException"/> - int Receive(byte[] buf, int off, int len, int waitMillis); - - /// <exception cref="IOException"/> - void Send(byte[] buf, int off, int len); - } -} diff --git a/crypto/src/crypto/tls/DefaultTlsAgreementCredentials.cs b/crypto/src/crypto/tls/DefaultTlsAgreementCredentials.cs deleted file mode 100644 index fab978886..000000000 --- a/crypto/src/crypto/tls/DefaultTlsAgreementCredentials.cs +++ /dev/null @@ -1,69 +0,0 @@ -using System; -using System.IO; - -using Org.BouncyCastle.Crypto.Agreement; -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Math; -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class DefaultTlsAgreementCredentials - : AbstractTlsAgreementCredentials - { - protected readonly Certificate mCertificate; - protected readonly AsymmetricKeyParameter mPrivateKey; - - protected readonly IBasicAgreement mBasicAgreement; - protected readonly bool mTruncateAgreement; - - public DefaultTlsAgreementCredentials(Certificate certificate, AsymmetricKeyParameter privateKey) - { - if (certificate == null) - throw new ArgumentNullException("certificate"); - if (certificate.IsEmpty) - throw new ArgumentException("cannot be empty", "certificate"); - if (privateKey == null) - throw new ArgumentNullException("privateKey"); - if (!privateKey.IsPrivate) - throw new ArgumentException("must be private", "privateKey"); - - if (privateKey is DHPrivateKeyParameters) - { - mBasicAgreement = new DHBasicAgreement(); - mTruncateAgreement = true; - } - else if (privateKey is ECPrivateKeyParameters) - { - mBasicAgreement = new ECDHBasicAgreement(); - mTruncateAgreement = false; - } - else - { - throw new ArgumentException("type not supported: " + Platform.GetTypeName(privateKey), "privateKey"); - } - - this.mCertificate = certificate; - this.mPrivateKey = privateKey; - } - - public override Certificate Certificate - { - get { return mCertificate; } - } - - /// <exception cref="IOException"></exception> - public override byte[] GenerateAgreement(AsymmetricKeyParameter peerPublicKey) - { - mBasicAgreement.Init(mPrivateKey); - BigInteger agreementValue = mBasicAgreement.CalculateAgreement(peerPublicKey); - - if (mTruncateAgreement) - { - return BigIntegers.AsUnsignedByteArray(agreementValue); - } - - return BigIntegers.AsUnsignedByteArray(mBasicAgreement.GetFieldSize(), agreementValue); - } - } -} diff --git a/crypto/src/crypto/tls/DefaultTlsCipherFactory.cs b/crypto/src/crypto/tls/DefaultTlsCipherFactory.cs deleted file mode 100644 index af0ec126a..000000000 --- a/crypto/src/crypto/tls/DefaultTlsCipherFactory.cs +++ /dev/null @@ -1,227 +0,0 @@ -using System; -using System.IO; - -using Org.BouncyCastle.Crypto.Engines; -using Org.BouncyCastle.Crypto.Modes; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class DefaultTlsCipherFactory - : AbstractTlsCipherFactory - { - /// <exception cref="IOException"></exception> - public override TlsCipher CreateCipher(TlsContext context, int encryptionAlgorithm, int macAlgorithm) - { - switch (encryptionAlgorithm) - { - case EncryptionAlgorithm.cls_3DES_EDE_CBC: - return CreateDesEdeCipher(context, macAlgorithm); - case EncryptionAlgorithm.AES_128_CBC: - return CreateAESCipher(context, 16, macAlgorithm); - case EncryptionAlgorithm.AES_128_CCM: - // NOTE: Ignores macAlgorithm - return CreateCipher_Aes_Ccm(context, 16, 16); - case EncryptionAlgorithm.AES_128_CCM_8: - // NOTE: Ignores macAlgorithm - return CreateCipher_Aes_Ccm(context, 16, 8); - case EncryptionAlgorithm.AES_128_GCM: - // NOTE: Ignores macAlgorithm - return CreateCipher_Aes_Gcm(context, 16, 16); - case EncryptionAlgorithm.AES_128_OCB_TAGLEN96: - // NOTE: Ignores macAlgorithm - return CreateCipher_Aes_Ocb(context, 16, 12); - case EncryptionAlgorithm.AES_256_CBC: - return CreateAESCipher(context, 32, macAlgorithm); - case EncryptionAlgorithm.AES_256_CCM: - // NOTE: Ignores macAlgorithm - return CreateCipher_Aes_Ccm(context, 32, 16); - case EncryptionAlgorithm.AES_256_CCM_8: - // NOTE: Ignores macAlgorithm - return CreateCipher_Aes_Ccm(context, 32, 8); - case EncryptionAlgorithm.AES_256_GCM: - // NOTE: Ignores macAlgorithm - return CreateCipher_Aes_Gcm(context, 32, 16); - case EncryptionAlgorithm.AES_256_OCB_TAGLEN96: - // NOTE: Ignores macAlgorithm - return CreateCipher_Aes_Ocb(context, 32, 12); - case EncryptionAlgorithm.CAMELLIA_128_CBC: - return CreateCamelliaCipher(context, 16, macAlgorithm); - case EncryptionAlgorithm.CAMELLIA_128_GCM: - // NOTE: Ignores macAlgorithm - return CreateCipher_Camellia_Gcm(context, 16, 16); - case EncryptionAlgorithm.CAMELLIA_256_CBC: - return CreateCamelliaCipher(context, 32, macAlgorithm); - case EncryptionAlgorithm.CAMELLIA_256_GCM: - // NOTE: Ignores macAlgorithm - return CreateCipher_Camellia_Gcm(context, 32, 16); - case EncryptionAlgorithm.CHACHA20_POLY1305: - // NOTE: Ignores macAlgorithm - return CreateChaCha20Poly1305(context); - case EncryptionAlgorithm.NULL: - return CreateNullCipher(context, macAlgorithm); - case EncryptionAlgorithm.RC4_128: - return CreateRC4Cipher(context, 16, macAlgorithm); - case EncryptionAlgorithm.SEED_CBC: - return CreateSeedCipher(context, macAlgorithm); - default: - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } - - /// <exception cref="IOException"></exception> - protected virtual TlsBlockCipher CreateAESCipher(TlsContext context, int cipherKeySize, int macAlgorithm) - { - return new TlsBlockCipher(context, CreateAesBlockCipher(), CreateAesBlockCipher(), - CreateHMacDigest(macAlgorithm), CreateHMacDigest(macAlgorithm), cipherKeySize); - } - - /// <exception cref="IOException"></exception> - protected virtual TlsBlockCipher CreateCamelliaCipher(TlsContext context, int cipherKeySize, int macAlgorithm) - { - return new TlsBlockCipher(context, CreateCamelliaBlockCipher(), - CreateCamelliaBlockCipher(), CreateHMacDigest(macAlgorithm), - CreateHMacDigest(macAlgorithm), cipherKeySize); - } - - /// <exception cref="IOException"></exception> - protected virtual TlsCipher CreateChaCha20Poly1305(TlsContext context) - { - return new Chacha20Poly1305(context); - } - - /// <exception cref="IOException"></exception> - protected virtual TlsAeadCipher CreateCipher_Aes_Ccm(TlsContext context, int cipherKeySize, int macSize) - { - return new TlsAeadCipher(context, CreateAeadBlockCipher_Aes_Ccm(), - CreateAeadBlockCipher_Aes_Ccm(), cipherKeySize, macSize); - } - - /// <exception cref="IOException"></exception> - protected virtual TlsAeadCipher CreateCipher_Aes_Gcm(TlsContext context, int cipherKeySize, int macSize) - { - return new TlsAeadCipher(context, CreateAeadBlockCipher_Aes_Gcm(), - CreateAeadBlockCipher_Aes_Gcm(), cipherKeySize, macSize); - } - - /// <exception cref="IOException"></exception> - protected virtual TlsAeadCipher CreateCipher_Aes_Ocb(TlsContext context, int cipherKeySize, int macSize) - { - return new TlsAeadCipher(context, CreateAeadBlockCipher_Aes_Ocb(), - CreateAeadBlockCipher_Aes_Ocb(), cipherKeySize, macSize, TlsAeadCipher.NONCE_DRAFT_CHACHA20_POLY1305); - } - - /// <exception cref="IOException"></exception> - protected virtual TlsAeadCipher CreateCipher_Camellia_Gcm(TlsContext context, int cipherKeySize, int macSize) - { - return new TlsAeadCipher(context, CreateAeadBlockCipher_Camellia_Gcm(), - CreateAeadBlockCipher_Camellia_Gcm(), cipherKeySize, macSize); - } - - /// <exception cref="IOException"></exception> - protected virtual TlsBlockCipher CreateDesEdeCipher(TlsContext context, int macAlgorithm) - { - return new TlsBlockCipher(context, CreateDesEdeBlockCipher(), CreateDesEdeBlockCipher(), - CreateHMacDigest(macAlgorithm), CreateHMacDigest(macAlgorithm), 24); - } - - /// <exception cref="IOException"></exception> - protected virtual TlsNullCipher CreateNullCipher(TlsContext context, int macAlgorithm) - { - return new TlsNullCipher(context, CreateHMacDigest(macAlgorithm), - CreateHMacDigest(macAlgorithm)); - } - - /// <exception cref="IOException"></exception> - protected virtual TlsStreamCipher CreateRC4Cipher(TlsContext context, int cipherKeySize, int macAlgorithm) - { - return new TlsStreamCipher(context, CreateRC4StreamCipher(), CreateRC4StreamCipher(), - CreateHMacDigest(macAlgorithm), CreateHMacDigest(macAlgorithm), cipherKeySize, false); - } - - /// <exception cref="IOException"></exception> - protected virtual TlsBlockCipher CreateSeedCipher(TlsContext context, int macAlgorithm) - { - return new TlsBlockCipher(context, CreateSeedBlockCipher(), CreateSeedBlockCipher(), - CreateHMacDigest(macAlgorithm), CreateHMacDigest(macAlgorithm), 16); - } - - protected virtual IBlockCipher CreateAesEngine() - { - return new AesEngine(); - } - - protected virtual IBlockCipher CreateCamelliaEngine() - { - return new CamelliaEngine(); - } - - protected virtual IBlockCipher CreateAesBlockCipher() - { - return new CbcBlockCipher(CreateAesEngine()); - } - - protected virtual IAeadBlockCipher CreateAeadBlockCipher_Aes_Ccm() - { - return new CcmBlockCipher(CreateAesEngine()); - } - - protected virtual IAeadBlockCipher CreateAeadBlockCipher_Aes_Gcm() - { - // TODO Consider allowing custom configuration of multiplier - return new GcmBlockCipher(CreateAesEngine()); - } - - protected virtual IAeadBlockCipher CreateAeadBlockCipher_Aes_Ocb() - { - return new OcbBlockCipher(CreateAesEngine(), CreateAesEngine()); - } - - protected virtual IAeadBlockCipher CreateAeadBlockCipher_Camellia_Gcm() - { - // TODO Consider allowing custom configuration of multiplier - return new GcmBlockCipher(CreateCamelliaEngine()); - } - - protected virtual IBlockCipher CreateCamelliaBlockCipher() - { - return new CbcBlockCipher(CreateCamelliaEngine()); - } - - protected virtual IBlockCipher CreateDesEdeBlockCipher() - { - return new CbcBlockCipher(new DesEdeEngine()); - } - - protected virtual IStreamCipher CreateRC4StreamCipher() - { - return new RC4Engine(); - } - - protected virtual IBlockCipher CreateSeedBlockCipher() - { - return new CbcBlockCipher(new SeedEngine()); - } - - /// <exception cref="IOException"></exception> - protected virtual IDigest CreateHMacDigest(int macAlgorithm) - { - switch (macAlgorithm) - { - case MacAlgorithm.cls_null: - return null; - case MacAlgorithm.hmac_md5: - return TlsUtilities.CreateHash(HashAlgorithm.md5); - case MacAlgorithm.hmac_sha1: - return TlsUtilities.CreateHash(HashAlgorithm.sha1); - case MacAlgorithm.hmac_sha256: - return TlsUtilities.CreateHash(HashAlgorithm.sha256); - case MacAlgorithm.hmac_sha384: - return TlsUtilities.CreateHash(HashAlgorithm.sha384); - case MacAlgorithm.hmac_sha512: - return TlsUtilities.CreateHash(HashAlgorithm.sha512); - default: - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } - } -} diff --git a/crypto/src/crypto/tls/DefaultTlsClient.cs b/crypto/src/crypto/tls/DefaultTlsClient.cs deleted file mode 100644 index 64d29863b..000000000 --- a/crypto/src/crypto/tls/DefaultTlsClient.cs +++ /dev/null @@ -1,115 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Asn1.X509; -using Org.BouncyCastle.Crypto; -using Org.BouncyCastle.Crypto.Digests; -using Org.BouncyCastle.Crypto.Engines; -using Org.BouncyCastle.Crypto.Modes; -using Org.BouncyCastle.Crypto.Parameters; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class DefaultTlsClient - : AbstractTlsClient - { - protected TlsDHVerifier mDHVerifier; - - public DefaultTlsClient() - : this(new DefaultTlsCipherFactory()) - { - } - - public DefaultTlsClient(TlsCipherFactory cipherFactory) - : this(cipherFactory, new DefaultTlsDHVerifier()) - { - } - - public DefaultTlsClient(TlsCipherFactory cipherFactory, TlsDHVerifier dhVerifier) - : base(cipherFactory) - { - this.mDHVerifier = dhVerifier; - } - - public override int[] GetCipherSuites() - { - return new int[] - { - CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, - CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256, - CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA, - CipherSuite.TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256, - CipherSuite.TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256, - CipherSuite.TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA, - CipherSuite.TLS_RSA_WITH_AES_128_GCM_SHA256, - CipherSuite.TLS_RSA_WITH_AES_128_CBC_SHA256, - CipherSuite.TLS_RSA_WITH_AES_128_CBC_SHA, - }; - } - - public override TlsKeyExchange GetKeyExchange() - { - int keyExchangeAlgorithm = TlsUtilities.GetKeyExchangeAlgorithm(mSelectedCipherSuite); - - switch (keyExchangeAlgorithm) - { - case KeyExchangeAlgorithm.DH_anon: - case KeyExchangeAlgorithm.DH_DSS: - case KeyExchangeAlgorithm.DH_RSA: - return CreateDHKeyExchange(keyExchangeAlgorithm); - - case KeyExchangeAlgorithm.DHE_DSS: - case KeyExchangeAlgorithm.DHE_RSA: - return CreateDheKeyExchange(keyExchangeAlgorithm); - - case KeyExchangeAlgorithm.ECDH_anon: - case KeyExchangeAlgorithm.ECDH_ECDSA: - case KeyExchangeAlgorithm.ECDH_RSA: - return CreateECDHKeyExchange(keyExchangeAlgorithm); - - case KeyExchangeAlgorithm.ECDHE_ECDSA: - case KeyExchangeAlgorithm.ECDHE_RSA: - return CreateECDheKeyExchange(keyExchangeAlgorithm); - - case KeyExchangeAlgorithm.RSA: - return CreateRsaKeyExchange(); - - default: - /* - * Note: internal error here; the TlsProtocol implementation verifies that the - * server-selected cipher suite was in the list of client-offered cipher suites, so if - * we now can't produce an implementation, we shouldn't have offered it! - */ - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } - - protected virtual TlsKeyExchange CreateDHKeyExchange(int keyExchange) - { - return new TlsDHKeyExchange(keyExchange, mSupportedSignatureAlgorithms, mDHVerifier, null); - } - - protected virtual TlsKeyExchange CreateDheKeyExchange(int keyExchange) - { - return new TlsDheKeyExchange(keyExchange, mSupportedSignatureAlgorithms, mDHVerifier, null); - } - - protected virtual TlsKeyExchange CreateECDHKeyExchange(int keyExchange) - { - return new TlsECDHKeyExchange(keyExchange, mSupportedSignatureAlgorithms, mNamedCurves, mClientECPointFormats, - mServerECPointFormats); - } - - protected virtual TlsKeyExchange CreateECDheKeyExchange(int keyExchange) - { - return new TlsECDheKeyExchange(keyExchange, mSupportedSignatureAlgorithms, mNamedCurves, mClientECPointFormats, - mServerECPointFormats); - } - - protected virtual TlsKeyExchange CreateRsaKeyExchange() - { - return new TlsRsaKeyExchange(mSupportedSignatureAlgorithms); - } - } -} diff --git a/crypto/src/crypto/tls/DefaultTlsDHVerifier.cs b/crypto/src/crypto/tls/DefaultTlsDHVerifier.cs deleted file mode 100644 index ae26d04c3..000000000 --- a/crypto/src/crypto/tls/DefaultTlsDHVerifier.cs +++ /dev/null @@ -1,101 +0,0 @@ -using System; -using System.Collections; - -using Org.BouncyCastle.Crypto.Agreement; -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Math; -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class DefaultTlsDHVerifier - : TlsDHVerifier - { - public static readonly int DefaultMinimumPrimeBits = 2048; - - protected static readonly IList DefaultGroups = Platform.CreateArrayList(); - - private static void AddDefaultGroup(DHParameters dhParameters) - { - DefaultGroups.Add(dhParameters); - } - - static DefaultTlsDHVerifier() - { - AddDefaultGroup(DHStandardGroups.rfc7919_ffdhe2048); - AddDefaultGroup(DHStandardGroups.rfc7919_ffdhe3072); - AddDefaultGroup(DHStandardGroups.rfc7919_ffdhe4096); - AddDefaultGroup(DHStandardGroups.rfc7919_ffdhe6144); - AddDefaultGroup(DHStandardGroups.rfc7919_ffdhe8192); - - AddDefaultGroup(DHStandardGroups.rfc3526_1536); - AddDefaultGroup(DHStandardGroups.rfc3526_2048); - AddDefaultGroup(DHStandardGroups.rfc3526_3072); - AddDefaultGroup(DHStandardGroups.rfc3526_4096); - AddDefaultGroup(DHStandardGroups.rfc3526_6144); - AddDefaultGroup(DHStandardGroups.rfc3526_8192); - } - - // IList is (DHParameters) - protected readonly IList mGroups; - protected readonly int mMinimumPrimeBits; - - /// <summary>Accept various standard DH groups with 'P' at least <c>DefaultMinimumPrimeBits</c> bits.</summary> - public DefaultTlsDHVerifier() - : this(DefaultMinimumPrimeBits) - { - } - - /// <summary>Accept various standard DH groups with 'P' at least the specified number of bits.</summary> - public DefaultTlsDHVerifier(int minimumPrimeBits) - : this(DefaultGroups, minimumPrimeBits) - { - } - - /// <summary>Accept a custom set of group parameters, subject to a minimum bitlength for 'P'.</summary> - /// <param name="groups">An <c>IList</c> of acceptable <c>DHParameters</c>.</param> - /// <param name="minimumPrimeBits">The minimum acceptable bitlength of the 'P' parameter.</param> - public DefaultTlsDHVerifier(IList groups, int minimumPrimeBits) - { - this.mGroups = groups; - this.mMinimumPrimeBits = minimumPrimeBits; - } - - public virtual bool Accept(DHParameters dhParameters) - { - return CheckMinimumPrimeBits(dhParameters) && CheckGroup(dhParameters); - } - - public virtual int MinimumPrimeBits - { - get { return mMinimumPrimeBits; } - } - - protected virtual bool AreGroupsEqual(DHParameters a, DHParameters b) - { - return a == b || (AreParametersEqual(a.P, b.P) && AreParametersEqual(a.G, b.G)); - } - - protected virtual bool AreParametersEqual(BigInteger a, BigInteger b) - { - return a == b || a.Equals(b); - } - - protected virtual bool CheckGroup(DHParameters dhParameters) - { - foreach (DHParameters group in mGroups) - { - if (AreGroupsEqual(dhParameters, group)) - { - return true; - } - } - return false; - } - - protected virtual bool CheckMinimumPrimeBits(DHParameters dhParameters) - { - return dhParameters.P.BitLength >= MinimumPrimeBits; - } - } -} diff --git a/crypto/src/crypto/tls/DefaultTlsEncryptionCredentials.cs b/crypto/src/crypto/tls/DefaultTlsEncryptionCredentials.cs deleted file mode 100644 index 5348ee88d..000000000 --- a/crypto/src/crypto/tls/DefaultTlsEncryptionCredentials.cs +++ /dev/null @@ -1,52 +0,0 @@ -using System; -using System.IO; - -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class DefaultTlsEncryptionCredentials - : AbstractTlsEncryptionCredentials - { - protected readonly TlsContext mContext; - protected readonly Certificate mCertificate; - protected readonly AsymmetricKeyParameter mPrivateKey; - - public DefaultTlsEncryptionCredentials(TlsContext context, Certificate certificate, - AsymmetricKeyParameter privateKey) - { - if (certificate == null) - throw new ArgumentNullException("certificate"); - if (certificate.IsEmpty) - throw new ArgumentException("cannot be empty", "certificate"); - if (privateKey == null) - throw new ArgumentNullException("'privateKey' cannot be null"); - if (!privateKey.IsPrivate) - throw new ArgumentException("must be private", "privateKey"); - - if (privateKey is RsaKeyParameters) - { - } - else - { - throw new ArgumentException("type not supported: " + Platform.GetTypeName(privateKey), "privateKey"); - } - - this.mContext = context; - this.mCertificate = certificate; - this.mPrivateKey = privateKey; - } - - public override Certificate Certificate - { - get { return mCertificate; } - } - - /// <exception cref="IOException"></exception> - public override byte[] DecryptPreMasterSecret(byte[] encryptedPreMasterSecret) - { - return TlsRsaUtilities.SafeDecryptPreMasterSecret(mContext, (RsaKeyParameters)mPrivateKey, encryptedPreMasterSecret); - } - } -} diff --git a/crypto/src/crypto/tls/DefaultTlsServer.cs b/crypto/src/crypto/tls/DefaultTlsServer.cs deleted file mode 100644 index 90f357687..000000000 --- a/crypto/src/crypto/tls/DefaultTlsServer.cs +++ /dev/null @@ -1,166 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Crypto.Agreement; -using Org.BouncyCastle.Crypto.Parameters; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class DefaultTlsServer - : AbstractTlsServer - { - public DefaultTlsServer() - : base() - { - } - - public DefaultTlsServer(TlsCipherFactory cipherFactory) - : base(cipherFactory) - { - } - - protected virtual TlsSignerCredentials GetDsaSignerCredentials() - { - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - protected virtual TlsSignerCredentials GetECDsaSignerCredentials() - { - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - protected virtual TlsEncryptionCredentials GetRsaEncryptionCredentials() - { - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - protected virtual TlsSignerCredentials GetRsaSignerCredentials() - { - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - protected virtual DHParameters GetDHParameters() - { - return DHStandardGroups.rfc7919_ffdhe2048; - } - - protected override int[] GetCipherSuites() - { - return new int[] - { - CipherSuite.TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384, - CipherSuite.TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256, - CipherSuite.TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384, - CipherSuite.TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256, - CipherSuite.TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA, - CipherSuite.TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA, - CipherSuite.TLS_DHE_RSA_WITH_AES_256_GCM_SHA384, - CipherSuite.TLS_DHE_RSA_WITH_AES_128_GCM_SHA256, - CipherSuite.TLS_DHE_RSA_WITH_AES_256_CBC_SHA256, - CipherSuite.TLS_DHE_RSA_WITH_AES_128_CBC_SHA256, - CipherSuite.TLS_DHE_RSA_WITH_AES_256_CBC_SHA, - CipherSuite.TLS_DHE_RSA_WITH_AES_128_CBC_SHA, - CipherSuite.TLS_RSA_WITH_AES_256_GCM_SHA384, - CipherSuite.TLS_RSA_WITH_AES_128_GCM_SHA256, - CipherSuite.TLS_RSA_WITH_AES_256_CBC_SHA256, - CipherSuite.TLS_RSA_WITH_AES_128_CBC_SHA256, - CipherSuite.TLS_RSA_WITH_AES_256_CBC_SHA, - CipherSuite.TLS_RSA_WITH_AES_128_CBC_SHA, - }; - } - - public override TlsCredentials GetCredentials() - { - int keyExchangeAlgorithm = TlsUtilities.GetKeyExchangeAlgorithm(mSelectedCipherSuite); - - switch (keyExchangeAlgorithm) - { - case KeyExchangeAlgorithm.DHE_DSS: - return GetDsaSignerCredentials(); - - case KeyExchangeAlgorithm.DH_anon: - case KeyExchangeAlgorithm.ECDH_anon: - return null; - - case KeyExchangeAlgorithm.ECDHE_ECDSA: - return GetECDsaSignerCredentials(); - - case KeyExchangeAlgorithm.DHE_RSA: - case KeyExchangeAlgorithm.ECDHE_RSA: - return GetRsaSignerCredentials(); - - case KeyExchangeAlgorithm.RSA: - return GetRsaEncryptionCredentials(); - - default: - /* Note: internal error here; selected a key exchange we don't implement! */ - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } - - public override TlsKeyExchange GetKeyExchange() - { - int keyExchangeAlgorithm = TlsUtilities.GetKeyExchangeAlgorithm(mSelectedCipherSuite); - - switch (keyExchangeAlgorithm) - { - case KeyExchangeAlgorithm.DH_anon: - case KeyExchangeAlgorithm.DH_DSS: - case KeyExchangeAlgorithm.DH_RSA: - return CreateDHKeyExchange(keyExchangeAlgorithm); - - case KeyExchangeAlgorithm.DHE_DSS: - case KeyExchangeAlgorithm.DHE_RSA: - return CreateDheKeyExchange(keyExchangeAlgorithm); - - case KeyExchangeAlgorithm.ECDH_anon: - case KeyExchangeAlgorithm.ECDH_ECDSA: - case KeyExchangeAlgorithm.ECDH_RSA: - return CreateECDHKeyExchange(keyExchangeAlgorithm); - - case KeyExchangeAlgorithm.ECDHE_ECDSA: - case KeyExchangeAlgorithm.ECDHE_RSA: - return CreateECDheKeyExchange(keyExchangeAlgorithm); - - case KeyExchangeAlgorithm.RSA: - return CreateRsaKeyExchange(); - - default: - /* - * Note: internal error here; the TlsProtocol implementation verifies that the - * server-selected cipher suite was in the list of client-offered cipher suites, so if - * we now can't produce an implementation, we shouldn't have offered it! - */ - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } - - protected virtual TlsKeyExchange CreateDHKeyExchange(int keyExchange) - { - return new TlsDHKeyExchange(keyExchange, mSupportedSignatureAlgorithms, null, GetDHParameters()); - } - - protected virtual TlsKeyExchange CreateDheKeyExchange(int keyExchange) - { - return new TlsDheKeyExchange(keyExchange, mSupportedSignatureAlgorithms, null, GetDHParameters()); - } - - protected virtual TlsKeyExchange CreateECDHKeyExchange(int keyExchange) - { - return new TlsECDHKeyExchange(keyExchange, mSupportedSignatureAlgorithms, mNamedCurves, mClientECPointFormats, - mServerECPointFormats); - } - - protected virtual TlsKeyExchange CreateECDheKeyExchange(int keyExchange) - { - return new TlsECDheKeyExchange(keyExchange, mSupportedSignatureAlgorithms, mNamedCurves, mClientECPointFormats, - mServerECPointFormats); - } - - protected virtual TlsKeyExchange CreateRsaKeyExchange() - { - return new TlsRsaKeyExchange(mSupportedSignatureAlgorithms); - } - } -} diff --git a/crypto/src/crypto/tls/DefaultTlsSignerCredentials.cs b/crypto/src/crypto/tls/DefaultTlsSignerCredentials.cs deleted file mode 100644 index 0ff732a97..000000000 --- a/crypto/src/crypto/tls/DefaultTlsSignerCredentials.cs +++ /dev/null @@ -1,93 +0,0 @@ -using System; -using System.IO; - -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class DefaultTlsSignerCredentials - : AbstractTlsSignerCredentials - { - protected readonly TlsContext mContext; - protected readonly Certificate mCertificate; - protected readonly AsymmetricKeyParameter mPrivateKey; - protected readonly SignatureAndHashAlgorithm mSignatureAndHashAlgorithm; - - protected readonly TlsSigner mSigner; - - public DefaultTlsSignerCredentials(TlsContext context, Certificate certificate, AsymmetricKeyParameter privateKey) - : this(context, certificate, privateKey, null) - { - } - - public DefaultTlsSignerCredentials(TlsContext context, Certificate certificate, AsymmetricKeyParameter privateKey, - SignatureAndHashAlgorithm signatureAndHashAlgorithm) - { - if (certificate == null) - throw new ArgumentNullException("certificate"); - if (certificate.IsEmpty) - throw new ArgumentException("cannot be empty", "clientCertificate"); - if (privateKey == null) - throw new ArgumentNullException("privateKey"); - if (!privateKey.IsPrivate) - throw new ArgumentException("must be private", "privateKey"); - if (TlsUtilities.IsTlsV12(context) && signatureAndHashAlgorithm == null) - throw new ArgumentException("cannot be null for (D)TLS 1.2+", "signatureAndHashAlgorithm"); - - if (privateKey is RsaKeyParameters) - { - mSigner = new TlsRsaSigner(); - } - else if (privateKey is DsaPrivateKeyParameters) - { - mSigner = new TlsDssSigner(); - } - else if (privateKey is ECPrivateKeyParameters) - { - mSigner = new TlsECDsaSigner(); - } - else - { - throw new ArgumentException("type not supported: " + Platform.GetTypeName(privateKey), "privateKey"); - } - - this.mSigner.Init(context); - - this.mContext = context; - this.mCertificate = certificate; - this.mPrivateKey = privateKey; - this.mSignatureAndHashAlgorithm = signatureAndHashAlgorithm; - } - - public override Certificate Certificate - { - get { return mCertificate; } - } - - /// <exception cref="IOException"></exception> - public override byte[] GenerateCertificateSignature(byte[] hash) - { - try - { - if (TlsUtilities.IsTlsV12(mContext)) - { - return mSigner.GenerateRawSignature(mSignatureAndHashAlgorithm, mPrivateKey, hash); - } - else - { - return mSigner.GenerateRawSignature(mPrivateKey, hash); - } - } - catch (CryptoException e) - { - throw new TlsFatalAlert(AlertDescription.internal_error, e); - } - } - - public override SignatureAndHashAlgorithm SignatureAndHashAlgorithm - { - get { return mSignatureAndHashAlgorithm; } - } - } -} diff --git a/crypto/src/crypto/tls/DefaultTlsSrpGroupVerifier.cs b/crypto/src/crypto/tls/DefaultTlsSrpGroupVerifier.cs deleted file mode 100644 index cc933bff9..000000000 --- a/crypto/src/crypto/tls/DefaultTlsSrpGroupVerifier.cs +++ /dev/null @@ -1,70 +0,0 @@ -using System; -using System.Collections; - -using Org.BouncyCastle.Crypto.Agreement.Srp; -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Math; -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class DefaultTlsSrpGroupVerifier - : TlsSrpGroupVerifier - { - protected static readonly IList DefaultGroups = Platform.CreateArrayList(); - - static DefaultTlsSrpGroupVerifier() - { - DefaultGroups.Add(Srp6StandardGroups.rfc5054_1024); - DefaultGroups.Add(Srp6StandardGroups.rfc5054_1536); - DefaultGroups.Add(Srp6StandardGroups.rfc5054_2048); - DefaultGroups.Add(Srp6StandardGroups.rfc5054_3072); - DefaultGroups.Add(Srp6StandardGroups.rfc5054_4096); - DefaultGroups.Add(Srp6StandardGroups.rfc5054_6144); - DefaultGroups.Add(Srp6StandardGroups.rfc5054_8192); - } - - // Vector is (SRP6GroupParameters) - protected readonly IList mGroups; - - /** - * Accept only the group parameters specified in RFC 5054 Appendix A. - */ - public DefaultTlsSrpGroupVerifier() - : this(DefaultGroups) - { - } - - /** - * Specify a custom set of acceptable group parameters. - * - * @param groups a {@link Vector} of acceptable {@link SRP6GroupParameters} - */ - public DefaultTlsSrpGroupVerifier(IList groups) - { - this.mGroups = groups; - } - - public virtual bool Accept(Srp6GroupParameters group) - { - foreach (Srp6GroupParameters entry in mGroups) - { - if (AreGroupsEqual(group, entry)) - { - return true; - } - } - return false; - } - - protected virtual bool AreGroupsEqual(Srp6GroupParameters a, Srp6GroupParameters b) - { - return a == b || (AreParametersEqual(a.N, b.N) && AreParametersEqual(a.G, b.G)); - } - - protected virtual bool AreParametersEqual(BigInteger a, BigInteger b) - { - return a == b || a.Equals(b); - } - } -} diff --git a/crypto/src/crypto/tls/DeferredHash.cs b/crypto/src/crypto/tls/DeferredHash.cs deleted file mode 100644 index f402f26d2..000000000 --- a/crypto/src/crypto/tls/DeferredHash.cs +++ /dev/null @@ -1,201 +0,0 @@ -using System; -using System.Collections; - -using Org.BouncyCastle.Security; -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /** - * Buffers input until the hash algorithm is determined. - */ - internal class DeferredHash - : TlsHandshakeHash - { - protected const int BUFFERING_HASH_LIMIT = 4; - - protected TlsContext mContext; - - private DigestInputBuffer mBuf; - private IDictionary mHashes; - private int mPrfHashAlgorithm; - - internal DeferredHash() - { - this.mBuf = new DigestInputBuffer(); - this.mHashes = Platform.CreateHashtable(); - this.mPrfHashAlgorithm = -1; - } - - private DeferredHash(byte prfHashAlgorithm, IDigest prfHash) - { - this.mBuf = null; - this.mHashes = Platform.CreateHashtable(); - this.mPrfHashAlgorithm = prfHashAlgorithm; - mHashes[prfHashAlgorithm] = prfHash; - } - - public virtual void Init(TlsContext context) - { - this.mContext = context; - } - - public virtual TlsHandshakeHash NotifyPrfDetermined() - { - int prfAlgorithm = mContext.SecurityParameters.PrfAlgorithm; - if (prfAlgorithm == PrfAlgorithm.tls_prf_legacy) - { - CombinedHash legacyHash = new CombinedHash(); - legacyHash.Init(mContext); - mBuf.UpdateDigest(legacyHash); - return legacyHash.NotifyPrfDetermined(); - } - - this.mPrfHashAlgorithm = TlsUtilities.GetHashAlgorithmForPrfAlgorithm(prfAlgorithm); - - CheckTrackingHash((byte)mPrfHashAlgorithm); - - return this; - } - - public virtual void TrackHashAlgorithm(byte hashAlgorithm) - { - if (mBuf == null) - throw new InvalidOperationException("Too late to track more hash algorithms"); - - CheckTrackingHash(hashAlgorithm); - } - - public virtual void SealHashAlgorithms() - { - CheckStopBuffering(); - } - - public virtual TlsHandshakeHash StopTracking() - { - byte prfHashAlgorithm = (byte)mPrfHashAlgorithm; - IDigest prfHash = TlsUtilities.CloneHash(prfHashAlgorithm, (IDigest)mHashes[prfHashAlgorithm]); - if (mBuf != null) - { - mBuf.UpdateDigest(prfHash); - } - DeferredHash result = new DeferredHash(prfHashAlgorithm, prfHash); - result.Init(mContext); - return result; - } - - public virtual IDigest ForkPrfHash() - { - CheckStopBuffering(); - - byte prfHashAlgorithm = (byte)mPrfHashAlgorithm; - if (mBuf != null) - { - IDigest prfHash = TlsUtilities.CreateHash(prfHashAlgorithm); - mBuf.UpdateDigest(prfHash); - return prfHash; - } - - return TlsUtilities.CloneHash(prfHashAlgorithm, (IDigest)mHashes[prfHashAlgorithm]); - } - - public virtual byte[] GetFinalHash(byte hashAlgorithm) - { - IDigest d = (IDigest)mHashes[hashAlgorithm]; - if (d == null) - throw new InvalidOperationException("HashAlgorithm." + HashAlgorithm.GetText(hashAlgorithm) + " is not being tracked"); - - d = TlsUtilities.CloneHash(hashAlgorithm, d); - if (mBuf != null) - { - mBuf.UpdateDigest(d); - } - - return DigestUtilities.DoFinal(d); - } - - public virtual string AlgorithmName - { - get { throw new InvalidOperationException("Use Fork() to get a definite IDigest"); } - } - - public virtual int GetByteLength() - { - throw new InvalidOperationException("Use Fork() to get a definite IDigest"); - } - - public virtual int GetDigestSize() - { - throw new InvalidOperationException("Use Fork() to get a definite IDigest"); - } - - public virtual void Update(byte input) - { - if (mBuf != null) - { - mBuf.WriteByte(input); - return; - } - - foreach (IDigest hash in mHashes.Values) - { - hash.Update(input); - } - } - - public virtual void BlockUpdate(byte[] input, int inOff, int len) - { - if (mBuf != null) - { - mBuf.Write(input, inOff, len); - return; - } - - foreach (IDigest hash in mHashes.Values) - { - hash.BlockUpdate(input, inOff, len); - } - } - - public virtual int DoFinal(byte[] output, int outOff) - { - throw new InvalidOperationException("Use Fork() to get a definite IDigest"); - } - - public virtual void Reset() - { - if (mBuf != null) - { - mBuf.SetLength(0); - return; - } - - foreach (IDigest hash in mHashes.Values) - { - hash.Reset(); - } - } - - protected virtual void CheckStopBuffering() - { - if (mBuf != null && mHashes.Count <= BUFFERING_HASH_LIMIT) - { - foreach (IDigest hash in mHashes.Values) - { - mBuf.UpdateDigest(hash); - } - - this.mBuf = null; - } - } - - protected virtual void CheckTrackingHash(byte hashAlgorithm) - { - if (!mHashes.Contains(hashAlgorithm)) - { - IDigest hash = TlsUtilities.CreateHash(hashAlgorithm); - mHashes[hashAlgorithm] = hash; - } - } - } -} diff --git a/crypto/src/crypto/tls/DigestInputBuffer.cs b/crypto/src/crypto/tls/DigestInputBuffer.cs deleted file mode 100644 index acc6756e4..000000000 --- a/crypto/src/crypto/tls/DigestInputBuffer.cs +++ /dev/null @@ -1,17 +0,0 @@ -using System; -using System.IO; - -using Org.BouncyCastle.Crypto.IO; -using Org.BouncyCastle.Utilities.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - internal class DigestInputBuffer - : MemoryStream - { - internal void UpdateDigest(IDigest d) - { - Streams.WriteBufTo(this, new DigestSink(d)); - } - } -} diff --git a/crypto/src/crypto/tls/DigitallySigned.cs b/crypto/src/crypto/tls/DigitallySigned.cs deleted file mode 100644 index 8b7344fd9..000000000 --- a/crypto/src/crypto/tls/DigitallySigned.cs +++ /dev/null @@ -1,70 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class DigitallySigned - { - protected readonly SignatureAndHashAlgorithm mAlgorithm; - protected readonly byte[] mSignature; - - public DigitallySigned(SignatureAndHashAlgorithm algorithm, byte[] signature) - { - if (signature == null) - throw new ArgumentNullException("signature"); - - this.mAlgorithm = algorithm; - this.mSignature = signature; - } - - /** - * @return a {@link SignatureAndHashAlgorithm} (or null before TLS 1.2). - */ - public virtual SignatureAndHashAlgorithm Algorithm - { - get { return mAlgorithm; } - } - - public virtual byte[] Signature - { - get { return mSignature; } - } - - /** - * Encode this {@link DigitallySigned} to a {@link Stream}. - * - * @param output - * the {@link Stream} to encode to. - * @throws IOException - */ - public virtual void Encode(Stream output) - { - if (mAlgorithm != null) - { - mAlgorithm.Encode(output); - } - TlsUtilities.WriteOpaque16(mSignature, output); - } - - /** - * Parse a {@link DigitallySigned} from a {@link Stream}. - * - * @param context - * the {@link TlsContext} of the current connection. - * @param input - * the {@link Stream} to parse from. - * @return a {@link DigitallySigned} object. - * @throws IOException - */ - public static DigitallySigned Parse(TlsContext context, Stream input) - { - SignatureAndHashAlgorithm algorithm = null; - if (TlsUtilities.IsTlsV12(context)) - { - algorithm = SignatureAndHashAlgorithm.Parse(input); - } - byte[] signature = TlsUtilities.ReadOpaque16(input); - return new DigitallySigned(algorithm, signature); - } - } -} diff --git a/crypto/src/crypto/tls/DtlsClientProtocol.cs b/crypto/src/crypto/tls/DtlsClientProtocol.cs deleted file mode 100644 index fe6381dfa..000000000 --- a/crypto/src/crypto/tls/DtlsClientProtocol.cs +++ /dev/null @@ -1,864 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Security; -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class DtlsClientProtocol - : DtlsProtocol - { - public DtlsClientProtocol(SecureRandom secureRandom) - : base(secureRandom) - { - } - - public virtual DtlsTransport Connect(TlsClient client, DatagramTransport transport) - { - if (client == null) - throw new ArgumentNullException("client"); - if (transport == null) - throw new ArgumentNullException("transport"); - - SecurityParameters securityParameters = new SecurityParameters(); - securityParameters.entity = ConnectionEnd.client; - - ClientHandshakeState state = new ClientHandshakeState(); - state.client = client; - state.clientContext = new TlsClientContextImpl(mSecureRandom, securityParameters); - - securityParameters.clientRandom = TlsProtocol.CreateRandomBlock(client.ShouldUseGmtUnixTime(), - state.clientContext.NonceRandomGenerator); - - client.Init(state.clientContext); - - DtlsRecordLayer recordLayer = new DtlsRecordLayer(transport, state.clientContext, client, ContentType.handshake); - client.NotifyCloseHandle(recordLayer); - - TlsSession sessionToResume = state.client.GetSessionToResume(); - if (sessionToResume != null && sessionToResume.IsResumable) - { - SessionParameters sessionParameters = sessionToResume.ExportSessionParameters(); - if (sessionParameters != null && sessionParameters.IsExtendedMasterSecret) - { - state.tlsSession = sessionToResume; - state.sessionParameters = sessionParameters; - } - } - - try - { - return ClientHandshake(state, recordLayer); - } - catch (TlsFatalAlert fatalAlert) - { - AbortClientHandshake(state, recordLayer, fatalAlert.AlertDescription); - throw fatalAlert; - } - catch (IOException e) - { - AbortClientHandshake(state, recordLayer, AlertDescription.internal_error); - throw e; - } - catch (Exception e) - { - AbortClientHandshake(state, recordLayer, AlertDescription.internal_error); - throw new TlsFatalAlert(AlertDescription.internal_error, e); - } - finally - { - securityParameters.Clear(); - } - } - - internal virtual void AbortClientHandshake(ClientHandshakeState state, DtlsRecordLayer recordLayer, byte alertDescription) - { - recordLayer.Fail(alertDescription); - InvalidateSession(state); - } - - internal virtual DtlsTransport ClientHandshake(ClientHandshakeState state, DtlsRecordLayer recordLayer) - { - SecurityParameters securityParameters = state.clientContext.SecurityParameters; - DtlsReliableHandshake handshake = new DtlsReliableHandshake(state.clientContext, recordLayer, - state.client.GetHandshakeTimeoutMillis()); - - byte[] clientHelloBody = GenerateClientHello(state, state.client); - - recordLayer.SetWriteVersion(ProtocolVersion.DTLSv10); - - handshake.SendMessage(HandshakeType.client_hello, clientHelloBody); - - DtlsReliableHandshake.Message serverMessage = handshake.ReceiveMessage(); - - while (serverMessage.Type == HandshakeType.hello_verify_request) - { - ProtocolVersion recordLayerVersion = recordLayer.ReadVersion; - ProtocolVersion client_version = state.clientContext.ClientVersion; - - /* - * RFC 6347 4.2.1 DTLS 1.2 server implementations SHOULD use DTLS version 1.0 regardless of - * the version of TLS that is expected to be negotiated. DTLS 1.2 and 1.0 clients MUST use - * the version solely to indicate packet formatting (which is the same in both DTLS 1.2 and - * 1.0) and not as part of version negotiation. - */ - if (!recordLayerVersion.IsEqualOrEarlierVersionOf(client_version)) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - - recordLayer.ReadVersion = null; - - byte[] cookie = ProcessHelloVerifyRequest(state, serverMessage.Body); - byte[] patched = PatchClientHelloWithCookie(clientHelloBody, cookie); - - handshake.ResetHandshakeMessagesDigest(); - handshake.SendMessage(HandshakeType.client_hello, patched); - - serverMessage = handshake.ReceiveMessage(); - } - - if (serverMessage.Type == HandshakeType.server_hello) - { - ProtocolVersion recordLayerVersion = recordLayer.ReadVersion; - ReportServerVersion(state, recordLayerVersion); - recordLayer.SetWriteVersion(recordLayerVersion); - - ProcessServerHello(state, serverMessage.Body); - } - else - { - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - - handshake.NotifyHelloComplete(); - - ApplyMaxFragmentLengthExtension(recordLayer, securityParameters.maxFragmentLength); - - if (state.resumedSession) - { - securityParameters.masterSecret = Arrays.Clone(state.sessionParameters.MasterSecret); - recordLayer.InitPendingEpoch(state.client.GetCipher()); - - // NOTE: Calculated exclusive of the actual Finished message from the server - byte[] resExpectedServerVerifyData = TlsUtilities.CalculateVerifyData(state.clientContext, ExporterLabel.server_finished, - TlsProtocol.GetCurrentPrfHash(state.clientContext, handshake.HandshakeHash, null)); - ProcessFinished(handshake.ReceiveMessageBody(HandshakeType.finished), resExpectedServerVerifyData); - - // NOTE: Calculated exclusive of the Finished message itself - byte[] resClientVerifyData = TlsUtilities.CalculateVerifyData(state.clientContext, ExporterLabel.client_finished, - TlsProtocol.GetCurrentPrfHash(state.clientContext, handshake.HandshakeHash, null)); - handshake.SendMessage(HandshakeType.finished, resClientVerifyData); - - handshake.Finish(); - - state.clientContext.SetResumableSession(state.tlsSession); - - state.client.NotifyHandshakeComplete(); - - return new DtlsTransport(recordLayer); - } - - InvalidateSession(state); - - if (state.selectedSessionID.Length > 0) - { - state.tlsSession = new TlsSessionImpl(state.selectedSessionID, null); - } - - serverMessage = handshake.ReceiveMessage(); - - if (serverMessage.Type == HandshakeType.supplemental_data) - { - ProcessServerSupplementalData(state, serverMessage.Body); - serverMessage = handshake.ReceiveMessage(); - } - else - { - state.client.ProcessServerSupplementalData(null); - } - - state.keyExchange = state.client.GetKeyExchange(); - state.keyExchange.Init(state.clientContext); - - Certificate serverCertificate = null; - - if (serverMessage.Type == HandshakeType.certificate) - { - serverCertificate = ProcessServerCertificate(state, serverMessage.Body); - serverMessage = handshake.ReceiveMessage(); - } - else - { - // Okay, Certificate is optional - state.keyExchange.SkipServerCredentials(); - } - - // TODO[RFC 3546] Check whether empty certificates is possible, allowed, or excludes CertificateStatus - if (serverCertificate == null || serverCertificate.IsEmpty) - { - state.allowCertificateStatus = false; - } - - if (serverMessage.Type == HandshakeType.certificate_status) - { - ProcessCertificateStatus(state, serverMessage.Body); - serverMessage = handshake.ReceiveMessage(); - } - else - { - // Okay, CertificateStatus is optional - } - - if (serverMessage.Type == HandshakeType.server_key_exchange) - { - ProcessServerKeyExchange(state, serverMessage.Body); - serverMessage = handshake.ReceiveMessage(); - } - else - { - // Okay, ServerKeyExchange is optional - state.keyExchange.SkipServerKeyExchange(); - } - - if (serverMessage.Type == HandshakeType.certificate_request) - { - ProcessCertificateRequest(state, serverMessage.Body); - - /* - * TODO Give the client a chance to immediately select the CertificateVerify hash - * algorithm here to avoid tracking the other hash algorithms unnecessarily? - */ - TlsUtilities.TrackHashAlgorithms(handshake.HandshakeHash, - state.certificateRequest.SupportedSignatureAlgorithms); - - serverMessage = handshake.ReceiveMessage(); - } - else - { - // Okay, CertificateRequest is optional - } - - if (serverMessage.Type == HandshakeType.server_hello_done) - { - if (serverMessage.Body.Length != 0) - { - throw new TlsFatalAlert(AlertDescription.decode_error); - } - } - else - { - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - - handshake.HandshakeHash.SealHashAlgorithms(); - - IList clientSupplementalData = state.client.GetClientSupplementalData(); - if (clientSupplementalData != null) - { - byte[] supplementalDataBody = GenerateSupplementalData(clientSupplementalData); - handshake.SendMessage(HandshakeType.supplemental_data, supplementalDataBody); - } - - if (state.certificateRequest != null) - { - state.clientCredentials = state.authentication.GetClientCredentials(state.certificateRequest); - - /* - * RFC 5246 If no suitable certificate is available, the client MUST send a certificate - * message containing no certificates. - * - * NOTE: In previous RFCs, this was SHOULD instead of MUST. - */ - Certificate clientCertificate = null; - if (state.clientCredentials != null) - { - clientCertificate = state.clientCredentials.Certificate; - } - if (clientCertificate == null) - { - clientCertificate = Certificate.EmptyChain; - } - - byte[] certificateBody = GenerateCertificate(clientCertificate); - handshake.SendMessage(HandshakeType.certificate, certificateBody); - } - - if (state.clientCredentials != null) - { - state.keyExchange.ProcessClientCredentials(state.clientCredentials); - } - else - { - state.keyExchange.SkipClientCredentials(); - } - - byte[] clientKeyExchangeBody = GenerateClientKeyExchange(state); - handshake.SendMessage(HandshakeType.client_key_exchange, clientKeyExchangeBody); - - TlsHandshakeHash prepareFinishHash = handshake.PrepareToFinish(); - securityParameters.sessionHash = TlsProtocol.GetCurrentPrfHash(state.clientContext, prepareFinishHash, null); - - TlsProtocol.EstablishMasterSecret(state.clientContext, state.keyExchange); - recordLayer.InitPendingEpoch(state.client.GetCipher()); - - if (state.clientCredentials != null && state.clientCredentials is TlsSignerCredentials) - { - TlsSignerCredentials signerCredentials = (TlsSignerCredentials)state.clientCredentials; - - /* - * RFC 5246 4.7. digitally-signed element needs SignatureAndHashAlgorithm from TLS 1.2 - */ - SignatureAndHashAlgorithm signatureAndHashAlgorithm = TlsUtilities.GetSignatureAndHashAlgorithm( - state.clientContext, signerCredentials); - - byte[] hash; - if (signatureAndHashAlgorithm == null) - { - hash = securityParameters.SessionHash; - } - else - { - hash = prepareFinishHash.GetFinalHash(signatureAndHashAlgorithm.Hash); - } - - byte[] signature = signerCredentials.GenerateCertificateSignature(hash); - DigitallySigned certificateVerify = new DigitallySigned(signatureAndHashAlgorithm, signature); - byte[] certificateVerifyBody = GenerateCertificateVerify(state, certificateVerify); - handshake.SendMessage(HandshakeType.certificate_verify, certificateVerifyBody); - } - - // NOTE: Calculated exclusive of the Finished message itself - byte[] clientVerifyData = TlsUtilities.CalculateVerifyData(state.clientContext, ExporterLabel.client_finished, - TlsProtocol.GetCurrentPrfHash(state.clientContext, handshake.HandshakeHash, null)); - handshake.SendMessage(HandshakeType.finished, clientVerifyData); - - if (state.expectSessionTicket) - { - serverMessage = handshake.ReceiveMessage(); - if (serverMessage.Type == HandshakeType.session_ticket) - { - ProcessNewSessionTicket(state, serverMessage.Body); - } - else - { - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - } - - // NOTE: Calculated exclusive of the actual Finished message from the server - byte[] expectedServerVerifyData = TlsUtilities.CalculateVerifyData(state.clientContext, ExporterLabel.server_finished, - TlsProtocol.GetCurrentPrfHash(state.clientContext, handshake.HandshakeHash, null)); - ProcessFinished(handshake.ReceiveMessageBody(HandshakeType.finished), expectedServerVerifyData); - - handshake.Finish(); - - if (state.tlsSession != null) - { - state.sessionParameters = new SessionParameters.Builder() - .SetCipherSuite(securityParameters.CipherSuite) - .SetCompressionAlgorithm(securityParameters.CompressionAlgorithm) - .SetExtendedMasterSecret(securityParameters.IsExtendedMasterSecret) - .SetMasterSecret(securityParameters.MasterSecret) - .SetPeerCertificate(serverCertificate) - .SetPskIdentity(securityParameters.PskIdentity) - .SetSrpIdentity(securityParameters.SrpIdentity) - // TODO Consider filtering extensions that aren't relevant to resumed sessions - .SetServerExtensions(state.serverExtensions) - .Build(); - - state.tlsSession = TlsUtilities.ImportSession(state.tlsSession.SessionID, state.sessionParameters); - - state.clientContext.SetResumableSession(state.tlsSession); - } - - state.client.NotifyHandshakeComplete(); - - return new DtlsTransport(recordLayer); - } - - protected virtual byte[] GenerateCertificateVerify(ClientHandshakeState state, DigitallySigned certificateVerify) - { - MemoryStream buf = new MemoryStream(); - certificateVerify.Encode(buf); - return buf.ToArray(); - } - - protected virtual byte[] GenerateClientHello(ClientHandshakeState state, TlsClient client) - { - ProtocolVersion client_version = client.ClientVersion; - if (!client_version.IsDtls) - throw new TlsFatalAlert(AlertDescription.internal_error); - - TlsClientContextImpl context = state.clientContext; - - context.SetClientVersion(client_version); - - SecurityParameters securityParameters = context.SecurityParameters; - - // Session ID - byte[] session_id = TlsUtilities.EmptyBytes; - if (state.tlsSession != null) - { - session_id = state.tlsSession.SessionID; - if (session_id == null || session_id.Length > 32) - { - session_id = TlsUtilities.EmptyBytes; - } - } - - bool fallback = client.IsFallback; - - state.offeredCipherSuites = client.GetCipherSuites(); - - if (session_id.Length > 0 && state.sessionParameters != null) - { - if (!state.sessionParameters.IsExtendedMasterSecret - || !Arrays.Contains(state.offeredCipherSuites, state.sessionParameters.CipherSuite) - || CompressionMethod.cls_null != state.sessionParameters.CompressionAlgorithm) - { - session_id = TlsUtilities.EmptyBytes; - } - } - - state.clientExtensions = TlsExtensionsUtilities.EnsureExtensionsInitialised(client.GetClientExtensions()); - - TlsExtensionsUtilities.AddExtendedMasterSecretExtension(state.clientExtensions); - - MemoryStream buf = new MemoryStream(); - - TlsUtilities.WriteVersion(client_version, buf); - - buf.Write(securityParameters.ClientRandom, 0, securityParameters.ClientRandom.Length); - - TlsUtilities.WriteOpaque8(session_id, buf); - - // Cookie - TlsUtilities.WriteOpaque8(TlsUtilities.EmptyBytes, buf); - - // Cipher Suites (and SCSV) - { - /* - * RFC 5746 3.4. The client MUST include either an empty "renegotiation_info" extension, - * or the TLS_EMPTY_RENEGOTIATION_INFO_SCSV signaling cipher suite value in the - * ClientHello. Including both is NOT RECOMMENDED. - */ - byte[] renegExtData = TlsUtilities.GetExtensionData(state.clientExtensions, ExtensionType.renegotiation_info); - bool noRenegExt = (null == renegExtData); - - bool noRenegSCSV = !Arrays.Contains(state.offeredCipherSuites, CipherSuite.TLS_EMPTY_RENEGOTIATION_INFO_SCSV); - - if (noRenegExt && noRenegSCSV) - { - // TODO Consider whether to default to a client extension instead - state.offeredCipherSuites = Arrays.Append(state.offeredCipherSuites, CipherSuite.TLS_EMPTY_RENEGOTIATION_INFO_SCSV); - } - - /* - * RFC 7507 4. If a client sends a ClientHello.client_version containing a lower value - * than the latest (highest-valued) version supported by the client, it SHOULD include - * the TLS_FALLBACK_SCSV cipher suite value in ClientHello.cipher_suites [..]. (The - * client SHOULD put TLS_FALLBACK_SCSV after all cipher suites that it actually intends - * to negotiate.) - */ - if (fallback && !Arrays.Contains(state.offeredCipherSuites, CipherSuite.TLS_FALLBACK_SCSV)) - { - state.offeredCipherSuites = Arrays.Append(state.offeredCipherSuites, CipherSuite.TLS_FALLBACK_SCSV); - } - - TlsUtilities.WriteUint16ArrayWithUint16Length(state.offeredCipherSuites, buf); - } - - TlsUtilities.WriteUint8ArrayWithUint8Length(new byte[]{ CompressionMethod.cls_null }, buf); - - TlsProtocol.WriteExtensions(buf, state.clientExtensions); - - return buf.ToArray(); - } - - protected virtual byte[] GenerateClientKeyExchange(ClientHandshakeState state) - { - MemoryStream buf = new MemoryStream(); - state.keyExchange.GenerateClientKeyExchange(buf); - return buf.ToArray(); - } - - protected virtual void InvalidateSession(ClientHandshakeState state) - { - if (state.sessionParameters != null) - { - state.sessionParameters.Clear(); - state.sessionParameters = null; - } - - if (state.tlsSession != null) - { - state.tlsSession.Invalidate(); - state.tlsSession = null; - } - } - - protected virtual void ProcessCertificateRequest(ClientHandshakeState state, byte[] body) - { - if (state.authentication == null) - { - /* - * RFC 2246 7.4.4. It is a fatal handshake_failure alert for an anonymous server to - * request client identification. - */ - throw new TlsFatalAlert(AlertDescription.handshake_failure); - } - - MemoryStream buf = new MemoryStream(body, false); - - state.certificateRequest = CertificateRequest.Parse(state.clientContext, buf); - - TlsProtocol.AssertEmpty(buf); - - state.keyExchange.ValidateCertificateRequest(state.certificateRequest); - } - - protected virtual void ProcessCertificateStatus(ClientHandshakeState state, byte[] body) - { - if (!state.allowCertificateStatus) - { - /* - * RFC 3546 3.6. If a server returns a "CertificateStatus" message, then the - * server MUST have included an extension of type "status_request" with empty - * "extension_data" in the extended server hello.. - */ - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - - MemoryStream buf = new MemoryStream(body, false); - - state.certificateStatus = CertificateStatus.Parse(buf); - - TlsProtocol.AssertEmpty(buf); - - // TODO[RFC 3546] Figure out how to provide this to the client/authentication. - } - - protected virtual byte[] ProcessHelloVerifyRequest(ClientHandshakeState state, byte[] body) - { - MemoryStream buf = new MemoryStream(body, false); - - ProtocolVersion server_version = TlsUtilities.ReadVersion(buf); - byte[] cookie = TlsUtilities.ReadOpaque8(buf); - - TlsProtocol.AssertEmpty(buf); - - // TODO Seems this behaviour is not yet in line with OpenSSL for DTLS 1.2 - // reportServerVersion(state, server_version); - if (!server_version.IsEqualOrEarlierVersionOf(state.clientContext.ClientVersion)) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - - /* - * RFC 6347 This specification increases the cookie size limit to 255 bytes for greater - * future flexibility. The limit remains 32 for previous versions of DTLS. - */ - if (!ProtocolVersion.DTLSv12.IsEqualOrEarlierVersionOf(server_version) && cookie.Length > 32) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - - return cookie; - } - - protected virtual void ProcessNewSessionTicket(ClientHandshakeState state, byte[] body) - { - MemoryStream buf = new MemoryStream(body, false); - - NewSessionTicket newSessionTicket = NewSessionTicket.Parse(buf); - - TlsProtocol.AssertEmpty(buf); - - state.client.NotifyNewSessionTicket(newSessionTicket); - } - - protected virtual Certificate ProcessServerCertificate(ClientHandshakeState state, byte[] body) - { - MemoryStream buf = new MemoryStream(body, false); - - Certificate serverCertificate = Certificate.Parse(buf); - - TlsProtocol.AssertEmpty(buf); - - state.keyExchange.ProcessServerCertificate(serverCertificate); - state.authentication = state.client.GetAuthentication(); - state.authentication.NotifyServerCertificate(serverCertificate); - - return serverCertificate; - } - - protected virtual void ProcessServerHello(ClientHandshakeState state, byte[] body) - { - SecurityParameters securityParameters = state.clientContext.SecurityParameters; - - MemoryStream buf = new MemoryStream(body, false); - - { - ProtocolVersion server_version = TlsUtilities.ReadVersion(buf); - ReportServerVersion(state, server_version); - } - - securityParameters.serverRandom = TlsUtilities.ReadFully(32, buf); - - state.selectedSessionID = TlsUtilities.ReadOpaque8(buf); - if (state.selectedSessionID.Length > 32) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - state.client.NotifySessionID(state.selectedSessionID); - state.resumedSession = state.selectedSessionID.Length > 0 && state.tlsSession != null - && Arrays.AreEqual(state.selectedSessionID, state.tlsSession.SessionID); - - int selectedCipherSuite = TlsUtilities.ReadUint16(buf); - if (!Arrays.Contains(state.offeredCipherSuites, selectedCipherSuite) - || selectedCipherSuite == CipherSuite.TLS_NULL_WITH_NULL_NULL - || CipherSuite.IsScsv(selectedCipherSuite) - || !TlsUtilities.IsValidCipherSuiteForVersion(selectedCipherSuite, state.clientContext.ServerVersion)) - { - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - ValidateSelectedCipherSuite(selectedCipherSuite, AlertDescription.illegal_parameter); - state.client.NotifySelectedCipherSuite(selectedCipherSuite); - - byte selectedCompressionMethod = TlsUtilities.ReadUint8(buf); - if (CompressionMethod.cls_null != selectedCompressionMethod) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - state.client.NotifySelectedCompressionMethod(selectedCompressionMethod); - - /* - * RFC3546 2.2 The extended server hello message format MAY be sent in place of the server - * hello message when the client has requested extended functionality via the extended - * client hello message specified in Section 2.1. ... Note that the extended server hello - * message is only sent in response to an extended client hello message. This prevents the - * possibility that the extended server hello message could "break" existing TLS 1.0 - * clients. - */ - - /* - * TODO RFC 3546 2.3 If [...] the older session is resumed, then the server MUST ignore - * extensions appearing in the client hello, and send a server hello containing no - * extensions. - */ - - // Integer -> byte[] - state.serverExtensions = TlsProtocol.ReadExtensions(buf); - - /* - * RFC 7627 4. Clients and servers SHOULD NOT accept handshakes that do not use the extended - * master secret [..]. (and see 5.2, 5.3) - */ - securityParameters.extendedMasterSecret = TlsExtensionsUtilities.HasExtendedMasterSecretExtension(state.serverExtensions); - - if (!securityParameters.IsExtendedMasterSecret - && (state.resumedSession || state.client.RequiresExtendedMasterSecret())) - { - throw new TlsFatalAlert(AlertDescription.handshake_failure); - } - - /* - * RFC 3546 2.2 Note that the extended server hello message is only sent in response to an - * extended client hello message. However, see RFC 5746 exception below. We always include - * the SCSV, so an Extended Server Hello is always allowed. - */ - if (state.serverExtensions != null) - { - foreach (int extType in state.serverExtensions.Keys) - { - /* - * RFC 5746 3.6. Note that sending a "renegotiation_info" extension in response to a - * ClientHello containing only the SCSV is an explicit exception to the prohibition - * in RFC 5246, Section 7.4.1.4, on the server sending unsolicited extensions and is - * only allowed because the client is signaling its willingness to receive the - * extension via the TLS_EMPTY_RENEGOTIATION_INFO_SCSV SCSV. - */ - if (extType == ExtensionType.renegotiation_info) - continue; - - /* - * RFC 5246 7.4.1.4 An extension type MUST NOT appear in the ServerHello unless the - * same extension type appeared in the corresponding ClientHello. If a client - * receives an extension type in ServerHello that it did not request in the - * associated ClientHello, it MUST abort the handshake with an unsupported_extension - * fatal alert. - */ - if (null == TlsUtilities.GetExtensionData(state.clientExtensions, extType)) - throw new TlsFatalAlert(AlertDescription.unsupported_extension); - - /* - * RFC 3546 2.3. If [...] the older session is resumed, then the server MUST ignore - * extensions appearing in the client hello, and send a server hello containing no - * extensions[.] - */ - if (state.resumedSession) - { - // TODO[compat-gnutls] GnuTLS test server sends server extensions e.g. ec_point_formats - // TODO[compat-openssl] OpenSSL test server sends server extensions e.g. ec_point_formats - // TODO[compat-polarssl] PolarSSL test server sends server extensions e.g. ec_point_formats - //throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - } - } - - /* - * RFC 5746 3.4. Client Behavior: Initial Handshake - */ - { - /* - * When a ServerHello is received, the client MUST check if it includes the - * "renegotiation_info" extension: - */ - byte[] renegExtData = TlsUtilities.GetExtensionData(state.serverExtensions, ExtensionType.renegotiation_info); - if (renegExtData != null) - { - /* - * If the extension is present, set the secure_renegotiation flag to TRUE. The - * client MUST then verify that the length of the "renegotiated_connection" - * field is zero, and if it is not, MUST abort the handshake (by sending a fatal - * handshake_failure alert). - */ - state.secure_renegotiation = true; - - if (!Arrays.ConstantTimeAreEqual(renegExtData, TlsProtocol.CreateRenegotiationInfo(TlsUtilities.EmptyBytes))) - throw new TlsFatalAlert(AlertDescription.handshake_failure); - } - } - - // TODO[compat-gnutls] GnuTLS test server fails to send renegotiation_info extension when resuming - state.client.NotifySecureRenegotiation(state.secure_renegotiation); - - IDictionary sessionClientExtensions = state.clientExtensions, sessionServerExtensions = state.serverExtensions; - if (state.resumedSession) - { - if (selectedCipherSuite != state.sessionParameters.CipherSuite - || selectedCompressionMethod != state.sessionParameters.CompressionAlgorithm) - { - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - - sessionClientExtensions = null; - sessionServerExtensions = state.sessionParameters.ReadServerExtensions(); - } - - securityParameters.cipherSuite = selectedCipherSuite; - securityParameters.compressionAlgorithm = selectedCompressionMethod; - - if (sessionServerExtensions != null && sessionServerExtensions.Count > 0) - { - { - /* - * RFC 7366 3. If a server receives an encrypt-then-MAC request extension from a client - * and then selects a stream or Authenticated Encryption with Associated Data (AEAD) - * ciphersuite, it MUST NOT send an encrypt-then-MAC response extension back to the - * client. - */ - bool serverSentEncryptThenMAC = TlsExtensionsUtilities.HasEncryptThenMacExtension(sessionServerExtensions); - if (serverSentEncryptThenMAC && !TlsUtilities.IsBlockCipherSuite(securityParameters.CipherSuite)) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - securityParameters.encryptThenMac = serverSentEncryptThenMAC; - } - - securityParameters.maxFragmentLength = EvaluateMaxFragmentLengthExtension(state.resumedSession, - sessionClientExtensions, sessionServerExtensions, AlertDescription.illegal_parameter); - - securityParameters.truncatedHMac = TlsExtensionsUtilities.HasTruncatedHMacExtension(sessionServerExtensions); - - /* - * TODO It's surprising that there's no provision to allow a 'fresh' CertificateStatus to be - * sent in a session resumption handshake. - */ - state.allowCertificateStatus = !state.resumedSession - && TlsUtilities.HasExpectedEmptyExtensionData(sessionServerExtensions, ExtensionType.status_request, - AlertDescription.illegal_parameter); - - state.expectSessionTicket = !state.resumedSession - && TlsUtilities.HasExpectedEmptyExtensionData(sessionServerExtensions, ExtensionType.session_ticket, - AlertDescription.illegal_parameter); - } - - if (sessionClientExtensions != null) - { - state.client.ProcessServerExtensions(sessionServerExtensions); - } - - securityParameters.prfAlgorithm = TlsProtocol.GetPrfAlgorithm(state.clientContext, - securityParameters.CipherSuite); - - /* - * RFC 5246 7.4.9. Any cipher suite which does not explicitly specify verify_data_length has - * a verify_data_length equal to 12. This includes all existing cipher suites. - */ - securityParameters.verifyDataLength = 12; - } - - protected virtual void ProcessServerKeyExchange(ClientHandshakeState state, byte[] body) - { - MemoryStream buf = new MemoryStream(body, false); - - state.keyExchange.ProcessServerKeyExchange(buf); - - TlsProtocol.AssertEmpty(buf); - } - - protected virtual void ProcessServerSupplementalData(ClientHandshakeState state, byte[] body) - { - MemoryStream buf = new MemoryStream(body, false); - IList serverSupplementalData = TlsProtocol.ReadSupplementalDataMessage(buf); - state.client.ProcessServerSupplementalData(serverSupplementalData); - } - - protected virtual void ReportServerVersion(ClientHandshakeState state, ProtocolVersion server_version) - { - TlsClientContextImpl clientContext = state.clientContext; - ProtocolVersion currentServerVersion = clientContext.ServerVersion; - if (null == currentServerVersion) - { - clientContext.SetServerVersion(server_version); - state.client.NotifyServerVersion(server_version); - } - else if (!currentServerVersion.Equals(server_version)) - { - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - } - - protected static byte[] PatchClientHelloWithCookie(byte[] clientHelloBody, byte[] cookie) - { - int sessionIDPos = 34; - int sessionIDLength = TlsUtilities.ReadUint8(clientHelloBody, sessionIDPos); - - int cookieLengthPos = sessionIDPos + 1 + sessionIDLength; - int cookiePos = cookieLengthPos + 1; - - byte[] patched = new byte[clientHelloBody.Length + cookie.Length]; - Array.Copy(clientHelloBody, 0, patched, 0, cookieLengthPos); - TlsUtilities.CheckUint8(cookie.Length); - TlsUtilities.WriteUint8((byte)cookie.Length, patched, cookieLengthPos); - Array.Copy(cookie, 0, patched, cookiePos, cookie.Length); - Array.Copy(clientHelloBody, cookiePos, patched, cookiePos + cookie.Length, clientHelloBody.Length - cookiePos); - - return patched; - } - - protected internal class ClientHandshakeState - { - internal TlsClient client = null; - internal TlsClientContextImpl clientContext = null; - internal TlsSession tlsSession = null; - internal SessionParameters sessionParameters = null; - internal SessionParameters.Builder sessionParametersBuilder = null; - internal int[] offeredCipherSuites = null; - internal IDictionary clientExtensions = null; - internal IDictionary serverExtensions = null; - internal byte[] selectedSessionID = null; - internal bool resumedSession = false; - internal bool secure_renegotiation = false; - internal bool allowCertificateStatus = false; - internal bool expectSessionTicket = false; - internal TlsKeyExchange keyExchange = null; - internal TlsAuthentication authentication = null; - internal CertificateStatus certificateStatus = null; - internal CertificateRequest certificateRequest = null; - internal TlsCredentials clientCredentials = null; - } - } -} diff --git a/crypto/src/crypto/tls/DtlsEpoch.cs b/crypto/src/crypto/tls/DtlsEpoch.cs deleted file mode 100644 index af14035ce..000000000 --- a/crypto/src/crypto/tls/DtlsEpoch.cs +++ /dev/null @@ -1,56 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - internal class DtlsEpoch - { - private readonly DtlsReplayWindow mReplayWindow = new DtlsReplayWindow(); - - private readonly int mEpoch; - private readonly TlsCipher mCipher; - - private long mSequenceNumber = 0; - - internal DtlsEpoch(int epoch, TlsCipher cipher) - { - if (epoch < 0) - throw new ArgumentException("must be >= 0", "epoch"); - if (cipher == null) - throw new ArgumentNullException("cipher"); - - this.mEpoch = epoch; - this.mCipher = cipher; - } - - internal long AllocateSequenceNumber() - { - lock (this) - { - if (mSequenceNumber >= (1L << 48)) - throw new TlsFatalAlert(AlertDescription.internal_error); - - return mSequenceNumber++; - } - } - - internal TlsCipher Cipher - { - get { return mCipher; } - } - - internal int Epoch - { - get { return mEpoch; } - } - - internal DtlsReplayWindow ReplayWindow - { - get { return mReplayWindow; } - } - - internal long SequenceNumber - { - get { lock(this) return mSequenceNumber; } - } - } -} diff --git a/crypto/src/crypto/tls/DtlsHandshakeRetransmit.cs b/crypto/src/crypto/tls/DtlsHandshakeRetransmit.cs deleted file mode 100644 index 8bfae78b1..000000000 --- a/crypto/src/crypto/tls/DtlsHandshakeRetransmit.cs +++ /dev/null @@ -1,11 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - interface DtlsHandshakeRetransmit - { - /// <exception cref="IOException"/> - void ReceivedHandshakeRecord(int epoch, byte[] buf, int off, int len); - } -} diff --git a/crypto/src/crypto/tls/DtlsProtocol.cs b/crypto/src/crypto/tls/DtlsProtocol.cs deleted file mode 100644 index e4ebd436c..000000000 --- a/crypto/src/crypto/tls/DtlsProtocol.cs +++ /dev/null @@ -1,92 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Security; -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class DtlsProtocol - { - protected readonly SecureRandom mSecureRandom; - - protected DtlsProtocol(SecureRandom secureRandom) - { - if (secureRandom == null) - throw new ArgumentNullException("secureRandom"); - - this.mSecureRandom = secureRandom; - } - - /// <exception cref="IOException"/> - protected virtual void ProcessFinished(byte[] body, byte[] expected_verify_data) - { - MemoryStream buf = new MemoryStream(body, false); - - byte[] verify_data = TlsUtilities.ReadFully(expected_verify_data.Length, buf); - - TlsProtocol.AssertEmpty(buf); - - if (!Arrays.ConstantTimeAreEqual(expected_verify_data, verify_data)) - throw new TlsFatalAlert(AlertDescription.handshake_failure); - } - - /// <exception cref="IOException"/> - internal static void ApplyMaxFragmentLengthExtension(DtlsRecordLayer recordLayer, short maxFragmentLength) - { - if (maxFragmentLength >= 0) - { - if (!MaxFragmentLength.IsValid((byte)maxFragmentLength)) - throw new TlsFatalAlert(AlertDescription.internal_error); - - int plainTextLimit = 1 << (8 + maxFragmentLength); - recordLayer.SetPlaintextLimit(plainTextLimit); - } - } - - /// <exception cref="IOException"/> - protected static short EvaluateMaxFragmentLengthExtension(bool resumedSession, IDictionary clientExtensions, - IDictionary serverExtensions, byte alertDescription) - { - short maxFragmentLength = TlsExtensionsUtilities.GetMaxFragmentLengthExtension(serverExtensions); - if (maxFragmentLength >= 0) - { - if (!MaxFragmentLength.IsValid((byte)maxFragmentLength) - || (!resumedSession && maxFragmentLength != TlsExtensionsUtilities - .GetMaxFragmentLengthExtension(clientExtensions))) - { - throw new TlsFatalAlert(alertDescription); - } - } - return maxFragmentLength; - } - - /// <exception cref="IOException"/> - protected static byte[] GenerateCertificate(Certificate certificate) - { - MemoryStream buf = new MemoryStream(); - certificate.Encode(buf); - return buf.ToArray(); - } - - /// <exception cref="IOException"/> - protected static byte[] GenerateSupplementalData(IList supplementalData) - { - MemoryStream buf = new MemoryStream(); - TlsProtocol.WriteSupplementalData(buf, supplementalData); - return buf.ToArray(); - } - - /// <exception cref="IOException"/> - protected static void ValidateSelectedCipherSuite(int selectedCipherSuite, byte alertDescription) - { - switch (TlsUtilities.GetEncryptionAlgorithm(selectedCipherSuite)) - { - case EncryptionAlgorithm.RC4_40: - case EncryptionAlgorithm.RC4_128: - throw new TlsFatalAlert(alertDescription); - } - } - } -} diff --git a/crypto/src/crypto/tls/DtlsReassembler.cs b/crypto/src/crypto/tls/DtlsReassembler.cs deleted file mode 100644 index 11fe609cf..000000000 --- a/crypto/src/crypto/tls/DtlsReassembler.cs +++ /dev/null @@ -1,125 +0,0 @@ -using System; -using System.Collections; - -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - class DtlsReassembler - { - private readonly byte mMsgType; - private readonly byte[] mBody; - - private readonly IList mMissing = Platform.CreateArrayList(); - - internal DtlsReassembler(byte msg_type, int length) - { - this.mMsgType = msg_type; - this.mBody = new byte[length]; - this.mMissing.Add(new Range(0, length)); - } - - internal byte MsgType - { - get { return mMsgType; } - } - - internal byte[] GetBodyIfComplete() - { - return mMissing.Count == 0 ? mBody : null; - } - - internal void ContributeFragment(byte msg_type, int length, byte[] buf, int off, int fragment_offset, - int fragment_length) - { - int fragment_end = fragment_offset + fragment_length; - - if (this.mMsgType != msg_type || this.mBody.Length != length || fragment_end > length) - { - return; - } - - if (fragment_length == 0) - { - // NOTE: Empty messages still require an empty fragment to complete it - if (fragment_offset == 0 && mMissing.Count > 0) - { - Range firstRange = (Range)mMissing[0]; - if (firstRange.End == 0) - { - mMissing.RemoveAt(0); - } - } - return; - } - - for (int i = 0; i < mMissing.Count; ++i) - { - Range range = (Range)mMissing[i]; - if (range.Start >= fragment_end) - { - break; - } - if (range.End > fragment_offset) - { - - int copyStart = System.Math.Max(range.Start, fragment_offset); - int copyEnd = System.Math.Min(range.End, fragment_end); - int copyLength = copyEnd - copyStart; - - Array.Copy(buf, off + copyStart - fragment_offset, mBody, copyStart, - copyLength); - - if (copyStart == range.Start) - { - if (copyEnd == range.End) - { - mMissing.RemoveAt(i--); - } - else - { - range.Start = copyEnd; - } - } - else - { - if (copyEnd != range.End) - { - mMissing.Insert(++i, new Range(copyEnd, range.End)); - } - range.End = copyStart; - } - } - } - } - - internal void Reset() - { - this.mMissing.Clear(); - this.mMissing.Add(new Range(0, mBody.Length)); - } - - private class Range - { - private int mStart, mEnd; - - internal Range(int start, int end) - { - this.mStart = start; - this.mEnd = end; - } - - public int Start - { - get { return mStart; } - set { this.mStart = value; } - } - - public int End - { - get { return mEnd; } - set { this.mEnd = value; } - } - } - } -} diff --git a/crypto/src/crypto/tls/DtlsRecordLayer.cs b/crypto/src/crypto/tls/DtlsRecordLayer.cs deleted file mode 100644 index 69870dd91..000000000 --- a/crypto/src/crypto/tls/DtlsRecordLayer.cs +++ /dev/null @@ -1,585 +0,0 @@ -using System; -using System.IO; -#if !PORTABLE || DOTNET -using System.Net.Sockets; -#endif - -using Org.BouncyCastle.Utilities.Date; - -namespace Org.BouncyCastle.Crypto.Tls -{ - internal class DtlsRecordLayer - : DatagramTransport - { - private const int RECORD_HEADER_LENGTH = 13; - private const int MAX_FRAGMENT_LENGTH = 1 << 14; - private const long TCP_MSL = 1000L * 60 * 2; - private const long RETRANSMIT_TIMEOUT = TCP_MSL * 2; - - private static void SendDatagram(DatagramTransport sender, byte[] buf, int off, int len) - { - //try - //{ - // sender.Send(buf, off, len); - //} - //catch (InterruptedIOException e) - //{ - // e.bytesTransferred = 0; - // throw e; - //} - - sender.Send(buf, off, len); - } - - private readonly DatagramTransport mTransport; - private readonly TlsContext mContext; - private readonly TlsPeer mPeer; - - private readonly ByteQueue mRecordQueue = new ByteQueue(); - - private volatile bool mClosed = false; - private volatile bool mFailed = false; - private volatile ProtocolVersion mReadVersion = null, mWriteVersion = null; - private volatile bool mInHandshake; - private volatile int mPlaintextLimit; - private DtlsEpoch mCurrentEpoch, mPendingEpoch; - private DtlsEpoch mReadEpoch, mWriteEpoch; - - private DtlsHandshakeRetransmit mRetransmit = null; - private DtlsEpoch mRetransmitEpoch = null; - private Timeout mRetransmitTimeout = null; - - internal DtlsRecordLayer(DatagramTransport transport, TlsContext context, TlsPeer peer, byte contentType) - { - this.mTransport = transport; - this.mContext = context; - this.mPeer = peer; - - this.mInHandshake = true; - - this.mCurrentEpoch = new DtlsEpoch(0, new TlsNullCipher(context)); - this.mPendingEpoch = null; - this.mReadEpoch = mCurrentEpoch; - this.mWriteEpoch = mCurrentEpoch; - - SetPlaintextLimit(MAX_FRAGMENT_LENGTH); - } - - internal bool IsClosed - { - get { return mClosed; } - } - - internal virtual void SetPlaintextLimit(int plaintextLimit) - { - this.mPlaintextLimit = plaintextLimit; - } - - internal virtual int ReadEpoch - { - get { return mReadEpoch.Epoch; } - } - - internal virtual ProtocolVersion ReadVersion - { - get { return mReadVersion; } - set { this.mReadVersion = value; } - } - - internal virtual void SetWriteVersion(ProtocolVersion writeVersion) - { - this.mWriteVersion = writeVersion; - } - - internal virtual void InitPendingEpoch(TlsCipher pendingCipher) - { - if (mPendingEpoch != null) - throw new InvalidOperationException(); - - /* - * TODO "In order to ensure that any given sequence/epoch pair is unique, implementations - * MUST NOT allow the same epoch value to be reused within two times the TCP maximum segment - * lifetime." - */ - - // TODO Check for overflow - this.mPendingEpoch = new DtlsEpoch(mWriteEpoch.Epoch + 1, pendingCipher); - } - - internal virtual void HandshakeSuccessful(DtlsHandshakeRetransmit retransmit) - { - if (mReadEpoch == mCurrentEpoch || mWriteEpoch == mCurrentEpoch) - { - // TODO - throw new InvalidOperationException(); - } - - if (retransmit != null) - { - this.mRetransmit = retransmit; - this.mRetransmitEpoch = mCurrentEpoch; - this.mRetransmitTimeout = new Timeout(RETRANSMIT_TIMEOUT); - } - - this.mInHandshake = false; - this.mCurrentEpoch = mPendingEpoch; - this.mPendingEpoch = null; - } - - internal virtual void ResetWriteEpoch() - { - if (mRetransmitEpoch != null) - { - this.mWriteEpoch = mRetransmitEpoch; - } - else - { - this.mWriteEpoch = mCurrentEpoch; - } - } - - public virtual int GetReceiveLimit() - { - return System.Math.Min(this.mPlaintextLimit, - mReadEpoch.Cipher.GetPlaintextLimit(mTransport.GetReceiveLimit() - RECORD_HEADER_LENGTH)); - } - - public virtual int GetSendLimit() - { - return System.Math.Min(this.mPlaintextLimit, - mWriteEpoch.Cipher.GetPlaintextLimit(mTransport.GetSendLimit() - RECORD_HEADER_LENGTH)); - } - - public virtual int Receive(byte[] buf, int off, int len, int waitMillis) - { - long currentTimeMillis = DateTimeUtilities.CurrentUnixMs(); - - Timeout timeout = Timeout.ForWaitMillis(waitMillis, currentTimeMillis); - byte[] record = null; - - while (waitMillis >= 0) - { - if (mRetransmitTimeout != null && mRetransmitTimeout.RemainingMillis(currentTimeMillis) < 1) - { - mRetransmit = null; - mRetransmitEpoch = null; - mRetransmitTimeout = null; - } - - int receiveLimit = System.Math.Min(len, GetReceiveLimit()) + RECORD_HEADER_LENGTH; - if (record == null || record.Length < receiveLimit) - { - record = new byte[receiveLimit]; - } - - int received = ReceiveRecord(record, 0, receiveLimit, waitMillis); - int processed = ProcessRecord(received, record, buf, off); - if (processed >= 0) - { - return processed; - } - - currentTimeMillis = DateTimeUtilities.CurrentUnixMs(); - waitMillis = Timeout.GetWaitMillis(timeout, currentTimeMillis); - } - - return -1; - } - - /// <exception cref="IOException"/> - public virtual void Send(byte[] buf, int off, int len) - { - byte contentType = ContentType.application_data; - - if (this.mInHandshake || this.mWriteEpoch == this.mRetransmitEpoch) - { - contentType = ContentType.handshake; - - byte handshakeType = TlsUtilities.ReadUint8(buf, off); - if (handshakeType == HandshakeType.finished) - { - DtlsEpoch nextEpoch = null; - if (this.mInHandshake) - { - nextEpoch = mPendingEpoch; - } - else if (this.mWriteEpoch == this.mRetransmitEpoch) - { - nextEpoch = mCurrentEpoch; - } - - if (nextEpoch == null) - { - // TODO - throw new InvalidOperationException(); - } - - // Implicitly send change_cipher_spec and change to pending cipher state - - // TODO Send change_cipher_spec and finished records in single datagram? - byte[] data = new byte[]{ 1 }; - SendRecord(ContentType.change_cipher_spec, data, 0, data.Length); - - mWriteEpoch = nextEpoch; - } - } - - SendRecord(contentType, buf, off, len); - } - - public virtual void Close() - { - if (!mClosed) - { - if (mInHandshake) - { - Warn(AlertDescription.user_canceled, "User canceled handshake"); - } - CloseTransport(); - } - } - - internal virtual void Failed() - { - if (!mClosed) - { - mFailed = true; - - CloseTransport(); - } - } - - internal virtual void Fail(byte alertDescription) - { - if (!mClosed) - { - try - { - RaiseAlert(AlertLevel.fatal, alertDescription, null, null); - } - catch (Exception) - { - // Ignore - } - - mFailed = true; - - CloseTransport(); - } - } - - internal virtual void Warn(byte alertDescription, string message) - { - RaiseAlert(AlertLevel.warning, alertDescription, message, null); - } - - private void CloseTransport() - { - if (!mClosed) - { - /* - * RFC 5246 7.2.1. Unless some other fatal alert has been transmitted, each party is - * required to send a close_notify alert before closing the write side of the - * connection. The other party MUST respond with a close_notify alert of its own and - * close down the connection immediately, discarding any pending writes. - */ - - try - { - if (!mFailed) - { - Warn(AlertDescription.close_notify, null); - } - mTransport.Close(); - } - catch (Exception) - { - // Ignore - } - - mClosed = true; - } - } - - private void RaiseAlert(byte alertLevel, byte alertDescription, string message, Exception cause) - { - mPeer.NotifyAlertRaised(alertLevel, alertDescription, message, cause); - - byte[] error = new byte[2]; - error[0] = (byte)alertLevel; - error[1] = (byte)alertDescription; - - SendRecord(ContentType.alert, error, 0, 2); - } - - private int ReceiveDatagram(byte[] buf, int off, int len, int waitMillis) - { - try - { - return mTransport.Receive(buf, off, len, waitMillis); - } - catch (TlsTimeoutException) - { - return -1; - } -#if !PORTABLE || DOTNET - catch (SocketException e) - { - if (TlsUtilities.IsTimeout(e)) - return -1; - - throw e; - } -#endif - //catch (InterruptedIOException e) - //{ - // e.bytesTransferred = 0; - // throw e; - //} - } - - private int ProcessRecord(int received, byte[] record, byte[] buf, int off) - { - // NOTE: received < 0 (timeout) is covered by this first case - if (received < RECORD_HEADER_LENGTH) - { - return -1; - } - int length = TlsUtilities.ReadUint16(record, 11); - if (received != (length + RECORD_HEADER_LENGTH)) - { - return -1; - } - - byte type = TlsUtilities.ReadUint8(record, 0); - - switch (type) - { - case ContentType.alert: - case ContentType.application_data: - case ContentType.change_cipher_spec: - case ContentType.handshake: - case ContentType.heartbeat: - break; - default: - return -1; - } - - int epoch = TlsUtilities.ReadUint16(record, 3); - - DtlsEpoch recordEpoch = null; - if (epoch == mReadEpoch.Epoch) - { - recordEpoch = mReadEpoch; - } - else if (type == ContentType.handshake && mRetransmitEpoch != null - && epoch == mRetransmitEpoch.Epoch) - { - recordEpoch = mRetransmitEpoch; - } - - if (recordEpoch == null) - { - return -1; - } - - long seq = TlsUtilities.ReadUint48(record, 5); - if (recordEpoch.ReplayWindow.ShouldDiscard(seq)) - { - return -1; - } - - ProtocolVersion version = TlsUtilities.ReadVersion(record, 1); - if (!version.IsDtls) - { - return -1; - } - - if (mReadVersion != null && !mReadVersion.Equals(version)) - { - return -1; - } - - byte[] plaintext = recordEpoch.Cipher.DecodeCiphertext( - GetMacSequenceNumber(recordEpoch.Epoch, seq), type, record, RECORD_HEADER_LENGTH, - received - RECORD_HEADER_LENGTH); - - recordEpoch.ReplayWindow.ReportAuthenticated(seq); - - if (plaintext.Length > this.mPlaintextLimit) - { - return -1; - } - - if (mReadVersion == null) - { - mReadVersion = version; - } - - switch (type) - { - case ContentType.alert: - { - if (plaintext.Length == 2) - { - byte alertLevel = plaintext[0]; - byte alertDescription = plaintext[1]; - - mPeer.NotifyAlertReceived(alertLevel, alertDescription); - - if (alertLevel == AlertLevel.fatal) - { - Failed(); - throw new TlsFatalAlert(alertDescription); - } - - // TODO Can close_notify be a fatal alert? - if (alertDescription == AlertDescription.close_notify) - { - CloseTransport(); - } - } - - return -1; - } - case ContentType.application_data: - { - if (mInHandshake) - { - // TODO Consider buffering application data for new epoch that arrives - // out-of-order with the Finished message - return -1; - } - break; - } - case ContentType.change_cipher_spec: - { - // Implicitly receive change_cipher_spec and change to pending cipher state - - for (int i = 0; i < plaintext.Length; ++i) - { - byte message = TlsUtilities.ReadUint8(plaintext, i); - if (message != ChangeCipherSpec.change_cipher_spec) - { - continue; - } - - if (mPendingEpoch != null) - { - mReadEpoch = mPendingEpoch; - } - } - - return -1; - } - case ContentType.handshake: - { - if (!mInHandshake) - { - if (mRetransmit != null) - { - mRetransmit.ReceivedHandshakeRecord(epoch, plaintext, 0, plaintext.Length); - } - - // TODO Consider support for HelloRequest - return -1; - } - break; - } - case ContentType.heartbeat: - { - // TODO[RFC 6520] - return -1; - } - } - - /* - * NOTE: If we receive any non-handshake data in the new epoch implies the peer has - * received our final flight. - */ - if (!mInHandshake && mRetransmit != null) - { - this.mRetransmit = null; - this.mRetransmitEpoch = null; - this.mRetransmitTimeout = null; - } - - Array.Copy(plaintext, 0, buf, off, plaintext.Length); - return plaintext.Length; - } - - private int ReceiveRecord(byte[] buf, int off, int len, int waitMillis) - { - if (mRecordQueue.Available > 0) - { - int length = 0; - if (mRecordQueue.Available >= RECORD_HEADER_LENGTH) - { - byte[] lengthBytes = new byte[2]; - mRecordQueue.Read(lengthBytes, 0, 2, 11); - length = TlsUtilities.ReadUint16(lengthBytes, 0); - } - - int received = System.Math.Min(mRecordQueue.Available, RECORD_HEADER_LENGTH + length); - mRecordQueue.RemoveData(buf, off, received, 0); - return received; - } - - { - int received = ReceiveDatagram(buf, off, len, waitMillis); - if (received >= RECORD_HEADER_LENGTH) - { - int fragmentLength = TlsUtilities.ReadUint16(buf, off + 11); - int recordLength = RECORD_HEADER_LENGTH + fragmentLength; - if (received > recordLength) - { - mRecordQueue.AddData(buf, off + recordLength, received - recordLength); - received = recordLength; - } - } - return received; - } - } - - private void SendRecord(byte contentType, byte[] buf, int off, int len) - { - // Never send anything until a valid ClientHello has been received - if (mWriteVersion == null) - return; - - if (len > this.mPlaintextLimit) - throw new TlsFatalAlert(AlertDescription.internal_error); - - /* - * RFC 5246 6.2.1 Implementations MUST NOT send zero-length fragments of Handshake, Alert, - * or ChangeCipherSpec content types. - */ - if (len < 1 && contentType != ContentType.application_data) - throw new TlsFatalAlert(AlertDescription.internal_error); - - int recordEpoch = mWriteEpoch.Epoch; - long recordSequenceNumber = mWriteEpoch.AllocateSequenceNumber(); - - byte[] ciphertext = mWriteEpoch.Cipher.EncodePlaintext( - GetMacSequenceNumber(recordEpoch, recordSequenceNumber), contentType, buf, off, len); - - // TODO Check the ciphertext length? - - byte[] record = new byte[ciphertext.Length + RECORD_HEADER_LENGTH]; - TlsUtilities.WriteUint8(contentType, record, 0); - ProtocolVersion version = mWriteVersion; - TlsUtilities.WriteVersion(version, record, 1); - TlsUtilities.WriteUint16(recordEpoch, record, 3); - TlsUtilities.WriteUint48(recordSequenceNumber, record, 5); - TlsUtilities.WriteUint16(ciphertext.Length, record, 11); - Array.Copy(ciphertext, 0, record, RECORD_HEADER_LENGTH, ciphertext.Length); - - SendDatagram(mTransport, record, 0, record.Length); - } - - private static long GetMacSequenceNumber(int epoch, long sequence_number) - { - return ((epoch & 0xFFFFFFFFL) << 48) | sequence_number; - } - } -} diff --git a/crypto/src/crypto/tls/DtlsReliableHandshake.cs b/crypto/src/crypto/tls/DtlsReliableHandshake.cs deleted file mode 100644 index 4fc351376..000000000 --- a/crypto/src/crypto/tls/DtlsReliableHandshake.cs +++ /dev/null @@ -1,449 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Utilities; -using Org.BouncyCastle.Utilities.Date; - -namespace Org.BouncyCastle.Crypto.Tls -{ - internal class DtlsReliableHandshake - { - private const int MaxReceiveAhead = 16; - private const int MessageHeaderLength = 12; - - private const int InitialResendMillis = 1000; - private const int MaxResendMillis = 60000; - - private readonly DtlsRecordLayer mRecordLayer; - private readonly Timeout mHandshakeTimeout; - - private TlsHandshakeHash mHandshakeHash; - - private IDictionary mCurrentInboundFlight = Platform.CreateHashtable(); - private IDictionary mPreviousInboundFlight = null; - private IList mOutboundFlight = Platform.CreateArrayList(); - - private int mResendMillis = -1; - private Timeout mResendTimeout = null; - - private int mMessageSeq = 0, mNextReceiveSeq = 0; - - internal DtlsReliableHandshake(TlsContext context, DtlsRecordLayer transport, int timeoutMillis) - { - this.mRecordLayer = transport; - this.mHandshakeTimeout = Timeout.ForWaitMillis(timeoutMillis); - this.mHandshakeHash = new DeferredHash(); - this.mHandshakeHash.Init(context); - } - - internal void NotifyHelloComplete() - { - this.mHandshakeHash = mHandshakeHash.NotifyPrfDetermined(); - } - - internal TlsHandshakeHash HandshakeHash - { - get { return mHandshakeHash; } - } - - internal TlsHandshakeHash PrepareToFinish() - { - TlsHandshakeHash result = mHandshakeHash; - this.mHandshakeHash = mHandshakeHash.StopTracking(); - return result; - } - - internal void SendMessage(byte msg_type, byte[] body) - { - TlsUtilities.CheckUint24(body.Length); - - if (mResendTimeout != null) - { - CheckInboundFlight(); - - mResendMillis = -1; - mResendTimeout = null; - - mOutboundFlight.Clear(); - } - - Message message = new Message(mMessageSeq++, msg_type, body); - - mOutboundFlight.Add(message); - - WriteMessage(message); - UpdateHandshakeMessagesDigest(message); - } - - internal byte[] ReceiveMessageBody(byte msg_type) - { - Message message = ReceiveMessage(); - if (message.Type != msg_type) - throw new TlsFatalAlert(AlertDescription.unexpected_message); - - return message.Body; - } - - internal Message ReceiveMessage() - { - long currentTimeMillis = DateTimeUtilities.CurrentUnixMs(); - - if (mResendTimeout == null) - { - mResendMillis = InitialResendMillis; - mResendTimeout = new Timeout(mResendMillis, currentTimeMillis); - - PrepareInboundFlight(Platform.CreateHashtable()); - } - - byte[] buf = null; - - for (;;) - { - if (mRecordLayer.IsClosed) - throw new TlsFatalAlert(AlertDescription.user_canceled); - - Message pending = GetPendingMessage(); - if (pending != null) - return pending; - - int handshakeMillis = Timeout.GetWaitMillis(mHandshakeTimeout, currentTimeMillis); - if (handshakeMillis < 0) - throw new TlsFatalAlert(AlertDescription.handshake_failure); - - int waitMillis = System.Math.Max(1, Timeout.GetWaitMillis(mResendTimeout, currentTimeMillis)); - if (handshakeMillis > 0) - { - waitMillis = System.Math.Min(waitMillis, handshakeMillis); - } - - int receiveLimit = mRecordLayer.GetReceiveLimit(); - if (buf == null || buf.Length < receiveLimit) - { - buf = new byte[receiveLimit]; - } - - int received = mRecordLayer.Receive(buf, 0, receiveLimit, waitMillis); - if (received < 0) - { - ResendOutboundFlight(); - } - else - { - ProcessRecord(MaxReceiveAhead, mRecordLayer.ReadEpoch, buf, 0, received); - } - - currentTimeMillis = DateTimeUtilities.CurrentUnixMs(); - } - } - - internal void Finish() - { - DtlsHandshakeRetransmit retransmit = null; - if (mResendTimeout != null) - { - CheckInboundFlight(); - } - else - { - PrepareInboundFlight(null); - - if (mPreviousInboundFlight != null) - { - /* - * RFC 6347 4.2.4. In addition, for at least twice the default MSL defined for [TCP], - * when in the FINISHED state, the node that transmits the last flight (the server in an - * ordinary handshake or the client in a resumed handshake) MUST respond to a retransmit - * of the peer's last flight with a retransmit of the last flight. - */ - retransmit = new Retransmit(this); - } - } - - mRecordLayer.HandshakeSuccessful(retransmit); - } - - internal void ResetHandshakeMessagesDigest() - { - mHandshakeHash.Reset(); - } - - private int BackOff(int timeoutMillis) - { - /* - * TODO[DTLS] implementations SHOULD back off handshake packet size during the - * retransmit backoff. - */ - return System.Math.Min(timeoutMillis * 2, MaxResendMillis); - } - - /** - * Check that there are no "extra" messages left in the current inbound flight - */ - private void CheckInboundFlight() - { - foreach (int key in mCurrentInboundFlight.Keys) - { - if (key >= mNextReceiveSeq) - { - // TODO Should this be considered an error? - } - } - } - - private Message GetPendingMessage() - { - DtlsReassembler next = (DtlsReassembler)mCurrentInboundFlight[mNextReceiveSeq]; - if (next != null) - { - byte[] body = next.GetBodyIfComplete(); - if (body != null) - { - mPreviousInboundFlight = null; - return UpdateHandshakeMessagesDigest(new Message(mNextReceiveSeq++, next.MsgType, body)); - } - } - return null; - } - - private void PrepareInboundFlight(IDictionary nextFlight) - { - ResetAll(mCurrentInboundFlight); - mPreviousInboundFlight = mCurrentInboundFlight; - mCurrentInboundFlight = nextFlight; - } - - private void ProcessRecord(int windowSize, int epoch, byte[] buf, int off, int len) - { - bool checkPreviousFlight = false; - - while (len >= MessageHeaderLength) - { - int fragment_length = TlsUtilities.ReadUint24(buf, off + 9); - int message_length = fragment_length + MessageHeaderLength; - if (len < message_length) - { - // NOTE: Truncated message - ignore it - break; - } - - int length = TlsUtilities.ReadUint24(buf, off + 1); - int fragment_offset = TlsUtilities.ReadUint24(buf, off + 6); - if (fragment_offset + fragment_length > length) - { - // NOTE: Malformed fragment - ignore it and the rest of the record - break; - } - - /* - * NOTE: This very simple epoch check will only work until we want to support - * renegotiation (and we're not likely to do that anyway). - */ - byte msg_type = TlsUtilities.ReadUint8(buf, off + 0); - int expectedEpoch = msg_type == HandshakeType.finished ? 1 : 0; - if (epoch != expectedEpoch) - { - break; - } - - int message_seq = TlsUtilities.ReadUint16(buf, off + 4); - if (message_seq >= (mNextReceiveSeq + windowSize)) - { - // NOTE: Too far ahead - ignore - } - else if (message_seq >= mNextReceiveSeq) - { - DtlsReassembler reassembler = (DtlsReassembler)mCurrentInboundFlight[message_seq]; - if (reassembler == null) - { - reassembler = new DtlsReassembler(msg_type, length); - mCurrentInboundFlight[message_seq] = reassembler; - } - - reassembler.ContributeFragment(msg_type, length, buf, off + MessageHeaderLength, fragment_offset, - fragment_length); - } - else if (mPreviousInboundFlight != null) - { - /* - * NOTE: If we receive the previous flight of incoming messages in full again, - * retransmit our last flight - */ - - DtlsReassembler reassembler = (DtlsReassembler)mPreviousInboundFlight[message_seq]; - if (reassembler != null) - { - reassembler.ContributeFragment(msg_type, length, buf, off + MessageHeaderLength, fragment_offset, - fragment_length); - checkPreviousFlight = true; - } - } - - off += message_length; - len -= message_length; - } - - if (checkPreviousFlight && CheckAll(mPreviousInboundFlight)) - { - ResendOutboundFlight(); - ResetAll(mPreviousInboundFlight); - } - } - - private void ResendOutboundFlight() - { - mRecordLayer.ResetWriteEpoch(); - for (int i = 0; i < mOutboundFlight.Count; ++i) - { - WriteMessage((Message)mOutboundFlight[i]); - } - - mResendMillis = BackOff(mResendMillis); - mResendTimeout = new Timeout(mResendMillis); - } - - private Message UpdateHandshakeMessagesDigest(Message message) - { - if (message.Type != HandshakeType.hello_request) - { - byte[] body = message.Body; - byte[] buf = new byte[MessageHeaderLength]; - TlsUtilities.WriteUint8(message.Type, buf, 0); - TlsUtilities.WriteUint24(body.Length, buf, 1); - TlsUtilities.WriteUint16(message.Seq, buf, 4); - TlsUtilities.WriteUint24(0, buf, 6); - TlsUtilities.WriteUint24(body.Length, buf, 9); - mHandshakeHash.BlockUpdate(buf, 0, buf.Length); - mHandshakeHash.BlockUpdate(body, 0, body.Length); - } - return message; - } - - private void WriteMessage(Message message) - { - int sendLimit = mRecordLayer.GetSendLimit(); - int fragmentLimit = sendLimit - MessageHeaderLength; - - // TODO Support a higher minimum fragment size? - if (fragmentLimit < 1) - { - // TODO Should we be throwing an exception here? - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - int length = message.Body.Length; - - // NOTE: Must still send a fragment if body is empty - int fragment_offset = 0; - do - { - int fragment_length = System.Math.Min(length - fragment_offset, fragmentLimit); - WriteHandshakeFragment(message, fragment_offset, fragment_length); - fragment_offset += fragment_length; - } - while (fragment_offset < length); - } - - private void WriteHandshakeFragment(Message message, int fragment_offset, int fragment_length) - { - RecordLayerBuffer fragment = new RecordLayerBuffer(MessageHeaderLength + fragment_length); - TlsUtilities.WriteUint8(message.Type, fragment); - TlsUtilities.WriteUint24(message.Body.Length, fragment); - TlsUtilities.WriteUint16(message.Seq, fragment); - TlsUtilities.WriteUint24(fragment_offset, fragment); - TlsUtilities.WriteUint24(fragment_length, fragment); - fragment.Write(message.Body, fragment_offset, fragment_length); - - fragment.SendToRecordLayer(mRecordLayer); - } - - private static bool CheckAll(IDictionary inboundFlight) - { - foreach (DtlsReassembler r in inboundFlight.Values) - { - if (r.GetBodyIfComplete() == null) - { - return false; - } - } - return true; - } - - private static void ResetAll(IDictionary inboundFlight) - { - foreach (DtlsReassembler r in inboundFlight.Values) - { - r.Reset(); - } - } - - internal class Message - { - private readonly int mMessageSeq; - private readonly byte mMsgType; - private readonly byte[] mBody; - - internal Message(int message_seq, byte msg_type, byte[] body) - { - this.mMessageSeq = message_seq; - this.mMsgType = msg_type; - this.mBody = body; - } - - public int Seq - { - get { return mMessageSeq; } - } - - public byte Type - { - get { return mMsgType; } - } - - public byte[] Body - { - get { return mBody; } - } - } - - internal class RecordLayerBuffer - : MemoryStream - { - internal RecordLayerBuffer(int size) - : base(size) - { - } - - internal void SendToRecordLayer(DtlsRecordLayer recordLayer) - { -#if PORTABLE - byte[] buf = ToArray(); - int bufLen = buf.Length; -#else - byte[] buf = GetBuffer(); - int bufLen = (int)Length; -#endif - - recordLayer.Send(buf, 0, bufLen); - Platform.Dispose(this); - } - } - - internal class Retransmit - : DtlsHandshakeRetransmit - { - private readonly DtlsReliableHandshake mOuter; - - internal Retransmit(DtlsReliableHandshake outer) - { - this.mOuter = outer; - } - - public void ReceivedHandshakeRecord(int epoch, byte[] buf, int off, int len) - { - mOuter.ProcessRecord(0, epoch, buf, off, len); - } - } - } -} diff --git a/crypto/src/crypto/tls/DtlsReplayWindow.cs b/crypto/src/crypto/tls/DtlsReplayWindow.cs deleted file mode 100644 index ea18e805e..000000000 --- a/crypto/src/crypto/tls/DtlsReplayWindow.cs +++ /dev/null @@ -1,85 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /** - * RFC 4347 4.1.2.5 Anti-replay - * <p/> - * Support fast rejection of duplicate records by maintaining a sliding receive window - */ - internal class DtlsReplayWindow - { - private const long VALID_SEQ_MASK = 0x0000FFFFFFFFFFFFL; - - private const long WINDOW_SIZE = 64L; - - private long mLatestConfirmedSeq = -1; - private long mBitmap = 0; - - /** - * Check whether a received record with the given sequence number should be rejected as a duplicate. - * - * @param seq the 48-bit DTLSPlainText.sequence_number field of a received record. - * @return true if the record should be discarded without further processing. - */ - internal bool ShouldDiscard(long seq) - { - if ((seq & VALID_SEQ_MASK) != seq) - return true; - - if (seq <= mLatestConfirmedSeq) - { - long diff = mLatestConfirmedSeq - seq; - if (diff >= WINDOW_SIZE) - return true; - if ((mBitmap & (1L << (int)diff)) != 0) - return true; - } - - return false; - } - - /** - * Report that a received record with the given sequence number passed authentication checks. - * - * @param seq the 48-bit DTLSPlainText.sequence_number field of an authenticated record. - */ - internal void ReportAuthenticated(long seq) - { - if ((seq & VALID_SEQ_MASK) != seq) - throw new ArgumentException("out of range", "seq"); - - if (seq <= mLatestConfirmedSeq) - { - long diff = mLatestConfirmedSeq - seq; - if (diff < WINDOW_SIZE) - { - mBitmap |= (1L << (int)diff); - } - } - else - { - long diff = seq - mLatestConfirmedSeq; - if (diff >= WINDOW_SIZE) - { - mBitmap = 1; - } - else - { - mBitmap <<= (int)diff; - mBitmap |= 1; - } - mLatestConfirmedSeq = seq; - } - } - - /** - * When a new epoch begins, sequence numbers begin again at 0 - */ - internal void Reset() - { - mLatestConfirmedSeq = -1; - mBitmap = 0; - } - } -} diff --git a/crypto/src/crypto/tls/DtlsServerProtocol.cs b/crypto/src/crypto/tls/DtlsServerProtocol.cs deleted file mode 100644 index b4ed75198..000000000 --- a/crypto/src/crypto/tls/DtlsServerProtocol.cs +++ /dev/null @@ -1,719 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Asn1.X509; -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Security; -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class DtlsServerProtocol - : DtlsProtocol - { - protected bool mVerifyRequests = true; - - public DtlsServerProtocol(SecureRandom secureRandom) - : base(secureRandom) - { - } - - public virtual bool VerifyRequests - { - get { return mVerifyRequests; } - set { this.mVerifyRequests = value; } - } - - public virtual DtlsTransport Accept(TlsServer server, DatagramTransport transport) - { - if (server == null) - throw new ArgumentNullException("server"); - if (transport == null) - throw new ArgumentNullException("transport"); - - SecurityParameters securityParameters = new SecurityParameters(); - securityParameters.entity = ConnectionEnd.server; - - ServerHandshakeState state = new ServerHandshakeState(); - state.server = server; - state.serverContext = new TlsServerContextImpl(mSecureRandom, securityParameters); - - securityParameters.serverRandom = TlsProtocol.CreateRandomBlock(server.ShouldUseGmtUnixTime(), - state.serverContext.NonceRandomGenerator); - - server.Init(state.serverContext); - - DtlsRecordLayer recordLayer = new DtlsRecordLayer(transport, state.serverContext, server, ContentType.handshake); - server.NotifyCloseHandle(recordLayer); - - // TODO Need to handle sending of HelloVerifyRequest without entering a full connection - - try - { - return ServerHandshake(state, recordLayer); - } - catch (TlsFatalAlert fatalAlert) - { - AbortServerHandshake(state, recordLayer, fatalAlert.AlertDescription); - throw fatalAlert; - } - catch (IOException e) - { - AbortServerHandshake(state, recordLayer, AlertDescription.internal_error); - throw e; - } - catch (Exception e) - { - AbortServerHandshake(state, recordLayer, AlertDescription.internal_error); - throw new TlsFatalAlert(AlertDescription.internal_error, e); - } - finally - { - securityParameters.Clear(); - } - } - - internal virtual void AbortServerHandshake(ServerHandshakeState state, DtlsRecordLayer recordLayer, byte alertDescription) - { - recordLayer.Fail(alertDescription); - InvalidateSession(state); - } - - internal virtual DtlsTransport ServerHandshake(ServerHandshakeState state, DtlsRecordLayer recordLayer) - { - SecurityParameters securityParameters = state.serverContext.SecurityParameters; - DtlsReliableHandshake handshake = new DtlsReliableHandshake(state.serverContext, recordLayer, - state.server.GetHandshakeTimeoutMillis()); - DtlsReliableHandshake.Message clientMessage = handshake.ReceiveMessage(); - - // NOTE: DTLSRecordLayer requires any DTLS version, we don't otherwise constrain this - //ProtocolVersion recordLayerVersion = recordLayer.ReadVersion; - - if (clientMessage.Type == HandshakeType.client_hello) - { - ProcessClientHello(state, clientMessage.Body); - } - else - { - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - - { - byte[] serverHelloBody = GenerateServerHello(state); - - ApplyMaxFragmentLengthExtension(recordLayer, securityParameters.maxFragmentLength); - - ProtocolVersion recordLayerVersion = state.serverContext.ServerVersion; - recordLayer.ReadVersion = recordLayerVersion; - recordLayer.SetWriteVersion(recordLayerVersion); - - handshake.SendMessage(HandshakeType.server_hello, serverHelloBody); - } - - handshake.NotifyHelloComplete(); - - IList serverSupplementalData = state.server.GetServerSupplementalData(); - if (serverSupplementalData != null) - { - byte[] supplementalDataBody = GenerateSupplementalData(serverSupplementalData); - handshake.SendMessage(HandshakeType.supplemental_data, supplementalDataBody); - } - - state.keyExchange = state.server.GetKeyExchange(); - state.keyExchange.Init(state.serverContext); - - state.serverCredentials = state.server.GetCredentials(); - - Certificate serverCertificate = null; - - if (state.serverCredentials == null) - { - state.keyExchange.SkipServerCredentials(); - } - else - { - state.keyExchange.ProcessServerCredentials(state.serverCredentials); - - serverCertificate = state.serverCredentials.Certificate; - byte[] certificateBody = GenerateCertificate(serverCertificate); - handshake.SendMessage(HandshakeType.certificate, certificateBody); - } - - // TODO[RFC 3546] Check whether empty certificates is possible, allowed, or excludes CertificateStatus - if (serverCertificate == null || serverCertificate.IsEmpty) - { - state.allowCertificateStatus = false; - } - - if (state.allowCertificateStatus) - { - CertificateStatus certificateStatus = state.server.GetCertificateStatus(); - if (certificateStatus != null) - { - byte[] certificateStatusBody = GenerateCertificateStatus(state, certificateStatus); - handshake.SendMessage(HandshakeType.certificate_status, certificateStatusBody); - } - } - - byte[] serverKeyExchange = state.keyExchange.GenerateServerKeyExchange(); - if (serverKeyExchange != null) - { - handshake.SendMessage(HandshakeType.server_key_exchange, serverKeyExchange); - } - - if (state.serverCredentials != null) - { - state.certificateRequest = state.server.GetCertificateRequest(); - if (state.certificateRequest != null) - { - if (TlsUtilities.IsTlsV12(state.serverContext) != (state.certificateRequest.SupportedSignatureAlgorithms != null)) - throw new TlsFatalAlert(AlertDescription.internal_error); - - state.keyExchange.ValidateCertificateRequest(state.certificateRequest); - - byte[] certificateRequestBody = GenerateCertificateRequest(state, state.certificateRequest); - handshake.SendMessage(HandshakeType.certificate_request, certificateRequestBody); - - TlsUtilities.TrackHashAlgorithms(handshake.HandshakeHash, - state.certificateRequest.SupportedSignatureAlgorithms); - } - } - - handshake.SendMessage(HandshakeType.server_hello_done, TlsUtilities.EmptyBytes); - - handshake.HandshakeHash.SealHashAlgorithms(); - - clientMessage = handshake.ReceiveMessage(); - - if (clientMessage.Type == HandshakeType.supplemental_data) - { - ProcessClientSupplementalData(state, clientMessage.Body); - clientMessage = handshake.ReceiveMessage(); - } - else - { - state.server.ProcessClientSupplementalData(null); - } - - if (state.certificateRequest == null) - { - state.keyExchange.SkipClientCredentials(); - } - else - { - if (clientMessage.Type == HandshakeType.certificate) - { - ProcessClientCertificate(state, clientMessage.Body); - clientMessage = handshake.ReceiveMessage(); - } - else - { - if (TlsUtilities.IsTlsV12(state.serverContext)) - { - /* - * RFC 5246 If no suitable certificate is available, the client MUST send a - * certificate message containing no certificates. - * - * NOTE: In previous RFCs, this was SHOULD instead of MUST. - */ - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - - NotifyClientCertificate(state, Certificate.EmptyChain); - } - } - - if (clientMessage.Type == HandshakeType.client_key_exchange) - { - ProcessClientKeyExchange(state, clientMessage.Body); - } - else - { - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - - TlsHandshakeHash prepareFinishHash = handshake.PrepareToFinish(); - securityParameters.sessionHash = TlsProtocol.GetCurrentPrfHash(state.serverContext, prepareFinishHash, null); - - TlsProtocol.EstablishMasterSecret(state.serverContext, state.keyExchange); - recordLayer.InitPendingEpoch(state.server.GetCipher()); - - /* - * RFC 5246 7.4.8 This message is only sent following a client certificate that has signing - * capability (i.e., all certificates except those containing fixed Diffie-Hellman - * parameters). - */ - if (ExpectCertificateVerifyMessage(state)) - { - byte[] certificateVerifyBody = handshake.ReceiveMessageBody(HandshakeType.certificate_verify); - ProcessCertificateVerify(state, certificateVerifyBody, prepareFinishHash); - } - - // NOTE: Calculated exclusive of the actual Finished message from the client - byte[] expectedClientVerifyData = TlsUtilities.CalculateVerifyData(state.serverContext, ExporterLabel.client_finished, - TlsProtocol.GetCurrentPrfHash(state.serverContext, handshake.HandshakeHash, null)); - ProcessFinished(handshake.ReceiveMessageBody(HandshakeType.finished), expectedClientVerifyData); - - if (state.expectSessionTicket) - { - NewSessionTicket newSessionTicket = state.server.GetNewSessionTicket(); - byte[] newSessionTicketBody = GenerateNewSessionTicket(state, newSessionTicket); - handshake.SendMessage(HandshakeType.session_ticket, newSessionTicketBody); - } - - // NOTE: Calculated exclusive of the Finished message itself - byte[] serverVerifyData = TlsUtilities.CalculateVerifyData(state.serverContext, ExporterLabel.server_finished, - TlsProtocol.GetCurrentPrfHash(state.serverContext, handshake.HandshakeHash, null)); - handshake.SendMessage(HandshakeType.finished, serverVerifyData); - - handshake.Finish(); - - //{ - // state.sessionParameters = new SessionParameters.Builder() - // .SetCipherSuite(securityParameters.CipherSuite) - // .SetCompressionAlgorithm(securityParameters.CompressionAlgorithm) - // .SetExtendedMasterSecret(securityParameters.IsExtendedMasterSecret) - // .SetMasterSecret(securityParameters.MasterSecret) - // .SetPeerCertificate(state.clientCertificate) - // .SetPskIdentity(securityParameters.PskIdentity) - // .SetSrpIdentity(securityParameters.SrpIdentity) - // // TODO Consider filtering extensions that aren't relevant to resumed sessions - // .SetServerExtensions(state.serverExtensions) - // .Build(); - - // state.tlsSession = TlsUtilities.ImportSession(state.tlsSession.SessionID, state.sessionParameters); - - // state.serverContext.SetResumableSession(state.tlsSession); - //} - - state.server.NotifyHandshakeComplete(); - - return new DtlsTransport(recordLayer); - } - - protected virtual void InvalidateSession(ServerHandshakeState state) - { - if (state.sessionParameters != null) - { - state.sessionParameters.Clear(); - state.sessionParameters = null; - } - - if (state.tlsSession != null) - { - state.tlsSession.Invalidate(); - state.tlsSession = null; - } - } - - protected virtual byte[] GenerateCertificateRequest(ServerHandshakeState state, CertificateRequest certificateRequest) - { - MemoryStream buf = new MemoryStream(); - certificateRequest.Encode(buf); - return buf.ToArray(); - } - - protected virtual byte[] GenerateCertificateStatus(ServerHandshakeState state, CertificateStatus certificateStatus) - { - MemoryStream buf = new MemoryStream(); - certificateStatus.Encode(buf); - return buf.ToArray(); - } - - protected virtual byte[] GenerateNewSessionTicket(ServerHandshakeState state, NewSessionTicket newSessionTicket) - { - MemoryStream buf = new MemoryStream(); - newSessionTicket.Encode(buf); - return buf.ToArray(); - } - - protected virtual byte[] GenerateServerHello(ServerHandshakeState state) - { - SecurityParameters securityParameters = state.serverContext.SecurityParameters; - - MemoryStream buf = new MemoryStream(); - - { - ProtocolVersion server_version = state.server.GetServerVersion(); - if (!server_version.IsEqualOrEarlierVersionOf(state.serverContext.ClientVersion)) - throw new TlsFatalAlert(AlertDescription.internal_error); - - // TODO Read RFCs for guidance on the expected record layer version number - // recordStream.setReadVersion(server_version); - // recordStream.setWriteVersion(server_version); - // recordStream.setRestrictReadVersion(true); - state.serverContext.SetServerVersion(server_version); - - TlsUtilities.WriteVersion(state.serverContext.ServerVersion, buf); - } - - buf.Write(securityParameters.ServerRandom, 0, securityParameters.ServerRandom.Length); - - /* - * The server may return an empty session_id to indicate that the session will not be cached - * and therefore cannot be resumed. - */ - TlsUtilities.WriteOpaque8(TlsUtilities.EmptyBytes, buf); - - int selectedCipherSuite = state.server.GetSelectedCipherSuite(); - if (!Arrays.Contains(state.offeredCipherSuites, selectedCipherSuite) - || selectedCipherSuite == CipherSuite.TLS_NULL_WITH_NULL_NULL - || CipherSuite.IsScsv(selectedCipherSuite) - || !TlsUtilities.IsValidCipherSuiteForVersion(selectedCipherSuite, state.serverContext.ServerVersion)) - { - throw new TlsFatalAlert(AlertDescription.internal_error); - } - ValidateSelectedCipherSuite(selectedCipherSuite, AlertDescription.internal_error); - securityParameters.cipherSuite = selectedCipherSuite; - - byte selectedCompressionMethod = state.server.GetSelectedCompressionMethod(); - if (!Arrays.Contains(state.offeredCompressionMethods, selectedCompressionMethod)) - throw new TlsFatalAlert(AlertDescription.internal_error); - securityParameters.compressionAlgorithm = selectedCompressionMethod; - - TlsUtilities.WriteUint16(selectedCipherSuite, buf); - TlsUtilities.WriteUint8(selectedCompressionMethod, buf); - - state.serverExtensions = TlsExtensionsUtilities.EnsureExtensionsInitialised(state.server.GetServerExtensions()); - - /* - * RFC 5746 3.6. Server Behavior: Initial Handshake - */ - if (state.secure_renegotiation) - { - byte[] renegExtData = TlsUtilities.GetExtensionData(state.serverExtensions, ExtensionType.renegotiation_info); - bool noRenegExt = (null == renegExtData); - - if (noRenegExt) - { - /* - * Note that sending a "renegotiation_info" extension in response to a ClientHello - * containing only the SCSV is an explicit exception to the prohibition in RFC 5246, - * Section 7.4.1.4, on the server sending unsolicited extensions and is only allowed - * because the client is signaling its willingness to receive the extension via the - * TLS_EMPTY_RENEGOTIATION_INFO_SCSV SCSV. - */ - - /* - * If the secure_renegotiation flag is set to TRUE, the server MUST include an empty - * "renegotiation_info" extension in the ServerHello message. - */ - state.serverExtensions[ExtensionType.renegotiation_info] = TlsProtocol.CreateRenegotiationInfo(TlsUtilities.EmptyBytes); - } - } - - if (securityParameters.IsExtendedMasterSecret) - { - TlsExtensionsUtilities.AddExtendedMasterSecretExtension(state.serverExtensions); - } - - /* - * TODO RFC 3546 2.3 If [...] the older session is resumed, then the server MUST ignore - * extensions appearing in the client hello, and send a server hello containing no - * extensions. - */ - - if (state.serverExtensions.Count > 0) - { - securityParameters.encryptThenMac = TlsExtensionsUtilities.HasEncryptThenMacExtension(state.serverExtensions); - - securityParameters.maxFragmentLength = EvaluateMaxFragmentLengthExtension(state.resumedSession, - state.clientExtensions, state.serverExtensions, AlertDescription.internal_error); - - securityParameters.truncatedHMac = TlsExtensionsUtilities.HasTruncatedHMacExtension(state.serverExtensions); - - /* - * TODO It's surprising that there's no provision to allow a 'fresh' CertificateStatus to be sent in - * a session resumption handshake. - */ - state.allowCertificateStatus = !state.resumedSession - && TlsUtilities.HasExpectedEmptyExtensionData(state.serverExtensions, ExtensionType.status_request, - AlertDescription.internal_error); - - state.expectSessionTicket = !state.resumedSession - && TlsUtilities.HasExpectedEmptyExtensionData(state.serverExtensions, ExtensionType.session_ticket, - AlertDescription.internal_error); - - TlsProtocol.WriteExtensions(buf, state.serverExtensions); - } - - securityParameters.prfAlgorithm = TlsProtocol.GetPrfAlgorithm(state.serverContext, - securityParameters.CipherSuite); - - /* - * RFC 5246 7.4.9. Any cipher suite which does not explicitly specify verify_data_length - * has a verify_data_length equal to 12. This includes all existing cipher suites. - */ - securityParameters.verifyDataLength = 12; - - return buf.ToArray(); - } - - protected virtual void NotifyClientCertificate(ServerHandshakeState state, Certificate clientCertificate) - { - if (state.certificateRequest == null) - throw new InvalidOperationException(); - - if (state.clientCertificate != null) - throw new TlsFatalAlert(AlertDescription.unexpected_message); - - state.clientCertificate = clientCertificate; - - if (clientCertificate.IsEmpty) - { - state.keyExchange.SkipClientCredentials(); - } - else - { - - /* - * TODO RFC 5246 7.4.6. If the certificate_authorities list in the certificate request - * message was non-empty, one of the certificates in the certificate chain SHOULD be - * issued by one of the listed CAs. - */ - - state.clientCertificateType = TlsUtilities.GetClientCertificateType(clientCertificate, - state.serverCredentials.Certificate); - - state.keyExchange.ProcessClientCertificate(clientCertificate); - } - - /* - * RFC 5246 7.4.6. If the client does not send any certificates, the server MAY at its - * discretion either continue the handshake without client authentication, or respond with a - * fatal handshake_failure alert. Also, if some aspect of the certificate chain was - * unacceptable (e.g., it was not signed by a known, trusted CA), the server MAY at its - * discretion either continue the handshake (considering the client unauthenticated) or send - * a fatal alert. - */ - state.server.NotifyClientCertificate(clientCertificate); - } - - protected virtual void ProcessClientCertificate(ServerHandshakeState state, byte[] body) - { - MemoryStream buf = new MemoryStream(body, false); - - Certificate clientCertificate = Certificate.Parse(buf); - - TlsProtocol.AssertEmpty(buf); - - NotifyClientCertificate(state, clientCertificate); - } - - protected virtual void ProcessCertificateVerify(ServerHandshakeState state, byte[] body, TlsHandshakeHash prepareFinishHash) - { - if (state.certificateRequest == null) - throw new InvalidOperationException(); - - MemoryStream buf = new MemoryStream(body, false); - - TlsServerContextImpl context = state.serverContext; - DigitallySigned clientCertificateVerify = DigitallySigned.Parse(context, buf); - - TlsProtocol.AssertEmpty(buf); - - // Verify the CertificateVerify message contains a correct signature. - try - { - SignatureAndHashAlgorithm signatureAlgorithm = clientCertificateVerify.Algorithm; - - byte[] hash; - if (TlsUtilities.IsTlsV12(context)) - { - TlsUtilities.VerifySupportedSignatureAlgorithm(state.certificateRequest.SupportedSignatureAlgorithms, signatureAlgorithm); - hash = prepareFinishHash.GetFinalHash(signatureAlgorithm.Hash); - } - else - { - hash = context.SecurityParameters.SessionHash; - } - - X509CertificateStructure x509Cert = state.clientCertificate.GetCertificateAt(0); - SubjectPublicKeyInfo keyInfo = x509Cert.SubjectPublicKeyInfo; - AsymmetricKeyParameter publicKey = PublicKeyFactory.CreateKey(keyInfo); - - TlsSigner tlsSigner = TlsUtilities.CreateTlsSigner((byte)state.clientCertificateType); - tlsSigner.Init(context); - if (!tlsSigner.VerifyRawSignature(signatureAlgorithm, clientCertificateVerify.Signature, publicKey, hash)) - throw new TlsFatalAlert(AlertDescription.decrypt_error); - } - catch (TlsFatalAlert e) - { - throw e; - } - catch (Exception e) - { - throw new TlsFatalAlert(AlertDescription.decrypt_error, e); - } - } - - protected virtual void ProcessClientHello(ServerHandshakeState state, byte[] body) - { - MemoryStream buf = new MemoryStream(body, false); - - // TODO Read RFCs for guidance on the expected record layer version number - ProtocolVersion client_version = TlsUtilities.ReadVersion(buf); - if (!client_version.IsDtls) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - - /* - * Read the client random - */ - byte[] client_random = TlsUtilities.ReadFully(32, buf); - - byte[] sessionID = TlsUtilities.ReadOpaque8(buf); - if (sessionID.Length > 32) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - - // TODO RFC 4347 has the cookie length restricted to 32, but not in RFC 6347 - byte[] cookie = TlsUtilities.ReadOpaque8(buf); - - int cipher_suites_length = TlsUtilities.ReadUint16(buf); - if (cipher_suites_length < 2 || (cipher_suites_length & 1) != 0) - { - throw new TlsFatalAlert(AlertDescription.decode_error); - } - - /* - * NOTE: "If the session_id field is not empty (implying a session resumption request) this - * vector must include at least the cipher_suite from that session." - */ - state.offeredCipherSuites = TlsUtilities.ReadUint16Array(cipher_suites_length / 2, buf); - - int compression_methods_length = TlsUtilities.ReadUint8(buf); - if (compression_methods_length < 1) - { - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - - state.offeredCompressionMethods = TlsUtilities.ReadUint8Array(compression_methods_length, buf); - - /* - * TODO RFC 3546 2.3 If [...] the older session is resumed, then the server MUST ignore - * extensions appearing in the client hello, and send a server hello containing no - * extensions. - */ - state.clientExtensions = TlsProtocol.ReadExtensions(buf); - - TlsServerContextImpl context = state.serverContext; - SecurityParameters securityParameters = context.SecurityParameters; - - /* - * TODO[resumption] Check RFC 7627 5.4. for required behaviour - */ - - /* - * RFC 7627 4. Clients and servers SHOULD NOT accept handshakes that do not use the extended - * master secret [..]. (and see 5.2, 5.3) - */ - securityParameters.extendedMasterSecret = TlsExtensionsUtilities.HasExtendedMasterSecretExtension(state.clientExtensions); - if (!securityParameters.IsExtendedMasterSecret && state.server.RequiresExtendedMasterSecret()) - { - throw new TlsFatalAlert(AlertDescription.handshake_failure); - } - - context.SetClientVersion(client_version); - - state.server.NotifyClientVersion(client_version); - state.server.NotifyFallback(Arrays.Contains(state.offeredCipherSuites, CipherSuite.TLS_FALLBACK_SCSV)); - - securityParameters.clientRandom = client_random; - - state.server.NotifyOfferedCipherSuites(state.offeredCipherSuites); - state.server.NotifyOfferedCompressionMethods(state.offeredCompressionMethods); - - /* - * RFC 5746 3.6. Server Behavior: Initial Handshake - */ - { - /* - * RFC 5746 3.4. The client MUST include either an empty "renegotiation_info" extension, - * or the TLS_EMPTY_RENEGOTIATION_INFO_SCSV signaling cipher suite value in the - * ClientHello. Including both is NOT RECOMMENDED. - */ - - /* - * When a ClientHello is received, the server MUST check if it includes the - * TLS_EMPTY_RENEGOTIATION_INFO_SCSV SCSV. If it does, set the secure_renegotiation flag - * to TRUE. - */ - if (Arrays.Contains(state.offeredCipherSuites, CipherSuite.TLS_EMPTY_RENEGOTIATION_INFO_SCSV)) - { - state.secure_renegotiation = true; - } - - /* - * The server MUST check if the "renegotiation_info" extension is included in the - * ClientHello. - */ - byte[] renegExtData = TlsUtilities.GetExtensionData(state.clientExtensions, ExtensionType.renegotiation_info); - if (renegExtData != null) - { - /* - * If the extension is present, set secure_renegotiation flag to TRUE. The - * server MUST then verify that the length of the "renegotiated_connection" - * field is zero, and if it is not, MUST abort the handshake. - */ - state.secure_renegotiation = true; - - if (!Arrays.ConstantTimeAreEqual(renegExtData, TlsProtocol.CreateRenegotiationInfo(TlsUtilities.EmptyBytes))) - throw new TlsFatalAlert(AlertDescription.handshake_failure); - } - } - - state.server.NotifySecureRenegotiation(state.secure_renegotiation); - - if (state.clientExtensions != null) - { - // NOTE: Validates the padding extension data, if present - TlsExtensionsUtilities.GetPaddingExtension(state.clientExtensions); - - state.server.ProcessClientExtensions(state.clientExtensions); - } - } - - protected virtual void ProcessClientKeyExchange(ServerHandshakeState state, byte[] body) - { - MemoryStream buf = new MemoryStream(body, false); - - state.keyExchange.ProcessClientKeyExchange(buf); - - TlsProtocol.AssertEmpty(buf); - } - - protected virtual void ProcessClientSupplementalData(ServerHandshakeState state, byte[] body) - { - MemoryStream buf = new MemoryStream(body, false); - IList clientSupplementalData = TlsProtocol.ReadSupplementalDataMessage(buf); - state.server.ProcessClientSupplementalData(clientSupplementalData); - } - - protected virtual bool ExpectCertificateVerifyMessage(ServerHandshakeState state) - { - return state.clientCertificateType >= 0 && TlsUtilities.HasSigningCapability((byte)state.clientCertificateType); - } - - protected internal class ServerHandshakeState - { - internal TlsServer server = null; - internal TlsServerContextImpl serverContext = null; - internal TlsSession tlsSession = null; - internal SessionParameters sessionParameters = null; - internal SessionParameters.Builder sessionParametersBuilder = null; - internal int[] offeredCipherSuites = null; - internal byte[] offeredCompressionMethods = null; - internal IDictionary clientExtensions = null; - internal IDictionary serverExtensions = null; - internal bool resumedSession = false; - internal bool secure_renegotiation = false; - internal bool allowCertificateStatus = false; - internal bool expectSessionTicket = false; - internal TlsKeyExchange keyExchange = null; - internal TlsCredentials serverCredentials = null; - internal CertificateRequest certificateRequest = null; - internal short clientCertificateType = -1; - internal Certificate clientCertificate = null; - } - } -} diff --git a/crypto/src/crypto/tls/DtlsTransport.cs b/crypto/src/crypto/tls/DtlsTransport.cs deleted file mode 100644 index f2f716561..000000000 --- a/crypto/src/crypto/tls/DtlsTransport.cs +++ /dev/null @@ -1,132 +0,0 @@ -using System; -using System.IO; -#if !PORTABLE || DOTNET -using System.Net.Sockets; -#endif - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class DtlsTransport - : DatagramTransport - { - private readonly DtlsRecordLayer mRecordLayer; - - internal DtlsTransport(DtlsRecordLayer recordLayer) - { - this.mRecordLayer = recordLayer; - } - - public virtual int GetReceiveLimit() - { - return mRecordLayer.GetReceiveLimit(); - } - - public virtual int GetSendLimit() - { - return mRecordLayer.GetSendLimit(); - } - - public virtual int Receive(byte[] buf, int off, int len, int waitMillis) - { - if (null == buf) - throw new ArgumentNullException("buf"); - if (off < 0 || off >= buf.Length) - throw new ArgumentException("invalid offset: " + off, "off"); - if (len < 0 || len > buf.Length - off) - throw new ArgumentException("invalid length: " + len, "len"); - if (waitMillis < 0) - throw new ArgumentException("cannot be negative", "waitMillis"); - - try - { - return mRecordLayer.Receive(buf, off, len, waitMillis); - } - catch (TlsFatalAlert fatalAlert) - { - mRecordLayer.Fail(fatalAlert.AlertDescription); - throw fatalAlert; - } - catch (TlsTimeoutException e) - { - throw e; - } -#if !PORTABLE || DOTNET - catch (SocketException e) - { - if (TlsUtilities.IsTimeout(e)) - throw e; - - mRecordLayer.Fail(AlertDescription.internal_error); - throw new TlsFatalAlert(AlertDescription.internal_error, e); - } -#endif - //catch (InterruptedIOException e) - //{ - // throw e; - //} - catch (IOException e) - { - mRecordLayer.Fail(AlertDescription.internal_error); - throw e; - } - catch (Exception e) - { - mRecordLayer.Fail(AlertDescription.internal_error); - throw new TlsFatalAlert(AlertDescription.internal_error, e); - } - } - - public virtual void Send(byte[] buf, int off, int len) - { - if (null == buf) - throw new ArgumentNullException("buf"); - if (off < 0 || off >= buf.Length) - throw new ArgumentException("invalid offset: " + off, "off"); - if (len < 0 || len > buf.Length - off) - throw new ArgumentException("invalid length: " + len, "len"); - - try - { - mRecordLayer.Send(buf, off, len); - } - catch (TlsFatalAlert fatalAlert) - { - mRecordLayer.Fail(fatalAlert.AlertDescription); - throw fatalAlert; - } - catch (TlsTimeoutException e) - { - throw e; - } -#if !PORTABLE || DOTNET - catch (SocketException e) - { - if (TlsUtilities.IsTimeout(e)) - throw e; - - mRecordLayer.Fail(AlertDescription.internal_error); - throw new TlsFatalAlert(AlertDescription.internal_error, e); - } -#endif - //catch (InterruptedIOException e) - //{ - // throw e; - //} - catch (IOException e) - { - mRecordLayer.Fail(AlertDescription.internal_error); - throw e; - } - catch (Exception e) - { - mRecordLayer.Fail(AlertDescription.internal_error); - throw new TlsFatalAlert(AlertDescription.internal_error, e); - } - } - - public virtual void Close() - { - mRecordLayer.Close(); - } - } -} diff --git a/crypto/src/crypto/tls/ECBasisType.cs b/crypto/src/crypto/tls/ECBasisType.cs deleted file mode 100644 index 5416e17c0..000000000 --- a/crypto/src/crypto/tls/ECBasisType.cs +++ /dev/null @@ -1,16 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary>RFC 4492 5.4. (Errata ID: 2389)</summary> - public abstract class ECBasisType - { - public const byte ec_basis_trinomial = 1; - public const byte ec_basis_pentanomial = 2; - - public static bool IsValid(byte ecBasisType) - { - return ecBasisType >= ec_basis_trinomial && ecBasisType <= ec_basis_pentanomial; - } - } -} diff --git a/crypto/src/crypto/tls/ECCurveType.cs b/crypto/src/crypto/tls/ECCurveType.cs deleted file mode 100644 index 1b352e9c4..000000000 --- a/crypto/src/crypto/tls/ECCurveType.cs +++ /dev/null @@ -1,29 +0,0 @@ -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary> - /// RFC 4492 5.4 - /// </summary> - public abstract class ECCurveType - { - /** - * Indicates the elliptic curve domain parameters are conveyed verbosely, and the - * underlying finite field is a prime field. - */ - public const byte explicit_prime = 1; - - /** - * Indicates the elliptic curve domain parameters are conveyed verbosely, and the - * underlying finite field is a characteristic-2 field. - */ - public const byte explicit_char2 = 2; - - /** - * Indicates that a named curve is used. This option SHOULD be used when applicable. - */ - public const byte named_curve = 3; - - /* - * Values 248 through 255 are reserved for private use. - */ - } -} diff --git a/crypto/src/crypto/tls/ECPointFormat.cs b/crypto/src/crypto/tls/ECPointFormat.cs deleted file mode 100644 index 21b0fdd97..000000000 --- a/crypto/src/crypto/tls/ECPointFormat.cs +++ /dev/null @@ -1,16 +0,0 @@ -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary> - /// RFC 4492 5.1.2 - /// </summary> - public abstract class ECPointFormat - { - public const byte uncompressed = 0; - public const byte ansiX962_compressed_prime = 1; - public const byte ansiX962_compressed_char2 = 2; - - /* - * reserved (248..255) - */ - } -} diff --git a/crypto/src/crypto/tls/EncryptionAlgorithm.cs b/crypto/src/crypto/tls/EncryptionAlgorithm.cs deleted file mode 100644 index 45eef18e3..000000000 --- a/crypto/src/crypto/tls/EncryptionAlgorithm.cs +++ /dev/null @@ -1,69 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary>RFC 2246</summary> - /// <remarks> - /// Note that the values here are implementation-specific and arbitrary. It is recommended not to - /// depend on the particular values (e.g. serialization). - /// </remarks> - public abstract class EncryptionAlgorithm - { - public const int NULL = 0; - public const int RC4_40 = 1; - public const int RC4_128 = 2; - public const int RC2_CBC_40 = 3; - public const int IDEA_CBC = 4; - public const int DES40_CBC = 5; - public const int DES_CBC = 6; - public const int cls_3DES_EDE_CBC = 7; - - /* - * RFC 3268 - */ - public const int AES_128_CBC = 8; - public const int AES_256_CBC = 9; - - /* - * RFC 5289 - */ - public const int AES_128_GCM = 10; - public const int AES_256_GCM = 11; - - /* - * RFC 4132 - */ - public const int CAMELLIA_128_CBC = 12; - public const int CAMELLIA_256_CBC = 13; - - /* - * RFC 4162 - */ - public const int SEED_CBC = 14; - - /* - * RFC 6655 - */ - public const int AES_128_CCM = 15; - public const int AES_128_CCM_8 = 16; - public const int AES_256_CCM = 17; - public const int AES_256_CCM_8 = 18; - - /* - * RFC 6367 - */ - public const int CAMELLIA_128_GCM = 19; - public const int CAMELLIA_256_GCM = 20; - - /* - * RFC 7905 - */ - public const int CHACHA20_POLY1305 = 21; - - /* - * draft-zauner-tls-aes-ocb-04 - */ - public const int AES_128_OCB_TAGLEN96 = 103; - public const int AES_256_OCB_TAGLEN96 = 104; - } -} diff --git a/crypto/src/crypto/tls/ExporterLabel.cs b/crypto/src/crypto/tls/ExporterLabel.cs deleted file mode 100644 index 12603f3ff..000000000 --- a/crypto/src/crypto/tls/ExporterLabel.cs +++ /dev/null @@ -1,37 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary>RFC 5705</summary> - public abstract class ExporterLabel - { - /* - * RFC 5246 - */ - public const string client_finished = "client finished"; - public const string server_finished = "server finished"; - public const string master_secret = "master secret"; - public const string key_expansion = "key expansion"; - - /* - * RFC 5216 - */ - public const string client_EAP_encryption = "client EAP encryption"; - - /* - * RFC 5281 - */ - public const string ttls_keying_material = "ttls keying material"; - public const string ttls_challenge = "ttls challenge"; - - /* - * RFC 5764 - */ - public const string dtls_srtp = "EXTRACTOR-dtls_srtp"; - - /* - * RFC 7627 - */ - public static readonly string extended_master_secret = "extended master secret"; - } -} diff --git a/crypto/src/crypto/tls/ExtensionType.cs b/crypto/src/crypto/tls/ExtensionType.cs deleted file mode 100644 index f17210b80..000000000 --- a/crypto/src/crypto/tls/ExtensionType.cs +++ /dev/null @@ -1,128 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class ExtensionType - { - /* - * RFC 2546 2.3. - */ - public const int server_name = 0; - public const int max_fragment_length = 1; - public const int client_certificate_url = 2; - public const int trusted_ca_keys = 3; - public const int truncated_hmac = 4; - public const int status_request = 5; - - /* - * RFC 4681 - */ - public const int user_mapping = 6; - - /* - * RFC 5878 - */ - public const int client_authz = 7; - public const int server_authz = 8; - - /* - * RFC RFC6091 - */ - public const int cert_type = 9; - - /* - * draft-ietf-tls-negotiated-ff-dhe-10 - */ - public const int supported_groups = 10; - - /* - * RFC 4492 5.1. - */ - [Obsolete("Use 'supported_groups' instead")] - public const int elliptic_curves = supported_groups; - public const int ec_point_formats = 11; - - /* - * RFC 5054 2.8.1. - */ - public const int srp = 12; - - /* - * RFC 5246 7.4.1.4. - */ - public const int signature_algorithms = 13; - - /* - * RFC 5764 9. - */ - public const int use_srtp = 14; - - /* - * RFC 6520 6. - */ - public const int heartbeat = 15; - - /* - * RFC 7301 - */ - public const int application_layer_protocol_negotiation = 16; - - /* - * RFC 6961 - */ - public const int status_request_v2 = 17; - - /* - * RFC 6962 - */ - public const int signed_certificate_timestamp = 18; - - /* - * RFC 7250 - */ - public const int client_certificate_type = 19; - public const int server_certificate_type = 20; - - /* - * RFC 7685 - */ - public const int padding = 21; - - /* - * RFC 7366 - */ - public const int encrypt_then_mac = 22; - - /* - * RFC 7627 - */ - public const int extended_master_secret = 23; - - /* - * draft-ietf-tokbind-negotiation-08 - */ - public static readonly int DRAFT_token_binding = 24; - - /* - * RFC 7924 - */ - public const int cached_info = 25; - - /* - * RFC 5077 7. - */ - public const int session_ticket = 35; - - /* - * draft-ietf-tls-negotiated-ff-dhe-01 - * - * WARNING: Placeholder value; the real value is TBA - */ - public static readonly int negotiated_ff_dhe_groups = 101; - - /* - * RFC 5746 3.2. - */ - public const int renegotiation_info = 0xff01; - } -} diff --git a/crypto/src/crypto/tls/FiniteFieldDheGroup.cs b/crypto/src/crypto/tls/FiniteFieldDheGroup.cs deleted file mode 100644 index 437504941..000000000 --- a/crypto/src/crypto/tls/FiniteFieldDheGroup.cs +++ /dev/null @@ -1,21 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /* - * draft-ietf-tls-negotiated-ff-dhe-01 - */ - public abstract class FiniteFieldDheGroup - { - public const byte ffdhe2432 = 0; - public const byte ffdhe3072 = 1; - public const byte ffdhe4096 = 2; - public const byte ffdhe6144 = 3; - public const byte ffdhe8192 = 4; - - public static bool IsValid(byte group) - { - return group >= ffdhe2432 && group <= ffdhe8192; - } - } -} diff --git a/crypto/src/crypto/tls/HandshakeType.cs b/crypto/src/crypto/tls/HandshakeType.cs deleted file mode 100644 index e63042ac3..000000000 --- a/crypto/src/crypto/tls/HandshakeType.cs +++ /dev/null @@ -1,40 +0,0 @@ -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class HandshakeType - { - /* - * RFC 2246 7.4 - */ - public const byte hello_request = 0; - public const byte client_hello = 1; - public const byte server_hello = 2; - public const byte certificate = 11; - public const byte server_key_exchange = 12; - public const byte certificate_request = 13; - public const byte server_hello_done = 14; - public const byte certificate_verify = 15; - public const byte client_key_exchange = 16; - public const byte finished = 20; - - /* - * RFC 3546 2.4 - */ - public const byte certificate_url = 21; - public const byte certificate_status = 22; - - /* - * (DTLS) RFC 4347 4.3.2 - */ - public const byte hello_verify_request = 3; - - /* - * RFC 4680 - */ - public const byte supplemental_data = 23; - - /* - * RFC 5077 - */ - public const byte session_ticket = 4; - } -} diff --git a/crypto/src/crypto/tls/HashAlgorithm.cs b/crypto/src/crypto/tls/HashAlgorithm.cs deleted file mode 100644 index a6b42d4ed..000000000 --- a/crypto/src/crypto/tls/HashAlgorithm.cs +++ /dev/null @@ -1,65 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary>RFC 5246 7.4.1.4.1</summary> - public abstract class HashAlgorithm - { - public const byte none = 0; - public const byte md5 = 1; - public const byte sha1 = 2; - public const byte sha224 = 3; - public const byte sha256 = 4; - public const byte sha384 = 5; - public const byte sha512 = 6; - - public static string GetName(byte hashAlgorithm) - { - switch (hashAlgorithm) - { - case none: - return "none"; - case md5: - return "md5"; - case sha1: - return "sha1"; - case sha224: - return "sha224"; - case sha256: - return "sha256"; - case sha384: - return "sha384"; - case sha512: - return "sha512"; - default: - return "UNKNOWN"; - } - } - - public static string GetText(byte hashAlgorithm) - { - return GetName(hashAlgorithm) + "(" + hashAlgorithm + ")"; - } - - public static bool IsPrivate(byte hashAlgorithm) - { - return 224 <= hashAlgorithm && hashAlgorithm <= 255; - } - - public static bool IsRecognized(byte hashAlgorithm) - { - switch (hashAlgorithm) - { - case md5: - case sha1: - case sha224: - case sha256: - case sha384: - case sha512: - return true; - default: - return false; - } - } - } -} diff --git a/crypto/src/crypto/tls/HeartbeatExtension.cs b/crypto/src/crypto/tls/HeartbeatExtension.cs deleted file mode 100644 index 049837266..000000000 --- a/crypto/src/crypto/tls/HeartbeatExtension.cs +++ /dev/null @@ -1,52 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class HeartbeatExtension - { - protected readonly byte mMode; - - public HeartbeatExtension(byte mode) - { - if (!HeartbeatMode.IsValid(mode)) - throw new ArgumentException("not a valid HeartbeatMode value", "mode"); - - this.mMode = mode; - } - - public virtual byte Mode - { - get { return mMode; } - } - - /** - * Encode this {@link HeartbeatExtension} to a {@link Stream}. - * - * @param output - * the {@link Stream} to encode to. - * @throws IOException - */ - public virtual void Encode(Stream output) - { - TlsUtilities.WriteUint8(mMode, output); - } - - /** - * Parse a {@link HeartbeatExtension} from a {@link Stream}. - * - * @param input - * the {@link Stream} to parse from. - * @return a {@link HeartbeatExtension} object. - * @throws IOException - */ - public static HeartbeatExtension Parse(Stream input) - { - byte mode = TlsUtilities.ReadUint8(input); - if (!HeartbeatMode.IsValid(mode)) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - - return new HeartbeatExtension(mode); - } - } -} diff --git a/crypto/src/crypto/tls/HeartbeatMessage.cs b/crypto/src/crypto/tls/HeartbeatMessage.cs deleted file mode 100644 index 3f22f7e1d..000000000 --- a/crypto/src/crypto/tls/HeartbeatMessage.cs +++ /dev/null @@ -1,109 +0,0 @@ -using System; -using System.IO; - -using Org.BouncyCastle.Utilities; -using Org.BouncyCastle.Utilities.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class HeartbeatMessage - { - protected readonly byte mType; - protected readonly byte[] mPayload; - protected readonly int mPaddingLength; - - public HeartbeatMessage(byte type, byte[] payload, int paddingLength) - { - if (!HeartbeatMessageType.IsValid(type)) - throw new ArgumentException("not a valid HeartbeatMessageType value", "type"); - if (payload == null || payload.Length >= (1 << 16)) - throw new ArgumentException("must have length < 2^16", "payload"); - if (paddingLength < 16) - throw new ArgumentException("must be at least 16", "paddingLength"); - - this.mType = type; - this.mPayload = payload; - this.mPaddingLength = paddingLength; - } - - /** - * Encode this {@link HeartbeatMessage} to a {@link Stream}. - * - * @param output - * the {@link Stream} to encode to. - * @throws IOException - */ - public virtual void Encode(TlsContext context, Stream output) - { - TlsUtilities.WriteUint8(mType, output); - - TlsUtilities.CheckUint16(mPayload.Length); - TlsUtilities.WriteUint16(mPayload.Length, output); - output.Write(mPayload, 0, mPayload.Length); - - byte[] padding = new byte[mPaddingLength]; - context.NonceRandomGenerator.NextBytes(padding); - output.Write(padding, 0, padding.Length); - } - - /** - * Parse a {@link HeartbeatMessage} from a {@link Stream}. - * - * @param input - * the {@link Stream} to parse from. - * @return a {@link HeartbeatMessage} object. - * @throws IOException - */ - public static HeartbeatMessage Parse(Stream input) - { - byte type = TlsUtilities.ReadUint8(input); - if (!HeartbeatMessageType.IsValid(type)) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - - int payload_length = TlsUtilities.ReadUint16(input); - - PayloadBuffer buf = new PayloadBuffer(); - Streams.PipeAll(input, buf); - - byte[] payload = buf.ToTruncatedByteArray(payload_length); - if (payload == null) - { - /* - * RFC 6520 4. If the payload_length of a received HeartbeatMessage is too large, the - * received HeartbeatMessage MUST be discarded silently. - */ - return null; - } - - TlsUtilities.CheckUint16(buf.Length); - int padding_length = (int)buf.Length - payload.Length; - - /* - * RFC 6520 4. The padding of a received HeartbeatMessage message MUST be ignored - */ - return new HeartbeatMessage(type, payload, padding_length); - } - - internal class PayloadBuffer - : MemoryStream - { - internal byte[] ToTruncatedByteArray(int payloadLength) - { - /* - * RFC 6520 4. The padding_length MUST be at least 16. - */ - int minimumCount = payloadLength + 16; - if (Length < minimumCount) - return null; - -#if PORTABLE - byte[] buf = ToArray(); -#else - byte[] buf = GetBuffer(); -#endif - - return Arrays.CopyOf(buf, payloadLength); - } - } - } -} diff --git a/crypto/src/crypto/tls/HeartbeatMessageType.cs b/crypto/src/crypto/tls/HeartbeatMessageType.cs deleted file mode 100644 index 57a4b86be..000000000 --- a/crypto/src/crypto/tls/HeartbeatMessageType.cs +++ /dev/null @@ -1,18 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /* - * RFC 6520 3. - */ - public abstract class HeartbeatMessageType - { - public const byte heartbeat_request = 1; - public const byte heartbeat_response = 2; - - public static bool IsValid(byte heartbeatMessageType) - { - return heartbeatMessageType >= heartbeat_request && heartbeatMessageType <= heartbeat_response; - } - } -} diff --git a/crypto/src/crypto/tls/HeartbeatMode.cs b/crypto/src/crypto/tls/HeartbeatMode.cs deleted file mode 100644 index f1570a84d..000000000 --- a/crypto/src/crypto/tls/HeartbeatMode.cs +++ /dev/null @@ -1,18 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /* - * RFC 6520 - */ - public abstract class HeartbeatMode - { - public const byte peer_allowed_to_send = 1; - public const byte peer_not_allowed_to_send = 2; - - public static bool IsValid(byte heartbeatMode) - { - return heartbeatMode >= peer_allowed_to_send && heartbeatMode <= peer_not_allowed_to_send; - } - } -} diff --git a/crypto/src/crypto/tls/KeyExchangeAlgorithm.cs b/crypto/src/crypto/tls/KeyExchangeAlgorithm.cs deleted file mode 100644 index 9b1b3ba5e..000000000 --- a/crypto/src/crypto/tls/KeyExchangeAlgorithm.cs +++ /dev/null @@ -1,54 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary>RFC 2246</summary> - /// <remarks> - /// Note that the values here are implementation-specific and arbitrary. It is recommended not to - /// depend on the particular values (e.g. serialization). - /// </remarks> - public abstract class KeyExchangeAlgorithm - { - public const int NULL = 0; - public const int RSA = 1; - public const int RSA_EXPORT = 2; - public const int DHE_DSS = 3; - public const int DHE_DSS_EXPORT = 4; - public const int DHE_RSA = 5; - public const int DHE_RSA_EXPORT = 6; - public const int DH_DSS = 7; - public const int DH_DSS_EXPORT = 8; - public const int DH_RSA = 9; - public const int DH_RSA_EXPORT = 10; - public const int DH_anon = 11; - public const int DH_anon_EXPORT = 12; - - /* - * RFC 4279 - */ - public const int PSK = 13; - public const int DHE_PSK = 14; - public const int RSA_PSK = 15; - - /* - * RFC 4429 - */ - public const int ECDH_ECDSA = 16; - public const int ECDHE_ECDSA = 17; - public const int ECDH_RSA = 18; - public const int ECDHE_RSA = 19; - public const int ECDH_anon = 20; - - /* - * RFC 5054 - */ - public const int SRP = 21; - public const int SRP_DSS = 22; - public const int SRP_RSA = 23; - - /* - * RFC 5489 - */ - public const int ECDHE_PSK = 24; - } -} diff --git a/crypto/src/crypto/tls/MacAlgorithm.cs b/crypto/src/crypto/tls/MacAlgorithm.cs deleted file mode 100644 index e4aa88de6..000000000 --- a/crypto/src/crypto/tls/MacAlgorithm.cs +++ /dev/null @@ -1,25 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary>RFC 2246</summary> - /// <remarks> - /// Note that the values here are implementation-specific and arbitrary. It is recommended not to - /// depend on the particular values (e.g. serialization). - /// </remarks> - public abstract class MacAlgorithm - { - public const int cls_null = 0; - public const int md5 = 1; - public const int sha = 2; - - /* - * RFC 5246 - */ - public const int hmac_md5 = md5; - public const int hmac_sha1 = sha; - public const int hmac_sha256 = 3; - public const int hmac_sha384 = 4; - public const int hmac_sha512 = 5; - } -} diff --git a/crypto/src/crypto/tls/MaxFragmentLength.cs b/crypto/src/crypto/tls/MaxFragmentLength.cs deleted file mode 100644 index 5b10b35dd..000000000 --- a/crypto/src/crypto/tls/MaxFragmentLength.cs +++ /dev/null @@ -1,20 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class MaxFragmentLength - { - /* - * RFC 3546 3.2. - */ - public const byte pow2_9 = 1; - public const byte pow2_10 = 2; - public const byte pow2_11 = 3; - public const byte pow2_12 = 4; - - public static bool IsValid(byte maxFragmentLength) - { - return maxFragmentLength >= pow2_9 && maxFragmentLength <= pow2_12; - } - } -} diff --git a/crypto/src/crypto/tls/NameType.cs b/crypto/src/crypto/tls/NameType.cs deleted file mode 100644 index 782164215..000000000 --- a/crypto/src/crypto/tls/NameType.cs +++ /dev/null @@ -1,17 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class NameType - { - /* - * RFC 3546 3.1. - */ - public const byte host_name = 0; - - public static bool IsValid(byte nameType) - { - return nameType == host_name; - } - } -} diff --git a/crypto/src/crypto/tls/NamedCurve.cs b/crypto/src/crypto/tls/NamedCurve.cs deleted file mode 100644 index b8aa0ecde..000000000 --- a/crypto/src/crypto/tls/NamedCurve.cs +++ /dev/null @@ -1,77 +0,0 @@ -using System; - -using Org.BouncyCastle.Asn1.Sec; -using Org.BouncyCastle.Asn1.X9; -using Org.BouncyCastle.Crypto.Parameters; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary> - /// RFC 4492 5.1.1 - /// The named curves defined here are those specified in SEC 2 [13]. Note that many of - /// these curves are also recommended in ANSI X9.62 [7] and FIPS 186-2 [11]. Values 0xFE00 - /// through 0xFEFF are reserved for private use. Values 0xFF01 and 0xFF02 indicate that the - /// client supports arbitrary prime and characteristic-2 curves, respectively (the curve - /// parameters must be encoded explicitly in ECParameters). - /// </summary> - public abstract class NamedCurve - { - public const int sect163k1 = 1; - public const int sect163r1 = 2; - public const int sect163r2 = 3; - public const int sect193r1 = 4; - public const int sect193r2 = 5; - public const int sect233k1 = 6; - public const int sect233r1 = 7; - public const int sect239k1 = 8; - public const int sect283k1 = 9; - public const int sect283r1 = 10; - public const int sect409k1 = 11; - public const int sect409r1 = 12; - public const int sect571k1 = 13; - public const int sect571r1 = 14; - public const int secp160k1 = 15; - public const int secp160r1 = 16; - public const int secp160r2 = 17; - public const int secp192k1 = 18; - public const int secp192r1 = 19; - public const int secp224k1 = 20; - public const int secp224r1 = 21; - public const int secp256k1 = 22; - public const int secp256r1 = 23; - public const int secp384r1 = 24; - public const int secp521r1 = 25; - - /* - * RFC 7027 - */ - public const int brainpoolP256r1 = 26; - public const int brainpoolP384r1 = 27; - public const int brainpoolP512r1 = 28; - - /* - * reserved (0xFE00..0xFEFF) - */ - - public const int arbitrary_explicit_prime_curves = 0xFF01; - public const int arbitrary_explicit_char2_curves = 0xFF02; - - public static bool IsValid(int namedCurve) - { - return (namedCurve >= sect163k1 && namedCurve <= brainpoolP512r1) - || (namedCurve >= arbitrary_explicit_prime_curves && namedCurve <= arbitrary_explicit_char2_curves); - } - - public static bool RefersToASpecificNamedCurve(int namedCurve) - { - switch (namedCurve) - { - case arbitrary_explicit_prime_curves: - case arbitrary_explicit_char2_curves: - return false; - default: - return true; - } - } - } -} diff --git a/crypto/src/crypto/tls/NewSessionTicket.cs b/crypto/src/crypto/tls/NewSessionTicket.cs deleted file mode 100644 index a84026b8c..000000000 --- a/crypto/src/crypto/tls/NewSessionTicket.cs +++ /dev/null @@ -1,53 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class NewSessionTicket - { - protected readonly long mTicketLifetimeHint; - protected readonly byte[] mTicket; - - public NewSessionTicket(long ticketLifetimeHint, byte[] ticket) - { - this.mTicketLifetimeHint = ticketLifetimeHint; - this.mTicket = ticket; - } - - public virtual long TicketLifetimeHint - { - get { return mTicketLifetimeHint; } - } - - public virtual byte[] Ticket - { - get { return mTicket; } - } - - /** - * Encode this {@link NewSessionTicket} to a {@link Stream}. - * - * @param output the {@link Stream} to encode to. - * @throws IOException - */ - public virtual void Encode(Stream output) - { - TlsUtilities.WriteUint32(mTicketLifetimeHint, output); - TlsUtilities.WriteOpaque16(mTicket, output); - } - - /** - * Parse a {@link NewSessionTicket} from a {@link Stream}. - * - * @param input the {@link Stream} to parse from. - * @return a {@link NewSessionTicket} object. - * @throws IOException - */ - public static NewSessionTicket Parse(Stream input) - { - long ticketLifetimeHint = TlsUtilities.ReadUint32(input); - byte[] ticket = TlsUtilities.ReadOpaque16(input); - return new NewSessionTicket(ticketLifetimeHint, ticket); - } - } -} diff --git a/crypto/src/crypto/tls/OcspStatusRequest.cs b/crypto/src/crypto/tls/OcspStatusRequest.cs deleted file mode 100644 index d9203a3c4..000000000 --- a/crypto/src/crypto/tls/OcspStatusRequest.cs +++ /dev/null @@ -1,131 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Asn1; -using Org.BouncyCastle.Asn1.Ocsp; -using Org.BouncyCastle.Asn1.X509; -using Org.BouncyCastle.Utilities; -using Org.BouncyCastle.Utilities.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /** - * RFC 3546 3.6 - */ - public class OcspStatusRequest - { - protected readonly IList mResponderIDList; - protected readonly X509Extensions mRequestExtensions; - - /** - * @param responderIDList - * an {@link IList} of {@link ResponderID}, specifying the list of trusted OCSP - * responders. An empty list has the special meaning that the responders are - * implicitly known to the server - e.g., by prior arrangement. - * @param requestExtensions - * OCSP request extensions. A null value means that there are no extensions. - */ - public OcspStatusRequest(IList responderIDList, X509Extensions requestExtensions) - { - this.mResponderIDList = responderIDList; - this.mRequestExtensions = requestExtensions; - } - - /** - * @return an {@link IList} of {@link ResponderID} - */ - public virtual IList ResponderIDList - { - get { return mResponderIDList; } - } - - /** - * @return OCSP request extensions - */ - public virtual X509Extensions RequestExtensions - { - get { return mRequestExtensions; } - } - - /** - * Encode this {@link OcspStatusRequest} to a {@link Stream}. - * - * @param output - * the {@link Stream} to encode to. - * @throws IOException - */ - public virtual void Encode(Stream output) - { - if (mResponderIDList == null || mResponderIDList.Count < 1) - { - TlsUtilities.WriteUint16(0, output); - } - else - { - MemoryStream buf = new MemoryStream(); - for (int i = 0; i < mResponderIDList.Count; ++i) - { - ResponderID responderID = (ResponderID)mResponderIDList[i]; - byte[] derEncoding = responderID.GetEncoded(Asn1Encodable.Der); - TlsUtilities.WriteOpaque16(derEncoding, buf); - } - TlsUtilities.CheckUint16(buf.Length); - TlsUtilities.WriteUint16((int)buf.Length, output); - Streams.WriteBufTo(buf, output); - } - - if (mRequestExtensions == null) - { - TlsUtilities.WriteUint16(0, output); - } - else - { - byte[] derEncoding = mRequestExtensions.GetEncoded(Asn1Encodable.Der); - TlsUtilities.CheckUint16(derEncoding.Length); - TlsUtilities.WriteUint16(derEncoding.Length, output); - output.Write(derEncoding, 0, derEncoding.Length); - } - } - - /** - * Parse a {@link OcspStatusRequest} from a {@link Stream}. - * - * @param input - * the {@link Stream} to parse from. - * @return an {@link OcspStatusRequest} object. - * @throws IOException - */ - public static OcspStatusRequest Parse(Stream input) - { - IList responderIDList = Platform.CreateArrayList(); - { - int length = TlsUtilities.ReadUint16(input); - if (length > 0) - { - byte[] data = TlsUtilities.ReadFully(length, input); - MemoryStream buf = new MemoryStream(data, false); - do - { - byte[] derEncoding = TlsUtilities.ReadOpaque16(buf); - ResponderID responderID = ResponderID.GetInstance(TlsUtilities.ReadDerObject(derEncoding)); - responderIDList.Add(responderID); - } - while (buf.Position < buf.Length); - } - } - - X509Extensions requestExtensions = null; - { - int length = TlsUtilities.ReadUint16(input); - if (length > 0) - { - byte[] derEncoding = TlsUtilities.ReadFully(length, input); - requestExtensions = X509Extensions.GetInstance(TlsUtilities.ReadDerObject(derEncoding)); - } - } - - return new OcspStatusRequest(responderIDList, requestExtensions); - } - } -} diff --git a/crypto/src/crypto/tls/PrfAlgorithm.cs b/crypto/src/crypto/tls/PrfAlgorithm.cs deleted file mode 100644 index 871241bd2..000000000 --- a/crypto/src/crypto/tls/PrfAlgorithm.cs +++ /dev/null @@ -1,24 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary>RFC 5246</summary> - /// <remarks> - /// Note that the values here are implementation-specific and arbitrary. It is recommended not to - /// depend on the particular values (e.g. serialization). - /// </remarks> - public abstract class PrfAlgorithm - { - /* - * Placeholder to refer to the legacy TLS algorithm - */ - public const int tls_prf_legacy = 0; - - public const int tls_prf_sha256 = 1; - - /* - * Implied by RFC 5288 - */ - public const int tls_prf_sha384 = 2; - } -} diff --git a/crypto/src/crypto/tls/ProtocolVersion.cs b/crypto/src/crypto/tls/ProtocolVersion.cs deleted file mode 100644 index b0d55183a..000000000 --- a/crypto/src/crypto/tls/ProtocolVersion.cs +++ /dev/null @@ -1,159 +0,0 @@ -using System; -using System.IO; - -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public sealed class ProtocolVersion - { - public static readonly ProtocolVersion SSLv3 = new ProtocolVersion(0x0300, "SSL 3.0"); - public static readonly ProtocolVersion TLSv10 = new ProtocolVersion(0x0301, "TLS 1.0"); - public static readonly ProtocolVersion TLSv11 = new ProtocolVersion(0x0302, "TLS 1.1"); - public static readonly ProtocolVersion TLSv12 = new ProtocolVersion(0x0303, "TLS 1.2"); - public static readonly ProtocolVersion DTLSv10 = new ProtocolVersion(0xFEFF, "DTLS 1.0"); - public static readonly ProtocolVersion DTLSv12 = new ProtocolVersion(0xFEFD, "DTLS 1.2"); - - private readonly int version; - private readonly String name; - - private ProtocolVersion(int v, String name) - { - this.version = v & 0xffff; - this.name = name; - } - - public int FullVersion - { - get { return version; } - } - - public int MajorVersion - { - get { return version >> 8; } - } - - public int MinorVersion - { - get { return version & 0xff; } - } - - public bool IsDtls - { - get { return MajorVersion == 0xFE; } - } - - public bool IsSsl - { - get { return this == SSLv3; } - } - - public bool IsTls - { - get { return MajorVersion == 0x03; } - } - - public ProtocolVersion GetEquivalentTLSVersion() - { - if (!IsDtls) - { - return this; - } - if (this == DTLSv10) - { - return TLSv11; - } - return TLSv12; - } - - public bool IsEqualOrEarlierVersionOf(ProtocolVersion version) - { - if (MajorVersion != version.MajorVersion) - { - return false; - } - int diffMinorVersion = version.MinorVersion - MinorVersion; - return IsDtls ? diffMinorVersion <= 0 : diffMinorVersion >= 0; - } - - public bool IsLaterVersionOf(ProtocolVersion version) - { - if (MajorVersion != version.MajorVersion) - { - return false; - } - int diffMinorVersion = version.MinorVersion - MinorVersion; - return IsDtls ? diffMinorVersion > 0 : diffMinorVersion < 0; - } - - public override bool Equals(object other) - { - return this == other || (other is ProtocolVersion && Equals((ProtocolVersion)other)); - } - - public bool Equals(ProtocolVersion other) - { - return other != null && this.version == other.version; - } - - public override int GetHashCode() - { - return version; - } - - /// <exception cref="IOException"/> - public static ProtocolVersion Get(int major, int minor) - { - switch (major) - { - case 0x03: - { - switch (minor) - { - case 0x00: - return SSLv3; - case 0x01: - return TLSv10; - case 0x02: - return TLSv11; - case 0x03: - return TLSv12; - } - return GetUnknownVersion(major, minor, "TLS"); - } - case 0xFE: - { - switch (minor) - { - case 0xFF: - return DTLSv10; - case 0xFE: - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - case 0xFD: - return DTLSv12; - } - return GetUnknownVersion(major, minor, "DTLS"); - } - default: - { - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - } - } - - public override string ToString() - { - return name; - } - - private static ProtocolVersion GetUnknownVersion(int major, int minor, string prefix) - { - TlsUtilities.CheckUint8(major); - TlsUtilities.CheckUint8(minor); - - int v = (major << 8) | minor; - String hex = Platform.ToUpperInvariant(Convert.ToString(0x10000 | v, 16).Substring(1)); - return new ProtocolVersion(v, prefix + " 0x" + hex); - } - } -} diff --git a/crypto/src/crypto/tls/PskTlsClient.cs b/crypto/src/crypto/tls/PskTlsClient.cs deleted file mode 100644 index d5fa43543..000000000 --- a/crypto/src/crypto/tls/PskTlsClient.cs +++ /dev/null @@ -1,75 +0,0 @@ -using System; -using System.Collections; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class PskTlsClient - : AbstractTlsClient - { - protected TlsDHVerifier mDHVerifier; - protected TlsPskIdentity mPskIdentity; - - public PskTlsClient(TlsPskIdentity pskIdentity) - : this(new DefaultTlsCipherFactory(), pskIdentity) - { - } - - public PskTlsClient(TlsCipherFactory cipherFactory, TlsPskIdentity pskIdentity) - : this(cipherFactory, new DefaultTlsDHVerifier(), pskIdentity) - { - } - - public PskTlsClient(TlsCipherFactory cipherFactory, TlsDHVerifier dhVerifier, TlsPskIdentity pskIdentity) - : base(cipherFactory) - { - this.mDHVerifier = dhVerifier; - this.mPskIdentity = pskIdentity; - } - - public override int[] GetCipherSuites() - { - return new int[] - { - CipherSuite.TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA256, - CipherSuite.TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA, - }; - } - - public override TlsKeyExchange GetKeyExchange() - { - int keyExchangeAlgorithm = TlsUtilities.GetKeyExchangeAlgorithm(mSelectedCipherSuite); - - switch (keyExchangeAlgorithm) - { - case KeyExchangeAlgorithm.DHE_PSK: - case KeyExchangeAlgorithm.ECDHE_PSK: - case KeyExchangeAlgorithm.PSK: - case KeyExchangeAlgorithm.RSA_PSK: - return CreatePskKeyExchange(keyExchangeAlgorithm); - - default: - /* - * Note: internal error here; the TlsProtocol implementation verifies that the - * server-selected cipher suite was in the list of client-offered cipher suites, so if - * we now can't produce an implementation, we shouldn't have offered it! - */ - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } - - public override TlsAuthentication GetAuthentication() - { - /* - * Note: This method is not called unless a server certificate is sent, which may be the - * case e.g. for RSA_PSK key exchange. - */ - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - protected virtual TlsKeyExchange CreatePskKeyExchange(int keyExchange) - { - return new TlsPskKeyExchange(keyExchange, mSupportedSignatureAlgorithms, mPskIdentity, null, mDHVerifier, null, - mNamedCurves, mClientECPointFormats, mServerECPointFormats); - } - } -} diff --git a/crypto/src/crypto/tls/PskTlsServer.cs b/crypto/src/crypto/tls/PskTlsServer.cs deleted file mode 100644 index a3778420d..000000000 --- a/crypto/src/crypto/tls/PskTlsServer.cs +++ /dev/null @@ -1,93 +0,0 @@ -using System; - -using Org.BouncyCastle.Crypto.Agreement; -using Org.BouncyCastle.Crypto.Parameters; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class PskTlsServer - : AbstractTlsServer - { - protected TlsPskIdentityManager mPskIdentityManager; - - public PskTlsServer(TlsPskIdentityManager pskIdentityManager) - : this(new DefaultTlsCipherFactory(), pskIdentityManager) - { - } - - public PskTlsServer(TlsCipherFactory cipherFactory, TlsPskIdentityManager pskIdentityManager) - : base(cipherFactory) - { - this.mPskIdentityManager = pskIdentityManager; - } - - protected virtual TlsEncryptionCredentials GetRsaEncryptionCredentials() - { - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - protected virtual DHParameters GetDHParameters() - { - return DHStandardGroups.rfc7919_ffdhe2048; - } - - protected override int[] GetCipherSuites() - { - return new int[] - { - CipherSuite.TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA256, - CipherSuite.TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA, - CipherSuite.TLS_DHE_PSK_WITH_AES_128_CBC_SHA256, - CipherSuite.TLS_DHE_PSK_WITH_AES_128_CBC_SHA - }; - } - - public override TlsCredentials GetCredentials() - { - int keyExchangeAlgorithm = TlsUtilities.GetKeyExchangeAlgorithm(mSelectedCipherSuite); - - switch (keyExchangeAlgorithm) - { - case KeyExchangeAlgorithm.DHE_PSK: - case KeyExchangeAlgorithm.ECDHE_PSK: - case KeyExchangeAlgorithm.PSK: - return null; - - case KeyExchangeAlgorithm.RSA_PSK: - return GetRsaEncryptionCredentials(); - - default: - /* Note: internal error here; selected a key exchange we don't implement! */ - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } - - public override TlsKeyExchange GetKeyExchange() - { - int keyExchangeAlgorithm = TlsUtilities.GetKeyExchangeAlgorithm(mSelectedCipherSuite); - - switch (keyExchangeAlgorithm) - { - case KeyExchangeAlgorithm.DHE_PSK: - case KeyExchangeAlgorithm.ECDHE_PSK: - case KeyExchangeAlgorithm.PSK: - case KeyExchangeAlgorithm.RSA_PSK: - return CreatePskKeyExchange(keyExchangeAlgorithm); - - default: - /* - * Note: internal error here; the TlsProtocol implementation verifies that the - * server-selected cipher suite was in the list of client-offered cipher suites, so if - * we now can't produce an implementation, we shouldn't have offered it! - */ - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } - - protected virtual TlsKeyExchange CreatePskKeyExchange(int keyExchange) - { - return new TlsPskKeyExchange(keyExchange, mSupportedSignatureAlgorithms, null, mPskIdentityManager, - null, GetDHParameters(), mNamedCurves, mClientECPointFormats, mServerECPointFormats); - } - } -} diff --git a/crypto/src/crypto/tls/RecordStream.cs b/crypto/src/crypto/tls/RecordStream.cs deleted file mode 100644 index 5d556ad06..000000000 --- a/crypto/src/crypto/tls/RecordStream.cs +++ /dev/null @@ -1,412 +0,0 @@ -using System; -using System.IO; - -using Org.BouncyCastle.Utilities; -using Org.BouncyCastle.Utilities.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary>An implementation of the TLS 1.0/1.1/1.2 record layer, allowing downgrade to SSLv3.</summary> - internal class RecordStream - { - private const int DEFAULT_PLAINTEXT_LIMIT = (1 << 14); - - internal const int TLS_HEADER_SIZE = 5; - internal const int TLS_HEADER_TYPE_OFFSET = 0; - internal const int TLS_HEADER_VERSION_OFFSET = 1; - internal const int TLS_HEADER_LENGTH_OFFSET = 3; - - private TlsProtocol mHandler; - private Stream mInput; - private Stream mOutput; - private TlsCompression mPendingCompression = null, mReadCompression = null, mWriteCompression = null; - private TlsCipher mPendingCipher = null, mReadCipher = null, mWriteCipher = null; - private SequenceNumber mReadSeqNo = new SequenceNumber(), mWriteSeqNo = new SequenceNumber(); - private MemoryStream mBuffer = new MemoryStream(); - - private TlsHandshakeHash mHandshakeHash = null; - private readonly BaseOutputStream mHandshakeHashUpdater; - - private ProtocolVersion mReadVersion = null, mWriteVersion = null; - private bool mRestrictReadVersion = true; - - private int mPlaintextLimit, mCompressedLimit, mCiphertextLimit; - - internal RecordStream(TlsProtocol handler, Stream input, Stream output) - { - this.mHandler = handler; - this.mInput = input; - this.mOutput = output; - this.mReadCompression = new TlsNullCompression(); - this.mWriteCompression = this.mReadCompression; - this.mHandshakeHashUpdater = new HandshakeHashUpdateStream(this); - } - - internal virtual void Init(TlsContext context) - { - this.mReadCipher = new TlsNullCipher(context); - this.mWriteCipher = this.mReadCipher; - this.mHandshakeHash = new DeferredHash(); - this.mHandshakeHash.Init(context); - - SetPlaintextLimit(DEFAULT_PLAINTEXT_LIMIT); - } - - internal virtual int GetPlaintextLimit() - { - return mPlaintextLimit; - } - - internal virtual void SetPlaintextLimit(int plaintextLimit) - { - this.mPlaintextLimit = plaintextLimit; - this.mCompressedLimit = this.mPlaintextLimit + 1024; - this.mCiphertextLimit = this.mCompressedLimit + 1024; - } - - internal virtual ProtocolVersion ReadVersion - { - get { return mReadVersion; } - set { this.mReadVersion = value; } - } - - internal virtual void SetWriteVersion(ProtocolVersion writeVersion) - { - this.mWriteVersion = writeVersion; - } - - /** - * RFC 5246 E.1. "Earlier versions of the TLS specification were not fully clear on what the - * record layer version number (TLSPlaintext.version) should contain when sending ClientHello - * (i.e., before it is known which version of the protocol will be employed). Thus, TLS servers - * compliant with this specification MUST accept any value {03,XX} as the record layer version - * number for ClientHello." - */ - internal virtual void SetRestrictReadVersion(bool enabled) - { - this.mRestrictReadVersion = enabled; - } - - internal virtual void SetPendingConnectionState(TlsCompression tlsCompression, TlsCipher tlsCipher) - { - this.mPendingCompression = tlsCompression; - this.mPendingCipher = tlsCipher; - } - - internal virtual void SentWriteCipherSpec() - { - if (mPendingCompression == null || mPendingCipher == null) - throw new TlsFatalAlert(AlertDescription.handshake_failure); - - this.mWriteCompression = this.mPendingCompression; - this.mWriteCipher = this.mPendingCipher; - this.mWriteSeqNo = new SequenceNumber(); - } - - internal virtual void ReceivedReadCipherSpec() - { - if (mPendingCompression == null || mPendingCipher == null) - throw new TlsFatalAlert(AlertDescription.handshake_failure); - - this.mReadCompression = this.mPendingCompression; - this.mReadCipher = this.mPendingCipher; - this.mReadSeqNo = new SequenceNumber(); - } - - internal virtual void FinaliseHandshake() - { - if (mReadCompression != mPendingCompression || mWriteCompression != mPendingCompression - || mReadCipher != mPendingCipher || mWriteCipher != mPendingCipher) - { - throw new TlsFatalAlert(AlertDescription.handshake_failure); - } - this.mPendingCompression = null; - this.mPendingCipher = null; - } - - internal virtual void CheckRecordHeader(byte[] recordHeader) - { - byte type = TlsUtilities.ReadUint8(recordHeader, TLS_HEADER_TYPE_OFFSET); - - /* - * RFC 5246 6. If a TLS implementation receives an unexpected record type, it MUST send an - * unexpected_message alert. - */ - CheckType(type, AlertDescription.unexpected_message); - - if (!mRestrictReadVersion) - { - int version = TlsUtilities.ReadVersionRaw(recordHeader, TLS_HEADER_VERSION_OFFSET); - if ((version & 0xffffff00) != 0x0300) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - else - { - ProtocolVersion version = TlsUtilities.ReadVersion(recordHeader, TLS_HEADER_VERSION_OFFSET); - if (mReadVersion == null) - { - // Will be set later in 'readRecord' - } - else if (!version.Equals(mReadVersion)) - { - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - } - - int length = TlsUtilities.ReadUint16(recordHeader, TLS_HEADER_LENGTH_OFFSET); - - CheckLength(length, mCiphertextLimit, AlertDescription.record_overflow); - } - - internal virtual bool ReadRecord() - { - byte[] recordHeader = TlsUtilities.ReadAllOrNothing(TLS_HEADER_SIZE, mInput); - if (recordHeader == null) - return false; - - byte type = TlsUtilities.ReadUint8(recordHeader, TLS_HEADER_TYPE_OFFSET); - - /* - * RFC 5246 6. If a TLS implementation receives an unexpected record type, it MUST send an - * unexpected_message alert. - */ - CheckType(type, AlertDescription.unexpected_message); - - if (!mRestrictReadVersion) - { - int version = TlsUtilities.ReadVersionRaw(recordHeader, TLS_HEADER_VERSION_OFFSET); - if ((version & 0xffffff00) != 0x0300) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - else - { - ProtocolVersion version = TlsUtilities.ReadVersion(recordHeader, TLS_HEADER_VERSION_OFFSET); - if (mReadVersion == null) - { - mReadVersion = version; - } - else if (!version.Equals(mReadVersion)) - { - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - } - - int length = TlsUtilities.ReadUint16(recordHeader, TLS_HEADER_LENGTH_OFFSET); - - CheckLength(length, mCiphertextLimit, AlertDescription.record_overflow); - - byte[] plaintext = DecodeAndVerify(type, mInput, length); - mHandler.ProcessRecord(type, plaintext, 0, plaintext.Length); - return true; - } - - internal virtual byte[] DecodeAndVerify(byte type, Stream input, int len) - { - byte[] buf = TlsUtilities.ReadFully(len, input); - - long seqNo = mReadSeqNo.NextValue(AlertDescription.unexpected_message); - byte[] decoded = mReadCipher.DecodeCiphertext(seqNo, type, buf, 0, buf.Length); - - CheckLength(decoded.Length, mCompressedLimit, AlertDescription.record_overflow); - - /* - * TODO 5246 6.2.2. Implementation note: Decompression functions are responsible for - * ensuring that messages cannot cause internal buffer overflows. - */ - Stream cOut = mReadCompression.Decompress(mBuffer); - if (cOut != mBuffer) - { - cOut.Write(decoded, 0, decoded.Length); - cOut.Flush(); - decoded = GetBufferContents(); - } - - /* - * RFC 5246 6.2.2. If the decompression function encounters a TLSCompressed.fragment that - * would decompress to a length in excess of 2^14 bytes, it should report a fatal - * decompression failure error. - */ - CheckLength(decoded.Length, mPlaintextLimit, AlertDescription.decompression_failure); - - /* - * RFC 5246 6.2.1 Implementations MUST NOT send zero-length fragments of Handshake, Alert, - * or ChangeCipherSpec content types. - */ - if (decoded.Length < 1 && type != ContentType.application_data) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - - return decoded; - } - - internal virtual void WriteRecord(byte type, byte[] plaintext, int plaintextOffset, int plaintextLength) - { - // Never send anything until a valid ClientHello has been received - if (mWriteVersion == null) - return; - - /* - * RFC 5246 6. Implementations MUST NOT send record types not defined in this document - * unless negotiated by some extension. - */ - CheckType(type, AlertDescription.internal_error); - - /* - * RFC 5246 6.2.1 The length should not exceed 2^14. - */ - CheckLength(plaintextLength, mPlaintextLimit, AlertDescription.internal_error); - - /* - * RFC 5246 6.2.1 Implementations MUST NOT send zero-length fragments of Handshake, Alert, - * or ChangeCipherSpec content types. - */ - if (plaintextLength < 1 && type != ContentType.application_data) - throw new TlsFatalAlert(AlertDescription.internal_error); - - Stream cOut = mWriteCompression.Compress(mBuffer); - - long seqNo = mWriteSeqNo.NextValue(AlertDescription.internal_error); - - byte[] ciphertext; - if (cOut == mBuffer) - { - ciphertext = mWriteCipher.EncodePlaintext(seqNo, type, plaintext, plaintextOffset, plaintextLength); - } - else - { - cOut.Write(plaintext, plaintextOffset, plaintextLength); - cOut.Flush(); - byte[] compressed = GetBufferContents(); - - /* - * RFC 5246 6.2.2. Compression must be lossless and may not increase the content length - * by more than 1024 bytes. - */ - CheckLength(compressed.Length, plaintextLength + 1024, AlertDescription.internal_error); - - ciphertext = mWriteCipher.EncodePlaintext(seqNo, type, compressed, 0, compressed.Length); - } - - /* - * RFC 5246 6.2.3. The length may not exceed 2^14 + 2048. - */ - CheckLength(ciphertext.Length, mCiphertextLimit, AlertDescription.internal_error); - - byte[] record = new byte[ciphertext.Length + TLS_HEADER_SIZE]; - TlsUtilities.WriteUint8(type, record, TLS_HEADER_TYPE_OFFSET); - TlsUtilities.WriteVersion(mWriteVersion, record, TLS_HEADER_VERSION_OFFSET); - TlsUtilities.WriteUint16(ciphertext.Length, record, TLS_HEADER_LENGTH_OFFSET); - Array.Copy(ciphertext, 0, record, TLS_HEADER_SIZE, ciphertext.Length); - mOutput.Write(record, 0, record.Length); - mOutput.Flush(); - } - - internal virtual void NotifyHelloComplete() - { - this.mHandshakeHash = mHandshakeHash.NotifyPrfDetermined(); - } - - internal virtual TlsHandshakeHash HandshakeHash - { - get { return mHandshakeHash; } - } - - internal virtual Stream HandshakeHashUpdater - { - get { return mHandshakeHashUpdater; } - } - - internal virtual TlsHandshakeHash PrepareToFinish() - { - TlsHandshakeHash result = mHandshakeHash; - this.mHandshakeHash = mHandshakeHash.StopTracking(); - return result; - } - - internal virtual void SafeClose() - { - try - { - Platform.Dispose(mInput); - } - catch (IOException) - { - } - - try - { - Platform.Dispose(mOutput); - } - catch (IOException) - { - } - } - - internal virtual void Flush() - { - mOutput.Flush(); - } - - private byte[] GetBufferContents() - { - byte[] contents = mBuffer.ToArray(); - mBuffer.SetLength(0); - return contents; - } - - private static void CheckType(byte type, byte alertDescription) - { - switch (type) - { - case ContentType.application_data: - case ContentType.alert: - case ContentType.change_cipher_spec: - case ContentType.handshake: - //case ContentType.heartbeat: - break; - default: - throw new TlsFatalAlert(alertDescription); - } - } - - private static void CheckLength(int length, int limit, byte alertDescription) - { - if (length > limit) - throw new TlsFatalAlert(alertDescription); - } - - private class HandshakeHashUpdateStream - : BaseOutputStream - { - private readonly RecordStream mOuter; - public HandshakeHashUpdateStream(RecordStream mOuter) - { - this.mOuter = mOuter; - } - - public override void Write(byte[] buf, int off, int len) - { - mOuter.mHandshakeHash.BlockUpdate(buf, off, len); - } - } - - private class SequenceNumber - { - private long value = 0L; - private bool exhausted = false; - - internal long NextValue(byte alertDescription) - { - if (exhausted) - { - throw new TlsFatalAlert(alertDescription); - } - long result = value; - if (++value == 0) - { - exhausted = true; - } - return result; - } - } - } -} diff --git a/crypto/src/crypto/tls/SecurityParameters.cs b/crypto/src/crypto/tls/SecurityParameters.cs deleted file mode 100644 index f3ec7011e..000000000 --- a/crypto/src/crypto/tls/SecurityParameters.cs +++ /dev/null @@ -1,108 +0,0 @@ -using System; - -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class SecurityParameters - { - internal int entity = -1; - internal int cipherSuite = -1; - internal byte compressionAlgorithm = CompressionMethod.cls_null; - internal int prfAlgorithm = -1; - internal int verifyDataLength = -1; - internal byte[] masterSecret = null; - internal byte[] clientRandom = null; - internal byte[] serverRandom = null; - internal byte[] sessionHash = null; - internal byte[] pskIdentity = null; - internal byte[] srpIdentity = null; - - // TODO Keep these internal, since it's maybe not the ideal place for them - internal short maxFragmentLength = -1; - internal bool truncatedHMac = false; - internal bool encryptThenMac = false; - internal bool extendedMasterSecret = false; - - internal virtual void Clear() - { - if (this.masterSecret != null) - { - Arrays.Fill(this.masterSecret, (byte)0); - this.masterSecret = null; - } - } - - /** - * @return {@link ConnectionEnd} - */ - public virtual int Entity - { - get { return entity; } - } - - /** - * @return {@link CipherSuite} - */ - public virtual int CipherSuite - { - get { return cipherSuite; } - } - - /** - * @return {@link CompressionMethod} - */ - public virtual byte CompressionAlgorithm - { - get { return compressionAlgorithm; } - } - - /** - * @return {@link PRFAlgorithm} - */ - public virtual int PrfAlgorithm - { - get { return prfAlgorithm; } - } - - public virtual int VerifyDataLength - { - get { return verifyDataLength; } - } - - public virtual byte[] MasterSecret - { - get { return masterSecret; } - } - - public virtual byte[] ClientRandom - { - get { return clientRandom; } - } - - public virtual byte[] ServerRandom - { - get { return serverRandom; } - } - - public virtual byte[] SessionHash - { - get { return sessionHash; } - } - - public virtual byte[] PskIdentity - { - get { return pskIdentity; } - } - - public virtual byte[] SrpIdentity - { - get { return srpIdentity; } - } - - public virtual bool IsExtendedMasterSecret - { - get { return extendedMasterSecret; } - } - } -} diff --git a/crypto/src/crypto/tls/ServerName.cs b/crypto/src/crypto/tls/ServerName.cs deleted file mode 100644 index 45d18b79b..000000000 --- a/crypto/src/crypto/tls/ServerName.cs +++ /dev/null @@ -1,105 +0,0 @@ -using System; -using System.IO; - -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class ServerName - { - protected readonly byte mNameType; - protected readonly object mName; - - public ServerName(byte nameType, object name) - { - if (!IsCorrectType(nameType, name)) - throw new ArgumentException("not an instance of the correct type", "name"); - - this.mNameType = nameType; - this.mName = name; - } - - public virtual byte NameType - { - get { return mNameType; } - } - - public virtual object Name - { - get { return mName; } - } - - public virtual string GetHostName() - { - if (!IsCorrectType(Tls.NameType.host_name, mName)) - throw new InvalidOperationException("'name' is not a HostName string"); - - return (string)mName; - } - - /** - * Encode this {@link ServerName} to a {@link Stream}. - * - * @param output - * the {@link Stream} to encode to. - * @throws IOException - */ - public virtual void Encode(Stream output) - { - TlsUtilities.WriteUint8(mNameType, output); - - switch (mNameType) - { - case Tls.NameType.host_name: - byte[] asciiEncoding = Strings.ToAsciiByteArray((string)mName); - if (asciiEncoding.Length < 1) - throw new TlsFatalAlert(AlertDescription.internal_error); - TlsUtilities.WriteOpaque16(asciiEncoding, output); - break; - default: - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } - - /** - * Parse a {@link ServerName} from a {@link Stream}. - * - * @param input - * the {@link Stream} to parse from. - * @return a {@link ServerName} object. - * @throws IOException - */ - public static ServerName Parse(Stream input) - { - byte name_type = TlsUtilities.ReadUint8(input); - object name; - - switch (name_type) - { - case Tls.NameType.host_name: - { - byte[] asciiEncoding = TlsUtilities.ReadOpaque16(input); - if (asciiEncoding.Length < 1) - throw new TlsFatalAlert(AlertDescription.decode_error); - name = Strings.FromAsciiByteArray(asciiEncoding); - break; - } - default: - throw new TlsFatalAlert(AlertDescription.decode_error); - } - - return new ServerName(name_type, name); - } - - protected static bool IsCorrectType(byte nameType, object name) - { - switch (nameType) - { - case Tls.NameType.host_name: - return name is string; - default: - throw new ArgumentException("unsupported NameType", "nameType"); - } - } - } -} diff --git a/crypto/src/crypto/tls/ServerNameList.cs b/crypto/src/crypto/tls/ServerNameList.cs deleted file mode 100644 index ed4e59359..000000000 --- a/crypto/src/crypto/tls/ServerNameList.cs +++ /dev/null @@ -1,105 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Utilities; -using Org.BouncyCastle.Utilities.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class ServerNameList - { - protected readonly IList mServerNameList; - - /** - * @param serverNameList an {@link IList} of {@link ServerName}. - */ - public ServerNameList(IList serverNameList) - { - if (serverNameList == null) - throw new ArgumentNullException("serverNameList"); - - this.mServerNameList = serverNameList; - } - - /** - * @return an {@link IList} of {@link ServerName}. - */ - public virtual IList ServerNames - { - get { return mServerNameList; } - } - - /** - * Encode this {@link ServerNameList} to a {@link Stream}. - * - * @param output - * the {@link Stream} to encode to. - * @throws IOException - */ - public virtual void Encode(Stream output) - { - MemoryStream buf = new MemoryStream(); - - byte[] nameTypesSeen = TlsUtilities.EmptyBytes; - foreach (ServerName entry in ServerNames) - { - nameTypesSeen = CheckNameType(nameTypesSeen, entry.NameType); - if (nameTypesSeen == null) - throw new TlsFatalAlert(AlertDescription.internal_error); - - entry.Encode(buf); - } - - TlsUtilities.CheckUint16(buf.Length); - TlsUtilities.WriteUint16((int)buf.Length, output); - Streams.WriteBufTo(buf, output); - } - - /** - * Parse a {@link ServerNameList} from a {@link Stream}. - * - * @param input - * the {@link Stream} to parse from. - * @return a {@link ServerNameList} object. - * @throws IOException - */ - public static ServerNameList Parse(Stream input) - { - int length = TlsUtilities.ReadUint16(input); - if (length < 1) - throw new TlsFatalAlert(AlertDescription.decode_error); - - byte[] data = TlsUtilities.ReadFully(length, input); - - MemoryStream buf = new MemoryStream(data, false); - - byte[] nameTypesSeen = TlsUtilities.EmptyBytes; - IList server_name_list = Platform.CreateArrayList(); - while (buf.Position < buf.Length) - { - ServerName entry = ServerName.Parse(buf); - - nameTypesSeen = CheckNameType(nameTypesSeen, entry.NameType); - if (nameTypesSeen == null) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - - server_name_list.Add(entry); - } - - return new ServerNameList(server_name_list); - } - - private static byte[] CheckNameType(byte[] nameTypesSeen, byte nameType) - { - /* - * RFC 6066 3. The ServerNameList MUST NOT contain more than one name of the same - * name_type. - */ - if (!NameType.IsValid(nameType) || Arrays.Contains(nameTypesSeen, nameType)) - return null; - - return Arrays.Append(nameTypesSeen, nameType); - } - } -} diff --git a/crypto/src/crypto/tls/ServerOnlyTlsAuthentication.cs b/crypto/src/crypto/tls/ServerOnlyTlsAuthentication.cs deleted file mode 100644 index 485889709..000000000 --- a/crypto/src/crypto/tls/ServerOnlyTlsAuthentication.cs +++ /dev/null @@ -1,15 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class ServerOnlyTlsAuthentication - : TlsAuthentication - { - public abstract void NotifyServerCertificate(Certificate serverCertificate); - - public TlsCredentials GetClientCredentials(CertificateRequest certificateRequest) - { - return null; - } - } -} diff --git a/crypto/src/crypto/tls/ServerSrpParams.cs b/crypto/src/crypto/tls/ServerSrpParams.cs deleted file mode 100644 index 556ac5310..000000000 --- a/crypto/src/crypto/tls/ServerSrpParams.cs +++ /dev/null @@ -1,75 +0,0 @@ -using System; -using System.IO; - -using Org.BouncyCastle.Math; -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class ServerSrpParams - { - protected BigInteger m_N, m_g, m_B; - protected byte[] m_s; - - public ServerSrpParams(BigInteger N, BigInteger g, byte[] s, BigInteger B) - { - this.m_N = N; - this.m_g = g; - this.m_s = Arrays.Clone(s); - this.m_B = B; - } - - public virtual BigInteger B - { - get { return m_B; } - } - - public virtual BigInteger G - { - get { return m_g; } - } - - public virtual BigInteger N - { - get { return m_N; } - } - - public virtual byte[] S - { - get { return m_s; } - } - - /** - * Encode this {@link ServerSRPParams} to an {@link OutputStream}. - * - * @param output - * the {@link OutputStream} to encode to. - * @throws IOException - */ - public virtual void Encode(Stream output) - { - TlsSrpUtilities.WriteSrpParameter(m_N, output); - TlsSrpUtilities.WriteSrpParameter(m_g, output); - TlsUtilities.WriteOpaque8(m_s, output); - TlsSrpUtilities.WriteSrpParameter(m_B, output); - } - - /** - * Parse a {@link ServerSRPParams} from an {@link InputStream}. - * - * @param input - * the {@link InputStream} to parse from. - * @return a {@link ServerSRPParams} object. - * @throws IOException - */ - public static ServerSrpParams Parse(Stream input) - { - BigInteger N = TlsSrpUtilities.ReadSrpParameter(input); - BigInteger g = TlsSrpUtilities.ReadSrpParameter(input); - byte[] s = TlsUtilities.ReadOpaque8(input); - BigInteger B = TlsSrpUtilities.ReadSrpParameter(input); - - return new ServerSrpParams(N, g, s, B); - } - } -} diff --git a/crypto/src/crypto/tls/SessionParameters.cs b/crypto/src/crypto/tls/SessionParameters.cs deleted file mode 100644 index e827172ea..000000000 --- a/crypto/src/crypto/tls/SessionParameters.cs +++ /dev/null @@ -1,180 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public sealed class SessionParameters - { - public sealed class Builder - { - private int mCipherSuite = -1; - private short mCompressionAlgorithm = -1; - private byte[] mMasterSecret = null; - private Certificate mPeerCertificate = null; - private byte[] mPskIdentity = null; - private byte[] mSrpIdentity = null; - private byte[] mEncodedServerExtensions = null; - private bool mExtendedMasterSecret = false; - - public Builder() - { - } - - public SessionParameters Build() - { - Validate(this.mCipherSuite >= 0, "cipherSuite"); - Validate(this.mCompressionAlgorithm >= 0, "compressionAlgorithm"); - Validate(this.mMasterSecret != null, "masterSecret"); - return new SessionParameters(mCipherSuite, (byte)mCompressionAlgorithm, mMasterSecret, mPeerCertificate, - mPskIdentity, mSrpIdentity, mEncodedServerExtensions, mExtendedMasterSecret); - } - - public Builder SetCipherSuite(int cipherSuite) - { - this.mCipherSuite = cipherSuite; - return this; - } - - public Builder SetCompressionAlgorithm(byte compressionAlgorithm) - { - this.mCompressionAlgorithm = compressionAlgorithm; - return this; - } - - public Builder SetExtendedMasterSecret(bool extendedMasterSecret) - { - this.mExtendedMasterSecret = extendedMasterSecret; - return this; - } - - public Builder SetMasterSecret(byte[] masterSecret) - { - this.mMasterSecret = masterSecret; - return this; - } - - public Builder SetPeerCertificate(Certificate peerCertificate) - { - this.mPeerCertificate = peerCertificate; - return this; - } - - public Builder SetPskIdentity(byte[] pskIdentity) - { - this.mPskIdentity = pskIdentity; - return this; - } - - public Builder SetSrpIdentity(byte[] srpIdentity) - { - this.mSrpIdentity = srpIdentity; - return this; - } - - public Builder SetServerExtensions(IDictionary serverExtensions) - { - if (serverExtensions == null) - { - mEncodedServerExtensions = null; - } - else - { - MemoryStream buf = new MemoryStream(); - TlsProtocol.WriteExtensions(buf, serverExtensions); - mEncodedServerExtensions = buf.ToArray(); - } - return this; - } - - private void Validate(bool condition, string parameter) - { - if (!condition) - throw new InvalidOperationException("Required session parameter '" + parameter + "' not configured"); - } - } - - private int mCipherSuite; - private byte mCompressionAlgorithm; - private byte[] mMasterSecret; - private Certificate mPeerCertificate; - private byte[] mPskIdentity; - private byte[] mSrpIdentity; - private byte[] mEncodedServerExtensions; - private bool mExtendedMasterSecret; - - private SessionParameters(int cipherSuite, byte compressionAlgorithm, byte[] masterSecret, - Certificate peerCertificate, byte[] pskIdentity, byte[] srpIdentity, byte[] encodedServerExtensions, - bool extendedMasterSecret) - { - this.mCipherSuite = cipherSuite; - this.mCompressionAlgorithm = compressionAlgorithm; - this.mMasterSecret = Arrays.Clone(masterSecret); - this.mPeerCertificate = peerCertificate; - this.mPskIdentity = Arrays.Clone(pskIdentity); - this.mSrpIdentity = Arrays.Clone(srpIdentity); - this.mEncodedServerExtensions = encodedServerExtensions; - this.mExtendedMasterSecret = extendedMasterSecret; - } - - public void Clear() - { - if (this.mMasterSecret != null) - { - Arrays.Fill(this.mMasterSecret, (byte)0); - } - } - - public SessionParameters Copy() - { - return new SessionParameters(mCipherSuite, mCompressionAlgorithm, mMasterSecret, mPeerCertificate, - mPskIdentity, mSrpIdentity, mEncodedServerExtensions, mExtendedMasterSecret); - } - - public int CipherSuite - { - get { return mCipherSuite; } - } - - public byte CompressionAlgorithm - { - get { return mCompressionAlgorithm; } - } - - public bool IsExtendedMasterSecret - { - get { return mExtendedMasterSecret; } - } - - public byte[] MasterSecret - { - get { return mMasterSecret; } - } - - public Certificate PeerCertificate - { - get { return mPeerCertificate; } - } - - public byte[] PskIdentity - { - get { return mPskIdentity; } - } - - public byte[] SrpIdentity - { - get { return mSrpIdentity; } - } - - public IDictionary ReadServerExtensions() - { - if (mEncodedServerExtensions == null) - return null; - - MemoryStream buf = new MemoryStream(mEncodedServerExtensions, false); - return TlsProtocol.ReadExtensions(buf); - } - } -} diff --git a/crypto/src/crypto/tls/SignatureAlgorithm.cs b/crypto/src/crypto/tls/SignatureAlgorithm.cs deleted file mode 100644 index 35b961762..000000000 --- a/crypto/src/crypto/tls/SignatureAlgorithm.cs +++ /dev/null @@ -1,15 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /** - * RFC 5246 7.4.1.4.1 (in RFC 2246, there were no specific values assigned) - */ - public abstract class SignatureAlgorithm - { - public const byte anonymous = 0; - public const byte rsa = 1; - public const byte dsa = 2; - public const byte ecdsa = 3; - } -} diff --git a/crypto/src/crypto/tls/SignatureAndHashAlgorithm.cs b/crypto/src/crypto/tls/SignatureAndHashAlgorithm.cs deleted file mode 100644 index f74205b62..000000000 --- a/crypto/src/crypto/tls/SignatureAndHashAlgorithm.cs +++ /dev/null @@ -1,94 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /** - * RFC 5246 7.4.1.4.1 - */ - public class SignatureAndHashAlgorithm - { - protected readonly byte mHash; - protected readonly byte mSignature; - - /** - * @param hash {@link HashAlgorithm} - * @param signature {@link SignatureAlgorithm} - */ - public SignatureAndHashAlgorithm(byte hash, byte signature) - { - if (!TlsUtilities.IsValidUint8(hash)) - { - throw new ArgumentException("should be a uint8", "hash"); - } - if (!TlsUtilities.IsValidUint8(signature)) - { - throw new ArgumentException("should be a uint8", "signature"); - } - if (signature == SignatureAlgorithm.anonymous) - { - throw new ArgumentException("MUST NOT be \"anonymous\"", "signature"); - } - - this.mHash = hash; - this.mSignature = signature; - } - - /** - * @return {@link HashAlgorithm} - */ - public virtual byte Hash - { - get { return mHash; } - } - - /** - * @return {@link SignatureAlgorithm} - */ - public virtual byte Signature - { - get { return mSignature; } - } - - public override bool Equals(object obj) - { - if (!(obj is SignatureAndHashAlgorithm)) - { - return false; - } - SignatureAndHashAlgorithm other = (SignatureAndHashAlgorithm)obj; - return other.Hash == Hash && other.Signature == Signature; - } - - public override int GetHashCode() - { - return ((int)Hash << 16) | (int)Signature; - } - - /** - * Encode this {@link SignatureAndHashAlgorithm} to a {@link Stream}. - * - * @param output the {@link Stream} to encode to. - * @throws IOException - */ - public virtual void Encode(Stream output) - { - TlsUtilities.WriteUint8(Hash, output); - TlsUtilities.WriteUint8(Signature, output); - } - - /** - * Parse a {@link SignatureAndHashAlgorithm} from a {@link Stream}. - * - * @param input the {@link Stream} to parse from. - * @return a {@link SignatureAndHashAlgorithm} object. - * @throws IOException - */ - public static SignatureAndHashAlgorithm Parse(Stream input) - { - byte hash = TlsUtilities.ReadUint8(input); - byte signature = TlsUtilities.ReadUint8(input); - return new SignatureAndHashAlgorithm(hash, signature); - } - } -} diff --git a/crypto/src/crypto/tls/SignerInputBuffer.cs b/crypto/src/crypto/tls/SignerInputBuffer.cs deleted file mode 100644 index 7bc69624c..000000000 --- a/crypto/src/crypto/tls/SignerInputBuffer.cs +++ /dev/null @@ -1,37 +0,0 @@ -using System; -using System.IO; - -using Org.BouncyCastle.Utilities.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - internal class SignerInputBuffer - : MemoryStream - { - internal void UpdateSigner(ISigner s) - { - Streams.WriteBufTo(this, new SigStream(s)); - } - - private class SigStream - : BaseOutputStream - { - private readonly ISigner s; - - internal SigStream(ISigner s) - { - this.s = s; - } - - public override void WriteByte(byte b) - { - s.Update(b); - } - - public override void Write(byte[] buf, int off, int len) - { - s.BlockUpdate(buf, off, len); - } - } - } -} diff --git a/crypto/src/crypto/tls/SimulatedTlsSrpIdentityManager.cs b/crypto/src/crypto/tls/SimulatedTlsSrpIdentityManager.cs deleted file mode 100644 index 3e9737cd7..000000000 --- a/crypto/src/crypto/tls/SimulatedTlsSrpIdentityManager.cs +++ /dev/null @@ -1,69 +0,0 @@ -using System; - -using Org.BouncyCastle.Crypto.Agreement.Srp; -using Org.BouncyCastle.Crypto.Macs; -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Math; -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /** - * An implementation of {@link TlsSRPIdentityManager} that simulates the existence of "unknown" identities - * to obscure the fact that there is no verifier for them. - */ - public class SimulatedTlsSrpIdentityManager - : TlsSrpIdentityManager - { - private static readonly byte[] PREFIX_PASSWORD = Strings.ToByteArray("password"); - private static readonly byte[] PREFIX_SALT = Strings.ToByteArray("salt"); - - /** - * Create a {@link SimulatedTlsSRPIdentityManager} that implements the algorithm from RFC 5054 2.5.1.3 - * - * @param group the {@link SRP6GroupParameters} defining the group that SRP is operating in - * @param seedKey the secret "seed key" referred to in RFC 5054 2.5.1.3 - * @return an instance of {@link SimulatedTlsSRPIdentityManager} - */ - public static SimulatedTlsSrpIdentityManager GetRfc5054Default(Srp6GroupParameters group, byte[] seedKey) - { - Srp6VerifierGenerator verifierGenerator = new Srp6VerifierGenerator(); - verifierGenerator.Init(group, TlsUtilities.CreateHash(HashAlgorithm.sha1)); - - HMac mac = new HMac(TlsUtilities.CreateHash(HashAlgorithm.sha1)); - mac.Init(new KeyParameter(seedKey)); - - return new SimulatedTlsSrpIdentityManager(group, verifierGenerator, mac); - } - - protected readonly Srp6GroupParameters mGroup; - protected readonly Srp6VerifierGenerator mVerifierGenerator; - protected readonly IMac mMac; - - public SimulatedTlsSrpIdentityManager(Srp6GroupParameters group, Srp6VerifierGenerator verifierGenerator, IMac mac) - { - this.mGroup = group; - this.mVerifierGenerator = verifierGenerator; - this.mMac = mac; - } - - public virtual TlsSrpLoginParameters GetLoginParameters(byte[] identity) - { - mMac.BlockUpdate(PREFIX_SALT, 0, PREFIX_SALT.Length); - mMac.BlockUpdate(identity, 0, identity.Length); - - byte[] salt = new byte[mMac.GetMacSize()]; - mMac.DoFinal(salt, 0); - - mMac.BlockUpdate(PREFIX_PASSWORD, 0, PREFIX_PASSWORD.Length); - mMac.BlockUpdate(identity, 0, identity.Length); - - byte[] password = new byte[mMac.GetMacSize()]; - mMac.DoFinal(password, 0); - - BigInteger verifier = mVerifierGenerator.GenerateVerifier(salt, identity, password); - - return new TlsSrpLoginParameters(mGroup, verifier, salt); - } - } -} diff --git a/crypto/src/crypto/tls/SrpTlsClient.cs b/crypto/src/crypto/tls/SrpTlsClient.cs deleted file mode 100644 index df1607751..000000000 --- a/crypto/src/crypto/tls/SrpTlsClient.cs +++ /dev/null @@ -1,104 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class SrpTlsClient - : AbstractTlsClient - { - protected TlsSrpGroupVerifier mGroupVerifier; - - protected byte[] mIdentity; - protected byte[] mPassword; - - public SrpTlsClient(byte[] identity, byte[] password) - : this(new DefaultTlsCipherFactory(), new DefaultTlsSrpGroupVerifier(), identity, password) - { - } - - public SrpTlsClient(TlsCipherFactory cipherFactory, byte[] identity, byte[] password) - : this(cipherFactory, new DefaultTlsSrpGroupVerifier(), identity, password) - { - } - - public SrpTlsClient(TlsCipherFactory cipherFactory, TlsSrpGroupVerifier groupVerifier, - byte[] identity, byte[] password) - : base(cipherFactory) - { - this.mGroupVerifier = groupVerifier; - this.mIdentity = Arrays.Clone(identity); - this.mPassword = Arrays.Clone(password); - } - - protected virtual bool RequireSrpServerExtension - { - // No explicit guidance in RFC 5054; by default an (empty) extension from server is optional - get { return false; } - } - - public override int[] GetCipherSuites() - { - return new int[] - { - CipherSuite.TLS_SRP_SHA_RSA_WITH_AES_128_CBC_SHA - }; - } - - public override IDictionary GetClientExtensions() - { - IDictionary clientExtensions = TlsExtensionsUtilities.EnsureExtensionsInitialised(base.GetClientExtensions()); - TlsSrpUtilities.AddSrpExtension(clientExtensions, this.mIdentity); - return clientExtensions; - } - - public override void ProcessServerExtensions(IDictionary serverExtensions) - { - if (!TlsUtilities.HasExpectedEmptyExtensionData(serverExtensions, ExtensionType.srp, - AlertDescription.illegal_parameter)) - { - if (RequireSrpServerExtension) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - - base.ProcessServerExtensions(serverExtensions); - } - - public override TlsKeyExchange GetKeyExchange() - { - int keyExchangeAlgorithm = TlsUtilities.GetKeyExchangeAlgorithm(mSelectedCipherSuite); - - switch (keyExchangeAlgorithm) - { - case KeyExchangeAlgorithm.SRP: - case KeyExchangeAlgorithm.SRP_DSS: - case KeyExchangeAlgorithm.SRP_RSA: - return CreateSrpKeyExchange(keyExchangeAlgorithm); - - default: - /* - * Note: internal error here; the TlsProtocol implementation verifies that the - * server-selected cipher suite was in the list of client-offered cipher suites, so if - * we now can't produce an implementation, we shouldn't have offered it! - */ - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } - - public override TlsAuthentication GetAuthentication() - { - /* - * Note: This method is not called unless a server certificate is sent, which may be the - * case e.g. for SRP_DSS or SRP_RSA key exchange. - */ - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - protected virtual TlsKeyExchange CreateSrpKeyExchange(int keyExchange) - { - return new TlsSrpKeyExchange(keyExchange, mSupportedSignatureAlgorithms, mGroupVerifier, mIdentity, mPassword); - } - } -} diff --git a/crypto/src/crypto/tls/SrpTlsServer.cs b/crypto/src/crypto/tls/SrpTlsServer.cs deleted file mode 100644 index f97878380..000000000 --- a/crypto/src/crypto/tls/SrpTlsServer.cs +++ /dev/null @@ -1,121 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class SrpTlsServer - : AbstractTlsServer - { - protected TlsSrpIdentityManager mSrpIdentityManager; - - protected byte[] mSrpIdentity = null; - protected TlsSrpLoginParameters mLoginParameters = null; - - public SrpTlsServer(TlsSrpIdentityManager srpIdentityManager) - : this(new DefaultTlsCipherFactory(), srpIdentityManager) - { - } - - public SrpTlsServer(TlsCipherFactory cipherFactory, TlsSrpIdentityManager srpIdentityManager) - : base(cipherFactory) - { - this.mSrpIdentityManager = srpIdentityManager; - } - - protected virtual TlsSignerCredentials GetDsaSignerCredentials() - { - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - protected virtual TlsSignerCredentials GetRsaSignerCredentials() - { - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - protected override int[] GetCipherSuites() - { - return new int[] - { - CipherSuite.TLS_SRP_SHA_DSS_WITH_AES_256_CBC_SHA, - CipherSuite.TLS_SRP_SHA_DSS_WITH_AES_128_CBC_SHA, - CipherSuite.TLS_SRP_SHA_RSA_WITH_AES_256_CBC_SHA, - CipherSuite.TLS_SRP_SHA_RSA_WITH_AES_128_CBC_SHA, - CipherSuite.TLS_SRP_SHA_WITH_AES_256_CBC_SHA, - CipherSuite.TLS_SRP_SHA_WITH_AES_128_CBC_SHA - }; - } - - public override void ProcessClientExtensions(IDictionary clientExtensions) - { - base.ProcessClientExtensions(clientExtensions); - - this.mSrpIdentity = TlsSrpUtilities.GetSrpExtension(clientExtensions); - } - - public override int GetSelectedCipherSuite() - { - int cipherSuite = base.GetSelectedCipherSuite(); - - if (TlsSrpUtilities.IsSrpCipherSuite(cipherSuite)) - { - if (mSrpIdentity != null) - { - this.mLoginParameters = mSrpIdentityManager.GetLoginParameters(mSrpIdentity); - } - - if (mLoginParameters == null) - throw new TlsFatalAlert(AlertDescription.unknown_psk_identity); - } - - return cipherSuite; - } - - public override TlsCredentials GetCredentials() - { - int keyExchangeAlgorithm = TlsUtilities.GetKeyExchangeAlgorithm(mSelectedCipherSuite); - - switch (keyExchangeAlgorithm) - { - case KeyExchangeAlgorithm.SRP: - return null; - - case KeyExchangeAlgorithm.SRP_DSS: - return GetDsaSignerCredentials(); - - case KeyExchangeAlgorithm.SRP_RSA: - return GetRsaSignerCredentials(); - - default: - /* Note: internal error here; selected a key exchange we don't implement! */ - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } - - public override TlsKeyExchange GetKeyExchange() - { - int keyExchangeAlgorithm = TlsUtilities.GetKeyExchangeAlgorithm(mSelectedCipherSuite); - - switch (keyExchangeAlgorithm) - { - case KeyExchangeAlgorithm.SRP: - case KeyExchangeAlgorithm.SRP_DSS: - case KeyExchangeAlgorithm.SRP_RSA: - return CreateSrpKeyExchange(keyExchangeAlgorithm); - - default: - /* - * Note: internal error here; the TlsProtocol implementation verifies that the - * server-selected cipher suite was in the list of client-offered cipher suites, so if - * we now can't produce an implementation, we shouldn't have offered it! - */ - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } - - protected virtual TlsKeyExchange CreateSrpKeyExchange(int keyExchange) - { - return new TlsSrpKeyExchange(keyExchange, mSupportedSignatureAlgorithms, mSrpIdentity, mLoginParameters); - } - } -} diff --git a/crypto/src/crypto/tls/SrtpProtectionProfile.cs b/crypto/src/crypto/tls/SrtpProtectionProfile.cs deleted file mode 100644 index 6e9091bb9..000000000 --- a/crypto/src/crypto/tls/SrtpProtectionProfile.cs +++ /dev/null @@ -1,21 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class SrtpProtectionProfile - { - /* - * RFC 5764 4.1.2. - */ - public const int SRTP_AES128_CM_HMAC_SHA1_80 = 0x0001; - public const int SRTP_AES128_CM_HMAC_SHA1_32 = 0x0002; - public const int SRTP_NULL_HMAC_SHA1_80 = 0x0005; - public const int SRTP_NULL_HMAC_SHA1_32 = 0x0006; - - /* - * RFC 7714 14.2. - */ - public const int SRTP_AEAD_AES_128_GCM = 0x0007; - public const int SRTP_AEAD_AES_256_GCM = 0x0008; - } -} diff --git a/crypto/src/crypto/tls/Ssl3Mac.cs b/crypto/src/crypto/tls/Ssl3Mac.cs deleted file mode 100644 index 8bdb342dc..000000000 --- a/crypto/src/crypto/tls/Ssl3Mac.cs +++ /dev/null @@ -1,110 +0,0 @@ -using System; - -using Org.BouncyCastle.Crypto; -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /** - * HMAC implementation based on original internet draft for HMAC (RFC 2104) - * - * The difference is that padding is concatentated versus XORed with the key - * - * H(K + opad, H(K + ipad, text)) - */ - public class Ssl3Mac - : IMac - { - private const byte IPAD_BYTE = 0x36; - private const byte OPAD_BYTE = 0x5C; - - internal static readonly byte[] IPAD = GenPad(IPAD_BYTE, 48); - internal static readonly byte[] OPAD = GenPad(OPAD_BYTE, 48); - - private readonly IDigest digest; - private readonly int padLength; - - private byte[] secret; - - /** - * Base constructor for one of the standard digest algorithms that the byteLength of - * the algorithm is know for. Behaviour is undefined for digests other than MD5 or SHA1. - * - * @param digest the digest. - */ - public Ssl3Mac(IDigest digest) - { - this.digest = digest; - - if (digest.GetDigestSize() == 20) - { - this.padLength = 40; - } - else - { - this.padLength = 48; - } - } - - public virtual string AlgorithmName - { - get { return digest.AlgorithmName + "/SSL3MAC"; } - } - - public virtual void Init(ICipherParameters parameters) - { - secret = Arrays.Clone(((KeyParameter)parameters).GetKey()); - - Reset(); - } - - public virtual int GetMacSize() - { - return digest.GetDigestSize(); - } - - public virtual void Update(byte input) - { - digest.Update(input); - } - - public virtual void BlockUpdate(byte[] input, int inOff, int len) - { - digest.BlockUpdate(input, inOff, len); - } - - public virtual int DoFinal(byte[] output, int outOff) - { - byte[] tmp = new byte[digest.GetDigestSize()]; - digest.DoFinal(tmp, 0); - - digest.BlockUpdate(secret, 0, secret.Length); - digest.BlockUpdate(OPAD, 0, padLength); - digest.BlockUpdate(tmp, 0, tmp.Length); - - int len = digest.DoFinal(output, outOff); - - Reset(); - - return len; - } - - /** - * Reset the mac generator. - */ - public virtual void Reset() - { - digest.Reset(); - digest.BlockUpdate(secret, 0, secret.Length); - digest.BlockUpdate(IPAD, 0, padLength); - } - - private static byte[] GenPad(byte b, int count) - { - byte[] padding = new byte[count]; - Arrays.Fill(padding, b); - return padding; - } - } -} diff --git a/crypto/src/crypto/tls/SupplementalDataEntry.cs b/crypto/src/crypto/tls/SupplementalDataEntry.cs deleted file mode 100644 index 5adc4fa52..000000000 --- a/crypto/src/crypto/tls/SupplementalDataEntry.cs +++ /dev/null @@ -1,26 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class SupplementalDataEntry - { - protected readonly int mDataType; - protected readonly byte[] mData; - - public SupplementalDataEntry(int dataType, byte[] data) - { - this.mDataType = dataType; - this.mData = data; - } - - public virtual int DataType - { - get { return mDataType; } - } - - public virtual byte[] Data - { - get { return mData; } - } - } -} diff --git a/crypto/src/crypto/tls/SupplementalDataType.cs b/crypto/src/crypto/tls/SupplementalDataType.cs deleted file mode 100644 index 79511c50a..000000000 --- a/crypto/src/crypto/tls/SupplementalDataType.cs +++ /dev/null @@ -1,13 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary>RFC 4680</summary> - public abstract class SupplementalDataType - { - /* - * RFC 4681 - */ - public const int user_mapping_data = 0; - } -} diff --git a/crypto/src/crypto/tls/Timeout.cs b/crypto/src/crypto/tls/Timeout.cs deleted file mode 100644 index 924073c4f..000000000 --- a/crypto/src/crypto/tls/Timeout.cs +++ /dev/null @@ -1,121 +0,0 @@ -using System; - -using Org.BouncyCastle.Utilities.Date; - -namespace Org.BouncyCastle.Crypto.Tls -{ - internal class Timeout - { - private long durationMillis; - private long startMillis; - - internal Timeout(long durationMillis) - : this(durationMillis, DateTimeUtilities.CurrentUnixMs()) - { - } - - internal Timeout(long durationMillis, long currentTimeMillis) - { - this.durationMillis = System.Math.Max(0, durationMillis); - this.startMillis = System.Math.Max(0, currentTimeMillis); - } - - //internal long RemainingMillis() - //{ - // return RemainingMillis(DateTimeUtilities.CurrentUnixMs()); - //} - - internal long RemainingMillis(long currentTimeMillis) - { - lock (this) - { - // If clock jumped backwards, reset start time - if (startMillis > currentTimeMillis) - { - startMillis = currentTimeMillis; - return durationMillis; - } - - long elapsed = currentTimeMillis - startMillis; - long remaining = durationMillis - elapsed; - - // Once timeout reached, lock it in - if (remaining <= 0) - { - return durationMillis = 0L; - } - - return remaining; - } - } - - //internal static int ConstrainWaitMillis(int waitMillis, Timeout timeout) - //{ - // return ConstrainWaitMillis(waitMillis, timeout, DateTimeUtilities.CurrentUnixMs()); - //} - - internal static int ConstrainWaitMillis(int waitMillis, Timeout timeout, long currentTimeMillis) - { - if (waitMillis < 0) - return -1; - - int timeoutMillis = GetWaitMillis(timeout, currentTimeMillis); - if (timeoutMillis < 0) - return -1; - - if (waitMillis == 0) - return timeoutMillis; - - if (timeoutMillis == 0) - return waitMillis; - - return System.Math.Min(waitMillis, timeoutMillis); - } - - internal static Timeout ForWaitMillis(int waitMillis) - { - return ForWaitMillis(waitMillis, DateTimeUtilities.CurrentUnixMs()); - } - - internal static Timeout ForWaitMillis(int waitMillis, long currentTimeMillis) - { - if (waitMillis < 0) - throw new ArgumentException("cannot be negative", "waitMillis"); - - if (waitMillis > 0) - return new Timeout(waitMillis, currentTimeMillis); - - return null; - } - - //internal static int GetWaitMillis(Timeout timeout) - //{ - // return GetWaitMillis(timeout, DateTimeUtilities.CurrentUnixMs()); - //} - - internal static int GetWaitMillis(Timeout timeout, long currentTimeMillis) - { - if (null == timeout) - return 0; - - long remainingMillis = timeout.RemainingMillis(currentTimeMillis); - if (remainingMillis < 1L) - return -1; - - if (remainingMillis > int.MaxValue) - return int.MaxValue; - - return (int)remainingMillis; - } - - //internal static bool HasExpired(Timeout timeout) - //{ - // return HasExpired(timeout, DateTimeUtilities.CurrentUnixMs()); - //} - - internal static bool HasExpired(Timeout timeout, long currentTimeMillis) - { - return null != timeout && timeout.RemainingMillis(currentTimeMillis) < 1L; - } - } -} diff --git a/crypto/src/crypto/tls/TlsAeadCipher.cs b/crypto/src/crypto/tls/TlsAeadCipher.cs deleted file mode 100644 index 9a65d5ee5..000000000 --- a/crypto/src/crypto/tls/TlsAeadCipher.cs +++ /dev/null @@ -1,252 +0,0 @@ -using System; -using System.IO; - -using Org.BouncyCastle.Crypto.Modes; -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class TlsAeadCipher - : TlsCipher - { - // TODO[draft-zauner-tls-aes-ocb-04] Apply data volume limit described in section 8.4 - - public const int NONCE_RFC5288 = 1; - - /* - * draft-zauner-tls-aes-ocb-04 specifies the nonce construction from draft-ietf-tls-chacha20-poly1305-04 - */ - internal const int NONCE_DRAFT_CHACHA20_POLY1305 = 2; - - protected readonly TlsContext context; - protected readonly int macSize; - // TODO SecurityParameters.record_iv_length - protected readonly int record_iv_length; - - protected readonly IAeadBlockCipher encryptCipher; - protected readonly IAeadBlockCipher decryptCipher; - - protected readonly byte[] encryptImplicitNonce, decryptImplicitNonce; - - protected readonly int nonceMode; - - /// <exception cref="IOException"></exception> - public TlsAeadCipher(TlsContext context, IAeadBlockCipher clientWriteCipher, IAeadBlockCipher serverWriteCipher, - int cipherKeySize, int macSize) - : this(context, clientWriteCipher, serverWriteCipher, cipherKeySize, macSize, NONCE_RFC5288) - { - } - - /// <exception cref="IOException"></exception> - internal TlsAeadCipher(TlsContext context, IAeadBlockCipher clientWriteCipher, IAeadBlockCipher serverWriteCipher, - int cipherKeySize, int macSize, int nonceMode) - { - if (!TlsUtilities.IsTlsV12(context)) - throw new TlsFatalAlert(AlertDescription.internal_error); - - this.nonceMode = nonceMode; - - // TODO SecurityParameters.fixed_iv_length - int fixed_iv_length; - - switch (nonceMode) - { - case NONCE_RFC5288: - fixed_iv_length = 4; - this.record_iv_length = 8; - break; - case NONCE_DRAFT_CHACHA20_POLY1305: - fixed_iv_length = 12; - this.record_iv_length = 0; - break; - default: - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - this.context = context; - this.macSize = macSize; - - int key_block_size = (2 * cipherKeySize) + (2 * fixed_iv_length); - - byte[] key_block = TlsUtilities.CalculateKeyBlock(context, key_block_size); - - int offset = 0; - - KeyParameter client_write_key = new KeyParameter(key_block, offset, cipherKeySize); - offset += cipherKeySize; - KeyParameter server_write_key = new KeyParameter(key_block, offset, cipherKeySize); - offset += cipherKeySize; - byte[] client_write_IV = Arrays.CopyOfRange(key_block, offset, offset + fixed_iv_length); - offset += fixed_iv_length; - byte[] server_write_IV = Arrays.CopyOfRange(key_block, offset, offset + fixed_iv_length); - offset += fixed_iv_length; - - if (offset != key_block_size) - throw new TlsFatalAlert(AlertDescription.internal_error); - - KeyParameter encryptKey, decryptKey; - if (context.IsServer) - { - this.encryptCipher = serverWriteCipher; - this.decryptCipher = clientWriteCipher; - this.encryptImplicitNonce = server_write_IV; - this.decryptImplicitNonce = client_write_IV; - encryptKey = server_write_key; - decryptKey = client_write_key; - } - else - { - this.encryptCipher = clientWriteCipher; - this.decryptCipher = serverWriteCipher; - this.encryptImplicitNonce = client_write_IV; - this.decryptImplicitNonce = server_write_IV; - encryptKey = client_write_key; - decryptKey = server_write_key; - } - - // NOTE: Ensure dummy nonce is not part of the generated sequence(s) - byte[] dummyNonce = new byte[fixed_iv_length + record_iv_length]; - dummyNonce[0] = (byte)~encryptImplicitNonce[0]; - dummyNonce[1] = (byte)~decryptImplicitNonce[1]; - - this.encryptCipher.Init(true, new AeadParameters(encryptKey, 8 * macSize, dummyNonce)); - this.decryptCipher.Init(false, new AeadParameters(decryptKey, 8 * macSize, dummyNonce)); - } - - public virtual int GetPlaintextLimit(int ciphertextLimit) - { - // TODO We ought to be able to ask the decryptCipher (independently of it's current state!) - return ciphertextLimit - macSize - record_iv_length; - } - - /// <exception cref="IOException"></exception> - public virtual byte[] EncodePlaintext(long seqNo, byte type, byte[] plaintext, int offset, int len) - { - byte[] nonce = new byte[encryptImplicitNonce.Length + record_iv_length]; - - switch (nonceMode) - { - case NONCE_RFC5288: - Array.Copy(encryptImplicitNonce, 0, nonce, 0, encryptImplicitNonce.Length); - // RFC 5288/6655: The nonce_explicit MAY be the 64-bit sequence number. - TlsUtilities.WriteUint64(seqNo, nonce, encryptImplicitNonce.Length); - break; - case NONCE_DRAFT_CHACHA20_POLY1305: - TlsUtilities.WriteUint64(seqNo, nonce, nonce.Length - 8); - for (int i = 0; i < encryptImplicitNonce.Length; ++i) - { - nonce[i] ^= encryptImplicitNonce[i]; - } - break; - default: - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - int plaintextOffset = offset; - int plaintextLength = len; - int ciphertextLength = encryptCipher.GetOutputSize(plaintextLength); - - byte[] output = new byte[record_iv_length + ciphertextLength]; - if (record_iv_length != 0) - { - Array.Copy(nonce, nonce.Length - record_iv_length, output, 0, record_iv_length); - } - int outputPos = record_iv_length; - - byte[] additionalData = GetAdditionalData(seqNo, type, plaintextLength); - AeadParameters parameters = new AeadParameters(null, 8 * macSize, nonce, additionalData); - - try - { - encryptCipher.Init(true, parameters); - outputPos += encryptCipher.ProcessBytes(plaintext, plaintextOffset, plaintextLength, output, outputPos); - outputPos += encryptCipher.DoFinal(output, outputPos); - } - catch (Exception e) - { - throw new TlsFatalAlert(AlertDescription.internal_error, e); - } - - if (outputPos != output.Length) - { - // NOTE: Existing AEAD cipher implementations all give exact output lengths - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - return output; - } - - /// <exception cref="IOException"></exception> - public virtual byte[] DecodeCiphertext(long seqNo, byte type, byte[] ciphertext, int offset, int len) - { - if (GetPlaintextLimit(len) < 0) - throw new TlsFatalAlert(AlertDescription.decode_error); - - byte[] nonce = new byte[decryptImplicitNonce.Length + record_iv_length]; - - switch (nonceMode) - { - case NONCE_RFC5288: - Array.Copy(decryptImplicitNonce, 0, nonce, 0, decryptImplicitNonce.Length); - Array.Copy(ciphertext, offset, nonce, nonce.Length - record_iv_length, record_iv_length); - break; - case NONCE_DRAFT_CHACHA20_POLY1305: - TlsUtilities.WriteUint64(seqNo, nonce, nonce.Length - 8); - for (int i = 0; i < decryptImplicitNonce.Length; ++i) - { - nonce[i] ^= decryptImplicitNonce[i]; - } - break; - default: - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - int ciphertextOffset = offset + record_iv_length; - int ciphertextLength = len - record_iv_length; - int plaintextLength = decryptCipher.GetOutputSize(ciphertextLength); - - byte[] output = new byte[plaintextLength]; - int outputPos = 0; - - byte[] additionalData = GetAdditionalData(seqNo, type, plaintextLength); - AeadParameters parameters = new AeadParameters(null, 8 * macSize, nonce, additionalData); - - try - { - decryptCipher.Init(false, parameters); - outputPos += decryptCipher.ProcessBytes(ciphertext, ciphertextOffset, ciphertextLength, output, outputPos); - outputPos += decryptCipher.DoFinal(output, outputPos); - } - catch (Exception e) - { - throw new TlsFatalAlert(AlertDescription.bad_record_mac, e); - } - - if (outputPos != output.Length) - { - // NOTE: Existing AEAD cipher implementations all give exact output lengths - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - return output; - } - - /// <exception cref="IOException"></exception> - protected virtual byte[] GetAdditionalData(long seqNo, byte type, int len) - { - /* - * additional_data = seq_num + TLSCompressed.type + TLSCompressed.version + - * TLSCompressed.length - */ - - byte[] additional_data = new byte[13]; - TlsUtilities.WriteUint64(seqNo, additional_data, 0); - TlsUtilities.WriteUint8(type, additional_data, 8); - TlsUtilities.WriteVersion(context.ServerVersion, additional_data, 9); - TlsUtilities.WriteUint16(len, additional_data, 11); - - return additional_data; - } - } -} diff --git a/crypto/src/crypto/tls/TlsAgreementCredentials.cs b/crypto/src/crypto/tls/TlsAgreementCredentials.cs deleted file mode 100644 index 7c64072e8..000000000 --- a/crypto/src/crypto/tls/TlsAgreementCredentials.cs +++ /dev/null @@ -1,12 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public interface TlsAgreementCredentials - : TlsCredentials - { - /// <exception cref="IOException"></exception> - byte[] GenerateAgreement(AsymmetricKeyParameter peerPublicKey); - } -} diff --git a/crypto/src/crypto/tls/TlsAuthentication.cs b/crypto/src/crypto/tls/TlsAuthentication.cs deleted file mode 100644 index 9aea5e449..000000000 --- a/crypto/src/crypto/tls/TlsAuthentication.cs +++ /dev/null @@ -1,31 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public interface TlsAuthentication - { - /// <summary> - /// Called by the protocol handler to report the server certificate. - /// </summary> - /// <remarks> - /// This method is responsible for certificate verification and validation - /// </remarks> - /// <param name="serverCertificate">The server <see cref="Certificate"/> received</param> - /// <exception cref="IOException"></exception> - void NotifyServerCertificate(Certificate serverCertificate); - - /// <summary> - /// Return client credentials in response to server's certificate request - /// </summary> - /// <param name="certificateRequest"> - /// A <see cref="CertificateRequest"/> containing server certificate request details - /// </param> - /// <returns> - /// A <see cref="TlsCredentials"/> to be used for client authentication - /// (or <c>null</c> for no client authentication) - /// </returns> - /// <exception cref="IOException"></exception> - TlsCredentials GetClientCredentials(CertificateRequest certificateRequest); - } -} diff --git a/crypto/src/crypto/tls/TlsBlockCipher.cs b/crypto/src/crypto/tls/TlsBlockCipher.cs deleted file mode 100644 index 76b476a18..000000000 --- a/crypto/src/crypto/tls/TlsBlockCipher.cs +++ /dev/null @@ -1,395 +0,0 @@ -using System; -using System.IO; - -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Security; -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary> - /// A generic TLS 1.0-1.2 / SSLv3 block cipher. This can be used for AES or 3DES for example. - /// </summary> - public class TlsBlockCipher - : TlsCipher - { - protected readonly TlsContext context; - protected readonly byte[] randomData; - protected readonly bool useExplicitIV; - protected readonly bool encryptThenMac; - - protected readonly IBlockCipher encryptCipher; - protected readonly IBlockCipher decryptCipher; - - protected readonly TlsMac mWriteMac; - protected readonly TlsMac mReadMac; - - public virtual TlsMac WriteMac - { - get { return mWriteMac; } - } - - public virtual TlsMac ReadMac - { - get { return mReadMac; } - } - - /// <exception cref="IOException"></exception> - public TlsBlockCipher(TlsContext context, IBlockCipher clientWriteCipher, IBlockCipher serverWriteCipher, - IDigest clientWriteDigest, IDigest serverWriteDigest, int cipherKeySize) - { - this.context = context; - - this.randomData = new byte[256]; - context.NonceRandomGenerator.NextBytes(randomData); - - this.useExplicitIV = TlsUtilities.IsTlsV11(context); - this.encryptThenMac = context.SecurityParameters.encryptThenMac; - - int key_block_size = (2 * cipherKeySize) + clientWriteDigest.GetDigestSize() - + serverWriteDigest.GetDigestSize(); - - // From TLS 1.1 onwards, block ciphers don't need client_write_IV - if (!useExplicitIV) - { - key_block_size += clientWriteCipher.GetBlockSize() + serverWriteCipher.GetBlockSize(); - } - - byte[] key_block = TlsUtilities.CalculateKeyBlock(context, key_block_size); - - int offset = 0; - - TlsMac clientWriteMac = new TlsMac(context, clientWriteDigest, key_block, offset, - clientWriteDigest.GetDigestSize()); - offset += clientWriteDigest.GetDigestSize(); - TlsMac serverWriteMac = new TlsMac(context, serverWriteDigest, key_block, offset, - serverWriteDigest.GetDigestSize()); - offset += serverWriteDigest.GetDigestSize(); - - KeyParameter client_write_key = new KeyParameter(key_block, offset, cipherKeySize); - offset += cipherKeySize; - KeyParameter server_write_key = new KeyParameter(key_block, offset, cipherKeySize); - offset += cipherKeySize; - - byte[] client_write_IV, server_write_IV; - if (useExplicitIV) - { - client_write_IV = new byte[clientWriteCipher.GetBlockSize()]; - server_write_IV = new byte[serverWriteCipher.GetBlockSize()]; - } - else - { - client_write_IV = Arrays.CopyOfRange(key_block, offset, offset + clientWriteCipher.GetBlockSize()); - offset += clientWriteCipher.GetBlockSize(); - server_write_IV = Arrays.CopyOfRange(key_block, offset, offset + serverWriteCipher.GetBlockSize()); - offset += serverWriteCipher.GetBlockSize(); - } - - if (offset != key_block_size) - { - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - ICipherParameters encryptParams, decryptParams; - if (context.IsServer) - { - this.mWriteMac = serverWriteMac; - this.mReadMac = clientWriteMac; - this.encryptCipher = serverWriteCipher; - this.decryptCipher = clientWriteCipher; - encryptParams = new ParametersWithIV(server_write_key, server_write_IV); - decryptParams = new ParametersWithIV(client_write_key, client_write_IV); - } - else - { - this.mWriteMac = clientWriteMac; - this.mReadMac = serverWriteMac; - this.encryptCipher = clientWriteCipher; - this.decryptCipher = serverWriteCipher; - encryptParams = new ParametersWithIV(client_write_key, client_write_IV); - decryptParams = new ParametersWithIV(server_write_key, server_write_IV); - } - - this.encryptCipher.Init(true, encryptParams); - this.decryptCipher.Init(false, decryptParams); - } - - public virtual int GetPlaintextLimit(int ciphertextLimit) - { - int blockSize = encryptCipher.GetBlockSize(); - int macSize = mWriteMac.Size; - - int plaintextLimit = ciphertextLimit; - - // An explicit IV consumes 1 block - if (useExplicitIV) - { - plaintextLimit -= blockSize; - } - - // Leave room for the MAC, and require block-alignment - if (encryptThenMac) - { - plaintextLimit -= macSize; - plaintextLimit -= plaintextLimit % blockSize; - } - else - { - plaintextLimit -= plaintextLimit % blockSize; - plaintextLimit -= macSize; - } - - // Minimum 1 byte of padding - --plaintextLimit; - - return plaintextLimit; - } - - public virtual byte[] EncodePlaintext(long seqNo, byte type, byte[] plaintext, int offset, int len) - { - int blockSize = encryptCipher.GetBlockSize(); - int macSize = mWriteMac.Size; - - ProtocolVersion version = context.ServerVersion; - - int enc_input_length = len; - if (!encryptThenMac) - { - enc_input_length += macSize; - } - - int padding_length = blockSize - 1 - (enc_input_length % blockSize); - - /* - * Don't use variable-length padding with truncated MACs. - * - * See "Tag Size Does Matter: Attacks and Proofs for the TLS Record Protocol", Paterson, - * Ristenpart, Shrimpton. - */ - if (encryptThenMac || !context.SecurityParameters.truncatedHMac) - { - // TODO[DTLS] Consider supporting in DTLS (without exceeding send limit though) - if (!version.IsDtls && !version.IsSsl) - { - // Add a random number of extra blocks worth of padding - int maxExtraPadBlocks = (255 - padding_length) / blockSize; - int actualExtraPadBlocks = ChooseExtraPadBlocks(context.SecureRandom, maxExtraPadBlocks); - padding_length += actualExtraPadBlocks * blockSize; - } - } - - int totalSize = len + macSize + padding_length + 1; - if (useExplicitIV) - { - totalSize += blockSize; - } - - byte[] outBuf = new byte[totalSize]; - int outOff = 0; - - if (useExplicitIV) - { - byte[] explicitIV = new byte[blockSize]; - context.NonceRandomGenerator.NextBytes(explicitIV); - - encryptCipher.Init(true, new ParametersWithIV(null, explicitIV)); - - Array.Copy(explicitIV, 0, outBuf, outOff, blockSize); - outOff += blockSize; - } - - int blocks_start = outOff; - - Array.Copy(plaintext, offset, outBuf, outOff, len); - outOff += len; - - if (!encryptThenMac) - { - byte[] mac = mWriteMac.CalculateMac(seqNo, type, plaintext, offset, len); - Array.Copy(mac, 0, outBuf, outOff, mac.Length); - outOff += mac.Length; - } - - for (int i = 0; i <= padding_length; i++) - { - outBuf[outOff++] = (byte)padding_length; - } - - for (int i = blocks_start; i < outOff; i += blockSize) - { - encryptCipher.ProcessBlock(outBuf, i, outBuf, i); - } - - if (encryptThenMac) - { - byte[] mac = mWriteMac.CalculateMac(seqNo, type, outBuf, 0, outOff); - Array.Copy(mac, 0, outBuf, outOff, mac.Length); - outOff += mac.Length; - } - - // assert outBuf.length == outOff; - - return outBuf; - } - - /// <exception cref="IOException"></exception> - public virtual byte[] DecodeCiphertext(long seqNo, byte type, byte[] ciphertext, int offset, int len) - { - int blockSize = decryptCipher.GetBlockSize(); - int macSize = mReadMac.Size; - - int minLen = blockSize; - if (encryptThenMac) - { - minLen += macSize; - } - else - { - minLen = System.Math.Max(minLen, macSize + 1); - } - - if (useExplicitIV) - { - minLen += blockSize; - } - - if (len < minLen) - throw new TlsFatalAlert(AlertDescription.decode_error); - - int blocks_length = len; - if (encryptThenMac) - { - blocks_length -= macSize; - } - - if (blocks_length % blockSize != 0) - throw new TlsFatalAlert(AlertDescription.decryption_failed); - - if (encryptThenMac) - { - int end = offset + len; - byte[] receivedMac = Arrays.CopyOfRange(ciphertext, end - macSize, end); - byte[] calculatedMac = mReadMac.CalculateMac(seqNo, type, ciphertext, offset, len - macSize); - - bool badMacEtm = !Arrays.ConstantTimeAreEqual(calculatedMac, receivedMac); - if (badMacEtm) - { - /* - * RFC 7366 3. The MAC SHALL be evaluated before any further processing such as - * decryption is performed, and if the MAC verification fails, then processing SHALL - * terminate immediately. For TLS, a fatal bad_record_mac MUST be generated [2]. For - * DTLS, the record MUST be discarded, and a fatal bad_record_mac MAY be generated - * [4]. This immediate response to a bad MAC eliminates any timing channels that may - * be available through the use of manipulated packet data. - */ - throw new TlsFatalAlert(AlertDescription.bad_record_mac); - } - } - - if (useExplicitIV) - { - decryptCipher.Init(false, new ParametersWithIV(null, ciphertext, offset, blockSize)); - - offset += blockSize; - blocks_length -= blockSize; - } - - for (int i = 0; i < blocks_length; i += blockSize) - { - decryptCipher.ProcessBlock(ciphertext, offset + i, ciphertext, offset + i); - } - - // If there's anything wrong with the padding, this will return zero - int totalPad = CheckPaddingConstantTime(ciphertext, offset, blocks_length, blockSize, encryptThenMac ? 0 : macSize); - bool badMac = (totalPad == 0); - - int dec_output_length = blocks_length - totalPad; - - if (!encryptThenMac) - { - dec_output_length -= macSize; - int macInputLen = dec_output_length; - int macOff = offset + macInputLen; - byte[] receivedMac = Arrays.CopyOfRange(ciphertext, macOff, macOff + macSize); - byte[] calculatedMac = mReadMac.CalculateMacConstantTime(seqNo, type, ciphertext, offset, macInputLen, - blocks_length - macSize, randomData); - - badMac |= !Arrays.ConstantTimeAreEqual(calculatedMac, receivedMac); - } - - if (badMac) - throw new TlsFatalAlert(AlertDescription.bad_record_mac); - - return Arrays.CopyOfRange(ciphertext, offset, offset + dec_output_length); - } - - protected virtual int CheckPaddingConstantTime(byte[] buf, int off, int len, int blockSize, int macSize) - { - int end = off + len; - byte lastByte = buf[end - 1]; - int padlen = lastByte & 0xff; - int totalPad = padlen + 1; - - int dummyIndex = 0; - byte padDiff = 0; - - if ((TlsUtilities.IsSsl(context) && totalPad > blockSize) || (macSize + totalPad > len)) - { - totalPad = 0; - } - else - { - int padPos = end - totalPad; - do - { - padDiff |= (byte)(buf[padPos++] ^ lastByte); - } - while (padPos < end); - - dummyIndex = totalPad; - - if (padDiff != 0) - { - totalPad = 0; - } - } - - // Run some extra dummy checks so the number of checks is always constant - { - byte[] dummyPad = randomData; - while (dummyIndex < 256) - { - padDiff |= (byte)(dummyPad[dummyIndex++] ^ lastByte); - } - // Ensure the above loop is not eliminated - dummyPad[0] ^= padDiff; - } - - return totalPad; - } - - protected virtual int ChooseExtraPadBlocks(SecureRandom r, int max) - { - // return r.NextInt(max + 1); - - int x = r.NextInt(); - int n = LowestBitSet(x); - return System.Math.Min(n, max); - } - - protected virtual int LowestBitSet(int x) - { - if (x == 0) - return 32; - - uint ux = (uint)x; - int n = 0; - while ((ux & 1U) == 0) - { - ++n; - ux >>= 1; - } - return n; - } - } -} diff --git a/crypto/src/crypto/tls/TlsCipher.cs b/crypto/src/crypto/tls/TlsCipher.cs deleted file mode 100644 index 7bd8573ac..000000000 --- a/crypto/src/crypto/tls/TlsCipher.cs +++ /dev/null @@ -1,16 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public interface TlsCipher - { - int GetPlaintextLimit(int ciphertextLimit); - - /// <exception cref="IOException"></exception> - byte[] EncodePlaintext(long seqNo, byte type, byte[] plaintext, int offset, int len); - - /// <exception cref="IOException"></exception> - byte[] DecodeCiphertext(long seqNo, byte type, byte[] ciphertext, int offset, int len); - } -} diff --git a/crypto/src/crypto/tls/TlsCipherFactory.cs b/crypto/src/crypto/tls/TlsCipherFactory.cs deleted file mode 100644 index 4e1fe0eb9..000000000 --- a/crypto/src/crypto/tls/TlsCipherFactory.cs +++ /dev/null @@ -1,11 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public interface TlsCipherFactory - { - /// <exception cref="IOException"></exception> - TlsCipher CreateCipher(TlsContext context, int encryptionAlgorithm, int macAlgorithm); - } -} diff --git a/crypto/src/crypto/tls/TlsClient.cs b/crypto/src/crypto/tls/TlsClient.cs deleted file mode 100644 index 73f169054..000000000 --- a/crypto/src/crypto/tls/TlsClient.cs +++ /dev/null @@ -1,148 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public interface TlsClient - : TlsPeer - { - /// <summary> - /// Called at the start of a new TLS session, before any other methods. - /// </summary> - /// <param name="context"> - /// A <see cref="TlsProtocolHandler"/> - /// </param> - void Init(TlsClientContext context); - - /// <summary>Return the session this client wants to resume, if any.</summary> - /// <remarks>Note that the peer's certificate chain for the session (if any) may need to be periodically revalidated.</remarks> - /// <returns> - /// A <see cref="TlsSession"/> representing the resumable session to be used for this connection, - /// or null to use a new session. - /// </returns> - TlsSession GetSessionToResume(); - - /// <summary> - /// Return the <see cref="ProtocolVersion"/> to use for the <c>TLSPlaintext.version</c> field prior to - /// receiving the server version. NOTE: This method is <b>not</b> called for DTLS. - /// </summary> - /// <remarks> - /// See RFC 5246 E.1.: "TLS clients that wish to negotiate with older servers MAY send any value - /// {03,XX} as the record layer version number. Typical values would be {03,00}, the lowest - /// version number supported by the client, and the value of ClientHello.client_version. No - /// single value will guarantee interoperability with all old servers, but this is a complex - /// topic beyond the scope of this document." - /// </remarks> - /// <returns>The <see cref="ProtocolVersion"/> to use.</returns> - ProtocolVersion ClientHelloRecordLayerVersion { get; } - - ProtocolVersion ClientVersion { get; } - - bool IsFallback { get; } - - /// <summary> - /// Get the list of cipher suites that this client supports. - /// </summary> - /// <returns> - /// An array of <see cref="CipherSuite"/> values, each specifying a supported cipher suite. - /// </returns> - int[] GetCipherSuites(); - - /// <summary> - /// Get the list of compression methods that this client supports. - /// </summary> - /// <returns> - /// An array of <see cref="CompressionMethod"/> values, each specifying a supported compression method. - /// </returns> - byte[] GetCompressionMethods(); - - /// <summary> - /// Get the (optional) table of client extensions to be included in (extended) client hello. - /// </summary> - /// <returns> - /// A <see cref="IDictionary"/> (Int32 -> byte[]). May be null. - /// </returns> - /// <exception cref="IOException"></exception> - IDictionary GetClientExtensions(); - - /// <exception cref="IOException"></exception> - void NotifyServerVersion(ProtocolVersion selectedVersion); - - /// <summary> - /// Notifies the client of the session_id sent in the ServerHello. - /// </summary> - /// <param name="sessionID">An array of <see cref="System.Byte"/></param> - void NotifySessionID(byte[] sessionID); - - /// <summary> - /// Report the cipher suite that was selected by the server. - /// </summary> - /// <remarks> - /// The protocol handler validates this value against the offered cipher suites - /// <seealso cref="GetCipherSuites"/> - /// </remarks> - /// <param name="selectedCipherSuite"> - /// A <see cref="CipherSuite"/> - /// </param> - void NotifySelectedCipherSuite(int selectedCipherSuite); - - /// <summary> - /// Report the compression method that was selected by the server. - /// </summary> - /// <remarks> - /// The protocol handler validates this value against the offered compression methods - /// <seealso cref="GetCompressionMethods"/> - /// </remarks> - /// <param name="selectedCompressionMethod"> - /// A <see cref="CompressionMethod"/> - /// </param> - void NotifySelectedCompressionMethod(byte selectedCompressionMethod); - - /// <summary> - /// Report the extensions from an extended server hello. - /// </summary> - /// <remarks> - /// Will only be called if we returned a non-null result from <see cref="GetClientExtensions"/>. - /// </remarks> - /// <param name="serverExtensions"> - /// A <see cref="IDictionary"/> (Int32 -> byte[]) - /// </param> - void ProcessServerExtensions(IDictionary serverExtensions); - - /// <param name="serverSupplementalData">A <see cref="IList">list</see> of <see cref="SupplementalDataEntry"/></param> - /// <exception cref="IOException"/> - void ProcessServerSupplementalData(IList serverSupplementalData); - - /// <summary> - /// Return an implementation of <see cref="TlsKeyExchange"/> to negotiate the key exchange - /// part of the protocol. - /// </summary> - /// <returns> - /// A <see cref="TlsKeyExchange"/> - /// </returns> - /// <exception cref="IOException"/> - TlsKeyExchange GetKeyExchange(); - - /// <summary> - /// Return an implementation of <see cref="TlsAuthentication"/> to handle authentication - /// part of the protocol. - /// </summary> - /// <exception cref="IOException"/> - TlsAuthentication GetAuthentication(); - - /// <returns>A <see cref="IList">list</see> of <see cref="SupplementalDataEntry"/></returns> - /// <exception cref="IOException"/> - IList GetClientSupplementalData(); - - /// <summary>RFC 5077 3.3. NewSessionTicket Handshake Message</summary> - /// <remarks> - /// This method will be called (only) when a NewSessionTicket handshake message is received. The - /// ticket is opaque to the client and clients MUST NOT examine the ticket under the assumption - /// that it complies with e.g. <i>RFC 5077 4. Recommended Ticket Construction</i>. - /// </remarks> - /// <param name="newSessionTicket">The <see cref="NewSessionTicket">ticket</see></param> - /// <exception cref="IOException"/> - void NotifyNewSessionTicket(NewSessionTicket newSessionTicket); - } -} diff --git a/crypto/src/crypto/tls/TlsClientContext.cs b/crypto/src/crypto/tls/TlsClientContext.cs deleted file mode 100644 index b077d0aaf..000000000 --- a/crypto/src/crypto/tls/TlsClientContext.cs +++ /dev/null @@ -1,11 +0,0 @@ -using System; - -using Org.BouncyCastle.Security; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public interface TlsClientContext - : TlsContext - { - } -} diff --git a/crypto/src/crypto/tls/TlsClientContextImpl.cs b/crypto/src/crypto/tls/TlsClientContextImpl.cs deleted file mode 100644 index 674d68937..000000000 --- a/crypto/src/crypto/tls/TlsClientContextImpl.cs +++ /dev/null @@ -1,20 +0,0 @@ -using System; - -using Org.BouncyCastle.Security; - -namespace Org.BouncyCastle.Crypto.Tls -{ - internal class TlsClientContextImpl - : AbstractTlsContext, TlsClientContext - { - internal TlsClientContextImpl(SecureRandom secureRandom, SecurityParameters securityParameters) - : base(secureRandom, securityParameters) - { - } - - public override bool IsServer - { - get { return false; } - } - } -} diff --git a/crypto/src/crypto/tls/TlsClientProtocol.cs b/crypto/src/crypto/tls/TlsClientProtocol.cs deleted file mode 100644 index 1fe5744d3..000000000 --- a/crypto/src/crypto/tls/TlsClientProtocol.cs +++ /dev/null @@ -1,918 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Security; -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class TlsClientProtocol - : TlsProtocol - { - protected TlsClient mTlsClient = null; - internal TlsClientContextImpl mTlsClientContext = null; - - protected byte[] mSelectedSessionID = null; - - protected TlsKeyExchange mKeyExchange = null; - protected TlsAuthentication mAuthentication = null; - - protected CertificateStatus mCertificateStatus = null; - protected CertificateRequest mCertificateRequest = null; - - /** - * Constructor for blocking mode. - * @param stream The bi-directional stream of data to/from the server - * @param secureRandom Random number generator for various cryptographic functions - */ - public TlsClientProtocol(Stream stream, SecureRandom secureRandom) - : base(stream, secureRandom) - { - } - - /** - * Constructor for blocking mode. - * @param input The stream of data from the server - * @param output The stream of data to the server - * @param secureRandom Random number generator for various cryptographic functions - */ - public TlsClientProtocol(Stream input, Stream output, SecureRandom secureRandom) - : base(input, output, secureRandom) - { - } - - /** - * Constructor for non-blocking mode.<br/> - * <br/> - * When data is received, use {@link #offerInput(java.nio.ByteBuffer)} to - * provide the received ciphertext, then use - * {@link #readInput(byte[], int, int)} to read the corresponding cleartext.<br/> - * <br/> - * Similarly, when data needs to be sent, use - * {@link #offerOutput(byte[], int, int)} to provide the cleartext, then use - * {@link #readOutput(byte[], int, int)} to get the corresponding - * ciphertext. - * - * @param secureRandom - * Random number generator for various cryptographic functions - */ - public TlsClientProtocol(SecureRandom secureRandom) - : base(secureRandom) - { - } - - /** - * Initiates a TLS handshake in the role of client.<br/> - * <br/> - * In blocking mode, this will not return until the handshake is complete. - * In non-blocking mode, use {@link TlsPeer#NotifyHandshakeComplete()} to - * receive a callback when the handshake is complete. - * - * @param tlsClient The {@link TlsClient} to use for the handshake. - * @throws IOException If in blocking mode and handshake was not successful. - */ - public virtual void Connect(TlsClient tlsClient) - { - if (tlsClient == null) - throw new ArgumentNullException("tlsClient"); - if (this.mTlsClient != null) - throw new InvalidOperationException("'Connect' can only be called once"); - - this.mTlsClient = tlsClient; - - this.mSecurityParameters = new SecurityParameters(); - this.mSecurityParameters.entity = ConnectionEnd.client; - - this.mTlsClientContext = new TlsClientContextImpl(mSecureRandom, mSecurityParameters); - - this.mSecurityParameters.clientRandom = CreateRandomBlock(tlsClient.ShouldUseGmtUnixTime(), - mTlsClientContext.NonceRandomGenerator); - - this.mTlsClient.Init(mTlsClientContext); - this.mRecordStream.Init(mTlsClientContext); - - tlsClient.NotifyCloseHandle(this); - - TlsSession sessionToResume = tlsClient.GetSessionToResume(); - if (sessionToResume != null && sessionToResume.IsResumable) - { - SessionParameters sessionParameters = sessionToResume.ExportSessionParameters(); - if (sessionParameters != null && sessionParameters.IsExtendedMasterSecret) - { - this.mTlsSession = sessionToResume; - this.mSessionParameters = sessionParameters; - } - } - - SendClientHelloMessage(); - this.mConnectionState = CS_CLIENT_HELLO; - - BlockForHandshake(); - } - - protected override void CleanupHandshake() - { - base.CleanupHandshake(); - - this.mSelectedSessionID = null; - this.mKeyExchange = null; - this.mAuthentication = null; - this.mCertificateStatus = null; - this.mCertificateRequest = null; - } - - protected override TlsContext Context - { - get { return mTlsClientContext; } - } - - internal override AbstractTlsContext ContextAdmin - { - get { return mTlsClientContext; } - } - - protected override TlsPeer Peer - { - get { return mTlsClient; } - } - - protected override void HandleHandshakeMessage(byte type, MemoryStream buf) - { - if (this.mResumedSession) - { - if (type != HandshakeType.finished || this.mConnectionState != CS_SERVER_HELLO) - throw new TlsFatalAlert(AlertDescription.unexpected_message); - - ProcessFinishedMessage(buf); - this.mConnectionState = CS_SERVER_FINISHED; - - SendChangeCipherSpecMessage(); - SendFinishedMessage(); - this.mConnectionState = CS_CLIENT_FINISHED; - - CompleteHandshake(); - return; - } - - switch (type) - { - case HandshakeType.certificate: - { - switch (this.mConnectionState) - { - case CS_SERVER_HELLO: - case CS_SERVER_SUPPLEMENTAL_DATA: - { - if (this.mConnectionState == CS_SERVER_HELLO) - { - HandleSupplementalData(null); - } - - // Parse the Certificate message and Send to cipher suite - - this.mPeerCertificate = Certificate.Parse(buf); - - AssertEmpty(buf); - - // TODO[RFC 3546] Check whether empty certificates is possible, allowed, or excludes CertificateStatus - if (this.mPeerCertificate == null || this.mPeerCertificate.IsEmpty) - { - this.mAllowCertificateStatus = false; - } - - this.mKeyExchange.ProcessServerCertificate(this.mPeerCertificate); - - this.mAuthentication = mTlsClient.GetAuthentication(); - this.mAuthentication.NotifyServerCertificate(this.mPeerCertificate); - - break; - } - default: - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - - this.mConnectionState = CS_SERVER_CERTIFICATE; - break; - } - case HandshakeType.certificate_status: - { - switch (this.mConnectionState) - { - case CS_SERVER_CERTIFICATE: - { - if (!this.mAllowCertificateStatus) - { - /* - * RFC 3546 3.6. If a server returns a "CertificateStatus" message, then the - * server MUST have included an extension of type "status_request" with empty - * "extension_data" in the extended server hello.. - */ - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - - this.mCertificateStatus = CertificateStatus.Parse(buf); - - AssertEmpty(buf); - - // TODO[RFC 3546] Figure out how to provide this to the client/authentication. - - this.mConnectionState = CS_CERTIFICATE_STATUS; - break; - } - default: - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - break; - } - case HandshakeType.finished: - { - switch (this.mConnectionState) - { - case CS_CLIENT_FINISHED: - case CS_SERVER_SESSION_TICKET: - { - if (this.mConnectionState == CS_CLIENT_FINISHED && this.mExpectSessionTicket) - { - /* - * RFC 5077 3.3. This message MUST be sent if the server included a - * SessionTicket extension in the ServerHello. - */ - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - - ProcessFinishedMessage(buf); - this.mConnectionState = CS_SERVER_FINISHED; - - CompleteHandshake(); - break; - } - default: - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - break; - } - case HandshakeType.server_hello: - { - switch (this.mConnectionState) - { - case CS_CLIENT_HELLO: - { - ReceiveServerHelloMessage(buf); - this.mConnectionState = CS_SERVER_HELLO; - - this.mRecordStream.NotifyHelloComplete(); - - ApplyMaxFragmentLengthExtension(); - - if (this.mResumedSession) - { - this.mSecurityParameters.masterSecret = Arrays.Clone(this.mSessionParameters.MasterSecret); - this.mRecordStream.SetPendingConnectionState(Peer.GetCompression(), Peer.GetCipher()); - } - else - { - InvalidateSession(); - - if (this.mSelectedSessionID.Length > 0) - { - this.mTlsSession = new TlsSessionImpl(this.mSelectedSessionID, null); - } - } - - break; - } - default: - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - break; - } - case HandshakeType.supplemental_data: - { - switch (this.mConnectionState) - { - case CS_SERVER_HELLO: - { - HandleSupplementalData(ReadSupplementalDataMessage(buf)); - break; - } - default: - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - break; - } - case HandshakeType.server_hello_done: - { - switch (this.mConnectionState) - { - case CS_SERVER_HELLO: - case CS_SERVER_SUPPLEMENTAL_DATA: - case CS_SERVER_CERTIFICATE: - case CS_CERTIFICATE_STATUS: - case CS_SERVER_KEY_EXCHANGE: - case CS_CERTIFICATE_REQUEST: - { - if (mConnectionState < CS_SERVER_SUPPLEMENTAL_DATA) - { - HandleSupplementalData(null); - } - - if (mConnectionState < CS_SERVER_CERTIFICATE) - { - // There was no server certificate message; check it's OK - this.mKeyExchange.SkipServerCredentials(); - this.mAuthentication = null; - } - - if (mConnectionState < CS_SERVER_KEY_EXCHANGE) - { - // There was no server key exchange message; check it's OK - this.mKeyExchange.SkipServerKeyExchange(); - } - - AssertEmpty(buf); - - this.mConnectionState = CS_SERVER_HELLO_DONE; - - this.mRecordStream.HandshakeHash.SealHashAlgorithms(); - - IList clientSupplementalData = mTlsClient.GetClientSupplementalData(); - if (clientSupplementalData != null) - { - SendSupplementalDataMessage(clientSupplementalData); - } - this.mConnectionState = CS_CLIENT_SUPPLEMENTAL_DATA; - - TlsCredentials clientCreds = null; - if (mCertificateRequest == null) - { - this.mKeyExchange.SkipClientCredentials(); - } - else - { - clientCreds = this.mAuthentication.GetClientCredentials(mCertificateRequest); - - if (clientCreds == null) - { - this.mKeyExchange.SkipClientCredentials(); - - /* - * RFC 5246 If no suitable certificate is available, the client MUST Send a - * certificate message containing no certificates. - * - * NOTE: In previous RFCs, this was SHOULD instead of MUST. - */ - SendCertificateMessage(Certificate.EmptyChain); - } - else - { - this.mKeyExchange.ProcessClientCredentials(clientCreds); - - SendCertificateMessage(clientCreds.Certificate); - } - } - - this.mConnectionState = CS_CLIENT_CERTIFICATE; - - /* - * Send the client key exchange message, depending on the key exchange we are using - * in our CipherSuite. - */ - SendClientKeyExchangeMessage(); - this.mConnectionState = CS_CLIENT_KEY_EXCHANGE; - - if (TlsUtilities.IsSsl(Context)) - { - EstablishMasterSecret(Context, mKeyExchange); - } - - TlsHandshakeHash prepareFinishHash = mRecordStream.PrepareToFinish(); - this.mSecurityParameters.sessionHash = GetCurrentPrfHash(Context, prepareFinishHash, null); - - if (!TlsUtilities.IsSsl(Context)) - { - EstablishMasterSecret(Context, mKeyExchange); - } - - mRecordStream.SetPendingConnectionState(Peer.GetCompression(), Peer.GetCipher()); - - if (clientCreds != null && clientCreds is TlsSignerCredentials) - { - TlsSignerCredentials signerCredentials = (TlsSignerCredentials)clientCreds; - - /* - * RFC 5246 4.7. digitally-signed element needs SignatureAndHashAlgorithm from TLS 1.2 - */ - SignatureAndHashAlgorithm signatureAndHashAlgorithm = TlsUtilities.GetSignatureAndHashAlgorithm( - Context, signerCredentials); - - byte[] hash; - if (signatureAndHashAlgorithm == null) - { - hash = mSecurityParameters.SessionHash; - } - else - { - hash = prepareFinishHash.GetFinalHash(signatureAndHashAlgorithm.Hash); - } - - byte[] signature = signerCredentials.GenerateCertificateSignature(hash); - DigitallySigned certificateVerify = new DigitallySigned(signatureAndHashAlgorithm, signature); - SendCertificateVerifyMessage(certificateVerify); - - this.mConnectionState = CS_CERTIFICATE_VERIFY; - } - - SendChangeCipherSpecMessage(); - SendFinishedMessage(); - break; - } - default: - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - - this.mConnectionState = CS_CLIENT_FINISHED; - break; - } - case HandshakeType.server_key_exchange: - { - switch (this.mConnectionState) - { - case CS_SERVER_HELLO: - case CS_SERVER_SUPPLEMENTAL_DATA: - case CS_SERVER_CERTIFICATE: - case CS_CERTIFICATE_STATUS: - { - if (mConnectionState < CS_SERVER_SUPPLEMENTAL_DATA) - { - HandleSupplementalData(null); - } - - if (mConnectionState < CS_SERVER_CERTIFICATE) - { - // There was no server certificate message; check it's OK - this.mKeyExchange.SkipServerCredentials(); - this.mAuthentication = null; - } - - this.mKeyExchange.ProcessServerKeyExchange(buf); - - AssertEmpty(buf); - break; - } - default: - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - - this.mConnectionState = CS_SERVER_KEY_EXCHANGE; - break; - } - case HandshakeType.certificate_request: - { - switch (this.mConnectionState) - { - case CS_SERVER_CERTIFICATE: - case CS_CERTIFICATE_STATUS: - case CS_SERVER_KEY_EXCHANGE: - { - if (this.mConnectionState != CS_SERVER_KEY_EXCHANGE) - { - // There was no server key exchange message; check it's OK - this.mKeyExchange.SkipServerKeyExchange(); - } - - if (this.mAuthentication == null) - { - /* - * RFC 2246 7.4.4. It is a fatal handshake_failure alert for an anonymous server - * to request client identification. - */ - throw new TlsFatalAlert(AlertDescription.handshake_failure); - } - - this.mCertificateRequest = CertificateRequest.Parse(Context, buf); - - AssertEmpty(buf); - - this.mKeyExchange.ValidateCertificateRequest(this.mCertificateRequest); - - /* - * TODO Give the client a chance to immediately select the CertificateVerify hash - * algorithm here to avoid tracking the other hash algorithms unnecessarily? - */ - TlsUtilities.TrackHashAlgorithms(this.mRecordStream.HandshakeHash, - this.mCertificateRequest.SupportedSignatureAlgorithms); - - break; - } - default: - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - - this.mConnectionState = CS_CERTIFICATE_REQUEST; - break; - } - case HandshakeType.session_ticket: - { - switch (this.mConnectionState) - { - case CS_CLIENT_FINISHED: - { - if (!this.mExpectSessionTicket) - { - /* - * RFC 5077 3.3. This message MUST NOT be sent if the server did not include a - * SessionTicket extension in the ServerHello. - */ - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - - /* - * RFC 5077 3.4. If the client receives a session ticket from the server, then it - * discards any Session ID that was sent in the ServerHello. - */ - InvalidateSession(); - - ReceiveNewSessionTicketMessage(buf); - break; - } - default: - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - - this.mConnectionState = CS_SERVER_SESSION_TICKET; - break; - } - case HandshakeType.hello_request: - { - AssertEmpty(buf); - - /* - * RFC 2246 7.4.1.1 Hello request This message will be ignored by the client if the - * client is currently negotiating a session. This message may be ignored by the client - * if it does not wish to renegotiate a session, or the client may, if it wishes, - * respond with a no_renegotiation alert. - */ - if (this.mConnectionState == CS_END) - { - RefuseRenegotiation(); - } - break; - } - case HandshakeType.client_hello: - case HandshakeType.client_key_exchange: - case HandshakeType.certificate_verify: - case HandshakeType.hello_verify_request: - default: - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - } - - protected virtual void HandleSupplementalData(IList serverSupplementalData) - { - this.mTlsClient.ProcessServerSupplementalData(serverSupplementalData); - this.mConnectionState = CS_SERVER_SUPPLEMENTAL_DATA; - - this.mKeyExchange = mTlsClient.GetKeyExchange(); - this.mKeyExchange.Init(Context); - } - - protected virtual void ReceiveNewSessionTicketMessage(MemoryStream buf) - { - NewSessionTicket newSessionTicket = NewSessionTicket.Parse(buf); - - AssertEmpty(buf); - - mTlsClient.NotifyNewSessionTicket(newSessionTicket); - } - - protected virtual void ReceiveServerHelloMessage(MemoryStream buf) - { - { - ProtocolVersion server_version = TlsUtilities.ReadVersion(buf); - if (server_version.IsDtls) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - - // Check that this matches what the server is Sending in the record layer - if (!server_version.Equals(this.mRecordStream.ReadVersion)) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - - ProtocolVersion client_version = Context.ClientVersion; - if (!server_version.IsEqualOrEarlierVersionOf(client_version)) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - - this.mRecordStream.SetWriteVersion(server_version); - ContextAdmin.SetServerVersion(server_version); - this.mTlsClient.NotifyServerVersion(server_version); - } - - /* - * Read the server random - */ - this.mSecurityParameters.serverRandom = TlsUtilities.ReadFully(32, buf); - - this.mSelectedSessionID = TlsUtilities.ReadOpaque8(buf); - if (this.mSelectedSessionID.Length > 32) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - this.mTlsClient.NotifySessionID(this.mSelectedSessionID); - this.mResumedSession = this.mSelectedSessionID.Length > 0 && this.mTlsSession != null - && Arrays.AreEqual(this.mSelectedSessionID, this.mTlsSession.SessionID); - - /* - * Find out which CipherSuite the server has chosen and check that it was one of the offered - * ones, and is a valid selection for the negotiated version. - */ - int selectedCipherSuite = TlsUtilities.ReadUint16(buf); - if (!Arrays.Contains(this.mOfferedCipherSuites, selectedCipherSuite) - || selectedCipherSuite == CipherSuite.TLS_NULL_WITH_NULL_NULL - || CipherSuite.IsScsv(selectedCipherSuite) - || !TlsUtilities.IsValidCipherSuiteForVersion(selectedCipherSuite, Context.ServerVersion)) - { - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - this.mTlsClient.NotifySelectedCipherSuite(selectedCipherSuite); - - /* - * Find out which CompressionMethod the server has chosen and check that it was one of the - * offered ones. - */ - byte selectedCompressionMethod = TlsUtilities.ReadUint8(buf); - if (!Arrays.Contains(this.mOfferedCompressionMethods, selectedCompressionMethod)) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - this.mTlsClient.NotifySelectedCompressionMethod(selectedCompressionMethod); - - /* - * RFC 3546 2.2 The extended server hello message format MAY be sent in place of the server - * hello message when the client has requested extended functionality via the extended - * client hello message specified in Section 2.1. ... Note that the extended server hello - * message is only sent in response to an extended client hello message. This prevents the - * possibility that the extended server hello message could "break" existing TLS 1.0 - * clients. - */ - this.mServerExtensions = ReadExtensions(buf); - - /* - * RFC 7627 4. Clients and servers SHOULD NOT accept handshakes that do not use the extended - * master secret [..]. (and see 5.2, 5.3) - */ - this.mSecurityParameters.extendedMasterSecret = !TlsUtilities.IsSsl(mTlsClientContext) - && TlsExtensionsUtilities.HasExtendedMasterSecretExtension(mServerExtensions); - - if (!mSecurityParameters.IsExtendedMasterSecret - && (mResumedSession || mTlsClient.RequiresExtendedMasterSecret())) - { - throw new TlsFatalAlert(AlertDescription.handshake_failure); - } - - /* - * RFC 3546 2.2 Note that the extended server hello message is only sent in response to an - * extended client hello message. - * - * However, see RFC 5746 exception below. We always include the SCSV, so an Extended Server - * Hello is always allowed. - */ - if (this.mServerExtensions != null) - { - foreach (int extType in this.mServerExtensions.Keys) - { - /* - * RFC 5746 3.6. Note that Sending a "renegotiation_info" extension in response to a - * ClientHello containing only the SCSV is an explicit exception to the prohibition - * in RFC 5246, Section 7.4.1.4, on the server Sending unsolicited extensions and is - * only allowed because the client is signaling its willingness to receive the - * extension via the TLS_EMPTY_RENEGOTIATION_INFO_SCSV SCSV. - */ - if (extType == ExtensionType.renegotiation_info) - continue; - - /* - * RFC 5246 7.4.1.4 An extension type MUST NOT appear in the ServerHello unless the - * same extension type appeared in the corresponding ClientHello. If a client - * receives an extension type in ServerHello that it did not request in the - * associated ClientHello, it MUST abort the handshake with an unsupported_extension - * fatal alert. - */ - if (null == TlsUtilities.GetExtensionData(this.mClientExtensions, extType)) - throw new TlsFatalAlert(AlertDescription.unsupported_extension); - - /* - * RFC 3546 2.3. If [...] the older session is resumed, then the server MUST ignore - * extensions appearing in the client hello, and Send a server hello containing no - * extensions[.] - */ - if (this.mResumedSession) - { - // TODO[compat-gnutls] GnuTLS test server Sends server extensions e.g. ec_point_formats - // TODO[compat-openssl] OpenSSL test server Sends server extensions e.g. ec_point_formats - // TODO[compat-polarssl] PolarSSL test server Sends server extensions e.g. ec_point_formats - // throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - } - } - - /* - * RFC 5746 3.4. Client Behavior: Initial Handshake - */ - { - /* - * When a ServerHello is received, the client MUST check if it includes the - * "renegotiation_info" extension: - */ - byte[] renegExtData = TlsUtilities.GetExtensionData(this.mServerExtensions, ExtensionType.renegotiation_info); - if (renegExtData != null) - { - /* - * If the extension is present, set the secure_renegotiation flag to TRUE. The - * client MUST then verify that the length of the "renegotiated_connection" - * field is zero, and if it is not, MUST abort the handshake (by Sending a fatal - * handshake_failure alert). - */ - this.mSecureRenegotiation = true; - - if (!Arrays.ConstantTimeAreEqual(renegExtData, CreateRenegotiationInfo(TlsUtilities.EmptyBytes))) - throw new TlsFatalAlert(AlertDescription.handshake_failure); - } - } - - // TODO[compat-gnutls] GnuTLS test server fails to Send renegotiation_info extension when resuming - this.mTlsClient.NotifySecureRenegotiation(this.mSecureRenegotiation); - - IDictionary sessionClientExtensions = mClientExtensions, sessionServerExtensions = mServerExtensions; - if (this.mResumedSession) - { - if (selectedCipherSuite != this.mSessionParameters.CipherSuite - || selectedCompressionMethod != this.mSessionParameters.CompressionAlgorithm) - { - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - - sessionClientExtensions = null; - sessionServerExtensions = this.mSessionParameters.ReadServerExtensions(); - } - - this.mSecurityParameters.cipherSuite = selectedCipherSuite; - this.mSecurityParameters.compressionAlgorithm = selectedCompressionMethod; - - if (sessionServerExtensions != null && sessionServerExtensions.Count > 0) - { - { - /* - * RFC 7366 3. If a server receives an encrypt-then-MAC request extension from a client - * and then selects a stream or Authenticated Encryption with Associated Data (AEAD) - * ciphersuite, it MUST NOT send an encrypt-then-MAC response extension back to the - * client. - */ - bool serverSentEncryptThenMAC = TlsExtensionsUtilities.HasEncryptThenMacExtension(sessionServerExtensions); - if (serverSentEncryptThenMAC && !TlsUtilities.IsBlockCipherSuite(selectedCipherSuite)) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - - this.mSecurityParameters.encryptThenMac = serverSentEncryptThenMAC; - } - - this.mSecurityParameters.maxFragmentLength = ProcessMaxFragmentLengthExtension(sessionClientExtensions, - sessionServerExtensions, AlertDescription.illegal_parameter); - - this.mSecurityParameters.truncatedHMac = TlsExtensionsUtilities.HasTruncatedHMacExtension(sessionServerExtensions); - - /* - * TODO It's surprising that there's no provision to allow a 'fresh' CertificateStatus to be sent in - * a session resumption handshake. - */ - this.mAllowCertificateStatus = !this.mResumedSession - && TlsUtilities.HasExpectedEmptyExtensionData(sessionServerExtensions, ExtensionType.status_request, - AlertDescription.illegal_parameter); - - this.mExpectSessionTicket = !this.mResumedSession - && TlsUtilities.HasExpectedEmptyExtensionData(sessionServerExtensions, ExtensionType.session_ticket, - AlertDescription.illegal_parameter); - } - - if (sessionClientExtensions != null) - { - this.mTlsClient.ProcessServerExtensions(sessionServerExtensions); - } - - this.mSecurityParameters.prfAlgorithm = GetPrfAlgorithm(Context, this.mSecurityParameters.CipherSuite); - - /* - * RFC 5246 7.4.9. Any cipher suite which does not explicitly specify - * verify_data_length has a verify_data_length equal to 12. This includes all - * existing cipher suites. - */ - this.mSecurityParameters.verifyDataLength = 12; - } - - protected virtual void SendCertificateVerifyMessage(DigitallySigned certificateVerify) - { - HandshakeMessage message = new HandshakeMessage(HandshakeType.certificate_verify); - - certificateVerify.Encode(message); - - message.WriteToRecordStream(this); - } - - protected virtual void SendClientHelloMessage() - { - this.mRecordStream.SetWriteVersion(this.mTlsClient.ClientHelloRecordLayerVersion); - - ProtocolVersion client_version = this.mTlsClient.ClientVersion; - if (client_version.IsDtls) - throw new TlsFatalAlert(AlertDescription.internal_error); - - ContextAdmin.SetClientVersion(client_version); - - /* - * TODO RFC 5077 3.4. When presenting a ticket, the client MAY generate and include a - * Session ID in the TLS ClientHello. - */ - byte[] session_id = TlsUtilities.EmptyBytes; - if (this.mTlsSession != null) - { - session_id = this.mTlsSession.SessionID; - if (session_id == null || session_id.Length > 32) - { - session_id = TlsUtilities.EmptyBytes; - } - } - - bool fallback = this.mTlsClient.IsFallback; - - this.mOfferedCipherSuites = this.mTlsClient.GetCipherSuites(); - - this.mOfferedCompressionMethods = this.mTlsClient.GetCompressionMethods(); - - if (session_id.Length > 0 && this.mSessionParameters != null) - { - if (!mSessionParameters.IsExtendedMasterSecret - || !Arrays.Contains(this.mOfferedCipherSuites, mSessionParameters.CipherSuite) - || !Arrays.Contains(this.mOfferedCompressionMethods, mSessionParameters.CompressionAlgorithm)) - { - session_id = TlsUtilities.EmptyBytes; - } - } - - this.mClientExtensions = TlsExtensionsUtilities.EnsureExtensionsInitialised(this.mTlsClient.GetClientExtensions()); - - if (!client_version.IsSsl) - { - TlsExtensionsUtilities.AddExtendedMasterSecretExtension(this.mClientExtensions); - } - - HandshakeMessage message = new HandshakeMessage(HandshakeType.client_hello); - - TlsUtilities.WriteVersion(client_version, message); - - message.Write(this.mSecurityParameters.ClientRandom); - - TlsUtilities.WriteOpaque8(session_id, message); - - // Cipher Suites (and SCSV) - { - /* - * RFC 5746 3.4. The client MUST include either an empty "renegotiation_info" extension, - * or the TLS_EMPTY_RENEGOTIATION_INFO_SCSV signaling cipher suite value in the - * ClientHello. Including both is NOT RECOMMENDED. - */ - byte[] renegExtData = TlsUtilities.GetExtensionData(mClientExtensions, ExtensionType.renegotiation_info); - bool noRenegExt = (null == renegExtData); - - bool noRenegScsv = !Arrays.Contains(mOfferedCipherSuites, CipherSuite.TLS_EMPTY_RENEGOTIATION_INFO_SCSV); - - if (noRenegExt && noRenegScsv) - { - // TODO Consider whether to default to a client extension instead - this.mOfferedCipherSuites = Arrays.Append(mOfferedCipherSuites, CipherSuite.TLS_EMPTY_RENEGOTIATION_INFO_SCSV); - } - - /* - * RFC 7507 4. If a client sends a ClientHello.client_version containing a lower value - * than the latest (highest-valued) version supported by the client, it SHOULD include - * the TLS_FALLBACK_SCSV cipher suite value in ClientHello.cipher_suites [..]. (The - * client SHOULD put TLS_FALLBACK_SCSV after all cipher suites that it actually intends - * to negotiate.) - */ - if (fallback && !Arrays.Contains(mOfferedCipherSuites, CipherSuite.TLS_FALLBACK_SCSV)) - { - this.mOfferedCipherSuites = Arrays.Append(mOfferedCipherSuites, CipherSuite.TLS_FALLBACK_SCSV); - } - - TlsUtilities.WriteUint16ArrayWithUint16Length(mOfferedCipherSuites, message); - } - - TlsUtilities.WriteUint8ArrayWithUint8Length(mOfferedCompressionMethods, message); - - WriteExtensions(message, mClientExtensions); - - message.WriteToRecordStream(this); - } - - protected virtual void SendClientKeyExchangeMessage() - { - HandshakeMessage message = new HandshakeMessage(HandshakeType.client_key_exchange); - - this.mKeyExchange.GenerateClientKeyExchange(message); - - message.WriteToRecordStream(this); - } - } -} diff --git a/crypto/src/crypto/tls/TlsCloseable.cs b/crypto/src/crypto/tls/TlsCloseable.cs deleted file mode 100644 index 01625d7a0..000000000 --- a/crypto/src/crypto/tls/TlsCloseable.cs +++ /dev/null @@ -1,11 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public interface TlsCloseable - { - /// <exception cref="IOException"/> - void Close(); - } -} diff --git a/crypto/src/crypto/tls/TlsCompression.cs b/crypto/src/crypto/tls/TlsCompression.cs deleted file mode 100644 index 177d64b7e..000000000 --- a/crypto/src/crypto/tls/TlsCompression.cs +++ /dev/null @@ -1,12 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public interface TlsCompression - { - Stream Compress(Stream output); - - Stream Decompress(Stream output); - } -} diff --git a/crypto/src/crypto/tls/TlsContext.cs b/crypto/src/crypto/tls/TlsContext.cs deleted file mode 100644 index d066723fc..000000000 --- a/crypto/src/crypto/tls/TlsContext.cs +++ /dev/null @@ -1,45 +0,0 @@ -using System; - -using Org.BouncyCastle.Crypto.Prng; -using Org.BouncyCastle.Security; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public interface TlsContext - { - IRandomGenerator NonceRandomGenerator { get; } - - SecureRandom SecureRandom { get; } - - SecurityParameters SecurityParameters { get; } - - bool IsServer { get; } - - ProtocolVersion ClientVersion { get; } - - ProtocolVersion ServerVersion { get; } - - /** - * Used to get the resumable session, if any, used by this connection. Only available after the - * handshake has successfully completed. - * - * @return A {@link TlsSession} representing the resumable session used by this connection, or - * null if no resumable session available. - * @see TlsPeer#NotifyHandshakeComplete() - */ - TlsSession ResumableSession { get; } - - object UserObject { get; set; } - - /** - * Export keying material according to RFC 5705: "Keying Material Exporters for TLS". - * - * @param asciiLabel indicates which application will use the exported keys. - * @param context_value allows the application using the exporter to mix its own data with the TLS PRF for - * the exporter output. - * @param length the number of bytes to generate - * @return a pseudorandom bit string of 'length' bytes generated from the master_secret. - */ - byte[] ExportKeyingMaterial(string asciiLabel, byte[] context_value, int length); - } -} diff --git a/crypto/src/crypto/tls/TlsCredentials.cs b/crypto/src/crypto/tls/TlsCredentials.cs deleted file mode 100644 index 5c5f1c02e..000000000 --- a/crypto/src/crypto/tls/TlsCredentials.cs +++ /dev/null @@ -1,9 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public interface TlsCredentials - { - Certificate Certificate { get; } - } -} diff --git a/crypto/src/crypto/tls/TlsDHKeyExchange.cs b/crypto/src/crypto/tls/TlsDHKeyExchange.cs deleted file mode 100644 index 63abe27ce..000000000 --- a/crypto/src/crypto/tls/TlsDHKeyExchange.cs +++ /dev/null @@ -1,249 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Asn1.X509; -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Security; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary>(D)TLS DH key exchange.</summary> - public class TlsDHKeyExchange - : AbstractTlsKeyExchange - { - protected TlsSigner mTlsSigner; - protected TlsDHVerifier mDHVerifier; - protected DHParameters mDHParameters; - - protected AsymmetricKeyParameter mServerPublicKey; - protected TlsAgreementCredentials mAgreementCredentials; - - protected DHPrivateKeyParameters mDHAgreePrivateKey; - protected DHPublicKeyParameters mDHAgreePublicKey; - - [Obsolete("Use constructor that takes a TlsDHVerifier")] - public TlsDHKeyExchange(int keyExchange, IList supportedSignatureAlgorithms, DHParameters dhParameters) - : this(keyExchange, supportedSignatureAlgorithms, new DefaultTlsDHVerifier(), dhParameters) - { - } - - public TlsDHKeyExchange(int keyExchange, IList supportedSignatureAlgorithms, TlsDHVerifier dhVerifier, DHParameters dhParameters) - : base(keyExchange, supportedSignatureAlgorithms) - { - switch (keyExchange) - { - case KeyExchangeAlgorithm.DH_anon: - case KeyExchangeAlgorithm.DH_RSA: - case KeyExchangeAlgorithm.DH_DSS: - this.mTlsSigner = null; - break; - case KeyExchangeAlgorithm.DHE_RSA: - this.mTlsSigner = new TlsRsaSigner(); - break; - case KeyExchangeAlgorithm.DHE_DSS: - this.mTlsSigner = new TlsDssSigner(); - break; - default: - throw new InvalidOperationException("unsupported key exchange algorithm"); - } - - this.mDHVerifier = dhVerifier; - this.mDHParameters = dhParameters; - } - - public override void Init(TlsContext context) - { - base.Init(context); - - if (this.mTlsSigner != null) - { - this.mTlsSigner.Init(context); - } - } - - public override void SkipServerCredentials() - { - if (mKeyExchange != KeyExchangeAlgorithm.DH_anon) - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - - public override void ProcessServerCertificate(Certificate serverCertificate) - { - if (mKeyExchange == KeyExchangeAlgorithm.DH_anon) - throw new TlsFatalAlert(AlertDescription.unexpected_message); - if (serverCertificate.IsEmpty) - throw new TlsFatalAlert(AlertDescription.decode_error); - - X509CertificateStructure x509Cert = serverCertificate.GetCertificateAt(0); - - SubjectPublicKeyInfo keyInfo = x509Cert.SubjectPublicKeyInfo; - try - { - this.mServerPublicKey = PublicKeyFactory.CreateKey(keyInfo); - } - catch (Exception e) - { - throw new TlsFatalAlert(AlertDescription.unsupported_certificate, e); - } - - if (mTlsSigner == null) - { - try - { - this.mDHAgreePublicKey = (DHPublicKeyParameters)this.mServerPublicKey; - this.mDHParameters = mDHAgreePublicKey.Parameters; - } - catch (InvalidCastException e) - { - throw new TlsFatalAlert(AlertDescription.certificate_unknown, e); - } - - TlsUtilities.ValidateKeyUsage(x509Cert, KeyUsage.KeyAgreement); - } - else - { - if (!mTlsSigner.IsValidPublicKey(this.mServerPublicKey)) - { - throw new TlsFatalAlert(AlertDescription.certificate_unknown); - } - - TlsUtilities.ValidateKeyUsage(x509Cert, KeyUsage.DigitalSignature); - } - - base.ProcessServerCertificate(serverCertificate); - } - - public override bool RequiresServerKeyExchange - { - get - { - switch (mKeyExchange) - { - case KeyExchangeAlgorithm.DH_anon: - case KeyExchangeAlgorithm.DHE_DSS: - case KeyExchangeAlgorithm.DHE_RSA: - return true; - default: - return false; - } - } - } - - public override byte[] GenerateServerKeyExchange() - { - if (!RequiresServerKeyExchange) - return null; - - // DH_anon is handled here, DHE_* in a subclass - - MemoryStream buf = new MemoryStream(); - this.mDHAgreePrivateKey = TlsDHUtilities.GenerateEphemeralServerKeyExchange(mContext.SecureRandom, - this.mDHParameters, buf); - return buf.ToArray(); - } - - public override void ProcessServerKeyExchange(Stream input) - { - if (!RequiresServerKeyExchange) - throw new TlsFatalAlert(AlertDescription.unexpected_message); - - // DH_anon is handled here, DHE_* in a subclass - - this.mDHParameters = TlsDHUtilities.ReceiveDHParameters(mDHVerifier, input); - this.mDHAgreePublicKey = new DHPublicKeyParameters(TlsDHUtilities.ReadDHParameter(input), mDHParameters); - } - - public override void ValidateCertificateRequest(CertificateRequest certificateRequest) - { - if (mKeyExchange == KeyExchangeAlgorithm.DH_anon) - throw new TlsFatalAlert(AlertDescription.handshake_failure); - - byte[] types = certificateRequest.CertificateTypes; - for (int i = 0; i < types.Length; ++i) - { - switch (types[i]) - { - case ClientCertificateType.rsa_sign: - case ClientCertificateType.dss_sign: - case ClientCertificateType.rsa_fixed_dh: - case ClientCertificateType.dss_fixed_dh: - case ClientCertificateType.ecdsa_sign: - break; - default: - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - } - } - - public override void ProcessClientCredentials(TlsCredentials clientCredentials) - { - if (mKeyExchange == KeyExchangeAlgorithm.DH_anon) - throw new TlsFatalAlert(AlertDescription.internal_error); - - if (clientCredentials is TlsAgreementCredentials) - { - // TODO Validate client cert has matching parameters (see 'areCompatibleParameters')? - - this.mAgreementCredentials = (TlsAgreementCredentials)clientCredentials; - } - else if (clientCredentials is TlsSignerCredentials) - { - // OK - } - else - { - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } - - public override void GenerateClientKeyExchange(Stream output) - { - /* - * RFC 2246 7.4.7.2 If the client certificate already contains a suitable Diffie-Hellman - * key, then Yc is implicit and does not need to be sent again. In this case, the Client Key - * Exchange message will be sent, but will be empty. - */ - if (mAgreementCredentials == null) - { - this.mDHAgreePrivateKey = TlsDHUtilities.GenerateEphemeralClientKeyExchange(mContext.SecureRandom, - mDHParameters, output); - } - } - - public override void ProcessClientCertificate(Certificate clientCertificate) - { - if (mKeyExchange == KeyExchangeAlgorithm.DH_anon) - throw new TlsFatalAlert(AlertDescription.unexpected_message); - - // TODO Extract the public key - // TODO If the certificate is 'fixed', take the public key as dhAgreePublicKey - } - - public override void ProcessClientKeyExchange(Stream input) - { - if (mDHAgreePublicKey != null) - { - // For dss_fixed_dh and rsa_fixed_dh, the key arrived in the client certificate - return; - } - - this.mDHAgreePublicKey = new DHPublicKeyParameters(TlsDHUtilities.ReadDHParameter(input), mDHParameters); - } - - public override byte[] GeneratePremasterSecret() - { - if (mAgreementCredentials != null) - { - return mAgreementCredentials.GenerateAgreement(mDHAgreePublicKey); - } - - if (mDHAgreePrivateKey != null) - { - return TlsDHUtilities.CalculateDHBasicAgreement(mDHAgreePublicKey, mDHAgreePrivateKey); - } - - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } -} diff --git a/crypto/src/crypto/tls/TlsDHUtilities.cs b/crypto/src/crypto/tls/TlsDHUtilities.cs deleted file mode 100644 index fb521336e..000000000 --- a/crypto/src/crypto/tls/TlsDHUtilities.cs +++ /dev/null @@ -1,470 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Crypto.Agreement; -using Org.BouncyCastle.Crypto.Generators; -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Math; -using Org.BouncyCastle.Security; -using Org.BouncyCastle.Utilities; -using Org.BouncyCastle.Utilities.Encoders; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class TlsDHUtilities - { - internal static readonly BigInteger Two = BigInteger.Two; - - /* - * TODO[draft-ietf-tls-negotiated-ff-dhe-01] Move these groups to DHStandardGroups once reaches RFC - */ - private static BigInteger FromHex(String hex) - { - return new BigInteger(1, Hex.DecodeStrict(hex)); - } - - private static DHParameters FromSafeP(String hexP) - { - BigInteger p = FromHex(hexP), q = p.ShiftRight(1); - return new DHParameters(p, Two, q); - } - - private static readonly string draft_ffdhe2432_p = - "FFFFFFFFFFFFFFFFADF85458A2BB4A9AAFDC5620273D3CF1" - + "D8B9C583CE2D3695A9E13641146433FBCC939DCE249B3EF9" - + "7D2FE363630C75D8F681B202AEC4617AD3DF1ED5D5FD6561" - + "2433F51F5F066ED0856365553DED1AF3B557135E7F57C935" - + "984F0C70E0E68B77E2A689DAF3EFE8721DF158A136ADE735" - + "30ACCA4F483A797ABC0AB182B324FB61D108A94BB2C8E3FB" - + "B96ADAB760D7F4681D4F42A3DE394DF4AE56EDE76372BB19" - + "0B07A7C8EE0A6D709E02FCE1CDF7E2ECC03404CD28342F61" - + "9172FE9CE98583FF8E4F1232EEF28183C3FE3B1B4C6FAD73" - + "3BB5FCBC2EC22005C58EF1837D1683B2C6F34A26C1B2EFFA" - + "886B4238611FCFDCDE355B3B6519035BBC34F4DEF99C0238" - + "61B46FC9D6E6C9077AD91D2691F7F7EE598CB0FAC186D91C" - + "AEFE13098533C8B3FFFFFFFFFFFFFFFF"; - internal static readonly DHParameters draft_ffdhe2432 = FromSafeP(draft_ffdhe2432_p); - - private static readonly string draft_ffdhe3072_p = - "FFFFFFFFFFFFFFFFADF85458A2BB4A9AAFDC5620273D3CF1" - + "D8B9C583CE2D3695A9E13641146433FBCC939DCE249B3EF9" - + "7D2FE363630C75D8F681B202AEC4617AD3DF1ED5D5FD6561" - + "2433F51F5F066ED0856365553DED1AF3B557135E7F57C935" - + "984F0C70E0E68B77E2A689DAF3EFE8721DF158A136ADE735" - + "30ACCA4F483A797ABC0AB182B324FB61D108A94BB2C8E3FB" - + "B96ADAB760D7F4681D4F42A3DE394DF4AE56EDE76372BB19" - + "0B07A7C8EE0A6D709E02FCE1CDF7E2ECC03404CD28342F61" - + "9172FE9CE98583FF8E4F1232EEF28183C3FE3B1B4C6FAD73" - + "3BB5FCBC2EC22005C58EF1837D1683B2C6F34A26C1B2EFFA" - + "886B4238611FCFDCDE355B3B6519035BBC34F4DEF99C0238" - + "61B46FC9D6E6C9077AD91D2691F7F7EE598CB0FAC186D91C" - + "AEFE130985139270B4130C93BC437944F4FD4452E2D74DD3" - + "64F2E21E71F54BFF5CAE82AB9C9DF69EE86D2BC522363A0D" - + "ABC521979B0DEADA1DBF9A42D5C4484E0ABCD06BFA53DDEF" - + "3C1B20EE3FD59D7C25E41D2B66C62E37FFFFFFFFFFFFFFFF"; - internal static readonly DHParameters draft_ffdhe3072 = FromSafeP(draft_ffdhe3072_p); - - private static readonly string draft_ffdhe4096_p = - "FFFFFFFFFFFFFFFFADF85458A2BB4A9AAFDC5620273D3CF1" - + "D8B9C583CE2D3695A9E13641146433FBCC939DCE249B3EF9" - + "7D2FE363630C75D8F681B202AEC4617AD3DF1ED5D5FD6561" - + "2433F51F5F066ED0856365553DED1AF3B557135E7F57C935" - + "984F0C70E0E68B77E2A689DAF3EFE8721DF158A136ADE735" - + "30ACCA4F483A797ABC0AB182B324FB61D108A94BB2C8E3FB" - + "B96ADAB760D7F4681D4F42A3DE394DF4AE56EDE76372BB19" - + "0B07A7C8EE0A6D709E02FCE1CDF7E2ECC03404CD28342F61" - + "9172FE9CE98583FF8E4F1232EEF28183C3FE3B1B4C6FAD73" - + "3BB5FCBC2EC22005C58EF1837D1683B2C6F34A26C1B2EFFA" - + "886B4238611FCFDCDE355B3B6519035BBC34F4DEF99C0238" - + "61B46FC9D6E6C9077AD91D2691F7F7EE598CB0FAC186D91C" - + "AEFE130985139270B4130C93BC437944F4FD4452E2D74DD3" - + "64F2E21E71F54BFF5CAE82AB9C9DF69EE86D2BC522363A0D" - + "ABC521979B0DEADA1DBF9A42D5C4484E0ABCD06BFA53DDEF" - + "3C1B20EE3FD59D7C25E41D2B669E1EF16E6F52C3164DF4FB" - + "7930E9E4E58857B6AC7D5F42D69F6D187763CF1D55034004" - + "87F55BA57E31CC7A7135C886EFB4318AED6A1E012D9E6832" - + "A907600A918130C46DC778F971AD0038092999A333CB8B7A" - + "1A1DB93D7140003C2A4ECEA9F98D0ACC0A8291CDCEC97DCF" - + "8EC9B55A7F88A46B4DB5A851F44182E1C68A007E5E655F6A" - + "FFFFFFFFFFFFFFFF"; - internal static readonly DHParameters draft_ffdhe4096 = FromSafeP(draft_ffdhe4096_p); - - private static readonly string draft_ffdhe6144_p = - "FFFFFFFFFFFFFFFFADF85458A2BB4A9AAFDC5620273D3CF1" - + "D8B9C583CE2D3695A9E13641146433FBCC939DCE249B3EF9" - + "7D2FE363630C75D8F681B202AEC4617AD3DF1ED5D5FD6561" - + "2433F51F5F066ED0856365553DED1AF3B557135E7F57C935" - + "984F0C70E0E68B77E2A689DAF3EFE8721DF158A136ADE735" - + "30ACCA4F483A797ABC0AB182B324FB61D108A94BB2C8E3FB" - + "B96ADAB760D7F4681D4F42A3DE394DF4AE56EDE76372BB19" - + "0B07A7C8EE0A6D709E02FCE1CDF7E2ECC03404CD28342F61" - + "9172FE9CE98583FF8E4F1232EEF28183C3FE3B1B4C6FAD73" - + "3BB5FCBC2EC22005C58EF1837D1683B2C6F34A26C1B2EFFA" - + "886B4238611FCFDCDE355B3B6519035BBC34F4DEF99C0238" - + "61B46FC9D6E6C9077AD91D2691F7F7EE598CB0FAC186D91C" - + "AEFE130985139270B4130C93BC437944F4FD4452E2D74DD3" - + "64F2E21E71F54BFF5CAE82AB9C9DF69EE86D2BC522363A0D" - + "ABC521979B0DEADA1DBF9A42D5C4484E0ABCD06BFA53DDEF" - + "3C1B20EE3FD59D7C25E41D2B669E1EF16E6F52C3164DF4FB" - + "7930E9E4E58857B6AC7D5F42D69F6D187763CF1D55034004" - + "87F55BA57E31CC7A7135C886EFB4318AED6A1E012D9E6832" - + "A907600A918130C46DC778F971AD0038092999A333CB8B7A" - + "1A1DB93D7140003C2A4ECEA9F98D0ACC0A8291CDCEC97DCF" - + "8EC9B55A7F88A46B4DB5A851F44182E1C68A007E5E0DD902" - + "0BFD64B645036C7A4E677D2C38532A3A23BA4442CAF53EA6" - + "3BB454329B7624C8917BDD64B1C0FD4CB38E8C334C701C3A" - + "CDAD0657FCCFEC719B1F5C3E4E46041F388147FB4CFDB477" - + "A52471F7A9A96910B855322EDB6340D8A00EF092350511E3" - + "0ABEC1FFF9E3A26E7FB29F8C183023C3587E38DA0077D9B4" - + "763E4E4B94B2BBC194C6651E77CAF992EEAAC0232A281BF6" - + "B3A739C1226116820AE8DB5847A67CBEF9C9091B462D538C" - + "D72B03746AE77F5E62292C311562A846505DC82DB854338A" - + "E49F5235C95B91178CCF2DD5CACEF403EC9D1810C6272B04" - + "5B3B71F9DC6B80D63FDD4A8E9ADB1E6962A69526D43161C1" - + "A41D570D7938DAD4A40E329CD0E40E65FFFFFFFFFFFFFFFF"; - internal static readonly DHParameters draft_ffdhe6144 = FromSafeP(draft_ffdhe6144_p); - - private static readonly string draft_ffdhe8192_p = - "FFFFFFFFFFFFFFFFADF85458A2BB4A9AAFDC5620273D3CF1" - + "D8B9C583CE2D3695A9E13641146433FBCC939DCE249B3EF9" - + "7D2FE363630C75D8F681B202AEC4617AD3DF1ED5D5FD6561" - + "2433F51F5F066ED0856365553DED1AF3B557135E7F57C935" - + "984F0C70E0E68B77E2A689DAF3EFE8721DF158A136ADE735" - + "30ACCA4F483A797ABC0AB182B324FB61D108A94BB2C8E3FB" - + "B96ADAB760D7F4681D4F42A3DE394DF4AE56EDE76372BB19" - + "0B07A7C8EE0A6D709E02FCE1CDF7E2ECC03404CD28342F61" - + "9172FE9CE98583FF8E4F1232EEF28183C3FE3B1B4C6FAD73" - + "3BB5FCBC2EC22005C58EF1837D1683B2C6F34A26C1B2EFFA" - + "886B4238611FCFDCDE355B3B6519035BBC34F4DEF99C0238" - + "61B46FC9D6E6C9077AD91D2691F7F7EE598CB0FAC186D91C" - + "AEFE130985139270B4130C93BC437944F4FD4452E2D74DD3" - + "64F2E21E71F54BFF5CAE82AB9C9DF69EE86D2BC522363A0D" - + "ABC521979B0DEADA1DBF9A42D5C4484E0ABCD06BFA53DDEF" - + "3C1B20EE3FD59D7C25E41D2B669E1EF16E6F52C3164DF4FB" - + "7930E9E4E58857B6AC7D5F42D69F6D187763CF1D55034004" - + "87F55BA57E31CC7A7135C886EFB4318AED6A1E012D9E6832" - + "A907600A918130C46DC778F971AD0038092999A333CB8B7A" - + "1A1DB93D7140003C2A4ECEA9F98D0ACC0A8291CDCEC97DCF" - + "8EC9B55A7F88A46B4DB5A851F44182E1C68A007E5E0DD902" - + "0BFD64B645036C7A4E677D2C38532A3A23BA4442CAF53EA6" - + "3BB454329B7624C8917BDD64B1C0FD4CB38E8C334C701C3A" - + "CDAD0657FCCFEC719B1F5C3E4E46041F388147FB4CFDB477" - + "A52471F7A9A96910B855322EDB6340D8A00EF092350511E3" - + "0ABEC1FFF9E3A26E7FB29F8C183023C3587E38DA0077D9B4" - + "763E4E4B94B2BBC194C6651E77CAF992EEAAC0232A281BF6" - + "B3A739C1226116820AE8DB5847A67CBEF9C9091B462D538C" - + "D72B03746AE77F5E62292C311562A846505DC82DB854338A" - + "E49F5235C95B91178CCF2DD5CACEF403EC9D1810C6272B04" - + "5B3B71F9DC6B80D63FDD4A8E9ADB1E6962A69526D43161C1" - + "A41D570D7938DAD4A40E329CCFF46AAA36AD004CF600C838" - + "1E425A31D951AE64FDB23FCEC9509D43687FEB69EDD1CC5E" - + "0B8CC3BDF64B10EF86B63142A3AB8829555B2F747C932665" - + "CB2C0F1CC01BD70229388839D2AF05E454504AC78B758282" - + "2846C0BA35C35F5C59160CC046FD8251541FC68C9C86B022" - + "BB7099876A460E7451A8A93109703FEE1C217E6C3826E52C" - + "51AA691E0E423CFC99E9E31650C1217B624816CDAD9A95F9" - + "D5B8019488D9C0A0A1FE3075A577E23183F81D4A3F2FA457" - + "1EFC8CE0BA8A4FE8B6855DFE72B0A66EDED2FBABFBE58A30" - + "FAFABE1C5D71A87E2F741EF8C1FE86FEA6BBFDE530677F0D" - + "97D11D49F7A8443D0822E506A9F4614E011E2A94838FF88C" - + "D68C8BB7C5C6424CFFFFFFFFFFFFFFFF"; - internal static readonly DHParameters draft_ffdhe8192 = FromSafeP(draft_ffdhe8192_p); - - - public static void AddNegotiatedDheGroupsClientExtension(IDictionary extensions, byte[] dheGroups) - { - extensions[ExtensionType.negotiated_ff_dhe_groups] = CreateNegotiatedDheGroupsClientExtension(dheGroups); - } - - public static void AddNegotiatedDheGroupsServerExtension(IDictionary extensions, byte dheGroup) - { - extensions[ExtensionType.negotiated_ff_dhe_groups] = CreateNegotiatedDheGroupsServerExtension(dheGroup); - } - - public static byte[] GetNegotiatedDheGroupsClientExtension(IDictionary extensions) - { - byte[] extensionData = TlsUtilities.GetExtensionData(extensions, ExtensionType.negotiated_ff_dhe_groups); - return extensionData == null ? null : ReadNegotiatedDheGroupsClientExtension(extensionData); - } - - public static short GetNegotiatedDheGroupsServerExtension(IDictionary extensions) - { - byte[] extensionData = TlsUtilities.GetExtensionData(extensions, ExtensionType.negotiated_ff_dhe_groups); - return extensionData == null ? (short)-1 : (short)ReadNegotiatedDheGroupsServerExtension(extensionData); - } - - public static byte[] CreateNegotiatedDheGroupsClientExtension(byte[] dheGroups) - { - if (dheGroups == null || dheGroups.Length < 1 || dheGroups.Length > 255) - throw new TlsFatalAlert(AlertDescription.internal_error); - - return TlsUtilities.EncodeUint8ArrayWithUint8Length(dheGroups); - } - - public static byte[] CreateNegotiatedDheGroupsServerExtension(byte dheGroup) - { - return TlsUtilities.EncodeUint8(dheGroup); - } - - public static byte[] ReadNegotiatedDheGroupsClientExtension(byte[] extensionData) - { - byte[] dheGroups = TlsUtilities.DecodeUint8ArrayWithUint8Length(extensionData); - if (dheGroups.Length < 1) - throw new TlsFatalAlert(AlertDescription.decode_error); - return dheGroups; - } - - public static byte ReadNegotiatedDheGroupsServerExtension(byte[] extensionData) - { - return TlsUtilities.DecodeUint8(extensionData); - } - - public static DHParameters GetParametersForDHEGroup(short dheGroup) - { - switch (dheGroup) - { - case FiniteFieldDheGroup.ffdhe2432: - return draft_ffdhe2432; - case FiniteFieldDheGroup.ffdhe3072: - return draft_ffdhe3072; - case FiniteFieldDheGroup.ffdhe4096: - return draft_ffdhe4096; - case FiniteFieldDheGroup.ffdhe6144: - return draft_ffdhe6144; - case FiniteFieldDheGroup.ffdhe8192: - return draft_ffdhe8192; - default: - return null; - } - } - - public static bool ContainsDheCipherSuites(int[] cipherSuites) - { - for (int i = 0; i < cipherSuites.Length; ++i) - { - if (IsDheCipherSuite(cipherSuites[i])) - return true; - } - return false; - } - - public static bool IsDheCipherSuite(int cipherSuite) - { - switch (cipherSuite) - { - /* - * RFC 2246 - */ - case CipherSuite.TLS_DHE_DSS_EXPORT_WITH_DES40_CBC_SHA: - case CipherSuite.TLS_DHE_DSS_WITH_DES_CBC_SHA: - case CipherSuite.TLS_DHE_DSS_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_DHE_RSA_EXPORT_WITH_DES40_CBC_SHA: - case CipherSuite.TLS_DHE_RSA_WITH_DES_CBC_SHA: - case CipherSuite.TLS_DHE_RSA_WITH_3DES_EDE_CBC_SHA: - - /* - * RFC 3268 - */ - case CipherSuite.TLS_DHE_DSS_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_DHE_DSS_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_CBC_SHA: - - /* - * RFC 5932 - */ - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_128_CBC_SHA: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_128_CBC_SHA: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_256_CBC_SHA: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_256_CBC_SHA: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_256_CBC_SHA256: - - /* - * RFC 4162 - */ - case CipherSuite.TLS_DHE_DSS_WITH_SEED_CBC_SHA: - case CipherSuite.TLS_DHE_RSA_WITH_SEED_CBC_SHA: - - /* - * RFC 4279 - */ - case CipherSuite.TLS_DHE_PSK_WITH_RC4_128_SHA: - case CipherSuite.TLS_DHE_PSK_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_DHE_PSK_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_DHE_PSK_WITH_AES_256_CBC_SHA: - - /* - * RFC 4785 - */ - case CipherSuite.TLS_DHE_PSK_WITH_NULL_SHA: - - /* - * RFC 5246 - */ - case CipherSuite.TLS_DHE_DSS_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_CBC_SHA256: - - /* - * RFC 5288 - */ - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DHE_DSS_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_AES_256_GCM_SHA384: - - /* - * RFC 5487 - */ - case CipherSuite.TLS_DHE_PSK_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DHE_PSK_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DHE_PSK_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DHE_PSK_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_DHE_PSK_WITH_NULL_SHA256: - case CipherSuite.TLS_DHE_PSK_WITH_NULL_SHA384: - - /* - * RFC 6367 - */ - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_DHE_PSK_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DHE_PSK_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_DHE_PSK_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DHE_PSK_WITH_CAMELLIA_256_CBC_SHA384: - - /* - * RFC 6655 - */ - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_CCM: - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_CCM: - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_CCM_8: - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_CCM_8: - case CipherSuite.TLS_DHE_PSK_WITH_AES_128_CCM: - case CipherSuite.TLS_DHE_PSK_WITH_AES_256_CCM: - case CipherSuite.TLS_PSK_DHE_WITH_AES_128_CCM_8: - case CipherSuite.TLS_PSK_DHE_WITH_AES_256_CCM_8: - - /* - * draft-ietf-tls-chacha20-poly1305-04 - */ - case CipherSuite.DRAFT_TLS_DHE_PSK_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.DRAFT_TLS_DHE_RSA_WITH_CHACHA20_POLY1305_SHA256: - - /* - * DH_anon cipher suites are consider ephemeral DH - */ - case CipherSuite.TLS_DH_anon_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_DH_anon_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_DH_anon_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DH_anon_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DH_anon_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_DH_anon_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_DH_anon_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_128_CBC_SHA: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_256_CBC_SHA: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_DH_anon_WITH_RC4_128_MD5: - case CipherSuite.TLS_DH_anon_WITH_SEED_CBC_SHA: - - return true; - - default: - return false; - } - } - - public static bool AreCompatibleParameters(DHParameters a, DHParameters b) - { - return a.P.Equals(b.P) && a.G.Equals(b.G) - && (a.Q == null || b.Q == null || a.Q.Equals(b.Q)); - } - - public static byte[] CalculateDHBasicAgreement(DHPublicKeyParameters publicKey, - DHPrivateKeyParameters privateKey) - { - DHBasicAgreement basicAgreement = new DHBasicAgreement(); - basicAgreement.Init(privateKey); - BigInteger agreementValue = basicAgreement.CalculateAgreement(publicKey); - - /* - * RFC 5246 8.1.2. Leading bytes of Z that contain all zero bits are stripped before it is - * used as the pre_master_secret. - */ - return BigIntegers.AsUnsignedByteArray(agreementValue); - } - - public static AsymmetricCipherKeyPair GenerateDHKeyPair(SecureRandom random, DHParameters dhParams) - { - DHBasicKeyPairGenerator dhGen = new DHBasicKeyPairGenerator(); - dhGen.Init(new DHKeyGenerationParameters(random, dhParams)); - return dhGen.GenerateKeyPair(); - } - - public static DHPrivateKeyParameters GenerateEphemeralClientKeyExchange(SecureRandom random, - DHParameters dhParams, Stream output) - { - AsymmetricCipherKeyPair kp = GenerateDHKeyPair(random, dhParams); - - DHPublicKeyParameters dhPublic = (DHPublicKeyParameters)kp.Public; - WriteDHParameter(dhPublic.Y, output); - - return (DHPrivateKeyParameters)kp.Private; - } - - public static DHPrivateKeyParameters GenerateEphemeralServerKeyExchange(SecureRandom random, - DHParameters dhParams, Stream output) - { - AsymmetricCipherKeyPair kp = GenerateDHKeyPair(random, dhParams); - - DHPublicKeyParameters dhPublic = (DHPublicKeyParameters)kp.Public; - WriteDHParameters(dhParams, output); - WriteDHParameter(dhPublic.Y, output); - - return (DHPrivateKeyParameters)kp.Private; - } - - public static BigInteger ReadDHParameter(Stream input) - { - return new BigInteger(1, TlsUtilities.ReadOpaque16(input)); - } - - public static DHParameters ReadDHParameters(Stream input) - { - BigInteger p = ReadDHParameter(input); - BigInteger g = ReadDHParameter(input); - - return new DHParameters(p, g); - } - - public static DHParameters ReceiveDHParameters(TlsDHVerifier dhVerifier, Stream input) - { - DHParameters dhParameters = ReadDHParameters(input); - if (!dhVerifier.Accept(dhParameters)) - throw new TlsFatalAlert(AlertDescription.insufficient_security); - - return dhParameters; - } - - public static void WriteDHParameter(BigInteger x, Stream output) - { - TlsUtilities.WriteOpaque16(BigIntegers.AsUnsignedByteArray(x), output); - } - - public static void WriteDHParameters(DHParameters dhParameters, Stream output) - { - WriteDHParameter(dhParameters.P, output); - WriteDHParameter(dhParameters.G, output); - } - } -} diff --git a/crypto/src/crypto/tls/TlsDHVerifier.cs b/crypto/src/crypto/tls/TlsDHVerifier.cs deleted file mode 100644 index 867403c3c..000000000 --- a/crypto/src/crypto/tls/TlsDHVerifier.cs +++ /dev/null @@ -1,15 +0,0 @@ -using System; - -using Org.BouncyCastle.Crypto.Parameters; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary>An interface for verifying that Diffie-Hellman parameters are acceptable.</summary> - public interface TlsDHVerifier - { - /// <summary>Verify that the given <c>DHParameters</c> are acceptable.</summary> - /// <param name="dhParameters">The <c>DHParameters</c> to verify.</param> - /// <returns>true if (and only if) the specified parameters are acceptable.</returns> - bool Accept(DHParameters dhParameters); - } -} diff --git a/crypto/src/crypto/tls/TlsDeflateCompression.cs b/crypto/src/crypto/tls/TlsDeflateCompression.cs deleted file mode 100644 index 9e1152908..000000000 --- a/crypto/src/crypto/tls/TlsDeflateCompression.cs +++ /dev/null @@ -1,68 +0,0 @@ -using System; -using System.IO; - -using Org.BouncyCastle.Utilities.Zlib; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class TlsDeflateCompression : TlsCompression - { - public const int LEVEL_NONE = JZlib.Z_NO_COMPRESSION; - public const int LEVEL_FASTEST = JZlib.Z_BEST_SPEED; - public const int LEVEL_SMALLEST = JZlib.Z_BEST_COMPRESSION; - public const int LEVEL_DEFAULT = JZlib.Z_DEFAULT_COMPRESSION; - - protected readonly ZStream zIn, zOut; - - public TlsDeflateCompression() - : this(LEVEL_DEFAULT) - { - } - - public TlsDeflateCompression(int level) - { - this.zIn = new ZStream(); - this.zIn.inflateInit(); - - this.zOut = new ZStream(); - this.zOut.deflateInit(level); - } - - public virtual Stream Compress(Stream output) - { - return new DeflateOutputStream(output, zOut, true); - } - - public virtual Stream Decompress(Stream output) - { - return new DeflateOutputStream(output, zIn, false); - } - - protected class DeflateOutputStream : ZOutputStream - { - public DeflateOutputStream(Stream output, ZStream z, bool compress) - : base(output, z) - { - this.compress = compress; - - /* - * See discussion at http://www.bolet.org/~pornin/deflate-flush.html . - */ - this.FlushMode = JZlib.Z_SYNC_FLUSH; - } - - public override void Flush() - { - /* - * TODO The inflateSyncPoint doesn't appear to work the way I hoped at the moment. - * In any case, we may like to accept PARTIAL_FLUSH input, not just SYNC_FLUSH. - * It's not clear how to check this in the Inflater. - */ - //if (!this.compress && (z == null || z.istate == null || z.istate.inflateSyncPoint(z) <= 0)) - //{ - // throw new TlsFatalAlert(AlertDescription.decompression_failure); - //} - } - } - } -} diff --git a/crypto/src/crypto/tls/TlsDheKeyExchange.cs b/crypto/src/crypto/tls/TlsDheKeyExchange.cs deleted file mode 100644 index 5007d7daa..000000000 --- a/crypto/src/crypto/tls/TlsDheKeyExchange.cs +++ /dev/null @@ -1,97 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Security; -using Org.BouncyCastle.Utilities.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class TlsDheKeyExchange - : TlsDHKeyExchange - { - protected TlsSignerCredentials mServerCredentials = null; - - [Obsolete("Use constructor that takes a TlsDHVerifier")] - public TlsDheKeyExchange(int keyExchange, IList supportedSignatureAlgorithms, DHParameters dhParameters) - : this(keyExchange, supportedSignatureAlgorithms, new DefaultTlsDHVerifier(), dhParameters) - { - } - - public TlsDheKeyExchange(int keyExchange, IList supportedSignatureAlgorithms, TlsDHVerifier dhVerifier, DHParameters dhParameters) - : base(keyExchange, supportedSignatureAlgorithms, dhVerifier, dhParameters) - { - } - - public override void ProcessServerCredentials(TlsCredentials serverCredentials) - { - if (!(serverCredentials is TlsSignerCredentials)) - throw new TlsFatalAlert(AlertDescription.internal_error); - - ProcessServerCertificate(serverCredentials.Certificate); - - this.mServerCredentials = (TlsSignerCredentials)serverCredentials; - } - - public override byte[] GenerateServerKeyExchange() - { - if (this.mDHParameters == null) - throw new TlsFatalAlert(AlertDescription.internal_error); - - DigestInputBuffer buf = new DigestInputBuffer(); - - this.mDHAgreePrivateKey = TlsDHUtilities.GenerateEphemeralServerKeyExchange(mContext.SecureRandom, - this.mDHParameters, buf); - - /* - * RFC 5246 4.7. digitally-signed element needs SignatureAndHashAlgorithm from TLS 1.2 - */ - SignatureAndHashAlgorithm signatureAndHashAlgorithm = TlsUtilities.GetSignatureAndHashAlgorithm( - mContext, mServerCredentials); - - IDigest d = TlsUtilities.CreateHash(signatureAndHashAlgorithm); - - SecurityParameters securityParameters = mContext.SecurityParameters; - d.BlockUpdate(securityParameters.clientRandom, 0, securityParameters.clientRandom.Length); - d.BlockUpdate(securityParameters.serverRandom, 0, securityParameters.serverRandom.Length); - buf.UpdateDigest(d); - - byte[] hash = DigestUtilities.DoFinal(d); - - byte[] signature = mServerCredentials.GenerateCertificateSignature(hash); - - DigitallySigned signed_params = new DigitallySigned(signatureAndHashAlgorithm, signature); - signed_params.Encode(buf); - - return buf.ToArray(); - } - - public override void ProcessServerKeyExchange(Stream input) - { - SecurityParameters securityParameters = mContext.SecurityParameters; - - SignerInputBuffer buf = new SignerInputBuffer(); - Stream teeIn = new TeeInputStream(input, buf); - - this.mDHParameters = TlsDHUtilities.ReceiveDHParameters(mDHVerifier, teeIn); - this.mDHAgreePublicKey = new DHPublicKeyParameters(TlsDHUtilities.ReadDHParameter(teeIn), mDHParameters); - - DigitallySigned signed_params = ParseSignature(input); - - ISigner signer = InitVerifyer(mTlsSigner, signed_params.Algorithm, securityParameters); - buf.UpdateSigner(signer); - if (!signer.VerifySignature(signed_params.Signature)) - throw new TlsFatalAlert(AlertDescription.decrypt_error); - } - - protected virtual ISigner InitVerifyer(TlsSigner tlsSigner, SignatureAndHashAlgorithm algorithm, - SecurityParameters securityParameters) - { - ISigner signer = tlsSigner.CreateVerifyer(algorithm, this.mServerPublicKey); - signer.BlockUpdate(securityParameters.clientRandom, 0, securityParameters.clientRandom.Length); - signer.BlockUpdate(securityParameters.serverRandom, 0, securityParameters.serverRandom.Length); - return signer; - } - } -} diff --git a/crypto/src/crypto/tls/TlsDsaSigner.cs b/crypto/src/crypto/tls/TlsDsaSigner.cs deleted file mode 100644 index f0c1e9451..000000000 --- a/crypto/src/crypto/tls/TlsDsaSigner.cs +++ /dev/null @@ -1,82 +0,0 @@ -using System; - -using Org.BouncyCastle.Crypto.Digests; -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Crypto.Signers; -using Org.BouncyCastle.Security; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class TlsDsaSigner - : AbstractTlsSigner - { - public override byte[] GenerateRawSignature(SignatureAndHashAlgorithm algorithm, - AsymmetricKeyParameter privateKey, byte[] hash) - { - ISigner signer = MakeSigner(algorithm, true, true, - new ParametersWithRandom(privateKey, this.mContext.SecureRandom)); - if (algorithm == null) - { - // Note: Only use the SHA1 part of the (MD5/SHA1) hash - signer.BlockUpdate(hash, 16, 20); - } - else - { - signer.BlockUpdate(hash, 0, hash.Length); - } - return signer.GenerateSignature(); - } - - public override bool VerifyRawSignature(SignatureAndHashAlgorithm algorithm, byte[] sigBytes, - AsymmetricKeyParameter publicKey, byte[] hash) - { - ISigner signer = MakeSigner(algorithm, true, false, publicKey); - if (algorithm == null) - { - // Note: Only use the SHA1 part of the (MD5/SHA1) hash - signer.BlockUpdate(hash, 16, 20); - } - else - { - signer.BlockUpdate(hash, 0, hash.Length); - } - return signer.VerifySignature(sigBytes); - } - - public override ISigner CreateSigner(SignatureAndHashAlgorithm algorithm, AsymmetricKeyParameter privateKey) - { - return MakeSigner(algorithm, false, true, privateKey); - } - - public override ISigner CreateVerifyer(SignatureAndHashAlgorithm algorithm, AsymmetricKeyParameter publicKey) - { - return MakeSigner(algorithm, false, false, publicKey); - } - - protected virtual ICipherParameters MakeInitParameters(bool forSigning, ICipherParameters cp) - { - return cp; - } - - protected virtual ISigner MakeSigner(SignatureAndHashAlgorithm algorithm, bool raw, bool forSigning, - ICipherParameters cp) - { - if ((algorithm != null) != TlsUtilities.IsTlsV12(mContext)) - throw new InvalidOperationException(); - - if (algorithm != null && algorithm.Signature != SignatureAlgorithm) - throw new InvalidOperationException(); - - byte hashAlgorithm = algorithm == null ? HashAlgorithm.sha1 : algorithm.Hash; - IDigest d = raw ? new NullDigest() : TlsUtilities.CreateHash(hashAlgorithm); - - ISigner s = new DsaDigestSigner(CreateDsaImpl(hashAlgorithm), d); - s.Init(forSigning, MakeInitParameters(forSigning, cp)); - return s; - } - - protected abstract byte SignatureAlgorithm { get; } - - protected abstract IDsa CreateDsaImpl(byte hashAlgorithm); - } -} diff --git a/crypto/src/crypto/tls/TlsDssSigner.cs b/crypto/src/crypto/tls/TlsDssSigner.cs deleted file mode 100644 index 707ef3853..000000000 --- a/crypto/src/crypto/tls/TlsDssSigner.cs +++ /dev/null @@ -1,26 +0,0 @@ -using System; - -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Crypto.Signers; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class TlsDssSigner - : TlsDsaSigner - { - public override bool IsValidPublicKey(AsymmetricKeyParameter publicKey) - { - return publicKey is DsaPublicKeyParameters; - } - - protected override IDsa CreateDsaImpl(byte hashAlgorithm) - { - return new DsaSigner(new HMacDsaKCalculator(TlsUtilities.CreateHash(hashAlgorithm))); - } - - protected override byte SignatureAlgorithm - { - get { return Tls.SignatureAlgorithm.dsa; } - } - } -} diff --git a/crypto/src/crypto/tls/TlsECDHKeyExchange.cs b/crypto/src/crypto/tls/TlsECDHKeyExchange.cs deleted file mode 100644 index 44fd94cbd..000000000 --- a/crypto/src/crypto/tls/TlsECDHKeyExchange.cs +++ /dev/null @@ -1,252 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Asn1.X509; -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Security; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary>(D)TLS ECDH key exchange (see RFC 4492).</summary> - public class TlsECDHKeyExchange - : AbstractTlsKeyExchange - { - protected TlsSigner mTlsSigner; - protected int[] mNamedCurves; - protected byte[] mClientECPointFormats, mServerECPointFormats; - - protected AsymmetricKeyParameter mServerPublicKey; - protected TlsAgreementCredentials mAgreementCredentials; - - protected ECPrivateKeyParameters mECAgreePrivateKey; - protected ECPublicKeyParameters mECAgreePublicKey; - - public TlsECDHKeyExchange(int keyExchange, IList supportedSignatureAlgorithms, int[] namedCurves, - byte[] clientECPointFormats, byte[] serverECPointFormats) - : base(keyExchange, supportedSignatureAlgorithms) - { - switch (keyExchange) - { - case KeyExchangeAlgorithm.ECDHE_RSA: - this.mTlsSigner = new TlsRsaSigner(); - break; - case KeyExchangeAlgorithm.ECDHE_ECDSA: - this.mTlsSigner = new TlsECDsaSigner(); - break; - case KeyExchangeAlgorithm.ECDH_anon: - case KeyExchangeAlgorithm.ECDH_RSA: - case KeyExchangeAlgorithm.ECDH_ECDSA: - this.mTlsSigner = null; - break; - default: - throw new InvalidOperationException("unsupported key exchange algorithm"); - } - - this.mNamedCurves = namedCurves; - this.mClientECPointFormats = clientECPointFormats; - this.mServerECPointFormats = serverECPointFormats; - } - - public override void Init(TlsContext context) - { - base.Init(context); - - if (this.mTlsSigner != null) - { - this.mTlsSigner.Init(context); - } - } - - public override void SkipServerCredentials() - { - if (mKeyExchange != KeyExchangeAlgorithm.ECDH_anon) - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - - public override void ProcessServerCertificate(Certificate serverCertificate) - { - if (mKeyExchange == KeyExchangeAlgorithm.ECDH_anon) - throw new TlsFatalAlert(AlertDescription.unexpected_message); - if (serverCertificate.IsEmpty) - throw new TlsFatalAlert(AlertDescription.decode_error); - - X509CertificateStructure x509Cert = serverCertificate.GetCertificateAt(0); - - SubjectPublicKeyInfo keyInfo = x509Cert.SubjectPublicKeyInfo; - try - { - this.mServerPublicKey = PublicKeyFactory.CreateKey(keyInfo); - } - catch (Exception e) - { - throw new TlsFatalAlert(AlertDescription.unsupported_certificate, e); - } - - if (mTlsSigner == null) - { - try - { - this.mECAgreePublicKey = TlsEccUtilities.ValidateECPublicKey((ECPublicKeyParameters) this.mServerPublicKey); - } - catch (InvalidCastException e) - { - throw new TlsFatalAlert(AlertDescription.certificate_unknown, e); - } - - TlsUtilities.ValidateKeyUsage(x509Cert, KeyUsage.KeyAgreement); - } - else - { - if (!mTlsSigner.IsValidPublicKey(this.mServerPublicKey)) - throw new TlsFatalAlert(AlertDescription.certificate_unknown); - - TlsUtilities.ValidateKeyUsage(x509Cert, KeyUsage.DigitalSignature); - } - - base.ProcessServerCertificate(serverCertificate); - } - - public override bool RequiresServerKeyExchange - { - get - { - switch (mKeyExchange) - { - case KeyExchangeAlgorithm.ECDH_anon: - case KeyExchangeAlgorithm.ECDHE_ECDSA: - case KeyExchangeAlgorithm.ECDHE_RSA: - return true; - default: - return false; - } - } - } - - public override byte[] GenerateServerKeyExchange() - { - if (!RequiresServerKeyExchange) - return null; - - // ECDH_anon is handled here, ECDHE_* in a subclass - - MemoryStream buf = new MemoryStream(); - this.mECAgreePrivateKey = TlsEccUtilities.GenerateEphemeralServerKeyExchange(mContext.SecureRandom, mNamedCurves, - mClientECPointFormats, buf); - return buf.ToArray(); - } - - public override void ProcessServerKeyExchange(Stream input) - { - if (!RequiresServerKeyExchange) - throw new TlsFatalAlert(AlertDescription.unexpected_message); - - // ECDH_anon is handled here, ECDHE_* in a subclass - - ECDomainParameters curve_params = TlsEccUtilities.ReadECParameters(mNamedCurves, mClientECPointFormats, input); - - byte[] point = TlsUtilities.ReadOpaque8(input); - - this.mECAgreePublicKey = TlsEccUtilities.ValidateECPublicKey(TlsEccUtilities.DeserializeECPublicKey( - mClientECPointFormats, curve_params, point)); - } - - public override void ValidateCertificateRequest(CertificateRequest certificateRequest) - { - if (mKeyExchange == KeyExchangeAlgorithm.ECDH_anon) - throw new TlsFatalAlert(AlertDescription.handshake_failure); - - /* - * RFC 4492 3. [...] The ECDSA_fixed_ECDH and RSA_fixed_ECDH mechanisms are usable with - * ECDH_ECDSA and ECDH_RSA. Their use with ECDHE_ECDSA and ECDHE_RSA is prohibited because - * the use of a long-term ECDH client key would jeopardize the forward secrecy property of - * these algorithms. - */ - byte[] types = certificateRequest.CertificateTypes; - for (int i = 0; i < types.Length; ++i) - { - switch (types[i]) - { - case ClientCertificateType.rsa_sign: - case ClientCertificateType.dss_sign: - case ClientCertificateType.ecdsa_sign: - case ClientCertificateType.rsa_fixed_ecdh: - case ClientCertificateType.ecdsa_fixed_ecdh: - break; - default: - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - } - } - - public override void ProcessClientCredentials(TlsCredentials clientCredentials) - { - if (mKeyExchange == KeyExchangeAlgorithm.ECDH_anon) - throw new TlsFatalAlert(AlertDescription.internal_error); - - if (clientCredentials is TlsAgreementCredentials) - { - // TODO Validate client cert has matching parameters (see 'TlsEccUtilities.AreOnSameCurve')? - - this.mAgreementCredentials = (TlsAgreementCredentials)clientCredentials; - } - else if (clientCredentials is TlsSignerCredentials) - { - // OK - } - else - { - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } - - public override void GenerateClientKeyExchange(Stream output) - { - if (mAgreementCredentials == null) - { - this.mECAgreePrivateKey = TlsEccUtilities.GenerateEphemeralClientKeyExchange(mContext.SecureRandom, - mServerECPointFormats, mECAgreePublicKey.Parameters, output); - } - } - - public override void ProcessClientCertificate(Certificate clientCertificate) - { - if (mKeyExchange == KeyExchangeAlgorithm.ECDH_anon) - throw new TlsFatalAlert(AlertDescription.unexpected_message); - - // TODO Extract the public key - // TODO If the certificate is 'fixed', take the public key as mECAgreeClientPublicKey - } - - public override void ProcessClientKeyExchange(Stream input) - { - if (mECAgreePublicKey != null) - { - // For ecdsa_fixed_ecdh and rsa_fixed_ecdh, the key arrived in the client certificate - return; - } - - byte[] point = TlsUtilities.ReadOpaque8(input); - - ECDomainParameters curve_params = this.mECAgreePrivateKey.Parameters; - - this.mECAgreePublicKey = TlsEccUtilities.ValidateECPublicKey(TlsEccUtilities.DeserializeECPublicKey( - mServerECPointFormats, curve_params, point)); - } - - public override byte[] GeneratePremasterSecret() - { - if (mAgreementCredentials != null) - { - return mAgreementCredentials.GenerateAgreement(mECAgreePublicKey); - } - - if (mECAgreePrivateKey != null) - { - return TlsEccUtilities.CalculateECDHBasicAgreement(mECAgreePublicKey, mECAgreePrivateKey); - } - - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } -} diff --git a/crypto/src/crypto/tls/TlsECDheKeyExchange.cs b/crypto/src/crypto/tls/TlsECDheKeyExchange.cs deleted file mode 100644 index e0553b3f0..000000000 --- a/crypto/src/crypto/tls/TlsECDheKeyExchange.cs +++ /dev/null @@ -1,131 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Math.EC; -using Org.BouncyCastle.Security; -using Org.BouncyCastle.Utilities; -using Org.BouncyCastle.Utilities.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary>(D)TLS ECDHE key exchange (see RFC 4492).</summary> - public class TlsECDheKeyExchange - : TlsECDHKeyExchange - { - protected TlsSignerCredentials mServerCredentials = null; - - public TlsECDheKeyExchange(int keyExchange, IList supportedSignatureAlgorithms, int[] namedCurves, - byte[] clientECPointFormats, byte[] serverECPointFormats) - : base(keyExchange, supportedSignatureAlgorithms, namedCurves, clientECPointFormats, serverECPointFormats) - { - } - - public override void ProcessServerCredentials(TlsCredentials serverCredentials) - { - if (!(serverCredentials is TlsSignerCredentials)) - throw new TlsFatalAlert(AlertDescription.internal_error); - - ProcessServerCertificate(serverCredentials.Certificate); - - this.mServerCredentials = (TlsSignerCredentials)serverCredentials; - } - - public override byte[] GenerateServerKeyExchange() - { - DigestInputBuffer buf = new DigestInputBuffer(); - - this.mECAgreePrivateKey = TlsEccUtilities.GenerateEphemeralServerKeyExchange(mContext.SecureRandom, mNamedCurves, - mClientECPointFormats, buf); - - /* - * RFC 5246 4.7. digitally-signed element needs SignatureAndHashAlgorithm from TLS 1.2 - */ - SignatureAndHashAlgorithm signatureAndHashAlgorithm = TlsUtilities.GetSignatureAndHashAlgorithm( - mContext, mServerCredentials); - - IDigest d = TlsUtilities.CreateHash(signatureAndHashAlgorithm); - - SecurityParameters securityParameters = mContext.SecurityParameters; - d.BlockUpdate(securityParameters.clientRandom, 0, securityParameters.clientRandom.Length); - d.BlockUpdate(securityParameters.serverRandom, 0, securityParameters.serverRandom.Length); - buf.UpdateDigest(d); - - byte[] hash = DigestUtilities.DoFinal(d); - - byte[] signature = mServerCredentials.GenerateCertificateSignature(hash); - - DigitallySigned signed_params = new DigitallySigned(signatureAndHashAlgorithm, signature); - signed_params.Encode(buf); - - return buf.ToArray(); - } - - public override void ProcessServerKeyExchange(Stream input) - { - SecurityParameters securityParameters = mContext.SecurityParameters; - - SignerInputBuffer buf = new SignerInputBuffer(); - Stream teeIn = new TeeInputStream(input, buf); - - ECDomainParameters curve_params = TlsEccUtilities.ReadECParameters(mNamedCurves, mClientECPointFormats, teeIn); - - byte[] point = TlsUtilities.ReadOpaque8(teeIn); - - DigitallySigned signed_params = ParseSignature(input); - - ISigner signer = InitVerifyer(mTlsSigner, signed_params.Algorithm, securityParameters); - buf.UpdateSigner(signer); - if (!signer.VerifySignature(signed_params.Signature)) - throw new TlsFatalAlert(AlertDescription.decrypt_error); - - this.mECAgreePublicKey = TlsEccUtilities.ValidateECPublicKey(TlsEccUtilities.DeserializeECPublicKey( - mClientECPointFormats, curve_params, point)); - } - - public override void ValidateCertificateRequest(CertificateRequest certificateRequest) - { - /* - * RFC 4492 3. [...] The ECDSA_fixed_ECDH and RSA_fixed_ECDH mechanisms are usable with - * ECDH_ECDSA and ECDH_RSA. Their use with ECDHE_ECDSA and ECDHE_RSA is prohibited because - * the use of a long-term ECDH client key would jeopardize the forward secrecy property of - * these algorithms. - */ - byte[] types = certificateRequest.CertificateTypes; - for (int i = 0; i < types.Length; ++i) - { - switch (types[i]) - { - case ClientCertificateType.rsa_sign: - case ClientCertificateType.dss_sign: - case ClientCertificateType.ecdsa_sign: - break; - default: - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - } - } - - public override void ProcessClientCredentials(TlsCredentials clientCredentials) - { - if (clientCredentials is TlsSignerCredentials) - { - // OK - } - else - { - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } - - protected virtual ISigner InitVerifyer(TlsSigner tlsSigner, SignatureAndHashAlgorithm algorithm, - SecurityParameters securityParameters) - { - ISigner signer = tlsSigner.CreateVerifyer(algorithm, this.mServerPublicKey); - signer.BlockUpdate(securityParameters.clientRandom, 0, securityParameters.clientRandom.Length); - signer.BlockUpdate(securityParameters.serverRandom, 0, securityParameters.serverRandom.Length); - return signer; - } - } -} diff --git a/crypto/src/crypto/tls/TlsECDsaSigner.cs b/crypto/src/crypto/tls/TlsECDsaSigner.cs deleted file mode 100644 index fa9d0b714..000000000 --- a/crypto/src/crypto/tls/TlsECDsaSigner.cs +++ /dev/null @@ -1,26 +0,0 @@ -using System; - -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Crypto.Signers; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class TlsECDsaSigner - : TlsDsaSigner - { - public override bool IsValidPublicKey(AsymmetricKeyParameter publicKey) - { - return publicKey is ECPublicKeyParameters; - } - - protected override IDsa CreateDsaImpl(byte hashAlgorithm) - { - return new ECDsaSigner(new HMacDsaKCalculator(TlsUtilities.CreateHash(hashAlgorithm))); - } - - protected override byte SignatureAlgorithm - { - get { return Tls.SignatureAlgorithm.ecdsa; } - } - } -} diff --git a/crypto/src/crypto/tls/TlsEccUtilities.cs b/crypto/src/crypto/tls/TlsEccUtilities.cs deleted file mode 100644 index ec8752a62..000000000 --- a/crypto/src/crypto/tls/TlsEccUtilities.cs +++ /dev/null @@ -1,691 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Asn1.X9; -using Org.BouncyCastle.Crypto; -using Org.BouncyCastle.Crypto.Agreement; -using Org.BouncyCastle.Crypto.EC; -using Org.BouncyCastle.Crypto.Generators; -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Math; -using Org.BouncyCastle.Math.EC; -using Org.BouncyCastle.Math.Field; -using Org.BouncyCastle.Security; -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class TlsEccUtilities - { - private static readonly string[] CurveNames = new string[] { "sect163k1", "sect163r1", "sect163r2", "sect193r1", - "sect193r2", "sect233k1", "sect233r1", "sect239k1", "sect283k1", "sect283r1", "sect409k1", "sect409r1", - "sect571k1", "sect571r1", "secp160k1", "secp160r1", "secp160r2", "secp192k1", "secp192r1", "secp224k1", - "secp224r1", "secp256k1", "secp256r1", "secp384r1", "secp521r1", - "brainpoolP256r1", "brainpoolP384r1", "brainpoolP512r1"}; - - public static void AddSupportedEllipticCurvesExtension(IDictionary extensions, int[] namedCurves) - { - extensions[ExtensionType.supported_groups] = CreateSupportedEllipticCurvesExtension(namedCurves); - } - - public static void AddSupportedPointFormatsExtension(IDictionary extensions, byte[] ecPointFormats) - { - extensions[ExtensionType.ec_point_formats] = CreateSupportedPointFormatsExtension(ecPointFormats); - } - - public static int[] GetSupportedEllipticCurvesExtension(IDictionary extensions) - { - byte[] extensionData = TlsUtilities.GetExtensionData(extensions, ExtensionType.supported_groups); - return extensionData == null ? null : ReadSupportedEllipticCurvesExtension(extensionData); - } - - public static byte[] GetSupportedPointFormatsExtension(IDictionary extensions) - { - byte[] extensionData = TlsUtilities.GetExtensionData(extensions, ExtensionType.ec_point_formats); - return extensionData == null ? null : ReadSupportedPointFormatsExtension(extensionData); - } - - public static byte[] CreateSupportedEllipticCurvesExtension(int[] namedCurves) - { - if (namedCurves == null || namedCurves.Length < 1) - throw new TlsFatalAlert(AlertDescription.internal_error); - - return TlsUtilities.EncodeUint16ArrayWithUint16Length(namedCurves); - } - - public static byte[] CreateSupportedPointFormatsExtension(byte[] ecPointFormats) - { - if (ecPointFormats == null || !Arrays.Contains(ecPointFormats, ECPointFormat.uncompressed)) - { - /* - * RFC 4492 5.1. If the Supported Point Formats Extension is indeed sent, it MUST - * contain the value 0 (uncompressed) as one of the items in the list of point formats. - */ - - // NOTE: We add it at the end (lowest preference) - ecPointFormats = Arrays.Append(ecPointFormats, ECPointFormat.uncompressed); - } - - return TlsUtilities.EncodeUint8ArrayWithUint8Length(ecPointFormats); - } - - public static int[] ReadSupportedEllipticCurvesExtension(byte[] extensionData) - { - if (extensionData == null) - throw new ArgumentNullException("extensionData"); - - MemoryStream buf = new MemoryStream(extensionData, false); - - int length = TlsUtilities.ReadUint16(buf); - if (length < 2 || (length & 1) != 0) - throw new TlsFatalAlert(AlertDescription.decode_error); - - int[] namedCurves = TlsUtilities.ReadUint16Array(length / 2, buf); - - TlsProtocol.AssertEmpty(buf); - - return namedCurves; - } - - public static byte[] ReadSupportedPointFormatsExtension(byte[] extensionData) - { - byte[] ecPointFormats = TlsUtilities.DecodeUint8ArrayWithUint8Length(extensionData); - if (!Arrays.Contains(ecPointFormats, ECPointFormat.uncompressed)) - { - /* - * RFC 4492 5.1. If the Supported Point Formats Extension is indeed sent, it MUST - * contain the value 0 (uncompressed) as one of the items in the list of point formats. - */ - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - return ecPointFormats; - } - - public static string GetNameOfNamedCurve(int namedCurve) - { - return IsSupportedNamedCurve(namedCurve) ? CurveNames[namedCurve - 1] : null; - } - - public static ECDomainParameters GetParametersForNamedCurve(int namedCurve) - { - string curveName = GetNameOfNamedCurve(namedCurve); - if (curveName == null) - return null; - - // Parameters are lazily created the first time a particular curve is accessed - - X9ECParameters ecP = ECKeyPairGenerator.FindECCurveByName(curveName); - if (ecP == null) - return null; - - // It's a bit inefficient to do this conversion every time - return new ECDomainParameters(ecP.Curve, ecP.G, ecP.N, ecP.H, ecP.GetSeed()); - } - - public static bool HasAnySupportedNamedCurves() - { - return CurveNames.Length > 0; - } - - public static bool ContainsEccCipherSuites(int[] cipherSuites) - { - for (int i = 0; i < cipherSuites.Length; ++i) - { - if (IsEccCipherSuite(cipherSuites[i])) - return true; - } - return false; - } - - public static bool IsEccCipherSuite(int cipherSuite) - { - switch (cipherSuite) - { - /* - * RFC 4492 - */ - case CipherSuite.TLS_ECDH_ECDSA_WITH_NULL_SHA: - case CipherSuite.TLS_ECDH_ECDSA_WITH_RC4_128_SHA: - case CipherSuite.TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_NULL_SHA: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_RC4_128_SHA: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_ECDH_RSA_WITH_NULL_SHA: - case CipherSuite.TLS_ECDH_RSA_WITH_RC4_128_SHA: - case CipherSuite.TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_ECDHE_RSA_WITH_NULL_SHA: - case CipherSuite.TLS_ECDHE_RSA_WITH_RC4_128_SHA: - case CipherSuite.TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_ECDH_anon_WITH_NULL_SHA: - case CipherSuite.TLS_ECDH_anon_WITH_RC4_128_SHA: - case CipherSuite.TLS_ECDH_anon_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_ECDH_anon_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_ECDH_anon_WITH_AES_256_CBC_SHA: - - /* - * RFC 5289 - */ - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_256_GCM_SHA384: - - /* - * RFC 5489 - */ - case CipherSuite.TLS_ECDHE_PSK_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_PSK_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_ECDHE_PSK_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_PSK_WITH_NULL_SHA: - case CipherSuite.TLS_ECDHE_PSK_WITH_NULL_SHA256: - case CipherSuite.TLS_ECDHE_PSK_WITH_NULL_SHA384: - case CipherSuite.TLS_ECDHE_PSK_WITH_RC4_128_SHA: - - /* - * RFC 6367 - */ - case CipherSuite.TLS_ECDHE_ECDSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_ECDH_ECDSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_ECDH_ECDSA_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_RSA_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_ECDH_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_ECDH_RSA_WITH_CAMELLIA_256_CBC_SHA384: - - case CipherSuite.TLS_ECDHE_ECDSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_ECDH_ECDSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_ECDH_ECDSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_ECDHE_RSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_ECDHE_RSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_ECDH_RSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_ECDH_RSA_WITH_CAMELLIA_256_GCM_SHA384: - - case CipherSuite.TLS_ECDHE_PSK_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_PSK_WITH_CAMELLIA_256_CBC_SHA384: - - /* - * RFC 7251 - */ - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_CCM: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_CCM_8: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_CCM: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_CCM_8: - - /* - * draft-ietf-tls-chacha20-poly1305-04 - */ - case CipherSuite.DRAFT_TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.DRAFT_TLS_ECDHE_PSK_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.DRAFT_TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256: - - return true; - - default: - return false; - } - } - - public static bool AreOnSameCurve(ECDomainParameters a, ECDomainParameters b) - { - return a != null && a.Equals(b); - } - - public static bool IsSupportedNamedCurve(int namedCurve) - { - return (namedCurve > 0 && namedCurve <= CurveNames.Length); - } - - public static bool IsCompressionPreferred(byte[] ecPointFormats, byte compressionFormat) - { - if (ecPointFormats == null) - return false; - - for (int i = 0; i < ecPointFormats.Length; ++i) - { - byte ecPointFormat = ecPointFormats[i]; - if (ecPointFormat == ECPointFormat.uncompressed) - return false; - if (ecPointFormat == compressionFormat) - return true; - } - return false; - } - - public static byte[] SerializeECFieldElement(int fieldSize, BigInteger x) - { - return BigIntegers.AsUnsignedByteArray((fieldSize + 7) / 8, x); - } - - public static byte[] SerializeECPoint(byte[] ecPointFormats, ECPoint point) - { - ECCurve curve = point.Curve; - - /* - * RFC 4492 5.7. ...an elliptic curve point in uncompressed or compressed format. Here, the - * format MUST conform to what the server has requested through a Supported Point Formats - * Extension if this extension was used, and MUST be uncompressed if this extension was not - * used. - */ - bool compressed = false; - if (ECAlgorithms.IsFpCurve(curve)) - { - compressed = IsCompressionPreferred(ecPointFormats, ECPointFormat.ansiX962_compressed_prime); - } - else if (ECAlgorithms.IsF2mCurve(curve)) - { - compressed = IsCompressionPreferred(ecPointFormats, ECPointFormat.ansiX962_compressed_char2); - } - return point.GetEncoded(compressed); - } - - public static byte[] SerializeECPublicKey(byte[] ecPointFormats, ECPublicKeyParameters keyParameters) - { - return SerializeECPoint(ecPointFormats, keyParameters.Q); - } - - public static BigInteger DeserializeECFieldElement(int fieldSize, byte[] encoding) - { - int requiredLength = (fieldSize + 7) / 8; - if (encoding.Length != requiredLength) - throw new TlsFatalAlert(AlertDescription.decode_error); - return new BigInteger(1, encoding); - } - - public static ECPoint DeserializeECPoint(byte[] ecPointFormats, ECCurve curve, byte[] encoding) - { - if (encoding == null || encoding.Length < 1) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - - byte actualFormat; - switch (encoding[0]) - { - case 0x02: // compressed - case 0x03: // compressed - { - if (ECAlgorithms.IsF2mCurve(curve)) - { - actualFormat = ECPointFormat.ansiX962_compressed_char2; - } - else if (ECAlgorithms.IsFpCurve(curve)) - { - actualFormat = ECPointFormat.ansiX962_compressed_prime; - } - else - { - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - break; - } - case 0x04: // uncompressed - { - actualFormat = ECPointFormat.uncompressed; - break; - } - case 0x00: // infinity - case 0x06: // hybrid - case 0x07: // hybrid - default: - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - - if (actualFormat != ECPointFormat.uncompressed - && (ecPointFormats == null || !Arrays.Contains(ecPointFormats, actualFormat))) - { - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - - return curve.DecodePoint(encoding); - } - - public static ECPublicKeyParameters DeserializeECPublicKey(byte[] ecPointFormats, ECDomainParameters curve_params, - byte[] encoding) - { - try - { - ECPoint Y = DeserializeECPoint(ecPointFormats, curve_params.Curve, encoding); - return new ECPublicKeyParameters(Y, curve_params); - } - catch (Exception e) - { - throw new TlsFatalAlert(AlertDescription.illegal_parameter, e); - } - } - - public static byte[] CalculateECDHBasicAgreement(ECPublicKeyParameters publicKey, ECPrivateKeyParameters privateKey) - { - ECDHBasicAgreement basicAgreement = new ECDHBasicAgreement(); - basicAgreement.Init(privateKey); - BigInteger agreementValue = basicAgreement.CalculateAgreement(publicKey); - - /* - * RFC 4492 5.10. Note that this octet string (Z in IEEE 1363 terminology) as output by - * FE2OSP, the Field Element to Octet String Conversion Primitive, has constant length for - * any given field; leading zeros found in this octet string MUST NOT be truncated. - */ - return BigIntegers.AsUnsignedByteArray(basicAgreement.GetFieldSize(), agreementValue); - } - - public static AsymmetricCipherKeyPair GenerateECKeyPair(SecureRandom random, ECDomainParameters ecParams) - { - ECKeyPairGenerator keyPairGenerator = new ECKeyPairGenerator(); - keyPairGenerator.Init(new ECKeyGenerationParameters(ecParams, random)); - return keyPairGenerator.GenerateKeyPair(); - } - - public static ECPrivateKeyParameters GenerateEphemeralClientKeyExchange(SecureRandom random, byte[] ecPointFormats, - ECDomainParameters ecParams, Stream output) - { - AsymmetricCipherKeyPair kp = GenerateECKeyPair(random, ecParams); - - ECPublicKeyParameters ecPublicKey = (ECPublicKeyParameters)kp.Public; - WriteECPoint(ecPointFormats, ecPublicKey.Q, output); - - return (ECPrivateKeyParameters)kp.Private; - } - - // TODO Refactor around ServerECDHParams before making this public - internal static ECPrivateKeyParameters GenerateEphemeralServerKeyExchange(SecureRandom random, int[] namedCurves, - byte[] ecPointFormats, Stream output) - { - /* First we try to find a supported named curve from the client's list. */ - int namedCurve = -1; - if (namedCurves == null) - { - // TODO Let the peer choose the default named curve - namedCurve = NamedCurve.secp256r1; - } - else - { - for (int i = 0; i < namedCurves.Length; ++i) - { - int entry = namedCurves[i]; - if (NamedCurve.IsValid(entry) && IsSupportedNamedCurve(entry)) - { - namedCurve = entry; - break; - } - } - } - - ECDomainParameters ecParams = null; - if (namedCurve >= 0) - { - ecParams = GetParametersForNamedCurve(namedCurve); - } - else - { - /* If no named curves are suitable, check if the client supports explicit curves. */ - if (Arrays.Contains(namedCurves, NamedCurve.arbitrary_explicit_prime_curves)) - { - ecParams = GetParametersForNamedCurve(NamedCurve.secp256r1); - } - else if (Arrays.Contains(namedCurves, NamedCurve.arbitrary_explicit_char2_curves)) - { - ecParams = GetParametersForNamedCurve(NamedCurve.sect283r1); - } - } - - if (ecParams == null) - { - /* - * NOTE: We shouldn't have negotiated ECDHE key exchange since we apparently can't find - * a suitable curve. - */ - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - if (namedCurve < 0) - { - WriteExplicitECParameters(ecPointFormats, ecParams, output); - } - else - { - WriteNamedECParameters(namedCurve, output); - } - - return GenerateEphemeralClientKeyExchange(random, ecPointFormats, ecParams, output); - } - - public static ECPublicKeyParameters ValidateECPublicKey(ECPublicKeyParameters key) - { - // TODO Check RFC 4492 for validation - return key; - } - - public static int ReadECExponent(int fieldSize, Stream input) - { - BigInteger K = ReadECParameter(input); - if (K.BitLength < 32) - { - int k = K.IntValue; - if (k > 0 && k < fieldSize) - { - return k; - } - } - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - - public static BigInteger ReadECFieldElement(int fieldSize, Stream input) - { - return DeserializeECFieldElement(fieldSize, TlsUtilities.ReadOpaque8(input)); - } - - public static BigInteger ReadECParameter(Stream input) - { - // TODO Are leading zeroes okay here? - return new BigInteger(1, TlsUtilities.ReadOpaque8(input)); - } - - public static ECDomainParameters ReadECParameters(int[] namedCurves, byte[] ecPointFormats, Stream input) - { - try - { - byte curveType = TlsUtilities.ReadUint8(input); - - switch (curveType) - { - case ECCurveType.explicit_prime: - { - CheckNamedCurve(namedCurves, NamedCurve.arbitrary_explicit_prime_curves); - - BigInteger prime_p = ReadECParameter(input); - BigInteger a = ReadECFieldElement(prime_p.BitLength, input); - BigInteger b = ReadECFieldElement(prime_p.BitLength, input); - byte[] baseEncoding = TlsUtilities.ReadOpaque8(input); - BigInteger order = ReadECParameter(input); - BigInteger cofactor = ReadECParameter(input); - ECCurve curve = new FpCurve(prime_p, a, b, order, cofactor); - ECPoint basePoint = DeserializeECPoint(ecPointFormats, curve, baseEncoding); - return new ECDomainParameters(curve, basePoint, order, cofactor); - } - case ECCurveType.explicit_char2: - { - CheckNamedCurve(namedCurves, NamedCurve.arbitrary_explicit_char2_curves); - - int m = TlsUtilities.ReadUint16(input); - byte basis = TlsUtilities.ReadUint8(input); - if (!ECBasisType.IsValid(basis)) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - - int k1 = ReadECExponent(m, input), k2 = -1, k3 = -1; - if (basis == ECBasisType.ec_basis_pentanomial) - { - k2 = ReadECExponent(m, input); - k3 = ReadECExponent(m, input); - } - - BigInteger a = ReadECFieldElement(m, input); - BigInteger b = ReadECFieldElement(m, input); - byte[] baseEncoding = TlsUtilities.ReadOpaque8(input); - BigInteger order = ReadECParameter(input); - BigInteger cofactor = ReadECParameter(input); - - ECCurve curve = (basis == ECBasisType.ec_basis_pentanomial) - ? new F2mCurve(m, k1, k2, k3, a, b, order, cofactor) - : new F2mCurve(m, k1, a, b, order, cofactor); - - ECPoint basePoint = DeserializeECPoint(ecPointFormats, curve, baseEncoding); - - return new ECDomainParameters(curve, basePoint, order, cofactor); - } - case ECCurveType.named_curve: - { - int namedCurve = TlsUtilities.ReadUint16(input); - if (!NamedCurve.RefersToASpecificNamedCurve(namedCurve)) - { - /* - * RFC 4492 5.4. All those values of NamedCurve are allowed that refer to a - * specific curve. Values of NamedCurve that indicate support for a class of - * explicitly defined curves are not allowed here [...]. - */ - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - - CheckNamedCurve(namedCurves, namedCurve); - - return GetParametersForNamedCurve(namedCurve); - } - default: - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - } - catch (Exception e) - { - throw new TlsFatalAlert(AlertDescription.illegal_parameter, e); - } - } - - private static void CheckNamedCurve(int[] namedCurves, int namedCurve) - { - if (namedCurves != null && !Arrays.Contains(namedCurves, namedCurve)) - { - /* - * RFC 4492 4. [...] servers MUST NOT negotiate the use of an ECC cipher suite - * unless they can complete the handshake while respecting the choice of curves - * and compression techniques specified by the client. - */ - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - } - - public static void WriteECExponent(int k, Stream output) - { - BigInteger K = BigInteger.ValueOf(k); - WriteECParameter(K, output); - } - - public static void WriteECFieldElement(ECFieldElement x, Stream output) - { - TlsUtilities.WriteOpaque8(x.GetEncoded(), output); - } - - public static void WriteECFieldElement(int fieldSize, BigInteger x, Stream output) - { - TlsUtilities.WriteOpaque8(SerializeECFieldElement(fieldSize, x), output); - } - - public static void WriteECParameter(BigInteger x, Stream output) - { - TlsUtilities.WriteOpaque8(BigIntegers.AsUnsignedByteArray(x), output); - } - - public static void WriteExplicitECParameters(byte[] ecPointFormats, ECDomainParameters ecParameters, - Stream output) - { - ECCurve curve = ecParameters.Curve; - - if (ECAlgorithms.IsFpCurve(curve)) - { - TlsUtilities.WriteUint8(ECCurveType.explicit_prime, output); - - WriteECParameter(curve.Field.Characteristic, output); - } - else if (ECAlgorithms.IsF2mCurve(curve)) - { - IPolynomialExtensionField field = (IPolynomialExtensionField)curve.Field; - int[] exponents = field.MinimalPolynomial.GetExponentsPresent(); - - TlsUtilities.WriteUint8(ECCurveType.explicit_char2, output); - - int m = exponents[exponents.Length - 1]; - TlsUtilities.CheckUint16(m); - TlsUtilities.WriteUint16(m, output); - - if (exponents.Length == 3) - { - TlsUtilities.WriteUint8(ECBasisType.ec_basis_trinomial, output); - WriteECExponent(exponents[1], output); - } - else if (exponents.Length == 5) - { - TlsUtilities.WriteUint8(ECBasisType.ec_basis_pentanomial, output); - WriteECExponent(exponents[1], output); - WriteECExponent(exponents[2], output); - WriteECExponent(exponents[3], output); - } - else - { - throw new ArgumentException("Only trinomial and pentomial curves are supported"); - } - } - else - { - throw new ArgumentException("'ecParameters' not a known curve type"); - } - - WriteECFieldElement(curve.A, output); - WriteECFieldElement(curve.B, output); - TlsUtilities.WriteOpaque8(SerializeECPoint(ecPointFormats, ecParameters.G), output); - WriteECParameter(ecParameters.N, output); - WriteECParameter(ecParameters.H, output); - } - - public static void WriteECPoint(byte[] ecPointFormats, ECPoint point, Stream output) - { - TlsUtilities.WriteOpaque8(SerializeECPoint(ecPointFormats, point), output); - } - - public static void WriteNamedECParameters(int namedCurve, Stream output) - { - if (!NamedCurve.RefersToASpecificNamedCurve(namedCurve)) - { - /* - * RFC 4492 5.4. All those values of NamedCurve are allowed that refer to a specific - * curve. Values of NamedCurve that indicate support for a class of explicitly defined - * curves are not allowed here [...]. - */ - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - TlsUtilities.WriteUint8(ECCurveType.named_curve, output); - TlsUtilities.CheckUint16(namedCurve); - TlsUtilities.WriteUint16(namedCurve, output); - } - } -} diff --git a/crypto/src/crypto/tls/TlsEncryptionCredentials.cs b/crypto/src/crypto/tls/TlsEncryptionCredentials.cs deleted file mode 100644 index 52f007006..000000000 --- a/crypto/src/crypto/tls/TlsEncryptionCredentials.cs +++ /dev/null @@ -1,12 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public interface TlsEncryptionCredentials - : TlsCredentials - { - /// <exception cref="IOException"></exception> - byte[] DecryptPreMasterSecret(byte[] encryptedPreMasterSecret); - } -} diff --git a/crypto/src/crypto/tls/TlsException.cs b/crypto/src/crypto/tls/TlsException.cs deleted file mode 100644 index 18ca22a58..000000000 --- a/crypto/src/crypto/tls/TlsException.cs +++ /dev/null @@ -1,24 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class TlsException - : IOException - { - public TlsException() - : base() - { - } - - public TlsException(string message) - : base(message) - { - } - - public TlsException(string message, Exception cause) - : base(message, cause) - { - } - } -} diff --git a/crypto/src/crypto/tls/TlsExtensionsUtilities.cs b/crypto/src/crypto/tls/TlsExtensionsUtilities.cs deleted file mode 100644 index 4b3d9e0c5..000000000 --- a/crypto/src/crypto/tls/TlsExtensionsUtilities.cs +++ /dev/null @@ -1,368 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class TlsExtensionsUtilities - { - public static IDictionary EnsureExtensionsInitialised(IDictionary extensions) - { - return extensions == null ? Platform.CreateHashtable() : extensions; - } - - /// <exception cref="IOException"></exception> - public static void AddClientCertificateTypeExtensionClient(IDictionary extensions, byte[] certificateTypes) - { - extensions[ExtensionType.client_certificate_type] = CreateCertificateTypeExtensionClient(certificateTypes); - } - - /// <exception cref="IOException"></exception> - public static void AddClientCertificateTypeExtensionServer(IDictionary extensions, byte certificateType) - { - extensions[ExtensionType.client_certificate_type] = CreateCertificateTypeExtensionServer(certificateType); - } - - public static void AddEncryptThenMacExtension(IDictionary extensions) - { - extensions[ExtensionType.encrypt_then_mac] = CreateEncryptThenMacExtension(); - } - - public static void AddExtendedMasterSecretExtension(IDictionary extensions) - { - extensions[ExtensionType.extended_master_secret] = CreateExtendedMasterSecretExtension(); - } - - /// <exception cref="IOException"></exception> - public static void AddHeartbeatExtension(IDictionary extensions, HeartbeatExtension heartbeatExtension) - { - extensions[ExtensionType.heartbeat] = CreateHeartbeatExtension(heartbeatExtension); - } - - /// <exception cref="IOException"></exception> - public static void AddMaxFragmentLengthExtension(IDictionary extensions, byte maxFragmentLength) - { - extensions[ExtensionType.max_fragment_length] = CreateMaxFragmentLengthExtension(maxFragmentLength); - } - - /// <exception cref="IOException"></exception> - public static void AddPaddingExtension(IDictionary extensions, int dataLength) - { - extensions[ExtensionType.padding] = CreatePaddingExtension(dataLength); - } - - /// <exception cref="IOException"></exception> - public static void AddServerCertificateTypeExtensionClient(IDictionary extensions, byte[] certificateTypes) - { - extensions[ExtensionType.server_certificate_type] = CreateCertificateTypeExtensionClient(certificateTypes); - } - - /// <exception cref="IOException"></exception> - public static void AddServerCertificateTypeExtensionServer(IDictionary extensions, byte certificateType) - { - extensions[ExtensionType.server_certificate_type] = CreateCertificateTypeExtensionServer(certificateType); - } - - /// <exception cref="IOException"></exception> - public static void AddServerNameExtension(IDictionary extensions, ServerNameList serverNameList) - { - extensions[ExtensionType.server_name] = CreateServerNameExtension(serverNameList); - } - - /// <exception cref="IOException"></exception> - public static void AddStatusRequestExtension(IDictionary extensions, CertificateStatusRequest statusRequest) - { - extensions[ExtensionType.status_request] = CreateStatusRequestExtension(statusRequest); - } - - public static void AddTruncatedHMacExtension(IDictionary extensions) - { - extensions[ExtensionType.truncated_hmac] = CreateTruncatedHMacExtension(); - } - - /// <exception cref="IOException"></exception> - public static byte[] GetClientCertificateTypeExtensionClient(IDictionary extensions) - { - byte[] extensionData = TlsUtilities.GetExtensionData(extensions, ExtensionType.client_certificate_type); - return extensionData == null ? null : ReadCertificateTypeExtensionClient(extensionData); - } - - /// <exception cref="IOException"></exception> - public static short GetClientCertificateTypeExtensionServer(IDictionary extensions) - { - byte[] extensionData = TlsUtilities.GetExtensionData(extensions, ExtensionType.client_certificate_type); - return extensionData == null ? (short)-1 : (short)ReadCertificateTypeExtensionServer(extensionData); - } - - /// <exception cref="IOException"></exception> - public static HeartbeatExtension GetHeartbeatExtension(IDictionary extensions) - { - byte[] extensionData = TlsUtilities.GetExtensionData(extensions, ExtensionType.heartbeat); - return extensionData == null ? null : ReadHeartbeatExtension(extensionData); - } - - /// <exception cref="IOException"></exception> - public static short GetMaxFragmentLengthExtension(IDictionary extensions) - { - byte[] extensionData = TlsUtilities.GetExtensionData(extensions, ExtensionType.max_fragment_length); - return extensionData == null ? (short)-1 : (short)ReadMaxFragmentLengthExtension(extensionData); - } - - /// <exception cref="IOException"></exception> - public static int GetPaddingExtension(IDictionary extensions) - { - byte[] extensionData = TlsUtilities.GetExtensionData(extensions, ExtensionType.padding); - return extensionData == null ? -1 : ReadPaddingExtension(extensionData); - } - - /// <exception cref="IOException"></exception> - public static byte[] GetServerCertificateTypeExtensionClient(IDictionary extensions) - { - byte[] extensionData = TlsUtilities.GetExtensionData(extensions, ExtensionType.server_certificate_type); - return extensionData == null ? null : ReadCertificateTypeExtensionClient(extensionData); - } - - /// <exception cref="IOException"></exception> - public static short GetServerCertificateTypeExtensionServer(IDictionary extensions) - { - byte[] extensionData = TlsUtilities.GetExtensionData(extensions, ExtensionType.server_certificate_type); - return extensionData == null ? (short)-1 : (short)ReadCertificateTypeExtensionServer(extensionData); - } - - /// <exception cref="IOException"></exception> - public static ServerNameList GetServerNameExtension(IDictionary extensions) - { - byte[] extensionData = TlsUtilities.GetExtensionData(extensions, ExtensionType.server_name); - return extensionData == null ? null : ReadServerNameExtension(extensionData); - } - - /// <exception cref="IOException"></exception> - public static CertificateStatusRequest GetStatusRequestExtension(IDictionary extensions) - { - byte[] extensionData = TlsUtilities.GetExtensionData(extensions, ExtensionType.status_request); - return extensionData == null ? null : ReadStatusRequestExtension(extensionData); - } - - /// <exception cref="IOException"></exception> - public static bool HasEncryptThenMacExtension(IDictionary extensions) - { - byte[] extensionData = TlsUtilities.GetExtensionData(extensions, ExtensionType.encrypt_then_mac); - return extensionData == null ? false : ReadEncryptThenMacExtension(extensionData); - } - - /// <exception cref="IOException"></exception> - public static bool HasExtendedMasterSecretExtension(IDictionary extensions) - { - byte[] extensionData = TlsUtilities.GetExtensionData(extensions, ExtensionType.extended_master_secret); - return extensionData == null ? false : ReadExtendedMasterSecretExtension(extensionData); - } - - /// <exception cref="IOException"></exception> - public static bool HasTruncatedHMacExtension(IDictionary extensions) - { - byte[] extensionData = TlsUtilities.GetExtensionData(extensions, ExtensionType.truncated_hmac); - return extensionData == null ? false : ReadTruncatedHMacExtension(extensionData); - } - - /// <exception cref="IOException"></exception> - public static byte[] CreateCertificateTypeExtensionClient(byte[] certificateTypes) - { - if (certificateTypes == null || certificateTypes.Length < 1 || certificateTypes.Length > 255) - throw new TlsFatalAlert(AlertDescription.internal_error); - - return TlsUtilities.EncodeUint8ArrayWithUint8Length(certificateTypes); - } - - /// <exception cref="IOException"></exception> - public static byte[] CreateCertificateTypeExtensionServer(byte certificateType) - { - return TlsUtilities.EncodeUint8(certificateType); - } - - public static byte[] CreateEmptyExtensionData() - { - return TlsUtilities.EmptyBytes; - } - - public static byte[] CreateEncryptThenMacExtension() - { - return CreateEmptyExtensionData(); - } - - public static byte[] CreateExtendedMasterSecretExtension() - { - return CreateEmptyExtensionData(); - } - - /// <exception cref="IOException"></exception> - public static byte[] CreateHeartbeatExtension(HeartbeatExtension heartbeatExtension) - { - if (heartbeatExtension == null) - throw new TlsFatalAlert(AlertDescription.internal_error); - - MemoryStream buf = new MemoryStream(); - - heartbeatExtension.Encode(buf); - - return buf.ToArray(); - } - - /// <exception cref="IOException"></exception> - public static byte[] CreateMaxFragmentLengthExtension(byte maxFragmentLength) - { - return TlsUtilities.EncodeUint8(maxFragmentLength); - } - - /// <exception cref="IOException"></exception> - public static byte[] CreatePaddingExtension(int dataLength) - { - TlsUtilities.CheckUint16(dataLength); - return new byte[dataLength]; - } - - /// <exception cref="IOException"></exception> - public static byte[] CreateServerNameExtension(ServerNameList serverNameList) - { - if (serverNameList == null) - throw new TlsFatalAlert(AlertDescription.internal_error); - - MemoryStream buf = new MemoryStream(); - - serverNameList.Encode(buf); - - return buf.ToArray(); - } - - /// <exception cref="IOException"></exception> - public static byte[] CreateStatusRequestExtension(CertificateStatusRequest statusRequest) - { - if (statusRequest == null) - { - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - MemoryStream buf = new MemoryStream(); - - statusRequest.Encode(buf); - - return buf.ToArray(); - } - - public static byte[] CreateTruncatedHMacExtension() - { - return CreateEmptyExtensionData(); - } - - /// <exception cref="IOException"></exception> - private static bool ReadEmptyExtensionData(byte[] extensionData) - { - if (extensionData == null) - throw new ArgumentNullException("extensionData"); - - if (extensionData.Length != 0) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - - return true; - } - - /// <exception cref="IOException"></exception> - public static byte[] ReadCertificateTypeExtensionClient(byte[] extensionData) - { - byte[] certificateTypes = TlsUtilities.DecodeUint8ArrayWithUint8Length(extensionData); - if (certificateTypes.Length < 1) - throw new TlsFatalAlert(AlertDescription.decode_error); - return certificateTypes; - } - - /// <exception cref="IOException"></exception> - public static byte ReadCertificateTypeExtensionServer(byte[] extensionData) - { - return TlsUtilities.DecodeUint8(extensionData); - } - - /// <exception cref="IOException"></exception> - public static bool ReadEncryptThenMacExtension(byte[] extensionData) - { - return ReadEmptyExtensionData(extensionData); - } - - /// <exception cref="IOException"></exception> - public static bool ReadExtendedMasterSecretExtension(byte[] extensionData) - { - return ReadEmptyExtensionData(extensionData); - } - - /// <exception cref="IOException"></exception> - public static HeartbeatExtension ReadHeartbeatExtension(byte[] extensionData) - { - if (extensionData == null) - throw new ArgumentNullException("extensionData"); - - MemoryStream buf = new MemoryStream(extensionData, false); - - HeartbeatExtension heartbeatExtension = HeartbeatExtension.Parse(buf); - - TlsProtocol.AssertEmpty(buf); - - return heartbeatExtension; - } - - /// <exception cref="IOException"></exception> - public static byte ReadMaxFragmentLengthExtension(byte[] extensionData) - { - return TlsUtilities.DecodeUint8(extensionData); - } - - /// <exception cref="IOException"></exception> - public static int ReadPaddingExtension(byte[] extensionData) - { - if (extensionData == null) - throw new ArgumentNullException("extensionData"); - - for (int i = 0; i < extensionData.Length; ++i) - { - if (extensionData[i] != 0) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - return extensionData.Length; - } - - /// <exception cref="IOException"></exception> - public static ServerNameList ReadServerNameExtension(byte[] extensionData) - { - if (extensionData == null) - throw new ArgumentNullException("extensionData"); - - MemoryStream buf = new MemoryStream(extensionData, false); - - ServerNameList serverNameList = ServerNameList.Parse(buf); - - TlsProtocol.AssertEmpty(buf); - - return serverNameList; - } - - /// <exception cref="IOException"></exception> - public static CertificateStatusRequest ReadStatusRequestExtension(byte[] extensionData) - { - if (extensionData == null) - throw new ArgumentNullException("extensionData"); - - MemoryStream buf = new MemoryStream(extensionData, false); - - CertificateStatusRequest statusRequest = CertificateStatusRequest.Parse(buf); - - TlsProtocol.AssertEmpty(buf); - - return statusRequest; - } - - /// <exception cref="IOException"></exception> - public static bool ReadTruncatedHMacExtension(byte[] extensionData) - { - return ReadEmptyExtensionData(extensionData); - } - } -} diff --git a/crypto/src/crypto/tls/TlsFatalAlert.cs b/crypto/src/crypto/tls/TlsFatalAlert.cs deleted file mode 100644 index 6f1898179..000000000 --- a/crypto/src/crypto/tls/TlsFatalAlert.cs +++ /dev/null @@ -1,26 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class TlsFatalAlert - : TlsException - { - private readonly byte alertDescription; - - public TlsFatalAlert(byte alertDescription) - : this(alertDescription, null) - { - } - - public TlsFatalAlert(byte alertDescription, Exception alertCause) - : base(Tls.AlertDescription.GetText(alertDescription), alertCause) - { - this.alertDescription = alertDescription; - } - - public virtual byte AlertDescription - { - get { return alertDescription; } - } - } -} diff --git a/crypto/src/crypto/tls/TlsFatalAlertReceived.cs b/crypto/src/crypto/tls/TlsFatalAlertReceived.cs deleted file mode 100644 index 044fc8027..000000000 --- a/crypto/src/crypto/tls/TlsFatalAlertReceived.cs +++ /dev/null @@ -1,21 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class TlsFatalAlertReceived - : TlsException - { - private readonly byte alertDescription; - - public TlsFatalAlertReceived(byte alertDescription) - : base(Tls.AlertDescription.GetText(alertDescription), null) - { - this.alertDescription = alertDescription; - } - - public virtual byte AlertDescription - { - get { return alertDescription; } - } - } -} diff --git a/crypto/src/crypto/tls/TlsHandshakeHash.cs b/crypto/src/crypto/tls/TlsHandshakeHash.cs deleted file mode 100644 index 7118d9769..000000000 --- a/crypto/src/crypto/tls/TlsHandshakeHash.cs +++ /dev/null @@ -1,22 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public interface TlsHandshakeHash - : IDigest - { - void Init(TlsContext context); - - TlsHandshakeHash NotifyPrfDetermined(); - - void TrackHashAlgorithm(byte hashAlgorithm); - - void SealHashAlgorithms(); - - TlsHandshakeHash StopTracking(); - - IDigest ForkPrfHash(); - - byte[] GetFinalHash(byte hashAlgorithm); - } -} diff --git a/crypto/src/crypto/tls/TlsKeyExchange.cs b/crypto/src/crypto/tls/TlsKeyExchange.cs deleted file mode 100644 index 6731f6f63..000000000 --- a/crypto/src/crypto/tls/TlsKeyExchange.cs +++ /dev/null @@ -1,54 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary> - /// A generic interface for key exchange implementations in (D)TLS. - /// </summary> - public interface TlsKeyExchange - { - void Init(TlsContext context); - - /// <exception cref="IOException"/> - void SkipServerCredentials(); - - /// <exception cref="IOException"/> - void ProcessServerCredentials(TlsCredentials serverCredentials); - - /// <exception cref="IOException"/> - void ProcessServerCertificate(Certificate serverCertificate); - - bool RequiresServerKeyExchange { get; } - - /// <exception cref="IOException"/> - byte[] GenerateServerKeyExchange(); - - /// <exception cref="IOException"/> - void SkipServerKeyExchange(); - - /// <exception cref="IOException"/> - void ProcessServerKeyExchange(Stream input); - - /// <exception cref="IOException"/> - void ValidateCertificateRequest(CertificateRequest certificateRequest); - - /// <exception cref="IOException"/> - void SkipClientCredentials(); - - /// <exception cref="IOException"/> - void ProcessClientCredentials(TlsCredentials clientCredentials); - - /// <exception cref="IOException"/> - void ProcessClientCertificate(Certificate clientCertificate); - - /// <exception cref="IOException"/> - void GenerateClientKeyExchange(Stream output); - - /// <exception cref="IOException"/> - void ProcessClientKeyExchange(Stream input); - - /// <exception cref="IOException"/> - byte[] GeneratePremasterSecret(); - } -} diff --git a/crypto/src/crypto/tls/TlsMac.cs b/crypto/src/crypto/tls/TlsMac.cs deleted file mode 100644 index a80319a17..000000000 --- a/crypto/src/crypto/tls/TlsMac.cs +++ /dev/null @@ -1,173 +0,0 @@ -using System; -using System.IO; - -using Org.BouncyCastle.Crypto.Digests; -using Org.BouncyCastle.Crypto.Macs; -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Security; -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary> - /// A generic TLS MAC implementation, acting as an HMAC based on some underlying Digest. - /// </summary> - public class TlsMac - { - protected readonly TlsContext context; - protected readonly byte[] secret; - protected readonly IMac mac; - protected readonly int digestBlockSize; - protected readonly int digestOverhead; - protected readonly int macLength; - - /** - * Generate a new instance of an TlsMac. - * - * @param context the TLS client context - * @param digest The digest to use. - * @param key A byte-array where the key for this MAC is located. - * @param keyOff The number of bytes to skip, before the key starts in the buffer. - * @param keyLen The length of the key. - */ - public TlsMac(TlsContext context, IDigest digest, byte[] key, int keyOff, int keyLen) - { - this.context = context; - - KeyParameter keyParameter = new KeyParameter(key, keyOff, keyLen); - - this.secret = Arrays.Clone(keyParameter.GetKey()); - - // TODO This should check the actual algorithm, not rely on the engine type - if (digest is LongDigest) - { - this.digestBlockSize = 128; - this.digestOverhead = 16; - } - else - { - this.digestBlockSize = 64; - this.digestOverhead = 8; - } - - if (TlsUtilities.IsSsl(context)) - { - this.mac = new Ssl3Mac(digest); - - // TODO This should check the actual algorithm, not assume based on the digest size - if (digest.GetDigestSize() == 20) - { - /* - * NOTE: When SHA-1 is used with the SSL 3.0 MAC, the secret + input pad is not - * digest block-aligned. - */ - this.digestOverhead = 4; - } - } - else - { - this.mac = new HMac(digest); - - // NOTE: The input pad for HMAC is always a full digest block - } - - this.mac.Init(keyParameter); - - this.macLength = mac.GetMacSize(); - if (context.SecurityParameters.truncatedHMac) - { - this.macLength = System.Math.Min(this.macLength, 10); - } - } - - /** - * @return the MAC write secret - */ - public virtual byte[] MacSecret - { - get { return this.secret; } - } - - /** - * @return The output length of this MAC. - */ - public virtual int Size - { - get { return macLength; } - } - - /** - * Calculate the MAC for some given data. - * - * @param type The message type of the message. - * @param message A byte-buffer containing the message. - * @param offset The number of bytes to skip, before the message starts. - * @param length The length of the message. - * @return A new byte-buffer containing the MAC value. - */ - public virtual byte[] CalculateMac(long seqNo, byte type, byte[] message, int offset, int length) - { - ProtocolVersion serverVersion = context.ServerVersion; - bool isSsl = serverVersion.IsSsl; - - byte[] macHeader = new byte[isSsl ? 11 : 13]; - TlsUtilities.WriteUint64(seqNo, macHeader, 0); - TlsUtilities.WriteUint8(type, macHeader, 8); - if (!isSsl) - { - TlsUtilities.WriteVersion(serverVersion, macHeader, 9); - } - TlsUtilities.WriteUint16(length, macHeader, macHeader.Length - 2); - - mac.BlockUpdate(macHeader, 0, macHeader.Length); - mac.BlockUpdate(message, offset, length); - - return Truncate(MacUtilities.DoFinal(mac)); - } - - public virtual byte[] CalculateMacConstantTime(long seqNo, byte type, byte[] message, int offset, int length, - int fullLength, byte[] dummyData) - { - /* - * Actual MAC only calculated on 'length' bytes... - */ - byte[] result = CalculateMac(seqNo, type, message, offset, length); - - /* - * ...but ensure a constant number of complete digest blocks are processed (as many as would - * be needed for 'fullLength' bytes of input). - */ - int headerLength = TlsUtilities.IsSsl(context) ? 11 : 13; - - // How many extra full blocks do we need to calculate? - int extra = GetDigestBlockCount(headerLength + fullLength) - GetDigestBlockCount(headerLength + length); - - while (--extra >= 0) - { - mac.BlockUpdate(dummyData, 0, digestBlockSize); - } - - // One more byte in case the implementation is "lazy" about processing blocks - mac.Update(dummyData[0]); - mac.Reset(); - - return result; - } - - protected virtual int GetDigestBlockCount(int inputLength) - { - // NOTE: This calculation assumes a minimum of 1 pad byte - return (inputLength + digestOverhead) / digestBlockSize; - } - - protected virtual byte[] Truncate(byte[] bs) - { - if (bs.Length <= macLength) - { - return bs; - } - - return Arrays.CopyOf(bs, macLength); - } - } -} diff --git a/crypto/src/crypto/tls/TlsNoCloseNotifyException.cs b/crypto/src/crypto/tls/TlsNoCloseNotifyException.cs deleted file mode 100644 index 0bafd820b..000000000 --- a/crypto/src/crypto/tls/TlsNoCloseNotifyException.cs +++ /dev/null @@ -1,23 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary> - /// This exception will be thrown(only) when the connection is closed by the peer without sending a - /// <code cref="AlertDescription.close_notify">close_notify</code> warning alert. - /// </summary> - /// <remarks> - /// If this happens, the TLS protocol cannot rule out truncation of the connection data (potentially - /// malicious). It may be possible to check for truncation via some property of a higher level protocol - /// built upon TLS, e.g.the Content-Length header for HTTPS. - /// </remarks> - public class TlsNoCloseNotifyException - : EndOfStreamException - { - public TlsNoCloseNotifyException() - : base("No close_notify alert received before connection closed") - { - } - } -} diff --git a/crypto/src/crypto/tls/TlsNullCipher.cs b/crypto/src/crypto/tls/TlsNullCipher.cs deleted file mode 100644 index f30ace24f..000000000 --- a/crypto/src/crypto/tls/TlsNullCipher.cs +++ /dev/null @@ -1,118 +0,0 @@ -using System; -using System.IO; - -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary> - /// A NULL CipherSuite, with optional MAC. - /// </summary> - public class TlsNullCipher - : TlsCipher - { - protected readonly TlsContext context; - - protected readonly TlsMac writeMac; - protected readonly TlsMac readMac; - - public TlsNullCipher(TlsContext context) - { - this.context = context; - this.writeMac = null; - this.readMac = null; - } - - /// <exception cref="IOException"></exception> - public TlsNullCipher(TlsContext context, IDigest clientWriteDigest, IDigest serverWriteDigest) - { - if ((clientWriteDigest == null) != (serverWriteDigest == null)) - throw new TlsFatalAlert(AlertDescription.internal_error); - - this.context = context; - - TlsMac clientWriteMac = null, serverWriteMac = null; - - if (clientWriteDigest != null) - { - int key_block_size = clientWriteDigest.GetDigestSize() - + serverWriteDigest.GetDigestSize(); - byte[] key_block = TlsUtilities.CalculateKeyBlock(context, key_block_size); - - int offset = 0; - - clientWriteMac = new TlsMac(context, clientWriteDigest, key_block, offset, - clientWriteDigest.GetDigestSize()); - offset += clientWriteDigest.GetDigestSize(); - - serverWriteMac = new TlsMac(context, serverWriteDigest, key_block, offset, - serverWriteDigest.GetDigestSize()); - offset += serverWriteDigest.GetDigestSize(); - - if (offset != key_block_size) - { - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } - - if (context.IsServer) - { - writeMac = serverWriteMac; - readMac = clientWriteMac; - } - else - { - writeMac = clientWriteMac; - readMac = serverWriteMac; - } - } - - public virtual int GetPlaintextLimit(int ciphertextLimit) - { - int result = ciphertextLimit; - if (writeMac != null) - { - result -= writeMac.Size; - } - return result; - } - - /// <exception cref="IOException"></exception> - public virtual byte[] EncodePlaintext(long seqNo, byte type, byte[] plaintext, int offset, int len) - { - if (writeMac == null) - { - return Arrays.CopyOfRange(plaintext, offset, offset + len); - } - - byte[] mac = writeMac.CalculateMac(seqNo, type, plaintext, offset, len); - byte[] ciphertext = new byte[len + mac.Length]; - Array.Copy(plaintext, offset, ciphertext, 0, len); - Array.Copy(mac, 0, ciphertext, len, mac.Length); - return ciphertext; - } - - /// <exception cref="IOException"></exception> - public virtual byte[] DecodeCiphertext(long seqNo, byte type, byte[] ciphertext, int offset, int len) - { - if (readMac == null) - { - return Arrays.CopyOfRange(ciphertext, offset, offset + len); - } - - int macSize = readMac.Size; - if (len < macSize) - throw new TlsFatalAlert(AlertDescription.decode_error); - - int macInputLen = len - macSize; - - byte[] receivedMac = Arrays.CopyOfRange(ciphertext, offset + macInputLen, offset + len); - byte[] computedMac = readMac.CalculateMac(seqNo, type, ciphertext, offset, macInputLen); - - if (!Arrays.ConstantTimeAreEqual(receivedMac, computedMac)) - throw new TlsFatalAlert(AlertDescription.bad_record_mac); - - return Arrays.CopyOfRange(ciphertext, offset, offset + macInputLen); - } - } -} diff --git a/crypto/src/crypto/tls/TlsNullCompression.cs b/crypto/src/crypto/tls/TlsNullCompression.cs deleted file mode 100644 index 45f8fc708..000000000 --- a/crypto/src/crypto/tls/TlsNullCompression.cs +++ /dev/null @@ -1,19 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class TlsNullCompression - : TlsCompression - { - public virtual Stream Compress(Stream output) - { - return output; - } - - public virtual Stream Decompress(Stream output) - { - return output; - } - } -} diff --git a/crypto/src/crypto/tls/TlsPeer.cs b/crypto/src/crypto/tls/TlsPeer.cs deleted file mode 100644 index 817871b14..000000000 --- a/crypto/src/crypto/tls/TlsPeer.cs +++ /dev/null @@ -1,91 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public interface TlsPeer - { - void NotifyCloseHandle(TlsCloseable closehandle); - - /// <exception cref="IOException"/> - void Cancel(); - - /// <summary> - /// Specify the timeout, in milliseconds, to use for the complete handshake process. - /// </summary> - /// <remarks> - /// Negative values are not allowed. A timeout of zero means an infinite timeout (i.e. the - /// handshake will never time out). NOTE: Currently only respected by DTLS protocols. - /// </remarks> - int GetHandshakeTimeoutMillis(); - - /// <summary> - /// This implementation supports RFC 7627 and will always negotiate the extended_master_secret - /// extension where possible. - /// </summary> - /// <remarks> - /// When connecting to a peer that does not offer/accept this extension, it is recommended to - /// abort the handshake. This option is provided for interoperability with legacy peers, - /// although some TLS features will be disabled in that case (see RFC 7627 5.4). - /// </remarks> - /// <returns> - /// <code>true</code> if the handshake should be aborted when the peer does not negotiate the - /// extended_master_secret extension, or <code>false</code> to support legacy interoperability. - /// </returns> - bool RequiresExtendedMasterSecret(); - - /// <summary> - /// draft-mathewson-no-gmtunixtime-00 2. "If existing users of a TLS implementation may rely on - /// gmt_unix_time containing the current time, we recommend that implementors MAY provide the - /// ability to set gmt_unix_time as an option only, off by default." - /// </summary> - /// <returns> - /// <code>true</code> if the current time should be used in the gmt_unix_time field of - /// Random, or <code>false</code> if gmt_unix_time should contain a cryptographically - /// random value. - /// </returns> - bool ShouldUseGmtUnixTime(); - - /// <summary> - /// Report whether the server supports secure renegotiation - /// </summary> - /// <remarks> - /// The protocol handler automatically processes the relevant extensions - /// </remarks> - /// <param name="secureRenegotiation"> - /// A <see cref="System.Boolean"/>, true if the server supports secure renegotiation - /// </param> - /// <exception cref="IOException"></exception> - void NotifySecureRenegotiation(bool secureRenegotiation); - - /// <summary> - /// Return an implementation of <see cref="TlsCompression"/> to handle record compression. - /// </summary> - /// <returns>A <see cref="TlsCompression"/></returns> - /// <exception cref="IOException"/> - TlsCompression GetCompression(); - - /// <summary> - /// Return an implementation of <see cref="TlsCipher"/> to use for encryption/decryption. - /// </summary> - /// <returns>A <see cref="TlsCipher"/></returns> - /// <exception cref="IOException"/> - TlsCipher GetCipher(); - - /// <summary>This method will be called when an alert is raised by the protocol.</summary> - /// <param name="alertLevel"><see cref="AlertLevel"/></param> - /// <param name="alertDescription"><see cref="AlertDescription"/></param> - /// <param name="message">A human-readable message explaining what caused this alert. May be null.</param> - /// <param name="cause">The <c>Exception</c> that caused this alert to be raised. May be null.</param> - void NotifyAlertRaised(byte alertLevel, byte alertDescription, string message, Exception cause); - - /// <summary>This method will be called when an alert is received from the remote peer.</summary> - /// <param name="alertLevel"><see cref="AlertLevel"/></param> - /// <param name="alertDescription"><see cref="AlertDescription"/></param> - void NotifyAlertReceived(byte alertLevel, byte alertDescription); - - /// <summary>Notifies the peer that the handshake has been successfully completed.</summary> - /// <exception cref="IOException"></exception> - void NotifyHandshakeComplete(); - } -} diff --git a/crypto/src/crypto/tls/TlsProtocol.cs b/crypto/src/crypto/tls/TlsProtocol.cs deleted file mode 100644 index 9e5d5c12e..000000000 --- a/crypto/src/crypto/tls/TlsProtocol.cs +++ /dev/null @@ -1,1448 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Crypto.Prng; -using Org.BouncyCastle.Security; -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class TlsProtocol - : TlsCloseable - { - /* - * Our Connection states - */ - protected const short CS_START = 0; - protected const short CS_CLIENT_HELLO = 1; - protected const short CS_SERVER_HELLO = 2; - protected const short CS_SERVER_SUPPLEMENTAL_DATA = 3; - protected const short CS_SERVER_CERTIFICATE = 4; - protected const short CS_CERTIFICATE_STATUS = 5; - protected const short CS_SERVER_KEY_EXCHANGE = 6; - protected const short CS_CERTIFICATE_REQUEST = 7; - protected const short CS_SERVER_HELLO_DONE = 8; - protected const short CS_CLIENT_SUPPLEMENTAL_DATA = 9; - protected const short CS_CLIENT_CERTIFICATE = 10; - protected const short CS_CLIENT_KEY_EXCHANGE = 11; - protected const short CS_CERTIFICATE_VERIFY = 12; - protected const short CS_CLIENT_FINISHED = 13; - protected const short CS_SERVER_SESSION_TICKET = 14; - protected const short CS_SERVER_FINISHED = 15; - protected const short CS_END = 16; - - /* - * Different modes to handle the known IV weakness - */ - protected const short ADS_MODE_1_Nsub1 = 0; // 1/n-1 record splitting - protected const short ADS_MODE_0_N = 1; // 0/n record splitting - protected const short ADS_MODE_0_N_FIRSTONLY = 2; // 0/n record splitting on first data fragment only - - /* - * Queues for data from some protocols. - */ - private ByteQueue mApplicationDataQueue = new ByteQueue(0); - private ByteQueue mAlertQueue = new ByteQueue(2); - private ByteQueue mHandshakeQueue = new ByteQueue(0); - // private ByteQueue mHeartbeatQueue = new ByteQueue(); - - /* - * The Record Stream we use - */ - internal RecordStream mRecordStream; - protected SecureRandom mSecureRandom; - - private TlsStream mTlsStream = null; - - private volatile bool mClosed = false; - private volatile bool mFailedWithError = false; - private volatile bool mAppDataReady = false; - private volatile bool mAppDataSplitEnabled = true; - private volatile int mAppDataSplitMode = ADS_MODE_1_Nsub1; - private byte[] mExpectedVerifyData = null; - - protected TlsSession mTlsSession = null; - protected SessionParameters mSessionParameters = null; - protected SecurityParameters mSecurityParameters = null; - protected Certificate mPeerCertificate = null; - - protected int[] mOfferedCipherSuites = null; - protected byte[] mOfferedCompressionMethods = null; - protected IDictionary mClientExtensions = null; - protected IDictionary mServerExtensions = null; - - protected short mConnectionState = CS_START; - protected bool mResumedSession = false; - protected bool mReceivedChangeCipherSpec = false; - protected bool mSecureRenegotiation = false; - protected bool mAllowCertificateStatus = false; - protected bool mExpectSessionTicket = false; - - protected bool mBlocking = true; - protected ByteQueueStream mInputBuffers = null; - protected ByteQueueStream mOutputBuffer = null; - - public TlsProtocol(Stream stream, SecureRandom secureRandom) - : this(stream, stream, secureRandom) - { - } - - public TlsProtocol(Stream input, Stream output, SecureRandom secureRandom) - { - this.mRecordStream = new RecordStream(this, input, output); - this.mSecureRandom = secureRandom; - } - - public TlsProtocol(SecureRandom secureRandom) - { - this.mBlocking = false; - this.mInputBuffers = new ByteQueueStream(); - this.mOutputBuffer = new ByteQueueStream(); - this.mRecordStream = new RecordStream(this, mInputBuffers, mOutputBuffer); - this.mSecureRandom = secureRandom; - } - - protected abstract TlsContext Context { get; } - - internal abstract AbstractTlsContext ContextAdmin { get; } - - protected abstract TlsPeer Peer { get; } - - protected virtual void HandleAlertMessage(byte alertLevel, byte alertDescription) - { - Peer.NotifyAlertReceived(alertLevel, alertDescription); - - if (alertLevel == AlertLevel.warning) - { - HandleAlertWarningMessage(alertDescription); - } - else - { - HandleFailure(); - - throw new TlsFatalAlertReceived(alertDescription); - } - } - - protected virtual void HandleAlertWarningMessage(byte alertDescription) - { - /* - * RFC 5246 7.2.1. The other party MUST respond with a close_notify alert of its own - * and close down the connection immediately, discarding any pending writes. - */ - if (alertDescription == AlertDescription.close_notify) - { - if (!mAppDataReady) - throw new TlsFatalAlert(AlertDescription.handshake_failure); - - HandleClose(false); - } - } - - protected virtual void HandleChangeCipherSpecMessage() - { - } - - protected virtual void HandleClose(bool user_canceled) - { - if (!mClosed) - { - this.mClosed = true; - - if (user_canceled && !mAppDataReady) - { - RaiseAlertWarning(AlertDescription.user_canceled, "User canceled handshake"); - } - - RaiseAlertWarning(AlertDescription.close_notify, "Connection closed"); - - mRecordStream.SafeClose(); - - if (!mAppDataReady) - { - CleanupHandshake(); - } - } - } - - protected virtual void HandleException(byte alertDescription, string message, Exception cause) - { - if (!mClosed) - { - RaiseAlertFatal(alertDescription, message, cause); - - HandleFailure(); - } - } - - protected virtual void HandleFailure() - { - this.mClosed = true; - this.mFailedWithError = true; - - /* - * RFC 2246 7.2.1. The session becomes unresumable if any connection is terminated - * without proper close_notify messages with level equal to warning. - */ - // TODO This isn't quite in the right place. Also, as of TLS 1.1 the above is obsolete. - InvalidateSession(); - - mRecordStream.SafeClose(); - - if (!mAppDataReady) - { - CleanupHandshake(); - } - } - - protected abstract void HandleHandshakeMessage(byte type, MemoryStream buf); - - protected virtual void ApplyMaxFragmentLengthExtension() - { - if (mSecurityParameters.maxFragmentLength >= 0) - { - if (!MaxFragmentLength.IsValid((byte)mSecurityParameters.maxFragmentLength)) - throw new TlsFatalAlert(AlertDescription.internal_error); - - int plainTextLimit = 1 << (8 + mSecurityParameters.maxFragmentLength); - mRecordStream.SetPlaintextLimit(plainTextLimit); - } - } - - protected virtual void CheckReceivedChangeCipherSpec(bool expected) - { - if (expected != mReceivedChangeCipherSpec) - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - - protected virtual void CleanupHandshake() - { - if (this.mExpectedVerifyData != null) - { - Arrays.Fill(this.mExpectedVerifyData, (byte)0); - this.mExpectedVerifyData = null; - } - - this.mSecurityParameters.Clear(); - this.mPeerCertificate = null; - - this.mOfferedCipherSuites = null; - this.mOfferedCompressionMethods = null; - this.mClientExtensions = null; - this.mServerExtensions = null; - - this.mResumedSession = false; - this.mReceivedChangeCipherSpec = false; - this.mSecureRenegotiation = false; - this.mAllowCertificateStatus = false; - this.mExpectSessionTicket = false; - } - - protected virtual void BlockForHandshake() - { - if (mBlocking) - { - while (this.mConnectionState != CS_END) - { - if (this.mClosed) - { - // NOTE: Any close during the handshake should have raised an exception. - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - SafeReadRecord(); - } - } - } - - protected virtual void CompleteHandshake() - { - try - { - this.mConnectionState = CS_END; - - this.mAlertQueue.Shrink(); - this.mHandshakeQueue.Shrink(); - - this.mRecordStream.FinaliseHandshake(); - - this.mAppDataSplitEnabled = !TlsUtilities.IsTlsV11(Context); - - /* - * If this was an initial handshake, we are now ready to send and receive application data. - */ - if (!mAppDataReady) - { - this.mAppDataReady = true; - - if (mBlocking) - { - this.mTlsStream = new TlsStream(this); - } - } - - if (this.mTlsSession != null) - { - if (this.mSessionParameters == null) - { - this.mSessionParameters = new SessionParameters.Builder() - .SetCipherSuite(this.mSecurityParameters.CipherSuite) - .SetCompressionAlgorithm(this.mSecurityParameters.CompressionAlgorithm) - .SetExtendedMasterSecret(this.mSecurityParameters.IsExtendedMasterSecret) - .SetMasterSecret(this.mSecurityParameters.MasterSecret) - .SetPeerCertificate(this.mPeerCertificate) - .SetPskIdentity(this.mSecurityParameters.PskIdentity) - .SetSrpIdentity(this.mSecurityParameters.SrpIdentity) - // TODO Consider filtering extensions that aren't relevant to resumed sessions - .SetServerExtensions(this.mServerExtensions) - .Build(); - - this.mTlsSession = new TlsSessionImpl(this.mTlsSession.SessionID, this.mSessionParameters); - } - - ContextAdmin.SetResumableSession(this.mTlsSession); - } - - Peer.NotifyHandshakeComplete(); - } - finally - { - CleanupHandshake(); - } - } - - protected internal void ProcessRecord(byte protocol, byte[] buf, int off, int len) - { - /* - * Have a look at the protocol type, and add it to the correct queue. - */ - switch (protocol) - { - case ContentType.alert: - { - mAlertQueue.AddData(buf, off, len); - ProcessAlertQueue(); - break; - } - case ContentType.application_data: - { - if (!mAppDataReady) - throw new TlsFatalAlert(AlertDescription.unexpected_message); - - mApplicationDataQueue.AddData(buf, off, len); - ProcessApplicationDataQueue(); - break; - } - case ContentType.change_cipher_spec: - { - ProcessChangeCipherSpec(buf, off, len); - break; - } - case ContentType.handshake: - { - if (mHandshakeQueue.Available > 0) - { - mHandshakeQueue.AddData(buf, off, len); - ProcessHandshakeQueue(mHandshakeQueue); - } - else - { - ByteQueue tmpQueue = new ByteQueue(buf, off, len); - ProcessHandshakeQueue(tmpQueue); - int remaining = tmpQueue.Available; - if (remaining > 0) - { - mHandshakeQueue.AddData(buf, off + len - remaining, remaining); - } - } - break; - } - //case ContentType.heartbeat: - //{ - // if (!mAppDataReady) - // throw new TlsFatalAlert(AlertDescription.unexpected_message); - - // // TODO[RFC 6520] - // //mHeartbeatQueue.AddData(buf, offset, len); - // //ProcessHeartbeat(); - // break; - //} - default: - // Record type should already have been checked - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } - - private void ProcessHandshakeQueue(ByteQueue queue) - { - while (queue.Available >= 4) - { - /* - * We need the first 4 bytes, they contain type and length of the message. - */ - byte[] beginning = new byte[4]; - queue.Read(beginning, 0, 4, 0); - byte type = TlsUtilities.ReadUint8(beginning, 0); - int length = TlsUtilities.ReadUint24(beginning, 1); - int totalLength = 4 + length; - - /* - * Check if we have enough bytes in the buffer to read the full message. - */ - if (queue.Available < totalLength) - break; - - /* - * RFC 2246 7.4.9. The value handshake_messages includes all handshake messages - * starting at client hello up to, but not including, this finished message. - * [..] Note: [Also,] Hello Request messages are omitted from handshake hashes. - */ - if (HandshakeType.hello_request != type) - { - if (HandshakeType.finished == type) - { - CheckReceivedChangeCipherSpec(true); - - TlsContext ctx = Context; - if (this.mExpectedVerifyData == null - && ctx.SecurityParameters.MasterSecret != null) - { - this.mExpectedVerifyData = CreateVerifyData(!ctx.IsServer); - } - } - else - { - CheckReceivedChangeCipherSpec(mConnectionState == CS_END); - } - - queue.CopyTo(mRecordStream.HandshakeHashUpdater, totalLength); - } - - queue.RemoveData(4); - - MemoryStream buf = queue.ReadFrom(length); - - /* - * Now, parse the message. - */ - HandleHandshakeMessage(type, buf); - } - } - - private void ProcessApplicationDataQueue() - { - /* - * There is nothing we need to do here. - * - * This function could be used for callbacks when application data arrives in the future. - */ - } - - private void ProcessAlertQueue() - { - while (mAlertQueue.Available >= 2) - { - /* - * An alert is always 2 bytes. Read the alert. - */ - byte[] alert = mAlertQueue.RemoveData(2, 0); - byte alertLevel = alert[0]; - byte alertDescription = alert[1]; - - HandleAlertMessage(alertLevel, alertDescription); - } - } - - /** - * This method is called, when a change cipher spec message is received. - * - * @throws IOException If the message has an invalid content or the handshake is not in the correct - * state. - */ - private void ProcessChangeCipherSpec(byte[] buf, int off, int len) - { - for (int i = 0; i < len; ++i) - { - byte message = TlsUtilities.ReadUint8(buf, off + i); - - if (message != ChangeCipherSpec.change_cipher_spec) - throw new TlsFatalAlert(AlertDescription.decode_error); - - if (this.mReceivedChangeCipherSpec - || mAlertQueue.Available > 0 - || mHandshakeQueue.Available > 0) - { - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - - mRecordStream.ReceivedReadCipherSpec(); - - this.mReceivedChangeCipherSpec = true; - - HandleChangeCipherSpecMessage(); - } - } - - protected internal virtual int ApplicationDataAvailable() - { - return mApplicationDataQueue.Available; - } - - /** - * Read data from the network. The method will return immediately, if there is still some data - * left in the buffer, or block until some application data has been read from the network. - * - * @param buf The buffer where the data will be copied to. - * @param offset The position where the data will be placed in the buffer. - * @param len The maximum number of bytes to read. - * @return The number of bytes read. - * @throws IOException If something goes wrong during reading data. - */ - protected internal virtual int ReadApplicationData(byte[] buf, int offset, int len) - { - if (len < 1) - return 0; - - while (mApplicationDataQueue.Available == 0) - { - if (this.mClosed) - { - if (this.mFailedWithError) - throw new IOException("Cannot read application data on failed TLS connection"); - - if (!mAppDataReady) - throw new InvalidOperationException("Cannot read application data until initial handshake completed."); - - return 0; - } - - SafeReadRecord(); - } - - len = System.Math.Min(len, mApplicationDataQueue.Available); - mApplicationDataQueue.RemoveData(buf, offset, len, 0); - return len; - } - - protected virtual void SafeCheckRecordHeader(byte[] recordHeader) - { - try - { - mRecordStream.CheckRecordHeader(recordHeader); - } - catch (TlsFatalAlert e) - { - HandleException(e.AlertDescription, "Failed to read record", e); - throw e; - } - catch (IOException e) - { - HandleException(AlertDescription.internal_error, "Failed to read record", e); - throw e; - } - catch (Exception e) - { - HandleException(AlertDescription.internal_error, "Failed to read record", e); - throw new TlsFatalAlert(AlertDescription.internal_error, e); - } - } - - protected virtual void SafeReadRecord() - { - try - { - if (mRecordStream.ReadRecord()) - return; - - if (!mAppDataReady) - throw new TlsFatalAlert(AlertDescription.handshake_failure); - } - catch (TlsFatalAlertReceived e) - { - // Connection failure already handled at source - throw e; - } - catch (TlsFatalAlert e) - { - HandleException(e.AlertDescription, "Failed to read record", e); - throw e; - } - catch (IOException e) - { - HandleException(AlertDescription.internal_error, "Failed to read record", e); - throw e; - } - catch (Exception e) - { - HandleException(AlertDescription.internal_error, "Failed to read record", e); - throw new TlsFatalAlert(AlertDescription.internal_error, e); - } - - HandleFailure(); - - throw new TlsNoCloseNotifyException(); - } - - protected virtual void SafeWriteRecord(byte type, byte[] buf, int offset, int len) - { - try - { - mRecordStream.WriteRecord(type, buf, offset, len); - } - catch (TlsFatalAlert e) - { - HandleException(e.AlertDescription, "Failed to write record", e); - throw e; - } - catch (IOException e) - { - HandleException(AlertDescription.internal_error, "Failed to write record", e); - throw e; - } - catch (Exception e) - { - HandleException(AlertDescription.internal_error, "Failed to write record", e); - throw new TlsFatalAlert(AlertDescription.internal_error, e); - } - } - - /** - * Send some application data to the remote system. - * <p/> - * The method will handle fragmentation internally. - * - * @param buf The buffer with the data. - * @param offset The position in the buffer where the data is placed. - * @param len The length of the data. - * @throws IOException If something goes wrong during sending. - */ - protected internal virtual void WriteData(byte[] buf, int offset, int len) - { - if (this.mClosed) - throw new IOException("Cannot write application data on closed/failed TLS connection"); - - while (len > 0) - { - /* - * RFC 5246 6.2.1. Zero-length fragments of Application data MAY be sent as they are - * potentially useful as a traffic analysis countermeasure. - * - * NOTE: Actually, implementations appear to have settled on 1/n-1 record splitting. - */ - - if (this.mAppDataSplitEnabled) - { - /* - * Protect against known IV attack! - * - * DO NOT REMOVE THIS CODE, EXCEPT YOU KNOW EXACTLY WHAT YOU ARE DOING HERE. - */ - switch (mAppDataSplitMode) - { - case ADS_MODE_0_N: - SafeWriteRecord(ContentType.application_data, TlsUtilities.EmptyBytes, 0, 0); - break; - case ADS_MODE_0_N_FIRSTONLY: - this.mAppDataSplitEnabled = false; - SafeWriteRecord(ContentType.application_data, TlsUtilities.EmptyBytes, 0, 0); - break; - case ADS_MODE_1_Nsub1: - default: - SafeWriteRecord(ContentType.application_data, buf, offset, 1); - ++offset; - --len; - break; - } - } - - if (len > 0) - { - // Fragment data according to the current fragment limit. - int toWrite = System.Math.Min(len, mRecordStream.GetPlaintextLimit()); - SafeWriteRecord(ContentType.application_data, buf, offset, toWrite); - offset += toWrite; - len -= toWrite; - } - } - } - - protected virtual void SetAppDataSplitMode(int appDataSplitMode) - { - if (appDataSplitMode < ADS_MODE_1_Nsub1 || appDataSplitMode > ADS_MODE_0_N_FIRSTONLY) - throw new ArgumentException("Illegal appDataSplitMode mode: " + appDataSplitMode, "appDataSplitMode"); - - this.mAppDataSplitMode = appDataSplitMode; - } - - protected virtual void WriteHandshakeMessage(byte[] buf, int off, int len) - { - if (len < 4) - throw new TlsFatalAlert(AlertDescription.internal_error); - - byte type = TlsUtilities.ReadUint8(buf, off); - if (type != HandshakeType.hello_request) - { - mRecordStream.HandshakeHashUpdater.Write(buf, off, len); - } - - int total = 0; - do - { - // Fragment data according to the current fragment limit. - int toWrite = System.Math.Min(len - total, mRecordStream.GetPlaintextLimit()); - SafeWriteRecord(ContentType.handshake, buf, off + total, toWrite); - total += toWrite; - } - while (total < len); - } - - /// <summary>The secure bidirectional stream for this connection</summary> - /// <remarks>Only allowed in blocking mode.</remarks> - public virtual Stream Stream - { - get - { - if (!mBlocking) - throw new InvalidOperationException("Cannot use Stream in non-blocking mode! Use OfferInput()/OfferOutput() instead."); - return this.mTlsStream; - } - } - - /** - * Should be called in non-blocking mode when the input data reaches EOF. - */ - public virtual void CloseInput() - { - if (mBlocking) - throw new InvalidOperationException("Cannot use CloseInput() in blocking mode!"); - - if (mClosed) - return; - - if (mInputBuffers.Available > 0) - throw new EndOfStreamException(); - - if (!mAppDataReady) - throw new TlsFatalAlert(AlertDescription.handshake_failure); - - throw new TlsNoCloseNotifyException(); - } - - /** - * Equivalent to <code>OfferInput(input, 0, input.length)</code> - * @see TlsProtocol#OfferInput(byte[], int, int) - * @param input The input buffer to offer - * @throws IOException If an error occurs while decrypting or processing a record - */ - public virtual void OfferInput(byte[] input) - { - OfferInput(input, 0, input.Length); - } - - /** - * Offer input from an arbitrary source. Only allowed in non-blocking mode.<br/> - * <br/> - * This method will decrypt and process all records that are fully available. - * If only part of a record is available, the buffer will be retained until the - * remainder of the record is offered.<br/> - * <br/> - * If any records containing application data were processed, the decrypted data - * can be obtained using {@link #readInput(byte[], int, int)}. If any records - * containing protocol data were processed, a response may have been generated. - * You should always check to see if there is any available output after calling - * this method by calling {@link #getAvailableOutputBytes()}. - * @param input The input buffer to offer - * @param inputOff The offset within the input buffer that input begins - * @param inputLen The number of bytes of input being offered - * @throws IOException If an error occurs while decrypting or processing a record - */ - public virtual void OfferInput(byte[] input, int inputOff, int inputLen) - { - if (mBlocking) - throw new InvalidOperationException("Cannot use OfferInput() in blocking mode! Use Stream instead."); - if (mClosed) - throw new IOException("Connection is closed, cannot accept any more input"); - - mInputBuffers.Write(input, inputOff, inputLen); - - // loop while there are enough bytes to read the length of the next record - while (mInputBuffers.Available >= RecordStream.TLS_HEADER_SIZE) - { - byte[] recordHeader = new byte[RecordStream.TLS_HEADER_SIZE]; - mInputBuffers.Peek(recordHeader); - - int totalLength = TlsUtilities.ReadUint16(recordHeader, RecordStream.TLS_HEADER_LENGTH_OFFSET) + RecordStream.TLS_HEADER_SIZE; - if (mInputBuffers.Available < totalLength) - { - // not enough bytes to read a whole record - SafeCheckRecordHeader(recordHeader); - break; - } - - SafeReadRecord(); - - if (mClosed) - { - if (mConnectionState != CS_END) - { - // NOTE: Any close during the handshake should have raised an exception. - throw new TlsFatalAlert(AlertDescription.internal_error); - } - break; - } - } - } - - /** - * Gets the amount of received application data. A call to {@link #readInput(byte[], int, int)} - * is guaranteed to be able to return at least this much data.<br/> - * <br/> - * Only allowed in non-blocking mode. - * @return The number of bytes of available application data - */ - public virtual int GetAvailableInputBytes() - { - if (mBlocking) - throw new InvalidOperationException("Cannot use GetAvailableInputBytes() in blocking mode! Use ApplicationDataAvailable() instead."); - - return ApplicationDataAvailable(); - } - - /** - * Retrieves received application data. Use {@link #getAvailableInputBytes()} to check - * how much application data is currently available. This method functions similarly to - * {@link InputStream#read(byte[], int, int)}, except that it never blocks. If no data - * is available, nothing will be copied and zero will be returned.<br/> - * <br/> - * Only allowed in non-blocking mode. - * @param buffer The buffer to hold the application data - * @param offset The start offset in the buffer at which the data is written - * @param length The maximum number of bytes to read - * @return The total number of bytes copied to the buffer. May be less than the - * length specified if the length was greater than the amount of available data. - */ - public virtual int ReadInput(byte[] buffer, int offset, int length) - { - if (mBlocking) - throw new InvalidOperationException("Cannot use ReadInput() in blocking mode! Use Stream instead."); - - return ReadApplicationData(buffer, offset, System.Math.Min(length, ApplicationDataAvailable())); - } - - /** - * Offer output from an arbitrary source. Only allowed in non-blocking mode.<br/> - * <br/> - * After this method returns, the specified section of the buffer will have been - * processed. Use {@link #readOutput(byte[], int, int)} to get the bytes to - * transmit to the other peer.<br/> - * <br/> - * This method must not be called until after the handshake is complete! Attempting - * to call it before the handshake is complete will result in an exception. - * @param buffer The buffer containing application data to encrypt - * @param offset The offset at which to begin reading data - * @param length The number of bytes of data to read - * @throws IOException If an error occurs encrypting the data, or the handshake is not complete - */ - public virtual void OfferOutput(byte[] buffer, int offset, int length) - { - if (mBlocking) - throw new InvalidOperationException("Cannot use OfferOutput() in blocking mode! Use Stream instead."); - if (!mAppDataReady) - throw new IOException("Application data cannot be sent until the handshake is complete!"); - - WriteData(buffer, offset, length); - } - - /** - * Gets the amount of encrypted data available to be sent. A call to - * {@link #readOutput(byte[], int, int)} is guaranteed to be able to return at - * least this much data.<br/> - * <br/> - * Only allowed in non-blocking mode. - * @return The number of bytes of available encrypted data - */ - public virtual int GetAvailableOutputBytes() - { - if (mBlocking) - throw new InvalidOperationException("Cannot use GetAvailableOutputBytes() in blocking mode! Use Stream instead."); - - return mOutputBuffer.Available; - } - - /** - * Retrieves encrypted data to be sent. Use {@link #getAvailableOutputBytes()} to check - * how much encrypted data is currently available. This method functions similarly to - * {@link InputStream#read(byte[], int, int)}, except that it never blocks. If no data - * is available, nothing will be copied and zero will be returned.<br/> - * <br/> - * Only allowed in non-blocking mode. - * @param buffer The buffer to hold the encrypted data - * @param offset The start offset in the buffer at which the data is written - * @param length The maximum number of bytes to read - * @return The total number of bytes copied to the buffer. May be less than the - * length specified if the length was greater than the amount of available data. - */ - public virtual int ReadOutput(byte[] buffer, int offset, int length) - { - if (mBlocking) - throw new InvalidOperationException("Cannot use ReadOutput() in blocking mode! Use Stream instead."); - - return mOutputBuffer.Read(buffer, offset, length); - } - - protected virtual void InvalidateSession() - { - if (this.mSessionParameters != null) - { - this.mSessionParameters.Clear(); - this.mSessionParameters = null; - } - - if (this.mTlsSession != null) - { - this.mTlsSession.Invalidate(); - this.mTlsSession = null; - } - } - - protected virtual void ProcessFinishedMessage(MemoryStream buf) - { - if (mExpectedVerifyData == null) - throw new TlsFatalAlert(AlertDescription.internal_error); - - byte[] verify_data = TlsUtilities.ReadFully(mExpectedVerifyData.Length, buf); - - AssertEmpty(buf); - - /* - * Compare both checksums. - */ - if (!Arrays.ConstantTimeAreEqual(mExpectedVerifyData, verify_data)) - { - /* - * Wrong checksum in the finished message. - */ - throw new TlsFatalAlert(AlertDescription.decrypt_error); - } - } - - protected virtual void RaiseAlertFatal(byte alertDescription, string message, Exception cause) - { - Peer.NotifyAlertRaised(AlertLevel.fatal, alertDescription, message, cause); - - byte[] alert = new byte[]{ AlertLevel.fatal, alertDescription }; - - try - { - mRecordStream.WriteRecord(ContentType.alert, alert, 0, 2); - } - catch (Exception) - { - // We are already processing an exception, so just ignore this - } - } - - protected virtual void RaiseAlertWarning(byte alertDescription, string message) - { - Peer.NotifyAlertRaised(AlertLevel.warning, alertDescription, message, null); - - byte[] alert = new byte[]{ AlertLevel.warning, alertDescription }; - - SafeWriteRecord(ContentType.alert, alert, 0, 2); - } - - protected virtual void SendCertificateMessage(Certificate certificate) - { - if (certificate == null) - { - certificate = Certificate.EmptyChain; - } - - if (certificate.IsEmpty) - { - TlsContext context = Context; - if (!context.IsServer) - { - ProtocolVersion serverVersion = Context.ServerVersion; - if (serverVersion.IsSsl) - { - string errorMessage = serverVersion.ToString() + " client didn't provide credentials"; - RaiseAlertWarning(AlertDescription.no_certificate, errorMessage); - return; - } - } - } - - HandshakeMessage message = new HandshakeMessage(HandshakeType.certificate); - - certificate.Encode(message); - - message.WriteToRecordStream(this); - } - - protected virtual void SendChangeCipherSpecMessage() - { - byte[] message = new byte[]{ 1 }; - SafeWriteRecord(ContentType.change_cipher_spec, message, 0, message.Length); - mRecordStream.SentWriteCipherSpec(); - } - - protected virtual void SendFinishedMessage() - { - byte[] verify_data = CreateVerifyData(Context.IsServer); - - HandshakeMessage message = new HandshakeMessage(HandshakeType.finished, verify_data.Length); - - message.Write(verify_data, 0, verify_data.Length); - - message.WriteToRecordStream(this); - } - - protected virtual void SendSupplementalDataMessage(IList supplementalData) - { - HandshakeMessage message = new HandshakeMessage(HandshakeType.supplemental_data); - - WriteSupplementalData(message, supplementalData); - - message.WriteToRecordStream(this); - } - - protected virtual byte[] CreateVerifyData(bool isServer) - { - TlsContext context = Context; - string asciiLabel = isServer ? ExporterLabel.server_finished : ExporterLabel.client_finished; - byte[] sslSender = isServer ? TlsUtilities.SSL_SERVER : TlsUtilities.SSL_CLIENT; - byte[] hash = GetCurrentPrfHash(context, mRecordStream.HandshakeHash, sslSender); - return TlsUtilities.CalculateVerifyData(context, asciiLabel, hash); - } - - /** - * Closes this connection. - * - * @throws IOException If something goes wrong during closing. - */ - public virtual void Close() - { - HandleClose(true); - } - - protected internal virtual void Flush() - { - mRecordStream.Flush(); - } - - public virtual bool IsClosed - { - get { return mClosed; } - } - - protected virtual short ProcessMaxFragmentLengthExtension(IDictionary clientExtensions, IDictionary serverExtensions, - byte alertDescription) - { - short maxFragmentLength = TlsExtensionsUtilities.GetMaxFragmentLengthExtension(serverExtensions); - if (maxFragmentLength >= 0) - { - if (!MaxFragmentLength.IsValid((byte)maxFragmentLength) - || (!this.mResumedSession && maxFragmentLength != TlsExtensionsUtilities - .GetMaxFragmentLengthExtension(clientExtensions))) - { - throw new TlsFatalAlert(alertDescription); - } - } - return maxFragmentLength; - } - - protected virtual void RefuseRenegotiation() - { - /* - * RFC 5746 4.5 SSLv3 clients that refuse renegotiation SHOULD use a fatal - * handshake_failure alert. - */ - if (TlsUtilities.IsSsl(Context)) - throw new TlsFatalAlert(AlertDescription.handshake_failure); - - RaiseAlertWarning(AlertDescription.no_renegotiation, "Renegotiation not supported"); - } - - /** - * Make sure the InputStream 'buf' now empty. Fail otherwise. - * - * @param buf The InputStream to check. - * @throws IOException If 'buf' is not empty. - */ - protected internal static void AssertEmpty(MemoryStream buf) - { - if (buf.Position < buf.Length) - throw new TlsFatalAlert(AlertDescription.decode_error); - } - - protected internal static byte[] CreateRandomBlock(bool useGmtUnixTime, IRandomGenerator randomGenerator) - { - byte[] result = new byte[32]; - randomGenerator.NextBytes(result); - - if (useGmtUnixTime) - { - TlsUtilities.WriteGmtUnixTime(result, 0); - } - - return result; - } - - protected internal static byte[] CreateRenegotiationInfo(byte[] renegotiated_connection) - { - return TlsUtilities.EncodeOpaque8(renegotiated_connection); - } - - protected internal static void EstablishMasterSecret(TlsContext context, TlsKeyExchange keyExchange) - { - byte[] pre_master_secret = keyExchange.GeneratePremasterSecret(); - - try - { - context.SecurityParameters.masterSecret = TlsUtilities.CalculateMasterSecret(context, pre_master_secret); - } - finally - { - // TODO Is there a way to ensure the data is really overwritten? - /* - * RFC 2246 8.1. The pre_master_secret should be deleted from memory once the - * master_secret has been computed. - */ - if (pre_master_secret != null) - { - Arrays.Fill(pre_master_secret, (byte)0); - } - } - } - - /** - * 'sender' only relevant to SSLv3 - */ - protected internal static byte[] GetCurrentPrfHash(TlsContext context, TlsHandshakeHash handshakeHash, byte[] sslSender) - { - IDigest d = handshakeHash.ForkPrfHash(); - - if (sslSender != null && TlsUtilities.IsSsl(context)) - { - d.BlockUpdate(sslSender, 0, sslSender.Length); - } - - return DigestUtilities.DoFinal(d); - } - - protected internal static IDictionary ReadExtensions(MemoryStream input) - { - if (input.Position >= input.Length) - return null; - - byte[] extBytes = TlsUtilities.ReadOpaque16(input); - - AssertEmpty(input); - - MemoryStream buf = new MemoryStream(extBytes, false); - - // Integer -> byte[] - IDictionary extensions = Platform.CreateHashtable(); - - while (buf.Position < buf.Length) - { - int extension_type = TlsUtilities.ReadUint16(buf); - byte[] extension_data = TlsUtilities.ReadOpaque16(buf); - - /* - * RFC 3546 2.3 There MUST NOT be more than one extension of the same type. - */ - if (extensions.Contains(extension_type)) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - - extensions.Add(extension_type, extension_data); - } - - return extensions; - } - - protected internal static IList ReadSupplementalDataMessage(MemoryStream input) - { - byte[] supp_data = TlsUtilities.ReadOpaque24(input); - - AssertEmpty(input); - - MemoryStream buf = new MemoryStream(supp_data, false); - - IList supplementalData = Platform.CreateArrayList(); - - while (buf.Position < buf.Length) - { - int supp_data_type = TlsUtilities.ReadUint16(buf); - byte[] data = TlsUtilities.ReadOpaque16(buf); - - supplementalData.Add(new SupplementalDataEntry(supp_data_type, data)); - } - - return supplementalData; - } - - protected internal static void WriteExtensions(Stream output, IDictionary extensions) - { - MemoryStream buf = new MemoryStream(); - - /* - * NOTE: There are reports of servers that don't accept a zero-length extension as the last - * one, so we write out any zero-length ones first as a best-effort workaround. - */ - WriteSelectedExtensions(buf, extensions, true); - WriteSelectedExtensions(buf, extensions, false); - - byte[] extBytes = buf.ToArray(); - - TlsUtilities.WriteOpaque16(extBytes, output); - } - - protected internal static void WriteSelectedExtensions(Stream output, IDictionary extensions, bool selectEmpty) - { - foreach (int extension_type in extensions.Keys) - { - byte[] extension_data = (byte[])extensions[extension_type]; - if (selectEmpty == (extension_data.Length == 0)) - { - TlsUtilities.CheckUint16(extension_type); - TlsUtilities.WriteUint16(extension_type, output); - TlsUtilities.WriteOpaque16(extension_data, output); - } - } - } - - protected internal static void WriteSupplementalData(Stream output, IList supplementalData) - { - MemoryStream buf = new MemoryStream(); - - foreach (SupplementalDataEntry entry in supplementalData) - { - int supp_data_type = entry.DataType; - TlsUtilities.CheckUint16(supp_data_type); - TlsUtilities.WriteUint16(supp_data_type, buf); - TlsUtilities.WriteOpaque16(entry.Data, buf); - } - - byte[] supp_data = buf.ToArray(); - - TlsUtilities.WriteOpaque24(supp_data, output); - } - - protected internal static int GetPrfAlgorithm(TlsContext context, int ciphersuite) - { - bool isTLSv12 = TlsUtilities.IsTlsV12(context); - - switch (ciphersuite) - { - case CipherSuite.TLS_DH_anon_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DH_anon_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DH_anon_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_DHE_PSK_WITH_AES_128_CCM: - case CipherSuite.TLS_DHE_PSK_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DHE_PSK_WITH_AES_256_CCM: - case CipherSuite.TLS_DHE_PSK_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.DRAFT_TLS_DHE_PSK_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_CCM: - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_CCM_8: - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_CCM: - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_CCM_8: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_ECDH_ECDSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_ECDH_ECDSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_ECDH_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_ECDH_RSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_CCM: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_CCM_8: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_CCM: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_CCM_8: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.DRAFT_TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.DRAFT_TLS_ECDHE_PSK_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_ECDHE_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_RSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.DRAFT_TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.TLS_PSK_DHE_WITH_AES_128_CCM_8: - case CipherSuite.TLS_PSK_DHE_WITH_AES_256_CCM_8: - case CipherSuite.TLS_PSK_WITH_AES_128_CCM: - case CipherSuite.TLS_PSK_WITH_AES_128_CCM_8: - case CipherSuite.TLS_PSK_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_PSK_WITH_AES_256_CCM: - case CipherSuite.TLS_PSK_WITH_AES_256_CCM_8: - case CipherSuite.TLS_PSK_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.DRAFT_TLS_PSK_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.TLS_RSA_PSK_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_RSA_PSK_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.DRAFT_TLS_RSA_PSK_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.TLS_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_RSA_WITH_AES_128_CCM: - case CipherSuite.TLS_RSA_WITH_AES_128_CCM_8: - case CipherSuite.TLS_RSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_RSA_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_RSA_WITH_AES_256_CCM: - case CipherSuite.TLS_RSA_WITH_AES_256_CCM_8: - case CipherSuite.TLS_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_RSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_RSA_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_RSA_WITH_NULL_SHA256: - { - if (isTLSv12) - { - return PrfAlgorithm.tls_prf_sha256; - } - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - - case CipherSuite.TLS_DH_anon_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_DH_DSS_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DH_DSS_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_DH_RSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DH_RSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_DHE_DSS_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_DHE_PSK_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DHE_PSK_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_ECDH_ECDSA_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_ECDH_ECDSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_ECDH_RSA_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_ECDH_RSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_ECDHE_RSA_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_RSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_PSK_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_PSK_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_RSA_PSK_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_RSA_PSK_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_RSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_RSA_WITH_CAMELLIA_256_GCM_SHA384: - { - if (isTLSv12) - { - return PrfAlgorithm.tls_prf_sha384; - } - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - - case CipherSuite.TLS_DHE_PSK_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_DHE_PSK_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_DHE_PSK_WITH_NULL_SHA384: - case CipherSuite.TLS_ECDHE_PSK_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_PSK_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_PSK_WITH_NULL_SHA384: - case CipherSuite.TLS_PSK_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_PSK_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_PSK_WITH_NULL_SHA384: - case CipherSuite.TLS_RSA_PSK_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_RSA_PSK_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_RSA_PSK_WITH_NULL_SHA384: - { - if (isTLSv12) - { - return PrfAlgorithm.tls_prf_sha384; - } - return PrfAlgorithm.tls_prf_legacy; - } - - default: - { - if (isTLSv12) - { - return PrfAlgorithm.tls_prf_sha256; - } - return PrfAlgorithm.tls_prf_legacy; - } - } - } - - internal class HandshakeMessage - : MemoryStream - { - internal HandshakeMessage(byte handshakeType) - : this(handshakeType, 60) - { - } - - internal HandshakeMessage(byte handshakeType, int length) - : base(length + 4) - { - TlsUtilities.WriteUint8(handshakeType, this); - // Reserve space for length - TlsUtilities.WriteUint24(0, this); - } - - internal void Write(byte[] data) - { - Write(data, 0, data.Length); - } - - internal void WriteToRecordStream(TlsProtocol protocol) - { - // Patch actual length back in - long length = Length - 4; - TlsUtilities.CheckUint24(length); - this.Position = 1; - TlsUtilities.WriteUint24((int)length, this); - -#if PORTABLE - byte[] buf = ToArray(); - int bufLen = buf.Length; -#else - byte[] buf = GetBuffer(); - int bufLen = (int)Length; -#endif - - protocol.WriteHandshakeMessage(buf, 0, bufLen); - Platform.Dispose(this); - } - } - } -} diff --git a/crypto/src/crypto/tls/TlsProtocolHandler.cs b/crypto/src/crypto/tls/TlsProtocolHandler.cs deleted file mode 100644 index 6f223467f..000000000 --- a/crypto/src/crypto/tls/TlsProtocolHandler.cs +++ /dev/null @@ -1,39 +0,0 @@ -using System; -using System.Collections; -using System.IO; -using System.Text; - -using Org.BouncyCastle.Asn1; -using Org.BouncyCastle.Asn1.X509; -using Org.BouncyCastle.Crypto.Agreement; -using Org.BouncyCastle.Crypto.Agreement.Srp; -using Org.BouncyCastle.Crypto.Digests; -using Org.BouncyCastle.Crypto.Encodings; -using Org.BouncyCastle.Crypto.Engines; -using Org.BouncyCastle.Crypto.Generators; -using Org.BouncyCastle.Crypto.IO; -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Crypto.Prng; -using Org.BouncyCastle.Math; -using Org.BouncyCastle.Security; -using Org.BouncyCastle.Utilities; -using Org.BouncyCastle.Utilities.Date; - -namespace Org.BouncyCastle.Crypto.Tls -{ - [Obsolete("Use 'TlsClientProtocol' instead")] - public class TlsProtocolHandler - : TlsClientProtocol - { - public TlsProtocolHandler(Stream stream, SecureRandom secureRandom) - : base(stream, stream, secureRandom) - { - } - - /// <remarks>Both streams can be the same object</remarks> - public TlsProtocolHandler(Stream input, Stream output, SecureRandom secureRandom) - : base(input, output, secureRandom) - { - } - } -} diff --git a/crypto/src/crypto/tls/TlsPskIdentity.cs b/crypto/src/crypto/tls/TlsPskIdentity.cs deleted file mode 100644 index 119064ee7..000000000 --- a/crypto/src/crypto/tls/TlsPskIdentity.cs +++ /dev/null @@ -1,15 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public interface TlsPskIdentity - { - void SkipIdentityHint(); - - void NotifyIdentityHint(byte[] psk_identity_hint); - - byte[] GetPskIdentity(); - - byte[] GetPsk(); - } -} diff --git a/crypto/src/crypto/tls/TlsPskIdentityManager.cs b/crypto/src/crypto/tls/TlsPskIdentityManager.cs deleted file mode 100644 index a72c2299c..000000000 --- a/crypto/src/crypto/tls/TlsPskIdentityManager.cs +++ /dev/null @@ -1,11 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public interface TlsPskIdentityManager - { - byte[] GetHint(); - - byte[] GetPsk(byte[] identity); - } -} diff --git a/crypto/src/crypto/tls/TlsPskKeyExchange.cs b/crypto/src/crypto/tls/TlsPskKeyExchange.cs deleted file mode 100644 index aec7af7b5..000000000 --- a/crypto/src/crypto/tls/TlsPskKeyExchange.cs +++ /dev/null @@ -1,334 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Asn1.X509; -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Security; -using Org.BouncyCastle.Utilities; -using Org.BouncyCastle.Utilities.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary>(D)TLS PSK key exchange (RFC 4279).</summary> - public class TlsPskKeyExchange - : AbstractTlsKeyExchange - { - protected TlsPskIdentity mPskIdentity; - protected TlsPskIdentityManager mPskIdentityManager; - - protected TlsDHVerifier mDHVerifier; - protected DHParameters mDHParameters; - protected int[] mNamedCurves; - protected byte[] mClientECPointFormats, mServerECPointFormats; - - protected byte[] mPskIdentityHint = null; - protected byte[] mPsk = null; - - protected DHPrivateKeyParameters mDHAgreePrivateKey = null; - protected DHPublicKeyParameters mDHAgreePublicKey = null; - - protected ECPrivateKeyParameters mECAgreePrivateKey = null; - protected ECPublicKeyParameters mECAgreePublicKey = null; - - protected AsymmetricKeyParameter mServerPublicKey = null; - protected RsaKeyParameters mRsaServerPublicKey = null; - protected TlsEncryptionCredentials mServerCredentials = null; - protected byte[] mPremasterSecret; - - [Obsolete("Use constructor that takes a TlsDHVerifier")] - public TlsPskKeyExchange(int keyExchange, IList supportedSignatureAlgorithms, TlsPskIdentity pskIdentity, - TlsPskIdentityManager pskIdentityManager, DHParameters dhParameters, int[] namedCurves, - byte[] clientECPointFormats, byte[] serverECPointFormats) - : this(keyExchange, supportedSignatureAlgorithms, pskIdentity, pskIdentityManager, new DefaultTlsDHVerifier(), - dhParameters, namedCurves, clientECPointFormats, serverECPointFormats) - { - } - - public TlsPskKeyExchange(int keyExchange, IList supportedSignatureAlgorithms, TlsPskIdentity pskIdentity, - TlsPskIdentityManager pskIdentityManager, TlsDHVerifier dhVerifier, DHParameters dhParameters, int[] namedCurves, - byte[] clientECPointFormats, byte[] serverECPointFormats) - : base(keyExchange, supportedSignatureAlgorithms) - { - switch (keyExchange) - { - case KeyExchangeAlgorithm.DHE_PSK: - case KeyExchangeAlgorithm.ECDHE_PSK: - case KeyExchangeAlgorithm.PSK: - case KeyExchangeAlgorithm.RSA_PSK: - break; - default: - throw new InvalidOperationException("unsupported key exchange algorithm"); - } - - this.mPskIdentity = pskIdentity; - this.mPskIdentityManager = pskIdentityManager; - this.mDHVerifier = dhVerifier; - this.mDHParameters = dhParameters; - this.mNamedCurves = namedCurves; - this.mClientECPointFormats = clientECPointFormats; - this.mServerECPointFormats = serverECPointFormats; - } - - public override void SkipServerCredentials() - { - if (mKeyExchange == KeyExchangeAlgorithm.RSA_PSK) - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - - public override void ProcessServerCredentials(TlsCredentials serverCredentials) - { - if (!(serverCredentials is TlsEncryptionCredentials)) - throw new TlsFatalAlert(AlertDescription.internal_error); - - ProcessServerCertificate(serverCredentials.Certificate); - - this.mServerCredentials = (TlsEncryptionCredentials)serverCredentials; - } - - public override byte[] GenerateServerKeyExchange() - { - this.mPskIdentityHint = mPskIdentityManager.GetHint(); - - if (this.mPskIdentityHint == null && !RequiresServerKeyExchange) - return null; - - MemoryStream buf = new MemoryStream(); - - if (this.mPskIdentityHint == null) - { - TlsUtilities.WriteOpaque16(TlsUtilities.EmptyBytes, buf); - } - else - { - TlsUtilities.WriteOpaque16(this.mPskIdentityHint, buf); - } - - if (this.mKeyExchange == KeyExchangeAlgorithm.DHE_PSK) - { - if (this.mDHParameters == null) - throw new TlsFatalAlert(AlertDescription.internal_error); - - this.mDHAgreePrivateKey = TlsDHUtilities.GenerateEphemeralServerKeyExchange(mContext.SecureRandom, - this.mDHParameters, buf); - } - else if (this.mKeyExchange == KeyExchangeAlgorithm.ECDHE_PSK) - { - this.mECAgreePrivateKey = TlsEccUtilities.GenerateEphemeralServerKeyExchange(mContext.SecureRandom, - mNamedCurves, mClientECPointFormats, buf); - } - - return buf.ToArray(); - } - - public override void ProcessServerCertificate(Certificate serverCertificate) - { - if (mKeyExchange != KeyExchangeAlgorithm.RSA_PSK) - throw new TlsFatalAlert(AlertDescription.unexpected_message); - if (serverCertificate.IsEmpty) - throw new TlsFatalAlert(AlertDescription.decode_error); - - X509CertificateStructure x509Cert = serverCertificate.GetCertificateAt(0); - - SubjectPublicKeyInfo keyInfo = x509Cert.SubjectPublicKeyInfo; - try - { - this.mServerPublicKey = PublicKeyFactory.CreateKey(keyInfo); - } - catch (Exception e) - { - throw new TlsFatalAlert(AlertDescription.unsupported_certificate, e); - } - - // Sanity check the PublicKeyFactory - if (this.mServerPublicKey.IsPrivate) - throw new TlsFatalAlert(AlertDescription.internal_error); - - this.mRsaServerPublicKey = ValidateRsaPublicKey((RsaKeyParameters)this.mServerPublicKey); - - TlsUtilities.ValidateKeyUsage(x509Cert, KeyUsage.KeyEncipherment); - - base.ProcessServerCertificate(serverCertificate); - } - - public override bool RequiresServerKeyExchange - { - get - { - switch (mKeyExchange) - { - case KeyExchangeAlgorithm.DHE_PSK: - case KeyExchangeAlgorithm.ECDHE_PSK: - return true; - default: - return false; - } - } - } - - public override void ProcessServerKeyExchange(Stream input) - { - this.mPskIdentityHint = TlsUtilities.ReadOpaque16(input); - - if (this.mKeyExchange == KeyExchangeAlgorithm.DHE_PSK) - { - this.mDHParameters = TlsDHUtilities.ReceiveDHParameters(mDHVerifier, input); - this.mDHAgreePublicKey = new DHPublicKeyParameters(TlsDHUtilities.ReadDHParameter(input), mDHParameters); - } - else if (this.mKeyExchange == KeyExchangeAlgorithm.ECDHE_PSK) - { - ECDomainParameters ecParams = TlsEccUtilities.ReadECParameters(mNamedCurves, mClientECPointFormats, input); - - byte[] point = TlsUtilities.ReadOpaque8(input); - - this.mECAgreePublicKey = TlsEccUtilities.ValidateECPublicKey(TlsEccUtilities.DeserializeECPublicKey( - mClientECPointFormats, ecParams, point)); - } - } - - public override void ValidateCertificateRequest(CertificateRequest certificateRequest) - { - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - - public override void ProcessClientCredentials(TlsCredentials clientCredentials) - { - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - public override void GenerateClientKeyExchange(Stream output) - { - if (mPskIdentityHint == null) - { - mPskIdentity.SkipIdentityHint(); - } - else - { - mPskIdentity.NotifyIdentityHint(mPskIdentityHint); - } - - byte[] psk_identity = mPskIdentity.GetPskIdentity(); - if (psk_identity == null) - throw new TlsFatalAlert(AlertDescription.internal_error); - - this.mPsk = mPskIdentity.GetPsk(); - if (mPsk == null) - throw new TlsFatalAlert(AlertDescription.internal_error); - - TlsUtilities.WriteOpaque16(psk_identity, output); - - mContext.SecurityParameters.pskIdentity = psk_identity; - - if (this.mKeyExchange == KeyExchangeAlgorithm.DHE_PSK) - { - this.mDHAgreePrivateKey = TlsDHUtilities.GenerateEphemeralClientKeyExchange(mContext.SecureRandom, - mDHParameters, output); - } - else if (this.mKeyExchange == KeyExchangeAlgorithm.ECDHE_PSK) - { - this.mECAgreePrivateKey = TlsEccUtilities.GenerateEphemeralClientKeyExchange(mContext.SecureRandom, - mServerECPointFormats, mECAgreePublicKey.Parameters, output); - } - else if (this.mKeyExchange == KeyExchangeAlgorithm.RSA_PSK) - { - this.mPremasterSecret = TlsRsaUtilities.GenerateEncryptedPreMasterSecret(mContext, - this.mRsaServerPublicKey, output); - } - } - - public override void ProcessClientKeyExchange(Stream input) - { - byte[] psk_identity = TlsUtilities.ReadOpaque16(input); - - this.mPsk = mPskIdentityManager.GetPsk(psk_identity); - if (mPsk == null) - throw new TlsFatalAlert(AlertDescription.unknown_psk_identity); - - mContext.SecurityParameters.pskIdentity = psk_identity; - - if (this.mKeyExchange == KeyExchangeAlgorithm.DHE_PSK) - { - this.mDHAgreePublicKey = new DHPublicKeyParameters(TlsDHUtilities.ReadDHParameter(input), mDHParameters); - } - else if (this.mKeyExchange == KeyExchangeAlgorithm.ECDHE_PSK) - { - byte[] point = TlsUtilities.ReadOpaque8(input); - - ECDomainParameters curve_params = this.mECAgreePrivateKey.Parameters; - - this.mECAgreePublicKey = TlsEccUtilities.ValidateECPublicKey(TlsEccUtilities.DeserializeECPublicKey( - mServerECPointFormats, curve_params, point)); - } - else if (this.mKeyExchange == KeyExchangeAlgorithm.RSA_PSK) - { - byte[] encryptedPreMasterSecret; - if (TlsUtilities.IsSsl(mContext)) - { - // TODO Do any SSLv3 clients actually include the length? - encryptedPreMasterSecret = Streams.ReadAll(input); - } - else - { - encryptedPreMasterSecret = TlsUtilities.ReadOpaque16(input); - } - - this.mPremasterSecret = mServerCredentials.DecryptPreMasterSecret(encryptedPreMasterSecret); - } - } - - public override byte[] GeneratePremasterSecret() - { - byte[] other_secret = GenerateOtherSecret(mPsk.Length); - - MemoryStream buf = new MemoryStream(4 + other_secret.Length + mPsk.Length); - TlsUtilities.WriteOpaque16(other_secret, buf); - TlsUtilities.WriteOpaque16(mPsk, buf); - - Arrays.Fill(mPsk, (byte)0); - this.mPsk = null; - - return buf.ToArray(); - } - - protected virtual byte[] GenerateOtherSecret(int pskLength) - { - if (this.mKeyExchange == KeyExchangeAlgorithm.DHE_PSK) - { - if (mDHAgreePrivateKey != null) - { - return TlsDHUtilities.CalculateDHBasicAgreement(mDHAgreePublicKey, mDHAgreePrivateKey); - } - - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - if (this.mKeyExchange == KeyExchangeAlgorithm.ECDHE_PSK) - { - if (mECAgreePrivateKey != null) - { - return TlsEccUtilities.CalculateECDHBasicAgreement(mECAgreePublicKey, mECAgreePrivateKey); - } - - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - if (this.mKeyExchange == KeyExchangeAlgorithm.RSA_PSK) - { - return this.mPremasterSecret; - } - - return new byte[pskLength]; - } - - protected virtual RsaKeyParameters ValidateRsaPublicKey(RsaKeyParameters key) - { - // TODO What is the minimum bit length required? - // key.Modulus.BitLength; - - if (!key.Exponent.IsProbablePrime(2)) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - - return key; - } - } -} diff --git a/crypto/src/crypto/tls/TlsRsaKeyExchange.cs b/crypto/src/crypto/tls/TlsRsaKeyExchange.cs deleted file mode 100644 index 0e7195ff6..000000000 --- a/crypto/src/crypto/tls/TlsRsaKeyExchange.cs +++ /dev/null @@ -1,140 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Asn1; -using Org.BouncyCastle.Asn1.X509; -using Org.BouncyCastle.Crypto.Encodings; -using Org.BouncyCastle.Crypto.Engines; -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Security; -using Org.BouncyCastle.Utilities.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary>(D)TLS and SSLv3 RSA key exchange.</summary> - public class TlsRsaKeyExchange - : AbstractTlsKeyExchange - { - protected AsymmetricKeyParameter mServerPublicKey = null; - - protected RsaKeyParameters mRsaServerPublicKey = null; - - protected TlsEncryptionCredentials mServerCredentials = null; - - protected byte[] mPremasterSecret; - - public TlsRsaKeyExchange(IList supportedSignatureAlgorithms) - : base(KeyExchangeAlgorithm.RSA, supportedSignatureAlgorithms) - { - } - - public override void SkipServerCredentials() - { - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - - public override void ProcessServerCredentials(TlsCredentials serverCredentials) - { - if (!(serverCredentials is TlsEncryptionCredentials)) - throw new TlsFatalAlert(AlertDescription.internal_error); - - ProcessServerCertificate(serverCredentials.Certificate); - - this.mServerCredentials = (TlsEncryptionCredentials)serverCredentials; - } - - public override void ProcessServerCertificate(Certificate serverCertificate) - { - if (serverCertificate.IsEmpty) - throw new TlsFatalAlert(AlertDescription.decode_error); - - X509CertificateStructure x509Cert = serverCertificate.GetCertificateAt(0); - - SubjectPublicKeyInfo keyInfo = x509Cert.SubjectPublicKeyInfo; - try - { - this.mServerPublicKey = PublicKeyFactory.CreateKey(keyInfo); - } - catch (Exception e) - { - throw new TlsFatalAlert(AlertDescription.unsupported_certificate, e); - } - - // Sanity check the PublicKeyFactory - if (this.mServerPublicKey.IsPrivate) - throw new TlsFatalAlert(AlertDescription.internal_error); - - this.mRsaServerPublicKey = ValidateRsaPublicKey((RsaKeyParameters)this.mServerPublicKey); - - TlsUtilities.ValidateKeyUsage(x509Cert, KeyUsage.KeyEncipherment); - - base.ProcessServerCertificate(serverCertificate); - } - - public override void ValidateCertificateRequest(CertificateRequest certificateRequest) - { - byte[] types = certificateRequest.CertificateTypes; - for (int i = 0; i < types.Length; ++i) - { - switch (types[i]) - { - case ClientCertificateType.rsa_sign: - case ClientCertificateType.dss_sign: - case ClientCertificateType.ecdsa_sign: - break; - default: - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - } - } - - public override void ProcessClientCredentials(TlsCredentials clientCredentials) - { - if (!(clientCredentials is TlsSignerCredentials)) - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - public override void GenerateClientKeyExchange(Stream output) - { - this.mPremasterSecret = TlsRsaUtilities.GenerateEncryptedPreMasterSecret(mContext, mRsaServerPublicKey, output); - } - - public override void ProcessClientKeyExchange(Stream input) - { - byte[] encryptedPreMasterSecret; - if (TlsUtilities.IsSsl(mContext)) - { - // TODO Do any SSLv3 clients actually include the length? - encryptedPreMasterSecret = Streams.ReadAll(input); - } - else - { - encryptedPreMasterSecret = TlsUtilities.ReadOpaque16(input); - } - - this.mPremasterSecret = mServerCredentials.DecryptPreMasterSecret(encryptedPreMasterSecret); - } - - public override byte[] GeneratePremasterSecret() - { - if (this.mPremasterSecret == null) - throw new TlsFatalAlert(AlertDescription.internal_error); - - byte[] tmp = this.mPremasterSecret; - this.mPremasterSecret = null; - return tmp; - } - - protected virtual RsaKeyParameters ValidateRsaPublicKey(RsaKeyParameters key) - { - // TODO What is the minimum bit length required? - // key.Modulus.BitLength; - - if (!key.Exponent.IsProbablePrime(2)) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - - return key; - } - } -} diff --git a/crypto/src/crypto/tls/TlsRsaSigner.cs b/crypto/src/crypto/tls/TlsRsaSigner.cs deleted file mode 100644 index 1614f503b..000000000 --- a/crypto/src/crypto/tls/TlsRsaSigner.cs +++ /dev/null @@ -1,102 +0,0 @@ -using System; - -using Org.BouncyCastle.Crypto.Digests; -using Org.BouncyCastle.Crypto.Encodings; -using Org.BouncyCastle.Crypto.Engines; -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Crypto.Signers; -using Org.BouncyCastle.Security; -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class TlsRsaSigner - : AbstractTlsSigner - { - public override byte[] GenerateRawSignature(SignatureAndHashAlgorithm algorithm, - AsymmetricKeyParameter privateKey, byte[] hash) - { - ISigner signer = MakeSigner(algorithm, true, true, - new ParametersWithRandom(privateKey, this.mContext.SecureRandom)); - signer.BlockUpdate(hash, 0, hash.Length); - return signer.GenerateSignature(); - } - - public override bool VerifyRawSignature(SignatureAndHashAlgorithm algorithm, byte[] sigBytes, - AsymmetricKeyParameter publicKey, byte[] hash) - { - ISigner signer = MakeSigner(algorithm, true, false, publicKey); - signer.BlockUpdate(hash, 0, hash.Length); - return signer.VerifySignature(sigBytes); - } - - public override ISigner CreateSigner(SignatureAndHashAlgorithm algorithm, AsymmetricKeyParameter privateKey) - { - return MakeSigner(algorithm, false, true, new ParametersWithRandom(privateKey, this.mContext.SecureRandom)); - } - - public override ISigner CreateVerifyer(SignatureAndHashAlgorithm algorithm, AsymmetricKeyParameter publicKey) - { - return MakeSigner(algorithm, false, false, publicKey); - } - - public override bool IsValidPublicKey(AsymmetricKeyParameter publicKey) - { - return publicKey is RsaKeyParameters && !publicKey.IsPrivate; - } - - protected virtual ISigner MakeSigner(SignatureAndHashAlgorithm algorithm, bool raw, bool forSigning, - ICipherParameters cp) - { - if ((algorithm != null) != TlsUtilities.IsTlsV12(mContext)) - throw new InvalidOperationException(); - if (algorithm != null && algorithm.Signature != SignatureAlgorithm.rsa) - throw new InvalidOperationException(); - - IDigest d; - if (raw) - { - d = new NullDigest(); - } - else if (algorithm == null) - { - d = new CombinedHash(); - } - else - { - d = TlsUtilities.CreateHash(algorithm.Hash); - } - - ISigner s; - if (algorithm != null) - { - /* - * RFC 5246 4.7. In RSA signing, the opaque vector contains the signature generated - * using the RSASSA-PKCS1-v1_5 signature scheme defined in [PKCS1]. - */ - s = new RsaDigestSigner(d, TlsUtilities.GetOidForHashAlgorithm(algorithm.Hash)); - } - else - { - /* - * RFC 5246 4.7. Note that earlier versions of TLS used a different RSA signature scheme - * that did not include a DigestInfo encoding. - */ - s = new GenericSigner(CreateRsaImpl(), d); - } - s.Init(forSigning, cp); - return s; - } - - protected virtual IAsymmetricBlockCipher CreateRsaImpl() - { - /* - * RFC 5246 7.4.7.1. Implementation note: It is now known that remote timing-based attacks - * on TLS are possible, at least when the client and server are on the same LAN. - * Accordingly, implementations that use static RSA keys MUST use RSA blinding or some other - * anti-timing technique, as described in [TIMING]. - */ - return new Pkcs1Encoding(new RsaBlindedEngine()); - } - } -} diff --git a/crypto/src/crypto/tls/TlsRsaUtilities.cs b/crypto/src/crypto/tls/TlsRsaUtilities.cs deleted file mode 100644 index 0e42c1733..000000000 --- a/crypto/src/crypto/tls/TlsRsaUtilities.cs +++ /dev/null @@ -1,132 +0,0 @@ -using System; -using System.IO; - -using Org.BouncyCastle.Crypto.Encodings; -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Crypto.Engines; -using Org.BouncyCastle.Security; -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class TlsRsaUtilities - { - /// <exception cref="IOException"></exception> - public static byte[] GenerateEncryptedPreMasterSecret(TlsContext context, RsaKeyParameters rsaServerPublicKey, - Stream output) - { - /* - * Choose a PremasterSecret and send it encrypted to the server - */ - byte[] premasterSecret = new byte[48]; - context.SecureRandom.NextBytes(premasterSecret); - TlsUtilities.WriteVersion(context.ClientVersion, premasterSecret, 0); - - Pkcs1Encoding encoding = new Pkcs1Encoding(new RsaBlindedEngine()); - encoding.Init(true, new ParametersWithRandom(rsaServerPublicKey, context.SecureRandom)); - - try - { - byte[] encryptedPreMasterSecret = encoding.ProcessBlock(premasterSecret, 0, premasterSecret.Length); - - if (TlsUtilities.IsSsl(context)) - { - // TODO Do any SSLv3 servers actually expect the length? - output.Write(encryptedPreMasterSecret, 0, encryptedPreMasterSecret.Length); - } - else - { - TlsUtilities.WriteOpaque16(encryptedPreMasterSecret, output); - } - } - catch (InvalidCipherTextException e) - { - /* - * This should never happen, only during decryption. - */ - throw new TlsFatalAlert(AlertDescription.internal_error, e); - } - - return premasterSecret; - } - - public static byte[] SafeDecryptPreMasterSecret(TlsContext context, RsaKeyParameters rsaServerPrivateKey, - byte[] encryptedPreMasterSecret) - { - /* - * RFC 5246 7.4.7.1. - */ - ProtocolVersion clientVersion = context.ClientVersion; - - // TODO Provide as configuration option? - bool versionNumberCheckDisabled = false; - - /* - * Generate 48 random bytes we can use as a Pre-Master-Secret, if the - * PKCS1 padding check should fail. - */ - byte[] fallback = new byte[48]; - context.SecureRandom.NextBytes(fallback); - - byte[] M = Arrays.Clone(fallback); - try - { - Pkcs1Encoding encoding = new Pkcs1Encoding(new RsaBlindedEngine(), fallback); - encoding.Init(false, - new ParametersWithRandom(rsaServerPrivateKey, context.SecureRandom)); - - M = encoding.ProcessBlock(encryptedPreMasterSecret, 0, encryptedPreMasterSecret.Length); - } - catch (Exception) - { - /* - * This should never happen since the decryption should never throw an exception - * and return a random value instead. - * - * In any case, a TLS server MUST NOT generate an alert if processing an - * RSA-encrypted premaster secret message fails, or the version number is not as - * expected. Instead, it MUST continue the handshake with a randomly generated - * premaster secret. - */ - } - - /* - * If ClientHello.client_version is TLS 1.1 or higher, server implementations MUST - * check the version number [..]. - */ - if (versionNumberCheckDisabled && clientVersion.IsEqualOrEarlierVersionOf(ProtocolVersion.TLSv10)) - { - /* - * If the version number is TLS 1.0 or earlier, server - * implementations SHOULD check the version number, but MAY have a - * configuration option to disable the check. - * - * So there is nothing to do here. - */ - } - else - { - /* - * OK, we need to compare the version number in the decrypted Pre-Master-Secret with the - * clientVersion received during the handshake. If they don't match, we replace the - * decrypted Pre-Master-Secret with a random one. - */ - int correct = (clientVersion.MajorVersion ^ (M[0] & 0xff)) - | (clientVersion.MinorVersion ^ (M[1] & 0xff)); - correct |= correct >> 1; - correct |= correct >> 2; - correct |= correct >> 4; - int mask = ~((correct & 1) - 1); - - /* - * mask will be all bits set to 0xff if the version number differed. - */ - for (int i = 0; i < 48; i++) - { - M[i] = (byte)((M[i] & (~mask)) | (fallback[i] & mask)); - } - } - return M; - } - } -} diff --git a/crypto/src/crypto/tls/TlsServer.cs b/crypto/src/crypto/tls/TlsServer.cs deleted file mode 100644 index e791f93a9..000000000 --- a/crypto/src/crypto/tls/TlsServer.cs +++ /dev/null @@ -1,93 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public interface TlsServer - : TlsPeer - { - void Init(TlsServerContext context); - - /// <exception cref="IOException"></exception> - void NotifyClientVersion(ProtocolVersion clientVersion); - - /// <exception cref="IOException"></exception> - void NotifyFallback(bool isFallback); - - /// <exception cref="IOException"></exception> - void NotifyOfferedCipherSuites(int[] offeredCipherSuites); - - /// <exception cref="IOException"></exception> - void NotifyOfferedCompressionMethods(byte[] offeredCompressionMethods); - - /// <param name="clientExtensions">A <see cref="IDictionary"/> (Int32 -> byte[]). Will never be null.</param> - /// <exception cref="IOException"></exception> - void ProcessClientExtensions(IDictionary clientExtensions); - - /// <exception cref="IOException"></exception> - ProtocolVersion GetServerVersion(); - - /// <exception cref="IOException"></exception> - int GetSelectedCipherSuite(); - - /// <exception cref="IOException"></exception> - byte GetSelectedCompressionMethod(); - - /// <summary> - /// Get the (optional) table of server extensions to be included in (extended) server hello. - /// </summary> - /// <returns> - /// A <see cref="IDictionary"/> (Int32 -> byte[]). May be null. - /// </returns> - /// <exception cref="IOException"></exception> - IDictionary GetServerExtensions(); - - /// <returns> - /// A <see cref="IList"/> (<see cref="SupplementalDataEntry"/>). May be null. - /// </returns> - /// <exception cref="IOException"></exception> - IList GetServerSupplementalData(); - - /// <exception cref="IOException"></exception> - TlsCredentials GetCredentials(); - - /// <remarks> - /// This method will be called (only) if the server included an extension of type - /// "status_request" with empty "extension_data" in the extended server hello. See <i>RFC 3546 - /// 3.6. Certificate Status Request</i>. If a non-null <see cref="CertificateStatus"/> is returned, it - /// is sent to the client as a handshake message of type "certificate_status". - /// </remarks> - /// <returns>A <see cref="CertificateStatus"/> to be sent to the client (or null for none).</returns> - /// <exception cref="IOException"></exception> - CertificateStatus GetCertificateStatus(); - - /// <exception cref="IOException"></exception> - TlsKeyExchange GetKeyExchange(); - - /// <exception cref="IOException"></exception> - CertificateRequest GetCertificateRequest(); - - /// <param name="clientSupplementalData"><see cref="IList"/> (<see cref="SupplementalDataEntry"/>)</param> - /// <exception cref="IOException"></exception> - void ProcessClientSupplementalData(IList clientSupplementalData); - - /// <summary> - /// Called by the protocol handler to report the client certificate, only if <c>GetCertificateRequest</c> - /// returned non-null. - /// </summary> - /// <remarks>Note: this method is responsible for certificate verification and validation.</remarks> - /// <param name="clientCertificate">the effective client certificate (may be an empty chain).</param> - /// <exception cref="IOException"></exception> - void NotifyClientCertificate(Certificate clientCertificate); - - /// <summary>RFC 5077 3.3. NewSessionTicket Handshake Message.</summary> - /// <remarks> - /// This method will be called (only) if a NewSessionTicket extension was sent by the server. See - /// <i>RFC 5077 4. Recommended Ticket Construction</i> for recommended format and protection. - /// </remarks> - /// <returns>The <see cref="NewSessionTicket">ticket</see>)</returns> - /// <exception cref="IOException"></exception> - NewSessionTicket GetNewSessionTicket(); - } -} diff --git a/crypto/src/crypto/tls/TlsServerContext.cs b/crypto/src/crypto/tls/TlsServerContext.cs deleted file mode 100644 index 4021571aa..000000000 --- a/crypto/src/crypto/tls/TlsServerContext.cs +++ /dev/null @@ -1,11 +0,0 @@ -using System; - -using Org.BouncyCastle.Security; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public interface TlsServerContext - : TlsContext - { - } -} diff --git a/crypto/src/crypto/tls/TlsServerContextImpl.cs b/crypto/src/crypto/tls/TlsServerContextImpl.cs deleted file mode 100644 index d56566ffc..000000000 --- a/crypto/src/crypto/tls/TlsServerContextImpl.cs +++ /dev/null @@ -1,20 +0,0 @@ -using System; - -using Org.BouncyCastle.Security; - -namespace Org.BouncyCastle.Crypto.Tls -{ - internal class TlsServerContextImpl - : AbstractTlsContext, TlsServerContext - { - internal TlsServerContextImpl(SecureRandom secureRandom, SecurityParameters securityParameters) - : base(secureRandom, securityParameters) - { - } - - public override bool IsServer - { - get { return true; } - } - } -} diff --git a/crypto/src/crypto/tls/TlsServerProtocol.cs b/crypto/src/crypto/tls/TlsServerProtocol.cs deleted file mode 100644 index 85b450c9e..000000000 --- a/crypto/src/crypto/tls/TlsServerProtocol.cs +++ /dev/null @@ -1,832 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Asn1.X509; -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Security; -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class TlsServerProtocol - : TlsProtocol - { - protected TlsServer mTlsServer = null; - internal TlsServerContextImpl mTlsServerContext = null; - - protected TlsKeyExchange mKeyExchange = null; - protected TlsCredentials mServerCredentials = null; - protected CertificateRequest mCertificateRequest = null; - - protected short mClientCertificateType = -1; - protected TlsHandshakeHash mPrepareFinishHash = null; - - /** - * Constructor for blocking mode. - * @param stream The bi-directional stream of data to/from the client - * @param output The stream of data to the client - * @param secureRandom Random number generator for various cryptographic functions - */ - public TlsServerProtocol(Stream stream, SecureRandom secureRandom) - : base(stream, secureRandom) - { - } - - /** - * Constructor for blocking mode. - * @param input The stream of data from the client - * @param output The stream of data to the client - * @param secureRandom Random number generator for various cryptographic functions - */ - public TlsServerProtocol(Stream input, Stream output, SecureRandom secureRandom) - : base(input, output, secureRandom) - { - } - - /** - * Constructor for non-blocking mode.<br/> - * <br/> - * When data is received, use {@link #offerInput(java.nio.ByteBuffer)} to - * provide the received ciphertext, then use - * {@link #readInput(byte[], int, int)} to read the corresponding cleartext.<br/> - * <br/> - * Similarly, when data needs to be sent, use - * {@link #offerOutput(byte[], int, int)} to provide the cleartext, then use - * {@link #readOutput(byte[], int, int)} to get the corresponding - * ciphertext. - * - * @param secureRandom - * Random number generator for various cryptographic functions - */ - public TlsServerProtocol(SecureRandom secureRandom) - : base(secureRandom) - { - } - - /** - * Receives a TLS handshake in the role of server.<br/> - * <br/> - * In blocking mode, this will not return until the handshake is complete. - * In non-blocking mode, use {@link TlsPeer#notifyHandshakeComplete()} to - * receive a callback when the handshake is complete. - * - * @param tlsServer - * @throws IOException If in blocking mode and handshake was not successful. - */ - public virtual void Accept(TlsServer tlsServer) - { - if (tlsServer == null) - throw new ArgumentNullException("tlsServer"); - if (this.mTlsServer != null) - throw new InvalidOperationException("'Accept' can only be called once"); - - this.mTlsServer = tlsServer; - - this.mSecurityParameters = new SecurityParameters(); - this.mSecurityParameters.entity = ConnectionEnd.server; - - this.mTlsServerContext = new TlsServerContextImpl(mSecureRandom, mSecurityParameters); - - this.mSecurityParameters.serverRandom = CreateRandomBlock(tlsServer.ShouldUseGmtUnixTime(), - mTlsServerContext.NonceRandomGenerator); - - this.mTlsServer.Init(mTlsServerContext); - this.mRecordStream.Init(mTlsServerContext); - - tlsServer.NotifyCloseHandle(this); - - this.mRecordStream.SetRestrictReadVersion(false); - - BlockForHandshake(); - } - - protected override void CleanupHandshake() - { - base.CleanupHandshake(); - - this.mKeyExchange = null; - this.mServerCredentials = null; - this.mCertificateRequest = null; - this.mPrepareFinishHash = null; - } - - protected override TlsContext Context - { - get { return mTlsServerContext; } - } - - internal override AbstractTlsContext ContextAdmin - { - get { return mTlsServerContext; } - } - - protected override TlsPeer Peer - { - get { return mTlsServer; } - } - - protected override void HandleHandshakeMessage(byte type, MemoryStream buf) - { - switch (type) - { - case HandshakeType.client_hello: - { - switch (this.mConnectionState) - { - case CS_START: - { - ReceiveClientHelloMessage(buf); - this.mConnectionState = CS_CLIENT_HELLO; - - SendServerHelloMessage(); - this.mConnectionState = CS_SERVER_HELLO; - - mRecordStream.NotifyHelloComplete(); - - IList serverSupplementalData = mTlsServer.GetServerSupplementalData(); - if (serverSupplementalData != null) - { - SendSupplementalDataMessage(serverSupplementalData); - } - this.mConnectionState = CS_SERVER_SUPPLEMENTAL_DATA; - - this.mKeyExchange = mTlsServer.GetKeyExchange(); - this.mKeyExchange.Init(Context); - - this.mServerCredentials = mTlsServer.GetCredentials(); - - Certificate serverCertificate = null; - - if (this.mServerCredentials == null) - { - this.mKeyExchange.SkipServerCredentials(); - } - else - { - this.mKeyExchange.ProcessServerCredentials(this.mServerCredentials); - - serverCertificate = this.mServerCredentials.Certificate; - SendCertificateMessage(serverCertificate); - } - this.mConnectionState = CS_SERVER_CERTIFICATE; - - // TODO[RFC 3546] Check whether empty certificates is possible, allowed, or excludes CertificateStatus - if (serverCertificate == null || serverCertificate.IsEmpty) - { - this.mAllowCertificateStatus = false; - } - - if (this.mAllowCertificateStatus) - { - CertificateStatus certificateStatus = mTlsServer.GetCertificateStatus(); - if (certificateStatus != null) - { - SendCertificateStatusMessage(certificateStatus); - } - } - - this.mConnectionState = CS_CERTIFICATE_STATUS; - - byte[] serverKeyExchange = this.mKeyExchange.GenerateServerKeyExchange(); - if (serverKeyExchange != null) - { - SendServerKeyExchangeMessage(serverKeyExchange); - } - this.mConnectionState = CS_SERVER_KEY_EXCHANGE; - - if (this.mServerCredentials != null) - { - this.mCertificateRequest = mTlsServer.GetCertificateRequest(); - if (this.mCertificateRequest != null) - { - if (TlsUtilities.IsTlsV12(Context) != (mCertificateRequest.SupportedSignatureAlgorithms != null)) - throw new TlsFatalAlert(AlertDescription.internal_error); - - this.mKeyExchange.ValidateCertificateRequest(mCertificateRequest); - - SendCertificateRequestMessage(mCertificateRequest); - - TlsUtilities.TrackHashAlgorithms(this.mRecordStream.HandshakeHash, - this.mCertificateRequest.SupportedSignatureAlgorithms); - } - } - this.mConnectionState = CS_CERTIFICATE_REQUEST; - - SendServerHelloDoneMessage(); - this.mConnectionState = CS_SERVER_HELLO_DONE; - - this.mRecordStream.HandshakeHash.SealHashAlgorithms(); - - break; - } - case CS_END: - { - RefuseRenegotiation(); - break; - } - default: - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - break; - } - case HandshakeType.supplemental_data: - { - switch (this.mConnectionState) - { - case CS_SERVER_HELLO_DONE: - { - mTlsServer.ProcessClientSupplementalData(ReadSupplementalDataMessage(buf)); - this.mConnectionState = CS_CLIENT_SUPPLEMENTAL_DATA; - break; - } - default: - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - break; - } - case HandshakeType.certificate: - { - switch (this.mConnectionState) - { - case CS_SERVER_HELLO_DONE: - case CS_CLIENT_SUPPLEMENTAL_DATA: - { - if (mConnectionState < CS_CLIENT_SUPPLEMENTAL_DATA) - { - mTlsServer.ProcessClientSupplementalData(null); - } - - if (this.mCertificateRequest == null) - throw new TlsFatalAlert(AlertDescription.unexpected_message); - - ReceiveCertificateMessage(buf); - this.mConnectionState = CS_CLIENT_CERTIFICATE; - break; - } - default: - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - break; - } - case HandshakeType.client_key_exchange: - { - switch (this.mConnectionState) - { - case CS_SERVER_HELLO_DONE: - case CS_CLIENT_SUPPLEMENTAL_DATA: - case CS_CLIENT_CERTIFICATE: - { - if (mConnectionState < CS_CLIENT_SUPPLEMENTAL_DATA) - { - mTlsServer.ProcessClientSupplementalData(null); - } - - if (mConnectionState < CS_CLIENT_CERTIFICATE) - { - if (this.mCertificateRequest == null) - { - this.mKeyExchange.SkipClientCredentials(); - } - else - { - if (TlsUtilities.IsTlsV12(Context)) - { - /* - * RFC 5246 If no suitable certificate is available, the client MUST Send a - * certificate message containing no certificates. - * - * NOTE: In previous RFCs, this was SHOULD instead of MUST. - */ - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - else if (TlsUtilities.IsSsl(Context)) - { - if (this.mPeerCertificate == null) - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - else - { - NotifyClientCertificate(Certificate.EmptyChain); - } - } - } - - ReceiveClientKeyExchangeMessage(buf); - this.mConnectionState = CS_CLIENT_KEY_EXCHANGE; - break; - } - default: - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - break; - } - case HandshakeType.certificate_verify: - { - switch (this.mConnectionState) - { - case CS_CLIENT_KEY_EXCHANGE: - { - /* - * RFC 5246 7.4.8 This message is only sent following a client certificate that has - * signing capability (i.e., all certificates except those containing fixed - * Diffie-Hellman parameters). - */ - if (!ExpectCertificateVerifyMessage()) - throw new TlsFatalAlert(AlertDescription.unexpected_message); - - ReceiveCertificateVerifyMessage(buf); - this.mConnectionState = CS_CERTIFICATE_VERIFY; - - break; - } - default: - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - break; - } - case HandshakeType.finished: - { - switch (this.mConnectionState) - { - case CS_CLIENT_KEY_EXCHANGE: - case CS_CERTIFICATE_VERIFY: - { - if (mConnectionState < CS_CERTIFICATE_VERIFY && ExpectCertificateVerifyMessage()) - throw new TlsFatalAlert(AlertDescription.unexpected_message); - - ProcessFinishedMessage(buf); - this.mConnectionState = CS_CLIENT_FINISHED; - - if (this.mExpectSessionTicket) - { - SendNewSessionTicketMessage(mTlsServer.GetNewSessionTicket()); - } - this.mConnectionState = CS_SERVER_SESSION_TICKET; - - SendChangeCipherSpecMessage(); - SendFinishedMessage(); - this.mConnectionState = CS_SERVER_FINISHED; - - CompleteHandshake(); - break; - } - default: - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - break; - } - case HandshakeType.hello_request: - case HandshakeType.hello_verify_request: - case HandshakeType.server_hello: - case HandshakeType.server_key_exchange: - case HandshakeType.certificate_request: - case HandshakeType.server_hello_done: - case HandshakeType.session_ticket: - default: - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - } - - protected override void HandleAlertWarningMessage(byte alertDescription) - { - /* - * SSL 3.0 If the server has sent a certificate request Message, the client must send - * either the certificate message or a no_certificate alert. - */ - if (AlertDescription.no_certificate == alertDescription && null != mCertificateRequest - && TlsUtilities.IsSsl(mTlsServerContext)) - { - switch (mConnectionState) - { - case CS_SERVER_HELLO_DONE: - case CS_CLIENT_SUPPLEMENTAL_DATA: - { - if (mConnectionState < CS_CLIENT_SUPPLEMENTAL_DATA) - { - mTlsServer.ProcessClientSupplementalData(null); - } - - NotifyClientCertificate(Certificate.EmptyChain); - this.mConnectionState = CS_CLIENT_CERTIFICATE; - return; - } - } - } - - base.HandleAlertWarningMessage(alertDescription); - } - - protected virtual void NotifyClientCertificate(Certificate clientCertificate) - { - if (mCertificateRequest == null) - throw new InvalidOperationException(); - if (mPeerCertificate != null) - throw new TlsFatalAlert(AlertDescription.unexpected_message); - - this.mPeerCertificate = clientCertificate; - - if (clientCertificate.IsEmpty) - { - this.mKeyExchange.SkipClientCredentials(); - } - else - { - - /* - * TODO RFC 5246 7.4.6. If the certificate_authorities list in the certificate request - * message was non-empty, one of the certificates in the certificate chain SHOULD be - * issued by one of the listed CAs. - */ - - this.mClientCertificateType = TlsUtilities.GetClientCertificateType(clientCertificate, - this.mServerCredentials.Certificate); - - this.mKeyExchange.ProcessClientCertificate(clientCertificate); - } - - /* - * RFC 5246 7.4.6. If the client does not Send any certificates, the server MAY at its - * discretion either continue the handshake without client authentication, or respond with a - * fatal handshake_failure alert. Also, if some aspect of the certificate chain was - * unacceptable (e.g., it was not signed by a known, trusted CA), the server MAY at its - * discretion either continue the handshake (considering the client unauthenticated) or Send - * a fatal alert. - */ - this.mTlsServer.NotifyClientCertificate(clientCertificate); - } - - protected virtual void ReceiveCertificateMessage(MemoryStream buf) - { - Certificate clientCertificate = Certificate.Parse(buf); - - AssertEmpty(buf); - - NotifyClientCertificate(clientCertificate); - } - - protected virtual void ReceiveCertificateVerifyMessage(MemoryStream buf) - { - if (mCertificateRequest == null) - throw new InvalidOperationException(); - - DigitallySigned clientCertificateVerify = DigitallySigned.Parse(Context, buf); - - AssertEmpty(buf); - - // Verify the CertificateVerify message contains a correct signature. - try - { - SignatureAndHashAlgorithm signatureAlgorithm = clientCertificateVerify.Algorithm; - - byte[] hash; - if (TlsUtilities.IsTlsV12(Context)) - { - TlsUtilities.VerifySupportedSignatureAlgorithm(mCertificateRequest.SupportedSignatureAlgorithms, signatureAlgorithm); - hash = mPrepareFinishHash.GetFinalHash(signatureAlgorithm.Hash); - } - else - { - hash = mSecurityParameters.SessionHash; - } - - X509CertificateStructure x509Cert = mPeerCertificate.GetCertificateAt(0); - SubjectPublicKeyInfo keyInfo = x509Cert.SubjectPublicKeyInfo; - AsymmetricKeyParameter publicKey = PublicKeyFactory.CreateKey(keyInfo); - - TlsSigner tlsSigner = TlsUtilities.CreateTlsSigner((byte)mClientCertificateType); - tlsSigner.Init(Context); - if (!tlsSigner.VerifyRawSignature(signatureAlgorithm, clientCertificateVerify.Signature, publicKey, hash)) - throw new TlsFatalAlert(AlertDescription.decrypt_error); - } - catch (TlsFatalAlert e) - { - throw e; - } - catch (Exception e) - { - throw new TlsFatalAlert(AlertDescription.decrypt_error, e); - } - } - - protected virtual void ReceiveClientHelloMessage(MemoryStream buf) - { - ProtocolVersion client_version = TlsUtilities.ReadVersion(buf); - mRecordStream.SetWriteVersion(client_version); - - if (client_version.IsDtls) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - - byte[] client_random = TlsUtilities.ReadFully(32, buf); - - /* - * TODO RFC 5077 3.4. If a ticket is presented by the client, the server MUST NOT attempt to - * use the Session ID in the ClientHello for stateful session resumption. - */ - byte[] sessionID = TlsUtilities.ReadOpaque8(buf); - if (sessionID.Length > 32) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - - /* - * TODO RFC 5246 7.4.1.2. If the session_id field is not empty (implying a session - * resumption request), this vector MUST include at least the cipher_suite from that - * session. - */ - int cipher_suites_length = TlsUtilities.ReadUint16(buf); - if (cipher_suites_length < 2 || (cipher_suites_length & 1) != 0) - throw new TlsFatalAlert(AlertDescription.decode_error); - - this.mOfferedCipherSuites = TlsUtilities.ReadUint16Array(cipher_suites_length / 2, buf); - - /* - * TODO RFC 5246 7.4.1.2. If the session_id field is not empty (implying a session - * resumption request), it MUST include the compression_method from that session. - */ - int compression_methods_length = TlsUtilities.ReadUint8(buf); - if (compression_methods_length < 1) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - - this.mOfferedCompressionMethods = TlsUtilities.ReadUint8Array(compression_methods_length, buf); - - /* - * TODO RFC 3546 2.3 If [...] the older session is resumed, then the server MUST ignore - * extensions appearing in the client hello, and Send a server hello containing no - * extensions. - */ - this.mClientExtensions = ReadExtensions(buf); - - /* - * TODO[resumption] Check RFC 7627 5.4. for required behaviour - */ - - /* - * RFC 7627 4. Clients and servers SHOULD NOT accept handshakes that do not use the extended - * master secret [..]. (and see 5.2, 5.3) - */ - this.mSecurityParameters.extendedMasterSecret = TlsExtensionsUtilities.HasExtendedMasterSecretExtension(mClientExtensions); - if (!mSecurityParameters.IsExtendedMasterSecret && mTlsServer.RequiresExtendedMasterSecret()) - { - throw new TlsFatalAlert(AlertDescription.handshake_failure); - } - - ContextAdmin.SetClientVersion(client_version); - - mTlsServer.NotifyClientVersion(client_version); - mTlsServer.NotifyFallback(Arrays.Contains(mOfferedCipherSuites, CipherSuite.TLS_FALLBACK_SCSV)); - - mSecurityParameters.clientRandom = client_random; - - mTlsServer.NotifyOfferedCipherSuites(mOfferedCipherSuites); - mTlsServer.NotifyOfferedCompressionMethods(mOfferedCompressionMethods); - - /* - * RFC 5746 3.6. Server Behavior: Initial Handshake - */ - { - /* - * RFC 5746 3.4. The client MUST include either an empty "renegotiation_info" extension, - * or the TLS_EMPTY_RENEGOTIATION_INFO_SCSV signaling cipher suite value in the - * ClientHello. Including both is NOT RECOMMENDED. - */ - - /* - * When a ClientHello is received, the server MUST check if it includes the - * TLS_EMPTY_RENEGOTIATION_INFO_SCSV SCSV. If it does, set the secure_renegotiation flag - * to TRUE. - */ - if (Arrays.Contains(mOfferedCipherSuites, CipherSuite.TLS_EMPTY_RENEGOTIATION_INFO_SCSV)) - { - this.mSecureRenegotiation = true; - } - - /* - * The server MUST check if the "renegotiation_info" extension is included in the - * ClientHello. - */ - byte[] renegExtData = TlsUtilities.GetExtensionData(mClientExtensions, ExtensionType.renegotiation_info); - if (renegExtData != null) - { - /* - * If the extension is present, set secure_renegotiation flag to TRUE. The - * server MUST then verify that the length of the "renegotiated_connection" - * field is zero, and if it is not, MUST abort the handshake. - */ - this.mSecureRenegotiation = true; - - if (!Arrays.ConstantTimeAreEqual(renegExtData, CreateRenegotiationInfo(TlsUtilities.EmptyBytes))) - throw new TlsFatalAlert(AlertDescription.handshake_failure); - } - } - - mTlsServer.NotifySecureRenegotiation(this.mSecureRenegotiation); - - if (mClientExtensions != null) - { - // NOTE: Validates the padding extension data, if present - TlsExtensionsUtilities.GetPaddingExtension(mClientExtensions); - - mTlsServer.ProcessClientExtensions(mClientExtensions); - } - } - - protected virtual void ReceiveClientKeyExchangeMessage(MemoryStream buf) - { - mKeyExchange.ProcessClientKeyExchange(buf); - - AssertEmpty(buf); - - if (TlsUtilities.IsSsl(Context)) - { - EstablishMasterSecret(Context, mKeyExchange); - } - - this.mPrepareFinishHash = mRecordStream.PrepareToFinish(); - this.mSecurityParameters.sessionHash = GetCurrentPrfHash(Context, mPrepareFinishHash, null); - - if (!TlsUtilities.IsSsl(Context)) - { - EstablishMasterSecret(Context, mKeyExchange); - } - - mRecordStream.SetPendingConnectionState(Peer.GetCompression(), Peer.GetCipher()); - } - - protected virtual void SendCertificateRequestMessage(CertificateRequest certificateRequest) - { - HandshakeMessage message = new HandshakeMessage(HandshakeType.certificate_request); - - certificateRequest.Encode(message); - - message.WriteToRecordStream(this); - } - - protected virtual void SendCertificateStatusMessage(CertificateStatus certificateStatus) - { - HandshakeMessage message = new HandshakeMessage(HandshakeType.certificate_status); - - certificateStatus.Encode(message); - - message.WriteToRecordStream(this); - } - - protected virtual void SendNewSessionTicketMessage(NewSessionTicket newSessionTicket) - { - if (newSessionTicket == null) - throw new TlsFatalAlert(AlertDescription.internal_error); - - HandshakeMessage message = new HandshakeMessage(HandshakeType.session_ticket); - - newSessionTicket.Encode(message); - - message.WriteToRecordStream(this); - } - - protected virtual void SendServerHelloMessage() - { - HandshakeMessage message = new HandshakeMessage(HandshakeType.server_hello); - - { - ProtocolVersion server_version = mTlsServer.GetServerVersion(); - if (!server_version.IsEqualOrEarlierVersionOf(Context.ClientVersion)) - throw new TlsFatalAlert(AlertDescription.internal_error); - - mRecordStream.ReadVersion = server_version; - mRecordStream.SetWriteVersion(server_version); - mRecordStream.SetRestrictReadVersion(true); - ContextAdmin.SetServerVersion(server_version); - - TlsUtilities.WriteVersion(server_version, message); - } - - message.Write(this.mSecurityParameters.serverRandom); - - /* - * The server may return an empty session_id to indicate that the session will not be cached - * and therefore cannot be resumed. - */ - TlsUtilities.WriteOpaque8(TlsUtilities.EmptyBytes, message); - - int selectedCipherSuite = mTlsServer.GetSelectedCipherSuite(); - if (!Arrays.Contains(mOfferedCipherSuites, selectedCipherSuite) - || selectedCipherSuite == CipherSuite.TLS_NULL_WITH_NULL_NULL - || CipherSuite.IsScsv(selectedCipherSuite) - || !TlsUtilities.IsValidCipherSuiteForVersion(selectedCipherSuite, Context.ServerVersion)) - { - throw new TlsFatalAlert(AlertDescription.internal_error); - } - mSecurityParameters.cipherSuite = selectedCipherSuite; - - byte selectedCompressionMethod = mTlsServer.GetSelectedCompressionMethod(); - if (!Arrays.Contains(mOfferedCompressionMethods, selectedCompressionMethod)) - { - throw new TlsFatalAlert(AlertDescription.internal_error); - } - mSecurityParameters.compressionAlgorithm = selectedCompressionMethod; - - TlsUtilities.WriteUint16(selectedCipherSuite, message); - TlsUtilities.WriteUint8(selectedCompressionMethod, message); - - this.mServerExtensions = TlsExtensionsUtilities.EnsureExtensionsInitialised(mTlsServer.GetServerExtensions()); - - /* - * RFC 5746 3.6. Server Behavior: Initial Handshake - */ - if (this.mSecureRenegotiation) - { - byte[] renegExtData = TlsUtilities.GetExtensionData(this.mServerExtensions, ExtensionType.renegotiation_info); - bool noRenegExt = (null == renegExtData); - - if (noRenegExt) - { - /* - * Note that Sending a "renegotiation_info" extension in response to a ClientHello - * containing only the SCSV is an explicit exception to the prohibition in RFC 5246, - * Section 7.4.1.4, on the server Sending unsolicited extensions and is only allowed - * because the client is signaling its willingness to receive the extension via the - * TLS_EMPTY_RENEGOTIATION_INFO_SCSV SCSV. - */ - - /* - * If the secure_renegotiation flag is set to TRUE, the server MUST include an empty - * "renegotiation_info" extension in the ServerHello message. - */ - this.mServerExtensions[ExtensionType.renegotiation_info] = CreateRenegotiationInfo(TlsUtilities.EmptyBytes); - } - } - - if (TlsUtilities.IsSsl(mTlsServerContext)) - { - mSecurityParameters.extendedMasterSecret = false; - } - else if (mSecurityParameters.IsExtendedMasterSecret) - { - TlsExtensionsUtilities.AddExtendedMasterSecretExtension(mServerExtensions); - } - - /* - * TODO RFC 3546 2.3 If [...] the older session is resumed, then the server MUST ignore - * extensions appearing in the client hello, and Send a server hello containing no - * extensions. - */ - - if (this.mServerExtensions.Count > 0) - { - this.mSecurityParameters.encryptThenMac = TlsExtensionsUtilities.HasEncryptThenMacExtension(mServerExtensions); - - this.mSecurityParameters.maxFragmentLength = ProcessMaxFragmentLengthExtension(mClientExtensions, - mServerExtensions, AlertDescription.internal_error); - - this.mSecurityParameters.truncatedHMac = TlsExtensionsUtilities.HasTruncatedHMacExtension(mServerExtensions); - - /* - * TODO It's surprising that there's no provision to allow a 'fresh' CertificateStatus to be sent in - * a session resumption handshake. - */ - this.mAllowCertificateStatus = !mResumedSession - && TlsUtilities.HasExpectedEmptyExtensionData(mServerExtensions, ExtensionType.status_request, - AlertDescription.internal_error); - - this.mExpectSessionTicket = !mResumedSession - && TlsUtilities.HasExpectedEmptyExtensionData(mServerExtensions, ExtensionType.session_ticket, - AlertDescription.internal_error); - - WriteExtensions(message, this.mServerExtensions); - } - - mSecurityParameters.prfAlgorithm = GetPrfAlgorithm(Context, mSecurityParameters.CipherSuite); - - /* - * RFC 5246 7.4.9. Any cipher suite which does not explicitly specify verify_data_length has - * a verify_data_length equal to 12. This includes all existing cipher suites. - */ - mSecurityParameters.verifyDataLength = 12; - - ApplyMaxFragmentLengthExtension(); - - message.WriteToRecordStream(this); - } - - protected virtual void SendServerHelloDoneMessage() - { - byte[] message = new byte[4]; - TlsUtilities.WriteUint8(HandshakeType.server_hello_done, message, 0); - TlsUtilities.WriteUint24(0, message, 1); - - WriteHandshakeMessage(message, 0, message.Length); - } - - protected virtual void SendServerKeyExchangeMessage(byte[] serverKeyExchange) - { - HandshakeMessage message = new HandshakeMessage(HandshakeType.server_key_exchange, serverKeyExchange.Length); - - message.Write(serverKeyExchange); - - message.WriteToRecordStream(this); - } - - protected virtual bool ExpectCertificateVerifyMessage() - { - return mClientCertificateType >= 0 && TlsUtilities.HasSigningCapability((byte)mClientCertificateType); - } - } -} diff --git a/crypto/src/crypto/tls/TlsSession.cs b/crypto/src/crypto/tls/TlsSession.cs deleted file mode 100644 index 6c229913b..000000000 --- a/crypto/src/crypto/tls/TlsSession.cs +++ /dev/null @@ -1,15 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public interface TlsSession - { - SessionParameters ExportSessionParameters(); - - byte[] SessionID { get; } - - void Invalidate(); - - bool IsResumable { get; } - } -} diff --git a/crypto/src/crypto/tls/TlsSessionImpl.cs b/crypto/src/crypto/tls/TlsSessionImpl.cs deleted file mode 100644 index 4f0ff819e..000000000 --- a/crypto/src/crypto/tls/TlsSessionImpl.cs +++ /dev/null @@ -1,51 +0,0 @@ -using System; - -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - internal class TlsSessionImpl - : TlsSession - { - internal readonly byte[] mSessionID; - internal readonly SessionParameters mSessionParameters; - internal bool mResumable; - - internal TlsSessionImpl(byte[] sessionID, SessionParameters sessionParameters) - { - if (sessionID == null) - throw new ArgumentNullException("sessionID"); - if (sessionID.Length > 32) - throw new ArgumentException("cannot be longer than 32 bytes", "sessionID"); - - this.mSessionID = Arrays.Clone(sessionID); - this.mSessionParameters = sessionParameters; - this.mResumable = sessionID.Length > 0 - && null != sessionParameters - && sessionParameters.IsExtendedMasterSecret; - } - - public virtual SessionParameters ExportSessionParameters() - { - lock (this) - { - return this.mSessionParameters == null ? null : this.mSessionParameters.Copy(); - } - } - - public virtual byte[] SessionID - { - get { lock (this) return mSessionID; } - } - - public virtual void Invalidate() - { - lock (this) this.mResumable = false; - } - - public virtual bool IsResumable - { - get { lock (this) return mResumable; } - } - } -} diff --git a/crypto/src/crypto/tls/TlsSigner.cs b/crypto/src/crypto/tls/TlsSigner.cs deleted file mode 100644 index ffdd4c9a1..000000000 --- a/crypto/src/crypto/tls/TlsSigner.cs +++ /dev/null @@ -1,29 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public interface TlsSigner - { - void Init(TlsContext context); - - byte[] GenerateRawSignature(AsymmetricKeyParameter privateKey, byte[] md5AndSha1); - - byte[] GenerateRawSignature(SignatureAndHashAlgorithm algorithm, - AsymmetricKeyParameter privateKey, byte[] hash); - - bool VerifyRawSignature(byte[] sigBytes, AsymmetricKeyParameter publicKey, byte[] md5AndSha1); - - bool VerifyRawSignature(SignatureAndHashAlgorithm algorithm, byte[] sigBytes, - AsymmetricKeyParameter publicKey, byte[] hash); - - ISigner CreateSigner(AsymmetricKeyParameter privateKey); - - ISigner CreateSigner(SignatureAndHashAlgorithm algorithm, AsymmetricKeyParameter privateKey); - - ISigner CreateVerifyer(AsymmetricKeyParameter publicKey); - - ISigner CreateVerifyer(SignatureAndHashAlgorithm algorithm, AsymmetricKeyParameter publicKey); - - bool IsValidPublicKey(AsymmetricKeyParameter publicKey); - } -} diff --git a/crypto/src/crypto/tls/TlsSignerCredentials.cs b/crypto/src/crypto/tls/TlsSignerCredentials.cs deleted file mode 100644 index 92ed7cc19..000000000 --- a/crypto/src/crypto/tls/TlsSignerCredentials.cs +++ /dev/null @@ -1,14 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public interface TlsSignerCredentials - : TlsCredentials - { - /// <exception cref="IOException"></exception> - byte[] GenerateCertificateSignature(byte[] hash); - - SignatureAndHashAlgorithm SignatureAndHashAlgorithm { get; } - } -} diff --git a/crypto/src/crypto/tls/TlsSrpGroupVerifier.cs b/crypto/src/crypto/tls/TlsSrpGroupVerifier.cs deleted file mode 100644 index 185f2f50a..000000000 --- a/crypto/src/crypto/tls/TlsSrpGroupVerifier.cs +++ /dev/null @@ -1,17 +0,0 @@ -using System; - -using Org.BouncyCastle.Crypto.Parameters; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public interface TlsSrpGroupVerifier - { - /** - * Check whether the given SRP group parameters are acceptable for use. - * - * @param group the {@link SRP6GroupParameters} to check - * @return true if (and only if) the specified group parameters are acceptable - */ - bool Accept(Srp6GroupParameters group); - } -} diff --git a/crypto/src/crypto/tls/TlsSrpIdentityManager.cs b/crypto/src/crypto/tls/TlsSrpIdentityManager.cs deleted file mode 100644 index 080a0dc16..000000000 --- a/crypto/src/crypto/tls/TlsSrpIdentityManager.cs +++ /dev/null @@ -1,21 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public interface TlsSrpIdentityManager - { - /** - * Lookup the {@link TlsSRPLoginParameters} corresponding to the specified identity. - * - * NOTE: To avoid "identity probing", unknown identities SHOULD be handled as recommended in RFC - * 5054 2.5.1.3. {@link SimulatedTlsSRPIdentityManager} is provided for this purpose. - * - * @param identity - * the SRP identity sent by the connecting client - * @return the {@link TlsSRPLoginParameters} for the specified identity, or else 'simulated' - * parameters if the identity is not recognized. A null value is also allowed, but not - * recommended. - */ - TlsSrpLoginParameters GetLoginParameters(byte[] identity); - } -} diff --git a/crypto/src/crypto/tls/TlsSrpKeyExchange.cs b/crypto/src/crypto/tls/TlsSrpKeyExchange.cs deleted file mode 100644 index 691c88131..000000000 --- a/crypto/src/crypto/tls/TlsSrpKeyExchange.cs +++ /dev/null @@ -1,285 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Asn1.X509; -using Org.BouncyCastle.Crypto.Agreement.Srp; -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Math; -using Org.BouncyCastle.Security; -using Org.BouncyCastle.Utilities; -using Org.BouncyCastle.Utilities.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <summary>(D)TLS SRP key exchange (RFC 5054).</summary> - public class TlsSrpKeyExchange - : AbstractTlsKeyExchange - { - protected static TlsSigner CreateSigner(int keyExchange) - { - switch (keyExchange) - { - case KeyExchangeAlgorithm.SRP: - return null; - case KeyExchangeAlgorithm.SRP_RSA: - return new TlsRsaSigner(); - case KeyExchangeAlgorithm.SRP_DSS: - return new TlsDssSigner(); - default: - throw new ArgumentException("unsupported key exchange algorithm"); - } - } - - protected TlsSigner mTlsSigner; - protected TlsSrpGroupVerifier mGroupVerifier; - protected byte[] mIdentity; - protected byte[] mPassword; - - protected AsymmetricKeyParameter mServerPublicKey = null; - - protected Srp6GroupParameters mSrpGroup = null; - protected Srp6Client mSrpClient = null; - protected Srp6Server mSrpServer = null; - protected BigInteger mSrpPeerCredentials = null; - protected BigInteger mSrpVerifier = null; - protected byte[] mSrpSalt = null; - - protected TlsSignerCredentials mServerCredentials = null; - - [Obsolete("Use constructor taking an explicit 'groupVerifier' argument")] - public TlsSrpKeyExchange(int keyExchange, IList supportedSignatureAlgorithms, byte[] identity, byte[] password) - : this(keyExchange, supportedSignatureAlgorithms, new DefaultTlsSrpGroupVerifier(), identity, password) - { - } - - public TlsSrpKeyExchange(int keyExchange, IList supportedSignatureAlgorithms, TlsSrpGroupVerifier groupVerifier, - byte[] identity, byte[] password) - : base(keyExchange, supportedSignatureAlgorithms) - { - this.mTlsSigner = CreateSigner(keyExchange); - this.mGroupVerifier = groupVerifier; - this.mIdentity = identity; - this.mPassword = password; - this.mSrpClient = new Srp6Client(); - } - - public TlsSrpKeyExchange(int keyExchange, IList supportedSignatureAlgorithms, byte[] identity, - TlsSrpLoginParameters loginParameters) - : base(keyExchange, supportedSignatureAlgorithms) - { - this.mTlsSigner = CreateSigner(keyExchange); - this.mIdentity = identity; - this.mSrpServer = new Srp6Server(); - this.mSrpGroup = loginParameters.Group; - this.mSrpVerifier = loginParameters.Verifier; - this.mSrpSalt = loginParameters.Salt; - } - - public override void Init(TlsContext context) - { - base.Init(context); - - if (this.mTlsSigner != null) - { - this.mTlsSigner.Init(context); - } - } - - public override void SkipServerCredentials() - { - if (mTlsSigner != null) - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - - public override void ProcessServerCertificate(Certificate serverCertificate) - { - if (mTlsSigner == null) - throw new TlsFatalAlert(AlertDescription.unexpected_message); - if (serverCertificate.IsEmpty) - throw new TlsFatalAlert(AlertDescription.decode_error); - - X509CertificateStructure x509Cert = serverCertificate.GetCertificateAt(0); - - SubjectPublicKeyInfo keyInfo = x509Cert.SubjectPublicKeyInfo; - try - { - this.mServerPublicKey = PublicKeyFactory.CreateKey(keyInfo); - } - catch (Exception e) - { - throw new TlsFatalAlert(AlertDescription.unsupported_certificate, e); - } - - if (!mTlsSigner.IsValidPublicKey(this.mServerPublicKey)) - throw new TlsFatalAlert(AlertDescription.certificate_unknown); - - TlsUtilities.ValidateKeyUsage(x509Cert, KeyUsage.DigitalSignature); - - base.ProcessServerCertificate(serverCertificate); - } - - public override void ProcessServerCredentials(TlsCredentials serverCredentials) - { - if ((mKeyExchange == KeyExchangeAlgorithm.SRP) || !(serverCredentials is TlsSignerCredentials)) - throw new TlsFatalAlert(AlertDescription.internal_error); - - ProcessServerCertificate(serverCredentials.Certificate); - - this.mServerCredentials = (TlsSignerCredentials)serverCredentials; - } - - public override bool RequiresServerKeyExchange - { - get { return true; } - } - - public override byte[] GenerateServerKeyExchange() - { - mSrpServer.Init(mSrpGroup, mSrpVerifier, TlsUtilities.CreateHash(HashAlgorithm.sha1), mContext.SecureRandom); - BigInteger B = mSrpServer.GenerateServerCredentials(); - - ServerSrpParams srpParams = new ServerSrpParams(mSrpGroup.N, mSrpGroup.G, mSrpSalt, B); - - DigestInputBuffer buf = new DigestInputBuffer(); - - srpParams.Encode(buf); - - if (mServerCredentials != null) - { - /* - * RFC 5246 4.7. digitally-signed element needs SignatureAndHashAlgorithm from TLS 1.2 - */ - SignatureAndHashAlgorithm signatureAndHashAlgorithm = TlsUtilities.GetSignatureAndHashAlgorithm( - mContext, mServerCredentials); - - IDigest d = TlsUtilities.CreateHash(signatureAndHashAlgorithm); - - SecurityParameters securityParameters = mContext.SecurityParameters; - d.BlockUpdate(securityParameters.clientRandom, 0, securityParameters.clientRandom.Length); - d.BlockUpdate(securityParameters.serverRandom, 0, securityParameters.serverRandom.Length); - buf.UpdateDigest(d); - - byte[] hash = new byte[d.GetDigestSize()]; - d.DoFinal(hash, 0); - - byte[] signature = mServerCredentials.GenerateCertificateSignature(hash); - - DigitallySigned signed_params = new DigitallySigned(signatureAndHashAlgorithm, signature); - signed_params.Encode(buf); - } - - return buf.ToArray(); - } - - public override void ProcessServerKeyExchange(Stream input) - { - SecurityParameters securityParameters = mContext.SecurityParameters; - - SignerInputBuffer buf = null; - Stream teeIn = input; - - if (mTlsSigner != null) - { - buf = new SignerInputBuffer(); - teeIn = new TeeInputStream(input, buf); - } - - ServerSrpParams srpParams = ServerSrpParams.Parse(teeIn); - - if (buf != null) - { - DigitallySigned signed_params = ParseSignature(input); - - ISigner signer = InitVerifyer(mTlsSigner, signed_params.Algorithm, securityParameters); - buf.UpdateSigner(signer); - if (!signer.VerifySignature(signed_params.Signature)) - throw new TlsFatalAlert(AlertDescription.decrypt_error); - } - - this.mSrpGroup = new Srp6GroupParameters(srpParams.N, srpParams.G); - - if (!mGroupVerifier.Accept(mSrpGroup)) - throw new TlsFatalAlert(AlertDescription.insufficient_security); - - this.mSrpSalt = srpParams.S; - - /* - * RFC 5054 2.5.3: The client MUST abort the handshake with an "illegal_parameter" alert if - * B % N = 0. - */ - try - { - this.mSrpPeerCredentials = Srp6Utilities.ValidatePublicValue(mSrpGroup.N, srpParams.B); - } - catch (CryptoException e) - { - throw new TlsFatalAlert(AlertDescription.illegal_parameter, e); - } - - this.mSrpClient.Init(mSrpGroup, TlsUtilities.CreateHash(HashAlgorithm.sha1), mContext.SecureRandom); - } - - public override void ValidateCertificateRequest(CertificateRequest certificateRequest) - { - throw new TlsFatalAlert(AlertDescription.unexpected_message); - } - - public override void ProcessClientCredentials(TlsCredentials clientCredentials) - { - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - public override void GenerateClientKeyExchange(Stream output) - { - BigInteger A = mSrpClient.GenerateClientCredentials(mSrpSalt, mIdentity, mPassword); - TlsSrpUtilities.WriteSrpParameter(A, output); - - mContext.SecurityParameters.srpIdentity = Arrays.Clone(mIdentity); - } - - public override void ProcessClientKeyExchange(Stream input) - { - /* - * RFC 5054 2.5.4: The server MUST abort the handshake with an "illegal_parameter" alert if - * A % N = 0. - */ - try - { - this.mSrpPeerCredentials = Srp6Utilities.ValidatePublicValue(mSrpGroup.N, TlsSrpUtilities.ReadSrpParameter(input)); - } - catch (CryptoException e) - { - throw new TlsFatalAlert(AlertDescription.illegal_parameter, e); - } - - mContext.SecurityParameters.srpIdentity = Arrays.Clone(mIdentity); - } - - public override byte[] GeneratePremasterSecret() - { - try - { - BigInteger S = mSrpServer != null - ? mSrpServer.CalculateSecret(mSrpPeerCredentials) - : mSrpClient.CalculateSecret(mSrpPeerCredentials); - - // TODO Check if this needs to be a fixed size - return BigIntegers.AsUnsignedByteArray(S); - } - catch (CryptoException e) - { - throw new TlsFatalAlert(AlertDescription.illegal_parameter, e); - } - } - - protected virtual ISigner InitVerifyer(TlsSigner tlsSigner, SignatureAndHashAlgorithm algorithm, - SecurityParameters securityParameters) - { - ISigner signer = tlsSigner.CreateVerifyer(algorithm, this.mServerPublicKey); - signer.BlockUpdate(securityParameters.clientRandom, 0, securityParameters.clientRandom.Length); - signer.BlockUpdate(securityParameters.serverRandom, 0, securityParameters.serverRandom.Length); - return signer; - } - } -} diff --git a/crypto/src/crypto/tls/TlsSrpLoginParameters.cs b/crypto/src/crypto/tls/TlsSrpLoginParameters.cs deleted file mode 100644 index 5ae4641f6..000000000 --- a/crypto/src/crypto/tls/TlsSrpLoginParameters.cs +++ /dev/null @@ -1,36 +0,0 @@ -using System; - -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Math; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class TlsSrpLoginParameters - { - protected readonly Srp6GroupParameters mGroup; - protected readonly BigInteger mVerifier; - protected readonly byte[] mSalt; - - public TlsSrpLoginParameters(Srp6GroupParameters group, BigInteger verifier, byte[] salt) - { - this.mGroup = group; - this.mVerifier = verifier; - this.mSalt = salt; - } - - public virtual Srp6GroupParameters Group - { - get { return mGroup; } - } - - public virtual byte[] Salt - { - get { return mSalt; } - } - - public virtual BigInteger Verifier - { - get { return mVerifier; } - } - } -} diff --git a/crypto/src/crypto/tls/TlsSrpUtilities.cs b/crypto/src/crypto/tls/TlsSrpUtilities.cs deleted file mode 100644 index 873189dc6..000000000 --- a/crypto/src/crypto/tls/TlsSrpUtilities.cs +++ /dev/null @@ -1,74 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -using Org.BouncyCastle.Math; -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public abstract class TlsSrpUtilities - { - public static void AddSrpExtension(IDictionary extensions, byte[] identity) - { - extensions[ExtensionType.srp] = CreateSrpExtension(identity); - } - - public static byte[] GetSrpExtension(IDictionary extensions) - { - byte[] extensionData = TlsUtilities.GetExtensionData(extensions, ExtensionType.srp); - return extensionData == null ? null : ReadSrpExtension(extensionData); - } - - public static byte[] CreateSrpExtension(byte[] identity) - { - if (identity == null) - throw new TlsFatalAlert(AlertDescription.internal_error); - - return TlsUtilities.EncodeOpaque8(identity); - } - - public static byte[] ReadSrpExtension(byte[] extensionData) - { - if (extensionData == null) - throw new ArgumentNullException("extensionData"); - - MemoryStream buf = new MemoryStream(extensionData, false); - byte[] identity = TlsUtilities.ReadOpaque8(buf); - - TlsProtocol.AssertEmpty(buf); - - return identity; - } - - public static BigInteger ReadSrpParameter(Stream input) - { - return new BigInteger(1, TlsUtilities.ReadOpaque16(input)); - } - - public static void WriteSrpParameter(BigInteger x, Stream output) - { - TlsUtilities.WriteOpaque16(BigIntegers.AsUnsignedByteArray(x), output); - } - - public static bool IsSrpCipherSuite(int cipherSuite) - { - switch (cipherSuite) - { - case CipherSuite.TLS_SRP_SHA_DSS_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_DSS_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_DSS_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_RSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_RSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_RSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_WITH_AES_256_CBC_SHA: - return true; - - default: - return false; - } - } - } -} diff --git a/crypto/src/crypto/tls/TlsSrtpUtilities.cs b/crypto/src/crypto/tls/TlsSrtpUtilities.cs deleted file mode 100644 index 626c0e3a4..000000000 --- a/crypto/src/crypto/tls/TlsSrtpUtilities.cs +++ /dev/null @@ -1,62 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /** - * RFC 5764 DTLS Extension to Establish Keys for SRTP. - */ - public abstract class TlsSRTPUtils - { - public static void AddUseSrtpExtension(IDictionary extensions, UseSrtpData useSRTPData) - { - extensions[ExtensionType.use_srtp] = CreateUseSrtpExtension(useSRTPData); - } - - public static UseSrtpData GetUseSrtpExtension(IDictionary extensions) - { - byte[] extensionData = TlsUtilities.GetExtensionData(extensions, ExtensionType.use_srtp); - return extensionData == null ? null : ReadUseSrtpExtension(extensionData); - } - - public static byte[] CreateUseSrtpExtension(UseSrtpData useSrtpData) - { - if (useSrtpData == null) - throw new ArgumentNullException("useSrtpData"); - - MemoryStream buf = new MemoryStream(); - - // SRTPProtectionProfiles - TlsUtilities.WriteUint16ArrayWithUint16Length(useSrtpData.ProtectionProfiles, buf); - - // srtp_mki - TlsUtilities.WriteOpaque8(useSrtpData.Mki, buf); - - return buf.ToArray(); - } - - public static UseSrtpData ReadUseSrtpExtension(byte[] extensionData) - { - if (extensionData == null) - throw new ArgumentNullException("extensionData"); - - MemoryStream buf = new MemoryStream(extensionData, true); - - // SRTPProtectionProfiles - int length = TlsUtilities.ReadUint16(buf); - if (length < 2 || (length & 1) != 0) - { - throw new TlsFatalAlert(AlertDescription.decode_error); - } - int[] protectionProfiles = TlsUtilities.ReadUint16Array(length / 2, buf); - - // srtp_mki - byte[] mki = TlsUtilities.ReadOpaque8(buf); - - TlsProtocol.AssertEmpty(buf); - - return new UseSrtpData(protectionProfiles, mki); - } - } -} diff --git a/crypto/src/crypto/tls/TlsStream.cs b/crypto/src/crypto/tls/TlsStream.cs deleted file mode 100644 index bfd80edf2..000000000 --- a/crypto/src/crypto/tls/TlsStream.cs +++ /dev/null @@ -1,97 +0,0 @@ -using System; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - internal class TlsStream - : Stream - { - private readonly TlsProtocol handler; - - internal TlsStream(TlsProtocol handler) - { - this.handler = handler; - } - - public override bool CanRead - { - get { return !handler.IsClosed; } - } - - public override bool CanSeek - { - get { return false; } - } - - public override bool CanWrite - { - get { return !handler.IsClosed; } - } - -#if PORTABLE - protected override void Dispose(bool disposing) - { - if (disposing) - { - handler.Close(); - } - base.Dispose(disposing); - } -#else - public override void Close() - { - handler.Close(); - base.Close(); - } -#endif - - public override void Flush() - { - handler.Flush(); - } - - public override long Length - { - get { throw new NotSupportedException(); } - } - - public override long Position - { - get { throw new NotSupportedException(); } - set { throw new NotSupportedException(); } - } - - public override int Read(byte[] buf, int off, int len) - { - return this.handler.ReadApplicationData(buf, off, len); - } - - public override int ReadByte() - { - byte[] buf = new byte[1]; - if (this.Read(buf, 0, 1) <= 0) - return -1; - return buf[0]; - } - - public override long Seek(long offset, SeekOrigin origin) - { - throw new NotSupportedException(); - } - - public override void SetLength(long value) - { - throw new NotSupportedException(); - } - - public override void Write(byte[] buf, int off, int len) - { - this.handler.WriteData(buf, off, len); - } - - public override void WriteByte(byte b) - { - this.handler.WriteData(new byte[] { b }, 0, 1); - } - } -} diff --git a/crypto/src/crypto/tls/TlsStreamCipher.cs b/crypto/src/crypto/tls/TlsStreamCipher.cs deleted file mode 100644 index 555442e9a..000000000 --- a/crypto/src/crypto/tls/TlsStreamCipher.cs +++ /dev/null @@ -1,152 +0,0 @@ -using System; -using System.IO; - -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Crypto.Tls; -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class TlsStreamCipher - : TlsCipher - { - protected readonly TlsContext context; - - protected readonly IStreamCipher encryptCipher; - protected readonly IStreamCipher decryptCipher; - - protected readonly TlsMac writeMac; - protected readonly TlsMac readMac; - - protected readonly bool usesNonce; - - /// <exception cref="IOException"></exception> - public TlsStreamCipher(TlsContext context, IStreamCipher clientWriteCipher, - IStreamCipher serverWriteCipher, IDigest clientWriteDigest, IDigest serverWriteDigest, - int cipherKeySize, bool usesNonce) - { - bool isServer = context.IsServer; - - this.context = context; - this.usesNonce = usesNonce; - - this.encryptCipher = clientWriteCipher; - this.decryptCipher = serverWriteCipher; - - int key_block_size = (2 * cipherKeySize) + clientWriteDigest.GetDigestSize() - + serverWriteDigest.GetDigestSize(); - - byte[] key_block = TlsUtilities.CalculateKeyBlock(context, key_block_size); - - int offset = 0; - - // Init MACs - TlsMac clientWriteMac = new TlsMac(context, clientWriteDigest, key_block, offset, - clientWriteDigest.GetDigestSize()); - offset += clientWriteDigest.GetDigestSize(); - TlsMac serverWriteMac = new TlsMac(context, serverWriteDigest, key_block, offset, - serverWriteDigest.GetDigestSize()); - offset += serverWriteDigest.GetDigestSize(); - - // Build keys - KeyParameter clientWriteKey = new KeyParameter(key_block, offset, cipherKeySize); - offset += cipherKeySize; - KeyParameter serverWriteKey = new KeyParameter(key_block, offset, cipherKeySize); - offset += cipherKeySize; - - if (offset != key_block_size) - { - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - ICipherParameters encryptParams, decryptParams; - if (isServer) - { - this.writeMac = serverWriteMac; - this.readMac = clientWriteMac; - this.encryptCipher = serverWriteCipher; - this.decryptCipher = clientWriteCipher; - encryptParams = serverWriteKey; - decryptParams = clientWriteKey; - } - else - { - this.writeMac = clientWriteMac; - this.readMac = serverWriteMac; - this.encryptCipher = clientWriteCipher; - this.decryptCipher = serverWriteCipher; - encryptParams = clientWriteKey; - decryptParams = serverWriteKey; - } - - if (usesNonce) - { - byte[] dummyNonce = new byte[8]; - encryptParams = new ParametersWithIV(encryptParams, dummyNonce); - decryptParams = new ParametersWithIV(decryptParams, dummyNonce); - } - - this.encryptCipher.Init(true, encryptParams); - this.decryptCipher.Init(false, decryptParams); - } - - public virtual int GetPlaintextLimit(int ciphertextLimit) - { - return ciphertextLimit - writeMac.Size; - } - - public virtual byte[] EncodePlaintext(long seqNo, byte type, byte[] plaintext, int offset, int len) - { - if (usesNonce) - { - UpdateIV(encryptCipher, true, seqNo); - } - - byte[] outBuf = new byte[len + writeMac.Size]; - - encryptCipher.ProcessBytes(plaintext, offset, len, outBuf, 0); - - byte[] mac = writeMac.CalculateMac(seqNo, type, plaintext, offset, len); - encryptCipher.ProcessBytes(mac, 0, mac.Length, outBuf, len); - - return outBuf; - } - - /// <exception cref="IOException"></exception> - public virtual byte[] DecodeCiphertext(long seqNo, byte type, byte[] ciphertext, int offset, int len) - { - if (usesNonce) - { - UpdateIV(decryptCipher, false, seqNo); - } - - int macSize = readMac.Size; - if (len < macSize) - throw new TlsFatalAlert(AlertDescription.decode_error); - - int plaintextLength = len - macSize; - - byte[] deciphered = new byte[len]; - decryptCipher.ProcessBytes(ciphertext, offset, len, deciphered, 0); - CheckMac(seqNo, type, deciphered, plaintextLength, len, deciphered, 0, plaintextLength); - return Arrays.CopyOfRange(deciphered, 0, plaintextLength); - } - - /// <exception cref="IOException"></exception> - protected virtual void CheckMac(long seqNo, byte type, byte[] recBuf, int recStart, int recEnd, byte[] calcBuf, int calcOff, int calcLen) - { - byte[] receivedMac = Arrays.CopyOfRange(recBuf, recStart, recEnd); - byte[] computedMac = readMac.CalculateMac(seqNo, type, calcBuf, calcOff, calcLen); - - if (!Arrays.ConstantTimeAreEqual(receivedMac, computedMac)) - throw new TlsFatalAlert(AlertDescription.bad_record_mac); - } - - protected virtual void UpdateIV(IStreamCipher cipher, bool forEncryption, long seqNo) - { - byte[] nonce = new byte[8]; - TlsUtilities.WriteUint64(seqNo, nonce, 0); - cipher.Init(forEncryption, new ParametersWithIV(null, nonce)); - } - } -} diff --git a/crypto/src/crypto/tls/TlsTimeoutException.cs b/crypto/src/crypto/tls/TlsTimeoutException.cs deleted file mode 100644 index 71931e43d..000000000 --- a/crypto/src/crypto/tls/TlsTimeoutException.cs +++ /dev/null @@ -1,23 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - public class TlsTimeoutException - : TlsException - { - public TlsTimeoutException() - : base() - { - } - - public TlsTimeoutException(string message) - : base(message) - { - } - - public TlsTimeoutException(string message, Exception cause) - : base(message, cause) - { - } - } -} diff --git a/crypto/src/crypto/tls/TlsUtilities.cs b/crypto/src/crypto/tls/TlsUtilities.cs deleted file mode 100644 index 2fb631edd..000000000 --- a/crypto/src/crypto/tls/TlsUtilities.cs +++ /dev/null @@ -1,2362 +0,0 @@ -using System; -using System.Collections; -#if !PORTABLE || DOTNET -using System.Net.Sockets; -#endif -using System.IO; - -using Org.BouncyCastle.Asn1; -using Org.BouncyCastle.Asn1.Nist; -using Org.BouncyCastle.Asn1.Pkcs; -using Org.BouncyCastle.Asn1.X509; -using Org.BouncyCastle.Crypto.Digests; -using Org.BouncyCastle.Crypto.Macs; -using Org.BouncyCastle.Crypto.Parameters; -using Org.BouncyCastle.Security; -using Org.BouncyCastle.Utilities; -using Org.BouncyCastle.Utilities.Date; -using Org.BouncyCastle.Utilities.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <remarks>Some helper functions for MicroTLS.</remarks> - public abstract class TlsUtilities - { - public static readonly byte[] EmptyBytes = new byte[0]; - public static readonly short[] EmptyShorts = new short[0]; - public static readonly int[] EmptyInts = new int[0]; - public static readonly long[] EmptyLongs = new long[0]; - - public static void CheckUint8(int i) - { - if (!IsValidUint8(i)) - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - public static void CheckUint8(long i) - { - if (!IsValidUint8(i)) - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - public static void CheckUint16(int i) - { - if (!IsValidUint16(i)) - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - public static void CheckUint16(long i) - { - if (!IsValidUint16(i)) - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - public static void CheckUint24(int i) - { - if (!IsValidUint24(i)) - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - public static void CheckUint24(long i) - { - if (!IsValidUint24(i)) - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - public static void CheckUint32(long i) - { - if (!IsValidUint32(i)) - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - public static void CheckUint48(long i) - { - if (!IsValidUint48(i)) - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - public static void CheckUint64(long i) - { - if (!IsValidUint64(i)) - throw new TlsFatalAlert(AlertDescription.internal_error); - } - - public static bool IsValidUint8(int i) - { - return (i & 0xFF) == i; - } - - public static bool IsValidUint8(long i) - { - return (i & 0xFFL) == i; - } - - public static bool IsValidUint16(int i) - { - return (i & 0xFFFF) == i; - } - - public static bool IsValidUint16(long i) - { - return (i & 0xFFFFL) == i; - } - - public static bool IsValidUint24(int i) - { - return (i & 0xFFFFFF) == i; - } - - public static bool IsValidUint24(long i) - { - return (i & 0xFFFFFFL) == i; - } - - public static bool IsValidUint32(long i) - { - return (i & 0xFFFFFFFFL) == i; - } - - public static bool IsValidUint48(long i) - { - return (i & 0xFFFFFFFFFFFFL) == i; - } - - public static bool IsValidUint64(long i) - { - return true; - } - - public static bool IsSsl(TlsContext context) - { - return context.ServerVersion.IsSsl; - } - - public static bool IsTlsV11(ProtocolVersion version) - { - return ProtocolVersion.TLSv11.IsEqualOrEarlierVersionOf(version.GetEquivalentTLSVersion()); - } - - public static bool IsTlsV11(TlsContext context) - { - return IsTlsV11(context.ServerVersion); - } - - public static bool IsTlsV12(ProtocolVersion version) - { - return ProtocolVersion.TLSv12.IsEqualOrEarlierVersionOf(version.GetEquivalentTLSVersion()); - } - - public static bool IsTlsV12(TlsContext context) - { - return IsTlsV12(context.ServerVersion); - } - - public static void WriteUint8(byte i, Stream output) - { - output.WriteByte(i); - } - - public static void WriteUint8(byte i, byte[] buf, int offset) - { - buf[offset] = i; - } - - public static void WriteUint16(int i, Stream output) - { - output.WriteByte((byte)(i >> 8)); - output.WriteByte((byte)i); - } - - public static void WriteUint16(int i, byte[] buf, int offset) - { - buf[offset] = (byte)(i >> 8); - buf[offset + 1] = (byte)i; - } - - public static void WriteUint24(int i, Stream output) - { - output.WriteByte((byte)(i >> 16)); - output.WriteByte((byte)(i >> 8)); - output.WriteByte((byte)i); - } - - public static void WriteUint24(int i, byte[] buf, int offset) - { - buf[offset] = (byte)(i >> 16); - buf[offset + 1] = (byte)(i >> 8); - buf[offset + 2] = (byte)i; - } - - public static void WriteUint32(long i, Stream output) - { - output.WriteByte((byte)(i >> 24)); - output.WriteByte((byte)(i >> 16)); - output.WriteByte((byte)(i >> 8)); - output.WriteByte((byte)i); - } - - public static void WriteUint32(long i, byte[] buf, int offset) - { - buf[offset] = (byte)(i >> 24); - buf[offset + 1] = (byte)(i >> 16); - buf[offset + 2] = (byte)(i >> 8); - buf[offset + 3] = (byte)i; - } - - public static void WriteUint48(long i, Stream output) - { - output.WriteByte((byte)(i >> 40)); - output.WriteByte((byte)(i >> 32)); - output.WriteByte((byte)(i >> 24)); - output.WriteByte((byte)(i >> 16)); - output.WriteByte((byte)(i >> 8)); - output.WriteByte((byte)i); - } - - public static void WriteUint48(long i, byte[] buf, int offset) - { - buf[offset] = (byte)(i >> 40); - buf[offset + 1] = (byte)(i >> 32); - buf[offset + 2] = (byte)(i >> 24); - buf[offset + 3] = (byte)(i >> 16); - buf[offset + 4] = (byte)(i >> 8); - buf[offset + 5] = (byte)i; - } - - public static void WriteUint64(long i, Stream output) - { - output.WriteByte((byte)(i >> 56)); - output.WriteByte((byte)(i >> 48)); - output.WriteByte((byte)(i >> 40)); - output.WriteByte((byte)(i >> 32)); - output.WriteByte((byte)(i >> 24)); - output.WriteByte((byte)(i >> 16)); - output.WriteByte((byte)(i >> 8)); - output.WriteByte((byte)i); - } - - public static void WriteUint64(long i, byte[] buf, int offset) - { - buf[offset] = (byte)(i >> 56); - buf[offset + 1] = (byte)(i >> 48); - buf[offset + 2] = (byte)(i >> 40); - buf[offset + 3] = (byte)(i >> 32); - buf[offset + 4] = (byte)(i >> 24); - buf[offset + 5] = (byte)(i >> 16); - buf[offset + 6] = (byte)(i >> 8); - buf[offset + 7] = (byte)i; - } - - public static void WriteOpaque8(byte[] buf, Stream output) - { - WriteUint8((byte)buf.Length, output); - output.Write(buf, 0, buf.Length); - } - - public static void WriteOpaque16(byte[] buf, Stream output) - { - WriteUint16(buf.Length, output); - output.Write(buf, 0, buf.Length); - } - - public static void WriteOpaque24(byte[] buf, Stream output) - { - WriteUint24(buf.Length, output); - output.Write(buf, 0, buf.Length); - } - - public static void WriteUint8Array(byte[] uints, Stream output) - { - output.Write(uints, 0, uints.Length); - } - - public static void WriteUint8Array(byte[] uints, byte[] buf, int offset) - { - for (int i = 0; i < uints.Length; ++i) - { - WriteUint8(uints[i], buf, offset); - ++offset; - } - } - - public static void WriteUint8ArrayWithUint8Length(byte[] uints, Stream output) - { - CheckUint8(uints.Length); - WriteUint8((byte)uints.Length, output); - WriteUint8Array(uints, output); - } - - public static void WriteUint8ArrayWithUint8Length(byte[] uints, byte[] buf, int offset) - { - CheckUint8(uints.Length); - WriteUint8((byte)uints.Length, buf, offset); - WriteUint8Array(uints, buf, offset + 1); - } - - public static void WriteUint16Array(int[] uints, Stream output) - { - for (int i = 0; i < uints.Length; ++i) - { - WriteUint16(uints[i], output); - } - } - - public static void WriteUint16Array(int[] uints, byte[] buf, int offset) - { - for (int i = 0; i < uints.Length; ++i) - { - WriteUint16(uints[i], buf, offset); - offset += 2; - } - } - - public static void WriteUint16ArrayWithUint16Length(int[] uints, Stream output) - { - int length = 2 * uints.Length; - CheckUint16(length); - WriteUint16(length, output); - WriteUint16Array(uints, output); - } - - public static void WriteUint16ArrayWithUint16Length(int[] uints, byte[] buf, int offset) - { - int length = 2 * uints.Length; - CheckUint16(length); - WriteUint16(length, buf, offset); - WriteUint16Array(uints, buf, offset + 2); - } - - public static byte DecodeUint8(byte[] buf) - { - if (buf == null) - throw new ArgumentNullException("buf"); - if (buf.Length != 1) - throw new TlsFatalAlert(AlertDescription.decode_error); - return ReadUint8(buf, 0); - } - - public static byte[] DecodeUint8ArrayWithUint8Length(byte[] buf) - { - if (buf == null) - throw new ArgumentNullException("buf"); - - int count = ReadUint8(buf, 0); - if (buf.Length != (count + 1)) - throw new TlsFatalAlert(AlertDescription.decode_error); - - byte[] uints = new byte[count]; - for (int i = 0; i < count; ++i) - { - uints[i] = ReadUint8(buf, i + 1); - } - return uints; - } - - public static byte[] EncodeOpaque8(byte[] buf) - { - CheckUint8(buf.Length); - return Arrays.Prepend(buf, (byte)buf.Length); - } - - public static byte[] EncodeUint8(byte val) - { - CheckUint8(val); - - byte[] extensionData = new byte[1]; - WriteUint8(val, extensionData, 0); - return extensionData; - } - - public static byte[] EncodeUint8ArrayWithUint8Length(byte[] uints) - { - byte[] result = new byte[1 + uints.Length]; - WriteUint8ArrayWithUint8Length(uints, result, 0); - return result; - } - - public static byte[] EncodeUint16ArrayWithUint16Length(int[] uints) - { - int length = 2 * uints.Length; - byte[] result = new byte[2 + length]; - WriteUint16ArrayWithUint16Length(uints, result, 0); - return result; - } - - public static byte ReadUint8(Stream input) - { - int i = input.ReadByte(); - if (i < 0) - throw new EndOfStreamException(); - return (byte)i; - } - - public static byte ReadUint8(byte[] buf, int offset) - { - return buf[offset]; - } - - public static int ReadUint16(Stream input) - { - int i1 = input.ReadByte(); - int i2 = input.ReadByte(); - if (i2 < 0) - throw new EndOfStreamException(); - return (i1 << 8) | i2; - } - - public static int ReadUint16(byte[] buf, int offset) - { - uint n = (uint)buf[offset] << 8; - n |= (uint)buf[++offset]; - return (int)n; - } - - public static int ReadUint24(Stream input) - { - int i1 = input.ReadByte(); - int i2 = input.ReadByte(); - int i3 = input.ReadByte(); - if (i3 < 0) - throw new EndOfStreamException(); - return (i1 << 16) | (i2 << 8) | i3; - } - - public static int ReadUint24(byte[] buf, int offset) - { - uint n = (uint)buf[offset] << 16; - n |= (uint)buf[++offset] << 8; - n |= (uint)buf[++offset]; - return (int)n; - } - - public static long ReadUint32(Stream input) - { - int i1 = input.ReadByte(); - int i2 = input.ReadByte(); - int i3 = input.ReadByte(); - int i4 = input.ReadByte(); - if (i4 < 0) - throw new EndOfStreamException(); - return (long)(uint)((i1 << 24) | (i2 << 16) | (i3 << 8) | i4); - } - - public static long ReadUint32(byte[] buf, int offset) - { - uint n = (uint)buf[offset] << 24; - n |= (uint)buf[++offset] << 16; - n |= (uint)buf[++offset] << 8; - n |= (uint)buf[++offset]; - return (long)n; - } - - public static long ReadUint48(Stream input) - { - int hi = ReadUint24(input); - int lo = ReadUint24(input); - return ((long)(hi & 0xffffffffL) << 24) | (long)(lo & 0xffffffffL); - } - - public static long ReadUint48(byte[] buf, int offset) - { - int hi = ReadUint24(buf, offset); - int lo = ReadUint24(buf, offset + 3); - return ((long)(hi & 0xffffffffL) << 24) | (long)(lo & 0xffffffffL); - } - - public static byte[] ReadAllOrNothing(int length, Stream input) - { - if (length < 1) - return EmptyBytes; - byte[] buf = new byte[length]; - int read = Streams.ReadFully(input, buf); - if (read == 0) - return null; - if (read != length) - throw new EndOfStreamException(); - return buf; - } - - public static byte[] ReadFully(int length, Stream input) - { - if (length < 1) - return EmptyBytes; - byte[] buf = new byte[length]; - if (length != Streams.ReadFully(input, buf)) - throw new EndOfStreamException(); - return buf; - } - - public static void ReadFully(byte[] buf, Stream input) - { - if (Streams.ReadFully(input, buf, 0, buf.Length) < buf.Length) - throw new EndOfStreamException(); - } - - public static byte[] ReadOpaque8(Stream input) - { - byte length = ReadUint8(input); - byte[] bytes = new byte[length]; - ReadFully(bytes, input); - return bytes; - } - - public static byte[] ReadOpaque16(Stream input) - { - int length = ReadUint16(input); - byte[] bytes = new byte[length]; - ReadFully(bytes, input); - return bytes; - } - - public static byte[] ReadOpaque24(Stream input) - { - int length = ReadUint24(input); - return ReadFully(length, input); - } - - public static byte[] ReadUint8Array(int count, Stream input) - { - byte[] uints = new byte[count]; - for (int i = 0; i < count; ++i) - { - uints[i] = ReadUint8(input); - } - return uints; - } - - public static int[] ReadUint16Array(int count, Stream input) - { - int[] uints = new int[count]; - for (int i = 0; i < count; ++i) - { - uints[i] = ReadUint16(input); - } - return uints; - } - - public static ProtocolVersion ReadVersion(byte[] buf, int offset) - { - return ProtocolVersion.Get(buf[offset], buf[offset + 1]); - } - - public static ProtocolVersion ReadVersion(Stream input) - { - int i1 = input.ReadByte(); - int i2 = input.ReadByte(); - if (i2 < 0) - throw new EndOfStreamException(); - return ProtocolVersion.Get(i1, i2); - } - - public static int ReadVersionRaw(byte[] buf, int offset) - { - return (buf[offset] << 8) | buf[offset + 1]; - } - - public static int ReadVersionRaw(Stream input) - { - int i1 = input.ReadByte(); - int i2 = input.ReadByte(); - if (i2 < 0) - throw new EndOfStreamException(); - return (i1 << 8) | i2; - } - - public static Asn1Object ReadAsn1Object(byte[] encoding) - { - MemoryStream input = new MemoryStream(encoding, false); - Asn1InputStream asn1 = new Asn1InputStream(input, encoding.Length); - Asn1Object result = asn1.ReadObject(); - if (null == result) - throw new TlsFatalAlert(AlertDescription.decode_error); - if (input.Position != input.Length) - throw new TlsFatalAlert(AlertDescription.decode_error); - return result; - } - - public static Asn1Object ReadDerObject(byte[] encoding) - { - /* - * NOTE: The current ASN.1 parsing code can't enforce DER-only parsing, but since DER is - * canonical, we can check it by re-encoding the result and comparing to the original. - */ - Asn1Object result = ReadAsn1Object(encoding); - byte[] check = result.GetEncoded(Asn1Encodable.Der); - if (!Arrays.AreEqual(check, encoding)) - throw new TlsFatalAlert(AlertDescription.decode_error); - return result; - } - - public static void WriteGmtUnixTime(byte[] buf, int offset) - { - int t = (int)(DateTimeUtilities.CurrentUnixMs() / 1000L); - buf[offset] = (byte)(t >> 24); - buf[offset + 1] = (byte)(t >> 16); - buf[offset + 2] = (byte)(t >> 8); - buf[offset + 3] = (byte)t; - } - - public static void WriteVersion(ProtocolVersion version, Stream output) - { - output.WriteByte((byte)version.MajorVersion); - output.WriteByte((byte)version.MinorVersion); - } - - public static void WriteVersion(ProtocolVersion version, byte[] buf, int offset) - { - buf[offset] = (byte)version.MajorVersion; - buf[offset + 1] = (byte)version.MinorVersion; - } - - public static IList GetAllSignatureAlgorithms() - { - IList v = Platform.CreateArrayList(4); - v.Add(SignatureAlgorithm.anonymous); - v.Add(SignatureAlgorithm.rsa); - v.Add(SignatureAlgorithm.dsa); - v.Add(SignatureAlgorithm.ecdsa); - return v; - } - - public static IList GetDefaultDssSignatureAlgorithms() - { - return VectorOfOne(new SignatureAndHashAlgorithm(HashAlgorithm.sha1, SignatureAlgorithm.dsa)); - } - - public static IList GetDefaultECDsaSignatureAlgorithms() - { - return VectorOfOne(new SignatureAndHashAlgorithm(HashAlgorithm.sha1, SignatureAlgorithm.ecdsa)); - } - - public static IList GetDefaultRsaSignatureAlgorithms() - { - return VectorOfOne(new SignatureAndHashAlgorithm(HashAlgorithm.sha1, SignatureAlgorithm.rsa)); - } - - public static byte[] GetExtensionData(IDictionary extensions, int extensionType) - { - return extensions == null ? null : (byte[])extensions[extensionType]; - } - - public static IList GetDefaultSupportedSignatureAlgorithms() - { - byte[] hashAlgorithms = new byte[]{ HashAlgorithm.sha1, HashAlgorithm.sha224, HashAlgorithm.sha256, - HashAlgorithm.sha384, HashAlgorithm.sha512 }; - byte[] signatureAlgorithms = new byte[]{ SignatureAlgorithm.rsa, SignatureAlgorithm.dsa, - SignatureAlgorithm.ecdsa }; - - IList result = Platform.CreateArrayList(); - for (int i = 0; i < signatureAlgorithms.Length; ++i) - { - for (int j = 0; j < hashAlgorithms.Length; ++j) - { - result.Add(new SignatureAndHashAlgorithm(hashAlgorithms[j], signatureAlgorithms[i])); - } - } - return result; - } - - public static SignatureAndHashAlgorithm GetSignatureAndHashAlgorithm(TlsContext context, - TlsSignerCredentials signerCredentials) - { - SignatureAndHashAlgorithm signatureAndHashAlgorithm = null; - if (IsTlsV12(context)) - { - signatureAndHashAlgorithm = signerCredentials.SignatureAndHashAlgorithm; - if (signatureAndHashAlgorithm == null) - throw new TlsFatalAlert(AlertDescription.internal_error); - } - return signatureAndHashAlgorithm; - } - - public static bool HasExpectedEmptyExtensionData(IDictionary extensions, int extensionType, - byte alertDescription) - { - byte[] extension_data = GetExtensionData(extensions, extensionType); - if (extension_data == null) - return false; - if (extension_data.Length != 0) - throw new TlsFatalAlert(alertDescription); - return true; - } - - public static TlsSession ImportSession(byte[] sessionID, SessionParameters sessionParameters) - { - return new TlsSessionImpl(sessionID, sessionParameters); - } - - public static bool IsSignatureAlgorithmsExtensionAllowed(ProtocolVersion clientVersion) - { - return ProtocolVersion.TLSv12.IsEqualOrEarlierVersionOf(clientVersion.GetEquivalentTLSVersion()); - } - - /** - * Add a 'signature_algorithms' extension to existing extensions. - * - * @param extensions A {@link Hashtable} to add the extension to. - * @param supportedSignatureAlgorithms {@link Vector} containing at least 1 {@link SignatureAndHashAlgorithm}. - * @throws IOException - */ - public static void AddSignatureAlgorithmsExtension(IDictionary extensions, IList supportedSignatureAlgorithms) - { - extensions[ExtensionType.signature_algorithms] = CreateSignatureAlgorithmsExtension(supportedSignatureAlgorithms); - } - - /** - * Get a 'signature_algorithms' extension from extensions. - * - * @param extensions A {@link Hashtable} to get the extension from, if it is present. - * @return A {@link Vector} containing at least 1 {@link SignatureAndHashAlgorithm}, or null. - * @throws IOException - */ - public static IList GetSignatureAlgorithmsExtension(IDictionary extensions) - { - byte[] extensionData = GetExtensionData(extensions, ExtensionType.signature_algorithms); - return extensionData == null ? null : ReadSignatureAlgorithmsExtension(extensionData); - } - - /** - * Create a 'signature_algorithms' extension value. - * - * @param supportedSignatureAlgorithms A {@link Vector} containing at least 1 {@link SignatureAndHashAlgorithm}. - * @return A byte array suitable for use as an extension value. - * @throws IOException - */ - public static byte[] CreateSignatureAlgorithmsExtension(IList supportedSignatureAlgorithms) - { - MemoryStream buf = new MemoryStream(); - - // supported_signature_algorithms - EncodeSupportedSignatureAlgorithms(supportedSignatureAlgorithms, false, buf); - - return buf.ToArray(); - } - - /** - * Read 'signature_algorithms' extension data. - * - * @param extensionData The extension data. - * @return A {@link Vector} containing at least 1 {@link SignatureAndHashAlgorithm}. - * @throws IOException - */ - public static IList ReadSignatureAlgorithmsExtension(byte[] extensionData) - { - if (extensionData == null) - throw new ArgumentNullException("extensionData"); - - MemoryStream buf = new MemoryStream(extensionData, false); - - // supported_signature_algorithms - IList supported_signature_algorithms = ParseSupportedSignatureAlgorithms(false, buf); - - TlsProtocol.AssertEmpty(buf); - - return supported_signature_algorithms; - } - - public static void EncodeSupportedSignatureAlgorithms(IList supportedSignatureAlgorithms, bool allowAnonymous, - Stream output) - { - if (supportedSignatureAlgorithms == null) - throw new ArgumentNullException("supportedSignatureAlgorithms"); - if (supportedSignatureAlgorithms.Count < 1 || supportedSignatureAlgorithms.Count >= (1 << 15)) - throw new ArgumentException("must have length from 1 to (2^15 - 1)", "supportedSignatureAlgorithms"); - - // supported_signature_algorithms - int length = 2 * supportedSignatureAlgorithms.Count; - CheckUint16(length); - WriteUint16(length, output); - - foreach (SignatureAndHashAlgorithm entry in supportedSignatureAlgorithms) - { - if (!allowAnonymous && entry.Signature == SignatureAlgorithm.anonymous) - { - /* - * RFC 5246 7.4.1.4.1 The "anonymous" value is meaningless in this context but used - * in Section 7.4.3. It MUST NOT appear in this extension. - */ - throw new ArgumentException( - "SignatureAlgorithm.anonymous MUST NOT appear in the signature_algorithms extension"); - } - entry.Encode(output); - } - } - - public static IList ParseSupportedSignatureAlgorithms(bool allowAnonymous, Stream input) - { - // supported_signature_algorithms - int length = ReadUint16(input); - if (length < 2 || (length & 1) != 0) - throw new TlsFatalAlert(AlertDescription.decode_error); - int count = length / 2; - IList supportedSignatureAlgorithms = Platform.CreateArrayList(count); - for (int i = 0; i < count; ++i) - { - SignatureAndHashAlgorithm entry = SignatureAndHashAlgorithm.Parse(input); - if (!allowAnonymous && entry.Signature == SignatureAlgorithm.anonymous) - { - /* - * RFC 5246 7.4.1.4.1 The "anonymous" value is meaningless in this context but used - * in Section 7.4.3. It MUST NOT appear in this extension. - */ - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - supportedSignatureAlgorithms.Add(entry); - } - return supportedSignatureAlgorithms; - } - - public static void VerifySupportedSignatureAlgorithm(IList supportedSignatureAlgorithms, SignatureAndHashAlgorithm signatureAlgorithm) - { - if (supportedSignatureAlgorithms == null) - throw new ArgumentNullException("supportedSignatureAlgorithms"); - if (supportedSignatureAlgorithms.Count < 1 || supportedSignatureAlgorithms.Count >= (1 << 15)) - throw new ArgumentException("must have length from 1 to (2^15 - 1)", "supportedSignatureAlgorithms"); - if (signatureAlgorithm == null) - throw new ArgumentNullException("signatureAlgorithm"); - - if (signatureAlgorithm.Signature != SignatureAlgorithm.anonymous) - { - foreach (SignatureAndHashAlgorithm entry in supportedSignatureAlgorithms) - { - if (entry.Hash == signatureAlgorithm.Hash && entry.Signature == signatureAlgorithm.Signature) - return; - } - } - - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - - public static byte[] PRF(TlsContext context, byte[] secret, string asciiLabel, byte[] seed, int size) - { - ProtocolVersion version = context.ServerVersion; - - if (version.IsSsl) - throw new InvalidOperationException("No PRF available for SSLv3 session"); - - byte[] label = Strings.ToByteArray(asciiLabel); - byte[] labelSeed = Concat(label, seed); - - int prfAlgorithm = context.SecurityParameters.PrfAlgorithm; - - if (prfAlgorithm == PrfAlgorithm.tls_prf_legacy) - return PRF_legacy(secret, label, labelSeed, size); - - IDigest prfDigest = CreatePrfHash(prfAlgorithm); - byte[] buf = new byte[size]; - HMacHash(prfDigest, secret, labelSeed, buf); - return buf; - } - - public static byte[] PRF_legacy(byte[] secret, string asciiLabel, byte[] seed, int size) - { - byte[] label = Strings.ToByteArray(asciiLabel); - byte[] labelSeed = Concat(label, seed); - - return PRF_legacy(secret, label, labelSeed, size); - } - - internal static byte[] PRF_legacy(byte[] secret, byte[] label, byte[] labelSeed, int size) - { - int s_half = (secret.Length + 1) / 2; - byte[] s1 = new byte[s_half]; - byte[] s2 = new byte[s_half]; - Array.Copy(secret, 0, s1, 0, s_half); - Array.Copy(secret, secret.Length - s_half, s2, 0, s_half); - - byte[] b1 = new byte[size]; - byte[] b2 = new byte[size]; - HMacHash(CreateHash(HashAlgorithm.md5), s1, labelSeed, b1); - HMacHash(CreateHash(HashAlgorithm.sha1), s2, labelSeed, b2); - for (int i = 0; i < size; i++) - { - b1[i] ^= b2[i]; - } - return b1; - } - - internal static byte[] Concat(byte[] a, byte[] b) - { - byte[] c = new byte[a.Length + b.Length]; - Array.Copy(a, 0, c, 0, a.Length); - Array.Copy(b, 0, c, a.Length, b.Length); - return c; - } - - internal static void HMacHash(IDigest digest, byte[] secret, byte[] seed, byte[] output) - { - HMac mac = new HMac(digest); - mac.Init(new KeyParameter(secret)); - byte[] a = seed; - int size = digest.GetDigestSize(); - int iterations = (output.Length + size - 1) / size; - byte[] buf = new byte[mac.GetMacSize()]; - byte[] buf2 = new byte[mac.GetMacSize()]; - for (int i = 0; i < iterations; i++) - { - mac.BlockUpdate(a, 0, a.Length); - mac.DoFinal(buf, 0); - a = buf; - mac.BlockUpdate(a, 0, a.Length); - mac.BlockUpdate(seed, 0, seed.Length); - mac.DoFinal(buf2, 0); - Array.Copy(buf2, 0, output, (size * i), System.Math.Min(size, output.Length - (size * i))); - } - } - - internal static void ValidateKeyUsage(X509CertificateStructure c, int keyUsageBits) - { - X509Extensions exts = c.TbsCertificate.Extensions; - if (exts != null) - { - X509Extension ext = exts.GetExtension(X509Extensions.KeyUsage); - if (ext != null) - { - DerBitString ku = KeyUsage.GetInstance(ext); - int bits = ku.GetBytes()[0]; - if ((bits & keyUsageBits) != keyUsageBits) - throw new TlsFatalAlert(AlertDescription.certificate_unknown); - } - } - } - - internal static byte[] CalculateKeyBlock(TlsContext context, int size) - { - SecurityParameters securityParameters = context.SecurityParameters; - byte[] master_secret = securityParameters.MasterSecret; - byte[] seed = Concat(securityParameters.ServerRandom, securityParameters.ClientRandom); - - if (IsSsl(context)) - return CalculateKeyBlock_Ssl(master_secret, seed, size); - - return PRF(context, master_secret, ExporterLabel.key_expansion, seed, size); - } - - internal static byte[] CalculateKeyBlock_Ssl(byte[] master_secret, byte[] random, int size) - { - IDigest md5 = CreateHash(HashAlgorithm.md5); - IDigest sha1 = CreateHash(HashAlgorithm.sha1); - int md5Size = md5.GetDigestSize(); - byte[] shatmp = new byte[sha1.GetDigestSize()]; - byte[] tmp = new byte[size + md5Size]; - - int i = 0, pos = 0; - while (pos < size) - { - byte[] ssl3Const = SSL3_CONST[i]; - - sha1.BlockUpdate(ssl3Const, 0, ssl3Const.Length); - sha1.BlockUpdate(master_secret, 0, master_secret.Length); - sha1.BlockUpdate(random, 0, random.Length); - sha1.DoFinal(shatmp, 0); - - md5.BlockUpdate(master_secret, 0, master_secret.Length); - md5.BlockUpdate(shatmp, 0, shatmp.Length); - md5.DoFinal(tmp, pos); - - pos += md5Size; - ++i; - } - - return Arrays.CopyOfRange(tmp, 0, size); - } - - internal static byte[] CalculateMasterSecret(TlsContext context, byte[] pre_master_secret) - { - SecurityParameters securityParameters = context.SecurityParameters; - - byte[] seed = securityParameters.IsExtendedMasterSecret - ? securityParameters.SessionHash - : Concat(securityParameters.ClientRandom, securityParameters.ServerRandom); - - if (IsSsl(context)) - return CalculateMasterSecret_Ssl(pre_master_secret, seed); - - string asciiLabel = securityParameters.IsExtendedMasterSecret - ? ExporterLabel.extended_master_secret - : ExporterLabel.master_secret; - - return PRF(context, pre_master_secret, asciiLabel, seed, 48); - } - - internal static byte[] CalculateMasterSecret_Ssl(byte[] pre_master_secret, byte[] random) - { - IDigest md5 = CreateHash(HashAlgorithm.md5); - IDigest sha1 = CreateHash(HashAlgorithm.sha1); - int md5Size = md5.GetDigestSize(); - byte[] shatmp = new byte[sha1.GetDigestSize()]; - - byte[] rval = new byte[md5Size * 3]; - int pos = 0; - - for (int i = 0; i < 3; ++i) - { - byte[] ssl3Const = SSL3_CONST[i]; - - sha1.BlockUpdate(ssl3Const, 0, ssl3Const.Length); - sha1.BlockUpdate(pre_master_secret, 0, pre_master_secret.Length); - sha1.BlockUpdate(random, 0, random.Length); - sha1.DoFinal(shatmp, 0); - - md5.BlockUpdate(pre_master_secret, 0, pre_master_secret.Length); - md5.BlockUpdate(shatmp, 0, shatmp.Length); - md5.DoFinal(rval, pos); - - pos += md5Size; - } - - return rval; - } - - internal static byte[] CalculateVerifyData(TlsContext context, string asciiLabel, byte[] handshakeHash) - { - if (IsSsl(context)) - return handshakeHash; - - SecurityParameters securityParameters = context.SecurityParameters; - byte[] master_secret = securityParameters.MasterSecret; - int verify_data_length = securityParameters.VerifyDataLength; - - return PRF(context, master_secret, asciiLabel, handshakeHash, verify_data_length); - } - - public static IDigest CreateHash(byte hashAlgorithm) - { - switch (hashAlgorithm) - { - case HashAlgorithm.md5: - return new MD5Digest(); - case HashAlgorithm.sha1: - return new Sha1Digest(); - case HashAlgorithm.sha224: - return new Sha224Digest(); - case HashAlgorithm.sha256: - return new Sha256Digest(); - case HashAlgorithm.sha384: - return new Sha384Digest(); - case HashAlgorithm.sha512: - return new Sha512Digest(); - default: - throw new ArgumentException("unknown HashAlgorithm", "hashAlgorithm"); - } - } - - public static IDigest CreateHash(SignatureAndHashAlgorithm signatureAndHashAlgorithm) - { - return signatureAndHashAlgorithm == null - ? new CombinedHash() - : CreateHash(signatureAndHashAlgorithm.Hash); - } - - public static IDigest CloneHash(byte hashAlgorithm, IDigest hash) - { - switch (hashAlgorithm) - { - case HashAlgorithm.md5: - return new MD5Digest((MD5Digest)hash); - case HashAlgorithm.sha1: - return new Sha1Digest((Sha1Digest)hash); - case HashAlgorithm.sha224: - return new Sha224Digest((Sha224Digest)hash); - case HashAlgorithm.sha256: - return new Sha256Digest((Sha256Digest)hash); - case HashAlgorithm.sha384: - return new Sha384Digest((Sha384Digest)hash); - case HashAlgorithm.sha512: - return new Sha512Digest((Sha512Digest)hash); - default: - throw new ArgumentException("unknown HashAlgorithm", "hashAlgorithm"); - } - } - - public static IDigest CreatePrfHash(int prfAlgorithm) - { - switch (prfAlgorithm) - { - case PrfAlgorithm.tls_prf_legacy: - return new CombinedHash(); - default: - return CreateHash(GetHashAlgorithmForPrfAlgorithm(prfAlgorithm)); - } - } - - public static IDigest ClonePrfHash(int prfAlgorithm, IDigest hash) - { - switch (prfAlgorithm) - { - case PrfAlgorithm.tls_prf_legacy: - return new CombinedHash((CombinedHash)hash); - default: - return CloneHash(GetHashAlgorithmForPrfAlgorithm(prfAlgorithm), hash); - } - } - - public static byte GetHashAlgorithmForPrfAlgorithm(int prfAlgorithm) - { - switch (prfAlgorithm) - { - case PrfAlgorithm.tls_prf_legacy: - throw new ArgumentException("legacy PRF not a valid algorithm", "prfAlgorithm"); - case PrfAlgorithm.tls_prf_sha256: - return HashAlgorithm.sha256; - case PrfAlgorithm.tls_prf_sha384: - return HashAlgorithm.sha384; - default: - throw new ArgumentException("unknown PrfAlgorithm", "prfAlgorithm"); - } - } - - public static DerObjectIdentifier GetOidForHashAlgorithm(byte hashAlgorithm) - { - switch (hashAlgorithm) - { - case HashAlgorithm.md5: - return PkcsObjectIdentifiers.MD5; - case HashAlgorithm.sha1: - return X509ObjectIdentifiers.IdSha1; - case HashAlgorithm.sha224: - return NistObjectIdentifiers.IdSha224; - case HashAlgorithm.sha256: - return NistObjectIdentifiers.IdSha256; - case HashAlgorithm.sha384: - return NistObjectIdentifiers.IdSha384; - case HashAlgorithm.sha512: - return NistObjectIdentifiers.IdSha512; - default: - throw new ArgumentException("unknown HashAlgorithm", "hashAlgorithm"); - } - } - - internal static short GetClientCertificateType(Certificate clientCertificate, Certificate serverCertificate) - { - if (clientCertificate.IsEmpty) - return -1; - - X509CertificateStructure x509Cert = clientCertificate.GetCertificateAt(0); - SubjectPublicKeyInfo keyInfo = x509Cert.SubjectPublicKeyInfo; - try - { - AsymmetricKeyParameter publicKey = PublicKeyFactory.CreateKey(keyInfo); - if (publicKey.IsPrivate) - throw new TlsFatalAlert(AlertDescription.internal_error); - - /* - * TODO RFC 5246 7.4.6. The certificates MUST be signed using an acceptable hash/ - * signature algorithm pair, as described in Section 7.4.4. Note that this relaxes the - * constraints on certificate-signing algorithms found in prior versions of TLS. - */ - - /* - * RFC 5246 7.4.6. Client Certificate - */ - - /* - * RSA public key; the certificate MUST allow the key to be used for signing with the - * signature scheme and hash algorithm that will be employed in the certificate verify - * message. - */ - if (publicKey is RsaKeyParameters) - { - ValidateKeyUsage(x509Cert, KeyUsage.DigitalSignature); - return ClientCertificateType.rsa_sign; - } - - /* - * DSA public key; the certificate MUST allow the key to be used for signing with the - * hash algorithm that will be employed in the certificate verify message. - */ - if (publicKey is DsaPublicKeyParameters) - { - ValidateKeyUsage(x509Cert, KeyUsage.DigitalSignature); - return ClientCertificateType.dss_sign; - } - - /* - * ECDSA-capable public key; the certificate MUST allow the key to be used for signing - * with the hash algorithm that will be employed in the certificate verify message; the - * public key MUST use a curve and point format supported by the server. - */ - if (publicKey is ECPublicKeyParameters) - { - ValidateKeyUsage(x509Cert, KeyUsage.DigitalSignature); - // TODO Check the curve and point format - return ClientCertificateType.ecdsa_sign; - } - - // TODO Add support for ClientCertificateType.*_fixed_* - - throw new TlsFatalAlert(AlertDescription.unsupported_certificate); - } - catch (Exception e) - { - throw new TlsFatalAlert(AlertDescription.unsupported_certificate, e); - } - } - - internal static void TrackHashAlgorithms(TlsHandshakeHash handshakeHash, IList supportedSignatureAlgorithms) - { - if (supportedSignatureAlgorithms != null) - { - foreach (SignatureAndHashAlgorithm signatureAndHashAlgorithm in supportedSignatureAlgorithms) - { - byte hashAlgorithm = signatureAndHashAlgorithm.Hash; - - if (HashAlgorithm.IsRecognized(hashAlgorithm)) - { - handshakeHash.TrackHashAlgorithm(hashAlgorithm); - } - else //if (HashAlgorithm.IsPrivate(hashAlgorithm)) - { - // TODO Support values in the "Reserved for Private Use" range - } - } - } - } - - public static bool HasSigningCapability(byte clientCertificateType) - { - switch (clientCertificateType) - { - case ClientCertificateType.dss_sign: - case ClientCertificateType.ecdsa_sign: - case ClientCertificateType.rsa_sign: - return true; - default: - return false; - } - } - - public static TlsSigner CreateTlsSigner(byte clientCertificateType) - { - switch (clientCertificateType) - { - case ClientCertificateType.dss_sign: - return new TlsDssSigner(); - case ClientCertificateType.ecdsa_sign: - return new TlsECDsaSigner(); - case ClientCertificateType.rsa_sign: - return new TlsRsaSigner(); - default: - throw new ArgumentException("not a type with signing capability", "clientCertificateType"); - } - } - - internal static readonly byte[] SSL_CLIENT = {0x43, 0x4C, 0x4E, 0x54}; - internal static readonly byte[] SSL_SERVER = {0x53, 0x52, 0x56, 0x52}; - - // SSL3 magic mix constants ("A", "BB", "CCC", ...) - internal static readonly byte[][] SSL3_CONST = GenSsl3Const(); - - private static byte[][] GenSsl3Const() - { - int n = 10; - byte[][] arr = new byte[n][]; - for (int i = 0; i < n; i++) - { - byte[] b = new byte[i + 1]; - Arrays.Fill(b, (byte)('A' + i)); - arr[i] = b; - } - return arr; - } - - private static IList VectorOfOne(object obj) - { - IList v = Platform.CreateArrayList(1); - v.Add(obj); - return v; - } - - public static int GetCipherType(int ciphersuite) - { - switch (GetEncryptionAlgorithm(ciphersuite)) - { - case EncryptionAlgorithm.AES_128_CCM: - case EncryptionAlgorithm.AES_128_CCM_8: - case EncryptionAlgorithm.AES_128_GCM: - case EncryptionAlgorithm.AES_128_OCB_TAGLEN96: - case EncryptionAlgorithm.AES_256_CCM: - case EncryptionAlgorithm.AES_256_CCM_8: - case EncryptionAlgorithm.AES_256_GCM: - case EncryptionAlgorithm.AES_256_OCB_TAGLEN96: - case EncryptionAlgorithm.CAMELLIA_128_GCM: - case EncryptionAlgorithm.CAMELLIA_256_GCM: - case EncryptionAlgorithm.CHACHA20_POLY1305: - return CipherType.aead; - - case EncryptionAlgorithm.RC2_CBC_40: - case EncryptionAlgorithm.IDEA_CBC: - case EncryptionAlgorithm.DES40_CBC: - case EncryptionAlgorithm.DES_CBC: - case EncryptionAlgorithm.cls_3DES_EDE_CBC: - case EncryptionAlgorithm.AES_128_CBC: - case EncryptionAlgorithm.AES_256_CBC: - case EncryptionAlgorithm.CAMELLIA_128_CBC: - case EncryptionAlgorithm.CAMELLIA_256_CBC: - case EncryptionAlgorithm.SEED_CBC: - return CipherType.block; - - case EncryptionAlgorithm.NULL: - case EncryptionAlgorithm.RC4_40: - case EncryptionAlgorithm.RC4_128: - return CipherType.stream; - - default: - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } - - public static int GetEncryptionAlgorithm(int ciphersuite) - { - switch (ciphersuite) - { - case CipherSuite.TLS_DH_anon_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_DH_DSS_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_DH_RSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_DHE_DSS_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_DHE_PSK_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_DHE_RSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_ECDH_anon_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_ECDHE_PSK_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_PSK_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_RSA_PSK_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_RSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_DSS_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_RSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_WITH_3DES_EDE_CBC_SHA: - return EncryptionAlgorithm.cls_3DES_EDE_CBC; - - case CipherSuite.TLS_DH_anon_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_DH_anon_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_DH_DSS_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_DH_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_DHE_DSS_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DHE_PSK_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_DHE_PSK_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDH_anon_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_PSK_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_PSK_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_RSA_PSK_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_RSA_PSK_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_RSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_SRP_SHA_DSS_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_RSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_WITH_AES_128_CBC_SHA: - return EncryptionAlgorithm.AES_128_CBC; - - case CipherSuite.TLS_DHE_PSK_WITH_AES_128_CCM: - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_CCM: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_CCM: - case CipherSuite.TLS_PSK_WITH_AES_128_CCM: - case CipherSuite.TLS_RSA_WITH_AES_128_CCM: - return EncryptionAlgorithm.AES_128_CCM; - - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_CCM_8: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_CCM_8: - case CipherSuite.TLS_PSK_DHE_WITH_AES_128_CCM_8: - case CipherSuite.TLS_PSK_WITH_AES_128_CCM_8: - case CipherSuite.TLS_RSA_WITH_AES_128_CCM_8: - return EncryptionAlgorithm.AES_128_CCM_8; - - case CipherSuite.TLS_DH_anon_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DHE_PSK_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_PSK_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_RSA_PSK_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_RSA_WITH_AES_128_GCM_SHA256: - return EncryptionAlgorithm.AES_128_GCM; - - case CipherSuite.TLS_DH_anon_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_DH_anon_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_DH_DSS_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_DH_RSA_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_DHE_DSS_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_DHE_PSK_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_DHE_PSK_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_ECDH_anon_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_PSK_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_ECDHE_PSK_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_PSK_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_PSK_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_RSA_PSK_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_RSA_PSK_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_RSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_RSA_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_SRP_SHA_DSS_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_RSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_WITH_AES_256_CBC_SHA: - return EncryptionAlgorithm.AES_256_CBC; - - case CipherSuite.TLS_DHE_PSK_WITH_AES_256_CCM: - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_CCM: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_CCM: - case CipherSuite.TLS_PSK_WITH_AES_256_CCM: - case CipherSuite.TLS_RSA_WITH_AES_256_CCM: - return EncryptionAlgorithm.AES_256_CCM; - - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_CCM_8: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_CCM_8: - case CipherSuite.TLS_PSK_DHE_WITH_AES_256_CCM_8: - case CipherSuite.TLS_PSK_WITH_AES_256_CCM_8: - case CipherSuite.TLS_RSA_WITH_AES_256_CCM_8: - return EncryptionAlgorithm.AES_256_CCM_8; - - case CipherSuite.TLS_DH_anon_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DH_DSS_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DH_RSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DHE_DSS_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DHE_PSK_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_PSK_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_RSA_PSK_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_RSA_WITH_AES_256_GCM_SHA384: - return EncryptionAlgorithm.AES_256_GCM; - - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_128_CBC_SHA: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_CAMELLIA_128_CBC_SHA: - case CipherSuite.TLS_DH_DSS_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_CAMELLIA_128_CBC_SHA: - case CipherSuite.TLS_DH_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_128_CBC_SHA: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DHE_PSK_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_128_CBC_SHA: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_ECDH_ECDSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_ECDH_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_PSK_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_PSK_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_RSA_WITH_CAMELLIA_128_CBC_SHA: - case CipherSuite.TLS_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_RSA_PSK_WITH_CAMELLIA_128_CBC_SHA256: - return EncryptionAlgorithm.CAMELLIA_128_CBC; - - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DHE_PSK_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_ECDH_ECDSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_ECDH_RSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_ECDHE_RSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_PSK_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_RSA_PSK_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_RSA_WITH_CAMELLIA_128_GCM_SHA256: - return EncryptionAlgorithm.CAMELLIA_128_GCM; - - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_256_CBC_SHA: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_CAMELLIA_256_CBC_SHA: - case CipherSuite.TLS_DH_DSS_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_CAMELLIA_256_CBC_SHA: - case CipherSuite.TLS_DH_RSA_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_256_CBC_SHA: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_DHE_PSK_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_256_CBC_SHA: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_ECDH_ECDSA_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_ECDH_RSA_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_PSK_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_RSA_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_PSK_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_RSA_WITH_CAMELLIA_256_CBC_SHA: - case CipherSuite.TLS_RSA_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_RSA_PSK_WITH_CAMELLIA_256_CBC_SHA384: - return EncryptionAlgorithm.CAMELLIA_256_CBC; - - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_DH_DSS_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_DH_RSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_DHE_PSK_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_ECDH_ECDSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_ECDH_RSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_ECDHE_RSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_PSK_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_RSA_PSK_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_RSA_WITH_CAMELLIA_256_GCM_SHA384: - return EncryptionAlgorithm.CAMELLIA_256_GCM; - - case CipherSuite.DRAFT_TLS_DHE_PSK_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.DRAFT_TLS_DHE_RSA_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.DRAFT_TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.DRAFT_TLS_ECDHE_PSK_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.DRAFT_TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.DRAFT_TLS_PSK_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.DRAFT_TLS_RSA_PSK_WITH_CHACHA20_POLY1305_SHA256: - return EncryptionAlgorithm.CHACHA20_POLY1305; - - case CipherSuite.TLS_RSA_WITH_NULL_MD5: - return EncryptionAlgorithm.NULL; - - case CipherSuite.TLS_DHE_PSK_WITH_NULL_SHA: - case CipherSuite.TLS_ECDH_anon_WITH_NULL_SHA: - case CipherSuite.TLS_ECDH_ECDSA_WITH_NULL_SHA: - case CipherSuite.TLS_ECDH_RSA_WITH_NULL_SHA: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_NULL_SHA: - case CipherSuite.TLS_ECDHE_PSK_WITH_NULL_SHA: - case CipherSuite.TLS_ECDHE_RSA_WITH_NULL_SHA: - case CipherSuite.TLS_PSK_WITH_NULL_SHA: - case CipherSuite.TLS_RSA_PSK_WITH_NULL_SHA: - case CipherSuite.TLS_RSA_WITH_NULL_SHA: - return EncryptionAlgorithm.NULL; - - case CipherSuite.TLS_DHE_PSK_WITH_NULL_SHA256: - case CipherSuite.TLS_ECDHE_PSK_WITH_NULL_SHA256: - case CipherSuite.TLS_PSK_WITH_NULL_SHA256: - case CipherSuite.TLS_RSA_PSK_WITH_NULL_SHA256: - case CipherSuite.TLS_RSA_WITH_NULL_SHA256: - return EncryptionAlgorithm.NULL; - - case CipherSuite.TLS_DHE_PSK_WITH_NULL_SHA384: - case CipherSuite.TLS_ECDHE_PSK_WITH_NULL_SHA384: - case CipherSuite.TLS_PSK_WITH_NULL_SHA384: - case CipherSuite.TLS_RSA_PSK_WITH_NULL_SHA384: - return EncryptionAlgorithm.NULL; - - case CipherSuite.TLS_DH_anon_WITH_RC4_128_MD5: - case CipherSuite.TLS_RSA_WITH_RC4_128_MD5: - return EncryptionAlgorithm.RC4_128; - - case CipherSuite.TLS_DHE_PSK_WITH_RC4_128_SHA: - case CipherSuite.TLS_ECDH_anon_WITH_RC4_128_SHA: - case CipherSuite.TLS_ECDH_ECDSA_WITH_RC4_128_SHA: - case CipherSuite.TLS_ECDH_RSA_WITH_RC4_128_SHA: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_RC4_128_SHA: - case CipherSuite.TLS_ECDHE_PSK_WITH_RC4_128_SHA: - case CipherSuite.TLS_ECDHE_RSA_WITH_RC4_128_SHA: - case CipherSuite.TLS_PSK_WITH_RC4_128_SHA: - case CipherSuite.TLS_RSA_WITH_RC4_128_SHA: - case CipherSuite.TLS_RSA_PSK_WITH_RC4_128_SHA: - return EncryptionAlgorithm.RC4_128; - - case CipherSuite.TLS_DH_anon_WITH_SEED_CBC_SHA: - case CipherSuite.TLS_DH_DSS_WITH_SEED_CBC_SHA: - case CipherSuite.TLS_DH_RSA_WITH_SEED_CBC_SHA: - case CipherSuite.TLS_DHE_DSS_WITH_SEED_CBC_SHA: - case CipherSuite.TLS_DHE_RSA_WITH_SEED_CBC_SHA: - case CipherSuite.TLS_RSA_WITH_SEED_CBC_SHA: - return EncryptionAlgorithm.SEED_CBC; - - default: - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } - - public static int GetKeyExchangeAlgorithm(int ciphersuite) - { - switch (ciphersuite) - { - case CipherSuite.TLS_DH_anon_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_DH_anon_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_DH_anon_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DH_anon_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DH_anon_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_DH_anon_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_DH_anon_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_128_CBC_SHA: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_256_CBC_SHA: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_DH_anon_WITH_RC4_128_MD5: - case CipherSuite.TLS_DH_anon_WITH_SEED_CBC_SHA: - return KeyExchangeAlgorithm.DH_anon; - - case CipherSuite.TLS_DH_DSS_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_DH_DSS_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_DH_DSS_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_DH_DSS_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DH_DSS_WITH_CAMELLIA_128_CBC_SHA: - case CipherSuite.TLS_DH_DSS_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_CAMELLIA_256_CBC_SHA: - case CipherSuite.TLS_DH_DSS_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_DH_DSS_WITH_SEED_CBC_SHA: - return KeyExchangeAlgorithm.DH_DSS; - - case CipherSuite.TLS_DH_RSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_DH_RSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_DH_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_DH_RSA_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DH_RSA_WITH_CAMELLIA_128_CBC_SHA: - case CipherSuite.TLS_DH_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_CAMELLIA_256_CBC_SHA: - case CipherSuite.TLS_DH_RSA_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_DH_RSA_WITH_SEED_CBC_SHA: - return KeyExchangeAlgorithm.DH_RSA; - - case CipherSuite.TLS_DHE_DSS_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_DHE_DSS_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_DHE_DSS_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_DHE_DSS_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_128_CBC_SHA: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_256_CBC_SHA: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_DHE_DSS_WITH_SEED_CBC_SHA: - return KeyExchangeAlgorithm.DHE_DSS; - - case CipherSuite.TLS_DHE_PSK_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_DHE_PSK_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_DHE_PSK_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DHE_PSK_WITH_AES_128_CCM: - case CipherSuite.TLS_DHE_PSK_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DHE_PSK_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_DHE_PSK_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_DHE_PSK_WITH_AES_256_CCM: - case CipherSuite.TLS_DHE_PSK_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DHE_PSK_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DHE_PSK_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DHE_PSK_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_DHE_PSK_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.DRAFT_TLS_DHE_PSK_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.TLS_DHE_PSK_WITH_NULL_SHA: - case CipherSuite.TLS_DHE_PSK_WITH_NULL_SHA256: - case CipherSuite.TLS_DHE_PSK_WITH_NULL_SHA384: - case CipherSuite.TLS_DHE_PSK_WITH_RC4_128_SHA: - case CipherSuite.TLS_PSK_DHE_WITH_AES_128_CCM_8: - case CipherSuite.TLS_PSK_DHE_WITH_AES_256_CCM_8: - return KeyExchangeAlgorithm.DHE_PSK; - - case CipherSuite.TLS_DHE_RSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_CCM: - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_CCM_8: - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_CCM: - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_CCM_8: - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_128_CBC_SHA: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_256_CBC_SHA: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.DRAFT_TLS_DHE_RSA_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_SEED_CBC_SHA: - return KeyExchangeAlgorithm.DHE_RSA; - - case CipherSuite.TLS_ECDH_anon_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_ECDH_anon_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_ECDH_anon_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_ECDH_anon_WITH_NULL_SHA: - case CipherSuite.TLS_ECDH_anon_WITH_RC4_128_SHA: - return KeyExchangeAlgorithm.ECDH_anon; - - case CipherSuite.TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_ECDH_ECDSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_ECDH_ECDSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_ECDH_ECDSA_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_ECDH_ECDSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_ECDH_ECDSA_WITH_NULL_SHA: - case CipherSuite.TLS_ECDH_ECDSA_WITH_RC4_128_SHA: - return KeyExchangeAlgorithm.ECDH_ECDSA; - - case CipherSuite.TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_ECDH_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_ECDH_RSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_ECDH_RSA_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_ECDH_RSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_ECDH_RSA_WITH_NULL_SHA: - case CipherSuite.TLS_ECDH_RSA_WITH_RC4_128_SHA: - return KeyExchangeAlgorithm.ECDH_RSA; - - case CipherSuite.TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_CCM: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_CCM_8: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_CCM: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_CCM_8: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.DRAFT_TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_NULL_SHA: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_RC4_128_SHA: - return KeyExchangeAlgorithm.ECDHE_ECDSA; - - case CipherSuite.TLS_ECDHE_PSK_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_PSK_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_ECDHE_PSK_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_PSK_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_PSK_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.DRAFT_TLS_ECDHE_PSK_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.TLS_ECDHE_PSK_WITH_NULL_SHA: - case CipherSuite.TLS_ECDHE_PSK_WITH_NULL_SHA256: - case CipherSuite.TLS_ECDHE_PSK_WITH_NULL_SHA384: - case CipherSuite.TLS_ECDHE_PSK_WITH_RC4_128_SHA: - return KeyExchangeAlgorithm.ECDHE_PSK; - - case CipherSuite.TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_ECDHE_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_RSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_ECDHE_RSA_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_RSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.DRAFT_TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.TLS_ECDHE_RSA_WITH_NULL_SHA: - case CipherSuite.TLS_ECDHE_RSA_WITH_RC4_128_SHA: - return KeyExchangeAlgorithm.ECDHE_RSA; - - case CipherSuite.TLS_PSK_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_PSK_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_PSK_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_PSK_WITH_AES_128_CCM: - case CipherSuite.TLS_PSK_WITH_AES_128_CCM_8: - case CipherSuite.TLS_PSK_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_PSK_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_PSK_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_PSK_WITH_AES_256_CCM: - case CipherSuite.TLS_PSK_WITH_AES_256_CCM_8: - case CipherSuite.TLS_PSK_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_PSK_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_PSK_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_PSK_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_PSK_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.DRAFT_TLS_PSK_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.TLS_PSK_WITH_NULL_SHA: - case CipherSuite.TLS_PSK_WITH_NULL_SHA256: - case CipherSuite.TLS_PSK_WITH_NULL_SHA384: - case CipherSuite.TLS_PSK_WITH_RC4_128_SHA: - return KeyExchangeAlgorithm.PSK; - - case CipherSuite.TLS_RSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_RSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_RSA_WITH_AES_128_CCM: - case CipherSuite.TLS_RSA_WITH_AES_128_CCM_8: - case CipherSuite.TLS_RSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_RSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_RSA_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_RSA_WITH_AES_256_CCM: - case CipherSuite.TLS_RSA_WITH_AES_256_CCM_8: - case CipherSuite.TLS_RSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_RSA_WITH_CAMELLIA_128_CBC_SHA: - case CipherSuite.TLS_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_RSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_RSA_WITH_CAMELLIA_256_CBC_SHA: - case CipherSuite.TLS_RSA_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_RSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.DRAFT_TLS_RSA_PSK_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.TLS_RSA_WITH_NULL_MD5: - case CipherSuite.TLS_RSA_WITH_NULL_SHA: - case CipherSuite.TLS_RSA_WITH_NULL_SHA256: - case CipherSuite.TLS_RSA_WITH_RC4_128_MD5: - case CipherSuite.TLS_RSA_WITH_RC4_128_SHA: - case CipherSuite.TLS_RSA_WITH_SEED_CBC_SHA: - return KeyExchangeAlgorithm.RSA; - - case CipherSuite.TLS_RSA_PSK_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_RSA_PSK_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_RSA_PSK_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_RSA_PSK_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_RSA_PSK_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_RSA_PSK_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_RSA_PSK_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_RSA_PSK_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_RSA_PSK_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_RSA_PSK_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_RSA_PSK_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_RSA_PSK_WITH_NULL_SHA: - case CipherSuite.TLS_RSA_PSK_WITH_NULL_SHA256: - case CipherSuite.TLS_RSA_PSK_WITH_NULL_SHA384: - case CipherSuite.TLS_RSA_PSK_WITH_RC4_128_SHA: - return KeyExchangeAlgorithm.RSA_PSK; - - case CipherSuite.TLS_SRP_SHA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_WITH_AES_256_CBC_SHA: - return KeyExchangeAlgorithm.SRP; - - case CipherSuite.TLS_SRP_SHA_DSS_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_DSS_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_DSS_WITH_AES_256_CBC_SHA: - return KeyExchangeAlgorithm.SRP_DSS; - - case CipherSuite.TLS_SRP_SHA_RSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_RSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_RSA_WITH_AES_256_CBC_SHA: - return KeyExchangeAlgorithm.SRP_RSA; - - default: - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } - - public static int GetMacAlgorithm(int ciphersuite) - { - switch (ciphersuite) - { - case CipherSuite.TLS_DH_anon_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DH_anon_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_DH_DSS_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DH_DSS_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_DH_RSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DH_RSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_DHE_DSS_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_DHE_PSK_WITH_AES_128_CCM: - case CipherSuite.TLS_DHE_PSK_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DHE_PSK_WITH_AES_256_CCM: - case CipherSuite.TLS_DHE_PSK_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DHE_PSK_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DHE_PSK_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.DRAFT_TLS_DHE_PSK_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_CCM: - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_CCM_8: - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_CCM: - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_CCM_8: - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.DRAFT_TLS_DHE_RSA_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_ECDH_ECDSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_ECDH_ECDSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_ECDH_RSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_ECDH_RSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_CCM: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_CCM_8: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_CCM: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_CCM_8: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.DRAFT_TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.DRAFT_TLS_ECDHE_PSK_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_ECDHE_RSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_ECDHE_RSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.DRAFT_TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.TLS_PSK_DHE_WITH_AES_128_CCM_8: - case CipherSuite.TLS_PSK_DHE_WITH_AES_256_CCM_8: - case CipherSuite.TLS_PSK_WITH_AES_128_CCM: - case CipherSuite.TLS_PSK_WITH_AES_128_CCM_8: - case CipherSuite.TLS_PSK_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_PSK_WITH_AES_256_CCM: - case CipherSuite.TLS_PSK_WITH_AES_256_CCM_8: - case CipherSuite.TLS_PSK_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_PSK_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_PSK_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.DRAFT_TLS_PSK_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.TLS_RSA_PSK_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_RSA_PSK_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_RSA_PSK_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_RSA_PSK_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.DRAFT_TLS_RSA_PSK_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.TLS_RSA_WITH_AES_128_CCM: - case CipherSuite.TLS_RSA_WITH_AES_128_CCM_8: - case CipherSuite.TLS_RSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_RSA_WITH_AES_256_CCM: - case CipherSuite.TLS_RSA_WITH_AES_256_CCM_8: - case CipherSuite.TLS_RSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_RSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_RSA_WITH_CAMELLIA_256_GCM_SHA384: - return MacAlgorithm.cls_null; - - case CipherSuite.TLS_DH_anon_WITH_RC4_128_MD5: - case CipherSuite.TLS_RSA_WITH_NULL_MD5: - case CipherSuite.TLS_RSA_WITH_RC4_128_MD5: - return MacAlgorithm.hmac_md5; - - case CipherSuite.TLS_DH_anon_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_DH_anon_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_DH_anon_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_128_CBC_SHA: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_256_CBC_SHA: - case CipherSuite.TLS_DH_anon_WITH_SEED_CBC_SHA: - case CipherSuite.TLS_DH_DSS_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_DH_DSS_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_DH_DSS_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_DH_DSS_WITH_CAMELLIA_128_CBC_SHA: - case CipherSuite.TLS_DH_DSS_WITH_CAMELLIA_256_CBC_SHA: - case CipherSuite.TLS_DH_DSS_WITH_SEED_CBC_SHA: - case CipherSuite.TLS_DH_RSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_DH_RSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_DH_RSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_DH_RSA_WITH_CAMELLIA_128_CBC_SHA: - case CipherSuite.TLS_DH_RSA_WITH_CAMELLIA_256_CBC_SHA: - case CipherSuite.TLS_DH_RSA_WITH_SEED_CBC_SHA: - case CipherSuite.TLS_DHE_DSS_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_DHE_DSS_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_DHE_DSS_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_128_CBC_SHA: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_256_CBC_SHA: - case CipherSuite.TLS_DHE_DSS_WITH_SEED_CBC_SHA: - case CipherSuite.TLS_DHE_PSK_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_DHE_PSK_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_DHE_PSK_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_DHE_PSK_WITH_NULL_SHA: - case CipherSuite.TLS_DHE_PSK_WITH_RC4_128_SHA: - case CipherSuite.TLS_DHE_RSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_128_CBC_SHA: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_256_CBC_SHA: - case CipherSuite.TLS_DHE_RSA_WITH_SEED_CBC_SHA: - case CipherSuite.TLS_ECDH_anon_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_ECDH_anon_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_ECDH_anon_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_ECDH_anon_WITH_NULL_SHA: - case CipherSuite.TLS_ECDH_anon_WITH_RC4_128_SHA: - case CipherSuite.TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_ECDH_ECDSA_WITH_NULL_SHA: - case CipherSuite.TLS_ECDH_ECDSA_WITH_RC4_128_SHA: - case CipherSuite.TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_ECDH_RSA_WITH_NULL_SHA: - case CipherSuite.TLS_ECDH_RSA_WITH_RC4_128_SHA: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_NULL_SHA: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_RC4_128_SHA: - case CipherSuite.TLS_ECDHE_PSK_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_ECDHE_PSK_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_ECDHE_PSK_WITH_NULL_SHA: - case CipherSuite.TLS_ECDHE_PSK_WITH_RC4_128_SHA: - case CipherSuite.TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_ECDHE_RSA_WITH_NULL_SHA: - case CipherSuite.TLS_ECDHE_RSA_WITH_RC4_128_SHA: - case CipherSuite.TLS_RSA_PSK_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_RSA_PSK_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_RSA_PSK_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_PSK_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_PSK_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_PSK_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_PSK_WITH_NULL_SHA: - case CipherSuite.TLS_PSK_WITH_RC4_128_SHA: - case CipherSuite.TLS_RSA_PSK_WITH_NULL_SHA: - case CipherSuite.TLS_RSA_PSK_WITH_RC4_128_SHA: - case CipherSuite.TLS_RSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_RSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_RSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_RSA_WITH_CAMELLIA_128_CBC_SHA: - case CipherSuite.TLS_RSA_WITH_CAMELLIA_256_CBC_SHA: - case CipherSuite.TLS_RSA_WITH_NULL_SHA: - case CipherSuite.TLS_RSA_WITH_RC4_128_SHA: - case CipherSuite.TLS_RSA_WITH_SEED_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_DSS_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_DSS_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_DSS_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_RSA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_RSA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_RSA_WITH_AES_256_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_WITH_3DES_EDE_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_WITH_AES_128_CBC_SHA: - case CipherSuite.TLS_SRP_SHA_WITH_AES_256_CBC_SHA: - return MacAlgorithm.hmac_sha1; - - case CipherSuite.TLS_DH_anon_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DH_anon_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_DHE_PSK_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DHE_PSK_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DHE_PSK_WITH_NULL_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDH_ECDSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDH_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_PSK_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_PSK_WITH_NULL_SHA256: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_PSK_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_PSK_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_PSK_WITH_NULL_SHA256: - case CipherSuite.TLS_RSA_PSK_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_RSA_PSK_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_RSA_PSK_WITH_NULL_SHA256: - case CipherSuite.TLS_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_RSA_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_RSA_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_RSA_WITH_NULL_SHA256: - return MacAlgorithm.hmac_sha256; - - case CipherSuite.TLS_DHE_PSK_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_DHE_PSK_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_DHE_PSK_WITH_NULL_SHA384: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDH_ECDSA_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDH_RSA_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_PSK_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_PSK_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_PSK_WITH_NULL_SHA384: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_RSA_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_PSK_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_PSK_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_PSK_WITH_NULL_SHA384: - case CipherSuite.TLS_RSA_PSK_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_RSA_PSK_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_RSA_PSK_WITH_NULL_SHA384: - return MacAlgorithm.hmac_sha384; - - default: - throw new TlsFatalAlert(AlertDescription.internal_error); - } - } - - public static ProtocolVersion GetMinimumVersion(int ciphersuite) - { - switch (ciphersuite) - { - case CipherSuite.TLS_DH_anon_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DH_anon_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DH_anon_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_DH_anon_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_DH_anon_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_DH_DSS_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DH_DSS_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_DH_DSS_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_DH_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DH_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_DH_RSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_DHE_DSS_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_DHE_DSS_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_DHE_PSK_WITH_AES_128_CCM: - case CipherSuite.TLS_DHE_PSK_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DHE_PSK_WITH_AES_256_CCM: - case CipherSuite.TLS_DHE_PSK_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DHE_PSK_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DHE_PSK_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.DRAFT_TLS_DHE_PSK_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_CCM: - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_CCM_8: - case CipherSuite.TLS_DHE_RSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_CCM: - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_CCM_8: - case CipherSuite.TLS_DHE_RSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_DHE_RSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.DRAFT_TLS_DHE_RSA_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDH_ECDSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_ECDH_ECDSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_ECDH_ECDSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_ECDH_ECDSA_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_ECDH_ECDSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDH_RSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_ECDH_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_ECDH_RSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_ECDH_RSA_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_ECDH_RSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_CCM: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_CCM_8: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_CCM: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_CCM_8: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_ECDSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.DRAFT_TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.DRAFT_TLS_ECDHE_PSK_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_ECDHE_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_ECDHE_RSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_ECDHE_RSA_WITH_CAMELLIA_256_CBC_SHA384: - case CipherSuite.TLS_ECDHE_RSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.DRAFT_TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.TLS_PSK_DHE_WITH_AES_128_CCM_8: - case CipherSuite.TLS_PSK_DHE_WITH_AES_256_CCM_8: - case CipherSuite.TLS_PSK_WITH_AES_128_CCM: - case CipherSuite.TLS_PSK_WITH_AES_128_CCM_8: - case CipherSuite.TLS_PSK_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_PSK_WITH_AES_256_CCM: - case CipherSuite.TLS_PSK_WITH_AES_256_CCM_8: - case CipherSuite.TLS_PSK_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_PSK_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_PSK_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.DRAFT_TLS_PSK_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.TLS_RSA_PSK_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_RSA_PSK_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_RSA_PSK_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_RSA_PSK_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.DRAFT_TLS_RSA_PSK_WITH_CHACHA20_POLY1305_SHA256: - case CipherSuite.TLS_RSA_WITH_AES_128_CBC_SHA256: - case CipherSuite.TLS_RSA_WITH_AES_128_CCM: - case CipherSuite.TLS_RSA_WITH_AES_128_CCM_8: - case CipherSuite.TLS_RSA_WITH_AES_128_GCM_SHA256: - case CipherSuite.TLS_RSA_WITH_AES_256_CBC_SHA256: - case CipherSuite.TLS_RSA_WITH_AES_256_CCM: - case CipherSuite.TLS_RSA_WITH_AES_256_CCM_8: - case CipherSuite.TLS_RSA_WITH_AES_256_GCM_SHA384: - case CipherSuite.TLS_RSA_WITH_CAMELLIA_128_CBC_SHA256: - case CipherSuite.TLS_RSA_WITH_CAMELLIA_128_GCM_SHA256: - case CipherSuite.TLS_RSA_WITH_CAMELLIA_256_CBC_SHA256: - case CipherSuite.TLS_RSA_WITH_CAMELLIA_256_GCM_SHA384: - case CipherSuite.TLS_RSA_WITH_NULL_SHA256: - return ProtocolVersion.TLSv12; - - default: - return ProtocolVersion.SSLv3; - } - } - - public static bool IsAeadCipherSuite(int ciphersuite) - { - return CipherType.aead == GetCipherType(ciphersuite); - } - - public static bool IsBlockCipherSuite(int ciphersuite) - { - return CipherType.block == GetCipherType(ciphersuite); - } - - public static bool IsStreamCipherSuite(int ciphersuite) - { - return CipherType.stream == GetCipherType(ciphersuite); - } - - public static bool IsValidCipherSuiteForSignatureAlgorithms(int cipherSuite, IList sigAlgs) - { - int keyExchangeAlgorithm; - try - { - keyExchangeAlgorithm = GetKeyExchangeAlgorithm(cipherSuite); - } - catch (IOException) - { - return true; - } - - switch (keyExchangeAlgorithm) - { - case KeyExchangeAlgorithm.DH_anon: - case KeyExchangeAlgorithm.DH_anon_EXPORT: - case KeyExchangeAlgorithm.ECDH_anon: - return sigAlgs.Contains(SignatureAlgorithm.anonymous); - - case KeyExchangeAlgorithm.DHE_RSA: - case KeyExchangeAlgorithm.DHE_RSA_EXPORT: - case KeyExchangeAlgorithm.ECDHE_RSA: - case KeyExchangeAlgorithm.SRP_RSA: - return sigAlgs.Contains(SignatureAlgorithm.rsa); - - case KeyExchangeAlgorithm.DHE_DSS: - case KeyExchangeAlgorithm.DHE_DSS_EXPORT: - case KeyExchangeAlgorithm.SRP_DSS: - return sigAlgs.Contains(SignatureAlgorithm.dsa); - - case KeyExchangeAlgorithm.ECDHE_ECDSA: - return sigAlgs.Contains(SignatureAlgorithm.ecdsa); - - default: - return true; - } - } - - public static bool IsValidCipherSuiteForVersion(int cipherSuite, ProtocolVersion serverVersion) - { - return GetMinimumVersion(cipherSuite).IsEqualOrEarlierVersionOf(serverVersion.GetEquivalentTLSVersion()); - } - - public static IList GetUsableSignatureAlgorithms(IList sigHashAlgs) - { - if (sigHashAlgs == null) - return GetAllSignatureAlgorithms(); - - IList v = Platform.CreateArrayList(4); - v.Add(SignatureAlgorithm.anonymous); - foreach (SignatureAndHashAlgorithm sigHashAlg in sigHashAlgs) - { - //if (sigHashAlg.Hash >= MINIMUM_HASH_STRICT) - { - byte sigAlg = sigHashAlg.Signature; - if (!v.Contains(sigAlg)) - { - v.Add(sigAlg); - } - } - } - return v; - } - -#if !PORTABLE || DOTNET - public static bool IsTimeout(SocketException e) - { -#if NET_1_1 - return 10060 == e.ErrorCode; -#else - return SocketError.TimedOut == e.SocketErrorCode; -#endif - } -#endif - } -} diff --git a/crypto/src/crypto/tls/UrlAndHash.cs b/crypto/src/crypto/tls/UrlAndHash.cs deleted file mode 100644 index 9ffd2cbf8..000000000 --- a/crypto/src/crypto/tls/UrlAndHash.cs +++ /dev/null @@ -1,94 +0,0 @@ -using System; -using System.IO; - -using Org.BouncyCastle.Utilities; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /** - * RFC 6066 5. - */ - public class UrlAndHash - { - protected readonly string mUrl; - protected readonly byte[] mSha1Hash; - - public UrlAndHash(string url, byte[] sha1Hash) - { - if (url == null || url.Length < 1 || url.Length >= (1 << 16)) - throw new ArgumentException("must have length from 1 to (2^16 - 1)", "url"); - if (sha1Hash != null && sha1Hash.Length != 20) - throw new ArgumentException("must have length == 20, if present", "sha1Hash"); - - this.mUrl = url; - this.mSha1Hash = sha1Hash; - } - - public virtual string Url - { - get { return mUrl; } - } - - public virtual byte[] Sha1Hash - { - get { return mSha1Hash; } - } - - /** - * Encode this {@link UrlAndHash} to a {@link Stream}. - * - * @param output the {@link Stream} to encode to. - * @throws IOException - */ - public virtual void Encode(Stream output) - { - byte[] urlEncoding = Strings.ToByteArray(this.mUrl); - TlsUtilities.WriteOpaque16(urlEncoding, output); - - if (this.mSha1Hash == null) - { - TlsUtilities.WriteUint8(0, output); - } - else - { - TlsUtilities.WriteUint8(1, output); - output.Write(this.mSha1Hash, 0, this.mSha1Hash.Length); - } - } - - /** - * Parse a {@link UrlAndHash} from a {@link Stream}. - * - * @param context - * the {@link TlsContext} of the current connection. - * @param input - * the {@link Stream} to parse from. - * @return a {@link UrlAndHash} object. - * @throws IOException - */ - public static UrlAndHash Parse(TlsContext context, Stream input) - { - byte[] urlEncoding = TlsUtilities.ReadOpaque16(input); - if (urlEncoding.Length < 1) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - string url = Strings.FromByteArray(urlEncoding); - - byte[] sha1Hash = null; - byte padding = TlsUtilities.ReadUint8(input); - switch (padding) - { - case 0: - if (TlsUtilities.IsTlsV12(context)) - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - break; - case 1: - sha1Hash = TlsUtilities.ReadFully(20, input); - break; - default: - throw new TlsFatalAlert(AlertDescription.illegal_parameter); - } - - return new UrlAndHash(url, sha1Hash); - } - } -} diff --git a/crypto/src/crypto/tls/UseSrtpData.cs b/crypto/src/crypto/tls/UseSrtpData.cs deleted file mode 100644 index fe8f8accb..000000000 --- a/crypto/src/crypto/tls/UseSrtpData.cs +++ /dev/null @@ -1,56 +0,0 @@ -using System; -using System.Collections; -using System.IO; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /** - * RFC 5764 4.1.1 - */ - public class UseSrtpData - { - protected readonly int[] mProtectionProfiles; - protected readonly byte[] mMki; - - /** - * @param protectionProfiles see {@link SrtpProtectionProfile} for valid constants. - * @param mki valid lengths from 0 to 255. - */ - public UseSrtpData(int[] protectionProfiles, byte[] mki) - { - if (protectionProfiles == null || protectionProfiles.Length < 1 - || protectionProfiles.Length >= (1 << 15)) - { - throw new ArgumentException("must have length from 1 to (2^15 - 1)", "protectionProfiles"); - } - - if (mki == null) - { - mki = TlsUtilities.EmptyBytes; - } - else if (mki.Length > 255) - { - throw new ArgumentException("cannot be longer than 255 bytes", "mki"); - } - - this.mProtectionProfiles = protectionProfiles; - this.mMki = mki; - } - - /** - * @return see {@link SrtpProtectionProfile} for valid constants. - */ - public virtual int[] ProtectionProfiles - { - get { return mProtectionProfiles; } - } - - /** - * @return valid lengths from 0 to 255. - */ - public virtual byte[] Mki - { - get { return mMki; } - } - } -} diff --git a/crypto/src/crypto/tls/UserMappingType.cs b/crypto/src/crypto/tls/UserMappingType.cs deleted file mode 100644 index 6cff51736..000000000 --- a/crypto/src/crypto/tls/UserMappingType.cs +++ /dev/null @@ -1,13 +0,0 @@ -using System; - -namespace Org.BouncyCastle.Crypto.Tls -{ - /// <remarks>RFC 4681</remarks> - public abstract class UserMappingType - { - /* - * RFC 4681 - */ - public const byte upn_domain_hint = 64; - } -} |