#include <windows.h> #include <stdio.h> #include <ntdll.h> int WINAPI iWinMain() { #ifdef _WIN64 PTEB_7 pTEB = (PTEB_7)__readgsqword(0x30); LPWSTR captionMsg = L"64-bit Application"; #else PTEB_7 pTEB = (PTEB_7)__readfsdword(0x18); LPWSTR captionMsg = L"32-bit Application"; #endif ULONG_PTR lastError; WCHAR mainMsg[MAX_PATH] = {0}; LoadLibraryW(L"target.dll"); lastError = GetLastError(); _snwprintf( mainMsg, MAX_PATH, L"LastError: 0x%p", lastError); MessageBoxW( NULL, mainMsg, captionMsg, MB_ICONINFORMATION); return 0; }Inside debugger:
........ ........ 004010A5 PUSH main.00401068 ; UNICODE "target.dll" 004010AA CALL DWORD PTR DS:[<&KERNEL32.LoadLibraryW>] ; kernel32.LoadLibraryW 004010B0 CALL DWORD PTR DS:[<&KERNEL32.GetLastError>] ; kernel32.GetLastError ........ ........ GetLastError MOV EAX,DWORD PTR FS:[18] 751F680C MOV EAX,DWORD PTR DS:[EAX+34] 751F680F RET ........ ........Retrieve the LastErrorValue directly from the information stored in the current TEB (Thread Environment Block)
typedef struct _TEB_7 { NT_TIB NtTib; PVOID EnvironmentPointer; CLIENT_ID Cid; PVOID ActiveRpcInfo; PVOID ThreadLocalStoragePointer; PPEB_VISTA_7 Peb; ULONG LastErrorValue;#include <windows.h> #include <stdio.h> #include <ntdll.h> #define GET_LAST_ERROR_FROM_TEB int WINAPI iWinMain() { #ifdef _WIN64 PTEB_7 pTEB = (PTEB_7)__readgsqword(0x30); LPWSTR captionMsg = L"64-bit Application"; #else PTEB_7 pTEB = (PTEB_7)__readfsdword(0x18); LPWSTR captionMsg = L"32-bit Application"; #endif ULONG_PTR lastError; WCHAR mainMsg[MAX_PATH] = {0}; LoadLibraryW(L"target.dll"); #ifdef GET_LAST_ERROR_FROM_TEB lastError = pTEB->LastErrorValue; #else lastError = GetLastError(); #endif _snwprintf( mainMsg, MAX_PATH, L"LastError: 0x%p", lastError); MessageBoxW( NULL, mainMsg, captionMsg, MB_ICONINFORMATION); return 0; }
Source:
http://www.mediafire.com/download/dobcx2s4v0tm5zv/GetLastError.rar