Как заставить приложение C # аварийно завершить работу с AccessViolationException - PullRequest
5 голосов
/ 31 мая 2019

Как преднамеренно завершить работу приложения с AccessViolationException в c #?

У меня есть консольное приложение, в котором используется неуправляемая DLL, которая в конечном итоге дает сбой из-за исключений нарушения прав доступа.Из-за этого мне нужно намеренно бросить AccessViolationException, чтобы проверить, как он ведет себя при определенных обстоятельствах.

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

Удивительно, но это не работает:

public static void Crash()
{
    throw new AccessViolationException();
}

И этого:

public static unsafe void Crash()
{
    for (int i = 1; true; i++)
    {
        var ptr = (int*)i;
        int value = *ptr;
    }
}

Ответы [ 2 ]

3 голосов
/ 31 мая 2019

Детерминированный подход заключается в том, чтобы Windows выбрасывала его для вас:

Из ответа Петър Петрова на: Как вызвать сбой приложения C #

[DllImport("kernel32.dll")]
static extern void RaiseException(uint dwExceptionCode, uint dwExceptionFlags,  uint nNumberOfArguments, IntPtr lpArguments);

void start()
{
    RaiseException(0xC0000005, 0, 0, new IntPtr(1));
}
2 голосов
/ 31 мая 2019

Это «родной» способ - хотя подход @Storm на 100% детерминирован. Хитрость заключается в попытке записи в память вдали от текущего указателя. И.Е. даже несмотря на то, что я выделил 4 байта в моей программе, следующие несколько тысяч байтов все еще находятся в той части памяти, которая зарезервирована для моей программы. Стреляй далеко, и ты должен получить это.

int[] array = new int[1];
fixed (int* ptr = array)
{
      ptr[2000000] = 42;
}
...