天天看點

《windows核心程式設計》筆記(一)

1,windows對程式錯誤的處理,

int APIENTRY _tWinMain(HINSTANCE hInstance,HINSTANCE hPrevInstance,LPTSTR    lpCmdLine,int       nCmdShow)

{

    LPVOID lpMsgBuf;

    HANDLE hFile = ::CreateFile(_T("C:\\12.txt"),0,0,NULL,OPEN_EXISTING,0,NULL);//打開檔案

    if(INVALID_HANDLE_VALUE==hFile)

    {//檔案不存在

        FormatMessage(FORMAT_MESSAGE_ALLOCATE_BUFFER | FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS, NULL, GetLastError(),0, (LPTSTR) &lpMsgBuf,0,NULL);

        MessageBox( NULL, (LPCWSTR)lpMsgBuf, _T("錯誤資訊"), MB_OK | MB_ICONINFORMATION );

        LocalFree( lpMsgBuf );

    }

        return 0;

}

調試時,在Watch視窗輸入“@err,hr”,就可以顯示線程的最後錯誤代碼的号碼和該錯誤的描述資訊。

2008060701.jpg

VC6.0還帶了一個實用小程式,可以用來将錯誤代碼轉換為相應的文本描述資訊。

2008060702.jpg

書中給出了一個模仿VC6自帶的那個Error Lookup實用程式的示例:

#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);

   case IDC_ERRORCODE: 

      EnableWindow(GetDlgItem(hwnd, IDOK), Edit_GetTextLength(hwndCtl) > 0);//設定“lookup"按鈕是否enable

   case IDOK:

      // Get the error code

      DWORD dwError = GetDlgItemInt(hwnd, IDC_ERRORCODE, NULL, FALSE);//擷取錯誤代碼号碼

      HLOCAL hlocal = NULL;   // Buffer that gets the error message string

      // Use the default system locale since we look for Windows messages.

      // Note: this MAKELANGID combination has 0 as value

      DWORD systemLocale = MAKELANGID(LANG_NEUTRAL, SUBLANG_NEUTRAL);//本地語言

      // Get the error code's textual description

      BOOL fOk = FormatMessage(

         FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS |

         FORMAT_MESSAGE_ALLOCATE_BUFFER, 

         NULL, dwError, systemLocale, 

         (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) 

         {

            fOk = FormatMessage(

               FORMAT_MESSAGE_FROM_HMODULE | FORMAT_MESSAGE_IGNORE_INSERTS |

               FORMAT_MESSAGE_ALLOCATE_BUFFER,

               hDll, dwError, systemLocale,

               (PTSTR) &hlocal, 0, NULL);

            FreeLibrary(hDll);

         }

      }

      if (fOk && (hlocal != NULL))

         SetDlgItemText(hwnd, IDC_ERRORTEXT, (PCTSTR) LocalLock(hlocal)); 

         LocalFree(hlocal);

      } 

      else 

         SetDlgItemText(hwnd, IDC_ERRORTEXT, TEXT("No text found for this error number."));

   }

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);//設定為最前的視窗

   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);

這裡用到了幾個宏定義,下面這個是用來指定消息處理函數的

// The normal HANDLE_MSG macro in WindowsX.h does not work properly for dialog

// boxes because DlgProc returns a BOOL instead of an LRESULT (like

// WndProcs). This chHANDLE_DLGMSG macro corrects the problem:

#define chHANDLE_DLGMSG(hWnd, message, fn)                 \

   case (message): return (SetDlgMsgResult(hWnd, uMsg,     \

      HANDLE_##message((hWnd), (wParam), (lParam), (fn))))

下面這個是用來為視窗設定大/小圖示

// Sets the dialog box icons

inline void chSETDLGICONS(HWND hWnd, int idi) 

   SendMessage(hWnd, WM_SETICON, ICON_BIG,  (LPARAM) 

      LoadIcon((HINSTANCE) GetWindowLongPtr(hWnd, GWLP_HINSTANCE), 

         MAKEINTRESOURCE(idi)));

   SendMessage(hWnd, WM_SETICON, ICON_SMALL, (LPARAM) 

      MAKEINTRESOURCE(idi)));

本文轉自Phinecos(洞庭散人)部落格園部落格,原文連結:http://www.cnblogs.com/phinecos/archive/2008/06/07/1215565.html,如需轉載請自行聯系原作者

下一篇: 30.10. MySQL

繼續閱讀