Added the sector offset in zones.dat files and
[u/mrichter/AliRoot.git] / MUON / mapping / AliMpReader.cxx
1 // $Id$
2 // Category: sector
3 //
4 // Class AliMpReader
5 // -------------------
6 // Class that takes care of reading the sector data.
7 // Included in AliRoot: 2003/05/02
8 // Authors: David Guez, Ivana Hrivnacova; IPN Orsay
9
10 #if !defined(__HP_aCC) && !defined(__alpha)
11   #include <sstream>
12 #endif
13
14 #include <Riostream.h>
15 #include <Rstrstream.h>
16 #include <TSystem.h>
17 #include <TError.h>
18 #include <TMath.h>
19
20 #include "AliMpReader.h"
21 #include "AliMpSector.h"
22 #include "AliMpFiles.h"
23 #include "AliMpZone.h"
24 #include "AliMpSubZone.h"
25 #include "AliMpRow.h"
26 #include "AliMpVRowSegment.h"
27 #include "AliMpRowSegment.h"
28 #include "AliMpRowSegmentLSpecial.h"
29 #include "AliMpRowSegmentRSpecial.h"
30 #include "AliMpPadRow.h"
31 #include "AliMpMotifMap.h"
32 #include "AliMpMotif.h"
33 #include "AliMpMotifSpecial.h"
34 #include "AliMpMotifType.h"
35 #include "AliMpConnection.h"
36 #include "AliMpIntPair.h"
37 #include "AliMpDirection.h"
38
39 ClassImp(AliMpReader)
40
41 #ifdef WITH_ROOT
42 const Int_t    AliMpReader::fgkSeparator = 100;
43 #endif
44
45 const TString  AliMpReader::fgkSectorKeyword  = "SECTOR_DATA";
46 const TString  AliMpReader::fgkZoneKeyword    = "ZONE";
47 const TString  AliMpReader::fgkSubZoneKeyword = "SUBZONE";
48 const TString  AliMpReader::fgkRowKeyword     = "ROW_SEGMENT";
49 const TString  AliMpReader::fgkEofKeyword     = "EOF";
50 const TString  AliMpReader::fgkSectorSpecialKeyword  = "SECTOR_SPECIAL_DATA";
51 const TString  AliMpReader::fgkMotifKeyword          = "MOTIF";
52 const TString  AliMpReader::fgkRowSpecialKeyword     = "ROW";
53 const TString  AliMpReader::fgkPadRowsKeyword        = "PAD_ROWS";
54 const TString  AliMpReader::fgkPadRowSegmentKeyword  = "PAD_ROW_SEGMENT";
55
56 //_____________________________________________________________________________
57 AliMpReader::AliMpReader(AliMpStationType station, AliMpPlaneType plane) 
58   : TObject(),
59     fStationType(station),
60     fPlaneType(plane),
61     fSector(0),
62     fVerboseLevel(0)
63 {
64 //
65 }
66
67 //_____________________________________________________________________________
68 AliMpReader::AliMpReader() 
69   : TObject(),
70     fStationType(kStation1),
71     fPlaneType(kBendingPlane),
72     fSector(0),
73     fVerboseLevel(0)
74 {
75 //
76 }
77
78 //_____________________________________________________________________________
79 AliMpReader::AliMpReader(const AliMpReader& right) 
80   : TObject(right) {
81 // 
82   Fatal("AliMpReader", "Copy constructor not provided.");
83 }
84
85 //_____________________________________________________________________________
86 AliMpReader::~AliMpReader() {
87 //  
88 }
89
90 //
91 // operators
92 //
93
94 //_____________________________________________________________________________
95 AliMpReader& AliMpReader::operator=(const AliMpReader& right)
96 {
97   // check assignement to self
98   if (this == &right) return *this;
99
100   Fatal("operator =", "Assignement operator not provided.");
101     
102   return *this;  
103 }    
104
105 //
106 // private methods
107 //
108
109 #ifdef WITH_ROOT
110 //_____________________________________________________________________________
111 Int_t  AliMpReader::GetIndex(const string& s) const 
112 {
113 // Converts the TString to integer.
114 // ---
115
116   if (s.length() > 5) {
117     Fatal("GetIndex", "String too long.");
118     return 0;
119   }  
120
121   Int_t index = 0;
122   for (Int_t i=s.length(); i>=0; --i)  index = index*100 + int(s[i]);
123   
124   return index;
125 }
126
127 //______________________________________________________________________________
128 Int_t  AliMpReader::GetIndex(const AliMpIntPair& pair) const
129 {
130 // Converts the pair of integers to integer.
131 // ---
132
133   if (pair.GetFirst() >= fgkSeparator || pair.GetSecond() >= fgkSeparator)
134     Fatal("GetIndex", "Index out of limit.");
135       
136   return pair.GetFirst()*fgkSeparator + pair.GetSecond() + 1;
137 }  
138
139 //_____________________________________________________________________________
140 string  AliMpReader::GetString(Int_t index) const
141 {
142 // Converts the integer index to the string.
143 // ---
144
145   string s;
146   while (index >0) {
147     Char_t c = index%100;
148     s += c;
149     index = index/100;
150   }
151   
152   return s;
153   
154 }
155
156 //______________________________________________________________________________
157 AliMpIntPair  AliMpReader::GetPair(Int_t index) const
158 {
159 // Converts the integer index to the pair of integers.
160 // ---
161
162   return AliMpIntPair((index-1)/fgkSeparator, (index-1)%fgkSeparator);
163 }  
164 #endif
165
166 //_____________________________________________________________________________
167 void  AliMpReader::ReadSectorData(ifstream& in)
168 {
169 // Reads sector input data;
170 // prepares zones and rows vectors to be filled in.
171 // ---
172
173   TString keyword;
174   in >> keyword;
175   
176   if (fVerboseLevel>0) 
177     cout << keyword << endl;
178
179   if (keyword != fgkSectorKeyword) {
180      Fatal("ReadSectorData", "Wrong file format.");
181      return;
182   }   
183     
184   Int_t nofZones, nofRows;
185   TString directionStr;
186   Double_t offsetX, offsetY;
187   in >> nofZones;
188   in >> nofRows;
189   in >> directionStr;
190   in >> offsetX;
191   in >> offsetY;
192   
193   AliMpDirection direction;
194   direction = (directionStr == "Y") ? kY  :  kX;
195   if (fVerboseLevel>0) 
196      cout << nofZones << " " <<  nofRows << endl;
197
198   fSector = new AliMpSector("Not defined", nofZones, nofRows,direction,
199                             TVector2(offsetX, offsetY));
200   
201   TString nextKeyword;
202   in >> nextKeyword;
203     
204   if (nextKeyword != fgkZoneKeyword) {
205      Fatal("ReadSectorData", "Wrong file format.");
206      return;
207   }      
208   
209   ReadZoneData(in);
210 }  
211
212 //_____________________________________________________________________________
213 void AliMpReader::ReadZoneData(ifstream& in)
214 {
215 // Reads zone input data;
216 // creates zone and adds it to zones vector.
217 // ---
218
219   Int_t zoneID;
220   Double_t  sizex, sizey; 
221   in >> zoneID;    
222   in >> sizex;
223   in >> sizey;
224   if (fVerboseLevel>0) 
225      cout << fgkZoneKeyword << " " <<  zoneID << "  "        
226           << sizex << " " << sizey << endl;
227   
228   AliMpZone* zone =  fSector->GetZone(zoneID);
229   zone->SetPadDimensions(TVector2(sizex/2.,sizey/2.)); 
230       
231   TString nextKeyword;
232   in >> nextKeyword;
233     
234   if (nextKeyword != fgkSubZoneKeyword) {
235      Fatal("ReadZoneData", "Wrong file format.");
236      return;
237   }  
238     
239   ReadSubZoneData(in, zone);
240 }
241
242 //_____________________________________________________________________________
243 void AliMpReader::ReadSubZoneData(ifstream& in, AliMpZone* zone)
244 {
245 // Reads subzone input data;
246 // creates subzone and its to the specified zone.
247 // ---
248
249   if (fVerboseLevel>0) 
250     cout << fgkSubZoneKeyword << " ";
251
252   AliMpVMotif* motif = ReadMotifData(in, zone);
253   AliMpSubZone* subZone = new AliMpSubZone(motif); 
254   zone->AddSubZone(subZone); 
255
256   TString nextKeyword;
257   in >> nextKeyword;
258     
259   if (nextKeyword != fgkRowKeyword) {
260      Fatal("ReadSubZoneData", "Wrong file format.");
261      return;
262   }  
263     
264   ReadRowSegmentsData(in, zone, subZone);
265 }   
266
267 //_____________________________________________________________________________
268 AliMpVMotif*  AliMpReader::ReadMotifData(ifstream& in, AliMpZone* zone)
269 {
270 // Reads the motif input data.
271 // ---
272
273   TString  motifID;
274   TString  motifTypeID;
275   in >> motifID;
276   in >> motifTypeID;
277   if (fVerboseLevel>0) {
278     cout << motifID << " " 
279          << motifTypeID << endl;
280   }      
281   
282   AliMpMotifMap* motifMap = fSector->GetMotifMap();
283
284   AliMpMotifType* motifType = 0;
285   AliMpVMotif* motif 
286     = motifMap->FindMotif(motifID, motifTypeID, zone->GetPadDimensions());
287   if (!motif) {    
288     motifType = motifMap->FindMotifType(motifTypeID);
289     if (!motifType) {
290       motifType = BuildMotifType(motifTypeID);     
291       motifMap->AddMotifType(motifType);
292     }
293     
294     if (zone->GetPadDimensions().X() != 0. && zone->GetPadDimensions().Y() != 0.) 
295       motif = new AliMpMotif(motifID, motifType, zone->GetPadDimensions());
296     else 
297       motif = BuildMotifSpecial(motifID, motifType);
298       
299     if (motif) 
300       motifMap->AddMotif(motif);
301
302   }  
303
304   return motif;   
305 }  
306
307 //_____________________________________________________________________________
308 void AliMpReader::ReadRowSegmentsData(ifstream& in, 
309                                       AliMpZone* zone, AliMpSubZone* subZone)
310 {
311 // Reads row segments input data of a specified zone and subzone;
312 // creates row segment and adds it to the specified subzone
313 // and a corresponding row in the rows vector.
314 // ---
315
316   TString nextKeyword;
317   do {
318     // 
319     // Read data from file
320     //
321     Int_t offX, offY, inRow, nofMotifs, firstMotifPositionId, firstMotifPositionDId;
322     in >> offX;
323     in >> offY;
324     in >> inRow;
325     in >> nofMotifs;
326     in >> firstMotifPositionId;
327     in >> firstMotifPositionDId;
328     if (fVerboseLevel>0) 
329        cout << fgkRowKeyword << " " 
330             << offX << " " << offY << " " << inRow << " " << nofMotifs << " " 
331             << firstMotifPositionId << " " << firstMotifPositionDId
332             << endl;
333
334     in >> nextKeyword;
335
336     //
337     // Process data
338     //
339     AliMpRow* row = fSector->GetRow(inRow);
340     AliMpVMotif* motif = subZone->GetMotif();
341     
342     // Create row segment and add it to its zone, row   
343     AliMpVRowSegment* rowSegment
344       = new AliMpRowSegment(row, motif, AliMpIntPair(offX, offY), nofMotifs, 
345                         firstMotifPositionId, firstMotifPositionDId);
346                         
347     subZone->AddRowSegment(rowSegment);
348     row->AddRowSegment(rowSegment);
349   }
350   while (!in.eof() && (nextKeyword == fgkRowKeyword));
351
352   if (in.eof()) return;
353
354   if (nextKeyword == fgkZoneKeyword) {
355     ReadZoneData(in);
356   }
357   else if (nextKeyword == fgkSubZoneKeyword) {
358     ReadSubZoneData(in, zone);
359   }   
360   else {
361     Fatal("ReadRowSegmentsData", "Wrong file format.");
362   } 
363 }   
364
365 //_____________________________________________________________________________
366 void AliMpReader::ReadSectorSpecialData(ifstream& in, AliMpXDirection direction)
367 {
368 // Reads sector input data
369 // with a special (irregular) motifs.
370 // ---
371
372   TString keyword;
373   in >> keyword;
374   if (fVerboseLevel>0) 
375     cout << keyword << endl;
376
377   if (keyword != fgkSectorSpecialKeyword) {
378      Fatal("ReadSectorSpecialData", "Wrong file format.");
379      return;
380   }   
381
382   TString nextKeyword;
383   in >> nextKeyword;
384   if (fVerboseLevel>0) 
385     cout << keyword << endl;
386     
387   if (nextKeyword != fgkMotifKeyword) {
388     Fatal("ReadSectorSpecialData", "Wrong file format.");
389     return;
390   }  
391
392   ReadMotifsSpecialData(in);     
393   ReadRowSpecialData(in, direction); 
394 }  
395
396 //_____________________________________________________________________________
397 void AliMpReader::ReadMotifsSpecialData(ifstream& in)
398 {
399 // Reads the special (irregular) motifs input data.
400 // ---
401
402   if (fVerboseLevel>0) 
403     cout << fgkMotifKeyword << " ";
404
405   TString nextKeyword;
406   do {
407     Int_t zone;
408     in >> zone;
409     AliMpVMotif* motif =  ReadMotifData(in, fSector->GetZone(zone));
410     AliMpSubZone* subZone = new AliMpSubZone(motif); 
411     fSector->GetZone(zone)->AddSubZone(subZone); 
412   
413     in >> nextKeyword;
414     if (fVerboseLevel>0) 
415       cout << nextKeyword << " ";      
416   }
417   while (nextKeyword == fgkMotifKeyword);
418     
419   if (nextKeyword != fgkRowSpecialKeyword) {
420      Fatal("ReadMotifSpecialData", "Wrong file format.");
421      return;
422   }      
423 }  
424
425 //_____________________________________________________________________________
426 void AliMpReader::ReadRowSpecialData(ifstream& in, AliMpXDirection direction)
427 {
428 // Reads row input data
429 // with a special (irregular) motifs.
430 // ---
431
432   Int_t id;
433   in >> id;
434   if (fVerboseLevel>0) 
435       cout << id << endl;      
436   
437   // Get the row and its border
438   AliMpRow* row = fSector->GetRow(id);
439
440   AliMpVRowSegmentSpecial* segment = 0;
441   if (direction == kLeft) {
442     AliMpVRowSegment* firstNormalSeg = row->GetRowSegment(0);
443     Double_t offsetX = firstNormalSeg->LeftBorderX();
444   
445     // Create a special row segment
446     segment = new AliMpRowSegmentLSpecial(row, offsetX);
447     row->AddRowSegmentInFront(segment);
448   }
449   else { 
450     AliMpVRowSegment* precedentNormalSeg 
451       = row->GetRowSegment(row->GetNofRowSegments()-1);
452     Double_t offsetX = precedentNormalSeg->RightBorderX();
453   
454     // Create a special row segment
455     segment = new AliMpRowSegmentRSpecial(row, offsetX);
456     row->AddRowSegment(segment);
457   }  
458       
459   TString nextKeyword;
460   in >> nextKeyword;
461   if (fVerboseLevel>0) 
462     cout << nextKeyword << " ";
463     
464   if (nextKeyword != fgkPadRowsKeyword) {
465      Fatal("ReadRowSpecialData", "Wrong file format.");
466      return;
467   }  
468     
469   ReadRowSegmentSpecialData(in, segment, direction); 
470   
471   // Update row segment and set it to all subzones associated with
472   // contained motifs
473   
474   segment->UpdateMotifVector();
475   segment->UpdatePadsOffset();
476   
477   for (Int_t i=0; i<segment->GetNofMotifs(); i++) {
478     AliMpSubZone* subZone = 0;
479     Int_t j = 0;
480     while (!subZone && j<fSector->GetNofZones())
481       subZone = fSector->GetZone(++j)->FindSubZone(segment->GetMotif(i));
482     
483     subZone->AddRowSegment(segment);
484   }  
485 }  
486
487 //_____________________________________________________________________________
488 void AliMpReader::ReadRowSegmentSpecialData(ifstream& in, 
489                                             AliMpVRowSegmentSpecial* segment,
490                                             AliMpXDirection direction)
491 {
492 // Reads row segment input data
493 // with a special (irregular) motifs.
494 // ---
495
496   Int_t nofPadRows;
497   in >> nofPadRows;
498   if (fVerboseLevel>0) 
499     cout << nofPadRows << endl;
500   
501   TString keyword;
502   in >> keyword;
503   if (fVerboseLevel>0) 
504     cout << keyword << " ";
505     
506   if (keyword != fgkPadRowSegmentKeyword) {
507      Fatal("ReadRowSegmentSpecialData", "Wrong file format.");
508      return;
509   }  
510   
511   //
512   // Process data
513   //
514     
515   PadRowVector  newPadRows;
516   for (Int_t i=0; i<nofPadRows; i++) {
517     
518      // Create pad row
519      AliMpPadRow* padRow = new AliMpPadRow(direction);
520      segment->AddPadRow(padRow);
521      
522      // Keep the new rows in a temporary vector
523 #ifdef WITH_STL
524      newPadRows.push_back(padRow);
525 #endif
526 #ifdef WITH_ROOT
527      newPadRows.Add(padRow);
528 #endif
529   }   
530       
531   TString nextKeyword;
532   do {
533     // 
534     // Read data from file
535     //
536     Int_t    nofPadsInRow, motifPositionId;
537     TString   motifId, motifTypeId;
538     in >> nofPadsInRow;
539     in >> motifId;
540     in >> motifPositionId; 
541   
542     if (fVerboseLevel>0) 
543        cout << nofPadsInRow << " " << motifId << " " << motifPositionId << endl;
544
545     in >> nextKeyword;
546     if (fVerboseLevel>0) 
547       cout << nextKeyword << " ";
548
549     //
550     // Process data
551     //
552     
553     for (Int_t i=0; i<nofPadRows; i++) {
554     
555       // Get pad row from the temporary vector
556 #ifdef WITH_STL
557       AliMpPadRow* padRow = newPadRows[i];
558 #endif
559 #ifdef WITH_ROOT
560       AliMpPadRow* padRow = (AliMpPadRow*)newPadRows[i];
561 #endif
562       
563       // Find motif
564       AliMpVMotif* motif = fSector->GetMotifMap()->FindMotif(motifId);
565       
566       if (!motif) {
567         Fatal("ReadRowSegmentSpecialData", "Unknown motif.");
568         return;
569       }
570
571       // Create pad row segment
572       padRow->AddPadRowSegment(dynamic_cast<AliMpMotif *>(motif), 
573                                motifPositionId, nofPadsInRow);
574     }  
575   }
576   while (!in.eof() && (nextKeyword == fgkPadRowSegmentKeyword));
577   
578   if (in.eof()) return;
579
580   if (nextKeyword == fgkPadRowsKeyword) {
581     ReadRowSegmentSpecialData(in, segment, direction);
582   }
583   else if (nextKeyword == fgkRowSpecialKeyword) {
584     ReadRowSpecialData(in, direction);
585   }   
586   else {
587     Fatal("ReadRowSegmentSpecialData", "Wrong file format.");
588   } 
589 }  
590
591 //
592 // public methods
593 //
594
595 //_____________________________________________________________________________
596 AliMpSector* AliMpReader::BuildSector()
597 {
598 // Reads the mapping data from ascii file
599 // $MINSTALL/data/fileName and creates the basic objects:
600 // zones, subzones, rows, row segments, motifs.
601 // ---
602
603   // Open input file
604   ifstream in(AliMpFiles::Instance()
605               ->SectorFilePath(fStationType, fPlaneType).Data(), ios::in);
606   if (!in) {
607      cerr << AliMpFiles::Instance()
608               ->SectorFilePath(fStationType, fPlaneType) << endl;       
609      Error("BuildSector", "File not found.");
610      return 0;
611   }
612   
613   ReadSectorData(in);
614   fSector->SetRowSegmentOffsets();
615
616   // Open input file for special inner zone
617   TString sectorSpecialFileName 
618     = AliMpFiles::Instance()->SectorSpecialFilePath(fStationType, fPlaneType);
619   if (!gSystem->AccessPathName(sectorSpecialFileName.Data())) {
620     ifstream in2(sectorSpecialFileName.Data(), ios::in);
621     if (!in2) { 
622        cerr << AliMpFiles::Instance()
623               ->SectorSpecialFilePath(fStationType, fPlaneType) << endl;        
624        Error("BuildSector", "File not found.");
625        return 0;
626     }
627     
628     ReadSectorSpecialData(in2, kLeft);
629   }   
630
631   // Open input file for special outer zone
632   TString sectorSpecialFileName2 
633     = AliMpFiles::Instance()->SectorSpecialFilePath2(fStationType, fPlaneType);
634   if (!gSystem->AccessPathName(sectorSpecialFileName2.Data())) {
635     ifstream in3(sectorSpecialFileName2.Data(), ios::in);
636     if (!in3) { 
637        cerr << AliMpFiles::Instance()
638               ->SectorSpecialFilePath2(fStationType, fPlaneType) << endl;       
639        Error("Build", "File not found.");
640        return 0;
641     }
642     
643     ReadSectorSpecialData(in3, kRight);
644   }   
645
646   fSector->Initialize();
647   
648   return fSector;
649 }  
650
651 //_____________________________________________________________________________
652 AliMpMotifType* AliMpReader::BuildMotifType(const TString& motifTypeId)
653 {
654
655   // Read the files describing a motif in the "$MINSTALL/data" directory
656   // and fill the AliMpMotifType structure with.
657   // The files mentioned are are named padPos<maskName>.dat
658   // and connect<maskName>.dat
659
660   AliMpMotifType*  motifType = new AliMpMotifType(motifTypeId); 
661
662   TString strPadPos 
663     = AliMpFiles::Instance()
664       ->PadPosFilePath(fStationType, fPlaneType, motifTypeId);
665   ifstream padPos(strPadPos.Data());
666   if (fVerboseLevel>0) cout<<"Opening file "<<strPadPos<<endl;
667
668   PadMapType positions;
669
670   char line[256];
671   do {
672     padPos.getline(line,255);
673     if (!padPos) break;
674
675 #if defined (__HP_aCC) || (__alpha)
676     strstream strline;
677     strline << line;
678 #else
679     istringstream strline(line);
680 #endif    
681     string key;
682
683     strline>>key;
684     if ((key=="#") || (key=="") ) continue;
685
686     int i,j;
687     strline>>i>>j;
688 #ifdef WITH_STL
689     positions[key].first=i;
690     positions[key].second=j;
691 #endif
692 #ifdef WITH_ROOT
693     positions.Add(GetIndex(key), GetIndex(AliMpIntPair(i,j))); 
694 #endif
695   } while (!padPos.eof());
696
697   padPos.close();
698
699   if (fVerboseLevel>0) 
700     cout << "Opening file "
701          << AliMpFiles::Instance()->BergToGCFilePath(fStationType)
702          << endl;
703
704   ifstream bergToGCFile(AliMpFiles::Instance()->BergToGCFilePath(fStationType));
705   Int_t gassiChannel[80];
706   while(1) {
707     Int_t bergNum;
708     TString gcStr;
709     bergToGCFile>>bergNum>>gcStr;
710     if (!bergToGCFile.good()) break;
711     if (gcStr=="GND") continue;
712     if (bergNum>80) {
713         Fatal("BuildMotifType","Berg number > 80 ...");
714         continue;
715     }
716     gassiChannel[bergNum-1]= atoi(gcStr);
717   }
718   bergToGCFile.close();
719   
720   TString strMotif 
721     = AliMpFiles::Instance()
722       ->MotifFilePath(fStationType, fPlaneType, motifTypeId);
723   ifstream motif(strMotif);
724   if (fVerboseLevel>0) cout<<"Opening file "<<strMotif<<endl;
725
726
727   Int_t nofPadsX=0;
728   Int_t nofPadsY=0;
729
730   do {
731   
732     Int_t ix,iy,numBerg,numKapton,padNum,gassiNum;
733
734     TString lineStr,token;
735     lineStr.ReadLine(motif);
736     if (!motif.good()) break;
737 #if defined (__HP_aCC) || (__alpha)
738     strstream tokenList;
739     tokenList << lineStr.Data();
740 #else
741     istringstream tokenList(lineStr.Data());
742 #endif    
743     
744     token.ReadToken(tokenList);
745     if (!tokenList.good()) continue; // column is missing...
746     if ( (token.Length()>0) && (token[0]=='#') ) continue; // this is a comment line
747     
748     numBerg = atoi(token.Data());
749     if (numBerg==0) {
750       Warning("BuildMotifType","Berg number invalid");
751       continue;
752     }
753     
754     token.ReadToken(tokenList);
755     if (!tokenList.good()) continue; // column is missing...
756     numKapton = atoi(token.Data());
757     if (numKapton==0) continue;
758
759     
760     token.ReadToken(tokenList);
761     if (!tokenList.good()) continue; // column is missing...
762     if (token=="GND") continue;
763     string padName = token.Data();
764     padNum = motifType->PadNum(token);
765     
766      token.ReadToken(tokenList);
767      if (token.IsNull() ) continue; // column is missing...
768 //     if (token[0]!='E') {
769 //       cerr<<"Problem : gassinumber isn't begining with E:"<<token<<endl;
770 //       continue;
771 //     }  else {
772 //        gassiNum = atoi(token.Data() +1 )-1;
773 //     }
774     if ( (numBerg<1) || (numBerg>80) ) {
775         Warning("BuildMotifType","Berg number outside range");
776         continue;
777     }
778     
779     gassiNum  = gassiChannel[numBerg-1];
780
781 #ifdef WITH_STL
782     PadMapTypeIterator iter = positions.find(padName);
783     if (iter==positions.end()) {
784       cerr<<"Problem: Pad number "<<padNum<<" found in the file "<<strMotif
785           <<" but not in the file"<<strPadPos<<endl;
786       continue;
787     }
788
789     ix= iter->second.first;
790     iy= iter->second.second;
791 #endif
792
793 #ifdef WITH_ROOT
794     Long_t value = positions.GetValue(GetIndex(padName));
795     if (!value) {
796       cerr<<"Problem: Pad number "<<padNum<<" found in the file "<<strMotif
797           <<" but not in the file"<<strPadPos<<endl;
798       continue;
799     }
800
801     ix = GetPair(value).GetFirst();
802     iy = GetPair(value).GetSecond();
803 #endif
804
805     motifType->AddConnection(AliMpIntPair(ix,iy),
806                   new AliMpConnection(padNum,numBerg,numKapton,gassiNum));
807
808     if (ix>=nofPadsX) nofPadsX=ix+1;
809     if (iy>=nofPadsY) nofPadsY=iy+1;
810
811   } while (!motif.eof());    
812
813
814   motifType->SetNofPads(nofPadsX, nofPadsY);
815
816   motif.close();
817
818   return motifType;
819 }
820
821
822 //_____________________________________________________________________________
823 AliMpMotifSpecial*  
824 AliMpReader::BuildMotifSpecial(const TString& motifID,
825                                AliMpMotifType* motifType)
826 {
827 // Build a special motif by reading the file motifSpecial<motifId>.dat
828 // in the data directory
829 // ---
830
831   // Open the input file
832   ifstream in(AliMpFiles::Instance()
833               ->MotifSpecialFilePath(fStationType, fPlaneType, motifID).Data(), 
834               ios::in);
835   if (!in) {    
836      Error("BuildMotifSpecial", "File not found.");
837      return 0;
838   }
839
840   AliMpMotifSpecial* res = new AliMpMotifSpecial(motifID,motifType);
841   Int_t i,j;
842   Double_t x,y;
843   in >> i;
844   while (!in.eof()){
845     in >>j >>x >> y;
846     res->SetPadDimensions(AliMpIntPair(i,j),TVector2(x/2.,y/2.));
847     in >> i;
848   }
849   
850   in.close();
851   return res;
852 }
853
854
855 //_____________________________________________________________________________
856 void AliMpReader::SetVerboseLevel(Int_t verboseLevel)
857 {
858 // Sets verbose level.
859 // ---
860
861   fVerboseLevel = verboseLevel;
862 }
863