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

Side by Side Diff: content/common/sandbox_init_linux.cc

Issue 10454110: Block ptrace (and ptrace-like) syscalls from the renderer and worker processs. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src/
Patch Set: Created 8 years, 6 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 | « no previous file | content/renderer/renderer_main_platform_delegate_linux.cc » ('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) 2012 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "content/public/common/sandbox_init.h" 5 #include "content/public/common/sandbox_init.h"
6 6
7 #if defined(OS_LINUX) && defined(__x86_64__) 7 #if defined(OS_LINUX) && defined(__x86_64__)
8 8
9 #include <asm/unistd.h> 9 #include <asm/unistd.h>
10 #include <errno.h> 10 #include <errno.h>
(...skipping 30 matching lines...) Expand all
41 #endif 41 #endif
42 42
43 #ifndef __NR_readlinkat 43 #ifndef __NR_readlinkat
44 #define __NR_readlinkat 267 44 #define __NR_readlinkat 267
45 #endif 45 #endif
46 46
47 #ifndef __NR_eventfd2 47 #ifndef __NR_eventfd2
48 #define __NR_eventfd2 290 48 #define __NR_eventfd2 290
49 #endif 49 #endif
50 50
51 #ifndef __NR_process_vm_readv
52 #define __NR_process_vm_readv 310
53 #endif
54
55 #ifndef __NR_process_vm_writev
56 #define __NR_process_vm_writev 311
57 #endif
58
51 // Constants from very new header files that we can't yet include. 59 // Constants from very new header files that we can't yet include.
52 #ifndef SECCOMP_MODE_FILTER 60 #ifndef SECCOMP_MODE_FILTER
53 #define SECCOMP_MODE_FILTER 2 61 #define SECCOMP_MODE_FILTER 2
54 #define SECCOMP_RET_KILL 0x00000000U 62 #define SECCOMP_RET_KILL 0x00000000U
55 #define SECCOMP_RET_TRAP 0x00030000U 63 #define SECCOMP_RET_TRAP 0x00030000U
56 #define SECCOMP_RET_ERRNO 0x00050000U 64 #define SECCOMP_RET_ERRNO 0x00050000U
57 #define SECCOMP_RET_ALLOW 0x7fff0000U 65 #define SECCOMP_RET_ALLOW 0x7fff0000U
58 #endif 66 #endif
59 67
60 68
(...skipping 97 matching lines...) Expand 10 before | Expand all | Expand 10 after
158 // "4" is magic offset for the arch number. 166 // "4" is magic offset for the arch number.
159 EmitLoad(4, program); 167 EmitLoad(4, program);
160 EmitJEQJT1(AUDIT_ARCH_X86_64, program); 168 EmitJEQJT1(AUDIT_ARCH_X86_64, program);
161 EmitRet(SECCOMP_RET_KILL, program); 169 EmitRet(SECCOMP_RET_KILL, program);
162 170
163 // Load the syscall number. 171 // Load the syscall number.
164 // "0" is magic offset for the syscall number. 172 // "0" is magic offset for the syscall number.
165 EmitLoad(0, program); 173 EmitLoad(0, program);
166 } 174 }
167 175
176 static void EmitTrap(std::vector<struct sock_filter>* program) {
177 EmitRet(SECCOMP_RET_TRAP, program);
178 }
179
180 static void EmitAllow(std::vector<struct sock_filter>* program) {
181 EmitRet(SECCOMP_RET_ALLOW, program);
182 }
183
168 static void EmitAllowSyscall(int nr, std::vector<struct sock_filter>* program) { 184 static void EmitAllowSyscall(int nr, std::vector<struct sock_filter>* program) {
169 EmitJEQJF(nr, 1, program); 185 EmitJEQJF(nr, 1, program);
170 EmitRet(SECCOMP_RET_ALLOW, program); 186 EmitAllow(program);
187 }
188
189 static void EmitDenySyscall(int nr, std::vector<struct sock_filter>* program) {
190 EmitJEQJF(nr, 1, program);
191 EmitTrap(program);
171 } 192 }
172 193
173 static void EmitAllowSyscallArgN(int nr, 194 static void EmitAllowSyscallArgN(int nr,
174 int arg_nr, 195 int arg_nr,
175 int arg_val, 196 int arg_val,
176 std::vector<struct sock_filter>* program) { 197 std::vector<struct sock_filter>* program) {
177 // Jump forward 4 on no-match so that we also skip the unneccessary reload of 198 // Jump forward 4 on no-match so that we also skip the unneccessary reload of
178 // syscall_nr. (It is unneccessary because we have not trashed it yet.) 199 // syscall_nr. (It is unneccessary because we have not trashed it yet.)
179 EmitJEQJF(nr, 4, program); 200 EmitJEQJF(nr, 4, program);
180 EmitLoadArg(arg_nr, program); 201 EmitLoadArg(arg_nr, program);
181 EmitJEQJF(arg_val, 1, program); 202 EmitJEQJF(arg_val, 1, program);
182 EmitRet(SECCOMP_RET_ALLOW, program); 203 EmitAllow(program);
183 // We trashed syscall_nr so put it back in the accumulator. 204 // We trashed syscall_nr so put it back in the accumulator.
184 EmitLoad(0, program); 205 EmitLoad(0, program);
185 } 206 }
186 207
187 static void EmitFailSyscall(int nr, int err, 208 static void EmitFailSyscall(int nr, int err,
188 std::vector<struct sock_filter>* program) { 209 std::vector<struct sock_filter>* program) {
189 EmitJEQJF(nr, 1, program); 210 EmitJEQJF(nr, 1, program);
190 EmitRet(SECCOMP_RET_ERRNO | err, program); 211 EmitRet(SECCOMP_RET_ERRNO | err, program);
191 } 212 }
192 213
193 static void EmitTrap(std::vector<struct sock_filter>* program) {
194 EmitRet(SECCOMP_RET_TRAP, program);
195 }
196
197 // TODO(cevans) -- only really works as advertised once we restrict clone() 214 // TODO(cevans) -- only really works as advertised once we restrict clone()
198 // to CLONE_THREAD. 215 // to CLONE_THREAD.
199 static void EmitAllowSignalSelf(std::vector<struct sock_filter>* program) { 216 static void EmitAllowSignalSelf(std::vector<struct sock_filter>* program) {
200 EmitAllowSyscallArgN(__NR_kill, 1, getpid(), program); 217 EmitAllowSyscallArgN(__NR_kill, 1, getpid(), program);
201 EmitAllowSyscallArgN(__NR_tgkill, 1, getpid(), program); 218 EmitAllowSyscallArgN(__NR_tgkill, 1, getpid(), program);
202 } 219 }
203 220
204 static void EmitAllowGettime(std::vector<struct sock_filter>* program) { 221 static void EmitAllowGettime(std::vector<struct sock_filter>* program) {
205 EmitAllowSyscall(__NR_clock_gettime, program); 222 EmitAllowSyscall(__NR_clock_gettime, program);
206 EmitAllowSyscall(__NR_gettimeofday, program); 223 EmitAllowSyscall(__NR_gettimeofday, program);
(...skipping 119 matching lines...) Expand 10 before | Expand all | Expand 10 after
326 EmitAllowSignalSelf(program); 343 EmitAllowSignalSelf(program);
327 344
328 // These are under investigation, and hopefully not here for the long term. 345 // These are under investigation, and hopefully not here for the long term.
329 EmitAllowSyscall(__NR_shmctl, program); 346 EmitAllowSyscall(__NR_shmctl, program);
330 EmitAllowSyscall(__NR_shmat, program); 347 EmitAllowSyscall(__NR_shmat, program);
331 EmitAllowSyscall(__NR_shmdt, program); 348 EmitAllowSyscall(__NR_shmdt, program);
332 349
333 EmitSetupEmptyFileSystem(program); 350 EmitSetupEmptyFileSystem(program);
334 } 351 }
335 352
353 static void ApplyNoPtracePolicy(std::vector<struct sock_filter>* program) {
354 EmitDenySyscall(__NR_ptrace, program);
355 EmitDenySyscall(__NR_process_vm_readv, program);
356 EmitDenySyscall(__NR_process_vm_writev, program);
jln (very slow on Chromium) 2012/06/01 18:34:37 Not a huge deal, but maybe add move_pages and migr
357 }
358
336 static bool CanUseSeccompFilters() { 359 static bool CanUseSeccompFilters() {
337 int ret = prctl(PR_SET_SECCOMP, SECCOMP_MODE_FILTER, 0, 0, 0); 360 int ret = prctl(PR_SET_SECCOMP, SECCOMP_MODE_FILTER, 0, 0, 0);
338 if (ret != 0 && errno == EFAULT) 361 if (ret != 0 && errno == EFAULT)
339 return true; 362 return true;
340 return false; 363 return false;
341 } 364 }
342 365
343 static void InstallFilter(const std::vector<struct sock_filter>& program) { 366 static void InstallFilter(const std::vector<struct sock_filter>& program) {
344 int ret = prctl(PR_SET_NO_NEW_PRIVS, 1, 0, 0, 0); 367 int ret = prctl(PR_SET_NO_NEW_PRIVS, 1, 0, 0, 0);
345 PLOG_IF(FATAL, ret != 0) << "prctl(PR_SET_NO_NEW_PRIVS) failed"; 368 PLOG_IF(FATAL, ret != 0) << "prctl(PR_SET_NO_NEW_PRIVS) failed";
(...skipping 27 matching lines...) Expand all
373 396
374 CheckSingleThreaded(); 397 CheckSingleThreaded();
375 398
376 std::vector<struct sock_filter> program; 399 std::vector<struct sock_filter> program;
377 EmitPreamble(&program); 400 EmitPreamble(&program);
378 401
379 if (process_type == switches::kGpuProcess) { 402 if (process_type == switches::kGpuProcess) {
380 ApplyGPUPolicy(&program); 403 ApplyGPUPolicy(&program);
381 } else if (process_type == switches::kPpapiPluginProcess) { 404 } else if (process_type == switches::kPpapiPluginProcess) {
382 ApplyFlashPolicy(&program); 405 ApplyFlashPolicy(&program);
406 } else if (process_type == switches::kRendererProcess ||
407 process_type == switches::kWorkerProcess) {
408 ApplyNoPtracePolicy(&program);
383 } else { 409 } else {
jln (very slow on Chromium) 2012/06/01 18:34:37 This whole section (up to line 418) is becoming di
384 NOTREACHED(); 410 NOTREACHED();
385 } 411 }
386 412
387 EmitTrap(&program); 413 if (process_type == switches::kRendererProcess ||
414 process_type == switches::kWorkerProcess) {
415 EmitAllow(&program);
416 } else {
417 EmitTrap(&program);
418 }
388 419
389 InstallSIGSYSHandler(); 420 InstallSIGSYSHandler();
390 InstallFilter(program); 421 InstallFilter(program);
391 } 422 }
392 423
393 } // namespace content 424 } // namespace content
394 425
395 #else 426 #else
396 427
397 namespace content { 428 namespace content {
398 429
399 void InitializeSandbox() { 430 void InitializeSandbox() {
400 } 431 }
401 432
402 } // namespace content 433 } // namespace content
403 434
404 #endif 435 #endif
405 436
OLDNEW
« no previous file with comments | « no previous file | content/renderer/renderer_main_platform_delegate_linux.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698