1 #include <alpaka/alpaka.hpp> 18 template <
typename TAcc,
typename = std::enable_if_t<alpaka::isAccelerator<TAcc>>>
20 unsigned char const* __restrict__
data,
21 uint32_t
const* __restrict__
offsets,
22 int const* __restrict__
feds,
25 EcalElectronicsMappingDevice::ConstView eid2did,
26 uint32_t
const nbytesTotal)
const {
30 auto const ifed = alpaka::getIdx<alpaka::Grid, alpaka::Blocks>(acc)[0u];
31 auto const threadIdx = alpaka::getIdx<alpaka::Block, alpaka::Threads>(acc)[0u];
36 auto const fed =
feds[ifed];
37 auto const isBarrel = is_barrel(static_cast<uint8_t>(fed - 600));
39 auto const gridDim = alpaka::getWorkDiv<alpaka::Grid, alpaka::Blocks>(acc)[0u];
41 auto*
samples =
isBarrel ? digisDevEB.data()->data() : digisDevEE.data()->data();
42 auto* ids =
isBarrel ? digisDevEB.id() : digisDevEE.id();
43 auto* pChannelsCounter =
isBarrel ? &digisDevEB.size() : &digisDevEE.size();
54 auto const fed_header =
buffer[0];
60 uint32_t numbChannels(0);
83 for (uint8_t
i = 4;
i < 9; ++
i) {
84 for (uint8_t
j = 0;
j < 14; ++
j, ++ch) {
85 const uint8_t
shift =
j * 4;
88 const bool problematic =
91 if (!(regular || problematic)) {
101 uint8_t ntccblockwords =
isBarrel ? 18 : 36;
102 auto const* tower_blocks_start =
buffer + 9 + ntccblockwords + 6;
103 auto const* trailer =
buffer + (size / 8 - 1);
104 auto const* current_tower_block = tower_blocks_start;
106 uint8_t next_tower_id = exp_ttids[iCh];
107 while (current_tower_block < trailer && iCh < numbChannels) {
108 auto const w = *current_tower_block;
115 while (exp_ttids[iCh] < next_tower_id) {
123 if (ttid != next_tower_id) {
124 next_tower_id = find_next_tower_block(current_tower_block, trailer,
bx, lv1);
133 next_tower_id = exp_ttids[iCh];
135 uint16_t
const dccbx =
bx & 0xfff;
136 uint16_t
const dccl1 = lv1 & 0xfff;
138 if (fov >= 1 && !is_synced_towerblock(dccbx, bxlocal, dccl1, lv1local)) {
139 current_tower_block += block_length;
145 uint32_t
const nchannels = (block_length - 1) / 3;
147 bool bad_block =
false;
148 auto& ch_with_bad_block = alpaka::declareSharedVar<uint32_t, __COUNTER__>(acc);
153 alpaka::syncBlockThreads(acc);
155 auto const threadsPerBlock = alpaka::getWorkDiv<alpaka::Block, alpaka::Threads>(acc)[0u];
159 for (uint32_t
i = 0;
i < nchannels;
i += threadsPerBlock) {
167 if (channel < nchannels && channel < ch_with_bad_block) {
169 wdata = current_tower_block[1 + channel * 3];
170 stripid = wdata & 0x7;
171 xtalid = (wdata >> 4) & 0x7;
174 if (stripid < ElectronicsIdGPU::MIN_STRIPID || stripid > ElectronicsIdGPU::MAX_STRIPID ||
175 xtalid < ElectronicsIdGPU::MIN_XTALID || xtalid > ElectronicsIdGPU::MAX_XTALID) {
180 auto const prev_channel = channel - 1;
181 auto const prevwdata = current_tower_block[1 + prev_channel * 3];
182 uint8_t
const laststripid = prevwdata & 0x7;
183 uint8_t
const lastxtalid = (prevwdata >> 4) & 0x7;
184 if ((stripid == laststripid && xtalid <= lastxtalid) || (stripid < laststripid)) {
191 if (bad_block && channel < ch_with_bad_block) {
192 alpaka::atomicMin(acc, &ch_with_bad_block, channel, alpaka::hierarchy::Threads{});
196 alpaka::syncBlockThreads(acc);
199 if (channel >= nchannels || channel >= ch_with_bad_block) {
203 ElectronicsIdGPU
eid{fed2dcc(fed), ttid, stripid, xtalid};
204 auto const didraw =
isBarrel ? compute_ebdetid(
eid) : eid2did[
eid.linearIndex()].rawid();
210 uint16_t sampleValues[kSampleSize];
211 sampleValues[0] = (wdata >> 16) & 0x3fff;
212 sampleValues[1] = (wdata >> 32) & 0x3fff;
213 sampleValues[2] = (wdata >> 48) & 0x3fff;
214 auto const wdata1 = current_tower_block[2 + channel * 3];
215 sampleValues[3] = wdata1 & 0x3fff;
216 sampleValues[4] = (wdata1 >> 16) & 0x3fff;
217 sampleValues[5] = (wdata1 >> 32) & 0x3fff;
218 sampleValues[6] = (wdata1 >> 48) & 0x3fff;
219 auto const wdata2 = current_tower_block[3 + channel * 3];
220 sampleValues[7] = wdata2 & 0x3fff;
221 sampleValues[8] = (wdata2 >> 16) & 0x3fff;
222 sampleValues[9] = (wdata2 >> 32) & 0x3fff;
225 bool isSaturation =
true;
226 short firstGainZeroSampID{-1}, firstGainZeroSampADC{-1};
227 for (uint32_t si = 0; si < kSampleSize; ++si) {
228 if (
gainId(sampleValues[si]) == 0) {
229 firstGainZeroSampID = si;
230 firstGainZeroSampADC =
adc(sampleValues[si]);
234 if (firstGainZeroSampID != -1) {
235 unsigned int plateauEnd =
std::min(kSampleSize, (
unsigned int)(firstGainZeroSampID + 5));
236 for (
unsigned int s = firstGainZeroSampID;
s < plateauEnd;
s++) {
237 if (!(
gainId(sampleValues[
s]) == 0 &&
adc(sampleValues[
s]) == firstGainZeroSampADC)) {
238 isSaturation =
false;
243 if (firstGainZeroSampID < 3) {
244 isSaturation =
false;
251 bool gainSwitchError =
false;
252 for (
unsigned int si = 1; si < kSampleSize; ++si) {
253 if ((
gainId(sampleValues[si - 1]) >
gainId(sampleValues[si])) && numGain < 5)
254 gainSwitchError =
true;
255 if (
gainId(sampleValues[si - 1]) ==
gainId(sampleValues[si]))
268 std::memcpy(&
samples[
pos * kSampleSize], sampleValues, kSampleSize *
sizeof(uint16_t));
271 current_tower_block += block_length;
277 uint32_t
const nbytes,
278 uint32_t
const nbytes_per_row = 20)
const {
279 for (uint32_t
i = 0;
i < nbytes; ++
i) {
280 if (
i % nbytes_per_row == 0 &&
i > 0)
287 for (uint32_t
i = 0;
i < size; ++
i) {
288 uint8_t
const b61 = (
buffer[
i] >> 61) & 0x1;
289 uint8_t
const b62 = (
buffer[
i] >> 62) & 0x1;
290 uint8_t
const b63 = (
buffer[
i] >> 63) & 0x1;
291 printf(
"[word: %u] %u%u%u\n",
i, b63, b62, b61);
295 ALPAKA_FN_INLINE ALPAKA_FN_ACC
bool is_barrel(uint8_t dccid)
const {
296 return dccid >= ElectronicsIdGPU::MIN_DCCID_EBM && dccid <= ElectronicsIdGPU::MAX_DCCID_EBP;
299 ALPAKA_FN_INLINE ALPAKA_FN_ACC uint8_t
fed2dcc(
int fed)
const {
return static_cast<uint8_t
>(fed - 600); }
303 return ((
dcc >= ElectronicsIdGPU::MIN_DCCID_EBM &&
dcc <= ElectronicsIdGPU::MAX_DCCID_EBM)) ? -1 : 1;
309 uint32_t
const lv1)
const {
310 const auto* next_tower_block = current_tower_block + 1;
323 while (next_tower_block < trailer) {
324 if ((*next_tower_block &
mask) ==
sign) {
325 current_tower_block = next_tower_block;
336 uint16_t
const dccl1,
337 uint16_t
const l1)
const {
338 bool const bxsync = (
bx == 0 && dccbx == 3564) || (
bx == dccbx && dccbx != 3564);
339 bool const l1sync = (l1 == ((dccl1 - 1) & 0xfff));
340 return bxsync && l1sync;
345 return (
tower > 12 &&
tower < 21) || (
tower > 28 && tower < 37) || (tower > 44 &&
tower < 53) ||
351 auto const dcc =
eid.dccId();
354 auto const xtal =
eid.xtalId();
358 bool EBPlus = (zside_for_eb(
eid) > 0);
359 bool EBMinus = !EBPlus;
361 if (zside_for_eb(
eid) < 0) {
362 smid =
dcc + 19 - ElectronicsIdGPU::DCCID_PHI0_EBM;
363 iphi = (smid - 19) * ElectronicsIdGPU::kCrystalsInPhi;
364 iphi += 5 * ((
tower - 1) % ElectronicsIdGPU::kTowersInPhi);
366 smid =
dcc + 1 - ElectronicsIdGPU::DCCID_PHI0_EBP;
367 iphi = (smid - 1) * ElectronicsIdGPU::kCrystalsInPhi;
368 iphi += 5 * (ElectronicsIdGPU::kTowersInPhi - ((
tower - 1) % ElectronicsIdGPU::kTowersInPhi) - 1);
371 bool RightTower = right_tower_for_eb(
tower);
372 int ieta = 5 * ((
tower - 1) / ElectronicsIdGPU::kTowersInPhi) + 1;
375 if (
strip % 2 == 1) {
377 iphi += (xtal - 1) + 1;
379 iphi += (4 - (xtal - 1)) + 1;
382 iphi += (4 - (xtal - 1)) + 1;
384 iphi += (xtal - 1) + 1;
388 if (
strip % 2 == 1) {
390 iphi += (4 - (xtal - 1)) + 1;
392 iphi += (xtal - 1) + 1;
395 iphi += (xtal - 1) + 1;
397 iphi += (4 - (xtal - 1)) + 1;
401 if (zside_for_eb(
eid) < 0)
405 return did.rawId() | ((
ieta > 0) ? (0x10000 | (
ieta << 9)) : ((-
ieta) << 9)) | (
iphi & 0x1FF);
408 ALPAKA_FN_INLINE ALPAKA_FN_ACC
int adc(uint16_t
sample)
const {
return sample & 0xfff; }
418 uint32_t
const nfedsWithData,
419 uint32_t
const nbytesTotal) {
428 auto workDiv = cms::alpakatools::make_workdiv<Acc1D>(nfedsWithData, 32);
429 alpaka::exec<Acc1D>(
queue,
432 inputDevice.
data.data(),
434 inputDevice.
feds.data(),
ALPAKA_FN_ACC int dcc(int ieta, int iphi)
common ppss p3p6s2 common epss epspn46 common const1 w2
void unpackRaw(Queue &queue, InputDataHost const &inputHost, EcalDigiDeviceCollection &digisDevEB, EcalDigiDeviceCollection &digisDevEE, EcalElectronicsMappingDevice const &mapping, uint32_t const nfedsWithData, uint32_t const nbytesTotal)
ALPAKA_FN_ACC void operator()(TAcc const &acc, unsigned char const *__restrict__ data, uint32_t const *__restrict__ offsets, int const *__restrict__ feds, EcalDigiDeviceCollection::View digisDevEB, EcalDigiDeviceCollection::View digisDevEE, EcalElectronicsMappingDevice::ConstView eid2did, uint32_t const nbytesTotal) const
ALPAKA_FN_INLINE ALPAKA_FN_ACC uint8_t find_next_tower_block(uint64_t const *¤t_tower_block, uint64_t const *trailer, uint32_t const bx, uint32_t const lv1) const
ALPAKA_FN_INLINE ALPAKA_FN_ACC uint32_t compute_ebdetid(ElectronicsIdGPU const &eid) const
ALPAKA_FN_INLINE ALPAKA_FN_ACC bool is_synced_towerblock(uint16_t const dccbx, uint16_t const bx, uint16_t const dccl1, uint16_t const l1) const
ALPAKA_FN_INLINE ALPAKA_FN_ACC bool is_barrel(uint8_t dccid) const
ALPAKA_FN_INLINE ALPAKA_FN_ACC bool right_tower_for_eb(int tower) const
ALPAKA_FN_INLINE ALPAKA_FN_ACC int gainId(uint16_t sample) const
PortableCollection< EcalElectronicsMappingSoA > EcalElectronicsMappingDevice
ALPAKA_FN_INLINE ALPAKA_FN_ACC uint8_t fed2dcc(int fed) const
constexpr int gainId(sample_type sample)
get the gainId (2 bits)
unsigned long long uint64_t
ALPAKA_FN_INLINE ALPAKA_FN_ACC int zside_for_eb(ElectronicsIdGPU const &eid) const
static constexpr unsigned int sampleSize
PortableCollection< EcalDigiSoA > EcalDigiDeviceCollection
char data[epos_bytes_allocation]
static unsigned int const shift
ALPAKA_FN_INLINE ALPAKA_FN_ACC int adc(uint16_t sample) const
T1 atomicMin(T1 *a, T2 b)
ALPAKA_FN_INLINE ALPAKA_FN_ACC void print_first3bits(uint64_t const *buffer, uint32_t size) const
T1 atomicAdd(T1 *a, T2 b)
ALPAKA_FN_INLINE ALPAKA_FN_ACC void print_raw_buffer(uint8_t const *const buffer, uint32_t const nbytes, uint32_t const nbytes_per_row=20) const
uint16_t *__restrict__ uint16_t const *__restrict__ adc