int translation_queue::find_dir_commits()

in src/translation_queue.h [65:126]


int translation_queue::find_dir_commits(sha1_ref head) {
  long long earliest_ct = LLONG_MAX;
  for (auto &source : sources) {
    if (source.is_repeat)
      continue;

    long long earliest_ct_for_source = LLONG_MAX;
    if (source.find_dir_commits(cache, earliest_ct_for_source))
      return error("failed to find commits for '" +
                   std::string(dirs.list[source.dir_index].name) + "'");
    earliest_ct = std::min(earliest_ct, earliest_ct_for_source);
  }

  // Nothing to do if we have no untranslated commits.
  if (earliest_ct == LLONG_MAX)
    return 0;

  for (auto &source : sources) {
    if (source.is_repeat)
      continue;
    if (source.fparents.empty())
      continue;
    if (!source.head)
      continue;

    // Lock in existing already translated commits (to be merged onto this
    // branch) if there is a dir head, which means this tool already ran on
    // this branch.  We have a precise ancestry path so we should typically
    // use it, merging in commits that have been translated on other branches.
    //
    // However, if it would be possible to fast-forward the monorepo head into
    // this directory, do not lock anything in.  We don't want to start
    // generating merges until we actually have different content.
    //
    // Look at the first commit in the queue.  Note that it's not clear how
    // the main head could be missing here, but certainly you can
    // fast-forward from nothing.
    sha1_ref mono;
    if (!head || (!cache.compute_mono(source.fparents.back().commit, mono) &&
                  !cache.merge_base_is_ancestor(head, mono))) {
      // Locking these in means we'll generate merges from them, even though
      // they've been translated on *some* branch already.
      source.lock_in_start_dir_commits();
      earliest_ct = std::min(earliest_ct, source.fparents.back().ct);
    }
  }

  // For every other dir, look back further past commits to translate.  We want
  // a head that matches the commit date of the earliest other commit we're
  // handling.
  std::string since = "--since=" + std::to_string(earliest_ct);
  for (auto &source : sources) {
    if (source.is_repeat)
      continue;
    if (source.head)
      continue;
    if (source.find_dir_commits_to_match_and_update_head(cache, since))
      return error("failed to list first parents limit for '" +
                   std::string(dirs.list[source.dir_index].name) + "'");
  }
  return 0;
}