aboutsummaryrefslogtreecommitdiffstats
path: root/sound/soc/codecs/wm8731.c
diff options
context:
space:
mode:
Diffstat (limited to 'sound/soc/codecs/wm8731.c')
-rw-r--r--sound/soc/codecs/wm8731.c179
1 files changed, 122 insertions, 57 deletions
diff --git a/sound/soc/codecs/wm8731.c b/sound/soc/codecs/wm8731.c
index 9402fcaf04fa..7f8a7e36b33e 100644
--- a/sound/soc/codecs/wm8731.c
+++ b/sound/soc/codecs/wm8731.c
@@ -19,6 +19,7 @@
19#include <linux/pm.h> 19#include <linux/pm.h>
20#include <linux/i2c.h> 20#include <linux/i2c.h>
21#include <linux/platform_device.h> 21#include <linux/platform_device.h>
22#include <linux/spi/spi.h>
22#include <sound/core.h> 23#include <sound/core.h>
23#include <sound/pcm.h> 24#include <sound/pcm.h>
24#include <sound/pcm_params.h> 25#include <sound/pcm_params.h>
@@ -28,7 +29,6 @@
28 29
29#include "wm8731.h" 30#include "wm8731.h"
30 31
31#define AUDIO_NAME "wm8731"
32#define WM8731_VERSION "0.13" 32#define WM8731_VERSION "0.13"
33 33
34struct snd_soc_codec_device soc_codec_dev_wm8731; 34struct snd_soc_codec_device soc_codec_dev_wm8731;
@@ -570,88 +570,144 @@ static struct snd_soc_device *wm8731_socdev;
570 * low = 0x1a 570 * low = 0x1a
571 * high = 0x1b 571 * high = 0x1b
572 */ 572 */
573static unsigned short normal_i2c[] = { 0, I2C_CLIENT_END };
574 573
575/* Magic definition of all other variables and things */ 574static int wm8731_i2c_probe(struct i2c_client *i2c,
576I2C_CLIENT_INSMOD; 575 const struct i2c_device_id *id)
577
578static struct i2c_driver wm8731_i2c_driver;
579static struct i2c_client client_template;
580
581/* If the i2c layer weren't so broken, we could pass this kind of data
582 around */
583
584static int wm8731_codec_probe(struct i2c_adapter *adap, int addr, int kind)
585{ 576{
586 struct snd_soc_device *socdev = wm8731_socdev; 577 struct snd_soc_device *socdev = wm8731_socdev;
587 struct wm8731_setup_data *setup = socdev->codec_data;
588 struct snd_soc_codec *codec = socdev->codec; 578 struct snd_soc_codec *codec = socdev->codec;
589 struct i2c_client *i2c;
590 int ret; 579 int ret;
591 580
592 if (addr != setup->i2c_address)
593 return -ENODEV;
594
595 client_template.adapter = adap;
596 client_template.addr = addr;
597
598 i2c = kmemdup(&client_template, sizeof(client_template), GFP_KERNEL);
599 if (i2c == NULL)
600 return -ENOMEM;
601
602 i2c_set_clientdata(i2c, codec); 581 i2c_set_clientdata(i2c, codec);
603 codec->control_data = i2c; 582 codec->control_data = i2c;
604 583
605 ret = i2c_attach_client(i2c);
606 if (ret < 0) {
607 pr_err("failed to attach codec at addr %x\n", addr);
608 goto err;
609 }
610
611 ret = wm8731_init(socdev); 584 ret = wm8731_init(socdev);
612 if (ret < 0) { 585 if (ret < 0)
613 pr_err("failed to initialise WM8731\n"); 586 pr_err("failed to initialise WM8731\n");
614 goto err;
615 }
616 return ret;
617 587
618err:
619 kfree(i2c);
620 return ret; 588 return ret;
621} 589}
622 590
623static int wm8731_i2c_detach(struct i2c_client *client) 591static int wm8731_i2c_remove(struct i2c_client *client)
624{ 592{
625 struct snd_soc_codec *codec = i2c_get_clientdata(client); 593 struct snd_soc_codec *codec = i2c_get_clientdata(client);
626 i2c_detach_client(client);
627 kfree(codec->reg_cache); 594 kfree(codec->reg_cache);
628 kfree(client);
629 return 0; 595 return 0;
630} 596}
631 597
632static int wm8731_i2c_attach(struct i2c_adapter *adap) 598static const struct i2c_device_id wm8731_i2c_id[] = {
633{ 599 { "wm8731", 0 },
634 return i2c_probe(adap, &addr_data, wm8731_codec_probe); 600 { }
635} 601};
602MODULE_DEVICE_TABLE(i2c, wm8731_i2c_id);
636 603
637/* corgi i2c codec control layer */
638static struct i2c_driver wm8731_i2c_driver = { 604static struct i2c_driver wm8731_i2c_driver = {
639 .driver = { 605 .driver = {
640 .name = "WM8731 I2C Codec", 606 .name = "WM8731 I2C Codec",
641 .owner = THIS_MODULE, 607 .owner = THIS_MODULE,
642 }, 608 },
643 .id = I2C_DRIVERID_WM8731, 609 .probe = wm8731_i2c_probe,
644 .attach_adapter = wm8731_i2c_attach, 610 .remove = wm8731_i2c_remove,
645 .detach_client = wm8731_i2c_detach, 611 .id_table = wm8731_i2c_id,
646 .command = NULL,
647}; 612};
648 613
649static struct i2c_client client_template = { 614static int wm8731_add_i2c_device(struct platform_device *pdev,
650 .name = "WM8731", 615 const struct wm8731_setup_data *setup)
651 .driver = &wm8731_i2c_driver, 616{
652}; 617 struct i2c_board_info info;
618 struct i2c_adapter *adapter;
619 struct i2c_client *client;
620 int ret;
621
622 ret = i2c_add_driver(&wm8731_i2c_driver);
623 if (ret != 0) {
624 dev_err(&pdev->dev, "can't add i2c driver\n");
625 return ret;
626 }
627
628 memset(&info, 0, sizeof(struct i2c_board_info));
629 info.addr = setup->i2c_address;
630 strlcpy(info.type, "wm8731", I2C_NAME_SIZE);
631
632 adapter = i2c_get_adapter(setup->i2c_bus);
633 if (!adapter) {
634 dev_err(&pdev->dev, "can't get i2c adapter %d\n",
635 setup->i2c_bus);
636 goto err_driver;
637 }
638
639 client = i2c_new_device(adapter, &info);
640 i2c_put_adapter(adapter);
641 if (!client) {
642 dev_err(&pdev->dev, "can't add i2c device at 0x%x\n",
643 (unsigned int)info.addr);
644 goto err_driver;
645 }
646
647 return 0;
648
649err_driver:
650 i2c_del_driver(&wm8731_i2c_driver);
651 return -ENODEV;
652}
653#endif 653#endif
654 654
655#if defined(CONFIG_SPI_MASTER)
656static int __devinit wm8731_spi_probe(struct spi_device *spi)
657{
658 struct snd_soc_device *socdev = wm8731_socdev;
659 struct snd_soc_codec *codec = socdev->codec;
660 int ret;
661
662 codec->control_data = spi;
663
664 ret = wm8731_init(socdev);
665 if (ret < 0)
666 dev_err(&spi->dev, "failed to initialise WM8731\n");
667
668 return ret;
669}
670
671static int __devexit wm8731_spi_remove(struct spi_device *spi)
672{
673 return 0;
674}
675
676static struct spi_driver wm8731_spi_driver = {
677 .driver = {
678 .name = "wm8731",
679 .bus = &spi_bus_type,
680 .owner = THIS_MODULE,
681 },
682 .probe = wm8731_spi_probe,
683 .remove = __devexit_p(wm8731_spi_remove),
684};
685
686static int wm8731_spi_write(struct spi_device *spi, const char *data, int len)
687{
688 struct spi_transfer t;
689 struct spi_message m;
690 u8 msg[2];
691
692 if (len <= 0)
693 return 0;
694
695 msg[0] = data[0];
696 msg[1] = data[1];
697
698 spi_message_init(&m);
699 memset(&t, 0, (sizeof t));
700
701 t.tx_buf = &msg[0];
702 t.len = len;
703
704 spi_message_add_tail(&t, &m);
705 spi_sync(spi, &m);
706
707 return len;
708}
709#endif /* CONFIG_SPI_MASTER */
710
655static int wm8731_probe(struct platform_device *pdev) 711static int wm8731_probe(struct platform_device *pdev)
656{ 712{
657 struct snd_soc_device *socdev = platform_get_drvdata(pdev); 713 struct snd_soc_device *socdev = platform_get_drvdata(pdev);
@@ -680,16 +736,21 @@ static int wm8731_probe(struct platform_device *pdev)
680 INIT_LIST_HEAD(&codec->dapm_paths); 736 INIT_LIST_HEAD(&codec->dapm_paths);
681 737
682 wm8731_socdev = socdev; 738 wm8731_socdev = socdev;
739 ret = -ENODEV;
740
683#if defined(CONFIG_I2C) || defined(CONFIG_I2C_MODULE) 741#if defined(CONFIG_I2C) || defined(CONFIG_I2C_MODULE)
684 if (setup->i2c_address) { 742 if (setup->i2c_address) {
685 normal_i2c[0] = setup->i2c_address;
686 codec->hw_write = (hw_write_t)i2c_master_send; 743 codec->hw_write = (hw_write_t)i2c_master_send;
687 ret = i2c_add_driver(&wm8731_i2c_driver); 744 ret = wm8731_add_i2c_device(pdev, setup);
745 }
746#endif
747#if defined(CONFIG_SPI_MASTER)
748 if (setup->spi) {
749 codec->hw_write = (hw_write_t)wm8731_spi_write;
750 ret = spi_register_driver(&wm8731_spi_driver);
688 if (ret != 0) 751 if (ret != 0)
689 printk(KERN_ERR "can't add i2c driver"); 752 printk(KERN_ERR "can't add spi driver");
690 } 753 }
691#else
692 /* Add other interfaces here */
693#endif 754#endif
694 755
695 if (ret != 0) { 756 if (ret != 0) {
@@ -711,8 +772,12 @@ static int wm8731_remove(struct platform_device *pdev)
711 snd_soc_free_pcms(socdev); 772 snd_soc_free_pcms(socdev);
712 snd_soc_dapm_free(socdev); 773 snd_soc_dapm_free(socdev);
713#if defined(CONFIG_I2C) || defined(CONFIG_I2C_MODULE) 774#if defined(CONFIG_I2C) || defined(CONFIG_I2C_MODULE)
775 i2c_unregister_device(codec->control_data);
714 i2c_del_driver(&wm8731_i2c_driver); 776 i2c_del_driver(&wm8731_i2c_driver);
715#endif 777#endif
778#if defined(CONFIG_SPI_MASTER)
779 spi_unregister_driver(&wm8731_spi_driver);
780#endif
716 kfree(codec->private_data); 781 kfree(codec->private_data);
717 kfree(codec); 782 kfree(codec);
718 783