comparison mercurial/merge.py @ 3730:d377f8d25662

merge: only store one direction of copies in the copy map simplify checkpair generate copied hash from copy map make copy cases more symmetrical
author Matt Mackall <mpm@selenic.com>
date Thu, 30 Nov 2006 17:36:33 -0600
parents 581d20773326
children b4af5f92e04b
comparison
equal deleted inserted replaced
3729:581d20773326 3730:d377f8d25662
134 u2 = nonoverlap(m2, m1, ma) 134 u2 = nonoverlap(m2, m1, ma)
135 ctx = util.cachefunc(lambda f, n: repo.filectx(f, fileid=n[:20])) 135 ctx = util.cachefunc(lambda f, n: repo.filectx(f, fileid=n[:20]))
136 136
137 def checkpair(c, f2, man): 137 def checkpair(c, f2, man):
138 ''' check if an apparent pair actually matches ''' 138 ''' check if an apparent pair actually matches '''
139 if f2 not in man:
140 return
139 c2 = ctx(f2, man[f2]) 141 c2 = ctx(f2, man[f2])
140 ca = c.ancestor(c2) 142 ca = c.ancestor(c2)
141 if not ca or c == ca or c2 == ca: 143 if not ca or c == ca or c2 == ca:
142 return 144 return
143 if ca.path() == c.path() or ca.path() == c2.path(): 145 if ca.path() == c.path() or ca.path() == c2.path():
144 copy[c.path()] = f2 146 copy[c.path()] = f2
145 copy[f2] = c.path()
146 147
147 for f in u1: 148 for f in u1:
148 c = ctx(dcopies.get(f, f), m1[f]) 149 c = ctx(dcopies.get(f, f), m1[f])
149 for of in findold(c, limit): 150 for of in findold(c, limit):
150 if of in m2: 151 checkpair(c, of, m2)
151 checkpair(c, of, m2)
152 152
153 for f in u2: 153 for f in u2:
154 c = ctx(f, m2[f]) 154 c = ctx(f, m2[f])
155 for of in findold(c, limit): 155 for of in findold(c, limit):
156 if of in m1: 156 checkpair(c, of, m1)
157 checkpair(c, of, m1)
158 157
159 return copy 158 return copy
160 159
161 def manifestmerge(repo, p1, p2, pa, overwrite, partial): 160 def manifestmerge(repo, p1, p2, pa, overwrite, partial):
162 """ 161 """
174 m2 = p2.manifest() 173 m2 = p2.manifest()
175 ma = pa.manifest() 174 ma = pa.manifest()
176 backwards = (pa == p2) 175 backwards = (pa == p2)
177 action = [] 176 action = []
178 copy = {} 177 copy = {}
179 copied = {}
180 178
181 def fmerge(f, f2=None, fa=None): 179 def fmerge(f, f2=None, fa=None):
182 """merge executable flags""" 180 """merge executable flags"""
183 if not f2: 181 if not f2:
184 f2 = f 182 f2 = f
190 repo.ui.debug(" %s: %s -> %s\n" % (f, msg, m)) 188 repo.ui.debug(" %s: %s -> %s\n" % (f, msg, m))
191 action.append((f, m) + args) 189 action.append((f, m) + args)
192 190
193 if pa and not (backwards or overwrite): 191 if pa and not (backwards or overwrite):
194 copy = findcopies(repo, m1, m2, ma, pa.rev()) 192 copy = findcopies(repo, m1, m2, ma, pa.rev())
193 copied = dict.fromkeys(copy.values())
195 194
196 # Compare manifests 195 # Compare manifests
197 for f, n in m1.iteritems(): 196 for f, n in m1.iteritems():
198 if partial and not partial(f): 197 if partial and not partial(f):
199 continue 198 continue
214 act("update permissions", "e", f, m2.execf(f)) 213 act("update permissions", "e", f, m2.execf(f))
215 # contents same, check mode bits 214 # contents same, check mode bits
216 elif m1.execf(f) != m2.execf(f): 215 elif m1.execf(f) != m2.execf(f):
217 if overwrite or fmerge(f) != m1.execf(f): 216 if overwrite or fmerge(f) != m1.execf(f):
218 act("update permissions", "e", f, m2.execf(f)) 217 act("update permissions", "e", f, m2.execf(f))
218 elif f in copied:
219 continue
219 elif f in copy: 220 elif f in copy:
220 f2 = copy[f] 221 f2 = copy[f]
221 copied[f2] = True 222 if f2 in m1: # case 2 A,B/B/B
222 if f in ma: # case 3,20 A/B/A 223 act("local copied to " + f2, "m",
223 act("remote moved to " + f2, "m", 224 f, f2, f, fmerge(f, f2, f2), False)
224 f, f2, f2, fmerge(f, f2, f), True) 225 else: # case 4,21 A/B/B
225 else: 226 act("local moved to " + f2, "m",
226 if f2 in m1: # case 2 A,B/B/B 227 f, f2, f, fmerge(f, f2, f2), False)
227 act("local copied to " + f2, "m",
228 f, f2, f, fmerge(f, f2, f2), False)
229 else: # case 4,21 A/B/B
230 act("local moved to " + f2, "m",
231 f, f2, f, fmerge(f, f2, f2), False)
232 elif f in ma: 228 elif f in ma:
233 if n != ma[f] and not overwrite: 229 if n != ma[f] and not overwrite:
234 if repo.ui.prompt( 230 if repo.ui.prompt(
235 (_(" local changed %s which remote deleted\n") % f) + 231 (_(" local changed %s which remote deleted\n") % f) +
236 _("(k)eep or (d)elete?"), _("[kd]"), _("k")) == _("d"): 232 _("(k)eep or (d)elete?"), _("[kd]"), _("k")) == _("d"):
249 continue 245 continue
250 if f in copied: 246 if f in copied:
251 continue 247 continue
252 if f in copy: 248 if f in copy:
253 f2 = copy[f] 249 f2 = copy[f]
254 # rename case 1, A/A,B/A 250 if f2 in m2: # rename case 1, A/A,B/A
255 act("remote copied to " + f, "m", 251 act("remote copied to " + f, "m",
256 f2, f, f, fmerge(f2, f, f2), False) 252 f2, f, f, fmerge(f2, f, f2), False)
253 else: # case 3,20 A/B/A
254 act("remote moved to " + f, "m",
255 f2, f, f, fmerge(f2, f, f2), True)
257 elif f in ma: 256 elif f in ma:
258 if overwrite or backwards: 257 if overwrite or backwards:
259 act("recreating", "g", f, m2.execf(f)) 258 act("recreating", "g", f, m2.execf(f))
260 elif n != ma[f]: 259 elif n != ma[f]:
261 if repo.ui.prompt( 260 if repo.ui.prompt(