merged Sys.Web.Services 2.0 support in my branch:
[mono.git] / mcs / class / corlib / System.Reflection / Assembly.cs
1 //
2 // System.Reflection/Assembly.cs
3 //
4 // Author:
5 //   Paolo Molaro (lupus@ximian.com)
6 //
7 // (C) 2001 Ximian, Inc.  http://www.ximian.com
8 // Copyright (C) 2004-2005 Novell, Inc (http://www.novell.com)
9 //
10 // Permission is hereby granted, free of charge, to any person obtaining
11 // a copy of this software and associated documentation files (the
12 // "Software"), to deal in the Software without restriction, including
13 // without limitation the rights to use, copy, modify, merge, publish,
14 // distribute, sublicense, and/or sell copies of the Software, and to
15 // permit persons to whom the Software is furnished to do so, subject to
16 // the following conditions:
17 // 
18 // The above copyright notice and this permission notice shall be
19 // included in all copies or substantial portions of the Software.
20 // 
21 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
22 // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
23 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
24 // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
25 // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
26 // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
27 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
28 //
29
30 using System.Security;
31 using System.Security.Policy;
32 using System.Security.Permissions;
33 using System.Runtime.Serialization;
34 using System.Reflection.Emit;
35 using System.IO;
36 using System.Globalization;
37 using System.Runtime.CompilerServices;
38 using System.Runtime.InteropServices;
39 using System.Collections;
40 using System.Configuration.Assemblies;
41
42 using Mono.Security;
43
44 namespace System.Reflection {
45
46 #if NET_2_0
47         [ComVisible (true)]
48         [ComDefaultInterfaceAttribute (typeof (_Assembly))]
49 #endif
50         [Serializable]
51         [ClassInterface(ClassInterfaceType.None)]
52         public class Assembly : System.Reflection.ICustomAttributeProvider, _Assembly,
53                 System.Security.IEvidenceFactory, System.Runtime.Serialization.ISerializable {
54
55                 internal class ResolveEventHolder {
56                         public event ModuleResolveEventHandler ModuleResolve;
57                 }
58
59                 // Note: changes to fields must be reflected in _MonoReflectionAssembly struct (object-internals.h)
60                 private IntPtr _mono_assembly;
61
62                 private ResolveEventHolder resolve_event_holder;
63                 private Evidence _evidence;
64                 internal PermissionSet _minimum;        // for SecurityAction.RequestMinimum
65                 internal PermissionSet _optional;       // for SecurityAction.RequestOptional
66                 internal PermissionSet _refuse;         // for SecurityAction.RequestRefuse
67                 private PermissionSet _granted;         // for the resolved assembly granted permissions
68                 private PermissionSet _denied;          // for the resolved assembly denied permissions
69                 private bool fromByteArray;
70                 private string assemblyName;
71
72                 internal Assembly () 
73                 {
74                         resolve_event_holder = new ResolveEventHolder ();
75                 }
76
77                 //
78                 // We can't store the event directly in this class, since the
79                 // compiler would silently insert the fields before _mono_assembly
80                 //
81                 public event ModuleResolveEventHandler ModuleResolve {
82                         [SecurityPermission (SecurityAction.LinkDemand, ControlAppDomain = true)]
83                         add {
84                                 resolve_event_holder.ModuleResolve += value;
85                         }
86                         [SecurityPermission (SecurityAction.LinkDemand, ControlAppDomain = true)]
87                         remove {
88                                 resolve_event_holder.ModuleResolve -= value;
89                         }
90                 }
91
92                 [MethodImplAttribute (MethodImplOptions.InternalCall)]
93                 private extern string get_code_base (bool escaped);
94
95                 [MethodImplAttribute (MethodImplOptions.InternalCall)]
96                 private extern string get_location ();
97
98                 [MethodImplAttribute (MethodImplOptions.InternalCall)]
99                 private extern string InternalImageRuntimeVersion ();
100
101                 [MethodImplAttribute (MethodImplOptions.InternalCall)]
102                 private extern bool get_global_assembly_cache ();
103
104                 // SECURITY: this should be the only caller to icall get_code_base
105                 private string GetCodeBase (bool escaped)
106                 {
107                         string cb = get_code_base (escaped);
108                         if (SecurityManager.SecurityEnabled) {
109                                 // we cannot divulge local file informations
110                                 if (String.Compare ("FILE://", 0, cb, 0, 7, true, CultureInfo.InvariantCulture) == 0) {
111                                         string file = cb.Substring (7);
112                                         new FileIOPermission (FileIOPermissionAccess.PathDiscovery, file).Demand ();
113                                 }
114                         }
115                         return cb;
116                 }
117
118                 public virtual string CodeBase {
119                         get { return GetCodeBase (false); }
120                 }
121
122                 public virtual string EscapedCodeBase {
123                         get { return GetCodeBase (true); }
124                 }
125
126                 public virtual string FullName {
127                         get {
128                                 //
129                                 // FIXME: This is wrong, but it gets us going
130                                 // in the compiler for now
131                                 //
132                                 return ToString ();
133                         }
134                 }
135
136                 public virtual extern MethodInfo EntryPoint {
137                         [MethodImplAttribute (MethodImplOptions.InternalCall)]
138                         get;
139                 }
140
141                 public virtual Evidence Evidence {
142                         [SecurityPermission (SecurityAction.Demand, ControlEvidence = true)]
143                         get { return UnprotectedGetEvidence (); }
144                 }
145
146                 // note: the security runtime requires evidences but may be unable to do so...
147                 internal Evidence UnprotectedGetEvidence ()
148                 {
149                         // if the host (runtime) hasn't provided it's own evidence...
150                         if (_evidence == null) {
151                                 // ... we will provide our own
152                                 lock (this) {
153                                         _evidence = Evidence.GetDefaultHostEvidence (this);
154                                 }
155                         }
156                         return _evidence;
157                 }
158
159                 public bool GlobalAssemblyCache {
160                         get {
161                                 return get_global_assembly_cache ();
162                         }
163                 }
164
165                 internal bool FromByteArray {
166                         set { fromByteArray = true; }
167                 }
168
169                 public virtual String Location {
170                         get {
171                                 if (fromByteArray)
172                                         return String.Empty;
173
174                                 string loc = get_location ();
175                                 if ((loc != String.Empty) && SecurityManager.SecurityEnabled) {
176                                         // we cannot divulge local file informations
177                                         new FileIOPermission (FileIOPermissionAccess.PathDiscovery, loc).Demand ();
178                                 }
179                                 return loc;
180                         }
181                 }
182
183 #if NET_1_1
184                 [ComVisible (false)]
185                 public virtual string ImageRuntimeVersion {
186                         get {
187                                 return InternalImageRuntimeVersion ();
188                         }
189                 }
190 #endif
191
192                 [SecurityPermission (SecurityAction.LinkDemand, SerializationFormatter = true)]
193                 public virtual void GetObjectData (SerializationInfo info, StreamingContext context)
194                 {
195                         if (info == null)
196                                 throw new ArgumentNullException ("info");
197
198                         UnitySerializationHolder.GetAssemblyData (this, info, context);
199                 }
200
201 #if ONLY_1_1
202                 public new Type GetType ()
203                 {
204                         return base.GetType ();
205                 }
206 #endif
207
208                 public virtual bool IsDefined (Type attributeType, bool inherit)
209                 {
210                         return MonoCustomAttrs.IsDefined (this, attributeType, inherit);
211                 }
212
213                 public virtual object [] GetCustomAttributes (bool inherit)
214                 {
215                         return MonoCustomAttrs.GetCustomAttributes (this, inherit);
216                 }
217
218                 public virtual object [] GetCustomAttributes (Type attributeType, bool inherit)
219                 {
220                         return MonoCustomAttrs.GetCustomAttributes (this, attributeType, inherit);
221                 }
222
223                 [MethodImplAttribute (MethodImplOptions.InternalCall)]
224                 private extern object GetFilesInternal (String name, bool getResourceModules);
225
226                 public virtual FileStream[] GetFiles ()
227                 {
228                         return GetFiles (false);
229                 }
230
231                 public virtual FileStream [] GetFiles (bool getResourceModules)
232                 {
233                         string[] names = (string[]) GetFilesInternal (null, getResourceModules);
234                         if (names == null)
235                                 return new FileStream [0];
236
237                         FileStream[] res = new FileStream [names.Length];
238                         for (int i = 0; i < names.Length; ++i)
239                                 res [i] = new FileStream (names [i], FileMode.Open, FileAccess.Read);
240                         return res;
241                 }
242
243                 public virtual FileStream GetFile (String name)
244                 {
245                         if (name == null)
246                                 throw new ArgumentNullException ("name");
247                         if (name.Length == 0)
248                                 throw new ArgumentException ("name");
249
250                         string filename = (string)GetFilesInternal (name, true);
251                         if (filename != null)
252                                 return new FileStream (filename, FileMode.Open, FileAccess.Read);
253                         else
254                                 return null;
255                 }
256
257                 [MethodImplAttribute (MethodImplOptions.InternalCall)]
258                 internal extern IntPtr GetManifestResourceInternal (String name, out int size, out Module module);
259
260                 public virtual Stream GetManifestResourceStream (String name)
261                 {
262                         if (name == null)
263                                 throw new ArgumentNullException ("name");
264                         if (name == "")
265                                 throw new ArgumentException ("name cannot have zero length.");
266
267                         ManifestResourceInfo info = GetManifestResourceInfo (name);
268                         if (info == null)
269                                 return null;
270
271                         if (info.ReferencedAssembly != null)
272                                 return info.ReferencedAssembly.GetManifestResourceStream (name);
273                         if ((info.FileName != null) && (info.ResourceLocation == 0)) {
274                                 if (fromByteArray)
275 #if NET_2_0
276                                         throw new FileNotFoundException (info.FileName);
277 #else
278                                         return null;
279 #endif
280
281                                 string filename = Path.Combine (Path.GetDirectoryName (Location),
282                                                                                         info.FileName);
283                                 return new FileStream (filename, FileMode.Open, FileAccess.Read);
284                         }
285
286                         int size;
287                         Module module;
288                         IntPtr data = GetManifestResourceInternal (name, out size, out module);
289                         if (data == (IntPtr) 0)
290                                 return null;
291                         else {
292                                 IntPtrStream stream = new IntPtrStream (data, size);
293                                 /* 
294                                  * The returned pointer points inside metadata, so
295                                  * we have to increase the refcount of the module, and decrease
296                                  * it when the stream is finalized.
297                                  */
298                                 stream.Closed += new EventHandler (new ResourceCloseHandler (module).OnClose);
299                                 return stream;
300                         }
301                 }
302
303                 public virtual Stream GetManifestResourceStream (Type type, String name)
304                 {
305                         string ns;
306                         if (type != null)
307                                 ns = type.Namespace;
308                         else 
309                                 ns = null;
310
311                         if ((ns == null) || (ns == ""))
312                                 return GetManifestResourceStream (name);
313                         else
314                                 return GetManifestResourceStream (ns + "." + name);
315                 }
316
317                 [MethodImplAttribute (MethodImplOptions.InternalCall)]
318                 private extern Type[] GetTypes (bool exportedOnly);
319                 
320                 public virtual Type[] GetTypes ()
321                 {
322                         return GetTypes (false);
323                 }
324
325                 public virtual Type[] GetExportedTypes ()
326                 {
327                         return GetTypes (true);
328                 }
329
330                 public virtual Type GetType (String name, Boolean throwOnError)
331                 {
332                         return GetType (name, throwOnError, false);
333                 }
334
335                 public virtual Type GetType (String name) {
336                         return GetType (name, false, false);
337                 }
338
339                 [MethodImplAttribute (MethodImplOptions.InternalCall)]
340                 internal extern Type InternalGetType (Module module, String name, Boolean throwOnError, Boolean ignoreCase);
341
342                 public Type GetType (string name, bool throwOnError, bool ignoreCase)
343                 {
344                         if (name == null)
345                                 throw new ArgumentNullException (name);
346
347                         return InternalGetType (null, name, throwOnError, ignoreCase);
348                 }
349
350                 [MethodImplAttribute (MethodImplOptions.InternalCall)]
351                 internal extern static void InternalGetAssemblyName (string assemblyFile, AssemblyName aname);
352                 
353                 [MethodImplAttribute (MethodImplOptions.InternalCall)]
354                 static extern void FillName (Assembly ass, AssemblyName aname);
355
356                 [MonoTODO ("copiedName == true is not supported")]
357                 public virtual AssemblyName GetName (Boolean copiedName)
358                 {
359                         // CodeBase, which is restricted, will be copied into the AssemblyName object so...
360                         if (SecurityManager.SecurityEnabled) {
361                                 GetCodeBase (true); // this will ensure the Demand is made
362                         }
363                         return UnprotectedGetName ();
364                 }
365
366                 public virtual AssemblyName GetName ()
367                 {
368                         return GetName (false);
369                 }
370
371                 // the security runtime requires access to the assemblyname (e.g. to get the strongname)
372                 internal virtual AssemblyName UnprotectedGetName ()
373                 {
374                         AssemblyName aname = new AssemblyName ();
375                         FillName (this, aname);
376                         return aname;
377                 }
378
379                 public override string ToString ()
380                 {
381                         // note: ToString work without requiring CodeBase (so no checks are needed)
382
383                         if (assemblyName != null)
384                                 return assemblyName;
385
386                         AssemblyName aname = new AssemblyName ();
387                         FillName (this, aname);
388                         assemblyName = aname.ToString ();
389
390                         return assemblyName;
391                 }
392
393                 public static String CreateQualifiedName (String assemblyName, String typeName) 
394                 {
395                         return typeName + ", " + assemblyName;
396                 }
397
398                 public static Assembly GetAssembly (Type type)
399                 {
400                         if (type != null)
401                                 return type.Assembly;
402                         throw new ArgumentNullException ("type");
403                 }
404
405
406                 [MethodImplAttribute (MethodImplOptions.InternalCall)]
407                 public static extern Assembly GetEntryAssembly();
408
409                 public Assembly GetSatelliteAssembly (CultureInfo culture)
410                 {
411                         return GetSatelliteAssembly (culture, null);
412                 }
413
414                 public Assembly GetSatelliteAssembly (CultureInfo culture, Version version)
415                 {
416                         if (culture == null)
417                                 throw new ArgumentException ("culture");
418
419                         AssemblyName aname = GetName (true);
420                         if (version != null)
421                                 aname.Version = version;
422
423                         aname.CultureInfo = culture;
424                         aname.Name = aname.Name + ".resources";
425                         return Load (aname);
426                 }
427                 
428                 [MethodImplAttribute (MethodImplOptions.InternalCall)]
429                 private extern static Assembly LoadFrom (String assemblyFile, bool refonly);
430
431                 public static Assembly LoadFrom (String assemblyFile)
432                 {
433                         return LoadFrom (assemblyFile, false);
434                 }
435
436                 public static Assembly LoadFrom (String assemblyFile, Evidence securityEvidence)
437                 {
438                         Assembly a = LoadFrom (assemblyFile, false);
439                         if ((a != null) && (securityEvidence != null)) {
440                                 // merge evidence (i.e. replace defaults with provided evidences)
441                                 a.Evidence.Merge (securityEvidence);
442                         }
443                         return a;
444                 }
445
446 #if NET_1_1
447
448                 [MonoTODO("This overload is not currently implemented")]
449                 // FIXME: What are we missing?
450                 public static Assembly LoadFrom (String assemblyFile, Evidence securityEvidence, byte[] hashValue, AssemblyHashAlgorithm hashAlgorithm)
451                 {
452                         if (assemblyFile == null)
453                                 throw new ArgumentNullException ("assemblyFile");
454                         if (assemblyFile == String.Empty)
455                                 throw new ArgumentException ("Name can't be the empty string", "assemblyFile");
456                         throw new NotImplementedException ();
457                 }
458
459                 public static Assembly LoadFile (String path, Evidence securityEvidence)
460                 {
461                         if (path == null)
462                                 throw new ArgumentNullException ("path");
463                         if (path == String.Empty)
464                                 throw new ArgumentException ("Path can't be empty", "path");
465                         // FIXME: Make this do the right thing
466                         return LoadFrom (path, securityEvidence);
467                 }
468
469                 public static Assembly LoadFile (String path)
470                 {
471                         return LoadFile (path, null);
472                 }
473 #endif
474
475                 public static Assembly Load (String assemblyString)
476                 {
477                         return AppDomain.CurrentDomain.Load (assemblyString);
478                 }
479                 
480                 public static Assembly Load (String assemblyString, Evidence assemblySecurity)
481                 {
482                         return AppDomain.CurrentDomain.Load (assemblyString, assemblySecurity);
483                 }
484
485                 public static Assembly Load (AssemblyName assemblyRef)
486                 {
487                         return AppDomain.CurrentDomain.Load (assemblyRef);
488                 }
489
490                 public static Assembly Load (AssemblyName assemblyRef, Evidence assemblySecurity)
491                 {
492                         return AppDomain.CurrentDomain.Load (assemblyRef, assemblySecurity);
493                 }
494
495                 public static Assembly Load (Byte[] rawAssembly)
496                 {
497                         return AppDomain.CurrentDomain.Load (rawAssembly);
498                 }
499
500                 public static Assembly Load (Byte[] rawAssembly, Byte[] rawSymbolStore)
501                 {
502                         return AppDomain.CurrentDomain.Load (rawAssembly, rawSymbolStore);
503                 }
504
505                 public static Assembly Load (Byte[] rawAssembly, Byte[] rawSymbolStore,
506                                              Evidence securityEvidence)
507                 {
508                         return AppDomain.CurrentDomain.Load (rawAssembly, rawSymbolStore, securityEvidence);
509                 }
510
511 #if NET_2_0
512                 public static Assembly ReflectionOnlyLoad (byte[] rawAssembly)
513                 {
514                         return AppDomain.CurrentDomain.Load (rawAssembly, null, null, true);
515                 }
516
517                 public static Assembly ReflectionOnlyLoad (string assemblyName) 
518                 {
519                         return AppDomain.CurrentDomain.Load (assemblyName, null, true);
520                 }
521
522                 public static Assembly ReflectionOnlyLoadFrom (string assemblyFile) 
523                 {
524                         if (assemblyFile == null)
525                                 throw new ArgumentNullException ("assemblyFile");
526                         
527                         return LoadFrom (assemblyFile, true);
528                 }
529 #endif
530
531 #if NET_2_0
532                 [Obsolete ("")]
533 #endif
534                 public static Assembly LoadWithPartialName (string partialName)
535                 {
536                         return LoadWithPartialName (partialName, null);
537                 }
538
539                 [MonoTODO ("Not implemented")]
540                 public Module LoadModule (string moduleName, byte [] rawModule)
541                 {
542                         throw new NotImplementedException ();
543                 }
544
545                 [MonoTODO ("Not implemented")]
546                 public Module LoadModule (string moduleName, byte [] rawModule, byte [] rawSymbolStore)
547                 {
548                         throw new NotImplementedException ();
549                 }
550
551                 [MethodImplAttribute (MethodImplOptions.InternalCall)]
552                 private static extern Assembly load_with_partial_name (string name, Evidence e);
553
554 #if NET_2_0
555                 [Obsolete ("")]
556 #endif
557                 public static Assembly LoadWithPartialName (string partialName, Evidence securityEvidence)
558                 {
559                         return LoadWithPartialName (partialName, securityEvidence, true);
560                 }
561
562                 /**
563                  * LAMESPEC: It is possible for this method to throw exceptions IF the name supplied
564                  * is a valid gac name and contains filesystem entry charachters at the end of the name
565                  * ie System/// will throw an exception. However ////System will not as that is canocolized
566                  * out of the name.
567                  */
568
569                 // FIXME: LoadWithPartialName must look cache (no CAS) or read from disk (CAS)
570                 internal static Assembly LoadWithPartialName (string partialName, Evidence securityEvidence, bool oldBehavior)
571                 {
572                         if (!oldBehavior)
573                                 throw new NotImplementedException ();
574
575                         if (partialName == null)
576                                 throw new NullReferenceException ();
577
578                         return load_with_partial_name (partialName, securityEvidence);
579                 }
580
581                 public Object CreateInstance (String typeName) 
582                 {
583                         return CreateInstance (typeName, false);
584                 }
585
586                 public Object CreateInstance (String typeName, Boolean ignoreCase)
587                 {
588                         Type t = GetType (typeName, false, ignoreCase);
589                         if (t == null)
590                                 return null;
591
592                         try {
593                                 return Activator.CreateInstance (t);
594                         } catch (InvalidOperationException) {
595                                 throw new ArgumentException ("It is illegal to invoke a method on a Type loaded via ReflectionOnly methods.");
596                         }
597                 }
598
599                 public Object CreateInstance (String typeName, Boolean ignoreCase,
600                                               BindingFlags bindingAttr, Binder binder,
601                                               Object[] args, CultureInfo culture,
602                                               Object[] activationAttributes)
603                 {
604                         Type t = GetType (typeName, false, ignoreCase);
605                         if (t == null)
606                                 return null;
607
608                         try {
609                                 return Activator.CreateInstance (t, bindingAttr, binder, args, culture, activationAttributes);
610                         } catch (InvalidOperationException) {
611                                 throw new ArgumentException ("It is illegal to invoke a method on a Type loaded via ReflectionOnly methods.");
612                         }
613                 }
614
615                 public Module[] GetLoadedModules ()
616                 {
617                         return GetLoadedModules (false);
618                 }
619
620                 // FIXME: Currently, the two sets of modules are equal
621                 public Module[] GetLoadedModules (bool getResourceModules)
622                 {
623                         return GetModules (getResourceModules);
624                 }
625
626                 public Module[] GetModules ()
627                 {
628                         return GetModules (false);
629                 }
630
631                 public Module GetModule (String name)
632                 {
633                         if (name == null)
634                                 throw new ArgumentNullException ("name");
635                         if (name == "")
636                                 throw new ArgumentException ("Name can't be empty");
637
638                         Module[] modules = GetModules (true);
639                         foreach (Module module in modules) {
640                                 if (module.ScopeName == name)
641                                         return module;
642                         }
643
644                         return null;
645                 }
646
647                 [MethodImplAttribute (MethodImplOptions.InternalCall)]
648                 internal extern Module[] GetModulesInternal ();
649
650                 public Module[] GetModules (bool getResourceModules) {
651                         Module[] modules = GetModulesInternal ();
652
653                         if (!getResourceModules) {
654                                 ArrayList result = new ArrayList (modules.Length);
655                                 foreach (Module m in modules)
656                                         if (!m.IsResource ())
657                                                 result.Add (m);
658                                 return (Module[])result.ToArray (typeof (Module));
659                         }
660                         else
661                                 return modules;
662                 }
663
664                 [MethodImplAttribute (MethodImplOptions.InternalCall)]
665                 internal extern string[] GetNamespaces ();
666                 
667                 [MethodImplAttribute (MethodImplOptions.InternalCall)]
668                 public extern virtual String[] GetManifestResourceNames ();
669
670                 [MethodImplAttribute (MethodImplOptions.InternalCall)]
671                 public extern static Assembly GetExecutingAssembly ();
672
673                 [MethodImplAttribute (MethodImplOptions.InternalCall)]
674                 public extern static Assembly GetCallingAssembly ();
675
676                 [MethodImplAttribute (MethodImplOptions.InternalCall)]
677                 public extern AssemblyName[] GetReferencedAssemblies ();
678
679                 [MethodImplAttribute (MethodImplOptions.InternalCall)]
680                 private extern bool GetManifestResourceInfoInternal (String name, ManifestResourceInfo info);
681
682                 public virtual ManifestResourceInfo GetManifestResourceInfo (String resourceName)
683                 {
684                         if (resourceName == null)
685                                 throw new ArgumentNullException ("resourceName");
686                         if (resourceName == "")
687                                 throw new ArgumentException ("String cannot have zero length.");
688                         ManifestResourceInfo result = new ManifestResourceInfo ();
689                         bool found = GetManifestResourceInfoInternal (resourceName, result);
690                         if (found)
691                                 return result;
692                         else
693                                 return null;
694                 }
695
696                 private class ResourceCloseHandler {
697
698                         Module module;
699
700                         public ResourceCloseHandler (Module module) {
701                                 this.module = module;
702                         }
703
704                         public void OnClose (object sender, EventArgs e) {
705                                 // The module dtor will take care of things
706                                 module = null;
707                         }
708                 }
709
710                 //
711                 // The following functions are only for the Mono Debugger.
712                 //
713
714                 [MethodImplAttribute (MethodImplOptions.InternalCall)]
715                 internal static extern int MonoDebugger_GetMethodToken (MethodBase method);
716
717 #if NET_2_0
718                 [MonoTODO ("Always returns zero")]
719                 [ComVisible (false)]
720                 public long HostContext {
721                         get { return 0; }
722                 }
723
724                 [ComVisible (false)]
725                 public extern Module ManifestModule {
726                         [MethodImplAttribute (MethodImplOptions.InternalCall)]
727                         get;
728                 }
729
730                 [ComVisible (false)]
731                 public virtual extern bool ReflectionOnly {
732                         [MethodImplAttribute (MethodImplOptions.InternalCall)]
733                         get;
734                 }
735 #endif
736
737                 // Code Access Security
738
739                 internal void Resolve () 
740                 {
741                         lock (this) {
742                                 // FIXME: As we (currently) delay the resolution until the first CAS
743                                 // Demand it's too late to evaluate the Minimum permission set as a 
744                                 // condition to load the assembly into the AppDomain
745                                 LoadAssemblyPermissions ();
746                                 Evidence e = new Evidence (UnprotectedGetEvidence ()); // we need a copy to add PRE
747                                 e.AddHost (new PermissionRequestEvidence (_minimum, _optional, _refuse));
748                                 _granted = SecurityManager.ResolvePolicy (e,
749                                         _minimum, _optional, _refuse, out _denied);
750                         }
751                 }
752
753                 internal PermissionSet GrantedPermissionSet {
754                         get {
755                                 if (_granted == null) {
756                                         if (SecurityManager.ResolvingPolicyLevel != null) {
757                                                 if (SecurityManager.ResolvingPolicyLevel.IsFullTrustAssembly (this))
758                                                         return DefaultPolicies.FullTrust;
759                                                 else
760                                                         return null; // we can't resolve during resolution
761                                         }
762                                         Resolve ();
763                                 }
764                                 return _granted;
765                         }
766                 }
767
768                 internal PermissionSet DeniedPermissionSet {
769                         get {
770                                 // yes we look for granted, as denied may be null
771                                 if (_granted == null) {
772                                         if (SecurityManager.ResolvingPolicyLevel != null) {
773                                                 if (SecurityManager.ResolvingPolicyLevel.IsFullTrustAssembly (this))
774                                                         return null;
775                                                 else
776                                                         return DefaultPolicies.FullTrust; // deny unrestricted
777                                         }
778                                         Resolve ();
779                                 }
780                                 return _denied;
781                         }
782                 }
783
784                 [MethodImplAttribute (MethodImplOptions.InternalCall)]
785                 extern internal static bool LoadPermissions (Assembly a, 
786                         ref IntPtr minimum, ref int minLength,
787                         ref IntPtr optional, ref int optLength,
788                         ref IntPtr refused, ref int refLength);
789
790                 // Support for SecurityAction.RequestMinimum, RequestOptional and RequestRefuse
791                 private void LoadAssemblyPermissions ()
792                 {
793                         IntPtr minimum = IntPtr.Zero, optional = IntPtr.Zero, refused = IntPtr.Zero;
794                         int minLength = 0, optLength = 0, refLength = 0;
795                         if (LoadPermissions (this, ref minimum, ref minLength, ref optional,
796                                 ref optLength, ref refused, ref refLength)) {
797
798                                 // Note: no need to cache these permission sets as they will only be created once
799                                 // at assembly resolution time.
800                                 if (minLength > 0) {
801                                         byte[] data = new byte [minLength];
802                                         Marshal.Copy (minimum, data, 0, minLength);
803                                         _minimum = SecurityManager.Decode (data);
804                                 }
805                                 if (optLength > 0) {
806                                         byte[] data = new byte [optLength];
807                                         Marshal.Copy (optional, data, 0, optLength);
808                                         _optional = SecurityManager.Decode (data);
809                                 }
810                                 if (refLength > 0) {
811                                         byte[] data = new byte [refLength];
812                                         Marshal.Copy (refused, data, 0, refLength);
813                                         _refuse = SecurityManager.Decode (data);
814                                 }
815                         }
816                 }
817         }
818 }