Merge "Fix missing mode_t on Windows."
diff --git a/src/base/file_utils.cc b/src/base/file_utils.cc
index a51b9b2..6487dbd 100644
--- a/src/base/file_utils.cc
+++ b/src/base/file_utils.cc
@@ -53,7 +53,7 @@
 }
 
 bool ReadFile(const std::string& path, std::string* out) {
-  base::ScopedFile fd = base::OpenFile(path.c_str(), O_RDONLY);
+  base::ScopedFile fd = base::OpenFile(path, O_RDONLY);
   if (!fd)
     return false;
 
diff --git a/src/base/unix_socket_unittest.cc b/src/base/unix_socket_unittest.cc
index 382f9bc..887b9ec 100644
--- a/src/base/unix_socket_unittest.cc
+++ b/src/base/unix_socket_unittest.cc
@@ -200,8 +200,8 @@
   ASSERT_TRUE(srv_conn);
   ASSERT_TRUE(cli->is_connected());
 
-  ScopedFile null_fd(open("/dev/null", O_RDONLY));
-  ScopedFile zero_fd(open("/dev/zero", O_RDONLY));
+  ScopedFile null_fd(base::OpenFile("/dev/null", O_RDONLY));
+  ScopedFile zero_fd(base::OpenFile("/dev/zero", O_RDONLY));
 
   auto cli_did_recv = task_runner_.CreateCheckpoint("cli_did_recv");
   EXPECT_CALL(event_listener_, OnDataAvailable(cli.get()))
diff --git a/src/base/watchdog_posix.cc b/src/base/watchdog_posix.cc
index d8c064c..85cbb96 100644
--- a/src/base/watchdog_posix.cc
+++ b/src/base/watchdog_posix.cc
@@ -127,7 +127,7 @@
 }
 
 void Watchdog::ThreadMain() {
-  base::ScopedFile stat_fd(open("/proc/self/stat", O_RDONLY));
+  base::ScopedFile stat_fd(base::OpenFile("/proc/self/stat", O_RDONLY));
   if (!stat_fd) {
     PERFETTO_ELOG("Failed to open stat file to enforce resource limits.");
     return;
diff --git a/src/perfetto_cmd/perfetto_cmd.cc b/src/perfetto_cmd/perfetto_cmd.cc
index bd166ba..d2fb134 100644
--- a/src/perfetto_cmd/perfetto_cmd.cc
+++ b/src/perfetto_cmd/perfetto_cmd.cc
@@ -333,7 +333,7 @@
     // violation (about system_server ending up with a writable FD to our dir).
     char fdpath[64];
     sprintf(fdpath, "/proc/self/fd/%d", fileno(*trace_out_stream_));
-    base::ScopedFile read_only_fd(open(fdpath, O_RDONLY));
+    base::ScopedFile read_only_fd(base::OpenFile(fdpath, O_RDONLY));
     PERFETTO_CHECK(read_only_fd);
     trace_out_stream_.reset();
     android::binder::Status status =
@@ -359,7 +359,7 @@
     // If we are tracing to DropBox, there's no need to make a
     // filesystem-visible temporary file.
     // TODO(skyostil): Fall back to base::TempFile for older devices.
-    fd.reset(open(kTempDropBoxTraceDir, O_TMPFILE | O_RDWR, 0600));
+    fd = base::OpenFile(kTempDropBoxTraceDir, O_TMPFILE | O_RDWR, 0600);
     if (!fd) {
       PERFETTO_ELOG("Could not create a temporary trace file in %s",
                     kTempDropBoxTraceDir);
@@ -371,7 +371,7 @@
   } else if (trace_out_path_ == "-") {
     fd.reset(dup(STDOUT_FILENO));
   } else {
-    fd.reset(open(trace_out_path_.c_str(), O_RDWR | O_CREAT | O_TRUNC, 0600));
+    fd = base::OpenFile(trace_out_path_, O_RDWR | O_CREAT | O_TRUNC, 0600);
   }
   trace_out_stream_.reset(fdopen(fd.release(), "wb"));
   PERFETTO_CHECK(trace_out_stream_);
diff --git a/src/perfetto_cmd/rate_limiter.cc b/src/perfetto_cmd/rate_limiter.cc
index 081b6ed..af7ef7f 100644
--- a/src/perfetto_cmd/rate_limiter.cc
+++ b/src/perfetto_cmd/rate_limiter.cc
@@ -157,8 +157,7 @@
 }
 
 bool RateLimiter::LoadState(PerfettoCmdState* state) {
-  base::ScopedFile in_fd;
-  in_fd.reset(open(GetStateFilePath().c_str(), O_RDONLY));
+  base::ScopedFile in_fd(base::OpenFile(GetStateFilePath(), O_RDONLY));
 
   if (!in_fd)
     return false;
@@ -170,15 +169,14 @@
 }
 
 bool RateLimiter::SaveState(const PerfettoCmdState& state) {
-  base::ScopedFile out_fd;
   // Rationale for 0666: the cmdline client can be executed under two
   // different Unix UIDs: shell and statsd. If we run one after the
   // other and the file has 0600 permissions, then the 2nd run won't
   // be able to read the file and will clear it, aborting the trace.
   // SELinux still prevents that anything other than the perfetto
   // executable can change the guardrail file.
-  out_fd.reset(
-      open(GetStateFilePath().c_str(), O_WRONLY | O_CREAT | O_TRUNC, 0666));
+  base::ScopedFile out_fd(
+      base::OpenFile(GetStateFilePath(), O_WRONLY | O_CREAT | O_TRUNC, 0666));
   if (!out_fd)
     return false;
   char buf[1024];
diff --git a/src/perfetto_cmd/rate_limiter_unittest.cc b/src/perfetto_cmd/rate_limiter_unittest.cc
index 753e0e6..8a180a9 100644
--- a/src/perfetto_cmd/rate_limiter_unittest.cc
+++ b/src/perfetto_cmd/rate_limiter_unittest.cc
@@ -69,8 +69,7 @@
 };
 
 void WriteGarbageToFile(const std::string& path) {
-  base::ScopedFile fd;
-  fd.reset(open(path.c_str(), O_WRONLY | O_CREAT, 0600));
+  base::ScopedFile fd(base::OpenFile(path, O_WRONLY | O_CREAT, 0600));
   constexpr char data[] = "Some random bytes.";
   if (write(fd.get(), data, sizeof(data)) != sizeof(data))
     ADD_FAILURE() << "Could not write garbage";
diff --git a/src/profiling/memory/client.cc b/src/profiling/memory/client.cc
index 5c19059..1d63c83 100644
--- a/src/profiling/memory/client.cc
+++ b/src/profiling/memory/client.cc
@@ -171,9 +171,11 @@
   PERFETTO_DCHECK(pthread_key_.valid());
 
   uint64_t size = 0;
+  base::ScopedFile maps(base::OpenFile("/proc/self/maps", O_RDONLY));
+  base::ScopedFile mem(base::OpenFile("/proc/self/mem", O_RDONLY));
   int fds[2];
-  fds[0] = open("/proc/self/maps", O_RDONLY | O_CLOEXEC);
-  fds[1] = open("/proc/self/mem", O_RDONLY | O_CLOEXEC);
+  fds[0] = *maps;
+  fds[1] = *mem;
   auto fd = socket_pool_.Borrow();
   // Send an empty record to transfer fds for /proc/self/maps and
   // /proc/self/mem.
diff --git a/src/profiling/memory/client_unittest.cc b/src/profiling/memory/client_unittest.cc
index df848da..8b5d79b 100644
--- a/src/profiling/memory/client_unittest.cc
+++ b/src/profiling/memory/client_unittest.cc
@@ -25,15 +25,15 @@
 
 TEST(SocketPoolTest, Basic) {
   std::vector<base::ScopedFile> files;
-  files.emplace_back(open("/dev/null", O_RDONLY));
+  files.emplace_back(base::OpenFile("/dev/null", O_RDONLY));
   SocketPool pool(std::move(files));
   BorrowedSocket sock = pool.Borrow();
 }
 
 TEST(SocketPoolTest, Multiple) {
   std::vector<base::ScopedFile> files;
-  files.emplace_back(open("/dev/null", O_RDONLY));
-  files.emplace_back(open("/dev/null", O_RDONLY));
+  files.emplace_back(base::OpenFile("/dev/null", O_RDONLY));
+  files.emplace_back(base::OpenFile("/dev/null", O_RDONLY));
   SocketPool pool(std::move(files));
   BorrowedSocket sock = pool.Borrow();
   BorrowedSocket sock_2 = pool.Borrow();
@@ -41,7 +41,7 @@
 
 TEST(SocketPoolTest, Blocked) {
   std::vector<base::ScopedFile> files;
-  files.emplace_back(open("/dev/null", O_RDONLY));
+  files.emplace_back(base::OpenFile("/dev/null", O_RDONLY));
   SocketPool pool(std::move(files));
   BorrowedSocket sock = pool.Borrow();
   std::thread t([&pool] { pool.Borrow(); });
@@ -54,7 +54,7 @@
 
 TEST(SocketPoolTest, MultipleBlocked) {
   std::vector<base::ScopedFile> files;
-  files.emplace_back(open("/dev/null", O_RDONLY));
+  files.emplace_back(base::OpenFile("/dev/null", O_RDONLY));
   SocketPool pool(std::move(files));
   BorrowedSocket sock = pool.Borrow();
   std::thread t([&pool] { pool.Borrow(); });
diff --git a/src/profiling/memory/socket_listener_unittest.cc b/src/profiling/memory/socket_listener_unittest.cc
index 65d7455..f40cb9f 100644
--- a/src/profiling/memory/socket_listener_unittest.cc
+++ b/src/profiling/memory/socket_listener_unittest.cc
@@ -68,8 +68,9 @@
 
   task_runner.RunUntilCheckpoint("connected");
   uint64_t size = 1;
-  base::ScopedFile fds[2] = {base::ScopedFile(open("/dev/null", O_RDONLY)),
-                             base::ScopedFile(open("/dev/null", O_RDONLY))};
+  base::ScopedFile fds[2] = {
+      base::ScopedFile(base::OpenFile("/dev/null", O_RDONLY)),
+      base::ScopedFile(base::OpenFile("/dev/null", O_RDONLY))};
   int raw_fds[2] = {*fds[0], *fds[1]};
   ASSERT_TRUE(client_socket->Send(&size, sizeof(size), raw_fds,
                                   base::ArraySize(raw_fds),
diff --git a/src/profiling/memory/unwinding_unittest.cc b/src/profiling/memory/unwinding_unittest.cc
index f80a0ee..3993692 100644
--- a/src/profiling/memory/unwinding_unittest.cc
+++ b/src/profiling/memory/unwinding_unittest.cc
@@ -33,7 +33,7 @@
 namespace {
 
 TEST(UnwindingTest, StackMemoryOverlay) {
-  base::ScopedFile proc_mem(open("/proc/self/mem", O_RDONLY));
+  base::ScopedFile proc_mem(base::OpenFile("/proc/self/mem", O_RDONLY));
   ASSERT_TRUE(proc_mem);
   uint8_t fake_stack[1] = {120};
   StackMemory memory(*proc_mem, 0u, fake_stack, 1);
@@ -45,7 +45,7 @@
 TEST(UnwindingTest, StackMemoryNonOverlay) {
   uint8_t value = 52;
 
-  base::ScopedFile proc_mem(open("/proc/self/mem", O_RDONLY));
+  base::ScopedFile proc_mem(base::OpenFile("/proc/self/mem", O_RDONLY));
   ASSERT_TRUE(proc_mem);
   uint8_t fake_stack[1] = {120};
   StackMemory memory(*proc_mem, 0u, fake_stack, 1);
@@ -55,7 +55,7 @@
 }
 
 TEST(UnwindingTest, FileDescriptorMapsParse) {
-  base::ScopedFile proc_maps(open("/proc/self/maps", O_RDONLY));
+  base::ScopedFile proc_maps(base::OpenFile("/proc/self/maps", O_RDONLY));
   ASSERT_TRUE(proc_maps);
   FileDescriptorMaps maps(std::move(proc_maps));
   ASSERT_TRUE(maps.Parse());
@@ -119,8 +119,8 @@
 
 // TODO(fmayer): Investigate why this fails out of tree.
 TEST(UnwindingTest, MAYBE_DoUnwind) {
-  base::ScopedFile proc_maps(open("/proc/self/maps", O_RDONLY));
-  base::ScopedFile proc_mem(open("/proc/self/mem", O_RDONLY));
+  base::ScopedFile proc_maps(base::OpenFile("/proc/self/maps", O_RDONLY));
+  base::ScopedFile proc_mem(base::OpenFile("/proc/self/mem", O_RDONLY));
   GlobalCallstackTrie callsites;
   ProcessMetadata metadata(getpid(), std::move(proc_maps), std::move(proc_mem),
                            &callsites);
diff --git a/src/trace_processor/trace_processor_shell.cc b/src/trace_processor/trace_processor_shell.cc
index 487ac8f..05540e1 100644
--- a/src/trace_processor/trace_processor_shell.cc
+++ b/src/trace_processor/trace_processor_shell.cc
@@ -202,8 +202,7 @@
   TraceProcessor::Config config;
   config.optimization_mode = OptimizationMode::kMaxBandwidth;
   TraceProcessor tp(config);
-  base::ScopedFile fd;
-  fd.reset(open(trace_file_path, O_RDONLY));
+  base::ScopedFile fd(base::OpenFile(trace_file_path, O_RDONLY));
   PERFETTO_CHECK(fd);
 
   // Load the trace in chunks using async IO. We create a simple pipeline where,
diff --git a/src/traced/probes/ftrace/ftrace_controller.cc b/src/traced/probes/ftrace/ftrace_controller.cc
index 5cff028..08a1deb 100644
--- a/src/traced/probes/ftrace/ftrace_controller.cc
+++ b/src/traced/probes/ftrace/ftrace_controller.cc
@@ -73,18 +73,14 @@
 }
 
 void WriteToFile(const char* path, const char* str) {
-  int fd = open(path, O_WRONLY);
-  if (fd == -1)
+  auto fd = base::OpenFile(path, O_WRONLY);
+  if (!fd)
     return;
-  perfetto::base::ignore_result(write(fd, str, strlen(str)));
-  perfetto::base::ignore_result(close(fd));
+  perfetto::base::ignore_result(write(*fd, str, strlen(str)));
 }
 
 void ClearFile(const char* path) {
-  int fd = open(path, O_WRONLY | O_TRUNC);
-  if (fd == -1)
-    return;
-  perfetto::base::ignore_result(close(fd));
+  auto fd = base::OpenFile(path, O_WRONLY | O_TRUNC);
 }
 
 }  // namespace
diff --git a/src/traced/probes/ftrace/ftrace_controller_unittest.cc b/src/traced/probes/ftrace/ftrace_controller_unittest.cc
index 9e74a0a..aa059f8 100644
--- a/src/traced/probes/ftrace/ftrace_controller_unittest.cc
+++ b/src/traced/probes/ftrace/ftrace_controller_unittest.cc
@@ -163,7 +163,7 @@
   }
 
   base::ScopedFile OpenPipeForCpu(size_t /*cpu*/) override {
-    return base::ScopedFile(open("/dev/null", O_RDONLY));
+    return base::ScopedFile(base::OpenFile("/dev/null", O_RDONLY));
   }
 
   MOCK_METHOD2(WriteToFile,
diff --git a/src/traced/probes/sys_stats/sys_stats_data_source.cc b/src/traced/probes/sys_stats/sys_stats_data_source.cc
index cd6efd1..00ab945 100644
--- a/src/traced/probes/sys_stats/sys_stats_data_source.cc
+++ b/src/traced/probes/sys_stats/sys_stats_data_source.cc
@@ -45,8 +45,7 @@
 constexpr size_t kReadBufSize = 1024 * 16;
 
 base::ScopedFile OpenReadOnly(const char* path) {
-  base::ScopedFile fd;
-  fd.reset(open(path, O_RDONLY | O_CLOEXEC));
+  base::ScopedFile fd(base::OpenFile(path, O_RDONLY));
   if (!fd)
     PERFETTO_PLOG("Failed opening %s", path);
   return fd;
diff --git a/tools/pipestats.cc b/tools/pipestats.cc
index d82ecbb..15fbe27 100644
--- a/tools/pipestats.cc
+++ b/tools/pipestats.cc
@@ -47,7 +47,7 @@
 
 int PipestatsMain(int argc, char** argv) {
   PERFETTO_CHECK(argc == 2);
-  base::ScopedFile trace_fd(open(argv[1], O_RDONLY));
+  base::ScopedFile trace_fd(base::OpenFile(argv[1], O_RDONLY));
   PERFETTO_CHECK(trace_fd);
   std::thread reader(ReadLoop, trace_fd.get());