7 #ifndef __EPICS_METRIC__
8 #define __EPICS_METRIC__ 1
10 #include <unordered_map>
11 #include "artdaq-utilities/Plugins/MetricMacros.hh"
12 #include "messagefacility/MessageLogger/MessageLogger.h"
16 #pragma clang diagnostic push
17 #pragma clang diagnostic ignored "-Wunused-parameter"
21 #pragma clang diagnostic pop
24 #include "TRACE/tracemf.h"
25 #define TRACE_NAME "EPICSMetric"
38 std::unordered_map<std::string, chid> channels_;
40 bool checkChannel_(std::string name)
42 if (!channels_.count(name))
45 ca_search(name.c_str(), &channel);
46 auto sts = ca_pend_io(5.0);
47 if (sts != ECA_NORMAL)
49 SEVCHK(ca_clear_channel(channel), NULL);
50 TLOG(TLVL_WARNING) <<
"Channel \"" << name <<
"\" not found!";
51 channels_[name] =
nullptr;
54 channels_[name] = channel;
57 return channels_[name] !=
nullptr;
60 std::string parseChannelName_(std::string prefix_, std::string name)
62 std::string caName = name;
63 if (name.find(
".")) caName = name.replace(name.find(
"."), 1,
"_");
65 caName = prefix_ +
"_" + caName;
66 TLOG(TLVL_DEBUG) <<
"Channel name is: \"" << caName <<
"\"";
76 explicit EpicsMetric(fhicl::ParameterSet
const& pset, std::string
const& app_name)
77 : MetricPlugin(pset, app_name), prefix_(pset.get<std::string>(
"channel_name_prefix",
"artdaq")), channels_() {}
79 virtual ~
EpicsMetric() { MetricPlugin::stopMetrics(); }
85 std::string
getLibName()
const override {
return "epics"; }
92 for (
auto channel : channels_)
94 SEVCHK(ca_clear_channel(channel.second), NULL);
114 void sendMetric_(
const std::string& name,
const std::string& value,
const std::string& unit)
override
117 std::string caName = parseChannelName_(prefix_, name);
119 std::string tmpValue = value +
" " + unit;
121 if (checkChannel_(caName))
124 if (tmpValue.size() > 40)
126 tmpValue = tmpValue.erase(40);
128 SEVCHK(ca_put(DBR_STRING, channels_[caName], tmpValue.c_str()), NULL);
129 SEVCHK(ca_flush_io(), NULL);
143 void sendMetric_(
const std::string& name,
const int& value,
const std::string& unit)
override
147 std::string caName = parseChannelName_(prefix_, name);
151 TLOG(TLVL_DEBUG) <<
"Not sure if I can send ChannelAccess Units...configure in db instead.";
154 if (checkChannel_(caName))
156 dbr_long_t val =
static_cast<dbr_long_t
>(value);
157 SEVCHK(ca_put(DBR_LONG, channels_[caName], &val), NULL);
158 SEVCHK(ca_flush_io(), NULL);
172 void sendMetric_(
const std::string& name,
const double& value,
const std::string& unit)
override
176 std::string caName = parseChannelName_(prefix_, name);
180 TLOG(TLVL_DEBUG) <<
"Not sure if I can send ChannelAccess Units...configure in db instead.";
183 if (checkChannel_(caName))
185 dbr_double_t val =
static_cast<dbr_double_t
>(value);
186 SEVCHK(ca_put(DBR_DOUBLE, channels_[caName], &val), NULL);
187 SEVCHK(ca_flush_io(), NULL);
201 void sendMetric_(
const std::string& name,
const float& value,
const std::string& unit)
override
205 std::string caName = parseChannelName_(prefix_, name);
209 TLOG(TLVL_DEBUG) <<
"Not sure if I can send ChannelAccess Units...configure in db instead.";
212 if (checkChannel_(caName))
214 dbr_float_t val =
static_cast<dbr_float_t
>(value);
215 SEVCHK(ca_put(DBR_FLOAT, channels_[caName], &val), NULL);
216 SEVCHK(ca_flush_io(), NULL);
230 void sendMetric_(
const std::string& name,
const unsigned long int& value,
const std::string& unit)
override
234 std::string caName = parseChannelName_(prefix_, name);
238 TLOG(TLVL_DEBUG) <<
"Not sure if I can send ChannelAccess Units...configure in db instead.";
241 if (checkChannel_(caName))
243 dbr_ulong_t val =
static_cast<dbr_ulong_t
>(value);
244 SEVCHK(ca_put(DBR_LONG, channels_[caName], &val), NULL);
245 SEVCHK(ca_flush_io(), NULL);
253 #endif // End ifndef __EPICS_METRIC__
void sendMetric_(const std::string &name, const float &value, const std::string &unit) override
Send a float metric data point to ChannelAccess.
void sendMetric_(const std::string &name, const unsigned long int &value, const std::string &unit) override
Send an unsigned integer metric data point to ChannelAccess.
An instance of the MetricPlugin class that sends metric data using the Channel Access protocol from E...
void stopMetrics_() override
Clears the registered ChannelAccess channels.
void startMetrics_() override
No initialization is needed to start sending metrics.
std::string getLibName() const override
Gets the unique library name of this plugin.
void sendMetric_(const std::string &name, const std::string &value, const std::string &unit) override
Send a string metric data point to ChannelAccess.
EpicsMetric(fhicl::ParameterSet const &pset, std::string const &app_name)
Construct an instance of the EpicsMetric plugin.
void sendMetric_(const std::string &name, const double &value, const std::string &unit) override
Send a double metric data point to ChannelAccess.
void sendMetric_(const std::string &name, const int &value, const std::string &unit) override
Send an integer metric data point to ChannelAccess.