From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 7F94AC433EF for ; Sun, 17 Oct 2021 11:29:55 +0000 (UTC) Received: from bombadil.infradead.org (bombadil.infradead.org [198.137.202.133]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by mail.kernel.org (Postfix) with ESMTPS id 3BBBA61247 for ; Sun, 17 Oct 2021 11:29:55 +0000 (UTC) DMARC-Filter: OpenDMARC Filter v1.4.1 mail.kernel.org 3BBBA61247 Authentication-Results: mail.kernel.org; dmarc=fail (p=reject dis=none) header.from=svenpeter.dev Authentication-Results: mail.kernel.org; spf=none smtp.mailfrom=lists.infradead.org DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=lists.infradead.org; s=bombadil.20210309; h=Sender: Content-Transfer-Encoding:Content-Type:List-Subscribe:List-Help:List-Post: List-Archive:List-Unsubscribe:List-Id:Subject:Cc:To:From:Date:References: In-Reply-To:Message-Id:Mime-Version:Reply-To:Content-ID:Content-Description: Resent-Date:Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID: List-Owner; bh=gBem8eL14v3W0mwyHAe1yv2jBr+/QLiQjpPxFb6sbXU=; b=K/ioq6TFuqu4qo Rv0OtnNULPIQ6yqEzZAci7Ho6KwFqWPi8qi2+ZPA4UG7kokb5NMXX/6WdcjN1vDQBf9QWOwTORSeW HISZ9bKUnwUCvMKFlPj5dWIwqvWT92M+smLnZzlfcszywSHfEyWQ+VGpEzf7LHxKT8ZnaVimEYXbg drR1yHqFmzMak431RRxTNknFw6luUk9vPook8k4Tpe5BGOxvhrGjiP250NTKciEuy2pnf+AOV8F0n gfy4uROJGXmjT2nP8aLZGmkGZDqd9RJH/CoWdpSefvelTBNcwOM6jQ59rPwdlDgGeQ4XpLs5ep32B yZa9RdCw5LmRBwWXHdHg==; Received: from localhost ([::1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mc4L8-00CDqx-Kk; Sun, 17 Oct 2021 11:28:30 +0000 Received: from out5-smtp.messagingengine.com ([66.111.4.29]) by bombadil.infradead.org with esmtps (Exim 4.94.2 #2 (Red Hat Linux)) id 1mc4L4-00CDot-24 for linux-arm-kernel@lists.infradead.org; Sun, 17 Oct 2021 11:28:28 +0000 Received: from compute1.internal (compute1.nyi.internal [10.202.2.41]) by mailout.nyi.internal (Postfix) with ESMTP id 08A925C007C; Sun, 17 Oct 2021 07:28:21 -0400 (EDT) Received: from imap47 ([10.202.2.97]) by compute1.internal (MEProxy); Sun, 17 Oct 2021 07:28:21 -0400 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=svenpeter.dev; h=mime-version:message-id:in-reply-to:references:date:from:to :cc:subject:content-type; s=fm2; bh=pQj6+m7y4hXdLMBfvIO37cQDFQ8Q VWlHkCoWLx9Kz3Y=; b=M2LYDawK34OkgNZnvX4QfZrE6Q2PwMhfxeiWWVSg8hw2 /1xJBT9nXKggu4NkHYLwUOdhO3DEjPXq/4AfyBO6ANs7vfhCXgcDNgj9G+dubKUs PkLk3KVZpd28ffKcM/4Me5tWxDu1l8Iwj53fGS2bYvBz6Dv6g7wtcQPLsJdWk6fM aFj76R1zpJIBWAEvaNH7G/zZ8iUMtWchhV/x8WpjSYaVkjpGfZtAL4mXuWvvHh/1 2Pgs3dm1kcech8Ab6Vy9BcfihblSvGFre3Cz+AkXrL1wUiJ0WbDx5prkeUqrvMki 2sPq3vXgNlLbw55pjWy1cYknxb+rXDKTcPsFRlVqow== DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d= messagingengine.com; h=cc:content-type:date:from:in-reply-to :message-id:mime-version:references:subject:to:x-me-proxy :x-me-proxy:x-me-sender:x-me-sender:x-sasl-enc; s=fm1; bh=pQj6+m 7y4hXdLMBfvIO37cQDFQ8QVWlHkCoWLx9Kz3Y=; b=TvsyD7qyMeFDpiCqqNGsu7 qnp1XrbDvLxle6piTd2IWpwo3IWZ7q+ka2hULCdhndcYo/PwiNNKuA05TMyJQxLf /d45BYagW7IPZdUAuvIj0FQi75Sra5b6pQH0mfZ1YfUfejuqSEBDzUN6CxwA+ZL2 /v7oPIGcMDgW3YLPNiZgPh7Ra/ZA+RtQhNyz4R+6GE4QmTQsG/iDDBnmBsXvMKxe pMt8Ie9zgAdHId8+bZUI9RqxTXHqbJ/JBJFu4Kb/1Mbr/SvI4fsDNUdSX5asR7eu 8/E1imr4fU2Ps7ypmTxaDAeoVBdfqQao+2hKbYkT+jhAJ5NC+v9qks7HmzTzH5gw == X-ME-Sender: X-ME-Proxy-Cause: gggruggvucftvghtrhhoucdtuddrgedvtddrvddukedggedtucetufdoteggodetrfdotf fvucfrrhhofhhilhgvmecuhfgrshhtofgrihhlpdfqfgfvpdfurfetoffkrfgpnffqhgen uceurghilhhouhhtmecufedttdenucesvcftvggtihhpihgvnhhtshculddquddttddmne cujfgurhepofgfggfkjghffffhvffutgesthdtredtreertdenucfhrhhomhepfdfuvhgv nhcurfgvthgvrhdfuceoshhvvghnsehsvhgvnhhpvghtvghrrdguvghvqeenucggtffrrg htthgvrhhnpefgieegieffuefhtedtjefgteejteefleefgfefgfdvvddtgffhffduhedv feekffenucevlhhushhtvghrufhiiigvpedtnecurfgrrhgrmhepmhgrihhlfhhrohhmpe hsvhgvnhesshhvvghnphgvthgvrhdruggvvh X-ME-Proxy: Received: by mailuser.nyi.internal (Postfix, from userid 501) id 658022740061; Sun, 17 Oct 2021 07:28:20 -0400 (EDT) X-Mailer: MessagingEngine.com Webmail Interface User-Agent: Cyrus-JMAP/3.5.0-alpha0-1345-g8441cd7852-fm-20211006.001-g8441cd78 Mime-Version: 1.0 Message-Id: In-Reply-To: References: <20210916154911.3168-1-sven@svenpeter.dev> <20210916154911.3168-3-sven@svenpeter.dev> Date: Sun, 17 Oct 2021 13:27:59 +0200 From: "Sven Peter" To: "Mark Kettenis" Cc: "Jassi Brar" , "Rob Herring" , "Hector Martin" , "Alyssa Rosenzweig" , mohamed.mediouni@caramail.com, "Stan Skowronek" , devicetree@vger.kernel.org, linux-arm-kernel@lists.infradead.org, linux-kernel@vger.kernel.org Subject: Re: [PATCH v2 2/2] mailbox: apple: Add driver for Apple mailboxes X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20211017_042826_295618_695E3A26 X-CRM114-Status: GOOD ( 31.27 ) X-BeenThere: linux-arm-kernel@lists.infradead.org X-Mailman-Version: 2.1.34 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Content-Type: text/plain; charset="us-ascii" Content-Transfer-Encoding: 7bit Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org Hi Mark, On Sun, Oct 17, 2021, at 13:25, Mark Kettenis wrote: >> From: Sven Peter >> Date: Thu, 16 Sep 2021 17:49:11 +0200 > > Hi Sven, > >> Apple SoCs such as the M1 come with various co-processors. Mailboxes >> are used to communicate with those. This driver adds support for >> two variants of those mailboxes. >> >> Signed-off-by: Sven Peter >> --- >> MAINTAINERS | 2 + >> drivers/mailbox/Kconfig | 12 + >> drivers/mailbox/Makefile | 2 + >> drivers/mailbox/apple-mailbox.c | 431 ++++++++++++++++++++++++++++++++ >> include/linux/apple-mailbox.h | 18 ++ >> 5 files changed, 465 insertions(+) >> create mode 100644 drivers/mailbox/apple-mailbox.c >> create mode 100644 include/linux/apple-mailbox.h >> >> diff --git a/MAINTAINERS b/MAINTAINERS >> index 47de27282c98..cf0500bbea5b 100644 >> --- a/MAINTAINERS >> +++ b/MAINTAINERS >> @@ -1724,8 +1724,10 @@ F: Documentation/devicetree/bindings/mailbox/apple,mailbox.yaml >> F: Documentation/devicetree/bindings/pinctrl/apple,pinctrl.yaml >> F: arch/arm64/boot/dts/apple/ >> F: drivers/irqchip/irq-apple-aic.c >> +F: drivers/mailbox/apple-mailbox.c >> F: include/dt-bindings/interrupt-controller/apple-aic.h >> F: include/dt-bindings/pinctrl/apple.h >> +F: include/linux/apple-mailbox.h >> >> ARM/ARTPEC MACHINE SUPPORT >> M: Jesper Nilsson >> diff --git a/drivers/mailbox/Kconfig b/drivers/mailbox/Kconfig >> index c9fc06c7e685..d9cd3606040e 100644 >> --- a/drivers/mailbox/Kconfig >> +++ b/drivers/mailbox/Kconfig >> @@ -8,6 +8,18 @@ menuconfig MAILBOX >> >> if MAILBOX >> >> +config APPLE_MAILBOX >> + tristate "Apple Mailbox driver" >> + depends on ARCH_APPLE || (ARM64 && COMPILE_TEST) >> + default ARCH_APPLE >> + help >> + Apple SoCs have various co-processors required for certain >> + peripherals to work (NVMe, display controller, etc.). This >> + driver adds support for the mailbox controller used to >> + communicate with those. >> + >> + Say Y here if you have a Apple SoC. >> + >> config ARM_MHU >> tristate "ARM MHU Mailbox" >> depends on ARM_AMBA >> diff --git a/drivers/mailbox/Makefile b/drivers/mailbox/Makefile >> index c2089f04887e..338cc05e5431 100644 >> --- a/drivers/mailbox/Makefile >> +++ b/drivers/mailbox/Makefile >> @@ -58,3 +58,5 @@ obj-$(CONFIG_SUN6I_MSGBOX) += sun6i-msgbox.o >> obj-$(CONFIG_SPRD_MBOX) += sprd-mailbox.o >> >> obj-$(CONFIG_QCOM_IPCC) += qcom-ipcc.o >> + >> +obj-$(CONFIG_APPLE_MAILBOX) += apple-mailbox.o >> diff --git a/drivers/mailbox/apple-mailbox.c b/drivers/mailbox/apple-mailbox.c >> new file mode 100644 >> index 000000000000..2622a6369075 >> --- /dev/null >> +++ b/drivers/mailbox/apple-mailbox.c >> @@ -0,0 +1,431 @@ >> +// SPDX-License-Identifier: GPL-2.0-only OR MIT >> +/* >> + * Apple mailbox driver >> + * >> + * Copyright (C) 2021 The Asahi Linux Contributors >> + * >> + * This driver adds support for two mailbox variants (called ASC and M3 by >> + * Apple) found in Apple SoCs such as the M1. It consists of two FIFOs used to >> + * exchange 64+32 bit messages between the main CPU and a co-processor. >> + * Various coprocessors implement different IPC protocols based on these simple >> + * messages and shared memory buffers. >> + * >> + * Both the main CPU and the co-processor see the same set of registers but >> + * the first FIFO (A2I) is always used to transfer messages from the application >> + * processor (us) to the I/O processor and the second one (I2A) for the >> + * other direction. >> + */ >> + >> +#include >> +#include >> +#include >> +#include >> +#include >> +#include >> +#include >> +#include >> +#include >> +#include >> +#include >> + >> +#define APPLE_ASC_MBOX_CONTROL_FULL BIT(16) >> +#define APPLE_ASC_MBOX_CONTROL_EMPTY BIT(17) >> + >> +#define APPLE_ASC_MBOX_A2I_CONTROL 0x110 >> +#define APPLE_ASC_MBOX_A2I_SEND0 0x800 >> +#define APPLE_ASC_MBOX_A2I_SEND1 0x808 >> +#define APPLE_ASC_MBOX_A2I_RECV0 0x810 >> +#define APPLE_ASC_MBOX_A2I_RECV1 0x818 >> + >> +#define APPLE_ASC_MBOX_I2A_CONTROL 0x114 >> +#define APPLE_ASC_MBOX_I2A_SEND0 0x820 >> +#define APPLE_ASC_MBOX_I2A_SEND1 0x828 >> +#define APPLE_ASC_MBOX_I2A_RECV0 0x830 >> +#define APPLE_ASC_MBOX_I2A_RECV1 0x838 >> + >> +#define APPLE_M3_MBOX_CONTROL_FULL BIT(16) >> +#define APPLE_M3_MBOX_CONTROL_EMPTY BIT(17) >> + >> +#define APPLE_M3_MBOX_A2I_CONTROL 0x50 >> +#define APPLE_M3_MBOX_A2I_SEND0 0x60 >> +#define APPLE_M3_MBOX_A2I_SEND1 0x68 >> +#define APPLE_M3_MBOX_A2I_RECV0 0x70 >> +#define APPLE_M3_MBOX_A2I_RECV1 0x78 >> + >> +#define APPLE_M3_MBOX_I2A_CONTROL 0x80 >> +#define APPLE_M3_MBOX_I2A_SEND0 0x90 >> +#define APPLE_M3_MBOX_I2A_SEND1 0x98 >> +#define APPLE_M3_MBOX_I2A_RECV0 0xa0 >> +#define APPLE_M3_MBOX_I2A_RECV1 0xa8 >> + >> +#define APPLE_M3_MBOX_IRQ_ENABLE 0x48 >> +#define APPLE_M3_MBOX_IRQ_ACK 0x4c >> +#define APPLE_M3_MBOX_IRQ_A2I_EMPTY BIT(0) >> +#define APPLE_M3_MBOX_IRQ_A2I_NOT_EMPTY BIT(1) >> +#define APPLE_M3_MBOX_IRQ_I2A_EMPTY BIT(2) >> +#define APPLE_M3_MBOX_IRQ_I2A_NOT_EMPTY BIT(3) >> + >> +#define APPLE_MBOX_MSG1_OUTCNT GENMASK(56, 52) >> +#define APPLE_MBOX_MSG1_INCNT GENMASK(51, 48) >> +#define APPLE_MBOX_MSG1_OUTPTR GENMASK(47, 44) >> +#define APPLE_MBOX_MSG1_INPTR GENMASK(43, 40) >> +#define APPLE_MBOX_MSG1_MSG GENMASK(31, 0) >> + >> +struct apple_mbox_hw { >> + unsigned int control_full; >> + unsigned int control_empty; >> + >> + unsigned int a2i_control; >> + unsigned int a2i_send0; >> + unsigned int a2i_send1; >> + >> + unsigned int i2a_control; >> + unsigned int i2a_recv0; >> + unsigned int i2a_recv1; >> + >> + bool has_irq_controls; >> + unsigned int irq_enable; >> + unsigned int irq_ack; >> + unsigned int irq_bit_recv_not_empty; >> + unsigned int irq_bit_send_empty; >> +}; >> + >> +static const struct apple_mbox_hw apple_mbox_asc_hw = { >> + .control_full = APPLE_ASC_MBOX_CONTROL_FULL, >> + .control_empty = APPLE_ASC_MBOX_CONTROL_EMPTY, >> + >> + .a2i_control = APPLE_ASC_MBOX_A2I_CONTROL, >> + .a2i_send0 = APPLE_ASC_MBOX_A2I_SEND0, >> + .a2i_send1 = APPLE_ASC_MBOX_A2I_SEND1, >> + >> + .i2a_control = APPLE_ASC_MBOX_I2A_CONTROL, >> + .i2a_recv0 = APPLE_ASC_MBOX_I2A_RECV0, >> + .i2a_recv1 = APPLE_ASC_MBOX_I2A_RECV1, >> + >> + .has_irq_controls = false, >> +}; >> + >> +static const struct apple_mbox_hw apple_mbox_m3_hw = { >> + .control_full = APPLE_M3_MBOX_CONTROL_FULL, >> + .control_empty = APPLE_M3_MBOX_CONTROL_EMPTY, >> + >> + .a2i_control = APPLE_M3_MBOX_A2I_CONTROL, >> + .a2i_send0 = APPLE_M3_MBOX_A2I_SEND0, >> + .a2i_send1 = APPLE_M3_MBOX_A2I_SEND1, >> + >> + .i2a_control = APPLE_M3_MBOX_I2A_CONTROL, >> + .i2a_recv0 = APPLE_M3_MBOX_I2A_RECV0, >> + .i2a_recv1 = APPLE_M3_MBOX_I2A_RECV1, >> + >> + .has_irq_controls = true, >> + .irq_enable = APPLE_M3_MBOX_IRQ_ENABLE, >> + .irq_ack = APPLE_M3_MBOX_IRQ_ACK, >> + .irq_bit_recv_not_empty = APPLE_M3_MBOX_IRQ_I2A_NOT_EMPTY, >> + .irq_bit_send_empty = APPLE_M3_MBOX_IRQ_A2I_EMPTY, >> +}; >> + >> +static const struct of_device_id apple_mbox_of_match[] = { >> + { .compatible = "apple,t8103-asc-mailbox", .data = &apple_mbox_asc_hw }, >> + { .compatible = "apple,t8103-m3-mailbox", .data = &apple_mbox_m3_hw }, >> + {} >> +}; >> +MODULE_DEVICE_TABLE(of, apple_mbox_of_match); >> + >> +struct apple_mbox { >> + void __iomem *regs; >> + const struct apple_mbox_hw *hw; >> + >> + int irq_recv_not_empty; >> + int irq_send_empty; >> + >> + struct clk_bulk_data *clks; >> + int num_clks; >> + >> + struct mbox_chan chan; >> + >> + struct device *dev; >> + struct mbox_controller controller; >> +}; >> + >> +static bool apple_mbox_hw_can_send(struct apple_mbox *apple_mbox) >> +{ >> + u32 mbox_ctrl = >> + readl_relaxed(apple_mbox->regs + apple_mbox->hw->a2i_control); >> + >> + return !(mbox_ctrl & apple_mbox->hw->control_full); >> +} >> + >> +static int apple_mbox_hw_send(struct apple_mbox *apple_mbox, >> + struct apple_mbox_msg *msg) >> +{ >> + if (!apple_mbox_hw_can_send(apple_mbox)) >> + return -EBUSY; >> + >> + dev_dbg(apple_mbox->dev, "> TX %016llx %08x\n", msg->msg0, msg->msg1); >> + >> + /* >> + * This message may be related to a shared memory buffer and we must >> + * ensure all previous writes to normal memory are visible before >> + * submitting it. >> + */ >> + dma_wmb(); >> + >> + writeq_relaxed(msg->msg0, apple_mbox->regs + apple_mbox->hw->a2i_send0); >> + writeq_relaxed(FIELD_PREP(APPLE_MBOX_MSG1_MSG, msg->msg1), >> + apple_mbox->regs + apple_mbox->hw->a2i_send1); >> + >> + return 0; >> +} >> + >> +static bool apple_mbox_hw_can_recv(struct apple_mbox *apple_mbox) >> +{ >> + u32 mbox_ctrl = >> + readl_relaxed(apple_mbox->regs + apple_mbox->hw->i2a_control); >> + >> + return !(mbox_ctrl & apple_mbox->hw->control_empty); >> +} >> + >> +static int apple_mbox_hw_recv(struct apple_mbox *apple_mbox, >> + struct apple_mbox_msg *msg) >> +{ >> + if (!apple_mbox_hw_can_recv(apple_mbox)) >> + return -ENOMSG; >> + >> + msg->msg0 = readq_relaxed(apple_mbox->regs + apple_mbox->hw->i2a_recv0); >> + msg->msg1 = FIELD_GET( >> + APPLE_MBOX_MSG1_MSG, >> + readq_relaxed(apple_mbox->regs + apple_mbox->hw->i2a_recv1)); >> + >> + dev_dbg(apple_mbox->dev, "< RX %016llx %08x\n", msg->msg0, msg->msg1); >> + >> + /* >> + * This message may be related to a shared memory buffer and we must >> + * ensure any following reads from normal memory only happen after >> + * having read this message. >> + */ >> + dma_rmb(); >> + >> + return 0; >> +} >> + >> +static int apple_mbox_chan_send_data(struct mbox_chan *chan, void *data) >> +{ >> + struct apple_mbox *apple_mbox = chan->con_priv; >> + struct apple_mbox_msg *msg = data; >> + int ret; >> + >> + ret = apple_mbox_hw_send(apple_mbox, msg); >> + if (ret) >> + return ret; >> + >> + /* >> + * The interrupt is level triggered and will keep firing as long as the >> + * FIFO is empty. It will also keep firing if the FIFO was empty >> + * at any point in the past until it has been acknowledged at the >> + * mailbox level. By acknowledging it here we can ensure that we will >> + * only get the interrupt once the FIFO has been cleared again. >> + * If the FIFO is already empty before the ack it will fire again >> + * immediately after the ack. >> + */ >> + if (apple_mbox->hw->has_irq_controls) { >> + writel_relaxed(apple_mbox->hw->irq_bit_send_empty, >> + apple_mbox->regs + apple_mbox->hw->irq_ack); >> + } >> + enable_irq(apple_mbox->irq_send_empty); >> + >> + return 0; >> +} >> + >> +static irqreturn_t apple_mbox_send_empty_irq(int irq, void *data) >> +{ >> + struct apple_mbox *apple_mbox = data; >> + >> + /* >> + * We don't need to acknowledge the interrupt at the mailbox level >> + * here even if supported by the hardware. It will keep firing but that >> + * doesn't matter since it's disabled at the main interrupt controller. >> + * apple_mbox_chan_send_data will acknowledge it before enabling >> + * it at the main controller again. >> + */ >> + disable_irq_nosync(apple_mbox->irq_send_empty); >> + mbox_chan_txdone(&apple_mbox->chan, 0); >> + return IRQ_HANDLED; >> +} >> + >> +static irqreturn_t apple_mbox_recv_irq(int irq, void *data) >> +{ >> + struct apple_mbox *apple_mbox = data; >> + struct apple_mbox_msg msg; >> + >> + while (apple_mbox_hw_recv(apple_mbox, &msg) == 0) >> + mbox_chan_received_data(&apple_mbox->chan, (void *)&msg); >> + >> + /* >> + * The interrupt will keep firing even if there are no more messages >> + * unless we also acknowledge it at the mailbox level here. >> + * There's no race if a message comes in between the check in the while >> + * loop above and the ack below: If a new messages arrives inbetween >> + * those two the interrupt will just fire again immediately after the >> + * ack since it's level triggered. >> + */ >> + if (apple_mbox->hw->has_irq_controls) { >> + writel_relaxed(apple_mbox->hw->irq_bit_recv_not_empty, >> + apple_mbox->regs + apple_mbox->hw->irq_ack); >> + } >> + >> + return IRQ_HANDLED; >> +} >> + >> +static struct mbox_chan *apple_mbox_of_xlate(struct mbox_controller *mbox, >> + const struct of_phandle_args *spec) >> +{ >> + struct apple_mbox *apple_mbox = dev_get_drvdata(mbox->dev); >> + >> + if (spec->args_count != 0) >> + return ERR_PTR(-EINVAL); >> + if (apple_mbox->chan.con_priv) >> + return ERR_PTR(-EBUSY); >> + >> + apple_mbox->chan.con_priv = apple_mbox; >> + return &apple_mbox->chan; >> +} >> + >> +static int apple_mbox_chan_startup(struct mbox_chan *chan) >> +{ >> + struct apple_mbox *apple_mbox = chan->con_priv; >> + >> + /* >> + * Only some variants of this mailbox HW provide interrupt control >> + * at the mailbox level. We therefore need to handle enabling/disabling >> + * interrupts at the main interrupt controller anyway for hardware that >> + * doesn't. Just always keep the interrupts we care about enabled at >> + * the mailbox level so that both hardware revisions behave almost >> + * the same. >> + */ >> + if (apple_mbox->hw->has_irq_controls) { >> + writel_relaxed(apple_mbox->hw->irq_bit_recv_not_empty | >> + apple_mbox->hw->irq_bit_send_empty, >> + apple_mbox->regs + apple_mbox->hw->irq_enable); >> + } >> + >> + enable_irq(apple_mbox->irq_recv_not_empty); >> + return 0; >> +} >> + >> +static void apple_mbox_chan_shutdown(struct mbox_chan *chan) >> +{ >> + struct apple_mbox *apple_mbox = chan->con_priv; >> + >> + disable_irq(apple_mbox->irq_recv_not_empty); >> +} >> + >> +static const struct mbox_chan_ops apple_mbox_ops = { >> + .send_data = apple_mbox_chan_send_data, >> + .startup = apple_mbox_chan_startup, >> + .shutdown = apple_mbox_chan_shutdown, >> +}; >> + >> +static int apple_mbox_probe(struct platform_device *pdev) >> +{ >> + int ret; >> + const struct of_device_id *match; >> + char *irqname; >> + struct apple_mbox *mbox; >> + struct device *dev = &pdev->dev; >> + >> + match = of_match_node(apple_mbox_of_match, pdev->dev.of_node); >> + if (!match) >> + return -EINVAL; >> + if (!match->data) >> + return -EINVAL; >> + >> + mbox = devm_kzalloc(dev, sizeof(*mbox), GFP_KERNEL); >> + if (!mbox) >> + return -ENOMEM; >> + platform_set_drvdata(pdev, mbox); >> + >> + mbox->dev = dev; >> + mbox->regs = devm_platform_ioremap_resource(pdev, 0); >> + if (IS_ERR(mbox->regs)) >> + return PTR_ERR(mbox->regs); >> + >> + mbox->hw = match->data; >> + mbox->irq_recv_not_empty = >> + platform_get_irq_byname(pdev, "recv-not-empty"); >> + if (mbox->irq_recv_not_empty < 0) >> + return -ENODEV; >> + >> + mbox->irq_send_empty = platform_get_irq_byname(pdev, "send-empty"); >> + if (mbox->irq_send_empty < 0) >> + return -ENODEV; >> + >> + ret = devm_clk_bulk_get_all(dev, &mbox->clks); >> + if (ret < 0) >> + return ret; >> + mbox->num_clks = ret; >> + >> + ret = clk_bulk_prepare_enable(mbox->num_clks, mbox->clks); >> + if (ret) >> + return ret; > > Given that we now realized that the clocks are really power domains, > the clock code should probably be dropped. Makes the driver smaller > since power domains are handle automatically by the core device code. > Yup, thanks for pointing that out! I'll drop it from the code and the binding for v3. Sven _______________________________________________ linux-arm-kernel mailing list linux-arm-kernel@lists.infradead.org http://lists.infradead.org/mailman/listinfo/linux-arm-kernel