|
@@ -1541,41 +1541,73 @@ class Builder:
|
|
|
"""Prepare the working directory for a thread.
|
|
|
|
|
|
This clones or fetches the repo into the thread's work directory.
|
|
|
+ Optionally, it can create a linked working tree of the repo in the
|
|
|
+ thread's work directory instead.
|
|
|
|
|
|
Args:
|
|
|
thread_num: Thread number (0, 1, ...)
|
|
|
- setup_git: True to set up a git repo clone
|
|
|
+ setup_git:
|
|
|
+ 'clone' to set up a git clone
|
|
|
+ 'worktree' to set up a git worktree
|
|
|
"""
|
|
|
thread_dir = self.GetThreadDir(thread_num)
|
|
|
builderthread.Mkdir(thread_dir)
|
|
|
git_dir = os.path.join(thread_dir, '.git')
|
|
|
|
|
|
- # Clone the repo if it doesn't already exist
|
|
|
- # TODO(sjg@chromium): Perhaps some git hackery to symlink instead, so
|
|
|
- # we have a private index but uses the origin repo's contents?
|
|
|
+ # Create a worktree or a git repo clone for this thread if it
|
|
|
+ # doesn't already exist
|
|
|
if setup_git and self.git_dir:
|
|
|
src_dir = os.path.abspath(self.git_dir)
|
|
|
- if os.path.exists(git_dir):
|
|
|
+ if os.path.isdir(git_dir):
|
|
|
+ # This is a clone of the src_dir repo, we can keep using
|
|
|
+ # it but need to fetch from src_dir.
|
|
|
Print('\rFetching repo for thread %d' % thread_num,
|
|
|
newline=False)
|
|
|
gitutil.Fetch(git_dir, thread_dir)
|
|
|
terminal.PrintClear()
|
|
|
- else:
|
|
|
+ elif os.path.isfile(git_dir):
|
|
|
+ # This is a worktree of the src_dir repo, we don't need to
|
|
|
+ # create it again or update it in any way.
|
|
|
+ pass
|
|
|
+ elif os.path.exists(git_dir):
|
|
|
+ # Don't know what could trigger this, but we probably
|
|
|
+ # can't create a git worktree/clone here.
|
|
|
+ raise ValueError('Git dir %s exists, but is not a file '
|
|
|
+ 'or a directory.' % git_dir)
|
|
|
+ elif setup_git == 'worktree':
|
|
|
+ Print('\rChecking out worktree for thread %d' % thread_num,
|
|
|
+ newline=False)
|
|
|
+ gitutil.AddWorktree(src_dir, thread_dir)
|
|
|
+ terminal.PrintClear()
|
|
|
+ elif setup_git == 'clone' or setup_git == True:
|
|
|
Print('\rCloning repo for thread %d' % thread_num,
|
|
|
newline=False)
|
|
|
gitutil.Clone(src_dir, thread_dir)
|
|
|
terminal.PrintClear()
|
|
|
+ else:
|
|
|
+ raise ValueError("Can't setup git repo with %s." % setup_git)
|
|
|
|
|
|
def _PrepareWorkingSpace(self, max_threads, setup_git):
|
|
|
"""Prepare the working directory for use.
|
|
|
|
|
|
- Set up the git repo for each thread.
|
|
|
+ Set up the git repo for each thread. Creates a linked working tree
|
|
|
+ if git-worktree is available, or clones the repo if it isn't.
|
|
|
|
|
|
Args:
|
|
|
max_threads: Maximum number of threads we expect to need.
|
|
|
- setup_git: True to set up a git repo clone
|
|
|
+ setup_git: True to set up a git worktree or a git clone
|
|
|
"""
|
|
|
builderthread.Mkdir(self._working_dir)
|
|
|
+ if setup_git and self.git_dir:
|
|
|
+ src_dir = os.path.abspath(self.git_dir)
|
|
|
+ if gitutil.CheckWorktreeIsAvailable(src_dir):
|
|
|
+ setup_git = 'worktree'
|
|
|
+ # If we previously added a worktree but the directory for it
|
|
|
+ # got deleted, we need to prune its files from the repo so
|
|
|
+ # that we can check out another in its place.
|
|
|
+ gitutil.PruneWorktrees(src_dir)
|
|
|
+ else:
|
|
|
+ setup_git = 'clone'
|
|
|
for thread in range(max_threads):
|
|
|
self._PrepareThread(thread, setup_git)
|
|
|
|