[PATCH 0/3] Apple M1 clock gate driver

From: Sven Peter
Date: Mon May 24 2021 - 14:28:01 EST



Hi,

This series adds support for the clock gates present in Apple's SoCs such as
the M1.

These SoCs have various clock gates for their peripherals usually located in
one or two MMIO regions. Each clock gate is a single 32 bit register which
contains bits for the requested and the actual mode. The mode is represented by
four bits. We however only care about "everything enabled" (0b1111) and
"everything disabled" (0b000) for now. The other modes are probably different
low-power states which don't even seem to be used by MacOS. The actual power
management is located in a different region (and probably handled by a separate
processor on the M1).

Additionally, these clocks have a topology that is usually specified in Apple's
Device Tree. As far as I can tell most Linux drivers seem to encode this topology
directly in the source code though. Despite this, we would still like to encode
the topology in the device tree itself:

Apple seems to only change HW blocks when they have a very good reason and even
then they seem to keep the changes minimal. This specific clock gate MMIO block
has already been used in the Apple A7 released in 2013. The only differences
since then are the available clocks (which can be identified by a simple offset)
and their topology.

It's likely that Apple will still use this block in future SoCs as well. By
encoding the clock gate topology inside the device tree as well we can use a
single driver and only need updates to the device tree once they are released.
This might allow end users to already run their favorite distribution by just
updating the bootloader with a new device tree instead of having to wait until
the new topology is integrated into their distro kernel.

Additionally, the driver itself can be kept very simple and not much code needs
to be duplicated and then updated for each new SoC between various consumers of
these device tree nodes (Linux, u-boot, and OpenBSD for now).


This series therefore creates a single device tree node for each clock gate.
This unfortunately maps a whole page out of which only a single register will
be used for each node.

The other alternative I considered was to create a syscon/simple-mfd node
and have the clock nodes as children. The gates would then use a regmap which
would only require a single entry in the pagetable for all clocks. I decided
against this option since the clock gate MMIO region actually isn't a
multi-function device.

I'll also gladly implement other solutions - especially if there is a way to
keep the clock toplogy inside the device tree without having to create a
pagetable entry for every single clock node.

Best,


Sven

Sven Peter (3):
dt-bindings: clock: add DT bindings for apple,gate-clock
clk: add support for gate clocks on Apple SoCs
arm64: apple: add uart gate clocks

.../bindings/clock/apple,gate-clock.yaml | 60 +++++++
MAINTAINERS | 2 +
arch/arm64/boot/dts/apple/t8103.dtsi | 36 ++++-
drivers/clk/Kconfig | 12 ++
drivers/clk/Makefile | 1 +
drivers/clk/clk-apple-gate.c | 152 ++++++++++++++++++
6 files changed, 262 insertions(+), 1 deletion(-)
create mode 100644 Documentation/devicetree/bindings/clock/apple,gate-clock.yaml
create mode 100644 drivers/clk/clk-apple-gate.c

--
2.25.1