]>
Commit | Line | Data |
---|---|---|
2874c5fd | 1 | /* SPDX-License-Identifier: GPL-2.0-or-later */ |
2129a235 PD |
2 | /* |
3 | * Copyright (C) 2003 Matjaz Breskvar <phoenix@bsemi.com> | |
4 | * Copyright (C) 2010-2011 Jonas Bonn <jonas@southpole.se> | |
5 | * Copyright (C) 2012 Regents of the University of California | |
2129a235 PD |
6 | */ |
7 | ||
8 | #ifndef _ASM_RISCV_ELF_H | |
9 | #define _ASM_RISCV_ELF_H | |
10 | ||
87309e10 GR |
11 | #include <uapi/linux/elf.h> |
12 | #include <linux/compat.h> | |
2129a235 PD |
13 | #include <uapi/asm/elf.h> |
14 | #include <asm/auxvec.h> | |
15 | #include <asm/byteorder.h> | |
38f5bd23 | 16 | #include <asm/cacheinfo.h> |
e72c4333 | 17 | #include <asm/cpufeature.h> |
2129a235 | 18 | |
2129a235 PD |
19 | /* |
20 | * These are used to set parameters in the core dumps. | |
21 | */ | |
22 | #define ELF_ARCH EM_RISCV | |
23 | ||
87309e10 | 24 | #ifndef ELF_CLASS |
2129a235 PD |
25 | #ifdef CONFIG_64BIT |
26 | #define ELF_CLASS ELFCLASS64 | |
27 | #else | |
28 | #define ELF_CLASS ELFCLASS32 | |
29 | #endif | |
87309e10 | 30 | #endif |
2129a235 | 31 | |
2129a235 | 32 | #define ELF_DATA ELFDATA2LSB |
2129a235 PD |
33 | |
34 | /* | |
35 | * This is used to ensure we don't load something for the wrong architecture. | |
36 | */ | |
f4b395e6 GR |
37 | #define elf_check_arch(x) (((x)->e_machine == EM_RISCV) && \ |
38 | ((x)->e_ident[EI_CLASS] == ELF_CLASS)) | |
2129a235 | 39 | |
f4b395e6 GR |
40 | extern bool compat_elf_check_arch(Elf32_Ehdr *hdr); |
41 | #define compat_elf_check_arch compat_elf_check_arch | |
87309e10 | 42 | |
2129a235 | 43 | #define CORE_DUMP_USE_REGSET |
9549fb35 | 44 | #define ELF_FDPIC_CORE_EFLAGS 0 |
2129a235 PD |
45 | #define ELF_EXEC_PAGESIZE (PAGE_SIZE) |
46 | ||
47 | /* | |
48 | * This is the location that an ET_DYN program is loaded if exec'ed. Typical | |
49 | * use of this is to invoke "./ld.so someprog" to test out a new version of | |
50 | * the loader. We need to make sure that it is out of the way of the program | |
51 | * that it will "exec", and that there is sufficient room for the brk. | |
52 | */ | |
add2cc6b | 53 | #define ELF_ET_DYN_BASE ((DEFAULT_MAP_WINDOW / 3) * 2) |
2129a235 | 54 | |
d5935537 | 55 | #ifdef CONFIG_64BIT |
87309e10 | 56 | #ifdef CONFIG_COMPAT |
9dc30419 | 57 | #define STACK_RND_MASK (is_compat_task() ? \ |
87309e10 GR |
58 | 0x7ff >> (PAGE_SHIFT - 12) : \ |
59 | 0x3ffff >> (PAGE_SHIFT - 12)) | |
60 | #else | |
d5935537 KW |
61 | #define STACK_RND_MASK (0x3ffff >> (PAGE_SHIFT - 12)) |
62 | #endif | |
87309e10 | 63 | #endif |
2350bd19 | 64 | |
2129a235 | 65 | /* |
2350bd19 PD |
66 | * Provides information on the availiable set of ISA extensions to userspace, |
67 | * via a bitmap that coorespends to each single-letter ISA extension. This is | |
68 | * essentially defunct, but will remain for compatibility with userspace. | |
2129a235 | 69 | */ |
50724efc | 70 | #define ELF_HWCAP riscv_get_elf_hwcap() |
2129a235 PD |
71 | extern unsigned long elf_hwcap; |
72 | ||
9549fb35 GU |
73 | #define ELF_FDPIC_PLAT_INIT(_r, _exec_map_addr, _interp_map_addr, dynamic_addr) \ |
74 | do { \ | |
75 | (_r)->a1 = _exec_map_addr; \ | |
76 | (_r)->a2 = _interp_map_addr; \ | |
77 | (_r)->a3 = dynamic_addr; \ | |
78 | } while (0) | |
79 | ||
2129a235 PD |
80 | /* |
81 | * This yields a string that ld.so will use to load implementation | |
82 | * specific libraries for optimization. This is more specific in | |
83 | * intent than poking at uname or /proc/cpuinfo. | |
84 | */ | |
85 | #define ELF_PLATFORM (NULL) | |
86 | ||
87309e10 GR |
87 | #define COMPAT_ELF_PLATFORM (NULL) |
88 | ||
2129a235 PD |
89 | #define ARCH_DLINFO \ |
90 | do { \ | |
87309e10 GR |
91 | /* \ |
92 | * Note that we add ulong after elf_addr_t because \ | |
93 | * casting current->mm->context.vdso triggers a cast \ | |
94 | * warning of cast from pointer to integer for \ | |
95 | * COMPAT ELFCLASS32. \ | |
96 | */ \ | |
2129a235 | 97 | NEW_AUX_ENT(AT_SYSINFO_EHDR, \ |
87309e10 | 98 | (elf_addr_t)(ulong)current->mm->context.vdso); \ |
38f5bd23 ZL |
99 | NEW_AUX_ENT(AT_L1I_CACHESIZE, \ |
100 | get_cache_size(1, CACHE_TYPE_INST)); \ | |
101 | NEW_AUX_ENT(AT_L1I_CACHEGEOMETRY, \ | |
102 | get_cache_geometry(1, CACHE_TYPE_INST)); \ | |
103 | NEW_AUX_ENT(AT_L1D_CACHESIZE, \ | |
104 | get_cache_size(1, CACHE_TYPE_DATA)); \ | |
105 | NEW_AUX_ENT(AT_L1D_CACHEGEOMETRY, \ | |
106 | get_cache_geometry(1, CACHE_TYPE_DATA)); \ | |
107 | NEW_AUX_ENT(AT_L2_CACHESIZE, \ | |
108 | get_cache_size(2, CACHE_TYPE_UNIFIED)); \ | |
109 | NEW_AUX_ENT(AT_L2_CACHEGEOMETRY, \ | |
110 | get_cache_geometry(2, CACHE_TYPE_UNIFIED)); \ | |
da29dbcd GH |
111 | NEW_AUX_ENT(AT_L3_CACHESIZE, \ |
112 | get_cache_size(3, CACHE_TYPE_UNIFIED)); \ | |
113 | NEW_AUX_ENT(AT_L3_CACHEGEOMETRY, \ | |
114 | get_cache_geometry(3, CACHE_TYPE_UNIFIED)); \ | |
e92f469b VC |
115 | /* \ |
116 | * Should always be nonzero unless there's a kernel bug. \ | |
117 | * If we haven't determined a sensible value to give to \ | |
118 | * userspace, omit the entry: \ | |
119 | */ \ | |
120 | if (likely(signal_minsigstksz)) \ | |
121 | NEW_AUX_ENT(AT_MINSIGSTKSZ, signal_minsigstksz); \ | |
122 | else \ | |
123 | NEW_AUX_ENT(AT_IGNORE, 0); \ | |
2129a235 | 124 | } while (0) |
9549fb35 GU |
125 | |
126 | #ifdef CONFIG_MMU | |
2129a235 PD |
127 | #define ARCH_HAS_SETUP_ADDITIONAL_PAGES |
128 | struct linux_binprm; | |
129 | extern int arch_setup_additional_pages(struct linux_binprm *bprm, | |
130 | int uses_interp); | |
6bd33e1e | 131 | #endif /* CONFIG_MMU */ |
2129a235 | 132 | |
e53d2818 NK |
133 | #define ELF_CORE_COPY_REGS(dest, regs) \ |
134 | do { \ | |
135 | *(struct user_regs_struct *)&(dest) = \ | |
136 | *(struct user_regs_struct *)regs; \ | |
137 | } while (0); | |
138 | ||
87309e10 GR |
139 | #ifdef CONFIG_COMPAT |
140 | ||
141 | #define SET_PERSONALITY(ex) \ | |
142 | do { if ((ex).e_ident[EI_CLASS] == ELFCLASS32) \ | |
143 | set_thread_flag(TIF_32BIT); \ | |
144 | else \ | |
145 | clear_thread_flag(TIF_32BIT); \ | |
146 | if (personality(current->personality) != PER_LINUX32) \ | |
147 | set_personality(PER_LINUX | \ | |
148 | (current->personality & (~PER_MASK))); \ | |
149 | } while (0) | |
150 | ||
151 | #define COMPAT_ELF_ET_DYN_BASE ((TASK_SIZE_32 / 3) * 2) | |
152 | ||
153 | /* rv32 registers */ | |
154 | typedef compat_ulong_t compat_elf_greg_t; | |
155 | typedef compat_elf_greg_t compat_elf_gregset_t[ELF_NGREG]; | |
156 | ||
3092eb45 GR |
157 | extern int compat_arch_setup_additional_pages(struct linux_binprm *bprm, |
158 | int uses_interp); | |
159 | #define compat_arch_setup_additional_pages \ | |
160 | compat_arch_setup_additional_pages | |
161 | ||
87309e10 | 162 | #endif /* CONFIG_COMPAT */ |
2129a235 | 163 | #endif /* _ASM_RISCV_ELF_H */ |