Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2025-10-25 09:05:24

0001 
0002 // Copyright 2023, Jefferson Science Associates, LLC.
0003 // Subject to the terms in the LICENSE file found in the top-level directory.
0004 
0005 #pragma once
0006 
0007 #include <JANA/JFactory.h>
0008 #include <JANA/Components/JHasRunCallbacks.h>
0009 #include <JANA/Components/JLightweightOutput.h>
0010 #include <JANA/JVersion.h>
0011 #include <typeindex>
0012 
0013 #if JANA2_HAVE_PODIO
0014 #include "JANA/Components/JPodioOutput.h"
0015 #endif
0016 
0017 
0018 class JMultifactory : public JFactory {
0019 
0020 private:
0021     std::vector<OutputBase*> m_owned_outputs;
0022     std::map<std::pair<std::type_index, std::string>, OutputBase*> m_output_index;
0023 
0024 public:
0025     JMultifactory() {
0026         SetCallbackStyle(CallbackStyle::LegacyMode);
0027     }
0028     virtual ~JMultifactory() {
0029         for (auto* output : m_owned_outputs) {
0030             delete output;
0031         }
0032     }
0033 
0034     // This is a hack for EICrecon.
0035     // Goes away once EICrecon migrates JOmniFactory onto JFactory
0036     using JFactory::ChangeRun;
0037     virtual void ChangeRun(int32_t) {};
0038 
0039 
0040     // IMPLEMENTED BY USERS
0041 
0042     void Init() override {}
0043     void BeginRun(const std::shared_ptr<const JEvent>&) override {}
0044     void Process(const std::shared_ptr<const JEvent>&) override {}
0045     void EndRun() override {}
0046     void Finish() override {}
0047 
0048 
0049     // CALLED BY USERS
0050 
0051     template <typename T>
0052     void DeclareOutput(std::string short_name, bool owns_data=true);
0053 
0054     template <typename T>
0055     void SetData(std::string short_name, std::vector<T*> data);
0056 
0057 #if JANA2_HAVE_PODIO
0058 
0059     template <typename T>
0060     void DeclarePodioOutput(std::string unique_name, bool owns_data=true);
0061 
0062     template <typename T>
0063     void SetCollection(std::string unique_name, typename T::collection_type&& collection);
0064 
0065     template <typename T>
0066     void SetCollection(std::string unique_name, std::unique_ptr<typename T::collection_type> collection);
0067 
0068 #endif
0069 };
0070 
0071 
0072 
0073 template <typename T>
0074 void JMultifactory::DeclareOutput(std::string short_name, bool owns_data) {
0075 
0076     auto* output = new jana::components::Output<T>(this);
0077     output->SetShortName(short_name);
0078     output->SetNotOwnerFlag(!owns_data);
0079     m_owned_outputs.push_back(output);
0080     m_output_index[{std::type_index(typeid(T)), short_name}] = output;
0081 }
0082 
0083 template <typename T>
0084 void JMultifactory::SetData(std::string short_name, std::vector<T*> data) {
0085     auto it = m_output_index.find({std::type_index(typeid(T)), short_name});
0086     if (it == m_output_index.end()) {
0087         auto ex = JException("Couldn't find output with short_name '%s'. Hint: Did you call DeclareOutput() in the constructor?", short_name.c_str());
0088         ex.function_name = "JMultifactory::SetData";
0089         ex.type_name = m_type_name;
0090         ex.instance_name = m_prefix;
0091         ex.plugin_name = m_plugin_name;
0092         throw ex;
0093     }
0094     auto* typed_output = dynamic_cast<jana::components::Output<T>*>(it->second);
0095     if (typed_output == nullptr) {
0096         auto ex = JException("OutputBase not castable to Output<T>. Hint: Did you mean to use SetCollection?");
0097         ex.function_name = "JMultifactory::SetData";
0098         ex.type_name = m_type_name;
0099         ex.instance_name = m_prefix;
0100         ex.plugin_name = m_plugin_name;
0101         throw ex;
0102     }
0103     (*typed_output)() = std::move(data);
0104 }
0105 
0106 
0107 #if JANA2_HAVE_PODIO
0108 
0109 template <typename T>
0110 void JMultifactory::DeclarePodioOutput(std::string unique_name, bool owns_data) {
0111     auto* output = new jana::components::PodioOutput<T>(this);
0112     output->SetUniqueName(unique_name);
0113     output->SetSubsetCollection(!owns_data);
0114     m_owned_outputs.push_back(output);
0115     m_output_index[{std::type_index(typeid(T)), unique_name}] = output;
0116 }
0117 
0118 template <typename T>
0119 void JMultifactory::SetCollection(std::string unique_name, typename T::collection_type&& collection) {
0120     auto it = m_output_index.find({std::type_index(typeid(T)), unique_name});
0121     if (it == m_output_index.end()) {
0122         auto ex = JException("Couldn't find output with short_name '%s'. Hint: Did you call DeclareOutput() in the constructor?", unique_name.c_str());
0123         ex.function_name = "JMultifactory::SetData";
0124         ex.type_name = m_type_name;
0125         ex.instance_name = m_prefix;
0126         ex.plugin_name = m_plugin_name;
0127         throw ex;
0128     }
0129     auto* typed_output = dynamic_cast<jana::components::PodioOutput<T>*>(it->second);
0130     if (typed_output == nullptr) {
0131         auto ex = JException("Databundle not castable to JLightweightDatabundleT. Hint: Did you mean to use SetCollection?");
0132         ex.function_name = "JMultifactory::SetData";
0133         ex.type_name = m_type_name;
0134         ex.instance_name = m_prefix;
0135         ex.plugin_name = m_plugin_name;
0136         throw ex;
0137     }
0138     *((*typed_output)()) = std::move(collection);
0139 }
0140 
0141 template <typename T>
0142 void JMultifactory::SetCollection(std::string unique_name, std::unique_ptr<typename T::collection_type> collection) {
0143     auto it = m_output_index.find({std::type_index(typeid(T)), unique_name});
0144     if (it == m_output_index.end()) {
0145         auto ex = JException("Couldn't find output with short_name '%s'. Hint: Did you call DeclareOutput() in the constructor?", unique_name.c_str());
0146         ex.function_name = "JMultifactory::SetData";
0147         ex.type_name = m_type_name;
0148         ex.instance_name = m_prefix;
0149         ex.plugin_name = m_plugin_name;
0150         throw ex;
0151     }
0152     auto* typed_output = dynamic_cast<jana::components::PodioOutput<T>*>(it->second);
0153     if (typed_output == nullptr) {
0154         auto ex = JException("Databundle not castable to JLightweightDatabundleT. Hint: Did you mean to use SetCollection?");
0155         ex.function_name = "JMultifactory::SetData";
0156         ex.type_name = m_type_name;
0157         ex.instance_name = m_prefix;
0158         ex.plugin_name = m_plugin_name;
0159         throw ex;
0160     }
0161     *((*typed_output)()) = std::move(*collection);
0162 }
0163 
0164 #endif // JANA2_HAVE_PODIO
0165 
0166 
0167 
0168