// @(#)root/core:$Id$
// author: Lukasz Janyst <ljanyst@cern.ch>

#include "TSchemaRuleSet.h"
#include "TSchemaRule.h"
#include "TObjArray.h"
#include "TObjString.h"
#include "TClass.h"
#include "TROOT.h"
#include "Riostream.h"

#include "TVirtualCollectionProxy.h"
#include "TVirtualStreamerInfo.h"
#include "TVirtualMutex.h"
#include "TInterpreter.h" // For gInterpreterMutex
#include "TStreamerElement.h"
#include "TClassEdit.h"

ClassImp(TSchemaRule)

using namespace ROOT;

//------------------------------------------------------------------------------
TSchemaRuleSet::TSchemaRuleSet(): fPersistentRules( 0 ), fRemainingRules( 0 ),
                                  fAllRules( 0 ), fVersion(-3), fCheckSum( 0 )
{
   // Default constructor.

   fPersistentRules = new TObjArray();
   fRemainingRules  = new TObjArray();
   fAllRules        = new TObjArray();
   fAllRules->SetOwner( kTRUE );
}

//------------------------------------------------------------------------------
TSchemaRuleSet::~TSchemaRuleSet()
{
   // Destructor.

   delete fPersistentRules;
   delete fRemainingRules;
   delete fAllRules;
}

//------------------------------------------------------------------------------
void TSchemaRuleSet::ls(Option_t *) const
{
   // The ls function lists the contents of a class on stdout. Ls output
   // is typically much less verbose then Dump().

   TROOT::IndentLevel();
   std::cout << "TSchemaRuleSet for " << fClassName << ":\n";
   TROOT::IncreaseDirLevel();
   TObject *object = 0;
   TIter next(fPersistentRules);
   while ((object = next())) {
      object->ls(fClassName);
   }
   TROOT::DecreaseDirLevel();
}

//------------------------------------------------------------------------------
Bool_t TSchemaRuleSet::AddRules( TSchemaRuleSet* /* rules */, EConsistencyCheck /* checkConsistency */, TString * /* errmsg */ )
{
   return kFALSE;
}

//------------------------------------------------------------------------------
Bool_t TSchemaRuleSet::AddRule( TSchemaRule* rule, EConsistencyCheck checkConsistency, TString *errmsg )
{
   // The consistency check always fails if the TClass object was not set!
   // if checkConsistency is:
   //   kNoCheck: no check is done, register the rule as is
   //   kCheckConflict: check only for conflicting rules
   //   kCheckAll: check for conflict and check for rule about members that are not in the current class layout.
   // return kTRUE if the layout is accepted, in which case we take ownership of
   // the rule object.
   // return kFALSE if the rule failed one of the test, the rule now needs to be deleted by the caller.

   //---------------------------------------------------------------------------
   // Cannot verify the consistency if the TClass object is not present
   //---------------------------------------------------------------------------
   if( (checkConsistency != kNoCheck) && !fClass )
      return kFALSE;

   if( !rule->IsValid() )
      return kFALSE;

   //---------------------------------------------------------------------------
   // If we don't check the consistency then we should just add the object
   //---------------------------------------------------------------------------
   if( checkConsistency == kNoCheck ) {
      if( rule->GetEmbed() )
         fPersistentRules->Add( rule );
      else
         fRemainingRules->Add( rule );
      fAllRules->Add( rule );
      return kTRUE;
   }

   //---------------------------------------------------------------------------
   // Check if all of the target data members specified in the rule are
   // present int the target class
   //---------------------------------------------------------------------------
   TObject* obj;
   // Check only if we have some information about the class, otherwise we have
   // nothing to check against
   bool streamerInfosTest;
   {
     R__LOCKGUARD2(gInterpreterMutex);
     streamerInfosTest = (fClass->GetStreamerInfos()==0 || fClass->GetStreamerInfos()->GetEntries()==0);
   }
   if( rule->GetTarget()  && !(fClass->TestBit(TClass::kIsEmulation) && streamerInfosTest) ) {
      TObjArrayIter titer( rule->GetTarget() );
      while( (obj = titer.Next()) ) {
         TObjString* str = (TObjString*)obj;
         if( !fClass->GetDataMember( str->GetString() ) && !fClass->GetBaseClass( str->GetString() ) ) {
            if (checkConsistency == kCheckAll) {
               if (errmsg) {
                  errmsg->Form("the target member (%s) is unknown",str->GetString().Data());
               }
               return kFALSE;
            } else {
               // We ignore the rules that do not apply ...
               delete rule;
               return kTRUE;
            }
         }
      }
   }

   //---------------------------------------------------------------------------
   // Check if there is a rule conflicting with this one
   //---------------------------------------------------------------------------
   const TObjArray* rules = FindRules( rule->GetSourceClass() );
   TObjArrayIter it( rules );
   TSchemaRule *r;

   while( (obj = it.Next()) ) {
      r = (TSchemaRule *) obj;
      if( rule->Conflicts( r ) ) {
         delete rules;
         if ( *r == *rule) {
            // The rules are duplicate from each other,
            // just ignore the new ones.
            if (errmsg) {
               *errmsg = "it conflicts with one of the other rules";
            }
            delete rule;
            return kTRUE;
         }
         if (errmsg) {
            *errmsg = "The existing rule is:\n   ";
            r->AsString(*errmsg,"s");
            *errmsg += "\nand the ignored rule is:\n   ";
            rule->AsString(*errmsg);
            *errmsg += ".\n";
         }
         return kFALSE;
      }
   }
   delete rules;

   //---------------------------------------------------------------------------
   // No conflicts - insert the rules
   //---------------------------------------------------------------------------
   if( rule->GetEmbed() )
      fPersistentRules->Add( rule );
   else
      fRemainingRules->Add( rule );
   fAllRules->Add( rule );

   return kTRUE;
}

//------------------------------------------------------------------------------
void TSchemaRuleSet::AsString(TString &out) const
{
   // Fill the string 'out' with the string representation of the rule.

   TObjArrayIter it( fAllRules );
   TSchemaRule *rule;
   while( (rule = (TSchemaRule*)it.Next()) ) {
      rule->AsString(out);
      out += "\n";
   }
}

//------------------------------------------------------------------------------
Bool_t TSchemaRuleSet::HasRuleWithSourceClass( const TString &source ) const
{
   // Return True if we have any rule whose source class is 'source'.

   TObjArrayIter it( fAllRules );
   TObject *obj;
   while( (obj = it.Next()) ) {
      TSchemaRule* rule = (TSchemaRule*)obj;
      if( rule->GetSourceClass() == source )
         return kTRUE;
   }
   // There was no explicit rule, let's see we have implicit rules.
   if (fClass->GetCollectionProxy()) {
      if (fClass->GetCollectionProxy()->GetValueClass() == 0) {
         // We have a numeric collection, let see if the target is
         // also a numeric collection.
         TClass *src = TClass::GetClass(source);
         if (src && src->GetCollectionProxy() &&
             src->GetCollectionProxy()->HasPointers() == fClass->GetCollectionProxy()->HasPointers()) {
            TVirtualCollectionProxy *proxy = src->GetCollectionProxy();
            if (proxy->GetValueClass() == 0) {
               return kTRUE;
            }
         }
      } else {
         TClass *vTargetClass = fClass->GetCollectionProxy()->GetValueClass();
         TClass *src = TClass::GetClass(source);
         if (vTargetClass->GetSchemaRules()) {
            if (src && src->GetCollectionProxy() &&
                src->GetCollectionProxy()->HasPointers() == fClass->GetCollectionProxy()->HasPointers()) {
               TClass *vSourceClass = src->GetCollectionProxy()->GetValueClass();
               if (vSourceClass) {
                  return vTargetClass->GetSchemaRules()->HasRuleWithSourceClass( vSourceClass->GetName() );
               }
            }
         }
      }
   } else if (!strncmp(fClass->GetName(),"std::pair<",10) || !strncmp(fClass->GetName(),"pair<",5)) {
      if (!strncmp(source,"std::pair<",10) || !strncmp(source,"pair<",5)) {
         // std::pair can be converted into each other if both its parameter can be converted into
         // each other.
         TClass *src = TClass::GetClass(source);
         if (!src) {
            Error("HasRuleWithSourceClass","Can not find the TClass for %s when matching with %s\n",source.Data(),fClass->GetName());
            return kFALSE;
         }
         TVirtualStreamerInfo *sourceInfo = src->GetStreamerInfo();
         TVirtualStreamerInfo *targetInfo = fClass->GetStreamerInfo();
         if (!sourceInfo) {
            Error("HasRuleWithSourceClass","Can not find the StreamerInfo for %s when matching with %s\n",source.Data(),fClass->GetName());
            return kFALSE;
         }
         if (!targetInfo) {
            Error("HasRuleWithSourceClass","Can not find the StreamerInfo for target class %s\n",fClass->GetName());
            return kFALSE;
         }
         for(int i = 0 ; i<2 ; ++i) {
            TStreamerElement *sourceElement = (TStreamerElement*)sourceInfo->GetElements()->At(i);
            TStreamerElement *targetElement = (TStreamerElement*)targetInfo->GetElements()->At(i);
            if (sourceElement->GetClass()) {
               if (!targetElement->GetClass()) {
                  return kFALSE;
               }
               if (sourceElement->GetClass() == targetElement->GetClass()) {
                  continue;
               }
               TSchemaRuleSet *rules = sourceElement->GetClass()->GetSchemaRules();
               if (!rules || !rules->HasRuleWithSourceClass( targetElement->GetClass()->GetName() ) ) {
                  return kFALSE;
               }
            } else if (targetElement->GetClass()) {
               return kFALSE;
            } else {
               // both side are numeric element we can deal with it.
            }
         }
         // Both side are pairs and have convertible types, let records this as a renaming rule
         ROOT::TSchemaRule *ruleobj = new ROOT::TSchemaRule();
         ruleobj->SetSourceClass(source);
         ruleobj->SetTargetClass(fClass->GetName());
         ruleobj->SetVersion("[1-]");
         const_cast<TSchemaRuleSet*>(this)->AddRule(ruleobj);
         return kTRUE;
      }
   }
   return kFALSE;
}

//------------------------------------------------------------------------------
const TObjArray* TSchemaRuleSet::FindRules( const TString &source ) const
{
   // Return all the rules that are about the given 'source' class.
   // User has to delete the returned array
   TObject*      obj;
   TObjArrayIter it( fAllRules );
   TObjArray*    arr = new TObjArray();
   arr->SetOwner( kFALSE );

   while( (obj = it.Next()) ) {
      TSchemaRule* rule = (TSchemaRule*)obj;
      if( rule->GetSourceClass() == source )
         arr->Add( rule );
   }

#if 0
   // Le't's see we have implicit rules.
   if (fClass->GetCollectionProxy()) {
      if (fClass->GetCollectionProxy()->GetValueClass() == 0
          && (fClass->GetCollectionProxy()->GetCollectionType() == TClassEdit::kVector
              || (fClass->GetCollectionProxy()->GetProperties() & TVirtualCollectionProxy::kIsEmulated))) {
         // We have a numeric collection, let see if the target is
         // also a numeric collection (humm just a vector for now)
         TClass *src = TClass::GetClass(source);
         if (src && src->GetCollectionProxy()) {
            TVirtualCollectionProxy *proxy = src->GetCollectionProxy();
            if (proxy->GetValueClass() == 0) {
               // ... would need to check if we already have
               // the rule (or any rule?)
            }
         }
      }
   }
#endif
   return arr;
}

//------------------------------------------------------------------------------
const TSchemaMatch* TSchemaRuleSet::FindRules( const TString &source, Int_t version ) const
{
   // Return all the rules that applies to the specified version of the given 'source' class.
   // User has to delete the returned array

   TObject*      obj;
   TObjArrayIter it( fAllRules );
   TSchemaMatch* arr = new TSchemaMatch();
   arr->SetOwner( kFALSE );

   while( (obj = it.Next()) ) {
      TSchemaRule* rule = (TSchemaRule*)obj;
      if( rule->GetSourceClass() == source && rule->TestVersion( version ) )
         arr->Add( rule );
   }

   if( arr->GetEntriesFast() )
      return arr;
   else {
      delete arr;
      return 0;
   }
}

//------------------------------------------------------------------------------
const TSchemaMatch* TSchemaRuleSet::FindRules( const TString &source, UInt_t checksum ) const
{
   // Return all the rules that applies to the specified checksum of the given 'source' class.
   // User has to delete the returned array

   TObject*      obj;
   TObjArrayIter it( fAllRules );
   TSchemaMatch* arr = new TSchemaMatch();
   arr->SetOwner( kFALSE );

   while( (obj = it.Next()) ) {
      TSchemaRule* rule = (TSchemaRule*)obj;
      if( rule->GetSourceClass() == source && rule->TestChecksum( checksum ) )
         arr->Add( rule );
   }

   if( arr->GetEntriesFast() )
      return arr;
   else {
      delete arr;
      return 0;
   }
}

//------------------------------------------------------------------------------
const TSchemaMatch* TSchemaRuleSet::FindRules( const TString &source, Int_t version, UInt_t checksum ) const
{
   // Return all the rules that applies to the specified version OR checksum of the given 'source' class.
   // User has to delete the returned array

   TObject*      obj;
   TObjArrayIter it( fAllRules );
   TSchemaMatch* arr = new TSchemaMatch();
   arr->SetOwner( kFALSE );

   while( (obj = it.Next()) ) {
      TSchemaRule* rule = (TSchemaRule*)obj;
      if( rule->GetSourceClass() == source && ( rule->TestVersion( version ) || rule->TestChecksum( checksum ) ) )
         arr->Add( rule );
   }

   if( arr->GetEntriesFast() )
      return arr;
   else {
      delete arr;
      return 0;
   }
}

//------------------------------------------------------------------------------
TClass* TSchemaRuleSet::GetClass()
{
   return fClass;
}

//------------------------------------------------------------------------------
UInt_t TSchemaRuleSet::GetClassCheckSum() const
{
   if (fCheckSum == 0 && fClass) {
      const_cast<TSchemaRuleSet*>(this)->fCheckSum = fClass->GetCheckSum();
   }
   return fCheckSum;
}

//------------------------------------------------------------------------------
TString TSchemaRuleSet::GetClassName() const
{
   return fClassName;
}

//------------------------------------------------------------------------------
Int_t TSchemaRuleSet::GetClassVersion() const
{
   return fVersion;
}

//------------------------------------------------------------------------------
const TObjArray* TSchemaRuleSet::GetRules() const
{
   return fAllRules;
}

//------------------------------------------------------------------------------
const TObjArray* TSchemaRuleSet::GetPersistentRules() const
{
   return fPersistentRules;
}

//------------------------------------------------------------------------------
void TSchemaRuleSet::RemoveRule( TSchemaRule* rule )
{
   // Remove given rule from the set - the rule is not being deleted!
   fPersistentRules->Remove( rule );
   fRemainingRules->Remove( rule );
   fAllRules->Remove( rule );
}

//------------------------------------------------------------------------------
void TSchemaRuleSet::RemoveRules( TObjArray* rules )
{
   // remove given array of rules from the set - the rules are not being deleted!
   TObject*      obj;
   TObjArrayIter it( rules );

   while( (obj = it.Next()) ) {
      fPersistentRules->Remove( obj );
      fRemainingRules->Remove( obj );
      fAllRules->Remove( obj );
   }
}

//------------------------------------------------------------------------------
void TSchemaRuleSet::SetClass( TClass* cls )
{
   // Set the TClass associated with this rule set.

   fClass     = cls;
   fClassName = cls->GetName();
   fVersion   = cls->GetClassVersion();
}


//------------------------------------------------------------------------------
const TSchemaRule* TSchemaMatch::GetRuleWithSource( const TString& name ) const
{
   // Return the rule that has 'name' as a source.

   for( Int_t i = 0; i < GetEntries(); ++i ) {
      TSchemaRule* rule = (ROOT::TSchemaRule*)At(i);
      if( rule->HasSource( name ) ) return rule;
   }
   return 0;
}

//------------------------------------------------------------------------------
const TSchemaRule* TSchemaMatch::GetRuleWithTarget( const TString& name ) const
{
   // Return the rule that has 'name' as a target.

   for( Int_t i=0; i<GetEntries(); ++i) {
      ROOT::TSchemaRule *rule = (ROOT::TSchemaRule*)At(i);
      if( rule->HasTarget( name ) ) return rule;
   }
   return 0;
}

//------------------------------------------------------------------------------
Bool_t TSchemaMatch::HasRuleWithSource( const TString& name, Bool_t needingAlloc ) const
{
   // Return true if the set of rules has at least one rule that has the data
   // member named 'name' as a source.
   // If needingAlloc is true, only the rule that requires the data member to
   // be cached will be taken in consideration.

   for( Int_t i = 0; i < GetEntries(); ++i ) {
      TSchemaRule* rule = (ROOT::TSchemaRule*)At(i);
      if( rule->HasSource( name ) ) {
         if (needingAlloc) {
            const TObjArray *targets = rule->GetTarget();
            if (targets && (targets->GetEntries() > 1 || targets->GetEntries()==0) ) {
               return kTRUE;
            }
            if (targets && name != targets->UncheckedAt(0)->GetName() ) {
               return kTRUE;
            }
            // If the rule has the same source and target and does not
            // have any actions, then it does not need allocation.
            if (rule->GetReadFunctionPointer() || rule->GetReadRawFunctionPointer()) {
               return kTRUE;
            }
         } else {
            return kTRUE;
         }
      }
   }
   return kFALSE;
}

//------------------------------------------------------------------------------
Bool_t TSchemaMatch::HasRuleWithTarget( const TString& name, Bool_t willset ) const
{
   // Return true if the set of rules has at least one rule that has the data
   // member named 'name' as a target.
   // If willset is true, only the rule that will set the value of the data member.

   for( Int_t i=0; i<GetEntries(); ++i) {
      ROOT::TSchemaRule *rule = (ROOT::TSchemaRule*)At(i);
      if( rule->HasTarget( name ) ) {
         if (willset) {
            const TObjArray *targets = rule->GetTarget();
            if (targets && (targets->GetEntries() > 1 || targets->GetEntries()==0) ) {
               return kTRUE;
            }
            const TObjArray *sources = rule->GetSource();
            if (sources && (sources->GetEntries() > 1 || sources->GetEntries()==0) ) {
               return kTRUE;
            }
            if (sources && name != sources->UncheckedAt(0)->GetName() ) {
               return kTRUE;
            }
            // If the rule has the same source and target and does not
            // have any actions, then it will not directly set the value.
            if (rule->GetReadFunctionPointer() || rule->GetReadRawFunctionPointer()) {
               return kTRUE;
            }
         } else {
            return kTRUE;
         }
      }
   }
   return kFALSE;
}

//______________________________________________________________________________
void TSchemaRuleSet::Streamer(TBuffer &R__b)
{
   // Stream an object of class ROOT::TSchemaRuleSet.

   if (R__b.IsReading()) {
      R__b.ReadClassBuffer(ROOT::TSchemaRuleSet::Class(),this);
      fAllRules->Clear();
      fAllRules->AddAll(fPersistentRules);
   } else {
      GetClassCheckSum();
      R__b.WriteClassBuffer(ROOT::TSchemaRuleSet::Class(),this);
   }
}

 TSchemaRuleSet.cxx:1
 TSchemaRuleSet.cxx:2
 TSchemaRuleSet.cxx:3
 TSchemaRuleSet.cxx:4
 TSchemaRuleSet.cxx:5
 TSchemaRuleSet.cxx:6
 TSchemaRuleSet.cxx:7
 TSchemaRuleSet.cxx:8
 TSchemaRuleSet.cxx:9
 TSchemaRuleSet.cxx:10
 TSchemaRuleSet.cxx:11
 TSchemaRuleSet.cxx:12
 TSchemaRuleSet.cxx:13
 TSchemaRuleSet.cxx:14
 TSchemaRuleSet.cxx:15
 TSchemaRuleSet.cxx:16
 TSchemaRuleSet.cxx:17
 TSchemaRuleSet.cxx:18
 TSchemaRuleSet.cxx:19
 TSchemaRuleSet.cxx:20
 TSchemaRuleSet.cxx:21
 TSchemaRuleSet.cxx:22
 TSchemaRuleSet.cxx:23
 TSchemaRuleSet.cxx:24
 TSchemaRuleSet.cxx:25
 TSchemaRuleSet.cxx:26
 TSchemaRuleSet.cxx:27
 TSchemaRuleSet.cxx:28
 TSchemaRuleSet.cxx:29
 TSchemaRuleSet.cxx:30
 TSchemaRuleSet.cxx:31
 TSchemaRuleSet.cxx:32
 TSchemaRuleSet.cxx:33
 TSchemaRuleSet.cxx:34
 TSchemaRuleSet.cxx:35
 TSchemaRuleSet.cxx:36
 TSchemaRuleSet.cxx:37
 TSchemaRuleSet.cxx:38
 TSchemaRuleSet.cxx:39
 TSchemaRuleSet.cxx:40
 TSchemaRuleSet.cxx:41
 TSchemaRuleSet.cxx:42
 TSchemaRuleSet.cxx:43
 TSchemaRuleSet.cxx:44
 TSchemaRuleSet.cxx:45
 TSchemaRuleSet.cxx:46
 TSchemaRuleSet.cxx:47
 TSchemaRuleSet.cxx:48
 TSchemaRuleSet.cxx:49
 TSchemaRuleSet.cxx:50
 TSchemaRuleSet.cxx:51
 TSchemaRuleSet.cxx:52
 TSchemaRuleSet.cxx:53
 TSchemaRuleSet.cxx:54
 TSchemaRuleSet.cxx:55
 TSchemaRuleSet.cxx:56
 TSchemaRuleSet.cxx:57
 TSchemaRuleSet.cxx:58
 TSchemaRuleSet.cxx:59
 TSchemaRuleSet.cxx:60
 TSchemaRuleSet.cxx:61
 TSchemaRuleSet.cxx:62
 TSchemaRuleSet.cxx:63
 TSchemaRuleSet.cxx:64
 TSchemaRuleSet.cxx:65
 TSchemaRuleSet.cxx:66
 TSchemaRuleSet.cxx:67
 TSchemaRuleSet.cxx:68
 TSchemaRuleSet.cxx:69
 TSchemaRuleSet.cxx:70
 TSchemaRuleSet.cxx:71
 TSchemaRuleSet.cxx:72
 TSchemaRuleSet.cxx:73
 TSchemaRuleSet.cxx:74
 TSchemaRuleSet.cxx:75
 TSchemaRuleSet.cxx:76
 TSchemaRuleSet.cxx:77
 TSchemaRuleSet.cxx:78
 TSchemaRuleSet.cxx:79
 TSchemaRuleSet.cxx:80
 TSchemaRuleSet.cxx:81
 TSchemaRuleSet.cxx:82
 TSchemaRuleSet.cxx:83
 TSchemaRuleSet.cxx:84
 TSchemaRuleSet.cxx:85
 TSchemaRuleSet.cxx:86
 TSchemaRuleSet.cxx:87
 TSchemaRuleSet.cxx:88
 TSchemaRuleSet.cxx:89
 TSchemaRuleSet.cxx:90
 TSchemaRuleSet.cxx:91
 TSchemaRuleSet.cxx:92
 TSchemaRuleSet.cxx:93
 TSchemaRuleSet.cxx:94
 TSchemaRuleSet.cxx:95
 TSchemaRuleSet.cxx:96
 TSchemaRuleSet.cxx:97
 TSchemaRuleSet.cxx:98
 TSchemaRuleSet.cxx:99
 TSchemaRuleSet.cxx:100
 TSchemaRuleSet.cxx:101
 TSchemaRuleSet.cxx:102
 TSchemaRuleSet.cxx:103
 TSchemaRuleSet.cxx:104
 TSchemaRuleSet.cxx:105
 TSchemaRuleSet.cxx:106
 TSchemaRuleSet.cxx:107
 TSchemaRuleSet.cxx:108
 TSchemaRuleSet.cxx:109
 TSchemaRuleSet.cxx:110
 TSchemaRuleSet.cxx:111
 TSchemaRuleSet.cxx:112
 TSchemaRuleSet.cxx:113
 TSchemaRuleSet.cxx:114
 TSchemaRuleSet.cxx:115
 TSchemaRuleSet.cxx:116
 TSchemaRuleSet.cxx:117
 TSchemaRuleSet.cxx:118
 TSchemaRuleSet.cxx:119
 TSchemaRuleSet.cxx:120
 TSchemaRuleSet.cxx:121
 TSchemaRuleSet.cxx:122
 TSchemaRuleSet.cxx:123
 TSchemaRuleSet.cxx:124
 TSchemaRuleSet.cxx:125
 TSchemaRuleSet.cxx:126
 TSchemaRuleSet.cxx:127
 TSchemaRuleSet.cxx:128
 TSchemaRuleSet.cxx:129
 TSchemaRuleSet.cxx:130
 TSchemaRuleSet.cxx:131
 TSchemaRuleSet.cxx:132
 TSchemaRuleSet.cxx:133
 TSchemaRuleSet.cxx:134
 TSchemaRuleSet.cxx:135
 TSchemaRuleSet.cxx:136
 TSchemaRuleSet.cxx:137
 TSchemaRuleSet.cxx:138
 TSchemaRuleSet.cxx:139
 TSchemaRuleSet.cxx:140
 TSchemaRuleSet.cxx:141
 TSchemaRuleSet.cxx:142
 TSchemaRuleSet.cxx:143
 TSchemaRuleSet.cxx:144
 TSchemaRuleSet.cxx:145
 TSchemaRuleSet.cxx:146
 TSchemaRuleSet.cxx:147
 TSchemaRuleSet.cxx:148
 TSchemaRuleSet.cxx:149
 TSchemaRuleSet.cxx:150
 TSchemaRuleSet.cxx:151
 TSchemaRuleSet.cxx:152
 TSchemaRuleSet.cxx:153
 TSchemaRuleSet.cxx:154
 TSchemaRuleSet.cxx:155
 TSchemaRuleSet.cxx:156
 TSchemaRuleSet.cxx:157
 TSchemaRuleSet.cxx:158
 TSchemaRuleSet.cxx:159
 TSchemaRuleSet.cxx:160
 TSchemaRuleSet.cxx:161
 TSchemaRuleSet.cxx:162
 TSchemaRuleSet.cxx:163
 TSchemaRuleSet.cxx:164
 TSchemaRuleSet.cxx:165
 TSchemaRuleSet.cxx:166
 TSchemaRuleSet.cxx:167
 TSchemaRuleSet.cxx:168
 TSchemaRuleSet.cxx:169
 TSchemaRuleSet.cxx:170
 TSchemaRuleSet.cxx:171
 TSchemaRuleSet.cxx:172
 TSchemaRuleSet.cxx:173
 TSchemaRuleSet.cxx:174
 TSchemaRuleSet.cxx:175
 TSchemaRuleSet.cxx:176
 TSchemaRuleSet.cxx:177
 TSchemaRuleSet.cxx:178
 TSchemaRuleSet.cxx:179
 TSchemaRuleSet.cxx:180
 TSchemaRuleSet.cxx:181
 TSchemaRuleSet.cxx:182
 TSchemaRuleSet.cxx:183
 TSchemaRuleSet.cxx:184
 TSchemaRuleSet.cxx:185
 TSchemaRuleSet.cxx:186
 TSchemaRuleSet.cxx:187
 TSchemaRuleSet.cxx:188
 TSchemaRuleSet.cxx:189
 TSchemaRuleSet.cxx:190
 TSchemaRuleSet.cxx:191
 TSchemaRuleSet.cxx:192
 TSchemaRuleSet.cxx:193
 TSchemaRuleSet.cxx:194
 TSchemaRuleSet.cxx:195
 TSchemaRuleSet.cxx:196
 TSchemaRuleSet.cxx:197
 TSchemaRuleSet.cxx:198
 TSchemaRuleSet.cxx:199
 TSchemaRuleSet.cxx:200
 TSchemaRuleSet.cxx:201
 TSchemaRuleSet.cxx:202
 TSchemaRuleSet.cxx:203
 TSchemaRuleSet.cxx:204
 TSchemaRuleSet.cxx:205
 TSchemaRuleSet.cxx:206
 TSchemaRuleSet.cxx:207
 TSchemaRuleSet.cxx:208
 TSchemaRuleSet.cxx:209
 TSchemaRuleSet.cxx:210
 TSchemaRuleSet.cxx:211
 TSchemaRuleSet.cxx:212
 TSchemaRuleSet.cxx:213
 TSchemaRuleSet.cxx:214
 TSchemaRuleSet.cxx:215
 TSchemaRuleSet.cxx:216
 TSchemaRuleSet.cxx:217
 TSchemaRuleSet.cxx:218
 TSchemaRuleSet.cxx:219
 TSchemaRuleSet.cxx:220
 TSchemaRuleSet.cxx:221
 TSchemaRuleSet.cxx:222
 TSchemaRuleSet.cxx:223
 TSchemaRuleSet.cxx:224
 TSchemaRuleSet.cxx:225
 TSchemaRuleSet.cxx:226
 TSchemaRuleSet.cxx:227
 TSchemaRuleSet.cxx:228
 TSchemaRuleSet.cxx:229
 TSchemaRuleSet.cxx:230
 TSchemaRuleSet.cxx:231
 TSchemaRuleSet.cxx:232
 TSchemaRuleSet.cxx:233
 TSchemaRuleSet.cxx:234
 TSchemaRuleSet.cxx:235
 TSchemaRuleSet.cxx:236
 TSchemaRuleSet.cxx:237
 TSchemaRuleSet.cxx:238
 TSchemaRuleSet.cxx:239
 TSchemaRuleSet.cxx:240
 TSchemaRuleSet.cxx:241
 TSchemaRuleSet.cxx:242
 TSchemaRuleSet.cxx:243
 TSchemaRuleSet.cxx:244
 TSchemaRuleSet.cxx:245
 TSchemaRuleSet.cxx:246
 TSchemaRuleSet.cxx:247
 TSchemaRuleSet.cxx:248
 TSchemaRuleSet.cxx:249
 TSchemaRuleSet.cxx:250
 TSchemaRuleSet.cxx:251
 TSchemaRuleSet.cxx:252
 TSchemaRuleSet.cxx:253
 TSchemaRuleSet.cxx:254
 TSchemaRuleSet.cxx:255
 TSchemaRuleSet.cxx:256
 TSchemaRuleSet.cxx:257
 TSchemaRuleSet.cxx:258
 TSchemaRuleSet.cxx:259
 TSchemaRuleSet.cxx:260
 TSchemaRuleSet.cxx:261
 TSchemaRuleSet.cxx:262
 TSchemaRuleSet.cxx:263
 TSchemaRuleSet.cxx:264
 TSchemaRuleSet.cxx:265
 TSchemaRuleSet.cxx:266
 TSchemaRuleSet.cxx:267
 TSchemaRuleSet.cxx:268
 TSchemaRuleSet.cxx:269
 TSchemaRuleSet.cxx:270
 TSchemaRuleSet.cxx:271
 TSchemaRuleSet.cxx:272
 TSchemaRuleSet.cxx:273
 TSchemaRuleSet.cxx:274
 TSchemaRuleSet.cxx:275
 TSchemaRuleSet.cxx:276
 TSchemaRuleSet.cxx:277
 TSchemaRuleSet.cxx:278
 TSchemaRuleSet.cxx:279
 TSchemaRuleSet.cxx:280
 TSchemaRuleSet.cxx:281
 TSchemaRuleSet.cxx:282
 TSchemaRuleSet.cxx:283
 TSchemaRuleSet.cxx:284
 TSchemaRuleSet.cxx:285
 TSchemaRuleSet.cxx:286
 TSchemaRuleSet.cxx:287
 TSchemaRuleSet.cxx:288
 TSchemaRuleSet.cxx:289
 TSchemaRuleSet.cxx:290
 TSchemaRuleSet.cxx:291
 TSchemaRuleSet.cxx:292
 TSchemaRuleSet.cxx:293
 TSchemaRuleSet.cxx:294
 TSchemaRuleSet.cxx:295
 TSchemaRuleSet.cxx:296
 TSchemaRuleSet.cxx:297
 TSchemaRuleSet.cxx:298
 TSchemaRuleSet.cxx:299
 TSchemaRuleSet.cxx:300
 TSchemaRuleSet.cxx:301
 TSchemaRuleSet.cxx:302
 TSchemaRuleSet.cxx:303
 TSchemaRuleSet.cxx:304
 TSchemaRuleSet.cxx:305
 TSchemaRuleSet.cxx:306
 TSchemaRuleSet.cxx:307
 TSchemaRuleSet.cxx:308
 TSchemaRuleSet.cxx:309
 TSchemaRuleSet.cxx:310
 TSchemaRuleSet.cxx:311
 TSchemaRuleSet.cxx:312
 TSchemaRuleSet.cxx:313
 TSchemaRuleSet.cxx:314
 TSchemaRuleSet.cxx:315
 TSchemaRuleSet.cxx:316
 TSchemaRuleSet.cxx:317
 TSchemaRuleSet.cxx:318
 TSchemaRuleSet.cxx:319
 TSchemaRuleSet.cxx:320
 TSchemaRuleSet.cxx:321
 TSchemaRuleSet.cxx:322
 TSchemaRuleSet.cxx:323
 TSchemaRuleSet.cxx:324
 TSchemaRuleSet.cxx:325
 TSchemaRuleSet.cxx:326
 TSchemaRuleSet.cxx:327
 TSchemaRuleSet.cxx:328
 TSchemaRuleSet.cxx:329
 TSchemaRuleSet.cxx:330
 TSchemaRuleSet.cxx:331
 TSchemaRuleSet.cxx:332
 TSchemaRuleSet.cxx:333
 TSchemaRuleSet.cxx:334
 TSchemaRuleSet.cxx:335
 TSchemaRuleSet.cxx:336
 TSchemaRuleSet.cxx:337
 TSchemaRuleSet.cxx:338
 TSchemaRuleSet.cxx:339
 TSchemaRuleSet.cxx:340
 TSchemaRuleSet.cxx:341
 TSchemaRuleSet.cxx:342
 TSchemaRuleSet.cxx:343
 TSchemaRuleSet.cxx:344
 TSchemaRuleSet.cxx:345
 TSchemaRuleSet.cxx:346
 TSchemaRuleSet.cxx:347
 TSchemaRuleSet.cxx:348
 TSchemaRuleSet.cxx:349
 TSchemaRuleSet.cxx:350
 TSchemaRuleSet.cxx:351
 TSchemaRuleSet.cxx:352
 TSchemaRuleSet.cxx:353
 TSchemaRuleSet.cxx:354
 TSchemaRuleSet.cxx:355
 TSchemaRuleSet.cxx:356
 TSchemaRuleSet.cxx:357
 TSchemaRuleSet.cxx:358
 TSchemaRuleSet.cxx:359
 TSchemaRuleSet.cxx:360
 TSchemaRuleSet.cxx:361
 TSchemaRuleSet.cxx:362
 TSchemaRuleSet.cxx:363
 TSchemaRuleSet.cxx:364
 TSchemaRuleSet.cxx:365
 TSchemaRuleSet.cxx:366
 TSchemaRuleSet.cxx:367
 TSchemaRuleSet.cxx:368
 TSchemaRuleSet.cxx:369
 TSchemaRuleSet.cxx:370
 TSchemaRuleSet.cxx:371
 TSchemaRuleSet.cxx:372
 TSchemaRuleSet.cxx:373
 TSchemaRuleSet.cxx:374
 TSchemaRuleSet.cxx:375
 TSchemaRuleSet.cxx:376
 TSchemaRuleSet.cxx:377
 TSchemaRuleSet.cxx:378
 TSchemaRuleSet.cxx:379
 TSchemaRuleSet.cxx:380
 TSchemaRuleSet.cxx:381
 TSchemaRuleSet.cxx:382
 TSchemaRuleSet.cxx:383
 TSchemaRuleSet.cxx:384
 TSchemaRuleSet.cxx:385
 TSchemaRuleSet.cxx:386
 TSchemaRuleSet.cxx:387
 TSchemaRuleSet.cxx:388
 TSchemaRuleSet.cxx:389
 TSchemaRuleSet.cxx:390
 TSchemaRuleSet.cxx:391
 TSchemaRuleSet.cxx:392
 TSchemaRuleSet.cxx:393
 TSchemaRuleSet.cxx:394
 TSchemaRuleSet.cxx:395
 TSchemaRuleSet.cxx:396
 TSchemaRuleSet.cxx:397
 TSchemaRuleSet.cxx:398
 TSchemaRuleSet.cxx:399
 TSchemaRuleSet.cxx:400
 TSchemaRuleSet.cxx:401
 TSchemaRuleSet.cxx:402
 TSchemaRuleSet.cxx:403
 TSchemaRuleSet.cxx:404
 TSchemaRuleSet.cxx:405
 TSchemaRuleSet.cxx:406
 TSchemaRuleSet.cxx:407
 TSchemaRuleSet.cxx:408
 TSchemaRuleSet.cxx:409
 TSchemaRuleSet.cxx:410
 TSchemaRuleSet.cxx:411
 TSchemaRuleSet.cxx:412
 TSchemaRuleSet.cxx:413
 TSchemaRuleSet.cxx:414
 TSchemaRuleSet.cxx:415
 TSchemaRuleSet.cxx:416
 TSchemaRuleSet.cxx:417
 TSchemaRuleSet.cxx:418
 TSchemaRuleSet.cxx:419
 TSchemaRuleSet.cxx:420
 TSchemaRuleSet.cxx:421
 TSchemaRuleSet.cxx:422
 TSchemaRuleSet.cxx:423
 TSchemaRuleSet.cxx:424
 TSchemaRuleSet.cxx:425
 TSchemaRuleSet.cxx:426
 TSchemaRuleSet.cxx:427
 TSchemaRuleSet.cxx:428
 TSchemaRuleSet.cxx:429
 TSchemaRuleSet.cxx:430
 TSchemaRuleSet.cxx:431
 TSchemaRuleSet.cxx:432
 TSchemaRuleSet.cxx:433
 TSchemaRuleSet.cxx:434
 TSchemaRuleSet.cxx:435
 TSchemaRuleSet.cxx:436
 TSchemaRuleSet.cxx:437
 TSchemaRuleSet.cxx:438
 TSchemaRuleSet.cxx:439
 TSchemaRuleSet.cxx:440
 TSchemaRuleSet.cxx:441
 TSchemaRuleSet.cxx:442
 TSchemaRuleSet.cxx:443
 TSchemaRuleSet.cxx:444
 TSchemaRuleSet.cxx:445
 TSchemaRuleSet.cxx:446
 TSchemaRuleSet.cxx:447
 TSchemaRuleSet.cxx:448
 TSchemaRuleSet.cxx:449
 TSchemaRuleSet.cxx:450
 TSchemaRuleSet.cxx:451
 TSchemaRuleSet.cxx:452
 TSchemaRuleSet.cxx:453
 TSchemaRuleSet.cxx:454
 TSchemaRuleSet.cxx:455
 TSchemaRuleSet.cxx:456
 TSchemaRuleSet.cxx:457
 TSchemaRuleSet.cxx:458
 TSchemaRuleSet.cxx:459
 TSchemaRuleSet.cxx:460
 TSchemaRuleSet.cxx:461
 TSchemaRuleSet.cxx:462
 TSchemaRuleSet.cxx:463
 TSchemaRuleSet.cxx:464
 TSchemaRuleSet.cxx:465
 TSchemaRuleSet.cxx:466
 TSchemaRuleSet.cxx:467
 TSchemaRuleSet.cxx:468
 TSchemaRuleSet.cxx:469
 TSchemaRuleSet.cxx:470
 TSchemaRuleSet.cxx:471
 TSchemaRuleSet.cxx:472
 TSchemaRuleSet.cxx:473
 TSchemaRuleSet.cxx:474
 TSchemaRuleSet.cxx:475
 TSchemaRuleSet.cxx:476
 TSchemaRuleSet.cxx:477
 TSchemaRuleSet.cxx:478
 TSchemaRuleSet.cxx:479
 TSchemaRuleSet.cxx:480
 TSchemaRuleSet.cxx:481
 TSchemaRuleSet.cxx:482
 TSchemaRuleSet.cxx:483
 TSchemaRuleSet.cxx:484
 TSchemaRuleSet.cxx:485
 TSchemaRuleSet.cxx:486
 TSchemaRuleSet.cxx:487
 TSchemaRuleSet.cxx:488
 TSchemaRuleSet.cxx:489
 TSchemaRuleSet.cxx:490
 TSchemaRuleSet.cxx:491
 TSchemaRuleSet.cxx:492
 TSchemaRuleSet.cxx:493
 TSchemaRuleSet.cxx:494
 TSchemaRuleSet.cxx:495
 TSchemaRuleSet.cxx:496
 TSchemaRuleSet.cxx:497
 TSchemaRuleSet.cxx:498
 TSchemaRuleSet.cxx:499
 TSchemaRuleSet.cxx:500
 TSchemaRuleSet.cxx:501
 TSchemaRuleSet.cxx:502
 TSchemaRuleSet.cxx:503
 TSchemaRuleSet.cxx:504
 TSchemaRuleSet.cxx:505
 TSchemaRuleSet.cxx:506
 TSchemaRuleSet.cxx:507
 TSchemaRuleSet.cxx:508
 TSchemaRuleSet.cxx:509
 TSchemaRuleSet.cxx:510
 TSchemaRuleSet.cxx:511
 TSchemaRuleSet.cxx:512
 TSchemaRuleSet.cxx:513
 TSchemaRuleSet.cxx:514
 TSchemaRuleSet.cxx:515
 TSchemaRuleSet.cxx:516
 TSchemaRuleSet.cxx:517
 TSchemaRuleSet.cxx:518
 TSchemaRuleSet.cxx:519
 TSchemaRuleSet.cxx:520
 TSchemaRuleSet.cxx:521
 TSchemaRuleSet.cxx:522
 TSchemaRuleSet.cxx:523
 TSchemaRuleSet.cxx:524
 TSchemaRuleSet.cxx:525
 TSchemaRuleSet.cxx:526
 TSchemaRuleSet.cxx:527
 TSchemaRuleSet.cxx:528
 TSchemaRuleSet.cxx:529
 TSchemaRuleSet.cxx:530
 TSchemaRuleSet.cxx:531
 TSchemaRuleSet.cxx:532
 TSchemaRuleSet.cxx:533
 TSchemaRuleSet.cxx:534
 TSchemaRuleSet.cxx:535
 TSchemaRuleSet.cxx:536
 TSchemaRuleSet.cxx:537
 TSchemaRuleSet.cxx:538
 TSchemaRuleSet.cxx:539
 TSchemaRuleSet.cxx:540
 TSchemaRuleSet.cxx:541
 TSchemaRuleSet.cxx:542
 TSchemaRuleSet.cxx:543
 TSchemaRuleSet.cxx:544
 TSchemaRuleSet.cxx:545
 TSchemaRuleSet.cxx:546
 TSchemaRuleSet.cxx:547
 TSchemaRuleSet.cxx:548
 TSchemaRuleSet.cxx:549
 TSchemaRuleSet.cxx:550
 TSchemaRuleSet.cxx:551
 TSchemaRuleSet.cxx:552
 TSchemaRuleSet.cxx:553
 TSchemaRuleSet.cxx:554
 TSchemaRuleSet.cxx:555
 TSchemaRuleSet.cxx:556
 TSchemaRuleSet.cxx:557
 TSchemaRuleSet.cxx:558
 TSchemaRuleSet.cxx:559
 TSchemaRuleSet.cxx:560
 TSchemaRuleSet.cxx:561
 TSchemaRuleSet.cxx:562
 TSchemaRuleSet.cxx:563
 TSchemaRuleSet.cxx:564
 TSchemaRuleSet.cxx:565
 TSchemaRuleSet.cxx:566
 TSchemaRuleSet.cxx:567
 TSchemaRuleSet.cxx:568
 TSchemaRuleSet.cxx:569