Home | History | Annotate | Download | only in src
      1 /*************************************************************************/
      2 /* module:          Definition of WBXML/XML tags for the en-/decoder     */
      3 /* file:            XLTTags.c                                            */
      4 /* target system:   all                                                  */
      5 /* target OS:       all                                                  */
      6 /*************************************************************************/
      7 
      8 /*
      9  * Copyright Notice
     10  * Copyright (c) Ericsson, IBM, Lotus, Matsushita Communication
     11  * Industrial Co., Ltd., Motorola, Nokia, Openwave Systems, Inc.,
     12  * Palm, Inc., Psion, Starfish Software, Symbian, Ltd. (2001).
     13  * All Rights Reserved.
     14  * Implementation of all or part of any Specification may require
     15  * licenses under third party intellectual property rights,
     16  * including without limitation, patent rights (such a third party
     17  * may or may not be a Supporter). The Sponsors of the Specification
     18  * are not responsible and shall not be held responsible in any
     19  * manner for identifying or failing to identify any or all such
     20  * third party intellectual property rights.
     21  *
     22  * THIS DOCUMENT AND THE INFORMATION CONTAINED HEREIN ARE PROVIDED
     23  * ON AN "AS IS" BASIS WITHOUT WARRANTY OF ANY KIND AND ERICSSON, IBM,
     24  * LOTUS, MATSUSHITA COMMUNICATION INDUSTRIAL CO. LTD, MOTOROLA,
     25  * NOKIA, PALM INC., PSION, STARFISH SOFTWARE AND ALL OTHER SYNCML
     26  * SPONSORS DISCLAIM ALL WARRANTIES, EXPRESS OR IMPLIED, INCLUDING
     27  * BUT NOT LIMITED TO ANY WARRANTY THAT THE USE OF THE INFORMATION
     28  * HEREIN WILL NOT INFRINGE ANY RIGHTS OR ANY IMPLIED WARRANTIES OF
     29  * MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. IN NO EVENT
     30  * SHALL ERICSSON, IBM, LOTUS, MATSUSHITA COMMUNICATION INDUSTRIAL CO.,
     31  * LTD, MOTOROLA, NOKIA, PALM INC., PSION, STARFISH SOFTWARE OR ANY
     32  * OTHER SYNCML SPONSOR BE LIABLE TO ANY PARTY FOR ANY LOSS OF
     33  * PROFITS, LOSS OF BUSINESS, LOSS OF USE OF DATA, INTERRUPTION OF
     34  * BUSINESS, OR FOR DIRECT, INDIRECT, SPECIAL OR EXEMPLARY, INCIDENTAL,
     35  * PUNITIVE OR CONSEQUENTIAL DAMAGES OF ANY KIND IN CONNECTION WITH
     36  * THIS DOCUMENT OR THE INFORMATION CONTAINED HEREIN, EVEN IF ADVISED
     37  * OF THE POSSIBILITY OF SUCH LOSS OR DAMAGE.
     38  *
     39  * The above notice and this paragraph must be included on all copies
     40  * of this document that are made.
     41  *
     42  */
     43 
     44 
     45 #include "xlttags.h"
     46 
     47 #include <libstr.h>
     48 #include <smlerr.h>
     49 #include <libmem.h>
     50 #include <libutil.h>
     51 #include <mgr.h>
     52 
     53 #include "xltmetinf.h"
     54 #include "xltdevinf.h"
     55 #include "xlttagtbl.h"
     56 
     57 
     58 // %%% luz:2003-07-31: added SyncML namespace tables
     59 const char * const SyncMLNamespaces[SML_NUM_VERS] = {
     60   "???",
     61   "SYNCML:SYNCML1.0",
     62   "SYNCML:SYNCML1.1",
     63   "SYNCML:SYNCML1.2"
     64 };
     65 
     66 /* local prototypes */
     67 #ifdef NOWSM
     68 const // without WSM, the tag table is a global read-only constant
     69 #endif
     70 TagPtr_t getTagTable(SmlPcdataExtension_t ext);
     71 
     72 //SmlPcdataExtension_t   getByName(String_t ns);
     73 void freeDtdTable(DtdPtr_t tbl);
     74 
     75 #ifdef NOWSM
     76 const // without WSM, the DTD table is a global read-only constant
     77 #endif
     78 DtdPtr_t getDtdTable();
     79 
     80 
     81 // free table obtained with getDtdTable()
     82 void freeDtdTable(DtdPtr_t tbl)
     83 {
     84   #ifndef NOWSM
     85   // only with WSM this is an allocated table
     86   smlLibFree(tbl);
     87   #endif
     88 }
     89 
     90 /**
     91  * FUNCTION: getDtdTable
     92  *
     93  * Returns a copy of the table containing all known (sub) dtd's
     94  * On error a NULL pointer is returned
     95  */
     96 #ifdef NOWSM
     97 const // without WSM, the DTD table is a global read-only constant
     98 #endif
     99 DtdPtr_t getDtdTable() {
    100   #ifdef NOWSM
    101   // NOWSM method, table is const, just return a pointer
    102 	static const Dtd_t XltDtdTbl[] = {
    103 		{ "SYNCML:SYNCML1.0", SML_EXT_UNDEFINED}, // %%% note that this is the default, will be override by syncml version specific string from
    104 		{ "syncml:metinf",    SML_EXT_METINF},
    105     { "syncml:devinf",    SML_EXT_DEVINF},
    106     { "syncml:dmddf1.2",    SML_EXT_DMTND},
    107 		{ NULL,               SML_EXT_LAST}
    108 	};
    109 	return (DtdPtr_t)XltDtdTbl;
    110   #else
    111   // WSM method wasting a lot of memory
    112 	DtdPtr_t _tmpPtr;
    113 
    114 	Dtd_t XltDtdTbl[] = {
    115 		{ "SYNCML:SYNCML1.0", SML_EXT_UNDEFINED},
    116 		{ "syncml:metinf",    SML_EXT_METINF},
    117     { "syncml:devinf",    SML_EXT_DEVINF},
    118     { "syncml:dmddf1.2",    SML_EXT_DMTND},
    119 		{ NULL,               SML_EXT_LAST}
    120 	};
    121 	_tmpPtr = NULL;
    122 	_tmpPtr = (DtdPtr_t)smlLibMalloc(sizeof(XltDtdTbl));
    123 	if (_tmpPtr == NULL) return NULL;
    124 	smlLibMemcpy(_tmpPtr, &XltDtdTbl, sizeof(XltDtdTbl));
    125 	return _tmpPtr;
    126 	#endif
    127 }
    128 
    129 
    130 /**
    131  * FUNCTION: getExtName
    132  *
    133  * Returns the official name for a given extention/sub-DTD
    134  * and stored it in 'name'. If not found name isn't modified
    135  */
    136 // %%% luz:2003-04-24: added syncmlvers parameter
    137 // %%% luz:2003-07-31: changed to vers enum
    138 Ret_t getExtName(SmlPcdataExtension_t ext, String_t *name, SmlVersion_t vers) {
    139 	DtdPtr_t dtdhead = getDtdTable();
    140 	DtdPtr_t dtd = dtdhead;
    141 	const char *dtdname;
    142 	if (!dtdhead) return -1;
    143 	for (;dtd->ext != SML_EXT_LAST; dtd++) {
    144 		if (!dtd->name) continue; /* skip empty names (should not appear but better be on the safe side) */
    145 		if (dtd->ext == ext) {
    146 		  String_t _tmp;
    147 		  // this is the default
    148 		  dtdname=dtd->name;
    149 		  // %%% luz:2003-04-24: added dynamic generation of namespace according to SyncML version
    150 		  if (ext==SML_EXT_UNDEFINED && vers!=SML_VERS_UNDEF) {
    151 		    // this requests SyncML namespace
    152                     if (vers >= SML_NUM_VERS )
    153                     {
    154                        return SML_ERR_INVALID_SIZE;
    155                     }
    156 		    dtdname=SyncMLNamespaces[vers];
    157 		  }
    158 			_tmp = smlLibMalloc(smlLibStrlen(dtdname)+1);
    159 			if (!_tmp) {
    160 				freeDtdTable(dtdhead);
    161 				return SML_ERR_NOT_ENOUGH_SPACE;
    162 			}
    163 			smlLibStrcpy(_tmp, dtdname);
    164 			freeDtdTable(dtdhead);
    165 			*name = _tmp;
    166 			return SML_ERR_OK;
    167 		}
    168 	}
    169 	freeDtdTable(dtdhead);
    170 	return -1;
    171 }
    172 
    173 /**
    174  * FUNCTION: getCpByName
    175  *
    176  * Returns the codepage constant assoziated with the name stored in 'ns'
    177  *
    178  * RETURN:             a SmlPcdataExtension_t representing the corresponding codepage id.
    179  *                     If no corresponding codepage is found -1 is returned.
    180  */
    181 SmlPcdataExtension_t getExtByName(String_t ns) {
    182 	DtdPtr_t dtdhead = getDtdTable();
    183 	DtdPtr_t dtd = dtdhead;
    184 	SmlPcdataExtension_t ext = (SmlPcdataExtension_t) 255;
    185 	if (!dtdhead) return SML_EXT_UNDEFINED;
    186 	for (;dtd->ext != SML_EXT_LAST; dtd++) {
    187 	  const char *dtdname=dtd->name;
    188 		if (!dtdname) continue; /* skip empty names (should not appear but better be on the safe side) */
    189 		if (dtd->ext==SML_EXT_UNDEFINED && smlLibStrncmp("SYNCML:SYNCML",ns,13)==0) {
    190 		  // SyncML namespace is ok without checking version!
    191 			ext = SML_EXT_UNDEFINED;
    192 			break;
    193 		}
    194 		else if (smlLibStrcmp(dtdname,ns) == 0) {
    195 			ext = dtd->ext;
    196 			break;
    197 		}
    198 	}
    199 	freeDtdTable(dtdhead);
    200 	return ext;
    201 }
    202 
    203 
    204 
    205 /* if the commands are not defined we let the functions point to NULL */
    206 #ifndef RESULT_RECEIVE
    207 #define buildResults NULL
    208 #endif
    209 
    210 #ifndef MAP_RECEIVE
    211 #define buildMap NULL
    212 #endif
    213 
    214 #ifndef EXEC_RECEIVE
    215 #define buildExec NULL
    216 #endif
    217 
    218 #if !defined(ATOM_RECEIVE) && !defined(SEQUENCE_RECEIVE)
    219 #define buildAtomOrSeq NULL
    220 #endif
    221 
    222 #ifndef SEARCH_RECEIVE
    223 #define buildSearch NULL
    224 #endif
    225 
    226 
    227 /**
    228  * FUNCTION: getTagTable
    229  *
    230  * Returns the tag table - this function is used to avoid a global
    231  * tag table variable
    232  *
    233  * RETURN:             a pointer to the tag table containing tag ids,
    234  *                     codepages, wbxml tags and xml tags
    235  */
    236 /* T.K. initialized the structure via _TOKEN Macro, to take
    237  * out the XML name tags when not compiled with XML support.
    238  * In addtion removed the (unused) pointer for the build functions
    239  */
    240 #ifdef __SML_XML__
    241 #define _TOKEN(id, wbxml, xml) (id), (wbxml), (xml)
    242 #else
    243 #define _TOKEN(id, wbxml, xml) (id), (wbxml), ""
    244 #endif
    245 
    246 #ifdef NOWSM
    247 const // without WSM, the tag table is a global read-only constant
    248 #endif
    249 TagPtr_t getTagTable(SmlPcdataExtension_t ext)
    250 {
    251   #ifndef NOWSM
    252   int mySize = 0;
    253   TagPtr_t _tmpTagPtr;
    254   SyncMLInfoPtr_t pGA = NULL;
    255   #else
    256   TagPtr_t _tmpTagPtr=NULL;
    257   #endif
    258   /* standard SyncML codepage */
    259   static const Tag_t syncml[] =
    260   {
    261     { _TOKEN(TN_ADD,            0x05,    "Add")},
    262     { _TOKEN(TN_ALERT,          0x06,    "Alert")},
    263     { _TOKEN(TN_ARCHIVE,        0x07,    "Archive")},
    264     { _TOKEN(TN_ATOMIC,         0x08,    "Atomic")},
    265     { _TOKEN(TN_CHAL,           0x09,    "Chal")},
    266     { _TOKEN(TN_CMD,            0x0A,    "Cmd")},
    267     { _TOKEN(TN_CMDID,          0x0B,    "CmdID")},
    268     { _TOKEN(TN_CMDREF,         0x0C,    "CmdRef")},
    269     { _TOKEN(TN_COPY,           0x0D,    "Copy")},
    270     { _TOKEN(TN_CRED,           0x0E,    "Cred")},
    271     { _TOKEN(TN_DATA,           0x0F,    "Data")},
    272     { _TOKEN(TN_DELETE,         0x10,    "Delete")},
    273     { _TOKEN(TN_EXEC,           0x11,    "Exec")},
    274     { _TOKEN(TN_FINAL,          0x12,    "Final")},
    275     { _TOKEN(TN_GET,            0x13,    "Get")},
    276     { _TOKEN(TN_ITEM,           0x14,    "Item")},
    277     { _TOKEN(TN_LANG,           0x15,    "Lang")},
    278     { _TOKEN(TN_LOCNAME,        0x16,    "LocName")},
    279     { _TOKEN(TN_LOCURI,         0x17,    "LocURI")},
    280     { _TOKEN(TN_MAP,            0x18,    "Map")},
    281     { _TOKEN(TN_MAPITEM,        0x19,    "MapItem")},
    282     { _TOKEN(TN_META,           0x1A,    "Meta")},
    283     { _TOKEN(TN_MSGID,          0x1B,    "MsgID")},
    284     { _TOKEN(TN_MSGREF,         0x1C,    "MsgRef")},
    285     { _TOKEN(TN_NORESP,         0x1D,    "NoResp")},
    286     { _TOKEN(TN_NORESULTS,      0x1E,    "NoResults")},
    287     { _TOKEN(TN_PUT,            0x1F,    "Put")},
    288     { _TOKEN(TN_REPLACE,        0x20,    "Replace")},
    289     { _TOKEN(TN_RESPURI,        0x21,    "RespURI")},
    290     { _TOKEN(TN_RESULTS,        0x22,    "Results")},
    291     { _TOKEN(TN_SEARCH,         0x23,    "Search")},
    292     { _TOKEN(TN_SEQUENCE,       0x24,    "Sequence")},
    293     { _TOKEN(TN_SESSIONID,      0x25,    "SessionID")},
    294     { _TOKEN(TN_SFTDEL,         0x26,    "SftDel")},
    295     { _TOKEN(TN_SOURCE,         0x27,    "Source")},
    296     { _TOKEN(TN_SOURCEREF,      0x28,    "SourceRef")},
    297     { _TOKEN(TN_STATUS,         0x29,    "Status")},
    298     { _TOKEN(TN_SYNC,           0x2A,    "Sync")},
    299     { _TOKEN(TN_SYNCBODY,       0x2B,    "SyncBody")},
    300     { _TOKEN(TN_SYNCHDR,        0x2C,    "SyncHdr")},
    301     { _TOKEN(TN_SYNCML,         0x2D,    "SyncML")},
    302     { _TOKEN(TN_TARGET,         0x2E,    "Target")},
    303     { _TOKEN(TN_TARGETREF,      0x2F,    "TargetRef")},
    304     { _TOKEN(TN_VERSION,        0x31,    "VerDTD")},
    305     { _TOKEN(TN_PROTO,          0x32,    "VerProto")},
    306     { _TOKEN(TN_NUMBEROFCHANGES,0x33,    "NumberOfChanges")},
    307 		{ _TOKEN(TN_MOREDATA,       0x34,    "MoreData")},
    308 	/* from version 1.2 */
    309     { _TOKEN(TN_CORRELATOR,          0x3C,    "Correlator")},
    310 
    311     { _TOKEN(TN_UNDEF,          0x00,    NULL)}
    312   };
    313 
    314   #ifdef __USE_METINF__
    315 	static const Tag_t metinf[] =  {
    316     { _TOKEN(TN_METINF_ANCHOR,      0x05,	"Anchor")},
    317     { _TOKEN(TN_METINF_EMI,		      0x06,   "EMI")},
    318     { _TOKEN(TN_METINF_FORMAT,		  0x07,	"Format")},
    319     { _TOKEN(TN_METINF_FREEID,		  0x08,	"FreeID")},
    320     { _TOKEN(TN_METINF_FREEMEM,	    0x09,	"FreeMem")},
    321     { _TOKEN(TN_METINF_LAST,     	  0x0A,	"Last")},
    322     { _TOKEN(TN_METINF_MARK,		    0x0B,	"Mark")},
    323     { _TOKEN(TN_METINF_MAXMSGSIZE,  0x0C,	"MaxMsgSize")},
    324     { _TOKEN(TN_METINF_MEM,		      0x0D,	"Mem")},
    325     { _TOKEN(TN_METINF_METINF,		  0x0E,	"MetInf")},
    326     { _TOKEN(TN_METINF_NEXT,		    0x0F,	"Next")},
    327     { _TOKEN(TN_METINF_NEXTNONCE,	  0x10,	"NextNonce")},
    328     { _TOKEN(TN_METINF_SHAREDMEM,	  0x11,	"SharedMem")},
    329     { _TOKEN(TN_METINF_SIZE,		    0x12,	"Size")},
    330     { _TOKEN(TN_METINF_TYPE,		    0x13,	"Type")},
    331     { _TOKEN(TN_METINF_VERSION,	    0x14,	"Version")},
    332 		/* SCTSTK - 18/03/2002, S.H. 2002-04-05 : SyncML 1.1 */
    333     { _TOKEN(TN_METINF_MAXOBJSIZE,	0x15,	"MaxObjSize")},
    334     { _TOKEN(TN_UNDEF,				      0x00,	NULL)}
    335 	};
    336   #endif
    337 
    338 
    339   #ifdef __USE_DEVINF__
    340   static const Tag_t devinf[] = {
    341     {_TOKEN(TN_DEVINF_CTCAP,       0x05,   "CTCap")},
    342     {_TOKEN(TN_DEVINF_CTTYPE,      0x06,   "CTType")},
    343     {_TOKEN(TN_DEVINF_DATASTORE,   0x07,   "DataStore")},
    344     {_TOKEN(TN_DEVINF_DATATYPE,    0x08,   "DataType")},
    345     {_TOKEN(TN_DEVINF_DEVID,       0x09,   "DevID")},
    346     {_TOKEN(TN_DEVINF_DEVINF,      0x0A,   "DevInf")},
    347     {_TOKEN(TN_DEVINF_DEVTYP,      0x0B,   "DevTyp")},
    348     {_TOKEN(TN_DEVINF_DISPLAYNAME, 0x0C,   "DisplayName")},
    349     {_TOKEN(TN_DEVINF_DSMEM,       0x0D,   "DSMem")},
    350     {_TOKEN(TN_DEVINF_EXT,         0x0E,   "Ext")},
    351     {_TOKEN(TN_DEVINF_FWV,         0x0F,   "FwV")},
    352     {_TOKEN(TN_DEVINF_HWV,         0x10,   "HwV")},
    353     {_TOKEN(TN_DEVINF_MAN,         0x11,   "Man")},
    354     {_TOKEN(TN_DEVINF_MAXGUIDSIZE, 0x12,   "MaxGUIDSize")},
    355     {_TOKEN(TN_DEVINF_MAXID,       0x13,   "MaxID")},
    356     {_TOKEN(TN_DEVINF_MAXMEM,      0x14,   "MaxMem")},
    357     {_TOKEN(TN_DEVINF_MOD,         0x15,   "Mod")},
    358     {_TOKEN(TN_DEVINF_OEM,         0x16,   "OEM")},
    359     {_TOKEN(TN_DEVINF_PARAMNAME,   0x17,   "ParamName")},
    360     {_TOKEN(TN_DEVINF_PROPNAME,    0x18,   "PropName")},
    361     {_TOKEN(TN_DEVINF_RX,          0x19,   "Rx")},
    362     {_TOKEN(TN_DEVINF_RXPREF,      0x1A,   "Rx-Pref")},
    363     {_TOKEN(TN_DEVINF_SHAREDMEM,   0x1B,   "SharedMem")},
    364     {_TOKEN(TN_DEVINF_SIZE,        0x1C,   "Size")},
    365     {_TOKEN(TN_DEVINF_SOURCEREF,   0x1D,   "SourceRef")},
    366     {_TOKEN(TN_DEVINF_SWV,         0x1E,   "SwV")},
    367     {_TOKEN(TN_DEVINF_SYNCCAP,     0x1F,   "SyncCap")},
    368     {_TOKEN(TN_DEVINF_SYNCTYPE,    0x20,   "SyncType")},
    369     {_TOKEN(TN_DEVINF_TX,          0x21,   "Tx")},
    370     {_TOKEN(TN_DEVINF_TXPREF,      0x22,   "Tx-Pref")},
    371     {_TOKEN(TN_DEVINF_VALENUM,     0x23,   "ValEnum")},
    372     {_TOKEN(TN_DEVINF_VERCT,       0x24,   "VerCT")},
    373     {_TOKEN(TN_DEVINF_VERDTD,      0x25,   "VerDTD")},
    374     {_TOKEN(TN_DEVINF_XNAM,        0x26,   "XNam")},
    375     {_TOKEN(TN_DEVINF_XVAL,        0x27,   "XVal")},
    376     // %%% luz:2003-04-28 : added these, they were missing
    377     {_TOKEN(TN_DEVINF_UTC,         0x28,   "UTC")},
    378     {_TOKEN(TN_DEVINF_NOFM,        0x29,   "SupportNumberOfChanges")},
    379     {_TOKEN(TN_DEVINF_LARGEOBJECT, 0x2A,   "SupportLargeObjs")},
    380     // %%% end luz
    381     { _TOKEN(TN_UNDEF,			       0x00,	NULL)}
    382   };
    383   #endif
    384 
    385   #ifdef __USE_DMTND__
    386   static const Tag_t dmtnd[] =  {
    387     { _TOKEN(TN_DMTND_AccessType,   0x05,     "AccessType")},
    388     { _TOKEN(TN_DMTND_ACL,          0x06,     "ACL")},
    389     { _TOKEN(TN_DMTND_Add,          0x07,     "Add")},
    390     { _TOKEN(TN_DMTND_b64,          0x08,     "b64")},
    391     { _TOKEN(TN_DMTND_bin,          0x09,     "bin")},
    392     { _TOKEN(TN_DMTND_bool,         0x0A,     "bool")},
    393     { _TOKEN(TN_DMTND_chr,          0x0B,     "chr")},
    394     { _TOKEN(TN_DMTND_CaseSense,    0x0C,     "CaseSense")},
    395     { _TOKEN(TN_DMTND_CIS,          0x0D,     "CIS")},
    396     { _TOKEN(TN_DMTND_Copy,         0x0E,     "Copy")},
    397     { _TOKEN(TN_DMTND_CS,           0x0F,     "CS")},
    398     { _TOKEN(TN_DMTND_date,         0x10,     "date")},
    399     { _TOKEN(TN_DMTND_DDFName,      0x11,     "DDFName")},
    400     { _TOKEN(TN_DMTND_DefaultValue, 0x12,     "DefaultValue")},
    401     { _TOKEN(TN_DMTND_Delete,       0x13,     "Delete")},
    402     { _TOKEN(TN_DMTND_Description,  0x14,     "Description")},
    403     { _TOKEN(TN_DMTND_DFFormat,     0x15,     "DFFormat")},
    404     { _TOKEN(TN_DMTND_DFProperties, 0x16,     "DFProperties")},
    405     { _TOKEN(TN_DMTND_DFTitle,      0x17,     "DFTitle")},
    406     { _TOKEN(TN_DMTND_DFType,       0x18,     "DFType")},
    407     { _TOKEN(TN_DMTND_Dynamic,      0x19,     "Dynamic")},
    408     { _TOKEN(TN_DMTND_Exec,         0x1A,     "Exec")},
    409     { _TOKEN(TN_DMTND_float,        0x1B,     "float")},
    410     { _TOKEN(TN_DMTND_Format,       0x1C,     "Format")},
    411     { _TOKEN(TN_DMTND_Get,          0x1D,     "Get")},
    412     { _TOKEN(TN_DMTND_int,          0x1E,     "int")},
    413     { _TOKEN(TN_DMTND_Man,          0x1F,     "Man")},
    414     { _TOKEN(TN_DMTND_MgmtTree,     0x20,     "MgmtTree")},
    415     { _TOKEN(TN_DMTND_MIME,         0x21,     "MIME")},
    416     { _TOKEN(TN_DMTND_Mod,          0x22,     "Mod")},
    417     { _TOKEN(TN_DMTND_Name,         0x23,     "Name")},
    418     { _TOKEN(TN_DMTND_Node,         0x24,     "Node")},
    419     { _TOKEN(TN_DMTND_node,         0x25,     "node")},
    420     { _TOKEN(TN_DMTND_NodeName,     0x26,     "NodeName")},
    421     { _TOKEN(TN_DMTND_null,         0x27,     "null")},
    422     { _TOKEN(TN_DMTND_Occurrence,   0x28,     "Occurrence")},
    423     { _TOKEN(TN_DMTND_One,          0x29,     "One")},
    424     { _TOKEN(TN_DMTND_OneOrMore,    0x2A,     "OneOrMore")},
    425     { _TOKEN(TN_DMTND_OneOrN,       0x2B,     "OneOrN")},
    426     { _TOKEN(TN_DMTND_Path,         0x2C,     "Path")},
    427     { _TOKEN(TN_DMTND_Permanent,    0x2D,     "Permanent")},
    428     { _TOKEN(TN_DMTND_Replace,      0x2E,     "Replace")},
    429     { _TOKEN(TN_DMTND_RTProperties, 0x2F,     "RTProperties")},
    430     { _TOKEN(TN_DMTND_Scope,        0x30,     "Scope")},
    431     { _TOKEN(TN_DMTND_Size,         0x31,     "Size")},
    432     { _TOKEN(TN_DMTND_time,         0x32,     "time")},
    433     { _TOKEN(TN_DMTND_Title,        0x33,     "Title")},
    434     { _TOKEN(TN_DMTND_TStamp,       0x34,     "TStamp")},
    435     { _TOKEN(TN_DMTND_Type,         0x35,     "Type")},
    436     { _TOKEN(TN_DMTND_Value,        0x36,     "Value")},
    437     { _TOKEN(TN_DMTND_VerDTD,       0x37,     "VerDTD")},
    438     { _TOKEN(TN_DMTND_VerNo,        0x38,     "VerNo")},
    439     { _TOKEN(TN_DMTND_xml,          0x39,     "xml")},
    440     { _TOKEN(TN_DMTND_ZeroOrMore,   0x3A,     "ZeroOrMore")},
    441     { _TOKEN(TN_DMTND_ZeroOrN,      0x3B,     "ZeroOrN")},
    442     { _TOKEN(TN_DMTND_ZeroOrOne,    0x3C,     "ZeroOrOne") }
    443   };
    444   #endif
    445 
    446   #ifndef NOWSM
    447   _tmpTagPtr = NULL;
    448   pGA = mgrGetSyncMLAnchor();
    449   if (pGA == NULL) return NULL;
    450   #endif
    451 
    452   /* get the correct codepage */
    453   if (ext == SML_EXT_UNDEFINED) {
    454     #ifndef NOWSM
    455     _tmpTagPtr = pGA->tokTbl->SyncML;
    456     if (_tmpTagPtr == NULL) {
    457 		  mySize = sizeof(syncml);
    458 		  pGA->tokTbl->SyncML = (TagPtr_t)smlLibMalloc(mySize);
    459 		  if (pGA->tokTbl->SyncML == NULL) return NULL;
    460 		  smlLibMemcpy(pGA->tokTbl->SyncML, &syncml, mySize);
    461       _tmpTagPtr = pGA->tokTbl->SyncML;
    462     }
    463     #else
    464     _tmpTagPtr=(TagPtr_t)syncml;
    465     #endif
    466   }
    467 
    468   #ifdef __USE_METINF__
    469 	else if (ext == SML_EXT_METINF) {
    470     #ifndef NOWSM
    471     _tmpTagPtr = pGA->tokTbl->MetInf;
    472     if (_tmpTagPtr == NULL) {
    473 		  mySize = sizeof(metinf);
    474 		  pGA->tokTbl->MetInf = (TagPtr_t)smlLibMalloc(mySize);
    475 		  if (pGA->tokTbl->MetInf == NULL) return NULL;
    476 		  smlLibMemcpy(pGA->tokTbl->MetInf, &metinf, mySize);
    477       _tmpTagPtr = pGA->tokTbl->MetInf;
    478     }
    479     #else
    480     _tmpTagPtr=(TagPtr_t)metinf;
    481     #endif
    482   }
    483   #endif
    484 
    485   #ifdef __USE_DEVINF__
    486 	else if (ext == SML_EXT_DEVINF) {
    487     #ifndef NOWSM
    488     _tmpTagPtr = pGA->tokTbl->DevInf;
    489     if (_tmpTagPtr == NULL) {
    490   		mySize = sizeof(devinf);
    491   		pGA->tokTbl->DevInf = (TagPtr_t)smlLibMalloc(mySize);
    492   		if (pGA->tokTbl->DevInf == NULL) return NULL;
    493   		smlLibMemcpy(pGA->tokTbl->DevInf, &devinf, mySize);
    494       _tmpTagPtr = pGA->tokTbl->DevInf;
    495     }
    496     #else
    497     _tmpTagPtr=(TagPtr_t)devinf;
    498     #endif
    499   }
    500   #endif
    501 
    502   #ifdef __USE_DMTND__
    503   else if (ext == SML_EXT_DMTND) {
    504     #ifndef NOWSM
    505     _tmpTagPtr = pGA->tokTbl->DmTnd;
    506     if (_tmpTagPtr == NULL) {
    507   		mySize = sizeof(dmtnd);
    508   		pGA->tokTbl->DmTnd = (TagPtr_t)smlLibMalloc(mySize);
    509   		if (pGA->tokTbl->DmTnd == NULL) return NULL;
    510   		smlLibMemcpy(pGA->tokTbl->DmTnd, &dmtnd, mySize);
    511       _tmpTagPtr = pGA->tokTbl->DmTnd;
    512     }
    513     #else
    514     _tmpTagPtr=(TagPtr_t)dmtnd;
    515     #endif
    516   }
    517   #endif
    518 
    519   return _tmpTagPtr;
    520 }
    521 
    522 #undef _TOKEN // we don't need that macro any longer
    523 
    524 /**
    525  * FUNCTION: getTagString
    526  *
    527  * Returns a tag string which belongs to a tag ID.
    528  * This function is needed for the XML encoding
    529  *
    530  * PRE-Condition:   valid tag ID, the tagSring has to be allocated
    531  *
    532  * POST-Condition:  tag string is returned
    533  *
    534  * IN:              tagId, the ID for the tag
    535  *
    536  * IN/OUT:          tagString, allocated string into which the XML
    537  *                             tag string will be written
    538  *
    539  * RETURN:          0,if OK
    540  */
    541 #ifdef __SML_XML__
    542 Ret_t getTagString(XltTagID_t tagID, String_t tagString, SmlPcdataExtension_t ext)
    543 {
    544   int i = 0;
    545   TagPtr_t pTags = getTagTable(ext);
    546   if (pTags == NULL) {
    547     tagString[0] = '\0';
    548     return SML_ERR_NOT_ENOUGH_SPACE;
    549   }
    550   while (((pTags+i)->id) != TN_UNDEF) {
    551     if ((((pTags+i)->id) == tagID)) {
    552       String_t _tmp = (pTags+i)->xml;
    553       smlLibStrcpy(tagString, _tmp);
    554       return SML_ERR_OK;
    555     }
    556     i++;
    557   }
    558   //smlLibStrcpy(tagString, '\0');
    559   tagString[0] = '\0';
    560   return SML_ERR_XLT_INVAL_PROTO_ELEM;
    561 }
    562 #endif
    563 
    564 /**
    565  * FUNCTION: getTagByte
    566  *
    567  * Returns a WBXML byte which belongs to a tag ID in a defined codepage.
    568  * This function is needed for the WBXML encoding
    569  *
    570  * PRE-Condition:   valid tag ID, valid code page
    571  *
    572  * POST-Condition:  tag byte is returned
    573  *
    574  * IN:              tagId, the ID for the tag
    575  *                  cp, code page group for the tag
    576  *                  pTagByte, the byte representation of the tag
    577  *
    578  * RETURN:          0, if OK
    579  */
    580 Ret_t getTagByte(XltTagID_t tagID, SmlPcdataExtension_t ext, Byte_t *pTagByte)
    581 {
    582   int i = 0;
    583   TagPtr_t pTags = getTagTable(ext);
    584   if (pTags == NULL)
    585   {
    586     return SML_ERR_NOT_ENOUGH_SPACE;
    587   }
    588   while (((pTags+i)->id) != TN_UNDEF)
    589   {
    590     if (((pTags+i)->id) == tagID)
    591     {
    592     	*pTagByte = (pTags+i)->wbxml;
    593       return SML_ERR_OK;
    594     }
    595     i++;
    596   }
    597   *pTagByte = 0;
    598   return SML_ERR_XLT_INVAL_PROTO_ELEM;
    599 }
    600 
    601 /**
    602  * FUNCTION: getCodePage
    603  *
    604  * Returns the code page which belongs to a certain PCDATA extension type.
    605  *
    606  * PRE-Condition:   valid PCDATA extension type
    607  *
    608  * POST-Condition:  the code page is returned
    609  *
    610  * IN:              ext, the PCDATA extension type
    611  *
    612  * RETURN:          the code page
    613  */
    614 Byte_t getCodePage(SmlPcdataExtension_t ext)
    615 {
    616   #ifdef __USE_DMTND__
    617   if (ext == SML_EXT_DMTND)
    618     return 2;
    619   #endif
    620   #ifdef __USE_METINF__
    621   if (ext == SML_EXT_METINF)
    622     return 1;
    623   #endif
    624   #ifdef __USE_DEVINF__
    625   if (ext == SML_EXT_DEVINF)
    626     return 0;
    627   #endif
    628     return 0;
    629 }
    630 
    631 /**
    632  * FUNCTION: getCodePageById
    633  *
    634  * Returns the codepage which belongs to a certain tag ID
    635  *
    636  * PRE-Condition:   valid tag ID
    637  *
    638  * POST-Condition:  the code page is returned
    639  *
    640  * IN:              tagID, the ID of the tag
    641  *                  pCp, the codepage/extention of the tag
    642  *
    643  * RETURN:          0, if OK
    644  */
    645 Ret_t getExtById(XltTagID_t tagID,  SmlPcdataExtension_t *pExt)
    646 {
    647     int i = 0;
    648 	SmlPcdataExtension_t ext;
    649 	/* Iterate over all defined extensions to find the corresponding TAG.
    650 	 * Empty extensions, e.g. not defined numbers will be skipped.
    651 	 */
    652 	for (ext = SML_EXT_UNDEFINED; ext < SML_EXT_LAST; ext++) {
    653 		TagPtr_t pTags = getTagTable(ext);
    654 		if (pTags == NULL) {
    655 			continue; /* skip empty codepage */
    656 		}
    657 		i = 0;
    658 		while (((pTags+i)->id) != TN_UNDEF) {
    659 			if ((((pTags+i)->id) == tagID)){
    660        			*pExt = ext;
    661     			return SML_ERR_OK;
    662     	    }
    663     		i++;
    664         }
    665     }
    666 	/* tag not found in any extension */
    667   *pExt = (SmlPcdataExtension_t)255;
    668   return SML_ERR_XLT_INVAL_PROTO_ELEM;
    669 }
    670 
    671 /**
    672  * FUNCTION: getTagIDByStringAndCodepage
    673  *
    674  * Returns the tag ID which belongs to a tag string in a certain codepage
    675  *
    676  * PRE-Condition:   valid tag string, valid code page
    677  *
    678  * POST-Condition:  tag id is returned
    679  *
    680  * IN:              tag, the string representation of the tag
    681  *                  cp, code page group for the tag
    682  *                  pTagID, the tag id of the tag
    683  *
    684  * RETURN:          0, if OK
    685  */
    686 
    687 Ret_t getTagIDByStringAndExt(String_t tag, SmlPcdataExtension_t ext, XltTagID_t *pTagID)
    688 {
    689     int i = 0;
    690     TagPtr_t pTags = getTagTable(ext);
    691     if (pTags == NULL) {
    692       return SML_ERR_NOT_ENOUGH_SPACE;
    693     }
    694     for (i=0;((pTags+i)->id) != TN_UNDEF; i++) {
    695 	    if (*(pTags+i)->xml != *tag) continue; // if the first char doesn't match we skip the strcmp to speed things up
    696         if (smlLibStrcmp(((pTags+i)->xml), tag) == 0) {
    697             *pTagID = (pTags+i)->id;
    698             return SML_ERR_OK;
    699         }
    700     }
    701     *pTagID = TN_UNDEF;
    702     return SML_ERR_XLT_INVAL_PROTO_ELEM;
    703 }
    704 
    705 /**
    706  * FUNCTION: getTagIDByByteAndCodepage
    707  *
    708  * Returns the tag ID which belongs to a tag byte in a certain codepage
    709  *
    710  * PRE-Condition:   valid tag byte, valid code page
    711  *
    712  * POST-Condition:  tag id is returned
    713  *
    714  * IN:              tag, the byte representation of the tag
    715  *                  cp, code page group for the tag
    716  *                  pTagID, the tag id of the tag
    717  *
    718  * RETURN:          0, if OK
    719  */
    720 Ret_t getTagIDByByteAndExt(Byte_t tag, SmlPcdataExtension_t ext, XltTagID_t *pTagID)
    721 {
    722 
    723     int i = 0;
    724     TagPtr_t pTags = getTagTable(ext);
    725     if (pTags == NULL)
    726     {
    727       return SML_ERR_NOT_ENOUGH_SPACE;
    728     }
    729     while (((pTags+i)->id) != TN_UNDEF)
    730     {
    731       if (((pTags+i)->wbxml) == tag)
    732       {
    733         *pTagID = (pTags+i)->id;
    734         return SML_ERR_OK;
    735       }
    736       i++;
    737     }
    738     *pTagID = TN_UNDEF;
    739     return SML_ERR_XLT_INVAL_PROTO_ELEM;
    740 }
    741 
    742 /**
    743  * FUNCTION: getTagIDByStringAndNamespace
    744  *
    745  * Returns the tag ID which belongs to a tag string in a certain namespace
    746  *
    747  * PRE-Condition:   valid tag string, valid namespace
    748  *
    749  * POST-Condition:  tag id is returned
    750  *
    751  * IN:              tag, the string representation of the tag
    752  *                  ns, namespace group for the tag
    753  *                  pTagID, the tag id of the tag
    754  *
    755  * RETURN:          0, if OK
    756  */
    757 #ifdef __SML_XML__
    758 Ret_t getTagIDByStringAndNamespace(String_t tag, String_t ns, XltTagID_t *pTagID)
    759 {
    760     int i = 0;
    761     TagPtr_t pTags = getTagTable(getExtByName(ns));
    762     if (pTags == NULL)
    763     {
    764       return SML_ERR_NOT_ENOUGH_SPACE;
    765     }
    766     while (((pTags+i)->id) != TN_UNDEF)
    767     {
    768       if ((smlLibStrcmp(((pTags+i)->xml), tag) == 0))
    769       {
    770         *pTagID = (pTags+i)->id;
    771         return SML_ERR_OK;
    772       }
    773       i++;
    774     }
    775     *pTagID = TN_UNDEF;
    776     return SML_ERR_XLT_INVAL_PROTO_ELEM;
    777 }
    778 
    779 #endif
    780