#include "AliHLTMUONConstants.h"
#include "AliHLTMUONUtils.h"
#include "AliHLTMUONDataBlockWriter.h"
+#include "AliHLTMUONHitReconstructor.h"
#include "AliHLTLogging.h"
#include "AliHLTSystem.h"
#include "AliHLTDefinitions.h"
#include <cstdlib>
#include <cerrno>
#include <cassert>
+#include <fstream>
+
+//STEER
+#include "AliCDBManager.h"
+#include "AliCDBStorage.h"
+#include "AliGeomManager.h"
+
+//MUON
+#include "AliMUONGeometryTransformer.h"
+#include "AliMUONCalibrationData.h"
+#include "AliMUONVCalibParam.h"
+
+//MUON/mapping
+#include "AliMpCDB.h"
+#include "AliMpPad.h"
+#include "AliMpSegmentation.h"
+#include "AliMpDDLStore.h"
+#include "AliMpDEIterator.h"
+#include "AliMpVSegmentation.h"
+#include "AliMpDEManager.h"
+#include "AliMpDetElement.h"
ClassImp(AliHLTMUONHitReconstructorComponent)
AliHLTMUONHitReconstructorComponent::AliHLTMUONHitReconstructorComponent() :
AliHLTProcessor(),
fHitRec(NULL),
- fDDLDir(""),
- fDDL(0),
- fReaderType(false),
+ fDDL(-1),
+ fLutSize(0),
+ fLut(NULL),
+ fIdToEntry(),
fWarnForUnexpecedBlock(false)
{
///
///
/// Default destructor.
///
+
+ if (fHitRec != NULL)
+ {
+ delete fHitRec;
+ }
+ if (fLut != NULL)
+ {
+ delete fLut;
+ }
}
const char* AliHLTMUONHitReconstructorComponent::GetComponentID()
/// Inherited from AliHLTComponent.
/// Parses the command line parameters and initialises the component.
///
+
+ HLTInfo("Initialising dHLT hit reconstruction component.");
+
+ // Must make sure that fHitRec and fLut is deleted if it is still
+ // allocated for whatever reason.
+ FreeMemory();
- // perform initialization. We check whether our relative output size is specified in the arguments.
-
- HLTInfo("Initialising DHLT HitReconstruction Component");
-
- fHitRec = new AliHLTMUONHitReconstructor();
- fWarnForUnexpecedBlock = false;
-
- // this is to get rid of the warning "unused parameter"
- if (argc==0 && argv==NULL) {
- HLTError("Arguments missing", " no arguments" );
- }
-
- char lutFileName[500],buspatchFileName[500];
-
- int i = 0;
- char* cpErr;
- while ( i < argc )
- {
- HLTDebug("argv[%d] == %s", i, argv[i] );
-
- if ( !strcmp( argv[i], "-lut" ) ) {
- if ( argc <= i+1 ) {
- HLTError("LookupTable filename not specified" );
- return EINVAL; /* Invalid argument */
+ try
+ {
+ fHitRec = new AliHLTMUONHitReconstructor();
}
-
- sprintf(lutFileName,"%s",argv[i+1]);
-
- i += 2;
- continue;
- }// lut argument
-
-
- if ( !strcmp( argv[i], "-ddl" ) ) {
- if ( argc <= i+1 ) {
- HLTError("DDL number not specified" );
- return EINVAL; /* Invalid argument */
+ catch (const std::bad_alloc&)
+ {
+ HLTError("Could not allocate more memory for the hit reconstructor component.");
+ return -ENOMEM;
}
-
- unsigned long num = strtoul( argv[i+1], &cpErr, 0 );
- if (cpErr == NULL or *cpErr != '\0')
- {
- HLTError("Cannot convert '%s' to DDL Number ", argv[i+1] );
- return EINVAL;
- }
- if (num < 13 or 20 < num)
- {
- HLTError("The DDL number must be in the range [13..20].");
- return EINVAL;
+
+ // Initialise fields with default values then parse the command line.
+ fDDL = -1;
+ fIdToEntry.clear();
+ fWarnForUnexpecedBlock = false;
+
+ const char* lutFileName = NULL;
+ const char* cdbPath = NULL;
+ Int_t run = -1;
+ bool useCDB = false;
+
+ for (int i = 0; i < argc; i++)
+ {
+ HLTDebug("argv[%d] == %s", i, argv[i]);
+
+ if (strcmp( argv[i], "-ddl" ) == 0)
+ {
+ if (argc <= i+1)
+ {
+ HLTError("The DDL number was not specified. Must be in the range [13..20].");
+ FreeMemory(); // Make sure we cleanup to avoid partial initialisation.
+ return -EINVAL;
+ }
+
+ char* cpErr = NULL;
+ unsigned long num = strtoul( argv[i+1], &cpErr, 0 );
+ if (cpErr == NULL or *cpErr != '\0')
+ {
+ HLTError("Cannot convert '%s' to DDL a number.", argv[i+1] );
+ FreeMemory(); // Make sure we cleanup to avoid partial initialisation.
+ return -EINVAL;
+ }
+ if (num < 13 or 20 < num)
+ {
+ HLTError("The DDL number must be in the range [13..20].");
+ FreeMemory(); // Make sure we cleanup to avoid partial initialisation.
+ return -EINVAL;
+ }
+ fDDL = num - 1; // convert to range [12..19]
+
+ i++;
+ continue;
+ } // -ddl argument
+
+ if (strcmp( argv[i], "-lut" ) == 0)
+ {
+ if (argc <= i+1)
+ {
+ HLTError("The lookup table filename was not specified.");
+ FreeMemory(); // Make sure we cleanup to avoid partial initialisation.
+ return -EINVAL;
+ }
+ lutFileName = argv[i+1];
+ i++;
+ continue;
+ } // -lut argument
+
+ if (strcmp( argv[i], "-cdb" ) == 0)
+ {
+ useCDB = true;
+ continue;
+ } // -cdb argument
+
+ if (strcmp( argv[i], "-cdbpath" ) == 0)
+ {
+ if ( argc <= i+1 )
+ {
+ HLTError("The CDB path was not specified." );
+ FreeMemory(); // Make sure we cleanup to avoid partial initialisation.
+ return -EINVAL;
+ }
+ cdbPath = argv[i+1];
+ useCDB = true;
+ i++;
+ continue;
+ } // -cdb argument
+
+ if (strcmp( argv[i], "-run" ) == 0)
+ {
+ if ( argc <= i+1 )
+ {
+ HLTError("The RUN number was not specified." );
+ FreeMemory(); // Make sure we cleanup to avoid partial initialisation.
+ return -EINVAL;
+ }
+
+ char* cpErr = NULL;
+ run = Int_t( strtoul(argv[i+1], &cpErr, 0) );
+ if (cpErr == NULL or *cpErr != '\0')
+ {
+ HLTError("Cannot convert '%s' to a valid run number."
+ " Expected an integer value.", argv[i+1]
+ );
+ FreeMemory(); // Make sure we cleanup to avoid partial initialisation.
+ return -EINVAL;
+ }
+
+ i++;
+ continue;
+ } // -run argument
+
+ if (strcmp( argv[i], "-warn_on_unexpected_block" ) == 0)
+ {
+ fWarnForUnexpecedBlock = true;
+ continue;
+ }
+
+ HLTError("Unknown option '%s'", argv[i]);
+ FreeMemory(); // Make sure we cleanup to avoid partial initialisation.
+ return -EINVAL;
+
+ } // for loop
+
+ if (lutFileName == NULL) useCDB = true;
+
+ if (fDDL == -1)
+ {
+ HLTWarning("DDL number not specified. Cannot check if incomming data is valid.");
}
- fDDL = num - 1;
- i += 2;
- continue;
- }// ddl argument
-
-
- if ( !strcmp( argv[i], "-rawdir" ) ) {
- if ( argc <= i+1 ) {
- HLTError("DDL directory not specified" );
- return EINVAL; /* Invalid argument */
+ int result = 0;
+ if (useCDB)
+ {
+ HLTInfo("Loading lookup table information from CDB for DDL %d.", fDDL+1);
+ if (fDDL == -1)
+ HLTWarning("DDL number not specified. The lookup table loaded from CDB will be empty!");
+ result = ReadCDB(cdbPath, run);
}
-
- fDDLDir = argv[i+1] ;
-
- i += 2;
- continue;
- }// ddl directory argument
-
-
- if ( !strcmp( argv[i], "-buspatchmap" ) ) {
- if ( argc <= i+1 ) {
- HLTError("Buspatch filename not specified" );
- return EINVAL; /* Invalid argument */
+ else
+ {
+ HLTInfo("Loading lookup table information from file %s.", lutFileName);
+ result = ReadLookUpTable(lutFileName);
}
-
- sprintf(buspatchFileName,"%s",argv[i+1]);
-
- i += 2;
- continue;
- }// buspatch argument
-
- if ( !strcmp( argv[i], "-rawreader" ) ) {
- fReaderType = true; // true when using rawreader for standalone it is set to false.
- i += 1;
- continue;
- }
-
- if ( !strcmp( argv[i], "-warn_on_unexpected_block" ) ) {
- fWarnForUnexpecedBlock = true;
- i++;
- continue;
- }
-
- HLTError("Unknown option '%s'", argv[i] );
- return EINVAL;
-
- }//while loop
-
- int lutline = fHitRec->GetLutLine(fDDL);
- AliHLTMUONHitReconstructor::DHLTLut* lookupTable = new AliHLTMUONHitReconstructor::DHLTLut[lutline];
- if(!ReadLookUpTable(lookupTable,lutFileName)){
- HLTError("Failed to read lut, lut cannot be read, DoInit");
- return ENOENT ; /* No such file or directory */
- }else{
-
- BusToDetElem busToDetElem;
- BusToDDL busToDDL;
- if(!ReadBusPatchToDetElemFile(busToDetElem,busToDDL,buspatchFileName)){
- HLTError("Failed to read buspatchmap, buspatchmap cannot be read, DoInit");
- return ENOENT ; /* No such file or directory */
- }
-
- fHitRec->SetBusToDetMap(busToDetElem);
- fHitRec->SetBusToDDLMap(busToDDL);
- fHitRec->LoadLookUpTable(lookupTable,fDDL);
-
- }// reading lut
-
- delete []lookupTable;
-
- HLTInfo("Initialisation of DHLT HitReconstruction Component is done");
-
- return 0;
+ if (result != 0)
+ {
+ // Error messages already generated in ReadCDB or ReadLookUpTable.
+ FreeMemory(); // Make sure we cleanup to avoid partial initialisation.
+ return result;
+ }
+
+ fHitRec->SetLookUpTable(fLut, &fIdToEntry);
+
+ return 0;
}
/// Inherited from AliHLTComponent. Performs a cleanup of the component.
///
- if(fHitRec)
- delete fHitRec;
-
- HLTInfo(" Deinitialising DHLT HitReconstruction Component");
-
- return 0;
+ HLTInfo("Deinitialising dHLT hit reconstruction component.");
+ FreeMemory();
+ return 0;
}
continue;
}
+ if (fDDL != -1)
+ {
+ bool ddl[22];
+ AliHLTMUONUtils::UnpackSpecBits(blocks[n].fSpecification, ddl);
+ if (not ddl[fDDL])
+ {
+ HLTWarning("Received raw data from an unexpected DDL.");
+ }
+ }
+
// Create a new output data block and initialise the header.
AliHLTMUONRecHitsBlockWriter block(outputPtr+totalSize, size-totalSize);
if (not block.InitCommonHeader())
+ fHitRec->GetkDDLHeaderSize();
AliHLTUInt32_t nofHit = block.MaxNumberOfEntries();
+#ifdef DEBUG
HLTDebug("=========== Dumping DDL payload buffer ==========");
for (AliHLTUInt32_t j = 0; j < totalDDLSize; j++)
HLTDebug("buffer[%d] : %x",j,buffer[j]);
HLTDebug("================== End of dump =================");
+#endif // DEBUG
if (not fHitRec->Run(buffer, ddlRawDataSize, block.GetArray(), nofHit))
{
HLTError("Error while processing of hit reconstruction algorithm.");
size = totalSize; // Must tell the framework how much buffer space was used.
- return EIO;
+ return -EIO;
}
// nofHit should now contain the number of reconstructed hits actually found
}
-bool AliHLTMUONHitReconstructorComponent::ReadLookUpTable(AliHLTMUONHitReconstructor::DHLTLut* lookupTable, const char* lutpath)
+void AliHLTMUONHitReconstructorComponent::FreeMemory()
+{
+ /// Deletes any allocated objects if they are allocated else nothing is
+ /// done for objects not yet allocated.
+ /// This is used as a helper method to make sure the corresponding pointers
+ /// are NULL and we get back to a well defined state.
+
+ if (fHitRec != NULL)
+ {
+ delete fHitRec;
+ fHitRec = NULL;
+ }
+ if (fLut != NULL)
+ {
+ delete fLut;
+ fLut = NULL;
+ fLutSize = 0;
+ }
+
+ fIdToEntry.clear();
+}
+
+
+int AliHLTMUONHitReconstructorComponent::ReadLookUpTable(const char* lutFileName)
{
- ///
/// Read in the lookup table from a text file.
- ///
+ /// Note that this method could leave fLut allocated which is cleaned up
+ /// by DoInit with a call to FreeMemory().
+
+ assert( fLut == NULL );
+ assert( fLutSize == 0 );
+ assert( fIdToEntry.empty() );
+
+ std::ifstream file(lutFileName);
+ if (not file.good())
+ {
+ HLTError("Could not open the LUT file %s", lutFileName);
+ return -ENOENT;
+ }
+
+ // First count the number of lines of text in the LUT file before decoding.
+ // This is not the most optimal. It would be better to read and decode at the
+ // same time but we are not allowed to use STL and ROOT containers are too
+ // heavy for this task. At least this is done only at the start of run.
+ std::string str;
+ AliHLTUInt32_t lineCount = 0;
+ while (std::getline(file, str)) lineCount++;
+ if (not file.eof())
+ {
+ HLTError("There was a problem reading the LUT file %s", lutFileName);
+ return -EIO;
+ }
+ if (lineCount == 0)
+ {
+ HLTWarning("The LUT file %s was empty.", lutFileName);
+ }
+
+ // Add one extra LUT line for the first element which is used as a sentinel value.
+ lineCount++;
+
+ try
+ {
+ fLut = new AliHLTMUONHitRecoLutRow[lineCount];
+ fLutSize = lineCount;
+ }
+ catch (const std::bad_alloc&)
+ {
+ HLTError("Could not allocate more memory for the lookuptable.");
+ return -ENOMEM;
+ }
- if (fDDL < AliHLTMUONHitReconstructor::GetkDDLOffSet() ||
- fDDL >= AliHLTMUONHitReconstructor::GetkDDLOffSet() + AliHLTMUONHitReconstructor::GetkNofDDL()){
- HLTError("DDL number is out of range");
- return false;
- }
-
- int lutLine = fHitRec->GetLutLine(fDDL);
-
- FILE* fin = fopen(lutpath, "r");
- if (fin == NULL){
- HLTError("Failed to open file: %s",lutpath);
- return false;
- }
-
- for(int i=0;i<lutLine;i++){
- fscanf(
- fin,
- "%d\t%d\t%d\t%f\t%f\t%f\t%d\t%d\n",
- &lookupTable[i].fIdManuChannel,
- &lookupTable[i].fIX,
- &lookupTable[i].fIY,
- &lookupTable[i].fRealX,
- &lookupTable[i].fRealY,
- &lookupTable[i].fRealZ,
- &lookupTable[i].fPcbZone,
- &lookupTable[i].fPlane
- );
- }
-
- fclose(fin);
- return true;
+ // Initialise the sentinel value.
+ fLut[0].fDetElemId = 0;
+ fLut[0].fIX = 0;
+ fLut[0].fIY = 0;
+ fLut[0].fRealX = 0.0;
+ fLut[0].fRealY = 0.0;
+ fLut[0].fRealZ = 0.0;
+ fLut[0].fHalfPadSize = 0.0;
+ fLut[0].fPlane = -1;
+ fLut[0].fPed = -1;
+ fLut[0].fSigma = -1;
+ fLut[0].fA0 = -1;
+ fLut[0].fA1 = -1;
+ fLut[0].fThres = -1;
+ fLut[0].fSat = -1;
+
+ // Clear the eof flag and start reading from the beginning of the file again.
+ file.clear();
+ file.seekg(0, std::ios::beg);
+ if (not file.good())
+ {
+ HLTError("There was a problem seeking in the LUT file %s", lutFileName);
+ return -EIO;
+ }
+
+ AliHLTInt32_t idManuChannel;
+ for (AliHLTUInt32_t i = 1; i < fLutSize; i++)
+ {
+ if (std::getline(file, str).fail())
+ {
+ HLTError("There was a problem reading line %d of LUT file %s", i, lutFileName);
+ return -EIO;
+ }
+
+ int result = sscanf(
+ str.c_str(), "%d\t%d\t%d\t%d\t%e\t%e\t%e\t%e\t%d\t%e\t%e\t%e\t%e\t%d\t%d",
+ &idManuChannel, &fLut[i].fDetElemId, &fLut[i].fIX,
+ &fLut[i].fIY, &fLut[i].fRealX,
+ &fLut[i].fRealY, &fLut[i].fRealZ,
+ &fLut[i].fHalfPadSize, &fLut[i].fPlane,
+ &fLut[i].fPed, &fLut[i].fSigma, &fLut[i].fA0,
+ &fLut[i].fA1, &fLut[i].fThres, &fLut[i].fSat
+ );
+
+ if (result != 15)
+ {
+ HLTError("Line %d in LUT file %s does not contain 15 elements.", i, lutFileName);
+ return -EIO;
+ }
+
+ fIdToEntry[idManuChannel] = i;
+ }
+
+ return 0;
}
-bool AliHLTMUONHitReconstructorComponent::ReadBusPatchToDetElemFile(BusToDetElem& busToDetElem, BusToDDL& busToDDL, const char* buspatchmappath)
+int AliHLTMUONHitReconstructorComponent::ReadCDB(const char* cdbPath, Int_t run)
{
- ///
- /// Read in the lookup table for bus patch to detector element IDs from a text file.
- ///
+ // Reads LUT from CDB.
+ // TODO: merge this with CreateHitRecoLookupTables.C, make this static and use in the macro for example.
+
+ assert( fLut == NULL );
+ assert( fLutSize == 0 );
+ assert( fIdToEntry.empty() );
+
+ std::vector<AliHLTMUONHitRecoLutRow> lutList;
+ AliHLTMUONHitRecoLutRow lut;
+ AliHLTUInt32_t iEntry = 0;
+
+ Bool_t warn = kFALSE;
+
+ AliCDBManager* cdbManager = AliCDBManager::Instance();
+ if (cdbManager == NULL)
+ {
+ HLTError("CDB manager instance does not exist.");
+ return -EIO;
+ }
+
+ const char* cdbPathUsed = "unknown (not set)";
+ if (cdbPath != NULL)
+ {
+ cdbManager->SetDefaultStorage(cdbPath);
+ cdbPathUsed = cdbPath;
+ }
+ else
+ {
+ AliCDBStorage* store = cdbManager->GetDefaultStorage();
+ if (store != NULL) cdbPathUsed = store->GetURI().Data();
+ }
+
+ if (run != -1) cdbManager->SetRun(run);
+ Int_t runUsed = cdbManager->GetRun();
+
+ if (not AliMpCDB::LoadDDLStore(warn))
+ {
+ HLTError("Failed to load DDL store specified for CDB path '%s' and run no. %d",
+ cdbPathUsed, runUsed
+ );
+ return -ENOENT;
+ }
+ AliMpDDLStore* ddlStore = AliMpDDLStore::Instance();
+ if (ddlStore == NULL)
+ {
+ HLTError("Could not find DDL store instance.");
+ return -EIO;
+ }
+ AliMpSegmentation* mpSegFactory = AliMpSegmentation::Instance();
+ if (mpSegFactory == NULL)
+ {
+ HLTError("Could not find segmentation mapping (AliMpSegmentation) instance.");
+ return -EIO;
+ }
+
+ AliGeomManager::LoadGeometry();
+ AliMUONGeometryTransformer chamberGeometryTransformer;
+ if (not chamberGeometryTransformer.LoadGeometryData())
+ {
+ HLTError("Failed to load geomerty data.");
+ return -ENOENT;
+ }
+
+ AliMUONCalibrationData calibData(run);
+
+ Int_t chamberId;
+
+ for(Int_t iCh = 6; iCh < 10; iCh++)
+ {
+ chamberId = iCh;
+
+ AliMpDEIterator it;
+ for ( it.First(chamberId); ! it.IsDone(); it.Next() )
+ {
+ Int_t detElemId = it.CurrentDEId();
+ int iDDL = ddlStore->GetDetElement(detElemId)->GetDdlId();
+ if (iDDL != fDDL) continue;
+
+ for (Int_t iCath = 0 ; iCath <= 1 ; iCath++)
+ {
+ AliMp::CathodType cath;
+
+ if(iCath == 0)
+ cath = AliMp::kCath0;
+ else
+ cath = AliMp::kCath1;
+
+ const AliMpVSegmentation* seg = mpSegFactory->GetMpSegmentation(detElemId, cath);
+ AliMp::PlaneType plane = seg->PlaneType();
+ Int_t maxIX = seg->MaxPadIndexX();
+ Int_t maxIY = seg->MaxPadIndexY();
+
+ Int_t idManuChannel, manuId, channelId, buspatchId;
+ AliHLTFloat32_t padSizeX, padSizeY;
+ AliHLTFloat32_t halfPadSize;
+ Double_t realX, realY, realZ;
+ Double_t localX, localY, localZ;
+ Float_t calibA0Coeff,calibA1Coeff,pedestal,sigma;
+ Int_t thresold,saturation;
+
+ // Pad Info of a slat to print in lookuptable
+ for (Int_t iX = 0; iX<= maxIX ; iX++)
+ for (Int_t iY = 0; iY<= maxIY ; iY++)
+ {
+ if (not seg->HasPad(AliMpIntPair(iX,iY))) continue;
+
+ AliMpPad pad = seg->PadByIndices(AliMpIntPair(iX,iY), kFALSE);
+
+ // Getting Manu id
+ manuId = pad.GetLocation().GetFirst();
+ manuId &= 0x7FF; // 11 bits
+
+ buspatchId = ddlStore->GetBusPatchId(detElemId,manuId);
+
+ // Getting channel id
+ channelId = pad.GetLocation().GetSecond();
+ channelId &= 0x3F; // 6 bits
+
+ idManuChannel = buspatchId << 11;
+ idManuChannel = (idManuChannel | manuId) << 6;
+ idManuChannel |= channelId;
+
+ localX = pad.Position().X();
+ localY = pad.Position().Y();
+ localZ = 0.0;
+
+ chamberGeometryTransformer.Local2Global(
+ detElemId,localX,localY,localZ,
+ realX,realY,realZ
+ );
+
+ padSizeX = pad.Dimensions().X();
+ padSizeY = pad.Dimensions().Y();
+
+ calibA0Coeff = (calibData.Gains(detElemId, manuId))->ValueAsFloat(channelId, 0);
+ calibA1Coeff = (calibData.Gains(detElemId, manuId))->ValueAsFloat(channelId, 1);
+ thresold = (calibData.Gains(detElemId, manuId))->ValueAsInt(channelId, 2);
+ saturation = (calibData.Gains(detElemId, manuId))->ValueAsInt(channelId, 4);
+
+ pedestal = (calibData.Pedestals(detElemId, manuId))->ValueAsFloat(channelId, 0);
+ sigma = (calibData.Pedestals(detElemId, manuId))->ValueAsFloat(channelId, 1);
+
+ if (plane == 0)
+ halfPadSize = padSizeX;
+ else
+ halfPadSize = padSizeY;
+
+ fIdToEntry[idManuChannel] = iEntry+1;
+
+ lut.fDetElemId = detElemId;
+ lut.fIX = iX;
+ lut.fIY = iY;
+ lut.fRealX = realX;
+ lut.fRealY = realY;
+ lut.fRealZ = realZ;
+ lut.fHalfPadSize = halfPadSize;
+ lut.fPlane = plane;
+ lut.fPed = pedestal;
+ lut.fSigma = sigma;
+ lut.fA0 = calibA0Coeff;
+ lut.fA1 = calibA1Coeff;
+ lut.fThres = thresold;
+ lut.fSat = saturation;
+
+ lutList.push_back(lut);
+ iEntry++;
+ } // iX, iY loop
+ } // iCath loop
+ } // detElemId loop
+ } // ichamber loop
+
+ try
+ {
+ // Use iEntry+1 since we add one extra LUT line for the first element
+ // which is used as a sentinel value.
+ fLut = new AliHLTMUONHitRecoLutRow[iEntry+1];
+ fLutSize = iEntry+1;
+ }
+ catch (const std::bad_alloc&)
+ {
+ HLTError("Could not allocate more memory for the lookuptable.");
+ return -ENOMEM;
+ }
+
+ // Initialise the sentinel value.
+ fLut[0].fDetElemId = 0;
+ fLut[0].fIX = 0;
+ fLut[0].fIY = 0;
+ fLut[0].fRealX = 0.0;
+ fLut[0].fRealY = 0.0;
+ fLut[0].fRealZ = 0.0;
+ fLut[0].fHalfPadSize = 0.0;
+ fLut[0].fPlane = -1;
+ fLut[0].fPed = -1;
+ fLut[0].fSigma = -1;
+ fLut[0].fA0 = -1;
+ fLut[0].fA1 = -1;
+ fLut[0].fThres = -1;
+ fLut[0].fSat = -1;
+
+ for (AliHLTUInt32_t i = 0; i < iEntry; i++)
+ fLut[i+1] = lutList[i];
+
+ return 0;
+}
+
+
+bool AliHLTMUONHitReconstructorComponent::GenerateLookupTable(
+ AliHLTInt32_t ddl, const char* filename,
+ const char* cdbPath, Int_t run
+ )
+{
+ /// Generates a ASCII text file containing the lookup table (LUT) from
+ /// the CDB, which can be used for the hit reconstructor component later.
+ /// @param ddl Must be the DDL for which to generate the DDL,
+ /// in the range [13..20].
+ /// @param filename The name of the LUT file to generate.
+ /// @param cdbPath The CDB path to use.
+ /// @param run The run number to use for the CDB.
+ /// @return True if the generation of the LUT file succeeded.
+
+ AliHLTMUONHitReconstructorComponent comp;
+
+ if (ddl < 12 or 19 < ddl)
+ {
+ std::cerr << "ERROR: the DDL number must be in the range [12..19]." << std::endl;
+ return false;
+ }
+
+ comp.fDDL = ddl;
+ if (comp.ReadCDB(cdbPath, run) != 0) return false;
+
+ char str[1024*4];
+ std::fstream file(filename, std::ios::out);
+ if (not file)
+ {
+ std::cerr << "ERROR: could not open file: " << filename << std::endl;
+ return false;
+ }
+
+ assert( comp.fLut != NULL );
+
+ for (IdManuChannelToEntry::iterator id = comp.fIdToEntry.begin();
+ id != comp.fIdToEntry.end();
+ id++
+ )
+ {
+ AliHLTInt32_t idManuChannel = id->first;
+ AliHLTInt32_t row = id->second;
+
+ assert( row < comp.fLutSize );
+
+ sprintf(str, "%d\t%d\t%d\t%d\t%.15e\t%.15e\t%.15e\t%.15e\t%d\t%.15e\t%.15e\t%.15e\t%.15e\t%d\t%d",
+ idManuChannel, comp.fLut[row].fDetElemId, comp.fLut[row].fIX,
+ comp.fLut[row].fIY, comp.fLut[row].fRealX,
+ comp.fLut[row].fRealY, comp.fLut[row].fRealZ,
+ comp.fLut[row].fHalfPadSize, comp.fLut[row].fPlane,
+ comp.fLut[row].fPed, comp.fLut[row].fSigma, comp.fLut[row].fA0,
+ comp.fLut[row].fA1, comp.fLut[row].fThres, comp.fLut[row].fSat
+ );
+
+ file << str << endl;
+ if (file.fail())
+ {
+ std::cerr << "ERROR: There was an I/O error when writing to the file: "
+ << filename << std::endl;
+ return false;
+ }
+ }
- char getLine[80];
- char temp;
- int detElem, minBusPatch, maxBusPatch, ddl;
-
- FILE* fin = fopen(buspatchmappath, "r");
- if (fin == NULL){
- HLTError("Failed to open file: %s",buspatchmappath);
- return false;
- }
-
- while (feof(fin)==0){
- fgets(getLine,80,fin);
- sscanf(getLine, "%d\t%d %c %d\t%d", &detElem, &minBusPatch, &temp, &maxBusPatch,&ddl);
- if (detElem >= 700 && detElem <= 1025){
-
- for(int i = minBusPatch; i <= maxBusPatch; i++){
- busToDetElem[i] = detElem;
- busToDDL[i] = ddl;
- }//for loop
- } // detElem condn
- } // while loop for file
-
- fclose(fin);
- return true;
+ return true;
}