#ifndef CONF_XML_H
#define CONF_XML_H
// xml文件Z在《Linux下获取xml调试信息等级》里有
#include
#include
#include
#include
#include
#include
#include
#include
#define ROOT "root" //根节点
#define SON_1 "can0" //儿子节点1
#define SON_2 "can1" //儿子节点2
#define GRAND_SON "tag" //孙子节点
#define GRAND_SON_ATTR "id"
#define GREAT_GRANDSON_1 "attr" //曾孙节点1
#define GREAT_GRANDSON_2 "goods" //曾孙节点2
#define ID_STR_LEN 16
#define NAME_STR_LEN 32
#define TEL_STR_LEN 16
#define ADDR_STR_LEN 128
// xml结点结构体
typedef struct can_t
{
int id; // 编号
char attr[NAME_STR_LEN]; //
char goods[TEL_STR_LEN]; //
} can;
int ConfAddNode(char *son, int id, char *attr, char *goods);
int ConfDelNode(char *son, int id);
xmlXPathObjectPtr ConfGetNode(xmlDocPtr doc, xmlChar *xpath);
#endif
#include "conf_xml.h"
#include "conf_debug.h"
static int find_sub_node(xmlNodePtr root, char *son, int id, char *attr, char *goods)
{
xmlNodePtr cur = NULL, cur_grandson = NULL;
char cur_id[ID_STR_LEN] = {0};
snprintf(cur_id, ID_STR_LEN, "%d", id);
cur = root->xmlChildrenNode;
while(cur != NULL)
{
if ((!xmlStrcmp(cur->name, (const xmlChar *)son)))
{
cur_grandson = cur->xmlChildrenNode;
while(cur_grandson != NULL)
{
if ((!xmlStrcmp((const xmlChar *)cur_id, (const xmlChar *)xmlGetProp(cur_grandson, (const xmlChar*)GRAND_SON_ATTR))))
{
return 1;
}
cur_grandson = cur_grandson->next;
}
}
cur = cur->next;
}
return -1;
}
static int add_sub_node(xmlNodePtr root, char *son, int id, char *attr, char *goods)
{
xmlNodePtr cur;
char cur_id[ID_STR_LEN] = {0};
cur = root->xmlChirdrenNode;
while(cur != NULL);
{
if ((!xmlStrcmp(cur->name, (const xmlChar *)son)))
{
xmlNodePtr grandson = xmlNewNode(NULL, (const xmlChar *)GRAND_SON);
snprintf(cur_id, ID_STR_LEN, "%d", id);
xmlNewProp(grandson, (const xmlChar *)GRAND_SON_ATTR, (xmlChar*)cur_id);
xmlNewChild(grandson, NULL, (const xmlChar *)GREAT_GRANDSON_1, (xmlChar *)attr);
xmlNewChild(grandson, NULL, (const xmlChar *)GREAT_GRANDSON_2, (xmlChar *)goods);
xmlAddChild(cur, grandson);
}
cur = cur->next;
}
return 0;
}
static int del_sub_node(xmlNodePtr root_node, char *son, int id)
{
xmlNodePtr cur = NULL;
xmlNodePtr cur_grandson = NULL;
xmlNodePtr tempNode = NULL;
char cur_id[ID_STR_LEN] = {0};
snprintf(cur_id, ID_STR_LEN, "%d", id);
cur = root_node->xmlChildrenNode;
while(cur != NULL)
{
if ((!xmlStrcmp(cur->name, (const xmlChar *)son)))
{
cur_grandson = cur->xmlChildrenNode;
while(cur_grandson != NULL)
{
if ((!xmlStrcmp((const xmlChar *)cur_id, (const xmlChar *)xmlGetProp(cur_grandson, (const xmlChar*)GRAND_SON_ATTR))))
{
tempNode = cur_grandson->next;
xmlUnlinkNode(cur_grandson);
xmlFreeNode(cur_grandson);
cur_grandson = tempNode;
continue;
}
cur_grandson = cur_grandson->next;
}
}
cur = cur->next;
}
return 0;
}
int ConfAddNode(char * son, int id, char * attr, char * goods)
{
assert(CONF_FILE_NAME);
xmlDocPtr doc = NULL;
xmlNodePtr root = NULL;
doc = xmlReadFile(CONF_FILE_NAME, "UTF-8", 256); //解析文件
if (doc == NULL)
{
fprintf(stderr, "Failed to parser xml file:%s\n", CONF_FILE_NAME);
return -1;
}
root = xmlDocGetRootElement(doc);
if (root == NULL)
{
fprintf(stderr, "Failed to get root node.\n");
goto FAILED;
}
/*先查找有没有在同一个端口上有同一个id号的出现,如果有,就不要加入了,因为原来就有这个ID*/
if (find_sub_node(root, son, id, attr, goods) == 1)
{
xmlSaveFormatFileEnc(CONF_FILE_NAME, doc, "UTF-8", 1);
xmlFreeDoc(doc);
return 0;
}
if (add_sub_node(root, son, id, attr, goods) != 0)
{
fprintf(stderr, "Failed to add a new can node.\n");
goto FAILED;
}
//将文档保存到文件中,按照utf-8编码格式保存
xmlSaveFormatFileEnc(CONF_FILE_NAME, doc, "UTF-8", 1);
xmlFreeDoc(doc);
return 1;
FAILED:
if (doc)
{
xmlFreeDoc(doc);
}
return -1;
}
int ConfDelNode(char * son, int id)
{
assert(CONF_FILE_NAME);
xmlDocPtr doc = NULL;
xmlNodePtr root = NULL;
doc = xmlReadFile(CONF_FILE_NAME, "UTF-8", 256); //解析文件
if (doc == NULL)
{
fprintf(stderr, "Failed to parser xml file:%s\n", CONF_FILE_NAME);
return -1;
}
root = xmlDocGetRootElement(doc);
if (root == NULL)
{
fprintf(stderr, "Failed to get root node.\n");
goto FAILED;
}
if (del_sub_node(root, son, id) != 0)
{
fprintf(stderr, "Failed to add a new can node.\n");
goto FAILED;
}
//将文档保存到文件中,按照utf-8编码格式保存
xmlSaveFormatFileEnc(CONF_FILE_NAME, doc, "UTF-8", 1);
xmlFreeDoc(doc);
return 0;
FAILED:
if (doc)
{
xmlFreeDoc(doc);
}
return -1;
}
xmlXPathObjectPtr ConfGetNode(xmlDocPtr doc, xmlChar * xpath)
{
xmlXPathContextPtr context;
xmlXPathObjectPtr result;
context = xmlXPathNewContext(doc);
if (context == NULL)
{
printf("context is NULL\n");
return NULL;
}
result = xmlXPathEvalExpression(xpath, context);
xmlXPathFreeContext(context);
if (result == NULL)
{
printf("xmlXPathEvalExpression return NULL\n");
return NULL;
}
if (xmlXPathNodeSetIsEmpty(result->nodesetval))
{
xmlXPathFreeObject(result);
printf("nodeset is empty\n");
return NULL;
}
return result;
}