C++ MSXML内存泄漏

C++ MSXML内存泄漏,c++,memory-leaks,msxml,msxml6,msxml4,C++,Memory Leaks,Msxml,Msxml6,Msxml4,我必须处理一个使用MSXML将测量数据写入简单XML文件的遗留应用程序。基本上,这就是正在发生的事情: MSXML2::IXMLDOMDocument2Ptr pXmlDocument; HRESULT comResult = CXMLUtil::createXMLDocument(pXmlDocument); // ... check HRESULT ... MSXML2::IXMLDOMNodePtr pXmlMainNode = pXmlDocument.GetInterfacePtr()

我必须处理一个使用MSXML将测量数据写入简单XML文件的遗留应用程序。基本上,这就是正在发生的事情:

MSXML2::IXMLDOMDocument2Ptr pXmlDocument;
HRESULT comResult = CXMLUtil::createXMLDocument(pXmlDocument);
// ... check HRESULT ...
MSXML2::IXMLDOMNodePtr pXmlMainNode = pXmlDocument.GetInterfacePtr();
MSXML2::IXMLDOMNodePtr pXmlSubNode = CXMLUtil::AppendNewElement(pXmlDocument, pXmlMainNode, RootTag, "");
// ... create further nodes ...
MSXML2::IXMLDOMNodePtr pXmlTmpNode = CXMLUtil::AppendNewElement(
pXmlDocument,
pXmlDataSetNode,
measDataTag,
measdata,
numberOfDataItems );
// ... append further items ...
在每个项目之后,调用
pXmlTmpNode.Release()
。最后,所有其他节点以及
pXmlDocument
都被
释放

createXMLDocument
定义如下:

HRESULT CXMLUtil::createXMLDocument(MSXML2::IXMLDOMDocument2Ptr &pXmlDocument) {
    MSXML2::IXMLDOMDocument2 *xmlDocument = 0;
    HRESULT comError = CoCreateInstance(__uuidof(MSXML2::DOMDocument),NULL,CLSCTX_INPROC_SERVER,IID_PPV_ARGS(&xmlDocument));
    if (comError) return comError;
    xmlDocument->put_async(VARIANT_FALSE);
    xmlDocument->put_validateOnParse(VARIANT_FALSE);
    xmlDocument->put_resolveExternals(VARIANT_FALSE);
    xmlDocument->put_preserveWhiteSpace(VARIANT_TRUE);
    MSXML2::IXMLDOMDocument2Ptr ptr(xmlDocument);
    pXmlDocument = ptr;
    return comError;
}
对于附加新元素(即
未生成的字符
数组),应用此函数:

MSXML2::IXMLDOMNodePtr CXMLUtil::AppendNewElement(MSXML2::IXMLDOMDocument2Ptr pXMLDom, MSXML2::IXMLDOMNodePtr pParent, CComBSTR strElementName, unsigned char* pData, long nData) {
    MSXML2::IXMLDOMNodePtr pData1 = pXMLDom->createElement(BSTR(strElementName));
    pData1->put_dataType(CComBSTR(_T("bin.base64")));
    SAFEARRAY* psa = SafeArrayCreateVector( VT_UI1, 0L, nData);
    psa->pvData = pData;
    VARIANT var;
    VariantInit(&var);
    var.parray = psa;
    var.vt = (VT_ARRAY | VT_UI1 );
    pData1->nodeTypedValue = var;
    pParent->appendChild(pData1);
    SafeArrayDestroy(psa);
    return pData1;
}

无论是使用
#import
还是
#import
,似乎都存在内存泄漏。由于
measdata
等可能会很大,这是一个相当大的问题。我能做些什么使代码正常工作吗? 谢谢,马修

MSXML2::IXMLDOMDocument2 *xmlDocument = 0;
HRESULT comError = CoCreateInstance(__uuidof(MSXML2::DOMDocument),
    NULL,CLSCTX_INPROC_SERVER,IID_PPV_ARGS(&xmlDocument));
...
MSXML2::IXMLDOMDocument2Ptr ptr(xmlDocument);
pXmlDocument = ptr;
此代码泄漏
xmlDocument
ptr(xmlDocument)
额外添加了一个
AddRef
,但是没有
版本
用于xmlDocument超出范围。您在任何地方都使用智能PTR,没有理由不在这里使用,可能是这样的:

MSXML2::IXMLDOMDocument2Ptr xmlDocument;
HRESULT comError = CoCreateInstance(__uuidof(MSXML2::DOMDocument),
    NULL,CLSCTX_INPROC_SERVER,IID_PPV_ARGS(&xmlDocument));
...
pXmlDocument = xmlDocument;

“似乎存在内存泄漏”:您是如何确定的?多次调用函数并观察进程的内存消耗。“进程的内存消耗”这是什么意思?具体来说,是哪个计数器。顺便说一句,
if(comError)
通常应该是。如果您在solaris上,请使用此工具:
MSXML2::IXMLDOMDocument2Ptr xmlDocument
无法完成;它告诉我这是一个抽象类。然而,在创建
ptr
指针之后添加一个额外的
Release
,成功了。非常感谢。