MessageBox标题乱码

1.查一下m_pszAppName是否有被修改

2.看下紧接着是否有这样一句代码:

AfxGetModuleState()->m_lpszCurrentAppName = m_pszAppName;

没有的话加上就好。

修改AppName很多人参考MSDN,可MSDN上的例子有缺陷!

 

 

 

原因大概如下:

m_pszAppName与m_lpszCurrentAppName未保持一致造成的。查看MFC源码,在程序最开始AfxWinInit中调用CWinApp::SetCurrentHandles,其中有一句pModuleState->m_lpszCurrentAppName = m_pszAppName,因此两个指针必须保持一致。

软件在InitInstance中设置了m_pszAppName,未同时修改m_lpszCurrentAppName,free(m_pszAppName)后造成m_lpszCurrentAppName内存无效,成为野指针。

MessageBox在弹框时如果未传入标题,则会使用AfxGetAppName作为标题名,而AfxGetAppName返回的是m_lpszCurrentAppName,此时该指针指向的内存已经失效,导致了标题乱码。

 

参考文章:https://blog.csdn.net/wdsswadjsn/article/details/3220338

摘录如下:

As far as I understand, the MSDN documentation regarding how to change
CWinApp::m_pszAppName is incorrect. Following the documentation can lead to
memory access violation errors. Additionally, the KB article 154744 also
gives wrong advise about how to change m_pszAppName.

Here's why:

At the very beginning of application initialization, AfxWinInit calls
CWinApp::SetCurrentHandles, which caches the current value of the
m_pszAppName pointer as follows:

pModuleState->m_lpszCurrentAppName = m_pszAppName;

That is, the module state struct holds a copy of the m_pszAppName pointer.
Now, if you change m_pszAppName in InitInstance as adviced in MSDN, you
still have the old pointer value in pModuleState->m_lpszCurrentAppName. The
AfxGetAppName() function returns AfxGetModuleState()->m_lpszCurrentAppName.

Many times replacing m_pszAppName does not lead into problems because
_tcsdup will return the same pointer value as before. But of course, the
pointer value can be different, and if it is, it can lead into a crash later
when someone is calling AfxGetAppName().

For example, the following code in InitInstance is almost certain to fail
because the app name is relatively long and causes _tcsdup to return a
pointer value that is different than before:

free( ( void* )m_pszAppName ); m_pszAppName = NULL;
m_pszAppName = _tcsdup(
"ABCABCABCABCABCABCABCABCABCABCABCABCABCABCABCABCABC" );
const TCHAR* ptsz = AfxGetAppName();
_ASSERTE( lstrcmp( ptsz, m_pszAppName ) == 0 ); // TYPICALLY FAILS

Now, my question is: Can Microsoft fix the buggy documentation? And, what is
the correct way of changing m_pszAppName. Is the following safe in
InitInstance:

free( ( void* )m_pszAppName ); m_pszAppName = NULL;
m_pszAppName = _tcsdup( "<new name>" );
AfxGetModuleState()->m_lpszCurrentAppName = m_pszAppName;

 

posted @ 2021-09-03 16:01  快雪  阅读(649)  评论(0编辑  收藏  举报