SXXXXXXX_PyBusMonitor1553/doc/Radar-Startup-Guide.md
2025-12-17 07:59:30 +01:00

293 lines
7.0 KiB
Markdown

# Radar Startup Sequence
## Overview
Questo modulo implementa la sequenza di inizializzazione radar identica a quella utilizzata da GrifoScope, analizzata dal codice sorgente C++.
## Background - Analisi GrifoScope
### Sequenza Originale (da `g346_a1a2.cpp`)
GrifoScope all'avvio esegue:
1. **Inizializzazione Sicura** (`startProtection()`):
```cpp
// A1
dSymbInt.setFromUser(127); // Symbol intensity massima
dIfGain.setFromUser(127); // IF Gain massimo
// A2
dSilence.setFromUser(1); // Silence ON → TX disabilitato
dStby.setFromUser(1); // Standby ON → Radar inattivo
```
2. **Attivazione** (quando utente preme "Run" e toglie Standby/Silence):
```cpp
actSTBY.setActionValue(0, 1); // Toggle: 0=OFF, 1=ON
// Shortcut: CTRL+F1
```
## Campi 1553 Critici
### Messaggio A2 - Word 01 (Radar Mode Command)
| Campo | Bit | Descrizione | Valori |
|-------|-----|-------------|--------|
| **stby** | 7 | Standby control | 0=OFF (operativo), 1=ON (standby) |
| **silence** | 3 | Silence control | 0=OFF (TX abilitato), 1=ON (TX disabilitato) |
| **freeze** | 6 | Freeze selection | 0=No freeze, 1=Freeze |
| **ibit_request** | 8 | IBIT request | 0=No IBIT, 1=Request IBIT |
**Nota bit positions**: Usano `IDD_REVBIT16(n) = 15-n` dal C++
## API Python
### Funzioni Principali
#### `initialize_radar_safe_state() -> (MsgA1, MsgA2)`
Crea messaggi con configurazione sicura iniziale:
- A1: `symbol_intensity=127` (massimo)
- A2: `stby=1, silence=1, mode=NO_OPERATION`
```python
from pybusmonitor1553.core.radar_startup import initialize_radar_safe_state
msg_a1, msg_a2 = initialize_radar_safe_state()
bc.send_command(1, msg_a1)
bc.send_command(2, msg_a2)
```
#### `activate_radar_operational(...) -> MsgA2`
Crea messaggio A2 per attivazione (Standby/Silence OFF):
```python
from pybusmonitor1553.core.radar_startup import activate_radar_operational
from pybusmonitor1553.lib1553.constants import MasterMode
msg_a2 = activate_radar_operational(
master_mode=MasterMode.RWS,
designation_control=2, # TWS
range_scale=0,
scan_width=0
)
bc.send_command(2, msg_a2)
```
#### `radar_startup_sequence(bc, ...) -> bool`
Sequenza completa automatica:
```python
from pybusmonitor1553.core.bus_controller import BusController
from pybusmonitor1553.core.radar_startup import radar_startup_sequence
from pybusmonitor1553.lib1553.constants import MasterMode
bc = BusController(rt_ip="192.168.1.100")
bc.connect()
success = radar_startup_sequence(
bc,
target_mode=MasterMode.RWS,
verify_steps=True, # Verifica con B7 ogni step
step_delay=0.5 # 500ms tra gli step
)
if success:
print("Radar ready!")
```
#### `quick_start_radar(...) -> BusController`
All-in-one: connette e avvia radar in una chiamata:
```python
from pybusmonitor1553.core.radar_startup import quick_start_radar
bc = quick_start_radar(
rt_ip="192.168.1.100",
mode=MasterMode.RWS
)
if bc:
# Radar pronto, bc già connesso
bc.send_command(...)
```
## Sequenza Step-by-Step
### Step 1: SAFE MODE (Power-On Protection)
```python
# Crea messaggi sicuri
msg_a1, msg_a2_safe = initialize_radar_safe_state()
# Invia al radar
bc.send_command(1, msg_a1)
time.sleep(0.1)
bc.send_command(2, msg_a2_safe)
# Stato: Radar in standby, TX disabilitato
```
### Step 2: Verifica Stato (Opzionale)
```python
msg_b7 = bc.request_data(7, MsgB7, timeout=1.0)
if msg_b7:
print(f"Mode: {msg_b7.master_mode}")
print(f"Valid: {msg_b7.valid_data_flag == 0}")
```
### Step 3: Attivazione Operativa
```python
msg_a2_active = activate_radar_operational(
master_mode=MasterMode.RWS
)
bc.send_command(2, msg_a2_active)
# Stato: Radar operativo, TX abilitato
```
### Step 4: Verifica Attivazione
```python
msg_b7 = bc.request_data(7, MsgB7, timeout=1.0)
if msg_b7 and msg_b7.valid_data_flag == 0:
print("✓ Radar OPERATIONAL")
```
## Esempi Completi
Vedi `tools/radar_startup_examples.py`:
1. **Manual Startup** - Step-by-step manuale
2. **Automatic Startup** - Usando `radar_startup_sequence()`
3. **Quick Start** - All-in-one con `quick_start_radar()`
4. **Shutdown Sequence** - Ritorno sicuro a SAFE MODE
5. **Continuous Operation** - Ciclo completo con cambio modi
6. **Error Handling** - Gestione timeout e recovery
### Esecuzione Esempi
```bash
cd tools
python radar_startup_examples.py
```
## Testing Senza Hardware
Per testare senza radar reale:
```python
# Usa localhost con simulatore RT (futuro)
bc = BusController(rt_ip="127.0.0.1", rt_port=51553)
bc.connect()
# Oppure verifica solo la creazione messaggi
msg_a1, msg_a2 = initialize_radar_safe_state()
print(f"A2 packed: {msg_a2.pack().hex()}")
```
## Logging
Il modulo usa logging standard Python:
```python
import logging
logging.basicConfig(
level=logging.INFO,
format='%(asctime)s - %(name)s - %(levelname)s - %(message)s'
)
# Output:
# 2025-12-16 10:30:00 - radar_startup - INFO - Step 1: Sending SAFE MODE configuration
# 2025-12-16 10:30:01 - radar_startup - INFO - ✓ SAFE MODE messages sent
# ...
```
## Troubleshooting
### Radar non risponde a B7
```python
# Verifica connessione
if not bc.is_connected:
bc.connect()
# Aumenta timeout
msg_b7 = bc.request_data(7, MsgB7, timeout=2.0)
# Verifica rete
bc.get_statistics() # Controlla timeouts
```
### Startup fallisce
```python
# Prova senza verifiche intermedie
success = radar_startup_sequence(
bc,
verify_steps=False, # Skip B7 checks
step_delay=1.0 # Più tempo tra step
)
# Oppure manuale recovery
msg_a1, msg_a2 = initialize_radar_safe_state()
bc.send_command(1, msg_a1)
bc.send_command(2, msg_a2)
```
### Valori campi non corretti
```python
# Debug: stampa valori packed
msg_a2 = activate_radar_operational()
print(f"A2 word 0: 0x{struct.unpack('>H', msg_a2.pack()[0:2])[0]:04X}")
# Verifica bit positions
assert msg_a2.stby == 0, "Standby should be OFF"
assert msg_a2.silence == 0, "Silence should be OFF"
```
## Integrazione con GUI
```python
class RadarControlPanel:
def __init__(self):
self.bc = BusController()
def on_run_button_clicked(self):
"""Equivalente al pulsante 'Run' di GrifoScope"""
if not self.bc.is_connected:
self.bc.connect()
# Startup automatico
success = radar_startup_sequence(self.bc)
if success:
self.status_label.setText("Radar OPERATIONAL")
self.enable_controls(True)
def on_standby_toggle(self):
"""Equivalente a CTRL+F1 in GrifoScope"""
msg_a2 = MsgA2()
msg_a2.stby = 1 if self.standby_active else 0
self.bc.send_command(2, msg_a2)
```
## Riferimenti
- **Analisi Completa**: `doc/GrifoScope-Startup-Sequence.md`
- **ICD Reference**: `doc/ICD_DECD_FTH - GRIFO-F_TH...md`
- **C++ Source**: `cpp/GrifoScope/GrifoMCS/GADS/MCS/MCS_G346/g346/g346_a1a2.cpp`
- **Message Definitions**: `pybusmonitor1553/lib1553/messages/msg_a2.py`
## See Also
- [Bus Controller README](../pybusmonitor1553/core/README_BusController.md)
- [UDP1553 Protocol](../doc/UDP1553-Protocol-Implementation.md)
- [Message Mapping](../doc/C++-Python-Message-Mapping.md)