Exemplo n.º 1
0
        internal virtual DtlsTransport ServerHandshake(DtlsServerProtocol.ServerHandshakeState state, DtlsRecordLayer recordLayer)
        {
            SecurityParameters    securityParameters    = state.serverContext.SecurityParameters;
            DtlsReliableHandshake dtlsReliableHandshake = new DtlsReliableHandshake(state.serverContext, recordLayer);

            DtlsReliableHandshake.Message message = dtlsReliableHandshake.ReceiveMessage();
            ProtocolVersion discoveredPeerVersion = recordLayer.DiscoveredPeerVersion;

            state.serverContext.SetClientVersion(discoveredPeerVersion);
            if (message.Type != 1)
            {
                throw new TlsFatalAlert(10);
            }
            this.ProcessClientHello(state, message.Body);
            byte[] body = this.GenerateServerHello(state);
            DtlsProtocol.ApplyMaxFragmentLengthExtension(recordLayer, securityParameters.maxFragmentLength);
            dtlsReliableHandshake.SendMessage(2, body);
            dtlsReliableHandshake.NotifyHelloComplete();
            IList serverSupplementalData = state.server.GetServerSupplementalData();

            if (serverSupplementalData != null)
            {
                byte[] body2 = DtlsProtocol.GenerateSupplementalData(serverSupplementalData);
                dtlsReliableHandshake.SendMessage(23, body2);
            }
            state.keyExchange = state.server.GetKeyExchange();
            state.keyExchange.Init(state.serverContext);
            state.serverCredentials = state.server.GetCredentials();
            Certificate certificate = null;

            if (state.serverCredentials == null)
            {
                state.keyExchange.SkipServerCredentials();
            }
            else
            {
                state.keyExchange.ProcessServerCredentials(state.serverCredentials);
                certificate = state.serverCredentials.Certificate;
                byte[] body3 = DtlsProtocol.GenerateCertificate(certificate);
                dtlsReliableHandshake.SendMessage(11, body3);
            }
            if (certificate == null || certificate.IsEmpty)
            {
                state.allowCertificateStatus = false;
            }
            if (state.allowCertificateStatus)
            {
                CertificateStatus certificateStatus = state.server.GetCertificateStatus();
                if (certificateStatus != null)
                {
                    byte[] body4 = this.GenerateCertificateStatus(state, certificateStatus);
                    dtlsReliableHandshake.SendMessage(22, body4);
                }
            }
            byte[] array = state.keyExchange.GenerateServerKeyExchange();
            if (array != null)
            {
                dtlsReliableHandshake.SendMessage(12, array);
            }
            if (state.serverCredentials != null)
            {
                state.certificateRequest = state.server.GetCertificateRequest();
                if (state.certificateRequest != null)
                {
                    state.keyExchange.ValidateCertificateRequest(state.certificateRequest);
                    byte[] body5 = this.GenerateCertificateRequest(state, state.certificateRequest);
                    dtlsReliableHandshake.SendMessage(13, body5);
                    TlsUtilities.TrackHashAlgorithms(dtlsReliableHandshake.HandshakeHash, state.certificateRequest.SupportedSignatureAlgorithms);
                }
            }
            dtlsReliableHandshake.SendMessage(14, TlsUtilities.EmptyBytes);
            dtlsReliableHandshake.HandshakeHash.SealHashAlgorithms();
            message = dtlsReliableHandshake.ReceiveMessage();
            if (message.Type == 23)
            {
                this.ProcessClientSupplementalData(state, message.Body);
                message = dtlsReliableHandshake.ReceiveMessage();
            }
            else
            {
                state.server.ProcessClientSupplementalData(null);
            }
            if (state.certificateRequest == null)
            {
                state.keyExchange.SkipClientCredentials();
            }
            else if (message.Type == 11)
            {
                this.ProcessClientCertificate(state, message.Body);
                message = dtlsReliableHandshake.ReceiveMessage();
            }
            else
            {
                if (TlsUtilities.IsTlsV12(state.serverContext))
                {
                    throw new TlsFatalAlert(10);
                }
                this.NotifyClientCertificate(state, Certificate.EmptyChain);
            }
            if (message.Type == 16)
            {
                this.ProcessClientKeyExchange(state, message.Body);
                TlsHandshakeHash tlsHandshakeHash = dtlsReliableHandshake.PrepareToFinish();
                securityParameters.sessionHash = TlsProtocol.GetCurrentPrfHash(state.serverContext, tlsHandshakeHash, null);
                TlsProtocol.EstablishMasterSecret(state.serverContext, state.keyExchange);
                recordLayer.InitPendingEpoch(state.server.GetCipher());
                if (this.ExpectCertificateVerifyMessage(state))
                {
                    byte[] body6 = dtlsReliableHandshake.ReceiveMessageBody(15);
                    this.ProcessCertificateVerify(state, body6, tlsHandshakeHash);
                }
                byte[] expected_verify_data = TlsUtilities.CalculateVerifyData(state.serverContext, "client finished", TlsProtocol.GetCurrentPrfHash(state.serverContext, dtlsReliableHandshake.HandshakeHash, null));
                this.ProcessFinished(dtlsReliableHandshake.ReceiveMessageBody(20), expected_verify_data);
                if (state.expectSessionTicket)
                {
                    NewSessionTicket newSessionTicket = state.server.GetNewSessionTicket();
                    byte[]           body7            = this.GenerateNewSessionTicket(state, newSessionTicket);
                    dtlsReliableHandshake.SendMessage(4, body7);
                }
                byte[] body8 = TlsUtilities.CalculateVerifyData(state.serverContext, "server finished", TlsProtocol.GetCurrentPrfHash(state.serverContext, dtlsReliableHandshake.HandshakeHash, null));
                dtlsReliableHandshake.SendMessage(20, body8);
                dtlsReliableHandshake.Finish();
                state.server.NotifyHandshakeComplete();
                return(new DtlsTransport(recordLayer));
            }
            throw new TlsFatalAlert(10);
        }
Exemplo n.º 2
0
        internal virtual DtlsTransport ClientHandshake(DtlsClientProtocol.ClientHandshakeState state, DtlsRecordLayer recordLayer)
        {
            SecurityParameters    securityParameters    = state.clientContext.SecurityParameters;
            DtlsReliableHandshake dtlsReliableHandshake = new DtlsReliableHandshake(state.clientContext, recordLayer);

            byte[] array = this.GenerateClientHello(state, state.client);
            dtlsReliableHandshake.SendMessage(1, array);
            DtlsReliableHandshake.Message message = dtlsReliableHandshake.ReceiveMessage();
            while (message.Type == 3)
            {
                ProtocolVersion protocolVersion = recordLayer.ResetDiscoveredPeerVersion();
                ProtocolVersion clientVersion   = state.clientContext.ClientVersion;
                if (!protocolVersion.IsEqualOrEarlierVersionOf(clientVersion))
                {
                    throw new TlsFatalAlert(47);
                }
                byte[] cookie = this.ProcessHelloVerifyRequest(state, message.Body);
                byte[] body   = DtlsClientProtocol.PatchClientHelloWithCookie(array, cookie);
                dtlsReliableHandshake.ResetHandshakeMessagesDigest();
                dtlsReliableHandshake.SendMessage(1, body);
                message = dtlsReliableHandshake.ReceiveMessage();
            }
            if (message.Type != 2)
            {
                throw new TlsFatalAlert(10);
            }
            this.ReportServerVersion(state, recordLayer.DiscoveredPeerVersion);
            this.ProcessServerHello(state, message.Body);
            dtlsReliableHandshake.NotifyHelloComplete();
            DtlsProtocol.ApplyMaxFragmentLengthExtension(recordLayer, securityParameters.maxFragmentLength);
            if (state.resumedSession)
            {
                securityParameters.masterSecret = Arrays.Clone(state.sessionParameters.MasterSecret);
                recordLayer.InitPendingEpoch(state.client.GetCipher());
                byte[] expected_verify_data = TlsUtilities.CalculateVerifyData(state.clientContext, "server finished", TlsProtocol.GetCurrentPrfHash(state.clientContext, dtlsReliableHandshake.HandshakeHash, null));
                this.ProcessFinished(dtlsReliableHandshake.ReceiveMessageBody(20), expected_verify_data);
                byte[] body2 = TlsUtilities.CalculateVerifyData(state.clientContext, "client finished", TlsProtocol.GetCurrentPrfHash(state.clientContext, dtlsReliableHandshake.HandshakeHash, null));
                dtlsReliableHandshake.SendMessage(20, body2);
                dtlsReliableHandshake.Finish();
                state.clientContext.SetResumableSession(state.tlsSession);
                state.client.NotifyHandshakeComplete();
                return(new DtlsTransport(recordLayer));
            }
            this.InvalidateSession(state);
            if (state.selectedSessionID.Length > 0)
            {
                state.tlsSession = new TlsSessionImpl(state.selectedSessionID, null);
            }
            message = dtlsReliableHandshake.ReceiveMessage();
            if (message.Type == 23)
            {
                this.ProcessServerSupplementalData(state, message.Body);
                message = dtlsReliableHandshake.ReceiveMessage();
            }
            else
            {
                state.client.ProcessServerSupplementalData(null);
            }
            state.keyExchange = state.client.GetKeyExchange();
            state.keyExchange.Init(state.clientContext);
            Certificate certificate = null;

            if (message.Type == 11)
            {
                certificate = this.ProcessServerCertificate(state, message.Body);
                message     = dtlsReliableHandshake.ReceiveMessage();
            }
            else
            {
                state.keyExchange.SkipServerCredentials();
            }
            if (certificate == null || certificate.IsEmpty)
            {
                state.allowCertificateStatus = false;
            }
            if (message.Type == 22)
            {
                this.ProcessCertificateStatus(state, message.Body);
                message = dtlsReliableHandshake.ReceiveMessage();
            }
            if (message.Type == 12)
            {
                this.ProcessServerKeyExchange(state, message.Body);
                message = dtlsReliableHandshake.ReceiveMessage();
            }
            else
            {
                state.keyExchange.SkipServerKeyExchange();
            }
            if (message.Type == 13)
            {
                this.ProcessCertificateRequest(state, message.Body);
                TlsUtilities.TrackHashAlgorithms(dtlsReliableHandshake.HandshakeHash, state.certificateRequest.SupportedSignatureAlgorithms);
                message = dtlsReliableHandshake.ReceiveMessage();
            }
            if (message.Type != 14)
            {
                throw new TlsFatalAlert(10);
            }
            if (message.Body.Length != 0)
            {
                throw new TlsFatalAlert(50);
            }
            dtlsReliableHandshake.HandshakeHash.SealHashAlgorithms();
            IList clientSupplementalData = state.client.GetClientSupplementalData();

            if (clientSupplementalData != null)
            {
                byte[] body3 = DtlsProtocol.GenerateSupplementalData(clientSupplementalData);
                dtlsReliableHandshake.SendMessage(23, body3);
            }
            if (state.certificateRequest != null)
            {
                state.clientCredentials = state.authentication.GetClientCredentials(state.certificateRequest);
                Certificate certificate2 = null;
                if (state.clientCredentials != null)
                {
                    certificate2 = state.clientCredentials.Certificate;
                }
                if (certificate2 == null)
                {
                    certificate2 = Certificate.EmptyChain;
                }
                byte[] body4 = DtlsProtocol.GenerateCertificate(certificate2);
                dtlsReliableHandshake.SendMessage(11, body4);
            }
            if (state.clientCredentials != null)
            {
                state.keyExchange.ProcessClientCredentials(state.clientCredentials);
            }
            else
            {
                state.keyExchange.SkipClientCredentials();
            }
            byte[] body5 = this.GenerateClientKeyExchange(state);
            dtlsReliableHandshake.SendMessage(16, body5);
            TlsHandshakeHash tlsHandshakeHash = dtlsReliableHandshake.PrepareToFinish();

            securityParameters.sessionHash = TlsProtocol.GetCurrentPrfHash(state.clientContext, tlsHandshakeHash, null);
            TlsProtocol.EstablishMasterSecret(state.clientContext, state.keyExchange);
            recordLayer.InitPendingEpoch(state.client.GetCipher());
            if (state.clientCredentials != null && state.clientCredentials is TlsSignerCredentials)
            {
                TlsSignerCredentials      tlsSignerCredentials      = (TlsSignerCredentials)state.clientCredentials;
                SignatureAndHashAlgorithm signatureAndHashAlgorithm = TlsUtilities.GetSignatureAndHashAlgorithm(state.clientContext, tlsSignerCredentials);
                byte[] hash;
                if (signatureAndHashAlgorithm == null)
                {
                    hash = securityParameters.SessionHash;
                }
                else
                {
                    hash = tlsHandshakeHash.GetFinalHash(signatureAndHashAlgorithm.Hash);
                }
                byte[]          signature         = tlsSignerCredentials.GenerateCertificateSignature(hash);
                DigitallySigned certificateVerify = new DigitallySigned(signatureAndHashAlgorithm, signature);
                byte[]          body6             = this.GenerateCertificateVerify(state, certificateVerify);
                dtlsReliableHandshake.SendMessage(15, body6);
            }
            byte[] body7 = TlsUtilities.CalculateVerifyData(state.clientContext, "client finished", TlsProtocol.GetCurrentPrfHash(state.clientContext, dtlsReliableHandshake.HandshakeHash, null));
            dtlsReliableHandshake.SendMessage(20, body7);
            if (state.expectSessionTicket)
            {
                message = dtlsReliableHandshake.ReceiveMessage();
                if (message.Type != 4)
                {
                    throw new TlsFatalAlert(10);
                }
                this.ProcessNewSessionTicket(state, message.Body);
            }
            byte[] expected_verify_data2 = TlsUtilities.CalculateVerifyData(state.clientContext, "server finished", TlsProtocol.GetCurrentPrfHash(state.clientContext, dtlsReliableHandshake.HandshakeHash, null));
            this.ProcessFinished(dtlsReliableHandshake.ReceiveMessageBody(20), expected_verify_data2);
            dtlsReliableHandshake.Finish();
            if (state.tlsSession != null)
            {
                state.sessionParameters = new SessionParameters.Builder().SetCipherSuite(securityParameters.CipherSuite).SetCompressionAlgorithm(securityParameters.CompressionAlgorithm).SetMasterSecret(securityParameters.MasterSecret).SetPeerCertificate(certificate).SetPskIdentity(securityParameters.PskIdentity).SetSrpIdentity(securityParameters.SrpIdentity).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));
        }