ROOT  6.06/09
Reference Guide
TSchemaRule.cxx
Go to the documentation of this file.
1 // @(#)root/core:$Id$
2 // author: Lukasz Janyst <ljanyst@cern.ch>
3 
4 #include "TSchemaRule.h"
5 #include "TSchemaRuleProcessor.h"
6 #include "TObjArray.h"
7 #include "TObjString.h"
8 #include "TNamed.h"
9 #include <utility>
10 #include <iostream>
11 #include <vector>
12 #include <list>
13 #include <string>
14 #include <cstdlib>
15 #include "TROOT.h"
16 #include "Riostream.h"
17 
18 #include "RConversionRuleParser.h"
19 
20 ClassImp(TSchemaRule)
21 
22 using namespace ROOT;
23 
24 namespace {
25  static Bool_t IsIrrelevantCharacter(char c)
26  {
27  return (c == ' ' || c == '\n' || c == '\t');
28  }
29 
30  static void AdvanceOverIrrelevantCharacter(const char*& str)
31  {
32  while (IsIrrelevantCharacter(*str)) {
33  ++str;
34  }
35  }
36 
37  // check if lhs matches rhs if we ignore irelevant white space differences
38 
39  static Bool_t IsCodeEquivalent(const TString& lhs, const TString& rhs)
40  {
41  Bool_t result = kTRUE;
42 
43  if (lhs != rhs) {
44  const char null = '\0';
45  const char* left = lhs.Data();
46  const char* right = rhs.Data();
47  Bool_t literal = false;
48  // skip initial white space
49  AdvanceOverIrrelevantCharacter(left);
50  AdvanceOverIrrelevantCharacter(right);
51 
52  while (*left != null || *right != null) {
53  // If both chars are white space, skip consecutive white space
54  if (!literal && IsIrrelevantCharacter(*left) && IsIrrelevantCharacter(*right)) {
55  AdvanceOverIrrelevantCharacter(left);
56  AdvanceOverIrrelevantCharacter(right);
57  continue;
58  }
59  // Check if one string has trailing white space, and the other doesn't.
60  if (*left == null || *right == null) {
61  AdvanceOverIrrelevantCharacter(left);
62  AdvanceOverIrrelevantCharacter(right);
63  result = (*left == null && *right == null);
64  break;
65  }
66 
67  if (*left != *right) {
68  result = kFALSE;
69  break;
70  }
71 
72  if (*left == '"') {
73  literal = !literal;
74  }
75  ++left;
76  ++right;
77  }
78  }
79  return result;
80  }
81 
82 }
83 
84 ////////////////////////////////////////////////////////////////////////////////
85 /// Default Constructor.
86 
87 TSchemaRule::TSchemaRule(): fVersionVect( 0 ), fChecksumVect( 0 ),
88  fTargetVect( 0 ), fSourceVect( 0 ),
89  fIncludeVect( 0 ), fEmbed( kTRUE ),
90  fReadFuncPtr( 0 ), fReadRawFuncPtr( 0 ),
91  fRuleType( kNone )
92 {
93 }
94 
95 ////////////////////////////////////////////////////////////////////////////////
96 /// Destructor.
97 
99 {
100  delete fVersionVect;
101  delete fChecksumVect;
102  delete fTargetVect;
103  delete fSourceVect;
104  delete fIncludeVect;
105 }
106 
107 ////////////////////////////////////////////////////////////////////////////////
108 /// Copy Constructor.
109 
111  fVersionVect( 0 ), fChecksumVect( 0 ),
112  fTargetVect( 0 ), fSourceVect( 0 ),
113  fIncludeVect( 0 ), fEmbed( kTRUE ),
114  fReadFuncPtr( 0 ), fReadRawFuncPtr( 0 ),
115  fRuleType( kNone )
116 {
117  *this = rhs;
118 }
119 
120 ////////////////////////////////////////////////////////////////////////////////
121 /// Copy operator.
122 
124 {
125  if( this != &rhs ) {
126  fVersion = rhs.fVersion;
127  fChecksum = rhs.fChecksum;
129  fTarget = rhs.fTarget;
130  fSource = rhs.fSource;
131  fInclude = rhs.fInclude;
132  fCode = rhs.fCode;
133  fEmbed = rhs.fEmbed;
136  fRuleType = rhs.fRuleType;
137  fAttributes = rhs.fAttributes;
138  }
139  return *this;
140 }
141 
142 ////////////////////////////////////////////////////////////////////////////////
143 /// Return true if the rule have the same effects.
144 
146 {
147  if( this != &rhs ) {
148  Bool_t result = ( fVersion == rhs.fVersion
149  && fChecksum == rhs.fChecksum
150  && fSourceClass == rhs.fSourceClass
151  && fTargetClass == rhs.fTargetClass
152  && fSource == rhs.fSource
153  && fTarget == rhs.fTarget
154  && fInclude == rhs.fInclude
155  && IsCodeEquivalent(fCode, rhs.fCode)
156  && fEmbed == rhs.fEmbed
157  && fRuleType == rhs.fRuleType
158  && fAttributes == rhs.fAttributes );
159  if (result &&
160  ( (fReadRawFuncPtr != rhs.fReadRawFuncPtr && fReadRawFuncPtr != 0 && rhs.fReadRawFuncPtr != 0)
161  || (fReadFuncPtr != rhs.fReadFuncPtr && fReadFuncPtr != 0 && rhs.fReadFuncPtr != 0) ) )
162  {
163  result = kFALSE;
164  }
165 
166  return result;
167  }
168  return kTRUE;
169 }
170 
171 ////////////////////////////////////////////////////////////////////////////////
172 /// The ls function lists the contents of a class on stdout. Ls output
173 /// is typically much less verbose then Dump().
174 
175 void TSchemaRule::ls(Option_t *targetname) const
176 {
178  std::cout << "Schema Evolution Rule: ";
179  if (fRuleType==kReadRule) std::cout << "read ";
180  else if (fRuleType==kReadRawRule) std::cout << "readraw ";
181  std::cout << "\n";
184  std::cout << "sourceClass=\"" << fSourceClass << "\" ";
185  if (fVersion.Length()) std::cout << "version=\"" << fVersion << "\" ";
186  if (fChecksum.Length()) std::cout << "checksum=\"" << fChecksum << "\" ";
187  if (targetname && targetname[0]) std::cout << "targetClass=\"" << targetname << "\" ";
188  else std::cout << "targetClass\"" << fTargetClass << "\" ";
189  std::cout << "\n";
191  std::cout << "source=\"" << fSource << "\" ";
192  std::cout << "target=\"" << fTarget << "\" ";
193  std::cout << "\n";
194  if (fInclude.Length()) {
196  std::cout << "include=\"" << fInclude << "\" " << "\n";
197  }
198  if (fAttributes.Length()) {
200  std::cout << "attributes=\"" << fAttributes << "\"" << "\n";
201  }
202  if (fCode.Length()) {
204  std::cout << "code=\"{" << fCode << "}\" "
205  << "\n";
206  }
208 }
209 
210 ////////////////////////////////////////////////////////////////////////////////
211 /// Add to the string 'out' the string representation of the rule.
212 /// if options contains:
213 /// 's' : add the short form of the rule is possible
214 /// 'x' : add the xml form of the rule
215 
216 void TSchemaRule::AsString(TString &out, const char *options) const
217 {
218  TString opt(options);
219  opt.ToLower();
220  Bool_t shortform = opt.Contains('s');
221  Bool_t xmlform = opt.Contains('x');
222 
223  TString end;
224  if (xmlform) {
225  /*
226  <read sourceClass="ClassA" version="[2]" targetClass="ClassA" source="int m_unit;" target="m_unit" >
227  <![CDATA[ { m_unit = 10*onfile.m_unit; } ]]>
228  </read>
229  */
230  shortform = kFALSE;
231  out += "<";
232  if (fRuleType==kReadRule) { out += "read "; end = "</read>"; }
233  else if (fRuleType==kReadRawRule) { out += "readraw "; end = "</readraw>"; }
234  else { out += "-- "; end = "-->"; }
235 
236  } else {
237  if (!shortform || fRuleType!=kReadRule) {
238  out += "type=";
239  if (fRuleType==kReadRule) out += "read ";
240  else if (fRuleType==kReadRawRule) out += "readraw ";
241  else out += " ";
242  }
243  }
244  if (!shortform || (fSourceClass != fTargetClass) ) {
245  out += "sourceClass=\"" + fSourceClass + "\" ";
246  out += "targetClass=\"" + fTargetClass + "\" ";
247  } else {
248  out += fSourceClass + " ";
249  }
250  if (shortform && fTarget == fSource) {
251  out += fSource + " ";
252  }
253  if (!shortform || (fVersion != "[1-]")) {
254  if (fVersion.Length()) out += "version=\"" + fVersion + "\" ";
255  }
256  if (fChecksum.Length()) out += "checksum=\"" + fChecksum + "\" ";
257  if (!shortform || fTarget != fSource) {
258  out += "source=\"" + fSource + "\" ";
259  out += "target=\"" + fTarget + "\" ";
260  }
261  if (fInclude.Length()) out += "include=\"" + fInclude + "\" ";
262  if (fAttributes.Length()) out += "attributes=\"" + fAttributes + "\" ";
263  if (xmlform) {
264  out += "> ";
265  }
266  if (xmlform) {
267  if (fCode.Length()) {
268  out += "\n<![CDATA[ { " + fCode + " ]]>\n ";
269  } else if (fReadFuncPtr) {
270  // Can we guess?
271  // out += "code=\" + nameof(fReadFuncPtr) + "\" ";
272  } else if (fReadRawFuncPtr) {
273  // Can we guess?
274  // out += "code=\" + nameof(fReadRawFuncPtr) + "\" ";
275  }
276  } else {
277  if (fCode.Length()) {
278  out += "code=\"{" + fCode + "}\" ";
279  } else if (fReadFuncPtr) {
280  // Can we guess?
281  // out += "code=\" + nameof(fReadFuncPtr) + "\" ";
282  } else if (fReadRawFuncPtr) {
283  // Can we guess?
284  // out += "code=\" + nameof(fReadRawFuncPtr) + "\" ";
285  }
286  }
287  if (xmlform) {
288  out += end;
289  }
290 }
291 
292 ////////////////////////////////////////////////////////////////////////////////
293 /// Zero out this rule object.
294 
295 void TSchemaRule::Clear( const char * /* option */)
296 {
297  fVersion.Clear();
298  fChecksum.Clear();
300  fTarget.Clear();
301  fSource.Clear();
302  fInclude.Clear();
303  fCode.Clear();
304  fAttributes.Clear();
305  fReadRawFuncPtr = 0;
306  fReadFuncPtr = 0;
307  fRuleType = kNone;
308  delete fVersionVect; fVersionVect = 0;
309  delete fChecksumVect; fChecksumVect = 0;
310  delete fTargetVect; fTargetVect = 0;
311  delete fSourceVect; fSourceVect = 0;
312  delete fIncludeVect; fIncludeVect = 0;
313 }
314 
315 ////////////////////////////////////////////////////////////////////////////////
316 /// Set the content fot this object from the rule
317 /// See TClass::AddRule for details on the syntax.
318 
319 Bool_t TSchemaRule::SetFromRule( const char *rule )
320 {
321  //-----------------------------------------------------------------------
322  // Parse the rule and check it's validity
323  /////////////////////////////////////////////////////////////////////////////
324 
325  ROOT::MembersMap_t rule_values;
326 
327  std::string error_string;
328  if( !ParseRule( rule, rule_values, error_string) ) {
329  Error("SetFromRule","The rule (%s) is invalid: %s",rule,error_string.c_str());
330  return kFALSE;
331  }
332  ROOT::MembersMap_t ::const_iterator it1;
333 
334  it1 = rule_values.find( "type" );
335  if( it1 != rule_values.end() ) {
336  if (it1->second == "read" || it1->second == "Read") {
338  } else if (it1->second == "readraw" || it1->second == "ReadRaw") {
340  } else {
342  }
343  } else {
344  // Default to read.
346  }
347  it1 = rule_values.find( "targetClass" );
348  if( it1 != rule_values.end() ) SetTargetClass( it1->second );
349  it1 = rule_values.find( "sourceClass" );
350  if( it1 != rule_values.end() ) SetSourceClass( it1->second );
351  it1 = rule_values.find( "target" );
352  if( it1 != rule_values.end() ) SetTarget( it1->second );
353  it1 = rule_values.find( "source" );
354  if( it1 != rule_values.end() ) SetSource( it1->second );
355  it1 = rule_values.find( "version" );
356  if( it1 != rule_values.end() ) SetVersion( it1->second );
357  it1 = rule_values.find( "checksum" );
358  if( it1 != rule_values.end() ) SetChecksum( it1->second );
359  it1 = rule_values.find( "embed" );
360  if( it1 != rule_values.end() ) SetEmbed( it1->second == "false" ? false : true );
361  it1 = rule_values.find( "include" );
362  if( it1 != rule_values.end() ) SetInclude( it1->second );
363  it1 = rule_values.find( "attributes" );
364  if( it1 != rule_values.end() ) SetAttributes( it1->second );
365  it1 = rule_values.find( "code" );
366  if( it1 != rule_values.end() ) SetCode( it1->second );
367  // if (code is functioname) {
368  // switch (ruleobj->GetRuleType() ) {
369  // case kRead: SetReadFunctionPointer( )
370  // case kReadRewa: SetReadRawFunctionPointer( )
371  // }
372 
373  return kTRUE;
374 }
375 
376 ////////////////////////////////////////////////////////////////////////////////
377 /// Set the version string - returns kFALSE if the format is incorrect
378 
380 {
381  fVersion = "";
382  Bool_t ret = ProcessVersion( version );
383  if( ret )
384  fVersion = version;
385  return ret;
386 }
387 
388 ////////////////////////////////////////////////////////////////////////////////
389 /// Get the version string.
390 
391 const char *TSchemaRule::GetVersion() const
392 {
393  return fVersion;
394 }
395 
396 
397 ////////////////////////////////////////////////////////////////////////////////
398 /// Check if given version number is defined in this rule
399 
401 {
402  if( fVersion == "" )
403  return kFALSE;
404 
405  if( !fVersionVect )
406  ProcessVersion( fVersion ); // At this point the version string should always be correct
407 
408  if (version == -1) {
409  version = 1;
410  }
411 
412  std::vector<std::pair<Int_t, Int_t> >::iterator it;
413  for( it = fVersionVect->begin(); it != fVersionVect->end(); ++it ) {
414  if( version >= it->first && version <= it->second )
415  return kTRUE;
416  }
417  return kFALSE;
418 }
419 
420 ////////////////////////////////////////////////////////////////////////////////
421 /// Set the checksum string - returns kFALSE if the format is incorrect
422 
424 {
425  fChecksum = "";
426  Bool_t ret = ProcessChecksum( checksum );
427  if( ret )
428  fChecksum = checksum;
429  return ret;
430 }
431 
432 ////////////////////////////////////////////////////////////////////////////////
433 /// Check if given checksum is defined in this rule
434 
436 {
437  if( fChecksum == "" )
438  return kFALSE;
439 
440  if( !fChecksumVect )
441  ProcessChecksum( fChecksum ); // At this point the checksum string should always be correct
442 
443  std::vector<UInt_t>::iterator it;
444  for( it = fChecksumVect->begin(); it != fChecksumVect->end(); ++it ) {
445  if( checksum == *it )
446  return kTRUE;
447  }
448  return kFALSE;
449 }
450 
451 ////////////////////////////////////////////////////////////////////////////////
452 /// Set the source class of this rule (i.e. the onfile class).
453 
454 void TSchemaRule::SetSourceClass( const TString& classname )
455 {
456  fSourceClass = classname;
457 }
458 
459 ////////////////////////////////////////////////////////////////////////////////
460 /// Get the source class of this rule (i.e. the onfile class).
461 
462 const char *TSchemaRule::GetSourceClass() const
463 {
464  return fSourceClass;
465 }
466 
467 ////////////////////////////////////////////////////////////////////////////////
468 /// Set the target class of this rule (i.e. the in memory class).
469 
470 void TSchemaRule::SetTargetClass( const TString& classname )
471 {
472  fTargetClass = classname;
473 }
474 
475 ////////////////////////////////////////////////////////////////////////////////
476 /// Get the targte class of this rule (i.e. the in memory class).
477 
478 const char *TSchemaRule::GetTargetClass() const
479 {
480  return fTargetClass;
481 }
482 
483 ////////////////////////////////////////////////////////////////////////////////
484 /// Set the target member of this rule (i.e. the in memory data member).
485 
486 void TSchemaRule::SetTarget( const TString& target )
487 {
488  fTarget = target;
489 
490  if( target == "" ) {
491  delete fTargetVect;
492  fTargetVect = 0;
493  return;
494  }
495 
496  if( !fTargetVect ) {
497  fTargetVect = new TObjArray();
499  }
500  ProcessList( fTargetVect, target );
501 }
502 
503 ////////////////////////////////////////////////////////////////////////////////
504 /// Get the target data members of this rule as a simple string (i.e. the in memory data member).
505 
506 const char *TSchemaRule::GetTargetString() const
507 {
508  return fTarget;
509 }
510 
511 ////////////////////////////////////////////////////////////////////////////////
512 /// Get the target data members of this rule (i.e. the in memory data member).
513 
515 {
516  if( fTarget == "" )
517  return 0;
518 
519  if( !fTargetVect ) {
520  fTargetVect = new TObjArray();
522  ProcessList( fTargetVect, fTarget );
523  }
524 
525  return fTargetVect;
526 }
527 
528 ////////////////////////////////////////////////////////////////////////////////
529 /// Set the list of source members. This should be in the form of a declaration:
530 /// Int_t fOldMember; TNamed fName;
531 
532 void TSchemaRule::SetSource( const TString& source )
533 {
534  fSource = source;
535 
536  if( source == "" ) {
537  delete fSourceVect;
538  fSourceVect = 0;
539  return;
540  }
541 
542  if( !fSourceVect ) {
543  fSourceVect = new TObjArray();
545  }
546 
547  ProcessDeclaration( fSourceVect, source );
548 }
549 
550 ////////////////////////////////////////////////////////////////////////////////
551 /// Get the list of source members as a TObjArray of TNamed object,
552 /// with the name being the member name and the title being its type.
553 
555 {
556  if( fSource == "" )
557  return 0;
558 
559  if( !fSourceVect ) {
560  fSourceVect = new TObjArray();
563  }
564  return fSourceVect;
565 }
566 
567 ////////////////////////////////////////////////////////////////////////////////
568 /// Set the comma separated list of header files to include to be able
569 /// to compile this rule.
570 
571 void TSchemaRule::SetInclude( const TString& incl )
572 {
573  fInclude = incl;
574 
575  if( incl == "" ) {
576  delete fIncludeVect;
577  fIncludeVect = 0;
578  return;
579  }
580 
581  if( !fIncludeVect ) {
582  fIncludeVect = new TObjArray();
584  }
585 
586  ProcessList( fIncludeVect, incl );
587 }
588 
589 ////////////////////////////////////////////////////////////////////////////////
590 /// Return the list of header files to include to be able to
591 /// compile this rule as a TObjArray of TObjString
592 
594 {
595  if( fInclude == "" )
596  return 0;
597 
598  if( !fIncludeVect ) {
599  fIncludeVect = new TObjArray();
602  }
603 
604  return fIncludeVect;
605 }
606 
607 ////////////////////////////////////////////////////////////////////////////////
608 /// Set whether this rule should be save in the ROOT file (if true)
609 
611 {
612  fEmbed = embed;
613 }
614 
615 ////////////////////////////////////////////////////////////////////////////////
616 /// Return true if this rule should be saved in the ROOT File.
617 
619 {
620  return fEmbed;
621 }
622 
623 ////////////////////////////////////////////////////////////////////////////////
624 /// Return kTRUE if this rule is valid.
625 
627 {
628  return (fVersionVect || fChecksumVect) && (fSourceClass.Length() != 0);
629 }
630 
631 ////////////////////////////////////////////////////////////////////////////////
632 /// Set the source code of this rule.
633 
634 void TSchemaRule::SetCode( const TString& code )
635 {
636  fCode = code;
637 }
638 
639 ////////////////////////////////////////////////////////////////////////////////
640 /// Get the source code of this rule.
641 
642 const char *TSchemaRule::GetCode() const
643 {
644  return fCode;
645 }
646 
647 ////////////////////////////////////////////////////////////////////////////////
648 /// Set the attributes code of this rule.
649 
650 void TSchemaRule::SetAttributes( const TString& attributes )
651 {
652  fAttributes = attributes;
653 }
654 
655 ////////////////////////////////////////////////////////////////////////////////
656 /// Get the attributes code of this rule.
657 
658 const char *TSchemaRule::GetAttributes() const
659 {
660  return fAttributes;
661 }
662 
663 ////////////////////////////////////////////////////////////////////////////////
664 /// Return true if one of the rule's data member target is 'target'.
665 
666 Bool_t TSchemaRule::HasTarget( const TString& target ) const
667 {
668  if( !fTargetVect )
669  return kFALSE;
670 
671  TObject* obj;
673  while( (obj = it.Next()) ) {
674  TObjString* str = (TObjString*)obj;
675  if( str->GetString() == target )
676  return kTRUE;
677  }
678  return kFALSE;
679 }
680 
681 ////////////////////////////////////////////////////////////////////////////////
682 /// Return true if one of the rule's data member source is 'source'
683 
684 Bool_t TSchemaRule::HasSource( const TString& source ) const
685 {
686  if( !fSourceVect )
687  return kFALSE;
688 
689  TObject* obj;
691  while( (obj = it.Next()) ) {
692  TSources* var = (TSources*)obj;
693  if( var->GetName() == source )
694  return kTRUE;
695  }
696  return kFALSE;
697 }
698 
699 ////////////////////////////////////////////////////////////////////////////////
700 /// Set the pointer to the function to be run for the rule (if it is a read rule).
701 
703 {
704  fReadFuncPtr = ptr;
705 }
706 
707 ////////////////////////////////////////////////////////////////////////////////
708 /// Get the pointer to the function to be run for the rule (if it is a read rule).
709 
711 {
712  return fReadFuncPtr;
713 }
714 
715 ////////////////////////////////////////////////////////////////////////////////
716 /// Set the pointer to the function to be run for the rule (if it is a raw read rule).
717 
719 {
720  fReadRawFuncPtr = ptr;
721 }
722 
723 ////////////////////////////////////////////////////////////////////////////////
724 /// Get the pointer to the function to be run for the rule (if it is a raw read rule).
725 
727 {
728  return fReadRawFuncPtr;
729 }
730 
731 ////////////////////////////////////////////////////////////////////////////////
732 /// Set the type of the rule.
733 
735 {
736  fRuleType = type;
737 }
738 
739 ////////////////////////////////////////////////////////////////////////////////
740 /// Return kTRUE if the rule is a strict renaming of one of the data member of the class.
741 
743 {
744  return fSourceClass != "" && (fVersion != "" || fChecksum != "") && fTarget == "" && fSource == "" && fInclude == "" && fCode == "" && fAttributes == "";
745 }
746 
747 ////////////////////////////////////////////////////////////////////////////////
748 /// Return kTRUE if the rule is a strict renaming of the class to a new name.
749 
751 {
752  return fSourceClass != "" && (fVersion != "" || fChecksum != "") && fTarget != "" && fSource != "" && fInclude == "" && fCode == "" && fAttributes == "";
753 }
754 
755 ////////////////////////////////////////////////////////////////////////////////
756 /// Return the type of the rule.
757 
759 {
760  return fRuleType;
761 }
762 
763 ////////////////////////////////////////////////////////////////////////////////
764 /// Check if this rule conflicts with the given one.
765 
767 {
768  //---------------------------------------------------------------------------
769  // If the rules have different sources then the don't conflict
770  /////////////////////////////////////////////////////////////////////////////
771 
772  if( fSourceClass != rule->fSourceClass )
773  return kFALSE;
774 
775  //---------------------------------------------------------------------------
776  // Check if the rules have common target
777  /////////////////////////////////////////////////////////////////////////////
778 
779  if( !rule->GetTarget() )
780  return kFALSE;
781 
782  Bool_t haveCommonTargets = kFALSE;
783  TObjArrayIter titer( rule->GetTarget() );
784  TObjString *str;
785  TObject *obj;
786 
787  while( (obj = titer.Next() ) ) {
788  str = (TObjString*)obj;
789  if( HasTarget( str->String() ) )
790  haveCommonTargets = kTRUE;
791  }
792 
793  if( !haveCommonTargets )
794  return kFALSE;
795 
796  //---------------------------------------------------------------------------
797  // Check if there are conflicting checksums
798  /////////////////////////////////////////////////////////////////////////////
799 
800  if( fChecksumVect ) {
801  std::vector<UInt_t>::iterator it;
802  for( it = fChecksumVect->begin(); it != fChecksumVect->end(); ++it )
803  if( rule->TestChecksum( *it ) )
804  return kTRUE;
805  }
806 
807  //---------------------------------------------------------------------------
808  // Check if there are conflicting versions
809  /////////////////////////////////////////////////////////////////////////////
810 
811  if( fVersionVect && rule->fVersionVect )
812  {
813  std::vector<std::pair<Int_t, Int_t> >::iterator it1;
814  std::vector<std::pair<Int_t, Int_t> >::iterator it2;
815  for( it1 = fVersionVect->begin(); it1 != fVersionVect->end(); ++it1 ) {
816  for( it2 = rule->fVersionVect->begin();
817  it2 != rule->fVersionVect->end(); ++it2 ) {
818  //------------------------------------------------------------------
819  // the rules conflict it their version ranges intersect
820  ////////////////////////////////////////////////////////////////////
821 
822  if( it1->first >= it2->first && it1->first <= it2->second )
823  return kTRUE;
824 
825  if( it1->first < it2->first && it1->second >= it2->first )
826  return kTRUE;
827  }
828  }
829  }
830  return kFALSE;
831 }
832 
833 ////////////////////////////////////////////////////////////////////////////////
834 /// Check if specified version string is correct and build version vector.
835 
837 {
838  //---------------------------------------------------------------------------
839  // Check if we have valid list
840  /////////////////////////////////////////////////////////////////////////////
841 
842  if( version[0] != '[' || version[version.Length()-1] != ']' )
843  return kFALSE;
844  std::string ver = version.Data();
845 
846  std::list<std::string> versions;
847  Internal::TSchemaRuleProcessor::SplitList( ver.substr( 1, ver.size()-2), versions );
848 
849  if( versions.empty() )
850  {
851  delete fVersionVect;
852  fVersionVect = 0;
853  return kFALSE;
854  }
855 
856  if( !fVersionVect )
857  fVersionVect = new std::vector<std::pair<Int_t, Int_t> >;
858  fVersionVect->clear();
859 
860  //---------------------------------------------------------------------------
861  // Check the validity of each list element
862  /////////////////////////////////////////////////////////////////////////////
863 
864  std::list<std::string>::iterator it;
865  for( it = versions.begin(); it != versions.end(); ++it ) {
866  std::pair<Int_t, Int_t> verpair;
868  {
869  delete fVersionVect;
870  fVersionVect = 0;
871  return kFALSE;
872  }
873  fVersionVect->push_back( verpair );
874  }
875  return kTRUE;
876 }
877 
878 ////////////////////////////////////////////////////////////////////////////////
879 /// Check if specified checksum string is correct and build checksum vector.
880 
882 {
883  //---------------------------------------------------------------------------
884  // Check if we have valid list
885  /////////////////////////////////////////////////////////////////////////////
886 
887  if (!checksum[0])
888  return kFALSE;
889  std::string chk = (const char*)checksum;
890  if( chk[0] != '[' || chk[chk.size()-1] != ']' )
891  return kFALSE;
892 
893  std::list<std::string> checksums;
894  Internal::TSchemaRuleProcessor::SplitList( chk.substr( 1, chk.size()-2), checksums );
895 
896  if( checksums.empty() ) {
897  delete fChecksumVect;
898  fChecksumVect = 0;
899  return kFALSE;
900  }
901 
902  if( !fChecksumVect )
903  fChecksumVect = new std::vector<UInt_t>;
904  fChecksumVect->clear();
905 
906  //---------------------------------------------------------------------------
907  // Check the validity of each list element
908  /////////////////////////////////////////////////////////////////////////////
909 
910  std::list<std::string>::iterator it;
911  for( it = checksums.begin(); it != checksums.end(); ++it ) {
913  delete fChecksumVect;
914  fChecksumVect = 0;
915  return kFALSE;
916  }
917  fChecksumVect->push_back( atoi( it->c_str() ) );
918  }
919  return kTRUE;
920 }
921 
922 ////////////////////////////////////////////////////////////////////////////////
923 /// Split the list as a comma separated list into a TObjArray of TObjString.
924 
925 void TSchemaRule::ProcessList( TObjArray* array, const TString& list )
926 {
927  std::list<std::string> elems;
928  std::list<std::string>::iterator it;
929  Internal::TSchemaRuleProcessor::SplitList( (const char*)list, elems );
930 
931  array->Clear();
932 
933  if( elems.empty() )
934  return;
935 
936  for( it = elems.begin(); it != elems.end(); ++it ) {
937  TObjString *str = new TObjString;
938  *str = it->c_str();
939  array->Add( str );
940  }
941 }
942 
943 ////////////////////////////////////////////////////////////////////////////////
944 /// Split the list as a declaration into as a TObjArray of TNamed(name,type).
945 
947 {
948  std::list<std::pair<ROOT::Internal::TSchemaType,std::string> > elems;
949  std::list<std::pair<ROOT::Internal::TSchemaType,std::string> >::iterator it;
950  Internal::TSchemaRuleProcessor::SplitDeclaration( (const char*)list, elems );
951 
952  array->Clear();
953 
954  if( elems.empty() )
955  return;
956 
957  for( it = elems.begin(); it != elems.end(); ++it ) {
958  TSources *type = new TSources( it->second.c_str(), it->first.fType.c_str(), it->first.fDimensions.c_str() ) ;
959  array->Add( type );
960  }
961 }
962 
963 #if 0
964 ////////////////////////////////////////////////////////////////////////////////
965 /// Generate the actual function for the rule.
966 
967 Bool_t TSchemaRule::GenerateFor( TStreamerInfo *info )
968 {
969  String funcname = fSourceClass + "_to_" + fTargetClass;
970  if (info) funcname += "_v" + info->GetClassVersion();
971  TString names = fSource + "_" + fTarget;
972  name.ReplaceAll(',','_');
973  name.ReplaceAll(':','_');
974  funcname += "_" + name;
975 
976  String filename = funcname + ".C";
977  if (!false) {
978  filename += '+';
979  }
980 
981  std::ofstream fileout(filename);
982 
983 
984  ROOT::WriteReadRawRuleFunc( *rIt, 0, mappedname, nameTypeMap, fileout );
985  ROOT::WriteReadRuleFunc( *rIt, 0, mappedname, nameTypeMap, fileout );
986 
987  gROOT->LoadMacro(filename);
988 }
989 
990 #endif
Describe Streamer information for one class version.
Definition: TStreamerInfo.h:47
TString fCode
Includes vector.
Definition: TSchemaRule.h:116
void(* ReadRawFuncPtr_t)(char *, TBuffer &)
Definition: TSchemaRule.h:43
An array of TObjects.
Definition: TObjArray.h:39
static Int_t DecreaseDirLevel()
Decrease the indentation level for ls().
Definition: TROOT.cxx:2390
void WriteReadRawRuleFunc(SchemaRuleMap_t &rule, int index, std::string &mappedName, MembersTypeMap_t &members, std::ostream &output)
Write the conversion function for ReadRaw rule, the function name is being written to rule["funcname"...
Bool_t IsAliasRule() const
Return kTRUE if the rule is a strict renaming of one of the data member of the class.
Bool_t TestVersion(Int_t version) const
Check if given version number is defined in this rule.
const char * GetVersion() const
Get the version string.
void SetReadRawFunctionPointer(ReadRawFuncPtr_t ptr)
Set the pointer to the function to be run for the rule (if it is a raw read rule).
Bool_t GetEmbed() const
Return true if this rule should be saved in the ROOT File.
Ssiz_t Length() const
Definition: TString.h:390
Collectable string class.
Definition: TObjString.h:32
virtual void Clear(Option_t *option="")
Remove all objects from the array.
Definition: TObjArray.cxx:297
ReadRawFuncPtr_t fReadRawFuncPtr
Conversion function pointer for read rule.
Definition: TSchemaRule.h:119
const char Option_t
Definition: RtypesCore.h:62
void AsString(TString &out, const char *options="") const
Add to the string 'out' the string representation of the rule.
virtual void SetOwner(Bool_t enable=kTRUE)
Set whether this collection is the owner (enable==true) of its content.
Bool_t HasSource(const TString &source) const
Return true if one of the rule's data member source is 'source'.
static bool IsANumber(const std::string &source)
#define gROOT
Definition: TROOT.h:340
Basic string class.
Definition: TString.h:137
void ToLower()
Change string to lower-case.
Definition: TString.cxx:1088
int Int_t
Definition: RtypesCore.h:41
bool Bool_t
Definition: RtypesCore.h:59
virtual ~TSchemaRule()
Destructor.
Definition: TSchemaRule.cxx:98
Iterator of object array.
Definition: TObjArray.h:124
const Bool_t kFALSE
Definition: Rtypes.h:92
TSchemaRule()
Default Constructor.
Definition: TSchemaRule.cxx:87
Bool_t SetVersion(const TString &version)
Set the version string - returns kFALSE if the format is incorrect.
TObjArray * fTargetVect
Definition: TSchemaRule.h:111
TSchemaRule & operator=(const TSchemaRule &rhs)
Copy operator.
TString fSourceClass
Source checksum vector (for searching purposes)
Definition: TSchemaRule.h:108
void SetTargetClass(const TString &classname)
Set the target class of this rule (i.e. the in memory class).
RuleType_t fRuleType
Conversion function pointer for readraw rule.
Definition: TSchemaRule.h:120
const char * String
Definition: TXMLSetup.cxx:94
const char * Data() const
Definition: TString.h:349
null_t< F > null()
static void SplitDeclaration(const std::string &source, std::list< std::pair< ROOT::Internal::TSchemaType, std::string > > &result)
void SetAttributes(const TString &attributes)
Set the attributes code of this rule.
bool ParseRule(std::string rule, MembersMap_t &result, std::string &error_string)
Parse the schema rule as specified in the LinkDef file.
void Clear()
Clear string without changing its capacity.
Definition: TString.cxx:1139
std::vector< std::pair< Int_t, Int_t > > * fVersionVect
Definition: TSchemaRule.h:105
TObject * Next()
Return next object in array. Returns 0 when no more objects in array.
Definition: TObjArray.cxx:852
void Clear(Option_t *="")
Zero out this rule object.
virtual void Error(const char *method, const char *msgfmt,...) const
Issue error message.
Definition: TObject.cxx:918
void SetSource(const TString &source)
Set the list of source members.
Int_t GetClassVersion() const
char * out
Definition: TBase64.cxx:29
Bool_t ProcessChecksum(const TString &checksum) const
Check if specified checksum string is correct and build checksum vector.
TObjArray * fSourceVect
Definition: TSchemaRule.h:113
void SetSourceClass(const TString &classname)
Set the source class of this rule (i.e. the onfile class).
ReadFuncPtr_t fReadFuncPtr
Definition: TSchemaRule.h:118
void SetInclude(const TString &include)
Set the comma separated list of header files to include to be able to compile this rule...
ReadRawFuncPtr_t GetReadRawFunctionPointer() const
Get the pointer to the function to be run for the rule (if it is a raw read rule).
RuleType_t GetRuleType() const
Return the type of the rule.
std::map< std::string, std::string > MembersMap_t
Bool_t TestChecksum(UInt_t checksum) const
Check if given checksum is defined in this rule.
TString GetString() const
Definition: TObjString.h:50
Bool_t HasTarget(const TString &target) const
Return true if one of the rule's data member target is 'target'.
static void SplitList(const std::string &source, std::list< std::string > &result, char delimiter=',')
std::vector< UInt_t > * fChecksumVect
Definition: TSchemaRule.h:107
void SetTarget(const TString &target)
Set the target member of this rule (i.e. the in memory data member).
unsigned int UInt_t
Definition: RtypesCore.h:42
void SetCode(const TString &code)
Set the source code of this rule.
const Handle_t kNone
Definition: GuiTypes.h:89
void ls(Option_t *option="") const
The ls function lists the contents of a class on stdout.
virtual const char * GetName() const
Returns name of object.
Definition: TNamed.h:51
const TObjArray * GetInclude() const
Return the list of header files to include to be able to compile this rule as a TObjArray of TObjStri...
static void ProcessList(TObjArray *array, const TString &list)
Split the list as a comma separated list into a TObjArray of TObjString.
Bool_t SetChecksum(const TString &checksum)
Set the checksum string - returns kFALSE if the format is incorrect.
TString fInclude
Source data member vector (for searching purposes)
Definition: TSchemaRule.h:114
TString fSource
Target data member vector (for searching purposes)
Definition: TSchemaRule.h:112
const char * GetSourceClass() const
Get the source class of this rule (i.e. the onfile class).
const char * GetTargetClass() const
Get the targte class of this rule (i.e. the in memory class).
void WriteReadRuleFunc(SchemaRuleMap_t &rule, int index, std::string &mappedName, MembersTypeMap_t &members, std::ostream &output)
Write the conversion function for Read rule, the function name is being written to rule["funcname"]...
static void ProcessDeclaration(TObjArray *array, const TString &list)
Split the list as a declaration into as a TObjArray of TNamed(name,type).
void(* ReadFuncPtr_t)(char *, TVirtualObject *)
Definition: TSchemaRule.h:42
const TObjArray * GetSource() const
Get the list of source members as a TObjArray of TNamed object, with the name being the member name a...
const char * GetAttributes() const
Get the attributes code of this rule.
void SetReadFunctionPointer(ReadFuncPtr_t ptr)
Set the pointer to the function to be run for the rule (if it is a read rule).
int type
Definition: TGX11.cxx:120
const TObjArray * GetTarget() const
Get the target data members of this rule (i.e. the in memory data member).
Bool_t IsValid() const
Return kTRUE if this rule is valid.
void SetEmbed(Bool_t embed)
Set whether this rule should be save in the ROOT file (if true)
Bool_t IsRenameRule() const
Return kTRUE if the rule is a strict renaming of the class to a new name.
TString fTargetClass
Definition: TSchemaRule.h:109
#define name(a, b)
Definition: linkTestLib0.cpp:5
Mother of all ROOT objects.
Definition: TObject.h:58
static Int_t IncreaseDirLevel()
Increase the indentation level for ls().
Definition: TROOT.cxx:2453
TString fChecksum
Source version vector (for searching purposes)
Definition: TSchemaRule.h:106
const char * GetCode() const
Get the source code of this rule.
Bool_t Contains(const char *pat, ECaseCompare cmp=kExact) const
Definition: TString.h:567
ReadFuncPtr_t GetReadFunctionPointer() const
Get the pointer to the function to be run for the rule (if it is a read rule).
Bool_t Conflicts(const TSchemaRule *rule) const
Check if this rule conflicts with the given one.
const char * GetTargetString() const
Get the target data members of this rule as a simple string (i.e. the in memory data member)...
ClassImp(TSchemaRule) using namespace ROOT
Bool_t ProcessVersion(const TString &version) const
Check if specified version string is correct and build version vector.
static void IndentLevel()
Functions used by ls() to indent an object hierarchy.
Definition: TROOT.cxx:2461
void Add(TObject *obj)
Definition: TObjArray.h:75
double result[121]
TObjArray * fIncludeVect
Definition: TSchemaRule.h:115
const Bool_t kTRUE
Definition: Rtypes.h:91
TObject * obj
void SetRuleType(RuleType_t type)
Set the type of the rule.
Bool_t SetFromRule(const char *rule)
Set the content fot this object from the rule See TClass::AddRule for details on the syntax...
Bool_t operator==(const TSchemaRule &rhs) const
Return true if the rule have the same effects.
static bool ProcessVersion(const std::string &source, std::pair< Int_t, Int_t > &result)