调用 COM Interop 并设置超时
我想知道如何实现这一点。我有一个 COM 对象,其操作有时需要很长时间,另外我注意到,如果出现问题,它有自己的超时 20 分钟。这对于客户端程序来说等待这么长时间是不可接受的。
因此,我正在考虑在另一个线程上调用 COM 操作,并在一定的超时后终止该线程。
我有 COM 助手通过反射进行调用,这是同步的:
ComInvoke.Get<bool>(dcomSrv, "Launched");
这从 COM 实例获取一个布尔属性
,我想使用任务包装它:
var task = Task.Factory.StartNew<bool>(() =>
{
return ComInvoke.Get<bool>(dcomSrv, "Launched");
});
if (task.Wait(5000) == false)
{
task.Dispose();
throw new Exception("Task timeout");
}
问题是在任务中没有循环可以使用取消令牌。
您认为这是一个好的解决方案还是您有更好的解决方案?
谢谢你!
I was wondering how to accomplish this. I have a COM object whose operations sometimes take long, additionally I noticed, it has it's own timeout 20 minutes if something goes wrong. This is unacceptable for the client program to wait so long.
Therefore I'm thinking about invoking the COM operation on another thread and after certain timeout just kill the thread.
I have COM helper to do the invokation via reflection, which is synchronous:
ComInvoke.Get<bool>(dcomSrv, "Launched");
this gets a boolean property from COM instance
and I want to wrap this using Task:
var task = Task.Factory.StartNew<bool>(() =>
{
return ComInvoke.Get<bool>(dcomSrv, "Launched");
});
if (task.Wait(5000) == false)
{
task.Dispose();
throw new Exception("Task timeout");
}
The thing is that in the task there is no loop where I could make use of cancelation token.
What do you think, is this a good solution or do you have something better?
Thank you!
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
Task::Dispose
实际上不会停止Task
的底层线程,并且由于 TPL 默认情况下使用 ThreadPool 来安排其工作,因此此逻辑将消耗 ThreadPool 线程DCOM 对象阻止它的整整 20 分钟。事实上,我很确定如果您对未完成的Task
调用Dispose
,您会遇到异常。在这种情况下,可能不应该使用 TPL,您只想启动自己的
Thread
实例,如果它未按所需数量完成,则Abort
它的时间。Task::Dispose
will not actually stop theTask
's underlying thread and, because the TPL uses the ThreadPool by default to schedule it's work, this logic will consume a ThreadPool thread for the full 20 minutes that the DCOM object is blocking it. As a matter of fact, I'm pretty sure you'll get an exception if you callDispose
on an uncompletedTask
.This is a case where TPL probably shouldn't be used and you just want to spin up your own
Thread
instance and justAbort
it if it does not complete in the desired amount of time.