ATLAS Offline Software
Loading...
Searching...
No Matches
TileDCSCondAlg.cxx
Go to the documentation of this file.
1//Dear emacs, this is -*- c++ -*-
2/*
3 Copyright (C) 2002-2025 CERN for the benefit of the ATLAS collaboration
4*/
5
6// Tile includes
7#include "TileDCSCondAlg.h"
10
11// Athena includes
16
17#include "CoralBase/Attribute.h"
18
19#include <cmath>
20#include <fstream>
21
22TileDCSCondAlg::TileDCSCondAlg(const std::string& name, ISvcLocator* pSvcLocator) :
23 AthCondAlgorithm(name, pSvcLocator),
24 m_cabling(nullptr)
25{
26
27}
28
29
31
32 ATH_MSG_DEBUG( "In initialize()" );
33
34 ATH_CHECK( m_hvKey.initialize(m_readHV) );
35
36 ATH_CHECK( m_hvSetKey.initialize(m_readHVSet) );
37 ATH_CHECK( m_emScaleKey.initialize(!m_readHVSet) );
38
39 ATH_CHECK( m_statesKey.initialize(m_readStates) );
40
41
42 ATH_MSG_INFO( "Will read the following folders: "
43 << ((m_readHV) ? m_hvKey.key() : "") << " "
44 << ((m_readHVSet) ? m_hvSetKey.key() : "") << " "
45 << ((m_readStates) ? m_statesKey.key() : ""));
46
47 //=== get TileCablingSvc
48 ATH_CHECK( m_cablingSvc.retrieve() );
49
50 //=== cache pointers to cabling helpers
51 m_cabling = m_cablingSvc->cablingService();
52
53 if (!m_cabling) {
54 ATH_MSG_ERROR( "Pointer to TileCablingService is zero: " << m_cabling);
55 return StatusCode::FAILURE;
56 }
57
58 std::map<TileModuleType, unsigned int> roses{{LONG_BARREL, 2}, {EXTENDED_BARREL, 3}};
59
60 for (TileModuleType moduleType : {LONG_BARREL, EXTENDED_BARREL}) {
61
62 unsigned int ros = roses[moduleType];
63 unsigned int channel = 0;
64
65 for (; channel < TileCalibUtils::MAX_CHAN; ++channel) {
66 int pmt = m_cabling->channel2hole(ros, channel);
67 m_isChannelUsed[moduleType][channel] = (pmt > 0); // positive pmt - means channel is connected
68
69 if (moduleType == EXTENDED_BARREL) {
72 }
73
74 pmt = std::abs(pmt);
75 m_channel2pmt[moduleType][channel] = pmt - 1;
76 m_pmt2channel[moduleType][pmt - 1] = channel; // note - pmt-1 is used as index
77 }
78
79 for (; channel < 68; ++channel) {
80 m_channel2pmt[moduleType][channel] = channel;
81 m_pmt2channel[moduleType][channel] = channel;
82 }
83
84 }
85
86 // description of EBA15 and EBC18 channel 0-3 do not exist, channel 18,19 used
93 // description of EB with special C10 - channel 4 (pmt 5) is not used
95
96 if (m_readHVSet) {
97 // read special deltas for few unstable PMTs
98 readBadHV("BadHVChannels.dat");
99 if (readConfig(m_dcsChHvSetInCool, "Drawer", m_rosDrawerHVSet)) return StatusCode::FAILURE;
100 }
101
102 if (readConfig(m_dcsChStatesInCool, "_LVPS_", m_rosDrawerStates)) return StatusCode::FAILURE;
103 if (readConfig(m_dcsChHvInCool, "Drawer", m_rosDrawerHV)) return StatusCode::FAILURE;
104
105 ATH_CHECK( m_dcsStateKey.initialize() );
106
107 return StatusCode::SUCCESS;
108}
109
110
111StatusCode TileDCSCondAlg::execute(const EventContext& ctx) const {
112
114
115 if (dcsState.isValid()) {
116 ATH_MSG_DEBUG("Found valid TileDCSState: " << dcsState.key());
117 return StatusCode::SUCCESS;
118 }
119
120 std::unique_ptr<TileDCSState> dcsStateData = std::make_unique<TileDCSState>();
121 dcsStateData->setGoodDrawer(m_goodDrawer.value());
122 dcsStateData->setWarningDrawer(m_warningDrawer.value());
123
124 if (m_readHV) {
125
127 dcsState.addDependency(hv);
128 for (const CondAttrListCollection::ChanAttrListPair& chanAttrListPair : **hv) {
129
130 const CondAttrListCollection::ChanNum coolChannel = chanAttrListPair.first;
131
132 const std::pair<int, int> rosDrawerPair = m_rosDrawerHV.at(coolChannel);
133 unsigned int ros = rosDrawerPair.first;
134 unsigned int drawer = rosDrawerPair.second;
135
136 ATH_MSG_VERBOSE( "ros: " << ros
137 << ", drawer: " << drawer
138 << ", COOL channel: " << coolChannel
139 << ", payload: " << chanAttrListPair.second);
140
141 int moduleType = (ros > 2) ? EXTENDED_BARREL : LONG_BARREL;
142 int pmt0 = 0; // runs over paylod parameters
143 for (const coral::Attribute& attribute : chanAttrListPair.second) {
144 int channel = m_pmt2channel[moduleType][pmt0];
145 dcsStateData->setChannelHV(ros, drawer, channel, attribute.data<float>());
146 ATH_MSG_VERBOSE( "HV[" << pmt0 << "] = " << attribute.data<float>() );
147 ++pmt0;
148 }
149
150 }
151 }
152
153
154 if (m_readHVSet) {
155
157 dcsState.addDependency(hvSet);
158 for (const CondAttrListCollection::ChanAttrListPair& chanAttrListPair : **hvSet) {
159
160 const CondAttrListCollection::ChanNum coolChannel = chanAttrListPair.first;
161
162 const std::pair<int, int> rosDrawerPair = m_rosDrawerHVSet.at(coolChannel);
163 unsigned int ros = rosDrawerPair.first;
164 unsigned int drawer = rosDrawerPair.second;
165
166 ATH_MSG_VERBOSE( "ros: " << ros
167 << ", drawer: " << drawer
168 << ", COOL channel: " << coolChannel
169 << ", payload: " << chanAttrListPair.second);
170
171 int moduleType = (ros > 2) ? EXTENDED_BARREL : LONG_BARREL;
172 int pmt0 = 0; // runs over paylod parameters
173 for (const coral::Attribute& attribute : chanAttrListPair.second) {
174 int channel = m_pmt2channel[moduleType][pmt0];
175 dcsStateData->setChannelHVSet(ros, drawer, channel, attribute.data<float>());
176 ATH_MSG_VERBOSE( "HVSET[" << pmt0 << "] = " << attribute.data<float>() );
177 ++pmt0;
178 }
179
180 }
181 } else {
182 ATH_CHECK( fillReferenceHV(*dcsStateData, dcsState, ctx) );
183
184 }
185
186
187 if (m_readStates) {
188
190 dcsState.addDependency(states);
191 for (const CondAttrListCollection::ChanAttrListPair& chanAttrListPair : **states) {
192
193 CondAttrListCollection::ChanNum coolChannel = chanAttrListPair.first;
194
195 std::pair<int, int> rosDrawerPair = m_rosDrawerStates.at(coolChannel);
196 unsigned int ros = rosDrawerPair.first;
197 unsigned int drawer = rosDrawerPair.second;
198
199 ATH_MSG_VERBOSE( "ros: " << ros
200 << ", drawer: " << drawer
201 << ", COOL channel: " << coolChannel
202 << ", payload: " << chanAttrListPair.second);
203
204 for (const coral::Attribute& attribute : chanAttrListPair.second) {
205 dcsStateData->setDrawerStates(ros, drawer, attribute.data<int>());
206 ATH_MSG_VERBOSE( "STATES = " << attribute.data<int>() );
207 }
208
209 }
210 }
211
212
213 for (unsigned int ros = 1; ros < TileCalibUtils::MAX_ROS; ++ros) {
214 for (unsigned int drawer = 0; drawer < TileCalibUtils::MAX_DRAWER; ++drawer) {
215
216 TileDCSState::TileDCSStatus drawerStatus = dcsStateData->getDCSStatus(ros, drawer);
217
218 int moduleType = (ros > 2) ? EXTENDED_BARREL : LONG_BARREL;
219 int specialModuleType(moduleType);
220 if (moduleType == EXTENDED_BARREL) {
221 if ((ros == 3 && drawer == 14) || (ros == 4 && drawer == 17)) {
222 specialModuleType = EXTENDED_BARREL_NO_D4; // EBA15 EBC18
223 } else if (!m_cabling->C10_connected(drawer)) {
224 specialModuleType = EXTENDED_BARREL_SPECIAL_C10; // EB modules with special C10
225 }
226 }
227
228 for (unsigned int channel = 0; channel < TileCalibUtils::MAX_CHAN; ++channel) {
229 if (m_isChannelUsed[specialModuleType][channel]) {
230
232
233 float hvSet(dcsStateData->getChannelHVSet(ros, drawer, channel));
234 float hv(dcsStateData->getChannelHV(ros, drawer, channel));
235
236 // ignore zero "set" and negative "measured" HV, set status to unknown
237 if (hvSet >= 1.0 && hv >= 0.0 // HV can't be negative
238 && hvSet < 999.9 && hv < 999.9) { // HV can't be greater 930V
239
240 std::map<int, std::pair<float, float>>::const_iterator itr =
241 m_knownBadHV.find(getChannelKey(ros, drawer, channel));
242
243 if (itr != m_knownBadHV.end()) { // known unstable PMTs
244
245 float hvGap = (m_readHVSet) ? // take into account offset if HVSET is used
246 std::fabs(hvSet + itr->second.second - hv) : std::fabs(hvSet - hv);
247
248 if (hvGap <= m_goodHVLimit) channelHVStatus = TileDCSState::OK_KNOWNBADPMT;
249 else if (hvGap <= m_warningHVLimit) channelHVStatus = TileDCSState::WARNING_KNOWNBADPMT;
250 else channelHVStatus = TileDCSState::ALERT_KNOWNBADPMT;
251 } else {
252 float hvGap = std::fabs(hvSet - hv);
253 if (hvGap <= m_goodHVLimit) channelHVStatus = TileDCSState::OK;
254 else if (hvGap <= m_warningHVLimit) channelHVStatus = TileDCSState::WARNING;
255 else channelHVStatus = TileDCSState::ALERT;
256 }
257
258 }
259
260 dcsStateData->setDCSHVStatus(ros, drawer, channel, channelHVStatus);
261
262 if (drawerStatus > TileDCSState::OK && !m_readHVSet) {
263 dcsStateData->setDCSStatus(ros, drawer, channel, drawerStatus);
264 } else {
265 dcsStateData->setDCSStatus(ros, drawer, channel, std::max(drawerStatus, channelHVStatus));
266 }
267
268 } else {
269 dcsStateData->setDCSHVStatus(ros, drawer, channel, TileDCSState::NON_EXISTING);
270 dcsStateData->setDCSStatus(ros, drawer, channel, TileDCSState::NON_EXISTING);
271 }
272 }
273
274
275 if (msgLvl(MSG::VERBOSE)) {
276 msg(MSG::VERBOSE) << "Module = " << TileCalibUtils::getDrawerString(ros, drawer)
277 << " Status = " << drawerStatus << endmsg;
278
279 std::string ignored = ((drawerStatus > TileDCSState::OK && !m_readHVSet) ? " ignored" : "");
280
281 for (unsigned int channel = 0; channel < TileCalibUtils::MAX_CHAN; ++channel) {
282 int pmt0 = m_channel2pmt[moduleType][channel];
283 TileDCSState::TileDCSStatus status = dcsStateData->getDCSHVStatus(ros, drawer, channel);
284 msg(MSG::VERBOSE) << "Module = " << TileCalibUtils::getDrawerString(ros, drawer)
285 << " channel = " << channel
286 << " pmt = " << pmt0 + 1
287 << " HV = " << dcsStateData->getChannelHV(ros, drawer, channel)
288 << " HVSET = " << dcsStateData->getChannelHVSet(ros, drawer, channel)
289 << " Status = " << status
290 << ignored << endmsg;
291 }
292 }
293
294 }
295 }
296
297 // Define validity of the output cond object
298 if(dcsState.record(std::move(dcsStateData)).isFailure()) {
299
300 ATH_MSG_ERROR("Could not record TileDCSState object with "
301 << dcsState.key()
302 << " with EventRange " << dcsState.getRange()
303 << " into Conditions Store");
304
305 return StatusCode::FAILURE;
306 } else {
307
308 ATH_MSG_VERBOSE("Recorded TileDCSState object with "
309 << dcsState.key()
310 << " with EventRange " << dcsState.getRange()
311 << " into Conditions Store");
312 }
313
314 return StatusCode::SUCCESS;
315
316}
317
318
319
320//_____________________________________________________________________________
321int TileDCSCondAlg::readConfig(const std::string& fileName,
322 const std::string& subStr,
323 std::vector<std::pair<int, int>>& rosDrawer) {
324
325 std::string fullFileName = PathResolver::find_file(fileName, "DATAPATH");
326 std::ifstream file(fullFileName.c_str());
327 if (!file.is_open()) {
328 ATH_MSG_ERROR( "Can't find " << fileName);
329 return 2;
330 } else {
331 ATH_MSG_DEBUG( "Reading file " << fullFileName);
332 }
333
334 rosDrawer.resize(257, std::make_pair<int, int>(0xFFFF, 0xFFFF));
335
336 std::string compName[5] = { "XXX", "ATLTILLV01", "ATLTILLV02", "ATLTILLV00", "ATLTILLV03" };
337
338 unsigned int ind, ros, module;
339 std::string s, line;
340 size_t pos;
341
342 while (true) {
343
344 file >> s >> ind >> line;
345
346 if (file.eof() || file.fail()) break;
347 if (ind > 1000000) break;
348
349 for (ros = 1; ros < TileCalibUtils::MAX_ROS; ++ros) {
350 pos = line.find(compName[ros]);
351 if (pos != std::string::npos) break;
352 }
353
354 if (ros == TileCalibUtils::MAX_ROS) {
355 msg(MSG::WARNING) << "File " << fileName << " Wrong computer name in " << line << endmsg;
356 continue;
357 }
358
359 pos = line.find(subStr);
360 if (pos == std::string::npos) {
361 ATH_MSG_WARNING( "File " << fileName << " Word " << subStr << " not found in " << line);
362 continue;
363 }
364
365 module = atoi(&line[pos + subStr.size()]);
366 if (module < 1 || module > TileCalibUtils::MAX_DRAWER) {
367 ATH_MSG_WARNING( "File " << fileName << " Wrong module number in " << line);
368 continue;
369 }
370
371 ATH_MSG_VERBOSE("Module = " << TileCalibUtils::getDrawerString(ros, module - 1) << " ind = " << ind);
372
373 if (rosDrawer.size() <= ind) {
374 rosDrawer.resize(ind + 1, std::make_pair<int, int> (0xFFFF, 0xFFFF));
375 }
376
377 rosDrawer[ind] = std::make_pair<int, int>(ros, (module - 1));
378
379 }
380
381 file.close();
382
383 return 0;
384}
385
386//_____________________________________________________________________________
387int TileDCSCondAlg::readBadHV(const std::string& fileName) {
388
389 std::string fullFileName = PathResolver::find_file(fileName, "DATAPATH");
390 std::ifstream file(fullFileName.c_str());
391 if (!file.is_open()) {
392 ATH_MSG_WARNING( "Can't find " << fileName);
393 return 1;
394 } else {
395 ATH_MSG_DEBUG("Reading file " << fullFileName);
396 }
397
398 std::string partName[5] = { "AUX", "LBA", "LBC", "EBA", "EBC" };
399
400 unsigned int ros, module, pmt;
401 float delta, offset;
402 char ll[256];
403 std::string line;
404 size_t pos = 0;
405
406 while (true) {
407
408 file.getline(ll, sizeof(ll));
409
410 if (file.eof() || file.fail()) break;
411
412 line = std::string(ll);
413
414 for (ros = 1; ros < TileCalibUtils::MAX_ROS; ++ros) {
415 pos = line.find(partName[ros]);
416 if (pos != std::string::npos) break;
417 }
418 if (ros == TileCalibUtils::MAX_ROS) {
419 ATH_MSG_WARNING( "File " << fileName << " Partition name not found in " << line);
420 continue;
421 }
422
423 module = atoi(&line[pos + 3]);
424 if (module < 1 || module > TileCalibUtils::MAX_DRAWER) {
425 ATH_MSG_WARNING( "File " << fileName << " Wrong module number in " << line);
426 continue;
427 }
428
429 pos = line.find("PMT number");
430 if (pos == std::string::npos) {
431 ATH_MSG_WARNING( "File " << fileName << " Word 'PMT number' not found in " << line);
432 continue;
433 }
434
435 pmt = atoi(&line[pos + 10]);
436 if (pmt < 1 || pmt > TileCalibUtils::MAX_CHAN) {
437 ATH_MSG_WARNING( "File " << fileName << " Wrong pmt number in " << line);
438 continue;
439 }
440
441 pos = line.find("Step Value is");
442 if (pos == std::string::npos) {
443 ATH_MSG_WARNING( "File " << fileName << " Word 'Step Value is' not found in " << line);
444 continue;
445 }
446
447 delta = atof(&line[pos + 13]);
448 if (delta <= 0.0 || delta > 1000.0) {
449 ATH_MSG_WARNING( "File " << fileName << " Wrong delta number in " << line);
450 continue;
451 }
452
453 pos = line.find("Offset is:");
454 if (pos == std::string::npos) {
455 ATH_MSG_WARNING( "File " << fileName << " Word 'Offset is:' not found in " << line);
456 continue;
457 }
458
459 offset = atof(&line[pos + 10]);
460 if (offset < -1000.0 || offset > 1000.0) {
461 ATH_MSG_WARNING( "File " << fileName << " Wrong offset number in " << line);
462 continue;
463 }
464
465 ATH_MSG_WARNING( "Module = " << TileCalibUtils::getDrawerString(ros, module - 1)
466 << " pmt = " << pmt
467 << " delta = " << delta
468 << " offset = " << offset);
469
470 int moduleType = (ros > 2) ? EXTENDED_BARREL : LONG_BARREL;
471 int channel = m_pmt2channel[moduleType][pmt - 1];
472 m_knownBadHV[getChannelKey(ros, module - 1, channel)] = std::make_pair(delta, offset);
473
474 }
475
476 file.close();
477
478 return 0;
479}
480
483 const EventContext& ctx) const {
484
486 wh.addDependency(emScale);
487
488 float laserReferenceHV = -5.;
489 float cesReferenceHV = -5.;
490
491 for (unsigned int ros = 1; ros < TileCalibUtils::MAX_ROS; ++ros) {
492 int moduleType = (ros > 2) ? EXTENDED_BARREL : LONG_BARREL;
493
494 for (unsigned int drawer = 0; drawer < TileCalibUtils::MAX_DRAWER; ++drawer) {
495 unsigned int drawerIdx = TileCalibUtils::getDrawerIdx(ros, drawer);
496
497 for (unsigned int channel = 0; channel < TileCalibUtils::MAX_CHAN; ++channel) {
498 int pmt0 = m_channel2pmt[moduleType][channel];
499
500 cesReferenceHV = emScale->getCesiumReferenceHV(drawerIdx, channel);
501 laserReferenceHV = emScale->getLaserReferenceHV(drawerIdx, channel);
502
503 if (laserReferenceHV >= 0.) {
504 dcsState.setChannelHVSet(ros, drawer, channel, laserReferenceHV);
505 } else {
506 dcsState.setChannelHVSet(ros, drawer, channel, cesReferenceHV);
507 }
508
509 if (msgLvl(MSG::VERBOSE)) {
510 msg(MSG::VERBOSE) << "Module = " << TileCalibUtils::getDrawerString(ros, drawer)
511 << " channel = " << channel
512 << " pmt = " << pmt0 + 1
513 << " HVref = " << dcsState.getChannelHVSet(ros, drawer, channel);
514
515 if (laserReferenceHV >= 0.) {
516 msg(MSG::VERBOSE) << " Taken from Laser run (replace "
517 << cesReferenceHV << " cesium value)" << endmsg;
518 } else {
519 msg(MSG::VERBOSE) << endmsg;
520 }
521 }
522 }
523 }
524 }
525
526 return StatusCode::SUCCESS;
527}
528
529
531 return StatusCode::SUCCESS;
532}
#define endmsg
#define ATH_CHECK
Evaluate an expression and check for errors.
#define ATH_MSG_ERROR(x)
#define ATH_MSG_INFO(x)
#define ATH_MSG_VERBOSE(x)
#define ATH_MSG_WARNING(x)
#define ATH_MSG_DEBUG(x)
bool msgLvl(const MSG::Level lvl) const
Base class for conditions algorithms.
ChanAttrListMap::value_type ChanAttrListPair
static std::string find_file(const std::string &logical_file_name, const std::string &search_path)
const std::string & key() const
void addDependency(const EventIDRange &range)
const EventIDRange & getRange() const
StatusCode record(const EventIDRange &range, T *t)
record handle, with explicit range DEPRECATED
static const unsigned int MAX_ROS
Number of ROSs.
static std::string getDrawerString(unsigned int ros, unsigned int drawer)
Return the drawer name, e.g.
static const unsigned int MAX_DRAWER
Number of drawers in ROS 1-4.
static unsigned int getDrawerIdx(unsigned int ros, unsigned int drawer)
Returns a drawer hash.
static const unsigned int MAX_CHAN
Number of channels in drawer.
unsigned int getChannelKey(unsigned int ros, unsigned int drawer, unsigned int channel) const
@ brief Return Tile channel key used as index in internal caches @ ros Tile ROS in range [1....
Gaudi::Property< std::string > m_dcsChHvInCool
File name with mapping Tile DCS HV DB COOL channels to ROS and drawer.
bool m_isChannelUsed[4][NUMBER_OF_CHANNELS]
std::map< int, std::pair< float, float > > m_knownBadHV
Gaudi::Property< std::string > m_dcsChHvSetInCool
File name with mapping Tile DCS HVSET DB COOL channels to ROS and drawer.
int readBadHV(const std::string &fileName)
Read special deltas for few unstable PMTs.
SG::WriteCondHandleKey< TileDCSState > m_dcsStateKey
The name of TileDCSState object to produce and put into condition store.
Gaudi::Property< std::string > m_dcsChStatesInCool
File name with mapping Tile DCS STATES DB COOL channels to ROS and drawer.
std::vector< std::pair< int, int > > m_rosDrawerHV
int m_pmt2channel[2][NUMBER_OF_HVSET_CHANNELS]
Gaudi::Property< float > m_goodHVLimit
Tile DCS Status is OK if difference between measured and requested HV is below this limit.
Gaudi::Property< bool > m_readHVSet
Flag to control reading Tile DCS HVSET folder from DB.
std::vector< std::pair< int, int > > m_rosDrawerStates
virtual StatusCode initialize() override
Gaudi::Property< float > m_warningHVLimit
Mask channels with difference between measured and requested HV above this limit.
SG::ReadCondHandleKey< CondAttrListCollection > m_hvSetKey
The Tile DCS HVSET COOL folder name.
Gaudi::Property< std::vector< int > > m_warningDrawer
Status is WARNING if Tile DCS drawer states is like this.
Gaudi::Property< int > m_goodDrawer
Status is OK if Tile DCS drawer states is like this.
TileDCSCondAlg(const std::string &name, ISvcLocator *pSvcLocator)
SG::ReadCondHandleKey< CondAttrListCollection > m_hvKey
The Tile DCS HV COOL folder name.
const TileCablingService * m_cabling
virtual StatusCode execute(const EventContext &ctx) const override
int m_channel2pmt[2][NUMBER_OF_HVSET_CHANNELS]
Gaudi::Property< bool > m_readHV
Flag to control reading Tile DCS HV folder from DB.
SG::ReadCondHandleKey< CondAttrListCollection > m_statesKey
The Tile DCS STATES COOL folder name.
std::vector< std::pair< int, int > > m_rosDrawerHVSet
ServiceHandle< TileCablingSvc > m_cablingSvc
Name of Tile cabling service.
Gaudi::Property< bool > m_readStates
Flag to control reading Tile DCS STATES folder from DB.
virtual StatusCode finalize() override
int readConfig(const std::string &fileName, const std::string &subStr, std::vector< std::pair< int, int > > &rosDrawer)
Read mapping of DB COOL channels into Tile ROS and drawer pairs.
StatusCode fillReferenceHV(TileDCSState &dcsState, SG::WriteCondHandle< TileDCSState > &wh, const EventContext &ctx) const
Store reference HV from Tile CES or Laser DB folder in TileDCSState.
SG::ReadCondHandleKey< TileEMScale > m_emScaleKey
The name of TileEMScale object to get reference HV from Cesium or Laser folder.
Condition object to keep Tile DCS status from DB.
float getChannelHVSet(unsigned int ros, unsigned int drawer, unsigned int channel) const
Return requested HV reported by DCS for given Tile channel.
TileDCSStatus
Describes Tile DCS status.
void setChannelHVSet(unsigned int ros, unsigned int drawer, unsigned int channel, float hvSet)
Store requested HV reported by DCS for given Tile channel.
TFile * file