hc
2024-12-19 9370bb92b2d16684ee45cf24e879c93c509162da
kernel/drivers/clk/socfpga/clk-gate.c
....@@ -1,19 +1,9 @@
1
+// SPDX-License-Identifier: GPL-2.0-or-later
12 /*
23 * Copyright 2011-2012 Calxeda, Inc.
34 * Copyright (C) 2012-2013 Altera Corporation <www.altera.com>
45 *
5
- * This program is free software; you can redistribute it and/or modify
6
- * it under the terms of the GNU General Public License as published by
7
- * the Free Software Foundation; either version 2 of the License, or
8
- * (at your option) any later version.
9
- *
10
- * This program is distributed in the hope that it will be useful,
11
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
12
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13
- * GNU General Public License for more details.
14
- *
156 * Based from clk-highbank.c
16
- *
177 */
188 #include <linux/slab.h>
199 #include <linux/clk-provider.h>
....@@ -40,22 +30,23 @@
4030 {
4131 u32 l4_src;
4232 u32 perpll_src;
33
+ const char *name = clk_hw_get_name(hwclk);
4334
44
- if (streq(hwclk->init->name, SOCFPGA_L4_MP_CLK)) {
35
+ if (streq(name, SOCFPGA_L4_MP_CLK)) {
4536 l4_src = readl(clk_mgr_base_addr + CLKMGR_L4SRC);
4637 return l4_src &= 0x1;
4738 }
48
- if (streq(hwclk->init->name, SOCFPGA_L4_SP_CLK)) {
39
+ if (streq(name, SOCFPGA_L4_SP_CLK)) {
4940 l4_src = readl(clk_mgr_base_addr + CLKMGR_L4SRC);
5041 return !!(l4_src & 2);
5142 }
5243
5344 perpll_src = readl(clk_mgr_base_addr + CLKMGR_PERPLL_SRC);
54
- if (streq(hwclk->init->name, SOCFPGA_MMC_CLK))
45
+ if (streq(name, SOCFPGA_MMC_CLK))
5546 return perpll_src &= 0x3;
56
- if (streq(hwclk->init->name, SOCFPGA_NAND_CLK) ||
57
- streq(hwclk->init->name, SOCFPGA_NAND_X_CLK))
58
- return (perpll_src >> 2) & 3;
47
+ if (streq(name, SOCFPGA_NAND_CLK) ||
48
+ streq(name, SOCFPGA_NAND_X_CLK))
49
+ return (perpll_src >> 2) & 3;
5950
6051 /* QSPI clock */
6152 return (perpll_src >> 4) & 3;
....@@ -65,24 +56,25 @@
6556 static int socfpga_clk_set_parent(struct clk_hw *hwclk, u8 parent)
6657 {
6758 u32 src_reg;
59
+ const char *name = clk_hw_get_name(hwclk);
6860
69
- if (streq(hwclk->init->name, SOCFPGA_L4_MP_CLK)) {
61
+ if (streq(name, SOCFPGA_L4_MP_CLK)) {
7062 src_reg = readl(clk_mgr_base_addr + CLKMGR_L4SRC);
7163 src_reg &= ~0x1;
7264 src_reg |= parent;
7365 writel(src_reg, clk_mgr_base_addr + CLKMGR_L4SRC);
74
- } else if (streq(hwclk->init->name, SOCFPGA_L4_SP_CLK)) {
66
+ } else if (streq(name, SOCFPGA_L4_SP_CLK)) {
7567 src_reg = readl(clk_mgr_base_addr + CLKMGR_L4SRC);
7668 src_reg &= ~0x2;
7769 src_reg |= (parent << 1);
7870 writel(src_reg, clk_mgr_base_addr + CLKMGR_L4SRC);
7971 } else {
8072 src_reg = readl(clk_mgr_base_addr + CLKMGR_PERPLL_SRC);
81
- if (streq(hwclk->init->name, SOCFPGA_MMC_CLK)) {
73
+ if (streq(name, SOCFPGA_MMC_CLK)) {
8274 src_reg &= ~0x3;
8375 src_reg |= parent;
84
- } else if (streq(hwclk->init->name, SOCFPGA_NAND_CLK) ||
85
- streq(hwclk->init->name, SOCFPGA_NAND_X_CLK)) {
76
+ } else if (streq(name, SOCFPGA_NAND_CLK) ||
77
+ streq(name, SOCFPGA_NAND_X_CLK)) {
8678 src_reg &= ~0xC;
8779 src_reg |= (parent << 2);
8880 } else {/* QSPI clock */
....@@ -176,23 +168,30 @@
176168 .set_parent = socfpga_clk_set_parent,
177169 };
178170
179
-static void __init __socfpga_gate_init(struct device_node *node,
180
- const struct clk_ops *ops)
171
+void __init socfpga_gate_init(struct device_node *node)
181172 {
182173 u32 clk_gate[2];
183174 u32 div_reg[3];
184175 u32 clk_phase[2];
185176 u32 fixed_div;
186
- struct clk *clk;
177
+ struct clk_hw *hw_clk;
187178 struct socfpga_gate_clk *socfpga_clk;
188179 const char *clk_name = node->name;
189180 const char *parent_name[SOCFPGA_MAX_PARENTS];
190
- struct clk_init_data init = {};
181
+ struct clk_init_data init;
182
+ struct clk_ops *ops;
191183 int rc;
184
+ int err;
192185
193186 socfpga_clk = kzalloc(sizeof(*socfpga_clk), GFP_KERNEL);
194187 if (WARN_ON(!socfpga_clk))
195188 return;
189
+
190
+ ops = kmemdup(&gateclk_ops, sizeof(gateclk_ops), GFP_KERNEL);
191
+ if (WARN_ON(!ops)) {
192
+ kfree(socfpga_clk);
193
+ return;
194
+ }
196195
197196 rc = of_property_read_u32_array(node, "clk-gate", clk_gate, 2);
198197 if (rc)
....@@ -202,8 +201,8 @@
202201 socfpga_clk->hw.reg = clk_mgr_base_addr + clk_gate[0];
203202 socfpga_clk->hw.bit_idx = clk_gate[1];
204203
205
- gateclk_ops.enable = clk_gate_ops.enable;
206
- gateclk_ops.disable = clk_gate_ops.disable;
204
+ ops->enable = clk_gate_ops.enable;
205
+ ops->disable = clk_gate_ops.disable;
207206 }
208207
209208 rc = of_property_read_u32(node, "fixed-divider", &fixed_div);
....@@ -234,20 +233,23 @@
234233 init.flags = 0;
235234
236235 init.num_parents = of_clk_parent_fill(node, parent_name, SOCFPGA_MAX_PARENTS);
236
+ if (init.num_parents < 2) {
237
+ ops->get_parent = NULL;
238
+ ops->set_parent = NULL;
239
+ }
240
+
237241 init.parent_names = parent_name;
238242 socfpga_clk->hw.hw.init = &init;
239243
240
- clk = clk_register(NULL, &socfpga_clk->hw.hw);
241
- if (WARN_ON(IS_ERR(clk))) {
244
+ hw_clk = &socfpga_clk->hw.hw;
245
+
246
+ err = clk_hw_register(NULL, hw_clk);
247
+ if (err) {
248
+ kfree(ops);
242249 kfree(socfpga_clk);
243250 return;
244251 }
245
- rc = of_clk_add_provider(node, of_clk_src_simple_get, clk);
252
+ rc = of_clk_add_provider(node, of_clk_src_simple_get, hw_clk);
246253 if (WARN_ON(rc))
247254 return;
248
-}
249
-
250
-void __init socfpga_gate_init(struct device_node *node)
251
-{
252
- __socfpga_gate_init(node, &gateclk_ops);
253255 }