node_t * ROXML_API roxml_load_buf(char *buffer) { node_t *current_node = NULL; if(buffer == NULL) { return NULL; } current_node = roxml_create_node(0, buffer, ROXML_ELM_NODE | ROXML_BUFF); current_node = roxml_parent_node(NULL, current_node); return roxml_load(current_node, NULL, buffer); }
node_t * ROXML_API roxml_load_doc(char *filename) { node_t *current_node = NULL; FILE* file = fopen(filename, "r"); if(file == NULL) { return NULL; } current_node = roxml_create_node(0, file, ROXML_ELM_NODE | ROXML_FILE); current_node = roxml_parent_node(NULL, current_node); return roxml_load(current_node, file, NULL); }
node_t * ROXML_API roxml_load_fd(int fd) { FILE * file = NULL; node_t *current_node = NULL; if(fd < 0) { return NULL; } file = fdopen(fd, "r"); if(file == NULL) { return NULL; } current_node = roxml_create_node(0, file, ROXML_ELM_NODE | ROXML_FILE); current_node = roxml_parent_node(NULL, current_node); return roxml_load(current_node, file, NULL); }
int _func_load_close_node(char * chunk, void * data) { #ifdef DEBUG_PARSING fprintf(stderr, "calling func %s chunk %c\n",__func__,chunk[0]); #endif /* DEBUG_PARSING */ int cur = 1; roxml_load_ctx_t *context = (roxml_load_ctx_t*)data; switch(context->state) { case STATE_NODE_NAME: context->empty_text_node = 1; context->current_node = roxml_parent_node(context->current_node, context->candidat_node, 0); break; case STATE_NODE_ATTR: if((context->mode != MODE_COMMENT_DQUOTE)||(context->mode != MODE_COMMENT_QUOTE)) { if(context->inside_node_state == STATE_INSIDE_VAL) { node_t * to_be_closed = NULL; if(context->content_quoted) { context->content_quoted = 0; to_be_closed = roxml_create_node(context->pos-1, context->src, ROXML_ATTR_NODE | context->type); } else { to_be_closed = roxml_create_node(context->pos, context->src, ROXML_ATTR_NODE | context->type); } roxml_close_node(context->candidat_val, to_be_closed); } context->current_node = roxml_parent_node(context->current_node, context->candidat_node, 0); context->inside_node_state = STATE_INSIDE_ARG_BEG; roxml_process_unaliased_ns(context); } else { context->pos++; return 1; } break; case STATE_NODE_SINGLE: if(context->doctype) { context->doctype--; if(context->doctype > 0) { context->pos++; return 1; } context->candidat_node->end = context->pos; } context->empty_text_node = 1; context->current_node = roxml_parent_node(context->current_node, context->candidat_node, 0); if(context->current_node->prnt != NULL) { context->current_node = context->current_node->prnt; } roxml_process_unaliased_ns(context); break; case STATE_NODE_END: context->empty_text_node = 1; roxml_close_node(context->current_node, context->candidat_node); context->candidat_node = NULL; if(context->current_node->prnt != NULL) { context->current_node = context->current_node->prnt; } break; case STATE_NODE_CDATA: case STATE_NODE_CONTENT: default: context->pos++; return 1; break; } if(context->candidat_node && context->candidat_node->ns && ((context->candidat_node->ns->type & ROXML_INVALID) == ROXML_INVALID)) { roxml_free_node(context->candidat_node->ns); } context->state = STATE_NODE_CONTENT; context->previous_state = STATE_NODE_CONTENT; context->candidat_txt = roxml_create_node(context->pos+1, context->src, ROXML_TXT_NODE | context->type); #ifdef IGNORE_EMPTY_TEXT_NODES while(chunk[cur] != '\0') { if(chunk[cur] == '<') { break; } else if(!ROXML_WHITE(chunk[cur])) { context->empty_text_node = 0; break; } cur++; } #endif /* IGNORE_EMPTY_TEXT_NODES */ while((chunk[cur] != '<')&&(chunk[cur] != '\0')) { cur++; } context->pos += cur; return cur; }
int _func_load_default(char * chunk, void * data) { node_t * to_be_closed; int cur = 1; roxml_load_ctx_t *context = (roxml_load_ctx_t*)data; #ifdef DEBUG_PARSING fprintf(stderr, "calling func %s chunk %c\n",__func__,chunk[0]); #endif /* DEBUG_PARSING */ switch(context->state) { case STATE_NODE_SINGLE: context->state = context->previous_state; break; case STATE_NODE_BEG: if(context->ns == 0) { roxml_process_begin_node(context, context->pos-1); } context->ns = 0; context->state = STATE_NODE_NAME; context->curr_name = chunk; while(!ROXML_WHITE(chunk[cur])&&(chunk[cur] != '>')&&(chunk[cur] != '/')&&(chunk[cur] != ':')&&(chunk[cur] != '\0')) { cur++; } context->curr_name_len = cur; break; case STATE_NODE_ATTR: if(context->inside_node_state == STATE_INSIDE_ARG_BEG) { if(context->nsdef) { if(context->namespaces == NULL) { context->namespaces = context->candidat_arg; context->last_ns = context->candidat_arg; } else { context->last_ns->next = context->candidat_arg; context->last_ns = context->candidat_arg; } } else if(context->ns == 0) { context->candidat_arg = roxml_create_node(context->pos-1, context->src, ROXML_ATTR_NODE | context->type); context->candidat_arg = roxml_parent_node(context->candidat_node, context->candidat_arg, 0); } context->ns = 0; context->inside_node_state = STATE_INSIDE_ARG; context->curr_name = chunk; while((chunk[cur] != '=')&&(chunk[cur] != '>')&&(chunk[cur] != ':')&&(chunk[cur] != '\0')) { cur++; } context->curr_name_len = cur; if(context->nsdef) { roxml_ns_t * ns = calloc(1, sizeof(roxml_ns_t)+(1+context->curr_name_len)); ns->id = ROXML_NS_ID; ns->alias = (char*)ns + sizeof(roxml_ns_t); memcpy(ns->alias, context->curr_name, context->curr_name_len); context->candidat_arg->priv = ns; context->nsdef = 0; if(context->candidat_node->ns) { if((context->candidat_node->ns->type & ROXML_INVALID) == ROXML_INVALID) { if(strcmp(context->candidat_arg->prnt->ns->src.buf, ns->alias) == 0) { roxml_free_node(context->candidat_node->ns); context->candidat_node->ns = context->candidat_arg; } } } } } else if(context->inside_node_state == STATE_INSIDE_VAL_BEG) { if(context->mode != MODE_COMMENT_NONE) { context->content_quoted = 1; context->candidat_val = roxml_create_node(context->pos+1, context->src, ROXML_TXT_NODE | context->type); } else { context->candidat_val = roxml_create_node(context->pos, context->src, ROXML_TXT_NODE | context->type); } context->candidat_val = roxml_parent_node(context->candidat_arg, context->candidat_val, 0); context->inside_node_state = STATE_INSIDE_VAL; } else if((context->inside_node_state == STATE_INSIDE_ARG)&&(chunk[0] == '=')) { context->inside_node_state = STATE_INSIDE_VAL_BEG; to_be_closed = roxml_create_node(context->pos, context->src, ROXML_ATTR_NODE | context->type); roxml_close_node(context->candidat_arg, to_be_closed); if((context->curr_name_len==5)&&(strncmp(context->curr_name, "xmlns", 5) == 0)) { context->nsdef = 1; } } break; } context->pos += cur; return cur; }
int XHCPcmd_SETRULE_handle (int sockd, int argc, char **argv, char *data) { node_t *nTmp; node_t **lstNodes; char *newId = NULL; int nb; // A supprimer !!! char *zaza = NULL; printf ("Entree XHCPcmd_SETRULE_handle avec %d arguments\n", argc); int i; for ( i=0; i<argc; i++ ) printf ( "%d - %s\n", i, argv[i]); if ( (nTmp = roxml_load_buf (data)) == NULL ) { XHCP_printXHCPResponse (sockd, RES_SYNTAXERR); // Syntax Error return XHCP_EXE_ERROR; } printf ("Chargement XML OK\n"); if ( argc == 2 ) // pas de node mais id donné en argument newId = strdup(argv[1]); // On recherche si un id est présent if ( (lstNodes = roxml_xpath (nTmp, "//determinator[@guid]", &nb )) != NULL ) { node_t *attr_tmp = roxml_get_attr (lstNodes[0], "guid", 0); if ( newId == NULL && argc == 1 ) { newId = roxml_get_content(attr_tmp, NULL, 0, NULL); } roxml_del_node(attr_tmp); } if ( newId == NULL ) newId = XHCP_getUuid(); printf("a la fin id = %s\n",newId==NULL ? "NULL":newId); lstNodes = roxml_xpath (nTmp, "//determinator", &nb ); if ( nb == 1 ) nTmp = lstNodes[0]; else { printf("Pas trouve //derterminator, nb=%d\n",nb); XHCP_printXHCPResponse (sockd, RES_SYNTAXERR); // Syntax Error return XHCP_EXE_ERROR; } // Ajout d'un nouveau noeud roxml_add_node(nTmp, 0, ROXML_ATTR_NODE, "guid", newId); printf("attribut ajouté\n"); printf("Nouvel arbre determinator\n"); roxml_commit_changes (nTmp, NULL, &zaza, 1); printf("%s\n", zaza); free(zaza); lstNodes = roxml_xpath (rootConfig, "//determinators", &nb ); if ( nb != 1 ) { printf("Pas trouve //determinators, nb=%d\n",nb); XHCP_printXHCPResponse (sockd, RES_INTNERROR); // Internal error return XHCP_EXE_ERROR; } /* On ratache le nouveau determinator à la liste */ roxml_parent_node(lstNodes[0], nTmp); saveHal4lConfig (HAL4L_getConfigFile ()); //roxml_close (nTmp); loadHal4lConfig (HAL4L_getConfigFile ()); free(newId); XHCP_printXHCPResponse (sockd, RES_CFGDOCUPL ); // Configuration document uploaded return XHCP_EXE_SUCCESS; }
node_t * roxml_add_node(node_t * parent, int position, int type, char *name, char *value) { int name_l = 0; int end_node = 0; int content_l = 0; int content_pos = 0; int end_content = 0; char * buffer = NULL; node_t * new_node; int allow_attrib_child; if(parent) { if(parent->type & ROXML_ATTR_NODE) { if(((type & ROXML_TXT_NODE) == 0)||(parent->chld)) { return NULL; } } else if((parent->type & ROXML_ELM_NODE) == 0) { if(parent->prnt && (parent->prnt->type & ROXML_ELM_NODE)) { parent = parent->prnt; } else { return NULL; } } } if(value) { content_l = strlen(value); } if(name) { name_l = strlen(name); } if(type & ROXML_ATTR_NODE) { int xmlns_l = 0; if(!name || !value) { return NULL; } if(type & ROXML_NS_NODE) { if(name_l > 0) { xmlns_l = 6; } else { xmlns_l = 5; } buffer = (char*)malloc(sizeof(char)*(name_l+content_l+xmlns_l+4)); sprintf(buffer,"xmlns%s%s=\"%s\"", name_l?":":"", name, value); } else { buffer = (char*)malloc(sizeof(char)*(name_l+content_l+4)); sprintf(buffer,"%s=\"%s\"",name, value); } content_pos = name_l + 2 + xmlns_l; end_node = name_l + 1 + xmlns_l; end_content = name_l + content_l + 2 + xmlns_l; } else if(type & ROXML_CMT_NODE) { if(!value) { return NULL; } buffer = (char*)malloc(sizeof(char)*(content_l+8)); sprintf(buffer,"<!--%s-->", value); content_pos = 0; end_node = content_l + 4; end_content = content_l + 4; } else if(type & ROXML_PI_NODE) { if(!name) { return NULL; } if(content_l) { buffer = (char*)malloc(sizeof(char)*(name_l+content_l+8)); sprintf(buffer,"<?%s %s?>", name, value); end_node = name_l + content_l + 3; end_content = name_l + content_l + 5; } else { buffer = (char*)malloc(sizeof(char)*(name_l+7)); sprintf(buffer,"<?%s?>", name); end_node = name_l + 2; end_content = name_l + 4; } content_pos = 0; } else if(type & ROXML_TXT_NODE) { if(!value) { return NULL; } buffer = (char*)malloc(sizeof(char)*(content_l+1)); sprintf(buffer,"%s", value); content_pos = 0; end_node = content_l + 1; end_content = content_l + 1; } else if(type & ROXML_ELM_NODE) { if(!name) { return NULL; } if(value) { buffer = (char*)malloc(sizeof(char)*(name_l*2+content_l+6)); sprintf(buffer,"<%s>%s</%s>",name, value, name); content_pos = name_l+2; end_node = name_l + content_l + 2; end_content = end_node; } else { buffer = (char*)malloc(sizeof(char)*(name_l+5)); sprintf(buffer,"<%s />",name); } } else { return NULL; } new_node = roxml_create_node(0, buffer, type | ROXML_PENDING | ROXML_BUFF); new_node->end = end_node; if(type & ROXML_NS_NODE) { roxml_ns_t * ns = calloc(1, sizeof(roxml_ns_t) + name_l + 1); ns->id = ROXML_NS_ID; ns->alias = (char*)ns + sizeof(roxml_ns_t); strcpy(ns->alias, name); new_node->priv = ns; } if(((type & ROXML_ELM_NODE) && content_l) || (type & ROXML_ATTR_NODE)) { node_t *new_txt = roxml_create_node(content_pos, buffer, ROXML_TXT_NODE | ROXML_PENDING | ROXML_BUFF); roxml_append_node(new_node, new_txt); new_txt->end = end_content; } if(parent == NULL) { xpath_tok_table_t * table = (xpath_tok_table_t*)calloc(1, sizeof(xpath_tok_table_t)); parent = roxml_create_node(0, NULL, ROXML_ELM_NODE | ROXML_PENDING | ROXML_BUFF); parent->end = 1; table->id = ROXML_REQTABLE_ID; table->ids[ROXML_REQTABLE_ID] = 1; pthread_mutex_init(&table->mut, NULL); parent->priv = (void*)table; roxml_append_node(parent, new_node); } else { roxml_parent_node(parent, new_node, position); } return new_node; }
node_t * roxml_add_node(node_t * parent, int position, int type, char *name, char *value) { int name_l = 0; int end_node = 0; int content_l = 0; int content_pos = 0; int end_content = 0; char * buffer = NULL; node_t * new_node; if(parent && !(parent->type & ROXML_ELM_NODE)) { return NULL; } if(value) { content_l = strlen(value); } if(name) { name_l = strlen(name); } if(type & ROXML_ATTR_NODE) { if(!name || !value) { return NULL; } buffer = (char*)malloc(sizeof(char)*(name_l+content_l+4)); sprintf(buffer,"%s=\"%s\"",name, value); content_pos = name_l+2; end_node = name_l + 1; end_content = name_l + content_l + 2; } else if(type & ROXML_CMT_NODE) { if(!value) { return NULL; } buffer = (char*)malloc(sizeof(char)*(content_l+8)); sprintf(buffer,"<!--%s-->", value); content_pos = 0; end_node = content_l + 4; end_content = content_l + 4; } else if(type & ROXML_PI_NODE) { if(!value) { return NULL; } buffer = (char*)malloc(sizeof(char)*(content_l+7)); sprintf(buffer,"<? %s ?>", value); content_pos = 0; end_node = content_l + 4; end_content = content_l + 4; } else if(type & ROXML_TXT_NODE) { if(!value) { return NULL; } buffer = (char*)malloc(sizeof(char)*(content_l+1)); sprintf(buffer,"%s", value); content_pos = 0; end_node = content_l + 1; end_content = content_l + 1; } else if(type & ROXML_ELM_NODE) { if(!name) { return NULL; } if(content_l) { if(!value) { return NULL; } buffer = (char*)malloc(sizeof(char)*(name_l*2+content_l+6)); sprintf(buffer,"<%s>%s</%s>",name, value, name); content_pos = name_l+2; end_node = name_l + content_l + 2; end_content = end_node; } else { buffer = (char*)malloc(sizeof(char)*(name_l+5)); sprintf(buffer,"<%s />",name); } } new_node = roxml_create_node(0, buffer, type | ROXML_PENDING | ROXML_BUFF); new_node->end = end_node; if(value && name) { node_t *new_txt = roxml_create_node(content_pos, buffer, ROXML_TXT_NODE | ROXML_PENDING | ROXML_BUFF); roxml_parent_node(new_node, new_txt); new_txt->end = end_content; } if(parent == NULL) { parent = roxml_create_node(0, NULL, ROXML_ELM_NODE | ROXML_PENDING | ROXML_BUFF); parent->end = 1; roxml_parent_node(parent, new_node); } else { roxml_parent_node_at(parent, new_node, position); } return new_node; }