Fixed raw reading and writing. Problem was, that Cvetan had
authorcholm <cholm@f7af4fe6-9843-0410-8265-dc069ae4e863>
Thu, 7 Feb 2008 16:29:43 +0000 (16:29 +0000)
committercholm <cholm@f7af4fe6-9843-0410-8265-dc069ae4e863>
Thu, 7 Feb 2008 16:29:43 +0000 (16:29 +0000)
put the default to read raw data with 8x32bit common data
header and the variable size RCU trailer.   However, none
of the RCU firmware that we have available to us does this,
so all raw data that we would write could not be read by
AliAltroRawStreamer!

From Cvetans comments it seems that the TPC has some
RCU firmware that does write an 8x32bit common data
header and the RCU trailers - I guess someone is not
telling us the full story here - or the TPC is in
fact using some other piece of code to read the
data with!

In any case, I implemented code in AliFMDParameters to
set and get the mode for the raw reading.   Since
AliAltroBuffer _always_ writes the newer format (CDH of
8x32bit and RCU trailer) one should leave the defaults in
AliFMDParameters when reading simulated raw data.
However, when reading raw data from the real detectors, one
need to use the old format (7x32bit CDH and no RCU trailer),
which is done by doing

   AliFMDParameters* p = AliFMDParameters::Instance();
   p->UseRcuTrailer(false);
   p->UseCompleteHeader(false);

Also implemented code in AliFMDRawReader to correctly
skip the first 19 timebins (14 before the trigger, and
5 "extra" timebins from some funny stuff in the ALTROs).
Similarly, the AliFMDRawWriter will start the data in
timebin 19 (counting from 0).

FMD/AliFMDParameters.cxx
FMD/AliFMDParameters.h
FMD/AliFMDRawReader.cxx
FMD/AliFMDRawWriter.cxx
FMD/scripts/ReadRaw.C

index a0d5860..330eaab 100644 (file)
@@ -93,6 +93,8 @@ AliFMDParameters::AliFMDParameters()
     fFixedMaxStrip(0),
     fFixedPulseGain(0), 
     fEdepMip(0),
+    fHasRcuTrailer(kTRUE),
+    fHasCompleteHeader(kTRUE),
     fZeroSuppression(0), 
     fSampleRate(0), 
     fPedestal(0), 
index 84222a9..c763d24 100644 (file)
@@ -161,6 +161,14 @@ public:
       @param min Minimum strip number (0-127). 
       @param max Maximum strip number (0-127). */
   void SetStripRange(UShort_t min=0, UShort_t max=127);
+  /** Whether raw data is in the old ALTRO format (i.e., no RCU
+      trailer), or in the new format (with a trailer). 
+      @param yes if true the raw data has RCU trailer */ 
+  void UseRcuTrailer(Bool_t yes=kTRUE) { fHasRcuTrailer = yes; } 
+  /** Whether raw data has full common data header (8 32bit words) or
+      the older invalid format (7 32bit words with bogus entries)
+      @param yes if true the raw data has complete data header */ 
+  void UseCompleteHeader(Bool_t yes=kTRUE) { fHasCompleteHeader = yes; } 
   /** @} */
 
   /** @{ */
@@ -261,6 +269,16 @@ public:
                       Char_t ring, 
                       UShort_t sector, 
                       UShort_t strip) const;
+  /** Get the number of pre-samples in ALTRO channels
+      @param detector Detector # (1-3)
+      @param ring     Ring ID ('I' or 'O')
+      @param sector   Sector number (0-39)
+      @param strip    Strip number (0-511)
+      @return Maximum strip */
+  UShort_t GetPreSamples(UShort_t, 
+                        Char_t, 
+                        UShort_t, 
+                        UShort_t) const { return 14+5; }
   /** Translate hardware address to detector coordinates 
       @param ddl      DDL number 
       @param board    Board address
@@ -314,6 +332,15 @@ public:
       @return Get the map that translates hardware to detector
       coordinates */ 
   AliFMDAltroMapping* GetAltroMap() const;
+  /** Whether raw data is in the old ALTRO format (i.e., no RCU
+      trailer), or in the new format (with a trailer). 
+      @return false if the raw data has no RCU trailer */ 
+  Bool_t HasRcuTrailer() const { return fHasRcuTrailer; } 
+  /** Whether raw data has full common data header (8 32bit words) or
+      the older invalid format (7 32bit words with bogus entries)
+      @return false if the raw data has incomplete data header */ 
+  Bool_t HasCompleteHeader() const { return fHasCompleteHeader; } 
+
   /** @} */
 
   static const char* PulseGainPath()       { return fgkPulseGain; }
@@ -344,6 +371,8 @@ protected:
       fFixedMaxStrip(o.fFixedMaxStrip),
       fFixedPulseGain(o.fFixedPulseGain),
       fEdepMip(o.fEdepMip),
+      fHasRcuTrailer(o.fHasRcuTrailer),
+      fHasCompleteHeader(o.fHasCompleteHeader),
       fZeroSuppression(o.fZeroSuppression),
       fSampleRate(o.fSampleRate),
       fPedestal(o.fPedestal),
@@ -406,6 +435,8 @@ protected:
   UShort_t        fFixedMaxStrip;        // Maximum strip read-out 
   mutable Float_t fFixedPulseGain;       //! Gain (cached)
   mutable Float_t fEdepMip;              //! Cache of energy loss for a MIP
+  Bool_t          fHasRcuTrailer;        // if the raw data has RCU trailer
+  Bool_t          fHasCompleteHeader;    // raw data has incomplete data header
   
   AliFMDCalibZeroSuppression* fZeroSuppression; // Zero suppression from CDB
   AliFMDCalibSampleRate*      fSampleRate;      // Sample rate from CDB 
index 3d39c5d..227af2b 100644 (file)
@@ -111,10 +111,13 @@ AliFMDRawReader::ReadAdcs(TClonesArray* array)
   // Get sample rate 
   AliFMDParameters* pars = AliFMDParameters::Instance();
   AliFMDRawStream input(fReader);
+  AliFMDDebug(5, ("Setting old RCU format and 7 word headers"));
+  input.SetOldRCUFormat(!pars->HasRcuTrailer());
+  input.SetShortDataHeader(!pars->HasCompleteHeader());
 
   UShort_t stripMin = 0;
   UShort_t stripMax = 127;
-  UShort_t preSamp  = 0;
+  UShort_t preSamp  = 14+5;
   
   UInt_t ddl    = 0;
   UInt_t rate   = 0;
@@ -123,7 +126,9 @@ AliFMDRawReader::ReadAdcs(TClonesArray* array)
   // Data array is approx twice the size needed. 
   UShort_t data[2048];
 
-  while (input.ReadChannel(ddl, hwaddr, last, data)) {
+  Bool_t isGood = kTRUE;
+  while (isGood) {
+    isGood = input.ReadChannel(ddl, hwaddr, last, data);
 
     AliFMDDebug(5, ("Read channel 0x%x of size %d", hwaddr, last));
     UShort_t det, sec, str;
@@ -136,6 +141,7 @@ AliFMDRawReader::ReadAdcs(TClonesArray* array)
     rate     = pars->GetSampleRate(det, ring, sec, str);
     stripMin = pars->GetMinStrip(det, ring, sec, str);
     stripMax = pars->GetMaxStrip(det, ring, sec, str);
+    preSamp  = pars->GetPreSamples(det, ring, sec, str);
     AliFMDDebug(5, ("DDL 0x%04x, address 0x%03x maps to FMD%d%c[%2d,%3d]", 
                       ddl, hwaddr, det, ring, sec, str));
     
@@ -143,10 +149,15 @@ AliFMDRawReader::ReadAdcs(TClonesArray* array)
     for (size_t i = 0; i < last; i++) {
       if (i < preSamp) continue;
       Int_t    n      = array->GetEntriesFast();
-      UShort_t curStr = str + stripMin + i / rate;
+      Short_t  curStr = str + stripMin + (i-preSamp) / rate;
       if ((curStr-str) > stripMax) {
-       AliError(Form("Current strip is %d but DB says max is %d", 
-                     curStr, stripMax));
+       // AliInfo(Form("timebin %4d -> (%3d+%3d+(%4d-%d)/%d) -> %d", 
+       //              i, str, stripMin, i, preSamp, rate, curStr));
+       // AliError(Form("Current strip is %3d (0x%04x,0x%03x,%4d) "
+       //               "but DB says max is %3d (rate=%d)", 
+       //               curStr, ddl, hwaddr, i, str+stripMax, rate));
+       // Garbage timebins - ignore 
+       continue;
       }
       AliFMDDebug(5, ("making digit for FMD%d%c[%2d,%3d] from sample %4d", 
                       det, ring, sec, curStr, i));
index 9e8b487..55cf76d 100644 (file)
@@ -214,6 +214,8 @@ AliFMDRawWriter::WriteDigits(TClonesArray* digits)
                    det, ring, sector, strip));
       continue;
     }
+    preSamples = pars->GetPreSamples(det, ring, sector, strip);
+    
     AliFMDDebug(10, ("FMD%d%c[%2d,%3d]-> ddl: 0x%x addr: 0x%x", 
                    det, ring, sector, strip, ddl, addr));
     if (addr != prevaddr) {
index 612098c..05472c6 100644 (file)
@@ -7,17 +7,82 @@
     @brief Read raw data into a TClonesArray - for testing 
  */
 void
-ReadRaw()
+ReadRaw(const char* file=0, Int_t evno=0, bool old=false)
 {
+  TString        src(file ? file : "");
   AliCDBManager* cdb = AliCDBManager::Instance();
   cdb->SetRun(0);
   cdb->SetDefaultStorage("local://$ALICE_ROOT");
-  AliLog::SetModuleDebugLevel("FMD", 10);
+  AliLog::SetModuleDebugLevel("FMD", 1);
   AliFMDParameters::Instance()->Init();
-  AliRawReader* r = new AliRawReaderFile(0);
+  AliFMDParameters::Instance()->UseRcuTrailer(!old);
+  AliFMDParameters::Instance()->UseCompleteHeader(!old);
+  AliRawReader*                   r = 0;
+  if (src.IsNull())               {
+    std::cout << "Reading via AliRawReaderFile" << std::endl;
+    r = new AliRawReaderFile(0);
+  }
+  else if (src.EndsWith(".root")) { 
+    std::cout << "Reading via AliRawReaderRoot" << std::endl;
+    r = new AliRawReaderRoot(src.Data(), evno);
+  }
+  else if (src.EndsWith(".raw"))  {
+    std::cout << "Reading via AliRawReaderDate" << std::endl;
+    r = new AliRawReaderDate(src.Data());
+  }
+  else {
+    std::cerr << "Unknown raw type for source " << src 
+             << " assuming simulated raw files in directory " << src 
+             << std::endl;
+    r = new AliRawReaderFile(src);
+  }
   AliFMDRawReader* fr = new AliFMDRawReader(r, 0);
-  TClonesArray* a = new TClonesArray("AliFMDDigit");
+  TClonesArray*    a  = new TClonesArray("AliFMDDigit", 0);
   fr->ReadAdcs(a);
+
+  std::cout << "Read " << a->GetEntriesFast() << " digits" << std::endl;
+  
+  bool read[3][2][40][512];
+  for (UShort_t det = 0; det < 3; det++) {
+    for (UShort_t rng = 0; rng < 2; rng++) { 
+      for (UShort_t sec = 0; sec < 40; sec++) {
+       for (UShort_t str = 0; str < 512; str++) { 
+         read[det][rng][sec][str] = false;
+       }
+      }
+    }
+  }
+  
+
+  TIter next(a);
+  AliFMDDigit* d = 0;
+  while ((d = static_cast<AliFMDDigit*>(next()))) {
+    UShort_t det = d->Detector() - 1;
+    UShort_t rng = d->Ring() == 'I' ? 0 : 1;
+    UShort_t sec = d->Sector();
+    UShort_t str = d->Strip();
+    read[det][rng][sec][str] = true;
+  }
+  const UShort_t lineLength = 64;
+  for (UShort_t det = 0; det < 3; det++) {
+    for (UShort_t rng = 0; rng < 2; rng++) { 
+      if (det == 0 && rng == 1) continue;
+      Char_t   rid  = rng == 0 ? 'I' : 'O';
+      UShort_t nsec = rng == 0 ?  20 :  40;
+      UShort_t nstr = rng == 0 ? 512 : 256;
+      std::cout << "FMD" << det+1 << rid << ":" << std::endl;
+      for (UShort_t sec = 0; sec < nsec; sec++) {
+       std::cout << " Sector " << sec << "\n" << std::flush;
+       for (UShort_t str = 0; str < nstr; str++) { 
+         bool on = read[det][rng][sec][str];
+         if (str % lineLength == 0) std::cout << "  ";
+         std::cout << (on ? '+' : '-');
+         if (str % lineLength == lineLength-1) std::cout << "\n";
+       }
+      }
+    }
+  }
+  // a->ls();
 }
 //____________________________________________________________________
 //