Microsoft KB Archive/150789

= FIX: DFX_Bool Calls Default with AFX_RFX_LONGBINARY =

Article ID: 150789

Article Last Modified on 11/18/2003

-

APPLIES TO


 * Microsoft Visual C++ 4.0 Standard Edition
 * Microsoft Visual C++ 4.1 Subscription
 * Microsoft Foundation Class Library 4.2

-



This article was previously published under Q150789



SYMPTOMS
Memory adjacent to the BOOL variable gets overwritten when working with a BOOL CDaoRecordset field data member.



CAUSE
The DFX_Bool function delegates the Fixup case to CDaoFieldExchange::Default and incorrectly passes AFX_RFX_LONGBINARY as the field data type.



RESOLUTION
To resolve this problem, copy the DFX_Bool function to the project and give it a different name. For example, rename it DFX_Bool2. In the call to CDaoFieldExchange::Default, change the field data type from AFX_RFX_LONGBINARY to AFX_RFX_BOOL by using the following code:

Change this code case CDaoFieldExchange::Fixup: // Convert BOOL value from AFX_DAO_TRUE/FALSE to TRUE/FALSE value = (value != AFX_DAO_FALSE);

pFX->Default(lpszName, (void*)&value,        AFX_RFX_LONGBINARY, dwBindOptions); return; to this code: case CDaoFieldExchange::Fixup: // Convert BOOL value from AFX_DAO_TRUE/FALSE to TRUE/FALSE value = (value != AFX_DAO_FALSE);

pFX->Default(lpszName, (void*)&value,        AFX_RFX_BOOL, dwBindOptions);       // <<-- Change to AFX_RFX_BOOL return; Then, change the class of the CDaoRecordset-derived DoFieldExchange function to call this new function in place of calling DFX_Bool.



STATUS
Microsoft has confirmed this to be a bug in the Microsoft products listed at the beginning of this article. This bug was corrected in Visual C++ 32-bit Edition version 4.2.



MORE INFORMATION
The code for the Fixup case in CDaoFieldExchange::Default is: case Fixup: if (m_prs->GetFieldLength(m_nField-1) == DAO_NULL) {        // Set the value to PSEUDO NULL and mark the status NULL SetNullValue(pv, dwColumnType); m_prs->SetNullFieldStatus(m_nField-1); }     return; The dwColumn type is the variable that is incorrectly set to AFX_RFX_LONGBINARY in DFX_Bool. Note that SetNullValue is called with the value passed in the second parameter. The code for SetNullValue (showing relevant cases) is: void CDaoFieldExchange::SetNullValue(void* pv, DWORD dwDataType) {     switch (dwDataType) {        .         ..

case AFX_RFX_LONGBINARY: ((CLongBinary*)pv)->m_dwDataLength = 0; break;

case AFX_RFX_BOOL: *(BOOL*)pv = AFX_RFX_BOOL_PSEUDO_NULL; break;

.       .        .    } } Note that the AFX_RFX_BOOL case (the one that should be called) sets the BOOL variable to the constant AFX_RFX_BOOL_PSEUDO_NULL. The AFX_RFX_LONGBINARY case (incorrectly called in the MFC source) sets the m_dwDataLength member of a CLongBinary object (at an offset in the object beyond the size of a BOOL) to zero. Whatever is adjacent to the BOOL variable has 4 bytes of its memory overwritten. The symptoms of this memory overwrite depend on what that variable was used for. There can also be no symptoms.

Additional query words: kbVC400bug 4.00 4.10 4.20 vcfixlist420 MfcDAO

Keywords: kbbug kbfix kbdatabase KB150789

-

[mailto:TECHNET@MICROSOFT.COM Send feedback to Microsoft]

© Microsoft Corporation. All rights reserved.