From 941a2b4eaa63ec14c6cf258d41d5c4f3362ed8b6 Mon Sep 17 00:00:00 2001 From: Emanuele Trabattoni Date: Sat, 4 Apr 2026 03:11:44 +0200 Subject: [PATCH 1/7] debug testing commit --- RotaxMonitor/.vscode/extensions.json | 4 +- RotaxMonitor/boards/esp32-s3-n16r8.json | 4 +- RotaxMonitor/platformio.ini | 64 +++++++------------- RotaxMonitor/src/isr.cpp | 2 +- RotaxMonitor/src/isr.h | 24 ++++---- RotaxMonitor/src/main.cpp | 79 +++++++++++++------------ RotaxMonitor/src/pins.h | 10 ++-- RotaxMonitor/src/tasks.cpp | 63 ++++++++++---------- RotaxMonitor/src/tasks.h | 2 +- RotaxMonitorTester/src/main.cpp | 20 ++++++- RotaxMonitorTester/src/pins.h | 1 + 11 files changed, 138 insertions(+), 135 deletions(-) diff --git a/RotaxMonitor/.vscode/extensions.json b/RotaxMonitor/.vscode/extensions.json index 080e70d..411655e 100644 --- a/RotaxMonitor/.vscode/extensions.json +++ b/RotaxMonitor/.vscode/extensions.json @@ -1,7 +1,7 @@ { - // See http://go.microsoft.com/fwlink/?LinkId=827846 - // for the documentation about the extensions.json format "recommendations": [ + "Jason2866.esp-decoder", + "pioarduino.pioarduino-ide", "platformio.platformio-ide" ], "unwantedRecommendations": [ diff --git a/RotaxMonitor/boards/esp32-s3-n16r8.json b/RotaxMonitor/boards/esp32-s3-n16r8.json index c0612bf..65002da 100644 --- a/RotaxMonitor/boards/esp32-s3-n16r8.json +++ b/RotaxMonitor/boards/esp32-s3-n16r8.json @@ -11,8 +11,8 @@ "-DARDUINO_RUNNING_CORE=1", "-DARDUINO_EVENT_RUNNING_CORE=1", "-DBOARD_HAS_PSRAM", - "-DARDUINO_USB_MODE=1", - "-DARDUINO_USB_CDC_ON_BOOT=0" + "-DARDUINO_USB_MODE=0", + "-DARDUINO_USB_CDC_ON_BOOT=1" ], "f_cpu": "240000000L", "f_flash": "80000000L", diff --git a/RotaxMonitor/platformio.ini b/RotaxMonitor/platformio.ini index 63497eb..fafe8ac 100644 --- a/RotaxMonitor/platformio.ini +++ b/RotaxMonitor/platformio.ini @@ -8,9 +8,9 @@ ; Please visit documentation for the other options and examples ; https://docs.platformio.org/page/projectconf.html -[env:esp32-s3-n16r8] -board = esp32-s3-n16r8 -platform = https://github.com/pioarduino/platform-espressif32/releases/download/55.03.37/platform-espressif32.zip +[env:esp32-s3-devkitc1-n16r8] +board = esp32-s3-devkitc1-n16r8 +platform = https://github.com/pioarduino/platform-espressif32/releases/download/stable/platform-espressif32.zip framework = arduino lib_deps = hideakitai/DebugLog@^0.8.4 @@ -18,51 +18,29 @@ lib_deps = hideakitai/PCA95x5@^0.1.3 adafruit/Adafruit SSD1306@^2.5.16 garfius/Menu-UI@^1.2.0 -board_build.partitions = partitions/default_16MB.csv -board_build.psram = enabled monitor_speed = 115200 upload_speed = 921600 build_type = release -[env:esp32-s3-n16r8-debug] -board = ${env:esp32-s3-n16r8.board} -platform = ${env:esp32-s3-n16r8.platform} -framework = ${env:esp32-s3-n16r8.framework} -lib_deps = ${env:esp32-s3-n16r8.lib_deps} -board_build.partitions = partitions/default_16MB.csv -board_build.psram = enabled +[env:esp32-s3-devkitc1-n16r8-debug] +board = ${env:esp32-s3-devkitc1-n16r8.board} +platform = ${env:esp32-s3-devkitc1-n16r8.platform} +framework = ${env:esp32-s3-devkitc1-n16r8.framework} +lib_deps = ${env:esp32-s3-devkitc1-n16r8.lib_deps} + +build_type = debug + monitor_speed = 115200 upload_speed = 921600 -build_type = debug -build_flags = - -O0 - -g3 - -ggdb - -fno-inline - -fno-ipa-sra - -fno-tree-sra - -fno-builtin +debug_tool = esp-builtin +debug_speed = 15000 -[env:esp32-devtest-debug] -board = esp32dev -platform = https://github.com/pioarduino/platform-espressif32/releases/download/55.03.37/platform-espressif32.zip -framework = arduino -lib_deps = - hideakitai/DebugLog@^0.8.4 - bblanchon/ArduinoJson@^7.4.2 - hideakitai/PCA95x5@^0.1.3 - adafruit/Adafruit SSD1306@^2.5.16 - garfius/Menu-UI@^1.2.0 -board_build.flash_size = 4MB -board_build.partitions = default.csv -monitor_speed = 115200 -build_type = debug -build_flags = - -O0 - -g3 - -ggdb - -fno-inline - -fno-ipa-sra - -fno-tree-sra - -fno-builtin +build_flags = + -O0 + -g3 + -ggdb3 + -fno-inline + -DCORE_DEBUG_LEVEL=5 + -DARDUINO_USB_CDC_ON_BOOT=0 + -fstack-protector-all diff --git a/RotaxMonitor/src/isr.cpp b/RotaxMonitor/src/isr.cpp index 64c479e..e3d1c6d 100644 --- a/RotaxMonitor/src/isr.cpp +++ b/RotaxMonitor/src/isr.cpp @@ -17,7 +17,7 @@ void trig_isr(void *arg) BaseType_t xHigherPriorityTaskWoken = pdFALSE; isrParams *params = (isrParams *)arg; ignitionBoxStatus *box = params->ign_stat; - TaskHandle_t task_handle = *params->rt_handle_ptr; + TaskHandle_t task_handle = params->rt_handle_ptr; // exit if task not running if (!task_handle) diff --git a/RotaxMonitor/src/isr.h b/RotaxMonitor/src/isr.h index 0dad9f9..56080fe 100644 --- a/RotaxMonitor/src/isr.h +++ b/RotaxMonitor/src/isr.h @@ -1,7 +1,7 @@ #pragma once // Test device Flag -#define TEST +// #define TEST // Arduino Libraries #include @@ -20,14 +20,14 @@ // ===================== // Event Flags (bitmask) // ===================== -#define TRIG_FLAG_12P (1 << 0) -#define TRIG_FLAG_12N (1 << 2) -#define TRIG_FLAG_34P (1 << 1) -#define TRIG_FLAG_34N (1 << 3) +static const uint32_t TRIG_FLAG_12P = (1 << 0); +static const uint32_t TRIG_FLAG_12N = (1 << 1); +static const uint32_t TRIG_FLAG_34P = (1 << 2); +static const uint32_t TRIG_FLAG_34N = (1 << 3); -#define SPARK_FLAG_NIL (1 << 8) -#define SPARK_FLAG_12 (1 << 9) -#define SPARK_FLAG_34 (1 << 10) +static const uint32_t SPARK_FLAG_NIL = (1 << 8); +static const uint32_t SPARK_FLAG_12 = (1 << 9); +static const uint32_t SPARK_FLAG_34 = (1 << 10); // Spark Status enum sparkStatus @@ -75,11 +75,11 @@ struct ignitionBoxStatus float volts_gen = 0.0; }; -struct isrParams { +struct isrParams +{ const uint32_t flag; - ignitionBoxStatus* ign_stat; - TaskHandle_t* rt_handle_ptr; + ignitionBoxStatus *ign_stat; + TaskHandle_t rt_handle_ptr; }; - void IRAM_ATTR trig_isr(void *arg); diff --git a/RotaxMonitor/src/main.cpp b/RotaxMonitor/src/main.cpp index 6001f01..6ab2d20 100644 --- a/RotaxMonitor/src/main.cpp +++ b/RotaxMonitor/src/main.cpp @@ -12,6 +12,9 @@ #include #include +// #define CH_B_ENABLE +#define TEST + void printTaskList() { char buffer[1024]; @@ -51,15 +54,15 @@ void loop() { // global variables bool running = true; - Devices dev; + static Devices dev; // Task handle - TaskHandle_t trigA_TaskHandle = NULL; - TaskHandle_t trigB_TaskHandle = NULL; + static TaskHandle_t trigA_TaskHandle = NULL; + static TaskHandle_t trigB_TaskHandle = NULL; - QueueHandle_t rt_taskA_queue = xQueueCreate(10, sizeof(ignitionBoxStatus)); - QueueHandle_t rt_taskB_queue = xQueueCreate(10, sizeof(ignitionBoxStatus)); - rtTaskParams taskA_params{ + static QueueHandle_t rt_taskA_queue = xQueueCreate(10, sizeof(ignitionBoxStatus)); + static QueueHandle_t rt_taskB_queue = xQueueCreate(10, sizeof(ignitionBoxStatus)); + static rtTaskParams taskA_params{ .rt_running = true, .dev = &dev, .rt_handle_ptr = &trigA_TaskHandle, @@ -75,13 +78,14 @@ void loop() .rt_resets = rtTaskResets{.rst_io_12p = RST_EXT_A12P, .rst_io_12n = RST_EXT_A12N, .rst_io_34p = RST_EXT_A34P, .rst_io_34n = RST_EXT_A34N}}; LOG_INFO("Task Variables OK"); -#ifndef TEST + +#ifdef CH_B_ENABLE QueueHandle_t rt_taskB_queue = xQueueCreate(10, sizeof(ignitionBoxStatus)); rtTaskParams taskB_params{ .rt_running = true, .dev = &dev, - .rt_queue = rt_taskB_queue, .rt_handle_ptr = &trigB_TaskHandle, + .rt_queue = rt_taskB_queue, .rt_int = rtTaskInterrupts{ .isr_ptr = trig_isr, .trig_pin_12p = TRIG_PIN_B12P, @@ -95,6 +99,7 @@ void loop() bool spiA_ok = true; bool spiB_ok = true; + #ifndef TEST // Init 2 SPI interfaces SPIClass SPI_A(FSPI); @@ -102,6 +107,7 @@ void loop() SPIClass SPI_B(HSPI); spiB_ok = SPI_B.begin(SPI_B_SCK, SPI_B_MISO, SPI_B_MOSI); #endif + if (!spiA_ok || !spiB_ok) { LOG_ERROR("Unable to Initialize SPI Busses"); @@ -140,7 +146,7 @@ void loop() // Ignition B on Core 1 auto ignB_task_success = pdPASS; -#ifndef TEST +#ifdef CH_B_ENABLE ignB_task_success = xTaskCreatePinnedToCore( rtIgnitionTask, "rtIgnitionTask_boxB", @@ -171,40 +177,37 @@ void loop() ignitionBoxStatus ignA; if (xQueueReceive(rt_taskA_queue, &ignA, pdMS_TO_TICKS(100)) == pdTRUE) { - printField("++ Timestamp", (uint32_t)ignA.timestamp, 0, 0); - if (firstRun) - Serial.println("========== Coils 12 ============="); - printField("Pickup Tim", (uint32_t)ignA.coils12.trig_time, 0, 1); - printField("Spark Tim", (uint32_t)ignA.coils12.spark_time, 0, 2); - printField("Spark Dly", (uint32_t)ignA.coils12.spark_delay, 0, 3); - printField("Spark Sts", (uint32_t)ignA.coils12.spark_status, 0, 4); - printField("Peak P_IN", ignA.coils12.peak_p_in, 0, 5); - printField("Peak P_OUT", ignA.coils12.peak_p_out, 0, 6); - printField("Peak N_IN", ignA.coils12.peak_n_in, 0, 7); - printField("Peak N_OUT", ignA.coils12.peak_n_out, 0, 8); - printField("SoftStart ", (uint32_t)ignA.coils12.sstart_status, 0, 9); - if (firstRun) - Serial.println("========== Coils 34 ============="); - printField("Pickup Tim", (uint32_t)ignA.coils34.trig_time, 0, 11); - printField("Spark Tim", (uint32_t)ignA.coils34.spark_time, 0, 12); - printField("Spark Dly", (uint32_t)ignA.coils34.spark_delay, 0, 13); - printField("Spark Sts", (uint32_t)ignA.coils34.spark_delay, 0, 14); - printField("Peak P_IN", ignA.coils34.peak_p_in, 0, 15); - printField("Peak P_OUT", ignA.coils34.peak_p_out, 0, 16); - printField("Peak N_IN", ignA.coils34.peak_n_in, 0, 17); - printField("Peak N_OUT", ignA.coils34.peak_n_out, 0, 18); - printField("SoftStart ", (uint32_t)ignA.coils34.sstart_status, 0, 19); - if (firstRun) - Serial.println("========== END ============="); - if (count++ % 10 == 0) + if (count++ % 10000 == 0) { firstRun = true; clearScreen(); setCursor(0, 0); - } - else + printField("++ Timestamp", (uint32_t)ignA.timestamp, 0, 0); + Serial.println("========== Coils 12 ============="); + printField("Pickup Tim", (uint32_t)ignA.coils12.trig_time, 0, 1); + printField("Spark Tim", (uint32_t)ignA.coils12.spark_time, 0, 2); + printField("Spark Dly", (uint32_t)ignA.coils12.spark_delay, 0, 3); + printField("Spark Sts", (uint32_t)ignA.coils12.spark_status, 0, 4); + printField("Peak P_IN", ignA.coils12.peak_p_in, 0, 5); + printField("Peak P_OUT", ignA.coils12.peak_p_out, 0, 6); + printField("Peak N_IN", ignA.coils12.peak_n_in, 0, 7); + printField("Peak N_OUT", ignA.coils12.peak_n_out, 0, 8); + printField("SoftStart ", (uint32_t)ignA.coils12.sstart_status, 0, 9); - firstRun = false; + Serial.println("========== Coils 34 ============="); + printField("Pickup Tim", (uint32_t)ignA.coils34.trig_time, 0, 11); + printField("Spark Tim", (uint32_t)ignA.coils34.spark_time, 0, 12); + printField("Spark Dly", (uint32_t)ignA.coils34.spark_delay, 0, 13); + printField("Spark Sts", (uint32_t)ignA.coils34.spark_delay, 0, 14); + printField("Peak P_IN", ignA.coils34.peak_p_in, 0, 15); + printField("Peak P_OUT", ignA.coils34.peak_p_out, 0, 16); + printField("Peak N_IN", ignA.coils34.peak_n_in, 0, 17); + printField("Peak N_OUT", ignA.coils34.peak_n_out, 0, 18); + printField("SoftStart ", (uint32_t)ignA.coils34.sstart_status, 0, 19); + + Serial.println("========== END ============="); + count = 0; + } } } diff --git a/RotaxMonitor/src/pins.h b/RotaxMonitor/src/pins.h index de0bec2..6e4958d 100644 --- a/RotaxMonitor/src/pins.h +++ b/RotaxMonitor/src/pins.h @@ -67,8 +67,8 @@ // ===================== #define TRIG_PIN_A12P 18 #define TRIG_PIN_A12N 21 -#define TRIG_PIN_A34P 33 -#define TRIG_PIN_A34N 34 +#define TRIG_PIN_A34P 38 // ATTENZIONEEEEEEEEEEE +#define TRIG_PIN_A34N 39 // ATTENZIONEEEEEEEEEEE #define TRIG_PIN_B12P 38 #define TRIG_PIN_B12N 39 #define TRIG_PIN_B34P 40 @@ -78,9 +78,9 @@ // SPARK DETECT INPUTS // ===================== #define SPARK_PIN_A12 42 -#define SPARK_PIN_A34 45 // OK (strapping ma consentito) -#define SPARK_PIN_B12 46 // OK (strapping ma consentito) -#define SPARK_PIN_B34 47 +#define SPARK_PIN_A34 42 // OK (strapping ma consentito) 45 +#define SPARK_PIN_B12 42 // OK (strapping ma consentito) 46 +#define SPARK_PIN_B34 42 // ===================== // PCA9555 (I2C EXPANDER) diff --git a/RotaxMonitor/src/tasks.cpp b/RotaxMonitor/src/tasks.cpp index 7e8349b..d81d715 100644 --- a/RotaxMonitor/src/tasks.cpp +++ b/RotaxMonitor/src/tasks.cpp @@ -16,13 +16,14 @@ void rtIgnitionTask(void *pvParameters) const rtTaskInterrupts rt_int = params->rt_int; // copy to avoid external override const rtTaskResets rt_rst = params->rt_resets; // copy to avoid external override QueueHandle_t rt_queue = params->rt_queue; - TaskHandle_t *rt_handle_ptr = params->rt_handle_ptr; + TaskHandle_t rt_handle_ptr = *params->rt_handle_ptr; Devices *dev = params->dev; ADS1256 *adc = dev->adc_a; PCA9555 *io = dev->io; + static ignitionBoxStatus ign_box_sts; + // Variables for ISR, static to be fixed in memory locations - static ignitionBoxStatus ign_box_sts; // common for all ISR calls static isrParams isr_params_t12p{ .flag = TRIG_FLAG_12P, .ign_stat = &ign_box_sts, @@ -47,7 +48,7 @@ void rtIgnitionTask(void *pvParameters) .flag = SPARK_FLAG_34, .ign_stat = &ign_box_sts, .rt_handle_ptr = rt_handle_ptr}; - + LOG_INFO("rtTask ISR Params OK"); pinMode(POT_A_CS, OUTPUT); @@ -80,19 +81,20 @@ void rtIgnitionTask(void *pvParameters) // WAIT FOR PICKUP SIGNAL xTaskNotifyWait( - ULONG_MAX, // non pulire all'ingresso + 0x00, // non pulire all'ingresso ULONG_MAX, // pulisci i primi 8 bit &pickup_flag, // valore ricevuto portMAX_DELAY); #ifdef DEBUG - LOG_INFO("Iteration [", it++, "]"); Serial.print("\033[2J"); // clear screen Serial.print("\033[H"); // cursor home - LOG_INFO("Pickup Flags: ", printBits(pickup_flag).c_str()); + LOG_INFO("Iteration [", it++, "]"); + if (!names.contains(pickup_flag)) { LOG_ERROR("Wrong Pickup Flag"); + LOG_ERROR("Pickup Flags: ", printBits(pickup_flag).c_str()); continue; } else @@ -106,18 +108,17 @@ void rtIgnitionTask(void *pvParameters) if (ign_box_sts.coils12.spark_ok || ign_box_sts.coils34.spark_ok) // otherwise timeout if none is set in the ISR spark_flag = ign_box_sts.coils12.spark_ok ? SPARK_FLAG_12 : SPARK_FLAG_34; else - spark_flag == SPARK_FLAG_NIL; - - xTaskNotifyStateClear(NULL); - ulTaskNotifyValueClear(NULL, 0xFFFFFFFF); + spark_flag = SPARK_FLAG_NIL; #ifdef DEBUG - LOG_INFO("Spark Flags: ", printBits(spark_flag).c_str()); - if (!names.contains(spark_flag)) - LOG_ERROR("No Spark"); - else + // LOG_INFO("Spark Flags: ", printBits(spark_flag).c_str()); + LOG_INFO("Spark12:", ign_box_sts.coils12.spark_ok ? "TRUE" : "FALSE"); + LOG_INFO("Spark34:", ign_box_sts.coils34.spark_ok ? "TRUE" : "FALSE"); + if (names.contains(spark_flag)) LOG_INFO("Spark Trigger:", names.at(spark_flag)); #endif + xTaskNotifyStateClear(NULL); + ulTaskNotifyValueClear(NULL, 0xFFFFFFFF); // A trigger from pickup 12 is followed by a spark event on 34 or vice versa pickup 34 triggers spark on 12 if ((pickup_flag == TRIG_FLAG_12P || pickup_flag == TRIG_FLAG_12N) && spark_flag != SPARK_FLAG_12) @@ -147,15 +148,16 @@ void rtIgnitionTask(void *pvParameters) case TRIG_FLAG_12P: case TRIG_FLAG_34P: { + LOG_INFO("POSITIVE Edge"); // Timeout not occourred, expected POSITIVE edge spark OCCOURRED if (spark_flag != SPARK_FLAG_NIL) { - coils->spark_delay = coils->spark_time - coils->trig_time; + coils->spark_delay = coils->trig_time - coils->spark_time; coils->sstart_status = softStartStatus::NORMAL; // because spark on positive edge coils->spark_status = sparkStatus::SPARK_POS_OK; // do not wait for spark on negative edge #ifdef DEBUG - LOG_INFO("Trigger Spark POSITIVE"); - LOG_INFO("Spark12 Delay Timer: ", (int)coils->spark_delay); + LOG_INFO("Spark on POSITIVE pulse"); + LOG_INFO("Spark Delay Timer: ", (int32_t)coils->spark_delay); #endif } // Timeout occourred, expected POSITIVE edge spark NOT OCCOURRED @@ -164,33 +166,34 @@ void rtIgnitionTask(void *pvParameters) coils->spark_status = sparkStatus::SPARK_NEG_WAIT; coils->sstart_status = softStartStatus::NORMAL; } - new_data = true; + new_data = false; break; // Do nothing more on positive pulse } // CASES for NEGATIVE cycle triggering of pickup and sparks 12 & 34 case TRIG_FLAG_12N: case TRIG_FLAG_34N: { - const bool expected_negative12 = coils->spark_status == sparkStatus::SPARK_NEG_WAIT; + LOG_INFO("NEGATIVE Edge"); + const bool expected_negative = coils->spark_status == sparkStatus::SPARK_NEG_WAIT; // Timeout not occourred, expected NEGATIVE edge spark OCCOURRED - if (spark_flag != SPARK_FLAG_NIL && expected_negative12) + if (spark_flag != SPARK_FLAG_NIL && expected_negative) { - coils->spark_delay = coils->spark_time - coils->trig_time; + coils->spark_delay = coils->trig_time - coils->spark_time; coils->sstart_status = softStartStatus::SOFT_START; coils->spark_status == sparkStatus::SPARK_NEG_OK; #ifdef DEBUG - LOG_INFO("Trigger Spark NEGATIVE"); - LOG_INFO("Spark12 Delay Timer: ", (int)ign_box_sts.coils12.spark_delay); + LOG_INFO("Spark on NEGATIVE pulse"); + LOG_INFO("Spark Delay Timer: ", (int32_t)coils->spark_delay); #endif } // Timeout occourred, expected POSITIVE edge spark NOT OCCOURRED - else if (spark_flag == SPARK_FLAG_NIL && expected_negative12) + else if (spark_flag == SPARK_FLAG_NIL && expected_negative) { coils->sstart_status = softStartStatus::NORMAL; coils->spark_status = sparkStatus::SPARK_NEG_FAIL; } // Timeout not occouured, unexpected negative edge spark - else if (spark_flag != SPARK_FLAG_NIL && !expected_negative12) + else if (spark_flag != SPARK_FLAG_NIL && !expected_negative) { coils->sstart_status = softStartStatus::SOFT_START; coils->spark_status = sparkStatus::SPARK_NEG_UNEXPECTED; @@ -210,8 +213,8 @@ void rtIgnitionTask(void *pvParameters) if (new_data) { - vTaskDelay(pdMS_TO_TICKS(1)); // delay 1ms to allow peak detectors to charge for negative cycle - // read adc channels: pickup12, out12 [ pos + neg ] + // vTaskDelay(pdMS_TO_TICKS(1)); // delay 1ms to allow peak detectors to charge for negative cycle + // read adc channels: pickup12, out12 [ pos + neg ] if (adc) // read only if adc initialized { // from peak detector circuits @@ -225,7 +228,7 @@ void rtIgnitionTask(void *pvParameters) ign_box_sts.coils34.peak_n_out = adcReadChannel(adc, ADC_CH_PEAK_34N_OUT); } else // simulate adc read timig - vTaskDelay(pdMS_TO_TICKS(6)); + vTaskDelay(pdMS_TO_TICKS(1)); // reset peak detectors + sample and hold // outputs on io expander @@ -237,7 +240,7 @@ void rtIgnitionTask(void *pvParameters) io->write(iostat & ~rst_bitmask); } else - vTaskDelay(pdMS_TO_TICKS(2)); + vTaskDelay(pdMS_TO_TICKS(1)); // send essage to main loop with ignition info, by copy so local static variable is ok if (rt_queue) @@ -245,7 +248,7 @@ void rtIgnitionTask(void *pvParameters) if (xQueueSendToBack(rt_queue, (void *)&ign_box_sts, pdMS_TO_TICKS(1)) != pdPASS) { q_fail_count++; - LOG_ERROR("Failed to send to rt_queue"); + // LOG_ERROR("Failed to send to rt_queue"); } } } diff --git a/RotaxMonitor/src/tasks.h b/RotaxMonitor/src/tasks.h index d10b840..36d83f9 100644 --- a/RotaxMonitor/src/tasks.h +++ b/RotaxMonitor/src/tasks.h @@ -2,7 +2,7 @@ #define DEBUGLOG_DEFAULT_LOG_LEVEL_DEBUG // Serial debug flag -// #define DEBUG +#define DEBUG // Arduino Libraries #include diff --git a/RotaxMonitorTester/src/main.cpp b/RotaxMonitorTester/src/main.cpp index 1985d2f..20230a6 100644 --- a/RotaxMonitorTester/src/main.cpp +++ b/RotaxMonitorTester/src/main.cpp @@ -15,6 +15,17 @@ static uint32_t count = 0; #define SPARK_DLY_MIN 10 #define SPARK_DLY_MAX 490 +#define PAUSE_LONG_MIN 10000 +#define PAUSE_LONG_MAX PAUSE_LONG_MIN*100 + +void clearScreen(){ + Serial.print("\033[2J"); // clear screen + Serial.print("\033[H"); // cursor home + Serial.flush(); +} + +static double filtered = 0; + static const std::map pin2Name = { {PIN_TRIG_A12P, "HIGH_PIN_TRIG_A12P"}, {~PIN_TRIG_A12P, "LOW_PIN_TRIG_A12P"}, @@ -81,6 +92,13 @@ void loop() } else { stsA.soft_start = false; } + + double new_val = (float)(map(analogRead(FREQ_POT), 0, 4096, PAUSE_LONG_MIN, PAUSE_LONG_MAX)); + filtered = filtered + 0.1 * (new_val - filtered); + stsA.pause_long_us = (uint32_t)filtered; LOG_INFO("Spark Delay uS: ", stsA.spark_delay_us, "\tSoft Start: ", stsA.soft_start ? "TRUE" : "FALSE"); - delay(500); + LOG_INFO("Pause: ", (uint32_t)(stsA.pause_long_us / 1000), "ms"); + + delay(100); + clearScreen(); } diff --git a/RotaxMonitorTester/src/pins.h b/RotaxMonitorTester/src/pins.h index a0b8c36..14591da 100644 --- a/RotaxMonitorTester/src/pins.h +++ b/RotaxMonitorTester/src/pins.h @@ -20,3 +20,4 @@ // Pot #define SPARK_DELAY_POT 12 +#define FREQ_POT 14 From 0dc5d1ce79c87037722d521857bef1071775fc10 Mon Sep 17 00:00:00 2001 From: Emanuele Trabattoni Date: Sat, 4 Apr 2026 03:25:33 +0200 Subject: [PATCH 2/7] Debug Config OK, ready to realtime debugging --- RotaxMonitor/platformio.ini | 35 +++++++++++++++++++++++++---------- RotaxMonitor/src/main.cpp | 2 +- 2 files changed, 26 insertions(+), 11 deletions(-) diff --git a/RotaxMonitor/platformio.ini b/RotaxMonitor/platformio.ini index fafe8ac..8dbfd44 100644 --- a/RotaxMonitor/platformio.ini +++ b/RotaxMonitor/platformio.ini @@ -18,9 +18,18 @@ lib_deps = hideakitai/PCA95x5@^0.1.3 adafruit/Adafruit SSD1306@^2.5.16 garfius/Menu-UI@^1.2.0 -monitor_speed = 115200 + +;Upload protocol configuration +upload_protocol = esptool +upload_port = /dev/ttyACM1 upload_speed = 921600 -build_type = release + +;Monitor configuration +monitor_speed = 115200 +monitor_port = /dev/ttyACM1 + +; Build configuration +build_type = debug [env:esp32-s3-devkitc1-n16r8-debug] board = ${env:esp32-s3-devkitc1-n16r8.board} @@ -28,19 +37,25 @@ platform = ${env:esp32-s3-devkitc1-n16r8.platform} framework = ${env:esp32-s3-devkitc1-n16r8.framework} lib_deps = ${env:esp32-s3-devkitc1-n16r8.lib_deps} -build_type = debug - -monitor_speed = 115200 +;Upload protocol configuration +upload_protocol = esptool +upload_port = /dev/ttyACM1 upload_speed = 921600 +;Monitor configuration +monitor_speed = 115200 +monitor_port = /dev/ttyACM1 + +; Debug configuration debug_tool = esp-builtin debug_speed = 15000 -build_flags = +; Build configuration +build_type = debug +build_flags = -O0 -g3 -ggdb3 - -fno-inline - -DCORE_DEBUG_LEVEL=5 - -DARDUINO_USB_CDC_ON_BOOT=0 - -fstack-protector-all + -DCORE_DEBUG_LEVEL=5 + -DARDUINO_USB_CDC_ON_BOOT=0 + -fstack-protector-all diff --git a/RotaxMonitor/src/main.cpp b/RotaxMonitor/src/main.cpp index 6ab2d20..2b20cb5 100644 --- a/RotaxMonitor/src/main.cpp +++ b/RotaxMonitor/src/main.cpp @@ -25,8 +25,8 @@ void printTaskList() void setup() { - delay(250); Serial.begin(115200); + delay(250); // Setup Logger LOG_ATTACH_SERIAL(Serial); From b0842aadef32c0ddadeafdf185b3b2cd1c3f2c51 Mon Sep 17 00:00:00 2001 From: Emanuele Trabattoni Date: Sat, 4 Apr 2026 16:27:52 +0200 Subject: [PATCH 3/7] Sync 12 and 34 working --- RotaxMonitor/platformio.ini | 9 +++++---- RotaxMonitor/src/isr.cpp | 40 ++++++++++++++++++++++++++----------- RotaxMonitor/src/isr.h | 20 +++++++++++++++++++ RotaxMonitor/src/main.cpp | 10 +++++----- RotaxMonitor/src/pins.h | 14 ++++++------- RotaxMonitor/src/tasks.cpp | 26 ++++++++++++++---------- RotaxMonitor/src/tasks.h | 4 ++-- RotaxMonitor/src/ui.h | 11 ++++++++++ 8 files changed, 93 insertions(+), 41 deletions(-) diff --git a/RotaxMonitor/platformio.ini b/RotaxMonitor/platformio.ini index 8dbfd44..88ee606 100644 --- a/RotaxMonitor/platformio.ini +++ b/RotaxMonitor/platformio.ini @@ -21,12 +21,12 @@ lib_deps = ;Upload protocol configuration upload_protocol = esptool -upload_port = /dev/ttyACM1 +upload_port = /dev/ttyACM2 upload_speed = 921600 ;Monitor configuration monitor_speed = 115200 -monitor_port = /dev/ttyACM1 +monitor_port = /dev/ttyACM2 ; Build configuration build_type = debug @@ -39,12 +39,12 @@ lib_deps = ${env:esp32-s3-devkitc1-n16r8.lib_deps} ;Upload protocol configuration upload_protocol = esptool -upload_port = /dev/ttyACM1 +upload_port = /dev/ttyACM2 upload_speed = 921600 ;Monitor configuration monitor_speed = 115200 -monitor_port = /dev/ttyACM1 +monitor_port = /dev/ttyACM2 ; Debug configuration debug_tool = esp-builtin @@ -58,4 +58,5 @@ build_flags = -ggdb3 -DCORE_DEBUG_LEVEL=5 -DARDUINO_USB_CDC_ON_BOOT=0 + -DARDUINO_USB_MODE=0 -fstack-protector-all diff --git a/RotaxMonitor/src/isr.cpp b/RotaxMonitor/src/isr.cpp index e3d1c6d..0c62ab5 100644 --- a/RotaxMonitor/src/isr.cpp +++ b/RotaxMonitor/src/isr.cpp @@ -7,12 +7,11 @@ void trig_isr(void *arg) { const int64_t time_us = esp_timer_get_time(); + static uint8_t isr_firing_count = 0; // exit if invalid args if (!arg) return; - // FOR TESTING ONLY - digitalWrite(POT_A_CS, HIGH); BaseType_t xHigherPriorityTaskWoken = pdFALSE; isrParams *params = (isrParams *)arg; @@ -23,37 +22,54 @@ void trig_isr(void *arg) if (!task_handle) return; - // reset spark flags, cannot be same time as trigger flags - box->coils12.spark_ok = false; - box->coils34.spark_ok = false; - switch (params->flag) { case TRIG_FLAG_12P: case TRIG_FLAG_12N: - box->coils12.trig_time = time_us; - xTaskNotifyFromISR(task_handle, params->flag, eSetValueWithOverwrite, &xHigherPriorityTaskWoken); + //if (isr_firing_count == 0) + { + // only on first trigger to avoid multiple firing due to noise, to be fixed with hardware debounce + isr_firing_count++; + box->coils12.spark_ok = false; // reset spark ok flag on new trigger event + box->coils12.trig_time = time_us; + xTaskNotifyFromISR(task_handle, params->flag, eSetValueWithOverwrite, &xHigherPriorityTaskWoken); + } break; + case TRIG_FLAG_34P: case TRIG_FLAG_34N: - box->coils34.trig_time = time_us; - xTaskNotifyFromISR(task_handle, params->flag, eSetValueWithOverwrite, &xHigherPriorityTaskWoken); + //if (isr_firing_count == 0) + { + // only on first trigger to avoid multiple firing due to noise, to be fixed with hardware debounce + isr_firing_count++; + box->coils34.spark_ok = false; // reset spark ok flag on new trigger event + box->coils34.trig_time = time_us; + xTaskNotifyFromISR(task_handle, params->flag, eSetValueWithOverwrite, &xHigherPriorityTaskWoken); + } break; case SPARK_FLAG_12: + //if (isr_firing_count > 0) // only consider spark if a trigger has been detected, otherwise noise on spark pin can cause false positives + { + box->coils34.spark_ok = false; box->coils12.spark_ok = true; box->coils12.spark_time = time_us; + isr_firing_count = 0; // reset trigger timeout counter on spark event vTaskNotifyGiveFromISR(task_handle, &xHigherPriorityTaskWoken); + } break; case SPARK_FLAG_34: + //if (isr_firing_count > 0) // only consider spark if a trigger has been detected, otherwise noise on spark pin can cause false positives + { + box->coils12.spark_ok = false; box->coils34.spark_ok = true; box->coils34.spark_time = time_us; + isr_firing_count = 0; // reset trigger timeout counter on spark event vTaskNotifyGiveFromISR(task_handle, &xHigherPriorityTaskWoken); + } break; default: break; } - // FOR TESTING ONLY - digitalWrite(POT_A_CS, LOW); if (xHigherPriorityTaskWoken) portYIELD_FROM_ISR(); diff --git a/RotaxMonitor/src/isr.h b/RotaxMonitor/src/isr.h index 56080fe..0b1bb8a 100644 --- a/RotaxMonitor/src/isr.h +++ b/RotaxMonitor/src/isr.h @@ -6,6 +6,7 @@ // Arduino Libraries #include #include "soc/gpio_struct.h" +#include #ifndef TEST #include "pins.h" #else @@ -45,12 +46,31 @@ enum sparkStatus SPARK_SYNC_FAIL, }; +static const std::map sparkStatusNames = { + {SPARK_POS_OK, "SPARK_POS_OK"}, + {SPARK_NEG_OK, "SPARK_NEG_OK"}, + {SPARK_POS_SKIP, "SPARK_POS_SKIP"}, + {SPARK_NEG_SKIP, "SPARK_NEG_SKIP"}, + {SPARK_POS_WAIT, "SPARK_POS_WAIT"}, + {SPARK_NEG_WAIT, "SPARK_NEG_WAIT"}, + {SPARK_POS_FAIL, "SPARK_POS_FAIL"}, + {SPARK_NEG_FAIL, "SPARK_NEG_FAIL"}, + {SPARK_POS_UNEXPECTED, "SPARK_POS_UNEXPECTED"}, + {SPARK_NEG_UNEXPECTED, "SPARK_NEG_UNEXPECTED"}, + {SPARK_SYNC_FAIL, "SPARK_SYNC_FAIL"}, +}; + enum softStartStatus { NORMAL, SOFT_START }; +const std::map softStartStatusNames = { + {NORMAL, "NORMAL"}, + {SOFT_START, "SOFT_START"}, +}; + struct coilsStatus { int64_t trig_time; diff --git a/RotaxMonitor/src/main.cpp b/RotaxMonitor/src/main.cpp index 2b20cb5..5686de3 100644 --- a/RotaxMonitor/src/main.cpp +++ b/RotaxMonitor/src/main.cpp @@ -25,7 +25,7 @@ void printTaskList() void setup() { - Serial.begin(115200); + Serial.begin(921600); delay(250); // Setup Logger @@ -187,23 +187,23 @@ void loop() printField("Pickup Tim", (uint32_t)ignA.coils12.trig_time, 0, 1); printField("Spark Tim", (uint32_t)ignA.coils12.spark_time, 0, 2); printField("Spark Dly", (uint32_t)ignA.coils12.spark_delay, 0, 3); - printField("Spark Sts", (uint32_t)ignA.coils12.spark_status, 0, 4); + printField("Spark Sts", sparkStatusNames.at(ignA.coils12.spark_status), 0, 4); printField("Peak P_IN", ignA.coils12.peak_p_in, 0, 5); printField("Peak P_OUT", ignA.coils12.peak_p_out, 0, 6); printField("Peak N_IN", ignA.coils12.peak_n_in, 0, 7); printField("Peak N_OUT", ignA.coils12.peak_n_out, 0, 8); - printField("SoftStart ", (uint32_t)ignA.coils12.sstart_status, 0, 9); + printField("SoftStart ", softStartStatusNames.at(ignA.coils12.sstart_status), 0, 9); Serial.println("========== Coils 34 ============="); printField("Pickup Tim", (uint32_t)ignA.coils34.trig_time, 0, 11); printField("Spark Tim", (uint32_t)ignA.coils34.spark_time, 0, 12); printField("Spark Dly", (uint32_t)ignA.coils34.spark_delay, 0, 13); - printField("Spark Sts", (uint32_t)ignA.coils34.spark_delay, 0, 14); + printField("Spark Sts", sparkStatusNames.at(ignA.coils34.spark_status), 0, 14); printField("Peak P_IN", ignA.coils34.peak_p_in, 0, 15); printField("Peak P_OUT", ignA.coils34.peak_p_out, 0, 16); printField("Peak N_IN", ignA.coils34.peak_n_in, 0, 17); printField("Peak N_OUT", ignA.coils34.peak_n_out, 0, 18); - printField("SoftStart ", (uint32_t)ignA.coils34.sstart_status, 0, 19); + printField("SoftStart ", softStartStatusNames.at(ignA.coils34.sstart_status), 0, 19); Serial.println("========== END ============="); count = 0; diff --git a/RotaxMonitor/src/pins.h b/RotaxMonitor/src/pins.h index 6e4958d..a818b89 100644 --- a/RotaxMonitor/src/pins.h +++ b/RotaxMonitor/src/pins.h @@ -59,16 +59,16 @@ // ===================== // DIGITAL POT // ===================== -#define POT_A_CS 1 -#define POT_B_CS 2 +//#define POT_A_CS 1 +//#define POT_B_CS 2 // ===================== // TRIGGER INPUT INTERRUPTS // ===================== #define TRIG_PIN_A12P 18 #define TRIG_PIN_A12N 21 -#define TRIG_PIN_A34P 38 // ATTENZIONEEEEEEEEEEE -#define TRIG_PIN_A34N 39 // ATTENZIONEEEEEEEEEEE +#define TRIG_PIN_A34P 1 +#define TRIG_PIN_A34N 2 #define TRIG_PIN_B12P 38 #define TRIG_PIN_B12N 39 #define TRIG_PIN_B34P 40 @@ -78,9 +78,9 @@ // SPARK DETECT INPUTS // ===================== #define SPARK_PIN_A12 42 -#define SPARK_PIN_A34 42 // OK (strapping ma consentito) 45 -#define SPARK_PIN_B12 42 // OK (strapping ma consentito) 46 -#define SPARK_PIN_B34 42 +#define SPARK_PIN_A34 45 // OK (strapping ma consentito) 45 +#define SPARK_PIN_B12 46 // OK (strapping ma consentito) 46 +#define SPARK_PIN_B34 47 // ===================== // PCA9555 (I2C EXPANDER) diff --git a/RotaxMonitor/src/tasks.cpp b/RotaxMonitor/src/tasks.cpp index d81d715..7b6f2d9 100644 --- a/RotaxMonitor/src/tasks.cpp +++ b/RotaxMonitor/src/tasks.cpp @@ -51,8 +51,6 @@ void rtIgnitionTask(void *pvParameters) LOG_INFO("rtTask ISR Params OK"); - pinMode(POT_A_CS, OUTPUT); - // Attach Pin Interrupts attachInterruptArg(digitalPinToInterrupt(rt_int.trig_pin_12p), rt_int.isr_ptr, (void *)&isr_params_t12p, RISING); attachInterruptArg(digitalPinToInterrupt(rt_int.trig_pin_12n), rt_int.isr_ptr, (void *)&isr_params_t12n, RISING); @@ -73,6 +71,7 @@ void rtIgnitionTask(void *pvParameters) // Global rt_task_ptr variables uint32_t it = 0; uint32_t q_fail_count = 0; + bool first_cycle = true; while (params->rt_running) { @@ -85,6 +84,11 @@ void rtIgnitionTask(void *pvParameters) ULONG_MAX, // pulisci i primi 8 bit &pickup_flag, // valore ricevuto portMAX_DELAY); + + if (first_cycle && pickup_flag != TRIG_FLAG_12P) // skip first cycle because of possible initial noise on pickup signals at startu + { + continue; + } #ifdef DEBUG Serial.print("\033[2J"); // clear screen @@ -105,6 +109,7 @@ void rtIgnitionTask(void *pvParameters) // WAIT FOR SPARK TO HAPPEN auto spark_timeout = ulTaskNotifyTake(pdTRUE, pdMS_TO_TICKS(spark_timeout_max)); + //auto spark_timeout = ulTaskNotifyTake(pdTRUE, portMAX_DELAY); if (ign_box_sts.coils12.spark_ok || ign_box_sts.coils34.spark_ok) // otherwise timeout if none is set in the ISR spark_flag = ign_box_sts.coils12.spark_ok ? SPARK_FLAG_12 : SPARK_FLAG_34; else @@ -121,7 +126,7 @@ void rtIgnitionTask(void *pvParameters) ulTaskNotifyValueClear(NULL, 0xFFFFFFFF); // A trigger from pickup 12 is followed by a spark event on 34 or vice versa pickup 34 triggers spark on 12 - if ((pickup_flag == TRIG_FLAG_12P || pickup_flag == TRIG_FLAG_12N) && spark_flag != SPARK_FLAG_12) + if ((pickup_flag == TRIG_FLAG_12P || pickup_flag == TRIG_FLAG_12N) && (spark_flag != SPARK_FLAG_12 && spark_flag != SPARK_FLAG_NIL)) { ign_box_sts.coils12.spark_status = ign_box_sts.coils34.spark_status = sparkStatus::SPARK_SYNC_FAIL; // Save error on circular buffer and skip to next cycle // @@ -133,6 +138,7 @@ void rtIgnitionTask(void *pvParameters) switch (pickup_flag) { case TRIG_FLAG_12P: + first_cycle = false; case TRIG_FLAG_12N: coils = &ign_box_sts.coils12; break; @@ -148,16 +154,15 @@ void rtIgnitionTask(void *pvParameters) case TRIG_FLAG_12P: case TRIG_FLAG_34P: { - LOG_INFO("POSITIVE Edge"); // Timeout not occourred, expected POSITIVE edge spark OCCOURRED if (spark_flag != SPARK_FLAG_NIL) { - coils->spark_delay = coils->trig_time - coils->spark_time; + coils->spark_delay = coils->spark_time - coils->trig_time; coils->sstart_status = softStartStatus::NORMAL; // because spark on positive edge coils->spark_status = sparkStatus::SPARK_POS_OK; // do not wait for spark on negative edge #ifdef DEBUG LOG_INFO("Spark on POSITIVE pulse"); - LOG_INFO("Spark Delay Timer: ", (int32_t)coils->spark_delay); + LOG_INFO("Spark Delay Time: ", (int32_t)coils->spark_delay); #endif } // Timeout occourred, expected POSITIVE edge spark NOT OCCOURRED @@ -173,17 +178,16 @@ void rtIgnitionTask(void *pvParameters) case TRIG_FLAG_12N: case TRIG_FLAG_34N: { - LOG_INFO("NEGATIVE Edge"); const bool expected_negative = coils->spark_status == sparkStatus::SPARK_NEG_WAIT; // Timeout not occourred, expected NEGATIVE edge spark OCCOURRED if (spark_flag != SPARK_FLAG_NIL && expected_negative) { - coils->spark_delay = coils->trig_time - coils->spark_time; + coils->spark_delay = coils->spark_time - coils->trig_time; coils->sstart_status = softStartStatus::SOFT_START; - coils->spark_status == sparkStatus::SPARK_NEG_OK; + coils->spark_status = sparkStatus::SPARK_NEG_OK; #ifdef DEBUG LOG_INFO("Spark on NEGATIVE pulse"); - LOG_INFO("Spark Delay Timer: ", (int32_t)coils->spark_delay); + LOG_INFO("Spark Delay Time: ", (int32_t)coils->spark_delay); #endif } // Timeout occourred, expected POSITIVE edge spark NOT OCCOURRED @@ -248,7 +252,7 @@ void rtIgnitionTask(void *pvParameters) if (xQueueSendToBack(rt_queue, (void *)&ign_box_sts, pdMS_TO_TICKS(1)) != pdPASS) { q_fail_count++; - // LOG_ERROR("Failed to send to rt_queue"); + LOG_ERROR("Failed to send to rt_queue"); } } } diff --git a/RotaxMonitor/src/tasks.h b/RotaxMonitor/src/tasks.h index 36d83f9..1fde989 100644 --- a/RotaxMonitor/src/tasks.h +++ b/RotaxMonitor/src/tasks.h @@ -2,7 +2,7 @@ #define DEBUGLOG_DEFAULT_LOG_LEVEL_DEBUG // Serial debug flag -#define DEBUG +//#define DEBUG // Arduino Libraries #include @@ -16,7 +16,7 @@ #include "devices.h" // Global Variables and Flags -const uint8_t spark_timeout_max = 2; // in milliseconds +const uint8_t spark_timeout_max = 1; // in milliseconds // Debug Variables #ifdef DEBUG diff --git a/RotaxMonitor/src/ui.h b/RotaxMonitor/src/ui.h index bf7f793..a9f8c9f 100644 --- a/RotaxMonitor/src/ui.h +++ b/RotaxMonitor/src/ui.h @@ -45,4 +45,15 @@ void printField(const char name[], const float val, const uint8_t x, const uint8 setCursor(x+16, y); Serial.print(val); Serial.flush(); +} + +void printField(const char name[], const char *val, const uint8_t x, const uint8_t y) { + if (firstRun) { + setCursor(x,y); + Serial.printf("%15s: %s\n", name, val); + return; + } + setCursor(x+16, y); + Serial.print(val); + Serial.flush(); } \ No newline at end of file From 38c595fd7b4208ccdf64b4890e13b399457f5351 Mon Sep 17 00:00:00 2001 From: Emanuele Trabattoni Date: Sat, 4 Apr 2026 20:00:30 +0200 Subject: [PATCH 4/7] revert on double task wait, normal and soft start working --- RotaxMonitor/src/isr.cpp | 39 +++++------ RotaxMonitor/src/isr.h | 27 ++++---- RotaxMonitor/src/main.cpp | 76 +++++++++++++--------- RotaxMonitor/src/tasks.cpp | 53 +++++++++------ RotaxMonitorTester/.vscode/extensions.json | 4 +- RotaxMonitorTester/platformio.ini | 6 +- RotaxMonitorTester/src/main.cpp | 12 ++-- RotaxMonitorTester/src/pins.h | 2 +- 8 files changed, 128 insertions(+), 91 deletions(-) diff --git a/RotaxMonitor/src/isr.cpp b/RotaxMonitor/src/isr.cpp index 0c62ab5..622b339 100644 --- a/RotaxMonitor/src/isr.cpp +++ b/RotaxMonitor/src/isr.cpp @@ -26,7 +26,7 @@ void trig_isr(void *arg) { case TRIG_FLAG_12P: case TRIG_FLAG_12N: - //if (isr_firing_count == 0) + // if (isr_firing_count == 0) { // only on first trigger to avoid multiple firing due to noise, to be fixed with hardware debounce isr_firing_count++; @@ -35,10 +35,9 @@ void trig_isr(void *arg) xTaskNotifyFromISR(task_handle, params->flag, eSetValueWithOverwrite, &xHigherPriorityTaskWoken); } break; - case TRIG_FLAG_34P: case TRIG_FLAG_34N: - //if (isr_firing_count == 0) + // if (isr_firing_count == 0) { // only on first trigger to avoid multiple firing due to noise, to be fixed with hardware debounce isr_firing_count++; @@ -48,24 +47,26 @@ void trig_isr(void *arg) } break; case SPARK_FLAG_12: - //if (isr_firing_count > 0) // only consider spark if a trigger has been detected, otherwise noise on spark pin can cause false positives - { - box->coils34.spark_ok = false; - box->coils12.spark_ok = true; - box->coils12.spark_time = time_us; - isr_firing_count = 0; // reset trigger timeout counter on spark event - vTaskNotifyGiveFromISR(task_handle, &xHigherPriorityTaskWoken); - } + // if (isr_firing_count > 0) // only consider spark if a trigger has been detected, otherwise noise on spark pin can cause false positives + { + isr_firing_count = 0; // reset trigger timeout counter on spark event + box->coils34.spark_ok = false; + box->coils12.spark_ok = true; + box->coils12.spark_time = time_us; + xTaskNotifyFromISR(task_handle, params->flag, eSetValueWithOverwrite, &xHigherPriorityTaskWoken); + // vTaskNotifyGiveFromISR(task_handle, &xHigherPriorityTaskWoken); + } break; case SPARK_FLAG_34: - //if (isr_firing_count > 0) // only consider spark if a trigger has been detected, otherwise noise on spark pin can cause false positives - { - box->coils12.spark_ok = false; - box->coils34.spark_ok = true; - box->coils34.spark_time = time_us; - isr_firing_count = 0; // reset trigger timeout counter on spark event - vTaskNotifyGiveFromISR(task_handle, &xHigherPriorityTaskWoken); - } + // if (isr_firing_count > 0) // only consider spark if a trigger has been detected, otherwise noise on spark pin can cause false positives + { + isr_firing_count = 0; // reset trigger timeout counter on spark event + box->coils12.spark_ok = false; + box->coils34.spark_ok = true; + box->coils34.spark_time = time_us; + xTaskNotifyFromISR(task_handle, params->flag, eSetValueWithOverwrite, &xHigherPriorityTaskWoken); + // vTaskNotifyGiveFromISR(task_handle, &xHigherPriorityTaskWoken); + } break; default: break; diff --git a/RotaxMonitor/src/isr.h b/RotaxMonitor/src/isr.h index 0b1bb8a..f3c38c6 100644 --- a/RotaxMonitor/src/isr.h +++ b/RotaxMonitor/src/isr.h @@ -63,36 +63,41 @@ static const std::map sparkStatusNames = { enum softStartStatus { NORMAL, - SOFT_START + SOFT_START, + ERROR, }; const std::map softStartStatusNames = { {NORMAL, "NORMAL"}, {SOFT_START, "SOFT_START"}, + {ERROR, "ERROR"}, }; struct coilsStatus { - int64_t trig_time; - int64_t spark_time; - int64_t spark_delay; - sparkStatus spark_status; - softStartStatus sstart_status; - float peak_p_in, peak_n_in; - float peak_p_out, peak_n_out; - float trigger_spark; - bool spark_ok; + int64_t trig_time = 0; + int64_t spark_time = 0; + int64_t spark_delay = 0; // in microseconds + sparkStatus spark_status = sparkStatus::SPARK_POS_OK; + softStartStatus sstart_status = softStartStatus::NORMAL; + float peak_p_in = 0.0, peak_n_in = 0.0; + float peak_p_out = 0.0, peak_n_out = 0.0; + float trigger_spark = 0.0; + bool spark_ok = false; + uint32_t n_events = 0; + }; // Task internal Status struct ignitionBoxStatus { - int64_t timestamp; + int64_t timestamp = 0; // coils pairs for each ignition coilsStatus coils12; coilsStatus coils34; // voltage from generator float volts_gen = 0.0; + uint32_t n_queue_errors = 0; }; struct isrParams diff --git a/RotaxMonitor/src/main.cpp b/RotaxMonitor/src/main.cpp index 5686de3..714f204 100644 --- a/RotaxMonitor/src/main.cpp +++ b/RotaxMonitor/src/main.cpp @@ -168,46 +168,58 @@ void loop() LOG_INFO("Real Time Tasks A & B initialized"); ////////////////////// MAIN LOOP ////////////////////// - uint32_t count(0); clearScreen(); setCursor(0, 0); + ignitionBoxStatus ignA; + int64_t last = esp_timer_get_time(); + uint32_t missed_firings12 = 0; + uint32_t missed_firings34 = 0; while (running) { - ignitionBoxStatus ignA; - if (xQueueReceive(rt_taskA_queue, &ignA, pdMS_TO_TICKS(100)) == pdTRUE) + if (xQueueReceive(rt_taskA_queue, &ignA, pdMS_TO_TICKS(1000)) == pdTRUE) { - if (count++ % 10000 == 0) - { - firstRun = true; - clearScreen(); - setCursor(0, 0); - printField("++ Timestamp", (uint32_t)ignA.timestamp, 0, 0); - Serial.println("========== Coils 12 ============="); - printField("Pickup Tim", (uint32_t)ignA.coils12.trig_time, 0, 1); - printField("Spark Tim", (uint32_t)ignA.coils12.spark_time, 0, 2); - printField("Spark Dly", (uint32_t)ignA.coils12.spark_delay, 0, 3); - printField("Spark Sts", sparkStatusNames.at(ignA.coils12.spark_status), 0, 4); - printField("Peak P_IN", ignA.coils12.peak_p_in, 0, 5); - printField("Peak P_OUT", ignA.coils12.peak_p_out, 0, 6); - printField("Peak N_IN", ignA.coils12.peak_n_in, 0, 7); - printField("Peak N_OUT", ignA.coils12.peak_n_out, 0, 8); - printField("SoftStart ", softStartStatusNames.at(ignA.coils12.sstart_status), 0, 9); + if (ignA.coils12.spark_status == sparkStatus::SPARK_NEG_FAIL || ignA.coils12.spark_status == sparkStatus::SPARK_POS_FAIL) + missed_firings12++; + if (ignA.coils34.spark_status == sparkStatus::SPARK_POS_FAIL || ignA.coils34.spark_status == sparkStatus::SPARK_NEG_FAIL) + missed_firings34++; + clearScreen(); + setCursor(0, 0); + printField("++ Timestamp", (uint32_t)ignA.timestamp, 0, 0); + Serial.println("========== Coils 12 ============="); + printField("Events", (uint32_t)ignA.coils12.n_events, 0, 1); + printField("Missed Firing", missed_firings12, 0, 2); + printField("Spark Dly", (uint32_t)ignA.coils12.spark_delay, 0, 3); + printField("Spark Sts", sparkStatusNames.at(ignA.coils12.spark_status), 0, 4); + // printField("Peak P_IN", ignA.coils12.peak_p_in, 0, 5); + // printField("Peak P_OUT", ignA.coils12.peak_p_out, 0, 6); + // printField("Peak N_IN", ignA.coils12.peak_n_in, 0, 7); + // printField("Peak N_OUT", ignA.coils12.peak_n_out, 0, 8); + printField("Soft Start ", softStartStatusNames.at(ignA.coils12.sstart_status), 0, 9); - Serial.println("========== Coils 34 ============="); - printField("Pickup Tim", (uint32_t)ignA.coils34.trig_time, 0, 11); - printField("Spark Tim", (uint32_t)ignA.coils34.spark_time, 0, 12); - printField("Spark Dly", (uint32_t)ignA.coils34.spark_delay, 0, 13); - printField("Spark Sts", sparkStatusNames.at(ignA.coils34.spark_status), 0, 14); - printField("Peak P_IN", ignA.coils34.peak_p_in, 0, 15); - printField("Peak P_OUT", ignA.coils34.peak_p_out, 0, 16); - printField("Peak N_IN", ignA.coils34.peak_n_in, 0, 17); - printField("Peak N_OUT", ignA.coils34.peak_n_out, 0, 18); - printField("SoftStart ", softStartStatusNames.at(ignA.coils34.sstart_status), 0, 19); + Serial.println("========== Coils 34 ============="); + printField("Events", (uint32_t)ignA.coils34.n_events, 0, 11); + printField("Missed Firing", missed_firings34, 0, 12); + printField("Spark Dly", (uint32_t)ignA.coils34.spark_delay, 0, 13); + printField("Spark Sts", sparkStatusNames.at(ignA.coils34.spark_status), 0, 14); + // printField("Peak P_IN", ignA.coils34.peak_p_in, 0, 15); + // printField("Peak P_OUT", ignA.coils34.peak_p_out, 0, 16); + // printField("Peak N_IN", ignA.coils34.peak_n_in, 0, 17); + // printField("Peak N_OUT", ignA.coils34.peak_n_out, 0, 18); + printField("Soft Start ", softStartStatusNames.at(ignA.coils34.sstart_status), 0, 19); - Serial.println("========== END ============="); - count = 0; - } + Serial.println("========== END ============="); + Serial.println(); + auto delta = (esp_timer_get_time() - last) / 1000000.0f; //in seconds + delta = delta > 0 ? 1.0f / delta : 0; // Calculate frequency (Hz) + printField("Frequency (Hz)", delta, 0, 21); + printField("Queue Errors", (uint32_t)ignA.n_queue_errors, 0, 22); + last = esp_timer_get_time(); + } else + { + setCursor(0, 22); + Serial.print("Waiting for data... ");; + Serial.flush(); } } diff --git a/RotaxMonitor/src/tasks.cpp b/RotaxMonitor/src/tasks.cpp index 7b6f2d9..ba55408 100644 --- a/RotaxMonitor/src/tasks.cpp +++ b/RotaxMonitor/src/tasks.cpp @@ -21,7 +21,7 @@ void rtIgnitionTask(void *pvParameters) ADS1256 *adc = dev->adc_a; PCA9555 *io = dev->io; - static ignitionBoxStatus ign_box_sts; + ignitionBoxStatus ign_box_sts; // Variables for ISR, static to be fixed in memory locations static isrParams isr_params_t12p{ @@ -69,9 +69,9 @@ void rtIgnitionTask(void *pvParameters) LOG_WARN("rtTask Init Correct"); // Global rt_task_ptr variables - uint32_t it = 0; - uint32_t q_fail_count = 0; bool first_cycle = true; + bool cycle12 = false; + bool cycle34 = false; while (params->rt_running) { @@ -107,13 +107,26 @@ void rtIgnitionTask(void *pvParameters) } #endif - // WAIT FOR SPARK TO HAPPEN - auto spark_timeout = ulTaskNotifyTake(pdTRUE, pdMS_TO_TICKS(spark_timeout_max)); - //auto spark_timeout = ulTaskNotifyTake(pdTRUE, portMAX_DELAY); - if (ign_box_sts.coils12.spark_ok || ign_box_sts.coils34.spark_ok) // otherwise timeout if none is set in the ISR - spark_flag = ign_box_sts.coils12.spark_ok ? SPARK_FLAG_12 : SPARK_FLAG_34; - else + // WAIT FOR SPARK TO HAPPEN OR TIMEOUT + // auto spark_timeout = ulTaskNotifyTake(pdTRUE, pdMS_TO_TICKS(spark_timeout_max)); + // if (ign_box_sts.coils12.spark_ok || ign_box_sts.coils34.spark_ok) // otherwise timeout if none is set in the ISR + // spark_flag = ign_box_sts.coils12.spark_ok ? SPARK_FLAG_12 : SPARK_FLAG_34; + // else + // spark_flag = SPARK_FLAG_NIL; + + spark_flag = SPARK_FLAG_NIL; // default value in case of timeout, to be set by ISR if spark event occours + // WAIT FOR SPARK TO HAPPEN OR TIMEOUT + auto sp = xTaskNotifyWait( + 0x00, // non pulire all'ingresso + ULONG_MAX, // pulisci i primi 8 bit + &spark_flag, // valore ricevuto + pdMS_TO_TICKS(spark_timeout_max)); // wait for spark event or timeout + + // timeout occurred, set spark flag to nil + if (sp == pdFALSE) + { spark_flag = SPARK_FLAG_NIL; + } #ifdef DEBUG // LOG_INFO("Spark Flags: ", printBits(spark_flag).c_str()); @@ -129,8 +142,6 @@ void rtIgnitionTask(void *pvParameters) if ((pickup_flag == TRIG_FLAG_12P || pickup_flag == TRIG_FLAG_12N) && (spark_flag != SPARK_FLAG_12 && spark_flag != SPARK_FLAG_NIL)) { ign_box_sts.coils12.spark_status = ign_box_sts.coils34.spark_status = sparkStatus::SPARK_SYNC_FAIL; - // Save error on circular buffer and skip to next cycle // - LOG_ERROR("Spark Mismatch"); continue; } @@ -148,7 +159,6 @@ void rtIgnitionTask(void *pvParameters) break; } - bool new_data = false; switch (pickup_flag) { case TRIG_FLAG_12P: @@ -171,8 +181,7 @@ void rtIgnitionTask(void *pvParameters) coils->spark_status = sparkStatus::SPARK_NEG_WAIT; coils->sstart_status = softStartStatus::NORMAL; } - new_data = false; - break; // Do nothing more on positive pulse + continue; // Do nothing more on positive pulse } // CASES for NEGATIVE cycle triggering of pickup and sparks 12 & 34 case TRIG_FLAG_12N: @@ -193,7 +202,7 @@ void rtIgnitionTask(void *pvParameters) // Timeout occourred, expected POSITIVE edge spark NOT OCCOURRED else if (spark_flag == SPARK_FLAG_NIL && expected_negative) { - coils->sstart_status = softStartStatus::NORMAL; + coils->sstart_status = softStartStatus::ERROR; coils->spark_status = sparkStatus::SPARK_NEG_FAIL; } // Timeout not occouured, unexpected negative edge spark @@ -203,7 +212,11 @@ void rtIgnitionTask(void *pvParameters) coils->spark_status = sparkStatus::SPARK_NEG_UNEXPECTED; } // Wait for finish of negative pulse to save data to buffer - new_data = true; + coils->n_events++; + if (pickup_flag == TRIG_FLAG_12N) + cycle12 = true; + else + cycle34 = true; break; } default: @@ -215,8 +228,10 @@ void rtIgnitionTask(void *pvParameters) break; } - if (new_data) + if (cycle12 && cycle34) // wait for both 12 and 34 cycles to complete before sending data to main loop and resetting peak detectors { + cycle12 = false; + cycle34 = false; // vTaskDelay(pdMS_TO_TICKS(1)); // delay 1ms to allow peak detectors to charge for negative cycle // read adc channels: pickup12, out12 [ pos + neg ] if (adc) // read only if adc initialized @@ -249,9 +264,9 @@ void rtIgnitionTask(void *pvParameters) // send essage to main loop with ignition info, by copy so local static variable is ok if (rt_queue) ign_box_sts.timestamp = esp_timer_get_time(); // update data timestamp - if (xQueueSendToBack(rt_queue, (void *)&ign_box_sts, pdMS_TO_TICKS(1)) != pdPASS) + if (xQueueSendToBack(rt_queue, (void *)&ign_box_sts, 0) != pdPASS) { - q_fail_count++; + ign_box_sts.n_queue_errors++; LOG_ERROR("Failed to send to rt_queue"); } } diff --git a/RotaxMonitorTester/.vscode/extensions.json b/RotaxMonitorTester/.vscode/extensions.json index 080e70d..411655e 100644 --- a/RotaxMonitorTester/.vscode/extensions.json +++ b/RotaxMonitorTester/.vscode/extensions.json @@ -1,7 +1,7 @@ { - // See http://go.microsoft.com/fwlink/?LinkId=827846 - // for the documentation about the extensions.json format "recommendations": [ + "Jason2866.esp-decoder", + "pioarduino.pioarduino-ide", "platformio.platformio-ide" ], "unwantedRecommendations": [ diff --git a/RotaxMonitorTester/platformio.ini b/RotaxMonitorTester/platformio.ini index 8fb436c..7e45ba0 100644 --- a/RotaxMonitorTester/platformio.ini +++ b/RotaxMonitorTester/platformio.ini @@ -10,7 +10,7 @@ [env:esp32-devtest-release] board = esp32dev -platform = https://github.com/pioarduino/platform-espressif32/releases/download/55.03.37/platform-espressif32.zip +platform = https://github.com/pioarduino/platform-espressif32/releases/download/stable/platform-espressif32.zip framework = arduino lib_deps = hideakitai/DebugLog@^0.8.4 @@ -21,8 +21,8 @@ build_type = release [env:esp32-devtest-debug] board = esp32dev -platform = https://github.com/pioarduino/platform-espressif32/releases/download/55.03.37/platform-espressif32.zip -framework = arduino +platform = https://github.com/pioarduino/platform-espressif32/releases/download/stable/platform-espressif32.zip + lib_deps = hideakitai/DebugLog@^0.8.4 board_build.flash_size = 4MB diff --git a/RotaxMonitorTester/src/main.cpp b/RotaxMonitorTester/src/main.cpp index 20230a6..a9d6c66 100644 --- a/RotaxMonitorTester/src/main.cpp +++ b/RotaxMonitorTester/src/main.cpp @@ -15,7 +15,7 @@ static uint32_t count = 0; #define SPARK_DLY_MIN 10 #define SPARK_DLY_MAX 490 -#define PAUSE_LONG_MIN 10000 +#define PAUSE_LONG_MIN 5000 #define PAUSE_LONG_MAX PAUSE_LONG_MIN*100 void clearScreen(){ @@ -46,15 +46,16 @@ static timerStatus stsA = { .clock_period_us = (uint32_t)PERIOD_US, .pause_long_us = 10000, .pause_short_us = 1000, - .coil_pulse_us = 500, - .spark_pulse_us = 50, - .spark_delay_us = 10, + .coil_pulse_us = 1000, + .spark_pulse_us = 100, + .spark_delay_us = 50, .main_task = NULL}; void setup() { Serial.begin(115200); + delay(1000); LOG_ATTACH_SERIAL(Serial); pinMode(PIN_TRIG_A12P, OUTPUT); @@ -98,6 +99,9 @@ void loop() stsA.pause_long_us = (uint32_t)filtered; LOG_INFO("Spark Delay uS: ", stsA.spark_delay_us, "\tSoft Start: ", stsA.soft_start ? "TRUE" : "FALSE"); LOG_INFO("Pause: ", (uint32_t)(stsA.pause_long_us / 1000), "ms"); + LOG_INFO("Coil Pulse: ", stsA.coil_pulse_us, "us"); + LOG_INFO("Spark Pulse: ", stsA.spark_pulse_us, "us"); + delay(100); clearScreen(); diff --git a/RotaxMonitorTester/src/pins.h b/RotaxMonitorTester/src/pins.h index 14591da..cced640 100644 --- a/RotaxMonitorTester/src/pins.h +++ b/RotaxMonitorTester/src/pins.h @@ -19,5 +19,5 @@ #define SPARK_B34 5 // Pot -#define SPARK_DELAY_POT 12 +#define SPARK_DELAY_POT 13 #define FREQ_POT 14 From c5d80052e5bc2652b501d527fbb0d506acf6b9c2 Mon Sep 17 00:00:00 2001 From: Emanuele Trabattoni Date: Sat, 4 Apr 2026 22:12:53 +0200 Subject: [PATCH 5/7] Thans to copilot, microsecond resolution to wait for spark. no missing firings detected --- RotaxMonitor/platformio.ini | 8 +++++- RotaxMonitor/src/isr.cpp | 51 ++++++++++++------------------------- RotaxMonitor/src/isr.h | 1 + RotaxMonitor/src/main.cpp | 15 ++++++----- RotaxMonitor/src/tasks.cpp | 41 +++++++++++++++++++++-------- RotaxMonitor/src/tasks.h | 3 ++- 6 files changed, 64 insertions(+), 55 deletions(-) diff --git a/RotaxMonitor/platformio.ini b/RotaxMonitor/platformio.ini index 88ee606..4803271 100644 --- a/RotaxMonitor/platformio.ini +++ b/RotaxMonitor/platformio.ini @@ -29,7 +29,13 @@ monitor_speed = 115200 monitor_port = /dev/ttyACM2 ; Build configuration -build_type = debug +build_type = release +build_flags = + -DARDUINO_USB_CDC_ON_BOOT=0 + -DARDUINO_USB_MODE=0 + -fstack-protector-all + -DCONFIG_FREERTOS_GENERATE_RUN_TIME_STATS=1 + -DCONFIG_FREERTOS_USE_TRACE_FACILITY=1 [env:esp32-s3-devkitc1-n16r8-debug] board = ${env:esp32-s3-devkitc1-n16r8.board} diff --git a/RotaxMonitor/src/isr.cpp b/RotaxMonitor/src/isr.cpp index 622b339..a0c84c9 100644 --- a/RotaxMonitor/src/isr.cpp +++ b/RotaxMonitor/src/isr.cpp @@ -7,7 +7,6 @@ void trig_isr(void *arg) { const int64_t time_us = esp_timer_get_time(); - static uint8_t isr_firing_count = 0; // exit if invalid args if (!arg) @@ -26,47 +25,29 @@ void trig_isr(void *arg) { case TRIG_FLAG_12P: case TRIG_FLAG_12N: - // if (isr_firing_count == 0) - { - // only on first trigger to avoid multiple firing due to noise, to be fixed with hardware debounce - isr_firing_count++; - box->coils12.spark_ok = false; // reset spark ok flag on new trigger event - box->coils12.trig_time = time_us; - xTaskNotifyFromISR(task_handle, params->flag, eSetValueWithOverwrite, &xHigherPriorityTaskWoken); - } + // only on first trigger to avoid multiple firing due to noise, to be fixed with hardware debounce + box->coils12.trig_time = time_us; + xTaskNotifyFromISR(task_handle, params->flag, eSetValueWithOverwrite, &xHigherPriorityTaskWoken); break; case TRIG_FLAG_34P: case TRIG_FLAG_34N: - // if (isr_firing_count == 0) - { - // only on first trigger to avoid multiple firing due to noise, to be fixed with hardware debounce - isr_firing_count++; - box->coils34.spark_ok = false; // reset spark ok flag on new trigger event - box->coils34.trig_time = time_us; - xTaskNotifyFromISR(task_handle, params->flag, eSetValueWithOverwrite, &xHigherPriorityTaskWoken); - } + // only on first trigger to avoid multiple firing due to noise, to be fixed with hardware debounce + box->coils34.trig_time = time_us; + xTaskNotifyFromISR(task_handle, params->flag, eSetValueWithOverwrite, &xHigherPriorityTaskWoken); break; case SPARK_FLAG_12: - // if (isr_firing_count > 0) // only consider spark if a trigger has been detected, otherwise noise on spark pin can cause false positives - { - isr_firing_count = 0; // reset trigger timeout counter on spark event - box->coils34.spark_ok = false; - box->coils12.spark_ok = true; - box->coils12.spark_time = time_us; - xTaskNotifyFromISR(task_handle, params->flag, eSetValueWithOverwrite, &xHigherPriorityTaskWoken); - // vTaskNotifyGiveFromISR(task_handle, &xHigherPriorityTaskWoken); - } + box->coils34.spark_ok = false; + box->coils12.spark_ok = true; + box->coils12.spark_time = time_us; + xTaskNotifyFromISR(task_handle, params->flag, eSetValueWithOverwrite, &xHigherPriorityTaskWoken); + // vTaskNotifyGiveFromISR(task_handle, &xHigherPriorityTaskWoken); break; case SPARK_FLAG_34: - // if (isr_firing_count > 0) // only consider spark if a trigger has been detected, otherwise noise on spark pin can cause false positives - { - isr_firing_count = 0; // reset trigger timeout counter on spark event - box->coils12.spark_ok = false; - box->coils34.spark_ok = true; - box->coils34.spark_time = time_us; - xTaskNotifyFromISR(task_handle, params->flag, eSetValueWithOverwrite, &xHigherPriorityTaskWoken); - // vTaskNotifyGiveFromISR(task_handle, &xHigherPriorityTaskWoken); - } + box->coils12.spark_ok = false; + box->coils34.spark_ok = true; + box->coils34.spark_time = time_us; + xTaskNotifyFromISR(task_handle, params->flag, eSetValueWithOverwrite, &xHigherPriorityTaskWoken); + // vTaskNotifyGiveFromISR(task_handle, &xHigherPriorityTaskWoken); break; default: break; diff --git a/RotaxMonitor/src/isr.h b/RotaxMonitor/src/isr.h index f3c38c6..0893b2c 100644 --- a/RotaxMonitor/src/isr.h +++ b/RotaxMonitor/src/isr.h @@ -29,6 +29,7 @@ static const uint32_t TRIG_FLAG_34N = (1 << 3); static const uint32_t SPARK_FLAG_NIL = (1 << 8); static const uint32_t SPARK_FLAG_12 = (1 << 9); static const uint32_t SPARK_FLAG_34 = (1 << 10); +static const uint32_t SPARK_FLAG_TIMEOUT = (1 << 11); // Spark Status enum sparkStatus diff --git a/RotaxMonitor/src/main.cpp b/RotaxMonitor/src/main.cpp index 714f204..70977b6 100644 --- a/RotaxMonitor/src/main.cpp +++ b/RotaxMonitor/src/main.cpp @@ -12,14 +12,16 @@ #include #include +// FreeRTOS directives +#include "freertos/FreeRTOS.h" +#include "freertos/task.h" + // #define CH_B_ENABLE #define TEST -void printTaskList() -{ +void printTaskStats() { char buffer[1024]; - Serial.println("Task Name\tState\tPrio\tStack\tNum"); - vTaskList(buffer); + vTaskGetRunTimeStats(buffer); Serial.println(buffer); } @@ -174,6 +176,7 @@ void loop() int64_t last = esp_timer_get_time(); uint32_t missed_firings12 = 0; uint32_t missed_firings34 = 0; + uint32_t counter = 0; while (running) { @@ -217,9 +220,7 @@ void loop() last = esp_timer_get_time(); } else { - setCursor(0, 22); - Serial.print("Waiting for data... ");; - Serial.flush(); + Serial.println("Waiting for data... ");; } } diff --git a/RotaxMonitor/src/tasks.cpp b/RotaxMonitor/src/tasks.cpp index ba55408..6b5606a 100644 --- a/RotaxMonitor/src/tasks.cpp +++ b/RotaxMonitor/src/tasks.cpp @@ -1,4 +1,11 @@ #include "tasks.h" +#include + +// Timeout callback for microsecond precision +void spark_timeout_callback(void* arg) { + TaskHandle_t handle = (TaskHandle_t)arg; + xTaskNotify(handle, SPARK_FLAG_TIMEOUT, eSetValueWithOverwrite); +} void rtIgnitionTask(void *pvParameters) { @@ -51,6 +58,16 @@ void rtIgnitionTask(void *pvParameters) LOG_INFO("rtTask ISR Params OK"); + // Create esp_timer for microsecond precision timeout + esp_timer_handle_t timeout_timer; + esp_timer_create_args_t timer_args = { + .callback = spark_timeout_callback, + .arg = (void*)rt_handle_ptr, + .dispatch_method = ESP_TIMER_TASK, + .name = "spark_timeout" + }; + esp_timer_create(&timer_args, &timeout_timer); + // Attach Pin Interrupts attachInterruptArg(digitalPinToInterrupt(rt_int.trig_pin_12p), rt_int.isr_ptr, (void *)&isr_params_t12p, RISING); attachInterruptArg(digitalPinToInterrupt(rt_int.trig_pin_12n), rt_int.isr_ptr, (void *)&isr_params_t12n, RISING); @@ -107,25 +124,25 @@ void rtIgnitionTask(void *pvParameters) } #endif - // WAIT FOR SPARK TO HAPPEN OR TIMEOUT - // auto spark_timeout = ulTaskNotifyTake(pdTRUE, pdMS_TO_TICKS(spark_timeout_max)); - // if (ign_box_sts.coils12.spark_ok || ign_box_sts.coils34.spark_ok) // otherwise timeout if none is set in the ISR - // spark_flag = ign_box_sts.coils12.spark_ok ? SPARK_FLAG_12 : SPARK_FLAG_34; - // else - // spark_flag = SPARK_FLAG_NIL; + // Start microsecond precision timeout timer + esp_timer_stop(timeout_timer); // stop timer in case it was running from previous cycle + esp_timer_start_once(timeout_timer, spark_timeout_max); spark_flag = SPARK_FLAG_NIL; // default value in case of timeout, to be set by ISR if spark event occours // WAIT FOR SPARK TO HAPPEN OR TIMEOUT - auto sp = xTaskNotifyWait( + BaseType_t sp = pdFALSE; + sp = xTaskNotifyWait( 0x00, // non pulire all'ingresso ULONG_MAX, // pulisci i primi 8 bit &spark_flag, // valore ricevuto - pdMS_TO_TICKS(spark_timeout_max)); // wait for spark event or timeout + portMAX_DELAY); // wait indefinitely, timeout handled by esp_timer - // timeout occurred, set spark flag to nil - if (sp == pdFALSE) - { + // Handle timeout or spark event + if (spark_flag == SPARK_FLAG_TIMEOUT) { spark_flag = SPARK_FLAG_NIL; + } else { + // Spark occurred, stop the timer + esp_timer_stop(timeout_timer); } #ifdef DEBUG @@ -271,6 +288,8 @@ void rtIgnitionTask(void *pvParameters) } } } + // Delete the timeout timer + esp_timer_delete(timeout_timer); LOG_WARN("Ending realTime Task"); // Ignition A Interrupts DETACH detachInterrupt(rt_int.trig_pin_12p); diff --git a/RotaxMonitor/src/tasks.h b/RotaxMonitor/src/tasks.h index 1fde989..c1196eb 100644 --- a/RotaxMonitor/src/tasks.h +++ b/RotaxMonitor/src/tasks.h @@ -16,7 +16,7 @@ #include "devices.h" // Global Variables and Flags -const uint8_t spark_timeout_max = 1; // in milliseconds +const uint32_t spark_timeout_max = 500; // in microseconds // Debug Variables #ifdef DEBUG @@ -27,6 +27,7 @@ static const std::map names = { {TRIG_FLAG_34N, "TRIG_FLAG_34N"}, {SPARK_FLAG_12, "SPARK_FLAG_12"}, {SPARK_FLAG_34, "SPARK_FLAG_34"}, + {SPARK_FLAG_TIMEOUT, "SPARK_FLAG_TIMEOUT"}, }; #endif From a2d0afa0c92e2fde91c08c9b5e4f4e84c9f9c166 Mon Sep 17 00:00:00 2001 From: Emanuele Trabattoni Date: Sun, 5 Apr 2026 11:16:10 +0200 Subject: [PATCH 6/7] adc read ok, very slow --- RotaxMonitor/platformio.ini | 2 +- RotaxMonitor/src/devices.h | 3 +++ RotaxMonitor/src/main.cpp | 51 ++++++++++++++++++++++--------------- RotaxMonitor/src/pins.h | 10 +++----- RotaxMonitor/src/tasks.cpp | 7 +++-- 5 files changed, 43 insertions(+), 30 deletions(-) diff --git a/RotaxMonitor/platformio.ini b/RotaxMonitor/platformio.ini index 4803271..f1dd197 100644 --- a/RotaxMonitor/platformio.ini +++ b/RotaxMonitor/platformio.ini @@ -49,7 +49,7 @@ upload_port = /dev/ttyACM2 upload_speed = 921600 ;Monitor configuration -monitor_speed = 115200 +monitor_speed = 921600 monitor_port = /dev/ttyACM2 ; Debug configuration diff --git a/RotaxMonitor/src/devices.h b/RotaxMonitor/src/devices.h index 869729f..e6027e5 100644 --- a/RotaxMonitor/src/devices.h +++ b/RotaxMonitor/src/devices.h @@ -1,5 +1,8 @@ #pragma once +// Library defines +#define ADS1256_SPI_ALREADY_STARTED + // Device Libraries #include #include diff --git a/RotaxMonitor/src/main.cpp b/RotaxMonitor/src/main.cpp index 70977b6..a149e9e 100644 --- a/RotaxMonitor/src/main.cpp +++ b/RotaxMonitor/src/main.cpp @@ -19,7 +19,13 @@ // #define CH_B_ENABLE #define TEST -void printTaskStats() { +float freqToRPM(float freq) +{ + return freq * 60.0f; // 1 pulse per revolution +} + +void printTaskStats() +{ char buffer[1024]; vTaskGetRunTimeStats(buffer); Serial.println(buffer); @@ -102,14 +108,15 @@ void loop() bool spiA_ok = true; bool spiB_ok = true; -#ifndef TEST // Init 2 SPI interfaces SPIClass SPI_A(FSPI); spiA_ok = SPI_A.begin(SPI_A_SCK, SPI_A_MISO, SPI_A_MOSI); + SPI_A.setDataMode(SPI_MODE1); // ADS1256 requires SPI mode 1 + #ifndef TEST SPIClass SPI_B(HSPI); spiB_ok = SPI_B.begin(SPI_B_SCK, SPI_B_MISO, SPI_B_MOSI); -#endif - + SPI_B.setDataMode(SPI_MODE1); // ADS1256 requires SPI mode 1 + #endif if (!spiA_ok || !spiB_ok) { LOG_ERROR("Unable to Initialize SPI Busses"); @@ -119,13 +126,13 @@ void loop() } LOG_INFO("Init SPI OK"); -#ifndef TEST // Init ADC_A - dev.adc_a = new ADS1256(ADC_A_DRDY, ADC_A_RST, ADC_A_SYNC, ADC_A_CS, 2.5, &SPI_A); + dev.adc_a = new ADS1256(ADC_A_DRDY, ADS1256::PIN_UNUSED, ADC_A_SYNC, ADC_A_CS, 2.5, &SPI_A); dev.adc_a->InitializeADC(); dev.adc_a->setPGA(PGA_1); - dev.adc_a->setDRATE(DRATE_1000SPS); + dev.adc_a->setDRATE(DRATE_30000SPS); +#ifndef TEST // Init ADC_B dev.adc_a = new ADS1256(ADC_B_DRDY, ADC_B_RST, ADC_B_SYNC, ADC_B_CS, 2.5, &SPI_B); dev.adc_a->InitializeADC(); @@ -185,7 +192,7 @@ void loop() if (ignA.coils12.spark_status == sparkStatus::SPARK_NEG_FAIL || ignA.coils12.spark_status == sparkStatus::SPARK_POS_FAIL) missed_firings12++; if (ignA.coils34.spark_status == sparkStatus::SPARK_POS_FAIL || ignA.coils34.spark_status == sparkStatus::SPARK_NEG_FAIL) - missed_firings34++; + missed_firings34++; clearScreen(); setCursor(0, 0); printField("++ Timestamp", (uint32_t)ignA.timestamp, 0, 0); @@ -194,10 +201,10 @@ void loop() printField("Missed Firing", missed_firings12, 0, 2); printField("Spark Dly", (uint32_t)ignA.coils12.spark_delay, 0, 3); printField("Spark Sts", sparkStatusNames.at(ignA.coils12.spark_status), 0, 4); - // printField("Peak P_IN", ignA.coils12.peak_p_in, 0, 5); - // printField("Peak P_OUT", ignA.coils12.peak_p_out, 0, 6); - // printField("Peak N_IN", ignA.coils12.peak_n_in, 0, 7); - // printField("Peak N_OUT", ignA.coils12.peak_n_out, 0, 8); + printField("Peak P_IN", ignA.coils12.peak_p_in, 0, 5); + printField("Peak N_IN", ignA.coils12.peak_n_in, 0, 7); + printField("Peak P_OUT", ignA.coils12.peak_p_out, 0, 6); + printField("Peak N_OUT", ignA.coils12.peak_n_out, 0, 8); printField("Soft Start ", softStartStatusNames.at(ignA.coils12.sstart_status), 0, 9); Serial.println("========== Coils 34 ============="); @@ -205,22 +212,24 @@ void loop() printField("Missed Firing", missed_firings34, 0, 12); printField("Spark Dly", (uint32_t)ignA.coils34.spark_delay, 0, 13); printField("Spark Sts", sparkStatusNames.at(ignA.coils34.spark_status), 0, 14); - // printField("Peak P_IN", ignA.coils34.peak_p_in, 0, 15); - // printField("Peak P_OUT", ignA.coils34.peak_p_out, 0, 16); - // printField("Peak N_IN", ignA.coils34.peak_n_in, 0, 17); - // printField("Peak N_OUT", ignA.coils34.peak_n_out, 0, 18); + printField("Peak P_IN", ignA.coils34.peak_p_in, 0, 15); + printField("Peak N_IN", ignA.coils34.peak_n_in, 0, 17); + printField("Peak P_OUT", ignA.coils34.peak_p_out, 0, 16); + printField("Peak N_OUT", ignA.coils34.peak_n_out, 0, 18); printField("Soft Start ", softStartStatusNames.at(ignA.coils34.sstart_status), 0, 19); Serial.println("========== END ============="); Serial.println(); - auto delta = (esp_timer_get_time() - last) / 1000000.0f; //in seconds - delta = delta > 0 ? 1.0f / delta : 0; // Calculate frequency (Hz) - printField("Frequency (Hz)", delta, 0, 21); + auto freq = (esp_timer_get_time() - last) / 1000000.0f; // in seconds + freq = freq > 0 ? 1.0f / freq : 0; // Calculate frequency (Hz) + printField("Engine RPM", freqToRPM(freq), 0, 21); printField("Queue Errors", (uint32_t)ignA.n_queue_errors, 0, 22); last = esp_timer_get_time(); - } else + } + else { - Serial.println("Waiting for data... ");; + Serial.println("Waiting for data... "); + delay(500); } } diff --git a/RotaxMonitor/src/pins.h b/RotaxMonitor/src/pins.h index a818b89..62a3ded 100644 --- a/RotaxMonitor/src/pins.h +++ b/RotaxMonitor/src/pins.h @@ -48,19 +48,17 @@ // ===================== #define ADC_A_CS 4 #define ADC_A_DRDY 5 -#define ADC_A_RST 6 -#define ADC_A_SYNC 7 +#define ADC_A_SYNC 6 #define ADC_B_CS 14 #define ADC_B_DRDY 15 -#define ADC_B_RST 16 -#define ADC_B_SYNC 17 +#define ADC_B_SYNC 16 // ===================== // DIGITAL POT // ===================== -//#define POT_A_CS 1 -//#define POT_B_CS 2 +#define POT_A_CS 7 +#define POT_B_CS 17 // ===================== // TRIGGER INPUT INTERRUPTS diff --git a/RotaxMonitor/src/tasks.cpp b/RotaxMonitor/src/tasks.cpp index 6b5606a..7f3348d 100644 --- a/RotaxMonitor/src/tasks.cpp +++ b/RotaxMonitor/src/tasks.cpp @@ -162,6 +162,7 @@ void rtIgnitionTask(void *pvParameters) continue; } + // Select coil status reference based on pickup_flag coilsStatus *coils; switch (pickup_flag) { @@ -176,6 +177,7 @@ void rtIgnitionTask(void *pvParameters) break; } + // Select logic based on pickup and spark flags switch (pickup_flag) { case TRIG_FLAG_12P: @@ -249,7 +251,6 @@ void rtIgnitionTask(void *pvParameters) { cycle12 = false; cycle34 = false; - // vTaskDelay(pdMS_TO_TICKS(1)); // delay 1ms to allow peak detectors to charge for negative cycle // read adc channels: pickup12, out12 [ pos + neg ] if (adc) // read only if adc initialized { @@ -283,7 +284,9 @@ void rtIgnitionTask(void *pvParameters) ign_box_sts.timestamp = esp_timer_get_time(); // update data timestamp if (xQueueSendToBack(rt_queue, (void *)&ign_box_sts, 0) != pdPASS) { - ign_box_sts.n_queue_errors++; + static uint32_t n_errors = 0; + n_errors++; + ign_box_sts.n_queue_errors = n_errors; LOG_ERROR("Failed to send to rt_queue"); } } From 5c9ef7e93b852618a173c8b54c1d659dfff608b0 Mon Sep 17 00:00:00 2001 From: Emanuele Trabattoni Date: Sun, 5 Apr 2026 17:05:10 +0200 Subject: [PATCH 7/7] Fast ADC readings ok, to verify timing and settling time --- RotaxMonitor/platformio.ini | 4 +-- RotaxMonitor/src/ADS1256.cpp | 10 +++--- RotaxMonitor/src/isr.h | 1 + RotaxMonitor/src/main.cpp | 55 +++++++++++++++-------------- RotaxMonitor/src/tasks.cpp | 2 ++ RotaxMonitor/src/ui.h | 57 +++++++++---------------------- RotaxMonitorTester/platformio.ini | 4 +-- RotaxMonitorTester/src/main.cpp | 15 ++++---- 8 files changed, 66 insertions(+), 82 deletions(-) diff --git a/RotaxMonitor/platformio.ini b/RotaxMonitor/platformio.ini index f1dd197..117d9d2 100644 --- a/RotaxMonitor/platformio.ini +++ b/RotaxMonitor/platformio.ini @@ -25,8 +25,8 @@ upload_port = /dev/ttyACM2 upload_speed = 921600 ;Monitor configuration -monitor_speed = 115200 monitor_port = /dev/ttyACM2 +monitor_speed = 921600 ; Build configuration build_type = release @@ -49,8 +49,8 @@ upload_port = /dev/ttyACM2 upload_speed = 921600 ;Monitor configuration -monitor_speed = 921600 monitor_port = /dev/ttyACM2 +monitor_speed = 921600 ; Debug configuration debug_tool = esp-builtin diff --git a/RotaxMonitor/src/ADS1256.cpp b/RotaxMonitor/src/ADS1256.cpp index 3372b47..79e2430 100644 --- a/RotaxMonitor/src/ADS1256.cpp +++ b/RotaxMonitor/src/ADS1256.cpp @@ -120,14 +120,14 @@ void ADS1256::setDRATE(uint8_t drate) //Setting DRATE (sampling frequency) { writeRegister(DRATE_REG, drate); _DRATE = drate; - delay(200); + delayMicroseconds(500); } void ADS1256::setMUX(uint8_t mux) //Setting MUX (input channel) { writeRegister(MUX_REG, mux); _MUX = mux; - delay(200); + //delayMicroseconds(500); } void ADS1256::setPGA(uint8_t pga) //Setting PGA (input voltage range) @@ -138,7 +138,7 @@ void ADS1256::setPGA(uint8_t pga) //Setting PGA (input voltage range) _ADCON = (_ADCON & 0b11111000) | (_PGA & 0b00000111); // Clearing and then setting bits 2-0 based on pga writeRegister(ADCON_REG, _ADCON); - delay(200); + delayMicroseconds(1000); //Delay to allow the PGA to settle after changing its value updateConversionParameter(); //Update the multiplier according top the new PGA value } @@ -501,8 +501,6 @@ void ADS1256::writeRegister(uint8_t registerAddress, uint8_t registerValueToWrit CS_HIGH(); _spi->endTransaction(); - delay(100); - } long ADS1256::readRegister(uint8_t registerAddress) //Reading a register @@ -524,7 +522,7 @@ long ADS1256::readRegister(uint8_t registerAddress) //Reading a register CS_HIGH(); _spi->endTransaction(); - delay(100); + return regValue; } diff --git a/RotaxMonitor/src/isr.h b/RotaxMonitor/src/isr.h index 0893b2c..c75e2c0 100644 --- a/RotaxMonitor/src/isr.h +++ b/RotaxMonitor/src/isr.h @@ -99,6 +99,7 @@ struct ignitionBoxStatus // voltage from generator float volts_gen = 0.0; uint32_t n_queue_errors = 0; + uint32_t adc_read_time = 0; }; struct isrParams diff --git a/RotaxMonitor/src/main.cpp b/RotaxMonitor/src/main.cpp index a149e9e..ef60521 100644 --- a/RotaxMonitor/src/main.cpp +++ b/RotaxMonitor/src/main.cpp @@ -130,7 +130,7 @@ void loop() dev.adc_a = new ADS1256(ADC_A_DRDY, ADS1256::PIN_UNUSED, ADC_A_SYNC, ADC_A_CS, 2.5, &SPI_A); dev.adc_a->InitializeADC(); dev.adc_a->setPGA(PGA_1); - dev.adc_a->setDRATE(DRATE_30000SPS); + dev.adc_a->setDRATE(DRATE_7500SPS); #ifndef TEST // Init ADC_B @@ -189,42 +189,45 @@ void loop() { if (xQueueReceive(rt_taskA_queue, &ignA, pdMS_TO_TICKS(1000)) == pdTRUE) { - if (ignA.coils12.spark_status == sparkStatus::SPARK_NEG_FAIL || ignA.coils12.spark_status == sparkStatus::SPARK_POS_FAIL) + float freq = (esp_timer_get_time() - last) / 1000000.0f; // in seconds + freq = freq > 0 ? 1.0f / freq : 0; // Calculate frequency (Hz) + last = esp_timer_get_time(); + + if (ignA.coils12.spark_status == sparkStatus::SPARK_POS_FAIL || ignA.coils12.spark_status == sparkStatus::SPARK_NEG_FAIL) missed_firings12++; if (ignA.coils34.spark_status == sparkStatus::SPARK_POS_FAIL || ignA.coils34.spark_status == sparkStatus::SPARK_NEG_FAIL) missed_firings34++; + clearScreen(); setCursor(0, 0); - printField("++ Timestamp", (uint32_t)ignA.timestamp, 0, 0); + printField("++ Timestamp", (uint32_t)ignA.timestamp); Serial.println("========== Coils 12 ============="); - printField("Events", (uint32_t)ignA.coils12.n_events, 0, 1); - printField("Missed Firing", missed_firings12, 0, 2); - printField("Spark Dly", (uint32_t)ignA.coils12.spark_delay, 0, 3); - printField("Spark Sts", sparkStatusNames.at(ignA.coils12.spark_status), 0, 4); - printField("Peak P_IN", ignA.coils12.peak_p_in, 0, 5); - printField("Peak N_IN", ignA.coils12.peak_n_in, 0, 7); - printField("Peak P_OUT", ignA.coils12.peak_p_out, 0, 6); - printField("Peak N_OUT", ignA.coils12.peak_n_out, 0, 8); - printField("Soft Start ", softStartStatusNames.at(ignA.coils12.sstart_status), 0, 9); + printField("Events", (uint32_t)ignA.coils12.n_events); + printField("Missed Firing", missed_firings12); + printField("Spark Dly", (uint32_t)ignA.coils12.spark_delay); + printField("Spark Sts", sparkStatusNames.at(ignA.coils12.spark_status)); + printField("Peak P_IN", ignA.coils12.peak_p_in); + printField("Peak N_IN", ignA.coils12.peak_n_in); + printField("Peak P_OUT", ignA.coils12.peak_p_out); + printField("Peak N_OUT", ignA.coils12.peak_n_out); + printField("Soft Start ", softStartStatusNames.at(ignA.coils12.sstart_status)); Serial.println("========== Coils 34 ============="); - printField("Events", (uint32_t)ignA.coils34.n_events, 0, 11); - printField("Missed Firing", missed_firings34, 0, 12); - printField("Spark Dly", (uint32_t)ignA.coils34.spark_delay, 0, 13); - printField("Spark Sts", sparkStatusNames.at(ignA.coils34.spark_status), 0, 14); - printField("Peak P_IN", ignA.coils34.peak_p_in, 0, 15); - printField("Peak N_IN", ignA.coils34.peak_n_in, 0, 17); - printField("Peak P_OUT", ignA.coils34.peak_p_out, 0, 16); - printField("Peak N_OUT", ignA.coils34.peak_n_out, 0, 18); - printField("Soft Start ", softStartStatusNames.at(ignA.coils34.sstart_status), 0, 19); + printField("Events", (uint32_t)ignA.coils34.n_events); + printField("Missed Firing", missed_firings34); + printField("Spark Dly", (uint32_t)ignA.coils34.spark_delay); + printField("Spark Sts", sparkStatusNames.at(ignA.coils34.spark_status)); + printField("Peak P_IN", ignA.coils34.peak_p_in); + printField("Peak N_IN", ignA.coils34.peak_n_in); + printField("Peak P_OUT", ignA.coils34.peak_p_out); + printField("Peak N_OUT", ignA.coils34.peak_n_out); + printField("Soft Start ", softStartStatusNames.at(ignA.coils34.sstart_status)); Serial.println("========== END ============="); Serial.println(); - auto freq = (esp_timer_get_time() - last) / 1000000.0f; // in seconds - freq = freq > 0 ? 1.0f / freq : 0; // Calculate frequency (Hz) - printField("Engine RPM", freqToRPM(freq), 0, 21); - printField("Queue Errors", (uint32_t)ignA.n_queue_errors, 0, 22); - last = esp_timer_get_time(); + printField("Engine RPM", freqToRPM(freq)); + printField("ADC Read Time", (uint32_t)ignA.adc_read_time); + printField("Queue Errors", (uint32_t)ignA.n_queue_errors); } else { diff --git a/RotaxMonitor/src/tasks.cpp b/RotaxMonitor/src/tasks.cpp index 7f3348d..8a72bc0 100644 --- a/RotaxMonitor/src/tasks.cpp +++ b/RotaxMonitor/src/tasks.cpp @@ -254,6 +254,7 @@ void rtIgnitionTask(void *pvParameters) // read adc channels: pickup12, out12 [ pos + neg ] if (adc) // read only if adc initialized { + uint32_t start_adc_read = esp_timer_get_time(); // from peak detector circuits ign_box_sts.coils12.peak_p_in = adcReadChannel(adc, ADC_CH_PEAK_12P_IN); ign_box_sts.coils12.peak_n_in = adcReadChannel(adc, ADC_CH_PEAK_12N_IN); @@ -263,6 +264,7 @@ void rtIgnitionTask(void *pvParameters) ign_box_sts.coils12.peak_n_out = adcReadChannel(adc, ADC_CH_PEAK_12N_OUT); ign_box_sts.coils34.peak_p_out = adcReadChannel(adc, ADC_CH_PEAK_34P_OUT); ign_box_sts.coils34.peak_n_out = adcReadChannel(adc, ADC_CH_PEAK_34N_OUT); + ign_box_sts.adc_read_time = (uint32_t)(esp_timer_get_time() - start_adc_read); } else // simulate adc read timig vTaskDelay(pdMS_TO_TICKS(1)); diff --git a/RotaxMonitor/src/ui.h b/RotaxMonitor/src/ui.h index a9f8c9f..9c801be 100644 --- a/RotaxMonitor/src/ui.h +++ b/RotaxMonitor/src/ui.h @@ -2,58 +2,35 @@ #include -static bool firstRun = true; - -void clearScreen(){ +void clearScreen() +{ Serial.print("\033[2J"); // clear screen Serial.print("\033[H"); // cursor home Serial.flush(); } -void setCursor(const uint8_t x, const uint8_t y) { - Serial.printf("\033[%d;%d", y, x+1); +void setCursor(const uint8_t x, const uint8_t y) +{ + Serial.printf("\033[%d;%d", y, x + 1); Serial.flush(); } -void printField(const char name[], const uint32_t val, const uint8_t x, const uint8_t y) { - if (firstRun) { - setCursor(x,y); - Serial.printf("%15s: %06d\n", name, val); - return; - } - setCursor(x+16, y); - Serial.print(val); +void printField(const char name[], const uint32_t val) +{ + Serial.printf("%15s: %06d\n", name, val); } -void printField(const char name[], const int64_t val, const uint8_t x, const uint8_t y) { - if (firstRun) { - setCursor(x,y); - Serial.printf("%15s: %06u\n", name, (uint64_t)val); - return; - } - setCursor(x+16, y); - Serial.print((uint64_t)val); - Serial.flush(); +void printField(const char name[], const int64_t val) +{ + Serial.printf("%15s: %06u\n", name, (uint64_t)val); } -void printField(const char name[], const float val, const uint8_t x, const uint8_t y) { - if (firstRun) { - setCursor(x,y); - Serial.printf("%15s: %4.2f\n", name, val); - return; - } - setCursor(x+16, y); - Serial.print(val); - Serial.flush(); +void printField(const char name[], const float val) +{ + Serial.printf("%15s: %4.2f\n", name, val); } -void printField(const char name[], const char *val, const uint8_t x, const uint8_t y) { - if (firstRun) { - setCursor(x,y); - Serial.printf("%15s: %s\n", name, val); - return; - } - setCursor(x+16, y); - Serial.print(val); - Serial.flush(); +void printField(const char name[], const char *val) +{ + Serial.printf("%15s: %s\n", name, val); } \ No newline at end of file diff --git a/RotaxMonitorTester/platformio.ini b/RotaxMonitorTester/platformio.ini index 7e45ba0..2653613 100644 --- a/RotaxMonitorTester/platformio.ini +++ b/RotaxMonitorTester/platformio.ini @@ -16,7 +16,7 @@ lib_deps = hideakitai/DebugLog@^0.8.4 board_build.flash_size = 4MB board_build.partitions = default.csv -monitor_speed = 115200 +monitor_speed = 921600 build_type = release [env:esp32-devtest-debug] @@ -27,7 +27,7 @@ lib_deps = hideakitai/DebugLog@^0.8.4 board_build.flash_size = 4MB board_build.partitions = default.csv -monitor_speed = 115200 +monitor_speed = 921600 build_type = debug build_flags = -O0 diff --git a/RotaxMonitorTester/src/main.cpp b/RotaxMonitorTester/src/main.cpp index a9d6c66..ea657e7 100644 --- a/RotaxMonitorTester/src/main.cpp +++ b/RotaxMonitorTester/src/main.cpp @@ -18,13 +18,16 @@ static uint32_t count = 0; #define PAUSE_LONG_MIN 5000 #define PAUSE_LONG_MAX PAUSE_LONG_MIN*100 +#define RPM_MIN 800 +#define RPM_MAX 5500 + void clearScreen(){ Serial.print("\033[2J"); // clear screen Serial.print("\033[H"); // cursor home Serial.flush(); } -static double filtered = 0; +static double filtered_rpm = 0; static const std::map pin2Name = { {PIN_TRIG_A12P, "HIGH_PIN_TRIG_A12P"}, @@ -54,7 +57,7 @@ static timerStatus stsA = { void setup() { - Serial.begin(115200); + Serial.begin(921600); delay(1000); LOG_ATTACH_SERIAL(Serial); @@ -94,11 +97,11 @@ void loop() stsA.soft_start = false; } - double new_val = (float)(map(analogRead(FREQ_POT), 0, 4096, PAUSE_LONG_MIN, PAUSE_LONG_MAX)); - filtered = filtered + 0.1 * (new_val - filtered); - stsA.pause_long_us = (uint32_t)filtered; + double new_rpm = (double)(map(analogRead(FREQ_POT), 0, 4096, RPM_MIN, RPM_MAX)); + filtered_rpm = filtered_rpm + 0.1 * (new_rpm - filtered_rpm); + stsA.pause_long_us = (uint32_t)(60000000.0f / filtered_rpm / 2.0f); LOG_INFO("Spark Delay uS: ", stsA.spark_delay_us, "\tSoft Start: ", stsA.soft_start ? "TRUE" : "FALSE"); - LOG_INFO("Pause: ", (uint32_t)(stsA.pause_long_us / 1000), "ms"); + LOG_INFO("Engine Rpm: ", (uint32_t)(filtered_rpm)); LOG_INFO("Coil Pulse: ", stsA.coil_pulse_us, "us"); LOG_INFO("Spark Pulse: ", stsA.spark_pulse_us, "us");