Files
Jungfraujoch/receiver/host/Completion.cpp

51 lines
1.6 KiB
C++

// Copyright (2019-2022) Paul Scherrer Institute
// SPDX-License-Identifier: GPL-3.0-or-later
#include <bitset>
#include "Completion.h"
#include "../../common/JFJochException.h"
#include "../../common/Definitions.h"
inline uint64_t bit_concat(uint32_t high, uint32_t low) {
return (uint64_t(high) << 32) | low;
}
Completion parse_hw_completion(uint32_t tmp[16]) {
Completion c{};
c.handle = tmp[0];
c.module = tmp[1] & 0xFF;
c.packet_count = (tmp[1] & (0xFFFF0000)) >> 16;
uint64_t detector_frame_number = bit_concat(tmp[2], tmp[3]);
uint32_t parity = (std::bitset<32>(tmp[0]).count() + std::bitset<32>(tmp[1]).count()
+ std::bitset<32>(tmp[2]).count() + std::bitset<32>(tmp[3]).count()) % 2;
if (parity == 1)
throw JFJochException(JFJochExceptionCategory::HardwareParityError, "Wrong parity in work completion");
if (c.handle == HANDLE_START) {
c.type = Completion::Type::Start;
} else if (c.handle == HANDLE_END) {
c.type = Completion::Type::End;
c.frame_number = detector_frame_number;
} else {
c.type = Completion::Type::Image;
if (detector_frame_number == 0)
throw JFJochException(JFJochExceptionCategory::HardwareParityError, "Detector frame number cannot be zero");
else
c.frame_number = detector_frame_number - 1;
c.timestamp = bit_concat(tmp[4], tmp[5]);
c.bunchid = bit_concat(tmp[6], tmp[7]);
c.exptime = tmp[8];
c.debug = tmp[9];
c.packet_mask[0] = bit_concat(tmp[14], tmp[15]);
c.packet_mask[1] = bit_concat(tmp[12], tmp[13]);
}
return c;
}