78 mCalibHandler->checkUpdates(ctx);
89 mDigitizerTRU.
flush();
99 if (mcReader ==
nullptr) {
103 auto& timesview = context->getEventRecords();
104 LOG(
debug) <<
"GOT " << timesview.size() <<
" COLLISSION TIMES";
107 if (timesview.size() == 0) {
114 auto& eventParts = context->getEventParts();
124 mDigitizerTRU.
setFEE(mCalibHandler->getFEEDCS());
138 for (
int collID = 0; collID < timesview.size(); ++collID) {
140 if (mRunDigitizerTRU ==
false) {
144 if (intRate < 10000.) {
154 for (
auto& part : eventParts[collID]) {
161 context->retrieveHits(mSimChains,
"EMCHit", part.sourceID, part.entryID, &mHits);
171 std::vector<o2::emcal::LabeledDigit> summedLabeledDigits;
172 std::vector<o2::emcal::Digit> summedDigits;
174 summedLabeledDigits = mSumDigitizerTRU.
process(mHits);
175 for (
auto labeledsummeddigit : summedLabeledDigits) {
176 summedDigits.push_back(labeledsummeddigit.getDigit());
179 for (
auto& hit : mHits) {
180 summedDigits.emplace_back(hit.GetDetectorID(), hit.GetEnergyLoss(), hit.GetTime());
185 mDigitizerTRU.
process(summedDigits);
195 std::vector<o2::InteractionRecord> mbtriggers;
196 if (mRequireCTPInput) {
201 std::vector<uint64_t> inputmasks;
205 LOG(
debug) <<
"Found trigger class for EMCAL cluster: " << trg.name <<
" with input mask " << std::bitset<64>(trg.descriptor->getInputsMask());
206 inputmasks.emplace_back(trg.descriptor->getInputsMask());
209 unsigned long ft0mask = 0, fv0mask = 0;
210 std::map<std::string, uint64_t> detInputName2Mask =
211 {{
"MVBA", 1}, {
"MVOR", 2}, {
"MVNC", 4}, {
"MVCH", 8}, {
"MVIR", 0x10}, {
"MT0A", 1}, {
"MT0C", 2}, {
"MTSC", 4}, {
"MTCE", 8}, {
"MTVX", 0x10}};
213 std::map<std::string, std::pair<o2::detectors::DetID, std::string>> ctpInput2DetInput = {
214 {
"0VBA", {
o2::detectors::DetID::FV0,
"MVBA"}}, {
"0VOR", {
o2::detectors::DetID::FV0,
"MVOR"}}, {
"0VNC", {
o2::detectors::DetID::FV0,
"MVNC"}}, {
"0VCH", {
o2::detectors::DetID::FV0,
"MVCH"}}, {
"0VIR", {
o2::detectors::DetID::FV0,
"MVIR"}}, {
"0T0A", {
o2::detectors::DetID::FT0,
"MT0A"}}, {
"0T0C", {
o2::detectors::DetID::FT0,
"MT0C"}}, {
"0TSC", {
o2::detectors::DetID::FT0,
"MTSC"}}, {
"0TCE", {
o2::detectors::DetID::FT0,
"MTCE"}}, {
"0TVX", {
o2::detectors::DetID::FT0,
"MTVX"}}};
219 for (
const auto& input : ctpinputs) {
220 LOG(
debug) <<
"CTP det input: " << input.name <<
" with mask " << std::bitset<64>(input.inputMask);
221 bool isSelected =
false;
222 for (
auto testmask : inputmasks) {
223 if (testmask & input.inputMask) {
228 std::string usedInputName = input.name;
231 auto found = ctpInput2DetInput.find(input.name);
232 if (found != ctpInput2DetInput.end()) {
233 usedInputName = found->second.second;
234 usedDetID = found->second.first;
235 LOG(
debug) <<
"Decoded " << input.name <<
" -> " << usedInputName;
238 auto maskFound = detInputName2Mask.find(usedInputName);
239 if (maskFound != detInputName2Mask.end()) {
241 ft0mask |= maskFound->second;
243 fv0mask |= maskFound->second;
249 LOG(
debug) <<
"FTO mask: " << std::bitset<64>(ft0mask);
250 LOG(
debug) <<
"FVO mask: " << std::bitset<64>(fv0mask);
251 for (
const auto& trg : ctx.
inputs().
get<gsl::span<o2::ft0::DetTrigInput>>(
"ft0inputs")) {
252 if (trg.mInputs.to_ulong() & ft0mask) {
253 mbtriggers.emplace_back(trg.mIntRecord);
256 for (
const auto& trg : ctx.
inputs().
get<gsl::span<o2::fv0::DetTrigInput>>(
"fv0inputs")) {
257 if (trg.mInputs.to_ulong() & fv0mask) {
258 if (std::find(mbtriggers.begin(), mbtriggers.end(), trg.mIntRecord) == mbtriggers.end()) {
259 mbtriggers.emplace_back(trg.mIntRecord);
265 LOG(info) <<
" CALLING EMCAL DIGITIZATION ";
269 std::vector<std::tuple<o2::InteractionRecord, std::bitset<5>>> acceptedTriggers;
270 enum EMCALTriggerBits { kMB,
273 TRandom3 mRandomGenerator(std::chrono::high_resolution_clock::now().time_since_epoch().
count());
277 for (
int collID = 0; collID < timesview.size(); ++collID) {
279 std::bitset<5> trigger{0x1};
280 if (mRequireCTPInput) {
294 auto mbtrigger = std::find(mbtriggers.begin(), mbtriggers.end(), timesview[collID]);
295 if (mbtrigger != mbtriggers.end()) {
304 downscaling = trg.downScale;
307 if (mRandomGenerator.Uniform(0., 1) < downscaling) {
309 trigger.set(EMCALTriggerBits::kMB,
true);
312 for (
auto emcalTrigger : emcalTriggers) {
313 auto bcTimingOfEmcalTrigger = emcalTrigger.mInterRecord.bc;
314 auto bcTimingOfMBTrigger = (*mbtrigger).bc;
315 if (std::abs(bcTimingOfEmcalTrigger - bcTimingOfMBTrigger) < 12) {
316 if (emcalTrigger.mTriggeredTRU < 32) {
317 trigger.set(EMCALTriggerBits::kEMC,
true);
319 trigger.set(EMCALTriggerBits::kDMC,
true);
327 trigger.set(EMCALTriggerBits::kMB,
false);
332 if (!trigger.any()) {
336 acceptedTriggers.push_back(std::make_tuple(timesview[collID], trigger));
337 LOG(
debug) <<
"EMCAL TRU simulation: Sending trg = " << trigger <<
" to CTP";
339 mDigitizer.
setEventTime(timesview[collID], trigger.any());
341 if (!mDigitizer.
isLive()) {
347 for (
auto& part : eventParts[collID]) {
353 auto& mcEventHeader = mcReader->
getMCEventHeader(part.sourceID, part.entryID);
354 mcEventHeader.
print();
358 context->retrieveHits(mSimChains,
"EMCHit", part.sourceID, part.entryID, &mHits);
360 LOG(info) <<
"For collision " << collID <<
" eventID " << part.entryID <<
" found " << mHits.size() <<
" hits ";
362 std::vector<o2::emcal::LabeledDigit> summedDigits;
364 summedDigits = mSumDigitizer.
process(mHits);
366 for (
auto& hit : mHits) {
367 o2::emcal::MCLabel digitlabel(hit.GetTrackID(), part.entryID, part.sourceID,
false, 1.);
368 if (hit.GetEnergyLoss() < __DBL_EPSILON__) {
371 summedDigits.emplace_back(hit.GetDetectorID(), hit.GetEnergyLoss(), hit.GetTime(), digitlabel);
376 mDigitizer.
process(summedDigits);
390 LOG(info) <<
"EMCAL: Sending ROMode= " << roMode <<
" to GRPUpdater";
393 std::vector<o2::ctp::CTPInputDigit> triggerinputs;
404 for (
auto& trg : acceptedTriggers) {
411 if (std::get<1>(trg)[
i] != 0) {
416 triggerinputs.push_back(nextdigit);
421 LOG(info) <<
"Digitization took " << timer.CpuTime() <<
"s";
468 std::vector<OutputSpec> outputs;
469 outputs.emplace_back(
"EMC",
"DIGITS", 0, Lifetime::Timeframe);
470 outputs.emplace_back(
"EMC",
"TRGRDIG", 0, Lifetime::Timeframe);
472 outputs.emplace_back(
"EMC",
"DIGITSMCTR", 0, Lifetime::Timeframe);
474 outputs.emplace_back(
"EMC",
"ROMode", 0, Lifetime::Timeframe);
475 outputs.emplace_back(
"EMC",
"TRIGGERINPUT", 0, Lifetime::Timeframe);
477 std::vector<o2::framework::InputSpec> inputs;
478 inputs.emplace_back(
"collisioncontext",
"SIM",
"COLLISIONCONTEXT",
static_cast<SubSpecificationType>(channel), Lifetime::Timeframe);
479 std::shared_ptr<CalibLoader> calibloader;
481 calibloader = std::make_shared<CalibLoader>();
482 calibloader->enableSimParams(
true);
483 calibloader->enableFEEDCS(
true);
484 calibloader->defineInputSpecs(inputs);
486 if (requireCTPInput) {
487 inputs.emplace_back(
"ft0inputs",
"FT0",
"TRIGGERINPUT", 0, Lifetime::Timeframe);
488 inputs.emplace_back(
"fv0inputs",
"FV0",
"TRIGGERINPUT", 0, Lifetime::Timeframe);
489 inputs.emplace_back(
"ctpconfig",
"CTP",
"CTPCONFIG", 0, Lifetime::Condition,
ccdbParamSpec(
"CTP/Config/Config",
true));
496 AlgorithmSpec{o2::framework::adaptFromTask<DigitizerSpec>(calibloader, requireCTPInput)},
498 {
"pileup", VariantType::Int, 1, {
"whether to run in continuous time mode"}},
499 {
"disable-dig-tru", VariantType::Bool,
false, {
"Disable TRU digitisation"}},
500 {
"debug-stream", VariantType::Bool,
false, {
"Enable debug streaming"}}}
DataAllocator & outputs()
The data allocator is used to allocate memory for the output data.
ServiceRegistryRef services()
The services registry associated with this processing context.