Project
Loading...
Searching...
No Matches
Configuration.cxx
Go to the documentation of this file.
1// Copyright 2019-2020 CERN and copyright holders of ALICE O2.
2// See https://alice-o2.web.cern.ch/copyright for details of the copyright holders.
3// All rights not expressly granted are reserved.
4//
5// This software is distributed under the terms of the GNU General Public
6// License v3 (GPL Version 3), copied verbatim in the file "COPYING".
7//
8// In applying this license CERN does not waive the privileges and immunities
9// granted to it by virtue of its status as an Intergovernmental Organization
10// or submit itself to any jurisdiction.
11
14
16#include "CCDB/CcdbApi.h"
18#include <sstream>
19#include <regex>
21#include <fairlogger/Logger.h>
22#include <iostream>
23
24using namespace o2::ctp;
25//
26const std::map<std::string, std::string> CTPInput::run2DetToRun3Det = {{"T", "FT0"}, {"V", "FV0"}, {"U", "FDD"}, {"E", "EMC"}, {"D", "EMC"}, {"H", "TRD"}, {"O", "TOF"}, {"P", "PHS"}, {"Z", "ZDC"}};
27const std::map<std::string, std::string> CTPConfiguration::detName2LTG = {{"FV0", "1"}, {"FT0", "2"}, {"FDD", "3"}, {"ITS", "4"}, {"TOF", "5"}, {"MFT", "6"}, {"TPC", "7"}, {"MCH", "8"}, {"MID", "9"}, {"TST", "10"}, {"TRD", "13"}, {"HMP", "14"}, {"ZDC", "15"}, {"PHS", "16"}, {"EMC", "17"}, {"CPV", "18"}};
28//
30{
31 bool isdet = det.getID() >= det.getNDetectors();
32 isdet |= det.getID() < 0;
33 if (isdet) {
34 LOG(error) << " Detector does not exist: " << det.getID();
35 return false;
36 }
37 return true;
38}
40{
41 for (auto& c : str) {
42 c = std::toupper(c);
43 }
44}
45bool CTPConfiguration::isNumber(const std::string& s)
46{
47 return !s.empty() && std::find_if(s.begin(),
48 s.end(), [](unsigned char c) { return !std::isdigit(c); }) == s.end();
49}
50//
51int BCMask::setBCmask(std::vector<std::string>& tokens)
52{
53 BCmask.reset();
54 name = tokens[1];
55 bool coded = tokens[2].find("L") != std::string::npos;
56 coded |= tokens[2].find("H") != std::string::npos;
57 std::cout << "coded:" << coded << std::endl;
58 if (coded) {
59 // jusko notation
60 std::string bcmaskstr = tokens[2];
61 size_t pos = 0;
62 size_t posnext = 0;
63 int bccur = 0;
64 while (bccur < 3564) {
65 // std::cout << "pos:" << pos << std::endl;
66 size_t posH = bcmaskstr.find('H', pos);
67 size_t posL = bcmaskstr.find('L', pos);
68 // std::cout << "H:" << posH << " L:" << posL << std::endl;
69 bool b = 1;
70 posnext = posH;
71 if (posL < posH) {
72 posnext = posL;
73 b = 0;
74 }
75 std::string bcsub = bcmaskstr.substr(pos, posnext - pos);
76 // std::cout << "bcsub:" << bcsub << " b:" << b << std::endl;
77 int bcrange = 0;
78 try {
79 bcrange = std::stoull(bcsub);
80 } catch (...) {
81 LOG(warning) << "problem in bcmask decoding H:" << posH << " posL:" << posL << " bcsub:" << bcsub;
82 return 1;
83 }
84 if (b) {
85 for (int bc = bccur; bc < bccur + bcrange; bc++) {
86 try {
87 BCmask.set(bc, 1);
88 } catch (...) {
89 LOG(warning) << "BC mask decoding to big bc:" << bc;
90 }
91 }
92 }
93 bccur += bcrange;
94 pos = posnext + 1;
95 // std::cout << "bccur:" << bccur << std::endl;
96 }
97 } else {
98 // list of integers
99 for (uint32_t i = 2; i < tokens.size(); i++) {
100 uint32_t bc;
101 try {
102 bc = std::stoull(tokens[i]);
103 } catch (...) {
104 LOG(info) << "mask syntax:" << i << ":" << tokens[i];
105 continue;
106 }
107 BCmask.set(bc, 1);
108 }
109 }
110 return 0;
111}
112void BCMask::printStream(std::ostream& stream) const
113{
114 stream << "CTP BC mask:" << name << ":" << mask;
115 stream << " # of active BC:" << BCmask.count() << std::endl;
116}
117//
118const std::set<std::string> CTPGenerator::Generators = {"bcd1m", "bcd2m", "bcd10", "bcd20", "rnd1m", "rnd2m", "rnd10", "rnd20"};
119void CTPGenerator::printStream(std::ostream& stream) const
120{
121 stream << "CTP generator:" << name << " frequency:" << frequency << std::endl;
122}
123//
124CTPInput::CTPInput(std::string& name, std::string& det, uint32_t index)
125{
126 this->name = name;
127 inputMask = (1ull << (index - 1));
128 detID = o2::detectors::DetID(det.c_str());
129}
130CTPInput::CTPInput(const char* name, const char* det, uint32_t index)
131{
132 this->name = std::string(name);
133 inputMask = (1ull << (index - 1));
135}
136void CTPInput::setRun3DetName(std::string& run2Name)
137{
138 std::string run3Name = CTPInput::run2DetToRun3Det.at(run2Name);
139 detID = o2::detectors::DetID(run3Name.c_str());
140}
141void CTPInput::printStream(std::ostream& stream) const
142{
143 stream << "CTP Input:" << name << " Detector:" << getInputDetName() << " Level:" << level << " Hardware mask:0x" << std::hex << inputMask << std::dec;
144 stream << " index:" << getIndex() << std::endl;
145}
146//
147std::uint64_t CTPDescriptor::getInputsMask() const
148{
149 uint64_t mask = 0;
150 for (const auto& inp : inputs) {
151 mask |= inp->inputMask;
152 }
153 return mask;
154}
155void CTPDescriptor::printStream(std::ostream& stream) const
156{
157 stream << "CTP Descriptor:" << name << " Inputs:";
158 for (const auto& inp : inputs) {
159 stream << inp->name << " ";
160 }
161 stream << std::endl;
162}
163//
164void CTPDetector::printStream(std::ostream& stream) const
165{
166 stream << "CTP Detector:" << getName() << " HBaccepted:" << HBaccepted;
167 stream << " Mode:" << mode << " FErst:" << ferst << std::endl;
168}
169
170void CTPCluster::printStream(std::ostream& stream) const
171{
172 stream << "CTP Cluster:" << name << " " << getClusterDetNames();
173 stream << " det mask:0b" << std::hex << maskCluster << " " << std::dec;
174 stream << " clust index:" << hwMask;
175 stream << std::endl;
176}
177void CTPClass::printStream(std::ostream& stream) const
178{
179 stream << "CTP Class:" << name << " Hardware mask:" << classMask << " Cluster index:" << clusterIndex << " Desc index:" << descriptorIndex;
180 stream << " Downscale:" << downScale;
181 stream << " BCM:";
182 for (const auto& bcm : BCClassMask) {
183 stream << bcm->name << " ";
184 }
185 if (descriptor != nullptr) {
186 stream << " Descriptor:" << descriptor->name;
187 }
188 if (cluster != nullptr) {
189 stream << " Cluster:" << cluster->name;
190 }
191 stream << std::endl;
192}
195int CTPConfiguration::addInput(std::string& inp, int clsindex, std::map<int, std::vector<int>>& descInputsIndex)
196{
197 LOG(info) << "adding input:" << inp;
198 CTPInput ctpinp;
199 std::string sinp = inp;
200 ;
201 if (inp[0] == '~') {
202 sinp = inp.substr(1, inp.size() - 1);
203 ctpinp.neg = 0;
204 }
205 if (inp[0] == 'b') { // BC downscale
206 ctpinp.level = "b";
207 ctpinp.name = inp;
208 } else if (inp[0] == 'r') { // randpm gen
209 ctpinp.level = "r";
210 ctpinp.name = inp;
211 } else if (isNumber(sinp)) { // inputs as number
212 int index = std::stoi(sinp);
214 ctpinp.inputMask = 1ull << (index - 1);
215 ctpinp.level = ctpinp.name[0];
216 if (ctpinp.neg == 0) {
217 ctpinp.name = "~" + ctpinp.name;
218 }
219 } else { // input as string or error
220 ctpinp.name = inp;
222 ctpinp.level = sinp[0];
223 ctpinp.inputMask = 1ull << (index - 1);
224 }
225 // add to desc
226 // check if already there
227 for (uint32_t i = 0; i < mInputs.size(); i++) {
228 if (mInputs[i].name == ctpinp.name) {
229 LOG(info) << "input found at:" << i;
230 descInputsIndex[clsindex].push_back(i);
231 return 0;
232 }
233 }
234 mInputs.push_back(ctpinp);
235 descInputsIndex[clsindex].push_back(mInputs.size() - 1);
236 LOG(info) << "input inderted at:" << mInputs.size() - 1;
237 return 0;
238}
239int CTPConfiguration::loadConfigurationRun3(const std::string& ctpconfiguration)
240{
241 LOG(info) << "Loading CTP configuration.";
242 std::map<int, std::vector<int>> clsDescIndex;
244 mConfigString = ctpconfiguration;
245 std::istringstream iss(ctpconfiguration);
246 int ret = 0;
247 int level = START;
248 std::string line;
249 int ver = 0;
250 int iline = 0;
251 while (std::getline(iss, line)) {
253 if (line.size() == 0) {
254 continue;
255 }
256 if (line.at(0) == '#') {
257 continue;
258 }
259 if (iline == 0) {
260 if (line.find("ver") != std::string::npos) {
261 ver = 1;
262 LOG(info) << "CTP Config vesrion:" << line;
263 } else {
264 LOG(info) << "CTP Config version: 0";
265 }
266 }
267 iline++;
268 if (ver == 0) {
269 ret = processConfigurationLineRun3(line, level, clsDescIndex);
270 } else {
271 ret = processConfigurationLineRun3v2(line, level, clsDescIndex);
272 }
273 if (ret) {
274 return ret;
275 }
276 }
277 if (ver == 0) {
278 for (auto& cls : mCTPClasses) {
279 cls.cluster = &mClusters[cls.clusterIndex];
280 if (cls.descriptorIndex != 0xff) {
281 cls.descriptor = &mDescriptors[cls.descriptorIndex];
282 if (cls.getIndex() != 0xff) {
283 for (auto const& inp : clsDescIndex[cls.getIndex()]) {
284 mDescriptors.at(cls.descriptorIndex).inputs.push_back(&mInputs.at(inp));
285 }
286 }
287 }
288 }
290 } else {
291 for (auto& cls : mCTPClasses) {
292 cls.cluster = &mClusters[cls.clusterIndex];
293 }
294 }
295 return ret;
296}
297int CTPConfiguration::processConfigurationLineRun3(std::string& line, int& level, std::map<int, std::vector<int>>& descInputsIndex)
298{
299 LOG(info) << "Processing line";
300 LOG(info) << "line:" << line << " lev:" << level;
301 //
302 std::vector<std::string> tokens = o2::utils::Str::tokenize(line, ' ');
303 size_t ntokens = tokens.size();
304 if (ntokens == 0) {
305 LOG(warning) << "# of tokens zero in line:" << line;
306 return 0;
307 }
308 size_t first;
309 if (((first = line.find("run")) != std::string::npos) && (level == START)) {
310 level = RUN;
311 } else if ((line.find("inp") != std::string::npos) && ((level == RUN) || (level == INPUTS))) {
312 level = INPUTS;
313 } else if (((first = line.find("bcm")) != std::string::npos) && ((level == RUN) || (level == INPUTS) || (level == MASKS))) {
314 level = MASKS;
315 } else if (CTPGenerator::Generators.count(tokens[0]) && ((level == RUN) || (level == INPUTS) || (level == MASKS) || (level == GENS))) {
316 level = GENS;
317 } else if ((first = line.find("LTG")) != std::string::npos) {
318 level = LTG;
319 } else if ((first = line.find("cluster")) != std::string::npos) {
320 level = CLUSTER;
321 } else {
322 bool knownlevels = ((level == LTGitems) || (level == CLASS));
323 if (knownlevels == false) {
324 level = UNKNOWN;
325 }
326 }
327 LOG(info) << "Level:" << level;
328 switch (level) {
329 case RUN: {
330 try {
331 mRunNumber = std::stoul(tokens[1]);
332 } catch (...) {
333 LOG(error) << "RUN:" << tokens[1] << std::endl;
334 }
335 level = RUN;
336 break;
337 }
338 case INPUTS: {
339 level = INPUTS;
340 if (tokens.size() < 3) {
341 LOG(error) << "Wrong input line:" << line;
342 break;
343 }
344 CTPInput ctpinp;
345 ctpinp.name = tokens[1];
346 ctpinp.level = tokens[1][0];
347 std::string run2Name{tokens[1][1]};
348 ctpinp.setRun3DetName(run2Name);
349 uint32_t index = std::stoul(tokens[2]);
350 ctpinp.inputMask = (1ull << (index - 1));
351 mInputs.push_back(ctpinp);
352 LOG(info) << "Input:" << ctpinp.name << " index:" << index;
353 break;
354 }
355 case MASKS: {
356 BCMask bcmask;
357 if (tokens.size() < 3) {
358 LOG(error) << "Wrong bc mask:" << line;
359 break;
360 }
361 bcmask.name = tokens[1];
362 bool coded = tokens[2].find("L") != std::string::npos;
363 coded |= tokens[2].find("H") != std::string::npos;
364 // std::cout << "coded:" << coded << std::endl;
365 if (coded) {
366 // jusko notation
367 } else {
368 // list of integers
369 for (uint32_t i = 2; i < ntokens; i++) {
370 uint32_t bc;
371 try {
372 bc = std::stoull(tokens[i]);
373 } catch (...) {
374 LOG(info) << "mask syntax:" << i << ":" << tokens[i];
375 continue;
376 }
377 bcmask.BCmask.set(bc, 1);
378 }
379 }
380 mBCMasks.push_back(bcmask);
381 LOG(info) << "BC mask added:" << bcmask.name;
382 break;
383 }
384 case GENS: {
386 gen.name = tokens[0];
387 gen.frequency = tokens[1];
388 LOG(info) << "Gen added:" << line;
389 break;
390 }
391 case LTG: {
392 CTPDetector ctpdet;
393 std::string detname = tokens[1];
394 capitaliseString(detname);
395 o2::detectors::DetID det(detname.c_str());
396 if (isDetector(det)) {
397 ctpdet.detID = det.getID();
398 LOG(info) << "Detector found:" << det.getID() << " " << detname;
399 } else {
400 LOG(info) << "Unknown detectors:" << line;
401 }
402 mDetectors.push_back(ctpdet);
403 level = LTGitems;
404 break;
405 }
406 case LTGitems: {
407 if (ntokens == 1) {
408 mDetectors.back().mode = tokens[0];
409 }
410 LOG(info) << "LTGitem:" << line;
411 break;
412 }
413 case CLUSTER: {
414 CTPCluster cluster;
415 try {
416 cluster.hwMask = std::stoull(tokens[0]);
417 } catch (...) {
418 LOG(info) << "Cluster syntax error:" << line;
419 return level;
420 }
421 LOG(info) << "Cluster:" << line;
422 cluster.name = tokens[2];
424 for (uint32_t item = 3; item < ntokens; item++) {
425 std::string detname = tokens[item];
426 capitaliseString(detname);
427 // LOG(info) << "Detector:" << detname;
428 o2::detectors::DetID det(detname.c_str());
429 isDetector(det);
430 mask |= det.getMask();
431 }
432 cluster.maskCluster = mask;
433 mClusters.push_back(cluster);
434 level = CLASS;
435 // LOG(info) << "Cluster done:" << cluster.name << std::endl;
436 break;
437 }
438 case CLASS: {
439 // add to the last cluster
440 if (tokens.size() < 3) {
441 LOG(error) << "CTPClass: less than 3 items in class:" << line;
442 break;
443 }
444 uint64_t index;
445 try {
446 index = std::stoull(tokens[0]);
447 } catch (...) {
448 LOG(info) << "Class syntax error:" << line;
449 return level;
450 }
451 LOG(info) << "Class:" << line;
452 CTPClass cls;
453 cls.classMask = 1ull << index;
454 cls.name = tokens[1];
455 cls.clusterIndex = mClusters.size() - 1;
456 CTPDescriptor desc;
457 desc.name = "d" + cls.name;
458 // LOG(info) << "point:" << cls.cluster << " " << &mClusters.front();
459 for (uint32_t i = 2; i < tokens.size(); i++) {
460 std::string token = tokens[i];
461 bool isGenerator = 0;
462 for (auto const& gen : CTPGenerator::Generators) {
463 if (token.find(gen) != std::string::npos) {
464 isGenerator = 1;
465 break;
466 }
467 }
468 if (isGenerator) {
469 addInput(token, index, descInputsIndex);
470 LOG(info) << "Class generator found:" << desc.name;
471 } else if (token.find("~") != std::string::npos) { // inverted input
472 // std::cout << "Inverted input" << std::endl;
473 addInput(token, index, descInputsIndex);
474 } else if (isNumber(token)) { // normal input as number
475 // std::cout << "Normal input" << std::endl;
476 addInput(token, index, descInputsIndex);
477 // LOG(info) << "Class input descriptor:" << mDescriptors[mDescriptors.size() - 1].name;
478 } else if (token.find("0x") != std::string::npos) { // downscale
479 // std::cout << "Downscale" << std::endl;
480 cls.downScale = std::stoul(token, nullptr, 16);
481 } else if (token.find("bcm") != std::string::npos) { // bcmask
482 // std::cout << "Mask" << std::endl;
483 uint32_t i = 0;
484 for (auto const& bcm : mBCMasks) {
485 if (bcm.name == token) {
486 cls.BCClassMask.push_back(&bcm);
487 LOG(info) << "Class BCMask found:" << token;
488 break;
489 }
490 i++;
491 }
492 if (i == mBCMasks.size()) {
493 LOG(error) << "Class BCMask NOT found:" << token << " assuming input";
494 }
495 } else { // input as string or descriptor
496 addInput(token, index, descInputsIndex);
497 }
498 }
499 mDescriptors.push_back(desc);
500 cls.descriptorIndex = mDescriptors.size() - 1;
501 //
502 mCTPClasses.push_back(cls);
503 break;
504 }
505 default: {
506 LOG(info) << "unknown line:" << line;
507 }
508 }
509 return 0;
510}
511int CTPConfiguration::processConfigurationLineRun3v2(std::string& line, int& level, std::map<int, std::vector<int>>& descInputsIndex)
512{
513 LOG(debug) << "Processing line";
514 LOG(debug) << "line:" << line << " lev:" << level;
515 //
516 std::vector<std::string> tokens = o2::utils::Str::tokenize(line, ' ');
517 size_t ntokens = tokens.size();
518 if (ntokens == 0) {
519 LOG(warning) << "# of tokens zero in line:" << line;
520 return 0;
521 }
522 size_t first;
523 if (((first = line.find("ver")) != std::string::npos) && (level == START)) {
524 mVersion = line;
525 // std::cout << "debug:" << mVersion << std::endl;
526 level = VERSION;
527 return 0;
528 } else if (((first = line.find("run")) != std::string::npos) && (level == VERSION)) {
529 level = RUN;
530 } else if ((line.find("INPUTS") != std::string::npos) && (level == RUN)) {
531 level = INPUTS;
532 return 0;
533 } else if ((line.find("inp") != std::string::npos) && (level == INPUTS)) {
534 level = INPUTS;
535 } else if ((line.find("BCMASKS") != std::string::npos) && ((level == INPUTS) || (level == RUN))) {
536 level = MASKS;
537 return 0;
538 } else if (((first = line.find("bcm")) != std::string::npos) && (level == MASKS)) {
539 level = MASKS;
540 } else if (line.find("GENS") != std::string::npos) {
541 level = GENS;
542 return 0;
543 } else if (CTPGenerator::Generators.count(tokens[0]) && (level == GENS)) {
544 level = GENS;
545 } else if (line.find("DESCRIPTORS") != std::string::npos) {
547 return 0;
548 } else if ((tokens[0][0] == 'D') && (level == DESCRIPTORS)) {
550 } else if ((first = line.find("LTG")) != std::string::npos) {
551 level = LTG;
552 } else if ((first = line.find("cluster")) != std::string::npos) {
553 level = CLUSTER;
554 } else {
555 bool knownlevels = ((level == LTGitems) || (level == CLASS));
556 if (knownlevels == false) {
557 level = UNKNOWN;
558 }
559 }
560 LOG(debug) << "Level:" << level;
561 switch (level) {
562 case VERSION: {
563 break;
564 }
565 case RUN: {
566 try {
567 mRunNumber = std::stoul(tokens[1]);
568 } catch (...) {
569 LOG(error) << "RUN line:" << line;
570 }
571 level = RUN;
572 break;
573 }
574 case INPUTS: {
575 level = INPUTS;
576 if (tokens.size() != 3) {
577 LOG(error) << "Wrong input line:" << line;
578 return 1;
579 }
580 CTPInput ctpinp;
581 ctpinp.name = tokens[1];
582 ctpinp.level = tokens[1][0];
583 std::string run2Name{tokens[1][1]};
584 ctpinp.setRun3DetName(run2Name);
585 uint32_t index = std::stoul(tokens[2]);
586 ctpinp.inputMask = (1ull << (index - 1));
587 mInputs.push_back(ctpinp);
588 LOG(debug) << "Input:" << ctpinp.name << " index:" << index;
589 break;
590 }
591 case MASKS: {
592 BCMask bcmask;
593 if (tokens.size() < 3) {
594 LOG(error) << "Wrong bc mask:" << line;
595 break;
596 }
597 bcmask.setBCmask(tokens);
598 mBCMasks.push_back(bcmask);
599 LOG(debug) << "BC mask added:" << bcmask.name;
600 break;
601 }
602 case GENS: {
604 gen.name = tokens[0];
605 gen.frequency = tokens[1];
606 mGenerators.push_back(gen);
607 LOG(debug) << "Gen added:" << line;
608 break;
609 }
610 case DESCRIPTORS: {
611 if ((tokens.size() < 2)) {
612 if (line.find("TRUE") != std::string::npos) {
613 CTPDescriptor desc;
614 desc.name = tokens[0];
615 mDescriptors.push_back(desc);
616 break;
617 } else {
618 LOG(warning) << "Unexpected Descriptor:" << line;
619 break;
620 }
621 }
622 CTPDescriptor desc;
623 desc.name = tokens[0];
624 for (uint32_t i = 1; i < tokens.size(); i++) {
625 const CTPInput* inp = isInputInConfig(tokens[i]);
626 if (inp != nullptr) {
627 desc.inputs.push_back(inp);
628 }
629 }
630 mDescriptors.push_back(desc);
631 break;
632 }
633 case LTG: {
634 CTPDetector ctpdet;
635 std::string detname = tokens[1];
636 capitaliseString(detname);
637 o2::detectors::DetID det(detname.c_str());
638 if (isDetector(det)) {
639 ctpdet.detID = det.getID();
640 LOG(debug) << "Detector found:" << det.getID() << " " << detname;
641 } else {
642 LOG(error) << "Unknown detectors:" << line;
643 }
644 mDetectors.push_back(ctpdet);
645 level = LTGitems;
646 break;
647 }
648 case LTGitems: {
649 if (ntokens == 1) {
650 mDetectors.back().mode = tokens[0];
651 }
652 LOG(debug) << "LTGitem:" << line;
653 break;
654 }
655 case CLUSTER: {
656 CTPCluster cluster;
657 try {
658 cluster.hwMask = std::stoull(tokens[0]);
659 } catch (...) {
660 LOG(error) << "Cluster syntax error:" << line;
661 return level;
662 }
663 LOG(debug) << "Cluster:" << line;
664 cluster.name = tokens[2];
666 for (uint32_t item = 3; item < ntokens; item++) {
667 std::string detname = tokens[item];
668 capitaliseString(detname);
669 // LOG(info) << "Detector:" << detname;
670 o2::detectors::DetID det(detname.c_str());
671 isDetector(det);
672 mask |= det.getMask();
673 }
674 cluster.maskCluster = mask;
675 mClusters.push_back(cluster);
676 level = CLASS;
677 // LOG(info) << "Cluster done:" << cluster.name << std::endl;
678 break;
679 }
680 case CLASS: {
681 // add to the last cluster
682 if (tokens.size() < 6) {
683 LOG(error) << "CTPClass items < 6" << line;
684 break;
685 }
686 uint64_t index;
687 try {
688 index = std::stoull(tokens[1]);
689 } catch (...) {
690 LOG(error) << "Class syntax error:" << line;
691 return level;
692 }
693 LOG(debug) << "Class:" << line;
694 CTPClass cls;
695 cls.classMask = 1ull << index;
696 cls.name = tokens[0];
697 // Descriptor
698 std::string descname = tokens[2];
699 int dindex;
700 if (descname.find("DTRUE") != std::string::npos) {
701 descname = "DTRUE";
702 }
703 const CTPDescriptor* desc = isDescriptorInConfig(descname, dindex);
704 if (desc != nullptr) {
705 cls.descriptor = desc;
706 cls.descriptorIndex = dindex;
707 }
708 cls.clusterIndex = mClusters.size() - 1;
709 // PF not member of class
710 std::string bcmask = tokens[5];
711 bcmask = bcmask.substr(1, bcmask.size() - 2);
712 if (bcmask.size()) {
713 const BCMask* bcm = isBCMaskInConfigP(bcmask);
714 if (bcm != nullptr) {
715 cls.BCClassMask.push_back(bcm);
716 }
717 }
718 // Down scaling
719 if (tokens.size() > 6) {
720 cls.downScale = std::stoul(tokens[6], nullptr, 16);
721 }
722 mCTPClasses.push_back(cls);
723 break;
724 }
725 default: {
726 LOG(warning) << "unknown line:" << line;
727 }
728 }
729 return 0;
730}
731void CTPConfiguration::printStream(std::ostream& stream) const
732{
733 stream << "Configuration:" << mName << " Version:" << mVersion << std::endl;
734 stream << "Run:" << mRunNumber << " cfg name:" << mName << std::endl;
735 stream << "CTP BC masks:" << std::endl;
736 for (const auto& i : mBCMasks) {
737 i.printStream(stream);
738 }
739 stream << "CTP inputs:" << mInputs.size() << std::endl;
740 for (const auto& i : mInputs) {
741 i.printStream(stream);
742 }
743 stream << "CTP generators:" << std::endl;
744 for (const auto& i : mGenerators) {
745 i.printStream(stream);
746 }
747 stream << "CTP descriptors:" << mDescriptors.size() << std::endl;
748 for (const auto& i : mDescriptors) {
749 i.printStream(stream);
750 }
751 stream << "CTP detectors:" << mDetectors.size() << std::endl;
752 for (const auto& i : mDetectors) {
753 i.printStream(stream);
754 }
755 stream << "CTP clusters:" << std::endl;
756 for (const auto& i : mClusters) {
757 i.printStream(stream);
758 }
759 stream << "CTP classes:" << std::endl;
760 for (const auto& i : mCTPClasses) {
761 i.printStream(stream);
762 }
763}
764uint64_t CTPConfiguration::getInputMask(const std::string& name) const
765{
766 for (auto const& inp : mInputs) {
767 if (inp.name == name) {
768 return inp.inputMask;
769 }
770 }
771 return 0;
772}
773int CTPConfiguration::getInputIndex(const std::string& name) const
774{
775 int index = 0xff;
776 const CTPInput* inp = isInputInConfig(name);
777 if (inp != nullptr) {
778 index = inp->getIndex();
779 }
780 LOG(info) << "input:" << name << " index:" << index;
781 return index;
782}
784{
785 if (index < (int)mCTPClasses.size()) {
786 return mCTPClasses[index].name;
787 } else {
788 std::string name = "Cls" + std::to_string(index);
789 return name;
790 }
791};
793{
794 for (auto& cls : mCTPClasses) {
795 if (cls.classMask == (1ull << index)) {
796 return cls.name;
797 }
798 }
799 std::string ret = "not found";
800 return ret;
801}
803{
804 const CTPClass* clsfound = nullptr;
805 for (auto const& cls : mCTPClasses) {
806 if (index == cls.getIndex()) {
807 clsfound = &cls;
808 break;
809 }
810 }
811 return clsfound;
812}
813bool CTPConfiguration::isMaskInInputs(const uint64_t& mask) const
814{
815 for (auto const& inp : mInputs) {
816 if (inp.inputMask == mask) {
817 return true;
818 }
819 }
820 return false;
821}
822bool CTPConfiguration::isBCMaskInConfig(const std::string maskname) const
823{
824 for (auto& bcm : mBCMasks) {
825 if (bcm.name == maskname) {
826 return true;
827 }
828 }
829 return false;
830}
831const BCMask* CTPConfiguration::isBCMaskInConfigP(const std::string maskname) const
832{
833 for (const auto& bcm : mBCMasks) {
834 if (bcm.name == maskname) {
835 LOG(info) << "isBCMaskInConfigP found:" << maskname;
836 return &bcm;
837 }
838 }
839 LOG(info) << "isBCMaskInConfigP NOT found:" << maskname;
840 return nullptr;
841}
842const CTPInput* CTPConfiguration::isInputInConfig(const std::string inpname) const
843{
844 for (const auto& inp : mInputs) {
845 if (inp.name == inpname) {
846 LOG(info) << "isInputInConfig found:" << inpname;
847 return &inp;
848 }
849 }
850 LOG(info) << "isInputInConfig NOT found:" << inpname;
851 return nullptr;
852}
854{
855 for (const auto& inp : mInputs) {
856 // std::cout << "isInputINConfig:" << inp.name << " " << inp.getIndex() << " " << index << std::endl;
857 if (inp.getIndex() == index) {
858 LOG(info) << "Found input:" << inp.name << " index:" << inp.getIndex();
859 return &inp;
860 }
861 }
862 return nullptr;
863}
864const CTPDescriptor* CTPConfiguration::isDescriptorInConfig(const std::string descname, int& index) const
865{
866 index = 0;
867 for (const auto& desc : mDescriptors) {
868 if (desc.name == descname) {
869 LOG(info) << "isDescriptorInConfig found:" << descname;
870 return &desc;
871 }
872 index++;
873 }
874 LOG(info) << "isDescriptorInConfig NOT found:" << descname;
875 return nullptr;
876}
878// using run3 conventions for inputs
879{
880 LOG(info) << "Creating Inputs";
881 for (auto& des : mDescriptors) {
882 if (CTPConfiguration::isNumber(des.name)) {
883 // parse here if more inputs
884 uint32_t index = std::stoul(des.name);
885 if (index > 100) {
886 index = index - 100;
887 }
888 // CTPInput* inp = const_cast<CTPInput*>(isInputInConfig(index));
889 LOG(info) << "Desc index:" << index;
890 const CTPInput* inp = isInputInConfig(index);
891 if (inp) {
892 des.inputs.push_back(inp);
893 } else {
894 LOG(warning) << "Descriptor not found:" << des.name;
895 }
896 } else {
897 LOG(info) << "Input is not a number:" << des.name;
898 }
899 }
900}
901std::map<o2::detectors::DetID::ID, std::vector<CTPInput>> CTPConfiguration::getDet2InputMap()
902{
903 std::map<o2::detectors::DetID::ID, std::vector<CTPInput>> det2inp;
904 for (auto const& inp : mInputs) {
905 det2inp[inp.detID].push_back(inp);
906 }
907 return det2inp;
908}
910{
911 uint64_t clsmask = 0;
912 for (auto const& cls : mCTPClasses) {
913 clsmask |= cls.classMask;
914 }
915 return clsmask;
916}
918{
919 uint64_t clsmask = 0;
920 for (auto const& cls : mCTPClasses) {
921 if (cls.name.find("TRUE") != std::string::npos) { // ignoring internal ctp generators
922 continue;
923 }
924 clsmask |= cls.classMask;
925 }
926 return clsmask;
927}
929{
930 uint64_t clsmask = 0;
931 for (auto const& cls : mCTPClasses) {
932 bool exclude = cls.name.find("TRUE") != std::string::npos; // ignoring internal ctp generators
933 exclude += cls.name.find("EMC") != std::string::npos;
934 exclude += cls.name.find("TRD") != std::string::npos;
935 exclude += cls.name.find("HMP") != std::string::npos;
936 if (!exclude) {
937 clsmask |= cls.classMask;
938 }
939 }
940 return clsmask;
941}
942// Hardware positions of classes
944{
945 uint64_t clsmask = getTriggerClassMask();
946 std::vector<int> classlist;
947 for (int i = 0; i < 64; i++) {
948 if ((1ull << i) & clsmask) {
949 classlist.push_back(i);
950 }
951 }
952 return classlist;
953}
954std::vector<std::string> CTPConfiguration::getDetectorList() const
955{
956 std::vector<std::string> detlist;
957 for (auto const& det : mDetectors) {
958 std::string sdet(det.getName());
959 detlist.push_back(sdet);
960 }
961 return detlist;
962}
964{
966 for (auto const& det : mDetectors) {
967 mask |= det.getMask();
968 }
969 return mask;
970}
971// This is special case of general approach:
972// classmask = fin(inputmask)g
973uint64_t CTPConfiguration::getClassMaskForInputMask(uint64_t inputMask) const
974{
975 uint64_t clsmask = 0;
976 for (auto const& cls : mCTPClasses) {
977 if (cls.descriptor) {
978 // std::cout << cls.name << std::hex << " " << cls.descriptor->getInputsMask() << " " << inputMask << std::endl;
979 if (cls.descriptor->getInputsMask() & inputMask) {
980 clsmask += cls.classMask;
981 // std::cout << " clsmask:" << clsmask << std::endl;
982 }
983 }
984 }
985 return clsmask;
986}
988{
989 for (auto& cls : mCTPClasses) {
990 cls.descriptor = &mDescriptors[cls.descriptorIndex];
991 }
992 return 0;
993}
995{
996 LOG(info) << "Checking consistency run:" << mRunNumber;
997 int ret = 0;
998 // All inputs used ?
999 // std::map<const CTPInput*, int> inputs;
1000 std::map<std::string, int> inputs;
1001 for (auto const& inp : mInputs) {
1002 inputs[inp.name] = 0;
1003 }
1004 // Are all descriptors used
1005 // std::map<const CTPDescriptor*, int> descs;
1006 std::map<std::string, int> descs;
1007 for (auto const& desc : mDescriptors) {
1008 descs[desc.name] = 0;
1009 // std::cout << "1 " << &desc << std::endl;
1010 for (auto const inp : desc.inputs) {
1011 inputs[inp->name] += 1;
1012 }
1013 }
1014 std::cout << "desc1:" << descs.size() << std::endl;
1015 //
1016 for (const auto& cls : mCTPClasses) {
1017 if (cls.classMask == 0) {
1018 std::cout << "ERROR class:" << cls.name << " NO CLASS MASK" << std::endl;
1019 ret++;
1020 }
1021 if (cls.cluster == nullptr) {
1022 std::cout << "ERROR class:" << cls.name << " NO CLUSTER" << std::endl;
1023 ret++;
1024 }
1025 if (cls.clusterIndex == 0xff) {
1026 std::cout << "ERROR class:" << cls.name << " NO CLUSTER INDEX" << std::endl;
1027 ret++;
1028 }
1029 if (cls.descriptor == nullptr) {
1030 std::cout << "ERROR class:" << cls.name << " NO DESCRIPTOR" << std::endl;
1031 ret++;
1032 } else {
1033 descs[cls.descriptor->name] += 1;
1034 // std::cout << "2 " << cls.descriptor << std::endl;
1035 }
1036 if (cls.descriptorIndex == 0xff) {
1037 std::cout << "ERROR class:" << cls.name << " NO DESCRIPTOR INDEX" << std::endl;
1038 ret++;
1039 } else {
1040 // std::cout << "3 " << &mDescriptors[cls.descriptorIndex] << std::endl;
1041 }
1042 }
1043 int iw = 0;
1044 for (auto const& inp : inputs) {
1045 if (inp.second == 0) {
1046 iw++;
1047 std::cout << "WARNING inputs:";
1048 }
1049 std::cout << inp.first << " " << inp.second << std::endl;
1050 }
1051 std::cout << "Descriptors check:" << descs.size() << std::endl;
1052 for (auto const& desc : descs) {
1053 if (desc.second == 0) {
1054 iw++;
1055 std::cout << "WARNING descriptors:";
1056 }
1057 // std::cout << (desc.first)->name << " " << desc.second << std::endl;
1058 std::cout << (desc.first) << " " << desc.second << std::endl;
1059 }
1060 std::cout << "CTP Config consistency checked. WARNINGS:" << iw << " ERRORS:" << ret << std::endl;
1061 return ret;
1062}
1064{
1065 std::cout << mConfigString << std::endl;
1066};
1067//
1069{
1070 int ret = 0;
1071 std::ifstream inpcfg(filename);
1072 if (inpcfg.is_open()) {
1073 std::string line;
1074 while (std::getline(inpcfg, line)) {
1076 if (line.size() == 0) {
1077 continue;
1078 }
1079 if (line[0] == '#') {
1080 continue;
1081 }
1082 std::vector<std::string> tokens = o2::utils::Str::tokenize(line, ' ');
1083 size_t ntokens = tokens.size();
1084 if (ntokens < 6) {
1085 LOG(warning) << "# of tokens < 6 in line:" << ntokens << ":" << line;
1086 ret++;
1087 } else {
1088 CTPInput inp;
1089 uint32_t index = 0;
1090 try {
1091 index = std::stoi(tokens[0]);
1092 } catch (...) {
1093 LOG(warning) << line;
1094 ret++;
1095 continue;
1096 }
1097 std::string det = tokens[1];
1099 std::string name = tokens[2];
1100 CTPInputs.push_back(CTPInput(name, det, index));
1101 }
1102 }
1103 } else {
1104 LOG(info) << "Can not open file:" << filename;
1105 ret++;
1106 }
1107 return ret;
1108}
1115{
1116 for (auto const& input : CTPInputs) {
1117 input.printStream(stream);
1118 }
1119}
1120//
1121// EMBA - software generated input for EMC - Min Bias Accepted
1122//
1123const std::vector<CTPInput> CTPInputsConfiguration::CTPInputsDefault =
1124 {
1125 CTPInput("MT0A", "FT0", 1), CTPInput("MT0C", "FT0", 2), CTPInput("MTVX", "FT0", 3), CTPInput("MTSC", "FT0", 4), CTPInput("MTCE", "FT0", 5),
1126 CTPInput("MVBA", "FV0", 6), CTPInput("MVOR", "FV0", 7), CTPInput("MVIR", "FV0", 8), CTPInput("MVNC", "FV0", 9), CTPInput("MVCH", "FV0", 10),
1127 CTPInput("0UCE", "FDD", 13), CTPInput("0USC", "FDD", 15), CTPInput("0UVX", "FDD", 16), CTPInput("0U0C", "FDD", 17), CTPInput("0U0A", "FDD", 18),
1128 CTPInput("0DMC", "EMC", 14), CTPInput("0DJ1", "EMC", 41), CTPInput("0DG1", "EMC", 42), CTPInput("0DJ2", "EMC", 43), CTPInput("0DG2", "EMC", 44),
1129 CTPInput("0EMC", "EMC", 21), CTPInput("0EJ1", "EMC", 37), CTPInput("0EG1", "EMC", 38), CTPInput("0EJ2", "EMC", 39), CTPInput("0EG2", "EMC", 40),
1130 CTPInput("0PH0", "PHS", 22), CTPInput("1PHL", "PHS", 27), CTPInput("1PHH", "PHS", 28), CTPInput("1PHL", "PHM", 29),
1131 CTPInput("1ZED", "ZDC", 25), CTPInput("1ZNC", "ZDC", 26), CTPInput("EMBA", "EMC", 48)};
1139{
1140 uint32_t indexcor = index;
1141 if (index > 100) {
1142 indexcor = index - 100;
1143 }
1144 for (auto& inp : defaultInputConfig.CTPInputs) {
1145 if (inp.getIndex() == indexcor) {
1146 std::string name = inp.name;
1147 if (index > 100) {
1148 name[0] = '0';
1149 }
1150 return name;
1151 }
1152 }
1153 LOG(info) << "Input with index:" << index << " not in deafult input config";
1154 return "";
1155}
1159{
1160 if (index > o2::ctp::CTP_NINPUTS) {
1161 LOG(warn) << "getInputNameFRomIndex: index too big:" << index;
1162 return "none";
1163 }
1165 if (inp.getIndex() == index) {
1166 std::string name = inp.name;
1167 return name;
1168 }
1169 }
1170 LOG(info) << "Input with index:" << index << " not in deafult input config";
1171 return "none";
1172}
1174{
1175 std::string namecorr = name;
1176 if ((name[0] == '0') || (name[0] == 'M') || (name[0] == '1')) {
1177 namecorr = namecorr.substr(1, namecorr.size() - 1);
1178 } else {
1179 LOG(warn) << "Input name without level:" << name;
1180 }
1182 if (inp.name.find(namecorr) != std::string::npos) {
1183 return inp.getIndex();
1184 }
1185 }
1186 LOG(warn) << "Input with name:" << name << " not in default input config";
1187 return 0xff;
1188}
1189
1190int CtpCfg::readAndSave(std::string& path)
1191{
1192 std::string file = path + filename;
1193 std::ifstream ctpcfg(file);
1194 if (ctpcfg.is_open()) {
1195 std::string line;
1196 while (std::getline(ctpcfg, line)) {
1198 if (line.size() == 0) {
1199 continue;
1200 }
1201 if (line[0] == '#') {
1202 continue;
1203 }
1204 std::vector<std::string> tokens = o2::utils::Str::tokenize(line, ' ');
1205 size_t ntokens = tokens.size();
1206 if (ntokens < 2) {
1207 LOG(warn) << "Not enough tokens";
1208 continue;
1209 }
1210 if (tokens[0].find("TForbits") != std::string::npos) {
1211 TFOrbits = std::atol(tokens[1].c_str());
1212 } else if (tokens[0].find("ccdb") != std::string::npos) {
1213 ccdb = std::atoi(tokens[1].c_str());
1214 } else if (tokens[0].find("orbitshift") != std::string::npos) {
1215 orbitShift = std::atol(tokens[1].c_str());
1216 } else if (tokens[0].find("ir_inputs") != std::string::npos) {
1217 irInputs_1_24 = std::stoul(tokens[2].c_str(), nullptr, 16);
1218 irInputs_25_48 = std::stoul(tokens[1].c_str(), nullptr, 16);
1219 } else {
1220 LOG(warn) << " Token not found:" << tokens[0];
1221 }
1222 }
1223 LOG(warn) << "Open file success:" << file;
1224 } else {
1225 LOG(warn) << "Can not open file:" << file;
1226 return 1;
1227 }
1228 return 0;
1229}
1230
1231std::ostream& o2::ctp::operator<<(std::ostream& in, const o2::ctp::CTPConfiguration& conf)
1232{
1233 conf.printStream(in);
1234 return in;
1235}
definition of CTPConfiguration and related CTP structures
default_random_engine gen(dev())
uint64_t bc
Definition RawEventData.h:5
int32_t i
uint16_t pos
Definition RawData.h:3
uint32_t c
Definition RawData.h:2
std::ostringstream debug
std::vector< std::string > getDetectorList() const
std::vector< int > getTriggerClassList() const
static bool isNumber(const std::string &s)
uint64_t getInputMask(const std::string &name) const
uint64_t getTriggerClassMaskWInputsNoTrgDets() const
uint64_t getTriggerClassMask() const
std::string getClassNameFromIndex(int index)
const CTPInput * isInputInConfig(const std::string inpname) const
std::string getClassNameFromHWIndex(int index)
const BCMask * isBCMaskInConfigP(const std::string bcmask) const
bool isBCMaskInConfig(const std::string maskname) const
int addInput(std::string &inp, int clsindex, std::map< int, std::vector< int > > &descInputsIndex)
int getInputIndex(const std::string &name) const
o2::detectors::DetID::mask_t getDetectorMask() const
static void capitaliseString(std::string &str)
uint64_t getClassMaskForInputMask(uint64_t inputMask) const
const CTPDescriptor * isDescriptorInConfig(const std::string descname, int &index) const
void printStream(std::ostream &stream) const
int loadConfigurationRun3(const std::string &ctpconfiguartion)
const CTPClass * getCTPClassFromHWIndex(const int index) const
uint64_t getTriggerClassMaskWInputs() const
std::map< o2::detectors::DetID::ID, std::vector< CTPInput > > getDet2InputMap()
bool isMaskInInputs(const uint64_t &mask) const
bool isDetector(const o2::detectors::DetID &det)
static const std::map< std::string, std::string > detName2LTG
Static class with identifiers, bitmasks and names for ALICE detectors.
Definition DetID.h:58
GLenum mode
Definition glcorearb.h:266
GLint GLsizei count
Definition glcorearb.h:399
GLuint index
Definition glcorearb.h:781
GLuint const GLchar * name
Definition glcorearb.h:781
GLint first
Definition glcorearb.h:399
GLboolean GLboolean GLboolean b
Definition glcorearb.h:1233
GLsizei const GLchar *const * path
Definition glcorearb.h:3591
GLint level
Definition glcorearb.h:275
GLuint GLuint stream
Definition glcorearb.h:1806
GLint GLuint mask
Definition glcorearb.h:291
std::ostream & operator<<(std::ostream &in, const CTPConfiguration &conf)
int32_t const char int32_t line
std::string to_string(gsl::span< T, Size > span)
Definition common.h:52
std::string filename()
std::string name
std::string mask
std::bitset< o2::constants::lhc::LHCMaxBunches > BCmask
int setBCmask(std::vector< std::string > &tokens)
void printStream(std::ostream &stream) const
Class = Mask+Descriptor+Cluster.
std::vector< BCMask const * > BCClassMask
void printStream(std::ostream &strem) const
int getIndex() const
std::uint64_t classMask
CTPCluster const * cluster
CTPDescriptor const * descriptor
List of detectors.
o2::detectors::DetID::mask_t maskCluster
std::string getClusterDetNames() const
void printStream(std::ostream &strem) const
Descriptor = Generator or List of [negated] inputs.
std::vector< CTPInput const * > inputs
std::uint64_t getInputsMask() const
void printStream(std::ostream &strem) const
The main part is Local Trigger Generator (LTG)
void printStream(std::ostream &stream) const
const char * getName() const
o2::detectors::DetID::ID detID
CTP internal generator: 4 for L0 and 4 for LM levels.
void printStream(std::ostream &stream) const
static const std::set< std::string > Generators
uint32_t getIndex() const
CTPInput()=default
std::string level
o2::detectors::DetID::ID detID
void printStream(std::ostream &strem) const
void setRun3DetName(std::string &run2Name)
static const std::map< std::string, std::string > run2DetToRun3Det
std::uint64_t inputMask
std::string getInputDetName() const
static CTPInputsConfiguration defaultInputConfig
std::vector< CTPInput > CTPInputs
int createInputsConfigFromFile(std::string &filename)
void printStream(std::ostream &strem) const
static std::string getInputNameFromIndex(uint32_t index)
static int getInputIndexFromName(std::string &name)
static const std::vector< CTPInput > CTPInputsDefault
static std::string getInputNameFromIndex100(uint32_t index)
uint32_t irInputs_25_48
uint32_t irInputs_1_24
int readAndSave(std::string &path)
std::string filename
static void trim(std::string &s)
Definition StringUtils.h:71
static std::vector< std::string > tokenize(const std::string &src, char delim, bool trimToken=true, bool skipEmpty=true)
LOG(info)<< "Compressed in "<< sw.CpuTime()<< " s"
const std::string str