git-sh-setup: Fix scripts whose PWD is a symlink into a git work-dir

I want directories of my working tree to be linked to from various
paths on my filesystem where third-party components expect them, both
in development and production environments.  A build system's install
step could solve this, but I develop scripts and web pages that don't
need to be built.  Git's submodule system could solve this, but we
tend to develop, branch, and test those directories all in unison, so
one big repository feels more natural.  We prefer to edit and commit
on the symlinked paths, not the canonical ones, and in that setting,
"git pull" fails to find the top-level directory of the repository
while other commands work fine.

"git pull" fails because POSIX shells have a notion of current working
directory that is different from getcwd().  The shell stores this path
in PWD.  As a result, "cd ../" can be interpreted differently in a
shell script than chdir("../") in a C program.  The shell interprets
"../" by essentially stripping the last textual path component from
PWD, whereas C chdir() follows the ".." link in the current directory
on the filesystem.  When PWD is a symlink, these are different
destinations.  As a result, Git's C commands find the correct
top-level working tree, and shell scripts do not.

Changes:

* When interpreting a relative upward (../) path in cd_to_toplevel,
  prepend the cwd without symlinks, given by /bin/pwd
* Add tests for cd_to_toplevel and "git pull" in a symlinked
  directory that failed before this fix, plus contrasting scenarios
  that already worked

Signed-off-by: Marcel M. Cary <marcel@oak.homeunix.org>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
3 files changed
tree: 4727c50223b6301c49c2bb0b3e54c6927ce4377d
  1. arm/
  2. compat/
  3. contrib/
  4. Documentation/
  5. git-gui/
  6. gitk-git/
  7. gitweb/
  8. mozilla-sha1/
  9. perl/
  10. ppc/
  11. t/
  12. templates/
  13. xdiff/
  14. .gitattributes
  15. .gitignore
  16. .mailmap
  17. abspath.c
  18. alias.c
  19. alloc.c
  20. archive-tar.c
  21. archive-zip.c
  22. archive.c
  23. archive.h
  24. attr.c
  25. attr.h
  26. base85.c
  27. blob.c
  28. blob.h
  29. branch.c
  30. branch.h
  31. builtin-add.c
  32. builtin-annotate.c
  33. builtin-apply.c
  34. builtin-archive.c
  35. builtin-blame.c
  36. builtin-branch.c
  37. builtin-bundle.c
  38. builtin-cat-file.c
  39. builtin-check-attr.c
  40. builtin-check-ref-format.c
  41. builtin-checkout-index.c
  42. builtin-checkout.c
  43. builtin-clean.c
  44. builtin-clone.c
  45. builtin-commit-tree.c
  46. builtin-commit.c
  47. builtin-config.c
  48. builtin-count-objects.c
  49. builtin-describe.c
  50. builtin-diff-files.c
  51. builtin-diff-index.c
  52. builtin-diff-tree.c
  53. builtin-diff.c
  54. builtin-fast-export.c
  55. builtin-fetch--tool.c
  56. builtin-fetch-pack.c
  57. builtin-fetch.c
  58. builtin-fmt-merge-msg.c
  59. builtin-for-each-ref.c
  60. builtin-fsck.c
  61. builtin-gc.c
  62. builtin-grep.c
  63. builtin-help.c
  64. builtin-http-fetch.c
  65. builtin-init-db.c
  66. builtin-log.c
  67. builtin-ls-files.c
  68. builtin-ls-remote.c
  69. builtin-ls-tree.c
  70. builtin-mailinfo.c
  71. builtin-mailsplit.c
  72. builtin-merge-base.c
  73. builtin-merge-file.c
  74. builtin-merge-ours.c
  75. builtin-merge-recursive.c
  76. builtin-merge.c
  77. builtin-mv.c
  78. builtin-name-rev.c
  79. builtin-pack-objects.c
  80. builtin-pack-refs.c
  81. builtin-prune-packed.c
  82. builtin-prune.c
  83. builtin-push.c
  84. builtin-read-tree.c
  85. builtin-receive-pack.c
  86. builtin-reflog.c
  87. builtin-remote.c
  88. builtin-rerere.c
  89. builtin-reset.c
  90. builtin-rev-list.c
  91. builtin-rev-parse.c
  92. builtin-revert.c
  93. builtin-rm.c
  94. builtin-send-pack.c
  95. builtin-shortlog.c
  96. builtin-show-branch.c
  97. builtin-show-ref.c
  98. builtin-stripspace.c
  99. builtin-symbolic-ref.c
  100. builtin-tag.c
  101. builtin-tar-tree.c
  102. builtin-unpack-objects.c
  103. builtin-update-index.c
  104. builtin-update-ref.c
  105. builtin-upload-archive.c
  106. builtin-verify-pack.c
  107. builtin-verify-tag.c
  108. builtin-write-tree.c
  109. builtin.h
  110. bundle.c
  111. bundle.h
  112. cache-tree.c
  113. cache-tree.h
  114. cache.h
  115. check-builtins.sh
  116. check-racy.c
  117. check_bindir
  118. color.c
  119. color.h
  120. combine-diff.c
  121. command-list.txt
  122. commit.c
  123. commit.h
  124. config.c
  125. config.mak.in
  126. configure.ac
  127. connect.c
  128. convert.c
  129. copy.c
  130. COPYING
  131. csum-file.c
  132. csum-file.h
  133. ctype.c
  134. daemon.c
  135. date.c
  136. decorate.c
  137. decorate.h
  138. delta.h
  139. diff-delta.c
  140. diff-lib.c
  141. diff-no-index.c
  142. diff.c
  143. diff.h
  144. diffcore-break.c
  145. diffcore-delta.c
  146. diffcore-order.c
  147. diffcore-pickaxe.c
  148. diffcore-rename.c
  149. diffcore.h
  150. dir.c
  151. dir.h
  152. dump-cache-tree.c
  153. editor.c
  154. entry.c
  155. environment.c
  156. exec_cmd.c
  157. exec_cmd.h
  158. fast-import.c
  159. fetch-pack.h
  160. fixup-builtins
  161. fsck.c
  162. fsck.h
  163. generate-cmdlist.sh
  164. git-add--interactive.perl
  165. git-am.sh
  166. git-archimport.perl
  167. git-bisect.sh
  168. git-compat-util.h
  169. git-cvsexportcommit.perl
  170. git-cvsimport.perl
  171. git-cvsserver.perl
  172. git-filter-branch.sh
  173. git-instaweb.sh
  174. git-lost-found.sh
  175. git-merge-octopus.sh
  176. git-merge-one-file.sh
  177. git-merge-resolve.sh
  178. git-mergetool.sh
  179. git-parse-remote.sh
  180. git-pull.sh
  181. git-quiltimport.sh
  182. git-rebase--interactive.sh
  183. git-rebase.sh
  184. git-relink.perl
  185. git-repack.sh
  186. git-request-pull.sh
  187. git-send-email.perl
  188. git-sh-setup.sh
  189. git-stash.sh
  190. git-submodule.sh
  191. git-svn.perl
  192. GIT-VERSION-GEN
  193. git-web--browse.sh
  194. git.c
  195. git.spec.in
  196. graph.c
  197. graph.h
  198. grep.c
  199. grep.h
  200. hash-object.c
  201. hash.c
  202. hash.h
  203. help.c
  204. help.h
  205. http-push.c
  206. http-walker.c
  207. http.c
  208. http.h
  209. ident.c
  210. imap-send.c
  211. index-pack.c
  212. INSTALL
  213. levenshtein.c
  214. levenshtein.h
  215. list-objects.c
  216. list-objects.h
  217. ll-merge.c
  218. ll-merge.h
  219. lockfile.c
  220. log-tree.c
  221. log-tree.h
  222. mailmap.c
  223. mailmap.h
  224. Makefile
  225. match-trees.c
  226. merge-file.c
  227. merge-index.c
  228. merge-recursive.c
  229. merge-recursive.h
  230. merge-tree.c
  231. mktag.c
  232. mktree.c
  233. name-hash.c
  234. object.c
  235. object.h
  236. pack-check.c
  237. pack-redundant.c
  238. pack-refs.c
  239. pack-refs.h
  240. pack-revindex.c
  241. pack-revindex.h
  242. pack-write.c
  243. pack.h
  244. pager.c
  245. parse-options.c
  246. parse-options.h
  247. patch-delta.c
  248. patch-id.c
  249. patch-ids.c
  250. patch-ids.h
  251. path.c
  252. pkt-line.c
  253. pkt-line.h
  254. preload-index.c
  255. pretty.c
  256. progress.c
  257. progress.h
  258. quote.c
  259. quote.h
  260. reachable.c
  261. reachable.h
  262. read-cache.c
  263. README
  264. reflog-walk.c
  265. reflog-walk.h
  266. refs.c
  267. refs.h
  268. remote.c
  269. remote.h
  270. rerere.c
  271. rerere.h
  272. revision.c
  273. revision.h
  274. run-command.c
  275. run-command.h
  276. send-pack.h
  277. server-info.c
  278. setup.c
  279. sha1-lookup.c
  280. sha1-lookup.h
  281. sha1_file.c
  282. sha1_name.c
  283. shallow.c
  284. shell.c
  285. shortlog.h
  286. show-index.c
  287. sideband.c
  288. sideband.h
  289. strbuf.c
  290. strbuf.h
  291. string-list.c
  292. string-list.h
  293. symlinks.c
  294. tag.c
  295. tag.h
  296. tar.h
  297. test-chmtime.c
  298. test-date.c
  299. test-delta.c
  300. test-genrandom.c
  301. test-match-trees.c
  302. test-parse-options.c
  303. test-path-utils.c
  304. test-sha1.c
  305. test-sha1.sh
  306. thread-utils.c
  307. thread-utils.h
  308. trace.c
  309. transport.c
  310. transport.h
  311. tree-diff.c
  312. tree-walk.c
  313. tree-walk.h
  314. tree.c
  315. tree.h
  316. unpack-file.c
  317. unpack-trees.c
  318. unpack-trees.h
  319. update-server-info.c
  320. upload-pack.c
  321. usage.c
  322. userdiff.c
  323. userdiff.h
  324. utf8.c
  325. utf8.h
  326. var.c
  327. walker.c
  328. walker.h
  329. wrapper.c
  330. write_or_die.c
  331. ws.c
  332. wt-status.c
  333. wt-status.h
  334. xdiff-interface.c
  335. xdiff-interface.h