* [PATCH 0/2] clk: Add basic register clock controller
@ 2023-04-14 18:12 David Yang
2023-04-14 18:12 ` [PATCH 1/2] dt-bindings: clock: Add reg-clock-controller David Yang
2023-04-14 18:13 ` [PATCH 2/2] clk: Add basic register clock controller David Yang
0 siblings, 2 replies; 9+ messages in thread
From: David Yang @ 2023-04-14 18:12 UTC (permalink / raw)
To: linux-clk
Cc: David Yang, Michael Turquette, Stephen Boyd, Rob Herring,
Krzysztof Kozlowski, devicetree, linux-kernel
These clocks were provided in `include/linux/clk-provider.h`, but lacks DT
bindings. Add a clock controller to avoid operation conflict on same
register.
*** BLURB HERE ***
David Yang (2):
dt-bindings: clock: Add reg-clock-controller
clk: Add basic register clock controller
.../bindings/clock/reg-clock-controller.yaml | 245 +++++++
drivers/clk/Makefile | 1 +
drivers/clk/clk-reg.c | 638 ++++++++++++++++++
3 files changed, 884 insertions(+)
create mode 100644 Documentation/devicetree/bindings/clock/reg-clock-controller.yaml
create mode 100644 drivers/clk/clk-reg.c
base-commit: 7a934f4bd7d6f9da84c8812da3ba42ee10f5778e
--
2.39.2
^ permalink raw reply [flat|nested] 9+ messages in thread
* [PATCH 1/2] dt-bindings: clock: Add reg-clock-controller
2023-04-14 18:12 [PATCH 0/2] clk: Add basic register clock controller David Yang
@ 2023-04-14 18:12 ` David Yang
2023-04-14 21:08 ` Krzysztof Kozlowski
` (2 more replies)
2023-04-14 18:13 ` [PATCH 2/2] clk: Add basic register clock controller David Yang
1 sibling, 3 replies; 9+ messages in thread
From: David Yang @ 2023-04-14 18:12 UTC (permalink / raw)
To: linux-clk
Cc: David Yang, Michael Turquette, Stephen Boyd, Rob Herring,
Krzysztof Kozlowski, devicetree, linux-kernel
Add DT bindings documentation for reg-clock-controller, collection of
basic clocks common to many platforms.
Signed-off-by: David Yang <mmyangfl@gmail.com>
---
.../bindings/clock/reg-clock-controller.yaml | 245 ++++++++++++++++++
1 file changed, 245 insertions(+)
create mode 100644 Documentation/devicetree/bindings/clock/reg-clock-controller.yaml
diff --git a/Documentation/devicetree/bindings/clock/reg-clock-controller.yaml b/Documentation/devicetree/bindings/clock/reg-clock-controller.yaml
new file mode 100644
index 000000000000..a6a7e0b05821
--- /dev/null
+++ b/Documentation/devicetree/bindings/clock/reg-clock-controller.yaml
@@ -0,0 +1,245 @@
+# SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause)
+%YAML 1.2
+---
+$id: http://devicetree.org/schemas/clock/reg-clock-controller.yaml#
+$schema: http://devicetree.org/meta-schemas/core.yaml#
+
+title: Simple straight-forward register-based clocks
+
+maintainers:
+ - David Yang <mmyangfl@gmail.com>
+
+description: |
+ Basic clocks common to many platforms.
+
+ If your clocks don't fit into these catagories, simply create your clock
+ controller. This driver normally work well with other controllers as long as
+ they operate on different registers.
+
+ See linux/clk-provider.h for details about properties for each type of clock.
+
+properties:
+ compatible:
+ enum:
+ - reg-clock-controller
+
+ ranges: true
+
+ '#address-cells':
+ const: 1
+
+ '#size-cells':
+ const: 1
+
+required:
+ - compatible
+ - ranges
+ - '#address-cells'
+ - '#size-cells'
+
+patternProperties:
+ ".*gate-clock@.*":
+ type: object
+
+ description: |
+ Clock which can gate its output.
+
+ properties:
+ compatible:
+ const: gate-clock
+
+ reg:
+ maxItems: 1
+
+ '#clock-cells':
+ const: 0
+
+ clocks:
+ maxItems: 1
+ description:
+ Parent clock.
+
+ clock-output-name:
+ maxItems: 1
+
+ bit-index:
+ $ref: /schemas/types.yaml#/definitions/uint32
+ description:
+ Bit index which controls the output.
+
+ required:
+ - compatible
+ - reg
+ - '#clock-cells'
+ - bit-index
+
+ additionalProperties: false
+
+ ".*divider-clock@.*":
+ type: object
+
+ description: |
+ Clock with an adjustable divider affecting its output frequency.
+
+ properties:
+ compatible:
+ const: divider-clock
+
+ reg:
+ maxItems: 1
+
+ '#clock-cells':
+ const: 0
+
+ clocks:
+ description:
+ Parent clocks.
+
+ clock-output-name:
+ maxItems: 1
+
+ shift:
+ $ref: /schemas/types.yaml#/definitions/uint32
+ description:
+ Shift to the divider bit field.
+
+ width:
+ $ref: /schemas/types.yaml#/definitions/uint32
+ description:
+ Width of the divider bit field.
+
+ dividers:
+ $ref: /schemas/types.yaml#/definitions/uint32-array
+ description:
+ Array of value/divider pairs.
+
+ required:
+ - compatible
+ - reg
+ - '#clock-cells'
+ - shift
+ - width
+
+ additionalProperties: false
+
+ ".*mux-clock@.*":
+ type: object
+
+ description: |
+ Clock with multiple selectable parents.
+
+ properties:
+ compatible:
+ const: mux-clock
+
+ reg:
+ maxItems: 1
+
+ '#clock-cells':
+ const: 0
+
+ clocks:
+ minItems: 1
+ description:
+ Parent clock.
+
+ clock-output-name:
+ maxItems: 1
+
+ shift:
+ $ref: /schemas/types.yaml#/definitions/uint32
+ description:
+ Shift to multiplexer bit field.
+
+ mask:
+ $ref: /schemas/types.yaml#/definitions/uint32
+ description:
+ Mask of mutliplexer bit field.
+
+ table:
+ $ref: /schemas/types.yaml#/definitions/uint32-array
+ description:
+ Array of register values corresponding to the parent index.
+
+ required:
+ - compatible
+ - reg
+ - '#clock-cells'
+ - shift
+ - mask
+
+ additionalProperties: false
+
+ ".*fractional-divider-clock@.*":
+ type: object
+
+ description: |
+ Clock with adjustable fractional divider affecting its output frequency.
+
+ properties:
+ compatible:
+ const: fractional_divider-clock
+
+ reg:
+ maxItems: 1
+
+ '#clock-cells':
+ const: 0
+
+ clocks:
+ maxItems: 1
+ description:
+ Parent clock.
+
+ clock-output-name:
+ maxItems: 1
+
+ numerator-shift:
+ $ref: /schemas/types.yaml#/definitions/uint32
+ description:
+ Shift to the numerator bit field.
+
+ numerator-width:
+ $ref: /schemas/types.yaml#/definitions/uint32
+ description:
+ Width of the numerator bit field.
+
+ denominator-shift:
+ $ref: /schemas/types.yaml#/definitions/uint32
+ description:
+ Shift to the denominator bit field.
+
+ denominator-width:
+ $ref: /schemas/types.yaml#/definitions/uint32
+ description:
+ Width of the denominator bit field.
+
+ required:
+ - compatible
+ - reg
+ - '#clock-cells'
+ - numerator-shift
+ - numerator-width
+ - denominator-shift
+ - denominator-width
+
+ additionalProperties: false
+
+additionalProperties: true
+
+examples:
+ - |
+ clks: reg-clk-ctrl@ffff0000 {
+ compatible = "reg-clock-controller";
+ #address-cells = <1>;
+ #size-cells = <1>;
+ ranges = <0 0xffff0000 0x1000>;
+
+ my_clk: gate-clock@cc-3 {
+ compatible = "gate-clock";
+ #clock-cells = <0>;
+ reg = <0xcc 4>;
+ bit-index = <3>;
+ clock-output-name = "my-clk";
+ };
+ };
--
2.39.2
^ permalink raw reply related [flat|nested] 9+ messages in thread
* [PATCH 2/2] clk: Add basic register clock controller
2023-04-14 18:12 [PATCH 0/2] clk: Add basic register clock controller David Yang
2023-04-14 18:12 ` [PATCH 1/2] dt-bindings: clock: Add reg-clock-controller David Yang
@ 2023-04-14 18:13 ` David Yang
1 sibling, 0 replies; 9+ messages in thread
From: David Yang @ 2023-04-14 18:13 UTC (permalink / raw)
To: linux-clk
Cc: David Yang, Michael Turquette, Stephen Boyd, Rob Herring,
Krzysztof Kozlowski, devicetree, linux-kernel, Philipp Zabel
These clocks were provided in `include/linux/clk-provider.h`, but lacks DT
bindings. Add a clock controller to avoid operation conflict on same
register.
Signed-off-by: David Yang <mmyangfl@gmail.com>
---
drivers/clk/Makefile | 1 +
drivers/clk/clk-reg.c | 638 ++++++++++++++++++++++++++++++++++++++++++
2 files changed, 639 insertions(+)
create mode 100644 drivers/clk/clk-reg.c
diff --git a/drivers/clk/Makefile b/drivers/clk/Makefile
index e3ca0d058a25..9468b2028a5b 100644
--- a/drivers/clk/Makefile
+++ b/drivers/clk/Makefile
@@ -15,6 +15,7 @@ obj-$(CONFIG_COMMON_CLK) += clk-fractional-divider.o
obj-$(CONFIG_COMMON_CLK) += clk-gpio.o
ifeq ($(CONFIG_OF), y)
obj-$(CONFIG_COMMON_CLK) += clk-conf.o
+obj-$(CONFIG_COMMON_CLK) += clk-reg.o
endif
# hardware specific clock types
diff --git a/drivers/clk/clk-reg.c b/drivers/clk/clk-reg.c
new file mode 100644
index 000000000000..a115921a9cbd
--- /dev/null
+++ b/drivers/clk/clk-reg.c
@@ -0,0 +1,638 @@
+// SPDX-License-Identifier: GPL-2.0-or-later OR MIT
+/*
+ * Copyright (c) 2023 David Yang
+ *
+ * Simple straight-forward register clocks bindings
+ */
+
+#include <linux/clk.h>
+#include <linux/clk-provider.h>
+#include <linux/device.h>
+#include <linux/err.h>
+#include <linux/io.h>
+#include <linux/kernel.h>
+#include <linux/of.h>
+#include <linux/of_address.h>
+#include <linux/of_clk.h>
+#include <linux/platform_device.h>
+#include <linux/reset-controller.h>
+#include <linux/slab.h>
+
+struct regclk_ctrl {
+ spinlock_t lock;
+
+ void __iomem *base;
+ struct reset_controller_dev rcdev;
+ bool rst_set_to_disable;
+};
+
+struct regclk_flag {
+ const char *prop;
+ unsigned long flag;
+};
+
+static const struct regclk_flag regclk_flags[] = {
+ { "set-rate-gate", CLK_SET_RATE_GATE },
+ { "set-parent-gate", CLK_SET_PARENT_GATE },
+ { "set-rate-parent", CLK_SET_RATE_PARENT },
+ { "ignore-unused", CLK_IGNORE_UNUSED },
+ { "get-rate-nocache", CLK_GET_RATE_NOCACHE },
+ { "set-rate-no-reparent", CLK_SET_RATE_NO_REPARENT },
+ { "get-accuracy-nocache", CLK_GET_ACCURACY_NOCACHE },
+ { "recalc-new-rates", CLK_RECALC_NEW_RATES },
+ { "set-rate-ungate", CLK_SET_RATE_UNGATE },
+ { "critical", CLK_IS_CRITICAL },
+ { "ops-parent-enable", CLK_OPS_PARENT_ENABLE },
+ { "duty-cycle-parent", CLK_DUTY_CYCLE_PARENT },
+ { }
+};
+
+static const struct regclk_flag regclk_gate_flags[] = {
+ { "set-to-disable", CLK_GATE_SET_TO_DISABLE },
+ { "hiword-mask", CLK_GATE_HIWORD_MASK },
+ { "big-endian", CLK_GATE_BIG_ENDIAN },
+ { }
+};
+
+static const struct regclk_flag regclk_divider_flags[] = {
+ { "one-based", CLK_DIVIDER_ONE_BASED },
+ { "power-of-two", CLK_DIVIDER_POWER_OF_TWO },
+ { "allow-zero", CLK_DIVIDER_ALLOW_ZERO },
+ { "hiword-mask", CLK_DIVIDER_HIWORD_MASK },
+ { "round-closest", CLK_DIVIDER_ROUND_CLOSEST },
+ { "read-only", CLK_DIVIDER_READ_ONLY },
+ { "max-at-zero", CLK_DIVIDER_MAX_AT_ZERO },
+ { "big-endian", CLK_DIVIDER_BIG_ENDIAN },
+ { }
+};
+
+static const struct regclk_flag regclk_mux_flags[] = {
+ { "index-one", CLK_MUX_INDEX_ONE },
+ { "index-bit", CLK_MUX_INDEX_BIT },
+ { "hiword-mask", CLK_MUX_HIWORD_MASK },
+ { "read-only", CLK_MUX_READ_ONLY },
+ { "round-closest", CLK_MUX_ROUND_CLOSEST },
+ { "big-endian", CLK_MUX_BIG_ENDIAN },
+ { }
+};
+
+static const struct regclk_flag regclk_fractional_divider_flags[] = {
+ { "zero-based", CLK_FRAC_DIVIDER_ZERO_BASED },
+ { "big-endian", CLK_FRAC_DIVIDER_BIG_ENDIAN },
+ { "power-of-two-ps", CLK_FRAC_DIVIDER_POWER_OF_TWO_PS },
+ { }
+};
+
+static unsigned long
+regclk_get_flags(struct device_node *np, const struct regclk_flag *defs)
+{
+ unsigned long flags = 0;
+
+ for (int i = 0; defs[i].prop; i++)
+ if (of_property_read_bool(np, defs[i].prop))
+ flags |= defs[i].flag;
+
+ return flags;
+}
+
+static const char *regclk_name(struct device_node *np)
+{
+ const char *name;
+
+ if (!of_property_read_string(np, "clock-output-name", &name))
+ return name;
+
+ return of_node_full_name(np);
+}
+
+static struct clk_hw *
+regclk_register_gate(struct device_node *np, struct regclk_ctrl *priv)
+{
+ const char *name;
+ const char *parent_name;
+ unsigned long flags;
+ void __iomem *reg;
+ u32 bit_idx;
+ unsigned long clk_gate_flags;
+
+ const char *property;
+ struct clk_hw *hw;
+ struct clk_hw *retptr;
+ int ret;
+
+ reg = of_iomap(np, 0);
+ if (!reg)
+ return ERR_PTR(-ENOMEM);
+ name = regclk_name(np);
+ if (!name)
+ return ERR_PTR(-EINVAL);
+
+ property = "bit-index";
+ if (of_property_read_u32(np, property, &bit_idx))
+ goto err_property;
+
+ parent_name = of_clk_get_parent_name(np, 0);
+ flags = regclk_get_flags(np, regclk_flags);
+ clk_gate_flags = regclk_get_flags(np, regclk_gate_flags);
+
+ hw = __clk_hw_register_gate(NULL, np, name, parent_name,
+ NULL, NULL, flags, reg, bit_idx,
+ clk_gate_flags, &priv->lock);
+ if (IS_ERR(hw))
+ return hw;
+
+ ret = of_clk_add_hw_provider(np, of_clk_hw_simple_get, hw);
+ if (ret) {
+ retptr = ERR_PTR(ret);
+ goto err_register;
+ }
+
+ return hw;
+
+err_register:
+ clk_hw_unregister(hw);
+ return retptr;
+
+err_property:
+ pr_err("%s: clock %s missing required property \"%s\"\n",
+ __func__, name, property);
+ return ERR_PTR(-EINVAL);
+}
+
+static struct clk_hw *
+regclk_register_divider(struct device_node *np, struct regclk_ctrl *priv)
+{
+ const char *name;
+ const char *parent_name;
+ unsigned long flags;
+ void __iomem *reg;
+ u32 shift;
+ u32 width;
+ unsigned long clk_divider_flags;
+ struct clk_div_table *table = NULL;
+
+ struct property *prop;
+ const char *property;
+ struct clk_hw *hw;
+ struct clk_hw *retptr;
+ int ret;
+
+ reg = of_iomap(np, 0);
+ if (!reg)
+ return ERR_PTR(-ENOMEM);
+
+ name = regclk_name(np);
+ if (!name)
+ return ERR_PTR(-EINVAL);
+
+ property = "shift";
+ if (of_property_read_u32(np, property, &shift))
+ goto err_property;
+ property = "width";
+ if (of_property_read_u32(np, property, &width))
+ goto err_property;
+
+ prop = of_find_property(np, "dividers", NULL);
+ if (prop) {
+ unsigned int len = (prop->length / sizeof(u32) + 1) / 2;
+
+ table = kmalloc_array(len + 1, sizeof(*table), GFP_KERNEL);
+ if (!table)
+ return ERR_PTR(-ENOMEM);
+
+ for (unsigned int i = 0; i <= len; i++) {
+ u32 val;
+ u32 div;
+
+ if (of_property_read_u32_index(np, "dividers",
+ 2 * i + 0, &val)) {
+ retptr = ERR_PTR(-EINVAL);
+ goto err_table;
+ }
+ if (of_property_read_u32_index(np, "dividers",
+ 2 * i + 1, &div)) {
+ if (i == len)
+ div = 0;
+ retptr = ERR_PTR(-EINVAL);
+ goto err_table;
+ }
+
+ table[i].val = val;
+ table[i].div = div;
+ }
+
+ memset(&table[len], 0, sizeof(table[len]));
+ }
+
+ parent_name = of_clk_get_parent_name(np, 0);
+ flags = regclk_get_flags(np, regclk_flags);
+ clk_divider_flags = regclk_get_flags(np, regclk_divider_flags);
+
+ hw = __clk_hw_register_divider(NULL, np, name, parent_name,
+ NULL, NULL, flags, reg, shift, width,
+ clk_divider_flags, table, &priv->lock);
+ if (IS_ERR(hw)) {
+ retptr = hw;
+ goto err_table;
+ }
+
+ ret = of_clk_add_hw_provider(np, of_clk_hw_simple_get, hw);
+ if (ret) {
+ retptr = ERR_PTR(ret);
+ goto err_register;
+ }
+
+ return hw;
+
+err_register:
+ clk_hw_unregister(hw);
+err_table:
+ kfree(table);
+ return retptr;
+
+err_property:
+ pr_err("%s: clock %s missing required property \"%s\"\n",
+ __func__, name, property);
+ return ERR_PTR(-EINVAL);
+}
+
+static struct clk_hw *
+regclk_register_mux(struct device_node *np, struct regclk_ctrl *priv)
+{
+ const char *name;
+ u8 num_parents;
+ const char **parent_names;
+ unsigned long flags;
+ void __iomem *reg;
+ u32 shift;
+ u32 mask;
+ unsigned long clk_mux_flags;
+ u32 *table;
+
+ const char *property;
+ struct clk_hw *hw;
+ struct clk_hw *retptr;
+ int ret;
+
+ reg = of_iomap(np, 0);
+ if (!reg)
+ return ERR_PTR(-ENOMEM);
+ name = regclk_name(np);
+ if (!name)
+ return ERR_PTR(-EINVAL);
+
+ property = "shift";
+ if (of_property_read_u32(np, property, &shift))
+ goto err_property;
+ property = "mask";
+ if (of_property_read_u32(np, property, &mask))
+ goto err_property;
+
+ num_parents = of_clk_get_parent_count(np);
+
+ parent_names = kmalloc_array(num_parents, sizeof(*parent_names),
+ GFP_KERNEL);
+ if (!parent_names)
+ return ERR_PTR(-ENOMEM);
+ for (int i = 0; i < num_parents; i++) {
+ parent_names[i] = of_clk_get_parent_name(np, i);
+ if (!parent_names[i]) {
+ retptr = ERR_PTR(-EINVAL);
+ goto err_parents;
+ }
+ }
+
+ table = kmalloc_array(num_parents, sizeof(*table), GFP_KERNEL);
+ if (!table) {
+ retptr = ERR_PTR(-ENOMEM);
+ goto err_parents;
+ }
+ for (int i = 0; i < num_parents; i++) {
+ if (of_property_read_u32(np, "table", &table[i])) {
+ retptr = ERR_PTR(-EINVAL);
+ goto err_table;
+ }
+ }
+
+ flags = regclk_get_flags(np, regclk_flags);
+ clk_mux_flags = regclk_get_flags(np, regclk_mux_flags);
+
+ hw = __clk_hw_register_mux(NULL, np, name, num_parents, parent_names,
+ NULL, NULL, flags, reg, shift, mask,
+ clk_mux_flags, table, &priv->lock);
+ if (IS_ERR(hw))
+ goto err_table;
+
+ ret = of_clk_add_hw_provider(np, of_clk_hw_simple_get, hw);
+ if (ret) {
+ retptr = ERR_PTR(ret);
+ goto err_register;
+ }
+
+ return hw;
+
+err_register:
+ clk_hw_unregister(hw);
+err_table:
+ kfree(table);
+err_parents:
+ kfree(parent_names);
+ return retptr;
+
+err_property:
+ pr_err("%s: clock %s missing required property \"%s\"\n",
+ __func__, name, property);
+ return ERR_PTR(-EINVAL);
+}
+
+static struct clk_hw *
+regclk_register_fractional_divider(struct device_node *np, struct regclk_ctrl *priv)
+{
+ const char *name;
+ const char *parent_name;
+ unsigned long flags;
+ void __iomem *reg;
+ u32 mshift;
+ u32 mwidth;
+ u32 nshift;
+ u32 nwidth;
+ unsigned long clk_divider_flags;
+
+ const char *property;
+ struct clk_hw *hw;
+ struct clk_hw *retptr;
+ int ret;
+
+ reg = of_iomap(np, 0);
+ if (!reg)
+ return ERR_PTR(-ENOMEM);
+ name = regclk_name(np);
+ if (!name)
+ return ERR_PTR(-EINVAL);
+
+ property = "numerator-shift";
+ if (of_property_read_u32(np, property, &mshift))
+ goto err_property;
+ property = "numerator-width";
+ if (of_property_read_u32(np, property, &mwidth))
+ goto err_property;
+ property = "denominator-shift";
+ if (of_property_read_u32(np, property, &nshift))
+ goto err_property;
+ property = "denominator-width";
+ if (of_property_read_u32(np, property, &nwidth))
+ goto err_property;
+
+ parent_name = of_clk_get_parent_name(np, 0);
+ flags = regclk_get_flags(np, regclk_flags);
+ clk_divider_flags = regclk_get_flags(np, regclk_fractional_divider_flags);
+
+ hw = clk_hw_register_fractional_divider(NULL, name, parent_name,
+ flags, reg, mshift, mwidth,
+ nshift, nwidth,
+ clk_divider_flags, &priv->lock);
+ if (IS_ERR(hw))
+ return hw;
+
+ ret = of_clk_add_hw_provider(np, of_clk_hw_simple_get, hw);
+ if (ret) {
+ retptr = ERR_PTR(ret);
+ goto err_register;
+ }
+
+ return hw;
+
+err_register:
+ clk_hw_unregister(hw);
+ return retptr;
+
+err_property:
+ pr_err("%s: clock %s missing required property \"%s\"\n",
+ __func__, name, property);
+ return ERR_PTR(-EINVAL);
+}
+
+/** regclk **/
+
+static void regclk_unsetup(struct device_node *np)
+{
+ struct clk_hw *hw = np->data;
+
+ if (!hw)
+ return;
+
+ if (of_device_is_compatible(np, "gate-clock"))
+ clk_hw_unregister_gate(hw);
+ else if (of_device_is_compatible(np, "divider-clock"))
+ clk_hw_unregister_divider(hw);
+ else if (of_device_is_compatible(np, "mux-clock"))
+ clk_hw_unregister_mux(hw);
+ else if (of_device_is_compatible(np, "fractional-divider-clock"))
+ clk_hw_unregister_fractional_divider(hw);
+}
+
+static int regclk_setup(struct device_node *np, struct regclk_ctrl *priv)
+{
+ struct clk_hw *hw = np->data;
+
+ if (of_device_is_compatible(np, "gate-clock"))
+ hw = regclk_register_gate(np, priv);
+ else if (of_device_is_compatible(np, "divider-clock"))
+ hw = regclk_register_divider(np, priv);
+ else if (of_device_is_compatible(np, "mux-clock"))
+ hw = regclk_register_mux(np, priv);
+ else if (of_device_is_compatible(np, "fractional-divider-clock"))
+ hw = regclk_register_fractional_divider(np, priv);
+ else {
+ pr_warn("%s: starnge node %s ...\n",
+ __func__, of_node_full_name(np));
+ return 0;
+ }
+
+ if (IS_ERR(hw)) {
+ int ret = PTR_ERR(hw);
+
+ pr_err("%s: cannot register clock %s, ret %d\n",
+ __func__, of_node_full_name(np), ret);
+ return ret;
+ }
+
+ np->data = hw;
+ return 0;
+}
+
+/** regclk_reset **/
+
+#if IS_ENABLED(CONFIG_RESET_CONTROLLER)
+static int
+regclk_reset_assert(struct reset_controller_dev *rcdev, unsigned long id)
+{
+ struct regclk_ctrl *priv = container_of(rcdev, struct regclk_ctrl, rcdev);
+ unsigned long flags;
+ u32 offset = id >> 5;
+ u8 bit = id & 0x1f;
+ u32 val;
+
+ if (WARN_ON(!priv->base))
+ return 0;
+
+ spin_lock_irqsave(&priv->lock, flags);
+
+ val = readl(priv->base + offset);
+ if (priv->rst_set_to_disable)
+ val &= ~BIT(bit);
+ else
+ val |= BIT(bit);
+ writel(val, priv->base + offset);
+
+ spin_unlock_irqrestore(&priv->lock, flags);
+
+ return 0;
+}
+
+static int
+regclk_reset_deassert(struct reset_controller_dev *rcdev, unsigned long id)
+{
+ struct regclk_ctrl *priv = container_of(rcdev, struct regclk_ctrl, rcdev);
+ unsigned long flags;
+ u32 offset = id >> 5;
+ u8 bit = id & 0x1f;
+ u32 val;
+
+ if (WARN_ON(!priv->base))
+ return 0;
+
+ spin_lock_irqsave(&priv->lock, flags);
+
+ val = readl(priv->base + offset);
+ if (priv->rst_set_to_disable)
+ val |= BIT(bit);
+ else
+ val &= ~BIT(bit);
+ writel(val, priv->base + offset);
+
+ spin_unlock_irqrestore(&priv->lock, flags);
+
+ return 0;
+}
+
+static const struct reset_control_ops regclk_reset_ops = {
+ .assert = regclk_reset_assert,
+ .deassert = regclk_reset_deassert,
+};
+
+static int regclk_reset_of_xlate(struct reset_controller_dev *rcdev,
+ const struct of_phandle_args *reset_spec)
+{
+ return (reset_spec->args[0] << 5) | (reset_spec->args[1] & 0x1f);
+}
+
+static void regclk_reset_unsetup(struct device_node *np)
+{
+ struct regclk_ctrl *priv = np->data;
+
+ reset_controller_unregister(&priv->rcdev);
+}
+
+static int regclk_reset_setup(struct device_node *np, struct regclk_ctrl *priv)
+{
+ priv->base = of_iomap(np, 0);
+ priv->rst_set_to_disable = of_property_read_bool(np, "set-to-disable");
+
+ /* register no matter whether reg exists, to detect dts bug */
+ priv->rcdev.ops = ®clk_reset_ops;
+ priv->rcdev.of_node = np;
+ priv->rcdev.of_reset_n_cells = 2;
+ priv->rcdev.of_xlate = regclk_reset_of_xlate;
+ return reset_controller_register(&priv->rcdev);
+}
+#else
+static void regclk_reset_unsetup(struct device_node *np)
+{
+}
+
+static int regclk_reset_setup(struct device_node *np, struct regclk_ctrl *priv)
+{
+ return 0;
+}
+#endif
+
+/** regclk_ctrl **/
+
+static void regclk_ctrl_unsetup(struct device_node *np)
+{
+ struct device_node *child;
+
+ regclk_reset_unsetup(np);
+
+ for_each_child_of_node(np, child)
+ regclk_unsetup(child);
+
+ kfree(np->data);
+}
+
+static int regclk_ctrl_setup(struct device_node *np)
+{
+ struct regclk_ctrl *priv;
+ struct device_node *child;
+ int ret;
+
+ priv = kzalloc(sizeof(*priv), GFP_KERNEL);
+ if (!priv)
+ return -ENOMEM;
+
+ spin_lock_init(&priv->lock);
+ np->data = priv;
+
+ for_each_child_of_node(np, child) {
+ ret = regclk_setup(child, priv);
+ if (ret)
+ goto err;
+ }
+
+ ret = regclk_reset_setup(np, priv);
+ if (ret)
+ goto err;
+
+ return 0;
+
+err:
+ regclk_ctrl_unsetup(np);
+ return ret;
+}
+
+/** driver **/
+
+static void __init regclk_ctrl_init(struct device_node *np)
+{
+ regclk_ctrl_setup(np);
+}
+CLK_OF_DECLARE(regclk_ctrl, "reg-clock-controller", regclk_ctrl_init);
+
+static int regclk_ctrl_remove(struct platform_device *pdev)
+{
+ regclk_ctrl_unsetup(pdev->dev.of_node);
+
+ return 0;
+}
+
+/* This function is not executed when regclk_ctrl_init succeeded. */
+static int regclk_ctrl_probe(struct platform_device *pdev)
+{
+ return regclk_ctrl_setup(pdev->dev.of_node);
+}
+
+static const struct of_device_id regclk_ctrl_ids[] = {
+ { .compatible = "reg-clock-controller" },
+ { }
+};
+
+static struct platform_driver regclk_ctrl_driver = {
+ .driver = {
+ .name = "reg_clk_controller",
+ .of_match_table = regclk_ctrl_ids,
+ },
+ .probe = regclk_ctrl_probe,
+ .remove = regclk_ctrl_remove,
+};
+builtin_platform_driver(regclk_ctrl_driver);
--
2.39.2
^ permalink raw reply related [flat|nested] 9+ messages in thread
* Re: [PATCH 1/2] dt-bindings: clock: Add reg-clock-controller
2023-04-14 18:12 ` [PATCH 1/2] dt-bindings: clock: Add reg-clock-controller David Yang
@ 2023-04-14 21:08 ` Krzysztof Kozlowski
2023-04-17 17:47 ` Yangfl
2023-04-17 13:10 ` Rob Herring
2023-04-17 20:49 ` Rob Herring
2 siblings, 1 reply; 9+ messages in thread
From: Krzysztof Kozlowski @ 2023-04-14 21:08 UTC (permalink / raw)
To: David Yang, linux-clk
Cc: Michael Turquette, Stephen Boyd, Rob Herring, Krzysztof Kozlowski,
devicetree, linux-kernel
On 14/04/2023 20:12, David Yang wrote:
> Add DT bindings documentation for reg-clock-controller, collection of
> basic clocks common to many platforms.
>
> Signed-off-by: David Yang <mmyangfl@gmail.com>
> ---
> .../bindings/clock/reg-clock-controller.yaml | 245 ++++++++++++++++++
> 1 file changed, 245 insertions(+)
> create mode 100644 Documentation/devicetree/bindings/clock/reg-clock-controller.yaml
>
> diff --git a/Documentation/devicetree/bindings/clock/reg-clock-controller.yaml b/Documentation/devicetree/bindings/clock/reg-clock-controller.yaml
> new file mode 100644
> index 000000000000..a6a7e0b05821
> --- /dev/null
> +++ b/Documentation/devicetree/bindings/clock/reg-clock-controller.yaml
> @@ -0,0 +1,245 @@
> +# SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause)
> +%YAML 1.2
> +---
> +$id: http://devicetree.org/schemas/clock/reg-clock-controller.yaml#
> +$schema: http://devicetree.org/meta-schemas/core.yaml#
> +
> +title: Simple straight-forward register-based clocks
> +
> +maintainers:
> + - David Yang <mmyangfl@gmail.com>
> +
> +description: |
> + Basic clocks common to many platforms.
> +
> + If your clocks don't fit into these catagories, simply create your clock
typo: categories
> + controller. This driver normally work well with other controllers as long as
> + they operate on different registers.
> +
> + See linux/clk-provider.h for details about properties for each type of clock.
Describe here what is this device, what such simple clock controller
represents.
> +
> +properties:
> + compatible:
> + enum:
> + - reg-clock-controller
> +
> + ranges: true
> +
> + '#address-cells':
> + const: 1
> +
> + '#size-cells':
> + const: 1
> +
> +required:
> + - compatible
> + - ranges
> + - '#address-cells'
> + - '#size-cells'
required goes after patternProperties.
> +
> +patternProperties:
> + ".*gate-clock@.*":
"gate-clock@" should be equivalent. However this should be just "clock".
> + type: object
> +
> + description: |
Do not need '|' unless you need to preserve formatting.
> + Clock which can gate its output.
> +
> + properties:
> + compatible:
> + const: gate-clock
> +
> + reg:
> + maxItems: 1
> +
> + '#clock-cells':
> + const: 0
> +
> + clocks:
> + maxItems: 1
> + description:
> + Parent clock.
> +
> + clock-output-name:
names
Don't create your own properties.
> + maxItems: 1
> +
> + bit-index:
> + $ref: /schemas/types.yaml#/definitions/uint32
> + description:
> + Bit index which controls the output.
I suggest to use same property as nvme, so bits.
> +
> + required:
> + - compatible
> + - reg
> + - '#clock-cells'
> + - bit-index
> +
> + additionalProperties: false
> +
> + ".*divider-clock@.*":
> + type: object
> +
> + description: |
> + Clock with an adjustable divider affecting its output frequency.
> +
> + properties:
> + compatible:
> + const: divider-clock
> +
> + reg:
> + maxItems: 1
> +
> + '#clock-cells':
> + const: 0
> +
> + clocks:
> + description:
> + Parent clocks.
> +
> + clock-output-name:
> + maxItems: 1
> +
> + shift:
> + $ref: /schemas/types.yaml#/definitions/uint32
> + description:
> + Shift to the divider bit field.
> +
> + width:
> + $ref: /schemas/types.yaml#/definitions/uint32
> + description:
> + Width of the divider bit field.
> +
> + dividers:
> + $ref: /schemas/types.yaml#/definitions/uint32-array
> + description:
> + Array of value/divider pairs.
Then it looks like matrix.
> +
> + required:
> + - compatible
> + - reg
> + - '#clock-cells'
> + - shift
> + - width
> +
> + additionalProperties: false
> +
> + ".*mux-clock@.*":
> + type: object
> +
> + description: |
> + Clock with multiple selectable parents.
> +
> + properties:
> + compatible:
> + const: mux-clock
> +
> + reg:
> + maxItems: 1
> +
> + '#clock-cells':
> + const: 0
> +
> + clocks:
> + minItems: 1
> + description:
> + Parent clock.
> +
> + clock-output-name:
> + maxItems: 1
> +
> + shift:
> + $ref: /schemas/types.yaml#/definitions/uint32
> + description:
> + Shift to multiplexer bit field.
> +
> + mask:
> + $ref: /schemas/types.yaml#/definitions/uint32
> + description:
> + Mask of mutliplexer bit field.
> +
> + table:
> + $ref: /schemas/types.yaml#/definitions/uint32-array
> + description:
> + Array of register values corresponding to the parent index.
> +
> + required:
> + - compatible
> + - reg
> + - '#clock-cells'
> + - shift
> + - mask
> +
> + additionalProperties: false
> +
> + ".*fractional-divider-clock@.*":
> + type: object
> +
> + description: |
> + Clock with adjustable fractional divider affecting its output frequency.
> +
> + properties:
> + compatible:
> + const: fractional_divider-clock
> +
> + reg:
> + maxItems: 1
> +
> + '#clock-cells':
> + const: 0
> +
> + clocks:
> + maxItems: 1
> + description:
> + Parent clock.
> +
> + clock-output-name:
> + maxItems: 1
> +
> + numerator-shift:
> + $ref: /schemas/types.yaml#/definitions/uint32
> + description:
> + Shift to the numerator bit field.
> +
> + numerator-width:
> + $ref: /schemas/types.yaml#/definitions/uint32
> + description:
> + Width of the numerator bit field.
> +
> + denominator-shift:
> + $ref: /schemas/types.yaml#/definitions/uint32
> + description:
> + Shift to the denominator bit field.
> +
> + denominator-width:
> + $ref: /schemas/types.yaml#/definitions/uint32
> + description:
> + Width of the denominator bit field.
> +
> + required:
> + - compatible
> + - reg
> + - '#clock-cells'
> + - numerator-shift
> + - numerator-width
> + - denominator-shift
> + - denominator-width
> +
> + additionalProperties: false
> +
> +additionalProperties: true
No, come on. This must be false.
> +
> +examples:
> + - |
> + clks: reg-clk-ctrl@ffff0000 {
Names should be generic, so clock-controller
Drop the label.
> + compatible = "reg-clock-controller";
> + #address-cells = <1>;
> + #size-cells = <1>;
> + ranges = <0 0xffff0000 0x1000>;
> +
> + my_clk: gate-clock@cc-3 {
Drop label.
That's a new unit address to me. Did I miss a change in DT spec?
> + compatible = "gate-clock";
> + #clock-cells = <0>;
> + reg = <0xcc 4>;
reg is after compatible.
> + bit-index = <3>;
> + clock-output-name = "my-clk";
Plus, test your patches. This fails testing...
> + };
> + };
Best regards,
Krzysztof
^ permalink raw reply [flat|nested] 9+ messages in thread
* Re: [PATCH 1/2] dt-bindings: clock: Add reg-clock-controller
2023-04-14 18:12 ` [PATCH 1/2] dt-bindings: clock: Add reg-clock-controller David Yang
2023-04-14 21:08 ` Krzysztof Kozlowski
@ 2023-04-17 13:10 ` Rob Herring
2023-04-17 20:49 ` Rob Herring
2 siblings, 0 replies; 9+ messages in thread
From: Rob Herring @ 2023-04-17 13:10 UTC (permalink / raw)
To: David Yang
Cc: Stephen Boyd, Michael Turquette, Krzysztof Kozlowski, devicetree,
linux-clk, Rob Herring, linux-kernel
On Sat, 15 Apr 2023 02:12:59 +0800, David Yang wrote:
> Add DT bindings documentation for reg-clock-controller, collection of
> basic clocks common to many platforms.
>
> Signed-off-by: David Yang <mmyangfl@gmail.com>
> ---
> .../bindings/clock/reg-clock-controller.yaml | 245 ++++++++++++++++++
> 1 file changed, 245 insertions(+)
> create mode 100644 Documentation/devicetree/bindings/clock/reg-clock-controller.yaml
>
My bot found errors running 'make DT_CHECKER_FLAGS=-m dt_binding_check'
on your patch (DT_CHECKER_FLAGS is new in v5.13):
yamllint warnings/errors:
dtschema/dtc warnings/errors:
/builds/robherring/dt-review-ci/linux/Documentation/devicetree/bindings/clock/reg-clock-controller.example.dtb: reg-clk-ctrl@ffff0000: 'gate-clock@cc-3' does not match any of the regexes: '.*-names$', '.*-supply$', '^#.*-cells$', '^#[a-zA-Z0-9,+\\-._]{0,63}$', '^[a-zA-Z0-9][a-zA-Z0-9,+\\-._]{0,63}$', '^[a-zA-Z][a-zA-Z0-9,+\\-._]{0,63}@[0-9a-fA-F]+(,[0-9a-fA-F]+)*$', '^__.*__$', 'pinctrl-[0-9]+'
From schema: /usr/local/lib/python3.10/dist-packages/dtschema/schemas/dt-core.yaml
doc reference errors (make refcheckdocs):
See https://patchwork.ozlabs.org/project/devicetree-bindings/patch/20230414181302.986271-2-mmyangfl@gmail.com
The base for the series is generally the latest rc1. A different dependency
should be noted in *this* patch.
If you already ran 'make dt_binding_check' and didn't see the above
error(s), then make sure 'yamllint' is installed and dt-schema is up to
date:
pip3 install dtschema --upgrade
Please check and re-submit after running the above command yourself. Note
that DT_SCHEMA_FILES can be set to your schema file to speed up checking
your schema. However, it must be unset to test all examples with your schema.
^ permalink raw reply [flat|nested] 9+ messages in thread
* Re: [PATCH 1/2] dt-bindings: clock: Add reg-clock-controller
2023-04-14 21:08 ` Krzysztof Kozlowski
@ 2023-04-17 17:47 ` Yangfl
0 siblings, 0 replies; 9+ messages in thread
From: Yangfl @ 2023-04-17 17:47 UTC (permalink / raw)
To: Krzysztof Kozlowski
Cc: linux-clk, Michael Turquette, Stephen Boyd, Rob Herring,
Krzysztof Kozlowski, devicetree, linux-kernel
Krzysztof Kozlowski <krzysztof.kozlowski@linaro.org> 于2023年4月15日周六 05:08写道:
>
> On 14/04/2023 20:12, David Yang wrote:
> > Add DT bindings documentation for reg-clock-controller, collection of
> > basic clocks common to many platforms.
> >
> > Signed-off-by: David Yang <mmyangfl@gmail.com>
> > ---
> > .../bindings/clock/reg-clock-controller.yaml | 245 ++++++++++++++++++
> > 1 file changed, 245 insertions(+)
> > create mode 100644 Documentation/devicetree/bindings/clock/reg-clock-controller.yaml
> >
> > diff --git a/Documentation/devicetree/bindings/clock/reg-clock-controller.yaml b/Documentation/devicetree/bindings/clock/reg-clock-controller.yaml
> > new file mode 100644
> > index 000000000000..a6a7e0b05821
> > --- /dev/null
> > +++ b/Documentation/devicetree/bindings/clock/reg-clock-controller.yaml
> > @@ -0,0 +1,245 @@
> > +# SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause)
> > +%YAML 1.2
> > +---
> > +$id: http://devicetree.org/schemas/clock/reg-clock-controller.yaml#
> > +$schema: http://devicetree.org/meta-schemas/core.yaml#
> > +
> > +title: Simple straight-forward register-based clocks
> > +
> > +maintainers:
> > + - David Yang <mmyangfl@gmail.com>
> > +
> > +description: |
> > + Basic clocks common to many platforms.
> > +
> > + If your clocks don't fit into these catagories, simply create your clock
>
> typo: categories
Fixed in v2.
>
> > + controller. This driver normally work well with other controllers as long as
> > + they operate on different registers.
> > +
> > + See linux/clk-provider.h for details about properties for each type of clock.
>
> Describe here what is this device, what such simple clock controller
> represents.
Description has been rewritten in v3, to describe the device.
>
> > +
> > +properties:
> > + compatible:
> > + enum:
> > + - reg-clock-controller
> > +
> > + ranges: true
> > +
> > + '#address-cells':
> > + const: 1
> > +
> > + '#size-cells':
> > + const: 1
> > +
> > +required:
> > + - compatible
> > + - ranges
> > + - '#address-cells'
> > + - '#size-cells'
>
> required goes after patternProperties.
Fixed in v2.
>
> > +
> > +patternProperties:
> > + ".*gate-clock@.*":
>
> "gate-clock@" should be equivalent. However this should be just "clock".
Fixed in v3.
>
> > + type: object
> > +
> > + description: |
>
> Do not need '|' unless you need to preserve formatting.
Fixed in v2.
>
> > + Clock which can gate its output.
> > +
> > + properties:
> > + compatible:
> > + const: gate-clock
> > +
> > + reg:
> > + maxItems: 1
> > +
> > + '#clock-cells':
> > + const: 0
> > +
> > + clocks:
> > + maxItems: 1
> > + description:
> > + Parent clock.
> > +
> > + clock-output-name:
>
> names
>
> Don't create your own properties.
Fixed in v2, "clock-output-names".
>
> > + maxItems: 1
> > +
> > + bit-index:
> > + $ref: /schemas/types.yaml#/definitions/uint32
> > + description:
> > + Bit index which controls the output.
>
> I suggest to use same property as nvme, so bits.
Replaced with "bits" in v2.
>
> > +
> > + required:
> > + - compatible
> > + - reg
> > + - '#clock-cells'
> > + - bit-index
> > +
> > + additionalProperties: false
> > +
> > + ".*divider-clock@.*":
> > + type: object
> > +
> > + description: |
> > + Clock with an adjustable divider affecting its output frequency.
> > +
> > + properties:
> > + compatible:
> > + const: divider-clock
> > +
> > + reg:
> > + maxItems: 1
> > +
> > + '#clock-cells':
> > + const: 0
> > +
> > + clocks:
> > + description:
> > + Parent clocks.
> > +
> > + clock-output-name:
> > + maxItems: 1
> > +
> > + shift:
> > + $ref: /schemas/types.yaml#/definitions/uint32
> > + description:
> > + Shift to the divider bit field.
> > +
> > + width:
> > + $ref: /schemas/types.yaml#/definitions/uint32
> > + description:
> > + Width of the divider bit field.
> > +
> > + dividers:
> > + $ref: /schemas/types.yaml#/definitions/uint32-array
> > + description:
> > + Array of value/divider pairs.
>
> Then it looks like matrix.
This part of bindings has been (temporarily) removed from this series
since v2, to make it simpler.
>
> > +
> > + required:
> > + - compatible
> > + - reg
> > + - '#clock-cells'
> > + - shift
> > + - width
> > +
> > + additionalProperties: false
> > +
> > + ".*mux-clock@.*":
> > + type: object
> > +
> > + description: |
> > + Clock with multiple selectable parents.
> > +
> > + properties:
> > + compatible:
> > + const: mux-clock
> > +
> > + reg:
> > + maxItems: 1
> > +
> > + '#clock-cells':
> > + const: 0
> > +
> > + clocks:
> > + minItems: 1
> > + description:
> > + Parent clock.
> > +
> > + clock-output-name:
> > + maxItems: 1
> > +
> > + shift:
> > + $ref: /schemas/types.yaml#/definitions/uint32
> > + description:
> > + Shift to multiplexer bit field.
> > +
> > + mask:
> > + $ref: /schemas/types.yaml#/definitions/uint32
> > + description:
> > + Mask of mutliplexer bit field.
> > +
> > + table:
> > + $ref: /schemas/types.yaml#/definitions/uint32-array
> > + description:
> > + Array of register values corresponding to the parent index.
> > +
> > + required:
> > + - compatible
> > + - reg
> > + - '#clock-cells'
> > + - shift
> > + - mask
> > +
> > + additionalProperties: false
> > +
> > + ".*fractional-divider-clock@.*":
> > + type: object
> > +
> > + description: |
> > + Clock with adjustable fractional divider affecting its output frequency.
> > +
> > + properties:
> > + compatible:
> > + const: fractional_divider-clock
> > +
> > + reg:
> > + maxItems: 1
> > +
> > + '#clock-cells':
> > + const: 0
> > +
> > + clocks:
> > + maxItems: 1
> > + description:
> > + Parent clock.
> > +
> > + clock-output-name:
> > + maxItems: 1
> > +
> > + numerator-shift:
> > + $ref: /schemas/types.yaml#/definitions/uint32
> > + description:
> > + Shift to the numerator bit field.
> > +
> > + numerator-width:
> > + $ref: /schemas/types.yaml#/definitions/uint32
> > + description:
> > + Width of the numerator bit field.
> > +
> > + denominator-shift:
> > + $ref: /schemas/types.yaml#/definitions/uint32
> > + description:
> > + Shift to the denominator bit field.
> > +
> > + denominator-width:
> > + $ref: /schemas/types.yaml#/definitions/uint32
> > + description:
> > + Width of the denominator bit field.
> > +
> > + required:
> > + - compatible
> > + - reg
> > + - '#clock-cells'
> > + - numerator-shift
> > + - numerator-width
> > + - denominator-shift
> > + - denominator-width
> > +
> > + additionalProperties: false
> > +
> > +additionalProperties: true
>
> No, come on. This must be false.
Fixed with "false" in v2.
>
> > +
> > +examples:
> > + - |
> > + clks: reg-clk-ctrl@ffff0000 {
>
> Names should be generic, so clock-controller
>
> Drop the label.
Dropped in v2.
>
> > + compatible = "reg-clock-controller";
> > + #address-cells = <1>;
> > + #size-cells = <1>;
> > + ranges = <0 0xffff0000 0x1000>;
> > +
> > + my_clk: gate-clock@cc-3 {
>
> Drop label.
>
> That's a new unit address to me. Did I miss a change in DT spec?
Dropped label in v2.
>
> > + compatible = "gate-clock";
> > + #clock-cells = <0>;
> > + reg = <0xcc 4>;
>
> reg is after compatible.
>
> > + bit-index = <3>;
> > + clock-output-name = "my-clk";
>
> Plus, test your patches. This fails testing...
Fix name error in v3.
>
> > + };
> > + };
>
> Best regards,
> Krzysztof
>
^ permalink raw reply [flat|nested] 9+ messages in thread
* Re: [PATCH 1/2] dt-bindings: clock: Add reg-clock-controller
2023-04-14 18:12 ` [PATCH 1/2] dt-bindings: clock: Add reg-clock-controller David Yang
2023-04-14 21:08 ` Krzysztof Kozlowski
2023-04-17 13:10 ` Rob Herring
@ 2023-04-17 20:49 ` Rob Herring
2023-04-17 21:39 ` Yangfl
2 siblings, 1 reply; 9+ messages in thread
From: Rob Herring @ 2023-04-17 20:49 UTC (permalink / raw)
To: David Yang
Cc: linux-clk, Michael Turquette, Stephen Boyd, Krzysztof Kozlowski,
devicetree, linux-kernel
On Sat, Apr 15, 2023 at 02:12:59AM +0800, David Yang wrote:
> Add DT bindings documentation for reg-clock-controller, collection of
> basic clocks common to many platforms.
>
> Signed-off-by: David Yang <mmyangfl@gmail.com>
> ---
> .../bindings/clock/reg-clock-controller.yaml | 245 ++++++++++++++++++
> 1 file changed, 245 insertions(+)
> create mode 100644 Documentation/devicetree/bindings/clock/reg-clock-controller.yaml
>
> diff --git a/Documentation/devicetree/bindings/clock/reg-clock-controller.yaml b/Documentation/devicetree/bindings/clock/reg-clock-controller.yaml
> new file mode 100644
> index 000000000000..a6a7e0b05821
> --- /dev/null
> +++ b/Documentation/devicetree/bindings/clock/reg-clock-controller.yaml
> @@ -0,0 +1,245 @@
> +# SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause)
> +%YAML 1.2
> +---
> +$id: http://devicetree.org/schemas/clock/reg-clock-controller.yaml#
> +$schema: http://devicetree.org/meta-schemas/core.yaml#
> +
> +title: Simple straight-forward register-based clocks
'simple' means extended one property at a time with little foresight. In
the end, 'simple' bindings are never simple. s/simple/generic/ as well.
When we first started the clock binding, we had exactly this. There's
still bindings for at least some of it. It turned out to be a bad
idea because it was difficult to get correct and complete. So this
binding is exactly what we don't want.
Rob
^ permalink raw reply [flat|nested] 9+ messages in thread
* Re: [PATCH 1/2] dt-bindings: clock: Add reg-clock-controller
2023-04-17 20:49 ` Rob Herring
@ 2023-04-17 21:39 ` Yangfl
2023-04-18 0:14 ` Stephen Boyd
0 siblings, 1 reply; 9+ messages in thread
From: Yangfl @ 2023-04-17 21:39 UTC (permalink / raw)
To: Rob Herring
Cc: linux-clk, Michael Turquette, Stephen Boyd, Krzysztof Kozlowski,
devicetree, linux-kernel
Rob Herring <robh@kernel.org> 于2023年4月18日周二 04:49写道:
>
> On Sat, Apr 15, 2023 at 02:12:59AM +0800, David Yang wrote:
> > Add DT bindings documentation for reg-clock-controller, collection of
> > basic clocks common to many platforms.
> >
> > Signed-off-by: David Yang <mmyangfl@gmail.com>
> > ---
> > .../bindings/clock/reg-clock-controller.yaml | 245 ++++++++++++++++++
> > 1 file changed, 245 insertions(+)
> > create mode 100644 Documentation/devicetree/bindings/clock/reg-clock-controller.yaml
> >
> > diff --git a/Documentation/devicetree/bindings/clock/reg-clock-controller.yaml b/Documentation/devicetree/bindings/clock/reg-clock-controller.yaml
> > new file mode 100644
> > index 000000000000..a6a7e0b05821
> > --- /dev/null
> > +++ b/Documentation/devicetree/bindings/clock/reg-clock-controller.yaml
> > @@ -0,0 +1,245 @@
> > +# SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause)
> > +%YAML 1.2
> > +---
> > +$id: http://devicetree.org/schemas/clock/reg-clock-controller.yaml#
> > +$schema: http://devicetree.org/meta-schemas/core.yaml#
> > +
> > +title: Simple straight-forward register-based clocks
>
> 'simple' means extended one property at a time with little foresight. In
> the end, 'simple' bindings are never simple. s/simple/generic/ as well.
>
> When we first started the clock binding, we had exactly this. There's
> still bindings for at least some of it. It turned out to be a bad
> idea because it was difficult to get correct and complete. So this
> binding is exactly what we don't want.
>
> Rob
Thanks. So in the next version v2, clock-controller are made merely
container of clocks. The real jobs are done by sub clock nodes, so
that clocks, with or without hardware-specific clock types
"compatible", can be declared independently and individually as dt
nodes, instead of hardware clock "controllers" with quite arbitrary
clock identifiers listed under include/dt-bindings/clock/.
^ permalink raw reply [flat|nested] 9+ messages in thread
* Re: [PATCH 1/2] dt-bindings: clock: Add reg-clock-controller
2023-04-17 21:39 ` Yangfl
@ 2023-04-18 0:14 ` Stephen Boyd
0 siblings, 0 replies; 9+ messages in thread
From: Stephen Boyd @ 2023-04-18 0:14 UTC (permalink / raw)
To: Rob Herring, Yangfl
Cc: linux-clk, Michael Turquette, Krzysztof Kozlowski, devicetree,
linux-kernel
Quoting Yangfl (2023-04-17 14:39:23)
> Rob Herring <robh@kernel.org> 于2023年4月18日周二 04:49写道:
> >
> > On Sat, Apr 15, 2023 at 02:12:59AM +0800, David Yang wrote:
> > > Add DT bindings documentation for reg-clock-controller, collection of
> > > basic clocks common to many platforms.
> > >
> > > Signed-off-by: David Yang <mmyangfl@gmail.com>
> > > ---
> > > .../bindings/clock/reg-clock-controller.yaml | 245 ++++++++++++++++++
> > > 1 file changed, 245 insertions(+)
> > > create mode 100644 Documentation/devicetree/bindings/clock/reg-clock-controller.yaml
> > >
> > > diff --git a/Documentation/devicetree/bindings/clock/reg-clock-controller.yaml b/Documentation/devicetree/bindings/clock/reg-clock-controller.yaml
> > > new file mode 100644
> > > index 000000000000..a6a7e0b05821
> > > --- /dev/null
> > > +++ b/Documentation/devicetree/bindings/clock/reg-clock-controller.yaml
> > > @@ -0,0 +1,245 @@
> > > +# SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause)
> > > +%YAML 1.2
> > > +---
> > > +$id: http://devicetree.org/schemas/clock/reg-clock-controller.yaml#
> > > +$schema: http://devicetree.org/meta-schemas/core.yaml#
> > > +
> > > +title: Simple straight-forward register-based clocks
> >
> > 'simple' means extended one property at a time with little foresight. In
> > the end, 'simple' bindings are never simple. s/simple/generic/ as well.
> >
> > When we first started the clock binding, we had exactly this. There's
> > still bindings for at least some of it. It turned out to be a bad
> > idea because it was difficult to get correct and complete. So this
> > binding is exactly what we don't want.
> >
> > Rob
>
> Thanks. So in the next version v2, clock-controller are made merely
> container of clocks. The real jobs are done by sub clock nodes, so
> that clocks, with or without hardware-specific clock types
> "compatible", can be declared independently and individually as dt
> nodes, instead of hardware clock "controllers" with quite arbitrary
> clock identifiers listed under include/dt-bindings/clock/.
No. Write actual drivers and actual bindings for real devices.
^ permalink raw reply [flat|nested] 9+ messages in thread
end of thread, other threads:[~2023-04-18 0:14 UTC | newest]
Thread overview: 9+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2023-04-14 18:12 [PATCH 0/2] clk: Add basic register clock controller David Yang
2023-04-14 18:12 ` [PATCH 1/2] dt-bindings: clock: Add reg-clock-controller David Yang
2023-04-14 21:08 ` Krzysztof Kozlowski
2023-04-17 17:47 ` Yangfl
2023-04-17 13:10 ` Rob Herring
2023-04-17 20:49 ` Rob Herring
2023-04-17 21:39 ` Yangfl
2023-04-18 0:14 ` Stephen Boyd
2023-04-14 18:13 ` [PATCH 2/2] clk: Add basic register clock controller David Yang
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.