Commit 576c25eb5954035b64112188d9a2683144600f3d
Exists in
master
and in
20 other branches
Merge tag 'arm64-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/cmarinas/linux-aarch64
Pull ARM64 update from Catalin Marinas: - User tagged pointers support (top 8-bit of user pointers automatically ignored by the CPU). - Kernel mode NEON (no users for arm64 yet but work in progress). - arm64 kernel Image header extended to accommodate future EFI stub. - Remove BogoMIPS reporting (not relevant, it's just the timer frequency). - Clean-up (EM_AARCH64/EM_ARM to elf-em.h, ELF notes in read-only segment, unused variable). - Bug-fixes (RAM boundaries not 2MB aligned, perf, includes). * tag 'arm64-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/cmarinas/linux-aarch64: Documentation/arm64: clarify requirements for DTB placement arm64: mm: permit use of tagged pointers at EL0 Move the EM_ARM and EM_AARCH64 definitions to uapi/linux/elf-em.h arm64: Remove unused cpu_name ascii in arch/arm64/mm/proc.S arm64: delay: don't bother reporting bogomips in /proc/cpuinfo arm64: Fix mapping of memory banks not ending on a PMD_SIZE boundary arm64: move elf notes into readonly segment arm64: Enable interrupts in the EL0 undef handler arm64: Expand arm64 image header ARM64: include: asm: include "asm/types.h" in "pgtable-2level-types.h" and "pgtable-3level-types.h" arm64: add support for kernel mode NEON arm64: perf: fix ARMv8 EVTYPE_MASK to include NSH bit arm64: perf: fix group validation when using enable_on_exec
Showing 19 changed files Side-by-side Diff
- Documentation/arm64/booting.txt
- Documentation/arm64/tagged-pointers.txt
- arch/arm/include/asm/elf.h
- arch/arm64/Kconfig
- arch/arm64/include/asm/elf.h
- arch/arm64/include/asm/neon.h
- arch/arm64/include/asm/pgtable-2level-types.h
- arch/arm64/include/asm/pgtable-3level-types.h
- arch/arm64/include/asm/pgtable-hwdef.h
- arch/arm64/kernel/entry.S
- arch/arm64/kernel/fpsimd.c
- arch/arm64/kernel/head.S
- arch/arm64/kernel/perf_event.c
- arch/arm64/kernel/setup.c
- arch/arm64/kernel/smp.c
- arch/arm64/kernel/vmlinux.lds.S
- arch/arm64/mm/mmu.c
- arch/arm64/mm/proc.S
- include/uapi/linux/elf-em.h
Documentation/arm64/booting.txt
... | ... | @@ -45,9 +45,9 @@ |
45 | 45 | |
46 | 46 | Requirement: MANDATORY |
47 | 47 | |
48 | -The device tree blob (dtb) must be no bigger than 2 megabytes in size | |
49 | -and placed at a 2-megabyte boundary within the first 512 megabytes from | |
50 | -the start of the kernel image. This is to allow the kernel to map the | |
48 | +The device tree blob (dtb) must be placed on an 8-byte boundary within | |
49 | +the first 512 megabytes from the start of the kernel image and must not | |
50 | +cross a 2-megabyte boundary. This is to allow the kernel to map the | |
51 | 51 | blob using a single section mapping in the initial page tables. |
52 | 52 | |
53 | 53 | |
54 | 54 | |
55 | 55 | |
56 | 56 | |
... | ... | @@ -68,13 +68,23 @@ |
68 | 68 | |
69 | 69 | Requirement: MANDATORY |
70 | 70 | |
71 | -The decompressed kernel image contains a 32-byte header as follows: | |
71 | +The decompressed kernel image contains a 64-byte header as follows: | |
72 | 72 | |
73 | - u32 magic = 0x14000008; /* branch to stext, little-endian */ | |
74 | - u32 res0 = 0; /* reserved */ | |
73 | + u32 code0; /* Executable code */ | |
74 | + u32 code1; /* Executable code */ | |
75 | 75 | u64 text_offset; /* Image load offset */ |
76 | + u64 res0 = 0; /* reserved */ | |
76 | 77 | u64 res1 = 0; /* reserved */ |
77 | 78 | u64 res2 = 0; /* reserved */ |
79 | + u64 res3 = 0; /* reserved */ | |
80 | + u64 res4 = 0; /* reserved */ | |
81 | + u32 magic = 0x644d5241; /* Magic number, little endian, "ARM\x64" */ | |
82 | + u32 res5 = 0; /* reserved */ | |
83 | + | |
84 | + | |
85 | +Header notes: | |
86 | + | |
87 | +- code0/code1 are responsible for branching to stext. | |
78 | 88 | |
79 | 89 | The image must be placed at the specified offset (currently 0x80000) |
80 | 90 | from the start of the system RAM and called there. The start of the |
Documentation/arm64/tagged-pointers.txt
1 | + Tagged virtual addresses in AArch64 Linux | |
2 | + ========================================= | |
3 | + | |
4 | +Author: Will Deacon <will.deacon@arm.com> | |
5 | +Date : 12 June 2013 | |
6 | + | |
7 | +This document briefly describes the provision of tagged virtual | |
8 | +addresses in the AArch64 translation system and their potential uses | |
9 | +in AArch64 Linux. | |
10 | + | |
11 | +The kernel configures the translation tables so that translations made | |
12 | +via TTBR0 (i.e. userspace mappings) have the top byte (bits 63:56) of | |
13 | +the virtual address ignored by the translation hardware. This frees up | |
14 | +this byte for application use, with the following caveats: | |
15 | + | |
16 | + (1) The kernel requires that all user addresses passed to EL1 | |
17 | + are tagged with tag 0x00. This means that any syscall | |
18 | + parameters containing user virtual addresses *must* have | |
19 | + their top byte cleared before trapping to the kernel. | |
20 | + | |
21 | + (2) Tags are not guaranteed to be preserved when delivering | |
22 | + signals. This means that signal handlers in applications | |
23 | + making use of tags cannot rely on the tag information for | |
24 | + user virtual addresses being maintained for fields inside | |
25 | + siginfo_t. One exception to this rule is for signals raised | |
26 | + in response to debug exceptions, where the tag information | |
27 | + will be preserved. | |
28 | + | |
29 | + (3) Special care should be taken when using tagged pointers, | |
30 | + since it is likely that C compilers will not hazard two | |
31 | + addresses differing only in the upper bits. | |
32 | + | |
33 | +The architecture prevents the use of a tagged PC, so the upper byte will | |
34 | +be set to a sign-extension of bit 55 on exception return. |
arch/arm/include/asm/elf.h
arch/arm64/Kconfig
arch/arm64/include/asm/elf.h
... | ... | @@ -33,8 +33,6 @@ |
33 | 33 | typedef elf_greg_t elf_gregset_t[ELF_NGREG]; |
34 | 34 | typedef struct user_fpsimd_state elf_fpregset_t; |
35 | 35 | |
36 | -#define EM_AARCH64 183 | |
37 | - | |
38 | 36 | /* |
39 | 37 | * AArch64 static relocation types. |
40 | 38 | */ |
... | ... | @@ -151,7 +149,6 @@ |
151 | 149 | #define arch_randomize_brk arch_randomize_brk |
152 | 150 | |
153 | 151 | #ifdef CONFIG_COMPAT |
154 | -#define EM_ARM 40 | |
155 | 152 | #define COMPAT_ELF_PLATFORM ("v8l") |
156 | 153 | |
157 | 154 | #define COMPAT_ELF_ET_DYN_BASE (randomize_et_dyn(2 * TASK_SIZE_32 / 3)) |
arch/arm64/include/asm/neon.h
1 | +/* | |
2 | + * linux/arch/arm64/include/asm/neon.h | |
3 | + * | |
4 | + * Copyright (C) 2013 Linaro Ltd <ard.biesheuvel@linaro.org> | |
5 | + * | |
6 | + * This program is free software; you can redistribute it and/or modify | |
7 | + * it under the terms of the GNU General Public License version 2 as | |
8 | + * published by the Free Software Foundation. | |
9 | + */ | |
10 | + | |
11 | +#define cpu_has_neon() (1) | |
12 | + | |
13 | +void kernel_neon_begin(void); | |
14 | +void kernel_neon_end(void); |
arch/arm64/include/asm/pgtable-2level-types.h
arch/arm64/include/asm/pgtable-3level-types.h
arch/arm64/include/asm/pgtable-hwdef.h
arch/arm64/kernel/entry.S
... | ... | @@ -423,6 +423,7 @@ |
423 | 423 | * Data abort handling |
424 | 424 | */ |
425 | 425 | mrs x0, far_el1 |
426 | + bic x0, x0, #(0xff << 56) | |
426 | 427 | disable_step x1 |
427 | 428 | isb |
428 | 429 | enable_dbg |
... | ... | @@ -476,6 +477,8 @@ |
476 | 477 | * Undefined instruction |
477 | 478 | */ |
478 | 479 | mov x0, sp |
480 | + // enable interrupts before calling the main handler | |
481 | + enable_irq | |
479 | 482 | b do_undefinstr |
480 | 483 | el0_dbg: |
481 | 484 | /* |
arch/arm64/kernel/fpsimd.c
... | ... | @@ -21,6 +21,7 @@ |
21 | 21 | #include <linux/init.h> |
22 | 22 | #include <linux/sched.h> |
23 | 23 | #include <linux/signal.h> |
24 | +#include <linux/hardirq.h> | |
24 | 25 | |
25 | 26 | #include <asm/fpsimd.h> |
26 | 27 | #include <asm/cputype.h> |
... | ... | @@ -82,6 +83,33 @@ |
82 | 83 | memset(¤t->thread.fpsimd_state, 0, sizeof(struct fpsimd_state)); |
83 | 84 | fpsimd_load_state(¤t->thread.fpsimd_state); |
84 | 85 | } |
86 | + | |
87 | +#ifdef CONFIG_KERNEL_MODE_NEON | |
88 | + | |
89 | +/* | |
90 | + * Kernel-side NEON support functions | |
91 | + */ | |
92 | +void kernel_neon_begin(void) | |
93 | +{ | |
94 | + /* Avoid using the NEON in interrupt context */ | |
95 | + BUG_ON(in_interrupt()); | |
96 | + preempt_disable(); | |
97 | + | |
98 | + if (current->mm) | |
99 | + fpsimd_save_state(¤t->thread.fpsimd_state); | |
100 | +} | |
101 | +EXPORT_SYMBOL(kernel_neon_begin); | |
102 | + | |
103 | +void kernel_neon_end(void) | |
104 | +{ | |
105 | + if (current->mm) | |
106 | + fpsimd_load_state(¤t->thread.fpsimd_state); | |
107 | + | |
108 | + preempt_enable(); | |
109 | +} | |
110 | +EXPORT_SYMBOL(kernel_neon_end); | |
111 | + | |
112 | +#endif /* CONFIG_KERNEL_MODE_NEON */ | |
85 | 113 | |
86 | 114 | /* |
87 | 115 | * FP/SIMD support code initialisation. |
arch/arm64/kernel/head.S
... | ... | @@ -112,6 +112,14 @@ |
112 | 112 | .quad TEXT_OFFSET // Image load offset from start of RAM |
113 | 113 | .quad 0 // reserved |
114 | 114 | .quad 0 // reserved |
115 | + .quad 0 // reserved | |
116 | + .quad 0 // reserved | |
117 | + .quad 0 // reserved | |
118 | + .byte 0x41 // Magic number, "ARM\x64" | |
119 | + .byte 0x52 | |
120 | + .byte 0x4d | |
121 | + .byte 0x64 | |
122 | + .word 0 // reserved | |
115 | 123 | |
116 | 124 | ENTRY(stext) |
117 | 125 | mov x21, x0 // x21=FDT |
arch/arm64/kernel/perf_event.c
... | ... | @@ -325,9 +325,12 @@ |
325 | 325 | if (is_software_event(event)) |
326 | 326 | return 1; |
327 | 327 | |
328 | - if (event->pmu != leader_pmu || event->state <= PERF_EVENT_STATE_OFF) | |
328 | + if (event->pmu != leader_pmu || event->state < PERF_EVENT_STATE_OFF) | |
329 | 329 | return 1; |
330 | 330 | |
331 | + if (event->state == PERF_EVENT_STATE_OFF && !event->attr.enable_on_exec) | |
332 | + return 1; | |
333 | + | |
331 | 334 | return armpmu->get_event_idx(hw_events, &fake_event) >= 0; |
332 | 335 | } |
333 | 336 | |
... | ... | @@ -781,7 +784,7 @@ |
781 | 784 | /* |
782 | 785 | * PMXEVTYPER: Event selection reg |
783 | 786 | */ |
784 | -#define ARMV8_EVTYPE_MASK 0xc00000ff /* Mask for writable bits */ | |
787 | +#define ARMV8_EVTYPE_MASK 0xc80000ff /* Mask for writable bits */ | |
785 | 788 | #define ARMV8_EVTYPE_EVENT 0xff /* Mask for EVENT bits */ |
786 | 789 | |
787 | 790 | /* |
arch/arm64/kernel/setup.c
... | ... | @@ -328,9 +328,6 @@ |
328 | 328 | #ifdef CONFIG_SMP |
329 | 329 | seq_printf(m, "processor\t: %d\n", i); |
330 | 330 | #endif |
331 | - seq_printf(m, "BogoMIPS\t: %lu.%02lu\n\n", | |
332 | - loops_per_jiffy / (500000UL/HZ), | |
333 | - loops_per_jiffy / (5000UL/HZ) % 100); | |
334 | 331 | } |
335 | 332 | |
336 | 333 | /* dump out the processor features */ |
arch/arm64/kernel/smp.c
... | ... | @@ -223,11 +223,7 @@ |
223 | 223 | |
224 | 224 | void __init smp_cpus_done(unsigned int max_cpus) |
225 | 225 | { |
226 | - unsigned long bogosum = loops_per_jiffy * num_online_cpus(); | |
227 | - | |
228 | - pr_info("SMP: Total of %d processors activated (%lu.%02lu BogoMIPS).\n", | |
229 | - num_online_cpus(), bogosum / (500000/HZ), | |
230 | - (bogosum / (5000/HZ)) % 100); | |
226 | + pr_info("SMP: Total of %d processors activated.\n", num_online_cpus()); | |
231 | 227 | } |
232 | 228 | |
233 | 229 | void __init smp_prepare_boot_cpu(void) |
arch/arm64/kernel/vmlinux.lds.S
... | ... | @@ -71,6 +71,7 @@ |
71 | 71 | |
72 | 72 | RO_DATA(PAGE_SIZE) |
73 | 73 | EXCEPTION_TABLE(8) |
74 | + NOTES | |
74 | 75 | _etext = .; /* End of text and rodata section */ |
75 | 76 | |
76 | 77 | . = ALIGN(PAGE_SIZE); |
... | ... | @@ -121,8 +122,6 @@ |
121 | 122 | _edata = .; |
122 | 123 | } |
123 | 124 | _edata_loc = __data_loc + SIZEOF(.data); |
124 | - | |
125 | - NOTES | |
126 | 125 | |
127 | 126 | BSS_SECTION(0, 0, 0) |
128 | 127 | _end = .; |
arch/arm64/mm/mmu.c
... | ... | @@ -296,6 +296,7 @@ |
296 | 296 | static void __init map_mem(void) |
297 | 297 | { |
298 | 298 | struct memblock_region *reg; |
299 | + phys_addr_t limit; | |
299 | 300 | |
300 | 301 | /* |
301 | 302 | * Temporarily limit the memblock range. We need to do this as |
302 | 303 | |
... | ... | @@ -303,9 +304,11 @@ |
303 | 304 | * memory addressable from the initial direct kernel mapping. |
304 | 305 | * |
305 | 306 | * The initial direct kernel mapping, located at swapper_pg_dir, |
306 | - * gives us PGDIR_SIZE memory starting from PHYS_OFFSET (aligned). | |
307 | + * gives us PGDIR_SIZE memory starting from PHYS_OFFSET (which must be | |
308 | + * aligned to 2MB as per Documentation/arm64/booting.txt). | |
307 | 309 | */ |
308 | - memblock_set_current_limit((PHYS_OFFSET & PGDIR_MASK) + PGDIR_SIZE); | |
310 | + limit = PHYS_OFFSET + PGDIR_SIZE; | |
311 | + memblock_set_current_limit(limit); | |
309 | 312 | |
310 | 313 | /* map all the memory banks */ |
311 | 314 | for_each_memblock(memory, reg) { |
... | ... | @@ -314,6 +317,22 @@ |
314 | 317 | |
315 | 318 | if (start >= end) |
316 | 319 | break; |
320 | + | |
321 | +#ifndef CONFIG_ARM64_64K_PAGES | |
322 | + /* | |
323 | + * For the first memory bank align the start address and | |
324 | + * current memblock limit to prevent create_mapping() from | |
325 | + * allocating pte page tables from unmapped memory. | |
326 | + * When 64K pages are enabled, the pte page table for the | |
327 | + * first PGDIR_SIZE is already present in swapper_pg_dir. | |
328 | + */ | |
329 | + if (start < limit) | |
330 | + start = ALIGN(start, PMD_SIZE); | |
331 | + if (end < limit) { | |
332 | + limit = end & PMD_MASK; | |
333 | + memblock_set_current_limit(limit); | |
334 | + } | |
335 | +#endif | |
317 | 336 | |
318 | 337 | create_mapping(start, __phys_to_virt(start), end - start); |
319 | 338 | } |
arch/arm64/mm/proc.S
... | ... | @@ -95,10 +95,6 @@ |
95 | 95 | ret |
96 | 96 | ENDPROC(cpu_do_switch_mm) |
97 | 97 | |
98 | -cpu_name: | |
99 | - .ascii "AArch64 Processor" | |
100 | - .align | |
101 | - | |
102 | 98 | .section ".text.init", #alloc, #execinstr |
103 | 99 | |
104 | 100 | /* |
... | ... | @@ -151,7 +147,7 @@ |
151 | 147 | * both user and kernel. |
152 | 148 | */ |
153 | 149 | ldr x10, =TCR_TxSZ(VA_BITS) | TCR_FLAGS | TCR_IPS_40BIT | \ |
154 | - TCR_ASID16 | (1 << 31) | |
150 | + TCR_ASID16 | TCR_TBI0 | (1 << 31) | |
155 | 151 | #ifdef CONFIG_ARM64_64K_PAGES |
156 | 152 | orr x10, x10, TCR_TG0_64K |
157 | 153 | orr x10, x10, TCR_TG1_64K |
include/uapi/linux/elf-em.h
... | ... | @@ -22,6 +22,7 @@ |
22 | 22 | #define EM_PPC 20 /* PowerPC */ |
23 | 23 | #define EM_PPC64 21 /* PowerPC64 */ |
24 | 24 | #define EM_SPU 23 /* Cell BE SPU */ |
25 | +#define EM_ARM 40 /* ARM 32 bit */ | |
25 | 26 | #define EM_SH 42 /* SuperH */ |
26 | 27 | #define EM_SPARCV9 43 /* SPARC v9 64-bit */ |
27 | 28 | #define EM_IA_64 50 /* HP/Intel IA-64 */ |
... | ... | @@ -34,6 +35,7 @@ |
34 | 35 | #define EM_MN10300 89 /* Panasonic/MEI MN10300, AM33 */ |
35 | 36 | #define EM_BLACKFIN 106 /* ADI Blackfin Processor */ |
36 | 37 | #define EM_TI_C6000 140 /* TI C6X DSPs */ |
38 | +#define EM_AARCH64 183 /* ARM 64 bit */ | |
37 | 39 | #define EM_FRV 0x5441 /* Fujitsu FR-V */ |
38 | 40 | #define EM_AVR32 0x18ad /* Atmel AVR32 */ |
39 | 41 |