当我在发布模式下编译时,我在std :: string的重新分配上有堆损坏。
实际上,在名为Atc.dll
的DLL中,我调用了另一个名为Utilies.dll
的DLL中的函数。在Atc.dll
中我的函数结束时,我有堆损坏。
我在Atc.dll
中的功能:
void CoreController::readConfigXMLFile()
{
ConfigFileManager configFileManager;
std::string pathXmlFilesTemp = configFileManager.getPathXMLFiles();
}
然后,这是getPathXMLFiles
中声明的函数Utilies.dll
:
std::string ConfigFileManager::getPathXMLFiles()
{
bool err = false;
std::string ret = "";
if (!mParserXml.getNodeTextValue(sPathXmlFilesTag, ret))
{
err = true;
}
if (err)
{
ret = sPathXMLFilesDefault;
}
return ret;
}
注意:如果在这里我没有调用函数getNodeTextValue
,则不会发生堆损坏。因此,函数getNodeTextValue
与getPathXMLFiles
:
bool ParseXml::getNodeTextValue(const string& path, string& nodeValue)
{
DOMNode* child = XmlNode::getChildNodeByPath(xmlNode, path);
//If path is valid.
if(XmlNode::isValid(child))
{
char* str = XmlNode::getTextValue(child);
//If node contains text.
if(str != NULL)
{
nodeValue = str;
XmlNode::freeXMLString(str);
return true;
}
}
//Either path is not valid or node does not contain text
nodeValue = "";
return false;
}
这就是发生堆损坏的地方(STL):
void _Tidy(bool _Built = false,
size_type _Newsize = 0)
{ // initialize buffer, deallocating any storage
if (!_Built)
;
else if (this->_BUF_SIZE <= this->_Myres)
{ // copy any leftovers to small buffer and deallocate
_Elem *_Ptr = this->_Bx._Ptr;
if (0 < _Newsize)
_Traits::copy(this->_Bx._Buf, _Ptr, _Newsize);
this->_Alval.deallocate(_Ptr, this->_Myres + 1); // <-- HEAP CORRUPTION
}
this->_Myres = this->_BUF_SIZE - 1;
_Eos(_Newsize);
}
有人可以告诉我为什么会发生这种堆损坏以及如何避免它?
感谢您的帮助。
答案 0 :(得分:8)
通常的原因(在Windows上)是你在1 dll中分配内存,然后在释放时将其传递给另一个dll。通常情况下这很好,但是如果每个dll都使用不同的CRT(C运行时库)构建,那么就会出现这样的问题。原因是调试CRT的内存分配与发布CRT略有不同(主要是用保护块填充所有alloc来显示缓冲区溢出等)。
因此,请确保所有dll(和您的应用)都使用相同的CRT构建。