ATO-37 - STEER/CDB/AliOCDBtoolkit.cxx - Use consistently SetSpecificStorage
[u/mrichter/AliRoot.git] / STEER / CDB / AliOCDBtoolkit.cxx
1 /**************************************************************************
2  * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
3  *                                                                        *
4  * Author: The ALICE Off-line Project.                                    *
5  * Contributors are mentioned in the code where appropriate.              *
6  *                                                                        *
7  * Permission to use, copy, modify and distribute this software and its   *
8  * documentation strictly for non-commercial purposes is hereby granted   *
9  * without fee, provided that the above copyright notice appears in all   *
10  * copies and that both the copyright notice and this permission notice   *
11  * appear in the supporting documentation. The authors make no claims     *
12  * about the suitability of this software for any purpose. It is          *
13  * provided "as is" without express or implied warranty.                  *
14  **************************************************************************/
15
16 /*
17
18   Primary goal of the proposal was to provide functionality to browse and compare the content of the OCDB
19   specified by different means.
20
21   a.) galice.root               - as currently implemented by Ruben in MC (or any file with cdbMap, and cdbList)
22   b.) AliESDs.root              - for the reconstructed data
23   c.) ocdb snapshot             - as used for grid productions
24   d.) TMap(s)                   - as used internally in galice.root and AliESDs,root  
25   e.) log file (if possible)    - looks logs aways used similar syntax, tested and working
26   f.) C macro                   - custom macro
27
28   Content comparison should be done:
29   a.) on the level of symbolic links 
30   b.) on the level of content itself 
31   - by by byte comparison dif
32   - data member by data member comparison
33
34   Implementation assumption:
35   All input formats (a .. f) will  be converted to the TMap storages and TList if AliCDBIds 
36
37   Example usage:
38   AliOCDBtoolkit::MakeDiffExampleUseCase();
39   or from the AliOCDBtoolkit.sh in propmpt
40   ocdbMakeTable AliESDs.root ESD OCDBrec.list
41   ocdbMakeTable galice.root MC OCDBsim.list
42
43   
44    
45
46
47
48   //=============================================================================
49   // Functionality to dump content of  objects in human readable format
50   //=============================================================================
51   Use case examples 
52   1.) compare oontent of alignent OCDB files for differnt yers
53   2.) compare ClusterParam for different periods
54   
55   
56    
57   =================================================================================================================
58   // 1.)
59   // Compare alignment example:
60   // Compare TPC alignemnt 2013 and 2010
61   //
62   AliOCDBtoolkit::DumpOCDBFile("/cvmfs/alice.gsi.de/alice/data/2013/OCDB/TPC/Align/Data/Run0_999999999_v1_s0.root","TPCalign2013.dump",1,1);
63   AliOCDBtoolkit::DumpOCDBFile("/cvmfs/alice.gsi.de/alice/data/2010/OCDB/TPC/Align/Data/Run0_999999999_v1_s0.root","TPCalign2010.dump",1,1);
64   diff  TPCalign2013.dump TPCalign2010.dump > TPCalign2013_TPCalign2010.diff
65   //
66   //    
67   =================================================================================================================
68   //  2.) 
69   // Compare CluterParam OCDB etry
70   //
71   AliOCDBtoolkit::DumpOCDBFile("/cvmfs/alice.gsi.de/alice/data/2010/OCDB/TPC/Calib/ClusterParam/Run131541_999999999_v2_s0.root","2010_TPC_Calib_ClusterParam_Run131541_999999999_v2_s0.dump",1);
72   AliOCDBtoolkit:: AliOCDBtoolkit::DumpOCDBFile("/cvmfs/alice.gsi.de/alice/data/2010/OCDB/TPC/Calib/ClusterParam/Run0_999999999_v1_s0.root","2010_TPC_Calib_ClusterParam_Run0_999999999_v1_s0.dump",1);
73   AliOCDBtoolkit::DumpOCDBFile("/cvmfs/alice.gsi.de/alice/data/2013/OCDB/TPC/Calib/ClusterParam/Run0_999999999_v1_s0.root","2013_TPC_Calib_ClusterParam_Run0_999999999_v1_s0.dump",1);
74   diff 2010_TPC_Calib_ClusterParam_Run131541_999999999_v2_s0.dump 2010_TPC_Calib_ClusterParam_Run0_999999999_v1_s0.dump
75  
76
77 */
78
79 /*
80   To check:
81   1.) Verify hash value uasge as and MD5 sum - 
82
83  */
84
85 using namespace std;
86
87 // STD
88 #include <iostream>
89 #include <algorithm>
90 #include <sstream>
91 #include <stdexcept>
92 #include <functional>
93 #include "TRealData.h"
94 #include "TDataMember.h"
95 #include "TClass.h"
96 #include "TROOT.h"
97 #include <TVectorD.h>
98 //
99 #include "TSystem.h"
100 #include "TObjArray.h"
101 #include "TString.h"
102 #include "TTree.h"
103 #include "TMessage.h"
104 //
105 #include "AliCDBManager.h"
106 #include "AliCDBEntry.h"
107 #include "AliOCDBtoolkit.h"
108 #include "AliCDBStorage.h"
109
110
111 void AliOCDBtoolkit::MakeDiffExampleUseCase(){
112   //
113   // Example usage for the MC 
114   // To run example case, assuming presence of following files in working directory: 
115   //    - rec.log        
116   //    - galice.root   
117   //    - AliESDs.root
118   //
119   AliCDBManager * man = AliCDBManager::Instance();
120   AliOCDBtoolkit::LoadOCDBFromLog("rec.log",0);
121   const TMap *cdbMapLog= man->GetStorageMap();        // this is map of 
122   const TList *cdbListLog=man->GetRetrievedIds();     // this is list of AliCDBId
123   //  TList *cdbListLog0=man->GetRetrievedIds();     // this is list of AliCDBId
124   //
125   TFile *fmc = TFile::Open("galice.root");
126   TMap *cdbMapMC= (TMap*)fmc->Get("cdbMap");          // 
127   TList *cdbListMC0= (TList*)fmc->Get("cdbList");     // this is list of TObjStrings
128   TList *cdbListMC = AliOCDBtoolkit::ConvertListStringToCDBId(cdbListMC0);        // convert to the TObjArray of AliCDBids
129   //
130   TFile *fesd = TFile::Open("AliESDs.root");
131   TList *listESD = ((TTree*)fesd->Get("esdTree"))->GetUserInfo();
132   TMap *cdbMapESD= (TMap*)listESD->FindObject("cdbMap");  
133   TList *cdbListESD0= (TList*)listESD->FindObject("cdbList"); // this is list of TObjStrings
134   TList *cdbListESD = AliOCDBtoolkit::ConvertListStringToCDBId(cdbListESD0);              // convert to the TObjArray  of AliCDBids
135   //
136   //
137   //
138   printf("\n\n");
139   printf("Diff log>>>ESD\n\n:");
140   MakeDiff(cdbMapLog, cdbListLog, cdbMapESD, cdbListESD,0);
141   printf("\n\n");
142   printf("Diff ESD>>>log\n\n:");
143   MakeDiff(cdbMapESD, cdbListESD,cdbMapLog, cdbListLog,0);
144   // 
145   printf("\n\n");
146   printf("Diff ESD>>>MC\n\n:");
147   MakeDiff(cdbMapMC, cdbListMC, cdbMapESD, cdbListESD,0);
148 }
149
150
151 void AliOCDBtoolkit::DumpOCDBAsTxt(const TString fInput, const TString fType, const TString outfile){
152   //
153   //
154   //
155   TFile *file;
156   const TMap *cdbMap=0;
157   const TList *cdbList=0;
158   //
159   //
160   AliCDBManager * man = AliCDBManager::Instance();
161
162   if(fType.EqualTo("MC",TString::kIgnoreCase)){
163         file = TFile::Open(fInput.Data());
164         cdbMap = (TMap*)file->Get("cdbMap");
165         if (!cdbMap){
166           printf("cdbMap does not exist in input file\t%s. Exiting\n",fInput.Data());
167           return;
168         }
169         // 
170         man->SetDefaultStorage(((TPair*)cdbMap->FindObject("default"))->Value()->GetName());
171         TList *cdbListMC0 = (TList*)file->Get("cdbList");     // this is list of TObjStrings
172         cdbList = AliOCDBtoolkit::ConvertListStringToCDBId(cdbListMC0);        // convert to the TObjArray of AliCDBids
173   } 
174     else if(fType.EqualTo("ESD",TString::kIgnoreCase)){
175       file = TFile::Open(fInput.Data());
176       if (!file) {
177         printf("Input file  does not exist %s. Exiting\n",fInput.Data());
178         return;
179       }
180       TList *listESD = ((TTree*)file->Get("esdTree"))->GetUserInfo();
181       cdbMap = (TMap*)listESD->FindObject("cdbMap");  
182       if (!cdbMap){
183         printf("cdbMap does not exist in input file\t%s. Exiting\n",fInput.Data());
184         return;
185       }
186       man->SetDefaultStorage(((TPair*)cdbMap->FindObject("default"))->Value()->GetName());
187       TList *cdbListESD0= (TList*)listESD->FindObject("cdbList"); // this is list of TObjStrings
188       cdbList = ConvertListStringToCDBId(cdbListESD0);              // convert to the TObjArray  of AliCDBids
189     }
190     else if(fType.EqualTo("log",TString::kIgnoreCase)){
191         LoadOCDBFromLog(fInput.Data(),0);
192         cdbMap = man->GetStorageMap();        // this is map of 
193         cdbList =man->GetRetrievedIds();     // this is list of AliCDBId
194     }
195     else{
196         printf("unsupported option: %s",fType.Data());
197         return;
198     }
199   cout <<"BEGINDUMP:" << endl;
200   DumpOCDB(cdbMap,cdbList,outfile);
201 }
202
203
204 Bool_t AliOCDBtoolkit::ParseInfoFromOcdbString(TString ocdbString, TString &ocdbPath, Int_t &run0, Int_t &run1, Int_t &version, Int_t &subVersion){
205   // Functionalit
206   // Parse OCDB id string and provide basic ocdb information
207   //
208   //  a.) parse ocdbPath
209   Int_t indexBeginPath= ocdbString.Index("path: ")+7;
210   if (indexBeginPath<0) return kFALSE;
211   Int_t indexEndPath=ocdbString.Index(";",indexBeginPath);
212   if (indexEndPath<0) return kFALSE;
213   ocdbPath=TString(&(ocdbString.Data()[indexBeginPath]), indexEndPath-indexBeginPath-1);
214   // b.) parse runRange
215   Int_t indexRun0= ocdbString.Index(": [",indexEndPath)+3;
216   if (indexRun0<0) return kFALSE;
217   Int_t indexRun1= ocdbString.Index(",",indexRun0)+1;
218   if (indexRun1<0) return kFALSE;
219   run0=atoi(&(ocdbString.Data()[indexRun0]));
220   run1=atoi(&(ocdbString.Data()[indexRun1]));
221   AliCDBRunRange runRange(run0,run1);
222   //c.) parse version, subversion
223   Int_t indexVersion= ocdbString.Index("version: v",indexRun1)+10;
224   if (indexVersion<0) return kFALSE;
225   Int_t indexSubVersion= ocdbString.Index("_s",indexVersion)+2;
226   if (indexSubVersion<0) return kFALSE;
227   version=atoi(&(ocdbString.Data()[indexVersion]));
228   subVersion=atoi(&(ocdbString.Data()[indexSubVersion]));
229   return kTRUE;
230 }
231
232 Bool_t AliOCDBtoolkit::ParseInfoFromOcdbString(TString ocdbString, AliCDBId &cdbId){
233   //
234   // Parse OCDB id string and provide basic ocdb information and fillcdbID object
235   //
236   TString ocdbPath;
237   Int_t run0=0, run1=0;
238   Int_t version=0, subVersion=0;
239   Bool_t parseStatus = ParseInfoFromOcdbString(ocdbString, ocdbPath, run0,run1,version,subVersion); 
240   if (parseStatus) {
241     AliCDBRunRange runRange(run0,run1);
242     cdbId=AliCDBId(ocdbPath.Data(),runRange,version,subVersion);
243     AliCDBId* id = AliCDBId::MakeFromString(ocdbString);
244     cdbId=*id;
245     delete id;
246   }
247   //
248   return parseStatus;
249 }
250
251 TList  * AliOCDBtoolkit::ConvertListStringToCDBId(const TList *cdbList0){
252   //
253   // Convert input  list of the TObjString to list to AliCDBid 
254   //
255   Int_t entriesList0=cdbList0->GetEntries();
256   TList * array0 = new TList();
257   AliCDBId tmp0;
258   for (Int_t ientry0=0; ientry0<entriesList0; ientry0++){
259     if (cdbList0->At(ientry0)==0) continue;
260     Bool_t isId =  cdbList0->At(ientry0)->IsA()->InheritsFrom("AliCDBId");
261     if (isId){
262       array0->AddLast(cdbList0->At(ientry0));
263     }else{
264       Bool_t isString =  cdbList0->At(ientry0)->IsA()->InheritsFrom("TObjString");
265       if (isString){
266         TObjString* sid0 = dynamic_cast<TObjString*> (cdbList0->At(ientry0));
267         Bool_t status =  ParseInfoFromOcdbString(sid0->String(), tmp0);
268         if (!status) continue; 
269         array0->AddLast(new AliCDBId(tmp0));
270       }
271     }
272   }
273   return array0;  
274 }
275
276
277
278 void AliOCDBtoolkit::LoadOCDBFromLog(const char *logName, Int_t verbose){
279   //
280   // Initilaize OCDB
281   // Load OCDB setting as specified in log
282   // Assuming fixed version of the log 
283   // AliCDBManager is initilaized - ocdbMap and ID list can be exported
284   //
285
286   // Parsing/loading sequence:
287   //    0.) SetDefault storage  *** Default Storage URI:
288   //    1.) SetSpecific storage  *** Specific storage
289   //    2.) SetRunNumber  Run number:
290   //    3.) Set used IDs
291   //
292   AliCDBManager * man = AliCDBManager::Instance();
293   //
294   // 0.) SetDefault storage  *** Default Storage URI:
295   // 
296   TString  defaultOCDB = gSystem->GetFromPipe(TString::Format("cat %s| grep \"Storage URI:\"",logName).Data());
297   TObjArray *array = defaultOCDB.Tokenize("\"");
298   man->SetDefaultStorage(array->Last()->GetName());
299   delete array;
300   //
301   // 1.) SetSpecific storage  *** Specific storage
302   //
303   TString  specificStorage  = gSystem->GetFromPipe(TString::Format("cat %s| grep \"Specific storage\"",logName).Data());
304   array = specificStorage.Tokenize("\"");
305   Int_t entries = array->GetEntries();
306   for (Int_t i=1; i<entries-2; i+=4){    
307     // add protection here line shuld be in expected format
308     if ((verbose&2)>0) printf("%s\t%s\n",array->At(i)->GetName(),array->At(i+2)->GetName());    
309     man->SetSpecificStorage(array->At(i)->GetName(),array->At(i+2)->GetName());
310   }
311   delete array;
312   //
313   // 2.) SetRunNumber  Run number:
314   //
315   TString  runLine  = gSystem->GetFromPipe(TString::Format("cat %s| grep \"I-AliCDBManager::Print: Run number =\"",logName).Data());
316   array = runLine.Tokenize("=");
317   Int_t run = 0;
318   if (array->GetEntries()>1) run=atoi(array->At(1)->GetName()); 
319   delete array;
320   man->SetRun(run);  
321   //
322   // 3.) Set used IDs
323   //   
324   TString  ids =   gSystem->GetFromPipe(TString::Format("cat %s| grep I-AliCDB | grep path| grep range | grep version", logName).Data());
325   array= ids.Tokenize("\n");
326   entries = array->GetEntries();
327   //
328   for (Int_t i=0; i<entries; i++){
329     //
330     TString ocdbString = array->At(i)->GetName();
331     TString ocdbEntry;
332     TString ocdbPath;
333     Int_t run0=0, run1=0;
334     Int_t version=0, subVersion=0;
335     Bool_t parseStatus = ParseInfoFromOcdbString(ocdbString, ocdbPath, run0,run1,version,subVersion); 
336     if (!parseStatus) continue;
337     AliCDBRunRange runRange(run0,run1);
338     //
339     if ((verbose&2)!=0) {
340       printf("%s/Run%d_%d_v%d_s%d.root\n",ocdbPath.Data(),run0,run1,version,subVersion); 
341     }
342     try {
343       man->Get(ocdbPath.Data(),runRange,version,subVersion);      
344     } catch(const exception &e){
345       cerr << "OCDB retrieval failed!" << endl;
346       cerr << "Detailes: " << e.what() << endl;
347     }    
348   }  
349   if ((verbose&1)!=0){
350     man->Print();
351     man->GetStorageMap()->Print();
352     man->GetRetrievedIds()->Print(); 
353   }
354 }
355
356 void  AliOCDBtoolkit::SetStorage(const TMap *cdbMap){
357   //
358   // Set storages as speified in the map - TO CHECK.. Should go to the AliCDBmanager if not alreadyhhere
359   //   
360   AliCDBManager * man = AliCDBManager::Instance();  
361   TIter iter(cdbMap->GetTable());
362   TPair* aPair=0;
363   while ((aPair = (TPair*) iter.Next())) {
364     //    aPair->Value();
365     //aPair->Print();
366     if (TString(aPair->GetName())=="default") man->SetDefaultStorage(aPair->Value()->GetName());
367     else
368       man->SetSpecificStorage(aPair->GetName(), aPair->Value()->GetName());
369   }  
370 }
371  
372 void AliOCDBtoolkit::LoadOCDBFromMap(const TMap *cdbMap, const TList *cdbList){
373   //
374   // Initilaize OCDB
375   // Load OCDB setting as specified in maps
376   // Or Do we have already implementation in AliCDBanager?  TO CHECK.. Should go to the AliCDBmanager if not alreadyhhere
377   AliCDBManager * man = AliCDBManager::Instance();  
378   AliOCDBtoolkit::SetStorage(cdbMap);  
379   TIter iter(cdbList);
380   TObjString *ocdbString=0;
381   while (( ocdbString= (TObjString*) iter.Next())) {
382     AliCDBId* cdbId = AliCDBId::MakeFromString(ocdbString->String());
383     try {
384       //      AliCDBEntry * cdbEntry = (AliCDBEntry*) man->Get(*cdbId,kTRUE);
385       man->Get(*cdbId,kTRUE);
386     } catch(const exception &e){
387       cerr << "OCDB retrieval failed!" << endl;
388       cerr << "Detailes: " << e.what() << endl;
389     }   
390   }    
391 }
392
393 void AliOCDBtoolkit::LoadOCDBFromESD(const char *fname){
394   //
395   // Load OCDB setup from the ESD file
396   // 
397   TFile * fesd = TFile::Open(fname);
398   TList *listESD = ((TTree*)fesd->Get("esdTree"))->GetUserInfo();
399   TMap *cdbMapESD= (TMap*)listESD->FindObject("cdbMap");  
400   TList *cdbListESD0= (TList*)listESD->FindObject("cdbList"); // this is list of TObjStrings
401   AliOCDBtoolkit::SetStorage(cdbMapESD); 
402   AliOCDBtoolkit::LoadOCDBFromMap(cdbMapESD, cdbListESD0);
403 }
404
405
406 void AliOCDBtoolkit::MakeDiff(const TMap *cdbMap0, const TList *cdbList0, const TMap */*cdbMap1*/, const TList *cdbList1, Int_t /*verbose*/){
407   //
408   //
409   // Print difference between the 2 ocdb maps
410   // Input:
411   //   maps and list charactireizing OCDB setup  
412   // Output:
413   //   To be decided.
414   //
415   AliOCDBtoolkit::SetStorage(cdbMap0);
416   Int_t entriesList0=cdbList0->GetEntries();
417   Int_t entriesList1=cdbList1->GetEntries();
418   //
419   for (Int_t ientry0=0; ientry0<entriesList0; ientry0++){
420     AliCDBId *id0    = dynamic_cast<AliCDBId*> (cdbList0->At(ientry0));
421     AliCDBId *id1=0;
422     for (Int_t ientry1=0; ientry1<entriesList1; ientry1++){
423       AliCDBId *cid1    = dynamic_cast<AliCDBId*> (cdbList1->At(ientry1));
424       //id0.Print();
425       //cid1.Print();
426       if (cid1->GetPath().Contains(id0->GetPath().Data())==0) continue;
427       id1=cid1;
428     }
429     if (!id1) {
430       printf("Missing entry\t");
431       id0->Print();
432       continue;
433     }
434     //   Bool_t isOK=kTRUE;
435     if (id0->GetFirstRun()!= id1->GetFirstRun() ||id0->GetLastRun()!= id1->GetLastRun()){
436       printf("Differrent run range\n");
437       id0->Print();
438       id1->Print();
439     }    
440     if (id0->GetVersion()!= id1->GetVersion() ||id0->GetSubVersion()!= id1->GetSubVersion()){
441       printf("Differrent version\n");
442       id0->Print();
443       id1->Print();
444     }    
445   }
446 }
447
448 void AliOCDBtoolkit::DumpOCDB(const TMap *cdbMap0, const TList *cdbList0, const TString outfile){
449   //
450   // Dump the OCDB configuatation as formated text file 
451   // with following collumns
452   // cdb name  prefix cdb path
453   // OCDB entries are sorted alphabetically
454   // e.g:
455   // TPC/Calib/RecoParam /hera/alice/jwagner/software/aliroot/AliRoot_TPCdev/OCDB/ TPC/Calib/RecoParam/Run0_999999999_v0_s0.root $SIZE_AliCDBEntry_Object $HASH_AliCDBEntry_Object
456   
457   AliCDBManager * man = AliCDBManager::Instance();
458   AliOCDBtoolkit::SetStorage(cdbMap0);  
459   TList * cdbList = (TList*) cdbList0;   // sorted array
460   cdbList->Sort();
461
462   TIter next(cdbList);
463   AliCDBId *CDBId=0;
464   TString cdbName="";
465   TString cdbPath="";
466   TObjString *ostr;
467   AliCDBEntry *cdbEntry=0;
468   UInt_t hash;
469   TMessage * file;
470   Int_t size; 
471   FILE *ofs = fopen(outfile.Data(),"w");
472   
473   while ((CDBId  =(AliCDBId*) next())){
474     cdbName = CDBId->GetPath();
475     ostr = (TObjString*)cdbMap0->GetValue(cdbName.Data());
476     if(!ostr) ostr = (TObjString*)cdbMap0->GetValue("default");
477     cdbPath = ostr->GetString();
478     if(cdbPath.Contains("local://"))cdbPath=cdbPath(8,cdbPath.Length()).Data();
479     try {
480       cdbEntry = (AliCDBEntry*) man->Get(*CDBId,kTRUE);
481     }catch(const exception &e){
482       cerr << "OCDB retrieval failed!" << endl;
483       cerr << "Detailes: " << e.what() << endl;
484     }  
485     if (!cdbEntry) {
486       printf("Object not avaliable\n");
487       CDBId->Print();
488       continue;
489     }
490     TObject *obj = cdbEntry->GetObject();
491     file = new TMessage(TBuffer::kWrite);
492     file->WriteObject(obj);
493     size = file->Length();
494     if(!obj){
495       fprintf(ofs,"object %s empty!\n",cdbName.Data());
496       continue;
497     }
498     hash = TString::Hash(file->Buffer(),size);
499     fprintf(ofs,"%s\t%s\t%s/Run%d_%d_v%d_s%d.root\t%d\t%u\n",
500            cdbName.Data(),
501            cdbPath.Data(),
502            cdbName.Data(),
503            CDBId->GetFirstRun(),
504            CDBId->GetLastRun(),
505            CDBId->GetVersion(),
506            CDBId->GetSubVersion(),
507            size,
508            hash
509            );
510     //if(!(CDBId->GetPathLevel(0)).Contains("TPC")) continue;
511     //cout << CDBId.ToString() << endl;
512     delete file;
513   }
514   fclose(ofs);
515 }
516
517
518 //====================================================================================================
519 //  Dump object part
520 //==================================================================================================== 
521
522
523
524
525
526 void AliOCDBtoolkit::DumpOCDBFile(const char *finput , const char *foutput, Bool_t dumpMetaData, Bool_t xml){
527   //
528   //  
529   //  DumpOCDBFile("$ALICE_ROOT/OCDB/ITS/Align/Data/Run0_999999999_v0_s0.root", "ITS_Align_Data_Run0_999999999_v0_s0.dump")
530   //
531   if (finput==0) return ;
532   TFile *falignITS  = TFile::Open(finput);
533   AliCDBEntry *entry  = (AliCDBEntry*)falignITS->Get("AliCDBEntry");
534   if (!entry) return; 
535   TObject *obj = ((AliCDBEntry*)falignITS->Get("AliCDBEntry"))->GetObject();  
536
537   //
538   if (!xml){
539     if (dumpMetaData) gROOT->ProcessLine(TString::Format("((TObject*)%p)->Dump(); >%s",entry, foutput).Data());
540     if (!obj) return;
541     gROOT->ProcessLine(TString::Format("AliOCDBtoolkit::DumpObjectRecursive((TObject*)%p); >>%s",obj, foutput).Data());
542   }
543   if (xml){
544     TFile * f = TFile::Open(TString::Format("%s.xml",foutput).Data(),"recreate");
545     if (dumpMetaData) entry->Write("AliCDBEntry");
546     else obj->Write("AliCDBEntry");
547     f->Close();
548   }
549 }
550
551
552
553 void AliOCDBtoolkit::DumpObjectRecursive(TObject *obj){
554   //
555   //
556   //
557   Int_t counterRec=0;
558   printf("==> Dumping object at: %p, name=%s, class=%s)\n", obj, obj->GetName(), (obj->IsA()->GetName()));
559   DumpObjectRecursive(obj, TString(obj->IsA()->GetName())+".",counterRec);
560 }
561  
562 //
563 //
564 //
565 void AliOCDBtoolkit::DumpObjectRecursive(TObject *obj, TString prefix, Int_t &counterRec){
566   //
567   // Recursive dump of the TObject
568   // Dump all basic types and follow pointers to the objects
569   // current limitation:
570   //    a.) clases and structures not derived from TObject not followed (to fix)
571   //    b.) dynamic arrays not followed
572   //    c.) std maps,array ....  not followed
573   //    
574   //
575   if (!obj) return;
576   //
577   // Special case of Collection classes
578   //
579   if (obj->IsA()->InheritsFrom(TCollection::Class())) {
580     TIter myiter((TCollection*)obj);
581     TObject  *arObject=0;
582     Int_t counter=0;
583     while ((arObject = (TObject*)myiter.Next())) {
584       TString prefixArr = TString::Format("%s[%d]",prefix.Data(),counter);
585       DumpObjectRecursive(arObject,prefixArr,counterRec);
586       counter++;
587     } 
588     counterRec++;
589     return;
590   }
591
592   TClass * cl = obj->IsA();
593   if (!(cl->GetListOfRealData())) cl->BuildRealData();
594   TRealData* rd = 0;
595   TIter next(cl->GetListOfRealData());  
596   while ((rd = (TRealData*) next())) {
597     counterRec++;
598     TDataMember* dm = rd->GetDataMember();
599     TDataType* dtype = dm->GetDataType();
600     Int_t offset = rd->GetThisOffset();
601     char* pointer = ((char*) obj) + offset;
602     
603     if (dm->IsaPointer()) {
604       // We have a pointer to an object or a pointer to an array of basic types.
605       TClass* clobj = 0;
606       if (!dm->IsBasic()) {
607         clobj = TClass::GetClass(dm->GetTypeName());
608       }
609       if (clobj) {
610         // We have a pointer to an object.
611         //
612         if (!clobj->InheritsFrom(TObject::Class())) {
613           // It must be a TObject object.
614           continue; 
615         }
616         char** apointer = (char**) pointer;
617         TObject* robj = (TObject*) *apointer;
618         //      
619         if(!robj)
620           printf("M:%s%s\n",prefix.Data(),dm->GetName()); // Missing - 0 pointer
621         else{
622           printf("T:%s\t%s%s\n", clobj->GetName(),prefix.Data(), dm->GetName());
623           TString prefixNew=prefix;
624           prefixNew+=dm->GetName();
625           prefixNew+=".";
626           if (robj!=obj) DumpObjectRecursive(robj,prefixNew,counterRec);  // trivial check 
627           if (robj==obj){
628             printf("R:%s\t%s%s\n",clobj->GetName(),prefix.Data(), dm->GetName());
629           }
630         }
631       }
632     } else if (dm->IsBasic()) {
633       //
634       // Basic data type
635       //
636       const char* index = dm->GetArrayIndex();
637       if (dm->GetArrayDim()==0){
638         printf("B:\t%s%s\t%s\n", prefix.Data(),rd->GetName(), dtype->AsString(pointer));
639       }
640       //
641       // Basic array - fixed length
642       //
643       //      if (dm->GetArrayDim()>0 && strlen(index) != 0){
644       if (dm->GetArrayDim()>0 ){
645         printf("A:\t%s%s\t",prefix.Data(),rd->GetName());
646         Int_t counter=0;
647         for  (Int_t idim=0; idim<dm->GetArrayDim(); idim++){
648           //printf("A:%d\t%d\n", dm->GetArrayDim(),dm->GetMaxIndex(idim));
649           for (Int_t j=0; j<dm->GetMaxIndex(idim); j++){
650             printf("%s\t",dtype->AsString(pointer+dm->GetUnitSize()*counter));
651             counter++;
652             if (counter%5==0) printf("\nA:\t%s%s\t",prefix.Data(),rd->GetName());
653           }
654         }
655         printf("\n");
656       }
657       //
658       // Basic array - dynamic length
659       //
660       if (dm->GetArrayDim()>0 && strlen(index) != 0){
661         //
662         // Dump first only for the moment
663         //  
664         printf("B:\t%s%s\t%s\n",prefix.Data(),rd->GetName(), dtype->AsString(pointer));
665       }
666     } else {
667     }
668   }
669 }  
670
671 //
672 // Small checks to test the TRealData and TDataType
673 //
674
675
676
677 void DumpDataSimple(){
678   //
679   // Dump example for elenatr data types 
680   //
681   TObject *obj = new TVectorD(20);
682   TClass * cl = obj->IsA();
683   if (!cl->GetListOfRealData()) cl->BuildRealData();
684   //
685   TRealData* rd = 0;
686   rd = (TRealData*)(cl->GetListOfRealData()->FindObject("fNrows"));
687   TDataMember* dm = rd->GetDataMember();
688   TDataType* dtype = dm->GetDataType();
689   //
690   Int_t offset = rd->GetThisOffset();
691   char* pointer = ((char*) obj) + offset;
692   printf("%s\n",dtype->AsString(pointer));
693 }
694
695 void DumpDataArray(){
696   //
697   // print array example
698   // 
699   TObject *obj = new TVectorD(20);
700   TClass * cl = obj->IsA();
701   if (!cl->GetListOfRealData()) cl->BuildRealData();
702   TRealData* rd = 0;
703   rd = (TRealData*)(cl->GetListOfRealData()->FindObject("*fElements"));
704   TDataMember* dm = rd->GetDataMember();
705   TDataType* dtype = dm->GetDataType();
706   dtype->Print();
707   //
708   Int_t offset = rd->GetThisOffset();
709   char* pointer = ((char*) obj) + offset; 
710   printf("%s\n",dtype->AsString(pointer));
711 }
712
713 void DumpTObjectArray(){
714   //
715   //
716   //
717   TObjArray *array = new TObjArray(10);
718   for (Int_t i=0; i<10; i++) array->AddLast(new TNamed(Form("n%d",i), Form("n%d",i)));  
719    AliOCDBtoolkit::DumpObjectRecursive(array);
720   //
721   //
722   TObject *obj = array;
723   TClass * cl = obj->IsA();
724   if (!cl->GetListOfRealData()) cl->BuildRealData();
725   TRealData* rd = 0;
726   rd = (TRealData*)(cl->GetListOfRealData()->FindObject("*fCont"));
727   TDataMember* dm = rd->GetDataMember();
728   TDataType* dtype = dm->GetDataType();
729   //
730   Int_t offset = rd->GetThisOffset();
731   char* pointer = ((char*) obj) + offset;
732   char** apointer = (char**) pointer;
733   //we have pointer to pointer here
734   TObject** ppobj = (TObject**) *apointer;
735   (*ppobj)->Print();
736   //
737   TIter myiter(array);
738   TObject  *arObject; 
739   dtype->Print();
740   while ((arObject = (TObject*)myiter.Next())) {
741     AliOCDBtoolkit::DumpObjectRecursive(arObject);
742   } 
743 }
744
745
746 Bool_t AliOCDBtoolkit::AddoptOCDBEntry( const char *finput, const char *output,  Int_t ustartRun, Int_t uendRun){
747   //
748   // Addopt OCDB entry - keeping all of the CDBentry quantities
749   // // Example usage: 
750   //  AliOCDBtoolkit::AddoptOCDBEntry("/cvmfs/alice.gsi.de/alice/simulation/2008/v4-15-Release/Residual/TPC/Calib/ClusterParam/Run127712_130850_v4_s0.root",0,0,AliCDBRunRange::Infinity())
751   TFile * fin = TFile::Open(finput);
752   if (!fin) return kFALSE;
753   AliCDBEntry * entry = (AliCDBEntry*) fin->Get("AliCDBEntry");
754   if (!entry) return kFALSE;
755   
756   AliCDBStorage* pocdbStorage = 0;
757   if (output!=0) AliCDBManager::Instance()->GetStorage(output);
758   else{
759     TString localStorage = "local://"+gSystem->GetFromPipe("pwd")+"/OCDB";
760     pocdbStorage = AliCDBManager::Instance()->GetStorage(localStorage.Data());
761   }
762   //
763   AliCDBId  idIn = entry->GetId();
764   AliCDBMetaData *metaDataIn = entry->GetMetaData();
765
766   AliCDBMetaData *metaData= new AliCDBMetaData();
767   metaData->SetObjectClassName(metaDataIn->GetObjectClassName());
768   metaData->SetResponsible(TString::Format("%s: copy",metaDataIn->GetResponsible()).Data());
769   metaData->SetBeamPeriod(metaDataIn->GetBeamPeriod());
770   //
771   metaData->SetAliRootVersion(metaDataIn->GetAliRootVersion()); //root version
772   metaData->SetComment((TString::Format("%s: copy",metaDataIn->GetComment()).Data()));
773   AliCDBId* id1=NULL;
774   id1=new AliCDBId(idIn.GetPath(), ustartRun, uendRun);
775   pocdbStorage->Put(entry->GetObject(), (*id1), metaData);
776   return kTRUE;
777 }
778
779
780 void AliOCDBtoolkit::MakeSnapshotFromTxt(const TString fInput, const TString outfile, Bool_t singleKeys){
781   //
782   // Make snasphot form the txt file
783   //
784   AliCDBManager * man = AliCDBManager::Instance();
785   LoadOCDBFromList(fInput.Data());
786   man->DumpToSnapshotFile(outfile.Data(), singleKeys);
787
788 }