diff options
author | Junio C Hamano <gitster@pobox.com> | 2013-12-17 23:47:08 +0400 |
---|---|---|
committer | Junio C Hamano <gitster@pobox.com> | 2013-12-17 23:47:08 +0400 |
commit | fb230b35236c0d510bc0fdbabaafee027550c7eb (patch) | |
tree | 6e86dd28412c9568893504674a77a37567f52353 /builtin | |
parent | 053fbe672cb0e31b832e1da1e18556f7dbcdba36 (diff) | |
parent | c57f6281ff847db7094d708f5c5b939d378f7120 (diff) |
Merge branch 'mm/mv-file-to-no-such-dir-with-slash'
* mm/mv-file-to-no-such-dir-with-slash:
mv: let 'git mv file no-such-dir/' error out
Diffstat (limited to 'builtin')
-rw-r--r-- | builtin/mv.c | 23 |
1 files changed, 16 insertions, 7 deletions
diff --git a/builtin/mv.c b/builtin/mv.c index 2e0e61b651..08fbc033e4 100644 --- a/builtin/mv.c +++ b/builtin/mv.c @@ -16,9 +16,12 @@ static const char * const builtin_mv_usage[] = { NULL }; +#define DUP_BASENAME 1 +#define KEEP_TRAILING_SLASH 2 + static const char **internal_copy_pathspec(const char *prefix, const char **pathspec, - int count, int base_name) + int count, unsigned flags) { int i; const char **result = xmalloc((count + 1) * sizeof(const char *)); @@ -27,11 +30,12 @@ static const char **internal_copy_pathspec(const char *prefix, for (i = 0; i < count; i++) { int length = strlen(result[i]); int to_copy = length; - while (to_copy > 0 && is_dir_sep(result[i][to_copy - 1])) + while (!(flags & KEEP_TRAILING_SLASH) && + to_copy > 0 && is_dir_sep(result[i][to_copy - 1])) to_copy--; - if (to_copy != length || base_name) { + if (to_copy != length || flags & DUP_BASENAME) { char *it = xmemdupz(result[i], to_copy); - if (base_name) { + if (flags & DUP_BASENAME) { result[i] = xstrdup(basename(it)); free(it); } else @@ -87,16 +91,21 @@ int cmd_mv(int argc, const char **argv, const char *prefix) source = internal_copy_pathspec(prefix, argv, argc, 0); modes = xcalloc(argc, sizeof(enum update_mode)); - dest_path = internal_copy_pathspec(prefix, argv + argc, 1, 0); + /* + * Keep trailing slash, needed to let + * "git mv file no-such-dir/" error out. + */ + dest_path = internal_copy_pathspec(prefix, argv + argc, 1, + KEEP_TRAILING_SLASH); submodule_gitfile = xcalloc(argc, sizeof(char *)); if (dest_path[0][0] == '\0') /* special case: "." was normalized to "" */ - destination = internal_copy_pathspec(dest_path[0], argv, argc, 1); + destination = internal_copy_pathspec(dest_path[0], argv, argc, DUP_BASENAME); else if (!lstat(dest_path[0], &st) && S_ISDIR(st.st_mode)) { dest_path[0] = add_slash(dest_path[0]); - destination = internal_copy_pathspec(dest_path[0], argv, argc, 1); + destination = internal_copy_pathspec(dest_path[0], argv, argc, DUP_BASENAME); } else { if (argc != 1) die("destination '%s' is not a directory", dest_path[0]); |