aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--sound/soc/codecs/ak4535.c110
-rw-r--r--sound/soc/codecs/ak4535.h1
2 files changed, 54 insertions, 57 deletions
diff --git a/sound/soc/codecs/ak4535.c b/sound/soc/codecs/ak4535.c
index 7da9f467b7b8..e512cd79d767 100644
--- a/sound/soc/codecs/ak4535.c
+++ b/sound/soc/codecs/ak4535.c
@@ -535,87 +535,85 @@ static struct snd_soc_device *ak4535_socdev;
535 535
536#if defined(CONFIG_I2C) || defined(CONFIG_I2C_MODULE) 536#if defined(CONFIG_I2C) || defined(CONFIG_I2C_MODULE)
537 537
538#define I2C_DRIVERID_AK4535 0xfefe /* liam - need a proper id */ 538static int ak4535_i2c_probe(struct i2c_client *i2c,
539 539 const struct i2c_device_id *id)
540static unsigned short normal_i2c[] = { 0, I2C_CLIENT_END };
541
542/* Magic definition of all other variables and things */
543I2C_CLIENT_INSMOD;
544
545static struct i2c_driver ak4535_i2c_driver;
546static struct i2c_client client_template;
547
548/* If the i2c layer weren't so broken, we could pass this kind of data
549 around */
550static int ak4535_codec_probe(struct i2c_adapter *adap, int addr, int kind)
551{ 540{
552 struct snd_soc_device *socdev = ak4535_socdev; 541 struct snd_soc_device *socdev = ak4535_socdev;
553 struct ak4535_setup_data *setup = socdev->codec_data;
554 struct snd_soc_codec *codec = socdev->codec; 542 struct snd_soc_codec *codec = socdev->codec;
555 struct i2c_client *i2c;
556 int ret; 543 int ret;
557 544
558 if (addr != setup->i2c_address)
559 return -ENODEV;
560
561 client_template.adapter = adap;
562 client_template.addr = addr;
563
564 i2c = kmemdup(&client_template, sizeof(client_template), GFP_KERNEL);
565 if (i2c == NULL)
566 return -ENOMEM;
567
568 i2c_set_clientdata(i2c, codec); 545 i2c_set_clientdata(i2c, codec);
569 codec->control_data = i2c; 546 codec->control_data = i2c;
570 547
571 ret = i2c_attach_client(i2c);
572 if (ret < 0) {
573 printk(KERN_ERR "failed to attach codec at addr %x\n", addr);
574 goto err;
575 }
576
577 ret = ak4535_init(socdev); 548 ret = ak4535_init(socdev);
578 if (ret < 0) { 549 if (ret < 0)
579 printk(KERN_ERR "failed to initialise AK4535\n"); 550 printk(KERN_ERR "failed to initialise AK4535\n");
580 goto err;
581 }
582 return ret;
583 551
584err:
585 kfree(i2c);
586 return ret; 552 return ret;
587} 553}
588 554
589static int ak4535_i2c_detach(struct i2c_client *client) 555static int ak4535_i2c_remove(struct i2c_client *client)
590{ 556{
591 struct snd_soc_codec *codec = i2c_get_clientdata(client); 557 struct snd_soc_codec *codec = i2c_get_clientdata(client);
592 i2c_detach_client(client);
593 kfree(codec->reg_cache); 558 kfree(codec->reg_cache);
594 kfree(client);
595 return 0; 559 return 0;
596} 560}
597 561
598static int ak4535_i2c_attach(struct i2c_adapter *adap) 562static const struct i2c_device_id ak4535_i2c_id[] = {
599{ 563 { "ak4535", 0 },
600 return i2c_probe(adap, &addr_data, ak4535_codec_probe); 564 { }
601} 565};
566MODULE_DEVICE_TABLE(i2c, ak4535_i2c_id);
602 567
603/* corgi i2c codec control layer */
604static struct i2c_driver ak4535_i2c_driver = { 568static struct i2c_driver ak4535_i2c_driver = {
605 .driver = { 569 .driver = {
606 .name = "AK4535 I2C Codec", 570 .name = "AK4535 I2C Codec",
607 .owner = THIS_MODULE, 571 .owner = THIS_MODULE,
608 }, 572 },
609 .id = I2C_DRIVERID_AK4535, 573 .probe = ak4535_i2c_probe,
610 .attach_adapter = ak4535_i2c_attach, 574 .remove = ak4535_i2c_remove,
611 .detach_client = ak4535_i2c_detach, 575 .id_table = ak4535_i2c_id,
612 .command = NULL,
613}; 576};
614 577
615static struct i2c_client client_template = { 578static int ak4535_add_i2c_device(struct platform_device *pdev,
616 .name = "AK4535", 579 const struct ak4535_setup_data *setup)
617 .driver = &ak4535_i2c_driver, 580{
618}; 581 struct i2c_board_info info;
582 struct i2c_adapter *adapter;
583 struct i2c_client *client;
584 int ret;
585
586 ret = i2c_add_driver(&ak4535_i2c_driver);
587 if (ret != 0) {
588 dev_err(&pdev->dev, "can't add i2c driver\n");
589 return ret;
590 }
591
592 memset(&info, 0, sizeof(struct i2c_board_info));
593 info.addr = setup->i2c_address;
594 strlcpy(info.type, "ak4535", I2C_NAME_SIZE);
595
596 adapter = i2c_get_adapter(setup->i2c_bus);
597 if (!adapter) {
598 dev_err(&pdev->dev, "can't get i2c adapter %d\n",
599 setup->i2c_bus);
600 goto err_driver;
601 }
602
603 client = i2c_new_device(adapter, &info);
604 i2c_put_adapter(adapter);
605 if (!client) {
606 dev_err(&pdev->dev, "can't add i2c device at 0x%x\n",
607 (unsigned int)info.addr);
608 goto err_driver;
609 }
610
611 return 0;
612
613err_driver:
614 i2c_del_driver(&ak4535_i2c_driver);
615 return -ENODEV;
616}
619#endif 617#endif
620 618
621static int ak4535_probe(struct platform_device *pdev) 619static int ak4535_probe(struct platform_device *pdev)
@@ -648,12 +646,9 @@ static int ak4535_probe(struct platform_device *pdev)
648 ak4535_socdev = socdev; 646 ak4535_socdev = socdev;
649#if defined(CONFIG_I2C) || defined(CONFIG_I2C_MODULE) 647#if defined(CONFIG_I2C) || defined(CONFIG_I2C_MODULE)
650 if (setup->i2c_address) { 648 if (setup->i2c_address) {
651 normal_i2c[0] = setup->i2c_address;
652 codec->hw_write = (hw_write_t)i2c_master_send; 649 codec->hw_write = (hw_write_t)i2c_master_send;
653 codec->hw_read = (hw_read_t)i2c_master_recv; 650 codec->hw_read = (hw_read_t)i2c_master_recv;
654 ret = i2c_add_driver(&ak4535_i2c_driver); 651 ret = ak4535_add_i2c_device(pdev, setup);
655 if (ret != 0)
656 printk(KERN_ERR "can't add i2c driver");
657 } 652 }
658#else 653#else
659 /* Add other interfaces here */ 654 /* Add other interfaces here */
@@ -678,6 +673,7 @@ static int ak4535_remove(struct platform_device *pdev)
678 snd_soc_free_pcms(socdev); 673 snd_soc_free_pcms(socdev);
679 snd_soc_dapm_free(socdev); 674 snd_soc_dapm_free(socdev);
680#if defined(CONFIG_I2C) || defined(CONFIG_I2C_MODULE) 675#if defined(CONFIG_I2C) || defined(CONFIG_I2C_MODULE)
676 i2c_unregister_device(codec->control_data);
681 i2c_del_driver(&ak4535_i2c_driver); 677 i2c_del_driver(&ak4535_i2c_driver);
682#endif 678#endif
683 kfree(codec->private_data); 679 kfree(codec->private_data);
diff --git a/sound/soc/codecs/ak4535.h b/sound/soc/codecs/ak4535.h
index e9fe30e2c056..c7a58703ea39 100644
--- a/sound/soc/codecs/ak4535.h
+++ b/sound/soc/codecs/ak4535.h
@@ -37,6 +37,7 @@
37#define AK4535_CACHEREGNUM 0x10 37#define AK4535_CACHEREGNUM 0x10
38 38
39struct ak4535_setup_data { 39struct ak4535_setup_data {
40 int i2c_bus;
40 unsigned short i2c_address; 41 unsigned short i2c_address;
41}; 42};
42 43