IKVM11  11
Java SE 11 Virtual Machine for .NET
Loading...
Searching...
No Matches
ReflectUtil.cs
Go to the documentation of this file.
1/*
2 Copyright (C) 2008-2012 Jeroen Frijters
3
4 This software is provided 'as-is', without any express or implied
5 warranty. In no event will the authors be held liable for any damages
6 arising from the use of this software.
7
8 Permission is granted to anyone to use this software for any purpose,
9 including commercial applications, and to alter it and redistribute it
10 freely, subject to the following restrictions:
11
12 1. The origin of this software must not be misrepresented; you must not
13 claim that you wrote the original software. If you use this software
14 in a product, an acknowledgment in the product documentation would be
15 appreciated but is not required.
16 2. Altered source versions must be plainly marked as such, and must not be
17 misrepresented as being the original software.
18 3. This notice may not be removed or altered from any source distribution.
19
20 Jeroen Frijters
21 jeroen@frijters.net
22
23*/
24using System;
25
26#if IMPORTER || EXPORTER
27using IKVM.Reflection;
29
30using Type = IKVM.Reflection.Type;
31#else
32using System.Reflection;
33using System.Reflection.Emit;
34#endif
35
36namespace IKVM.Runtime
37{
38
39 static class ReflectUtil
40 {
41
42 internal static bool IsSameAssembly(Type type1, Type type2)
43 {
44 return type1.Assembly.Equals(type2.Assembly);
45 }
46
47 internal static bool IsFromAssembly(Type type, Assembly assembly)
48 {
49 return type.Assembly.Equals(assembly);
50 }
51
52 internal static Assembly GetAssembly(Type type)
53 {
54 return type.Assembly;
55 }
56
57 internal static bool IsDynamicAssembly(Assembly asm)
58 {
59#if IMPORTER || EXPORTER
60 return false;
61#else
62 return asm.IsDynamic;
63#endif
64 }
65
66 internal static bool IsReflectionOnly(Type type)
67 {
68 while (type.HasElementType)
69 type = type.GetElementType();
70
71 var asm = type.Assembly;
72 if (asm != null && asm.ReflectionOnly)
73 return true;
74
75 if (!type.IsGenericType || type.IsGenericTypeDefinition)
76 return false;
77
78 // we have a generic type instantiation, it might have ReflectionOnly type arguments
79 foreach (Type arg in type.GetGenericArguments())
80 if (IsReflectionOnly(arg))
81 return true;
82
83 return false;
84 }
85
86 internal static bool ContainsTypeBuilder(Type type)
87 {
88 while (type.HasElementType)
89 type = type.GetElementType();
90
91 if (!type.IsGenericType || type.IsGenericTypeDefinition)
92 return type is TypeBuilder;
93
94 foreach (Type arg in type.GetGenericArguments())
95 if (ContainsTypeBuilder(arg))
96 return true;
97
98 return type.GetGenericTypeDefinition() is TypeBuilder;
99 }
100
101 internal static bool IsVector(Type type)
102 {
103#if IMPORTER || EXPORTER
104 return type.IsSZArray;
105#else
106#if NET
107 return type.IsSZArray;
108#else
109 // there's no API to distinguish an array of rank 1 from a vector,
110 // so we check if the type name ends in [], which indicates it's a vector
111 // (non-vectors will have [*] or [,]).
112 return type.IsArray && type.Name.EndsWith("[]");
113#endif
114#endif
115 }
116
117 internal static bool IsDynamicMethod(MethodInfo method)
118 {
119 // there's no way to distinguish a baked DynamicMethod from a RuntimeMethodInfo and
120 // on top of that Mono behaves completely different from .NET
121 try
122 {
123 // on Mono 2.10 the MetadataToken property returns zero instead of throwing InvalidOperationException
124 return method.MetadataToken == 0;
125 }
126 catch (InvalidOperationException)
127 {
128 return true;
129 }
130 }
131
132 internal static MethodBuilder DefineTypeInitializer(TypeBuilder typeBuilder, RuntimeClassLoader loader)
133 {
134 var attr = MethodAttributes.Static | MethodAttributes.RTSpecialName | MethodAttributes.SpecialName | MethodAttributes.Private;
135 return typeBuilder.DefineMethod(ConstructorInfo.TypeConstructorName, attr, null, Type.EmptyTypes);
136 }
137
138 internal static bool MatchNameAndPublicKeyToken(AssemblyName name1, AssemblyName name2)
139 {
140 return name1.Name.Equals(name2.Name, StringComparison.OrdinalIgnoreCase) && CompareKeys(name1.GetPublicKeyToken(), name2.GetPublicKeyToken());
141 }
142
143 static bool CompareKeys(byte[] b1, byte[] b2)
144 {
145 int len1 = b1 == null ? 0 : b1.Length;
146 int len2 = b2 == null ? 0 : b2.Length;
147 if (len1 != len2)
148 return false;
149
150 for (int i = 0; i < len1; i++)
151 if (b1[i] != b2[i])
152 return false;
153
154 return true;
155 }
156
157 internal static bool IsConstructor(MethodBase method)
158 {
159 return method.IsSpecialName && method.Name == ConstructorInfo.ConstructorName;
160 }
161
162 internal static MethodBuilder DefineConstructor(TypeBuilder tb, MethodAttributes attribs, Type[] parameterTypes)
163 {
164 return tb.DefineMethod(ConstructorInfo.ConstructorName, attribs | MethodAttributes.SpecialName | MethodAttributes.RTSpecialName, null, parameterTypes);
165 }
166
172 internal static bool CanOwnDynamicMethod(Type type)
173 {
174 return type != null && !type.IsInterface && !type.HasElementType && !type.IsGenericTypeDefinition && !type.IsGenericParameter;
175 }
176
177 internal static bool MatchParameterInfos(ParameterInfo p1, ParameterInfo p2)
178 {
179 if (p1.ParameterType != p2.ParameterType)
180 {
181 return false;
182 }
183 if (!MatchTypes(p1.GetOptionalCustomModifiers(), p2.GetOptionalCustomModifiers()))
184 {
185 return false;
186 }
187 if (!MatchTypes(p1.GetRequiredCustomModifiers(), p2.GetRequiredCustomModifiers()))
188 {
189 return false;
190 }
191 return true;
192 }
193
194 private static bool MatchTypes(Type[] t1, Type[] t2)
195 {
196 if (t1.Length == t2.Length)
197 {
198 for (int i = 0; i < t1.Length; i++)
199 {
200 if (t1[i] != t2[i])
201 {
202 return false;
203 }
204 }
205 return true;
206 }
207 return false;
208 }
209
210#if IMPORTER
211
212 internal static Type GetMissingType(Type type)
213 {
214 while (type.HasElementType)
215 type = type.GetElementType();
216
217 if (type.__IsMissing)
218 {
219 return type;
220 }
221 else if (type.__ContainsMissingType)
222 {
223 if (type.IsGenericType)
224 {
225 foreach (var arg in type.GetGenericArguments())
226 {
227 var t1 = GetMissingType(arg);
228 if (t1.__IsMissing)
229 return t1;
230 }
231 }
232
233 throw new NotImplementedException(type.FullName);
234 }
235 else
236 {
237 return type;
238 }
239 }
240
241#endif
242
243 }
244
245}
IKVM.Reflection.Type Type
IKVM.Reflection.Assembly Assembly
IKVM.Reflection.AssemblyName AssemblyName
IKVM.Reflection.ConstructorInfo ConstructorInfo
IKVM.Reflection.MethodInfo MethodInfo
IKVM.Reflection.ParameterInfo ParameterInfo
IKVM.Reflection.MethodBase MethodBase
Runtime support for a class loader.