⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 dotconfpp.cpp

📁 访问unix风格的配置文件
💻 CPP
📖 第 1 页 / 共 2 页
字号:
#include "ace_ext_export.h"#include "dotconfpp.h"#if !defined(R_OK)#define R_OK 04#endifDOTCONFDocumentNode::DOTCONFDocumentNode():previousNode(NULL), nextNode(NULL), parentNode(NULL), childNode(NULL),    values(NULL), valuesCount(0),    name(NULL), lineNum(0), fileName(NULL), closed(true){}DOTCONFDocumentNode::~DOTCONFDocumentNode(){    free(name);    if(values != NULL){        for(int i = 0 ; i < valuesCount; i++){            free(values[i]);        }        free(values);    }}void DOTCONFDocumentNode::pushValue(char * _value){    valuesCount++;    values = (char**)realloc(values, valuesCount*sizeof(char*));    values[valuesCount-1] = strdup(_value);}const char* DOTCONFDocumentNode::getValue(int index) const{    if(index >= valuesCount){        return NULL;    }    return values[index];}DOTCONFDocument::DOTCONFDocument(DOTCONFDocument::CaseSensitive caseSensitivity):    mempool(NULL),    curParent(NULL), curPrev(NULL), curLine(0), file(NULL), fileName(NULL){    if(caseSensitivity == CASESENSETIVE){        cmp_func = strcmp;    } else {        cmp_func = strcasecmp;    }    mempool = new AsyncDNSMemPool(1024);    mempool->initialize();}DOTCONFDocument::~DOTCONFDocument(){    for(std::list<DOTCONFDocumentNode*>::iterator i = nodeTree.begin(); i != nodeTree.end(); i++){        delete(*i);    }    for(std::list<char*>::iterator i = requiredOptions.begin(); i != requiredOptions.end(); i++){        free(*i);    }    for(std::list<char*>::iterator i = processedFiles.begin(); i != processedFiles.end(); i++){        free(*i);    }    free(fileName);    delete mempool;}int DOTCONFDocument::cleanupLine(char * line){    char * start = line;    char * bg = line;    bool multiline = false;    bool concat = false;    char * word = NULL;    if(!words.empty() && quoted)        concat = true;    while(*line){        if((*line == '#' || *line == ';') && !quoted){            *bg = 0;            if(strlen(start)){                                if(concat){                    word = (char*)mempool->alloc(strlen(words.back())+strlen(start)+1);                    strcpy(word, words.back());                    strcat(word, start);                    words.pop_back();                    concat = false;                } else {                    word = mempool->strdup(start);                }                words.push_back(word);            }            break;        }        if(*line == '=' && !quoted){             *line = ' ';continue;        }        // Allowing \" in there causes problems with directory paths        // like "C:\MaNGOS\"        //if(*line == '\\' && (*(line+1) == '"' || *(line+1) == '\'')){        if(*line == '\\' && (*(line+1) == '\'')) {            *bg++ = *(line+1);            line+=2; continue;        }        if(*line == '\\' && *(line+1) == 'n'){            *bg++ = '\n';            line+=2; continue;        }        if(*line == '\\' && *(line+1) == 'r'){            *bg++ = '\r';            line+=2; continue;        }        if(*line == '\\' && (*(line+1) == '\n' || *(line+1) == '\r')){             *bg = 0;            if(strlen(start)){                                if(concat){                    word = (char*)mempool->alloc(strlen(words.back())+strlen(start)+1);                    strcpy(word, words.back());                    strcat(word, start);                    words.pop_back();                    concat = false;                } else {                    word = mempool->strdup(start);                }                words.push_back(word);            }            multiline = true;            break;        }        if(*line == '"' || *line == '\''){             quoted = !quoted;            line++; continue;        }        if(isspace(*line) && !quoted){            *bg++ = 0;            if(strlen(start)){                                if(concat){                    word = (char*)mempool->alloc(strlen(words.back())+strlen(start)+1);                    strcpy(word, words.back());                    strcat(word, start);                    words.pop_back();                    concat = false;                } else {                    word = mempool->strdup(start);                }                words.push_back(word);            }            start = bg;            while(isspace(*++line));            continue;        }        *bg++ = *line++;    }    if(quoted && !multiline){        error(curLine, fileName, "unterminated quote");        return -1;    }    return multiline?1:0;}int DOTCONFDocument::parseLine(){    char * word = NULL;    char * nodeName = NULL;    char * nodeValue = NULL;    DOTCONFDocumentNode * tagNode = NULL;    bool newNode = false;    for(std::list<char*>::iterator i = words.begin(); i != words.end(); i++) {        word = *i;        if(*word == '<'){            newNode = true;        }        if(newNode){            nodeValue = NULL;            nodeName = NULL;            newNode = false;        }        size_t wordLen = strlen(word);        if(word[wordLen-1] == '>'){            word[wordLen-1] = 0;            newNode = true;        }        if(nodeName == NULL){            nodeName = word;            bool closed = true;             if(*nodeName == '<'){                if(*(nodeName+1) != '/'){                     nodeName++;                    closed = false;                } else {                     nodeName+=2;                    std::list<DOTCONFDocumentNode*>::reverse_iterator itr=nodeTree.rbegin();                    for(; itr!=nodeTree.rend(); ++itr){                        if(!cmp_func(nodeName, (*itr)->name) && !(*itr)->closed){                            (*itr)->closed = true;                            curParent = (*itr)->parentNode;                            curPrev = *itr;                            break;                        }                    }                    if(itr==nodeTree.rend()){                        error(curLine, fileName, "not matched closing tag </%s>", nodeName);                        return -1;                    }                    continue;                }            }            tagNode = new DOTCONFDocumentNode;            tagNode->name = strdup(nodeName);            tagNode->document = this;            tagNode->fileName = processedFiles.back();            tagNode->lineNum = curLine;            tagNode->closed = closed;            if(!nodeTree.empty()){                DOTCONFDocumentNode * prev = nodeTree.back();                if(prev->closed){                    curPrev->nextNode = tagNode;                    tagNode->previousNode = curPrev;                    tagNode->parentNode = curParent;                } else {                    prev->childNode = tagNode;                    tagNode->parentNode = prev;                    curParent = prev;                }            }            nodeTree.push_back(tagNode);            curPrev = tagNode;        } else {            nodeValue = word;            tagNode->pushValue(nodeValue);        }    }    return 0;}int DOTCONFDocument::parseFile(DOTCONFDocumentNode * _parent){    char str[512];    int ret = 0;    curLine = 0;    curParent = _parent;    quoted = false;    size_t slen = 0;    while(fgets(str, 511, file)){        curLine++;    slen = strlen(str);        if( slen >= 510 ){            error(curLine, fileName, "warning: line too long");        }    if(str[slen-1] != '\n'){        str[slen] = '\n';        str[slen+1] = 0;    }        if((ret = cleanupLine(str)) == -1){            break;        }        if(ret == 0){            if(!words.empty()){                ret = parseLine();                mempool->free();                words.clear();                if(ret == -1){                    break;                }            }        }    }    return ret;}int DOTCONFDocument::checkConfig(const std::list<DOTCONFDocumentNode*>::iterator & from){    int ret = 0;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -