Пост

Функция обратного вызова для обработки ошибок GLFW

Перевод поста NogginBops "The GLFW error callback"

Пост не является авторским и/или официальным
Ссылка на оригинал: The GLFW error callback
Автор оригинала: NogginBops

В этом посте я расскажу об обратном вызове ошибок GLFW и о том, зачем вам может понадобиться установить свой собственный.

Поскольку GLFW — это C API, он не использует исключения для передачи ошибок. Вместо этого в нём применяется обратный вызов ошибок (error callback), который вызывается при возникновении ошибки. Важно помнить, что в GLFW ошибки не являются фатальными до тех пор, пока успешно выполнена функция glfwInit(). Вещи могут работать некорректно, но они не приведут к падению процесса или потока.

Вот выдержка из документации GLFW:

Reported errors are never fatal. As long as GLFW was successfully initialized, it will remain initialized and in a safe state until terminated regardless of how many errors occur. If an error occurs during initialization that causes glfwInit to fail, any part of the library that was initialized will be safely terminated.

Сообщаемые ошибки никогда не являются фатальными. Если инициализация GLFW прошла успешно, библиотека останется в рабочем и безопасном состоянии до момента её завершения, независимо от количества возникших ошибок. Если же ошибка происходит во время инициализации и приводит к неудаче вызова glfwInit, все успешно инициализированные части библиотеки будут безопасно завершены.

Однако, взглянув на стандартную функцию обратного вызова в OpenTK, мы видим следующее:

1
2
3
4
private static void DefaultErrorCallback(ErrorCode errorCode, string description)
{
    throw new GLFWException($"{description} (this is thrown from OpenTKs default GLFW error handler, if you find this exception inconvenient set your own error callback using GLFWProvider.SetErrorCallback)", errorCode);
}

Она просто выбрасывает исключение GLFWException при каждой ошибке. Но если ошибки GLFW не фатальны, зачем вообще выбрасывать исключение? Для наглядности. Большинство ошибок GLFW означают, что пользователь делает с API что-то, чего делать не следует, и часто имеет смысл как можно быстрее показать эти ошибки пользователю.

Однако это не так актуально в случае с Wayland. Поскольку некоторые возможности GLFW невозможно реализовать на Wayland (например, glfwGetWindowPos), GLFW будет выдавать ошибку ErrorCode.FeatureUnavailable при попытке использовать такие возможности. Это означает, что программы, которые обычно не вызывают ошибок на других платформах, внезапно могут вызвать множество ошибок (error callback) в Wayland.

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

«Так как же установить свой собственный обработчик ошибок?» — спросите вы. Это очень просто: используйте GLFWProvider.SetErrorCallback:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
// Определяем собственную функцию обратного вызова ошибок.
private static void MyErrorCallback(ErrorCode errorCode, string description)
{
    if (errorCode == ErrorCode.FeatureUnavailable)
    {
        Console.WriteLine($"GLFW feature unavailable: {description}");
    }
    else
    {
        throw new GLFWException($"{description} (this is thrown from OpenTKs default GLFW error handler, if you find this exception inconvenient set your own error callback using GLFWProvider.SetErrorCallback)", errorCode);
    }
}

// Устанавливаем нашу функцию обратного вызова ошибок.
GLFWProvider.SetErrorCallback(MyErrorCallback);
Авторский пост защищен лицензией CC BY-NC-SA 4.0

Популярные теги