File indexing completed on 2024-04-06 11:58:08
0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016
0017
0018
0019
0020 #include <iostream>
0021 #include <fstream>
0022 #include <memory>
0023
0024 #include "FWCore/Framework/interface/ModuleFactory.h"
0025 #include "FWCore/Framework/interface/DependentRecordImplementation.h"
0026 #include "FWCore/Framework/interface/ESProducer.h"
0027 #include "FWCore/Framework/interface/ESProductHost.h"
0028 #include "FWCore/Framework/interface/ESTransientHandle.h"
0029 #include "FWCore/Utilities/interface/ReusableObjectHolder.h"
0030 #include "FWCore/Utilities/interface/TypeDemangler.h"
0031
0032 #include "CondFormats/HcalObjects/interface/AllObjects.h"
0033 #include "CondFormats/DataRecord/interface/HcalAllRcds.h"
0034 #include "CalibCalorimetry/HcalAlgos/interface/HcalDbASCIIIO.h"
0035 #include "CalibFormats/HcalObjects/interface/HcalDbService.h"
0036 #include "CalibFormats/HcalObjects/interface/HcalDbRecord.h"
0037
0038 class HcalDbProducer : public edm::ESProducer {
0039 public:
0040 HcalDbProducer(const edm::ParameterSet&);
0041 ~HcalDbProducer() override;
0042
0043 std::shared_ptr<HcalDbService> produce(const HcalDbRecord&);
0044
0045 private:
0046 using HostType = edm::ESProductHost<HcalDbService,
0047 HcalPedestalsRcd,
0048 HcalPedestalWidthsRcd,
0049 HcalGainsRcd,
0050 HcalGainWidthsRcd,
0051 HcalQIEDataRcd,
0052 HcalQIETypesRcd,
0053 HcalChannelQualityRcd,
0054 HcalZSThresholdsRcd,
0055 HcalRespCorrsRcd,
0056 HcalL1TriggerObjectsRcd,
0057 HcalTimeCorrsRcd,
0058 HcalLUTCorrsRcd,
0059 HcalPFCorrsRcd,
0060 HcalLutMetadataRcd,
0061 HcalSiPMParametersRcd,
0062 HcalTPChannelParametersRcd,
0063 HcalMCParamsRcd,
0064 HcalRecoParamsRcd,
0065 HcalElectronicsMapRcd,
0066 HcalFrontEndMapRcd,
0067 HcalSiPMCharacteristicsRcd,
0068 HcalTPParametersRcd>;
0069
0070
0071 template <typename ProductType>
0072 static void serviceSetData(HostType& host, const ProductType& item, std::false_type) {
0073 host.setData(&item);
0074 }
0075 template <typename ProductType>
0076 static void serviceSetData(HostType& host, const ProductType& item, std::true_type) {
0077 host.setData(&item, true);
0078 }
0079 template <typename ProductType, typename RecordType, const char* LABEL, typename EffectiveType>
0080 class ServiceTokenImpl {
0081 public:
0082 ServiceTokenImpl()
0083 : dumpName_(edm::typeDemangle(typeid(ProductType).name()).substr(4))
0084 {
0085 if constexpr (EffectiveType::value) {
0086 dumpName_ = "Effective" + dumpName_;
0087 }
0088 }
0089 void setConsumes(edm::ESConsumesCollector& cc) { token_ = cc.consumes(edm::ESInputTag{"", LABEL}); }
0090 void setupHcalDbService(HostType& host,
0091 const RecordType& record,
0092 const std::vector<std::string>& dumpRequest,
0093 std::ostream* dumpStream) {
0094 const auto& item = record.get(token_);
0095 serviceSetData(host, item, EffectiveType{});
0096
0097 if (std::find(dumpRequest.begin(), dumpRequest.end(), dumpName_) != dumpRequest.end()) {
0098 *dumpStream << "New HCAL " << dumpName_ << " set" << std::endl;
0099 HcalDbASCIIIO::dumpObject(*dumpStream, item);
0100 }
0101 }
0102
0103 private:
0104 edm::ESGetToken<ProductType, RecordType> token_;
0105 std::string dumpName_;
0106 };
0107
0108 template <typename ProductType, const char* LABEL, typename EffectiveType = std::false_type>
0109 struct ServiceToken {
0110 using Product = ProductType;
0111 static constexpr const char* label = LABEL;
0112 using Effective = EffectiveType;
0113 };
0114
0115 template <typename RecordType, typename... TokenHolders>
0116 class TokensForServiceHolder {
0117 public:
0118 void setConsumes(edm::ESConsumesCollector& cc) {
0119 std::apply([&cc](auto&&... item) { ((item.setConsumes(cc)), ...); }, tokens_);
0120 }
0121 void setupHcalDbService(HostType& host,
0122 const HcalDbRecord& record,
0123 const std::vector<std::string>& dumpRequest,
0124 std::ostream* dumpStream) {
0125 host.ifRecordChanges<RecordType>(record, [this, &host, &dumpRequest, &dumpStream](auto const& rec) {
0126 std::apply([&host, &rec, &dumpRequest, &dumpStream](
0127 auto&&... item) { ((item.setupHcalDbService(host, rec, dumpRequest, dumpStream)), ...); },
0128 tokens_);
0129 });
0130 }
0131
0132 private:
0133 std::tuple<ServiceTokenImpl<typename TokenHolders::Product,
0134 RecordType,
0135 TokenHolders::label,
0136 typename TokenHolders::Effective>...>
0137 tokens_;
0138 };
0139
0140
0141 template <typename ProductT, typename RecordT>
0142 class TokenAndTopologyHolder {
0143 public:
0144 using Product = ProductT;
0145 using Record = RecordT;
0146
0147 TokenAndTopologyHolder() = default;
0148
0149 void setConsumes(edm::ESConsumesCollector&& cc, const edm::ESInputTag& tag) {
0150 token_ = cc.consumes(tag);
0151 topoToken_ = cc.consumes();
0152 }
0153
0154 const auto& token() const { return token_; }
0155
0156 const auto& topoToken() const { return topoToken_; }
0157
0158 private:
0159 edm::ESGetToken<ProductT, RecordT> token_;
0160 edm::ESGetToken<HcalTopology, HcalRecNumberingRecord> topoToken_;
0161 };
0162
0163 template <typename ProductType, typename RecordType, size_t IND1, size_t IND2>
0164 std::unique_ptr<ProductType> produceWithTopology(RecordType const& record) {
0165 const auto& tokenHolder = std::get<IND2>(std::get<IND1>(tokenHolders_));
0166 auto item = record.getTransientHandle(tokenHolder.token());
0167
0168 auto productWithTopology = std::make_unique<ProductType>(*item);
0169 const auto& topo = record.get(tokenHolder.topoToken());
0170 productWithTopology->setTopo(&topo);
0171
0172 return productWithTopology;
0173 }
0174
0175 template <size_t IND1, size_t IND2>
0176 void setupProduce(const char* label, const edm::ESInputTag& tag) {
0177 auto& holder = std::get<IND2>(std::get<IND1>(tokenHolders_));
0178
0179 using HolderT = typename std::remove_reference<decltype(holder)>::type;
0180 using ProductT = typename HolderT::Product;
0181 using RecordT = typename HolderT::Record;
0182
0183 holder.setConsumes(
0184 setWhatProduced(
0185 this, &HcalDbProducer::produceWithTopology<ProductT, RecordT, IND1, IND2>, edm::es::Label(label)),
0186 tag);
0187 }
0188
0189 template <size_t IND1, size_t... IND2s>
0190 void setupProduceAllImpl(const char* label, const edm::ESInputTag& tag, std::index_sequence<IND2s...>) {
0191 ((setupProduce<IND1, IND2s>(label, tag)), ...);
0192 }
0193
0194 template <size_t IND1>
0195 void setupProduceAll(const char* label, const edm::ESInputTag& tag) {
0196 setupProduceAllImpl<IND1>(
0197 label, tag, std::make_index_sequence<std::tuple_size_v<std::tuple_element_t<IND1, decltype(tokenHolders_)>>>{});
0198 }
0199
0200
0201 edm::ReusableObjectHolder<HostType> holder_;
0202
0203
0204 constexpr static const char kWithTopoEff[] = "withTopoEff";
0205 constexpr static const char kWithTopo[] = "withTopo";
0206 constexpr static const char kEmpty[] = "";
0207 std::tuple<TokensForServiceHolder<HcalPedestalWidthsRcd,
0208 ServiceToken<HcalPedestalWidths, kWithTopoEff, std::true_type>,
0209 ServiceToken<HcalPedestalWidths, kWithTopo>>,
0210 TokensForServiceHolder<HcalPedestalsRcd,
0211 ServiceToken<HcalPedestals, kWithTopoEff, std::true_type>,
0212 ServiceToken<HcalPedestals, kWithTopo>>,
0213 TokensForServiceHolder<HcalRecoParamsRcd, ServiceToken<HcalRecoParams, kWithTopo>>,
0214 TokensForServiceHolder<HcalMCParamsRcd, ServiceToken<HcalMCParams, kWithTopo>>,
0215 TokensForServiceHolder<HcalLutMetadataRcd, ServiceToken<HcalLutMetadata, kWithTopo>>,
0216 TokensForServiceHolder<HcalTPParametersRcd, ServiceToken<HcalTPParameters, kEmpty>>,
0217 TokensForServiceHolder<HcalTPChannelParametersRcd, ServiceToken<HcalTPChannelParameters, kWithTopo>>,
0218 TokensForServiceHolder<HcalSiPMCharacteristicsRcd, ServiceToken<HcalSiPMCharacteristics, kEmpty>>,
0219 TokensForServiceHolder<HcalSiPMParametersRcd, ServiceToken<HcalSiPMParameters, kWithTopo>>,
0220 TokensForServiceHolder<HcalFrontEndMapRcd, ServiceToken<HcalFrontEndMap, kEmpty>>,
0221 TokensForServiceHolder<HcalElectronicsMapRcd, ServiceToken<HcalElectronicsMap, kEmpty>>,
0222 TokensForServiceHolder<HcalL1TriggerObjectsRcd, ServiceToken<HcalL1TriggerObjects, kWithTopo>>,
0223 TokensForServiceHolder<HcalZSThresholdsRcd, ServiceToken<HcalZSThresholds, kWithTopo>>,
0224 TokensForServiceHolder<HcalChannelQualityRcd, ServiceToken<HcalChannelQuality, kWithTopo>>,
0225 TokensForServiceHolder<HcalGainWidthsRcd, ServiceToken<HcalGainWidths, kWithTopo>>,
0226 TokensForServiceHolder<HcalQIETypesRcd, ServiceToken<HcalQIETypes, kWithTopo>>,
0227 TokensForServiceHolder<HcalQIEDataRcd, ServiceToken<HcalQIEData, kWithTopo>>,
0228 TokensForServiceHolder<HcalTimeCorrsRcd, ServiceToken<HcalTimeCorrs, kWithTopo>>,
0229 TokensForServiceHolder<HcalPFCorrsRcd, ServiceToken<HcalPFCorrs, kWithTopo>>,
0230 TokensForServiceHolder<HcalLUTCorrsRcd, ServiceToken<HcalLUTCorrs, kWithTopo>>,
0231 TokensForServiceHolder<HcalGainsRcd, ServiceToken<HcalGains, kWithTopo>>,
0232 TokensForServiceHolder<HcalRespCorrsRcd, ServiceToken<HcalRespCorrs, kWithTopo>>>
0233 tokensForService_;
0234
0235
0236 std::tuple<
0237
0238 std::tuple<TokenAndTopologyHolder<HcalPedestals, HcalPedestalsRcd>,
0239 TokenAndTopologyHolder<HcalPedestalWidths, HcalPedestalWidthsRcd>,
0240 TokenAndTopologyHolder<HcalGains, HcalGainsRcd>,
0241 TokenAndTopologyHolder<HcalGainWidths, HcalGainWidthsRcd>,
0242 TokenAndTopologyHolder<HcalQIEData, HcalQIEDataRcd>,
0243 TokenAndTopologyHolder<HcalQIETypes, HcalQIETypesRcd>,
0244 TokenAndTopologyHolder<HcalChannelQuality, HcalChannelQualityRcd>,
0245 TokenAndTopologyHolder<HcalZSThresholds, HcalZSThresholdsRcd>,
0246 TokenAndTopologyHolder<HcalRespCorrs, HcalRespCorrsRcd>,
0247 TokenAndTopologyHolder<HcalL1TriggerObjects, HcalL1TriggerObjectsRcd>,
0248 TokenAndTopologyHolder<HcalTimeCorrs, HcalTimeCorrsRcd>,
0249 TokenAndTopologyHolder<HcalLUTCorrs, HcalLUTCorrsRcd>,
0250 TokenAndTopologyHolder<HcalPFCorrs, HcalPFCorrsRcd>,
0251 TokenAndTopologyHolder<HcalLutMetadata, HcalLutMetadataRcd>,
0252 TokenAndTopologyHolder<HcalSiPMParameters, HcalSiPMParametersRcd>,
0253 TokenAndTopologyHolder<HcalTPChannelParameters, HcalTPChannelParametersRcd>,
0254 TokenAndTopologyHolder<HcalMCParams, HcalMCParamsRcd>,
0255 TokenAndTopologyHolder<HcalRecoParams, HcalRecoParamsRcd>>,
0256
0257 std::tuple<TokenAndTopologyHolder<HcalPedestals, HcalPedestalsRcd>,
0258 TokenAndTopologyHolder<HcalPedestalWidths, HcalPedestalWidthsRcd>>>
0259 tokenHolders_;
0260
0261 std::vector<std::string> mDumpRequest;
0262 std::ostream* mDumpStream;
0263 };
0264
0265 HcalDbProducer::HcalDbProducer(const edm::ParameterSet& fConfig) : ESProducer(), mDumpRequest(), mDumpStream(nullptr) {
0266 auto cc = setWhatProduced(this);
0267 std::apply([&cc](auto&&... item) { ((item.setConsumes(cc)), ...); }, tokensForService_);
0268
0269
0270 setupProduceAll<0>("withTopo", edm::ESInputTag{});
0271
0272 setupProduceAll<1>("withTopoEff", edm::ESInputTag{"", "effective"});
0273
0274 mDumpRequest = fConfig.getUntrackedParameter<std::vector<std::string>>("dump", std::vector<std::string>());
0275 if (!mDumpRequest.empty()) {
0276 std::string otputFile = fConfig.getUntrackedParameter<std::string>("file", "");
0277 mDumpStream = otputFile.empty() ? &std::cout : new std::ofstream(otputFile.c_str());
0278 }
0279 }
0280
0281 HcalDbProducer::~HcalDbProducer() {
0282 if (mDumpStream != &std::cout)
0283 delete mDumpStream;
0284 }
0285
0286
0287 std::shared_ptr<HcalDbService> HcalDbProducer::produce(const HcalDbRecord& record) {
0288 auto host = holder_.makeOrGet([]() { return new HostType; });
0289
0290 std::apply([this, &host, &record](
0291 auto&&... item) { ((item.setupHcalDbService(*host, record, mDumpRequest, mDumpStream)), ...); },
0292 tokensForService_);
0293
0294 return host;
0295 }
0296
0297 DEFINE_FWK_EVENTSETUP_MODULE(HcalDbProducer);