<p>laforge <strong>submitted</strong> this change.</p><p><a href="https://gerrit.osmocom.org/c/simtrace2/+/18474">View Change</a></p><div style="white-space:pre-wrap">Approvals:
Jenkins Builder: Verified
laforge: Looks good to me, approved
</div><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;"><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-Reviewer: Jenkins Builder </div>
<div style="display:none"> Gerrit-Reviewer: laforge <laforge@osmocom.org> </div>
<div style="display:none"> Gerrit-MessageType: merged </div>