Замутил тестовый проект под .Net Core (NETCOREAPP2_0), создающий COM-объект.
Получаю ошибку вызова CoCreateInstance — 0x800401F0 (CO_E_NOTINITIALIZED — CoInitialize has not been called).
Указание атрибута [MTAThread] не помогает.
[MTAThread]
static void Main(string[] args)
Подскажите — как заставить Core инициализировать COM?
Ну, кроме кроме явного вызова CoInitialize, конечно.
-- Пользователи не приняли программу. Всех пришлось уничтожить. --
Здравствуйте, Arsen.Shnurkov, Вы писали:
AS>я думаю, надо написать
AS>Thread.CurrentThread.TrySetApartmentState(ApartmentState.MTA);
Помогло, спасибо.
Я верну назад ссылку, которую ты стер
https://github.com/dotnet/coreclr/issues/13688#issuecomment-326759385
Насколько я понимаю, бардак до сих пор присутствует.
| Тестовый код |
| static void Main(string[] args)
{
try
{
var curAState=System.Threading.Thread.CurrentThread.GetApartmentState();
Console.WriteLine("GetApartmentState: {0}",curAState);
bool r=System.Threading.Thread.CurrentThread.TrySetApartmentState(System.Threading.ApartmentState.MTA);
Console.WriteLine("TrySetApartmentState(MTA): {0}",r);
Exec();
}
catch(Exception e)
{
Console.WriteLine("ERROR: {0} - {1}",e.Source,e.Message);
}
}//Main
|
| |
Вывод:
GetApartmentState: MTA
TrySetApartmentState(MTA): True
Получается, что COM не инициализирован, но GetApartmentState возвращает обратное (MTA).
Еще отмечу, что нужно принудительно освобождать ссылки на COM-объекты (диспозить/закрывать .NET обертки) перед выходом из Main.
Иначе, при завершении главного потока, происходит выгрузка DLL с активными COM-объектами.
| И вылазят проблемы типа такой: |
| GetApartmentState: MTA
TrySetApartmentState(MTA): True
Assertion failed:
module_lock_count: 2
false, file ..\source\ibp_com.cpp, line 112
|
| |
На нормальном .NET FW с этим можно было не париться.
UPD. Добавил в конец Main принудительную(?) сборку мусора. Вроде тоже помогает освободить все ссылки на COM-объекты:
GC.Collect();
GC.WaitForPendingFinalizers();
-- Пользователи не приняли программу. Всех пришлось уничтожить. --
Здравствуйте, Коваленко Дмитрий, Вы писали:
КД>UPD. Добавил в конец Main принудительную(?) сборку мусора. Вроде тоже помогает освободить все ссылки на COM-объекты:
Опередил

Это ещё одно гениальное решение команды .Net core: вызов финалайзеров
более не гарантирован даже при мягком завершении процесса. Угу, CLI, ecma-335 и прочая куча умных слов —
не, не слышал.
Логики в этом нет, поэтому или ждать, пока команда net core сама перенаступает на грабли, которые были решены ещё в первом фреймворке, или оставаться на full .NET.