Back to home page

Project CMSSW displayed by LXR

 
 

    


File indexing completed on 2022-08-18 23:53:39

0001 /****************************************************************************
0002  *
0003  * This is a part of TotemDQM and TOTEM offline software.
0004  * Authors:
0005  *   Jan Kašpar (jan.kaspar@gmail.com)
0006  *
0007  ****************************************************************************/
0008 
0009 #include "FWCore/Framework/interface/ESHandle.h"
0010 #include "FWCore/Framework/interface/MakerMacros.h"
0011 #include "FWCore/Framework/interface/Event.h"
0012 #include "FWCore/Framework/interface/EventSetup.h"
0013 #include "FWCore/Framework/interface/LuminosityBlock.h"
0014 #include "FWCore/ParameterSet/interface/ParameterSet.h"
0015 #include "FWCore/Utilities/interface/InputTag.h"
0016 
0017 #include "DQMServices/Core/interface/DQMOneEDAnalyzer.h"
0018 #include "DQMServices/Core/interface/DQMStore.h"
0019 
0020 #include "DataFormats/CTPPSDetId/interface/CTPPSDetId.h"
0021 #include "DataFormats/CTPPSReco/interface/CTPPSLocalTrackLite.h"
0022 #include "DataFormats/ProtonReco/interface/ForwardProton.h"
0023 #include "DataFormats/OnlineMetaData/interface/CTPPSRecord.h"
0024 
0025 #include <string>
0026 
0027 //----------------------------------------------------------------------------------------------------
0028 
0029 class CTPPSCommonDQMSource : public DQMOneEDAnalyzer<edm::LuminosityBlockCache<std::vector<int>>> {
0030 public:
0031   CTPPSCommonDQMSource(const edm::ParameterSet &ps);
0032   ~CTPPSCommonDQMSource() override;
0033 
0034 protected:
0035   void bookHistograms(DQMStore::IBooker &, edm::Run const &, edm::EventSetup const &) override;
0036   void analyze(edm::Event const &e, edm::EventSetup const &eSetup) override;
0037   std::shared_ptr<std::vector<int>> globalBeginLuminosityBlock(const edm::LuminosityBlock &iLumi,
0038                                                                const edm::EventSetup &c) const override;
0039   void globalEndLuminosityBlock(const edm::LuminosityBlock &iLumi, const edm::EventSetup &c) override;
0040 
0041   void analyzeCTPPSRecord(edm::Event const &event, edm::EventSetup const &eventSetup);
0042   void analyzeTracks(edm::Event const &event, edm::EventSetup const &eventSetup);
0043   void analyzeProtons(edm::Event const &event, edm::EventSetup const &eventSetup);
0044 
0045 private:
0046   const unsigned int verbosity;
0047   constexpr static int MAX_LUMIS = 6000;
0048   constexpr static int MAX_VBINS = 18;
0049 
0050   const edm::EDGetTokenT<CTPPSRecord> ctppsRecordToken;
0051   const edm::EDGetTokenT<std::vector<CTPPSLocalTrackLite>> tokenLocalTrackLite;
0052   const edm::EDGetTokenT<std::vector<reco::ForwardProton>> tokenRecoProtons;
0053 
0054   bool makeProtonRecoPlots_;
0055   bool perLSsaving_;  //to avoid nanoDQMIO crashing, driven by  DQMServices/Core/python/DQMStore_cfi.py
0056 
0057   int currentLS;
0058   int endLS;
0059 
0060   std::vector<int> rpstate;
0061 
0062   /// plots related to the whole system
0063   struct GlobalPlots {
0064     MonitorElement *RPState = nullptr;
0065     MonitorElement *events_per_bx = nullptr, *events_per_bx_short = nullptr;
0066     MonitorElement *h_trackCorr_hor = nullptr, *h_trackCorr_vert = nullptr;
0067 
0068     void Init(DQMStore::IBooker &ibooker);
0069   };
0070 
0071   GlobalPlots globalPlots;
0072 
0073   /// plots related to one arm
0074   struct ArmPlots {
0075     int id;
0076 
0077     MonitorElement *h_numRPWithTrack_top = nullptr, *h_numRPWithTrack_hor = nullptr, *h_numRPWithTrack_bot = nullptr;
0078     MonitorElement *h_trackCorr = nullptr, *h_trackCorr_overlap = nullptr;
0079 
0080     MonitorElement *h_proton_xi = nullptr, *h_proton_th_x = nullptr, *h_proton_th_y = nullptr, *h_proton_t = nullptr,
0081                    *h_proton_time = nullptr;
0082 
0083     struct TrackingRPPlots {
0084       MonitorElement *h_x, *h_y;
0085     };
0086 
0087     std::map<unsigned int, TrackingRPPlots> trackingRPPlots;
0088 
0089     struct TimingRPPlots {
0090       MonitorElement *h_x, *h_time;
0091     };
0092 
0093     std::map<unsigned int, TimingRPPlots> timingRPPlots;
0094 
0095     ArmPlots() {}
0096 
0097     ArmPlots(DQMStore::IBooker &ibooker, int _id, bool makeProtonRecoPlots);
0098   };
0099 
0100   std::map<unsigned int, ArmPlots> armPlots;
0101 };
0102 
0103 //----------------------------------------------------------------------------------------------------
0104 //----------------------------------------------------------------------------------------------------
0105 
0106 using namespace std;
0107 using namespace edm;
0108 
0109 const int CTPPSCommonDQMSource::MAX_LUMIS;
0110 const int CTPPSCommonDQMSource::MAX_VBINS;
0111 
0112 //----------------------------------------------------------------------------------------------------
0113 
0114 void CTPPSCommonDQMSource::GlobalPlots::Init(DQMStore::IBooker &ibooker) {
0115   ibooker.setCurrentFolder("CTPPS/common");
0116 
0117   events_per_bx = ibooker.book1D("events per BX", "rp;Event.BX", 4002, -1.5, 4000. + 0.5);
0118   events_per_bx_short = ibooker.book1D("events per BX (short)", "rp;Event.BX", 102, -1.5, 100. + 0.5);
0119 
0120   /*
0121      RP State (HV & LV & Insertion):
0122      0 -> not used
0123      1 -> bad
0124      2 -> warning
0125      3 -> ok
0126   */
0127   RPState = ibooker.book2D("rpstate per LS",
0128                            "RP State per Lumisection;Luminosity Section;",
0129                            MAX_LUMIS,
0130                            0,
0131                            MAX_LUMIS,
0132                            MAX_VBINS,
0133                            0.,
0134                            MAX_VBINS);
0135   {
0136     TH2F *hist = RPState->getTH2F();
0137     hist->SetCanExtend(TH1::kAllAxes);
0138     TAxis *ya = hist->GetYaxis();
0139     ya->SetBinLabel(1, "45, 210, FR-BT");
0140     ya->SetBinLabel(2, "45, 210, FR-HR");
0141     ya->SetBinLabel(3, "45, 210, FR-TP");
0142     ya->SetBinLabel(4, "45, 220, C1");
0143     ya->SetBinLabel(5, "45, 220, FR-BT");
0144     ya->SetBinLabel(6, "45, 220, FR-HR");
0145     ya->SetBinLabel(7, "45, 220, FR-TP");
0146     ya->SetBinLabel(8, "45, 220, NR-BP");
0147     ya->SetBinLabel(9, "45, 220, NR-TP");
0148     ya->SetBinLabel(10, "56, 210, FR-BT");
0149     ya->SetBinLabel(11, "56, 210, FR-HR");
0150     ya->SetBinLabel(12, "56, 210, FR-TP");
0151     ya->SetBinLabel(13, "56, 220, C1");
0152     ya->SetBinLabel(14, "56, 220, FR-BT");
0153     ya->SetBinLabel(15, "56, 220, FR-HR");
0154     ya->SetBinLabel(16, "56, 220, FR-TP");
0155     ya->SetBinLabel(17, "56, 220, NR-BP");
0156     ya->SetBinLabel(18, "56, 220, NR-TP");
0157   }
0158 
0159   h_trackCorr_hor = ibooker.book2D("track correlation hor", "ctpps_common_rp_hor", 8, -0.5, 7.5, 8, -0.5, 7.5);
0160   {
0161     TH2F *hist = h_trackCorr_hor->getTH2F();
0162     TAxis *xa = hist->GetXaxis(), *ya = hist->GetYaxis();
0163     xa->SetBinLabel(1, "45, 210, FR");
0164     ya->SetBinLabel(1, "45, 210, FR");
0165     xa->SetBinLabel(2, "45, 220, NR");
0166     ya->SetBinLabel(2, "45, 220, NR");
0167     xa->SetBinLabel(3, "45, 220, C1");
0168     ya->SetBinLabel(3, "45, 220, C1");
0169     xa->SetBinLabel(4, "45, 220, FR");
0170     ya->SetBinLabel(4, "45, 220, FR");
0171 
0172     xa->SetBinLabel(5, "56, 210, FR");
0173     ya->SetBinLabel(5, "56, 210, FR");
0174     xa->SetBinLabel(6, "56, 220, NR");
0175     ya->SetBinLabel(6, "56, 220, NR");
0176     xa->SetBinLabel(7, "56, 220, C1");
0177     ya->SetBinLabel(7, "56, 220, C1");
0178     xa->SetBinLabel(8, "56, 220, FR");
0179     ya->SetBinLabel(8, "56, 220, FR");
0180   }
0181 
0182   h_trackCorr_vert = ibooker.book2D("track correlation vert", "ctpps_common_rp_vert", 8, -0.5, 7.5, 8, -0.5, 7.5);
0183   {
0184     TH2F *hist = h_trackCorr_vert->getTH2F();
0185     TAxis *xa = hist->GetXaxis(), *ya = hist->GetYaxis();
0186     xa->SetBinLabel(1, "45, 210, FR-TP");
0187     ya->SetBinLabel(1, "45, 210, FR-TP");
0188     xa->SetBinLabel(2, "45, 210, FR-BT");
0189     ya->SetBinLabel(2, "45, 210, FR-BT");
0190     xa->SetBinLabel(3, "45, 220, FR-TP");
0191     ya->SetBinLabel(3, "45, 220, FR-TP");
0192     xa->SetBinLabel(4, "45, 220, FR-BT");
0193     ya->SetBinLabel(4, "45, 220, FR-BT");
0194     xa->SetBinLabel(5, "56, 210, FR-TP");
0195     ya->SetBinLabel(5, "56, 210, FR-TP");
0196     xa->SetBinLabel(6, "56, 210, FR-BT");
0197     ya->SetBinLabel(6, "56, 210, FR-BT");
0198     xa->SetBinLabel(7, "56, 220, FR-TP");
0199     ya->SetBinLabel(7, "56, 220, FR-TP");
0200     xa->SetBinLabel(8, "56, 220, FR-BT");
0201     ya->SetBinLabel(8, "56, 220, FR-BT");
0202   }
0203 }
0204 
0205 //----------------------------------------------------------------------------------------------------
0206 
0207 CTPPSCommonDQMSource::ArmPlots::ArmPlots(DQMStore::IBooker &ibooker, int _id, bool makeProtonRecoPlots) : id(_id) {
0208   string name;
0209   CTPPSDetId(CTPPSDetId::sdTrackingStrip, id, 0).armName(name, CTPPSDetId::nShort);
0210 
0211   ibooker.setCurrentFolder("CTPPS/common/sector " + name);
0212 
0213   string title = "ctpps_common_sector_" + name;
0214 
0215   h_numRPWithTrack_top =
0216       ibooker.book1D("number of top RPs with tracks", title + ";number of top RPs with tracks", 5, -0.5, 4.5);
0217   h_numRPWithTrack_hor =
0218       ibooker.book1D("number of hor RPs with tracks", title + ";number of hor RPs with tracks", 5, -0.5, 4.5);
0219   h_numRPWithTrack_bot =
0220       ibooker.book1D("number of bot RPs with tracks", title + ";number of bot RPs with tracks", 5, -0.5, 4.5);
0221 
0222   h_trackCorr = ibooker.book2D("track correlation", title, 8, -0.5, 7.5, 8, -0.5, 7.5);
0223   TH2F *h_trackCorr_h = h_trackCorr->getTH2F();
0224   TAxis *xa = h_trackCorr_h->GetXaxis(), *ya = h_trackCorr_h->GetYaxis();
0225   xa->SetBinLabel(1, "210, FR-HR");
0226   ya->SetBinLabel(1, "210, FR-HR");
0227   xa->SetBinLabel(2, "210, FR-TP");
0228   ya->SetBinLabel(2, "210, FR-TP");
0229   xa->SetBinLabel(3, "210, FR-BT");
0230   ya->SetBinLabel(3, "210, FR-BT");
0231   xa->SetBinLabel(4, "220, NR-HR");
0232   ya->SetBinLabel(4, "220, NR-HR");
0233   xa->SetBinLabel(5, "220, C1");
0234   ya->SetBinLabel(5, "220, C1");
0235   xa->SetBinLabel(6, "220, FR-HR");
0236   ya->SetBinLabel(6, "220, FR-HR");
0237   xa->SetBinLabel(7, "220, FR-TP");
0238   ya->SetBinLabel(7, "220, FR-TP");
0239   xa->SetBinLabel(8, "220, FR-BT");
0240   ya->SetBinLabel(8, "220, FR-BT");
0241 
0242   h_trackCorr_overlap = ibooker.book2D("track correlation hor-vert overlaps", title, 8, -0.5, 7.5, 8, -0.5, 7.5);
0243   h_trackCorr_h = h_trackCorr_overlap->getTH2F();
0244   xa = h_trackCorr_h->GetXaxis();
0245   ya = h_trackCorr_h->GetYaxis();
0246   xa->SetBinLabel(1, "210, FR-HR");
0247   ya->SetBinLabel(1, "210, FR-HR");
0248   xa->SetBinLabel(2, "210, FR-TP");
0249   ya->SetBinLabel(2, "210, FR-TP");
0250   xa->SetBinLabel(3, "210, FR-BT");
0251   ya->SetBinLabel(3, "210, FR-BT");
0252   xa->SetBinLabel(4, "220, NR-HR");
0253   ya->SetBinLabel(4, "220, NR-HR");
0254   xa->SetBinLabel(5, "220, C1");
0255   ya->SetBinLabel(5, "220, C1");
0256   xa->SetBinLabel(6, "220, FR-HR");
0257   ya->SetBinLabel(6, "220, FR-HR");
0258   xa->SetBinLabel(7, "220, FR-TP");
0259   ya->SetBinLabel(7, "220, FR-TP");
0260   xa->SetBinLabel(8, "220, FR-BT");
0261   ya->SetBinLabel(8, "220, FR-BT");
0262 
0263   if (makeProtonRecoPlots) {
0264     h_proton_xi = ibooker.book1D("proton xi", title + ";xi", 100, 0., 0.3);
0265     h_proton_th_x = ibooker.book1D("proton theta st x", ";#theta^{*}_{x}   (rad)", 250, -500E-6, +500E-6);
0266     h_proton_th_y = ibooker.book1D("proton theta st y", ";#theta^{*}_{y}   (rad)", 250, -500E-6, +500E-6);
0267     h_proton_t = ibooker.book1D("proton t", title + ";|t|   GeV^{2}", 100, 0., 5.);
0268     h_proton_time = ibooker.book1D("proton time", title + ";time   (ns)", 100, -1., 1.);
0269   }
0270 
0271   for (const unsigned int rpDecId : {3, 22, 16, 23}) {
0272     unsigned int st = rpDecId / 10, rp = rpDecId % 10, rpFullDecId = id * 100 + rpDecId;
0273     CTPPSDetId rpId(CTPPSDetId::sdTrackingStrip, id, st, rp);
0274     string stName, rpName;
0275     rpId.stationName(stName, CTPPSDetId::nShort);
0276     rpId.rpName(rpName, CTPPSDetId::nShort);
0277     rpName = stName + "_" + rpName;
0278 
0279     const bool timingRP = (rpDecId == 22 || rpDecId == 16);
0280 
0281     if (timingRP) {
0282       timingRPPlots[rpFullDecId] = {
0283           ibooker.book1D(rpName + " - track x histogram", title + "/" + rpName + ";track x   (mm)", 200, 0., 40.),
0284           ibooker.book1D(
0285               rpName + " - track time histogram", title + "/" + rpName + ";track time   (ns)", 100, -25., +50.)};
0286     } else {
0287       trackingRPPlots[rpFullDecId] = {
0288           ibooker.book1D(rpName + " - track x histogram", title + "/" + rpName + ";track x   (mm)", 200, 0., 40.),
0289           ibooker.book1D(rpName + " - track y histogram", title + "/" + rpName + ";track y   (mm)", 200, -20., +20.)};
0290     }
0291   }
0292 }
0293 
0294 //----------------------------------------------------------------------------------------------------
0295 //----------------------------------------------------------------------------------------------------
0296 
0297 CTPPSCommonDQMSource::CTPPSCommonDQMSource(const edm::ParameterSet &ps)
0298     : verbosity(ps.getUntrackedParameter<unsigned int>("verbosity", 0)),
0299       ctppsRecordToken(consumes<CTPPSRecord>(ps.getUntrackedParameter<edm::InputTag>("ctppsmetadata"))),
0300       tokenLocalTrackLite(
0301           consumes<vector<CTPPSLocalTrackLite>>(ps.getUntrackedParameter<edm::InputTag>("tagLocalTrackLite"))),
0302       tokenRecoProtons(
0303           consumes<std::vector<reco::ForwardProton>>(ps.getUntrackedParameter<InputTag>("tagRecoProtons"))),
0304       makeProtonRecoPlots_(ps.getParameter<bool>("makeProtonRecoPlots")),
0305       perLSsaving_(ps.getUntrackedParameter<bool>("perLSsaving", false)) {
0306   currentLS = 0;
0307   endLS = 0;
0308   rpstate.clear();
0309 }
0310 
0311 //----------------------------------------------------------------------------------------------------
0312 
0313 CTPPSCommonDQMSource::~CTPPSCommonDQMSource() {}
0314 
0315 //----------------------------------------------------------------------------------------------------
0316 
0317 void CTPPSCommonDQMSource::bookHistograms(DQMStore::IBooker &ibooker, edm::Run const &, edm::EventSetup const &) {
0318   // global plots
0319   globalPlots.Init(ibooker);
0320 
0321   // loop over arms
0322   for (unsigned int arm = 0; arm < 2; arm++) {
0323     armPlots[arm] = ArmPlots(ibooker, arm, makeProtonRecoPlots_);
0324   }
0325 }
0326 
0327 //----------------------------------------------------------------------------------------------------
0328 
0329 void CTPPSCommonDQMSource::analyze(edm::Event const &event, edm::EventSetup const &eventSetup) {
0330   analyzeCTPPSRecord(event, eventSetup);
0331   analyzeTracks(event, eventSetup);
0332 
0333   if (makeProtonRecoPlots_)
0334     analyzeProtons(event, eventSetup);
0335 }
0336 
0337 //----------------------------------------------------------------------------------------------------
0338 
0339 void CTPPSCommonDQMSource::analyzeCTPPSRecord(edm::Event const &event, edm::EventSetup const &eventSetup) {
0340   Handle<CTPPSRecord> hCTPPSRecord;
0341   event.getByToken(ctppsRecordToken, hCTPPSRecord);
0342 
0343   if (!hCTPPSRecord.isValid()) {
0344     if (verbosity)
0345       LogProblem("CTPPSCommonDQMSource") << "ERROR in CTPPSCommonDQMSource::analyzeCTPPSRecord > input not available.";
0346 
0347     return;
0348   }
0349 
0350   auto &rpstate = *luminosityBlockCache(event.getLuminosityBlock().index());
0351   if (rpstate.empty()) {
0352     rpstate.reserve(CTPPSRecord::RomanPot::Last);
0353     for (uint8_t i = 0; i < CTPPSRecord::RomanPot::Last; ++i)
0354       rpstate.push_back(hCTPPSRecord->status(i));
0355   }
0356 }
0357 
0358 //----------------------------------------------------------------------------------------------------
0359 
0360 void CTPPSCommonDQMSource::analyzeTracks(edm::Event const &event, edm::EventSetup const &eventSetup) {
0361   // get event data
0362   Handle<vector<CTPPSLocalTrackLite>> hTracks;
0363   event.getByToken(tokenLocalTrackLite, hTracks);
0364 
0365   // check validity
0366   if (!hTracks.isValid()) {
0367     if (verbosity)
0368       LogProblem("CTPPSCommonDQMSource") << "ERROR in CTPPSCommonDQMSource::analyzeTracks > input not available.";
0369 
0370     return;
0371   }
0372 
0373   //------------------------------
0374   // collect indeces of RP with tracks, for each correlation plot
0375   set<signed int> s_rp_idx_global_hor, s_rp_idx_global_vert;
0376   map<unsigned int, set<signed int>> ms_rp_idx_arm;
0377 
0378   for (auto &tr : *hTracks) {
0379     const CTPPSDetId rpId(tr.rpId());
0380     const unsigned int arm = rpId.arm();
0381     const unsigned int stNum = rpId.station();
0382     const unsigned int rpNum = rpId.rp();
0383     const unsigned int stRPNum = stNum * 10 + rpNum;
0384 
0385     {
0386       signed int idx = -1;
0387       if (stRPNum == 3)
0388         idx = 0;
0389       if (stRPNum == 22)
0390         idx = 1;
0391       if (stRPNum == 16)
0392         idx = 2;
0393       if (stRPNum == 23)
0394         idx = 3;
0395 
0396       if (idx >= 0)
0397         s_rp_idx_global_hor.insert(4 * arm + idx);
0398     }
0399 
0400     {
0401       signed int idx = -1;
0402       if (stRPNum == 4)
0403         idx = 0;
0404       if (stRPNum == 5)
0405         idx = 1;
0406       if (stRPNum == 24)
0407         idx = 2;
0408       if (stRPNum == 25)
0409         idx = 3;
0410 
0411       if (idx >= 0)
0412         s_rp_idx_global_vert.insert(4 * arm + idx);
0413     }
0414 
0415     {
0416       signed int idx = -1;
0417       if (stRPNum == 3)
0418         idx = 0;
0419       if (stRPNum == 4)
0420         idx = 1;
0421       if (stRPNum == 5)
0422         idx = 2;
0423       if (stRPNum == 22)
0424         idx = 3;
0425       if (stRPNum == 16)
0426         idx = 4;
0427       if (stRPNum == 23)
0428         idx = 5;
0429       if (stRPNum == 24)
0430         idx = 6;
0431       if (stRPNum == 25)
0432         idx = 7;
0433 
0434       const signed int hor = ((rpNum == 2) || (rpNum == 3) || (rpNum == 6)) ? 1 : 0;
0435 
0436       if (idx >= 0)
0437         ms_rp_idx_arm[arm].insert(idx * 10 + hor);
0438     }
0439   }
0440 
0441   //------------------------------
0442   // Global Plots
0443 
0444   globalPlots.events_per_bx->Fill(event.bunchCrossing());
0445   globalPlots.events_per_bx_short->Fill(event.bunchCrossing());
0446 
0447   for (const auto &idx1 : s_rp_idx_global_hor)
0448     for (const auto &idx2 : s_rp_idx_global_hor)
0449       globalPlots.h_trackCorr_hor->Fill(idx1, idx2);
0450 
0451   for (const auto &idx1 : s_rp_idx_global_vert)
0452     for (const auto &idx2 : s_rp_idx_global_vert)
0453       globalPlots.h_trackCorr_vert->Fill(idx1, idx2);
0454 
0455   //------------------------------
0456   // Arm Plots
0457 
0458   map<unsigned int, set<unsigned int>> mTop, mHor, mBot;
0459 
0460   for (auto &tr : *hTracks) {
0461     CTPPSDetId rpId(tr.rpId());
0462     const unsigned int rpNum = rpId.rp();
0463     const unsigned int armIdx = rpId.arm();
0464 
0465     if (rpNum == 0 || rpNum == 4)
0466       mTop[armIdx].insert(rpId);
0467     if (rpNum == 2 || rpNum == 3 || rpNum == 6)
0468       mHor[armIdx].insert(rpId);
0469     if (rpNum == 1 || rpNum == 5)
0470       mBot[armIdx].insert(rpId);
0471 
0472     auto &ap = armPlots[rpId.arm()];
0473     unsigned int rpDecId = rpId.arm() * 100 + rpId.station() * 10 + rpId.rp();
0474 
0475     // fill in reference tracking-RP plots
0476     {
0477       auto it = ap.trackingRPPlots.find(rpDecId);
0478       if (it != ap.trackingRPPlots.end()) {
0479         it->second.h_x->Fill(tr.x());
0480         it->second.h_y->Fill(tr.y());
0481       }
0482     }
0483 
0484     // fill in reference timing-RP plots
0485     {
0486       auto it = ap.timingRPPlots.find(rpDecId);
0487       if (it != ap.timingRPPlots.end()) {
0488         it->second.h_x->Fill(tr.x());
0489         it->second.h_time->Fill(tr.time());
0490       }
0491     }
0492   }
0493 
0494   for (auto &p : armPlots) {
0495     p.second.h_numRPWithTrack_top->Fill(mTop[p.first].size());
0496     p.second.h_numRPWithTrack_hor->Fill(mHor[p.first].size());
0497     p.second.h_numRPWithTrack_bot->Fill(mBot[p.first].size());
0498   }
0499 
0500   //------------------------------
0501   // Correlation plots
0502 
0503   for (const auto &ap : ms_rp_idx_arm) {
0504     auto &plots = armPlots[ap.first];
0505 
0506     for (const auto &idx1 : ap.second) {
0507       for (const auto &idx2 : ap.second) {
0508         plots.h_trackCorr->Fill(idx1 / 10, idx2 / 10);
0509 
0510         if ((idx1 % 10) != (idx2 % 10))
0511           plots.h_trackCorr_overlap->Fill(idx1 / 10, idx2 / 10);
0512       }
0513     }
0514   }
0515 }
0516 
0517 //----------------------------------------------------------------------------------------------------
0518 
0519 void CTPPSCommonDQMSource::analyzeProtons(edm::Event const &event, edm::EventSetup const &eventSetup) {
0520   // get event data
0521   Handle<vector<reco::ForwardProton>> hRecoProtons;
0522   event.getByToken(tokenRecoProtons, hRecoProtons);
0523 
0524   // check validity
0525   if (!hRecoProtons.isValid()) {
0526     if (verbosity)
0527       LogProblem("CTPPSCommonDQMSource") << "ERROR in CTPPSCommonDQMSource::analyzeProtons > input not available.";
0528 
0529     return;
0530   }
0531 
0532   // loop over protons
0533   for (auto &p : *hRecoProtons) {
0534     if (!p.validFit())
0535       continue;
0536 
0537     signed int armIndex = -1;
0538     if (p.lhcSector() == reco::ForwardProton::LHCSector::sector45)
0539       armIndex = 0;
0540     if (p.lhcSector() == reco::ForwardProton::LHCSector::sector56)
0541       armIndex = 1;
0542     if (armIndex < 0)
0543       continue;
0544 
0545     auto &plots = armPlots[armIndex];
0546 
0547     plots.h_proton_xi->Fill(p.xi());
0548     plots.h_proton_th_x->Fill(p.thetaX());
0549     plots.h_proton_th_y->Fill(p.thetaY());
0550     plots.h_proton_t->Fill(fabs(p.t()));
0551     plots.h_proton_time->Fill(p.time());
0552   }
0553 }
0554 
0555 //----------------------------------------------------------------------------------------------------
0556 
0557 std::shared_ptr<std::vector<int>> CTPPSCommonDQMSource::globalBeginLuminosityBlock(const edm::LuminosityBlock &,
0558                                                                                    const edm::EventSetup &) const {
0559   return std::make_shared<std::vector<int>>();
0560 }
0561 
0562 //----------------------------------------------------------------------------------------------------
0563 
0564 void CTPPSCommonDQMSource::globalEndLuminosityBlock(const edm::LuminosityBlock &iLumi, const edm::EventSetup &c) {
0565   auto const &rpstate = *luminosityBlockCache(iLumi.index());
0566   auto currentLS = iLumi.id().luminosityBlock();
0567   if (!perLSsaving_) {
0568     for (std::vector<int>::size_type i = 0; i < rpstate.size(); i++)
0569       globalPlots.RPState->setBinContent(currentLS, i + 1, rpstate[i]);
0570   }
0571 }
0572 
0573 //----------------------------------------------------------------------------------------------------
0574 
0575 DEFINE_FWK_MODULE(CTPPSCommonDQMSource);