1. 程式人生 > >MFC程序打開文件對話框出錯的問題解決

MFC程序打開文件對話框出錯的問題解決

protect pat lpc lan file cst nat bing 縮小

前幾天從網上下了個圖像分析的mfc小程序,是VC6的

用VC6在本地編譯生成都沒問題。執行起來彈出一個未處理的錯誤,程序崩潰退出。

想起來原來遇到過打開文件對話框方面的問題,當時項目時間緊張未能深究。

這次要好好看下這個問題。

詳細做法就是深入仔細的跟蹤、跟蹤、跟蹤。

。。

應用代碼,跟進

MFC的代碼,跟進

Alt+8調出反匯編,跟進。

重復多次重復追蹤、縮小目標。確定問題是:在CFileDialog 的析構函數中,調用了CString 的析構函數,

恰恰是析構CSring 出錯了。

CFileDialog 的定義例如以下,就是析構這個 m_strFilter 出錯的。
class CFileDialog : public CCommonDialog
{
DECLARE_DYNAMIC(CFileDialog)

public:
// Attributes
OPENFILENAME m_ofn; // open file parameter block

// Constructors
CFileDialog(BOOL bOpenFileDialog, // TRUE for FileOpen, FALSE for FileSaveAs
LPCTSTR lpszDefExt = NULL,
LPCTSTR lpszFileName = NULL,
DWORD dwFlags = OFN_HIDEREADONLY | OFN_OVERWRITEPROMPT,
LPCTSTR lpszFilter = NULL,
CWnd* pParentWnd = NULL);

......省略n 多行

protected:
BOOL m_bOpenFileDialog; // TRUE for file open, FALSE for file save
CString m_strFilter; // filter string
// separate fields with ‘|‘, terminate with ‘||\0‘
TCHAR m_szFileTitle[64]; // contains file title after return
TCHAR m_szFileName[_MAX_PATH]; // contains full path name after return

OPENFILENAME* m_pofnTemp;

virtual BOOL OnNotify(WPARAM wParam, LPARAM lParam, LRESULT* pResult);
};

發現這裏面找的m_strFilter 的地址就不正確

0012F7EC 是 CFileDialog 實例的地址

析構m_strFilter 找的是0012F8A8,再運行就會出錯。去這個地址瞄一眼。感覺就不正確啊

於是在構造函數跟蹤時。發現m_strFilter 的地址是0012F89C

比較兩次合成ecx 中m_strFilter的this指針時。非常明顯不同

add ecx 0b0h ;構造時

add ecx 0bch ;析構時

喔喔,算偏移嘛。怎麽會不一樣呢,這個,再花時間研究下吧。

嗐呀,說不定有人研究過啦。靈機一動,bing 下"add ecx 0b0h",果然。第一條就命中

http://blog.titilima.com/show-590-1.html。這裏已有答案。

感謝作者李馬先生 :-)

原因講的非常清楚了。

但是怎麽改呢,難道去動vs 的源代碼。

當然VS的源代碼也是能夠改的。只是呢,通過定義追溯文件發現到了

C:\Program Files\Microsoft SDKs\Windows\v7.1\Include 以下

當初MFC4.2 的年代應該還沒有v7.1 的版本號呀,去看下文件夾設定吧

v7.1 的include 在最上面。

果斷移到最下。所有又一次生成,沒問題啦,奧也。

技術分享

自已是否動過這個設定記不清了。亦或是後來裝VS2010或DDK的時候影響了??

總之呢,我們能夠覺得。就VC6本身來說還是沒問題的,因為安裝多個開發環境造成的沖突是本問題出現的原因。

??

MFC程序打開文件對話框出錯的問題解決