From nobody Wed Jun 17 01:35:13 2026 Received: from foss.arm.com (foss.arm.com [217.140.110.172]) by smtp.subspace.kernel.org (Postfix) with ESMTP id 4420D31715F; Tue, 28 Apr 2026 20:16:34 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=217.140.110.172 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407396; cv=none; b=c+IfS9cPReW9x5kvnO3yA+oD/Un9ZKdXn3AncOv5LQKMLDOxou9dZT9mot6/XoFhdYLPlprNhT2qZYaqFfLTnDIy7g+vTZZSGbu9UFd8p/NF+iiQKFP0EPVrnBs6KUIaOxQ/8c38plDE5dy9aqOt9enSdjs8yV5+Clk4++D8pOw= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407396; c=relaxed/simple; bh=WC1R4qV6I0MneBfZAXWbYrl3W9fg6IoQSFQXIfGStN0=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=Ro0XMq9x53VlCBL8CprlvfuF3eDtWU3kluq6IKGDuWk1dPg8ErRhQ+c+42cStL2E3UFfFRw/oPYM7p6oSvGtj1T+iOcoBFDd/G9JXTIZKfqyZ1NtQaCI28Z8Odezv0vILBmKqtWpEFfShLUEeTXH2z22v4bYQLUU86VZKTAz1Rk= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com; spf=pass smtp.mailfrom=arm.com; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b=eXg0vLHP; arc=none smtp.client-ip=217.140.110.172 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=arm.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b="eXg0vLHP" 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 31E031C0A; Tue, 28 Apr 2026 13:16:28 -0700 (PDT) Received: from pluto.fritz.box (usa-sjc-mx-foss1.foss.arm.com [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 6E5F63F763; Tue, 28 Apr 2026 13:16:30 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=simple/simple; d=arm.com; s=foss; t=1777407393; bh=WC1R4qV6I0MneBfZAXWbYrl3W9fg6IoQSFQXIfGStN0=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=eXg0vLHPQ3z00T2suRMC+1YVlZGq/JF+YxyiR0zHsDToIvSf0OOIqifdnSUEXnlgK bvnswCmmcSzcbBADcouX48T7DVIMZ2qhLB6/qtXsy2wnypmu+yg8HZ1mIv/03HGX64 yJoYVDu84IeRCMZd+BwhjFT5BgNIhQLR6VdJoIUE= From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org, arm-scmi@vger.kernel.org, linux-clk@vger.kernel.org, linux-renesas-soc@vger.kernel.org Cc: sudeep.holla@arm.com, philip.radford@arm.com, james.quinlan@broadcom.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, etienne.carriere@foss.st.com, peng.fan@oss.nxp.com, michal.simek@amd.com, geert+renesas@glider.be, kuninori.morimoto.gx@renesas.com, marek.vasut+renesas@gmail.com, Cristian Marussi , Michael Turquette , Stephen Boyd Subject: [PATCH v3 01/15] clk: scmi: Fix clock rate rounding Date: Tue, 28 Apr 2026 21:15:08 +0100 Message-ID: <20260428201522.903875-2-cristian.marussi@arm.com> X-Mailer: git-send-email 2.53.0 In-Reply-To: <20260428201522.903875-1-cristian.marussi@arm.com> References: <20260428201522.903875-1-cristian.marussi@arm.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" While the do_div() helper used for rounding expects its divisor argument to be a 32bits quantity, the currently provided divisor parameter is a 64bit value that, as a consequence, is silently truncated and a possible source of bugs. Fix by using the proper div64_ul helper. Cc: Michael Turquette Cc: Stephen Boyd Cc: linux-clk@vger.kernel.org Fixes: 7a8655e19bdb ("clk: scmi: Fix the rounding of clock rate") Signed-off-by: Cristian Marussi Tested-by: Florian Fainelli --- drivers/clk/clk-scmi.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/clk/clk-scmi.c b/drivers/clk/clk-scmi.c index 6b286ea6f121..b6a12f3bc123 100644 --- a/drivers/clk/clk-scmi.c +++ b/drivers/clk/clk-scmi.c @@ -10,9 +10,9 @@ #include #include #include +#include #include #include -#include =20 #define NOT_ATOMIC false #define ATOMIC true @@ -83,7 +83,7 @@ static int scmi_clk_determine_rate(struct clk_hw *hw, =20 ftmp =3D req->rate - fmin; ftmp +=3D clk->info->range.step_size - 1; /* to round up */ - do_div(ftmp, clk->info->range.step_size); + ftmp =3D div64_ul(ftmp, clk->info->range.step_size); =20 req->rate =3D ftmp * clk->info->range.step_size + fmin; =20 --=20 2.53.0 From nobody Wed Jun 17 01:35:13 2026 Received: from foss.arm.com (foss.arm.com [217.140.110.172]) by smtp.subspace.kernel.org (Postfix) with ESMTP id 4B1983148DD; Tue, 28 Apr 2026 20:16:37 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=217.140.110.172 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407399; cv=none; b=dOzLl6C80qIAKGFU8xL4qrIoSkzuY7IQYsRfUJk+/I5O3TOmM0+Na91Y8HN2API0Hsn494nyLb97bWZyFDhmaegFRZLUWh+iUF/oxgsSlgNA2Vvh/59+CZignBMgrWzVXG8ZIY+t1T4c39G4PXNcj/I80OVwCGDdd86TMgDdvOE= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407399; c=relaxed/simple; bh=FouQA+bv5j1EdgH3z1eqPEIT8/R9xB/bagn+V+J4Zec=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=g2OzkgmLNXx5btJvpVPzGYnr8jxfNr6mpuOJjyoE/5phwirnJ+fweioe4Alc0xQavZCR47+V5Uckj8A2fjfNNtMvUd07zgFSXGNCfG5Jvpcc2fN3YnwxKcKHdypKSapIosTdaSocp70NqcgcruVJv+o2ptHQbaZ6PQBlDkPCIos= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com; spf=pass smtp.mailfrom=arm.com; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b=MFx+FfVS; arc=none smtp.client-ip=217.140.110.172 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=arm.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b="MFx+FfVS" 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 4BBC13295; Tue, 28 Apr 2026 13:16:31 -0700 (PDT) Received: from pluto.fritz.box (usa-sjc-mx-foss1.foss.arm.com [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 043A73F763; Tue, 28 Apr 2026 13:16:33 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=simple/simple; d=arm.com; s=foss; t=1777407396; bh=FouQA+bv5j1EdgH3z1eqPEIT8/R9xB/bagn+V+J4Zec=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=MFx+FfVS7ekISqM2rC0y9p6YaqHj+egphpXU1nI6RUH1Fy1d+2YVVCcd7mki2DfWg Q7AizXEqaBzeIjEhKDYugYignd54bKJCO9um69zP9UWvpFfw8pyiuO0GWBQSbNdlAP WtlVihIU7iFjXmcLmDZNPrE7Vd/0EnVPdUli5Mwg= From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org, arm-scmi@vger.kernel.org, linux-clk@vger.kernel.org, linux-renesas-soc@vger.kernel.org Cc: sudeep.holla@arm.com, philip.radford@arm.com, james.quinlan@broadcom.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, etienne.carriere@foss.st.com, peng.fan@oss.nxp.com, michal.simek@amd.com, geert+renesas@glider.be, kuninori.morimoto.gx@renesas.com, marek.vasut+renesas@gmail.com, Cristian Marussi Subject: [PATCH v3 02/15] firmware: arm_scmi: Add clock determine_rate operation Date: Tue, 28 Apr 2026 21:15:09 +0100 Message-ID: <20260428201522.903875-3-cristian.marussi@arm.com> X-Mailer: git-send-email 2.53.0 In-Reply-To: <20260428201522.903875-1-cristian.marussi@arm.com> References: <20260428201522.903875-1-cristian.marussi@arm.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" Add a clock operation to help determining the effective rate, closest to the required one, that a specific clock can support. Calculation is currently performed kernel side and the logic is taken directly from the SCMI Clock driver: embedding the determinate rate logic in the protocol layer enables simplifications in the SCMI Clock protocol interface and will more easily accommodate further evolutions where such determine_rate logic into is optionally delegated to the platform SCMI server. Signed-off-by: Cristian Marussi Tested-by: Florian Fainelli --- v1 --> v2 - use the fixed rounding algo using div64_ul Spoiler alert next SCMI spec will most probably include a new CLOCK_DETERMINE_RATE command to delegate to the platform such calculations, so this clock proto_ops will be needed anyway sooner or later --- drivers/firmware/arm_scmi/clock.c | 42 +++++++++++++++++++++++++++++++ include/linux/scmi_protocol.h | 6 +++++ 2 files changed, 48 insertions(+) diff --git a/drivers/firmware/arm_scmi/clock.c b/drivers/firmware/arm_scmi/= clock.c index ab36871650a1..54b55517b759 100644 --- a/drivers/firmware/arm_scmi/clock.c +++ b/drivers/firmware/arm_scmi/clock.c @@ -5,6 +5,7 @@ * Copyright (C) 2018-2022 ARM Ltd. */ =20 +#include #include #include #include @@ -624,6 +625,46 @@ static int scmi_clock_rate_set(const struct scmi_proto= col_handle *ph, return ret; } =20 +static int scmi_clock_determine_rate(const struct scmi_protocol_handle *ph, + u32 clk_id, unsigned long *rate) +{ + u64 fmin, fmax, ftmp; + struct scmi_clock_info *clk; + struct clock_info *ci =3D ph->get_priv(ph); + + if (!rate) + return -EINVAL; + + clk =3D scmi_clock_domain_lookup(ci, clk_id); + if (IS_ERR(clk)) + return PTR_ERR(clk); + + /* + * If we can't figure out what rate it will be, so just return the + * rate back to the caller. + */ + if (clk->rate_discrete) + return 0; + + fmin =3D clk->range.min_rate; + fmax =3D clk->range.max_rate; + if (*rate <=3D fmin) { + *rate =3D fmin; + return 0; + } else if (*rate >=3D fmax) { + *rate =3D fmax; + return 0; + } + + ftmp =3D *rate - fmin; + ftmp +=3D clk->range.step_size - 1; /* to round up */ + ftmp =3D div64_ul(ftmp, clk->range.step_size); + + *rate =3D ftmp * clk->range.step_size + fmin; + + return 0; +} + static int scmi_clock_config_set(const struct scmi_protocol_handle *ph, u32 clk_id, enum clk_state state, @@ -936,6 +977,7 @@ static const struct scmi_clk_proto_ops clk_proto_ops = =3D { .info_get =3D scmi_clock_info_get, .rate_get =3D scmi_clock_rate_get, .rate_set =3D scmi_clock_rate_set, + .determine_rate =3D scmi_clock_determine_rate, .enable =3D scmi_clock_enable, .disable =3D scmi_clock_disable, .state_get =3D scmi_clock_state_get, diff --git a/include/linux/scmi_protocol.h b/include/linux/scmi_protocol.h index aafaac1496b0..28579c145045 100644 --- a/include/linux/scmi_protocol.h +++ b/include/linux/scmi_protocol.h @@ -91,6 +91,10 @@ enum scmi_clock_oem_config { * @info_get: get the information of the specified clock * @rate_get: request the current clock rate of a clock * @rate_set: set the clock rate of a clock + * @determine_rate: determine the effective rate that can be supported by a + * clock calculating the closest allowed rate. + * Note that @rate is an input/output parameter used both to + * describe the requested rate and report the closest match * @enable: enables the specified clock * @disable: disables the specified clock * @state_get: get the status of the specified clock @@ -108,6 +112,8 @@ struct scmi_clk_proto_ops { u64 *rate); int (*rate_set)(const struct scmi_protocol_handle *ph, u32 clk_id, u64 rate); + int (*determine_rate)(const struct scmi_protocol_handle *ph, u32 clk_id, + unsigned long *rate); int (*enable)(const struct scmi_protocol_handle *ph, u32 clk_id, bool atomic); int (*disable)(const struct scmi_protocol_handle *ph, u32 clk_id, --=20 2.53.0 From nobody Wed Jun 17 01:35:13 2026 Received: from foss.arm.com (foss.arm.com [217.140.110.172]) by smtp.subspace.kernel.org (Postfix) with ESMTP id 0E9DA313E1D; Tue, 28 Apr 2026 20:16:40 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=217.140.110.172 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407402; cv=none; b=lDqE8OoLpBGFrl7Qvy+jvjT4zhG0Fo9LTPlQGG0FOvX5w8qhvrXa9DA0GeY2tieRxsBRq/HYppga3S9FVlQo/rCDG3W1JEUVr5cO7q+Mt8NYQLna1gKUVwKtzI8qfkOXkfrsjJre2rROm70tzgXuaZIU1XI3lQDMRzSXXcwVopM= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407402; c=relaxed/simple; bh=rgpT6JeYUUTF8dPGQi0+aswaXnBqWOyh+njR4c8YQ2g=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=ZfsOwoOCrM828lk7feqEr+JhNDkvpcGD7Qvt1DCju31LEkLrMMdjP5NmOHv0fKdcI0StJIzVoCNMb+3lgkgzmUNJPj7aoUrie+uFymbuj3TFimvBAa/+BPrUjNLmPsFiTKbD9w4di/9sK6sgXFZXWT7gclKY32noZDZCegEX90I= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com; spf=pass smtp.mailfrom=arm.com; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b=GB74LoxZ; arc=none smtp.client-ip=217.140.110.172 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=arm.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b="GB74LoxZ" 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 0897A3296; Tue, 28 Apr 2026 13:16:35 -0700 (PDT) Received: from pluto.fritz.box (usa-sjc-mx-foss1.foss.arm.com [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 1F17D3F763; Tue, 28 Apr 2026 13:16:36 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=simple/simple; d=arm.com; s=foss; t=1777407400; bh=rgpT6JeYUUTF8dPGQi0+aswaXnBqWOyh+njR4c8YQ2g=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=GB74LoxZt7ZhrnoGJQDDlRWTGE6uIx44OLgSl2LCWR0MZxb0v33zPyUCzUf1DyP5J jzYYV3pb9HRq/+jMQ+r7cYUsR/AWv7/eRYcCvglhbqlF8Dmbgj4/y7MKpyBAmIkNVu GPgofIaURFERY3XQuXqF7pnV/fzYrZB6hOCc41ZI= From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org, arm-scmi@vger.kernel.org, linux-clk@vger.kernel.org, linux-renesas-soc@vger.kernel.org Cc: sudeep.holla@arm.com, philip.radford@arm.com, james.quinlan@broadcom.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, etienne.carriere@foss.st.com, peng.fan@oss.nxp.com, michal.simek@amd.com, geert+renesas@glider.be, kuninori.morimoto.gx@renesas.com, marek.vasut+renesas@gmail.com, Cristian Marussi , Brian Masney , Michael Turquette , Stephen Boyd Subject: [PATCH v3 03/15] clk: scmi: Use new determine_rate clock operation Date: Tue, 28 Apr 2026 21:15:10 +0100 Message-ID: <20260428201522.903875-4-cristian.marussi@arm.com> X-Mailer: git-send-email 2.53.0 In-Reply-To: <20260428201522.903875-1-cristian.marussi@arm.com> References: <20260428201522.903875-1-cristian.marussi@arm.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" Use the Clock protocol layer determine_rate logic to calculate the closest rate that can be supported by a specific clock. No functional change. Cc: Brian Masney Cc: Michael Turquette Cc: Stephen Boyd Cc: linux-clk@vger.kernel.org Signed-off-by: Cristian Marussi Tested-by: Florian Fainelli --- @brian: I'd modify further this clk-scmi driver, with a patch on top of this series, to properly use your new CLK_ROUNDING_NOOP flag once your series AND another (already reviewed) series on clk-scmi from Peng are in. --- drivers/clk/clk-scmi.c | 31 ++++++------------------------- 1 file changed, 6 insertions(+), 25 deletions(-) diff --git a/drivers/clk/clk-scmi.c b/drivers/clk/clk-scmi.c index b6a12f3bc123..c223e4ef1dd1 100644 --- a/drivers/clk/clk-scmi.c +++ b/drivers/clk/clk-scmi.c @@ -10,7 +10,6 @@ #include #include #include -#include #include #include =20 @@ -57,35 +56,17 @@ static unsigned long scmi_clk_recalc_rate(struct clk_hw= *hw, static int scmi_clk_determine_rate(struct clk_hw *hw, struct clk_rate_request *req) { - u64 fmin, fmax, ftmp; + int ret; struct scmi_clk *clk =3D to_scmi_clk(hw); =20 /* - * We can't figure out what rate it will be, so just return the - * rate back to the caller. scmi_clk_recalc_rate() will be called - * after the rate is set and we'll know what rate the clock is + * If we could not get a better rate scmi_clk_recalc_rate() will be + * called after the rate is set and we'll know what rate the clock is * running at then. */ - if (clk->info->rate_discrete) - return 0; - - fmin =3D clk->info->range.min_rate; - fmax =3D clk->info->range.max_rate; - if (req->rate <=3D fmin) { - req->rate =3D fmin; - - return 0; - } else if (req->rate >=3D fmax) { - req->rate =3D fmax; - - return 0; - } - - ftmp =3D req->rate - fmin; - ftmp +=3D clk->info->range.step_size - 1; /* to round up */ - ftmp =3D div64_ul(ftmp, clk->info->range.step_size); - - req->rate =3D ftmp * clk->info->range.step_size + fmin; + ret =3D scmi_proto_clk_ops->determine_rate(clk->ph, clk->id, &req->rate); + if (ret) + return ret; =20 return 0; } --=20 2.53.0 From nobody Wed Jun 17 01:35:13 2026 Received: from foss.arm.com (foss.arm.com [217.140.110.172]) by smtp.subspace.kernel.org (Postfix) with ESMTP id AE129320A0E; Tue, 28 Apr 2026 20:16:44 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=217.140.110.172 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407406; cv=none; b=IB+2KBuWaZcOEPMTzYrXfLQX3Qh3MVMapAPVq8TXEAZ0+YS3TWZhWj4A4ORLR/dVJX6DTER5uRnOMiBTVv2igo5qE1/mPkyC6CzTUYN83nAFhmZP8PXrrSvA6mnvQ5s2XHlieodm08Uq7IWtJTGjtuUBfk2BJE4hxk5hqaH8G+Y= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407406; c=relaxed/simple; bh=3PpAaUWJz5Jjai21GNJJLV+2UFa/r2ZvY9KI4xPqbu0=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=eOGWj2dLOV73u1V7PnjcS4iEM0YKMC4a3GJRgxcGqItTm5yz61JefBo46c5ThwVD4De9WdskMso8nIEgF6xkw6hS8gigBgj+tprW/i9o+z1CrTJwl5l7TjhFLJuJsOJdRhIwPFH7rV8c1tUPD3Wz0D+D1TP1HwZRPm8kw7CLauM= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com; spf=pass smtp.mailfrom=arm.com; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b=E5QOFggF; arc=none smtp.client-ip=217.140.110.172 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=arm.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b="E5QOFggF" 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 A8D1B3297; Tue, 28 Apr 2026 13:16:38 -0700 (PDT) Received: from pluto.fritz.box (usa-sjc-mx-foss1.foss.arm.com [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id D2F0C3F763; Tue, 28 Apr 2026 13:16:40 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=simple/simple; d=arm.com; s=foss; t=1777407404; bh=3PpAaUWJz5Jjai21GNJJLV+2UFa/r2ZvY9KI4xPqbu0=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=E5QOFggFMhSEoJAixpZ64tiWKKFhzebrQoKVeLp7v+ItMEUCwbPlsC8sPKqMZ5k9a b4HonzF5wToJ7nMCRos+MvK3pLVBYsEs2Vb7YYLyxjjXO6ihNkyWN1aKjBwZt7LgC1 nAHoX3AV2RAv3c6NT9x1pwr5ohE0dmTSb/TQThyM= From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org, arm-scmi@vger.kernel.org, linux-clk@vger.kernel.org, linux-renesas-soc@vger.kernel.org Cc: sudeep.holla@arm.com, philip.radford@arm.com, james.quinlan@broadcom.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, etienne.carriere@foss.st.com, peng.fan@oss.nxp.com, michal.simek@amd.com, geert+renesas@glider.be, kuninori.morimoto.gx@renesas.com, marek.vasut+renesas@gmail.com, Cristian Marussi , Peng Fan Subject: [PATCH v3 04/15] firmware: arm_scmi: Simplify clock rates exposed interface Date: Tue, 28 Apr 2026 21:15:11 +0100 Message-ID: <20260428201522.903875-5-cristian.marussi@arm.com> X-Mailer: git-send-email 2.53.0 In-Reply-To: <20260428201522.903875-1-cristian.marussi@arm.com> References: <20260428201522.903875-1-cristian.marussi@arm.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" Introduce a new internal struct scmi_clock_desc so as to be able to hide, in the future, some of the needlessly public fields currently kept inside scmi_clock_info, while keeping exposed only the two new min_rate and max_rate fields for each clock. No functional change. Reviewed-by: Peng Fan Signed-off-by: Cristian Marussi Tested-by: Florian Fainelli --- v1 --> v2 - removed useless parenthesis - reworded comit message --- drivers/firmware/arm_scmi/clock.c | 145 +++++++++++++++--------------- include/linux/scmi_protocol.h | 2 + 2 files changed, 74 insertions(+), 73 deletions(-) diff --git a/drivers/firmware/arm_scmi/clock.c b/drivers/firmware/arm_scmi/= clock.c index 54b55517b759..467b13a3a18f 100644 --- a/drivers/firmware/arm_scmi/clock.c +++ b/drivers/firmware/arm_scmi/clock.c @@ -157,13 +157,27 @@ struct scmi_clock_rate_notify_payld { __le32 rate_high; }; =20 +struct scmi_clock_desc { + u32 id; + bool rate_discrete; + unsigned int num_rates; + u64 rates[SCMI_MAX_NUM_RATES]; +#define RATE_MIN 0 +#define RATE_MAX 1 +#define RATE_STEP 2 + struct scmi_clock_info info; +}; + +#define to_desc(p) (container_of(p, struct scmi_clock_desc, info)) + struct clock_info { int num_clocks; int max_async_req; bool notify_rate_changed_cmd; bool notify_rate_change_requested_cmd; atomic_t cur_async_req; - struct scmi_clock_info *clk; + struct scmi_clock_desc *clkds; +#define CLOCK_INFO(c, i) (&(((c)->clkds + (i))->info)) int (*clock_config_set)(const struct scmi_protocol_handle *ph, u32 clk_id, enum clk_state state, enum scmi_clock_oem_config oem_type, @@ -185,7 +199,7 @@ scmi_clock_domain_lookup(struct clock_info *ci, u32 clk= _id) if (clk_id >=3D ci->num_clocks) return ERR_PTR(-EINVAL); =20 - return ci->clk + clk_id; + return CLOCK_INFO(ci, clk_id); } =20 static int @@ -226,8 +240,7 @@ scmi_clock_protocol_attributes_get(const struct scmi_pr= otocol_handle *ph, =20 struct scmi_clk_ipriv { struct device *dev; - u32 clk_id; - struct scmi_clock_info *clk; + struct scmi_clock_desc *clkd; }; =20 static void iter_clk_possible_parents_prepare_message(void *message, unsig= ned int desc_index, @@ -236,7 +249,7 @@ static void iter_clk_possible_parents_prepare_message(v= oid *message, unsigned in struct scmi_msg_clock_possible_parents *msg =3D message; const struct scmi_clk_ipriv *p =3D priv; =20 - msg->id =3D cpu_to_le32(p->clk_id); + msg->id =3D cpu_to_le32(p->clkd->id); /* Set the number of OPPs to be skipped/already read */ msg->skip_parents =3D cpu_to_le32(desc_index); } @@ -246,7 +259,6 @@ static int iter_clk_possible_parents_update_state(struc= t scmi_iterator_state *st { const struct scmi_msg_resp_clock_possible_parents *r =3D response; struct scmi_clk_ipriv *p =3D priv; - struct device *dev =3D ((struct scmi_clk_ipriv *)p)->dev; u32 flags; =20 flags =3D le32_to_cpu(r->num_parent_flags); @@ -258,12 +270,13 @@ static int iter_clk_possible_parents_update_state(str= uct scmi_iterator_state *st * assume it's returned+remaining on first call. */ if (!st->max_resources) { - p->clk->num_parents =3D st->num_returned + st->num_remaining; - p->clk->parents =3D devm_kcalloc(dev, p->clk->num_parents, - sizeof(*p->clk->parents), - GFP_KERNEL); - if (!p->clk->parents) { - p->clk->num_parents =3D 0; + p->clkd->info.num_parents =3D st->num_returned + st->num_remaining; + p->clkd->info.parents =3D devm_kcalloc(p->dev, + p->clkd->info.num_parents, + sizeof(*p->clkd->info.parents), + GFP_KERNEL); + if (!p->clkd->info.parents) { + p->clkd->info.num_parents =3D 0; return -ENOMEM; } st->max_resources =3D st->num_returned + st->num_remaining; @@ -280,29 +293,27 @@ static int iter_clk_possible_parents_process_response= (const struct scmi_protocol const struct scmi_msg_resp_clock_possible_parents *r =3D response; struct scmi_clk_ipriv *p =3D priv; =20 - u32 *parent =3D &p->clk->parents[st->desc_index + st->loop_idx]; + u32 *parent =3D &p->clkd->info.parents[st->desc_index + st->loop_idx]; =20 *parent =3D le32_to_cpu(r->possible_parents[st->loop_idx]); =20 return 0; } =20 -static int scmi_clock_possible_parents(const struct scmi_protocol_handle *= ph, u32 clk_id, - struct scmi_clock_info *clk) +static int scmi_clock_possible_parents(const struct scmi_protocol_handle *= ph, + u32 clk_id, struct clock_info *cinfo) { struct scmi_iterator_ops ops =3D { .prepare_message =3D iter_clk_possible_parents_prepare_message, .update_state =3D iter_clk_possible_parents_update_state, .process_response =3D iter_clk_possible_parents_process_response, }; - + struct scmi_clock_desc *clkd =3D &cinfo->clkds[clk_id]; struct scmi_clk_ipriv ppriv =3D { - .clk_id =3D clk_id, - .clk =3D clk, + .clkd =3D clkd, .dev =3D ph->dev, }; void *iter; - int ret; =20 iter =3D ph->hops->iter_response_init(ph, &ops, 0, CLOCK_POSSIBLE_PARENTS_GET, @@ -311,9 +322,7 @@ static int scmi_clock_possible_parents(const struct scm= i_protocol_handle *ph, u3 if (IS_ERR(iter)) return PTR_ERR(iter); =20 - ret =3D ph->hops->iter_response_run(iter); - - return ret; + return ph->hops->iter_response_run(iter); } =20 static int @@ -352,7 +361,7 @@ static int scmi_clock_attributes_get(const struct scmi_= protocol_handle *ph, u32 attributes; struct scmi_xfer *t; struct scmi_msg_resp_clock_attributes *attr; - struct scmi_clock_info *clk =3D cinfo->clk + clk_id; + struct scmi_clock_info *clk =3D CLOCK_INFO(cinfo, clk_id); =20 ret =3D ph->xops->xfer_get_init(ph, CLOCK_ATTRIBUTES, sizeof(clk_id), sizeof(*attr), &t); @@ -394,7 +403,7 @@ static int scmi_clock_attributes_get(const struct scmi_= protocol_handle *ph, clk->rate_change_requested_notifications =3D true; if (PROTOCOL_REV_MAJOR(ph->version) >=3D 0x3) { if (SUPPORTS_PARENT_CLOCK(attributes)) - scmi_clock_possible_parents(ph, clk_id, clk); + scmi_clock_possible_parents(ph, clk_id, cinfo); if (SUPPORTS_GET_PERMISSIONS(attributes)) scmi_clock_get_permissions(ph, clk_id, clk); if (SUPPORTS_EXTENDED_CONFIG(attributes)) @@ -424,7 +433,7 @@ static void iter_clk_describe_prepare_message(void *mes= sage, struct scmi_msg_clock_describe_rates *msg =3D message; const struct scmi_clk_ipriv *p =3D priv; =20 - msg->id =3D cpu_to_le32(p->clk_id); + msg->id =3D cpu_to_le32(p->clkd->id); /* Set the number of rates to be skipped/already read */ msg->rate_index =3D cpu_to_le32(desc_index); } @@ -457,14 +466,14 @@ iter_clk_describe_update_state(struct scmi_iterator_s= tate *st, flags =3D le32_to_cpu(r->num_rates_flags); st->num_remaining =3D NUM_REMAINING(flags); st->num_returned =3D NUM_RETURNED(flags); - p->clk->rate_discrete =3D RATE_DISCRETE(flags); + p->clkd->rate_discrete =3D RATE_DISCRETE(flags); =20 /* Warn about out of spec replies ... */ - if (!p->clk->rate_discrete && + if (!p->clkd->rate_discrete && (st->num_returned !=3D 3 || st->num_remaining !=3D 0)) { dev_warn(p->dev, "Out-of-spec CLOCK_DESCRIBE_RATES reply for %s - returned:%d remaining= :%d rx_len:%zd\n", - p->clk->name, st->num_returned, st->num_remaining, + p->clkd->info.name, st->num_returned, st->num_remaining, st->rx_len); =20 SCMI_QUIRK(clock_rates_triplet_out_of_spec, @@ -479,38 +488,19 @@ iter_clk_describe_process_response(const struct scmi_= protocol_handle *ph, const void *response, struct scmi_iterator_state *st, void *priv) { - int ret =3D 0; struct scmi_clk_ipriv *p =3D priv; const struct scmi_msg_resp_clock_describe_rates *r =3D response; =20 - if (!p->clk->rate_discrete) { - switch (st->desc_index + st->loop_idx) { - case 0: - p->clk->range.min_rate =3D RATE_TO_U64(r->rate[0]); - break; - case 1: - p->clk->range.max_rate =3D RATE_TO_U64(r->rate[1]); - break; - case 2: - p->clk->range.step_size =3D RATE_TO_U64(r->rate[2]); - break; - default: - ret =3D -EINVAL; - break; - } - } else { - u64 *rate =3D &p->clk->list.rates[st->desc_index + st->loop_idx]; + p->clkd->rates[st->desc_index + st->loop_idx] =3D + RATE_TO_U64(r->rate[st->loop_idx]); + p->clkd->num_rates++; =20 - *rate =3D RATE_TO_U64(r->rate[st->loop_idx]); - p->clk->list.num_rates++; - } - - return ret; + return 0; } =20 static int scmi_clock_describe_rates_get(const struct scmi_protocol_handle *ph, u32 c= lk_id, - struct scmi_clock_info *clk) + struct clock_info *cinfo) { int ret; void *iter; @@ -519,9 +509,9 @@ scmi_clock_describe_rates_get(const struct scmi_protoco= l_handle *ph, u32 clk_id, .update_state =3D iter_clk_describe_update_state, .process_response =3D iter_clk_describe_process_response, }; + struct scmi_clock_desc *clkd =3D &cinfo->clkds[clk_id]; struct scmi_clk_ipriv cpriv =3D { - .clk_id =3D clk_id, - .clk =3D clk, + .clkd =3D clkd, .dev =3D ph->dev, }; =20 @@ -536,16 +526,23 @@ scmi_clock_describe_rates_get(const struct scmi_proto= col_handle *ph, u32 clk_id, if (ret) return ret; =20 - if (!clk->rate_discrete) { + /* empty set ? */ + if (!clkd->num_rates) + return 0; + + if (!clkd->rate_discrete) { + clkd->info.max_rate =3D clkd->rates[RATE_MAX]; dev_dbg(ph->dev, "Min %llu Max %llu Step %llu Hz\n", - clk->range.min_rate, clk->range.max_rate, - clk->range.step_size); - } else if (clk->list.num_rates) { - sort(clk->list.rates, clk->list.num_rates, - sizeof(clk->list.rates[0]), rate_cmp_func, NULL); + clkd->rates[RATE_MIN], clkd->rates[RATE_MAX], + clkd->rates[RATE_STEP]); + } else { + sort(clkd->rates, clkd->num_rates, + sizeof(clkd->rates[0]), rate_cmp_func, NULL); + clkd->info.max_rate =3D clkd->rates[clkd->num_rates - 1]; } + clkd->info.min_rate =3D clkd->rates[RATE_MIN]; =20 - return ret; + return 0; } =20 static int @@ -630,6 +627,7 @@ static int scmi_clock_determine_rate(const struct scmi_= protocol_handle *ph, { u64 fmin, fmax, ftmp; struct scmi_clock_info *clk; + struct scmi_clock_desc *clkd; struct clock_info *ci =3D ph->get_priv(ph); =20 if (!rate) @@ -639,15 +637,17 @@ static int scmi_clock_determine_rate(const struct scm= i_protocol_handle *ph, if (IS_ERR(clk)) return PTR_ERR(clk); =20 + clkd =3D to_desc(clk); + /* * If we can't figure out what rate it will be, so just return the * rate back to the caller. */ - if (clk->rate_discrete) + if (clkd->rate_discrete) return 0; =20 - fmin =3D clk->range.min_rate; - fmax =3D clk->range.max_rate; + fmin =3D clk->min_rate; + fmax =3D clk->max_rate; if (*rate <=3D fmin) { *rate =3D fmin; return 0; @@ -657,10 +657,10 @@ static int scmi_clock_determine_rate(const struct scm= i_protocol_handle *ph, } =20 ftmp =3D *rate - fmin; - ftmp +=3D clk->range.step_size - 1; /* to round up */ - ftmp =3D div64_ul(ftmp, clk->range.step_size); + ftmp +=3D clkd->rates[RATE_STEP] - 1; /* to round up */ + ftmp =3D div64_ul(ftmp, clkd->rates[RATE_STEP]); =20 - *rate =3D ftmp * clk->range.step_size + fmin; + *rate =3D ftmp * clkd->rates[RATE_STEP] + fmin; =20 return 0; } @@ -1122,17 +1122,16 @@ static int scmi_clock_protocol_init(const struct sc= mi_protocol_handle *ph) if (ret) return ret; =20 - cinfo->clk =3D devm_kcalloc(ph->dev, cinfo->num_clocks, - sizeof(*cinfo->clk), GFP_KERNEL); - if (!cinfo->clk) + cinfo->clkds =3D devm_kcalloc(ph->dev, cinfo->num_clocks, + sizeof(*cinfo->clkds), GFP_KERNEL); + if (!cinfo->clkds) return -ENOMEM; =20 for (clkid =3D 0; clkid < cinfo->num_clocks; clkid++) { - struct scmi_clock_info *clk =3D cinfo->clk + clkid; - + cinfo->clkds[clkid].id =3D clkid; ret =3D scmi_clock_attributes_get(ph, clkid, cinfo); if (!ret) - scmi_clock_describe_rates_get(ph, clkid, clk); + scmi_clock_describe_rates_get(ph, clkid, cinfo); } =20 if (PROTOCOL_REV_MAJOR(ph->version) >=3D 0x3) { diff --git a/include/linux/scmi_protocol.h b/include/linux/scmi_protocol.h index 28579c145045..7283302b0c85 100644 --- a/include/linux/scmi_protocol.h +++ b/include/linux/scmi_protocol.h @@ -51,6 +51,8 @@ struct scmi_clock_info { bool rate_ctrl_forbidden; bool parent_ctrl_forbidden; bool extended_config; + u64 min_rate; + u64 max_rate; union { struct { int num_rates; --=20 2.53.0 From nobody Wed Jun 17 01:35:13 2026 Received: from foss.arm.com (foss.arm.com [217.140.110.172]) by smtp.subspace.kernel.org (Postfix) with ESMTP id 7A83B3148A8; Tue, 28 Apr 2026 20:16:48 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=217.140.110.172 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407410; cv=none; b=WOPBzUZjJ6Pcq7a+BU1/8qH+YzLFf168NaPXKwJ4NiJAXy8WXxUKhh8l/xy5tEgRqJdmaQEpvGFxFf2NCIZrn/Vi0mScEAvshg5dVbniKsZl+/iu4mI/GyV7kFLRIjAT54T7dI09VowheU7JkWsi9Oan+vQ413clasL0lakWuBY= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407410; c=relaxed/simple; bh=AxDBdwk/l4DP4oCMpuyPHG7biswl244Z7Wb0hlRCNKM=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=oCvucKWAFoIfMT3WwwtZqy98TqcUQYl6/JQ1eE96Xw8YzHMEVgE48XIrdeaVOgRil26uu1A+xbzb4TVfbjTzuDjnGB0npGELEQbccEAT9rekdVv0Vf77i0Z0r55Xv+DPL84d7xt60OX9DOa+kJ9YXIoANzvhmjHiJ42AxhDNLpc= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com; spf=pass smtp.mailfrom=arm.com; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b=M2A31r0K; arc=none smtp.client-ip=217.140.110.172 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=arm.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b="M2A31r0K" 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 642DF3295; Tue, 28 Apr 2026 13:16:42 -0700 (PDT) Received: from pluto.fritz.box (usa-sjc-mx-foss1.foss.arm.com [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 7DBB53F763; Tue, 28 Apr 2026 13:16:44 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=simple/simple; d=arm.com; s=foss; t=1777407407; bh=AxDBdwk/l4DP4oCMpuyPHG7biswl244Z7Wb0hlRCNKM=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=M2A31r0Kaq8GNq9yXH8N4fFR25LcJGqKWN1DSOluFfiFblJk7ZVNWym76fXAc4fr8 wtqmPRO0QdvobTJeYwTV1ORk/GoWYqby8VZ+UZ+0OpBsYEkFNSgZWCvGtGeB/Ly5Y3 3QNcpvs2P/PXI4Y2Hg+1L8nY358RPM+0RL/rpuRo= From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org, arm-scmi@vger.kernel.org, linux-clk@vger.kernel.org, linux-renesas-soc@vger.kernel.org Cc: sudeep.holla@arm.com, philip.radford@arm.com, james.quinlan@broadcom.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, etienne.carriere@foss.st.com, peng.fan@oss.nxp.com, michal.simek@amd.com, geert+renesas@glider.be, kuninori.morimoto.gx@renesas.com, marek.vasut+renesas@gmail.com, Cristian Marussi , Michael Turquette , Stephen Boyd , Peng Fan Subject: [PATCH v3 05/15] clk: scmi: Use new simplified per-clock rate properties Date: Tue, 28 Apr 2026 21:15:12 +0100 Message-ID: <20260428201522.903875-6-cristian.marussi@arm.com> X-Mailer: git-send-email 2.53.0 In-Reply-To: <20260428201522.903875-1-cristian.marussi@arm.com> References: <20260428201522.903875-1-cristian.marussi@arm.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" Use the new min_rate and max_rate unified properties that provide the proper values without having to consider the clock type. Cc: Michael Turquette Cc: Stephen Boyd Cc: linux-clk@vger.kernel.org Reviewed-by: Peng Fan Signed-off-by: Cristian Marussi Tested-by: Florian Fainelli --- v1 --> v2 - Collected Peng Reviewed-by tag --- drivers/clk/clk-scmi.c | 17 ++--------------- 1 file changed, 2 insertions(+), 15 deletions(-) diff --git a/drivers/clk/clk-scmi.c b/drivers/clk/clk-scmi.c index c223e4ef1dd1..7c562559ad8b 100644 --- a/drivers/clk/clk-scmi.c +++ b/drivers/clk/clk-scmi.c @@ -202,7 +202,6 @@ 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; =20 struct clk_init_data init =3D { .flags =3D CLK_GET_RATE_NOCACHE, @@ -217,20 +216,8 @@ static int scmi_clk_ops_init(struct device *dev, struc= t scmi_clk *sclk, if (ret) return ret; =20 - if (sclk->info->rate_discrete) { - int num_rates =3D sclk->info->list.num_rates; - - if (num_rates <=3D 0) - return -EINVAL; - - min_rate =3D sclk->info->list.rates[0]; - max_rate =3D sclk->info->list.rates[num_rates - 1]; - } else { - min_rate =3D sclk->info->range.min_rate; - max_rate =3D sclk->info->range.max_rate; - } - - clk_hw_set_rate_range(&sclk->hw, min_rate, max_rate); + clk_hw_set_rate_range(&sclk->hw, sclk->info->min_rate, + sclk->info->max_rate); return ret; } =20 --=20 2.53.0 From nobody Wed Jun 17 01:35:13 2026 Received: from foss.arm.com (foss.arm.com [217.140.110.172]) by smtp.subspace.kernel.org (Postfix) with ESMTP id C02F8318EE6; Tue, 28 Apr 2026 20:16:51 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=217.140.110.172 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407412; cv=none; b=YgcdEgLk1bv2MMQaRvp5glYLLiPEy/DT7/rWcc7mxBHz6tzAZvHn0wUsRS8MlNLCwbX66hQJeKQdnRrYcNXWVPZeWHX7cdLh3UM2t+674QVlnO0s6arX516pPFqcsgc7wZUmBZdRaQx8Lpc64+Cy73rOoR7a5vq9B2tzA90bCjo= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407412; c=relaxed/simple; bh=Jx+iLBHfzCZCNu0Rbo9kQcSH7PClpwB4Q84bljdtVgQ=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=FaiHGcjojyM74LPHzGw3soioTV7YYWH7p5Fv8aP8/prSLso2jDkdZvhT52U1MD5c2PatEABhKoy+5pfxFg7YODsBG3cX5j62VCy83zwH7JsqKYdff/cWAdGfAs6xYFytdVHz/9M0chvW1AVi+iO2g/9Kg0YwDCUXvLap34LzCyg= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com; spf=pass smtp.mailfrom=arm.com; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b=sr0/0rj5; arc=none smtp.client-ip=217.140.110.172 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=arm.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b="sr0/0rj5" 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 9C90E3297; Tue, 28 Apr 2026 13:16:45 -0700 (PDT) Received: from pluto.fritz.box (usa-sjc-mx-foss1.foss.arm.com [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 324CD3F763; Tue, 28 Apr 2026 13:16:48 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=simple/simple; d=arm.com; s=foss; t=1777407411; bh=Jx+iLBHfzCZCNu0Rbo9kQcSH7PClpwB4Q84bljdtVgQ=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=sr0/0rj5P8vzwkIIc0/cpwv1h5ZJ9lneWh5bUsnTMKh670rVMXPYa01dNXg2q5TKq /cpYwe9MsfAPSFDOrnIvNWdSZPiSETE10P1++Q2VCypLXHF4N8PHyMHDJMmZOzwhZC 3LBrU2qq3dptQPMJEkEODWjL59PPy9F2fsFnj/A4= From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org, arm-scmi@vger.kernel.org, linux-clk@vger.kernel.org, linux-renesas-soc@vger.kernel.org Cc: sudeep.holla@arm.com, philip.radford@arm.com, james.quinlan@broadcom.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, etienne.carriere@foss.st.com, peng.fan@oss.nxp.com, michal.simek@amd.com, geert+renesas@glider.be, kuninori.morimoto.gx@renesas.com, marek.vasut+renesas@gmail.com, Cristian Marussi , Peng Fan Subject: [PATCH v3 06/15] firmware: arm_scmi: Drop unused clock rate interfaces Date: Tue, 28 Apr 2026 21:15:13 +0100 Message-ID: <20260428201522.903875-7-cristian.marussi@arm.com> X-Mailer: git-send-email 2.53.0 In-Reply-To: <20260428201522.903875-1-cristian.marussi@arm.com> References: <20260428201522.903875-1-cristian.marussi@arm.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" Only the unified interface exposing min_rate/max_rate is now used. Reviewed-by: Peng Fan Signed-off-by: Cristian Marussi Tested-by: Florian Fainelli --- v1 --> v2 - Collected Peng Reviewed-by tag --- include/linux/scmi_protocol.h | 11 ----------- 1 file changed, 11 deletions(-) diff --git a/include/linux/scmi_protocol.h b/include/linux/scmi_protocol.h index 7283302b0c85..d97b4e734744 100644 --- a/include/linux/scmi_protocol.h +++ b/include/linux/scmi_protocol.h @@ -53,17 +53,6 @@ struct scmi_clock_info { bool extended_config; u64 min_rate; u64 max_rate; - union { - struct { - int num_rates; - u64 rates[SCMI_MAX_NUM_RATES]; - } list; - struct { - u64 min_rate; - u64 max_rate; - u64 step_size; - } range; - }; int num_parents; u32 *parents; }; --=20 2.53.0 From nobody Wed Jun 17 01:35:13 2026 Received: from foss.arm.com (foss.arm.com [217.140.110.172]) by smtp.subspace.kernel.org (Postfix) with ESMTP id F314B3191D0; Tue, 28 Apr 2026 20:16:54 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=217.140.110.172 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407416; cv=none; b=BRMgo0cUW8Veo01dxpuZJJ6lz2NKOzipXhH/G8xlJ41DpgXcQFrhZI5LFK2Q9N6+jGMn4LvrwKakv9+44ymxWvIeaOz4ZqEZViIFrVg8QQc2mtHIc3FwwFrXOliq4pGGr6n0de2DJ/bnumDBm7mdQEOU0fSmxEKSrqE1CLG67gg= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407416; c=relaxed/simple; bh=yjQhykXQOdB+c522lN4y/AmjYIvZxdLbJ/Nwp3R+Ax4=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=JyPeXHpZwaUne1d0bCZf4RiQ8XLMc02AtOu0N63zAckCMWXK/6Zr1+sXIQkpquu4gf2HUtEtA8KCXPJgV+ovDHwszFVOm1mE0mEYyaBBDpTFeXUQgQaFOGz8IqJ8tVsGm9coYGOAFUdXdEYQ2OvL0qDeI4R21Rhn3xVRdqo2yyo= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com; spf=pass smtp.mailfrom=arm.com; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b=MnYKtfFr; arc=none smtp.client-ip=217.140.110.172 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=arm.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b="MnYKtfFr" 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 DAD821C0A; Tue, 28 Apr 2026 13:16:48 -0700 (PDT) Received: from pluto.fritz.box (usa-sjc-mx-foss1.foss.arm.com [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 6F1953F763; Tue, 28 Apr 2026 13:16:51 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=simple/simple; d=arm.com; s=foss; t=1777407414; bh=yjQhykXQOdB+c522lN4y/AmjYIvZxdLbJ/Nwp3R+Ax4=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=MnYKtfFrvIFEdI9OR+IGgz45xJuLl3pLjdZheCtsDs8qOMFmpgo+LtwJ6S2C4cFQF G60+CDXR6JTXqlhrGrWEkGDrrBg9srdbo7WU3oOeRj08qw3+o4BuvwQX+X2poQfPp5 GVEx0XGvld7DVk0XJE72g/T7OpzW5l+vUUuhW4E0= From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org, arm-scmi@vger.kernel.org, linux-clk@vger.kernel.org, linux-renesas-soc@vger.kernel.org Cc: sudeep.holla@arm.com, philip.radford@arm.com, james.quinlan@broadcom.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, etienne.carriere@foss.st.com, peng.fan@oss.nxp.com, michal.simek@amd.com, geert+renesas@glider.be, kuninori.morimoto.gx@renesas.com, marek.vasut+renesas@gmail.com, Cristian Marussi , Peng Fan Subject: [PATCH v3 07/15] firmware: arm_scmi: Make clock rates allocation dynamic Date: Tue, 28 Apr 2026 21:15:14 +0100 Message-ID: <20260428201522.903875-8-cristian.marussi@arm.com> X-Mailer: git-send-email 2.53.0 In-Reply-To: <20260428201522.903875-1-cristian.marussi@arm.com> References: <20260428201522.903875-1-cristian.marussi@arm.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" Leveraging SCMI Clock protocol dynamic discovery capabilities, move away from the static per-clock rates allocation model in favour of a dynamic runtime allocation based on effectively discovered resources. No functional change. Reviewed-by: Peng Fan Signed-off-by: Cristian Marussi Tested-by: Florian Fainelli --- v2 --> v3 - collected Review-by tags --- drivers/firmware/arm_scmi/clock.c | 19 ++++++++++++++++--- include/linux/scmi_protocol.h | 1 - 2 files changed, 16 insertions(+), 4 deletions(-) diff --git a/drivers/firmware/arm_scmi/clock.c b/drivers/firmware/arm_scmi/= clock.c index 467b13a3a18f..c9b62edce4fd 100644 --- a/drivers/firmware/arm_scmi/clock.c +++ b/drivers/firmware/arm_scmi/clock.c @@ -161,7 +161,7 @@ struct scmi_clock_desc { u32 id; bool rate_discrete; unsigned int num_rates; - u64 rates[SCMI_MAX_NUM_RATES]; + u64 *rates; #define RATE_MIN 0 #define RATE_MAX 1 #define RATE_STEP 2 @@ -480,6 +480,18 @@ iter_clk_describe_update_state(struct scmi_iterator_st= ate *st, QUIRK_OUT_OF_SPEC_TRIPLET); } =20 + if (!st->max_resources) { + int num_rates =3D st->num_returned + st->num_remaining; + + p->clkd->rates =3D devm_kcalloc(p->dev, num_rates, + sizeof(*p->clkd->rates), GFP_KERNEL); + if (!p->clkd->rates) + return -ENOMEM; + + /* max_resources is used by the iterators to control bounds */ + st->max_resources =3D st->num_returned + st->num_remaining; + } + return 0; } =20 @@ -493,6 +505,8 @@ iter_clk_describe_process_response(const struct scmi_pr= otocol_handle *ph, =20 p->clkd->rates[st->desc_index + st->loop_idx] =3D RATE_TO_U64(r->rate[st->loop_idx]); + + /* Count only effectively discovered rates */ p->clkd->num_rates++; =20 return 0; @@ -515,8 +529,7 @@ scmi_clock_describe_rates_get(const struct scmi_protoco= l_handle *ph, u32 clk_id, .dev =3D ph->dev, }; =20 - iter =3D ph->hops->iter_response_init(ph, &ops, SCMI_MAX_NUM_RATES, - CLOCK_DESCRIBE_RATES, + iter =3D ph->hops->iter_response_init(ph, &ops, 0, CLOCK_DESCRIBE_RATES, sizeof(struct scmi_msg_clock_describe_rates), &cpriv); if (IS_ERR(iter)) diff --git a/include/linux/scmi_protocol.h b/include/linux/scmi_protocol.h index d97b4e734744..5552ac04c820 100644 --- a/include/linux/scmi_protocol.h +++ b/include/linux/scmi_protocol.h @@ -15,7 +15,6 @@ =20 #define SCMI_MAX_STR_SIZE 64 #define SCMI_SHORT_NAME_MAX_SIZE 16 -#define SCMI_MAX_NUM_RATES 16 =20 /** * struct scmi_revision_info - version information structure --=20 2.53.0 From nobody Wed Jun 17 01:35:13 2026 Received: from foss.arm.com (foss.arm.com [217.140.110.172]) by smtp.subspace.kernel.org (Postfix) with ESMTP id 5645231AA8F; Tue, 28 Apr 2026 20:16:58 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=217.140.110.172 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407419; cv=none; b=TppEL1RcChaU4hQUXAdeWrpCPX4e6X6iLWjutPdsAorGnGXnyEs46gPMTu2n2uKf3Om/k3xbXFBD1Yqd1gBKL1bAM+InJ2I7LxBXZODSiiM65kA0UkJ4QkF9fZqL1+izrMaC2Zi9A5FWlxg/3DK38Py/CHjWqVG9jXFOLe4/wk0= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407419; c=relaxed/simple; bh=FCP9MWDXBkmpmaTgWI8hodUMzwfIaYuwHBhh3J2kcKA=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=b2z5+dXbFf1KCX/VRnXzRyP6R0EI39IH0rE+99VjGhhDH/1oqlaHvgpEY9zCDWgEiO48HneTy0oGLZKzKyggWzJvG0iHfkj4OMNjpMnANYwIcWGO+ffVXUTHEUUhSm2sJlTq6x8F4dyPWK1qL9J6s2yGjvH9E+0HAxBGacNjcbU= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com; spf=pass smtp.mailfrom=arm.com; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b=dpe6DzK+; arc=none smtp.client-ip=217.140.110.172 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=arm.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b="dpe6DzK+" 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 41B531C01; Tue, 28 Apr 2026 13:16:52 -0700 (PDT) Received: from pluto.fritz.box (usa-sjc-mx-foss1.foss.arm.com [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id AF53B3F763; Tue, 28 Apr 2026 13:16:54 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=simple/simple; d=arm.com; s=foss; t=1777407417; bh=FCP9MWDXBkmpmaTgWI8hodUMzwfIaYuwHBhh3J2kcKA=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=dpe6DzK+9m+K4NwKt0FoWDDVcTtvjQx2HvJxkemaZkUvsIQJKuYWheQ4vdWRez6Yp cGOfYFbzoVxSHMCqcmUH4hwdRfeUSoDeL0ll58r2/4zFHqUh8PaIseJTS2wZXP7WC+ RVEenmDDDlLc1YP58my65VERLEe0b0BwuVgwvHI8= From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org, arm-scmi@vger.kernel.org, linux-clk@vger.kernel.org, linux-renesas-soc@vger.kernel.org Cc: sudeep.holla@arm.com, philip.radford@arm.com, james.quinlan@broadcom.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, etienne.carriere@foss.st.com, peng.fan@oss.nxp.com, michal.simek@amd.com, geert+renesas@glider.be, kuninori.morimoto.gx@renesas.com, marek.vasut+renesas@gmail.com, Cristian Marussi , Peng Fan Subject: [PATCH v3 08/15] firmware: arm_scmi: Harden clock parents discovery Date: Tue, 28 Apr 2026 21:15:15 +0100 Message-ID: <20260428201522.903875-9-cristian.marussi@arm.com> X-Mailer: git-send-email 2.53.0 In-Reply-To: <20260428201522.903875-1-cristian.marussi@arm.com> References: <20260428201522.903875-1-cristian.marussi@arm.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" Fix clock parents enumeration to account only for effectively discovered parents during enumeration, avoiding to trust the total number of parents declared upfront by the platform. Reviewed-by: Peng Fan Signed-off-by: Cristian Marussi Tested-by: Florian Fainelli --- v2 --> v3 - collected Reviewed-by tags --- drivers/firmware/arm_scmi/clock.c | 18 ++++++++++-------- 1 file changed, 10 insertions(+), 8 deletions(-) diff --git a/drivers/firmware/arm_scmi/clock.c b/drivers/firmware/arm_scmi/= clock.c index c9b62edce4fd..d07cfef243fd 100644 --- a/drivers/firmware/arm_scmi/clock.c +++ b/drivers/firmware/arm_scmi/clock.c @@ -270,15 +270,15 @@ static int iter_clk_possible_parents_update_state(str= uct scmi_iterator_state *st * assume it's returned+remaining on first call. */ if (!st->max_resources) { - p->clkd->info.num_parents =3D st->num_returned + st->num_remaining; - p->clkd->info.parents =3D devm_kcalloc(p->dev, - p->clkd->info.num_parents, + int num_parents =3D st->num_returned + st->num_remaining; + + p->clkd->info.parents =3D devm_kcalloc(p->dev, num_parents, sizeof(*p->clkd->info.parents), GFP_KERNEL); - if (!p->clkd->info.parents) { - p->clkd->info.num_parents =3D 0; + if (!p->clkd->info.parents) return -ENOMEM; - } + + /* max_resources is used by the iterators to control bounds */ st->max_resources =3D st->num_returned + st->num_remaining; } =20 @@ -293,9 +293,11 @@ static int iter_clk_possible_parents_process_response(= const struct scmi_protocol const struct scmi_msg_resp_clock_possible_parents *r =3D response; struct scmi_clk_ipriv *p =3D priv; =20 - u32 *parent =3D &p->clkd->info.parents[st->desc_index + st->loop_idx]; + p->clkd->info.parents[st->desc_index + st->loop_idx] =3D + le32_to_cpu(r->possible_parents[st->loop_idx]); =20 - *parent =3D le32_to_cpu(r->possible_parents[st->loop_idx]); + /* Count only effectively discovered parents */ + p->clkd->info.num_parents++; =20 return 0; } --=20 2.53.0 From nobody Wed Jun 17 01:35:13 2026 Received: from foss.arm.com (foss.arm.com [217.140.110.172]) by smtp.subspace.kernel.org (Postfix) with ESMTP id B6F1C31E824; Tue, 28 Apr 2026 20:17:01 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=217.140.110.172 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407423; cv=none; b=fFh3G0urWh2Aw1rTe+oeRayC4v0lrtNtdk5uPVqfErU1Gs29HsIl5FmdrBC0QmJtwKkK7diMG1pE/JvnsWbE4B5h7vJXSMjNSX+u6emVsstXGc+5zElj44MjTWuNDPwd6ort8ecSkvpOzaonaWcpj6YTb+jntsbstLg8c4tDYxY= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407423; c=relaxed/simple; bh=ydGSxVs7029/nGMXlye2/Mws9V6mzCtDA5RxCjGimS4=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=JtIpuDal4PlvkYgkCa1isIjq74ebz5HSIn+eKVux3GlaYQUbklCY65TzFh+IAiXJ6GBg6HzDGt/rlC4JP1zQc5mRJsG3piC/v/kePFLZbAaxklXXBaEOGxGipMKYyZ9WwPLZxM7EblzqjTs5LHQkfKDRek1jwnFj1sZiW5SBSCw= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com; spf=pass smtp.mailfrom=arm.com; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b=a3Qh79Fc; arc=none smtp.client-ip=217.140.110.172 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=arm.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b="a3Qh79Fc" 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 943063295; Tue, 28 Apr 2026 13:16:55 -0700 (PDT) Received: from pluto.fritz.box (usa-sjc-mx-foss1.foss.arm.com [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 16B9E3F763; Tue, 28 Apr 2026 13:16:57 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=simple/simple; d=arm.com; s=foss; t=1777407421; bh=ydGSxVs7029/nGMXlye2/Mws9V6mzCtDA5RxCjGimS4=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=a3Qh79FcFLY+WZHqhFshbyqDMI0ZEI/lttWBT2xTG/3PYcQvNakAhxiqIeYjiMCTb CM9c94RV3iQrnX/hV0LEF1PLliKKXLnV1ZjnxWvTSbKpDkXNe8NW5m9UNtWwdEbQ8E wxWd71AItpmxHq0RbICj7ttjf/+389AthdIPVSYE= From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org, arm-scmi@vger.kernel.org, linux-clk@vger.kernel.org, linux-renesas-soc@vger.kernel.org Cc: sudeep.holla@arm.com, philip.radford@arm.com, james.quinlan@broadcom.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, etienne.carriere@foss.st.com, peng.fan@oss.nxp.com, michal.simek@amd.com, geert+renesas@glider.be, kuninori.morimoto.gx@renesas.com, marek.vasut+renesas@gmail.com, Cristian Marussi , Peng Fan Subject: [PATCH v3 09/15] firmware: arm_scmi: Refactor iterators internal allocation Date: Tue, 28 Apr 2026 21:15:16 +0100 Message-ID: <20260428201522.903875-10-cristian.marussi@arm.com> X-Mailer: git-send-email 2.53.0 In-Reply-To: <20260428201522.903875-1-cristian.marussi@arm.com> References: <20260428201522.903875-1-cristian.marussi@arm.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" Use cleanup handlers to manage iterator data structures. No functional change. Reviewed-by: Peng Fan Signed-off-by: Cristian Marussi Tested-by: Florian Fainelli --- v2 --> v3 - collected Reviewed tags --- drivers/firmware/arm_scmi/driver.c | 35 +++++++++++++++--------------- 1 file changed, 18 insertions(+), 17 deletions(-) diff --git a/drivers/firmware/arm_scmi/driver.c b/drivers/firmware/arm_scmi= /driver.c index f167194f7cf6..66cb64c8ed3d 100644 --- a/drivers/firmware/arm_scmi/driver.c +++ b/drivers/firmware/arm_scmi/driver.c @@ -17,6 +17,7 @@ #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt =20 #include +#include #include #include #include @@ -1789,39 +1790,41 @@ static void *scmi_iterator_init(const struct scmi_p= rotocol_handle *ph, size_t tx_size, void *priv) { int ret; - struct scmi_iterator *i; =20 - i =3D devm_kzalloc(ph->dev, sizeof(*i), GFP_KERNEL); + struct scmi_iterator *i __free(kfree) =3D kzalloc(sizeof(*i), GFP_KERNEL); if (!i) return ERR_PTR(-ENOMEM); =20 + if (!ops || !ph) + return ERR_PTR(-EINVAL); + i->ph =3D ph; i->ops =3D ops; i->priv =3D priv; =20 ret =3D ph->xops->xfer_get_init(ph, msg_id, tx_size, 0, &i->t); - if (ret) { - devm_kfree(ph->dev, i); + if (ret) return ERR_PTR(ret); - } =20 i->state.max_resources =3D max_resources; i->msg =3D i->t->tx.buf; i->resp =3D i->t->rx.buf; =20 - return i; + return no_free_ptr(i); } =20 static int scmi_iterator_run(void *iter) { - int ret =3D -EINVAL; + int ret; struct scmi_iterator_ops *iops; const struct scmi_protocol_handle *ph; struct scmi_iterator_state *st; - struct scmi_iterator *i =3D iter; =20 - if (!i || !i->ops || !i->ph) - return ret; + if (!iter) + return -EINVAL; + + /* Take ownership of the iterator */ + struct scmi_iterator *i __free(kfree) =3D iter; =20 iops =3D i->ops; ph =3D i->ph; @@ -1846,12 +1849,12 @@ static int scmi_iterator_run(void *iter) break; } =20 - for (st->loop_idx =3D 0; st->loop_idx < st->num_returned; - st->loop_idx++) { + for (st->loop_idx =3D 0; !ret && st->loop_idx < st->num_returned; + st->loop_idx++) ret =3D iops->process_response(ph, i->resp, st, i->priv); - if (ret) - goto out; - } + + if (ret) + break; =20 st->desc_index +=3D st->num_returned; ph->xops->reset_rx_to_maxsz(ph, i->t); @@ -1861,10 +1864,8 @@ static int scmi_iterator_run(void *iter) */ } while (st->num_returned && st->num_remaining); =20 -out: /* Finalize and destroy iterator */ ph->xops->xfer_put(ph, i->t); - devm_kfree(ph->dev, i); =20 return ret; } --=20 2.53.0 From nobody Wed Jun 17 01:35:13 2026 Received: from foss.arm.com (foss.arm.com [217.140.110.172]) by smtp.subspace.kernel.org (Postfix) with ESMTP id D4DCB318EE6; Tue, 28 Apr 2026 20:17:04 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=217.140.110.172 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407426; cv=none; b=jlRvpjXPlV+9d+opgINfd3HmlvqQFX2QEh464dcsFCo6yvwz8KFDdyRGnxLvDYVaooNN0VKOtO4KSQ7XzXFqTe9FWedfy40WIwDugyZzVWdiAWAa9GJwGfz98+AerG4jBfsuILRPQMki7CNRUh4xerhM+/bvDT6rRW1hoAf/wAI= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407426; c=relaxed/simple; bh=K7PZn6YSuIfgQkzQTbiCZFkzHkWlX1uWSHiLxI+Ap24=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=Kb0QSguFfg+XFH9EmvUNjHAnVGaAXOyp9RX85B7TylzXuxLDPUgctX4QpnbdvGM/9GRtjnk/JOaZJJ9g4vUijnzDEqRHSiCXbOKP0j2GZTnIMPGXatRA4ZR8SyUyHwUyAXzSxxDBhXQhWH8tdOOETFW6lprJK0ySk/iPMeAoaGc= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com; spf=pass smtp.mailfrom=arm.com; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b=oEwZIu3w; arc=none smtp.client-ip=217.140.110.172 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=arm.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b="oEwZIu3w" 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 E9D3A3296; Tue, 28 Apr 2026 13:16:58 -0700 (PDT) Received: from pluto.fritz.box (usa-sjc-mx-foss1.foss.arm.com [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 6BE303F763; Tue, 28 Apr 2026 13:17:01 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=simple/simple; d=arm.com; s=foss; t=1777407424; bh=K7PZn6YSuIfgQkzQTbiCZFkzHkWlX1uWSHiLxI+Ap24=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=oEwZIu3w6S/Fe/vvdZdjMfnQ4oQ+JYSwW2y2KJHyi9vKTrIE0MMpyf1g5jXHKhO1Z x8LlifbPhYbE6pr8TGPstQIyx0NuUkMeoSjHC1Uh1+UfL9TGbb3xbqCK95XiVMukSX RiNn83gOJePq6gy9zrt9pKtHkLLI4aiF9tONwFdk= From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org, arm-scmi@vger.kernel.org, linux-clk@vger.kernel.org, linux-renesas-soc@vger.kernel.org Cc: sudeep.holla@arm.com, philip.radford@arm.com, james.quinlan@broadcom.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, etienne.carriere@foss.st.com, peng.fan@oss.nxp.com, michal.simek@amd.com, geert+renesas@glider.be, kuninori.morimoto.gx@renesas.com, marek.vasut+renesas@gmail.com, Cristian Marussi Subject: [PATCH v3 10/15] firmware: arm_scmi: Add bound iterators support Date: Tue, 28 Apr 2026 21:15:17 +0100 Message-ID: <20260428201522.903875-11-cristian.marussi@arm.com> X-Mailer: git-send-email 2.53.0 In-Reply-To: <20260428201522.903875-1-cristian.marussi@arm.com> References: <20260428201522.903875-1-cristian.marussi@arm.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" SCMI core stack provides some common helpers to handle in a unified way multipart message replies: such iterator-helpers, when run, currently process by default the whole set of discovered resources. Introduce an alternative way to run the initialized iterator on a limited range of resources. Note that the subset of resources that can be chosen is anyway limited by the SCMI protocol specification, since you are only allowed to choose the start-index on a multi-part enumeration NOT the end-index, so that the effective number of returned items by a bound iterators depends really on platform side decisions. Suggested-by: Etienne Carriere Signed-off-by: Cristian Marussi Tested-by: Florian Fainelli --- v2 --> v3 - fixed typos in commit message --- drivers/firmware/arm_scmi/clock.c | 3 +- drivers/firmware/arm_scmi/driver.c | 58 +++++++++++++++++++-------- drivers/firmware/arm_scmi/protocols.h | 13 +++++- 3 files changed, 55 insertions(+), 19 deletions(-) diff --git a/drivers/firmware/arm_scmi/clock.c b/drivers/firmware/arm_scmi/= clock.c index d07cfef243fd..8ce889dfc87b 100644 --- a/drivers/firmware/arm_scmi/clock.c +++ b/drivers/firmware/arm_scmi/clock.c @@ -505,8 +505,7 @@ iter_clk_describe_process_response(const struct scmi_pr= otocol_handle *ph, struct scmi_clk_ipriv *p =3D priv; const struct scmi_msg_resp_clock_describe_rates *r =3D response; =20 - p->clkd->rates[st->desc_index + st->loop_idx] =3D - RATE_TO_U64(r->rate[st->loop_idx]); + p->clkd->rates[p->clkd->num_rates] =3D RATE_TO_U64(r->rate[st->loop_idx]); =20 /* Count only effectively discovered rates */ p->clkd->num_rates++; diff --git a/drivers/firmware/arm_scmi/driver.c b/drivers/firmware/arm_scmi= /driver.c index 66cb64c8ed3d..cb4865fd8af2 100644 --- a/drivers/firmware/arm_scmi/driver.c +++ b/drivers/firmware/arm_scmi/driver.c @@ -1813,48 +1813,50 @@ static void *scmi_iterator_init(const struct scmi_p= rotocol_handle *ph, return no_free_ptr(i); } =20 -static int scmi_iterator_run(void *iter) +static int __scmi_iterator_run(void *iter, unsigned int *start, unsigned i= nt *end) { int ret; struct scmi_iterator_ops *iops; const struct scmi_protocol_handle *ph; struct scmi_iterator_state *st; + struct scmi_iterator *i; =20 if (!iter) return -EINVAL; =20 - /* Take ownership of the iterator */ - struct scmi_iterator *i __free(kfree) =3D iter; - + i =3D iter; iops =3D i->ops; ph =3D i->ph; st =3D &i->state; =20 + /* Reinitialize state for next run */ + st->num_returned =3D 0; + st->num_remaining =3D 0; + st->desc_index =3D start ? *start : 0; + do { iops->prepare_message(i->msg, st->desc_index, i->priv); ret =3D ph->xops->do_xfer(ph, i->t); if (ret) - break; + return ret; =20 st->rx_len =3D i->t->rx.len; ret =3D iops->update_state(st, i->resp, i->priv); if (ret) - break; + return ret; =20 if (st->num_returned > st->max_resources - st->desc_index) { dev_err(ph->dev, "No. of resources can't exceed %d\n", st->max_resources); - ret =3D -EINVAL; - break; + return -EINVAL; } =20 - for (st->loop_idx =3D 0; !ret && st->loop_idx < st->num_returned; - st->loop_idx++) + for (st->loop_idx =3D 0; st->loop_idx < st->num_returned; st->loop_idx++= ) { ret =3D iops->process_response(ph, i->resp, st, i->priv); - - if (ret) - break; + if (ret) + return ret; + } =20 st->desc_index +=3D st->num_returned; ph->xops->reset_rx_to_maxsz(ph, i->t); @@ -1862,14 +1864,36 @@ static int scmi_iterator_run(void *iter) * check for both returned and remaining to avoid infinite * loop due to buggy firmware */ - } while (st->num_returned && st->num_remaining); + } while (st->num_returned && st->num_remaining && + (!end || (st->desc_index <=3D min(*end, st->max_resources - 1)))); =20 - /* Finalize and destroy iterator */ - ph->xops->xfer_put(ph, i->t); + return 0; +} + +static void scmi_iterator_cleanup(void *iter) +{ + struct scmi_iterator *i =3D iter; + + i->ph->xops->xfer_put(i->ph, i->t); + kfree(i); +} + +static int scmi_iterator_run(void *iter) +{ + int ret; + + ret =3D __scmi_iterator_run(iter, NULL, NULL); + scmi_iterator_cleanup(iter); =20 return ret; } =20 +static int scmi_iterator_run_bound(void *iter, unsigned int *start, + unsigned int *end) +{ + return __scmi_iterator_run(iter, start, end); +} + struct scmi_msg_get_fc_info { __le32 domain; __le32 message_id; @@ -2048,6 +2072,8 @@ static const struct scmi_proto_helpers_ops helpers_op= s =3D { .get_max_msg_size =3D scmi_common_get_max_msg_size, .iter_response_init =3D scmi_iterator_init, .iter_response_run =3D scmi_iterator_run, + .iter_response_run_bound =3D scmi_iterator_run_bound, + .iter_response_cleanup =3D scmi_iterator_cleanup, .protocol_msg_check =3D scmi_protocol_msg_check, .fastchannel_init =3D scmi_common_fastchannel_init, .fastchannel_db_ring =3D scmi_common_fastchannel_db_ring, diff --git a/drivers/firmware/arm_scmi/protocols.h b/drivers/firmware/arm_s= cmi/protocols.h index f51245aca259..e2ef604c16ef 100644 --- a/drivers/firmware/arm_scmi/protocols.h +++ b/drivers/firmware/arm_scmi/protocols.h @@ -259,7 +259,15 @@ struct scmi_fc_info { * multi-part responses using the custom operations * provided in @ops. * @iter_response_run: A common helper to trigger the run of a previously - * initialized iterator. + * initialized iterator. Note that unbound iterators are + * automatically cleaned up. + * @iter_response_run_bound: A common helper to trigger the run of a previ= ously + * initialized iterator, but only within the + * specified, optional, @start and @end resource + * indexes. Note that these bound-iterators need + * explicit cleanup via @iter_response_bound_cleanup. + * @iter_response_bound_cleanup: A common helper to finally release the it= erator + * for bound iterators. * @protocol_msg_check: A common helper to check is a specific protocol me= ssage * is supported. * @fastchannel_init: A common helper used to initialize FC descriptors by @@ -276,6 +284,9 @@ struct scmi_proto_helpers_ops { unsigned int max_resources, u8 msg_id, size_t tx_size, void *priv); int (*iter_response_run)(void *iter); + int (*iter_response_run_bound)(void *iter, + unsigned int *start, unsigned int *end); + void (*iter_response_cleanup)(void *iter); int (*protocol_msg_check)(const struct scmi_protocol_handle *ph, u32 message_id, u32 *attributes); void (*fastchannel_init)(const struct scmi_protocol_handle *ph, --=20 2.53.0 From nobody Wed Jun 17 01:35:13 2026 Received: from foss.arm.com (foss.arm.com [217.140.110.172]) by smtp.subspace.kernel.org (Postfix) with ESMTP id 7947131AA8F; Tue, 28 Apr 2026 20:17:08 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=217.140.110.172 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407430; cv=none; b=U496jHy/qwsoks6fCvRaZpDTg6chd+xJRTh1uu04TflYogPuwcRECt+UqQPhMHjy4k7mlzPVqkJLfcegs7LlBhua6xdMqpD4fcnTjQN4UsTI07WdV1QFTtr3wNlPPnFCJa0whCsAYG5m2uAH6pzsF3lhhxR9bZ+tmGOxVhhio8U= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407430; c=relaxed/simple; bh=OwrS1tuzfQVio2IobCkB91DzRSW/Wbs2qREjyQ2A8Gw=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=Q2e3jL5cnIK3p+Bsei65QuapYnXDT9NYGr/A9y4jnBJQ/cyQjx11ZVJ4u801EAMChFHerwfBR5VKuQy4U1TPSm0RLo+9wTbQrSF+pPlk3+X+n4RL88G+dZHNwGOxaedgOUhI/3p/WBoG8xc1qCN5D0Z5gV4X8ZI7sdFG26x8Qnk= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com; spf=pass smtp.mailfrom=arm.com; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b=hC7y1OJt; arc=none smtp.client-ip=217.140.110.172 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=arm.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b="hC7y1OJt" 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 3BE141C01; Tue, 28 Apr 2026 13:17:02 -0700 (PDT) Received: from pluto.fritz.box (usa-sjc-mx-foss1.foss.arm.com [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id BD3A73F763; Tue, 28 Apr 2026 13:17:04 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=simple/simple; d=arm.com; s=foss; t=1777407427; bh=OwrS1tuzfQVio2IobCkB91DzRSW/Wbs2qREjyQ2A8Gw=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=hC7y1OJtFYOyBrZ3QxB/oKhe66SRPsjFysNW3FB3RH9ix6nRQYuECZZaUpiDiPKFT ILX2W8l/AZwvC0v7bNVGWJUedNa6l2l64S4OwZXfakHw2ekX9SW9My2Tsp2ErPAsw+ qLPgszOcxsi3nP9PUWRxh11L5x3MhsKbuPLKRDZw= From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org, arm-scmi@vger.kernel.org, linux-clk@vger.kernel.org, linux-renesas-soc@vger.kernel.org Cc: sudeep.holla@arm.com, philip.radford@arm.com, james.quinlan@broadcom.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, etienne.carriere@foss.st.com, peng.fan@oss.nxp.com, michal.simek@amd.com, geert+renesas@glider.be, kuninori.morimoto.gx@renesas.com, marek.vasut+renesas@gmail.com, Cristian Marussi Subject: [PATCH v3 11/15] firmware: arm_scmi: Fix bound iterators returning too many items Date: Tue, 28 Apr 2026 21:15:18 +0100 Message-ID: <20260428201522.903875-12-cristian.marussi@arm.com> X-Mailer: git-send-email 2.53.0 In-Reply-To: <20260428201522.903875-1-cristian.marussi@arm.com> References: <20260428201522.903875-1-cristian.marussi@arm.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" From: Geert Uytterhoeven When using a bound-iterator with an upper bound, commands are sent, and responses are received, until the upper bound is reached. However, it is up to the SCMI provider implementation to decide how many rates are returned in response to a single CLOCK_DESCRIBE_RATES command. If the last response contains rates beyond the specified upper bound, they are still passed up for further processing. This may lead to buffer overflows in unprepared callsites. While the imprecise bound handling may have been intentional (it was mentioned in the commit message introducing the code), it is still confusing for users, and may cause hard to debug crashes. Fix this by strictly enforcing the upper bound. Note that this may cause an increase in the number of CLOCK_DESCRIBE_RATES commands issued, as retrieving the last rate may no longer be done inadvertentently, but require its own command. Signed-off-by: Geert Uytterhoeven [Cristian: removed Fixed tag referring the same series] Signed-off-by: Cristian Marussi Tested-by: Florian Fainelli --- drivers/firmware/arm_scmi/driver.c | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-) diff --git a/drivers/firmware/arm_scmi/driver.c b/drivers/firmware/arm_scmi= /driver.c index cb4865fd8af2..fd031a8d40df 100644 --- a/drivers/firmware/arm_scmi/driver.c +++ b/drivers/firmware/arm_scmi/driver.c @@ -1820,6 +1820,7 @@ static int __scmi_iterator_run(void *iter, unsigned i= nt *start, unsigned int *en const struct scmi_protocol_handle *ph; struct scmi_iterator_state *st; struct scmi_iterator *i; + unsigned int n; =20 if (!iter) return -EINVAL; @@ -1852,13 +1853,17 @@ static int __scmi_iterator_run(void *iter, unsigned= int *start, unsigned int *en return -EINVAL; } =20 - for (st->loop_idx =3D 0; st->loop_idx < st->num_returned; st->loop_idx++= ) { + if (end) + n =3D min(st->num_returned, *end - st->desc_index + 1); + else + n =3D st->num_returned; + for (st->loop_idx =3D 0; st->loop_idx < n; st->loop_idx++) { ret =3D iops->process_response(ph, i->resp, st, i->priv); if (ret) return ret; } =20 - st->desc_index +=3D st->num_returned; + st->desc_index +=3D n; ph->xops->reset_rx_to_maxsz(ph, i->t); /* * check for both returned and remaining to avoid infinite --=20 2.53.0 From nobody Wed Jun 17 01:35:13 2026 Received: from foss.arm.com (foss.arm.com [217.140.110.172]) by smtp.subspace.kernel.org (Postfix) with ESMTP id 3F5923264D0; Tue, 28 Apr 2026 20:17:11 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=217.140.110.172 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407433; cv=none; b=a80QDJFzSEbMFZKwMXzEnDh+VRhafeHyOpDK4NtXz39tNO27ujQKh9qn2lXpxzF4z1YuO4acoXhhLYrd9IIgWmvWkMJTop98Eo8lf4ZNxMCH8NtzNnIs6l22v8wfaO6h/dkHLNg0al4YfT9iJ+8i1vQLYcm7lN4KHsgSa+DGDGg= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407433; c=relaxed/simple; bh=6nEFcFhdP808ZVtmXdMcMA3pZOK4Wb1QnGW2QZeFifA=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=DpTMZuY5R3Aa6slzVseTfsW1AB8kpNf4EYJyVW4SMec9+ududhTMk83YauPM+Ic0ADb260bmp72GJkM63mrtcX77ypApBJsmKztzZGlQoWgUSl7zwQVQ08Kqc1Fv6tcTpeRSll/IEeuRnYoR3w1wLWix4RUw7WqllQplUDYH8C0= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com; spf=pass smtp.mailfrom=arm.com; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b=ar26Xeqf; arc=none smtp.client-ip=217.140.110.172 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=arm.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b="ar26Xeqf" 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 546781C0A; Tue, 28 Apr 2026 13:17:05 -0700 (PDT) Received: from pluto.fritz.box (usa-sjc-mx-foss1.foss.arm.com [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 10D3E3F763; Tue, 28 Apr 2026 13:17:07 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=simple/simple; d=arm.com; s=foss; t=1777407430; bh=6nEFcFhdP808ZVtmXdMcMA3pZOK4Wb1QnGW2QZeFifA=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=ar26XeqfQe/6RVcliRdSrSnj7NmY5hVXRpqHsifVOXS1jPW9CABFa6omEunngt+Nq JNq0FAv/a97S3Ggrp7XEHuJKtGjsqoreSJ9tsiFIUTiZ5sIhxya4ZHSCsMqZ9Lecbk g/yv+7IQWsLIec9WncInr/I/ZcbY1+8Mctb5fYaE= From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org, arm-scmi@vger.kernel.org, linux-clk@vger.kernel.org, linux-renesas-soc@vger.kernel.org Cc: sudeep.holla@arm.com, philip.radford@arm.com, james.quinlan@broadcom.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, etienne.carriere@foss.st.com, peng.fan@oss.nxp.com, michal.simek@amd.com, geert+renesas@glider.be, kuninori.morimoto.gx@renesas.com, marek.vasut+renesas@gmail.com, Cristian Marussi Subject: [PATCH v3 12/15] firmware: arm_scmi: Use proper iter_response_bound_cleanup() name Date: Tue, 28 Apr 2026 21:15:19 +0100 Message-ID: <20260428201522.903875-13-cristian.marussi@arm.com> X-Mailer: git-send-email 2.53.0 In-Reply-To: <20260428201522.903875-1-cristian.marussi@arm.com> References: <20260428201522.903875-1-cristian.marussi@arm.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" From: Geert Uytterhoeven The documentation speaks of the "iter_response_bound_cleanup()" protocol helper, while the actual helper is called "iter_response_cleanup()". Settle on the former name, because the helper is only needed when using bound-iterators. Signed-off-by: Geert Uytterhoeven [Cristian: removed Fixed tag referring the same series] Signed-off-by: Cristian Marussi Tested-by: Florian Fainelli --- drivers/firmware/arm_scmi/driver.c | 6 +++--- drivers/firmware/arm_scmi/protocols.h | 2 +- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/drivers/firmware/arm_scmi/driver.c b/drivers/firmware/arm_scmi= /driver.c index fd031a8d40df..57785c0c0424 100644 --- a/drivers/firmware/arm_scmi/driver.c +++ b/drivers/firmware/arm_scmi/driver.c @@ -1875,7 +1875,7 @@ static int __scmi_iterator_run(void *iter, unsigned i= nt *start, unsigned int *en return 0; } =20 -static void scmi_iterator_cleanup(void *iter) +static void scmi_iterator_bound_cleanup(void *iter) { struct scmi_iterator *i =3D iter; =20 @@ -1888,7 +1888,7 @@ static int scmi_iterator_run(void *iter) int ret; =20 ret =3D __scmi_iterator_run(iter, NULL, NULL); - scmi_iterator_cleanup(iter); + scmi_iterator_bound_cleanup(iter); =20 return ret; } @@ -2078,7 +2078,7 @@ static const struct scmi_proto_helpers_ops helpers_op= s =3D { .iter_response_init =3D scmi_iterator_init, .iter_response_run =3D scmi_iterator_run, .iter_response_run_bound =3D scmi_iterator_run_bound, - .iter_response_cleanup =3D scmi_iterator_cleanup, + .iter_response_bound_cleanup =3D scmi_iterator_bound_cleanup, .protocol_msg_check =3D scmi_protocol_msg_check, .fastchannel_init =3D scmi_common_fastchannel_init, .fastchannel_db_ring =3D scmi_common_fastchannel_db_ring, diff --git a/drivers/firmware/arm_scmi/protocols.h b/drivers/firmware/arm_s= cmi/protocols.h index e2ef604c16ef..15ad5162e37a 100644 --- a/drivers/firmware/arm_scmi/protocols.h +++ b/drivers/firmware/arm_scmi/protocols.h @@ -286,7 +286,7 @@ struct scmi_proto_helpers_ops { int (*iter_response_run)(void *iter); int (*iter_response_run_bound)(void *iter, unsigned int *start, unsigned int *end); - void (*iter_response_cleanup)(void *iter); + void (*iter_response_bound_cleanup)(void *iter); int (*protocol_msg_check)(const struct scmi_protocol_handle *ph, u32 message_id, u32 *attributes); void (*fastchannel_init)(const struct scmi_protocol_handle *ph, --=20 2.53.0 From nobody Wed Jun 17 01:35:13 2026 Received: from foss.arm.com (foss.arm.com [217.140.110.172]) by smtp.subspace.kernel.org (Postfix) with ESMTP id 8FA823264DD; Tue, 28 Apr 2026 20:17:14 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=217.140.110.172 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407436; cv=none; b=Obl2f7o/yOwWxdGvjAj8Hx2qTEthP6Fzd8vD/LXipWqzD+YrauYloe+aTwtYYjs3P1v81O8CMSw7qyCRcMTX7TzdcBGMuGfzKYlKbveb7R5bq5ApHiS6IWB7hIfyaXAGIQ/koCiYMGxtBEapLCGGyobI7W7g9gAPoP+J5flBeUA= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407436; c=relaxed/simple; bh=P2pDG/wbyXu8rvvGPP+RiEpj+f5STXBcLJcHsAu83UY=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=Lp7YAQcGE056/1T3dScBlnorRxYCIigDFkoq5wP09qa78BrP6HY1ZYN1E6k7WoxbMCjjNiGASH1T/1OCB4CAIBSiRS7PHReNkX6gNyFBJp3beOjdgZMqja8AnZ7WC/P/AOCOxlZVPduvDiKcjfeLLLqiI5FNy5IGPYnLwiTxwPU= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com; spf=pass smtp.mailfrom=arm.com; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b=mwefKaPm; arc=none smtp.client-ip=217.140.110.172 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=arm.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b="mwefKaPm" 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 9B8401C01; Tue, 28 Apr 2026 13:17:08 -0700 (PDT) Received: from pluto.fritz.box (usa-sjc-mx-foss1.foss.arm.com [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 2DA1F3F763; Tue, 28 Apr 2026 13:17:11 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=simple/simple; d=arm.com; s=foss; t=1777407434; bh=P2pDG/wbyXu8rvvGPP+RiEpj+f5STXBcLJcHsAu83UY=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=mwefKaPmm0jyQSIKhiKALsZAnUBD5homuXnTZ/E9KJK9X2uI+QGVOROS/kc7ndgUY byJn61FFion6HCwp0l5D6sE/lnrOo+yvE4lierNqg5tBQffFaurJAzZDVvDgpkfCRF sqsf8B072etWsleBq+rnQDxnw661yx2Nv8ujsJTE= From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org, arm-scmi@vger.kernel.org, linux-clk@vger.kernel.org, linux-renesas-soc@vger.kernel.org Cc: sudeep.holla@arm.com, philip.radford@arm.com, james.quinlan@broadcom.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, etienne.carriere@foss.st.com, peng.fan@oss.nxp.com, michal.simek@amd.com, geert+renesas@glider.be, kuninori.morimoto.gx@renesas.com, marek.vasut+renesas@gmail.com, Cristian Marussi Subject: [PATCH v3 13/15] firmware: arm_scmi: Use bound iterators to minimize discovered rates Date: Tue, 28 Apr 2026 21:15:20 +0100 Message-ID: <20260428201522.903875-14-cristian.marussi@arm.com> X-Mailer: git-send-email 2.53.0 In-Reply-To: <20260428201522.903875-1-cristian.marussi@arm.com> References: <20260428201522.903875-1-cristian.marussi@arm.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" Clock rates are guaranteed to be returned in ascending order for SCMI clock protocol versions greater than 1.0: in such a case, use bounded iterators to minimize the number of message exchanges needed to discover min and max rate. Signed-off-by: Cristian Marussi Tested-by: Florian Fainelli --- v1 --> v2 - fixed final ret value in scmi_clock_describe_get --- drivers/firmware/arm_scmi/clock.c | 90 +++++++++++++++++++++++++++---- 1 file changed, 81 insertions(+), 9 deletions(-) diff --git a/drivers/firmware/arm_scmi/clock.c b/drivers/firmware/arm_scmi/= clock.c index 8ce889dfc87b..15a963b1edb9 100644 --- a/drivers/firmware/arm_scmi/clock.c +++ b/drivers/firmware/arm_scmi/clock.c @@ -160,6 +160,7 @@ struct scmi_clock_rate_notify_payld { struct scmi_clock_desc { u32 id; bool rate_discrete; + unsigned int tot_rates; unsigned int num_rates; u64 *rates; #define RATE_MIN 0 @@ -483,15 +484,16 @@ iter_clk_describe_update_state(struct scmi_iterator_s= tate *st, } =20 if (!st->max_resources) { - int num_rates =3D st->num_returned + st->num_remaining; + unsigned int tot_rates =3D st->num_returned + st->num_remaining; =20 - p->clkd->rates =3D devm_kcalloc(p->dev, num_rates, + p->clkd->rates =3D devm_kcalloc(p->dev, tot_rates, sizeof(*p->clkd->rates), GFP_KERNEL); if (!p->clkd->rates) return -ENOMEM; =20 /* max_resources is used by the iterators to control bounds */ - st->max_resources =3D st->num_returned + st->num_remaining; + p->clkd->tot_rates =3D tot_rates; + st->max_resources =3D tot_rates; } =20 return 0; @@ -514,8 +516,8 @@ iter_clk_describe_process_response(const struct scmi_pr= otocol_handle *ph, } =20 static int -scmi_clock_describe_rates_get(const struct scmi_protocol_handle *ph, u32 c= lk_id, - struct clock_info *cinfo) +scmi_clock_describe_rates_get_full(const struct scmi_protocol_handle *ph, + struct scmi_clock_desc *clkd) { int ret; void *iter; @@ -524,7 +526,6 @@ scmi_clock_describe_rates_get(const struct scmi_protoco= l_handle *ph, u32 clk_id, .update_state =3D iter_clk_describe_update_state, .process_response =3D iter_clk_describe_process_response, }; - struct scmi_clock_desc *clkd =3D &cinfo->clkds[clk_id]; struct scmi_clk_ipriv cpriv =3D { .clkd =3D clkd, .dev =3D ph->dev, @@ -544,17 +545,88 @@ scmi_clock_describe_rates_get(const struct scmi_proto= col_handle *ph, u32 clk_id, if (!clkd->num_rates) return 0; =20 + if (clkd->rate_discrete) + sort(clkd->rates, clkd->num_rates, + sizeof(clkd->rates[0]), rate_cmp_func, NULL); + + return 0; +} + +static int +scmi_clock_describe_rates_get_lazy(const struct scmi_protocol_handle *ph, + struct scmi_clock_desc *clkd) +{ + struct scmi_iterator_ops ops =3D { + .prepare_message =3D iter_clk_describe_prepare_message, + .update_state =3D iter_clk_describe_update_state, + .process_response =3D iter_clk_describe_process_response, + }; + struct scmi_clk_ipriv cpriv =3D { + .clkd =3D clkd, + .dev =3D ph->dev, + }; + unsigned int first, last; + void *iter; + int ret; + + iter =3D ph->hops->iter_response_init(ph, &ops, 0, CLOCK_DESCRIBE_RATES, + sizeof(struct scmi_msg_clock_describe_rates), + &cpriv); + if (IS_ERR(iter)) + return PTR_ERR(iter); + + /* Try to grab a triplet, so that in case is NON-discrete we are done */ + first =3D 0; + last =3D 2; + ret =3D ph->hops->iter_response_run_bound(iter, &first, &last); + if (ret) + goto out; + + /* If discrete grab the last value, which should be the max */ + if (clkd->rate_discrete && clkd->tot_rates > 3) { + first =3D clkd->tot_rates - 1; + last =3D clkd->tot_rates - 1; + ret =3D ph->hops->iter_response_run_bound(iter, &first, &last); + } + +out: + ph->hops->iter_response_cleanup(iter); + + return ret; +} + +static int +scmi_clock_describe_rates_get(const struct scmi_protocol_handle *ph, + u32 clk_id, struct clock_info *cinfo) +{ + struct scmi_clock_desc *clkd =3D &cinfo->clkds[clk_id]; + int ret; + + /* + * Since only after SCMI Clock v1.0 the returned rates are guaranteed to + * be discovered in ascending order, lazy enumeration cannot be use for + * SCMI Clock v1.0 protocol. + */ + if (PROTOCOL_REV_MAJOR(ph->version) > 0x1) + ret =3D scmi_clock_describe_rates_get_lazy(ph, clkd); + else + ret =3D scmi_clock_describe_rates_get_full(ph, clkd); + + if (ret) + return ret; + + clkd->info.min_rate =3D clkd->rates[RATE_MIN]; if (!clkd->rate_discrete) { clkd->info.max_rate =3D clkd->rates[RATE_MAX]; dev_dbg(ph->dev, "Min %llu Max %llu Step %llu Hz\n", clkd->rates[RATE_MIN], clkd->rates[RATE_MAX], clkd->rates[RATE_STEP]); } else { - sort(clkd->rates, clkd->num_rates, - sizeof(clkd->rates[0]), rate_cmp_func, NULL); clkd->info.max_rate =3D clkd->rates[clkd->num_rates - 1]; + dev_dbg(ph->dev, "Clock:%s DISCRETE:%d -> Min %llu Max %llu\n", + clkd->info.name, clkd->rate_discrete, + clkd->info.min_rate, clkd->info.max_rate); } - clkd->info.min_rate =3D clkd->rates[RATE_MIN]; =20 return 0; } --=20 2.53.0 From nobody Wed Jun 17 01:35:13 2026 Received: from foss.arm.com (foss.arm.com [217.140.110.172]) by smtp.subspace.kernel.org (Postfix) with ESMTP id 552B633F5B4; Tue, 28 Apr 2026 20:17:18 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=217.140.110.172 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407440; cv=none; b=Hr3/qwTfm3NbS1I/y0XrqL+Zsby+vRwVREouJ4ssJ+v0IIb54H1e91/nmAsypXwdhaXu02y79jKbgEC0sImN+i2p2qapULo0/poVCYoHeEUUf2mLdVmvMBzaJ2mMbpF1K/5ev2SBYg6ed9mQ/1oGl4vknFzwJgpDf+sTnIStns8= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407440; c=relaxed/simple; bh=Va/JAFXv1Mv8JmjPvWUiIYbL1IHuJCCIZgDN7C5J2qI=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=SYhHOXROzgONbds8LvUwINe9tzzRtlcIjrojRDscyJwLgeZwpo8eAj7ZOy1IUKy6+dURgwJcmxBwEV9iaqlN3CAZCvDFBy31dSUvMpyka9JXfpTJBL1K969jDnSSyEUqS3R9rUnBuBk/1Qxo5s+Ab94iWTuiyCUeGAFBRkaKPBU= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com; spf=pass smtp.mailfrom=arm.com; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b=KgbOa5J/; arc=none smtp.client-ip=217.140.110.172 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=arm.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b="KgbOa5J/" 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 C97883295; Tue, 28 Apr 2026 13:17:11 -0700 (PDT) Received: from pluto.fritz.box (usa-sjc-mx-foss1.foss.arm.com [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 6FD003F763; Tue, 28 Apr 2026 13:17:14 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=simple/simple; d=arm.com; s=foss; t=1777407437; bh=Va/JAFXv1Mv8JmjPvWUiIYbL1IHuJCCIZgDN7C5J2qI=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=KgbOa5J/xsBO8ib08nnLCnge8bFbCShJQPMq2C2+Bp5vODcd8uUAeeY2acVLel5w0 IVlaAyHz6Y+0oPoFqAn9DdPFdaLy0JJbQIvou8t2u5+231tBX0QrqoKFaLAKIM4VC+ bXWNSYTpxA07yaa/J/Jog2uovYiy04oEYLOz+CXs= From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org, arm-scmi@vger.kernel.org, linux-clk@vger.kernel.org, linux-renesas-soc@vger.kernel.org Cc: sudeep.holla@arm.com, philip.radford@arm.com, james.quinlan@broadcom.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, etienne.carriere@foss.st.com, peng.fan@oss.nxp.com, michal.simek@amd.com, geert+renesas@glider.be, kuninori.morimoto.gx@renesas.com, marek.vasut+renesas@gmail.com, Cristian Marussi Subject: [PATCH v3 14/15] firmware: arm_scmi: Fix OOB in scmi_clock_describe_rates_get_lazy() Date: Tue, 28 Apr 2026 21:15:21 +0100 Message-ID: <20260428201522.903875-15-cristian.marussi@arm.com> X-Mailer: git-send-email 2.53.0 In-Reply-To: <20260428201522.903875-1-cristian.marussi@arm.com> References: <20260428201522.903875-1-cristian.marussi@arm.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" From: Geert Uytterhoeven Lazy discovery of discrete rates works as follows: A. Grab the first three rates, B. Grab the last rate, if there are more than three rates. It is up to the SCMI provider implementation to decide how many rates are returned in response to a single CLOCK_DESCRIBE_RATES command. Each rate received is stored in the scmi_clock_rates.rates[] array, and .num_rates is updated accordingly. When more than 3 rates have been received after step A, the last rate may have been received already, and stored in scmi_clock_rates.rates[] (which has space for scmi_clock_desc.tot_rates entries). Hence grabbing the last rate again will store it a second time, beyond the end of the array. Fix this by only grabbing the last rate when we don't already have it. Signed-off-by: Geert Uytterhoeven [Cristian: removed Fixed tag referring the same series] Signed-off-by: Cristian Marussi Tested-by: Florian Fainelli --- drivers/firmware/arm_scmi/clock.c | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/drivers/firmware/arm_scmi/clock.c b/drivers/firmware/arm_scmi/= clock.c index 15a963b1edb9..ba25a9c6d3ae 100644 --- a/drivers/firmware/arm_scmi/clock.c +++ b/drivers/firmware/arm_scmi/clock.c @@ -582,15 +582,18 @@ scmi_clock_describe_rates_get_lazy(const struct scmi_= protocol_handle *ph, if (ret) goto out; =20 - /* If discrete grab the last value, which should be the max */ - if (clkd->rate_discrete && clkd->tot_rates > 3) { + /* + * If discrete and we don't already have it, grab the last value, which + * should be the max + */ + if (clkd->rate_discrete && clkd->tot_rates > clkd->num_rates) { first =3D clkd->tot_rates - 1; last =3D clkd->tot_rates - 1; ret =3D ph->hops->iter_response_run_bound(iter, &first, &last); } =20 out: - ph->hops->iter_response_cleanup(iter); + ph->hops->iter_response_bound_cleanup(iter); =20 return ret; } --=20 2.53.0 From nobody Wed Jun 17 01:35:13 2026 Received: from foss.arm.com (foss.arm.com [217.140.110.172]) by smtp.subspace.kernel.org (Postfix) with ESMTP id 64B1539527C; Tue, 28 Apr 2026 20:17:21 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=217.140.110.172 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407443; cv=none; b=fi3ixzsBdwp8IJRgXytIXjv/AG9RbRdre4b8ftTEaDsvXRAyfuukRnieYoZWvb+HrhDJaRNeuCAEXEk+mG/W9j8OwsB4UAiQ1CBearUzuLpF4mQGnH0fJtWerap6xOLLSG4K2GASEUQR0eB1z6Tgx/eqMpfov6+mgDZuu8Edmbg= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1777407443; c=relaxed/simple; bh=cinOs3FUzEPcdTbTkmYDC2KeojNRYuDSqaYF95xRaEE=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=PiCbGKCXDpUmAU1Q27/+cAKQkrUHUj9075ryB1CJ4/f/7BI7oZIB4qaMS+tumMzQNsqOrYgm+nl+CEmRGBl/sWJkUHOQNOoC3dRayJ3HJNHZX/AFbZAT6puv3VfLMxMFvcLw3aMy2RnKqYGjI8nhVywdouYjsr4Vc52oFzJQxfE= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com; spf=pass smtp.mailfrom=arm.com; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b=NtgNhkQO; arc=none smtp.client-ip=217.140.110.172 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=arm.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=arm.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=arm.com header.i=@arm.com header.b="NtgNhkQO" 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 4C3FC3296; Tue, 28 Apr 2026 13:17:15 -0700 (PDT) Received: from pluto.fritz.box (usa-sjc-mx-foss1.foss.arm.com [172.31.20.19]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id C44323F763; Tue, 28 Apr 2026 13:17:17 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=simple/simple; d=arm.com; s=foss; t=1777407440; bh=cinOs3FUzEPcdTbTkmYDC2KeojNRYuDSqaYF95xRaEE=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=NtgNhkQOPzrpXCvuuBj7InMLpjtPlyueQ0+wSAnEIlKG6qH9rONfJiyyoGZGn82OD wxZu2++vFuX3jjcCy9nQ7d55xoFhEgRhP59P5E3qxLf3oKiae7i4G0D8aux6z1eEcC ZnMyHwl1KV0FBl9laXYPeM4doJ9EztzKwJXDVtOU= From: Cristian Marussi To: linux-kernel@vger.kernel.org, linux-arm-kernel@lists.infradead.org, arm-scmi@vger.kernel.org, linux-clk@vger.kernel.org, linux-renesas-soc@vger.kernel.org Cc: sudeep.holla@arm.com, philip.radford@arm.com, james.quinlan@broadcom.com, f.fainelli@gmail.com, vincent.guittot@linaro.org, etienne.carriere@foss.st.com, peng.fan@oss.nxp.com, michal.simek@amd.com, geert+renesas@glider.be, kuninori.morimoto.gx@renesas.com, marek.vasut+renesas@gmail.com, Cristian Marussi , Peng Fan Subject: [PATCH v3 15/15] firmware: arm_scmi: Introduce all_rates_get clock operation Date: Tue, 28 Apr 2026 21:15:22 +0100 Message-ID: <20260428201522.903875-16-cristian.marussi@arm.com> X-Mailer: git-send-email 2.53.0 In-Reply-To: <20260428201522.903875-1-cristian.marussi@arm.com> References: <20260428201522.903875-1-cristian.marussi@arm.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" Add a clock operation to get the whole set of rates available to a specific clock: when needed this request could transparently trigger a full rate discovery enumeration if this specific clock-rates were previously only lazily enumerated. Reviewed-by: Peng Fan Signed-off-by: Cristian Marussi Tested-by: Florian Fainelli --- v2 --> v3 - collected Reviewed tags --- drivers/firmware/arm_scmi/clock.c | 85 +++++++++++++++++++++---------- include/linux/scmi_protocol.h | 9 ++++ 2 files changed, 67 insertions(+), 27 deletions(-) diff --git a/drivers/firmware/arm_scmi/clock.c b/drivers/firmware/arm_scmi/= clock.c index ba25a9c6d3ae..316d3cd90c81 100644 --- a/drivers/firmware/arm_scmi/clock.c +++ b/drivers/firmware/arm_scmi/clock.c @@ -159,10 +159,8 @@ struct scmi_clock_rate_notify_payld { =20 struct scmi_clock_desc { u32 id; - bool rate_discrete; unsigned int tot_rates; - unsigned int num_rates; - u64 *rates; + struct scmi_clock_rates r; #define RATE_MIN 0 #define RATE_MAX 1 #define RATE_STEP 2 @@ -469,10 +467,10 @@ iter_clk_describe_update_state(struct scmi_iterator_s= tate *st, flags =3D le32_to_cpu(r->num_rates_flags); st->num_remaining =3D NUM_REMAINING(flags); st->num_returned =3D NUM_RETURNED(flags); - p->clkd->rate_discrete =3D RATE_DISCRETE(flags); + p->clkd->r.rate_discrete =3D RATE_DISCRETE(flags); =20 /* Warn about out of spec replies ... */ - if (!p->clkd->rate_discrete && + if (!p->clkd->r.rate_discrete && (st->num_returned !=3D 3 || st->num_remaining !=3D 0)) { dev_warn(p->dev, "Out-of-spec CLOCK_DESCRIBE_RATES reply for %s - returned:%d remaining= :%d rx_len:%zd\n", @@ -486,9 +484,9 @@ iter_clk_describe_update_state(struct scmi_iterator_sta= te *st, if (!st->max_resources) { unsigned int tot_rates =3D st->num_returned + st->num_remaining; =20 - p->clkd->rates =3D devm_kcalloc(p->dev, tot_rates, - sizeof(*p->clkd->rates), GFP_KERNEL); - if (!p->clkd->rates) + p->clkd->r.rates =3D devm_kcalloc(p->dev, tot_rates, + sizeof(*p->clkd->r.rates), GFP_KERNEL); + if (!p->clkd->r.rates) return -ENOMEM; =20 /* max_resources is used by the iterators to control bounds */ @@ -507,10 +505,10 @@ iter_clk_describe_process_response(const struct scmi_= protocol_handle *ph, struct scmi_clk_ipriv *p =3D priv; const struct scmi_msg_resp_clock_describe_rates *r =3D response; =20 - p->clkd->rates[p->clkd->num_rates] =3D RATE_TO_U64(r->rate[st->loop_idx]); + p->clkd->r.rates[p->clkd->r.num_rates] =3D RATE_TO_U64(r->rate[st->loop_i= dx]); =20 /* Count only effectively discovered rates */ - p->clkd->num_rates++; + p->clkd->r.num_rates++; =20 return 0; } @@ -531,7 +529,13 @@ scmi_clock_describe_rates_get_full(const struct scmi_p= rotocol_handle *ph, .dev =3D ph->dev, }; =20 - iter =3D ph->hops->iter_response_init(ph, &ops, 0, CLOCK_DESCRIBE_RATES, + /* + * Using tot_rates as max_resources parameter here so as to trigger + * the dynamic allocation only when strictly needed: when trying a + * full enumeration after a lazy one tot_rates will be non-zero. + */ + iter =3D ph->hops->iter_response_init(ph, &ops, clkd->tot_rates, + CLOCK_DESCRIBE_RATES, sizeof(struct scmi_msg_clock_describe_rates), &cpriv); if (IS_ERR(iter)) @@ -542,12 +546,12 @@ scmi_clock_describe_rates_get_full(const struct scmi_= protocol_handle *ph, return ret; =20 /* empty set ? */ - if (!clkd->num_rates) + if (!clkd->r.num_rates) return 0; =20 - if (clkd->rate_discrete) - sort(clkd->rates, clkd->num_rates, - sizeof(clkd->rates[0]), rate_cmp_func, NULL); + if (clkd->r.rate_discrete && PROTOCOL_REV_MAJOR(ph->version) =3D=3D 0x1) + sort(clkd->r.rates, clkd->r.num_rates, + sizeof(clkd->r.rates[0]), rate_cmp_func, NULL); =20 return 0; } @@ -586,7 +590,7 @@ scmi_clock_describe_rates_get_lazy(const struct scmi_pr= otocol_handle *ph, * If discrete and we don't already have it, grab the last value, which * should be the max */ - if (clkd->rate_discrete && clkd->tot_rates > clkd->num_rates) { + if (clkd->r.rate_discrete && clkd->tot_rates > clkd->r.num_rates) { first =3D clkd->tot_rates - 1; last =3D clkd->tot_rates - 1; ret =3D ph->hops->iter_response_run_bound(iter, &first, &last); @@ -618,16 +622,16 @@ scmi_clock_describe_rates_get(const struct scmi_proto= col_handle *ph, if (ret) return ret; =20 - clkd->info.min_rate =3D clkd->rates[RATE_MIN]; - if (!clkd->rate_discrete) { - clkd->info.max_rate =3D clkd->rates[RATE_MAX]; + clkd->info.min_rate =3D clkd->r.rates[RATE_MIN]; + if (!clkd->r.rate_discrete) { + clkd->info.max_rate =3D clkd->r.rates[RATE_MAX]; dev_dbg(ph->dev, "Min %llu Max %llu Step %llu Hz\n", - clkd->rates[RATE_MIN], clkd->rates[RATE_MAX], - clkd->rates[RATE_STEP]); + clkd->r.rates[RATE_MIN], clkd->r.rates[RATE_MAX], + clkd->r.rates[RATE_STEP]); } else { - clkd->info.max_rate =3D clkd->rates[clkd->num_rates - 1]; + clkd->info.max_rate =3D clkd->r.rates[clkd->r.num_rates - 1]; dev_dbg(ph->dev, "Clock:%s DISCRETE:%d -> Min %llu Max %llu\n", - clkd->info.name, clkd->rate_discrete, + clkd->info.name, clkd->r.rate_discrete, clkd->info.min_rate, clkd->info.max_rate); } =20 @@ -732,7 +736,7 @@ static int scmi_clock_determine_rate(const struct scmi_= protocol_handle *ph, * If we can't figure out what rate it will be, so just return the * rate back to the caller. */ - if (clkd->rate_discrete) + if (clkd->r.rate_discrete) return 0; =20 fmin =3D clk->min_rate; @@ -746,14 +750,40 @@ static int scmi_clock_determine_rate(const struct scm= i_protocol_handle *ph, } =20 ftmp =3D *rate - fmin; - ftmp +=3D clkd->rates[RATE_STEP] - 1; /* to round up */ - ftmp =3D div64_ul(ftmp, clkd->rates[RATE_STEP]); + ftmp +=3D clkd->r.rates[RATE_STEP] - 1; /* to round up */ + ftmp =3D div64_ul(ftmp, clkd->r.rates[RATE_STEP]); =20 - *rate =3D ftmp * clkd->rates[RATE_STEP] + fmin; + *rate =3D ftmp * clkd->r.rates[RATE_STEP] + fmin; =20 return 0; } =20 +static const struct scmi_clock_rates * +scmi_clock_all_rates_get(const struct scmi_protocol_handle *ph, u32 clk_id) +{ + struct clock_info *ci =3D ph->get_priv(ph); + struct scmi_clock_desc *clkd; + struct scmi_clock_info *clk; + + clk =3D scmi_clock_domain_lookup(ci, clk_id); + if (IS_ERR(clk) || !clk->name[0]) + return NULL; + + clkd =3D to_desc(clk); + /* Needs full enumeration ? */ + if (clkd->r.rate_discrete && clkd->tot_rates !=3D clkd->r.num_rates) { + int ret; + + /* rates[] is already allocated BUT we need to re-enumerate */ + clkd->r.num_rates =3D 0; + ret =3D scmi_clock_describe_rates_get_full(ph, clkd); + if (ret) + return NULL; + } + + return &clkd->r; +} + static int scmi_clock_config_set(const struct scmi_protocol_handle *ph, u32 clk_id, enum clk_state state, @@ -1067,6 +1097,7 @@ static const struct scmi_clk_proto_ops clk_proto_ops = =3D { .rate_get =3D scmi_clock_rate_get, .rate_set =3D scmi_clock_rate_set, .determine_rate =3D scmi_clock_determine_rate, + .all_rates_get =3D scmi_clock_all_rates_get, .enable =3D scmi_clock_enable, .disable =3D scmi_clock_disable, .state_get =3D scmi_clock_state_get, diff --git a/include/linux/scmi_protocol.h b/include/linux/scmi_protocol.h index 5552ac04c820..c710107c2120 100644 --- a/include/linux/scmi_protocol.h +++ b/include/linux/scmi_protocol.h @@ -40,6 +40,12 @@ struct scmi_revision_info { char sub_vendor_id[SCMI_SHORT_NAME_MAX_SIZE]; }; =20 +struct scmi_clock_rates { + bool rate_discrete; + unsigned int num_rates; + u64 *rates; +}; + struct scmi_clock_info { char name[SCMI_MAX_STR_SIZE]; unsigned int enable_latency; @@ -85,6 +91,7 @@ enum scmi_clock_oem_config { * clock calculating the closest allowed rate. * Note that @rate is an input/output parameter used both to * describe the requested rate and report the closest match + * @all_rates_get: get the list of all available rates for the specified c= lock. * @enable: enables the specified clock * @disable: disables the specified clock * @state_get: get the status of the specified clock @@ -104,6 +111,8 @@ struct scmi_clk_proto_ops { u64 rate); int (*determine_rate)(const struct scmi_protocol_handle *ph, u32 clk_id, unsigned long *rate); + const struct scmi_clock_rates __must_check *(*all_rates_get) + (const struct scmi_protocol_handle *ph, u32 clk_id); int (*enable)(const struct scmi_protocol_handle *ph, u32 clk_id, bool atomic); int (*disable)(const struct scmi_protocol_handle *ph, u32 clk_id, --=20 2.53.0