diff --git a/software/CMakeLists.txt b/software/CMakeLists.txt index 5472451..9c0441f 100644 --- a/software/CMakeLists.txt +++ b/software/CMakeLists.txt @@ -2,24 +2,13 @@ cmake_minimum_required(VERSION 3.20.0) +# This line should ideally be after project() and find_package(Zephyr) +# target_include_directories(app PRIVATE ${ZEPHYR_BASE}/include/zephyr/drivers) # <-- WRONG POSITION + list(APPEND BOARD_ROOT ${CMAKE_CURRENT_SOURCE_DIR}) find_package(Zephyr REQUIRED HINTS $ENV{ZEPHYR_BASE}) project(valve_node) -target_sources(app PRIVATE src/main.c) -target_sources(app PRIVATE lib/canbus.c) - -# source files for modbus waterlevel sensor -zephyr_library_sources_ifdef(CONFIG_HAS_MODBUS_WATERLEVEL_SENSOR - lib/waterlevel_sensor.c -) - -#source files for valve -zephyr_library_sources_ifdef(CONFIG_HAS_VALVE - lib/valve.c -) - -zephyr_include_directories( - lib -) +target_include_directories(app PRIVATE ${ZEPHYR_BASE}/include/zephyr/drivers) +target_sources(app PRIVATE src/main2.c) \ No newline at end of file diff --git a/software/CMakeLists.txt.orig b/software/CMakeLists.txt.orig new file mode 100644 index 0000000..5472451 --- /dev/null +++ b/software/CMakeLists.txt.orig @@ -0,0 +1,25 @@ +# SPDX-License-Identifier: Apache-2.0 + +cmake_minimum_required(VERSION 3.20.0) + +list(APPEND BOARD_ROOT ${CMAKE_CURRENT_SOURCE_DIR}) + +find_package(Zephyr REQUIRED HINTS $ENV{ZEPHYR_BASE}) +project(valve_node) + +target_sources(app PRIVATE src/main.c) +target_sources(app PRIVATE lib/canbus.c) + +# source files for modbus waterlevel sensor +zephyr_library_sources_ifdef(CONFIG_HAS_MODBUS_WATERLEVEL_SENSOR + lib/waterlevel_sensor.c +) + +#source files for valve +zephyr_library_sources_ifdef(CONFIG_HAS_VALVE + lib/valve.c +) + +zephyr_include_directories( + lib +) diff --git a/software/boards/iten/valve_node/valve_node.dts b/software/boards/iten/valve_node/valve_node.dts index f1f38ab..528b7cf 100644 --- a/software/boards/iten/valve_node/valve_node.dts +++ b/software/boards/iten/valve_node/valve_node.dts @@ -5,13 +5,14 @@ */ /dts-v1/; +#include #include #include #include / { model = "Iten engineering Valve Node"; - compatible = "iten,valve-node", "st,stm32f103rb"; + compatible = "st,stm32f103rb"; can_loopback0: can_loopback0 { status = "disabled"; @@ -24,7 +25,6 @@ zephyr,sram = &sram0; zephyr,flash = &flash0; zephyr,canbus = &can1; - //zephyr,canbus = &can_loopback0; }; leds: leds { @@ -71,19 +71,10 @@ sw0 = &user_button; watchdog0 = &iwdg; die-temp0 = &die_temp; + adc-motor-current = &motor_current_channel; + adc-vref = &vref_channel; }; - - zephyr,user { - motoropen: motor_open { - gpios = <&gpiob 13 0>; - label = "Motor Open"; - }; - fake: fake { - gpios = <&gpiob 11 GPIO_PULL_UP>; - label = "CAN RX pullup"; - }; - }; }; &clk_lsi { @@ -107,7 +98,7 @@ ahb-prescaler = <1>; apb1-prescaler = <2>; apb2-prescaler = <1>; - adc-prescaler = <2>; + adc-prescaler = <6>; }; &usart1 { @@ -125,7 +116,6 @@ modbus0 { compatible = "zephyr,modbus-serial"; status = "okay"; - //de-gpios = <&gpioa 15 GPIO_ACTIVE_LOW>; }; }; @@ -148,14 +138,33 @@ &rtc { clocks = <&rcc STM32_CLOCK_BUS_APB1 0x10000000>, - <&rcc STM32_SRC_LSI RTC_SEL(2)>; + <&rcc STM32_SRC_LSI RTC_SEL(2)>; status = "okay"; }; &adc1 { - pinctrl-0 = <&adc1_in0_pa0>; + pinctrl-0 = <&adc_pb1_pins>; pinctrl-names = "default"; status = "okay"; + + #address-cells = <1>; + #size-cells = <0>; + + motor_current_channel: channel@9 { + reg = <0x9>; + zephyr,gain = "ADC_GAIN_1"; + zephyr,reference = "ADC_REF_VDD_1"; + zephyr,acquisition-time = <49159>; + zephyr,resolution = <12>; + }; + + vref_channel: channel@11 { /* 17 dezimal = 11 hex */ + reg = <0x11>; + zephyr,gain = "ADC_GAIN_1"; + zephyr,reference = "ADC_REF_VDD_1"; + zephyr,acquisition-time = <49159>; + zephyr,resolution = <12>; + }; }; &die_temp { @@ -172,7 +181,6 @@ #address-cells = <1>; #size-cells = <1>; - /* Set 2KB of storage at the end of 128KB flash */ storage_partition: partition@1f800 { label = "storage"; reg = <0x0001f800 DT_SIZE_K(2)>; @@ -184,9 +192,15 @@ pinctrl-0 = <&can_rx_pa11 &can_tx_pa12>; pinctrl-names = "default"; status= "okay"; - bus-speed = <125000>; + bitrate = <125000>; }; &exti { status = "okay"; }; + +&pinctrl { + adc_pb1_pins: adc_pb1_pins { + pinmux = ; + }; +}; \ No newline at end of file diff --git a/software/prj.conf b/software/prj.conf index f297171..d5705af 100644 --- a/software/prj.conf +++ b/software/prj.conf @@ -14,4 +14,7 @@ CONFIG_UART_CONSOLE=y # Console on USART1 CONFIG_SHELL=y CONFIG_CAN_SHELL=y CONFIG_GPIO_SHELL=y -CONFIG_REBOOT=y \ No newline at end of file +CONFIG_REBOOT=y + +CONFIG_ADC=y +CONFIG_ADC_STM32=y \ No newline at end of file diff --git a/software/src/main2.c b/software/src/main2.c new file mode 100644 index 0000000..42c1b06 --- /dev/null +++ b/software/src/main2.c @@ -0,0 +1,86 @@ +#include +#include +#include +#include +#include +#include + +LOG_MODULE_REGISTER(main2, LOG_LEVEL_DBG); + +#define MOTOR_ADC_NODE DT_ALIAS(adc_motor_current) +#define VREF_ADC_NODE DT_ALIAS(adc_vref) + +static const struct device * const adc_dev = DEVICE_DT_GET(DT_PARENT(MOTOR_ADC_NODE)); +static const uint8_t motor_channel_id = DT_REG_ADDR(MOTOR_ADC_NODE); +static const uint8_t vref_channel_id = DT_REG_ADDR(VREF_ADC_NODE); + +int main(void) +{ + int err; + int16_t adc_raw_value; + + LOG_INF("Starting ADC test with direct register setup..."); + + if (!device_is_ready(adc_dev)) { + LOG_ERR("ADC device is not ready"); + return 0; + } + + LOG_INF("Manually setting up ADC registers..."); + + uint32_t adc_base = DT_REG_ADDR(DT_NODELABEL(adc1)); + + volatile uint32_t *ADC_CR2 = (uint32_t *)(adc_base + 0x08); + volatile uint32_t *ADC_SMPR1 = (uint32_t *)(adc_base + 0x0C); + volatile uint32_t *ADC_SMPR2 = (uint32_t *)(adc_base + 0x10); + + // Schritt 1: Internen VREFINT-Kanal einschalten + const uint32_t ADC_CR2_TSVREFE_BIT = 23; + *ADC_CR2 |= (1 << ADC_CR2_TSVREFE_BIT); + LOG_INF("VREFINT channel enabled via CR2 register."); + + // Schritt 2: Lange Abtastzeiten für Stabilität setzen + *ADC_SMPR2 |= (0b111 << (3 * 9)); + *ADC_SMPR1 |= (0b111 << (3 * (17 - 10))); + LOG_INF("Acquisition times set directly in SMPR registers."); + + + k_busy_wait(10); + + + while (1) { + int32_t motor_raw = 0; + int32_t vref_raw = 0; + + struct adc_sequence sequence = { + .buffer = &adc_raw_value, + .buffer_size = sizeof(adc_raw_value), + .resolution = 12, + }; + + // Motor-Kanal lesen + sequence.channels = BIT(motor_channel_id); + if (adc_read(adc_dev, &sequence) == 0) { + motor_raw = adc_raw_value; + } + + // VREF-Kanal lesen + sequence.channels = BIT(vref_channel_id); + if (adc_read(adc_dev, &sequence) == 0) { + vref_raw = adc_raw_value; + } + + // VDD-Berechnung mit dem generischen, aber für Sie gut funktionierenden 1200mV-Wert + int32_t vdd_mv = (vref_raw > 0) ? (1200 * 4095 / vref_raw) : 0; + int32_t motor_mv = 0; + + if (motor_raw > 0 && vdd_mv > 0) { + motor_mv = motor_raw; + err = adc_raw_to_millivolts(vdd_mv, ADC_GAIN_1, 12, &motor_mv); + } + + LOG_INF("Motor Raw: %4d, Motor mV: %4d | VDD: %4d mV", motor_raw, motor_mv, vdd_mv); + k_sleep(K_MSEC(2000)); + } + return 0; +} \ No newline at end of file