2012-11-06 37 views
0

我有一個奇怪的問題,我一直無法診斷,並希望有人能夠至少指向正確的方向。我有一個C++ MFC應用程序,它從各種來源收集數據並將其顯示在屏幕上。然而,經過一段隨機時間間隔(通常大約5-10分鐘)後,顯示屏會以我從未見過的方式「損壞」,或者可以按照下圖所示的方式進行追蹤(左側正常,右側已損壞):MFC應用程序中的奇怪控制顯示損壞

Example of Display Corruption

基本症狀是:

  • 向上/向下箭頭的圖像變成 「5」 S和 「6」 秒。
  • 打開組合框列表會導致只顯示項目文本(列表邊框和滾動條未顯示)。
  • 某些控件上的背景色不會更新或正確顯示。
  • Z順序被破壞,應用程序通過放置在頂部的其他窗口控制「泄漏」。
  • 在應用程序焦點按下打印屏幕時不再將窗口捕獲到剪貼板。
  • 關閉並重新打開窗口什麼都不做。
  • 重新啓動應用程序會使事情恢復正常。

事情我已經想消滅作爲一個可能的原因包括:

  • 操作系統&計算機:同樣的問題也存在於各種系統從Windows 7-64位到Windows Xp-32位。
  • 多線程:我添加了一個互斥鎖,以防止顯示更新同時發生,但它沒有效果(如預期的那樣)。
  • 內存損壞:這一直是我的假設,但根本沒有任何記憶腐敗跡象。基礎顯示代碼已經使用了多年,沒有類似的問題以及基礎網絡消息庫。
  • 具體代碼:我已將問題的範圍縮小到其他各種顯示無問題的特定對話框中。他們都使用相同的基本代碼,這似乎表明問題在於對話框的特定顯示代碼。到目前爲止,究竟如何或爲什麼會發生這個問題。

任何關於什麼原因或如何縮小範圍的想法是很好的。

更新1: 做一些更多的定時/重複測試,它看起來像這樣留下一個對話運行一會兒導致該問題。問題出現之前,金額時間始終在300-400秒之間。

+0

看起來像是什麼,某處導致未定義的行爲 – Dan

+0

如果您嘗試從多個線程更新控件,可能會這樣做。您應該通過單個線程完成與Windows的所有交互。 –

+0

在「工作人員」線程中更新了控件的一小部分,但禁用此操作對此問題沒有影響。我已經進行了雙重檢查,並且所有控制更新都是從主線程中的WM_TIMER觸發的(工作線程只是以線程安全的方式收集數據)。 – uesp

回答

1

這聽起來像你的應用程序可能泄露GDI對象。要檢查是否屬於這種情況,請打開任務管理器並啓用GDI Objects列。觀察你的過程的數量,看看它是否持續增加。

如果確實如此,您應該閱讀Detect and Plug GDI Leaks in Your Code with Two Powerful Tools for Windows XP。該MSDN文章還提供了一個名爲GDILeaks.exe的工具,可幫助您識別您的GDI泄漏。

在這些症狀在短時間內出現的情況下,它應該是重複繪製的東西,不能正確釋放GDI資源。可能在窗口過程中(或稱之爲)(例如OnPaint)。

+0

確實,GDI對象數量增加,並且一旦達到10,000就會出現顯示問題。我在對話框中有3個自定義控件,所以問題可能在某處。我覺得這是一件簡單的事情! – uesp

+0

原來是在調用:: CreateSolidBrush()30次/秒的OnCtlColor()處理程序中,而不是創建一次筆刷並返回該句柄。不知道爲什麼我這樣做,但經過快速測試後,我確認GDI手柄不再泄漏。 – uesp

0

如果我沒有記錯的Windows的GUI使用這些小圖標的TTF(?)字體,看起來字體被莫名其妙地銷燬(DeleteObject的被稱爲與字體的處理?)

+0

我嘗試尋找如何顯示這些箭頭但找不到任何東西。在那裏有一些自定義的字體代碼,我會仔細檢查以確保我沒有刪除/關閉我不應該的東西。 – uesp

+0

我註釋了對話框中使用的自定義字體,但它沒有效果。代碼中沒有任何地方我實際上刪除/關閉句柄,直到對話框被銷燬(這從來沒有發揮作用)。 – uesp

相關問題