0001
0002
0003
0004
0005
0006
0007
0008
0009
0010 #include <linux/clk-provider.h>
0011 #include <linux/delay.h>
0012 #include <linux/module.h>
0013 #include <linux/slab.h>
0014 #include <linux/platform_device.h>
0015 #include <linux/mfd/wm831x/core.h>
0016
0017 struct wm831x_clk {
0018 struct wm831x *wm831x;
0019 struct clk_hw xtal_hw;
0020 struct clk_hw fll_hw;
0021 struct clk_hw clkout_hw;
0022 bool xtal_ena;
0023 };
0024
0025 static int wm831x_xtal_is_prepared(struct clk_hw *hw)
0026 {
0027 struct wm831x_clk *clkdata = container_of(hw, struct wm831x_clk,
0028 xtal_hw);
0029
0030 return clkdata->xtal_ena;
0031 }
0032
0033 static unsigned long wm831x_xtal_recalc_rate(struct clk_hw *hw,
0034 unsigned long parent_rate)
0035 {
0036 struct wm831x_clk *clkdata = container_of(hw, struct wm831x_clk,
0037 xtal_hw);
0038
0039 if (clkdata->xtal_ena)
0040 return 32768;
0041 else
0042 return 0;
0043 }
0044
0045 static const struct clk_ops wm831x_xtal_ops = {
0046 .is_prepared = wm831x_xtal_is_prepared,
0047 .recalc_rate = wm831x_xtal_recalc_rate,
0048 };
0049
0050 static const struct clk_init_data wm831x_xtal_init = {
0051 .name = "xtal",
0052 .ops = &wm831x_xtal_ops,
0053 };
0054
0055 static const unsigned long wm831x_fll_auto_rates[] = {
0056 2048000,
0057 11289600,
0058 12000000,
0059 12288000,
0060 19200000,
0061 22579600,
0062 24000000,
0063 24576000,
0064 };
0065
0066 static int wm831x_fll_is_prepared(struct clk_hw *hw)
0067 {
0068 struct wm831x_clk *clkdata = container_of(hw, struct wm831x_clk,
0069 fll_hw);
0070 struct wm831x *wm831x = clkdata->wm831x;
0071 int ret;
0072
0073 ret = wm831x_reg_read(wm831x, WM831X_FLL_CONTROL_1);
0074 if (ret < 0) {
0075 dev_err(wm831x->dev, "Unable to read FLL_CONTROL_1: %d\n",
0076 ret);
0077 return true;
0078 }
0079
0080 return (ret & WM831X_FLL_ENA) != 0;
0081 }
0082
0083 static int wm831x_fll_prepare(struct clk_hw *hw)
0084 {
0085 struct wm831x_clk *clkdata = container_of(hw, struct wm831x_clk,
0086 fll_hw);
0087 struct wm831x *wm831x = clkdata->wm831x;
0088 int ret;
0089
0090 ret = wm831x_set_bits(wm831x, WM831X_FLL_CONTROL_1,
0091 WM831X_FLL_ENA, WM831X_FLL_ENA);
0092 if (ret != 0)
0093 dev_crit(wm831x->dev, "Failed to enable FLL: %d\n", ret);
0094
0095
0096 usleep_range(2000, 3000);
0097
0098 return ret;
0099 }
0100
0101 static void wm831x_fll_unprepare(struct clk_hw *hw)
0102 {
0103 struct wm831x_clk *clkdata = container_of(hw, struct wm831x_clk,
0104 fll_hw);
0105 struct wm831x *wm831x = clkdata->wm831x;
0106 int ret;
0107
0108 ret = wm831x_set_bits(wm831x, WM831X_FLL_CONTROL_1, WM831X_FLL_ENA, 0);
0109 if (ret != 0)
0110 dev_crit(wm831x->dev, "Failed to disable FLL: %d\n", ret);
0111 }
0112
0113 static unsigned long wm831x_fll_recalc_rate(struct clk_hw *hw,
0114 unsigned long parent_rate)
0115 {
0116 struct wm831x_clk *clkdata = container_of(hw, struct wm831x_clk,
0117 fll_hw);
0118 struct wm831x *wm831x = clkdata->wm831x;
0119 int ret;
0120
0121 ret = wm831x_reg_read(wm831x, WM831X_CLOCK_CONTROL_2);
0122 if (ret < 0) {
0123 dev_err(wm831x->dev, "Unable to read CLOCK_CONTROL_2: %d\n",
0124 ret);
0125 return 0;
0126 }
0127
0128 if (ret & WM831X_FLL_AUTO)
0129 return wm831x_fll_auto_rates[ret & WM831X_FLL_AUTO_FREQ_MASK];
0130
0131 dev_err(wm831x->dev, "FLL only supported in AUTO mode\n");
0132
0133 return 0;
0134 }
0135
0136 static long wm831x_fll_round_rate(struct clk_hw *hw, unsigned long rate,
0137 unsigned long *unused)
0138 {
0139 int best = 0;
0140 int i;
0141
0142 for (i = 0; i < ARRAY_SIZE(wm831x_fll_auto_rates); i++)
0143 if (abs(wm831x_fll_auto_rates[i] - rate) <
0144 abs(wm831x_fll_auto_rates[best] - rate))
0145 best = i;
0146
0147 return wm831x_fll_auto_rates[best];
0148 }
0149
0150 static int wm831x_fll_set_rate(struct clk_hw *hw, unsigned long rate,
0151 unsigned long parent_rate)
0152 {
0153 struct wm831x_clk *clkdata = container_of(hw, struct wm831x_clk,
0154 fll_hw);
0155 struct wm831x *wm831x = clkdata->wm831x;
0156 int i;
0157
0158 for (i = 0; i < ARRAY_SIZE(wm831x_fll_auto_rates); i++)
0159 if (wm831x_fll_auto_rates[i] == rate)
0160 break;
0161 if (i == ARRAY_SIZE(wm831x_fll_auto_rates))
0162 return -EINVAL;
0163
0164 if (wm831x_fll_is_prepared(hw))
0165 return -EPERM;
0166
0167 return wm831x_set_bits(wm831x, WM831X_CLOCK_CONTROL_2,
0168 WM831X_FLL_AUTO_FREQ_MASK, i);
0169 }
0170
0171 static const char *wm831x_fll_parents[] = {
0172 "xtal",
0173 "clkin",
0174 };
0175
0176 static u8 wm831x_fll_get_parent(struct clk_hw *hw)
0177 {
0178 struct wm831x_clk *clkdata = container_of(hw, struct wm831x_clk,
0179 fll_hw);
0180 struct wm831x *wm831x = clkdata->wm831x;
0181 int ret;
0182
0183
0184 ret = wm831x_reg_read(wm831x, WM831X_CLOCK_CONTROL_2);
0185 if (ret < 0) {
0186 dev_err(wm831x->dev, "Unable to read CLOCK_CONTROL_2: %d\n",
0187 ret);
0188 return 0;
0189 }
0190
0191 if (ret & WM831X_FLL_AUTO)
0192 return 0;
0193
0194 ret = wm831x_reg_read(wm831x, WM831X_FLL_CONTROL_5);
0195 if (ret < 0) {
0196 dev_err(wm831x->dev, "Unable to read FLL_CONTROL_5: %d\n",
0197 ret);
0198 return 0;
0199 }
0200
0201 switch (ret & WM831X_FLL_CLK_SRC_MASK) {
0202 case 0:
0203 return 0;
0204 case 1:
0205 return 1;
0206 default:
0207 dev_err(wm831x->dev, "Unsupported FLL clock source %d\n",
0208 ret & WM831X_FLL_CLK_SRC_MASK);
0209 return 0;
0210 }
0211 }
0212
0213 static const struct clk_ops wm831x_fll_ops = {
0214 .is_prepared = wm831x_fll_is_prepared,
0215 .prepare = wm831x_fll_prepare,
0216 .unprepare = wm831x_fll_unprepare,
0217 .round_rate = wm831x_fll_round_rate,
0218 .recalc_rate = wm831x_fll_recalc_rate,
0219 .set_rate = wm831x_fll_set_rate,
0220 .get_parent = wm831x_fll_get_parent,
0221 };
0222
0223 static const struct clk_init_data wm831x_fll_init = {
0224 .name = "fll",
0225 .ops = &wm831x_fll_ops,
0226 .parent_names = wm831x_fll_parents,
0227 .num_parents = ARRAY_SIZE(wm831x_fll_parents),
0228 .flags = CLK_SET_RATE_GATE,
0229 };
0230
0231 static int wm831x_clkout_is_prepared(struct clk_hw *hw)
0232 {
0233 struct wm831x_clk *clkdata = container_of(hw, struct wm831x_clk,
0234 clkout_hw);
0235 struct wm831x *wm831x = clkdata->wm831x;
0236 int ret;
0237
0238 ret = wm831x_reg_read(wm831x, WM831X_CLOCK_CONTROL_1);
0239 if (ret < 0) {
0240 dev_err(wm831x->dev, "Unable to read CLOCK_CONTROL_1: %d\n",
0241 ret);
0242 return false;
0243 }
0244
0245 return (ret & WM831X_CLKOUT_ENA) != 0;
0246 }
0247
0248 static int wm831x_clkout_prepare(struct clk_hw *hw)
0249 {
0250 struct wm831x_clk *clkdata = container_of(hw, struct wm831x_clk,
0251 clkout_hw);
0252 struct wm831x *wm831x = clkdata->wm831x;
0253 int ret;
0254
0255 ret = wm831x_reg_unlock(wm831x);
0256 if (ret != 0) {
0257 dev_crit(wm831x->dev, "Failed to lock registers: %d\n", ret);
0258 return ret;
0259 }
0260
0261 ret = wm831x_set_bits(wm831x, WM831X_CLOCK_CONTROL_1,
0262 WM831X_CLKOUT_ENA, WM831X_CLKOUT_ENA);
0263 if (ret != 0)
0264 dev_crit(wm831x->dev, "Failed to enable CLKOUT: %d\n", ret);
0265
0266 wm831x_reg_lock(wm831x);
0267
0268 return ret;
0269 }
0270
0271 static void wm831x_clkout_unprepare(struct clk_hw *hw)
0272 {
0273 struct wm831x_clk *clkdata = container_of(hw, struct wm831x_clk,
0274 clkout_hw);
0275 struct wm831x *wm831x = clkdata->wm831x;
0276 int ret;
0277
0278 ret = wm831x_reg_unlock(wm831x);
0279 if (ret != 0) {
0280 dev_crit(wm831x->dev, "Failed to lock registers: %d\n", ret);
0281 return;
0282 }
0283
0284 ret = wm831x_set_bits(wm831x, WM831X_CLOCK_CONTROL_1,
0285 WM831X_CLKOUT_ENA, 0);
0286 if (ret != 0)
0287 dev_crit(wm831x->dev, "Failed to disable CLKOUT: %d\n", ret);
0288
0289 wm831x_reg_lock(wm831x);
0290 }
0291
0292 static const char *wm831x_clkout_parents[] = {
0293 "fll",
0294 "xtal",
0295 };
0296
0297 static u8 wm831x_clkout_get_parent(struct clk_hw *hw)
0298 {
0299 struct wm831x_clk *clkdata = container_of(hw, struct wm831x_clk,
0300 clkout_hw);
0301 struct wm831x *wm831x = clkdata->wm831x;
0302 int ret;
0303
0304 ret = wm831x_reg_read(wm831x, WM831X_CLOCK_CONTROL_1);
0305 if (ret < 0) {
0306 dev_err(wm831x->dev, "Unable to read CLOCK_CONTROL_1: %d\n",
0307 ret);
0308 return 0;
0309 }
0310
0311 if (ret & WM831X_CLKOUT_SRC)
0312 return 1;
0313 else
0314 return 0;
0315 }
0316
0317 static int wm831x_clkout_set_parent(struct clk_hw *hw, u8 parent)
0318 {
0319 struct wm831x_clk *clkdata = container_of(hw, struct wm831x_clk,
0320 clkout_hw);
0321 struct wm831x *wm831x = clkdata->wm831x;
0322
0323 return wm831x_set_bits(wm831x, WM831X_CLOCK_CONTROL_1,
0324 WM831X_CLKOUT_SRC,
0325 parent << WM831X_CLKOUT_SRC_SHIFT);
0326 }
0327
0328 static const struct clk_ops wm831x_clkout_ops = {
0329 .is_prepared = wm831x_clkout_is_prepared,
0330 .prepare = wm831x_clkout_prepare,
0331 .unprepare = wm831x_clkout_unprepare,
0332 .get_parent = wm831x_clkout_get_parent,
0333 .set_parent = wm831x_clkout_set_parent,
0334 };
0335
0336 static const struct clk_init_data wm831x_clkout_init = {
0337 .name = "clkout",
0338 .ops = &wm831x_clkout_ops,
0339 .parent_names = wm831x_clkout_parents,
0340 .num_parents = ARRAY_SIZE(wm831x_clkout_parents),
0341 .flags = CLK_SET_RATE_PARENT,
0342 };
0343
0344 static int wm831x_clk_probe(struct platform_device *pdev)
0345 {
0346 struct wm831x *wm831x = dev_get_drvdata(pdev->dev.parent);
0347 struct wm831x_clk *clkdata;
0348 int ret;
0349
0350 clkdata = devm_kzalloc(&pdev->dev, sizeof(*clkdata), GFP_KERNEL);
0351 if (!clkdata)
0352 return -ENOMEM;
0353
0354 clkdata->wm831x = wm831x;
0355
0356
0357 ret = wm831x_reg_read(wm831x, WM831X_CLOCK_CONTROL_2);
0358 if (ret < 0) {
0359 dev_err(wm831x->dev, "Unable to read CLOCK_CONTROL_2: %d\n",
0360 ret);
0361 return ret;
0362 }
0363 clkdata->xtal_ena = ret & WM831X_XTAL_ENA;
0364
0365 clkdata->xtal_hw.init = &wm831x_xtal_init;
0366 ret = devm_clk_hw_register(&pdev->dev, &clkdata->xtal_hw);
0367 if (ret)
0368 return ret;
0369
0370 clkdata->fll_hw.init = &wm831x_fll_init;
0371 ret = devm_clk_hw_register(&pdev->dev, &clkdata->fll_hw);
0372 if (ret)
0373 return ret;
0374
0375 clkdata->clkout_hw.init = &wm831x_clkout_init;
0376 ret = devm_clk_hw_register(&pdev->dev, &clkdata->clkout_hw);
0377 if (ret)
0378 return ret;
0379
0380 platform_set_drvdata(pdev, clkdata);
0381
0382 return 0;
0383 }
0384
0385 static struct platform_driver wm831x_clk_driver = {
0386 .probe = wm831x_clk_probe,
0387 .driver = {
0388 .name = "wm831x-clk",
0389 },
0390 };
0391
0392 module_platform_driver(wm831x_clk_driver);
0393
0394
0395 MODULE_AUTHOR("Mark Brown <broonie@opensource.wolfsonmicro.com>");
0396 MODULE_DESCRIPTION("WM831x clock driver");
0397 MODULE_LICENSE("GPL");
0398 MODULE_ALIAS("platform:wm831x-clk");