Когда вы вызываете функцию Windows, она проверяет переданные ей параметры, а затем пытается выполнить работу. Если передан недопустимый параметр или если данную операцию нельзя выполнить по другой причине, она возвращает значение, свидетельствующее об ошибке.
За каждой ошибкой закреплен свой 32-битный код.
Функция Windows, обнаружив ошибку, через механизм локальной памяти потока сопоставляет соответствующий код ошибки с вызывающим потоком. Это позволяет потокам работать независимо друг от друга, не вмешиваясь в чужие ошибки.
Когда функция вернет вам управление, ее возвратное значение будет указывать на то, что произошла какая-то ошибка. Какая именно - вы узнаете, вызвав функцию
GetLastError(). Она просто возвращает 32-битный код ошибки для данного потока.
Список кодов ошибок, определенных Microsoft, содержится в файле WinError.h.
Функцию
GetLastError необходимо вызывать сразу же за проверяемой функцией, иначе код ошибки будет утерян.
Для отладки бывает нужно следить не за одной ошибкой, а за их постоянным изменением, для этого нет необходимости включать в код постоянные проверки и чтение
GetLastError, можно в окне дебаггирования Visual C++ ввести @error. В окне вы увидите значение переменной ошибки.
Так как ошибки, которые возникают в программе, возникают не только в процессе отладки, но могут быть обусловлены текущим состоянием системы, на которой бежит программа, то иногда бывает полезно сообщить тип ошибки в нормальном текстовом виде. В Windows есть специальная функция, которая "конвертирует" код ошибки в ее описание - FormatMessage.
DWORD FormatMessage(
DWORD dwFlags,
LPCVOID pSource,
DWORD dwMessageId,
DWORD dwLanguageId,
PTSTR pszBuffer,
DWORD nSize,
Va_list *Aguments);
Для разработчика особенно важно при создании API или SDK подобных вещей создавать сходный механизм возврата ошибок для своих функций.
С этой целью вы просто устанавливаете код последней ошибки в потоке и возвращаете значение
FALSE,
INVALID_HANDLE_VALUE,
NULL или что-то другое, более подходящее по ситуации. Чтобы установить код последней ошибки в потоке используйте
SetLastError.
void Set LastError(DWORD dwErrCode);
Параметр - 32-битное число. Использовать лучше подходящий код ошибки Windows, однако если такового подходящего не нашлось, то можно ввести свой собственный код ошибки. Он должен представлять собой 32-битное число, разбитое по следующим правилам.
Биты
31-30 - Код тяжести - 0=успех, 1=информация, 2=предупреждение, 3=ошибка
29 - Кем определен - 0-Microsoft 1-пользователем
28 - Должен быть 0
27-16 - Определяется Microsoft. (Код подсистемы)
15-0 - Код ошибки.
Собственно, Microsoft обещает, что бит 29 будет в ее ошибках всегда равен 0, поэтому, поставив там 1, вы будете в какой-то степени в безопасности от конфликтов с кодами ошибок Microsoft.