#include "dcdc_controller.h" #include "driver/gpio.h" #include "esp_log.h" #include "sdkconfig.h" static const char *TAG = "dcdc"; #ifndef CONFIG_WATCH_DCDC_EN_GPIO_0 #define CONFIG_WATCH_DCDC_EN_GPIO_0 2 #endif #ifndef CONFIG_WATCH_DCDC_EN_GPIO_1 #define CONFIG_WATCH_DCDC_EN_GPIO_1 4 #endif #ifndef CONFIG_WATCH_DCDC_EN_GPIO_2 #define CONFIG_WATCH_DCDC_EN_GPIO_2 5 #endif #ifndef CONFIG_WATCH_DCDC_EN_GPIO_3 #define CONFIG_WATCH_DCDC_EN_GPIO_3 18 #endif #ifndef CONFIG_WATCH_DCDC_EN_GPIO_4 #define CONFIG_WATCH_DCDC_EN_GPIO_4 19 #endif static const gpio_num_t s_dcdc_gpio_map[DCDC_CHANNEL_COUNT] = { (gpio_num_t)CONFIG_WATCH_DCDC_EN_GPIO_0, (gpio_num_t)CONFIG_WATCH_DCDC_EN_GPIO_1, (gpio_num_t)CONFIG_WATCH_DCDC_EN_GPIO_2, (gpio_num_t)CONFIG_WATCH_DCDC_EN_GPIO_3, (gpio_num_t)CONFIG_WATCH_DCDC_EN_GPIO_4, }; static bool s_initialized; static bool s_channel_state[DCDC_CHANNEL_COUNT]; static bool dcdc_is_channel_valid(dcdc_channel_t channel) { return channel >= DCDC_CHANNEL_0 && channel < DCDC_CHANNEL_COUNT; } esp_err_t dcdc_init(void) { if (s_initialized) { return ESP_OK; } gpio_config_t cfg = { .intr_type = GPIO_INTR_DISABLE, .mode = GPIO_MODE_OUTPUT, .pull_down_en = GPIO_PULLDOWN_DISABLE, .pull_up_en = GPIO_PULLUP_DISABLE, .pin_bit_mask = 0, }; for (int i = 0; i < DCDC_CHANNEL_COUNT; ++i) { cfg.pin_bit_mask = 1ULL << s_dcdc_gpio_map[i]; esp_err_t err = gpio_config(&cfg); if (err != ESP_OK) { ESP_LOGE(TAG, "Не вдалося налаштувати GPIO %d (канал %d): %s", (int)s_dcdc_gpio_map[i], i, esp_err_to_name(err)); return err; } ESP_ERROR_CHECK_WITHOUT_ABORT(gpio_set_level(s_dcdc_gpio_map[i], 0)); s_channel_state[i] = false; } s_initialized = true; ESP_LOGI(TAG, "DCDC контролер ініціалізовано, каналів: %d", DCDC_CHANNEL_COUNT); return ESP_OK; } esp_err_t dcdc_set_state(dcdc_channel_t channel, bool enabled) { if (!dcdc_is_channel_valid(channel)) { return ESP_ERR_INVALID_ARG; } esp_err_t err = gpio_set_level(s_dcdc_gpio_map[channel], enabled ? 1 : 0); if (err == ESP_OK) { s_channel_state[channel] = enabled; ESP_LOGI(TAG, "Канал %d -> %s", channel, enabled ? "ON" : "OFF"); } return err; } esp_err_t dcdc_enable(dcdc_channel_t channel) { return dcdc_set_state(channel, true); } esp_err_t dcdc_disable(dcdc_channel_t channel) { return dcdc_set_state(channel, false); } esp_err_t dcdc_toggle(dcdc_channel_t channel) { if (!dcdc_is_channel_valid(channel)) { return ESP_ERR_INVALID_ARG; } return dcdc_set_state(channel, !s_channel_state[channel]); } bool dcdc_get_state(dcdc_channel_t channel) { if (!dcdc_is_channel_valid(channel)) { return false; } return s_channel_state[channel]; } size_t dcdc_channel_count(void) { return DCDC_CHANNEL_COUNT; } gpio_num_t dcdc_get_gpio(dcdc_channel_t channel) { if (!dcdc_is_channel_valid(channel)) { return GPIO_NUM_NC; } return s_dcdc_gpio_map[channel]; }