]>
Commit | Line | Data |
---|---|---|
0156411b CM |
1 | /* |
2 | * arch/arm64/kernel/sys32.c | |
3 | * | |
4 | * Copyright (C) 2015 ARM Ltd. | |
5 | * | |
6 | * This program is free software(void); 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 | * This program is distributed in the hope that it will be useful, | |
11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | |
12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
13 | * GNU General Public License for more details. | |
14 | * | |
15 | * You should have received a copy of the GNU General Public License | |
16 | * along with this program. If not, see <http(void);//www.gnu.org/licenses/>. | |
17 | */ | |
18 | ||
19 | /* | |
20 | * Needed to avoid conflicting __NR_* macros between uapi/asm/unistd.h and | |
21 | * asm/unistd32.h. | |
22 | */ | |
23 | #define __COMPAT_SYSCALL_NR | |
24 | ||
55f84926 | 25 | #include <linux/compat.h> |
0156411b CM |
26 | #include <linux/compiler.h> |
27 | #include <linux/syscalls.h> | |
28 | ||
27d83e68 MR |
29 | #include <asm/syscall.h> |
30 | ||
3085e164 MR |
31 | asmlinkage long compat_sys_sigreturn(void); |
32 | asmlinkage long compat_sys_rt_sigreturn(void); | |
55f84926 MR |
33 | |
34 | COMPAT_SYSCALL_DEFINE3(aarch32_statfs64, const char __user *, pathname, | |
35 | compat_size_t, sz, struct compat_statfs64 __user *, buf) | |
36 | { | |
37 | /* | |
38 | * 32-bit ARM applies an OABI compatibility fixup to statfs64 and | |
39 | * fstatfs64 regardless of whether OABI is in use, and therefore | |
40 | * arbitrary binaries may rely upon it, so we must do the same. | |
41 | * For more details, see commit: | |
42 | * | |
43 | * 713c481519f19df9 ("[ARM] 3108/2: old ABI compat: statfs64 and | |
44 | * fstatfs64") | |
45 | */ | |
46 | if (sz == 88) | |
47 | sz = 84; | |
48 | ||
49 | return kcompat_sys_statfs64(pathname, sz, buf); | |
50 | } | |
51 | ||
52 | COMPAT_SYSCALL_DEFINE3(aarch32_fstatfs64, unsigned int, fd, compat_size_t, sz, | |
53 | struct compat_statfs64 __user *, buf) | |
54 | { | |
55 | /* see aarch32_statfs64 */ | |
56 | if (sz == 88) | |
57 | sz = 84; | |
58 | ||
59 | return kcompat_sys_fstatfs64(fd, sz, buf); | |
60 | } | |
61 | ||
62 | /* | |
63 | * Note: off_4k is always in units of 4K. If we can't do the | |
64 | * requested offset because it is not page-aligned, we return -EINVAL. | |
65 | */ | |
66 | COMPAT_SYSCALL_DEFINE6(aarch32_mmap2, unsigned long, addr, unsigned long, len, | |
67 | unsigned long, prot, unsigned long, flags, | |
68 | unsigned long, fd, unsigned long, off_4k) | |
69 | { | |
70 | if (off_4k & (~PAGE_MASK >> 12)) | |
71 | return -EINVAL; | |
72 | ||
73 | off_4k >>= (PAGE_SHIFT - 12); | |
74 | ||
75 | return ksys_mmap_pgoff(addr, len, prot, flags, fd, off_4k); | |
76 | } | |
77 | ||
78 | #ifdef CONFIG_CPU_BIG_ENDIAN | |
79 | #define arg_u32p(name) u32, name##_hi, u32, name##_lo | |
80 | #else | |
81 | #define arg_u32p(name) u32, name##_lo, u32, name##_hi | |
82 | #endif | |
83 | ||
84 | #define arg_u64(name) (((u64)name##_hi << 32) | name##_lo) | |
85 | ||
86 | COMPAT_SYSCALL_DEFINE6(aarch32_pread64, unsigned int, fd, char __user *, buf, | |
87 | size_t, count, u32, __pad, arg_u32p(pos)) | |
88 | { | |
89 | return ksys_pread64(fd, buf, count, arg_u64(pos)); | |
90 | } | |
91 | ||
92 | COMPAT_SYSCALL_DEFINE6(aarch32_pwrite64, unsigned int, fd, | |
93 | const char __user *, buf, size_t, count, u32, __pad, | |
94 | arg_u32p(pos)) | |
95 | { | |
96 | return ksys_pwrite64(fd, buf, count, arg_u64(pos)); | |
97 | } | |
98 | ||
99 | COMPAT_SYSCALL_DEFINE4(aarch32_truncate64, const char __user *, pathname, | |
100 | u32, __pad, arg_u32p(length)) | |
101 | { | |
102 | return ksys_truncate(pathname, arg_u64(length)); | |
103 | } | |
104 | ||
105 | COMPAT_SYSCALL_DEFINE4(aarch32_ftruncate64, unsigned int, fd, u32, __pad, | |
106 | arg_u32p(length)) | |
107 | { | |
108 | return ksys_ftruncate(fd, arg_u64(length)); | |
109 | } | |
110 | ||
111 | COMPAT_SYSCALL_DEFINE5(aarch32_readahead, int, fd, u32, __pad, | |
112 | arg_u32p(offset), size_t, count) | |
113 | { | |
114 | return ksys_readahead(fd, arg_u64(offset), count); | |
115 | } | |
116 | ||
117 | COMPAT_SYSCALL_DEFINE6(aarch32_fadvise64_64, int, fd, int, advice, | |
118 | arg_u32p(offset), arg_u32p(len)) | |
119 | { | |
120 | return ksys_fadvise64_64(fd, arg_u64(offset), arg_u64(len), advice); | |
121 | } | |
122 | ||
123 | COMPAT_SYSCALL_DEFINE6(aarch32_sync_file_range2, int, fd, unsigned int, flags, | |
124 | arg_u32p(offset), arg_u32p(nbytes)) | |
125 | { | |
126 | return ksys_sync_file_range(fd, arg_u64(offset), arg_u64(nbytes), | |
127 | flags); | |
128 | } | |
129 | ||
130 | COMPAT_SYSCALL_DEFINE6(aarch32_fallocate, int, fd, int, mode, | |
131 | arg_u32p(offset), arg_u32p(len)) | |
132 | { | |
133 | return ksys_fallocate(fd, mode, arg_u64(offset), arg_u64(len)); | |
134 | } | |
0156411b | 135 | |
4378a7d4 MR |
136 | #undef __SYSCALL |
137 | #define __SYSCALL(nr, sym) asmlinkage long __arm64_##sym(const struct pt_regs *); | |
138 | #include <asm/unistd32.h> | |
139 | ||
0156411b | 140 | #undef __SYSCALL |
1e29ab31 | 141 | #define __SYSCALL(nr, sym) [nr] = __arm64_##sym, |
0156411b | 142 | |
80d63bc3 | 143 | const syscall_fn_t compat_sys_call_table[__NR_compat_syscalls] = { |
1e29ab31 | 144 | [0 ... __NR_compat_syscalls - 1] = __arm64_sys_ni_syscall, |
0156411b CM |
145 | #include <asm/unistd32.h> |
146 | }; |