aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMichal Simek2012-10-15 04:49:22 -0500
committerMichal Simek2012-12-13 07:38:53 -0600
commitbf0e12c753ee71fa9fcb1210e5b961ba1df7981f (patch)
tree9c67cd157b2fe1403cfbe25f29fc2dc962b3c964 /arch/microblaze
parent4336bac52b85201cf92c775940ee70097471c4e2 (diff)
downloadam43-linux-kernel-bf0e12c753ee71fa9fcb1210e5b961ba1df7981f.tar.gz
am43-linux-kernel-bf0e12c753ee71fa9fcb1210e5b961ba1df7981f.tar.xz
am43-linux-kernel-bf0e12c753ee71fa9fcb1210e5b961ba1df7981f.zip
microblaze: uaccess.h: Fix timerfd syscall
__pu_val must be volatile to ensure that the value is not lost. It was causing the problem with timerfd syscall where using inline asm at the end of function call doesn't save u64 bit value to the stack. In comparison both cases you can find out this fragment where you can see the first part which is saved u64 value to stack and then using it in __put_user_asm_8 macro. Origin broken implementation misses the first two swi instructions. swi r22, r1, 28 /* missing without volatile */ swi r23, r1, 32 ... addik r4, r1, 28 lwi r3, r4, 0 swi r3, r25, 0 lwi r3, r4, 4 swi r3, r25, 4 addk r3, r0, r0 NOTE: Moving __put_val initialization after declaration has not impact on this bug. It is just coding style issue. Signed-off-by: Michal Simek <monstr@monstr.eu>
Diffstat (limited to 'arch/microblaze')
-rw-r--r--arch/microblaze/include/asm/uaccess.h3
1 files changed, 1 insertions, 2 deletions
diff --git a/arch/microblaze/include/asm/uaccess.h b/arch/microblaze/include/asm/uaccess.h
index ef25f7538d4..927540d3cb7 100644
--- a/arch/microblaze/include/asm/uaccess.h
+++ b/arch/microblaze/include/asm/uaccess.h
@@ -298,11 +298,10 @@ extern long __user_bad(void);
298 298
299#define __put_user_check(x, ptr, size) \ 299#define __put_user_check(x, ptr, size) \
300({ \ 300({ \
301 typeof(*(ptr)) __pu_val; \ 301 typeof(*(ptr)) volatile __pu_val = x; \
302 typeof(*(ptr)) __user *__pu_addr = (ptr); \ 302 typeof(*(ptr)) __user *__pu_addr = (ptr); \
303 int __pu_err = 0; \ 303 int __pu_err = 0; \
304 \ 304 \
305 __pu_val = (x); \
306 if (access_ok(VERIFY_WRITE, __pu_addr, size)) { \ 305 if (access_ok(VERIFY_WRITE, __pu_addr, size)) { \
307 switch (size) { \ 306 switch (size) { \
308 case 1: \ 307 case 1: \