[PATCH net-next v8 15/15] dpll: sit9531x: allow the device tree to override two board facts
From: Ali Rouhi
Date: Wed Sep 02 2026 - 17:59:06 EST
From: Oleg Zadorozhnyi <Oleg.Zadorozhnyi@xxxxxxxxxxxxxxxxx>
Two things the driver reads from the chip can be wrong on a board, and
neither has anywhere else to come from.
The VCO frequency is derived from the feedback divider, which is exact
while the loop runs but not while a PLL sits in free-run with a divider
the configuration never programmed; a board that knows its own VCO can
state it. The output-to-PLL routing is read from the output map
registers, which describe what the loaded configuration did -- and a board
whose outputs are fanned out differently from what those registers imply
can state that too.
Both are optional. Absent the properties the driver behaves exactly as
before, deriving one and reading the other.
Signed-off-by: Oleg Zadorozhnyi <Oleg.Zadorozhnyi@xxxxxxxxxxxxxxxxx>
Assisted-by: Claude:claude-4-opus [chat]
Signed-off-by: Ali Rouhi <arouhi@xxxxxxxxxx>
---
drivers/dpll/sit9531x/core.c | 39 ++++++++++++++++++++++++++++++++++++
1 file changed, 39 insertions(+)
diff --git a/drivers/dpll/sit9531x/core.c b/drivers/dpll/sit9531x/core.c
index c3d7c4851549..d75ac02047b5 100644
--- a/drivers/dpll/sit9531x/core.c
+++ b/drivers/dpll/sit9531x/core.c
@@ -3158,6 +3158,43 @@ static u64 sit9531x_derive_clock_id(struct sit9531x_dev *sitdev)
return clkid;
}
+/*
+ * Board-config overrides for fixed efuse/blob routing the chip registers do
+ * not describe unambiguously. Absent properties leave pll_fvco[] zeroed
+ * (derive from DIVN) and out_pll_map_valid false (use the OUT_MAP registers).
+ */
+static void sit9531x_parse_board_config(struct sit9531x_dev *sitdev)
+{
+ u32 map[SIT9531X_MAX_OUTPUTS];
+ int n, i;
+
+ device_property_read_u64_array(sitdev->dev, "sitime,pll-fvco",
+ sitdev->pll_fvco, SIT9531X_NUM_PLLS);
+
+ if (!device_property_present(sitdev->dev, "sitime,output-pll-map"))
+ return;
+
+ /*
+ * Any 1..MAX_OUTPUTS length is accepted so the 8-output SiT95317 need
+ * not pad to 12; variant detection has not run yet and entries past
+ * the detected num_outputs are never indexed. Trailing entries of a
+ * short map must read as unmapped rather than 0 (== PLLA), which
+ * would mark unrouted outputs active in sit9531x_out_state_fetch().
+ */
+ memset(sitdev->out_pll_map, SIT9531X_OUT_PLL_UNMAPPED,
+ sizeof(sitdev->out_pll_map));
+
+ n = device_property_count_u32(sitdev->dev, "sitime,output-pll-map");
+ if (n <= 0 || n > SIT9531X_MAX_OUTPUTS ||
+ device_property_read_u32_array(sitdev->dev, "sitime,output-pll-map",
+ map, n))
+ return;
+
+ for (i = 0; i < n; i++)
+ sitdev->out_pll_map[i] = map[i];
+ sitdev->out_pll_map_valid = true;
+}
+
int sit9531x_dev_probe(struct sit9531x_dev *sitdev)
{
struct clk *xtal_clk;
@@ -3192,6 +3229,8 @@ int sit9531x_dev_probe(struct sit9531x_dev *sitdev)
if (sitdev->reset_gpio)
fsleep(10000); /* internal boot after release */
+ sit9531x_parse_board_config(sitdev);
+
rc = sit9531x_read_variant_id(sitdev, &variant_id);
if (rc)
return rc;
--
2.43.0