laforge has submitted this change. ( 
https://gerrit.osmocom.org/c/libosmocore/+/35022?usp=email )

Change subject: soft_uart: rework osmo_uart_rx_bit() to use flow state
......................................................................

soft_uart: rework osmo_uart_rx_bit() to use flow state

Change-Id: I40ab5d12b6f7087daa51405468f5c4ea639561ea
Related: OS#4396
---
M src/core/soft_uart.c
1 file changed, 55 insertions(+), 38 deletions(-)

Approvals:
  laforge: Looks good to me, approved
  Jenkins Builder: Verified
  jolly: Looks good to me, but someone else must approve




diff --git a/src/core/soft_uart.c b/src/core/soft_uart.c
index 5b58848..c7c8020 100644
--- a/src/core/soft_uart.c
+++ b/src/core/soft_uart.c
@@ -26,6 +26,14 @@
 #include <osmocom/core/timer.h>
 #include <osmocom/core/soft_uart.h>

+/*! Rx/Tx flow state of a soft-UART */
+enum suart_flow_state {
+       SUART_FLOW_ST_IDLE,     /*!< waiting for a start bit or Tx data */
+       SUART_FLOW_ST_DATA,     /*!< receiving/transmitting data bits */
+       SUART_FLOW_ST_PARITY,   /*!< receiving/transmitting parity bits */
+       SUART_FLOW_ST_STOP,     /*!< receiving/transmitting stop bits */
+};
+
 /*! Internal state of a soft-UART */
 struct osmo_soft_uart {
        struct osmo_soft_uart_cfg cfg;
@@ -39,6 +47,7 @@
                unsigned int flags;
                unsigned int status;
                struct osmo_timer_list timer;
+               enum suart_flow_state flow_state;
        } rx;
        struct {
                bool running;
@@ -98,50 +107,46 @@
 /* receive a single bit */
 static inline void osmo_uart_rx_bit(struct osmo_soft_uart *suart, const ubit_t 
bit)
 {
-       unsigned int num_parity_bits = 0;
-
        if (!suart->rx.running)
                return;

-       if (suart->rx.bit_count == 0) {
-               /* start bit is 0.  Wait if there is none */
-               if (bit == 0) {
-                       /* START bit */
-                       suart->rx.flags = 0;
+       switch (suart->rx.flow_state) {
+       case SUART_FLOW_ST_IDLE:
+               if (bit == 0) { /* start bit condition */
+                       suart->rx.flow_state = SUART_FLOW_ST_DATA;
+                       suart->rx.flags = 0x00;
                        suart->rx.shift_reg = 0;
-                       suart->rx.bit_count++;
-               }
-               return;
-       }
-
-       if (suart->cfg.parity_mode != OSMO_SUART_PARITY_NONE)
-               num_parity_bits = 1;
-
-       suart->rx.bit_count++;
-       if (suart->rx.bit_count <= 1 + suart->cfg.num_data_bits) {
-               /* DATA bit */
-               suart->rx.shift_reg = suart->rx.shift_reg >> 1;
-               if (bit)
-                       suart->rx.shift_reg |= 0x80;
-       } else if (suart->cfg.parity_mode != OSMO_SUART_PARITY_NONE &&
-                  suart->rx.bit_count == 1 + suart->cfg.num_data_bits + 1) {
-               /* PARITY bit */
-               suart->rx.parity_bit = bit;
-               /* TODO: verify parity */
-               //suart->rx.flags |= OSMO_SUART_F_PARITY_ERROR;
-       } else if (suart->rx.bit_count <=
-                  1 + suart->cfg.num_data_bits + num_parity_bits + 
suart->cfg.num_stop_bits) {
-               /* STOP bit */
-               if (bit != 1) {
-                       fprintf(stderr, "framing error: stop bit %u != 1\n", 
suart->rx.bit_count);
-                       suart->rx.flags |= OSMO_SUART_F_FRAMING_ERROR;
-               }
-
-               if (suart->rx.bit_count == 1 + suart->cfg.num_data_bits + 
num_parity_bits + suart->cfg.num_stop_bits) {
-                       //printf("Rx: 0x%02x %c\n", suart->rx.shift_reg, 
suart->rx.shift_reg);
-                       suart_rx_ch(suart, suart->rx.shift_reg);
                        suart->rx.bit_count = 0;
                }
+               break;
+       case SUART_FLOW_ST_DATA:
+               suart->rx.bit_count++;
+               suart->rx.shift_reg >>= 1;
+               if (bit != 0)
+                       suart->rx.shift_reg |= 0x80;
+               if (suart->rx.bit_count >= suart->cfg.num_data_bits) {
+                       /* we have accumulated enough data bits */
+                       if (suart->cfg.parity_mode != OSMO_SUART_PARITY_NONE)
+                               suart->rx.flow_state = SUART_FLOW_ST_PARITY;
+                       else
+                               suart->rx.flow_state = SUART_FLOW_ST_STOP;
+               }
+               break;
+       case SUART_FLOW_ST_PARITY:
+               /* TODO: actually verify parity */
+               suart->rx.flow_state = SUART_FLOW_ST_STOP;
+               break;
+       case SUART_FLOW_ST_STOP:
+               suart->rx.bit_count++;
+               if (bit != 1)
+                       suart->rx.flags |= OSMO_SUART_F_FRAMING_ERROR;
+
+               if (suart->rx.bit_count >= (suart->cfg.num_data_bits + 
suart->cfg.num_stop_bits)) {
+                       /* we have accumulated enough stop bits */
+                       suart_rx_ch(suart, suart->rx.shift_reg);
+                       suart->rx.flow_state = SUART_FLOW_ST_IDLE;
+               }
+               break;
        }
 }

@@ -291,10 +296,12 @@
        if (!enable && suart->rx.running) {
                suart_flush_rx(suart);
                suart->rx.running = false;
+               suart->rx.flow_state = SUART_FLOW_ST_IDLE;
        } else if (enable && !suart->rx.running) {
                if (!suart->rx.msg)
                        suart->rx.msg = msgb_alloc_c(suart, 
suart->cfg.rx_buf_size, "soft_uart rx");
                suart->rx.running = true;
+               suart->rx.flow_state = SUART_FLOW_ST_IDLE;
        }

        return 0;

--
To view, visit https://gerrit.osmocom.org/c/libosmocore/+/35022?usp=email
To unsubscribe, or for help writing mail filters, visit 
https://gerrit.osmocom.org/settings

Gerrit-Project: libosmocore
Gerrit-Branch: master
Gerrit-Change-Id: I40ab5d12b6f7087daa51405468f5c4ea639561ea
Gerrit-Change-Number: 35022
Gerrit-PatchSet: 4
Gerrit-Owner: fixeria <vyanits...@sysmocom.de>
Gerrit-Reviewer: Jenkins Builder
Gerrit-Reviewer: jolly <andr...@eversberg.eu>
Gerrit-Reviewer: laforge <lafo...@osmocom.org>
Gerrit-MessageType: merged

Reply via email to