123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272 |
- #if !BESTHTTP_DISABLE_ALTERNATE_SSL && (!UNITY_WEBGL || UNITY_EDITOR)
- 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 System.Collections.Generic.List<string> HostNames { get; set; }
- public AbstractTlsClient()
- : this(new DefaultTlsCipherFactory())
- {
- }
- public AbstractTlsClient(TlsCipherFactory cipherFactory)
- {
- this.mCipherFactory = cipherFactory;
- }
- protected virtual bool AllowUnexpectedServerExtension(int extensionType, byte[] extensionData)
- {
- switch (extensionType)
- {
- case ExtensionType.elliptic_curves:
- /*
- * 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;
- 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);
- }
- if (this.HostNames != null && this.HostNames.Count > 0)
- {
- var list = new System.Collections.Generic.List<ServerName>(this.HostNames.Count);
- for (int i = 0; i < this.HostNames.Count; ++i)
- list.Add(new ServerName(Tls.NameType.host_name, this.HostNames[i]));
- TlsExtensionsUtilities.AddServerNameExtension(clientExtensions, new ServerNameList(list));
- }
- 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.elliptic_curves);
- 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)
- {
- }
- }
- }
- #endif
|