Skip to content

Commit f92d495

Browse files
authored
Merge pull request libgit2#5131 from pks-t/pks/fileops-mkdir-in-root
fileops: fix creation of directory in filesystem root
2 parents dacac9e + 5ae22a6 commit f92d495

File tree

2 files changed

+46
-3
lines changed

2 files changed

+46
-3
lines changed

src/fileops.c

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -495,7 +495,9 @@ int git_futils_mkdir(
495495
* equal to length of the root path). The path may be less than the
496496
* root path length on Windows, where `C:` == `C:/`.
497497
*/
498-
if ((len == 1 && parent_path.ptr[0] == '.') || len <= root_len) {
498+
if ((len == 1 && parent_path.ptr[0] == '.') ||
499+
(len == 1 && parent_path.ptr[0] == '/') ||
500+
len <= root_len) {
499501
relative = make_path.ptr;
500502
break;
501503
}

tests/repo/init.c

Lines changed: 43 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -878,14 +878,55 @@ void test_repo_init__at_filesystem_root(void)
878878
git_repository_free(repo);
879879
}
880880

881-
void test_repo_init__nonexistent_paths(void)
881+
void test_repo_init__nonexisting_directory(void)
882882
{
883+
git_repository_init_options opts = GIT_REPOSITORY_INIT_OPTIONS_INIT;
883884
git_repository *repo;
884885

886+
/*
887+
* If creating a repo with non-existing parent directories, then libgit2
888+
* will by default create the complete directory hierarchy if using
889+
* `git_repository_init`. Thus, let's use the extended version and not
890+
* set the `GIT_REPOSITORY_INIT_MKPATH` flag.
891+
*/
892+
cl_git_fail(git_repository_init_ext(&repo, "nonexisting/path", &opts));
893+
}
894+
895+
void test_repo_init__nonexisting_root(void)
896+
{
885897
#ifdef GIT_WIN32
898+
git_repository *repo;
899+
900+
/*
901+
* This really only depends on the nonexistence of the Q: drive. We
902+
* cannot implement the equivalent test on Unix systems, as there is
903+
* fundamentally no path that is disconnected from the root directory.
904+
*/
886905
cl_git_fail(git_repository_init(&repo, "Q:/non/existent/path", 0));
887906
cl_git_fail(git_repository_init(&repo, "Q:\\non\\existent\\path", 0));
888907
#else
889-
cl_git_fail(git_repository_init(&repo, "/non/existent/path", 0));
908+
clar__skip();
909+
#endif
910+
}
911+
912+
void test_repo_init__unwriteable_directory(void)
913+
{
914+
#ifndef GIT_WIN32
915+
git_repository *repo;
916+
917+
if (geteuid() == 0)
918+
clar__skip();
919+
920+
/*
921+
* Create a non-writeable directory so that we cannot create directories
922+
* inside of it. The root user has CAP_DAC_OVERRIDE, so he doesn't care
923+
* for the directory permissions and thus we need to skip the test if
924+
* run as root user.
925+
*/
926+
cl_must_pass(p_mkdir("unwriteable", 0444));
927+
cl_git_fail(git_repository_init(&repo, "unwriteable/repo", 0));
928+
cl_must_pass(p_rmdir("unwriteable"));
929+
#else
930+
clar__skip();
890931
#endif
891932
}

0 commit comments

Comments
 (0)