fedora core 6 1.2949 + vserver 2.2.0
[linux-2.6.git] / include / asm-sparc / uaccess.h
index 68e718b..3cf132e 100644 (file)
@@ -18,7 +18,7 @@
 
 #ifndef __ASSEMBLY__
 
-/* Sparc is not segmented, however we need to be able to fool verify_area()
+/* Sparc is not segmented, however we need to be able to fool access_ok()
  * when doing system calls from kernel mode legitimately.
  *
  * "For historical reasons, these macros are grossly misnamed." -Linus
  * No one can read/write anything from userland in the kernel space by setting
  * large size and address near to PAGE_OFFSET - a fault will break his intentions.
  */
-#define __user_ok(addr,size) ((addr) < STACK_TOP)
+#define __user_ok(addr, size) ({ (void)(size); (addr) < STACK_TOP; })
 #define __kernel_ok (segment_eq(get_fs(), KERNEL_DS))
 #define __access_ok(addr,size) (__user_ok((addr) & get_fs().seg,(size)))
-#define access_ok(type,addr,size) __access_ok((unsigned long)(addr),(size))
-
-static inline int verify_area(int type, const void __user * addr, unsigned long size)
-{
-       return access_ok(type,addr,size)?0:-EFAULT;
-}
+#define access_ok(type, addr, size)                                    \
+       ({ (void)(type); __access_ok((unsigned long)(addr), size); })
 
 /*
  * The exception table consists of pairs of addresses: the first is the
@@ -94,10 +90,12 @@ extern void __ret_efault(void);
  */
 #define put_user(x,ptr) ({ \
 unsigned long __pu_addr = (unsigned long)(ptr); \
+__chk_user_ptr(ptr); \
 __put_user_check((__typeof__(*(ptr)))(x),__pu_addr,sizeof(*(ptr))); })
 
 #define get_user(x,ptr) ({ \
 unsigned long __gu_addr = (unsigned long)(ptr); \
+__chk_user_ptr(ptr); \
 __get_user_check((x),__gu_addr,sizeof(*(ptr)),__typeof__(*(ptr))); })
 
 /*
@@ -109,7 +107,7 @@ __get_user_check((x),__gu_addr,sizeof(*(ptr)),__typeof__(*(ptr))); })
 #define __get_user(x,ptr) __get_user_nocheck((x),(ptr),sizeof(*(ptr)),__typeof__(*(ptr)))
 
 struct __large_struct { unsigned long buf[100]; };
-#define __m(x) ((struct __large_struct *)(x))
+#define __m(x) ((struct __large_struct __user *)(x))
 
 #define __put_user_check(x,addr,size) ({ \
 register int __pu_ret; \
@@ -122,17 +120,6 @@ case 8: __put_user_asm(x,d,addr,__pu_ret); break; \
 default: __pu_ret = __put_user_bad(); break; \
 } } else { __pu_ret = -EFAULT; } __pu_ret; })
 
-#define __put_user_check_ret(x,addr,size,retval) ({ \
-register int __foo __asm__ ("l1"); \
-if (__access_ok(addr,size)) { \
-switch (size) { \
-case 1: __put_user_asm_ret(x,b,addr,retval,__foo); break; \
-case 2: __put_user_asm_ret(x,h,addr,retval,__foo); break; \
-case 4: __put_user_asm_ret(x,,addr,retval,__foo); break; \
-case 8: __put_user_asm_ret(x,d,addr,retval,__foo); break; \
-default: if (__put_user_bad()) return retval; break; \
-} } else return retval; })
-
 #define __put_user_nocheck(x,addr,size) ({ \
 register int __pu_ret; \
 switch (size) { \
@@ -143,16 +130,6 @@ case 8: __put_user_asm(x,d,addr,__pu_ret); break; \
 default: __pu_ret = __put_user_bad(); break; \
 } __pu_ret; })
 
-#define __put_user_nocheck_ret(x,addr,size,retval) ({ \
-register int __foo __asm__ ("l1"); \
-switch (size) { \
-case 1: __put_user_asm_ret(x,b,addr,retval,__foo); break; \
-case 2: __put_user_asm_ret(x,h,addr,retval,__foo); break; \
-case 4: __put_user_asm_ret(x,,addr,retval,__foo); break; \
-case 8: __put_user_asm_ret(x,d,addr,retval,__foo); break; \
-default: if (__put_user_bad()) return retval; break; \
-} })
-
 #define __put_user_asm(x,size,addr,ret)                                        \
 __asm__ __volatile__(                                                  \
        "/* Put user asm, inline. */\n"                                 \
@@ -172,32 +149,6 @@ __asm__ __volatile__(                                                      \
        : "=&r" (ret) : "r" (x), "m" (*__m(addr)),                      \
         "i" (-EFAULT))
 
-#define __put_user_asm_ret(x,size,addr,ret,foo)                                \
-if (__builtin_constant_p(ret) && ret == -EFAULT)                       \
-__asm__ __volatile__(                                                  \
-       "/* Put user asm ret, inline. */\n"                             \
-"1:\t" "st"#size " %1, %2\n\n\t"                                       \
-       ".section __ex_table,#alloc\n\t"                                \
-       ".align 4\n\t"                                                  \
-       ".word  1b, __ret_efault\n\n\t"                                 \
-       ".previous\n\n\t"                                               \
-       : "=r" (foo) : "r" (x), "m" (*__m(addr)));                      \
-else                                                                   \
-__asm__ __volatile(                                                    \
-       "/* Put user asm ret, inline. */\n"                             \
-"1:\t" "st"#size " %1, %2\n\n\t"                                       \
-       ".section .fixup,#alloc,#execinstr\n\t"                         \
-       ".align 4\n"                                                    \
-"3:\n\t"                                                               \
-       "ret\n\t"                                                       \
-       " restore %%g0, %3, %%o0\n\t"                                   \
-       ".previous\n\n\t"                                               \
-       ".section __ex_table,#alloc\n\t"                                \
-       ".align 4\n\t"                                                  \
-       ".word  1b, 3b\n\n\t"                                           \
-       ".previous\n\n\t"                                               \
-       : "=r" (foo) : "r" (x), "m" (*__m(addr)), "i" (ret))
-
 extern int __put_user_bad(void);
 
 #define __get_user_check(x,addr,size,type) ({ \
@@ -292,34 +243,37 @@ __asm__ __volatile__(                                                     \
 
 extern int __get_user_bad(void);
 
-extern unsigned long __copy_user(void *to, const void *from, unsigned long size);
+extern unsigned long __copy_user(void __user *to, const void __user *from, unsigned long size);
 
 static inline unsigned long copy_to_user(void __user *to, const void *from, unsigned long n)
 {
        if (n && __access_ok((unsigned long) to, n))
-               return __copy_user((void *) to, from, n);
+               return __copy_user(to, (__force void __user *) from, n);
        else
                return n;
 }
 
 static inline unsigned long __copy_to_user(void __user *to, const void *from, unsigned long n)
 {
-       return __copy_user((void *)to, from, n);
+       return __copy_user(to, (__force void __user *) from, n);
 }
 
 static inline unsigned long copy_from_user(void *to, const void __user *from, unsigned long n)
 {
        if (n && __access_ok((unsigned long) from, n))
-               return __copy_user(to, (void *) from, n);
+               return __copy_user((__force void __user *) to, from, n);
        else
                return n;
 }
 
 static inline unsigned long __copy_from_user(void *to, const void __user *from, unsigned long n)
 {
-       return __copy_user(to, (void *)from, n);
+       return __copy_user((__force void __user *) to, from, n);
 }
 
+#define __copy_to_user_inatomic __copy_to_user
+#define __copy_from_user_inatomic __copy_from_user
+
 static inline unsigned long __clear_user(void __user *addr, unsigned long size)
 {
        unsigned long ret;