我有一个自定义框架,其中主机应用程序运行事件循环并将来宾应用程序加载到单独的应用程序域中。来宾应用程序可以通过提供的 API 来利用事件循环。我想让来宾应用程序能够自动将所有延续传播到事件循环中,就像在 .NET GUI 应用程序和 UI 线程中所做的那样。因此,我创建了一个能够做到这一点的自定义同步上下文。
但问题是我无法开始使用这个新的上下文。每当我尝试设置它时,它都会null
在跨应用程序域边界的下一个回调中重置。
这里有一个快速的代码片段来说明这个问题:
using System;
using System.Threading;
class Test : MarshalByRefObject {
public void Do() {
Console.WriteLine("TID: {0}, SC: {1}",
Thread.CurrentThread.ManagedThreadId,
SynchronizationContext.Current != null ? "present" : "absent");
SynchronizationContext.SetSynchronizationContext(new SynchronizationContext());
}
}
static class Program {
static void Main() {
try {
var domain = AppDomain.CreateDomain("Other Domain");
var obj = (Test)domain.CreateInstanceAndUnwrap(typeof(Test).Assembly.FullName, typeof(Test).FullName);
obj.Do();
obj.Do();
} catch (Exception e) {
Console.WriteLine(e.ToString());
}
}
}
输出:
TID: 1, SC: absent
TID: 1, SC: absent
SynchronizationContext.SetThreadStaticContext
如果它在桌面上可用,还有一种方法可以潜在地解决上述问题。
当然,总有一种方法可以在执行任何其他工作之前在每个回调中显式设置上下文。但这似乎有点糟糕。除此之外,我看不到解决这个鸡蛋问题的优雅方法。顺便说一句,它在 Mono 上按预期工作。