oscura 0.7.0__py3-none-any.whl → 0.10.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 (175) hide show
  1. oscura/__init__.py +19 -19
  2. oscura/analyzers/__init__.py +2 -0
  3. oscura/analyzers/digital/extraction.py +2 -3
  4. oscura/analyzers/digital/quality.py +1 -1
  5. oscura/analyzers/digital/timing.py +1 -1
  6. oscura/analyzers/eye/__init__.py +5 -1
  7. oscura/analyzers/eye/generation.py +501 -0
  8. oscura/analyzers/jitter/__init__.py +6 -6
  9. oscura/analyzers/jitter/timing.py +419 -0
  10. oscura/analyzers/patterns/__init__.py +94 -0
  11. oscura/analyzers/patterns/reverse_engineering.py +991 -0
  12. oscura/analyzers/power/__init__.py +35 -12
  13. oscura/analyzers/power/basic.py +3 -3
  14. oscura/analyzers/power/soa.py +1 -1
  15. oscura/analyzers/power/switching.py +3 -3
  16. oscura/analyzers/signal_classification.py +529 -0
  17. oscura/analyzers/signal_integrity/sparams.py +3 -3
  18. oscura/analyzers/statistics/__init__.py +4 -0
  19. oscura/analyzers/statistics/basic.py +152 -0
  20. oscura/analyzers/statistics/correlation.py +47 -6
  21. oscura/analyzers/validation.py +1 -1
  22. oscura/analyzers/waveform/__init__.py +2 -0
  23. oscura/analyzers/waveform/measurements.py +329 -163
  24. oscura/analyzers/waveform/measurements_with_uncertainty.py +91 -35
  25. oscura/analyzers/waveform/spectral.py +498 -54
  26. oscura/api/dsl/commands.py +15 -6
  27. oscura/api/server/templates/base.html +137 -146
  28. oscura/api/server/templates/export.html +84 -110
  29. oscura/api/server/templates/home.html +248 -267
  30. oscura/api/server/templates/protocols.html +44 -48
  31. oscura/api/server/templates/reports.html +27 -35
  32. oscura/api/server/templates/session_detail.html +68 -78
  33. oscura/api/server/templates/sessions.html +62 -72
  34. oscura/api/server/templates/waveforms.html +54 -64
  35. oscura/automotive/__init__.py +1 -1
  36. oscura/automotive/can/session.py +1 -1
  37. oscura/automotive/dbc/generator.py +638 -23
  38. oscura/automotive/dtc/data.json +102 -17
  39. oscura/automotive/uds/decoder.py +99 -6
  40. oscura/cli/analyze.py +8 -2
  41. oscura/cli/batch.py +36 -5
  42. oscura/cli/characterize.py +18 -4
  43. oscura/cli/export.py +47 -5
  44. oscura/cli/main.py +2 -0
  45. oscura/cli/onboarding/wizard.py +10 -6
  46. oscura/cli/pipeline.py +585 -0
  47. oscura/cli/visualize.py +6 -4
  48. oscura/convenience.py +400 -32
  49. oscura/core/config/loader.py +0 -1
  50. oscura/core/measurement_result.py +286 -0
  51. oscura/core/progress.py +1 -1
  52. oscura/core/schemas/device_mapping.json +8 -2
  53. oscura/core/schemas/packet_format.json +24 -4
  54. oscura/core/schemas/protocol_definition.json +12 -2
  55. oscura/core/types.py +300 -199
  56. oscura/correlation/multi_protocol.py +1 -1
  57. oscura/export/legacy/__init__.py +11 -0
  58. oscura/export/legacy/wav.py +75 -0
  59. oscura/exporters/__init__.py +19 -0
  60. oscura/exporters/wireshark.py +809 -0
  61. oscura/hardware/acquisition/file.py +5 -19
  62. oscura/hardware/acquisition/saleae.py +10 -10
  63. oscura/hardware/acquisition/socketcan.py +4 -6
  64. oscura/hardware/acquisition/synthetic.py +1 -5
  65. oscura/hardware/acquisition/visa.py +6 -6
  66. oscura/hardware/security/side_channel_detector.py +5 -508
  67. oscura/inference/message_format.py +686 -1
  68. oscura/jupyter/display.py +2 -2
  69. oscura/jupyter/magic.py +3 -3
  70. oscura/loaders/__init__.py +17 -12
  71. oscura/loaders/binary.py +1 -1
  72. oscura/loaders/chipwhisperer.py +1 -2
  73. oscura/loaders/configurable.py +1 -1
  74. oscura/loaders/csv_loader.py +2 -2
  75. oscura/loaders/hdf5_loader.py +1 -1
  76. oscura/loaders/lazy.py +6 -1
  77. oscura/loaders/mmap_loader.py +0 -1
  78. oscura/loaders/numpy_loader.py +8 -7
  79. oscura/loaders/preprocessing.py +3 -5
  80. oscura/loaders/rigol.py +21 -7
  81. oscura/loaders/sigrok.py +2 -5
  82. oscura/loaders/tdms.py +3 -2
  83. oscura/loaders/tektronix.py +38 -32
  84. oscura/loaders/tss.py +20 -27
  85. oscura/loaders/vcd.py +13 -8
  86. oscura/loaders/wav.py +1 -6
  87. oscura/pipeline/__init__.py +76 -0
  88. oscura/pipeline/handlers/__init__.py +165 -0
  89. oscura/pipeline/handlers/analyzers.py +1045 -0
  90. oscura/pipeline/handlers/decoders.py +899 -0
  91. oscura/pipeline/handlers/exporters.py +1103 -0
  92. oscura/pipeline/handlers/filters.py +891 -0
  93. oscura/pipeline/handlers/loaders.py +640 -0
  94. oscura/pipeline/handlers/transforms.py +768 -0
  95. oscura/reporting/__init__.py +88 -1
  96. oscura/reporting/automation.py +348 -0
  97. oscura/reporting/citations.py +374 -0
  98. oscura/reporting/core.py +54 -0
  99. oscura/reporting/formatting/__init__.py +11 -0
  100. oscura/reporting/formatting/measurements.py +320 -0
  101. oscura/reporting/html.py +57 -0
  102. oscura/reporting/interpretation.py +431 -0
  103. oscura/reporting/summary.py +329 -0
  104. oscura/reporting/templates/enhanced/protocol_re.html +504 -503
  105. oscura/reporting/visualization.py +542 -0
  106. oscura/side_channel/__init__.py +38 -57
  107. oscura/utils/builders/signal_builder.py +5 -5
  108. oscura/utils/comparison/compare.py +7 -9
  109. oscura/utils/comparison/golden.py +1 -1
  110. oscura/utils/filtering/convenience.py +2 -2
  111. oscura/utils/math/arithmetic.py +38 -62
  112. oscura/utils/math/interpolation.py +20 -20
  113. oscura/utils/pipeline/__init__.py +4 -17
  114. oscura/utils/progressive.py +1 -4
  115. oscura/utils/triggering/edge.py +1 -1
  116. oscura/utils/triggering/pattern.py +2 -2
  117. oscura/utils/triggering/pulse.py +2 -2
  118. oscura/utils/triggering/window.py +3 -3
  119. oscura/validation/hil_testing.py +11 -11
  120. oscura/visualization/__init__.py +47 -284
  121. oscura/visualization/batch.py +160 -0
  122. oscura/visualization/plot.py +542 -53
  123. oscura/visualization/styles.py +184 -318
  124. oscura/workflows/__init__.py +2 -0
  125. oscura/workflows/batch/advanced.py +1 -1
  126. oscura/workflows/batch/aggregate.py +7 -8
  127. oscura/workflows/complete_re.py +251 -23
  128. oscura/workflows/digital.py +27 -4
  129. oscura/workflows/multi_trace.py +136 -17
  130. oscura/workflows/waveform.py +788 -0
  131. {oscura-0.7.0.dist-info → oscura-0.10.0.dist-info}/METADATA +59 -79
  132. {oscura-0.7.0.dist-info → oscura-0.10.0.dist-info}/RECORD +135 -149
  133. oscura/side_channel/dpa.py +0 -1025
  134. oscura/utils/optimization/__init__.py +0 -19
  135. oscura/utils/optimization/parallel.py +0 -443
  136. oscura/utils/optimization/search.py +0 -532
  137. oscura/utils/pipeline/base.py +0 -338
  138. oscura/utils/pipeline/composition.py +0 -248
  139. oscura/utils/pipeline/parallel.py +0 -449
  140. oscura/utils/pipeline/pipeline.py +0 -375
  141. oscura/utils/search/__init__.py +0 -16
  142. oscura/utils/search/anomaly.py +0 -424
  143. oscura/utils/search/context.py +0 -294
  144. oscura/utils/search/pattern.py +0 -288
  145. oscura/utils/storage/__init__.py +0 -61
  146. oscura/utils/storage/database.py +0 -1166
  147. oscura/visualization/accessibility.py +0 -526
  148. oscura/visualization/annotations.py +0 -371
  149. oscura/visualization/axis_scaling.py +0 -305
  150. oscura/visualization/colors.py +0 -451
  151. oscura/visualization/digital.py +0 -436
  152. oscura/visualization/eye.py +0 -571
  153. oscura/visualization/histogram.py +0 -281
  154. oscura/visualization/interactive.py +0 -1035
  155. oscura/visualization/jitter.py +0 -1042
  156. oscura/visualization/keyboard.py +0 -394
  157. oscura/visualization/layout.py +0 -400
  158. oscura/visualization/optimization.py +0 -1079
  159. oscura/visualization/palettes.py +0 -446
  160. oscura/visualization/power.py +0 -508
  161. oscura/visualization/power_extended.py +0 -955
  162. oscura/visualization/presets.py +0 -469
  163. oscura/visualization/protocols.py +0 -1246
  164. oscura/visualization/render.py +0 -223
  165. oscura/visualization/rendering.py +0 -444
  166. oscura/visualization/reverse_engineering.py +0 -838
  167. oscura/visualization/signal_integrity.py +0 -989
  168. oscura/visualization/specialized.py +0 -643
  169. oscura/visualization/spectral.py +0 -1226
  170. oscura/visualization/thumbnails.py +0 -340
  171. oscura/visualization/time_axis.py +0 -351
  172. oscura/visualization/waveform.py +0 -454
  173. {oscura-0.7.0.dist-info → oscura-0.10.0.dist-info}/WHEEL +0 -0
  174. {oscura-0.7.0.dist-info → oscura-0.10.0.dist-info}/entry_points.txt +0 -0
  175. {oscura-0.7.0.dist-info → oscura-0.10.0.dist-info}/licenses/LICENSE +0 -0
@@ -1,12 +1,13 @@
1
- """Power analysis module for Oscura.
1
+ """Power analysis module for Oscura - IEEE 1459-2010 compliant.
2
2
 
3
3
  Provides comprehensive power analysis capabilities including:
4
- - Basic power measurements (instantaneous, average, RMS, peak)
5
- - AC power analysis (reactive, apparent, power factor)
4
+ - Basic power measurements (instantaneous, average, RMS, peak) per IEEE 1459
5
+ - AC power analysis (reactive, apparent, power factor, harmonics) per IEEE 1459
6
6
  - Switching loss analysis for power electronics
7
+ - Conduction loss analysis (MOSFET, IGBT, diode)
7
8
  - Safe Operating Area (SOA) analysis
8
- - Ripple measurement
9
- - Efficiency calculations
9
+ - Ripple measurement and analysis
10
+ - Efficiency calculations (single and multi-output)
10
11
 
11
12
 
12
13
  Example:
@@ -14,6 +15,9 @@ Example:
14
15
  >>> power_trace = instantaneous_power(voltage_trace, current_trace)
15
16
  >>> stats = power_statistics(power_trace)
16
17
  >>> print(f"Average power: {stats['average']:.2f} W")
18
+
19
+ References:
20
+ IEEE 1459-2010: Standard for Power Quality Definitions
17
21
  """
18
22
 
19
23
  from oscura.analyzers.power.ac_power import (
@@ -23,6 +27,7 @@ from oscura.analyzers.power.ac_power import (
23
27
  phase_angle,
24
28
  power_factor,
25
29
  reactive_power,
30
+ three_phase_power,
26
31
  total_harmonic_distortion_power,
27
32
  )
28
33
  from oscura.analyzers.power.basic import (
@@ -30,39 +35,51 @@ from oscura.analyzers.power.basic import (
30
35
  energy,
31
36
  instantaneous_power,
32
37
  peak_power,
38
+ power_profile,
33
39
  power_statistics,
34
40
  rms_power,
35
41
  )
36
42
  from oscura.analyzers.power.conduction import (
37
43
  conduction_loss,
44
+ diode_conduction_loss,
38
45
  duty_cycle_weighted_loss,
39
46
  forward_voltage,
47
+ igbt_conduction_loss,
40
48
  mosfet_conduction_loss,
41
49
  on_resistance,
50
+ temperature_derating,
42
51
  )
43
52
  from oscura.analyzers.power.efficiency import (
44
53
  efficiency,
54
+ efficiency_vs_load,
55
+ loss_breakdown,
45
56
  multi_output_efficiency,
46
57
  power_conversion_efficiency,
58
+ thermal_efficiency,
47
59
  )
48
60
  from oscura.analyzers.power.ripple import (
49
61
  extract_ripple,
50
62
  ripple,
63
+ ripple_envelope,
51
64
  ripple_frequency,
65
+ ripple_harmonics,
52
66
  ripple_percentage,
53
67
  ripple_statistics,
54
68
  )
55
69
  from oscura.analyzers.power.soa import (
56
70
  SOALimit,
71
+ SOAViolation,
57
72
  check_soa_violations,
58
73
  create_mosfet_soa,
59
74
  plot_soa,
60
75
  soa_analysis,
61
76
  )
62
77
  from oscura.analyzers.power.switching import (
78
+ SwitchingEvent,
63
79
  switching_energy,
64
80
  switching_frequency,
65
81
  switching_loss,
82
+ switching_times,
66
83
  total_switching_loss,
67
84
  turn_off_loss,
68
85
  turn_on_loss,
@@ -70,22 +87,25 @@ from oscura.analyzers.power.switching import (
70
87
 
71
88
  __all__ = [
72
89
  "SOALimit",
90
+ "SOAViolation",
91
+ "SwitchingEvent",
73
92
  "apparent_power",
74
93
  "average_power",
75
94
  "check_soa_violations",
76
- # Conduction
77
95
  "conduction_loss",
78
96
  "create_mosfet_soa",
97
+ "diode_conduction_loss",
79
98
  "displacement_power_factor",
80
99
  "distortion_power_factor",
81
100
  "duty_cycle_weighted_loss",
82
- # Efficiency
83
101
  "efficiency",
102
+ "efficiency_vs_load",
84
103
  "energy",
85
104
  "extract_ripple",
86
105
  "forward_voltage",
87
- # Basic power
106
+ "igbt_conduction_loss",
88
107
  "instantaneous_power",
108
+ "loss_breakdown",
89
109
  "mosfet_conduction_loss",
90
110
  "multi_output_efficiency",
91
111
  "on_resistance",
@@ -94,21 +114,24 @@ __all__ = [
94
114
  "plot_soa",
95
115
  "power_conversion_efficiency",
96
116
  "power_factor",
117
+ "power_profile",
97
118
  "power_statistics",
98
- # AC power
99
119
  "reactive_power",
100
- # Ripple
101
120
  "ripple",
121
+ "ripple_envelope",
102
122
  "ripple_frequency",
123
+ "ripple_harmonics",
103
124
  "ripple_percentage",
104
125
  "ripple_statistics",
105
126
  "rms_power",
106
- # SOA
107
127
  "soa_analysis",
108
128
  "switching_energy",
109
129
  "switching_frequency",
110
- # Switching
111
130
  "switching_loss",
131
+ "switching_times",
132
+ "temperature_derating",
133
+ "thermal_efficiency",
134
+ "three_phase_power",
112
135
  "total_harmonic_distortion_power",
113
136
  "total_switching_loss",
114
137
  "turn_off_loss",
@@ -232,7 +232,7 @@ def energy(
232
232
  power = instantaneous_power(voltage, current)
233
233
 
234
234
  data = power.data
235
- sample_period = power.metadata.time_base
235
+ sample_period = 1.0 / power.metadata.sample_rate
236
236
 
237
237
  # Apply time limits
238
238
  if start_time is not None or end_time is not None:
@@ -290,7 +290,7 @@ def power_statistics(
290
290
  power = instantaneous_power(voltage, current)
291
291
 
292
292
  data = power.data
293
- sample_period = power.metadata.time_base
293
+ sample_period = 1.0 / power.metadata.sample_rate
294
294
 
295
295
  # Use scipy trapezoid for stable API across NumPy versions
296
296
  from scipy.integrate import trapezoid
@@ -330,7 +330,7 @@ def power_profile(
330
330
  """
331
331
  power = instantaneous_power(voltage, current)
332
332
  data = power.data
333
- sample_period = power.metadata.time_base
333
+ sample_period = 1.0 / power.metadata.sample_rate
334
334
 
335
335
  if window_size is None:
336
336
  # Auto-select: ~1% of total samples or 100, whichever is larger
@@ -105,7 +105,7 @@ def soa_analysis(
105
105
  min_len = min(len(v_data), len(i_data))
106
106
  v_data = v_data[:min_len]
107
107
  i_data = i_data[:min_len]
108
- sample_period = voltage.metadata.time_base
108
+ sample_period = 1.0 / voltage.metadata.sample_rate
109
109
 
110
110
  # Select applicable limits based on pulse width
111
111
  if pulse_width is None:
@@ -65,7 +65,7 @@ def _prepare_switching_data(
65
65
  v_data = voltage.data[:min_len]
66
66
  i_data = current.data[:min_len]
67
67
  p_data = power.data[:min_len]
68
- sample_period = power.metadata.time_base
68
+ sample_period = 1.0 / power.metadata.sample_rate
69
69
  return v_data, i_data, p_data, sample_period
70
70
 
71
71
 
@@ -386,7 +386,7 @@ def switching_energy(
386
386
  >>> print(f"Switching energy: {e*1e9:.2f} nJ")
387
387
  """
388
388
  power = instantaneous_power(voltage, current)
389
- sample_period = power.metadata.time_base
389
+ sample_period = 1.0 / power.metadata.sample_rate
390
390
  time_vector = np.arange(len(power.data)) * sample_period
391
391
 
392
392
  # Select time window
@@ -540,7 +540,7 @@ def switching_times(
540
540
  min_len = min(len(voltage.data), len(current.data))
541
541
  v_data = voltage.data[:min_len]
542
542
  i_data = current.data[:min_len]
543
- sample_period = voltage.metadata.time_base
543
+ sample_period = 1.0 / voltage.metadata.sample_rate
544
544
 
545
545
  v_min, v_max = float(np.min(v_data)), float(np.max(v_data))
546
546
  i_min, i_max = float(np.min(i_data)), float(np.max(i_data))