summaryrefslogtreecommitdiff
path: root/merge-ort.c
diff options
context:
space:
mode:
authorElijah Newren <newren@gmail.com>2021-01-01 02:34:42 (GMT)
committerJunio C Hamano <gitster@pobox.com>2021-01-04 18:40:45 (GMT)
commit991bbdcab94d93c2a325c4ce74cff139f0f49d97 (patch)
treeac589c0b18e48c4b8453f5cb37fad9c668100949 /merge-ort.c
parent5a1a1e8ea9fdd4a575c711b91f176838ea502e44 (diff)
downloadgit-991bbdcab94d93c2a325c4ce74cff139f0f49d97.zip
git-991bbdcab94d93c2a325c4ce74cff139f0f49d97.tar.gz
git-991bbdcab94d93c2a325c4ce74cff139f0f49d97.tar.bz2
merge-ort: handle book-keeping around two- and three-way content merge
In addition to the content merge (which will go in a subsequent commit), we need to worry about conflict messages, placing results in higher order stages in case of a df_conflict, and making sure the results are placed in ci->merged.result so that they will show up in the working tree. Take care of all that external book-keeping, moving the simplistic just-take-HEAD code into the barebones handle_content_merge() function for now. Subsequent commits will flesh out handle_content_merge(). Signed-off-by: Elijah Newren <newren@gmail.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
Diffstat (limited to 'merge-ort.c')
-rw-r--r--merge-ort.c52
1 files changed, 41 insertions, 11 deletions
diff --git a/merge-ort.c b/merge-ort.c
index 1adc27a..47e230f 100644
--- a/merge-ort.c
+++ b/merge-ort.c
@@ -640,7 +640,15 @@ static int handle_content_merge(struct merge_options *opt,
const int extra_marker_size,
struct version_info *result)
{
- die("Not yet implemented");
+ int clean = 0;
+ /*
+ * TODO: Needs a two-way or three-way content merge, but we're
+ * just being lazy and copying the version from HEAD and
+ * leaving it as conflicted.
+ */
+ result->mode = a->mode;
+ oidcpy(&result->oid, &a->oid);
+ return clean;
}
/*** Function Grouping: functions related to detect_and_process_renames(), ***
@@ -1138,16 +1146,38 @@ static void process_entry(struct merge_options *opt,
*/
die("Not yet implemented.");
} else if (ci->filemask >= 6) {
- /*
- * TODO: Needs a two-way or three-way content merge, but we're
- * just being lazy and copying the version from HEAD and
- * leaving it as conflicted.
- */
- ci->merged.clean = 0;
- ci->merged.result.mode = ci->stages[1].mode;
- oidcpy(&ci->merged.result.oid, &ci->stages[1].oid);
- /* When we fix above, we'll call handle_content_merge() */
- (void)handle_content_merge;
+ /* Need a two-way or three-way content merge */
+ struct version_info merged_file;
+ unsigned clean_merge;
+ struct version_info *o = &ci->stages[0];
+ struct version_info *a = &ci->stages[1];
+ struct version_info *b = &ci->stages[2];
+
+ clean_merge = handle_content_merge(opt, path, o, a, b,
+ ci->pathnames,
+ opt->priv->call_depth * 2,
+ &merged_file);
+ ci->merged.clean = clean_merge &&
+ !ci->df_conflict && !ci->path_conflict;
+ ci->merged.result.mode = merged_file.mode;
+ ci->merged.is_null = (merged_file.mode == 0);
+ oidcpy(&ci->merged.result.oid, &merged_file.oid);
+ if (clean_merge && ci->df_conflict) {
+ assert(df_file_index == 1 || df_file_index == 2);
+ ci->filemask = 1 << df_file_index;
+ ci->stages[df_file_index].mode = merged_file.mode;
+ oidcpy(&ci->stages[df_file_index].oid, &merged_file.oid);
+ }
+ if (!clean_merge) {
+ const char *reason = _("content");
+ if (ci->filemask == 6)
+ reason = _("add/add");
+ if (S_ISGITLINK(merged_file.mode))
+ reason = _("submodule");
+ path_msg(opt, path, 0,
+ _("CONFLICT (%s): Merge conflict in %s"),
+ reason, path);
+ }
} else if (ci->filemask == 3 || ci->filemask == 5) {
/* Modify/delete */
const char *modify_branch, *delete_branch;