00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022 #include "TBranchProxy.h"
00023 #include "TLeaf.h"
00024 #include "TBranchElement.h"
00025 #include "TStreamerElement.h"
00026 #include "TStreamerInfo.h"
00027
00028 ClassImp(ROOT::TBranchProxy);
00029
00030 ROOT::TBranchProxy::TBranchProxy() :
00031 fDirector(0), fInitialized(false), fBranchName(""), fParent(0),
00032 fDataMember(""), fIsMember(false), fIsClone(false), fIsaPointer(0),
00033 fClassName(""), fClass(0), fElement(0), fMemberOffset(0), fOffset(0),
00034 fBranch(0), fBranchCount(0),
00035 fLastTree(0), fRead(-1), fWhere(0),fCollection(0)
00036 {
00037
00038 };
00039
00040 ROOT::TBranchProxy::TBranchProxy(TBranchProxyDirector* boss, const char* top,
00041 const char* name) :
00042 fDirector(boss), fInitialized(false), fBranchName(top), fParent(0),
00043 fDataMember(""), fIsMember(false), fIsClone(false), fIsaPointer(false),
00044 fClassName(""), fClass(0), fElement(0), fMemberOffset(0), fOffset(0),
00045 fBranch(0), fBranchCount(0),
00046 fLastTree(0), fRead(-1), fWhere(0),fCollection(0)
00047 {
00048
00049
00050 if (fBranchName.Length() && fBranchName[fBranchName.Length()-1]!='.' && name) {
00051 ((TString&)fBranchName).Append(".");
00052 }
00053 if (name) ((TString&)fBranchName).Append(name);
00054 boss->Attach(this);
00055 }
00056
00057 ROOT::TBranchProxy::TBranchProxy(TBranchProxyDirector* boss, const char *top, const char *name, const char *membername) :
00058 fDirector(boss), fInitialized(false), fBranchName(top), fParent(0),
00059 fDataMember(membername), fIsMember(true), fIsClone(false), fIsaPointer(false),
00060 fClassName(""), fClass(0), fElement(0), fMemberOffset(0), fOffset(0),
00061 fBranch(0), fBranchCount(0),
00062 fLastTree(0), fRead(-1), fWhere(0),fCollection(0)
00063 {
00064
00065
00066 if (name && strlen(name)) {
00067 if (fBranchName.Length() && fBranchName[fBranchName.Length()-1]!='.') {
00068 ((TString&)fBranchName).Append(".");
00069 }
00070 ((TString&)fBranchName).Append(name);
00071 }
00072 boss->Attach(this);
00073 }
00074
00075 ROOT::TBranchProxy::TBranchProxy(TBranchProxyDirector* boss, TBranchProxy *parent, const char* membername, const char* top,
00076 const char* name) :
00077 fDirector(boss), fInitialized(false), fBranchName(top), fParent(parent),
00078 fDataMember(membername), fIsMember(true), fIsClone(false), fIsaPointer(false),
00079 fClassName(""), fClass(0), fElement(0), fMemberOffset(0), fOffset(0),
00080 fBranch(0), fBranchCount(0),
00081 fLastTree(0), fRead(-1), fWhere(0),fCollection(0)
00082 {
00083
00084
00085 if (name && strlen(name)) {
00086 if (fBranchName.Length() && fBranchName[fBranchName.Length()-1]!='.') {
00087 ((TString&)fBranchName).Append(".");
00088 }
00089 ((TString&)fBranchName).Append(name);
00090 }
00091 boss->Attach(this);
00092 }
00093
00094 ROOT::TBranchProxy::~TBranchProxy()
00095 {
00096
00097 }
00098
00099 void ROOT::TBranchProxy::Reset()
00100 {
00101
00102
00103 fWhere = 0;
00104 fBranch = 0;
00105 fBranchCount = 0;
00106 fRead = -1;
00107 fClass = 0;
00108 fElement = 0;
00109 fMemberOffset = 0;
00110 fIsClone = false;
00111 fInitialized = false;
00112 fLastTree = 0;
00113 delete fCollection;
00114 fCollection = 0;
00115 }
00116
00117 void ROOT::TBranchProxy::Print()
00118 {
00119
00120
00121 cout << "fBranchName " << fBranchName << endl;
00122
00123 cout << "fBranch " << fBranch << endl;
00124 if (fBranchCount) cout << "fBranchCount " << fBranchCount << endl;
00125 }
00126
00127 Bool_t ROOT::TBranchProxy::Setup()
00128 {
00129
00130
00131
00132
00133 if (!fDirector->GetTree()) {
00134 return false;
00135 }
00136 if (fParent) {
00137
00138 fParent->Setup();
00139
00140 TClass *pcl = fParent->GetClass();
00141 R__ASSERT(pcl);
00142
00143 if (pcl==TClonesArray::Class()) {
00144
00145
00146 Int_t i = fDirector->GetReadEntry();
00147 if (i<0) fDirector->SetReadEntry(0);
00148 fParent->Read();
00149 if (i<0) fDirector->SetReadEntry(i);
00150
00151 TClonesArray *clones;
00152 clones = (TClonesArray*)fParent->GetStart();
00153
00154 pcl = clones->GetClass();
00155 } else if (pcl->GetCollectionProxy()) {
00156
00157
00158 if (fCollection) delete fCollection;
00159 fCollection = pcl->GetCollectionProxy()->Generate();
00160 pcl = fCollection->GetValueClass();
00161 if (pcl == 0) {
00162 Error("Setup","Not finding TClass for collecion for the data member %s seems no longer be in class %s",fDataMember.Data(),fParent->GetClass()->GetName());
00163 return false;
00164 }
00165 }
00166
00167 fElement = (TStreamerElement*)pcl->GetStreamerInfo()->GetElements()->FindObject(fDataMember);
00168 if (fElement == 0) {
00169 Error("Setup","Data member %s seems no longer be in class %s",fDataMember.Data(),pcl->GetName());
00170 return false;
00171 }
00172
00173 fIsaPointer = fElement->IsaPointer();
00174 fClass = fElement->GetClassPointer();
00175
00176
00177 fIsClone = (fClass==TClonesArray::Class());
00178
00179 fOffset = fMemberOffset = fElement->GetOffset();
00180
00181 fWhere = fParent->fWhere;
00182
00183 if (fParent->IsaPointer()) {
00184
00185
00186 } else {
00187
00188
00189 }
00190
00191
00192
00193 } else if (!fBranch) {
00194
00195
00196
00197 fBranch = fDirector->GetTree()->GetBranch(fBranchName.Data());
00198 if (!fBranch) return false;
00199
00200 {
00201
00202 TLeaf *leaf = (TLeaf*) fBranch->GetListOfLeaves()->At(0);
00203 if (leaf) leaf = leaf->GetLeafCount();
00204 if (leaf) {
00205 fBranchCount = leaf->GetBranch();
00206
00207
00208
00209 }
00210 }
00211
00212 fWhere = (double*)fBranch->GetAddress();
00213
00214 if (!fWhere && fBranch->IsA()==TBranchElement::Class()
00215 && ((TBranchElement*)fBranch)->GetMother()) {
00216
00217 TBranchElement* be = ((TBranchElement*)fBranch);
00218
00219 be->GetMother()->SetAddress(0);
00220 fWhere = (double*)fBranch->GetAddress();
00221
00222 }
00223 if (fBranch->IsA()==TBranch::Class()) {
00224 TLeaf *leaf2;
00225 if (fDataMember.Length()) {
00226 leaf2 = fBranch->GetLeaf(fDataMember);
00227 fWhere = leaf2->GetValuePointer();
00228 } else if (!fWhere) {
00229 leaf2 = (TLeaf*)fBranch->GetListOfLeaves()->At(0);
00230 fWhere = leaf2->GetValuePointer();
00231 }
00232 }
00233
00234 if (!fWhere) {
00235 fBranch->SetAddress(0);
00236 fWhere = (double*)fBranch->GetAddress();
00237 }
00238
00239
00240 if (fWhere && fBranch->IsA()==TBranchElement::Class()) {
00241
00242 TBranchElement* be = ((TBranchElement*)fBranch);
00243
00244 TStreamerInfo * info = be->GetInfo();
00245 Int_t id = be->GetID();
00246 if (id>=0) {
00247 fOffset = info->GetOffsets()[id];
00248 fElement = (TStreamerElement*)info->GetElements()->At(id);
00249 fIsaPointer = fElement->IsaPointer();
00250 fClass = fElement->GetClassPointer();
00251
00252 if ((fIsMember || (be->GetType()!=3 && be->GetType() !=4))
00253 && (be->GetType()!=31 && be->GetType()!=41)) {
00254
00255 if (fClass==TClonesArray::Class()) {
00256 Int_t i = be->GetTree()->GetReadEntry();
00257 if (i<0) i = 0;
00258 be->GetEntry(i);
00259
00260 TClonesArray *clones;
00261 if ( fIsMember && be->GetType()==3 ) {
00262 clones = (TClonesArray*)be->GetObject();
00263 } else if (fIsaPointer) {
00264 clones = (TClonesArray*)*(void**)((char*)fWhere+fOffset);
00265 } else {
00266 clones = (TClonesArray*)((char*)fWhere+fOffset);
00267 }
00268 if (!fIsMember) fIsClone = true;
00269 fClass = clones->GetClass();
00270 } else if (fClass && fClass->GetCollectionProxy()) {
00271 delete fCollection;
00272 fCollection = fClass->GetCollectionProxy()->Generate();
00273 fClass = fCollection->GetValueClass();
00274 }
00275
00276 }
00277 if (fClass) fClassName = fClass->GetName();
00278 } else {
00279 fClassName = be->GetClassName();
00280 fClass = TClass::GetClass(fClassName);
00281 }
00282
00283 if (be->GetType()==3) {
00284
00285
00286 if (!fIsMember) fIsClone = true;
00287 fIsaPointer = false;
00288 fWhere = be->GetObject();
00289
00290 } else if (be->GetType()==4) {
00291
00292
00293 fCollection = be->GetCollectionProxy()->Generate();
00294 fIsaPointer = false;
00295 fWhere = be->GetObject();
00296
00297 } else if (id<0) {
00298
00299
00300 fIsaPointer = false;
00301 fWhere = be->GetObject();
00302
00303 } else if (be->GetType()==41) {
00304
00305 fCollection = be->GetCollectionProxy()->Generate();
00306 fWhere = be->GetObject();
00307 fOffset += be->GetOffset();
00308
00309 } else if (be->GetType()==31) {
00310
00311 fWhere = be->GetObject();
00312 fOffset += be->GetOffset();
00313
00314 } else if (be->GetType()==2) {
00315
00316
00317 fWhere = be->GetObject();
00318
00319 } else {
00320
00321
00322 fWhere = ((unsigned char*)be->GetObject()) + fOffset;
00323
00324 }
00325 } else {
00326 fClassName = fBranch->GetClassName();
00327 fClass = TClass::GetClass(fClassName);
00328 }
00329
00330
00331
00332
00333
00334
00335
00336
00337
00338
00339
00340
00341
00342
00343
00344
00345
00346
00347
00348
00349
00350 if ( fBranch->IsA()==TBranchElement::Class() &&
00351 (((TBranchElement*)fBranch)->GetType()==3 || fClass==TClonesArray::Class()) &&
00352 !fIsMember ) {
00353 fIsClone = true;
00354 }
00355
00356 if (fIsMember) {
00357 if ( fBranch->IsA()==TBranchElement::Class() &&
00358 fClass==TClonesArray::Class() &&
00359 (((TBranchElement*)fBranch)->GetType()==31 || ((TBranchElement*)fBranch)->GetType()==3) ) {
00360
00361 TBranchElement *bcount = ((TBranchElement*)fBranch)->GetBranchCount();
00362 TString member;
00363 if (bcount) {
00364 TString bname = fBranch->GetName();
00365 TString bcname = bcount->GetName();
00366 member = bname.Remove(0,bcname.Length()+1);
00367 } else {
00368 member = fDataMember;
00369 }
00370
00371 fMemberOffset = fClass->GetDataMemberOffset(member);
00372
00373 if (fMemberOffset<0) {
00374 Error("Setup","%s",Form("Negative offset %d for %s in %s",
00375 fMemberOffset,fBranch->GetName(),
00376 bcount?bcount->GetName():"unknown"));
00377 }
00378
00379 } else if (fClass) {
00380
00381 fElement = (TStreamerElement*)
00382 fClass->GetStreamerInfo()->GetElements()->FindObject(fDataMember);
00383 if (fElement)
00384 fMemberOffset = fElement->GetOffset();
00385 else {
00386
00387
00388 TString member;
00389
00390 Bool_t forgotWhenThisHappens = false;
00391 R__ASSERT(forgotWhenThisHappens);
00392
00393 member += fDataMember;
00394 fMemberOffset = fClass->GetDataMemberOffset(member);
00395
00396 }
00397
00398 } else if (fBranch->IsA() != TBranch::Class()) {
00399 Error("Setup","%s",Form("Missing TClass object for %s\n",fClassName.Data()));
00400 }
00401
00402 if ( fBranch->IsA()==TBranchElement::Class()
00403 && (((TBranchElement*)fBranch)->GetType()==31 || ((TBranchElement*)fBranch)->GetType()==3) ) {
00404
00405 fOffset = fMemberOffset;
00406
00407 } else {
00408
00409 fWhere = ((unsigned char*)fWhere) + fMemberOffset;
00410 }
00411 }
00412 }
00413 if (fClass==TClonesArray::Class()) fIsClone = true;
00414 if (fWhere!=0) {
00415 if (fCollection) {
00416 if (IsaPointer()) {
00417 fCollection->PushProxy( *(void**)fWhere );
00418 } else {
00419 fCollection->PushProxy( fWhere );
00420 }
00421 }
00422 fLastTree = fDirector->GetTree();
00423 fInitialized = true;
00424 return true;
00425 } else {
00426 return false;
00427 }
00428 }