Commit 12f9ac17 by Edward Thomson

apply: validate unchanged mode when applying both

When applying to both the index and the working directory, ensure that
the working directory's mode matches the index's mode.  It's not
sufficient to look only at the hashed object id to determine that the
file is unchanged, git also takes the mode into account.
parent b73a42f6
......@@ -79,6 +79,8 @@ static int workdir_reader_read(
{
workdir_reader *reader = (workdir_reader *)_reader;
git_buf path = GIT_BUF_INIT;
struct stat st;
git_filemode_t filemode;
git_filter_list *filters = NULL;
const git_index_entry *idx_entry;
git_oid id;
......@@ -88,6 +90,16 @@ static int workdir_reader_read(
git_repository_workdir(reader->repo), filename)) < 0)
goto done;
if ((error = p_lstat(path.ptr, &st)) < 0) {
if (error == -1 && errno == ENOENT)
error = GIT_ENOTFOUND;
giterr_set(GITERR_OS, "could not stat '%s'", path.ptr);
goto done;
}
filemode = git_futils_canonical_mode(st.st_mode);
/*
* Patch application - for example - uses the filtered version of
* the working directory data to match git. So we will run the
......@@ -108,6 +120,7 @@ static int workdir_reader_read(
if (reader->index) {
if (!(idx_entry = git_index_get_bypath(reader->index, filename, 0)) ||
filemode != idx_entry->mode ||
!git_oid_equal(&id, &idx_entry->id)) {
error = GIT_READER_MISMATCH;
goto done;
......
......@@ -204,6 +204,23 @@ void test_apply_both__index_must_match_workdir(void)
git_diff_free(diff);
}
void test_apply_both__index_mode_must_match_workdir(void)
{
git_diff *diff;
if (!cl_is_chmod_supported())
clar__skip();
/* Set a file in the working directory executable. */
cl_must_pass(p_chmod("merge-recursive/asparagus.txt", 0755));
cl_git_pass(git_diff_from_buffer(&diff, DIFF_MODIFY_TWO_FILES,
strlen(DIFF_MODIFY_TWO_FILES)));
cl_git_fail_with(GIT_EAPPLYFAIL, git_apply(repo, diff, GIT_APPLY_LOCATION_BOTH, NULL));
git_diff_free(diff);
}
void test_apply_both__application_failure_leaves_workdir_unmodified(void)
{
git_diff *diff;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment