#pragma once

#include <map>
#include <string>
#include <vector>

namespace fgc {

// Structured decode of a firmware DUMP block (the text between "DUMP BEGIN" and
// "DUMP END"). Mirrors firmware/tools/decode_dump.py, which is authoritative for
// the on-wire field names and the TMC status-register bit tables.

struct DumpAxis {
    char        axis = '?';           // 'Y' (yaw) / 'P' (pitch)
    std::string state_name = "?";     // BOOT/RESET/HOMING/READY/ERROR
    bool        enabled = false;
    bool        eeprom_restored = false;
    bool        has_encoder = false;
    long        lim_neg = 0;
    long        lim_pos = 0;
    long        hold_target = 0;
    long        speed = 0;
    int         hsub = 0;

    // Raw register hex strings as received, keyed by name (GCONF, DRV_STATUS...).
    std::map<std::string, std::string> regs;

    // Decoded status registers + their set-bit names.
    unsigned                 drv_status = 0;
    unsigned                 gstat = 0;
    unsigned                 ramp_stat = 0;
    int                      cs_actual = 0;   // (DRV_STATUS >> 16) & 0x1F
    int                      sg_result = 0;   //  DRV_STATUS        & 0x3FF
    std::vector<std::string> drv_flags;
    std::vector<std::string> gstat_flags;
    std::vector<std::string> ramp_flags;
};

struct DumpData {
    bool                     valid = false;
    std::string              build;
    long                     uptime_ms = 0;
    unsigned                 mcusr = 0;
    long                     free_ram = 0;
    std::vector<std::string> reset_flags;
    std::vector<DumpAxis>    axes;
};

// Parse a raw DUMP block. Returns {valid=false} for empty/malformed input (no
// "DUMP BEGIN .. DUMP END" pair).
DumpData parseDump(const std::string& block);

// Human-readable lines for a decoded dump (console-reusable pretty print).
std::vector<std::string> formatDump(const DumpData& d);

}  // namespace fgc
