From 54a25f87e943fc77f57e86849897ad6602519286 Mon Sep 17 00:00:00 2001 From: Wu Fengguang Date: Fri, 30 Oct 2009 11:44:26 +0100 Subject: ALSA: hda - vectorize intelhdmi The Intel IbexPeak HDMI codec supports 2 converters and 3 pins, which requires converting the cvt_nid/pin_nid to arrays. The active pin number (the one connected with a live HDMI monitor/sink) will be dynamically identified on hotplug events. It exports two HDMI devices, so that user space can choose the A/V pipe for sending the audio samples. It's still undefined behavior when there are two active monitors connected and routed to the same audio converter. Signed-off-by: Wu Fengguang Signed-off-by: Takashi Iwai --- sound/pci/hda/hda_local.h | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) (limited to 'sound/pci/hda/hda_local.h') diff --git a/sound/pci/hda/hda_local.h b/sound/pci/hda/hda_local.h index 5f1dcc59002b..461e0c15c77a 100644 --- a/sound/pci/hda/hda_local.h +++ b/sound/pci/hda/hda_local.h @@ -541,11 +541,13 @@ int snd_hdmi_get_eld(struct hdmi_eld *, struct hda_codec *, hda_nid_t); void snd_hdmi_show_eld(struct hdmi_eld *eld); #ifdef CONFIG_PROC_FS -int snd_hda_eld_proc_new(struct hda_codec *codec, struct hdmi_eld *eld); +int snd_hda_eld_proc_new(struct hda_codec *codec, struct hdmi_eld *eld, + int index); void snd_hda_eld_proc_free(struct hda_codec *codec, struct hdmi_eld *eld); #else static inline int snd_hda_eld_proc_new(struct hda_codec *codec, - struct hdmi_eld *eld) + struct hdmi_eld *eld, + int index) { return 0; } -- cgit v1.2.3-59-g8ed1b From a2f6309e8392e2c14c04594fca8b4876c8c9bc36 Mon Sep 17 00:00:00 2001 From: Takashi Iwai Date: Wed, 11 Nov 2009 09:34:25 +0100 Subject: ALSA: hda - Add power on/off counter Added the power on/off counter and expose via sysfs files. The sysfs files, power_on_acct and power_off_acct, are created under each codec hwdep sysfs directory (e.g. /sys/class/sound/hwC0D0). The files show the msec length of the codec power-on and power-off, respectively. Signed-off-by: Takashi Iwai --- sound/pci/hda/hda_codec.c | 16 ++++++++++++++++ sound/pci/hda/hda_codec.h | 4 ++++ sound/pci/hda/hda_hwdep.c | 38 ++++++++++++++++++++++++++++++++++++++ sound/pci/hda/hda_local.h | 9 +++++++++ 4 files changed, 67 insertions(+) (limited to 'sound/pci/hda/hda_local.h') diff --git a/sound/pci/hda/hda_codec.c b/sound/pci/hda/hda_codec.c index 2b787b013e93..444d9039c1ac 100644 --- a/sound/pci/hda/hda_codec.c +++ b/sound/pci/hda/hda_codec.c @@ -515,6 +515,7 @@ static int snd_hda_bus_dev_register(struct snd_device *device) struct hda_codec *codec; list_for_each_entry(codec, &bus->codec_list, list) { snd_hda_hwdep_add_sysfs(codec); + snd_hda_hwdep_add_power_sysfs(codec); } return 0; } @@ -2452,9 +2453,11 @@ static void hda_call_codec_suspend(struct hda_codec *codec) codec->afg ? codec->afg : codec->mfg, AC_PWRST_D3); #ifdef CONFIG_SND_HDA_POWER_SAVE + snd_hda_update_power_acct(codec); cancel_delayed_work(&codec->power_work); codec->power_on = 0; codec->power_transition = 0; + codec->power_jiffies = jiffies; #endif } @@ -3191,6 +3194,17 @@ static void hda_keep_power_on(struct hda_codec *codec) { codec->power_count++; codec->power_on = 1; + codec->power_jiffies = jiffies; +} + +void snd_hda_update_power_acct(struct hda_codec *codec) +{ + unsigned long delta = jiffies - codec->power_jiffies; + if (codec->power_on) + codec->power_on_acct += delta; + else + codec->power_off_acct += delta; + codec->power_jiffies += delta; } void snd_hda_power_up(struct hda_codec *codec) @@ -3201,7 +3215,9 @@ void snd_hda_power_up(struct hda_codec *codec) if (codec->power_on || codec->power_transition) return; + snd_hda_update_power_acct(codec); codec->power_on = 1; + codec->power_jiffies = jiffies; if (bus->ops.pm_notify) bus->ops.pm_notify(bus); hda_call_codec_resume(codec); diff --git a/sound/pci/hda/hda_codec.h b/sound/pci/hda/hda_codec.h index cbf199a98ab2..b16678cade18 100644 --- a/sound/pci/hda/hda_codec.h +++ b/sound/pci/hda/hda_codec.h @@ -812,6 +812,9 @@ struct hda_codec { unsigned int power_transition :1; /* power-state in transition */ int power_count; /* current (global) power refcount */ struct delayed_work power_work; /* delayed task for powerdown */ + unsigned long power_on_acct; + unsigned long power_off_acct; + unsigned long power_jiffies; #endif /* codec-specific additional proc output */ @@ -936,6 +939,7 @@ const char *snd_hda_get_jack_location(u32 cfg); void snd_hda_power_up(struct hda_codec *codec); void snd_hda_power_down(struct hda_codec *codec); #define snd_hda_codec_needs_resume(codec) codec->power_count +void snd_hda_update_power_acct(struct hda_codec *codec); #else static inline void snd_hda_power_up(struct hda_codec *codec) {} static inline void snd_hda_power_down(struct hda_codec *codec) {} diff --git a/sound/pci/hda/hda_hwdep.c b/sound/pci/hda/hda_hwdep.c index cc24e6721d74..d24328661c6a 100644 --- a/sound/pci/hda/hda_hwdep.c +++ b/sound/pci/hda/hda_hwdep.c @@ -154,6 +154,44 @@ int /*__devinit*/ snd_hda_create_hwdep(struct hda_codec *codec) return 0; } +#ifdef CONFIG_SND_HDA_POWER_SAVE +static ssize_t power_on_acct_show(struct device *dev, + struct device_attribute *attr, + char *buf) +{ + struct snd_hwdep *hwdep = dev_get_drvdata(dev); + struct hda_codec *codec = hwdep->private_data; + snd_hda_update_power_acct(codec); + return sprintf(buf, "%u\n", jiffies_to_msecs(codec->power_on_acct)); +} + +static ssize_t power_off_acct_show(struct device *dev, + struct device_attribute *attr, + char *buf) +{ + struct snd_hwdep *hwdep = dev_get_drvdata(dev); + struct hda_codec *codec = hwdep->private_data; + snd_hda_update_power_acct(codec); + return sprintf(buf, "%u\n", jiffies_to_msecs(codec->power_off_acct)); +} + +static struct device_attribute power_attrs[] = { + __ATTR_RO(power_on_acct), + __ATTR_RO(power_off_acct), +}; + +int snd_hda_hwdep_add_power_sysfs(struct hda_codec *codec) +{ + struct snd_hwdep *hwdep = codec->hwdep; + int i; + + for (i = 0; i < ARRAY_SIZE(power_attrs); i++) + snd_add_device_sysfs_file(SNDRV_DEVICE_TYPE_HWDEP, hwdep->card, + hwdep->device, &power_attrs[i]); + return 0; +} +#endif /* CONFIG_SND_HDA_POWER_SAVE */ + #ifdef CONFIG_SND_HDA_RECONFIG /* diff --git a/sound/pci/hda/hda_local.h b/sound/pci/hda/hda_local.h index 461e0c15c77a..015fbac914b3 100644 --- a/sound/pci/hda/hda_local.h +++ b/sound/pci/hda/hda_local.h @@ -437,6 +437,15 @@ int snd_hda_create_hwdep(struct hda_codec *codec); static inline int snd_hda_create_hwdep(struct hda_codec *codec) { return 0; } #endif +#ifdef CONFIG_SND_HDA_POWER_SAVE +int snd_hda_hwdep_add_power_sysfs(struct hda_codec *codec); +#else +static inline int snd_hda_hwdep_add_power_sysfs(struct hda_codec *codec) +{ + return 0; +} +#endif + #ifdef CONFIG_SND_HDA_RECONFIG int snd_hda_hwdep_add_sysfs(struct hda_codec *codec); #else -- cgit v1.2.3-59-g8ed1b From 7288561af9a931c59e431336b553d897ee37b67d Mon Sep 17 00:00:00 2001 From: Takashi Iwai Date: Thu, 12 Nov 2009 10:01:18 +0100 Subject: ALSA: hda - Fix build error without CONFIG_SND_HDA_HWDEP=y CONFIG_SND_HDA_POWER_SAVE is independent from CONFIG_SND_HDA_HWDEP. Thus snd_hda_hwdep_add_power_sysfs() needs the check of both kconfigs. Signed-off-by: Takashi Iwai --- sound/pci/hda/hda_local.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'sound/pci/hda/hda_local.h') diff --git a/sound/pci/hda/hda_local.h b/sound/pci/hda/hda_local.h index 015fbac914b3..c1ca3182e6a4 100644 --- a/sound/pci/hda/hda_local.h +++ b/sound/pci/hda/hda_local.h @@ -437,7 +437,7 @@ int snd_hda_create_hwdep(struct hda_codec *codec); static inline int snd_hda_create_hwdep(struct hda_codec *codec) { return 0; } #endif -#ifdef CONFIG_SND_HDA_POWER_SAVE +#if defined(CONFIG_SND_HDA_POWER_SAVE) && defined(CONFIG_SND_HDA_HWDEP) int snd_hda_hwdep_add_power_sysfs(struct hda_codec *codec); #else static inline int snd_hda_hwdep_add_power_sysfs(struct hda_codec *codec) -- cgit v1.2.3-59-g8ed1b From 123c07aeddd71fbb295842a8c19866e780b9a100 Mon Sep 17 00:00:00 2001 From: Jaroslav Kysela Date: Wed, 21 Oct 2009 14:48:23 +0200 Subject: ALSA: hda_intel: Digital PC Beep - change behaviour for input layer Original implementation was keeping registered input device for SND_BEEP and SND_TONE events all time. This patch changes this behaviour: If digital PC Beep is turned off using universal control switch, the input device is unregistered. Explanation: The kd_mksound() send SND_BEEP and SND_TONE only to last registered device acceping those events. It means that the HDA Intel audio driver blocks also the internal PC Speaker device (pcspkr.c driver) even if the HDA Beep is muted. The user can easy disable all beeps using 'setterm -blength 0' or 'xset b off' command. Signed-off-by: Jaroslav Kysela Signed-off-by: Takashi Iwai --- sound/pci/hda/hda_beep.c | 88 +++++++++++++++++++++++++++++++++--------- sound/pci/hda/hda_beep.h | 4 ++ sound/pci/hda/hda_codec.c | 12 ++++++ sound/pci/hda/hda_local.h | 15 +++++++ sound/pci/hda/patch_analog.c | 2 +- sound/pci/hda/patch_realtek.c | 2 +- sound/pci/hda/patch_sigmatel.c | 16 ++++---- 7 files changed, 111 insertions(+), 28 deletions(-) (limited to 'sound/pci/hda/hda_local.h') diff --git a/sound/pci/hda/hda_beep.c b/sound/pci/hda/hda_beep.c index 3f51a981e604..0e986537d570 100644 --- a/sound/pci/hda/hda_beep.c +++ b/sound/pci/hda/hda_beep.c @@ -113,23 +113,25 @@ static int snd_hda_beep_event(struct input_dev *dev, unsigned int type, return 0; } -int snd_hda_attach_beep_device(struct hda_codec *codec, int nid) +static void snd_hda_do_detach(struct hda_beep *beep) +{ + input_unregister_device(beep->dev); + beep->dev = NULL; + cancel_work_sync(&beep->beep_work); + /* turn off beep for sure */ + snd_hda_codec_write_cache(beep->codec, beep->nid, 0, + AC_VERB_SET_BEEP_CONTROL, 0); +} + +static int snd_hda_do_attach(struct hda_beep *beep) { struct input_dev *input_dev; - struct hda_beep *beep; + struct hda_codec *codec = beep->codec; int err; - if (!snd_hda_get_bool_hint(codec, "beep")) - return 0; /* disabled explicitly */ - - beep = kzalloc(sizeof(*beep), GFP_KERNEL); - if (beep == NULL) - return -ENOMEM; - snprintf(beep->phys, sizeof(beep->phys), - "card%d/codec#%d/beep0", codec->bus->card->number, codec->addr); input_dev = input_allocate_device(); if (!input_dev) { - kfree(beep); + printk(KERN_INFO "hda_beep: unable to allocate input device\n"); return -ENOMEM; } @@ -151,21 +153,71 @@ int snd_hda_attach_beep_device(struct hda_codec *codec, int nid) err = input_register_device(input_dev); if (err < 0) { input_free_device(input_dev); - kfree(beep); + printk(KERN_INFO "hda_beep: unable to register input device\n"); return err; } + beep->dev = input_dev; + return 0; +} + +static void snd_hda_do_register(struct work_struct *work) +{ + struct hda_beep *beep = + container_of(work, struct hda_beep, register_work); + int request; + + mutex_lock(&beep->mutex); + request = beep->request_enable; + if (beep->enabled != request) { + if (!request) { + snd_hda_do_detach(beep); + } else { + if (snd_hda_do_attach(beep) < 0) + goto __out; + } + beep->enabled = request; + } + __out: + mutex_unlock(&beep->mutex); +} + +int snd_hda_enable_beep_device(struct hda_codec *codec, int enable) +{ + struct hda_beep *beep = codec->beep; + enable = !!enable; + if (beep && beep->enabled != enable) { + beep->request_enable = enable; + schedule_work(&beep->register_work); + return 1; + } + return 0; +} +EXPORT_SYMBOL_HDA(snd_hda_enable_beep_device); + +int snd_hda_attach_beep_device(struct hda_codec *codec, int nid) +{ + struct hda_beep *beep; + + if (!snd_hda_get_bool_hint(codec, "beep")) + return 0; /* disabled explicitly */ + beep = kzalloc(sizeof(*beep), GFP_KERNEL); + if (beep == NULL) + return -ENOMEM; + snprintf(beep->phys, sizeof(beep->phys), + "card%d/codec#%d/beep0", codec->bus->card->number, codec->addr); /* enable linear scale */ snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_DIGI_CONVERT_2, 0x01); beep->nid = nid; - beep->dev = input_dev; beep->codec = codec; - beep->enabled = 1; codec->beep = beep; + INIT_WORK(&beep->register_work, &snd_hda_do_register); INIT_WORK(&beep->beep_work, &snd_hda_generate_beep); + mutex_init(&beep->mutex); + return 0; } EXPORT_SYMBOL_HDA(snd_hda_attach_beep_device); @@ -174,11 +226,11 @@ void snd_hda_detach_beep_device(struct hda_codec *codec) { struct hda_beep *beep = codec->beep; if (beep) { - cancel_work_sync(&beep->beep_work); - - input_unregister_device(beep->dev); - kfree(beep); + cancel_work_sync(&beep->register_work); + if (beep->enabled) + snd_hda_do_detach(beep); codec->beep = NULL; + kfree(beep); } } EXPORT_SYMBOL_HDA(snd_hda_detach_beep_device); diff --git a/sound/pci/hda/hda_beep.h b/sound/pci/hda/hda_beep.h index 0c3de787c717..68465f679d8c 100644 --- a/sound/pci/hda/hda_beep.h +++ b/sound/pci/hda/hda_beep.h @@ -32,11 +32,15 @@ struct hda_beep { int tone; hda_nid_t nid; unsigned int enabled:1; + unsigned int request_enable:1; unsigned int linear_tone:1; /* linear tone for IDT/STAC codec */ + struct work_struct register_work; /* scheduled task for beep event */ struct work_struct beep_work; /* scheduled task for beep event */ + struct mutex mutex; }; #ifdef CONFIG_SND_HDA_INPUT_BEEP +int snd_hda_enable_beep_device(struct hda_codec *codec, int enable); int snd_hda_attach_beep_device(struct hda_codec *codec, int nid); void snd_hda_detach_beep_device(struct hda_codec *codec); #else diff --git a/sound/pci/hda/hda_codec.c b/sound/pci/hda/hda_codec.c index 444d9039c1ac..7fd2abe1129d 100644 --- a/sound/pci/hda/hda_codec.c +++ b/sound/pci/hda/hda_codec.c @@ -30,6 +30,7 @@ #include #include #include "hda_local.h" +#include "hda_beep.h" #include /* @@ -1734,6 +1735,17 @@ int snd_hda_mixer_amp_switch_put(struct snd_kcontrol *kcontrol, } EXPORT_SYMBOL_HDA(snd_hda_mixer_amp_switch_put); +int snd_hda_mixer_amp_switch_put_beep(struct snd_kcontrol *kcontrol, + struct snd_ctl_elem_value *ucontrol) +{ + struct hda_codec *codec = snd_kcontrol_chip(kcontrol); + long *valp = ucontrol->value.integer.value; + + snd_hda_enable_beep_device(codec, *valp); + return snd_hda_mixer_amp_switch_put(kcontrol, ucontrol); +} +EXPORT_SYMBOL_HDA(snd_hda_mixer_amp_switch_put_beep); + /* * bound volume controls * diff --git a/sound/pci/hda/hda_local.h b/sound/pci/hda/hda_local.h index c1ca3182e6a4..3001794ad291 100644 --- a/sound/pci/hda/hda_local.h +++ b/sound/pci/hda/hda_local.h @@ -66,6 +66,19 @@ /* stereo mute switch */ #define HDA_CODEC_MUTE(xname, nid, xindex, direction) \ HDA_CODEC_MUTE_MONO(xname, nid, 3, xindex, direction) +/* special beep mono mute switch with index (index=0,1,...) (channel=1,2) */ +#define HDA_CODEC_MUTE_BEEP_MONO_IDX(xname, xcidx, nid, channel, xindex, direction) \ + { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = xname, .index = xcidx, \ + .info = snd_hda_mixer_amp_switch_info, \ + .get = snd_hda_mixer_amp_switch_get, \ + .put = snd_hda_mixer_amp_switch_put_beep, \ + .private_value = HDA_COMPOSE_AMP_VAL(nid, channel, xindex, direction) } +/* special beep mono mute switch */ +#define HDA_CODEC_MUTE_BEEP_MONO(xname, nid, channel, xindex, direction) \ + HDA_CODEC_MUTE_BEEP_MONO_IDX(xname, 0, nid, channel, xindex, direction) +/* special beep stereo mute switch */ +#define HDA_CODEC_MUTE_BEEP(xname, nid, xindex, direction) \ + HDA_CODEC_MUTE_BEEP_MONO(xname, nid, 3, xindex, direction) int snd_hda_mixer_amp_volume_info(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_info *uinfo); @@ -81,6 +94,8 @@ int snd_hda_mixer_amp_switch_get(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol); int snd_hda_mixer_amp_switch_put(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol); +int snd_hda_mixer_amp_switch_put_beep(struct snd_kcontrol *kcontrol, + struct snd_ctl_elem_value *ucontrol); /* lowlevel accessor with caching; use carefully */ int snd_hda_codec_amp_read(struct hda_codec *codec, hda_nid_t nid, int ch, int direction, int index); diff --git a/sound/pci/hda/patch_analog.c b/sound/pci/hda/patch_analog.c index 2d603f6aba63..a0293614a0b9 100644 --- a/sound/pci/hda/patch_analog.c +++ b/sound/pci/hda/patch_analog.c @@ -159,7 +159,7 @@ static void ad198x_free_kctls(struct hda_codec *codec); /* additional beep mixers; the actual parameters are overwritten at build */ static struct snd_kcontrol_new ad_beep_mixer[] = { HDA_CODEC_VOLUME("Beep Playback Volume", 0, 0, HDA_OUTPUT), - HDA_CODEC_MUTE("Beep Playback Switch", 0, 0, HDA_OUTPUT), + HDA_CODEC_MUTE_BEEP("Beep Playback Switch", 0, 0, HDA_OUTPUT), { } /* end */ }; diff --git a/sound/pci/hda/patch_realtek.c b/sound/pci/hda/patch_realtek.c index 49de107db16b..8c04e0e0f655 100644 --- a/sound/pci/hda/patch_realtek.c +++ b/sound/pci/hda/patch_realtek.c @@ -2413,7 +2413,7 @@ static void alc_free_kctls(struct hda_codec *codec); /* additional beep mixers; the actual parameters are overwritten at build */ static struct snd_kcontrol_new alc_beep_mixer[] = { HDA_CODEC_VOLUME("Beep Playback Volume", 0, 0, HDA_INPUT), - HDA_CODEC_MUTE("Beep Playback Switch", 0, 0, HDA_INPUT), + HDA_CODEC_MUTE_BEEP("Beep Playback Switch", 0, 0, HDA_INPUT), { } /* end */ }; diff --git a/sound/pci/hda/patch_sigmatel.c b/sound/pci/hda/patch_sigmatel.c index 8d65d2b25234..87ba239ff1c9 100644 --- a/sound/pci/hda/patch_sigmatel.c +++ b/sound/pci/hda/patch_sigmatel.c @@ -2648,6 +2648,7 @@ static int stac92xx_clfe_switch_put(struct snd_kcontrol *kcontrol, enum { STAC_CTL_WIDGET_VOL, STAC_CTL_WIDGET_MUTE, + STAC_CTL_WIDGET_MUTE_BEEP, STAC_CTL_WIDGET_MONO_MUX, STAC_CTL_WIDGET_HP_SWITCH, STAC_CTL_WIDGET_IO_SWITCH, @@ -2658,6 +2659,7 @@ enum { static struct snd_kcontrol_new stac92xx_control_templates[] = { HDA_CODEC_VOLUME(NULL, 0, 0, 0), HDA_CODEC_MUTE(NULL, 0, 0, 0), + HDA_CODEC_MUTE_BEEP(NULL, 0, 0, 0), STAC_MONO_MUX, STAC_CODEC_HP_SWITCH(NULL), STAC_CODEC_IO_SWITCH(NULL, 0), @@ -3221,11 +3223,14 @@ static int stac92xx_auto_create_beep_ctls(struct hda_codec *codec, { struct sigmatel_spec *spec = codec->spec; u32 caps = query_amp_caps(codec, nid, HDA_OUTPUT); - int err; + int err, type = STAC_CTL_WIDGET_MUTE_BEEP; + + if (spec->anabeep_nid == nid) + type = STAC_CTL_WIDGET_MUTE; /* check for mute support for the the amp */ if ((caps & AC_AMPCAP_MUTE) >> AC_AMPCAP_MUTE_SHIFT) { - err = stac92xx_add_control(spec, STAC_CTL_WIDGET_MUTE, + err = stac92xx_add_control(spec, type, "Beep Playback Switch", HDA_COMPOSE_AMP_VAL(nid, 1, 0, HDA_OUTPUT)); if (err < 0) @@ -3258,12 +3263,7 @@ static int stac92xx_dig_beep_switch_put(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol) { struct hda_codec *codec = snd_kcontrol_chip(kcontrol); - int enabled = !!ucontrol->value.integer.value[0]; - if (codec->beep->enabled != enabled) { - codec->beep->enabled = enabled; - return 1; - } - return 0; + return snd_hda_enable_beep_device(codec, ucontrol->value.integer.value[0]); } static struct snd_kcontrol_new stac92xx_dig_beep_ctrl = { -- cgit v1.2.3-59-g8ed1b From 3911a4c19e927738766003839aa447becbdbaa27 Mon Sep 17 00:00:00 2001 From: Jaroslav Kysela Date: Wed, 11 Nov 2009 13:43:01 +0100 Subject: ALSA: hda - proc - introduce Control: lines to show mixer<->NID assignment This is an initial patch to show universal control<->NID assigment in proc codec file. The change helps to debug codec related problems. Signed-off-by: Jaroslav Kysela Signed-off-by: Takashi Iwai --- sound/pci/hda/hda_codec.c | 32 ++++++++++++------------ sound/pci/hda/hda_generic.c | 17 ++++++++----- sound/pci/hda/hda_local.h | 11 +++++++-- sound/pci/hda/hda_proc.c | 55 ++++++++++++++++++++++++++++++------------ sound/pci/hda/patch_analog.c | 4 ++- sound/pci/hda/patch_ca0110.c | 4 +-- sound/pci/hda/patch_cirrus.c | 12 ++++----- sound/pci/hda/patch_realtek.c | 3 ++- sound/pci/hda/patch_sigmatel.c | 4 +-- 9 files changed, 92 insertions(+), 50 deletions(-) (limited to 'sound/pci/hda/hda_local.h') diff --git a/sound/pci/hda/hda_codec.c b/sound/pci/hda/hda_codec.c index 7fd2abe1129d..1ed1d88e1834 100644 --- a/sound/pci/hda/hda_codec.c +++ b/sound/pci/hda/hda_codec.c @@ -946,7 +946,7 @@ int /*__devinit*/ snd_hda_codec_new(struct hda_bus *bus, unsigned int codec_addr mutex_init(&codec->control_mutex); init_hda_cache(&codec->amp_cache, sizeof(struct hda_amp_info)); init_hda_cache(&codec->cmd_cache, sizeof(struct hda_cache_head)); - snd_array_init(&codec->mixers, sizeof(struct snd_kcontrol *), 32); + snd_array_init(&codec->mixers, sizeof(struct hda_nid_item), 60); snd_array_init(&codec->init_pins, sizeof(struct hda_pincfg), 16); snd_array_init(&codec->driver_pins, sizeof(struct hda_pincfg), 16); if (codec->bus->modelname) { @@ -1517,18 +1517,20 @@ struct snd_kcontrol *snd_hda_find_mixer_ctl(struct hda_codec *codec, EXPORT_SYMBOL_HDA(snd_hda_find_mixer_ctl); /* Add a control element and assign to the codec */ -int snd_hda_ctl_add(struct hda_codec *codec, struct snd_kcontrol *kctl) +int snd_hda_ctl_add(struct hda_codec *codec, hda_nid_t nid, + struct snd_kcontrol *kctl) { int err; - struct snd_kcontrol **knewp; + struct hda_nid_item *item; err = snd_ctl_add(codec->bus->card, kctl); if (err < 0) return err; - knewp = snd_array_new(&codec->mixers); - if (!knewp) + item = snd_array_new(&codec->mixers); + if (!item) return -ENOMEM; - *knewp = kctl; + item->kctl = kctl; + item->nid = nid; return 0; } EXPORT_SYMBOL_HDA(snd_hda_ctl_add); @@ -1537,9 +1539,9 @@ EXPORT_SYMBOL_HDA(snd_hda_ctl_add); void snd_hda_ctls_clear(struct hda_codec *codec) { int i; - struct snd_kcontrol **kctls = codec->mixers.list; + struct hda_nid_item *items = codec->mixers.list; for (i = 0; i < codec->mixers.used; i++) - snd_ctl_remove(codec->bus->card, kctls[i]); + snd_ctl_remove(codec->bus->card, items[i].kctl); snd_array_free(&codec->mixers); } @@ -1645,7 +1647,7 @@ int snd_hda_add_vmaster(struct hda_codec *codec, char *name, kctl = snd_ctl_make_virtual_master(name, tlv); if (!kctl) return -ENOMEM; - err = snd_hda_ctl_add(codec, kctl); + err = snd_hda_ctl_add(codec, 0, kctl); if (err < 0) return err; @@ -2139,7 +2141,7 @@ int snd_hda_create_spdif_out_ctls(struct hda_codec *codec, hda_nid_t nid) return -ENOMEM; kctl->id.index = idx; kctl->private_value = nid; - err = snd_hda_ctl_add(codec, kctl); + err = snd_hda_ctl_add(codec, nid, kctl); if (err < 0) return err; } @@ -2184,8 +2186,8 @@ int snd_hda_create_spdif_share_sw(struct hda_codec *codec, if (!mout->dig_out_nid) return 0; /* ATTENTION: here mout is passed as private_data, instead of codec */ - return snd_hda_ctl_add(codec, - snd_ctl_new1(&spdif_share_sw, mout)); + return snd_hda_ctl_add(codec, mout->dig_out_nid, + snd_ctl_new1(&spdif_share_sw, mout)); } EXPORT_SYMBOL_HDA(snd_hda_create_spdif_share_sw); @@ -2289,7 +2291,7 @@ int snd_hda_create_spdif_in_ctls(struct hda_codec *codec, hda_nid_t nid) if (!kctl) return -ENOMEM; kctl->private_value = nid; - err = snd_hda_ctl_add(codec, kctl); + err = snd_hda_ctl_add(codec, nid, kctl); if (err < 0) return err; } @@ -3165,7 +3167,7 @@ int snd_hda_add_new_ctls(struct hda_codec *codec, struct snd_kcontrol_new *knew) kctl = snd_ctl_new1(knew, codec); if (!kctl) return -ENOMEM; - err = snd_hda_ctl_add(codec, kctl); + err = snd_hda_ctl_add(codec, 0, kctl); if (err < 0) { if (!codec->addr) return err; @@ -3173,7 +3175,7 @@ int snd_hda_add_new_ctls(struct hda_codec *codec, struct snd_kcontrol_new *knew) if (!kctl) return -ENOMEM; kctl->id.device = codec->addr; - err = snd_hda_ctl_add(codec, kctl); + err = snd_hda_ctl_add(codec, 0, kctl); if (err < 0) return err; } diff --git a/sound/pci/hda/hda_generic.c b/sound/pci/hda/hda_generic.c index b36f6c5a92df..092c6a7c2ff3 100644 --- a/sound/pci/hda/hda_generic.c +++ b/sound/pci/hda/hda_generic.c @@ -727,7 +727,8 @@ static int create_mixer(struct hda_codec *codec, struct hda_gnode *node, if (is_loopback) add_input_loopback(codec, node->nid, HDA_INPUT, index); snd_printdd("[%s] NID=0x%x, DIR=IN, IDX=0x%x\n", name, node->nid, index); - err = snd_hda_ctl_add(codec, snd_ctl_new1(&knew, codec)); + err = snd_hda_ctl_add(codec, node->nid, + snd_ctl_new1(&knew, codec)); if (err < 0) return err; created = 1; @@ -737,7 +738,8 @@ static int create_mixer(struct hda_codec *codec, struct hda_gnode *node, if (is_loopback) add_input_loopback(codec, node->nid, HDA_OUTPUT, 0); snd_printdd("[%s] NID=0x%x, DIR=OUT\n", name, node->nid); - err = snd_hda_ctl_add(codec, snd_ctl_new1(&knew, codec)); + err = snd_hda_ctl_add(codec, node->nid, + snd_ctl_new1(&knew, codec)); if (err < 0) return err; created = 1; @@ -751,7 +753,8 @@ static int create_mixer(struct hda_codec *codec, struct hda_gnode *node, (node->amp_in_caps & AC_AMPCAP_NUM_STEPS)) { knew = (struct snd_kcontrol_new)HDA_CODEC_VOLUME(name, node->nid, index, HDA_INPUT); snd_printdd("[%s] NID=0x%x, DIR=IN, IDX=0x%x\n", name, node->nid, index); - err = snd_hda_ctl_add(codec, snd_ctl_new1(&knew, codec)); + err = snd_hda_ctl_add(codec, node->nid, + snd_ctl_new1(&knew, codec)); if (err < 0) return err; created = 1; @@ -759,7 +762,8 @@ static int create_mixer(struct hda_codec *codec, struct hda_gnode *node, (node->amp_out_caps & AC_AMPCAP_NUM_STEPS)) { knew = (struct snd_kcontrol_new)HDA_CODEC_VOLUME(name, node->nid, 0, HDA_OUTPUT); snd_printdd("[%s] NID=0x%x, DIR=OUT\n", name, node->nid); - err = snd_hda_ctl_add(codec, snd_ctl_new1(&knew, codec)); + err = snd_hda_ctl_add(codec, node->nid, + snd_ctl_new1(&knew, codec)); if (err < 0) return err; created = 1; @@ -857,7 +861,7 @@ static int build_input_controls(struct hda_codec *codec) } /* create input MUX if multiple sources are available */ - err = snd_hda_ctl_add(codec, snd_ctl_new1(&cap_sel, codec)); + err = snd_hda_ctl_add(codec, 0, snd_ctl_new1(&cap_sel, codec)); if (err < 0) return err; @@ -875,7 +879,8 @@ static int build_input_controls(struct hda_codec *codec) HDA_CODEC_VOLUME(name, adc_node->nid, spec->input_mux.items[i].index, HDA_INPUT); - err = snd_hda_ctl_add(codec, snd_ctl_new1(&knew, codec)); + err = snd_hda_ctl_add(codec, adc_node->nid, + snd_ctl_new1(&knew, codec)); if (err < 0) return err; } diff --git a/sound/pci/hda/hda_local.h b/sound/pci/hda/hda_local.h index 3001794ad291..e6a0918f70d3 100644 --- a/sound/pci/hda/hda_local.h +++ b/sound/pci/hda/hda_local.h @@ -440,7 +440,13 @@ int snd_hda_override_amp_caps(struct hda_codec *codec, hda_nid_t nid, int dir, unsigned int caps); u32 snd_hda_query_pin_caps(struct hda_codec *codec, hda_nid_t nid); -int snd_hda_ctl_add(struct hda_codec *codec, struct snd_kcontrol *kctl); +struct hda_nid_item { + struct snd_kcontrol *kctl; + hda_nid_t nid; +}; + +int snd_hda_ctl_add(struct hda_codec *codec, hda_nid_t nid, + struct snd_kcontrol *kctl); void snd_hda_ctls_clear(struct hda_codec *codec); /* @@ -514,7 +520,8 @@ int snd_hda_check_amp_list_power(struct hda_codec *codec, * AMP control callbacks */ /* retrieve parameters from private_value */ -#define get_amp_nid(kc) ((kc)->private_value & 0xffff) +#define get_amp_nid_(pv) ((pv) & 0xffff) +#define get_amp_nid(kc) get_amp_nid_((kc)->private_value) #define get_amp_channels(kc) (((kc)->private_value >> 16) & 0x3) #define get_amp_direction(kc) (((kc)->private_value >> 18) & 0x1) #define get_amp_index(kc) (((kc)->private_value >> 19) & 0xf) diff --git a/sound/pci/hda/hda_proc.c b/sound/pci/hda/hda_proc.c index f5b783ce450d..f465cff28041 100644 --- a/sound/pci/hda/hda_proc.c +++ b/sound/pci/hda/hda_proc.c @@ -46,6 +46,41 @@ static const char *get_wid_type_name(unsigned int wid_value) return "UNKNOWN Widget"; } +static void print_nid_mixers(struct snd_info_buffer *buffer, + struct hda_codec *codec, hda_nid_t nid) +{ + int i; + struct hda_nid_item *items = codec->mixers.list; + struct snd_kcontrol *kctl; + for (i = 0; i < codec->mixers.used; i++) { + if (items[i].nid == nid) { + kctl = items[i].kctl; + snd_iprintf(buffer, + " Control: name=\"%s\", index=%i, device=%i\n", + kctl->id.name, kctl->id.index, kctl->id.device); + } + } +} + +static void print_nid_pcms(struct snd_info_buffer *buffer, + struct hda_codec *codec, hda_nid_t nid) +{ + int pcm, type; + struct hda_pcm *cpcm; + for (pcm = 0; pcm < codec->num_pcms; pcm++) { + cpcm = &codec->pcm_info[pcm]; + for (type = 0; type < 2; type++) { + if (cpcm->stream[type].nid != nid || cpcm->pcm == NULL) + continue; + snd_iprintf(buffer, " Device: name=\"%s\", " + "type=\"%s\", device=%i\n", + cpcm->name, + snd_hda_pcm_type_name[cpcm->pcm_type], + cpcm->pcm->device); + } + } +} + static void print_amp_caps(struct snd_info_buffer *buffer, struct hda_codec *codec, hda_nid_t nid, int dir) { @@ -309,21 +344,7 @@ static void print_audio_io(struct snd_info_buffer *buffer, struct hda_codec *codec, hda_nid_t nid, unsigned int wid_type) { - int pcm, conv; - for (pcm = 0; pcm < codec->num_pcms; pcm++) { - int type; - struct hda_pcm *cpcm = &codec->pcm_info[pcm]; - for (type = 0; type < 2; type++) { - if (cpcm->stream[type].nid != nid || cpcm->pcm == NULL) - continue; - snd_iprintf(buffer, " Device: name=\"%s\", " - "type=\"%s\", device=%i\n", - cpcm->name, - snd_hda_pcm_type_name[cpcm->pcm_type], - cpcm->pcm->device); - } - } - conv = snd_hda_codec_read(codec, nid, 0, AC_VERB_GET_CONV, 0); + int conv = snd_hda_codec_read(codec, nid, 0, AC_VERB_GET_CONV, 0); snd_iprintf(buffer, " Converter: stream=%d, channel=%d\n", (conv & AC_CONV_STREAM) >> AC_CONV_STREAM_SHIFT, @@ -471,6 +492,7 @@ static void print_gpio(struct snd_info_buffer *buffer, (data & (1<private_value = spec->beep_amp; - err = snd_hda_ctl_add(codec, kctl); + err = snd_hda_ctl_add(codec, + get_amp_nid_(spec->beep_amp), + kctl); if (err < 0) return err; } diff --git a/sound/pci/hda/patch_ca0110.c b/sound/pci/hda/patch_ca0110.c index d08353d3bb7f..af478019088e 100644 --- a/sound/pci/hda/patch_ca0110.c +++ b/sound/pci/hda/patch_ca0110.c @@ -144,7 +144,7 @@ static int _add_switch(struct hda_codec *codec, hda_nid_t nid, const char *pfx, struct snd_kcontrol_new knew = HDA_CODEC_MUTE_MONO(namestr, nid, chan, 0, type); sprintf(namestr, "%s %s Switch", pfx, dirstr[dir]); - return snd_hda_ctl_add(codec, snd_ctl_new1(&knew, codec)); + return snd_hda_ctl_add(codec, nid, snd_ctl_new1(&knew, codec)); } static int _add_volume(struct hda_codec *codec, hda_nid_t nid, const char *pfx, @@ -155,7 +155,7 @@ static int _add_volume(struct hda_codec *codec, hda_nid_t nid, const char *pfx, struct snd_kcontrol_new knew = HDA_CODEC_VOLUME_MONO(namestr, nid, chan, 0, type); sprintf(namestr, "%s %s Volume", pfx, dirstr[dir]); - return snd_hda_ctl_add(codec, snd_ctl_new1(&knew, codec)); + return snd_hda_ctl_add(codec, nid, snd_ctl_new1(&knew, codec)); } #define add_out_switch(codec, nid, pfx) _add_switch(codec, nid, pfx, 3, 0) diff --git a/sound/pci/hda/patch_cirrus.c b/sound/pci/hda/patch_cirrus.c index 8ba306856d38..9ac09e4568b3 100644 --- a/sound/pci/hda/patch_cirrus.c +++ b/sound/pci/hda/patch_cirrus.c @@ -500,7 +500,7 @@ static int add_mute(struct hda_codec *codec, const char *name, int index, knew.private_value = pval; snprintf(tmp, sizeof(tmp), "%s %s Switch", name, dir_sfx[dir]); *kctlp = snd_ctl_new1(&knew, codec); - return snd_hda_ctl_add(codec, *kctlp); + return snd_hda_ctl_add(codec, get_amp_nid_(pval), *kctlp); } static int add_volume(struct hda_codec *codec, const char *name, @@ -513,7 +513,7 @@ static int add_volume(struct hda_codec *codec, const char *name, knew.private_value = pval; snprintf(tmp, sizeof(tmp), "%s %s Volume", name, dir_sfx[dir]); *kctlp = snd_ctl_new1(&knew, codec); - return snd_hda_ctl_add(codec, *kctlp); + return snd_hda_ctl_add(codec, get_amp_nid_(pval), *kctlp); } static void fix_volume_caps(struct hda_codec *codec, hda_nid_t dac) @@ -536,14 +536,14 @@ static int add_vmaster(struct hda_codec *codec, hda_nid_t dac) spec->vmaster_sw = snd_ctl_make_virtual_master("Master Playback Switch", NULL); - err = snd_hda_ctl_add(codec, spec->vmaster_sw); + err = snd_hda_ctl_add(codec, dac, spec->vmaster_sw); if (err < 0) return err; snd_hda_set_vmaster_tlv(codec, dac, HDA_OUTPUT, tlv); spec->vmaster_vol = snd_ctl_make_virtual_master("Master Playback Volume", tlv); - err = snd_hda_ctl_add(codec, spec->vmaster_vol); + err = snd_hda_ctl_add(codec, dac, spec->vmaster_vol); if (err < 0) return err; return 0; @@ -756,13 +756,13 @@ static int build_input(struct hda_codec *codec) if (!kctl) return -ENOMEM; kctl->private_value = (long)spec->capture_bind[i]; - err = snd_hda_ctl_add(codec, kctl); + err = snd_hda_ctl_add(codec, 0, kctl); if (err < 0) return err; } if (spec->num_inputs > 1 && !spec->mic_detect) { - err = snd_hda_ctl_add(codec, + err = snd_hda_ctl_add(codec, 0, snd_ctl_new1(&cs_capture_source, codec)); if (err < 0) return err; diff --git a/sound/pci/hda/patch_realtek.c b/sound/pci/hda/patch_realtek.c index 8c04e0e0f655..fff9de245646 100644 --- a/sound/pci/hda/patch_realtek.c +++ b/sound/pci/hda/patch_realtek.c @@ -2461,7 +2461,8 @@ static int alc_build_controls(struct hda_codec *codec) if (!kctl) return -ENOMEM; kctl->private_value = spec->beep_amp; - err = snd_hda_ctl_add(codec, kctl); + err = snd_hda_ctl_add(codec, + get_amp_nid_(spec->beep_amp), kctl); if (err < 0) return err; } diff --git a/sound/pci/hda/patch_sigmatel.c b/sound/pci/hda/patch_sigmatel.c index 87ba239ff1c9..a3872b90d6ed 100644 --- a/sound/pci/hda/patch_sigmatel.c +++ b/sound/pci/hda/patch_sigmatel.c @@ -1085,7 +1085,7 @@ static int stac92xx_build_controls(struct hda_codec *codec) if (!spec->auto_mic && spec->num_dmuxes > 0 && snd_hda_get_bool_hint(codec, "separate_dmux") == 1) { stac_dmux_mixer.count = spec->num_dmuxes; - err = snd_hda_ctl_add(codec, + err = snd_hda_ctl_add(codec, 0, snd_ctl_new1(&stac_dmux_mixer, codec)); if (err < 0) return err; @@ -1101,7 +1101,7 @@ static int stac92xx_build_controls(struct hda_codec *codec) spec->spdif_mute = 1; } stac_smux_mixer.count = spec->num_smuxes; - err = snd_hda_ctl_add(codec, + err = snd_hda_ctl_add(codec, 0, snd_ctl_new1(&stac_smux_mixer, codec)); if (err < 0) return err; -- cgit v1.2.3-59-g8ed1b From 4d02d1b638af580ae3d69367248539a8b3893064 Mon Sep 17 00:00:00 2001 From: Jaroslav Kysela Date: Thu, 12 Nov 2009 10:15:48 +0100 Subject: ALSA: hda - proc - add support for dynamic controls to mixer<->NID mapping This patch adds support for dynamically created controls to proc codec file (Control: lines). Signed-off-by: Jaroslav Kysela Signed-off-by: Takashi Iwai --- sound/pci/hda/hda_codec.c | 7 ++++++- sound/pci/hda/hda_local.h | 3 +++ sound/pci/hda/patch_analog.c | 2 ++ sound/pci/hda/patch_realtek.c | 2 ++ sound/pci/hda/patch_sigmatel.c | 10 +++++++--- sound/pci/hda/patch_via.c | 2 ++ 6 files changed, 22 insertions(+), 4 deletions(-) (limited to 'sound/pci/hda/hda_local.h') diff --git a/sound/pci/hda/hda_codec.c b/sound/pci/hda/hda_codec.c index 1ed1d88e1834..d71e651046eb 100644 --- a/sound/pci/hda/hda_codec.c +++ b/sound/pci/hda/hda_codec.c @@ -1523,6 +1523,11 @@ int snd_hda_ctl_add(struct hda_codec *codec, hda_nid_t nid, int err; struct hda_nid_item *item; + if (kctl->id.subdevice & (1<<31)) { + if (nid == 0) + nid = kctl->id.subdevice & 0xffff; + kctl->id.subdevice = 0; + } err = snd_ctl_add(codec->bus->card, kctl); if (err < 0) return err; @@ -3160,7 +3165,7 @@ EXPORT_SYMBOL_HDA(snd_hda_check_board_codec_sid_config); */ int snd_hda_add_new_ctls(struct hda_codec *codec, struct snd_kcontrol_new *knew) { - int err; + int err; for (; knew->name; knew++) { struct snd_kcontrol *kctl; diff --git a/sound/pci/hda/hda_local.h b/sound/pci/hda/hda_local.h index e6a0918f70d3..3bfcf42ff6cf 100644 --- a/sound/pci/hda/hda_local.h +++ b/sound/pci/hda/hda_local.h @@ -33,6 +33,7 @@ /* mono volume with index (index=0,1,...) (channel=1,2) */ #define HDA_CODEC_VOLUME_MONO_IDX(xname, xcidx, nid, channel, xindex, direction) \ { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = xname, .index = xcidx, \ + .subdevice = (1<<31)|(nid), \ .access = SNDRV_CTL_ELEM_ACCESS_READWRITE | \ SNDRV_CTL_ELEM_ACCESS_TLV_READ | \ SNDRV_CTL_ELEM_ACCESS_TLV_CALLBACK, \ @@ -53,6 +54,7 @@ /* mono mute switch with index (index=0,1,...) (channel=1,2) */ #define HDA_CODEC_MUTE_MONO_IDX(xname, xcidx, nid, channel, xindex, direction) \ { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = xname, .index = xcidx, \ + .subdevice = (1<<31)|(nid), \ .info = snd_hda_mixer_amp_switch_info, \ .get = snd_hda_mixer_amp_switch_get, \ .put = snd_hda_mixer_amp_switch_put, \ @@ -69,6 +71,7 @@ /* special beep mono mute switch with index (index=0,1,...) (channel=1,2) */ #define HDA_CODEC_MUTE_BEEP_MONO_IDX(xname, xcidx, nid, channel, xindex, direction) \ { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = xname, .index = xcidx, \ + .subdevice = (1<<31)|(nid), \ .info = snd_hda_mixer_amp_switch_info, \ .get = snd_hda_mixer_amp_switch_get, \ .put = snd_hda_mixer_amp_switch_put_beep, \ diff --git a/sound/pci/hda/patch_analog.c b/sound/pci/hda/patch_analog.c index ef3383912b6e..2d345606265b 100644 --- a/sound/pci/hda/patch_analog.c +++ b/sound/pci/hda/patch_analog.c @@ -2571,6 +2571,8 @@ static int add_control(struct ad198x_spec *spec, int type, const char *name, knew->name = kstrdup(name, GFP_KERNEL); if (! knew->name) return -ENOMEM; + if (get_amp_nid_(val)) + knew->subdevice = (1<<31)|get_amp_nid_(val); knew->private_value = val; return 0; } diff --git a/sound/pci/hda/patch_realtek.c b/sound/pci/hda/patch_realtek.c index fff9de245646..c0a98e724a25 100644 --- a/sound/pci/hda/patch_realtek.c +++ b/sound/pci/hda/patch_realtek.c @@ -4323,6 +4323,8 @@ static int add_control(struct alc_spec *spec, int type, const char *name, knew->name = kstrdup(name, GFP_KERNEL); if (!knew->name) return -ENOMEM; + if (get_amp_nid_(val)) + knew->subdevice = (1<<31)|get_amp_nid_(val); knew->private_value = val; return 0; } diff --git a/sound/pci/hda/patch_sigmatel.c b/sound/pci/hda/patch_sigmatel.c index a3872b90d6ed..d2ddb959c290 100644 --- a/sound/pci/hda/patch_sigmatel.c +++ b/sound/pci/hda/patch_sigmatel.c @@ -2671,7 +2671,8 @@ static struct snd_kcontrol_new stac92xx_control_templates[] = { static struct snd_kcontrol_new * stac_control_new(struct sigmatel_spec *spec, struct snd_kcontrol_new *ktemp, - const char *name) + const char *name, + hda_nid_t nid) { struct snd_kcontrol_new *knew; @@ -2687,6 +2688,8 @@ stac_control_new(struct sigmatel_spec *spec, spec->kctls.alloced--; return NULL; } + if (nid) + knew->subdevice = (1<<31)|nid; return knew; } @@ -2695,7 +2698,8 @@ static int stac92xx_add_control_temp(struct sigmatel_spec *spec, int idx, const char *name, unsigned long val) { - struct snd_kcontrol_new *knew = stac_control_new(spec, ktemp, name); + struct snd_kcontrol_new *knew = stac_control_new(spec, ktemp, name, + get_amp_nid_(val)); if (!knew) return -ENOMEM; knew->index = idx; @@ -2766,7 +2770,7 @@ static int stac92xx_add_input_source(struct sigmatel_spec *spec) if (!spec->num_adcs || imux->num_items <= 1) return 0; /* no need for input source control */ knew = stac_control_new(spec, &stac_input_src_temp, - stac_input_src_temp.name); + stac_input_src_temp.name, 0); if (!knew) return -ENOMEM; knew->count = spec->num_adcs; diff --git a/sound/pci/hda/patch_via.c b/sound/pci/hda/patch_via.c index 5a856009c916..14219d898b2e 100644 --- a/sound/pci/hda/patch_via.c +++ b/sound/pci/hda/patch_via.c @@ -442,6 +442,8 @@ static int via_add_control(struct via_spec *spec, int type, const char *name, knew->name = kstrdup(name, GFP_KERNEL); if (!knew->name) return -ENOMEM; + if (get_amp_nid_(val)) + knew->subdevice = (1<<31)|get_amp_nid_(val); knew->private_value = val; return 0; } -- cgit v1.2.3-59-g8ed1b From 9c96fa599fe4f0ccc6e3e606df6652335afe28e8 Mon Sep 17 00:00:00 2001 From: Takashi Iwai Date: Mon, 16 Nov 2009 11:25:33 +0100 Subject: ALSA: hda - Get rid of magic digits for subdev hack Define a proper const for a magic 31bit flag for subdev / NID setup with a brief comment. Signed-off-by: Takashi Iwai --- sound/pci/hda/hda_codec.c | 2 +- sound/pci/hda/hda_local.h | 15 ++++++++++++--- sound/pci/hda/patch_analog.c | 2 +- sound/pci/hda/patch_realtek.c | 2 +- sound/pci/hda/patch_sigmatel.c | 2 +- sound/pci/hda/patch_via.c | 2 +- 6 files changed, 17 insertions(+), 8 deletions(-) (limited to 'sound/pci/hda/hda_local.h') diff --git a/sound/pci/hda/hda_codec.c b/sound/pci/hda/hda_codec.c index d71e651046eb..5e21b35207ab 100644 --- a/sound/pci/hda/hda_codec.c +++ b/sound/pci/hda/hda_codec.c @@ -1523,7 +1523,7 @@ int snd_hda_ctl_add(struct hda_codec *codec, hda_nid_t nid, int err; struct hda_nid_item *item; - if (kctl->id.subdevice & (1<<31)) { + if (kctl->id.subdevice & HDA_SUBDEV_NID_FLAG) { if (nid == 0) nid = kctl->id.subdevice & 0xffff; kctl->id.subdevice = 0; diff --git a/sound/pci/hda/hda_local.h b/sound/pci/hda/hda_local.h index 3bfcf42ff6cf..4e77f4747291 100644 --- a/sound/pci/hda/hda_local.h +++ b/sound/pci/hda/hda_local.h @@ -23,6 +23,15 @@ #ifndef __SOUND_HDA_LOCAL_H #define __SOUND_HDA_LOCAL_H +/* We abuse kcontrol_new.subdev field to pass the NID corresponding to + * the given new control. If id.subdev has a bit flag HDA_SUBDEV_NID_FLAG, + * snd_hda_ctl_add() takes the lower-bit subdev value as a valid NID. + * + * Note that the subdevice field is cleared again before the real registration + * in snd_hda_ctl_add(), so that this value won't appear in the outside. + */ +#define HDA_SUBDEV_NID_FLAG (1U << 31) + /* * for mixer controls */ @@ -33,7 +42,7 @@ /* mono volume with index (index=0,1,...) (channel=1,2) */ #define HDA_CODEC_VOLUME_MONO_IDX(xname, xcidx, nid, channel, xindex, direction) \ { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = xname, .index = xcidx, \ - .subdevice = (1<<31)|(nid), \ + .subdevice = HDA_SUBDEV_NID_FLAG | (nid), \ .access = SNDRV_CTL_ELEM_ACCESS_READWRITE | \ SNDRV_CTL_ELEM_ACCESS_TLV_READ | \ SNDRV_CTL_ELEM_ACCESS_TLV_CALLBACK, \ @@ -54,7 +63,7 @@ /* mono mute switch with index (index=0,1,...) (channel=1,2) */ #define HDA_CODEC_MUTE_MONO_IDX(xname, xcidx, nid, channel, xindex, direction) \ { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = xname, .index = xcidx, \ - .subdevice = (1<<31)|(nid), \ + .subdevice = HDA_SUBDEV_NID_FLAG | (nid), \ .info = snd_hda_mixer_amp_switch_info, \ .get = snd_hda_mixer_amp_switch_get, \ .put = snd_hda_mixer_amp_switch_put, \ @@ -71,7 +80,7 @@ /* special beep mono mute switch with index (index=0,1,...) (channel=1,2) */ #define HDA_CODEC_MUTE_BEEP_MONO_IDX(xname, xcidx, nid, channel, xindex, direction) \ { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = xname, .index = xcidx, \ - .subdevice = (1<<31)|(nid), \ + .subdevice = HDA_SUBDEV_NID_FLAG | (nid), \ .info = snd_hda_mixer_amp_switch_info, \ .get = snd_hda_mixer_amp_switch_get, \ .put = snd_hda_mixer_amp_switch_put_beep, \ diff --git a/sound/pci/hda/patch_analog.c b/sound/pci/hda/patch_analog.c index 2d345606265b..ceb0c603da04 100644 --- a/sound/pci/hda/patch_analog.c +++ b/sound/pci/hda/patch_analog.c @@ -2572,7 +2572,7 @@ static int add_control(struct ad198x_spec *spec, int type, const char *name, if (! knew->name) return -ENOMEM; if (get_amp_nid_(val)) - knew->subdevice = (1<<31)|get_amp_nid_(val); + knew->subdevice = HDA_SUBDEV_NID_FLAG | get_amp_nid_(val); knew->private_value = val; return 0; } diff --git a/sound/pci/hda/patch_realtek.c b/sound/pci/hda/patch_realtek.c index c0a98e724a25..eee3143eef75 100644 --- a/sound/pci/hda/patch_realtek.c +++ b/sound/pci/hda/patch_realtek.c @@ -4324,7 +4324,7 @@ static int add_control(struct alc_spec *spec, int type, const char *name, if (!knew->name) return -ENOMEM; if (get_amp_nid_(val)) - knew->subdevice = (1<<31)|get_amp_nid_(val); + knew->subdevice = HDA_SUBDEV_NID_FLAG | get_amp_nid_(val); knew->private_value = val; return 0; } diff --git a/sound/pci/hda/patch_sigmatel.c b/sound/pci/hda/patch_sigmatel.c index d2ddb959c290..7f76a97954f9 100644 --- a/sound/pci/hda/patch_sigmatel.c +++ b/sound/pci/hda/patch_sigmatel.c @@ -2689,7 +2689,7 @@ stac_control_new(struct sigmatel_spec *spec, return NULL; } if (nid) - knew->subdevice = (1<<31)|nid; + knew->subdevice = HDA_SUBDEV_NID_FLAG | nid; return knew; } diff --git a/sound/pci/hda/patch_via.c b/sound/pci/hda/patch_via.c index 14219d898b2e..0c621d74b165 100644 --- a/sound/pci/hda/patch_via.c +++ b/sound/pci/hda/patch_via.c @@ -443,7 +443,7 @@ static int via_add_control(struct via_spec *spec, int type, const char *name, if (!knew->name) return -ENOMEM; if (get_amp_nid_(val)) - knew->subdevice = (1<<31)|get_amp_nid_(val); + knew->subdevice = HDA_SUBDEV_NID_FLAG | get_amp_nid_(val); knew->private_value = val; return 0; } -- cgit v1.2.3-59-g8ed1b From 85dd662ff4d2967084acfc761a33717383297e42 Mon Sep 17 00:00:00 2001 From: Jaroslav Kysela Date: Wed, 11 Nov 2009 13:49:07 +0100 Subject: ALSA: hda - move snd_hda_pcm_type_name from hda_codec.h to hda_local.h The snd_hda_pcm_type_name array is local only. Signed-off-by: Jaroslav Kysela Signed-off-by: Takashi Iwai --- sound/pci/hda/hda_codec.h | 1 - sound/pci/hda/hda_local.h | 2 ++ 2 files changed, 2 insertions(+), 1 deletion(-) (limited to 'sound/pci/hda/hda_local.h') diff --git a/sound/pci/hda/hda_codec.h b/sound/pci/hda/hda_codec.h index 51920563bc7f..be6c5f443cd9 100644 --- a/sound/pci/hda/hda_codec.h +++ b/sound/pci/hda/hda_codec.h @@ -898,7 +898,6 @@ int snd_hda_codec_build_controls(struct hda_codec *codec); /* * PCM */ -extern const char *snd_hda_pcm_type_name[]; int snd_hda_build_pcms(struct hda_bus *bus); int snd_hda_codec_build_pcms(struct hda_codec *codec); void snd_hda_codec_setup_stream(struct hda_codec *codec, hda_nid_t nid, diff --git a/sound/pci/hda/hda_local.h b/sound/pci/hda/hda_local.h index 4e77f4747291..7c049839ea26 100644 --- a/sound/pci/hda/hda_local.h +++ b/sound/pci/hda/hda_local.h @@ -92,6 +92,8 @@ #define HDA_CODEC_MUTE_BEEP(xname, nid, xindex, direction) \ HDA_CODEC_MUTE_BEEP_MONO(xname, nid, 3, xindex, direction) +extern const char *snd_hda_pcm_type_name[]; + int snd_hda_mixer_amp_volume_info(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_info *uinfo); int snd_hda_mixer_amp_volume_get(struct snd_kcontrol *kcontrol, -- cgit v1.2.3-59-g8ed1b From 67d634c07afd8f70973d925463e775fdb89ad536 Mon Sep 17 00:00:00 2001 From: Takashi Iwai Date: Mon, 16 Nov 2009 15:35:59 +0100 Subject: ALSA: hda - Fix build errors with CONFIG_SND_HDA_INPUT_BEEP=n Disable beep-related codes when CONFIG_SND_HDA_INPUT_BEEP isn't set. Signed-off-by: Takashi Iwai --- sound/pci/hda/hda_codec.c | 2 ++ sound/pci/hda/hda_local.h | 8 ++++++++ sound/pci/hda/patch_analog.c | 6 ++++++ sound/pci/hda/patch_realtek.c | 8 ++++++++ 4 files changed, 24 insertions(+) (limited to 'sound/pci/hda/hda_local.h') diff --git a/sound/pci/hda/hda_codec.c b/sound/pci/hda/hda_codec.c index e344235da491..2be61b31fb3c 100644 --- a/sound/pci/hda/hda_codec.c +++ b/sound/pci/hda/hda_codec.c @@ -1959,6 +1959,7 @@ int snd_hda_mixer_amp_switch_put(struct snd_kcontrol *kcontrol, } EXPORT_SYMBOL_HDA(snd_hda_mixer_amp_switch_put); +#ifdef CONFIG_SND_HDA_INPUT_BEEP /** * snd_hda_mixer_amp_switch_put_beep - Put callback for a beep AMP switch * @@ -1975,6 +1976,7 @@ int snd_hda_mixer_amp_switch_put_beep(struct snd_kcontrol *kcontrol, return snd_hda_mixer_amp_switch_put(kcontrol, ucontrol); } EXPORT_SYMBOL_HDA(snd_hda_mixer_amp_switch_put_beep); +#endif /* CONFIG_SND_HDA_INPUT_BEEP */ /* * bound volume controls diff --git a/sound/pci/hda/hda_local.h b/sound/pci/hda/hda_local.h index 7c049839ea26..d4a3d0942c00 100644 --- a/sound/pci/hda/hda_local.h +++ b/sound/pci/hda/hda_local.h @@ -77,6 +77,7 @@ /* stereo mute switch */ #define HDA_CODEC_MUTE(xname, nid, xindex, direction) \ HDA_CODEC_MUTE_MONO(xname, nid, 3, xindex, direction) +#ifdef CONFIG_SND_HDA_INPUT_BEEP /* special beep mono mute switch with index (index=0,1,...) (channel=1,2) */ #define HDA_CODEC_MUTE_BEEP_MONO_IDX(xname, xcidx, nid, channel, xindex, direction) \ { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = xname, .index = xcidx, \ @@ -85,6 +86,11 @@ .get = snd_hda_mixer_amp_switch_get, \ .put = snd_hda_mixer_amp_switch_put_beep, \ .private_value = HDA_COMPOSE_AMP_VAL(nid, channel, xindex, direction) } +#else +/* no digital beep - just the standard one */ +#define HDA_CODEC_MUTE_BEEP_MONO_IDX(xname, xcidx, nid, ch, xidx, dir) \ + HDA_CODEC_MUTE_MONO_IDX(xname, xcidx, nid, ch, xidx, dir) +#endif /* CONFIG_SND_HDA_INPUT_BEEP */ /* special beep mono mute switch */ #define HDA_CODEC_MUTE_BEEP_MONO(xname, nid, channel, xindex, direction) \ HDA_CODEC_MUTE_BEEP_MONO_IDX(xname, 0, nid, channel, xindex, direction) @@ -108,8 +114,10 @@ int snd_hda_mixer_amp_switch_get(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol); int snd_hda_mixer_amp_switch_put(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol); +#ifdef CONFIG_SND_HDA_INPUT_BEEP int snd_hda_mixer_amp_switch_put_beep(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol); +#endif /* lowlevel accessor with caching; use carefully */ int snd_hda_codec_amp_read(struct hda_codec *codec, hda_nid_t nid, int ch, int direction, int index); diff --git a/sound/pci/hda/patch_analog.c b/sound/pci/hda/patch_analog.c index ceb0c603da04..8a1064bdf4c6 100644 --- a/sound/pci/hda/patch_analog.c +++ b/sound/pci/hda/patch_analog.c @@ -156,6 +156,7 @@ static const char *ad_slave_sws[] = { static void ad198x_free_kctls(struct hda_codec *codec); +#ifdef CONFIG_SND_HDA_INPUT_BEEP /* additional beep mixers; the actual parameters are overwritten at build */ static struct snd_kcontrol_new ad_beep_mixer[] = { HDA_CODEC_VOLUME("Beep Playback Volume", 0, 0, HDA_OUTPUT), @@ -165,6 +166,9 @@ static struct snd_kcontrol_new ad_beep_mixer[] = { #define set_beep_amp(spec, nid, idx, dir) \ ((spec)->beep_amp = HDA_COMPOSE_AMP_VAL(nid, 1, idx, dir)) /* mono */ +#else +#define set_beep_amp(spec, nid, idx, dir) /* NOP */ +#endif static int ad198x_build_controls(struct hda_codec *codec) { @@ -194,6 +198,7 @@ static int ad198x_build_controls(struct hda_codec *codec) } /* create beep controls if needed */ +#ifdef CONFIG_SND_HDA_INPUT_BEEP if (spec->beep_amp) { struct snd_kcontrol_new *knew; for (knew = ad_beep_mixer; knew->name; knew++) { @@ -209,6 +214,7 @@ static int ad198x_build_controls(struct hda_codec *codec) return err; } } +#endif /* if we have no master control, let's create it */ if (!snd_hda_find_mixer_ctl(codec, "Master Playback Volume")) { diff --git a/sound/pci/hda/patch_realtek.c b/sound/pci/hda/patch_realtek.c index eee3143eef75..ef7d21097eeb 100644 --- a/sound/pci/hda/patch_realtek.c +++ b/sound/pci/hda/patch_realtek.c @@ -2410,12 +2410,14 @@ static const char *alc_slave_sws[] = { static void alc_free_kctls(struct hda_codec *codec); +#ifdef CONFIG_SND_HDA_INPUT_BEEP /* additional beep mixers; the actual parameters are overwritten at build */ static struct snd_kcontrol_new alc_beep_mixer[] = { HDA_CODEC_VOLUME("Beep Playback Volume", 0, 0, HDA_INPUT), HDA_CODEC_MUTE_BEEP("Beep Playback Switch", 0, 0, HDA_INPUT), { } /* end */ }; +#endif static int alc_build_controls(struct hda_codec *codec) { @@ -2452,6 +2454,7 @@ static int alc_build_controls(struct hda_codec *codec) return err; } +#ifdef CONFIG_SND_HDA_INPUT_BEEP /* create beep controls if needed */ if (spec->beep_amp) { struct snd_kcontrol_new *knew; @@ -2467,6 +2470,7 @@ static int alc_build_controls(struct hda_codec *codec) return err; } } +#endif /* if we have no master control, let's create it */ if (!spec->no_analog && @@ -4780,8 +4784,12 @@ static void set_capture_mixer(struct hda_codec *codec) } } +#ifdef CONFIG_SND_HDA_INPUT_BEEP #define set_beep_amp(spec, nid, idx, dir) \ ((spec)->beep_amp = HDA_COMPOSE_AMP_VAL(nid, 3, idx, dir)) +#else +#define set_beep_amp(spec, nid, idx, dir) /* NOP */ +#endif /* * OK, here we have finally the patch for ALC880 -- cgit v1.2.3-59-g8ed1b From 23ccc2bd246a5bdb1ac03dc9040a0585c1890ef3 Mon Sep 17 00:00:00 2001 From: Wu Fengguang Date: Wed, 18 Nov 2009 12:38:01 +0800 Subject: ALSA: intelhdmi - export monitor-presence and ELD-valid status Signed-off-by: Wu Fengguang Signed-off-by: Takashi Iwai --- sound/pci/hda/hda_eld.c | 8 +++++++- sound/pci/hda/hda_local.h | 4 +++- sound/pci/hda/patch_intelhdmi.c | 8 +++----- 3 files changed, 13 insertions(+), 7 deletions(-) (limited to 'sound/pci/hda/hda_local.h') diff --git a/sound/pci/hda/hda_eld.c b/sound/pci/hda/hda_eld.c index 20fa6aee29c0..de50cfcf644e 100644 --- a/sound/pci/hda/hda_eld.c +++ b/sound/pci/hda/hda_eld.c @@ -477,6 +477,8 @@ static void hdmi_print_eld_info(struct snd_info_entry *entry, [4 ... 7] = "reserved" }; + snd_iprintf(buffer, "monitor_present\t\t%d\n", e->monitor_present); + snd_iprintf(buffer, "eld_valid\t\t%d\n", e->eld_valid); snd_iprintf(buffer, "monitor_name\t\t%s\n", e->monitor_name); snd_iprintf(buffer, "connection_type\t\t%s\n", eld_connection_type_names[e->conn_type]); @@ -518,7 +520,11 @@ static void hdmi_write_eld_info(struct snd_info_entry *entry, * monitor_name manufacture_id product_id * eld_version edid_version */ - if (!strcmp(name, "connection_type")) + if (!strcmp(name, "monitor_present")) + e->monitor_present = val; + else if (!strcmp(name, "eld_valid")) + e->eld_valid = val; + else if (!strcmp(name, "connection_type")) e->conn_type = val; else if (!strcmp(name, "port_id")) e->port_id = val; diff --git a/sound/pci/hda/hda_local.h b/sound/pci/hda/hda_local.h index d4a3d0942c00..070b74384d43 100644 --- a/sound/pci/hda/hda_local.h +++ b/sound/pci/hda/hda_local.h @@ -569,9 +569,11 @@ struct cea_sad { * ELD: EDID Like Data */ struct hdmi_eld { + bool monitor_present; + bool eld_valid; int eld_size; int baseline_len; - int eld_ver; /* (eld_ver == 0) indicates invalid ELD */ + int eld_ver; int cea_edid_ver; char monitor_name[ELD_MAX_MNL + 1]; int manufacture_id; diff --git a/sound/pci/hda/patch_intelhdmi.c b/sound/pci/hda/patch_intelhdmi.c index 82312c67f8dd..095c993f4b76 100644 --- a/sound/pci/hda/patch_intelhdmi.c +++ b/sound/pci/hda/patch_intelhdmi.c @@ -62,8 +62,6 @@ struct intel_hdmi_spec { /* * HDMI sink attached to each pin */ - bool sink_present[INTEL_HDMI_PINS]; - bool sink_eldv[INTEL_HDMI_PINS]; struct hdmi_eld sink_eld[INTEL_HDMI_PINS]; /* @@ -645,7 +643,7 @@ static void hdmi_setup_audio_infoframe(struct hda_codec *codec, hda_nid_t nid, for (i = 0; i < spec->num_pins; i++) { if (spec->pin_cvt[i] != nid) continue; - if (spec->sink_present[i] != true) + if (!spec->sink_eld[i].monitor_present) continue; pin_nid = spec->pin[i]; @@ -675,8 +673,8 @@ static void hdmi_intrinsic_event(struct hda_codec *codec, unsigned int res) if (index < 0) return; - spec->sink_present[index] = pind; - spec->sink_eldv[index] = eldv; + spec->sink_eld[index].monitor_present = pind; + spec->sink_eld[index].eld_valid = eldv; if (pind && eldv) { hdmi_parse_eld(codec, index); -- cgit v1.2.3-59-g8ed1b From 864f92be7e8d4a0ba11d912e3f03d1a92a031dee Mon Sep 17 00:00:00 2001 From: Wu Fengguang Date: Wed, 18 Nov 2009 12:38:02 +0800 Subject: ALSA: hda - introduce snd_hda_jack_detect() and snd_hda_pin_sense() This helps merge duplicate code. v2: add snd_hda_jack_detect() and comments recommended by Takashi. Signed-off-by: Wu Fengguang Signed-off-by: Takashi Iwai --- sound/pci/hda/hda_codec.c | 34 +++++++ sound/pci/hda/hda_eld.c | 7 +- sound/pci/hda/hda_local.h | 2 + sound/pci/hda/patch_cirrus.c | 19 +--- sound/pci/hda/patch_realtek.c | 206 ++++++++++-------------------------------- 5 files changed, 91 insertions(+), 177 deletions(-) (limited to 'sound/pci/hda/hda_local.h') diff --git a/sound/pci/hda/hda_codec.c b/sound/pci/hda/hda_codec.c index 2be61b31fb3c..9cfdb771928c 100644 --- a/sound/pci/hda/hda_codec.c +++ b/sound/pci/hda/hda_codec.c @@ -1317,6 +1317,40 @@ u32 snd_hda_query_pin_caps(struct hda_codec *codec, hda_nid_t nid) } EXPORT_SYMBOL_HDA(snd_hda_query_pin_caps); +/** + * snd_hda_pin_sense - execute pin sense measurement + * @codec: the CODEC to sense + * @nid: the pin NID to sense + * + * Execute necessary pin sense measurement and return its Presence Detect, + * Impedance, ELD Valid etc. status bits. + */ +u32 snd_hda_pin_sense(struct hda_codec *codec, hda_nid_t nid) +{ + u32 pincap = snd_hda_query_pin_caps(codec, nid); + + if (pincap & AC_PINCAP_TRIG_REQ) /* need trigger? */ + snd_hda_codec_read(codec, nid, 0, AC_VERB_SET_PIN_SENSE, 0); + + return snd_hda_codec_read(codec, nid, 0, + AC_VERB_GET_PIN_SENSE, 0); +} +EXPORT_SYMBOL_HDA(snd_hda_pin_sense); + +/** + * snd_hda_jack_detect - query pin Presence Detect status + * @codec: the CODEC to sense + * @nid: the pin NID to sense + * + * Query and return the pin's Presence Detect status. + */ +int snd_hda_jack_detect(struct hda_codec *codec, hda_nid_t nid) +{ + u32 sense = snd_hda_pin_sense(codec, nid); + return !!(sense & AC_PINSENSE_PRESENCE); +} +EXPORT_SYMBOL_HDA(snd_hda_jack_detect); + /* * read the current volume to info * if the cache exists, read the cache value. diff --git a/sound/pci/hda/hda_eld.c b/sound/pci/hda/hda_eld.c index de50cfcf644e..4228f2fe5956 100644 --- a/sound/pci/hda/hda_eld.c +++ b/sound/pci/hda/hda_eld.c @@ -309,17 +309,12 @@ out_fail: return -EINVAL; } -static int hdmi_present_sense(struct hda_codec *codec, hda_nid_t nid) -{ - return snd_hda_codec_read(codec, nid, 0, AC_VERB_GET_PIN_SENSE, 0); -} - static int hdmi_eld_valid(struct hda_codec *codec, hda_nid_t nid) { int eldv; int present; - present = hdmi_present_sense(codec, nid); + present = snd_hda_pin_sense(codec, nid); eldv = (present & AC_PINSENSE_ELDV); present = (present & AC_PINSENSE_PRESENCE); diff --git a/sound/pci/hda/hda_local.h b/sound/pci/hda/hda_local.h index 070b74384d43..5778ae882b83 100644 --- a/sound/pci/hda/hda_local.h +++ b/sound/pci/hda/hda_local.h @@ -461,6 +461,8 @@ u32 query_amp_caps(struct hda_codec *codec, hda_nid_t nid, int direction); int snd_hda_override_amp_caps(struct hda_codec *codec, hda_nid_t nid, int dir, unsigned int caps); u32 snd_hda_query_pin_caps(struct hda_codec *codec, hda_nid_t nid); +u32 snd_hda_pin_sense(struct hda_codec *codec, hda_nid_t nid); +int snd_hda_jack_detect(struct hda_codec *codec, hda_nid_t nid); struct hda_nid_item { struct snd_kcontrol *kctl; diff --git a/sound/pci/hda/patch_cirrus.c b/sound/pci/hda/patch_cirrus.c index 9ac09e4568b3..2439e84dcb21 100644 --- a/sound/pci/hda/patch_cirrus.c +++ b/sound/pci/hda/patch_cirrus.c @@ -807,7 +807,7 @@ static void cs_automute(struct hda_codec *codec) { struct cs_spec *spec = codec->spec; struct auto_pin_cfg *cfg = &spec->autocfg; - unsigned int caps, present, hp_present; + unsigned int caps, hp_present; hda_nid_t nid; int i; @@ -817,12 +817,7 @@ static void cs_automute(struct hda_codec *codec) caps = snd_hda_query_pin_caps(codec, nid); if (!(caps & AC_PINCAP_PRES_DETECT)) continue; - if (caps & AC_PINCAP_TRIG_REQ) - snd_hda_codec_read(codec, nid, 0, - AC_VERB_SET_PIN_SENSE, 0); - present = snd_hda_codec_read(codec, nid, 0, - AC_VERB_GET_PIN_SENSE, 0); - hp_present |= (present & AC_PINSENSE_PRESENCE) != 0; + hp_present = snd_hda_jack_detect(codec, nid); if (hp_present) break; } @@ -844,15 +839,11 @@ static void cs_automic(struct hda_codec *codec) struct cs_spec *spec = codec->spec; struct auto_pin_cfg *cfg = &spec->autocfg; hda_nid_t nid; - unsigned int caps, present; + unsigned int present; nid = cfg->input_pins[spec->automic_idx]; - caps = snd_hda_query_pin_caps(codec, nid); - if (caps & AC_PINCAP_TRIG_REQ) - snd_hda_codec_read(codec, nid, 0, AC_VERB_SET_PIN_SENSE, 0); - present = snd_hda_codec_read(codec, nid, 0, - AC_VERB_GET_PIN_SENSE, 0); - if (present & AC_PINSENSE_PRESENCE) + present = snd_hda_jack_detect(codec, nid); + if (present) change_cur_input(codec, spec->automic_idx, 0); else { unsigned int imic = (spec->automic_idx == AUTO_PIN_MIC) ? diff --git a/sound/pci/hda/patch_realtek.c b/sound/pci/hda/patch_realtek.c index 578420523606..cbb2d326e6ad 100644 --- a/sound/pci/hda/patch_realtek.c +++ b/sound/pci/hda/patch_realtek.c @@ -961,18 +961,12 @@ static void alc_fix_pll_init(struct hda_codec *codec, hda_nid_t nid, static void alc_automute_pin(struct hda_codec *codec) { struct alc_spec *spec = codec->spec; - unsigned int present, pincap; unsigned int nid = spec->autocfg.hp_pins[0]; int i; if (!nid) return; - pincap = snd_hda_query_pin_caps(codec, nid); - if (pincap & AC_PINCAP_TRIG_REQ) /* need trigger? */ - snd_hda_codec_read(codec, nid, 0, AC_VERB_SET_PIN_SENSE, 0); - present = snd_hda_codec_read(codec, nid, 0, - AC_VERB_GET_PIN_SENSE, 0); - spec->jack_present = (present & AC_PINSENSE_PRESENCE) != 0; + spec->jack_present = snd_hda_jack_detect(codec, nid); for (i = 0; i < ARRAY_SIZE(spec->autocfg.speaker_pins); i++) { nid = spec->autocfg.speaker_pins[i]; if (!nid) @@ -1012,9 +1006,7 @@ static void alc_mic_automute(struct hda_codec *codec) cap_nid = spec->capsrc_nids ? spec->capsrc_nids[0] : spec->adc_nids[0]; - present = snd_hda_codec_read(codec, spec->ext_mic.pin, 0, - AC_VERB_GET_PIN_SENSE, 0); - present &= AC_PINSENSE_PRESENCE; + present = snd_hda_jack_detect(codec, spec->ext_mic.pin); if (present) { alive = &spec->ext_mic; dead = &spec->int_mic; @@ -1513,7 +1505,7 @@ static struct hda_verb alc888_fujitsu_xa3530_verbs[] = { static void alc_automute_amp(struct hda_codec *codec) { struct alc_spec *spec = codec->spec; - unsigned int val, mute, pincap; + unsigned int mute; hda_nid_t nid; int i; @@ -1522,13 +1514,7 @@ static void alc_automute_amp(struct hda_codec *codec) nid = spec->autocfg.hp_pins[i]; if (!nid) break; - pincap = snd_hda_query_pin_caps(codec, nid); - if (pincap & AC_PINCAP_TRIG_REQ) /* need trigger? */ - snd_hda_codec_read(codec, nid, 0, - AC_VERB_SET_PIN_SENSE, 0); - val = snd_hda_codec_read(codec, nid, 0, - AC_VERB_GET_PIN_SENSE, 0); - if (val & AC_PINSENSE_PRESENCE) { + if (snd_hda_jack_detect(codec, nid)) { spec->jack_present = 1; break; } @@ -2784,8 +2770,7 @@ static void alc880_uniwill_mic_automute(struct hda_codec *codec) unsigned int present; unsigned char bits; - present = snd_hda_codec_read(codec, 0x18, 0, - AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; + present = snd_hda_jack_detect(codec, 0x18); bits = present ? HDA_AMP_MUTE : 0; snd_hda_codec_amp_stereo(codec, 0x0b, HDA_INPUT, 1, HDA_AMP_MUTE, bits); } @@ -5102,11 +5087,8 @@ static struct hda_verb alc260_hp_unsol_verbs[] = { static void alc260_hp_automute(struct hda_codec *codec) { struct alc_spec *spec = codec->spec; - unsigned int present; - present = snd_hda_codec_read(codec, 0x10, 0, - AC_VERB_GET_PIN_SENSE, 0); - spec->jack_present = (present & AC_PINSENSE_PRESENCE) != 0; + spec->jack_present = snd_hda_jack_detect(codec, 0x10); alc260_hp_master_update(codec, 0x0f, 0x10, 0x11); } @@ -5171,11 +5153,8 @@ static struct hda_verb alc260_hp_3013_unsol_verbs[] = { static void alc260_hp_3013_automute(struct hda_codec *codec) { struct alc_spec *spec = codec->spec; - unsigned int present; - present = snd_hda_codec_read(codec, 0x15, 0, - AC_VERB_GET_PIN_SENSE, 0); - spec->jack_present = (present & AC_PINSENSE_PRESENCE) != 0; + spec->jack_present = snd_hda_jack_detect(codec, 0x15); alc260_hp_master_update(codec, 0x15, 0x10, 0x11); } @@ -5188,12 +5167,8 @@ static void alc260_hp_3013_unsol_event(struct hda_codec *codec, static void alc260_hp_3012_automute(struct hda_codec *codec) { - unsigned int present, bits; + unsigned int bits = snd_hda_jack_detect(codec, 0x10) ? 0 : PIN_OUT; - present = snd_hda_codec_read(codec, 0x10, 0, - AC_VERB_GET_PIN_SENSE, 0) & AC_PINSENSE_PRESENCE; - - bits = present ? 0 : PIN_OUT; snd_hda_codec_write(codec, 0x0f, 0, AC_VERB_SET_PIN_WIDGET_CONTROL, bits); snd_hda_codec_write(codec, 0x11, 0, AC_VERB_SET_PIN_WIDGET_CONTROL, @@ -5763,8 +5738,7 @@ static void alc260_replacer_672v_automute(struct hda_codec *codec) unsigned int present; /* speaker --> GPIO Data 0, hp or spdif --> GPIO data 1 */ - present = snd_hda_codec_read(codec, 0x0f, 0, - AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; + present = snd_hda_jack_detect(codec, 0x0f); if (present) { snd_hda_codec_write_cache(codec, 0x01, 0, AC_VERB_SET_GPIO_DATA, 1); @@ -8196,12 +8170,8 @@ static void alc883_mitac_setup(struct hda_codec *codec) /* static void alc883_mitac_mic_automute(struct hda_codec *codec) { - unsigned int present; - unsigned char bits; + unsigned char bits = snd_hda_jack_detect(codec, 0x18) ? HDA_AMP_MUTE : 0; - present = snd_hda_codec_read(codec, 0x18, 0, - AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; - bits = present ? HDA_AMP_MUTE : 0; snd_hda_codec_amp_stereo(codec, 0x0b, HDA_INPUT, 1, HDA_AMP_MUTE, bits); } */ @@ -8423,10 +8393,8 @@ static struct hda_channel_mode alc888_3st_hp_modes[3] = { /* toggle front-jack and RCA according to the hp-jack state */ static void alc888_lenovo_ms7195_front_automute(struct hda_codec *codec) { - unsigned int present; + unsigned int present = snd_hda_jack_detect(codec, 0x1b); - present = snd_hda_codec_read(codec, 0x1b, 0, - AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; snd_hda_codec_amp_stereo(codec, 0x14, HDA_OUTPUT, 0, HDA_AMP_MUTE, present ? HDA_AMP_MUTE : 0); snd_hda_codec_amp_stereo(codec, 0x15, HDA_OUTPUT, 0, @@ -8436,10 +8404,8 @@ static void alc888_lenovo_ms7195_front_automute(struct hda_codec *codec) /* toggle RCA according to the front-jack state */ static void alc888_lenovo_ms7195_rca_automute(struct hda_codec *codec) { - unsigned int present; + unsigned int present = snd_hda_jack_detect(codec, 0x14); - present = snd_hda_codec_read(codec, 0x14, 0, - AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; snd_hda_codec_amp_stereo(codec, 0x15, HDA_OUTPUT, 0, HDA_AMP_MUTE, present ? HDA_AMP_MUTE : 0); } @@ -8532,24 +8498,16 @@ static void alc883_haier_w66_setup(struct hda_codec *codec) static void alc883_lenovo_101e_ispeaker_automute(struct hda_codec *codec) { - unsigned int present; - unsigned char bits; + int bits = snd_hda_jack_detect(codec, 0x14) ? HDA_AMP_MUTE : 0; - present = snd_hda_codec_read(codec, 0x14, 0, AC_VERB_GET_PIN_SENSE, 0) - & AC_PINSENSE_PRESENCE; - bits = present ? HDA_AMP_MUTE : 0; snd_hda_codec_amp_stereo(codec, 0x15, HDA_OUTPUT, 0, HDA_AMP_MUTE, bits); } static void alc883_lenovo_101e_all_automute(struct hda_codec *codec) { - unsigned int present; - unsigned char bits; + int bits = snd_hda_jack_detect(codec, 0x1b) ? HDA_AMP_MUTE : 0; - present = snd_hda_codec_read(codec, 0x1b, 0, - AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; - bits = present ? HDA_AMP_MUTE : 0; snd_hda_codec_amp_stereo(codec, 0x15, HDA_OUTPUT, 0, HDA_AMP_MUTE, bits); snd_hda_codec_amp_stereo(codec, 0x14, HDA_OUTPUT, 0, @@ -8700,8 +8658,7 @@ static void alc889A_mb31_automute(struct hda_codec *codec) /* Mute only in 2ch or 4ch mode */ if (snd_hda_codec_read(codec, 0x15, 0, AC_VERB_GET_CONNECT_SEL, 0) == 0x00) { - present = snd_hda_codec_read(codec, 0x15, 0, - AC_VERB_GET_PIN_SENSE, 0) & AC_PINSENSE_PRESENCE; + present = snd_hda_jack_detect(codec, 0x15); snd_hda_codec_amp_stereo(codec, 0x14, HDA_OUTPUT, 0, HDA_AMP_MUTE, present ? HDA_AMP_MUTE : 0); snd_hda_codec_amp_stereo(codec, 0x16, HDA_OUTPUT, 0, @@ -10044,10 +10001,8 @@ static void alc262_hp_master_update(struct hda_codec *codec) static void alc262_hp_bpc_automute(struct hda_codec *codec) { struct alc_spec *spec = codec->spec; - unsigned int presence; - presence = snd_hda_codec_read(codec, 0x1b, 0, - AC_VERB_GET_PIN_SENSE, 0); - spec->jack_present = !!(presence & AC_PINSENSE_PRESENCE); + + spec->jack_present = snd_hda_jack_detect(codec, 0x1b); alc262_hp_master_update(codec); } @@ -10061,10 +10016,8 @@ static void alc262_hp_bpc_unsol_event(struct hda_codec *codec, unsigned int res) static void alc262_hp_wildwest_automute(struct hda_codec *codec) { struct alc_spec *spec = codec->spec; - unsigned int presence; - presence = snd_hda_codec_read(codec, 0x15, 0, - AC_VERB_GET_PIN_SENSE, 0); - spec->jack_present = !!(presence & AC_PINSENSE_PRESENCE); + + spec->jack_present = snd_hda_jack_detect(codec, 0x15); alc262_hp_master_update(codec); } @@ -10298,13 +10251,8 @@ static void alc262_hippo_automute(struct hda_codec *codec) { struct alc_spec *spec = codec->spec; hda_nid_t hp_nid = spec->autocfg.hp_pins[0]; - unsigned int present; - /* need to execute and sync at first */ - snd_hda_codec_read(codec, hp_nid, 0, AC_VERB_SET_PIN_SENSE, 0); - present = snd_hda_codec_read(codec, hp_nid, 0, - AC_VERB_GET_PIN_SENSE, 0); - spec->jack_present = (present & 0x80000000) != 0; + spec->jack_present = snd_hda_jack_detect(codec, hp_nid); alc262_hippo_master_update(codec); } @@ -10630,21 +10578,8 @@ static void alc262_fujitsu_automute(struct hda_codec *codec, int force) unsigned int mute; if (force || !spec->sense_updated) { - unsigned int present; - /* need to execute and sync at first */ - snd_hda_codec_read(codec, 0x14, 0, AC_VERB_SET_PIN_SENSE, 0); - /* check laptop HP jack */ - present = snd_hda_codec_read(codec, 0x14, 0, - AC_VERB_GET_PIN_SENSE, 0); - /* need to execute and sync at first */ - snd_hda_codec_read(codec, 0x1b, 0, AC_VERB_SET_PIN_SENSE, 0); - /* check docking HP jack */ - present |= snd_hda_codec_read(codec, 0x1b, 0, - AC_VERB_GET_PIN_SENSE, 0); - if (present & AC_PINSENSE_PRESENCE) - spec->jack_present = 1; - else - spec->jack_present = 0; + spec->jack_present = snd_hda_jack_detect(codec, 0x14) || + snd_hda_jack_detect(codec, 0x1b); spec->sense_updated = 1; } /* unmute internal speaker only if both HPs are unplugged and @@ -10689,12 +10624,7 @@ static void alc262_lenovo_3000_automute(struct hda_codec *codec, int force) unsigned int mute; if (force || !spec->sense_updated) { - unsigned int present_int_hp; - /* need to execute and sync at first */ - snd_hda_codec_read(codec, 0x1b, 0, AC_VERB_SET_PIN_SENSE, 0); - present_int_hp = snd_hda_codec_read(codec, 0x1b, 0, - AC_VERB_GET_PIN_SENSE, 0); - spec->jack_present = (present_int_hp & 0x80000000) != 0; + spec->jack_present = snd_hda_jack_detect(codec, 0x1b); spec->sense_updated = 1; } if (spec->jack_present) { @@ -10886,12 +10816,7 @@ static void alc262_ultra_automute(struct hda_codec *codec) mute = 0; /* auto-mute only when HP is used as HP */ if (!spec->cur_mux[0]) { - unsigned int present; - /* need to execute and sync at first */ - snd_hda_codec_read(codec, 0x15, 0, AC_VERB_SET_PIN_SENSE, 0); - present = snd_hda_codec_read(codec, 0x15, 0, - AC_VERB_GET_PIN_SENSE, 0); - spec->jack_present = (present & AC_PINSENSE_PRESENCE) != 0; + spec->jack_present = snd_hda_jack_detect(codec, 0x15); if (spec->jack_present) mute = HDA_AMP_MUTE; } @@ -11933,10 +11858,7 @@ static void alc268_acer_automute(struct hda_codec *codec, int force) unsigned int mute; if (force || !spec->sense_updated) { - unsigned int present; - present = snd_hda_codec_read(codec, 0x14, 0, - AC_VERB_GET_PIN_SENSE, 0); - spec->jack_present = (present & 0x80000000) != 0; + spec->jack_present = snd_hda_jack_detect(codec, 0x14); spec->sense_updated = 1; } if (spec->jack_present) @@ -12055,8 +11977,7 @@ static void alc268_aspire_one_speaker_automute(struct hda_codec *codec) unsigned int present; unsigned char bits; - present = snd_hda_codec_read(codec, 0x15, 0, - AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; + present = snd_hda_jack_detect(codec, 0x15); bits = present ? AMP_IN_MUTE(0) : 0; snd_hda_codec_amp_stereo(codec, 0x0f, HDA_INPUT, 0, AMP_IN_MUTE(0), bits); @@ -13039,8 +12960,7 @@ static void alc269_quanta_fl1_speaker_automute(struct hda_codec *codec) unsigned int present; unsigned char bits; - present = snd_hda_codec_read(codec, 0x15, 0, - AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; + present = snd_hda_jack_detect(codec, 0x15); bits = present ? AMP_IN_MUTE(0) : 0; snd_hda_codec_amp_stereo(codec, 0x0c, HDA_INPUT, 0, AMP_IN_MUTE(0), bits); @@ -13065,12 +12985,10 @@ static void alc269_lifebook_speaker_automute(struct hda_codec *codec) unsigned char bits; /* Check laptop headphone socket */ - present = snd_hda_codec_read(codec, 0x15, 0, - AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; + present = snd_hda_jack_detect(codec, 0x15); /* Check port replicator headphone socket */ - present |= snd_hda_codec_read(codec, 0x1a, 0, - AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; + present |= snd_hda_jack_detect(codec, 0x1a); bits = present ? AMP_IN_MUTE(0) : 0; snd_hda_codec_amp_stereo(codec, 0x0c, HDA_INPUT, 0, @@ -13094,11 +13012,8 @@ static void alc269_lifebook_mic_autoswitch(struct hda_codec *codec) unsigned int present_laptop; unsigned int present_dock; - present_laptop = snd_hda_codec_read(codec, 0x18, 0, - AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; - - present_dock = snd_hda_codec_read(codec, 0x1b, 0, - AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; + present_laptop = snd_hda_jack_detect(codec, 0x18); + present_dock = snd_hda_jack_detect(codec, 0x1b); /* Laptop mic port overrides dock mic port, design decision */ if (present_dock) @@ -13183,8 +13098,7 @@ static void alc269_speaker_automute(struct hda_codec *codec) unsigned int present; unsigned char bits; - present = snd_hda_codec_read(codec, 0x15, 0, - AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; + present = snd_hda_jack_detect(codec, 0x15); bits = present ? AMP_IN_MUTE(0) : 0; snd_hda_codec_amp_stereo(codec, 0x0c, HDA_INPUT, 0, AMP_IN_MUTE(0), bits); @@ -14162,10 +14076,8 @@ static struct hda_verb alc861_toshiba_init_verbs[] = { /* toggle speaker-output according to the hp-jack state */ static void alc861_toshiba_automute(struct hda_codec *codec) { - unsigned int present; + unsigned int present = snd_hda_jack_detect(codec, 0x0f); - present = snd_hda_codec_read(codec, 0x0f, 0, - AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; snd_hda_codec_amp_stereo(codec, 0x16, HDA_INPUT, 0, HDA_AMP_MUTE, present ? HDA_AMP_MUTE : 0); snd_hda_codec_amp_stereo(codec, 0x1a, HDA_INPUT, 3, @@ -15070,9 +14982,9 @@ static void alc861vd_lenovo_mic_automute(struct hda_codec *codec) unsigned int present; unsigned char bits; - present = snd_hda_codec_read(codec, 0x18, 0, - AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; + present = snd_hda_jack_detect(codec, 0x18); bits = present ? HDA_AMP_MUTE : 0; + snd_hda_codec_amp_stereo(codec, 0x0b, HDA_INPUT, 1, HDA_AMP_MUTE, bits); } @@ -16383,9 +16295,9 @@ static void alc662_lenovo_101e_ispeaker_automute(struct hda_codec *codec) unsigned int present; unsigned char bits; - present = snd_hda_codec_read(codec, 0x14, 0, - AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; + present = snd_hda_jack_detect(codec, 0x14); bits = present ? HDA_AMP_MUTE : 0; + snd_hda_codec_amp_stereo(codec, 0x15, HDA_OUTPUT, 0, HDA_AMP_MUTE, bits); } @@ -16395,9 +16307,9 @@ static void alc662_lenovo_101e_all_automute(struct hda_codec *codec) unsigned int present; unsigned char bits; - present = snd_hda_codec_read(codec, 0x1b, 0, - AC_VERB_GET_PIN_SENSE, 0) & 0x80000000; + present = snd_hda_jack_detect(codec, 0x1b); bits = present ? HDA_AMP_MUTE : 0; + snd_hda_codec_amp_stereo(codec, 0x15, HDA_OUTPUT, 0, HDA_AMP_MUTE, bits); snd_hda_codec_amp_stereo(codec, 0x14, HDA_OUTPUT, 0, @@ -16456,9 +16368,7 @@ static void alc663_m51va_speaker_automute(struct hda_codec *codec) unsigned int present; unsigned char bits; - present = snd_hda_codec_read(codec, 0x21, 0, - AC_VERB_GET_PIN_SENSE, 0) - & AC_PINSENSE_PRESENCE; + present = snd_hda_jack_detect(codec, 0x21); bits = present ? HDA_AMP_MUTE : 0; snd_hda_codec_amp_stereo(codec, 0x0c, HDA_INPUT, 0, AMP_IN_MUTE(0), bits); @@ -16471,9 +16381,7 @@ static void alc663_21jd_two_speaker_automute(struct hda_codec *codec) unsigned int present; unsigned char bits; - present = snd_hda_codec_read(codec, 0x21, 0, - AC_VERB_GET_PIN_SENSE, 0) - & AC_PINSENSE_PRESENCE; + present = snd_hda_jack_detect(codec, 0x21); bits = present ? HDA_AMP_MUTE : 0; snd_hda_codec_amp_stereo(codec, 0x0c, HDA_INPUT, 0, AMP_IN_MUTE(0), bits); @@ -16490,9 +16398,7 @@ static void alc663_15jd_two_speaker_automute(struct hda_codec *codec) unsigned int present; unsigned char bits; - present = snd_hda_codec_read(codec, 0x15, 0, - AC_VERB_GET_PIN_SENSE, 0) - & AC_PINSENSE_PRESENCE; + present = snd_hda_jack_detect(codec, 0x15); bits = present ? HDA_AMP_MUTE : 0; snd_hda_codec_amp_stereo(codec, 0x0c, HDA_INPUT, 0, AMP_IN_MUTE(0), bits); @@ -16509,9 +16415,7 @@ static void alc662_f5z_speaker_automute(struct hda_codec *codec) unsigned int present; unsigned char bits; - present = snd_hda_codec_read(codec, 0x1b, 0, - AC_VERB_GET_PIN_SENSE, 0) - & AC_PINSENSE_PRESENCE; + present = snd_hda_jack_detect(codec, 0x1b); bits = present ? 0 : PIN_OUT; snd_hda_codec_write(codec, 0x14, 0, AC_VERB_SET_PIN_WIDGET_CONTROL, bits); @@ -16521,12 +16425,8 @@ static void alc663_two_hp_m1_speaker_automute(struct hda_codec *codec) { unsigned int present1, present2; - present1 = snd_hda_codec_read(codec, 0x21, 0, - AC_VERB_GET_PIN_SENSE, 0) - & AC_PINSENSE_PRESENCE; - present2 = snd_hda_codec_read(codec, 0x15, 0, - AC_VERB_GET_PIN_SENSE, 0) - & AC_PINSENSE_PRESENCE; + present1 = snd_hda_jack_detect(codec, 0x21); + present2 = snd_hda_jack_detect(codec, 0x15); if (present1 || present2) { snd_hda_codec_write_cache(codec, 0x14, 0, @@ -16541,12 +16441,8 @@ static void alc663_two_hp_m2_speaker_automute(struct hda_codec *codec) { unsigned int present1, present2; - present1 = snd_hda_codec_read(codec, 0x1b, 0, - AC_VERB_GET_PIN_SENSE, 0) - & AC_PINSENSE_PRESENCE; - present2 = snd_hda_codec_read(codec, 0x15, 0, - AC_VERB_GET_PIN_SENSE, 0) - & AC_PINSENSE_PRESENCE; + present1 = snd_hda_jack_detect(codec, 0x1b); + present2 = snd_hda_jack_detect(codec, 0x15); if (present1 || present2) { snd_hda_codec_amp_stereo(codec, 0x0c, HDA_INPUT, 0, @@ -16706,9 +16602,7 @@ static void alc663_g71v_hp_automute(struct hda_codec *codec) unsigned int present; unsigned char bits; - present = snd_hda_codec_read(codec, 0x21, 0, - AC_VERB_GET_PIN_SENSE, 0) - & AC_PINSENSE_PRESENCE; + present = snd_hda_jack_detect(codec, 0x21); bits = present ? HDA_AMP_MUTE : 0; snd_hda_codec_amp_stereo(codec, 0x15, HDA_OUTPUT, 0, HDA_AMP_MUTE, bits); @@ -16721,9 +16615,7 @@ static void alc663_g71v_front_automute(struct hda_codec *codec) unsigned int present; unsigned char bits; - present = snd_hda_codec_read(codec, 0x15, 0, - AC_VERB_GET_PIN_SENSE, 0) - & AC_PINSENSE_PRESENCE; + present = snd_hda_jack_detect(codec, 0x15); bits = present ? HDA_AMP_MUTE : 0; snd_hda_codec_amp_stereo(codec, 0x14, HDA_OUTPUT, 0, HDA_AMP_MUTE, bits); -- cgit v1.2.3-59-g8ed1b