#ifndef SPOOF_GATE_CLIENT_H
#define SPOOF_GATE_CLIENT_H

// ============================================================================
// Spoof Gate Client — T1 consumer of gateway rid_spoof_gate.py scores
//
// The T2 gateway (pdl_platform/pdl_quantum/integrations/rid_spoof_gate.py)
// computes a per-track spoof probability in [0,1] and broadcasts it over
// the LoRa mesh as MSG_TYPE_SPOOF_SCORE (0x11).
//
// This module maintains an 8-entry LRU cache of received scores, expiring
// entries after 30 seconds.  threat_correlator.cpp can query the cache to
// down-weight candidate confidence for flagged tracks.
//
// Wire-up (do NOT edit existing files — see SPOOF_PEC_INTEGRATION_NOTES.md):
//   - config.h: add #define MSG_TYPE_SPOOF_SCORE 0x11
//   - main.cpp setup(): call spoof_gate_init();
//   - main.cpp loop() dispatch switch: add
//       case MSG_TYPE_SPOOF_SCORE:
//           spoof_gate_handle_packet(rx_buf, rx_len);
//           break;
//   - threat_correlator.cpp correlator_run(): apply score (see notes file)
// ============================================================================

#include <cstdint>
#include <cstddef>

// ---------------------------------------------------------------------------
// On-wire message layout (8 bytes, little-endian)
// ---------------------------------------------------------------------------
// Byte 0    : msg_type = MSG_TYPE_SPOOF_SCORE (0x11)  — written by gateway
// Bytes 1-4 : track_id  (uint32_t LE)
// Byte 5    : score_q8  (uint8_t, score * 255 rounded)
// Bytes 6-7 : reserved (must be 0x00)
//
// NOTE: msg_type is the first byte of rx_buf and has already been consumed
// by main.cpp's switch() before handle_packet is called.  The full 8-byte
// buffer (including byte 0) is passed; parse starts at offset 1.
// ---------------------------------------------------------------------------
struct SpoofScoreMsg {
    uint32_t track_id;      // mesh track identifier
    uint8_t  score_q8;      // spoof probability * 255  (0 = clean, 255 = certain spoof)
    uint8_t  reserved[3];   // padding — must be 0
} __attribute__((packed));

// Minimum on-wire length accepted by handle_packet (msg_type + struct)
#define SPOOF_SCORE_MSG_MIN_LEN (1u + sizeof(SpoofScoreMsg))

// Cache configuration (static memory only)
#define SPOOF_GATE_CACHE_SIZE    8u     // max concurrent tracks cached
#define SPOOF_GATE_ENTRY_TTL_MS  30000u // entries expire after 30 seconds

// ---------------------------------------------------------------------------
// Public API
// ---------------------------------------------------------------------------

// Call once from setup().
void spoof_gate_init();

// Feed a raw LoRa rx_buf of length len.  The first byte is msg_type (0x11).
// Silently ignores malformed or undersized packets.
// Thread-safety: single-threaded ESP32 main loop assumed.
void spoof_gate_handle_packet(const uint8_t* buf, size_t len);

// Look up the most recent spoof score for track_id.
// Returns 0 if the track is not cached or if its entry has expired.
uint8_t spoof_gate_score_for_track(uint32_t track_id);

// Returns true if the cached spoof score for track_id >= threshold.
// Returns false when the track is unknown (score = 0).
bool spoof_gate_should_promote(uint32_t track_id, uint8_t threshold);

#endif // SPOOF_GATE_CLIENT_H
