From 66aeb448c33933f38de65f33db131af481ec470a Mon Sep 17 00:00:00 2001 From: Andrej Babic Date: Mon, 29 Jun 2020 13:49:17 +0200 Subject: [PATCH] Raw buffer reader --- scripts/BinaryBufferReader.py | 143 ++++++++++++++++++++++++++++++++++ 1 file changed, 143 insertions(+) create mode 100644 scripts/BinaryBufferReader.py diff --git a/scripts/BinaryBufferReader.py b/scripts/BinaryBufferReader.py new file mode 100644 index 0000000..50aa904 --- /dev/null +++ b/scripts/BinaryBufferReader.py @@ -0,0 +1,143 @@ +import numpy +from argparse import ArgumentParser +from ctypes import * + +FOLDER_MOD = 100000 +FILE_MOD = 1000 +FILE_EXTENSION = ".bin" +MODULE_X_SIZE = 1024 +MODULE_Y_SIZE = 512 +MODULE_N_PIXELS = MODULE_X_SIZE * MODULE_Y_SIZE +MODULE_N_BYTES = MODULE_N_PIXELS * 2 + + +class BufferBinaryFormat(Structure): + _pack_ = 1 + _fields_ = [("FORMAT_MARKER", c_char), + ("pulse_id", c_uint64), + ("frame_index", c_uint64), + ("daq_rec", c_uint64), + ("n_recv_packets", c_uint64), + ("module_id", c_uint64), + ("data", c_uint16 * MODULE_N_PIXELS)] + + +class BinaryBufferReader(object): + def __init__(self, root_folder, n_modules): + self.root_folder = root_folder + self.n_modules = n_modules + + def read_pulse_id(self, pulse_id): + + index_in_file = get_file_frame_index(pulse_id) + n_bytes_offset = index_in_file * sizeof(BufferBinaryFormat) + n_bytes_to_read = sizeof(BufferBinaryFormat) + + metadata = {"pulse_id": 0, + "frame_index": 0, + "daq_rec": 0, + "is_good_frame": True} + data = numpy.zeros(shape=[self.n_modules*MODULE_Y_SIZE*MODULE_X_SIZE], + dtype="byte") + metadata_init = False + + for i_module in range(self.n_modules): + device_name = "M%02d" % i_module + + filename = get_filename( + root_folder=self.root_folder, + device_name=device_name, + pulse_id=pulse_id) + + print("Reading file", filename, "for module", i_module) + + with open(filename, 'rb') as input_file: + input_file.seek(n_bytes_offset) + frame_buffer = BufferBinaryFormat.from_buffer_copy( + input_file.read(n_bytes_to_read)) + + if frame_buffer.FORMAT_MARKER == 0xBE: + is_good_frame = frame_buffer.n_recv_packets == 128 + + if is_good_frame: + if not metadata_init: + metadata["pulse_id"] = frame_buffer.pulse_id + metadata["frame_index"] = frame_buffer.frame_index + metadata["daq_rec"] = frame_buffer.daq_rec + + metadata_init = True + + if metadata["is_good_frame"]: + if metadata["pulse_id"] != frame_buffer.pulse_id: + metadata["is_good_frame"] = False + + if metadata["frame_index"] != frame_buffer.frame_index: + metadata["is_good_frame"] = False + + if metadata["daq_rec"] != frame_buffer.daq_rec: + metadata["is_good_frame"] = False + else: + metadata["is_good_frame"] = False + print("Module", i_module, + "n_lost_packets", 128-frame_buffer.n_recv_packets) + + start_byte_image = MODULE_N_BYTES * i_module + stop_byte_image = start_byte_image + MODULE_N_BYTES + + frame_data = numpy.frombuffer(frame_buffer.data, + count=MODULE_N_BYTES, + dtype="bytes") + + data[start_byte_image:stop_byte_image] = frame_data + + else: + metadata["is_good_frame"] = False + print("No data for module", i_module, "at pulse_id", pulse_id) + + if not metadata_init: + metadata["is_good_frame"] = False + + return metadata, data + + +def get_file_frame_index(pulse_id): + file_base = pulse_id // FILE_MOD + file_base *= FILE_MOD + + return pulse_id - file_base + + +def get_filename(root_folder, device_name, pulse_id): + folder_base = pulse_id // FOLDER_MOD + folder_base *= FOLDER_MOD + + file_base = pulse_id // FILE_MOD + file_base *= FILE_MOD + + return "%s/%s/%s/%s%s" % (root_folder, + device_name, + folder_base, + file_base, + FILE_EXTENSION) + + +def main(): + parser = ArgumentParser(description='Read DAQ Binary Buffer') + parser.add_argument('root_folder', type=str, + help="Absolute path to root folder of device.") + parser.add_argument('n_modules', type=int, + help="Number of modules to read from this device.") + parser.add_argument('pulse_id', type=int, + help="Pulse_id to retrieve.") + + arguments = parser.parse_args() + + reader = BinaryBufferReader(arguments.root_folder, + arguments.n_modules) + + metadata, data = reader.read_pulse_id(arguments.pulse_id) + print(metadata) + + +if __name__ == "__main__": + main()