00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00034 #include <string.h>
00035
00036 #include "wbxml.h"
00037
00038
00039
00040 static WBXMLTreeAttribute *construct_attribute_list(WBXMLAttribute **atts);
00041 static void add_node_to_tree(WBXMLTreeNode *node, WBXMLTreeClbCtx *tree_ctx);
00042
00043 #if defined ( WBXML_SUPPORT_SYNCML )
00044
00047 typedef enum WBXMLSyncMLDataType_e {
00048 WBXML_SYNCML_DATA_TYPE_NORMAL = 0,
00049 WBXML_SYNCML_DATA_TYPE_WBXML
00050 } WBXMLSyncMLDataType;
00051
00052 static WBXMLSyncMLDataType syncml_wbxml_data_type(WBXMLTreeClbCtx *tree_ctx);
00053 #endif
00054
00055
00056
00057
00058
00059
00060 void wbxml_tree_clb_wbxml_start_document(void *ctx, WB_LONG charset, const WBXMLLangEntry *lang)
00061 {
00062 WBXMLTreeClbCtx *tree_ctx = (WBXMLTreeClbCtx *) ctx;
00063
00064 if (tree_ctx->error != WBXML_OK)
00065 return;
00066
00067 tree_ctx->tree->lang = lang;
00068 }
00069
00070
00071 void wbxml_tree_clb_wbxml_end_document(void *ctx)
00072 {
00073 WBXMLTreeClbCtx *tree_ctx = (WBXMLTreeClbCtx *) ctx;
00074
00075 if (tree_ctx->error != WBXML_OK)
00076 return;
00077 }
00078
00079
00080 void wbxml_tree_clb_wbxml_start_element(void *ctx, WBXMLTag *element, WBXMLAttribute **attrs, WB_BOOL empty)
00081 {
00082 WBXMLTreeClbCtx *tree_ctx = (WBXMLTreeClbCtx *) ctx;
00083 WBXMLTreeNode *node = NULL;
00084
00085 if (tree_ctx->error != WBXML_OK)
00086 return;
00087
00088
00089 if ((node = wbxml_tree_node_create(WBXML_TREE_ELEMENT_NODE)) == NULL) {
00090 tree_ctx->error = WBXML_ERROR_NOT_ENOUGH_MEMORY;
00091 return;
00092 }
00093
00094
00095 if ((node->name = wbxml_tag_duplicate(element)) == NULL) {
00096 wbxml_tree_node_destroy(node);
00097 tree_ctx->error = WBXML_ERROR_NOT_ENOUGH_MEMORY;
00098 return;
00099 }
00100
00101
00102 if (attrs != NULL) {
00103 if ((node->attrs = construct_attribute_list(attrs)) == NULL) {
00104 wbxml_tree_node_destroy(node);
00105 tree_ctx->error = WBXML_ERROR_NOT_ENOUGH_MEMORY;
00106 return;
00107 }
00108 }
00109
00110
00111 add_node_to_tree(node, tree_ctx);
00112 }
00113
00114
00115 void wbxml_tree_clb_wbxml_end_element(void *ctx, WBXMLTag *element, WB_BOOL empty)
00116 {
00117 WBXMLTreeClbCtx *tree_ctx = (WBXMLTreeClbCtx *) ctx;
00118
00119 if (tree_ctx->error != WBXML_OK)
00120 return;
00121
00122 if (tree_ctx->current == NULL) {
00123 tree_ctx->error = WBXML_ERROR_INTERNAL;
00124 return;
00125 }
00126
00127 if (tree_ctx->current->parent == NULL) {
00128
00129 if (tree_ctx->current != tree_ctx->tree->root) {
00130 tree_ctx->error = WBXML_ERROR_INTERNAL;
00131 }
00132 }
00133 else {
00134
00135 tree_ctx->current = tree_ctx->current->parent;
00136 }
00137 }
00138
00139
00140 void wbxml_tree_clb_wbxml_characters(void *ctx, WB_UTINY *ch, WB_ULONG start, WB_ULONG length)
00141 {
00142 WBXMLTreeClbCtx *tree_ctx = (WBXMLTreeClbCtx *) ctx;
00143 WBXMLTreeNode *node = NULL;
00144 #if defined ( WBXML_SUPPORT_SYNCML )
00145 WBXMLTree *tmp_tree = NULL;
00146 #endif
00147
00148 if (tree_ctx->error != WBXML_OK)
00149 return;
00150
00151 #if defined ( WBXML_SUPPORT_SYNCML )
00152
00153 if (syncml_wbxml_data_type(tree_ctx) == WBXML_SYNCML_DATA_TYPE_WBXML)
00154 {
00155
00156 if (wbxml_tree_from_wbxml(ch + start, length, WBXML_LANG_UNKNOWN, &tmp_tree) != WBXML_OK) {
00157
00158 goto text_node;
00159 }
00160
00161
00162 if ((node = wbxml_tree_node_create(WBXML_TREE_TREE_NODE)) == NULL) {
00163 wbxml_tree_destroy(tmp_tree);
00164 tree_ctx->error = WBXML_ERROR_NOT_ENOUGH_MEMORY;
00165 return;
00166 }
00167
00168
00169 node->tree = tmp_tree;
00170 }
00171 else {
00172 #endif
00173
00174 text_node:
00175
00176 if ((node = wbxml_tree_node_create(WBXML_TREE_TEXT_NODE)) == NULL) {
00177 tree_ctx->error = WBXML_ERROR_NOT_ENOUGH_MEMORY;
00178 return;
00179 }
00180
00181
00182 if ((node->content = wbxml_buffer_create_real(ch + start, length, length)) == NULL) {
00183 wbxml_tree_node_destroy(node);
00184 tree_ctx->error = WBXML_ERROR_NOT_ENOUGH_MEMORY;
00185 return;
00186 }
00187
00188 #if defined ( WBXML_SUPPORT_SYNCML )
00189 }
00190 #endif
00191
00192
00193 add_node_to_tree(node, tree_ctx);
00194
00195
00196 tree_ctx->current = tree_ctx->current->parent;
00197 }
00198
00199
00200 void wbxml_tree_clb_wbxml_pi(void *ctx, const WB_UTINY *target, WB_UTINY *data)
00201 {
00203 }
00204
00205
00206
00207
00208
00209
00215 static WBXMLTreeAttribute *construct_attribute_list(WBXMLAttribute **attrs)
00216 {
00217 WBXMLTreeAttribute *attr = NULL, *first = NULL, *curr = NULL;
00218 WB_ULONG i = 0;
00219
00220 if (attrs == NULL)
00221 return NULL;
00222
00223 while (attrs[i] != NULL) {
00224
00225 if ((attr = wbxml_tree_attribute_create()) == NULL) {
00226 wbxml_tree_attribute_destroy(first);
00227 return NULL;
00228 }
00229
00230
00231 if (curr != NULL)
00232 curr->next = attr;
00233
00234
00235 if ((attr->attr = wbxml_attribute_duplicate(attrs[i])) == NULL) {
00236 wbxml_tree_attribute_destroy(first);
00237 return NULL;
00238 }
00239
00240
00241 if (i == 0)
00242 first = attr;
00243
00244
00245 curr = attr;
00246 i++;
00247 }
00248
00249 return first;
00250 }
00251
00252
00258 static void add_node_to_tree(WBXMLTreeNode *node, WBXMLTreeClbCtx *tree_ctx)
00259 {
00260 WBXMLTreeNode *parent = NULL, *tmp = NULL;
00261
00262
00263 parent = tree_ctx->current;
00264 node->parent = parent;
00265 tree_ctx->current = node;
00266
00267
00268 if (parent != NULL) {
00269
00270 if (parent->children != NULL) {
00271
00272 tmp = parent->children;
00273
00274 while (tmp->next != NULL)
00275 tmp = tmp->next;
00276
00277 node->prev = tmp;
00278 tmp->next = node;
00279 }
00280 else {
00281
00282 parent->children = node;
00283 }
00284 }
00285 else {
00286
00287 tree_ctx->tree->root = node;
00288 }
00289 }
00290
00291
00292 #if defined ( WBXML_SUPPORT_SYNCML )
00293
00299 static WBXMLSyncMLDataType syncml_wbxml_data_type(WBXMLTreeClbCtx *tree_ctx)
00300 {
00301 WBXMLTreeNode *node = NULL;
00302
00303 if ((tree_ctx == NULL) || (tree_ctx->current == NULL))
00304 return WBXML_SYNCML_DATA_TYPE_NORMAL;
00305
00306
00307 if ((tree_ctx->current->type == WBXML_TREE_ELEMENT_NODE) &&
00308 (tree_ctx->current->name != NULL) &&
00309 (WBXML_STRCMP(wbxml_tag_get_xml_name(tree_ctx->current->name), "Data") == 0))
00310 {
00311
00312 if (((tree_ctx->current->parent != NULL) &&
00313 (tree_ctx->current->parent->children != NULL) &&
00314 ((node = wbxml_tree_get_element_node_from_name(tree_ctx->current->parent->children, "Meta", FALSE)) != NULL)) ||
00315 ((tree_ctx->current->parent != NULL) &&
00316 (tree_ctx->current->parent->parent != NULL) &&
00317 (tree_ctx->current->parent->parent->children != NULL) &&
00318 ((node = wbxml_tree_get_element_node_from_name(tree_ctx->current->parent->parent->children, "Meta", FALSE)) != NULL)))
00319 {
00320
00321 if ((node = wbxml_tree_get_element_node_from_name(node->children, "Type", FALSE)) != NULL)
00322 {
00323
00324 if ((node->children != NULL) &&
00325 (node->children->type == WBXML_TREE_TEXT_NODE) &&
00326 (wbxml_buffer_compare_cstr(node->children->content, "application/vnd.syncml-devinf+wbxml") == 0))
00327 {
00328 return WBXML_SYNCML_DATA_TYPE_WBXML;
00329 }
00330 }
00331 }
00332 }
00333
00334 return WBXML_SYNCML_DATA_TYPE_NORMAL;
00335 }
00336
00337 #endif