LoadContext.cs 2.6 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798
  1. using System;
  2. using System.Collections.Concurrent;
  3. using System.Collections.Generic;
  4. using System.IO;
  5. using System.Reflection;
  6. using System.Threading;
  7. //#if DNXCORE50
  8. using System.Runtime.Loader;
  9. //#endif
  10. namespace Atomic.Bootstrap
  11. {
  12. public abstract class LoadContext : AssemblyLoadContext, IAssemblyLoadContext
  13. {
  14. private readonly AssemblyLoaderCache _cache = new AssemblyLoaderCache();
  15. private readonly string _friendlyName;
  16. public LoadContext()
  17. {
  18. }
  19. public LoadContext(string friendlyName)
  20. {
  21. _friendlyName = friendlyName;
  22. }
  23. protected override Assembly Load(AssemblyName assemblyName)
  24. {
  25. return _cache.GetOrAdd(assemblyName, LoadAssembly);
  26. }
  27. Assembly IAssemblyLoadContext.Load(AssemblyName assemblyName)
  28. {
  29. return LoadFromAssemblyName(assemblyName);
  30. }
  31. public abstract Assembly LoadAssembly(AssemblyName assemblyName);
  32. public Assembly LoadFile(string path)
  33. {
  34. // Look for platform specific native image
  35. string nativeImagePath = GetNativeImagePath(path);
  36. if (nativeImagePath != null)
  37. {
  38. return LoadFromNativeImagePath(nativeImagePath, path);
  39. }
  40. return LoadFromAssemblyPath(path);
  41. }
  42. public Assembly LoadStream(Stream assembly, Stream assemblySymbols)
  43. {
  44. if (assemblySymbols == null)
  45. {
  46. return LoadFromStream(assembly);
  47. }
  48. return LoadFromStream(assembly, assemblySymbols);
  49. }
  50. public static void InitializeDefaultContext(LoadContext loadContext)
  51. {
  52. AssemblyLoadContext.InitializeDefaultContext(loadContext);
  53. }
  54. private string GetNativeImagePath(string ilPath)
  55. {
  56. var directory = Path.GetDirectoryName(ilPath);
  57. var arch = IntPtr.Size == 4 ? "x86" : "AMD64";
  58. var nativeImageName = Path.GetFileNameWithoutExtension(ilPath) + ".ni.dll";
  59. var nativePath = Path.Combine(directory, arch, nativeImageName);
  60. if (File.Exists(nativePath))
  61. {
  62. return nativePath;
  63. }
  64. else
  65. {
  66. // Runtime is arch sensitive so the ni is in the same folder as IL
  67. nativePath = Path.Combine(directory, nativeImageName);
  68. if (File.Exists(nativePath))
  69. {
  70. return nativePath;
  71. }
  72. }
  73. return null;
  74. }
  75. public virtual void Dispose()
  76. {
  77. }
  78. }
  79. }