1 // Licensed to the .NET Foundation under one or more agreements.
2 // The .NET Foundation licenses this file to you under the MIT license.
3 // See the LICENSE file in the project root for more information.
4 
5 using System;
6 using System.Collections;
7 using System.Collections.Generic;
8 using System.Globalization;
9 using System.Reflection;
10 using System.Runtime.Serialization;
11 using System.Security.Cryptography;
12 using System.Text;
13 using System.Xml;
14 using System.Xml.Schema;
15 using System.Xml.Serialization;
16 
17 namespace SerializationTestTypes
18 {
19     interface IGenericNameProvider
20     {
GetParameterCount()21         int GetParameterCount();
GetParameterName(int paramIndex)22         string GetParameterName(int paramIndex);
GetNamespaces()23         string GetNamespaces();
GetGenericTypeName()24         string GetGenericTypeName();
25         bool ParametersFromBuiltInNamespaces { get; }
26     }
27 
28     class GenericNameProvider : IGenericNameProvider
29     {
30         string genericTypeName;
31         object[] genericParams;
GenericNameProvider(Type type)32         internal GenericNameProvider(Type type)
33             : this(type.GetGenericTypeDefinition().FullName, type.GetGenericArguments())
34         {
35         }
36 
GenericNameProvider(string genericTypeName, object[] genericParams)37         internal GenericNameProvider(string genericTypeName, object[] genericParams)
38         {
39             this.genericTypeName = genericTypeName;
40             this.genericParams = new object[genericParams.Length];
41             genericParams.CopyTo(this.genericParams, 0);
42         }
43 
GetParameterCount()44         public int GetParameterCount()
45         {
46             return genericParams.Length;
47         }
48 
GetParameterName(int paramIndex)49         public string GetParameterName(int paramIndex)
50         {
51             return GetStableName(paramIndex).Name;
52         }
53 
GetNamespaces()54         public string GetNamespaces()
55         {
56             StringBuilder namespaces = new StringBuilder();
57             for (int j = 0; j < GetParameterCount(); j++)
58                 namespaces.Append(" ").Append(GetStableName(j).Namespace);
59             return namespaces.ToString();
60         }
61 
GetGenericTypeName()62         public string GetGenericTypeName()
63         {
64             return genericTypeName;
65         }
66 
67         public bool ParametersFromBuiltInNamespaces
68         {
69             get
70             {
71                 bool parametersFromBuiltInNamespaces = true;
72                 for (int j = 0; j < GetParameterCount(); j++)
73                 {
74                     if (parametersFromBuiltInNamespaces)
75                         parametersFromBuiltInNamespaces = DataContract.IsBuiltInNamespace(GetStableName(j).Namespace);
76                     else
77                         break;
78                 }
79                 return parametersFromBuiltInNamespaces;
80             }
81         }
82 
GetStableName(int i)83         XmlQualifiedName GetStableName(int i)
84         {
85             object o = genericParams[i];
86             XmlQualifiedName qname = o as XmlQualifiedName;
87             if (qname == null)
88             {
89                 Type paramType = o as Type;
90                 if (paramType != null)
91                     genericParams[i] = qname = DataContract.GetStableName(paramType);
92                 else
93                     genericParams[i] = qname = ((DataContract)o).StableName;
94             }
95             return qname;
96         }
97     }
98 
99     class GenericInfo : IGenericNameProvider
100     {
101         string genericTypeName;
102         XmlQualifiedName stableName;
103         List<GenericInfo> paramGenericInfos;
104 
GenericInfo(XmlQualifiedName stableName, string genericTypeName)105         internal GenericInfo(XmlQualifiedName stableName, string genericTypeName)
106         {
107             this.stableName = stableName;
108             this.genericTypeName = genericTypeName;
109         }
110 
Add(GenericInfo actualParamInfo)111         internal void Add(GenericInfo actualParamInfo)
112         {
113             if (paramGenericInfos == null)
114                 paramGenericInfos = new List<GenericInfo>();
115             paramGenericInfos.Add(actualParamInfo);
116         }
117 
GetExpandedStableName()118         internal XmlQualifiedName GetExpandedStableName()
119         {
120             if (paramGenericInfos == null)
121                 return stableName;
122             return new XmlQualifiedName(DataContract.ExpandGenericParameters(XmlConvert.DecodeName(stableName.Name), this), stableName.Namespace);
123         }
124 
GetStableNamespace()125         internal string GetStableNamespace()
126         {
127             return stableName.Namespace;
128         }
129 
130         internal XmlQualifiedName StableName
131         {
132             get { return stableName; }
133         }
134 
135         internal IList<GenericInfo> Parameters
136         {
137             get { return paramGenericInfos; }
138         }
139 
GetParameterCount()140         public int GetParameterCount()
141         {
142             return paramGenericInfos.Count;
143         }
144 
GetParameterName(int paramIndex)145         public string GetParameterName(int paramIndex)
146         {
147             return paramGenericInfos[paramIndex].GetExpandedStableName().Name;
148         }
149 
GetNamespaces()150         public string GetNamespaces()
151         {
152             StringBuilder namespaces = new StringBuilder();
153             for (int j = 0; j < paramGenericInfos.Count; j++)
154                 namespaces.Append(" ").Append(paramGenericInfos[j].GetStableNamespace());
155             return namespaces.ToString();
156         }
157 
GetGenericTypeName()158         public string GetGenericTypeName()
159         {
160             return genericTypeName;
161         }
162 
163         public bool ParametersFromBuiltInNamespaces
164         {
165             get
166             {
167                 bool parametersFromBuiltInNamespaces = true;
168                 for (int j = 0; j < paramGenericInfos.Count; j++)
169                 {
170                     if (parametersFromBuiltInNamespaces)
171                         parametersFromBuiltInNamespaces = DataContract.IsBuiltInNamespace(paramGenericInfos[j].GetStableNamespace());
172                     else
173                         break;
174                 }
175                 return parametersFromBuiltInNamespaces;
176             }
177         }
178 
179     }
180 
181     class RuntimeTypeHandleEqualityComparer : IEqualityComparer<RuntimeTypeHandle>
182     {
183         static RuntimeTypeHandleEqualityComparer comparer;
184 
185         static public RuntimeTypeHandleEqualityComparer Comparer
186         {
187             get
188             {
189                 if (comparer == null)
190                 {
191                     comparer = new RuntimeTypeHandleEqualityComparer();
192                 }
193 
194                 return comparer;
195             }
196         }
197 
Equals(RuntimeTypeHandle x, RuntimeTypeHandle y)198         public bool Equals(RuntimeTypeHandle x, RuntimeTypeHandle y)
199         {
200             return x.Equals(y);
201         }
202 
GetHashCode(RuntimeTypeHandle obj)203         public int GetHashCode(RuntimeTypeHandle obj)
204         {
205             return obj.GetHashCode();
206         }
207     }
208 
209     public class DataContract
210     {
211         static Dictionary<RuntimeTypeHandle, DataContract> cache = new Dictionary<RuntimeTypeHandle, DataContract>(RuntimeTypeHandleEqualityComparer.Comparer);
212         static MD5CryptoServiceProvider md5 = null;
213 
214         Type underlyingType;
215         bool isValueType;
216         XmlQualifiedName stableName;
217         protected internal bool supportCollectionDataContract;
218 
GetDataContract(Type type, bool supportCollectionDataContract)219         public static DataContract GetDataContract(Type type, bool supportCollectionDataContract)
220         {
221             return GetDataContract(type.TypeHandle, type, supportCollectionDataContract);
222         }
223 
IsBuiltInNamespace(string ns)224         internal static bool IsBuiltInNamespace(string ns)
225         {
226             return (ns == Globals.SchemaNamespace || ns == Globals.SerializationNamespace);
227         }
228 
ExpandGenericParameters(string format, IGenericNameProvider genericNameProvider)229         internal static string ExpandGenericParameters(string format, IGenericNameProvider genericNameProvider)
230         {
231             string digest = null;
232             StringBuilder typeName = new StringBuilder();
233             for (int i = 0; i < format.Length; i++)
234             {
235                 char ch = format[i];
236                 if (ch == '{')
237                 {
238                     i++;
239                     int start = i;
240                     for (; i < format.Length; i++)
241                         if (format[i] == '}')
242                             break;
243                     if (i == format.Length)
244                         throw new ArgumentException("GenericNameBraceMismatch");
245                     if (format[start] == '#' && i == (start + 1))
246                     {
247                         if (!genericNameProvider.ParametersFromBuiltInNamespaces)
248                         {
249                             if (digest == null)
250                                 digest = GetNamespacesDigest(String.Format(CultureInfo.InvariantCulture, " {0}{1}", genericNameProvider.GetParameterCount(), genericNameProvider.GetNamespaces()));
251                             typeName.Append(digest);
252                         }
253                     }
254                     else
255                     {
256                         int paramIndex;
257                         if (!Int32.TryParse(format.Substring(start, i - start), out paramIndex) || paramIndex < 0 || paramIndex >= genericNameProvider.GetParameterCount())
258                             throw new ArgumentException("GenericParameterNotValid");
259                         typeName.Append(genericNameProvider.GetParameterName(paramIndex));
260                     }
261                 }
262                 else
263                     typeName.Append(ch);
264             }
265             return typeName.ToString();
266         }
267 
GetNamespacesDigest(string namespaces)268         private static string GetNamespacesDigest(string namespaces)
269         {
270             if (md5 == null)
271                 md5 = new MD5CryptoServiceProvider();
272             byte[] namespaceBytes = Encoding.UTF8.GetBytes(namespaces);
273             byte[] digestBytes = md5.ComputeHash(namespaceBytes);
274             char[] digestChars = new char[24];
275             const int digestLen = 6;
276             int digestCharsLen = Convert.ToBase64CharArray(digestBytes, 0, digestLen, digestChars, 0);
277             StringBuilder digest = new StringBuilder();
278             for (int i = 0; i < digestCharsLen; i++)
279             {
280                 char ch = digestChars[i];
281                 switch (ch)
282                 {
283                     case '=':
284                         break;
285                     case '/':
286                         digest.Append("_S");
287                         break;
288                     case '+':
289                         digest.Append("_P");
290                         break;
291                     default:
292                         digest.Append(ch);
293                         break;
294                 }
295             }
296             return digest.ToString();
297         }
298 
BindGenericParameters(DataContract[] paramContracts, Dictionary<DataContract, DataContract> boundContracts)299         internal virtual DataContract BindGenericParameters(DataContract[] paramContracts, Dictionary<DataContract, DataContract> boundContracts)
300         {
301             return this;
302         }
303 
GetDataContract(RuntimeTypeHandle typeHandle, Type type)304         public static DataContract GetDataContract(RuntimeTypeHandle typeHandle, Type type)
305         {
306             return GetDataContract(typeHandle, type, false);
307         }
308 
GetDataContract(RuntimeTypeHandle typeHandle, Type type, bool supportCollectionDataContract)309         public static DataContract GetDataContract(RuntimeTypeHandle typeHandle, Type type, bool supportCollectionDataContract)
310         {
311             DataContract dataContract = null;
312             if (!cache.TryGetValue(typeHandle, out dataContract))
313             {
314                 lock (cache)
315                 {
316                     if (!cache.TryGetValue(typeHandle, out dataContract))
317                     {
318                         if (type == null)
319                             type = Type.GetTypeFromHandle(typeHandle);
320                         type = UnwrapNullableType(type);
321                         dataContract = CreateDataContract(type, supportCollectionDataContract);
322                         cache.Add(typeHandle, dataContract);
323                     }
324                 }
325             }
326             return dataContract;
327         }
328 
UnwrapNullableType(Type type)329         internal static Type UnwrapNullableType(Type type)
330         {
331             if (type.IsGenericType && type.GetGenericTypeDefinition() == Globals.TypeOfNullable)
332                 type = type.GetGenericArguments()[0];
333             return type;
334         }
335 
CreateDataContract(Type type, bool supportCollectionDataContract)336         public static DataContract CreateDataContract(Type type, bool supportCollectionDataContract)
337         {
338             DataContract primitiveContract = PrimitiveDataContract.GetPrimitiveDataContract(type);
339 
340             if (primitiveContract != null)
341                 return primitiveContract;
342 
343             if (type.IsArray)
344                 return new ArrayDataContract(type);
345 
346             if (type.IsEnum)
347                 return new EnumDataContract(type);
348             if (supportCollectionDataContract)
349             {
350                 DataContract collectionDataContract;
351                 Type itemType;
352                 if (CollectionDataContract.IsCollectionOrTryCreate(type, true, out collectionDataContract, out itemType, true))
353                 {
354                     return collectionDataContract;
355                 }
356             }
357             return new ClassDataContract(type);
358         }
359 
GetStableName(Type type)360         public static XmlQualifiedName GetStableName(Type type)
361         {
362             bool hasDataContract;
363             return GetStableName(type, out hasDataContract);
364         }
365 
GetStableName(Type type, bool supportCollectionDataContract)366         public static XmlQualifiedName GetStableName(Type type, bool supportCollectionDataContract)
367         {
368             bool hasDataContract;
369             return GetStableName(type, out hasDataContract, supportCollectionDataContract);
370         }
371 
GetStableName(Type type, out bool hasDataContract)372         public static XmlQualifiedName GetStableName(Type type, out bool hasDataContract)
373         {
374             return GetStableName(type, out hasDataContract, false);
375         }
376 
GetStableName(Type type, out bool hasDataContract, bool supportCollectionDataContract)377         public static XmlQualifiedName GetStableName(Type type, out bool hasDataContract, bool supportCollectionDataContract)
378         {
379             DataContract primitiveContract = PrimitiveDataContract.GetPrimitiveDataContract(type);
380             if (primitiveContract != null)
381             {
382                 hasDataContract = false;
383                 return primitiveContract.StableName;
384             }
385 
386             string name = null, ns = null;
387             if (type.IsArray)
388             {
389                 hasDataContract = false;
390                 Type elementType = type;
391                 string arrayOfPrefix = "";
392                 while (elementType.IsArray)
393                 {
394                     arrayOfPrefix += "ArrayOf";
395                     elementType = elementType.GetElementType();
396                     if (elementType == Globals.TypeOfByteArray)
397                         break;
398                 }
399                 XmlQualifiedName elementStableName = GetStableName(elementType, supportCollectionDataContract);
400                 name = arrayOfPrefix + elementStableName.Name;
401                 ns = (elementStableName.Namespace == Globals.SchemaNamespace) ? Globals.SerializationNamespace : elementStableName.Namespace;
402             }
403             else if (type.IsSerializable && !type.IsEnum)
404             {
405                 if (type.IsDefined(Globals.TypeOfDataContractAttribute, false))
406                     throw new Exception("TypeTwoWaySerializable" + type.FullName);
407                 hasDataContract = false;
408                 name = GetDefaultStableLocalName(type);
409                 ns = GetDefaultStableNamespace(type);
410             }
411             else
412             {
413                 object[] dataContractAttributes = type.GetCustomAttributes(Globals.TypeOfDataContractAttribute, false);
414                 if (dataContractAttributes != null && dataContractAttributes.Length > 0)
415                 {
416                     DataContractAttribute dataContractAttribute = (DataContractAttribute)dataContractAttributes[0];
417                     hasDataContract = true;
418                     if (dataContractAttribute.Name != null)
419                     {
420                         name = dataContractAttribute.Name;
421                         if (name.Length == 0)
422                             throw new Exception("InvalidDataContractName" + type.FullName);
423                     }
424                     else
425                         name = GetDefaultStableLocalName(type);
426 
427                     if (dataContractAttribute.Namespace != null)
428                     {
429                         ns = dataContractAttribute.Namespace;
430                     }
431                     else
432                     {
433                         string clrNs = type.Namespace;
434                         if (clrNs == null)
435                             clrNs = String.Empty;
436                         ns = GetGlobalContractNamespace(clrNs, type.Module);
437                         if (ns == null)
438                             ns = GetGlobalContractNamespace(clrNs, type.Assembly);
439 
440                         if (ns == null)
441                             ns = GetDefaultStableNamespace(type);
442                     }
443                     Uri uri;
444                     if (Uri.TryCreate(ns, UriKind.RelativeOrAbsolute, out uri))
445                     {
446                         string normalizedNs = uri.ToString();
447 
448                         if (normalizedNs == Globals.SerializationNamespace || normalizedNs == Globals.SchemaNamespace || normalizedNs == Globals.SchemaInstanceNamespace)
449                             throw new Exception("InvalidNamespace" + type.FullName + " :" + Globals.SerializationNamespace + " :" + Globals.SchemaNamespace + " :" + Globals.SchemaInstanceNamespace);
450                     }
451                 }
452                 else if (type.IsEnum)
453                 {
454                     hasDataContract = false;
455                     name = GetDefaultStableLocalName(type);
456                     ns = GetDefaultStableNamespace(type);
457                 }
458                 else if (type.GetInterface("System.Xml.Serialization.IXmlSerializable") != null)
459                 {
460                     hasDataContract = false;
461                     name = GetDefaultStableLocalName(type);
462                     ns = GetDefaultStableNamespace(type);
463                 }
464                 else
465                 {
466                     object[] collectionDataContractAttributes = type.GetCustomAttributes(Globals.TypeOfCollectionDataContractAttribute, false);
467                     if (supportCollectionDataContract && collectionDataContractAttributes != null && collectionDataContractAttributes.Length > 0)
468                     {
469                         CollectionDataContractAttribute collectionDataContractAttribute = (CollectionDataContractAttribute)collectionDataContractAttributes[0];
470                         hasDataContract = true;
471                         if (collectionDataContractAttribute.Name != null)
472                         {
473                             name = collectionDataContractAttribute.Name;
474                             if (name.Length == 0)
475                                 throw new Exception("InvalidDataContractName" + type.FullName);
476                         }
477                         else
478                             name = GetDefaultStableLocalName(type);
479 
480                         if (collectionDataContractAttribute.Namespace != null)
481                         {
482                             ns = collectionDataContractAttribute.Namespace;
483                         }
484                         else
485                         {
486                             string clrNs = type.Namespace;
487                             if (clrNs == null)
488                                 clrNs = String.Empty;
489                             ns = GetGlobalContractNamespace(clrNs, type.Module);
490                             if (ns == null)
491                                 ns = GetGlobalContractNamespace(clrNs, type.Assembly);
492 
493                             if (ns == null)
494                                 ns = GetDefaultStableNamespace(type);
495                         }
496                         Uri uri;
497                         if (Uri.TryCreate(ns, UriKind.RelativeOrAbsolute, out uri))
498                         {
499                             string normalizedNs = uri.ToString();
500 
501                             if (normalizedNs == Globals.SerializationNamespace || normalizedNs == Globals.SchemaNamespace || normalizedNs == Globals.SchemaInstanceNamespace)
502                                 throw new Exception("InvalidNamespace" + type.FullName + " :" + Globals.SerializationNamespace + " :" + Globals.SchemaNamespace + " :" + Globals.SchemaInstanceNamespace);
503                         }
504                     }
505                     else
506                     {
507                         hasDataContract = false;
508                         name = GetDefaultStableLocalName(type);
509                         ns = GetDefaultStableNamespace(type);
510                     }
511                 }
512             }
513             return new XmlQualifiedName(name, ns);
514         }
515 
GetDefaultStableLocalName(Type type)516         static string GetDefaultStableLocalName(Type type)
517         {
518             if (type.DeclaringType == null)
519                 return type.Name;
520             int nsLen = (type.Namespace == null) ? 0 : type.Namespace.Length;
521             if (nsLen > 0)
522                 nsLen++;
523             return type.FullName.Substring(nsLen).Replace('+', '.');
524         }
525 
GetDefaultStableNamespace(Type type)526         static string GetDefaultStableNamespace(Type type)
527         {
528             return GetDefaultStableNamespace(type.Namespace);
529         }
530 
GetDefaultStableNamespace(string clrNs)531         public static string GetDefaultStableNamespace(string clrNs)
532         {
533             if (clrNs == null) clrNs = String.Empty;
534             return Globals.DefaultNamespace + clrNs.Replace('.', '/');
535         }
536 
GetGlobalContractNamespace(string clrNs, ICustomAttributeProvider customAttribuetProvider)537         static string GetGlobalContractNamespace(string clrNs, ICustomAttributeProvider customAttribuetProvider)
538         {
539             object[] nsAttributes = customAttribuetProvider.GetCustomAttributes(typeof(ContractNamespaceAttribute), false);
540             string dataContractNs = null;
541             for (int i = 0; i < nsAttributes.Length; i++)
542             {
543                 ContractNamespaceAttribute nsAttribute = (ContractNamespaceAttribute)nsAttributes[i];
544                 string clrNsInAttribute = nsAttribute.ClrNamespace;
545                 if (clrNsInAttribute == null)
546                     clrNsInAttribute = String.Empty;
547                 if (clrNsInAttribute == clrNs)
548                 {
549                     if (nsAttribute.ContractNamespace == null)
550                         throw new Exception("InvalidGlobalContractNamespace:" + clrNs);
551                     if (dataContractNs != null)
552                         throw new Exception("ContractNamespaceAlreadySet:" + dataContractNs + " :: " + nsAttribute.ContractNamespace + " :: " + clrNs);
553                     dataContractNs = nsAttribute.ContractNamespace;
554                 }
555             }
556             return dataContractNs;
557         }
558 
GetIsReferenceValue()559         bool GetIsReferenceValue()
560         {
561             Type type = this.UnderlyingType;
562             {
563                 object[] dataContractAttributes = type.GetCustomAttributes(Globals.TypeOfDataContractAttribute, false);
564                 object[] serAttributes = type.GetCustomAttributes(Globals.TypeOfSerializableAttribute, false);
565 
566                 if (dataContractAttributes != null && dataContractAttributes.Length > 0)
567                 {
568                     DataContractAttribute dataContractAttribute = (DataContractAttribute)dataContractAttributes[0];
569                     if (!dataContractAttribute.IsReference && this is ClassDataContract && ((ClassDataContract)this).BaseContract != null)
570                     {
571                         return ((ClassDataContract)this).BaseContract.IsReference;
572                     }
573                     else
574                     {
575                         return dataContractAttribute.IsReference;
576                     }
577                 }
578                 else if (serAttributes != null && serAttributes.Length > 0)
579                 {
580                     if (this is ClassDataContract && ((ClassDataContract)this).BaseContract != null)
581                     {
582                         return ((ClassDataContract)this).BaseContract.IsReference;
583                     }
584                     else
585                     {
586                         return false;
587                     }
588                 }
589             }
590             {
591                 object[] collectionDataContractAttributes = type.GetCustomAttributes(Globals.TypeOfCollectionDataContractAttribute, false);
592                 if (collectionDataContractAttributes != null && collectionDataContractAttributes.Length > 0)
593                 {
594                     CollectionDataContractAttribute collectionDataContractAttribute = (CollectionDataContractAttribute)collectionDataContractAttributes[0];
595                     return collectionDataContractAttribute.IsReference;
596                 }
597             }
598             return false;
599         }
600 
DataContract()601         public DataContract()
602         {
603         }
604 
DataContract(bool supportCollectionDataContract)605         public DataContract(bool supportCollectionDataContract)
606         {
607             this.supportCollectionDataContract = supportCollectionDataContract;
608         }
609 
DataContract(Type type)610         public DataContract(Type type)
611         {
612             underlyingType = type;
613             isValueType = type.IsValueType;
614         }
615 
DataContract(Type type, bool supportCollectionDataContract)616         public DataContract(Type type, bool supportCollectionDataContract)
617             : this(type)
618         {
619             this.supportCollectionDataContract = supportCollectionDataContract;
620         }
621 
622         public Type UnderlyingType
623         {
624             get { return underlyingType; }
625         }
626 
627         public virtual string TopLevelElementName
628         {
629             get { return StableName.Name; }
630         }
631 
632         public virtual string TopLevelElementNamespace
633         {
634             get { return StableName.Namespace; }
635         }
636 
637         public bool IsValueType
638         {
639             get { return isValueType; }
640             set { isValueType = value; }
641         }
642 
643         public XmlQualifiedName StableName
644         {
645             get { return stableName; }
646             set { stableName = value; }
647         }
648 
649         public virtual bool IsISerializable
650         {
651             get { return false; }
652             set { throw new InvalidOperationException("RequiresClassDataContractToSetIsISerializable"); }
653         }
654 
655         public bool IsReference
656         {
657             get { return GetIsReferenceValue(); }
658         }
659 
IsAlpha(char ch)660         static bool IsAlpha(char ch)
661         {
662             return (ch >= 'A' && ch <= 'Z' || ch >= 'a' && ch <= 'z');
663         }
664 
IsDigit(char ch)665         static bool IsDigit(char ch)
666         {
667             return (ch >= '0' && ch <= '9');
668         }
669 
IsAsciiLocalName(string localName)670         static bool IsAsciiLocalName(string localName)
671         {
672             if (String.IsNullOrEmpty(localName) || localName.Length == 0)
673                 return false;
674             if (!IsAlpha(localName[0]))
675                 return false;
676             for (int i = 1; i < localName.Length; i++)
677             {
678                 char ch = localName[i];
679                 if (!IsAlpha(ch) && !IsDigit(ch))
680                     return false;
681             }
682             return true;
683         }
684 
EncodeLocalName(string localName)685         static internal string EncodeLocalName(string localName)
686         {
687             if (IsAsciiLocalName(localName))
688                 return localName;
689 
690             if (IsValidNCName(localName))
691                 return localName;
692 
693             return XmlConvert.EncodeLocalName(localName);
694         }
695 
IsValidNCName(string name)696         internal static bool IsValidNCName(string name)
697         {
698             try
699             {
700                 XmlConvert.VerifyNCName(name);
701                 return true;
702             }
703             catch (XmlException)
704             {
705                 return false;
706             }
707         }
708 
Equals(object other)709         public override bool Equals(object other)
710         {
711             if ((object)this == other)
712                 return true;
713             DataContract dataContract = other as DataContract;
714             if (dataContract != null)
715             {
716                 return (StableName.Name == dataContract.StableName.Name && StableName.Namespace == dataContract.StableName.Namespace && IsValueType == dataContract.IsValueType && IsReference == dataContract.IsReference);
717             }
718             return false;
719         }
720 
GetHashCode()721         public override int GetHashCode()
722         {
723             return base.GetHashCode();
724         }
725     }
726 
727     public class ClassDataContract : DataContract
728     {
729         ClassDataContract baseContract;
730         List<DataMember> members;
731         string[][] memberNames;
732         bool isISerializable;
733         bool hasDataContract;
734 
ClassDataContract(Type type)735         public ClassDataContract(Type type)
736             : this(type, false)
737         {
738         }
739 
ClassDataContract(Type type, bool supportCollectionDataContract)740         public ClassDataContract(Type type, bool supportCollectionDataContract)
741             : base(type, supportCollectionDataContract)
742         {
743             Init(type);
744         }
745 
746 
Init(Type type)747         void Init(Type type)
748         {
749             this.StableName = DataContract.GetStableName(type, out hasDataContract, supportCollectionDataContract);
750             Type baseType = type.BaseType;
751             isISerializable = (Globals.TypeOfISerializable.IsAssignableFrom(type));
752             if (isISerializable)
753             {
754                 if (hasDataContract)
755                     throw new Exception("DataContractTypeCannotBeISerializable: " + type.FullName);
756                 if (!Globals.TypeOfISerializable.IsAssignableFrom(baseType))
757                 {
758                     while (baseType != null)
759                     {
760                         if (baseType.IsDefined(Globals.TypeOfDataContractAttribute, false))
761                             throw new Exception("ISerializableCannotInheritFromDataContract:" + type.FullName + "::" + baseType.FullName);
762                         baseType = baseType.BaseType;
763                     }
764                 }
765             }
766             if (baseType != null && baseType != Globals.TypeOfObject && baseType != Globals.TypeOfValueType)
767                 this.BaseContract = (ClassDataContract)DataContract.GetDataContract(baseType, supportCollectionDataContract);
768             else
769                 this.BaseContract = null;
770         }
771 
ImportDataMembers()772         void ImportDataMembers()
773         {
774             Type type = this.UnderlyingType;
775             members = new List<DataMember>();
776             Dictionary<string, DataMember> memberNamesTable = new Dictionary<string, DataMember>();
777             MemberInfo[] memberInfos = type.GetMembers(BindingFlags.DeclaredOnly | BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic);
778 
779             for (int i = 0; i < memberInfos.Length; i++)
780             {
781                 MemberInfo member = memberInfos[i];
782                 if (hasDataContract)
783                 {
784                     object[] memberAttributes = member.GetCustomAttributes(typeof(System.Runtime.Serialization.DataMemberAttribute), false);
785                     if (memberAttributes != null && memberAttributes.Length > 0)
786                     {
787                         if (memberAttributes.Length > 1)
788                             throw new Exception("TooManyDataMembers:" + member.DeclaringType.FullName + "::" + member.Name);
789                         if (member.MemberType == MemberTypes.Property)
790                         {
791                             PropertyInfo property = (PropertyInfo)member;
792                             MethodInfo getMethod = property.GetGetMethod(true);
793                             if (getMethod != null && IsMethodOverriding(getMethod))
794                                 continue;
795                             MethodInfo setMethod = property.GetSetMethod(true);
796                             if (setMethod != null && IsMethodOverriding(setMethod))
797                                 continue;
798                             if (getMethod == null)
799                                 throw new Exception(" NoGetMethodForProperty : " + property.DeclaringType + " ::" + property.Name);
800                             if (setMethod == null)
801                                 throw new Exception("NoSetMethodForProperty : " + property.DeclaringType + " :: " + property.Name);
802                             if (getMethod.GetParameters().Length > 0)
803                                 throw new Exception("IndexedPropertyCannotBeSerialized :" + property.DeclaringType + " :: " + property.Name);
804                         }
805                         else if (member.MemberType != MemberTypes.Field)
806                             throw new Exception("InvalidMember : " + type.FullName + " :: " + member.Name + " :: " + typeof(System.Runtime.Serialization.DataMemberAttribute).FullName);
807 
808                         DataMember memberContract = new DataMember(member);
809                         System.Runtime.Serialization.DataMemberAttribute memberAttribute = (System.Runtime.Serialization.DataMemberAttribute)memberAttributes[0];
810                         if (memberAttribute.Name == null)
811                             memberContract.Name = member.Name;
812                         else
813                             memberContract.Name = memberAttribute.Name;
814                         memberContract.Order = memberAttribute.Order;
815                         memberContract.IsRequired = memberAttribute.IsRequired;
816                         CheckAndAddMember(members, memberContract, memberNamesTable);
817                     }
818                 }
819                 else
820                 {
821                     FieldInfo field = member as FieldInfo;
822                     if (field != null && !field.IsNotSerialized)
823                     {
824                         DataMember memberContract = new DataMember(member);
825                         memberContract.Name = member.Name;
826                         object[] optionalFields = field.GetCustomAttributes(Globals.TypeOfOptionalFieldAttribute, false);
827                         if (optionalFields == null || optionalFields.Length == 0)
828                             memberContract.Order = Globals.DefaultVersion;
829                         else
830                         {
831                             memberContract.IsRequired = Globals.DefaultIsRequired;
832                         }
833                         CheckAndAddMember(members, memberContract, memberNamesTable);
834                     }
835                 }
836             }
837             if (members.Count > 1)
838                 members.Sort(DataMemberComparer.Singleton);
839         }
840 
CheckAndAddMember(List<DataMember> members, DataMember memberContract, Dictionary<string, DataMember> memberNamesTable)841         public static void CheckAndAddMember(List<DataMember> members, DataMember memberContract, Dictionary<string, DataMember> memberNamesTable)
842         {
843             DataMember existingMemberContract;
844             if (memberNamesTable.TryGetValue(memberContract.Name, out existingMemberContract))
845                 throw new Exception("DupMemberName :" + existingMemberContract.MemberInfo.Name + " :: " + memberContract.MemberInfo.Name + " :: " + memberContract.MemberInfo.DeclaringType.FullName + " :: " + memberContract.Name);
846             memberNamesTable.Add(memberContract.Name, memberContract);
847             members.Add(memberContract);
848         }
849 
IsMethodOverriding(MethodInfo method)850         static bool IsMethodOverriding(MethodInfo method)
851         {
852             return method.IsVirtual && ((method.Attributes & MethodAttributes.NewSlot) == 0);
853         }
854 
855         public ClassDataContract BaseContract
856         {
857             get { return baseContract; }
858             set { baseContract = value; }
859         }
860 
861         public string[][] MemberNames
862         {
863             get
864             {
865                 if (memberNames == null)
866                 {
867                     lock (this)
868                     {
869                         if (memberNames == null && Members != null)
870                         {
871                             if (baseContract == null)
872                                 memberNames = new string[1][];
873                             else
874                             {
875                                 int baseTypesCount = baseContract.MemberNames.Length;
876                                 memberNames = new string[baseTypesCount + 1][];
877                                 Array.Copy(baseContract.MemberNames, 0, memberNames, 0, baseTypesCount);
878                             }
879                             string[] declaredMemberNames = new string[Members.Count];
880                             for (int i = 0; i < Members.Count; i++)
881                                 declaredMemberNames[i] = Members[i].Name;
882                             memberNames[memberNames.Length - 1] = declaredMemberNames;
883                         }
884                     }
885                 }
886                 return memberNames;
887             }
888         }
889 
890         public List<DataMember> Members
891         {
892             get
893             {
894                 if (members == null && UnderlyingType != null && !IsISerializable)
895                 {
896                     lock (this)
897                     {
898                         if (members == null)
899                         {
900                             ImportDataMembers();
901                         }
902                     }
903                 }
904                 return members;
905             }
906             set { members = value; }
907         }
908 
Equals(object other)909         public override bool Equals(object other)
910         {
911             if ((object)this == other)
912                 return true;
913 
914             if (base.Equals(other))
915             {
916                 ClassDataContract dataContract = other as ClassDataContract;
917                 if (dataContract != null)
918                 {
919                     if (IsISerializable)
920                     {
921                         if (!dataContract.IsISerializable)
922                             return false;
923                     }
924                     else
925                     {
926                         if (dataContract.IsISerializable)
927                             return false;
928 
929                         if (Members == null)
930                         {
931                             if (dataContract.Members != null)
932                                 return false;
933                         }
934                         else if (dataContract.Members == null)
935                             return false;
936                         else
937                         {
938                             if (Members.Count != dataContract.Members.Count)
939                                 return false;
940 
941                             for (int i = 0; i < Members.Count; i++)
942                             {
943                                 if (!Members[i].Equals(dataContract.Members[i]))
944                                     return false;
945                             }
946                         }
947                     }
948 
949                     if (BaseContract == null)
950                         return (dataContract.BaseContract == null);
951                     else if (dataContract.BaseContract == null)
952                         return false;
953                     else
954                         return BaseContract.StableName.Equals(dataContract.BaseContract.StableName);
955                 }
956             }
957             return false;
958         }
959 
GetHashCode()960         public override int GetHashCode()
961         {
962             return base.GetHashCode();
963         }
964 
965         public class DataMemberComparer : IComparer<DataMember>
966         {
Compare(DataMember x, DataMember y)967             public int Compare(DataMember x, DataMember y)
968             {
969                 if (x.Order < y.Order)
970                     return -1;
971                 if (x.Order > y.Order)
972                     return 1;
973                 return String.Compare(x.Name, y.Name, StringComparison.InvariantCulture);
974             }
975 
Equals(DataMember x, DataMember y)976             public bool Equals(DataMember x, DataMember y)
977             {
978                 return x == y;
979             }
980 
GetHashCode(DataMember x)981             public int GetHashCode(DataMember x)
982             {
983                 return ((object)x).GetHashCode();
984             }
985             public static DataMemberComparer Singleton = new DataMemberComparer();
986         }
987 
988         public class DataMemberOrderComparer : IComparer<DataMember>
989         {
Compare(DataMember x, DataMember y)990             public int Compare(DataMember x, DataMember y)
991             {
992                 return x.Order - y.Order;
993             }
994 
Equals(DataMember x, DataMember y)995             public bool Equals(DataMember x, DataMember y)
996             {
997                 return x.Order == y.Order;
998             }
999 
GetHashCode(DataMember x)1000             public int GetHashCode(DataMember x)
1001             {
1002                 return ((object)x).GetHashCode();
1003             }
1004             public static DataMemberOrderComparer Singleton = new DataMemberOrderComparer();
1005         }
1006 
1007     }
1008 
1009     public class DataMember
1010     {
1011         DataContract memberTypeContract;
1012         string name;
1013         int order;
1014         bool isRequired;
1015         bool isNullable;
1016         MemberInfo memberInfo;
1017         protected internal bool supportCollectionDataContract;
1018 
DataMember()1019         public DataMember()
1020         {
1021         }
1022 
DataMember(MemberInfo memberInfo)1023         public DataMember(MemberInfo memberInfo)
1024         {
1025             this.memberInfo = memberInfo;
1026         }
1027 
1028         public MemberInfo MemberInfo
1029         {
1030             get { return memberInfo; }
1031         }
1032 
1033         public string Name
1034         {
1035             get { return name; }
1036             set { name = value; }
1037         }
1038 
1039         public int Order
1040         {
1041             get { return order; }
1042             set { order = value; }
1043         }
1044 
1045         internal bool IsNullable
1046         {
1047             get { return isNullable; }
1048             set { isNullable = value; }
1049         }
1050 
1051         public bool IsRequired
1052         {
1053             get { return isRequired; }
1054             set { isRequired = value; }
1055         }
1056 
GetMemberValue(object obj)1057         public object GetMemberValue(object obj)
1058         {
1059             FieldInfo field = MemberInfo as FieldInfo;
1060 
1061             if (field != null)
1062                 return ((FieldInfo)MemberInfo).GetValue(obj);
1063 
1064             return ((PropertyInfo)MemberInfo).GetValue(obj, null);
1065         }
1066 
1067         public Type MemberType
1068         {
1069             get
1070             {
1071                 FieldInfo field = MemberInfo as FieldInfo;
1072                 if (field != null)
1073                     return field.FieldType;
1074                 return ((PropertyInfo)MemberInfo).PropertyType;
1075             }
1076         }
1077 
1078         public DataContract MemberTypeContract
1079         {
1080             get
1081             {
1082                 if (memberTypeContract == null)
1083                 {
1084                     if (MemberInfo != null)
1085                     {
1086                         lock (this)
1087                         {
1088                             if (memberTypeContract == null)
1089                             {
1090                                 memberTypeContract = DataContract.GetDataContract(MemberType, supportCollectionDataContract);
1091                             }
1092                         }
1093                     }
1094                 }
1095                 return memberTypeContract;
1096             }
1097             set
1098             {
1099                 memberTypeContract = value;
1100             }
1101         }
1102 
Equals(object other)1103         public override bool Equals(object other)
1104         {
1105             if ((object)this == other)
1106                 return true;
1107 
1108             DataMember dataMember = other as DataMember;
1109             if (dataMember != null)
1110             {
1111                 return (Name == dataMember.Name
1112                         && IsNullable == dataMember.IsNullable
1113                         && IsRequired == dataMember.IsRequired
1114                         && MemberTypeContract.StableName.Equals(dataMember.MemberTypeContract.StableName));
1115             }
1116             return false;
1117         }
1118 
operator <(DataMember dm1, DataMember dm2)1119         public static bool operator <(DataMember dm1, DataMember dm2)
1120         {
1121             if (dm1.Order != dm2.Order)
1122                 return dm1.Order < dm2.Order;
1123             else
1124                 return ((string.Compare(dm1.Name, dm2.Name) < 0) ? true : false);
1125         }
1126 
operator >(DataMember dm1, DataMember dm2)1127         public static bool operator >(DataMember dm1, DataMember dm2)
1128         {
1129             if (dm1.Order != dm2.Order)
1130                 return dm1.Order > dm2.Order;
1131             else
1132                 return ((string.Compare(dm1.Name, dm2.Name) > 0) ? true : false);
1133         }
1134 
NameOrderEquals(object other)1135         public bool NameOrderEquals(object other)
1136         {
1137             if ((object)this == other)
1138                 return true;
1139             DataMember dataMember = other as DataMember;
1140             if (dataMember != null)
1141             {
1142                 return (Name == dataMember.Name
1143                         && Order == dataMember.Order
1144                         && MemberTypeContract.StableName.Equals(dataMember.MemberTypeContract.StableName));
1145             }
1146             return false;
1147 
1148         }
1149 
GetHashCode()1150         public override int GetHashCode()
1151         {
1152             return base.GetHashCode();
1153         }
1154     }
1155 
1156     public class PrimitiveDataContract : DataContract
1157     {
1158         static Dictionary<Type, PrimitiveDataContract> typeToContract = new Dictionary<Type, PrimitiveDataContract>();
1159         static Dictionary<XmlQualifiedName, PrimitiveDataContract> nameToContract = new Dictionary<XmlQualifiedName, PrimitiveDataContract>();
1160         static PrimitiveDataContract objectContract = new PrimitiveDataContract(typeof(object));
1161 
PrimitiveDataContract()1162         static PrimitiveDataContract()
1163         {
1164             Add(new PrimitiveDataContract(typeof(char)));
1165             Add(new PrimitiveDataContract(typeof(bool)));
1166             Add(new PrimitiveDataContract(typeof(sbyte)));
1167             Add(new PrimitiveDataContract(typeof(byte)));
1168             Add(new PrimitiveDataContract(typeof(short)));
1169             Add(new PrimitiveDataContract(typeof(ushort)));
1170             Add(new PrimitiveDataContract(typeof(int)));
1171             Add(new PrimitiveDataContract(typeof(uint)));
1172             Add(new PrimitiveDataContract(typeof(long)));
1173             Add(new PrimitiveDataContract(typeof(ulong)));
1174             Add(new PrimitiveDataContract(typeof(float)));
1175             Add(new PrimitiveDataContract(typeof(double)));
1176             Add(new PrimitiveDataContract(typeof(decimal)));
1177             Add(new PrimitiveDataContract(typeof(DateTime)));
1178             Add(new PrimitiveDataContract(typeof(string)));
1179             Add(new PrimitiveDataContract(typeof(byte[])));
1180             Add(new PrimitiveDataContract(typeof(TimeSpan)));
1181             Add(new PrimitiveDataContract(typeof(Guid)));
1182             Add(new PrimitiveDataContract(typeof(Uri)));
1183             Add(objectContract);
1184         }
Add(PrimitiveDataContract primitiveContract)1185         static public void Add(PrimitiveDataContract primitiveContract)
1186         {
1187             typeToContract.Add(primitiveContract.UnderlyingType, primitiveContract);
1188             nameToContract.Add(primitiveContract.StableName, primitiveContract);
1189         }
1190 
GetPrimitiveDataContract(Type type)1191         static public PrimitiveDataContract GetPrimitiveDataContract(Type type)
1192         {
1193             PrimitiveDataContract retVal = null;
1194             if (type.IsInterface)
1195                 retVal = objectContract;
1196             else
1197                 typeToContract.TryGetValue(type, out retVal);
1198             return retVal;
1199         }
1200 
GetPrimitiveDataContract(string name, string ns)1201         static public PrimitiveDataContract GetPrimitiveDataContract(string name, string ns)
1202         {
1203             PrimitiveDataContract retVal = null;
1204             nameToContract.TryGetValue(new XmlQualifiedName(name, ns), out retVal);
1205             return retVal;
1206         }
1207 
PrimitiveDataContract(Type type)1208         PrimitiveDataContract(Type type) : base(type)
1209         {
1210             string name = null;
1211             string ns = Globals.SchemaNamespace;
1212             switch (Type.GetTypeCode(type))
1213             {
1214                 case TypeCode.Char:
1215                     name = "char";
1216                     ns = Globals.SerializationNamespace;
1217                     break;
1218                 case TypeCode.Boolean:
1219                     name = "boolean";
1220                     break;
1221                 case TypeCode.SByte:
1222                     name = "byte";
1223                     break;
1224                 case TypeCode.Byte:
1225                     name = "unsignedByte";
1226                     break;
1227                 case TypeCode.Int16:
1228                     name = "short";
1229                     break;
1230                 case TypeCode.UInt16:
1231                     name = "unsignedShort";
1232                     break;
1233                 case TypeCode.Int32:
1234                     name = "int";
1235                     break;
1236                 case TypeCode.UInt32:
1237                     name = "unsignedInt";
1238                     break;
1239                 case TypeCode.Int64:
1240                     name = "long";
1241                     break;
1242                 case TypeCode.UInt64:
1243                     name = "unsignedLong";
1244                     break;
1245                 case TypeCode.Single:
1246                     name = "float";
1247                     break;
1248                 case TypeCode.Double:
1249                     name = "double";
1250                     break;
1251                 case TypeCode.Decimal:
1252                     name = "decimal";
1253                     break;
1254                 case TypeCode.DateTime:
1255                     name = "dateTime";
1256                     break;
1257                 case TypeCode.String:
1258                     name = "string";
1259                     break;
1260                 default:
1261                     if (type == Globals.TypeOfByteArray)
1262                     {
1263                         name = "base64Binary";
1264                         ns = Globals.SerializationNamespace;
1265                     }
1266                     else if (type == Globals.TypeOfObject)
1267                     {
1268                         name = "anyType";
1269                     }
1270                     else if (type == Globals.TypeOfTimeSpan)
1271                     {
1272                         name = "duration";
1273                     }
1274                     else if (type == Globals.TypeOfGuid)
1275                     {
1276                         name = "guid";
1277                     }
1278                     else if (type == Globals.TypeOfUri)
1279                     {
1280                         name = "anyURI";
1281                     }
1282                     else
1283                         throw new Exception(string.Format("{0} is an invalidPrimitiveType", type.FullName));
1284                     break;
1285             }
1286             StableName = new XmlQualifiedName(name, ns);
1287         }
1288 
1289         public override string TopLevelElementNamespace
1290         {
1291             get { return Globals.SerializationNamespace; }
1292         }
1293     }
1294 
1295     public class ArrayDataContract : DataContract
1296     {
1297         DataContract itemContract;
1298         int rank;
1299 
ArrayDataContract(Type type, bool supportCollectionDataContract)1300         public ArrayDataContract(Type type, bool supportCollectionDataContract)
1301             : base(type, supportCollectionDataContract)
1302         {
1303             rank = type.GetArrayRank();
1304             StableName = DataContract.GetStableName(type, supportCollectionDataContract);
1305         }
1306 
ArrayDataContract(Type type)1307         public ArrayDataContract(Type type)
1308             : this(type, false)
1309         {
1310         }
1311 
1312         public DataContract ItemContract
1313         {
1314             get
1315             {
1316                 if (itemContract == null && UnderlyingType != null)
1317                 {
1318                     itemContract = DataContract.GetDataContract(UnderlyingType.GetElementType(), supportCollectionDataContract);
1319                 }
1320                 return itemContract;
1321             }
1322             set
1323             {
1324                 itemContract = value;
1325             }
1326         }
1327 
Equals(object other)1328         public override bool Equals(object other)
1329         {
1330             if ((object)this == other)
1331                 return true;
1332 
1333             if (base.Equals(other))
1334             {
1335                 ArrayDataContract dataContract = other as ArrayDataContract;
1336                 if (dataContract != null)
1337                 {
1338                     return ItemContract.Equals(dataContract.itemContract);
1339                 }
1340             }
1341             return false;
1342         }
1343 
GetHashCode()1344         public override int GetHashCode()
1345         {
1346             return base.GetHashCode();
1347         }
1348     }
1349 
1350     public class EnumDataContract : DataContract
1351     {
1352         PrimitiveDataContract baseContract;
1353         List<DataMember> members;
1354         List<long> values;
1355         bool isULong;
1356         bool isFlags;
1357         bool hasDataContract;
1358 
EnumDataContract()1359         public EnumDataContract()
1360         {
1361             IsValueType = true;
1362         }
1363 
EnumDataContract(Type type)1364         public EnumDataContract(Type type) : base(type)
1365         {
1366             StableName = DataContract.GetStableName(type, out hasDataContract);
1367             Type baseType = Enum.GetUnderlyingType(type);
1368             baseContract = PrimitiveDataContract.GetPrimitiveDataContract(baseType);
1369             isULong = (baseType == Globals.TypeOfULong);
1370             IsFlags = type.IsDefined(Globals.TypeOfFlagsAttribute, false);
1371         }
1372 
1373         public PrimitiveDataContract BaseContract
1374         {
1375             get
1376             {
1377                 return baseContract;
1378             }
1379             set
1380             {
1381                 baseContract = value;
1382                 isULong = (baseContract.UnderlyingType == Globals.TypeOfULong);
1383             }
1384         }
1385 
ImportDataMembers()1386         void ImportDataMembers()
1387         {
1388             Type type = this.UnderlyingType;
1389             FieldInfo[] fields = type.GetFields(BindingFlags.Static | BindingFlags.Public);
1390             members = new List<DataMember>(fields.Length);
1391             Dictionary<string, DataMember> memberNamesTable = new Dictionary<string, DataMember>();
1392             values = new List<long>(fields.Length);
1393 
1394             for (int i = 0; i < fields.Length; i++)
1395             {
1396                 FieldInfo field = fields[i];
1397                 bool dataMemberValid = false;
1398                 object[] memberAttributes = field.GetCustomAttributes(Globals.TypeOfDataMemberAttribute, false);
1399                 if (hasDataContract)
1400                 {
1401                     if (memberAttributes != null && memberAttributes.Length > 0)
1402                     {
1403                         if (memberAttributes.Length > 1)
1404                             throw new Exception("TooManyDataMembers :" + field.DeclaringType.FullName + " :: " + field.Name);
1405                         DataMemberAttribute memberAttribute = (DataMemberAttribute)memberAttributes[0];
1406                         DataMember memberContract = new DataMember(field);
1407                         if (memberAttribute.Name == null || memberAttribute.Name.Length == 0)
1408                             memberContract.Name = field.Name;
1409                         else
1410                             memberContract.Name = memberAttribute.Name;
1411                         ClassDataContract.CheckAndAddMember(members, memberContract, memberNamesTable);
1412                         dataMemberValid = true;
1413                     }
1414                 }
1415                 else
1416                 {
1417                     if (!field.IsNotSerialized)
1418                     {
1419                         DataMember memberContract = new DataMember(field);
1420                         memberContract.Name = field.Name;
1421                         ClassDataContract.CheckAndAddMember(members, memberContract, memberNamesTable);
1422                         dataMemberValid = true;
1423                     }
1424                 }
1425 
1426                 if (dataMemberValid)
1427                 {
1428                     object enumValue = field.GetValue(null);
1429                     if (isULong)
1430                         values.Add((long)((IConvertible)enumValue).ToUInt64(null));
1431                     else
1432                         values.Add(((IConvertible)enumValue).ToInt64(null));
1433                 }
1434             }
1435         }
1436 
1437         public List<DataMember> Members
1438         {
1439             get
1440             {
1441                 if (members == null && UnderlyingType != null)
1442                 {
1443                     lock (this)
1444                     {
1445                         if (members == null)
1446                         {
1447                             ImportDataMembers();
1448                         }
1449                     }
1450                 }
1451                 return members;
1452             }
1453             set { members = value; }
1454         }
1455 
1456         public List<long> Values
1457         {
1458             get
1459             {
1460                 if (values == null && UnderlyingType != null)
1461                 {
1462                     lock (this)
1463                     {
1464                         if (values == null)
1465                         {
1466                             ImportDataMembers();
1467                         }
1468                     }
1469                 }
1470                 return values;
1471             }
1472             set { values = value; }
1473         }
1474 
1475         public bool IsFlags
1476         {
1477             get { return isFlags; }
1478             set { isFlags = value; }
1479         }
1480 
Equals(object other)1481         public override bool Equals(object other)
1482         {
1483             if ((object)this == other)
1484                 return true;
1485 
1486             if (base.Equals(other))
1487             {
1488                 EnumDataContract dataContract = other as EnumDataContract;
1489                 if (dataContract != null)
1490                 {
1491                     if (IsFlags != dataContract.IsFlags)
1492                         return false;
1493 
1494                     if (Members.Count != dataContract.Members.Count || Values.Count != dataContract.Values.Count)
1495                         return false;
1496 
1497                     for (int i = 0; i < Members.Count; i++)
1498                     {
1499                         if (Values[i] != dataContract.Values[i] || Members[i].Name != dataContract.Members[i].Name)
1500                             return false;
1501                     }
1502 
1503                     return BaseContract.StableName.Equals(dataContract.BaseContract.StableName);
1504                 }
1505             }
1506             return false;
1507         }
GetHashCode()1508         public override int GetHashCode()
1509         {
1510             if (members != null)
1511             {
1512                 int hash = 0;
1513                 foreach (DataMember member in members)
1514                     hash += member.Name.GetHashCode();
1515                 hash += base.StableName.GetHashCode();
1516                 return hash;
1517             }
1518             else
1519             {
1520                 return base.GetHashCode();
1521             }
1522         }
1523     }
1524 
1525     public enum CollectionKind : byte
1526     {
1527         None,
1528         GenericDictionary,
1529         Dictionary,
1530         GenericList,
1531         GenericCollection,
1532         List,
1533         GenericEnumerable,
1534         Collection,
1535         Enumerable,
1536         Array,
1537     }
1538 
1539     [DataContractAttribute(Namespace = "http://schemas.microsoft.com/2003/10/Serialization/Arrays")]
1540     public struct KeyValue<K, V>
1541     {
1542         K key;
1543         V value;
1544 
KeyValueSerializationTestTypes.KeyValue1545         internal KeyValue(K key, V value)
1546         {
1547             this.key = key;
1548             this.value = value;
1549         }
1550 
1551         [DataMember(IsRequired = true)]
1552         public K Key
1553         {
1554             get { return key; }
1555             set { key = value; }
1556         }
1557 
1558         [DataMember(IsRequired = true)]
1559         public V Value
1560         {
1561             get { return value; }
1562             set { this.value = value; }
1563         }
1564     }
1565 
1566     public class CollectionDataContract : DataContract
1567     {
1568         public CollectionKind Kind;
1569         public Type ItemType;
1570         public string ItemName;
1571         public String CollectionItemName;
1572         public string KeyName;
1573         public string ValueName;
1574 
1575         public bool IsDictionary
1576         {
1577             get { return !String.IsNullOrEmpty(KeyName); }
1578         }
1579 
1580         public MethodInfo GetEnumeratorMethod;
1581         public MethodInfo AddMethod;
1582         public ConstructorInfo Constructor;
1583 
CollectionDataContract(Type type, CollectionKind kind, Type itemType, MethodInfo getEnumeratorMethod, MethodInfo addMethod, ConstructorInfo constructor)1584         public CollectionDataContract(Type type, CollectionKind kind, Type itemType, MethodInfo getEnumeratorMethod, MethodInfo addMethod, ConstructorInfo constructor)
1585             : base(type)
1586         {
1587             this.supportCollectionDataContract = true;
1588             StableName = DataContract.GetStableName(type, true); //TODO
1589             Kind = kind;
1590             this.ItemType = itemType;
1591             this.KeyName = null;
1592             this.ValueName = null;
1593 
1594             this.GetEnumeratorMethod = getEnumeratorMethod;
1595             this.AddMethod = addMethod;
1596             this.Constructor = constructor;
1597             if (itemType != null)
1598             {
1599                 itemContract = DataContract.GetDataContract(itemType, true);
1600             }
1601             Init(type);
1602         }
1603 
1604         DataContract itemContract;
1605         public DataContract ItemContract
1606         {
1607             get
1608             {
1609                 if (itemContract == null && UnderlyingType != null)
1610                 {
1611                     itemContract = DataContract.GetDataContract(UnderlyingType.GetElementType(), true);
1612                 }
1613                 return itemContract;
1614             }
1615             set
1616             {
1617                 itemContract = value;
1618             }
1619         }
1620 
Init(Type type)1621         void Init(Type type)
1622         {
1623             object[] collectionDataContractAttributes = type.GetCustomAttributes(Globals.TypeOfCollectionDataContractAttribute, false);
1624             CollectionDataContractAttribute collectionContractAttribute = null;
1625 
1626             if (collectionDataContractAttributes != null && collectionDataContractAttributes.Length > 0)
1627             {
1628                 collectionContractAttribute = (CollectionDataContractAttribute)collectionDataContractAttributes[0];
1629             }
1630 
1631             if (ItemType != null)
1632             {
1633                 bool isDictionary = (Kind == CollectionKind.Dictionary || Kind == CollectionKind.GenericDictionary);
1634                 string itemName = null, keyName = null, valueName = null;
1635                 if (collectionContractAttribute != null)
1636                 {
1637                     if (!String.IsNullOrEmpty(collectionContractAttribute.ItemName))
1638                     {
1639                         itemName = DataContract.EncodeLocalName(collectionContractAttribute.ItemName);
1640                     }
1641                     if (!String.IsNullOrEmpty(collectionContractAttribute.KeyName))
1642                     {
1643                         keyName = DataContract.EncodeLocalName(collectionContractAttribute.KeyName);
1644                     }
1645                     if (!String.IsNullOrEmpty(collectionContractAttribute.ValueName))
1646                     {
1647                         valueName = DataContract.EncodeLocalName(collectionContractAttribute.ValueName);
1648                     }
1649                 }
1650 
1651                 this.ItemName = itemName ?? DataContract.GetStableName(DataContract.UnwrapNullableType(ItemType), true).Name;
1652                 this.CollectionItemName = this.ItemName;
1653                 if (isDictionary)
1654                 {
1655                     this.KeyName = keyName ?? Globals.KeyLocalName;
1656                     this.ValueName = valueName ?? Globals.ValueLocalName;
1657                 }
1658             }
1659         }
1660 
IsCollectionHelper(Type type, out Type itemType, bool constructorRequired)1661         static bool IsCollectionHelper(Type type, out Type itemType, bool constructorRequired)
1662         {
1663             if (type.IsArray && DataContract.GetDataContract(type, true) == null)
1664             {
1665                 itemType = type.GetElementType();
1666                 return true;
1667             }
1668             DataContract dataContract;
1669             return IsCollectionOrTryCreate(type, false /*tryCreate*/, out dataContract, out itemType, constructorRequired);
1670         }
1671 
IsCollectionDataContract(Type type)1672         internal static bool IsCollectionDataContract(Type type)
1673         {
1674             return type.IsDefined(Globals.TypeOfCollectionDataContractAttribute, false);
1675         }
1676 
IsCollectionOrTryCreate(Type type, bool tryCreate, out DataContract dataContract, out Type itemType, bool constructorRequired)1677         public static bool IsCollectionOrTryCreate(Type type, bool tryCreate, out DataContract dataContract, out Type itemType, bool constructorRequired)
1678         {
1679             dataContract = null;
1680             itemType = Globals.TypeOfObject;
1681             MethodInfo addMethod, getEnumeratorMethod;
1682             bool hasCollectionDataContract = IsCollectionDataContract(type);
1683             Type baseType = type.BaseType;
1684             bool isBaseTypeCollection = (baseType != null && baseType != Globals.TypeOfObject
1685                 && baseType != Globals.TypeOfValueType && baseType != Globals.TypeOfUri) ? IsCollection(baseType) : false;
1686 
1687             if (!Globals.TypeOfIEnumerable.IsAssignableFrom(type) ||
1688                 IsDC(type) || Globals.TypeOfIXmlSerializable.IsAssignableFrom(type))
1689             {
1690                 return false;
1691             }
1692 
1693             if (type.IsInterface)
1694             {
1695                 Type interfaceTypeToCheck = type.IsGenericType ? type.GetGenericTypeDefinition() : type;
1696                 Type[] knownInterfaces = KnownInterfaces;
1697                 for (int i = 0; i < knownInterfaces.Length; i++)
1698                 {
1699                     if (knownInterfaces[i] == interfaceTypeToCheck)
1700                     {
1701                         addMethod = null;
1702                         if (type.IsGenericType)
1703                         {
1704                             Type[] genericArgs = type.GetGenericArguments();
1705                             if (interfaceTypeToCheck == Globals.TypeOfIDictionaryGeneric)
1706                             {
1707                                 itemType = Globals.TypeOfKeyValue.MakeGenericType(genericArgs);
1708                                 addMethod = type.GetMethod(Globals.AddMethodName);
1709                                 getEnumeratorMethod = Globals.TypeOfIEnumerableGeneric.MakeGenericType(Globals.TypeOfKeyValuePair.MakeGenericType(genericArgs)).GetMethod(Globals.GetEnumeratorMethodName);
1710                             }
1711                             else
1712                             {
1713                                 itemType = genericArgs[0];
1714                                 getEnumeratorMethod = Globals.TypeOfIEnumerableGeneric.MakeGenericType(itemType).GetMethod(Globals.GetEnumeratorMethodName);
1715                             }
1716                         }
1717                         else
1718                         {
1719                             if (interfaceTypeToCheck == Globals.TypeOfIDictionary)
1720                             {
1721                                 itemType = typeof(KeyValue<object, object>);
1722                                 addMethod = type.GetMethod(Globals.AddMethodName);
1723                             }
1724                             else
1725                             {
1726                                 itemType = Globals.TypeOfObject;
1727                             }
1728                             getEnumeratorMethod = Globals.TypeOfIEnumerable.GetMethod(Globals.GetEnumeratorMethodName);
1729                         }
1730                         if (tryCreate)
1731                             dataContract = new CollectionDataContract(type, (CollectionKind)(i + 1), itemType, getEnumeratorMethod, addMethod, null/*defaultCtor*/);
1732                         return true;
1733                     }
1734                 }
1735             }
1736             ConstructorInfo defaultCtor = null;
1737             if (!type.IsValueType && constructorRequired)
1738             {
1739                 defaultCtor = type.GetConstructor(BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic, null, Globals.EmptyTypeArray, null);
1740             }
1741 
1742             Type knownInterfaceType = null;
1743             CollectionKind kind = CollectionKind.None;
1744             bool multipleDefinitions = false;
1745             Type[] interfaceTypes = type.GetInterfaces();
1746             foreach (Type interfaceType in interfaceTypes)
1747             {
1748                 Type interfaceTypeToCheck = interfaceType.IsGenericType ? interfaceType.GetGenericTypeDefinition() : interfaceType;
1749                 Type[] knownInterfaces = KnownInterfaces;
1750                 for (int i = 0; i < knownInterfaces.Length; i++)
1751                 {
1752                     if (knownInterfaces[i] == interfaceTypeToCheck)
1753                     {
1754                         CollectionKind currentKind = (CollectionKind)(i + 1);
1755                         if (kind == CollectionKind.None || currentKind < kind)
1756                         {
1757                             kind = currentKind;
1758                             knownInterfaceType = interfaceType;
1759                             multipleDefinitions = false;
1760                         }
1761                         else if ((kind & currentKind) == currentKind)
1762                             multipleDefinitions = true;
1763                         break;
1764                     }
1765                 }
1766             }
1767 
1768             if (kind == CollectionKind.None)
1769             {
1770                 throw new Exception("CollectionTypeIsNotIEnumerable");
1771             }
1772 
1773             if (kind == CollectionKind.Enumerable || kind == CollectionKind.Collection || kind == CollectionKind.GenericEnumerable)
1774             {
1775                 if (multipleDefinitions)
1776                     knownInterfaceType = Globals.TypeOfIEnumerable;
1777                 itemType = knownInterfaceType.IsGenericType ? knownInterfaceType.GetGenericArguments()[0] : Globals.TypeOfObject;
1778                 GetCollectionMethods(type, knownInterfaceType, new Type[] { itemType },
1779                                      false,
1780                                      out getEnumeratorMethod, out addMethod);
1781                 if (tryCreate)
1782                     dataContract = new CollectionDataContract(type, kind, itemType, getEnumeratorMethod, addMethod, defaultCtor);
1783             }
1784             else
1785             {
1786                 if (multipleDefinitions)
1787                 {
1788                     throw new Exception("SR.CollectionTypeHasMultipleDefinitionsOfInterface");
1789                 }
1790 
1791                 Type[] addMethodTypeArray = null;
1792                 switch (kind)
1793                 {
1794                     case CollectionKind.GenericDictionary:
1795                         addMethodTypeArray = knownInterfaceType.GetGenericArguments();
1796                         bool isOpenGeneric = knownInterfaceType.IsGenericTypeDefinition
1797                             || (addMethodTypeArray[0].IsGenericParameter && addMethodTypeArray[1].IsGenericParameter);
1798                         itemType = isOpenGeneric ? Globals.TypeOfKeyValue : Globals.TypeOfKeyValue.MakeGenericType(addMethodTypeArray);
1799                         break;
1800                     case CollectionKind.Dictionary:
1801                         addMethodTypeArray = new Type[] { Globals.TypeOfObject, Globals.TypeOfObject };
1802                         itemType = Globals.TypeOfKeyValue.MakeGenericType(addMethodTypeArray);
1803                         break;
1804                     case CollectionKind.GenericList:
1805                     case CollectionKind.GenericCollection:
1806                         addMethodTypeArray = knownInterfaceType.GetGenericArguments();
1807                         itemType = addMethodTypeArray[0];
1808                         break;
1809                     case CollectionKind.List:
1810                         itemType = Globals.TypeOfObject;
1811                         addMethodTypeArray = new Type[] { itemType };
1812                         break;
1813                 }
1814                 if (tryCreate)
1815                 {
1816                     GetCollectionMethods(type, knownInterfaceType, addMethodTypeArray,
1817                                      true,
1818                                      out getEnumeratorMethod, out addMethod);
1819                     dataContract = new CollectionDataContract(type, kind, itemType, getEnumeratorMethod, addMethod, defaultCtor);
1820                 }
1821             }
1822             return true;
1823         }
1824 
IsDC(Type type)1825         internal static bool IsDC(Type type)
1826         {
1827             if (type.GetCustomAttributes(Globals.TypeOfDataContractAttribute, false) != null && type.GetCustomAttributes(Globals.TypeOfDataContractAttribute, false).Length > 0)
1828             {
1829                 return true;
1830             }
1831             else
1832             {
1833                 return false;
1834             }
1835         }
1836 
IsCollection(Type type)1837         internal static bool IsCollection(Type type)
1838         {
1839             Type itemType;
1840             return IsCollection(type, out itemType);
1841         }
1842 
IsCollection(Type type, out Type itemType)1843         internal static bool IsCollection(Type type, out Type itemType)
1844         {
1845             return IsCollectionHelper(type, out itemType, true /*constructorRequired*/);
1846         }
1847 
1848         static Type[] _knownInterfaces;
1849         internal static Type[] KnownInterfaces
1850         {
1851             get
1852             {
1853                 if (_knownInterfaces == null)
1854                 {
1855                     _knownInterfaces = new Type[]
1856                     {
1857                         Globals.TypeOfIDictionaryGeneric,
1858                         Globals.TypeOfIDictionary,
1859                         Globals.TypeOfIListGeneric,
1860                         Globals.TypeOfICollectionGeneric,
1861                         Globals.TypeOfIList,
1862                         Globals.TypeOfIEnumerableGeneric,
1863                         Globals.TypeOfICollection,
1864                         Globals.TypeOfIEnumerable
1865                     };
1866                 }
1867                 return _knownInterfaces;
1868             }
1869         }
1870 
FindCollectionMethodsOnInterface(Type type, Type interfaceType, ref MethodInfo addMethod, ref MethodInfo getEnumeratorMethod)1871         static void FindCollectionMethodsOnInterface(Type type, Type interfaceType, ref MethodInfo addMethod, ref MethodInfo getEnumeratorMethod)
1872         {
1873             InterfaceMapping mapping = type.GetInterfaceMap(interfaceType);
1874             for (int i = 0; i < mapping.TargetMethods.Length; i++)
1875             {
1876                 if (mapping.InterfaceMethods[i].Name == Globals.AddMethodName)
1877                     addMethod = mapping.InterfaceMethods[i];
1878                 else if (mapping.InterfaceMethods[i].Name == Globals.GetEnumeratorMethodName)
1879                     getEnumeratorMethod = mapping.InterfaceMethods[i];
1880             }
1881         }
1882 
IsKnownInterface(Type type)1883         static bool IsKnownInterface(Type type)
1884         {
1885             Type typeToCheck = type.IsGenericType ? type.GetGenericTypeDefinition() : type;
1886             foreach (Type knownInterfaceType in KnownInterfaces)
1887             {
1888                 if (typeToCheck == knownInterfaceType)
1889                 {
1890                     return true;
1891                 }
1892             }
1893             return false;
1894         }
1895 
GetCollectionMethods(Type type, Type interfaceType, Type[] addMethodTypeArray, bool addMethodOnInterface, out MethodInfo getEnumeratorMethod, out MethodInfo addMethod)1896         static void GetCollectionMethods(Type type, Type interfaceType, Type[] addMethodTypeArray, bool addMethodOnInterface, out MethodInfo getEnumeratorMethod, out MethodInfo addMethod)
1897         {
1898             addMethod = getEnumeratorMethod = null;
1899 
1900             if (addMethodOnInterface)
1901             {
1902                 addMethod = type.GetMethod(Globals.AddMethodName, BindingFlags.Instance | BindingFlags.Public, null, addMethodTypeArray, null);
1903                 if (addMethod == null || addMethod.GetParameters()[0].ParameterType != addMethodTypeArray[0])
1904                 {
1905                     FindCollectionMethodsOnInterface(type, interfaceType, ref addMethod, ref getEnumeratorMethod);
1906                     if (addMethod == null)
1907                     {
1908                         Type[] parentInterfaceTypes = interfaceType.GetInterfaces();
1909                         foreach (Type parentInterfaceType in parentInterfaceTypes)
1910                         {
1911                             if (IsKnownInterface(parentInterfaceType))
1912                             {
1913                                 FindCollectionMethodsOnInterface(type, parentInterfaceType, ref addMethod, ref getEnumeratorMethod);
1914                                 if (addMethod == null)
1915                                 {
1916                                     break;
1917                                 }
1918                             }
1919                         }
1920                     }
1921                 }
1922             }
1923             else
1924             {
1925                 addMethod = type.GetMethod(Globals.AddMethodName, BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic, null, addMethodTypeArray, null);
1926                 if (addMethod == null)
1927                     return;
1928             }
1929 
1930             if (getEnumeratorMethod == null)
1931             {
1932                 getEnumeratorMethod = type.GetMethod(Globals.GetEnumeratorMethodName, BindingFlags.Instance | BindingFlags.Public, null, Globals.EmptyTypeArray, null);
1933                 if (getEnumeratorMethod == null || !Globals.TypeOfIEnumerator.IsAssignableFrom(getEnumeratorMethod.ReturnType))
1934                 {
1935                     Type ienumerableInterface = interfaceType.GetInterface("System.Collections.Generic.IEnumerable*");
1936                     if (ienumerableInterface == null)
1937                         ienumerableInterface = Globals.TypeOfIEnumerable;
1938                     getEnumeratorMethod = GetTargetMethodWithName(Globals.GetEnumeratorMethodName, type, ienumerableInterface);
1939                 }
1940             }
1941         }
1942 
GetTargetMethodWithName(string name, Type type, Type interfaceType)1943         internal static MethodInfo GetTargetMethodWithName(string name, Type type, Type interfaceType)
1944         {
1945             InterfaceMapping mapping = type.GetInterfaceMap(interfaceType);
1946             for (int i = 0; i < mapping.TargetMethods.Length; i++)
1947             {
1948                 if (mapping.InterfaceMethods[i].Name == name)
1949                     return mapping.InterfaceMethods[i];
1950             }
1951             return null;
1952         }
Equals(object other)1953         public override bool Equals(object other)
1954         {
1955             if ((object)this == other)
1956                 return true;
1957             if (base.Equals(other))
1958             {
1959                 CollectionDataContract collectionContract = other as CollectionDataContract;
1960                 if (collectionContract != null)
1961                 {
1962                     if (!collectionContract.ItemContract.Equals(this.ItemContract)) { return false; }
1963                     if (collectionContract.ItemName != this.ItemName) { return false; }
1964                     if (collectionContract.KeyName != this.KeyName) { return false; }
1965                     if (collectionContract.ValueName != this.ValueName) { return false; }
1966                     if (collectionContract.TopLevelElementName != this.TopLevelElementName) { return false; }
1967                     if (collectionContract.TopLevelElementNamespace != this.TopLevelElementNamespace) { return false; }
1968                     if (collectionContract.IsDictionary != this.IsDictionary) { return false; }
1969                     return true;
1970                 }
1971             }
1972             return false;
1973         }
1974 
GetHashCode()1975         public override int GetHashCode()
1976         {
1977             return base.GetHashCode();
1978         }
1979     }
1980 
1981     public static class Globals
1982     {
1983         internal static Type TypeOfObject = typeof(object);
1984         internal static Type TypeOfValueType = typeof(ValueType);
1985         internal static Type TypeOfArray = typeof(Array);
1986         internal static Type TypeOfEnum = typeof(Enum);
1987         internal static Type TypeOfString = typeof(string);
1988         internal static Type TypeOfStringArray = typeof(string[]);
1989         internal static Type TypeOfInt = typeof(int);
1990         internal static Type TypeOfIntArray = typeof(int[]);
1991         internal static Type TypeOfLong = typeof(long);
1992         internal static Type TypeOfULong = typeof(ulong);
1993         internal static Type TypeOfVoid = typeof(void);
1994         internal static Type TypeOfDouble = typeof(double);
1995         internal static Type TypeOfBool = typeof(bool);
1996         internal static Type TypeOfByte = typeof(byte);
1997         internal static Type TypeOfByteArray = typeof(byte[]);
1998         internal static Type TypeOfTimeSpan = typeof(TimeSpan);
1999         internal static Type TypeOfGuid = typeof(Guid);
2000         internal static Type TypeOfUri = typeof(Uri);
2001         internal static Type TypeOfIntPtr = typeof(IntPtr);
2002         internal static Type TypeOfStreamingContext = typeof(StreamingContext);
2003         internal static Type TypeOfISerializable = typeof(ISerializable);
2004         internal static Type TypeOfIDeserializationCallback = typeof(IDeserializationCallback);
2005         internal static Type TypeOfIObjectReference = typeof(IObjectReference);
2006         internal static Type TypeOfBytePtr = typeof(byte*);
2007         internal static Type TypeOfKnownTypeAttribute = typeof(KnownTypeAttribute);
2008         internal static Type TypeOfDataContractAttribute = typeof(DataContractAttribute);
2009         internal static Type TypeOfContractNamespaceAttribute = typeof(ContractNamespaceAttribute);
2010         internal static Type TypeOfDataMemberAttribute = typeof(DataMemberAttribute);
2011         internal static Type TypeOfOptionalFieldAttribute = typeof(OptionalFieldAttribute);
2012         internal static Type TypeOfObjectArray = typeof(object[]);
2013         internal static Type TypeOfOnSerializingAttribute = typeof(OnSerializingAttribute);
2014         internal static Type TypeOfOnSerializedAttribute = typeof(OnSerializedAttribute);
2015         internal static Type TypeOfOnDeserializingAttribute = typeof(OnDeserializingAttribute);
2016         internal static Type TypeOfOnDeserializedAttribute = typeof(OnDeserializedAttribute);
2017         internal static Type TypeOfFlagsAttribute = typeof(FlagsAttribute);
2018         internal static Type TypeOfSerializableAttribute = typeof(SerializableAttribute);
2019         internal static Type TypeOfSerializationInfo = typeof(SerializationInfo);
2020         internal static Type TypeOfSerializationInfoEnumerator = typeof(SerializationInfoEnumerator);
2021         internal static Type TypeOfSerializationEntry = typeof(SerializationEntry);
2022         internal static Type TypeOfIXmlSerializable = typeof(IXmlSerializable);
2023         internal static Type TypeOfXmlSchemaProviderAttribute = typeof(XmlSchemaProviderAttribute);
2024         internal static Type TypeOfXmlRootAttribute = typeof(XmlRootAttribute);
2025         internal static Type TypeOfXmlQualifiedName = typeof(XmlQualifiedName);
2026         internal static Type TypeOfXmlSchemaType = typeof(XmlSchemaType);
2027         internal static Type TypeOfXmlSchemaSet = typeof(XmlSchemaSet);
2028         internal static object[] EmptyObjectArray = new object[0];
2029         internal static Type[] EmptyTypeArray = new Type[0];
2030         internal static Type TypeOfIExtensibleDataObject = typeof(IExtensibleDataObject);
2031         internal static Type TypeOfExtensionDataObject = typeof(ExtensionDataObject);
2032         internal static Type TypeOfNullable = typeof(Nullable<>);
2033         internal static Type TypeOfCollectionDataContractAttribute = typeof(CollectionDataContractAttribute);
2034         internal static Type TypeOfIEnumerable = typeof(IEnumerable);
2035         internal static Type TypeOfIDictionaryGeneric = typeof(IDictionary<,>);
2036         internal static Type TypeOfIEnumerableGeneric = typeof(IEnumerable<>);
2037         internal static Type TypeOfIDictionary = typeof(IDictionary);
2038         internal static Type TypeOfKeyValuePair = typeof(KeyValuePair<,>);
2039         internal static Type TypeOfKeyValue = typeof(KeyValue<,>);
2040         internal static Type TypeOfIListGeneric = typeof(IList<>);
2041         internal static Type TypeOfICollectionGeneric = typeof(ICollection<>);
2042         internal static Type TypeOfIList = typeof(IList);
2043         internal static Type TypeOfICollection = typeof(ICollection);
2044         internal static Type TypeOfIEnumerator = typeof(IEnumerator);
2045         public const string KeyLocalName = "Key";
2046         public const string ValueLocalName = "Value";
2047         public const string AddMethodName = "Add";
2048         public static string SchemaInstanceNamespace = XmlSchema.InstanceNamespace;
2049         public static string SchemaNamespace = XmlSchema.Namespace;
2050         public static string DefaultNamespace = "http://tempuri.org/";
2051         public static bool DefaultIsRequired = false;
2052         public static int DefaultVersion = 1;
2053         public static string GetEnumeratorMethodName = "GetEnumerator";
2054         public static string SerializationNamespace = "http://schemas.microsoft.com/2003/10/Serialization/";
2055     }
2056 }
2057