| Linus Torvalds | 1da177e | 2005-04-16 15:20:36 -0700 | [diff] [blame] | 1 | /*  | 
 | 2 |  * Copyright (C) 2001 Chris Emerson (cemerson@chiark.greenend.org.uk) | 
 | 3 |  * Copyright (C) 2001, 2002 Jeff Dike (jdike@karaya.com) | 
 | 4 |  * Licensed under the GPL | 
 | 5 |  */ | 
 | 6 |  | 
 | 7 | #include <setjmp.h> | 
 | 8 | #include <string.h> | 
 | 9 |  | 
 | 10 | /* These are here rather than tt/uaccess.c because skas mode needs them in | 
 | 11 |  * order to do SIGBUS recovery when a tmpfs mount runs out of room. | 
 | 12 |  */ | 
 | 13 |  | 
 | 14 | unsigned long __do_user_copy(void *to, const void *from, int n, | 
 | 15 | 			     void **fault_addr, void **fault_catcher, | 
 | 16 | 			     void (*op)(void *to, const void *from, | 
 | 17 | 					int n), int *faulted_out) | 
 | 18 | { | 
 | 19 | 	unsigned long *faddrp = (unsigned long *) fault_addr, ret; | 
 | 20 |  | 
 | 21 | 	sigjmp_buf jbuf; | 
 | 22 | 	*fault_catcher = &jbuf; | 
 | 23 | 	if(sigsetjmp(jbuf, 1) == 0){ | 
 | 24 | 		(*op)(to, from, n); | 
 | 25 | 		ret = 0; | 
 | 26 | 		*faulted_out = 0; | 
 | 27 | 	}  | 
 | 28 | 	else { | 
 | 29 | 		ret = *faddrp; | 
 | 30 | 		*faulted_out = 1; | 
 | 31 | 	} | 
 | 32 | 	*fault_addr = NULL; | 
 | 33 | 	*fault_catcher = NULL; | 
 | 34 | 	return ret; | 
 | 35 | } | 
 | 36 |  | 
 | 37 | void __do_copy(void *to, const void *from, int n) | 
 | 38 | { | 
 | 39 | 	memcpy(to, from, n); | 
 | 40 | }	 | 
 | 41 |  | 
 | 42 |  | 
 | 43 | int __do_copy_to_user(void *to, const void *from, int n, | 
 | 44 | 		      void **fault_addr, void **fault_catcher) | 
 | 45 | { | 
 | 46 | 	unsigned long fault; | 
 | 47 | 	int faulted; | 
 | 48 |  | 
 | 49 | 	fault = __do_user_copy(to, from, n, fault_addr, fault_catcher, | 
 | 50 | 			       __do_copy, &faulted); | 
 | 51 | 	if(!faulted) return(0); | 
 | 52 | 	else return(n - (fault - (unsigned long) to)); | 
 | 53 | } | 
 | 54 |  | 
 | 55 | /* | 
 | 56 |  * Overrides for Emacs so that we follow Linus's tabbing style. | 
 | 57 |  * Emacs will notice this stuff at the end of the file and automatically | 
 | 58 |  * adjust the settings for this buffer only.  This must remain at the end | 
 | 59 |  * of the file. | 
 | 60 |  * --------------------------------------------------------------------------- | 
 | 61 |  * Local variables: | 
 | 62 |  * c-file-style: "linux" | 
 | 63 |  * End: | 
 | 64 |  */ |