コード例 #1
0
        /// <summary>
        /// Processes the shared key response.
        /// </summary>
        /// <param name="responseHeaders">Response transport headers.</param>
        private SymmetricAlgorithm ProcessSharedKeyResponse(ITransportHeaders responseHeaders)
        {
            // Get the encrypted key and initialization vector from the transport headers sent by the server
            string encryptedKey = (string)responseHeaders[CommonHeaderNames.SHARED_KEY];
            string encryptedIV  = (string)responseHeaders[CommonHeaderNames.SHARED_IV];

            if (encryptedKey == null || encryptedKey == string.Empty)
            {
                throw new CryptoRemotingException(LanguageResource.CryptoRemotingException_KeyChanged);
            }

            if (encryptedIV == null || encryptedIV == string.Empty)
            {
                throw new CryptoRemotingException(LanguageResource.CryptoRemotingException_IVMissing);
            }

            // Create symmetric algorithm and set shared key and initialization vector
            SymmetricAlgorithm sharedProvider = CryptoTools.CreateSymmetricCryptoProvider(_algorithm);

            sharedProvider.Key = _rsaProvider.Decrypt(Convert.FromBase64String(encryptedKey), _oaep);
            sharedProvider.IV  = _rsaProvider.Decrypt(Convert.FromBase64String(encryptedIV), _oaep);

            // Return the encryption provider
            return(sharedProvider);
        }
コード例 #2
0
        /// <summary>Verarbeitet die Antwort der Servers einer Anfrage nach einen Gemeinsamen Schlüssel</summary>
        /// <param name="responseHeaders">Transport-Header-Auflistung</param>
        /// <returns>Verschlüsselungsanbieter</returns>
        private SymmetricAlgorithm ProcessSharedKeyResponse(ITransportHeaders responseHeaders)
        {
            // Gemeinsamen Schlüssel und Inizialisierungsvektor asu den Antwort-Headern lesen
            string encryptedKey = (string)responseHeaders[CommonHeaderNames.SHARED_KEY];
            string encryptedIV  = (string)responseHeaders[CommonHeaderNames.SHARED_IV];

            // Wenn kein gemeinsamer Schlüssel übermittelt wurde ...
            if (encryptedKey == null || encryptedKey == string.Empty)
            {
                // Ausnahme werfen
                throw new CryptoRemotingException(LanguageResource.CryptoRemotingException_KeyChanged);
            }

            // Wenn kein Inizialisierungsvektor übermittelt wurde ...
            if (encryptedIV == null || encryptedIV == string.Empty)
            {
                // Ausnahme werfen
                throw new CryptoRemotingException(LanguageResource.CryptoRemotingException_IVMissing);
            }

            // Gemeinsamen Schlüssel und Inizialisierungsvektor entschlüsseln
            SymmetricAlgorithm sharedProvider = CryptoTools.CreateSymmetricCryptoProvider(_algorithm);

            sharedProvider.Key = _rsaProvider.Decrypt(Convert.FromBase64String(encryptedKey), _oaep);
            sharedProvider.IV  = _rsaProvider.Decrypt(Convert.FromBase64String(encryptedIV), _oaep);

            // Verschlüsselungsanbieter zurückgeben
            return(sharedProvider);
        }
コード例 #3
0
        /// <summary>Verschlüsselt eine bestimmte Remoting-Nachricht</summary>
        /// <param name="requestHeaders">Anfrage-Transport-Header-Auflistung</param>
        /// <param name="requestStream">Anfrage-Datenstrom</param>
        /// <returns>Verschlüsselter Datenstrom</returns>
        private Stream EncryptMessage(ITransportHeaders requestHeaders, Stream requestStream)
        {
            // Nachricht verschlüsseln
            requestStream = CryptoTools.GetEncryptedStream(requestStream, _provider);

            // Statusinformationen über die Sicherheitstransaktion in die Header-Auflistung schreiben
            requestHeaders[CommonHeaderNames.SECURE_TRANSACTION_STATE] = ((int)SecureTransactionStage.SendingEncryptedMessage).ToString();
            requestHeaders[CommonHeaderNames.SECURE_TRANSACTION_ID]    = _secureTransactionID.ToString();

            // Verschlüsselten Datenstrom zurückgeben
            return(requestStream);
        }
コード例 #4
0
        /// <summary>
        /// Encrypts the message.
        /// </summary>
        /// <param name="requestHeaders">Request transport headers.</param>
        /// <param name="requestStream">Request stream.</param>
        private Stream EncryptMessage(ITransportHeaders requestHeaders, Stream requestStream)
        {
            // Encrypt message using the symmetric encryption algorithm
            requestStream = CryptoTools.GetEncryptedStream(requestStream, _provider);

            // Send the current secure transaction stage and identifier in the transport headers
            requestHeaders[CommonHeaderNames.SECURE_TRANSACTION_STATE] = ((int)SecureTransactionStage.SendingEncryptedMessage).ToString();
            requestHeaders[CommonHeaderNames.SECURE_TRANSACTION_ID]    = _secureTransactionID.ToString();

            // Return the encrypted data stream
            return(requestStream);
        }
コード例 #5
0
        /// <summary>
        /// Processes the encrypted message.
        /// </summary>
        /// <param name="transactID">Secure transaction identifier.</param>
        /// <param name="sinkStack">The sink stack.</param>
        /// <param name="requestMsg">Request message.</param>
        /// <param name="requestHeaders">Request transport headers.</param>
        /// <param name="requestStream">Request stream.</param>
        /// <param name="responseMsg">Response message.</param>
        /// <param name="responseHeaders">Response transport headers.</param>
        /// <param name="responseStream">Response stream.</param>
        public ServerProcessing ProcessEncryptedMessage(Guid transactID, IServerChannelSinkStack sinkStack, IMessage requestMsg, ITransportHeaders requestHeaders, Stream requestStream, out IMessage responseMsg, out ITransportHeaders responseHeaders, out Stream responseStream)
        {
            // Get the client connection data
            ClientConnectionData connectionData;

            lock (_connections.SyncRoot)
            {
                connectionData = (ClientConnectionData)_connections[transactID.ToString()];
            }

            if (connectionData == null)
            {
                throw new CryptoRemotingException(LanguageResource.CryptoRemotingException_ClientConnectionInfoMissing);
            }

            // Update the timestamp and indicate that method call is in progress
            connectionData.UpdateTimestamp();
            connectionData.BeginMethodCall();

            try
            {
                // Decrypt the data stream
                Stream decryptedStream = CryptoTools.GetDecryptedStream(requestStream, connectionData.CryptoProvider);
                requestStream.Close();

                // Pass decrypted message for further processing to the next channel sink
                ServerProcessing processingResult = _next.ProcessMessage(sinkStack, requestMsg, requestHeaders, decryptedStream, out responseMsg, out responseHeaders, out responseStream);

                // Update secure transaction state
                responseHeaders[CommonHeaderNames.SECURE_TRANSACTION_STATE] = ((int)SecureTransactionStage.SendingEncryptedResult).ToString();

                // Encrypt the response stream and close the original response stream now that we're done with it
                Stream encryptedStream = CryptoTools.GetEncryptedStream(responseStream, connectionData.CryptoProvider);
                responseStream.Close();                 //

                // Use encrypted data stream as a response stream
                responseStream = encryptedStream;
                return(processingResult);
            }
            finally
            {
                // Method call is finished, so the connection data can be swept
                connectionData.EndMethodCall();
                connectionData.UpdateTimestamp();
            }
        }
コード例 #6
0
        /// <summary>
        /// Decrypts the incoming response stream.
        /// </summary>
        /// <param name="responseStream">The response stream.</param>
        /// <param name="responseHeaders">The response headers.</param>
        private Stream DecryptResponse(Stream responseStream, ITransportHeaders responseHeaders)
        {
            try
            {
                if (responseHeaders != null && (SecureTransactionStage)Convert.ToInt32((string)responseHeaders[CommonHeaderNames.SECURE_TRANSACTION_STATE]) == SecureTransactionStage.SendingEncryptedResult)
                {
                    // Decrypt the response stream and close it as we won't be using it anymore
                    Stream decryptedStream = CryptoTools.GetDecryptedStream(responseStream, _provider);
                    responseStream.Close();
                    return(decryptedStream);
                }
            }
            catch { }

            // Failed to decrypt server's response
            return(null);
        }
コード例 #7
0
        /// <summary>
        /// Erzeugt den gemeinsamen Schlüssel und bereitet dessen Übertragung zum Client vor.
        /// </summary>
        /// <param name="transactID">Sicherheitstransaktionskennung</param>
        /// <param name="requestHeaders">Anfrage-Header vom Client</param>
        /// <param name="responseMsg">Antwortnachricht</param>
        /// <param name="responseHeaders">Antwort-Header</param>
        /// <param name="responseStream">Antwort-Datenstrom</param>
        /// <returns>Status</returns>
        private ServerProcessing MakeSharedKey(Guid transactID, ITransportHeaders requestHeaders, out IMessage responseMsg, out ITransportHeaders responseHeaders, out Stream responseStream)
        {
            // Gemeinsamer Schlüssel und Inizialisierungsvektor
            SymmetricAlgorithm symmetricProvider = CryptoTools.CreateSymmetricCryptoProvider(_algorithm);

            // Clientverbindungsdaten erzeugen
            ClientConnectionData connectionData = new ClientConnectionData(transactID, symmetricProvider);

            lock (_connections.SyncRoot)
            {
                // Clientverbindungsdaten unter der angegebenen Sicherheitstransaktionskennung speichern
                _connections[transactID.ToString()] = connectionData;
            }
            // RSA Kryptografieanbieter erzeugen
            RSACryptoServiceProvider rsaProvider = new RSACryptoServiceProvider();

            // Öffentlichen Schlüssel (vom Client) aus den Anfrage-Headern lesen
            string publicKey = (string)requestHeaders[CommonHeaderNames.PUBLIC_KEY];

            // Wenn kein öffentlicher Schlüssel gefunden wurde ...
            if (string.IsNullOrEmpty(publicKey))
            {
                throw new CryptoRemotingException(LanguageResource.CryptoRemotingException_PublicKeyNotFound);
            }

            // Öffentlichen Schlüssel in den Kryptografieanbieter laden
            rsaProvider.FromXmlString(publicKey);

            // Gemeinsamen Schlüssel und dessen Inizialisierungsfaktor verschlüsseln
            byte[] encryptedKey = rsaProvider.Encrypt(symmetricProvider.Key, _oaep);
            byte[] encryptedIV  = rsaProvider.Encrypt(symmetricProvider.IV, _oaep);

            // Antwort-Header zusammenstellen
            responseHeaders = new TransportHeaders();
            responseHeaders[CommonHeaderNames.SECURE_TRANSACTION_STATE] = ((int)SecureTransactionStage.SendingSharedKey).ToString();
            responseHeaders[CommonHeaderNames.SHARED_KEY] = Convert.ToBase64String(encryptedKey);
            responseHeaders[CommonHeaderNames.SHARED_IV]  = Convert.ToBase64String(encryptedIV);

            // Es wird keine Antwortnachricht benötigt
            responseMsg    = null;
            responseStream = new MemoryStream();

            // Vollständige Verarbeitung zurückmelden
            return(ServerProcessing.Complete);
        }
コード例 #8
0
        /// <summary>
        /// Entschlüsselt die eingehende Nachricht vom Client.
        /// </summary>
        /// <param name="transactID">Sicherheitstransaktionskennung</param>
        /// <param name="sinkStack">Senkenstapel</param>
        /// <param name="requestMsg">Anfrage-Nachricht vom Client</param>
        /// <param name="requestHeaders">Anfrage-Header vom Cient</param>
        /// <param name="requestStream">Anfrage-Datenstrom</param>
        /// <param name="responseMsg">Antwort-Nachricht</param>
        /// <param name="responseHeaders">Antwort-Header</param>
        /// <param name="responseStream">Antwort-Datenstrom</param>
        /// <returns>Verarbeitungsstatus</returns>
        public ServerProcessing ProcessEncryptedMessage(Guid transactID, IServerChannelSinkStack sinkStack, IMessage requestMsg, ITransportHeaders requestHeaders, Stream requestStream, out IMessage responseMsg, out ITransportHeaders responseHeaders, out Stream responseStream)
        {
            // Variable für Client-Verbindungsinformationen
            ClientConnectionData connectionData;

            lock (_connections.SyncRoot)
            {
                // Client-Verbindungsdaten über die angegebene Sicherheitstransaktionskennung abrufen
                connectionData = (ClientConnectionData)_connections[transactID.ToString()];
            }
            // Wenn keine Verbindungsdaten zu dieser Sicherheitstransaktionskennung gefunden wurden ...
            if (connectionData == null)
            {
                // Ausnahme werfen
                throw new CryptoRemotingException(LanguageResource.CryptoRemotingException_ClientConnectionInfoMissing);
            }

            // Zeitstempel aktualisieren
            connectionData.UpdateTimestamp();

            // Datenstrom entschlüsseln
            Stream decryptedStream = CryptoTools.GetDecryptedStream(requestStream, connectionData.CryptoProvider);

            // Verschlüsselten-Quelldatenstrom schließen
            requestStream.Close();

            // Entschlüsselte Nachricht zur Weiterverarbeitung an die nächste Kanalsenke weitergeben
            ServerProcessing processingResult = _next.ProcessMessage(sinkStack, requestMsg, requestHeaders, decryptedStream, out responseMsg, out responseHeaders, out responseStream);

            // Status der Sicherheitstransaktion auf "verschlüsselte Atwortnachricht senden" einstellen
            responseHeaders[CommonHeaderNames.SECURE_TRANSACTION_STATE] = ((int)SecureTransactionStage.SendingEncryptedResult).ToString();

            // Antwortnachricht verschlüsseln
            Stream encryptedStream = CryptoTools.GetEncryptedStream(responseStream, connectionData.CryptoProvider);

            // Unverschlüsselten Quell-Datenstrom schließen
            responseStream.Close();             // close the plaintext stream now that we're done with it

            // Verschlüsselten Datenstrom als Antwort-Datenstrom verwenden
            responseStream = encryptedStream;

            // Verarbeitungsstatus zurückgeben
            return(processingResult);
        }
コード例 #9
0
        /// <summary>Entschlüsselt den eingehenden Antwort-Datenstrom</summary>
        /// <param name="responseStream">Antwort-Datenstrom</param>
        /// <param name="responseHeaders">Antwort-Transportheader</param>
        /// <returns>Entschlüsselter Datenstrom (oder null, wenn die Verschlüsselung fehlgeschlagen ist)</returns>
        private Stream DecryptResponse(Stream responseStream, ITransportHeaders responseHeaders)
        {
            try
            {
                // Wenn laut Header verschlüsselte Daten vom Server zurückgesendet wurden ...
                if (responseHeaders != null && (SecureTransactionStage)Convert.ToInt32((string)responseHeaders[CommonHeaderNames.SECURE_TRANSACTION_STATE]) == SecureTransactionStage.SendingEncryptedResult)
                {
                    // Antwort-Datenstrom entschlüsseln
                    Stream decryptedStream = CryptoTools.GetDecryptedStream(responseStream, _provider);
                    responseStream.Close();                     // close the old stream as we won't be using it anymore

                    // Entschlüsselten Datenstrom zurückgeben
                    return(decryptedStream);
                }
            }
            catch {}

            // Nichts zurückgeben
            return(null);
        }
コード例 #10
0
        /// <summary>
        /// Creates the shared key.
        /// </summary>
        /// <param name="transactID">Secure transaction identifier.</param>
        /// <param name="requestHeaders">Request transport headers.</param>
        /// <param name="responseMsg">The response message.</param>
        /// <param name="responseHeaders">The response headers.</param>
        /// <param name="responseStream">The response stream.</param>
        private ServerProcessing MakeSharedKey(Guid transactID, ITransportHeaders requestHeaders, out IMessage responseMsg, out ITransportHeaders responseHeaders, out Stream responseStream)
        {
            // save shared symmetric encryption key and initialization vector for the current client connection
            SymmetricAlgorithm   symmetricProvider = CryptoTools.CreateSymmetricCryptoProvider(_algorithm);
            ClientConnectionData connectionData    = new ClientConnectionData(transactID, symmetricProvider);

            // Store client data connection under the specified security transaction identifier
            lock (_connections.SyncRoot)
            {
                _connections[transactID.ToString()] = connectionData;
            }

            // Get client's RSA public key
            string publicKey = (string)requestHeaders[CommonHeaderNames.PUBLIC_KEY];

            if (string.IsNullOrEmpty(publicKey))
            {
                throw new CryptoRemotingException(LanguageResource.CryptoRemotingException_PublicKeyNotFound);
            }

            // Initialize RSA cryptographic provider using the client's public key
            RSACryptoServiceProvider rsaProvider = new RSACryptoServiceProvider();

            rsaProvider.FromXmlString(publicKey);

            // Encrypt shared key for the symmetric algorithm using the client's public key
            byte[] encryptedKey = rsaProvider.Encrypt(symmetricProvider.Key, _oaep);
            byte[] encryptedIV  = rsaProvider.Encrypt(symmetricProvider.IV, _oaep);

            // Put the data to the response headers
            responseHeaders = new TransportHeaders();
            responseHeaders[CommonHeaderNames.SECURE_TRANSACTION_STATE] = ((int)SecureTransactionStage.SendingSharedKey).ToString();
            responseHeaders[CommonHeaderNames.SHARED_KEY] = Convert.ToBase64String(encryptedKey);
            responseHeaders[CommonHeaderNames.SHARED_IV]  = Convert.ToBase64String(encryptedIV);

            // There is no response message
            responseMsg    = null;
            responseStream = new MemoryStream();
            return(ServerProcessing.Complete);
        }