Kannel: Open Source WAP and SMS gateway  svn-r5335
decompile.c
Go to the documentation of this file.
1 /* ====================================================================
2  * The Kannel Software License, Version 1.0
3  *
4  * Copyright (c) 2001-2018 Kannel Group
5  * Copyright (c) 1998-2001 WapIT Ltd.
6  * All rights reserved.
7  *
8  * Redistribution and use in source and binary forms, with or without
9  * modification, are permitted provided that the following conditions
10  * are met:
11  *
12  * 1. Redistributions of source code must retain the above copyright
13  * notice, this list of conditions and the following disclaimer.
14  *
15  * 2. Redistributions in binary form must reproduce the above copyright
16  * notice, this list of conditions and the following disclaimer in
17  * the documentation and/or other materials provided with the
18  * distribution.
19  *
20  * 3. The end-user documentation included with the redistribution,
21  * if any, must include the following acknowledgment:
22  * "This product includes software developed by the
23  * Kannel Group (http://www.kannel.org/)."
24  * Alternately, this acknowledgment may appear in the software itself,
25  * if and wherever such third-party acknowledgments normally appear.
26  *
27  * 4. The names "Kannel" and "Kannel Group" must not be used to
28  * endorse or promote products derived from this software without
29  * prior written permission. For written permission, please
30  * contact org@kannel.org.
31  *
32  * 5. Products derived from this software may not be called "Kannel",
33  * nor may "Kannel" appear in their name, without prior written
34  * permission of the Kannel Group.
35  *
36  * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
37  * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
38  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
39  * DISCLAIMED. IN NO EVENT SHALL THE KANNEL GROUP OR ITS CONTRIBUTORS
40  * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY,
41  * OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT
42  * OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
43  * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
44  * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
45  * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
46  * EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
47  * ====================================================================
48  *
49  * This software consists of voluntary contributions made by many
50  * individuals on behalf of the Kannel Group. For more information on
51  * the Kannel Group, please see <http://www.kannel.org/>.
52  *
53  * Portions of this software are based upon software originally written at
54  * WapIT Ltd., Helsinki, Finland for the Kannel project.
55  */
56 
57 /*
58  * decompile.c - A program to test the WML compiler. This tool was written
59  * from the WBXML 1.2 and WML 1.1 specs.
60  *
61  * Author: Chris Wulff, Vanteon (cwulff@vanteon.com)
62  *
63  */
64 
65 #include <stdio.h>
66 #include <stdlib.h>
67 #include <memory.h>
68 #include <string.h>
69 
70 #include "decompile.h"
71 
73 long dtd_id;
74 
75 #define INDENT_SIZE 4
76 
78 {
79  {1, "UNKNOWN"},
80  {2, "-//WAPFORUM//DTD WML 1.0//EN\"\n"
81  "\"http://www.wapforum.org/DTD/wml.xml"},
82  {3, "-//WAPFORUM//DTD WTA 1.0//EN"},
83  {4, "-//WAPFORUM//DTD WML 1.1//EN\"\n"
84  "\"http://www.wapforum.org/DTD/wml_1.1.xml"},
85  {5, "-//WAPFORUM//DTD SI 1.0//EN\"\n"
86  "\"http://www.wapforum.org/DTD/si.dtd"},
87  {6, "-//WAPFORUM//DTD SL 1.0//EN\"\n"
88  "\"http://www.wapforum.org/DTD/sl.dtd"},
89  {7, "-//WAPFORUM//DTD CO 1.0//EN"},
90  {8, "-//WAPFORUM//DTD CHANNEL 1.1//EN"},
91  {9, "-//WAPFORUM//DTD WML 1.2//EN\"\n"
92  "\"http://www.wapforum.org/DTD/wml12.dtd"},
93  {0, NULL}
94 };
95 
96 
97 /**************************************
98  * DTD Public Type 4 (WML 1.1) Tables *
99  **************************************/
100 
102 {
103  {4, "a", 0, 0x1c},
104  {4, "anchor", 0, 0x22},
105  {4, "access", 0, 0x23},
106  {4, "b", 0, 0x24},
107  {4, "big", 0, 0x25},
108  {4, "br", 0, 0x26},
109  {4, "card", 0, 0x27},
110  {4, "do", 0, 0x28},
111  {4, "em", 0, 0x29},
112  {4, "fieldset", 0, 0x2a},
113  {4, "go", 0, 0x2b},
114  {4, "head", 0, 0x2c},
115  {4, "i", 0, 0x2d},
116  {4, "img", 0, 0x2e},
117  {4, "input", 0, 0x2f},
118  {4, "meta", 0, 0x30},
119  {4, "noop", 0, 0x31},
120  {4, "p", 0, 0x20},
121  {4, "postfield", 0, 0x21},
122  {4, "pre", 0, 0x1b},
123  {4, "prev", 0, 0x32},
124  {4, "onevent", 0, 0x33},
125  {4, "optgroup", 0, 0x34},
126  {4, "option", 0, 0x35},
127  {4, "refresh", 0, 0x36},
128  {4, "select", 0, 0x37},
129  {4, "setvar", 0, 0x3e},
130  {4, "small", 0, 0x38},
131  {4, "strong", 0, 0x39},
132  {4, "table", 0, 0x1f},
133  {4, "td", 0, 0x1d},
134  {4, "template", 0, 0x3b},
135  {4, "timer", 0, 0x3c},
136  {4, "tr", 0, 0x1e},
137  {4, "u", 0, 0x3d},
138  {4, "wml", 0, 0x3f},
139 
140  {6, "TAG_05", 1, 0x05},
141  {6, "TAG_06", 1, 0x06},
142  {6, "TAG_07", 1, 0x07},
143 
144  {0, NULL, 0, 0}
145 };
146 
148 {
149  {4, "accept-charset", NULL, 0, 0x05},
150  {4, "accesskey", NULL, 0, 0x5e},
151  {4, "align", NULL, 0, 0x52},
152  {4, "align", "bottom", 0, 0x06},
153  {4, "align", "center", 0, 0x07},
154  {4, "align", "left", 0, 0x08},
155  {4, "align", "middle", 0, 0x09},
156  {4, "align", "right", 0, 0x0a},
157  {4, "align", "top", 0, 0x0b},
158  {4, "alt", NULL, 0, 0x0c},
159  {4, "class", NULL, 0, 0x54},
160  {4, "columns", NULL, 0, 0x53},
161  {4, "content", NULL, 0, 0x0d},
162  {4, "content", "application/vnd.wap.wmlc;charset=", 0, 0x5c},
163  {4, "domain", NULL, 0, 0x0f},
164  {4, "emptyok", "false", 0, 0x10},
165  {4, "emptyok", "true", 0, 0x11},
166  {4, "enctype", NULL, 0, 0x5f},
167  {4, "enctype", "application/x-www-form-urlencoded", 0, 0x60},
168  {4, "enctype", "multipart/form-data", 0, 0x61},
169  {4, "format", NULL, 0, 0x12},
170  {4, "forua", "false", 0, 0x56},
171  {4, "forua", "true", 0, 0x57},
172  {4, "height", NULL, 0, 0x13},
173  {4, "href", NULL, 0, 0x4a},
174  {4, "href", "http://", 0, 0x4b},
175  {4, "href", "https://", 0, 0x4c},
176  {4, "hspace", NULL, 0, 0x14},
177  {4, "http-equiv", NULL, 0, 0x5a},
178  {4, "http-equiv", "Content-Type", 0, 0x5b},
179  {4, "http-equiv", "Expires", 0, 0x5d},
180  {4, "id", NULL, 0, 0x55},
181  {4, "ivalue", NULL, 0, 0x15},
182  {4, "iname", NULL, 0, 0x16},
183  {4, "label", NULL, 0, 0x18},
184  {4, "localsrc", NULL, 0, 0x19},
185  {4, "maxlength", NULL, 0, 0x1a},
186  {4, "method", "get", 0, 0x1b},
187  {4, "method", "post", 0, 0x1c},
188  {4, "mode", "nowrap", 0, 0x1d},
189  {4, "mode", "wrap", 0, 0x1e},
190  {4, "multiple", "false", 0, 0x1f},
191  {4, "multiple", "true", 0, 0x20},
192  {4, "name", NULL, 0, 0x21},
193  {4, "newcontext", "false", 0, 0x22},
194  {4, "newcontext", "true", 0, 0x23},
195  {4, "onenterbackward", NULL, 0, 0x25},
196  {4, "onenterforward", NULL, 0, 0x26},
197  {4, "onpick", NULL, 0, 0x24},
198  {4, "ontimer", NULL, 0, 0x27},
199  {4, "optional", "false", 0, 0x28},
200  {4, "optional", "true", 0, 0x29},
201  {4, "path", NULL, 0, 0x2a},
202  {4, "scheme", NULL, 0, 0x2e},
203  {4, "sendreferer", "false", 0, 0x2f},
204  {4, "sendreferer", "true", 0, 0x30},
205  {4, "size", NULL, 0, 0x31},
206  {4, "src", NULL, 0, 0x32},
207  {4, "src", "http://", 0, 0x58},
208  {4, "src", "https://", 0, 0x59},
209  {4, "ordered", "true", 0, 0x33},
210  {4, "ordered", "false", 0, 0x34},
211  {4, "tabindex", NULL, 0, 0x35},
212  {4, "title", NULL, 0, 0x36},
213  {4, "type", NULL, 0, 0x37},
214  {4, "type", "accept", 0, 0x38},
215  {4, "type", "delete", 0, 0x39},
216  {4, "type", "help", 0, 0x3a},
217  {4, "type", "password", 0, 0x3b},
218  {4, "type", "onpick", 0, 0x3c},
219  {4, "type", "onenterbackward", 0, 0x3d},
220  {4, "type", "onenterforward", 0, 0x3e},
221  {4, "type", "ontimer", 0, 0x3f},
222  {4, "type", "options", 0, 0x45},
223  {4, "type", "prev", 0, 0x46},
224  {4, "type", "reset", 0, 0x47},
225  {4, "type", "text", 0, 0x48},
226  {4, "type", "vnd.", 0, 0x49},
227  {4, "value", NULL, 0, 0x4d},
228  {4, "vspace", NULL, 0, 0x4e},
229  {4, "width", NULL, 0, 0x4f},
230  {4, "xml:lang", NULL, 0, 0x50},
231 
232  {6, "ATTR_06", NULL, 1, 0x06},
233  {6, "ATTR_07", NULL, 1, 0x07},
234  {6, "ATTR_08", NULL, 1, 0x08},
235  {6, "ATTR_11", NULL, 1, 0x11},
236  {6, "ATTR_12", NULL, 1, 0x12},
237  {6, "ATTR_13", NULL, 1, 0x13},
238  {6, "ATTR_14", NULL, 1, 0x14},
239  {6, "ATTR_15", NULL, 1, 0x15},
240  {6, "ATTR_21", NULL, 1, 0x21},
241  {6, "ATTR_22", NULL, 1, 0x22},
242  {6, "ATTR_23", NULL, 1, 0x23},
243  {6, "ATTR_24", NULL, 1, 0x24},
244  {6, "ATTR_28", NULL, 1, 0x28},
245  {6, "ATTR_29", NULL, 1, 0x29},
246  {6, "ATTR_45", NULL, 1, 0x45},
247  {6, "ATTR_61", NULL, 1, 0x61},
248  {6, "ATTR_62", NULL, 1, 0x62},
249  {6, "ATTR_63", NULL, 1, 0x63},
250  {6, "ATTR_64", NULL, 1, 0x64},
251  {6, "ATTR_6A", NULL, 1, 0x6A},
252  {6, "ATTR_6B", NULL, 1, 0x6B},
253  {6, "ATTR_6C", NULL, 1, 0x6C},
254  {6, "ATTR_70", NULL, 1, 0x70},
255  {6, "ATTR_71", NULL, 1, 0x71},
256  {6, "ATTR_73", NULL, 1, 0x73},
257  {6, "ATTR_74", NULL, 1, 0x74},
258 
259  {0, NULL, NULL, 0, 0}
260 };
261 
263 {
264  {4, ".com/", 0, 0x85},
265  {4, ".edu/", 0, 0x86},
266  {4, ".net/", 0, 0x87},
267  {4, ".org/", 0, 0x88},
268  {4, "accept", 0, 0x89},
269  {4, "bottom", 0, 0x8a},
270  {4, "clear", 0, 0x8b},
271  {4, "delete", 0, 0x8c},
272  {4, "help", 0, 0x8d},
273  {4, "http://", 0, 0x8e},
274  {4, "http://www.", 0, 0x8f},
275  {4, "https://", 0, 0x90},
276  {4, "https://www.", 0, 0x91},
277  {4, "middle", 0, 0x93},
278  {4, "nowrap", 0, 0x94},
279  {4, "onenterbackward", 0, 0x96},
280  {4, "onenterforward", 0, 0x97},
281  {4, "onpick", 0, 0x95},
282  {4, "ontimer", 0, 0x98},
283  {4, "options", 0, 0x99},
284  {4, "password", 0, 0x9a},
285  {4, "reset", 0, 0x9b},
286  {4, "text", 0, 0x9d},
287  {4, "top", 0, 0x9e},
288  {4, "unknown", 0, 0x9f},
289  {4, "wrap", 0, 0xa0},
290  {4, "www.", 0, 0xa1},
291  {0, NULL, 0, 0}
292 };
293 
294 
295 /**************************
296  * Node Tree Construction *
297  **************************/
298 
299 /*
300  * Function: NewNode
301  *
302  * Description:
303  *
304  * Allocate and initialize a new node. This links the new node
305  * as the first child of the current node in the buffer. This causes
306  * child nodes to be linked in reverse order. If there is no current
307  * node, then the new node will be linked in as the first child at the
308  * top of the tree.
309  *
310  * Parameters:
311  *
312  * buffer - WBXML buffer to link the new node into
313  * type - Type of node to allocate
314  *
315  * Return value:
316  *
317  * P_WBXML_NODE - A pointer to the newly allocated node.
318  *
319  */
321 {
322  if (buffer)
323  {
324  P_WBXML_NODE newnode = malloc(sizeof(WBXML_NODE));
325 
326  if (newnode)
327  {
328  newnode->m_prev = NULL;
329  newnode->m_child = NULL;
330 
331  if (buffer->m_curnode)
332  {
333  /* Insert this node as the first child of the current node */
334  newnode->m_parent = buffer->m_curnode;
335  newnode->m_next = buffer->m_curnode->m_child;
336 
337  if (buffer->m_curnode->m_child)
338  {
339  ((P_WBXML_NODE)buffer->m_curnode->m_child)->m_prev = newnode;
340  }
341 
342  buffer->m_curnode->m_child = newnode;
343  }
344  else
345  {
346  /* Insert this node at the top of the tree */
347  newnode->m_parent = NULL;
348  newnode->m_next = buffer->m_tree;
349 
350  if (buffer->m_tree)
351  {
352  buffer->m_tree->m_prev = newnode;
353  }
354 
355  buffer->m_tree = newnode;
356  }
357 
358  newnode->m_page = buffer->m_curpage;
359  newnode->m_type = type;
360  newnode->m_data = NULL;
361  }
362  else
363  {
365  }
366 
367  return newnode;
368  }
369  else
370  {
372  }
373 
374  return NULL;
375 }
376 
377 /*
378  * Function: FreeNode
379  *
380  * Description:
381  *
382  * Free a node, all its children and forward siblings.
383  *
384  * Parameters:
385  *
386  * node - The node to free
387  *
388  */
389 static void FreeNode(P_WBXML_NODE node)
390 {
391  if (node)
392  {
393  if (node->m_child)
394  {
395  FreeNode(node->m_child);
396  }
397 
398  if (node->m_next)
399  {
400  FreeNode(node->m_next);
401  }
402 
403  free(node);
404  }
405 }
406 
407 static void AddDTDNode(P_WBXML_INFO buffer, const WBXML_DTD_TYPE dtdnum, const WBXML_MB_U_INT32 index)
408 {
409  P_WBXML_NODE newnode = NewNode(buffer, NODE_DTD_TYPE);
410  newnode->m_data = malloc(sizeof(DTD_NODE_DATA));
411  memcpy( &( ((DTD_NODE_DATA*)newnode->m_data)->m_dtdnum ), &(dtdnum[0]), sizeof(WBXML_MB_U_INT32) );
412  memcpy( &( ((DTD_NODE_DATA*)newnode->m_data)->m_index ), &(index[0]), sizeof(WBXML_MB_U_INT32) );
413  dtd_id = (long) dtdnum[0];
414 }
415 
416 static void AddStringTableNode(P_WBXML_INFO buffer, const P_WBXML_STRING_TABLE strings)
417 {
418  P_WBXML_NODE newnode = NewNode(buffer, NODE_STRING_TABLE);
419  newnode->m_data = malloc(sizeof(WBXML_STRING_TABLE));
420  memcpy( newnode->m_data, strings, sizeof(WBXML_STRING_TABLE) );
421 }
422 
423 static void AddCodepageTagNode(P_WBXML_INFO buffer, WBXML_TAG tag)
424 {
425  P_WBXML_NODE newnode = NewNode(buffer, NODE_CODEPAGE_TAG);
426  newnode->m_data = malloc(sizeof(WBXML_TAG));
427  *((P_WBXML_TAG)newnode->m_data) = tag;
428 }
429 
431 {
433  newnode->m_data = malloc(sizeof(WBXML_MB_U_INT32));
434  memcpy( ((P_WBXML_MB_U_INT32)newnode->m_data), &index, sizeof(WBXML_MB_U_INT32) );
435 }
436 
437 static void AddAttrStartNode(P_WBXML_INFO buffer, WBXML_TAG tag)
438 {
439  P_WBXML_NODE newnode = NewNode(buffer, NODE_ATTRSTART);
440  newnode->m_data = malloc(sizeof(WBXML_TAG));
441  *((P_WBXML_TAG)newnode->m_data) = tag;
442 }
443 
445 {
446  P_WBXML_NODE newnode = NewNode(buffer, NODE_ATTRSTART_LITERAL);
447  newnode->m_data = malloc(sizeof(WBXML_MB_U_INT32));
448  memcpy( ((P_WBXML_MB_U_INT32)newnode->m_data), &index, sizeof(WBXML_MB_U_INT32) );
449 }
450 
451 static void AddAttrValueNode(P_WBXML_INFO buffer, WBXML_TAG tag)
452 {
453  P_WBXML_NODE newnode = NewNode(buffer, NODE_ATTRVALUE);
454  newnode->m_data = malloc(sizeof(WBXML_TAG));
455  *((P_WBXML_TAG)newnode->m_data) = tag;
456 }
457 
458 static void AddAttrEndNode(P_WBXML_INFO buffer)
459 {
460  P_WBXML_NODE newnode = NewNode(buffer, NODE_ATTREND);
461  newnode->m_data = NULL;
462 }
463 
464 static void AddStringNode(P_WBXML_INFO buffer, char* string)
465 {
466  P_WBXML_NODE newnode = NewNode(buffer, NODE_STRING);
467  newnode->m_data = strdup(string);
468 }
469 
470 static void AddVariableStringNode(P_WBXML_INFO buffer, char* string, WBXML_VARIABLE_TYPE type)
471 {
472  /* TODO: add this node */
473 }
474 
475 static void AddVariableIndexNode(P_WBXML_INFO buffer, char* string, WBXML_VARIABLE_TYPE type)
476 {
477  /* TODO: add this node */
478 }
479 
480 
481 /****************
482  * Flow Control *
483  ****************/
484 
485 void Message(char* msg)
486 {
487  printf("%s\n", msg);
488 }
489 
491 {
492  switch (error)
493  {
494  case ERR_END_OF_DATA:
495  Message("Input stream is incomplete (EOF).");
496  break;
497 
499  Message("Internal error: Bad parameter.");
500  break;
501 
502  case ERR_TAG_NOT_FOUND:
503  Message("Tag not found.");
504  break;
505 
506  case ERR_FILE_NOT_FOUND:
507  Message("File not found.");
508  break;
509 
510  case ERR_FILE_NOT_READ:
511  Message("File read error.");
512  break;
513 
515  Message("Not enough memory");
516  break;
517 
518  default:
519  Message("Unknown error.");
520  break;
521  }
522 
523  exit(error);
524 }
525 
527 {
528  switch (warning)
529  {
531  Message("Token EXT_0 encountered. This token is reserved for future expansion.");
532  break;
533 
535  Message("Token EXT_1 encountered. This token is reserved for future expansion.");
536  break;
537 
539  Message("Token EXT_2 encountered. This token is reserved for future expansion.");
540  break;
541 
542  default:
543  Message("Unknown warning.");
544  break;
545  }
546 }
547 
549 {
550  if (buffer)
551  {
552  WBXML_LENGTH bytesRead = (buffer->m_curpos - buffer->m_start);
553  if (bytesRead >= buffer->m_length)
554  {
555  return 0;
556  }
557  else
558  {
559  return (buffer->m_length - bytesRead);
560  }
561  }
562  else
563  {
565  }
566 
567  return 0;
568 }
569 
571 {
572  BOOL result = FALSE;
573 
574  if (buffer)
575  {
576  if (BytesLeft(buffer) >= sizeof(WBXML_TAG))
577  {
578  result = ((*((WBXML_TAG*) buffer->m_curpos)) == tag);
579  }
580  else
581  {
582  /* No more data, so nope, not this tag */
583  result = FALSE;
584  }
585  }
586  else
587  {
589  }
590 
591  return result;
592 }
593 
595 {
596  WBXML_U_INT8 result = *(buffer->m_curpos);
597 
598  /* NOTE THAT THESE ARE NOT UNIQUE! */
599  switch (type)
600  {
601  case CP_TAG_TAG:
602  return TRUE;
603  case CP_TAG_ATTRSTART:
604  return ((result & 0x80) != 0x80);
605  case CP_TAG_ATTRVALUE:
606  return ((result & 0x80) == 0x80);
607  default:
608  return FALSE;
609  }
610 }
611 
613 {
614  WBXML_INFO tmpbuffer;
615  memcpy(&tmpbuffer, buffer, sizeof(WBXML_INFO));
616  tmpbuffer.m_curpos += SWITCHPAGE_SIZE;
617 
618  return ((Is_switchPage(buffer) && IsCodepageTag(&tmpbuffer, CP_TAG_ATTRVALUE)) ||
619  IsCodepageTag(buffer, CP_TAG_ATTRVALUE) ||
620  Is_string(buffer) ||
621  Is_extension(buffer) ||
622  Is_entity(buffer) ||
623  Is_pi(buffer) ||
624  Is_opaque(buffer));
625 }
626 
628 {
629  WBXML_INFO tmpbuffer;
630  memcpy(&tmpbuffer, buffer, sizeof(WBXML_INFO));
631  tmpbuffer.m_curpos += SWITCHPAGE_SIZE;
632 
633  return ((Is_switchPage(buffer) &&
634  (IsTag(&tmpbuffer, TAG_EXT_0) ||
635  IsTag(&tmpbuffer, TAG_EXT_1) ||
636  IsTag(&tmpbuffer, TAG_EXT_2) ||
637  IsTag(&tmpbuffer, TAG_EXT_T_0) ||
638  IsTag(&tmpbuffer, TAG_EXT_T_1) ||
639  IsTag(&tmpbuffer, TAG_EXT_T_2) ||
640  IsTag(&tmpbuffer, TAG_EXT_I_0) ||
641  IsTag(&tmpbuffer, TAG_EXT_I_1) ||
642  IsTag(&tmpbuffer, TAG_EXT_I_2))) ||
643  (IsTag(buffer, TAG_EXT_0) ||
644  IsTag(buffer, TAG_EXT_1) ||
645  IsTag(buffer, TAG_EXT_2) ||
646  IsTag(buffer, TAG_EXT_T_0) ||
647  IsTag(buffer, TAG_EXT_T_1) ||
648  IsTag(buffer, TAG_EXT_T_2) ||
649  IsTag(buffer, TAG_EXT_I_0) ||
650  IsTag(buffer, TAG_EXT_I_1) ||
651  IsTag(buffer, TAG_EXT_I_2)));
652 }
653 
655 {
656  return (Is_inline(buffer) ||
657  Is_tableref(buffer));
658 }
659 
661 {
662  return IsTag(buffer, TAG_SWITCH_PAGE);
663 }
664 
666 {
667  return IsTag(buffer, TAG_STR_I);
668 }
669 
671 {
672  return IsTag(buffer, TAG_STR_T);
673 }
674 
676 {
677  return IsTag(buffer, TAG_ENTITY);
678 }
679 
681 {
682  return IsTag(buffer, TAG_PI);
683 }
684 
686 {
687  return IsTag(buffer, TAG_OPAQUE);
688 }
689 
691 {
692  BOOL result = FALSE;
693 
694  if (buffer)
695  {
696  if (BytesLeft(buffer) >= 1)
697  {
698  result = ((*buffer->m_curpos) == 0);
699  }
700  else
701  {
703  }
704  }
705  else
706  {
708  }
709 
710  return result;
711 }
712 
713 
714 /***********************
715  * Basic Type Decoders *
716  ***********************/
717 
719 {
720  if (buffer && result)
721  {
722  if (BytesLeft(buffer) >= 1)
723  {
724  *result = *(buffer->m_curpos);
725  (buffer->m_curpos)++;
726  }
727  else
728  {
730  }
731  }
732  else
733  {
735  }
736 }
737 
739 {
740  if (buffer && result)
741  {
742  int i;
743  for (i = 0; i < MAX_MB_U_INT32_BYTES; i++)
744  {
745  if (BytesLeft(buffer) >= 1)
746  {
747  (*result)[i] = *(buffer->m_curpos);
748  (buffer->m_curpos)++;
749 
750  if ( !( (*result)[i] & 0x80 ) )
751  break;
752  }
753  else
754  {
756  }
757  }
758  }
759  else
760  {
762  }
763 }
764 
765 void Read_bytes(P_WBXML_INFO buffer, WBXML_LENGTH length, P_WBXML_BYTES result)
766 {
767  if (buffer && result)
768  {
769  if (BytesLeft(buffer) >= length)
770  {
771  *result = (WBXML_BYTES) malloc(length*sizeof(unsigned char));
772  memcpy(*result, buffer->m_curpos, length);
773  buffer->m_curpos += length;
774  }
775  else
776  {
778  }
779  }
780  else
781  {
783  }
784 }
785 
787 {
788  if (buffer)
789  {
790  if (BytesLeft(buffer) >= sizeof(WBXML_TAG))
791  {
792  if ((*((WBXML_TAG*) buffer->m_curpos)) == tag)
793  {
794  buffer->m_curpos += sizeof(WBXML_TAG);
795  }
796  else
797  {
799  }
800  }
801  else
802  {
804  }
805  }
806  else
807  {
809  }
810 }
811 
813 {
814  WBXML_TAG tag = 0;
815 
816  if (buffer)
817  {
818  if (BytesLeft(buffer) >= sizeof(WBXML_TAG))
819  {
820  tag = *((WBXML_TAG*) buffer->m_curpos);
821 
822  switch (type)
823  {
824  case CP_TAG_TAG:
825  buffer->m_curpos += sizeof(WBXML_TAG);
826  break;
827 
828  case CP_TAG_ATTRSTART:
829  if ((tag & 0x80) != 0x80)
830  {
831  buffer->m_curpos += sizeof(WBXML_TAG);
832  }
833  else
834  {
836  }
837  break;
838 
839  case CP_TAG_ATTRVALUE:
840  if ((tag & 0x80) == 0x80)
841  {
842  buffer->m_curpos += sizeof(WBXML_TAG);
843  }
844  else
845  {
847  }
848  break;
849 
850  default:
852  break;
853  }
854  }
855  else
856  {
858  }
859  }
860  else
861  {
863  }
864 
865  return tag;
866 }
867 
868 
869 /**************************
870  * Basic Type Conversions *
871  **************************/
872 
874 {
875  long result = 0;
876 
877  if (value)
878  {
879  int i;
880  for (i = 0; i < MAX_MB_U_INT32_BYTES; i++)
881  {
882  result <<= 7;
883  result |= ((*value)[i] & 0x7f);
884 
885  if ( !( (*value)[i] & 0x80 ) )
886  break;
887  }
888  }
889  else
890  {
892  }
893 
894  return result;
895 }
896 
897 static void OutputEncodedString(const unsigned char* str)
898 {
899  /* Work our way down the string looking for illegal chars */
900  while (*str != 0)
901  {
902  if ((*str < 0x20) || (*str > 0x7F))
903  {
904  /* Out of range... encode */
905  printf("&#x%02x;", *str);
906  }
907  else
908  {
909  switch (*str)
910  {
911  case '<':
912  case '>':
913  case '&':
914  case '\'':
915  case '\"':
916  /* Special symbol... encode */
917  printf("&#x%2x", *str);
918  break;
919 
920  default:
921  printf("%c", *str);
922  break;
923  }
924  }
925 
926  str++;
927  }
928 }
929 
930 
931 /*******************************
932  * Document Structure Decoders *
933  *******************************/
934 
936 {
937  Read_version(buffer);
938  Read_publicid(buffer);
939  Read_charset(buffer);
940  Read_strtbl(buffer);
941  Read_body(buffer);
942 }
943 
945 {
946  WBXML_STRING_TABLE result;
947  Read_mb_u_int32(buffer, &(result.m_length));
948  Read_bytes(buffer, mb_u_int32_to_long(&(result.m_length)), &(result.m_strings));
949 
950  AddStringTableNode(buffer, &result);
951 }
952 
953 void Read_body (P_WBXML_INFO buffer)
954 {
955  while (Is_pi(buffer))
956  {
957  Read_pi(buffer);
958  }
959 
960  Read_element(buffer);
961 
962  while (Is_pi(buffer))
963  {
964  Read_pi(buffer);
965  }
966 }
967 
969 {
970  WBXML_TAG stagvalue = 0;
971 
972  if (Is_switchPage(buffer))
973  {
974  Read_switchPage(buffer);
975  }
976 
977  stagvalue = Read_stag(buffer);
978 
979  /* move the current node down to this one in the tree */
980  if (buffer->m_curnode)
981  buffer->m_curnode = buffer->m_curnode->m_child;
982  else buffer->m_curnode = buffer->m_tree;
983 
984  if ((stagvalue & CODEPAGE_TAG_HAS_ATTRS) == CODEPAGE_TAG_HAS_ATTRS)
985  {
986  do
987  {
988  Read_attribute(buffer);
989 
990  } while (!IsTag(buffer, TAG_END));
991 
992  ReadFixedTag(buffer, TAG_END);
993 
994  AddAttrEndNode(buffer);
995  }
996 
998  {
999  while (!IsTag(buffer, TAG_END))
1000  {
1001  Read_content(buffer);
1002  }
1003 
1004  ReadFixedTag(buffer, TAG_END);
1005  }
1006 
1007  /* move the current node back up one */
1008  buffer->m_curnode = buffer->m_curnode->m_parent;
1009 }
1010 
1012 {
1013  if (Is_string(buffer))
1014  {
1015  Read_string(buffer);
1016  }
1017  else if (Is_extension(buffer))
1018  {
1019  Read_extension(buffer);
1020  }
1021  else if (Is_entity(buffer))
1022  {
1023  Read_entity(buffer);
1024  }
1025  else if (Is_pi(buffer))
1026  {
1027  Read_pi(buffer);
1028  }
1029  else if (Is_opaque(buffer))
1030  {
1031  Read_opaque(buffer);
1032  }
1033  else
1034  {
1035  /* Assume it is an element */
1036  Read_element(buffer);
1037  }
1038 }
1039 
1041 {
1042  if (IsCodepageTag(buffer, CP_TAG_TAG))
1043  {
1044  WBXML_TAG tag = ReadCodepageTag(buffer, CP_TAG_TAG);
1045 
1046  AddCodepageTagNode(buffer, tag);
1047 
1048  return tag;
1049  }
1050  else if (IsTag(buffer, TAG_LITERAL))
1051  {
1052  WBXML_MB_U_INT32 index;
1053 
1054  ReadFixedTag(buffer, TAG_LITERAL);
1055  Read_index(buffer, &index);
1056 
1057  AddCodepageLiteralTagNode(buffer, index);
1058  }
1059  else
1060  {
1062  }
1063 
1064  return 0;
1065 }
1066 
1068 {
1069  Read_attrStart(buffer);
1070 
1071  while (Is_attrValue(buffer))
1072  {
1073  Read_attrValue(buffer);
1074  }
1075 }
1076 
1078 {
1079  if (Is_switchPage(buffer))
1080  {
1081  WBXML_TAG tag;
1082  Read_switchPage(buffer);
1083  tag = ReadCodepageTag(buffer, CP_TAG_ATTRSTART);
1084 
1085  AddAttrStartNode(buffer, tag);
1086  }
1087  else if (IsCodepageTag(buffer, CP_TAG_ATTRSTART))
1088  {
1089  WBXML_TAG tag;
1090  tag = ReadCodepageTag(buffer, CP_TAG_ATTRSTART);
1091 
1092  AddAttrStartNode(buffer, tag);
1093  }
1094  else if (IsTag(buffer, TAG_LITERAL))
1095  {
1096  WBXML_MB_U_INT32 index;
1097 
1098  ReadFixedTag(buffer, TAG_LITERAL);
1099  Read_index(buffer, &index);
1100 
1101  AddAttrStartLiteralNode(buffer, index);
1102  }
1103  else
1104  {
1106  }
1107 }
1108 
1110 {
1111  if (Is_switchPage(buffer))
1112  {
1113  WBXML_TAG tag;
1114  Read_switchPage(buffer);
1115  tag = ReadCodepageTag(buffer, CP_TAG_ATTRVALUE);
1116  AddAttrValueNode(buffer, tag);
1117  }
1118  else if (IsCodepageTag(buffer, CP_TAG_ATTRVALUE))
1119  {
1120  WBXML_TAG tag;
1121  tag = ReadCodepageTag(buffer, CP_TAG_ATTRVALUE);
1122  AddAttrValueNode(buffer, tag);
1123  }
1124  else if (Is_string(buffer))
1125  {
1126  Read_string(buffer);
1127  }
1128  else if (Is_extension(buffer))
1129  {
1130  Read_extension(buffer);
1131  }
1132  else if (Is_entity(buffer))
1133  {
1134  Read_entity(buffer);
1135  }
1136  else if (Is_opaque(buffer))
1137  {
1138  Read_opaque(buffer);
1139  }
1140  else
1141  {
1143  }
1144 }
1145 
1147 {
1148  if (Is_switchPage(buffer))
1149  {
1150  Read_switchPage(buffer);
1151  }
1152 
1153  if (IsTag(buffer, TAG_EXT_I_0))
1154  {
1155  char* str = NULL;
1156 
1157  ReadFixedTag(buffer, TAG_EXT_I_0);
1158  Read_termstr_rtn(buffer, &str);
1159 
1160  AddVariableStringNode(buffer, str, VAR_ESCAPED);
1161  }
1162  else if (IsTag(buffer, TAG_EXT_I_1))
1163  {
1164  char* str = NULL;
1165 
1166  ReadFixedTag(buffer, TAG_EXT_I_1);
1167  Read_termstr_rtn(buffer, &str);
1168 
1169  AddVariableStringNode(buffer, str, VAR_UNESCAPED);
1170  }
1171  else if (IsTag(buffer, TAG_EXT_I_2))
1172  {
1173  char* str = NULL;
1174 
1175  ReadFixedTag(buffer, TAG_EXT_I_2);
1176  Read_termstr_rtn(buffer, &str);
1177 
1178  AddVariableStringNode(buffer, str, VAR_UNCHANGED);
1179  }
1180  else if (IsTag(buffer, TAG_EXT_T_0))
1181  {
1182  WBXML_MB_U_INT32 index;
1183 
1184  ReadFixedTag(buffer, TAG_EXT_T_0);
1185  Read_index(buffer, &index);
1186 
1187  AddVariableIndexNode(buffer, index, VAR_ESCAPED);
1188  }
1189  else if (IsTag(buffer, TAG_EXT_T_1))
1190  {
1191  WBXML_MB_U_INT32 index;
1192 
1193  ReadFixedTag(buffer, TAG_EXT_T_1);
1194  Read_index(buffer, &index);
1195 
1196  AddVariableIndexNode(buffer, index, VAR_UNESCAPED);
1197  }
1198  else if (IsTag(buffer, TAG_EXT_T_2))
1199  {
1200  WBXML_MB_U_INT32 index;
1201 
1202  ReadFixedTag(buffer, TAG_EXT_T_2);
1203  Read_index(buffer, &index);
1204 
1205  AddVariableIndexNode(buffer, index, VAR_UNCHANGED);
1206  }
1207  else if (IsTag(buffer, TAG_EXT_0))
1208  {
1209  ReadFixedTag(buffer, TAG_EXT_0);
1210 
1212  }
1213  else if (IsTag(buffer, TAG_EXT_1))
1214  {
1215  ReadFixedTag(buffer, TAG_EXT_1);
1216 
1218  }
1219  else if (IsTag(buffer, TAG_EXT_2))
1220  {
1221  ReadFixedTag(buffer, TAG_EXT_2);
1222 
1224  }
1225  else
1226  {
1228  }
1229 }
1230 
1232 {
1233  if (Is_inline(buffer))
1234  {
1235  Read_inline(buffer);
1236  }
1237  else if (Is_tableref(buffer))
1238  {
1239  Read_tableref(buffer);
1240  }
1241  else
1242  {
1244  }
1245 }
1246 
1248 {
1249  WBXML_U_INT8 pageindex;
1250 
1251  ReadFixedTag(buffer, TAG_SWITCH_PAGE);
1252  Read_pageindex(buffer, &pageindex);
1253 
1254  /* Use the new codepage */
1255  buffer->m_curpage = pageindex;
1256 }
1257 
1259 {
1260  ReadFixedTag(buffer, TAG_STR_I);
1261  Read_termstr(buffer);
1262 }
1263 
1265 {
1266  WBXML_MB_U_INT32 index;
1267 
1268  ReadFixedTag(buffer, TAG_STR_T);
1269  Read_index(buffer, &index);
1270 }
1271 
1273 {
1274  ReadFixedTag(buffer, TAG_ENTITY);
1275  Read_entcode(buffer);
1276 }
1277 
1279 {
1280  WBXML_MB_U_INT32 result;
1281  Read_mb_u_int32(buffer, &result);
1282 }
1283 
1284 void Read_pi (P_WBXML_INFO buffer)
1285 {
1286  ReadFixedTag(buffer, TAG_PI);
1287  Read_attrStart(buffer);
1288 
1289  while (Is_attrValue(buffer))
1290  {
1291  Read_attrValue(buffer);
1292  }
1293 
1294  ReadFixedTag(buffer, TAG_END);
1295 }
1296 
1298 {
1299  WBXML_MB_U_INT32 length;
1300  WBXML_BYTES data;
1301 
1302  ReadFixedTag(buffer, TAG_OPAQUE);
1303  Read_length(buffer, &length);
1304  Read_bytes(buffer, mb_u_int32_to_long(&length), &data);
1305 }
1306 
1308 {
1309  WBXML_U_INT8 result;
1310 
1311  Read_u_int8(buffer, &result);
1312 }
1313 
1315 {
1316  if (Is_zero(buffer))
1317  {
1318  WBXML_MB_U_INT32 index;
1319 
1320  Read_index(buffer, &index);
1321 
1322  AddDTDNode(buffer, ZERO_WBXML_MB_U_INT32, index);
1323  }
1324  else
1325  {
1326  WBXML_MB_U_INT32 result;
1327 
1328  Read_mb_u_int32(buffer, &result);
1329 
1330  AddDTDNode(buffer, result, ZERO_WBXML_MB_U_INT32);
1331  }
1332 }
1333 
1335 {
1336  WBXML_MB_U_INT32 result;
1337 
1338  Read_mb_u_int32(buffer, &result);
1339 }
1340 
1341 void Read_termstr_rtn(P_WBXML_INFO buffer, char** result)
1342 {
1343 
1344 #define STRING_BLOCK_SIZE 256
1345 
1346  int buflen = STRING_BLOCK_SIZE;
1347  char* strbuf = (char*) malloc(buflen);
1348  BOOL doubled = FALSE;
1349  int i = 0;
1350 
1351  if (!result)
1353 
1354  while ( (BytesLeft(buffer) >= 1) && (*(buffer->m_curpos) != 0) )
1355  {
1356  if (i>=buflen)
1357  {
1358  buflen += STRING_BLOCK_SIZE;
1359  strbuf = realloc(strbuf, buflen);
1360  }
1361 
1362  if (*(buffer->m_curpos) != '$' || doubled == TRUE)
1363  {
1364  strbuf[i] = *(buffer->m_curpos);
1365  buffer->m_curpos++;
1366  i++;
1367  if (doubled == TRUE)
1368  doubled = FALSE;
1369  }
1370  else
1371  {
1372  strbuf[i] = *(buffer->m_curpos);
1373  i++;
1374  doubled = TRUE;
1375  }
1376  }
1377 
1378  strbuf[i] = 0;
1379  buffer->m_curpos++;
1380 
1381  if (*result)
1382  free(*result);
1383 
1384  *result = strbuf;
1385 }
1386 
1388 {
1389  char* strbuf = NULL;
1390 
1391  Read_termstr_rtn(buffer, &strbuf);
1392 
1393  AddStringNode(buffer, strbuf);
1394 
1395  free(strbuf);
1396 }
1397 
1399 {
1400  Read_mb_u_int32(buffer, result);
1401 }
1402 
1404 {
1405  Read_mb_u_int32(buffer, result);
1406 }
1407 
1409 {
1410  WBXML_U_INT8 result;
1411 
1412  Read_u_int8(buffer, &result);
1413 
1414  if (result != (WBXML_U_INT8) 0)
1415  {
1417  }
1418 }
1419 
1421 {
1422  Read_u_int8(buffer, result);
1423 }
1424 
1425 static void Init(P_WBXML_INFO buffer)
1426 {
1427  buffer->m_start = NULL;
1428  buffer->m_curpos = NULL;
1429  buffer->m_length = 0;
1430  buffer->m_tree = NULL;
1431  buffer->m_curnode = NULL;
1432  buffer->m_curpage = 0;
1433 }
1434 
1435 static size_t BufferLength(P_WBXML_INFO buffer)
1436 {
1437  size_t ret;
1438 
1439  while (buffer->m_curpos != '\0')
1440  buffer->m_curpos++;
1441 
1442  ret = buffer->m_curpos - buffer->m_start;
1443  buffer->m_curpos = buffer->m_start;
1444  return ret;
1445 }
1446 
1447 static void Free(P_WBXML_INFO buffer)
1448 {
1449  if (buffer->m_start)
1450  {
1451  free(buffer->m_start);
1452  buffer->m_start = NULL;
1453  }
1454 
1455  buffer->m_curpos = NULL;
1456  buffer->m_length = 0;
1457 
1458  FreeNode(buffer->m_tree);
1459  buffer->m_tree = NULL;
1460 }
1461 
1462 static long FileSize(FILE* file)
1463 {
1464  long curpos = ftell(file);
1465  long endpos;
1466  fseek(file, 0, SEEK_END);
1467  endpos = ftell(file);
1468  fseek(file, curpos, SEEK_SET);
1469 
1470  return endpos;
1471 }
1472 
1473 static void ReadBinary(P_WBXML_INFO buffer, FILE* file)
1474 {
1475  char buf[4096];
1476  int m = 1;
1477  long n;
1478 
1479  if (buffer && file)
1480  {
1481  if (file != stdin)
1482  {
1483  buffer->m_length = FileSize(file);
1484  buffer->m_start = (P_WBXML) malloc(buffer->m_length);
1485  buffer->m_curpos = buffer->m_start;
1486 
1487  if (!buffer->m_start)
1488  {
1489  fclose(file);
1491  }
1492 
1493  if (fread(buffer->m_start, 1, buffer->m_length, file) != buffer->m_length)
1494  {
1495  fclose(file);
1497  }
1498  else
1499  {
1500  fclose(file);
1501  }
1502  }
1503  else
1504  {
1505  while ((n = fread(buf, 1, sizeof(buf), file)) > 0)
1506  {
1507  buffer->m_start = (P_WBXML) realloc(buffer->m_start, sizeof(buf) * m);
1508  memcpy(buffer->m_start + (sizeof(buf) * (m - 1)), buf, sizeof(buf));
1509  m++;
1510  }
1511  buffer->m_length = BufferLength(buffer);
1512  buffer->m_curpos = buffer->m_start;
1513  }
1514 
1515  }
1516  else
1517  {
1519  }
1520 }
1521 
1522 static const char* DTDTypeName(long dtdnum)
1523 {
1524  int i = 0;
1525 
1526  /* Search the DTD list for a match */
1527  while (DTDTypeList[i].m_name)
1528  {
1529  if (DTDTypeList[i].m_id == dtdnum)
1530  {
1531  break;
1532  }
1533 
1534  i++;
1535  }
1536 
1537  return DTDTypeList[i].m_name;
1538 }
1539 
1540 static const char* CodepageTagName(WBXML_CODEPAGE page, WBXML_TAG tag)
1541 {
1542  int i = 0;
1543 
1544  /* Strip flags off of the tag */
1545  tag = (WBXML_TAG) (tag & CODEPAGE_TAG_MASK);
1546 
1547  /* Search the tag list for a match */
1548  while (CodepageTagNames[i].m_name)
1549  {
1550  if ((CodepageTagNames[i].m_dtd_id == dtd_id) &&
1551  (CodepageTagNames[i].m_page == page) &&
1552  (CodepageTagNames[i].m_tag == tag))
1553  {
1554  break;
1555  }
1556 
1557  i++;
1558  }
1559 
1560  return CodepageTagNames[i].m_name;
1561 }
1562 
1563 static const char* CodepageAttrstartName(WBXML_CODEPAGE page, WBXML_TAG tag, char** value)
1564 {
1565  int i = 0;
1566 
1567  /* Check Parameters */
1568  if (!value)
1569  {
1571  }
1572 
1573  /* Search the tag list for a match */
1574  while (CodepageAttrstartNames[i].m_name)
1575  {
1576  if ((CodepageAttrstartNames[i].m_dtd_id == dtd_id) &&
1577  (CodepageAttrstartNames[i].m_page == page) &&
1578  (CodepageAttrstartNames[i].m_tag == tag))
1579  {
1580  break;
1581  }
1582 
1583  i++;
1584  }
1585 
1586  /* Duplicate the value because it may be concatenated to */
1587  if (CodepageAttrstartNames[i].m_valueprefix)
1588  {
1589  *value = strdup(CodepageAttrstartNames[i].m_valueprefix);
1590  }
1591  else
1592  {
1593  *value = NULL;
1594  }
1595 
1596  /* Return the tag name */
1597  return CodepageAttrstartNames[i].m_name;
1598 }
1599 
1600 static void CodepageAttrvalueName(WBXML_CODEPAGE page, WBXML_TAG tag, char** value)
1601 {
1602  int i = 0;
1603 
1604  /* Check Parameters */
1605  if (!value)
1606  {
1608  }
1609 
1610  /* Search the tag list for a match */
1611  while (CodepageAttrvalueNames[i].m_name)
1612  {
1613  if ((CodepageAttrvalueNames[i].m_dtd_id == dtd_id) &&
1614  (CodepageAttrvalueNames[i].m_page == page) &&
1615  (CodepageAttrvalueNames[i].m_tag == tag))
1616  {
1617  break;
1618  }
1619 
1620  i++;
1621  }
1622 
1623  /* concatenate the value */
1624  if (CodepageAttrvalueNames[i].m_name)
1625  {
1626  if (*value)
1627  {
1628  *value = realloc(*value, strlen(*value) + strlen(CodepageAttrvalueNames[i].m_name) + 1);
1629  strcat(*value, CodepageAttrvalueNames[i].m_name);
1630  }
1631  else
1632  {
1633  *value = strdup(CodepageAttrvalueNames[i].m_name);
1634  }
1635  }
1636 }
1637 
1638 static const char* GetStringTableString(P_WBXML_NODE node, long index)
1639 {
1640  /* Find the string table node */
1641 
1642  P_WBXML_NODE pStringsNode = node;
1643 
1644  while (pStringsNode->m_parent)
1645  {
1646  pStringsNode = pStringsNode->m_parent;
1647  }
1648 
1649  while (pStringsNode->m_next)
1650  {
1651  pStringsNode = pStringsNode->m_next;
1652  }
1653 
1654  while (pStringsNode->m_prev && pStringsNode->m_type != NODE_STRING_TABLE)
1655  {
1656  pStringsNode = pStringsNode->m_prev;
1657  }
1658 
1659  if (pStringsNode->m_type != NODE_STRING_TABLE)
1660  {
1661  return "!!NO STRING TABLE!!";
1662  }
1663 
1664  /* Find the indexed string */
1665 
1666  if ((index >= 0) && (index < mb_u_int32_to_long(&((P_WBXML_STRING_TABLE)pStringsNode->m_data)->m_length)))
1667  {
1668  return (const char*) &(((P_WBXML_STRING_TABLE)pStringsNode->m_data)->m_strings[index]);
1669  }
1670  else
1671  {
1672  return "!!STRING TABLE INDEX TOO LARGE!!";
1673  }
1674 }
1675 
1676 static void DumpNode(P_WBXML_NODE node, int indent, BOOL *inattrs, BOOL hascontent, char** value)
1677 {
1678  P_WBXML_NODE curnode = node->m_child;
1679 
1680  WBXML_TAG nodetype = 0;
1681  long dtdnum = 0;
1682 
1683  BOOL bAttributesFollow = FALSE;
1684  BOOL bHasContent = FALSE;
1685 
1686  int i;
1687 
1688  if (!(*inattrs))
1689  {
1690  for (i=0; i<indent; i++)
1691  {
1692  printf(" ");
1693  }
1694  }
1695  else
1696  {
1697  if ((node->m_type != NODE_ATTRVALUE) && (*value))
1698  {
1699  printf("=\"");
1700  OutputEncodedString((unsigned char*) *value);
1701  printf("\"");
1702  free(*value);
1703  *value = NULL;
1704  }
1705  }
1706 
1707  switch (node->m_type)
1708  {
1709  case NODE_DTD_TYPE:
1710  printf("<?xml version=\"1.0\"?>\n<!DOCTYPE wml PUBLIC ");
1711 
1712  dtdnum = mb_u_int32_to_long( &((DTD_NODE_DATA*)node->m_data)->m_dtdnum );
1713  if ( dtdnum == 0)
1714  {
1715  printf("\"%s\">\n\n", GetStringTableString(node, mb_u_int32_to_long(&((DTD_NODE_DATA*)node->m_data)->m_index)) );
1716  }
1717  else
1718  {
1719  printf("\"%s\">\n\n", DTDTypeName(dtdnum) );
1720  }
1721  break;
1722 
1723  case NODE_CODEPAGE_TAG:
1724  nodetype = *((P_WBXML_TAG)node->m_data);
1725  if ((nodetype & CODEPAGE_TAG_MASK) == nodetype)
1726  {
1727  printf("<%s/>\n", CodepageTagName(node->m_page, nodetype));
1728  }
1729  else
1730  {
1732  {
1733  bHasContent = TRUE;
1734  }
1735 
1736  if ((nodetype & CODEPAGE_TAG_HAS_ATTRS) == CODEPAGE_TAG_HAS_ATTRS)
1737  {
1738  printf("<%s", CodepageTagName(node->m_page, nodetype));
1739  bAttributesFollow = TRUE;
1740  }
1741  else
1742  {
1743  printf("<%s>\n", CodepageTagName(node->m_page, nodetype));
1744  }
1745  }
1746  break;
1747 
1749  printf("<%s>\n", GetStringTableString(node, mb_u_int32_to_long(((P_WBXML_MB_U_INT32)node->m_data))) );
1750  break;
1751 
1752  case NODE_ATTRSTART:
1753  printf(" %s", CodepageAttrstartName(node->m_page, *((P_WBXML_TAG)node->m_data), value) );
1754  break;
1755 
1757  printf(" %s", GetStringTableString(node, mb_u_int32_to_long(((P_WBXML_MB_U_INT32)node->m_data))) );
1758  break;
1759 
1760  case NODE_ATTRVALUE:
1761  CodepageAttrvalueName(node->m_page, *((P_WBXML_TAG)node->m_data), value);
1762  break;
1763 
1764  case NODE_ATTREND:
1765  if (!hascontent)
1766  {
1767  printf("/");
1768  }
1769  printf(">\n");
1770  *inattrs = FALSE;
1771  break;
1772 
1773  case NODE_STRING:
1774  if (*inattrs)
1775  {
1776  /* concatenate the value */
1777  if (*value)
1778  {
1779  if (node->m_data)
1780  {
1781  *value = realloc(*value, strlen(*value) + strlen((char*) node->m_data) + 1);
1782  strcat(*value, (char*) node->m_data);
1783  }
1784  }
1785  else
1786  {
1787  if (node->m_data)
1788  {
1789  *value = strdup((char*) node->m_data);
1790  }
1791  }
1792  }
1793  else
1794  {
1795  OutputEncodedString((unsigned char*) node->m_data);
1796  printf("\n");
1797  }
1798  break;
1799 
1800  case NODE_VARIABLE_STRING:
1801  /* TODO: output variable string */
1802  break;
1803 
1804  case NODE_VARIABLE_INDEX:
1805  /* TODO: output variable string */
1806  break;
1807 
1808  default:
1809  break;
1810  }
1811 
1812  indent += INDENT_SIZE;
1813 
1814  if (curnode)
1815  {
1816  while (curnode->m_next) curnode = curnode->m_next;
1817 
1818  while (curnode)
1819  {
1820  DumpNode(curnode, indent, &bAttributesFollow, bHasContent, value);
1821  curnode = curnode->m_prev;
1822  }
1823  }
1824 
1825  indent -= INDENT_SIZE;
1826 
1827  /* Output the element end if we have one */
1829  {
1830  for (i=0; i<indent; i++)
1831  {
1832  printf(" ");
1833  }
1834 
1835  switch (node->m_type)
1836  {
1837  case NODE_CODEPAGE_TAG:
1838  printf("</%s>\n", CodepageTagName(node->m_page, *((P_WBXML_TAG)node->m_data)) );
1839  break;
1840 
1842  printf("</%s>\n", GetStringTableString(node, mb_u_int32_to_long(((P_WBXML_MB_U_INT32)node->m_data))) );
1843  break;
1844 
1845  default:
1846  break;
1847  }
1848  }
1849 }
1850 
1851 static void DumpNodes(P_WBXML_INFO buffer)
1852 {
1853  P_WBXML_NODE curnode = buffer->m_tree;
1854  BOOL bAttrsFollow = FALSE;
1855  char* value = NULL;
1856 
1857  if (curnode)
1858  {
1859  while (curnode->m_next) curnode = curnode->m_next;
1860 
1861  while (curnode)
1862  {
1863  DumpNode(curnode, 0, &bAttrsFollow, FALSE, &value);
1864  curnode = curnode->m_prev;
1865  }
1866  }
1867 }
1868 
1869 int main(int argc, char** argv)
1870 {
1871  WBXML_INFO buffer;
1872  FILE* file;
1873 
1874  if (argc < 2)
1875  {
1876  file = stdin;
1877  }
1878  else
1879  {
1880  file = fopen(argv[1], "r");
1881  if (!file)
1882  {
1884  }
1885  }
1886 
1887  Init(&buffer);
1888  ReadBinary(&buffer, file);
1889  Read_start(&buffer);
1890  DumpNodes(&buffer);
1891  Free(&buffer);
1892 
1893  return 0;
1894 }
WBXML_MB_U_INT32 m_length
Definition: decompile.h:201
static P_WBXML_NODE NewNode(P_WBXML_INFO buffer, WBXML_NODE_TYPE type)
Definition: decompile.c:320
void error(int err, const char *fmt,...)
Definition: log.c:648
#define TAG_OPAQUE
Definition: decompile.h:87
void * m_next
Definition: decompile.h:142
#define TAG_EXT_I_2
Definition: decompile.h:76
static const char * GetStringTableString(P_WBXML_NODE node, long index)
Definition: decompile.c:1638
WBXML_MB_U_INT32 * P_WBXML_MB_U_INT32
Definition: decompile.h:167
#define TAG_EXT_2
Definition: decompile.h:86
#define TAG_EXT_0
Definition: decompile.h:84
#define TAG_STR_T
Definition: decompile.h:82
BOOL IsCodepageTag(P_WBXML_INFO buffer, CP_TAG_TYPE type)
Definition: decompile.c:594
P_WBXML m_curpos
Definition: decompile.h:189
void Read_termstr_rtn(P_WBXML_INFO buffer, char **result)
Definition: decompile.c:1341
unsigned long WBXML_LENGTH
Definition: decompile.h:121
BOOL Is_tableref(P_WBXML_INFO buffer)
Definition: decompile.c:670
enum tagWBXML_PARSE_ERROR WBXML_PARSE_ERROR
unsigned char WBXML_CODEPAGE
Definition: decompile.h:119
unsigned char WBXML_TAG
Definition: decompile.h:116
WBXML_NODE * P_WBXML_NODE
Definition: decompile.h:151
WBXML_CODEPAGE m_page
Definition: decompile.h:238
static size_t BufferLength(P_WBXML_INFO buffer)
Definition: decompile.c:1435
#define TAG_EXT_T_0
Definition: decompile.h:79
CODEPAGE_TAG_NAME_LIST CodepageTagNames[]
Definition: decompile.c:101
void Read_entity(P_WBXML_INFO buffer)
Definition: decompile.c:1272
void Read_extension(P_WBXML_INFO buffer)
Definition: decompile.c:1146
BOOL Is_extension(P_WBXML_INFO buffer)
Definition: decompile.c:627
enum tagCP_TYPES CP_TAG_TYPE
P_WBXML_NODE m_tree
Definition: decompile.h:191
void Read_content(P_WBXML_INFO buffer)
Definition: decompile.c:1011
WBXML_BYTES * P_WBXML_BYTES
Definition: decompile.h:175
unsigned char WBXML_MB_U_INT32[MAX_MB_U_INT32_BYTES]
Definition: decompile.h:166
long mb_u_int32_to_long(P_WBXML_MB_U_INT32 value)
Definition: decompile.c:873
WBXML_VARIABLE_TYPE
Definition: decompile.h:153
WBXML_CODEPAGE m_page
Definition: decompile.h:146
void Read_index(P_WBXML_INFO buffer, P_WBXML_MB_U_INT32 result)
Definition: decompile.c:1398
int type
Definition: smsc_cimd2.c:215
WBXML_U_INT8 * P_WBXML_U_INT8
Definition: decompile.h:162
BOOL Is_zero(P_WBXML_INFO buffer)
Definition: decompile.c:690
static const char * CodepageAttrstartName(WBXML_CODEPAGE page, WBXML_TAG tag, char **value)
Definition: decompile.c:1563
BOOL Is_switchPage(P_WBXML_INFO buffer)
Definition: decompile.c:660
void * malloc(YYSIZE_T)
static const char * CodepageTagName(WBXML_CODEPAGE page, WBXML_TAG tag)
Definition: decompile.c:1540
void Read_pageindex(P_WBXML_INFO buffer, P_WBXML_U_INT8 result)
Definition: decompile.c:1420
void Read_publicid(P_WBXML_INFO buffer)
Definition: decompile.c:1314
#define realloc(p, n)
Definition: gwmem.h:193
static void AddDTDNode(P_WBXML_INFO buffer, const WBXML_DTD_TYPE dtdnum, const WBXML_MB_U_INT32 index)
Definition: decompile.c:407
void Read_length(P_WBXML_INFO buffer, P_WBXML_MB_U_INT32 result)
Definition: decompile.c:1403
FILE * file
Definition: log.c:169
WBXML_STRING_TABLE * P_WBXML_STRING_TABLE
Definition: decompile.h:206
BOOL Is_opaque(P_WBXML_INFO buffer)
Definition: decompile.c:685
#define TAG_EXT_T_1
Definition: decompile.h:80
void Read_switchPage(P_WBXML_INFO buffer)
Definition: decompile.c:1247
#define TAG_STR_I
Definition: decompile.h:72
static void DumpNode(P_WBXML_NODE node, int indent, BOOL *inattrs, BOOL hascontent, char **value)
Definition: decompile.c:1676
WBXML_CODEPAGE m_curpage
Definition: decompile.h:193
void Read_tableref(P_WBXML_INFO buffer)
Definition: decompile.c:1264
void Read_element(P_WBXML_INFO buffer)
Definition: decompile.c:968
void Read_mb_u_int32(P_WBXML_INFO buffer, P_WBXML_MB_U_INT32 result)
Definition: decompile.c:738
static void DumpNodes(P_WBXML_INFO buffer)
Definition: decompile.c:1851
static void AddAttrStartLiteralNode(P_WBXML_INFO buffer, WBXML_MB_U_INT32 index)
Definition: decompile.c:444
static void AddAttrStartNode(P_WBXML_INFO buffer, WBXML_TAG tag)
Definition: decompile.c:437
CODEPAGE_ATTRVALUE_NAME_LIST CodepageAttrvalueNames[]
Definition: decompile.c:262
#define STRING_BLOCK_SIZE
#define strdup(p)
Definition: gwmem.h:195
void free(void *)
CODEPAGE_ATTRSTART_NAME_LIST CodepageAttrstartNames[]
Definition: decompile.c:147
#define TAG_EXT_I_0
Definition: decompile.h:74
#define CODEPAGE_TAG_MASK
Definition: decompile.h:91
#define SWITCHPAGE_SIZE
Definition: decompile.h:96
void * m_prev
Definition: decompile.h:141
static const char * DTDTypeName(long dtdnum)
Definition: decompile.c:1522
BOOL Is_attrValue(P_WBXML_INFO buffer)
Definition: decompile.c:612
#define INDENT_SIZE
Definition: decompile.c:75
void Read_attribute(P_WBXML_INFO buffer)
Definition: decompile.c:1067
static void AddVariableStringNode(P_WBXML_INFO buffer, char *string, WBXML_VARIABLE_TYPE type)
Definition: decompile.c:470
WBXML_LENGTH m_length
Definition: decompile.h:190
unsigned char WBXML_U_INT8
Definition: decompile.h:161
DTD_TYPE_LIST DTDTypeList[]
Definition: decompile.c:77
#define TAG_LITERAL
Definition: decompile.h:73
BOOL Is_pi(P_WBXML_INFO buffer)
Definition: decompile.c:680
void Read_u_int8(P_WBXML_INFO buffer, P_WBXML_U_INT8 result)
Definition: decompile.c:718
void Read_version(P_WBXML_INFO buffer)
Definition: decompile.c:1307
#define CODEPAGE_TAG_HAS_CONTENT
Definition: decompile.h:92
#define MAX_MB_U_INT32_BYTES
Definition: decompile.h:164
P_WBXML_NODE m_curnode
Definition: decompile.h:192
void ParseError(WBXML_PARSE_ERROR error)
Definition: decompile.c:490
void Read_entcode(P_WBXML_INFO buffer)
Definition: decompile.c:1278
void ParseWarning(WBXML_PARSE_WARNING warning)
Definition: decompile.c:526
void warning(int err, const char *fmt,...)
Definition: log.c:660
WBXML * P_WBXML
Definition: decompile.h:113
BOOL Is_string(P_WBXML_INFO buffer)
Definition: decompile.c:654
WBXML_MB_U_INT32 WBXML_DTD_TYPE
Definition: decompile.h:177
static void AddVariableIndexNode(P_WBXML_INFO buffer, char *string, WBXML_VARIABLE_TYPE type)
Definition: decompile.c:475
void Read_attrStart(P_WBXML_INFO buffer)
Definition: decompile.c:1077
void Read_bytes(P_WBXML_INFO buffer, WBXML_LENGTH length, P_WBXML_BYTES result)
Definition: decompile.c:765
enum tagWBXML_PARSE_WARNING WBXML_PARSE_WARNING
#define TAG_EXT_T_2
Definition: decompile.h:81
WBXML_LENGTH BytesLeft(P_WBXML_INFO buffer)
Definition: decompile.c:548
static void FreeNode(P_WBXML_NODE node)
Definition: decompile.c:389
WBXML_TAG * P_WBXML_TAG
Definition: decompile.h:117
static void OutputEncodedString(const unsigned char *str)
Definition: decompile.c:897
static void AddCodepageLiteralTagNode(P_WBXML_INFO buffer, WBXML_MB_U_INT32 index)
Definition: decompile.c:430
static void ReadBinary(P_WBXML_INFO buffer, FILE *file)
Definition: decompile.c:1473
void Read_pi(P_WBXML_INFO buffer)
Definition: decompile.c:1284
WBXML_NODE_TYPE
Definition: decompile.h:123
BOOL Is_entity(P_WBXML_INFO buffer)
Definition: decompile.c:675
void Read_strtbl(P_WBXML_INFO buffer)
Definition: decompile.c:944
int BOOL
Definition: decompile.h:108
static void CodepageAttrvalueName(WBXML_CODEPAGE page, WBXML_TAG tag, char **value)
Definition: decompile.c:1600
static void AddAttrValueNode(P_WBXML_INFO buffer, WBXML_TAG tag)
Definition: decompile.c:451
unsigned char * WBXML_BYTES
Definition: decompile.h:174
void Read_termstr(P_WBXML_INFO buffer)
Definition: decompile.c:1387
void Message(char *msg)
Definition: decompile.c:485
P_WBXML m_start
Definition: decompile.h:188
void Read_start(P_WBXML_INFO buffer)
Definition: decompile.c:935
#define FALSE
Definition: decompile.h:109
long dtd_id
Definition: decompile.c:73
static void AddStringTableNode(P_WBXML_INFO buffer, const P_WBXML_STRING_TABLE strings)
Definition: decompile.c:416
#define TAG_PI
Definition: decompile.h:77
void * m_child
Definition: decompile.h:143
void Read_charset(P_WBXML_INFO buffer)
Definition: decompile.c:1334
#define TAG_EXT_1
Definition: decompile.h:85
static long FileSize(FILE *file)
Definition: decompile.c:1462
WBXML_NODE_TYPE m_type
Definition: decompile.h:145
#define TAG_END
Definition: decompile.h:70
void Read_opaque(P_WBXML_INFO buffer)
Definition: decompile.c:1297
static void Free(P_WBXML_INFO buffer)
Definition: decompile.c:1447
static void Init(P_WBXML_INFO buffer)
Definition: decompile.c:1425
void Read_string(P_WBXML_INFO buffer)
Definition: decompile.c:1231
static void AddAttrEndNode(P_WBXML_INFO buffer)
Definition: decompile.c:458
BOOL Is_inline(P_WBXML_INFO buffer)
Definition: decompile.c:665
#define TAG_EXT_I_1
Definition: decompile.h:75
int main(int argc, char **argv)
Definition: decompile.c:1869
void * m_data
Definition: decompile.h:147
const WBXML_MB_U_INT32 ZERO_WBXML_MB_U_INT32
Definition: decompile.c:72
BOOL IsTag(P_WBXML_INFO buffer, WBXML_TAG tag)
Definition: decompile.c:570
static void AddStringNode(P_WBXML_INFO buffer, char *string)
Definition: decompile.c:464
#define TRUE
Definition: decompile.h:110
#define TAG_SWITCH_PAGE
Definition: decompile.h:69
void ReadFixedTag(P_WBXML_INFO buffer, WBXML_TAG tag)
Definition: decompile.c:786
WBXML_BYTES m_strings
Definition: decompile.h:202
WBXML_TAG Read_stag(P_WBXML_INFO buffer)
Definition: decompile.c:1040
void * m_parent
Definition: decompile.h:144
static void AddCodepageTagNode(P_WBXML_INFO buffer, WBXML_TAG tag)
Definition: decompile.c:423
static XMLRPCDocument * msg
Definition: test_xmlrpc.c:86
void Read_attrValue(P_WBXML_INFO buffer)
Definition: decompile.c:1109
void Read_inline(P_WBXML_INFO buffer)
Definition: decompile.c:1258
void Read_zero(P_WBXML_INFO buffer)
Definition: decompile.c:1408
void Read_body(P_WBXML_INFO buffer)
Definition: decompile.c:953
WBXML_TAG ReadCodepageTag(P_WBXML_INFO buffer, CP_TAG_TYPE type)
Definition: decompile.c:812
#define CODEPAGE_TAG_HAS_ATTRS
Definition: decompile.h:93
#define TAG_ENTITY
Definition: decompile.h:71
See file LICENSE for details about the license agreement for using, modifying, copying or deriving work from this software.