aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2017-11-26 18:03:49 -0500
committerLinus Torvalds <torvalds@linux-foundation.org>2017-11-26 18:03:49 -0500
commitbbecb1cfcca55f98cfcb62fa36a32d79975d8816 (patch)
treeac86a653ea2c9e3c0352b7975026fde14dd3dec1
parentdec0029a59779d8279dde663ef8abe9824ee5773 (diff)
parent8bafae202c82dc257f649ea3c275a0f35ee15113 (diff)
Merge branch 'fixes' of git://git.armlinux.org.uk/~rmk/linux-arm
Pull ARM fixes from Russell King: - LPAE fixes for kernel-readonly regions - Fix for get_user_pages_fast on LPAE systems - avoid tying decompressor to a particular platform if DEBUG_LL is enabled - BUG if we attempt to return to userspace but the to-be-restored PSR value keeps us in privileged mode (defeating an issue that ftracetest found) * 'fixes' of git://git.armlinux.org.uk/~rmk/linux-arm: ARM: BUG if jumping to usermode address in kernel mode ARM: 8722/1: mm: make STRICT_KERNEL_RWX effective for LPAE ARM: 8721/1: mm: dump: check hardware RO bit for LPAE ARM: make decompressor debug output user selectable ARM: fix get_user_pages_fast
-rw-r--r--arch/arm/Kconfig.debug4
-rw-r--r--arch/arm/include/asm/assembler.h18
-rw-r--r--arch/arm/include/asm/pgtable.h12
-rw-r--r--arch/arm/kernel/entry-header.S6
-rw-r--r--arch/arm/mm/dump.c4
-rw-r--r--arch/arm/mm/init.c4
6 files changed, 42 insertions, 6 deletions
diff --git a/arch/arm/Kconfig.debug b/arch/arm/Kconfig.debug
index 12b8c8f8ec07..17685e19aed8 100644
--- a/arch/arm/Kconfig.debug
+++ b/arch/arm/Kconfig.debug
@@ -1776,9 +1776,9 @@ config DEBUG_UART_8250_FLOW_CONTROL
1776 default y if ARCH_EBSA110 || DEBUG_FOOTBRIDGE_COM1 || DEBUG_GEMINI || ARCH_RPC 1776 default y if ARCH_EBSA110 || DEBUG_FOOTBRIDGE_COM1 || DEBUG_GEMINI || ARCH_RPC
1777 1777
1778config DEBUG_UNCOMPRESS 1778config DEBUG_UNCOMPRESS
1779 bool 1779 bool "Enable decompressor debugging via DEBUG_LL output"
1780 depends on ARCH_MULTIPLATFORM || PLAT_SAMSUNG || ARM_SINGLE_ARMV7M 1780 depends on ARCH_MULTIPLATFORM || PLAT_SAMSUNG || ARM_SINGLE_ARMV7M
1781 default y if DEBUG_LL && !DEBUG_OMAP2PLUS_UART && \ 1781 depends on DEBUG_LL && !DEBUG_OMAP2PLUS_UART && \
1782 (!DEBUG_TEGRA_UART || !ZBOOT_ROM) && \ 1782 (!DEBUG_TEGRA_UART || !ZBOOT_ROM) && \
1783 !DEBUG_BRCMSTB_UART 1783 !DEBUG_BRCMSTB_UART
1784 help 1784 help
diff --git a/arch/arm/include/asm/assembler.h b/arch/arm/include/asm/assembler.h
index ad301f107dd2..bc8d4bbd82e2 100644
--- a/arch/arm/include/asm/assembler.h
+++ b/arch/arm/include/asm/assembler.h
@@ -518,4 +518,22 @@ THUMB( orr \reg , \reg , #PSR_T_BIT )
518#endif 518#endif
519 .endm 519 .endm
520 520
521 .macro bug, msg, line
522#ifdef CONFIG_THUMB2_KERNEL
5231: .inst 0xde02
524#else
5251: .inst 0xe7f001f2
526#endif
527#ifdef CONFIG_DEBUG_BUGVERBOSE
528 .pushsection .rodata.str, "aMS", %progbits, 1
5292: .asciz "\msg"
530 .popsection
531 .pushsection __bug_table, "aw"
532 .align 2
533 .word 1b, 2b
534 .hword \line
535 .popsection
536#endif
537 .endm
538
521#endif /* __ASM_ASSEMBLER_H__ */ 539#endif /* __ASM_ASSEMBLER_H__ */
diff --git a/arch/arm/include/asm/pgtable.h b/arch/arm/include/asm/pgtable.h
index 1c462381c225..150ece66ddf3 100644
--- a/arch/arm/include/asm/pgtable.h
+++ b/arch/arm/include/asm/pgtable.h
@@ -232,6 +232,18 @@ static inline pte_t *pmd_page_vaddr(pmd_t pmd)
232#define pte_valid_user(pte) \ 232#define pte_valid_user(pte) \
233 (pte_valid(pte) && pte_isset((pte), L_PTE_USER) && pte_young(pte)) 233 (pte_valid(pte) && pte_isset((pte), L_PTE_USER) && pte_young(pte))
234 234
235static inline bool pte_access_permitted(pte_t pte, bool write)
236{
237 pteval_t mask = L_PTE_PRESENT | L_PTE_USER;
238 pteval_t needed = mask;
239
240 if (write)
241 mask |= L_PTE_RDONLY;
242
243 return (pte_val(pte) & mask) == needed;
244}
245#define pte_access_permitted pte_access_permitted
246
235#if __LINUX_ARM_ARCH__ < 6 247#if __LINUX_ARM_ARCH__ < 6
236static inline void __sync_icache_dcache(pte_t pteval) 248static inline void __sync_icache_dcache(pte_t pteval)
237{ 249{
diff --git a/arch/arm/kernel/entry-header.S b/arch/arm/kernel/entry-header.S
index d523cd8439a3..7f4d80c2db6b 100644
--- a/arch/arm/kernel/entry-header.S
+++ b/arch/arm/kernel/entry-header.S
@@ -300,6 +300,8 @@
300 mov r2, sp 300 mov r2, sp
301 ldr r1, [r2, #\offset + S_PSR] @ get calling cpsr 301 ldr r1, [r2, #\offset + S_PSR] @ get calling cpsr
302 ldr lr, [r2, #\offset + S_PC]! @ get pc 302 ldr lr, [r2, #\offset + S_PC]! @ get pc
303 tst r1, #0xcf
304 bne 1f
303 msr spsr_cxsf, r1 @ save in spsr_svc 305 msr spsr_cxsf, r1 @ save in spsr_svc
304#if defined(CONFIG_CPU_V6) || defined(CONFIG_CPU_32v6K) 306#if defined(CONFIG_CPU_V6) || defined(CONFIG_CPU_32v6K)
305 @ We must avoid clrex due to Cortex-A15 erratum #830321 307 @ We must avoid clrex due to Cortex-A15 erratum #830321
@@ -314,6 +316,7 @@
314 @ after ldm {}^ 316 @ after ldm {}^
315 add sp, sp, #\offset + PT_REGS_SIZE 317 add sp, sp, #\offset + PT_REGS_SIZE
316 movs pc, lr @ return & move spsr_svc into cpsr 318 movs pc, lr @ return & move spsr_svc into cpsr
3191: bug "Returning to usermode but unexpected PSR bits set?", \@
317#elif defined(CONFIG_CPU_V7M) 320#elif defined(CONFIG_CPU_V7M)
318 @ V7M restore. 321 @ V7M restore.
319 @ Note that we don't need to do clrex here as clearing the local 322 @ Note that we don't need to do clrex here as clearing the local
@@ -329,6 +332,8 @@
329 ldr r1, [sp, #\offset + S_PSR] @ get calling cpsr 332 ldr r1, [sp, #\offset + S_PSR] @ get calling cpsr
330 ldr lr, [sp, #\offset + S_PC] @ get pc 333 ldr lr, [sp, #\offset + S_PC] @ get pc
331 add sp, sp, #\offset + S_SP 334 add sp, sp, #\offset + S_SP
335 tst r1, #0xcf
336 bne 1f
332 msr spsr_cxsf, r1 @ save in spsr_svc 337 msr spsr_cxsf, r1 @ save in spsr_svc
333 338
334 @ We must avoid clrex due to Cortex-A15 erratum #830321 339 @ We must avoid clrex due to Cortex-A15 erratum #830321
@@ -341,6 +346,7 @@
341 .endif 346 .endif
342 add sp, sp, #PT_REGS_SIZE - S_SP 347 add sp, sp, #PT_REGS_SIZE - S_SP
343 movs pc, lr @ return & move spsr_svc into cpsr 348 movs pc, lr @ return & move spsr_svc into cpsr
3491: bug "Returning to usermode but unexpected PSR bits set?", \@
344#endif /* !CONFIG_THUMB2_KERNEL */ 350#endif /* !CONFIG_THUMB2_KERNEL */
345 .endm 351 .endm
346 352
diff --git a/arch/arm/mm/dump.c b/arch/arm/mm/dump.c
index 35ff45470dbf..fc3b44028cfb 100644
--- a/arch/arm/mm/dump.c
+++ b/arch/arm/mm/dump.c
@@ -129,8 +129,8 @@ static const struct prot_bits section_bits[] = {
129 .val = PMD_SECT_USER, 129 .val = PMD_SECT_USER,
130 .set = "USR", 130 .set = "USR",
131 }, { 131 }, {
132 .mask = L_PMD_SECT_RDONLY, 132 .mask = L_PMD_SECT_RDONLY | PMD_SECT_AP2,
133 .val = L_PMD_SECT_RDONLY, 133 .val = L_PMD_SECT_RDONLY | PMD_SECT_AP2,
134 .set = "ro", 134 .set = "ro",
135 .clear = "RW", 135 .clear = "RW",
136#elif __LINUX_ARM_ARCH__ >= 6 136#elif __LINUX_ARM_ARCH__ >= 6
diff --git a/arch/arm/mm/init.c b/arch/arm/mm/init.c
index 81d4482b6861..a1f11a7ee81b 100644
--- a/arch/arm/mm/init.c
+++ b/arch/arm/mm/init.c
@@ -629,8 +629,8 @@ static struct section_perm ro_perms[] = {
629 .start = (unsigned long)_stext, 629 .start = (unsigned long)_stext,
630 .end = (unsigned long)__init_begin, 630 .end = (unsigned long)__init_begin,
631#ifdef CONFIG_ARM_LPAE 631#ifdef CONFIG_ARM_LPAE
632 .mask = ~L_PMD_SECT_RDONLY, 632 .mask = ~(L_PMD_SECT_RDONLY | PMD_SECT_AP2),
633 .prot = L_PMD_SECT_RDONLY, 633 .prot = L_PMD_SECT_RDONLY | PMD_SECT_AP2,
634#else 634#else
635 .mask = ~(PMD_SECT_APX | PMD_SECT_AP_WRITE), 635 .mask = ~(PMD_SECT_APX | PMD_SECT_AP_WRITE),
636 .prot = PMD_SECT_APX | PMD_SECT_AP_WRITE, 636 .prot = PMD_SECT_APX | PMD_SECT_AP_WRITE,