The ErrorShow Sample Application

[Previous] [Next]

The ErrorShow application, "01 ErrorShow.exe" (listed in Figure 1-2), demonstrates how to get the text description for an error code. The source code and resource files for the application are in the 01-ErrorShow directory on this book's companion CD-ROM. Basically, this application shows how the debugger's Watch window and Error Lookup programs do their things. When you start the program, the following window appears.

You can type any error number into the edit control. When you click the Look Up button, the error's text description is displayed in the scrollable window at the bottom. The only interesting feature of this application is how to call FormatMessage. Here's how I use this function:

 // Get the error code DWORD dwError = GetDlgItemInt(hwnd, IDC_ERRORCODE, NULL, FALSE); HLOCAL hlocal = NULL; // Buffer that gets the error message string // Get the error code's textual description BOOL fOk = FormatMessage( FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_ALLOCATE_BUFFER, NULL, dwError, MAKELANGID(LANG_ENGLISH, SUBLANG_ENGLISH_US), (LPTSTR) &hlocal, 0, NULL);  if (hlocal != NULL) { SetDlgItemText(hwnd, IDC_ERRORTEXT, (PCTSTR) LocalLock(hlocal)); LocalFree(hlocal); } else { SetDlgItemText(hwnd, IDC_ERRORTEXT, TEXT("Error number not found.")); } 

The first line retrieves the error code number out of the edit control. Then, a handle to a memory block is instantiated and initialized to NULL. The FormatMessage function internally allocates the block of memory and returns its handle back to us.

When calling FormatMessage, I pass the FORMAT_MESSAGE_FROM_ SYSTEM flag. This flag tells FormatMessage that we want the string for a system-defined error code. I also pass the FORMAT_MESSAGE_ALLOCATE_ BUFFER flag to tell the function to allocate a block of memory large enough for the error's text description. The handle to this block will be returned in the hlocal variable. The third parameter indicates the error number we want looked up, and the fourth parameter indicates what language we want the text description in.

If FormatMessage returns success, the text description is in the memory block and I copy it to the scrollable window at the bottom of the dialog box. If FormatMessage fails, I try to look up the message code in the NetMsg.dll module to see if the error is network-related. Using the handle of the NetMsg.dll module, I again call FormatMessage. You see, each DLL (or .exe) can have its own set of error codes that you can add to the module using the Message Compiler (MC.exe) and adding a resource to the module. This is what Visual Studio's Error Lookup tool allows you to do using the Modules dialog box.

Figure 1-2. The ErrorShow sample application

ErrorShow.cpp

 /****************************************************************************** Module: ErrorShow.cpp Notices: Copyright (c) 2000 Jeffrey Richter ******************************************************************************/ #include "..\CmnHdr.h" /* See Appendix A. */ #include <Windowsx.h> #include <tchar.h> #include "Resource.h" /////////////////////////////////////////////////////////////////////////////// #define ESM_POKECODEANDLOOKUP (WM_USER + 100) const TCHAR g_szAppName[] = TEXT("Error Show"); /////////////////////////////////////////////////////////////////////////////// BOOL Dlg_OnInitDialog(HWND hwnd, HWND hwndFocus, LPARAM lParam) { chSETDLGICONS(hwnd, IDI_ERRORSHOW); // Don't accept error codes more than 5 digits long Edit_LimitText(GetDlgItem(hwnd, IDC_ERRORCODE), 5); // Look up the command-line passed error number SendMessage(hwnd, ESM_POKECODEANDLOOKUP, lParam, 0); return(TRUE); } /////////////////////////////////////////////////////////////////////////////// void Dlg_OnCommand(HWND hwnd, int id, HWND hwndCtl, UINT codeNotify) { switch (id) { case IDCANCEL: EndDialog(hwnd, id); break; case IDC_ALWAYSONTOP: SetWindowPos(hwnd, IsDlgButtonChecked(hwnd, IDC_ALWAYSONTOP) ? HWND_TOPMOST : HWND_NOTOPMOST, 0, 0, 0, 0, SWP_NOMOVE | SWP_NOSIZE); break; case IDC_ERRORCODE: EnableWindow(GetDlgItem(hwnd, IDOK), Edit_GetTextLength(hwndCtl) > 0); break; case IDOK: // Get the error code DWORD dwError = GetDlgItemInt(hwnd, IDC_ERRORCODE, NULL, FALSE); HLOCAL hlocal = NULL; // Buffer that gets the error message string // Get the error code's textual description BOOL fOk = FormatMessage( FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_ALLOCATE_BUFFER, NULL, dwError, MAKELANGID(LANG_ENGLISH, SUBLANG_ENGLISH_US), (PTSTR) &hlocal, 0, NULL); if (!fOk) { // Is it a network-related error? HMODULE hDll = LoadLibraryEx(TEXT("netmsg.dll"), NULL, DONT_RESOLVE_DLL_REFERENCES); if (hDll != NULL) { FormatMessage( FORMAT_MESSAGE_FROM_HMODULE | FORMAT_MESSAGE_FROM_SYSTEM, hDll, dwError, MAKELANGID(LANG_ENGLISH, SUBLANG_ENGLISH_US), (PTSTR) &hlocal, 0, NULL); FreeLibrary(hDll); } } if (hlocal != NULL) { SetDlgItemText(hwnd, IDC_ERRORTEXT, (PCTSTR) LocalLock(hlocal)); LocalFree(hlocal); } else { SetDlgItemText(hwnd, IDC_ERRORTEXT, TEXT("Error number not found.")); } break; } } /////////////////////////////////////////////////////////////////////////////// INT_PTR WINAPI Dlg_Proc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam) { switch (uMsg) { chHANDLE_DLGMSG(hwnd, WM_INITDIALOG, Dlg_OnInitDialog); chHANDLE_DLGMSG(hwnd, WM_COMMAND, Dlg_OnCommand); case ESM_POKECODEANDLOOKUP: SetDlgItemInt(hwnd, IDC_ERRORCODE, (UINT) wParam, FALSE); FORWARD_WM_COMMAND(hwnd, IDOK, GetDlgItem(hwnd, IDOK), BN_CLICKED, PostMessage); SetForegroundWindow(hwnd); break; } return(FALSE); } /////////////////////////////////////////////////////////////////////////////// int WINAPI _tWinMain(HINSTANCE hinstExe, HINSTANCE, PTSTR pszCmdLine, int) { HWND hwnd = FindWindow(TEXT("#32770"), TEXT("Error Show")); if (IsWindow(hwnd)) { // An instance is already running, activate it and send it the new # SendMessage(hwnd, ESM_POKECODEANDLOOKUP, _ttoi(pszCmdLine), 0); } else { DialogBoxParam(hinstExe, MAKEINTRESOURCE(IDD_ERRORSHOW), NULL, Dlg_Proc, _ttoi(pszCmdLine)); } return(0); } //////////////////////////////// End of File ////////////////////////////////// 

ErrorShow.rc

 //Microsoft Developer Studio generated resource script. // #include "resource.h" #define APSTUDIO_READONLY_SYMBOLS ///////////////////////////////////////////////////////////////////////////// // // Generated from the TEXTINCLUDE 2 resource. // #include "afxres.h" ///////////////////////////////////////////////////////////////////////////// #undef APSTUDIO_READONLY_SYMBOLS ///////////////////////////////////////////////////////////////////////////// // English (U.S.) resources #if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU) #ifdef _WIN32 LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US #pragma code_page(1252) #endif //_WIN32 ///////////////////////////////////////////////////////////////////////////// // // Dialog // IDD_ERRORSHOW DIALOGEX 0, 0, 182, 42 STYLE DS_SETFOREGROUND | DS_3DLOOK | DS_CENTER | WS_MINIMIZEBOX | WS_VISIBLE | WS_CAPTION | WS_SYSMENU CAPTION "Error Show" FONT 8, "MS Sans Serif" BEGIN LTEXT "Error:",IDC_STATIC,4,4,19,8 EDITTEXT IDC_ERRORCODE,24,2,24,14,ES_AUTOHSCROLL | ES_NUMBER DEFPUSHBUTTON "Look up",IDOK,56,2,36,14 CONTROL "&On top",IDC_ALWAYSONTOP,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,104,4,38,10 EDITTEXT IDC_ERRORTEXT,4,20,176,20,ES_MULTILINE | ES_AUTOVSCROLL | ES_READONLY | NOT WS_BORDER | WS_VSCROLL, WS_EX_CLIENTEDGE END ///////////////////////////////////////////////////////////////////////////// // // DESIGNINFO // #ifdef APSTUDIO_INVOKED GUIDELINES DESIGNINFO DISCARDABLE BEGIN IDD_ERRORSHOW, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 175 TOPMARGIN, 7 BOTTOMMARGIN, 35 END END #endif // APSTUDIO_INVOKED #ifdef APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // TEXTINCLUDE // 1 TEXTINCLUDE DISCARDABLE BEGIN "resource.h\0" END 2 TEXTINCLUDE DISCARDABLE BEGIN "#include ""afxres.h""\r\n" "\0" END 3 TEXTINCLUDE DISCARDABLE BEGIN "\r\n" "\0" END #endif // APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // Icon // // Icon with lowest ID value placed first to ensure application icon // remains consistent on all systems. IDI_ERRORSHOW ICON DISCARDABLE "ErrorShow.ico" #endif // English (U.S.) resources ///////////////////////////////////////////////////////////////////////////// #ifndef APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // Generated from the TEXTINCLUDE 3 resource. // ///////////////////////////////////////////////////////////////////////////// #endif // not APSTUDIO_INVOKED 



Programming Applications for Microsoft Windows
Programming Applications for Microsoft Windows (Microsoft Programming Series)
ISBN: 1572319968
EAN: 2147483647
Year: 1999
Pages: 193

flylib.com © 2008-2017.
If you may any questions please contact us: flylib@qtcs.net