/* Internal routines */ static xode _xode_new(xode_pool p, const char* name, unsigned int type) { xode result = NULL; if (type > XODE_TYPE_LAST) return NULL; if (type != XODE_TYPE_CDATA && name == NULL) return NULL; if (p == NULL) { p = xode_pool_heap(1*1024); } /* Allocate & zero memory */ result = (xode)xode_pool_malloc(p, sizeof(_xode)); memset(result, '\0', sizeof(_xode)); /* Initialize fields */ if (type != XODE_TYPE_CDATA) result->name = xode_pool_strdup(p,name); result->type = type; result->p = p; return result; }
void *xode_pool_mallocx(xode_pool p, int size, char c) { void* result = xode_pool_malloc(p, size); if (result != NULL) memset(result, c, size); return result; }
/* * xode_insert_cdata -- append character data to a tag * If last child of the parent is CDATA, merges CDATA nodes. Otherwise * creates a CDATA node, and appends it to the parent's child list. * * parameters * parent -- parent tag * CDATA -- character data * size -- size of CDATA * or -1 for null-terminated CDATA strings * * returns * a pointer to the child CDATA node * or NULL if it was unsuccessful */ xode xode_insert_cdata(xode parent, const char* CDATA, unsigned int size) { xode result; if(CDATA == NULL || parent == NULL) return NULL; if(size == -1) size = strlen(CDATA); if ((parent->lastchild != NULL) && (parent->lastchild->type == XODE_TYPE_CDATA)) { result = parent->lastchild; result->data = _xode_merge(result->p, result->data, result->data_sz, CDATA, size); result->data_sz = result->data_sz + size; } else { result = _xode_insert(parent, "", XODE_TYPE_CDATA); if (result != NULL) { result->data = (char*)xode_pool_malloc(result->p, size + 1); memcpy(result->data, CDATA, size); result->data[size] = '\0'; result->data_sz = size; } } return result; }
xode_spool xode_spool_newfrompool(xode_pool p) { xode_spool s; s = xode_pool_malloc(p, sizeof(struct xode_spool_struct)); s->p = p; s->len = 0; s->last = NULL; s->first = NULL; return s; }
/* XXX efficient: move this to const char * and then loop through the existing heaps to see if src is within a block in this pool */ char *xode_pool_strdup(xode_pool p, const char *src) { char *ret; if(src == NULL) return NULL; ret = xode_pool_malloc(p,strlen(src) + 1); strcpy(ret,src); return ret; }
static char* _xode_merge(xode_pool p, char* dest, unsigned int destsize, const char* src, unsigned int srcsize) { char* result; result = (char*)xode_pool_malloc(p, destsize + srcsize + 1); memcpy(result, dest, destsize); memcpy(result+destsize, src, srcsize); result[destsize + srcsize] = '\0'; /* WARNING: major ugly hack: since we're throwing the old data away, let's jump in the xode_pool and subtract it from the size, this is for xmlstream's big-node checking */ p->size -= destsize; return result; }
char *xode_strunescape(xode_pool p, char *buf) { int i,j=0; char *temp; if (p == NULL || buf == NULL) return(NULL); if (strchr(buf,'&') == NULL) return(buf); temp = xode_pool_malloc(p,strlen(buf)+1); if (temp == NULL) return(NULL); for(i=0;i<strlen(buf);i++) { if (buf[i]=='&') { if (strncmp(&buf[i],"&",5)==0) { temp[j] = '&'; i += 4; } else if (strncmp(&buf[i],""",6)==0) { temp[j] = '\"'; i += 5; } else if (strncmp(&buf[i],"'",6)==0) { temp[j] = '\''; i += 5; } else if (strncmp(&buf[i],"<",4)==0) { temp[j] = '<'; i += 3; } else if (strncmp(&buf[i],">",4)==0) { temp[j] = '>'; i += 3; } } else { temp[j]=buf[i]; } j++; } temp[j]='\0'; return(temp); }
char *xode_spool_tostr(xode_spool s) { char *ret,*tmp; struct xode_spool_node *next; if(s == NULL || s->len == 0 || s->first == NULL) return NULL; ret = xode_pool_malloc(s->p, s->len + 1); *ret = '\0'; next = s->first; tmp = ret; while(next != NULL) { tmp = strcat(tmp,next->c); next = next->next; } return ret; }
void xode_spool_add(xode_spool s, char *str) { struct xode_spool_node *sn; int len; if(str == NULL) return; len = strlen(str); if(len == 0) return; sn = xode_pool_malloc(s->p, sizeof(struct xode_spool_node)); sn->c = xode_pool_strdup(s->p, str); sn->next = NULL; s->len += len; if(s->last != NULL) s->last->next = sn; s->last = sn; if(s->first == NULL) s->first = sn; }
/* easy safety utility (for creating blank mem for structs, etc) */ void *xode_pool_malloco(xode_pool p, int size) { void *block = xode_pool_malloc(p, size); memset(block, 0, size); return block; }
char *xode_strescape(xode_pool p, char *buf) { int i,j,oldlen,newlen; char *temp; if (p == NULL || buf == NULL) return(NULL); oldlen = newlen = strlen(buf); for(i=0;i<oldlen;i++) { switch(buf[i]) { case '&': newlen+=5; break; case '\'': newlen+=6; break; case '\"': newlen+=6; break; case '<': newlen+=4; break; case '>': newlen+=4; break; } } if(oldlen == newlen) return buf; temp = xode_pool_malloc(p,newlen+1); if (temp==NULL) return(NULL); for(i=j=0;i<oldlen;i++) { switch(buf[i]) { case '&': memcpy(&temp[j],"&",5); j += 5; break; case '\'': memcpy(&temp[j],"'",6); j += 6; break; case '\"': memcpy(&temp[j],""",6); j += 6; break; case '<': memcpy(&temp[j],"<",4); j += 4; break; case '>': memcpy(&temp[j],">",4); j += 4; break; default: temp[j++] = buf[i]; } } temp[j] = '\0'; return temp; }