Merge branch 'fixes' of git://git.armlinux.org.uk/~rmk/linux-arm
authorLinus Torvalds <torvalds@linux-foundation.org>
Thu, 18 Aug 2016 18:13:20 +0000 (11:13 -0700)
committerLinus Torvalds <torvalds@linux-foundation.org>
Thu, 18 Aug 2016 18:13:20 +0000 (11:13 -0700)
Pull ARM fixes from Russell King:
 "Only three fixes this time:

   - Emil found an overflow problem with the memory layout sanity check.

   - Ard Biesheuvel noticed that late-allocated page tables (for EFI)
     weren't being properly constructed.

   - Guenter Roeck reported a problem found on qemu caused by the recent
     addr_limit changes"

* 'fixes' of git://git.armlinux.org.uk/~rmk/linux-arm:
  ARM: fix address limit restoration for undefined instructions
  ARM: 8591/1: mm: use fully constructed struct pages for EFI pgd allocations
  ARM: 8590/1: sanity_check_meminfo(): avoid overflow on vmalloc_limit

arch/arm/kernel/entry-armv.S
arch/arm/mm/mmu.c

index bc5f507..9f157e7 100644 (file)
@@ -295,6 +295,7 @@ __und_svc_fault:
        bl      __und_fault
 
 __und_svc_finish:
+       get_thread_info tsk
        ldr     r5, [sp, #S_PSR]                @ Get SVC cpsr
        svc_exit r5                             @ return from exception
  UNWIND(.fnend         )
index 62f4d01..6344913 100644 (file)
@@ -728,7 +728,8 @@ static void *__init late_alloc(unsigned long sz)
 {
        void *ptr = (void *)__get_free_pages(PGALLOC_GFP, get_order(sz));
 
-       BUG_ON(!ptr);
+       if (!ptr || !pgtable_page_ctor(virt_to_page(ptr)))
+               BUG();
        return ptr;
 }
 
@@ -1155,10 +1156,19 @@ void __init sanity_check_meminfo(void)
 {
        phys_addr_t memblock_limit = 0;
        int highmem = 0;
-       phys_addr_t vmalloc_limit = __pa(vmalloc_min - 1) + 1;
+       u64 vmalloc_limit;
        struct memblock_region *reg;
        bool should_use_highmem = false;
 
+       /*
+        * Let's use our own (unoptimized) equivalent of __pa() that is
+        * not affected by wrap-arounds when sizeof(phys_addr_t) == 4.
+        * The result is used as the upper bound on physical memory address
+        * and may itself be outside the valid range for which phys_addr_t
+        * and therefore __pa() is defined.
+        */
+       vmalloc_limit = (u64)(uintptr_t)vmalloc_min - PAGE_OFFSET + PHYS_OFFSET;
+
        for_each_memblock(memory, reg) {
                phys_addr_t block_start = reg->base;
                phys_addr_t block_end = reg->base + reg->size;
@@ -1183,10 +1193,11 @@ void __init sanity_check_meminfo(void)
                        if (reg->size > size_limit) {
                                phys_addr_t overlap_size = reg->size - size_limit;
 
-                               pr_notice("Truncating RAM at %pa-%pa to -%pa",
-                                         &block_start, &block_end, &vmalloc_limit);
-                               memblock_remove(vmalloc_limit, overlap_size);
+                               pr_notice("Truncating RAM at %pa-%pa",
+                                         &block_start, &block_end);
                                block_end = vmalloc_limit;
+                               pr_cont(" to -%pa", &block_end);
+                               memblock_remove(vmalloc_limit, overlap_size);
                                should_use_highmem = true;
                        }
                }