diff options
-rw-r--r-- | src/win32/findfile.c | 78 | ||||
-rw-r--r-- | src/win32/findfile.h | 1 | ||||
-rw-r--r-- | tests/win32/systempath.c | 91 |
3 files changed, 144 insertions, 26 deletions
diff --git a/src/win32/findfile.c b/src/win32/findfile.c index 8975894fa..1e4d3d082 100644 --- a/src/win32/findfile.c +++ b/src/win32/findfile.c @@ -112,12 +112,26 @@ static int win32_find_git_for_windows_architecture_root(_findfile_path *root_pat static int win32_find_git_in_path(git_str *buf, const wchar_t *gitexe, const wchar_t *subdir) { - wchar_t *env = _wgetenv(L"PATH"), lastch; + wchar_t *path, *env, lastch; _findfile_path root; size_t gitexe_len = wcslen(gitexe); + DWORD len; + bool found = false; - if (!env) - return -1; + len = GetEnvironmentVariableW(L"PATH", NULL, 0); + + if (len < 0) + return -1; + + path = git__malloc(len * sizeof(wchar_t)); + GIT_ERROR_CHECK_ALLOC(path); + + len = GetEnvironmentVariableW(L"PATH", path, len); + + if (len < 0) + return -1; + + env = path; while ((env = win32_walkpath(env, root.path, MAX_PATH-1)) && *root.path) { root.len = (DWORD)wcslen(root.path); @@ -148,11 +162,13 @@ static int win32_find_git_in_path(git_str *buf, const wchar_t *gitexe, const wch } win32_path_to_8(buf, root.path); - return 0; + found = true; + break; } } - return GIT_ENOTFOUND; + git__free(path); + return found ? 0 : GIT_ENOTFOUND; } static int win32_find_git_in_registry( @@ -214,37 +230,47 @@ static int win32_find_existing_dirs( return (git_str_oom(out) ? -1 : 0); } -int git_win32__find_system_dirs(git_str *out, const wchar_t *subdir) +int git_win32__find_system_dir_in_path(git_str *out, const wchar_t *subdir) { - git_str buf = GIT_STR_INIT; + /* directories where git.exe & git.cmd are found */ + if (win32_find_git_in_path(out, L"git.exe", subdir) == 0) + return 0; - /* directories where git.exe & git.cmd are found */ - if (!win32_find_git_in_path(&buf, L"git.exe", subdir) && buf.size) - git_str_set(out, buf.ptr, buf.size); - else - git_str_clear(out); + return win32_find_git_in_path(out, L"git.cmd", subdir); +} - if (!win32_find_git_in_path(&buf, L"git.cmd", subdir) && buf.size) - git_str_join(out, GIT_PATH_LIST_SEPARATOR, out->ptr, buf.ptr); +static int git_win32__find_system_dir_in_registry(git_str *out, const wchar_t *subdir) +{ + git_str buf = GIT_STR_INIT; - /* directories where git is installed according to registry */ - if (!win32_find_git_in_registry( - &buf, HKEY_CURRENT_USER, REG_MSYSGIT_INSTALL_LOCAL, subdir) && buf.size) - git_str_join(out, GIT_PATH_LIST_SEPARATOR, out->ptr, buf.ptr); + /* directories where git is installed according to registry */ + if (!win32_find_git_in_registry( + &buf, HKEY_CURRENT_USER, REG_MSYSGIT_INSTALL_LOCAL, subdir) && buf.size) + git_str_join(out, GIT_PATH_LIST_SEPARATOR, out->ptr, buf.ptr); #ifdef GIT_ARCH_64 - if (!win32_find_git_in_registry( - &buf, HKEY_LOCAL_MACHINE, REG_MSYSGIT_INSTALL_LOCAL, subdir) && buf.size) - git_str_join(out, GIT_PATH_LIST_SEPARATOR, out->ptr, buf.ptr); + if (!win32_find_git_in_registry( + &buf, HKEY_LOCAL_MACHINE, REG_MSYSGIT_INSTALL_LOCAL, subdir) && buf.size) + git_str_join(out, GIT_PATH_LIST_SEPARATOR, out->ptr, buf.ptr); #endif - if (!win32_find_git_in_registry( - &buf, HKEY_LOCAL_MACHINE, REG_MSYSGIT_INSTALL, subdir) && buf.size) - git_str_join(out, GIT_PATH_LIST_SEPARATOR, out->ptr, buf.ptr); + if (!win32_find_git_in_registry( + &buf, HKEY_LOCAL_MACHINE, REG_MSYSGIT_INSTALL, subdir) && buf.size) + git_str_join(out, GIT_PATH_LIST_SEPARATOR, out->ptr, buf.ptr); - git_str_dispose(&buf); + git_str_dispose(&buf); - return (git_str_oom(out) ? -1 : 0); + return (git_str_oom(out) ? -1 : 0); +} + +int git_win32__find_system_dirs(git_str *out, const wchar_t *subdir) +{ + int error; + + if ((error = git_win32__find_system_dir_in_path(out, subdir)) == 0) + error = git_win32__find_system_dir_in_registry(out, subdir); + + return error; } int git_win32__find_global_dirs(git_str *out) diff --git a/src/win32/findfile.h b/src/win32/findfile.h index e11ccebc5..7f7691ce1 100644 --- a/src/win32/findfile.h +++ b/src/win32/findfile.h @@ -10,6 +10,7 @@ #include "common.h" +extern int git_win32__find_system_dir_in_path(git_str* out, const wchar_t* subdir); extern int git_win32__find_system_dirs(git_str *out, const wchar_t *subpath); extern int git_win32__find_global_dirs(git_str *out); extern int git_win32__find_xdg_dirs(git_str *out); diff --git a/tests/win32/systempath.c b/tests/win32/systempath.c new file mode 100644 index 000000000..0b77f7703 --- /dev/null +++ b/tests/win32/systempath.c @@ -0,0 +1,91 @@ +#include "clar_libgit2.h" +#include "futils.h" +#include "sysdir.h" +#include "win32/findfile.h" + +static char *path_save; +static git_str gfw_root = GIT_STR_INIT; + +void test_win32_systempath__initialize(void) +{ + path_save = cl_getenv("PATH"); + + cl_git_pass(git_str_puts(&gfw_root, clar_sandbox_path())); + cl_git_pass(git_str_puts(&gfw_root, "/fake_gfw_install")); +} + +void test_win32_systempath__cleanup(void) +{ + cl_fixture_cleanup("fake_gfw_install"); + git_str_dispose(&gfw_root); + + cl_setenv("PATH", path_save); + git__free(path_save); + path_save = NULL; + + git_sysdir_reset(); +} + +static void fix_path(git_str *s) +{ + char *c; + + for (c = s->ptr; *c; c++) { + if (*c == '/') + *c = '\\'; + } +} + +void test_win32_systempath__etc_gitconfig(void) +{ + git_str bin_path = GIT_STR_INIT, exe_path = GIT_STR_INIT, + etc_path = GIT_STR_INIT, config_path = GIT_STR_INIT, + path_env = GIT_STR_INIT, out = GIT_STR_INIT; + git_config *cfg; + int value; + + cl_git_pass(git_str_puts(&bin_path, gfw_root.ptr)); + cl_git_pass(git_str_puts(&bin_path, "/cmd")); + cl_git_pass(git_futils_mkdir_r(bin_path.ptr, 0755)); + + cl_git_pass(git_str_puts(&exe_path, bin_path.ptr)); + cl_git_pass(git_str_puts(&exe_path, "/git.cmd")); + cl_git_mkfile(exe_path.ptr, "This is a fake executable."); + + cl_git_pass(git_str_puts(&etc_path, gfw_root.ptr)); + cl_git_pass(git_str_puts(&etc_path, "/etc")); + cl_git_pass(git_futils_mkdir_r(etc_path.ptr, 0755)); + + git_str_clear(&etc_path); + + cl_git_pass(git_str_puts(&etc_path, gfw_root.ptr)); + cl_git_pass(git_str_puts(&etc_path, "/etc")); + cl_git_pass(git_futils_mkdir_r(etc_path.ptr, 0755)); + + cl_git_pass(git_str_puts(&config_path, etc_path.ptr)); + cl_git_pass(git_str_puts(&config_path, "/gitconfig")); + cl_git_mkfile(config_path.ptr, "[gfw]\n\ttest = 1337\n"); + + fix_path(&bin_path); + + cl_git_pass(git_str_puts(&path_env, "C:\\GitTempTest\\Foo;\"c:\\program files\\doesnotexisttesttemp\";")); + cl_git_pass(git_str_puts(&path_env, bin_path.ptr)); + cl_git_pass(git_str_puts(&path_env, ";C:\\fakefakedoesnotexist")); + cl_setenv("PATH", path_env.ptr); + + cl_git_pass(git_win32__find_system_dir_in_path(&out, L"etc")); + cl_assert_equal_s(out.ptr, etc_path.ptr); + + git_sysdir_reset(); + + cl_git_pass(git_config_open_default(&cfg)); + cl_git_pass(git_config_get_int32(&value, cfg, "gfw.test")); + cl_assert_equal_i(1337, value); + + git_str_dispose(&exe_path); + git_str_dispose(&etc_path); + git_str_dispose(&config_path); + git_str_dispose(&path_env); + git_str_dispose(&out); + git_config_free(cfg); +} |