Commit | Line | Data |
---|---|---|
22f65a38 | 1 | // SPDX-License-Identifier: (GPL-2.0 OR BSD-3-Clause) |
f8c11f79 | 2 | /* |
f8c11f79 NA |
3 | * Copyright (c) 2016 BayLibre, SAS. |
4 | * Author: Neil Armstrong <narmstrong@baylibre.com> | |
f8c11f79 | 5 | */ |
f8c11f79 | 6 | #include <linux/platform_device.h> |
ffb13e3b | 7 | #include <linux/mfd/syscon.h> |
81c7fcac | 8 | #include "clk-regmap.h" |
88e2da81 | 9 | #include "meson-aoclk.h" |
ffb13e3b | 10 | #include "gxbb-aoclk.h" |
f8c11f79 | 11 | |
f8c11f79 | 12 | #define GXBB_AO_GATE(_name, _bit) \ |
81c7fcac JB |
13 | static struct clk_regmap _name##_ao = { \ |
14 | .data = &(struct clk_regmap_gate_data) { \ | |
15 | .offset = AO_RTI_GEN_CNTL_REG0, \ | |
16 | .bit_idx = (_bit), \ | |
17 | }, \ | |
f8c11f79 NA |
18 | .hw.init = &(struct clk_init_data) { \ |
19 | .name = #_name "_ao", \ | |
81c7fcac | 20 | .ops = &clk_regmap_gate_ops, \ |
f8c11f79 NA |
21 | .parent_names = (const char *[]){ "clk81" }, \ |
22 | .num_parents = 1, \ | |
24a2e679 | 23 | .flags = CLK_IGNORE_UNUSED, \ |
f8c11f79 NA |
24 | }, \ |
25 | } | |
26 | ||
27 | GXBB_AO_GATE(remote, 0); | |
28 | GXBB_AO_GATE(i2c_master, 1); | |
29 | GXBB_AO_GATE(i2c_slave, 2); | |
30 | GXBB_AO_GATE(uart1, 3); | |
31 | GXBB_AO_GATE(uart2, 5); | |
32 | GXBB_AO_GATE(ir_blaster, 6); | |
33 | ||
62ec0b97 | 34 | static struct aoclk_cec_32k cec_32k_ao = { |
62ec0b97 NA |
35 | .hw.init = &(struct clk_init_data) { |
36 | .name = "cec_32k_ao", | |
37 | .ops = &meson_aoclk_cec_32k_ops, | |
38 | .parent_names = (const char *[]){ "xtal" }, | |
39 | .num_parents = 1, | |
40 | .flags = CLK_IGNORE_UNUSED, | |
41 | }, | |
42 | }; | |
43 | ||
88e2da81 | 44 | static const unsigned int gxbb_aoclk_reset[] = { |
f8c11f79 NA |
45 | [RESET_AO_REMOTE] = 16, |
46 | [RESET_AO_I2C_MASTER] = 18, | |
47 | [RESET_AO_I2C_SLAVE] = 19, | |
48 | [RESET_AO_UART1] = 17, | |
49 | [RESET_AO_UART2] = 22, | |
50 | [RESET_AO_IR_BLASTER] = 23, | |
51 | }; | |
52 | ||
81c7fcac | 53 | static struct clk_regmap *gxbb_aoclk_gate[] = { |
f8c11f79 NA |
54 | [CLKID_AO_REMOTE] = &remote_ao, |
55 | [CLKID_AO_I2C_MASTER] = &i2c_master_ao, | |
56 | [CLKID_AO_I2C_SLAVE] = &i2c_slave_ao, | |
57 | [CLKID_AO_UART1] = &uart1_ao, | |
58 | [CLKID_AO_UART2] = &uart2_ao, | |
59 | [CLKID_AO_IR_BLASTER] = &ir_blaster_ao, | |
60 | }; | |
61 | ||
88e2da81 | 62 | static const struct clk_hw_onecell_data gxbb_aoclk_onecell_data = { |
f8c11f79 NA |
63 | .hws = { |
64 | [CLKID_AO_REMOTE] = &remote_ao.hw, | |
65 | [CLKID_AO_I2C_MASTER] = &i2c_master_ao.hw, | |
66 | [CLKID_AO_I2C_SLAVE] = &i2c_slave_ao.hw, | |
67 | [CLKID_AO_UART1] = &uart1_ao.hw, | |
68 | [CLKID_AO_UART2] = &uart2_ao.hw, | |
69 | [CLKID_AO_IR_BLASTER] = &ir_blaster_ao.hw, | |
62ec0b97 | 70 | [CLKID_AO_CEC_32K] = &cec_32k_ao.hw, |
f8c11f79 | 71 | }, |
88e2da81 | 72 | .num = NR_CLKS, |
f8c11f79 NA |
73 | }; |
74 | ||
88e2da81 | 75 | static int gxbb_register_cec_ao_32k(struct platform_device *pdev) |
f8c11f79 | 76 | { |
ffb13e3b NA |
77 | struct device *dev = &pdev->dev; |
78 | struct regmap *regmap; | |
88e2da81 | 79 | int ret; |
f8c11f79 | 80 | |
ffb13e3b NA |
81 | regmap = syscon_node_to_regmap(of_get_parent(dev->of_node)); |
82 | if (IS_ERR(regmap)) { | |
83 | dev_err(dev, "failed to get regmap\n"); | |
88e2da81 | 84 | return PTR_ERR(regmap); |
f8c11f79 NA |
85 | } |
86 | ||
62ec0b97 NA |
87 | /* Specific clocks */ |
88 | cec_32k_ao.regmap = regmap; | |
89 | ret = devm_clk_hw_register(dev, &cec_32k_ao.hw); | |
88e2da81 YL |
90 | if (ret) { |
91 | dev_err(&pdev->dev, "clk cec_32k_ao register failed.\n"); | |
92 | return ret; | |
93 | } | |
94 | ||
95 | return 0; | |
96 | } | |
97 | ||
98 | static const struct meson_aoclk_data gxbb_aoclkc_data = { | |
99 | .reset_reg = AO_RTI_GEN_CNTL_REG0, | |
100 | .num_reset = ARRAY_SIZE(gxbb_aoclk_reset), | |
101 | .reset = gxbb_aoclk_reset, | |
102 | .num_clks = ARRAY_SIZE(gxbb_aoclk_gate), | |
103 | .clks = gxbb_aoclk_gate, | |
104 | .hw_data = &gxbb_aoclk_onecell_data, | |
105 | }; | |
106 | ||
107 | static int gxbb_aoclkc_probe(struct platform_device *pdev) | |
108 | { | |
109 | int ret = gxbb_register_cec_ao_32k(pdev); | |
62ec0b97 NA |
110 | if (ret) |
111 | return ret; | |
112 | ||
88e2da81 | 113 | return meson_aoclkc_probe(pdev); |
f8c11f79 NA |
114 | } |
115 | ||
116 | static const struct of_device_id gxbb_aoclkc_match_table[] = { | |
88e2da81 YL |
117 | { |
118 | .compatible = "amlogic,meson-gx-aoclkc", | |
119 | .data = &gxbb_aoclkc_data, | |
120 | }, | |
f8c11f79 NA |
121 | { } |
122 | }; | |
123 | ||
124 | static struct platform_driver gxbb_aoclkc_driver = { | |
125 | .probe = gxbb_aoclkc_probe, | |
126 | .driver = { | |
127 | .name = "gxbb-aoclkc", | |
128 | .of_match_table = gxbb_aoclkc_match_table, | |
129 | }, | |
130 | }; | |
131 | builtin_platform_driver(gxbb_aoclkc_driver); |