Browse Source

[ALSA] hda-intel - Switch to polling mode for CORB/RIRB communication

Automatically switch to polling mode for CORB/RIRB communication
if the irq-driven mode seems not working well.  If the polling
mode still doesn't work, switch to single_cmd mode as fallback.

Signed-off-by: Takashi Iwai <tiwai@suse.de>
Signed-off-by: Jaroslav Kysela <perex@suse.cz>
Takashi Iwai 19 years ago
parent
commit
e96224ae97
1 changed files with 17 additions and 1 deletions
  1. 17 1
      sound/pci/hda/hda_intel.c

+ 17 - 1
sound/pci/hda/hda_intel.c

@@ -332,6 +332,7 @@ struct azx {
 	int position_fix;
 	unsigned int initialized: 1;
 	unsigned int single_cmd: 1;
+	unsigned int polling_mode: 1;
 };
 
 /* driver types */
@@ -518,8 +519,23 @@ static unsigned int azx_rirb_get_response(struct hda_codec *codec)
 	struct azx *chip = codec->bus->private_data;
 	int timeout = 50;
 
-	while (chip->rirb.cmds) {
+	for (;;) {
+		if (chip->polling_mode) {
+			spin_lock_irq(&chip->reg_lock);
+			azx_update_rirb(chip);
+			spin_unlock_irq(&chip->reg_lock);
+		}
+		if (! chip->rirb.cmds)
+			break;
 		if (! --timeout) {
+			if (! chip->polling_mode) {
+				snd_printk(KERN_WARNING "hda_intel: "
+					   "azx_get_response timeout, "
+					   "switching to polling mode...\n");
+				chip->polling_mode = 1;
+				timeout = 50;
+				continue;
+			}
 			snd_printk(KERN_ERR
 				   "hda_intel: azx_get_response timeout, "
 				   "switching to single_cmd mode...\n");