diff options
author | Takashi Iwai <tiwai@suse.de> | 2008-04-22 11:28:11 -0400 |
---|---|---|
committer | Takashi Iwai <tiwai@suse.de> | 2008-04-24 06:00:41 -0400 |
commit | ebf029da38829ede6b53ac8a5ad45b149064ea16 (patch) | |
tree | aebf6bddd245a874577fc321978b3f7137e8ac39 /sound/pci/intel8x0m.c | |
parent | 6b9a9b329640b7e8143df7b2782884ea758650f7 (diff) |
[ALSA] Fix possible races at free_irq in PCI drivers
The irq handler of PCI drivers must be released before releasing other
resources since the handler for a shared irq can be still called and
may access the freed resource again.
Signed-off-by: Takashi Iwai <tiwai@suse.de>
Diffstat (limited to 'sound/pci/intel8x0m.c')
-rw-r--r-- | sound/pci/intel8x0m.c | 8 |
1 files changed, 2 insertions, 6 deletions
diff --git a/sound/pci/intel8x0m.c b/sound/pci/intel8x0m.c index 15db810d5893..faf674e671ac 100644 --- a/sound/pci/intel8x0m.c +++ b/sound/pci/intel8x0m.c | |||
@@ -985,18 +985,15 @@ static int snd_intel8x0_free(struct intel8x0m *chip) | |||
985 | /* reset channels */ | 985 | /* reset channels */ |
986 | for (i = 0; i < chip->bdbars_count; i++) | 986 | for (i = 0; i < chip->bdbars_count; i++) |
987 | iputbyte(chip, ICH_REG_OFF_CR + chip->ichd[i].reg_offset, ICH_RESETREGS); | 987 | iputbyte(chip, ICH_REG_OFF_CR + chip->ichd[i].reg_offset, ICH_RESETREGS); |
988 | /* --- */ | 988 | __hw_end: |
989 | if (chip->irq >= 0) | 989 | if (chip->irq >= 0) |
990 | synchronize_irq(chip->irq); | 990 | free_irq(chip->irq, chip); |
991 | __hw_end: | ||
992 | if (chip->bdbars.area) | 991 | if (chip->bdbars.area) |
993 | snd_dma_free_pages(&chip->bdbars); | 992 | snd_dma_free_pages(&chip->bdbars); |
994 | if (chip->addr) | 993 | if (chip->addr) |
995 | pci_iounmap(chip->pci, chip->addr); | 994 | pci_iounmap(chip->pci, chip->addr); |
996 | if (chip->bmaddr) | 995 | if (chip->bmaddr) |
997 | pci_iounmap(chip->pci, chip->bmaddr); | 996 | pci_iounmap(chip->pci, chip->bmaddr); |
998 | if (chip->irq >= 0) | ||
999 | free_irq(chip->irq, chip); | ||
1000 | pci_release_regions(chip->pci); | 997 | pci_release_regions(chip->pci); |
1001 | pci_disable_device(chip->pci); | 998 | pci_disable_device(chip->pci); |
1002 | kfree(chip); | 999 | kfree(chip); |
@@ -1018,7 +1015,6 @@ static int intel8x0m_suspend(struct pci_dev *pci, pm_message_t state) | |||
1018 | snd_pcm_suspend_all(chip->pcm[i]); | 1015 | snd_pcm_suspend_all(chip->pcm[i]); |
1019 | snd_ac97_suspend(chip->ac97); | 1016 | snd_ac97_suspend(chip->ac97); |
1020 | if (chip->irq >= 0) { | 1017 | if (chip->irq >= 0) { |
1021 | synchronize_irq(chip->irq); | ||
1022 | free_irq(chip->irq, chip); | 1018 | free_irq(chip->irq, chip); |
1023 | chip->irq = -1; | 1019 | chip->irq = -1; |
1024 | } | 1020 | } |