Merge branch 'x86-fixes-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git...
authorLinus Torvalds <torvalds@linux-foundation.org>
Sat, 5 Jul 2008 20:08:38 +0000 (13:08 -0700)
committerLinus Torvalds <torvalds@linux-foundation.org>
Sat, 5 Jul 2008 20:08:38 +0000 (13:08 -0700)
* 'x86-fixes-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/linux-2.6-tip:
  x86 ACPI: fix resume from suspend to RAM on uniprocessor x86-64
  x86 ACPI: normalize segment descriptor register on resume

drivers/ata/ahci.c
drivers/ide/ide-probe.c
drivers/ide/ide.c
fs/proc/task_mmu.c
mm/mempolicy.c

index 061817a..5e6468a 100644 (file)
@@ -1777,7 +1777,7 @@ static irqreturn_t ahci_interrupt(int irq, void *dev_instance)
        struct ahci_host_priv *hpriv;
        unsigned int i, handled = 0;
        void __iomem *mmio;
-       u32 irq_stat;
+       u32 irq_stat, irq_masked;
 
        VPRINTK("ENTER\n");
 
@@ -1786,16 +1786,17 @@ static irqreturn_t ahci_interrupt(int irq, void *dev_instance)
 
        /* sigh.  0xffffffff is a valid return from h/w */
        irq_stat = readl(mmio + HOST_IRQ_STAT);
-       irq_stat &= hpriv->port_map;
        if (!irq_stat)
                return IRQ_NONE;
 
+       irq_masked = irq_stat & hpriv->port_map;
+
        spin_lock(&host->lock);
 
        for (i = 0; i < host->n_ports; i++) {
                struct ata_port *ap;
 
-               if (!(irq_stat & (1 << i)))
+               if (!(irq_masked & (1 << i)))
                        continue;
 
                ap = host->ports[i];
@@ -1812,6 +1813,15 @@ static irqreturn_t ahci_interrupt(int irq, void *dev_instance)
                handled = 1;
        }
 
+       /* HOST_IRQ_STAT behaves as level triggered latch meaning that
+        * it should be cleared after all the port events are cleared;
+        * otherwise, it will raise a spurious interrupt after each
+        * valid one.  Please read section 10.6.2 of ahci 1.1 for more
+        * information.
+        *
+        * Also, use the unmasked value to clear interrupt as spurious
+        * pending event on a dummy port might cause screaming IRQ.
+        */
        writel(irq_stat, mmio + HOST_IRQ_STAT);
 
        spin_unlock(&host->lock);
index 380fa0c..d27061b 100644 (file)
@@ -646,8 +646,6 @@ static int ide_register_port(ide_hwif_t *hwif)
                goto out;
        }
 
-       get_device(&hwif->gendev);
-
        hwif->portdev = device_create_drvdata(ide_port_class, &hwif->gendev,
                                              MKDEV(0, 0), hwif, hwif->name);
        if (IS_ERR(hwif->portdev)) {
index c758dcb..300431d 100644 (file)
@@ -315,13 +315,14 @@ void ide_unregister(ide_hwif_t *hwif)
 
        BUG_ON(in_interrupt());
        BUG_ON(irqs_disabled());
+
        mutex_lock(&ide_cfg_mtx);
-       spin_lock_irq(&ide_lock);
-       if (!hwif->present)
-               goto abort;
-       __ide_port_unregister_devices(hwif);
-       hwif->present = 0;
 
+       spin_lock_irq(&ide_lock);
+       if (hwif->present) {
+               __ide_port_unregister_devices(hwif);
+               hwif->present = 0;
+       }
        spin_unlock_irq(&ide_lock);
 
        ide_proc_unregister_port(hwif);
@@ -351,16 +352,15 @@ void ide_unregister(ide_hwif_t *hwif)
        blk_unregister_region(MKDEV(hwif->major, 0), MAX_DRIVES<<PARTN_BITS);
        kfree(hwif->sg_table);
        unregister_blkdev(hwif->major, hwif->name);
-       spin_lock_irq(&ide_lock);
 
        if (hwif->dma_base)
                ide_release_dma_engine(hwif);
 
+       spin_lock_irq(&ide_lock);
        /* restore hwif data to pristine status */
        ide_init_port_data(hwif, hwif->index);
-
-abort:
        spin_unlock_irq(&ide_lock);
+
        mutex_unlock(&ide_cfg_mtx);
 }
 
@@ -1094,13 +1094,6 @@ struct bus_type ide_bus_type = {
 
 EXPORT_SYMBOL_GPL(ide_bus_type);
 
-static void ide_port_class_release(struct device *portdev)
-{
-       ide_hwif_t *hwif = dev_get_drvdata(portdev);
-
-       put_device(&hwif->gendev);
-}
-
 int ide_vlb_clk;
 EXPORT_SYMBOL_GPL(ide_vlb_clk);
 
@@ -1305,7 +1298,6 @@ static int __init ide_init(void)
                ret = PTR_ERR(ide_port_class);
                goto out_port_class;
        }
-       ide_port_class->dev_release = ide_port_class_release;
 
        init_ide_data();
 
index ab8ccc9..05053d7 100644 (file)
@@ -476,10 +476,10 @@ static ssize_t clear_refs_write(struct file *file, const char __user *buf,
                return -ESRCH;
        mm = get_task_mm(task);
        if (mm) {
-               static struct mm_walk clear_refs_walk;
-               memset(&clear_refs_walk, 0, sizeof(clear_refs_walk));
-               clear_refs_walk.pmd_entry = clear_refs_pte_range;
-               clear_refs_walk.mm = mm;
+               struct mm_walk clear_refs_walk = {
+                       .pmd_entry = clear_refs_pte_range,
+                       .mm = mm,
+               };
                down_read(&mm->mmap_sem);
                for (vma = mm->mmap; vma; vma = vma->vm_next) {
                        clear_refs_walk.private = vma;
index a37a503..c94e58b 100644 (file)
@@ -729,7 +729,11 @@ static long do_get_mempolicy(int *policy, nodemask_t *nmask,
        } else {
                *policy = pol == &default_policy ? MPOL_DEFAULT :
                                                pol->mode;
-               *policy |= pol->flags;
+               /*
+                * Internal mempolicy flags must be masked off before exposing
+                * the policy to userspace.
+                */
+               *policy |= (pol->flags & MPOL_MODE_FLAGS);
        }
 
        if (vma) {