<p>laforge has uploaded this change for <strong>review</strong>.</p><p><a href="https://gerrit.osmocom.org/c/simtrace2/+/18474">View Change</a></p><pre style="font-family: monospace,monospace; white-space: pre-wrap;">Introduce support for asynchronous USB transmission<br><br>libosmo-simtrace2 traditionally had only supported blocking, synchronous<br>I/O, while other osmocom programs such as remsim-client used<br>asynchronous USB I/O.<br><br>Using async USB I/O for IRQ + IN transfers while using blocking I/O for<br>OUT transfers doesn't seem to work reliably, so we have to offer a way<br>to perform the OUT transfers generated within libosmo-simtrace2 in async<br>mode.<br><br>Change-Id: Ib8939bdb7f533cd20a34a30a97f12b782b9816c2<br>---<br>A TODO-RELEASE<br>M host/include/osmocom/simtrace2/simtrace2_api.h<br>M host/lib/simtrace2_api.c<br>3 files changed, 79 insertions(+), 17 deletions(-)<br><br></pre><pre style="font-family: monospace,monospace; white-space: pre-wrap;">git pull ssh://gerrit.osmocom.org:29418/simtrace2 refs/changes/74/18474/1</pre><pre style="font-family: monospace,monospace; white-space: pre-wrap;"><span>diff --git a/TODO-RELEASE b/TODO-RELEASE</span><br><span>new file mode 100644</span><br><span>index 0000000..5da461b</span><br><span>--- /dev/null</span><br><span>+++ b/TODO-RELEASE</span><br><span>@@ -0,0 +1,10 @@</span><br><span style="color: hsl(120, 100%, 40%);">+# When cleaning up this file: bump API version in corresponding Makefile.am and rename corresponding debian/lib*.install</span><br><span style="color: hsl(120, 100%, 40%);">+# according to https://osmocom.org/projects/cellular-infrastructure/wiki/Make_a_new_release</span><br><span style="color: hsl(120, 100%, 40%);">+# In short: https://www.gnu.org/software/libtool/manual/html_node/Updating-version-info.html#Updating-version-info</span><br><span style="color: hsl(120, 100%, 40%);">+# LIBVERSION=c:r:a</span><br><span style="color: hsl(120, 100%, 40%);">+# If the library source code has changed at all since the last update, then increment revision: c:r + 1:a.</span><br><span style="color: hsl(120, 100%, 40%);">+# If any interfaces have been added, removed, or changed since the last update: c + 1:0:0.</span><br><span style="color: hsl(120, 100%, 40%);">+# If any interfaces have been added since the last public release: c:r:a + 1.</span><br><span style="color: hsl(120, 100%, 40%);">+# If any interfaces have been removed or changed since the last public release: c:r:0.</span><br><span style="color: hsl(120, 100%, 40%);">+#library     what                    description / commit summary line</span><br><span style="color: hsl(120, 100%, 40%);">+simtrace2    API/ABI change          osmo_st2_transport new member</span><br><span>diff --git a/host/include/osmocom/simtrace2/simtrace2_api.h b/host/include/osmocom/simtrace2/simtrace2_api.h</span><br><span>index aa1637d..d658d16 100644</span><br><span>--- a/host/include/osmocom/simtrace2/simtrace2_api.h</span><br><span>+++ b/host/include/osmocom/simtrace2/simtrace2_api.h</span><br><span>@@ -12,6 +12,8 @@</span><br><span>               uint8_t out;</span><br><span>                 uint8_t irq_in;</span><br><span>      } usb_ep;</span><br><span style="color: hsl(120, 100%, 40%);">+     /* use non-blocking / asynchronous libusb I/O */</span><br><span style="color: hsl(120, 100%, 40%);">+      bool usb_async;</span><br><span> </span><br><span>  /* UDP */</span><br><span>    int udp_fd;</span><br><span>@@ -39,8 +41,6 @@</span><br><span>      void *priv;</span><br><span> };</span><br><span> </span><br><span style="color: hsl(0, 100%, 40%);">-int osmo_st2_transp_tx_msg(struct osmo_st2_transport *transp, struct msgb *msg);</span><br><span style="color: hsl(0, 100%, 40%);">-</span><br><span> int osmo_st2_slot_tx_msg(struct osmo_st2_slot *slot, struct msgb *msg,</span><br><span>                          uint8_t msg_class, uint8_t msg_type);</span><br><span> </span><br><span>diff --git a/host/lib/simtrace2_api.c b/host/lib/simtrace2_api.c</span><br><span>index b3e4e38..4e16fd1 100644</span><br><span>--- a/host/lib/simtrace2_api.c</span><br><span>+++ b/host/lib/simtrace2_api.c</span><br><span>@@ -57,24 +57,61 @@</span><br><span>     return msgb_alloc_headroom(1024+32, 32, "SIMtrace");</span><br><span> }</span><br><span> </span><br><span style="color: hsl(0, 100%, 40%);">-/*! \brief Transmit a given command to the SIMtrace2 device */</span><br><span style="color: hsl(0, 100%, 40%);">-int osmo_st2_transp_tx_msg(struct osmo_st2_transport *transp, struct msgb *msg)</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+static void usb_out_xfer_cb(struct libusb_transfer *xfer)</span><br><span> {</span><br><span style="color: hsl(0, 100%, 40%);">-  int rc;</span><br><span style="color: hsl(120, 100%, 40%);">+       struct msgb *msg = xfer->user_data;</span><br><span> </span><br><span style="color: hsl(0, 100%, 40%);">-      printf("<- %s\n", msgb_hexdump(msg));</span><br><span style="color: hsl(0, 100%, 40%);">-</span><br><span style="color: hsl(0, 100%, 40%);">-      if (transp->udp_fd < 0) {</span><br><span style="color: hsl(0, 100%, 40%);">-         int xfer_len;</span><br><span style="color: hsl(0, 100%, 40%);">-</span><br><span style="color: hsl(0, 100%, 40%);">-           rc = libusb_bulk_transfer(transp->usb_devh, transp->usb_ep.out,</span><br><span style="color: hsl(0, 100%, 40%);">-                                     msgb_data(msg), msgb_length(msg),</span><br><span style="color: hsl(0, 100%, 40%);">-                                       &xfer_len, 100000);</span><br><span style="color: hsl(0, 100%, 40%);">-       } else {</span><br><span style="color: hsl(0, 100%, 40%);">-                rc = write(transp->udp_fd, msgb_data(msg), msgb_length(msg));</span><br><span style="color: hsl(120, 100%, 40%);">+      switch (xfer->status) {</span><br><span style="color: hsl(120, 100%, 40%);">+    case LIBUSB_TRANSFER_COMPLETED:</span><br><span style="color: hsl(120, 100%, 40%);">+               break;</span><br><span style="color: hsl(120, 100%, 40%);">+        case LIBUSB_TRANSFER_NO_DEVICE:</span><br><span style="color: hsl(120, 100%, 40%);">+               fprintf(stderr, "USB device disappeared\n");</span><br><span style="color: hsl(120, 100%, 40%);">+                exit(1);</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%);">+              fprintf(stderr, "USB OUT transfer failed, status=%u\n", xfer->status);</span><br><span style="color: hsl(120, 100%, 40%);">+           exit(1);</span><br><span style="color: hsl(120, 100%, 40%);">+              break;</span><br><span>       }</span><br><span> </span><br><span>        msgb_free(msg);</span><br><span style="color: hsl(120, 100%, 40%);">+       libusb_free_transfer(xfer);</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%);">+static int st2_transp_tx_msg_usb_async(struct osmo_st2_transport *transp, struct msgb *msg)</span><br><span style="color: hsl(120, 100%, 40%);">+{</span><br><span style="color: hsl(120, 100%, 40%);">+    struct libusb_transfer *xfer;</span><br><span style="color: hsl(120, 100%, 40%);">+ int rc;</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+     xfer = libusb_alloc_transfer(0);</span><br><span style="color: hsl(120, 100%, 40%);">+      OSMO_ASSERT(xfer);</span><br><span style="color: hsl(120, 100%, 40%);">+    xfer->dev_handle = transp->usb_devh;</span><br><span style="color: hsl(120, 100%, 40%);">+    xfer->flags = 0;</span><br><span style="color: hsl(120, 100%, 40%);">+   xfer->type = LIBUSB_TRANSFER_TYPE_BULK;</span><br><span style="color: hsl(120, 100%, 40%);">+    xfer->endpoint = transp->usb_ep.out;</span><br><span style="color: hsl(120, 100%, 40%);">+    xfer->timeout = 100000;</span><br><span style="color: hsl(120, 100%, 40%);">+    xfer->user_data = msg;</span><br><span style="color: hsl(120, 100%, 40%);">+     xfer->length = msgb_length(msg);</span><br><span style="color: hsl(120, 100%, 40%);">+   xfer->buffer = msgb_data(msg);</span><br><span style="color: hsl(120, 100%, 40%);">+     xfer->callback = usb_out_xfer_cb;</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+        rc = libusb_submit_transfer(xfer);</span><br><span style="color: hsl(120, 100%, 40%);">+    OSMO_ASSERT(rc == 0);</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+       return rc;</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%);">+/*! \brief Transmit a given command to the SIMtrace2 device */</span><br><span style="color: hsl(120, 100%, 40%);">+static int st2_transp_tx_msg_usb_sync(struct osmo_st2_transport *transp, struct msgb *msg)</span><br><span style="color: hsl(120, 100%, 40%);">+{</span><br><span style="color: hsl(120, 100%, 40%);">+        int rc;</span><br><span style="color: hsl(120, 100%, 40%);">+       int xfer_len;</span><br><span style="color: hsl(120, 100%, 40%);">+ rc = libusb_bulk_transfer(transp->usb_devh, transp->usb_ep.out,</span><br><span style="color: hsl(120, 100%, 40%);">+                           msgb_data(msg), msgb_length(msg),</span><br><span style="color: hsl(120, 100%, 40%);">+                             &xfer_len, 100000);</span><br><span style="color: hsl(120, 100%, 40%);">+     msgb_free(msg);</span><br><span>      return rc;</span><br><span> }</span><br><span> </span><br><span>@@ -98,9 +135,24 @@</span><br><span> int osmo_st2_slot_tx_msg(struct osmo_st2_slot *slot, struct msgb *msg,</span><br><span>                   uint8_t msg_class, uint8_t msg_type)</span><br><span> {</span><br><span style="color: hsl(0, 100%, 40%);">-      st_push_hdr(msg, msg_class, msg_type, slot->slot_nr);</span><br><span style="color: hsl(120, 100%, 40%);">+      struct osmo_st2_transport *transp = slot->transp;</span><br><span style="color: hsl(120, 100%, 40%);">+  int rc;</span><br><span> </span><br><span style="color: hsl(0, 100%, 40%);">-     return osmo_st2_transp_tx_msg(slot->transp, msg);</span><br><span style="color: hsl(120, 100%, 40%);">+  OSMO_ASSERT(transp);</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+        st_push_hdr(msg, msg_class, msg_type, slot->slot_nr);</span><br><span style="color: hsl(120, 100%, 40%);">+      printf("SIMtrace <- %s\n", msgb_hexdump(msg));</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ if (transp->udp_fd < 0) {</span><br><span style="color: hsl(120, 100%, 40%);">+               if (transp->usb_async)</span><br><span style="color: hsl(120, 100%, 40%);">+                     rc = st2_transp_tx_msg_usb_async(transp, msg);</span><br><span style="color: hsl(120, 100%, 40%);">+                else</span><br><span style="color: hsl(120, 100%, 40%);">+                  rc = st2_transp_tx_msg_usb_sync(transp, msg);</span><br><span style="color: hsl(120, 100%, 40%);">+ } else {</span><br><span style="color: hsl(120, 100%, 40%);">+              rc = write(transp->udp_fd, msgb_data(msg), msgb_length(msg));</span><br><span style="color: hsl(120, 100%, 40%);">+              msgb_free(msg);</span><br><span style="color: hsl(120, 100%, 40%);">+       }</span><br><span style="color: hsl(120, 100%, 40%);">+     return rc;</span><br><span> }</span><br><span> </span><br><span> /***********************************************************************</span><br><span></span><br></pre><p>To view, visit <a href="https://gerrit.osmocom.org/c/simtrace2/+/18474">change 18474</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/simtrace2/+/18474"/><meta itemprop="name" content="View Change"/></div></div>

<div style="display:none"> Gerrit-Project: simtrace2 </div>
<div style="display:none"> Gerrit-Branch: master </div>
<div style="display:none"> Gerrit-Change-Id: Ib8939bdb7f533cd20a34a30a97f12b782b9816c2 </div>
<div style="display:none"> Gerrit-Change-Number: 18474 </div>
<div style="display:none"> Gerrit-PatchSet: 1 </div>
<div style="display:none"> Gerrit-Owner: laforge <laforge@osmocom.org> </div>
<div style="display:none"> Gerrit-MessageType: newchange </div>