comparison mercurial/merge.py @ 34552:33c8a6837181

merge: check for path conflicts when updating (issue5628) When updating to a new revision, check for path conflicts caused by unknown files in the working directory, and handle these by backing up the file or directory and replacing it. Differential Revision: https://phab.mercurial-scm.org/D781
author Mark Thomas <mbthomas@fb.com>
date Mon, 02 Oct 2017 14:05:30 -0700
parents 1609a5afc4f5
children 0217d66846f7
comparison
equal deleted inserted replaced
34551:1609a5afc4f5 34552:33c8a6837181
674 Considers any actions that care about the presence of conflicting unknown 674 Considers any actions that care about the presence of conflicting unknown
675 files. For some actions, the result is to abort; for others, it is to 675 files. For some actions, the result is to abort; for others, it is to
676 choose a different action. 676 choose a different action.
677 """ 677 """
678 fileconflicts = set() 678 fileconflicts = set()
679 pathconflicts = set()
679 warnconflicts = set() 680 warnconflicts = set()
680 abortconflicts = set() 681 abortconflicts = set()
681 unknownconfig = _getcheckunknownconfig(repo, 'merge', 'checkunknown') 682 unknownconfig = _getcheckunknownconfig(repo, 'merge', 'checkunknown')
682 ignoredconfig = _getcheckunknownconfig(repo, 'merge', 'checkignored') 683 ignoredconfig = _getcheckunknownconfig(repo, 'merge', 'checkignored')
683 if not force: 684 if not force:
689 690
690 for f, (m, args, msg) in actions.iteritems(): 691 for f, (m, args, msg) in actions.iteritems():
691 if m in ('c', 'dc'): 692 if m in ('c', 'dc'):
692 if _checkunknownfile(repo, wctx, mctx, f): 693 if _checkunknownfile(repo, wctx, mctx, f):
693 fileconflicts.add(f) 694 fileconflicts.add(f)
695 elif f not in wctx:
696 path = _checkunknowndirs(repo, f)
697 if path is not None:
698 pathconflicts.add(path)
694 elif m == 'dg': 699 elif m == 'dg':
695 if _checkunknownfile(repo, wctx, mctx, f, args[0]): 700 if _checkunknownfile(repo, wctx, mctx, f, args[0]):
696 fileconflicts.add(f) 701 fileconflicts.add(f)
697 702
698 allconflicts = fileconflicts 703 allconflicts = fileconflicts | pathconflicts
699 ignoredconflicts = set([c for c in allconflicts 704 ignoredconflicts = set([c for c in allconflicts
700 if repo.dirstate._ignore(c)]) 705 if repo.dirstate._ignore(c)])
701 unknownconflicts = allconflicts - ignoredconflicts 706 unknownconflicts = allconflicts - ignoredconflicts
702 collectconflicts(ignoredconflicts, ignoredconfig) 707 collectconflicts(ignoredconflicts, ignoredconfig)
703 collectconflicts(unknownconflicts, unknownconfig) 708 collectconflicts(unknownconflicts, unknownconfig)
743 748
744 for f in sorted(warnconflicts): 749 for f in sorted(warnconflicts):
745 repo.ui.warn(_("%s: replacing untracked file\n") % f) 750 repo.ui.warn(_("%s: replacing untracked file\n") % f)
746 751
747 for f, (m, args, msg) in actions.iteritems(): 752 for f, (m, args, msg) in actions.iteritems():
748 backup = f in fileconflicts
749 if m == 'c': 753 if m == 'c':
754 backup = (f in fileconflicts or f in pathconflicts or
755 any(p in pathconflicts for p in util.finddirs(f)))
750 flags, = args 756 flags, = args
751 actions[f] = ('g', (flags, backup), msg) 757 actions[f] = ('g', (flags, backup), msg)
752 758
753 def _forgetremoved(wctx, mctx, branchmerge): 759 def _forgetremoved(wctx, mctx, branchmerge):
754 """ 760 """