##// END OF EJS Templates
merge: combine merge and get lists
Matt Mackall -
r2977:87a0332a default
parent child Browse files
Show More
@@ -1,333 +1,329 b''
1 # merge.py - directory-level update/merge handling for Mercurial
1 # merge.py - directory-level update/merge handling for Mercurial
2 #
2 #
3 # Copyright 2006 Matt Mackall <mpm@selenic.com>
3 # Copyright 2006 Matt Mackall <mpm@selenic.com>
4 #
4 #
5 # This software may be used and distributed according to the terms
5 # This software may be used and distributed according to the terms
6 # of the GNU General Public License, incorporated herein by reference.
6 # of the GNU General Public License, incorporated herein by reference.
7
7
8 from node import *
8 from node import *
9 from i18n import gettext as _
9 from i18n import gettext as _
10 from demandload import *
10 from demandload import *
11 demandload(globals(), "util os tempfile")
11 demandload(globals(), "util os tempfile")
12
12
13 def fmerge(f, local, other, ancestor):
13 def fmerge(f, local, other, ancestor):
14 """merge executable flags"""
14 """merge executable flags"""
15 a, b, c = ancestor.execf(f), local.execf(f), other.execf(f)
15 a, b, c = ancestor.execf(f), local.execf(f), other.execf(f)
16 return ((a^b) | (a^c)) ^ a
16 return ((a^b) | (a^c)) ^ a
17
17
18 def merge3(repo, fn, my, other, p1, p2):
18 def merge3(repo, fn, my, other, p1, p2):
19 """perform a 3-way merge in the working directory"""
19 """perform a 3-way merge in the working directory"""
20
20
21 def temp(prefix, node):
21 def temp(prefix, node):
22 pre = "%s~%s." % (os.path.basename(fn), prefix)
22 pre = "%s~%s." % (os.path.basename(fn), prefix)
23 (fd, name) = tempfile.mkstemp(prefix=pre)
23 (fd, name) = tempfile.mkstemp(prefix=pre)
24 f = os.fdopen(fd, "wb")
24 f = os.fdopen(fd, "wb")
25 repo.wwrite(fn, fl.read(node), f)
25 repo.wwrite(fn, fl.read(node), f)
26 f.close()
26 f.close()
27 return name
27 return name
28
28
29 fl = repo.file(fn)
29 fl = repo.file(fn)
30 base = fl.ancestor(my, other)
30 base = fl.ancestor(my, other)
31 a = repo.wjoin(fn)
31 a = repo.wjoin(fn)
32 b = temp("base", base)
32 b = temp("base", base)
33 c = temp("other", other)
33 c = temp("other", other)
34
34
35 repo.ui.note(_("resolving %s\n") % fn)
35 repo.ui.note(_("resolving %s\n") % fn)
36 repo.ui.debug(_("file %s: my %s other %s ancestor %s\n") %
36 repo.ui.debug(_("file %s: my %s other %s ancestor %s\n") %
37 (fn, short(my), short(other), short(base)))
37 (fn, short(my), short(other), short(base)))
38
38
39 cmd = (os.environ.get("HGMERGE") or repo.ui.config("ui", "merge")
39 cmd = (os.environ.get("HGMERGE") or repo.ui.config("ui", "merge")
40 or "hgmerge")
40 or "hgmerge")
41 r = util.system('%s "%s" "%s" "%s"' % (cmd, a, b, c), cwd=repo.root,
41 r = util.system('%s "%s" "%s" "%s"' % (cmd, a, b, c), cwd=repo.root,
42 environ={'HG_FILE': fn,
42 environ={'HG_FILE': fn,
43 'HG_MY_NODE': p1,
43 'HG_MY_NODE': p1,
44 'HG_OTHER_NODE': p2,
44 'HG_OTHER_NODE': p2,
45 'HG_FILE_MY_NODE': hex(my),
45 'HG_FILE_MY_NODE': hex(my),
46 'HG_FILE_OTHER_NODE': hex(other),
46 'HG_FILE_OTHER_NODE': hex(other),
47 'HG_FILE_BASE_NODE': hex(base)})
47 'HG_FILE_BASE_NODE': hex(base)})
48 if r:
48 if r:
49 repo.ui.warn(_("merging %s failed!\n") % fn)
49 repo.ui.warn(_("merging %s failed!\n") % fn)
50
50
51 os.unlink(b)
51 os.unlink(b)
52 os.unlink(c)
52 os.unlink(c)
53 return r
53 return r
54
54
55 def update(repo, node, branchmerge=False, force=False, partial=None,
55 def update(repo, node, branchmerge=False, force=False, partial=None,
56 wlock=None, show_stats=True, remind=True):
56 wlock=None, show_stats=True, remind=True):
57
57
58 overwrite = force and not branchmerge
58 overwrite = force and not branchmerge
59 forcemerge = force and branchmerge
59 forcemerge = force and branchmerge
60
60
61 if not wlock:
61 if not wlock:
62 wlock = repo.wlock()
62 wlock = repo.wlock()
63
63
64 ### check phase
64 ### check phase
65
65
66 pl = repo.dirstate.parents()
66 pl = repo.dirstate.parents()
67 if not overwrite and pl[1] != nullid:
67 if not overwrite and pl[1] != nullid:
68 raise util.Abort(_("outstanding uncommitted merges"))
68 raise util.Abort(_("outstanding uncommitted merges"))
69
69
70 p1, p2 = pl[0], node
70 p1, p2 = pl[0], node
71 pa = repo.changelog.ancestor(p1, p2)
71 pa = repo.changelog.ancestor(p1, p2)
72
72
73 # are we going backwards?
73 # are we going backwards?
74 backwards = (pa == p2)
74 backwards = (pa == p2)
75
75
76 # is there a linear path from p1 to p2?
76 # is there a linear path from p1 to p2?
77 linear_path = (pa == p1 or pa == p2)
77 linear_path = (pa == p1 or pa == p2)
78 if branchmerge and linear_path:
78 if branchmerge and linear_path:
79 raise util.Abort(_("there is nothing to merge, just use "
79 raise util.Abort(_("there is nothing to merge, just use "
80 "'hg update' or look at 'hg heads'"))
80 "'hg update' or look at 'hg heads'"))
81
81
82 if not linear_path and not (overwrite or branchmerge):
82 if not linear_path and not (overwrite or branchmerge):
83 raise util.Abort(_("update spans branches, use 'hg merge' "
83 raise util.Abort(_("update spans branches, use 'hg merge' "
84 "or 'hg update -C' to lose changes"))
84 "or 'hg update -C' to lose changes"))
85
85
86 modified, added, removed, deleted, unknown = repo.status()[:5]
86 modified, added, removed, deleted, unknown = repo.status()[:5]
87 if branchmerge and not forcemerge:
87 if branchmerge and not forcemerge:
88 if modified or added or removed:
88 if modified or added or removed:
89 raise util.Abort(_("outstanding uncommitted changes"))
89 raise util.Abort(_("outstanding uncommitted changes"))
90
90
91 m1n = repo.changelog.read(p1)[0]
91 m1n = repo.changelog.read(p1)[0]
92 m2n = repo.changelog.read(p2)[0]
92 m2n = repo.changelog.read(p2)[0]
93 man = repo.manifest.ancestor(m1n, m2n)
93 man = repo.manifest.ancestor(m1n, m2n)
94 m1 = repo.manifest.read(m1n).copy()
94 m1 = repo.manifest.read(m1n).copy()
95 m2 = repo.manifest.read(m2n).copy()
95 m2 = repo.manifest.read(m2n).copy()
96 ma = repo.manifest.read(man)
96 ma = repo.manifest.read(man)
97
97
98 if not force:
98 if not force:
99 for f in unknown:
99 for f in unknown:
100 if f in m2:
100 if f in m2:
101 if repo.file(f).cmp(m2[f], repo.wread(f)):
101 if repo.file(f).cmp(m2[f], repo.wread(f)):
102 raise util.Abort(_("'%s' already exists in the working"
102 raise util.Abort(_("'%s' already exists in the working"
103 " dir and differs from remote") % f)
103 " dir and differs from remote") % f)
104
104
105 # resolve the manifest to determine which files
105 # resolve the manifest to determine which files
106 # we care about merging
106 # we care about merging
107 repo.ui.note(_("resolving manifests\n"))
107 repo.ui.note(_("resolving manifests\n"))
108 repo.ui.debug(_(" overwrite %s branchmerge %s partial %s linear %s\n") %
108 repo.ui.debug(_(" overwrite %s branchmerge %s partial %s linear %s\n") %
109 (overwrite, branchmerge, bool(partial), linear_path))
109 (overwrite, branchmerge, bool(partial), linear_path))
110 repo.ui.debug(_(" ancestor %s local %s remote %s\n") %
110 repo.ui.debug(_(" ancestor %s local %s remote %s\n") %
111 (short(man), short(m1n), short(m2n)))
111 (short(man), short(m1n), short(m2n)))
112
112
113 merge = {}
113 action = {}
114 get = {}
115 remove = []
114 remove = []
116 forget = []
115 forget = []
117
116
118 # update m1 from working dir
117 # update m1 from working dir
119 umap = dict.fromkeys(unknown)
118 umap = dict.fromkeys(unknown)
120
119
121 for f in added + modified + unknown:
120 for f in added + modified + unknown:
122 m1[f] = m1.get(f, nullid) + "+"
121 m1[f] = m1.get(f, nullid) + "+"
123 m1.set(f, util.is_exec(repo.wjoin(f), m1.execf(f)))
122 m1.set(f, util.is_exec(repo.wjoin(f), m1.execf(f)))
124
123
125 for f in deleted + removed:
124 for f in deleted + removed:
126 del m1[f]
125 del m1[f]
127
126
128 # If we're jumping between revisions (as opposed to merging),
127 # If we're jumping between revisions (as opposed to merging),
129 # and if neither the working directory nor the target rev has
128 # and if neither the working directory nor the target rev has
130 # the file, then we need to remove it from the dirstate, to
129 # the file, then we need to remove it from the dirstate, to
131 # prevent the dirstate from listing the file when it is no
130 # prevent the dirstate from listing the file when it is no
132 # longer in the manifest.
131 # longer in the manifest.
133 if linear_path and f not in m2:
132 if linear_path and f not in m2:
134 forget.append(f)
133 forget.append(f)
135
134
136 if partial:
135 if partial:
137 for f in m1.keys():
136 for f in m1.keys():
138 if not partial(f): del m1[f]
137 if not partial(f): del m1[f]
139 for f in m2.keys():
138 for f in m2.keys():
140 if not partial(f): del m2[f]
139 if not partial(f): del m2[f]
141
140
142 # Compare manifests
141 # Compare manifests
143 for f, n in m1.iteritems():
142 for f, n in m1.iteritems():
144 if f in m2:
143 if f in m2:
145 queued = 0
144 queued = 0
146
145
147 # are files different?
146 # are files different?
148 if n != m2[f]:
147 if n != m2[f]:
149 a = ma.get(f, nullid)
148 a = ma.get(f, nullid)
150 # are both different from the ancestor?
149 # are both different from the ancestor?
151 if not overwrite and n != a and m2[f] != a:
150 if not overwrite and n != a and m2[f] != a:
152 repo.ui.debug(_(" %s versions differ, resolve\n") % f)
151 repo.ui.debug(_(" %s versions differ, resolve\n") % f)
153 merge[f] = (fmerge(f, m1, m2, ma), n[:20], m2[f])
152 action[f] = (fmerge(f, m1, m2, ma), n[:20], m2[f])
154 queued = 1
153 queued = 1
155 # are we clobbering?
154 # are we clobbering?
156 # is remote's version newer?
155 # is remote's version newer?
157 # or are we going back in time and clean?
156 # or are we going back in time and clean?
158 elif overwrite or m2[f] != a or (backwards and not n[20:]):
157 elif overwrite or m2[f] != a or (backwards and not n[20:]):
159 repo.ui.debug(_(" remote %s is newer, get\n") % f)
158 repo.ui.debug(_(" remote %s is newer, get\n") % f)
160 get[f] = (m2.execf(f), m2[f])
159 action[f] = (m2.execf(f), m2[f], None)
161 queued = 1
160 queued = 1
162 elif f in umap or f in added:
161 elif f in umap or f in added:
163 # this unknown file is the same as the checkout
162 # this unknown file is the same as the checkout
164 # we need to reset the dirstate if the file was added
163 # we need to reset the dirstate if the file was added
165 get[f] = (m2.execf(f), m2[f])
164 action[f] = (m2.execf(f), m2[f], None)
166
165
167 # do we still need to look at mode bits?
166 # do we still need to look at mode bits?
168 if not queued and m1.execf(f) != m2.execf(f):
167 if not queued and m1.execf(f) != m2.execf(f):
169 if overwrite:
168 if overwrite:
170 repo.ui.debug(_(" updating permissions for %s\n") % f)
169 repo.ui.debug(_(" updating permissions for %s\n") % f)
171 util.set_exec(repo.wjoin(f), m2.execf(f))
170 util.set_exec(repo.wjoin(f), m2.execf(f))
172 else:
171 else:
173 if fmerge(f, m1, m2, ma) != m1.execf(f):
172 if fmerge(f, m1, m2, ma) != m1.execf(f):
174 repo.ui.debug(_(" updating permissions for %s\n")
173 repo.ui.debug(_(" updating permissions for %s\n")
175 % f)
174 % f)
176 util.set_exec(repo.wjoin(f), mode)
175 util.set_exec(repo.wjoin(f), mode)
177 del m2[f]
176 del m2[f]
178 elif f in ma:
177 elif f in ma:
179 if n != ma[f]:
178 if n != ma[f]:
180 r = _("d")
179 r = _("d")
181 if not overwrite:
180 if not overwrite:
182 r = repo.ui.prompt(
181 r = repo.ui.prompt(
183 (_(" local changed %s which remote deleted\n") % f) +
182 (_(" local changed %s which remote deleted\n") % f) +
184 _("(k)eep or (d)elete?"), _("[kd]"), _("k"))
183 _("(k)eep or (d)elete?"), _("[kd]"), _("k"))
185 if r == _("d"):
184 if r == _("d"):
186 remove.append(f)
185 remove.append(f)
187 else:
186 else:
188 repo.ui.debug(_("other deleted %s\n") % f)
187 repo.ui.debug(_("other deleted %s\n") % f)
189 remove.append(f) # other deleted it
188 remove.append(f) # other deleted it
190 else:
189 else:
191 # file is created on branch or in working directory
190 # file is created on branch or in working directory
192 if overwrite and f not in umap:
191 if overwrite and f not in umap:
193 repo.ui.debug(_("remote deleted %s, clobbering\n") % f)
192 repo.ui.debug(_("remote deleted %s, clobbering\n") % f)
194 remove.append(f)
193 remove.append(f)
195 elif not n[20:]: # same as parent
194 elif not n[20:]: # same as parent
196 if backwards:
195 if backwards:
197 repo.ui.debug(_("remote deleted %s\n") % f)
196 repo.ui.debug(_("remote deleted %s\n") % f)
198 remove.append(f)
197 remove.append(f)
199 else:
198 else:
200 repo.ui.debug(_("local modified %s, keeping\n") % f)
199 repo.ui.debug(_("local modified %s, keeping\n") % f)
201 else:
200 else:
202 repo.ui.debug(_("working dir created %s, keeping\n") % f)
201 repo.ui.debug(_("working dir created %s, keeping\n") % f)
203
202
204 for f, n in m2.iteritems():
203 for f, n in m2.iteritems():
205 if f[0] == "/":
204 if f[0] == "/":
206 continue
205 continue
207 if f in ma and n != ma[f]:
206 if f in ma and n != ma[f]:
208 r = _("k")
207 r = _("k")
209 if not overwrite:
208 if not overwrite:
210 r = repo.ui.prompt(
209 r = repo.ui.prompt(
211 (_("remote changed %s which local deleted\n") % f) +
210 (_("remote changed %s which local deleted\n") % f) +
212 _("(k)eep or (d)elete?"), _("[kd]"), _("k"))
211 _("(k)eep or (d)elete?"), _("[kd]"), _("k"))
213 if r == _("k"):
212 if r == _("k"):
214 get[f] = (m2.execf(f), n)
213 action[f] = (m2.execf(f), n, None)
215 elif f not in ma:
214 elif f not in ma:
216 repo.ui.debug(_("remote created %s\n") % f)
215 repo.ui.debug(_("remote created %s\n") % f)
217 get[f] = (m2.execf(f), n)
216 action[f] = (m2.execf(f), n, None)
218 else:
217 else:
219 if overwrite or backwards:
218 if overwrite or backwards:
220 repo.ui.debug(_("local deleted %s, recreating\n") % f)
219 repo.ui.debug(_("local deleted %s, recreating\n") % f)
221 get[f] = (m2.execf(f), n)
220 action[f] = (m2.execf(f), n, None)
222 else:
221 else:
223 repo.ui.debug(_("local deleted %s\n") % f)
222 repo.ui.debug(_("local deleted %s\n") % f)
224
223
225 del m1, m2, ma
224 del m1, m2, ma
226
225
227 ### apply phase
226 ### apply phase
228
227
229 if linear_path or overwrite:
228 if linear_path or overwrite:
230 # we don't need to do any magic, just jump to the new rev
229 # we don't need to do any magic, just jump to the new rev
231 p1, p2 = p2, nullid
230 p1, p2 = p2, nullid
232
231
233 xp1 = hex(p1)
232 xp1 = hex(p1)
234 xp2 = hex(p2)
233 xp2 = hex(p2)
235 if p2 == nullid: xxp2 = ''
234 if p2 == nullid: xxp2 = ''
236 else: xxp2 = xp2
235 else: xxp2 = xp2
237
236
238 repo.hook('preupdate', throw=True, parent1=xp1, parent2=xxp2)
237 repo.hook('preupdate', throw=True, parent1=xp1, parent2=xxp2)
239
238
240 # get the files we don't need to change
239 # update files
241 files = get.keys()
240 unresolved = []
241 updated = 0
242 merged = 0
243 files = action.keys()
242 files.sort()
244 files.sort()
243 for f in files:
245 for f in files:
244 flag, node = get[f]
246 flag, my, other = action[f]
245 if f[0] == "/":
247 if f[0] == "/":
246 continue
248 continue
247 repo.ui.note(_("getting %s\n") % f)
249 if other:
248 t = repo.file(f).read(node)
250 repo.ui.status(_("merging %s\n") % f)
249 repo.wwrite(f, t)
251 if merge3(repo, f, my, other, xp1, xp2):
250 util.set_exec(repo.wjoin(f), flag)
252 unresolved.append(f)
251
253 merged += 1
252 # merge the tricky bits
254 else:
253 unresolved = []
255 repo.ui.note(_("getting %s\n") % f)
254 files = merge.keys()
256 t = repo.file(f).read(my)
255 files.sort()
257 repo.wwrite(f, t)
256 for f in files:
258 updated += 1
257 repo.ui.status(_("merging %s\n") % f)
258 flag, my, other = merge[f]
259 ret = merge3(repo, f, my, other, xp1, xp2)
260 if ret:
261 unresolved.append(f)
262 util.set_exec(repo.wjoin(f), flag)
259 util.set_exec(repo.wjoin(f), flag)
263
260
264 remove.sort()
261 remove.sort()
265 for f in remove:
262 for f in remove:
266 repo.ui.note(_("removing %s\n") % f)
263 repo.ui.note(_("removing %s\n") % f)
267 util.audit_path(f)
264 util.audit_path(f)
268 try:
265 try:
269 util.unlink(repo.wjoin(f))
266 util.unlink(repo.wjoin(f))
270 except OSError, inst:
267 except OSError, inst:
271 if inst.errno != errno.ENOENT:
268 if inst.errno != errno.ENOENT:
272 repo.ui.warn(_("update failed to remove %s: %s!\n") %
269 repo.ui.warn(_("update failed to remove %s: %s!\n") %
273 (f, inst.strerror))
270 (f, inst.strerror))
274
271
275 # update dirstate
272 # update dirstate
276 if not partial:
273 if not partial:
277 repo.dirstate.setparents(p1, p2)
274 repo.dirstate.setparents(p1, p2)
278 repo.dirstate.forget(forget)
275 repo.dirstate.forget(forget)
279 if branchmerge:
276 if branchmerge:
280 repo.dirstate.update(remove, 'r')
277 repo.dirstate.update(remove, 'r')
281 else:
278 else:
282 repo.dirstate.forget(remove)
279 repo.dirstate.forget(remove)
283
280
284 files = get.keys()
281 files = action.keys()
285 files.sort()
286 for f in files:
287 if branchmerge:
288 repo.dirstate.update([f], 'n', st_mtime=-1)
289 else:
290 repo.dirstate.update([f], 'n')
291
292 files = merge.keys()
293 files.sort()
282 files.sort()
294 for f in files:
283 for f in files:
295 if branchmerge:
284 flag, my, other = action[f]
296 # We've done a branch merge, mark this file as merged
285 if not other:
297 # so that we properly record the merger later
286 if branchmerge:
298 repo.dirstate.update([f], 'm')
287 repo.dirstate.update([f], 'n', st_mtime=-1)
288 else:
289 repo.dirstate.update([f], 'n')
299 else:
290 else:
300 # We've update-merged a locally modified file, so
291 if branchmerge:
301 # we set the dirstate to emulate a normal checkout
292 # We've done a branch merge, mark this file as merged
302 # of that file some time in the past. Thus our
293 # so that we properly record the merger later
303 # merge will appear as a normal local file
294 repo.dirstate.update([f], 'm')
304 # modification.
295 else:
305 fl = repo.file(f)
296 # We've update-merged a locally modified file, so
306 f_len = fl.size(fl.rev(other))
297 # we set the dirstate to emulate a normal checkout
307 repo.dirstate.update([f], 'n', st_size=f_len, st_mtime=-1)
298 # of that file some time in the past. Thus our
299 # merge will appear as a normal local file
300 # modification.
301 fl = repo.file(f)
302 f_len = fl.size(fl.rev(other))
303 repo.dirstate.update([f], 'n', st_size=f_len, st_mtime=-1)
308
304
309 if show_stats:
305 if show_stats:
310 stats = ((len(get), _("updated")),
306 stats = ((updated, _("updated")),
311 (len(merge) - len(unresolved), _("merged")),
307 (merged - len(unresolved), _("merged")),
312 (len(remove), _("removed")),
308 (len(remove), _("removed")),
313 (len(unresolved), _("unresolved")))
309 (len(unresolved), _("unresolved")))
314 note = ", ".join([_("%d files %s") % s for s in stats])
310 note = ", ".join([_("%d files %s") % s for s in stats])
315 repo.ui.status("%s\n" % note)
311 repo.ui.status("%s\n" % note)
316 if not partial:
312 if not partial:
317 if branchmerge:
313 if branchmerge:
318 if unresolved:
314 if unresolved:
319 repo.ui.status(_("There are unresolved merges,"
315 repo.ui.status(_("There are unresolved merges,"
320 " you can redo the full merge using:\n"
316 " you can redo the full merge using:\n"
321 " hg update -C %s\n"
317 " hg update -C %s\n"
322 " hg merge %s\n"
318 " hg merge %s\n"
323 % (repo.changelog.rev(p1),
319 % (repo.changelog.rev(p1),
324 repo.changelog.rev(p2))))
320 repo.changelog.rev(p2))))
325 elif remind:
321 elif remind:
326 repo.ui.status(_("(branch merge, don't forget to commit)\n"))
322 repo.ui.status(_("(branch merge, don't forget to commit)\n"))
327 elif unresolved:
323 elif unresolved:
328 repo.ui.status(_("There are unresolved merges with"
324 repo.ui.status(_("There are unresolved merges with"
329 " locally modified files.\n"))
325 " locally modified files.\n"))
330
326
331 repo.hook('update', parent1=xp1, parent2=xxp2, error=len(unresolved))
327 repo.hook('update', parent1=xp1, parent2=xxp2, error=len(unresolved))
332 return len(unresolved)
328 return len(unresolved)
333
329
@@ -1,141 +1,141 b''
1 adding a
1 adding a
2 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
2 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
3 0 files updated, 0 files merged, 0 files removed, 0 files unresolved
3 0 files updated, 0 files merged, 0 files removed, 0 files unresolved
4 diff -r 33aaa84a386b a
4 diff -r 33aaa84a386b a
5 --- a/a
5 --- a/a
6 +++ b/a
6 +++ b/a
7 @@ -1,1 +1,1 @@ a
7 @@ -1,1 +1,1 @@ a
8 -a
8 -a
9 +abc
9 +abc
10 adding b
10 adding b
11 M a
11 M a
12 changeset: 0:33aaa84a386b
12 changeset: 0:33aaa84a386b
13 user: test
13 user: test
14 date: Mon Jan 12 13:46:40 1970 +0000
14 date: Mon Jan 12 13:46:40 1970 +0000
15 summary: 1
15 summary: 1
16
16
17 resolving manifests
17 resolving manifests
18 overwrite False branchmerge False partial False linear True
18 overwrite False branchmerge False partial False linear True
19 ancestor a0c8bcbbb45c local a0c8bcbbb45c remote 1165e8bd193e
19 ancestor a0c8bcbbb45c local a0c8bcbbb45c remote 1165e8bd193e
20 a versions differ, resolve
20 a versions differ, resolve
21 remote created b
21 remote created b
22 getting b
23 merging a
22 merging a
24 resolving a
23 resolving a
25 file a: my b789fdd96dc2 other d730145abbf9 ancestor b789fdd96dc2
24 file a: my b789fdd96dc2 other d730145abbf9 ancestor b789fdd96dc2
25 getting b
26 1 files updated, 1 files merged, 0 files removed, 0 files unresolved
26 1 files updated, 1 files merged, 0 files removed, 0 files unresolved
27 changeset: 1:802f095af299
27 changeset: 1:802f095af299
28 tag: tip
28 tag: tip
29 user: test
29 user: test
30 date: Mon Jan 12 13:46:40 1970 +0000
30 date: Mon Jan 12 13:46:40 1970 +0000
31 summary: 2
31 summary: 2
32
32
33 resolving manifests
33 resolving manifests
34 overwrite False branchmerge False partial False linear True
34 overwrite False branchmerge False partial False linear True
35 ancestor a0c8bcbbb45c local 1165e8bd193e remote a0c8bcbbb45c
35 ancestor a0c8bcbbb45c local 1165e8bd193e remote a0c8bcbbb45c
36 remote deleted b
36 remote deleted b
37 removing b
37 removing b
38 0 files updated, 0 files merged, 1 files removed, 0 files unresolved
38 0 files updated, 0 files merged, 1 files removed, 0 files unresolved
39 changeset: 0:33aaa84a386b
39 changeset: 0:33aaa84a386b
40 user: test
40 user: test
41 date: Mon Jan 12 13:46:40 1970 +0000
41 date: Mon Jan 12 13:46:40 1970 +0000
42 summary: 1
42 summary: 1
43
43
44 abort: there is nothing to merge - use "hg update" instead
44 abort: there is nothing to merge - use "hg update" instead
45 failed
45 failed
46 changeset: 0:33aaa84a386b
46 changeset: 0:33aaa84a386b
47 user: test
47 user: test
48 date: Mon Jan 12 13:46:40 1970 +0000
48 date: Mon Jan 12 13:46:40 1970 +0000
49 summary: 1
49 summary: 1
50
50
51 resolving manifests
51 resolving manifests
52 overwrite False branchmerge False partial False linear True
52 overwrite False branchmerge False partial False linear True
53 ancestor a0c8bcbbb45c local a0c8bcbbb45c remote 1165e8bd193e
53 ancestor a0c8bcbbb45c local a0c8bcbbb45c remote 1165e8bd193e
54 a versions differ, resolve
54 a versions differ, resolve
55 remote created b
55 remote created b
56 getting b
57 merging a
56 merging a
58 resolving a
57 resolving a
59 file a: my b789fdd96dc2 other d730145abbf9 ancestor b789fdd96dc2
58 file a: my b789fdd96dc2 other d730145abbf9 ancestor b789fdd96dc2
59 getting b
60 1 files updated, 1 files merged, 0 files removed, 0 files unresolved
60 1 files updated, 1 files merged, 0 files removed, 0 files unresolved
61 changeset: 1:802f095af299
61 changeset: 1:802f095af299
62 tag: tip
62 tag: tip
63 user: test
63 user: test
64 date: Mon Jan 12 13:46:40 1970 +0000
64 date: Mon Jan 12 13:46:40 1970 +0000
65 summary: 2
65 summary: 2
66
66
67 changeset: 1:802f095af299
67 changeset: 1:802f095af299
68 tag: tip
68 tag: tip
69 user: test
69 user: test
70 date: Mon Jan 12 13:46:40 1970 +0000
70 date: Mon Jan 12 13:46:40 1970 +0000
71 files: a b
71 files: a b
72 description:
72 description:
73 2
73 2
74
74
75
75
76 changeset: 0:33aaa84a386b
76 changeset: 0:33aaa84a386b
77 user: test
77 user: test
78 date: Mon Jan 12 13:46:40 1970 +0000
78 date: Mon Jan 12 13:46:40 1970 +0000
79 files: a
79 files: a
80 description:
80 description:
81 1
81 1
82
82
83
83
84 diff -r 802f095af299 a
84 diff -r 802f095af299 a
85 --- a/a
85 --- a/a
86 +++ b/a
86 +++ b/a
87 @@ -1,1 +1,1 @@ a2
87 @@ -1,1 +1,1 @@ a2
88 -a2
88 -a2
89 +abc
89 +abc
90 1 files updated, 0 files merged, 1 files removed, 0 files unresolved
90 1 files updated, 0 files merged, 1 files removed, 0 files unresolved
91 adding b
91 adding b
92 M a
92 M a
93 changeset: 1:802f095af299
93 changeset: 1:802f095af299
94 user: test
94 user: test
95 date: Mon Jan 12 13:46:40 1970 +0000
95 date: Mon Jan 12 13:46:40 1970 +0000
96 summary: 2
96 summary: 2
97
97
98 abort: update spans branches, use 'hg merge' or 'hg update -C' to lose changes
98 abort: update spans branches, use 'hg merge' or 'hg update -C' to lose changes
99 failed
99 failed
100 abort: outstanding uncommitted changes
100 abort: outstanding uncommitted changes
101 failed
101 failed
102 resolving manifests
102 resolving manifests
103 overwrite False branchmerge True partial False linear False
103 overwrite False branchmerge True partial False linear False
104 ancestor a0c8bcbbb45c local 1165e8bd193e remote 4096f2872392
104 ancestor a0c8bcbbb45c local 1165e8bd193e remote 4096f2872392
105 a versions differ, resolve
105 a versions differ, resolve
106 b versions differ, resolve
106 b versions differ, resolve
107 merging a
107 merging a
108 resolving a
108 resolving a
109 file a: my d730145abbf9 other 13e0d5f949fa ancestor b789fdd96dc2
109 file a: my d730145abbf9 other 13e0d5f949fa ancestor b789fdd96dc2
110 merging b
110 merging b
111 resolving b
111 resolving b
112 file b: my 1e88685f5dde other 61de8c7723ca ancestor 000000000000
112 file b: my 1e88685f5dde other 61de8c7723ca ancestor 000000000000
113 0 files updated, 2 files merged, 0 files removed, 0 files unresolved
113 0 files updated, 2 files merged, 0 files removed, 0 files unresolved
114 (branch merge, don't forget to commit)
114 (branch merge, don't forget to commit)
115 changeset: 1:802f095af299
115 changeset: 1:802f095af299
116 user: test
116 user: test
117 date: Mon Jan 12 13:46:40 1970 +0000
117 date: Mon Jan 12 13:46:40 1970 +0000
118 summary: 2
118 summary: 2
119
119
120 changeset: 2:030602aee63d
120 changeset: 2:030602aee63d
121 tag: tip
121 tag: tip
122 parent: 0:33aaa84a386b
122 parent: 0:33aaa84a386b
123 user: test
123 user: test
124 date: Mon Jan 12 13:46:40 1970 +0000
124 date: Mon Jan 12 13:46:40 1970 +0000
125 summary: 3
125 summary: 3
126
126
127 diff -r 802f095af299 a
127 diff -r 802f095af299 a
128 --- a/a
128 --- a/a
129 +++ b/a
129 +++ b/a
130 @@ -1,1 +1,1 @@ a2
130 @@ -1,1 +1,1 @@ a2
131 -a2
131 -a2
132 +abc
132 +abc
133 adding a
133 adding a
134 pulling from ../a
134 pulling from ../a
135 requesting all changes
135 requesting all changes
136 adding changesets
136 adding changesets
137 adding manifests
137 adding manifests
138 adding file changes
138 adding file changes
139 added 1 changesets with 1 changes to 1 files
139 added 1 changesets with 1 changes to 1 files
140 merging a
140 merging a
141 0 files updated, 1 files merged, 0 files removed, 0 files unresolved
141 0 files updated, 1 files merged, 0 files removed, 0 files unresolved
General Comments 0
You need to be logged in to leave comments. Login now