MonoGenericClass.cs 28 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070
  1. //
  2. // System.Reflection.MonoGenericClass
  3. //
  4. // Sean MacIsaac ([email protected])
  5. // Paolo Molaro ([email protected])
  6. // Patrik Torstensson ([email protected])
  7. //
  8. // (C) 2001 Ximian, Inc.
  9. //
  10. //
  11. // Copyright (C) 2004 Novell, Inc (http://www.novell.com)
  12. //
  13. // Permission is hereby granted, free of charge, to any person obtaining
  14. // a copy of this software and associated documentation files (the
  15. // "Software"), to deal in the Software without restriction, including
  16. // without limitation the rights to use, copy, modify, merge, publish,
  17. // distribute, sublicense, and/or sell copies of the Software, and to
  18. // permit persons to whom the Software is furnished to do so, subject to
  19. // the following conditions:
  20. //
  21. // The above copyright notice and this permission notice shall be
  22. // included in all copies or substantial portions of the Software.
  23. //
  24. // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
  25. // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
  26. // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
  27. // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
  28. // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
  29. // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
  30. // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  31. //
  32. using System.Reflection;
  33. using System.Reflection.Emit;
  34. using System.Collections;
  35. using System.Runtime.CompilerServices;
  36. using System.Globalization;
  37. using System.Runtime.Serialization;
  38. using System.Text;
  39. namespace System.Reflection
  40. {
  41. /*
  42. * MonoGenericClass represents an instantiation of a generic TypeBuilder. MS
  43. * calls this class TypeBuilderInstantiation (a much better name). MS returns
  44. * NotImplementedException for many of the methods but we can't do that as gmcs
  45. * depends on them.
  46. */
  47. internal class MonoGenericClass : Type
  48. {
  49. #region Keep in sync with object-internals.h
  50. #pragma warning disable 649
  51. internal Type generic_type;
  52. Type[] type_arguments;
  53. bool initialized;
  54. #pragma warning restore 649
  55. #endregion
  56. Hashtable fields, ctors, methods;
  57. int event_count;
  58. int is_compiler_context;
  59. internal MonoGenericClass ()
  60. {
  61. // this should not be used
  62. throw new InvalidOperationException ();
  63. }
  64. internal MonoGenericClass (Type tb, Type[] args)
  65. {
  66. this.generic_type = tb;
  67. this.type_arguments = args;
  68. /*
  69. This is a temporary hack until we can fix the rest of the runtime
  70. to properly handle this class to be a complete UT.
  71. We must not regisrer this with the runtime after the type is created
  72. otherwise created_type.MakeGenericType will return an instance of MonoGenericClass,
  73. which is very very broken.
  74. */
  75. if (tb is TypeBuilder && !(tb as TypeBuilder).is_created)
  76. register_with_runtime (this);
  77. }
  78. internal override bool IsCompilerContext {
  79. get {
  80. if (is_compiler_context == 0) {
  81. bool is_cc = generic_type.IsCompilerContext;
  82. foreach (Type t in type_arguments)
  83. is_cc |= t.IsCompilerContext;
  84. is_compiler_context = is_cc ? 1 : -1;
  85. }
  86. return is_compiler_context == 1;
  87. }
  88. }
  89. internal override Type InternalResolve ()
  90. {
  91. Type gtd = generic_type.InternalResolve ();
  92. Type[] args = new Type [type_arguments.Length];
  93. for (int i = 0; i < type_arguments.Length; ++i)
  94. args [i] = type_arguments [i].InternalResolve ();
  95. return gtd.MakeGenericType (args);
  96. }
  97. [MethodImplAttribute(MethodImplOptions.InternalCall)]
  98. extern void initialize (MethodInfo[] methods, ConstructorInfo[] ctors, FieldInfo[] fields, PropertyInfo[] properties, EventInfo[] events);
  99. [MethodImplAttribute(MethodImplOptions.InternalCall)]
  100. internal static extern void register_with_runtime (Type type);
  101. EventInfo[] GetEventsFromGTD (BindingFlags flags) {
  102. TypeBuilder tb = generic_type as TypeBuilder;
  103. if (tb == null)
  104. return generic_type.GetEvents (flags);
  105. return tb.GetEvents_internal (flags);
  106. }
  107. ConstructorInfo[] GetConstructorsFromGTD (BindingFlags flags)
  108. {
  109. TypeBuilder tb = generic_type as TypeBuilder;
  110. if (tb == null)
  111. return generic_type.GetConstructors (flags);
  112. return tb.GetConstructorsInternal (flags);
  113. }
  114. /*
  115. MethodInfo[] GetMethodsFromGTD (BindingFlags bf)
  116. {
  117. TypeBuilder tb = generic_type as TypeBuilder;
  118. if (tb == null)
  119. return generic_type.GetMethods (bf);
  120. MethodInfo[] res = new MethodInfo [tb.num_methods];
  121. if (tb.num_methods > 0)
  122. Array.Copy (tb.methods, res, tb.num_methods);
  123. return res;
  124. }
  125. */
  126. FieldInfo[] GetFieldsFromGTD (BindingFlags bf)
  127. {
  128. TypeBuilder tb = generic_type as TypeBuilder;
  129. if (tb == null)
  130. return generic_type.GetFields (bf);
  131. FieldInfo[] res = new FieldInfo [tb.num_fields];
  132. if (tb.num_fields > 0)
  133. Array.Copy (tb.fields, res, tb.num_fields);
  134. return res;
  135. }
  136. /*@hint might not be honored so it required aditional filtering
  137. TODO move filtering into here for the TypeBuilder case and remove the hint ugliness
  138. */
  139. MethodInfo[] GetMethodsFromGTDWithHint (BindingFlags hint)
  140. {
  141. TypeBuilder tb = generic_type as TypeBuilder;
  142. if (tb == null)
  143. return generic_type.GetMethods (hint);
  144. if (tb.num_methods == 0)
  145. return new MethodInfo [0];
  146. MethodInfo[] res = new MethodInfo [tb.num_methods];
  147. Array.Copy (tb.methods, 0, res, 0, tb.num_methods);
  148. return res;
  149. }
  150. /*@hint might not be honored so it required aditional filtering
  151. TODO move filtering into here for the TypeBuilder case and remove the hint ugliness
  152. */
  153. ConstructorInfo[] GetConstructorsFromGTDWithHint (BindingFlags hint)
  154. {
  155. TypeBuilder tb = generic_type as TypeBuilder;
  156. if (tb == null)
  157. return generic_type.GetConstructors (hint);
  158. if (tb.ctors == null)
  159. return new ConstructorInfo [0];
  160. ConstructorInfo[] res = new ConstructorInfo [tb.ctors.Length];
  161. tb.ctors.CopyTo (res, 0);
  162. return res;
  163. }
  164. static Type PeelType (Type t) {
  165. if (t.HasElementType)
  166. return PeelType (t.GetElementType ());
  167. if (t.IsGenericType && !t.IsGenericParameter)
  168. return t.GetGenericTypeDefinition ();
  169. return t;
  170. }
  171. static PropertyInfo[] GetPropertiesInternal (Type type, BindingFlags bf)
  172. {
  173. TypeBuilder tb = type as TypeBuilder;
  174. if (tb != null)
  175. return tb.properties;
  176. return type.GetProperties (bf);
  177. }
  178. Type[] GetInterfacesFromGTD ()
  179. {
  180. TypeBuilder tb = generic_type as TypeBuilder;
  181. if (tb != null)
  182. return tb.interfaces;
  183. return generic_type.GetInterfaces ();
  184. }
  185. internal bool IsCreated {
  186. get {
  187. TypeBuilder tb = generic_type as TypeBuilder;
  188. return tb != null ? tb.is_created : true;
  189. }
  190. }
  191. private const BindingFlags flags = BindingFlags.Public | BindingFlags.NonPublic |
  192. BindingFlags.Static | BindingFlags.Instance | BindingFlags.DeclaredOnly;
  193. void initialize ()
  194. {
  195. if (initialized)
  196. return;
  197. MonoGenericClass parent = GetParentType () as MonoGenericClass;
  198. if (parent != null)
  199. parent.initialize ();
  200. EventInfo[] events = GetEventsFromGTD (flags);
  201. event_count = events.Length;
  202. initialize (generic_type.GetMethods (flags),
  203. GetConstructorsFromGTD (flags),
  204. generic_type.GetFields (flags),
  205. generic_type.GetProperties (flags),
  206. events);
  207. initialized = true;
  208. }
  209. Type GetParentType ()
  210. {
  211. return InflateType (generic_type.BaseType);
  212. }
  213. internal Type InflateType (Type type)
  214. {
  215. return InflateType (type, type_arguments, null);
  216. }
  217. internal Type InflateType (Type type, Type[] method_args)
  218. {
  219. return InflateType (type, type_arguments, method_args);
  220. }
  221. internal static Type InflateType (Type type, Type[] type_args, Type[] method_args)
  222. {
  223. if (type == null)
  224. return null;
  225. if (!type.IsGenericParameter && !type.ContainsGenericParameters)
  226. return type;
  227. if (type.IsGenericParameter) {
  228. if (type.DeclaringMethod == null)
  229. return type_args == null ? type : type_args [type.GenericParameterPosition];
  230. return method_args == null ? type : method_args [type.GenericParameterPosition];
  231. }
  232. if (type.IsPointer)
  233. return InflateType (type.GetElementType (), type_args, method_args).MakePointerType ();
  234. if (type.IsByRef)
  235. return InflateType (type.GetElementType (), type_args, method_args).MakeByRefType ();
  236. if (type.IsArray) {
  237. if (type.GetArrayRank () > 1)
  238. return InflateType (type.GetElementType (), type_args, method_args).MakeArrayType (type.GetArrayRank ());
  239. #if BOOTSTRAP_NET_2_0
  240. if (type.ToString ().EndsWith ("[*]"))
  241. #else
  242. if (type.ToString ().EndsWith ("[*]", StringComparison.Ordinal)) /*FIXME, the reflection API doesn't offer a way around this*/
  243. #endif
  244. return InflateType (type.GetElementType (), type_args, method_args).MakeArrayType (1);
  245. return InflateType (type.GetElementType (), type_args, method_args).MakeArrayType ();
  246. }
  247. Type[] args = type.GetGenericArguments ();
  248. for (int i = 0; i < args.Length; ++i)
  249. args [i] = InflateType (args [i], type_args, method_args);
  250. Type gtd = type.IsGenericTypeDefinition ? type : type.GetGenericTypeDefinition ();
  251. return gtd.MakeGenericType (args);
  252. }
  253. public override Type BaseType {
  254. get {
  255. Type parent = GetParentType ();
  256. return parent != null ? parent : generic_type.BaseType;
  257. }
  258. }
  259. Type[] GetInterfacesInternal ()
  260. {
  261. Type[] ifaces = GetInterfacesFromGTD ();
  262. if (ifaces == null)
  263. return new Type [0];
  264. Type[] res = new Type [ifaces.Length];
  265. for (int i = 0; i < res.Length; ++i)
  266. res [i] = InflateType (ifaces [i]);
  267. return res;
  268. }
  269. public override Type[] GetInterfaces ()
  270. {
  271. if (!IsCompilerContext) {
  272. Console.WriteLine ("--FAIL {0}", this);
  273. Console.WriteLine ("\tgt {0}/{1}/{2}", generic_type, generic_type.IsCompilerContext, generic_type.GetType ());
  274. foreach (Type t in type_arguments)
  275. Console.WriteLine ("\targ {0}/{1}/{2}", t, t.IsCompilerContext, t.GetType ());
  276. throw new NotSupportedException ();
  277. }
  278. return GetInterfacesInternal ();
  279. }
  280. protected override bool IsValueTypeImpl ()
  281. {
  282. return generic_type.IsValueType;
  283. }
  284. internal override MethodInfo GetMethod (MethodInfo fromNoninstanciated)
  285. {
  286. initialize ();
  287. if (methods == null)
  288. methods = new Hashtable ();
  289. if (!methods.ContainsKey (fromNoninstanciated))
  290. methods [fromNoninstanciated] = new MethodOnTypeBuilderInst (this, fromNoninstanciated);
  291. return (MethodInfo)methods [fromNoninstanciated];
  292. }
  293. internal override ConstructorInfo GetConstructor (ConstructorInfo fromNoninstanciated)
  294. {
  295. initialize ();
  296. if (ctors == null)
  297. ctors = new Hashtable ();
  298. if (!ctors.ContainsKey (fromNoninstanciated))
  299. ctors [fromNoninstanciated] = new ConstructorOnTypeBuilderInst (this, fromNoninstanciated);
  300. return (ConstructorInfo)ctors [fromNoninstanciated];
  301. }
  302. internal override FieldInfo GetField (FieldInfo fromNoninstanciated)
  303. {
  304. initialize ();
  305. if (fields == null)
  306. fields = new Hashtable ();
  307. if (!fields.ContainsKey (fromNoninstanciated))
  308. fields [fromNoninstanciated] = new FieldOnTypeBuilderInst (this, fromNoninstanciated);
  309. return (FieldInfo)fields [fromNoninstanciated];
  310. }
  311. public override MethodInfo[] GetMethods (BindingFlags bf)
  312. {
  313. if (!IsCompilerContext)
  314. throw new NotSupportedException ();
  315. ArrayList l = new ArrayList ();
  316. //
  317. // Walk up our class hierarchy and retrieve methods from our
  318. // parent classes.
  319. //
  320. if (!(generic_type is TypeBuilder)) {
  321. foreach (var method in generic_type.GetMethods (bf)) {
  322. var m = method;
  323. if (m.DeclaringType.IsGenericTypeDefinition)
  324. m = TypeBuilder.GetMethod (this, m);
  325. l.Add (m);
  326. }
  327. } else {
  328. Type current_type = this;
  329. do {
  330. MonoGenericClass gi = current_type as MonoGenericClass;
  331. if (gi != null)
  332. l.AddRange (gi.GetMethodsInternal (bf, this));
  333. else if (current_type is TypeBuilder)
  334. l.AddRange (current_type.GetMethods (bf));
  335. else {
  336. // If we encounter a `MonoType', its
  337. // GetMethodsByName() will return all the methods
  338. // from its parent type(s), so we can stop here.
  339. MonoType mt = (MonoType) current_type;
  340. l.AddRange (mt.GetMethodsByName (null, bf, false, this));
  341. break;
  342. }
  343. if ((bf & BindingFlags.DeclaredOnly) != 0)
  344. break;
  345. current_type = current_type.BaseType;
  346. } while (current_type != null);
  347. }
  348. MethodInfo[] result = new MethodInfo [l.Count];
  349. l.CopyTo (result);
  350. return result;
  351. }
  352. MethodInfo[] GetMethodsInternal (BindingFlags bf, MonoGenericClass reftype)
  353. {
  354. if (reftype != this)
  355. bf |= BindingFlags.DeclaredOnly; /*To avoid duplicates*/
  356. MethodInfo[] methods = GetMethodsFromGTDWithHint (bf);
  357. if (methods.Length == 0)
  358. return new MethodInfo [0];
  359. ArrayList l = new ArrayList ();
  360. bool match;
  361. MethodAttributes mattrs;
  362. initialize ();
  363. for (int i = 0; i < methods.Length; ++i) {
  364. MethodInfo c = methods [i];
  365. match = false;
  366. mattrs = c.Attributes;
  367. if ((mattrs & MethodAttributes.MemberAccessMask) == MethodAttributes.Public) {
  368. if ((bf & BindingFlags.Public) != 0)
  369. match = true;
  370. } else {
  371. if ((bf & BindingFlags.NonPublic) != 0)
  372. match = true;
  373. }
  374. if (!match)
  375. continue;
  376. match = false;
  377. if ((mattrs & MethodAttributes.Static) != 0) {
  378. if ((bf & BindingFlags.Static) != 0)
  379. match = true;
  380. } else {
  381. if ((bf & BindingFlags.Instance) != 0)
  382. match = true;
  383. }
  384. if (!match)
  385. continue;
  386. if (c.DeclaringType.IsGenericTypeDefinition)
  387. c = TypeBuilder.GetMethod (this, c);
  388. l.Add (c);
  389. }
  390. MethodInfo[] result = new MethodInfo [l.Count];
  391. l.CopyTo (result);
  392. return result;
  393. }
  394. public override ConstructorInfo[] GetConstructors (BindingFlags bf)
  395. {
  396. if (!IsCompilerContext)
  397. throw new NotSupportedException ();
  398. ArrayList l = new ArrayList ();
  399. Type current_type = this;
  400. do {
  401. MonoGenericClass gi = current_type as MonoGenericClass;
  402. if (gi != null)
  403. l.AddRange (gi.GetConstructorsInternal (bf, this));
  404. else if (current_type is TypeBuilder)
  405. l.AddRange (current_type.GetConstructors (bf));
  406. else {
  407. MonoType mt = (MonoType) current_type;
  408. l.AddRange (mt.GetConstructors_internal (bf, this));
  409. break;
  410. }
  411. if ((bf & BindingFlags.DeclaredOnly) != 0)
  412. break;
  413. current_type = current_type.BaseType;
  414. } while (current_type != null);
  415. ConstructorInfo[] result = new ConstructorInfo [l.Count];
  416. l.CopyTo (result);
  417. return result;
  418. }
  419. ConstructorInfo[] GetConstructorsInternal (BindingFlags bf, MonoGenericClass reftype)
  420. {
  421. ConstructorInfo[] ctors = GetConstructorsFromGTDWithHint (bf);
  422. if (ctors == null || ctors.Length == 0)
  423. return new ConstructorInfo [0];
  424. ArrayList l = new ArrayList ();
  425. bool match;
  426. MethodAttributes mattrs;
  427. initialize ();
  428. for (int i = 0; i < ctors.Length; i++) {
  429. ConstructorInfo c = ctors [i];
  430. match = false;
  431. mattrs = c.Attributes;
  432. if ((mattrs & MethodAttributes.MemberAccessMask) == MethodAttributes.Public) {
  433. if ((bf & BindingFlags.Public) != 0)
  434. match = true;
  435. } else {
  436. if ((bf & BindingFlags.NonPublic) != 0)
  437. match = true;
  438. }
  439. if (!match)
  440. continue;
  441. match = false;
  442. if ((mattrs & MethodAttributes.Static) != 0) {
  443. if ((bf & BindingFlags.Static) != 0)
  444. match = true;
  445. } else {
  446. if ((bf & BindingFlags.Instance) != 0)
  447. match = true;
  448. }
  449. if (!match)
  450. continue;
  451. l.Add (TypeBuilder.GetConstructor (this, c));
  452. }
  453. ConstructorInfo[] result = new ConstructorInfo [l.Count];
  454. l.CopyTo (result);
  455. return result;
  456. }
  457. public override FieldInfo[] GetFields (BindingFlags bf)
  458. {
  459. if (!IsCompilerContext)
  460. throw new NotSupportedException ();
  461. ArrayList l = new ArrayList ();
  462. Type current_type = this;
  463. do {
  464. MonoGenericClass gi = current_type as MonoGenericClass;
  465. if (gi != null)
  466. l.AddRange (gi.GetFieldsInternal (bf, this));
  467. else if (current_type is TypeBuilder)
  468. l.AddRange (current_type.GetFields (bf));
  469. else {
  470. MonoType mt = (MonoType) current_type;
  471. l.AddRange (mt.GetFields_internal (bf, this));
  472. break;
  473. }
  474. if ((bf & BindingFlags.DeclaredOnly) != 0)
  475. break;
  476. current_type = current_type.BaseType;
  477. } while (current_type != null);
  478. FieldInfo[] result = new FieldInfo [l.Count];
  479. l.CopyTo (result);
  480. return result;
  481. }
  482. FieldInfo[] GetFieldsInternal (BindingFlags bf, MonoGenericClass reftype)
  483. {
  484. FieldInfo[] fields = GetFieldsFromGTD (bf);
  485. if (fields.Length == 0)
  486. return new FieldInfo [0];
  487. ArrayList l = new ArrayList ();
  488. bool match;
  489. FieldAttributes fattrs;
  490. initialize ();
  491. for (int i = 0; i < fields.Length; i++) {
  492. FieldInfo c = fields [i];
  493. match = false;
  494. fattrs = c.Attributes;
  495. if ((fattrs & FieldAttributes.FieldAccessMask) == FieldAttributes.Public) {
  496. if ((bf & BindingFlags.Public) != 0)
  497. match = true;
  498. } else {
  499. if ((bf & BindingFlags.NonPublic) != 0)
  500. match = true;
  501. }
  502. if (!match)
  503. continue;
  504. match = false;
  505. if ((fattrs & FieldAttributes.Static) != 0) {
  506. if ((bf & BindingFlags.Static) != 0)
  507. match = true;
  508. } else {
  509. if ((bf & BindingFlags.Instance) != 0)
  510. match = true;
  511. }
  512. if (!match)
  513. continue;
  514. l.Add (TypeBuilder.GetField (this, c));
  515. }
  516. FieldInfo[] result = new FieldInfo [l.Count];
  517. l.CopyTo (result);
  518. return result;
  519. }
  520. public override PropertyInfo[] GetProperties (BindingFlags bf)
  521. {
  522. if (!IsCompilerContext)
  523. throw new NotSupportedException ();
  524. ArrayList l = new ArrayList ();
  525. Type current_type = this;
  526. do {
  527. MonoGenericClass gi = current_type as MonoGenericClass;
  528. if (gi != null)
  529. l.AddRange (gi.GetPropertiesInternal (bf, this));
  530. else if (current_type is TypeBuilder)
  531. l.AddRange (current_type.GetProperties (bf));
  532. else {
  533. MonoType mt = (MonoType) current_type;
  534. l.AddRange (mt.GetPropertiesByName (null, bf, false, this));
  535. break;
  536. }
  537. if ((bf & BindingFlags.DeclaredOnly) != 0)
  538. break;
  539. current_type = current_type.BaseType;
  540. } while (current_type != null);
  541. PropertyInfo[] result = new PropertyInfo [l.Count];
  542. l.CopyTo (result);
  543. return result;
  544. }
  545. PropertyInfo[] GetPropertiesInternal (BindingFlags bf, MonoGenericClass reftype)
  546. {
  547. PropertyInfo[] props = GetPropertiesInternal (generic_type, bf);
  548. if (props == null || props.Length == 0)
  549. return new PropertyInfo [0];
  550. ArrayList l = new ArrayList ();
  551. bool match;
  552. MethodAttributes mattrs;
  553. MethodInfo accessor;
  554. initialize ();
  555. foreach (PropertyInfo pinfo in props) {
  556. match = false;
  557. accessor = pinfo.GetGetMethod (true);
  558. if (accessor == null)
  559. accessor = pinfo.GetSetMethod (true);
  560. if (accessor == null)
  561. continue;
  562. mattrs = accessor.Attributes;
  563. if ((mattrs & MethodAttributes.MemberAccessMask) == MethodAttributes.Public) {
  564. if ((bf & BindingFlags.Public) != 0)
  565. match = true;
  566. } else {
  567. if ((bf & BindingFlags.NonPublic) != 0)
  568. match = true;
  569. }
  570. if (!match)
  571. continue;
  572. match = false;
  573. if ((mattrs & MethodAttributes.Static) != 0) {
  574. if ((bf & BindingFlags.Static) != 0)
  575. match = true;
  576. } else {
  577. if ((bf & BindingFlags.Instance) != 0)
  578. match = true;
  579. }
  580. if (!match)
  581. continue;
  582. l.Add (new PropertyOnTypeBuilderInst (reftype, pinfo));
  583. }
  584. PropertyInfo[] result = new PropertyInfo [l.Count];
  585. l.CopyTo (result);
  586. return result;
  587. }
  588. public override EventInfo[] GetEvents (BindingFlags bf)
  589. {
  590. if (!IsCompilerContext)
  591. throw new NotSupportedException ();
  592. ArrayList l = new ArrayList ();
  593. Type current_type = this;
  594. do {
  595. MonoGenericClass gi = current_type as MonoGenericClass;
  596. if (gi != null)
  597. l.AddRange (gi.GetEventsInternal (bf, this));
  598. else if (current_type is TypeBuilder)
  599. l.AddRange (current_type.GetEvents (bf));
  600. else {
  601. MonoType mt = (MonoType) current_type;
  602. l.AddRange (mt.GetEvents (bf));
  603. break;
  604. }
  605. if ((bf & BindingFlags.DeclaredOnly) != 0)
  606. break;
  607. current_type = current_type.BaseType;
  608. } while (current_type != null);
  609. EventInfo[] result = new EventInfo [l.Count];
  610. l.CopyTo (result);
  611. return result;
  612. }
  613. EventInfo[] GetEventsInternal (BindingFlags bf, MonoGenericClass reftype) {
  614. TypeBuilder tb = generic_type as TypeBuilder;
  615. if (tb == null) {
  616. EventInfo[] res = generic_type.GetEvents (bf);
  617. for (int i = 0; i < res.Length; ++i)
  618. res [i] = new EventOnTypeBuilderInst (this, res [i]);
  619. return res;
  620. }
  621. EventBuilder[] events = tb.events;
  622. if (events == null || events.Length == 0)
  623. return new EventInfo [0];
  624. initialize ();
  625. ArrayList l = new ArrayList ();
  626. bool match;
  627. MethodAttributes mattrs;
  628. MethodInfo accessor;
  629. for (int i = 0; i < event_count; ++i) {
  630. EventBuilder ev = events [i];
  631. match = false;
  632. accessor = ev.add_method;
  633. if (accessor == null)
  634. accessor = ev.remove_method;
  635. if (accessor == null)
  636. continue;
  637. mattrs = accessor.Attributes;
  638. if ((mattrs & MethodAttributes.MemberAccessMask) == MethodAttributes.Public) {
  639. if ((bf & BindingFlags.Public) != 0)
  640. match = true;
  641. } else {
  642. if ((bf & BindingFlags.NonPublic) != 0)
  643. match = true;
  644. }
  645. if (!match)
  646. continue;
  647. match = false;
  648. if ((mattrs & MethodAttributes.Static) != 0) {
  649. if ((bf & BindingFlags.Static) != 0)
  650. match = true;
  651. } else {
  652. if ((bf & BindingFlags.Instance) != 0)
  653. match = true;
  654. }
  655. if (!match)
  656. continue;
  657. l.Add (new EventOnTypeBuilderInst (this, ev));
  658. }
  659. EventInfo[] result = new EventInfo [l.Count];
  660. l.CopyTo (result);
  661. return result;
  662. }
  663. public override Type[] GetNestedTypes (BindingFlags bf)
  664. {
  665. return generic_type.GetNestedTypes (bf);
  666. }
  667. public override bool IsAssignableFrom (Type c)
  668. {
  669. if (c == this)
  670. return true;
  671. Type[] interfaces = GetInterfacesInternal ();
  672. if (c.IsInterface) {
  673. if (interfaces == null)
  674. return false;
  675. foreach (Type t in interfaces)
  676. if (c.IsAssignableFrom (t))
  677. return true;
  678. return false;
  679. }
  680. Type parent = GetParentType ();
  681. if (parent == null)
  682. return c == typeof (object);
  683. else
  684. return c.IsAssignableFrom (parent);
  685. }
  686. public override Type UnderlyingSystemType {
  687. get { return this; }
  688. }
  689. public override Assembly Assembly {
  690. get { return generic_type.Assembly; }
  691. }
  692. public override Module Module {
  693. get { return generic_type.Module; }
  694. }
  695. public override string Name {
  696. get { return generic_type.Name; }
  697. }
  698. public override string Namespace {
  699. get { return generic_type.Namespace; }
  700. }
  701. public override string FullName {
  702. get { return format_name (true, false); }
  703. }
  704. public override string AssemblyQualifiedName {
  705. get { return format_name (true, true); }
  706. }
  707. public override Guid GUID {
  708. get { throw new NotSupportedException (); }
  709. }
  710. string format_name (bool full_name, bool assembly_qualified)
  711. {
  712. StringBuilder sb = new StringBuilder (generic_type.FullName);
  713. bool compiler_ctx = IsCompilerContext;
  714. sb.Append ("[");
  715. for (int i = 0; i < type_arguments.Length; ++i) {
  716. if (i > 0)
  717. sb.Append (",");
  718. string name;
  719. if (full_name) {
  720. string assemblyName = type_arguments [i].Assembly.FullName;
  721. name = type_arguments [i].FullName;
  722. if (name != null && assemblyName != null)
  723. name = name + ", " + assemblyName;
  724. } else {
  725. name = type_arguments [i].ToString ();
  726. }
  727. if (name == null) {
  728. if (compiler_ctx && type_arguments [i].IsGenericParameter)
  729. name = type_arguments [i].Name;
  730. else
  731. return null;
  732. }
  733. if (full_name)
  734. sb.Append ("[");
  735. sb.Append (name);
  736. if (full_name)
  737. sb.Append ("]");
  738. }
  739. sb.Append ("]");
  740. if (assembly_qualified) {
  741. sb.Append (", ");
  742. sb.Append (generic_type.Assembly.FullName);
  743. }
  744. return sb.ToString ();
  745. }
  746. public override string ToString ()
  747. {
  748. return format_name (false, false);
  749. }
  750. public override Type GetGenericTypeDefinition ()
  751. {
  752. return generic_type;
  753. }
  754. public override Type[] GetGenericArguments ()
  755. {
  756. Type[] ret = new Type [type_arguments.Length];
  757. type_arguments.CopyTo (ret, 0);
  758. return ret;
  759. }
  760. public override bool ContainsGenericParameters {
  761. get {
  762. /*FIXME remove this once compound types are not instantiated using MGC*/
  763. if (HasElementType)
  764. return GetElementType ().ContainsGenericParameters;
  765. foreach (Type t in type_arguments) {
  766. if (t.ContainsGenericParameters)
  767. return true;
  768. }
  769. return false;
  770. }
  771. }
  772. public override bool IsGenericTypeDefinition {
  773. get { return false; }
  774. }
  775. public override bool IsGenericType {
  776. get { return !HasElementType; }
  777. }
  778. public override Type DeclaringType {
  779. get { return InflateType (generic_type.DeclaringType); }
  780. }
  781. public override RuntimeTypeHandle TypeHandle {
  782. get {
  783. if (!IsCompilerContext)
  784. throw new NotSupportedException ();
  785. return _impl;
  786. }
  787. }
  788. public override Type MakeArrayType ()
  789. {
  790. return new ArrayType (this, 0);
  791. }
  792. public override Type MakeArrayType (int rank)
  793. {
  794. if (rank < 1)
  795. throw new IndexOutOfRangeException ();
  796. return new ArrayType (this, rank);
  797. }
  798. public override Type MakeByRefType ()
  799. {
  800. return new ByRefType (this);
  801. }
  802. public override Type MakePointerType ()
  803. {
  804. return new PointerType (this);
  805. }
  806. public override Type GetElementType ()
  807. {
  808. throw new NotSupportedException ();
  809. }
  810. protected override bool HasElementTypeImpl ()
  811. {
  812. return false;
  813. }
  814. protected override bool IsCOMObjectImpl ()
  815. {
  816. return false;
  817. }
  818. protected override bool IsPrimitiveImpl ()
  819. {
  820. return false;
  821. }
  822. protected override bool IsArrayImpl ()
  823. {
  824. return false;
  825. }
  826. protected override bool IsByRefImpl ()
  827. {
  828. return false;
  829. }
  830. protected override bool IsPointerImpl ()
  831. {
  832. return false;
  833. }
  834. protected override TypeAttributes GetAttributeFlagsImpl ()
  835. {
  836. return generic_type.Attributes;
  837. }
  838. //stuff that throws
  839. public override Type GetInterface (string name, bool ignoreCase)
  840. {
  841. throw new NotSupportedException ();
  842. }
  843. public override EventInfo GetEvent (string name, BindingFlags bindingAttr)
  844. {
  845. if (!IsCompilerContext)
  846. throw new NotSupportedException ();
  847. foreach (var evt in GetEvents (bindingAttr)) {
  848. if (evt.Name == name)
  849. return evt;
  850. }
  851. return null;
  852. }
  853. public override FieldInfo GetField( string name, BindingFlags bindingAttr)
  854. {
  855. throw new NotSupportedException ();
  856. }
  857. public override MemberInfo[] GetMembers (BindingFlags bindingAttr)
  858. {
  859. throw new NotSupportedException ();
  860. }
  861. public override Type GetNestedType (string name, BindingFlags bindingAttr)
  862. {
  863. throw new NotSupportedException ();
  864. }
  865. public override object InvokeMember (string name, BindingFlags invokeAttr,
  866. Binder binder, object target, object[] args,
  867. ParameterModifier[] modifiers,
  868. CultureInfo culture, string[] namedParameters)
  869. {
  870. throw new NotSupportedException ();
  871. }
  872. protected override MethodInfo GetMethodImpl (string name, BindingFlags bindingAttr, Binder binder,
  873. CallingConventions callConvention, Type[] types,
  874. ParameterModifier[] modifiers)
  875. {
  876. throw new NotSupportedException ();
  877. }
  878. protected override PropertyInfo GetPropertyImpl (string name, BindingFlags bindingAttr, Binder binder,
  879. Type returnType, Type[] types, ParameterModifier[] modifiers)
  880. {
  881. throw new NotSupportedException ();
  882. }
  883. protected override ConstructorInfo GetConstructorImpl (BindingFlags bindingAttr,
  884. Binder binder,
  885. CallingConventions callConvention,
  886. Type[] types,
  887. ParameterModifier[] modifiers)
  888. {
  889. if (!IsCompilerContext)
  890. throw new NotSupportedException ();
  891. return MonoType.GetConstructorImpl (GetConstructors (bindingAttr), bindingAttr, binder, callConvention, types, modifiers);
  892. }
  893. //MemberInfo
  894. public override bool IsDefined (Type attributeType, bool inherit)
  895. {
  896. if (!IsCompilerContext)
  897. throw new NotSupportedException ();
  898. return generic_type.IsDefined (attributeType, inherit);
  899. }
  900. public override object [] GetCustomAttributes (bool inherit)
  901. {
  902. if (!IsCompilerContext)
  903. throw new NotSupportedException ();
  904. return generic_type.GetCustomAttributes (inherit);
  905. }
  906. public override object [] GetCustomAttributes (Type attributeType, bool inherit)
  907. {
  908. if (!IsCompilerContext)
  909. throw new NotSupportedException ();
  910. return generic_type.GetCustomAttributes (attributeType, inherit);
  911. }
  912. }
  913. }