Avoiding compilation warnings
[u/mrichter/AliRoot.git] / STEER / AliGeomManager.cxx
CommitLineData
67dd5535 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// Implementation of AliGeomManager, the geometry manager class
17// which interfaces to TGeo and the look-up table mapping unique
18// volume indices to symbolic volume names. For that it collects
19// several static methods.
20//-------------------------------------------------------------------------
21
22#include <TClass.h>
23#include <TFile.h>
24#include <TGeoManager.h>
25#include <TObjString.h>
26#include <TGeoPhysicalNode.h>
27#include <TClonesArray.h>
28#include <TGeoMatrix.h>
29#include <TGeoPhysicalNode.h>
99de26a3 30#include <TSystem.h>
5590c6c3 31#include <TStopwatch.h>
32#include <TGeoOverlap.h>
33#include <TPluginManager.h>
34#include <TROOT.h>
67dd5535 35
36#include "AliGeomManager.h"
37#include "AliLog.h"
38#include "AliAlignObj.h"
90dbf5fb 39#include "AliAlignObjParams.h"
67dd5535 40#include "AliCDBManager.h"
41#include "AliCDBStorage.h"
42#include "AliCDBEntry.h"
43
44ClassImp(AliGeomManager)
45
46Int_t AliGeomManager::fgLayerSize[kLastLayer - kFirstLayer] = {
47 80, 160, // ITS SPD first and second layer
48 84, 176, // ITS SDD first and second layer
49 748, 950, // ITS SSD first and second layer
50 36, 36, // TPC inner and outer chambers
51 90, 90, 90, 90, 90, 90, // 6 TRD chambers' layers
52 1638, // TOF
df117114 53 5, 5, // PHOS,CPV
67dd5535 54 7, // HMPID ??
3dfc15c0 55 1, // MUON ??
56 12 // EMCAL
67dd5535 57};
58
59const char* AliGeomManager::fgLayerName[kLastLayer - kFirstLayer] = {
60 "ITS inner pixels layer", "ITS outer pixels layer",
61 "ITS inner drifts layer", "ITS outer drifts layer",
62 "ITS inner strips layer", "ITS outer strips layer",
63 "TPC inner chambers layer", "TPC outer chambers layer",
64 "TRD chambers layer 1", "TRD chambers layer 2", "TRD chambers layer 3",
65 "TRD chambers layer 4", "TRD chambers layer 5", "TRD chambers layer 6",
66 "TOF layer",
df117114 67 "PHOS EMC layer","PHOS CPV layer",
3dfc15c0 68 "HMPID layer",
69 "MUON ?",
70 "EMCAL layer"
67dd5535 71};
72
73TString* AliGeomManager::fgSymName[kLastLayer - kFirstLayer] = {
74 0x0,0x0,
75 0x0,0x0,
76 0x0,0x0,
77 0x0,0x0,
78 0x0,0x0,0x0,
79 0x0,0x0,0x0,
80 0x0,
81 0x0,0x0,
82 0x0,
3dfc15c0 83 0x0,
67dd5535 84 0x0
85};
86
87TGeoPNEntry** AliGeomManager::fgPNEntry[kLastLayer - kFirstLayer] = {
88 0x0,0x0,
89 0x0,0x0,
90 0x0,0x0,
91 0x0,0x0,
92 0x0,0x0,0x0,
93 0x0,0x0,0x0,
94 0x0,
95 0x0,0x0,
96 0x0,
3dfc15c0 97 0x0,
67dd5535 98 0x0
99};
100
36b010bf 101TGeoHMatrix** AliGeomManager::fgOrigMatrix[kLastLayer - kFirstLayer] = {
67dd5535 102 0x0,0x0,
103 0x0,0x0,
104 0x0,0x0,
105 0x0,0x0,
106 0x0,0x0,0x0,
107 0x0,0x0,0x0,
108 0x0,
109 0x0,0x0,
110 0x0,
3dfc15c0 111 0x0,
67dd5535 112 0x0
113};
114
36b010bf 115AliAlignObj** AliGeomManager::fgAlignObjs[kLastLayer - kFirstLayer] = {
116 0x0,0x0,
117 0x0,0x0,
118 0x0,0x0,
119 0x0,0x0,
120 0x0,0x0,0x0,
121 0x0,0x0,0x0,
122 0x0,
123 0x0,0x0,
124 0x0,
3dfc15c0 125 0x0,
36b010bf 126 0x0
127};
67dd5535 128
129TGeoManager* AliGeomManager::fgGeometry = 0x0;
130
131//_____________________________________________________________________________
36b010bf 132void AliGeomManager::LoadGeometry(const char *geomFileName)
67dd5535 133{
9d47e237 134 // initialization
135 // Load geometry either from a file
136 // or from the corresponding CDB entry
67dd5535 137
36b010bf 138 fgGeometry = NULL;
b8cf7791 139 if (geomFileName && (!gSystem->AccessPathName(geomFileName))) {
36b010bf 140 fgGeometry = TGeoManager::Import(geomFileName);
b8cf7791 141 AliInfoClass(Form("From now on using geometry from custom geometry file %s",geomFileName));
36b010bf 142 }
143
144 if (!fgGeometry) {
36b010bf 145 AliCDBPath path("GRP","Geometry","Data");
146
147 AliCDBEntry *entry=AliCDBManager::Instance()->Get(path.GetPath());
148 if(!entry) AliFatalClass("Couldn't load geometry data from CDB!");
149
150 entry->SetOwner(0);
151 fgGeometry = (TGeoManager*) entry->GetObject();
152 if (!fgGeometry) AliFatalClass("Couldn't find TGeoManager in the specified CDB entry!");
b8cf7791 153
154 AliInfoClass(Form("From now on using geometry from CDB base folder %s",
155 AliCDBManager::Instance()->GetURI("Geometry/Align/Data")));
36b010bf 156 }
67dd5535 157
67dd5535 158 InitSymNamesLUT();
159 InitPNEntriesLUT();
36b010bf 160 InitOrigMatricesLUT();
67dd5535 161}
162
163//_____________________________________________________________________________
9d47e237 164void AliGeomManager::SetGeometry(TGeoManager *geom)
165{
166 // Load already active geometry
167 if (!geom) AliFatalClass("Pointer to the active geometry is 0x0!");
168
169 fgGeometry = geom;
170
171 InitSymNamesLUT();
172 InitPNEntriesLUT();
173 InitOrigMatricesLUT();
174}
175
176//_____________________________________________________________________________
67dd5535 177AliGeomManager::AliGeomManager():
36b010bf 178 TObject()
67dd5535 179{
180 // default constructor
181}
182
183//_____________________________________________________________________________
184AliGeomManager::~AliGeomManager()
185{
186 // dummy destructor
67dd5535 187}
188
189//_____________________________________________________________________________
190Int_t AliGeomManager::LayerSize(Int_t layerId)
191{
192 // Get the layer size for layer corresponding to layerId.
193 // Implemented only for ITS,TPC,TRD,TOF and HMPID
194 //
195 if (layerId < kFirstLayer || layerId >= kLastLayer) {
196 AliErrorClass(Form("Invalid layer index %d ! Layer range is (%d -> %d) !",layerId,kFirstLayer,kLastLayer));
197 return 0;
198 }
199 else {
200 return fgLayerSize[layerId - kFirstLayer];
201 }
202}
203
204//_____________________________________________________________________________
205const char* AliGeomManager::LayerName(Int_t layerId)
206{
207 // Get the layer name corresponding to layerId.
208 // Implemented only for ITS,TPC,TRD,TOF and HMPID
209 //
210 if (layerId < kFirstLayer || layerId >= kLastLayer) {
211 AliErrorClass(Form("Invalid layer index %d ! Layer range is (%d -> %d) !",layerId,kFirstLayer,kLastLayer));
212 return "Invalid Layer!";
213 }
214 else {
215 return fgLayerName[layerId - kFirstLayer];
216 }
217}
218
219//_____________________________________________________________________________
220UShort_t AliGeomManager::LayerToVolUID(ELayerID layerId, Int_t modId)
221{
222 // From detector (layer) name and module number (according to detector
223 // internal numbering) build the unique numerical identity of that volume
224 // inside ALICE
225 // fVolUID is 16 bits, first 5 reserved for layerID (32 possible values),
226 // remaining 11 for module ID inside det (2048 possible values).
227 // NO check for validity of given modId inside the layer for speed's sake.
228 //
229 return ((UShort_t(layerId) << 11) | UShort_t(modId));
230}
231
232//_____________________________________________________________________________
233UShort_t AliGeomManager::LayerToVolUID(Int_t layerId, Int_t modId)
234{
235 // From detector (layer) name and module number (according to detector
236 // internal numbering) build the unique numerical identity of that volume
237 // inside ALICE
238 // fVolUID is 16 bits, first 5 reserved for layerID (32 possible values),
239 // remaining 11 for module ID inside det (2048 possible values).
240 // NO check for validity of given modId inside the layer for speed's sake.
241 //
242 return ((UShort_t(layerId) << 11) | UShort_t(modId));
243}
244
245//_____________________________________________________________________________
246UShort_t AliGeomManager::LayerToVolUIDSafe(ELayerID layerId, Int_t modId)
247{
248 // From detector (layer) name and module number (according to detector
249 // internal numbering) build the unique numerical identity of that volume
250 // inside ALICE
251 // fVolUID is 16 bits, first 5 reserved for layerID (32 possible values),
252 // remaining 11 for module ID inside det (2048 possible values).
253 // Check validity of given modId inside the layer.
254 //
255 if(modId < 0 || modId >= LayerSize(layerId)){
256 AliErrorClass(Form("Invalid volume id %d ! Range of valid ids for layer \"%s\" is [0, %d] !",modId,LayerName(layerId),LayerSize(layerId)-1));
257 return 0;
258 }
259 return ((UShort_t(layerId) << 11) | UShort_t(modId));
260}
261
262//_____________________________________________________________________________
263UShort_t AliGeomManager::LayerToVolUIDSafe(Int_t layerId, Int_t modId)
264{
265 // From detector (layer) name and module number (according to detector
266 // internal numbering) build the unique numerical identity of that volume
267 // inside ALICE
268 // fVolUID is 16 bits, first 5 reserved for layerID (32 possible values),
269 // remaining 11 for module ID inside det (2048 possible values).
270 // Check validity of given modId inside the layer.
271 //
272 if(modId < 0 || modId >= LayerSize(layerId)){
273 AliErrorClass(Form("Invalid volume id %d ! Range of valid ids for layer \"%s\" is [0, %d] !",modId,LayerName(layerId),LayerSize(layerId)-1));
274 return 0;
275 }
276 return ((UShort_t(layerId) << 11) | UShort_t(modId));
277}
278
279//_____________________________________________________________________________
280AliGeomManager::ELayerID AliGeomManager::VolUIDToLayer(UShort_t voluid, Int_t &modId)
281{
282 // From voluid, unique numerical identity of that volume inside ALICE,
283 // (voluid is 16 bits, first 5 reserved for layerID (32 possible values),
284 // remaining 11 for module ID inside det (2048 possible values)), return
285 // the identity of the layer to which that volume belongs and sets the
286 // argument modId to the identity of that volume internally to the layer.
287 // NO check for validity of given voluid for speed's sake.
288 //
289 modId = voluid & 0x7ff;
290
291 return VolUIDToLayer(voluid);
292}
293
294//_____________________________________________________________________________
295AliGeomManager::ELayerID AliGeomManager::VolUIDToLayer(UShort_t voluid)
296{
297 // From voluid, unique numerical identity of that volume inside ALICE,
298 // (voluid is 16 bits, first 5 reserved for layerID (32 possible values),
299 // remaining 11 for module ID inside det (2048 possible values)), return
300 // the identity of the layer to which that volume belongs
301 // NO check for validity of given voluid for speed's sake.
302 //
303 return ELayerID(voluid >> 11);
304}
305
306//_____________________________________________________________________________
307AliGeomManager::ELayerID AliGeomManager::VolUIDToLayerSafe(UShort_t voluid, Int_t &modId)
308{
309 // From voluid, unique numerical identity of that volume inside ALICE,
310 // (voluid is 16 bits, first 5 reserved for layerID (32 possible values),
311 // remaining 11 for module ID inside det (2048 possible values)), returns
312 // the identity of the layer to which that volume belongs and sets the
313 // argument modId to the identity of that volume internally to the layer.
314 // Checks the validity of the given voluid
315 //
316 ELayerID layId = VolUIDToLayerSafe(voluid);
317 if(layId){
318 Int_t mId = Int_t(voluid & 0x7ff);
319 if( mId>=0 && mId<LayerSize(layId)){
320 modId = mId;
321 return layId;
322 }
323 }
324
325 AliErrorClass(Form("Invalid unique volume id: %d !",voluid));
326 modId = -1;
327 return kInvalidLayer;
328
329}
330
331//_____________________________________________________________________________
332AliGeomManager::ELayerID AliGeomManager::VolUIDToLayerSafe(UShort_t voluid)
333{
334 // From voluid, unique numerical identity of that volume inside ALICE,
335 // (voluid is 16 bits, first 5 reserved for layerID (32 possible values),
336 // remaining 11 for module ID inside det (2048 possible values)), returns
337 // the identity of the layer to which that volume belongs
338 // Checks the validity of the given voluid
339 //
340 if( (voluid >> 11) < kLastLayer) return ELayerID(voluid >> 11);
341
342 AliErrorClass(Form("Invalid layer id: %d !",(voluid >> 11)));
343 return kInvalidLayer;
344
345}
346
347//_____________________________________________________________________________
348Bool_t AliGeomManager::GetFromGeometry(const char *symname, AliAlignObj &alobj)
349{
350 // Get the alignment object which corresponds to the symbolic volume name
351 // symname (in case equal to the TGeo volume path)
352 // The method is extremely slow due to the searching by string,
353 // therefore it should be used with great care!!
354 // This method returns FALSE if the symname of the object was not
355 // valid neither to get a TGeoPEntry nor as a volume path, or if the path
356 // associated to the TGeoPNEntry was not valid.
357 //
358
359 // Reset the alignment object
360 alobj.SetPars(0,0,0,0,0,0);
361 alobj.SetSymName(symname);
362
36b010bf 363 if (!fgGeometry || !fgGeometry->IsClosed()) {
67dd5535 364 AliErrorClass("Can't get the alignment object! gGeoManager doesn't exist or it is still opened!");
365 return kFALSE;
366 }
367
36b010bf 368 if (!fgGeometry->GetListOfPhysicalNodes()) {
67dd5535 369 AliErrorClass("Can't get the alignment object! gGeoManager doesn't contain any aligned nodes!");
370 return kFALSE;
371 }
372
67dd5535 373 const char *path;
36b010bf 374 TGeoPNEntry* pne = fgGeometry->GetAlignableEntry(symname);
67dd5535 375 if(pne){
376 path = pne->GetTitle();
377 }else{
378 AliWarningClass(Form("The symbolic volume name %s does not correspond to a physical entry. Using it as a volume path!",symname));
379 path = symname;
380 }
36b010bf 381 TObjArray* nodesArr = fgGeometry->GetListOfPhysicalNodes();
67dd5535 382 TGeoPhysicalNode* node = NULL;
383 for (Int_t iNode = 0; iNode < nodesArr->GetEntriesFast(); iNode++) {
384 TGeoPhysicalNode* tempNode = (TGeoPhysicalNode*) nodesArr->UncheckedAt(iNode);
385 const char *nodePath = tempNode->GetName();
386 if (strcmp(path,nodePath) == 0) {
387 node = tempNode;
388 break;
389 }
390 }
391
392 if (!node) {
36b010bf 393 if (!fgGeometry->cd(path)) {
67dd5535 394 AliErrorClass(Form("%s not valid neither as symbolic volume name nor as volume path!",path));
395 return kFALSE;
396 }
397 else {
398 AliWarningClass(Form("Volume (%s) has not been misaligned!",path));
399 return kTRUE;
400 }
401 }
402
403 TGeoHMatrix align,gprime,g,ginv,l;
404 gprime = *node->GetMatrix();
405 l = *node->GetOriginalMatrix();
406 g = *node->GetMatrix(node->GetLevel()-1);
407 g *= l;
408 ginv = g.Inverse();
409 align = gprime * ginv;
410
411 return alobj.SetMatrix(align);
412}
413
414
415//_____________________________________________________________________________
416void AliGeomManager::InitAlignObjFromGeometry()
417{
418 // Loop over all alignable volumes and extract
419 // the corresponding alignment objects from
420 // the TGeo geometry
421
422 if(fgAlignObjs[0]) return;
423
67dd5535 424 for (Int_t iLayer = kFirstLayer; iLayer < AliGeomManager::kLastLayer; iLayer++) {
425 fgAlignObjs[iLayer-kFirstLayer] = new AliAlignObj*[LayerSize(iLayer)];
426 for (Int_t iModule = 0; iModule < LayerSize(iLayer); iModule++) {
427 UShort_t volid = LayerToVolUID(iLayer,iModule);
90dbf5fb 428 fgAlignObjs[iLayer-kFirstLayer][iModule] = new AliAlignObjParams("",volid,0,0,0,0,0,0,kTRUE);
67dd5535 429 const char *symname = SymName(volid);
430 if (!GetFromGeometry(symname, *fgAlignObjs[iLayer-kFirstLayer][iModule]))
431 AliErrorClass(Form("Failed to extract the alignment object for the volume (ID=%d and path=%s) !",volid,symname));
432 }
433 }
434
435}
436
437//_____________________________________________________________________________
438AliAlignObj* AliGeomManager::GetAlignObj(UShort_t voluid) {
439 // Returns the alignment object for given volume ID
440 //
441 Int_t modId;
442 ELayerID layerId = VolUIDToLayer(voluid,modId);
443 return GetAlignObj(layerId,modId);
444}
445
446//_____________________________________________________________________________
447AliAlignObj* AliGeomManager::GetAlignObj(ELayerID layerId, Int_t modId)
448{
449 // Returns pointer to alignment object given its layer and module ID
450 //
451 if(modId<0 || modId>=fgLayerSize[layerId-kFirstLayer]){
452 AliWarningClass(Form("Module number %d not in the valid range (0->%d) !",modId,fgLayerSize[layerId-kFirstLayer]-1));
453 return NULL;
454 }
455 InitAlignObjFromGeometry();
456
457 return fgAlignObjs[layerId-kFirstLayer][modId];
458}
459
460//_____________________________________________________________________________
461const char* AliGeomManager::SymName(UShort_t voluid) {
462 // Returns the symbolic volume name for given volume ID
463 //
464 Int_t modId;
465 ELayerID layerId = VolUIDToLayer(voluid,modId);
466 return SymName(layerId,modId);
467}
468
469//_____________________________________________________________________________
470const char* AliGeomManager::SymName(ELayerID layerId, Int_t modId)
471{
472 // Returns the symbolic volume name given for a given layer
473 // and module ID
474 //
475 if(modId<0 || modId>=fgLayerSize[layerId-kFirstLayer]){
476 AliWarningClass(Form("Module number %d not in the valid range (0->%d) !",modId,fgLayerSize[layerId-kFirstLayer]-1));
477 return NULL;
478 }
25fad4e5 479 InitSymNamesLUT();
67dd5535 480
481 return fgSymName[layerId-kFirstLayer][modId].Data();
482}
483
484//_____________________________________________________________________________
485void AliGeomManager::InitSymNamesLUT()
486{
487 // Initialize the look-up table which associates the unique
488 // numerical identity of each alignable volume to the
489 // corresponding symbolic volume name
490 // The LUTs are static; they are created at the creation of the
491 // AliGeomManager instance and recreated if the geometry has changed
492 //
493
25fad4e5 494 if(fgSymName[0]) return;
495
67dd5535 496 for (Int_t iLayer = 0; iLayer < (kLastLayer - kFirstLayer); iLayer++){
497 if(!fgSymName[iLayer]) fgSymName[iLayer]=new TString[fgLayerSize[iLayer]];
498 }
499
500 TString symname;
501 Int_t modnum; // in the following, set it to 0 at the start of each layer
502
503 /********************* ITS layers ***********************/
504 TString strSPD = "ITS/SPD";
505 TString strSDD = "ITS/SDD";
506 TString strSSD = "ITS/SSD";
507 TString strStave = "/Stave";
8f8273a4 508 TString strHalfStave = "/HalfStave";
67dd5535 509 TString strLadder = "/Ladder";
510 TString strSector = "/Sector";
511 TString strSensor = "/Sensor";
512 TString strEntryName1;
513 TString strEntryName2;
8f8273a4 514 TString strEntryName3;
67dd5535 515
516 /********************* SPD layer1 ***********************/
517 {
518 modnum = 0;
8f8273a4 519
520 for(Int_t cSect = 0; cSect<10; cSect++){
67dd5535 521 strEntryName1 = strSPD;
522 strEntryName1 += 0;
523 strEntryName1 += strSector;
8f8273a4 524 strEntryName1 += cSect;
525
526 for(Int_t cStave =0; cStave<2; cStave++){
67dd5535 527 strEntryName2 = strEntryName1;
528 strEntryName2 += strStave;
8f8273a4 529 strEntryName2 += cStave;
530
531 for (Int_t cHS=0; cHS<2; cHS++) {
532 strEntryName3 = strEntryName2;
533 strEntryName3 += strHalfStave;
534 strEntryName3 += cHS;
535
536 for(Int_t cLad =0; cLad<2; cLad++){
537 symname = strEntryName3;
538 symname += strLadder;
539 symname += cLad+cHS*2;
540 fgSymName[kSPD1-kFirstLayer][modnum] = symname.Data();
541 modnum++;
542 }
67dd5535 543 }
544 }
545 }
546 }
547
548 /********************* SPD layer2 ***********************/
549 {
550 modnum = 0;
551
8f8273a4 552 for(Int_t cSect = 0; cSect<10; cSect++){
67dd5535 553 strEntryName1 = strSPD;
554 strEntryName1 += 1;
555 strEntryName1 += strSector;
8f8273a4 556 strEntryName1 += cSect;
557
558 for(Int_t cStave =0; cStave<4; cStave++){
67dd5535 559 strEntryName2 = strEntryName1;
560 strEntryName2 += strStave;
8f8273a4 561 strEntryName2 += cStave;
562
563 for (Int_t cHS=0; cHS<2; cHS++) {
564 strEntryName3 = strEntryName2;
565 strEntryName3 += strHalfStave;
566 strEntryName3 += cHS;
567
568 for(Int_t cLad =0; cLad<2; cLad++){
569 symname = strEntryName3;
570 symname += strLadder;
571 symname += cLad+cHS*2;
572 fgSymName[kSPD2-kFirstLayer][modnum] = symname.Data();
573 modnum++;
574 }
67dd5535 575 }
576 }
577 }
578 }
579
8f8273a4 580// /********************* SPD layer1 ***********************/
581// {
582// modnum = 0;
583
584// for(Int_t c1 = 1; c1<=10; c1++){
585// strEntryName1 = strSPD;
586// strEntryName1 += 0;
587// strEntryName1 += strSector;
588// strEntryName1 += (c1-1);
589// for(Int_t c2 =1; c2<=2; c2++){
590// strEntryName2 = strEntryName1;
591// strEntryName2 += strStave;
592// strEntryName2 += (c2-1);
593// for(Int_t c3 =1; c3<=4; c3++){
594// symname = strEntryName2;
595// symname += strLadder;
596// symname += (c3-1);
597// fgSymName[kSPD1-kFirstLayer][modnum] = symname.Data();
598// modnum++;
599// }
600// }
601// }
602// }
603
604// /********************* SPD layer2 ***********************/
605// {
606// modnum = 0;
607
608// for(Int_t c1 = 1; c1<=10; c1++){
609// strEntryName1 = strSPD;
610// strEntryName1 += 1;
611// strEntryName1 += strSector;
612// strEntryName1 += (c1-1);
613// for(Int_t c2 =1; c2<=4; c2++){
614// strEntryName2 = strEntryName1;
615// strEntryName2 += strStave;
616// strEntryName2 += (c2-1);
617// for(Int_t c3 =1; c3<=4; c3++){
618// symname = strEntryName2;
619// symname += strLadder;
620// symname += (c3-1);
621// fgSymName[kSPD2-kFirstLayer][modnum] = symname.Data();
622// modnum++;
623// }
624// }
625// }
626// }
627
628
629
630
631
632
633
634
635
67dd5535 636 /********************* SDD layer1 ***********************/
637 {
638 modnum=0;
639
640 for(Int_t c1 = 1; c1<=14; c1++){
641 strEntryName1 = strSDD;
642 strEntryName1 += 2;
643 strEntryName1 +=strLadder;
644 strEntryName1 += (c1-1);
645 for(Int_t c2 =1; c2<=6; c2++){
646 symname = strEntryName1;
647 symname += strSensor;
648 symname += (c2-1);
649 fgSymName[kSDD1-kFirstLayer][modnum] = symname.Data();
650 modnum++;
651 }
652 }
653 }
654
655 /********************* SDD layer2 ***********************/
656 {
657 modnum=0;
658
659 for(Int_t c1 = 1; c1<=22; c1++){
660 strEntryName1 = strSDD;
661 strEntryName1 += 3;
662 strEntryName1 +=strLadder;
663 strEntryName1 += (c1-1);
664 for(Int_t c2 = 1; c2<=8; c2++){
665 symname = strEntryName1;
666 symname += strSensor;
667 symname += (c2-1);
668 fgSymName[kSDD2-kFirstLayer][modnum] = symname.Data();
669 modnum++;
670 }
671 }
672 }
673
674 /********************* SSD layer1 ***********************/
675 {
676 modnum=0;
677
678 for(Int_t c1 = 1; c1<=34; c1++){
679 strEntryName1 = strSSD;
680 strEntryName1 += 4;
681 strEntryName1 +=strLadder;
682 strEntryName1 += (c1-1);
683 for(Int_t c2 = 1; c2<=22; c2++){
684 symname = strEntryName1;
685 symname += strSensor;
686 symname += (c2-1);
687 fgSymName[kSSD1-kFirstLayer][modnum] = symname.Data();
688 modnum++;
689 }
690 }
691 }
692
693 /********************* SSD layer2 ***********************/
694 {
695 modnum=0;
696
697 for(Int_t c1 = 1; c1<=38; c1++){
698 strEntryName1 = strSSD;
699 strEntryName1 += 5;
700 strEntryName1 +=strLadder;
701 strEntryName1 += (c1-1);
702 for(Int_t c2 = 1; c2<=25; c2++){
703 symname = strEntryName1;
704 symname += strSensor;
705 symname += (c2-1);
706 fgSymName[kSSD2-kFirstLayer][modnum] = symname.Data();
707 modnum++;
708 }
709 }
710 }
711
712
713 /*************** TPC inner and outer layers ****************/
714 TString sAsector="TPC/EndcapA/Sector";
715 TString sCsector="TPC/EndcapC/Sector";
716 TString sInner="/InnerChamber";
717 TString sOuter="/OuterChamber";
718
719 /*************** TPC inner chambers' layer ****************/
720 {
721 modnum = 0;
722
723 for(Int_t cnt=1; cnt<=18; cnt++){
724 symname = sAsector;
725 symname += cnt;
726 symname += sInner;
727 fgSymName[kTPC1-kFirstLayer][modnum] = symname.Data();
728 modnum++;
729 }
730 for(Int_t cnt=1; cnt<=18; cnt++){
731 symname = sCsector;
732 symname += cnt;
733 symname += sInner;
734 fgSymName[kTPC1-kFirstLayer][modnum] = symname.Data();
735 modnum++;
736 }
737 }
738
739 /*************** TPC outer chambers' layer ****************/
740 {
741 modnum = 0;
742
743 for(Int_t cnt=1; cnt<=18; cnt++){
744 symname = sAsector;
745 symname += cnt;
746 symname += sOuter;
747 fgSymName[kTPC2-kFirstLayer][modnum] = symname.Data();
748 modnum++;
749 }
750 for(Int_t cnt=1; cnt<=18; cnt++){
751 symname = sCsector;
752 symname += cnt;
753 symname += sOuter;
754 fgSymName[kTPC2-kFirstLayer][modnum] = symname.Data();
755 modnum++;
756 }
757 }
758
759 /********************* TOF layer ***********************/
760 {
761 modnum=0;
762
763 Int_t nstrA=15;
764 Int_t nstrB=19;
765 Int_t nstrC=19;
766 Int_t nSectors=18;
767 Int_t nStrips=nstrA+2*nstrB+2*nstrC;
768
769 TString snSM = "TOF/sm";
770 TString snSTRIP = "/strip";
771
772 for (Int_t isect = 0; isect < nSectors; isect++) {
773 for (Int_t istr = 1; istr <= nStrips; istr++) {
774 symname = snSM;
775 symname += Form("%02d",isect);
776 symname += snSTRIP;
777 symname += Form("%02d",istr);
778 fgSymName[kTOF-kFirstLayer][modnum] = symname.Data();
779 modnum++;
780 }
781 }
782 }
783
784 /********************* HMPID layer ***********************/
785 {
786 TString str = "/HMPID/Chamber";
787
788 for (modnum=0; modnum < 7; modnum++) {
789 symname = str;
790 symname += modnum;
791 fgSymName[kHMPID-kFirstLayer][modnum] = symname.Data();
792 }
793 }
794
795 /********************* TRD layers 1-6 *******************/
796 //!! 6 layers with index increasing in outwards direction
797 {
798 Int_t arTRDlayId[6] = {kTRD1, kTRD2, kTRD3, kTRD4, kTRD5, kTRD6};
799
800 TString snStr = "TRD/sm";
801 TString snApp1 = "/st";
802 TString snApp2 = "/pl";
803
804 for(Int_t layer=0; layer<6; layer++){
805 modnum=0;
806 for (Int_t isect = 0; isect < 18; isect++) {
807 for (Int_t icham = 0; icham < 5; icham++) {
808 symname = snStr;
809 symname += Form("%02d",isect);
810 symname += snApp1;
811 symname += icham;
812 symname += snApp2;
813 symname += layer;
814 fgSymName[arTRDlayId[layer]-kFirstLayer][modnum] = symname.Data();
815 modnum++;
816 }
817 }
818 }
819 }
df117114 820
821 /********************* PHOS EMC layer ***********************/
822 {
823 TString str = "PHOS/Module";
824 modnum=0;
825
826 for (Int_t iModule=1; iModule <= 5; iModule++) {
827 symname = str;
828 symname += iModule;
829 modnum = iModule-1;
830 fgSymName[kPHOS1-kFirstLayer][modnum] = symname.Data();
831 }
832 }
833
f47b9233 834 /********************* PHOS CPV layer ***********************/
835 {
836 TString str = "PHOS/Module";
837 modnum=0;
838
839 for (Int_t iModule=1; iModule <= 5; iModule++) {
840 symname = str;
841 symname += iModule;
842 symname += "/CPV";
843 modnum = iModule-1;
844 fgSymName[kPHOS2-kFirstLayer][modnum] = symname.Data();
845 }
846 }
847
3dfc15c0 848 /********************* EMCAL layer ***********************/
849 {
850 TString str = "EMCAL/FullSupermodule";
851 modnum=0;
852
853 for (Int_t iModule=1; iModule <= 12; iModule++) {
854 symname = str;
855 symname += iModule;
856 if(iModule >10) {
857 symname = "EMCAL/HalfSupermodule";
858 symname += iModule-10;
859 }
860 modnum = iModule-1;
861 fgSymName[kEMCAL-kFirstLayer][modnum] = symname.Data();
862 }
863 }
f47b9233 864
67dd5535 865}
866
867//_____________________________________________________________________________
868void AliGeomManager::InitPNEntriesLUT()
869{
870 // Initialize the look-up table which associates the unique
871 // numerical identity of each alignable volume to the
872 // corresponding TGeoPNEntry.
873 // The LUTs are static; they are created at the creation of the
874 // AliGeomManager instance and recreated if the geometry has changed
875 //
36b010bf 876 if (fgPNEntry[0]) return;
67dd5535 877
36b010bf 878 if(!fgGeometry) {
879 AliErrorClass("Impossible to initialize PNEntries LUT without an active geometry");
880 return;
881 }
25fad4e5 882
67dd5535 883 for (Int_t iLayer = 0; iLayer < (kLastLayer - kFirstLayer); iLayer++){
36b010bf 884 fgPNEntry[iLayer] = new TGeoPNEntry*[fgLayerSize[iLayer]];
885 for(Int_t modnum=0; modnum<fgLayerSize[iLayer]; modnum++){
886 fgPNEntry[iLayer][modnum] = fgGeometry->GetAlignableEntry(fgSymName[iLayer][modnum]);
887 }
888 }
889}
890
891//_____________________________________________________________________________
892void AliGeomManager::InitOrigMatricesLUT()
893{
894 // Initialize the storage for the look-up table with the original global
895 // matrices for each alignable volume.
896 // The LUTs are static; the matrices are created on demand and recreated
897 // if the geometry has changed.
898 if (fgOrigMatrix[0]) return;
899
900 if (!fgGeometry || !fgGeometry->IsClosed()) {
901 AliErrorClass("Impossible to initialize orignal matrices LUT without an active geometry");
902 return;
67dd5535 903 }
904
36b010bf 905 for (Int_t iLayer = 0; iLayer < (kLastLayer - kFirstLayer); iLayer++){
906 fgOrigMatrix[iLayer] = new TGeoHMatrix*[fgLayerSize[iLayer]];
25fad4e5 907 for(Int_t modnum=0; modnum<fgLayerSize[iLayer]; modnum++){
36b010bf 908 if (!fgPNEntry[iLayer][modnum]) continue;
909 TGeoHMatrix *m = GetOrigGlobalMatrix(fgPNEntry[iLayer][modnum]);
910 if (!m) continue;
911 fgOrigMatrix[iLayer][modnum] = new TGeoHMatrix(*m);
67dd5535 912 }
913 }
36b010bf 914
67dd5535 915}
916
917//______________________________________________________________________
918TGeoHMatrix* AliGeomManager::GetMatrix(TGeoPNEntry* pne)
919{
920 // Get the transformation matrix for a given PNEntry
921 // by quering the TGeoManager
922
36b010bf 923 if (!fgGeometry || !fgGeometry->IsClosed()) {
25fad4e5 924 AliErrorClass("Can't get the global matrix! gGeoManager doesn't exist or it is still opened!");
925 return NULL;
926 }
927
67dd5535 928 TGeoPhysicalNode *pnode = pne->GetPhysicalNode();
929 if (pnode) return pnode->GetMatrix();
930
931 const char* path = pne->GetTitle();
36b010bf 932 if (!fgGeometry->cd(path)) {
67dd5535 933 AliErrorClass(Form("Volume path %s not valid!",path));
934 return NULL;
935 }
36b010bf 936 return fgGeometry->GetCurrentMatrix();
67dd5535 937}
938
939//______________________________________________________________________
940TGeoHMatrix* AliGeomManager::GetMatrix(Int_t index)
941{
942 // Get the global transformation matrix for a given alignable volume
943 // identified by its unique ID 'index' by quering the TGeoManager
944
67dd5535 945 TGeoPNEntry *pne = GetPNEntry(index);
946 if (!pne) return NULL;
947
948 return GetMatrix(pne);
949}
950
951//______________________________________________________________________
952TGeoHMatrix* AliGeomManager::GetMatrix(const char* symname)
953{
954 // Get the global transformation matrix for a given alignable volume
955 // identified by its symbolic name 'symname' by quering the TGeoManager
956
36b010bf 957 if (!fgGeometry || !fgGeometry->IsClosed()) {
958 AliErrorClass("No active geometry or geometry not yet closed!");
959 return NULL;
960 }
961
962 TGeoPNEntry* pne = fgGeometry->GetAlignableEntry(symname);
67dd5535 963 if (!pne) return NULL;
964
965 return GetMatrix(pne);
966}
967
968//______________________________________________________________________
969Bool_t AliGeomManager::GetTranslation(Int_t index, Double_t t[3])
970{
971 // Get the translation vector for a given module 'index'
972 // by quering the TGeoManager
973
974 TGeoHMatrix *m = GetMatrix(index);
975 if (!m) return kFALSE;
976
977 Double_t *trans = m->GetTranslation();
978 for (Int_t i = 0; i < 3; i++) t[i] = trans[i];
979
980 return kTRUE;
981}
982
983//______________________________________________________________________
984Bool_t AliGeomManager::GetRotation(Int_t index, Double_t r[9])
985{
986 // Get the rotation matrix for a given module 'index'
987 // by quering the TGeoManager
988
989 TGeoHMatrix *m = GetMatrix(index);
990 if (!m) return kFALSE;
991
992 Double_t *rot = m->GetRotationMatrix();
993 for (Int_t i = 0; i < 9; i++) r[i] = rot[i];
994
995 return kTRUE;
996}
997
5d534fe3 998//_____________________________________________________________________________
999Bool_t AliGeomManager::GetDeltaForBranch(Int_t index, TGeoHMatrix &inclusiveD)
1000{
1001 // The method sets the matrix passed as argument as the global delta
1002 // (for the volume referred by the unique index) including the displacements
1003 // of all parent volumes in the branch.
1004 //
1005 const char* symname = SymName(index);
1006 if(!symname) return kFALSE;
1007
1008 TGeoHMatrix go,invgo;
1009 go = *GetOrigGlobalMatrix(index);
1010 invgo = go.Inverse();
1011 inclusiveD = *GetMatrix(symname);
1012 inclusiveD.Multiply(&invgo);
1013
1014 return kTRUE;
1015}
1016
1017//_____________________________________________________________________________
1018Bool_t AliGeomManager::GetDeltaForBranch(AliAlignObj& aao, TGeoHMatrix &inclusiveD)
1019{
1020 // The method sets the matrix passed as argument as the global delta
1021 // (for the volume referred by the alignment object) including the displacements
1022 // of all parent volumes in the brach.
1023 //
1024 Int_t index = aao.GetVolUID();
1025 if(!index){
1026 AliErrorClass("Either the alignment object or its index are not valid");
1027 return kFALSE;
1028 }
1029 return GetDeltaForBranch(index, inclusiveD);
1030}
1031
36b010bf 1032//______________________________________________________________________
1033Bool_t AliGeomManager::GetOrigGlobalMatrix(const char* symname, TGeoHMatrix &m)
67dd5535 1034{
36b010bf 1035 // Get the global transformation matrix (ideal geometry) for a given alignable volume
1036 // identified by its symbolic name 'symname' by quering the TGeoManager
1037 m.Clear();
67dd5535 1038
36b010bf 1039 if (!fgGeometry || !fgGeometry->IsClosed()) {
1040 AliErrorClass("No active geometry or geometry not yet closed!");
67dd5535 1041 return kFALSE;
1042 }
36b010bf 1043 if (!fgGeometry->GetListOfPhysicalNodes()) {
67dd5535 1044 AliWarningClass("gGeoManager doesn't contain any aligned nodes!");
36b010bf 1045 if (!fgGeometry->cd(symname)) {
67dd5535 1046 AliErrorClass(Form("Volume path %s not valid!",symname));
1047 return kFALSE;
1048 }
1049 else {
36b010bf 1050 m = *fgGeometry->GetCurrentMatrix();
67dd5535 1051 return kTRUE;
1052 }
1053 }
1054
36b010bf 1055 TGeoPNEntry* pne = fgGeometry->GetAlignableEntry(symname);
67dd5535 1056 const char* path = NULL;
67dd5535 1057 if(pne){
1058 path = pne->GetTitle();
1059 }else{
1060 AliWarningClass(Form("The symbolic volume name %s does not correspond to a physical entry. Using it as a volume path!",symname));
1061 path=symname;
1062 }
1063
36b010bf 1064 return GetOrigGlobalMatrixFromPath(path,m);
1065}
1066
1067//_____________________________________________________________________________
1068Bool_t AliGeomManager::GetOrigGlobalMatrixFromPath(const char *path, TGeoHMatrix &m)
1069{
1070 // The method returns global matrix for the ideal detector geometry
1071 // Symname identifies either the corresponding TGeoPNEntry or directly
1072 // the volume path. The output global matrix is stored in 'm'.
1073 // Returns kFALSE in case TGeo has not been initialized or the symname
1074 // is invalid.
1075 //
1076 m.Clear();
1077
1078 if (!fgGeometry || !fgGeometry->IsClosed()) {
1079 AliErrorClass("Can't get the original global matrix! gGeoManager doesn't exist or it is still opened!");
67dd5535 1080 return kFALSE;
1081 }
1082
36b010bf 1083 if (!fgGeometry->CheckPath(path)) {
1084 AliErrorClass(Form("Volume path %s not valid!",path));
1085 return kFALSE;
1086 }
67dd5535 1087
36b010bf 1088 TIter next(fgGeometry->GetListOfPhysicalNodes());
1089 fgGeometry->cd(path);
67dd5535 1090
36b010bf 1091 while(fgGeometry->GetLevel()){
67dd5535 1092
1093 TGeoPhysicalNode *physNode = NULL;
1094 next.Reset();
36b010bf 1095 TGeoNode *node = fgGeometry->GetCurrentNode();
67dd5535 1096 while ((physNode=(TGeoPhysicalNode*)next()))
1097 if (physNode->GetNode() == node) break;
1098
1099 TGeoMatrix *lm = NULL;
1100 if (physNode) {
1101 lm = physNode->GetOriginalMatrix();
1102 if (!lm) lm = node->GetMatrix();
1103 } else
1104 lm = node->GetMatrix();
1105
1106 m.MultiplyLeft(lm);
1107
36b010bf 1108 fgGeometry->CdUp();
67dd5535 1109 }
1110
1111 return kTRUE;
1112}
1113
36b010bf 1114//_____________________________________________________________________________
1115TGeoHMatrix* AliGeomManager::GetOrigGlobalMatrix(TGeoPNEntry* pne)
1116{
1117 // The method returns global matrix for the ideal detector geometry
1118 // using the corresponding TGeoPNEntry as an input.
1119 // The method creates a new matrix, so it has to be used carefully in order
1120 // to avoid memory leaks.
1121 // In case of missing TGeoManager the method return NULL.
1122
1123 if (!fgGeometry || !fgGeometry->IsClosed()) {
1124 AliErrorClass("Can't get the global matrix! gGeoManager doesn't exist or it is still opened!");
1125 return NULL;
1126 }
1127
1128 const char* path = pne->GetTitle();
1129 static TGeoHMatrix m;
1130 if (!GetOrigGlobalMatrixFromPath(path,m))
1131 return NULL;
1132
1133 return &m;
1134}
1135
67dd5535 1136//______________________________________________________________________
36b010bf 1137TGeoHMatrix* AliGeomManager::GetOrigGlobalMatrix(Int_t index)
67dd5535 1138{
1139 // Get the original (ideal geometry) TGeo matrix for
1140 // a given module identified by 'index'.
36b010bf 1141 // In general the method is slow, so we use
1142 // LUT for fast access. The LUT is reset in case of
1143 // new geometry is loaded.
1144 Int_t modId;
1145 ELayerID layerId = VolUIDToLayer(index,modId);
67dd5535 1146
36b010bf 1147 if (fgOrigMatrix[layerId-kFirstLayer][modId])
1148 return fgOrigMatrix[layerId-kFirstLayer][modId];
1149 else {
1150 TGeoPNEntry *pne = GetPNEntry(index);
1151 if (!pne) return NULL;
1152 return GetOrigGlobalMatrix(pne);
1153 }
67dd5535 1154}
1155
1156//______________________________________________________________________
1157Bool_t AliGeomManager::GetOrigTranslation(Int_t index, Double_t t[3])
1158{
1159 // Get the original translation vector (ideal geometry)
1160 // for a given module 'index' by quering the TGeoManager
1161
36b010bf 1162 TGeoHMatrix *m = GetOrigGlobalMatrix(index);
1163 if (!m) return kFALSE;
67dd5535 1164
36b010bf 1165 Double_t *trans = m->GetTranslation();
67dd5535 1166 for (Int_t i = 0; i < 3; i++) t[i] = trans[i];
1167
1168 return kTRUE;
1169}
1170
1171//______________________________________________________________________
1172Bool_t AliGeomManager::GetOrigRotation(Int_t index, Double_t r[9])
1173{
1174 // Get the original rotation matrix (ideal geometry)
1175 // for a given module 'index' by quering the TGeoManager
1176
36b010bf 1177 TGeoHMatrix *m = GetOrigGlobalMatrix(index);
1178 if (!m) return kFALSE;
67dd5535 1179
36b010bf 1180 Double_t *rot = m->GetRotationMatrix();
67dd5535 1181 for (Int_t i = 0; i < 9; i++) r[i] = rot[i];
1182
1183 return kTRUE;
1184}
1185
1186//______________________________________________________________________
1187const TGeoHMatrix* AliGeomManager::GetTracking2LocalMatrix(Int_t index)
1188{
25fad4e5 1189 // Get the matrix which transforms from the tracking to the local RS
67dd5535 1190 // The method queries directly the TGeoPNEntry
1191
67dd5535 1192 TGeoPNEntry *pne = GetPNEntry(index);
1193 if (!pne) return NULL;
1194
1195 const TGeoHMatrix *m = pne->GetMatrix();
1196 if (!m)
1197 AliErrorClass(Form("TGeoPNEntry (%s) contains no matrix !",pne->GetName()));
1198
1199 return m;
1200}
1201
1202//______________________________________________________________________
1203Bool_t AliGeomManager::GetTrackingMatrix(Int_t index, TGeoHMatrix &m)
1204{
1205 // Get the matrix which transforms from the tracking r.s. to
1206 // the global one.
1207 // Returns kFALSE in case of error.
1208
1209 m.Clear();
1210
1211 TGeoHMatrix *m1 = GetMatrix(index);
1212 if (!m1) return kFALSE;
1213
1214 const TGeoHMatrix *m2 = GetTracking2LocalMatrix(index);
1215 if (!m2) return kFALSE;
1216
1217 m = *m1;
1218 m.Multiply(m2);
1219
1220 return kTRUE;
1221}
1222
1223//_____________________________________________________________________________
1224TGeoPNEntry* AliGeomManager::GetPNEntry(Int_t voluid) {
1225 // Returns the TGeoPNEntry for the given global volume ID "voluid"
1226 //
1227 Int_t modId;
1228 ELayerID layerId = VolUIDToLayer(voluid,modId);
1229 return GetPNEntry(layerId,modId);
1230}
1231
1232//_____________________________________________________________________________
67dd5535 1233TGeoPNEntry* AliGeomManager::GetPNEntry(ELayerID layerId, Int_t modId)
1234{
1235 // Returns the TGeoPNEntry for a given layer
1236 // and module ID
1237 //
25fad4e5 1238
67dd5535 1239 if(modId<0 || modId>=fgLayerSize[layerId-kFirstLayer]){
1240 AliWarningClass(Form("Module number %d not in the valid range (0->%d) !",modId,fgLayerSize[layerId-kFirstLayer]-1));
1241 return NULL;
1242 }
1243
1244 return fgPNEntry[layerId-kFirstLayer][modId];
1245}
1246
1247//_____________________________________________________________________________
5590c6c3 1248void AliGeomManager::CheckOverlapsOverPNs(Double_t threshold)
1249{
1250 // Check for overlaps/extrusions on physical nodes only;
1251 // this overlap-checker is meant to be used to check overlaps/extrusions
1252 // originated by the application of alignment objects.
1253 //
1254
1255 TObjArray* ovexlist = new TObjArray(64);
1256
1257 AliInfoClass("********* Checking overlaps/extrusions over physical nodes only *********");
1258 TObjArray* pnList = gGeoManager->GetListOfPhysicalNodes();
0cd61c1d 1259 TGeoVolume* mvol = 0;
5590c6c3 1260 TGeoPhysicalNode* pn;
1261 TObjArray* overlaps = new TObjArray(64);
1262 overlaps->SetOwner();
1263
1264 TStopwatch timer2;
1265 timer2.Start();
1266 for(Int_t pni=0; pni<pnList->GetEntriesFast(); pni++){
1267 pn = (TGeoPhysicalNode*) pnList->UncheckedAt(pni);
1268 // checking the volume of the mother (go upper in the tree in case it is an assembly)
1269 Int_t levup=1;
1270 while(((TGeoVolume*)pn->GetVolume(pn->GetLevel()-levup))->IsAssembly()) levup++;
1271 //Printf("Going to upper level");
1272 mvol = pn->GetVolume(pn->GetLevel()-levup);
1273 if(!mvol->IsSelected()){
1274 AliInfoClass(Form("Checking overlaps for volume %s",mvol->GetName()));
1275 mvol->CheckOverlaps(threshold);
1276 ovexlist = gGeoManager->GetListOfOverlaps();
1277 TIter next(ovexlist);
1278 TGeoOverlap *ov;
1279 while ((ov=(TGeoOverlap*)next())) overlaps->Add(ov->Clone());
1280 mvol->SelectVolume();
1281 }
1282 }
1283 mvol->SelectVolume(kTRUE); // clears the list of selected volumes
1284
1285 AliInfoClass(Form("Number of overlapping/extruding PNs: %d",overlaps->GetEntriesFast()));
1286 timer2.Stop();
1287 timer2.Print();
1288
1289 TIter nextN(overlaps);
1290 TGeoOverlap *ovlp;
1291 while ((ovlp=(TGeoOverlap*)nextN())) ovlp->PrintInfo();
1292
1293 overlaps->Delete();
1294 delete overlaps;
1295}
1296
1297//_____________________________________________________________________________
67dd5535 1298Bool_t AliGeomManager::ApplyAlignObjsFromCDB(const char* AlignDetsList)
1299{
1300 // Calls AddAlignObjsFromCDBSingleDet for the detectors appearing in
1301 // the list passed as argument (called by AliSimulation and
1302 // AliReconstruction)
1303 // Read the alignment objects from CDB.
1304 // Each detector is supposed to have the
1305 // alignment objects in DET/Align/Data CDB path.
1306 // All the detector objects are then collected,
1307 // sorted by geometry level (starting from ALIC) and
1308 // then applied to the TGeo geometry.
1309 // Finally an overlaps check is performed.
1310 //
1311
36b010bf 1312 TObjArray alignObjArray;
1313 alignObjArray.Clear();
1314 alignObjArray.SetOwner(0);
67dd5535 1315
1316 TString alObjsNotLoaded="";
1317 TString alObjsLoaded="";
1318
1319 TString AlignDetsString(AlignDetsList);
1320 TObjArray *detsarr = AlignDetsString.Tokenize(' ');
1321 TIter iter(detsarr);
1322 TObjString *str = 0;
1323
1324 while((str = (TObjString*) iter.Next())){
1325 TString det(str->String());
36b010bf 1326 AliInfoClass(Form("Loading alignment objs for %s",det.Data()));
1327 if(!LoadAlignObjsFromCDBSingleDet(det.Data(),alignObjArray)){
67dd5535 1328 alObjsNotLoaded += det.Data();
1329 alObjsNotLoaded += " ";
1330 } else {
1331 alObjsLoaded += det.Data();
1332 alObjsLoaded += " ";
1333 }
1334 }
1335
36b010bf 1336 if(!alObjsLoaded.IsNull()) AliInfoClass(Form("Alignment objects loaded for: %s",
1337 alObjsLoaded.Data()));
1338 if(!alObjsNotLoaded.IsNull()) AliInfoClass(Form("Didn't/couldn't load alignment objects for: %s",
1339 alObjsNotLoaded.Data()));
67dd5535 1340
9cb4fe0b 1341 return ApplyAlignObjsToGeom(alignObjArray);
67dd5535 1342}
1343
1344//_____________________________________________________________________________
36b010bf 1345Bool_t AliGeomManager::LoadAlignObjsFromCDBSingleDet(const char* detName, TObjArray& alignObjArray)
67dd5535 1346{
1347 // Adds the alignable objects found in the CDBEntry for the detector
1348 // passed as argument to the array of all alignment objects to be applyed
1349 // to geometry
1350 //
1351 // Fills array of single detector's alignable objects from CDB
1352
36b010bf 1353 AliDebugClass(2, Form("Loading alignment objs for detector: %s",detName));
67dd5535 1354
1355 AliCDBEntry *entry;
1356
1357 AliCDBPath path(detName,"Align","Data");
1358
1359 entry=AliCDBManager::Instance()->Get(path.GetPath());
1360 if(!entry){
36b010bf 1361 AliDebugClass(2,Form("Couldn't load alignment data for detector %s",detName));
67dd5535 1362 return kFALSE;
1363 }
1364 entry->SetOwner(1);
1365 TClonesArray *alignArray = (TClonesArray*) entry->GetObject();
1366 alignArray->SetOwner(0);
36b010bf 1367 AliDebugClass(2,Form("Found %d alignment objects for %s",
1368 alignArray->GetEntries(),detName));
67dd5535 1369
1370 AliAlignObj *alignObj=0;
1371 TIter iter(alignArray);
1372
1373 // loop over align objects in detector
1374 while( ( alignObj=(AliAlignObj *) iter.Next() ) ){
36b010bf 1375 alignObjArray.Add(alignObj);
67dd5535 1376 }
1377 // delete entry --- Don't delete, it is cached!
1378
36b010bf 1379 AliDebugClass(2, Form("fAlignObjArray entries: %d",alignObjArray.GetEntries() ));
67dd5535 1380 return kTRUE;
1381
1382}
1383
1384//_____________________________________________________________________________
5590c6c3 1385Bool_t AliGeomManager::ApplyAlignObjsToGeom(TObjArray& alignObjArray, Bool_t ovlpcheck)
67dd5535 1386{
1387 // Read collection of alignment objects (AliAlignObj derived) saved
1388 // in the TClonesArray alObjArray and apply them to gGeoManager
1389 //
36b010bf 1390 alignObjArray.Sort();
1391 Int_t nvols = alignObjArray.GetEntriesFast();
67dd5535 1392
1393 Bool_t flag = kTRUE;
1394
1395 for(Int_t j=0; j<nvols; j++)
1396 {
36b010bf 1397 AliAlignObj* alobj = (AliAlignObj*) alignObjArray.UncheckedAt(j);
5590c6c3 1398 if (alobj->ApplyToGeometry(ovlpcheck) == kFALSE) flag = kFALSE;
67dd5535 1399 }
1400
1401 if (AliDebugLevelClass() >= 1) {
36b010bf 1402 fgGeometry->GetTopNode()->CheckOverlaps(1);
1403 TObjArray* ovexlist = fgGeometry->GetListOfOverlaps();
67dd5535 1404 if(ovexlist->GetEntriesFast()){
36b010bf 1405 AliErrorClass("The application of alignment objects to the geometry caused huge overlaps/extrusions!");
67dd5535 1406 }
1407 }
1408
36b010bf 1409 // Update the TGeoPhysicalNodes
1410 fgGeometry->RefreshPhysicalNodes();
1411
67dd5535 1412 return flag;
1413
1414}
1415
1416//_____________________________________________________________________________
1417Bool_t AliGeomManager::ApplyAlignObjsToGeom(const char* fileName, const char* clArrayName)
1418{
1419 // read collection of alignment objects (AliAlignObj derived) saved
1420 // in the TClonesArray ClArrayName in the file fileName and apply
1421 // them to the geometry
1422 //
1423
1424 TFile* inFile = TFile::Open(fileName,"READ");
1425 if (!inFile || !inFile->IsOpen()) {
1426 AliErrorClass(Form("Could not open file %s !",fileName));
1427 return kFALSE;
1428 }
1429
36b010bf 1430 TClonesArray* alignObjArray = ((TClonesArray*) inFile->Get(clArrayName));
67dd5535 1431 inFile->Close();
36b010bf 1432 if (!alignObjArray) {
67dd5535 1433 AliErrorClass(Form("Could not get array (%s) from file (%s) !",clArrayName,fileName));
1434 return kFALSE;
1435 }
1436
36b010bf 1437 return ApplyAlignObjsToGeom(*alignObjArray);
67dd5535 1438
1439}
1440
1441//_____________________________________________________________________________
1442Bool_t AliGeomManager::ApplyAlignObjsToGeom(AliCDBParam* param, AliCDBId& Id)
1443{
1444 // read collection of alignment objects (AliAlignObj derived) saved
1445 // in the TClonesArray ClArrayName in the AliCDBEntry identified by
1446 // param (to get the AliCDBStorage) and Id; apply the alignment objects
1447 // to the geometry
1448 //
1449
1450 AliCDBStorage* storage = AliCDBManager::Instance()->GetStorage(param);
1451 AliCDBEntry* entry = storage->Get(Id);
36b010bf 1452 TClonesArray* alignObjArray = ((TClonesArray*) entry->GetObject());
67dd5535 1453
36b010bf 1454 return ApplyAlignObjsToGeom(*alignObjArray);
67dd5535 1455
1456}
1457
1458//_____________________________________________________________________________
1459Bool_t AliGeomManager::ApplyAlignObjsToGeom(const char* uri, const char* path, Int_t runnum, Int_t version, Int_t sversion)
1460{
1461 // read collection of alignment objects (AliAlignObj derived) saved
1462 // in the TClonesArray ClArrayName in the AliCDBEntry identified by
1463 // param (to get the AliCDBStorage) and Id; apply the alignment objects
1464 // to the geometry
1465 //
1466
1467 AliCDBParam* param = AliCDBManager::Instance()->CreateParameter(uri);
1468 AliCDBId id(path, runnum, runnum, version, sversion);
1469
1470 return ApplyAlignObjsToGeom(param, id);
1471
1472}
1473
1474//_____________________________________________________________________________
1475Bool_t AliGeomManager::ApplyAlignObjsToGeom(const char* detName, Int_t runnum, Int_t version, Int_t sversion)
1476{
1477 // read collection of alignment objects (AliAlignObj derived) saved
1478 // in the TClonesArray ClArrayName in the AliCDBEntry identified by
1479 // param (to get the AliCDBStorage) and Id; apply the alignment objects
1480 // to the geometry
1481 //
1482
1483 AliCDBPath path(detName,"Align","Data");
1484 AliCDBEntry* entry = AliCDBManager::Instance()->Get(path.GetPath(),runnum,version,sversion);
1485
1486 if(!entry) return kFALSE;
36b010bf 1487 TClonesArray* alignObjArray = ((TClonesArray*) entry->GetObject());
25fad4e5 1488
36b010bf 1489 return ApplyAlignObjsToGeom(*alignObjArray);
67dd5535 1490}