C# から呼び出す ATL COM exe があります。参照を C# にインポートすると、すべてが正常に機能し、exe が生成され、関数を呼び出すことができます。ここで、これらの COM オブジェクトのいくつかをインスタンス化します。ときどき、そのうちの 1 つがハングします。COM オブジェクトはまだ実行中なので、解放しても何も起こりません。正常に動作している他のすべてのオブジェクトを失うため、プロセスを強制終了することはできません。そう、
- 本当に1人だけを殺す方法はありますか?
- 要求された com オブジェクトごとに 1 つの exe を起動する方法はありますか?
- クライアントが予期せず終了した場合、COM exe はクリーンアップされません。これを修正する方法はありますか?
理想的には、オブジェクト インスタンスごとに 1 つの COM exe を起動し、それを Process.Kill() できるようにします。これらのいずれかがオプションですか?オブジェクトを作成するために使用するクラスは次のとおりです。この場合、RandomID() (人為的に) を返すのに非常に長い時間がかかります。また、別の言語でこれを行う方法があれば、それも試してみたいと思います。ありがとう。
public class MyComObject:IDisposable
{
private bool disposed = false;
MyMath test;
public MyComObject()
{
test = new MyMath();
}
public double GetRandomID()
{
if (test != null)
return test.RandomID();
else
return -1;
}
public void Dispose()
{
Dispose(true);
GC.SuppressFinalize(this);
}
private void Dispose(bool disposing)
{
if (!this.disposed)
{
if (test != null)
Marshal.ReleaseComObject(test);
disposing = true;
}
}
}
編集:これを「シングルユース」に設定できれば、すべてが思い通りに機能するようです。ただし、VS 2008 でこのオプションを設定する場所が見つかりません。
編集:Googleグループで答えを見つけました
class CMathServerModule : public CAtlExeModuleT< CMathServerModule >
{
public :
DECLARE_LIBID(LIBID_MathServerLib)
DECLARE_REGISTRY_APPID_RESOURCEID(IDR_MATHSERVER, "{2FA977F0-050C-4010-A09F-4FE6D75F3024}")
HRESULT RegisterClassObjects(DWORD dwClsContext, DWORD dwFlags)
throw()
{
dwFlags = ((dwFlags & ~(REGCLS_MULTIPLEUSE | REGCLS_MULTI_SEPARATE )) |
REGCLS_SINGLEUSE);
return CAtlExeModuleT<CMathServerModule>::RegisterClassObjects(dwClsContext, dwFlags);
}
};