У меня есть некоторый COM-компонент, который я называю от некоторого c# dll.
У меня также есть приложение winforms, которое использует это .dll.
Когда я закрываю приложение, я получаю это исключение:
COM-объект, который был разделен от его базового RCW, не может использоваться.
Отслеживание стека показывает, что это исключение прибывает из деструктора в .dll. Я реализовал этот деструктор для вызова некоторого метода очистки в COM.
Почему это происходит? Как лучше решить его?
Проблема описана здесь:
Безопасно ли вызывать RCW из финализатора?
и здесь:
Освободить объект Excel в моем деструкторе
Проблема в том, что не только время Что касается того, когда эти объекты должны быть собраны мусором, неизвестно, но порядок, в котором вызываются финализаторы , также недетерминирован. В этом случае вызываемая оболочка среды выполнения также имеет финализатор, который вызывает Marshal.FinalReleaseComObject на самом себе, что приводит к уменьшению счетчика ссылок на стороне COM объекта ограждение, чтобы этот COM-объект мог быть освобожден. Но поскольку порядок, в котором вызываются финализаторы , не определен, вполне возможно, что финализаторы для COM-объектов, на которые ссылаются ваши объекты, сработают перед финализатором для вашего объект. Таким образом, код в вашем финализаторе может иногда работать, но в большинстве случаев один или несколько из вызываемых оболочек времени выполнения, которые будут иметь ссылки на ваши объекты , уже имеют свои финализаторы вызывается, и базовый COM-объект будет выпущен до того, как ваш финализатор выполнит свой код.