d3e5a15d5d473ae520f905809bb0a77bc786f352
[mono.git] / mcs / class / Mono.Cecil / Mono.Cecil / GenericParameter.cs
1 //
2 // GenericParameter.cs
3 //
4 // Author:
5 //   Jb Evain (jbevain@gmail.com)
6 //
7 // Copyright (c) 2008 - 2010 Jb Evain
8 //
9 // Permission is hereby granted, free of charge, to any person obtaining
10 // a copy of this software and associated documentation files (the
11 // "Software"), to deal in the Software without restriction, including
12 // without limitation the rights to use, copy, modify, merge, publish,
13 // distribute, sublicense, and/or sell copies of the Software, and to
14 // permit persons to whom the Software is furnished to do so, subject to
15 // the following conditions:
16 //
17 // The above copyright notice and this permission notice shall be
18 // included in all copies or substantial portions of the Software.
19 //
20 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
21 // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
22 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
23 // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
24 // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
25 // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
26 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
27 //
28
29 using System;
30
31 using Mono.Collections.Generic;
32
33 using Mono.Cecil.Metadata;
34
35 namespace Mono.Cecil {
36
37         public sealed class GenericParameter : TypeReference, ICustomAttributeProvider {
38
39                 readonly IGenericParameterProvider owner;
40
41                 ushort attributes;
42                 Collection<TypeReference> constraints;
43                 Collection<CustomAttribute> custom_attributes;
44
45                 public GenericParameterAttributes Attributes {
46                         get { return (GenericParameterAttributes) attributes; }
47                         set { attributes = (ushort) value; }
48                 }
49
50                 public int Position {
51                         get {
52                                 if (owner == null)
53                                         return -1;
54
55                                 return owner.GenericParameters.IndexOf (this);
56                         }
57                 }
58
59                 public IGenericParameterProvider Owner {
60                         get { return owner; }
61                 }
62
63                 public bool HasConstraints {
64                         get {
65                                 if (constraints != null)
66                                         return constraints.Count > 0;
67
68                                 if (HasImage)
69                                         return Module.Read (this, (generic_parameter, reader) => reader.HasGenericConstraints (generic_parameter));
70
71                                 return false;
72                         }
73                 }
74
75                 public Collection<TypeReference> Constraints {
76                         get {
77                                 if (constraints != null)
78                                         return constraints;
79
80                                 if (HasImage)
81                                         return constraints = Module.Read (this, (generic_parameter, reader) => reader.ReadGenericConstraints (generic_parameter));
82
83                                 return constraints = new Collection<TypeReference> ();
84                         }
85                 }
86
87                 public bool HasCustomAttributes {
88                         get {
89                                 if (custom_attributes != null)
90                                         return custom_attributes.Count > 0;
91
92                                 return this.GetHasCustomAttributes (Module);
93                         }
94                 }
95
96                 public Collection<CustomAttribute> CustomAttributes {
97                         get { return custom_attributes ?? (custom_attributes = this.GetCustomAttributes (Module)); }
98                 }
99
100                 internal new bool HasImage {
101                         get { return Module != null && Module.HasImage; }
102                 }
103
104                 public override IMetadataScope Scope {
105                         get {
106                                 if (owner.GenericParameterType == GenericParameterType.Method)
107                                         return ((MethodReference) owner).DeclaringType.Scope;
108
109                                 return ((TypeReference) owner).Scope;
110                         }
111                 }
112
113                 public override ModuleDefinition Module {
114                         get { return ((MemberReference) owner).Module; }
115                 }
116
117                 public override string Name {
118                         get {
119                                 if (!string.IsNullOrEmpty (base.Name))
120                                         return base.Name;
121
122                                 return base.Name = (owner.GenericParameterType == GenericParameterType.Type ? "!" : "!!") + Position;
123                         }
124                 }
125
126                 public override string Namespace {
127                         get { return string.Empty; }
128                         set { throw new InvalidOperationException (); }
129                 }
130
131                 public override string FullName {
132                         get { return Name; }
133                 }
134
135                 public override bool IsGenericParameter {
136                         get { return true; }
137                 }
138
139                 internal override bool ContainsGenericParameter {
140                         get { return true; }
141                 }
142
143                 public override MetadataType MetadataType {
144                         get { return (MetadataType) etype; }
145                 }
146
147                 #region GenericParameterAttributes
148
149                 public bool IsNonVariant {
150                         get { return attributes.GetMaskedAttributes ((ushort) GenericParameterAttributes.VarianceMask, (ushort) GenericParameterAttributes.NonVariant); }
151                         set { attributes = attributes.SetMaskedAttributes ((ushort) GenericParameterAttributes.VarianceMask, (ushort) GenericParameterAttributes.NonVariant, value); }
152                 }
153
154                 public bool IsCovariant {
155                         get { return attributes.GetMaskedAttributes ((ushort) GenericParameterAttributes.VarianceMask, (ushort) GenericParameterAttributes.Covariant); }
156                         set { attributes = attributes.SetMaskedAttributes ((ushort) GenericParameterAttributes.VarianceMask, (ushort) GenericParameterAttributes.Covariant, value); }
157                 }
158
159                 public bool IsContravariant {
160                         get { return attributes.GetMaskedAttributes ((ushort) GenericParameterAttributes.VarianceMask, (ushort) GenericParameterAttributes.Contravariant); }
161                         set { attributes = attributes.SetMaskedAttributes ((ushort) GenericParameterAttributes.VarianceMask, (ushort) GenericParameterAttributes.Contravariant, value); }
162                 }
163
164                 public bool HasReferenceTypeConstraint {
165                         get { return attributes.GetAttributes ((ushort) GenericParameterAttributes.ReferenceTypeConstraint); }
166                         set { attributes = attributes.SetAttributes ((ushort) GenericParameterAttributes.ReferenceTypeConstraint, value); }
167                 }
168
169                 public bool HasNotNullableValueTypeConstraint {
170                         get { return attributes.GetAttributes ((ushort) GenericParameterAttributes.NotNullableValueTypeConstraint); }
171                         set { attributes = attributes.SetAttributes ((ushort) GenericParameterAttributes.NotNullableValueTypeConstraint, value); }
172                 }
173
174                 public bool HasDefaultConstructorConstraint {
175                         get { return attributes.GetAttributes ((ushort) GenericParameterAttributes.DefaultConstructorConstraint); }
176                         set { attributes = attributes.SetAttributes ((ushort) GenericParameterAttributes.DefaultConstructorConstraint, value); }
177                 }
178
179                 #endregion
180
181                 public GenericParameter (IGenericParameterProvider owner)
182                         : this (string.Empty, owner)
183                 {
184                 }
185
186                 public GenericParameter (string name, IGenericParameterProvider owner)
187                         : base (string.Empty, name)
188                 {
189                         if (owner == null)
190                                 throw new ArgumentNullException ();
191
192                         this.owner = owner;
193                         this.etype = owner.GenericParameterType == GenericParameterType.Type ? ElementType.Var : ElementType.MVar;
194                 }
195
196                 public override TypeDefinition Resolve ()
197                 {
198                         return null;
199                 }
200         }
201 }