X-Git-Url: http://git.uio.no/git/?a=blobdiff_plain;ds=sidebyside;f=TRD%2FAliTRDrawData.cxx;h=81fcf7f2f17c9f7c693705e314ab1468709f4154;hb=089086d30be8b3ee9f676b0e70b066b7cc045783;hp=1a3e9df7f25728b406c544b72a7baf237c9ed04e;hpb=88cb7938ca21d4a80991d4e7aa564008c29340f7;p=u%2Fmrichter%2FAliRoot.git diff --git a/TRD/AliTRDrawData.cxx b/TRD/AliTRDrawData.cxx index 1a3e9df7f25..81fcf7f2f17 100644 --- a/TRD/AliTRDrawData.cxx +++ b/TRD/AliTRDrawData.cxx @@ -21,34 +21,84 @@ // // /////////////////////////////////////////////////////////////////////////////// -#include + +#include +#include "TClass.h" + +#include "AliDAQ.h" +#include "AliRawDataHeaderSim.h" +#include "AliRawReader.h" +#include "AliLog.h" +#include "AliFstream.h" +#include "AliLoader.h" +#include "AliTreeLoader.h" #include "AliTRDrawData.h" #include "AliTRDdigitsManager.h" -#include "AliTRDgeometryFull.h" -#include "AliTRDparameter.h" -#include "AliTRDdataArrayI.h" -#include "AliTRDarrayI.h" +#include "AliTRDgeometry.h" +#include "AliTRDarrayDictionary.h" +#include "AliTRDarrayADC.h" +#include "AliTRDrawStream.h" +#include "AliTRDcalibDB.h" +#include "AliTRDSignalIndex.h" +#include "AliTRDfeeParam.h" +#include "AliTRDmcmSim.h" +#include "AliTRDtrackletWord.h" +#include "AliTRDdigitsParam.h" ClassImp(AliTRDrawData) +Int_t AliTRDrawData::fgDataSuppressionLevel = 0; + //_____________________________________________________________________________ -AliTRDrawData::AliTRDrawData():TObject() +AliTRDrawData::AliTRDrawData() + :TObject() + ,fRunLoader(NULL) + ,fGeo(NULL) + ,fFee(NULL) + ,fNumberOfDDLs(0) + ,fTrackletTree(NULL) + ,fTracklets(NULL) + ,fTracks(NULL) + ,fSMindexPos(0) + ,fStackindexPos(0) + ,fEventCounter(0) + ,fTrgFlags() + ,fMcmSim(new AliTRDmcmSim) + ,fDigitsParam(NULL) { + // + // Default constructor + // - fDebug = 0; - fDigitsManager = NULL; + fFee = AliTRDfeeParam::Instance(); + fNumberOfDDLs = AliDAQ::NumberOfDdls("TRD"); } //_____________________________________________________________________________ AliTRDrawData::AliTRDrawData(const AliTRDrawData &r) + :TObject(r) + ,fRunLoader(NULL) + ,fGeo(NULL) + ,fFee(NULL) + ,fNumberOfDDLs(0) + ,fTrackletTree(NULL) + ,fTracklets(NULL) + ,fTracks(NULL) + ,fSMindexPos(0) + ,fStackindexPos(0) + ,fEventCounter(0) + ,fTrgFlags() + ,fMcmSim(new AliTRDmcmSim) + ,fDigitsParam(NULL) { // - // AliTRDrawData copy constructor + // Copy constructor // - ((AliTRDrawData &) r).Copy(*this); + fFee = AliTRDfeeParam::Instance(); + fNumberOfDDLs = AliDAQ::NumberOfDdls("TRD"); } @@ -59,487 +109,582 @@ AliTRDrawData::~AliTRDrawData() // Destructor // - if (fDigitsManager) { - delete fDigitsManager; - fDigitsManager = NULL; + if (fTracklets){ + fTracklets->Delete(); + delete fTracklets; } -} - -//_____________________________________________________________________________ -AliTRDrawData &AliTRDrawData::operator=(const AliTRDrawData &r) -{ - // - // Assignment operator - // - - if (this != &r) ((AliTRDrawData &) r).Copy(*this); - return *this; - -} - -//_____________________________________________________________________________ -void AliTRDrawData::Copy(TObject &r) -{ - // - // Copy function - // - - ((AliTRDrawData &) r).fDebug = fDebug; - ((AliTRDrawData &) r).fDigitsManager = NULL; - -} - -//_____________________________________________________________________________ -Bool_t AliTRDrawData::OpenInput(const Char_t *name) -{ - // - // Opens a ROOT-file with the TRD digits - // - - // Create the digits manager - if (fDigitsManager) { - delete fDigitsManager; + if (fTracks){ + fTracks->Delete(); + delete fTracks; } - fDigitsManager = new AliTRDdigitsManager(); - fDigitsManager->SetDebug(fDebug); - // Open the input file - return fDigitsManager->Open(name); + delete fMcmSim; } //_____________________________________________________________________________ -Bool_t AliTRDrawData::Digit2Raw(const Char_t *name1, const Char_t *name2) +Bool_t AliTRDrawData::Digits2Raw(TTree *digitsTree, const TTree *tracks ) { // - // Convert the digits to raw data byte stream. The output is written - // into the the binary files and . + // Initialize necessary parameters and call one + // of the raw data simulator selected by SetRawVersion. // - // The pseudo raw data format is currently defined like this: + // Currently tracklet output is not spported yet and it + // will be supported in higher version simulator. // - // LDC header (8 bytes) - // FLAG - // LDC no. - // Number of detectors with data (not yet implemented) - // 5 empty bytes - // - // Subevent (= single chamber) header (8 bytes) - // FLAG - // Detector number (2 bytes) - // Number of data bytes (2 bytes) - // Number of pads with data (2 bytes) - // 1 empty byte - // - // Data bank - // - - const Int_t kLDCHeaderLength = 8; - const Int_t kSubeventHeaderLength = 8; - const Int_t kLDCDummyFlag = 0xAA; - const Int_t kSubeventDummyFlag = 0xBB; + AliTRDdigitsManager* const digitsManager = new AliTRDdigitsManager(); - int headerLDC[2]; - int headerSubevent[2]; - - Int_t ntotalbyte[2] = { 0 }; - Int_t nbyte = 0; - Int_t npads = 0; - unsigned char *byte_p; - unsigned char *header_p; - - AliTRDgeometryFull *geo = new AliTRDgeometryFull(); - AliTRDparameter *par = new AliTRDparameter("TRDparameter" - ,"TRD parameter class"); - AliTRDdataArrayI *digits; - - if (fDebug) { - Info("Digit2Raw","Open the LDC output files %s, %s" - ,name1,name2); - } - ofstream *outputFile1 = new ofstream(name1, ios::out | ios::binary); - ofstream *outputFile2 = new ofstream(name2, ios::out | ios::binary); - ofstream *outputFile; - - if (!fDigitsManager) { - Error("Digit2Raw","No input file open\n"); + if (!digitsManager->ReadDigits(digitsTree)) { + delete digitsManager; return kFALSE; } - // Read in the digit arrays - if (!fDigitsManager->ReadDigits()) { + if (tracks != NULL) { + delete digitsManager; + AliError("Tracklet input is not supported yet."); return kFALSE; } - // Count the number of chambers with data - Int_t ndetLDC0 = 0; - Int_t ndetLDC1 = 0; + fGeo = new AliTRDgeometry(); - if (fDebug > 1) { - Info("Digit2Raw","Write the LDC headers"); + if (!AliTRDcalibDB::Instance()) { + AliError("Could not get calibration object"); + delete fGeo; + delete digitsManager; + return kFALSE; } - // Write the LDC header 1 - byte_p = (unsigned char *) headerLDC; - header_p = byte_p; - *byte_p++ = kLDCDummyFlag; - *byte_p++ = 1; - *byte_p++ = ndetLDC0; - *byte_p++ = 0; - *byte_p++ = 0; - *byte_p++ = 0; - *byte_p++ = 0; - *byte_p++ = 0; - outputFile1->write(header_p,kLDCHeaderLength); - ntotalbyte[0] += kLDCHeaderLength; - - if (fDebug > 1) { - Info("Digit2Raw","LDC header 0 = %d, %d",headerLDC[0],headerLDC[1]); - } + Int_t retval = kTRUE; + Int_t rv = fFee->GetRAWversion(); - // Write the LDC header 1 - byte_p = (unsigned char *) headerLDC; - header_p = byte_p; - *byte_p++ = kLDCDummyFlag; - *byte_p++ = 2; - *byte_p++ = ndetLDC1; - *byte_p++ = 0; - *byte_p++ = 0; - *byte_p++ = 0; - *byte_p++ = 0; - *byte_p++ = 0; - outputFile2->write(header_p,kLDCHeaderLength); - ntotalbyte[1] += kLDCHeaderLength; - - if (fDebug > 1) { - Info("Digit2Raw","LDC header 1 = %d, %d",headerLDC[0],headerLDC[1]); + // Call appropriate Raw Simulator + if ( rv > 0 && rv <= 3 ) retval = Digits2Raw(digitsManager); + else { + retval = kFALSE; + AliWarning(Form("Unsupported raw version (%d).", rv)); } - // Loop through all detectors - for (Int_t det = 0; det < AliTRDgeometry::Ndet(); det++) { - - Int_t cham = geo->GetChamber(det); - Int_t plan = geo->GetPlane(det); - Int_t sect = geo->GetSector(det); - Int_t rowMax = par->GetRowMax(plan,cham,sect); - Int_t colMax = par->GetColMax(plan); - Int_t timeMax = par->GetTimeMax(); - Int_t bufferMax = rowMax*colMax*timeMax; - int *buffer = new int[bufferMax]; - - npads = 0; - nbyte = 0; - byte_p = (unsigned char *) buffer; - - // Determine the LDC (resp. output file) - Int_t ldc; - if (sect < 9) { - outputFile = outputFile1; - ldc = 0; - } - else { - outputFile = outputFile2; - ldc = 1; - } - - // Get the digits array - digits = fDigitsManager->GetDigits(det); - digits->Expand(); - - // Loop through the detector pixel - for (Int_t col = 0; col < colMax; col++) { - for (Int_t row = 0; row < rowMax; row++) { - - // Check whether data exists for this pad - Bool_t dataflag = kFALSE; - for (Int_t time = 0; time < timeMax; time++) { - Int_t data = digits->GetDataUnchecked(row,col,time); - if (data) { - dataflag = kTRUE; - break; - } - } - - if (dataflag) { - - npads++; - - // The pad row number - *byte_p++ = row + 1; - // The pad column number - *byte_p++ = col + 1; - nbyte += 2; - - Int_t nzero = 0; - for (Int_t time = 0; time < timeMax; time++) { + // Cleanup + delete fGeo; + delete digitsManager; - Int_t data = digits->GetDataUnchecked(row,col,time); + return retval; - if (!data) { - nzero++; - if ((nzero == 256) || - (time == timeMax-1)) { - *byte_p++ = 0; - *byte_p++ = nzero-1; - nbyte += 2; - nzero = 0; - } - } - else { - if (nzero) { - *byte_p++ = 0; - *byte_p++ = nzero-1; - nbyte += 2; - nzero = 0; - } - // High byte (MSB always set) - *byte_p++ = ((data >> 8) | 128); - // Low byte - *byte_p++ = (data & 0xff); - nbyte += 2; - } - - } +} - } +//_____________________________________________________________________________ +Bool_t AliTRDrawData::Digits2Raw(AliTRDdigitsManager *digitsManager) +{ + // + // Raw data simulator for all versions > 0. This is prepared for real data. + // This version simulate only raw data with ADC data and not with tracklet. + // + const Int_t kMaxHcWords = (fGeo->TBmax()/3) + * fGeo->ADCmax() + * fGeo->MCMmax() + * fGeo->ROBmaxC1()/2 + + 100 + 20; + + // Buffer to temporary store half chamber data + UInt_t *hcBuffer = new UInt_t[kMaxHcWords]; + + Bool_t newEvent = kFALSE; // only for correct readout tree + Bool_t newSM = kFALSE; // new SM flag, for writing SM index words + Bool_t newStack = kFALSE; // new stack flag, for writing stack index words + + // Get digits parameter + fDigitsParam = digitsManager->GetDigitsParam(); + + // sect is same as iDDL, so I use only sect here. + for (Int_t sect = 0; sect < fGeo->Nsector(); sect++) { + + char name[1024]; + snprintf(name,1024,"TRD_%d.ddl",sect + AliTRDrawStream::kDDLOffset); + + AliFstream* of = new AliFstream(name); + + // Write a dummy data header + AliRawDataHeaderSim header; // the event header + UInt_t hpos = of->Tellp(); + of->WriteBuffer((char *) (& header), sizeof(header)); + + // Reset payload byte size (payload does not include header). + Int_t npayloadbyte = 0; + + // check the existance of the data + // SM index word and Stack index word + UInt_t *iwbuffer = new UInt_t[109]; // index word buffer; max 109 = 2 SM headers + 67 dummy headers + 5*8 stack headers + Int_t nheader = 0; + UInt_t bStackMask = 0x0; + Bool_t bStackHasData = kFALSE; + Bool_t bSMHasData = kFALSE; + + //iwbuffer[nheader++] = 0x0001a020; // SM index words + iwbuffer[nheader++] = 0x0044b020; // SM index words | additional SM header:48 = 1 SM header + 47 dummy words(for future use) + iwbuffer[nheader++] = 0x10404071; // SM header + for ( Int_t i=0; i<66; i++ ) iwbuffer[nheader++] = 0x00000000; // dummy words + iwbuffer[nheader++] = 0x10000000; // end of dummy words + + for ( Int_t stack= 0; stack < fGeo->Nstack(); stack++) { + UInt_t linkMask = 0x0; + for( Int_t layer = 0; layer < fGeo->Nlayer(); layer++) { + Int_t iDet = fGeo->GetDetector(layer,stack,sect); + AliTRDarrayADC *digits = (AliTRDarrayADC *) digitsManager->GetDigits(iDet); + if ( fgDataSuppressionLevel==0 || digits->HasData() ) { + bStackMask = bStackMask | ( 1 << stack ); // active stack mask for new stack + linkMask = linkMask | ( 3 << (2*layer) ); // 3 = 0011 + bStackHasData = kTRUE; + bSMHasData = kTRUE; + } // has data + } // loop over layer + + if ( fgDataSuppressionLevel==0 || bStackHasData ){ + iwbuffer[nheader++] = 0x0007a000 | linkMask; // stack index word + link masks + if (fgDataSuppressionLevel==0) iwbuffer[nheader-1] = 0x0007afff; // no suppression + iwbuffer[nheader++] = 0x04045b01; // stack header + for (Int_t i=0;i<6;i++) iwbuffer[nheader++] = 0x00000000; // 6 dummy words + bStackHasData = kFALSE; } - - } - - // Fill the end of the buffer with zeros - while (nbyte % 4) { - *byte_p++ = 0; - nbyte++; - } - - if (fDebug > 1) { - Info("Digit2Raw","LDC = %d, det = %d, nbyte = %d (%d)",ldc,det,nbyte,bufferMax); + } // loop over stack + + if ( fgDataSuppressionLevel==0 || bSMHasData ){ + iwbuffer[0] = iwbuffer[0] | bStackMask; // add stack masks to SM index word + if (fgDataSuppressionLevel==0) iwbuffer[0] = 0x0044b03f; // no suppression : all stacks are active + of->WriteBuffer((char *) iwbuffer, nheader*4); + AliDebug(11, Form("SM %d index word: %08x", sect, iwbuffer[0])); + AliDebug(11, Form("SM %d header: %08x", sect, iwbuffer[1])); } - - // Write the subevent header - byte_p = (unsigned char *) headerSubevent; - header_p = byte_p; - *byte_p++ = kSubeventDummyFlag; - *byte_p++ = (det & 0xff); - *byte_p++ = (det >> 8); - *byte_p++ = (nbyte & 0xff); - *byte_p++ = (nbyte >> 8); - *byte_p++ = (npads & 0xff); - *byte_p++ = (npads >> 8); - *byte_p++ = 0; - outputFile->write(header_p,kSubeventHeaderLength); - - // Write the buffer to the file - byte_p = (unsigned char *) buffer; - outputFile->write(byte_p,nbyte); - - ntotalbyte[ldc] += nbyte + kSubeventHeaderLength; - - delete buffer; - - } - - if (fDebug) { - Info("Digit2Raw","Total size: LDC0 = %d, LDC1 = %d",ntotalbyte[0],ntotalbyte[1]); - } - - outputFile1->close(); - outputFile2->close(); - - delete geo; - delete par; - delete outputFile1; - delete outputFile2; - + // end of SM & stack header ------------------------------------------------------------------------ + // ------------------------------------------------------------------------------------------------- + + // Prepare chamber data + for( Int_t stack = 0; stack < fGeo->Nstack(); stack++) { + for( Int_t layer = 0; layer < fGeo->Nlayer(); layer++) { + + Int_t iDet = fGeo->GetDetector(layer,stack,sect); + if (iDet == 0){ + newEvent = kTRUE; // it is expected that each event has at least one tracklet; + // this is only needed for correct readout tree + fEventCounter++; + AliDebug(11, Form("New event!! Event counter: %d",fEventCounter)); + } + + if ( stack==0 && layer==0 ) newSM = kTRUE; // new SM flag + if ( layer==0 ) newStack = kTRUE; // new stack flag + AliDebug(15, Form("stack : %d, layer : %d, iDec : %d\n",stack,layer,iDet)); + // Get the digits array + AliTRDarrayADC *digits = (AliTRDarrayADC *) digitsManager->GetDigits(iDet); + if (fgDataSuppressionLevel==0 || digits->HasData() ) { // second part is new!! and is for indicating a new event + + if (digits->HasData()) digits->Expand(); + + Int_t hcwords = 0; + + // Process A side of the chamber + hcwords = ProduceHcData(digits,0,iDet,hcBuffer,kMaxHcWords,newEvent,newSM); + if ( newEvent ) newEvent = kFALSE; + //AssignLinkMask(hcBuffer, layer); // active link mask for this layer(2*HC) + of->WriteBuffer((char *) hcBuffer, hcwords*4); + npayloadbyte += hcwords*4; + + // Process B side of the chamber + hcwords = ProduceHcData(digits,1,iDet,hcBuffer,kMaxHcWords,newEvent,newSM); + of->WriteBuffer((char *) hcBuffer, hcwords*4); + npayloadbyte += hcwords*4; + } // has data + + } // loop over layer + } // loop over stack + + // Complete header + header.fSize = UInt_t(of->Tellp()) - hpos; + header.SetAttribute(0); // Valid data + of->Seekp(hpos); // Rewind to header position + of->WriteBuffer((char *) (& header), sizeof(header)); + delete of; + + delete [] iwbuffer; + + } // loop over sector(SM) + + delete [] hcBuffer; + return kTRUE; - } //_____________________________________________________________________________ -Bool_t AliTRDrawData::Raw2Digit(const Char_t *name1, const Char_t *name2) -{ - - const Int_t kLDCHeaderLength = 8; - const Int_t kSubeventHeaderLength = 8; - - const Int_t kNldc = 2; - const Char_t *name = 0; +void AliTRDrawData::ProduceSMIndexData(UInt_t *buf, Int_t& nw){ + // + // This function generates + // 1) SM index words : ssssssss ssssssss vvvv rrrr r d t mmmmm + // - s : size of SM header (number of header, default = 0x0001) + // - v : SM header version (default = 0xa) + // - r : reserved for future use (default = 00000) + // - d : track data enabled bit (default = 0) + // - t : tracklet data enabled bit (default = 1) + // - m : stack mask (each bit corresponds a stack, default = 11111) + // + // 2) SM header : rrr c vvvv vvvvvvvv vvvv rrrr bbbbbbbb + // - r : reserved for future use (default = 000) + // - c : clean check out flag (default = 1) + // - v : hardware design revision (default = 0x0404) + // - r : reserved for future use (default = 0x0) + // - b : physical board ID (default = 0x71) + // + // 3) stack index words : ssssssss ssssssss vvvv mmmm mmmmmmmm + // - s : size of stack header (number of header, (default = 0x0007) + // - v : header version (default = 0xa) + // - m : link mask (default = 0xfff) + // + // 4) stack header : vvvvvvvv vvvvvvvv bbbbbbbb rrrr rrr c + // - v : hardware design revision (default = 0x0404) + // - b : physical board ID (default = 0x5b) + // - r : reserved for future use (default = 0000 000) + // - c : clean checkout flag (default = 1) + // + // and 6 dummy words(0x00000000) + // + + //buf[nw++] = 0x0001a03f; // SM index words + fSMindexPos = nw; // memorize position of the SM index word for re-allocating stack mask + buf[nw++] = 0x0001b020; // SM index words + buf[nw++] = 0x10404071; // SM header + + fStackindexPos = nw; // memorize position of the stack index word for future adding + /* + for (Int_t istack=0; istack<5; istack++){ + buf[nw++] = 0x0007afff; // stack index words + buf[nw++] = 0x04045b01; // stack header + for (Int_t i=0;i<6;i++) buf[nw++] = 0x00000000; // 6 dummy words + } // loop over 5 stacks + */ +} - int headerLDC[2]; - int headerSubevent[2]; +//_____________________________________________________________________________ +void AliTRDrawData::AssignStackMask(UInt_t *buf, Int_t nStack){ + // + // This function re-assign stack mask active(from 0 to 1) in the SM index word + // + buf[fSMindexPos] = buf[fSMindexPos] | ( 1 << nStack ); +} - Int_t npads = 0; - Int_t nbyte = 0; - unsigned char *byte_p; - ifstream *inputFile = 0; - AliTRDdataArrayI *digits = 0; +//_____________________________________________________________________________ +Int_t AliTRDrawData::AddStackIndexWords(UInt_t *buf, Int_t /*nStack*/, Int_t nMax){ + // + // This function add stack index words and stack header when there is data for the stack + // + // 1) stack index words : ssssssss ssssssss vvvv mmmm mmmmmmmm + // - s : size of stack header (number of header, (default = 0x0007) + // - v : header version (default = 0xa) + // - m : link mask (default = 0xfff) + // - m : link mask (starting value = 0x000) + // + // 2) stack header : vvvvvvvv vvvvvvvv bbbbbbbb rrrr rrr c + // - v : hardware design revision (default = 0x0404) + // - b : physical board ID (default = 0x5b) + // - r : reserved for future use (default = 0000 000) + // - c : clean checkout flag (default = 1) + // + // and 6 dummy words(0x00000000) + // + + Int_t nAddedWords = 0; // Number of added words + if ( ShiftWords(buf, fStackindexPos, 8, nMax)== kFALSE ){ + AliError("Adding stack header failed."); + return 0; + } - AliTRDgeometryFull *geo = new AliTRDgeometryFull(); - AliTRDparameter *par = new AliTRDparameter("TRDparameter" - ,"TRD parameter class"); + buf[fStackindexPos++] = 0x0007a000; // stack index words + buf[fStackindexPos++] = 0x04045b01; // stack header + for (Int_t i=0;i<6;i++) buf[fStackindexPos++] = 0x00000000; // 6 dummy words + nAddedWords += 8; - // Create the digits manager - if (fDigitsManager) { - delete fDigitsManager; - } - fDigitsManager = new AliTRDdigitsManager(); - fDigitsManager->SetDebug(fDebug); - fDigitsManager->CreateArrays(); + return nAddedWords; +} - for (Int_t ldc = 0; ldc < kNldc; ldc++) { +//_____________________________________________________________________________ +void AliTRDrawData::AssignLinkMask(UInt_t *buf, Int_t nLayer){ + // + // This function re-assign link mask active(from 0 to 1) in the stack index word + // + buf[fStackindexPos-8] = buf[fStackindexPos-8] | ( 3 << (2*nLayer) ); // 3 = 0011 +} - if (ldc == 0) { - name = name1; +//_____________________________________________________________________________ +Bool_t AliTRDrawData::ShiftWords(UInt_t *buf, Int_t nStart, Int_t nWords, Int_t nMax){ + // + // This function shifts n words + // + //if ( nStart+nWords > sizeof(buf)/sizeof(UInt_t) ){ + // AliError("Words shift failed. No more buffer space."); + // return kFALSE; + //} + + for ( Int_t iw=nMax; iw>nStart-1; iw--){ + buf[iw+nWords] = buf[iw]; } - else if (ldc == 1) { - name = name2; - } - if (fDebug) { - Info("Raw2Digit","Open the LDC input file %s",name); - } - inputFile = new ifstream(name, ios::in | ios::binary); - - // Read the LDC header - byte_p = (unsigned char *) headerLDC; - inputFile->read(byte_p,kLDCHeaderLength); - - if (fDebug > 1) { - Info("Raw2Digit","LDC header no. %d:",ldc); - Info("Raw2Digit","\tflag = %d",*byte_p++); - Info("Raw2Digit","\tldc no = %d",*byte_p++); - Info("Raw2Digit","\tndet = %d",*byte_p++); - Info("Raw2Digit","\tempty = %d",*byte_p++); - Info("Raw2Digit","\tempty = %d",*byte_p++); - Info("Raw2Digit","\tempty = %d",*byte_p++); - Info("Raw2Digit","\tempty = %d",*byte_p++); - Info("Raw2Digit","\tempty = %d",*byte_p++); - } - - // Loop through the subevents - byte_p = (unsigned char *) headerSubevent; - while (inputFile->read(byte_p,kSubeventHeaderLength)) { - - Int_t flag = *byte_p++; - Int_t detl = *byte_p++; - Int_t deth = *byte_p++; - Int_t det = detl + (deth << 8); - Int_t nbytel = *byte_p++; - Int_t nbyteh = *byte_p++; - nbyte = nbytel + (nbyteh << 8); - Int_t npadsl = *byte_p++; - Int_t npadsh = *byte_p++; - npads = npadsl + (npadsh << 8); - if (fDebug > 2) { - Info("Raw2Digit","Subevent header:"); - Info("Raw2Digit","\tflag = %d",flag); - Info("Raw2Digit","\tdet = %d",det); - Info("Raw2Digit","\tnbyte = %d",nbyte); - Info("Raw2Digit","\tnpads = %d",npads); - Info("Raw2Digit","\tempty = %d",*byte_p++); - } - - // Create the data buffer - Int_t cham = geo->GetChamber(det); - Int_t plan = geo->GetPlane(det); - Int_t sect = geo->GetSector(det); - Int_t rowMax = par->GetRowMax(plan,cham,sect); - Int_t colMax = par->GetColMax(plan); - Int_t timeMax = par->GetTimeMax(); - Int_t bufferMax = rowMax*colMax*timeMax; - int *buffer = new int[bufferMax]; - byte_p = (unsigned char *) buffer; - memset(buffer,0,bufferMax*sizeof(int)); - - // Add a container for the digits of this detector - digits = fDigitsManager->GetDigits(det); - // Allocate memory space for the digits buffer - if (digits->GetNtime() == 0) { - digits->Allocate(rowMax,colMax,timeMax); - } + return kTRUE; +} - // Read the data - inputFile->read(byte_p,nbyte); - - Int_t time; - Int_t nzero; - Int_t data; - Int_t low; - Int_t high; - Int_t signal; - - // Decompress the data - while (nbyte > 0) { - - // The pad row number - Int_t row = (*byte_p++) - 1; - // The pad column number - Int_t col = (*byte_p++) - 1; - nbyte -= 2; - - time = nzero = 0; - - while ((time < timeMax) && - (nbyte > 0)) { - - data = *byte_p++; - nbyte--; - - if (data) { - if (!nzero) { - // signal for given timebim - low = *byte_p++; - high = data & 127; - signal = low + (high << 8); - if ((row < 0) || (col < 0) || (time < 0) || - (row >= rowMax) || (col >= colMax) || (time >= timeMax)) { - Error("Raw2Digit" - ,"row=%d(%d) col=%d(%d) time=%d(%d)" - ,row,rowMax,col,colMax,time,timeMax); +//_____________________________________________________________________________ +Int_t AliTRDrawData::ProduceHcData(AliTRDarrayADC *digits, Int_t side, Int_t det, UInt_t *buf, Int_t maxSize, Bool_t /*newEvent = kFALSE*/, Bool_t /*newSM = kFALSE*/){ + // + // This function produces the raw data for one HC, i.e. tracklets, tracklet endmarkers, + // raw data, raw data endmarkers. + // This function can be used for both ZS and NZS data + // + + Int_t nw = 0; // Number of written words + Int_t of = 0; // Number of overflowed words + Int_t *tempnw = &nw; // Number of written words for temp. buffer + Int_t *tempof = &of; // Number of overflowed words for temp. buffer + Int_t layer = fGeo->GetLayer( det ); // Layer + Int_t stack = fGeo->GetStack( det ); // Stack + Int_t sect = fGeo->GetSector( det ); // Sector (=iDDL) + const Int_t kCtype = fGeo->GetStack(det) == 2 ? 0 : 1; // Chamber type (0:C0, 1:C1) + + Bool_t trackletOn = fFee->GetTracklet(); // tracklet simulation active? + + AliDebug(1,Form("Producing raw data for sect=%d layer=%d stack=%d side=%d",sect,layer,stack,side)); + + UInt_t *tempBuffer = buf; // tempBuffer used to write ADC data + // different in case of tracklet writing + + if (trackletOn) { + tempBuffer = new UInt_t[maxSize]; + tempnw = new Int_t(0); + tempof = new Int_t(0); + } + + WriteIntermediateWords(tempBuffer,*tempnw,*tempof,maxSize,det,side); + + if (digits->HasData()) { + // scanning direction such, that tracklet-words are sorted in ascending z and then in ascending y order + // ROB numbering on chamber and MCM numbering on ROB increase with decreasing z and increasing y + for (Int_t iRobRow = 0; iRobRow <= (kCtype + 3)-1; iRobRow++ ) { + // ROB number should be increasing + Int_t iRob = iRobRow * 2 + side; + // MCM on one ROB + for (Int_t iMcmRB = 0; iMcmRB < fGeo->MCMmax(); iMcmRB++ ) { + Int_t iMcm = 16 - 4*(iMcmRB/4 + 1) + (iMcmRB%4); + + fMcmSim->Init(det, iRob, iMcm); + fMcmSim->SetData(digits); // no filtering done here (already done in digitizer) + if (trackletOn) { + fMcmSim->Tracklet(); + Int_t tempNw = fMcmSim->ProduceTrackletStream(&buf[nw], maxSize - nw); + if( tempNw < 0 ) { + of += tempNw; + nw += maxSize - nw; + AliError(Form("Buffer overflow detected. Please increase the buffer size and recompile.")); + } else { + nw += tempNw; + } } - else { - digits->SetDataUnchecked(row,col,time,signal); + fMcmSim->ZSMapping(); // Calculate zero suppression mapping + // at the moment it has to be rerun here + // Write MCM data to temp. buffer + Int_t tempNw = fMcmSim->ProduceRawStream( &tempBuffer[*tempnw], maxSize - *tempnw, fEventCounter ); + if ( tempNw < 0 ) { + *tempof += tempNw; + *tempnw += maxSize - nw; + AliError(Form("Buffer overflow detected. Please increase the buffer size and recompile.")); + } else { + *tempnw += tempNw; } - nbyte--; - time++; - } - else { - time += data + 1; - nzero = 0; } } - else { - if (!nzero) { - nzero = 1; + + // in case of tracklet writing copy temp data to final buffer + if (trackletOn) { + if (nw + *tempnw < maxSize) { + memcpy(&buf[nw], tempBuffer, *tempnw * sizeof(UInt_t)); + nw += *tempnw; } - else { - time++; - nzero = 0; + else { + AliError("Buffer overflow detected"); } } + } + if (trackletOn) { + delete [] tempBuffer; + delete tempof; + delete tempnw; } + + // Write end of raw data marker + if (nw+3 < maxSize) { + buf[nw++] = fgkEndOfDataMarker; + buf[nw++] = fgkEndOfDataMarker; + buf[nw++] = fgkEndOfDataMarker; + buf[nw++] = fgkEndOfDataMarker; + } else { + of += 4; + } + + if (of != 0) { + AliError("Buffer overflow. Data is truncated. Please increase buffer size and recompile."); + } + + return nw; +} - } +//_____________________________________________________________________________ +AliTRDdigitsManager *AliTRDrawData::Raw2Digits(AliRawReader *rawReader) +{ + // + // Vx of the raw data reading + // - digits->Compress(1,0); + rawReader->Select("TRD"); //[mj] - delete buffer; + AliTRDarrayADC *digits = 0; + AliTRDarrayDictionary *track0 = 0; + AliTRDarrayDictionary *track1 = 0; + AliTRDarrayDictionary *track2 = 0; - byte_p = (unsigned char *) headerSubevent; + //AliTRDSignalIndex *indexes = 0; + // Create the digits manager + AliTRDdigitsManager* digitsManager = new AliTRDdigitsManager(); + digitsManager->CreateArrays(); + + AliTRDrawStream input(rawReader); - } + // ----- preparing tracklet output ----- + AliDataLoader *trklLoader = AliRunLoader::Instance()->GetLoader("TRDLoader")->GetDataLoader("tracklets"); + if (!trklLoader) { + trklLoader = new AliDataLoader("TRD.Tracklets.root","tracklets", "tracklets"); + AliRunLoader::Instance()->GetLoader("TRDLoader")->AddDataLoader(trklLoader); + } + if (!trklLoader) { + return 0x0; + } + AliTreeLoader *trklTreeLoader = dynamic_cast (trklLoader->GetBaseLoader("tracklets-raw")); + if (!trklTreeLoader) { + trklTreeLoader = new AliTreeLoader("tracklets-raw", trklLoader); + trklLoader->AddBaseLoader(trklTreeLoader); + } + if (!trklTreeLoader) { + return 0x0; + } - inputFile->close(); - delete inputFile; - inputFile = 0; + if (!trklTreeLoader->Tree()) + trklTreeLoader->MakeTree(); + + input.SetTrackletArray(TrackletsArray()); + input.SetTrackArray(TracksArray()); + + // Loop through the digits + Int_t det = 0; + + while (det >= 0) + { + det = input.NextChamber(digitsManager); + + if (det >= 0) + { + // get... + digits = (AliTRDarrayADC *) digitsManager->GetDigits(det); + track0 = (AliTRDarrayDictionary *) digitsManager->GetDictionary(det,0); + track1 = (AliTRDarrayDictionary *) digitsManager->GetDictionary(det,1); + track2 = (AliTRDarrayDictionary *) digitsManager->GetDictionary(det,2); + // and compress + if (digits) digits->Compress(); + if (track0) track0->Compress(); + if (track1) track1->Compress(); + if (track2) track2->Compress(); + } + } + for (Int_t iSector = 0; iSector < fGeo->Nsector(); iSector++) { + fTrgFlags[iSector] = input.GetTriggerFlags(iSector); } - delete geo; - delete par; + trklTreeLoader->WriteData("OVERWRITE"); + trklLoader->UnloadAll(); - return kTRUE; + return digitsManager; +} + +//_____________________________________________________________________________ +void AliTRDrawData::WriteIntermediateWords(UInt_t* buf, Int_t& nw, Int_t& of, const Int_t& maxSize, const Int_t& det, const Int_t& side) { + // + // write tracklet end marker(0x10001000) + // and half chamber headers(H[0] and H[1]) + // + + Int_t layer = fGeo->GetLayer( det ); // Layer + Int_t stack = fGeo->GetStack( det ); // Stack + Int_t sect = fGeo->GetSector( det ); // Sector (=iDDL) + Int_t rv = fFee->GetRAWversion(); + const Int_t kNTBin = fDigitsParam->GetNTimeBins(det); + Bool_t trackletOn = fFee->GetTracklet(); + UInt_t x = 0; + + // Write end of tracklet marker + if (nw < maxSize){ + buf[nw++] = fgkEndOfTrackletMarker; + buf[nw++] = fgkEndOfTrackletMarker; // the number of tracklet end marker should be more than 2 + } + else { + of++; + } + + // Half Chamber header + // h[0] (there are 2 HC headers) xmmm mmmm nnnn nnnq qqss sssp ppcc ci01 + // , where x : Raw version speacial number (=1) + // m : Raw version major number (test pattern, ZS, disable tracklet, 0, options) + // n : Raw version minor number + // q : number of addtional header words (default = 1) + // s : SM sector number (ALICE numbering) + // p : plane(layer) number + // c : chamber(stack) number + // i : side number (0:A, 1:B) + Int_t majorv = 0; // The major version number + Int_t minorv = 0; // The minor version number + Int_t add = 1; // The number of additional header words to follow : now 1, previous 2 + Int_t tp = 0; // test pattern (default=0) + Int_t zs = (rv==3) ? 1 : 0; // zero suppression + Int_t dt = (trackletOn) ? 0 : 1; // disable tracklet + + majorv = (tp<<6) | (zs<<5) | (dt<<4) | 1; // major version + + x = (1<<31) | (majorv<<24) | (minorv<<17) | (add<<14) | (sect<<9) | (layer<<6) | (stack<<3) | (side<<2) | 1; + if (nw < maxSize) buf[nw++] = x; else of++; + + // h[1] tttt ttbb bbbb bbbb bbbb bbpp pphh hh01 + // , where t : number of time bins + // b : bunch crossing number + // p : pretrigger counter + // h : pretrigger phase + Int_t bcCtr = 99; // bunch crossing counter. Here it is set to 99 always for no reason + Int_t ptCtr = 15; // pretrigger counter. Here it is set to 15 always for no reason + Int_t ptPhase = 11; // pretrigger phase. Here it is set to 11 always for no reason + //x = (bcCtr<<16) | (ptCtr<<12) | (ptPhase<<8) | ((kNTBin-1)<<2) | 1; // old format + x = ((kNTBin)<<26) | (bcCtr<<10) | (ptCtr<<6) | (ptPhase<<2) | 1; + if (nw < maxSize) buf[nw++] = x; else of++; +} +TClonesArray *AliTRDrawData::TrackletsArray() +{ + // Returns the array of on-line tracklets + + if (!fTracklets) { + fTracklets = new TClonesArray("AliTRDtrackletWord", 200); + } + return fTracklets; +} + +TClonesArray* AliTRDrawData::TracksArray() +{ + // return array of GTU tracks (create TClonesArray if necessary) + + if (!fTracks) { + fTracks = new TClonesArray("AliESDTrdTrack",100); + } + return fTracks; }