blob: 328f4b63b5606cc22d7ca8f22189dc2bf4061aa1 [file] [log] [blame]
Fenglin Wu50b1eba2017-11-16 08:39:11 +08001/* Copyright (c) 2018, The Linux Foundation. All rights reserved.
2 *
3 * This program is free software; you can redistribute it and/or modify
4 * it under the terms of the GNU General Public License version 2 and
5 * only version 2 as published by the Free Software Foundation.
6 *
7 * This program is distributed in the hope that it will be useful,
8 * but WITHOUT ANY WARRANTY; without even the implied warranty of
9 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10 * GNU General Public License for more details.
11 */
12
13#define pr_fmt(fmt) "%s: " fmt, __func__
14
15#include <linux/bitops.h>
16#include <linux/device.h>
17#include <linux/err.h>
18#include <linux/init.h>
19#include <linux/kernel.h>
20#include <linux/module.h>
21#include <linux/mutex.h>
22#include <linux/of.h>
23#include <linux/of_address.h>
24#include <linux/platform_device.h>
25#include <linux/pwm.h>
26#include <linux/regmap.h>
27#include <linux/types.h>
28
29#define REG_SIZE_PER_LPG 0x100
30
31#define REG_LPG_PWM_SIZE_CLK 0x41
32#define REG_LPG_PWM_FREQ_PREDIV_CLK 0x42
33#define REG_LPG_PWM_TYPE_CONFIG 0x43
34#define REG_LPG_PWM_VALUE_LSB 0x44
35#define REG_LPG_PWM_VALUE_MSB 0x45
36#define REG_LPG_ENABLE_CONTROL 0x46
37#define REG_LPG_PWM_SYNC 0x47
38
39/* REG_LPG_PWM_SIZE_CLK */
40#define LPG_PWM_SIZE_MASK BIT(4)
41#define LPG_PWM_SIZE_SHIFT 4
42#define LPG_PWM_CLK_FREQ_SEL_MASK GENMASK(1, 0)
43
44/* REG_LPG_PWM_FREQ_PREDIV_CLK */
45#define LPG_PWM_FREQ_PREDIV_MASK GENMASK(6, 5)
46#define LPG_PWM_FREQ_PREDIV_SHIFT 5
47#define LPG_PWM_FREQ_EXPONENT_MASK GENMASK(2, 0)
48
49/* REG_LPG_PWM_TYPE_CONFIG */
50#define LPG_PWM_EN_GLITCH_REMOVAL_MASK BIT(5)
51
52/* REG_LPG_PWM_VALUE_LSB */
53#define LPG_PWM_VALUE_LSB_MASK GENMASK(7, 0)
54
55/* REG_LPG_PWM_VALUE_MSB */
56#define LPG_PWM_VALUE_MSB_MASK BIT(0)
57
58/* REG_LPG_ENABLE_CONTROL */
59#define LPG_EN_LPG_OUT_BIT BIT(7)
60#define LPG_PWM_SRC_SELECT_MASK BIT(2)
61#define LPG_PWM_SRC_SELECT_SHIFT 2
62#define LPG_EN_RAMP_GEN_MASK BIT(1)
63#define LPG_EN_RAMP_GEN_SHIFT 1
64
65/* REG_LPG_PWM_SYNC */
66#define LPG_PWM_VALUE_SYNC BIT(0)
67
68#define NUM_PWM_SIZE 2
69#define NUM_PWM_CLK 3
70#define NUM_CLK_PREDIV 4
71#define NUM_PWM_EXP 8
72
73enum {
74 LUT_PATTERN = 0,
75 PWM_OUTPUT,
76};
77
78static const int pwm_size[NUM_PWM_SIZE] = {6, 9};
79static const int clk_freq_hz[NUM_PWM_CLK] = {1024, 32768, 19200000};
80static const int clk_prediv[NUM_CLK_PREDIV] = {1, 3, 5, 6};
81static const int pwm_exponent[NUM_PWM_EXP] = {0, 1, 2, 3, 4, 5, 6, 7};
82
83struct lpg_pwm_config {
84 u32 pwm_size;
85 u32 pwm_clk;
86 u32 prediv;
87 u32 clk_exp;
88 u16 pwm_value;
89 u32 best_period_ns;
90};
91
92struct qpnp_lpg_channel {
93 struct qpnp_lpg_chip *chip;
94 struct lpg_pwm_config pwm_config;
95 u32 lpg_idx;
96 u32 reg_base;
97 u8 src_sel;
98 int current_period_ns;
99 int current_duty_ns;
100};
101
102struct qpnp_lpg_chip {
103 struct pwm_chip pwm_chip;
104 struct regmap *regmap;
105 struct device *dev;
106 struct qpnp_lpg_channel *lpgs;
107 struct mutex bus_lock;
108 u32 num_lpgs;
109};
110
111static int qpnp_lpg_write(struct qpnp_lpg_channel *lpg, u16 addr, u8 val)
112{
113 int rc;
114
115 mutex_lock(&lpg->chip->bus_lock);
116 rc = regmap_write(lpg->chip->regmap, lpg->reg_base + addr, val);
117 if (rc < 0)
118 dev_err(lpg->chip->dev, "Write addr 0x%x with value %d failed, rc=%d\n",
119 lpg->reg_base + addr, val, rc);
120 mutex_unlock(&lpg->chip->bus_lock);
121
122 return rc;
123}
124
125static int qpnp_lpg_masked_write(struct qpnp_lpg_channel *lpg,
126 u16 addr, u8 mask, u8 val)
127{
128 int rc;
129
130 mutex_lock(&lpg->chip->bus_lock);
131 rc = regmap_update_bits(lpg->chip->regmap, lpg->reg_base + addr,
132 mask, val);
133 if (rc < 0)
134 dev_err(lpg->chip->dev, "Update addr 0x%x to val 0x%x with mask 0x%x failed, rc=%d\n",
135 lpg->reg_base + addr, val, mask, rc);
136 mutex_unlock(&lpg->chip->bus_lock);
137
138 return rc;
139}
140
141static struct qpnp_lpg_channel *pwm_dev_to_qpnp_lpg(struct pwm_chip *pwm_chip,
142 struct pwm_device *pwm) {
143
144 struct qpnp_lpg_chip *chip = container_of(pwm_chip,
145 struct qpnp_lpg_chip, pwm_chip);
146 u32 hw_idx = pwm->hwpwm;
147
148 if (hw_idx >= chip->num_lpgs) {
149 dev_err(chip->dev, "hw index %d out of range [0-%d]\n",
150 hw_idx, chip->num_lpgs - 1);
151 return NULL;
152 }
153
154 return &chip->lpgs[hw_idx];
155}
156
157static int __find_index_in_array(int member, const int array[], int length)
158{
159 int i;
160
161 for (i = 0; i < length; i++) {
162 if (member == array[i])
163 return i;
164 }
165
166 return -EINVAL;
167}
168
169static int qpnp_lpg_set_pwm_config(struct qpnp_lpg_channel *lpg)
170{
171 int rc;
172 u8 val, mask;
173 int pwm_size_idx, pwm_clk_idx, prediv_idx, clk_exp_idx;
174
175 pwm_size_idx = __find_index_in_array(lpg->pwm_config.pwm_size,
176 pwm_size, ARRAY_SIZE(pwm_size));
177 pwm_clk_idx = __find_index_in_array(lpg->pwm_config.pwm_clk,
178 clk_freq_hz, ARRAY_SIZE(clk_freq_hz));
179 prediv_idx = __find_index_in_array(lpg->pwm_config.prediv,
180 clk_prediv, ARRAY_SIZE(clk_prediv));
181 clk_exp_idx = __find_index_in_array(lpg->pwm_config.clk_exp,
182 pwm_exponent, ARRAY_SIZE(pwm_exponent));
183
184 if (pwm_size_idx < 0 || pwm_clk_idx < 0
185 || prediv_idx < 0 || clk_exp_idx < 0)
186 return -EINVAL;
187
188 /* pwm_clk_idx is 1 bit lower than the register value */
189 pwm_clk_idx += 1;
190 val = pwm_size_idx << LPG_PWM_SIZE_SHIFT | pwm_clk_idx;
191 mask = LPG_PWM_SIZE_MASK | LPG_PWM_CLK_FREQ_SEL_MASK;
192 rc = qpnp_lpg_masked_write(lpg, REG_LPG_PWM_SIZE_CLK, mask, val);
193 if (rc < 0) {
194 dev_err(lpg->chip->dev, "Write LPG_PWM_SIZE_CLK failed, rc=%d\n",
195 rc);
196 return rc;
197 }
198
199 val = prediv_idx << LPG_PWM_FREQ_PREDIV_SHIFT | clk_exp_idx;
200 mask = LPG_PWM_FREQ_PREDIV_MASK | LPG_PWM_FREQ_EXPONENT_MASK;
201 rc = qpnp_lpg_masked_write(lpg, REG_LPG_PWM_FREQ_PREDIV_CLK, mask, val);
202 if (rc < 0) {
203 dev_err(lpg->chip->dev, "Write LPG_PWM_FREQ_PREDIV_CLK failed, rc=%d\n",
204 rc);
205 return rc;
206 }
207
208 val = lpg->pwm_config.pwm_value & LPG_PWM_VALUE_LSB_MASK;
209 rc = qpnp_lpg_write(lpg, REG_LPG_PWM_VALUE_LSB, val);
210 if (rc < 0) {
211 dev_err(lpg->chip->dev, "Write LPG_PWM_VALUE_LSB failed, rc=%d\n",
212 rc);
213 return rc;
214 }
215
216 val = lpg->pwm_config.pwm_value >> 8;
217 mask = LPG_PWM_VALUE_MSB_MASK;
218 rc = qpnp_lpg_masked_write(lpg, REG_LPG_PWM_VALUE_MSB, mask, val);
219 if (rc < 0) {
220 dev_err(lpg->chip->dev, "Write LPG_PWM_VALUE_MSB failed, rc=%d\n",
221 rc);
222 return rc;
223 }
224
225 val = LPG_PWM_VALUE_SYNC;
226 rc = qpnp_lpg_write(lpg, REG_LPG_PWM_SYNC, val);
227 if (rc < 0) {
228 dev_err(lpg->chip->dev, "Write LPG_PWM_SYNC failed, rc=%d\n",
229 rc);
230 return rc;
231 }
232
233 return rc;
234}
235
236static void __qpnp_lpg_calc_pwm_period(int period_ns,
237 struct lpg_pwm_config *pwm_config)
238{
239 struct lpg_pwm_config configs[NUM_PWM_SIZE];
240 int i, j, m, n;
241 int tmp1, tmp2;
242 int clk_period_ns = 0, pwm_clk_period_ns;
243 int clk_delta_ns = INT_MAX, min_clk_delta_ns = INT_MAX;
244 int pwm_period_delta = INT_MAX, min_pwm_period_delta = INT_MAX;
245 int pwm_size_step;
246
247 /*
248 * (2^pwm_size) * (2^pwm_exp) * prediv * NSEC_PER_SEC
249 * pwm_period = ---------------------------------------------------
250 * clk_freq_hz
251 *
252 * Searching the closest settings for the requested PWM period.
253 */
254 for (n = 0; n < ARRAY_SIZE(pwm_size); n++) {
255 pwm_clk_period_ns = period_ns >> pwm_size[n];
256 for (i = ARRAY_SIZE(clk_freq_hz) - 1; i >= 0; i--) {
257 for (j = 0; j < ARRAY_SIZE(clk_prediv); j++) {
258 for (m = 0; m < ARRAY_SIZE(pwm_exponent); m++) {
259 tmp1 = 1 << pwm_exponent[m];
260 tmp1 *= clk_prediv[j];
261 tmp2 = NSEC_PER_SEC / clk_freq_hz[i];
262
263 clk_period_ns = tmp1 * tmp2;
264
265 clk_delta_ns = abs(pwm_clk_period_ns
266 - clk_period_ns);
267 /*
268 * Find the closest setting for
269 * PWM frequency predivide value
270 */
271 if (clk_delta_ns < min_clk_delta_ns) {
272 min_clk_delta_ns
273 = clk_delta_ns;
274 configs[n].pwm_clk
275 = clk_freq_hz[i];
276 configs[n].prediv
277 = clk_prediv[j];
278 configs[n].clk_exp
279 = pwm_exponent[m];
280 configs[n].pwm_size
281 = pwm_size[n];
282 configs[n].best_period_ns
283 = clk_period_ns;
284 }
285 }
286 }
287 }
288
289 configs[n].best_period_ns *= 1 << pwm_size[n];
290 /* Find the closest setting for PWM period */
291 if (min_clk_delta_ns < INT_MAX >> pwm_size[n])
292 pwm_period_delta = min_clk_delta_ns << pwm_size[n];
293 else
294 pwm_period_delta = INT_MAX;
295 if (pwm_period_delta < min_pwm_period_delta) {
296 min_pwm_period_delta = pwm_period_delta;
297 memcpy(pwm_config, &configs[n],
298 sizeof(struct lpg_pwm_config));
299 }
300 }
301
302 /* Larger PWM size can achieve better resolution for PWM duty */
303 for (n = ARRAY_SIZE(pwm_size) - 1; n > 0; n--) {
304 if (pwm_config->pwm_size >= pwm_size[n])
305 break;
306 pwm_size_step = pwm_size[n] - pwm_config->pwm_size;
307 if (pwm_config->clk_exp >= pwm_size_step) {
308 pwm_config->pwm_size = pwm_size[n];
309 pwm_config->clk_exp -= pwm_size_step;
310 }
311 }
312 pr_debug("PWM setting for period_ns %d: pwm_clk = %dHZ, prediv = %d, exponent = %d, pwm_size = %d\n",
313 period_ns, pwm_config->pwm_clk, pwm_config->prediv,
314 pwm_config->clk_exp, pwm_config->pwm_size);
315 pr_debug("Actual period: %dns\n", pwm_config->best_period_ns);
316}
317
318static void __qpnp_lpg_calc_pwm_duty(int period_ns, int duty_ns,
319 struct lpg_pwm_config *pwm_config)
320{
321 u16 pwm_value, max_pwm_value;
322
323 if ((1 << pwm_config->pwm_size) > (INT_MAX / duty_ns))
324 pwm_value = duty_ns / (period_ns >> pwm_config->pwm_size);
325 else
326 pwm_value = (duty_ns << pwm_config->pwm_size) / period_ns;
327
328 max_pwm_value = (1 << pwm_config->pwm_size) - 1;
329 if (pwm_value > max_pwm_value)
330 pwm_value = max_pwm_value;
331 pwm_config->pwm_value = pwm_value;
332}
333
334static int qpnp_lpg_pwm_config(struct pwm_chip *pwm_chip,
335 struct pwm_device *pwm, int duty_ns, int period_ns)
336{
337 struct qpnp_lpg_channel *lpg;
338 int rc = 0;
339
340 lpg = pwm_dev_to_qpnp_lpg(pwm_chip, pwm);
341 if (lpg == NULL) {
342 dev_err(pwm_chip->dev, "lpg not found\n");
343 return -ENODEV;
344 }
345
346 if (duty_ns > period_ns) {
347 dev_err(pwm_chip->dev, "Duty %dns is larger than period %dns\n",
348 duty_ns, period_ns);
349 return -EINVAL;
350 }
351
352 if (period_ns != lpg->current_period_ns)
353 __qpnp_lpg_calc_pwm_period(period_ns, &lpg->pwm_config);
354
355 if (period_ns != lpg->current_period_ns ||
356 duty_ns != lpg->current_duty_ns)
357 __qpnp_lpg_calc_pwm_duty(period_ns, duty_ns, &lpg->pwm_config);
358
359 rc = qpnp_lpg_set_pwm_config(lpg);
360 if (rc < 0)
361 dev_err(pwm_chip->dev, "Config PWM failed for channel %d, rc=%d\n",
362 lpg->lpg_idx, rc);
363
364 return rc;
365}
366
367static int qpnp_lpg_pwm_enable(struct pwm_chip *pwm_chip,
368 struct pwm_device *pwm)
369{
370 struct qpnp_lpg_channel *lpg;
371 int rc = 0;
372 u8 mask, val;
373
374 lpg = pwm_dev_to_qpnp_lpg(pwm_chip, pwm);
375 if (lpg == NULL) {
376 dev_err(pwm_chip->dev, "lpg not found\n");
377 return -ENODEV;
378 }
379
380 mask = LPG_PWM_SRC_SELECT_MASK | LPG_EN_LPG_OUT_BIT;
381 val = lpg->src_sel << LPG_PWM_SRC_SELECT_SHIFT | LPG_EN_LPG_OUT_BIT;
382
383 rc = qpnp_lpg_masked_write(lpg, REG_LPG_ENABLE_CONTROL, mask, val);
384 if (rc < 0)
385 dev_err(pwm_chip->dev, "Enable PWM output failed for channel %d, rc=%d\n",
386 lpg->lpg_idx, rc);
387
388 return rc;
389}
390
391static void qpnp_lpg_pwm_disable(struct pwm_chip *pwm_chip,
392 struct pwm_device *pwm)
393{
394 struct qpnp_lpg_channel *lpg;
395 int rc;
396 u8 mask, val;
397
398 lpg = pwm_dev_to_qpnp_lpg(pwm_chip, pwm);
399 if (lpg == NULL) {
400 dev_err(pwm_chip->dev, "lpg not found\n");
401 return;
402 }
403
404 mask = LPG_PWM_SRC_SELECT_MASK | LPG_EN_LPG_OUT_BIT;
405 val = lpg->src_sel << LPG_PWM_SRC_SELECT_SHIFT;
406
407 rc = qpnp_lpg_masked_write(lpg, REG_LPG_ENABLE_CONTROL, mask, val);
408 if (rc < 0)
409 dev_err(pwm_chip->dev, "Disable PWM output failed for channel %d, rc=%d\n",
410 lpg->lpg_idx, rc);
411}
412
413#ifdef CONFIG_DEBUG_FS
414static void qpnp_lpg_pwm_dbg_show(struct pwm_chip *pwm_chip, struct seq_file *s)
415{
416 struct qpnp_lpg_channel *lpg;
417 struct lpg_pwm_config *cfg;
418 struct pwm_device *pwm;
419 int i;
420
421 for (i = 0; i < pwm_chip->npwm; i++) {
422 pwm = &pwm_chip->pwms[i];
423
424 lpg = pwm_dev_to_qpnp_lpg(pwm_chip, pwm);
425 if (lpg == NULL) {
426 dev_err(pwm_chip->dev, "lpg not found\n");
427 return;
428 }
429
430 if (test_bit(PWMF_REQUESTED, &pwm->flags)) {
431 seq_printf(s, "LPG %d is requested by %s\n",
432 lpg->lpg_idx + 1, pwm->label);
433 } else {
434 seq_printf(s, "LPG %d is free\n",
435 lpg->lpg_idx + 1);
436 continue;
437 }
438
439 if (pwm_is_enabled(pwm)) {
440 seq_puts(s, " enabled\n");
441 } else {
442 seq_puts(s, " disabled\n");
443 continue;
444 }
445
446 cfg = &lpg->pwm_config;
447 seq_printf(s, " clk = %dHz\n", cfg->pwm_clk);
448 seq_printf(s, " pwm_size = %d\n", cfg->pwm_size);
449 seq_printf(s, " prediv = %d\n", cfg->prediv);
450 seq_printf(s, " exponent = %d\n", cfg->clk_exp);
451 seq_printf(s, " pwm_value = %d\n", cfg->pwm_value);
452 seq_printf(s, " Requested period: %dns, best period = %dns\n",
453 pwm_get_period(pwm), cfg->best_period_ns);
454 }
455}
456#endif
457
458static const struct pwm_ops qpnp_lpg_pwm_ops = {
459 .config = qpnp_lpg_pwm_config,
460 .enable = qpnp_lpg_pwm_enable,
461 .disable = qpnp_lpg_pwm_disable,
462#ifdef CONFIG_DEBUG_FS
463 .dbg_show = qpnp_lpg_pwm_dbg_show,
464#endif
465 .owner = THIS_MODULE,
466};
467
468static int qpnp_lpg_parse_dt(struct qpnp_lpg_chip *chip)
469{
470 int rc = 0, i;
471 u64 base, length;
472 const __be32 *addr;
473
474 addr = of_get_address(chip->dev->of_node, 0, NULL, NULL);
475 if (!addr) {
476 dev_err(chip->dev, "Getting address failed\n");
477 return -EINVAL;
478 }
479 base = be32_to_cpu(addr[0]);
480 length = be32_to_cpu(addr[1]);
481
482 chip->num_lpgs = length / REG_SIZE_PER_LPG;
483 chip->lpgs = devm_kcalloc(chip->dev, chip->num_lpgs,
484 sizeof(*chip->lpgs), GFP_KERNEL);
485 if (!chip->lpgs)
486 return -ENOMEM;
487
488 for (i = 0; i < chip->num_lpgs; i++) {
489 chip->lpgs[i].chip = chip;
490 chip->lpgs[i].lpg_idx = i;
491 chip->lpgs[i].reg_base = base + i * REG_SIZE_PER_LPG;
492 chip->lpgs[i].src_sel = PWM_OUTPUT;
493 }
494
495 return rc;
496}
497
498static int qpnp_lpg_probe(struct platform_device *pdev)
499{
500 int rc;
501 struct qpnp_lpg_chip *chip;
502
503 chip = devm_kzalloc(&pdev->dev, sizeof(*chip), GFP_KERNEL);
504 if (!chip)
505 return -ENOMEM;
506
507 chip->dev = &pdev->dev;
508 chip->regmap = dev_get_regmap(chip->dev->parent, NULL);
509 if (!chip->regmap) {
510 dev_err(chip->dev, "Getting regmap failed\n");
511 return -EINVAL;
512 }
513
514 rc = qpnp_lpg_parse_dt(chip);
515 if (rc < 0) {
516 dev_err(chip->dev, "Devicetree properties parsing failed, rc=%d\n",
517 rc);
518 return rc;
519 }
520
521 dev_set_drvdata(chip->dev, chip);
522
523 mutex_init(&chip->bus_lock);
524 chip->pwm_chip.dev = chip->dev;
525 chip->pwm_chip.base = -1;
526 chip->pwm_chip.npwm = chip->num_lpgs;
527 chip->pwm_chip.ops = &qpnp_lpg_pwm_ops;
528
529 rc = pwmchip_add(&chip->pwm_chip);
530 if (rc < 0) {
531 dev_err(chip->dev, "Add pwmchip failed, rc=%d\n", rc);
532 mutex_destroy(&chip->bus_lock);
533 }
534
535 return rc;
536}
537
538static int qpnp_lpg_remove(struct platform_device *pdev)
539{
540 struct qpnp_lpg_chip *chip = dev_get_drvdata(&pdev->dev);
541 int rc = 0;
542
543 rc = pwmchip_remove(&chip->pwm_chip);
544 if (rc < 0)
545 dev_err(chip->dev, "Remove pwmchip failed, rc=%d\n", rc);
546
547 mutex_destroy(&chip->bus_lock);
548 dev_set_drvdata(chip->dev, NULL);
549
550 return rc;
551}
552
553static const struct of_device_id qpnp_lpg_of_match[] = {
554 { .compatible = "qcom,pwm-lpg",},
555 { },
556};
557
558static struct platform_driver qpnp_lpg_driver = {
559 .driver = {
560 .name = "qcom,pwm-lpg",
561 .of_match_table = qpnp_lpg_of_match,
562 },
563 .probe = qpnp_lpg_probe,
564 .remove = qpnp_lpg_remove,
565};
566module_platform_driver(qpnp_lpg_driver);
567
568MODULE_DESCRIPTION("QTI LPG driver");
569MODULE_LICENSE("GPL v2");
570MODULE_ALIAS("pwm:pwm-lpg");