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

Side by Side Diff: content/browser/zygote_host/zygote_host_impl_linux.cc

Issue 269543014: Use RecvMsgWithPid to find real PID for zygote children (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Respond to jln feedback Created 6 years, 7 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
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/browser/zygote_host/zygote_host_impl_linux.h" 5 #include "content/browser/zygote_host/zygote_host_impl_linux.h"
6 6
7 #include <string.h> 7 #include <string.h>
8 #include <sys/socket.h> 8 #include <sys/socket.h>
9 #include <sys/stat.h> 9 #include <sys/stat.h>
10 #include <sys/types.h> 10 #include <sys/types.h>
(...skipping 276 matching lines...) Expand 10 before | Expand all | Expand 10 after
287 return HANDLE_EINTR(read(control_fd_, buf, buf_len)); 287 return HANDLE_EINTR(read(control_fd_, buf, buf_len));
288 } 288 }
289 289
290 pid_t ZygoteHostImpl::ForkRequest( 290 pid_t ZygoteHostImpl::ForkRequest(
291 const std::vector<std::string>& argv, 291 const std::vector<std::string>& argv,
292 const std::vector<FileDescriptorInfo>& mapping, 292 const std::vector<FileDescriptorInfo>& mapping,
293 const std::string& process_type) { 293 const std::string& process_type) {
294 DCHECK(init_); 294 DCHECK(init_);
295 Pickle pickle; 295 Pickle pickle;
296 296
297 int raw_socks[2];
298 PCHECK(0 == socketpair(AF_UNIX, SOCK_SEQPACKET, 0, raw_socks));
299 base::ScopedFD my_sock(raw_socks[0]);
300 base::ScopedFD peer_sock(raw_socks[1]);
301 CHECK(UnixDomainSocket::EnableReceiveProcessId(my_sock.get()));
302
297 pickle.WriteInt(kZygoteCommandFork); 303 pickle.WriteInt(kZygoteCommandFork);
298 pickle.WriteString(process_type); 304 pickle.WriteString(process_type);
299 pickle.WriteInt(argv.size()); 305 pickle.WriteInt(argv.size());
300 for (std::vector<std::string>::const_iterator 306 for (std::vector<std::string>::const_iterator
301 i = argv.begin(); i != argv.end(); ++i) 307 i = argv.begin(); i != argv.end(); ++i)
302 pickle.WriteString(*i); 308 pickle.WriteString(*i);
303 309
304 pickle.WriteInt(mapping.size()); 310 pickle.WriteInt(1 + mapping.size());
jln (very slow on Chromium) 2014/05/05 19:01:42 This should be documented. How about something suc
mdempsky 2014/05/05 21:38:18 Done. I implemented something slightly different
305 311
306 std::vector<int> fds; 312 std::vector<int> fds;
307 // Scoped pointers cannot be stored in containers, so we have to use a 313 ScopedVector<base::ScopedFD> autoclose_fds;
308 // linked_ptr. 314
309 std::vector<linked_ptr<base::ScopedFD> > autodelete_fds; 315 // First FD to send is peer_sock.
316 fds.push_back(peer_sock.get());
317 autoclose_fds.push_back(new base::ScopedFD(peer_sock.Pass()));
318
319 // The rest come from mapping.
310 for (std::vector<FileDescriptorInfo>::const_iterator 320 for (std::vector<FileDescriptorInfo>::const_iterator
311 i = mapping.begin(); i != mapping.end(); ++i) { 321 i = mapping.begin(); i != mapping.end(); ++i) {
312 pickle.WriteUInt32(i->id); 322 pickle.WriteUInt32(i->id);
313 fds.push_back(i->fd.fd); 323 fds.push_back(i->fd.fd);
314 if (i->fd.auto_close) { 324 if (i->fd.auto_close) {
315 // Auto-close means we need to close the FDs after they have been passed 325 // Auto-close means we need to close the FDs after they have been passed
316 // to the other process. 326 // to the other process.
317 linked_ptr<base::ScopedFD> ptr(new base::ScopedFD(fds.back())); 327 autoclose_fds.push_back(new base::ScopedFD(i->fd.fd));
318 autodelete_fds.push_back(ptr);
319 } 328 }
320 } 329 }
321 330
322 pid_t pid; 331 pid_t pid;
323 { 332 {
324 base::AutoLock lock(control_lock_); 333 base::AutoLock lock(control_lock_);
325 if (!SendMessage(pickle, &fds)) 334 if (!SendMessage(pickle, &fds))
326 return base::kNullProcessHandle; 335 return base::kNullProcessHandle;
336 autoclose_fds.clear();
337
338 {
339 char buf[sizeof(kZygoteChildPingMessage) + 1];
340 ScopedVector<base::ScopedFD> recv_fds;
341 base::ProcessId real_pid;
342
343 ssize_t n = UnixDomainSocket::RecvMsgWithPid(
344 my_sock.get(), buf, sizeof(buf), &recv_fds, &real_pid);
345 if (n != sizeof(kZygoteChildPingMessage) ||
346 0 != memcmp(buf,
347 kZygoteChildPingMessage,
348 sizeof(kZygoteChildPingMessage))) {
349 LOG(ERROR) << "Did not receive ping from zygote child";
350 real_pid = -1;
jln (very slow on Chromium) 2014/05/05 19:01:42 Add NOTREACHED()? I wouldn't be shocked by LOG(FAT
mdempsky 2014/05/05 21:38:18 Done. Went with LOG(FATAL).
351 }
352 my_sock.reset();
353
354 // Always send PID back to zygote.
355 Pickle pid_pickle;
356 pid_pickle.WriteInt(kZygoteCommandForkRealPID);
357 pid_pickle.WriteInt(real_pid);
358 if (!SendMessage(pid_pickle, NULL))
359 return base::kNullProcessHandle;
360 }
327 361
328 // Read the reply, which pickles the PID and an optional UMA enumeration. 362 // Read the reply, which pickles the PID and an optional UMA enumeration.
329 static const unsigned kMaxReplyLength = 2048; 363 static const unsigned kMaxReplyLength = 2048;
330 char buf[kMaxReplyLength]; 364 char buf[kMaxReplyLength];
331 const ssize_t len = ReadReply(buf, sizeof(buf)); 365 const ssize_t len = ReadReply(buf, sizeof(buf));
332 366
333 Pickle reply_pickle(buf, len); 367 Pickle reply_pickle(buf, len);
334 PickleIterator iter(reply_pickle); 368 PickleIterator iter(reply_pickle);
335 if (len <= 0 || !reply_pickle.ReadInt(&iter, &pid)) 369 if (len <= 0 || !reply_pickle.ReadInt(&iter, &pid))
336 return base::kNullProcessHandle; 370 return base::kNullProcessHandle;
(...skipping 183 matching lines...) Expand 10 before | Expand all | Expand 10 after
520 return RenderSandboxHostLinux::GetInstance()->pid(); 554 return RenderSandboxHostLinux::GetInstance()->pid();
521 } 555 }
522 556
523 int ZygoteHostImpl::GetSandboxStatus() const { 557 int ZygoteHostImpl::GetSandboxStatus() const {
524 if (have_read_sandbox_status_word_) 558 if (have_read_sandbox_status_word_)
525 return sandbox_status_; 559 return sandbox_status_;
526 return 0; 560 return 0;
527 } 561 }
528 562
529 } // namespace content 563 } // namespace content
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698