libxml 2解析xml文字列


最近、sdkインタフェースをカプセル化して内部で使用しているとき、元のプロジェクトはc++で開発されていました.xml解析ツールはTinyxmlを使っています.いいですね.少なくともメモリの解放の問題を考えなくてもいいです.これもc++リソース管理のメリットです...
cのインタフェースが提供されているのでtinyxmlは明らかに使えません.後でlibxml 2を使いたいと思っています.彼はC言語で開発したからです.ネット上で既成品を探して、結果はすべて解析ファイルであることを発見して、xml文字列を解析する過程を記録しましょう、主にメモリの管理に気をつけてOKしました:
xmlNodePtr GetNextXmlNode(xmlNodePtr pstXmlNode)
{
    pstXmlNode = pstXmlNode->next;
    while(pstXmlNode)
    {
        if (XML_ELEMENT_NODE == pstXmlNode->type)
        {
            return pstXmlNode;
        }
        pstXmlNode = pstXmlNode->next; 
    } 
}


xmlNodePtr GetChildrenXmlNode(xmlNodePtr pstXmlNode)
{
    pstXmlNode = pstXmlNode->children;
    while(pstXmlNode)
    {
        if (XML_ELEMENT_NODE == pstXmlNode->type)
        {
            return pstXmlNode;
        }
        pstXmlNode = pstXmlNode->next; 
    }
}
static int ParseAppReqMsg(char *pszPayload , APP_RES_INFO *pstResInfo)
{ 
    if ((NULL == pstAppResInfo) || (NULL == pszRecvMsg))
	{
        return -1;
	}
    int nXmlSize = 0; 
    nXmlSize = strlen(pszPayload);
    xmlDocPtr pstXmlDoc = NULL;
    xmlNodePtr pstXmlNode = NULL;
    xmlNodePtr pstXmlSubNode = NULL;
    char *pszXmlNodeContent = NULL;
    pstXmlDoc = xmlParseMemory(pszPayload, nXmlSize);
    if (!pstXmlDoc)
    {
        printf("%s_%d: xmlParseMemory failed ,the xml is: %s", _LOG_TRACE_, pszPayload);
        return -1;
    }
    pstXmlNode = xmlDocGetRootElement(pstXmlDoc);
    if(!pstXmlNode)
    {
        xmlFreeDoc(pstXmlDoc);
        printf("%s_%d: xmlDocGetRootElement failed .", _LOG_TRACE_);
        return -1;
    }
    pstXmlSubNode = GetChildrenXmlNode(pstXmlNode);
    while(NULL != pstXmlSubNode)
    {
        pszXmlNodeContent = (char *)xmlNodeGetContent(pstXmlSubNode);
        if (0 == xmlStrncmp(pstXmlSubNode->name,XML_NODE_NAME_MSG_TYPE,sizeof(XML_NODE_NAME_MSG_TYPE)))
        {
            //to do      :UpdateDevConf,      
        }
        else if (0 == xmlStrncmp(pstXmlSubNode->name,XML_NODE_NAME_MSG_PROTOCAL,sizeof(XML_NODE_NAME_MSG_PROTOCAL)))
        {
            //to do      :1.0  ,      
        }
        else if (0 == xmlStrncmp(pstXmlSubNode->name,XML_NODE_NAME_MSG_PARAM,sizeof(XML_NODE_NAME_MSG_PARAM)))
        {
            char *pszXmlParamsContent = NULL; 
            xmlNodePtr pstXmlSubParamsNode = NULL;
            pstXmlSubParamsNode = GetChildrenXmlNode(pstXmlSubNode);
            while(NULL != pstXmlSubParamsNode)
            {
                pszXmlParamsContent = (char *)xmlNodeGetContent(pstXmlSubParamsNode);
                if (0 == xmlStrncmp(pstXmlSubNode->name,XML_NODE_NAME_MSG_PARAM_APP_NO,sizeof(XML_NODE_NAME_MSG_PARAM_APP_NO)))
                {
                    strncpy(pstResInfo->szAppNo, pszXmlParamsContent, APP_NO_SIZE -1);
                    pstResInfo->szAppNo[APP_NO_SIZE -1] = 0;
                }
                else if (0 == xmlStrncmp(pstXmlSubNode->name,XML_NODE_NAME_MSG_PARAM_CONFIGURL,sizeof(XML_NODE_NAME_MSG_PARAM_CONFIGURL)))
                {
                    strncpy(pstResInfo->szConfigUrl, pszXmlParamsContent, URL_SIZE -1);
                    pstResInfo->szAppNo[URL_SIZE -1] = 0;
                }
                else if (0 == xmlStrncmp(pstXmlSubNode->name,XML_NODE_NAME_MSG_PARAM_CONFIGMD5,sizeof(XML_NODE_NAME_MSG_PARAM_CONFIGMD5)))
                {
                    strncpy(pstResInfo->szConfigMd5, pszXmlParamsContent, MD5_SIZE -1);
                    pstResInfo->szAppNo[MD5_SIZE -1] = 0;
                }
                
                xmlFree(pszXmlParamsContent);
                pszXmlParamsContent = NULL;
                pstXmlSubParamsNode = GetNextXmlNode(pstXmlSubParamsNode);
                
            }
        }
        
        xmlFree(pszXmlNodeContent);
        pszXmlNodeContent= NULL;
        pstXmlSubNode = GetNextXmlNode(pstXmlSubNode);
        
    }
    xmlFreeDoc(pstXmlDoc);
	return 0;
}