Как я могу отладить ошибки кучи в библиотеке классов C #? - PullRequest
1 голос
/ 10 октября 2008

Я получаю ошибку повреждения кучи в модуле библиотеки C #, который я вызываю через COM в приложении C ++. Конкретная ошибка:

HEAP: модифицированный блок свободной кучи 4b61bb8 на 4b61be8 после освобождения
...
Это может быть связано с коррупция в куче и указывает ошибка в [app] .exe или любую из библиотек DLL, которые он загрузил.

Вершина стека вызовов:

CustomMarshalers.dll!System.Runtime.InteropServices.CustomMarshalers.EnumeratorViewOfEnumVariant.MoveNext() + 0x168 bytes

Теперь я понял, что .NET должен был уменьшить проблемы с памятью, а не сделать так, чтобы проблемы с памятью было невозможно исправить. Тем не менее, я не могу думать ни о чем, что я мог бы сделать, чтобы вызвать ошибку памяти, или как я мог бы попытаться исправить это. Конкретный модуль использует компоненты Microsoft.VisualStudio.VCProjectEngine .NET для итерации файлов проекта VC с довольно простыми итераторами. Он прерывается в операторе foreach при переборе файлов в фильтре (папке) VCProject, после того, как успешно завершил предыдущие около 100 вызовов. Фактический код, который нарушает:

    IVCCollection CollectionFiles = (IVCCollection)FolderInProject.Files;
    foreach (VCFile File in CollectionFiles)
    {
        [...]
    }

Как можно отладить это?

Обновление:

Когда я звоню из чистого консольного приложения C # (без COM или собственного кода), я получаю:

Необработанное исключение типа 'System.AccessViolationException' произошло в [component] .dll

дополнительный информация: Попытка прочитать или Запишите защищенную память. Это часто признак того, что другая память коррумпированы.

До сих пор не знаю, как я могу отладить это. Очевидно, что где-то произошла ошибка памяти ... но как я могу отследить ее в чистом управляемом коде, где модель памяти даже не раскрывается?

1 Ответ

1 голос
/ 10 октября 2008

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

Теперь другая возможность состоит в том, что вы все правильно упорядочиваете, но не совсем правильно вызываете интерфейс, что проявляется в неправильном использовании параметра, который в конечном итоге перебирает неуправляемую память. Отследить их не так весело, особенно если у вас нет доступа к источнику COM.

Одна хитрость заключается в том, чтобы позволить программе аварийно завершить работу за пределами вашего отладчика, нажмите Отладка, чтобы открыть окно выбора JIT Debugger. Затем установите флажок «Выбрать механизм отладки» (или что-то в этом роде) и убедитесь, что установлены флажки «Управляемый» и «Собственный». Подходящий экземпляр VS должен быть поврежден в самом коде, который умер, а не в самом близком управляемом коде к смерти.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...