Почему этот код вызывает исключение System.ExecutionEngineException - PullRequest
11 голосов
/ 05 ноября 2010

Справочная информация: Я использую управляемые библиотеки DirectX 9.0 для преобразования массивов трехмерных точек в двумерные экранные координаты.Для скорости я использую UnsafeNativeMethods, чтобы сделать все преобразования.

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

List<Vector3> verticesAfterClipping = new List<Vector3>;
public unsafe void ClipLine(Line lineToClip)
{
    this.verticesAfterClipping.Clear();

    // Clipping algorithm happens here... (this is psuedo-code of what it does)
    foreach(Vertex in lineToClip.Vertices)
    {
        bool thisIsClipped =   // Set to whether this vertex is clipped
        bool lastWasClipped =  // Set to whether last vertex was clipped

        if(thisIsClipped == false && lastWasClipped == true)
        {
            verticesAfterClipping.Add( /* intersection on clipping plane */ );
            verticesAfterClipping.Add( /* thisVertex */ );
        }
        else if (thisIsClipped == false && lastWasClipped == false)
        {
            verticesAfterClipping.Add( /* thisVertex */ );
        }
        else if (thisIsClipped == true && lastWasClipped == false)
        {
            verticesAfterClipping.Add(/* intersection on clipping plane */);
        }
    }

    // THIS IS WHERE BAD THINGS HAPPEN
    lineToClip.Vertices = new Vertex[verticesAfterClipping.Count];
    verticesAfterClipping.CopyTo(lineToClip.Vertices, 0);
}

Когда список verticesAfterClipping копируется в вершины lineToClip, объект lineToClip затем передается вUnsafeNativeMethod, который преобразует эти вершины в 2d вершины.Из всего, что я вижу, когда я прохожу его в режиме отладки, он работает совершенно нормально, пока просто не умрет.

Я просто не могу понять, что не так.Любая помощь будет высоко ценится.

Ответы [ 3 ]

14 голосов
/ 05 ноября 2010

Возможно, проблема не возникает в строке, которая выдает исключение.Это может быть просто симптомом того, что произошло раньше.

Исключение System.ExecutionEngineException выдается, когда CLR обнаруживает , что что-то пошло не так.Это может произойти через некоторое значительное время после возникновения проблемы.Это происходит потому, что исключение обычно является результатом повреждения внутренних структур данных - CLR обнаруживает, что что-то попало в состояние, которое не имеет смысла.Он генерирует неуловимое исключение, потому что продолжать его небезопасно.

Таким образом, у вас может быть какой-то код в какой-то совершенно не связанной части системы, который что-то повреждает, но это становится очевидным только при выполнении этого конкретного фрагмента кода.Код, который вы показали, может быть просто в порядке.(Этого также может и не быть ... Я не вижу ничего очевидного неправильного, но тогда я не очень хорошо знаю управляемые библиотеки DX 9. Я не вижу, какая функция этого метода требует, например, ключевое слово unsafe.)

К сожалению, это означает, что вам нужно начать разыгрывать сеть чуть шире.Практически все, что использует либо небезопасный код, либо COM-взаимодействие, потенциально подозрительно.К сожалению, это будет долгий и утомительный процесс.Один из способов, которым вы можете подойти к этому, - постараться постепенно упростить программу: какой самый маленький фрагмент кода может проиллюстрировать проблему?(Например, если вы поместите код, который вы там показали, в приложение, которое не содержит ничего, кроме простейшего возможного вызова этого метода, все равно произойдет ли сбой?)

1 голос
/ 22 января 2015

У меня одна и та же проблема с разными библиотеками.В моем случае все началось задолго до того, что мне пришлось запустить 32-разрядное приложение .net в 64-разрядной среде.Ну, это доставляет мне много проблем, совместимость между архитектурами или между CLR вашей .NET Framework также может быть вашей проблемой.

PS: Теперь я знаю что моя проблемано понятия не имею где это.

0 голосов
/ 26 октября 2018

У меня есть два класса, которые имеют дело с определенной таблицей в моей базе данных

StorageManager - класс, который имеет методы, которые обрабатывают прямое взаимодействие с базой данных

Контроллер - класс, который имеет методы для обработки вызовов API

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

Я написал эти методы для проверки уже существующих / дубликатов в неправильном классе, что в итоге привело к тому, что исключение executingengine выдается за меня.

Перемещение методов так, чтобы они жили в правильном контексте базы данных, казалось, исправило это для меня.

...