/**
 * @file switch_debouncer.c
 * @brief Implementierung des EPB-Schalter-Debouncers.
 *
 * @arch SWA-006
 * @reqs SWE-025
 *
 * ASIL: QM.
 */
#include "switch_debouncer.h"

typedef struct {
    SwitchState current;
    SwitchState candidate;
    uint8_t     candidate_count;
} DebouncerCtx;

static DebouncerCtx s_ctx;

static SwitchState raw_to_candidate(SwitchRaw raw)
{
    if (raw.apply_raw && !raw.release_raw) {
        return SWITCH_APPLY;
    }
    if (raw.release_raw && !raw.apply_raw) {
        return SWITCH_RELEASE;
    }
    return SWITCH_NEUTRAL;
}

EpbStatus switch_init(void)
{
    s_ctx.current = SWITCH_NEUTRAL;
    s_ctx.candidate = SWITCH_NEUTRAL;
    s_ctx.candidate_count = 0U;
    return EPB_OK;
}

void switch_step_10ms(SwitchRaw raw)
{
    const SwitchState observed = raw_to_candidate(raw);

    if (observed == s_ctx.candidate) {
        if (s_ctx.candidate_count < SWITCH_DEBOUNCE_SAMPLES) {
            ++s_ctx.candidate_count;
        }
    } else {
        s_ctx.candidate = observed;
        s_ctx.candidate_count = 1U;
    }

    if (s_ctx.candidate_count >= SWITCH_DEBOUNCE_SAMPLES) {
        s_ctx.current = s_ctx.candidate;
    }
}

SwitchState switch_get_state(void)
{
    return s_ctx.current;
}
