You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@mynewt.apache.org by je...@apache.org on 2023/02/23 07:09:57 UTC
[mynewt-core] 01/03: hw/bus: Add duplex_write_read function to bus_dev_ops
This is an automated email from the ASF dual-hosted git repository.
jerzy pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/mynewt-core.git
commit 420bce6ddcbd37031cf489cc0a11b9131fe29746
Author: Jerzy Kasenberg <je...@codecoup.pl>
AuthorDate: Fri Feb 17 15:21:24 2023 +0100
hw/bus: Add duplex_write_read function to bus_dev_ops
Duplex of SPI was not covered in bus drivers.
This adds bus_node_duplex_write_read() function that
can be used with SPI drivers that support duplex
mode.
For simplicity both buffers provided to function
have same length.
---
hw/bus/include/bus/bus.h | 21 +++++++++++++++++++++
hw/bus/include/bus/bus_driver.h | 4 ++++
hw/bus/src/bus.c | 39 +++++++++++++++++++++++++++++++++++++++
3 files changed, 64 insertions(+)
diff --git a/hw/bus/include/bus/bus.h b/hw/bus/include/bus/bus.h
index 4d357f376..e43c091a1 100644
--- a/hw/bus/include/bus/bus.h
+++ b/hw/bus/include/bus/bus.h
@@ -128,6 +128,27 @@ bus_node_write_read_transact(struct os_dev *node, const void *wbuf,
uint16_t wlength, void *rbuf, uint16_t rlength,
os_time_t timeout, uint16_t flags);
+/**
+ * Perform write and read in duplex mode (SPI)
+ *
+ * Writes data to node and automatically reads response at the same time.
+ *
+ * The timeout parameter applies to complete transaction time.
+ *
+ * @param node Node device object
+ * @param wbuf Buffer with data to be written
+ * @param rbuf Buffer to read data into
+ * @param length Length of data to be written and read
+ * @param timeout Operation timeout
+ * @param flags Flags
+ *
+ * @return 0 on success, SYS_xxx on error
+ */
+int
+bus_node_duplex_write_read(struct os_dev *node, const void *wbuf,
+ void *rbuf, uint16_t length,
+ os_time_t timeout, uint16_t flags);
+
/**
* Read data from node
*
diff --git a/hw/bus/include/bus/bus_driver.h b/hw/bus/include/bus/bus_driver.h
index 8429ab6a2..207aeb23f 100644
--- a/hw/bus/include/bus/bus_driver.h
+++ b/hw/bus/include/bus/bus_driver.h
@@ -68,6 +68,10 @@ struct bus_dev_ops {
const uint8_t *wbuf, uint16_t wlength,
uint8_t *rbuf, uint16_t rlength,
os_time_t timeout, uint16_t flags);
+ /* Duplex write and read */
+ int (* duplex_write_read)(struct bus_dev *bdev, struct bus_node *bnode,
+ const uint8_t *wbuf, uint8_t *rbuf, uint16_t length,
+ os_time_t timeout, uint16_t flags);
};
/**
diff --git a/hw/bus/src/bus.c b/hw/bus/src/bus.c
index 29987542a..f481be6dd 100644
--- a/hw/bus/src/bus.c
+++ b/hw/bus/src/bus.c
@@ -456,6 +456,45 @@ done:
return rc;
}
+int
+bus_node_duplex_write_read(struct os_dev *node, const void *wbuf,
+ void *rbuf, uint16_t length,
+ os_time_t timeout, uint16_t flags)
+{
+ struct bus_node *bnode = (struct bus_node *)node;
+ struct bus_dev *bdev = bnode->parent_bus;
+ int rc;
+
+ BUS_DEBUG_VERIFY_DEV(bdev);
+ BUS_DEBUG_VERIFY_NODE(bnode);
+
+ if (!bdev->dops->duplex_write_read) {
+ return SYS_ENOTSUP;
+ }
+
+ rc = bus_node_lock(node, bus_node_get_lock_timeout(node));
+ if (rc) {
+ return rc;
+ }
+
+ if (!bdev->enabled) {
+ rc = SYS_EIO;
+ goto done;
+ }
+
+ BUS_STATS_INC(bdev, bnode, write_ops);
+ BUS_STATS_INC(bdev, bnode, read_ops);
+ rc = bdev->dops->duplex_write_read(bdev, bnode, wbuf, rbuf, length, timeout, flags);
+ if (rc) {
+ BUS_STATS_INC(bdev, bnode, write_errors);
+ BUS_STATS_INC(bdev, bnode, read_errors);
+ }
+
+done:
+ (void)bus_node_unlock(node);
+
+ return rc;
+}
int
bus_node_lock(struct os_dev *node, os_time_t timeout)