Skip to content

Commit 657c365

Browse files
committed
Add test and fix missing module data in R1v1 format
1 parent 3a4deee commit 657c365

File tree

2 files changed

+47
-14
lines changed

2 files changed

+47
-14
lines changed

src/ctapipe_io_lst/__init__.py

+17-14
Original file line numberDiff line numberDiff line change
@@ -479,12 +479,9 @@ def fill_from_cta_r1(self, array_event, zfits_event):
479479
offset = self.data_stream.waveform_offset
480480
pixel_id_map = self.camera_config.pixel_id_map
481481

482-
# FIXME: missing modules / pixels
483-
# FIXME: DVR? should not happen in r1 but dl0, but our own converter uses the old R1
484-
485482
# reorder to nominal pixel order
486483
pixel_status = _reorder_pixel_status(
487-
zfits_event.pixel_status, pixel_id_map, set_dvr_bits=True
484+
zfits_event.pixel_status, pixel_id_map, set_dvr_bits=not self.dvr_applied,
488485
)
489486

490487
n_channels = zfits_event.num_channels
@@ -495,11 +492,16 @@ def fill_from_cta_r1(self, array_event, zfits_event):
495492
raw_waveform = zfits_event.waveform.reshape(readout_shape)
496493
waveform = raw_waveform.astype(np.float32) / scale - offset
497494

495+
if self.dvr_applied:
496+
stored_pixels = (zfits_event.pixel_status & PixelStatus.DVR_STATUS) > 0
497+
else:
498+
stored_pixels = slice(None) # all pixels stored
499+
498500
reordered_waveform = np.full((n_channels, N_PIXELS, n_samples), 0.0, dtype=np.float32)
499-
reordered_waveform[:, pixel_id_map] = waveform
501+
reordered_waveform[:, pixel_id_map[stored_pixels]] = waveform
500502
waveform = reordered_waveform
501503

502-
# FIXME, check using evb_preprocessing and make ctapipe support 2 gains
504+
503505
if zfits_event.num_channels == 2:
504506
selected_gain_channel = None
505507
else:
@@ -535,16 +537,17 @@ def fill_from_cta_r1(self, array_event, zfits_event):
535537
)
536538

537539
def fill_lst_from_ctar1(self, zfits_event):
540+
pixel_status = _reorder_pixel_status(
541+
zfits_event.pixel_status,
542+
self.pixel_id_map,
543+
set_dvr_bits=not self.dvr_applied,
544+
)
538545
evt = LSTEventContainer(
539-
pixel_status=zfits_event.pixel_status.copy(),
546+
pixel_status=pixel_status,
540547
first_capacitor_id=zfits_event.first_cell_id,
541548
calibration_monitoring_id=zfits_event.calibration_monitoring_id,
542549
local_clock_counter=zfits_event.module_hires_local_clock_counter,
543550
)
544-
# set bits for dvr if not already set
545-
if not self.dvr_applied:
546-
not_broken = get_channel_info(evt.pixel_status) != 0
547-
evt.pixel_status[not_broken] |= PixelStatus.DVR_STATUS_0
548551

549552
if zfits_event.debug is not None:
550553
debug = zfits_event.debug
@@ -971,7 +974,7 @@ def tag_flatfield_events(self, array_event):
971974
'''
972975
tel_id = self.tel_id
973976
waveform = array_event.r1.tel[tel_id].waveform
974-
977+
975978
if waveform.ndim == 3:
976979
image = waveform[HIGH_GAIN].sum(axis=1)
977980
else:
@@ -981,7 +984,7 @@ def tag_flatfield_events(self, array_event):
981984
n_in_range = np.count_nonzero(in_range)
982985

983986
looks_like_ff = n_in_range >= self.min_flatfield_pixel_fraction * image.size
984-
987+
985988
if looks_like_ff:
986989
# Tag as FF only events with 2-gains waveforms: both gains are needed for calibration
987990
if waveform.ndim == 3:
@@ -1091,7 +1094,7 @@ def fill_r0r1_camera_container(self, zfits_event):
10911094
if CTAPIPE_0_20:
10921095
# reorder to nominal pixel order
10931096
pixel_status = _reorder_pixel_status(
1094-
zfits_event.pixel_status, pixel_id_map, set_dvr_bits=True
1097+
zfits_event.pixel_status, pixel_id_map, set_dvr_bits=not self.dvr_applied
10951098
)
10961099
r1.pixel_status = pixel_status
10971100
r1.event_time = cta_high_res_to_time(

src/ctapipe_io_lst/tests/test_lsteventsource.py

+30
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@
2121
test_r0_path_all_streams = test_r0_dir / 'LST-1.1.Run02008.0000_first50.fits.fz'
2222

2323
test_missing_module_path = test_data / 'real/R0/20210215/LST-1.1.Run03669.0000_first50.fits.fz'
24+
test_missing_module_r1v1_path = test_data / 'real/R0/20240310/LST-1.1.Run17016.0000_first10.fits.fz'
2425

2526
test_drive_report = test_data / 'real/monitoring/DrivePositioning/DrivePosition_log_20200218.txt'
2627

@@ -142,6 +143,35 @@ def test_missing_modules():
142143
assert np.all(event.r0.tel[1].waveform[:, 514] == fill)
143144

144145

146+
def test_missing_modules_r1v1():
147+
from ctapipe_io_lst import LSTEventSource
148+
source = LSTEventSource(
149+
test_missing_module_r1v1_path,
150+
apply_drs4_corrections=False,
151+
pointing_information=False,
152+
)
153+
154+
assert source.lst_service.telescope_id == 1
155+
assert source.lst_service.num_modules == 264
156+
157+
n_events = 0
158+
for event in source:
159+
n_events += 1
160+
# one module missing, so 7 pixels
161+
assert np.count_nonzero(event.mon.tel[1].pixel_status.hardware_failing_pixels) == N_PIXELS_MODULE * N_GAINS
162+
assert np.count_nonzero(event.r0.tel[1].waveform == 0.0) == N_PIXELS_MODULE * N_SAMPLES * N_GAINS
163+
164+
missing_gain, missing_pixel = np.nonzero(event.mon.tel[1].pixel_status.hardware_failing_pixels)
165+
# 514 is one of the missing pixels
166+
for gain, pixel in zip(missing_gain, missing_pixel):
167+
np.testing.assert_equal(event.r0.tel[1].waveform[gain, pixel], 0.0)
168+
169+
if CTAPIPE_0_20:
170+
np.testing.assert_equal(event.lst.tel[1].evt.pixel_status, event.r1.tel[1].pixel_status)
171+
172+
assert n_events == 40
173+
174+
145175
def test_gain_selected():
146176
from ctapipe_io_lst import LSTEventSource
147177

0 commit comments

Comments
 (0)