From patchwork Mon Nov 22 23:06:25 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Cristian Marussi X-Patchwork-Id: 12693386 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 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 smtp.lore.kernel.org (Postfix) with ESMTPS id A3C18C433EF for ; Mon, 22 Nov 2021 23:15:00 +0000 (UTC) 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:MIME-Version:List-Subscribe:List-Help: List-Post:List-Archive:List-Unsubscribe:List-Id:References:In-Reply-To: Message-Id:Date:Subject:Cc:To:From:Reply-To:Content-ID:Content-Description: Resent-Date:Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID: List-Owner; bh=HuaoS3s+Em3Z10BHMGDwJ0IvEBrVShLkz03qiezu/wc=; b=igQxqaaazLAjDL taUiuOAWcnQEkYtUcsoFPisMJ5aJiry9st579xn+odAayr9kkAeNOq46z4CRHEk1vgBZ/CPmhQ4o0 8qWne5qMy1siAnscVJC8Ok1W41qrn8iV4UAi2aMYHIA8YaFlOn8TBhgoilnxWcqgxdop1GJcxkz8e nMPLl7z7q4EVMfT7I7hv1ijORVcAXha+iv4mTY5Wqkxhw4A6Vb5BtQrVCDSv5l1t3hKUO36PHgkdg PTyLI89QEV3CsdWHHwE8a+TfX3xyik/qiKjsKvU2nxNwEfvpSWTygTt8A9y+osNkje++fJDAG3GoH vsRdCPDwwZ+P3EJ+Y+nw==; Received: from localhost ([::1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIV8-000LWg-B0; Mon, 22 Nov 2021 23:13:30 +0000 Received: from foss.arm.com ([217.140.110.172]) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIOy-000JU9-L4 for linux-arm-kernel@lists.infradead.org; Mon, 22 Nov 2021 23:07:10 +0000 Received: from usa-sjc-imap-foss1.foss.arm.com (unknown [10.121.207.14]) by usa-sjc-mx-foss1.foss.arm.com (Postfix) with ESMTP id 842061063; Mon, 22 Nov 2021 15:07:05 -0800 (PST) Received: from e120937-lin.home (unknown [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 41BED3F5A1; Mon, 22 Nov 2021 15:07:03 -0800 (PST) From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org Cc: sudeep.holla@arm.com, james.quinlan@broadcom.com, Jonathan.Cameron@Huawei.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, souvik.chakravarty@arm.com, cristian.marussi@arm.com Subject: [PATCH v6 01/16] firmware: arm_scmi: Perform earlier cinfo lookup call in do_xfer Date: Mon, 22 Nov 2021 23:06:25 +0000 Message-Id: <20211122230640.1345-2-cristian.marussi@arm.com> X-Mailer: git-send-email 2.17.1 In-Reply-To: <20211122230640.1345-1-cristian.marussi@arm.com> References: <20211122230640.1345-1-cristian.marussi@arm.com> X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20211122_150708_793083_65DD29DB X-CRM114-Status: UNSURE ( 9.74 ) X-CRM114-Notice: Please train this message. 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: , MIME-Version: 1.0 Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org Lookup cinfo data early in do_xfer so as to avoid any further init work on xfer structure in case of error. No functional change. Reviewed-by: Florian Fainelli Signed-off-by: Cristian Marussi --- drivers/firmware/arm_scmi/driver.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/drivers/firmware/arm_scmi/driver.c b/drivers/firmware/arm_scmi/driver.c index 768926a77f5d..3cf161f3bcc7 100644 --- a/drivers/firmware/arm_scmi/driver.c +++ b/drivers/firmware/arm_scmi/driver.c @@ -766,6 +766,10 @@ static int do_xfer(const struct scmi_protocol_handle *ph, return -EINVAL; } + cinfo = idr_find(&info->tx_idr, pi->proto->id); + if (unlikely(!cinfo)) + return -EINVAL; + /* * Initialise protocol id now from protocol handle to avoid it being * overridden by mistake (or malice) by the protocol code mangling with @@ -774,10 +778,6 @@ static int do_xfer(const struct scmi_protocol_handle *ph, xfer->hdr.protocol_id = pi->proto->id; reinit_completion(&xfer->done); - cinfo = idr_find(&info->tx_idr, xfer->hdr.protocol_id); - if (unlikely(!cinfo)) - return -EINVAL; - trace_scmi_xfer_begin(xfer->transfer_id, xfer->hdr.id, xfer->hdr.protocol_id, xfer->hdr.seq, xfer->hdr.poll_completion); From patchwork Mon Nov 22 23:06:26 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Cristian Marussi X-Patchwork-Id: 12693385 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 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 smtp.lore.kernel.org (Postfix) with ESMTPS id EB25DC433F5 for ; Mon, 22 Nov 2021 23:13:47 +0000 (UTC) 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:MIME-Version:List-Subscribe:List-Help: List-Post:List-Archive:List-Unsubscribe:List-Id:References:In-Reply-To: Message-Id:Date:Subject:Cc:To:From:Reply-To:Content-ID:Content-Description: Resent-Date:Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID: List-Owner; bh=Gw9mcvCXkBK+sHA6CPlgFylOjLsj8BnomO0sDNHNjyM=; b=govIK1zoBJ5zFe RVHhQUgf0JuI3kvTG6QcFvOsMjIq62g3ocvxLLy/Xs7CnxNRMlH0VyPBBIil9OtL/cb/XRi87yF+8 2yF5B4R20UCHRRqZdAYw+ix5cy4dPgiV0SDpCgO+BbMUanOg2jmE2OFJDdRnvC+XMVaERAsz9sgwp 4YkKjCTkNTv+dPQzVoL/oN8HcogRPhyLvFB+zWafY3R7y9IKG9jT3QfDpro8wMX4mxfXzNyT2icNF YZexBxs+bu5zrMD/CgJU5VyHsEYwbm1ec0vyrJq/YOYMwWfXNWixfSCn+UCS+TKixesT7mTLhD6x4 1HHh2kstrwNkY3hkut/g==; Received: from localhost ([::1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpITv-000LD1-7Q; Mon, 22 Nov 2021 23:12:15 +0000 Received: from foss.arm.com ([217.140.110.172]) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIOx-000JVK-Tg for linux-arm-kernel@lists.infradead.org; Mon, 22 Nov 2021 23:07:09 +0000 Received: from usa-sjc-imap-foss1.foss.arm.com (unknown [10.121.207.14]) by usa-sjc-mx-foss1.foss.arm.com (Postfix) with ESMTP id 44ED713A1; Mon, 22 Nov 2021 15:07:07 -0800 (PST) Received: from e120937-lin.home (unknown [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id B944E3F5A1; Mon, 22 Nov 2021 15:07:05 -0800 (PST) From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org Cc: sudeep.holla@arm.com, james.quinlan@broadcom.com, Jonathan.Cameron@Huawei.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, souvik.chakravarty@arm.com, cristian.marussi@arm.com Subject: [PATCH v6 02/16] firmware: arm_scmi: Set polling timeout to max_rx_timeout_ms Date: Mon, 22 Nov 2021 23:06:26 +0000 Message-Id: <20211122230640.1345-3-cristian.marussi@arm.com> X-Mailer: git-send-email 2.17.1 In-Reply-To: <20211122230640.1345-1-cristian.marussi@arm.com> References: <20211122230640.1345-1-cristian.marussi@arm.com> X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20211122_150708_060556_829D1D74 X-CRM114-Status: UNSURE ( 8.36 ) X-CRM114-Notice: Please train this message. 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: , MIME-Version: 1.0 Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org Use transport specific transmission timeout (max_rx_timeout_ms) also for polling transactions. Signed-off-by: Cristian Marussi --- drivers/firmware/arm_scmi/driver.c | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/drivers/firmware/arm_scmi/driver.c b/drivers/firmware/arm_scmi/driver.c index 3cf161f3bcc7..568562121f64 100644 --- a/drivers/firmware/arm_scmi/driver.c +++ b/drivers/firmware/arm_scmi/driver.c @@ -724,8 +724,6 @@ static void xfer_put(const struct scmi_protocol_handle *ph, __scmi_xfer_put(&info->tx_minfo, xfer); } -#define SCMI_MAX_POLL_TO_NS (100 * NSEC_PER_USEC) - static bool scmi_xfer_done_no_timeout(struct scmi_chan_info *cinfo, struct scmi_xfer *xfer, ktime_t stop) { @@ -799,7 +797,8 @@ static int do_xfer(const struct scmi_protocol_handle *ph, } if (xfer->hdr.poll_completion) { - ktime_t stop = ktime_add_ns(ktime_get(), SCMI_MAX_POLL_TO_NS); + ktime_t stop = ktime_add_ms(ktime_get(), + info->desc->max_rx_timeout_ms); spin_until_cond(scmi_xfer_done_no_timeout(cinfo, xfer, stop)); if (ktime_before(ktime_get(), stop)) { From patchwork Mon Nov 22 23:06:27 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Cristian Marussi X-Patchwork-Id: 12693388 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 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 smtp.lore.kernel.org (Postfix) with ESMTPS id BB583C433F5 for ; Mon, 22 Nov 2021 23:17:18 +0000 (UTC) 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:MIME-Version:List-Subscribe:List-Help: List-Post:List-Archive:List-Unsubscribe:List-Id:References:In-Reply-To: Message-Id:Date:Subject:Cc:To:From:Reply-To:Content-ID:Content-Description: Resent-Date:Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID: List-Owner; bh=vIF9TioxV+rgeejlhxwO++NZ0vxx1tm8N1FZtxolNQ4=; b=pJ46QqgE5q7ECO m9J+gkdWkkGQMKZwDAFF/Gj0h7uUhwTekb5rbniRHGY9dNRQBw6qox9tfa2pHCcNrom1LEhJsj9YJ yQXWpqMtoqQ3tHJ8nLJ094jQtHFjD0KMV1zKeahe7enTNZL2QMDYF+w7XPZ7ADEUfUnL6QMXGxXYE o8wpz1UYI/trVPzUsY25BzJoTbEusiyRwTvt15LTERCX1TmWYFxHZGB0iOZ32SnX34x0FJF+3d38t WgvthVrZ4DRVB5N2Og4T27UsMPwGAzrJATdCZjwqa+iX9xXz+aUs7XZQHEx9nOA3oZo00Jtg61Inz +AGCdgp9IeDjHilCjycg==; Received: from localhost ([::1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIXH-000MCy-8Z; Mon, 22 Nov 2021 23:15:44 +0000 Received: from foss.arm.com ([217.140.110.172]) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIP0-000JWe-5w for linux-arm-kernel@lists.infradead.org; Mon, 22 Nov 2021 23:07:11 +0000 Received: from usa-sjc-imap-foss1.foss.arm.com (unknown [10.121.207.14]) by usa-sjc-mx-foss1.foss.arm.com (Postfix) with ESMTP id 0222C152B; Mon, 22 Nov 2021 15:07:09 -0800 (PST) Received: from e120937-lin.home (unknown [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 7A4A33F5A1; Mon, 22 Nov 2021 15:07:07 -0800 (PST) From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org Cc: sudeep.holla@arm.com, james.quinlan@broadcom.com, Jonathan.Cameron@Huawei.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, souvik.chakravarty@arm.com, cristian.marussi@arm.com Subject: [PATCH v6 03/16] firmware: arm_scmi: Refactor message response path Date: Mon, 22 Nov 2021 23:06:27 +0000 Message-Id: <20211122230640.1345-4-cristian.marussi@arm.com> X-Mailer: git-send-email 2.17.1 In-Reply-To: <20211122230640.1345-1-cristian.marussi@arm.com> References: <20211122230640.1345-1-cristian.marussi@arm.com> X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20211122_150710_361396_CB6CD829 X-CRM114-Status: GOOD ( 15.09 ) 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: , MIME-Version: 1.0 Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org Refactor code path waiting for message responses into a dedicated helper function. No functional change. Signed-off-by: Cristian Marussi --- drivers/firmware/arm_scmi/driver.c | 88 +++++++++++++++++++----------- 1 file changed, 56 insertions(+), 32 deletions(-) diff --git a/drivers/firmware/arm_scmi/driver.c b/drivers/firmware/arm_scmi/driver.c index 568562121f64..9a8d6bfd4ebb 100644 --- a/drivers/firmware/arm_scmi/driver.c +++ b/drivers/firmware/arm_scmi/driver.c @@ -738,6 +738,61 @@ static bool scmi_xfer_done_no_timeout(struct scmi_chan_info *cinfo, ktime_after(ktime_get(), stop); } +/** + * scmi_wait_for_message_response - An helper to group all the possible ways of + * waiting for a synchronous message response. + * + * @cinfo: SCMI channel info + * @xfer: Reference to the transfer being waited for. + * + * Chooses waiting strategy (sleep-waiting vs busy-waiting) depending on + * configuration flags like xfer->hdr.poll_completion. + * + * Return: 0 on Success, error otherwise. + */ +static int scmi_wait_for_message_response(struct scmi_chan_info *cinfo, + struct scmi_xfer *xfer) +{ + struct scmi_info *info = handle_to_scmi_info(cinfo->handle); + struct device *dev = info->dev; + int ret = 0, timeout_ms = info->desc->max_rx_timeout_ms; + + if (xfer->hdr.poll_completion) { + ktime_t stop = ktime_add_ms(ktime_get(), timeout_ms); + + spin_until_cond(scmi_xfer_done_no_timeout(cinfo, xfer, stop)); + if (ktime_before(ktime_get(), stop)) { + unsigned long flags; + + /* + * Do not fetch_response if an out-of-order delayed + * response is being processed. + */ + spin_lock_irqsave(&xfer->lock, flags); + if (xfer->state == SCMI_XFER_SENT_OK) { + info->desc->ops->fetch_response(cinfo, xfer); + xfer->state = SCMI_XFER_RESP_OK; + } + spin_unlock_irqrestore(&xfer->lock, flags); + } else { + dev_err(dev, + "timed out in resp(caller: %pS) - polling\n", + (void *)_RET_IP_); + ret = -ETIMEDOUT; + } + } else { + /* And we wait for the response. */ + if (!wait_for_completion_timeout(&xfer->done, + msecs_to_jiffies(timeout_ms))) { + dev_err(dev, "timed out in resp(caller: %pS)\n", + (void *)_RET_IP_); + ret = -ETIMEDOUT; + } + } + + return ret; +} + /** * do_xfer() - Do one transfer * @@ -752,7 +807,6 @@ static int do_xfer(const struct scmi_protocol_handle *ph, struct scmi_xfer *xfer) { int ret; - int timeout; const struct scmi_protocol_instance *pi = ph_to_pi(ph); struct scmi_info *info = handle_to_scmi_info(pi->handle); struct device *dev = info->dev; @@ -796,37 +850,7 @@ static int do_xfer(const struct scmi_protocol_handle *ph, return ret; } - if (xfer->hdr.poll_completion) { - ktime_t stop = ktime_add_ms(ktime_get(), - info->desc->max_rx_timeout_ms); - - spin_until_cond(scmi_xfer_done_no_timeout(cinfo, xfer, stop)); - if (ktime_before(ktime_get(), stop)) { - unsigned long flags; - - /* - * Do not fetch_response if an out-of-order delayed - * response is being processed. - */ - spin_lock_irqsave(&xfer->lock, flags); - if (xfer->state == SCMI_XFER_SENT_OK) { - info->desc->ops->fetch_response(cinfo, xfer); - xfer->state = SCMI_XFER_RESP_OK; - } - spin_unlock_irqrestore(&xfer->lock, flags); - } else { - ret = -ETIMEDOUT; - } - } else { - /* And we wait for the response. */ - timeout = msecs_to_jiffies(info->desc->max_rx_timeout_ms); - if (!wait_for_completion_timeout(&xfer->done, timeout)) { - dev_err(dev, "timed out in resp(caller: %pS)\n", - (void *)_RET_IP_); - ret = -ETIMEDOUT; - } - } - + ret = scmi_wait_for_message_response(cinfo, xfer); if (!ret && xfer->hdr.status) ret = scmi_to_linux_errno(xfer->hdr.status); From patchwork Mon Nov 22 23:06:28 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Cristian Marussi X-Patchwork-Id: 12693389 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 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 smtp.lore.kernel.org (Postfix) with ESMTPS id 5B15EC433EF for ; Mon, 22 Nov 2021 23:18:25 +0000 (UTC) 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:MIME-Version:List-Subscribe:List-Help: List-Post:List-Archive:List-Unsubscribe:List-Id:References:In-Reply-To: Message-Id:Date:Subject:Cc:To:From:Reply-To:Content-ID:Content-Description: Resent-Date:Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID: List-Owner; bh=XjubwfKkjkVUNHhTTQohYFq19qgiSjHf8jObOWYg1ZE=; b=z3kkDxO7BioRgb VB1MzjsbY0zJNXo3wcTW5snVrdlKCcfHYqLGPr0oahYEmFviqKAsIQ2uGkvoN6wrxO/5FkN7YzuvP StY03wXY1TupQAmOU21Yrq05U/HeVxk4czW1k/VBsAiLjuDOdp/YFXhM2Ie6qfes0sPIH1ksA9031 VzQSzCZMXf0Nq/Y6mNwqLvh4KZ6f0EoaYf1YHs5tcvrbumFRfc9Z8RKTWi7lFxwkmxvmdSq8OHb6K p80DvII51ihlSR4Ymh61Q9XA3L5M2LHkQiwpybazR3e/p66j5Tdv5Zu2659v52Y1YAQCWb7M6Jqf9 L/X1H4BdjTHcF7VVSvjg==; Received: from localhost ([::1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIYP-000MZz-Lw; Mon, 22 Nov 2021 23:16:54 +0000 Received: from foss.arm.com ([217.140.110.172]) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIP1-000JXh-Bs for linux-arm-kernel@lists.infradead.org; Mon, 22 Nov 2021 23:07:12 +0000 Received: from usa-sjc-imap-foss1.foss.arm.com (unknown [10.121.207.14]) by usa-sjc-mx-foss1.foss.arm.com (Postfix) with ESMTP id C78B91516; Mon, 22 Nov 2021 15:07:10 -0800 (PST) Received: from e120937-lin.home (unknown [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 385073F5A1; Mon, 22 Nov 2021 15:07:09 -0800 (PST) From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org Cc: sudeep.holla@arm.com, james.quinlan@broadcom.com, Jonathan.Cameron@Huawei.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, souvik.chakravarty@arm.com, cristian.marussi@arm.com Subject: [PATCH v6 04/16] include: trace: Add new scmi_xfer_response_wait event Date: Mon, 22 Nov 2021 23:06:28 +0000 Message-Id: <20211122230640.1345-5-cristian.marussi@arm.com> X-Mailer: git-send-email 2.17.1 In-Reply-To: <20211122230640.1345-1-cristian.marussi@arm.com> References: <20211122230640.1345-1-cristian.marussi@arm.com> X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20211122_150711_513182_911B2E3D X-CRM114-Status: UNSURE ( 7.92 ) X-CRM114-Notice: Please train this message. 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: , MIME-Version: 1.0 Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org Having a new step to trace SCMI stack while it waits for synchronous responses is useful to analyze system performance when changing waiting mode between polling and interrupt completion. Signed-off-by: Cristian Marussi --- v5 --> v6 - removed atomic flag / poll is enough - added timeout field --- include/trace/events/scmi.h | 28 ++++++++++++++++++++++++++++ 1 file changed, 28 insertions(+) diff --git a/include/trace/events/scmi.h b/include/trace/events/scmi.h index f3a4b4d60714..cee4b2b64ae4 100644 --- a/include/trace/events/scmi.h +++ b/include/trace/events/scmi.h @@ -33,6 +33,34 @@ TRACE_EVENT(scmi_xfer_begin, __entry->seq, __entry->poll) ); +TRACE_EVENT(scmi_xfer_response_wait, + TP_PROTO(int transfer_id, u8 msg_id, u8 protocol_id, u16 seq, + u32 timeout, bool poll), + TP_ARGS(transfer_id, msg_id, protocol_id, seq, timeout, poll), + + TP_STRUCT__entry( + __field(int, transfer_id) + __field(u8, msg_id) + __field(u8, protocol_id) + __field(u16, seq) + __field(u32, timeout) + __field(bool, poll) + ), + + TP_fast_assign( + __entry->transfer_id = transfer_id; + __entry->msg_id = msg_id; + __entry->protocol_id = protocol_id; + __entry->seq = seq; + __entry->timeout = timeout; + __entry->poll = poll; + ), + + TP_printk("transfer_id=%d msg_id=%u protocol_id=%u seq=%u tmo_ms=%u poll=%u", + __entry->transfer_id, __entry->msg_id, __entry->protocol_id, + __entry->seq, __entry->timeout, __entry->poll) +); + TRACE_EVENT(scmi_xfer_end, TP_PROTO(int transfer_id, u8 msg_id, u8 protocol_id, u16 seq, int status), From patchwork Mon Nov 22 23:06:29 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Cristian Marussi X-Patchwork-Id: 12693390 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 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 smtp.lore.kernel.org (Postfix) with ESMTPS id 6439FC433FE for ; Mon, 22 Nov 2021 23:19:28 +0000 (UTC) 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:MIME-Version:List-Subscribe:List-Help: List-Post:List-Archive:List-Unsubscribe:List-Id:References:In-Reply-To: Message-Id:Date:Subject:Cc:To:From:Reply-To:Content-ID:Content-Description: Resent-Date:Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID: List-Owner; bh=e2lSX+TolJTQGl6f1tGfY1SM642JI2KUs+q/9IYQtfE=; b=kICHSsL1d5AgJ5 68Rvt39xFyQPYtw+RTHwDVvN9QYZkAW9LMpjrHkaC3gbnbEMJzlKVrOvmqxKsoo4zPxdeDKGC3Tv6 aWC3zX1pY9qRu2ypMCevT33yOZR6e6EF1tiq/DiqEjSgx0k3SMZYSqXvWo+tDe7ibT61K0DO9/Neu +K8Vn71T+wumvw2P3zhCkjnyOnq1Q9p+2ymt7IhORLdSLUf3afC0sf28MmgW8TdV00/6UGnjAe31H vXcZrXN7oY6O6C9bH4aT4S/oVElYOz23nfgHvGRdSfdAmRHen1G8OuzDCIcLyEF5NZWVMSI8PPEzO 4nOFRNA19nfdbKn+fhWw==; Received: from localhost ([::1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIZL-000MqZ-FU; Mon, 22 Nov 2021 23:17:52 +0000 Received: from foss.arm.com ([217.140.110.172]) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIP3-000JXh-0Q for linux-arm-kernel@lists.infradead.org; Mon, 22 Nov 2021 23:07:14 +0000 Received: from usa-sjc-imap-foss1.foss.arm.com (unknown [10.121.207.14]) by usa-sjc-mx-foss1.foss.arm.com (Postfix) with ESMTP id B0B2DED1; Mon, 22 Nov 2021 15:07:12 -0800 (PST) Received: from e120937-lin.home (unknown [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 08B433F5A1; Mon, 22 Nov 2021 15:07:10 -0800 (PST) From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org Cc: sudeep.holla@arm.com, james.quinlan@broadcom.com, Jonathan.Cameron@Huawei.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, souvik.chakravarty@arm.com, cristian.marussi@arm.com Subject: [PATCH v6 05/16] firmware: arm_scmi: Use new trace event scmi_xfer_response_wait Date: Mon, 22 Nov 2021 23:06:29 +0000 Message-Id: <20211122230640.1345-6-cristian.marussi@arm.com> X-Mailer: git-send-email 2.17.1 In-Reply-To: <20211122230640.1345-1-cristian.marussi@arm.com> References: <20211122230640.1345-1-cristian.marussi@arm.com> X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20211122_150713_140187_6EBF07FE X-CRM114-Status: UNSURE ( 8.36 ) X-CRM114-Notice: Please train this message. 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: , MIME-Version: 1.0 Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org Use new trace event to mark start of waiting for response section. Signed-off-by: Cristian Marussi --- v5 --> v6 - removed atomic flag / poll is enough - added timeout field v4 --> v5 - consider atomic_enable flag too --- drivers/firmware/arm_scmi/driver.c | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/drivers/firmware/arm_scmi/driver.c b/drivers/firmware/arm_scmi/driver.c index 9a8d6bfd4ebb..476b91845e40 100644 --- a/drivers/firmware/arm_scmi/driver.c +++ b/drivers/firmware/arm_scmi/driver.c @@ -757,6 +757,11 @@ static int scmi_wait_for_message_response(struct scmi_chan_info *cinfo, struct device *dev = info->dev; int ret = 0, timeout_ms = info->desc->max_rx_timeout_ms; + trace_scmi_xfer_response_wait(xfer->transfer_id, xfer->hdr.id, + xfer->hdr.protocol_id, xfer->hdr.seq, + timeout_ms, + xfer->hdr.poll_completion); + if (xfer->hdr.poll_completion) { ktime_t stop = ktime_add_ms(ktime_get(), timeout_ms); From patchwork Mon Nov 22 23:06:30 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Cristian Marussi X-Patchwork-Id: 12693391 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 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 smtp.lore.kernel.org (Postfix) with ESMTPS id A624AC433F5 for ; Mon, 22 Nov 2021 23:20:29 +0000 (UTC) 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:MIME-Version:List-Subscribe:List-Help: List-Post:List-Archive:List-Unsubscribe:List-Id:References:In-Reply-To: Message-Id:Date:Subject:Cc:To:From:Reply-To:Content-ID:Content-Description: Resent-Date:Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID: List-Owner; bh=rhPbTvm/RpKi+OhLHCsJLCTiEVZF6uy8731/Rhn3MZ0=; b=EC4L4m6wnnRCvK Ac8CmzdZdTE8aa+ChmYD+g3+kY2JdLJCpMEAtlnjlmUXZB8lkQJiUE9u9yZtuXyw370wtWqw6VfvW 64TuV0oAwQT8shC6FFNC794VyTToiGSLz6v/DVhs7X1MGDBZeXr7PtabR0USSq6gJ2jFHiGuBzpIf A61IK/23HhkAdHD2L9JSEyPiobmCa3BIbe1zebsXL6NfJTge4nVckov+e/IXA3PC1C9viXZM0972Z Qv2IEnfpRqL53VUIT2H6FEWCY6b5GIWOzTWnT7X55D3WgyKLPlAIhyS76kv0PJGLkqC8AxdG7pATU QhBN+W3aU1GgHIN/m4rg==; Received: from localhost ([::1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIaO-000NCY-4s; Mon, 22 Nov 2021 23:18:57 +0000 Received: from foss.arm.com ([217.140.110.172]) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIP5-000JZM-1P for linux-arm-kernel@lists.infradead.org; Mon, 22 Nov 2021 23:07:16 +0000 Received: from usa-sjc-imap-foss1.foss.arm.com (unknown [10.121.207.14]) by usa-sjc-mx-foss1.foss.arm.com (Postfix) with ESMTP id 7E1F21063; Mon, 22 Nov 2021 15:07:14 -0800 (PST) Received: from e120937-lin.home (unknown [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id E80343F5A1; Mon, 22 Nov 2021 15:07:12 -0800 (PST) From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org Cc: sudeep.holla@arm.com, james.quinlan@broadcom.com, Jonathan.Cameron@Huawei.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, souvik.chakravarty@arm.com, cristian.marussi@arm.com Subject: [PATCH v6 06/16] firmware: arm_scmi: Add configurable polling mode for transports Date: Mon, 22 Nov 2021 23:06:30 +0000 Message-Id: <20211122230640.1345-7-cristian.marussi@arm.com> X-Mailer: git-send-email 2.17.1 In-Reply-To: <20211122230640.1345-1-cristian.marussi@arm.com> References: <20211122230640.1345-1-cristian.marussi@arm.com> X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20211122_150715_268325_46916F12 X-CRM114-Status: GOOD ( 18.95 ) 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: , MIME-Version: 1.0 Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org SCMI communications along TX channels can optionally be provided of a completion interrupt; when such interrupt is not available, command transactions should rely on polling, where the SCMI core takes care to repeatedly evaluate the transport-specific .poll_done() function, if available, to determine if and when a request was fully completed or timed out. Such mechanism is already present and working on a single transfer base: SCMI protocols can indeed enable hdr.poll_completion on specific commands ahead of each transfer and cause that transaction to be handled with polling. Introduce a couple of flags to be able to enforce such polling behaviour globally at will: - scmi_desc.force_polling: to statically switch the whole transport to polling mode. - scmi_chan_info.no_completion_irq: to switch a single channel dynamically to polling mode if, at runtime, is determined that no completion interrupt was available for such channel. Signed-off-by: Cristian Marussi --- v5 --> v6 - removed check on replies received by IRQs when xfer was requested as poll_completion (not all transport can suppress IRQs on an xfer basis) v4 --> v5 - make force_polling const - introduce polling_enabled flag to simplify checks on do_xfer v3 --> v4: - renamed .needs_polling flag to .no_completion_irq - refactored error path when polling needed but not supported --- drivers/firmware/arm_scmi/common.h | 11 +++++++++++ drivers/firmware/arm_scmi/driver.c | 17 +++++++++++++++++ 2 files changed, 28 insertions(+) diff --git a/drivers/firmware/arm_scmi/common.h b/drivers/firmware/arm_scmi/common.h index 6438b5248c24..99b74f4d39b6 100644 --- a/drivers/firmware/arm_scmi/common.h +++ b/drivers/firmware/arm_scmi/common.h @@ -339,11 +339,19 @@ void scmi_protocol_release(const struct scmi_handle *handle, u8 protocol_id); * @dev: Reference to device in the SCMI hierarchy corresponding to this * channel * @handle: Pointer to SCMI entity handle + * @no_completion_irq: Flag to indicate that this channel has no completion + * interrupt mechanism for synchronous commands. + * This can be dynamically set by transports at run-time + * inside their provided .chan_setup(). + * @polling_enabled: Flag used to annotate if polling mode is currently enabled + * on this channel. * @transport_info: Transport layer related information */ struct scmi_chan_info { struct device *dev; struct scmi_handle *handle; + bool no_completion_irq; + bool polling_enabled; void *transport_info; }; @@ -402,6 +410,8 @@ struct scmi_device *scmi_child_dev_find(struct device *parent, * be pending simultaneously in the system. May be overridden by the * get_max_msg op. * @max_msg_size: Maximum size of data per message that can be handled. + * @force_polling: Flag to force this whole transport to use SCMI core polling + * mechanism instead of completion interrupts even if available. */ struct scmi_desc { int (*transport_init)(void); @@ -410,6 +420,7 @@ struct scmi_desc { int max_rx_timeout_ms; int max_msg; int max_msg_size; + const bool force_polling; }; #ifdef CONFIG_ARM_SCMI_TRANSPORT_MAILBOX diff --git a/drivers/firmware/arm_scmi/driver.c b/drivers/firmware/arm_scmi/driver.c index 476b91845e40..8a30b832899c 100644 --- a/drivers/firmware/arm_scmi/driver.c +++ b/drivers/firmware/arm_scmi/driver.c @@ -817,6 +817,7 @@ static int do_xfer(const struct scmi_protocol_handle *ph, struct device *dev = info->dev; struct scmi_chan_info *cinfo; + /* Check for polling request on custom command xfers at first */ if (xfer->hdr.poll_completion && !info->desc->ops->poll_done) { dev_warn_once(dev, "Polling mode is not supported by transport.\n"); @@ -827,6 +828,10 @@ static int do_xfer(const struct scmi_protocol_handle *ph, if (unlikely(!cinfo)) return -EINVAL; + /* Initialized to true ONLY if also supported by transport. */ + if (cinfo->polling_enabled) + xfer->hdr.poll_completion = true; + /* * Initialise protocol id now from protocol handle to avoid it being * overridden by mistake (or malice) by the protocol code mangling with @@ -1527,6 +1532,18 @@ static int scmi_chan_setup(struct scmi_info *info, struct device *dev, if (ret) return ret; + if (tx && (cinfo->no_completion_irq || info->desc->force_polling)) { + if (info->desc->ops->poll_done) { + dev_info(dev, + "Enabled polling mode TX channel - prot_id:%d\n", + prot_id); + cinfo->polling_enabled = true; + } else { + dev_warn(dev, + "Polling mode NOT supported by transport.\n"); + } + } + idr_alloc: ret = idr_alloc(idr, cinfo, prot_id, prot_id + 1, GFP_KERNEL); if (ret != prot_id) { From patchwork Mon Nov 22 23:06:31 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Cristian Marussi X-Patchwork-Id: 12693393 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 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 smtp.lore.kernel.org (Postfix) with ESMTPS id CA2FEC433F5 for ; Mon, 22 Nov 2021 23:22:07 +0000 (UTC) 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:MIME-Version:List-Subscribe:List-Help: List-Post:List-Archive:List-Unsubscribe:List-Id:References:In-Reply-To: Message-Id:Date:Subject:Cc:To:From:Reply-To:Content-ID:Content-Description: Resent-Date:Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID: List-Owner; bh=a5R7rjCwQUsHppOdOqHc/aD7eHGSIucsSB2xtGldnLQ=; b=02Euxbbldcp1p7 5xc8HYtptb6XHqwUk4OxdVFDfO0I2WKFrvTFwRYCfHczEJhbIaAdPFkiRT/I+7mbi7v+/C4a2qkXD bcgDGlEbRG71169odQ1xUasOb8HGIkk3DqadUzpYVDLw1JbZNR6cjDuf3K9I/8kz/veCEbkcSBCy4 Jjz+oKFGo2gp1FQZe2bfyuwatajByBntBMghkrS2mUguqMv5SvBdzA3Bc41k2krN8KL3C91fFCRLU HmjBthbRs5sZOUb/w8gn31n5ifdePzFBcz/NyFpxN5T8nDU4dgN05LcyenO6IHhxnu2GVzUBx5bOc tmYcZwULYuKwBZ2I/t9g==; Received: from localhost ([::1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIc7-000Nrq-3u; Mon, 22 Nov 2021 23:20:43 +0000 Received: from foss.arm.com ([217.140.110.172]) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIP6-000Ja8-UN for linux-arm-kernel@lists.infradead.org; Mon, 22 Nov 2021 23:07:18 +0000 Received: from usa-sjc-imap-foss1.foss.arm.com (unknown [10.121.207.14]) by usa-sjc-mx-foss1.foss.arm.com (Postfix) with ESMTP id 37B3B13A1; Mon, 22 Nov 2021 15:07:16 -0800 (PST) Received: from e120937-lin.home (unknown [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id B41CB3F5A1; Mon, 22 Nov 2021 15:07:14 -0800 (PST) From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org Cc: sudeep.holla@arm.com, james.quinlan@broadcom.com, Jonathan.Cameron@Huawei.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, souvik.chakravarty@arm.com, cristian.marussi@arm.com Subject: [PATCH v6 07/16] firmware: arm_scmi: Make smc transport use common completions Date: Mon, 22 Nov 2021 23:06:31 +0000 Message-Id: <20211122230640.1345-8-cristian.marussi@arm.com> X-Mailer: git-send-email 2.17.1 In-Reply-To: <20211122230640.1345-1-cristian.marussi@arm.com> References: <20211122230640.1345-1-cristian.marussi@arm.com> X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20211122_150717_166742_2713ED67 X-CRM114-Status: GOOD ( 15.29 ) 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: , MIME-Version: 1.0 Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org When a completion irq is available use it and delegate command completion handling to the core SCMI completion mechanism. If no completion irq is available revert to polling, using the core common polling machinery. Reviewed-by: Florian Fainelli Signed-off-by: Cristian Marussi --- v4 --> v5 - removed RFC tag v3 --> v4 - renamed usage of .needs_polling to .no_completion_irq --- drivers/firmware/arm_scmi/smc.c | 40 ++++++++++++++++----------------- 1 file changed, 20 insertions(+), 20 deletions(-) diff --git a/drivers/firmware/arm_scmi/smc.c b/drivers/firmware/arm_scmi/smc.c index 4effecc3bb46..adaa40df3855 100644 --- a/drivers/firmware/arm_scmi/smc.c +++ b/drivers/firmware/arm_scmi/smc.c @@ -25,8 +25,6 @@ * @shmem: Transmit/Receive shared memory area * @shmem_lock: Lock to protect access to Tx/Rx shared memory area * @func_id: smc/hvc call function id - * @irq: Optional; employed when platforms indicates msg completion by intr. - * @tx_complete: Optional, employed only when irq is valid. */ struct scmi_smc { @@ -34,15 +32,14 @@ struct scmi_smc { struct scmi_shared_mem __iomem *shmem; struct mutex shmem_lock; u32 func_id; - int irq; - struct completion tx_complete; }; static irqreturn_t smc_msg_done_isr(int irq, void *data) { struct scmi_smc *scmi_info = data; - complete(&scmi_info->tx_complete); + scmi_rx_callback(scmi_info->cinfo, + shmem_read_header(scmi_info->shmem), NULL); return IRQ_HANDLED; } @@ -111,8 +108,8 @@ static int smc_chan_setup(struct scmi_chan_info *cinfo, struct device *dev, dev_err(dev, "failed to setup SCMI smc irq\n"); return ret; } - init_completion(&scmi_info->tx_complete); - scmi_info->irq = irq; + } else { + cinfo->no_completion_irq = true; } scmi_info->func_id = func_id; @@ -142,26 +139,21 @@ static int smc_send_message(struct scmi_chan_info *cinfo, struct scmi_smc *scmi_info = cinfo->transport_info; struct arm_smccc_res res; + /* + * Channel lock will be released only once response has been + * surely fully retrieved, so after .mark_txdone() + */ mutex_lock(&scmi_info->shmem_lock); - shmem_tx_prepare(scmi_info->shmem, xfer); - if (scmi_info->irq) - reinit_completion(&scmi_info->tx_complete); - arm_smccc_1_1_invoke(scmi_info->func_id, 0, 0, 0, 0, 0, 0, 0, &res); - if (scmi_info->irq) - wait_for_completion(&scmi_info->tx_complete); - - scmi_rx_callback(scmi_info->cinfo, - shmem_read_header(scmi_info->shmem), NULL); - - mutex_unlock(&scmi_info->shmem_lock); - /* Only SMCCC_RET_NOT_SUPPORTED is valid error code */ - if (res.a0) + if (res.a0) { + mutex_unlock(&scmi_info->shmem_lock); return -EOPNOTSUPP; + } + return 0; } @@ -173,6 +165,13 @@ static void smc_fetch_response(struct scmi_chan_info *cinfo, shmem_fetch_response(scmi_info->shmem, xfer); } +static void smc_mark_txdone(struct scmi_chan_info *cinfo, int ret) +{ + struct scmi_smc *scmi_info = cinfo->transport_info; + + mutex_unlock(&scmi_info->shmem_lock); +} + static bool smc_poll_done(struct scmi_chan_info *cinfo, struct scmi_xfer *xfer) { @@ -186,6 +185,7 @@ static const struct scmi_transport_ops scmi_smc_ops = { .chan_setup = smc_chan_setup, .chan_free = smc_chan_free, .send_message = smc_send_message, + .mark_txdone = smc_mark_txdone, .fetch_response = smc_fetch_response, .poll_done = smc_poll_done, }; From patchwork Mon Nov 22 23:06:32 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Cristian Marussi X-Patchwork-Id: 12693392 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 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 smtp.lore.kernel.org (Postfix) with ESMTPS id 40E12C433EF for ; Mon, 22 Nov 2021 23:21:36 +0000 (UTC) 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:MIME-Version:List-Subscribe:List-Help: List-Post:List-Archive:List-Unsubscribe:List-Id:References:In-Reply-To: Message-Id:Date:Subject:Cc:To:From:Reply-To:Content-ID:Content-Description: Resent-Date:Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID: List-Owner; bh=bMdsAGxKDNUshfDSd40a6xD6h6mTRsofFC6y9a18+jY=; b=gK3Jnn7yvZ573I TSSA1bjY9B6hmutc44yruxW7zs+Ib6aBvysO88V827rzZmDLtuMm76AVn2pIyzlpKy8ZlhTWAZXMA uOGPxL4zpCcxnIawdDQJoA2Ajx6SEYqz4Y7IlslUo3jydXF8mr86ArAnihL7nB3GwXuuSvOd5sZVg BRn2ilSGrKb49eyw+7n4dXptvCt6PHjLvZOrpDi+5/4D6oZyO91dtrdcveDVnr58/TVJ9lnOdTPkQ O0okuK9UpAsRV2PDXmRthuShsSE9TIoCT9VSt9zwE2JcQyLbUl+YRo2eNuZ9UsN02QhkdHlrmPnYS fypiqXUM2jg9Nzb/8FuQ==; Received: from localhost ([::1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIbQ-000Nac-Qe; Mon, 22 Nov 2021 23:20:01 +0000 Received: from foss.arm.com ([217.140.110.172]) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIP8-000JbE-J0 for linux-arm-kernel@lists.infradead.org; Mon, 22 Nov 2021 23:07:20 +0000 Received: from usa-sjc-imap-foss1.foss.arm.com (unknown [10.121.207.14]) by usa-sjc-mx-foss1.foss.arm.com (Postfix) with ESMTP id B08F4ED1; Mon, 22 Nov 2021 15:07:17 -0800 (PST) Received: from e120937-lin.home (unknown [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 6EC753F5A1; Mon, 22 Nov 2021 15:07:16 -0800 (PST) From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org Cc: sudeep.holla@arm.com, james.quinlan@broadcom.com, Jonathan.Cameron@Huawei.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, souvik.chakravarty@arm.com, cristian.marussi@arm.com Subject: [PATCH v6 08/16] firmware: arm_scmi: Add sync_cmds_atomic_replies transport flag Date: Mon, 22 Nov 2021 23:06:32 +0000 Message-Id: <20211122230640.1345-9-cristian.marussi@arm.com> X-Mailer: git-send-email 2.17.1 In-Reply-To: <20211122230640.1345-1-cristian.marussi@arm.com> References: <20211122230640.1345-1-cristian.marussi@arm.com> X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20211122_150718_783141_22C5D290 X-CRM114-Status: GOOD ( 20.94 ) 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: , MIME-Version: 1.0 Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org Add a flag to let the transport signal to the core if its handling of sync command implies that, after .send_message has returned successfully, the requested command can be assumed to be fully and completely executed on SCMI platform side so that any possible response value is already immediately available to be retrieved by a .fetch_response: in other words the polling phase can be skipped in such a case and the response values accessed straight away. Note that all of the above applies only when polling mode of operation was selected by the core: if instead a completion IRQ was found to be available the normal response processing path based on completions will still be followed. Signed-off-by: Cristian Marussi --- v5 --> v6 - added polling_capable helper flag v4 --> v5 - removed RFC tag - consider sync_cmds_atomic_replies flag when deciding if polling is to be supported and .poll_done() is not provided. - reviewed commit message --- drivers/firmware/arm_scmi/common.h | 8 ++++++ drivers/firmware/arm_scmi/driver.c | 43 +++++++++++++++++++++++------- 2 files changed, 41 insertions(+), 10 deletions(-) diff --git a/drivers/firmware/arm_scmi/common.h b/drivers/firmware/arm_scmi/common.h index 99b74f4d39b6..bf25f0e89c78 100644 --- a/drivers/firmware/arm_scmi/common.h +++ b/drivers/firmware/arm_scmi/common.h @@ -412,6 +412,13 @@ struct scmi_device *scmi_child_dev_find(struct device *parent, * @max_msg_size: Maximum size of data per message that can be handled. * @force_polling: Flag to force this whole transport to use SCMI core polling * mechanism instead of completion interrupts even if available. + * @sync_cmds_atomic_replies: Flag to indicate that the transport assures + * synchronous-command messages are atomically + * completed on .send_message: no need to poll + * actively waiting for a response. + * Used by core internally only when polling is + * selected as a waiting for reply method: i.e. + * if a completion irq was found use that anyway. */ struct scmi_desc { int (*transport_init)(void); @@ -421,6 +428,7 @@ struct scmi_desc { int max_msg; int max_msg_size; const bool force_polling; + const bool sync_cmds_atomic_replies; }; #ifdef CONFIG_ARM_SCMI_TRANSPORT_MAILBOX diff --git a/drivers/firmware/arm_scmi/driver.c b/drivers/firmware/arm_scmi/driver.c index 8a30b832899c..8c04632f3ba3 100644 --- a/drivers/firmware/arm_scmi/driver.c +++ b/drivers/firmware/arm_scmi/driver.c @@ -134,6 +134,8 @@ struct scmi_protocol_instance { * @notify_priv: Pointer to private data structure specific to notifications. * @node: List head * @users: Number of users of this instance + * @polling_capable: A flag to annotate if the underlying transport can operate + * in polling mode. */ struct scmi_info { struct device *dev; @@ -152,6 +154,7 @@ struct scmi_info { void *notify_priv; struct list_head node; int users; + bool polling_capable; }; #define handle_to_scmi_info(h) container_of(h, struct scmi_info, handle) @@ -763,10 +766,28 @@ static int scmi_wait_for_message_response(struct scmi_chan_info *cinfo, xfer->hdr.poll_completion); if (xfer->hdr.poll_completion) { - ktime_t stop = ktime_add_ms(ktime_get(), timeout_ms); + /* + * Real polling is needed only if transport has NOT declared + * itself to support synchronous commands replies. + */ + if (!info->desc->sync_cmds_atomic_replies) { + /* + * Poll on xfer using transport provided .poll_done(); + * assumes no completion interrupt was available. + */ + ktime_t stop = ktime_add_ms(ktime_get(), timeout_ms); + + spin_until_cond(scmi_xfer_done_no_timeout(cinfo, + xfer, stop)); + if (ktime_after(ktime_get(), stop)) { + dev_err(dev, + "timed out in resp(caller: %pS) - polling\n", + (void *)_RET_IP_); + ret = -ETIMEDOUT; + } + } - spin_until_cond(scmi_xfer_done_no_timeout(cinfo, xfer, stop)); - if (ktime_before(ktime_get(), stop)) { + if (!ret) { unsigned long flags; /* @@ -779,11 +800,6 @@ static int scmi_wait_for_message_response(struct scmi_chan_info *cinfo, xfer->state = SCMI_XFER_RESP_OK; } spin_unlock_irqrestore(&xfer->lock, flags); - } else { - dev_err(dev, - "timed out in resp(caller: %pS) - polling\n", - (void *)_RET_IP_); - ret = -ETIMEDOUT; } } else { /* And we wait for the response. */ @@ -818,7 +834,7 @@ static int do_xfer(const struct scmi_protocol_handle *ph, struct scmi_chan_info *cinfo; /* Check for polling request on custom command xfers at first */ - if (xfer->hdr.poll_completion && !info->desc->ops->poll_done) { + if (xfer->hdr.poll_completion && !info->polling_capable) { dev_warn_once(dev, "Polling mode is not supported by transport.\n"); return -EINVAL; @@ -1533,7 +1549,7 @@ static int scmi_chan_setup(struct scmi_info *info, struct device *dev, return ret; if (tx && (cinfo->no_completion_irq || info->desc->force_polling)) { - if (info->desc->ops->poll_done) { + if (info->polling_capable) { dev_info(dev, "Enabled polling mode TX channel - prot_id:%d\n", prot_id); @@ -1866,6 +1882,13 @@ static int scmi_probe(struct platform_device *pdev) info->dev = dev; info->desc = desc; + /* + * Annotate if the underlying transport for this instance has polling + * capabilities by providing a .poll_done callback OR not requiring + * real polling at all. + */ + info->polling_capable = info->desc->ops->poll_done || + info->desc->sync_cmds_atomic_replies; INIT_LIST_HEAD(&info->node); idr_init(&info->protocols); mutex_init(&info->protocols_mtx); From patchwork Mon Nov 22 23:06:33 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Cristian Marussi X-Patchwork-Id: 12693394 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 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 smtp.lore.kernel.org (Postfix) with ESMTPS id 4DD30C433F5 for ; Mon, 22 Nov 2021 23:23:13 +0000 (UTC) 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:MIME-Version:List-Subscribe:List-Help: List-Post:List-Archive:List-Unsubscribe:List-Id:References:In-Reply-To: Message-Id:Date:Subject:Cc:To:From:Reply-To:Content-ID:Content-Description: Resent-Date:Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID: List-Owner; bh=G946UM8dbphT8LGnoURF66yR0ESDtT05Gv3+5CRfVDg=; b=J4vY9dBHBulDd/ fXShCdIsacjm3ZJzzVi0DyEKrh7n1EX/viYhAas9IeLNbquodl0HswOWS5Lm06Q6ujPhV/MZmNq7E rFXgFQGhAHsZ2XYToB7JW3CMC0zfoiV0WIt7EZJMESwVwoPQ5eNANYbxqFliLeEZE6vDJ0UBonaap OK909xSpT/3lQac55NXDs7NLPHnXYkh2pj2Xv7CPjTwjrGz4PxalsInPiIuKPUnse9bQR9OOyaKXD +YP3npwAyaKIpHlSQPFr8J8oWGOqSRCWNJDHsRIvcmOiPVB1LVpAQfPWuSMP/ZUR2UaKVInKWaek1 hYk4r2l0lhM80eHUZJDA==; Received: from localhost ([::1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIct-000O9E-R3; Mon, 22 Nov 2021 23:21:32 +0000 Received: from foss.arm.com ([217.140.110.172]) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIPA-000Jby-7k for linux-arm-kernel@lists.infradead.org; Mon, 22 Nov 2021 23:07:21 +0000 Received: from usa-sjc-imap-foss1.foss.arm.com (unknown [10.121.207.14]) by usa-sjc-mx-foss1.foss.arm.com (Postfix) with ESMTP id 829BE1063; Mon, 22 Nov 2021 15:07:19 -0800 (PST) Received: from e120937-lin.home (unknown [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 40B063F5A1; Mon, 22 Nov 2021 15:07:17 -0800 (PST) From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org Cc: sudeep.holla@arm.com, james.quinlan@broadcom.com, Jonathan.Cameron@Huawei.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, souvik.chakravarty@arm.com, cristian.marussi@arm.com Subject: [PATCH v6 09/16] firmware: arm_scmi: Make smc support atomic sync commands replies Date: Mon, 22 Nov 2021 23:06:33 +0000 Message-Id: <20211122230640.1345-10-cristian.marussi@arm.com> X-Mailer: git-send-email 2.17.1 In-Reply-To: <20211122230640.1345-1-cristian.marussi@arm.com> References: <20211122230640.1345-1-cristian.marussi@arm.com> X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20211122_150720_386541_8B204BB2 X-CRM114-Status: GOOD ( 10.32 ) 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: , MIME-Version: 1.0 Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org Enable sync_cmds_atomic_replies in the SMC transport descriptor and remove SMC specific .poll_done callback support since polling is bypassed when sync_cmds_atomic_replies is set. Signed-off-by: Cristian Marussi --- v4 --> v5 - removed RFC tag - added comment on setting flag - remove smc_poll_done --- drivers/firmware/arm_scmi/smc.c | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/drivers/firmware/arm_scmi/smc.c b/drivers/firmware/arm_scmi/smc.c index adaa40df3855..95cafa1bbfbe 100644 --- a/drivers/firmware/arm_scmi/smc.c +++ b/drivers/firmware/arm_scmi/smc.c @@ -172,14 +172,6 @@ static void smc_mark_txdone(struct scmi_chan_info *cinfo, int ret) mutex_unlock(&scmi_info->shmem_lock); } -static bool -smc_poll_done(struct scmi_chan_info *cinfo, struct scmi_xfer *xfer) -{ - struct scmi_smc *scmi_info = cinfo->transport_info; - - return shmem_poll_done(scmi_info->shmem, xfer); -} - static const struct scmi_transport_ops scmi_smc_ops = { .chan_available = smc_chan_available, .chan_setup = smc_chan_setup, @@ -187,7 +179,6 @@ static const struct scmi_transport_ops scmi_smc_ops = { .send_message = smc_send_message, .mark_txdone = smc_mark_txdone, .fetch_response = smc_fetch_response, - .poll_done = smc_poll_done, }; const struct scmi_desc scmi_smc_desc = { @@ -195,4 +186,13 @@ const struct scmi_desc scmi_smc_desc = { .max_rx_timeout_ms = 30, .max_msg = 20, .max_msg_size = 128, + /* + * Setting .sync_cmds_atomic_replies to true for SMC assumes that, + * once the SMC instruction has completed successfully, the issued + * SCMI command would have been already fully processed by the SCMI + * platform firmware and so any possible response value expected + * for the issued command will be immmediately ready to be fetched + * from the shared memory area. + */ + .sync_cmds_atomic_replies = true, }; From patchwork Mon Nov 22 23:06:34 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Cristian Marussi X-Patchwork-Id: 12693395 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 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 smtp.lore.kernel.org (Postfix) with ESMTPS id 75194C433EF for ; Mon, 22 Nov 2021 23:23:48 +0000 (UTC) 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:MIME-Version:List-Subscribe:List-Help: List-Post:List-Archive:List-Unsubscribe:List-Id:References:In-Reply-To: Message-Id:Date:Subject:Cc:To:From:Reply-To:Content-ID:Content-Description: Resent-Date:Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID: List-Owner; bh=omtOllLf4mxUJptXqt2qKtNFwj1u5i4k42verWDJndk=; b=jz6wnCWAYKgaa4 TCKj+CbWX4j4PrcN3GvdGAcuvLo+o5a3mSM2bobLv7y5h5Md9tyaaA9RLAzZms2yAUvtGO9y4ymaE X+Rg/ClGjnbakrFlCfT4o+gyIb5aVJ5Om+J8wKjPI4ER1Jdr/sNoXN95WTokzDVsN4wAwzBgl27WN Nwg52gRXSGA0CzkWcW56JApgToCmCFZLFIcwvPcn/IAmcwKFhfw8lD+UZRb2d7v2ghdrVq/PUQXZl 26NAFd6BnqA718vXsuqEHCz8Mqx61rTbP0dIruz1UxFiUuHI44V3pOwibigtj/cTiFe1295mlyn5R 1+gORkNzH4hKPqz6Hqrg==; Received: from localhost ([::1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIda-000OQ4-Ni; Mon, 22 Nov 2021 23:22:15 +0000 Received: from foss.arm.com ([217.140.110.172]) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIPB-000JbE-Lv for linux-arm-kernel@lists.infradead.org; Mon, 22 Nov 2021 23:07:23 +0000 Received: from usa-sjc-imap-foss1.foss.arm.com (unknown [10.121.207.14]) by usa-sjc-mx-foss1.foss.arm.com (Postfix) with ESMTP id 6AD911516; Mon, 22 Nov 2021 15:07:21 -0800 (PST) Received: from e120937-lin.home (unknown [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id B87103F5A1; Mon, 22 Nov 2021 15:07:19 -0800 (PST) From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org Cc: sudeep.holla@arm.com, james.quinlan@broadcom.com, Jonathan.Cameron@Huawei.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, souvik.chakravarty@arm.com, cristian.marussi@arm.com, Etienne Carriere Subject: [PATCH v6 10/16] firmware: arm_scmi: Make optee support atomic sync commands replies Date: Mon, 22 Nov 2021 23:06:34 +0000 Message-Id: <20211122230640.1345-11-cristian.marussi@arm.com> X-Mailer: git-send-email 2.17.1 In-Reply-To: <20211122230640.1345-1-cristian.marussi@arm.com> References: <20211122230640.1345-1-cristian.marussi@arm.com> X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20211122_150721_839058_D733F910 X-CRM114-Status: GOOD ( 11.17 ) 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: , MIME-Version: 1.0 Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org Declare each OPTEE SCMI channel as not having a completion_irq so as to enable polling mode and then enable also .sync_cmds_atomic_replies flag in the OPTEE transport descriptor so that polling is itself effectively bypassed on the rx path: once the optee command invocation has successfully returned the core will directly fetch the response from the shared memory area. Remove OPTEE SCMI transport specific .poll_done callback support since polling is effectively bypassed when .sync_cmds_atomic_replies is set. Cc: Etienne Carriere Signed-off-by: Cristian Marussi --- drivers/firmware/arm_scmi/optee.c | 17 +++++++++-------- 1 file changed, 9 insertions(+), 8 deletions(-) diff --git a/drivers/firmware/arm_scmi/optee.c b/drivers/firmware/arm_scmi/optee.c index d9819b0197ec..f215e823d351 100644 --- a/drivers/firmware/arm_scmi/optee.c +++ b/drivers/firmware/arm_scmi/optee.c @@ -380,6 +380,9 @@ static int scmi_optee_chan_setup(struct scmi_chan_info *cinfo, struct device *de if (ret) goto err_close_sess; + /* Enable polling */ + cinfo->no_completion_irq = true; + mutex_lock(&scmi_optee_private->mu); list_add(&channel->link, &scmi_optee_private->channel_list); mutex_unlock(&scmi_optee_private->mu); @@ -440,9 +443,8 @@ static int scmi_optee_send_message(struct scmi_chan_info *cinfo, shmem_tx_prepare(shmem, xfer); ret = invoke_process_smt_channel(channel); - - scmi_rx_callback(cinfo, shmem_read_header(shmem), NULL); - mutex_unlock(&channel->mu); + if (ret) + mutex_unlock(&channel->mu); return ret; } @@ -456,13 +458,11 @@ static void scmi_optee_fetch_response(struct scmi_chan_info *cinfo, shmem_fetch_response(shmem, xfer); } -static bool scmi_optee_poll_done(struct scmi_chan_info *cinfo, - struct scmi_xfer *xfer) +static void scmi_optee_mark_txdone(struct scmi_chan_info *cinfo, int ret) { struct scmi_optee_channel *channel = cinfo->transport_info; - struct scmi_shared_mem *shmem = get_channel_shm(channel, xfer); - return shmem_poll_done(shmem, xfer); + mutex_unlock(&channel->mu); } static struct scmi_transport_ops scmi_optee_ops = { @@ -471,9 +471,9 @@ static struct scmi_transport_ops scmi_optee_ops = { .chan_setup = scmi_optee_chan_setup, .chan_free = scmi_optee_chan_free, .send_message = scmi_optee_send_message, + .mark_txdone = scmi_optee_mark_txdone, .fetch_response = scmi_optee_fetch_response, .clear_channel = scmi_optee_clear_channel, - .poll_done = scmi_optee_poll_done, }; static int scmi_optee_ctx_match(struct tee_ioctl_version_data *ver, const void *data) @@ -578,4 +578,5 @@ const struct scmi_desc scmi_optee_desc = { .max_rx_timeout_ms = 30, .max_msg = 20, .max_msg_size = SCMI_OPTEE_MAX_MSG_SIZE, + .sync_cmds_atomic_replies = true, }; From patchwork Mon Nov 22 23:06:35 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Cristian Marussi X-Patchwork-Id: 12693396 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 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 smtp.lore.kernel.org (Postfix) with ESMTPS id EAEADC433F5 for ; Mon, 22 Nov 2021 23:24:52 +0000 (UTC) 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:MIME-Version:List-Subscribe:List-Help: List-Post:List-Archive:List-Unsubscribe:List-Id:References:In-Reply-To: Message-Id:Date:Subject:Cc:To:From:Reply-To:Content-ID:Content-Description: Resent-Date:Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID: List-Owner; bh=Gy01LWP8DkXBIT+iZ0TBG9DIQPUofeyR/4eM94z/HCg=; b=R0UH041fg/B+5d XIAOnzNf1ZKJWWfWlE0oP5gejFTPMmqTJtzG3jv/Y+2+HolC7mXOaadJqjj2WeMq7sHE3zbp1/pnn J7bBGpkN3+FmauQdjq3eWmjwyzrp+5eecun4zLJro3uIrBvxVS6eJDj5NOmcIY+0dxE1VpWh9jZkA 8bVr0uFun0d4hfd/woI97d0vd+tbvmJD4Ma5NMTqCFA8fbF+GUelzYrbB8m9R5MBVX3JmiAaSRU+l vqytciOjaa9/BZi7iGjIP907Q0SvRrlnhc7Xypq4alrBe5C9mCk57G2TrGcMTNJeNtMbJ+kXdhOZ9 sxbHDBkAuFWpoLjZt7VA==; Received: from localhost ([::1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIeM-000Ojz-0m; Mon, 22 Nov 2021 23:23:02 +0000 Received: from foss.arm.com ([217.140.110.172]) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIPD-000JbE-GD for linux-arm-kernel@lists.infradead.org; Mon, 22 Nov 2021 23:07:25 +0000 Received: from usa-sjc-imap-foss1.foss.arm.com (unknown [10.121.207.14]) by usa-sjc-mx-foss1.foss.arm.com (Postfix) with ESMTP id 2BB9D152B; Mon, 22 Nov 2021 15:07:23 -0800 (PST) Received: from e120937-lin.home (unknown [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id A6EC03F5A1; Mon, 22 Nov 2021 15:07:21 -0800 (PST) From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org Cc: sudeep.holla@arm.com, james.quinlan@broadcom.com, Jonathan.Cameron@Huawei.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, souvik.chakravarty@arm.com, cristian.marussi@arm.com Subject: [PATCH v6 11/16] firmware: arm_scmi: Add support for atomic transports Date: Mon, 22 Nov 2021 23:06:35 +0000 Message-Id: <20211122230640.1345-12-cristian.marussi@arm.com> X-Mailer: git-send-email 2.17.1 In-Reply-To: <20211122230640.1345-1-cristian.marussi@arm.com> References: <20211122230640.1345-1-cristian.marussi@arm.com> X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20211122_150723_693907_1D8425BB X-CRM114-Status: GOOD ( 24.22 ) 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: , MIME-Version: 1.0 Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org An SCMI transport can be configured as .atomic_enabled in order to signal to the SCMI core that all its TX path is executed in atomic context. When a specific platform configuration had properly configured such a transport as .atomic_enabled, the SCMI core will also take care not to sleep in the corresponding RX path while waiting for a response. Asynchronous commands should not be used in an atomic context and as such a warning is emitted if polling was requested for an asynchronous command. Add also a method to check if, from the SCMI drivers, the underlying SCMI transport is configured to support atomic transaction of SCMI commands. Signed-off-by: Cristian Marussi --- v5 --> v6 - removed atomic_capable - fully relying on transport polling capabilities - removed polling/atomic support for delayed_reponse and WARN - merged with is_transport_atomic() patch - is_transport_atomic() now considers polling_capable and atomic_enabled flags v4 --> v5 - added .atomic_enabled flag to decide wheter to enable atomic mode or not for atomic_capable transports - reviewed commit message --- drivers/firmware/arm_scmi/common.h | 4 +++ drivers/firmware/arm_scmi/driver.c | 49 ++++++++++++++++++++++++++++-- include/linux/scmi_protocol.h | 8 +++++ 3 files changed, 59 insertions(+), 2 deletions(-) diff --git a/drivers/firmware/arm_scmi/common.h b/drivers/firmware/arm_scmi/common.h index bf25f0e89c78..97a65d5fbb1d 100644 --- a/drivers/firmware/arm_scmi/common.h +++ b/drivers/firmware/arm_scmi/common.h @@ -419,6 +419,9 @@ struct scmi_device *scmi_child_dev_find(struct device *parent, * Used by core internally only when polling is * selected as a waiting for reply method: i.e. * if a completion irq was found use that anyway. + * @atomic_enabled: Flag to indicate that this transport, which is assured not + * to sleep anywhere on the TX path, can be used in atomic mode + * when requested. */ struct scmi_desc { int (*transport_init)(void); @@ -429,6 +432,7 @@ struct scmi_desc { int max_msg_size; const bool force_polling; const bool sync_cmds_atomic_replies; + const bool atomic_enabled; }; #ifdef CONFIG_ARM_SCMI_TRANSPORT_MAILBOX diff --git a/drivers/firmware/arm_scmi/driver.c b/drivers/firmware/arm_scmi/driver.c index 8c04632f3ba3..7d6e97d7a077 100644 --- a/drivers/firmware/arm_scmi/driver.c +++ b/drivers/firmware/arm_scmi/driver.c @@ -907,6 +907,20 @@ static void reset_rx_to_maxsz(const struct scmi_protocol_handle *ph, * @ph: Pointer to SCMI protocol handle * @xfer: Transfer to initiate and wait for response * + * Using asynchronous commands in atomic/polling mode should be avoided since + * it could cause long busy-waiting here, so WARN if polling mode is detected + * for this command transaction since upper layers should refrain from issuing + * such kind of requests. + * + * The only other option would have been to refrain from using any asynchronous + * command even if made available, when an atomic transport is detected, and + * instead forcibly use the synchronous version (thing that can be easily + * attained at the protocol layer), but this would also have led to longer + * stalls of the channel for synchronous commands and possibly timeouts. + * (in other words there is usually a good reason if a platform provides an + * asynchronous version of a command and we should prefer to use it...just not + * in atomic/polling mode) + * * Return: -ETIMEDOUT in case of no delayed response, if transmit error, * return corresponding error, else if all goes well, return 0. */ @@ -918,12 +932,23 @@ static int do_xfer_with_response(const struct scmi_protocol_handle *ph, xfer->async_done = &async_response; + /* + * Delayed responses are not pollable, an async command should + * not have been used when requiring an atomic/poll context. + * (and Async + IgnoreDelayedResponses are sent via do_xfer) + */ + WARN_ON(xfer->hdr.poll_completion); + ret = do_xfer(ph, xfer); if (!ret) { - if (!wait_for_completion_timeout(xfer->async_done, timeout)) + if (!wait_for_completion_timeout(xfer->async_done, timeout)) { + dev_err(ph->dev, + "timed out in delayed resp(caller: %pS)\n", + (void *)_RET_IP_); ret = -ETIMEDOUT; - else if (xfer->hdr.status) + } else if (xfer->hdr.status) { ret = scmi_to_linux_errno(xfer->hdr.status); + } } xfer->async_done = NULL; @@ -1357,6 +1382,21 @@ static void scmi_devm_protocol_put(struct scmi_device *sdev, u8 protocol_id) WARN_ON(ret); } +/** + * scmi_is_transport_atomic - Method to check if underlying transport for an + * SCMI instance is configured as atomic. + * + * @handle: A reference to the SCMI platform instance. + * + * Return: True if transport is configured as atomic + */ +static bool scmi_is_transport_atomic(const struct scmi_handle *handle) +{ + struct scmi_info *info = handle_to_scmi_info(handle); + + return info->desc->atomic_enabled && info->polling_capable; +} + static inline struct scmi_handle *scmi_handle_get_from_info_unlocked(struct scmi_info *info) { @@ -1903,6 +1943,7 @@ static int scmi_probe(struct platform_device *pdev) handle->version = &info->version; handle->devm_protocol_get = scmi_devm_protocol_get; handle->devm_protocol_put = scmi_devm_protocol_put; + handle->is_transport_atomic = scmi_is_transport_atomic; if (desc->ops->link_supplier) { ret = desc->ops->link_supplier(dev); @@ -1921,6 +1962,10 @@ static int scmi_probe(struct platform_device *pdev) if (scmi_notification_init(handle)) dev_err(dev, "SCMI Notifications NOT available.\n"); + if (info->desc->atomic_enabled && !info->polling_capable) + dev_err(dev, + "Transport is not polling capable. Atomic mode not supported.\n"); + /* * Trigger SCMI Base protocol initialization. * It's mandatory and won't be ever released/deinit until the diff --git a/include/linux/scmi_protocol.h b/include/linux/scmi_protocol.h index 80e781c51ddc..9f895cb81818 100644 --- a/include/linux/scmi_protocol.h +++ b/include/linux/scmi_protocol.h @@ -612,6 +612,13 @@ struct scmi_notify_ops { * @devm_protocol_get: devres managed method to acquire a protocol and get specific * operations and a dedicated protocol handler * @devm_protocol_put: devres managed method to release a protocol + * @is_transport_atomic: method to check if the underlying transport for this + * instance handle is configured to support atomic + * transactions for commands. + * Some users of the SCMI stack in the upper layers could + * be interested to know if they can assume SCMI + * command transactions associated to this handle will + * never sleep and act accordingly. * @notify_ops: pointer to set of notifications related operations */ struct scmi_handle { @@ -622,6 +629,7 @@ struct scmi_handle { (*devm_protocol_get)(struct scmi_device *sdev, u8 proto, struct scmi_protocol_handle **ph); void (*devm_protocol_put)(struct scmi_device *sdev, u8 proto); + bool (*is_transport_atomic)(const struct scmi_handle *handle); const struct scmi_notify_ops *notify_ops; }; From patchwork Mon Nov 22 23:06:36 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Cristian Marussi X-Patchwork-Id: 12693398 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 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 smtp.lore.kernel.org (Postfix) with ESMTPS id B038EC433F5 for ; Mon, 22 Nov 2021 23:26:03 +0000 (UTC) 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:MIME-Version:List-Subscribe:List-Help: List-Post:List-Archive:List-Unsubscribe:List-Id:References:In-Reply-To: Message-Id:Date:Subject:Cc:To:From:Reply-To:Content-ID:Content-Description: Resent-Date:Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID: List-Owner; bh=9zWzgvaoLmWrbjsrrUoFHPAzN4+pzJ9Hf0RNfG2S7yc=; b=Duqk4V92dtVIdS RaEMJkP1La8R/JUNObPozVoedYKfTbUWsN5pXodTVxpF+wA+sBu8pEa3teY6e6aUZxezJ568GHEZT v4b5lF5LVT3oYsFRSSes8F7o64ohb8yjwliIX6SatbWN0uPVQ4csPRqA2lh00WFXNxIyaFSobO+LG 2nUoQ7+qDVaj6uCFj8bVOMOYDVgPZSPWTzVcyhkpEw8SNc3KAZSO9gt1xfzAMZG0XegotDGmnZAQY cnYDsDgu+eE35B1deWS8Ra9xmW+gqyGFglSWqlJ93sB0soc5Ug9nZDzQU5i7IcdZ5J4qYNYn9gbM4 pHkC/l9NrRpY6u9e8ezw==; Received: from localhost ([::1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIfn-000POq-Hi; Mon, 22 Nov 2021 23:24:32 +0000 Received: from foss.arm.com ([217.140.110.172]) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIPF-000JeS-HM for linux-arm-kernel@lists.infradead.org; Mon, 22 Nov 2021 23:07:27 +0000 Received: from usa-sjc-imap-foss1.foss.arm.com (unknown [10.121.207.14]) by usa-sjc-mx-foss1.foss.arm.com (Postfix) with ESMTP id 0202BED1; Mon, 22 Nov 2021 15:07:25 -0800 (PST) Received: from e120937-lin.home (unknown [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 66BC83F5A1; Mon, 22 Nov 2021 15:07:23 -0800 (PST) From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org Cc: sudeep.holla@arm.com, james.quinlan@broadcom.com, Jonathan.Cameron@Huawei.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, souvik.chakravarty@arm.com, cristian.marussi@arm.com Subject: [PATCH v6 12/16] firmware: arm_scmi: Add atomic mode support to smc transport Date: Mon, 22 Nov 2021 23:06:36 +0000 Message-Id: <20211122230640.1345-13-cristian.marussi@arm.com> X-Mailer: git-send-email 2.17.1 In-Reply-To: <20211122230640.1345-1-cristian.marussi@arm.com> References: <20211122230640.1345-1-cristian.marussi@arm.com> X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20211122_150725_765308_F9A334A0 X-CRM114-Status: GOOD ( 17.79 ) 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: , MIME-Version: 1.0 Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org Add a Kernel configuration option to enable SCMI SMC transport atomic mode operation for selected SCMI transactions and leave it as default disabled. Substitute mutex usages with busy-waiting and declare smc transport as .atomic_enabled if such Kernel configuration option is enabled. Signed-off-by: Cristian Marussi --- v5 --> v6 - remove usage of atomic_capable - removed needless union - reviewed Kconfig help v4 --> v5 - removed RFC tag - add CONFIG_ARM_SCMI_TRANSPORT_SMC_ATOMIC_ENABLE option - add .atomic_enable support - make atomic_capable dependent on CONFIG_ARM_SCMI_TRANSPORT_SMC_ATOMIC_ENABLE - make also usage of mutexes vs busy-waiting dependent on CONFIG_ARM_SCMI_TRANSPORT_SMC_ATOMIC_ENABLE --- drivers/firmware/arm_scmi/Kconfig | 14 +++++++ drivers/firmware/arm_scmi/smc.c | 67 ++++++++++++++++++++++++++++--- 2 files changed, 75 insertions(+), 6 deletions(-) diff --git a/drivers/firmware/arm_scmi/Kconfig b/drivers/firmware/arm_scmi/Kconfig index 638ecec89ff1..d429326433d1 100644 --- a/drivers/firmware/arm_scmi/Kconfig +++ b/drivers/firmware/arm_scmi/Kconfig @@ -78,6 +78,20 @@ config ARM_SCMI_TRANSPORT_SMC If you want the ARM SCMI PROTOCOL stack to include support for a transport based on SMC, answer Y. +config ARM_SCMI_TRANSPORT_SMC_ATOMIC_ENABLE + bool "Enable atomic mode support for SCMI SMC transport" + depends on ARM_SCMI_TRANSPORT_SMC + help + Enable support of atomic operation for SCMI SMC based transport. + + If you want the SCMI SMC based transport to operate in atomic + mode, avoiding any kind of sleeping behaviour for selected + transactions on the TX path, answer Y. + Enabling atomic mode operations allows any SCMI driver using this + transport to optionally ask for atomic SCMI transactions and operate + in atomic context too, at the price of using a number of busy-waiting + primitives all over instead. If unsure say N. + config ARM_SCMI_TRANSPORT_VIRTIO bool "SCMI transport based on VirtIO" depends on VIRTIO=y || VIRTIO=ARM_SCMI_PROTOCOL diff --git a/drivers/firmware/arm_scmi/smc.c b/drivers/firmware/arm_scmi/smc.c index 95cafa1bbfbe..0fc49cb49185 100644 --- a/drivers/firmware/arm_scmi/smc.c +++ b/drivers/firmware/arm_scmi/smc.c @@ -7,6 +7,7 @@ */ #include +#include #include #include #include @@ -14,6 +15,9 @@ #include #include #include +#ifdef CONFIG_ARM_SCMI_TRANSPORT_SMC_ATOMIC_ENABLE +#include +#endif #include #include "common.h" @@ -23,14 +27,23 @@ * * @cinfo: SCMI channel info * @shmem: Transmit/Receive shared memory area - * @shmem_lock: Lock to protect access to Tx/Rx shared memory area + * @shmem_lock: Lock to protect access to Tx/Rx shared memory area. + * Used when NOT operating in atomic mode. + * @inflight: Atomic flag to protect access to Tx/Rx shared memory area. + * Used when operating in atomic mode. * @func_id: smc/hvc call function id */ struct scmi_smc { struct scmi_chan_info *cinfo; struct scmi_shared_mem __iomem *shmem; +#ifndef CONFIG_ARM_SCMI_TRANSPORT_SMC_ATOMIC_ENABLE + /* Protect access to shmem area */ struct mutex shmem_lock; +#else +#define INFLIGHT_NONE MSG_TOKEN_MAX + atomic_t inflight; +#endif u32 func_id; }; @@ -54,6 +67,46 @@ static bool smc_chan_available(struct device *dev, int idx) return true; } +static inline void smc_channel_lock_init(struct scmi_smc *scmi_info) +{ +#ifndef CONFIG_ARM_SCMI_TRANSPORT_SMC_ATOMIC_ENABLE + mutex_init(&scmi_info->shmem_lock); +#else + atomic_set(&scmi_info->inflight, INFLIGHT_NONE); +#endif +} + +#ifdef CONFIG_ARM_SCMI_TRANSPORT_SMC_ATOMIC_ENABLE +static bool smc_xfer_inflight(struct scmi_xfer *xfer, atomic_t *inflight) +{ + int ret; + + ret = atomic_cmpxchg(inflight, INFLIGHT_NONE, xfer->hdr.seq); + + return ret == INFLIGHT_NONE; +} +#endif + +static inline void +smc_channel_lock_acquire(struct scmi_smc *scmi_info, + struct scmi_xfer *xfer __maybe_unused) +{ +#ifndef CONFIG_ARM_SCMI_TRANSPORT_SMC_ATOMIC_ENABLE + mutex_lock(&scmi_info->shmem_lock); +#else + spin_until_cond(smc_xfer_inflight(xfer, &scmi_info->inflight)); +#endif +} + +static inline void smc_channel_lock_release(struct scmi_smc *scmi_info) +{ +#ifndef CONFIG_ARM_SCMI_TRANSPORT_SMC_ATOMIC_ENABLE + mutex_unlock(&scmi_info->shmem_lock); +#else + atomic_set(&scmi_info->inflight, INFLIGHT_NONE); +#endif +} + static int smc_chan_setup(struct scmi_chan_info *cinfo, struct device *dev, bool tx) { @@ -114,7 +167,7 @@ static int smc_chan_setup(struct scmi_chan_info *cinfo, struct device *dev, scmi_info->func_id = func_id; scmi_info->cinfo = cinfo; - mutex_init(&scmi_info->shmem_lock); + smc_channel_lock_init(scmi_info); cinfo->transport_info = scmi_info; return 0; @@ -140,17 +193,18 @@ static int smc_send_message(struct scmi_chan_info *cinfo, struct arm_smccc_res res; /* - * Channel lock will be released only once response has been + * Channel will be released only once response has been * surely fully retrieved, so after .mark_txdone() */ - mutex_lock(&scmi_info->shmem_lock); + smc_channel_lock_acquire(scmi_info, xfer); + shmem_tx_prepare(scmi_info->shmem, xfer); arm_smccc_1_1_invoke(scmi_info->func_id, 0, 0, 0, 0, 0, 0, 0, &res); /* Only SMCCC_RET_NOT_SUPPORTED is valid error code */ if (res.a0) { - mutex_unlock(&scmi_info->shmem_lock); + smc_channel_lock_release(scmi_info); return -EOPNOTSUPP; } @@ -169,7 +223,7 @@ static void smc_mark_txdone(struct scmi_chan_info *cinfo, int ret) { struct scmi_smc *scmi_info = cinfo->transport_info; - mutex_unlock(&scmi_info->shmem_lock); + smc_channel_lock_release(scmi_info); } static const struct scmi_transport_ops scmi_smc_ops = { @@ -195,4 +249,5 @@ const struct scmi_desc scmi_smc_desc = { * from the shared memory area. */ .sync_cmds_atomic_replies = true, + .atomic_enabled = IS_ENABLED(CONFIG_ARM_SCMI_TRANSPORT_SMC_ATOMIC_ENABLE), }; From patchwork Mon Nov 22 23:06:37 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Cristian Marussi X-Patchwork-Id: 12693397 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 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 smtp.lore.kernel.org (Postfix) with ESMTPS id D0B1CC433EF for ; Mon, 22 Nov 2021 23:25:22 +0000 (UTC) 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:MIME-Version:List-Subscribe:List-Help: List-Post:List-Archive:List-Unsubscribe:List-Id:References:In-Reply-To: Message-Id:Date:Subject:Cc:To:From:Reply-To:Content-ID:Content-Description: Resent-Date:Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID: List-Owner; bh=PLlhrUHvsSnNGW7bJM2xcPUlSgQdHYThYtpMH/PPgdE=; b=dKrbFhC2zJqT7R c1AApOAY/m/KbpdKEszgnRmXy2FhXlviyDaKk48WIXMsfEAEMJz8xyaCyn/Rmxs23vZW1Q8JwW2mS jV1jzSi88IPKs4TxmLG6uHlZvfOywci2iGRj6CtWs6zbM8wLz7aAYzkL12Xy064ePfzlFIiUDoGPC bIg7gCVT/ACgo/HObb2VS2wXKo1MmeoZyvY9SvrCoG5UzR6/uClOAgeDxKBCvuTUWpWEhK0UuUwcZ kPPwe18z/A3xxYogE6ukCU5lmu6Ric4HbystoeYCgwijClTnCu6i7GdREqId0aCqMHXz4OOMKP2nt B8822gawZBErfN3qISiQ==; Received: from localhost ([::1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIfA-000P7y-FM; Mon, 22 Nov 2021 23:23:53 +0000 Received: from foss.arm.com ([217.140.110.172]) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIPH-000Jfm-Gv for linux-arm-kernel@lists.infradead.org; Mon, 22 Nov 2021 23:07:29 +0000 Received: from usa-sjc-imap-foss1.foss.arm.com (unknown [10.121.207.14]) by usa-sjc-mx-foss1.foss.arm.com (Postfix) with ESMTP id C9D3F1063; Mon, 22 Nov 2021 15:07:26 -0800 (PST) Received: from e120937-lin.home (unknown [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 387A63F5A1; Mon, 22 Nov 2021 15:07:25 -0800 (PST) From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org Cc: sudeep.holla@arm.com, james.quinlan@broadcom.com, Jonathan.Cameron@Huawei.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, souvik.chakravarty@arm.com, cristian.marussi@arm.com Subject: [PATCH v6 13/16] firmware: arm_scmi: Add new parameter to mark_txdone Date: Mon, 22 Nov 2021 23:06:37 +0000 Message-Id: <20211122230640.1345-14-cristian.marussi@arm.com> X-Mailer: git-send-email 2.17.1 In-Reply-To: <20211122230640.1345-1-cristian.marussi@arm.com> References: <20211122230640.1345-1-cristian.marussi@arm.com> X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20211122_150727_699174_C6D52353 X-CRM114-Status: GOOD ( 11.28 ) 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: , MIME-Version: 1.0 Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org Add a new xfer parameter to mark_txdone transport operation which enables the SCMI core to optionally pass back into the transport layer a reference to the xfer descriptor that is being handled. Signed-off-by: Cristian Marussi --- drivers/firmware/arm_scmi/common.h | 3 ++- drivers/firmware/arm_scmi/driver.c | 2 +- drivers/firmware/arm_scmi/mailbox.c | 3 ++- drivers/firmware/arm_scmi/optee.c | 3 ++- drivers/firmware/arm_scmi/smc.c | 3 ++- 5 files changed, 9 insertions(+), 5 deletions(-) diff --git a/drivers/firmware/arm_scmi/common.h b/drivers/firmware/arm_scmi/common.h index 97a65d5fbb1d..8ee12d6e1abe 100644 --- a/drivers/firmware/arm_scmi/common.h +++ b/drivers/firmware/arm_scmi/common.h @@ -381,7 +381,8 @@ struct scmi_transport_ops { unsigned int (*get_max_msg)(struct scmi_chan_info *base_cinfo); int (*send_message)(struct scmi_chan_info *cinfo, struct scmi_xfer *xfer); - void (*mark_txdone)(struct scmi_chan_info *cinfo, int ret); + void (*mark_txdone)(struct scmi_chan_info *cinfo, int ret, + struct scmi_xfer *xfer); void (*fetch_response)(struct scmi_chan_info *cinfo, struct scmi_xfer *xfer); void (*fetch_notification)(struct scmi_chan_info *cinfo, diff --git a/drivers/firmware/arm_scmi/driver.c b/drivers/firmware/arm_scmi/driver.c index 7d6e97d7a077..991b3cfd93c3 100644 --- a/drivers/firmware/arm_scmi/driver.c +++ b/drivers/firmware/arm_scmi/driver.c @@ -881,7 +881,7 @@ static int do_xfer(const struct scmi_protocol_handle *ph, ret = scmi_to_linux_errno(xfer->hdr.status); if (info->desc->ops->mark_txdone) - info->desc->ops->mark_txdone(cinfo, ret); + info->desc->ops->mark_txdone(cinfo, ret, xfer); trace_scmi_xfer_end(xfer->transfer_id, xfer->hdr.id, xfer->hdr.protocol_id, xfer->hdr.seq, ret); diff --git a/drivers/firmware/arm_scmi/mailbox.c b/drivers/firmware/arm_scmi/mailbox.c index e09eb12bf421..126f61934854 100644 --- a/drivers/firmware/arm_scmi/mailbox.c +++ b/drivers/firmware/arm_scmi/mailbox.c @@ -140,7 +140,8 @@ static int mailbox_send_message(struct scmi_chan_info *cinfo, return ret; } -static void mailbox_mark_txdone(struct scmi_chan_info *cinfo, int ret) +static void mailbox_mark_txdone(struct scmi_chan_info *cinfo, int ret, + struct scmi_xfer *xfer) { struct scmi_mailbox *smbox = cinfo->transport_info; diff --git a/drivers/firmware/arm_scmi/optee.c b/drivers/firmware/arm_scmi/optee.c index f215e823d351..9228fb668870 100644 --- a/drivers/firmware/arm_scmi/optee.c +++ b/drivers/firmware/arm_scmi/optee.c @@ -458,7 +458,8 @@ static void scmi_optee_fetch_response(struct scmi_chan_info *cinfo, shmem_fetch_response(shmem, xfer); } -static void scmi_optee_mark_txdone(struct scmi_chan_info *cinfo, int ret) +static void scmi_optee_mark_txdone(struct scmi_chan_info *cinfo, int ret, + struct scmi_xfer *xfer) { struct scmi_optee_channel *channel = cinfo->transport_info; diff --git a/drivers/firmware/arm_scmi/smc.c b/drivers/firmware/arm_scmi/smc.c index 0fc49cb49185..01dc03f52e86 100644 --- a/drivers/firmware/arm_scmi/smc.c +++ b/drivers/firmware/arm_scmi/smc.c @@ -219,7 +219,8 @@ static void smc_fetch_response(struct scmi_chan_info *cinfo, shmem_fetch_response(scmi_info->shmem, xfer); } -static void smc_mark_txdone(struct scmi_chan_info *cinfo, int ret) +static void smc_mark_txdone(struct scmi_chan_info *cinfo, int ret, + struct scmi_xfer *xfer) { struct scmi_smc *scmi_info = cinfo->transport_info; From patchwork Mon Nov 22 23:06:38 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Cristian Marussi X-Patchwork-Id: 12693399 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 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 smtp.lore.kernel.org (Postfix) with ESMTPS id 5F8A1C433F5 for ; Mon, 22 Nov 2021 23:26:52 +0000 (UTC) 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:MIME-Version:List-Subscribe:List-Help: List-Post:List-Archive:List-Unsubscribe:List-Id:References:In-Reply-To: Message-Id:Date:Subject:Cc:To:From:Reply-To:Content-ID:Content-Description: Resent-Date:Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID: List-Owner; bh=97On72D8BIrfnD/Rp3U9PONniprhZASzVDXdx6Sy/LE=; b=3H8EnsFDpgxbSe qEtEUkuE6kzPyEz5bMnlY1tXdTibfL0QegwO5LlxG7sEtOFsXmirV5cGeHKit1e46I6rgROki6MHR +iKBcOjqrjKID5POpRUw6ReB7fPf9dR4LceiBD2/HI2vCjFe1a06A/STfTU/1ZedgDm/Fk4vs6e3B W75Y1TMOKKnvpLIhy12KWtdgwvGZc9EPp5nFya8pxhIKt1zm/sfH1lgnJ8pmYgjpn67JfISy4RBNe I1PVAitX3tk3FqKaUzoS8I4h5rDSNd1r9vOo1uG9ytfXBniCtDC49wG4Q54kkwV5MmaaeNqtjlbB5 i1Gr774ahlU0WiOXzjQw==; Received: from localhost ([::1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIga-000Pjs-QX; Mon, 22 Nov 2021 23:25:21 +0000 Received: from foss.arm.com ([217.140.110.172]) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIPJ-000Jfm-E7 for linux-arm-kernel@lists.infradead.org; Mon, 22 Nov 2021 23:07:31 +0000 Received: from usa-sjc-imap-foss1.foss.arm.com (unknown [10.121.207.14]) by usa-sjc-mx-foss1.foss.arm.com (Postfix) with ESMTP id 171F313A1; Mon, 22 Nov 2021 15:07:29 -0800 (PST) Received: from e120937-lin.home (unknown [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 0CE403F5A1; Mon, 22 Nov 2021 15:07:26 -0800 (PST) From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org Cc: sudeep.holla@arm.com, james.quinlan@broadcom.com, Jonathan.Cameron@Huawei.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, souvik.chakravarty@arm.com, cristian.marussi@arm.com, "Michael S. Tsirkin" , Igor Skalkin , Peter Hilber , virtualization@lists.linux-foundation.org Subject: [PATCH v6 14/16] firmware: arm_scmi: Add atomic mode support to virtio transport Date: Mon, 22 Nov 2021 23:06:38 +0000 Message-Id: <20211122230640.1345-15-cristian.marussi@arm.com> X-Mailer: git-send-email 2.17.1 In-Reply-To: <20211122230640.1345-1-cristian.marussi@arm.com> References: <20211122230640.1345-1-cristian.marussi@arm.com> X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20211122_150729_643277_700D6483 X-CRM114-Status: GOOD ( 32.66 ) 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: , MIME-Version: 1.0 Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org Add support for .mark_txdone and .poll_done transport operations to SCMI VirtIO transport as pre-requisites to enable atomic operations. Add a Kernel configuration option to enable SCMI VirtIO transport polling and atomic mode for selected SCMI transactions while leaving it default disabled. Cc: "Michael S. Tsirkin" Cc: Igor Skalkin Cc: Peter Hilber Cc: virtualization@lists.linux-foundation.org Signed-off-by: Cristian Marussi --- drivers/firmware/arm_scmi/Kconfig | 15 ++ drivers/firmware/arm_scmi/virtio.c | 212 +++++++++++++++++++++++++++-- 2 files changed, 214 insertions(+), 13 deletions(-) diff --git a/drivers/firmware/arm_scmi/Kconfig b/drivers/firmware/arm_scmi/Kconfig index d429326433d1..7794bd41eaa0 100644 --- a/drivers/firmware/arm_scmi/Kconfig +++ b/drivers/firmware/arm_scmi/Kconfig @@ -118,6 +118,21 @@ config ARM_SCMI_TRANSPORT_VIRTIO_VERSION1_COMPLIANCE the ones implemented by kvmtool) and let the core Kernel VirtIO layer take care of the needed conversions, say N. +config ARM_SCMI_TRANSPORT_VIRTIO_ATOMIC_ENABLE + bool "Enable atomic mode for SCMI VirtIO transport" + depends on ARM_SCMI_TRANSPORT_VIRTIO + help + Enable support of atomic operation for SCMI VirtIO based transport. + + If you want the SCMI VirtIO based transport to operate in atomic + mode, avoiding any kind of sleeping behaviour for selected + transactions on the TX path, answer Y. + + Enabling atomic mode operations allows any SCMI driver using this + transport to optionally ask for atomic SCMI transactions and operate + in atomic context too, at the price of using a number of busy-waiting + primitives all over instead. If unsure say N. + endif #ARM_SCMI_PROTOCOL config ARM_SCMI_POWER_DOMAIN diff --git a/drivers/firmware/arm_scmi/virtio.c b/drivers/firmware/arm_scmi/virtio.c index fd0f6f91fc0b..3101024751b0 100644 --- a/drivers/firmware/arm_scmi/virtio.c +++ b/drivers/firmware/arm_scmi/virtio.c @@ -38,6 +38,7 @@ * @vqueue: Associated virtqueue * @cinfo: SCMI Tx or Rx channel * @free_list: List of unused scmi_vio_msg, maintained for Tx channels only + * @pending_cmds_list: List of pre-fetched commands queueud for later processing * @is_rx: Whether channel is an Rx channel * @ready: Whether transport user is ready to hear about channel * @max_msg: Maximum number of pending messages for this channel. @@ -49,6 +50,9 @@ struct scmi_vio_channel { struct virtqueue *vqueue; struct scmi_chan_info *cinfo; struct list_head free_list; +#ifdef CONFIG_ARM_SCMI_TRANSPORT_VIRTIO_ATOMIC_ENABLE + struct list_head pending_cmds_list; +#endif bool is_rx; bool ready; unsigned int max_msg; @@ -65,12 +69,22 @@ struct scmi_vio_channel { * @input: SDU used for (delayed) responses and notifications * @list: List which scmi_vio_msg may be part of * @rx_len: Input SDU size in bytes, once input has been received + * @poll_idx: Last used index registered for polling purposes if this message + * transaction reply was configured for polling. + * Note that virtqueue used index is an unsigned 16-bit. + * @poll_lock: Protect access to @poll_idx. */ struct scmi_vio_msg { struct scmi_msg_payld *request; struct scmi_msg_payld *input; struct list_head list; unsigned int rx_len; +#ifdef CONFIG_ARM_SCMI_TRANSPORT_VIRTIO_ATOMIC_ENABLE +#define VIO_MSG_POLL_DONE 0xffffffffUL + unsigned int poll_idx; + /* lock to protect access to poll_idx. */ + spinlock_t poll_lock; +#endif }; /* Only one SCMI VirtIO device can possibly exist */ @@ -104,17 +118,22 @@ static int scmi_vio_feed_vq_rx(struct scmi_vio_channel *vioch, return rc; } +static inline void scmi_vio_feed_vq_tx(struct scmi_vio_channel *vioch, + struct scmi_vio_msg *msg) +{ + /* Here IRQs are assumed to be already disabled by the caller */ + spin_lock(&vioch->lock); + list_add(&msg->list, &vioch->free_list); + spin_unlock(&vioch->lock); +} + static void scmi_finalize_message(struct scmi_vio_channel *vioch, struct scmi_vio_msg *msg) { - if (vioch->is_rx) { + if (vioch->is_rx) scmi_vio_feed_vq_rx(vioch, msg, vioch->cinfo->dev); - } else { - /* Here IRQs are assumed to be already disabled by the caller */ - spin_lock(&vioch->lock); - list_add(&msg->list, &vioch->free_list); - spin_unlock(&vioch->lock); - } + else + scmi_vio_feed_vq_tx(vioch, msg); } static void scmi_vio_complete_cb(struct virtqueue *vqueue) @@ -138,12 +157,29 @@ static void scmi_vio_complete_cb(struct virtqueue *vqueue) goto unlock_ready_out; } +#ifdef CONFIG_ARM_SCMI_TRANSPORT_VIRTIO_ATOMIC_ENABLE + /* At first loop on pending_cmd_list of buffered msg if any */ + if (!vioch->is_rx) { + struct scmi_vio_msg *tmp; + + list_for_each_entry_safe(msg, tmp, + &vioch->pending_cmds_list, + list) { + scmi_rx_callback(vioch->cinfo, + msg_read_header(msg->input), + msg); + scmi_vio_feed_vq_tx(vioch, msg); + } + } +#endif + /* IRQs already disabled here no need to irqsave */ spin_lock(&vioch->lock); if (cb_enabled) { virtqueue_disable_cb(vqueue); cb_enabled = false; } + msg = virtqueue_get_buf(vqueue, &length); if (!msg) { if (virtqueue_enable_cb(vqueue)) @@ -257,6 +293,9 @@ static int virtio_chan_setup(struct scmi_chan_info *cinfo, struct device *dev, GFP_KERNEL); if (!msg->request) return -ENOMEM; +#ifdef CONFIG_ARM_SCMI_TRANSPORT_VIRTIO_ATOMIC_ENABLE + spin_lock_init(&msg->poll_lock); +#endif } msg->input = devm_kzalloc(cinfo->dev, VIRTIO_SCMI_MAX_PDU_SIZE, @@ -324,13 +363,23 @@ static int virtio_send_message(struct scmi_chan_info *cinfo, } msg = list_first_entry(&vioch->free_list, typeof(*msg), list); - list_del(&msg->list); + list_del_init(&msg->list); msg_tx_prepare(msg->request, xfer); sg_init_one(&sg_out, msg->request, msg_command_size(xfer)); sg_init_one(&sg_in, msg->input, msg_response_size(xfer)); +#ifdef CONFIG_ARM_SCMI_TRANSPORT_VIRTIO_ATOMIC_ENABLE + if (xfer->hdr.poll_completion) { + /* Retrieve last used index and use it as polling reference. */ + spin_lock(&msg->poll_lock); + msg->poll_idx = virtqueue_enable_cb_prepare(vioch->vqueue); + spin_unlock(&msg->poll_lock); + xfer->priv = msg; + } +#endif + rc = virtqueue_add_sgs(vioch->vqueue, sgs, 1, 1, msg, GFP_ATOMIC); if (rc) { list_add(&msg->list, &vioch->free_list); @@ -350,10 +399,8 @@ static void virtio_fetch_response(struct scmi_chan_info *cinfo, { struct scmi_vio_msg *msg = xfer->priv; - if (msg) { + if (msg) msg_fetch_response(msg->input, msg->rx_len, xfer); - xfer->priv = NULL; - } } static void virtio_fetch_notification(struct scmi_chan_info *cinfo, @@ -361,11 +408,142 @@ static void virtio_fetch_notification(struct scmi_chan_info *cinfo, { struct scmi_vio_msg *msg = xfer->priv; - if (msg) { + if (msg) msg_fetch_notification(msg->input, msg->rx_len, max_len, xfer); - xfer->priv = NULL; +} + +#ifdef CONFIG_ARM_SCMI_TRANSPORT_VIRTIO_ATOMIC_ENABLE +/** + * virtio_mark_txdone - Mark transmission done + * + * Free successfully completed polling transfer messages. + * + * @cinfo: SCMI channel info + * @ret: Transmission return code + * @xfer: Transfer descriptor + */ +static void virtio_mark_txdone(struct scmi_chan_info *cinfo, int ret, + struct scmi_xfer *xfer) +{ + unsigned long flags; + struct scmi_vio_channel *vioch = cinfo->transport_info; + struct scmi_vio_msg *msg = xfer->priv; + + if (!msg) + return; + + /* Is a successfully polling reply message still to be finalized ? */ + spin_lock_irqsave(&msg->poll_lock, flags); + if (!ret && xfer->hdr.poll_completion && list_empty(&msg->list)) + scmi_vio_feed_vq_tx(vioch, msg); + spin_unlock_irqrestore(&msg->poll_lock, flags); + + xfer->priv = NULL; +} + +/** + * virtio_poll_done - Provide polling support for VirtIO transport + * + * @cinfo: SCMI channel info + * @xfer: Reference to the transfer being poll for. + * + * VirtIO core provides a polling mechanism based only on last used indexes: + * this means that it is possible to poll the virtqueues waiting for something + * new to arrive from the host side but the only way to check if the freshly + * arrived buffer was what we were waiting for is to compare the newly arrived + * message descriptors with the one we are polling on. + * + * As a consequence it can happen to dequeue something different from the buffer + * we were poll-waiting for: if that is the case such early fetched buffers are + * then added to a the @pending_cmds_list list for later processing within the + * usual VirtIO callbacks; so, basically, once something new is spotted we + * proceed to de-queue all the freshly received used buffers until we found the + * one we were polling on, or we empty the virtqueue. + * + * Note that we do NOT suppress notification with VIRTQ_USED_F_NO_NOTIFY even + * when polling since such flag is per-virtqueues and we do not want to + * suppress notifications as a whole: so, if the message we are polling for is + * delivered via usual IRQs callbacks, it will be handled as such and the + * polling loop will be transparently terminated anyway. + * + * Return: True once polling has successfully completed. + */ +static bool virtio_poll_done(struct scmi_chan_info *cinfo, + struct scmi_xfer *xfer) +{ + bool ret; + unsigned long flags; + struct scmi_vio_msg *msg = xfer->priv; + struct scmi_vio_channel *vioch = cinfo->transport_info; + + if (!msg) + return true; + + /* Processed already by other polling on another CPU ? */ + spin_lock_irqsave(&msg->poll_lock, flags); + if (msg->poll_idx == VIO_MSG_POLL_DONE) { + spin_unlock_irqrestore(&msg->poll_lock, flags); + return true; } + + /* Has cmdq index moved at all ? */ + ret = virtqueue_poll(vioch->vqueue, msg->poll_idx); + spin_unlock_irqrestore(&msg->poll_lock, flags); + if (ret) { + struct scmi_vio_msg *next_msg; + + spin_lock_irqsave(&vioch->lock, flags); + virtqueue_disable_cb(vioch->vqueue); + + /* + * If something arrived we cannot be sure if it was the reply to + * the xfer we are polling for some other replies to other, even + * possibly non-polling, pending xfer: process all new messages + * till the polling-for message is found OR the vqueue is empty. + */ + do { + unsigned int length; + + next_msg = virtqueue_get_buf(vioch->vqueue, &length); + if (next_msg) { + next_msg->rx_len = length; + if (next_msg == msg) { + ret = true; + break; + } + + list_add_tail(&next_msg->list, + &vioch->pending_cmds_list); + spin_lock(&next_msg->poll_lock); + next_msg->poll_idx = VIO_MSG_POLL_DONE; + spin_unlock(&next_msg->poll_lock); + ret = false; + } + } while (next_msg); + + /* + * When the polling loop has successfully terminated simply + * restart the vqueue, no matter if something else was queued + * in the meantime, it will be served by normal IRQ/callback. + * + * If we emptied the vqueue but there's still no sign + * of the message we are polling for, update the polling + * index to the current vqueue head. + */ + if (ret) { + virtqueue_enable_cb(vioch->vqueue); + } else { + spin_lock(&msg->poll_lock); + msg->poll_idx = + virtqueue_enable_cb_prepare(vioch->vqueue); + spin_unlock(&msg->poll_lock); + } + spin_unlock_irqrestore(&vioch->lock, flags); + } + + return ret; } +#endif static const struct scmi_transport_ops scmi_virtio_ops = { .link_supplier = virtio_link_supplier, @@ -376,6 +554,10 @@ static const struct scmi_transport_ops scmi_virtio_ops = { .send_message = virtio_send_message, .fetch_response = virtio_fetch_response, .fetch_notification = virtio_fetch_notification, +#ifdef CONFIG_ARM_SCMI_TRANSPORT_VIRTIO_ATOMIC_ENABLE + .mark_txdone = virtio_mark_txdone, + .poll_done = virtio_poll_done, +#endif }; static int scmi_vio_probe(struct virtio_device *vdev) @@ -418,6 +600,9 @@ static int scmi_vio_probe(struct virtio_device *vdev) spin_lock_init(&channels[i].lock); spin_lock_init(&channels[i].ready_lock); INIT_LIST_HEAD(&channels[i].free_list); +#ifdef CONFIG_ARM_SCMI_TRANSPORT_VIRTIO_ATOMIC_ENABLE + INIT_LIST_HEAD(&channels[i].pending_cmds_list); +#endif channels[i].vqueue = vqs[i]; sz = virtqueue_get_vring_size(channels[i].vqueue); @@ -506,4 +691,5 @@ const struct scmi_desc scmi_virtio_desc = { .max_rx_timeout_ms = 60000, /* for non-realtime virtio devices */ .max_msg = 0, /* overridden by virtio_get_max_msg() */ .max_msg_size = VIRTIO_SCMI_MAX_MSG_SIZE, + .atomic_enabled = IS_ENABLED(CONFIG_ARM_SCMI_TRANSPORT_VIRTIO_ATOMIC_ENABLE), }; From patchwork Mon Nov 22 23:06:39 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Cristian Marussi X-Patchwork-Id: 12693400 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 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 smtp.lore.kernel.org (Postfix) with ESMTPS id 6FDE5C433EF for ; Mon, 22 Nov 2021 23:27:30 +0000 (UTC) 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:MIME-Version:List-Subscribe:List-Help: List-Post:List-Archive:List-Unsubscribe:List-Id:References:In-Reply-To: Message-Id:Date:Subject:Cc:To:From:Reply-To:Content-ID:Content-Description: Resent-Date:Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID: List-Owner; bh=Wzj5frMQNdNOr+84OfJfeo6gSNCX79MlK989gLCRMHc=; b=ZE5hMYfNacFoLF RcsWyW0huvCC/vYZ1Mm8IItFQmPmTcNnDflmT2O4TZmzlYwyAQxn3+0lzipkXfKw1E19oRv6GD/Xm 1llO25cOG5HK9aGIsPbbY9UDxEO0lnh9EQnHS2WnbLCi5hqU2XBe8DdYrGrY4ieebdTs/kEmcV+3d l4sxctcEEr2glck8+KzSLfuOURTkb3H4RsM/Km3963R/5yFfQe+0OoDC0pk2YTzS32Vq7oeJrv+yd V8W9wREZO7CnQrn0cd84csEMUZ6ahG0Mhz3k5FFNvN1dK9wAr937/M/2Gtm5oQz/DuUZyT+pPQukS ph+/ESQgjAwgYwmaVnug==; Received: from localhost ([::1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIhB-000Q1j-TZ; Mon, 22 Nov 2021 23:25:58 +0000 Received: from foss.arm.com ([217.140.110.172]) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIPL-000Jhb-ON for linux-arm-kernel@lists.infradead.org; Mon, 22 Nov 2021 23:07:33 +0000 Received: from usa-sjc-imap-foss1.foss.arm.com (unknown [10.121.207.14]) by usa-sjc-mx-foss1.foss.arm.com (Postfix) with ESMTP id D6880ED1; Mon, 22 Nov 2021 15:07:30 -0800 (PST) Received: from e120937-lin.home (unknown [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 4C5353F5A1; Mon, 22 Nov 2021 15:07:29 -0800 (PST) From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org Cc: sudeep.holla@arm.com, james.quinlan@broadcom.com, Jonathan.Cameron@Huawei.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, souvik.chakravarty@arm.com, cristian.marussi@arm.com Subject: [PATCH v6 15/16] firmware: arm_scmi: Add atomic support to clock protocol Date: Mon, 22 Nov 2021 23:06:39 +0000 Message-Id: <20211122230640.1345-16-cristian.marussi@arm.com> X-Mailer: git-send-email 2.17.1 In-Reply-To: <20211122230640.1345-1-cristian.marussi@arm.com> References: <20211122230640.1345-1-cristian.marussi@arm.com> X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20211122_150732_054679_3B65F683 X-CRM114-Status: GOOD ( 11.34 ) 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: , MIME-Version: 1.0 Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org Introduce new _atomic variant for SCMI clock protocol operations related to enable disable operations: when an atomic operation is required the xfer poll_completion flag is set for that transaction. Signed-off-by: Cristian Marussi --- drivers/firmware/arm_scmi/clock.c | 22 +++++++++++++++++++--- include/linux/scmi_protocol.h | 3 +++ 2 files changed, 22 insertions(+), 3 deletions(-) diff --git a/drivers/firmware/arm_scmi/clock.c b/drivers/firmware/arm_scmi/clock.c index 35b56c8ba0c0..72f930c0e3e2 100644 --- a/drivers/firmware/arm_scmi/clock.c +++ b/drivers/firmware/arm_scmi/clock.c @@ -273,7 +273,7 @@ static int scmi_clock_rate_set(const struct scmi_protocol_handle *ph, static int scmi_clock_config_set(const struct scmi_protocol_handle *ph, u32 clk_id, - u32 config) + u32 config, bool atomic) { int ret; struct scmi_xfer *t; @@ -284,6 +284,8 @@ scmi_clock_config_set(const struct scmi_protocol_handle *ph, u32 clk_id, if (ret) return ret; + t->hdr.poll_completion = atomic; + cfg = t->tx.buf; cfg->id = cpu_to_le32(clk_id); cfg->attributes = cpu_to_le32(config); @@ -296,12 +298,24 @@ scmi_clock_config_set(const struct scmi_protocol_handle *ph, u32 clk_id, static int scmi_clock_enable(const struct scmi_protocol_handle *ph, u32 clk_id) { - return scmi_clock_config_set(ph, clk_id, CLOCK_ENABLE); + return scmi_clock_config_set(ph, clk_id, CLOCK_ENABLE, false); } static int scmi_clock_disable(const struct scmi_protocol_handle *ph, u32 clk_id) { - return scmi_clock_config_set(ph, clk_id, 0); + return scmi_clock_config_set(ph, clk_id, 0, false); +} + +static int scmi_clock_enable_atomic(const struct scmi_protocol_handle *ph, + u32 clk_id) +{ + return scmi_clock_config_set(ph, clk_id, CLOCK_ENABLE, true); +} + +static int scmi_clock_disable_atomic(const struct scmi_protocol_handle *ph, + u32 clk_id) +{ + return scmi_clock_config_set(ph, clk_id, 0, true); } static int scmi_clock_count_get(const struct scmi_protocol_handle *ph) @@ -330,6 +344,8 @@ static const struct scmi_clk_proto_ops clk_proto_ops = { .rate_set = scmi_clock_rate_set, .enable = scmi_clock_enable, .disable = scmi_clock_disable, + .enable_atomic = scmi_clock_enable_atomic, + .disable_atomic = scmi_clock_disable_atomic, }; static int scmi_clock_protocol_init(const struct scmi_protocol_handle *ph) diff --git a/include/linux/scmi_protocol.h b/include/linux/scmi_protocol.h index 9f895cb81818..d4971c991963 100644 --- a/include/linux/scmi_protocol.h +++ b/include/linux/scmi_protocol.h @@ -82,6 +82,9 @@ struct scmi_clk_proto_ops { u64 rate); int (*enable)(const struct scmi_protocol_handle *ph, u32 clk_id); int (*disable)(const struct scmi_protocol_handle *ph, u32 clk_id); + int (*enable_atomic)(const struct scmi_protocol_handle *ph, u32 clk_id); + int (*disable_atomic)(const struct scmi_protocol_handle *ph, + u32 clk_id); }; /** From patchwork Mon Nov 22 23:06:40 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Cristian Marussi X-Patchwork-Id: 12693401 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 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 smtp.lore.kernel.org (Postfix) with ESMTPS id 9B01FC433EF for ; Mon, 22 Nov 2021 23:28:13 +0000 (UTC) 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:MIME-Version:List-Subscribe:List-Help: List-Post:List-Archive:List-Unsubscribe:List-Id:References:In-Reply-To: Message-Id:Date:Subject:Cc:To:From:Reply-To:Content-ID:Content-Description: Resent-Date:Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID: List-Owner; bh=ttii41pPLO9SmgK91bFDXW3oOnXSoHwl9xLNwmJBO6I=; b=gTTfB+1I0xaLZ2 ZjtU4XSChMoerNz8gTqfg3DGpOviRIf1aSCjdoYl3HOFivqNMejHJiClDv/tBl2c+WdmSdmSh+WAM /jvZegSzC2Fmj77/izVdUuLvCWVZizuF2KeLQqKW2miT6QdYRUolV5ue91NuDPa9NNLoBcXAsA5xs tic00K58tbiacCmd/v0e+TheXKSWBtUyuXyU8f+8n6pKJcWJWftWv0cV67Kwr2aPFujMMS8UbjoHx Ohrkl/q5Ptgs402lkZPSD3GamD4VQ5Ll6HbjwCKGuxHwmryr+NuieIUaD1ttnYn1I4/InYCJqIvhn Dc+FHFrYiQqewn4oztHQ==; Received: from localhost ([::1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIht-000QKn-NV; Mon, 22 Nov 2021 23:26:42 +0000 Received: from foss.arm.com ([217.140.110.172]) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1mpIPN-000Jfm-4A for linux-arm-kernel@lists.infradead.org; Mon, 22 Nov 2021 23:07:35 +0000 Received: from usa-sjc-imap-foss1.foss.arm.com (unknown [10.121.207.14]) by usa-sjc-mx-foss1.foss.arm.com (Postfix) with ESMTP id DF7CE1063; Mon, 22 Nov 2021 15:07:32 -0800 (PST) Received: from e120937-lin.home (unknown [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 1856C3F5A1; Mon, 22 Nov 2021 15:07:30 -0800 (PST) From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org Cc: sudeep.holla@arm.com, james.quinlan@broadcom.com, Jonathan.Cameron@Huawei.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, souvik.chakravarty@arm.com, cristian.marussi@arm.com, Michael Turquette , Stephen Boyd , linux-clk@vger.kernel.org Subject: [PATCH v6 16/16] clk: scmi: Support atomic clock enable/disable API Date: Mon, 22 Nov 2021 23:06:40 +0000 Message-Id: <20211122230640.1345-17-cristian.marussi@arm.com> X-Mailer: git-send-email 2.17.1 In-Reply-To: <20211122230640.1345-1-cristian.marussi@arm.com> References: <20211122230640.1345-1-cristian.marussi@arm.com> X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20211122_150733_328580_090607D0 X-CRM114-Status: GOOD ( 16.61 ) 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: , MIME-Version: 1.0 Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org Support also atomic enable/disable clk_ops beside the bare non-atomic one (sprepare/unprepare) when the underlying SCMI transport is configured to support atomic transactions for synchronous commands. Cc: Michael Turquette Cc: Stephen Boyd Cc: linux-clk@vger.kernel.org Signed-off-by: Cristian Marussi --- V5 --> V6 - add concurrent availability of atomic and non atomic reqs --- drivers/clk/clk-scmi.c | 56 +++++++++++++++++++++++++++++++++++------- 1 file changed, 47 insertions(+), 9 deletions(-) diff --git a/drivers/clk/clk-scmi.c b/drivers/clk/clk-scmi.c index 1e357d364ca2..50033d873dde 100644 --- a/drivers/clk/clk-scmi.c +++ b/drivers/clk/clk-scmi.c @@ -88,21 +88,53 @@ static void scmi_clk_disable(struct clk_hw *hw) scmi_proto_clk_ops->disable(clk->ph, clk->id); } +static int scmi_clk_atomic_enable(struct clk_hw *hw) +{ + struct scmi_clk *clk = to_scmi_clk(hw); + + return scmi_proto_clk_ops->enable_atomic(clk->ph, clk->id); +} + +static void scmi_clk_atomic_disable(struct clk_hw *hw) +{ + struct scmi_clk *clk = to_scmi_clk(hw); + + scmi_proto_clk_ops->disable_atomic(clk->ph, clk->id); +} + +/* + * We can provide enable/disable atomic callbacks only if the underlying SCMI + * transport for an SCMI instance is configured to handle SCMI commands in an + * atomic manner. + * + * When no SCMI atomic transport support is available we instead provide only + * the prepare/unprepare API, as allowed by the clock framework when atomic + * calls are not available. + * + * Two distinct sets of clk_ops are provided since we could have multiple SCMI + * instances with different underlying transport quality, so they cannot be + * shared. + */ static const struct clk_ops scmi_clk_ops = { .recalc_rate = scmi_clk_recalc_rate, .round_rate = scmi_clk_round_rate, .set_rate = scmi_clk_set_rate, - /* - * We can't provide enable/disable callback as we can't perform the same - * in atomic context. Since the clock framework provides standard API - * clk_prepare_enable that helps cases using clk_enable in non-atomic - * context, it should be fine providing prepare/unprepare. - */ .prepare = scmi_clk_enable, .unprepare = scmi_clk_disable, }; -static int scmi_clk_ops_init(struct device *dev, struct scmi_clk *sclk) +static const struct clk_ops scmi_atomic_clk_ops = { + .recalc_rate = scmi_clk_recalc_rate, + .round_rate = scmi_clk_round_rate, + .set_rate = scmi_clk_set_rate, + .prepare = scmi_clk_enable, + .unprepare = scmi_clk_disable, + .enable = scmi_clk_atomic_enable, + .disable = scmi_clk_atomic_disable, +}; + +static int scmi_clk_ops_init(struct device *dev, struct scmi_clk *sclk, + const struct clk_ops *scmi_ops) { int ret; unsigned long min_rate, max_rate; @@ -110,7 +142,7 @@ static int scmi_clk_ops_init(struct device *dev, struct scmi_clk *sclk) struct clk_init_data init = { .flags = CLK_GET_RATE_NOCACHE, .num_parents = 0, - .ops = &scmi_clk_ops, + .ops = scmi_ops, .name = sclk->info->name, }; @@ -145,6 +177,7 @@ static int scmi_clocks_probe(struct scmi_device *sdev) struct device_node *np = dev->of_node; const struct scmi_handle *handle = sdev->handle; struct scmi_protocol_handle *ph; + const struct clk_ops *scmi_ops; if (!handle) return -ENODEV; @@ -168,6 +201,11 @@ static int scmi_clocks_probe(struct scmi_device *sdev) clk_data->num = count; hws = clk_data->hws; + if (handle->is_transport_atomic(handle)) + scmi_ops = &scmi_atomic_clk_ops; + else + scmi_ops = &scmi_clk_ops; + for (idx = 0; idx < count; idx++) { struct scmi_clk *sclk; @@ -184,7 +222,7 @@ static int scmi_clocks_probe(struct scmi_device *sdev) sclk->id = idx; sclk->ph = ph; - err = scmi_clk_ops_init(dev, sclk); + err = scmi_clk_ops_init(dev, sclk, scmi_ops); if (err) { dev_err(dev, "failed to register clock %d\n", idx); devm_kfree(dev, sclk);