|
| 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 | + |
| 12 | +/// @file FT0DataDecoderDPLSpec.h |
| 13 | + |
| 14 | +#if defined(__has_include) |
| 15 | +#if defined(__linux__) && (defined(__x86_64) || defined(__x86_64__)) && __has_include(<emmintrin.h>) && __has_include(<immintrin.h>) && defined(FT0_DECODER_AVX512) |
| 16 | + |
| 17 | +#ifndef O2_FT0DATADECODERDPLSPEC_H |
| 18 | +#define O2_FT0DATADECODERPLSPEC_H |
| 19 | +#include "Framework/DataProcessorSpec.h" |
| 20 | +#include "Framework/Task.h" |
| 21 | +#include "Framework/CallbackService.h" |
| 22 | +#include "Framework/ConfigParamRegistry.h" |
| 23 | +#include "Framework/ControlService.h" |
| 24 | +#include "Framework/Lifetime.h" |
| 25 | +#include "Framework/Output.h" |
| 26 | +#include "Framework/WorkflowSpec.h" |
| 27 | +#include "Framework/SerializationMethods.h" |
| 28 | +#include "DPLUtils/DPLRawParser.h" |
| 29 | +#include "Framework/InputRecordWalker.h" |
| 30 | +#include <string> |
| 31 | +#include <iostream> |
| 32 | +#include <algorithm> |
| 33 | +#include <vector> |
| 34 | +#include <gsl/span> |
| 35 | +#include <chrono> |
| 36 | +#include "CommonUtils/VerbosityConfig.h" |
| 37 | +#include "DataFormatsFT0/Digit.h" |
| 38 | +#include "DataFormatsFT0/ChannelData.h" |
| 39 | +#include "DataFormatsFT0/LookUpTable.h" |
| 40 | +#include "DataFormatsFIT/Triggers.h" |
| 41 | + |
| 42 | +using namespace o2::framework; |
| 43 | + |
| 44 | +namespace o2 |
| 45 | +{ |
| 46 | +namespace ft0 |
| 47 | +{ |
| 48 | +class FT0DataDecoderDPLSpec : public Task |
| 49 | +{ |
| 50 | + public: |
| 51 | + FT0DataDecoderDPLSpec() = default; |
| 52 | + ~FT0DataDecoderDPLSpec() override = default; |
| 53 | + using Digit_t = o2::ft0::Digit; |
| 54 | + using ChannelData_t = o2::ft0::ChannelData; |
| 55 | + using LookupTable_t = o2::ft0::SingleLUT; |
| 56 | + static constexpr int sNorbits = 256; |
| 57 | + static constexpr int sNBC = 3564; |
| 58 | + static constexpr int sNlinksMax = 24; |
| 59 | + using NChDataBC_t = std::array<uint32_t, sNBC + 4>; |
| 60 | + using NChDataOrbitBC_t = std::array<NChDataBC_t, sNlinksMax>; |
| 61 | + std::array<std::array<uint32_t, 16>, sNlinksMax> mLUT; |
| 62 | + NChDataOrbitBC_t mPosChDataPerLinkOrbit[sNorbits]; |
| 63 | + uint8_t mFEEID_TCM; |
| 64 | + void init(InitContext& ic) final |
| 65 | + { |
| 66 | + |
| 67 | + auto ccdbUrl = ic.options().get<std::string>("ccdb-path"); |
| 68 | + auto lutPath = ic.options().get<std::string>("lut-path"); |
| 69 | + mVecDigits.resize(sNorbits * sNBC); |
| 70 | + mVecChannelData.resize(216 * sNorbits * sNBC); |
| 71 | + mVecTriggers.resize(sNBC); |
| 72 | + // mVecChannelDataBuf.resize(216*3564); |
| 73 | + mVecChannelDataBuf.resize(143); |
| 74 | + if (ccdbUrl != "") { |
| 75 | + LookupTable_t::setCCDBurl(ccdbUrl); |
| 76 | + } |
| 77 | + if (lutPath != "") { |
| 78 | + LookupTable_t::setLUTpath(lutPath); |
| 79 | + } |
| 80 | + LookupTable_t::Instance().printFullMap(); |
| 81 | + |
| 82 | + const auto& lut = LookupTable_t::Instance().getMapEntryPM2ChannelID(); |
| 83 | + const auto& tcm = LookupTable_t::Instance().getEntryCRU_TCM(); |
| 84 | + mFEEID_TCM = tcm.mLinkID + 12 * tcm.mEndPointID; |
| 85 | + std::array<uint32_t, 16> tmpChunk; |
| 86 | + std::fill_n(tmpChunk.begin(), 16, 0xff); |
| 87 | + std::fill_n(mLUT.begin(), 16, tmpChunk); |
| 88 | + for (const auto& entry : lut) { |
| 89 | + const auto& key = entry.first; |
| 90 | + const auto& value = entry.second; |
| 91 | + const auto feeID = key.mEntryCRU.mLinkID + 12 * key.mEntryCRU.mEndPointID; |
| 92 | + |
| 93 | + if (feeID >= sNlinksMax || key.mLocalChannelID >= 16) { |
| 94 | + LOG(warning) << "Incorrect entry: " << key.mEntryCRU.mFEEID << " " << key.mLocalChannelID; |
| 95 | + } else { |
| 96 | + mLUT[feeID][key.mLocalChannelID] = value; |
| 97 | + } |
| 98 | + } |
| 99 | + } |
| 100 | + std::vector<o2::ft0::ChannelData> mVecChannelData; |
| 101 | + std::vector<std::array<o2::ft0::ChannelData, 25 * 216>> mVecChannelDataBuf; // buffer per orbit |
| 102 | + std::vector<o2::ft0::Digit> mVecDigits; |
| 103 | + std::vector<o2::fit::Triggers> mVecTriggers; |
| 104 | + void run(ProcessingContext& pc) final; |
| 105 | +}; |
| 106 | + |
| 107 | +framework::DataProcessorSpec getFT0DataDecoderDPLSpec(bool askSTFDist) |
| 108 | +{ |
| 109 | + std::vector<OutputSpec> outputSpec; |
| 110 | + outputSpec.emplace_back(o2::header::gDataOriginFT0, "DIGITSBC", 0, Lifetime::Timeframe); |
| 111 | + outputSpec.emplace_back(o2::header::gDataOriginFT0, "DIGITSCH", 0, Lifetime::Timeframe); |
| 112 | + std::vector<InputSpec> inputSpec{{"STF", ConcreteDataTypeMatcher{"FT0", "RAWDATA"}, Lifetime::Optional}}; |
| 113 | + if (askSTFDist) { |
| 114 | + inputSpec.emplace_back("STFDist", "FLP", "DISTSUBTIMEFRAME", 0, Lifetime::Timeframe); |
| 115 | + } |
| 116 | + std::string dataProcName = "ft0-datadecoder-dpl"; |
| 117 | + LOG(info) << dataProcName; |
| 118 | + return DataProcessorSpec{ |
| 119 | + dataProcName, |
| 120 | + inputSpec, |
| 121 | + outputSpec, |
| 122 | + adaptFromTask<FT0DataDecoderDPLSpec>(), |
| 123 | + {o2::framework::ConfigParamSpec{"ccdb-path", VariantType::String, "", {"CCDB url which contains LookupTable"}}, |
| 124 | + o2::framework::ConfigParamSpec{"lut-path", VariantType::String, "", {"LookupTable path, e.g. FT0/LookupTable"}}}}; |
| 125 | +} |
| 126 | + |
| 127 | +} // namespace ft0 |
| 128 | +} // namespace o2 |
| 129 | + |
| 130 | +#endif /* O2_FITDATAREADERDPL_H */ |
| 131 | +#endif |
| 132 | +#endif |
0 commit comments