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

📄 nad.c

📁 这是一个完全开放的
💻 C
📖 第 1 页 / 共 3 页
字号:
    for(attr = nad->elems[elem].attr; attr >= 0; attr = nad->attrs[attr].next)    {        if(nad->attrs[attr].lname <= 0) continue;        /* make enough space for the wrapper part */        ns = nad->attrs[attr].my_ns;        if(ns >= 0 && nad->nss[ns].iprefix >= 0)        {            NAD_SAFE(nad->cdata, nad->ccur + nad->attrs[attr].lname + nad->nss[ns].lprefix + 4, nad->clen);        } else {            NAD_SAFE(nad->cdata, nad->ccur + nad->attrs[attr].lname + 3, nad->clen);        }        *(nad->cdata + nad->ccur++) = ' ';        /* add the prefix if necessary */        if(ns >= 0 && nad->nss[ns].iprefix >= 0)        {            memcpy(nad->cdata + nad->ccur, nad->cdata + nad->nss[ns].iprefix, nad->nss[ns].lprefix);            nad->ccur += nad->nss[ns].lprefix;            *(nad->cdata + nad->ccur++) = ':';        }            /* copy in the name parts */        memcpy(nad->cdata + nad->ccur, nad->cdata + nad->attrs[attr].iname, nad->attrs[attr].lname);        nad->ccur += nad->attrs[attr].lname;        *(nad->cdata + nad->ccur++) = '=';        *(nad->cdata + nad->ccur++) = '\'';        /* copy in the escaped value */        _nad_escape(nad, nad->attrs[attr].ival, nad->attrs[attr].lval, 3);        /* make enough space for the closing quote and add it */        NAD_SAFE(nad->cdata, nad->ccur + 1, nad->clen);        *(nad->cdata + nad->ccur++) = '\'';    }    /* figure out what's next */    if(elem+1 == nad->ecur)        ndepth = -1;    else        ndepth = nad->elems[elem+1].depth;    /* handle based on if there are children, update nelem after done */    if(ndepth <= nad->elems[elem].depth)    {        /* make sure there's enough for what we could need */        NAD_SAFE(nad->cdata, nad->ccur + 2, nad->clen);        if(nad->elems[elem].lcdata == 0)        {            memcpy(nad->cdata + nad->ccur, "/>", 2);            nad->ccur += 2;        }else{            *(nad->cdata + nad->ccur++) = '>';            /* copy in escaped cdata */            _nad_escape(nad, nad->elems[elem].icdata, nad->elems[elem].lcdata,2);            /* make room */            ns = nad->elems[elem].my_ns;            if(ns >= 0 && nad->nss[ns].iprefix >= 0)            {                NAD_SAFE(nad->cdata, nad->ccur + 4 + nad->elems[elem].lname + nad->nss[ns].lprefix, nad->clen);            } else {                NAD_SAFE(nad->cdata, nad->ccur + 3 + nad->elems[elem].lname, nad->clen);            }            /* close tag */            memcpy(nad->cdata + nad->ccur, "</", 2);            nad->ccur += 2;                /* add the prefix if necessary */            if(ns >= 0 && nad->nss[ns].iprefix >= 0)            {                memcpy(nad->cdata + nad->ccur, nad->cdata + nad->nss[ns].iprefix, nad->nss[ns].lprefix);                nad->ccur += nad->nss[ns].lprefix;                *(nad->cdata + nad->ccur++) = ':';            }                memcpy(nad->cdata + nad->ccur, nad->cdata + nad->elems[elem].iname, nad->elems[elem].lname);            nad->ccur += nad->elems[elem].lname;            *(nad->cdata + nad->ccur++) = '>';        }        /* always try to append the tail */        _nad_escape(nad, nad->elems[elem].itail, nad->elems[elem].ltail,2);        /* if no siblings either, bail */        if(ndepth < nad->elems[elem].depth)            return elem+1;        /* next sibling */        elem++;    }else{        int nelem;        /* process any children */        /* close ourself and append any cdata first */        NAD_SAFE(nad->cdata, nad->ccur + 1, nad->clen);        *(nad->cdata + nad->ccur++) = '>';        _nad_escape(nad, nad->elems[elem].icdata, nad->elems[elem].lcdata,2);        /* process children */        nelem = _nad_lp0(nad,elem+1);        /* close and tail up */        ns = nad->elems[elem].my_ns;        if(ns >= 0 && nad->nss[ns].iprefix >= 0)        {            NAD_SAFE(nad->cdata, nad->ccur + 4 + nad->elems[elem].lname + nad->nss[ns].lprefix, nad->clen);        } else {            NAD_SAFE(nad->cdata, nad->ccur + 3 + nad->elems[elem].lname, nad->clen);        }        memcpy(nad->cdata + nad->ccur, "</", 2);        nad->ccur += 2;        if(ns >= 0 && nad->nss[ns].iprefix >= 0)        {            memcpy(nad->cdata + nad->ccur, nad->cdata + nad->nss[ns].iprefix, nad->nss[ns].lprefix);            nad->ccur += nad->nss[ns].lprefix;            *(nad->cdata + nad->ccur++) = ':';        }        memcpy(nad->cdata + nad->ccur, nad->cdata + nad->elems[elem].iname, nad->elems[elem].lname);        nad->ccur += nad->elems[elem].lname;        *(nad->cdata + nad->ccur++) = '>';        _nad_escape(nad, nad->elems[elem].itail, nad->elems[elem].ltail,2);        /* if the next element is not our sibling, we're done */        if(nelem < nad->ecur && nad->elems[nelem].depth < nad->elems[elem].depth)            return nelem;        /* for next sibling in while loop */        elem = nelem;    }    /* here's the end of that big while loop */    }    return elem;}void nad_print(nad_t nad, int elem, char **xml, int *len){    int ixml = nad->ccur;    _nad_ptr_check(__func__, nad);    _nad_lp0(nad,elem);    *len = nad->ccur - ixml;    *xml = nad->cdata + ixml;}/** * nads serialize to a buffer of this form: * * [buflen][ecur][acur][ncur][ccur][elems][attrs][nss][cdata] * * nothing is done with endianness or word length, so the nad must be * serialized and deserialized on the same platform * * buflen is not actually used by deserialize(), but is provided as a * convenience to the application so it knows how many bytes to read before * passing them in to deserialize() * * the depths array is not stored, so after deserialization * nad_append_elem() and nad_append_cdata() will not work. this is rarely * a problem */void nad_serialize(nad_t nad, char **buf, int *len) {    char *pos;    _nad_ptr_check(__func__, nad);    *len = sizeof(int) * 5 + /* 4 ints in nad_t, plus one for len */           sizeof(struct nad_elem_st) * nad->ecur +           sizeof(struct nad_attr_st) * nad->acur +           sizeof(struct nad_ns_st) * nad->ncur +           sizeof(char) * nad->ccur;    *buf = (char *) malloc(*len);    pos = *buf;    * (int *) pos = *len;       pos += sizeof(int);    * (int *) pos = nad->ecur;  pos += sizeof(int);    * (int *) pos = nad->acur;  pos += sizeof(int);    * (int *) pos = nad->ncur;  pos += sizeof(int);    * (int *) pos = nad->ccur;  pos += sizeof(int);    memcpy(pos, nad->elems, sizeof(struct nad_elem_st) * nad->ecur);    pos += sizeof(struct nad_elem_st) * nad->ecur;    memcpy(pos, nad->attrs, sizeof(struct nad_attr_st) * nad->acur);    pos += sizeof(struct nad_attr_st) * nad->acur;    memcpy(pos, nad->nss, sizeof(struct nad_ns_st) * nad->ncur);        pos += sizeof(struct nad_ns_st) * nad->ncur;    memcpy(pos, nad->cdata, sizeof(char) * nad->ccur);}nad_t nad_deserialize(nad_cache_t cache, const char *buf) {    nad_t nad = nad_new(cache);    const char *pos = buf + sizeof(int);  /* skip len */    _nad_ptr_check(__func__, nad);    nad->ecur = * (int *) pos; pos += sizeof(int);    nad->acur = * (int *) pos; pos += sizeof(int);    nad->ncur = * (int *) pos; pos += sizeof(int);    nad->ccur = * (int *) pos; pos += sizeof(int);    nad->elen = nad->ecur;    nad->alen = nad->acur;    nad->nlen = nad->ncur;    nad->clen = nad->ccur;    if(nad->ecur > 0)    {        nad->elems = (struct nad_elem_st *) malloc(sizeof(struct nad_elem_st) * nad->ecur);        memcpy(nad->elems, pos, sizeof(struct nad_elem_st) * nad->ecur);        pos += sizeof(struct nad_elem_st) * nad->ecur;    }    if(nad->acur > 0)    {        nad->attrs = (struct nad_attr_st *) malloc(sizeof(struct nad_attr_st) * nad->acur);        memcpy(nad->attrs, pos, sizeof(struct nad_attr_st) * nad->acur);        pos += sizeof(struct nad_attr_st) * nad->acur;    }    if(nad->ncur > 0)    {        nad->nss = (struct nad_ns_st *) malloc(sizeof(struct nad_ns_st) * nad->ncur);        memcpy(nad->nss, pos, sizeof(struct nad_ns_st) * nad->ncur);        pos += sizeof(struct nad_ns_st) * nad->ncur;    }    if(nad->ccur > 0)    {        nad->cdata = (char *) malloc(sizeof(char) * nad->ccur);        memcpy(nad->cdata, pos, sizeof(char) * nad->ccur);    }    return nad;}#ifdef HAVE_EXPAT/** parse a buffer into a nad */struct build_data {    nad_t               nad;    int                 depth;};static void _nad_parse_element_start(void *arg, const char *name, const char **atts) {    struct build_data *bd = (struct build_data *) arg;    char buf[1024];    char *uri, *elem, *prefix;    const char **attr;    int ns;    /* make a copy */    strncpy(buf, name, 1024);    buf[1023] = '\0';    /* expat gives us:         prefixed namespaced elem: uri|elem|prefix          default namespaced elem: uri|elem               un-namespaced elem: elem     */    /* extract all the bits */    uri = buf;    elem = strchr(uri, '|');    if(elem != NULL) {        *elem = '\0';        elem++;        prefix = strchr(elem, '|');        if(prefix != NULL) {            *prefix = '\0';            prefix++;        }        ns = nad_add_namespace(bd->nad, uri, prefix);    } else {        /* un-namespaced, just take it as-is */        uri = NULL;        elem = buf;        prefix = NULL;        ns = -1;    }    /* add it */    nad_append_elem(bd->nad, ns, elem, bd->depth);    /* now the attributes, one at a time */    attr = atts;    while(attr[0] != NULL) {        /* make a copy */        strncpy(buf, attr[0], 1024);        buf[1023] = '\0';        /* extract all the bits */        uri = buf;        elem = strchr(uri, '|');        if(elem != NULL) {            *elem = '\0';            elem++;            prefix = strchr(elem, '|');            if(prefix != NULL) {                *prefix = '\0';                prefix++;            }            ns = nad_add_namespace(bd->nad, uri, prefix);        } else {            /* un-namespaced, just take it as-is */            uri = NULL;            elem = buf;            prefix = NULL;            ns = -1;        }        /* add it */        nad_append_attr(bd->nad, ns, elem, (char *) attr[1]);        attr += 2;    }    bd->depth++;}static void _nad_parse_element_end(void *arg, const char *name) {    struct build_data *bd = (struct build_data *) arg;    bd->depth--;}static void _nad_parse_cdata(void *arg, const char *str, int len) {    struct build_data *bd = (struct build_data *) arg;    /* go */    nad_append_cdata(bd->nad, (char *) str, len, bd->depth);}static void _nad_parse_namespace_start(void *arg, const char *prefix, const char *uri) {    struct build_data *bd = (struct build_data *) arg;    int ns;    ns = nad_add_namespace(bd->nad, (char *) uri, (char *) prefix);    /* Always set the namespace (to catch cases where nad_add_namespace doesn't add it) */    bd->nad->scope = ns; }nad_t nad_parse(nad_cache_t cache, const char *buf, int len) {    struct build_data bd;    XML_Parser p;    if(len == 0)        len = strlen(buf);    p = XML_ParserCreateNS(NULL, '|');    if(p == NULL)        return NULL;    XML_SetReturnNSTriplet(p, 1);    bd.nad = nad_new(cache);    bd.depth = 0;    XML_SetUserData(p, (void *) &bd);    XML_SetElementHandler(p, _nad_parse_element_start, _nad_parse_element_end);    XML_SetCharacterDataHandler(p, _nad_parse_cdata);    XML_SetStartNamespaceDeclHandler(p, _nad_parse_namespace_start);    if(!XML_Parse(p, buf, len, 1)) {        XML_ParserFree(p);        nad_free(bd.nad);        return NULL;    }    XML_ParserFree(p);    if(bd.depth != 0)        return NULL;    return bd.nad;}#endif

⌨️ 快捷键说明

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