1 //------------------------------------------------------------
2 // Copyright (c) Microsoft Corporation. All rights reserved.
3 //------------------------------------------------------------
4 namespace System.ServiceModel.Channels
6 using System.Collections;
7 using System.Collections.Generic;
8 using System.Collections.ObjectModel;
9 using System.Diagnostics;
11 using System.Runtime.Serialization;
12 using System.ServiceModel;
13 using System.ServiceModel.Diagnostics;
14 using System.ServiceModel.Dispatcher;
17 public sealed class MessageHeaders : IEnumerable<MessageHeaderInfo>
19 int collectionVersion;
22 MessageVersion version;
23 IBufferedMessageData bufferedMessageData;
24 UnderstoodHeaders understoodHeaders;
25 const int InitialHeaderCount = 4;
26 const int MaxRecycledArrayLength = 8;
27 static XmlDictionaryString[] localNames;
29 internal const string WildcardAction = "*";
31 // The highest node and attribute counts reached by the BVTs were 1829 and 667 respectively.
32 const int MaxBufferedHeaderNodes = 4096;
33 const int MaxBufferedHeaderAttributes = 2048;
36 bool understoodHeadersModified;
38 public MessageHeaders(MessageVersion version, int initialSize)
40 Init(version, initialSize);
43 public MessageHeaders(MessageVersion version)
44 : this(version, InitialHeaderCount)
48 internal MessageHeaders(MessageVersion version, XmlDictionaryReader reader, XmlAttributeHolder[] envelopeAttributes, XmlAttributeHolder[] headerAttributes, ref int maxSizeOfHeaders)
51 if (maxSizeOfHeaders < 0)
53 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(
54 new ArgumentOutOfRangeException("maxSizeOfHeaders", maxSizeOfHeaders,
55 SR.GetString(SR.ValueMustBeNonNegative)));
59 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentNullException("version"));
61 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentNullException("reader"));
62 if (reader.IsEmptyElement)
67 XmlBuffer xmlBuffer = null;
68 EnvelopeVersion envelopeVersion = version.Envelope;
69 reader.ReadStartElement(XD.MessageDictionary.Header, envelopeVersion.DictionaryNamespace);
70 while (reader.IsStartElement())
72 if (xmlBuffer == null)
73 xmlBuffer = new XmlBuffer(maxSizeOfHeaders);
74 BufferedHeader bufferedHeader = new BufferedHeader(version, xmlBuffer, reader, envelopeAttributes, headerAttributes);
75 HeaderProcessing processing = bufferedHeader.MustUnderstand ? HeaderProcessing.MustUnderstand : 0;
76 HeaderKind kind = GetHeaderKind(bufferedHeader);
77 if (kind != HeaderKind.Unknown)
79 processing |= HeaderProcessing.Understood;
80 MessageHeaders.TraceUnderstood(bufferedHeader);
82 Header newHeader = new Header(kind, bufferedHeader, processing);
85 if (xmlBuffer != null)
88 maxSizeOfHeaders -= xmlBuffer.BufferSize;
90 reader.ReadEndElement();
91 this.collectionVersion = 0;
94 internal MessageHeaders(MessageVersion version, XmlDictionaryReader reader, IBufferedMessageData bufferedMessageData, RecycledMessageState recycledMessageState, bool[] understoodHeaders, bool understoodHeadersModified)
96 this.headers = new Header[InitialHeaderCount];
97 Init(version, reader, bufferedMessageData, recycledMessageState, understoodHeaders, understoodHeadersModified);
100 internal MessageHeaders(MessageVersion version, MessageHeaders headers, IBufferedMessageData bufferedMessageData)
102 this.version = version;
103 this.bufferedMessageData = bufferedMessageData;
104 this.headerCount = headers.headerCount;
105 this.headers = new Header[headerCount];
106 Array.Copy(headers.headers, this.headers, headerCount);
107 this.collectionVersion = 0;
110 public MessageHeaders(MessageHeaders collection)
112 if (collection == null)
113 throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("collection");
115 Init(collection.version, collection.headers.Length);
116 CopyHeadersFrom(collection);
117 this.collectionVersion = 0;
124 int index = FindHeaderProperty(HeaderKind.Action);
127 ActionHeader actionHeader = headers[index].HeaderInfo as ActionHeader;
128 if (actionHeader != null)
129 return actionHeader.Action;
130 using (XmlDictionaryReader reader = GetReaderAtHeader(index))
132 return ActionHeader.ReadHeaderValue(reader, version.Addressing);
138 SetActionHeader(ActionHeader.Create(value, version.Addressing));
140 SetHeaderProperty(HeaderKind.Action, null);
144 internal bool CanRecycle
146 get { return headers.Length <= MaxRecycledArrayLength; }
149 internal bool ContainsOnlyBufferedMessageHeaders
151 get { return (bufferedMessageData != null && collectionVersion == 0); }
154 internal int CollectionVersion
156 get { return collectionVersion; }
161 get { return headerCount; }
164 public EndpointAddress FaultTo
168 int index = FindHeaderProperty(HeaderKind.FaultTo);
171 FaultToHeader faultToHeader = headers[index].HeaderInfo as FaultToHeader;
172 if (faultToHeader != null)
173 return faultToHeader.FaultTo;
174 using (XmlDictionaryReader reader = GetReaderAtHeader(index))
176 return FaultToHeader.ReadHeaderValue(reader, version.Addressing);
182 SetFaultToHeader(FaultToHeader.Create(value, version.Addressing));
184 SetHeaderProperty(HeaderKind.FaultTo, null);
188 public EndpointAddress From
192 int index = FindHeaderProperty(HeaderKind.From);
195 FromHeader fromHeader = headers[index].HeaderInfo as FromHeader;
196 if (fromHeader != null)
197 return fromHeader.From;
198 using (XmlDictionaryReader reader = GetReaderAtHeader(index))
200 return FromHeader.ReadHeaderValue(reader, version.Addressing);
206 SetFromHeader(FromHeader.Create(value, version.Addressing));
208 SetHeaderProperty(HeaderKind.From, null);
212 internal bool HasMustUnderstandBeenModified
216 if (understoodHeaders != null)
218 return understoodHeaders.Modified;
222 return this.understoodHeadersModified;
227 public UniqueId MessageId
231 int index = FindHeaderProperty(HeaderKind.MessageId);
234 MessageIDHeader messageIDHeader = headers[index].HeaderInfo as MessageIDHeader;
235 if (messageIDHeader != null)
236 return messageIDHeader.MessageId;
237 using (XmlDictionaryReader reader = GetReaderAtHeader(index))
239 return MessageIDHeader.ReadHeaderValue(reader, version.Addressing);
245 SetMessageIDHeader(MessageIDHeader.Create(value, version.Addressing));
247 SetHeaderProperty(HeaderKind.MessageId, null);
251 public MessageVersion MessageVersion
253 get { return version; }
256 public UniqueId RelatesTo
260 return GetRelatesTo(RelatesToHeader.ReplyRelationshipType);
264 SetRelatesTo(RelatesToHeader.ReplyRelationshipType, value);
268 public EndpointAddress ReplyTo
272 int index = FindHeaderProperty(HeaderKind.ReplyTo);
275 ReplyToHeader replyToHeader = headers[index].HeaderInfo as ReplyToHeader;
276 if (replyToHeader != null)
277 return replyToHeader.ReplyTo;
278 using (XmlDictionaryReader reader = GetReaderAtHeader(index))
280 return ReplyToHeader.ReadHeaderValue(reader, version.Addressing);
286 SetReplyToHeader(ReplyToHeader.Create(value, version.Addressing));
288 SetHeaderProperty(HeaderKind.ReplyTo, null);
296 int index = FindHeaderProperty(HeaderKind.To);
299 ToHeader toHeader = headers[index].HeaderInfo as ToHeader;
300 if (toHeader != null)
302 using (XmlDictionaryReader reader = GetReaderAtHeader(index))
304 return ToHeader.ReadHeaderValue(reader, version.Addressing);
310 SetToHeader(ToHeader.Create(value, version.Addressing));
312 SetHeaderProperty(HeaderKind.To, null);
316 public UnderstoodHeaders UnderstoodHeaders
320 if (understoodHeaders == null)
321 understoodHeaders = new UnderstoodHeaders(this, understoodHeadersModified);
322 return understoodHeaders;
326 public MessageHeaderInfo this[int index]
330 if (index < 0 || index >= headerCount)
332 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(
333 new ArgumentOutOfRangeException("index", index,
334 SR.GetString(SR.ValueMustBeInRange, 0, headerCount)));
337 return headers[index].HeaderInfo;
341 public void Add(MessageHeader header)
343 Insert(headerCount, header);
346 internal void AddActionHeader(ActionHeader actionHeader)
348 Insert(headerCount, actionHeader, HeaderKind.Action);
351 internal void AddMessageIDHeader(MessageIDHeader messageIDHeader)
353 Insert(headerCount, messageIDHeader, HeaderKind.MessageId);
356 internal void AddRelatesToHeader(RelatesToHeader relatesToHeader)
358 Insert(headerCount, relatesToHeader, HeaderKind.RelatesTo);
361 internal void AddReplyToHeader(ReplyToHeader replyToHeader)
363 Insert(headerCount, replyToHeader, HeaderKind.ReplyTo);
366 internal void AddToHeader(ToHeader toHeader)
368 Insert(headerCount, toHeader, HeaderKind.To);
371 void Add(MessageHeader header, HeaderKind kind)
373 Insert(headerCount, header, kind);
376 void AddHeader(Header header)
378 InsertHeader(headerCount, header);
381 internal void AddUnderstood(int i)
383 headers[i].HeaderProcessing |= HeaderProcessing.Understood;
384 MessageHeaders.TraceUnderstood(headers[i].HeaderInfo);
387 internal void AddUnderstood(MessageHeaderInfo headerInfo)
389 if (headerInfo == null)
390 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentNullException("headerInfo"));
391 for (int i = 0; i < headerCount; i++)
393 if ((object)headers[i].HeaderInfo == (object)headerInfo)
395 if ((headers[i].HeaderProcessing & HeaderProcessing.Understood) != 0)
397 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentException(
398 SR.GetString(SR.HeaderAlreadyUnderstood, headerInfo.Name, headerInfo.Namespace), "headerInfo"));
406 void CaptureBufferedHeaders()
408 CaptureBufferedHeaders(-1);
411 void CaptureBufferedHeaders(int exceptIndex)
413 using (XmlDictionaryReader reader = GetBufferedMessageHeaderReaderAtHeaderContents(bufferedMessageData))
415 for (int i = 0; i < headerCount; i++)
417 if (reader.NodeType != XmlNodeType.Element)
419 if (reader.MoveToContent() != XmlNodeType.Element)
423 Header header = headers[i];
424 if (i == exceptIndex || header.HeaderType != HeaderType.BufferedMessageHeader)
430 headers[i] = new Header(header.HeaderKind, CaptureBufferedHeader(reader,
431 header.HeaderInfo), header.HeaderProcessing);
435 bufferedMessageData = null;
438 BufferedHeader CaptureBufferedHeader(XmlDictionaryReader reader, MessageHeaderInfo headerInfo)
440 XmlBuffer buffer = new XmlBuffer(int.MaxValue);
441 XmlDictionaryWriter writer = buffer.OpenSection(bufferedMessageData.Quotas);
442 writer.WriteNode(reader, false);
443 buffer.CloseSection();
445 return new BufferedHeader(version, buffer, 0, headerInfo);
448 BufferedHeader CaptureBufferedHeader(IBufferedMessageData bufferedMessageData, MessageHeaderInfo headerInfo, int bufferedMessageHeaderIndex)
450 XmlBuffer buffer = new XmlBuffer(int.MaxValue);
451 XmlDictionaryWriter writer = buffer.OpenSection(bufferedMessageData.Quotas);
452 WriteBufferedMessageHeader(bufferedMessageData, bufferedMessageHeaderIndex, writer);
453 buffer.CloseSection();
455 return new BufferedHeader(version, buffer, 0, headerInfo);
458 BufferedHeader CaptureWriteableHeader(MessageHeader writeableHeader)
460 XmlBuffer buffer = new XmlBuffer(int.MaxValue);
461 XmlDictionaryWriter writer = buffer.OpenSection(XmlDictionaryReaderQuotas.Max);
462 writeableHeader.WriteHeader(writer, this.version);
463 buffer.CloseSection();
465 return new BufferedHeader(version, buffer, 0, writeableHeader);
470 for (int i = 0; i < headerCount; i++)
471 headers[i] = new Header();
474 bufferedMessageData = null;
477 public void CopyHeaderFrom(Message message, int headerIndex)
480 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentNullException("message"));
481 CopyHeaderFrom(message.Headers, headerIndex);
484 public void CopyHeaderFrom(MessageHeaders collection, int headerIndex)
486 if (collection == null)
488 throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("collection");
491 if (collection.version != version)
493 #pragma warning suppress 56506 // Microsoft, collection.version is never null
494 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentException(SR.GetString(SR.MessageHeaderVersionMismatch, collection.version.ToString(), version.ToString()), "collection"));
497 if (headerIndex < 0 || headerIndex >= collection.headerCount)
499 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(
500 new ArgumentOutOfRangeException("headerIndex", headerIndex,
501 SR.GetString(SR.ValueMustBeInRange, 0, collection.headerCount)));
503 Header header = collection.headers[headerIndex];
504 HeaderProcessing processing = header.HeaderInfo.MustUnderstand ? HeaderProcessing.MustUnderstand : 0;
505 if ((header.HeaderProcessing & HeaderProcessing.Understood) != 0 || header.HeaderKind != HeaderKind.Unknown)
506 processing |= HeaderProcessing.Understood;
507 switch (header.HeaderType)
509 case HeaderType.BufferedMessageHeader:
510 AddHeader(new Header(header.HeaderKind, collection.CaptureBufferedHeader(collection.bufferedMessageData,
511 header.HeaderInfo, headerIndex), processing));
513 case HeaderType.ReadableHeader:
514 AddHeader(new Header(header.HeaderKind, header.ReadableHeader, processing));
516 case HeaderType.WriteableHeader:
517 AddHeader(new Header(header.HeaderKind, header.MessageHeader, processing));
520 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new InvalidOperationException(SR.GetString(SR.InvalidEnumValue, header.HeaderType)));
524 public void CopyHeadersFrom(Message message)
527 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentNullException("message"));
528 CopyHeadersFrom(message.Headers);
531 public void CopyHeadersFrom(MessageHeaders collection)
533 if (collection == null)
534 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentNullException("collection"));
535 for (int i = 0; i < collection.headerCount; i++)
536 CopyHeaderFrom(collection, i);
539 public void CopyTo(MessageHeaderInfo[] array, int index)
543 throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("array");
546 if (index < 0 || (index + headerCount) > array.Length)
548 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(
549 new ArgumentOutOfRangeException("index", index,
550 SR.GetString(SR.ValueMustBeInRange, 0, array.Length - headerCount)));
552 for (int i = 0; i < headerCount; i++)
553 array[i + index] = headers[i].HeaderInfo;
556 Exception CreateDuplicateHeaderException(HeaderKind kind)
561 case HeaderKind.Action:
562 name = AddressingStrings.Action;
564 case HeaderKind.FaultTo:
565 name = AddressingStrings.FaultTo;
567 case HeaderKind.From:
568 name = AddressingStrings.From;
570 case HeaderKind.MessageId:
571 name = AddressingStrings.MessageId;
573 case HeaderKind.ReplyTo:
574 name = AddressingStrings.ReplyTo;
577 name = AddressingStrings.To;
580 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new InvalidOperationException(SR.GetString(SR.InvalidEnumValue, kind)));
583 return new MessageHeaderException(
584 SR.GetString(SR.MultipleMessageHeaders, name, this.version.Addressing.Namespace),
586 this.version.Addressing.Namespace,
590 public int FindHeader(string name, string ns)
593 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentNullException("name"));
595 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentNullException("ns"));
597 if (ns == this.version.Addressing.Namespace)
599 return FindAddressingHeader(name, ns);
603 return FindNonAddressingHeader(name, ns, version.Envelope.UltimateDestinationActorValues);
607 int FindAddressingHeader(string name, string ns)
610 for (int i = 0; i < headerCount; i++)
612 if (headers[i].HeaderKind != HeaderKind.Unknown)
614 MessageHeaderInfo info = headers[i].HeaderInfo;
615 if (info.Name == name && info.Namespace == ns)
619 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(
620 new MessageHeaderException(SR.GetString(SR.MultipleMessageHeaders, name, ns), name, ns, true));
629 int FindNonAddressingHeader(string name, string ns, string[] actors)
632 for (int i = 0; i < headerCount; i++)
634 if (headers[i].HeaderKind == HeaderKind.Unknown)
636 MessageHeaderInfo info = headers[i].HeaderInfo;
637 if (info.Name == name && info.Namespace == ns)
639 for (int j = 0; j < actors.Length; j++)
641 if (actors[j] == info.Actor)
645 if (actors.Length == 1)
646 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new MessageHeaderException(SR.GetString(SR.MultipleMessageHeadersWithActor, name, ns, actors[0]), name, ns, true));
647 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new MessageHeaderException(SR.GetString(SR.MultipleMessageHeaders, name, ns), name, ns, true));
658 public int FindHeader(string name, string ns, params string[] actors)
661 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentNullException("name"));
663 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentNullException("ns"));
665 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentNullException("actors"));
667 for (int i = 0; i < headerCount; i++)
669 MessageHeaderInfo info = headers[i].HeaderInfo;
670 if (info.Name == name && info.Namespace == ns)
672 for (int j = 0; j < actors.Length; j++)
674 if (actors[j] == info.Actor)
678 if (actors.Length == 1)
679 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new MessageHeaderException(SR.GetString(SR.MultipleMessageHeadersWithActor, name, ns, actors[0]), name, ns, true));
680 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new MessageHeaderException(SR.GetString(SR.MultipleMessageHeaders, name, ns), name, ns, true));
690 int FindHeaderProperty(HeaderKind kind)
693 for (int i = 0; i < headerCount; i++)
695 if (headers[i].HeaderKind == kind)
698 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(CreateDuplicateHeaderException(kind));
705 int FindRelatesTo(Uri relationshipType, out UniqueId messageId)
707 UniqueId foundValue = null;
709 for (int i = 0; i < headerCount; i++)
711 if (headers[i].HeaderKind == HeaderKind.RelatesTo)
713 Uri tempRelationship;
715 GetRelatesToValues(i, out tempRelationship, out tempValue);
717 if (relationshipType == tempRelationship)
719 if (foundValue != null)
721 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(
722 new MessageHeaderException(
723 SR.GetString(SR.MultipleRelatesToHeaders, relationshipType.AbsoluteUri),
724 AddressingStrings.RelatesTo,
725 this.version.Addressing.Namespace,
728 foundValue = tempValue;
734 messageId = foundValue;
738 IEnumerator IEnumerable.GetEnumerator()
740 return this.GetEnumerator();
743 public IEnumerator<MessageHeaderInfo> GetEnumerator()
745 MessageHeaderInfo[] headers = new MessageHeaderInfo[headerCount];
747 return GetEnumerator(headers);
750 IEnumerator<MessageHeaderInfo> GetEnumerator(MessageHeaderInfo[] headers)
752 IList<MessageHeaderInfo> list = Array.AsReadOnly<MessageHeaderInfo>(headers);
753 return list.GetEnumerator();
756 internal IEnumerator<MessageHeaderInfo> GetUnderstoodEnumerator()
758 List<MessageHeaderInfo> understoodHeaders = new List<MessageHeaderInfo>();
760 for (int i = 0; i < headerCount; i++)
762 if ((headers[i].HeaderProcessing & HeaderProcessing.Understood) != 0)
764 understoodHeaders.Add(headers[i].HeaderInfo);
768 return understoodHeaders.GetEnumerator();
771 static XmlDictionaryReader GetBufferedMessageHeaderReaderAtHeaderContents(IBufferedMessageData bufferedMessageData)
773 XmlDictionaryReader reader = bufferedMessageData.GetMessageReader();
774 if (reader.NodeType == XmlNodeType.Element)
777 reader.ReadStartElement();
778 if (reader.NodeType == XmlNodeType.Element)
781 reader.ReadStartElement();
785 XmlDictionaryReader GetBufferedMessageHeaderReader(IBufferedMessageData bufferedMessageData, int bufferedMessageHeaderIndex)
787 // Check if we need to change representations
788 if (this.nodeCount > MaxBufferedHeaderNodes || this.attrCount > MaxBufferedHeaderAttributes)
790 CaptureBufferedHeaders();
791 return headers[bufferedMessageHeaderIndex].ReadableHeader.GetHeaderReader();
794 XmlDictionaryReader reader = GetBufferedMessageHeaderReaderAtHeaderContents(bufferedMessageData);
797 if (reader.NodeType != XmlNodeType.Element)
798 reader.MoveToContent();
799 if (bufferedMessageHeaderIndex == 0)
802 bufferedMessageHeaderIndex--;
808 void Skip(XmlDictionaryReader reader)
810 if (reader.MoveToContent() == XmlNodeType.Element && !reader.IsEmptyElement)
812 int depth = reader.Depth;
815 this.attrCount += reader.AttributeCount;
817 } while (reader.Read() && depth < reader.Depth);
820 if (reader.NodeType == XmlNodeType.EndElement)
828 this.attrCount += reader.AttributeCount;
834 public T GetHeader<T>(string name, string ns)
836 return GetHeader<T>(name, ns, DataContractSerializerDefaults.CreateSerializer(typeof(T), name, ns, int.MaxValue/*maxItems*/));
839 public T GetHeader<T>(string name, string ns, params string[] actors)
841 int index = FindHeader(name, ns, actors);
843 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new MessageHeaderException(SR.GetString(SR.HeaderNotFound, name, ns), name, ns));
844 return GetHeader<T>(index);
848 public T GetHeader<T>(string name, string ns, XmlObjectSerializer serializer)
850 if (serializer == null)
851 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentNullException("serializer"));
852 int index = FindHeader(name, ns);
854 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new MessageHeaderException(SR.GetString(SR.HeaderNotFound, name, ns), name, ns));
855 return GetHeader<T>(index, serializer);
858 public T GetHeader<T>(int index)
860 if (index < 0 || index >= headerCount)
862 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(
863 new ArgumentOutOfRangeException("index", index,
864 SR.GetString(SR.ValueMustBeInRange, 0, headerCount)));
867 MessageHeaderInfo headerInfo = headers[index].HeaderInfo;
868 return GetHeader<T>(index, DataContractSerializerDefaults.CreateSerializer(typeof(T), headerInfo.Name, headerInfo.Namespace, int.MaxValue/*maxItems*/));
871 public T GetHeader<T>(int index, XmlObjectSerializer serializer)
873 if (serializer == null)
874 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentNullException("serializer"));
875 using (XmlDictionaryReader reader = GetReaderAtHeader(index))
877 return (T)serializer.ReadObject(reader);
881 HeaderKind GetHeaderKind(MessageHeaderInfo headerInfo)
883 HeaderKind headerKind = HeaderKind.Unknown;
885 if (headerInfo.Namespace == this.version.Addressing.Namespace)
887 if (version.Envelope.IsUltimateDestinationActor(headerInfo.Actor))
889 string name = headerInfo.Name;
895 if (name == AddressingStrings.Action)
897 headerKind = HeaderKind.Action;
901 if (name == AddressingStrings.From)
903 headerKind = HeaderKind.From;
905 else if (name == AddressingStrings.FaultTo)
907 headerKind = HeaderKind.FaultTo;
911 if (name == AddressingStrings.MessageId)
913 headerKind = HeaderKind.MessageId;
917 if (name == AddressingStrings.ReplyTo)
919 headerKind = HeaderKind.ReplyTo;
921 else if (name == AddressingStrings.RelatesTo)
923 headerKind = HeaderKind.RelatesTo;
927 if (name == AddressingStrings.To)
929 headerKind = HeaderKind.To;
937 ValidateHeaderKind(headerKind);
941 void ValidateHeaderKind(HeaderKind headerKind)
943 if (this.version.Envelope == EnvelopeVersion.None)
945 if (headerKind != HeaderKind.Action && headerKind != HeaderKind.To)
947 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(
948 new InvalidOperationException(SR.GetString(SR.HeadersCannotBeAddedToEnvelopeVersion, this.version.Envelope)));
952 if (this.version.Addressing == AddressingVersion.None)
954 if (headerKind != HeaderKind.Unknown && headerKind != HeaderKind.Action && headerKind != HeaderKind.To)
956 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(
957 new InvalidOperationException(SR.GetString(SR.AddressingHeadersCannotBeAddedToAddressingVersion, this.version.Addressing)));
962 public XmlDictionaryReader GetReaderAtHeader(int headerIndex)
964 if (headerIndex < 0 || headerIndex >= headerCount)
966 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(
967 new ArgumentOutOfRangeException("headerIndex", headerIndex,
968 SR.GetString(SR.ValueMustBeInRange, 0, headerCount)));
971 switch (headers[headerIndex].HeaderType)
973 case HeaderType.ReadableHeader:
974 return headers[headerIndex].ReadableHeader.GetHeaderReader();
975 case HeaderType.WriteableHeader:
976 MessageHeader writeableHeader = headers[headerIndex].MessageHeader;
977 BufferedHeader bufferedHeader = CaptureWriteableHeader(writeableHeader);
978 headers[headerIndex] = new Header(headers[headerIndex].HeaderKind, bufferedHeader, headers[headerIndex].HeaderProcessing);
980 return bufferedHeader.GetHeaderReader();
981 case HeaderType.BufferedMessageHeader:
982 return GetBufferedMessageHeaderReader(bufferedMessageData, headerIndex);
984 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new InvalidOperationException(SR.GetString(SR.InvalidEnumValue, headers[headerIndex].HeaderType)));
988 internal UniqueId GetRelatesTo(Uri relationshipType)
990 if (relationshipType == null)
991 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentNullException("relationshipType"));
994 FindRelatesTo(relationshipType, out messageId);
998 void GetRelatesToValues(int index, out Uri relationshipType, out UniqueId messageId)
1000 RelatesToHeader relatesToHeader = headers[index].HeaderInfo as RelatesToHeader;
1001 if (relatesToHeader != null)
1003 relationshipType = relatesToHeader.RelationshipType;
1004 messageId = relatesToHeader.UniqueId;
1008 using (XmlDictionaryReader reader = GetReaderAtHeader(index))
1010 RelatesToHeader.ReadHeaderValue(reader, version.Addressing, out relationshipType, out messageId);
1015 internal string[] GetHeaderAttributes(string localName, string ns)
1017 string[] attrs = null;
1019 if (ContainsOnlyBufferedMessageHeaders)
1021 XmlDictionaryReader reader = bufferedMessageData.GetMessageReader();
1022 reader.ReadStartElement(); // Envelope
1023 reader.ReadStartElement(); // Header
1024 for (int index = 0; reader.IsStartElement(); index++)
1026 string value = reader.GetAttribute(localName, ns);
1030 attrs = new string[headerCount];
1031 attrs[index] = value;
1033 if (index == headerCount - 1)
1041 for (int index = 0; index < headerCount; index++)
1043 if (headers[index].HeaderType != HeaderType.WriteableHeader)
1045 using (XmlDictionaryReader reader = GetReaderAtHeader(index))
1047 string value = reader.GetAttribute(localName, ns);
1051 attrs = new string[headerCount];
1052 attrs[index] = value;
1062 internal MessageHeader GetMessageHeader(int index)
1064 if (index < 0 || index >= headerCount)
1066 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(
1067 new ArgumentOutOfRangeException("headerIndex", index,
1068 SR.GetString(SR.ValueMustBeInRange, 0, headerCount)));
1070 MessageHeader messageHeader;
1071 switch (headers[index].HeaderType)
1073 case HeaderType.WriteableHeader:
1074 case HeaderType.ReadableHeader:
1075 return headers[index].MessageHeader;
1076 case HeaderType.BufferedMessageHeader:
1077 messageHeader = CaptureBufferedHeader(bufferedMessageData, headers[index].HeaderInfo, index);
1078 headers[index] = new Header(headers[index].HeaderKind, messageHeader, headers[index].HeaderProcessing);
1079 collectionVersion++;
1080 return messageHeader;
1082 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new InvalidOperationException(SR.GetString(SR.InvalidEnumValue, headers[index].HeaderType)));
1086 internal Collection<MessageHeaderInfo> GetHeadersNotUnderstood()
1088 Collection<MessageHeaderInfo> notUnderstoodHeaders = null;
1090 for (int headerIndex = 0; headerIndex < headerCount; headerIndex++)
1092 if (headers[headerIndex].HeaderProcessing == HeaderProcessing.MustUnderstand)
1094 if (notUnderstoodHeaders == null)
1095 notUnderstoodHeaders = new Collection<MessageHeaderInfo>();
1097 MessageHeaderInfo headerInfo = headers[headerIndex].HeaderInfo;
1098 if (DiagnosticUtility.ShouldTraceWarning)
1100 TraceUtility.TraceEvent(TraceEventType.Warning, TraceCode.DidNotUnderstandMessageHeader,
1101 SR.GetString(SR.TraceCodeDidNotUnderstandMessageHeader),
1102 new MessageHeaderInfoTraceRecord(headerInfo), null, null);
1105 notUnderstoodHeaders.Add(headerInfo);
1109 return notUnderstoodHeaders;
1112 public bool HaveMandatoryHeadersBeenUnderstood()
1114 return HaveMandatoryHeadersBeenUnderstood(version.Envelope.MustUnderstandActorValues);
1117 public bool HaveMandatoryHeadersBeenUnderstood(params string[] actors)
1120 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentNullException("actors"));
1122 for (int headerIndex = 0; headerIndex < headerCount; headerIndex++)
1124 if (headers[headerIndex].HeaderProcessing == HeaderProcessing.MustUnderstand)
1126 for (int actorIndex = 0; actorIndex < actors.Length; ++actorIndex)
1128 if (headers[headerIndex].HeaderInfo.Actor == actors[actorIndex])
1139 internal void Init(MessageVersion version, int initialSize)
1143 if (initialSize < 0)
1145 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(
1146 new ArgumentOutOfRangeException("initialSize", initialSize,
1147 SR.GetString(SR.ValueMustBeNonNegative)));
1150 if (version == null)
1152 throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("version");
1155 this.version = version;
1156 headers = new Header[initialSize];
1159 internal void Init(MessageVersion version)
1163 this.version = version;
1164 this.collectionVersion = 0;
1167 internal void Init(MessageVersion version, XmlDictionaryReader reader, IBufferedMessageData bufferedMessageData, RecycledMessageState recycledMessageState, bool[] understoodHeaders, bool understoodHeadersModified)
1171 this.version = version;
1172 this.bufferedMessageData = bufferedMessageData;
1174 if (version.Envelope != EnvelopeVersion.None)
1176 this.understoodHeadersModified = (understoodHeaders != null) && understoodHeadersModified;
1177 if (reader.IsEmptyElement)
1182 EnvelopeVersion envelopeVersion = version.Envelope;
1183 Fx.Assert(reader.IsStartElement(XD.MessageDictionary.Header, envelopeVersion.DictionaryNamespace), "");
1184 reader.ReadStartElement();
1186 AddressingDictionary dictionary = XD.AddressingDictionary;
1188 if (localNames == null)
1190 XmlDictionaryString[] strings = new XmlDictionaryString[7];
1191 strings[(int)HeaderKind.To] = dictionary.To;
1192 strings[(int)HeaderKind.Action] = dictionary.Action;
1193 strings[(int)HeaderKind.MessageId] = dictionary.MessageId;
1194 strings[(int)HeaderKind.RelatesTo] = dictionary.RelatesTo;
1195 strings[(int)HeaderKind.ReplyTo] = dictionary.ReplyTo;
1196 strings[(int)HeaderKind.From] = dictionary.From;
1197 strings[(int)HeaderKind.FaultTo] = dictionary.FaultTo;
1198 System.Threading.Thread.MemoryBarrier();
1199 localNames = strings;
1204 while (reader.IsStartElement())
1206 ReadBufferedHeader(reader, recycledMessageState, localNames, (understoodHeaders == null) ? false : understoodHeaders[i++]);
1209 reader.ReadEndElement();
1211 this.collectionVersion = 0;
1214 public void Insert(int headerIndex, MessageHeader header)
1217 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentNullException("header"));
1218 if (!header.IsMessageVersionSupported(this.version))
1219 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentException(SR.GetString(SR.MessageHeaderVersionNotSupported,
1220 header.GetType().FullName, this.version.Envelope.ToString()), "header"));
1221 Insert(headerIndex, header, GetHeaderKind(header));
1224 void Insert(int headerIndex, MessageHeader header, HeaderKind kind)
1226 ReadableMessageHeader readableMessageHeader = header as ReadableMessageHeader;
1227 HeaderProcessing processing = header.MustUnderstand ? HeaderProcessing.MustUnderstand : 0;
1228 if (kind != HeaderKind.Unknown)
1229 processing |= HeaderProcessing.Understood;
1230 if (readableMessageHeader != null)
1231 InsertHeader(headerIndex, new Header(kind, readableMessageHeader, processing));
1233 InsertHeader(headerIndex, new Header(kind, header, processing));
1236 void InsertHeader(int headerIndex, Header header)
1238 ValidateHeaderKind(header.HeaderKind);
1240 if (headerIndex < 0 || headerIndex > headerCount)
1242 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(
1243 new ArgumentOutOfRangeException("headerIndex", headerIndex,
1244 SR.GetString(SR.ValueMustBeInRange, 0, headerCount)));
1247 if (headerCount == headers.Length)
1249 if (headers.Length == 0)
1251 headers = new Header[1];
1255 Header[] newHeaders = new Header[headers.Length * 2];
1256 headers.CopyTo(newHeaders, 0);
1257 headers = newHeaders;
1260 if (headerIndex < headerCount)
1262 if (bufferedMessageData != null)
1264 for (int i = headerIndex; i < headerCount; i++)
1266 if (headers[i].HeaderType == HeaderType.BufferedMessageHeader)
1268 CaptureBufferedHeaders();
1273 Array.Copy(headers, headerIndex, headers, headerIndex + 1, headerCount - headerIndex);
1275 headers[headerIndex] = header;
1277 collectionVersion++;
1280 internal bool IsUnderstood(int i)
1282 return (headers[i].HeaderProcessing & HeaderProcessing.Understood) != 0;
1285 internal bool IsUnderstood(MessageHeaderInfo headerInfo)
1287 if (headerInfo == null)
1288 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentNullException("headerInfo"));
1289 for (int i = 0; i < headerCount; i++)
1291 if ((object)headers[i].HeaderInfo == (object)headerInfo)
1293 if (IsUnderstood(i))
1301 void ReadBufferedHeader(XmlDictionaryReader reader, RecycledMessageState recycledMessageState, XmlDictionaryString[] localNames, bool understood)
1304 bool mustUnderstand;
1308 if (this.version.Addressing == AddressingVersion.None && reader.NamespaceURI == AddressingVersion.None.Namespace)
1310 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(
1311 new InvalidOperationException(SR.GetString(SR.AddressingHeadersCannotBeAddedToAddressingVersion, this.version.Addressing)));
1314 MessageHeader.GetHeaderAttributes(reader, version, out actor, out mustUnderstand, out relay, out isRefParam);
1316 HeaderKind kind = HeaderKind.Unknown;
1317 MessageHeaderInfo info = null;
1319 if (version.Envelope.IsUltimateDestinationActor(actor))
1321 Fx.Assert(version.Addressing.DictionaryNamespace != null, "non-None Addressing requires a non-null DictionaryNamespace");
1322 kind = (HeaderKind)reader.IndexOfLocalName(localNames, version.Addressing.DictionaryNamespace);
1326 info = ToHeader.ReadHeader(reader, version.Addressing, recycledMessageState.UriCache, actor, mustUnderstand, relay);
1328 case HeaderKind.Action:
1329 info = ActionHeader.ReadHeader(reader, version.Addressing, actor, mustUnderstand, relay);
1331 case HeaderKind.MessageId:
1332 info = MessageIDHeader.ReadHeader(reader, version.Addressing, actor, mustUnderstand, relay);
1334 case HeaderKind.RelatesTo:
1335 info = RelatesToHeader.ReadHeader(reader, version.Addressing, actor, mustUnderstand, relay);
1337 case HeaderKind.ReplyTo:
1338 info = ReplyToHeader.ReadHeader(reader, version.Addressing, actor, mustUnderstand, relay);
1340 case HeaderKind.From:
1341 info = FromHeader.ReadHeader(reader, version.Addressing, actor, mustUnderstand, relay);
1343 case HeaderKind.FaultTo:
1344 info = FaultToHeader.ReadHeader(reader, version.Addressing, actor, mustUnderstand, relay);
1347 kind = HeaderKind.Unknown;
1354 info = recycledMessageState.HeaderInfoCache.TakeHeaderInfo(reader, actor, mustUnderstand, relay, isRefParam);
1358 HeaderProcessing processing = mustUnderstand ? HeaderProcessing.MustUnderstand : 0;
1359 if (kind != HeaderKind.Unknown || understood)
1361 processing |= HeaderProcessing.Understood;
1362 MessageHeaders.TraceUnderstood(info);
1364 AddHeader(new Header(kind, info, processing));
1367 internal void Recycle(HeaderInfoCache headerInfoCache)
1369 for (int i = 0; i < headerCount; i++)
1371 if (headers[i].HeaderKind == HeaderKind.Unknown)
1373 headerInfoCache.ReturnHeaderInfo(headers[i].HeaderInfo);
1377 collectionVersion = 0;
1378 if (understoodHeaders != null)
1380 understoodHeaders.Modified = false;
1384 internal void RemoveUnderstood(MessageHeaderInfo headerInfo)
1386 if (headerInfo == null)
1387 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentNullException("headerInfo"));
1388 for (int i = 0; i < headerCount; i++)
1390 if ((object)headers[i].HeaderInfo == (object)headerInfo)
1392 if ((headers[i].HeaderProcessing & HeaderProcessing.Understood) == 0)
1394 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentException(
1395 SR.GetString(SR.HeaderAlreadyNotUnderstood, headerInfo.Name, headerInfo.Namespace), "headerInfo"));
1398 headers[i].HeaderProcessing &= ~HeaderProcessing.Understood;
1403 public void RemoveAll(string name, string ns)
1406 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentNullException("name"));
1408 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentNullException("ns"));
1409 for (int i = headerCount - 1; i >= 0; i--)
1411 MessageHeaderInfo info = headers[i].HeaderInfo;
1412 if (info.Name == name && info.Namespace == ns)
1419 public void RemoveAt(int headerIndex)
1421 if (headerIndex < 0 || headerIndex >= headerCount)
1423 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(
1424 new ArgumentOutOfRangeException("headerIndex", headerIndex,
1425 SR.GetString(SR.ValueMustBeInRange, 0, headerCount)));
1427 if (bufferedMessageData != null && headers[headerIndex].HeaderType == HeaderType.BufferedMessageHeader)
1428 CaptureBufferedHeaders(headerIndex);
1429 Array.Copy(headers, headerIndex + 1, headers, headerIndex, headerCount - headerIndex - 1);
1430 headers[--headerCount] = new Header();
1431 collectionVersion++;
1434 internal void ReplaceAt(int headerIndex, MessageHeader header)
1436 if (headerIndex < 0 || headerIndex >= headerCount)
1438 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(
1439 new ArgumentOutOfRangeException("headerIndex", headerIndex,
1440 SR.GetString(SR.ValueMustBeInRange, 0, headerCount)));
1445 throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("header");
1448 ReplaceAt(headerIndex, header, GetHeaderKind(header));
1451 void ReplaceAt(int headerIndex, MessageHeader header, HeaderKind kind)
1453 HeaderProcessing processing = header.MustUnderstand ? HeaderProcessing.MustUnderstand : 0;
1454 if (kind != HeaderKind.Unknown)
1455 processing |= HeaderProcessing.Understood;
1456 ReadableMessageHeader readableMessageHeader = header as ReadableMessageHeader;
1457 if (readableMessageHeader != null)
1458 headers[headerIndex] = new Header(kind, readableMessageHeader, processing);
1460 headers[headerIndex] = new Header(kind, header, processing);
1461 collectionVersion++;
1464 public void SetAction(XmlDictionaryString action)
1467 SetHeaderProperty(HeaderKind.Action, null);
1469 SetActionHeader(ActionHeader.Create(action, version.Addressing));
1472 internal void SetActionHeader(ActionHeader actionHeader)
1474 SetHeaderProperty(HeaderKind.Action, actionHeader);
1477 internal void SetFaultToHeader(FaultToHeader faultToHeader)
1479 SetHeaderProperty(HeaderKind.FaultTo, faultToHeader);
1482 internal void SetFromHeader(FromHeader fromHeader)
1484 SetHeaderProperty(HeaderKind.From, fromHeader);
1487 internal void SetMessageIDHeader(MessageIDHeader messageIDHeader)
1489 SetHeaderProperty(HeaderKind.MessageId, messageIDHeader);
1492 internal void SetRelatesTo(Uri relationshipType, UniqueId messageId)
1494 if (relationshipType == null)
1496 throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("relationshipType");
1499 RelatesToHeader relatesToHeader;
1500 if (!object.ReferenceEquals(messageId, null))
1502 relatesToHeader = RelatesToHeader.Create(messageId, version.Addressing, relationshipType);
1506 relatesToHeader = null;
1509 SetRelatesTo(RelatesToHeader.ReplyRelationshipType, relatesToHeader);
1512 void SetRelatesTo(Uri relationshipType, RelatesToHeader relatesToHeader)
1514 UniqueId previousUniqueId;
1515 int index = FindRelatesTo(relationshipType, out previousUniqueId);
1518 if (relatesToHeader == null)
1524 ReplaceAt(index, relatesToHeader, HeaderKind.RelatesTo);
1527 else if (relatesToHeader != null)
1529 Add(relatesToHeader, HeaderKind.RelatesTo);
1533 internal void SetReplyToHeader(ReplyToHeader replyToHeader)
1535 SetHeaderProperty(HeaderKind.ReplyTo, replyToHeader);
1538 internal void SetToHeader(ToHeader toHeader)
1540 SetHeaderProperty(HeaderKind.To, toHeader);
1543 void SetHeaderProperty(HeaderKind kind, MessageHeader header)
1545 int index = FindHeaderProperty(kind);
1554 ReplaceAt(index, header, kind);
1557 else if (header != null)
1563 public void WriteHeader(int headerIndex, XmlWriter writer)
1565 WriteHeader(headerIndex, XmlDictionaryWriter.CreateDictionaryWriter(writer));
1568 public void WriteHeader(int headerIndex, XmlDictionaryWriter writer)
1570 WriteStartHeader(headerIndex, writer);
1571 WriteHeaderContents(headerIndex, writer);
1572 writer.WriteEndElement();
1575 public void WriteStartHeader(int headerIndex, XmlWriter writer)
1577 WriteStartHeader(headerIndex, XmlDictionaryWriter.CreateDictionaryWriter(writer));
1580 public void WriteStartHeader(int headerIndex, XmlDictionaryWriter writer)
1584 throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("writer");
1587 if (headerIndex < 0 || headerIndex >= headerCount)
1589 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(
1590 new ArgumentOutOfRangeException("headerIndex", headerIndex,
1591 SR.GetString(SR.ValueMustBeInRange, 0, headerCount)));
1593 switch (headers[headerIndex].HeaderType)
1595 case HeaderType.ReadableHeader:
1596 case HeaderType.WriteableHeader:
1597 headers[headerIndex].MessageHeader.WriteStartHeader(writer, this.version);
1599 case HeaderType.BufferedMessageHeader:
1600 WriteStartBufferedMessageHeader(bufferedMessageData, headerIndex, writer);
1603 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new InvalidOperationException(SR.GetString(SR.InvalidEnumValue, headers[headerIndex].HeaderType)));
1607 public void WriteHeaderContents(int headerIndex, XmlWriter writer)
1609 WriteHeaderContents(headerIndex, XmlDictionaryWriter.CreateDictionaryWriter(writer));
1612 public void WriteHeaderContents(int headerIndex, XmlDictionaryWriter writer)
1616 throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("writer");
1619 if (headerIndex < 0 || headerIndex >= headerCount)
1621 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(
1622 new ArgumentOutOfRangeException("headerIndex", headerIndex,
1623 SR.GetString(SR.ValueMustBeInRange, 0, headerCount)));
1625 switch (headers[headerIndex].HeaderType)
1627 case HeaderType.ReadableHeader:
1628 case HeaderType.WriteableHeader:
1629 headers[headerIndex].MessageHeader.WriteHeaderContents(writer, this.version);
1631 case HeaderType.BufferedMessageHeader:
1632 WriteBufferedMessageHeaderContents(bufferedMessageData, headerIndex, writer);
1635 throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new InvalidOperationException(SR.GetString(SR.InvalidEnumValue, headers[headerIndex].HeaderType)));
1639 static void TraceUnderstood(MessageHeaderInfo info)
1641 if (DiagnosticUtility.ShouldTraceVerbose)
1643 TraceUtility.TraceEvent(TraceEventType.Verbose, TraceCode.UnderstoodMessageHeader,
1644 SR.GetString(SR.TraceCodeUnderstoodMessageHeader),
1645 new MessageHeaderInfoTraceRecord(info), null, null);
1649 void WriteBufferedMessageHeader(IBufferedMessageData bufferedMessageData, int bufferedMessageHeaderIndex, XmlWriter writer)
1651 using (XmlReader reader = GetBufferedMessageHeaderReader(bufferedMessageData, bufferedMessageHeaderIndex))
1653 writer.WriteNode(reader, false);
1657 void WriteStartBufferedMessageHeader(IBufferedMessageData bufferedMessageData, int bufferedMessageHeaderIndex, XmlWriter writer)
1659 using (XmlReader reader = GetBufferedMessageHeaderReader(bufferedMessageData, bufferedMessageHeaderIndex))
1661 writer.WriteStartElement(reader.Prefix, reader.LocalName, reader.NamespaceURI);
1662 writer.WriteAttributes(reader, false);
1666 void WriteBufferedMessageHeaderContents(IBufferedMessageData bufferedMessageData, int bufferedMessageHeaderIndex, XmlWriter writer)
1668 using (XmlReader reader = GetBufferedMessageHeaderReader(bufferedMessageData, bufferedMessageHeaderIndex))
1670 if (!reader.IsEmptyElement)
1672 reader.ReadStartElement();
1673 while (reader.NodeType != XmlNodeType.EndElement)
1675 writer.WriteNode(reader, false);
1677 reader.ReadEndElement();
1682 enum HeaderType : byte
1686 BufferedMessageHeader,
1690 enum HeaderKind : byte
1703 enum HeaderProcessing : byte
1705 MustUnderstand = 0x1,
1713 HeaderProcessing processing;
1714 MessageHeaderInfo info;
1716 public Header(HeaderKind kind, MessageHeaderInfo info, HeaderProcessing processing)
1719 this.type = HeaderType.BufferedMessageHeader;
1721 this.processing = processing;
1724 public Header(HeaderKind kind, ReadableMessageHeader readableHeader, HeaderProcessing processing)
1727 this.type = HeaderType.ReadableHeader;
1728 this.info = readableHeader;
1729 this.processing = processing;
1732 public Header(HeaderKind kind, MessageHeader header, HeaderProcessing processing)
1735 this.type = HeaderType.WriteableHeader;
1737 this.processing = processing;
1740 public HeaderType HeaderType
1742 get { return type; }
1745 public HeaderKind HeaderKind
1747 get { return kind; }
1750 public MessageHeaderInfo HeaderInfo
1752 get { return info; }
1755 public MessageHeader MessageHeader
1759 Fx.Assert(type == HeaderType.WriteableHeader || type == HeaderType.ReadableHeader, "");
1760 return (MessageHeader)info;
1764 public HeaderProcessing HeaderProcessing
1766 get { return processing; }
1767 set { processing = value; }
1770 public ReadableMessageHeader ReadableHeader
1774 Fx.Assert(type == HeaderType.ReadableHeader, "");
1775 return (ReadableMessageHeader)info;