diff --git a/software/apps/adc_dt/boards/weact_stm32g431_core.overlay b/software/apps/adc_dt/boards/weact_stm32g431_core.overlay index e1f4dfa..1911ee6 100644 --- a/software/apps/adc_dt/boards/weact_stm32g431_core.overlay +++ b/software/apps/adc_dt/boards/weact_stm32g431_core.overlay @@ -1,28 +1,38 @@ / { - zephyr,user { - io-channels = <&adc1 1>; - io-channel-names = "multi_sense"; - }; + vdd_sense: voltage-divider { + compatible = "voltage-divider"; + /* + * This reference must provide one argument (the channel number) + * because of the "#io-channel-cells = <1>" in the &adc1 node. + */ + io-channels = <&adc1 1>; + output-ohms = <2200>; + full-ohms = <3200>; + }; }; &adc1 { - status = "okay"; + status = "okay"; - pinctrl-0 = <&adc1_in1_pa0>; - pinctrl-names = "default"; + pinctrl-0 = <&adc1_in1_pa0>; + pinctrl-names = "default"; - st,adc-clock-source = "SYNC"; - st,adc-prescaler = <4>; + st,adc-clock-source = "SYNC"; + st,adc-prescaler = <4>; - #address-cells = <1>; - #size-cells = <0>; + #address-cells = <1>; + #size-cells = <0>; + /* + * This line is required by the st,stm32-adc driver binding. + * It declares that references to its channels need one extra argument. + */ + #io-channel-cells = <1>; - /* This defines channel 1 on adc1. The "1" in io-channels refers to this reg value. */ - adc_channel_1: channel@1 { - reg = <1>; - zephyr,gain = "ADC_GAIN_1"; - zephyr,reference = "ADC_REF_INTERNAL"; - zephyr,acquisition-time = ; - zephyr,resolution = <12>; - }; + adc_channel_1: channel@1 { + reg = <1>; + zephyr,gain = "ADC_GAIN_1"; + zephyr,reference = "ADC_REF_INTERNAL"; + zephyr,acquisition-time = ; + zephyr,resolution = <12>; + }; }; \ No newline at end of file diff --git a/software/apps/adc_dt/prj.conf b/software/apps/adc_dt/prj.conf index 8356908..a2f9a32 100644 --- a/software/apps/adc_dt/prj.conf +++ b/software/apps/adc_dt/prj.conf @@ -1,2 +1,4 @@ CONFIG_ADC=y +CONFIG_SENSOR=y +CONFIG_VOLTAGE_DIVIDER=y CONFIG_LOG=y \ No newline at end of file diff --git a/software/apps/adc_dt/src/main.c b/software/apps/adc_dt/src/main.c index dc2604c..2d7212b 100644 --- a/software/apps/adc_dt/src/main.c +++ b/software/apps/adc_dt/src/main.c @@ -1,57 +1,43 @@ #include #include #include -#include +#include #include LOG_MODULE_REGISTER(adc_dt_example, LOG_LEVEL_DBG); -/* Get the ADC channel specification from the devicetree */ -#define SENSE_NODE DT_PATH(zephyr_user) -static const struct adc_dt_spec sense_channel = ADC_DT_SPEC_GET_BY_NAME(SENSE_NODE, multi_sense); +/* Get the voltage divider device */ +#define VOLTAGE_DIVIDER_NODE DT_NODELABEL(vdd_sense) int main(void) { + const struct device *vdd_dev = DEVICE_DT_GET(VOLTAGE_DIVIDER_NODE); + struct sensor_value val; int err; - uint16_t buf; - struct adc_sequence sequence = { - .buffer = &buf, - .buffer_size = sizeof(buf), - }; - if (!device_is_ready(sense_channel.dev)) { - LOG_ERR("ADC controller device not ready"); + if (!device_is_ready(vdd_dev)) { + LOG_ERR("Voltage divider device not ready"); return 0; } - err = adc_channel_setup_dt(&sense_channel); - if (err < 0) { - LOG_ERR("Could not setup channel #%u (%d)", sense_channel.channel_id, err); - return 0; - } - - LOG_INF("ADC channel setup successful!"); + LOG_INF("Voltage divider device ready!"); while (1) { - // 1. Explicitly initialize the sequence structure from the devicetree spec. - // This sets sequence.channels correctly. - (void)adc_sequence_init_dt(&sense_channel, &sequence); - - // 2. Perform the read on the ADC device with the now-configured sequence. - err = adc_read(sense_channel.dev, &sequence); + err = sensor_sample_fetch(vdd_dev); if (err < 0) { - LOG_ERR("Could not read (%d)", err); + LOG_ERR("Could not fetch sample (%d)", err); k_sleep(K_MSEC(1000)); continue; } - int32_t val_mv = buf; - err = adc_raw_to_millivolts_dt(&sense_channel, &val_mv); + err = sensor_channel_get(vdd_dev, SENSOR_CHAN_VOLTAGE, &val); if (err < 0) { - LOG_WRN("Could not convert to millivolts (%d)", err); + LOG_ERR("Could not get channel (%d)", err); + k_sleep(K_MSEC(1000)); + continue; } - LOG_INF("ADC reading raw: %d -> %d mV", buf, val_mv); + LOG_INF("Voltage reading: %d.%06d V", val.val1, val.val2); k_sleep(K_MSEC(1000)); } diff --git a/software/apps/adc_test/CMakeLists.txt b/software/apps/adc_test/CMakeLists.txt new file mode 100644 index 0000000..e8285b1 --- /dev/null +++ b/software/apps/adc_test/CMakeLists.txt @@ -0,0 +1,6 @@ +cmake_minimum_required(VERSION 3.20) + +find_package(Zephyr REQUIRED HINTS $ENV{ZEPHYR_BASE}) +project(adc_test) + +target_sources(app PRIVATE src/main.c) diff --git a/software/apps/adc_test/boards/weact_stm32g431_core.overlay b/software/apps/adc_test/boards/weact_stm32g431_core.overlay index fb73dd3..6cf1e80 100644 --- a/software/apps/adc_test/boards/weact_stm32g431_core.overlay +++ b/software/apps/adc_test/boards/weact_stm32g431_core.overlay @@ -1,31 +1,8 @@ -/ { - zephyr,user { - io-channels = <&adc1 1>; - io-channel-names = "multisense"; - }; -}; - &adc1 { - #address-cells = <1>; - #size-cells = <0>; - status = "okay"; - st,adc-clock-source = "SYNC"; - st,adc-prescaler = <4>; pinctrl-0 = <&adc1_in1_pa0>; pinctrl-names = "default"; + status = "okay"; - channel@1 { - reg = <1>; - zephyr,gain = "ADC_GAIN_1"; - zephyr,reference = "ADC_REF_INTERNAL"; - zephyr,acquisition-time = ; - zephyr,resolution = <12>; - zephyr,vref-mv = <3300>; - }; + st,adc-clock-source = "SYNC"; + st,adc-prescaler = <4>; }; - -&pinctrl { - adc1_in1_pa0: adc1_in1_pa0 { - pinmux = ; - }; -}; \ No newline at end of file diff --git a/software/apps/adc_test/src/main.c b/software/apps/adc_test/src/main.c index bd57c7c..791e0f8 100644 --- a/software/apps/adc_test/src/main.c +++ b/software/apps/adc_test/src/main.c @@ -1,62 +1,73 @@ -/* - * Copyright (c) 2024 Your Name - * - * SPDX-License-Identifier: Apache-2.0 - */ - #include #include -#include +#include +#include -LOG_MODULE_REGISTER(adc_test, LOG_LEVEL_DBG); +// ADC-Knoten holen +static const struct device *adc_dev = DEVICE_DT_GET(DT_NODELABEL(adc1)); -#if !DT_NODE_EXISTS(DT_PATH(zephyr_user)) -#error "zephyr,user node not found" -#endif +// Kanaldefinitionen +#define MY_SIGNAL_CHANNEL 1 // PA0 +#define ADC_VREFINT_CHANNEL 18 // Intern -static const struct adc_dt_spec adc_channel = ADC_DT_SPEC_GET_BY_NAME(DT_PATH(zephyr_user), multisense); +// Puffer für ZWEI Messwerte +static int16_t sample_buffer[2]; -int main(void) +void main(void) { - int err; + int err; + // Die VREFINT-Spannung in mV aus dem Datenblatt deines Controllers + #define VREFINT_MV 1212 - if (!device_is_ready(adc_channel.dev)) { - LOG_ERR("ADC device not found: %s", adc_channel.dev->name); - return 0; - } + printk("*** ADC Ratiometric Measurement (Single Sequence) ***\n"); - err = adc_channel_setup_dt(&adc_channel); - if (err < 0) { - LOG_ERR("Could not setup channel #%d, error %d", adc_channel.channel_id, err); - return 0; - } + if (!device_is_ready(adc_dev)) { + printk("ADC device not ready!\n"); + return; + } - while (1) { - int16_t buffer[1]; - struct adc_sequence sequence = { - .channels = BIT(adc_channel.channel_id), - .buffer = buffer, - .buffer_size = sizeof(buffer), - .resolution = adc_channel.resolution, - .calibrate = true, - }; + // --- Einmaliges Setup der beiden Kanäle --- + const struct adc_channel_cfg signal_channel_cfg = { + .gain = ADC_GAIN_1, + .reference = ADC_REF_INTERNAL, + .acquisition_time = ADC_ACQ_TIME_DEFAULT, // Kurz für niederohmige Quellen + .channel_id = MY_SIGNAL_CHANNEL, + }; + const struct adc_channel_cfg vrefint_channel_cfg = { + .gain = ADC_GAIN_1, + .reference = ADC_REF_INTERNAL, + .acquisition_time = ADC_ACQ_TIME_MAX, // Lang für VREFINT + .channel_id = ADC_VREFINT_CHANNEL, + }; - err = adc_read(adc_channel.dev, &sequence); - if (err < 0) { - LOG_ERR("Could not read ADC, error %d", err); - continue; - } + adc_channel_setup(adc_dev, &signal_channel_cfg); + adc_channel_setup(adc_dev, &vrefint_channel_cfg); - int32_t millivolts = buffer[0]; - err = adc_raw_to_millivolts_dt(&adc_channel, &millivolts); - if (err < 0) { - LOG_ERR("Could not convert to millivolts (%d)", err); - continue; - } + // --- EINE Sequenz, die BEIDE Kanäle enthält --- + const struct adc_sequence sequence = { + .channels = BIT(MY_SIGNAL_CHANNEL) | BIT(ADC_VREFINT_CHANNEL), + .buffer = sample_buffer, + .buffer_size = sizeof(sample_buffer), + .resolution = 12, + }; - LOG_INF("ADC raw: %d, mV: %d", buffer[0], millivolts); + while (1) { + err = adc_read(adc_dev, &sequence); + if (err != 0) { + printk("ADC read failed with code %d\n", err); + } else { + // Die Ergebnisse sind in der Reihenfolge der Kanalnummern im Puffer + // Kanal 1 (MY_SIGNAL_CHANNEL) kommt vor Kanal 18 (ADC_VREFINT_CHANNEL) + int16_t signal_raw = sample_buffer[0]; + int16_t vrefint_raw = sample_buffer[1]; - k_msleep(500); - } - return 0; -} \ No newline at end of file + // Ratiometrische Berechnung + int32_t signal_mv = (int32_t)signal_raw * VREFINT_MV / vrefint_raw; + + printk("Signal: raw=%4d | VREFINT: raw=%4d | Calculated Voltage: %d mV\n", + signal_raw, vrefint_raw, signal_mv); + } + + k_msleep(2000); + } +} diff --git a/software/apps/adc_test/src/main.c2 b/software/apps/adc_test/src/main.c2 new file mode 100644 index 0000000..2a6387a --- /dev/null +++ b/software/apps/adc_test/src/main.c2 @@ -0,0 +1,80 @@ +#include +#include +#include + +// Definiere die Kanäle +#define ADC_VREFINT_CHANNEL 18 // Muss mit dem DTS übereinstimmen +#define MY_SIGNAL_CHANNEL 1 // Muss mit dem pinctrl im DTS übereinstimmen + +// ADC Device +static const struct device *adc_dev = DEVICE_DT_GET(DT_NODELABEL(adc1)); + +// ADC Kanal Konfigurationen +static const struct adc_channel_cfg vrefint_channel_cfg = { + .gain = ADC_GAIN_1, + .reference = ADC_REF_INTERNAL, // Bedeutet VDDA + .acquisition_time = ADC_ACQ_TIME_MAX, + .channel_id = ADC_VREFINT_CHANNEL, + .differential = 0, +}; + +static const struct adc_channel_cfg signal_channel_cfg = { + .gain = ADC_GAIN_1, + .reference = ADC_REF_INTERNAL, // Bedeutet VDDA + .acquisition_time = ADC_ACQ_TIME_MAX, + .channel_id = MY_SIGNAL_CHANNEL, + .differential = 0, +}; + +// Puffer für die Messwerte +#define BUFFER_SIZE 1 +static int16_t sample_buffer[BUFFER_SIZE]; + +// Sequenz für die Messungen +struct adc_sequence sequence_vrefint = { + .channels = BIT(ADC_VREFINT_CHANNEL), + .buffer = sample_buffer, + .buffer_size = sizeof(sample_buffer), + .resolution = 12, // STM32G4 hat 12-bit +}; + +struct adc_sequence sequence_signal = { + .channels = BIT(MY_SIGNAL_CHANNEL), + .buffer = sample_buffer, + .buffer_size = sizeof(sample_buffer), + .resolution = 12, +}; + + +void main(void) { + if (!device_is_ready(adc_dev)) { + printk("ADC device not found\n"); + return; + } + + // Kanäle konfigurieren + adc_channel_setup(adc_dev, &vrefint_channel_cfg); + adc_channel_setup(adc_dev, &signal_channel_cfg); + + while (1) { + // 1. VREFINT messen zur Kalibrierung + adc_read(adc_dev, &sequence_vrefint); + int16_t vrefint_raw = sample_buffer[0]; + + // 2. Dein eigentliches Signal messen + adc_read(adc_dev, &sequence_signal); + int16_t signal_raw = sample_buffer[0]; + + // 3. Spannung berechnen + // VREFINT Wert für STM32G431 bei 3.0V Vdda ist typ. 1.212V (1212 mV) + // Überprüfe den genauen Wert im Datenblatt für deinen Controller! + #define VREFINT_MV 1212 + + int32_t signal_mv = (int32_t)signal_raw * VREFINT_MV / vrefint_raw; + + printk("VREFINT raw: %d, Signal raw: %d, Calculated Voltage: %d mV\n", + vrefint_raw, signal_raw, signal_mv); + + k_msleep(1000); + } +} diff --git a/software/apps/adc_test/src/main.tabby b/software/apps/adc_test/src/main.tabby new file mode 100644 index 0000000..6210ca5 --- /dev/null +++ b/software/apps/adc_test/src/main.tabby @@ -0,0 +1,38 @@ +#include +#include + +#define PA0_PIN 0x04 +#define ADC_CHANNEL 0x03 + +int main(void) { + int16_t adc_value = 0; + + // Initialize the ADC + adc_config_t adc_config; + adc_config.mode = ADC_MODE_SINGLE_SHOT; + adc_config.channel = ADC_CHANNEL_PA0; + adc_config.sampling_rate = ADC_SAMP_RATE_1MS; + + adc_config.data_rate = ADC_DATA_RATE_4MS; + adc_config.aux = ADC_AUX_ALL; + + adc_config.atten = ADC_ATTEN_DB_11; + adc_config.ref = ADC_REF_INTERNAL; + + adc_config.cal = ADC_CAL_ALL; + + if (adc_config_data(&adc_config, &adc_context) < 0) { + zephyr_printf("Failed to configure ADC\n"); + return -1; + } + + // Read the analog input value + if (adc_read(&adc_context, &adc_value) < 0) { + zephyr_printf("Failed to read ADC value\n"); + return -1; + } + + zephyr_printf("ADC Value: %d\n", adc_value); + + return 0; +} diff --git a/software/apps/slave_node/boards/weact_stm32g431_core.overlay b/software/apps/slave_node/boards/weact_stm32g431_core.overlay index 5657198..79f8e74 100644 --- a/software/apps/slave_node/boards/weact_stm32g431_core.overlay +++ b/software/apps/slave_node/boards/weact_stm32g431_core.overlay @@ -25,10 +25,10 @@ &adc1 { status = "okay"; - pinctrl-0 = <&adc1_in1_pa0>; + pinctrl-0 = <&adc1_in1_pa0 &adc1_in15_pb0>; pinctrl-names = "default"; st,adc-clock-source = "SYNC"; - st,adc-prescaler = <4>; + st,adc-prescaler = <1>; #address-cells = <1>; #size-cells = <0>; @@ -36,9 +36,18 @@ reg = <1>; zephyr,gain = "ADC_GAIN_1"; zephyr,reference = "ADC_REF_INTERNAL"; + zephyr,acquisition-time = ; // Use maximum acquisition time for stability + zephyr,resolution = <12>; + zephyr,vref-mv = <2048>; // STM32G431 VREFBUF at 2.048V + }; + + channel@15 { + reg = <15>; + zephyr,gain = "ADC_GAIN_1"; + zephyr,reference = "ADC_REF_INTERNAL"; zephyr,acquisition-time = ; zephyr,resolution = <12>; - zephyr,vref-mv = <3300>; + zephyr,vref-mv = <2048>; // STM32G431 VREFBUF at 2.048V }; }; @@ -47,4 +56,9 @@ adc1_in1_pa0: adc1_in1_pa0 { pinmux = ; // PA0 in den Analogmodus setzen }; + + // Pinmux für PB0 als ADC1_IN15 (Analogmodus) - for lab supply testing + adc1_in15_pb0: adc1_in15_pb0 { + pinmux = ; // PB0 in den Analogmodus setzen + }; }; \ No newline at end of file diff --git a/software/apps/slave_node/src/main.c b/software/apps/slave_node/src/main.c index 058c8ae..25213c0 100644 --- a/software/apps/slave_node/src/main.c +++ b/software/apps/slave_node/src/main.c @@ -23,9 +23,12 @@ int main(void) return 0; } - // Test supply voltage reading - uint16_t supply_voltage = valve_get_supply_voltage(); - LOG_INF("Supply voltage: %u mV", supply_voltage); + // Test supply voltage reading periodically + while (1) { + uint16_t supply_voltage = valve_get_supply_voltage(); + LOG_INF("Supply voltage: %u mV", supply_voltage); + k_msleep(5000); // Read every 5 seconds + } LOG_INF("Irrigation System Slave Node started successfully"); return 0; diff --git a/software/lib/valve/valve.c b/software/lib/valve/valve.c index 24b7dc2..51b2276 100644 --- a/software/lib/valve/valve.c +++ b/software/lib/valve/valve.c @@ -12,9 +12,10 @@ LOG_MODULE_REGISTER(valve, LOG_LEVEL_DBG); static const struct device *adc_dev = DEVICE_DT_GET(DT_NODELABEL(adc1)); static const struct adc_channel_cfg adc_channel_cfg = { .gain = ADC_GAIN_1, - .reference = ADC_REF_INTERNAL, - .acquisition_time = ADC_ACQ_TIME_DEFAULT, + .reference = ADC_REF_INTERNAL, // STM32 only supports internal ref (1.2V) + .acquisition_time = ADC_ACQ_TIME_DEFAULT, // Use default acquisition time .channel_id = 1, // ADC1_IN1 (PA0) + .differential = 0, }; static const struct valve_gpios valve_gpios = { @@ -112,15 +113,34 @@ uint16_t valve_get_motor_current(void) { return (current_movement != VALVE_MOVEM uint16_t valve_get_supply_voltage(void) { - LOG_DBG("Starting supply voltage measurement"); + LOG_INF("=== ADC TEST MODE - PA0 LAB SUPPLY TEST ==="); + LOG_INF("Connect lab supply to PA0. Recommended: 1.0V"); + LOG_INF("Expected raw value for 1.0V: ~2007 (using 2.048V VREFBUF)"); + LOG_INF("ADC range: 0-2.048V (STM32G431 VREFBUF internal reference)"); + LOG_INF(""); - // Ensure VND7050AJ is enabled (RST=HIGH) - LOG_DBG("Enabling VND7050AJ (RST=1)"); - gpio_pin_set_dt(&valve_gpios.rst, 1); + // No VND7050AJ configuration - pure ADC test + // Just make sure pins are in safe state + gpio_pin_configure_dt(&valve_gpios.rst, GPIO_OUTPUT); + gpio_pin_configure_dt(&valve_gpios.sen, GPIO_OUTPUT); + gpio_pin_configure_dt(&valve_gpios.s0, GPIO_OUTPUT); + gpio_pin_configure_dt(&valve_gpios.s1, GPIO_OUTPUT); + gpio_pin_configure_dt(&valve_gpios.in0, GPIO_OUTPUT); + gpio_pin_configure_dt(&valve_gpios.in1, GPIO_OUTPUT); - // Wait for VND7050AJ to power up and stabilize - k_msleep(50); + // Set all VND7050AJ pins LOW for safety + gpio_pin_set_dt(&valve_gpios.rst, 0); + gpio_pin_set_dt(&valve_gpios.s0, 0); + gpio_pin_set_dt(&valve_gpios.s1, 0); + gpio_pin_set_dt(&valve_gpios.sen, 0); + gpio_pin_set_dt(&valve_gpios.in0, 0); + gpio_pin_set_dt(&valve_gpios.in1, 0); + LOG_INF("VND7050AJ disabled - all pins LOW"); + LOG_INF("PA0 is now isolated for lab supply testing"); + k_msleep(100); + + // Setup simple ADC sequence int16_t buf; struct adc_sequence sequence = { .buffer = &buf, @@ -129,47 +149,65 @@ uint16_t valve_get_supply_voltage(void) .resolution = 12, }; - // Configure VND7050AJ to output supply voltage on MULTISENSE - // According to VND7050AJ datasheet page 20: - // S0=1, S1=1: Supply voltage sensing mode - LOG_DBG("Setting S0=1, S1=1 for supply voltage sensing"); - gpio_pin_set_dt(&valve_gpios.s0, 1); - gpio_pin_set_dt(&valve_gpios.s1, 1); + LOG_INF("Starting continuous ADC readings every 500ms..."); - // Enable sensing - LOG_DBG("Enabling MULTISENSE (SEN=1)"); - gpio_pin_set_dt(&valve_gpios.sen, 1); + // Continuous monitoring loop with improved stability + int reading_count = 0; + int32_t samples[10]; // Buffer for averaging - // Wait for voltage to stabilize - k_msleep(10); - - // Read ADC value - LOG_DBG("Reading ADC channel %d", adc_channel_cfg.channel_id); - int ret = adc_read(adc_dev, &sequence); - if (ret < 0) { - LOG_ERR("Could not read ADC (%d)", ret); - gpio_pin_set_dt(&valve_gpios.sen, 0); - return 0; + while (1) { + // Take multiple samples and average them for stability + int valid_samples = 0; + int32_t sum = 0; + + for (int i = 0; i < 10; i++) { + k_msleep(50); // Longer delay between samples for stability + int adc_ret = adc_read(adc_dev, &sequence); + + if (adc_ret == 0 && buf > 100) { // Filter out near-zero readings (floating input) + samples[i] = buf; + sum += buf; + valid_samples++; + } else { + LOG_WRN("Sample %d invalid: raw=%d, ret=%d", i, buf, adc_ret); + samples[i] = 0; // Mark as invalid + } + } + + if (valid_samples > 0) { + // Calculate average + int32_t avg_raw = sum / valid_samples; + + // Calculate voltage using the correct VREFBUF reference (2.048V) + int32_t pa0_mv = (avg_raw * 2048) / 4096; // Using 2.048V VREFBUF + + // Calculate standard deviation to show stability + int32_t variance = 0; + for (int i = 0; i < valid_samples; i++) { + int32_t diff = samples[i] - avg_raw; + variance += diff * diff; + } + int32_t std_dev = (valid_samples > 1) ? variance / (valid_samples - 1) : 0; + + // Find min/max for this sample set + int32_t min_raw = samples[0], max_raw = samples[0]; + for (int i = 1; i < valid_samples; i++) { + if (samples[i] < min_raw) min_raw = samples[i]; + if (samples[i] > max_raw) max_raw = samples[i]; + } + + LOG_INF("Reading %d: avg_raw=%d (%dmV) | range=%d-%d | std_dev=%d | samples=%d/10", + reading_count, (int)avg_raw, (int)pa0_mv, + (int)min_raw, (int)max_raw, (int)std_dev, valid_samples); + } else { + LOG_ERR("Reading %d: All ADC samples failed", reading_count); + } + + reading_count++; + k_msleep(400); // Wait before next reading set } - // Disable sensing to save power - LOG_DBG("Disabling MULTISENSE (SEN=0)"); - gpio_pin_set_dt(&valve_gpios.sen, 0); - - // Convert ADC value to millivolts - // VDD = 3.3V, ADC resolution = 12-bit (4096 steps) - // ADC voltage = (buf / 4096) * 3300 mV - int32_t val_mv = ((int32_t)buf * 3300) / 4096; - - // VND7050AJ MULTISENSE voltage divider: - // According to datasheet page 35, MULTISENSE = VCC / 8 (8:1 voltage divider) - // So actual supply voltage = MULTISENSE * 8 - uint16_t supply_voltage_mv = (uint16_t)(val_mv * 8); - - LOG_INF("Supply voltage: %u mV (ADC raw: %d, ADC mV: %d)", - supply_voltage_mv, buf, (int)val_mv); - - return supply_voltage_mv; + return 0; // Never reached } void valve_set_max_open_time(uint16_t seconds) { max_opening_time_s = seconds; settings_save_one("valve/max_open_time", &max_opening_time_s, sizeof(max_opening_time_s)); } diff --git a/software/serial_monitor.py b/software/serial_monitor.py index 3692545..cfdd62d 100644 --- a/software/serial_monitor.py +++ b/software/serial_monitor.py @@ -2,12 +2,13 @@ import serial import time import sys +import argparse -def monitor_serial(): +def monitor_serial(port): try: # Open serial connection - ser = serial.Serial('/dev/ttyACM3', 115200, timeout=1) - print("Connected to /dev/ttyACM3") + ser = serial.Serial(port, 115200, timeout=1) + print(f"Connected to {port}") # Send reset command ser.write(b'reset\n') @@ -18,7 +19,7 @@ def monitor_serial(): # Read output for 10 seconds start_time = time.time() - while time.time() - start_time < 10: + while 1: #time.time() - start_time < 10: if ser.in_waiting > 0: data = ser.read(ser.in_waiting) try: @@ -36,4 +37,7 @@ def monitor_serial(): sys.exit(1) if __name__ == "__main__": - monitor_serial() + parser = argparse.ArgumentParser(description='Serial monitor.') + parser.add_argument('-p', '--port', help='Serial port to connect to', required=True) + args = parser.parse_args() + monitor_serial(args.port) diff --git a/software/serial_reset_monitor.py b/software/serial_reset_monitor.py index e7ad34b..f8cc6a5 100644 --- a/software/serial_reset_monitor.py +++ b/software/serial_reset_monitor.py @@ -6,7 +6,7 @@ import sys def monitor_serial_with_reset(): try: # Open serial port - ser = serial.Serial('/dev/ttyACM3', 115200, timeout=1) + ser = serial.Serial('/dev/ttyACM1', 115200, timeout=1) print("Serial port opened successfully") # Clear any existing data