imap-processing 0.6.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.
Files changed (398) hide show
  1. imap_processing/__init__.py +34 -0
  2. imap_processing/_version.py +3 -0
  3. imap_processing/ccsds/__init__.py +0 -0
  4. imap_processing/ccsds/ccsds_data.py +55 -0
  5. imap_processing/ccsds/excel_to_xtce.py +477 -0
  6. imap_processing/cdf/__init__.py +0 -0
  7. imap_processing/cdf/cdf_attribute_manager.py +322 -0
  8. imap_processing/cdf/config/imap_codice_global_cdf_attrs.yaml +212 -0
  9. imap_processing/cdf/config/imap_codice_l1a_variable_attrs.yaml +1358 -0
  10. imap_processing/cdf/config/imap_codice_l1b_variable_attrs.yaml +391 -0
  11. imap_processing/cdf/config/imap_constant_attrs.yaml +33 -0
  12. imap_processing/cdf/config/imap_default_global_cdf_attrs.yaml +17 -0
  13. imap_processing/cdf/config/imap_glows_global_cdf_attrs.yaml +41 -0
  14. imap_processing/cdf/config/imap_glows_l1a_variable_attrs.yaml +499 -0
  15. imap_processing/cdf/config/imap_glows_l1b_variable_attrs.yaml +334 -0
  16. imap_processing/cdf/config/imap_hi_global_cdf_attrs.yaml +51 -0
  17. imap_processing/cdf/config/imap_hi_variable_attrs.yaml +435 -0
  18. imap_processing/cdf/config/imap_hit_global_cdf_attrs.yaml +27 -0
  19. imap_processing/cdf/config/imap_hit_l1a_variable_attrs.yaml +493 -0
  20. imap_processing/cdf/config/imap_hit_l1b_variable_attrs.yaml +564 -0
  21. imap_processing/cdf/config/imap_idex_global_cdf_attrs.yaml +24 -0
  22. imap_processing/cdf/config/imap_idex_l1a_variable_attrs.yaml +426 -0
  23. imap_processing/cdf/config/imap_lo_global_cdf_attrs.yaml +90 -0
  24. imap_processing/cdf/config/imap_lo_l1a_variable_attrs.yaml +487 -0
  25. imap_processing/cdf/config/imap_lo_l1b_variable_attrs.yaml +121 -0
  26. imap_processing/cdf/config/imap_lo_l1c_variable_attrs.yaml +179 -0
  27. imap_processing/cdf/config/imap_mag_global_cdf_attrs.yaml +97 -0
  28. imap_processing/cdf/config/imap_mag_l1_variable_attrs.yaml +201 -0
  29. imap_processing/cdf/config/imap_swapi_global_cdf_attrs.yaml +33 -0
  30. imap_processing/cdf/config/imap_swapi_variable_attrs.yaml +137 -0
  31. imap_processing/cdf/config/imap_swe_global_cdf_attrs.yaml +24 -0
  32. imap_processing/cdf/config/imap_swe_l1a_variable_attrs.yaml +234 -0
  33. imap_processing/cdf/config/imap_swe_l1b_variable_attrs.yaml +273 -0
  34. imap_processing/cdf/config/imap_ultra_global_cdf_attrs.yaml +100 -0
  35. imap_processing/cdf/config/imap_ultra_l1a_variable_attrs.yaml +52 -0
  36. imap_processing/cdf/config/imap_ultra_l1b_variable_attrs.yaml +297 -0
  37. imap_processing/cdf/config/imap_ultra_l1c_variable_attrs.yaml +121 -0
  38. imap_processing/cdf/config/shared/default_global_cdf_attrs_schema.yaml +246 -0
  39. imap_processing/cdf/config/shared/default_variable_cdf_attrs_schema.yaml +466 -0
  40. imap_processing/cdf/imap_cdf_manager.py +64 -0
  41. imap_processing/cdf/utils.py +147 -0
  42. imap_processing/cli.py +863 -0
  43. imap_processing/codice/__init__.py +1 -0
  44. imap_processing/codice/codice_l0.py +54 -0
  45. imap_processing/codice/codice_l1a.py +558 -0
  46. imap_processing/codice/codice_l1b.py +194 -0
  47. imap_processing/codice/constants.py +986 -0
  48. imap_processing/codice/data/esa_sweep_values.csv +257 -0
  49. imap_processing/codice/data/lo_stepping_values.csv +129 -0
  50. imap_processing/codice/decompress.py +142 -0
  51. imap_processing/codice/packet_definitions/P_COD_NHK.xml +618 -0
  52. imap_processing/codice/packet_definitions/codice_packet_definition.xml +5073 -0
  53. imap_processing/codice/utils.py +95 -0
  54. imap_processing/decom.py +40 -0
  55. imap_processing/glows/__init__.py +1 -0
  56. imap_processing/glows/ancillary/l1b_conversion_table_v001.json +42 -0
  57. imap_processing/glows/l0/__init__.py +0 -0
  58. imap_processing/glows/l0/decom_glows.py +91 -0
  59. imap_processing/glows/l0/glows_l0_data.py +194 -0
  60. imap_processing/glows/l1a/glows_l1a.py +424 -0
  61. imap_processing/glows/l1a/glows_l1a_data.py +555 -0
  62. imap_processing/glows/l1b/glows_l1b.py +270 -0
  63. imap_processing/glows/l1b/glows_l1b_data.py +583 -0
  64. imap_processing/glows/packet_definitions/GLX_COMBINED.xml +254 -0
  65. imap_processing/glows/packet_definitions/P_GLX_TMSCDE.xml +97 -0
  66. imap_processing/glows/packet_definitions/P_GLX_TMSCHIST.xml +215 -0
  67. imap_processing/glows/utils/__init__.py +0 -0
  68. imap_processing/glows/utils/constants.py +105 -0
  69. imap_processing/hi/__init__.py +1 -0
  70. imap_processing/hi/l0/__init__.py +0 -0
  71. imap_processing/hi/l0/decom_hi.py +24 -0
  72. imap_processing/hi/l1a/__init__.py +0 -0
  73. imap_processing/hi/l1a/hi_l1a.py +73 -0
  74. imap_processing/hi/l1a/histogram.py +142 -0
  75. imap_processing/hi/l1a/housekeeping.py +27 -0
  76. imap_processing/hi/l1a/science_direct_event.py +341 -0
  77. imap_processing/hi/l1b/__init__.py +0 -0
  78. imap_processing/hi/l1b/hi_eng_unit_convert_table.csv +154 -0
  79. imap_processing/hi/l1b/hi_l1b.py +127 -0
  80. imap_processing/hi/l1c/__init__.py +0 -0
  81. imap_processing/hi/l1c/hi_l1c.py +228 -0
  82. imap_processing/hi/packet_definitions/__init__.py +0 -0
  83. imap_processing/hi/packet_definitions/hi_packet_definition.xml +482 -0
  84. imap_processing/hi/utils.py +27 -0
  85. imap_processing/hit/__init__.py +1 -0
  86. imap_processing/hit/l0/__init__.py +0 -0
  87. imap_processing/hit/l0/data_classes/housekeeping.py +240 -0
  88. imap_processing/hit/l0/data_classes/science_packet.py +259 -0
  89. imap_processing/hit/l0/decom_hit.py +467 -0
  90. imap_processing/hit/l0/utils/hit_base.py +57 -0
  91. imap_processing/hit/l1a/__init__.py +0 -0
  92. imap_processing/hit/l1a/hit_l1a.py +254 -0
  93. imap_processing/hit/l1b/hit_l1b.py +179 -0
  94. imap_processing/hit/packet_definitions/hit_packet_definitions.xml +1276 -0
  95. imap_processing/ialirt/__init__.py +0 -0
  96. imap_processing/ialirt/l0/__init__.py +0 -0
  97. imap_processing/ialirt/l0/process_hit.py +220 -0
  98. imap_processing/ialirt/packet_definitions/__init__.py +0 -0
  99. imap_processing/ialirt/packet_definitions/ialirt.xml +778 -0
  100. imap_processing/ialirt/packet_definitions/ialirt_hit.xml +186 -0
  101. imap_processing/idex/__init__.py +2 -0
  102. imap_processing/idex/idex_constants.py +27 -0
  103. imap_processing/idex/idex_l0.py +31 -0
  104. imap_processing/idex/idex_l1a.py +631 -0
  105. imap_processing/idex/packet_definitions/idex_packet_definition.xml +3162 -0
  106. imap_processing/lo/__init__.py +1 -0
  107. imap_processing/lo/l0/__init__.py +0 -0
  108. imap_processing/lo/l0/data_classes/science_direct_events.py +215 -0
  109. imap_processing/lo/l0/data_classes/star_sensor.py +98 -0
  110. imap_processing/lo/l0/decompression_tables/12_to_16_bit.csv +4097 -0
  111. imap_processing/lo/l0/decompression_tables/8_to_12_bit.csv +257 -0
  112. imap_processing/lo/l0/decompression_tables/8_to_16_bit.csv +257 -0
  113. imap_processing/lo/l0/decompression_tables/decompression_tables.py +75 -0
  114. imap_processing/lo/l0/lo_apid.py +15 -0
  115. imap_processing/lo/l0/lo_science.py +150 -0
  116. imap_processing/lo/l0/utils/binary_string.py +59 -0
  117. imap_processing/lo/l0/utils/bit_decompression.py +62 -0
  118. imap_processing/lo/l0/utils/lo_base.py +57 -0
  119. imap_processing/lo/l1a/__init__.py +0 -0
  120. imap_processing/lo/l1a/lo_l1a.py +157 -0
  121. imap_processing/lo/l1b/lo_l1b.py +160 -0
  122. imap_processing/lo/l1c/lo_l1c.py +180 -0
  123. imap_processing/lo/packet_definitions/lo_xtce.xml +3541 -0
  124. imap_processing/mag/__init__.py +2 -0
  125. imap_processing/mag/constants.py +108 -0
  126. imap_processing/mag/l0/decom_mag.py +170 -0
  127. imap_processing/mag/l0/mag_l0_data.py +118 -0
  128. imap_processing/mag/l1a/mag_l1a.py +317 -0
  129. imap_processing/mag/l1a/mag_l1a_data.py +1007 -0
  130. imap_processing/mag/l1b/__init__.py +0 -0
  131. imap_processing/mag/l1b/imap_calibration_mag_20240229_v01.cdf +0 -0
  132. imap_processing/mag/l1b/mag_l1b.py +125 -0
  133. imap_processing/mag/l1c/mag_l1c.py +57 -0
  134. imap_processing/mag/packet_definitions/MAG_SCI_COMBINED.xml +235 -0
  135. imap_processing/quality_flags.py +91 -0
  136. imap_processing/spice/__init__.py +1 -0
  137. imap_processing/spice/geometry.py +322 -0
  138. imap_processing/spice/kernels.py +459 -0
  139. imap_processing/spice/time.py +72 -0
  140. imap_processing/swapi/__init__.py +1 -0
  141. imap_processing/swapi/l1/__init__.py +0 -0
  142. imap_processing/swapi/l1/swapi_l1.py +685 -0
  143. imap_processing/swapi/l2/__init__.py +0 -0
  144. imap_processing/swapi/l2/swapi_l2.py +107 -0
  145. imap_processing/swapi/packet_definitions/__init__.py +0 -0
  146. imap_processing/swapi/packet_definitions/swapi_packet_definition.xml +708 -0
  147. imap_processing/swapi/swapi_utils.py +25 -0
  148. imap_processing/swe/__init__.py +1 -0
  149. imap_processing/swe/l1a/__init__.py +0 -0
  150. imap_processing/swe/l1a/swe_l1a.py +48 -0
  151. imap_processing/swe/l1a/swe_science.py +223 -0
  152. imap_processing/swe/l1b/engineering_unit_convert_table.csv +65 -0
  153. imap_processing/swe/l1b/swe_esa_lookup_table.csv +1441 -0
  154. imap_processing/swe/l1b/swe_l1b.py +49 -0
  155. imap_processing/swe/l1b/swe_l1b_science.py +557 -0
  156. imap_processing/swe/packet_definitions/__init__.py +0 -0
  157. imap_processing/swe/packet_definitions/swe_packet_definition.xml +303 -0
  158. imap_processing/swe/utils/__init__.py +0 -0
  159. imap_processing/swe/utils/swe_utils.py +9 -0
  160. imap_processing/tests/__init__.py +0 -0
  161. imap_processing/tests/ccsds/test_data/expected_output.xml +171 -0
  162. imap_processing/tests/ccsds/test_excel_to_xtce.py +285 -0
  163. imap_processing/tests/cdf/__init__.py +0 -0
  164. imap_processing/tests/cdf/imap_default_global_cdf_attrs.yaml +8 -0
  165. imap_processing/tests/cdf/shared/default_global_cdf_attrs_schema.yaml +246 -0
  166. imap_processing/tests/cdf/shared/default_variable_cdf_attrs_schema.yaml +466 -0
  167. imap_processing/tests/cdf/test_cdf_attribute_manager.py +353 -0
  168. imap_processing/tests/cdf/test_data/imap_default_global_test_cdf_attrs.yaml +7 -0
  169. imap_processing/tests/cdf/test_data/imap_instrument1_global_cdf_attrs.yaml +14 -0
  170. imap_processing/tests/cdf/test_data/imap_instrument1_level1_variable_attrs.yaml +23 -0
  171. imap_processing/tests/cdf/test_data/imap_instrument2_global_cdf_attrs.yaml +23 -0
  172. imap_processing/tests/cdf/test_data/imap_instrument2_level2_variable_attrs.yaml +30 -0
  173. imap_processing/tests/cdf/test_data/imap_test_global.yaml +26 -0
  174. imap_processing/tests/cdf/test_data/imap_test_variable.yaml +41 -0
  175. imap_processing/tests/cdf/test_imap_cdf_manager.py +62 -0
  176. imap_processing/tests/cdf/test_utils.py +109 -0
  177. imap_processing/tests/codice/__init__.py +0 -0
  178. imap_processing/tests/codice/conftest.py +56 -0
  179. imap_processing/tests/codice/data/eu_unit_lookup_table.csv +101 -0
  180. imap_processing/tests/codice/data/idle_export_eu.COD_NHK_20230822_122700 2.csv +100 -0
  181. imap_processing/tests/codice/data/idle_export_raw.COD_NHK_20230822_122700.csv +100 -0
  182. imap_processing/tests/codice/data/imap_codice_l0_hi-counters-aggregated_20240429_v001.pkts +0 -0
  183. imap_processing/tests/codice/data/imap_codice_l0_hi-counters-singles_20240429_v001.pkts +0 -0
  184. imap_processing/tests/codice/data/imap_codice_l0_hi-omni_20240429_v001.pkts +0 -0
  185. imap_processing/tests/codice/data/imap_codice_l0_hi-pha_20240429_v001.pkts +0 -0
  186. imap_processing/tests/codice/data/imap_codice_l0_hi-sectored_20240429_v001.pkts +0 -0
  187. imap_processing/tests/codice/data/imap_codice_l0_hskp_20100101_v001.pkts +0 -0
  188. imap_processing/tests/codice/data/imap_codice_l0_lo-counters-aggregated_20240429_v001.pkts +0 -0
  189. imap_processing/tests/codice/data/imap_codice_l0_lo-counters-singles_20240429_v001.pkts +0 -0
  190. imap_processing/tests/codice/data/imap_codice_l0_lo-nsw-angular_20240429_v001.pkts +0 -0
  191. imap_processing/tests/codice/data/imap_codice_l0_lo-nsw-priority_20240429_v001.pkts +0 -0
  192. imap_processing/tests/codice/data/imap_codice_l0_lo-nsw-species_20240429_v001.pkts +0 -0
  193. imap_processing/tests/codice/data/imap_codice_l0_lo-pha_20240429_v001.pkts +0 -0
  194. imap_processing/tests/codice/data/imap_codice_l0_lo-sw-angular_20240429_v001.pkts +0 -0
  195. imap_processing/tests/codice/data/imap_codice_l0_lo-sw-priority_20240429_v001.pkts +0 -0
  196. imap_processing/tests/codice/data/imap_codice_l0_lo-sw-species_20240429_v001.pkts +0 -0
  197. imap_processing/tests/codice/data/imap_codice_l1a_hi-counters-aggregated_20240429_v001.cdf +0 -0
  198. imap_processing/tests/codice/data/imap_codice_l1a_hi-counters-singles_20240429_v001.cdf +0 -0
  199. imap_processing/tests/codice/data/imap_codice_l1a_hi-omni_20240429_v001.cdf +0 -0
  200. imap_processing/tests/codice/data/imap_codice_l1a_hi-sectored_20240429_v001.cdf +0 -0
  201. imap_processing/tests/codice/data/imap_codice_l1a_hskp_20100101_v001.cdf +0 -0
  202. imap_processing/tests/codice/data/imap_codice_l1a_lo-counters-aggregated_20240429_v001.cdf +0 -0
  203. imap_processing/tests/codice/data/imap_codice_l1a_lo-counters-singles_20240429_v001.cdf +0 -0
  204. imap_processing/tests/codice/data/imap_codice_l1a_lo-nsw-angular_20240429_v001.cdf +0 -0
  205. imap_processing/tests/codice/data/imap_codice_l1a_lo-nsw-priority_20240429_v001.cdf +0 -0
  206. imap_processing/tests/codice/data/imap_codice_l1a_lo-nsw-species_20240429_v001.cdf +0 -0
  207. imap_processing/tests/codice/data/imap_codice_l1a_lo-sw-angular_20240429_v001.cdf +0 -0
  208. imap_processing/tests/codice/data/imap_codice_l1a_lo-sw-priority_20240429_v001.cdf +0 -0
  209. imap_processing/tests/codice/data/imap_codice_l1a_lo-sw-species_20240429_v001.cdf +0 -0
  210. imap_processing/tests/codice/data/imap_codice_l1b_hi-counters-aggregated_20240429_v001.cdf +0 -0
  211. imap_processing/tests/codice/data/imap_codice_l1b_hi-counters-singles_20240429_v001.cdf +0 -0
  212. imap_processing/tests/codice/data/imap_codice_l1b_hi-omni_20240429_v001.cdf +0 -0
  213. imap_processing/tests/codice/data/imap_codice_l1b_hi-sectored_20240429_v001.cdf +0 -0
  214. imap_processing/tests/codice/data/imap_codice_l1b_hskp_20100101_v001.cdf +0 -0
  215. imap_processing/tests/codice/data/imap_codice_l1b_lo-counters-aggregated_20240429_v001.cdf +0 -0
  216. imap_processing/tests/codice/data/imap_codice_l1b_lo-counters-singles_20240429_v001.cdf +0 -0
  217. imap_processing/tests/codice/data/imap_codice_l1b_lo-nsw-angular_20240429_v001.cdf +0 -0
  218. imap_processing/tests/codice/data/imap_codice_l1b_lo-nsw-priority_20240429_v001.cdf +0 -0
  219. imap_processing/tests/codice/data/imap_codice_l1b_lo-nsw-species_20240429_v001.cdf +0 -0
  220. imap_processing/tests/codice/data/imap_codice_l1b_lo-sw-angular_20240429_v001.cdf +0 -0
  221. imap_processing/tests/codice/data/imap_codice_l1b_lo-sw-priority_20240429_v001.cdf +0 -0
  222. imap_processing/tests/codice/data/imap_codice_l1b_lo-sw-species_20240429_v001.cdf +0 -0
  223. imap_processing/tests/codice/test_codice_l0.py +144 -0
  224. imap_processing/tests/codice/test_codice_l1a.py +187 -0
  225. imap_processing/tests/codice/test_codice_l1b.py +60 -0
  226. imap_processing/tests/codice/test_decompress.py +50 -0
  227. imap_processing/tests/conftest.py +372 -0
  228. imap_processing/tests/glows/direct_events_validation_data_l1a.csv +5704 -0
  229. imap_processing/tests/glows/glows_test_packet_20110921_v01.pkts +0 -0
  230. imap_processing/tests/glows/test_glows_decom.py +133 -0
  231. imap_processing/tests/glows/test_glows_l1a_cdf.py +85 -0
  232. imap_processing/tests/glows/test_glows_l1a_data.py +510 -0
  233. imap_processing/tests/glows/test_glows_l1b.py +348 -0
  234. imap_processing/tests/glows/test_glows_l1b_data.py +70 -0
  235. imap_processing/tests/hi/__init__.py +0 -0
  236. imap_processing/tests/hi/conftest.py +133 -0
  237. imap_processing/tests/hi/test_data/l0/20231030_H45_APP_NHK.bin +0 -0
  238. imap_processing/tests/hi/test_data/l0/20231030_H45_APP_NHK.csv +201 -0
  239. imap_processing/tests/hi/test_data/l0/20231030_H45_SCI_CNT.bin +0 -0
  240. imap_processing/tests/hi/test_data/l0/20231030_H45_SCI_DE.bin +0 -0
  241. imap_processing/tests/hi/test_data/l0/README.txt +54 -0
  242. imap_processing/tests/hi/test_decom.py +55 -0
  243. imap_processing/tests/hi/test_hi_l1b.py +31 -0
  244. imap_processing/tests/hi/test_hi_l1c.py +69 -0
  245. imap_processing/tests/hi/test_l1a.py +96 -0
  246. imap_processing/tests/hi/test_l1a_sci_de.py +72 -0
  247. imap_processing/tests/hi/test_utils.py +15 -0
  248. imap_processing/tests/hit/PREFLIGHT_raw_record_2023_256_15_59_04_apid1251.pkts +0 -0
  249. imap_processing/tests/hit/PREFLIGHT_raw_record_2023_256_15_59_04_apid1252.pkts +0 -0
  250. imap_processing/tests/hit/__init__.py +0 -0
  251. imap_processing/tests/hit/test_data/imap_hit_l0_hk_20100105_v001.pkts +0 -0
  252. imap_processing/tests/hit/test_data/sci_sample.ccsds +0 -0
  253. imap_processing/tests/hit/test_hit_decom.py +230 -0
  254. imap_processing/tests/hit/test_hit_l1a.py +224 -0
  255. imap_processing/tests/hit/test_hit_l1b.py +52 -0
  256. imap_processing/tests/hit/validation_data/hskp_sample_raw.csv +88 -0
  257. imap_processing/tests/ialirt/__init__.py +0 -0
  258. imap_processing/tests/ialirt/test_data/l0/IALiRT Raw Packet Telemetry.txt +33 -0
  259. imap_processing/tests/ialirt/test_data/l0/hit_ialirt_sample.ccsds +0 -0
  260. imap_processing/tests/ialirt/test_data/l0/hit_ialirt_sample.csv +1001 -0
  261. imap_processing/tests/ialirt/unit/__init__.py +0 -0
  262. imap_processing/tests/ialirt/unit/test_decom_ialirt.py +94 -0
  263. imap_processing/tests/ialirt/unit/test_process_hit.py +226 -0
  264. imap_processing/tests/idex/__init__.py +0 -0
  265. imap_processing/tests/idex/conftest.py +22 -0
  266. imap_processing/tests/idex/imap_idex_l0_raw_20230725_v001.pkts +0 -0
  267. imap_processing/tests/idex/impact_14_tof_high_data.txt +8189 -0
  268. imap_processing/tests/idex/test_idex_l0.py +45 -0
  269. imap_processing/tests/idex/test_idex_l1a.py +91 -0
  270. imap_processing/tests/lo/__init__.py +0 -0
  271. imap_processing/tests/lo/test_binary_string.py +21 -0
  272. imap_processing/tests/lo/test_bit_decompression.py +39 -0
  273. imap_processing/tests/lo/test_cdfs/imap_lo_l0_raw_20240627_v001.pkts +0 -0
  274. imap_processing/tests/lo/test_cdfs/imap_lo_l1a_de_20100101_v001.cdf +0 -0
  275. imap_processing/tests/lo/test_cdfs/imap_lo_l1a_spin_20100101_v001.cdf +0 -0
  276. imap_processing/tests/lo/test_cdfs/imap_lo_l1b_de_20100101_v001.cdf +0 -0
  277. imap_processing/tests/lo/test_lo_l1a.py +66 -0
  278. imap_processing/tests/lo/test_lo_l1b.py +74 -0
  279. imap_processing/tests/lo/test_lo_l1c.py +66 -0
  280. imap_processing/tests/lo/test_science_counts.py +41 -0
  281. imap_processing/tests/lo/test_science_direct_events.py +209 -0
  282. imap_processing/tests/lo/test_star_sensor.py +35 -0
  283. imap_processing/tests/mag/imap_mag_l1a_burst-magi_20231025_v001.cdf +0 -0
  284. imap_processing/tests/mag/mag_l0_test_data.pkts +0 -0
  285. imap_processing/tests/mag/mag_l0_test_output.csv +37 -0
  286. imap_processing/tests/mag/mag_l1_test_data.pkts +0 -0
  287. imap_processing/tests/mag/mag_l1a_test_output.csv +97 -0
  288. imap_processing/tests/mag/test_mag_decom.py +117 -0
  289. imap_processing/tests/mag/test_mag_l1a.py +856 -0
  290. imap_processing/tests/mag/test_mag_l1b.py +77 -0
  291. imap_processing/tests/mag/test_mag_l1c.py +40 -0
  292. imap_processing/tests/spice/__init__.py +0 -0
  293. imap_processing/tests/spice/test_data/imap_ena_sim_metakernel.template +4 -0
  294. imap_processing/tests/spice/test_data/imap_science_0001.tf +171 -0
  295. imap_processing/tests/spice/test_data/imap_sclk_0000.tsc +156 -0
  296. imap_processing/tests/spice/test_data/imap_sim_ck_2hr_2secsampling_with_nutation.bc +0 -0
  297. imap_processing/tests/spice/test_data/imap_simple_metakernel.template +3 -0
  298. imap_processing/tests/spice/test_data/imap_spk_demo.bsp +0 -0
  299. imap_processing/tests/spice/test_data/imap_wkcp.tf +1806 -0
  300. imap_processing/tests/spice/test_data/naif0012.tls +150 -0
  301. imap_processing/tests/spice/test_data/sim_1yr_imap_attitude.bc +0 -0
  302. imap_processing/tests/spice/test_data/sim_1yr_imap_pointing_frame.bc +0 -0
  303. imap_processing/tests/spice/test_geometry.py +214 -0
  304. imap_processing/tests/spice/test_kernels.py +272 -0
  305. imap_processing/tests/spice/test_time.py +35 -0
  306. imap_processing/tests/swapi/__init__.py +0 -0
  307. imap_processing/tests/swapi/conftest.py +16 -0
  308. imap_processing/tests/swapi/l0_data/__init__.py +0 -0
  309. imap_processing/tests/swapi/l0_data/imap_swapi_l0_raw_20231012_v001.pkts +0 -0
  310. imap_processing/tests/swapi/l0_validation_data/__init__.py +0 -0
  311. imap_processing/tests/swapi/l0_validation_data/idle_export_eu.SWP_AUT_20231012_125245.csv +124 -0
  312. imap_processing/tests/swapi/l0_validation_data/idle_export_eu.SWP_HK_20231012_125245.csv +98 -0
  313. imap_processing/tests/swapi/l0_validation_data/idle_export_eu.SWP_MG_20231012_125245.csv +9 -0
  314. imap_processing/tests/swapi/l0_validation_data/idle_export_eu.SWP_SCI_20231012_125245.csv +72 -0
  315. imap_processing/tests/swapi/l0_validation_data/idle_export_raw.SWP_AUT_20231012_125245.csv +124 -0
  316. imap_processing/tests/swapi/l0_validation_data/idle_export_raw.SWP_HK_20231012_125245.csv +98 -0
  317. imap_processing/tests/swapi/l0_validation_data/idle_export_raw.SWP_MG_20231012_125245.csv +9 -0
  318. imap_processing/tests/swapi/l0_validation_data/idle_export_raw.SWP_SCI_20231012_125245.csv +72 -0
  319. imap_processing/tests/swapi/test_swapi_decom.py +135 -0
  320. imap_processing/tests/swapi/test_swapi_l1.py +354 -0
  321. imap_processing/tests/swapi/test_swapi_l2.py +21 -0
  322. imap_processing/tests/swe/__init__.py +0 -0
  323. imap_processing/tests/swe/conftest.py +35 -0
  324. imap_processing/tests/swe/decompressed/20230927173238_4th_quarter_decompressed.csv +181 -0
  325. imap_processing/tests/swe/decompressed/20230927173253_1st_quarter_decompressed.csv +181 -0
  326. imap_processing/tests/swe/decompressed/20230927173308_2nd_quarter_decompressed.csv +181 -0
  327. imap_processing/tests/swe/decompressed/20230927173323_3rd_quarter_decompressed.csv +181 -0
  328. imap_processing/tests/swe/l0_data/2024051010_SWE_SCIENCE_packet.bin +0 -0
  329. imap_processing/tests/swe/l0_validation_data/idle_export_eu.SWE_SCIENCE_20240510_092742.csv +544 -0
  330. imap_processing/tests/swe/l0_validation_data/idle_export_raw.SWE_SCIENCE_20240510_092742.csv +363 -0
  331. imap_processing/tests/swe/test_swe_l1a.py +12 -0
  332. imap_processing/tests/swe/test_swe_l1a_science.py +129 -0
  333. imap_processing/tests/swe/test_swe_l1b.py +61 -0
  334. imap_processing/tests/swe/test_swe_l1b_science.py +65 -0
  335. imap_processing/tests/test_cli.py +229 -0
  336. imap_processing/tests/test_decom.py +66 -0
  337. imap_processing/tests/test_quality_flags.py +71 -0
  338. imap_processing/tests/test_utils.py +107 -0
  339. imap_processing/tests/ultra/__init__.py +0 -0
  340. imap_processing/tests/ultra/test_data/l0/FM45_40P_Phi28p5_BeamCal_LinearScan_phi28.50_theta-0.00_20240207T102740.CCSDS +0 -0
  341. imap_processing/tests/ultra/test_data/l0/FM45_7P_Phi0.0_BeamCal_LinearScan_phi0.04_theta-0.01_20230821T121304.CCSDS +0 -0
  342. imap_processing/tests/ultra/test_data/l0/FM45_TV_Cycle6_Hot_Ops_Front212_20240124T063837.CCSDS +0 -0
  343. imap_processing/tests/ultra/test_data/l0/Ultra45_EM_SwRI_Cal_Run7_ThetaScan_20220530T225054.CCSDS +0 -0
  344. imap_processing/tests/ultra/test_data/l0/ultra45_raw_sc_auxdata_Ultra45_EM_SwRI_Cal_Run7_ThetaScan_20220530T225054.csv +24 -0
  345. imap_processing/tests/ultra/test_data/l0/ultra45_raw_sc_enaphxtofhangimg_FM45_TV_Cycle6_Hot_Ops_Front212_20240124T063837.csv +105 -0
  346. imap_processing/tests/ultra/test_data/l0/ultra45_raw_sc_ultraimgrates_Ultra45_EM_SwRI_Cal_Run7_ThetaScan_20220530T225054.csv +24 -0
  347. imap_processing/tests/ultra/test_data/l0/ultra45_raw_sc_ultrarawimg_withFSWcalcs_FM45_40P_Phi28p5_BeamCal_LinearScan_phi2850_theta-000_20240207T102740.csv +3314 -0
  348. imap_processing/tests/ultra/test_data/l0/ultra45_raw_sc_ultrarawimgevent_FM45_7P_Phi00_BeamCal_LinearScan_phi004_theta-001_20230821T121304.csv +702 -0
  349. imap_processing/tests/ultra/unit/__init__.py +0 -0
  350. imap_processing/tests/ultra/unit/conftest.py +210 -0
  351. imap_processing/tests/ultra/unit/test_decom_apid_880.py +98 -0
  352. imap_processing/tests/ultra/unit/test_decom_apid_881.py +50 -0
  353. imap_processing/tests/ultra/unit/test_decom_apid_883.py +44 -0
  354. imap_processing/tests/ultra/unit/test_decom_apid_896.py +104 -0
  355. imap_processing/tests/ultra/unit/test_lookup_utils.py +68 -0
  356. imap_processing/tests/ultra/unit/test_ultra_l1a.py +338 -0
  357. imap_processing/tests/ultra/unit/test_ultra_l1b.py +122 -0
  358. imap_processing/tests/ultra/unit/test_ultra_l1b_annotated.py +57 -0
  359. imap_processing/tests/ultra/unit/test_ultra_l1b_extended.py +342 -0
  360. imap_processing/tests/ultra/unit/test_ultra_l1c.py +104 -0
  361. imap_processing/tests/ultra/unit/test_ultra_l1c_pset_bins.py +35 -0
  362. imap_processing/ultra/__init__.py +1 -0
  363. imap_processing/ultra/constants.py +60 -0
  364. imap_processing/ultra/l0/__init__.py +0 -0
  365. imap_processing/ultra/l0/decom_tools.py +281 -0
  366. imap_processing/ultra/l0/decom_ultra.py +278 -0
  367. imap_processing/ultra/l0/ultra_utils.py +326 -0
  368. imap_processing/ultra/l1a/__init__.py +0 -0
  369. imap_processing/ultra/l1a/ultra_l1a.py +319 -0
  370. imap_processing/ultra/l1b/badtimes.py +26 -0
  371. imap_processing/ultra/l1b/cullingmask.py +26 -0
  372. imap_processing/ultra/l1b/de.py +59 -0
  373. imap_processing/ultra/l1b/extendedspin.py +45 -0
  374. imap_processing/ultra/l1b/lookup_utils.py +165 -0
  375. imap_processing/ultra/l1b/ultra_l1b.py +65 -0
  376. imap_processing/ultra/l1b/ultra_l1b_annotated.py +54 -0
  377. imap_processing/ultra/l1b/ultra_l1b_extended.py +764 -0
  378. imap_processing/ultra/l1c/histogram.py +36 -0
  379. imap_processing/ultra/l1c/pset.py +36 -0
  380. imap_processing/ultra/l1c/ultra_l1c.py +52 -0
  381. imap_processing/ultra/l1c/ultra_l1c_pset_bins.py +54 -0
  382. imap_processing/ultra/lookup_tables/EgyNorm.mem.csv +32769 -0
  383. imap_processing/ultra/lookup_tables/FM45_Startup1_ULTRA_IMGPARAMS_20240719.csv +2 -0
  384. imap_processing/ultra/lookup_tables/ultra45_back-pos-luts.csv +4097 -0
  385. imap_processing/ultra/lookup_tables/ultra45_tdc_norm.csv +2050 -0
  386. imap_processing/ultra/lookup_tables/ultra90_back-pos-luts.csv +4097 -0
  387. imap_processing/ultra/lookup_tables/ultra90_tdc_norm.csv +2050 -0
  388. imap_processing/ultra/lookup_tables/yadjust.csv +257 -0
  389. imap_processing/ultra/packet_definitions/ULTRA_SCI_COMBINED.xml +547 -0
  390. imap_processing/ultra/packet_definitions/__init__.py +0 -0
  391. imap_processing/ultra/utils/__init__.py +0 -0
  392. imap_processing/ultra/utils/ultra_l1_utils.py +50 -0
  393. imap_processing/utils.py +413 -0
  394. imap_processing-0.6.0.dist-info/LICENSE +21 -0
  395. imap_processing-0.6.0.dist-info/METADATA +107 -0
  396. imap_processing-0.6.0.dist-info/RECORD +398 -0
  397. imap_processing-0.6.0.dist-info/WHEEL +4 -0
  398. imap_processing-0.6.0.dist-info/entry_points.txt +4 -0
@@ -0,0 +1,326 @@
1
+ """Contains data classes to support Ultra L0 processing."""
2
+
3
+ from dataclasses import fields
4
+ from typing import NamedTuple, Union
5
+
6
+ import numpy as np
7
+
8
+
9
+ class PacketProperties(NamedTuple):
10
+ """Class that represents properties of the ULTRA packet type."""
11
+
12
+ apid: list # List of APIDs
13
+ logical_source: list # List of logical sources
14
+ addition_to_logical_desc: str # Description of the logical source
15
+ width: Union[int, None] # Width of binary data (could be None).
16
+ block: Union[int, None] # Number of values in each block (could be None).
17
+ # This is important for decompressing the images and
18
+ # a description is available on page 171 of IMAP-Ultra Flight
19
+ # Software Specification document (7523-9009_Rev_-.pdf).
20
+ len_array: Union[
21
+ int, None
22
+ ] # Length of the array to be decompressed (could be None).
23
+ mantissa_bit_length: Union[int, None] # used to determine the level of
24
+ # precision that can be recovered from compressed data (could be None).
25
+
26
+
27
+ # Define PacketProperties instances directly in the module namespace
28
+ ULTRA_AUX = PacketProperties(
29
+ apid=[880, 994],
30
+ logical_source=["imap_ultra_l1a_45sensor-aux", "imap_ultra_l1a_90sensor-aux"],
31
+ addition_to_logical_desc="Auxiliary",
32
+ width=None,
33
+ block=None,
34
+ len_array=None,
35
+ mantissa_bit_length=None,
36
+ )
37
+ ULTRA_RATES = PacketProperties(
38
+ apid=[881, 945],
39
+ logical_source=["imap_ultra_l1a_45sensor-rates", "imap_ultra_l1a_90sensor-rates"],
40
+ addition_to_logical_desc="Image Rates",
41
+ width=5,
42
+ block=16,
43
+ len_array=48,
44
+ mantissa_bit_length=12,
45
+ )
46
+ ULTRA_TOF = PacketProperties(
47
+ apid=[883, 947],
48
+ logical_source=[
49
+ "imap_ultra_l1a_45sensor-histogram",
50
+ "imap_ultra_l1a_90sensor-histogram",
51
+ ],
52
+ addition_to_logical_desc="Time of Flight Images",
53
+ width=4,
54
+ block=15,
55
+ len_array=None,
56
+ mantissa_bit_length=4,
57
+ )
58
+ ULTRA_EVENTS = PacketProperties(
59
+ apid=[896, 960],
60
+ logical_source=["imap_ultra_l1a_45sensor-de", "imap_ultra_l1a_90sensor-de"],
61
+ addition_to_logical_desc="Single Events",
62
+ width=None,
63
+ block=None,
64
+ len_array=None,
65
+ mantissa_bit_length=None,
66
+ )
67
+
68
+
69
+ # Module-level constant for event field ranges
70
+ # Module-level constant for event field ranges
71
+ EVENT_FIELD_RANGES = {
72
+ # Coincidence Type
73
+ "COIN_TYPE": (0, 2),
74
+ # Start Type
75
+ "START_TYPE": (2, 4),
76
+ # Stop Type
77
+ "STOP_TYPE": (4, 8),
78
+ # Start Position Time to Digital Converter
79
+ "START_POS_TDC": (8, 19),
80
+ # Stop North Time to Digital Converter
81
+ "STOP_NORTH_TDC": (19, 30),
82
+ # Stop East Time to Digital Converter
83
+ "STOP_EAST_TDC": (30, 41),
84
+ # Stop South Time to Digital Converter
85
+ "STOP_SOUTH_TDC": (41, 52),
86
+ # Stop West Time to Digital Converter
87
+ "STOP_WEST_TDC": (52, 63),
88
+ # Coincidence North Time to Digital Converter
89
+ "COIN_NORTH_TDC": (63, 74),
90
+ # Coincidence South Time to Digital Converter
91
+ "COIN_SOUTH_TDC": (74, 85),
92
+ # Coincidence Discrete Time to Digital Converter
93
+ "COIN_DISCRETE_TDC": (85, 96),
94
+ # Energy/Pulse Height
95
+ "ENERGY_PH": (96, 108),
96
+ # Pulse Width
97
+ "PULSE_WIDTH": (108, 119),
98
+ # Event Flag Count
99
+ "EVENT_FLAG_CNT": (119, 120),
100
+ # Event Flag PHCmpSL
101
+ "EVENT_FLAG_PHCMPSL": (120, 121),
102
+ # Event Flag PHCmpSR
103
+ "EVENT_FLAG_PHCMPSR": (121, 122),
104
+ # Event Flag PHCmpCD
105
+ "EVENT_FLAG_PHCMPCD": (122, 123),
106
+ # Solid State Detector Flags
107
+ "SSD_FLAG_7": (123, 124),
108
+ "SSD_FLAG_6": (124, 125),
109
+ "SSD_FLAG_5": (125, 126),
110
+ "SSD_FLAG_4": (126, 127),
111
+ "SSD_FLAG_3": (127, 128),
112
+ "SSD_FLAG_2": (128, 129),
113
+ "SSD_FLAG_1": (129, 130),
114
+ "SSD_FLAG_0": (130, 131),
115
+ # Constant Fraction Discriminator Flag Coincidence Top North
116
+ "CFD_FLAG_COINTN": (131, 132),
117
+ # Constant Fraction Discriminator Flag Coincidence Bottom North
118
+ "CFD_FLAG_COINBN": (132, 133),
119
+ # Constant Fraction Discriminator Flag Coincidence Top South
120
+ "CFD_FLAG_COINTS": (133, 134),
121
+ # Constant Fraction Discriminator Flag Coincidence Bottom South
122
+ "CFD_FLAG_COINBS": (134, 135),
123
+ # Constant Fraction Discriminator Flag Coincidence Discrete
124
+ "CFD_FLAG_COIND": (135, 136),
125
+ # Constant Fraction Discriminator Flag Start Right Full
126
+ "CFD_FLAG_STARTRF": (136, 137),
127
+ # Constant Fraction Discriminator Flag Start Left Full
128
+ "CFD_FLAG_STARTLF": (137, 138),
129
+ # Constant Fraction Discriminator Flag Start Position Right
130
+ "CFD_FLAG_STARTRP": (138, 139),
131
+ # Constant Fraction Discriminator Flag Start Position Left
132
+ "CFD_FLAG_STARTLP": (139, 140),
133
+ # Constant Fraction Discriminator Flag Stop Top North
134
+ "CFD_FLAG_STOPTN": (140, 141),
135
+ # Constant Fraction Discriminator Flag Stop Bottom North
136
+ "CFD_FLAG_STOPBN": (141, 142),
137
+ # Constant Fraction Discriminator Flag Stop Top East
138
+ "CFD_FLAG_STOPTE": (142, 143),
139
+ # Constant Fraction Discriminator Flag Stop Bottom East
140
+ "CFD_FLAG_STOPBE": (143, 144),
141
+ # Constant Fraction Discriminator Flag Stop Top South
142
+ "CFD_FLAG_STOPTS": (144, 145),
143
+ # Constant Fraction Discriminator Flag Stop Bottom South
144
+ "CFD_FLAG_STOPBS": (145, 146),
145
+ # Constant Fraction Discriminator Flag Stop Top West
146
+ "CFD_FLAG_STOPTW": (146, 147),
147
+ # Constant Fraction Discriminator Flag Stop Bottom West
148
+ "CFD_FLAG_STOPBW": (147, 148),
149
+ # Bin
150
+ "BIN": (148, 156),
151
+ # Phase Angle
152
+ "PHASE_ANGLE": (156, 166),
153
+ }
154
+
155
+
156
+ RATES_KEYS = [
157
+ # Start Right Full Constant Fraction Discriminator (CFD) Pulses
158
+ "START_RF",
159
+ # Start Left Full Constant Fraction Discriminator (CFD) Pulses
160
+ "START_LF",
161
+ # Start Position Right Full Constant Fraction Discriminator (CFD) Pulses
162
+ "START_RP",
163
+ # Start Position Left Constant Fraction Discriminator (CFD) Pulses
164
+ "START_LP",
165
+ # Stop Top North Constant Fraction Discriminator (CFD) Pulses
166
+ "STOP_TN",
167
+ # Stop Bottom North Constant Fraction Discriminator (CFD) Pulses
168
+ "STOP_BN",
169
+ # Stop Top East Constant Fraction Discriminator (CFD) Pulses
170
+ "STOP_TE",
171
+ # Stop Bottom East Constant Fraction Discriminator (CFD) Pulses
172
+ "STOP_BE",
173
+ # Stop Top South Constant Fraction Discriminator (CFD) Pulses
174
+ "STOP_TS",
175
+ # Stop Bottom South Constant Fraction Discriminator (CFD) Pulses
176
+ "STOP_BS",
177
+ # Stop Top West Constant Fraction Discriminator (CFD) Pulses
178
+ "STOP_TW",
179
+ # Stop Bottom West Constant Fraction Discriminator (CFD) Pulses
180
+ "STOP_BW",
181
+ # Coincidence Top North Constant Fraction Discriminator (CFD) Pulses
182
+ "COIN_TN",
183
+ # Coincidence Bottom North Constant Fraction Discriminator (CFD) Pulses
184
+ "COIN_BN",
185
+ # Coincidence Top South Constant Fraction Discriminator (CFD) Pulses
186
+ "COIN_TS",
187
+ # Coincidence Bottom South Constant Fraction Discriminator (CFD) Pulses
188
+ "COIN_BS",
189
+ # Coincidence Discrete Constant Fraction Discriminator (CFD) Pulses
190
+ "COIN_D",
191
+ # Solid State Detector (SSD) Energy Pulses
192
+ "SSD0",
193
+ "SSD1",
194
+ "SSD2",
195
+ "SSD3",
196
+ "SSD4",
197
+ "SSD5",
198
+ "SSD6",
199
+ "SSD7",
200
+ # Start Position Time to Digital Converter (TDC) Chip VE Pulses
201
+ "START_POS",
202
+ # Stop North TDC-chip VE Pulses
203
+ "STOP_N",
204
+ # Stop East TDC-chip VE Pulses
205
+ "STOP_E",
206
+ # Stop South TDC-chip VE Pulses
207
+ "STOP_S",
208
+ # Stop West TDC-chip VE Pulses
209
+ "STOP_W",
210
+ # Coincidence North TDC-chip VE Pulses
211
+ "COIN_N_TDC",
212
+ # Coincidence Discrete TDC-chip VE Pulses
213
+ "COIN_D_TDC",
214
+ # Coincidence South TDC-chip VE Pulses
215
+ "COIN_S_TDC",
216
+ # Stop Top North Valid Pulse Height Flag
217
+ "STOP_TOP_N",
218
+ # Stop Bottom North Valid Pulse Height Flag
219
+ "STOP_BOT_N",
220
+ # Start-Right/Stop Single Coincidence.
221
+ # Stop can be either Top or Bottom.
222
+ # Coincidence is allowed, but not required.
223
+ # No SSD.
224
+ "START_RIGHT_STOP_COIN_SINGLE",
225
+ # Start-Left/Stop Single Coincidence.
226
+ # Stop can be either Top or Bottom.
227
+ # Coincidence is allowed, but not required.
228
+ # No SSD.
229
+ "START_LEFT_STOP_COIN_SINGLE",
230
+ # Start-Right/Stop/Coin Coincidence.
231
+ # Double Coincidence.
232
+ # Stop/Coin can be either Top or Bottom. No SSD.
233
+ "START_RIGHT_STOP_COIN_DOUBLE",
234
+ # Start-Left/Stop/Coin Coincidence.
235
+ # Double Coincidence.
236
+ # Stop/Coin can be either Top or Bottom. No SSD.
237
+ "START_LEFT_STOP_COIN_DOUBLE",
238
+ # Start/Stop/Coin Coincidence +
239
+ # Position Match.
240
+ # Double Coincidence + Fine Position Match
241
+ # between Stop and Coin measurements.
242
+ # No SSD.
243
+ "START_STOP_COIN_POS",
244
+ # Start-Right/SSD/Coin-D Coincidence.
245
+ # Energy Coincidence.
246
+ "START_RIGHT_SSD_COIN_D",
247
+ # Start-Left/SSD/Coin-D Coincidence.
248
+ # Energy Coincidence.
249
+ "START_LEFT_SSD_COIN_D",
250
+ # Event Analysis Activity Time.
251
+ "EVENT_ACTIVE_TIME",
252
+ # Events that would have been written to the FIFO.
253
+ # (attempted to write).
254
+ "FIFO_VALID_EVENTS",
255
+ # Events generated by the pulser.
256
+ "PULSER_EVENTS",
257
+ # Coincidence (windowed) between the Stop/Coin top.
258
+ "WINDOW_STOP_COIN",
259
+ # Coincidence between Start Left and Window-Stop/Coin.
260
+ "START_LEFT_WINDOW_STOP_COIN",
261
+ # Coincidence between Start Right and Window-Stop/Coin.
262
+ "START_RIGHT_WINDOW_STOP_COIN",
263
+ # TODO: Below will be added later. It is not in the current data.
264
+ # Processed events generated by the pulser.
265
+ # "PROCESSED_PULSER_EVENTS",
266
+ # Processed events.
267
+ # "PROCESSED_EVENTS",
268
+ # Discarded events.
269
+ # "DISCARDED_EVENTS"
270
+ ]
271
+
272
+
273
+ def append_fillval(decom_data: dict, packet): # type: ignore[no-untyped-def]
274
+ # ToDo, need packet param type
275
+ """
276
+ Append fill values to all fields.
277
+
278
+ Parameters
279
+ ----------
280
+ decom_data : dict
281
+ Parsed data.
282
+ packet : space_packet_parser.parser.Packet
283
+ Packet.
284
+ """
285
+ for key in decom_data:
286
+ if (key not in packet.header.keys()) and (key not in packet.data.keys()):
287
+ decom_data[key].append(np.iinfo(np.int64).min)
288
+
289
+
290
+ def parse_event(event_binary: str) -> dict:
291
+ """
292
+ Parse a binary string representing a single event.
293
+
294
+ Parameters
295
+ ----------
296
+ event_binary : str
297
+ Event binary string.
298
+
299
+ Returns
300
+ -------
301
+ fields_dict : dict
302
+ Dict of the fields for a single event.
303
+ """
304
+ fields_dict = {}
305
+ for field, (start, end) in EVENT_FIELD_RANGES.items():
306
+ field_value = int(event_binary[start:end], 2)
307
+ fields_dict[field] = field_value
308
+ return fields_dict
309
+
310
+
311
+ def append_ccsds_fields(decom_data: dict, ccsds_data_object: object) -> None:
312
+ """
313
+ Append CCSDS fields to event_data.
314
+
315
+ Parameters
316
+ ----------
317
+ decom_data : dict
318
+ Parsed data.
319
+ ccsds_data_object : DataclassInstance
320
+ CCSDS data object.
321
+ """
322
+ for field in fields(ccsds_data_object.__class__): # type: ignore[arg-type]
323
+ ccsds_key = field.name
324
+ if ccsds_key not in decom_data:
325
+ decom_data[ccsds_key] = []
326
+ decom_data[ccsds_key].append(getattr(ccsds_data_object, ccsds_key))
File without changes
@@ -0,0 +1,319 @@
1
+ """Generate ULTRA L1a CDFs."""
2
+
3
+ # TODO: Evaluate naming conventions for fields and variables
4
+ # TODO: Improved short and long descriptions for each variable
5
+ # TODO: Improved var_notes for each variable
6
+ import logging
7
+ from typing import Optional
8
+
9
+ import numpy as np
10
+ import xarray as xr
11
+
12
+ from imap_processing import decom, imap_module_directory
13
+ from imap_processing.cdf.imap_cdf_manager import ImapCdfAttributes
14
+ from imap_processing.spice.time import met_to_j2000ns
15
+ from imap_processing.ultra.l0.decom_ultra import process_ultra_apids
16
+ from imap_processing.ultra.l0.ultra_utils import (
17
+ ULTRA_AUX,
18
+ ULTRA_EVENTS,
19
+ ULTRA_RATES,
20
+ ULTRA_TOF,
21
+ )
22
+ from imap_processing.utils import group_by_apid
23
+
24
+ logger = logging.getLogger(__name__)
25
+
26
+
27
+ def initiate_data_arrays(decom_ultra: dict, apid: int) -> xr.Dataset:
28
+ """
29
+ Initiate xarray data arrays.
30
+
31
+ Parameters
32
+ ----------
33
+ decom_ultra : dict
34
+ Parsed data.
35
+ apid : int
36
+ Packet APID.
37
+
38
+ Returns
39
+ -------
40
+ dataset : xarray.Dataset
41
+ Data in xarray format.
42
+ """
43
+ if apid in ULTRA_EVENTS.apid:
44
+ index = ULTRA_EVENTS.apid.index(apid)
45
+ logical_source = ULTRA_EVENTS.logical_source[index]
46
+ addition_to_logical_desc = ULTRA_EVENTS.addition_to_logical_desc
47
+ raw_time = decom_ultra["EVENTTIMES"]
48
+ elif apid in ULTRA_TOF.apid:
49
+ index = ULTRA_TOF.apid.index(apid)
50
+ logical_source = ULTRA_TOF.logical_source[index]
51
+ addition_to_logical_desc = ULTRA_TOF.addition_to_logical_desc
52
+ raw_time = np.unique(decom_ultra["SHCOARSE"])
53
+ elif apid in ULTRA_AUX.apid:
54
+ index = ULTRA_AUX.apid.index(apid)
55
+ logical_source = ULTRA_AUX.logical_source[index]
56
+ addition_to_logical_desc = ULTRA_AUX.addition_to_logical_desc
57
+ raw_time = decom_ultra["SHCOARSE"]
58
+ elif apid in ULTRA_RATES.apid:
59
+ index = ULTRA_RATES.apid.index(apid)
60
+ logical_source = ULTRA_RATES.logical_source[index]
61
+ addition_to_logical_desc = ULTRA_RATES.addition_to_logical_desc
62
+ raw_time = decom_ultra["SHCOARSE"]
63
+ else:
64
+ raise ValueError(f"APID {apid} not recognized.")
65
+
66
+ # Load the CDF attributes
67
+ cdf_manager = ImapCdfAttributes()
68
+ cdf_manager.add_instrument_global_attrs("ultra")
69
+ cdf_manager.add_instrument_variable_attrs("ultra", "l1a")
70
+
71
+ epoch_time = xr.DataArray(
72
+ met_to_j2000ns(raw_time),
73
+ name="epoch",
74
+ dims=["epoch"],
75
+ attrs=cdf_manager.get_variable_attributes("epoch"),
76
+ )
77
+
78
+ sci_cdf_attrs = cdf_manager.get_global_attributes("imap_ultra_l1a_sci")
79
+ # replace the logical source and logical source description
80
+ sci_cdf_attrs["Logical_source"] = logical_source
81
+ sci_cdf_attrs["Logical_source_desc"] = (
82
+ f"IMAP Mission ULTRA Instrument Level-1A {addition_to_logical_desc} Data"
83
+ )
84
+
85
+ if apid not in (ULTRA_TOF.apid[0], ULTRA_TOF.apid[1]):
86
+ dataset = xr.Dataset(
87
+ coords={"epoch": epoch_time},
88
+ attrs=sci_cdf_attrs,
89
+ )
90
+ else:
91
+ row = xr.DataArray(
92
+ # Number of pixel rows
93
+ np.arange(54),
94
+ name="row",
95
+ dims=["row"],
96
+ attrs=cdf_manager.get_variable_attributes("ultra_metadata_attrs"),
97
+ )
98
+
99
+ column = xr.DataArray(
100
+ # Number of pixel columns
101
+ np.arange(180),
102
+ name="column",
103
+ dims=["column"],
104
+ attrs=cdf_manager.get_variable_attributes("ultra_metadata_attrs"),
105
+ )
106
+
107
+ sid = xr.DataArray(
108
+ # Number of pixel columns
109
+ np.arange(8),
110
+ name="sid",
111
+ dims=["sid"],
112
+ attrs=cdf_manager.get_variable_attributes("ultra_metadata_attrs"),
113
+ )
114
+
115
+ dataset = xr.Dataset(
116
+ coords={"epoch": epoch_time, "sid": sid, "row": row, "column": column},
117
+ attrs=sci_cdf_attrs,
118
+ )
119
+
120
+ return dataset
121
+
122
+
123
+ def get_event_time(decom_ultra_dict: dict) -> dict:
124
+ """
125
+ Get event times using data from events and aux packets.
126
+
127
+ Parameters
128
+ ----------
129
+ decom_ultra_dict : dict
130
+ Events and aux data.
131
+
132
+ Returns
133
+ -------
134
+ decom_events : dict
135
+ Ultra events data with calculated events timestamps.
136
+
137
+ Notes
138
+ -----
139
+ Equation for event time:
140
+ t = t_(spin start) + t_(spin start sub)/1000 +
141
+ t_(spin duration)/1000 * phase_angle/720
142
+ """
143
+ event_times, durations, spin_starts = ([] for _ in range(3))
144
+ decom_aux = decom_ultra_dict[ULTRA_AUX.apid[0]]
145
+ decom_events: dict = decom_ultra_dict[ULTRA_EVENTS.apid[0]]
146
+
147
+ timespinstart_array = np.array(decom_aux["TIMESPINSTART"])
148
+ timespinstartsub_array = np.array(decom_aux["TIMESPINSTARTSUB"]) / 1000
149
+
150
+ # spin start according to aux data
151
+ aux_spin_starts = timespinstart_array + timespinstartsub_array
152
+
153
+ for time in np.unique(decom_events["SHCOARSE"]):
154
+ # Get the nearest spin start and duration prior to the event
155
+ spin_start = aux_spin_starts[aux_spin_starts <= time][-1]
156
+ duration = np.array(decom_aux["DURATION"])[aux_spin_starts <= time][-1]
157
+
158
+ # Find the events
159
+ event_indices = np.where(np.array(decom_events["SHCOARSE"]) == time)
160
+
161
+ for event_index in event_indices[0]:
162
+ phase_angle = decom_events["PHASE_ANGLE"][event_index]
163
+
164
+ durations.append(duration)
165
+ spin_starts.append(spin_start)
166
+
167
+ # If there were no events, the time is set to 'SHCOARSE'
168
+ if decom_events["COUNT"][event_index] == 0:
169
+ event_times.append(decom_events["SHCOARSE"][event_index])
170
+ else:
171
+ event_times.append(spin_start + (duration / 1000) * (phase_angle / 720))
172
+
173
+ decom_events["DURATION"] = durations
174
+ decom_events["TIMESPINSTART"] = spin_starts
175
+ decom_events["EVENTTIMES"] = event_times
176
+
177
+ return decom_events
178
+
179
+
180
+ def create_dataset(decom_ultra_dict: dict) -> xr.Dataset:
181
+ """
182
+ Create xarray for packet.
183
+
184
+ Parameters
185
+ ----------
186
+ decom_ultra_dict : dict
187
+ Dictionary of parsed data.
188
+
189
+ Returns
190
+ -------
191
+ dataset : xarray.Dataset
192
+ Data in xarray format.
193
+ """
194
+ # Combine events and aux datasets so we can have proper event timestamps
195
+ if ULTRA_EVENTS.apid[0] in decom_ultra_dict.keys():
196
+ apid = ULTRA_EVENTS.apid[0]
197
+ decom_ultra = get_event_time(decom_ultra_dict)
198
+ else:
199
+ apid = next(iter(decom_ultra_dict.keys()))
200
+ decom_ultra = decom_ultra_dict[apid]
201
+
202
+ # Load the CDF attributes
203
+ # TODO: call this once and pass the object to the function
204
+ cdf_manager = ImapCdfAttributes()
205
+ cdf_manager.add_instrument_global_attrs("ultra")
206
+ cdf_manager.add_instrument_variable_attrs("ultra", "l1a")
207
+
208
+ dataset = initiate_data_arrays(decom_ultra, apid)
209
+
210
+ for key, value in decom_ultra.items():
211
+ # EVENT DATA and FASTDATA_00 have been broken down further
212
+ # (see ultra_utils.py) and are therefore not needed.
213
+ # SID is also not needed as it is used as a dimension.
214
+ if key in {"EVENTDATA", "FASTDATA_00", "SID"}:
215
+ continue
216
+ # Everything in the TOF packet has dimensions of (time, sid) except
217
+ # for PACKETDATA which has dimensions of (time, sid, row, column) and
218
+ # SHCOARSE with has dimensions of (time)
219
+ elif apid == ULTRA_TOF.apid[0] and key != "PACKETDATA" and key != "SHCOARSE":
220
+ # TODO: fix this to use the correct attributes
221
+ attrs = cdf_manager.get_variable_attributes("ultra_support_attrs")
222
+ dims = ["epoch", "sid"]
223
+ # AUX enums require string attributes
224
+ elif key in [
225
+ "SPINPERIODVALID",
226
+ "SPINPHASEVALID",
227
+ "SPINPERIODSOURCE",
228
+ "CATBEDHEATERFLAG",
229
+ "HWMODE",
230
+ "IMCENB",
231
+ "LEFTDEFLECTIONCHARGE",
232
+ "RIGHTDEFLECTIONCHARGE",
233
+ ]:
234
+ # TODO: fix this to use the correct attributes
235
+ attrs = cdf_manager.get_variable_attributes("string_base_attrs")
236
+ dims = ["epoch"]
237
+ # TOF packetdata has multiple dimensions
238
+ elif key == "PACKETDATA":
239
+ # TODO: fix this to use the correct attributes
240
+ attrs = cdf_manager.get_variable_attributes("packet_data_attrs")
241
+ dims = ["epoch", "sid", "row", "column"]
242
+ # Use metadata with a single dimension for
243
+ # all other data products
244
+ else:
245
+ # TODO: fix this to use the correct attributes
246
+ attrs = cdf_manager.get_variable_attributes("ultra_support_attrs")
247
+ dims = ["epoch"]
248
+
249
+ dataset[key] = xr.DataArray(
250
+ value,
251
+ name=key if key == "epoch" else key.lower(),
252
+ dims=dims,
253
+ attrs=attrs,
254
+ )
255
+
256
+ return dataset
257
+
258
+
259
+ def ultra_l1a(
260
+ packet_file: str, data_version: str, apid: Optional[int] = None
261
+ ) -> list[xr.Dataset]:
262
+ """
263
+ Will process ULTRA L0 data into L1A CDF files at output_filepath.
264
+
265
+ Parameters
266
+ ----------
267
+ packet_file : str
268
+ Path to the CCSDS data packet file.
269
+ data_version : str
270
+ Version of the data product being created.
271
+ apid : Optional[int]
272
+ Optional apid.
273
+
274
+ Returns
275
+ -------
276
+ output_datasets : list[xarray.Dataset]
277
+ List of xarray.Dataset.
278
+ """
279
+ xtce = str(
280
+ f"{imap_module_directory}/ultra/packet_definitions/" f"ULTRA_SCI_COMBINED.xml"
281
+ )
282
+
283
+ packets = decom.decom_packets(packet_file, xtce)
284
+ grouped_data = group_by_apid(packets)
285
+
286
+ output_datasets = []
287
+
288
+ # This is used for two purposes currently:
289
+ # 1. For testing purposes to only generate a dataset for a single apid.
290
+ # Each test dataset is only for a single apid while the rest of the apids
291
+ # contain zeros. Ideally we would have
292
+ # test data for all apids and remove this parameter.
293
+ # 2. When we are generating the l1a dataset for the events packet since
294
+ # right now we need to combine the events and aux packets to get the
295
+ # correct event timestamps (get_event_time). This part will change
296
+ # when we begin using the spin table in the database instead of the aux packet.
297
+ if apid is not None:
298
+ apids = [apid]
299
+ else:
300
+ apids = list(grouped_data.keys())
301
+
302
+ for apid in apids:
303
+ if apid == ULTRA_EVENTS.apid[0]:
304
+ decom_ultra_dict = {
305
+ apid: process_ultra_apids(grouped_data[apid], apid),
306
+ ULTRA_AUX.apid[0]: process_ultra_apids(
307
+ grouped_data[ULTRA_AUX.apid[0]], ULTRA_AUX.apid[0]
308
+ ),
309
+ }
310
+ else:
311
+ decom_ultra_dict = {
312
+ apid: process_ultra_apids(grouped_data[apid], apid),
313
+ }
314
+ dataset = create_dataset(decom_ultra_dict)
315
+ # TODO: move this to use ImapCdfAttributes().add_global_attribute()
316
+ dataset.attrs["Data_version"] = data_version
317
+ output_datasets.append(dataset)
318
+
319
+ return output_datasets
@@ -0,0 +1,26 @@
1
+ """Calculate Badtimes."""
2
+
3
+ import xarray as xr
4
+
5
+ from imap_processing.ultra.utils.ultra_l1_utils import create_dataset
6
+
7
+
8
+ def calculate_badtimes(extended_spin_dict: dict, name: str) -> xr.Dataset:
9
+ """
10
+ Create dataset with defined datatypes for Badtimes Data.
11
+
12
+ Parameters
13
+ ----------
14
+ extended_spin_dict : dict
15
+ L1b data dictionary.
16
+ name : str
17
+ Name of the dataset.
18
+
19
+ Returns
20
+ -------
21
+ badtimes_dataset : xarray.Dataset
22
+ Dataset containing the data.
23
+ """
24
+ badtimes_dataset = create_dataset(extended_spin_dict, name, "l1b")
25
+
26
+ return badtimes_dataset
@@ -0,0 +1,26 @@
1
+ """Calculate Culling Mask."""
2
+
3
+ import xarray as xr
4
+
5
+ from imap_processing.ultra.utils.ultra_l1_utils import create_dataset
6
+
7
+
8
+ def calculate_cullingmask(extended_spin_dict: dict, name: str) -> xr.Dataset:
9
+ """
10
+ Create dataset with defined datatype for Culling Mask Data.
11
+
12
+ Parameters
13
+ ----------
14
+ extended_spin_dict : dict
15
+ L1b data dictionary.
16
+ name : str
17
+ Name of the dataset.
18
+
19
+ Returns
20
+ -------
21
+ cullingmask_dataset : xarray.Dataset
22
+ Dataset containing the data.
23
+ """
24
+ cullingmask_dataset = create_dataset(extended_spin_dict, name, "l1b")
25
+
26
+ return cullingmask_dataset