summaryrefslogtreecommitdiff
path: root/path.c
AgeCommit message (Collapse)AuthorFilesLines
2016-02-03Merge branch 'js/dirname-basename'Libravatar Junio C Hamano1-9/+5
dirname() emulation has been added, as Msys2 lacks it. * js/dirname-basename: mingw: avoid linking to the C library's isalpha() t0060: loosen overly strict expectations t0060: verify that basename() and dirname() work as expected compat/basename.c: provide a dirname() compatibility function compat/basename: make basename() conform to POSIX Refactor skipping DOS drive prefixes
2016-01-12Refactor skipping DOS drive prefixesLibravatar Johannes Schindelin1-9/+5
Junio noticed that there is an implicit assumption in pretty much all the code calling has_dos_drive_prefix(): it forces all of its callsites to hardcode the knowledge that the DOS drive prefix is always two bytes long. While this assumption is pretty safe, we can still make the code more readable and less error-prone by introducing a function that skips the DOS drive prefix safely. While at it, we change the has_dos_drive_prefix() return value: it now returns the number of bytes to be skipped if there is a DOS drive prefix. Signed-off-by: Johannes Schindelin <johannes.schindelin@gmx.de> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2015-12-08Merge branch 'dt/refs-backend-pre-vtable'Libravatar Junio C Hamano1-0/+12
Code preparation for pluggable ref backends. * dt/refs-backend-pre-vtable: refs: break out ref conflict checks files_log_ref_write: new function initdb: make safe_create_dir public refs: split filesystem-based refs code into a new file refs/refs-internal.h: new header file refname_is_safe(): improve docstring pack_if_possible_fn(): use ref_type() instead of is_per_worktree_ref() copy_msg(): rename to copy_reflog_msg() verify_refname_available(): new function verify_refname_available(): rename function
2015-12-04Merge branch 'dk/gc-idx-wo-pack' into maintLibravatar Junio C Hamano1-1/+1
Having a leftover .idx file without corresponding .pack file in the repository hurts performance; "git gc" learned to prune them. We may want to do the same for .bitmap (and notice but not prune .keep) without corresponding .pack, but that can be a separate topic. * dk/gc-idx-wo-pack: gc: remove garbage .idx files from pack dir t5304: test cleaning pack garbage prepare_packed_git(): refactor garbage reporting in pack directory
2015-11-20Merge branch 'dk/gc-idx-wo-pack'Libravatar Jeff King1-1/+1
Having a leftover .idx file without corresponding .pack file in the repository hurts performance; "git gc" learned to prune them. * dk/gc-idx-wo-pack: gc: remove garbage .idx files from pack dir t5304: test cleaning pack garbage prepare_packed_git(): refactor garbage reporting in pack directory
2015-11-20initdb: make safe_create_dir publicLibravatar David Turner1-0/+12
Soon we will want to create initdb functions for ref backends, and code from initdb that calls this function needs to move into the files backend. So this function needs to be public. Signed-off-by: David Turner <dturner@twopensource.com> Signed-off-by: Junio C Hamano <gitster@pobox.com> Signed-off-by: Michael Haggerty <mhagger@alum.mit.edu> Signed-off-by: Jeff King <peff@peff.net>
2015-11-05Merge branch 'nd/clone-linked-checkout' into maintLibravatar Junio C Hamano1-5/+9
It was not possible to use a repository-lookalike created by "git worktree add" as a local source of "git clone". * nd/clone-linked-checkout: clone: better error when --reference is a linked checkout clone: allow --local from a linked checkout enter_repo: allow .git files in strict mode enter_repo: avoid duplicating logic, use is_git_directory() instead t0002: add test for enter_repo(), non-strict mode path.c: delete an extra space
2015-11-03Merge branch 'mk/submodule-gitdir-path' into maintLibravatar Junio C Hamano1-4/+18
The submodule code has been taught to work better with separate work trees created via "git worktree add". * mk/submodule-gitdir-path: path: implement common_dir handling in git_pathdup_submodule() submodule refactor: use strbuf_git_path_submodule() in add_submodule_odb()
2015-10-20Merge branch 'jk/war-on-sprintf'Libravatar Junio C Hamano1-34/+46
Many allocations that is manually counted (correctly) that are followed by strcpy/sprintf have been replaced with a less error prone constructs such as xstrfmt. Macintosh-specific breakage was noticed and corrected in this reroll. * jk/war-on-sprintf: (70 commits) name-rev: use strip_suffix to avoid magic numbers use strbuf_complete to conditionally append slash fsck: use for_each_loose_file_in_objdir Makefile: drop D_INO_IN_DIRENT build knob fsck: drop inode-sorting code convert strncpy to memcpy notes: document length of fanout path with a constant color: add color_set helper for copying raw colors prefer memcpy to strcpy help: clean up kfmclient munging receive-pack: simplify keep_arg computation avoid sprintf and strcpy with flex arrays use alloc_ref rather than hand-allocating "struct ref" color: add overflow checks for parsing colors drop strcpy in favor of raw sha1_to_hex use sha1_to_hex_r() instead of strcpy daemon: use cld->env_array when re-spawning stat_tracking_info: convert to argv_array http-push: use an argv_array for setup_revisions fetch-pack: use argv_array for index-pack / unpack-objects ...
2015-10-16Merge branch 'rd/test-path-utils'Libravatar Junio C Hamano1-0/+5
The normalize_ceiling_entry() function does not muck with the end of the path it accepts, and the real world callers do rely on that, but a test insisted that the function drops a trailing slash. * rd/test-path-utils: test-path-utils.c: remove incorrect assumption
2015-10-15Merge branch 'nd/clone-linked-checkout'Libravatar Junio C Hamano1-4/+8
It was not possible to use a repository-lookalike created by "git worktree add" as a local source of "git clone". * nd/clone-linked-checkout: clone: better error when --reference is a linked checkout clone: allow --local from a linked checkout enter_repo: allow .git files in strict mode enter_repo: avoid duplicating logic, use is_git_directory() instead t0002: add test for enter_repo(), non-strict mode path.c: delete an extra space
2015-10-15Merge branch 'mk/submodule-gitdir-path'Libravatar Junio C Hamano1-4/+17
The submodule code has been taught to work better with separate work trees created via "git worktree add". * mk/submodule-gitdir-path: path: implement common_dir handling in git_pathdup_submodule() submodule refactor: use strbuf_git_path_submodule() in add_submodule_odb()
2015-10-08test-path-utils.c: remove incorrect assumptionLibravatar Ray Donnelly1-0/+5
In normalize_ceiling_entry(), we test that normalized paths end with slash, *unless* the path to be normalized was already the root directory. However, normalize_path_copy() does not even enforce this condition. Even worse: on Windows, the root directory gets translated into a Windows directory by the Bash before being passed to `git.exe` (or `test-path-utils.exe`), which means that we cannot even know whether the path that was passed to us was the root directory to begin with. This issue has already caused endless hours of trying to "fix" the MSYS2 runtime, only to break other things due to MSYS2 ensuring that the converted path maintains the same state as the input path with respect to any final '/'. So let's just forget about this test. It is non-essential to Git's operation, anyway. Acked-by: Johannes Schindelin <johannes.schindelin@gmx.de> Signed-off-by: Ray Donnelly <mingw.android@gmail.com>
2015-10-05use strbuf_complete to conditionally append slashLibravatar Jeff King1-2/+1
When working with paths in strbufs, we frequently want to ensure that a directory contains a trailing slash before appending to it. We can shorten this code (and make the intent more obvious) by calling strbuf_complete. Most of these cases are trivially identical conversions, but there are two things to note: - in a few cases we did not check that the strbuf is non-empty (which would lead to an out-of-bounds memory access). These were generally not triggerable in practice, either from earlier assertions, or typically because we would have just fed the strbuf to opendir(), which would choke on an empty path. - in a few cases we indexed the buffer with "original_len" or similar, rather than the current sb->len, and it is not immediately obvious from the diff that they are the same. In all of these cases, I manually verified that the strbuf does not change between the assignment and the strbuf_complete call. This does not convert cases which look like: if (sb->len && !is_dir_sep(sb->buf[sb->len - 1])) strbuf_addch(sb, '/'); as those are obviously semantically different. Some of these cases arguably should be doing that, but that is out of scope for this change, which aims purely for cleanup with no behavior change (and at least it will make such sites easier to find and examine in the future, as we can grep for strbuf_complete). Signed-off-by: Jeff King <peff@peff.net> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2015-10-05remove_leading_path: use a strbuf for internal storageLibravatar Jeff King1-4/+6
This function strcpy's directly into a PATH_MAX-sized buffer. There's only one caller, which feeds the git_dir into it, so it's not easy to trigger in practice (even if you fed a large $GIT_DIR through the environment or .git file, it would have to actually exist and be accessible on the filesystem to get to this point). We can fix it by moving to a strbuf. Signed-off-by: Jeff King <peff@peff.net> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2015-10-05enter_repo: convert fixed-size buffers to strbufsLibravatar Jeff King1-28/+29
We use two PATH_MAX-sized buffers to represent the repo path, and must make sure not to overflow them. We do take care to check the lengths, but the logic is rather hard to follow, as we use several magic numbers (e.g., "PATH_MAX - 10"). And in fact you _can_ overflow the buffer if you have a ".git" file with an extremely long path in it. By switching to strbufs, these problems all go away. We do, however, retain the check that the initial input we get is no larger than PATH_MAX. This function is an entry point for untrusted repo names from the network, and it's a good idea to keep a sanity check (both to avoid allocating arbitrary amounts of memory, and also as a layer of defense against any downstream users of the names). Signed-off-by: Jeff King <peff@peff.net> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2015-09-28enter_repo: allow .git files in strict modeLibravatar Nguyễn Thái Ngọc Duy1-2/+7
Strict mode is about not guessing where .git is. If the user points to a .git file, we know exactly where the target .git dir will be. This makes it possible to serve .git files as repository on the server side. This may be needed even in local clone case because transport.c code uses upload-pack for fetching remote refs. But right now the clone/transport code goes with non-strict. Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2015-09-28enter_repo: avoid duplicating logic, use is_git_directory() insteadLibravatar Nguyễn Thái Ngọc Duy1-2/+1
It matters for linked checkouts where 'refs' directory won't be available in $GIT_DIR. is_git_directory() knows about $GIT_COMMON_DIR and can handle this case. Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2015-09-25add git_path_buf helper functionLibravatar Jeff King1-0/+10
If you have a function that uses git_path a lot, but would prefer to avoid the static buffers, it's useful to keep a single scratch buffer locally and reuse it for each call. You used to be able to do this with git_snpath: char buf[PATH_MAX]; foo(git_snpath(buf, sizeof(buf), "foo")); bar(git_snpath(buf, sizeof(buf), "bar")); but since 1a83c24, git_snpath has been replaced with strbuf_git_path. This is good, because it removes the arbitrary PATH_MAX limit. But using strbuf_git_path is more awkward for two reasons: 1. It adds to the buffer, rather than replacing it. This is consistent with other strbuf functions, but makes reuse of a single buffer more tedious. 2. It doesn't return the buffer, so you can't format as part of a function's arguments. The new git_path_buf solves both of these, so you can use it like: struct strbuf buf = STRBUF_INIT; foo(git_path_buf(&buf, "foo")); bar(git_path_buf(&buf, "bar")); strbuf_release(&buf); Signed-off-by: Jeff King <peff@peff.net> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2015-09-14path: implement common_dir handling in git_pathdup_submodule()Libravatar Max Kirillov1-4/+18
When submodule is a linked worktree, "git diff --submodule" and other calls which directly access the submodule's object database do not correctly calculate its path. Fix it by changing the git_pathdup_submodule() behavior, to use either common or per-worktree directory. Do it similarly as for parent repository, but ignore the GIT_COMMON_DIR environment variable, because it would mean common directory for the parent repository and does not make sense for submodule. Also add test for functionality which uses this call. Signed-off-by: Max Kirillov <max@max630.net> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2015-09-07path.c: delete an extra spaceLibravatar Nguyễn Thái Ngọc Duy1-1/+1
Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2015-09-01refs: make refs/bisect/* per-worktreeLibravatar David Turner1-0/+2
We need the place we stick refs for bisects in progress to not be shared between worktrees. So we make the refs/bisect/ hierarchy per-worktree. The is_per_worktree_ref function and associated docs learn that refs/bisect/ is per-worktree, as does the git_path code in path.c The ref-packing functions learn that per-worktree refs should not be packed (since packed-refs is common rather than per-worktree). Since refs/bisect is per-worktree, logs/refs/bisect should be too. Signed-off-by: David Turner <dturner@twopensource.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2015-09-01path: optimize common dir checkingLibravatar David Turner1-14/+213
Instead of a linear search over common_list to check whether a path is common, use a trie. The trie search operates on path prefixes, and handles excludes. Signed-off-by: David Turner <dturner@twopensource.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2015-09-01refs: clean up common_listLibravatar David Turner1-21/+37
Instead of common_list having formatting like ! and /, use a struct to hold common_list data in a structured form. We don't use 'exclude' yet; instead, we keep the old codepath that handles info/sparse-checkout and logs/HEAD. Later, we will use exclude. [jc: with "make common_list[] static" clean-up from Ramsay squashed in] Signed-off-by: David Turner <dturner@twopensource.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2015-08-17prepare_packed_git(): refactor garbage reporting in pack directoryLibravatar Junio C Hamano1-1/+1
The hook to report "garbage" files in $GIT_OBJECT_DIRECTORY/pack/ could be generic but is too specific to count-object's needs. Move the part to produce human-readable messages to count-objects, and refine the interface to callback with the "bits" with values defined in the cache.h header file, so that other callers (e.g. prune) can later use the same mechanism to enumerate different kinds of garbage files and do something intelligent about them, other than reporting in textual messages. Signed-off-by: Junio C Hamano <gitster@pobox.com>
2015-08-10memoize common git-path "constant" filesLibravatar Jeff King1-0/+10
One of the most common uses of git_path() is to pass a constant, like git_path("MERGE_MSG"). This has two drawbacks: 1. The return value is a static buffer, and the lifetime is dependent on other calls to git_path, etc. 2. There's no compile-time checking of the pathname. This is OK for a one-off (after all, we have to spell it correctly at least once), but many of these constant strings appear throughout the code. This patch introduces a series of functions to "memoize" these strings, which are essentially globals for the lifetime of the program. We compute the value once, take ownership of the buffer, and return the cached value for subsequent calls. cache.h provides a helper macro for defining these functions as one-liners, and defines a few common ones for global use. Using a macro is a little bit gross, but it does nicely document the purpose of the functions. If we need to touch them all later (e.g., because we learned how to change the git_dir variable at runtime, and need to invalidate all of the stored values), it will be much easier to have the complete list. Note that the shared-global functions have separate, manual declarations. We could do something clever with the macros (e.g., expand it to a declaration in some places, and a declaration _and_ a definition in path.c). But there aren't that many, and it's probably better to stay away from too-magical macros. Likewise, if we abandon the C preprocessor in favor of generating these with a script, we could get much fancier. E.g., normalizing "FOO/BAR-BAZ" into "git_path_foo_bar_baz". But the small amount of saved typing is probably not worth the resulting confusion to readers who want to grep for the function's definition. Signed-off-by: Jeff King <peff@peff.net> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2015-08-10path.c: drop git_path_submoduleLibravatar Jeff King1-10/+0
There are no callers of the slightly-dangerous static-buffer git_path_submodule left. Let's drop it. Signed-off-by: Jeff King <peff@peff.net> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2015-08-10cache.h: complete set of git_path_submodule helpersLibravatar Jeff King1-5/+30
The git_path function has "git_pathdup" and "strbuf_git_path" variants, but git_submodule_path only comes in the dangerous, static-buffer variant. That makes refactoring callers to use the safer functions hard (since they don't exist). Since we're already using a strbuf behind the scenes, it's easy to expose all three of these interfaces with thin wrappers. Signed-off-by: Jeff King <peff@peff.net> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2015-05-11Merge branch 'pt/xdg-config-path'Libravatar Junio C Hamano1-28/+15
Code clean-up for xdg configuration path support. * pt/xdg-config-path: path.c: remove home_config_paths() git-config: replace use of home_config_paths() git-commit: replace use of home_config_paths() credential-store.c: replace home_config_paths() with xdg_config_home() dir.c: replace home_config_paths() with xdg_config_home() attr.c: replace home_config_paths() with xdg_config_home() path.c: implement xdg_config_home()
2015-05-11Merge branch 'nd/multiple-work-trees'Libravatar Junio C Hamano1-77/+157
A replacement for contrib/workdir/git-new-workdir that does not rely on symbolic links and make sharing of objects and refs safer by making the borrowee and borrowers aware of each other. * nd/multiple-work-trees: (41 commits) prune --worktrees: fix expire vs worktree existence condition t1501: fix test with split index t2026: fix broken &&-chain t2026 needs procondition SANITY git-checkout.txt: a note about multiple checkout support for submodules checkout: add --ignore-other-wortrees checkout: pass whole struct to parse_branchname_arg instead of individual flags git-common-dir: make "modules/" per-working-directory directory checkout: do not fail if target is an empty directory t2025: add a test to make sure grafts is working from a linked checkout checkout: don't require a work tree when checking out into a new one git_path(): keep "info/sparse-checkout" per work-tree count-objects: report unused files in $GIT_DIR/worktrees/... gc: support prune --worktrees gc: factor out gc.pruneexpire parsing code gc: style change -- no SP before closing parenthesis checkout: clean up half-prepared directories in --to mode checkout: reject if the branch is already checked out elsewhere prune: strategies for linked checkouts checkout: support checking out into a new working directory ...
2015-05-06path.c: remove home_config_paths()Libravatar Paul Tan1-28/+0
home_config_paths() combines distinct functionality already implemented by expand_user_path() and xdg_config_home(), and it also hard-codes the path ~/.gitconfig, which makes it unsuitable to use for other home config file paths. Since its use will just add unnecessary complexity to the code, remove it. Signed-off-by: Paul Tan <pyokagan@gmail.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2015-05-06path.c: implement xdg_config_home()Libravatar Paul Tan1-0/+15
The XDG base dir spec[1] specifies that configuration files be stored in a subdirectory in $XDG_CONFIG_HOME. To construct such a configuration file path, home_config_paths() can be used. However, home_config_paths() combines distinct functionality: 1. Retrieve the home git config file path ~/.gitconfig 2. Construct the XDG config path of the file specified by `file`. This function was introduced in commit 21cf3227 ("read (but not write) from $XDG_CONFIG_HOME/git/config file"). While the intention of the function was to allow the home directory configuration file path and the xdg directory configuration file path to be retrieved with one function call, the hard-coding of the path ~/.gitconfig prevents it from being used for other configuration files. Furthermore, retrieving a file path relative to the user's home directory can be done with expand_user_path(). Hence, it can be seen that home_config_paths() introduces unnecessary complexity, especially if a user just wants to retrieve the xdg config file path. As such, implement a simpler function xdg_config_home() for constructing the XDG base dir spec configuration file path. This function, together with expand_user_path(), can replace all uses of home_config_paths(). [1] http://standards.freedesktop.org/basedir-spec/basedir-spec-0.7.html Helped-by: Eric Sunshine <sunshine@sunshineco.com> Signed-off-by: Paul Tan <pyokagan@gmail.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2015-04-14Merge branch 'pt/enter-repo-comment-fix'Libravatar Junio C Hamano1-8/+3
* pt/enter-repo-comment-fix: enter_repo(): fix docs to match code
2015-03-31enter_repo(): fix docs to match codeLibravatar Paul Tan1-8/+3
In b3256eb (standardize and improve lookup rules for external local repos), enter_repo() was modified to use a different precedence ordering of suffixes for DWIM of the repository path, and to ensure that the repository path is actually valid instead of just testing for existence. However, the documentation was not modified to reflect these changes. Fix the documentation to match the code. Documentation contributed by Jeff King. Signed-off-by: Jeff King <peff@peff.net> Signed-off-by: Paul Tan <pyokagan@gmail.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2014-12-17Sync with v2.1.4Libravatar Junio C Hamano1-0/+33
* maint-2.1: Git 2.1.4 Git 2.0.5 Git 1.9.5 Git 1.8.5.6 fsck: complain about NTFS ".git" aliases in trees read-cache: optionally disallow NTFS .git variants path: add is_ntfs_dotgit() helper fsck: complain about HFS+ ".git" aliases in trees read-cache: optionally disallow HFS+ .git variants utf8: add is_hfs_dotgit() helper fsck: notice .git case-insensitively t1450: refactor ".", "..", and ".git" fsck tests verify_dotfile(): reject .git case-insensitively read-tree: add tests for confusing paths like ".." and ".git" unpack-trees: propagate errors adding entries to the index
2014-12-17Sync with v2.0.5Libravatar Junio C Hamano1-0/+33
* maint-2.0: Git 2.0.5 Git 1.9.5 Git 1.8.5.6 fsck: complain about NTFS ".git" aliases in trees read-cache: optionally disallow NTFS .git variants path: add is_ntfs_dotgit() helper fsck: complain about HFS+ ".git" aliases in trees read-cache: optionally disallow HFS+ .git variants utf8: add is_hfs_dotgit() helper fsck: notice .git case-insensitively t1450: refactor ".", "..", and ".git" fsck tests verify_dotfile(): reject .git case-insensitively read-tree: add tests for confusing paths like ".." and ".git" unpack-trees: propagate errors adding entries to the index
2014-12-17Sync with v1.9.5Libravatar Junio C Hamano1-0/+33
* maint-1.9: Git 1.9.5 Git 1.8.5.6 fsck: complain about NTFS ".git" aliases in trees read-cache: optionally disallow NTFS .git variants path: add is_ntfs_dotgit() helper fsck: complain about HFS+ ".git" aliases in trees read-cache: optionally disallow HFS+ .git variants utf8: add is_hfs_dotgit() helper fsck: notice .git case-insensitively t1450: refactor ".", "..", and ".git" fsck tests verify_dotfile(): reject .git case-insensitively read-tree: add tests for confusing paths like ".." and ".git" unpack-trees: propagate errors adding entries to the index
2014-12-17Sync with v1.8.5.6Libravatar Junio C Hamano1-0/+33
* maint-1.8.5: Git 1.8.5.6 fsck: complain about NTFS ".git" aliases in trees read-cache: optionally disallow NTFS .git variants path: add is_ntfs_dotgit() helper fsck: complain about HFS+ ".git" aliases in trees read-cache: optionally disallow HFS+ .git variants utf8: add is_hfs_dotgit() helper fsck: notice .git case-insensitively t1450: refactor ".", "..", and ".git" fsck tests verify_dotfile(): reject .git case-insensitively read-tree: add tests for confusing paths like ".." and ".git" unpack-trees: propagate errors adding entries to the index
2014-12-17path: add is_ntfs_dotgit() helperLibravatar Johannes Schindelin1-0/+33
We do not allow paths with a ".git" component to be added to the index, as that would mean repository contents could overwrite our repository files. However, asking "is this path the same as .git" is not as simple as strcmp() on some filesystems. On NTFS (and FAT32), there exist so-called "short names" for backwards-compatibility: 8.3 compliant names that refer to the same files as their long names. As ".git" is not an 8.3 compliant name, a short name is generated automatically, typically "git~1". Depending on the Windows version, any combination of trailing spaces and periods are ignored, too, so that both "git~1." and ".git." still refer to the Git directory. The reason is that 8.3 stores file names shorter than 8 characters with trailing spaces. So literally, it does not matter for the short name whether it is padded with spaces or whether it is shorter than 8 characters, it is considered to be the exact same. The period is the separator between file name and file extension, and again, an empty extension consists just of spaces in 8.3 format. So technically, we would need only take care of the equivalent of this regex: (\.git {0,4}|git~1 {0,3})\. {0,3} However, there are indications that at least some Windows versions might be more lenient and accept arbitrary combinations of trailing spaces and periods and strip them out. So we're playing it real safe here. Besides, there can be little doubt about the intention behind using file names matching even the more lenient pattern specified above, therefore we should be fine with disallowing such patterns. Extra care is taken to catch names such as '.\\.git\\booh' because the backslash is marked as a directory separator only on Windows, and we want to use this new helper function also in fsck on other platforms. A big thank you goes to Ed Thomson and an unnamed Microsoft engineer for the detailed analysis performed to come up with the corresponding fixes for libgit2. This commit adds a function to detect whether a given file name can refer to the Git directory by mistake. Signed-off-by: Johannes Schindelin <johannes.schindelin@gmx.de> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2014-12-01git-common-dir: make "modules/" per-working-directory directoryLibravatar Max Kirillov1-1/+1
Each working directory of main repository has its own working directory of submodule, and in most cases they should be checked out to different revisions. So they should be separated. It looks logical to make submodule instances in different working directories to reuse the submodule directory in the common dir of the main repository, and probably this is how "checkout --to" should initialize them called on the main repository, but they also should work fine being completely separated clones. Testfile t7410-submodule-checkout-to.sh demostrates the behavior. Signed-off-by: Max Kirillov <max@max630.net> Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2014-12-01git_path(): keep "info/sparse-checkout" per work-treeLibravatar Nguyễn Thái Ngọc Duy1-1/+2
Currently git_path("info/sparse-checkout") resolves to $GIT_COMMON_DIR/info/sparse-checkout in multiple worktree mode. It makes more sense for the sparse checkout patterns to be per worktree, so you can have multiple checkouts with different parts of the tree. With this, "git checkout --to <new>" on a sparse checkout will create <new> as a full checkout. Which is expected, it's how a new checkout is made. The user can reshape the worktree afterwards. Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2014-12-01count-objects: report unused files in $GIT_DIR/worktrees/...Libravatar Nguyễn Thái Ngọc Duy1-2/+27
In linked checkouts, borrowed parts like config is taken from $GIT_COMMON_DIR. $GIT_DIR/config is never used. Report them as garbage. Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2014-12-01checkout: support checking out into a new working directoryLibravatar Nguyễn Thái Ngọc Duy1-1/+1
"git checkout --to" sets up a new working directory with a .git file pointing to $GIT_DIR/worktrees/<id>. It then executes "git checkout" again on the new worktree with the same arguments except "--to" is taken out. The second checkout execution, which is not contaminated with any info from the current repository, will actually check out and everything that normal "git checkout" does. Helped-by: Marc Branchaud <marcnarc@xiplink.com> Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2014-12-01$GIT_COMMON_DIR: a new environment variableLibravatar Nguyễn Thái Ngọc Duy1-0/+34
This variable is intended to support multiple working directories attached to a repository. Such a repository may have a main working directory, created by either "git init" or "git clone" and one or more linked working directories. These working directories and the main repository share the same repository directory. In linked working directories, $GIT_COMMON_DIR must be defined to point to the real repository directory and $GIT_DIR points to an unused subdirectory inside $GIT_COMMON_DIR. File locations inside the repository are reorganized from the linked worktree view point: - worktree-specific such as HEAD, logs/HEAD, index, other top-level refs and unrecognized files are from $GIT_DIR. - the rest like objects, refs, info, hooks, packed-refs, shallow... are from $GIT_COMMON_DIR (except info/sparse-checkout, but that's a separate patch) Scripts are supposed to retrieve paths in $GIT_DIR with "git rev-parse --git-path", which will take care of "$GIT_DIR vs $GIT_COMMON_DIR" business. The redirection is done by git_path(), git_pathdup() and strbuf_git_path(). The selected list of paths goes to $GIT_COMMON_DIR, not the other way around in case a developer adds a new worktree-specific file and it's accidentally promoted to be shared across repositories (this includes unknown files added by third party commands) The list of known files that belong to $GIT_DIR are: ADD_EDIT.patch BISECT_ANCESTORS_OK BISECT_EXPECTED_REV BISECT_LOG BISECT_NAMES CHERRY_PICK_HEAD COMMIT_MSG FETCH_HEAD HEAD MERGE_HEAD MERGE_MODE MERGE_RR NOTES_EDITMSG NOTES_MERGE_WORKTREE ORIG_HEAD REVERT_HEAD SQUASH_MSG TAG_EDITMSG fast_import_crash_* logs/HEAD next-index-* rebase-apply rebase-merge rsync-refs-* sequencer/* shallow_* Path mapping is NOT done for git_path_submodule(). Multi-checkouts are not supported as submodules. Helped-by: Jens Lehmann <Jens.Lehmann@web.de> Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2014-12-01git_path(): be aware of file relocation in $GIT_DIRLibravatar Nguyễn Thái Ngọc Duy1-2/+47
We allow the user to relocate certain paths out of $GIT_DIR via environment variables, e.g. GIT_OBJECT_DIRECTORY, GIT_INDEX_FILE and GIT_GRAFT_FILE. Callers are not supposed to use git_path() or git_pathdup() to get those paths. Instead they must use get_object_directory(), get_index_file() and get_graft_file() respectively. This is inconvenient and could be missed in review (for example, there's git_path("objects/info/alternates") somewhere in sha1_file.c). This patch makes git_path() and git_pathdup() understand those environment variables. So if you set GIT_OBJECT_DIRECTORY to /foo/bar, git_path("objects/abc") should return /foo/bar/abc. The same is done for the two remaining env variables. "git rev-parse --git-path" is the wrapper for script use. This patch kinda reverts a0279e1 (setup_git_env: use git_pathdup instead of xmalloc + sprintf - 2014-06-19) because using git_pathdup here would result in infinite recursion: setup_git_env() -> git_pathdup("objects") -> .. -> adjust_git_path() -> get_object_directory() -> oops, git_object_directory is NOT set yet -> setup_git_env() I wanted to make git_pathdup_literal() that skips adjust_git_path(). But that won't work because later on when $GIT_COMMON_DIR is introduced, git_pathdup_literal("objects") needs adjust_git_path() to replace $GIT_DIR with $GIT_COMMON_DIR. Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2014-12-01path.c: group git_path(), git_pathdup() and strbuf_git_path() togetherLibravatar Nguyễn Thái Ngọc Duy1-10/+10
Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2014-12-01path.c: rename vsnpath() to do_git_path()Libravatar Nguyễn Thái Ngọc Duy1-4/+4
The name vsnpath() gives an impression that this is general path handling function. It's not. This is the underlying implementation of git_path(), git_pathdup() and strbuf_git_path() which will prefix $GIT_DIR in the result string. Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2014-12-01git_snpath(): retire and replace with strbuf_git_path()Libravatar Nguyễn Thái Ngọc Duy1-9/+2
In the previous patch, git_snpath() is modified to allocate a new strbuf buffer because vsnpath() needs that. But that makes it awkward because git_snpath() receives a pre-allocated buffer from outside and has to copy data back. Rename it to strbuf_git_path() and make it receive strbuf directly. Using git_path() in update_refs_for_switch() which used to call git_snpath() is safe because that function and all of its callers do not keep any pointer to the round-robin buffer pool allocated by get_pathname(). Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2014-12-01path.c: make get_pathname() call sites return const char *Libravatar Nguyễn Thái Ngọc Duy1-3/+3
Before the previous commit, get_pathname returns an array of PATH_MAX length. Even if git_path() and similar functions does not use the whole array, git_path() caller can, in theory. After the commit, get_pathname() may return a buffer that has just enough room for the returned string and git_path() caller should never write beyond that. Make git_path(), mkpath() and git_path_submodule() return a const buffer to make sure callers do not write in it at all. This could have been part of the previous commit, but the "const" conversion is too much distraction from the core changes in path.c. Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
2014-12-01path.c: make get_pathname() return strbuf instead of static bufferLibravatar Nguyễn Thái Ngọc Duy1-69/+51
We've been avoiding PATH_MAX whenever possible. This patch makes get_pathname() return a strbuf and updates the callers to take advantage of this. The code is simplified as we no longer need to worry about buffer overflow. vsnpath() behavior is changed slightly: previously it always clears the buffer before writing, now it just appends. Fortunately this is a static function and all of its callers prepare the buffer properly: git_path() gets the buffer from get_pathname() which resets the buffer, the remaining call sites start with STRBUF_INIT'd buffer. Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>