Merge branch 'bw/realpath-wo-chdir'
authorJunio C Hamano <gitster@pobox.com>
Wed, 18 Jan 2017 23:12:16 +0000 (15:12 -0800)
committerJunio C Hamano <gitster@pobox.com>
Wed, 18 Jan 2017 23:12:16 +0000 (15:12 -0800)
The implementation of "real_path()" was to go there with chdir(2)
and call getcwd(3), but this obviously wouldn't be usable in a
threaded environment. Rewrite it to manually resolve relative
paths including symbolic links in path components.

* bw/realpath-wo-chdir:
real_path: set errno when max number of symlinks is exceeded
real_path: prevent redefinition of MAXSYMLINKS

1  2 
dir.c
diff --cc dir.c
index 4ac63bc940fa043fe82002dd6c282b0b5abcbad8,bfa8c8a9a51297c3a969c8706467504cb11ce51b..65c3e681b8e04aa47b6cf41faca0822ead59fb6a
--- 1/dir.c
--- 2/dir.c
+++ b/dir.c
@@@ -2725,40 -2748,3 +2725,40 @@@ void untracked_cache_add_to_index(struc
  {
        untracked_cache_invalidate_path(istate, path);
  }
-       char *git_dir = xstrdup(real_path(git_dir_));
-       char *work_tree = xstrdup(real_path(work_tree_));
 +
 +/* Update gitfile and core.worktree setting to connect work tree and git dir */
 +void connect_work_tree_and_git_dir(const char *work_tree_, const char *git_dir_)
 +{
 +      struct strbuf file_name = STRBUF_INIT;
 +      struct strbuf rel_path = STRBUF_INIT;
++      char *git_dir = real_pathdup(git_dir_);
++      char *work_tree = real_pathdup(work_tree_);
 +
 +      /* Update gitfile */
 +      strbuf_addf(&file_name, "%s/.git", work_tree);
 +      write_file(file_name.buf, "gitdir: %s",
 +                 relative_path(git_dir, work_tree, &rel_path));
 +
 +      /* Update core.worktree setting */
 +      strbuf_reset(&file_name);
 +      strbuf_addf(&file_name, "%s/config", git_dir);
 +      git_config_set_in_file(file_name.buf, "core.worktree",
 +                             relative_path(work_tree, git_dir, &rel_path));
 +
 +      strbuf_release(&file_name);
 +      strbuf_release(&rel_path);
 +      free(work_tree);
 +      free(git_dir);
 +}
 +
 +/*
 + * Migrate the git directory of the given path from old_git_dir to new_git_dir.
 + */
 +void relocate_gitdir(const char *path, const char *old_git_dir, const char *new_git_dir)
 +{
 +      if (rename(old_git_dir, new_git_dir) < 0)
 +              die_errno(_("could not migrate git directory from '%s' to '%s'"),
 +                      old_git_dir, new_git_dir);
 +
 +      connect_work_tree_and_git_dir(path, new_git_dir);
 +}