#ifndef ALIFMDDIGITIZER_H #define ALIFMDDIGITIZER_H /* Copyright(c) 1998-2000, ALICE Experiment at CERN, All rights * reserved. * * See cxx source for full Copyright notice */ #ifndef ALIDIGITIZER_H # include #endif #ifndef ALIRUNDIGITIZER_H # include #endif #ifndef ALIFMDEdepMAP_H # include "AliFMDEdepMap.h" #endif #ifndef __UTILITY__ # include #endif // #ifndef ROOT_TArrayF // # include // #endif //==================================================================== class TClonesArray; class AliFMD; class AliLoader; class AliRunLoader; class AliFMDDigit; //==================================================================== /** @class AliFMDBaseDigitizer AliFMDDigitizer.h @brief Base class for digitizers. This class contains the procedures simulation ADC signal for the Forward Multiplicity detector : Hits->Digits and Hits->SDigits Digits consists of - Detector # - Ring ID - Sector # - Strip # - ADC count in this channel Summable digits consists of - Detector # - Ring ID - Sector # - Strip # - Total energy deposited in the strip - ADC count in this channel As the Digits and SDigits have so much in common, the classes AliFMDDigitizer and AliFMDSDigitizer are implemented via a base class AliFMDBaseDigitizer. @verbatim +---------------------+ | AliFMDBaseDigitizer | +---------------------+ ^ | +----------+---------+ | | +-----------------+ +------------------+ | AliFMDDigitizer | | AliFMDSDigitizer | +-----------------+ +------------------+ @endverbatim These classes uses parameters fetched from the AliFMDParameters manager. The shaping function of the VA1 is generally given by @f[ f(x) = A(1 - \exp(-Bx)) @f] where A is the total charge collected in the pre-amp., and B is a paramter that depends on the shaping time of the VA1 circut. When simulating the shaping function of the VA1 pre-amp. chip, we have to take into account, that the shaping function depends on the previous value of read from the pre-amp. That results in the following algorithm: @code last = 0; for (i=0; i < n_pre_amp_charge; i++) { charge = GetCharge(i); if (last < charge) f(t) = (charge - last) * (1 - exp(-B * t)) + last else f(t) = (last - charge) * exp(-B * t) + charge) for (j=0; j < sample_rate; j++) adc[j] = f(i / (# samples)) last = charge } @endcode Here, the first loop is over all charges collected by the VA1 chip, and the @c sample_rate is how many times the ALTRO ADC samples each of the 128 charges from the pre-amp. The @c charge is the total charge @f$ Q@f$ collected by the VA1 pre-amplifier for a strip. @f$ Q@f$ is then given by @f[ Q = \frac{E}{e}\frac{S}{r} @f] where @f$ E@f$ is the total energy deposited in a silicon strip, @f$ R@f$ is the dynamic range of the VA1 pre-amp, @f$ e@f$ is the energy deposited by a single MIP, and @f$ S@f$ ALTRO channel size in each time step. The energy deposited per MIP is given by @f$ e = M \rho w @f$ where @f$ M@f$ is the universal number @f$ 1.664 \mbox{keV}\mbox{cm}^{2}\mbox{g}^{-1}@f$, @f$ \rho@f$ is the density of silicon, and @f$ w@f$ is the depth of the silicon sensor. The final ADC count is given by @f[ C' = C + P @f] where @f$ P@f$ is the (randomized) pedestal. This class uses the class template AliFMDEdepMap to make an internal cache of the energy deposted of the hits. The class template is instantasized as The first member of the values is the summed energy deposition in a given strip, while the second member of the values is the number of hits in a given strip. Using the second member, it's possible to do some checks on just how many times a strip got hit, and what kind of error we get in our reconstructed hits. Note, that this information is currently not written to the digits tree. I think a QA (Quality Assurance) digit tree is better suited for that task. However, the information is there to be used in the future. @ingroup FMD_sim */ class AliFMDBaseDigitizer : public AliDigitizer { public: /** CTOR */ AliFMDBaseDigitizer(); /** Normal CTOR @param manager Manager of digitization */ AliFMDBaseDigitizer(AliRunDigitizer * manager); /** Normal ctor @param name Name @param title Title */ AliFMDBaseDigitizer(const Char_t* name, const Char_t* title); /** DTOR */ virtual ~AliFMDBaseDigitizer(); /** Initialize */ virtual Bool_t Init(); /** The response shape of the VA1 shaping circuit is approximently given by @f[ f(x) = A(1 - \exp(-Bx)) @f] where @f$ A@f$ is the total charge collected by the pre-amp., and @f$ B@f$ is parameter that depends on the shaping time of the @b VA1 pre-amp. This member function sets the parameter @f$ B@f$ @param B */ void SetShapingTime(Float_t B=10) { fShapingTime = B; } /** @return Get the shaping time */ Float_t GetShapingTime() const { return fShapingTime; } protected: /** Sum energy deposited contributions from each hit in a cache @param fmd Pointer to detector */ virtual void SumContributions(AliFMD* fmd); /** For the stored energy contributions in the cache, convert the energy signal to ADC counts, and store the created digit in the digits array @param fmd Pointer to detector */ virtual void DigitizeHits(AliFMD* fmd) const; /** Convert the total energy deposited to a (set of) ADC count(s). See also the class description for more details. @param edep Total energy deposited in detector @param last Last charge collected in previous VA1 channnel @param detector Detector # @param ring Ring ID @param sector Sector # @param strip Strip # @param counts Array holding the counts on return */ virtual void ConvertToCount(Float_t edep, Float_t last, UShort_t detector, Char_t ring, UShort_t sector, UShort_t strip, TArrayI& counts) const; /** Make a pedestal @param detector Detector # @param ring Ring ID @param sector Sector # @param strip Strip # @return Pedestal value */ virtual UShort_t MakePedestal(UShort_t detector, Char_t ring, UShort_t sector, UShort_t strip) const; /** Add noise to each sample */ virtual void AddNoise(TArrayI&) const {} /** Add a digit to output */ virtual void AddDigit(AliFMD* /* fmd */, UShort_t /* detector */, Char_t /* ring */, UShort_t /* sector */, UShort_t /* strip */, Float_t /* edep */, UShort_t /* count1 */, Short_t /* count2 */, Short_t /* count3 */) const {} AliRunLoader* fRunLoader; //! Run loader AliFMDEdepMap fEdep; // Cache of Energy from hits Float_t fShapingTime; // Shaping profile parameter /** Copy CTOR @param o object to copy from */ AliFMDBaseDigitizer(const AliFMDBaseDigitizer& o) : AliDigitizer(o) {} /** Assignment operator @return Reference to this object */ AliFMDBaseDigitizer& operator=(const AliFMDBaseDigitizer&) { return *this; } ClassDef(AliFMDBaseDigitizer,2) // Base class for FMD digitizers }; //==================================================================== /** @class AliFMDDigitizer @brief Concrete digitizer to make digits from hits. See also AliFMDBaseDigitizer documentation. @ingroup FMD_sim */ class AliFMDDigitizer : public AliFMDBaseDigitizer { public: /** CTOR */ AliFMDDigitizer(); /** CTOR @param manager Manager of digitization */ AliFMDDigitizer(AliRunDigitizer * manager); /** DTOR */ virtual ~AliFMDDigitizer() {} /** Do everything @param option Not used */ virtual void Exec(Option_t* option=0); protected: /** Add a digit to output. @param fmd Pointer to detector object @param detector Detector # @param ring Ring ID @param sector Sector number @param strip Strip number @param edep Energy deposited (not used) @param count1 ADC count 1 @param count2 ADC count 2 (-1 if not used) @param count3 ADC count 3 (-1 if not used) */ virtual void AddDigit(AliFMD* fmd, UShort_t detector, Char_t ring, UShort_t sector, UShort_t strip, Float_t edep, UShort_t count1, Short_t count2, Short_t count3) const; /** MAke a pedestal @param detector Detector # @param ring Ring ID @param sector Sector number @param strip Strip number @return Random noise */ virtual UShort_t MakePedestal(UShort_t detector, Char_t ring, UShort_t sector, UShort_t strip) const; /** Check that digit data is consistent @param digit Digit @param nhits Number of hits @param counts ADC counts */ virtual void CheckDigit(AliFMDDigit* digit, UShort_t nhits, const TArrayI& counts); ClassDef(AliFMDDigitizer,1) // Make Digits from Hits }; //==================================================================== /** @class AliFMDSDigitizer AliFMDDigitizer.h @brief Concrete implementation to make summable digits. See also class documentation of AliFMDBaseDigitizer @ingroup FMD_sim */ class AliFMDSDigitizer : public AliFMDBaseDigitizer { public: /** CTOR */ AliFMDSDigitizer(); /** CTOR @param headerFile Where to write headings @param sdigFile Where to write digits. */ AliFMDSDigitizer(const Char_t* headerFile, const Char_t* sdigFile=""); /** DTOR */ virtual ~AliFMDSDigitizer(); /** Do it all @param option Not used */ virtual void Exec(Option_t* option=0); protected: /** Add a digit to output. @param fmd Pointer to detector object @param detector Detector # @param ring Ring ID @param sector Sector number @param strip Strip number @param edep Energy deposited (not used) @param count1 ADC count 1 @param count2 ADC count 2 (-1 if not used) @param count3 ADC count 3 (-1 if not used) */ virtual void AddDigit(AliFMD* fmd, UShort_t detector, Char_t ring, UShort_t sector, UShort_t strip, Float_t edep, UShort_t count1, Short_t count2, Short_t count3) const; ClassDef(AliFMDSDigitizer,0) // Make Summable Digits from Hits }; #endif //____________________________________________________________________ // // Local Variables: // mode: C++ // End: // // // EOF //