Back to home page

Project CMSSW displayed by LXR

 
 

    


File indexing completed on 2024-04-06 12:02:39

0001 #include "CondFormats/SiStripObjects/interface/ApvTimingAnalysis.h"
0002 #include "DataFormats/SiStripCommon/interface/SiStripHistoTitle.h"
0003 #include "DataFormats/SiStripCommon/interface/SiStripEnumsAndStrings.h"
0004 #include "FWCore/MessageLogger/interface/MessageLogger.h"
0005 #include <iostream>
0006 #include <sstream>
0007 #include <iomanip>
0008 #include <cmath>
0009 
0010 using namespace sistrip;
0011 
0012 // ----------------------------------------------------------------------------
0013 //
0014 const float ApvTimingAnalysis::optimumSamplingPoint_ = 15.;  // [ns]
0015 
0016 // ----------------------------------------------------------------------------
0017 //
0018 const float ApvTimingAnalysis::tickMarkHeightThreshold_ = 50.;  // [ADC]
0019 
0020 // ----------------------------------------------------------------------------
0021 //
0022 const float ApvTimingAnalysis::frameFindingThreshold_ = (2. / 3.);  // fraction of tick mark height
0023 
0024 // ----------------------------------------------------------------------------
0025 //
0026 float ApvTimingAnalysis::refTime_ = 1. * sistrip::invalid_;
0027 
0028 // ----------------------------------------------------------------------------
0029 //
0030 ApvTimingAnalysis::ApvTimingAnalysis(const uint32_t& key)
0031     : CommissioningAnalysis(key, sistrip::apvTimingAnalysis_),
0032       time_(1. * sistrip::invalid_),
0033       error_(1. * sistrip::invalid_),
0034       delay_(1. * sistrip::invalid_),
0035       height_(1. * sistrip::invalid_),
0036       base_(1. * sistrip::invalid_),
0037       peak_(1. * sistrip::invalid_),
0038       synchronized_(false) {
0039   ;
0040 }
0041 
0042 // ----------------------------------------------------------------------------
0043 //
0044 ApvTimingAnalysis::ApvTimingAnalysis()
0045     : CommissioningAnalysis(sistrip::apvTimingAnalysis_),
0046       time_(1. * sistrip::invalid_),
0047       error_(1. * sistrip::invalid_),
0048       delay_(1. * sistrip::invalid_),
0049       height_(1. * sistrip::invalid_),
0050       base_(1. * sistrip::invalid_),
0051       peak_(1. * sistrip::invalid_),
0052       synchronized_(false) {
0053   ;
0054 }
0055 
0056 // ----------------------------------------------------------------------------
0057 //
0058 void ApvTimingAnalysis::reset() {
0059   time_ = 1. * sistrip::invalid_;
0060   error_ = 1. * sistrip::invalid_;
0061   delay_ = 1. * sistrip::invalid_;
0062   height_ = 1. * sistrip::invalid_;
0063   base_ = 1. * sistrip::invalid_;
0064   peak_ = 1. * sistrip::invalid_;
0065   synchronized_ = false;
0066 }
0067 
0068 // ----------------------------------------------------------------------------
0069 //
0070 void ApvTimingAnalysis::refTime(const float& time, const float& targetDelay) {
0071   // Checks synchronization to reference time is done only once
0072   if (synchronized_) {
0073     edm::LogWarning(mlCommissioning_) << "[" << myName() << "::" << __func__ << "]"
0074                                       << " Attempting to re-synchronize with reference time!"
0075                                       << " Not allowed!";
0076     return;
0077   }
0078   synchronized_ = true;
0079 
0080   // Set reference time and check if tick mark time is valid
0081   refTime_ = time;
0082   if (time_ > sistrip::valid_) {
0083     return;
0084   }
0085 
0086   // Calculate position of "sampling point" of last tick;
0087   int32_t position;
0088   if (targetDelay == -1) {  // by default use latest tick
0089     position = static_cast<int32_t>(rint(refTime_ + optimumSamplingPoint_));
0090   } else {
0091     position = static_cast<int32_t>(rint(targetDelay + optimumSamplingPoint_));
0092   }
0093 
0094   // Calculate adjustment so that sampling point is multiple of 25 (ie, synched with FED sampling)
0095   float adjustment = 25 - position % 25;
0096 
0097   // Calculate delay required to synchronise with this adjusted sampling position
0098   if (targetDelay == -1) {  // by default align forward to the latest tick
0099     delay_ = (refTime_ + adjustment) - time_;
0100   } else {  // otherwise use the supplied target delay
0101     if (adjustment > 25 / 2)
0102       adjustment -= 25;  // go as close as possible to desired target
0103     delay_ = (targetDelay + adjustment) - time_;
0104   }
0105 
0106   // Check reference time
0107   if (refTime_ < 0. || refTime_ > sistrip::valid_) {
0108     refTime_ = sistrip::invalid_;
0109     addErrorCode(sistrip::invalidRefTime_);
0110   }
0111 
0112   // Check delay is valid
0113   if (delay_ < -sistrip::valid_ || delay_ > sistrip::valid_) {
0114     delay_ = sistrip::invalid_;
0115     addErrorCode(sistrip::invalidDelayTime_);
0116   }
0117 }
0118 
0119 // ----------------------------------------------------------------------------
0120 //
0121 uint16_t ApvTimingAnalysis::frameFindingThreshold() const {
0122   if ((getErrorCodes().empty() || getErrorCodes()[0] == "TickMarkRecovered") && time_ < sistrip::valid_ &&
0123       base_ < sistrip::valid_ && peak_ < sistrip::valid_ && height_ < sistrip::valid_ &&
0124       height_ > tickMarkHeightThreshold_) {
0125     return ((static_cast<uint16_t>(base_ + height_ * ApvTimingAnalysis::frameFindingThreshold_) / 32) * 32);
0126   } else {
0127     return sistrip::invalid_;
0128   }
0129 }
0130 
0131 // ----------------------------------------------------------------------------
0132 //
0133 bool ApvTimingAnalysis::foundTickMark() const {
0134   return ((getErrorCodes().empty() || getErrorCodes()[0] == "TickMarkRecovered") && time_ < sistrip::valid_ &&
0135           base_ < sistrip::valid_ && peak_ < sistrip::valid_ && height_ < sistrip::valid_ &&
0136           frameFindingThreshold() < sistrip::valid_);
0137 }
0138 
0139 // ----------------------------------------------------------------------------
0140 //
0141 bool ApvTimingAnalysis::isValid() const {
0142   return ((getErrorCodes().empty() || getErrorCodes()[0] == "TickMarkRecovered") && time_ < sistrip::valid_ &&
0143           base_ < sistrip::valid_ && peak_ < sistrip::valid_ && height_ < sistrip::valid_ &&
0144           frameFindingThreshold() < sistrip::valid_ && synchronized_ && refTime_ < sistrip::valid_ &&
0145           delay_ < sistrip::valid_);
0146 }
0147 
0148 // ----------------------------------------------------------------------------
0149 //
0150 void ApvTimingAnalysis::print(std::stringstream& ss, uint32_t not_used) {
0151   header(ss);
0152 
0153   float sampling1 = sistrip::invalid_;
0154   if (time_ <= sistrip::valid_) {
0155     sampling1 = time_ + optimumSamplingPoint_;
0156   }
0157 
0158   float sampling2 = sistrip::invalid_;
0159   if (refTime_ <= sistrip::valid_) {
0160     sampling2 = refTime_ + optimumSamplingPoint_;
0161   }
0162 
0163   float adjust = sistrip::invalid_;
0164   if (sampling1 <= sistrip::valid_ && delay_ <= sistrip::valid_) {
0165     adjust = sampling1 + delay_;
0166   }
0167 
0168   ss << std::fixed << std::setprecision(2) << " Tick mark: time of rising edge     [ns] : " << time_
0169      << std::endl
0170      //<< " Error on time of rising edge     [ns] : " << error_ << std::endl
0171      << " Tick mark: time of sampling point  [ns] : " << sampling1 << std::endl
0172      << " Ref tick: time of rising edge      [ns] : " << refTime_ << std::endl
0173      << " Ref tick: time of sampling point   [ns] : " << sampling2 << std::endl
0174      << " Ref tick: adjusted sampling point  [ns] : " << adjust << std::endl
0175      << " Delay required to synchronise      [ns] : " << delay_ << std::endl
0176      << " Tick mark bottom (baseline)       [ADC] : " << base_ << std::endl
0177      << " Tick mark top                     [ADC] : " << peak_ << std::endl
0178      << " Tick mark height                  [ADC] : " << height_ << std::endl
0179      << " Frame finding threshold           [ADC] : " << frameFindingThreshold() << std::endl
0180      << std::boolalpha << " Tick mark found                         : " << foundTickMark() << std::endl
0181      << " isValid                                 : " << isValid() << std::endl
0182      << std::noboolalpha << " Error codes (found " << std::setw(3) << std::setfill(' ') << getErrorCodes().size()
0183      << ")                 : ";
0184   if (getErrorCodes().empty()) {
0185     ss << "(none)";
0186   } else {
0187     VString::const_iterator istr = getErrorCodes().begin();
0188     VString::const_iterator jstr = getErrorCodes().end();
0189     for (; istr != jstr; ++istr) {
0190       ss << *istr << " ";
0191     }
0192   }
0193   ss << std::endl;
0194 }