merge-recursive: New data structures for deferring of D/F conflicts

Since we need to resolve paths (including renames) in-core first and defer
checking of D/F conflicts (namely waiting to see if directories are still
in the way after all paths are resolved) before updating files involved in
D/F conflicts, we will need to first process_renames, then record some
information about the rename needed at D/F resolution time, and then make
use of that information when resolving D/F conflicts at the end.

This commit adds some relevant data structures for storing the necessary
information.

Signed-off-by: Elijah Newren <newren@gmail.com>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
This commit is contained in:
Elijah Newren 2010-09-20 02:28:53 -06:00 committed by Junio C Hamano
parent 0c4918d1c1
commit 25c3936349

View File

@ -63,6 +63,22 @@ static int sha_eq(const unsigned char *a, const unsigned char *b)
return a && b && hashcmp(a, b) == 0;
}
enum rename_type {
RENAME_NORMAL = 0,
RENAME_DELETE,
RENAME_ONE_FILE_TO_TWO
};
struct rename_df_conflict_info {
enum rename_type rename_type;
struct diff_filepair *pair1;
struct diff_filepair *pair2;
const char *branch1;
const char *branch2;
struct stage_data *dst_entry1;
struct stage_data *dst_entry2;
};
/*
* Since we want to write the index eventually, we cannot reuse the index
* for these (temporary) data.
@ -74,9 +90,37 @@ struct stage_data
unsigned mode;
unsigned char sha[20];
} stages[4];
struct rename_df_conflict_info *rename_df_conflict_info;
unsigned processed:1;
};
static inline void setup_rename_df_conflict_info(enum rename_type rename_type,
struct diff_filepair *pair1,
struct diff_filepair *pair2,
const char *branch1,
const char *branch2,
struct stage_data *dst_entry1,
struct stage_data *dst_entry2)
{
struct rename_df_conflict_info *ci = xcalloc(1, sizeof(struct rename_df_conflict_info));
ci->rename_type = rename_type;
ci->pair1 = pair1;
ci->branch1 = branch1;
ci->branch2 = branch2;
ci->dst_entry1 = dst_entry1;
dst_entry1->rename_df_conflict_info = ci;
dst_entry1->processed = 0;
assert(!pair2 == !dst_entry2);
if (dst_entry2) {
ci->dst_entry2 = dst_entry2;
ci->pair2 = pair2;
dst_entry2->rename_df_conflict_info = ci;
dst_entry2->processed = 0;
}
}
static int show(struct merge_options *o, int v)
{
return (!o->call_depth && o->verbosity >= v) || o->verbosity >= 5;