Merge commit 'e26a9e0' into stable/for-linus-3.15
authorDavid Vrabel <david.vrabel@citrix.com>
Mon, 28 Apr 2014 09:31:04 +0000 (10:31 +0100)
committerDavid Vrabel <david.vrabel@citrix.com>
Mon, 28 Apr 2014 09:31:04 +0000 (10:31 +0100)
1  2 
arch/arm/include/asm/memory.h
arch/arm/kernel/head.S
arch/arm/kernel/setup.c
arch/arm/mm/dma-mapping.c
arch/arm/mm/mmu.c
arch/arm/mm/proc-v7.S
drivers/clocksource/timer-u300.c

   */
  #define UL(x) _AC(x, UL)
  
 +/* PAGE_OFFSET - the virtual address of the start of the kernel image */
 +#define PAGE_OFFSET           UL(CONFIG_PAGE_OFFSET)
 +
  #ifdef CONFIG_MMU
  
  /*
 - * PAGE_OFFSET - the virtual address of the start of the kernel image
   * TASK_SIZE - the maximum size of a user space task.
   * TASK_UNMAPPED_BASE - the lower boundary of the mmap VM area
   */
 -#define PAGE_OFFSET           UL(CONFIG_PAGE_OFFSET)
  #define TASK_SIZE             (UL(CONFIG_PAGE_OFFSET) - UL(SZ_16M))
  #define TASK_UNMAPPED_BASE    ALIGN(TASK_SIZE / 3, SZ_16M)
  
  #define END_MEM               (UL(CONFIG_DRAM_BASE) + CONFIG_DRAM_SIZE)
  #endif
  
 -#ifndef PAGE_OFFSET
 -#define PAGE_OFFSET           PLAT_PHYS_OFFSET
 -#endif
 -
  /*
   * The module can be at any place in ram in nommu mode.
   */
   * Physical vs virtual RAM address space conversion.  These are
   * private definitions which should NOT be used outside memory.h
   * files.  Use virt_to_phys/phys_to_virt/__pa/__va instead.
+  *
+  * PFNs are used to describe any physical page; this means
+  * PFN 0 == physical address 0.
   */
- #ifndef __virt_to_phys
- #ifdef CONFIG_ARM_PATCH_PHYS_VIRT
+ #if defined(__virt_to_phys)
+ #define PHYS_OFFSET   PLAT_PHYS_OFFSET
+ #define PHYS_PFN_OFFSET       ((unsigned long)(PHYS_OFFSET >> PAGE_SHIFT))
+ #define virt_to_pfn(kaddr) (__pa(kaddr) >> PAGE_SHIFT)
+ #elif defined(CONFIG_ARM_PATCH_PHYS_VIRT)
  
  /*
   * Constants used to force the right instruction encodings and shifts
  #define __PV_BITS_31_24       0x81000000
  #define __PV_BITS_7_0 0x81
  
- extern u64 __pv_phys_offset;
+ extern unsigned long __pv_phys_pfn_offset;
  extern u64 __pv_offset;
  extern void fixup_pv_table(const void *, unsigned long);
  extern const void *__pv_table_begin, *__pv_table_end;
  
- #define PHYS_OFFSET __pv_phys_offset
+ #define PHYS_OFFSET   ((phys_addr_t)__pv_phys_pfn_offset << PAGE_SHIFT)
+ #define PHYS_PFN_OFFSET       (__pv_phys_pfn_offset)
+ #define virt_to_pfn(kaddr) \
+       ((((unsigned long)(kaddr) - PAGE_OFFSET) >> PAGE_SHIFT) + \
+        PHYS_PFN_OFFSET)
  
  #define __pv_stub(from,to,instr,type)                 \
        __asm__("@ __pv_stub\n"                         \
@@@ -243,6 -259,7 +256,7 @@@ static inline unsigned long __phys_to_v
  #else
  
  #define PHYS_OFFSET   PLAT_PHYS_OFFSET
+ #define PHYS_PFN_OFFSET       ((unsigned long)(PHYS_OFFSET >> PAGE_SHIFT))
  
  static inline phys_addr_t __virt_to_phys(unsigned long x)
  {
@@@ -254,18 -271,11 +268,11 @@@ static inline unsigned long __phys_to_v
        return x - PHYS_OFFSET + PAGE_OFFSET;
  }
  
- #endif
- #endif
+ #define virt_to_pfn(kaddr) \
+       ((((unsigned long)(kaddr) - PAGE_OFFSET) >> PAGE_SHIFT) + \
+        PHYS_PFN_OFFSET)
  
- /*
-  * PFNs are used to describe any physical page; this means
-  * PFN 0 == physical address 0.
-  *
-  * This is the PFN of the first RAM page in the kernel
-  * direct-mapped view.  We assume this is the first page
-  * of RAM in the mem_map as well.
-  */
- #define PHYS_PFN_OFFSET       ((unsigned long)(PHYS_OFFSET >> PAGE_SHIFT))
+ #endif
  
  /*
   * These are *only* valid on the kernel direct mapped RAM memory.
@@@ -343,9 -353,9 +350,9 @@@ static inline __deprecated void *bus_to
   */
  #define ARCH_PFN_OFFSET               PHYS_PFN_OFFSET
  
- #define virt_to_page(kaddr)   pfn_to_page(__pa(kaddr) >> PAGE_SHIFT)
+ #define virt_to_page(kaddr)   pfn_to_page(virt_to_pfn(kaddr))
  #define virt_addr_valid(kaddr)        (((unsigned long)(kaddr) >= PAGE_OFFSET && (unsigned long)(kaddr) < (unsigned long)high_memory) \
-                                       && pfn_valid(__pa(kaddr) >> PAGE_SHIFT) )
+                                       && pfn_valid(virt_to_pfn(kaddr)))
  
  #endif
  
diff --combined arch/arm/kernel/head.S
@@@ -102,7 -102,7 +102,7 @@@ ENTRY(stext
        and     r3, r3, #0xf                    @ extract VMSA support
        cmp     r3, #5                          @ long-descriptor translation table format?
   THUMB( it    lo )                            @ force fixup-able long branch encoding
 -      blo     __error_p                       @ only classic page table format
 +      blo     __error_lpae                    @ only classic page table format
  #endif
  
  #ifndef CONFIG_XIP_KERNEL
@@@ -584,9 -584,10 +584,10 @@@ __fixup_pv_table
        subs    r3, r0, r3      @ PHYS_OFFSET - PAGE_OFFSET
        add     r4, r4, r3      @ adjust table start address
        add     r5, r5, r3      @ adjust table end address
-       add     r6, r6, r3      @ adjust __pv_phys_offset address
+       add     r6, r6, r3      @ adjust __pv_phys_pfn_offset address
        add     r7, r7, r3      @ adjust __pv_offset address
-       str     r8, [r6, #LOW_OFFSET]   @ save computed PHYS_OFFSET to __pv_phys_offset
+       mov     r0, r8, lsr #12 @ convert to PFN
+       str     r0, [r6, #LOW_OFFSET]   @ save computed PHYS_OFFSET to __pv_phys_pfn_offset
        strcc   ip, [r7, #HIGH_OFFSET]  @ save to __pv_offset high bits
        mov     r6, r3, lsr #24 @ constant for add/sub instructions
        teq     r3, r6, lsl #24 @ must be 16MiB aligned
@@@ -600,7 -601,7 +601,7 @@@ ENDPROC(__fixup_pv_table
  1:    .long   .
        .long   __pv_table_begin
        .long   __pv_table_end
- 2:    .long   __pv_phys_offset
+ 2:    .long   __pv_phys_pfn_offset
        .long   __pv_offset
  
        .text
@@@ -688,11 -689,11 +689,11 @@@ ENTRY(fixup_pv_table
  ENDPROC(fixup_pv_table)
  
        .data
-       .globl  __pv_phys_offset
-       .type   __pv_phys_offset, %object
- __pv_phys_offset:
-       .quad   0
-       .size   __pv_phys_offset, . -__pv_phys_offset
+       .globl  __pv_phys_pfn_offset
+       .type   __pv_phys_pfn_offset, %object
+ __pv_phys_pfn_offset:
+       .word   0
+       .size   __pv_phys_pfn_offset, . -__pv_phys_pfn_offset
  
        .globl  __pv_offset
        .type   __pv_offset, %object
diff --combined arch/arm/kernel/setup.c
@@@ -100,6 -100,9 +100,9 @@@ EXPORT_SYMBOL(system_serial_high)
  unsigned int elf_hwcap __read_mostly;
  EXPORT_SYMBOL(elf_hwcap);
  
+ unsigned int elf_hwcap2 __read_mostly;
+ EXPORT_SYMBOL(elf_hwcap2);
  
  #ifdef MULTI_CPU
  struct processor processor __read_mostly;
@@@ -731,7 -734,7 +734,7 @@@ static void __init request_standard_res
        kernel_data.end     = virt_to_phys(_end - 1);
  
        for_each_memblock(memory, region) {
 -              res = memblock_virt_alloc_low(sizeof(*res), 0);
 +              res = memblock_virt_alloc(sizeof(*res), 0);
                res->name  = "System RAM";
                res->start = __pfn_to_phys(memblock_region_memory_base_pfn(region));
                res->end = __pfn_to_phys(memblock_region_memory_end_pfn(region)) - 1;
@@@ -1005,6 -1008,15 +1008,15 @@@ static const char *hwcap_str[] = 
        NULL
  };
  
+ static const char *hwcap2_str[] = {
+       "aes",
+       "pmull",
+       "sha1",
+       "sha2",
+       "crc32",
+       NULL
+ };
  static int c_show(struct seq_file *m, void *v)
  {
        int i, j;
                        if (elf_hwcap & (1 << j))
                                seq_printf(m, "%s ", hwcap_str[j]);
  
+               for (j = 0; hwcap2_str[j]; j++)
+                       if (elf_hwcap2 & (1 << j))
+                               seq_printf(m, "%s ", hwcap2_str[j]);
                seq_printf(m, "\nCPU implementer\t: 0x%02x\n", cpuid >> 24);
                seq_printf(m, "CPU architecture: %s\n",
                           proc_arch[cpu_architecture()]);
@@@ -284,9 -284,6 +284,6 @@@ static void __dma_free_buffer(struct pa
  }
  
  #ifdef CONFIG_MMU
- #ifdef CONFIG_HUGETLB_PAGE
- #warning ARM Coherent DMA allocator does not (yet) support huge TLB
- #endif
  
  static void *__alloc_from_contiguous(struct device *dev, size_t size,
                                     pgprot_t prot, struct page **ret_page,
@@@ -1358,7 -1355,7 +1355,7 @@@ static void *arm_iommu_alloc_attrs(stru
        *handle = DMA_ERROR_CODE;
        size = PAGE_ALIGN(size);
  
 -      if (gfp & GFP_ATOMIC)
 +      if (!(gfp & __GFP_WAIT))
                return __iommu_alloc_atomic(dev, size, handle);
  
        /*
diff --combined arch/arm/mm/mmu.c
@@@ -232,16 -232,12 +232,16 @@@ __setup("noalign", noalign_setup)
  #endif /* ifdef CONFIG_CPU_CP15 / else */
  
  #define PROT_PTE_DEVICE               L_PTE_PRESENT|L_PTE_YOUNG|L_PTE_DIRTY|L_PTE_XN
 +#define PROT_PTE_S2_DEVICE    PROT_PTE_DEVICE
  #define PROT_SECT_DEVICE      PMD_TYPE_SECT|PMD_SECT_AP_WRITE
  
  static struct mem_type mem_types[] = {
        [MT_DEVICE] = {           /* Strongly ordered / ARMv6 shared device */
                .prot_pte       = PROT_PTE_DEVICE | L_PTE_MT_DEV_SHARED |
                                  L_PTE_SHARED,
 +              .prot_pte_s2    = s2_policy(PROT_PTE_S2_DEVICE) |
 +                                s2_policy(L_PTE_S2_MT_DEV_SHARED) |
 +                                L_PTE_SHARED,
                .prot_l1        = PMD_TYPE_TABLE,
                .prot_sect      = PROT_SECT_DEVICE | PMD_SECT_S,
                .domain         = DOMAIN_IO,
@@@ -512,9 -508,18 +512,19 @@@ static void __init build_mem_type_table
        cp = &cache_policies[cachepolicy];
        vecs_pgprot = kern_pgprot = user_pgprot = cp->pte;
        s2_pgprot = cp->pte_s2;
 -      hyp_device_pgprot = s2_device_pgprot = mem_types[MT_DEVICE].prot_pte;
 +      hyp_device_pgprot = mem_types[MT_DEVICE].prot_pte;
 +      s2_device_pgprot = mem_types[MT_DEVICE].prot_pte_s2;
  
+       /*
+        * We don't use domains on ARMv6 (since this causes problems with
+        * v6/v7 kernels), so we must use a separate memory type for user
+        * r/o, kernel r/w to map the vectors page.
+        */
+ #ifndef CONFIG_ARM_LPAE
+       if (cpu_arch == CPU_ARCH_ARMv6)
+               vecs_pgprot |= L_PTE_MT_VECTORS;
+ #endif
        /*
         * ARMv6 and above have extended page tables.
         */
diff --combined arch/arm/mm/proc-v7.S
@@@ -192,6 -192,7 +192,7 @@@ __v7_cr7mp_setup
        mov     r10, #(1 << 0)                  @ Cache/TLB ops broadcasting
        b       1f
  __v7_ca7mp_setup:
+ __v7_ca12mp_setup:
  __v7_ca15mp_setup:
        mov     r10, #0
  1:
@@@ -351,6 -352,7 +352,6 @@@ __v7_setup
  
  4:    mov     r10, #0
        mcr     p15, 0, r10, c7, c5, 0          @ I+BTB cache invalidate
 -      dsb
  #ifdef CONFIG_MMU
        mcr     p15, 0, r10, c8, c7, 0          @ invalidate I + D TLBs
        v7_ttb_setup r10, r4, r8, r5            @ TTBCR, TTBRx setup
        mcr     p15, 0, r5, c10, c2, 0          @ write PRRR
        mcr     p15, 0, r6, c10, c2, 1          @ write NMRR
  #endif
 +      dsb                                     @ Complete invalidations
  #ifndef CONFIG_ARM_THUMBEE
        mrc     p15, 0, r0, c0, c1, 0           @ read ID_PFR0 for ThumbEE
        and     r0, r0, #(0xf << 12)            @ ThumbEE enabled field
@@@ -483,6 -484,16 +484,16 @@@ __v7_ca7mp_proc_info
        __v7_proc __v7_ca7mp_setup
        .size   __v7_ca7mp_proc_info, . - __v7_ca7mp_proc_info
  
+       /*
+        * ARM Ltd. Cortex A12 processor.
+        */
+       .type   __v7_ca12mp_proc_info, #object
+ __v7_ca12mp_proc_info:
+       .long   0x410fc0d0
+       .long   0xff0ffff0
+       __v7_proc __v7_ca12mp_setup
+       .size   __v7_ca12mp_proc_info, . - __v7_ca12mp_proc_info
        /*
         * ARM Ltd. Cortex A15 processor.
         */
@@@ -1,4 -1,8 +1,4 @@@
  /*
 - *
 - * arch/arm/mach-u300/timer.c
 - *
 - *
   * Copyright (C) 2007-2009 ST-Ericsson AB
   * License terms: GNU General Public License (GPL) version 2
   * Timer COH 901 328, runs the OS timer interrupt.
@@@ -333,7 -337,7 +333,7 @@@ static irqreturn_t u300_timer_interrupt
  
  static struct irqaction u300_timer_irq = {
        .name           = "U300 Timer Tick",
-       .flags          = IRQF_DISABLED | IRQF_TIMER | IRQF_IRQPOLL,
+       .flags          = IRQF_TIMER | IRQF_IRQPOLL,
        .handler        = u300_timer_interrupt,
  };