aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorTakashi Iwai <tiwai@suse.de>2013-11-27 06:17:11 -0500
committerTakashi Iwai <tiwai@suse.de>2013-11-27 06:17:11 -0500
commit351892a8278b50f723974ad42ce591aae57b41e7 (patch)
tree63fafb11e0ae7921b9c882c18431ab85c493daad
parentd2208ca0562b40f02d507cd5845174dbe9dc8d6c (diff)
parent0e24dbb7f44877a3565ee461d2209b0942b1a753 (diff)
Merge branch 'topic/hda' into for-next
-rw-r--r--sound/pci/hda/Makefile5
-rw-r--r--sound/pci/hda/hda_codec.c185
-rw-r--r--sound/pci/hda/hda_codec.h8
-rw-r--r--sound/pci/hda/hda_generic.c4
-rw-r--r--sound/pci/hda/hda_intel.c2
-rw-r--r--sound/pci/hda/hda_local.h8
-rw-r--r--sound/pci/hda/patch_hdmi.c24
7 files changed, 166 insertions, 70 deletions
diff --git a/sound/pci/hda/Makefile b/sound/pci/hda/Makefile
index c091438286a3..5a40c652df41 100644
--- a/sound/pci/hda/Makefile
+++ b/sound/pci/hda/Makefile
@@ -3,7 +3,6 @@ snd-hda-intel-objs := hda_intel.o
3snd-hda-intel-$(CONFIG_SND_HDA_I915) += hda_i915.o 3snd-hda-intel-$(CONFIG_SND_HDA_I915) += hda_i915.o
4 4
5snd-hda-codec-y := hda_codec.o hda_jack.o hda_auto_parser.o 5snd-hda-codec-y := hda_codec.o hda_jack.o hda_auto_parser.o
6snd-hda-codec-$(CONFIG_SND_HDA_GENERIC) += hda_generic.o
7snd-hda-codec-$(CONFIG_PROC_FS) += hda_proc.o 6snd-hda-codec-$(CONFIG_PROC_FS) += hda_proc.o
8snd-hda-codec-$(CONFIG_SND_HDA_HWDEP) += hda_hwdep.o 7snd-hda-codec-$(CONFIG_SND_HDA_HWDEP) += hda_hwdep.o
9snd-hda-codec-$(CONFIG_SND_HDA_INPUT_BEEP) += hda_beep.o 8snd-hda-codec-$(CONFIG_SND_HDA_INPUT_BEEP) += hda_beep.o
@@ -12,6 +11,7 @@ snd-hda-codec-$(CONFIG_SND_HDA_INPUT_BEEP) += hda_beep.o
12CFLAGS_hda_codec.o := -I$(src) 11CFLAGS_hda_codec.o := -I$(src)
13CFLAGS_hda_intel.o := -I$(src) 12CFLAGS_hda_intel.o := -I$(src)
14 13
14snd-hda-codec-generic-objs := hda_generic.o
15snd-hda-codec-realtek-objs := patch_realtek.o 15snd-hda-codec-realtek-objs := patch_realtek.o
16snd-hda-codec-cmedia-objs := patch_cmedia.o 16snd-hda-codec-cmedia-objs := patch_cmedia.o
17snd-hda-codec-analog-objs := patch_analog.o 17snd-hda-codec-analog-objs := patch_analog.o
@@ -28,6 +28,9 @@ snd-hda-codec-hdmi-objs := patch_hdmi.o hda_eld.o
28obj-$(CONFIG_SND_HDA_INTEL) := snd-hda-codec.o 28obj-$(CONFIG_SND_HDA_INTEL) := snd-hda-codec.o
29 29
30# codec drivers (note: CONFIG_SND_HDA_CODEC_XXX are booleans) 30# codec drivers (note: CONFIG_SND_HDA_CODEC_XXX are booleans)
31ifdef CONFIG_SND_HDA_GENERIC
32obj-$(CONFIG_SND_HDA_INTEL) += snd-hda-codec-generic.o
33endif
31ifdef CONFIG_SND_HDA_CODEC_REALTEK 34ifdef CONFIG_SND_HDA_CODEC_REALTEK
32obj-$(CONFIG_SND_HDA_INTEL) += snd-hda-codec-realtek.o 35obj-$(CONFIG_SND_HDA_INTEL) += snd-hda-codec-realtek.o
33endif 36endif
diff --git a/sound/pci/hda/hda_codec.c b/sound/pci/hda/hda_codec.c
index 69178c4f4113..85886220ee74 100644
--- a/sound/pci/hda/hda_codec.c
+++ b/sound/pci/hda/hda_codec.c
@@ -96,19 +96,28 @@ EXPORT_SYMBOL_HDA(snd_hda_delete_codec_preset);
96 96
97#ifdef CONFIG_PM 97#ifdef CONFIG_PM
98#define codec_in_pm(codec) ((codec)->in_pm) 98#define codec_in_pm(codec) ((codec)->in_pm)
99static void hda_pm_work(struct work_struct *work);
99static void hda_power_work(struct work_struct *work); 100static void hda_power_work(struct work_struct *work);
100static void hda_keep_power_on(struct hda_codec *codec); 101static void hda_keep_power_on(struct hda_codec *codec);
101#define hda_codec_is_power_on(codec) ((codec)->power_on) 102#define hda_codec_is_power_on(codec) ((codec)->power_on)
102static inline void hda_call_pm_notify(struct hda_bus *bus, bool power_up) 103
104static void hda_call_pm_notify(struct hda_codec *codec, bool power_up)
103{ 105{
106 struct hda_bus *bus = codec->bus;
107
108 if ((power_up && codec->pm_up_notified) ||
109 (!power_up && !codec->pm_up_notified))
110 return;
104 if (bus->ops.pm_notify) 111 if (bus->ops.pm_notify)
105 bus->ops.pm_notify(bus, power_up); 112 bus->ops.pm_notify(bus, power_up);
113 codec->pm_up_notified = power_up;
106} 114}
115
107#else 116#else
108#define codec_in_pm(codec) 0 117#define codec_in_pm(codec) 0
109static inline void hda_keep_power_on(struct hda_codec *codec) {} 118static inline void hda_keep_power_on(struct hda_codec *codec) {}
110#define hda_codec_is_power_on(codec) 1 119#define hda_codec_is_power_on(codec) 1
111#define hda_call_pm_notify(bus, state) {} 120#define hda_call_pm_notify(codec, state) {}
112#endif 121#endif
113 122
114/** 123/**
@@ -831,6 +840,12 @@ static int snd_hda_bus_free(struct hda_bus *bus)
831 bus->ops.private_free(bus); 840 bus->ops.private_free(bus);
832 if (bus->workq) 841 if (bus->workq)
833 destroy_workqueue(bus->workq); 842 destroy_workqueue(bus->workq);
843
844#ifdef CONFIG_PM
845 if (bus->pm_wq)
846 destroy_workqueue(bus->pm_wq);
847#endif
848
834 kfree(bus); 849 kfree(bus);
835 return 0; 850 return 0;
836} 851}
@@ -875,6 +890,9 @@ int snd_hda_bus_new(struct snd_card *card,
875 .dev_register = snd_hda_bus_dev_register, 890 .dev_register = snd_hda_bus_dev_register,
876 .dev_free = snd_hda_bus_dev_free, 891 .dev_free = snd_hda_bus_dev_free,
877 }; 892 };
893#ifdef CONFIG_PM
894 char wqname[16];
895#endif
878 896
879 if (snd_BUG_ON(!temp)) 897 if (snd_BUG_ON(!temp))
880 return -EINVAL; 898 return -EINVAL;
@@ -911,6 +929,16 @@ int snd_hda_bus_new(struct snd_card *card,
911 return -ENOMEM; 929 return -ENOMEM;
912 } 930 }
913 931
932#ifdef CONFIG_PM
933 sprintf(wqname, "hda-pm-wq-%d", card->number);
934 bus->pm_wq = create_workqueue(wqname);
935 if (!bus->pm_wq) {
936 snd_printk(KERN_ERR "cannot create PM workqueue\n");
937 snd_hda_bus_free(bus);
938 return -ENOMEM;
939 }
940#endif
941
914 err = snd_device_new(card, SNDRV_DEV_BUS, bus, &dev_ops); 942 err = snd_device_new(card, SNDRV_DEV_BUS, bus, &dev_ops);
915 if (err < 0) { 943 if (err < 0) {
916 snd_hda_bus_free(bus); 944 snd_hda_bus_free(bus);
@@ -945,9 +973,6 @@ find_codec_preset(struct hda_codec *codec)
945 const struct hda_codec_preset *preset; 973 const struct hda_codec_preset *preset;
946 unsigned int mod_requested = 0; 974 unsigned int mod_requested = 0;
947 975
948 if (is_generic_config(codec))
949 return NULL; /* use the generic parser */
950
951 again: 976 again:
952 mutex_lock(&preset_mutex); 977 mutex_lock(&preset_mutex);
953 list_for_each_entry(tbl, &hda_preset_tables, list) { 978 list_for_each_entry(tbl, &hda_preset_tables, list) {
@@ -1330,6 +1355,28 @@ get_hda_cvt_setup(struct hda_codec *codec, hda_nid_t nid)
1330} 1355}
1331 1356
1332/* 1357/*
1358 * Dynamic symbol binding for the codec parsers
1359 */
1360#ifdef MODULE
1361#define load_parser_sym(sym) ((int (*)(struct hda_codec *))symbol_request(sym))
1362#define unload_parser_addr(addr) symbol_put_addr(addr)
1363#else
1364#define load_parser_sym(sym) (sym)
1365#define unload_parser_addr(addr) do {} while (0)
1366#endif
1367
1368#define load_parser(codec, sym) \
1369 ((codec)->parser = load_parser_sym(sym))
1370
1371static void unload_parser(struct hda_codec *codec)
1372{
1373 if (codec->parser) {
1374 unload_parser_addr(codec->parser);
1375 codec->parser = NULL;
1376 }
1377}
1378
1379/*
1333 * codec destructor 1380 * codec destructor
1334 */ 1381 */
1335static void snd_hda_codec_free(struct hda_codec *codec) 1382static void snd_hda_codec_free(struct hda_codec *codec)
@@ -1352,10 +1399,8 @@ static void snd_hda_codec_free(struct hda_codec *codec)
1352 codec->bus->caddr_tbl[codec->addr] = NULL; 1399 codec->bus->caddr_tbl[codec->addr] = NULL;
1353 if (codec->patch_ops.free) 1400 if (codec->patch_ops.free)
1354 codec->patch_ops.free(codec); 1401 codec->patch_ops.free(codec);
1355#ifdef CONFIG_PM 1402 hda_call_pm_notify(codec, false); /* cancel leftover refcounts */
1356 if (!codec->pm_down_notified) /* cancel leftover refcounts */ 1403 unload_parser(codec);
1357 hda_call_pm_notify(codec->bus, false);
1358#endif
1359 module_put(codec->owner); 1404 module_put(codec->owner);
1360 free_hda_cache(&codec->amp_cache); 1405 free_hda_cache(&codec->amp_cache);
1361 free_hda_cache(&codec->cmd_cache); 1406 free_hda_cache(&codec->cmd_cache);
@@ -1363,6 +1408,7 @@ static void snd_hda_codec_free(struct hda_codec *codec)
1363 kfree(codec->chip_name); 1408 kfree(codec->chip_name);
1364 kfree(codec->modelname); 1409 kfree(codec->modelname);
1365 kfree(codec->wcaps); 1410 kfree(codec->wcaps);
1411 codec->bus->num_codecs--;
1366 kfree(codec); 1412 kfree(codec);
1367} 1413}
1368 1414
@@ -1428,12 +1474,12 @@ int snd_hda_codec_new(struct hda_bus *bus,
1428#ifdef CONFIG_PM 1474#ifdef CONFIG_PM
1429 spin_lock_init(&codec->power_lock); 1475 spin_lock_init(&codec->power_lock);
1430 INIT_DELAYED_WORK(&codec->power_work, hda_power_work); 1476 INIT_DELAYED_WORK(&codec->power_work, hda_power_work);
1477 INIT_WORK(&codec->pm_work, hda_pm_work);
1431 /* snd_hda_codec_new() marks the codec as power-up, and leave it as is. 1478 /* snd_hda_codec_new() marks the codec as power-up, and leave it as is.
1432 * the caller has to power down appropriatley after initialization 1479 * the caller has to power down appropriatley after initialization
1433 * phase. 1480 * phase.
1434 */ 1481 */
1435 hda_keep_power_on(codec); 1482 hda_keep_power_on(codec);
1436 hda_call_pm_notify(bus, true);
1437#endif 1483#endif
1438 1484
1439 if (codec->bus->modelname) { 1485 if (codec->bus->modelname) {
@@ -1445,6 +1491,11 @@ int snd_hda_codec_new(struct hda_bus *bus,
1445 } 1491 }
1446 1492
1447 list_add_tail(&codec->list, &bus->codec_list); 1493 list_add_tail(&codec->list, &bus->codec_list);
1494 bus->num_codecs++;
1495#ifdef CONFIG_PM
1496 workqueue_set_max_active(bus->pm_wq, bus->num_codecs);
1497#endif
1498
1448 bus->caddr_tbl[codec_addr] = codec; 1499 bus->caddr_tbl[codec_addr] = codec;
1449 1500
1450 codec->vendor_id = snd_hda_param_read(codec, AC_NODE_ROOT, 1501 codec->vendor_id = snd_hda_param_read(codec, AC_NODE_ROOT,
@@ -1486,11 +1537,14 @@ int snd_hda_codec_new(struct hda_bus *bus,
1486#ifdef CONFIG_PM 1537#ifdef CONFIG_PM
1487 codec->d3_stop_clk = snd_hda_codec_get_supported_ps(codec, fg, 1538 codec->d3_stop_clk = snd_hda_codec_get_supported_ps(codec, fg,
1488 AC_PWRST_CLKSTOP); 1539 AC_PWRST_CLKSTOP);
1489 if (!codec->d3_stop_clk)
1490 bus->power_keep_link_on = 1;
1491#endif 1540#endif
1492 codec->epss = snd_hda_codec_get_supported_ps(codec, fg, 1541 codec->epss = snd_hda_codec_get_supported_ps(codec, fg,
1493 AC_PWRST_EPSS); 1542 AC_PWRST_EPSS);
1543#ifdef CONFIG_PM
1544 if (!codec->d3_stop_clk || !codec->epss)
1545 bus->power_keep_link_on = 1;
1546#endif
1547
1494 1548
1495 /* power-up all before initialization */ 1549 /* power-up all before initialization */
1496 hda_set_power_state(codec, AC_PWRST_D0); 1550 hda_set_power_state(codec, AC_PWRST_D0);
@@ -1537,6 +1591,31 @@ int snd_hda_codec_update_widgets(struct hda_codec *codec)
1537EXPORT_SYMBOL_HDA(snd_hda_codec_update_widgets); 1591EXPORT_SYMBOL_HDA(snd_hda_codec_update_widgets);
1538 1592
1539 1593
1594#ifdef CONFIG_SND_HDA_CODEC_HDMI
1595/* if all audio out widgets are digital, let's assume the codec as a HDMI/DP */
1596static bool is_likely_hdmi_codec(struct hda_codec *codec)
1597{
1598 hda_nid_t nid = codec->start_nid;
1599 int i;
1600
1601 for (i = 0; i < codec->num_nodes; i++, nid++) {
1602 unsigned int wcaps = get_wcaps(codec, nid);
1603 switch (get_wcaps_type(wcaps)) {
1604 case AC_WID_AUD_IN:
1605 return false; /* HDMI parser supports only HDMI out */
1606 case AC_WID_AUD_OUT:
1607 if (!(wcaps & AC_WCAP_DIGITAL))
1608 return false;
1609 break;
1610 }
1611 }
1612 return true;
1613}
1614#else
1615/* no HDMI codec parser support */
1616#define is_likely_hdmi_codec(codec) false
1617#endif /* CONFIG_SND_HDA_CODEC_HDMI */
1618
1540/** 1619/**
1541 * snd_hda_codec_configure - (Re-)configure the HD-audio codec 1620 * snd_hda_codec_configure - (Re-)configure the HD-audio codec
1542 * @codec: the HDA codec 1621 * @codec: the HDA codec
@@ -1548,6 +1627,7 @@ EXPORT_SYMBOL_HDA(snd_hda_codec_update_widgets);
1548 */ 1627 */
1549int snd_hda_codec_configure(struct hda_codec *codec) 1628int snd_hda_codec_configure(struct hda_codec *codec)
1550{ 1629{
1630 int (*patch)(struct hda_codec *) = NULL;
1551 int err; 1631 int err;
1552 1632
1553 codec->preset = find_codec_preset(codec); 1633 codec->preset = find_codec_preset(codec);
@@ -1557,29 +1637,40 @@ int snd_hda_codec_configure(struct hda_codec *codec)
1557 return err; 1637 return err;
1558 } 1638 }
1559 1639
1560 if (is_generic_config(codec)) { 1640 if (!is_generic_config(codec) && codec->preset)
1561 err = snd_hda_parse_generic_codec(codec); 1641 patch = codec->preset->patch;
1562 goto patched; 1642 if (!patch) {
1563 } 1643 unload_parser(codec); /* to be sure */
1564 if (codec->preset && codec->preset->patch) { 1644 if (is_likely_hdmi_codec(codec))
1565 err = codec->preset->patch(codec); 1645 patch = load_parser(codec, snd_hda_parse_hdmi_codec);
1566 goto patched; 1646#ifdef CONFIG_SND_HDA_GENERIC
1647 if (!patch)
1648 patch = load_parser(codec, snd_hda_parse_generic_codec);
1649#endif
1650 if (!patch) {
1651 printk(KERN_ERR "hda-codec: No codec parser is available\n");
1652 return -ENODEV;
1653 }
1567 } 1654 }
1568 1655
1569 /* call the default parser */ 1656 err = patch(codec);
1570 err = snd_hda_parse_generic_codec(codec); 1657 if (err < 0) {
1571 if (err < 0) 1658 unload_parser(codec);
1572 printk(KERN_ERR "hda-codec: No codec parser is available\n"); 1659 return err;
1660 }
1573 1661
1574 patched: 1662 if (codec->patch_ops.unsol_event) {
1575 if (!err && codec->patch_ops.unsol_event)
1576 err = init_unsol_queue(codec->bus); 1663 err = init_unsol_queue(codec->bus);
1664 if (err < 0)
1665 return err;
1666 }
1667
1577 /* audio codec should override the mixer name */ 1668 /* audio codec should override the mixer name */
1578 if (!err && (codec->afg || !*codec->bus->card->mixername)) 1669 if (codec->afg || !*codec->bus->card->mixername)
1579 snprintf(codec->bus->card->mixername, 1670 snprintf(codec->bus->card->mixername,
1580 sizeof(codec->bus->card->mixername), 1671 sizeof(codec->bus->card->mixername),
1581 "%s %s", codec->vendor_name, codec->chip_name); 1672 "%s %s", codec->vendor_name, codec->chip_name);
1582 return err; 1673 return 0;
1583} 1674}
1584EXPORT_SYMBOL_HDA(snd_hda_codec_configure); 1675EXPORT_SYMBOL_HDA(snd_hda_codec_configure);
1585 1676
@@ -2610,6 +2701,7 @@ int snd_hda_codec_reset(struct hda_codec *codec)
2610 codec->preset = NULL; 2701 codec->preset = NULL;
2611 codec->slave_dig_outs = NULL; 2702 codec->slave_dig_outs = NULL;
2612 codec->spdif_status_reset = 0; 2703 codec->spdif_status_reset = 0;
2704 unload_parser(codec);
2613 module_put(codec->owner); 2705 module_put(codec->owner);
2614 codec->owner = NULL; 2706 codec->owner = NULL;
2615 2707
@@ -4000,10 +4092,6 @@ static void hda_call_codec_resume(struct hda_codec *codec)
4000 * in the resume / power-save sequence 4092 * in the resume / power-save sequence
4001 */ 4093 */
4002 hda_keep_power_on(codec); 4094 hda_keep_power_on(codec);
4003 if (codec->pm_down_notified) {
4004 codec->pm_down_notified = 0;
4005 hda_call_pm_notify(codec->bus, true);
4006 }
4007 hda_set_power_state(codec, AC_PWRST_D0); 4095 hda_set_power_state(codec, AC_PWRST_D0);
4008 restore_shutup_pins(codec); 4096 restore_shutup_pins(codec);
4009 hda_exec_init_verbs(codec); 4097 hda_exec_init_verbs(codec);
@@ -4877,11 +4965,8 @@ static void hda_power_work(struct work_struct *work)
4877 spin_unlock(&codec->power_lock); 4965 spin_unlock(&codec->power_lock);
4878 4966
4879 state = hda_call_codec_suspend(codec, true); 4967 state = hda_call_codec_suspend(codec, true);
4880 if (!codec->pm_down_notified && 4968 if (!bus->power_keep_link_on && (state & AC_PWRST_CLK_STOP_OK))
4881 !bus->power_keep_link_on && (state & AC_PWRST_CLK_STOP_OK)) { 4969 hda_call_pm_notify(codec, false);
4882 codec->pm_down_notified = 1;
4883 hda_call_pm_notify(bus, false);
4884 }
4885} 4970}
4886 4971
4887static void hda_keep_power_on(struct hda_codec *codec) 4972static void hda_keep_power_on(struct hda_codec *codec)
@@ -4891,6 +4976,7 @@ static void hda_keep_power_on(struct hda_codec *codec)
4891 codec->power_on = 1; 4976 codec->power_on = 1;
4892 codec->power_jiffies = jiffies; 4977 codec->power_jiffies = jiffies;
4893 spin_unlock(&codec->power_lock); 4978 spin_unlock(&codec->power_lock);
4979 hda_call_pm_notify(codec, true);
4894} 4980}
4895 4981
4896/* update the power on/off account with the current jiffies */ 4982/* update the power on/off account with the current jiffies */
@@ -4910,8 +4996,6 @@ void snd_hda_update_power_acct(struct hda_codec *codec)
4910/* call this with codec->power_lock held! */ 4996/* call this with codec->power_lock held! */
4911static void __snd_hda_power_up(struct hda_codec *codec, bool wait_power_down) 4997static void __snd_hda_power_up(struct hda_codec *codec, bool wait_power_down)
4912{ 4998{
4913 struct hda_bus *bus = codec->bus;
4914
4915 /* Return if power_on or transitioning to power_on, unless currently 4999 /* Return if power_on or transitioning to power_on, unless currently
4916 * powering down. */ 5000 * powering down. */
4917 if ((codec->power_on || codec->power_transition > 0) && 5001 if ((codec->power_on || codec->power_transition > 0) &&
@@ -4938,11 +5022,6 @@ static void __snd_hda_power_up(struct hda_codec *codec, bool wait_power_down)
4938 codec->power_transition = 1; /* avoid reentrance */ 5022 codec->power_transition = 1; /* avoid reentrance */
4939 spin_unlock(&codec->power_lock); 5023 spin_unlock(&codec->power_lock);
4940 5024
4941 if (codec->pm_down_notified) {
4942 codec->pm_down_notified = 0;
4943 hda_call_pm_notify(bus, true);
4944 }
4945
4946 hda_call_codec_resume(codec); 5025 hda_call_codec_resume(codec);
4947 5026
4948 spin_lock(&codec->power_lock); 5027 spin_lock(&codec->power_lock);
@@ -5036,6 +5115,14 @@ int snd_hda_check_amp_list_power(struct hda_codec *codec,
5036 return 0; 5115 return 0;
5037} 5116}
5038EXPORT_SYMBOL_HDA(snd_hda_check_amp_list_power); 5117EXPORT_SYMBOL_HDA(snd_hda_check_amp_list_power);
5118
5119static void hda_pm_work(struct work_struct *work)
5120{
5121 struct hda_codec *codec =
5122 container_of(work, struct hda_codec, pm_work);
5123
5124 hda_call_codec_suspend(codec, false);
5125}
5039#endif 5126#endif
5040 5127
5041/* 5128/*
@@ -5611,9 +5698,17 @@ int snd_hda_suspend(struct hda_bus *bus)
5611 5698
5612 list_for_each_entry(codec, &bus->codec_list, list) { 5699 list_for_each_entry(codec, &bus->codec_list, list) {
5613 cancel_delayed_work_sync(&codec->jackpoll_work); 5700 cancel_delayed_work_sync(&codec->jackpoll_work);
5614 if (hda_codec_is_power_on(codec)) 5701 if (hda_codec_is_power_on(codec)) {
5615 hda_call_codec_suspend(codec, false); 5702 if (bus->num_codecs > 1)
5703 queue_work(bus->pm_wq, &codec->pm_work);
5704 else
5705 hda_call_codec_suspend(codec, false);
5706 }
5616 } 5707 }
5708
5709 if (bus->num_codecs > 1)
5710 flush_workqueue(bus->pm_wq);
5711
5617 return 0; 5712 return 0;
5618} 5713}
5619EXPORT_SYMBOL_HDA(snd_hda_suspend); 5714EXPORT_SYMBOL_HDA(snd_hda_suspend);
diff --git a/sound/pci/hda/hda_codec.h b/sound/pci/hda/hda_codec.h
index 7aa9870040c1..9a2798a0313c 100644
--- a/sound/pci/hda/hda_codec.h
+++ b/sound/pci/hda/hda_codec.h
@@ -673,6 +673,7 @@ struct hda_bus {
673 673
674 /* codec linked list */ 674 /* codec linked list */
675 struct list_head codec_list; 675 struct list_head codec_list;
676 unsigned int num_codecs;
676 /* link caddr -> codec */ 677 /* link caddr -> codec */
677 struct hda_codec *caddr_tbl[HDA_MAX_CODEC_ADDRESS + 1]; 678 struct hda_codec *caddr_tbl[HDA_MAX_CODEC_ADDRESS + 1];
678 679
@@ -683,6 +684,9 @@ struct hda_bus {
683 struct hda_bus_unsolicited *unsol; 684 struct hda_bus_unsolicited *unsol;
684 char workq_name[16]; 685 char workq_name[16];
685 struct workqueue_struct *workq; /* common workqueue for codecs */ 686 struct workqueue_struct *workq; /* common workqueue for codecs */
687#ifdef CONFIG_PM
688 struct workqueue_struct *pm_wq; /* workqueue to parallel codec PM */
689#endif
686 690
687 /* assigned PCMs */ 691 /* assigned PCMs */
688 DECLARE_BITMAP(pcm_dev_bits, SNDRV_PCM_DEVICES); 692 DECLARE_BITMAP(pcm_dev_bits, SNDRV_PCM_DEVICES);
@@ -834,6 +838,7 @@ struct hda_codec {
834 /* detected preset */ 838 /* detected preset */
835 const struct hda_codec_preset *preset; 839 const struct hda_codec_preset *preset;
836 struct module *owner; 840 struct module *owner;
841 int (*parser)(struct hda_codec *codec);
837 const char *vendor_name; /* codec vendor name */ 842 const char *vendor_name; /* codec vendor name */
838 const char *chip_name; /* codec chip name */ 843 const char *chip_name; /* codec chip name */
839 const char *modelname; /* model name for preset */ 844 const char *modelname; /* model name for preset */
@@ -907,7 +912,7 @@ struct hda_codec {
907#ifdef CONFIG_PM 912#ifdef CONFIG_PM
908 unsigned int power_on :1; /* current (global) power-state */ 913 unsigned int power_on :1; /* current (global) power-state */
909 unsigned int d3_stop_clk:1; /* support D3 operation without BCLK */ 914 unsigned int d3_stop_clk:1; /* support D3 operation without BCLK */
910 unsigned int pm_down_notified:1; /* PM notified to controller */ 915 unsigned int pm_up_notified:1; /* PM notified to controller */
911 unsigned int in_pm:1; /* suspend/resume being performed */ 916 unsigned int in_pm:1; /* suspend/resume being performed */
912 int power_transition; /* power-state in transition */ 917 int power_transition; /* power-state in transition */
913 int power_count; /* current (global) power refcount */ 918 int power_count; /* current (global) power refcount */
@@ -916,6 +921,7 @@ struct hda_codec {
916 unsigned long power_off_acct; 921 unsigned long power_off_acct;
917 unsigned long power_jiffies; 922 unsigned long power_jiffies;
918 spinlock_t power_lock; 923 spinlock_t power_lock;
924 struct work_struct pm_work; /* task to parallel multi-codec PM */
919#endif 925#endif
920 926
921 /* filter the requested power state per nid */ 927 /* filter the requested power state per nid */
diff --git a/sound/pci/hda/hda_generic.c b/sound/pci/hda/hda_generic.c
index 3067ed4fe3b2..9b251456f2a0 100644
--- a/sound/pci/hda/hda_generic.c
+++ b/sound/pci/hda/hda_generic.c
@@ -28,6 +28,7 @@
28#include <linux/ctype.h> 28#include <linux/ctype.h>
29#include <linux/string.h> 29#include <linux/string.h>
30#include <linux/bitops.h> 30#include <linux/bitops.h>
31#include <linux/module.h>
31#include <sound/core.h> 32#include <sound/core.h>
32#include <sound/jack.h> 33#include <sound/jack.h>
33#include "hda_codec.h" 34#include "hda_codec.h"
@@ -5291,3 +5292,6 @@ error:
5291 return err; 5292 return err;
5292} 5293}
5293EXPORT_SYMBOL_HDA(snd_hda_parse_generic_codec); 5294EXPORT_SYMBOL_HDA(snd_hda_parse_generic_codec);
5295
5296MODULE_LICENSE("GPL");
5297MODULE_DESCRIPTION("Generic HD-audio codec parser");
diff --git a/sound/pci/hda/hda_intel.c b/sound/pci/hda/hda_intel.c
index c6d230193da6..dfdb96603636 100644
--- a/sound/pci/hda/hda_intel.c
+++ b/sound/pci/hda/hda_intel.c
@@ -3978,7 +3978,7 @@ static DEFINE_PCI_DEVICE_TABLE(azx_ids) = {
3978 .driver_data = AZX_DRIVER_PCH | AZX_DCAPS_INTEL_PCH_NOPM }, 3978 .driver_data = AZX_DRIVER_PCH | AZX_DCAPS_INTEL_PCH_NOPM },
3979 /* Panther Point */ 3979 /* Panther Point */
3980 { PCI_DEVICE(0x8086, 0x1e20), 3980 { PCI_DEVICE(0x8086, 0x1e20),
3981 .driver_data = AZX_DRIVER_PCH | AZX_DCAPS_INTEL_PCH_NOPM }, 3981 .driver_data = AZX_DRIVER_PCH | AZX_DCAPS_INTEL_PCH },
3982 /* Lynx Point */ 3982 /* Lynx Point */
3983 { PCI_DEVICE(0x8086, 0x8c20), 3983 { PCI_DEVICE(0x8086, 0x8c20),
3984 .driver_data = AZX_DRIVER_PCH | AZX_DCAPS_INTEL_PCH }, 3984 .driver_data = AZX_DRIVER_PCH | AZX_DCAPS_INTEL_PCH },
diff --git a/sound/pci/hda/hda_local.h b/sound/pci/hda/hda_local.h
index d398b648bb5d..da80c5bd7fd4 100644
--- a/sound/pci/hda/hda_local.h
+++ b/sound/pci/hda/hda_local.h
@@ -352,14 +352,8 @@ int snd_hda_multi_out_analog_cleanup(struct hda_codec *codec,
352/* 352/*
353 * generic codec parser 353 * generic codec parser
354 */ 354 */
355#ifdef CONFIG_SND_HDA_GENERIC
356int snd_hda_parse_generic_codec(struct hda_codec *codec); 355int snd_hda_parse_generic_codec(struct hda_codec *codec);
357#else 356int snd_hda_parse_hdmi_codec(struct hda_codec *codec);
358static inline int snd_hda_parse_generic_codec(struct hda_codec *codec)
359{
360 return -ENODEV;
361}
362#endif
363 357
364/* 358/*
365 * generic proc interface 359 * generic proc interface
diff --git a/sound/pci/hda/patch_hdmi.c b/sound/pci/hda/patch_hdmi.c
index 08407bed093e..4098196b2300 100644
--- a/sound/pci/hda/patch_hdmi.c
+++ b/sound/pci/hda/patch_hdmi.c
@@ -1692,21 +1692,6 @@ static int hdmi_parse_codec(struct hda_codec *codec)
1692 } 1692 }
1693 } 1693 }
1694 1694
1695#ifdef CONFIG_PM
1696 /* We're seeing some problems with unsolicited hot plug events on
1697 * PantherPoint after S3, if this is not enabled */
1698 if (codec->vendor_id == 0x80862806)
1699 codec->bus->power_keep_link_on = 1;
1700 /*
1701 * G45/IbexPeak don't support EPSS: the unsolicited pin hot plug event
1702 * can be lost and presence sense verb will become inaccurate if the
1703 * HDA link is powered off at hot plug or hw initialization time.
1704 */
1705 else if (!(snd_hda_param_read(codec, codec->afg, AC_PAR_POWER_STATE) &
1706 AC_PWRST_EPSS))
1707 codec->bus->power_keep_link_on = 1;
1708#endif
1709
1710 return 0; 1695 return 0;
1711} 1696}
1712 1697
@@ -3214,6 +3199,15 @@ static int patch_via_hdmi(struct hda_codec *codec)
3214} 3199}
3215 3200
3216/* 3201/*
3202 * called from hda_codec.c for generic HDMI support
3203 */
3204int snd_hda_parse_hdmi_codec(struct hda_codec *codec)
3205{
3206 return patch_generic_hdmi(codec);
3207}
3208EXPORT_SYMBOL_HDA(snd_hda_parse_hdmi_codec);
3209
3210/*
3217 * patch entries 3211 * patch entries
3218 */ 3212 */
3219static const struct hda_codec_preset snd_hda_preset_hdmi[] = { 3213static const struct hda_codec_preset snd_hda_preset_hdmi[] = {