diff --git a/sbncode/CAFMaker/CAFMakerParams.h b/sbncode/CAFMaker/CAFMakerParams.h index 572bb5545..e2c2efbe8 100644 --- a/sbncode/CAFMaker/CAFMakerParams.h +++ b/sbncode/CAFMaker/CAFMakerParams.h @@ -338,6 +338,18 @@ namespace caf "crttracks" // sbnd }; + Atom SBNDFrameShiftInfoLabel { + Name("SBNDFrameShiftInfoLabel"), + Comment("Label of sbnd frame shift."), + "" // sbnd + }; + + Atom SBNDTimingInfoLabel { + Name("SBNDTimingInfoLabel"), + Comment("Label of sbnd timing shift."), + "" // sbnd + }; + Atom CRTPMTLabel { Name("CRTPMTLabel"), Comment("Label for the CRTPMT Matched variables from the crtpmt data product"), diff --git a/sbncode/CAFMaker/CAFMaker_module.cc b/sbncode/CAFMaker/CAFMaker_module.cc index f51183b46..29a35d0ee 100644 --- a/sbncode/CAFMaker/CAFMaker_module.cc +++ b/sbncode/CAFMaker/CAFMaker_module.cc @@ -118,6 +118,8 @@ #include "sbnobj/Common/Trigger/ExtraTriggerInfo.h" #include "sbnobj/Common/Reco/CRUMBSResult.h" #include "sbnobj/Common/Reco/OpT0FinderResult.h" +#include "sbnobj/SBND/Timing/TimingInfo.hh" +#include "sbnobj/SBND/Timing/FrameShiftInfo.hh" // GENIE #include "Framework/EventGen/EventRecord.h" @@ -316,6 +318,9 @@ class CAFMaker : public art::EDProducer { void FixPMTReferenceTimes(StandardRecord &rec, double PMT_reference_time); void FixCRTReferenceTimes(StandardRecord &rec, double CRTT0_reference_time, double CRTT1_reference_time); + void SBNDShiftCRTReference(StandardRecord &rec, double SBNDFrame) const; + void SBNDShiftPMTReference(StandardRecord &rec, double SBNDFrame) const; + /// Equivalent of FindManyP except a return that is !isValid() prints a /// messsage and aborts if StrictMode is true. template @@ -499,6 +504,44 @@ void CAFMaker::BlindEnergyParameters(StandardRecord* brec) { } } +void CAFMaker::SBNDShiftCRTReference(StandardRecord &rec, double SBNDFrame) const { + + //CRT Space Point + for (SRCRTSpacePoint &sp: rec.crt_spacepoints){ + sp.time += SBNDFrame; //ns + } + + //CRT Track + for (SRSBNDCRTTrack &trk: rec.sbnd_crt_tracks){ + trk.time += SBNDFrame; //ns + } + + //TODO: CRT Space Point and Track Match + for (SRSlice &slc: rec.slc){ + for (SRPFP &pfp: slc.reco.pfp){ + if(!std::isnan(pfp.trk.crtspacepoint.score)) pfp.trk.crtspacepoint.spacepoint.time += SBNDFrame; + + if(!std::isnan(pfp.trk.crtsbndtrack.score)) pfp.trk.crtsbndtrack.track.time += SBNDFrame; + } + } +} + +void CAFMaker::SBNDShiftPMTReference(StandardRecord &rec, double SBNDFrame) const { + + double SBNDFrame_us = SBNDFrame / 1000.0; //convert ns to us + + //Op Flash + for (SROpFlash &opf: rec.opflashes) { + opf.time += SBNDFrame_us; + opf.firsttime += SBNDFrame_us; + } + + //OpT0 match to slice + for (SRSlice &s: rec.slc) { + s.opt0.time += SBNDFrame_us; + } +} + void CAFMaker::FixPMTReferenceTimes(StandardRecord &rec, double PMT_reference_time) { // Fix the flashes for (SROpFlash &f: rec.opflashes) { @@ -1602,6 +1645,8 @@ void CAFMaker::produce(art::Event& evt) noexcept { std::vector srcrttracks; std::vector srcrtspacepoints; std::vector srsbndcrttracks; + caf::SRSBNDFrameShiftInfo srsbndframeshiftinfo; + caf::SRSBNDTimingInfo srsbndtiminginfo; if(fDet == kICARUS) { @@ -1650,6 +1695,22 @@ void CAFMaker::produce(art::Event& evt) noexcept { FillSBNDCRTTrack(sbndcrttracks[i], srsbndcrttracks.back()); } } + + art::Handle sbndframeshiftinfo_handle; + GetByLabelStrict(evt, fParams.SBNDFrameShiftInfoLabel(), sbndframeshiftinfo_handle); + // fill into event + if (sbndframeshiftinfo_handle.isValid()) { + sbnd::timing::FrameShiftInfo const& sbndframeshiftinfo(*sbndframeshiftinfo_handle); + FillSBNDFrameShiftInfo(sbndframeshiftinfo, srsbndframeshiftinfo); + } + + art::Handle sbndtiminginfo_handle; + GetByLabelStrict(evt, fParams.SBNDTimingInfoLabel(), sbndtiminginfo_handle); + // fill into event + if (sbndtiminginfo_handle.isValid()) { + sbnd::timing::TimingInfo const& sbndtiminginfo(*sbndtiminginfo_handle); + FillSBNDTimingInfo(sbndtiminginfo, srsbndtiminginfo); + } } // Get all of the CRTPMT Matches @@ -2367,6 +2428,9 @@ void CAFMaker::produce(art::Event& evt) noexcept { rec.nsbnd_crt_tracks = srsbndcrttracks.size(); rec.opflashes = srflashes; rec.nopflashes = srflashes.size(); + rec.sbnd_frames = srsbndframeshiftinfo; + rec.sbnd_timings = srsbndtiminginfo; + if (fParams.FillTrueParticles()) { rec.true_particles = true_particles; } @@ -2374,7 +2438,7 @@ void CAFMaker::produce(art::Event& evt) noexcept { rec.crtpmt_matches = srcrtpmtmatches; rec.ncrtpmt_matches = srcrtpmtmatches.size(); - // Fix the Reference time + // Move the reference time of reconstructed objects from trigger time to beam spill/beam gate opening time. // // We want MC and Data to have the same reference time. // In MC/LArSoft the "reference time" is canonically defined @@ -2391,6 +2455,7 @@ void CAFMaker::produce(art::Event& evt) noexcept { // filled with the default values, which are set to the numerical limits of double. // In this case, we should set the PMT_reference_time to 0. + // ICARUS: Fix the Reference time const bool hasValidTriggerTime = srtrigger.global_trigger_det_time > (std::numeric_limits::min() + std::numeric_limits::epsilon()) && @@ -2406,6 +2471,28 @@ void CAFMaker::produce(art::Event& evt) noexcept { FixPMTReferenceTimes(rec, PMT_reference_time); // TODO: TPC? + + // SBND: Fix the Reference time in data depending on the stream + // For more information, see: + // https://sbn-docdb.fnal.gov/cgi-bin/sso/RetrieveFile?docid=43090 + + if (isRealData && (fDet == kSBND)) + { + // Fill trigger info + FillTriggerSBND(srsbndtiminginfo, srtrigger); + + // Shift timing reference frame + if (!std::isnan(rec.sbnd_frames.frameApplyAtCaf) && (rec.sbnd_frames.frameApplyAtCaf != 0.0)){ + mf::LogInfo("CAFMaker") << "Setting Reference Timing for timing object in SBND \n" + << " Shift Apply At Caf Level = " << rec.sbnd_frames.frameApplyAtCaf << " ns\n"; + + //shift reference frame for CRT objects: crt trk, crt sp, crt sp match, crt trk match + SBNDShiftCRTReference(rec, rec.sbnd_frames.frameApplyAtCaf); + + //shift reference frame for PMT objects: opflash, opt0 + SBNDShiftPMTReference(rec, rec.sbnd_frames.frameApplyAtCaf); + } + } // Get metadata information for header unsigned int run = evt.run(); @@ -2690,7 +2777,6 @@ void CAFMaker::endJob() { if(fParams.CreateBlindedCAF() && fFlatFilep) AddMetadataToFile(fFlatFilep, metamap); } - } // end namespace caf DEFINE_ART_MODULE(caf::CAFMaker) //////////////////////////////////////////////////////////////////////// diff --git a/sbncode/CAFMaker/CMakeLists.txt b/sbncode/CAFMaker/CMakeLists.txt index 4cae127e2..df8b01a54 100644 --- a/sbncode/CAFMaker/CMakeLists.txt +++ b/sbncode/CAFMaker/CMakeLists.txt @@ -37,6 +37,7 @@ art_make_library( LIBRARY_NAME sbncode_CAFMaker sbnobj::Common_Analysis sbnobj::Common_PMT_Data sbnobj::SBND_CRT + sbnobj::SBND_Timing lardataalg::DetectorInfo art::Framework_Services_System_TriggerNamesService_service sbncode_Metadata_MetadataSBN_service diff --git a/sbncode/CAFMaker/FillReco.cxx b/sbncode/CAFMaker/FillReco.cxx index ae363dd61..95e76532b 100644 --- a/sbncode/CAFMaker/FillReco.cxx +++ b/sbncode/CAFMaker/FillReco.cxx @@ -141,6 +141,33 @@ namespace caf srsbndcrttrack.tof = track.ToF(); } + void FillSBNDFrameShiftInfo(const sbnd::timing::FrameShiftInfo &frame, + caf::SRSBNDFrameShiftInfo &srsbndframe, + bool allowEmpty) + { + srsbndframe.timingType = frame.TimingType(); + srsbndframe.frameTdcCrtt1 = frame.FrameTdcCrtt1(); + srsbndframe.frameTdcBes = frame.FrameTdcBes(); + srsbndframe.frameTdcRwm = frame.FrameTdcRwm(); + srsbndframe.frameHltCrtt1 = frame.FrameHltCrtt1(); + srsbndframe.frameHltBeamGate = frame.FrameHltBeamGate(); + srsbndframe.frameApplyAtCaf = frame.FrameApplyAtCaf(); + } + + void FillSBNDTimingInfo(const sbnd::timing::TimingInfo &timing, + caf::SRSBNDTimingInfo &srsbndtiming, + bool allowEmpty) + { + srsbndtiming.rawDAQHeaderTimestamp = timing.RawDAQHeaderTimestamp(); + srsbndtiming.tdcCrtt1 = timing.TdcCrtt1(); + srsbndtiming.tdcBes = timing.TdcBes(); + srsbndtiming.tdcRwm = timing.TdcRwm(); + srsbndtiming.tdcEtrig = timing.TdcEtrig(); + srsbndtiming.hltCrtt1 = timing.HltCrtt1(); + srsbndtiming.hltEtrig = timing.HltEtrig(); + srsbndtiming.hltBeamGate = timing.HltBeamGate(); + } + void FillCRTPMTMatch(const sbn::crt::CRTPMTMatching &match, caf::SRCRTPMTMatch &srmatch, bool allowEmpty){ diff --git a/sbncode/CAFMaker/FillReco.h b/sbncode/CAFMaker/FillReco.h index 4b24b4a98..eb4a034df 100644 --- a/sbncode/CAFMaker/FillReco.h +++ b/sbncode/CAFMaker/FillReco.h @@ -43,6 +43,9 @@ #include "sbnobj/Common/CRT/CRTPMTMatching.hh" #include "sbnobj/Common/CRT/CRTHitT0TaggingInfo.hh" #include "sbnobj/Common/PMT/Data/PMTBeamSignal.hh" +#include "sbnobj/SBND/Timing/TimingInfo.hh" +#include "sbnobj/SBND/Timing/FrameShiftInfo.hh" + #include "nusimdata/SimulationBase/MCParticle.h" #include "nusimdata/SimulationBase/MCTruth.h" @@ -281,6 +284,14 @@ namespace caf caf::SRPFP& srpfp, bool allowEmpty = false); + void FillSBNDFrameShiftInfo(const sbnd::timing::FrameShiftInfo &frame, + caf::SRSBNDFrameShiftInfo &srsbndframe, + bool allowEmpty = false); + + void FillSBNDTimingInfo(const sbnd::timing::TimingInfo &timing, + caf::SRSBNDTimingInfo &srsbndtiming, + bool allowEmpty = false); + template void CopyPropertyIfSet( const std::map& props, const std::string& search, U& value ); } diff --git a/sbncode/CAFMaker/FillTrigger.cxx b/sbncode/CAFMaker/FillTrigger.cxx index 009deccef..8bf82c02c 100644 --- a/sbncode/CAFMaker/FillTrigger.cxx +++ b/sbncode/CAFMaker/FillTrigger.cxx @@ -35,4 +35,13 @@ namespace caf // TODO: fill others? } + void FillTriggerSBND(caf::SRSBNDTimingInfo& timingInfo, caf::SRTrigger& triggerInfo){ + + triggerInfo.global_trigger_time = timingInfo.hltEtrig; + triggerInfo.beam_gate_time_abs = timingInfo.hltBeamGate; + + double diff_ts = triggerInfo.global_trigger_det_time - triggerInfo.beam_gate_det_time; + triggerInfo.trigger_within_gate = diff_ts; + } + } diff --git a/sbncode/CAFMaker/FillTrigger.h b/sbncode/CAFMaker/FillTrigger.h index b83c2e9f0..ea1aab7eb 100644 --- a/sbncode/CAFMaker/FillTrigger.h +++ b/sbncode/CAFMaker/FillTrigger.h @@ -4,6 +4,7 @@ #include "sbnobj/Common/Trigger/ExtraTriggerInfo.h" #include "sbnobj/Common/Trigger/BeamBits.h" #include "sbnanaobj/StandardRecord/SRTrigger.h" +#include "sbnanaobj/StandardRecord/SRSBNDTimingInfo.h" #include "lardataobj/RawData/TriggerData.h" #include @@ -18,6 +19,7 @@ namespace caf void FillTriggerMC(double absolute_time, caf::SRTrigger& triggerInfo); + void FillTriggerSBND(caf::SRSBNDTimingInfo& timingInfo, caf::SRTrigger& triggerInfo); } #endif