gpio: update config to use only one gpio for ATX PSU
All checks were successful
Build ESP32 BMC Firmware / build (push) Successful in 59s

This commit is contained in:
2026-03-12 15:28:20 +01:00
parent c6f4d26c58
commit ccf4569969
6 changed files with 25 additions and 143 deletions

View File

@@ -47,7 +47,7 @@
// ============================================================================
// Number of user-configurable GPIOs
#define BMC_GPIO_COUNT 16
#define BMC_GPIO_COUNT 1
// GPIO pin definitions with names and default modes
typedef struct {
@@ -60,54 +60,18 @@ typedef struct {
} bmc_gpio_def_t;
// Predefined GPIO assignments
#define BMC_GPIO_POWER_ON GPIO_NUM_4
#define BMC_GPIO_POWER_OFF GPIO_NUM_5
#define BMC_GPIO_RESET GPIO_NUM_6
#define BMC_GPIO_STATUS_LED GPIO_NUM_7
#define BMC_GPIO_PWR_GOOD GPIO_NUM_15
#define BMC_GPIO_TEMP_ALERT GPIO_NUM_16
#define BMC_GPIO_FAN_CTRL GPIO_NUM_17
#define BMC_GPIO_USER_1 GPIO_NUM_18
#define BMC_GPIO_USER_2 GPIO_NUM_21
#define BMC_GPIO_USER_3 GPIO_NUM_35
#define BMC_GPIO_USER_4 GPIO_NUM_36
#define BMC_GPIO_USER_5 GPIO_NUM_37
#define BMC_GPIO_USER_6 GPIO_NUM_38
#define BMC_GPIO_USER_7 GPIO_NUM_47
#define BMC_GPIO_USER_8 GPIO_NUM_48
#define BMC_GPIO_POWER GPIO_NUM_37
// Default GPIO configuration table
static const bmc_gpio_def_t bmc_gpio_defaults[BMC_GPIO_COUNT] = {
// Power control outputs
{ BMC_GPIO_POWER_ON, "POWER_ON", GPIO_MODE_OUTPUT, 0, false, false},
{ BMC_GPIO_POWER_OFF, "POWER_OFF", GPIO_MODE_OUTPUT, 0, false, false},
{ BMC_GPIO_RESET, "RESET", GPIO_MODE_OUTPUT, 0, true, false}, // Active-low reset
{BMC_GPIO_STATUS_LED, "STATUS_LED", GPIO_MODE_OUTPUT, 0, false, false},
// Status inputs
{ BMC_GPIO_PWR_GOOD, "PWR_GOOD", GPIO_MODE_INPUT, 0, false, false},
{BMC_GPIO_TEMP_ALERT, "TEMP_ALERT", GPIO_MODE_INPUT, 0, true, false}, // Active-low alert
// PWM output
{ BMC_GPIO_FAN_CTRL, "FAN_CTRL", GPIO_MODE_OUTPUT, 0, false, false},
// User-configurable GPIOs
{ BMC_GPIO_USER_1, "USER_1", GPIO_MODE_INPUT, 0, false, false},
{ BMC_GPIO_USER_2, "USER_2", GPIO_MODE_INPUT, 0, false, false},
{ BMC_GPIO_USER_3, "USER_3", GPIO_MODE_INPUT, 0, false, false},
{ BMC_GPIO_USER_4, "USER_4", GPIO_MODE_INPUT, 0, false, false},
{ BMC_GPIO_USER_5, "USER_5", GPIO_MODE_INPUT, 0, false, true}, // Input-only on ESP32-S3
{ BMC_GPIO_USER_6, "USER_6", GPIO_MODE_INPUT, 0, false, true}, // Input-only on ESP32-S3
{ BMC_GPIO_USER_7, "USER_7", GPIO_MODE_INPUT, 0, false, true}, // Input-only on ESP32-S3
{ BMC_GPIO_USER_8, "USER_8", GPIO_MODE_INPUT, 0, false, true}, // Input-only on ESP32-S3
{BMC_GPIO_POWER, "POWER", GPIO_MODE_OUTPUT, 1 /* AC power ON */, true, false},
};
// ============================================================================
// Power Control Timing
// ============================================================================
#define BMC_POWER_ON_PULSE_MS 100
#define BMC_POWER_OFF_PULSE_MS 5000
#define BMC_RESET_PULSE_MS 100
#define BMC_RESET_PULSE_MS 200
#define BMC_POWER_GOOD_DELAY_MS 2000
// ============================================================================

View File

@@ -218,61 +218,29 @@ esp_err_t gpio_toggle(gpio_num_t pin) {
esp_err_t gpio_power_on(void) {
ESP_LOGI(TAG, "Power ON sequence initiated");
// Pulse the POWER_ON signal
gpio_write(BMC_GPIO_POWER_ON, 1);
vTaskDelay(pdMS_TO_TICKS(BMC_POWER_ON_PULSE_MS));
gpio_write(BMC_GPIO_POWER_ON, 0);
// Wait for power good signal
vTaskDelay(pdMS_TO_TICKS(BMC_POWER_GOOD_DELAY_MS));
if (gpio_is_power_good()) {
ESP_LOGI(TAG, "Power ON successful - power good detected");
gpio_set_status_led(true);
return ESP_OK;
} else {
ESP_LOGW(TAG, "Power ON completed - no power good signal");
return ESP_OK; // Still return OK, just no confirmation
}
gpio_write(BMC_GPIO_POWER, 1);
return ESP_OK;
}
esp_err_t gpio_power_off(void) {
ESP_LOGI(TAG, "Power OFF sequence initiated");
// Pulse the POWER_OFF signal
gpio_write(BMC_GPIO_POWER_OFF, 1);
vTaskDelay(pdMS_TO_TICKS(BMC_POWER_OFF_PULSE_MS));
gpio_write(BMC_GPIO_POWER_OFF, 0);
gpio_set_status_led(false);
ESP_LOGI(TAG, "Power OFF completed");
gpio_write(BMC_GPIO_POWER, 0);
return ESP_OK;
}
esp_err_t gpio_reset(void) {
ESP_LOGI(TAG, "Reset sequence initiated");
// Pulse the RESET signal (active-low)
gpio_write(BMC_GPIO_RESET, 0); // Assert reset (active-low)
// Pulse the POWER signal
gpio_write(BMC_GPIO_POWER, 0);
vTaskDelay(pdMS_TO_TICKS(BMC_RESET_PULSE_MS));
gpio_write(BMC_GPIO_RESET, 1); // De-assert reset
gpio_write(BMC_GPIO_POWER, 1);
ESP_LOGI(TAG, "Reset completed");
return ESP_OK;
}
bool gpio_is_power_good(void) {
int idx = gpio_find_index(BMC_GPIO_PWR_GOOD);
if (idx < 0) {
return false;
}
int level = gpio_get_level(BMC_GPIO_PWR_GOOD);
bool gpio_power_status(void) {
int level = gpio_get_level(BMC_GPIO_POWER);
return (level == 1);
}
esp_err_t gpio_set_status_led(bool on) {
return gpio_write(BMC_GPIO_STATUS_LED, on ? 1 : 0);
}

View File

@@ -131,18 +131,10 @@ esp_err_t gpio_power_off(void);
esp_err_t gpio_reset(void);
/**
* @brief Check if power is good
* @brief Check if power is on or off
*
* @return true if power good signal is high, false otherwise
* @return true if power signal is high, false otherwise
*/
bool gpio_is_power_good(void);
/**
* @brief Set status LED state
*
* @param on true to turn on, false to turn off
* @return ESP_OK on success, error code otherwise
*/
esp_err_t gpio_set_status_led(bool on);
bool gpio_power_status(void);
#endif // GPIO_CONTROLLER_H

View File

@@ -17,12 +17,10 @@ static void eth_event_callback(eth_event_type_t event) {
switch (event) {
case ETH_EVENT_CONNECTED:
ESP_LOGI(TAG, "Ethernet connected");
gpio_set_status_led(true);
break;
case ETH_EVENT_DISCONNECTED:
ESP_LOGW(TAG, "Ethernet disconnected");
gpio_set_status_led(false);
break;
case ETH_EVENT_GOT_IP: {
@@ -51,9 +49,6 @@ void app_main(void) {
// Continue anyway - some GPIOs might still work
}
// Set status LED to indicate initialization
gpio_set_status_led(false);
// Initialize UART handler
ESP_LOGI(TAG, "Initializing UART handler...");
ret = uart_handler_init();
@@ -119,20 +114,5 @@ void app_main(void) {
ESP_LOGI(TAG, "Web interface: http://%s/", ip);
ESP_LOGI(TAG, "========================================");
// Main loop - monitor system health
while (1) {
// Update status LED based on connection state
if (ethernet_is_connected()) {
gpio_set_status_led(true);
} else {
// Blink LED if not connected
gpio_set_status_led(false);
vTaskDelay(pdMS_TO_TICKS(500));
gpio_set_status_led(true);
vTaskDelay(pdMS_TO_TICKS(500));
gpio_set_status_led(false);
}
vTaskDelay(pdMS_TO_TICKS(5000));
}
return;
}

View File

@@ -258,24 +258,7 @@ static esp_err_t api_gpio_config_handler(httpd_req_t *req) {
static esp_err_t api_power_status_handler(httpd_req_t *req) {
cJSON *status = cJSON_CreateObject();
cJSON_AddBoolToObject(status, "power_good", gpio_is_power_good());
// Get power control GPIO states
int power_on_idx = gpio_find_index(BMC_GPIO_POWER_ON);
int power_off_idx = gpio_find_index(BMC_GPIO_POWER_OFF);
if (power_on_idx >= 0) {
bmc_gpio_state_t state;
gpio_get_state(BMC_GPIO_POWER_ON, &state);
cJSON_AddNumberToObject(status, "power_on_state", state.value);
}
if (power_off_idx >= 0) {
bmc_gpio_state_t state;
gpio_get_state(BMC_GPIO_POWER_OFF, &state);
cJSON_AddNumberToObject(status, "power_off_state", state.value);
}
cJSON_AddStringToObject(status, "power_status", gpio_power_status() ? "on" : "off");
return send_json_success(req, status);
}
@@ -287,7 +270,7 @@ static esp_err_t api_power_on_handler(httpd_req_t *req) {
cJSON *response = cJSON_CreateObject();
cJSON_AddStringToObject(response, "message", "Power on sequence initiated");
cJSON_AddBoolToObject(response, "power_good", gpio_is_power_good());
cJSON_AddStringToObject(response, "power_status", "on");
return send_json_success(req, response);
}
@@ -300,6 +283,7 @@ static esp_err_t api_power_off_handler(httpd_req_t *req) {
cJSON *response = cJSON_CreateObject();
cJSON_AddStringToObject(response, "message", "Power off sequence initiated");
cJSON_AddStringToObject(response, "power_status", "off");
return send_json_success(req, response);
}
@@ -312,6 +296,7 @@ static esp_err_t api_power_reset_handler(httpd_req_t *req) {
cJSON *response = cJSON_CreateObject();
cJSON_AddStringToObject(response, "message", "Reset sequence initiated");
cJSON_AddStringToObject(response, "power_status", "on");
return send_json_success(req, response);
}
@@ -484,7 +469,7 @@ static esp_err_t api_system_status_handler(httpd_req_t *req) {
// Power status
cJSON *power = cJSON_CreateObject();
cJSON_AddBoolToObject(power, "power_good", gpio_is_power_good());
cJSON_AddBoolToObject(power, "power_status", gpio_power_status());
cJSON_AddItemToObject(status, "power", power);
// Network status
@@ -918,8 +903,9 @@ esp_err_t web_server_ws_broadcast(const uint8_t *data, size_t len) {
// Get client list - httpd has its own internal locking
esp_err_t ret = httpd_get_client_list(server, &clients, client_fds);
if (ret != ESP_OK) {
ESP_LOGW(TAG, "Failed to get client list: %s", esp_err_to_name(ret));
return ret;
// This can happen when there are no clients or server is busy - not a critical error
ESP_LOGD(TAG, "Could not get client list: %s (may be no clients connected)", esp_err_to_name(ret));
return ESP_OK; // Return OK since this is not a critical error
}
// Count and send to all WebSocket clients