You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@subversion.apache.org by pb...@apache.org on 2010/11/11 23:58:50 UTC

svn commit: r1034191 [3/3] - in /subversion/branches/issue-3668-3669: ./ build/ subversion/bindings/javahl/native/ subversion/bindings/javahl/src/org/apache/subversion/javahl/ subversion/include/ subversion/include/private/ subversion/libsvn_client/ su...

Modified: subversion/branches/issue-3668-3669/subversion/tests/cmdline/svntest/main.py
URL: http://svn.apache.org/viewvc/subversion/branches/issue-3668-3669/subversion/tests/cmdline/svntest/main.py?rev=1034191&r1=1034190&r2=1034191&view=diff
==============================================================================
--- subversion/branches/issue-3668-3669/subversion/tests/cmdline/svntest/main.py (original)
+++ subversion/branches/issue-3668-3669/subversion/tests/cmdline/svntest/main.py Thu Nov 11 22:58:49 2010
@@ -74,6 +74,8 @@ from svntest import Skip
 #####################################################################
 # Global stuff
 
+default_num_threads = 5
+
 class SVNProcessTerminatedBySignal(Failure):
   "Exception raised if a spawned process segfaulted, aborted, etc."
   pass
@@ -343,23 +345,22 @@ _safe_arg_re = re.compile(r'^[A-Za-z\d\.
 def _quote_arg(arg):
   """Quote ARG for a command line.
 
-  Simply surround every argument in double-quotes unless it contains
+  Return a quoted version of the string ARG, or just ARG if it contains
   only universally harmless characters.
 
   WARNING: This function cannot handle arbitrary command-line
-  arguments.  It can easily be confused by shell metacharacters.  A
-  perfect job would be difficult and OS-dependent (see, for example,
-  http://msdn.microsoft.com/library/en-us/vccelng/htm/progs_12.asp).
-  In other words, this function is just good enough for what we need
-  here."""
+  arguments: it is just good enough for what we need here."""
 
   arg = str(arg)
   if _safe_arg_re.match(arg):
     return arg
+
+  if windows:
+    # Note: subprocess.list2cmdline is Windows-specific.
+    return subprocess.list2cmdline([arg])
   else:
-    if os.name != 'nt':
-      arg = arg.replace('$', '\$')
-    return '"%s"' % (arg,)
+    # Quoting suitable for most Unix shells.
+    return "'" + arg.replace("'", "'\\''") + "'"
 
 def open_pipe(command, bufsize=0, stdin=None, stdout=None, stderr=None):
   """Opens a subprocess.Popen pipe to COMMAND using STDIN,
@@ -375,15 +376,7 @@ def open_pipe(command, bufsize=0, stdin=
   if (sys.platform == 'win32') and (command[0].endswith('.py')):
     command.insert(0, sys.executable)
 
-  # Quote only the arguments on Windows.  Later versions of subprocess,
-  # 2.5.2+ confirmed, don't require this quoting, but versions < 2.4.3 do.
-  if sys.platform == 'win32':
-    args = command[1:]
-    args = ' '.join([_quote_arg(x) for x in args])
-    command = command[0] + ' ' + args
-    command_string = command
-  else:
-    command_string = ' '.join(command)
+  command_string = command[0] + ' ' + ' '.join(map(_quote_arg, command[1:]))
 
   if not stdin:
     stdin = subprocess.PIPE
@@ -1099,9 +1092,8 @@ class TestSpawningThread(threading.Threa
   """A thread that runs test cases in their own processes.
   Receives test numbers to run from the queue, and saves results into
   the results field."""
-  def __init__(self, srcdir, queue):
+  def __init__(self, queue):
     threading.Thread.__init__(self)
-    self.srcdir = srcdir
     self.queue = queue
     self.results = []
 
@@ -1115,8 +1107,8 @@ class TestSpawningThread(threading.Threa
       self.run_one(next_index)
 
   def run_one(self, index):
-    command = os.path.join(self.srcdir, 'subversion/tests/cmdline',
-                           sys.argv[0])
+    command = os.path.abspath(sys.argv[0])
+
     args = []
     args.append(str(index))
     args.append('-c')
@@ -1297,6 +1289,12 @@ def _internal_run_tests(test_list, testn
   finished_tests = []
   tests_started = 0
 
+  # Some of the tests use sys.argv[0] to locate their test data
+  # directory.  Perhaps we should just be passing srcdir to the tests?
+  if srcdir:
+    sys.argv[0] = os.path.join(srcdir, 'subversion', 'tests', 'cmdline',
+                               sys.argv[0])
+
   if not parallel:
     for i, testnum in enumerate(testnums):
       if run_one_test(testnum, test_list) == 1:
@@ -1309,8 +1307,7 @@ def _internal_run_tests(test_list, testn
     for num in testnums:
       number_queue.put(num)
 
-    threads = [ TestSpawningThread(srcdir, number_queue)
-                for i in range(parallel) ]
+    threads = [ TestSpawningThread(number_queue) for i in range(parallel) ]
     for t in threads:
       t.start()
 
@@ -1362,8 +1359,8 @@ def _create_parser():
                     help='Print binary command-lines (not with --quiet)')
   parser.add_option('-q', '--quiet', action='store_true',
                     help='Print only unexpected results (not with --verbose)')
-  parser.add_option('-p', '--parallel', action='store_const', const=5,
-                    dest='parallel',
+  parser.add_option('-p', '--parallel', action='store_const',
+                    const=default_num_threads, dest='parallel',
                     help='Run the tests in parallel')
   parser.add_option('-c', action='store_true', dest='is_child_process',
                     help='Flag if we are running this python test as a ' +

Modified: subversion/branches/issue-3668-3669/subversion/tests/cmdline/upgrade_tests.py
URL: http://svn.apache.org/viewvc/subversion/branches/issue-3668-3669/subversion/tests/cmdline/upgrade_tests.py?rev=1034191&r1=1034190&r2=1034191&view=diff
==============================================================================
--- subversion/branches/issue-3668-3669/subversion/tests/cmdline/upgrade_tests.py (original)
+++ subversion/branches/issue-3668-3669/subversion/tests/cmdline/upgrade_tests.py Thu Nov 11 22:58:49 2010
@@ -672,6 +672,25 @@ def dirs_only_upgrade(sbox):
       })
   run_and_verify_status_no_server(sbox.wc_dir, expected_status)
 
+
+def upgrade_tree_conflict_data(sbox):
+  "upgrade tree conflict data (f20->f21)"
+
+  sbox.build(create_wc = False)
+  wc_dir = sbox.wc_dir
+  replace_sbox_with_tarfile(sbox, 'upgrade_tc.tar.bz2')
+
+  # Check and see if we can still read our tree conflicts
+  expected_status = svntest.actions.get_virginal_state(wc_dir, 2)
+  expected_status.tweak('A/D/G/pi', status='D ', treeconflict='C')
+  expected_status.tweak('A/D/G/tau', status='! ', treeconflict='C',
+                        wc_rev=None)
+  expected_status.tweak('A/D/G/rho', status='A ', copied='+',
+                        treeconflict='C', wc_rev='-')
+
+  run_and_verify_status_no_server(wc_dir, expected_status)
+
+
 ########################################################################
 # Run the tests
 
@@ -693,6 +712,7 @@ test_list = [ None,
               missing_dirs2,
               XFail(delete_and_keep_local),
               dirs_only_upgrade,
+              upgrade_tree_conflict_data,
              ]
 
 

Modified: subversion/branches/issue-3668-3669/subversion/tests/libsvn_fs_fs/fs-pack-test.c
URL: http://svn.apache.org/viewvc/subversion/branches/issue-3668-3669/subversion/tests/libsvn_fs_fs/fs-pack-test.c?rev=1034191&r1=1034190&r2=1034191&view=diff
==============================================================================
--- subversion/branches/issue-3668-3669/subversion/tests/libsvn_fs_fs/fs-pack-test.c (original)
+++ subversion/branches/issue-3668-3669/subversion/tests/libsvn_fs_fs/fs-pack-test.c Thu Nov 11 22:58:49 2010
@@ -34,16 +34,14 @@
 #include "../svn_test_fs.h"
 
 
-/*-----------------------------------------------------------------*/
 
-/** The actual fs-tests called by `make check` **/
+/*** Helper Functions ***/
 
 /* Write the format number and maximum number of files per directory
-   to a new format file in PATH, overwriting a previously existing file.
+   to a new format file in PATH, overwriting a previously existing
+   file.  Use POOL for temporary allocation.
 
-   Use POOL for temporary allocation.
-
-   This implementation is largely stolen from libsvn_fs_fs/fs_fs.c. */
+   (This implementation is largely stolen from libsvn_fs_fs/fs_fs.c.) */
 static svn_error_t *
 write_format(const char *path,
              int format,
@@ -97,12 +95,15 @@ get_rev_contents(svn_revnum_t rev, apr_p
   return apr_psprintf(pool, "%" APR_INT64_T_FMT "\n", num);
 }
 
-/* Create a packed filesystem in DIR.  Set the shard size to SHARD_SIZE
-   and create MAX_REV number of revisions.  Use POOL for allocations. */
+/* Create a packed filesystem in DIR.  Set the shard size to
+   SHARD_SIZE and create NUM_REVS number of revisions (in addition to
+   r0).  Use POOL for allocations.  After this function successfully
+   completes, the filesystem's youngest revision number will be the
+   same as NUM_REVS.  */
 static svn_error_t *
 create_packed_filesystem(const char *dir,
                          const svn_test_opts_t *opts,
-                         int max_rev,
+                         int num_revs,
                          int shard_size,
                          apr_pool_t *pool)
 {
@@ -133,9 +134,9 @@ create_packed_filesystem(const char *dir
   SVN_ERR(svn_test__create_greek_tree(txn_root, subpool));
   SVN_ERR(svn_fs_commit_txn(&conflict, &after_rev, txn, subpool));
 
-  /* Revisions 2-11: A bunch of random changes. */
+  /* Revisions 2 thru NUM_REVS-1: content tweaks to "iota". */
   iterpool = svn_pool_create(subpool);
-  while (after_rev < max_rev + 1)
+  while (after_rev < num_revs)
     {
       svn_pool_clear(iterpool);
       SVN_ERR(svn_fs_begin_txn(&txn, fs, after_rev, iterpool));
@@ -153,7 +154,10 @@ create_packed_filesystem(const char *dir
   return svn_fs_pack(dir, NULL, NULL, NULL, NULL, pool);
 }
 
-/* Pack a filesystem.  */
+
+/*** Tests ***/
+
+/* ------------------------------------------------------------------------ */
 #define REPO_NAME "test-repo-fsfs-pack"
 #define SHARD_SIZE 7
 #define MAX_REV 53
@@ -181,7 +185,8 @@ pack_filesystem(const svn_test_opts_t *o
   for (i = 0; i < (MAX_REV + 1) / SHARD_SIZE; i++)
     {
       path = svn_path_join_many(pool, REPO_NAME, "revs",
-            apr_psprintf(pool, "%d.pack", i / SHARD_SIZE), "pack", NULL);
+                                apr_psprintf(pool, "%d.pack", i / SHARD_SIZE),
+                                "pack", NULL);
 
       /* These files should exist. */
       SVN_ERR(svn_io_check_path(path, &kind, pool));
@@ -190,7 +195,8 @@ pack_filesystem(const svn_test_opts_t *o
                                  "Expected pack file '%s' not found", path);
 
       path = svn_path_join_many(pool, REPO_NAME, "revs",
-            apr_psprintf(pool, "%d.pack", i / SHARD_SIZE), "manifest", NULL);
+                                apr_psprintf(pool, "%d.pack", i / SHARD_SIZE),
+                                "manifest", NULL);
       SVN_ERR(svn_io_check_path(path, &kind, pool));
       if (kind != svn_node_file)
         return svn_error_createf(SVN_ERR_FS_GENERAL, NULL,
@@ -199,7 +205,8 @@ pack_filesystem(const svn_test_opts_t *o
 
       /* This directory should not exist. */
       path = svn_path_join_many(pool, REPO_NAME, "revs",
-            apr_psprintf(pool, "%d", i / SHARD_SIZE), NULL);
+                                apr_psprintf(pool, "%d", i / SHARD_SIZE),
+                                NULL);
       SVN_ERR(svn_io_check_path(path, &kind, pool));
       if (kind != svn_node_none)
         return svn_error_createf(SVN_ERR_FS_GENERAL, NULL,
@@ -220,12 +227,12 @@ pack_filesystem(const svn_test_opts_t *o
 
   /* Finally, make sure the final revision directory does exist. */
   path = svn_path_join_many(pool, REPO_NAME, "revs",
-        apr_psprintf(pool, "%d", (i / SHARD_SIZE) + 1), NULL);
+                            apr_psprintf(pool, "%d", (i / SHARD_SIZE) + 1),
+                            NULL);
   SVN_ERR(svn_io_check_path(path, &kind, pool));
   if (kind != svn_node_none)
     return svn_error_createf(SVN_ERR_FS_GENERAL, NULL,
-                             "Expected directory '%s' not found",
-                             path);
+                             "Expected directory '%s' not found", path);
 
 
   return SVN_NO_ERROR;
@@ -234,10 +241,10 @@ pack_filesystem(const svn_test_opts_t *o
 #undef SHARD_SIZE
 #undef MAX_REV
 
-/* Pack a filesystem.  */
+/* ------------------------------------------------------------------------ */
 #define REPO_NAME "test-repo-fsfs-pack-even"
 #define SHARD_SIZE 4
-#define MAX_REV 10
+#define MAX_REV 11
 static svn_error_t *
 pack_even_filesystem(const svn_test_opts_t *opts,
                      apr_pool_t *pool)
@@ -265,8 +272,10 @@ pack_even_filesystem(const svn_test_opts
 #undef SHARD_SIZE
 #undef MAX_REV
 
-/* Check reading from a packed filesystem. */
+/* ------------------------------------------------------------------------ */
 #define REPO_NAME "test-repo-read-packed-fs"
+#define SHARD_SIZE 5
+#define MAX_REV 11
 static svn_error_t *
 read_packed_fs(const svn_test_opts_t *opts,
                apr_pool_t *pool)
@@ -281,10 +290,10 @@ read_packed_fs(const svn_test_opts_t *op
       || (opts->server_minor_version && (opts->server_minor_version < 6)))
     return SVN_NO_ERROR;
 
-  SVN_ERR(create_packed_filesystem(REPO_NAME, opts, 11, 5, pool));
+  SVN_ERR(create_packed_filesystem(REPO_NAME, opts, MAX_REV, SHARD_SIZE, pool));
   SVN_ERR(svn_fs_open(&fs, REPO_NAME, NULL, pool));
 
-  for (i = 1; i < 12; i++)
+  for (i = 1; i < (MAX_REV + 1); i++)
     {
       svn_fs_root_t *rev_root;
       svn_stringbuf_t *sb;
@@ -306,9 +315,13 @@ read_packed_fs(const svn_test_opts_t *op
   return SVN_NO_ERROR;
 }
 #undef REPO_NAME
+#undef SHARD_SIZE
+#undef MAX_REV
 
-/* Check reading from a packed filesystem. */
+/* ------------------------------------------------------------------------ */
 #define REPO_NAME "test-repo-commit-packed-fs"
+#define SHARD_SIZE 5
+#define MAX_REV 10
 static svn_error_t *
 commit_packed_fs(const svn_test_opts_t *opts,
                  apr_pool_t *pool)
@@ -325,11 +338,11 @@ commit_packed_fs(const svn_test_opts_t *
     return SVN_NO_ERROR;
 
   /* Create the packed FS and open it. */
-  SVN_ERR(create_packed_filesystem(REPO_NAME, opts, 11, 5, pool));
+  SVN_ERR(create_packed_filesystem(REPO_NAME, opts, MAX_REV, 5, pool));
   SVN_ERR(svn_fs_open(&fs, REPO_NAME, NULL, pool));
 
   /* Now do a commit. */
-  SVN_ERR(svn_fs_begin_txn(&txn, fs, 12, pool));
+  SVN_ERR(svn_fs_begin_txn(&txn, fs, MAX_REV, pool));
   SVN_ERR(svn_fs_txn_root(&txn_root, txn, pool));
   SVN_ERR(svn_test__set_file_contents(txn_root, "iota",
           "How much better is it to get wisdom than gold! and to get "
@@ -339,9 +352,11 @@ commit_packed_fs(const svn_test_opts_t *
   return SVN_NO_ERROR;
 }
 #undef REPO_NAME
+#undef MAX_REV
+#undef SHARD_SIZE
 
-/* Get/set revprop while repository is being packed in background. */
-#define REPO_NAME "test-get-set-revprop-packed-fs"
+/* ------------------------------------------------------------------------ */
+#define REPO_NAME "test-repo-get-set-revprop-packed-fs"
 #define SHARD_SIZE 4
 #define MAX_REV 1
 static svn_error_t *
@@ -367,7 +382,7 @@ get_set_revprop_packed_fs(const svn_test
 
   subpool = svn_pool_create(pool);
   /* Do a commit to trigger packing. */
-  SVN_ERR(svn_fs_begin_txn(&txn, fs, MAX_REV + 1, subpool));
+  SVN_ERR(svn_fs_begin_txn(&txn, fs, MAX_REV, subpool));
   SVN_ERR(svn_fs_txn_root(&txn_root, txn, subpool));
   SVN_ERR(svn_test__set_file_contents(txn_root, "iota", "new-iota",  subpool));
   SVN_ERR(svn_fs_commit_txn(&conflict, &after_rev, txn, subpool));
@@ -377,14 +392,81 @@ get_set_revprop_packed_fs(const svn_test
   SVN_ERR(svn_fs_pack(REPO_NAME, NULL, NULL, NULL, NULL, pool));
 
   /* Try to get revprop for revision 0. */
-  SVN_ERR(svn_fs_revision_prop(&prop_value, fs, 0, SVN_PROP_REVISION_AUTHOR, pool));
+  SVN_ERR(svn_fs_revision_prop(&prop_value, fs, 0, SVN_PROP_REVISION_AUTHOR,
+                               pool));
 
   /* Try to change revprop for revision 0. */
   SVN_ERR(svn_fs_change_rev_prop(fs, 0, SVN_PROP_REVISION_AUTHOR,
-                                 svn_string_create("tweaked-author", pool), pool));
+                                 svn_string_create("tweaked-author", pool),
+                                 pool));
 
   return SVN_NO_ERROR;
 }
+#undef REPO_NAME
+#undef MAX_REV
+#undef SHARD_SIZE
+
+/* ------------------------------------------------------------------------ */
+/* Regression test for issue #3571 (fsfs 'svnadmin recover' expects
+   youngest revprop to be outside revprops.db). */
+#define REPO_NAME "test-repo-recover-fully-packed"
+#define SHARD_SIZE 4
+#define MAX_REV 7
+static svn_error_t *
+recover_fully_packed(const svn_test_opts_t *opts,
+                     apr_pool_t *pool)
+{
+  apr_pool_t *subpool;
+  svn_fs_t *fs;
+  svn_fs_txn_t *txn;
+  svn_fs_root_t *txn_root;
+  const char *conflict;
+  svn_revnum_t after_rev;
+  svn_error_t *err;
+
+  /* Bail (with success) on known-untestable scenarios */
+  if ((strcmp(opts->fs_type, "fsfs") != 0)
+      || (opts->server_minor_version && (opts->server_minor_version < 7)))
+    return SVN_NO_ERROR;
+
+  /* Create a packed FS for which every revision will live in a pack
+     digest file, and then recover it. */
+  SVN_ERR(create_packed_filesystem(REPO_NAME, opts, MAX_REV, SHARD_SIZE, pool));
+  SVN_ERR(svn_fs_recover(REPO_NAME, NULL, NULL, pool));
+
+  /* Add another revision, re-pack, re-recover. */
+  subpool = svn_pool_create(pool);
+  SVN_ERR(svn_fs_open(&fs, REPO_NAME, NULL, subpool));
+  SVN_ERR(svn_fs_begin_txn(&txn, fs, MAX_REV, subpool));
+  SVN_ERR(svn_fs_txn_root(&txn_root, txn, subpool));
+  SVN_ERR(svn_test__set_file_contents(txn_root, "A/mu", "new-mu", subpool));
+  SVN_ERR(svn_fs_commit_txn(&conflict, &after_rev, txn, subpool));
+  svn_pool_destroy(subpool);
+  SVN_ERR(svn_fs_pack(REPO_NAME, NULL, NULL, NULL, NULL, pool));
+  SVN_ERR(svn_fs_recover(REPO_NAME, NULL, NULL, pool));
+
+  /* Now, delete the youngest revprop file, and recover again.  This
+     time we want to see an error! */
+  SVN_ERR(svn_io_remove_file2(
+              svn_dirent_join_many(pool, REPO_NAME, PATH_REVPROPS_DIR,
+                                   apr_psprintf(pool, "%ld/%ld",
+                                                after_rev / SHARD_SIZE,
+                                                after_rev),
+                                   NULL),
+              FALSE, pool));
+  err = svn_fs_recover(REPO_NAME, NULL, NULL, pool);
+  if (! err)
+    return svn_error_create(SVN_ERR_TEST_FAILED, NULL,
+                            "Expected SVN_ERR_FS_CORRUPT error; got none");
+  if (err->apr_err != SVN_ERR_FS_CORRUPT)
+    return svn_error_create(SVN_ERR_TEST_FAILED, err,
+                            "Expected SVN_ERR_FS_CORRUPT error; got:");
+  svn_error_clear(err);
+  return SVN_NO_ERROR;
+}
+#undef REPO_NAME
+#undef MAX_REV
+#undef SHARD_SIZE
 
 /* ------------------------------------------------------------------------ */
 
@@ -403,5 +485,7 @@ struct svn_test_descriptor_t test_funcs[
                        "commit to a packed FSFS filesystem"),
     SVN_TEST_OPTS_PASS(get_set_revprop_packed_fs,
                        "get/set revprop while packing FSFS filesystem"),
+    SVN_TEST_OPTS_PASS(recover_fully_packed,
+                       "recover a fully packed filesystem"),
     SVN_TEST_NULL
   };

Modified: subversion/branches/issue-3668-3669/subversion/tests/libsvn_wc/op-depth-test.c
URL: http://svn.apache.org/viewvc/subversion/branches/issue-3668-3669/subversion/tests/libsvn_wc/op-depth-test.c?rev=1034191&r1=1034190&r2=1034191&view=diff
==============================================================================
--- subversion/branches/issue-3668-3669/subversion/tests/libsvn_wc/op-depth-test.c (original)
+++ subversion/branches/issue-3668-3669/subversion/tests/libsvn_wc/op-depth-test.c Thu Nov 11 22:58:49 2010
@@ -170,11 +170,16 @@ static svn_error_t *
 wc_revert(wc_baton_t *b, const char *path, svn_depth_t depth)
 {
   const char *abspath = wc_path(b, path);
+  const char *lock_root_abspath;
 
-  return svn_wc_revert4(b->wc_ctx, abspath, depth, FALSE, NULL,
-                        NULL, NULL, /* cancel baton + func */
-                        NULL, NULL, /* notify baton + func */
-                        b->pool);
+  SVN_ERR(svn_wc__acquire_write_lock(&lock_root_abspath, b->wc_ctx, abspath,
+                                     TRUE /* lock_anchor */, b->pool, b->pool));
+  SVN_ERR(svn_wc_revert4(b->wc_ctx, abspath, depth, FALSE, NULL,
+                         NULL, NULL, /* cancel baton + func */
+                         NULL, NULL, /* notify baton + func */
+                         b->pool));
+  SVN_ERR(svn_wc__release_write_lock(b->wc_ctx, lock_root_abspath, b->pool));
+  return SVN_NO_ERROR;
 }
 
 static svn_error_t *
@@ -215,6 +220,15 @@ wc_update(wc_baton_t *b, const char *pat
                             TRUE, FALSE, FALSE, ctx, b->pool);
 }
 
+static svn_error_t *
+wc_resolved(wc_baton_t *b, const char *path)
+{
+  svn_client_ctx_t *ctx;
+
+  SVN_ERR(svn_client_create_context(&ctx, b->pool));
+  return svn_client_resolved(wc_path(b, path), TRUE, ctx, b->pool);
+}
+
 /* Create the Greek tree on disk in the WC, and commit it. */
 static svn_error_t *
 add_and_commit_greek_tree(wc_baton_t *b)
@@ -274,6 +288,10 @@ typedef struct nodes_row_t {
     const char *repo_relpath;
 } nodes_row_t;
 
+/* Macro for filling in the REPO_* fields of a non-base NODES_ROW_T
+ * that has no copy-from info. */
+#define NO_COPY_FROM SVN_INVALID_REVNUM, NULL
+
 /* Return a human-readable string representing ROW. */
 static const char *
 print_row(const nodes_row_t *row,
@@ -437,6 +455,17 @@ check_db_rows(wc_baton_t *b,
 /* ---------------------------------------------------------------------- */
 /* The test functions */
 
+/* Definition of a copy sub-test and its expected results. */
+struct copy_subtest_t
+{
+  /* WC-relative or repo-relative source and destination paths. */
+  const char *from_path;
+  const char *to_path;
+  /* All the expected nodes table rows within the destination sub-tree.
+   * Terminated by an all-zero row. */
+  nodes_row_t expected[20];
+};
+
 /* Check that all kinds of WC-to-WC copies give correct op_depth results:
  * create a Greek tree, make copies in it, and check the resulting DB rows. */
 static svn_error_t *
@@ -474,14 +503,7 @@ wc_wc_copies(wc_baton_t *b)
   /* Test copying various things */
 
   {
-#define NO_COPY_FROM SVN_INVALID_REVNUM, NULL
-    struct subtest_t
-      {
-        const char *from_path;
-        const char *to_path;
-        nodes_row_t expected[20];
-      }
-    subtests[] =
+    struct copy_subtest_t subtests[] =
       {
         /* base file */
         { source_base_file, "A/C/copy1", {
@@ -559,7 +581,7 @@ wc_wc_copies(wc_baton_t *b)
 
         { 0 }
       };
-    struct subtest_t *subtest;
+    struct copy_subtest_t *subtest;
 
     /* Fix up the expected->local_relpath fields in the subtest data to be
      * relative to the WC root rather than to the copy destination dir. */
@@ -603,14 +625,7 @@ repo_wc_copies(wc_baton_t *b)
   /* Test copying various things */
 
   {
-#define NO_COPY_FROM SVN_INVALID_REVNUM, NULL
-    struct subtest_t
-      {
-        const char *from_path;
-        const char *to_path;
-        nodes_row_t expected[20];
-      }
-    subtests[] =
+    struct copy_subtest_t subtests[] =
       {
         /* file onto nothing */
         { "iota", "A/C/copy1", {
@@ -666,7 +681,7 @@ repo_wc_copies(wc_baton_t *b)
 
         { 0 }
       };
-    struct subtest_t *subtest;
+    struct copy_subtest_t *subtest;
     svn_client_ctx_t *ctx;
 
     /* Fix up the expected->local_relpath fields in the subtest data to be
@@ -1125,6 +1140,17 @@ test_delete_with_update(const svn_test_o
     };
     SVN_ERR(check_db_rows(&b, "A", rows));
   }
+  SVN_ERR(wc_resolved(&b, ""));
+  SVN_ERR(wc_update(&b, "", 1));
+  {
+    nodes_row_t rows[] = {
+      { 0, "A",       "normal",        1, "A"},
+      { 1, "A",       "normal",        NO_COPY_FROM},
+      { 2, "A/B",     "normal",        NO_COPY_FROM},
+      { 0 }
+    };
+    SVN_ERR(check_db_rows(&b, "A", rows));
+  }
 
   return SVN_NO_ERROR;
 }

Modified: subversion/branches/issue-3668-3669/tools/dev/unix-build/Makefile.svn
URL: http://svn.apache.org/viewvc/subversion/branches/issue-3668-3669/tools/dev/unix-build/Makefile.svn?rev=1034191&r1=1034190&r2=1034191&view=diff
==============================================================================
--- subversion/branches/issue-3668-3669/tools/dev/unix-build/Makefile.svn (original)
+++ subversion/branches/issue-3668-3669/tools/dev/unix-build/Makefile.svn Thu Nov 11 22:58:49 2010
@@ -38,6 +38,7 @@ APR_UTIL_VER	= 1.3.9
 HTTPD_VER	= 2.2.15
 NEON_VER	= 0.29.3
 SERF_VER	= 0.7.x
+SERF_OLD_VER	= 0.6.x
 CYRUS_SASL_VER	= 2.1.23
 SQLITE_VER	= 3.6.23.1
 
@@ -45,7 +46,6 @@ BDB_DIST	= db-$(BDB_VER).tar.gz
 APR_ICONV_DIST	= apr-iconv-$(APR_ICONV_VER).tar.gz
 GNU_ICONV_DIST	= libiconv-$(GNU_ICONV_VER).tar.gz
 NEON_DIST	= neon-$(NEON_VER).tar.gz
-#SERF_DIST	= serf-$(SERF_VER).tar.gz
 SQLITE_DIST	= sqlite-$(SQLITE_VER).tar.gz
 CYRUS_SASL_DIST	= cyrus-sasl-$(CYRUS_SASL_VER).tar.gz
 HTTPD_DIST	= httpd-$(HTTPD_VER).tar.bz2
@@ -70,6 +70,7 @@ HTTPD_URL	= http://archive.apache.org/di
 NEON_URL	= http://webdav.org/neon/$(NEON_DIST)
 #SERF_URL	= http://serf.googlecode.com/files/$(SERF_DIST)
 SERF_URL	= http://serf.googlecode.com/svn/branches/$(SERF_VER)
+SERF_OLD_URL	= http://serf.googlecode.com/svn/branches/$(SERF_OLD_VER)
 SQLITE_URL	= http://www.sqlite.org/$(SQLITE_DIST)
 CYRUS_SASL_URL	= ftp://ftp.andrew.cmu.edu/pub/cyrus-mail/$(CYRUS_SASL_DIST)
 
@@ -81,6 +82,7 @@ APR_UTIL_SRCDIR	= $(SRCDIR)/apr-util-$(A
 HTTPD_SRCDIR	= $(SRCDIR)/httpd-$(HTTPD_VER)
 NEON_SRCDIR	= $(SRCDIR)/neon-$(NEON_VER)
 SERF_SRCDIR	= $(SRCDIR)/serf-$(SERF_VER)
+SERF_OLD_SRCDIR	= $(SRCDIR)/serf-$(SERF_OLD_VER)
 SQLITE_SRCDIR	= $(SRCDIR)/sqlite-$(SQLITE_VER)
 CYRUS_SASL_SRCDIR	= $(SRCDIR)/cyrus-sasl-$(CYRUS_SASL_VER)
 SVN_SRCDIR	= $(SVN_WC)
@@ -93,6 +95,7 @@ APR_UTIL_OBJDIR	= $(OBJDIR)/apr-util-$(A
 HTTPD_OBJDIR	= $(OBJDIR)/httpd-$(HTTPD_VER)
 NEON_OBJDIR	= $(OBJDIR)/neon-$(NEON_VER)
 SERF_OBJDIR	= $(OBJDIR)/serf-$(SERF_VER)
+SERF_OLD_OBJDIR	= $(OBJDIR)/serf-$(SERF_OLD_VER)
 SQLITE_OBJDIR	= $(OBJDIR)/sqlite-$(SQLITE_VER)
 CYRUS_SASL_OBJDIR	= $(OBJDIR)/cyrus-sasl-$(CYRUS_SASL_VER)
 SVN_OBJDIR	= $(OBJDIR)/$(SVN_REL_WC)
@@ -109,8 +112,8 @@ svn_builddir	?=$(SVN_WC)
 .PHONY: all reset clean nuke
 
 all: dirs-create bdb-install apr-install iconv-install apr-util-install \
-	httpd-install neon-install serf-install sqlite-install \
-	cyrus-sasl-install svn-install svn-bindings-install
+	httpd-install neon-install serf-install serf-old-install \
+	sqlite-install cyrus-sasl-install svn-install svn-bindings-install
 
 # Use these to start a build from the beginning.
 reset: dirs-reset bdb-reset apr-reset iconv-reset apr-util-reset \
@@ -623,6 +626,47 @@ $(SERF_OBJDIR)/.installed: $(SERF_OBJDIR
 	touch $@
 
 #######################################################################
+# serf-old (compatible with Subversion 1.5)
+#######################################################################
+
+serf-old-retrieve:	$(SERF_OLD_OBJDIR)/.retrieved
+serf-old-configure:	$(SERF_OLD_OBJDIR)/.configured
+serf-old-compile:	$(SERF_OLD_OBJDIR)/.compiled
+serf-old-install:	$(SERF_OLD_OBJDIR)/.installed
+serf-old-reset:
+	$(foreach f, .retrieved .configured .compiled .installed, \
+		rm -f $(SERF_OLD_OBJDIR)/$(f);)
+
+serf-old-clean:
+	-(cd $(SERF_OLD_SRCDIR) && ./serfmake clean)
+
+# retrieve serf if not present yet
+$(SERF_OLD_OBJDIR)/.retrieved:
+	[ -d $(SERF_OLD_OBJDIR) ] || mkdir -p $(SERF_OLD_OBJDIR)
+	if [ ! -d $(SERF_OLD_SRCDIR) ]; then \
+		svn export $(SERF_OLD_URL) $(SERF_OLD_SRCDIR); \
+	fi
+	touch $@
+
+# compile serf (serf won't compile outside its source tree)
+$(SERF_OLD_OBJDIR)/.compiled: $(SERF_OLD_OBJDIR)/.retrieved
+	cd $(SERF_OLD_SRCDIR) && \
+		env CFLAGS="-O0 -g" ./serfmake --with-apr=$(PREFIX)/apr \
+			--prefix=$(PREFIX)/serf-old \
+			build
+	touch $@
+
+# install serf
+$(SERF_OLD_OBJDIR)/.installed: $(SERF_OLD_OBJDIR)/.compiled
+	cd $(SERF_OLD_SRCDIR) && \
+		./serfmake --with-apr=$(PREFIX)/apr \
+			--with-apr-util=$(PREFIX)/apr \
+			--prefix=$(PREFIX)/serf-old \
+			install
+	touch $@
+
+
+#######################################################################
 # sqlite
 #######################################################################
 
@@ -765,6 +809,7 @@ $(SVN_OBJDIR)/.retrieved:
 
 ifeq ($(BRANCH_MAJOR),1.5)
 BDB_FLAG=$(PREFIX)/bdb
+SERF_FLAG=--with-serf="$(PREFIX)/serf-old"
 else ifeq ($(BRANCH_MAJOR),1.4)
 BDB_FLAG=$(PREFIX)/bdb
 else ifeq ($(BRANCH_MAJOR),1.3)
@@ -777,6 +822,7 @@ else ifeq ($(BRANCH_MAJOR),1.0)
 BDB_FLAG=$(PREFIX)/bdb
 else
 BDB_FLAG=db.h:$(PREFIX)/bdb/include:$(PREFIX)/bdb/lib:db-$(BDB_MAJOR_VER)
+SERF_FLAG=--with-serf="$(PREFIX)/serf"
 endif
 
 ifeq ($(ENABLE_JAVA_BINDINGS),yes)
@@ -807,7 +853,7 @@ $(SVN_OBJDIR)/.configured: $(SVN_OBJDIR)
 			--with-apxs="$(PREFIX)/httpd/bin/apxs" \
 			--with-apache-libexecdir=$(PREFIX)/httpd/modules/svn-$(WC) \
 			--with-neon="$(PREFIX)/neon" \
-			--with-serf="$(PREFIX)/serf" \
+			$(SERF_FLAG) \
 			--with-sqlite="$(PREFIX)/sqlite" \
 			--with-berkeley-db="$(BDB_FLAG)" \
 			--with-sasl="$(PREFIX)/cyrus-sasl" \

Modified: subversion/branches/issue-3668-3669/tools/dist/construct-rolling-environment.sh
URL: http://svn.apache.org/viewvc/subversion/branches/issue-3668-3669/tools/dist/construct-rolling-environment.sh?rev=1034191&r1=1034190&r2=1034191&view=diff
==============================================================================
--- subversion/branches/issue-3668-3669/tools/dist/construct-rolling-environment.sh (original)
+++ subversion/branches/issue-3668-3669/tools/dist/construct-rolling-environment.sh Thu Nov 11 22:58:49 2010
@@ -53,11 +53,11 @@ TEMPDIR=$BASEDIR/temp
 case $LOCATION in
     US)
     APACHE_MIRROR=http://www.pangex.com/pub/apache
-    SOURCEFORGE_MIRROR=http://internap.dl.sourceforge.net/sourceforge
+    SOURCEFORGE_MIRROR=softlayer
     ;;
     UK)
     APACHE_MIRROR=http://apache.rmplc.co.uk
-    SOURCEFORGE_MIRROR=http://kent.dl.sourceforge.net/sourceforge
+    SOURCEFORGE_MIRROR=kent
     ;;
     *)
     echo "Unknown LOCATION" >&2
@@ -77,7 +77,7 @@ setup() {
 create_prefix() {
     wget -nc http://ftp.gnu.org/gnu/autoconf/$AUTOCONF.tar.bz2
     wget -nc http://ftp.gnu.org/gnu/libtool/$LIBTOOL.tar.gz
-    wget -nc $SOURCEFORGE_MIRROR/swig/$SWIG.tar.gz
+    wget -nc "http://sourceforge.net/projects/swig/files/swig/$SWIG/$SWIG.tar.gz/download?use_mirror=$SOURCEFORGE_MIRROR"
 
     tar jxvf $AUTOCONF.tar.bz2
     cd $AUTOCONF