Getting the following exception when my WCF client gets a response calls a Java based Spring Web Services server -
System.ServiceModel.Security.MessageSecurityException, System.ServiceModel, Version=3.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
Message security verification failed.
<StackTrace>
at System.ServiceModel.Security.MessageSecurityProtocol.VerifyIncomingMessage(Message& message, TimeSpan timeout, SecurityProtocolCorrelationState[] correlationStates)
at System.ServiceModel.Channels.SecurityChannelFactory`1.SecurityRequestChannel.ProcessReply(Message reply, SecurityProtocolCorrelationState correlationState, TimeSpan timeout)
at System.ServiceModel.Channels.SecurityChannelFactory`1.SecurityRequestChannel.Request(Message message, TimeSpan timeout)
at System.ServiceModel.Channels.TransactionRequestChannelGeneric`1.Request(Message message, TimeSpan timeout)
at System.ServiceModel.Dispatcher.RequestChannelBinder.Request(Message message, TimeSpan timeout)
at System.ServiceModel.Channels.ServiceChannel.Call(String action, Boolean oneway, ProxyOperationRuntime operation, Object[] ins, Object[] outs, TimeSpan timeout)
at System.ServiceModel.Channels.ServiceChannel.Call(String action, Boolean oneway, ProxyOperationRuntime operation, Object[] ins, Object[] outs)
at System.ServiceModel.Channels.ServiceChannelProxy.InvokeService(IMethodCallMessage methodCall, ProxyOperationRuntime operation)
at System.ServiceModel.Channels.ServiceChannelProxy.Invoke(IMessage message)
at System.Runtime.Remoting.Proxies.RealProxy.PrivateInvoke(MessageData& msgData, Int32 type)
at Exxx.Client.xxxService.xxxx.submitx(submitXxxRequest request)
at xxx.Client.ExxxService.exxxsClient.Exxx.Client.ExxxService.exxxs.submitxxx(submitxxxRequest request)
at xxx.Client.ExxxService.exxxsClient.submitxxx(submissionRequest submissionRequest)
at xxx.Client.ClientService.Submitxxx(String xxxId, String username, Int32 batchType)
at xxx.Main.Start()
at ESubmission.Service.SchedulerService.CreateInstance(String assemblyName, Object argsObj)
at ESubmission.Service.SchedulerService.LoadAssembly(BOESubmissionSchedule eSubmissionSchedule)
at ESubmission.Service.SchedulerService.<>c__DisplayClass2.<RunSchedules>b__0()
at System.Threading.ThreadHelper.ThreadStart_Context(Object state)
at System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state)
at System.Threading.ThreadHelper.ThreadStart()
</StackTrace>
<ExceptionString>System.ServiceModel.Security.MessageSecurityException: Message security verification failed. ---> System.Security.Cryptography.CryptographicException: The signature verification failed.
at System.IdentityModel.SignedXml.VerifySignature(HashAlgorithm hash, AsymmetricSignatureDeformatter deformatter)
at System.IdentityModel.SignedXml.StartSignatureVerification(SecurityKey verificationKey)
at System.ServiceModel.Security.WSSecurityOneDotZeroReceiveSecurityHeader.VerifySignature(SignedXml signedXml, Boolean isPrimarySignature, SecurityHeaderTokenResolver resolver, Object signatureTarget, String id)
at System.ServiceModel.Security.ReceiveSecurityHeader.ProcessPrimarySignature(SignedXml signedXml, Boolean isFromDecryptedSource)
at System.ServiceModel.Security.ReceiveSecurityHeader.ExecuteSignatureEncryptionProcessingPass()
at System.ServiceModel.Security.LaxModeSecurityHeaderElementInferenceEngine.ExecuteProcessingPasses(ReceiveSecurityHeader securityHeader, XmlDictionaryReader reader)
at System.ServiceModel.Security.ReceiveSecurityHeader.Process(TimeSpan timeout, ChannelBinding channelBinding, ExtendedProtectionPolicy extendedProtectionPolicy)
at System.ServiceModel.Security.MessageSecurityProtocol.ProcessSecurityHeader(ReceiveSecurityHeader securityHeader, Message& message, SecurityToken requiredSigningToken, TimeSpan timeout, SecurityProtocolCorrelationState[] correlationStates)
at System.ServiceModel.Security.AsymmetricSecurityProtocol.VerifyIncomingMessageCore(Message& message, String actor, TimeSpan timeout, SecurityProtocolCorrelationState[] correlationStates)
at System.ServiceModel.Security.MessageSecurityProtocol.VerifyIncomingMessage(Message& message, TimeSpan timeout, SecurityProtocolCorrelationState[] correlationStates)
--- End of inner exception stack trace ---</ExceptionString>
The Inner Exception - The signature verification failed.
<InnerException>
<ExceptionType>System.Security.Cryptography.CryptographicException, mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</ExceptionType>
<Message>The signature verification failed.</Message>
<StackTrace>
at System.IdentityModel.SignedXml.VerifySignature(HashAlgorithm hash, AsymmetricSignatureDeformatter deformatter)
at System.IdentityModel.SignedXml.StartSignatureVerification(SecurityKey verificationKey)
at System.ServiceModel.Security.WSSecurityOneDotZeroReceiveSecurityHeader.VerifySignature(SignedXml signedXml, Boolean isPrimarySignature, SecurityHeaderTokenResolver resolver, Object signatureTarget, String id)
at System.ServiceModel.Security.ReceiveSecurityHeader.ProcessPrimarySignature(SignedXml signedXml, Boolean isFromDecryptedSource)
at System.ServiceModel.Security.ReceiveSecurityHeader.ExecuteSignatureEncryptionProcessingPass()
at System.ServiceModel.Security.LaxModeSecurityHeaderElementInferenceEngine.ExecuteProcessingPasses(ReceiveSecurityHeader securityHeader, XmlDictionaryReader reader)
at System.ServiceModel.Security.ReceiveSecurityHeader.Process(TimeSpan timeout, ChannelBinding channelBinding, ExtendedProtectionPolicy extendedProtectionPolicy)
at System.ServiceModel.Security.MessageSecurityProtocol.ProcessSecurityHeader(ReceiveSecurityHeader securityHeader, Message& message, SecurityToken requiredSigningToken, TimeSpan timeout, SecurityProtocolCorrelationState[] correlationStates)
at System.ServiceModel.Security.AsymmetricSecurityProtocol.VerifyIncomingMessageCore(Message& message, String actor, TimeSpan timeout, SecurityProtocolCorrelationState[] correlationStates)
at System.ServiceModel.Security.MessageSecurityProtocol.VerifyIncomingMessage(Message& message, TimeSpan timeout, SecurityProtocolCorrelationState[] correlationStates)
</StackTrace>
<ExceptionString>System.Security.Cryptography.CryptographicException: The signature verification failed.
at System.IdentityModel.SignedXml.VerifySignature(HashAlgorithm hash, AsymmetricSignatureDeformatter deformatter)
at System.IdentityModel.SignedXml.StartSignatureVerification(SecurityKey verificationKey)
at System.ServiceModel.Security.WSSecurityOneDotZeroReceiveSecurityHeader.VerifySignature(SignedXml signedXml, Boolean isPrimarySignature, SecurityHeaderTokenResolver resolver, Object signatureTarget, String id)
at System.ServiceModel.Security.ReceiveSecurityHeader.ProcessPrimarySignature(SignedXml signedXml, Boolean isFromDecryptedSource)
at System.ServiceModel.Security.ReceiveSecurityHeader.ExecuteSignatureEncryptionProcessingPass()
at System.ServiceModel.Security.LaxModeSecurityHeaderElementInferenceEngine.ExecuteProcessingPasses(ReceiveSecurityHeader securityHeader, XmlDictionaryReader reader)
at System.ServiceModel.Security.ReceiveSecurityHeader.Process(TimeSpan timeout, ChannelBinding channelBinding, ExtendedProtectionPolicy extendedProtectionPolicy)
at System.ServiceModel.Security.MessageSecurityProtocol.ProcessSecurityHeader(ReceiveSecurityHeader securityHeader, Message& message, SecurityToken requiredSigningToken, TimeSpan timeout, SecurityProtocolCorrelationState[] correlationStates)
at System.ServiceModel.Security.AsymmetricSecurityProtocol.VerifyIncomingMessageCore(Message& message, String actor, TimeSpan timeout, SecurityProtocolCorrelationState[] correlationStates)
at System.ServiceModel.Security.MessageSecurityProtocol.VerifyIncomingMessage(Message& message, TimeSpan timeout, SecurityProtocolCorrelationState[] correlationStates)</ExceptionString>
The Java based server web-service seems to process my request fine but I'm having the above trouble with the response. Note: I have no access to the server side of things - I can request changes and query actions but that's all
The set-up
- WCF .NET 3.5 client web-service
- Java Spring Web Services 2.1.0 (SOAP protocol implementation) + Apache WSS4J 1.6.7 (WS-Security 1.1 implementation) server
- The following security binding in config:
[customBinding] [binding name="MY_BINDING"] [transactionFlow/] [security defaultAlgorithmSuite="Basic256Rsa15" authenticationMode="MutualCertificate" messageSecurityVersion="WSSecurity10WSTrust13WSSecureConversation13WSSecurityPolicy12BasicSecurityProfile10" requireDerivedKeys="false" messageProtectionOrder="SignBeforeEncrypt" allowSerializedSigningTokenOnReply="true" securityHeaderLayout="Lax" requireSignatureConfirmation="true" enableUnsecuredResponse="true"] [secureConversationBootstrap authenticationMode="CertificateOverTransport" messageSecurityVersion="WSSecurity11WSTrustFebruary2005WSSecureConversationFebruary2005WSSecurityPolicy11BasicSecurityProfile10" requireDerivedKeys="false" /] [/security] [textMessageEncoding messageVersion="Soap11WSAddressing10"/] [httpsTransport requireClientCertificate="true"/] [/binding] [/customBinding]
Binding has been modified in code like so
public static CustomBinding GetServiceBinding() { //Get custom binding reference from app.config CustomBinding binding = new CustomBinding(SettingsLookup.WcfCustomBindingName); binding.ReceiveTimeout = new TimeSpan(0, 0, 15, 0); binding.SendTimeout = new TimeSpan(0, 0, 15, 0); // Get the x509ProtectionParams from the security element X509SecurityTokenParameters tokenParameters = new X509SecurityTokenParameters(); tokenParameters.X509ReferenceStyle = X509KeyIdentifierClauseType.IssuerSerial; tokenParameters.RequireDerivedKeys = false; tokenParameters.InclusionMode = SecurityTokenInclusionMode.AlwaysToRecipient; // Reference the asymettric security element AsymmetricSecurityBindingElement securityBindingElement = binding.Elements.Find<AsymmetricSecurityBindingElement>(); // Set the X509SecurityTokenParameters to point to the one's just configured. This is for symetric encryption, for asymetric this line needs to change //securityBindingElement.ProtectionTokenParameters = tokenParameters; securityBindingElement.MessageSecurityVersion = MessageSecurityVersion.WSSecurity11WSTrustFebruary2005WSSecureConversationFebruary2005WSSecurityPolicy11BasicSecurityProfile10; securityBindingElement.InitiatorTokenParameters = tokenParameters; securityBindingElement.LocalClientSettings.DetectReplays = false; securityBindingElement.IncludeTimestamp = true; securityBindingElement.LocalClientSettings.TimestampValidityDuration = new TimeSpan(12, 0, 0); return binding; }
What I can't seem to do is:
Figure out which signature has failed? The stack trace for the inner exception mentions
System.ServiceModel.Security.ReceiveSecurityHeader.ProcessPrimarySignature
so I presumed the Primary Signature was the main envelope body signature? Contradictory to this, however, is the line in the StackTraceSystem.ServiceModel.Security.MessageSecurityProtocol.ProcessSecurityHeader
which would lead me to think that it's a header element - but which one?Check the signatures in a Console application or something similar using
System.Security.Cryptography.Xml.SignedXml
classes to verify in a separate, isolated environment which of the signatures are returning false forCheckSignature()
- I have tried this and cant seem to get it to return true for elements in my request from WCF (I've pulled the request from fiddler)
Any and all help appreciated