#include "string.h" #include "freertos/FreeRTOS.h" #include "freertos/timers.h" #include "esp_log.h" #include "driver/gpio.h" #include "nvs_flash.h" #include "main.h" #include "pumps.h" #define TAG "PUMP!" uint8_t running = 0; TimerHandle_t pump_timers[PUMPS]; static uint8_t pumps_duration[PUMPS] = {0}; static uint8_t pumps_enabled[PUMPS] = {0}; static uint8_t pumps_running[PUMPS] = {0}; static uint8_t safety = 1; void pumps_update_config() { ESP_LOGI(TAG, "writing config"); size_t size = sizeof(uint8_t) * PUMPS; nvs_set_blob(config_handle, "pumps_duration", &pumps_duration, size); nvs_commit(config_handle); } uint8_t pumps_set_duration(uint8_t idx, uint8_t time) { if(idx > PUMPS) return PUMPS_ERR_OUT_IDX; ESP_LOGI(TAG, "duration update: %d = %d", idx, time); pumps_duration[idx] = time; pumps_update_config(); return 0; } uint8_t pumps_get_duration(uint8_t idx) { return pumps_duration[idx]; } uint8_t pumps_set_enabled(uint8_t idx, uint8_t value) { uint8_t io = pump_gpio_map[idx]; value = (value ? 1 : 0); ESP_LOGD(TAG, "gpio: %d value: %d", io, value); // invert IO if(safety) gpio_set_level(io, value); return pumps_enabled[idx] = value; } uint8_t pumps_get_enabled(uint8_t idx) { return pumps_enabled[idx] ? 1 : 0; } uint8_t pumps_get_running(uint8_t idx) { return pumps_running[idx]; } uint8_t pump_enable(int8_t i) { ESP_LOGI(TAG, "pump: %d enabled", i); return gpio_set_level(pump_gpio_map[i], 0); } uint8_t pump_disable(int8_t i) { ESP_LOGI(TAG, "pump: %d disabled", i); return gpio_set_level(pump_gpio_map[i], 0); } void pump_timer_done(TimerHandle_t timer) { uint8_t idx = (pcTimerGetName(timer) - 0x48); ESP_LOGD(TAG, "pump done: %d", idx); running--; pumps_set_enabled(idx, 0); } void pumps_stop() { for(uint8_t i = 0; i < PUMPS; i++) { if(pump_timers[i] != NULL) { pump_disable(i); xTimerStop(pump_timers[i], 0); i++; } } } void pumps_run() { if(running > 0) return; for(uint8_t i = 0; i < PUMPS; i++) { if(pumps_duration[i] == 0) continue; running++; pump_timers[i] = xTimerCreate((const char *)(0x48 + i), (pumps_duration[i] * 1000 / portTICK_PERIOD_MS), pdFALSE, (void*)0, pump_timer_done); xTimerStart(pump_timers[i], 0); pumps_set_enabled(i, 1); } } uint8_t pumps_init() { gpio_config_t io_conf; // put the output high before initializing // to prevent relays from clacking for(uint8_t i = 0 ; i < 4; i++) { gpio_set_level(pump_gpio_map[i], 0); } io_conf.intr_type = GPIO_INTR_DISABLE; io_conf.mode = GPIO_MODE_OUTPUT; io_conf.pin_bit_mask = GPIO_PUMP_PIN_SEL; io_conf.pull_down_en = 1; io_conf.pull_up_en = 0; gpio_config(&io_conf); // zero out pump enabled, duration memset(&pumps_enabled, 0, sizeof(uint8_t) * PUMPS); memset(&pumps_duration, 5, sizeof(uint8_t) * PUMPS); size_t size = sizeof(uint8_t) * PUMPS; if(!nvs_get_blob(config_handle, "pumps_duration", &pumps_duration, &size)) { ESP_LOGI(TAG, "Initializing pumps config"); nvs_set_blob(config_handle, "pumps_duration", &pumps_duration, size); }; ESP_LOGI(TAG, "pumps_enabled: %d %d %d %d", pumps_enabled[0], pumps_enabled[1], pumps_enabled[2], pumps_enabled[3]); ESP_LOGI(TAG, "pumps_duration: %d %d %d %d", pumps_duration[0], pumps_duration[1], pumps_duration[2], pumps_duration[3]); return 0; }