1 /* SPDX-License-Identifier: GPL-2.0-only */ 2 /* 3 * linux/arch/arm/lib/getuser.S 4 * 5 * Copyright (C) 2001 Russell King 6 * 7 * Idea from x86 version, (C) Copyright 1998 8 * 9 * These functions have a non-standard call in 10 * efficient, especially as they return an err 11 * the "real" return value. 12 * 13 * __get_user_X 14 * 15 * Inputs: r0 contains the address 16 * r1 contains the address limit, 17 * Outputs: r0 is the error code 18 * r2, r3 contains the zero-exten 19 * lr corrupted 20 * 21 * No other registers must be altered. (see < 22 * for specific ASM register usage). 23 * 24 * Note that ADDR_LIMIT is either 0 or 0xc0000 25 * Note also that it is intended that __get_us 26 */ 27 #include <linux/linkage.h> 28 #include <asm/assembler.h> 29 #include <asm/errno.h> 30 #include <asm/domain.h> 31 32 ENTRY(__get_user_1) 33 check_uaccess r0, 1, r1, r2, __get_use 34 1: TUSER(ldrb) r2, [r0] 35 mov r0, #0 36 ret lr 37 ENDPROC(__get_user_1) 38 _ASM_NOKPROBE(__get_user_1) 39 40 ENTRY(__get_user_2) 41 check_uaccess r0, 2, r1, r2, __get_use 42 #if __LINUX_ARM_ARCH__ >= 6 43 44 2: TUSER(ldrh) r2, [r0] 45 46 #else 47 48 #ifdef CONFIG_CPU_USE_DOMAINS 49 rb .req ip 50 2: ldrbt r2, [r0], #1 51 3: ldrbt rb, [r0], #0 52 #else 53 rb .req r0 54 2: ldrb r2, [r0] 55 3: ldrb rb, [r0, #1] 56 #endif 57 #ifndef __ARMEB__ 58 orr r2, r2, rb, lsl #8 59 #else 60 orr r2, rb, r2, lsl #8 61 #endif 62 63 #endif /* __LINUX_ARM_ARCH__ >= 6 */ 64 65 mov r0, #0 66 ret lr 67 ENDPROC(__get_user_2) 68 _ASM_NOKPROBE(__get_user_2) 69 70 ENTRY(__get_user_4) 71 check_uaccess r0, 4, r1, r2, __get_use 72 4: TUSER(ldr) r2, [r0] 73 mov r0, #0 74 ret lr 75 ENDPROC(__get_user_4) 76 _ASM_NOKPROBE(__get_user_4) 77 78 ENTRY(__get_user_8) 79 check_uaccess r0, 8, r1, r2, __get_use 80 #ifdef CONFIG_THUMB2_KERNEL 81 5: TUSER(ldr) r2, [r0] 82 6: TUSER(ldr) r3, [r0, #4] 83 #else 84 5: TUSER(ldr) r2, [r0], #4 85 6: TUSER(ldr) r3, [r0] 86 #endif 87 mov r0, #0 88 ret lr 89 ENDPROC(__get_user_8) 90 _ASM_NOKPROBE(__get_user_8) 91 92 #ifdef __ARMEB__ 93 ENTRY(__get_user_32t_8) 94 check_uaccess r0, 8, r1, r2, __get_use 95 #ifdef CONFIG_CPU_USE_DOMAINS 96 add r0, r0, #4 97 7: ldrt r2, [r0] 98 #else 99 7: ldr r2, [r0, #4] 100 #endif 101 mov r0, #0 102 ret lr 103 ENDPROC(__get_user_32t_8) 104 _ASM_NOKPROBE(__get_user_32t_8) 105 106 ENTRY(__get_user_64t_1) 107 check_uaccess r0, 1, r1, r2, __get_use 108 8: TUSER(ldrb) r3, [r0] 109 mov r0, #0 110 ret lr 111 ENDPROC(__get_user_64t_1) 112 _ASM_NOKPROBE(__get_user_64t_1) 113 114 ENTRY(__get_user_64t_2) 115 check_uaccess r0, 2, r1, r2, __get_use 116 #ifdef CONFIG_CPU_USE_DOMAINS 117 rb .req ip 118 9: ldrbt r3, [r0], #1 119 10: ldrbt rb, [r0], #0 120 #else 121 rb .req r0 122 9: ldrb r3, [r0] 123 10: ldrb rb, [r0, #1] 124 #endif 125 orr r3, rb, r3, lsl #8 126 mov r0, #0 127 ret lr 128 ENDPROC(__get_user_64t_2) 129 _ASM_NOKPROBE(__get_user_64t_2) 130 131 ENTRY(__get_user_64t_4) 132 check_uaccess r0, 4, r1, r2, __get_use 133 11: TUSER(ldr) r3, [r0] 134 mov r0, #0 135 ret lr 136 ENDPROC(__get_user_64t_4) 137 _ASM_NOKPROBE(__get_user_64t_4) 138 #endif 139 140 __get_user_bad8: 141 mov r3, #0 142 __get_user_bad: 143 mov r2, #0 144 mov r0, #-EFAULT 145 ret lr 146 ENDPROC(__get_user_bad) 147 ENDPROC(__get_user_bad8) 148 _ASM_NOKPROBE(__get_user_bad) 149 _ASM_NOKPROBE(__get_user_bad8) 150 151 .pushsection __ex_table, "a" 152 .long 1b, __get_user_bad 153 .long 2b, __get_user_bad 154 #if __LINUX_ARM_ARCH__ < 6 155 .long 3b, __get_user_bad 156 #endif 157 .long 4b, __get_user_bad 158 .long 5b, __get_user_bad8 159 .long 6b, __get_user_bad8 160 #ifdef __ARMEB__ 161 .long 7b, __get_user_bad 162 .long 8b, __get_user_bad8 163 .long 9b, __get_user_bad8 164 .long 10b, __get_user_bad8 165 .long 11b, __get_user_bad8 166 #endif 167 .popsection
Linux® is a registered trademark of Linus Torvalds in the United States and other countries.
TOMOYO® is a registered trademark of NTT DATA CORPORATION.