using System;
using System.Collections.Concurrent;
using System.Collections.Generic;
using System.Diagnostics.Contracts;
using System.IO;
using System.Linq;
using System.Reflection;
using System.Text;
using System.Threading;
using System.Threading.Tasks; namespace System
{
partial class App
{
private class InjectItem
{
private ConcurrentDictionary<Guid, Assembly> _mapper; public AppDomain Domain { get; private set; }
public ConcurrentDictionary<Guid, Assembly> Mapper
{
get { return _mapper; }
} public InjectItem(AppDomain domain)
{
this.Domain = domain;
_mapper = new ConcurrentDictionary<Guid, Assembly>();
}
} private static SynchronizedCollection<InjectItem> _injectSet = new SynchronizedCollection<InjectItem>(); private static InjectItem CallInject(string domainName)
{
if (_injectSet == null)
{
var set = new SynchronizedCollection<InjectItem>();
set.Add(new InjectItem(AppDomain.CurrentDomain));
Interlocked.CompareExchange(ref _injectSet, set, null);
}
if (string.IsNullOrEmpty(domainName))
{
return _injectSet.First();
} domainName = string.Format("_{0}", domainName);
var q = from t in _injectSet
where t.Domain.FriendlyName == domainName
select t;
var item = q.SingleOrDefault();
if (item == null)
{
_injectSet.Add(item = new InjectItem(AppDomain.CreateDomain(domainName)));
}
return item;
} public static Assembly Inject(Guid checksum, object arg, Stream rawStream = null, string domainName = null)
{
Contract.Requires(checksum != Guid.Empty); var item = CallInject(domainName);
if (rawStream != null)
{
var raw = new MemoryStream();
rawStream.FixedCopyTo(raw);
raw.Position = 0L;
Guid checksumNew = CryptoManaged.MD5Hash(raw);
if (checksum != checksumNew)
{
throw new InvalidOperationException("checksum");
}
return item.Mapper.GetOrAdd(checksum, k => item.Domain.Load(raw.ToArray()));
}
Assembly ass;
if (!item.Mapper.TryGetValue(checksum, out ass))
{
throw new InvalidOperationException("checksum");
}
Type entryType = ass.GetType(string.Format("{0}.Program", ass.FullName), false);
if (entryType == null)
{
var eType = typeof(IAppEntry);
var q = from t in ass.GetTypes()
where t.IsSubclassOf(eType)
select t;
entryType = q.FirstOrDefault();
}
if (entryType != null)
{
var creator = entryType.GetConstructor(Type.EmptyTypes);
if (creator != null)
{
var entry = (IAppEntry)creator.Invoke(null);
try
{
entry.Main(arg);
}
catch (Exception ex)
{
LogError(ex, "Inject");
#if DEBUG
throw;
#endif
}
}
}
return ass;
} public static void Uninject(string domainName)
{
Contract.Requires(!string.IsNullOrEmpty(domainName)); var item = CallInject(domainName);
_injectSet.Remove(item);
try
{
AppDomain.Unload(item.Domain);
}
catch (Exception ex)
{
LogError(ex, "Uninject");
#if DEBUG
throw;
#endif
}
}
}
}

最新文章

  1. Java学习笔记,第三章
  2. atitit。企业的价值观 员工第一 vs 客户第一.docx
  3. .NET 4.0 任务(Task)
  4. VS2013无法链接到TFS(Visual studio online),错误TF31001,TF31002
  5. Ubuntu 16.04 LTS安装好需要设置的15件事(喜欢新版本)
  6. IntelliJ IDEA MyBatis插件安装
  7. 关于abbr 的一些用法
  8. Big Data Ingestion and streaming product introduction
  9. jQuery中的选择器(下)
  10. 在多机器上远程执行JMeter
  11. XML 和 DTD
  12. Hyper-V
  13. A - Piece of Cake Kattis - pieceofcake (数学)
  14. JsonResponse
  15. centos7 nginx图片 服务器可以访问ftp用户上传的图片资源的配置
  16. Spring框架基础
  17. 配置Sublime Text2的python运行环境(Sublime Text 3也类似)
  18. C#--整型与字节数组byte[]之间的转换
  19. 常用脚本lnmp
  20. IIS W3C日志记录字段和HTTP状态代码的说明

热门文章

  1. phalcon: 上下文转义
  2. OneProxy与其它数据库中间件的对比
  3. 浅谈AsyncState与AsyncDelegate使用的异同
  4. jmeter 逻辑控制器
  5. hdu----(4545)魔法串(LCS)
  6. 你不知道的JavaScript-- 事件流与事件处理
  7. HTTP &amp;&amp; socket
  8. webform工程中aspx页面为何不能调用appcode文件夹下的类(ASP.NET特殊文件夹的用法)
  9. mvc伪静态&lt;三&gt; IIS配置
  10. 《Play for Java》学习笔记(三)template+Message