From nobody Thu Sep 24 12:55:34 2026 Received: from smtp.kernel.org (aws-us-west-2-korg-mail-1.web.codeaurora.org [10.30.226.201]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id CA45247CC67; Wed, 23 Sep 2026 11:15:45 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=10.30.226.201 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1790162145; cv=none; b=afJ+BxJoxfYK8OGe3271LIEWAgllFBi2JX/INiesPeNUO98N/N7GVHoFrgNPcSp0mc6CPlMOrZWdVm3dwKTEm68DjWLd6PsJ+R3zUXq1Pg0XLdy3ehmz9wOXOe8ZNXZwX7PAxpcw4T0Yciejm2codKKlD7IUYrOc4WnRlv54z0U= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1790162145; c=relaxed/simple; bh=GWRpaHGKFV8s8x3vAIKkZwcDLAKZt3iWK+kaAuhZVyA=; h=From:Date:Subject:MIME-Version:Content-Type:Message-Id:References: In-Reply-To:To:Cc; b=iTjfzt1LDXlPNdvAkr4RxKqyOlkBP00ndpnkHdU4fOgzIdqAsAv035jbbbcoc1WKsx5Gu2g+knLgmMuE9MYZcupVFy63G2HII+m5+HQL0Wl74O2mlloQwGh9tLctbfIAixCYRtXGy4vYAHTEhvEhVxFExMFwNff7l9U9/Wl/SWk= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=kernel.org header.i=@kernel.org header.b=hiBSi7PF; arc=none smtp.client-ip=10.30.226.201 Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=kernel.org header.i=@kernel.org header.b="hiBSi7PF" Received: by smtp.kernel.org (Postfix) with ESMTPS id 5571BC2BCC7; Wed, 23 Sep 2026 11:15:45 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=kernel.org; s=k20201202; t=1790162145; bh=GWRpaHGKFV8s8x3vAIKkZwcDLAKZt3iWK+kaAuhZVyA=; h=From:Date:Subject:References:In-Reply-To:To:Cc:Reply-To:From; b=hiBSi7PFVynAZD4+8WfsN69cGARZktjL5LIhRoMS/tqhNrfm1ybX5Kkq8mBHwcI7m vd8BAnoPXl1c5tvq1JavJMjF7T8TGgftlK1k0X6Ekv1wON7bMUNI9Gal1UzBOUCmnr BwxI2U9pE9cX/qa7vOpiSLsIZaf6wX2bv6ndkXPR+FhaFZF6/czNBXvKZOXV+dJyg1 3dE02sc1SPOl7PkYTmATjjtv4kCqX8hUzsQaCoGB1cjYBapIoctv2HctgX6qnfw417 IfOImm6ZVXh46nhT6uJ8v3rd43mEJnlYwu9RuY14r0mMchgJRBT649oEMYY6YXsXfL Rw6vEuHRzLeWA== Received: from aws-us-west-2-korg-lkml-1.web.codeaurora.org (localhost.localdomain [127.0.0.1]) by smtp.lore.kernel.org (Postfix) with ESMTP id 3619CC98307; Wed, 23 Sep 2026 11:15:45 +0000 (UTC) From: Jian Hu via B4 Relay Date: Wed, 23 Sep 2026 19:14:47 +0800 Subject: [PATCH RFC 1/3] clk: meson: pll: Remove the dedicated n parameter Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" Content-Transfer-Encoding: quoted-printable Message-Id: <20260923-meson_refactor_n-v1-1-3a8ce27121a2@amlogic.com> References: <20260923-meson_refactor_n-v1-0-3a8ce27121a2@amlogic.com> In-Reply-To: <20260923-meson_refactor_n-v1-0-3a8ce27121a2@amlogic.com> To: Neil Armstrong , Jerome Brunet , Stephen Boyd , Brian Masney , Kevin Hilman , Martin Blumenstingl , Jerome Brunet , Rob Herring , Krzysztof Kozlowski , Conor Dooley Cc: linux-amlogic@lists.infradead.org, linux-clk@vger.kernel.org, linux-arm-kernel@lists.infradead.org, linux-kernel@vger.kernel.org, devicetree@vger.kernel.org, Jian Hu X-Mailer: b4 0.14.3 X-Developer-Signature: v=1; a=ed25519-sha256; t=1790162143; l=10655; i=jian.hu@amlogic.com; s=20260415; h=from:subject:message-id; bh=Al+kTQGUTXZOgkSHRDObWL+soFKOeqqmmJSU8iCEL1Q=; b=R9TSkGDzTK8pKdr7qVFLHHHARwy72wtcjL5RycccMeus7w3zEiM7oetX/orVfKXeAe+Nak/kN PW6QQtTM8bxCFEJ3ZXp0Z9slbADgfvLG8L3t8qd8xYxpOX7BcUniyzU X-Developer-Key: i=jian.hu@amlogic.com; a=ed25519; pk=zHUE+rNtH9z+Sb8au1/elWknjFQmy5QDVkBoxleuOIA= X-Endpoint-Received: by B4 Relay for jian.hu@amlogic.com/20260415 with auth_id=735 X-Original-From: Jian Hu Reply-To: jian.hu@amlogic.com From: Jian Hu The Meson PLL framework models the PLL pre-divider (N) using a dedicated field in struct meson_clk_pll_data. Since the common clock framework already provides a generic divider implementation, there is no need to keep PLL-specific support for it. Remove the dedicated n parameter from the framework and simplify the PLL rate calculation accordingly. The pre-divider will be represented as a separate divider clock by platform drivers where needed. Signed-off-by: Jian Hu --- drivers/clk/meson/clk-pll.c | 178 +++++++++-------------------------------= ---- drivers/clk/meson/clk-pll.h | 13 ---- 2 files changed, 34 insertions(+), 157 deletions(-) diff --git a/drivers/clk/meson/clk-pll.c b/drivers/clk/meson/clk-pll.c index 1ea6579a760f..de56d55e3b79 100644 --- a/drivers/clk/meson/clk-pll.c +++ b/drivers/clk/meson/clk-pll.c @@ -14,7 +14,7 @@ * +--------------------------------+ * | | * | +--+ | - * in >>-----[ /N ]--->| | +-----+ | + * in >>----------->| | +-----+ | * | | |------| DCO |---->> out * | +--------->| | +--v--+ | * | | +--+ | | @@ -23,7 +23,7 @@ * | | * +--------------------------------+ * - * out =3D in * (m + frac / frac_max) / n + * out =3D in * (m + frac / frac_max) */ =20 #include @@ -52,8 +52,7 @@ static int __pll_round_closest_mult(struct meson_clk_pll_= data *pll) } =20 static unsigned long __pll_params_to_rate(unsigned long parent_rate, - unsigned int m, unsigned int n, - unsigned int frac, + unsigned int m, unsigned int frac, struct meson_clk_pll_data *pll) { u64 rate =3D (u64)parent_rate * m; @@ -66,7 +65,7 @@ static unsigned long __pll_params_to_rate(unsigned long p= arent_rate, rate +=3D DIV_ROUND_UP_ULL(frac_rate, frac_max); } =20 - return DIV_ROUND_UP_ULL(rate, n); + return rate; } =20 static unsigned long meson_clk_pll_recalc_rate(struct clk_hw *hw, @@ -74,17 +73,7 @@ static unsigned long meson_clk_pll_recalc_rate(struct cl= k_hw *hw, { struct clk_regmap *clk =3D to_clk_regmap(hw); struct meson_clk_pll_data *pll =3D meson_clk_pll_data(clk); - unsigned int m, n, frac; - - n =3D meson_parm_read(clk->map, &pll->n); - - /* - * On some HW, N is set to zero on init. This value is invalid as - * it would result in a division by zero. The rate can't be - * calculated in this case - */ - if (n =3D=3D 0) - return 0; + unsigned int m, frac; =20 m =3D meson_parm_read(clk->map, &pll->m); =20 @@ -92,21 +81,20 @@ static unsigned long meson_clk_pll_recalc_rate(struct c= lk_hw *hw, meson_parm_read(clk->map, &pll->frac) : 0; =20 - return __pll_params_to_rate(parent_rate, m, n, frac, pll); + return __pll_params_to_rate(parent_rate, m, frac, pll); } =20 static unsigned int __pll_params_with_frac(unsigned long rate, unsigned long parent_rate, unsigned int m, - unsigned int n, struct meson_clk_pll_data *pll) { unsigned int frac_max =3D pll->frac_max ? pll->frac_max : (1 << pll->frac.width); - u64 val =3D (u64)rate * n; + u64 val =3D (u64)rate; =20 /* Bail out if we are already over the requested rate */ - if (rate < parent_rate * m / n) + if (rate < parent_rate * m) return 0; =20 if (pll->flags & CLK_MESON_PLL_ROUND_CLOSEST) @@ -119,145 +107,48 @@ static unsigned int __pll_params_with_frac(unsigned = long rate, return min((unsigned int)val, (frac_max - 1)); } =20 -static bool meson_clk_pll_is_better(unsigned long rate, - unsigned long best, - unsigned long now, - struct meson_clk_pll_data *pll) -{ - if (__pll_round_closest_mult(pll)) { - /* Round Closest */ - if (abs(now - rate) < abs(best - rate)) - return true; - } else { - /* Round down */ - if (now <=3D rate && best < now) - return true; - } - - return false; -} - -static int meson_clk_get_pll_table_index(unsigned int index, - unsigned int *m, - unsigned int *n, - struct meson_clk_pll_data *pll) +static int meson_clk_get_pll_multiplier(unsigned long rate, + unsigned long parent_rate, + unsigned int *m, + struct meson_clk_pll_data *pll) { - if (!pll->table[index].n) + if (!pll->range) return -EINVAL; =20 - *m =3D pll->table[index].m; - *n =3D pll->table[index].n; - - return 0; -} - -static unsigned int meson_clk_get_pll_range_m(unsigned long rate, - unsigned long parent_rate, - unsigned int n, - struct meson_clk_pll_data *pll) -{ - u64 val =3D (u64)rate * n; - - if (__pll_round_closest_mult(pll)) - return DIV_ROUND_CLOSEST_ULL(val, parent_rate); - - return div_u64(val, parent_rate); -} - -static int meson_clk_get_pll_range_index(unsigned long rate, - unsigned long parent_rate, - unsigned int index, - unsigned int *m, - unsigned int *n, - struct meson_clk_pll_data *pll) -{ - *n =3D index + 1; - - /* Check the predivider range */ - if (*n >=3D (1 << pll->n.width)) - return -EINVAL; - - if (*n =3D=3D 1) { - /* Get the boundaries out the way */ - if (rate <=3D pll->range->min * parent_rate) { - *m =3D pll->range->min; - return -ENODATA; - } else if (rate >=3D pll->range->max * parent_rate) { - *m =3D pll->range->max; - return -ENODATA; - } + if (rate <=3D pll->range->min * parent_rate) { + *m =3D pll->range->min; + return -ENODATA; + } else if (rate >=3D pll->range->max * parent_rate) { + *m =3D pll->range->max; + return -ENODATA; } =20 - *m =3D meson_clk_get_pll_range_m(rate, parent_rate, *n, pll); + if (__pll_round_closest_mult(pll)) + *m =3D DIV_ROUND_CLOSEST_ULL(rate, parent_rate); + else + *m =3D div_u64(rate, parent_rate); =20 - /* the pre-divider gives a multiplier too big - stop */ + /* Multiplier exceeds hardware range */ if (*m >=3D (1 << pll->m.width)) return -EINVAL; =20 return 0; } =20 -static int meson_clk_get_pll_get_index(unsigned long rate, - unsigned long parent_rate, - unsigned int index, - unsigned int *m, - unsigned int *n, - struct meson_clk_pll_data *pll) -{ - if (pll->range) - return meson_clk_get_pll_range_index(rate, parent_rate, - index, m, n, pll); - else if (pll->table) - return meson_clk_get_pll_table_index(index, m, n, pll); - - return -EINVAL; -} - -static int meson_clk_get_pll_settings(unsigned long rate, - unsigned long parent_rate, - unsigned int *best_m, - unsigned int *best_n, - struct meson_clk_pll_data *pll) -{ - unsigned long best =3D 0, now =3D 0; - unsigned int i, m, n; - int ret; - - for (i =3D 0, ret =3D 0; !ret; i++) { - ret =3D meson_clk_get_pll_get_index(rate, parent_rate, - i, &m, &n, pll); - if (ret =3D=3D -EINVAL) - break; - - now =3D __pll_params_to_rate(parent_rate, m, n, 0, pll); - if (meson_clk_pll_is_better(rate, best, now, pll)) { - best =3D now; - *best_m =3D m; - *best_n =3D n; - - if (now =3D=3D rate) - break; - } - } - - return best ? 0 : -EINVAL; -} - static int meson_clk_pll_determine_rate(struct clk_hw *hw, struct clk_rate_request *req) { struct clk_regmap *clk =3D to_clk_regmap(hw); struct meson_clk_pll_data *pll =3D meson_clk_pll_data(clk); - unsigned int m, n, frac; + unsigned int m, frac; unsigned long round; int ret; =20 - ret =3D meson_clk_get_pll_settings(req->rate, req->best_parent_rate, - &m, &n, pll); - if (ret) + ret =3D meson_clk_get_pll_multiplier(req->rate, req->best_parent_rate, &m= , pll); + if (ret && ret !=3D -ENODATA) return ret; =20 - round =3D __pll_params_to_rate(req->best_parent_rate, m, n, 0, pll); + round =3D __pll_params_to_rate(req->best_parent_rate, m, 0, pll); =20 if (!MESON_PARM_APPLICABLE(&pll->frac) || req->rate =3D=3D round) { req->rate =3D round; @@ -268,8 +159,8 @@ static int meson_clk_pll_determine_rate(struct clk_hw *= hw, * The rate provided by the setting is not an exact match, let's * try to improve the result using the fractional parameter */ - frac =3D __pll_params_with_frac(req->rate, req->best_parent_rate, m, n, p= ll); - req->rate =3D __pll_params_to_rate(req->best_parent_rate, m, n, frac, pll= ); + frac =3D __pll_params_with_frac(req->rate, req->best_parent_rate, m, pll); + req->rate =3D __pll_params_to_rate(req->best_parent_rate, m, frac, pll); =20 return 0; } @@ -420,7 +311,7 @@ static int meson_clk_pll_set_rate(struct clk_hw *hw, un= signed long rate, { struct clk_regmap *clk =3D to_clk_regmap(hw); struct meson_clk_pll_data *pll =3D meson_clk_pll_data(clk); - unsigned int enabled, m, n, frac =3D 0; + unsigned int enabled, m, frac =3D 0; unsigned long old_rate; int ret; =20 @@ -429,19 +320,18 @@ static int meson_clk_pll_set_rate(struct clk_hw *hw, = unsigned long rate, =20 old_rate =3D clk_hw_get_rate(hw); =20 - ret =3D meson_clk_get_pll_settings(rate, parent_rate, &m, &n, pll); - if (ret) + ret =3D meson_clk_get_pll_multiplier(rate, parent_rate, &m, pll); + if (ret && ret !=3D -ENODATA) return ret; =20 enabled =3D meson_parm_read(clk->map, &pll->en); if (enabled) meson_clk_pll_disable(hw); =20 - meson_parm_write(clk->map, &pll->n, n); meson_parm_write(clk->map, &pll->m, m); =20 if (MESON_PARM_APPLICABLE(&pll->frac)) { - frac =3D __pll_params_with_frac(rate, parent_rate, m, n, pll); + frac =3D __pll_params_with_frac(rate, parent_rate, m, pll); meson_parm_write(clk->map, &pll->frac, frac); } =20 diff --git a/drivers/clk/meson/clk-pll.h b/drivers/clk/meson/clk-pll.h index 949157fb7bf5..46feee72830f 100644 --- a/drivers/clk/meson/clk-pll.h +++ b/drivers/clk/meson/clk-pll.h @@ -11,29 +11,17 @@ #include #include "parm.h" =20 -struct pll_params_table { - unsigned int m; - unsigned int n; -}; - struct pll_mult_range { unsigned int min; unsigned int max; }; =20 -#define PLL_PARAMS(_m, _n) \ - { \ - .m =3D (_m), \ - .n =3D (_n), \ - } - #define CLK_MESON_PLL_ROUND_CLOSEST BIT(0) #define CLK_MESON_PLL_NOINIT_ENABLED BIT(1) =20 struct meson_clk_pll_data { struct parm en; struct parm m; - struct parm n; struct parm frac; struct parm l; struct parm rst; @@ -41,7 +29,6 @@ struct meson_clk_pll_data { struct parm l_detect; const struct reg_sequence *init_regs; unsigned int init_count; - const struct pll_params_table *table; const struct pll_mult_range *range; unsigned int frac_max; u8 flags; --=20 2.47.1 From nobody Thu Sep 24 12:55:34 2026 Received: from smtp.kernel.org (aws-us-west-2-korg-mail-1.web.codeaurora.org [10.30.226.201]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id CA5D4495030; Wed, 23 Sep 2026 11:15:45 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=10.30.226.201 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1790162145; cv=none; b=gH3RkXkr+mBm3hUPuajR3cTkWFiPbrgBNyr5GsHeA8qHd276+3fmGhOiI7bxQ9PHoU/u0F0+oZx/sCIZULuM23+rq7QJsaE6qjHCF7SmTPb3E912B/9mYP1oxjyR+YR+KTKXtGCaeM+YatWRoJiK7qqhiLL/NONHUEJgUkzQY6k= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1790162145; c=relaxed/simple; bh=bqP8YA42hWQqWkIXy1FVgmJ12q2wrxR9OYJQppEs/Uk=; h=From:Date:Subject:MIME-Version:Content-Type:Message-Id:References: In-Reply-To:To:Cc; b=LxSipJzUJrNbkUtQWPJRsACn36hjjXzqxrf5Krv3d2++cH+53upfa86wXmzVPZH7vNysVTSPev18r2wRSYmOvRkVV4GVv16odiqxobfltHSbUTJBbWp99vIAJADyq2F+RSTf78MvDJzUeGWCHPTm8rgVmvtC4MCIk+gXBWZkwrs= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=kernel.org header.i=@kernel.org header.b=dJjC2anh; arc=none smtp.client-ip=10.30.226.201 Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=kernel.org header.i=@kernel.org header.b="dJjC2anh" Received: by smtp.kernel.org (Postfix) with ESMTPS id 66A14C2BCFB; Wed, 23 Sep 2026 11:15:45 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=kernel.org; s=k20201202; t=1790162145; bh=bqP8YA42hWQqWkIXy1FVgmJ12q2wrxR9OYJQppEs/Uk=; h=From:Date:Subject:References:In-Reply-To:To:Cc:Reply-To:From; b=dJjC2anhcVyMwIC1G4OLRCia4y+JfJhGhEtcwMWg+VOrv4Phdfk2NFjfoQrNbW4kZ Hk4sg1nIdD6TjrD9OxxY9thkHw1qQDSP01beLgcok52CPSlFszMfNEabZnPTOrwgI8 Nibz+zN6sh7w9zoaldqeH87br0btn4o1yrEReajjoaUiPdChSHuFJSqBzcn+ZDTkAR jPk/4mwYZQNoG7zp4T39TfnNxDiktvfesjEIGJU6/0YstgtGVCsHS0lbG4QM4d7GDU lakTau7LiR37ejZHDtYWoRRtArl6OaJL7tnOnFZ+lvgH6uPk8/XMTZL+KBmiFQIH3E TOLbewP/AdtyA== Received: from aws-us-west-2-korg-lkml-1.web.codeaurora.org (localhost.localdomain [127.0.0.1]) by smtp.lore.kernel.org (Postfix) with ESMTP id 46279C982FA; Wed, 23 Sep 2026 11:15:45 +0000 (UTC) From: Jian Hu via B4 Relay Date: Wed, 23 Sep 2026 19:14:48 +0800 Subject: [PATCH RFC 2/3] dt-bindings: clock: amlogic: Add T7 pre-divider clock IDs Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" Content-Transfer-Encoding: quoted-printable Message-Id: <20260923-meson_refactor_n-v1-2-3a8ce27121a2@amlogic.com> References: <20260923-meson_refactor_n-v1-0-3a8ce27121a2@amlogic.com> In-Reply-To: <20260923-meson_refactor_n-v1-0-3a8ce27121a2@amlogic.com> To: Neil Armstrong , Jerome Brunet , Stephen Boyd , Brian Masney , Kevin Hilman , Martin Blumenstingl , Jerome Brunet , Rob Herring , Krzysztof Kozlowski , Conor Dooley Cc: linux-amlogic@lists.infradead.org, linux-clk@vger.kernel.org, linux-arm-kernel@lists.infradead.org, linux-kernel@vger.kernel.org, devicetree@vger.kernel.org, Jian Hu X-Mailer: b4 0.14.3 X-Developer-Signature: v=1; a=ed25519-sha256; t=1790162143; l=1524; i=jian.hu@amlogic.com; s=20260415; h=from:subject:message-id; bh=y0MWbUJ0faMiTivhM85sj5J18sYEBszLSGsO+sIOCFA=; b=9o8QfE60g+bIqq/2wkTFt/FkpyfPD2otY1SnuQcmVu8S+UxF0kzuuLZ0zwDw0KR6rsycd0FFI 4FTSu5UE/c3DSAXtZcRUDeqdhFYcaQMTLiR0/hR+AiwKWXztK20mW2G X-Developer-Key: i=jian.hu@amlogic.com; a=ed25519; pk=zHUE+rNtH9z+Sb8au1/elWknjFQmy5QDVkBoxleuOIA= X-Endpoint-Received: by B4 Relay for jian.hu@amlogic.com/20260415 with auth_id=735 X-Original-From: Jian Hu Reply-To: jian.hu@amlogic.com From: Jian Hu Add clock IDs for the T7 PLL pre-divider clocks. These IDs are required for the subsequent conversion of the PLL pre-divider into a standalone divider clock following the PLL framework refactoring. Signed-off-by: Jian Hu --- include/dt-bindings/clock/amlogic,t7-pll-clkc.h | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/include/dt-bindings/clock/amlogic,t7-pll-clkc.h b/include/dt-b= indings/clock/amlogic,t7-pll-clkc.h index e2481f2f1163..69c90bc0be0a 100644 --- a/include/dt-bindings/clock/amlogic,t7-pll-clkc.h +++ b/include/dt-bindings/clock/amlogic,t7-pll-clkc.h @@ -9,20 +9,24 @@ /* GP0 */ #define CLKID_GP0_PLL_DCO 0 #define CLKID_GP0_PLL 1 +#define CLKID_GP0_PREDIV 2 =20 /* GP1 */ #define CLKID_GP1_PLL_DCO 0 #define CLKID_GP1_PLL 1 +#define CLKID_GP1_PREDIV 2 =20 /* HIFI */ #define CLKID_HIFI_PLL_DCO 0 #define CLKID_HIFI_PLL 1 +#define CLKID_HIFI_PREDIV 2 =20 /* PCIE */ #define CLKID_PCIE_PLL_DCO 0 #define CLKID_PCIE_PLL_DCO_DIV2 1 #define CLKID_PCIE_PLL_OD 2 #define CLKID_PCIE_PLL 3 +#define CLKID_PCIE_PREDIV 4 =20 /* MPLL */ #define CLKID_MPLL_PREDIV 0 @@ -39,6 +43,7 @@ #define CLKID_HDMI_PLL_DCO 0 #define CLKID_HDMI_PLL_OD 1 #define CLKID_HDMI_PLL 2 +#define CLKID_HDMI_PREDIV 3 =20 /* MCLK */ #define CLKID_MCLK_PLL_DCO 0 @@ -52,5 +57,6 @@ #define CLKID_MCLK_1_DIV2 8 #define CLKID_MCLK_1_PRE 9 #define CLKID_MCLK_1 10 +#define CLKID_MCLK_PREDIV 11 =20 #endif /* __T7_PLL_CLKC_H */ --=20 2.47.1 From nobody Thu Sep 24 12:55:34 2026 Received: from smtp.kernel.org (aws-us-west-2-korg-mail-1.web.codeaurora.org [10.30.226.201]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id D4932495050; Wed, 23 Sep 2026 11:15:45 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=10.30.226.201 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1790162145; cv=none; b=WpxCdQ1w72DWnjhL3/66FR2pB7SbWCVJSHO34i6LNsMqFRJNV2Hq74Xnv1JzvzkI3eNeAkYA3MdTSFIJFlCEroEGo79eZU+p+7jHSjZ7AEu2ChNp6wnrNgmrLQybw0XssfpdgcSt9PxFdp554h7KniEHWuSP6/F+x5qr40ur6aI= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1790162145; c=relaxed/simple; bh=9V/M4QuDb1aTEKAcJYylTQN3hv5JlhRhajwreFSaOrk=; h=From:Date:Subject:MIME-Version:Content-Type:Message-Id:References: In-Reply-To:To:Cc; b=gm0ejJh2bw+gzGuCbzZ46qqClwRTRHaDfKWxSKmSnUiQyUCJ8g5f99+lQl5JUgEut1b4GMBXijZXwS3ldJIF/BF5TkSEFAflyJuYlQSBgtpppDTfC3GWn7MQx1iC0/9zEbI4NgUjV359n47A1gpgSTy5T1Cjg1WdqkuZyAdoOl4= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=kernel.org header.i=@kernel.org header.b=AP128hEA; arc=none smtp.client-ip=10.30.226.201 Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=kernel.org header.i=@kernel.org header.b="AP128hEA" Received: by smtp.kernel.org (Postfix) with ESMTPS id 7420EC2BCFA; Wed, 23 Sep 2026 11:15:45 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=kernel.org; s=k20201202; t=1790162145; bh=9V/M4QuDb1aTEKAcJYylTQN3hv5JlhRhajwreFSaOrk=; h=From:Date:Subject:References:In-Reply-To:To:Cc:Reply-To:From; b=AP128hEAVEZfnKD89oVHKDOlVxOM2sjMKUyKyDCiPZh6q5F7Llj5OqjgmIiSITvth 4SnHV3vktJpYDvnzxexU8FSEYipROctIhtrkwntmc0a2L2/SYZW+Uw1jZucgahdzb6 nGAr0BQQH7IReZoDb01IaAZpGsdOFJhsr2paNGtOmBSjTDP48wYWqe+fAFVhvK8ebW bvC6HzOGjd9mVz73/ixnsC1L2xFZ2D+JGXWFGqb+4D1d5sViGzrVl111oUfdLcIz1I iDOlXmhMk8IakEjGoOIuvesTtB9+Ytygk8pF/aP7Q2UDK6qqDfv535JZxRzlJolGhH CH5xegmVuJh6w== Received: from aws-us-west-2-korg-lkml-1.web.codeaurora.org (localhost.localdomain [127.0.0.1]) by smtp.lore.kernel.org (Postfix) with ESMTP id 56455C9830B; Wed, 23 Sep 2026 11:15:45 +0000 (UTC) From: Jian Hu via B4 Relay Date: Wed, 23 Sep 2026 19:14:49 +0800 Subject: [PATCH RFC 3/3] clk: meson: t7: Model PLL pre-divider as a divider clock Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" Content-Transfer-Encoding: quoted-printable Message-Id: <20260923-meson_refactor_n-v1-3-3a8ce27121a2@amlogic.com> References: <20260923-meson_refactor_n-v1-0-3a8ce27121a2@amlogic.com> In-Reply-To: <20260923-meson_refactor_n-v1-0-3a8ce27121a2@amlogic.com> To: Neil Armstrong , Jerome Brunet , Stephen Boyd , Brian Masney , Kevin Hilman , Martin Blumenstingl , Jerome Brunet , Rob Herring , Krzysztof Kozlowski , Conor Dooley Cc: linux-amlogic@lists.infradead.org, linux-clk@vger.kernel.org, linux-arm-kernel@lists.infradead.org, linux-kernel@vger.kernel.org, devicetree@vger.kernel.org, Jian Hu X-Mailer: b4 0.14.3 X-Developer-Signature: v=1; a=ed25519-sha256; t=1790162143; l=10156; i=jian.hu@amlogic.com; s=20260415; h=from:subject:message-id; bh=YqMo5icc69xckYBk4DLB/d4LRHXA7luoRj0+rYDAwok=; b=qvttVB6Wt2KwUtggaJdYIPBILVXCd2fyS/FGTvSDgbP/I6xP6IGz7a/ozA7UWV+8gM4OTCg+q +TAW7V5swB1Al3I4plkBLDEFqJ7bqjSEhE/oOn/o40mkh1IU/gxtdqw X-Developer-Key: i=jian.hu@amlogic.com; a=ed25519; pk=zHUE+rNtH9z+Sb8au1/elWknjFQmy5QDVkBoxleuOIA= X-Endpoint-Received: by B4 Relay for jian.hu@amlogic.com/20260415 with auth_id=735 X-Original-From: Jian Hu Reply-To: jian.hu@amlogic.com From: Jian Hu Replace the dedicated PLL pre-divider with a standalone divider clock. The PLL DCO now takes the pre-divider clock as its parent instead of the input clock directly. Signed-off-by: Jian Hu --- drivers/clk/meson/t7-pll.c | 183 ++++++++++++++++++++++++++++++++++-------= ---- 1 file changed, 141 insertions(+), 42 deletions(-) diff --git a/drivers/clk/meson/t7-pll.c b/drivers/clk/meson/t7-pll.c index 0a622f45fa36..049f0c879c45 100644 --- a/drivers/clk/meson/t7-pll.c +++ b/drivers/clk/meson/t7-pll.c @@ -71,6 +71,34 @@ #define MCLK_PLL_CNTL4 0x10 #define MCLK_PLL_STS 0x14 =20 +static const struct clk_div_table t7_prediv_div_table[] =3D { + { .val =3D 1, .div =3D 1 }, + { /* sentinel */ } +}; + +static struct clk_regmap t7_gp0_prediv =3D { + .data =3D &(struct clk_regmap_div_data){ + .offset =3D GP0PLL_CTRL0, + .shift =3D 10, + .width =3D 5, + .table =3D t7_prediv_div_table, + /* + * The hardware reset value is 0. Allow it during clock registration + * to avoid a warning from the common divider code. + * set_rate() will program the valid divider value (1). + */ + .flags =3D CLK_DIVIDER_ALLOW_ZERO, + }, + .hw.init =3D &(struct clk_init_data) { + .name =3D "gp0_prediv", + .ops =3D &clk_regmap_divider_ops, + .parent_data =3D &(const struct clk_parent_data) { + .fw_name =3D "in0", + }, + .num_parents =3D 1, + }, +}; + static const struct pll_mult_range t7_media_pll_mult_range =3D { .min =3D 125, .max =3D 250, @@ -97,11 +125,6 @@ static struct clk_regmap t7_gp0_pll_dco =3D { .shift =3D 0, .width =3D 8, }, - .n =3D { - .reg_off =3D GP0PLL_CTRL0, - .shift =3D 10, - .width =3D 5, - }, .l =3D { .reg_off =3D GP0PLL_STS, .shift =3D 31, @@ -119,8 +142,8 @@ static struct clk_regmap t7_gp0_pll_dco =3D { .hw.init =3D &(struct clk_init_data){ .name =3D "gp0_pll_dco", .ops =3D &meson_clk_pll_ops, - .parent_data =3D &(const struct clk_parent_data) { - .fw_name =3D "in0", + .parent_hws =3D (const struct clk_hw *[]) { + &t7_gp0_prediv.hw }, .num_parents =3D 1, }, @@ -159,6 +182,25 @@ static const struct reg_sequence t7_gp1_init_regs[] = =3D { { .reg =3D GP1PLL_CTRL3, .def =3D 0x00000000 }, }; =20 +static struct clk_regmap t7_gp1_prediv =3D { + .data =3D &(struct clk_regmap_div_data){ + .offset =3D GP1PLL_CTRL0, + .shift =3D 16, + .width =3D 5, + .table =3D t7_prediv_div_table, + /* Same rationale as gp0_prediv. */ + .flags =3D CLK_DIVIDER_ALLOW_ZERO, + }, + .hw.init =3D &(struct clk_init_data) { + .name =3D "gp1_prediv", + .ops =3D &clk_regmap_divider_ops, + .parent_data =3D &(const struct clk_parent_data) { + .fw_name =3D "in0", + }, + .num_parents =3D 1, + }, +}; + static struct clk_regmap t7_gp1_pll_dco =3D { .data =3D &(struct meson_clk_pll_data){ .en =3D { @@ -171,11 +213,6 @@ static struct clk_regmap t7_gp1_pll_dco =3D { .shift =3D 0, .width =3D 8, }, - .n =3D { - .reg_off =3D GP1PLL_CTRL0, - .shift =3D 16, - .width =3D 5, - }, .l =3D { .reg_off =3D GP1PLL_STS, .shift =3D 31, @@ -193,8 +230,8 @@ static struct clk_regmap t7_gp1_pll_dco =3D { .hw.init =3D &(struct clk_init_data){ .name =3D "gp1_pll_dco", .ops =3D &meson_clk_pll_ops, - .parent_data =3D &(const struct clk_parent_data) { - .fw_name =3D "in0", + .parent_hws =3D (const struct clk_hw *[]) { + &t7_gp1_prediv.hw }, .num_parents =3D 1, }, @@ -227,6 +264,25 @@ static const struct reg_sequence t7_hifi_init_regs[] = =3D { { .reg =3D HIFIPLL_CTRL6, .def =3D 0x56540000 } }; =20 +static struct clk_regmap t7_hifi_prediv =3D { + .data =3D &(struct clk_regmap_div_data){ + .offset =3D HIFIPLL_CTRL0, + .shift =3D 10, + .width =3D 5, + .table =3D t7_prediv_div_table, + /* Same rationale as gp0_prediv. */ + .flags =3D CLK_DIVIDER_ALLOW_ZERO, + }, + .hw.init =3D &(struct clk_init_data) { + .name =3D "hifi_prediv", + .ops =3D &clk_regmap_divider_ops, + .parent_data =3D &(const struct clk_parent_data) { + .fw_name =3D "in0", + }, + .num_parents =3D 1, + }, +}; + static struct clk_regmap t7_hifi_pll_dco =3D { .data =3D &(struct meson_clk_pll_data){ .en =3D { @@ -239,11 +295,6 @@ static struct clk_regmap t7_hifi_pll_dco =3D { .shift =3D 0, .width =3D 8, }, - .n =3D { - .reg_off =3D HIFIPLL_CTRL0, - .shift =3D 10, - .width =3D 5, - }, .frac =3D { .reg_off =3D HIFIPLL_CTRL1, .shift =3D 0, @@ -267,8 +318,8 @@ static struct clk_regmap t7_hifi_pll_dco =3D { .hw.init =3D &(struct clk_init_data){ .name =3D "hifi_pll_dco", .ops =3D &meson_clk_pll_ops, - .parent_data =3D &(const struct clk_parent_data) { - .fw_name =3D "in0", + .parent_hws =3D (const struct clk_hw *[]) { + &t7_hifi_prediv.hw }, .num_parents =3D 1, }, @@ -312,6 +363,25 @@ static const struct reg_sequence t7_pcie_pll_init_regs= [] =3D { { .reg =3D PCIEPLL_CTRL2, .def =3D 0x00001000 } }; =20 +static struct clk_regmap t7_pcie_prediv =3D { + .data =3D &(struct clk_regmap_div_data){ + .offset =3D PCIEPLL_CTRL0, + .shift =3D 10, + .width =3D 5, + .table =3D t7_prediv_div_table, + /* Same rationale as gp0_prediv. */ + .flags =3D CLK_DIVIDER_ALLOW_ZERO, + }, + .hw.init =3D &(struct clk_init_data) { + .name =3D "pcie_prediv", + .ops =3D &clk_regmap_divider_ops, + .parent_data =3D &(const struct clk_parent_data) { + .fw_name =3D "in0", + }, + .num_parents =3D 1, + }, +}; + static struct clk_regmap t7_pcie_pll_dco =3D { .data =3D &(struct meson_clk_pll_data){ .en =3D { @@ -324,11 +394,6 @@ static struct clk_regmap t7_pcie_pll_dco =3D { .shift =3D 0, .width =3D 8, }, - .n =3D { - .reg_off =3D PCIEPLL_CTRL0, - .shift =3D 10, - .width =3D 5, - }, .l =3D { .reg_off =3D PCIEPLL_CTRL0, .shift =3D 31, @@ -345,8 +410,8 @@ static struct clk_regmap t7_pcie_pll_dco =3D { .hw.init =3D &(struct clk_init_data){ .name =3D "pcie_pll_dco", .ops =3D &meson_clk_pcie_pll_ops, - .parent_data =3D &(const struct clk_parent_data) { - .fw_name =3D "in0", + .parent_hws =3D (const struct clk_hw *[]) { + &t7_pcie_prediv.hw }, .num_parents =3D 1, }, @@ -633,6 +698,25 @@ static const struct reg_sequence t7_hdmi_init_regs[] = =3D { { .reg =3D HDMIPLL_CTRL6, .def =3D 0x56540000 } }; =20 +static struct clk_regmap t7_hdmi_prediv =3D { + .data =3D &(struct clk_regmap_div_data){ + .offset =3D HDMIPLL_CTRL0, + .shift =3D 10, + .width =3D 5, + .table =3D t7_prediv_div_table, + /* Same rationale as gp0_prediv. */ + .flags =3D CLK_DIVIDER_ALLOW_ZERO, + }, + .hw.init =3D &(struct clk_init_data) { + .name =3D "hdmi_prediv", + .ops =3D &clk_regmap_divider_ops, + .parent_data =3D &(const struct clk_parent_data) { + .fw_name =3D "in0", + }, + .num_parents =3D 1, + }, +}; + static struct clk_regmap t7_hdmi_pll_dco =3D { .data =3D &(struct meson_clk_pll_data){ .en =3D { @@ -645,11 +729,6 @@ static struct clk_regmap t7_hdmi_pll_dco =3D { .shift =3D 0, .width =3D 9, }, - .n =3D { - .reg_off =3D HDMIPLL_CTRL0, - .shift =3D 10, - .width =3D 5, - }, .l =3D { .reg_off =3D HDMIPLL_CTRL0, .shift =3D 31, @@ -667,8 +746,8 @@ static struct clk_regmap t7_hdmi_pll_dco =3D { .hw.init =3D &(struct clk_init_data){ .name =3D "hdmi_pll_dco", .ops =3D &meson_clk_pll_ops, - .parent_data =3D (const struct clk_parent_data []) { - { .fw_name =3D "in0", } + .parent_hws =3D (const struct clk_hw *[]) { + &t7_hdmi_prediv.hw }, .num_parents =3D 1, }, @@ -722,6 +801,25 @@ static const struct reg_sequence t7_mclk_init_regs[] = =3D { { .reg =3D MCLK_PLL_CNTL4, .def =3D 0x00180303 }, }; =20 +static struct clk_regmap t7_mclk_prediv =3D { + .data =3D &(struct clk_regmap_div_data){ + .offset =3D MCLK_PLL_CNTL0, + .shift =3D 16, + .width =3D 5, + .table =3D t7_prediv_div_table, + /* Same rationale as gp0_prediv. */ + .flags =3D CLK_DIVIDER_ALLOW_ZERO, + }, + .hw.init =3D &(struct clk_init_data) { + .name =3D "mclk_prediv", + .ops =3D &clk_regmap_divider_ops, + .parent_data =3D &(const struct clk_parent_data) { + .fw_name =3D "in0", + }, + .num_parents =3D 1, + }, +}; + static struct clk_regmap t7_mclk_pll_dco =3D { .data =3D &(struct meson_clk_pll_data){ .en =3D { @@ -734,11 +832,6 @@ static struct clk_regmap t7_mclk_pll_dco =3D { .shift =3D 0, .width =3D 8, }, - .n =3D { - .reg_off =3D MCLK_PLL_CNTL0, - .shift =3D 16, - .width =3D 5, - }, .l =3D { .reg_off =3D MCLK_PLL_CNTL0, .shift =3D 31, @@ -761,8 +854,8 @@ static struct clk_regmap t7_mclk_pll_dco =3D { .hw.init =3D &(struct clk_init_data){ .name =3D "mclk_pll_dco", .ops =3D &meson_clk_pll_ops, - .parent_data =3D &(const struct clk_parent_data) { - .fw_name =3D "in0", + .parent_hws =3D (const struct clk_hw *[]) { + &t7_mclk_prediv.hw }, .num_parents =3D 1, }, @@ -939,21 +1032,25 @@ static struct clk_regmap t7_mclk_1 =3D { }; =20 static struct clk_hw *t7_gp0_hw_clks[] =3D { + [CLKID_GP0_PREDIV] =3D &t7_gp0_prediv.hw, [CLKID_GP0_PLL_DCO] =3D &t7_gp0_pll_dco.hw, [CLKID_GP0_PLL] =3D &t7_gp0_pll.hw, }; =20 static struct clk_hw *t7_gp1_hw_clks[] =3D { + [CLKID_GP1_PREDIV] =3D &t7_gp1_prediv.hw, [CLKID_GP1_PLL_DCO] =3D &t7_gp1_pll_dco.hw, [CLKID_GP1_PLL] =3D &t7_gp1_pll.hw, }; =20 static struct clk_hw *t7_hifi_hw_clks[] =3D { + [CLKID_HIFI_PREDIV] =3D &t7_hifi_prediv.hw, [CLKID_HIFI_PLL_DCO] =3D &t7_hifi_pll_dco.hw, [CLKID_HIFI_PLL] =3D &t7_hifi_pll.hw, }; =20 static struct clk_hw *t7_pcie_hw_clks[] =3D { + [CLKID_PCIE_PREDIV] =3D &t7_pcie_prediv.hw, [CLKID_PCIE_PLL_DCO] =3D &t7_pcie_pll_dco.hw, [CLKID_PCIE_PLL_DCO_DIV2] =3D &t7_pcie_pll_dco_div2.hw, [CLKID_PCIE_PLL_OD] =3D &t7_pcie_pll_od.hw, @@ -973,12 +1070,14 @@ static struct clk_hw *t7_mpll_hw_clks[] =3D { }; =20 static struct clk_hw *t7_hdmi_hw_clks[] =3D { + [CLKID_HDMI_PREDIV] =3D &t7_hdmi_prediv.hw, [CLKID_HDMI_PLL_DCO] =3D &t7_hdmi_pll_dco.hw, [CLKID_HDMI_PLL_OD] =3D &t7_hdmi_pll_od.hw, [CLKID_HDMI_PLL] =3D &t7_hdmi_pll.hw, }; =20 static struct clk_hw *t7_mclk_hw_clks[] =3D { + [CLKID_MCLK_PREDIV] =3D &t7_mclk_prediv.hw, [CLKID_MCLK_PLL_DCO] =3D &t7_mclk_pll_dco.hw, [CLKID_MCLK_PRE] =3D &t7_mclk_pre_od.hw, [CLKID_MCLK_PLL] =3D &t7_mclk_pll.hw, --=20 2.47.1