diff options
| -rw-r--r-- | arch/microblaze/include/asm/uaccess.h | 81 |
1 files changed, 36 insertions, 45 deletions
diff --git a/arch/microblaze/include/asm/uaccess.h b/arch/microblaze/include/asm/uaccess.h index fe954b394fdc..1af92025fff9 100644 --- a/arch/microblaze/include/asm/uaccess.h +++ b/arch/microblaze/include/asm/uaccess.h | |||
| @@ -71,6 +71,9 @@ struct exception_table_entry { | |||
| 71 | unsigned long insn, fixup; | 71 | unsigned long insn, fixup; |
| 72 | }; | 72 | }; |
| 73 | 73 | ||
| 74 | /* Returns 0 if exception not found and fixup otherwise. */ | ||
| 75 | extern unsigned long search_exception_table(unsigned long); | ||
| 76 | |||
| 74 | #ifndef CONFIG_MMU | 77 | #ifndef CONFIG_MMU |
| 75 | 78 | ||
| 76 | /* Check against bounds of physical memory */ | 79 | /* Check against bounds of physical memory */ |
| @@ -108,6 +111,39 @@ static inline int ___range_ok(unsigned long addr, unsigned long size) | |||
| 108 | # define __EX_TABLE_SECTION ".section .discard,\"a\"\n" | 111 | # define __EX_TABLE_SECTION ".section .discard,\"a\"\n" |
| 109 | #endif | 112 | #endif |
| 110 | 113 | ||
| 114 | extern unsigned long __copy_tofrom_user(void __user *to, | ||
| 115 | const void __user *from, unsigned long size); | ||
| 116 | |||
| 117 | /* Return: number of not copied bytes, i.e. 0 if OK or non-zero if fail. */ | ||
| 118 | static inline unsigned long __must_check __clear_user(void __user *to, | ||
| 119 | unsigned long n) | ||
| 120 | { | ||
| 121 | /* normal memset with two words to __ex_table */ | ||
| 122 | __asm__ __volatile__ ( \ | ||
| 123 | "1: sb r0, %2, r0;" \ | ||
| 124 | " addik %0, %0, -1;" \ | ||
| 125 | " bneid %0, 1b;" \ | ||
| 126 | " addik %2, %2, 1;" \ | ||
| 127 | "2: " \ | ||
| 128 | __EX_TABLE_SECTION \ | ||
| 129 | ".word 1b,2b;" \ | ||
| 130 | ".previous;" \ | ||
| 131 | : "=r"(n) \ | ||
| 132 | : "0"(n), "r"(to) | ||
| 133 | ); | ||
| 134 | return n; | ||
| 135 | } | ||
| 136 | |||
| 137 | static inline unsigned long __must_check clear_user(void __user *to, | ||
| 138 | unsigned long n) | ||
| 139 | { | ||
| 140 | might_sleep(); | ||
| 141 | if (unlikely(!access_ok(VERIFY_WRITE, to, n))) | ||
| 142 | return n; | ||
| 143 | |||
| 144 | return __clear_user(to, n); | ||
| 145 | } | ||
| 146 | |||
| 111 | #ifndef CONFIG_MMU | 147 | #ifndef CONFIG_MMU |
| 112 | 148 | ||
| 113 | /* Undefined function to trigger linker error */ | 149 | /* Undefined function to trigger linker error */ |
| @@ -173,53 +209,11 @@ extern int bad_user_access_length(void); | |||
| 173 | #define __copy_from_user_inatomic(to, from, n) \ | 209 | #define __copy_from_user_inatomic(to, from, n) \ |
| 174 | (__copy_from_user((to), (from), (n))) | 210 | (__copy_from_user((to), (from), (n))) |
| 175 | 211 | ||
| 176 | #define __clear_user(addr, n) (memset((void *)(addr), 0, (n)), 0) | ||
| 177 | |||
| 178 | /* stejne s MMU */ | ||
| 179 | static inline unsigned long clear_user(void *addr, unsigned long size) | ||
| 180 | { | ||
| 181 | if (access_ok(VERIFY_WRITE, addr, size)) | ||
| 182 | size = __clear_user(addr, size); | ||
| 183 | return size; | ||
| 184 | } | ||
| 185 | |||
| 186 | /* Returns 0 if exception not found and fixup otherwise. */ | ||
| 187 | extern unsigned long search_exception_table(unsigned long); | ||
| 188 | |||
| 189 | extern long strncpy_from_user(char *dst, const char *src, long count); | 212 | extern long strncpy_from_user(char *dst, const char *src, long count); |
| 190 | extern long strnlen_user(const char *src, long count); | 213 | extern long strnlen_user(const char *src, long count); |
| 191 | 214 | ||
| 192 | #else /* CONFIG_MMU */ | 215 | #else /* CONFIG_MMU */ |
| 193 | 216 | ||
| 194 | /* Return: number of not copied bytes, i.e. 0 if OK or non-zero if fail. */ | ||
| 195 | static inline unsigned long __must_check __clear_user(void __user *to, | ||
| 196 | unsigned long n) | ||
| 197 | { | ||
| 198 | /* normal memset with two words to __ex_table */ | ||
| 199 | __asm__ __volatile__ ( \ | ||
| 200 | "1: sb r0, %2, r0;" \ | ||
| 201 | " addik %0, %0, -1;" \ | ||
| 202 | " bneid %0, 1b;" \ | ||
| 203 | " addik %2, %2, 1;" \ | ||
| 204 | "2: " \ | ||
| 205 | __EX_TABLE_SECTION \ | ||
| 206 | ".word 1b,2b;" \ | ||
| 207 | ".previous;" \ | ||
| 208 | : "=r"(n) \ | ||
| 209 | : "0"(n), "r"(to) | ||
| 210 | ); | ||
| 211 | return n; | ||
| 212 | } | ||
| 213 | |||
| 214 | static inline unsigned long __must_check clear_user(void __user *to, | ||
| 215 | unsigned long n) | ||
| 216 | { | ||
| 217 | might_sleep(); | ||
| 218 | if (unlikely(!access_ok(VERIFY_WRITE, to, n))) | ||
| 219 | return n; | ||
| 220 | return __clear_user(to, n); | ||
| 221 | } | ||
| 222 | |||
| 223 | /* put_user and get_user macros */ | 217 | /* put_user and get_user macros */ |
| 224 | 218 | ||
| 225 | extern long __user_bad(void); | 219 | extern long __user_bad(void); |
| @@ -372,9 +366,6 @@ extern long __user_bad(void); | |||
| 372 | ? __put_user((x), (ptr)) : -EFAULT; \ | 366 | ? __put_user((x), (ptr)) : -EFAULT; \ |
| 373 | }) | 367 | }) |
| 374 | 368 | ||
| 375 | extern unsigned long __copy_tofrom_user(void __user *to, | ||
| 376 | const void __user *from, unsigned long size); | ||
| 377 | |||
| 378 | #define __copy_from_user(to, from, n) \ | 369 | #define __copy_from_user(to, from, n) \ |
| 379 | __copy_tofrom_user((__force void __user *)(to), \ | 370 | __copy_tofrom_user((__force void __user *)(to), \ |
| 380 | (void __user *)(from), (n)) | 371 | (void __user *)(from), (n)) |
