[alsa-devel] v3.1.8: hda-intel broken

Takashi Iwai tiwai at suse.de
Wed Feb 22 15:28:07 CET 2012


At Wed, 22 Feb 2012 14:02:52 +0000,
Russell King - ARM Linux wrote:
> 
> On Wed, Feb 22, 2012 at 09:26:27AM +0100, Takashi Iwai wrote:
> > At Tue, 21 Feb 2012 23:58:07 +0000,
> > Russell King - ARM Linux wrote:
> > > 
> > > v3.1.8:
> > > 
> > > <4>[1641072.853409] WARNING: at sound/pci/hda/hda_codec.c:5152 snd_array_new+0x47/0x9b [snd_hda_codec]()
> > > <4>[1641072.853412] Hardware name: 2081CTO
> > > <4>[1641072.853413] BUG? (num >= 4096)
> > > <4>[1641072.853415] Modules linked in: lp cdc_ether usbnet mii cdc_acm cdc_wdm usblp ftdi_sio usbserial parport_jtag fuse joydev cpufreq_ondemand acpi_cpufreq mperf nf_conntrack_netbios_ns nf_conntrack_broadcast ip6t_REJECT nf_conntrack_ipv6 nf_defrag_ipv6 ip6table_filter ip6_tables ipv6 uinput snd_hda_codec_conexant snd_hda_intel snd_hda_codec snd_hwdep snd_seq snd_seq_device arc4 snd_pcm snd_timer r852 sm_common nand nand_ids nand_ecc mtd iwlagn mac80211 snd_page_alloc ppdev iTCO_wdt parport_pc cfg80211 iTCO_vendor_support i2c_i801 thinkpad_acpi rfkill e1000e snd soundcore parport pcspkr wmi microcode firewire_ohci sdhci_pci sdhci mmc_core firewire_core crc_itu_t yenta_socket i915 drm_kms_helper drm i2c_algo_bit i2c_core video [last unloaded: ftdi_sio]
> > > <4>[1641072.853459] Pid: 3089, comm: bash Tainted: G        W   3.1.8 #2
> > > <4>[1641072.853461] Call Trace:
> > > <4>[1641072.853466]  [<c04387eb>] warn_slowpath_common+0x6a/0x7f
> > > <4>[1641072.853472]  [<f861d5d0>] ? snd_array_new+0x47/0x9b [snd_hda_codec]
> > > <4>[1641072.853475]  [<c0438873>] warn_slowpath_fmt+0x2b/0x2f
> > > <4>[1641072.853481]  [<f861d5d0>] snd_array_new+0x47/0x9b [snd_hda_codec]
> > > <4>[1641072.853488]  [<f861d65c>] snd_hda_input_jack_add+0x38/0xa2 [snd_hda_codec]
> > > <4>[1641072.853493]  [<f872dcc4>] cxt5051_init+0x62/0xea [snd_hda_codec_conexant]
> > > <4>[1641072.853500]  [<f8621c51>] hda_call_codec_resume+0xa5/0xba [snd_hda_codec]
> > > <4>[1641072.853506]  [<f861f369>] snd_hda_power_up+0x46/0x5c [snd_hda_codec]
> > > <4>[1641072.853513]  [<f861f3b9>] codec_exec_verb+0x3a/0xc7 [snd_hda_codec]
> > > <4>[1641072.853519]  [<f861f482>] snd_hda_codec_write+0x3c/0x43 [snd_hda_codec]
> > > <4>[1641072.853526]  [<f861f4b9>] set_pincfg+0x30/0x45 [snd_hda_codec]
> > > <4>[1641072.853532]  [<f861f507>] restore_pincfgs+0x39/0x46 [snd_hda_codec]
> > > <4>[1641072.853539]  [<f861fa0a>] snd_hda_codec_free+0x6c/0x1f8 [snd_hda_codec]
> > > <4>[1641072.853545]  [<f861fbdb>] snd_hda_bus_free+0x45/0x7c [snd_hda_codec]
> > > <4>[1641072.853552]  [<f861fdb9>] snd_hda_bus_dev_free+0x17/0x19 [snd_hda_codec]<4>[1641072.853560]  [<f80979a4>] snd_device_free+0x91/0xde [snd]
> > > <4>[1641072.853566]  [<f8097c9c>] snd_device_free_all+0x68/0x80 [snd]
> > > <4>[1641072.853572]  [<f80936e3>] snd_card_do_free+0x4e/0xdf [snd]
> > > <4>[1641072.853577]  [<f8094160>] snd_card_free+0x89/0x94 [snd]
> > > <4>[1641072.853581]  [<c044fcee>] ? wake_up_bit+0x20/0x20
> > > <4>[1641072.853585]  [<f86ccddf>] azx_remove+0x13/0x1f [snd_hda_intel]
> > > <4>[1641072.853589]  [<c05de80d>] pci_device_remove+0x2c/0x74
> > > <4>[1641072.853593]  [<c066371d>] __device_release_driver+0x66/0x9c
> > > <4>[1641072.853596]  [<c0663770>] device_release_driver+0x1d/0x28
> > > <4>[1641072.853599]  [<c0662caf>] driver_unbind+0x4d/0x7b
> > > <4>[1641072.853601]  [<c0662c62>] ? store_drivers_probe+0x33/0x33
> > > <4>[1641072.853604]  [<c06627fb>] drv_attr_store+0x24/0x28
> > > <4>[1641072.853607]  [<c05263a6>] sysfs_write_file+0xb3/0xec
> > > <4>[1641072.853609]  [<c05262f3>] ? sysfs_poll+0x73/0x73
> > > <4>[1641072.853612]  [<c04df254>] vfs_write+0x87/0xde
> > > <4>[1641072.853615]  [<c04e678e>] ? path_put+0x1a/0x1d
> > > <4>[1641072.853617]  [<c04df428>] sys_write+0x40/0x62
> > > <4>[1641072.853621]  [<c07c751f>] sysenter_do_call+0x12/0x28
> > > <4>[1641072.853623] ---[ end trace 3d590d4bbb62d735 ]---
> > > 
> > > >From what I can see, this uses the suspend/resume methods on device open/
> > > close.  The suspend method does nothing apart from "shutting up pins".  The
> > > resume method adds new jacks via snd_array_new(), which eventually ends up
> > > getting (after many many days of uptime) to 4096 entries.  And then it
> > > starts exploding with warnings every so often, filling my screen from top
> > > to bottom with abrtd boxes warning me that my kernel is doing this.
> > 
> > It looks like a problem in Conexant codec driver that tries to add the
> > input-jack entries in the init method.  The bug was probably triggered
> > since it's in the device free, i.e. the jack layer was already
> > released beforehand.  Actually there is no merit to call
> > snd_hda_input_jack_add() in the init callback.  It should be called
> > rather only once at the probing time.
> > 
> > A simple solution would be the patch like below.  Could you check
> > whether it fixes?
> > 
> > The patch is needed only up to 3.2, so it won't go to Linus tree with
> > Cc to stable like a normal fix.  I'm going to send a patch to stable
> > ML once after confirming that it works.
> > 
> > 
> > thanks,
> > 
> > Takashi
> > 
> > ---
> > diff --git a/sound/pci/hda/patch_conexant.c b/sound/pci/hda/patch_conexant.c
> > index 7bbc5f2..9e37200 100644
> > --- a/sound/pci/hda/patch_conexant.c
> > +++ b/sound/pci/hda/patch_conexant.c
> > @@ -1933,7 +1933,6 @@ static int cxt5051_init(struct hda_codec *codec)
> >  	struct conexant_spec *spec = codec->spec;
> >  
> >  	conexant_init(codec);
> > -	conexant_init_jacks(codec);
> 
> NOT fixed.  Why?  Look at the calltrace:
> 
> [   43.884480]  [<f825b663>] snd_hda_input_jack_add+0x3f/0xc1 [snd_hda_codec]
> [   43.884484]  [<f8270c4f>] cxt5051_init_mic_port+0x2e/0x41 [snd_hda_codec_conexant]
> [   43.884493]  [<f8270c90>] cxt5051_init+0x2e/0x69 [snd_hda_codec_conexant]
> 
> Particularly the middle line.

Damn.  Below is the revised patch.  Please give it a try.


thanks,

Takashi

---
From: Takashi Iwai <tiwai at suse.de>
Subject: [PATCH] ALSA: hda - Fix redundant jack creations for cx5051

The cx5051 parser calls snd_hda_input_jack_add() in the init callback
to create and initialize the jack detection instances.  Since the init
callback is called at each time when the device gets woken up after
suspend or power-saving mode, the duplicated instances are accumulated
at each call.  This ends up with the kernel warnings with the too
large array size.

The fix is simply to move the calls of snd_hda_input_jack_add() into
the parser section instead of the init callback.

The fix is needed only up to 3.2 kernel, since the HD-audio jack layer
was redesigned in the 3.3 kernel.

Reported-by: Russell King <rmk+kernel at arm.linux.org.uk>
Signed-off-by: Takashi Iwai <tiwai at suse.de>
---
 sound/pci/hda/patch_conexant.c |   11 ++++++++++-
 1 files changed, 10 insertions(+), 1 deletions(-)

diff --git a/sound/pci/hda/patch_conexant.c b/sound/pci/hda/patch_conexant.c
index 7072251..9b35b05 100644
--- a/sound/pci/hda/patch_conexant.c
+++ b/sound/pci/hda/patch_conexant.c
@@ -1899,6 +1899,10 @@ static void cxt5051_init_mic_port(struct hda_codec *codec, hda_nid_t nid,
 	snd_hda_codec_write(codec, nid, 0,
 			    AC_VERB_SET_UNSOLICITED_ENABLE,
 			    AC_USRSP_EN | event);
+}
+
+static void cxt5051_init_mic_jack(struct hda_codec *codec, hda_nid_t nid)
+{
 	snd_hda_input_jack_add(codec, nid, SND_JACK_MICROPHONE, NULL);
 	snd_hda_input_jack_report(codec, nid);
 }
@@ -1916,7 +1920,6 @@ static int cxt5051_init(struct hda_codec *codec)
 	struct conexant_spec *spec = codec->spec;
 
 	conexant_init(codec);
-	conexant_init_jacks(codec);
 
 	if (spec->auto_mic & AUTO_MIC_PORTB)
 		cxt5051_init_mic_port(codec, 0x17, CXT5051_PORTB_EVENT);
@@ -2037,6 +2040,12 @@ static int patch_cxt5051(struct hda_codec *codec)
 	if (spec->beep_amp)
 		snd_hda_attach_beep_device(codec, spec->beep_amp);
 
+	conexant_init_jacks(codec);
+	if (spec->auto_mic & AUTO_MIC_PORTB)
+		cxt5051_init_mic_jack(codec, 0x17);
+	if (spec->auto_mic & AUTO_MIC_PORTC)
+		cxt5051_init_mic_jack_port(codec, 0x18);
+
 	return 0;
 }
 
-- 
1.7.9



More information about the Alsa-devel mailing list