1 /*
2 * ALSA SoC Texas Instruments TAS2770 High Performance 4W Smart Amplifier
3 *
4 * Copyright (C) 2016 Texas Instruments, Inc.
5 *
6 * Author: saiprasad
7 *
8 * This package is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License version 2 as
10 * published by the Free Software Foundation.
11 *
12 * THIS PACKAGE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR
13 * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
14 * WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
15 *
16 */
17 #ifdef CONFIG_TAS2770_REGMAP
19 #define DEBUG
20 #include <linux/module.h>
21 #include <linux/moduleparam.h>
22 #include <linux/err.h>
23 #include <linux/init.h>
24 #include <linux/delay.h>
25 #include <linux/pm.h>
26 #include <linux/i2c.h>
27 #include <linux/gpio.h>
28 #include <linux/regulator/consumer.h>
29 #include <linux/firmware.h>
30 #include <linux/regmap.h>
31 #include <linux/of.h>
32 #include <linux/of_gpio.h>
33 #include <linux/slab.h>
34 #include <sound/soc.h>
36 #include "tas2770.h"
37 #include "tas2770-codec.h"
39 static const struct reg_default tas2770_reg_defaults[] = {
40 { TAS2770_Page, 0x00 },
41 { TAS2770_SoftwareReset, 0x00 },
42 { TAS2770_PowerControl, 0x0e },
43 { TAS2770_PlaybackConfigurationReg0, 0x10 },
44 { TAS2770_PlaybackConfigurationReg1, 0x01 },
45 { TAS2770_PlaybackConfigurationReg2, 0x00 },
46 { TAS2770_MiscConfigurationReg0, 0x07 },
47 { TAS2770_TDMConfigurationReg1, 0x02 },
48 { TAS2770_TDMConfigurationReg2, 0x0a },
49 { TAS2770_TDMConfigurationReg3, 0x10 },
50 { TAS2770_InterruptMaskReg0, 0xfc },
51 { TAS2770_InterruptMaskReg1, 0xb1 },
52 { TAS2770_InterruptConfiguration, 0x05 },
53 { TAS2770_MiscIRQ, 0x81 },
54 { TAS2770_ClockConfiguration, 0x0d },
56 };
58 static bool tas2770_volatile(struct device *dev, unsigned int reg)
59 {
60 switch (reg) {
61 case TAS2770_Page: /* regmap implementation requires this */
62 case TAS2770_SoftwareReset: /* always clears after write */
63 case TAS2770_BrownOutPreventionReg0:/* has a self clearing bit */
64 case TAS2770_LiveInterruptReg0:
65 case TAS2770_LiveInterruptReg1:
66 case TAS2770_LatchedInterruptReg0:/* Sticky interrupt flags */
67 case TAS2770_LatchedInterruptReg1:/* Sticky interrupt flags */
68 case TAS2770_VBATMSB:
69 case TAS2770_VBATLSB:
70 case TAS2770_TEMPMSB:
71 case TAS2770_TEMPLSB:
72 return true;
73 }
74 return false;
75 }
77 static bool tas2770_writeable(struct device *dev, unsigned int reg)
78 {
79 switch (reg) {
80 case TAS2770_LiveInterruptReg0:
81 case TAS2770_LiveInterruptReg1:
82 case TAS2770_LatchedInterruptReg0:
83 case TAS2770_LatchedInterruptReg1:
84 case TAS2770_VBATMSB:
85 case TAS2770_VBATLSB:
86 case TAS2770_TEMPMSB:
87 case TAS2770_TEMPLSB:
88 case TAS2770_TDMClockdetectionmonitor:
89 case TAS2770_RevisionandPGID:
90 return false;
91 }
92 return true;
93 }
95 #if 0
96 static const struct regmap_range_cfg tas2770_ranges[] = {
97 {
98 .range_min = 0,
99 .range_max = 1 * 128,
100 .selector_reg = TAS2770_Page,
101 .selector_mask = 0xff,
102 .selector_shift = 0,
103 .window_start = 0,
104 .window_len = 128,
105 },
106 };
107 #endif
109 static const struct regmap_config tas2770_i2c_regmap = {
110 .reg_bits = 8,
111 .val_bits = 8,
112 .writeable_reg = tas2770_writeable,
113 .volatile_reg = tas2770_volatile,
114 .reg_defaults = tas2770_reg_defaults,
115 .num_reg_defaults = ARRAY_SIZE(tas2770_reg_defaults),
116 // .cache_type = REGCACHE_NONE,
117 .cache_type = REGCACHE_RBTREE,
118 // .ranges = tas2770_ranges,
119 // .num_ranges = ARRAY_SIZE(tas2770_ranges),
120 .max_register = 1 * 128,
121 };
124 static void tas2770_hw_reset(struct tas2770_priv *pTAS2770)
125 {
126 if (gpio_is_valid(pTAS2770->mnResetGPIO)) {
127 gpio_direction_output(pTAS2770->mnResetGPIO, 0);
128 msleep(5);
129 gpio_direction_output(pTAS2770->mnResetGPIO, 1);
130 msleep(2);
131 }
133 pTAS2770->mnCurrentBook = -1;
134 pTAS2770->mnCurrentPage = -1;
135 }
137 void tas2770_clearIRQ(struct tas2770_priv *pTAS2770)
138 {
139 // unsigned int nValue;
140 #if 0
141 int nResult = 0;
143 nResult = pTAS2770->read(pTAS2770, TAS2770_FLAGS_1, &nValue);
144 if (nResult >= 0)
145 pTAS2770->read(pTAS2770, TAS2770_FLAGS_2, &nValue);
146 #endif
147 }
149 void tas2770_enableIRQ(struct tas2770_priv *pTAS2770, bool enable)
150 {
151 if (enable) {
152 if (pTAS2770->mbIRQEnable)
153 return;
155 if (gpio_is_valid(pTAS2770->mnIRQGPIO))
156 enable_irq(pTAS2770->mnIRQ);
158 schedule_delayed_work(&pTAS2770->irq_work, msecs_to_jiffies(10));
159 pTAS2770->mbIRQEnable = true;
160 } else {
161 if (!pTAS2770->mbIRQEnable)
162 return;
164 if (gpio_is_valid(pTAS2770->mnIRQGPIO))
165 disable_irq_nosync(pTAS2770->mnIRQ);
166 pTAS2770->mbIRQEnable = false;
167 }
168 }
170 static void irq_work_routine(struct work_struct *work)
171 {
172 struct tas2770_priv *pTAS2770 =
173 container_of(work, struct tas2770_priv, irq_work.work);
174 // unsigned int nDevInt1Status = 0, nDevInt2Status = 0;
175 // int nCounter = 2;
176 // int nResult = 0;
178 #ifdef CONFIG_TAS2770_CODEC
179 mutex_lock(&pTAS2770->codec_lock);
180 #endif
182 #ifdef CONFIG_TAS2770_MISC
183 mutex_lock(&pTAS2770->file_lock);
184 #endif
185 if (pTAS2770->mbRuntimeSuspend) {
186 dev_info(pTAS2770->dev, "%s, Runtime Suspended\n", __func__);
187 goto end;
188 }
190 if (!pTAS2770->mbPowerUp) {
191 dev_info(pTAS2770->dev, "%s, device not powered\n", __func__);
192 goto end;
193 }
195 #if 0
196 nResult = tas2770_dev_write(pTAS2770, TAS2770_INT_GEN_REG, 0x00);
197 if (nResult < 0)
198 goto reload;
200 nResult = tas2770_dev_read(pTAS2770, TAS2770_FLAGS_1, &nDevInt1Status);
201 if (nResult >= 0)
202 nResult = tas2770_dev_read(pTAS2770, TAS2770_FLAGS_2, &nDevInt2Status);
203 else
204 goto reload;
206 if (((nDevInt1Status & 0xfc) != 0) || ((nDevInt2Status & 0xc0) != 0)) {
207 /* in case of INT_OC, INT_UV, INT_OT, INT_BO, INT_CL, INT_CLK1, INT_CLK2 */
208 dev_dbg(pTAS2770->dev, "IRQ critical Error : 0x%x, 0x%x\n",
209 nDevInt1Status, nDevInt2Status);
211 if (nDevInt1Status & 0x80) {
212 pTAS2770->mnErrCode |= ERROR_OVER_CURRENT;
213 dev_err(pTAS2770->dev, "SPK over current!\n");
214 } else
215 pTAS2770->mnErrCode &= ~ERROR_OVER_CURRENT;
217 if (nDevInt1Status & 0x40) {
218 pTAS2770->mnErrCode |= ERROR_UNDER_VOLTAGE;
219 dev_err(pTAS2770->dev, "SPK under voltage!\n");
220 } else
221 pTAS2770->mnErrCode &= ~ERROR_UNDER_VOLTAGE;
223 if (nDevInt1Status & 0x20) {
224 pTAS2770->mnErrCode |= ERROR_CLK_HALT;
225 dev_err(pTAS2770->dev, "clk halted!\n");
226 } else
227 pTAS2770->mnErrCode &= ~ERROR_CLK_HALT;
229 if (nDevInt1Status & 0x10) {
230 pTAS2770->mnErrCode |= ERROR_DIE_OVERTEMP;
231 dev_err(pTAS2770->dev, "die over temperature!\n");
232 } else
233 pTAS2770->mnErrCode &= ~ERROR_DIE_OVERTEMP;
235 if (nDevInt1Status & 0x08) {
236 pTAS2770->mnErrCode |= ERROR_BROWNOUT;
237 dev_err(pTAS2770->dev, "brownout!\n");
238 } else
239 pTAS2770->mnErrCode &= ~ERROR_BROWNOUT;
241 if (nDevInt1Status & 0x04) {
242 pTAS2770->mnErrCode |= ERROR_CLK_LOST;
243 } else
244 pTAS2770->mnErrCode &= ~ERROR_CLK_LOST;
246 if (nDevInt2Status & 0x80) {
247 pTAS2770->mnErrCode |= ERROR_CLK_DET1;
248 dev_err(pTAS2770->dev, "clk detection 1!\n");
249 } else
250 pTAS2770->mnErrCode &= ~ERROR_CLK_DET1;
252 if (nDevInt2Status & 0x40) {
253 pTAS2770->mnErrCode |= ERROR_CLK_DET2;
254 dev_err(pTAS2770->dev, "clk detection 2!\n");
255 } else
256 pTAS2770->mnErrCode &= ~ERROR_CLK_DET2;
258 goto reload;
259 } else {
260 dev_dbg(pTAS2770->dev, "IRQ status : 0x%x, 0x%x\n",
261 nDevInt1Status, nDevInt2Status);
262 nCounter = 2;
264 while (nCounter > 0) {
265 nResult = tas2770_dev_read(pTAS2770, TAS2770_POWER_UP_FLAG_REG, &nDevInt1Status);
266 if (nResult < 0)
267 goto reload;
269 if ((nDevInt1Status & 0xc0) == 0xc0)
270 break;
272 nCounter--;
273 if (nCounter > 0) {
274 /* in case check pow status just after power on TAS2770 */
275 dev_dbg(pTAS2770->dev, "PowSts B: 0x%x, check again after 10ms\n",
276 nDevInt1Status);
277 msleep(10);
278 }
279 }
281 if ((nDevInt1Status & 0xc0) != 0xc0) {
282 dev_err(pTAS2770->dev, "%s, Critical ERROR B[%d]_P[%d]_R[%d]= 0x%x\n",
283 __func__,
284 TAS2770_BOOK_ID(TAS2770_POWER_UP_FLAG_REG),
285 TAS2770_PAGE_ID(TAS2770_POWER_UP_FLAG_REG),
286 TAS2770_PAGE_REG(TAS2770_POWER_UP_FLAG_REG),
287 nDevInt1Status);
288 pTAS2770->mnErrCode |= ERROR_CLASSD_PWR;
289 goto reload;
290 }
291 pTAS2770->mnErrCode &= ~ERROR_CLASSD_PWR;
292 }
294 nResult = tas2770_dev_write(pTAS2770, TAS2770_INT_GEN_REG, 0xff);
295 if (nResult < 0)
296 goto reload;
298 goto end;
300 reload:
301 /* hardware reset and reload */
302 tas2770_LoadConfig(pTAS2770, true);
303 #endif
305 end:
306 /*
307 if (!hrtimer_active(&pTAS2770->mtimer)) {
308 dev_dbg(pTAS2770->dev, "%s, start timer\n", __func__);
309 hrtimer_start(&pTAS2770->mtimer,
310 ns_to_ktime((u64)CHECK_PERIOD * NSEC_PER_MSEC), HRTIMER_MODE_REL);
311 }
312 */
314 #ifdef CONFIG_TAS2770_MISC
315 mutex_unlock(&pTAS2770->file_lock);
316 #endif
318 #ifdef CONFIG_TAS2770_CODEC
319 mutex_unlock(&pTAS2770->codec_lock);
320 #endif
321 }
323 static enum hrtimer_restart timer_func(struct hrtimer *timer)
324 {
325 struct tas2770_priv *pTAS2770 = container_of(timer, struct tas2770_priv, mtimer);
327 if (pTAS2770->mbPowerUp) {
328 if (!delayed_work_pending(&pTAS2770->irq_work))
329 schedule_delayed_work(&pTAS2770->irq_work, msecs_to_jiffies(20));
330 }
332 return HRTIMER_NORESTART;
333 }
335 static irqreturn_t tas2770_irq_handler(int irq, void *dev_id)
336 {
337 struct tas2770_priv *pTAS2770 = (struct tas2770_priv *)dev_id;
339 tas2770_enableIRQ(pTAS2770, false);
341 /* get IRQ status after 100 ms */
342 if (!delayed_work_pending(&pTAS2770->irq_work))
343 schedule_delayed_work(&pTAS2770->irq_work, msecs_to_jiffies(100));
345 return IRQ_HANDLED;
346 }
348 static int tas2770_runtime_suspend(struct tas2770_priv *pTAS2770)
349 {
350 dev_dbg(pTAS2770->dev, "%s\n", __func__);
352 pTAS2770->mbRuntimeSuspend = true;
354 if (hrtimer_active(&pTAS2770->mtimer)) {
355 dev_dbg(pTAS2770->dev, "cancel die temp timer\n");
356 hrtimer_cancel(&pTAS2770->mtimer);
357 }
359 if (delayed_work_pending(&pTAS2770->irq_work)) {
360 dev_dbg(pTAS2770->dev, "cancel IRQ work\n");
361 cancel_delayed_work_sync(&pTAS2770->irq_work);
362 }
364 return 0;
365 }
367 static int tas2770_runtime_resume(struct tas2770_priv *pTAS2770)
368 {
369 dev_dbg(pTAS2770->dev, "%s\n", __func__);
371 if (pTAS2770->mbPowerUp) {
372 /* if (!hrtimer_active(&pTAS2770->mtimer)) {
373 dev_dbg(pTAS2770->dev, "%s, start check timer\n", __func__);
374 hrtimer_start(&pTAS2770->mtimer,
375 ns_to_ktime((u64)CHECK_PERIOD * NSEC_PER_MSEC), HRTIMER_MODE_REL);
376 }
377 */
378 }
380 pTAS2770->mbRuntimeSuspend = false;
382 return 0;
383 }
385 int tas2770_parse_dt(struct device *dev, struct tas2770_priv *pTAS2770)
386 {
387 struct device_node *np = dev->of_node;
388 int rc = 0, ret = 0;
390 rc = of_property_read_u32(np, "ti,asi-format", &pTAS2770->mnASIFormat);
391 if (rc) {
392 dev_err(pTAS2770->dev, "Looking up %s property in node %s failed %d\n",
393 "ti,asi-format", np->full_name, rc);
394 } else {
395 dev_dbg(pTAS2770->dev, "ti,asi-format=%d", pTAS2770->mnASIFormat);
396 }
398 pTAS2770->mnResetGPIO = of_get_named_gpio(np, "ti,reset-gpio", 0);
399 if (!gpio_is_valid(pTAS2770->mnResetGPIO)) {
400 dev_err(pTAS2770->dev, "Looking up %s property in node %s failed %d\n",
401 "ti,reset-gpio", np->full_name, pTAS2770->mnResetGPIO);
402 } else {
403 dev_dbg(pTAS2770->dev, "ti,reset-gpio=%d", pTAS2770->mnResetGPIO);
404 }
406 pTAS2770->mnIRQGPIO = of_get_named_gpio(np, "ti,irq-gpio", 0);
407 if (!gpio_is_valid(pTAS2770->mnIRQGPIO)) {
408 dev_err(pTAS2770->dev, "Looking up %s property in node %s failed %d\n",
409 "ti,irq-gpio", np->full_name, pTAS2770->mnIRQGPIO);
410 } else {
411 dev_dbg(pTAS2770->dev, "ti,irq-gpio=%d", pTAS2770->mnIRQGPIO);
412 }
414 return ret;
415 }
417 static int tas2770_i2c_probe(struct i2c_client *client,
418 const struct i2c_device_id *id)
419 {
420 struct tas2770_priv *pTAS2770;
421 int nResult;
423 dev_info(&client->dev, "%s enter\n", __func__);
425 pTAS2770 = devm_kzalloc(&client->dev, sizeof(struct tas2770_priv), GFP_KERNEL);
426 if (pTAS2770 == NULL) {
427 dev_err(&client->dev, "%s, -ENOMEM \n", __func__);
428 nResult = -ENOMEM;
429 goto end;
430 }
432 pTAS2770->dev = &client->dev;
433 i2c_set_clientdata(client, pTAS2770);
434 dev_set_drvdata(&client->dev, pTAS2770);
436 pTAS2770->regmap = devm_regmap_init_i2c(client, &tas2770_i2c_regmap);
437 if (IS_ERR(pTAS2770->regmap)) {
438 nResult = PTR_ERR(pTAS2770->regmap);
439 dev_err(&client->dev, "Failed to allocate register map: %d\n",
440 nResult);
441 goto end;
442 }
444 //TODO
445 if (client->dev.of_node)
446 tas2770_parse_dt(&client->dev, pTAS2770);
448 if (gpio_is_valid(pTAS2770->mnResetGPIO)) {
449 nResult = gpio_request(pTAS2770->mnResetGPIO, "TAS2770_RESET");
450 if (nResult) {
451 dev_err(pTAS2770->dev, "%s: Failed to request gpio %d\n", __func__,
452 pTAS2770->mnResetGPIO);
453 nResult = -EINVAL;
454 goto free_gpio;
455 }
456 }
458 if (gpio_is_valid(pTAS2770->mnIRQGPIO)) {
459 nResult = gpio_request(pTAS2770->mnIRQGPIO, "TAS2770-IRQ");
460 if (nResult < 0) {
461 dev_err(pTAS2770->dev, "%s: GPIO %d request error\n",
462 __func__, pTAS2770->mnIRQGPIO);
463 goto free_gpio;
464 }
465 gpio_direction_input(pTAS2770->mnIRQGPIO);
466 pTAS2770->mnIRQ = gpio_to_irq(pTAS2770->mnIRQGPIO);
467 dev_dbg(pTAS2770->dev, "irq = %d\n", pTAS2770->mnIRQ);
468 nResult = request_threaded_irq(pTAS2770->mnIRQ, tas2770_irq_handler,
469 NULL, IRQF_TRIGGER_HIGH | IRQF_ONESHOT,
470 client->name, pTAS2770);
471 if (nResult < 0) {
472 dev_err(pTAS2770->dev,
473 "request_irq failed, %d\n", nResult);
474 goto free_gpio;
475 }
476 disable_irq_nosync(pTAS2770->mnIRQ);
477 INIT_DELAYED_WORK(&pTAS2770->irq_work, irq_work_routine);
478 }
480 pTAS2770->hw_reset = tas2770_hw_reset;
481 pTAS2770->enableIRQ = tas2770_enableIRQ;
482 pTAS2770->clearIRQ = tas2770_clearIRQ;
483 pTAS2770->runtime_suspend = tas2770_runtime_suspend;
484 pTAS2770->runtime_resume = tas2770_runtime_resume;
485 mutex_init(&pTAS2770->dev_lock);
487 // nResult = tas2770_LoadConfig(pTAS2770, false);
488 if (nResult < 0)
489 goto destroy_mutex;
491 #ifdef CONFIG_TAS2770_CODEC
492 mutex_init(&pTAS2770->codec_lock);
493 tas2770_register_codec(pTAS2770);
494 #endif
496 #ifdef CONFIG_TAS2770_MISC
497 // mutex_init(&pTAS2770->file_lock);
498 // tas2770_register_misc(pTAS2770);
499 #endif
501 hrtimer_init(&pTAS2770->mtimer, CLOCK_MONOTONIC, HRTIMER_MODE_REL);
502 pTAS2770->mtimer.function = timer_func;
504 destroy_mutex:
505 if (nResult < 0)
506 mutex_destroy(&pTAS2770->dev_lock);
508 free_gpio:
509 if (nResult < 0) {
510 if (gpio_is_valid(pTAS2770->mnResetGPIO))
511 gpio_free(pTAS2770->mnResetGPIO);
512 if (gpio_is_valid(pTAS2770->mnIRQGPIO))
513 gpio_free(pTAS2770->mnIRQGPIO);
514 }
516 end:
517 return nResult;
518 }
520 static int tas2770_i2c_remove(struct i2c_client *client)
521 {
522 struct tas2770_priv *pTAS2770 = i2c_get_clientdata(client);
524 dev_info(pTAS2770->dev, "%s\n", __func__);
526 #ifdef CONFIG_TAS2770_CODEC
527 tas2770_deregister_codec(pTAS2770);
528 mutex_destroy(&pTAS2770->codec_lock);
529 #endif
531 #ifdef CONFIG_TAS2770_MISC
532 // tas2770_deregister_misc(pTAS2770);
533 mutex_destroy(&pTAS2770->file_lock);
534 #endif
536 if (gpio_is_valid(pTAS2770->mnResetGPIO))
537 gpio_free(pTAS2770->mnResetGPIO);
538 if (gpio_is_valid(pTAS2770->mnIRQGPIO))
539 gpio_free(pTAS2770->mnIRQGPIO);
541 return 0;
542 }
545 static const struct i2c_device_id tas2770_i2c_id[] = {
546 { "tas2770", 0},
547 { }
548 };
549 MODULE_DEVICE_TABLE(i2c, tas2770_i2c_id);
551 #if defined(CONFIG_OF)
552 static const struct of_device_id tas2770_of_match[] = {
553 { .compatible = "ti,tas2770" },
554 {},
555 };
556 MODULE_DEVICE_TABLE(of, tas2770_of_match);
557 #endif
560 static struct i2c_driver tas2770_i2c_driver = {
561 .driver = {
562 .name = "tas2770",
563 .owner = THIS_MODULE,
564 #if defined(CONFIG_OF)
565 .of_match_table = of_match_ptr(tas2770_of_match),
566 #endif
567 },
568 .probe = tas2770_i2c_probe,
569 .remove = tas2770_i2c_remove,
570 .id_table = tas2770_i2c_id,
571 };
573 module_i2c_driver(tas2770_i2c_driver);
575 MODULE_AUTHOR("Texas Instruments Inc.");
576 MODULE_DESCRIPTION("TAS2770 I2C Smart Amplifier driver");
577 MODULE_LICENSE("GPL v2");
578 #endif