From 9d4080f7317fe9781c87671f06365a8c33bfa9c2 Mon Sep 17 00:00:00 2001 From: Thomas Petig Date: Sat, 29 Jun 2024 01:47:42 +0200 Subject: [PATCH] switch to modbus client, crc still failing --- include/modbus.hpp | 9 ----- include/modbusslave.hpp | 75 +++++++++++++++++++++++++++++++++++------ src/main.cpp | 46 +++++++++++++------------ 3 files changed, 89 insertions(+), 41 deletions(-) diff --git a/include/modbus.hpp b/include/modbus.hpp index 2fbd2b2..e0505ac 100644 --- a/include/modbus.hpp +++ b/include/modbus.hpp @@ -59,15 +59,6 @@ uint8_t tx_arr_crc(uart_inst_t* uartid, const uint8_t* ptr, int len) { crc = crc_update (crc, ptr, len); crc = crc_finalize(crc); -#if 0 - for (int i = 0; i < len; i++) { - printf("%x,", (int)ptr[i]); - } - printf("%x,", crc & 0xFF); - printf("%x,", (crc >> 8) & 0xFF); - printf("\r\n"); -#endif - uart_write_blocking(uartid, ptr, len); uart_putc(uartid, lsb(crc)); uart_putc(uartid, msb(crc)); diff --git a/include/modbusslave.hpp b/include/modbusslave.hpp index 1c5ea7f..d6c4fb4 100644 --- a/include/modbusslave.hpp +++ b/include/modbusslave.hpp @@ -49,7 +49,7 @@ void on_modbus_timeout(unsigned int alarm_num) { } constexpr int alarm_modbusslave = 1; -template< int UART, int TX, int RX, int TXEN, int RXEN > +template< int UART, int TX, int RX, int DE, int RE > class Slave { public: Slave() {} @@ -59,42 +59,69 @@ class Slave { gpio_set_function(TX, GPIO_FUNC_UART); gpio_set_function(RX, GPIO_FUNC_UART); uart_init(uart_id(), baud); - uart_set_fifo_enabled(uart_id(), false); - uart_set_hw_flow(uart_id(), false, false); + + gpio_init(RE); + gpio_set_dir(RE, GPIO_OUT); + gpio_init(DE); + gpio_set_dir(DE, GPIO_OUT); + rx_enable(); hardware_alarm_claim(alarm_modbusslave); - hardware_alarm_set_callback(alarm_modbusslave, &on_timeout); + hardware_alarm_set_callback(alarm_modbusslave, &on_modbus_timeout); // Set our data format //uart_set_format(uart_id(), 8, 1, UART_PARITY_NONE); // And set up and enable the interrupt hand - irq_set_exclusive_handler(uart_irq(), on_uart_rx); + irq_set_exclusive_handler(uart_irq(), on_slave_rx); irq_set_enabled(uart_irq(), true); // Now enable the UART to send interrupts - uart_set_irq_enables(uart_id(), true, false); + rx_enable(); return 0; } + /** + ** Enable RX on transceiver. + */ + void rx_enable() { + gpio_put(DE, 0); + gpio_put(RE, 0); + } + + /** + ** Disable transceiver. + */ + void all_disable() { + gpio_put(DE, 0); + gpio_put(RE, 1); + } + + /** + ** Enable TX on transceiver. + */ + void tx_enable() { + gpio_put(RE, 1); + gpio_put(DE, 1); + } /** ** Callback for one byte. */ - static void on_uart_rx() { + static void on_slave_rx() { + led_toggle(LED3_PIN); while (uart_is_readable(uart_id())) { tot_chars_rxed++; uint8_t ch = uart_getc(uart_id()); if (finished) { continue; } - if ((wait_start == 0) && (ch == 0x61)) { -// printf("X%xX\r\n", (int)ch); + if ((wait_start == 0) && (ch == 0x42)) { wait_start = 1; chars_rxed = 0; crc = crc_init(); } -// printf("RX %d-%x,", chars_rxed, (int)ch); raw_buffer[chars_rxed++] = ch; crc = crc_update(crc, &ch, 1); @@ -104,17 +131,33 @@ class Slave { } - if (wait_start == 1 && chars_rxed >= resp_len) { + if (wait_start == 1 && chars_rxed >= 8) { crc = crc_finalize(crc); finished=1; + Request r = {0x42, (function_code)raw_buffer[1], (uint16_t)(raw_buffer[2] << 8 | raw_buffer[3])}; + queue_try_add(&request_queue, &r); } } last_rx = get_absolute_time(); absolute_time_t to = delayed_by_us(last_rx, MODBUS_INTERFRAME_DELAY); - hardware_alarm_set_target(alarm_scd30, to); + hardware_alarm_set_target(alarm_modbusslave, to); } + int send_holding(uint8_t func, uint8_t size, uint8_t* data) + { + tx_enable(); + sleep_ms(20); + uint8_t d[32] = {0x42, func}; + for (int i = 0; i < size; i++) { + d[i+3] = data[i]; + } + + tx_arr_crc(uart_id(), d, size+3); + sleep_ms(20); + rx_enable(); + return 1; + } /** ** Check the CRC of the response. ** @@ -123,7 +166,17 @@ class Slave { int check_crc() { return crc == 0; } + int check_resp() { + if (finished && timeout) { + return check_crc(); + } else { + return 0; + } + } + void clear() { + clear_state(); + } private: diff --git a/src/main.cpp b/src/main.cpp index 8764b6e..50553a4 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -36,23 +36,34 @@ queue_t res_queue; void core1_entry() { + gpio_put(LED3_PIN, 1); watchdog_enable(5000,1); led_init(LED0_PIN); - printf("booting core 1\r\n"); gpio_put(LED0_PIN, 1); sleep_ms(1000); gpio_put(LED0_PIN, 0); measurement_t meas; + MODBUSSlave::Slave< 0, UART0_TX_PIN, UART0_RX_PIN, UART0_DE_PIN, UART0_RE_PIN> slave; + slave.init(); + slave.clear(); + gpio_put(LED3_PIN, 0); + uint8_t reg[16]; + for (int i = 0; i < 16; i++) { + reg[i] = 0; + } while(1) { - queue_remove_blocking(&res_queue, &meas); - led_toggle(LED0_PIN); - modbus_tx_enable(); - print_meas(meas); - printf("\r\n"); - printf("\r\n"); - sleep_ms(20); - watchdog_update(); - modbus_rx_enable(); + if(queue_try_remove(&res_queue, &meas)) { + led_toggle(LED1_PIN); +// print_meas(meas); + watchdog_update(); + } + MODBUSSlave::Request r; + if (queue_try_remove(&MODBUSSlave::request_queue, &r)) { + gpio_put(LED0_PIN, 1); + slave.clear(); + slave.send_holding(r.func, r.size * 2, reg); + gpio_put(LED0_PIN, 0); + } } } @@ -63,8 +74,7 @@ int main() { adc_gpio_init(26); adc_gpio_init(29); - modbus_init(); - printf("REBOOT\r\n"); + // modbus_init(); led_init(LED1_PIN); led_init(LED2_PIN); @@ -78,7 +88,6 @@ int main() { scd.init(); gpio_put(LED1_PIN, 1); - printf("UART1 initialised\r\n"); sleep_ms(1000); @@ -89,19 +98,15 @@ int main() { sleep_ms(1000); scd.txContStart(); scd.check_resp(); - printf("continous measurement startet\r\n"); - gpio_put(LED3_PIN, 1); measurement_t measurement; multicore_reset_core1(); multicore_launch_core1(&core1_entry); while (true) { - led_toggle(LED2_PIN); - gpio_put(LED1_PIN, 1); + gpio_put(LED2_PIN, 1); scd.txMeas(); - gpio_put(LED1_PIN, 0); - led_toggle(LED3_PIN); + gpio_put(LED2_PIN, 0); sleep_ms(2000); // scd.printMeas(false);//true); //scd.printStatus(); @@ -111,8 +116,7 @@ int main() { measurement.v_sys = adc_read_V(ADC_SYS); queue_try_add(&res_queue, &measurement); } else { - printf("ERROR\r\n"); - scd.printStatus(); + //scd.printStatus(); } } }