Rev 4729: merge trunk to get test cleanups and resolve conflicts in file:///home/vila/src/bzr/bugs/438158-dpush-strict/
Vincent Ladeuil
v.ladeuil+lp at free.fr
Fri Oct 2 15:50:36 BST 2009
At file:///home/vila/src/bzr/bugs/438158-dpush-strict/
------------------------------------------------------------
revno: 4729 [merge]
revision-id: v.ladeuil+lp at free.fr-20091002145035-z2arxiih2zaa5qo5
parent: v.ladeuil+lp at free.fr-20091002143530-v47dydvknxbkcfw8
parent: pqm at pqm.ubuntu.com-20091002101015-hed4j97ksfqyu4mp
committer: Vincent Ladeuil <v.ladeuil+lp at free.fr>
branch nick: 438158-dpush-strict
timestamp: Fri 2009-10-02 16:50:35 +0200
message:
merge trunk to get test cleanups and resolve conflicts
modified:
NEWS NEWS-20050323055033-4e00b5db738777ff
bzrlib/_btree_serializer_pyx.pyx _parse_btree_c.pyx-20080703034413-3q25bklkenti3p8p-2
bzrlib/_dirstate_helpers_pyx.pyx dirstate_helpers.pyx-20070503201057-u425eni465q4idwn-3
bzrlib/dirstate.py dirstate.py-20060728012006-d6mvoihjb3je9peu-1
bzrlib/inventory.py inventory.py-20050309040759-6648b84ca2005b37
bzrlib/mutabletree.py mutabletree.py-20060906023413-4wlkalbdpsxi2r4y-2
bzrlib/remote.py remote.py-20060720103555-yeeg2x51vn0rbtdp-1
bzrlib/tests/__init__.py selftest.py-20050531073622-8d0e3c8845c97a64
bzrlib/tests/per_interrepository/test_fetch.py test_fetch.py-20080425213627-j60cjh782ufm83ry-1
bzrlib/tests/per_intertree/test_compare.py test_compare.py-20060724101752-09ysswo1a92uqyoz-2
bzrlib/tests/per_workingtree/test_smart_add.py test_smart_add.py-20070215175752-9s5mxoz8aqpd80fm-1
bzrlib/tests/test_transform.py test_transaction.py-20060105172520-b3ffb3946550e6c4
bzrlib/transform.py transform.py-20060105172343-dd99e54394d91687
bzrlib/transport/ssh.py ssh.py-20060824042150-0s9787kng6zv1nwq-1
bzrlib/workingtree_4.py workingtree_4.py-20070208044105-5fgpc5j3ljlh5q6c-1
-------------- next part --------------
=== modified file 'NEWS'
--- a/NEWS 2009-10-02 09:11:43 +0000
+++ b/NEWS 2009-10-02 14:50:35 +0000
@@ -49,6 +49,10 @@
sent a signal to the bzr process specifically, for example by typing
``kill -QUIT PID`` in another shell. (Martin Pool, #341535)
+* ``bzr add`` in a tree that has files with ``\r`` or ``\n`` in the
+ filename will issue a warning and skip over those files.
+ (Robert Collins, #3918)
+
* ``bzr check`` in pack-0.92, 1.6 and 1.9 format repositories will no
longer report incorrect errors about ``Missing inventory ('TREE_ROOT', ...)``
(Robert Collins, #416732)
@@ -65,6 +69,10 @@
merges are present in the working tree.
(Vincent Ladeuil, #426344)
+* bzr will attempt to authenticate with SSH servers that support
+ ``keyboard-interactive`` auth but not ``password`` auth when using
+ Paramiko. (Andrew Bennetts, #433846)
+
* Clearer message when Bazaar runs out of memory, instead of a ``MemoryError``
traceback. (Martin Pool, #109115)
@@ -89,6 +97,10 @@
is a fairly well packed repository (not as good as 'bzr pack' but
good-enough.) (Robert Collins, John Arbash Meinel, #402652)
+* Fixed fetches from a stacked branch on a smart server that were failing
+ with some combinations of remote and local formats. This was causing
+ "unknown object type identifier 60" errors. (Andrew Bennetts, #427736)
+
* Network streams now decode adjacent records of the same type into a
single stream, reducing layering churn. (Robert Collins)
@@ -96,6 +108,14 @@
object when doing a merge, and there is limbo, or pending-deletions
directory. (Gary van der Merwe, #427773)
+* Occasional IndexError on renamed files have been fixed. Operations that
+ set a full inventory in the working tree will now go via the
+ apply_inventory_delta code path which is simpler and easier to
+ understand than dirstates set_state_from_inventory method. This may
+ have a small performance impact on operations built on _write_inventory,
+ but such operations are already doing full tree scans, so no radical
+ performance change should be observed. (Robert Collins, #403322)
+
* Prevent some kinds of incomplete data from being committed to a 2a
repository, such as revisions without inventories or inventories without
chk_bytes root records.
@@ -111,6 +131,9 @@
domains or user ids embedding '.sig'. Now they can.
(Matthew Fuller, Vincent Ladeuil, #430868)
+* When a file kind becomes unversionable after being added, a sensible
+ error will be shown instead of a traceback. (Robert Collins, #438569)
+
Improvements
************
@@ -171,6 +194,9 @@
documentation in ``developers/testing.txt`` for details.
(Vincent Ladeuil)
+* Stop showing the number of tests due to missing features in the test
+ progress bar. (Martin Pool)
+
* Test parameterisation now does a shallow copy, not a deep copy of the test
to be parameterised. This is not expected to break external use of test
parameterisation, and is substantially faster. (Robert Collins)
@@ -194,6 +220,18 @@
Bug Fixes
*********
+* ``bzr add`` in a tree that has files with ``\r`` or ``\n`` in the
+ filename will issue a warning and skip over those files.
+ (Robert Collins, #3918)
+
+* bzr will attempt to authenticate with SSH servers that support
+ ``keyboard-interactive`` auth but not ``password`` auth when using
+ Paramiko. (Andrew Bennetts, #433846)
+
+* Fixed fetches from a stacked branch on a smart server that were failing
+ with some combinations of remote and local formats. This was causing
+ "unknown object type identifier 60" errors. (Andrew Bennetts, #427736)
+
* Improve the time for ``bzr log DIR`` for 2a format repositories.
We had been using the same code path as for <2a formats, which required
iterating over all objects in all revisions.
@@ -203,6 +241,20 @@
object when doing a merge, and there is limbo, or pending-deletions
directory. (Gary van der Merwe, #427773)
+* Occasional IndexError on renamed files have been fixed. Operations that
+ set a full inventory in the working tree will now go via the
+ apply_inventory_delta code path which is simpler and easier to
+ understand than dirstates set_state_from_inventory method. This may
+ have a small performance impact on operations built on _write_inventory,
+ but such operations are already doing full tree scans, so no radical
+ performance change should be observed. (Robert Collins, #403322)
+
+* When a file kind becomes unversionable after being added, a sensible
+ error will be shown instead of a traceback. (Robert Collins, #438569)
+
+* Retrieving file text or mtime from a _PreviewTree has good performance when
+ there are many changes. (Aaron Bentley)
+
bzr 2.0.0
#########
=== modified file 'bzrlib/_btree_serializer_pyx.pyx'
--- a/bzrlib/_btree_serializer_pyx.pyx 2009-09-04 21:16:14 +0000
+++ b/bzrlib/_btree_serializer_pyx.pyx 2009-10-02 05:43:41 +0000
@@ -188,14 +188,13 @@
# And the next string is right after it
self._cur_str = last + 1
# The last character is right before the '\n'
- last = last
if last == self._start:
# parsed it all.
return 0
if last < self._start:
# Unexpected error condition - fail
- return -1
+ raise AssertionError("last < self._start")
if 0 == self._header_found:
# The first line in a leaf node is the header "type=leaf\n"
if strncmp("type=leaf", self._start, last - self._start) == 0:
@@ -204,14 +203,13 @@
else:
raise AssertionError('Node did not start with "type=leaf": %r'
% (safe_string_from_size(self._start, last - self._start)))
- return -1
key = self.extract_key(last)
# find the value area
temp_ptr = <char*>_my_memrchr(self._start, c'\0', last - self._start)
if temp_ptr == NULL:
# Invalid line
- return -1
+ raise AssertionError("Failed to find the value area")
else:
# capture the value string
value = safe_string_from_size(temp_ptr + 1, last - temp_ptr - 1)
@@ -225,15 +223,15 @@
# extract a reference list
loop_counter = loop_counter + 1
if last < self._start:
- return -1
+ raise AssertionError("last < self._start")
# find the next reference list end point:
temp_ptr = <char*>memchr(self._start, c'\t', last - self._start)
if temp_ptr == NULL:
# Only valid for the last list
if loop_counter != self.ref_list_length:
# Invalid line
- return -1
- raise AssertionError("invalid key")
+ raise AssertionError(
+ "invalid key, loop_counter != self.ref_list_length")
else:
# scan to the end of the ref list area
ref_ptr = last
@@ -259,7 +257,7 @@
else:
if last != self._start:
# unexpected reference data present
- return -1
+ raise AssertionError("unexpected reference data present")
node_value = (value, ())
PyList_Append(self.keys, (key, node_value))
return 0
=== modified file 'bzrlib/_dirstate_helpers_pyx.pyx'
--- a/bzrlib/_dirstate_helpers_pyx.pyx 2009-08-28 05:00:33 +0000
+++ b/bzrlib/_dirstate_helpers_pyx.pyx 2009-10-02 05:43:41 +0000
@@ -1202,7 +1202,9 @@
content_change = 0
target_exec = False
else:
- raise Exception, "unknown kind %s" % path_info[2]
+ if path is None:
+ path = self.pathjoin(old_dirname, old_basename)
+ raise errors.BadFileKindError(path, path_info[2])
if source_minikind == c'd':
if path is None:
old_path = path = self.pathjoin(old_dirname, old_basename)
=== modified file 'bzrlib/dirstate.py'
--- a/bzrlib/dirstate.py 2009-09-14 01:48:28 +0000
+++ b/bzrlib/dirstate.py 2009-10-02 05:43:41 +0000
@@ -1324,7 +1324,7 @@
key = (dirname_utf8, basename, file_id)
minikind = DirState._kind_to_minikind[inv_entry.kind]
if minikind == 't':
- fingerprint = inv_entry.reference_revision
+ fingerprint = inv_entry.reference_revision or ''
else:
fingerprint = ''
insertions[file_id] = (key, minikind, inv_entry.executable,
@@ -3328,7 +3328,9 @@
content_change = False
target_exec = False
else:
- raise Exception, "unknown kind %s" % path_info[2]
+ if path is None:
+ path = pathjoin(old_dirname, old_basename)
+ raise errors.BadFileKindError(path, path_info[2])
if source_minikind == 'd':
if path is None:
old_path = path = pathjoin(old_dirname, old_basename)
=== modified file 'bzrlib/inventory.py'
--- a/bzrlib/inventory.py 2009-09-25 21:24:21 +0000
+++ b/bzrlib/inventory.py 2009-10-02 05:43:41 +0000
@@ -2305,7 +2305,7 @@
try:
factory = entry_factory[kind]
except KeyError:
- raise BzrError("unknown kind %r" % kind)
+ raise errors.BadFileKindError(name, kind)
return factory(file_id, name, parent_id)
=== modified file 'bzrlib/mutabletree.py'
--- a/bzrlib/mutabletree.py 2009-09-07 23:14:05 +0000
+++ b/bzrlib/mutabletree.py 2009-09-28 02:02:30 +0000
@@ -23,6 +23,7 @@
from bzrlib.lazy_import import lazy_import
lazy_import(globals(), """
import os
+import re
from bzrlib import (
add,
@@ -427,6 +428,7 @@
dirs_to_add.append((path, None))
prev_dir = path.raw_path
+ illegalpath_re = re.compile(r'[\r\n]')
# dirs_to_add is initialised to a list of directories, but as we scan
# directories we append files to it.
# XXX: We should determine kind of files when we scan them rather than
@@ -443,6 +445,9 @@
if not InventoryEntry.versionable_kind(kind):
warning("skipping %s (can't add file of kind '%s')", abspath, kind)
continue
+ if illegalpath_re.search(directory.raw_path):
+ warning("skipping %r (contains \\n or \\r)" % abspath)
+ continue
if parent_ie is not None:
versioned = directory.base_path in parent_ie.children
=== modified file 'bzrlib/remote.py'
--- a/bzrlib/remote.py 2009-09-24 05:31:23 +0000
+++ b/bzrlib/remote.py 2009-10-02 05:43:41 +0000
@@ -1923,7 +1923,7 @@
:param search: The overall search to satisfy with streams.
:param sources: A list of Repository objects to query.
"""
- self.serialiser = self.to_format._serializer
+ self.from_serialiser = self.from_repository._format._serializer
self.seen_revs = set()
self.referenced_revs = set()
# If there are heads in the search, or the key count is > 0, we are not
@@ -1946,7 +1946,8 @@
def missing_parents_rev_handler(self, substream):
for content in substream:
revision_bytes = content.get_bytes_as('fulltext')
- revision = self.serialiser.read_revision_from_string(revision_bytes)
+ revision = self.from_serialiser.read_revision_from_string(
+ revision_bytes)
self.seen_revs.add(content.key[-1])
self.referenced_revs.update(revision.parent_ids)
yield content
=== modified file 'bzrlib/tests/__init__.py'
--- a/bzrlib/tests/__init__.py 2009-09-25 05:19:17 +0000
+++ b/bzrlib/tests/__init__.py 2009-10-01 14:44:43 +0000
@@ -496,8 +496,8 @@
a += ', %d err' % self.error_count
if self.failure_count:
a += ', %d fail' % self.failure_count
- if self.unsupported:
- a += ', %d missing' % len(self.unsupported)
+ # if self.unsupported:
+ # a += ', %d missing' % len(self.unsupported)
a += ']'
return a
=== modified file 'bzrlib/tests/per_interrepository/test_fetch.py'
--- a/bzrlib/tests/per_interrepository/test_fetch.py 2009-09-09 02:14:12 +0000
+++ b/bzrlib/tests/per_interrepository/test_fetch.py 2009-10-02 02:40:37 +0000
@@ -134,6 +134,44 @@
to_repo.texts.get_record_stream([('foo', revid)],
'unordered', True).next().get_bytes_as('fulltext'))
+ def test_fetch_from_stacked_smart(self):
+ self.setup_smart_server_with_call_log()
+ self.test_fetch_from_stacked()
+
+ def test_fetch_from_stacked_smart_old(self):
+ self.setup_smart_server_with_call_log()
+ self.disable_verb('Repository.get_stream_1.19')
+ self.test_fetch_from_stacked()
+
+ def test_fetch_from_stacked(self):
+ """Fetch from a stacked branch succeeds."""
+ if not self.repository_format.supports_external_lookups:
+ raise TestNotApplicable("Need stacking support in the source.")
+ builder = self.make_branch_builder('full-branch')
+ builder.start_series()
+ builder.build_snapshot('first', None, [
+ ('add', ('', 'root-id', 'directory', '')),
+ ('add', ('file', 'file-id', 'file', 'content\n'))])
+ builder.build_snapshot('second', ['first'], [
+ ('modify', ('file-id', 'second content\n'))])
+ builder.build_snapshot('third', ['second'], [
+ ('modify', ('file-id', 'third content\n'))])
+ builder.finish_series()
+ branch = builder.get_branch()
+ repo = self.make_repository('stacking-base')
+ trunk = repo.bzrdir.create_branch()
+ trunk.repository.fetch(branch.repository, 'second')
+ repo = self.make_repository('stacked')
+ stacked_branch = repo.bzrdir.create_branch()
+ stacked_branch.set_stacked_on_url(trunk.base)
+ stacked_branch.repository.fetch(branch.repository, 'third')
+ target = self.make_to_repository('target')
+ target.fetch(stacked_branch.repository, 'third')
+ target.lock_read()
+ self.addCleanup(target.unlock)
+ all_revs = set(['first', 'second', 'third'])
+ self.assertEqual(all_revs, set(target.get_parent_map(all_revs)))
+
def test_fetch_parent_inventories_at_stacking_boundary_smart(self):
self.setup_smart_server_with_call_log()
self.test_fetch_parent_inventories_at_stacking_boundary()
=== modified file 'bzrlib/tests/per_intertree/test_compare.py'
--- a/bzrlib/tests/per_intertree/test_compare.py 2009-08-28 05:00:33 +0000
+++ b/bzrlib/tests/per_intertree/test_compare.py 2009-10-02 05:43:41 +0000
@@ -948,6 +948,39 @@
(False, True))],
self.do_iter_changes(tree1, tree2))
+ def test_file_becomes_unversionable_bug_438569(self):
+ # This isn't strictly a intertree problem, but its the intertree code
+ # path that triggers all stat cache updates on both xml and dirstate
+ # trees.
+ # In bug 438569, a file becoming a fifo causes an assert. Fifo's are
+ # not versionable or diffable. For now, we simply stop cold when they
+ # are detected (because we don't know how far through the code the
+ # assumption 'fifo's do not exist' goes). In future we could report
+ # the kind change and have commit refuse to go futher, or something
+ # similar. One particular reason for choosing this approach is that
+ # there is no minikind for 'fifo' in dirstate today, so we can't
+ # actually update records that way.
+ # To add confusion, the totally generic code path works - but it
+ # doesn't update persistent metadata. So this test permits InterTrees
+ # to either work, or fail with BadFileKindError.
+ self.requireFeature(tests.OsFifoFeature)
+ tree1 = self.make_branch_and_tree('1')
+ self.build_tree(['1/a'])
+ tree1.set_root_id('root-id')
+ tree1.add(['a'], ['a-id'])
+ tree2 = self.make_branch_and_tree('2')
+ os.mkfifo('2/a')
+ tree2.add(['a'], ['a-id'], ['file'])
+ try:
+ tree1, tree2 = self.mutable_trees_to_test_trees(self, tree1, tree2)
+ except (KeyError,):
+ raise tests.TestNotApplicable(
+ "Cannot represent a FIFO in this case %s" % self.id())
+ try:
+ self.do_iter_changes(tree1, tree2)
+ except errors.BadFileKindError:
+ pass
+
def test_missing_in_target(self):
"""Test with the target files versioned but absent from disk."""
tree1 = self.make_branch_and_tree('1')
=== modified file 'bzrlib/tests/per_workingtree/test_smart_add.py'
--- a/bzrlib/tests/per_workingtree/test_smart_add.py 2009-07-10 07:14:02 +0000
+++ b/bzrlib/tests/per_workingtree/test_smart_add.py 2009-09-28 02:02:30 +0000
@@ -51,6 +51,18 @@
self.assertEqual([('', 'V', 'directory'), ('a', 'V', 'file')],
files)
+ def assertFilenameSkipped(self, filename):
+ tree = self.make_branch_and_tree('tree')
+ self.build_tree(['tree/'+filename])
+ tree.smart_add(['tree'])
+ self.assertEqual(None, tree.path2id(filename))
+
+ def test_path_containing_newline_skips(self):
+ self.assertFilenameSkipped('a\nb')
+
+ def test_path_containing_carriagereturn_skips(self):
+ self.assertFilenameSkipped('a\rb')
+
def test_save_false(self):
"""Dry-run add doesn't permanently affect the tree."""
wt = self.make_branch_and_tree('.')
=== modified file 'bzrlib/tests/test_transform.py'
--- a/bzrlib/tests/test_transform.py 2009-09-29 04:40:55 +0000
+++ b/bzrlib/tests/test_transform.py 2009-10-02 05:43:41 +0000
@@ -2629,7 +2629,9 @@
def test_walkdirs(self):
preview = self.get_empty_preview()
- preview.version_file('tree-root', preview.root)
+ root = preview.new_directory('', ROOT_PARENT, 'tree-root')
+ # FIXME: new_directory should mark root.
+ preview.adjust_path('', ROOT_PARENT, root)
preview_tree = preview.get_preview_tree()
file_trans_id = preview.new_file('a', preview.root, 'contents',
'a-id')
@@ -2666,11 +2668,11 @@
self.addCleanup(work_tree.unlock)
preview = TransformPreview(work_tree)
self.addCleanup(preview.finalize)
- preview_tree = preview.get_preview_tree()
file_trans_id = preview.trans_id_file_id('file-id')
preview.delete_contents(file_trans_id)
preview.create_file('a\nb\n', file_trans_id)
pb = progress.DummyProgress()
+ preview_tree = preview.get_preview_tree()
merger = Merger.from_revision_ids(pb, preview_tree,
child_tree.branch.last_revision(),
other_branch=child_tree.branch,
=== modified file 'bzrlib/transform.py'
--- a/bzrlib/transform.py 2009-09-29 04:40:55 +0000
+++ b/bzrlib/transform.py 2009-10-02 05:43:41 +0000
@@ -859,8 +859,8 @@
def get_preview_tree(self):
"""Return a tree representing the result of the transform.
- This tree only supports the subset of Tree functionality required
- by show_diff_trees. It must only be compared to tt._tree.
+ The tree is a snapshot, and altering the TreeTransform will invalidate
+ it.
"""
return _PreviewTree(self)
@@ -1635,15 +1635,12 @@
self._all_children_cache = {}
self._path2trans_id_cache = {}
self._final_name_cache = {}
-
- def _changes(self, file_id):
- for changes in self._transform.iter_changes():
- if changes[0] == file_id:
- return changes
+ self._iter_changes_cache = dict((c[0], c) for c in
+ self._transform.iter_changes())
def _content_change(self, file_id):
"""Return True if the content of this file changed"""
- changes = self._changes(file_id)
+ changes = self._iter_changes_cache.get(file_id)
# changes[2] is true if the file content changed. See
# InterTree.iter_changes.
return (changes is not None and changes[2])
@@ -1990,7 +1987,7 @@
def annotate_iter(self, file_id,
default_revision=_mod_revision.CURRENT_REVISION):
- changes = self._changes(file_id)
+ changes = self._iter_changes_cache.get(file_id)
if changes is None:
get_old = True
else:
=== modified file 'bzrlib/transport/ssh.py'
--- a/bzrlib/transport/ssh.py 2009-08-28 05:00:33 +0000
+++ b/bzrlib/transport/ssh.py 2009-10-02 05:43:41 +0000
@@ -504,7 +504,16 @@
except paramiko.SSHException, e:
# Don't know what happened, but just ignore it
pass
- if 'password' not in supported_auth_types:
+ # We treat 'keyboard-interactive' and 'password' auth methods identically,
+ # because Paramiko's auth_password method will automatically try
+ # 'keyboard-interactive' auth (using the password as the response) if
+ # 'password' auth is not available. Apparently some Debian and Gentoo
+ # OpenSSH servers require this.
+ # XXX: It's possible for a server to require keyboard-interactive auth that
+ # requires something other than a single password, but we currently don't
+ # support that.
+ if ('password' not in supported_auth_types and
+ 'keyboard-interactive' not in supported_auth_types):
raise errors.ConnectionError('Unable to authenticate to SSH host as'
'\n %s@%s\nsupported auth types: %s'
% (username, host, supported_auth_types))
=== modified file 'bzrlib/workingtree_4.py'
--- a/bzrlib/workingtree_4.py 2009-08-25 04:43:21 +0000
+++ b/bzrlib/workingtree_4.py 2009-09-30 21:38:49 +0000
@@ -1267,9 +1267,17 @@
if self._dirty:
raise AssertionError("attempting to write an inventory when the "
"dirstate is dirty will lose pending changes")
- self.current_dirstate().set_state_from_inventory(inv)
- self._make_dirty(reset_inventory=False)
- if self._inventory is not None:
+ had_inventory = self._inventory is not None
+ # Setting self._inventory = None forces the dirstate to regenerate the
+ # working inventory. We do this because self.inventory may be inv, or
+ # may have been modified, and either case would prevent a clean delta
+ # being created.
+ self._inventory = None
+ # generate a delta,
+ delta = inv._make_delta(self.inventory)
+ # and apply it.
+ self.apply_inventory_delta(delta)
+ if had_inventory:
self._inventory = inv
self.flush()
More information about the bazaar-commits
mailing list