1 /*
2 * Copyright (c) 2012 The Native Client Authors. All rights reserved.
3 * Use of this source code is governed by a BSD-style license that can be
4 * found in the LICENSE file.
5 */
6
7 #include <string.h>
8
9 #if defined(MEMORY_SANITIZER)
10 #include <sanitizer/msan_interface.h>
11 #endif
12
13 #include "native_client/src/trusted/service_runtime/nacl_copy.h"
14
15 #include "native_client/src/shared/platform/nacl_check.h"
16 #include "native_client/src/shared/platform/nacl_sync_checked.h"
17 #include "native_client/src/trusted/service_runtime/sel_ldr.h"
18
NaClCopyInFromUser(struct NaClApp * nap,void * dst_sys_ptr,uintptr_t src_usr_addr,size_t num_bytes)19 int NaClCopyInFromUser(struct NaClApp *nap,
20 void *dst_sys_ptr,
21 uintptr_t src_usr_addr,
22 size_t num_bytes) {
23 uintptr_t src_sys_addr;
24
25 src_sys_addr = NaClUserToSysAddrRange(nap, src_usr_addr, num_bytes);
26 if (kNaClBadAddress == src_sys_addr) {
27 return 0;
28 }
29 NaClCopyTakeLock(nap);
30 memcpy((void *) dst_sys_ptr, (void *) src_sys_addr, num_bytes);
31 NaClCopyDropLock(nap);
32
33 return 1;
34 }
35
NaClCopyInFromUserAndDropLock(struct NaClApp * nap,void * dst_sys_ptr,uintptr_t src_usr_addr,size_t num_bytes)36 int NaClCopyInFromUserAndDropLock(struct NaClApp *nap,
37 void *dst_sys_ptr,
38 uintptr_t src_usr_addr,
39 size_t num_bytes) {
40 uintptr_t src_sys_addr;
41
42 src_sys_addr = NaClUserToSysAddrRange(nap, src_usr_addr, num_bytes);
43 if (kNaClBadAddress == src_sys_addr) {
44 return 0;
45 }
46
47 memcpy((void *) dst_sys_ptr, (void *) src_sys_addr, num_bytes);
48 NaClCopyDropLock(nap);
49
50 return 1;
51 }
52
NaClCopyInFromUserZStr(struct NaClApp * nap,char * dst_buffer,size_t dst_buffer_bytes,uintptr_t src_usr_addr)53 int NaClCopyInFromUserZStr(struct NaClApp *nap,
54 char *dst_buffer,
55 size_t dst_buffer_bytes,
56 uintptr_t src_usr_addr) {
57 uintptr_t src_sys_addr;
58
59 CHECK(dst_buffer_bytes > 0);
60 src_sys_addr = NaClUserToSysAddr(nap, src_usr_addr);
61 if (kNaClBadAddress == src_sys_addr) {
62 dst_buffer[0] = '\0';
63 return 0;
64 }
65 NaClCopyTakeLock(nap);
66 strncpy(dst_buffer, (char *) src_sys_addr, dst_buffer_bytes);
67 NaClCopyDropLock(nap);
68
69 /* POSIX strncpy pads with NUL characters */
70 if (dst_buffer[dst_buffer_bytes - 1] != '\0') {
71 dst_buffer[dst_buffer_bytes - 1] = '\0';
72 return 0;
73 }
74 return 1;
75 }
76
77
NaClCopyOutToUser(struct NaClApp * nap,uintptr_t dst_usr_addr,const void * src_sys_ptr,size_t num_bytes)78 int NaClCopyOutToUser(struct NaClApp *nap,
79 uintptr_t dst_usr_addr,
80 const void *src_sys_ptr,
81 size_t num_bytes) {
82 uintptr_t dst_sys_addr;
83
84 dst_sys_addr = NaClUserToSysAddrRange(nap, dst_usr_addr, num_bytes);
85 if (kNaClBadAddress == dst_sys_addr) {
86 return 0;
87 }
88
89 #if defined(MEMORY_SANITIZER)
90 /*
91 * Make sure we don't leak information into the sandbox by copying
92 * uninitialized values.
93 */
94 __msan_check_mem_is_initialized(src_sys_ptr, num_bytes);
95 #endif
96
97 NaClCopyTakeLock(nap);
98 memcpy((void *) dst_sys_addr, src_sys_ptr, num_bytes);
99 NaClCopyDropLock(nap);
100
101 return 1;
102 }
103