#ifndef CHARGE_REGISTERS_H
#define CHARGE_REGISTERS_H

#include "charge_manager.h"

#define CHARGE_HUSB238_ADDR 0x08u
#define CHARGE_BQ25798_ADDR 0x6Bu

typedef struct {
    void *ctx;
    bool (*read)(void *ctx, uint8_t address7, uint8_t reg,
                 uint8_t *data, uint8_t length);
    bool (*write)(void *ctx, uint8_t address7, uint8_t reg,
                  const uint8_t *data, uint8_t length);
    /* enabled=true must pull the active-low BQ25798 CE pin low. */
    bool (*set_ce_enabled)(void *ctx, bool enabled);
    uint32_t (*millis)(void *ctx);
} charge_register_io;

typedef struct {
    charge_register_io io;
} charge_registers;

/* Call with the board's hardware CE pull-up already active. This keeps CE
 * disabled, makes watchdog expiry stop charging, and enables continuous VBUS
 * ADC. Readbacks are checked before initialization is accepted. */
bool charge_registers_init(charge_registers *device,
                           const charge_register_io *io);

/* Reads HUSB238 source state and BQ status/fault/ADC registers into a single
 * observation. Bus failures are represented by the observation's *_ok flags
 * so charge_manager_step() will fail closed. */
bool charge_registers_observe(charge_registers *device,
                              charge_observation *observation);

/* Kick the 40-second BQ watchdog. Schedule at <=10-second intervals while the
 * application is alive; any failure must disable charging and report a fault. */
bool charge_registers_kick_watchdog(charge_registers *device);

/* Provides the HAL callbacks expected by charge_manager_step(). */
charge_hal charge_registers_make_hal(charge_registers *device);

#endif
