diff options
Diffstat (limited to 'sound/pci/hda/patch_hdmi.c')
-rw-r--r-- | sound/pci/hda/patch_hdmi.c | 51 |
1 files changed, 29 insertions, 22 deletions
diff --git a/sound/pci/hda/patch_hdmi.c b/sound/pci/hda/patch_hdmi.c index f281c8068557..64f0a5e73a25 100644 --- a/sound/pci/hda/patch_hdmi.c +++ b/sound/pci/hda/patch_hdmi.c | |||
@@ -46,6 +46,9 @@ module_param(static_hdmi_pcm, bool, 0644); | |||
46 | MODULE_PARM_DESC(static_hdmi_pcm, "Don't restrict PCM parameters per ELD info"); | 46 | MODULE_PARM_DESC(static_hdmi_pcm, "Don't restrict PCM parameters per ELD info"); |
47 | 47 | ||
48 | #define is_haswell(codec) ((codec)->vendor_id == 0x80862807) | 48 | #define is_haswell(codec) ((codec)->vendor_id == 0x80862807) |
49 | #define is_broadwell(codec) ((codec)->vendor_id == 0x80862808) | ||
50 | #define is_haswell_plus(codec) (is_haswell(codec) || is_broadwell(codec)) | ||
51 | |||
49 | #define is_valleyview(codec) ((codec)->vendor_id == 0x80862882) | 52 | #define is_valleyview(codec) ((codec)->vendor_id == 0x80862882) |
50 | 53 | ||
51 | struct hdmi_spec_per_cvt { | 54 | struct hdmi_spec_per_cvt { |
@@ -1101,7 +1104,7 @@ static void hdmi_setup_audio_infoframe(struct hda_codec *codec, | |||
1101 | if (!channels) | 1104 | if (!channels) |
1102 | return; | 1105 | return; |
1103 | 1106 | ||
1104 | if (is_haswell(codec)) | 1107 | if (is_haswell_plus(codec)) |
1105 | snd_hda_codec_write(codec, pin_nid, 0, | 1108 | snd_hda_codec_write(codec, pin_nid, 0, |
1106 | AC_VERB_SET_AMP_GAIN_MUTE, | 1109 | AC_VERB_SET_AMP_GAIN_MUTE, |
1107 | AMP_OUT_UNMUTE); | 1110 | AMP_OUT_UNMUTE); |
@@ -1280,7 +1283,7 @@ static int hdmi_setup_stream(struct hda_codec *codec, hda_nid_t cvt_nid, | |||
1280 | struct hdmi_spec *spec = codec->spec; | 1283 | struct hdmi_spec *spec = codec->spec; |
1281 | int err; | 1284 | int err; |
1282 | 1285 | ||
1283 | if (is_haswell(codec)) | 1286 | if (is_haswell_plus(codec)) |
1284 | haswell_verify_D0(codec, cvt_nid, pin_nid); | 1287 | haswell_verify_D0(codec, cvt_nid, pin_nid); |
1285 | 1288 | ||
1286 | err = spec->ops.pin_hbr_setup(codec, pin_nid, is_hbr_format(format)); | 1289 | err = spec->ops.pin_hbr_setup(codec, pin_nid, is_hbr_format(format)); |
@@ -1421,7 +1424,7 @@ static int hdmi_pcm_open(struct hda_pcm_stream *hinfo, | |||
1421 | mux_idx); | 1424 | mux_idx); |
1422 | 1425 | ||
1423 | /* configure unused pins to choose other converters */ | 1426 | /* configure unused pins to choose other converters */ |
1424 | if (is_haswell(codec) || is_valleyview(codec)) | 1427 | if (is_haswell_plus(codec) || is_valleyview(codec)) |
1425 | intel_not_share_assigned_cvt(codec, per_pin->pin_nid, mux_idx); | 1428 | intel_not_share_assigned_cvt(codec, per_pin->pin_nid, mux_idx); |
1426 | 1429 | ||
1427 | snd_hda_spdif_ctls_assign(codec, pin_idx, per_cvt->cvt_nid); | 1430 | snd_hda_spdif_ctls_assign(codec, pin_idx, per_cvt->cvt_nid); |
@@ -1496,11 +1499,14 @@ static bool hdmi_present_sense(struct hdmi_spec_per_pin *per_pin, int repoll) | |||
1496 | * specification worked this way. Hence, we just ignore the data in | 1499 | * specification worked this way. Hence, we just ignore the data in |
1497 | * the unsolicited response to avoid custom WARs. | 1500 | * the unsolicited response to avoid custom WARs. |
1498 | */ | 1501 | */ |
1499 | int present = snd_hda_pin_sense(codec, pin_nid); | 1502 | int present; |
1500 | bool update_eld = false; | 1503 | bool update_eld = false; |
1501 | bool eld_changed = false; | 1504 | bool eld_changed = false; |
1502 | bool ret; | 1505 | bool ret; |
1503 | 1506 | ||
1507 | snd_hda_power_up(codec); | ||
1508 | present = snd_hda_pin_sense(codec, pin_nid); | ||
1509 | |||
1504 | mutex_lock(&per_pin->lock); | 1510 | mutex_lock(&per_pin->lock); |
1505 | pin_eld->monitor_present = !!(present & AC_PINSENSE_PRESENCE); | 1511 | pin_eld->monitor_present = !!(present & AC_PINSENSE_PRESENCE); |
1506 | if (pin_eld->monitor_present) | 1512 | if (pin_eld->monitor_present) |
@@ -1573,6 +1579,7 @@ static bool hdmi_present_sense(struct hdmi_spec_per_pin *per_pin, int repoll) | |||
1573 | jack->block_report = !ret; | 1579 | jack->block_report = !ret; |
1574 | 1580 | ||
1575 | mutex_unlock(&per_pin->lock); | 1581 | mutex_unlock(&per_pin->lock); |
1582 | snd_hda_power_down(codec); | ||
1576 | return ret; | 1583 | return ret; |
1577 | } | 1584 | } |
1578 | 1585 | ||
@@ -1607,7 +1614,7 @@ static int hdmi_add_pin(struct hda_codec *codec, hda_nid_t pin_nid) | |||
1607 | if (get_defcfg_connect(config) == AC_JACK_PORT_NONE) | 1614 | if (get_defcfg_connect(config) == AC_JACK_PORT_NONE) |
1608 | return 0; | 1615 | return 0; |
1609 | 1616 | ||
1610 | if (is_haswell(codec)) | 1617 | if (is_haswell_plus(codec)) |
1611 | intel_haswell_fixup_connect_list(codec, pin_nid); | 1618 | intel_haswell_fixup_connect_list(codec, pin_nid); |
1612 | 1619 | ||
1613 | pin_idx = spec->num_pins; | 1620 | pin_idx = spec->num_pins; |
@@ -1694,21 +1701,6 @@ static int hdmi_parse_codec(struct hda_codec *codec) | |||
1694 | } | 1701 | } |
1695 | } | 1702 | } |
1696 | 1703 | ||
1697 | #ifdef CONFIG_PM | ||
1698 | /* We're seeing some problems with unsolicited hot plug events on | ||
1699 | * PantherPoint after S3, if this is not enabled */ | ||
1700 | if (codec->vendor_id == 0x80862806) | ||
1701 | codec->bus->power_keep_link_on = 1; | ||
1702 | /* | ||
1703 | * G45/IbexPeak don't support EPSS: the unsolicited pin hot plug event | ||
1704 | * can be lost and presence sense verb will become inaccurate if the | ||
1705 | * HDA link is powered off at hot plug or hw initialization time. | ||
1706 | */ | ||
1707 | else if (!(snd_hda_param_read(codec, codec->afg, AC_PAR_POWER_STATE) & | ||
1708 | AC_PWRST_EPSS)) | ||
1709 | codec->bus->power_keep_link_on = 1; | ||
1710 | #endif | ||
1711 | |||
1712 | return 0; | 1704 | return 0; |
1713 | } | 1705 | } |
1714 | 1706 | ||
@@ -2260,18 +2252,22 @@ static int patch_generic_hdmi(struct hda_codec *codec) | |||
2260 | codec->spec = spec; | 2252 | codec->spec = spec; |
2261 | hdmi_array_init(spec, 4); | 2253 | hdmi_array_init(spec, 4); |
2262 | 2254 | ||
2263 | if (is_haswell(codec)) { | 2255 | if (is_haswell_plus(codec)) { |
2264 | intel_haswell_enable_all_pins(codec, true); | 2256 | intel_haswell_enable_all_pins(codec, true); |
2265 | intel_haswell_fixup_enable_dp12(codec); | 2257 | intel_haswell_fixup_enable_dp12(codec); |
2266 | } | 2258 | } |
2267 | 2259 | ||
2260 | if (is_haswell(codec) || is_valleyview(codec)) { | ||
2261 | codec->depop_delay = 0; | ||
2262 | } | ||
2263 | |||
2268 | if (hdmi_parse_codec(codec) < 0) { | 2264 | if (hdmi_parse_codec(codec) < 0) { |
2269 | codec->spec = NULL; | 2265 | codec->spec = NULL; |
2270 | kfree(spec); | 2266 | kfree(spec); |
2271 | return -EINVAL; | 2267 | return -EINVAL; |
2272 | } | 2268 | } |
2273 | codec->patch_ops = generic_hdmi_patch_ops; | 2269 | codec->patch_ops = generic_hdmi_patch_ops; |
2274 | if (is_haswell(codec)) { | 2270 | if (is_haswell_plus(codec)) { |
2275 | codec->patch_ops.set_power_state = haswell_set_power_state; | 2271 | codec->patch_ops.set_power_state = haswell_set_power_state; |
2276 | codec->dp_mst = true; | 2272 | codec->dp_mst = true; |
2277 | } | 2273 | } |
@@ -3218,6 +3214,15 @@ static int patch_via_hdmi(struct hda_codec *codec) | |||
3218 | } | 3214 | } |
3219 | 3215 | ||
3220 | /* | 3216 | /* |
3217 | * called from hda_codec.c for generic HDMI support | ||
3218 | */ | ||
3219 | int snd_hda_parse_hdmi_codec(struct hda_codec *codec) | ||
3220 | { | ||
3221 | return patch_generic_hdmi(codec); | ||
3222 | } | ||
3223 | EXPORT_SYMBOL_GPL(snd_hda_parse_hdmi_codec); | ||
3224 | |||
3225 | /* | ||
3221 | * patch entries | 3226 | * patch entries |
3222 | */ | 3227 | */ |
3223 | static const struct hda_codec_preset snd_hda_preset_hdmi[] = { | 3228 | static const struct hda_codec_preset snd_hda_preset_hdmi[] = { |
@@ -3271,6 +3276,7 @@ static const struct hda_codec_preset snd_hda_preset_hdmi[] = { | |||
3271 | { .id = 0x80862805, .name = "CougarPoint HDMI", .patch = patch_generic_hdmi }, | 3276 | { .id = 0x80862805, .name = "CougarPoint HDMI", .patch = patch_generic_hdmi }, |
3272 | { .id = 0x80862806, .name = "PantherPoint HDMI", .patch = patch_generic_hdmi }, | 3277 | { .id = 0x80862806, .name = "PantherPoint HDMI", .patch = patch_generic_hdmi }, |
3273 | { .id = 0x80862807, .name = "Haswell HDMI", .patch = patch_generic_hdmi }, | 3278 | { .id = 0x80862807, .name = "Haswell HDMI", .patch = patch_generic_hdmi }, |
3279 | { .id = 0x80862808, .name = "Broadwell HDMI", .patch = patch_generic_hdmi }, | ||
3274 | { .id = 0x80862880, .name = "CedarTrail HDMI", .patch = patch_generic_hdmi }, | 3280 | { .id = 0x80862880, .name = "CedarTrail HDMI", .patch = patch_generic_hdmi }, |
3275 | { .id = 0x80862882, .name = "Valleyview2 HDMI", .patch = patch_generic_hdmi }, | 3281 | { .id = 0x80862882, .name = "Valleyview2 HDMI", .patch = patch_generic_hdmi }, |
3276 | { .id = 0x808629fb, .name = "Crestline HDMI", .patch = patch_generic_hdmi }, | 3282 | { .id = 0x808629fb, .name = "Crestline HDMI", .patch = patch_generic_hdmi }, |
@@ -3326,6 +3332,7 @@ MODULE_ALIAS("snd-hda-codec-id:80862804"); | |||
3326 | MODULE_ALIAS("snd-hda-codec-id:80862805"); | 3332 | MODULE_ALIAS("snd-hda-codec-id:80862805"); |
3327 | MODULE_ALIAS("snd-hda-codec-id:80862806"); | 3333 | MODULE_ALIAS("snd-hda-codec-id:80862806"); |
3328 | MODULE_ALIAS("snd-hda-codec-id:80862807"); | 3334 | MODULE_ALIAS("snd-hda-codec-id:80862807"); |
3335 | MODULE_ALIAS("snd-hda-codec-id:80862808"); | ||
3329 | MODULE_ALIAS("snd-hda-codec-id:80862880"); | 3336 | MODULE_ALIAS("snd-hda-codec-id:80862880"); |
3330 | MODULE_ALIAS("snd-hda-codec-id:80862882"); | 3337 | MODULE_ALIAS("snd-hda-codec-id:80862882"); |
3331 | MODULE_ALIAS("snd-hda-codec-id:808629fb"); | 3338 | MODULE_ALIAS("snd-hda-codec-id:808629fb"); |