BinaryMessageEncoder.cs 18 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271
  1. //
  2. // BinaryMessageEncoder.cs
  3. //
  4. // Author: Atsushi Enomoto ([email protected])
  5. //
  6. // Copyright (C) 2005,2009 Novell, Inc (http://www.novell.com)
  7. //
  8. // Permission is hereby granted, free of charge, to any person obtaining
  9. // a copy of this software and associated documentation files (the
  10. // "Software"), to deal in the Software without restriction, including
  11. // without limitation the rights to use, copy, modify, merge, publish,
  12. // distribute, sublicense, and/or sell copies of the Software, and to
  13. // permit persons to whom the Software is furnished to do so, subject to
  14. // the following conditions:
  15. //
  16. // The above copyright notice and this permission notice shall be
  17. // included in all copies or substantial portions of the Software.
  18. //
  19. // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
  20. // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
  21. // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
  22. // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
  23. // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
  24. // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
  25. // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  26. //
  27. using System;
  28. using System.IO;
  29. using System.Collections.ObjectModel;
  30. using System.ServiceModel;
  31. using System.Text;
  32. using System.Xml;
  33. namespace System.ServiceModel.Channels
  34. {
  35. internal class BinaryMessageEncoder : MessageEncoder
  36. {
  37. static XmlDictionary soap_dictionary;
  38. // See [MC-NBFS] in Microsoft OSP. The strings are copied from the PDF, so the actual values might be wrong.
  39. static readonly string [] dict_strings = {
  40. "mustUnderstand", "Envelope",
  41. "http://www.w3.org/2003/05/soap-envelope",
  42. "http://www.w3.org/2005/08/addressing", "Header", "Action", "To", "Body", "Algorithm", "RelatesTo",
  43. "http://www.w3.org/2005/08/addressing/anonymous", "URI", "Reference", "MessageID", "Id", "Identifier",
  44. "http://schemas.xmlsoap.org/ws/2005/02/rm", "Transforms", "Transform", "DigestMethod", "DigestValue", "Address", "ReplyTo", "SequenceAcknowledgement", "AcknowledgementRange", "Upper", "Lower", "BufferRemaining",
  45. "http://schemas.microsoft.com/ws/2006/05/rm",
  46. "http://schemas.xmlsoap.org/ws/2005/02/rm/SequenceAcknowledgement", "SecurityTokenReference", "Sequence", "MessageNumber",
  47. "http://www.w3.org/2000/09/xmldsig#",
  48. "http://www.w3.org/2000/09/xmldsig#enveloped-signature", "KeyInfo",
  49. "http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd",
  50. "http://www.w3.org/2001/04/xmlenc#",
  51. "http://schemas.xmlsoap.org/ws/2005/02/sc", "DerivedKeyToken", "Nonce", "Signature", "SignedInfo", "CanonicalizationMethod", "SignatureMethod", "SignatureValue", "DataReference", "EncryptedData", "EncryptionMethod", "CipherData", "CipherValue",
  52. "http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd", "Security", "Timestamp", "Created", "Expires", "Length", "ReferenceList", "ValueType", "Type", "EncryptedHeader",
  53. "http://docs.oasis-open.org/wss/oasis-wss-wssecurity-secext-1.1.xsd", "RequestSecurityTokenResponseCollection",
  54. "http://schemas.xmlsoap.org/ws/2005/02/trust",
  55. "http://schemas.xmlsoap.org/ws/2005/02/trust#BinarySecret",
  56. "http://schemas.microsoft.com/ws/2006/02/transactions", "s", "Fault", "MustUnderstand", "role", "relay", "Code", "Reason", "Text", "Node", "Role", "Detail", "Value", "Subcode", "NotUnderstood", "qname", "", "From", "FaultTo", "EndpointReference", "PortType", "ServiceName", "PortName", "ReferenceProperties", "RelationshipType", "Reply", "a",
  57. "http://schemas.xmlsoap.org/ws/2006/02/addressingidentity", "Identity", "Spn", "Upn", "Rsa", "Dns", "X509v3Certificate",
  58. "http://www.w3.org/2005/08/addressing/fault", "ReferenceParameters", "IsReferenceParameter",
  59. "http://www.w3.org/2005/08/addressing/reply",
  60. "http://www.w3.org/2005/08/addressing/none", "Metadata",
  61. "http://schemas.xmlsoap.org/ws/2004/08/addressing",
  62. "http://schemas.xmlsoap.org/ws/2004/08/addressing/role/anonymous",
  63. "http://schemas.xmlsoap.org/ws/2004/08/addressing/fault",
  64. "http://schemas.xmlsoap.org/ws/2004/06/addressingex", "RedirectTo", "Via",
  65. "http://www.w3.org/2001/10/xml-exc-c14n#", "PrefixList", "InclusiveNamespaces", "ec", "SecurityContextToken", "Generation", "Label", "Offset", "Properties", "Cookie", "wsc",
  66. "http://schemas.xmlsoap.org/ws/2004/04/sc",
  67. "http://schemas.xmlsoap.org/ws/2004/04/security/sc/dk",
  68. "http://schemas.xmlsoap.org/ws/2004/04/security/sc/sct",
  69. "http://schemas.xmlsoap.org/ws/2004/04/security/trust/RST/SCT",
  70. "http://schemas.xmlsoap.org/ws/2004/04/security/trust/RSTR/SCT", "RenewNeeded", "BadContextToken", "c",
  71. "http://schemas.xmlsoap.org/ws/2005/02/sc/dk",
  72. "http://schemas.xmlsoap.org/ws/2005/02/sc/sct",
  73. "http://schemas.xmlsoap.org/ws/2005/02/trust/RST/SCT",
  74. "http://schemas.xmlsoap.org/ws/2005/02/trust/RSTR/SCT",
  75. "http://schemas.xmlsoap.org/ws/2005/02/trust/RST/SCT/Renew",
  76. "http://schemas.xmlsoap.org/ws/2005/02/trust/RSTR/SCT/Renew",
  77. "http://schemas.xmlsoap.org/ws/2005/02/trust/RST/SCT/Cancel",
  78. "http://schemas.xmlsoap.org/ws/2005/02/trust/RSTR/SCT/Cancel",
  79. "http://www.w3.org/2001/04/xmlenc#aes128-cbc",
  80. "http://www.w3.org/2001/04/xmlenc#kw-aes128",
  81. "http://www.w3.org/2001/04/xmlenc#aes192-cbc",
  82. "http://www.w3.org/2001/04/xmlenc#kw-aes192",
  83. "http://www.w3.org/2001/04/xmlenc#aes256-cbc",
  84. "http://www.w3.org/2001/04/xmlenc#kw-aes256",
  85. "http://www.w3.org/2001/04/xmlenc#des-cbc",
  86. "http://www.w3.org/2000/09/xmldsig#dsa-sha1",
  87. "http://www.w3.org/2001/10/xml-exc-c14n#WithComments",
  88. "http://www.w3.org/2000/09/xmldsig#hmac-sha1",
  89. "http://www.w3.org/2001/04/xmldsig-more#hmac-sha256",
  90. "http://schemas.xmlsoap.org/ws/2005/02/sc/dk/p_sha1",
  91. "http://www.w3.org/2001/04/xmlenc#ripemd160",
  92. "http://www.w3.org/2001/04/xmlenc#rsa-oaep-mgf1p",
  93. "http://www.w3.org/2000/09/xmldsig#rsa-sha1",
  94. "http://www.w3.org/2001/04/xmldsig-more#rsa-sha256",
  95. "http://www.w3.org/2001/04/xmlenc#rsa-1_5",
  96. "http://www.w3.org/2000/09/xmldsig#sha1",
  97. "http://www.w3.org/2001/04/xmlenc#sha256",
  98. "http://www.w3.org/2001/04/xmlenc#sha512",
  99. "http://www.w3.org/2001/04/xmlenc#tripledes-cbc",
  100. "http://www.w3.org/2001/04/xmlenc#kw-tripledes",
  101. "http://schemas.xmlsoap.org/2005/02/trust/tlsnego#TLS_Wrap",
  102. "http://schemas.xmlsoap.org/2005/02/trust/spnego#GSS_Wrap",
  103. "http://schemas.microsoft.com/ws/2006/05/security", "dnse", "o", "Password", "PasswordText", "Username", "UsernameToken", "BinarySecurityToken", "EncodingType", "KeyIdentifier",
  104. "http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-soap-message-security-1.0#Base64Binary",
  105. "http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-soap-message-security-1.0#HexBinary",
  106. "http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-soap-message-security-1.0#Text",
  107. "http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-x509-token-profile-1.0#X509SubjectKeyIdentifier",
  108. "http://docs.oasis-open.org/wss/oasis-wss-kerberos-token-profile-1.1#GSS_Kerberosv5_AP_REQ",
  109. "http://docs.oasis-open.org/wss/oasis-wss-kerberos-token-profile-1.1#GSS_Kerberosv5_AP_REQ1510",
  110. "http://docs.oasis-open.org/wss/oasis-wss-saml-token-profile-1.0#SAMLAssertionID", "Assertion", "urn:oasis:names:tc:SAML:1.0:assertion",
  111. "http://docs.oasis-open.org/wss/oasis-wss-rel-token-profile-1.0.pdf#license", "FailedAuthentication", "InvalidSecurityToken", "InvalidSecurity", "k", "SignatureConfirmation", "TokenType",
  112. "http://docs.oasis-open.org/wss/oasis-wss-soap-message-security-1.1#ThumbprintSHA1",
  113. "http://docs.oasis-open.org/wss/oasis-wss-soap-message-security-1.1#EncryptedKey",
  114. "http://docs.oasis-open.org/wss/oasis-wss-soap-message-security-1.1#EncryptedKeySHA1",
  115. "http://docs.oasis-open.org/wss/oasis-wss-saml-token-profile-1.1#SAMLV1.1",
  116. "http://docs.oasis-open.org/wss/oasis-wss-saml-token-profile-1.1#SAMLV2.0",
  117. "http://docs.oasis-open.org/wss/oasis-wss-saml-token-profile-1.1#SAMLID", "AUTH-HASH", "RequestSecurityTokenResponse", "KeySize", "RequestedTokenReference", "AppliesTo", "Authenticator", "CombinedHash", "BinaryExchange", "Lifetime", "RequestedSecurityToken", "Entropy", "RequestedProofToken", "ComputedKey", "RequestSecurityToken", "RequestType", "Context", "BinarySecret",
  118. "http://schemas.xmlsoap.org/ws/2005/02/trust/spnego",
  119. "http://schemas.xmlsoap.org/ws/2005/02/trust/tlsnego", "wst",
  120. "http://schemas.xmlsoap.org/ws/2004/04/trust",
  121. "http://schemas.xmlsoap.org/ws/2004/04/security/trust/RST/Issue",
  122. "http://schemas.xmlsoap.org/ws/2004/04/security/trust/RSTR/Issue",
  123. "http://schemas.xmlsoap.org/ws/2004/04/security/trust/Issue",
  124. "http://schemas.xmlsoap.org/ws/2004/04/security/trust/CK/PSHA1",
  125. "http://schemas.xmlsoap.org/ws/2004/04/security/trust/SymmetricKey",
  126. "http://schemas.xmlsoap.org/ws/2004/04/security/trust/Nonce", "KeyType",
  127. "http://schemas.xmlsoap.org/ws/2004/04/trust/SymmetricKey",
  128. "http://schemas.xmlsoap.org/ws/2004/04/trust/PublicKey", "Claims", "InvalidRequest", "RequestFailed", "SignWith", "EncryptWith", "EncryptionAlgorithm", "CanonicalizationAlgorithm", "ComputedKeyAlgorithm", "UseKey",
  129. "http://schemas.microsoft.com/net/2004/07/secext/WS-SPNego",
  130. "http://schemas.microsoft.com/net/2004/07/secext/TLSNego", "t",
  131. "http://schemas.xmlsoap.org/ws/2005/02/trust/RST/Issue",
  132. "http://schemas.xmlsoap.org/ws/2005/02/trust/RSTR/Issue",
  133. "http://schemas.xmlsoap.org/ws/2005/02/trust/Issue",
  134. "http://schemas.xmlsoap.org/ws/2005/02/trust/SymmetricKey",
  135. "http://schemas.xmlsoap.org/ws/2005/02/trust/CK/PSHA1",
  136. "http://schemas.xmlsoap.org/ws/2005/02/trust/Nonce", "RenewTarget", "CancelTarget", "RequestedTokenCancelled", "RequestedAttachedReference", "RequestedUnattachedReference", "IssuedTokens",
  137. "http://schemas.xmlsoap.org/ws/2005/02/trust/Renew",
  138. "http://schemas.xmlsoap.org/ws/2005/02/trust/Cancel",
  139. "http://schemas.xmlsoap.org/ws/2005/02/trust/PublicKey", "Access", "AccessDecision", "Advice", "AssertionID", "AssertionIDReference", "Attribute", "AttributeName", "AttributeNamespace", "AttributeStatement", "AttributeValue", "Audience", "AudienceRestrictionCondition", "AuthenticationInstant", "AuthenticationMethod", "AuthenticationStatement", "AuthorityBinding", "AuthorityKind", "AuthorizationDecisionStatement", "Binding", "Condition", "Conditions", "Decision", "DoNotCacheCondition", "Evidence", "IssueInstant", "Issuer", "Location", "MajorVersion", "MinorVersion", "NameIdentifier", "Format", "NameQualifier", "Namespace", "NotBefore", "NotOnOrAfter", "saml", "Statement", "Subject", "SubjectConfirmation", "SubjectConfirmationData", "ConfirmationMethod", "urn:oasis:names:tc:SAML:1.0:cm:holder-of-key", "urn:oasis:names:tc:SAML:1.0:cm:sender-vouches", "SubjectLocality", "DNSAddress", "IPAddress", "SubjectStatement", "urn:oasis:names:tc:SAML:1.0:am:unspecified", "xmlns", "Resource", "UserName", "urn:oasis:names:tc:SAML:1.1:nameid-format:WindowsDomainQualifiedName", "EmailName", "urn:oasis:names:tc:SAML:1.1:nameid-format:emailAddress", "u", "ChannelInstance",
  140. "http://schemas.microsoft.com/ws/2005/02/duplex", "Encoding", "MimeType", "CarriedKeyName", "Recipient", "EncryptedKey", "KeyReference", "e",
  141. "http://www.w3.org/2001/04/xmlenc#Element",
  142. "http://www.w3.org/2001/04/xmlenc#Content", "KeyName", "MgmtData", "KeyValue", "RSAKeyValue", "Modulus", "Exponent", "X509Data", "X509IssuerSerial", "X509IssuerName", "X509SerialNumber", "X509Certificate", "AckRequested",
  143. "http://schemas.xmlsoap.org/ws/2005/02/rm/AckRequested", "AcksTo", "Accept", "CreateSequence",
  144. "http://schemas.xmlsoap.org/ws/2005/02/rm/CreateSequence", "CreateSequenceRefused", "CreateSequenceResponse",
  145. "http://schemas.xmlsoap.org/ws/2005/02/rm/CreateSequenceResponse", "FaultCode", "InvalidAcknowledgement", "LastMessage",
  146. "http://schemas.xmlsoap.org/ws/2005/02/rm/LastMessage", "LastMessageNumberExceeded", "MessageNumberRollover", "Nack", "netrm", "Offer", "r", "SequenceFault", "SequenceTerminated", "TerminateSequence",
  147. "http://schemas.xmlsoap.org/ws/2005/02/rm/TerminateSequence", "UnknownSequence",
  148. "http://schemas.microsoft.com/ws/2006/02/tx/oletx", "oletx", "OleTxTransaction", "PropagationToken",
  149. "http://schemas.xmlsoap.org/ws/2004/10/wscoor", "wscoor", "CreateCoordinationContext", "CreateCoordinationContextResponse", "CoordinationContext", "CurrentContext", "CoordinationType", "RegistrationService", "Register", "RegisterResponse", "ProtocolIdentifier", "CoordinatorProtocolService", "ParticipantProtocolService",
  150. "http://schemas.xmlsoap.org/ws/2004/10/wscoor/CreateCoordinationContext",
  151. "http://schemas.xmlsoap.org/ws/2004/10/wscoor/CreateCoordinationContextResponse",
  152. "http://schemas.xmlsoap.org/ws/2004/10/wscoor/Register",
  153. "http://schemas.xmlsoap.org/ws/2004/10/wscoor/RegisterResponse",
  154. "http://schemas.xmlsoap.org/ws/2004/10/wscoor/fault", "ActivationCoordinatorPortType", "RegistrationCoordinatorPortType", "InvalidState", "InvalidProtocol", "InvalidParameters", "NoActivity", "ContextRefused", "AlreadyRegistered",
  155. "http://schemas.xmlsoap.org/ws/2004/10/wsat", "wsat",
  156. "http://schemas.xmlsoap.org/ws/2004/10/wsat/Completion",
  157. "http://schemas.xmlsoap.org/ws/2004/10/wsat/Durable2PC",
  158. "http://schemas.xmlsoap.org/ws/2004/10/wsat/Volatile2PC", "Prepare", "Prepared", "ReadOnly", "Commit", "Rollback", "Committed", "Aborted", "Replay",
  159. "http://schemas.xmlsoap.org/ws/2004/10/wsat/Commit",
  160. "http://schemas.xmlsoap.org/ws/2004/10/wsat/Rollback",
  161. "http://schemas.xmlsoap.org/ws/2004/10/wsat/Committed",
  162. "http://schemas.xmlsoap.org/ws/2004/10/wsat/Aborted",
  163. "http://schemas.xmlsoap.org/ws/2004/10/wsat/Prepare",
  164. "http://schemas.xmlsoap.org/ws/2004/10/wsat/Prepared",
  165. "http://schemas.xmlsoap.org/ws/2004/10/wsat/ReadOnly",
  166. "http://schemas.xmlsoap.org/ws/2004/10/wsat/Replay",
  167. "http://schemas.xmlsoap.org/ws/2004/10/wsat/fault", "CompletionCoordinatorPortType", "CompletionParticipantPortType", "CoordinatorPortType", "ParticipantPortType", "InconsistentInternalState", "mstx", "Enlistment", "protocol", "LocalTransactionId", "IsolationLevel", "IsolationFlags", "Description", "Loopback", "RegisterInfo", "ContextId", "TokenId", "AccessDenied", "InvalidPolicy", "CoordinatorRegistrationFailed", "TooManyEnlistments", "Disabled", "ActivityId",
  168. "http://schemas.microsoft.com/2004/09/ServiceModel/Diagnostics",
  169. "http://docs.oasis-open.org/wss/oasis-wss-kerberos-token-profile-1.1#Kerberosv5APREQSHA1",
  170. "http://schemas.xmlsoap.org/ws/2002/12/policy", "FloodMessage", "LinkUtility", "Hops",
  171. "http://schemas.microsoft.com/net/2006/05/peer/HopCount", "PeerVia",
  172. "http://schemas.microsoft.com/net/2006/05/peer", "PeerFlooder", "PeerTo",
  173. "http://schemas.microsoft.com/ws/2005/05/routing", "PacketRoutable",
  174. "http://schemas.microsoft.com/ws/2005/05/addressing/none",
  175. "http://schemas.microsoft.com/ws/2005/05/envelope/none",
  176. "http://www.w3.org/2001/XMLSchema-instance",
  177. "http://www.w3.org/2001/XMLSchema", "nil", "type", "char", "boolean", "byte", "unsignedByte", "short", "unsignedShort", "int", "unsignedInt", "long", "unsignedLong", "float", "double", "decimal", "dateTime", "string", "base64Binary", "anyType", "duration", "guid", "anyURI", "QName", "time", "date", "hexBinary", "gYearMonth", "gYear", "gMonthDay", "gDay", "gMonth", "integer", "positiveInteger", "negativeInteger", "nonPositiveInteger", "nonNegativeInteger", "normalizedString", "ConnectionLimitReached",
  178. "http://schemas.xmlsoap.org/soap/envelope/", "Actor", "Faultcode", "Faultstring", "Faultactor", "Detail"
  179. };
  180. static BinaryMessageEncoder ()
  181. {
  182. var d = new XmlDictionary ();
  183. soap_dictionary = d;
  184. foreach (var s in dict_strings)
  185. d.Add (s);
  186. }
  187. public BinaryMessageEncoder ()
  188. {
  189. }
  190. public BinaryMessageEncoder (BinaryMessageEncoderFactory owner, bool session)
  191. {
  192. this.owner = owner;
  193. this.session = session;
  194. }
  195. BinaryMessageEncoderFactory owner;
  196. bool session;
  197. public override string ContentType {
  198. get { return MediaType; }
  199. }
  200. public override string MediaType {
  201. get { return session ? "application/soap+msbinsession1" : "application/soap+msbin1"; }
  202. }
  203. public override MessageVersion MessageVersion {
  204. get { return MessageVersion.Default; }
  205. }
  206. [MonoTODO]
  207. public override Message ReadMessage (ArraySegment<byte> buffer,
  208. BufferManager bufferManager, string contentType)
  209. {
  210. if (contentType != ContentType)
  211. throw new ProtocolException ("Only content type 'application/soap+msbin1' is allowed.");
  212. // FIXME: retrieve reader session and message body.
  213. throw new NotImplementedException ();
  214. /*
  215. // FIXME: use bufferManager
  216. return Message.CreateMessage (
  217. XmlDictionaryReader.CreateBinaryReader (
  218. buffer.Array, buffer.Offset, buffer.Count,
  219. soap_dictionary,
  220. owner != null ? owner.Owner.ReaderQuotas : new XmlDictionaryReaderQuotas ()),
  221. int.MaxValue, MessageVersion);
  222. */
  223. }
  224. // It is sort of nasty hack, but there is no other way to provide reader/writer session from TCP stream.
  225. internal XmlBinaryReaderSession CurrentReaderSession { get; set; }
  226. internal XmlBinaryWriterSession CurrentWriterSession { get; set; }
  227. public override Message ReadMessage (Stream stream,
  228. int maxSizeOfHeaders, string contentType)
  229. {
  230. if (contentType != ContentType)
  231. throw new ProtocolException ("Only content type 'application/soap+msbin1' is allowed.");
  232. return Message.CreateMessage (
  233. XmlDictionaryReader.CreateBinaryReader (stream, session ? soap_dictionary : null, owner != null ? owner.Owner.ReaderQuotas : new XmlDictionaryReaderQuotas (), session ? CurrentReaderSession : null),
  234. maxSizeOfHeaders, MessageVersion);
  235. }
  236. public override void WriteMessage (Message message, Stream stream)
  237. {
  238. VerifyMessageVersion (message);
  239. using (var xw = XmlDictionaryWriter.CreateBinaryWriter (stream, session ? soap_dictionary : null, session ? CurrentWriterSession : null))
  240. message.WriteMessage (xw);
  241. }
  242. [MonoTODO]
  243. public override ArraySegment<byte> WriteMessage (
  244. Message message, int maxMessageSize,
  245. BufferManager bufferManager, int messageOffset)
  246. {
  247. VerifyMessageVersion (message);
  248. throw new NotImplementedException ();
  249. }
  250. }
  251. }