Comment 9 for bug 494269

Revision history for this message
John A Meinel (jameinel) wrote : Re: conflict on deleted directory?

As near as I can tell, this is primarily just a bug in our handling of tree root changes. The dirstate file has this record:
[(('', '', 'tree_root-20090718094551-uvi5mimdaxki5fki-1'),
  [('a', '', 0L, 0, ''),
   ('d',
    '',
    0L,
    0,
    '<email address hidden>')]),
 (('', '', 'tree_root-20090718094551-uvi5mimdaxki5fki-143'),
  [('d', '', 0L, 0, 'AAAQAEtE3EpLRNw/AAAAAAAAAAAAAEH/'),
   ('a', '', 0L, 0, '')])]

Which AIUI, says that the root directory has a value of "tree_root-20090718094551-uvi5mimdaxki5fki-1" in the basis-tree, but a value of 'tree_root-20090718094551-uvi5mimdaxki5fki-143' in the workingtree.

A "bzr revert" fails:
    raise ValueError("Cannot have multiple roots.")
ValueError: Cannot have multiple roots.

So somehow Update was able to tell the workingtree to change the root-id, but is unable to make that actually stick.
This also follows with "wt.inventory.root" vs "wt.basis_tree().inventory.root".

Note that "wt.branch.repository.revision_tree(wt.last_revision()).inventory.root" claims the -1 revision.

It is true that revision_tree(tag:upstream-2.6.22).inventory.root does claim -143 as the root id.

My quick probing seems to say that most "upstream" versions use the -143 root-id and the non-upstream versions use the -1 root-id.

This may be related to a similar bug. Where Alexander Belchenko noted that "bzr init && bzr add --file-ids-from" doesn't work perfectly in 2a. Because each tree gets a different root id.

In a quick test, it looks like "bzr init" creates a randomly generated root-id. And so "add --file-ids-from" doesn't get a chance to set the root id to something special.

So some ideas:

1) However you are creating these imports, we should try to make sure the root ids are the same. This probably needs to happen at 'initialization' time.

2) Our code should handle root-ids changing in a better way. Updating from a revision with one root-id to a revision with a different root-id should not leave the tree in a state that thinks it still is using the old revision-id. And reverting when there is a root-id change should 'just work' not leave us in a broken state.

Note that after update and getting into the weird state, if I do:

wt = WorkingTree.open('.')
wt.lock_write()
bt = wt.basis_tree()
bt.lock_read()
wt.set_root_id(bt.inventory.root.file_id)
bt.unlock()
wt.unlock()

It clears up the issues with 'bzr status' and 'bzr revert'. So it would seem that "update" and "revert" aren't calling set_root_id() correctly.