<p>Hoernchen has uploaded this change for <strong>review</strong>.</p><p><a href="https://gerrit.osmocom.org/c/osmo-ccid-firmware/+/16293">View Change</a></p><pre style="font-family: monospace,monospace; white-space: pre-wrap;">first attempt at rx timeout handling<br><br>The general idea is to provide hints to cuart so it can calculate<br>a reasonable timeout value when receiving multiple bytes instead of<br>having per-byte timeouts<br><br>Change-Id: Ia6ad2d83cea48a8661ed2e4eb50f9bcb85218454<br>---<br>M ccid_common/cuart.c<br>M ccid_common/cuart.h<br>M ccid_common/iso7816_fsm.c<br>3 files changed, 143 insertions(+), 29 deletions(-)<br><br></pre><pre style="font-family: monospace,monospace; white-space: pre-wrap;">git pull ssh://gerrit.osmocom.org:29418/osmo-ccid-firmware refs/changes/93/16293/1</pre><pre style="font-family: monospace,monospace; white-space: pre-wrap;"><span>diff --git a/ccid_common/cuart.c b/ccid_common/cuart.c</span><br><span>index 1ae50c6..1d777f9 100644</span><br><span>--- a/ccid_common/cuart.c</span><br><span>+++ b/ccid_common/cuart.c</span><br><span>@@ -49,7 +49,12 @@</span><br><span> {</span><br><span>    int secs, usecs;</span><br><span> </span><br><span style="color: hsl(0, 100%, 40%);">-    usecs = get_etu_in_us(cuart) * cuart->wtime_etu;</span><br><span style="color: hsl(120, 100%, 40%);">+   if(!cuart->current_wtime_byte)</span><br><span style="color: hsl(120, 100%, 40%);">+             return;</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+     /* timemout is wtime * ETU + expected number of bytes * (12ETU+1 slack)ETU */</span><br><span style="color: hsl(120, 100%, 40%);">+ usecs = get_etu_in_us(cuart) * cuart->wtime_etu +</span><br><span style="color: hsl(120, 100%, 40%);">+                  get_etu_in_us(cuart) * cuart->current_wtime_byte * (12+1);</span><br><span>        if (usecs > 1000000) {</span><br><span>            secs = usecs / 1000000;</span><br><span>              usecs = usecs % 1000000;</span><br><span>@@ -108,6 +113,15 @@</span><br><span>              cuart->rx_enabled = arg ? true : false;</span><br><span>           if (!cuart->rx_enabled)</span><br><span>                   osmo_timer_del(&cuart->wtime_tmr);</span><br><span style="color: hsl(120, 100%, 40%);">+//           else</span><br><span style="color: hsl(120, 100%, 40%);">+//                        card_uart_wtime_restart(cuart);</span><br><span style="color: hsl(120, 100%, 40%);">+               break;</span><br><span style="color: hsl(120, 100%, 40%);">+        case CUART_CTL_RX_TIMER_HINT:</span><br><span style="color: hsl(120, 100%, 40%);">+         cuart->current_wtime_byte = arg;</span><br><span style="color: hsl(120, 100%, 40%);">+           if(arg)</span><br><span style="color: hsl(120, 100%, 40%);">+                       card_uart_wtime_restart(cuart);</span><br><span style="color: hsl(120, 100%, 40%);">+               else</span><br><span style="color: hsl(120, 100%, 40%);">+                  osmo_timer_del(&cuart->wtime_tmr);</span><br><span>            break;</span><br><span>       default:</span><br><span>             break;</span><br><span>@@ -158,6 +172,12 @@</span><br><span>                if (cuart->rx_after_tx_compl)</span><br><span>                     card_uart_ctrl(cuart, CUART_CTL_RX, true);</span><br><span>           break;</span><br><span style="color: hsl(120, 100%, 40%);">+//      case CUART_E_RX_COMPLETE:</span><br><span style="color: hsl(120, 100%, 40%);">+//           osmo_timer_del(&cuart->wtime_tmr);</span><br><span style="color: hsl(120, 100%, 40%);">+//           break;</span><br><span style="color: hsl(120, 100%, 40%);">+//      case CUART_E_RX_SINGLE:</span><br><span style="color: hsl(120, 100%, 40%);">+//             card_uart_wtime_restart(cuart);</span><br><span style="color: hsl(120, 100%, 40%);">+//             break;</span><br><span>       default:</span><br><span>             break;</span><br><span>       }</span><br><span>diff --git a/ccid_common/cuart.h b/ccid_common/cuart.h</span><br><span>index 6a782db..1df0c49 100644</span><br><span>--- a/ccid_common/cuart.h</span><br><span>+++ b/ccid_common/cuart.h</span><br><span>@@ -23,6 +23,7 @@</span><br><span> </span><br><span> enum card_uart_ctl {</span><br><span>   CUART_CTL_RX,           /* enable/disable receiver */</span><br><span style="color: hsl(120, 100%, 40%);">+ CUART_CTL_RX_TIMER_HINT, /* tell cuart approximate number of rx bytes */</span><br><span>     CUART_CTL_NO_RXTX,              /* enable/disable receiver */</span><br><span>        CUART_CTL_POWER,        /* enable/disable ICC power */</span><br><span>       CUART_CTL_CLOCK,        /* enable/disable ICC clock */</span><br><span>@@ -78,6 +79,8 @@</span><br><span> </span><br><span>       uint32_t wtime_etu;</span><br><span>  struct osmo_timer_list wtime_tmr;</span><br><span style="color: hsl(120, 100%, 40%);">+     /* expected number of bytes, for timeout */</span><br><span style="color: hsl(120, 100%, 40%);">+   uint32_t current_wtime_byte;</span><br><span> </span><br><span>     /* driver-specific private data */</span><br><span>   union {</span><br><span>diff --git a/ccid_common/iso7816_fsm.c b/ccid_common/iso7816_fsm.c</span><br><span>index 44c8191..412bea7 100644</span><br><span>--- a/ccid_common/iso7816_fsm.c</span><br><span>+++ b/ccid_common/iso7816_fsm.c</span><br><span>@@ -68,14 +68,14 @@</span><br><span>  *  @note defined in ISO/IEC 7816-3:2006(E) section 9</span><br><span>  */</span><br><span> enum pps_state {</span><br><span style="color: hsl(0, 100%, 40%);">-      PPS_S_TX_PPS_REQ,  /*!< tx pps request */</span><br><span style="color: hsl(0, 100%, 40%);">-    PPS_S_WAIT_PPSS, /*!< initial byte */</span><br><span style="color: hsl(120, 100%, 40%);">+      PPS_S_PPS_REQ_INIT,  /*!< tx pps request */</span><br><span style="color: hsl(120, 100%, 40%);">+        PPS_S_TX_PPS_REQ,</span><br><span style="color: hsl(120, 100%, 40%);">+     PPS_S_WAIT_PPSX, /*!< initial byte */</span><br><span>     PPS_S_WAIT_PPS0, /*!< format byte */</span><br><span>      PPS_S_WAIT_PPS1, /*!< first parameter byte */</span><br><span>     PPS_S_WAIT_PPS2, /*!< second parameter byte */</span><br><span>    PPS_S_WAIT_PPS3, /*!< third parameter byte */</span><br><span>     PPS_S_WAIT_PCK, /*!< check byte */</span><br><span style="color: hsl(0, 100%, 40%);">-   PPS_S_WAIT_END, /*!< all done */</span><br><span>  PPS_S_DONE</span><br><span> };</span><br><span> </span><br><span>@@ -219,9 +219,11 @@</span><br><span>  struct iso7816_3_priv *ip = get_iso7816_3_priv(fi);</span><br><span>  OSMO_ASSERT(fi->fsm == &iso7816_3_fsm);</span><br><span> </span><br><span style="color: hsl(120, 100%, 40%);">+    card_uart_ctrl(ip->uart, CUART_CTL_RX_TIMER_HINT, 0);</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span>   /* go back to initial state in child FSMs */</span><br><span>         osmo_fsm_inst_state_chg(ip->atr_fi, ATR_S_WAIT_TS, 0, 0);</span><br><span style="color: hsl(0, 100%, 40%);">-    osmo_fsm_inst_state_chg(ip->pps_fi, PPS_S_TX_PPS_REQ, 0, 0);</span><br><span style="color: hsl(120, 100%, 40%);">+       osmo_fsm_inst_state_chg(ip->pps_fi, PPS_S_PPS_REQ_INIT, 0, 0);</span><br><span>    osmo_fsm_inst_state_chg(ip->tpdu_fi, TPDU_S_INIT, 0, 0);</span><br><span> }</span><br><span> </span><br><span>@@ -235,8 +237,13 @@</span><br><span>  case ISO7816_E_RESET_REL_IND:</span><br><span>                /* TOOD: this should happen before reset is released */</span><br><span>              card_uart_ctrl(ip->uart, CUART_CTL_RX, true);</span><br><span style="color: hsl(0, 100%, 40%);">-                osmo_fsm_inst_state_chg_ms(fi, ISO7816_S_WAIT_ATR,</span><br><span style="color: hsl(0, 100%, 40%);">-                                         fi_cycles2ms(fi, 40000), T_WAIT_ATR);</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+            /* let's be reasonable here: the 40k cycle delay to ATR start is</span><br><span style="color: hsl(120, 100%, 40%);">+           * ~1.4ms @ 2.5Mhz/6720 baud, 1ETU = 372 cycles -> 40k/372=107/12ETU ~ 9 byte</span><br><span style="color: hsl(120, 100%, 40%);">+               * default timeout for rx is 9600 ETU, ATR might be missing the TCK</span><br><span style="color: hsl(120, 100%, 40%);">+            * so it might time out, so just add this delay */</span><br><span style="color: hsl(120, 100%, 40%);">+            card_uart_ctrl(ip->uart, CUART_CTL_RX_TIMER_HINT, 32+9);</span><br><span style="color: hsl(120, 100%, 40%);">+           osmo_fsm_inst_state_chg(fi, ISO7816_S_WAIT_ATR, 0, 0);</span><br><span>               break;</span><br><span>       case ISO7816_E_POWER_UP_IND:</span><br><span>                 break;</span><br><span>@@ -308,6 +315,7 @@</span><br><span> {</span><br><span>    struct iso7816_3_priv *ip = get_iso7816_3_priv(fi);</span><br><span>  OSMO_ASSERT(fi->fsm == &iso7816_3_fsm);</span><br><span style="color: hsl(120, 100%, 40%);">+        card_uart_ctrl(ip->uart, CUART_CTL_RX_TIMER_HINT, 0);</span><br><span>     card_uart_ctrl(ip->uart, CUART_CTL_NO_RXTX, true);</span><br><span>        /* reset the TPDU state machine */</span><br><span>   osmo_fsm_inst_dispatch(ip->tpdu_fi, ISO7816_E_TPDU_CLEAR_REQ, NULL);</span><br><span>@@ -327,7 +335,7 @@</span><br><span>                break;</span><br><span>       case ISO7816_E_XCEIVE_PPS_CMD:</span><br><span>               osmo_fsm_inst_state_chg(fi, ISO7816_S_WAIT_PPS_RSP, 0, 0);</span><br><span style="color: hsl(0, 100%, 40%);">-              osmo_fsm_inst_state_chg(ip->pps_fi, PPS_S_TX_PPS_REQ, 0, 0);</span><br><span style="color: hsl(120, 100%, 40%);">+               osmo_fsm_inst_state_chg(ip->pps_fi, PPS_S_PPS_REQ_INIT, 0, 0);</span><br><span>            osmo_fsm_inst_dispatch(ip->pps_fi, event, data);</span><br><span>          break;</span><br><span>       default:</span><br><span>@@ -391,11 +399,13 @@</span><br><span> </span><br><span> static void iso7816_3_s_wait_pps_rsp_action(struct osmo_fsm_inst *fi, uint32_t event, void *data)</span><br><span> {</span><br><span style="color: hsl(120, 100%, 40%);">+        struct iso7816_3_priv *ip = get_iso7816_3_priv(fi);</span><br><span>  OSMO_ASSERT(fi->fsm == &iso7816_3_fsm);</span><br><span>       switch (event) {</span><br><span>     case ISO7816_E_TX_COMPL:</span><br><span>             /* Rx of single byte is already enabled by previous card_uart_tx() call */</span><br><span>           osmo_fsm_inst_state_chg(fi, ISO7816_S_IN_PPS_RSP, 0, 0);</span><br><span style="color: hsl(120, 100%, 40%);">+              osmo_fsm_inst_dispatch(ip->pps_fi, event, data);</span><br><span>          break;</span><br><span>       default:</span><br><span>             OSMO_ASSERT(0);</span><br><span>@@ -435,6 +445,7 @@</span><br><span>        [ISO7816_S_RESET] = {</span><br><span>                .name = "RESET",</span><br><span>           .in_event_mask =        S(ISO7816_E_RESET_REL_IND) |</span><br><span style="color: hsl(120, 100%, 40%);">+                                                  S(ISO7816_E_POWER_UP_IND) |</span><br><span>                                                  S(ISO7816_E_PPS_FAILED_IND)|</span><br><span>                                                         S(ISO7816_E_TPDU_FAILED_IND),</span><br><span>                .out_state_mask =       S(ISO7816_S_WAIT_ATR) |</span><br><span>@@ -751,6 +762,14 @@</span><br><span>       }</span><br><span> }</span><br><span> </span><br><span style="color: hsl(120, 100%, 40%);">+static void atr_done_onenter(struct osmo_fsm_inst *fi, uint32_t old_state)</span><br><span style="color: hsl(120, 100%, 40%);">+{</span><br><span style="color: hsl(120, 100%, 40%);">+     struct osmo_fsm_inst *parent_fi = fi->proc.parent;</span><br><span style="color: hsl(120, 100%, 40%);">+ struct iso7816_3_priv *ip = get_iso7816_3_priv(parent_fi);</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+  card_uart_ctrl(ip->uart, CUART_CTL_RX_TIMER_HINT, 0);</span><br><span style="color: hsl(120, 100%, 40%);">+}</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span> static const struct osmo_fsm_state atr_states[] = {</span><br><span>         [ATR_S_WAIT_TS] = {</span><br><span>          .name = "WAIT_TS",</span><br><span>@@ -847,7 +866,7 @@</span><br><span>           .name = "DONE",</span><br><span>            .in_event_mask =        0,</span><br><span>           .out_state_mask =       S(ATR_S_WAIT_TS),</span><br><span style="color: hsl(0, 100%, 40%);">-               //.action = atr_done_action,</span><br><span style="color: hsl(120, 100%, 40%);">+          .onenter = atr_done_onenter</span><br><span>  },</span><br><span> </span><br><span> };</span><br><span>@@ -868,7 +887,7 @@</span><br><span>   uint8_t pps0_recv;</span><br><span> };</span><br><span> </span><br><span style="color: hsl(0, 100%, 40%);">-static void pps_s_wait_ppss_onenter(struct osmo_fsm_inst *fi, uint32_t old_state)</span><br><span style="color: hsl(120, 100%, 40%);">+static void pps_s_pps_req_init_onenter(struct osmo_fsm_inst *fi, uint32_t old_state)</span><br><span> {</span><br><span>     struct pps_fsm_priv *atp = fi->priv;</span><br><span> </span><br><span>@@ -885,7 +904,7 @@</span><br><span>    }</span><br><span> }</span><br><span> </span><br><span style="color: hsl(0, 100%, 40%);">-static void pps_s_tx_pps_req_action(struct osmo_fsm_inst *fi, uint32_t event, void *data)</span><br><span style="color: hsl(120, 100%, 40%);">+static void pps_s_pps_req_init_action(struct osmo_fsm_inst *fi, uint32_t event, void *data)</span><br><span> {</span><br><span>        struct pps_fsm_priv *atp = fi->priv;</span><br><span>      struct osmo_fsm_inst *parent_fi = fi->proc.parent;</span><br><span>@@ -896,7 +915,8 @@</span><br><span> </span><br><span>      switch (event) {</span><br><span>     case ISO7816_E_XCEIVE_PPS_CMD:</span><br><span style="color: hsl(0, 100%, 40%);">-          osmo_fsm_inst_state_chg(fi, PPS_S_WAIT_PPSS, 0, 0);</span><br><span style="color: hsl(120, 100%, 40%);">+           osmo_fsm_inst_state_chg(fi, PPS_S_TX_PPS_REQ, 0, 0);</span><br><span style="color: hsl(120, 100%, 40%);">+          card_uart_set_rx_threshold(ip->uart, 1);</span><br><span>          card_uart_tx(ip->uart, msgb_data(data), msgb_length(data), true);</span><br><span>                 break;</span><br><span>       default:</span><br><span>@@ -904,10 +924,29 @@</span><br><span>     }</span><br><span> }</span><br><span> </span><br><span style="color: hsl(120, 100%, 40%);">+static void pps_s_tx_pps_req_action(struct osmo_fsm_inst *fi, uint32_t event, void *data)</span><br><span style="color: hsl(120, 100%, 40%);">+{</span><br><span style="color: hsl(120, 100%, 40%);">+      struct osmo_fsm_inst *parent_fi = fi->proc.parent;</span><br><span style="color: hsl(120, 100%, 40%);">+ struct iso7816_3_priv *ip = get_iso7816_3_priv(parent_fi);</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+  switch (event) {</span><br><span style="color: hsl(120, 100%, 40%);">+      case ISO7816_E_TX_COMPL:</span><br><span style="color: hsl(120, 100%, 40%);">+              card_uart_ctrl(ip->uart, CUART_CTL_RX_TIMER_HINT, 6);</span><br><span style="color: hsl(120, 100%, 40%);">+              osmo_fsm_inst_state_chg(fi, PPS_S_WAIT_PPSX, 0, 0);</span><br><span style="color: hsl(120, 100%, 40%);">+           break;</span><br><span style="color: hsl(120, 100%, 40%);">+        default:</span><br><span style="color: hsl(120, 100%, 40%);">+              OSMO_ASSERT(0);</span><br><span style="color: hsl(120, 100%, 40%);">+       }</span><br><span style="color: hsl(120, 100%, 40%);">+}</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span> static void pps_wait_pX_action(struct osmo_fsm_inst *fi, uint32_t event, void *data)</span><br><span> {</span><br><span>    struct pps_fsm_priv *atp = fi->priv;</span><br><span style="color: hsl(0, 100%, 40%);">-//       uint32_t guard_time_ms = atr_fi_gt_ms(fi);</span><br><span style="color: hsl(120, 100%, 40%);">+    struct osmo_fsm_inst *parent_fi = fi->proc.parent;</span><br><span style="color: hsl(120, 100%, 40%);">+ struct iso7816_3_priv *ip = get_iso7816_3_priv(parent_fi);</span><br><span>   uint8_t byte;</span><br><span> </span><br><span>    switch (event) {</span><br><span>@@ -916,7 +955,7 @@</span><br><span>               LOGPFSML(fi, LOGL_DEBUG, "RX byte '%02x'\n", byte);</span><br><span>                msgb_put_u8(atp->rx_cmd, byte);</span><br><span>           switch (fi->state) {</span><br><span style="color: hsl(0, 100%, 40%);">-         case PPS_S_WAIT_PPSS:</span><br><span style="color: hsl(120, 100%, 40%);">+         case PPS_S_WAIT_PPSX:</span><br><span>                        if (byte == 0xff)</span><br><span>                            osmo_fsm_inst_state_chg(fi, PPS_S_WAIT_PPS0, 0, 0);</span><br><span>                  break;</span><br><span>@@ -960,7 +999,7 @@</span><br><span>                                 uint8_t *pps_received = msgb_data(atp->rx_cmd);</span><br><span>                           uint8_t *pps_sent = msgb_data(atp->tx_cmd);</span><br><span> </span><br><span style="color: hsl(0, 100%, 40%);">-                              osmo_fsm_inst_state_chg(fi, PPS_S_WAIT_END, 0, 0);</span><br><span style="color: hsl(120, 100%, 40%);">+                            osmo_fsm_inst_state_chg(fi, PPS_S_DONE, 0, 0);</span><br><span> </span><br><span>                           /* pps was successful if response equals request</span><br><span>                              * rx buffer stays with the fsm, tx buffer gets handed back and freed</span><br><span>@@ -982,6 +1021,7 @@</span><br><span>                 }</span><br><span>            break;</span><br><span>       case ISO7816_E_WTIME_EXP:</span><br><span style="color: hsl(120, 100%, 40%);">+             osmo_fsm_inst_state_chg(fi, PPS_S_DONE, 0, 0);</span><br><span>               /* FIXME: timeout handling if no pps supported ? */</span><br><span>          osmo_fsm_inst_dispatch(fi->proc.parent, ISO7816_E_RX_ERR_IND, NULL);</span><br><span>              break;</span><br><span>@@ -991,22 +1031,37 @@</span><br><span> }</span><br><span> </span><br><span> </span><br><span style="color: hsl(120, 100%, 40%);">+static void pps_s_done_onenter(struct osmo_fsm_inst *fi, uint32_t old_state)</span><br><span style="color: hsl(120, 100%, 40%);">+{</span><br><span style="color: hsl(120, 100%, 40%);">+ struct osmo_fsm_inst *parent_fi = fi->proc.parent;</span><br><span style="color: hsl(120, 100%, 40%);">+ struct iso7816_3_priv *ip = get_iso7816_3_priv(parent_fi);</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+  card_uart_ctrl(ip->uart, CUART_CTL_RX_TIMER_HINT, 0);</span><br><span style="color: hsl(120, 100%, 40%);">+}</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span> static const struct osmo_fsm_state pps_states[] = {</span><br><span style="color: hsl(0, 100%, 40%);">-  [PPS_S_TX_PPS_REQ] = {</span><br><span style="color: hsl(0, 100%, 40%);">-          .name = "TX_PPS_REQ",</span><br><span style="color: hsl(120, 100%, 40%);">+       [PPS_S_PPS_REQ_INIT] = {</span><br><span style="color: hsl(120, 100%, 40%);">+              .name = "INIT",</span><br><span>            .in_event_mask =        S(ISO7816_E_XCEIVE_PPS_CMD) |</span><br><span>                                                        S(ISO7816_E_WTIME_EXP),</span><br><span style="color: hsl(0, 100%, 40%);">-         .out_state_mask =       S(PPS_S_TX_PPS_REQ) |</span><br><span style="color: hsl(0, 100%, 40%);">-                                                   S(PPS_S_WAIT_PPSS),</span><br><span style="color: hsl(0, 100%, 40%);">-             .action = pps_s_tx_pps_req_action,</span><br><span style="color: hsl(0, 100%, 40%);">-              .onenter = pps_s_wait_ppss_onenter,</span><br><span style="color: hsl(120, 100%, 40%);">+           .out_state_mask =       S(PPS_S_PPS_REQ_INIT) |</span><br><span style="color: hsl(120, 100%, 40%);">+                                                       S(PPS_S_TX_PPS_REQ),</span><br><span style="color: hsl(120, 100%, 40%);">+          .action = pps_s_pps_req_init_action,</span><br><span style="color: hsl(120, 100%, 40%);">+          .onenter = pps_s_pps_req_init_onenter,</span><br><span>       },</span><br><span style="color: hsl(0, 100%, 40%);">-      [PPS_S_WAIT_PPSS] = {</span><br><span style="color: hsl(120, 100%, 40%);">+ [PPS_S_TX_PPS_REQ] = {</span><br><span style="color: hsl(120, 100%, 40%);">+                .name = "TX_PPS_REQ",</span><br><span style="color: hsl(120, 100%, 40%);">+               .in_event_mask =        S(ISO7816_E_TX_COMPL),</span><br><span style="color: hsl(120, 100%, 40%);">+                .out_state_mask =       S(PPS_S_WAIT_PPSX),</span><br><span style="color: hsl(120, 100%, 40%);">+           .action = pps_s_tx_pps_req_action,</span><br><span style="color: hsl(120, 100%, 40%);">+    },</span><br><span style="color: hsl(120, 100%, 40%);">+    [PPS_S_WAIT_PPSX] = {</span><br><span>                .name = "WAIT_PPSS",</span><br><span>               .in_event_mask =        S(ISO7816_E_RX_SINGLE) |</span><br><span>                                                     S(ISO7816_E_WTIME_EXP),</span><br><span>              .out_state_mask =       S(PPS_S_WAIT_PPS0) |</span><br><span style="color: hsl(0, 100%, 40%);">-                                                    S(PPS_S_WAIT_PPSS),</span><br><span style="color: hsl(120, 100%, 40%);">+                                                   S(PPS_S_WAIT_PPSX),</span><br><span>          .action = pps_wait_pX_action,</span><br><span>        },</span><br><span>   [PPS_S_WAIT_PPS0] = {</span><br><span>@@ -1047,14 +1102,15 @@</span><br><span>              .name = "WAIT_PCK",</span><br><span>                .in_event_mask =        S(ISO7816_E_RX_SINGLE) |</span><br><span>                                                     S(ISO7816_E_WTIME_EXP),</span><br><span style="color: hsl(0, 100%, 40%);">-         .out_state_mask =       S(PPS_S_WAIT_END),</span><br><span style="color: hsl(120, 100%, 40%);">+            .out_state_mask =       S(PPS_S_DONE),</span><br><span>               .action = pps_wait_pX_action,</span><br><span>        },</span><br><span style="color: hsl(0, 100%, 40%);">-      [PPS_S_WAIT_END] = {</span><br><span style="color: hsl(0, 100%, 40%);">-            .name = "WAIT_END",</span><br><span style="color: hsl(120, 100%, 40%);">+ [PPS_S_DONE] = {</span><br><span style="color: hsl(120, 100%, 40%);">+              .name = "DONE",</span><br><span>            .in_event_mask =        0,</span><br><span style="color: hsl(0, 100%, 40%);">-              .out_state_mask =       S(PPS_S_TX_PPS_REQ) |</span><br><span style="color: hsl(0, 100%, 40%);">-                                                   S(PPS_S_WAIT_PPSS),</span><br><span style="color: hsl(120, 100%, 40%);">+           .out_state_mask =       S(PPS_S_PPS_REQ_INIT),</span><br><span style="color: hsl(120, 100%, 40%);">+                .action = NULL,</span><br><span style="color: hsl(120, 100%, 40%);">+               .onenter = pps_s_done_onenter,</span><br><span>       },</span><br><span> };</span><br><span> </span><br><span>@@ -1140,9 +1196,14 @@</span><br><span> #include <hal_gpio.h></span><br><span> static void tpdu_s_tx_hdr_action(struct osmo_fsm_inst *fi, uint32_t event, void *data)</span><br><span> {</span><br><span style="color: hsl(120, 100%, 40%);">+   struct osmo_fsm_inst *parent_fi = fi->proc.parent;</span><br><span style="color: hsl(120, 100%, 40%);">+ struct iso7816_3_priv *ip = get_iso7816_3_priv(parent_fi);</span><br><span>   OSMO_ASSERT(fi->fsm == &tpdu_fsm);</span><br><span>    switch (event) {</span><br><span>     case ISO7816_E_TX_COMPL:</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+            card_uart_set_rx_threshold(ip->uart, 1);</span><br><span style="color: hsl(120, 100%, 40%);">+           card_uart_ctrl(ip->uart, CUART_CTL_RX_TIMER_HINT, 1);</span><br><span>             /* Rx of single byte is already enabled by previous card_uart_tx() call */</span><br><span>           osmo_fsm_inst_state_chg(fi, TPDU_S_PROCEDURE, 0, 0);</span><br><span>                 break;</span><br><span>@@ -1167,11 +1228,15 @@</span><br><span>             LOGPFSML(fi, LOGL_DEBUG, "Received 0x%02x from UART\n", byte);</span><br><span>             if (byte == 0x60) {</span><br><span>                  /* NULL: wait for another procedure byte */</span><br><span style="color: hsl(120, 100%, 40%);">+                   card_uart_set_rx_threshold(ip->uart, 1);</span><br><span style="color: hsl(120, 100%, 40%);">+                   card_uart_ctrl(ip->uart, CUART_CTL_RX_TIMER_HINT, 1);</span><br><span>                     osmo_fsm_inst_state_chg(fi, TPDU_S_PROCEDURE, 0, 0);</span><br><span>                 } else if ((byte >= 0x60 && byte <= 0x6f) || (byte >= 0x90 && byte <= 0x9f)) {</span><br><span>                   //msgb_apdu_sw(tfp->apdu) = byte << 8;</span><br><span>                      msgb_put(tfp->tpdu, byte);</span><br><span>                        /* receive second SW byte (SW2) */</span><br><span style="color: hsl(120, 100%, 40%);">+                    card_uart_set_rx_threshold(ip->uart, 1);</span><br><span style="color: hsl(120, 100%, 40%);">+                   card_uart_ctrl(ip->uart, CUART_CTL_RX_TIMER_HINT, 1);</span><br><span>                     osmo_fsm_inst_state_chg(fi, TPDU_S_SW2, 0, 0);</span><br><span>                       break;</span><br><span>               } else if (byte == tpduh->ins) {</span><br><span>@@ -1187,6 +1252,7 @@</span><br><span>                          osmo_fsm_inst_state_chg(fi, TPDU_S_TX_REMAINING, 0, 0);</span><br><span>                      } else {</span><br><span>                             card_uart_set_rx_threshold(ip->uart, tpduh->p3);</span><br><span style="color: hsl(120, 100%, 40%);">+                                card_uart_ctrl(ip->uart, CUART_CTL_RX_TIMER_HINT, tpduh->p3);</span><br><span>                          osmo_fsm_inst_state_chg(fi, TPDU_S_RX_REMAINING, 0, 0);</span><br><span>                      }</span><br><span>            } else if (byte == (tpduh->ins ^ 0xFF)) {</span><br><span>@@ -1197,6 +1263,8 @@</span><br><span>                                 card_uart_tx(ip->uart, msgb_l3(tfp->tpdu), 1, false);</span><br><span>                          osmo_fsm_inst_state_chg(fi, TPDU_S_TX_SINGLE, 0, 0);</span><br><span>                         } else {</span><br><span style="color: hsl(120, 100%, 40%);">+                              card_uart_set_rx_threshold(ip->uart, 1);</span><br><span style="color: hsl(120, 100%, 40%);">+                           card_uart_ctrl(ip->uart, CUART_CTL_RX_TIMER_HINT, 1);</span><br><span>                             osmo_fsm_inst_state_chg(fi, TPDU_S_RX_SINGLE, 0, 0);</span><br><span>                         }</span><br><span>            } else</span><br><span>@@ -1216,6 +1284,7 @@</span><br><span>       switch (event) {</span><br><span>     case ISO7816_E_TX_COMPL:</span><br><span>             card_uart_set_rx_threshold(ip->uart, 1);</span><br><span style="color: hsl(120, 100%, 40%);">+           card_uart_ctrl(ip->uart, CUART_CTL_RX_TIMER_HINT, 1);</span><br><span>             osmo_fsm_inst_state_chg(fi, TPDU_S_SW1, 0, 0);</span><br><span>               break;</span><br><span>       default:</span><br><span>@@ -1227,10 +1296,14 @@</span><br><span> static void tpdu_s_tx_single_action(struct osmo_fsm_inst *fi, uint32_t event, void *data)</span><br><span> {</span><br><span>         struct tpdu_fsm_priv *tfp = get_tpdu_fsm_priv(fi);</span><br><span style="color: hsl(120, 100%, 40%);">+    struct osmo_fsm_inst *parent_fi = fi->proc.parent;</span><br><span style="color: hsl(120, 100%, 40%);">+ struct iso7816_3_priv *ip = get_iso7816_3_priv(parent_fi);</span><br><span> </span><br><span>       switch (event) {</span><br><span>     case ISO7816_E_TX_COMPL:</span><br><span>             tfp->tpdu->l3h += 1;</span><br><span style="color: hsl(120, 100%, 40%);">+            card_uart_set_rx_threshold(ip->uart, 1);</span><br><span style="color: hsl(120, 100%, 40%);">+           card_uart_ctrl(ip->uart, CUART_CTL_RX_TIMER_HINT, 1);</span><br><span>             if (msgb_l3len(tfp->tpdu))</span><br><span>                        osmo_fsm_inst_state_chg(fi, TPDU_S_PROCEDURE, 0, 0);</span><br><span>                 else</span><br><span>@@ -1261,6 +1334,7 @@</span><br><span>                                  msgb_l2len(tfp->tpdu));</span><br><span>          }</span><br><span>            card_uart_set_rx_threshold(ip->uart, 1);</span><br><span style="color: hsl(120, 100%, 40%);">+           card_uart_ctrl(ip->uart, CUART_CTL_RX_TIMER_HINT, 1);</span><br><span>             osmo_fsm_inst_state_chg(fi, TPDU_S_SW1, 0, 0);</span><br><span>               break;</span><br><span>       default:</span><br><span>@@ -1273,6 +1347,8 @@</span><br><span> {</span><br><span>        struct tpdu_fsm_priv *tfp = get_tpdu_fsm_priv(fi);</span><br><span>   struct osim_apdu_cmd_hdr *tpduh = msgb_tpdu_hdr(tfp->tpdu);</span><br><span style="color: hsl(120, 100%, 40%);">+        struct osmo_fsm_inst *parent_fi = fi->proc.parent;</span><br><span style="color: hsl(120, 100%, 40%);">+ struct iso7816_3_priv *ip = get_iso7816_3_priv(parent_fi);</span><br><span>   uint8_t byte;</span><br><span> </span><br><span>    switch (event) {</span><br><span>@@ -1280,6 +1356,10 @@</span><br><span>            byte = get_rx_byte_evt(fi->proc.parent, data);</span><br><span>            LOGPFSML(fi, LOGL_DEBUG, "Received 0x%02x from UART\n", byte);</span><br><span>             msgb_put_u8(tfp->tpdu, byte);</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+            card_uart_set_rx_threshold(ip->uart, 1);</span><br><span style="color: hsl(120, 100%, 40%);">+           card_uart_ctrl(ip->uart, CUART_CTL_RX_TIMER_HINT, 1);</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span>           /* determine if number of expected bytes received */</span><br><span>                 if (msgb_l2len(tfp->tpdu) == tpduh->p3)</span><br><span>                        osmo_fsm_inst_state_chg(fi, TPDU_S_SW1, 0, 0);</span><br><span>@@ -1306,6 +1386,7 @@</span><br><span>               //msgb_apdu_sw(tfp->apdu) = byte << 8;</span><br><span>              msgb_put_u8(tfp->tpdu, byte);</span><br><span>             card_uart_set_rx_threshold(ip->uart, 1);</span><br><span style="color: hsl(120, 100%, 40%);">+           card_uart_ctrl(ip->uart, CUART_CTL_RX_TIMER_HINT, 1);</span><br><span>             osmo_fsm_inst_state_chg(fi, TPDU_S_SW2, 0, 0);</span><br><span>               break;</span><br><span>       default:</span><br><span>@@ -1349,7 +1430,7 @@</span><br><span>     case ISO7816_E_TX_ERR_IND:</span><br><span>           /* FIXME: handle this in some different way */</span><br><span>               osmo_fsm_inst_state_chg(fi, TPDU_S_DONE, 0, 0);</span><br><span style="color: hsl(0, 100%, 40%);">-         osmo_fsm_inst_dispatch(fi->proc.parent, ISO7816_E_TPDU_DONE_IND, NULL);</span><br><span style="color: hsl(120, 100%, 40%);">+            osmo_fsm_inst_dispatch(fi->proc.parent, ISO7816_E_TPDU_FAILED_IND, NULL);</span><br><span>                 break;</span><br><span>       case ISO7816_E_TPDU_CLEAR_REQ:</span><br><span>               osmo_fsm_inst_state_chg(fi, TPDU_S_INIT, 0, 0);</span><br><span>@@ -1357,6 +1438,15 @@</span><br><span>     }</span><br><span> }</span><br><span> </span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+static void tpdu_s_done_onenter(struct osmo_fsm_inst *fi, uint32_t old_state)</span><br><span style="color: hsl(120, 100%, 40%);">+{</span><br><span style="color: hsl(120, 100%, 40%);">+        struct osmo_fsm_inst *parent_fi = fi->proc.parent;</span><br><span style="color: hsl(120, 100%, 40%);">+ struct iso7816_3_priv *ip = get_iso7816_3_priv(parent_fi);</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+  card_uart_ctrl(ip->uart, CUART_CTL_RX_TIMER_HINT, 0);</span><br><span style="color: hsl(120, 100%, 40%);">+}</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span> static const struct osmo_fsm_state tpdu_states[] = {</span><br><span>        [TPDU_S_INIT] = {</span><br><span>            .name = "INIT",</span><br><span>@@ -1433,6 +1523,7 @@</span><br><span>            .in_event_mask = 0,</span><br><span>          .out_state_mask = S(TPDU_S_INIT),</span><br><span>            .action = NULL,</span><br><span style="color: hsl(120, 100%, 40%);">+               .onenter = tpdu_s_done_onenter,</span><br><span>      },</span><br><span> };</span><br><span> static struct osmo_fsm tpdu_fsm = {</span><br><span></span><br></pre><p>To view, visit <a href="https://gerrit.osmocom.org/c/osmo-ccid-firmware/+/16293">change 16293</a>. To unsubscribe, or for help writing mail filters, visit <a href="https://gerrit.osmocom.org/settings">settings</a>.</p><div itemscope itemtype="http://schema.org/EmailMessage"><div itemscope itemprop="action" itemtype="http://schema.org/ViewAction"><link itemprop="url" href="https://gerrit.osmocom.org/c/osmo-ccid-firmware/+/16293"/><meta itemprop="name" content="View Change"/></div></div>

<div style="display:none"> Gerrit-Project: osmo-ccid-firmware </div>
<div style="display:none"> Gerrit-Branch: master </div>
<div style="display:none"> Gerrit-Change-Id: Ia6ad2d83cea48a8661ed2e4eb50f9bcb85218454 </div>
<div style="display:none"> Gerrit-Change-Number: 16293 </div>
<div style="display:none"> Gerrit-PatchSet: 1 </div>
<div style="display:none"> Gerrit-Owner: Hoernchen <ewild@sysmocom.de> </div>
<div style="display:none"> Gerrit-MessageType: newchange </div>