Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(146)

Side by Side Diff: sandbox/linux/seccomp/trusted_thread.cc

Issue 661438: Seccomp sandbox changes (performance and correctness fixes, primarily targetting x86-32) (Closed) Base URL: svn://chrome-svn/chrome/trunk/src/
Patch Set: '' Created 10 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « sandbox/linux/seccomp/syscall.cc ('k') | sandbox/sandbox.gyp » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2010 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
1 #include "sandbox_impl.h" 5 #include "sandbox_impl.h"
2 #include "syscall_table.h" 6 #include "syscall_table.h"
3 7
4 namespace playground { 8 namespace playground {
5 9
6 void Sandbox::createTrustedThread(int processFdPub, int cloneFdPub, 10 void Sandbox::createTrustedThread(int processFdPub, int cloneFdPub,
7 SecureMem::Args* secureMem) { 11 SecureMem::Args* secureMem) {
8 SecureMem::Args args = { { { { { 0 } } } } }; 12 SecureMem::Args args = { { { { { 0 } } } } };
9 args.self = &args; 13 args.self = &args;
10 args.newSecureMem = secureMem; 14 args.newSecureMem = secureMem;
11 args.processFdPub = processFdPub; 15 args.processFdPub = processFdPub;
12 args.cloneFdPub = cloneFdPub; 16 args.cloneFdPub = cloneFdPub;
13 #if defined(__x86_64__) 17 #if defined(__x86_64__)
14 asm volatile( 18 asm volatile(
15 "push %%rbx\n" 19 "push %%rbx\n"
16 "push %%rbp\n" 20 "push %%rbp\n"
17 "mov %0, %%rbp\n" // %rbp = args 21 "mov %0, %%rbp\n" // %rbp = args
18 "xor %%rbx, %%rbx\n" // initial sequence number 22 "xor %%rbx, %%rbx\n" // initial sequence number
19 "lea 999f(%%rip), %%r15\n" // continue in same thread 23 "lea 999f(%%rip), %%r15\n" // continue in same thread
20 "jmp 19f\n" // create trusted thread 24 "jmp 20f\n" // create trusted thread
21 25
22 // TODO(markus): Coalesce the read() operations by reading into a bigger 26 // TODO(markus): Coalesce the read() operations by reading into a bigger
23 // buffer. 27 // buffer.
24 28
25 // Parameters: 29 // Parameters:
26 // *%fs: secure memory region 30 // *%fs: secure memory region
27 // the page following this one contains the scratch space 31 // the page following this one contains the scratch space
28 // %r13: thread's side of threadFd 32 // %r13: thread's side of threadFd
29 // %r15: processFdPub 33 // %r15: processFdPub
30 34
(...skipping 102 matching lines...) Expand 10 before | Expand all | Expand 10 after
133 "jnz 4f\n" 137 "jnz 4f\n"
134 "syscall\n" 138 "syscall\n"
135 "mov %%rax, %%r8\n" 139 "mov %%rax, %%r8\n"
136 "mov $56, %%eax\n" // NR_clone 140 "mov $56, %%eax\n" // NR_clone
137 "mov $17, %%edi\n" // flags = SIGCHLD 141 "mov $17, %%edi\n" // flags = SIGCHLD
138 "mov $1, %%esi\n" // stack = 1 142 "mov $1, %%esi\n" // stack = 1
139 "syscall\n" 143 "syscall\n"
140 "test %%rax, %%rax\n" 144 "test %%rax, %%rax\n"
141 "js 25f\n" // exit process 145 "js 25f\n" // exit process
142 "mov %%rax, %%rdi\n" 146 "mov %%rax, %%rdi\n"
143 "jnz 7f\n" // wait for child, then return result 147 "jnz 8f\n" // wait for child, then return result
144 "mov %%fs:0x0, %%rdi\n" // start = secure_mem 148 "mov %%fs:0x0, %%rdi\n" // start = secure_mem
145 "mov $4096, %%esi\n" // len = 4096 149 "mov $4096, %%esi\n" // len = 4096
146 "mov $3, %%edx\n" // prot = PROT_READ | PROT_WRITE 150 "mov $3, %%edx\n" // prot = PROT_READ | PROT_WRITE
147 "mov $10, %%eax\n" // NR_mprotect 151 "mov $10, %%eax\n" // NR_mprotect
148 "syscall\n" 152 "syscall\n"
149 "mov %%r8d, 0xD4(%%rdi)\n" // set most recently returned SysV shm id 153 "mov %%r8d, 0xD4(%%rdi)\n" // set most recently returned SysV shm id
150 "xor %%rdi, %%rdi\n" 154 "xor %%rdi, %%rdi\n"
155
156 // When debugging messages are enabled, warn about expensive system calls
157 #ifndef NDEBUG
158 "cmpw $0, %%fs:0xD0\n" // debug mode
159 "jz 26f\n"
160 "mov $1, %%eax\n" // NR_write
161 "mov $2, %%edi\n" // fd = stderr
162 "lea 101f(%%rip), %%rsi\n" // "This is an expensive system call"
163 "mov $102f-101f, %%edx\n" // len = strlen(msg)
164 "syscall\n"
165 "xor %%rdi, %%rdi\n"
166 #endif
167
151 "jmp 26f\n" // exit program, no message 168 "jmp 26f\n" // exit program, no message
152 "4:syscall\n" 169 "4:syscall\n"
153 "jmp 14f\n" // return result 170 "jmp 15f\n" // return result
154 171
155 // If syscall number is -2, execute locked system call from the 172 // If syscall number is -2, execute locked system call from the
156 // secure memory area 173 // secure memory area
157 "5:jg 11f\n" 174 "5:jg 12f\n"
158 "cmp $-2, %%eax\n" 175 "cmp $-2, %%eax\n"
159 "jnz 8f\n" 176 "jnz 9f\n"
160 "cmp %%rbx, %%fs:0x8\n" 177 "cmp %%rbx, %%fs:0x8\n"
161 "jne 25f\n" // exit process 178 "jne 25f\n" // exit process
179
180 // When debugging messages are enabled, warn about expensive system calls
181 #ifndef NDEBUG
182 "cmpw $0, %%fs:0xD0\n" // debug mode
183 "jz 6f\n"
184 "mov $1, %%eax\n" // NR_write
185 "mov $2, %%edi\n" // fd = stderr
186 "lea 101f(%%rip), %%rsi\n" // "This is an expensive system call"
187 "mov $102f-101f, %%edx\n" // len = strlen(msg)
188 "syscall\n"
189 "6:"
190 #endif
191
162 "mov %%fs:0x10, %%rax\n" 192 "mov %%fs:0x10, %%rax\n"
163 "mov %%fs:0x18, %%rdi\n" 193 "mov %%fs:0x18, %%rdi\n"
164 "mov %%fs:0x20, %%rsi\n" 194 "mov %%fs:0x20, %%rsi\n"
165 "mov %%fs:0x28, %%rdx\n" 195 "mov %%fs:0x28, %%rdx\n"
166 "mov %%fs:0x30, %%r10\n" 196 "mov %%fs:0x30, %%r10\n"
167 "mov %%fs:0x38, %%r8\n" 197 "mov %%fs:0x38, %%r8\n"
168 "mov %%fs:0x40, %%r9\n" 198 "mov %%fs:0x40, %%r9\n"
169 "cmp %%rbx, %%fs:0x8\n" 199 "cmp %%rbx, %%fs:0x8\n"
170 "jne 25f\n" // exit process 200 "jne 25f\n" // exit process
171 201
172 // clone() has unusual calling conventions and must be handled specially 202 // clone() has unusual calling conventions and must be handled specially
173 "cmp $56, %%rax\n" // NR_clone 203 "cmp $56, %%rax\n" // NR_clone
174 "jz 18f\n" 204 "jz 19f\n"
175 205
176 // exit() terminates trusted thread 206 // exit() terminates trusted thread
177 "cmp $60, %%eax\n" // NR_exit 207 "cmp $60, %%eax\n" // NR_exit
178 "jz 17f\n" 208 "jz 18f\n"
179 209
180 // Perform requested system call 210 // Perform requested system call
181 "syscall\n" 211 "syscall\n"
182 212
183 // Unlock mutex 213 // Unlock mutex
184 "6:cmp %%rbx, %%fs:0x8\n" 214 "7:cmp %%rbx, %%fs:0x8\n"
185 "jne 25f\n" // exit process 215 "jne 25f\n" // exit process
186 "add $2, %%rbx\n" 216 "add $2, %%rbx\n"
187 "mov %%rax, %%r8\n" 217 "mov %%rax, %%r8\n"
188 "mov $56, %%eax\n" // NR_clone 218 "mov $56, %%eax\n" // NR_clone
189 "mov $17, %%rdi\n" // flags = SIGCHLD 219 "mov $17, %%rdi\n" // flags = SIGCHLD
190 "mov $1, %%rsi\n" // stack = 1 220 "mov $1, %%rsi\n" // stack = 1
191 "syscall\n" 221 "syscall\n"
192 "test %%rax, %%rax\n" 222 "test %%rax, %%rax\n"
193 "js 25f\n" // exit process 223 "js 25f\n" // exit process
194 "jz 22f\n" // unlock and exit 224 "jz 22f\n" // unlock and exit
195 "mov %%rax, %%rdi\n" 225 "mov %%rax, %%rdi\n"
196 "7:xor %%rsi, %%rsi\n" 226 "8:xor %%rsi, %%rsi\n"
197 "xor %%rdx, %%rdx\n" 227 "xor %%rdx, %%rdx\n"
198 "xor %%r10, %%r10\n" 228 "xor %%r10, %%r10\n"
199 "mov $61, %%eax\n" // NR_wait4 229 "mov $61, %%eax\n" // NR_wait4
200 "syscall\n" 230 "syscall\n"
201 "cmp $-4, %%eax\n" // EINTR 231 "cmp $-4, %%eax\n" // EINTR
202 "jz 7b\n" 232 "jz 8b\n"
203 "mov %%r8, %%rax\n" 233 "mov %%r8, %%rax\n"
204 "jmp 14f\n" // return result 234 "jmp 15f\n" // return result
205 235
206 // If syscall number is -3, read the time stamp counter 236 // If syscall number is -3, read the time stamp counter
207 "8:cmp $-3, %%eax\n" 237 "9:cmp $-3, %%eax\n"
208 "jnz 9f\n" 238 "jnz 10f\n"
209 "rdtsc\n" // sets %edx:%eax 239 "rdtsc\n" // sets %edx:%eax
210 "xor %%rcx, %%rcx\n" 240 "xor %%rcx, %%rcx\n"
211 "jmp 10f\n" 241 "jmp 11f\n"
212 "9:cmp $-4, %%eax\n" 242 "10:cmp $-4, %%eax\n"
213 "jnz 11f\n" 243 "jnz 12f\n"
214 "rdtscp\n" // sets %edx:%eax and %ecx 244 "rdtscp\n" // sets %edx:%eax and %ecx
215 "10:add $0x3C, %%rsi\n" 245 "11:add $0x3C, %%rsi\n"
216 "mov %%eax, 0(%%rsi)\n" 246 "mov %%eax, 0(%%rsi)\n"
217 "mov %%edx, 4(%%rsi)\n" 247 "mov %%edx, 4(%%rsi)\n"
218 "mov %%ecx, 8(%%rsi)\n" 248 "mov %%ecx, 8(%%rsi)\n"
219 "mov $12, %%edx\n" 249 "mov $12, %%edx\n"
220 "jmp 15f\n" // return result 250 "jmp 16f\n" // return result
221 251
222 // Check in syscallTable whether this system call is unrestricted 252 // Check in syscallTable whether this system call is unrestricted
223 "11:mov %%rax, %%r9\n" 253 "12:mov %%rax, %%r9\n"
224 #ifndef NDEBUG 254 #ifndef NDEBUG
225 "cmpw $0, %%fs:0xD0\n" // debug mode 255 "cmpw $0, %%fs:0xD0\n" // debug mode
226 "jnz 12f\n" 256 "jnz 13f\n"
227 #endif 257 #endif
228 "cmp playground$maxSyscall(%%rip), %%eax\n" 258 "cmp playground$maxSyscall(%%rip), %%eax\n"
229 "ja 25f\n" // exit process 259 "ja 25f\n" // exit process
230 "shl $4, %%rax\n" 260 "shl $4, %%rax\n"
231 "lea playground$syscallTable(%%rip), %%rdi\n" 261 "lea playground$syscallTable(%%rip), %%rdi\n"
232 "add %%rdi, %%rax\n" 262 "add %%rdi, %%rax\n"
233 "mov 0(%%rax), %%rax\n" 263 "mov 0(%%rax), %%rax\n"
234 "cmp $1, %%rax\n" 264 "cmp $1, %%rax\n"
235 "jne 25f\n" // exit process 265 "jne 25f\n" // exit process
236 266
237 // Default behavior for unrestricted system calls is to just execute 267 // Default behavior for unrestricted system calls is to just execute
238 // them. Read the remaining arguments first. 268 // them. Read the remaining arguments first.
239 "12:mov %%rsi, %%r8\n" 269 "13:mov %%rsi, %%r8\n"
240 "xor %%rax, %%rax\n" // NR_read 270 "xor %%rax, %%rax\n" // NR_read
241 "mov %%r13, %%rdi\n" // fd = threadFd 271 "mov %%r13, %%rdi\n" // fd = threadFd
242 "add $4, %%rsi\n" // buf = &scratch + 4 272 "add $4, %%rsi\n" // buf = &scratch + 4
243 "mov $48, %%edx\n" // len = 6*sizeof(void *) 273 "mov $48, %%edx\n" // len = 6*sizeof(void *)
244 "13:syscall\n" 274 "14:syscall\n"
245 "cmp $-4, %%rax\n" // EINTR 275 "cmp $-4, %%rax\n" // EINTR
246 "jz 13b\n" 276 "jz 14b\n"
247 "cmp %%rdx, %%rax\n" 277 "cmp %%rdx, %%rax\n"
248 "jnz 25f\n" // exit process 278 "jnz 25f\n" // exit process
249 "mov %%r9, %%rax\n" 279 "mov %%r9, %%rax\n"
250 "mov 0x04(%%r8), %%rdi\n" 280 "mov 0x04(%%r8), %%rdi\n"
251 "mov 0x0C(%%r8), %%rsi\n" 281 "mov 0x0C(%%r8), %%rsi\n"
252 "mov 0x14(%%r8), %%rdx\n" 282 "mov 0x14(%%r8), %%rdx\n"
253 "mov 0x1C(%%r8), %%r10\n" 283 "mov 0x1C(%%r8), %%r10\n"
254 "mov 0x2C(%%r8), %%r9\n" 284 "mov 0x2C(%%r8), %%r9\n"
255 "mov 0x24(%%r8), %%r8\n" 285 "mov 0x24(%%r8), %%r8\n"
256 "cmp $231, %%rax\n" // NR_exit_group 286 "cmp $231, %%rax\n" // NR_exit_group
257 "jz 26f\n" // exit program, no message 287 "jz 26f\n" // exit program, no message
258 "syscall\n" 288 "syscall\n"
259 289
260 // Return result of system call to sandboxed thread 290 // Return result of system call to sandboxed thread
261 "14:mov %%fs:0x0, %%rsi\n" 291 "15:mov %%fs:0x0, %%rsi\n"
262 "add $0x1034, %%rsi\n" // buf = &scratch + 52 292 "add $0x1034, %%rsi\n" // buf = &scratch + 52
263 "mov %%rax, (%%rsi)\n" 293 "mov %%rax, (%%rsi)\n"
264 "mov $8, %%edx\n" // len = 8 294 "mov $8, %%edx\n" // len = 8
265 "15:mov %%r13, %%rdi\n" // fd = threadFd 295 "16:mov %%r13, %%rdi\n" // fd = threadFd
266 "mov $1, %%eax\n" // NR_write 296 "mov $1, %%eax\n" // NR_write
267 "16:syscall\n" 297 "17:syscall\n"
268 "cmp %%rdx, %%rax\n" 298 "cmp %%rdx, %%rax\n"
269 "jz 1b\n" 299 "jz 1b\n"
270 "cmp $-4, %%rax\n" // EINTR 300 "cmp $-4, %%rax\n" // EINTR
271 "jz 16b\n" 301 "jz 17b\n"
272 "jmp 25f\n" // exit process 302 "jmp 25f\n" // exit process
273 303
274 // NR_exit: 304 // NR_exit:
275 // Exit trusted thread after cleaning up resources 305 // Exit trusted thread after cleaning up resources
276 "17:mov %%fs:0x0, %%rsi\n" 306 "18:mov %%fs:0x0, %%rsi\n"
277 "mov 0xE8(%%rsi), %%rdi\n" // fd = threadFdPub 307 "mov 0xE8(%%rsi), %%rdi\n" // fd = threadFdPub
278 "mov $3, %%eax\n" // NR_close 308 "mov $3, %%eax\n" // NR_close
279 "syscall\n" 309 "syscall\n"
280 "mov %%rsi, %%rdi\n" // start = secure_mem 310 "mov %%rsi, %%rdi\n" // start = secure_mem
281 "mov $8192, %%esi\n" // length = 4096 311 "mov $8192, %%esi\n" // length = 8192
282 "xor %%rdx, %%rdx\n" // prot = PROT_NONE 312 "xor %%rdx, %%rdx\n" // prot = PROT_NONE
283 "mov $10, %%eax\n" // NR_mprotect 313 "mov $10, %%eax\n" // NR_mprotect
284 "syscall\n" 314 "syscall\n"
285 "mov %%r13, %%rdi\n" // fd = threadFd 315 "mov %%r13, %%rdi\n" // fd = threadFd
286 "mov $3, %%eax\n" // NR_close 316 "mov $3, %%eax\n" // NR_close
287 "syscall\n" 317 "syscall\n"
288 "mov $56, %%eax\n" // NR_clone 318 "mov $56, %%eax\n" // NR_clone
289 "mov $17, %%rdi\n" // flags = SIGCHLD 319 "mov $17, %%rdi\n" // flags = SIGCHLD
290 "mov $1, %%rsi\n" // stack = 1 320 "mov $1, %%rsi\n" // stack = 1
291 "syscall\n" 321 "syscall\n"
292 "mov %%rax, %%rdi\n" 322 "mov %%rax, %%rdi\n"
293 "test %%rax, %%rax\n" 323 "test %%rax, %%rax\n"
324 "js 26f\n" // exit process
294 "jne 21f\n" // reap helper, exit thread 325 "jne 21f\n" // reap helper, exit thread
295 "jmp 22f\n" // unlock mutex 326 "jmp 22f\n" // unlock mutex
296 327
297 // NR_clone: 328 // NR_clone:
298 // Original trusted thread calls clone() to create new nascent 329 // Original trusted thread calls clone() to create new nascent
299 // thread. This thread is (typically) fully privileged and shares all 330 // thread. This thread is (typically) fully privileged and shares all
300 // resources with the caller (i.e. the previous trusted thread), 331 // resources with the caller (i.e. the previous trusted thread),
301 // and by extension it shares all resources with the sandbox'd 332 // and by extension it shares all resources with the sandbox'd
302 // threads. 333 // threads.
303 // N.B. It is possible to make the thread creation code crash before 334 // N.B. It is possible to make the thread creation code crash before
304 // it releases seccomp privileges. This is generally OK, as it just 335 // it releases seccomp privileges. This is generally OK, as it just
305 // terminates the program. But if we ever support signal handling, 336 // terminates the program. But if we ever support signal handling,
306 // we have to be careful that the user cannot install a SIGSEGV 337 // we have to be careful that the user cannot install a SIGSEGV
307 // handler that gets executed with elevated privileges. 338 // handler that gets executed with elevated privileges.
308 "18:mov %%fs:0x0, %%rbp\n" // %rbp = old_shared_mem 339 "19:mov %%fs:0x0, %%rbp\n" // %rbp = old_shared_mem
309 "syscall\n" // calls NR_clone 340 "syscall\n" // calls NR_clone
310 "cmp $-4095, %%rax\n" // return codes -1..-4095 are errno values 341 "cmp $-4095, %%rax\n" // return codes -1..-4095 are errno values
311 "jae 6b\n" 342 "jae 7b\n" // unlock mutex, return result
312 "add $2, %%rbx\n" 343 "add $2, %%rbx\n"
313 "test %%rax, %%rax\n" 344 "test %%rax, %%rax\n"
314 "jne 14b\n" // return result 345 "jne 15b\n" // return result
315 346
316 // In nascent thread, now. 347 // In nascent thread, now.
317 "sub $2, %%rbx\n" 348 "sub $2, %%rbx\n"
318 "xor %%r15, %%r15\n" // Request to return from clone() when done 349 "xor %%r15, %%r15\n" // Request to return from clone() when done
319 350
320 // Get thread id of nascent thread 351 // Get thread id of nascent thread
321 "19:mov $186, %%eax\n" // NR_gettid 352 "20:mov $186, %%eax\n" // NR_gettid
322 "syscall\n" 353 "syscall\n"
323 "mov %%rax, %%r14\n" 354 "mov %%rax, %%r14\n"
324 355
325 // Nascent thread creates socketpair() for sending requests to 356 // Nascent thread creates socketpair() for sending requests to
326 // trusted thread. 357 // trusted thread.
327 // We can create the filehandles on the stack. Filehandles are 358 // We can create the filehandles on the stack. Filehandles are
328 // always treated as untrusted. 359 // always treated as untrusted.
329 // socketpair(AF_UNIX, SOCK_STREAM, 0, fds) 360 // socketpair(AF_UNIX, SOCK_STREAM, 0, fds)
330 "push %%r15\n" 361 "push %%r15\n"
331 "mov $53, %%eax\n" // NR_socketpair 362 "mov $53, %%eax\n" // NR_socketpair
332 "mov $1, %%edi\n" // domain = AF_UNIX 363 "mov $1, %%edi\n" // domain = AF_UNIX
333 "mov $1, %%esi\n" // type = SOCK_STREAM 364 "mov $1, %%esi\n" // type = SOCK_STREAM
334 "xor %%rdx, %%rdx\n" // protocol = 0 365 "xor %%rdx, %%rdx\n" // protocol = 0
335 "sub $8, %%rsp\n" // sv = %rsp 366 "sub $8, %%rsp\n" // sv = %rsp
336 "mov %%rsp, %%r10\n" 367 "mov %%rsp, %%r10\n"
337 "syscall\n" 368 "syscall\n"
338 "test %%rax, %%rax\n" 369 "test %%rax, %%rax\n"
339 "jz 27f\n" 370 "jz 27f\n"
340 371
341 // If things went wrong, we don't have an (easy) way of signaling 372 // If things went wrong, we don't have an (easy) way of signaling
342 // the parent. For our purposes, it is sufficient to fail with a 373 // the parent. For our purposes, it is sufficient to fail with a
343 // fatal error. 374 // fatal error.
344 "jmp 25f\n" // exit process 375 "jmp 25f\n" // exit process
345 "20:mov $56, %%eax\n" // NR_clone
346 "mov $17, %%rdi\n" // flags = SIGCHLD
347 "mov $1, %%rsi\n" // stack = 1
348 "syscall\n"
349 "test %%rax, %%rax\n"
350 "js 25f\n" // exit process
351 "jz 22f\n" // unlock and exit
352 "mov %%rax, %%rdi\n"
353 "21:xor %%rsi, %%rsi\n" 376 "21:xor %%rsi, %%rsi\n"
354 "xor %%rdx, %%rdx\n" 377 "xor %%rdx, %%rdx\n"
355 "xor %%r10, %%r10\n" 378 "xor %%r10, %%r10\n"
356 "mov $61, %%eax\n" // NR_wait4 379 "mov $61, %%eax\n" // NR_wait4
357 "syscall\n" 380 "syscall\n"
358 "cmp $-4, %%eax\n" // EINTR 381 "cmp $-4, %%eax\n" // EINTR
359 "jz 21b\n" 382 "jz 21b\n"
360 "jmp 23f\n" // exit thread (no message) 383 "jmp 23f\n" // exit thread (no message)
361 "22:lea playground$syscall_mutex(%%rip), %%rdi\n" 384 "22:lea playground$syscall_mutex(%%rip), %%rdi\n"
362 "mov $4096, %%esi\n" 385 "mov $4096, %%esi\n"
363 "mov $3, %%edx\n" // prot = PROT_READ | PROT_WRITE 386 "mov $3, %%edx\n" // prot = PROT_READ | PROT_WRITE
364 "mov $10, %%eax\n" // NR_mprotect 387 "mov $10, %%eax\n" // NR_mprotect
365 "syscall\n" 388 "syscall\n"
366 "lock; addl $0x80000000, (%%rdi)\n" 389 "lock; addl $0x80000000, (%%rdi)\n"
367 "jz 23f\n" // exit thread 390 "jz 23f\n" // exit thread
368 "mov $1, %%edx\n" 391 "mov $1, %%edx\n"
369 "mov %%rdx, %%rsi\n" // FUTEX_WAKE 392 "mov %%rdx, %%rsi\n" // FUTEX_WAKE
370 "mov $202, %%eax\n" // NR_futex 393 "mov $202, %%eax\n" // NR_futex
371 "syscall\n" 394 "syscall\n"
372 "23:mov $60, %%eax\n" // NR_exit 395 "23:mov $60, %%eax\n" // NR_exit
373 "mov $1, %%edi\n" // status = 1 396 "mov $1, %%edi\n" // status = 1
374 "24:syscall\n" 397 "24:syscall\n"
375 "25:mov $1, %%eax\n" // NR_write 398 "25:mov $1, %%eax\n" // NR_write
376 "mov $2, %%edi\n" // fd = stderr 399 "mov $2, %%edi\n" // fd = stderr
377 "lea 100f(%%rip), %%rsi\n" 400 "lea 100f(%%rip), %%rsi\n" // "Sandbox violation detected"
378 "mov $101f-100f, %%edx\n" // len = strlen(msg) 401 "mov $101f-100f, %%edx\n" // len = strlen(msg)
379 "syscall\n" 402 "syscall\n"
380 "mov $1, %%edi\n" 403 "mov $1, %%edi\n"
381 "26:mov $231, %%eax\n" // NR_exit_group 404 "26:mov $231, %%eax\n" // NR_exit_group
382 "jmp 24b\n" 405 "jmp 24b\n"
383 406
384 // The first page is mapped read-only for use as securely shared memory 407 // The first page is mapped read-only for use as securely shared memory
385 "27:mov 0xC0(%%rbp), %%r12\n" // %r12 = secure shared memory 408 "27:mov 0xC0(%%rbp), %%r12\n" // %r12 = secure shared memory
386 "cmp %%rbx, 8(%%rbp)\n" 409 "cmp %%rbx, 8(%%rbp)\n"
387 "jne 25b\n" // exit process 410 "jne 25b\n" // exit process
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after
419 "mov 0(%%rsp), %%r9d\n" // %r9 = threadFdPub 442 "mov 0(%%rsp), %%r9d\n" // %r9 = threadFdPub
420 "add $8, %%rsp\n" 443 "add $8, %%rsp\n"
421 444
422 // Set up thread local storage with information on how to talk to 445 // Set up thread local storage with information on how to talk to
423 // trusted thread and trusted process. 446 // trusted thread and trusted process.
424 "lea 0xD8(%%r12), %%rsi\n" // args = &secure_mem.TLS; 447 "lea 0xD8(%%r12), %%rsi\n" // args = &secure_mem.TLS;
425 "mov $158, %%eax\n" // NR_arch_prctl 448 "mov $158, %%eax\n" // NR_arch_prctl
426 "mov $0x1001, %%edi\n" // option = ARCH_SET_GS 449 "mov $0x1001, %%edi\n" // option = ARCH_SET_GS
427 "syscall\n" 450 "syscall\n"
428 "cmp $-4095, %%rax\n" // return codes -1..-4095 are errno values 451 "cmp $-4095, %%rax\n" // return codes -1..-4095 are errno values
429 "jae 20b\n" // exit thread, unlock global mutex 452 "jae 25b\n" // exit process
430 453
431 // Check whether this is the initial thread, or a newly created one. 454 // Check whether this is the initial thread, or a newly created one.
432 // At startup we run the same code as when we create a new thread. At 455 // At startup we run the same code as when we create a new thread. At
433 // the very top of this function, you will find that we push 999(%rip) 456 // the very top of this function, you will find that we push 999(%rip)
434 // on the stack. That is the signal that we should return on the same 457 // on the stack. That is the signal that we should return on the same
435 // stack rather than return to where clone was called. 458 // stack rather than return to where clone was called.
436 "pop %%r15\n" 459 "pop %%r15\n"
437 "test %%r15, %%r15\n" 460 "test %%r15, %%r15\n"
438 "jne 28f\n" 461 "jne 28f\n"
439 462
(...skipping 77 matching lines...) Expand 10 before | Expand all | Expand 10 after
517 "jmp 26b\n" // exit process (no error message) 540 "jmp 26b\n" // exit process (no error message)
518 541
519 // Reap helper 542 // Reap helper
520 "29:mov %%rax, %%rdi\n" 543 "29:mov %%rax, %%rdi\n"
521 "30:xor %%rsi, %%rsi\n" 544 "30:xor %%rsi, %%rsi\n"
522 "xor %%rdx, %%rdx\n" 545 "xor %%rdx, %%rdx\n"
523 "xor %%r10, %%r10\n" 546 "xor %%r10, %%r10\n"
524 "mov $61, %%eax\n" // NR_wait4 547 "mov $61, %%eax\n" // NR_wait4
525 "syscall\n" 548 "syscall\n"
526 "cmp $-4, %%eax\n" // EINTR 549 "cmp $-4, %%eax\n" // EINTR
527 "jz 30\n" 550 "jz 30b\n"
528 551
529 // Release privileges by entering seccomp mode. 552 // Release privileges by entering seccomp mode.
530 "mov $157, %%eax\n" // NR_prctl 553 "mov $157, %%eax\n" // NR_prctl
531 "mov $22, %%edi\n" // PR_SET_SECCOMP 554 "mov $22, %%edi\n" // PR_SET_SECCOMP
532 "mov $1, %%esi\n" 555 "mov $1, %%esi\n"
533 "syscall\n" 556 "syscall\n"
534 "test %%rax, %%rax\n" 557 "test %%rax, %%rax\n"
535 "jnz 25b\n" // exit process 558 "jnz 25b\n" // exit process
536 559
537 // Back in the newly created sandboxed thread, wait for trusted process 560 // Back in the newly created sandboxed thread, wait for trusted process
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after
571 "pop %%rdi\n" 594 "pop %%rdi\n"
572 "pop %%rsi\n" 595 "pop %%rsi\n"
573 "pop %%rdx\n" 596 "pop %%rdx\n"
574 "pop %%rcx\n" 597 "pop %%rcx\n"
575 "pop %%rbx\n" 598 "pop %%rbx\n"
576 "pop %%rbp\n" 599 "pop %%rbp\n"
577 "ret\n" 600 "ret\n"
578 601
579 ".pushsection \".rodata\"\n" 602 ".pushsection \".rodata\"\n"
580 "100:.ascii \"Sandbox violation detected, program aborted\\n\"\n" 603 "100:.ascii \"Sandbox violation detected, program aborted\\n\"\n"
581 "101:\n" 604 "101:.ascii \"WARNING! This is an expensive system call\\n\"\n"
605 "102:\n"
582 ".popsection\n" 606 ".popsection\n"
583 607
584 "999:pop %%rbp\n" 608 "999:pop %%rbp\n"
585 "pop %%rbx\n" 609 "pop %%rbx\n"
586 : 610 :
587 : "g"(&args) 611 : "g"(&args)
588 : "rax", "rcx", "rdx", "rdi", "rsi", "r8", "r9", "r10", "r11", "r12", 612 : "rax", "rcx", "rdx", "rdi", "rsi", "r8", "r9", "r10", "r11", "r12",
589 "r13", "r14", "r15", "rsp", "memory" 613 "r13", "r14", "r15", "rsp", "memory"
590 #elif defined(__i386__) 614 #elif defined(__i386__)
591 struct user_desc u; 615 struct user_desc u;
(...skipping 14 matching lines...) Expand all
606 : 630 :
607 : "q"(8*u.entry_number+3)); 631 : "q"(8*u.entry_number+3));
608 asm volatile( 632 asm volatile(
609 "push %%ebx\n" 633 "push %%ebx\n"
610 "push %%ebp\n" 634 "push %%ebp\n"
611 "movd %0, %%mm6\n" // %mm6 = args 635 "movd %0, %%mm6\n" // %mm6 = args
612 "lea 999f, %%ebx\n" // continue in same thread 636 "lea 999f, %%ebx\n" // continue in same thread
613 "movd %%ebx, %%mm3\n" 637 "movd %%ebx, %%mm3\n"
614 "xor %%ebx, %%ebx\n" // initial sequence number 638 "xor %%ebx, %%ebx\n" // initial sequence number
615 "movd %%ebx, %%mm2\n" 639 "movd %%ebx, %%mm2\n"
616 "jmp 19f\n" // create trusted thread 640 "jmp 20f\n" // create trusted thread
617 641
618 // TODO(markus): Coalesce the read() operations by reading into a bigger 642 // TODO(markus): Coalesce the read() operations by reading into a bigger
619 // buffer. 643 // buffer.
620 644
621 // Parameters: 645 // Parameters:
622 // %mm5: secure memory region 646 // %mm5: secure memory region
623 // the page following this one contains the scratch space 647 // the page following this one contains the scratch space
624 // %mm0: thread's side of threadFd 648 // %mm0: thread's side of threadFd
625 // %mm1: processFdPub 649 // %mm1: processFdPub
626 // %mm3: return address after creation of new trusted thread 650 // %mm3: return address after creation of new trusted thread
(...skipping 11 matching lines...) Expand all
638 // 0x00: pointer to the secure shared memory region (i.e. self) 662 // 0x00: pointer to the secure shared memory region (i.e. self)
639 // 0x04: sequence number; must match %mm2 663 // 0x04: sequence number; must match %mm2
640 // 0x08: system call number; passed to syscall in %eax 664 // 0x08: system call number; passed to syscall in %eax
641 // 0x0C: first argument; passed to syscall in %ebx 665 // 0x0C: first argument; passed to syscall in %ebx
642 // 0x10: second argument; passed to syscall in %ecx 666 // 0x10: second argument; passed to syscall in %ecx
643 // 0x14: third argument; passed to syscall in %edx 667 // 0x14: third argument; passed to syscall in %edx
644 // 0x18: fourth argument; passed to syscall in %esi 668 // 0x18: fourth argument; passed to syscall in %esi
645 // 0x1C: fifth argument; passed to syscall in %edi 669 // 0x1C: fifth argument; passed to syscall in %edi
646 // 0x20: sixth argument; passed to syscall in %ebp 670 // 0x20: sixth argument; passed to syscall in %ebp
647 // 0x24: stored return address for clone() system call 671 // 0x24: stored return address for clone() system call
648 // 0x28: second stored return address for clone() system call 672 // 0x28: stored %ebp value for clone() system call
649 // 0x2C: stored %ebp value for clone() system call 673 // 0x2C: stored %edi value for clone() system call
650 // 0x30: stored %edi value for clone() system call 674 // 0x30: stored %esi value for clone() system call
651 // 0x34: stored %esi value for clone() system call 675 // 0x34: stored %edx value for clone() system call
652 // 0x38: stored %edx value for clone() system call 676 // 0x38: stored %ecx value for clone() system call
653 // 0x3C: stored %ecx value for clone() system call 677 // 0x3C: stored %ebx value for clone() system call
654 // 0x40: stored %ebx value for clone() system call 678 // 0x40: new shared memory for clone()
655 // 0x44: new shared memory for clone() 679 // 0x44: processFdPub for talking to trusted process
656 // 0x48: processFdPub for talking to trusted process 680 // 0x48: cloneFdPub for talking to trusted process
657 // 0x4C: cloneFdPub for talking to trusted process 681 // 0x4C: set to non-zero, if in debugging mode
658 // 0x50: set to non-zero, if in debugging mode 682 // 0x50: most recent SHM id returned by shmget(IPC_PRIVATE)
659 // 0x54: most recent SHM id returned by shmget(IPC_PRIVATE) 683 // 0x54: cookie assigned to us by the trusted process (TLS_COOKIE)
660 // 0x58: cookie assigned to us by the trusted process (TLS_COOKIE) 684 // 0x5C: thread id (TLS_TID)
661 // 0x60: thread id (TLS_TID) 685 // 0x64: threadFdPub (TLS_THREAD_FD)
662 // 0x68: threadFdPub (TLS_THREAD_FD)
663 // 0x200-0x1000: securely passed verified file name(s) 686 // 0x200-0x1000: securely passed verified file name(s)
664 687
665 // Layout of (untrusted) scratch space: 688 // Layout of (untrusted) scratch space:
666 // 0x00: syscall number; passed in %eax 689 // 0x00: syscall number; passed in %eax
667 // 0x04: first argument; passed in %ebx 690 // 0x04: first argument; passed in %ebx
668 // 0x08: second argument; passed in %ecx 691 // 0x08: second argument; passed in %ecx
669 // 0x0C: third argument; passed in %edx 692 // 0x0C: third argument; passed in %edx
670 // 0x10: fourth argument; passed in %esi 693 // 0x10: fourth argument; passed in %esi
671 // 0x14: fifth argument; passed in %edi 694 // 0x14: fifth argument; passed in %edi
672 // 0x18: sixth argument; passed in %ebp 695 // 0x18: sixth argument; passed in %ebp
673 // 0x1C: return value 696 // 0x1C: return value
674 // 0x20: RDTSCP result (%eax) 697 // 0x20: RDTSCP result (%eax)
675 // 0x24: RDTSCP result (%edx) 698 // 0x24: RDTSCP result (%edx)
676 // 0x28: RDTSCP result (%ecx) 699 // 0x28: RDTSCP result (%ecx)
700 // 0x2C: last system call (updated in syscall.cc)
701 // 0x30: number of consecutive calls to a time fnc. (e.g. gettimeofday)
677 702
678 "0:xor %%esp, %%esp\n" 703 "0:xor %%esp, %%esp\n"
679 "mov $2, %%eax\n" // %mm2 = initial sequence number 704 "mov $2, %%eax\n" // %mm2 = initial sequence number
680 "movd %%eax, %%mm2\n" 705 "movd %%eax, %%mm2\n"
681 706
682 // Read request from untrusted thread, or from trusted process. In either 707 // Read request from untrusted thread, or from trusted process. In either
683 // case, the data that we read has to be considered untrusted. 708 // case, the data that we read has to be considered untrusted.
684 // read(threadFd, &scratch, 4) 709 // read(threadFd, &scratch, 4)
685 "1:mov $3, %%eax\n" // NR_read 710 "1:mov $3, %%eax\n" // NR_read
686 "movd %%mm0, %%ebx\n" // fd = threadFd 711 "movd %%mm0, %%ebx\n" // fd = threadFd
(...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after
731 "jnz 4f\n" 756 "jnz 4f\n"
732 "int $0x80\n" 757 "int $0x80\n"
733 "mov %%eax, %%ebp\n" 758 "mov %%eax, %%ebp\n"
734 "mov $120, %%eax\n" // NR_clone 759 "mov $120, %%eax\n" // NR_clone
735 "mov $17, %%ebx\n" // flags = SIGCHLD 760 "mov $17, %%ebx\n" // flags = SIGCHLD
736 "mov $1, %%ecx\n" // stack = 1 761 "mov $1, %%ecx\n" // stack = 1
737 "int $0x80\n" 762 "int $0x80\n"
738 "test %%eax, %%eax\n" 763 "test %%eax, %%eax\n"
739 "js 25f\n" // exit process 764 "js 25f\n" // exit process
740 "mov %%eax, %%ebx\n" 765 "mov %%eax, %%ebx\n"
741 "jnz 7f\n" // wait for child, then return result 766 "jnz 8f\n" // wait for child, then return result
742 "movd %%mm5, %%ebx\n" // start = secure_mem 767 "movd %%mm5, %%ebx\n" // start = secure_mem
743 "mov $4096, %%ecx\n" // len = 4096 768 "mov $4096, %%ecx\n" // len = 4096
744 "mov $3, %%edx\n" // prot = PROT_READ | PROT_WRITE 769 "mov $3, %%edx\n" // prot = PROT_READ | PROT_WRITE
745 "mov $125, %%eax\n" // NR_mprotect 770 "mov $125, %%eax\n" // NR_mprotect
746 "int $0x80\n" 771 "int $0x80\n"
747 "mov %%ebp, 0x54(%%ebx)\n" // set most recently returned SysV shm id 772 "mov %%ebp, 0x50(%%ebx)\n" // set most recently returned SysV shm id
748 "xor %%ebx, %%ebx\n" 773 "xor %%ebx, %%ebx\n"
774
775 // When debugging messages are enabled, warn about expensive system calls
776 #ifndef NDEBUG
777 "movd %%mm5, %%ecx\n"
778 "cmpw $0, 0x4C(%%ecx)\n" // debug mode
779 "jz 26f\n"
780 "mov $4, %%eax\n" // NR_write
781 "mov $2, %%ebx\n" // fd = stderr
782 "lea 101f, %%ecx\n" // "This is an expensive system call"
783 "mov $102f-101f, %%edx\n" // len = strlen(msg)
784 "int $0x80\n"
785 "xor %%ebx, %%ebx\n"
786 #endif
787
749 "jmp 26f\n" // exit program, no message 788 "jmp 26f\n" // exit program, no message
750 "4:int $0x80\n" 789 "4:int $0x80\n"
751 "jmp 14f\n" // return result 790 "jmp 15f\n" // return result
752 791
753 // If syscall number is -2, execute locked system call from the 792 // If syscall number is -2, execute locked system call from the
754 // secure memory area 793 // secure memory area
755 "5:jg 11f\n" 794 "5:jg 12f\n"
756 "cmp $-2, %%eax\n" 795 "cmp $-2, %%eax\n"
757 "jnz 8f\n" 796 "jnz 9f\n"
758 "movd %%mm2, %%ebp\n" 797 "movd %%mm2, %%ebp\n"
759 "cmp %%ebp, 0x4-0x1000(%%ecx)\n" 798 "cmp %%ebp, 0x4-0x1000(%%ecx)\n"
760 "jne 25f\n" // exit process 799 "jne 25f\n" // exit process
800
801 // When debugging messages are enabled, warn about expensive system calls
802 #ifndef NDEBUG
803 "cmpw $0, 0x4C-0x1000(%%ecx)\n"
804 "jz 6f\n" // debug mode
805 "mov %%ecx, %%ebp\n"
806 "mov $4, %%eax\n" // NR_write
807 "mov $2, %%ebx\n" // fd = stderr
808 "lea 101f, %%ecx\n" // "This is an expensive system call"
809 "mov $102f-101f, %%edx\n" // len = strlen(msg)
810 "int $0x80\n"
811 "mov %%ebp, %%ecx\n"
812 "6:"
813 #endif
814
761 "mov 0x08-0x1000(%%ecx), %%eax\n" 815 "mov 0x08-0x1000(%%ecx), %%eax\n"
762 "mov 0x0C-0x1000(%%ecx), %%ebx\n" 816 "mov 0x0C-0x1000(%%ecx), %%ebx\n"
763 "mov 0x14-0x1000(%%ecx), %%edx\n" 817 "mov 0x14-0x1000(%%ecx), %%edx\n"
764 "mov 0x18-0x1000(%%ecx), %%esi\n" 818 "mov 0x18-0x1000(%%ecx), %%esi\n"
765 "mov 0x1C-0x1000(%%ecx), %%edi\n" 819 "mov 0x1C-0x1000(%%ecx), %%edi\n"
766 "mov 0x20-0x1000(%%ecx), %%ebp\n" 820 "mov 0x20-0x1000(%%ecx), %%ebp\n"
767 "mov 0x10-0x1000(%%ecx), %%ecx\n" 821 "mov 0x10-0x1000(%%ecx), %%ecx\n"
768 "movd %%edi, %%mm4\n" 822 "movd %%edi, %%mm4\n"
769 "movd %%ebp, %%mm7\n" 823 "movd %%ebp, %%mm7\n"
770 "movd %%mm2, %%ebp\n" 824 "movd %%mm2, %%ebp\n"
771 "movd %%mm5, %%edi\n" 825 "movd %%mm5, %%edi\n"
772 "cmp %%ebp, 4(%%edi)\n" 826 "cmp %%ebp, 4(%%edi)\n"
773 "jne 25f\n" // exit process 827 "jne 25f\n" // exit process
774 828
775 // clone() has unusual calling conventions and must be handled specially 829 // clone() has unusual calling conventions and must be handled specially
776 "cmp $120, %%eax\n" // NR_clone 830 "cmp $120, %%eax\n" // NR_clone
777 "jz 18f\n" 831 "jz 19f\n"
778 832
779 // exit() terminates trusted thread 833 // exit() terminates trusted thread
780 "cmp $1, %%eax\n" // NR_exit 834 "cmp $1, %%eax\n" // NR_exit
781 "jz 17f\n" 835 "jz 18f\n"
782 836
783 // Perform requested system call 837 // Perform requested system call
784 "movd %%mm4, %%edi\n" 838 "movd %%mm4, %%edi\n"
785 "movd %%mm7, %%ebp\n" 839 "movd %%mm7, %%ebp\n"
786 "int $0x80\n" 840 "int $0x80\n"
787 841
788 // Unlock mutex 842 // Unlock mutex
789 "6:movd %%mm2, %%ebp\n" 843 "7:movd %%mm2, %%ebp\n"
790 "movd %%mm5, %%edi\n" 844 "movd %%mm5, %%edi\n"
791 "cmp %%ebp, 4(%%edi)\n" 845 "cmp %%ebp, 4(%%edi)\n"
792 "jne 25f\n" // exit process 846 "jne 25f\n" // exit process
793 "add $2, %%ebp\n" 847 "add $2, %%ebp\n"
794 "movd %%ebp, %%mm2\n" 848 "movd %%ebp, %%mm2\n"
795 "mov %%eax, %%ebp\n" 849 "mov %%eax, %%ebp\n"
796 "mov $120, %%eax\n" // NR_clone 850 "mov $120, %%eax\n" // NR_clone
797 "mov $17, %%ebx\n" // flags = SIGCHLD 851 "mov $17, %%ebx\n" // flags = SIGCHLD
798 "mov $1, %%ecx\n" // stack = 1 852 "mov $1, %%ecx\n" // stack = 1
799 "int $0x80\n" 853 "int $0x80\n"
800 "test %%eax, %%eax\n" 854 "test %%eax, %%eax\n"
801 "js 25f\n" // exit process 855 "js 25f\n" // exit process
802 "jz 22f\n" // unlock and exit 856 "jz 22f\n" // unlock and exit
803 "mov %%eax, %%ebx\n" 857 "mov %%eax, %%ebx\n"
804 "7:xor %%ecx, %%ecx\n" 858 "8:xor %%ecx, %%ecx\n"
805 "xor %%edx, %%edx\n" 859 "xor %%edx, %%edx\n"
806 "mov $7, %%eax\n" // NR_waitpid 860 "mov $7, %%eax\n" // NR_waitpid
807 "int $0x80\n" 861 "int $0x80\n"
808 "cmp $-4, %%eax\n" // EINTR 862 "cmp $-4, %%eax\n" // EINTR
809 "jz 6\n" 863 "jz 6\n"
810 "mov %%ebp, %%eax\n" 864 "mov %%ebp, %%eax\n"
811 "jmp 14f\n" // return result 865 "jmp 15f\n" // return result
812 866
813 // If syscall number is -3, read the time stamp counter 867 // If syscall number is -3, read the time stamp counter
814 "8:cmp $-3, %%eax\n" 868 "9:cmp $-3, %%eax\n"
815 "jnz 9f\n" 869 "jnz 10f\n"
816 "rdtsc\n" // sets %edx:%eax 870 "rdtsc\n" // sets %edx:%eax
817 "xor %%ecx, %%ecx\n" 871 "xor %%ecx, %%ecx\n"
818 "jmp 10f\n" 872 "jmp 11f\n"
819 "9:cmp $-4, %%eax\n" 873 "10:cmp $-4, %%eax\n"
820 "jnz 11f\n" 874 "jnz 12f\n"
821 "rdtscp\n" // sets %edx:%eax and %ecx 875 "rdtscp\n" // sets %edx:%eax and %ecx
822 "10:movd %%mm5, %%ebx\n" 876 "11:movd %%mm5, %%ebx\n"
823 "add $0x1020, %%ebx\n" 877 "add $0x1020, %%ebx\n"
824 "mov %%eax, 0(%%ebx)\n" 878 "mov %%eax, 0(%%ebx)\n"
825 "mov %%edx, 4(%%ebx)\n" 879 "mov %%edx, 4(%%ebx)\n"
826 "mov %%ecx, 8(%%ebx)\n" 880 "mov %%ecx, 8(%%ebx)\n"
827 "mov %%ebx, %%ecx\n" 881 "mov %%ebx, %%ecx\n"
828 "mov $12, %%edx\n" 882 "mov $12, %%edx\n"
829 "jmp 15f\n" // return result 883 "jmp 16f\n" // return result
830 884
831 // Check in syscallTable whether this system call is unrestricted 885 // Check in syscallTable whether this system call is unrestricted
832 "11:mov %%eax, %%ebp\n" 886 "12:mov %%eax, %%ebp\n"
833 #ifndef NDEBUG 887 #ifndef NDEBUG
834 "cmpw $0, 0x50-0x1000(%%ecx)\n" 888 "cmpw $0, 0x4C-0x1000(%%ecx)\n"
835 "jnz 12f\n" // debug mode 889 "jnz 13f\n" // debug mode
836 #endif 890 #endif
837 "cmp playground$maxSyscall, %%eax\n" 891 "cmp playground$maxSyscall, %%eax\n"
838 "ja 25f\n" // exit process 892 "ja 25f\n" // exit process
839 "shl $3, %%eax\n" 893 "shl $3, %%eax\n"
840 "add $playground$syscallTable, %%eax\n" 894 "add $playground$syscallTable, %%eax\n"
841 "mov 0(%%eax), %%eax\n" 895 "mov 0(%%eax), %%eax\n"
842 "cmp $1, %%eax\n" 896 "cmp $1, %%eax\n"
843 "jne 25f\n" // exit process 897 "jne 25f\n" // exit process
844 898
845 // Default behavior for unrestricted system calls is to just execute 899 // Default behavior for unrestricted system calls is to just execute
846 // them. Read the remaining arguments first. 900 // them. Read the remaining arguments first.
847 "12:mov $3, %%eax\n" // NR_read 901 "13:mov $3, %%eax\n" // NR_read
848 "movd %%mm0, %%ebx\n" // fd = threadFd 902 "movd %%mm0, %%ebx\n" // fd = threadFd
849 "add $4, %%ecx\n" // buf = &scratch + 4 903 "add $4, %%ecx\n" // buf = &scratch + 4
850 "mov $24, %%edx\n" // len = 6*sizeof(void *) 904 "mov $24, %%edx\n" // len = 6*sizeof(void *)
851 "13:int $0x80\n" 905 "14:int $0x80\n"
852 "cmp $-4, %%eax\n" // EINTR 906 "cmp $-4, %%eax\n" // EINTR
853 "jz 13b\n" 907 "jz 14b\n"
854 "cmp %%edx, %%eax\n" 908 "cmp %%edx, %%eax\n"
855 "jnz 25f\n" // exit process 909 "jnz 25f\n" // exit process
856 "mov %%ebp, %%eax\n" 910 "mov %%ebp, %%eax\n"
857 "mov 0x00(%%ecx), %%ebx\n" 911 "mov 0x00(%%ecx), %%ebx\n"
858 "mov 0x08(%%ecx), %%edx\n" 912 "mov 0x08(%%ecx), %%edx\n"
859 "mov 0x0C(%%ecx), %%esi\n" 913 "mov 0x0C(%%ecx), %%esi\n"
860 "mov 0x10(%%ecx), %%edi\n" 914 "mov 0x10(%%ecx), %%edi\n"
861 "mov 0x14(%%ecx), %%ebp\n" 915 "mov 0x14(%%ecx), %%ebp\n"
862 "mov 0x04(%%ecx), %%ecx\n" 916 "mov 0x04(%%ecx), %%ecx\n"
863 "cmp $252, %%eax\n" // NR_exit_group 917 "cmp $252, %%eax\n" // NR_exit_group
864 "jz 26f\n" // exit program, no message 918 "jz 26f\n" // exit program, no message
865 "int $0x80\n" 919 "int $0x80\n"
866 920
867 // Return result of system call to sandboxed thread 921 // Return result of system call to sandboxed thread
868 "14:movd %%mm5, %%ecx\n" 922 "15:movd %%mm5, %%ecx\n"
869 "add $0x101C, %%ecx\n" // buf = &scratch + 28 923 "add $0x101C, %%ecx\n" // buf = &scratch + 28
870 "mov %%eax, (%%ecx)\n" 924 "mov %%eax, (%%ecx)\n"
871 "mov $4, %%edx\n" // len = 4 925 "mov $4, %%edx\n" // len = 4
872 "15:movd %%mm0, %%ebx\n" // fd = threadFd 926 "16:movd %%mm0, %%ebx\n" // fd = threadFd
873 "mov $4, %%eax\n" // NR_write 927 "mov $4, %%eax\n" // NR_write
874 "16:int $0x80\n" 928 "17:int $0x80\n"
875 "cmp %%edx, %%eax\n" 929 "cmp %%edx, %%eax\n"
876 "jz 1b\n" 930 "jz 1b\n"
877 "cmp $-4, %%eax\n" // EINTR 931 "cmp $-4, %%eax\n" // EINTR
878 "jz 16b\n" 932 "jz 17b\n"
879 "jmp 25f\n" // exit process 933 "jmp 25f\n" // exit process
880 934
881 // NR_exit: 935 // NR_exit:
882 // Exit trusted thread after cleaning up resources 936 // Exit trusted thread after cleaning up resources
883 "17:mov %%edi, %%ecx\n" 937 "18:mov %%edi, %%ecx\n"
884 "mov 0x68(%%ecx), %%ebx\n" // fd = threadFdPub 938 "mov 0x64(%%ecx), %%ebx\n" // fd = threadFdPub
885 "mov $6, %%eax\n" // NR_close 939 "mov $6, %%eax\n" // NR_close
886 "int $0x80\n" 940 "int $0x80\n"
887 "mov %%ecx, %%ebx\n" // start = secure_mem 941 "mov %%ecx, %%ebx\n" // start = secure_mem
888 "mov $8192, %%ecx\n" // length = 4096 942 "mov $8192, %%ecx\n" // length = 8192
889 "xor %%edx, %%edx\n" // prot = PROT_NONE 943 "xor %%edx, %%edx\n" // prot = PROT_NONE
890 "mov $125, %%eax\n" // NR_mprotect 944 "mov $125, %%eax\n" // NR_mprotect
891 "int $0x80\n" 945 "int $0x80\n"
892 "movd %%mm0, %%ebx\n" // fd = threadFd 946 "movd %%mm0, %%ebx\n" // fd = threadFd
893 "mov $6, %%eax\n" // NR_close 947 "mov $6, %%eax\n" // NR_close
894 "int $0x80\n" 948 "int $0x80\n"
895 "mov $120, %%eax\n" // NR_clone 949 "mov $120, %%eax\n" // NR_clone
896 "mov $17, %%ebx\n" // flags = SIGCHLD 950 "mov $17, %%ebx\n" // flags = SIGCHLD
897 "mov $1, %%ecx\n" // stack = 1 951 "mov $1, %%ecx\n" // stack = 1
898 "int $0x80\n" 952 "int $0x80\n"
899 "mov %%eax, %%ebx\n" 953 "mov %%eax, %%ebx\n"
900 "test %%eax, %%eax\n" 954 "test %%eax, %%eax\n"
955 "js 25f\n" // exit process
901 "jne 21f\n" // reap helper, exit thread 956 "jne 21f\n" // reap helper, exit thread
902 "jmp 22f\n" // unlock mutex 957 "jmp 22f\n" // unlock mutex
903 958
904 // NR_clone: 959 // NR_clone:
905 // Original trusted thread calls clone() to create new nascent 960 // Original trusted thread calls clone() to create new nascent
906 // thread. This thread is (typically) fully privileged and shares all 961 // thread. This thread is (typically) fully privileged and shares all
907 // resources with the caller (i.e. the previous trusted thread), 962 // resources with the caller (i.e. the previous trusted thread),
908 // and by extension it shares all resources with the sandbox'd 963 // and by extension it shares all resources with the sandbox'd
909 // threads. 964 // threads.
910 // N.B. It is possible to make the thread creation code crash before 965 // N.B. It is possible to make the thread creation code crash before
911 // it releases seccomp privileges. This is generally OK, as it just 966 // it releases seccomp privileges. This is generally OK, as it just
912 // terminates the program. But if we ever support signal handling, 967 // terminates the program. But if we ever support signal handling,
913 // we have to be careful that the user cannot install a SIGSEGV 968 // we have to be careful that the user cannot install a SIGSEGV
914 // handler that gets executed with elevated privileges. 969 // handler that gets executed with elevated privileges.
915 "18:movd %%edi, %%mm6\n" // %mm6 = old_shared_mem 970 "19:movd %%edi, %%mm6\n" // %mm6 = old_shared_mem
916 "movd %%mm4, %%edi\n" 971 "movd %%mm4, %%edi\n"
917 "movd %%mm7, %%ebp\n" 972 "movd %%mm7, %%ebp\n"
918 "int $0x80\n" // calls NR_clone 973 "int $0x80\n" // calls NR_clone
919 "cmp $-4095, %%eax\n" // return codes -1..-4095 are errno values 974 "cmp $-4095, %%eax\n" // return codes -1..-4095 are errno values
920 "jae 6b\n" 975 "jae 7b\n" // unlock mutex, return result
921 "movd %%mm2, %%edi\n" 976 "movd %%mm2, %%edi\n"
922 "add $2, %%edi\n" 977 "add $2, %%edi\n"
923 "movd %%edi, %%mm2\n" 978 "movd %%edi, %%mm2\n"
924 "test %%eax, %%eax\n" 979 "test %%eax, %%eax\n"
925 "jne 14b\n" // return result 980 "jne 15b\n" // return result
926 981
927 // In nascent thread, now. 982 // In nascent thread, now.
928 "sub $2, %%edi\n" 983 "sub $2, %%edi\n"
929 "movd %%edi, %%mm2\n" 984 "movd %%edi, %%mm2\n"
930 "movd %%eax, %%mm3\n" // Request to return from clone() when done 985 "movd %%eax, %%mm3\n" // Request to return from clone() when done
931 986
932 // Get thread id of nascent thread 987 // Get thread id of nascent thread
933 "19:mov $224, %%eax\n" // NR_gettid 988 "20:mov $224, %%eax\n" // NR_gettid
934 "int $0x80\n" 989 "int $0x80\n"
935 "movd %%eax, %%mm4\n" 990 "movd %%eax, %%mm4\n"
936 991
937 // Nascent thread creates socketpair() for sending requests to 992 // Nascent thread creates socketpair() for sending requests to
938 // trusted thread. 993 // trusted thread.
939 // We can create the filehandles on the stack. Filehandles are 994 // We can create the filehandles on the stack. Filehandles are
940 // always treated as untrusted. 995 // always treated as untrusted.
941 // socketpair(AF_UNIX, SOCK_STREAM, 0, fds) 996 // socketpair(AF_UNIX, SOCK_STREAM, 0, fds)
942 "mov $102, %%eax\n" // NR_socketcall 997 "mov $102, %%eax\n" // NR_socketcall
943 "mov $8, %%ebx\n" // socketpair 998 "mov $8, %%ebx\n" // socketpair
944 "sub $8, %%esp\n" // sv = %rsp 999 "sub $8, %%esp\n" // sv = %rsp
945 "push %%esp\n" 1000 "push %%esp\n"
946 "xor %%ecx, %%ecx\n" // protocol = 0 1001 "xor %%ecx, %%ecx\n" // protocol = 0
947 "push %%ecx\n" 1002 "push %%ecx\n"
948 "mov $1, %%ecx\n" // type = SOCK_STREAM 1003 "mov $1, %%ecx\n" // type = SOCK_STREAM
949 "push %%ecx\n" 1004 "push %%ecx\n"
950 "push %%ecx\n" // domain = AF_UNIX 1005 "push %%ecx\n" // domain = AF_UNIX
951 "mov %%esp, %%ecx\n" 1006 "mov %%esp, %%ecx\n"
952 "int $0x80\n" 1007 "int $0x80\n"
953 "add $0x10, %%esp\n" 1008 "add $0x10, %%esp\n"
954 "test %%eax, %%eax\n" 1009 "test %%eax, %%eax\n"
955 "jz 27f\n" 1010 "jz 27f\n"
956 1011
957 // If things went wrong, we don't have an (easy) way of signaling 1012 // If things went wrong, we don't have an (easy) way of signaling
958 // the parent. For our purposes, it is sufficient to fail with a 1013 // the parent. For our purposes, it is sufficient to fail with a
959 // fatal error. 1014 // fatal error.
960 "jmp 25f\n" // exit process 1015 "jmp 25f\n" // exit process
961 "20:mov $120, %%eax\n" // NR_clone
962 "mov $17, %%ebx\n" // flags = SIGCHLD
963 "mov $1, %%ecx\n" // stack = 1
964 "int $0x80\n"
965 "test %%eax, %%eax\n"
966 "js 25f\n" // exit process
967 "jz 22f\n" // unlock and exit
968 "mov %%eax, %%ebx\n"
969 "21:xor %%ecx, %%ecx\n" 1016 "21:xor %%ecx, %%ecx\n"
970 "xor %%edx, %%edx\n" 1017 "xor %%edx, %%edx\n"
971 "mov $7, %%eax\n" // NR_waitpid 1018 "mov $7, %%eax\n" // NR_waitpid
972 "int $0x80\n" 1019 "int $0x80\n"
973 "cmp $-4, %%eax\n" // EINTR 1020 "cmp $-4, %%eax\n" // EINTR
974 "jz 21b\n" 1021 "jz 21b\n"
975 "jmp 23f\n" // exit thread (no message) 1022 "jmp 23f\n" // exit thread (no message)
976 "22:lea playground$syscall_mutex, %%ebx\n" 1023 "22:lea playground$syscall_mutex, %%ebx\n"
977 "mov $4096, %%ecx\n" 1024 "mov $4096, %%ecx\n"
978 "mov $3, %%edx\n" // prot = PROT_READ | PROT_WRITE 1025 "mov $3, %%edx\n" // prot = PROT_READ | PROT_WRITE
979 "mov $125, %%eax\n" // NR_mprotect 1026 "mov $125, %%eax\n" // NR_mprotect
980 "int $0x80\n" 1027 "int $0x80\n"
981 "lock; addl $0x80000000, (%%ebx)\n" 1028 "lock; addl $0x80000000, (%%ebx)\n"
982 "jz 23f\n" // exit thread 1029 "jz 23f\n" // exit thread
983 "mov $1, %%edx\n" 1030 "mov $1, %%edx\n"
984 "mov %%edx, %%ecx\n" // FUTEX_WAKE 1031 "mov %%edx, %%ecx\n" // FUTEX_WAKE
985 "mov $240, %%eax\n" // NR_futex 1032 "mov $240, %%eax\n" // NR_futex
986 "int $0x80\n" 1033 "int $0x80\n"
987 "23:mov $1, %%eax\n" // NR_exit 1034 "23:mov $1, %%eax\n" // NR_exit
988 "mov $1, %%ebx\n" // status = 1 1035 "mov $1, %%ebx\n" // status = 1
989 "24:int $0x80\n" 1036 "24:int $0x80\n"
990 "25:mov $4, %%eax\n" // NR_write 1037 "25:mov $4, %%eax\n" // NR_write
991 "mov $2, %%ebx\n" // fd = stderr 1038 "mov $2, %%ebx\n" // fd = stderr
992 "lea 100f, %%ecx\n" 1039 "lea 100f, %%ecx\n" // "Sandbox violation detected"
993 "mov $101f-100f, %%edx\n" // len = strlen(msg) 1040 "mov $101f-100f, %%edx\n" // len = strlen(msg)
994 "int $0x80\n" 1041 "int $0x80\n"
995 "mov $1, %%ebx\n" 1042 "mov $1, %%ebx\n"
996 "26:mov $252, %%eax\n" // NR_exit_group 1043 "26:mov $252, %%eax\n" // NR_exit_group
997 "jmp 24b\n" 1044 "jmp 24b\n"
998 1045
999 // The first page is mapped read-only for use as securely shared memory 1046 // The first page is mapped read-only for use as securely shared memory
1000 "27:movd %%mm6, %%ebp\n" 1047 "27:movd %%mm6, %%ebp\n"
1001 "mov 0x44(%%ebp), %%esi\n" 1048 "mov 0x40(%%ebp), %%esi\n"
1002 "movd %%esi, %%mm5\n" // %mm5 = secure shared memory 1049 "movd %%esi, %%mm5\n" // %mm5 = secure shared memory
1003 "movd %%mm2, %%edi\n" 1050 "movd %%mm2, %%edi\n"
1004 "cmp %%edi, 4(%%ebp)\n" 1051 "cmp %%edi, 4(%%ebp)\n"
1005 "jne 25b\n" // exit process 1052 "jne 25b\n" // exit process
1006 "mov $125, %%eax\n" // NR_mprotect 1053 "mov $125, %%eax\n" // NR_mprotect
1007 "mov %%esi, %%ebx\n" 1054 "mov %%esi, %%ebx\n"
1008 "mov $4096, %%ecx\n" // len = 4096 1055 "mov $4096, %%ecx\n" // len = 4096
1009 "mov $1, %%edx\n" // prot = PROT_READ 1056 "mov $1, %%edx\n" // prot = PROT_READ
1010 "int $0x80\n" 1057 "int $0x80\n"
1011 1058
1012 // The second page is used as scratch space by the trusted thread. 1059 // The second page is used as scratch space by the trusted thread.
1013 // Make it writable. 1060 // Make it writable.
1014 "mov $125, %%eax\n" // NR_mprotect 1061 "mov $125, %%eax\n" // NR_mprotect
1015 "add $4096, %%ebx\n" // addr = secure_mem + 4096 1062 "add $4096, %%ebx\n" // addr = secure_mem + 4096
1016 "mov $3, %%edx\n" // prot = PROT_READ | PROT_WRITE 1063 "mov $3, %%edx\n" // prot = PROT_READ | PROT_WRITE
1017 "int $0x80\n" 1064 "int $0x80\n"
1018 1065
1019 // Call clone() to create new trusted thread(). 1066 // Call clone() to create new trusted thread().
1020 // clone(CLONE_VM|CLONE_FS|CLONE_FILES|CLONE_SIGHAND|CLONE_THREAD| 1067 // clone(CLONE_VM|CLONE_FS|CLONE_FILES|CLONE_SIGHAND|CLONE_THREAD|
1021 // CLONE_SYSVSEM|CLONE_UNTRACED, stack, NULL, NULL, NULL) 1068 // CLONE_SYSVSEM|CLONE_UNTRACED, stack, NULL, NULL, NULL)
1022 "mov 4(%%esp), %%eax\n" 1069 "mov 4(%%esp), %%eax\n"
1023 "movd %%eax, %%mm0\n" // %mm0 = threadFd 1070 "movd %%eax, %%mm0\n" // %mm0 = threadFd
1024 "mov $120, %%eax\n" // NR_clone 1071 "mov $120, %%eax\n" // NR_clone
1025 "mov $0x850F00, %%ebx\n" // flags = VM|FS|FILES|SIGH|THR|SYSV|UTR 1072 "mov $0x850F00, %%ebx\n" // flags = VM|FS|FILES|SIGH|THR|SYSV|UTR
1026 "mov $1, %%ecx\n" // stack = 1 1073 "mov $1, %%ecx\n" // stack = 1
1027 "movd 0x48(%%ebp), %%mm1\n" // %mm1 = processFdPub 1074 "movd 0x44(%%ebp), %%mm1\n" // %mm1 = processFdPub
1028 "cmp %%edi, 4(%%ebp)\n" 1075 "cmp %%edi, 4(%%ebp)\n"
1029 "jne 25b\n" // exit process 1076 "jne 25b\n" // exit process
1030 "int $0x80\n" 1077 "int $0x80\n"
1031 "test %%eax, %%eax\n" 1078 "test %%eax, %%eax\n"
1032 "js 25b\n" // exit process 1079 "js 25b\n" // exit process
1033 "jz 0b\n" // invoke trustedThreadFnc() 1080 "jz 0b\n" // invoke trustedThreadFnc()
1034 1081
1035 // Set up thread local storage 1082 // Set up thread local storage
1036 "mov $0x51, %%eax\n" // seg_32bit, limit_in_pages, useable 1083 "mov $0x51, %%eax\n" // seg_32bit, limit_in_pages, useable
1037 "push %%eax\n" 1084 "push %%eax\n"
1038 "mov $0xFFFFF, %%eax\n" // limit 1085 "mov $0xFFFFF, %%eax\n" // limit
1039 "push %%eax\n" 1086 "push %%eax\n"
1040 "add $0x58, %%esi\n" 1087 "add $0x54, %%esi\n"
1041 "push %%esi\n" // base_addr = &secure_mem.TLS 1088 "push %%esi\n" // base_addr = &secure_mem.TLS
1042 "mov %%fs, %%eax\n" 1089 "mov %%fs, %%eax\n"
1043 "shr $3, %%eax\n" 1090 "shr $3, %%eax\n"
1044 "push %%eax\n" // entry_number 1091 "push %%eax\n" // entry_number
1045 "mov $243, %%eax\n" // NR_set_thread_area 1092 "mov $243, %%eax\n" // NR_set_thread_area
1046 "mov %%esp, %%ebx\n" 1093 "mov %%esp, %%ebx\n"
1047 "int $0x80\n" 1094 "int $0x80\n"
1048 "test %%eax, %%eax\n" 1095 "test %%eax, %%eax\n"
1049 "jnz 25b\n" // exit process 1096 "jnz 25b\n" // exit process
1050 "add $16, %%esp\n" 1097 "add $16, %%esp\n"
(...skipping 22 matching lines...) Expand all
1073 "mov 0x2C(%%ebp), %%eax\n" 1120 "mov 0x2C(%%ebp), %%eax\n"
1074 "push %%eax\n" 1121 "push %%eax\n"
1075 "mov 0x30(%%ebp), %%eax\n" 1122 "mov 0x30(%%ebp), %%eax\n"
1076 "push %%eax\n" 1123 "push %%eax\n"
1077 "mov 0x34(%%ebp), %%eax\n" 1124 "mov 0x34(%%ebp), %%eax\n"
1078 "push %%eax\n" 1125 "push %%eax\n"
1079 "mov 0x38(%%ebp), %%eax\n" 1126 "mov 0x38(%%ebp), %%eax\n"
1080 "push %%eax\n" 1127 "push %%eax\n"
1081 "mov 0x3C(%%ebp), %%eax\n" 1128 "mov 0x3C(%%ebp), %%eax\n"
1082 "push %%eax\n" 1129 "push %%eax\n"
1083 "mov 0x40(%%ebp), %%eax\n"
1084 "push %%eax\n"
1085 "cmp %%edi, 4(%%ebp)\n" 1130 "cmp %%edi, 4(%%ebp)\n"
1086 "jne 25b\n" // exit process 1131 "jne 25b\n" // exit process
1087 1132
1088 // Nascent thread launches a helper that doesn't share any of our 1133 // Nascent thread launches a helper that doesn't share any of our
1089 // resources, except for pages mapped as MAP_SHARED. 1134 // resources, except for pages mapped as MAP_SHARED.
1090 // clone(0, %esp) 1135 // clone(0, %esp)
1091 "28:mov $120, %%eax\n" // NR_clone 1136 "28:mov $120, %%eax\n" // NR_clone
1092 "mov $17, %%ebx\n" // flags = SIGCHLD 1137 "mov $17, %%ebx\n" // flags = SIGCHLD
1093 "mov %%esp, %%ecx\n" // stack = %esp 1138 "mov %%esp, %%ecx\n" // stack = %esp
1094 "int $0x80\n" 1139 "int $0x80\n"
1095 "test %%eax, %%eax\n" 1140 "test %%eax, %%eax\n"
1096 "js 25b\n" // exit process 1141 "js 25b\n" // exit process
1097 "jne 29f\n" 1142 "jne 29f\n"
1098 1143
1099 // Use sendmsg() to send to the trusted process the file handles for 1144 // Use sendmsg() to send to the trusted process the file handles for
1100 // communicating with the new trusted thread. We also send the address 1145 // communicating with the new trusted thread. We also send the address
1101 // of the secure memory area (for sanity checks) and the thread id. 1146 // of the secure memory area (for sanity checks) and the thread id.
1102 "push %%esi\n" // threadFdPub 1147 "push %%esi\n" // threadFdPub
1103 "movd %%mm4, %%eax\n" // threadId 1148 "movd %%mm4, %%eax\n" // threadId
1104 "push %%eax\n" 1149 "push %%eax\n"
1105 "movd %%mm5, %%eax\n" // secure_mem 1150 "movd %%mm5, %%eax\n" // secure_mem
1106 "push %%eax\n" 1151 "push %%eax\n"
1107 "mov %%esp, %%ebx\n" // buf = &data 1152 "mov %%esp, %%ebx\n" // buf = &data
1108 "mov $12, %%eax\n" // len = sizeof(void*) + 2*sizeof(int) 1153 "mov $12, %%eax\n" // len = sizeof(void*) + 2*sizeof(int)
1109 "push %%eax\n" 1154 "push %%eax\n"
1110 "push %%ebx\n" 1155 "push %%ebx\n"
1111 "movd %%mm0, %%eax\n" // fd1 = threadFd 1156 "movd %%mm0, %%eax\n" // fd1 = threadFd
1112 "push %%eax\n" 1157 "push %%eax\n"
1113 "push %%esi\n" // fd0 = threadFdPub 1158 "push %%esi\n" // fd0 = threadFdPub
1114 "mov 0x4C(%%ebp), %%eax\n" // transport = Sandbox::cloneFdPub() 1159 "mov 0x48(%%ebp), %%eax\n" // transport = Sandbox::cloneFdPub()
1115 "cmp %%edi, 4(%%ebp)\n" 1160 "cmp %%edi, 4(%%ebp)\n"
1116 "jne 25b\n" // exit process 1161 "jne 25b\n" // exit process
1117 "push %%eax\n" 1162 "push %%eax\n"
1118 "call playground$sendFd\n" 1163 "call playground$sendFd\n"
1119 1164
1120 // Release syscall_mutex_. This signals the trusted process that 1165 // Release syscall_mutex_. This signals the trusted process that
1121 // it can write into the original thread's secure memory again. 1166 // it can write into the original thread's secure memory again.
1122 "mov $125, %%eax\n" // NR_mprotect 1167 "mov $125, %%eax\n" // NR_mprotect
1123 "lea playground$syscall_mutex, %%ebx\n" 1168 "lea playground$syscall_mutex, %%ebx\n"
1124 "mov $4096, %%ecx\n" 1169 "mov $4096, %%ecx\n"
1125 "mov $3, %%edx\n" // PROT_READ | PROT_WRITE 1170 "mov $3, %%edx\n" // PROT_READ | PROT_WRITE
1126 "int $0x80\n" 1171 "int $0x80\n"
1127 "lock; addl $0x80000000, (%%ebx)\n" 1172 "lock; addl $0x80000000, (%%ebx)\n"
1128 "jz 26b\n" // exit process (no error message) 1173 "jz 26b\n" // exit process (no error message)
1129 "mov $1, %%edx\n" 1174 "mov $1, %%edx\n"
1130 "mov %%edx, %%ecx\n" // FUTEX_WAKE 1175 "mov %%edx, %%ecx\n" // FUTEX_WAKE
1131 "mov $240, %%eax\n" // NR_futex 1176 "mov $240, %%eax\n" // NR_futex
1132 "int $0x80\n" 1177 "int $0x80\n"
1133 "jmp 26b\n" // exit process (no error message) 1178 "jmp 26b\n" // exit process (no error message)
1134 1179
1135 // Reap helper 1180 // Reap helper
1136 "29:mov %%eax, %%ebx\n" 1181 "29:mov %%eax, %%ebx\n"
1137 "30:xor %%ecx, %%ecx\n" 1182 "30:xor %%ecx, %%ecx\n"
1138 "xor %%edx, %%edx\n" 1183 "xor %%edx, %%edx\n"
1139 "mov $7, %%eax\n" // NR_waitpid 1184 "mov $7, %%eax\n" // NR_waitpid
1140 "int $0x80\n" 1185 "int $0x80\n"
1141 "cmp $-4, %%eax\n" // EINTR 1186 "cmp $-4, %%eax\n" // EINTR
1142 "jz 30\n" 1187 "jz 30b\n"
1143 1188
1144 // Release privileges by entering seccomp mode. 1189 // Release privileges by entering seccomp mode.
1145 "mov $172, %%eax\n" // NR_prctl 1190 "mov $172, %%eax\n" // NR_prctl
1146 "mov $22, %%ebx\n" // PR_SET_SECCOMP 1191 "mov $22, %%ebx\n" // PR_SET_SECCOMP
1147 "mov $1, %%ecx\n" 1192 "mov $1, %%ecx\n"
1148 "int $0x80\n" 1193 "int $0x80\n"
1149 "test %%eax, %%eax\n" 1194 "test %%eax, %%eax\n"
1150 "jnz 25b\n" // exit process 1195 "jnz 25b\n" // exit process
1151 1196
1152 // Back in the newly created sandboxed thread, wait for trusted process 1197 // Back in the newly created sandboxed thread, wait for trusted process
(...skipping 30 matching lines...) Expand all
1183 "32:pop %%ebx\n" 1228 "32:pop %%ebx\n"
1184 "pop %%ecx\n" 1229 "pop %%ecx\n"
1185 "pop %%edx\n" 1230 "pop %%edx\n"
1186 "pop %%esi\n" 1231 "pop %%esi\n"
1187 "pop %%edi\n" 1232 "pop %%edi\n"
1188 "pop %%ebp\n" 1233 "pop %%ebp\n"
1189 "ret\n" 1234 "ret\n"
1190 1235
1191 ".pushsection \".rodata\"\n" 1236 ".pushsection \".rodata\"\n"
1192 "100:.ascii \"Sandbox violation detected, program aborted\\n\"\n" 1237 "100:.ascii \"Sandbox violation detected, program aborted\\n\"\n"
1193 "101:\n" 1238 "101:.ascii \"WARNING! This is an expensive system call\\n\"\n"
1239 "102:\n"
1194 ".popsection\n" 1240 ".popsection\n"
1195 1241
1196 "999:pop %%ebp\n" 1242 "999:pop %%ebp\n"
1197 "pop %%ebx\n" 1243 "pop %%ebx\n"
1198 : 1244 :
1199 : "g"(&args) 1245 : "g"(&args)
1200 : "eax", "ecx", "edx", "edi", "esi", "esp", "memory" 1246 : "eax", "ecx", "edx", "edi", "esi", "esp", "memory"
1201 #else 1247 #else
1202 #error Unsupported target platform 1248 #error Unsupported target platform
1203 #endif 1249 #endif
1204 ); 1250 );
1205 } 1251 }
1206 1252
1207 } // namespace 1253 } // namespace
OLDNEW
« no previous file with comments | « sandbox/linux/seccomp/syscall.cc ('k') | sandbox/sandbox.gyp » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698