SNAP Library 4.1, User Reference  2018-07-26 16:30:42
SNAP, a general purpose, high performance system for analysis and manipulation of large networks
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros
xml.cpp
Go to the documentation of this file.
1 // Xml-Object-Saving
4 
5 TStr TXmlObjSer::GetTagNm(const TStr& TypeNm){
6  TStr& XmlTagNm=TypeNmToTagNmH.AddDat(TypeNm);
7  if (XmlTagNm.Empty()){
8  TChA XmlTagChA=TypeNm;
9  for (int ChN=0; ChN<XmlTagChA.Len(); ChN++){
10  char Ch=XmlTagChA[ChN];
11  if (!((('A'<=Ch)&&(Ch<='Z'))||(('a'<=Ch)&&(Ch<='z'))||(('0'<=Ch)&&(Ch<='9')))){
12  XmlTagChA.PutCh(ChN, '_');
13  }
14  }
15  while ((XmlTagChA.Len()>0)&&(XmlTagChA.LastCh()=='_')){
16  XmlTagChA.Pop();}
17  XmlTagNm=XmlTagChA;
18  }
19  return XmlTagNm;
20 }
21 
23  const PXmlTok& XmlTok, const TStr& Nm, const TStr& TypeNm){
24  // check if the token is full
25  EAssertR(!XmlTok.Empty(), "Xml-Token Empty");
26  // if name is empty then tag=type else tag=name
27  if (!Nm.Empty()){
28  // check if the token is tag
29  if (!XmlTok->IsTag()){
30  TStr ArgStr1="Expected: Tag";
31  TStr ArgStr2=TStr("Found: ")+XmlTok->GetSymStr();
32  TExcept::Throw("Invalid Xml-Token", ArgStr1, ArgStr2);
33  }
34  if (Nm!="-"){
35  // check if the tag is correct
36  if (!XmlTok->IsTag(Nm)){
37  TStr ArgStr1=TStr("Expected: ")+Nm;
38  TStr ArgStr2=TStr("Found: ")+XmlTok->GetStr();
39  TExcept::Throw("Invalid Xml-Tag", ArgStr1, ArgStr2);
40  }
41  // check if the type is correct
42  TStr TypeArgVal=XmlTok->GetStrArgVal("Type");
43  if (TypeArgVal!=TypeNm){
44  TStr ArgStr1=TStr("Expected: ")+TypeNm;
45  TStr ArgStr2=TStr("Found: ")+TypeArgVal;
46  TExcept::Throw("Invalid Xml-Type", ArgStr1, ArgStr2);
47  }
48  }
49  } else {
50  // check if the tag is correct
51  if (!XmlTok->IsTag(TypeNm)){
52  TStr ArgStr1=TStr("Expected: ")+TypeNm;
53  TStr ArgStr2=TStr("Found: ")+XmlTok->GetSymStr();
54  TExcept::Throw("Invalid Xml-Type-Tag", ArgStr1, ArgStr2);
55  }
56  }
57 }
58 
59 bool TXmlObjSer::GetBoolArg(const PXmlTok& XmlTok, const TStr& Nm){
60  TStr ValStr;
61  if (XmlTok->IsArg(Nm, ValStr)){
62  bool Val;
63  if (ValStr.IsBool(Val)){
64  return Val;
65  } else {
66  TExcept::Throw("Invalid Xml-Argument Boolean-Value", Nm, ValStr);
67  }
68  } else {
69  TExcept::Throw("Xml-Argument Missing", Nm);
70  }
71  Fail; return 0;
72 }
73 
74 int TXmlObjSer::GetIntArg(const PXmlTok& XmlTok, const TStr& Nm){
75  TStr ValStr;
76  if (XmlTok->IsArg(Nm, ValStr)){
77  int Val;
78  if (ValStr.IsInt(Val)){
79  return Val;
80  } else {
81  TExcept::Throw("Invalid Xml-Argument Integer-Value", Nm, ValStr);
82  }
83  } else {
84  TExcept::Throw("Xml-Argument Missing", Nm);
85  }
86  Fail; return 0;
87 }
88 
89 int64 TXmlObjSer::GetInt64Arg(const PXmlTok& XmlTok, const TStr& Nm){
90  TStr ValStr;
91  if (XmlTok->IsArg(Nm, ValStr)){
92  int64 Val;
93  if (ValStr.IsInt64(Val)){
94  return Val;
95  } else {
96  TExcept::Throw("Invalid Xml-Argument Integer64-Value", Nm, ValStr);
97  }
98  } else {
99  TExcept::Throw("Xml-Argument Missing", Nm);
100  }
101  Fail; return 0;
102 }
103 
104 double TXmlObjSer::GetFltArg(const PXmlTok& XmlTok, const TStr& Nm){
105  TStr ValStr;
106  if (XmlTok->IsArg(Nm, ValStr)){
107  double Val;
108  if (ValStr.IsFlt(Val)){
109  return Val;
110  } else {
111  TExcept::Throw("Invalid Xml-Argument Double-Value", Nm, ValStr);
112  }
113  } else {
114  TExcept::Throw("Xml-Argument Missing", Nm);
115  }
116  Fail; return 0;
117 }
118 
120 // Xml-Object-Serialization-Tag-Name
122  TSOut& _SOut, const bool& ETagP,
123  const TStr& Nm, const TStr& TypeNm,
124  const TStr& ArgNm, const TStr& ArgVal):
125  TagNm(), SOut(&_SOut){
126  if (Nm!="-"){
127  SOut->PutCh('<');
128  if (Nm.Empty()){
129  SOut->PutStr(TagNm=TypeNm);
130  } else {
131  SOut->PutStr(TagNm=Nm);
132  SOut->PutStr(" Type=\""); SOut->PutStr(TypeNm); SOut->PutCh('"');
133  }
134  if (!ArgNm.Empty()){
135  SOut->PutCh(' '); SOut->PutStr(ArgNm); SOut->PutCh('=');
136  SOut->PutCh('"'); SOut->PutStr(ArgVal); SOut->PutCh('"');
137  }
138  if (ETagP){
139  SOut->PutCh('/'); TagNm="";}
140  SOut->PutCh('>');
141  }
142 }
143 
145  TSOut& _SOut, const bool& ETagP,
146  const TStr& Nm, const TStr& TypeNm,
147  const TStr& ArgNm1, const TStr& ArgVal1,
148  const TStr& ArgNm2, const TStr& ArgVal2,
149  const TStr& ArgNm3, const TStr& ArgVal3,
150  const TStr& ArgNm4, const TStr& ArgVal4):
151  TagNm(), SOut(&_SOut){
152  if (Nm!="-"){
153  SOut->PutCh('<');
154  if (Nm.Empty()){
155  SOut->PutStr(TagNm=TypeNm);
156  } else {
157  SOut->PutStr(TagNm=Nm);
158  SOut->PutStr(" Type=\""); SOut->PutStr(TypeNm); SOut->PutCh('"');
159  }
160  if (!ArgNm1.Empty()){
161  SOut->PutCh(' '); SOut->PutStr(ArgNm1); SOut->PutCh('=');
162  SOut->PutCh('"'); SOut->PutStr(ArgVal1); SOut->PutCh('"');
163  }
164  if (!ArgNm2.Empty()){
165  SOut->PutCh(' '); SOut->PutStr(ArgNm2); SOut->PutCh('=');
166  SOut->PutCh('"'); SOut->PutStr(ArgVal2); SOut->PutCh('"');
167  }
168  if (!ArgNm3.Empty()){
169  SOut->PutCh(' '); SOut->PutStr(ArgNm3); SOut->PutCh('=');
170  SOut->PutCh('"'); SOut->PutStr(ArgVal3); SOut->PutCh('"');
171  }
172  if (!ArgNm4.Empty()){
173  SOut->PutCh(' '); SOut->PutStr(ArgNm4); SOut->PutCh('=');
174  SOut->PutCh('"'); SOut->PutStr(ArgVal4); SOut->PutCh('"');
175  }
176  if (ETagP){
177  SOut->PutCh('/'); TagNm="";}
178  SOut->PutCh('>');
179  }
180 }
181 
183  if (!TagNm.Empty()){
184  SOut->PutCh('<'); SOut->PutCh('/'); SOut->PutStr(TagNm); SOut->PutCh('>');
185  }
186 }
187 
189 // Xml-Chars
190 void TXmlChDef::SetChTy(TBSet& ChSet, const int& MnCh, const int& MxCh){
191  IAssert((0<=MnCh)&&((MxCh==-1)||((MnCh<=MxCh)&&(MxCh<Chs))));
192  ChSet.Incl(MnCh);
193  for (int Ch=MnCh+1; Ch<=MxCh; Ch++){
194  ChSet.Incl(Ch);}
195 }
196 
197 void TXmlChDef::SetChTy(TBSet& ChSet, const TStr& Str){
198  for (int ChN=0; ChN<Str.Len(); ChN++){
199  uchar Ch=Str[ChN];
200  ChSet.Incl(Ch);
201  }
202 }
203 
204 void TXmlChDef::SetEntityVal(const TStr& Nm, const TStr& Val){
205  EntityNmToValH.AddDat(Nm, Val);
206 }
207 
209  Chs(TUCh::Vals),
210  CharChSet(), CombChSet(), ExtChSet(),
211  LetterChSet(), DigitChSet(), NameChSet(), PubidChSet(),
212  EntityNmToValH(100){
213 
214  // Character-Sets
215  // Char ::= #x9 | #xA | #xD | [#x20-#xD7FF] | ...
216  CharChSet.Gen(Chs);
217  // ... because of DMoz (temporary patch)
218  SetChTy(CharChSet, 0x1); SetChTy(CharChSet, 0x3); SetChTy(CharChSet, 0x6);
220  // regular characters
221  SetChTy(CharChSet, 0x9); SetChTy(CharChSet, 0xA); SetChTy(CharChSet, 0xD);
222  SetChTy(CharChSet, 0x20, TUCh::Mx);
223  // BaseChar ::= [#x0041-#x005A] | [#x0061-#x007A] | [#x00C0-#x00D6] |
224  // [#x00D8-#x00F6] | [#x00F8-#x00FF] | ...
225  TBSet BaseChSet(Chs);
226  SetChTy(BaseChSet, 0x41, 0x5A); SetChTy(BaseChSet, 0x61, 0x7A);
227  SetChTy(BaseChSet, 0xC0, 0xD6); SetChTy(BaseChSet, 0xD8, 0xF6);
228  SetChTy(BaseChSet, 0xF8, 0xFF);
229  // Ideographic ::= ...
230  TBSet IdeoChSet(Chs);
231  // CombiningChar ::= ...
232  CombChSet.Gen(Chs);
233  // Extender ::= #x00B7 | ...
234  ExtChSet.Gen(Chs);
235  SetChTy(ExtChSet, 0xB7);
236  // Letter ::= BaseChar | Ideographic
237  LetterChSet=BaseChSet|IdeoChSet;
238  // Digit ::= [#x0030-#x0039] | ...
239  DigitChSet.Gen(Chs);
240  SetChTy(DigitChSet, 0x30, 0x39);
241  // NameChar ::= Letter | Digit | '.' | '-' | '_' | ':' | CombiningChar
243  uchar('.')|uchar('-')|uchar('_')|uchar(':')|CombChSet;
244  // PubidChar ::= #x20 | #xD | #xA | [a-zA-Z0-9] | [-'()+,./:=?;!*#@$_%]
245  PubidChSet.Gen(Chs);
246  SetChTy(PubidChSet, 0x20); SetChTy(PubidChSet, 0xD); SetChTy(PubidChSet, 0xA);
247  SetChTy(PubidChSet, 'a', 'z'); SetChTy(PubidChSet, 'A', 'Z');
248  SetChTy(PubidChSet, '0', '9'); SetChTy(PubidChSet, "-'()+,./:=?;!*#@$_%");
249 
250  // Standard-Entity-Sequences
251  SetEntityVal("amp", "&");
252  SetEntityVal("lt", "<"); SetEntityVal("gt", ">");
253  SetEntityVal("apos", "'"); SetEntityVal("quot", "\"");
254 }
255 
257 // Xml-Lexical
259 
262  PrevCh=Ch;
263  if (ChStack.Empty()){Ch=(RSIn.Eof()) ? TCh::EofCh : RSIn.GetCh();}
264  else {Ch=ChStack.Pop();}
265  ChN++; if (Ch==TCh::LfCh){LnN++; LnChN=0;} else {LnChN++;}
266  //putchar(Ch);
267  return Ch;
268 }
269 
271  if (Spacing==xspIntact){
272  } else
273  if (Spacing==xspPreserve){
274  int SrcChN=0; int DstChN=0;
275  while (SrcChN<TxtChA.Len()){
276  if (TxtChA[SrcChN]==TCh::CrCh){
277  TxtChA.PutCh(DstChN, TCh::LfCh); SrcChN++; DstChN++;
278  if ((SrcChN<TxtChA.Len())&&(TxtChA[SrcChN]==TCh::LfCh)){SrcChN++;}
279  } else {
280  if (SrcChN!=DstChN){
281  TxtChA.PutCh(DstChN, TxtChA[SrcChN]);}
282  SrcChN++; DstChN++;
283  }
284  }
285  TxtChA.Trunc(DstChN);
286  } else
287  if (Spacing==xspSeparate){
288  // squeeze series of white-spaces to single space
289  int SrcChN=0; int DstChN=0;
290  while (SrcChN<TxtChA.Len()){
291  if (ChDef.IsWs(TxtChA[SrcChN])){
292  if ((DstChN>0)&&(TxtChA[DstChN-1]==' ')){
293  SrcChN++;
294  } else {
295  TxtChA.PutCh(DstChN, ' ');
296  SrcChN++; DstChN++;
297  }
298  } else {
299  TxtChA.PutCh(DstChN, TxtChA[SrcChN]);
300  SrcChN++; DstChN++;
301  }
302  }
303  TxtChA.Trunc(DstChN);
304  } else
305  if (Spacing==xspTruncate){
306  // cut leading and trailing white-spaces and
307  // squeeze series of white-spaces to single space
308  int SrcChN=0; int DstChN=0;
309  while (SrcChN<TxtChA.Len()){
310  if (ChDef.IsWs(TxtChA[SrcChN])){
311  if ((DstChN>0)&&(TxtChA[DstChN-1]==' ')){
312  SrcChN++;
313  } else {
314  TxtChA.PutCh(DstChN, ' ');
315  SrcChN++; DstChN++;
316  }
317  } else {
318  TxtChA.PutCh(DstChN, TxtChA[SrcChN]);
319  SrcChN++; DstChN++;
320  }
321  }
322  TxtChA.Trunc(DstChN);
323  // delete trailing white-spaces
324  while ((TxtChA.Len()>0)&&(ChDef.IsWs(TxtChA.LastCh()))){
325  TxtChA.Pop();}
326  } else {
327  Fail;
328  }
329 }
330 
331 void TXmlLx::GetWs(const bool& IsRq){
332  // [3] S ::= (#x20 | #x9 | #xD | #xA)+
333  int WSpaces=0; TxtChA.Clr();
334  while (ChDef.IsWs(Ch)){
335  WSpaces++; TxtChA+=Ch; GetCh();}
336  if (IsRq&&(WSpaces==0)){
337  EThrow("White-space required.");}
338 }
339 
341  // [67] Reference ::= EntityRef | CharRef
342  if (Ch=='#'){
343  // [66] CharRef ::= '&#' [0-9]+ ';' | '&#x' [0-9a-fA-F]+ ';'
344  TChA RefChA; int RefCd=0;
345  if (GetCh()=='x'){
346  // hex-decimal character code
347  forever {
348  GetCh();
349  if (TCh::IsHex(Ch)){
350  RefChA+=Ch;
351  RefCd=RefCd*16+TCh::GetHex(Ch);
352  } else {
353  break;
354  }
355  }
356  } else {
357  // decimal character code
358  forever {
359  if (TCh::IsNum(Ch)){
360  RefChA+=Ch;
361  RefCd=RefCd*10+TCh::GetNum(Ch);
362  } else {
363  break;
364  }
365  GetCh();
366  }
367  }
368  if ((!RefChA.Empty())&&(Ch==';')){
369  GetCh();
370  if (RefCd < 0x80) {
371  // 8-bit char
372  uchar RefCh=uchar(RefCd);
373  return TStr(RefCh);
374  } else {
375  TStr ResStr = TUnicode::EncodeUtf8(RefCd);
376  return ResStr;
377  }
378  } else {
379  EThrow("Invalid Char-Reference."); Fail; return TStr();
380  }
381  } else {
382  // [68] EntityRef ::= '&' Name ';'
383  TStr EntityNm=GetName();
384  if ((!EntityNm.Empty())&&(Ch==';')){
385  GetCh();
386  TStr EntityVal;
387  if (IsEntityNm(EntityNm, EntityVal)){/*intentionaly empty*/}
388  else if (ChDef.IsEntityNm(EntityNm, EntityVal)){/*intentionaly empty*/}
389  else {EThrow(TStr("Entity-Reference (")+EntityNm+") does not exist.");}
390  return EntityVal;
391  } else {
392  EThrow("Invalid Entity-Reference."); Fail; return TStr();
393  }
394  }
395 }
396 
398  // [69] PEReference ::= '%' Name ';'
399  TStr EntityNm=GetName();
400  if ((EntityNm.Empty())||(Ch!=';')){EThrow("Invalid PEntity-Reference.");}
401  GetCh();
402  TStr EntityVal;
403  if (IsPEntityNm(EntityNm, EntityVal)){/*intentionaly empty*/}
404  else {EThrow(TStr("PEntity-Reference (")+EntityNm+") does not exist.");}
405  return EntityVal;
406 }
407 
409  // [25] Eq ::= S? '=' S?
410  GetWs(false);
411  if (Ch=='='){GetCh();}
412  else {EThrow("Equality ('=') character expected.");}
413  GetWs(false);
414 }
415 
417  // [5] Name ::= (Letter | '_' | ':') (NameChar)*
418  TChA NmChA;
419  if (ChDef.IsFirstNameCh(Ch)){
420  do {NmChA+=Ch;} while (ChDef.IsName(GetCh()));
421  } else {
422  EThrow("Invalid first name character.");
423  // EThrow(TStr::Fmt("Invalid first name character [%u:'%c%c%c%c%c'].",
424  // uint(Ch), Ch, RSIn.GetCh(), RSIn.GetCh(), RSIn.GetCh(), RSIn.GetCh()));
425  }
426  return NmChA;
427 }
428 
429 TStr TXmlLx::GetName(const TStr& RqNm){
430  TStr Nm=GetName();
431  // test if the name is equal to the required name
432  if (Nm==RqNm){return RqNm;}
433  else {EThrow(TStr("Name '")+RqNm+"' expected."); Fail; return TStr();}
434 }
435 
437  // [15] Comment ::= {{'<!-}}-' ((Char - '-') | ('-' (Char - '-')))* '-->'
438  if (GetCh()!='-'){EThrow("Invalid comment start.");}
439  TxtChA.Clr();
440  forever {
441  GetCh();
442  if (!ChDef.IsChar(Ch)){EThrow("Invalid comment character.");}
443  if (Ch=='-'){
444  if (GetCh()=='-'){
445  if (GetCh()=='>'){GetCh(); break;} // final bracket
446  else {EThrow("Invalid comment end.");}
447  } else {
448  if (!ChDef.IsChar(Ch)){EThrow("Invalid comment character.");}
449  TxtChA+='-'; TxtChA+=Ch; // special case if single '-'
450  }
451  } else {
452  TxtChA+=Ch; // usual char
453  }
454  }
455 }
456 
458  // [10] AttValue ::= '"' ([^<&"] | Reference)* '"'
459  // | "'" ([^<&'] | Reference)* "'"
460  uchar QCh=Ch;
461  if ((QCh!='"')&&(QCh!='\'')){EThrow("Invalid attribute-value start.");}
462  TChA ValChA; GetCh();
463  forever {
464  if ((Ch=='<')||(!ChDef.IsChar(Ch))){
465  EThrow("Invalid attribute-value character.");}
466  if (Ch==QCh){GetCh(); break;} // final quote
467  else if (Ch=='&'){GetCh(); ValChA+=GetReference();} // reference
468  else {ValChA+=Ch; GetCh();} // usual char
469  }
470  return ValChA;
471 }
472 
474  // [24] VersionInfo ::= {{S 'version' Eq}} (' VersionNum ' | " VersionNum ")
475  // [26] VersionNum ::= ([a-zA-Z0-9_.:] | '-')+
476  char QCh=Ch;
477  if ((Ch!='\'')&&(Ch!='"')){EThrow("Quote character (' or \") expected.");}
478  TChA VerNumChA;
479  GetCh();
480  do {
481  if ((('a'<=Ch)&&(Ch<='z'))||(('A'<=Ch)&&(Ch<='Z'))||
482  (('0'<=Ch)&&(Ch<='9'))||(Ch=='_')||(Ch=='.')||(Ch==':')||(Ch=='-')){
483  VerNumChA+=Ch;
484  } else {
485  EThrow("Invalid version-number character.");
486  }
487  GetCh();
488  } while (Ch!=QCh);
489  GetCh();
490  return VerNumChA;
491 }
492 
494  // [80] EncodingDecl ::= {{S 'encoding' Eq}} ('"' EncName '"' | "'" EncName "'" )
495  // [81] EncName ::= [A-Za-z] ([A-Za-z0-9._] | '-')*
496  char QCh=Ch;
497  if ((Ch!='\'')&&(Ch!='"')){EThrow("Quote character (' or \") expected.");}
498  TChA EncNmChA;
499  GetCh();
500  if ((('a'<=Ch)&&(Ch<='z'))||(('A'<=Ch)&&(Ch<='Z'))){EncNmChA+=Ch;}
501  else {EThrow("Invalid encoding-name character.");}
502  GetCh();
503  while (Ch!=QCh){
504  if ((('a'<=Ch)&&(Ch<='z'))||(('A'<=Ch)&&(Ch<='Z'))||
505  (('0'<=Ch)&&(Ch<='9'))||(Ch=='.')||(Ch=='_')||(Ch=='-')){EncNmChA+=Ch;}
506  else {EThrow("Invalid version-number character.");}
507  GetCh();
508  }
509  GetCh();
510  return EncNmChA;
511 }
512 
514  // [32] SDDecl ::= {{S 'standalone' Eq}}
515  // (("'" ('yes' | 'no') "'") | ('"' ('yes' | 'no') '"'))
516  char QCh=Ch;
517  if ((Ch!='\'')&&(Ch!='"')){EThrow("Quote character (' or \") expected.");}
518  TChA StalChA;
519  GetCh();
520  while (Ch!=QCh){
521  if (('a'<=Ch)&&(Ch<='z')){StalChA+=Ch;}
522  else {EThrow("Invalid standalone-value character.");}
523  GetCh();
524  }
525  GetCh();
526  TStr StalVal=StalChA;
527  if ((StalVal=="yes")||(StalVal=="no")){return StalVal;}
528  else {EThrow("Invalid standalone-value."); Fail; return TStr();}
529 }
530 
532  // [23] XMLDecl ::= {{'<?xml'}}... VersionInfo EncodingDecl? SDDecl? S? '?>'
533  // [24] VersionInfo ::= S 'version' Eq (' VersionNum ' | " VersionNum ")
534  GetWs(true);
535  TStr VerNm=GetName("version"); GetEq(); TStr VerVal=GetVersionNum();
536  if (VerVal!="1.0"){EThrow("Invalid XML version.");}
537  AddArg(VerNm, VerVal);
538  GetWs(false);
539  if (Ch!='?'){
540  // EncodingDecl ::= {{S}} 'encoding' Eq
541  // ('"' EncName '"' | "'" EncName "'" )
542  TStr EncNm=GetName("encoding"); GetEq(); TStr EncVal=GetEncName();
543  AddArg(EncNm, EncVal);
544  }
545  GetWs(false);
546  if (Ch!='?'){
547  // SDDecl ::= {{S}} 'standalone' Eq
548  // (("'" ('yes' | 'no') "'") | ('"' ('yes' | 'no') '"'))
549  TStr StalNm=GetName("standalone"); GetEq(); TStr StalVal=GetStalVal();
550  AddArg(StalNm, StalVal);
551  }
552  GetWs(false);
553  if (Ch=='?'){
554  GetCh();
555  if (Ch=='>'){GetCh();}
556  else {EThrow("Invalid end-of-tag in XML-declaration.");}
557  } else {
558  EThrow("Invalid end-of-tag in XML-declaration.");
559  }
560 }
561 
563  // [16] PI ::= {{'<?' PITarget}} (S (Char* - (Char* '?>' Char*)))? '?>'
564  // [17] PITarget ::= Name - (('X' | 'x') ('M' | 'm') ('L' | 'l'))
565  GetWs(false);
566  TxtChA.Clr();
567  forever {
568  if (!ChDef.IsChar(Ch)){EThrow("Invalid PI character.");}
569  if (Ch=='?'){
570  if (GetCh()=='>'){
571  GetCh(); break;
572  } else {
573  if (!ChDef.IsChar(Ch)){EThrow("Invalid PI character.");}
574  TxtChA+='?'; TxtChA+=Ch; // special case if single '?'
575  }
576  } else {
577  TxtChA+=Ch; // usual char
578  }
579  GetCh();
580  }
581 }
582 
584  // [11] SystemLiteral ::= ('"' [^"]* '"') | ("'" [^']* "'")
585  char QCh=Ch;
586  if ((Ch!='\'')&&(Ch!='"')){EThrow("Quote character (' or \") expected.");}
587  TChA LitChA; GetCh();
588  while (Ch!=QCh){
589  if (!ChDef.IsChar(Ch)){EThrow("Invalid System-Literal character.");}
590  LitChA+=Ch; GetCh();
591  }
592  GetCh();
593  return LitChA;
594 }
595 
597  // [12] PubidLiteral ::= '"' PubidChar* '"' | "'" (PubidChar - "'")* "'"
598  char QCh=Ch;
599  if ((Ch!='\'')&&(Ch!='"')){EThrow("Quote character (' or \") expected.");}
600  TChA LitChA; GetCh();
601  while (Ch!=QCh){
602  if (!ChDef.IsPubid(Ch)){EThrow("Invalid Public-Id-Literal character.");}
603  LitChA+=Ch; GetCh();
604  }
605  GetCh();
606  return LitChA;
607 }
608 
610  // ExternalID ::= 'SYSTEM' S SystemLiteral
611  // | 'PUBLIC' S PubidLiteral S SystemLiteral
612  TStr ExtIdNm=GetName();
613  if (ExtIdNm=="SYSTEM"){
614  GetWs(true); GetSystemLiteral();
615  } else if (ExtIdNm=="PUBLIC"){
616  GetWs(true); GetPubidLiteral(); GetWs(true); GetSystemLiteral();
617  } else {
618  EThrow("Invalid external-id ('SYSTEM' or 'PUBLIC' expected).");
619  }
620 }
621 
623  // [76] NDataDecl ::= S 'NDATA' S Name
624  GetName("NDATA"); GetWs(true); GetName();
625 }
626 
628  // [28] doctypedecl ::= {{'<!DOCTYPE'}} S Name (S ExternalID)? S?
629  // ('[' (markupdecl | PEReference | S)* ']' S?)? '>'
630  GetWs(true);
631  TStr DocTypeDeclNm=GetName();
632  GetWs(false);
633  if (Ch=='>'){GetCh(); return;}
634  if (Ch!='['){GetExternalId();}
635  GetWs(false);
636  if (Ch=='['){
637  GetCh();
638  // [28] (markupdecl | PEReference | S)*
639  GetWs(false);
640  while (Ch!=']'){
641  if (ChDef.IsWs(Ch)){GetWs(true);}
642  else if (Ch=='%'){GetPEReference();}
643  else {
644  GetSym();
645  }
646  }
647  GetCh();
648  }
649  GetWs(false);
650  // '>'
651  if (Ch=='>'){GetCh();}
652  else {EThrow("Invalid end-of-tag in document-type-declaration.");}
653  TagNm=DocTypeDeclNm;
654 }
655 
657  TxtChA.Clr();
658  while (Ch!='>'){
659  if (!ChDef.IsChar(Ch)){EThrow("Invalid Element character.");}
660  TxtChA+=Ch; GetCh();
661  }
662  GetCh();
663 }
664 
666  TxtChA.Clr();
667  while (Ch!='>'){
668  if (!ChDef.IsChar(Ch)){EThrow("Invalid Element character.");}
669  TxtChA+=Ch; GetCh();
670  }
671  GetCh();
672 }
673 
675  // [9] EntityValue ::= '"' ([^%&"] | PEReference | Reference)* '"'
676  // | "'" ([^%&'] | PEReference | Reference)* "'"
677  uchar QCh=Ch;
678  if ((QCh!='"')&&(QCh!='\'')){EThrow("Invalid entity-value start.");}
679  TChA ValChA; GetCh();
680  forever {
681  if (!ChDef.IsChar(Ch)){EThrow("Invalid entity-value character.");}
682  if (Ch==QCh){GetCh(); break;} // final quote
683  else if (Ch=='&'){GetCh(); ValChA+=GetReference();} // reference
684  else if (Ch=='%'){GetCh(); ValChA+=GetPEReference();} // pereference
685  else {ValChA+=Ch; GetCh();} // usual char
686  }
687  return ValChA;
688 }
689 
691  // [70] EntityDecl ::= GEDecl | PEDecl
692  // [71] GEDecl ::= '<!ENTITY' S Name S EntityDef S? '>'
693  // [72] PEDecl ::= '<!ENTITY' S '%' S Name S PEDef S? '>'
694  GetWs(true); TStr EntityNm;
695  if (Ch=='%'){
696  GetCh(); GetWs(true); EntityNm=GetName(); GetWs(true);
697  // [74] PEDef ::= EntityValue | ExternalID
698  if ((Ch=='\"')||(Ch=='\'')){
699  TStr EntityVal=GetEntityValue();
700  PutPEntityVal(EntityNm, EntityVal);
701  } else {
702  GetExternalId();
703  GetWs(false);
704  if (Ch!='>'){GetNData();}
705  }
706  } else {
707  EntityNm=GetName(); GetWs(true);
708  // [73] EntityDef ::= EntityValue | (ExternalID NDataDecl?)
709  if ((Ch=='\"')||(Ch=='\'')){
710  TStr EntityVal=GetEntityValue();
711  PutEntityVal(EntityNm, EntityVal);
712  } else {
713  GetExternalId();
714  }
715  }
716  GetWs(false);
717  if (Ch=='>'){GetCh();}
718  else {EThrow("Invalid end-of-tag in entity-declaration.");}
719  TagNm=EntityNm;
720 }
721 
723  // [82] NotationDecl ::= '<!NOTATION' S Name S (ExternalID | PublicID) S? '>'
724  // [83] PublicID ::= 'PUBLIC' S PubidLiteral
725  TxtChA.Clr();
726  while (Ch!='>'){
727  if (!ChDef.IsChar(Ch)){EThrow("Invalid Element character.");}
728  TxtChA+=Ch; GetCh();
729  }
730  GetCh();
731 }
732 
734  // [18] CDSect ::= CDStart CData CDEnd
735  // [19] CDStart ::= '<![CDATA{{['}}
736  // [20] CData ::= (Char* - (Char* ']]>' Char*))
737  // [21] CDEnd ::= ']]>'
738  if (Ch=='['){GetCh();}
739  else {EThrow("Invalid start of CDATA section.");}
740  TxtChA.Clr();
741  forever {
742  if (!ChDef.IsChar(Ch)){EThrow("Invalid CDATA character.");}
743  if ((Ch=='>')&&(TxtChA.Len()>=2)&&
744  (TxtChA.LastLastCh()==']') && (TxtChA.LastCh()==']')){
745  GetCh(); TxtChA.Pop(); TxtChA.Pop(); break;
746  } else {
747  TxtChA+=Ch; GetCh();
748  }
749  }
750 }
751 
753  // [3] S ::= (#x20 | #x9 | #xD | #xA)+
754  while (ChDef.IsWs(Ch)){GetCh();}
755 }
756 
758  if (Ch=='<'){
759  GetCh(); ClrArgV();
760  if (Ch=='?'){
761  GetCh(); TagNm=GetName();
762  if (TagNm.GetLc()=="xml"){Sym=xsyXmlDecl; GetXmlDecl();}
763  else {Sym=xsyPI; GetPI();}
764  } else
765  if (Ch=='!'){
766  GetCh();
767  if (Ch=='['){
768  GetCh(); TagNm=GetName();
769  if (TagNm=="CDATA"){Sym=xsyQStr; GetCDSect();}
770  else {EThrow(TStr("Invalid tag after '<![' (")+TagNm+").");}
771  } else
772  if (Ch=='-'){
774  } else {
775  TagNm=GetName();
776  if (TagNm=="DOCTYPE"){GetDocTypeDecl(); Sym=xsyDocTypeDecl;}
777  else if (TagNm=="ELEMENT"){GetElement(); Sym=xsyElement;}
778  else if (TagNm=="ATTLIST"){GetAttList(); Sym=xsyAttList;}
779  else if (TagNm=="ENTITY"){GetEntity(); Sym=xsyEntity;}
780  else if (TagNm=="NOTATION"){GetNotation(); Sym=xsyNotation;}
781  else {EThrow(TStr("Invalid tag (")+TagNm+").");}
782  }
783  } else
784  if (Ch=='/'){
785  // xsyETag
786  GetCh(); Sym=xsyETag; TagNm=GetName(); GetWs(false);
787  if (Ch=='>'){GetCh();}
788  else {EThrow("Invalid End-Tag.");}
789  } else {
790  // xsySTag or xsySETag
791  TagNm=GetName(); GetWs(false);
792  while ((Ch!='>')&&(Ch!='/')){
793  TStr AttrNm=GetName();
794  GetEq();
795  TStr AttrVal=GetAttValue();
796  GetWs(false);
797  AddArg(AttrNm, AttrVal);
798  }
799  if (Ch=='/'){
800  if (GetCh()=='>'){Sym=xsySETag; GetCh();}
801  else {EThrow("Invalid Empty-Element-Tag.");}
802  } else {
803  Sym=xsySTag; GetCh();
804  }
805  }
806  if (Spacing==xspTruncate){SkipWs();}
807  } else
808  if (ChDef.IsWs(Ch)){
809  Sym=xsyWs; GetWs(true); ToNrSpacing();
810  if (Spacing==xspTruncate){GetSym();}
811  } else
812  if (Ch==TCh::EofCh){
813  Sym=xsyEof;
814  } else {
815  Sym=xsyStr; TxtChA.Clr();
816  // [14] CharData ::= [^<&]* - ([^<&]* ']]>' [^<&]*)
817  forever {
818  if (!ChDef.IsChar(Ch)){
819  EThrow(TUInt::GetStr(Ch, "Invalid character (%d)."));}
820  // GetCh(); continue; // skip invalid characters
821  if (Ch=='<'){break;} // tag
822  if (Ch=='&'){GetCh(); TxtChA+=GetReference();} // reference
823  else {
824  if ((Ch=='>')&&(TxtChA.Len()>=2)&&
825  (TxtChA.LastLastCh()==']')&&(TxtChA.LastCh()==']')){
826  EThrow("Forbidden substring ']]>' in character data.");}
827  TxtChA+=Ch; GetCh(); // usual char
828  }
829  }
830  ToNrSpacing();
831  }
832  return Sym;
833 }
834 
836  TChA SymChA;
837  switch (Sym){
838  case xsyUndef:
839  SymChA="{Undef}"; break;
840  case xsyWs:
841  SymChA+="{Space:'"; SymChA+=TStr(TxtChA).GetHex(); SymChA+="'}"; break;
842  case xsyComment:
843  SymChA+="<!--"; SymChA+=TxtChA; SymChA+="-->"; break;
844  case xsyXmlDecl:{
845  SymChA+="<?"; SymChA+=TagNm;
846  for (int ArgN=0; ArgN<GetArgs(); ArgN++){
847  TStr ArgNm; TStr ArgVal; GetArg(ArgN, ArgNm, ArgVal);
848  char ArgValQCh=GetArgValQCh(ArgVal);
849  SymChA+=' '; SymChA+=ArgNm; SymChA+='=';
850  SymChA+=ArgValQCh; SymChA+=ArgVal; SymChA+=ArgValQCh;
851  }
852  SymChA+="?>"; break;}
853  case xsyPI:
854  SymChA+="<?"; SymChA+=TagNm;
855  if (!TxtChA.Empty()){SymChA+=' '; SymChA+=TxtChA;}
856  SymChA+="?>"; break;
857  case xsyDocTypeDecl:
858  SymChA+="<!DOCTYPE "; SymChA+=TagNm; SymChA+=">"; break;
859  case xsySTag:
860  case xsySETag:{
861  SymChA+="<"; SymChA+=TagNm;
862  for (int ArgN=0; ArgN<GetArgs(); ArgN++){
863  TStr ArgNm; TStr ArgVal; GetArg(ArgN, ArgNm, ArgVal);
864  char ArgValQCh=GetArgValQCh(ArgVal);
865  SymChA+=' '; SymChA+=ArgNm; SymChA+='=';
866  SymChA+=ArgValQCh; SymChA+=ArgVal; SymChA+=ArgValQCh;
867  }
868  if (Sym==xsySTag){SymChA+=">";}
869  else if (Sym==xsySETag){SymChA+="/>";}
870  else {Fail;}
871  break;}
872  case xsyETag:
873  SymChA+="</"; SymChA+=TagNm; SymChA+=">"; break;
874  case xsyStr:
875  SymChA="{String:'"; SymChA+=TxtChA; SymChA+="'}"; break;
876  case xsyQStr:
877  SymChA="{QString:'"; SymChA+=TxtChA; SymChA+="'}"; break;
878  case xsyEof:
879  SymChA="{Eof}"; break;
880  default: Fail;
881  }
882  return SymChA;
883 }
884 
885 void TXmlLx::EThrow(const TStr& MsgStr) const {
886  TChA FPosChA;
887  FPosChA+=" [File:"; FPosChA+=SIn->GetSNm();
888  FPosChA+=" Line:"; FPosChA+=TInt::GetStr(LnN);
889  FPosChA+=" Char:"; FPosChA+=TInt::GetStr(LnChN);
890  FPosChA+="]";
891  TStr FullMsgStr=MsgStr+FPosChA;
892  TExcept::Throw(FullMsgStr);
893 }
894 
896  TChA FPosChA;
897  FPosChA+=" [File:"; FPosChA+=SIn->GetSNm();
898  FPosChA+=" Line:"; FPosChA+=TInt::GetStr(LnN);
899  FPosChA+=" Char:"; FPosChA+=TInt::GetStr(LnChN);
900  FPosChA+="]";
901  return FPosChA;
902 }
903 
905  switch (XmlLxSym){
906  case xsyUndef: return "Undef";
907  case xsyWs: return "White-Space";
908  case xsyComment: return "Comment";
909  case xsyXmlDecl: return "Declaration";
910  case xsyPI: return "PI";
911  case xsyDocTypeDecl: return "Document-Type";
912  case xsyElement: return "Element";
913  case xsyAttList: return "Attribute-List";
914  case xsyEntity: return "Entity";
915  case xsyNotation: return "Notation";
916  case xsyTag: return "Tag";
917  case xsySTag: return "Start-Tag";
918  case xsyETag: return "End-Tag";
919  case xsySETag: return "Start-End-Tag";
920  case xsyStr: return "String";
921  case xsyQStr: return "Quoted-String";
922  case xsyEof: return "Eon-Of-File";
923  default: return "Undef";
924  }
925 }
926 
927 bool TXmlLx::IsTagNm(const TStr& Str){
928  TChA ChA=Str;
929  if (ChA.Len()>0){
930  if (TXmlLx::ChDef.IsFirstNameCh(ChA[0])){
931  for (int ChN=1; ChN<ChA.Len(); ChN++){
932  if (!TXmlLx::ChDef.IsName(ChA[ChN])){
933  return false;
934  }
935  }
936  return true;
937  } else {
938  return false;
939  }
940  } else {
941  return false;
942  }
943 }
944 
946  TChA XmlChA;
947  for (int ChN=0; ChN<PlainMem.Len(); ChN++){
948  uchar Ch=PlainMem[ChN];
949  if ((' '<=Ch)&&(Ch<='~')){
950  switch (Ch){
951  case '"': XmlChA+="&quot;"; break;
952  case '&': XmlChA+="&amp;"; break;
953  case '\'': XmlChA+="&apos;"; break;
954  case '<': XmlChA+="&lt;"; break;
955  case '>': XmlChA+="&gt;"; break;
956  default: XmlChA+=Ch;
957  }
958  } else
959  if ((Ch=='\r')||(Ch=='\n')){
960  XmlChA+=Ch;
961  } else {
962  XmlChA+='&'; XmlChA+='#'; XmlChA+=TUInt::GetStr(Ch); XmlChA+=';';
963  }
964  }
965  return XmlChA;
966 }
967 
969  TChA XmlChA;
970  for (int ChN=0; ChN<PlainChA.Len(); ChN++){
971  uchar Ch=PlainChA[ChN];
972  if ((' '<=Ch)&&(Ch<='~')){
973  switch (Ch){
974  case '"': XmlChA+="&quot;"; break;
975  case '&': XmlChA+="&amp;"; break;
976  case '\'': XmlChA+="&apos;"; break;
977  case '<': XmlChA+="&lt;"; break;
978  case '>': XmlChA+="&gt;"; break;
979  default: XmlChA+=Ch;
980  }
981  } else
982  if ((Ch=='\r')||(Ch=='\n')){
983  XmlChA+=Ch;
984  } else {
985  XmlChA+='&'; XmlChA+='#'; XmlChA+=TUInt::GetStr(Ch); XmlChA+=';';
986  }
987  }
988  return XmlChA;
989 }
990 
992  TChA PlainChA;
993  TChRet Ch(TStrIn::New(XmlStr));
994  Ch.GetCh();
995  while (!Ch.Eof()){
996  if (Ch()!='&'){
997  PlainChA+=Ch(); Ch.GetCh();
998  } else {
999  // [67] Reference ::= EntityRef | CharRef
1000  if (Ch.GetCh()=='#'){
1001  // [66] CharRef ::= '&#' [0-9]+ ';' | '&#x' [0-9a-fA-F]+ ';'
1002  TChA RefChA; int RefCd=0;
1003  if (Ch.GetCh()=='x'){
1004  // hex-decimal character code
1005  forever {
1006  Ch.GetCh();
1007  if (TCh::IsHex(Ch())){
1008  RefChA+=Ch();
1009  RefCd=RefCd*16+TCh::GetHex(Ch());
1010  } else {
1011  break;
1012  }
1013  }
1014  } else {
1015  // decimal character code
1016  forever {
1017  if (TCh::IsNum(Ch())){
1018  RefChA+=Ch();
1019  RefCd=RefCd*10+TCh::GetNum(Ch());
1020  } else {
1021  break;
1022  }
1023  Ch.GetCh();
1024  }
1025  }
1026  if ((!RefChA.Empty())&&(Ch()==';')){
1027  Ch.GetCh();
1028  if (RefCd < 0x80) {
1029  // ascii character
1030  uchar RefCh=uchar(RefCd);
1031  PlainChA+=RefCh;
1032  } else {
1033  // unicode
1034  TUnicode::EncodeUtf8(RefCd, PlainChA);
1035  }
1036  }
1037  } else {
1038  // [68] EntityRef ::= '&' Name ';'
1039  TChA EntityNm;
1040  while ((!Ch.Eof())&&(Ch()!=';')){
1041  EntityNm+=Ch(); Ch.GetCh();}
1042  if ((!EntityNm.Empty())&&(Ch()==';')){
1043  Ch.GetCh();
1044  if (EntityNm=="quot"){PlainChA+='"';}
1045  else if (EntityNm=="amp"){PlainChA+='&';}
1046  else if (EntityNm=="apos"){PlainChA+='\'';}
1047  else if (EntityNm=="lt"){PlainChA+='<';}
1048  else if (EntityNm=="gt"){PlainChA+='>';}
1049  }
1050  }
1051  }
1052  }
1053  return PlainChA;
1054 }
1055 
1057  TStr UsAsciiStr=XmlStr;
1058  UsAsciiStr.ChangeStrAll("&#232;", "c");
1059  UsAsciiStr.ChangeStrAll("&#200;", "C");
1060  UsAsciiStr.ChangeStrAll("&#154;", "s");
1061  UsAsciiStr.ChangeStrAll("&#138;", "S");
1062  UsAsciiStr.ChangeStrAll("&#158;", "z");
1063  UsAsciiStr.ChangeStrAll("&#142;", "Z");
1064  TChA UsAsciiChA=TXmlLx::GetPlainStrFromXmlStr(UsAsciiStr);
1065  for (int ChN=0; ChN<UsAsciiChA.Len(); ChN++){
1066  char Ch=UsAsciiChA[ChN];
1067  if ((Ch<' ')||('~'<Ch)){UsAsciiChA.PutCh(ChN, 'x');}
1068  }
1069  return UsAsciiChA;
1070 }
1071 
1073  TStr ChRefStr=YuEntRefStr;
1074  ChRefStr.ChangeStrAll("&ch;", "&#232;");
1075  ChRefStr.ChangeStrAll("&Ch;", "&#200;");
1076  ChRefStr.ChangeStrAll("&sh;", "&#154;");
1077  ChRefStr.ChangeStrAll("&Sh;", "&#138;");
1078  ChRefStr.ChangeStrAll("&zh;", "&#158;");
1079  ChRefStr.ChangeStrAll("&Zh;", "&#142;");
1080  ChRefStr.ChangeStrAll("&cs", "c");
1081  ChRefStr.ChangeStrAll("&Cs;", "C");
1082  ChRefStr.ChangeStrAll("&dz;", "dz");
1083  ChRefStr.ChangeStrAll("&Dz;", "Dz");
1084  return ChRefStr;
1085 }
1086 
1088 // Xml-Token
1089 bool TXmlTok::GetBoolArgVal(const TStr& ArgNm, const bool& DfVal) const {
1090  int ArgN=ArgNmValV.SearchForw(TStrKd(ArgNm));
1091  return (ArgN==-1) ? DfVal : (ArgNmValV[ArgN].Dat==TBool::TrueStr);
1092 }
1093 
1095  const TStr& ArgNm, const TStr& TrueVal, const bool& DfVal) const {
1096  int ArgN=ArgNmValV.SearchForw(TStrKd(ArgNm));
1097  return (ArgN==-1) ? DfVal : (ArgNmValV[ArgN].Dat==TrueVal);
1098 }
1099 
1100 bool TXmlTok::GetBoolArgVal(const TStr& ArgNm,
1101  const TStr& TrueVal, const TStr& FalseVal, const bool& DfVal) const {
1102  int ArgN=ArgNmValV.SearchForw(TStrKd(ArgNm));
1103  if (ArgN==-1){return DfVal;}
1104  TStr ArgVal=ArgNmValV[ArgN].Dat;
1105  if (ArgVal==TrueVal){return true;}
1106  IAssert(ArgVal == FalseVal); return false;
1107 }
1108 
1109 int TXmlTok::GetIntArgVal(const TStr& ArgNm, const int& DfVal) const {
1110  int ArgN=ArgNmValV.SearchForw(TStrKd(ArgNm));
1111  if (ArgN==-1){
1112  return DfVal;
1113  } else {
1114  int Val;
1115  if (ArgNmValV[ArgN].Dat.IsInt(Val)){return Val;} else {return DfVal;}
1116  }
1117 }
1118 
1119 double TXmlTok::GetFltArgVal(const TStr& ArgNm, const double& DfVal) const {
1120  int ArgN=ArgNmValV.SearchForw(TStrKd(ArgNm));
1121  if (ArgN==-1){
1122  return DfVal;
1123  } else {
1124  double Val;
1125  if (ArgNmValV[ArgN].Dat.IsFlt(Val)){return Val;} else {return DfVal;}
1126  }
1127 }
1128 
1129 TStr TXmlTok::GetStrArgVal(const TStr& ArgNm, const TStr& DfVal) const {
1130  int ArgN=ArgNmValV.SearchForw(TStrKd(ArgNm));
1131  return (ArgN==-1) ? DfVal : ArgNmValV[ArgN].Dat;
1132 }
1133 
1134 void TXmlTok::PutSubTok(const PXmlTok& Tok, const int& SubTokN){
1135  if (SubTokN==-1){
1136  ClrSubTok(); AddSubTok(Tok);
1137  } else {
1138  SubTokV[SubTokN]=Tok;
1139  }
1140 }
1141 
1142 PXmlTok TXmlTok::GetTagTok(const TStr& TagPath) const {
1143  if (TagPath.Empty()){
1144  return (TXmlTok*)this;
1145  } else {
1146  TStr TagNm; TStr RestTagPath; TagPath.SplitOnCh(TagNm, '|', RestTagPath);
1147  PXmlTok SubTok;
1148  for (int SubTokN=0; SubTokN<SubTokV.Len(); SubTokN++){
1149  SubTok=SubTokV[SubTokN];
1150  if ((SubTok->GetSym()==xsyTag)&&(SubTok->GetStr()==TagNm)){break;}
1151  else {SubTok=NULL;}
1152  }
1153  if ((SubTok.Empty())||(RestTagPath.Empty())){return SubTok;}
1154  else {return SubTok->GetTagTok(RestTagPath);}
1155  }
1156 }
1157 
1158 void TXmlTok::GetTagTokV(const TStr& TagPath, TXmlTokV& XmlTokV) const {
1159  XmlTokV.Clr();
1160  TStr PreTagPath; TStr TagNm; TagPath.SplitOnLastCh(PreTagPath, '|', TagNm);
1161  PXmlTok Tok=GetTagTok(PreTagPath);
1162  if (!Tok.Empty()){
1163  for (int SubTokN=0; SubTokN<Tok->GetSubToks(); SubTokN++){
1164  PXmlTok SubTok=Tok->GetSubTok(SubTokN);
1165  if ((SubTok->GetSym()==xsyTag)&&(SubTok->GetStr()==TagNm)){
1166  XmlTokV.Add(SubTok);}
1167  }
1168  }
1169 }
1170 
1171 void TXmlTok::GetTagValV(const TStr& TagNm, const bool& XmlP, TStrV& ValV) const {
1172  if ((Sym==xsyTag)&&(Str==TagNm)){
1173  ValV.Add(GetTokStr(XmlP));
1174  } else {
1175  for (int SubTokN=0; SubTokN<GetSubToks(); SubTokN++){
1176  GetSubTok(SubTokN)->GetTagValV(TagNm, XmlP, ValV);}
1177  }
1178 }
1179 
1180 TStr TXmlTok::GetTagVal(const TStr& TagNm, const bool& XmlP) const {
1181  TStrV ValV; GetTagValV(TagNm, XmlP, ValV);
1182  if (ValV.Len()>0){return ValV[0];} else {return "";}
1183 }
1184 
1185 void TXmlTok::AddTokToChA(const bool& XmlP, TChA& ChA) const {
1186  switch (Sym){
1187  case xsyWs:
1188  ChA+=Str; break;
1189  case xsyStr:
1190  if (XmlP){ChA+=TXmlLx::GetXmlStrFromPlainStr(Str);} else {ChA+=Str;} break;
1191  case xsyQStr:
1192  if (XmlP){ChA+="<![CDATA[";}
1193  ChA+=Str;
1194  if (XmlP){ChA+="]]>";} break;
1195  case xsyTag:
1196  if (XmlP){
1197  ChA+='<'; ChA+=Str;
1198  for (int ArgN=0; ArgN<GetArgs(); ArgN++){
1199  TStr ArgNm; TStr ArgVal; GetArg(ArgN, ArgNm, ArgVal);
1200  if (XmlP){ArgVal=TXmlLx::GetXmlStrFromPlainStr(ArgVal);}
1201  char ArgValQCh=TXmlLx::GetArgValQCh(ArgVal);
1202  ChA+=' '; ChA+=ArgNm; ChA+='=';
1203  ChA+=ArgValQCh; ChA+=ArgVal; ChA+=ArgValQCh;
1204  }
1205  }
1206  if (GetSubToks()==0){
1207  if (XmlP){ChA+="/>";}
1208  } else {
1209  if (XmlP){ChA+=">";}
1210  for (int SubTokN=0; SubTokN<GetSubToks(); SubTokN++){
1211  GetSubTok(SubTokN)->AddTokToChA(XmlP, ChA);}
1212  if (XmlP){ChA+="</"; ChA+=Str; ChA+='>';}
1213  }
1214  break;
1215  default: Fail;
1216  }
1217 }
1218 
1219 TStr TXmlTok::GetTokVStr(const TXmlTokV& TokV, const bool& XmlP){
1220  TChA TokVChA;
1221  for (int TokN=0; TokN<TokV.Len(); TokN++){
1222  if (TokN>0){TokVChA+=' ';}
1223  TokVChA+=TokV[TokN]->GetTokStr(XmlP);
1224  }
1225  return TokVChA;
1226 }
1227 
1229  switch (Lx.Sym){
1230  case xsyWs:
1231  case xsyStr:
1232  case xsyQStr:
1233  return TXmlTok::New(Lx.Sym, Lx.TxtChA);
1234  case xsySTag:
1235  case xsySETag:
1236  return TXmlTok::New(xsyTag, Lx.TagNm, Lx.ArgNmValKdV);
1237  default: Fail; return NULL;
1238  }
1239 }
1240 
1242 // Xml-Document
1244  // [27] Misc ::= Comment | PI | S
1245  while ((Lx.Sym==xsyComment)||(Lx.Sym==xsyPI)||(Lx.Sym==xsyWs)){
1246  Lx.GetSym();}
1247 }
1248 
1250  // [39] element ::= EmptyElemTag | STag content ETag
1251  PXmlTok Tok;
1252  if (Lx.Sym==xsySETag){
1253  Tok=TXmlTok::GetTok(Lx);
1254  } else
1255  if (Lx.Sym==xsySTag){
1256  Tok=TXmlTok::GetTok(Lx);
1257  forever {
1258  Lx.GetSym();
1259  if (Lx.Sym==xsyETag){
1260  if (Tok->GetStr()==Lx.TagNm){
1261  break;
1262  } else {
1263  TStr MsgStr=TStr("Invalid End-Tag '")+Lx.TagNm+
1264  "' ('"+Tok->GetStr()+"' expected).";
1265  Lx.EThrow(MsgStr);
1266  }
1267  } else {
1268  PXmlTok SubTok;
1269  switch (Lx.Sym){
1270  case xsySTag:
1271  SubTok=LoadTxtElement(Lx); break;
1272  case xsySETag:
1273  case xsyStr:
1274  case xsyQStr:
1275  case xsyWs:
1276  SubTok=TXmlTok::GetTok(Lx); break;
1277  case xsyPI:
1278  case xsyComment:
1279  break;
1280  default: Lx.EThrow("Content or End-Tag expected.");
1281  }
1282  if (!SubTok.Empty()){
1283  Tok->AddSubTok(SubTok);}
1284  }
1285  }
1286  } else
1287  if (Lx.Sym==xsyETag){
1288  TStr MsgStr=
1289  TStr("Xml-Element (Start-Tag or Empty-Element-Tag) required.")+
1290  TStr::GetStr(Lx.TagNm, " End-Tag </%s> encountered.");
1291  Lx.EThrow(MsgStr);
1292  } else {
1293  Lx.EThrow("Xml-Element (Start-Tag or Empty-Element-Tag) required.");
1294  }
1295  return Tok;
1296 }
1297 
1298 PXmlTok TXmlDoc::GetTagTok(const TStr& TagPath) const {
1299  if (TagPath.Empty()){
1300  return Tok;
1301  } else {
1302  TStr TagNm; TStr RestTagPath; TagPath.SplitOnCh(TagNm, '|', RestTagPath);
1303  if ((Tok->GetSym()==xsyTag)&&(Tok->GetStr()==TagNm)){
1304  if (RestTagPath.Empty()){return Tok;}
1305  else {return Tok->GetTagTok(RestTagPath);}
1306  } else {
1307  return NULL;
1308  }
1309  }
1310 }
1311 
1312 void TXmlDoc::PutTagTokStr(const TStr& TagPath, const TStr& TokStr) const {
1313  PXmlTok Tok=GetTagTok(TagPath);
1314  Tok->ClrSubTok();
1315  PXmlTok StrTok=TXmlTok::New(xsyStr, TokStr);
1316  Tok->AddSubTok(StrTok);
1317 }
1318 
1319 void TXmlDoc::GetTagTokV(const TStr& TagPath, TXmlTokV& XmlTokV) const {
1320  XmlTokV.Clr();
1321  TStr PreTagPath; TStr TagNm; TagPath.SplitOnLastCh(PreTagPath, '|', TagNm);
1322  PXmlTok Tok=GetTagTok(PreTagPath);
1323  if (!Tok.Empty()){
1324  for (int SubTokN=0; SubTokN<Tok->GetSubToks(); SubTokN++){
1325  PXmlTok SubTok=Tok->GetSubTok(SubTokN);
1326  if ((SubTok->GetSym()==xsyTag)&&(SubTok->GetStr()==TagNm)){
1327  XmlTokV.Add(SubTok);}
1328  }
1329  }
1330 }
1331 
1333  const TStr& TagPath, const TStr& ArgNm, const bool& DfVal) const {
1334  PXmlTok TagTok;
1335  if (IsTagTok(TagPath, TagTok)){
1336  return TagTok->GetBoolArgVal(ArgNm, DfVal);}
1337  else {return DfVal;}
1338 }
1339 
1341  const TStr& TagPath, const TStr& ArgNm, const int& DfVal) const {
1342  PXmlTok TagTok;
1343  if (IsTagTok(TagPath, TagTok)){
1344  return TagTok->GetIntArgVal(ArgNm, DfVal);}
1345  else {return DfVal;}
1346 }
1347 
1349  const TStr& TagPath, const TStr& ArgNm, const double& DfVal) const {
1350  PXmlTok TagTok;
1351  if (IsTagTok(TagPath, TagTok)){
1352  return TagTok->GetFltArgVal(ArgNm, DfVal);}
1353  else {return DfVal;}
1354 }
1355 
1357  const TStr& TagPath, const TStr& ArgNm, const TStr& DfVal) const {
1358  PXmlTok TagTok;
1359  if (IsTagTok(TagPath, TagTok)){
1360  return TagTok->GetStrArgVal(ArgNm, DfVal);}
1361  else {return DfVal;}
1362 }
1363 
1365  TChA ChA=Str;
1366  TChA XmlChA;
1367  for (int ChN=0; ChN<ChA.Len(); ChN++){
1368  uchar Ch=ChA[ChN];
1369  if ((' '<=Ch)&&(Ch<='~')){
1370  if (Ch=='&'){XmlChA+="&amp;";}
1371  else if (Ch=='>'){XmlChA+="&lt;";}
1372  else if (Ch=='<'){XmlChA+="&gt;";}
1373  else if (Ch=='\''){XmlChA+="&apos;";}
1374  else if (Ch=='\"'){XmlChA+="&quot;";}
1375  else {XmlChA+=Ch;}
1376  } else {
1377  XmlChA+="&#"; XmlChA+=TUInt::GetStr(Ch); XmlChA+=";";
1378  }
1379  }
1380  return XmlChA;
1381 }
1382 
1383 bool TXmlDoc::SkipTopTag(const PSIn& SIn){
1384  bool Ok=true;
1385  TXmlLx Lx(SIn, xspIntact);
1386  try {
1387  Lx.GetSym();
1388  // [22] prolog ::= XMLDecl? Misc* (doctypedecl Misc*)?
1389  if (Lx.Sym==xsyXmlDecl){Lx.GetSym();}
1390  LoadTxtMiscStar(Lx);
1391  if (Lx.Sym==xsyDocTypeDecl){Lx.GetSym();}
1392  LoadTxtMiscStar(Lx);
1393  Ok=true;
1394  }
1395  catch (PExcept Except){
1396  Ok=false;
1397  }
1398  return Ok;
1399 }
1400 
1402  PXmlDoc Doc=TXmlDoc::New();
1403  // [1] document ::= prolog element Misc*
1404  try {
1405  Lx.GetSym();
1406  // [22] prolog ::= XMLDecl? Misc* (doctypedecl Misc*)?
1407  if (Lx.Sym==xsyXmlDecl){Lx.GetSym();}
1408  LoadTxtMiscStar(Lx);
1409  if (Lx.Sym==xsyDocTypeDecl){Lx.GetSym();}
1410  LoadTxtMiscStar(Lx);
1411  Doc->Tok=LoadTxtElement(Lx);
1412  LoadTxtMiscStar(Lx);
1413  Doc->Ok=true; Doc->MsgStr="Ok";
1414  }
1415  catch (PExcept& Except){
1416  Doc->Ok=false; Doc->MsgStr=Except->GetMsgStr();
1417  }
1418  return Doc;
1419 }
1420 
1421 PXmlDoc TXmlDoc::LoadTxt(const PSIn& SIn, const TXmlSpacing& Spacing){
1422  TXmlLx Lx(SIn, Spacing); return LoadTxt(Lx);
1423 }
1424 
1425 PXmlDoc TXmlDoc::LoadTxt(const TStr& FNm, const TXmlSpacing& Spacing){
1426  PSIn SIn=TFIn::New(FNm); return LoadTxt(SIn, Spacing);
1427 }
1428 
1430  const TStr& FNm, TXmlDocV& XmlDocV, const TXmlSpacing& Spacing){
1431  XmlDocV.Clr();
1432  PSIn SIn=TFIn::New(FNm);
1433  TXmlLx Lx(SIn, Spacing);
1434  PXmlDoc XmlDoc;
1435  forever {
1436  Lx.SkipWs();
1437  XmlDoc=LoadTxt(Lx);
1438  if (XmlDoc->IsOk()){XmlDocV.Add(XmlDoc);}
1439  else {break;}
1440  }
1441 }
1442 
1444  PSIn SIn=TStrIn::New(Str);
1445  return LoadTxt(SIn);
1446 }
1447 
1449  PSOut SOut=TMOut::New(); TMOut& MOut=*(TMOut*)SOut();
1450  SaveTxt(SOut);
1451  Str=MOut.GetAsStr();
1452 }
1453 
1455 // Fast and dirty XML parser
1456 // very basic it does only <item>string</item>, no comments, no arguments
1458  if (NextSym != xsyUndef) {
1461  return Sym;
1462  }
1463  SymStr.Clr();
1464  char Ch;
1465  while (TCh::IsWs(Ch=GetCh())) { }
1466  if (Ch == TCh::EofCh) { Sym = xsyEof; return xsyEof; }
1467  if (Ch == '<') { // load tag
1468  Ch = GetCh();
1469  if (Ch == '/') { Sym = xsyETag; }
1470  else { Sym = xsySTag; SymStr.Push(Ch); }
1471  while((Ch=GetCh())!='>' && Ch!=TCh::EofCh) { SymStr.Push(Ch); }
1472  const int StrLen = SymStr.Len();
1473  if (StrLen > 1 && SymStr[StrLen-1] == '/') {
1474  Sym = xsyETag; SymStr[StrLen-1] = 0;
1475  for (char *c = SymStr.CStr()+StrLen-2; TCh::IsWs(*c); c--) { *c=0; }
1476  }
1477  } else { // load string
1478  _SymStr.Clr(); _SymStr.Push(Ch);
1479  while (! RSIn.Eof() && RSIn.PeekCh() != '<') { _SymStr.Push(GetCh()); }
1481  Sym = xsyStr;
1482  }
1483  if (Ch == TCh::EofCh) { SymStr.Clr(); Sym = xsyEof; return xsyEof; }
1484  return Sym;
1485 }
1486 
1488  GetSym();
1489  _SymStr = SymStr;
1490  return Sym;
1491 }
1492 
1494  if (NextSym == xsyUndef) {
1495  const TXmlLxSym TmpSim=Sym;
1496  const TChA TmpSymStr=SymStr;
1498  Sym=TmpSim;
1499  SymStr=TmpSymStr;
1500  }
1501  return NextSym;
1502 }
1503 
1505  PeekSym();
1506  _SymStr = NextSymStr;
1507  return NextSym;
1508 }
1509 
1510 void TXmlParser::SkipTillTag(const TChA& _SymStr) {
1511  while(PeekSym() != xsyEof) {
1512  if (NextSymStr == _SymStr) { return; }
1513  GetSym();
1514  }
1515 }
1516 
1517 // get <tag>value</tag>
1518 void TXmlParser::GetTagVal(const TChA& TagStr, TChA& TagVal) {
1519  EAssertR(GetTag(TagStr) == xsySTag, TStr::Fmt("Expected '<%s>'. Found '%s'", TagStr.CStr(), SymStr.CStr()).CStr());
1520  EAssertR(GetSym(TagVal) == xsyStr, "Expected string tag.");
1521  EAssertR(GetTag(TagStr) == xsyETag, TStr::Fmt("Expected '</%s>'. Found '%s'", TagStr.CStr(), SymStr.CStr()).CStr());
1522 }
1523 
1525  GetSym();
1526  EAssertR(TagStr==SymStr, TStr::Fmt("Expected xml symbol '%s'. Found '%s'",
1527  TagStr.CStr(), SymStr.CStr()).CStr());
1528  return Sym;
1529 }
1530 
1531 void TXmlParser::GetPlainStrFromXmlStr(const TChA& XmlStr, TChA& PlainChA) {
1532  static TChA EntityNm;
1533  PlainChA.Clr();
1534  const char *Ch = XmlStr.CStr();
1535  while (*Ch){
1536  if (*Ch!='&'){ PlainChA+=*Ch; Ch++; }
1537  else {
1538  if (*++Ch=='#'){
1539  TChA RefChA; int RefCd=0;
1540  if (*++Ch=='x'){
1541  forever { Ch++;
1542  if (TCh::IsHex(*Ch)){ RefChA+=*Ch; RefCd=RefCd*16+TCh::GetHex(*Ch); }
1543  else { break; } }
1544  } else { // decimal character code
1545  forever {
1546  if (TCh::IsNum(*Ch)){ RefChA+=*Ch; RefCd=RefCd*10+TCh::GetNum(*Ch); }
1547  else { break; } Ch++; }
1548  }
1549  if ((!RefChA.Empty())&&(*Ch==';')){
1550  Ch++; const uchar RefCh=uchar(RefCd); PlainChA+=RefCh; }
1551  } else {
1552  EntityNm.Clr();
1553  while ((*Ch)&&(*Ch!=';')){EntityNm+=*Ch; Ch++;}
1554  if ((!EntityNm.Empty())&&(*Ch==';')){ Ch++;
1555  if (EntityNm=="quot"){PlainChA+='"';}
1556  else if (EntityNm=="amp"){PlainChA+='&';}
1557  else if (EntityNm=="apos"){PlainChA+='\'';}
1558  else if (EntityNm=="lt"){PlainChA+='<';}
1559  else if (EntityNm=="gt"){PlainChA+='>';}
1560  }
1561  }
1562  }
1563  }
1564 }
TStr MsgStr
Definition: xml.h:329
#define IAssert(Cond)
Definition: bd.h:262
static bool IsHex(const char &Ch)
Definition: dt.h:1067
void SaveTxt(const PSOut &SOut)
Definition: xml.h:383
TChA NextSymStr
Definition: xml.h:405
void SkipTillTag(const TChA &_SymStr)
Definition: xml.cpp:1510
TChA SymStr
Definition: xml.h:405
TBSet PubidChSet
Definition: xml.h:46
TXmlLxSym GetSym()
Definition: xml.cpp:757
int GetArgs() const
Definition: xml.h:262
void PutSubTok(const PXmlTok &Tok, const int &SubTokN=-1)
Definition: xml.cpp:1134
TStr TagNm
Definition: xml.h:141
bool IsChar(const uchar &Ch) const
Definition: xml.h:68
void GetXmlDecl()
Definition: xml.cpp:531
TChA TxtChA
Definition: xml.h:140
void GetTagValV(const TStr &TagNm, const bool &XmlP, TStrV &ValV) const
Definition: xml.cpp:1171
Definition: xml.h:93
void GetEntity()
Definition: xml.cpp:690
Definition: xml.h:91
TStr GetStr() const
Definition: dt.h:1197
void GetArg(const int &ArgN, TStr &ArgNm, TStr &ArgVal) const
Definition: xml.h:263
int Len() const
Definition: dt.h:487
Definition: xml.h:93
void GetArg(const int &ArgN, TStr &ArgNm, TStr &ArgVal) const
Definition: xml.h:166
bool IsInt(const bool &Check, const int &MnVal, const int &MxVal, int &Val) const
Definition: dt.cpp:1159
TStr GetTagTokStrArgVal(const TStr &TagPath, const TStr &ArgNm, const TStr &DfVal=TStr()) const
Definition: xml.cpp:1356
bool GetTagTokBoolArgVal(const TStr &TagPath, const TStr &ArgNm, const bool &DfVal=false) const
Definition: xml.cpp:1332
void GetNData()
Definition: xml.cpp:622
TBSet CharChSet
Definition: xml.h:45
bool IsPEntityNm(const TStr &EntityNm, TStr &EntityVal) const
Definition: xml.h:179
TXmlLxSym NextSym
Definition: xml.h:404
Definition: bits.h:313
static TStr GetChRefFromYuEntRef(const TStr &YuEntRefStr)
Definition: xml.cpp:1072
TInt Chs
Definition: xml.h:44
static bool IsNum(const char &Ch)
Definition: dt.h:1064
static TStr GetXmlLxSymStr(const TXmlLxSym &XmlLxSym)
Definition: xml.cpp:904
virtual int PutCh(const char &Ch)=0
PSIn SIn
Definition: xml.h:101
PXmlTok Tok
Definition: xml.h:330
static TStr GetUsAsciiStrFromXmlStr(const TStr &EntRefStr)
Definition: xml.cpp:1056
Definition: xml.h:94
void AddArg(const TStr &ArgNm, const TStr &ArgVal)
Definition: xml.h:161
#define forever
Definition: bd.h:6
int Len() const
Definition: dt.h:134
void GetEq()
Definition: xml.cpp:408
bool Empty() const
Definition: dt.h:260
#define Fail
Definition: bd.h:238
bool Ok
Definition: xml.h:328
static TStr GetTagNm(const TStr &TypeNm)
Definition: xml.cpp:5
bool Empty() const
Definition: bd.h:501
TStr GetName()
Definition: xml.cpp:416
void PutCh(const int &ChN, const char &Ch)
Definition: dt.h:278
TXmlLxSym GetSym()
Definition: xml.cpp:1457
static PXmlTok New()
Definition: xml.h:212
void Clr()
Definition: dt.h:258
TChA ChStack
Definition: xml.h:103
void GetWs(const bool &IsRq)
Definition: xml.cpp:331
TStr GetSymStr() const
Definition: xml.cpp:835
TSizeTy Len() const
Returns the number of elements in the vector.
Definition: ds.h:575
double GetFltArgVal(const TStr &ArgNm, const double &DfVal=0) const
Definition: xml.cpp:1119
TSOut * SOut
Definition: xml.h:23
static TStr GetPlainStrFromXmlStr(const TStr &XmlStr)
Definition: xml.cpp:991
Definition: xml.h:90
static TStr GetXmlStrFromPlainMem(const TMem &PlainMem)
Definition: xml.cpp:945
TSIn & RSIn
Definition: xml.h:401
static int GetHex(const char &Ch)
Definition: dt.h:1069
TXmlTokV SubTokV
Definition: xml.h:203
int Len() const
Definition: dt.h:259
bool IsEntityNm(const TStr &EntityNm, TStr &EntityVal) const
Definition: xml.h:83
bool IsFirstNameCh(const uchar &Ch) const
Definition: xml.h:78
TStrStrH EntityNmToValH
Definition: xml.h:47
PXmlTok GetSubTok(const int &SubTokN) const
Definition: xml.h:294
static int64 GetInt64Arg(const PXmlTok &XmlTok, const TStr &Nm)
Definition: xml.cpp:89
static TXmlChDef ChDef
Definition: xml.h:100
void GetAttList()
Definition: xml.cpp:665
void SetChTy(TBSet &ChSet, const int &MnCh, const int &MxCh=-1)
Definition: xml.cpp:190
int GetTagTokIntArgVal(const TStr &TagPath, const TStr &ArgNm, const int &DfVal=0) const
Definition: xml.cpp:1340
static PSOut New(const int &MxBfL=1024)
Definition: fl.h:506
TStr GetAsStr() const
Definition: fl.cpp:869
void GetPI()
Definition: xml.cpp:562
void GetTagTokV(const TStr &TagPath, TXmlTokV &XmlTokV) const
Definition: xml.cpp:1319
void EThrow(const TStr &MsgStr) const
Definition: xml.cpp:885
static PXmlDoc LoadStr(const TStr &Str)
Definition: xml.cpp:1443
TBSet ExtChSet
Definition: xml.h:45
TChA _SymStr
Definition: xml.h:402
void ToNrSpacing()
Definition: xml.cpp:270
bool IsTagTok(const TStr &TagPath, PXmlTok &TagTok) const
Definition: xml.h:350
Definition: xml.h:96
TStr GetTokStr(const bool &XmlP=true) const
Definition: xml.h:316
void PutEntityVal(const TStr &Nm, const TStr &Val)
Definition: xml.h:177
Definition: dt.h:77
uchar PrevCh
Definition: xml.h:104
void SplitOnCh(TStr &LStr, const char &SplitCh, TStr &RStr) const
Definition: dt.cpp:901
TStr GetStalVal()
Definition: xml.cpp:513
char LastLastCh() const
Definition: dt.h:282
static const char EofCh
Definition: dt.h:1037
uchar GetCh()
Definition: xml.cpp:260
double GetTagTokFltArgVal(const TStr &TagPath, const TStr &ArgNm, const double &DfVal=0) const
Definition: xml.cpp:1348
static bool GetBoolArg(const PXmlTok &XmlTok, const TStr &Nm)
Definition: xml.cpp:59
void Incl(const int &BitN)
Definition: bits.h:344
static PSIn New(const TStr &FNm)
Definition: fl.cpp:290
TSIn & RSIn
Definition: xml.h:102
bool IsPubid(const uchar &Ch) const
Definition: xml.h:74
static bool IsWs(const char &Ch)
Definition: dt.h:1060
char GetCh()
Definition: xml.h:407
void Clr(const bool &DoDel=true, const TSizeTy &NoDelLim=-1)
Clears the contents of the vector.
Definition: ds.h:1022
int ChangeStrAll(const TStr &SrcStr, const TStr &DstStr, const bool &FromStartP=false)
Definition: dt.cpp:1141
TXmlLxSym GetTag(const TChA &TagStr)
Definition: xml.cpp:1524
void AddSubTok(const PXmlTok &Tok)
Definition: xml.h:292
char * CStr()
Definition: dt.h:255
static void Throw(const TStr &MsgStr)
Definition: ut.h:187
void SaveStr(TStr &Str)
Definition: xml.cpp:1448
virtual bool Eof()=0
bool IsBool(bool &Val) const
Definition: dt.cpp:1153
Definition: xml.h:98
void AddTokToChA(const bool &XmlP, TChA &ChA) const
Definition: xml.cpp:1185
bool Eof() const
Definition: fl.h:548
static PSIn New(const TStr &Str)
Definition: dt.h:708
Definition: xml.h:93
static int GetNum(const char &Ch)
Definition: dt.h:1066
void GetExternalId()
Definition: xml.cpp:609
TStr GetStr() const
Definition: dt.h:1279
TStrKdV ArgNmValKdV
Definition: xml.h:142
static TStr GetTokVStr(const TXmlTokV &TokV, const bool &XmlP=true)
Definition: xml.cpp:1219
char LastCh() const
Definition: dt.h:281
Definition: xml.h:92
int LnChN
Definition: xml.h:105
TXmlObjSerTagNm(TSOut &_SOut, const bool &ETagP, const TStr &Nm, const TStr &TypeNm, const TStr &ArgNm="", const TStr &ArgVal="")
Definition: xml.cpp:121
static double GetFltArg(const PXmlTok &XmlTok, const TStr &Nm)
Definition: xml.cpp:104
int GetIntArgVal(const TStr &ArgNm, const int &DfVal=0) const
Definition: xml.cpp:1109
void PutPEntityVal(const TStr &Nm, const TStr &Val)
Definition: xml.h:181
TStr GetLc() const
Definition: dt.h:499
Definition: xml.h:93
TStr GetSymStr() const
Definition: xml.h:242
void SetEntityVal(const TStr &Nm, const TStr &Val)
Definition: xml.cpp:204
TXmlLxSym Sym
Definition: xml.h:404
TBSet CombChSet
Definition: xml.h:45
static char GetArgValQCh(const TStr &ArgVal)
Definition: xml.h:171
unsigned char uchar
Definition: bd.h:10
void Gen(const int &_Bits)
Definition: bits.cpp:182
Definition: xml.h:90
bool IsArg(const TStr &ArgNm) const
Definition: xml.h:265
bool GetBoolArgVal(const TStr &ArgNm, const bool &DfVal=false) const
Definition: xml.cpp:1089
TXmlSpacing
Definition: xml.h:96
void Trunc()
Definition: dt.cpp:420
Definition: fl.h:128
TStr GetVersionNum()
Definition: xml.cpp:473
Definition: xml.h:93
PXmlTok GetTagTok(const TStr &TagPath) const
Definition: xml.cpp:1298
static const char LfCh
Definition: dt.h:1035
bool IsTag() const
Definition: xml.h:247
static PXmlTok GetTok(TXmlLx &Lx)
Definition: xml.cpp:1228
TStr GetStr() const
Definition: dt.h:678
TXmlLxSym Sym
Definition: xml.h:200
int GetArgs() const
Definition: xml.h:165
Definition: xml.h:198
TStr GetReference()
Definition: xml.cpp:340
Definition: fl.h:495
void ClrSubTok()
Definition: xml.h:295
static int GetIntArg(const PXmlTok &XmlTok, const TStr &Nm)
Definition: xml.cpp:74
Definition: xml.h:93
Definition: dt.h:201
bool IsName(const uchar &Ch) const
Definition: xml.h:73
#define EAssert(Cond)
Definition: bd.h:280
static TStr GetXmlStr(const TStr &Str)
Definition: xml.cpp:1364
TStr GetEncName()
Definition: xml.cpp:493
TStr GetStr() const
Definition: xml.h:244
TXmlChDef()
Definition: xml.cpp:208
TBSet NameChSet
Definition: xml.h:46
void GetNotation()
Definition: xml.cpp:722
TStr Str
Definition: xml.h:201
bool IsFlt(const bool &Check, const double &MnVal, const double &MxVal, double &Val, const char &DecDelimCh='.') const
Definition: dt.cpp:1265
PXmlTok GetTagTok(const TStr &TagPath) const
Definition: xml.cpp:1142
TStrKdV ArgNmValV
Definition: xml.h:202
long long int64
Definition: bd.h:27
TStr GetFPosStr() const
Definition: xml.cpp:895
TXmlLxSym
Definition: xml.h:89
static bool IsTagNm(const TStr &Str)
Definition: xml.cpp:927
static bool SkipTopTag(const PSIn &SIn)
Definition: xml.cpp:1383
Definition: dt.h:412
char GetCh()
Definition: fl.h:549
TXmlLxSym PeekSym()
Definition: xml.cpp:1493
bool Empty() const
Definition: dt.h:488
static TStr Fmt(const char *FmtStr,...)
Definition: dt.cpp:1599
TStr TagNm
Definition: xml.h:22
Definition: xml.h:92
void GetCDSect()
Definition: xml.cpp:733
TXmlSpacing Spacing
Definition: xml.h:106
int PutStr(const char *CStr)
Definition: fl.cpp:117
void GetTagTokV(const TStr &TagPath, TXmlTokV &XmlTokV) const
Definition: xml.cpp:1158
TSizeTy SearchForw(const TVal &Val, const TSizeTy &BValN=0) const
Returns the position of an element with value Val.
Definition: ds.h:1552
Definition: xml.h:92
TStr GetHex() const
Definition: dt.h:512
static const char CrCh
Definition: dt.h:1036
#define EAssertR(Cond, MsgStr)
Definition: bd.h:283
static PXmlDoc LoadTxt(TXmlLx &Lx)
Definition: xml.cpp:1401
static void GetPlainStrFromXmlStr(const TChA &XmlStr, TChA &PlainChA)
Definition: xml.cpp:1531
virtual TStr GetSNm() const
Definition: fl.cpp:20
TStr GetAttValue()
Definition: xml.cpp:457
TStr GetPEReference()
Definition: xml.cpp:397
void Push(const char &Ch)
Definition: dt.h:264
void GetElement()
Definition: xml.cpp:656
static PXmlTok LoadTxtElement(TXmlLx &Lx)
Definition: xml.cpp:1249
void ClrArgV()
Definition: xml.h:160
TBSet DigitChSet
Definition: xml.h:46
Definition: xml.h:90
void PutTagTokStr(const TStr &TagPath, const TStr &TokStr) const
Definition: xml.cpp:1312
void SkipWs()
Definition: xml.cpp:752
TXmlLxSym GetSym() const
Definition: xml.h:241
int LnN
Definition: xml.h:105
bool IsEntityNm(const TStr &EntityNm, TStr &EntityVal) const
Definition: xml.h:175
static const uchar Mx
Definition: dt.h:1095
TXmlLxSym Sym
Definition: xml.h:139
void GetDocTypeDecl()
Definition: xml.cpp:627
virtual char GetCh()=0
int EncodeUtf8(const TIntV &src, TIntV &dest) const
Definition: unicode.h:1792
int ChN
Definition: xml.h:105
void GetComment()
Definition: xml.cpp:436
TStr GetTagVal(const TStr &TagNm, const bool &XmlP) const
Definition: xml.cpp:1180
virtual char PeekCh()=0
~TXmlObjSerTagNm()
Definition: xml.cpp:182
char Pop()
Definition: dt.h:265
TSizeTy Add()
Adds a new element at the end of the vector, after its current last element.
Definition: ds.h:602
void SplitOnLastCh(TStr &LStr, const char &SplitCh, TStr &RStr) const
Definition: dt.cpp:912
static void AssertXmlHd(const PXmlTok &XmlTok, const TStr &Nm, const TStr &TypeNm)
Definition: xml.cpp:22
static void LoadTxtMiscStar(TXmlLx &Lx)
Definition: xml.cpp:1243
TStr GetSystemLiteral()
Definition: xml.cpp:583
bool IsWs(const uchar &Ch) const
Definition: xml.h:76
TStr GetPubidLiteral()
Definition: xml.cpp:596
static const TStr TrueStr
Definition: dt.h:981
TDat & AddDat(const TKey &Key)
Definition: hash.h:238
TBSet LetterChSet
Definition: xml.h:46
static PXmlDoc New()
Definition: xml.h:335
bool IsInt64(const bool &Check, const int64 &MnVal, const int64 &MxVal, int64 &Val) const
Definition: dt.cpp:1212
Definition: xml.h:42
uchar Ch
Definition: xml.h:104
TStr GetEntityValue()
Definition: xml.cpp:674
Definition: fl.h:535
Definition: xml.h:91
static TStrStrH TypeNmToTagNmH
Definition: xml.h:7
TKeyDat< TStr, TStr > TStrKd
Definition: ds.h:405
int GetSubToks() const
Definition: xml.h:293
void GetTagVal(const TChA &TagStr, TChA &TagVal)
Definition: xml.cpp:1518
Definition: dt.h:1090
TStr GetStrArgVal(const TStr &ArgNm, const TStr &DfVal=TStr()) const
Definition: xml.cpp:1129
static TStr GetXmlStrFromPlainStr(const TChA &PlainChA)
Definition: xml.cpp:968