]> www.pilppa.org Git - linux-2.6-omap-h63xx.git/commitdiff
Merge branch 'linux-2.6'
authorPaul Mackerras <paulus@samba.org>
Tue, 25 Mar 2008 21:44:18 +0000 (08:44 +1100)
committerPaul Mackerras <paulus@samba.org>
Tue, 25 Mar 2008 21:44:18 +0000 (08:44 +1100)
1  2 
arch/powerpc/kernel/process.c
arch/powerpc/mm/hash_utils_64.c
arch/powerpc/platforms/cell/iommu.c

index 7c8e3da238107b43fc943f999294cc7f8610671f,59311ec0d422d3eca2f94b358808bde287765fbc..8d506d86e2df560562230cdb675804e59122c4c6
@@@ -353,6 -353,12 +353,12 @@@ struct task_struct *__switch_to(struct 
        account_process_vtime(current);
        calculate_steal_time();
  
+       /*
+        * We can't take a PMU exception inside _switch() since there is a
+        * window where the kernel stack SLB and the kernel stack are out
+        * of sync. Hard disable here.
+        */
+       hard_irq_disable();
        last = _switch(old_thread, new_thread);
  
        local_irq_restore(flags);
@@@ -862,6 -868,11 +868,6 @@@ int sys_execve(unsigned long a0, unsign
        flush_spe_to_thread(current);
        error = do_execve(filename, (char __user * __user *) a1,
                          (char __user * __user *) a2, regs);
 -      if (error == 0) {
 -              task_lock(current);
 -              current->ptrace &= ~PT_DTRACE;
 -              task_unlock(current);
 -      }
        putname(filename);
  out:
        return error;
index 0b018b29cda84647dd6898a2808a6eb15477a32d,a83dfa3cf40c562cd8d0218c0efb903d60303a47..c2e5f61788b0cfbe779f337bd35847db9c93c5bb
@@@ -31,7 -31,6 +31,7 @@@
  #include <linux/cache.h>
  #include <linux/init.h>
  #include <linux/signal.h>
 +#include <linux/lmb.h>
  
  #include <asm/processor.h>
  #include <asm/pgtable.h>
@@@ -42,7 -41,7 +42,7 @@@
  #include <asm/system.h>
  #include <asm/uaccess.h>
  #include <asm/machdep.h>
 -#include <asm/lmb.h>
 +#include <asm/prom.h>
  #include <asm/abs_addr.h>
  #include <asm/tlbflush.h>
  #include <asm/io.h>
@@@ -192,24 -191,6 +192,24 @@@ int htab_bolt_mapping(unsigned long vst
        return ret < 0 ? ret : 0;
  }
  
 +static void htab_remove_mapping(unsigned long vstart, unsigned long vend,
 +                    int psize, int ssize)
 +{
 +      unsigned long vaddr;
 +      unsigned int step, shift;
 +
 +      shift = mmu_psize_defs[psize].shift;
 +      step = 1 << shift;
 +
 +      if (!ppc_md.hpte_removebolted) {
 +              printk("Sub-arch doesn't implement hpte_removebolted\n");
 +              return;
 +      }
 +
 +      for (vaddr = vstart; vaddr < vend; vaddr += step)
 +              ppc_md.hpte_removebolted(vaddr, psize, ssize);
 +}
 +
  static int __init htab_dt_scan_seg_sizes(unsigned long node,
                                         const char *uname, int depth,
                                         void *data)
@@@ -370,9 -351,14 +370,14 @@@ static void __init htab_init_page_sizes
                mmu_vmalloc_psize = MMU_PAGE_64K;
                if (mmu_linear_psize == MMU_PAGE_4K)
                        mmu_linear_psize = MMU_PAGE_64K;
-               if (cpu_has_feature(CPU_FTR_CI_LARGE_PAGE))
-                       mmu_io_psize = MMU_PAGE_64K;
-               else
+               if (cpu_has_feature(CPU_FTR_CI_LARGE_PAGE)) {
+                       /*
+                        * Don't use 64k pages for ioremap on pSeries, since
+                        * that would stop us accessing the HEA ethernet.
+                        */
+                       if (!machine_is(pseries))
+                               mmu_io_psize = MMU_PAGE_64K;
+               } else
                        mmu_ci_restrictions = 1;
        }
  #endif /* CONFIG_PPC_64K_PAGES */
@@@ -448,11 -434,6 +453,11 @@@ void create_section_mapping(unsigned lo
                        _PAGE_ACCESSED | _PAGE_DIRTY | _PAGE_COHERENT | PP_RWXX,
                        mmu_linear_psize, mmu_kernel_ssize));
  }
 +
 +void remove_section_mapping(unsigned long start, unsigned long end)
 +{
 +      htab_remove_mapping(start, end, mmu_linear_psize, mmu_kernel_ssize);
 +}
  #endif /* CONFIG_MEMORY_HOTPLUG */
  
  static inline void make_bl(unsigned int *insn_addr, void *func)
index d6a732503ea61bb7455751e37d2ae9177e0a1e31,d75ccded7f104b7e4f7d00577fa4aed26ce7659d..49fe641d434553a95d78e21364df3263ee10aa6b
  #include <linux/notifier.h>
  #include <linux/of.h>
  #include <linux/of_platform.h>
 +#include <linux/lmb.h>
  
  #include <asm/prom.h>
  #include <asm/iommu.h>
  #include <asm/machdep.h>
  #include <asm/pci-bridge.h>
  #include <asm/udbg.h>
 -#include <asm/lmb.h>
  #include <asm/firmware.h>
  #include <asm/cell-regs.h>
  
@@@ -802,17 -802,24 +802,24 @@@ static int __init cell_iommu_init_disab
  
  static u64 cell_iommu_get_fixed_address(struct device *dev)
  {
-       u64 cpu_addr, size, best_size, pci_addr = OF_BAD_ADDR;
+       u64 cpu_addr, size, best_size, dev_addr = OF_BAD_ADDR;
        struct device_node *np;
        const u32 *ranges = NULL;
-       int i, len, best;
+       int i, len, best, naddr, nsize, pna, range_size;
  
        np = of_node_get(dev->archdata.of_node);
-       while (np) {
+       while (1) {
+               naddr = of_n_addr_cells(np);
+               nsize = of_n_size_cells(np);
+               np = of_get_next_parent(np);
+               if (!np)
+                       break;
                ranges = of_get_property(np, "dma-ranges", &len);
-               if (ranges)
+               /* Ignore empty ranges, they imply no translation required */
+               if (ranges && len > 0)
                        break;
-               np = of_get_next_parent(np);
        }
  
        if (!ranges) {
  
        len /= sizeof(u32);
  
+       pna = of_n_addr_cells(np);
+       range_size = naddr + nsize + pna;
        /* dma-ranges format:
-        * 1 cell:  pci space
-        * 2 cells: pci address
-        * 2 cells: parent address
-        * 2 cells: size
+        * child addr   : naddr cells
+        * parent addr  : pna cells
+        * size         : nsize cells
         */
-       for (i = 0, best = -1, best_size = 0; i < len; i += 7) {
-               cpu_addr = of_translate_dma_address(np, ranges +i + 3);
-               size = of_read_number(ranges + i + 5, 2);
+       for (i = 0, best = -1, best_size = 0; i < len; i += range_size) {
+               cpu_addr = of_translate_dma_address(np, ranges + i + naddr);
+               size = of_read_number(ranges + i + naddr + pna, nsize);
  
                if (cpu_addr == 0 && size > best_size) {
                        best = i;
                }
        }
  
-       if (best >= 0)
-               pci_addr = of_read_number(ranges + best + 1, 2);
-       else
+       if (best >= 0) {
+               dev_addr = of_read_number(ranges + best, naddr);
+       else
                dev_dbg(dev, "iommu: no suitable range found!\n");
  
  out:
        of_node_put(np);
  
-       return pci_addr;
+       return dev_addr;
  }
  
  static int dma_set_mask_and_switch(struct device *dev, u64 dma_mask)