Подтвердить что ты не робот

Получение недостающей ошибки компонента в приложении VB6

У меня есть приложение VB6, в котором есть тонна сторонних компонентов. Приложение работает хорошо, но при выходе (и только при запуске в качестве автономного EXE, например, не в IDE), оно выдает сообщение об ошибке:

enter image description here

Я видел ошибки, подобные этим раньше, но обычно он говорит, какой компонент отсутствует в зависимостях или неправильно зарегистрирован.

Я запустил его через Process Monitor и получил следующие файлы, которые он не может найти:

enter image description here

И затем он уходит. Я искал имена файлов, которые он не может найти и не может найти ничего. Похоже, что он ищет варианты библиотек MSComENU, MSComEN и MSCOENU.

Я проверил и перепроверял, чтобы убедиться, что все сторонние компоненты есть, и они есть - приложение отлично работает, не будет, если их там не будет.

Стоит отметить, что ошибка возникает после того, как была запущена последняя строка кода VB6 (в событии Form_Unload). Я знаю это, потому что последняя строка - это окно сообщения, которое появляется.

Многое, намного позже EDIT: я, наконец, вернулся к решению проблемы и выяснил ее в процессе устранения (и это был процесс loooong). В конце концов, это не имело никакого отношения к любым записям MSCOMM *.dll. На самом деле, я не знаю, почему они все еще отображаются в Process Monitor. Проблема была намного проще.

У меня было несколько сторонних элементов управления в основной форме. Чтобы не загрязнять основную форму с помощью тонны кода обработки событий, я делегировал эти элементы управления новому классу, например:

' declaration code in main form'
Private WithEvents moDelegateObject as clsDelegateObject

' still in the main form, after initialization'
Set moDelegateObject = new clsDelegateObject
With moDelegateObject
    Set .ThirdPartyCtlHandler1 = me.ThirdPartyCtl1
    Set .ThirdPartyCtlHandler2 = me.ThirdPartyCtl2
    Set .ThirdPartyCtlHandler3 = me.ThirdPartyCtl3
end with

' declarations and properties inside of clsDelegateObject'
Private WithEvents moThirdPartyCtlHandler1 as ThirdPartyCtl
Private WithEvents moThirdPartyCtlHandler2 as ThirdPartyCtl
Private WithEvents moThirdPartyCtlHandler3 as ThirdPartyCtl
Public Event FooEvent() ' other various events as well '

Public Property Set ThirdPartyCtlHandler1(o as ThirdPartyCtl) 
    moThirdPartyCtlHandler1 = o
End Property 
Public Property Get ThirdPartyCtlHandler1() as ThirdPartyCtl
    ThirdPartyCtlHandler1 = moThirdPartyCtlHandler1 
End Property
' ... Repeat for each handler ...'

Отсутствовал код для явного освобождения этих объектов до закрытия. Это то, что обычно делает Visual Basic. Поэтому я добавил следующее в Form_QueryClose в основной форме:

With moDelegateObject
    Set .ThirdPartyCtlHandler1 = Nothing
    Set .ThirdPartyCtlHandler2 = Nothing
    Set .ThirdPartyCtlHandler3 = Nothing
End with
Set moDelegateObject = Nothing  

Последняя строка оказалась сверхъестественной, но я бросил ее туда ради полноты. Я думаю, что это была комбинация делегирования элементов управления классу делегатов и получение от него событий в основной форме и использование большого количества действительно непонятных сторонних элементов управления, которые способствовали этой проблеме. Вероятно, что сторонний элемент управления не выполняет чистое освобождение. Во всяком случае, извлеченный урок.

4b9b3361

Ответ 1

Это может быть проблема DLL_PROCESS_DETACH или CoUninitialize. В блоге Raymond Chen "The Old New Thing" есть несколько статей:

Как вы сказали, это сторонние компоненты. Вы можете попытаться сделать меньше тестовых случаев, пока проблема не исчезнет, ​​чтобы определить багги-компонент. Вы также можете попробовать отладчик собственного кода и проанализировать, какой код создал сообщение об ошибке.

Самое простое решение, однако, чтобы обойти эту проблему, вы пытаетесь заставить определенный порядок загрузки всех этих компонентов. В форме Main() или startup попытайтесь использовать некоторые функции каждого стороннего компонента в фиксированном порядке. Если ошибка все еще появляется, измените порядок, пока проблема не исчезнет. Это может сработать.

Ответ 2

Вы можете попытаться использовать зависимый ходок в списке ссылок в файле проекта, чтобы узнать, отсутствуют ли какие-либо из этих сторонних файлов. Если никаких зависимостей не хватает, попробуйте снова зарегистрировать файлы, используя regsvr32. Если какая-либо из команд regsvr32 терпит неудачу, возможно, вы обнаружили компонент с отсутствующими зависимостями.