gpt4 book ai didi

.net - COM +长时间运行的方法导致其他方法阻塞/挂起

转载 作者:行者123 更新时间:2023-12-03 12:55:54 25 4
gpt4 key购买 nike

我有一个长时间运行的COM +方法,我需要能够从另一个线程中取消该方法。我正在使用C#/。NET来交互COM +对象。我将两个COM +对象都配置为具有“免费”线程模型。此C#示例演示了我打算如何使用COM +对象。

static void Main(string[] args)
{
var sampleCOMClass = new SampleCOMObjectClass();
var cancelToken = new CancelCOMObjectClass();
try
{
Task.Factory.StartNew(() =>
{
Thread.Sleep(TimeSpan.FromSeconds(10));
cancelToken.Cancel(); // this method never makes it to COM
Console.WriteLine("Cancelled!");
});
sampleCOMClass.LongProcess(cancelToken);
}
finally
{
Marshal.ReleaseComObject(sampleCOMClass);
Marshal.ReleaseComObject(cancelToken);
}
}

我的长期运行过程正确地检查了取消 token ,以确定我们是否应该完成处理,但是 Cancel方法从未将其用于COM +对象。好像该方法正在阻塞,等待 LongProcess完成。我不知道为什么要这样做,因为我认为“免费”线程模型允许实现管理同步。

这是一个BitBucket存储库,其中包含一个要重现的最小示例。
https://bitbucket.org/theonlylawislove/so-blocking-com-call

为什么Cancel永远不会被调用/阻止?

取消COMObject
STDMETHODIMP CCancelCOMObject::Cancel(void)
{
_isCancelled = VARIANT_TRUE;
return S_OK;
}

STDMETHODIMP CCancelCOMObject::get_IsCancelled(VARIANT_BOOL* pVal)
{
*pVal = _isCancelled;
return S_OK;
}

SampleCOMObject
STDMETHODIMP CSampleCOMObject::LongProcess(ICancelCOMObject* cancel)
{
VARIANT_BOOL isCancelled = VARIANT_FALSE;
while(isCancelled == VARIANT_FALSE)
{
Sleep(1000);
cancel->get_IsCancelled(&isCancelled);
}
return S_OK;
}

最佳答案

事实证明,我的COM + exe具有此功能。

#define _ATL_APARTMENT_THREADED

删除那解决了我的问题。

奇怪的是,在指定“免费”线程模型时,ATL简单对象向导没有提及/修改此内容。

知道是谁投票决定结束这个问题,这将是很高兴的。这是完全有效的。

关于.net - COM +长时间运行的方法导致其他方法阻塞/挂起,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/23457206/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com