imap-processing 0.16.2__py3-none-any.whl → 0.18.0__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of imap-processing might be problematic. Click here for more details.
- imap_processing/_version.py +2 -2
- imap_processing/ccsds/excel_to_xtce.py +12 -0
- imap_processing/cdf/config/imap_codice_global_cdf_attrs.yaml +6 -6
- imap_processing/cdf/config/imap_codice_l1a_variable_attrs.yaml +35 -0
- imap_processing/cdf/config/imap_codice_l1b_variable_attrs.yaml +35 -0
- imap_processing/cdf/config/imap_codice_l2_variable_attrs.yaml +24 -0
- imap_processing/cdf/config/imap_hi_variable_attrs.yaml +8 -8
- imap_processing/cdf/config/imap_hit_global_cdf_attrs.yaml +1 -1
- imap_processing/cdf/config/imap_hit_l1a_variable_attrs.yaml +163 -100
- imap_processing/cdf/config/imap_hit_l2_variable_attrs.yaml +398 -415
- imap_processing/cdf/config/imap_ialirt_l1_variable_attrs.yaml +97 -54
- imap_processing/cdf/config/imap_idex_global_cdf_attrs.yaml +9 -9
- imap_processing/cdf/config/imap_idex_l2b_variable_attrs.yaml +233 -57
- imap_processing/cdf/config/imap_idex_l2c_variable_attrs.yaml +16 -90
- imap_processing/cdf/config/imap_lo_global_cdf_attrs.yaml +30 -0
- imap_processing/cdf/config/imap_mag_global_cdf_attrs.yaml +15 -1
- imap_processing/cdf/config/imap_swapi_variable_attrs.yaml +19 -0
- imap_processing/cdf/config/imap_swe_l1b_variable_attrs.yaml +20 -0
- imap_processing/cdf/config/imap_swe_l2_variable_attrs.yaml +39 -0
- imap_processing/cdf/config/imap_ultra_global_cdf_attrs.yaml +168 -0
- imap_processing/cdf/config/imap_ultra_l1a_variable_attrs.yaml +103 -2
- imap_processing/cdf/config/imap_ultra_l1b_variable_attrs.yaml +91 -11
- imap_processing/cdf/utils.py +7 -1
- imap_processing/cli.py +42 -13
- imap_processing/codice/codice_l1a.py +125 -78
- imap_processing/codice/codice_l1b.py +1 -1
- imap_processing/codice/codice_l2.py +0 -9
- imap_processing/codice/constants.py +481 -498
- imap_processing/hi/hi_l1a.py +4 -4
- imap_processing/hi/hi_l1b.py +2 -2
- imap_processing/hi/packet_definitions/TLM_HI_COMBINED_SCI.xml +218 -38
- imap_processing/hit/hit_utils.py +2 -2
- imap_processing/hit/l0/decom_hit.py +4 -3
- imap_processing/hit/l1a/hit_l1a.py +64 -24
- imap_processing/hit/l1b/constants.py +5 -0
- imap_processing/hit/l1b/hit_l1b.py +18 -16
- imap_processing/hit/l2/constants.py +1 -1
- imap_processing/hit/l2/hit_l2.py +4 -4
- imap_processing/ialirt/constants.py +21 -0
- imap_processing/ialirt/generate_coverage.py +188 -0
- imap_processing/ialirt/l0/parse_mag.py +62 -5
- imap_processing/ialirt/l0/process_swapi.py +1 -1
- imap_processing/ialirt/l0/process_swe.py +23 -7
- imap_processing/ialirt/utils/constants.py +22 -16
- imap_processing/ialirt/utils/create_xarray.py +42 -19
- imap_processing/idex/idex_constants.py +8 -5
- imap_processing/idex/idex_l2b.py +554 -58
- imap_processing/idex/idex_l2c.py +30 -196
- imap_processing/lo/l0/lo_apid.py +1 -0
- imap_processing/lo/l0/lo_star_sensor.py +48 -0
- imap_processing/lo/l1a/lo_l1a.py +74 -30
- imap_processing/lo/packet_definitions/lo_xtce.xml +5359 -106
- imap_processing/mag/constants.py +1 -0
- imap_processing/mag/l0/decom_mag.py +9 -6
- imap_processing/mag/l0/mag_l0_data.py +46 -0
- imap_processing/mag/l1d/__init__.py +0 -0
- imap_processing/mag/l1d/mag_l1d.py +133 -0
- imap_processing/mag/l1d/mag_l1d_data.py +588 -0
- imap_processing/mag/l2/__init__.py +0 -0
- imap_processing/mag/l2/mag_l2.py +25 -20
- imap_processing/mag/l2/mag_l2_data.py +191 -130
- imap_processing/quality_flags.py +20 -2
- imap_processing/spice/geometry.py +25 -3
- imap_processing/spice/pointing_frame.py +1 -1
- imap_processing/spice/spin.py +4 -0
- imap_processing/spice/time.py +51 -0
- imap_processing/swapi/l1/swapi_l1.py +12 -2
- imap_processing/swapi/l2/swapi_l2.py +59 -14
- imap_processing/swapi/swapi_utils.py +1 -1
- imap_processing/swe/l1b/swe_l1b.py +11 -4
- imap_processing/swe/l2/swe_l2.py +111 -17
- imap_processing/ultra/constants.py +49 -1
- imap_processing/ultra/l0/decom_tools.py +28 -14
- imap_processing/ultra/l0/decom_ultra.py +225 -15
- imap_processing/ultra/l0/ultra_utils.py +281 -8
- imap_processing/ultra/l1a/ultra_l1a.py +77 -8
- imap_processing/ultra/l1b/cullingmask.py +3 -3
- imap_processing/ultra/l1b/de.py +53 -15
- imap_processing/ultra/l1b/extendedspin.py +26 -2
- imap_processing/ultra/l1b/lookup_utils.py +171 -50
- imap_processing/ultra/l1b/quality_flag_filters.py +14 -0
- imap_processing/ultra/l1b/ultra_l1b_culling.py +198 -5
- imap_processing/ultra/l1b/ultra_l1b_extended.py +304 -66
- imap_processing/ultra/l1c/helio_pset.py +54 -7
- imap_processing/ultra/l1c/spacecraft_pset.py +9 -1
- imap_processing/ultra/l1c/ultra_l1c.py +2 -0
- imap_processing/ultra/l1c/ultra_l1c_pset_bins.py +106 -109
- imap_processing/ultra/packet_definitions/ULTRA_SCI_COMBINED.xml +3 -3
- imap_processing/ultra/utils/ultra_l1_utils.py +13 -1
- imap_processing/utils.py +20 -42
- {imap_processing-0.16.2.dist-info → imap_processing-0.18.0.dist-info}/METADATA +2 -2
- {imap_processing-0.16.2.dist-info → imap_processing-0.18.0.dist-info}/RECORD +95 -103
- imap_processing/lo/l0/data_classes/star_sensor.py +0 -98
- imap_processing/lo/l0/utils/lo_base.py +0 -57
- imap_processing/ultra/lookup_tables/Angular_Profiles_FM45_LeftSlit.csv +0 -526
- imap_processing/ultra/lookup_tables/Angular_Profiles_FM45_RightSlit.csv +0 -526
- imap_processing/ultra/lookup_tables/Angular_Profiles_FM90_LeftSlit.csv +0 -526
- imap_processing/ultra/lookup_tables/Angular_Profiles_FM90_RightSlit.csv +0 -524
- imap_processing/ultra/lookup_tables/EgyNorm.mem.csv +0 -32769
- imap_processing/ultra/lookup_tables/FM45_Startup1_ULTRA_IMGPARAMS_20240719.csv +0 -2
- imap_processing/ultra/lookup_tables/FM90_Startup1_ULTRA_IMGPARAMS_20240719.csv +0 -2
- imap_processing/ultra/lookup_tables/dps_grid45_compressed.cdf +0 -0
- imap_processing/ultra/lookup_tables/ultra45_back-pos-luts.csv +0 -4097
- imap_processing/ultra/lookup_tables/ultra45_tdc_norm.csv +0 -2050
- imap_processing/ultra/lookup_tables/ultra90_back-pos-luts.csv +0 -4097
- imap_processing/ultra/lookup_tables/ultra90_tdc_norm.csv +0 -2050
- imap_processing/ultra/lookup_tables/yadjust.csv +0 -257
- {imap_processing-0.16.2.dist-info → imap_processing-0.18.0.dist-info}/LICENSE +0 -0
- {imap_processing-0.16.2.dist-info → imap_processing-0.18.0.dist-info}/WHEEL +0 -0
- {imap_processing-0.16.2.dist-info → imap_processing-0.18.0.dist-info}/entry_points.txt +0 -0
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
"""Decommutates Ultra CCSDS packets."""
|
|
2
2
|
|
|
3
3
|
import logging
|
|
4
|
+
import math
|
|
4
5
|
from collections import defaultdict
|
|
5
6
|
from typing import cast
|
|
6
7
|
|
|
@@ -15,10 +16,21 @@ from imap_processing.ultra.l0.decom_tools import (
|
|
|
15
16
|
read_image_raw_events_binary,
|
|
16
17
|
)
|
|
17
18
|
from imap_processing.ultra.l0.ultra_utils import (
|
|
19
|
+
CMD_ECHO_MAP,
|
|
20
|
+
ENERGY_EVENT_FIELD_RANGES,
|
|
21
|
+
ENERGY_RATES_KEYS,
|
|
18
22
|
EVENT_FIELD_RANGES,
|
|
19
23
|
RATES_KEYS,
|
|
24
|
+
ULTRA_ENERGY_EVENTS,
|
|
25
|
+
ULTRA_ENERGY_RATES,
|
|
26
|
+
ULTRA_ENERGY_SPECTRA,
|
|
27
|
+
ULTRA_EVENTS,
|
|
28
|
+
ULTRA_PRI_1_EVENTS,
|
|
29
|
+
ULTRA_PRI_2_EVENTS,
|
|
30
|
+
ULTRA_PRI_3_EVENTS,
|
|
31
|
+
ULTRA_PRI_4_EVENTS,
|
|
20
32
|
ULTRA_RATES,
|
|
21
|
-
|
|
33
|
+
PacketProperties,
|
|
22
34
|
)
|
|
23
35
|
from imap_processing.utils import convert_to_binary_string
|
|
24
36
|
|
|
@@ -26,7 +38,7 @@ logging.basicConfig(level=logging.INFO)
|
|
|
26
38
|
logger = logging.getLogger(__name__)
|
|
27
39
|
|
|
28
40
|
|
|
29
|
-
def process_ultra_tof(ds: xr.Dataset) -> xr.Dataset:
|
|
41
|
+
def process_ultra_tof(ds: xr.Dataset, packet_props: PacketProperties) -> xr.Dataset:
|
|
30
42
|
"""
|
|
31
43
|
Unpack and decode Ultra TOF packets.
|
|
32
44
|
|
|
@@ -34,6 +46,9 @@ def process_ultra_tof(ds: xr.Dataset) -> xr.Dataset:
|
|
|
34
46
|
----------
|
|
35
47
|
ds : xarray.Dataset
|
|
36
48
|
TOF dataset.
|
|
49
|
+
packet_props : PacketProperties
|
|
50
|
+
Information that defines properties of the packet including the pixel window
|
|
51
|
+
dimensions of images and number of image panes.
|
|
37
52
|
|
|
38
53
|
Returns
|
|
39
54
|
-------
|
|
@@ -42,14 +57,35 @@ def process_ultra_tof(ds: xr.Dataset) -> xr.Dataset:
|
|
|
42
57
|
"""
|
|
43
58
|
scalar_keys = [key for key in ds.data_vars if key not in ("packetdata", "sid")]
|
|
44
59
|
|
|
60
|
+
image_planes = packet_props.image_planes
|
|
61
|
+
rows = packet_props.pixel_window_rows
|
|
62
|
+
cols = packet_props.pixel_window_columns
|
|
63
|
+
planes_per_packet = packet_props.image_planes_per_packet
|
|
64
|
+
|
|
65
|
+
if (
|
|
66
|
+
image_planes is None
|
|
67
|
+
or rows is None
|
|
68
|
+
or cols is None
|
|
69
|
+
or planes_per_packet is None
|
|
70
|
+
):
|
|
71
|
+
raise ValueError(
|
|
72
|
+
"Packet properties must specify pixel window dimensions, "
|
|
73
|
+
"width bit, image planes, and image planes per packet for this packet type."
|
|
74
|
+
)
|
|
75
|
+
# Calculate the number of image packets based on the number of image panes and
|
|
76
|
+
# planes per packet.
|
|
77
|
+
# There may be cases where the last packet has fewer planes than the
|
|
78
|
+
# planes_per_packet, to account for this, we use ceiling division.
|
|
79
|
+
num_image_packets = math.ceil(image_planes / planes_per_packet)
|
|
80
|
+
|
|
45
81
|
decom_data: defaultdict[str, list[np.ndarray]] = defaultdict(list)
|
|
46
82
|
decom_data["packetdata"] = []
|
|
47
83
|
valid_epoch = []
|
|
48
|
-
width = cast(int, ULTRA_TOF.width)
|
|
49
|
-
mantissa_bit_length = cast(int, ULTRA_TOF.mantissa_bit_length)
|
|
50
84
|
|
|
51
85
|
for val, group in ds.groupby("epoch"):
|
|
52
|
-
if set(group["sid"].values) >= set(
|
|
86
|
+
if set(group["sid"].values) >= set(
|
|
87
|
+
np.arange(0, image_planes, planes_per_packet)
|
|
88
|
+
):
|
|
53
89
|
valid_epoch.append(val)
|
|
54
90
|
group.sortby("sid")
|
|
55
91
|
|
|
@@ -57,13 +93,12 @@ def process_ultra_tof(ds: xr.Dataset) -> xr.Dataset:
|
|
|
57
93
|
decom_data[key].append(group[key].values)
|
|
58
94
|
|
|
59
95
|
image = []
|
|
60
|
-
for i in range(
|
|
96
|
+
for i in range(num_image_packets):
|
|
61
97
|
binary = convert_to_binary_string(group["packetdata"].values[i])
|
|
62
98
|
decompressed = decompress_image(
|
|
63
99
|
group["p00"].values[i],
|
|
64
100
|
binary,
|
|
65
|
-
|
|
66
|
-
mantissa_bit_length,
|
|
101
|
+
packet_props,
|
|
67
102
|
)
|
|
68
103
|
image.append(decompressed)
|
|
69
104
|
|
|
@@ -76,9 +111,9 @@ def process_ultra_tof(ds: xr.Dataset) -> xr.Dataset:
|
|
|
76
111
|
|
|
77
112
|
coords = {
|
|
78
113
|
"epoch": np.array(valid_epoch, dtype=np.uint64),
|
|
79
|
-
"sid": xr.DataArray(np.arange(
|
|
80
|
-
"row": xr.DataArray(np.arange(
|
|
81
|
-
"column": xr.DataArray(np.arange(
|
|
114
|
+
"sid": xr.DataArray(np.arange(num_image_packets), dims=["sid"], name="sid"),
|
|
115
|
+
"row": xr.DataArray(np.arange(rows), dims=["row"], name="row"),
|
|
116
|
+
"column": xr.DataArray(np.arange(cols), dims=["column"], name="column"),
|
|
82
117
|
}
|
|
83
118
|
|
|
84
119
|
dataset = xr.Dataset(coords=coords)
|
|
@@ -136,7 +171,7 @@ def get_event_id(shcoarse: NDArray) -> NDArray:
|
|
|
136
171
|
return np.array(event_ids, dtype=np.int64)
|
|
137
172
|
|
|
138
173
|
|
|
139
|
-
def process_ultra_events(ds: xr.Dataset) -> xr.Dataset:
|
|
174
|
+
def process_ultra_events(ds: xr.Dataset, apid: int) -> xr.Dataset:
|
|
140
175
|
"""
|
|
141
176
|
Unpack and decode Ultra EVENTS packets.
|
|
142
177
|
|
|
@@ -144,12 +179,28 @@ def process_ultra_events(ds: xr.Dataset) -> xr.Dataset:
|
|
|
144
179
|
----------
|
|
145
180
|
ds : xarray.Dataset
|
|
146
181
|
Events dataset.
|
|
182
|
+
apid : int
|
|
183
|
+
APID of the events dataset.
|
|
147
184
|
|
|
148
185
|
Returns
|
|
149
186
|
-------
|
|
150
187
|
ds : xarray.Dataset
|
|
151
188
|
Dataset containing the decoded and decompressed data.
|
|
152
189
|
"""
|
|
190
|
+
all_event_apids = set(
|
|
191
|
+
ULTRA_EVENTS.apid
|
|
192
|
+
+ ULTRA_PRI_1_EVENTS.apid
|
|
193
|
+
+ ULTRA_PRI_2_EVENTS.apid
|
|
194
|
+
+ ULTRA_PRI_3_EVENTS.apid
|
|
195
|
+
+ ULTRA_PRI_4_EVENTS.apid
|
|
196
|
+
)
|
|
197
|
+
if apid in all_event_apids:
|
|
198
|
+
field_ranges = EVENT_FIELD_RANGES
|
|
199
|
+
elif apid in ULTRA_ENERGY_EVENTS.apid:
|
|
200
|
+
field_ranges = ENERGY_EVENT_FIELD_RANGES
|
|
201
|
+
else:
|
|
202
|
+
raise ValueError(f"APID {apid} not recognized for Ultra events processing.")
|
|
203
|
+
|
|
153
204
|
all_events = []
|
|
154
205
|
all_indices = []
|
|
155
206
|
|
|
@@ -160,7 +211,7 @@ def process_ultra_events(ds: xr.Dataset) -> xr.Dataset:
|
|
|
160
211
|
field: attrs.get_variable_attributes(field).get(
|
|
161
212
|
"FILLVAL", np.iinfo(np.int64).min
|
|
162
213
|
)
|
|
163
|
-
for field in
|
|
214
|
+
for field in field_ranges
|
|
164
215
|
}
|
|
165
216
|
|
|
166
217
|
counts = ds["count"].values
|
|
@@ -173,7 +224,9 @@ def process_ultra_events(ds: xr.Dataset) -> xr.Dataset:
|
|
|
173
224
|
else:
|
|
174
225
|
# Here there are multiple images in a single packet,
|
|
175
226
|
# so we need to loop through each image and decompress it.
|
|
176
|
-
event_data_list = read_image_raw_events_binary(
|
|
227
|
+
event_data_list = read_image_raw_events_binary(
|
|
228
|
+
eventdata_array[i], count, field_ranges
|
|
229
|
+
)
|
|
177
230
|
all_events.extend(event_data_list)
|
|
178
231
|
# Keep track of how many times does the event occurred at this epoch.
|
|
179
232
|
all_indices.extend([i] * count)
|
|
@@ -189,7 +242,7 @@ def process_ultra_events(ds: xr.Dataset) -> xr.Dataset:
|
|
|
189
242
|
}
|
|
190
243
|
|
|
191
244
|
# Add the event data to the expanded dataset.
|
|
192
|
-
for key in
|
|
245
|
+
for key in field_ranges:
|
|
193
246
|
expanded_data[key] = np.array([event[key] for event in all_events])
|
|
194
247
|
|
|
195
248
|
event_ids = get_event_id(expanded_data["shcoarse"])
|
|
@@ -242,3 +295,160 @@ def process_ultra_rates(ds: xr.Dataset) -> xr.Dataset:
|
|
|
242
295
|
ds[key] = xr.DataArray(np.array(values), dims=["epoch"])
|
|
243
296
|
|
|
244
297
|
return ds
|
|
298
|
+
|
|
299
|
+
|
|
300
|
+
def process_ultra_energy_rates(ds: xr.Dataset) -> xr.Dataset:
|
|
301
|
+
"""
|
|
302
|
+
Unpack and decode Ultra ENERGY RATES packets.
|
|
303
|
+
|
|
304
|
+
Parameters
|
|
305
|
+
----------
|
|
306
|
+
ds : xarray.Dataset
|
|
307
|
+
Energy rates dataset.
|
|
308
|
+
|
|
309
|
+
Returns
|
|
310
|
+
-------
|
|
311
|
+
dataset : xarray.Dataset
|
|
312
|
+
Dataset containing the decoded and decompressed data.
|
|
313
|
+
"""
|
|
314
|
+
decom_data = defaultdict(list)
|
|
315
|
+
|
|
316
|
+
for rate in ds["ratedata"]:
|
|
317
|
+
raw_binary_string = convert_to_binary_string(rate.item())
|
|
318
|
+
decompressed_data = decompress_binary(
|
|
319
|
+
raw_binary_string,
|
|
320
|
+
cast(int, ULTRA_ENERGY_RATES.width),
|
|
321
|
+
cast(int, ULTRA_ENERGY_RATES.block),
|
|
322
|
+
cast(int, ULTRA_ENERGY_RATES.len_array),
|
|
323
|
+
cast(int, ULTRA_ENERGY_RATES.mantissa_bit_length),
|
|
324
|
+
)
|
|
325
|
+
|
|
326
|
+
for index in range(cast(int, ULTRA_ENERGY_RATES.len_array)):
|
|
327
|
+
decom_data[ENERGY_RATES_KEYS[index]].append(decompressed_data[index])
|
|
328
|
+
|
|
329
|
+
for key, values in decom_data.items():
|
|
330
|
+
ds[key] = xr.DataArray(np.array(values), dims=["epoch"])
|
|
331
|
+
|
|
332
|
+
return ds
|
|
333
|
+
|
|
334
|
+
|
|
335
|
+
def process_ultra_energy_spectra(ds: xr.Dataset) -> xr.Dataset:
|
|
336
|
+
"""
|
|
337
|
+
Unpack and decode Ultra ENERGY SPECTRA packets.
|
|
338
|
+
|
|
339
|
+
Parameters
|
|
340
|
+
----------
|
|
341
|
+
ds : xarray.Dataset
|
|
342
|
+
Energy rates dataset.
|
|
343
|
+
|
|
344
|
+
Returns
|
|
345
|
+
-------
|
|
346
|
+
dataset : xarray.Dataset
|
|
347
|
+
Dataset containing the decoded and decompressed data.
|
|
348
|
+
"""
|
|
349
|
+
energy_spectra = []
|
|
350
|
+
|
|
351
|
+
for rate in ds["compdata"]:
|
|
352
|
+
raw_binary_string = convert_to_binary_string(rate.item())
|
|
353
|
+
decompressed_data = decompress_binary(
|
|
354
|
+
raw_binary_string,
|
|
355
|
+
cast(int, ULTRA_ENERGY_SPECTRA.width),
|
|
356
|
+
cast(int, ULTRA_ENERGY_SPECTRA.block),
|
|
357
|
+
cast(int, ULTRA_ENERGY_SPECTRA.len_array),
|
|
358
|
+
cast(int, ULTRA_ENERGY_SPECTRA.mantissa_bit_length),
|
|
359
|
+
)
|
|
360
|
+
|
|
361
|
+
energy_spectra.append(decompressed_data)
|
|
362
|
+
|
|
363
|
+
energy_spectra = np.array(energy_spectra)
|
|
364
|
+
|
|
365
|
+
ds["ssd_sum"] = xr.DataArray(
|
|
366
|
+
energy_spectra,
|
|
367
|
+
dims=["epoch", "energyspectrastate"],
|
|
368
|
+
coords={"epoch": ds["epoch"], "energyspectrastate": np.arange(16)},
|
|
369
|
+
)
|
|
370
|
+
|
|
371
|
+
return ds
|
|
372
|
+
|
|
373
|
+
|
|
374
|
+
def process_ultra_cmd_echo(ds: xr.Dataset) -> xr.Dataset:
|
|
375
|
+
"""
|
|
376
|
+
Unpack and decode Ultra CMD ECHO packets.
|
|
377
|
+
|
|
378
|
+
Parameters
|
|
379
|
+
----------
|
|
380
|
+
ds : xarray.Dataset
|
|
381
|
+
Energy rates dataset.
|
|
382
|
+
|
|
383
|
+
Returns
|
|
384
|
+
-------
|
|
385
|
+
dataset : xarray.Dataset
|
|
386
|
+
Dataset containing the decoded and decompressed data.
|
|
387
|
+
"""
|
|
388
|
+
descriptions = []
|
|
389
|
+
|
|
390
|
+
fill = 0xFF
|
|
391
|
+
max_len = 10
|
|
392
|
+
arg_array = np.full((len(ds["epoch"]), max_len), fill, dtype=np.uint8)
|
|
393
|
+
|
|
394
|
+
for i, arg in enumerate(ds["args"].values):
|
|
395
|
+
# Converts to the numeric representations of each byte.
|
|
396
|
+
arg_array[i, : len(arg)] = np.frombuffer(arg, dtype=np.uint8)
|
|
397
|
+
|
|
398
|
+
# Default to "FILL" for unlisted values
|
|
399
|
+
for result in ds["result"].values:
|
|
400
|
+
descriptions.append(CMD_ECHO_MAP.get(result, "FILL"))
|
|
401
|
+
|
|
402
|
+
ds["arguments"] = xr.DataArray(
|
|
403
|
+
arg_array,
|
|
404
|
+
dims=["epoch", "arg_index"],
|
|
405
|
+
coords={
|
|
406
|
+
"epoch": ds["epoch"],
|
|
407
|
+
"arg_index": np.arange(10),
|
|
408
|
+
},
|
|
409
|
+
)
|
|
410
|
+
|
|
411
|
+
ds["result_description"] = xr.DataArray(
|
|
412
|
+
np.array(descriptions),
|
|
413
|
+
dims=["epoch"],
|
|
414
|
+
coords={"epoch": ds["epoch"]},
|
|
415
|
+
)
|
|
416
|
+
|
|
417
|
+
ds = ds.drop_vars(["args", "result"])
|
|
418
|
+
|
|
419
|
+
return ds
|
|
420
|
+
|
|
421
|
+
|
|
422
|
+
def process_ultra_macros_checksum(ds: xr.Dataset) -> xr.Dataset:
|
|
423
|
+
"""
|
|
424
|
+
Unpack and decode Ultra MACROS CHECKSUM packets.
|
|
425
|
+
|
|
426
|
+
Parameters
|
|
427
|
+
----------
|
|
428
|
+
ds : xarray.Dataset
|
|
429
|
+
Dataset containing macro checksums.
|
|
430
|
+
|
|
431
|
+
Returns
|
|
432
|
+
-------
|
|
433
|
+
dataset : xarray.Dataset
|
|
434
|
+
Dataset with unpacked and decoded checksum values.
|
|
435
|
+
"""
|
|
436
|
+
# big endian uint16
|
|
437
|
+
packed_dtype = np.dtype(">u2")
|
|
438
|
+
fill = np.iinfo(packed_dtype).max
|
|
439
|
+
n_epochs = ds.sizes["epoch"]
|
|
440
|
+
max_len = 256
|
|
441
|
+
|
|
442
|
+
checksum_array = np.full((n_epochs, max_len), fill)
|
|
443
|
+
|
|
444
|
+
for i, checksum in enumerate(ds["checksums"]):
|
|
445
|
+
checksum_array[i, :] = np.frombuffer(checksum.item(), dtype=packed_dtype)
|
|
446
|
+
|
|
447
|
+
ds["checksum"] = xr.DataArray(
|
|
448
|
+
checksum_array,
|
|
449
|
+
dims=["epoch", "checksum_index"],
|
|
450
|
+
coords={"epoch": ds["epoch"], "checksum_index": np.arange(max_len)},
|
|
451
|
+
)
|
|
452
|
+
ds = ds.drop_vars(["checksums"])
|
|
453
|
+
|
|
454
|
+
return ds
|