Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix reading of central trigger object in case of new mono trigger #262

Merged
merged 5 commits into from
Oct 15, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion .github/workflows/release_drafter.yml
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ on:
push:
# branches to consider in the event; optional, defaults to all
branches:
- master
- main

jobs:
update_release_draft:
Expand Down
32 changes: 24 additions & 8 deletions src/eventio/simtel/objects.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
''' Implementations of the simtel_array EventIO object types '''
import sys
import numpy as np
from io import BytesIO
import struct
Expand All @@ -20,13 +21,16 @@
unsigned_varint_arrays_differential,
varint_array,
varint,
unsigned_varint_array,
)
from ..version_handling import (
assert_exact_version,
assert_max_version,
assert_version_in
)

H_MAX_TRIG_TYPES = 4


def read_remaining_with_check(byte_stream, length):
pos = byte_stream.tell()
Expand All @@ -37,6 +41,15 @@


_s_int32 = struct.Struct('<i')
_s_float32 = struct.Struct('<f')


if sys.version_info < (3, 10):
def bit_count(num):
return bin(num).count("1")
else:
def bit_count(num):
return num.bit_count()

Check warning on line 52 in src/eventio/simtel/objects.py

View check run for this annotation

Codecov / codecov/patch

src/eventio/simtel/objects.py#L51-L52

Added lines #L51 - L52 were not covered by tests


class TelescopeObject(EventIOObject):
Expand Down Expand Up @@ -595,20 +608,23 @@
)

if version >= 2:
# konrad saves the trigger mask as crazy int, but it uses only 4 bits
# so it should be indentical to a normal unsigned int with 1 byte
event_info['teltrg_type_mask'] = read_array(
byte_stream, count=tels_trigger, dtype='uint8'
# read remaining data as varint_array only works with bytes, not a fileobj
data = read_remaining_with_check(byte_stream, self.header.content_size)
event_info['teltrg_type_mask'], bytes_read = unsigned_varint_array(
data, n_elements=tels_trigger,
)
assert np.all(event_info['teltrg_type_mask'] < 128), 'Unexpected trigger mask'
# back into a BytesIO to simplify code below
byte_stream = BytesIO(data[bytes_read:])

event_info['teltrg_time_by_type'] = {}
it = zip(event_info['triggered_telescopes'], event_info['teltrg_type_mask'])

for tel_id, mask in it:
# trigger times are only written if more than one trigger is there
if mask not in {0b001, 0b010, 0b100}:
# check the lowest 4 bits, individual times are only stored
# if more than one trigger fired
if bit_count(int(mask) & 0b1111) > 1:
event_info['teltrg_time_by_type'][tel_id] = {}
for trigger in range(3):
for trigger in range(H_MAX_TRIG_TYPES):
if bool_bit_from_pos(mask, trigger):
t = read_float(byte_stream)
event_info['teltrg_time_by_type'][tel_id][trigger] = t
Expand Down
Binary file added tests/resources/mono_trigger.simtel.zst
Binary file not shown.
9 changes: 9 additions & 0 deletions tests/simtel/test_simtel_objects.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,9 @@
from eventio.search_utils import (
yield_toplevel_of_type,
yield_n_subobjects,
yield_subobjects,
)
from eventio.simtel.objects import TriggerInformation

prod2_file = 'tests/resources/gamma_test.simtel.gz'
camorgan_v2_file = 'tests/resources/test_camorganv2.simtel.gz'
Expand Down Expand Up @@ -824,3 +826,10 @@ def test_2034():
assert isinstance(telescope_data, TelescopeData)
photo_electrons = next(telescope_data)
assert isinstance(photo_electrons, PhotoElectrons)


def test_mono_trigger():
"""Regression test for #261"""
with EventIOFile("tests/resources/mono_trigger.simtel.zst") as f:
for trigger in yield_subobjects(f, TriggerInformation):
trigger.parse()
Loading