bool MakeDirs()

in tools/common/file_system.cc [94:141]


bool MakeDirs(const std::string &path, int mode) {
  // If we got an empty string, we've recursed past the first segment in the
  // path. Assume it exists (if it doesn't, we'll fail when we try to create a
  // directory inside it).
  if (path.empty()) {
    return true;
  }

  struct stat dir_stats;
  if (stat(path.c_str(), &dir_stats) == 0) {
    // Return true if the directory already exists.
    if (S_ISDIR(dir_stats.st_mode)) {
      return true;
    }

    std::cerr << "error: path already exists but is not a directory: "
              << path << "\n";
    return false;
  }

  // Recurse to create the parent directory.
  if (!MakeDirs(Dirname(path).c_str(), mode)) {
    return false;
  }

  // Create the directory that was requested.
  if (mkdir(path.c_str(), mode) == 0) {
    return true;
  }

  // Race condition: The above call to `mkdir` could fail if there are multiple
  // calls to `MakeDirs` running at the same time with overlapping paths, so
  // check again to see if the directory exists despite the call failing. If it
  // does, that's ok.
  if (errno == EEXIST && stat(path.c_str(), &dir_stats) == 0) {
    if (S_ISDIR(dir_stats.st_mode)) {
      return true;
    }

    std::cerr << "error: path already exists but is not a directory: "
              << path << "\n";
    return false;
  }

  std::cerr << "error: could not create directory: " << path
            << " (" << strerror(errno) << ")\n";
  return false;
}