* [PATCH v3 0/3] Apple SPI controller driver
@ 2024-11-01 19:26 Janne Grunau via B4 Relay
2024-11-01 19:26 ` [PATCH v3 1/3] dt-bindings: spi: apple,spi: Add binding for Apple SPI controllers Janne Grunau via B4 Relay
` (3 more replies)
0 siblings, 4 replies; 14+ messages in thread
From: Janne Grunau via B4 Relay @ 2024-11-01 19:26 UTC (permalink / raw)
To: Hector Martin, Sven Peter, Alyssa Rosenzweig, Mark Brown,
Rob Herring, Krzysztof Kozlowski, Conor Dooley
Cc: asahi, linux-arm-kernel, linux-spi, devicetree, linux-kernel,
Janne Grunau
Hi all,
This updated series address the review comments from the original
submission in 2021 [1]. It adds a new SPI controller driver for Apple
SoCs and is based on spi-sifive. It has been tested with the generic
jedec,spi-nor support and with a downstream driver for an Apple specific
HID over SPI transport.
As usual, I'm splitting off the MAINTAINERS and DT binding changes.
We would rather merge the MAINTAINERS change through the Asahi-SoC
tree to avoid merge conflicts as things trickle upstream, since
we have other submissions touching that section of the file.
The DT binding change can go via the SPI tree or via ours, but it's
easier if we merge it, as then we can make the DT changes to
instantiate it without worrying about DT validation failures depending
on merge order.
This is mostly Hector's work with a few minor changes to address review
comments from me.
[1] https://lore.kernel.org/linux-spi/20211212034726.26306-1-marcan@marcan.st/
v2:
- removed '#address-cells' and '#size-cells' from the bindings and added
Rob's Rb:
- fixed (new) checkpatch warnings
- added t8112 (M2) SoC
- shorted long and complex source code lines
- switch to devm_clk_prepare_enable() and devm_pm_runtime_enable()
- switch to dev_err_probe() in probe function
- removed "pdev->dev.dma_mask = NULL;"
- got rid of apple_spi_remove()
Signed-off-by: Janne Grunau <j@jannau.net>
---
Changes in v3:
- fixed bindings_check warning
- converted top file comment to C++ style comments
- dropped verbose dev_err_probe after failed devm_* function
- stopped setting field in zero initialized struct to 0
- added error handling for devm_pm_runtime_enable()
- Link to v2: https://lore.kernel.org/r/20241101-asahi-spi-v2-0-763a8a84d834@jannau.net
Changes in v2:
- removed '#address-cells' and '#size-cells' from the bindings and added
Rob's Rb:
- fixed (new) checkpatch warnings
- added t8112 (M2) SoC
- shorted long and complex source code lines
- switch to devm_clk_prepare_enable() and devm_pm_runtime_enable()
- switch to dev_err_probe() in probe function
- removed "pdev->dev.dma_mask = NULL;"
- got rid of apple_spi_remove()
- Link to v1: https://lore.kernel.org/linux-spi/20211212034726.26306-1-marcan@marcan.st/
---
Hector Martin (3):
dt-bindings: spi: apple,spi: Add binding for Apple SPI controllers
spi: apple: Add driver for Apple SPI controller
MAINTAINERS: Add apple-spi driver & binding files
.../devicetree/bindings/spi/apple,spi.yaml | 62 +++
MAINTAINERS | 2 +
drivers/spi/Kconfig | 11 +
drivers/spi/Makefile | 1 +
drivers/spi/spi-apple.c | 531 +++++++++++++++++++++
5 files changed, 607 insertions(+)
---
base-commit: 98f7e32f20d28ec452afb208f9cffc08448a2652
change-id: 20240811-asahi-spi-f8740ba797d7
Best regards,
--
Janne Grunau <j@jannau.net>
^ permalink raw reply [flat|nested] 14+ messages in thread
* [PATCH v3 1/3] dt-bindings: spi: apple,spi: Add binding for Apple SPI controllers
2024-11-01 19:26 [PATCH v3 0/3] Apple SPI controller driver Janne Grunau via B4 Relay
@ 2024-11-01 19:26 ` Janne Grunau via B4 Relay
2024-11-02 2:36 ` Nick Chan
2024-11-04 18:56 ` Conor Dooley
2024-11-01 19:26 ` [PATCH v3 2/3] spi: apple: Add driver for Apple SPI controller Janne Grunau via B4 Relay
` (2 subsequent siblings)
3 siblings, 2 replies; 14+ messages in thread
From: Janne Grunau via B4 Relay @ 2024-11-01 19:26 UTC (permalink / raw)
To: Hector Martin, Sven Peter, Alyssa Rosenzweig, Mark Brown,
Rob Herring, Krzysztof Kozlowski, Conor Dooley
Cc: asahi, linux-arm-kernel, linux-spi, devicetree, linux-kernel,
Janne Grunau
From: Hector Martin <marcan@marcan.st>
The Apple SPI controller is present in SoCs such as the M1 (t8103) and
M1 Pro/Max (t600x). This controller uses one IRQ and one clock, and
doesn't need any special properties, so the binding is trivial.
Signed-off-by: Hector Martin <marcan@marcan.st>
Signed-off-by: Janne Grunau <j@jannau.net>
---
.../devicetree/bindings/spi/apple,spi.yaml | 62 ++++++++++++++++++++++
1 file changed, 62 insertions(+)
diff --git a/Documentation/devicetree/bindings/spi/apple,spi.yaml b/Documentation/devicetree/bindings/spi/apple,spi.yaml
new file mode 100644
index 0000000000000000000000000000000000000000..8b4f974faa23bcf9a1ea0a0eb52ad17ca196b341
--- /dev/null
+++ b/Documentation/devicetree/bindings/spi/apple,spi.yaml
@@ -0,0 +1,62 @@
+# SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause)
+%YAML 1.2
+---
+$id: http://devicetree.org/schemas/spi/apple,spi.yaml#
+$schema: http://devicetree.org/meta-schemas/core.yaml#
+
+title: Apple ARM SoC SPI controller
+
+allOf:
+ - $ref: spi-controller.yaml#
+
+maintainers:
+ - Hector Martin <marcan@marcan.st>
+
+properties:
+ compatible:
+ items:
+ - enum:
+ - apple,t8103-spi
+ - apple,t8112-spi
+ - apple,t6000-spi
+ - const: apple,spi
+
+ reg:
+ maxItems: 1
+
+ clocks:
+ maxItems: 1
+
+ interrupts:
+ maxItems: 1
+
+ power-domains:
+ maxItems: 1
+
+required:
+ - compatible
+ - reg
+ - clocks
+ - interrupts
+
+unevaluatedProperties: false
+
+examples:
+ - |
+ #include <dt-bindings/interrupt-controller/apple-aic.h>
+ #include <dt-bindings/interrupt-controller/irq.h>
+
+ soc {
+ #address-cells = <2>;
+ #size-cells = <2>;
+
+ spi: spi@39b104000 {
+ compatible = "apple,t6000-spi", "apple,spi";
+ reg = <0x3 0x9b104000 0x0 0x4000>;
+ interrupt-parent = <&aic>;
+ interrupts = <AIC_IRQ 0 1107 IRQ_TYPE_LEVEL_HIGH>;
+ #address-cells = <1>;
+ #size-cells = <0>;
+ clocks = <&clk>;
+ };
+ };
--
2.47.0
^ permalink raw reply related [flat|nested] 14+ messages in thread
* [PATCH v3 2/3] spi: apple: Add driver for Apple SPI controller
2024-11-01 19:26 [PATCH v3 0/3] Apple SPI controller driver Janne Grunau via B4 Relay
2024-11-01 19:26 ` [PATCH v3 1/3] dt-bindings: spi: apple,spi: Add binding for Apple SPI controllers Janne Grunau via B4 Relay
@ 2024-11-01 19:26 ` Janne Grunau via B4 Relay
2024-11-04 19:16 ` Christophe JAILLET
2024-11-01 19:26 ` [PATCH v3 3/3] MAINTAINERS: Add apple-spi driver & binding files Janne Grunau via B4 Relay
2024-11-02 13:11 ` [PATCH v3 0/3] Apple SPI controller driver Krzysztof Kozlowski
3 siblings, 1 reply; 14+ messages in thread
From: Janne Grunau via B4 Relay @ 2024-11-01 19:26 UTC (permalink / raw)
To: Hector Martin, Sven Peter, Alyssa Rosenzweig, Mark Brown,
Rob Herring, Krzysztof Kozlowski, Conor Dooley
Cc: asahi, linux-arm-kernel, linux-spi, devicetree, linux-kernel,
Janne Grunau
From: Hector Martin <marcan@marcan.st>
This SPI controller is present in Apple SoCs such as the M1 (t8103) and
M1 Pro/Max (t600x). It is a relatively straightforward design with two
16-entry FIFOs, arbitrary transfer sizes (up to 2**32 - 1) and fully
configurable word size up to 32 bits. It supports one hardware CS line
which can also be driven via the pinctrl/GPIO driver instead, if
desired. TX and RX can be independently enabled.
There are a surprising number of knobs for tweaking details of the
transfer, most of which we do not use right now. Hardware CS control
is available, but we haven't found a way to make it stay low across
multiple logical transfers, so we just use software CS control for now.
There is also a shared DMA offload coprocessor that can be used to handle
larger transfers without requiring an IRQ every 8-16 words, but that
feature depends on a bunch of scaffolding that isn't ready to be
upstreamed yet, so leave it for later.
The hardware shares some register bit definitions with spi-s3c24xx which
suggests it has a shared legacy with Samsung SoCs, but it is too
different to warrant sharing a driver.
Signed-off-by: Hector Martin <marcan@marcan.st>
Signed-off-by: Janne Grunau <j@jannau.net>
---
drivers/spi/Kconfig | 11 +
drivers/spi/Makefile | 1 +
drivers/spi/spi-apple.c | 531 ++++++++++++++++++++++++++++++++++++++++++++++++
3 files changed, 543 insertions(+)
diff --git a/drivers/spi/Kconfig b/drivers/spi/Kconfig
index ec1550c698d5f384f2c9ad74ebaccfcbdcfe7986..98a5d3f0dd52caa7ca3d6f906189542652978240 100644
--- a/drivers/spi/Kconfig
+++ b/drivers/spi/Kconfig
@@ -96,6 +96,17 @@ config SPI_AMLOGIC_SPIFC_A1
This enables master mode support for the SPIFC (SPI flash
controller) available in Amlogic A1 (A113L SoC).
+config SPI_APPLE
+ tristate "Apple SoC SPI Controller platform driver"
+ depends on ARCH_APPLE || COMPILE_TEST
+ help
+ This enables support for the SPI controller present on
+ many Apple SoCs, including the t8103 (M1), t8112 (M2)
+ and t600x (M1 Pro/Max/Ultra). Multiple SPI controller
+ instances are present on the SoC and each connects usually
+ to a single device like spi-nor (nvram), input device controller
+ or fingerprint sensor.
+
config SPI_AR934X
tristate "Qualcomm Atheros AR934X/QCA95XX SPI controller driver"
depends on ATH79 || COMPILE_TEST
diff --git a/drivers/spi/Makefile b/drivers/spi/Makefile
index a9b1bc259b68d1852250601ceafb0ac446b24f69..f059e2a5e5c6c9afce65922e5f77977f8cab82c4 100644
--- a/drivers/spi/Makefile
+++ b/drivers/spi/Makefile
@@ -19,6 +19,7 @@ obj-$(CONFIG_SPI_ALTERA) += spi-altera-platform.o
obj-$(CONFIG_SPI_ALTERA_CORE) += spi-altera-core.o
obj-$(CONFIG_SPI_ALTERA_DFL) += spi-altera-dfl.o
obj-$(CONFIG_SPI_AMLOGIC_SPIFC_A1) += spi-amlogic-spifc-a1.o
+obj-$(CONFIG_SPI_APPLE) += spi-apple.o
obj-$(CONFIG_SPI_AR934X) += spi-ar934x.o
obj-$(CONFIG_SPI_ARMADA_3700) += spi-armada-3700.o
obj-$(CONFIG_SPI_ASPEED_SMC) += spi-aspeed-smc.o
diff --git a/drivers/spi/spi-apple.c b/drivers/spi/spi-apple.c
new file mode 100644
index 0000000000000000000000000000000000000000..1a3f61501db56d0d7689cc3d6f987bf636130cdb
--- /dev/null
+++ b/drivers/spi/spi-apple.c
@@ -0,0 +1,531 @@
+// SPDX-License-Identifier: GPL-2.0
+//
+// Apple SoC SPI device driver
+//
+// Copyright The Asahi Linux Contributors
+//
+// Based on spi-sifive.c, Copyright 2018 SiFive, Inc.
+
+#include <linux/bitfield.h>
+#include <linux/bits.h>
+#include <linux/clk.h>
+#include <linux/module.h>
+#include <linux/interrupt.h>
+#include <linux/io.h>
+#include <linux/of.h>
+#include <linux/platform_device.h>
+#include <linux/pm_runtime.h>
+#include <linux/spi/spi.h>
+
+#define APPLE_SPI_CTRL 0x000
+#define APPLE_SPI_CTRL_RUN BIT(0)
+#define APPLE_SPI_CTRL_TX_RESET BIT(2)
+#define APPLE_SPI_CTRL_RX_RESET BIT(3)
+
+#define APPLE_SPI_CFG 0x004
+#define APPLE_SPI_CFG_CPHA BIT(1)
+#define APPLE_SPI_CFG_CPOL BIT(2)
+#define APPLE_SPI_CFG_MODE GENMASK(6, 5)
+#define APPLE_SPI_CFG_MODE_POLLED 0
+#define APPLE_SPI_CFG_MODE_IRQ 1
+#define APPLE_SPI_CFG_MODE_DMA 2
+#define APPLE_SPI_CFG_IE_RXCOMPLETE BIT(7)
+#define APPLE_SPI_CFG_IE_TXRXTHRESH BIT(8)
+#define APPLE_SPI_CFG_LSB_FIRST BIT(13)
+#define APPLE_SPI_CFG_WORD_SIZE GENMASK(16, 15)
+#define APPLE_SPI_CFG_WORD_SIZE_8B 0
+#define APPLE_SPI_CFG_WORD_SIZE_16B 1
+#define APPLE_SPI_CFG_WORD_SIZE_32B 2
+#define APPLE_SPI_CFG_FIFO_THRESH GENMASK(18, 17)
+#define APPLE_SPI_CFG_FIFO_THRESH_8B 0
+#define APPLE_SPI_CFG_FIFO_THRESH_4B 1
+#define APPLE_SPI_CFG_FIFO_THRESH_1B 2
+#define APPLE_SPI_CFG_IE_TXCOMPLETE BIT(21)
+
+#define APPLE_SPI_STATUS 0x008
+#define APPLE_SPI_STATUS_RXCOMPLETE BIT(0)
+#define APPLE_SPI_STATUS_TXRXTHRESH BIT(1)
+#define APPLE_SPI_STATUS_TXCOMPLETE BIT(2)
+
+#define APPLE_SPI_PIN 0x00c
+#define APPLE_SPI_PIN_KEEP_MOSI BIT(0)
+#define APPLE_SPI_PIN_CS BIT(1)
+
+#define APPLE_SPI_TXDATA 0x010
+#define APPLE_SPI_RXDATA 0x020
+#define APPLE_SPI_CLKDIV 0x030
+#define APPLE_SPI_CLKDIV_MAX 0x7ff
+#define APPLE_SPI_RXCNT 0x034
+#define APPLE_SPI_WORD_DELAY 0x038
+#define APPLE_SPI_TXCNT 0x04c
+
+#define APPLE_SPI_FIFOSTAT 0x10c
+#define APPLE_SPI_FIFOSTAT_TXFULL BIT(4)
+#define APPLE_SPI_FIFOSTAT_LEVEL_TX GENMASK(15, 8)
+#define APPLE_SPI_FIFOSTAT_RXEMPTY BIT(20)
+#define APPLE_SPI_FIFOSTAT_LEVEL_RX GENMASK(31, 24)
+
+#define APPLE_SPI_IE_XFER 0x130
+#define APPLE_SPI_IF_XFER 0x134
+#define APPLE_SPI_XFER_RXCOMPLETE BIT(0)
+#define APPLE_SPI_XFER_TXCOMPLETE BIT(1)
+
+#define APPLE_SPI_IE_FIFO 0x138
+#define APPLE_SPI_IF_FIFO 0x13c
+#define APPLE_SPI_FIFO_RXTHRESH BIT(4)
+#define APPLE_SPI_FIFO_TXTHRESH BIT(5)
+#define APPLE_SPI_FIFO_RXFULL BIT(8)
+#define APPLE_SPI_FIFO_TXEMPTY BIT(9)
+#define APPLE_SPI_FIFO_RXUNDERRUN BIT(16)
+#define APPLE_SPI_FIFO_TXOVERFLOW BIT(17)
+
+#define APPLE_SPI_SHIFTCFG 0x150
+#define APPLE_SPI_SHIFTCFG_CLK_ENABLE BIT(0)
+#define APPLE_SPI_SHIFTCFG_CS_ENABLE BIT(1)
+#define APPLE_SPI_SHIFTCFG_AND_CLK_DATA BIT(8)
+#define APPLE_SPI_SHIFTCFG_CS_AS_DATA BIT(9)
+#define APPLE_SPI_SHIFTCFG_TX_ENABLE BIT(10)
+#define APPLE_SPI_SHIFTCFG_RX_ENABLE BIT(11)
+#define APPLE_SPI_SHIFTCFG_BITS GENMASK(21, 16)
+#define APPLE_SPI_SHIFTCFG_OVERRIDE_CS BIT(24)
+
+#define APPLE_SPI_PINCFG 0x154
+#define APPLE_SPI_PINCFG_KEEP_CLK BIT(0)
+#define APPLE_SPI_PINCFG_KEEP_CS BIT(1)
+#define APPLE_SPI_PINCFG_KEEP_MOSI BIT(2)
+#define APPLE_SPI_PINCFG_CLK_IDLE_VAL BIT(8)
+#define APPLE_SPI_PINCFG_CS_IDLE_VAL BIT(9)
+#define APPLE_SPI_PINCFG_MOSI_IDLE_VAL BIT(10)
+
+#define APPLE_SPI_DELAY_PRE 0x160
+#define APPLE_SPI_DELAY_POST 0x168
+#define APPLE_SPI_DELAY_ENABLE BIT(0)
+#define APPLE_SPI_DELAY_NO_INTERBYTE BIT(1)
+#define APPLE_SPI_DELAY_SET_SCK BIT(4)
+#define APPLE_SPI_DELAY_SET_MOSI BIT(6)
+#define APPLE_SPI_DELAY_SCK_VAL BIT(8)
+#define APPLE_SPI_DELAY_MOSI_VAL BIT(12)
+
+#define APPLE_SPI_FIFO_DEPTH 16
+
+/*
+ * The slowest refclock available is 24MHz, the highest divider is 0x7ff,
+ * the largest word size is 32 bits, the FIFO depth is 16, the maximum
+ * intra-word delay is 0xffff refclocks. So the maximum time a transfer
+ * cycle can take is:
+ *
+ * (0x7ff * 32 + 0xffff) * 16 / 24e6 Hz ~= 87ms
+ *
+ * Double it and round it up to 200ms for good measure.
+ */
+#define APPLE_SPI_TIMEOUT_MS 200
+
+struct apple_spi {
+ void __iomem *regs; /* MMIO register address */
+ struct clk *clk; /* bus clock */
+ struct completion done; /* wake-up from interrupt */
+};
+
+static inline void reg_write(struct apple_spi *spi, int offset, u32 value)
+{
+ writel_relaxed(value, spi->regs + offset);
+}
+
+static inline u32 reg_read(struct apple_spi *spi, int offset)
+{
+ return readl_relaxed(spi->regs + offset);
+}
+
+static inline void reg_mask(struct apple_spi *spi, int offset, u32 clear, u32 set)
+{
+ u32 val = reg_read(spi, offset);
+
+ val &= ~clear;
+ val |= set;
+ reg_write(spi, offset, val);
+}
+
+static void apple_spi_init(struct apple_spi *spi)
+{
+ /* Set CS high (inactive) and disable override and auto-CS */
+ reg_write(spi, APPLE_SPI_PIN, APPLE_SPI_PIN_CS);
+ reg_mask(spi, APPLE_SPI_SHIFTCFG, APPLE_SPI_SHIFTCFG_OVERRIDE_CS, 0);
+ reg_mask(spi, APPLE_SPI_PINCFG, APPLE_SPI_PINCFG_CS_IDLE_VAL, APPLE_SPI_PINCFG_KEEP_CS);
+
+ /* Reset FIFOs */
+ reg_write(spi, APPLE_SPI_CTRL, APPLE_SPI_CTRL_RX_RESET | APPLE_SPI_CTRL_TX_RESET);
+
+ /* Configure defaults */
+ reg_write(spi, APPLE_SPI_CFG,
+ FIELD_PREP(APPLE_SPI_CFG_FIFO_THRESH, APPLE_SPI_CFG_FIFO_THRESH_8B) |
+ FIELD_PREP(APPLE_SPI_CFG_MODE, APPLE_SPI_CFG_MODE_IRQ) |
+ FIELD_PREP(APPLE_SPI_CFG_WORD_SIZE, APPLE_SPI_CFG_WORD_SIZE_8B));
+
+ /* Disable IRQs */
+ reg_write(spi, APPLE_SPI_IE_FIFO, 0);
+ reg_write(spi, APPLE_SPI_IE_XFER, 0);
+
+ /* Disable delays */
+ reg_write(spi, APPLE_SPI_DELAY_PRE, 0);
+ reg_write(spi, APPLE_SPI_DELAY_POST, 0);
+}
+
+static int apple_spi_prepare_message(struct spi_controller *ctlr, struct spi_message *msg)
+{
+ struct apple_spi *spi = spi_controller_get_devdata(ctlr);
+ struct spi_device *device = msg->spi;
+
+ u32 cfg = ((device->mode & SPI_CPHA ? APPLE_SPI_CFG_CPHA : 0) |
+ (device->mode & SPI_CPOL ? APPLE_SPI_CFG_CPOL : 0) |
+ (device->mode & SPI_LSB_FIRST ? APPLE_SPI_CFG_LSB_FIRST : 0));
+
+ /* Update core config */
+ reg_mask(spi, APPLE_SPI_CFG,
+ APPLE_SPI_CFG_CPHA | APPLE_SPI_CFG_CPOL | APPLE_SPI_CFG_LSB_FIRST, cfg);
+
+ return 0;
+}
+
+static void apple_spi_set_cs(struct spi_device *device, bool is_high)
+{
+ struct apple_spi *spi = spi_controller_get_devdata(device->controller);
+
+ reg_mask(spi, APPLE_SPI_PIN, APPLE_SPI_PIN_CS, is_high ? APPLE_SPI_PIN_CS : 0);
+}
+
+static bool apple_spi_prep_transfer(struct apple_spi *spi, struct spi_transfer *t)
+{
+ u32 cr, fifo_threshold;
+
+ /* Calculate and program the clock rate */
+ cr = DIV_ROUND_UP(clk_get_rate(spi->clk), t->speed_hz);
+ reg_write(spi, APPLE_SPI_CLKDIV, min_t(u32, cr, APPLE_SPI_CLKDIV_MAX));
+
+ /* Update bits per word */
+ reg_mask(spi, APPLE_SPI_SHIFTCFG, APPLE_SPI_SHIFTCFG_BITS,
+ FIELD_PREP(APPLE_SPI_SHIFTCFG_BITS, t->bits_per_word));
+
+ /* We will want to poll if the time we need to wait is
+ * less than the context switching time.
+ * Let's call that threshold 5us. The operation will take:
+ * bits_per_word * fifo_threshold / hz <= 5 * 10^-6
+ * 200000 * bits_per_word * fifo_threshold <= hz
+ */
+ fifo_threshold = APPLE_SPI_FIFO_DEPTH / 2;
+ return (200000 * t->bits_per_word * fifo_threshold) <= t->speed_hz;
+}
+
+static irqreturn_t apple_spi_irq(int irq, void *dev_id)
+{
+ struct apple_spi *spi = dev_id;
+ u32 fifo = reg_read(spi, APPLE_SPI_IF_FIFO) & reg_read(spi, APPLE_SPI_IE_FIFO);
+ u32 xfer = reg_read(spi, APPLE_SPI_IF_XFER) & reg_read(spi, APPLE_SPI_IE_XFER);
+
+ if (fifo || xfer) {
+ /* Disable interrupts until next transfer */
+ reg_write(spi, APPLE_SPI_IE_XFER, 0);
+ reg_write(spi, APPLE_SPI_IE_FIFO, 0);
+ complete(&spi->done);
+ return IRQ_HANDLED;
+ }
+
+ return IRQ_NONE;
+}
+
+static int apple_spi_wait(struct apple_spi *spi, u32 fifo_bit, u32 xfer_bit, int poll)
+{
+ int ret = 0;
+
+ if (poll) {
+ u32 fifo, xfer;
+ unsigned long timeout = jiffies + APPLE_SPI_TIMEOUT_MS * HZ / 1000;
+
+ do {
+ fifo = reg_read(spi, APPLE_SPI_IF_FIFO);
+ xfer = reg_read(spi, APPLE_SPI_IF_XFER);
+ if (time_after(jiffies, timeout)) {
+ ret = -ETIMEDOUT;
+ break;
+ }
+ } while (!((fifo & fifo_bit) || (xfer & xfer_bit)));
+ } else {
+ reinit_completion(&spi->done);
+ reg_write(spi, APPLE_SPI_IE_XFER, xfer_bit);
+ reg_write(spi, APPLE_SPI_IE_FIFO, fifo_bit);
+
+ if (!wait_for_completion_timeout(&spi->done,
+ msecs_to_jiffies(APPLE_SPI_TIMEOUT_MS)))
+ ret = -ETIMEDOUT;
+
+ reg_write(spi, APPLE_SPI_IE_XFER, 0);
+ reg_write(spi, APPLE_SPI_IE_FIFO, 0);
+ }
+
+ return ret;
+}
+
+static void apple_spi_tx(struct apple_spi *spi, const void **tx_ptr, u32 *left,
+ unsigned int bytes_per_word)
+{
+ u32 inuse, words, wrote;
+
+ if (!*tx_ptr)
+ return;
+
+ inuse = FIELD_GET(APPLE_SPI_FIFOSTAT_LEVEL_TX, reg_read(spi, APPLE_SPI_FIFOSTAT));
+ words = wrote = min_t(u32, *left, APPLE_SPI_FIFO_DEPTH - inuse);
+
+ if (!words)
+ return;
+
+ *left -= words;
+
+ switch (bytes_per_word) {
+ case 1: {
+ const u8 *p = *tx_ptr;
+
+ while (words--)
+ reg_write(spi, APPLE_SPI_TXDATA, *p++);
+ break;
+ }
+ case 2: {
+ const u16 *p = *tx_ptr;
+
+ while (words--)
+ reg_write(spi, APPLE_SPI_TXDATA, *p++);
+ break;
+ }
+ case 4: {
+ const u32 *p = *tx_ptr;
+
+ while (words--)
+ reg_write(spi, APPLE_SPI_TXDATA, *p++);
+ break;
+ }
+ default:
+ WARN_ON(1);
+ }
+
+ *tx_ptr = ((u8 *)*tx_ptr) + bytes_per_word * wrote;
+}
+
+static void apple_spi_rx(struct apple_spi *spi, void **rx_ptr, u32 *left,
+ unsigned int bytes_per_word)
+{
+ u32 words, read;
+
+ if (!*rx_ptr)
+ return;
+
+ words = read = FIELD_GET(APPLE_SPI_FIFOSTAT_LEVEL_RX, reg_read(spi, APPLE_SPI_FIFOSTAT));
+ WARN_ON(words > *left);
+
+ if (!words)
+ return;
+
+ *left -= min_t(u32, *left, words);
+
+ switch (bytes_per_word) {
+ case 1: {
+ u8 *p = *rx_ptr;
+
+ while (words--)
+ *p++ = reg_read(spi, APPLE_SPI_RXDATA);
+ break;
+ }
+ case 2: {
+ u16 *p = *rx_ptr;
+
+ while (words--)
+ *p++ = reg_read(spi, APPLE_SPI_RXDATA);
+ break;
+ }
+ case 4: {
+ u32 *p = *rx_ptr;
+
+ while (words--)
+ *p++ = reg_read(spi, APPLE_SPI_RXDATA);
+ break;
+ }
+ default:
+ WARN_ON(1);
+ }
+
+ *rx_ptr = ((u8 *)*rx_ptr) + bytes_per_word * read;
+}
+
+static int apple_spi_transfer_one(struct spi_controller *ctlr, struct spi_device *device,
+ struct spi_transfer *t)
+{
+ struct apple_spi *spi = spi_controller_get_devdata(ctlr);
+ bool poll = apple_spi_prep_transfer(spi, t);
+ const void *tx_ptr = t->tx_buf;
+ void *rx_ptr = t->rx_buf;
+ unsigned int bytes_per_word;
+ u32 words, remaining_tx, remaining_rx;
+ u32 xfer_flags = 0;
+ u32 fifo_flags;
+ int retries = 100;
+ int ret = 0;
+
+ if (t->bits_per_word > 16)
+ bytes_per_word = 4;
+ else if (t->bits_per_word > 8)
+ bytes_per_word = 2;
+ else
+ bytes_per_word = 1;
+
+ words = t->len / bytes_per_word;
+ remaining_tx = tx_ptr ? words : 0;
+ remaining_rx = rx_ptr ? words : 0;
+
+ /* Reset FIFOs */
+ reg_write(spi, APPLE_SPI_CTRL, APPLE_SPI_CTRL_RX_RESET | APPLE_SPI_CTRL_TX_RESET);
+
+ /* Clear IRQ flags */
+ reg_write(spi, APPLE_SPI_IF_XFER, ~0);
+ reg_write(spi, APPLE_SPI_IF_FIFO, ~0);
+
+ /* Determine transfer completion flags we wait for */
+ if (tx_ptr)
+ xfer_flags |= APPLE_SPI_XFER_TXCOMPLETE;
+ if (rx_ptr)
+ xfer_flags |= APPLE_SPI_XFER_RXCOMPLETE;
+
+ /* Set transfer length */
+ reg_write(spi, APPLE_SPI_TXCNT, remaining_tx);
+ reg_write(spi, APPLE_SPI_RXCNT, remaining_rx);
+
+ /* Prime transmit FIFO */
+ apple_spi_tx(spi, &tx_ptr, &remaining_tx, bytes_per_word);
+
+ /* Start transfer */
+ reg_write(spi, APPLE_SPI_CTRL, APPLE_SPI_CTRL_RUN);
+
+ /* TX again since a few words get popped off immediately */
+ apple_spi_tx(spi, &tx_ptr, &remaining_tx, bytes_per_word);
+
+ while (xfer_flags) {
+ fifo_flags = 0;
+
+ if (remaining_tx)
+ fifo_flags |= APPLE_SPI_FIFO_TXTHRESH;
+ if (remaining_rx)
+ fifo_flags |= APPLE_SPI_FIFO_RXTHRESH;
+
+ /* Wait for anything to happen */
+ ret = apple_spi_wait(spi, fifo_flags, xfer_flags, poll);
+ if (ret) {
+ dev_err(&ctlr->dev, "transfer timed out (remaining %d tx, %d rx)\n",
+ remaining_tx, remaining_rx);
+ goto err;
+ }
+
+ /* Stop waiting on transfer halves once they complete */
+ xfer_flags &= ~reg_read(spi, APPLE_SPI_IF_XFER);
+
+ /* Transmit and receive everything we can */
+ apple_spi_tx(spi, &tx_ptr, &remaining_tx, bytes_per_word);
+ apple_spi_rx(spi, &rx_ptr, &remaining_rx, bytes_per_word);
+ }
+
+ /*
+ * Sometimes the transfer completes before the last word is in the RX FIFO.
+ * Normally one retry is all it takes to get the last word out.
+ */
+ while (remaining_rx && retries--)
+ apple_spi_rx(spi, &rx_ptr, &remaining_rx, bytes_per_word);
+
+ if (remaining_tx)
+ dev_err(&ctlr->dev, "transfer completed with %d words left to transmit\n",
+ remaining_tx);
+ if (remaining_rx)
+ dev_err(&ctlr->dev, "transfer completed with %d words left to receive\n",
+ remaining_rx);
+
+err:
+ fifo_flags = reg_read(spi, APPLE_SPI_IF_FIFO);
+ WARN_ON(fifo_flags & APPLE_SPI_FIFO_TXOVERFLOW);
+ WARN_ON(fifo_flags & APPLE_SPI_FIFO_RXUNDERRUN);
+
+ /* Stop transfer */
+ reg_write(spi, APPLE_SPI_CTRL, 0);
+
+ return ret;
+}
+
+static int apple_spi_probe(struct platform_device *pdev)
+{
+ struct apple_spi *spi;
+ int ret, irq;
+ struct spi_controller *ctlr;
+
+ ctlr = devm_spi_alloc_master(&pdev->dev, sizeof(struct apple_spi));
+ if (!ctlr)
+ return -ENOMEM;
+
+ spi = spi_controller_get_devdata(ctlr);
+ init_completion(&spi->done);
+ platform_set_drvdata(pdev, ctlr);
+
+ spi->regs = devm_platform_ioremap_resource(pdev, 0);
+ if (IS_ERR(spi->regs))
+ return PTR_ERR(spi->regs);
+
+ spi->clk = devm_clk_get_enabled(&pdev->dev, NULL);
+ if (IS_ERR(spi->clk))
+ return dev_err_probe(&pdev->dev, PTR_ERR(spi->clk),
+ "Unable to find or enable bus clock\n");
+
+ irq = platform_get_irq(pdev, 0);
+ if (irq < 0)
+ return irq;
+
+ ret = devm_request_irq(&pdev->dev, irq, apple_spi_irq, 0,
+ dev_name(&pdev->dev), spi);
+ if (ret)
+ return dev_err_probe(&pdev->dev, ret, "Unable to bind to interrupt\n");
+
+ ctlr->dev.of_node = pdev->dev.of_node;
+ ctlr->bus_num = pdev->id;
+ ctlr->num_chipselect = 1;
+ ctlr->mode_bits = SPI_CPHA | SPI_CPOL | SPI_LSB_FIRST;
+ ctlr->bits_per_word_mask = SPI_BPW_RANGE_MASK(1, 32);
+ ctlr->prepare_message = apple_spi_prepare_message;
+ ctlr->set_cs = apple_spi_set_cs;
+ ctlr->transfer_one = apple_spi_transfer_one;
+ ctlr->auto_runtime_pm = true;
+
+ pm_runtime_set_active(&pdev->dev);
+ ret = devm_pm_runtime_enable(&pdev->dev);
+ if (ret < 0)
+ return ret;
+
+ apple_spi_init(spi);
+
+ ret = devm_spi_register_controller(&pdev->dev, ctlr);
+ if (ret < 0)
+ return dev_err_probe(&pdev->dev, ret, "devm_spi_register_controller failed\n");
+
+ return 0;
+}
+
+static const struct of_device_id apple_spi_of_match[] = {
+ { .compatible = "apple,spi", },
+ {}
+};
+MODULE_DEVICE_TABLE(of, apple_spi_of_match);
+
+static struct platform_driver apple_spi_driver = {
+ .probe = apple_spi_probe,
+ .driver = {
+ .name = "apple-spi",
+ .owner = THIS_MODULE,
+ .of_match_table = apple_spi_of_match,
+ },
+};
+module_platform_driver(apple_spi_driver);
+
+MODULE_AUTHOR("Hector Martin <marcan@marcan.st>");
+MODULE_DESCRIPTION("Apple SoC SPI driver");
+MODULE_LICENSE("GPL");
--
2.47.0
^ permalink raw reply related [flat|nested] 14+ messages in thread
* [PATCH v3 3/3] MAINTAINERS: Add apple-spi driver & binding files
2024-11-01 19:26 [PATCH v3 0/3] Apple SPI controller driver Janne Grunau via B4 Relay
2024-11-01 19:26 ` [PATCH v3 1/3] dt-bindings: spi: apple,spi: Add binding for Apple SPI controllers Janne Grunau via B4 Relay
2024-11-01 19:26 ` [PATCH v3 2/3] spi: apple: Add driver for Apple SPI controller Janne Grunau via B4 Relay
@ 2024-11-01 19:26 ` Janne Grunau via B4 Relay
2024-11-02 13:11 ` [PATCH v3 0/3] Apple SPI controller driver Krzysztof Kozlowski
3 siblings, 0 replies; 14+ messages in thread
From: Janne Grunau via B4 Relay @ 2024-11-01 19:26 UTC (permalink / raw)
To: Hector Martin, Sven Peter, Alyssa Rosenzweig, Mark Brown,
Rob Herring, Krzysztof Kozlowski, Conor Dooley
Cc: asahi, linux-arm-kernel, linux-spi, devicetree, linux-kernel,
Janne Grunau
From: Hector Martin <marcan@marcan.st>
This Apple SPI controller is present on Apple ARM SoCs (t8103/t6000).
Splitting this change from the binding/driver commits to avoid merge
conflicts with other things touching this section, as usual.
Signed-off-by: Hector Martin <marcan@marcan.st>
Signed-off-by: Janne Grunau <j@jannau.net>
---
MAINTAINERS | 2 ++
1 file changed, 2 insertions(+)
diff --git a/MAINTAINERS b/MAINTAINERS
index cc40a9d9b8cd10e2e00caa5a5881381cd40c0d9a..552febcb12a95766ff502960782941d9d016d5e0 100644
--- a/MAINTAINERS
+++ b/MAINTAINERS
@@ -2068,6 +2068,7 @@ F: Documentation/devicetree/bindings/pci/apple,pcie.yaml
F: Documentation/devicetree/bindings/pinctrl/apple,pinctrl.yaml
F: Documentation/devicetree/bindings/power/apple*
F: Documentation/devicetree/bindings/pwm/apple,s5l-fpwm.yaml
+F: Documentation/devicetree/bindings/spi/apple,spi.yaml
F: Documentation/devicetree/bindings/watchdog/apple,wdt.yaml
F: arch/arm64/boot/dts/apple/
F: drivers/bluetooth/hci_bcm4377.c
@@ -2085,6 +2086,7 @@ F: drivers/nvmem/apple-efuses.c
F: drivers/pinctrl/pinctrl-apple-gpio.c
F: drivers/pwm/pwm-apple.c
F: drivers/soc/apple/*
+F: drivers/spi/spi-apple.c
F: drivers/watchdog/apple_wdt.c
F: include/dt-bindings/interrupt-controller/apple-aic.h
F: include/dt-bindings/pinctrl/apple.h
--
2.47.0
^ permalink raw reply related [flat|nested] 14+ messages in thread
* Re: [PATCH v3 1/3] dt-bindings: spi: apple,spi: Add binding for Apple SPI controllers
2024-11-01 19:26 ` [PATCH v3 1/3] dt-bindings: spi: apple,spi: Add binding for Apple SPI controllers Janne Grunau via B4 Relay
@ 2024-11-02 2:36 ` Nick Chan
2024-11-02 8:36 ` Janne Grunau
2024-11-02 8:39 ` Mark Kettenis
2024-11-04 18:56 ` Conor Dooley
1 sibling, 2 replies; 14+ messages in thread
From: Nick Chan @ 2024-11-02 2:36 UTC (permalink / raw)
To: j, Hector Martin, Sven Peter, Alyssa Rosenzweig, Mark Brown,
Rob Herring, Krzysztof Kozlowski, Conor Dooley
Cc: asahi, linux-arm-kernel, linux-spi, devicetree, linux-kernel
On 2/11/2024 03:26, Janne Grunau via B4 Relay wrote:
[...]
> +properties:
> + compatible:
> + items:
> + - enum:
> + - apple,t8103-spi
> + - apple,t8112-spi
> + - apple,t6000-spi
> + - const: apple,spi
Apple A7-A11 SoCs seems to use a Samsung SPI block, so apple,spi is too
generic. Fallback to something like apple,t8103-spi instead.
[...]
Nick Chan
^ permalink raw reply [flat|nested] 14+ messages in thread
* Re: [PATCH v3 1/3] dt-bindings: spi: apple,spi: Add binding for Apple SPI controllers
2024-11-02 2:36 ` Nick Chan
@ 2024-11-02 8:36 ` Janne Grunau
2024-11-02 8:39 ` Mark Kettenis
1 sibling, 0 replies; 14+ messages in thread
From: Janne Grunau @ 2024-11-02 8:36 UTC (permalink / raw)
To: Nick Chan
Cc: Hector Martin, Sven Peter, Alyssa Rosenzweig, Mark Brown,
Rob Herring, Krzysztof Kozlowski, Conor Dooley, asahi,
linux-arm-kernel, linux-spi, devicetree, linux-kernel
On Sat, Nov 02, 2024 at 10:36:56AM +0800, Nick Chan wrote:
>
>
> On 2/11/2024 03:26, Janne Grunau via B4 Relay wrote:
>
> [...]
> > +properties:
> > + compatible:
> > + items:
> > + - enum:
> > + - apple,t8103-spi
> > + - apple,t8112-spi
> > + - apple,t6000-spi
> > + - const: apple,spi
> Apple A7-A11 SoCs seems to use a Samsung SPI block, so apple,spi is too
> generic. Fallback to something like apple,t8103-spi instead.
Have you looked at it? This one still seems to be somehow Samsung
related. See the previous discussion at
https://lore.kernel.org/linux-devicetree/d87ae109-4b58-7465-b16e-3bf7c9d60f1f@marcan.st/
Even the A7-A11 SPI controllers are not compatible "apple,spi" doesn't
prevent us from using something like "apple,s5l-spi" for those.
Janne
^ permalink raw reply [flat|nested] 14+ messages in thread
* Re: [PATCH v3 1/3] dt-bindings: spi: apple,spi: Add binding for Apple SPI controllers
2024-11-02 2:36 ` Nick Chan
2024-11-02 8:36 ` Janne Grunau
@ 2024-11-02 8:39 ` Mark Kettenis
2024-11-02 13:15 ` Nick Chan
1 sibling, 1 reply; 14+ messages in thread
From: Mark Kettenis @ 2024-11-02 8:39 UTC (permalink / raw)
To: Nick Chan
Cc: j, marcan, sven, alyssa, broonie, robh, krzk+dt, conor+dt, asahi,
linux-arm-kernel, linux-spi, devicetree, linux-kernel
> Date: Sat, 2 Nov 2024 10:36:56 +0800
> Content-Language: en-MW
>
> On 2/11/2024 03:26, Janne Grunau via B4 Relay wrote:
>
> [...]
> > +properties:
> > + compatible:
> > + items:
> > + - enum:
> > + - apple,t8103-spi
> > + - apple,t8112-spi
> > + - apple,t6000-spi
> > + - const: apple,spi
> Apple A7-A11 SoCs seems to use a Samsung SPI block, so apple,spi is too
> generic. Fallback to something like apple,t8103-spi instead.
Well, if that is a Samsung SPI block it probably should have a
"generic" compatible that starts with "samsung,". The M1/M2
controllers have a different SPI block (presumably) designed by Apple
themselves. So I think it is (still) appropriate that that one is
"apple,spi".
Also, (upstream) U-Boot already uses the "apple,spi" compatible. So
changing it for purity sake just causes pain.
^ permalink raw reply [flat|nested] 14+ messages in thread
* Re: [PATCH v3 0/3] Apple SPI controller driver
2024-11-01 19:26 [PATCH v3 0/3] Apple SPI controller driver Janne Grunau via B4 Relay
` (2 preceding siblings ...)
2024-11-01 19:26 ` [PATCH v3 3/3] MAINTAINERS: Add apple-spi driver & binding files Janne Grunau via B4 Relay
@ 2024-11-02 13:11 ` Krzysztof Kozlowski
2024-11-05 7:44 ` Janne Grunau
3 siblings, 1 reply; 14+ messages in thread
From: Krzysztof Kozlowski @ 2024-11-02 13:11 UTC (permalink / raw)
To: Janne Grunau
Cc: Hector Martin, Sven Peter, Alyssa Rosenzweig, Mark Brown,
Rob Herring, Krzysztof Kozlowski, Conor Dooley, asahi,
linux-arm-kernel, linux-spi, devicetree, linux-kernel
On Fri, Nov 01, 2024 at 08:26:11PM +0100, Janne Grunau wrote:
> Hi all,
>
> This updated series address the review comments from the original
> submission in 2021 [1]. It adds a new SPI controller driver for Apple
> SoCs and is based on spi-sifive. It has been tested with the generic
> jedec,spi-nor support and with a downstream driver for an Apple specific
> HID over SPI transport.
>
> As usual, I'm splitting off the MAINTAINERS and DT binding changes.
> We would rather merge the MAINTAINERS change through the Asahi-SoC
> tree to avoid merge conflicts as things trickle upstream, since
> we have other submissions touching that section of the file.
>
> The DT binding change can go via the SPI tree or via ours, but it's
> easier if we merge it, as then we can make the DT changes to
> instantiate it without worrying about DT validation failures depending
> on merge order.
>
> This is mostly Hector's work with a few minor changes to address review
> comments from me.
>
> [1] https://lore.kernel.org/linux-spi/20211212034726.26306-1-marcan@marcan.st/
>
> v2:
> - removed '#address-cells' and '#size-cells' from the bindings and added
> Rob's Rb:
Where?
Best regards,
Krzysztof
^ permalink raw reply [flat|nested] 14+ messages in thread
* Re: [PATCH v3 1/3] dt-bindings: spi: apple,spi: Add binding for Apple SPI controllers
2024-11-02 8:39 ` Mark Kettenis
@ 2024-11-02 13:15 ` Nick Chan
0 siblings, 0 replies; 14+ messages in thread
From: Nick Chan @ 2024-11-02 13:15 UTC (permalink / raw)
To: Mark Kettenis
Cc: j, marcan, sven, alyssa, broonie, robh, krzk+dt, conor+dt, asahi,
linux-arm-kernel, linux-spi, devicetree, linux-kernel
On 2/11/2024 16:39, Mark Kettenis wrote:
>> Date: Sat, 2 Nov 2024 10:36:56 +0800
>> Content-Language: en-MW
>>
>> On 2/11/2024 03:26, Janne Grunau via B4 Relay wrote:
>>
>> [...]
>>> +properties:
>>> + compatible:
>>> + items:
>>> + - enum:
>>> + - apple,t8103-spi
>>> + - apple,t8112-spi
>>> + - apple,t6000-spi
>>> + - const: apple,spi
>> Apple A7-A11 SoCs seems to use a Samsung SPI block, so apple,spi is too
>> generic. Fallback to something like apple,t8103-spi instead.
>
> Well, if that is a Samsung SPI block it probably should have a
> "generic" compatible that starts with "samsung,". The M1/M2
> controllers have a different SPI block (presumably) designed by Apple
> themselves. So I think it is (still) appropriate that that one is
> "apple,spi".
I just looked into the SPI on A7-A11 SoC in more detail instead of just
going off the ADT compatible. It seems a very big chunk of the registers
offsets and bits seems to be the same as the ones in M1. So, feel free to
ignore my comment above.
Acked-by: Nick Chan <towinchenmi@gmail.com>
>
> Also, (upstream) U-Boot already uses the "apple,spi" compatible. So
> changing it for purity sake just causes pain.
Well, if upstream U-Boot is using it, then I agree that "apple,spi"
should continue to be used.
>
Nick Chan
^ permalink raw reply [flat|nested] 14+ messages in thread
* Re: [PATCH v3 1/3] dt-bindings: spi: apple,spi: Add binding for Apple SPI controllers
2024-11-01 19:26 ` [PATCH v3 1/3] dt-bindings: spi: apple,spi: Add binding for Apple SPI controllers Janne Grunau via B4 Relay
2024-11-02 2:36 ` Nick Chan
@ 2024-11-04 18:56 ` Conor Dooley
2024-11-05 7:46 ` Janne Grunau
1 sibling, 1 reply; 14+ messages in thread
From: Conor Dooley @ 2024-11-04 18:56 UTC (permalink / raw)
To: j
Cc: Hector Martin, Sven Peter, Alyssa Rosenzweig, Mark Brown,
Rob Herring, Krzysztof Kozlowski, Conor Dooley, asahi,
linux-arm-kernel, linux-spi, devicetree, linux-kernel
[-- Attachment #1: Type: text/plain, Size: 276 bytes --]
On Fri, Nov 01, 2024 at 08:26:12PM +0100, Janne Grunau via B4 Relay wrote:
> + spi: spi@39b104000 {
nit: the label here serves no purpose, and could be dropped. No need to
respin for that obviously.
Reviewed-by: Conor Dooley <conor.dooley@microchip.com>
Cheers,
Conor.
[-- Attachment #2: signature.asc --]
[-- Type: application/pgp-signature, Size: 228 bytes --]
^ permalink raw reply [flat|nested] 14+ messages in thread
* Re: [PATCH v3 2/3] spi: apple: Add driver for Apple SPI controller
2024-11-01 19:26 ` [PATCH v3 2/3] spi: apple: Add driver for Apple SPI controller Janne Grunau via B4 Relay
@ 2024-11-04 19:16 ` Christophe JAILLET
2024-11-05 7:50 ` Janne Grunau
0 siblings, 1 reply; 14+ messages in thread
From: Christophe JAILLET @ 2024-11-04 19:16 UTC (permalink / raw)
To: Janne Grunau via B4 Relay
Cc: asahi, linux-arm-kernel, linux-spi, devicetree, linux-kernel,
Janne Grunau, Hector Martin, Sven Peter, Alyssa Rosenzweig,
Mark Brown, Rob Herring, Krzysztof Kozlowski, Conor Dooley
Le 01/11/2024 à 20:26, Janne Grunau via B4 Relay a écrit :
> From: Hector Martin <marcan-WKacp4m3WJJeoWH0uzbU5w@public.gmane.org>
>
> This SPI controller is present in Apple SoCs such as the M1 (t8103) and
> M1 Pro/Max (t600x). It is a relatively straightforward design with two
> 16-entry FIFOs, arbitrary transfer sizes (up to 2**32 - 1) and fully
> configurable word size up to 32 bits. It supports one hardware CS line
> which can also be driven via the pinctrl/GPIO driver instead, if
> desired. TX and RX can be independently enabled.
>
> There are a surprising number of knobs for tweaking details of the
> transfer, most of which we do not use right now. Hardware CS control
> is available, but we haven't found a way to make it stay low across
> multiple logical transfers, so we just use software CS control for now.
>
> There is also a shared DMA offload coprocessor that can be used to handle
> larger transfers without requiring an IRQ every 8-16 words, but that
> feature depends on a bunch of scaffolding that isn't ready to be
> upstreamed yet, so leave it for later.
>
> The hardware shares some register bit definitions with spi-s3c24xx which
> suggests it has a shared legacy with Samsung SoCs, but it is too
> different to warrant sharing a driver.
>
> Signed-off-by: Hector Martin <marcan-WKacp4m3WJJeoWH0uzbU5w@public.gmane.org>
> Signed-off-by: Janne Grunau <j@jannau.net>
> ---
Hi,
> diff --git a/drivers/spi/spi-apple.c b/drivers/spi/spi-apple.c
> new file mode 100644
> index 0000000000000000000000000000000000000000..1a3f61501db56d0d7689cc3d6f987bf636130cdb
> --- /dev/null
> +++ b/drivers/spi/spi-apple.c
> @@ -0,0 +1,531 @@
> +// SPDX-License-Identifier: GPL-2.0
> +//
> +// Apple SoC SPI device driver
> +//
> +// Copyright The Asahi Linux Contributors
> +//
> +// Based on spi-sifive.c, Copyright 2018 SiFive, Inc.
> +
> +#include <linux/bitfield.h>
> +#include <linux/bits.h>
> +#include <linux/clk.h>
> +#include <linux/module.h>
Move a few lines below to keep alphabetical order?
> +#include <linux/interrupt.h>
> +#include <linux/io.h>
> +#include <linux/of.h>
> +#include <linux/platform_device.h>
> +#include <linux/pm_runtime.h>
> +#include <linux/spi/spi.h>
...
> +static int apple_spi_probe(struct platform_device *pdev)
> +{
> + struct apple_spi *spi;
> + int ret, irq;
> + struct spi_controller *ctlr;
> +
> + ctlr = devm_spi_alloc_master(&pdev->dev, sizeof(struct apple_spi));
> + if (!ctlr)
> + return -ENOMEM;
> +
> + spi = spi_controller_get_devdata(ctlr);
> + init_completion(&spi->done);
> + platform_set_drvdata(pdev, ctlr);
Is it needed?
There is no platform_get_drvdata()
> +
> + spi->regs = devm_platform_ioremap_resource(pdev, 0);
> + if (IS_ERR(spi->regs))
> + return PTR_ERR(spi->regs);
> +
> + spi->clk = devm_clk_get_enabled(&pdev->dev, NULL);
> + if (IS_ERR(spi->clk))
> + return dev_err_probe(&pdev->dev, PTR_ERR(spi->clk),
> + "Unable to find or enable bus clock\n");
> +
> + irq = platform_get_irq(pdev, 0);
> + if (irq < 0)
> + return irq;
> +
> + ret = devm_request_irq(&pdev->dev, irq, apple_spi_irq, 0,
> + dev_name(&pdev->dev), spi);
> + if (ret)
> + return dev_err_probe(&pdev->dev, ret, "Unable to bind to interrupt\n");
> +
> + ctlr->dev.of_node = pdev->dev.of_node;
> + ctlr->bus_num = pdev->id;
> + ctlr->num_chipselect = 1;
> + ctlr->mode_bits = SPI_CPHA | SPI_CPOL | SPI_LSB_FIRST;
> + ctlr->bits_per_word_mask = SPI_BPW_RANGE_MASK(1, 32);
> + ctlr->prepare_message = apple_spi_prepare_message;
> + ctlr->set_cs = apple_spi_set_cs;
> + ctlr->transfer_one = apple_spi_transfer_one;
> + ctlr->auto_runtime_pm = true;
> +
> + pm_runtime_set_active(&pdev->dev);
> + ret = devm_pm_runtime_enable(&pdev->dev);
> + if (ret < 0)
> + return ret;
> +
> + apple_spi_init(spi);
> +
> + ret = devm_spi_register_controller(&pdev->dev, ctlr);
> + if (ret < 0)
> + return dev_err_probe(&pdev->dev, ret, "devm_spi_register_controller failed\n");
> +
> + return 0;
> +}
...
CJ
^ permalink raw reply [flat|nested] 14+ messages in thread
* Re: [PATCH v3 0/3] Apple SPI controller driver
2024-11-02 13:11 ` [PATCH v3 0/3] Apple SPI controller driver Krzysztof Kozlowski
@ 2024-11-05 7:44 ` Janne Grunau
0 siblings, 0 replies; 14+ messages in thread
From: Janne Grunau @ 2024-11-05 7:44 UTC (permalink / raw)
To: Krzysztof Kozlowski
Cc: Hector Martin, Sven Peter, Alyssa Rosenzweig, Mark Brown,
Rob Herring, Krzysztof Kozlowski, Conor Dooley, asahi,
linux-arm-kernel, linux-spi, devicetree, linux-kernel
On Sat, Nov 02, 2024 at 02:11:51PM +0100, Krzysztof Kozlowski wrote:
> On Fri, Nov 01, 2024 at 08:26:11PM +0100, Janne Grunau wrote:
> > Hi all,
> >
> > This updated series address the review comments from the original
> > submission in 2021 [1]. It adds a new SPI controller driver for Apple
> > SoCs and is based on spi-sifive. It has been tested with the generic
> > jedec,spi-nor support and with a downstream driver for an Apple specific
> > HID over SPI transport.
> >
> > As usual, I'm splitting off the MAINTAINERS and DT binding changes.
> > We would rather merge the MAINTAINERS change through the Asahi-SoC
> > tree to avoid merge conflicts as things trickle upstream, since
> > we have other submissions touching that section of the file.
> >
> > The DT binding change can go via the SPI tree or via ours, but it's
> > easier if we merge it, as then we can make the DT changes to
> > instantiate it without worrying about DT validation failures depending
> > on merge order.
> >
> > This is mostly Hector's work with a few minor changes to address review
> > comments from me.
> >
> > [1] https://lore.kernel.org/linux-spi/20211212034726.26306-1-marcan@marcan.st/
> >
> > v2:
> > - removed '#address-cells' and '#size-cells' from the bindings and added
> > Rob's Rb:
>
> Where?
Apparently only in my mind. fixed for v4
thanks,
Janne
^ permalink raw reply [flat|nested] 14+ messages in thread
* Re: [PATCH v3 1/3] dt-bindings: spi: apple,spi: Add binding for Apple SPI controllers
2024-11-04 18:56 ` Conor Dooley
@ 2024-11-05 7:46 ` Janne Grunau
0 siblings, 0 replies; 14+ messages in thread
From: Janne Grunau @ 2024-11-05 7:46 UTC (permalink / raw)
To: Conor Dooley
Cc: Hector Martin, Sven Peter, Alyssa Rosenzweig, Mark Brown,
Rob Herring, Krzysztof Kozlowski, Conor Dooley, asahi,
linux-arm-kernel, linux-spi, devicetree, linux-kernel
On Mon, Nov 04, 2024 at 06:56:59PM +0000, Conor Dooley wrote:
> On Fri, Nov 01, 2024 at 08:26:12PM +0100, Janne Grunau via B4 Relay wrote:
> > + spi: spi@39b104000 {
>
> nit: the label here serves no purpose, and could be dropped. No need to
> respin for that obviously.
removed since there will be a respin for minor driver changes
> Reviewed-by: Conor Dooley <conor.dooley@microchip.com>
thanks
Janne
^ permalink raw reply [flat|nested] 14+ messages in thread
* Re: [PATCH v3 2/3] spi: apple: Add driver for Apple SPI controller
2024-11-04 19:16 ` Christophe JAILLET
@ 2024-11-05 7:50 ` Janne Grunau
0 siblings, 0 replies; 14+ messages in thread
From: Janne Grunau @ 2024-11-05 7:50 UTC (permalink / raw)
To: Christophe JAILLET
Cc: Janne Grunau via B4 Relay, asahi, linux-arm-kernel, linux-spi,
devicetree, linux-kernel, Hector Martin, Sven Peter,
Alyssa Rosenzweig, Mark Brown, Rob Herring, Krzysztof Kozlowski,
Conor Dooley
On Mon, Nov 04, 2024 at 08:16:25PM +0100, Christophe JAILLET wrote:
> Le 01/11/2024 à 20:26, Janne Grunau via B4 Relay a écrit :
> > From: Hector Martin <marcan-WKacp4m3WJJeoWH0uzbU5w@public.gmane.org>
> >
> > This SPI controller is present in Apple SoCs such as the M1 (t8103) and
> > M1 Pro/Max (t600x). It is a relatively straightforward design with two
> > 16-entry FIFOs, arbitrary transfer sizes (up to 2**32 - 1) and fully
> > configurable word size up to 32 bits. It supports one hardware CS line
> > which can also be driven via the pinctrl/GPIO driver instead, if
> > desired. TX and RX can be independently enabled.
> >
> > There are a surprising number of knobs for tweaking details of the
> > transfer, most of which we do not use right now. Hardware CS control
> > is available, but we haven't found a way to make it stay low across
> > multiple logical transfers, so we just use software CS control for now.
> >
> > There is also a shared DMA offload coprocessor that can be used to handle
> > larger transfers without requiring an IRQ every 8-16 words, but that
> > feature depends on a bunch of scaffolding that isn't ready to be
> > upstreamed yet, so leave it for later.
> >
> > The hardware shares some register bit definitions with spi-s3c24xx which
> > suggests it has a shared legacy with Samsung SoCs, but it is too
> > different to warrant sharing a driver.
> >
> > Signed-off-by: Hector Martin <marcan-WKacp4m3WJJeoWH0uzbU5w@public.gmane.org>
> > Signed-off-by: Janne Grunau <j@jannau.net>
> > ---
>
> Hi,
>
> > diff --git a/drivers/spi/spi-apple.c b/drivers/spi/spi-apple.c
> > new file mode 100644
> > index 0000000000000000000000000000000000000000..1a3f61501db56d0d7689cc3d6f987bf636130cdb
> > --- /dev/null
> > +++ b/drivers/spi/spi-apple.c
> > @@ -0,0 +1,531 @@
> > +// SPDX-License-Identifier: GPL-2.0
> > +//
> > +// Apple SoC SPI device driver
> > +//
> > +// Copyright The Asahi Linux Contributors
> > +//
> > +// Based on spi-sifive.c, Copyright 2018 SiFive, Inc.
> > +
> > +#include <linux/bitfield.h>
> > +#include <linux/bits.h>
> > +#include <linux/clk.h>
> > +#include <linux/module.h>
>
> Move a few lines below to keep alphabetical order?
done
> > +#include <linux/interrupt.h>
> > +#include <linux/io.h>
> > +#include <linux/of.h>
> > +#include <linux/platform_device.h>
> > +#include <linux/pm_runtime.h>
> > +#include <linux/spi/spi.h>
>
> ...
>
> > +static int apple_spi_probe(struct platform_device *pdev)
> > +{
> > + struct apple_spi *spi;
> > + int ret, irq;
> > + struct spi_controller *ctlr;
> > +
> > + ctlr = devm_spi_alloc_master(&pdev->dev, sizeof(struct apple_spi));
> > + if (!ctlr)
> > + return -ENOMEM;
> > +
> > + spi = spi_controller_get_devdata(ctlr);
> > + init_completion(&spi->done);
> > + platform_set_drvdata(pdev, ctlr);
>
> Is it needed?
> There is no platform_get_drvdata()
no, it is not used anymore. It's a leftover from v1 which used
platform_get_drvdata() in apple_spi_remove() which is gone now.
thanks, I'll send a v4 shortly
Janne
^ permalink raw reply [flat|nested] 14+ messages in thread
end of thread, other threads:[~2024-11-05 7:50 UTC | newest]
Thread overview: 14+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2024-11-01 19:26 [PATCH v3 0/3] Apple SPI controller driver Janne Grunau via B4 Relay
2024-11-01 19:26 ` [PATCH v3 1/3] dt-bindings: spi: apple,spi: Add binding for Apple SPI controllers Janne Grunau via B4 Relay
2024-11-02 2:36 ` Nick Chan
2024-11-02 8:36 ` Janne Grunau
2024-11-02 8:39 ` Mark Kettenis
2024-11-02 13:15 ` Nick Chan
2024-11-04 18:56 ` Conor Dooley
2024-11-05 7:46 ` Janne Grunau
2024-11-01 19:26 ` [PATCH v3 2/3] spi: apple: Add driver for Apple SPI controller Janne Grunau via B4 Relay
2024-11-04 19:16 ` Christophe JAILLET
2024-11-05 7:50 ` Janne Grunau
2024-11-01 19:26 ` [PATCH v3 3/3] MAINTAINERS: Add apple-spi driver & binding files Janne Grunau via B4 Relay
2024-11-02 13:11 ` [PATCH v3 0/3] Apple SPI controller driver Krzysztof Kozlowski
2024-11-05 7:44 ` Janne Grunau
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).