subversion-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From julianf...@apache.org
Subject svn commit: r1634609 [10/11] - in /subversion/branches/move-tracking-2: ./ build/ notes/ subversion/ subversion/include/ subversion/include/private/ subversion/libsvn_client/ subversion/libsvn_delta/ subversion/libsvn_fs/ subversion/libsvn_fs_base/ sub...
Date Mon, 27 Oct 2014 17:28:16 GMT
Modified: subversion/branches/move-tracking-2/subversion/svnmucc/svnmucc.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/svnmucc/svnmucc.c?rev=1634609&r1=1634608&r2=1634609&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/svnmucc/svnmucc.c (original)
+++ subversion/branches/move-tracking-2/subversion/svnmucc/svnmucc.c Mon Oct 27 17:28:13 2014
@@ -251,14 +251,21 @@ sanitize_url(const char *url,
   return svn_uri_canonicalize(url, pool);
 }
 
+static void
+usage(apr_pool_t *pool)
+{
+  svn_error_clear(svn_cmdline_fprintf
+                  (stderr, pool, _("Type 'svnmucc --help' for usage.\n")));
+}
+
 /* Print a usage message on STREAM. */
 static void
-usage(FILE *stream, apr_pool_t *pool)
+help(FILE *stream, apr_pool_t *pool)
 {
   svn_error_clear(svn_cmdline_fputs(
     _("usage: svnmucc ACTION...\n"
       "Subversion multiple URL command client.\n"
-      "Type 'svnmucc --version' to see the program version.\n"
+      "Type 'svnmucc --version' to see the program version and RA modules.\n"
       "\n"
       "  Perform one or more Subversion repository URL-based ACTIONs, committing\n"
       "  the result as a (single) new revision.\n"
@@ -288,9 +295,18 @@ usage(FILE *stream, apr_pool_t *pool)
       "                           prompt only if standard input is a terminal)\n"
       "  --force-interactive    : do interactive prompting even if standard\n"
       "                           input is not a terminal\n"
-      "  --trust-server-cert    : accept SSL server certificates from unknown\n"
-      "                           certificate authorities without prompting (but\n"
-      "                           only with '--non-interactive')\n"
+      "  --trust-server-cert    : deprecated; same as --trust-unknown-ca\n"
+      "  --trust-unknown-ca     : with --non-interactive, accept SSL server\n"
+      "                           certificates from unknown certificate authorities\n"
+      "  --trust-cn-mismatch    : with --non-interactive, accept SSL server\n"
+      "                           certificates even if the server hostname does not\n"
+      "                           match the certificate's common name attribute\n"
+      "  --trust-expired        : with --non-interactive, accept expired SSL server\n"
+      "                           certificates\n"
+      "  --trust-not-yet-valid  : with --non-interactive, accept SSL server\n"
+      "                           certificates from the future\n"
+      "  --trust-other-failure  : with --non-interactive, accept SSL server\n"
+      "                           certificates with failures other than the above\n"
       "  -X [--extra-args] ARG  : append arguments from file ARG (one per line;\n"
       "                           use \"-\" to read from standard input)\n"
       "  --config-dir ARG       : use ARG to override the config directory\n"
@@ -308,7 +324,7 @@ insufficient(void)
 }
 
 static svn_error_t *
-display_version(apr_getopt_t *os, apr_pool_t *pool)
+display_version(apr_pool_t *pool)
 {
   const char *ra_desc_start
     = "The following repository access (RA) modules are available:\n\n";
@@ -317,7 +333,7 @@ display_version(apr_getopt_t *os, apr_po
   version_footer = svn_stringbuf_create(ra_desc_start, pool);
   SVN_ERR(svn_ra_print_modules(version_footer, pool));
 
-  SVN_ERR(svn_opt_print_help4(os, "svnmucc", TRUE, FALSE, FALSE,
+  SVN_ERR(svn_opt_print_help4(NULL, "svnmucc", TRUE, FALSE, FALSE,
                               version_footer->data,
                               NULL, NULL, NULL, NULL, NULL, pool));
 
@@ -455,7 +471,12 @@ sub_main(int *exit_code, int argc, const
     with_revprop_opt,
     non_interactive_opt,
     force_interactive_opt,
-    trust_server_cert_opt
+    trust_server_cert_opt,
+    trust_server_cert_unknown_ca_opt,
+    trust_server_cert_cn_mismatch_opt,
+    trust_server_cert_expired_opt,
+    trust_server_cert_not_yet_valid_opt,
+    trust_server_cert_other_failure_opt,
   };
   static const apr_getopt_option_t options[] = {
     {"message", 'm', 1, ""},
@@ -471,6 +492,11 @@ sub_main(int *exit_code, int argc, const
     {"non-interactive", non_interactive_opt, 0, ""},
     {"force-interactive", force_interactive_opt, 0, ""},
     {"trust-server-cert", trust_server_cert_opt, 0, ""},
+    {"trust-unknown-ca", trust_server_cert_unknown_ca_opt, 0, ""},
+    {"trust-cn-mismatch", trust_server_cert_cn_mismatch_opt, 0, ""},
+    {"trust-expired", trust_server_cert_expired_opt, 0, ""},
+    {"trust-not-yet-valid", trust_server_cert_not_yet_valid_opt, 0, ""},
+    {"trust-other-failure", trust_server_cert_other_failure_opt, 0, ""},
     {"config-dir", config_dir_opt, 1, ""},
     {"config-option",  config_inline_opt, 1, ""},
     {"no-auth-cache",  no_auth_cache_opt, 0, ""},
@@ -485,8 +511,14 @@ sub_main(int *exit_code, int argc, const
   apr_array_header_t *config_options;
   svn_boolean_t non_interactive = FALSE;
   svn_boolean_t force_interactive = FALSE;
-  svn_boolean_t trust_server_cert = FALSE;
+  svn_boolean_t trust_unknown_ca = FALSE;
+  svn_boolean_t trust_cn_mismatch = FALSE;
+  svn_boolean_t trust_expired = FALSE;
+  svn_boolean_t trust_not_yet_valid = FALSE;
+  svn_boolean_t trust_other_failure = FALSE;
   svn_boolean_t no_auth_cache = FALSE;
+  svn_boolean_t show_version = FALSE;
+  svn_boolean_t show_help = FALSE;
   svn_revnum_t base_revision = SVN_INVALID_REVNUM;
   apr_array_header_t *action_args;
   apr_hash_t *revprops = apr_hash_make(pool);
@@ -514,7 +546,11 @@ sub_main(int *exit_code, int argc, const
       if (APR_STATUS_IS_EOF(status))
         break;
       if (status != APR_SUCCESS)
-        return svn_error_wrap_apr(status, "getopt failure");
+        {
+          usage(pool);
+          *exit_code = EXIT_FAILURE;
+          return SVN_NO_ERROR;
+        }
       switch(opt)
         {
         case 'm':
@@ -567,8 +603,21 @@ sub_main(int *exit_code, int argc, const
         case force_interactive_opt:
           force_interactive = TRUE;
           break;
-        case trust_server_cert_opt:
-          trust_server_cert = TRUE;
+        case trust_server_cert_opt: /* backward compat */
+        case trust_server_cert_unknown_ca_opt:
+          trust_unknown_ca = TRUE;
+          break;
+        case trust_server_cert_cn_mismatch_opt:
+          trust_cn_mismatch = TRUE;
+          break;
+        case trust_server_cert_expired_opt:
+          trust_expired = TRUE;
+          break;
+        case trust_server_cert_not_yet_valid_opt:
+          trust_not_yet_valid = TRUE;
+          break;
+        case trust_server_cert_other_failure_opt:
+          trust_other_failure = TRUE;
           break;
         case config_dir_opt:
           SVN_ERR(svn_utf_cstring_to_utf8(&config_dir, arg, pool));
@@ -582,15 +631,27 @@ sub_main(int *exit_code, int argc, const
           no_auth_cache = TRUE;
           break;
         case version_opt:
-          SVN_ERR(display_version(opts, pool));
-          return SVN_NO_ERROR;
+          show_version = TRUE;
+          break;
         case 'h':
         case '?':
-          usage(stdout, pool);
-          return SVN_NO_ERROR;
+          show_help = TRUE;
+          break;
         }
     }
 
+  if (show_help)
+    {
+      help(stdout, pool);
+      return SVN_NO_ERROR;
+    }
+
+  if (show_version)
+    {
+      SVN_ERR(display_version(pool));
+      return SVN_NO_ERROR;
+    }
+
   if (non_interactive && force_interactive)
     {
       return svn_error_create(SVN_ERR_CL_ARG_PARSING_ERROR, NULL,
@@ -601,11 +662,28 @@ sub_main(int *exit_code, int argc, const
     non_interactive = !svn_cmdline__be_interactive(non_interactive,
                                                    force_interactive);
 
-  if (trust_server_cert && !non_interactive)
+  if (!non_interactive)
     {
+      if (trust_unknown_ca)
       return svn_error_create(SVN_ERR_CL_ARG_PARSING_ERROR, NULL,
-                              _("--trust-server-cert requires "
+                              _("--trust-unknown-ca requires "
                                 "--non-interactive"));
+      if (trust_cn_mismatch)
+        return svn_error_create(SVN_ERR_CL_ARG_PARSING_ERROR, NULL,
+                                _("--trust-cn-mismatch requires "
+                                  "--non-interactive"));
+      if (trust_expired)
+        return svn_error_create(SVN_ERR_CL_ARG_PARSING_ERROR, NULL,
+                                _("--trust-expired requires "
+                                  "--non-interactive"));
+      if (trust_not_yet_valid)
+        return svn_error_create(SVN_ERR_CL_ARG_PARSING_ERROR, NULL,
+                                _("--trust-not-yet-valid requires "
+                                  "--non-interactive"));
+      if (trust_other_failure)
+        return svn_error_create(SVN_ERR_CL_ARG_PARSING_ERROR, NULL,
+                                _("--trust-other-failure requires "
+                                  "--non-interactive"));
     }
 
   /* Copy the rest of our command-line arguments to an array,
@@ -663,17 +741,22 @@ sub_main(int *exit_code, int argc, const
   SVN_ERR(svn_client_create_context2(&ctx, cfg_hash, pool));
 
   cfg_config = svn_hash_gets(cfg_hash, SVN_CONFIG_CATEGORY_CONFIG);
-  SVN_ERR(svn_cmdline_create_auth_baton(&ctx->auth_baton,
-                                        non_interactive,
-                                        username,
-                                        password,
-                                        config_dir,
-                                        no_auth_cache,
-                                        trust_server_cert,
-                                        cfg_config,
-                                        ctx->cancel_func,
-                                        ctx->cancel_baton,
-                                        pool));
+  SVN_ERR(svn_cmdline_create_auth_baton2(
+            &ctx->auth_baton,
+            non_interactive,
+            username,
+            password,
+            config_dir,
+            no_auth_cache,
+            trust_unknown_ca,
+            trust_cn_mismatch,
+            trust_expired,
+            trust_not_yet_valid,
+            trust_other_failure,
+            cfg_config,
+            ctx->cancel_func,
+            ctx->cancel_baton,
+            pool));
 
   lmb.non_interactive = non_interactive;
   lmb.ctx = ctx;
@@ -711,7 +794,7 @@ sub_main(int *exit_code, int argc, const
       else if (! strcmp(action_string, "?") || ! strcmp(action_string, "h")
                || ! strcmp(action_string, "help"))
         {
-          usage(stdout, pool);
+          help(stdout, pool);
           return SVN_NO_ERROR;
         }
       else
@@ -872,7 +955,7 @@ sub_main(int *exit_code, int argc, const
   if (! actions->nelts)
     {
       *exit_code = EXIT_FAILURE;
-      usage(stderr, pool);
+      help(stderr, pool);
       return SVN_NO_ERROR;
     }
 

Modified: subversion/branches/move-tracking-2/subversion/svnrdump/svnrdump.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/svnrdump/svnrdump.c?rev=1634609&r1=1634608&r2=1634609&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/svnrdump/svnrdump.c (original)
+++ subversion/branches/move-tracking-2/subversion/svnrdump/svnrdump.c Mon Oct 27 17:28:13 2014
@@ -84,6 +84,11 @@ enum svn_svnrdump__longopt_t
     opt_force_interactive,
     opt_incremental,
     opt_trust_server_cert,
+    opt_trust_server_cert_unknown_ca,
+    opt_trust_server_cert_cn_mismatch,
+    opt_trust_server_cert_expired,
+    opt_trust_server_cert_not_yet_valid,
+    opt_trust_server_cert_other_failure,
     opt_version
   };
 
@@ -93,6 +98,11 @@ enum svn_svnrdump__longopt_t
                                    opt_auth_password, \
                                    opt_auth_nocache, \
                                    opt_trust_server_cert, \
+                                   opt_trust_server_cert_unknown_ca, \
+                                   opt_trust_server_cert_cn_mismatch, \
+                                   opt_trust_server_cert_expired, \
+                                   opt_trust_server_cert_not_yet_valid, \
+                                   opt_trust_server_cert_other_failure, \
                                    opt_non_interactive, \
                                    opt_force_interactive
 
@@ -154,11 +164,29 @@ static const apr_getopt_option_t svnrdum
                          "                             "
                          "    servers:global:http-library=serf")},
     {"trust-server-cert", opt_trust_server_cert, 0,
-                      N_("accept SSL server certificates from unknown\n"
+                      N_("deprecated; same as --trust-unknown-ca")},
+    {"trust-unknown-ca", opt_trust_server_cert_unknown_ca, 0,
+                      N_("with --non-interactive, accept SSL server\n"
                          "                             "
-                         "certificate authorities without prompting (but only\n"
+                         "certificates from unknown certificate authorities")},
+    {"trust-cn-mismatch", opt_trust_server_cert_cn_mismatch, 0,
+                      N_("with --non-interactive, accept SSL server\n"
                          "                             "
-                         "with '--non-interactive')") },
+                         "certificates even if the server hostname does not\n"
+                         "                             "
+                         "match the certificate's common name attribute")},
+    {"trust-expired", opt_trust_server_cert_expired, 0,
+                      N_("with --non-interactive, accept expired SSL server\n"
+                         "                             "
+                         "certificates")},
+    {"trust-not-yet-valid", opt_trust_server_cert_not_yet_valid, 0,
+                      N_("with --non-interactive, accept SSL server\n"
+                         "                             "
+                         "certificates from the future")},
+    {"trust-other-failure", opt_trust_server_cert_other_failure, 0,
+                      N_("with --non-interactive, accept SSL server\n"
+                         "                             "
+                         "certificates with failures other than the above")},
     {0, 0, 0, 0}
   };
 
@@ -352,7 +380,11 @@ init_client_context(svn_client_ctx_t **c
                     const char *config_dir,
                     const char *repos_url,
                     svn_boolean_t no_auth_cache,
-                    svn_boolean_t trust_server_cert,
+                    svn_boolean_t trust_unknown_ca,
+                    svn_boolean_t trust_cn_mismatch,
+                    svn_boolean_t trust_expired,
+                    svn_boolean_t trust_not_yet_valid,
+                    svn_boolean_t trust_other_failure,
                     apr_array_header_t *config_options,
                     apr_pool_t *pool)
 {
@@ -416,11 +448,14 @@ init_client_context(svn_client_ctx_t **c
   ctx->cancel_func = check_cancel;
 
   /* Default authentication providers for non-interactive use */
-  SVN_ERR(svn_cmdline_create_auth_baton(&(ctx->auth_baton), non_interactive,
-                                        username, password, config_dir,
-                                        no_auth_cache, trust_server_cert,
-                                        cfg_config, ctx->cancel_func,
-                                        ctx->cancel_baton, pool));
+  SVN_ERR(svn_cmdline_create_auth_baton2(&(ctx->auth_baton), non_interactive,
+                                         username, password, config_dir,
+                                         no_auth_cache, trust_unknown_ca,
+                                         trust_cn_mismatch, trust_expired,
+                                         trust_not_yet_valid,
+                                         trust_other_failure,
+                                         cfg_config, ctx->cancel_func,
+                                         ctx->cancel_baton, pool));
   *ctx_p = ctx;
   return SVN_NO_ERROR;
 }
@@ -837,7 +872,11 @@ sub_main(int *exit_code, int argc, const
   const char *username = NULL;
   const char *password = NULL;
   svn_boolean_t no_auth_cache = FALSE;
-  svn_boolean_t trust_server_cert = FALSE;
+  svn_boolean_t trust_unknown_ca = FALSE;
+  svn_boolean_t trust_cn_mismatch = FALSE;
+  svn_boolean_t trust_expired = FALSE;
+  svn_boolean_t trust_not_yet_valid = FALSE;
+  svn_boolean_t trust_other_failure = FALSE;
   svn_boolean_t non_interactive = FALSE;
   svn_boolean_t force_interactive = FALSE;
   apr_array_header_t *config_options = NULL;
@@ -959,8 +998,21 @@ sub_main(int *exit_code, int argc, const
           SVN_ERR(svn_utf_cstring_to_utf8(&opt_arg, opt_arg, pool));
           svn_hash_sets(opt_baton->skip_revprops, opt_arg, opt_arg);
           break;
-        case opt_trust_server_cert:
-          trust_server_cert = TRUE;
+        case opt_trust_server_cert: /* backward compat */
+        case opt_trust_server_cert_unknown_ca:
+          trust_unknown_ca = TRUE;
+          break;
+        case opt_trust_server_cert_cn_mismatch:
+          trust_cn_mismatch = TRUE;
+          break;
+        case opt_trust_server_cert_expired:
+          trust_expired = TRUE;
+          break;
+        case opt_trust_server_cert_not_yet_valid:
+          trust_not_yet_valid = TRUE;
+          break;
+        case opt_trust_server_cert_other_failure:
+          trust_other_failure = TRUE;
           break;
         case opt_config_option:
           if (!config_options)
@@ -1076,12 +1128,29 @@ sub_main(int *exit_code, int argc, const
       return SVN_NO_ERROR;
     }
 
-  /* --trust-server-cert can only be used with --non-interactive */
-  if (trust_server_cert && !non_interactive)
+  /* --trust-* can only be used with --non-interactive */
+  if (!non_interactive)
     {
+      if (trust_unknown_ca)
       return svn_error_create(SVN_ERR_CL_ARG_PARSING_ERROR, NULL,
-                              _("--trust-server-cert requires "
+                              _("--trust-unknown-ca requires "
                                 "--non-interactive"));
+      if (trust_cn_mismatch)
+        return svn_error_create(SVN_ERR_CL_ARG_PARSING_ERROR, NULL,
+                                _("--trust-cn-mismatch requires "
+                                  "--non-interactive"));
+      if (trust_expired)
+        return svn_error_create(SVN_ERR_CL_ARG_PARSING_ERROR, NULL,
+                                _("--trust-expired requires "
+                                  "--non-interactive"));
+      if (trust_not_yet_valid)
+        return svn_error_create(SVN_ERR_CL_ARG_PARSING_ERROR, NULL,
+                                _("--trust-not-yet-valid requires "
+                                  "--non-interactive"));
+      if (trust_other_failure)
+        return svn_error_create(SVN_ERR_CL_ARG_PARSING_ERROR, NULL,
+                                _("--trust-other-failure requires "
+                                  "--non-interactive"));
     }
 
   /* Expect one more non-option argument:  the repository URL. */
@@ -1128,7 +1197,11 @@ sub_main(int *exit_code, int argc, const
                               config_dir,
                               opt_baton->url,
                               no_auth_cache,
-                              trust_server_cert,
+                              trust_unknown_ca,
+                              trust_cn_mismatch,
+                              trust_expired,
+                              trust_not_yet_valid,
+                              trust_other_failure,
                               config_options,
                               pool));
 

Modified: subversion/branches/move-tracking-2/subversion/svnsync/svnsync.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/svnsync/svnsync.c?rev=1634609&r1=1634608&r2=1634609&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/svnsync/svnsync.c (original)
+++ subversion/branches/move-tracking-2/subversion/svnsync/svnsync.c Mon Oct 27 17:28:13 2014
@@ -68,6 +68,11 @@ enum svnsync__opt {
   svnsync_opt_disable_locking,
   svnsync_opt_version,
   svnsync_opt_trust_server_cert,
+  svnsync_opt_trust_server_cert_unknown_ca,
+  svnsync_opt_trust_server_cert_cn_mismatch,
+  svnsync_opt_trust_server_cert_expired,
+  svnsync_opt_trust_server_cert_not_yet_valid,
+  svnsync_opt_trust_server_cert_other_failure,
   svnsync_opt_allow_non_empty,
   svnsync_opt_steal_lock
 };
@@ -78,6 +83,11 @@ enum svnsync__opt {
                              svnsync_opt_auth_username, \
                              svnsync_opt_auth_password, \
                              svnsync_opt_trust_server_cert, \
+                             svnsync_opt_trust_server_cert_unknown_ca, \
+                             svnsync_opt_trust_server_cert_cn_mismatch, \
+                             svnsync_opt_trust_server_cert_expired, \
+                             svnsync_opt_trust_server_cert_not_yet_valid, \
+                             svnsync_opt_trust_server_cert_other_failure, \
                              svnsync_opt_source_username, \
                              svnsync_opt_source_password, \
                              svnsync_opt_sync_username, \
@@ -194,11 +204,29 @@ static const apr_getopt_option_t svnsync
                           "                             "
                           "see --source-password and --sync-password)") },
     {"trust-server-cert", svnsync_opt_trust_server_cert, 0,
-                       N_("accept SSL server certificates from unknown\n"
-                          "                             "
-                          "certificate authorities without prompting (but only\n"
-                          "                             "
-                          "with '--non-interactive')") },
+                      N_("deprecated; same as --trust-unknown-ca")},
+    {"trust-unknown-ca", svnsync_opt_trust_server_cert_unknown_ca, 0,
+                      N_("with --non-interactive, accept SSL server\n"
+                         "                             "
+                         "certificates from unknown certificate authorities")},
+    {"trust-cn-mismatch", svnsync_opt_trust_server_cert_cn_mismatch, 0,
+                      N_("with --non-interactive, accept SSL server\n"
+                         "                             "
+                         "certificates even if the server hostname does not\n"
+                         "                             "
+                         "match the certificate's common name attribute")},
+    {"trust-expired", svnsync_opt_trust_server_cert_expired, 0,
+                      N_("with --non-interactive, accept expired SSL server\n"
+                         "                             "
+                         "certificates")},
+    {"trust-not-yet-valid", svnsync_opt_trust_server_cert_not_yet_valid, 0,
+                      N_("with --non-interactive, accept SSL server\n"
+                         "                             "
+                         "certificates from the future")},
+    {"trust-other-failure", svnsync_opt_trust_server_cert_other_failure, 0,
+                      N_("with --non-interactive, accept SSL server\n"
+                         "                             "
+                         "certificates with failures other than the above")},
     {"source-username", svnsync_opt_source_username, 1,
                        N_("connect to source repository with username ARG") },
     {"source-password", svnsync_opt_source_password, 1,
@@ -252,7 +280,11 @@ static const apr_getopt_option_t svnsync
 
 typedef struct opt_baton_t {
   svn_boolean_t non_interactive;
-  svn_boolean_t trust_server_cert;
+  svn_boolean_t trust_server_cert_unknown_ca;
+  svn_boolean_t trust_server_cert_cn_mismatch;
+  svn_boolean_t trust_server_cert_expired;
+  svn_boolean_t trust_server_cert_not_yet_valid;
+  svn_boolean_t trust_server_cert_other_failure;
   svn_boolean_t no_auth_cache;
   svn_auth_baton_t *source_auth_baton;
   svn_auth_baton_t *sync_auth_baton;
@@ -1969,8 +2001,25 @@ sub_main(int *exit_code, int argc, const
             force_interactive = TRUE;
             break;
 
-          case svnsync_opt_trust_server_cert:
-            opt_baton.trust_server_cert = TRUE;
+          case svnsync_opt_trust_server_cert: /* backwards compat */
+          case svnsync_opt_trust_server_cert_unknown_ca:
+            opt_baton.trust_server_cert_unknown_ca = TRUE;
+            break;
+
+          case svnsync_opt_trust_server_cert_cn_mismatch:
+            opt_baton.trust_server_cert_cn_mismatch = TRUE;
+            break;
+
+          case svnsync_opt_trust_server_cert_expired:
+            opt_baton.trust_server_cert_expired = TRUE;
+            break;
+
+          case svnsync_opt_trust_server_cert_not_yet_valid:
+            opt_baton.trust_server_cert_not_yet_valid = TRUE;
+            break;
+
+          case svnsync_opt_trust_server_cert_other_failure:
+            opt_baton.trust_server_cert_other_failure = TRUE;
             break;
 
           case svnsync_opt_no_auth_cache:
@@ -2156,12 +2205,29 @@ sub_main(int *exit_code, int argc, const
                                 "mutually exclusive"));
     }
 
-  /* --trust-server-cert can only be used with --non-interactive */
-  if (opt_baton.trust_server_cert && !opt_baton.non_interactive)
+  /* --trust-* can only be used with --non-interactive */
+  if (!opt_baton.non_interactive)
     {
-      return svn_error_create(SVN_ERR_CL_ARG_PARSING_ERROR, NULL,
-                              _("--trust-server-cert requires "
-                                "--non-interactive"));
+      if (opt_baton.trust_server_cert_unknown_ca)
+        return svn_error_create(SVN_ERR_CL_ARG_PARSING_ERROR, NULL,
+                                _("--trust-unknown-ca requires "
+                                  "--non-interactive"));
+      if (opt_baton.trust_server_cert_cn_mismatch)
+        return svn_error_create(SVN_ERR_CL_ARG_PARSING_ERROR, NULL,
+                                _("--trust-cn-mismatch requires "
+                                  "--non-interactive"));
+      if (opt_baton.trust_server_cert_expired)
+        return svn_error_create(SVN_ERR_CL_ARG_PARSING_ERROR, NULL,
+                                _("--trust-expired requires "
+                                  "--non-interactive"));
+      if (opt_baton.trust_server_cert_not_yet_valid)
+        return svn_error_create(SVN_ERR_CL_ARG_PARSING_ERROR, NULL,
+                                _("--trust-not-yet-valid requires "
+                                  "--non-interactive"));
+      if (opt_baton.trust_server_cert_other_failure)
+        return svn_error_create(SVN_ERR_CL_ARG_PARSING_ERROR, NULL,
+                                _("--trust-other-failure requires "
+                                  "--non-interactive"));
     }
 
   SVN_ERR(svn_config_ensure(opt_baton.config_dir, pool));
@@ -2273,27 +2339,37 @@ sub_main(int *exit_code, int argc, const
   apr_signal(SIGXFSZ, SIG_IGN);
 #endif
 
-  err = svn_cmdline_create_auth_baton(&opt_baton.source_auth_baton,
-                                      opt_baton.non_interactive,
-                                      opt_baton.source_username,
-                                      opt_baton.source_password,
-                                      opt_baton.config_dir,
-                                      opt_baton.no_auth_cache,
-                                      opt_baton.trust_server_cert,
-                                      config,
-                                      check_cancel, NULL,
-                                      pool);
+  err = svn_cmdline_create_auth_baton2(
+          &opt_baton.source_auth_baton,
+          opt_baton.non_interactive,
+          opt_baton.source_username,
+          opt_baton.source_password,
+          opt_baton.config_dir,
+          opt_baton.no_auth_cache,
+          opt_baton.trust_server_cert_unknown_ca,
+          opt_baton.trust_server_cert_cn_mismatch,
+          opt_baton.trust_server_cert_expired,
+          opt_baton.trust_server_cert_not_yet_valid,
+          opt_baton.trust_server_cert_other_failure,
+          config,
+          check_cancel, NULL,
+          pool);
   if (! err)
-    err = svn_cmdline_create_auth_baton(&opt_baton.sync_auth_baton,
-                                        opt_baton.non_interactive,
-                                        opt_baton.sync_username,
-                                        opt_baton.sync_password,
-                                        opt_baton.config_dir,
-                                        opt_baton.no_auth_cache,
-                                        opt_baton.trust_server_cert,
-                                        config,
-                                        check_cancel, NULL,
-                                        pool);
+    err = svn_cmdline_create_auth_baton2(
+            &opt_baton.sync_auth_baton,
+            opt_baton.non_interactive,
+            opt_baton.sync_username,
+            opt_baton.sync_password,
+            opt_baton.config_dir,
+            opt_baton.no_auth_cache,
+            opt_baton.trust_server_cert_unknown_ca,
+            opt_baton.trust_server_cert_cn_mismatch,
+            opt_baton.trust_server_cert_expired,
+            opt_baton.trust_server_cert_not_yet_valid,
+            opt_baton.trust_server_cert_other_failure,
+            config,
+            check_cancel, NULL,
+            pool);
   if (! err)
     err = (*subcommand->cmd_func)(os, &opt_baton, pool);
   if (err)

Modified: subversion/branches/move-tracking-2/subversion/tests/cmdline/basic_tests.py
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/tests/cmdline/basic_tests.py?rev=1634609&r1=1634608&r2=1634609&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/tests/cmdline/basic_tests.py (original)
+++ subversion/branches/move-tracking-2/subversion/tests/cmdline/basic_tests.py Mon Oct 27 17:28:13 2014
@@ -2003,7 +2003,6 @@ def delete_keep_local_twice(sbox):
     logger.warn('Directory was really deleted')
     raise svntest.Failure
 
-@Wimp("Fails with recent httpd", cond_func=svntest.main.is_ra_type_dav)
 def special_paths_in_repos(sbox):
   "use folders with names like 'c:hi'"
 
@@ -2011,16 +2010,21 @@ def special_paths_in_repos(sbox):
   test_file_source = os.path.join(sbox.repo_dir, 'format')
   repo_url       = sbox.repo_url
 
-  for test_url in [ sbox.repo_url + '/c:hi',
-                    sbox.repo_url + '/C:',
-                    sbox.repo_url + '/C&',
-                    sbox.repo_url + '/C<',
-                    sbox.repo_url + '/C# hi',
-                    sbox.repo_url + '/C\\ri',
-                    sbox.repo_url + '/C?',
-                    sbox.repo_url + '/C+',
-                    sbox.repo_url + '/C%']:
+  test_urls = [ sbox.repo_url + '/c:hi',
+                sbox.repo_url + '/C:',
+                sbox.repo_url + '/C&',
+                sbox.repo_url + '/C<',
+                sbox.repo_url + '/C# hi',
+                sbox.repo_url + '/C?',
+                sbox.repo_url + '/C+',
+                sbox.repo_url + '/C%']
+
+  # On Windows Apache HTTPD breaks '\' for us :(
+  if not (svntest.main.is_os_windows() and
+          svntest.main.is_ra_type_dav()):
+    test_urls += [ sbox.repo_url + '/C\\ri' ]
 
+  for test_url in test_urls:
     test_file_url = test_url + '/' + test_url[test_url.rindex('/')+1:]
 
     # do some manipulations on a folder which problematic names

Modified: subversion/branches/move-tracking-2/subversion/tests/cmdline/externals_tests.py
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/tests/cmdline/externals_tests.py?rev=1634609&r1=1634608&r2=1634609&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/tests/cmdline/externals_tests.py (original)
+++ subversion/branches/move-tracking-2/subversion/tests/cmdline/externals_tests.py Mon Oct 27 17:28:13 2014
@@ -2795,23 +2795,26 @@ def include_immediate_dir_externals(sbox
 
 
 @Issue(4085)
-@XFail()
 def shadowing(sbox):
   "external shadows an existing dir"
 
-  sbox.build(read_only=True)
+  sbox.build()
   wc_dir = sbox.wc_dir
 
   # Setup external: /A/B/F as 'C' child of /A
   externals_prop = "^/A/B/F C\n"
+  change_external(sbox.ospath('A'), externals_prop, commit=False)
+
+  # An update errors out because the external is shadowed by an existing dir
+  svntest.main.run_svn("W205011: Error handling externals definition for '%s'"
+    % (sbox.wc_dir) + "/A/C", 'update', wc_dir)
+
+  # Remove the shadowed directory to unblock the external
+  svntest.main.run_svn(None, 'rm', sbox.repo_url + '/A/C', '-m', 'remove A/C')
+
+  # The next update should fetch the external and not error out
+  sbox.simple_update()
 
-  raised = False
-  try:
-    change_external(sbox.ospath('A'), externals_prop, commit=False)
-  except:
-    raised = True
-  if not raised:
-    raise svntest.Failure("Creating conflicting child 'C' of 'A' didn't error")
 
 # Test for issue #4093 'remapping a file external can segfault due to
 # "deleted" props'.
@@ -3228,7 +3231,6 @@ def update_dir_external_shallow(sbox):
                                         sbox.ospath('A/B/E'))
 
 @Issue(4411)
-@XFail()
 def switch_parent_relative_file_external(sbox):
   "switch parent-relative file external"
 
@@ -3444,6 +3446,41 @@ def update_deletes_file_external(sbox):
   sbox.simple_update()
   
 
+@Issue(4519)
+def switch_relative_externals(sbox):
+  "switch relative externals"
+
+  sbox.build(create_wc=False)
+
+  svntest.actions.run_and_verify_svnmucc(None, None, [],
+                                         '-U', sbox.repo_url, '-m', 'Q',
+                                         'mkdir', 'branches',
+                                         'cp', '1', 'A', 'trunk',
+                                         'cp', '1', 'A', 'branches/A',
+                                         'propset', 'svn:externals',
+                                            '../C dirExC\n ../mu fileExMu',
+                                            'trunk/B',
+                                         'propset', 'svn:externals',
+                                            '../C dirExC\n ../mu fileExMu',
+                                            'branches/A/B')
+
+  wc = sbox.add_wc_path('wc')
+
+  svntest.actions.run_and_verify_svn(None, None, [],
+                                     'co', sbox.repo_url + '/trunk', wc)
+
+  # This forgets to update some externals data
+  svntest.actions.run_and_verify_svn(None, None, [],
+                                     'switch', sbox.repo_url + '/branches/A', wc)
+
+  # This upgrade makes the following update fail
+  svntest.actions.run_and_verify_svn(None, None, [],
+                                     'upgrade', wc)
+
+  svntest.actions.run_and_verify_svn(None, None, [],
+                                     'up', wc)
+
+
 ########################################################################
 # Run the tests
 
@@ -3500,7 +3537,8 @@ test_list = [ None,
               file_external_unversioned_obstruction,
               file_external_versioned_obstruction,
               update_external_peg_rev,
-              update_deletes_file_external
+              update_deletes_file_external,
+              switch_relative_externals,
              ]
 
 if __name__ == '__main__':

Modified: subversion/branches/move-tracking-2/subversion/tests/cmdline/getopt_tests_data/svn_help_log_switch_stdout
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/tests/cmdline/getopt_tests_data/svn_help_log_switch_stdout?rev=1634609&r1=1634608&r2=1634609&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/tests/cmdline/getopt_tests_data/svn_help_log_switch_stdout (original)
+++ subversion/branches/move-tracking-2/subversion/tests/cmdline/getopt_tests_data/svn_help_log_switch_stdout Mon Oct 27 17:28:13 2014
@@ -122,9 +122,18 @@ Global options:
                              only if standard input is a terminal device)
   --force-interactive      : do interactive prompting even if standard input
                              is not a terminal device
-  --trust-server-cert      : accept SSL server certificates from unknown
-                             certificate authorities without prompting (but only
-                             with '--non-interactive')
+  --trust-server-cert      : deprecated; same as --trust-unknown-ca
+  --trust-unknown-ca       : with --non-interactive, accept SSL server
+                             certificates from unknown certificate authorities
+  --trust-cn-mismatch      : with --non-interactive, accept SSL server
+                             certificates even if the server hostname does not
+                             match the certificate's common name attribute
+  --trust-expired          : with --non-interactive, accept expired SSL server
+                             certificates
+  --trust-not-yet-valid    : with --non-interactive, accept SSL server
+                             certificates from the future
+  --trust-other-failure    : with --non-interactive, accept SSL server
+                             certificates with failures other than the above
   --config-dir ARG         : read user configuration files from directory ARG
   --config-option ARG      : set user configuration option in the format:
                                  FILE:SECTION:OPTION=[VALUE]
@@ -206,9 +215,18 @@ Global options:
                              only if standard input is a terminal device)
   --force-interactive      : do interactive prompting even if standard input
                              is not a terminal device
-  --trust-server-cert      : accept SSL server certificates from unknown
-                             certificate authorities without prompting (but only
-                             with '--non-interactive')
+  --trust-server-cert      : deprecated; same as --trust-unknown-ca
+  --trust-unknown-ca       : with --non-interactive, accept SSL server
+                             certificates from unknown certificate authorities
+  --trust-cn-mismatch      : with --non-interactive, accept SSL server
+                             certificates even if the server hostname does not
+                             match the certificate's common name attribute
+  --trust-expired          : with --non-interactive, accept expired SSL server
+                             certificates
+  --trust-not-yet-valid    : with --non-interactive, accept SSL server
+                             certificates from the future
+  --trust-other-failure    : with --non-interactive, accept SSL server
+                             certificates with failures other than the above
   --config-dir ARG         : read user configuration files from directory ARG
   --config-option ARG      : set user configuration option in the format:
                                  FILE:SECTION:OPTION=[VALUE]

Modified: subversion/branches/move-tracking-2/subversion/tests/cmdline/lock_tests.py
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/tests/cmdline/lock_tests.py?rev=1634609&r1=1634608&r2=1634609&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/tests/cmdline/lock_tests.py (original)
+++ subversion/branches/move-tracking-2/subversion/tests/cmdline/lock_tests.py Mon Oct 27 17:28:13 2014
@@ -1964,7 +1964,6 @@ def lock_hook_messages(sbox):
                                            expected_err, actual_stderr)
 
 
-@XFail(svntest.main.is_ra_type_dav)
 def failing_post_hooks(sbox):
   "locking with failing post-lock and post-unlock"
 
@@ -1978,20 +1977,25 @@ def failing_post_hooks(sbox):
   pi_path = sbox.ospath('A/D/G/pi')
   expected_status = svntest.actions.get_virginal_state(wc_dir, 1)
   expected_status.tweak('A/D/G/pi', writelocked='K')
-  expected_fail_err_re = ".*error text"
-  
+
+  if svntest.main.is_ra_type_dav():
+    expected_lock_err = []
+    expected_unlock_err = '.*svn: E165009: Unlock succeeded.*' #
+  else:
+    expected_unlock_err = expected_lock_err = ".*error text"
+
   # Failing post-lock doesn't stop lock being created.
-  svntest.actions.run_and_verify_svn2(None, "'pi' locked by user",
-                                      expected_fail_err_re, 1,
-                                      'lock', '-m', '', pi_path)
+  svntest.actions.run_and_verify_svn(None, "'pi' locked by user",
+                                     expected_lock_err,
+                                     'lock', '-m', '', pi_path)
   svntest.actions.run_and_verify_status(wc_dir, expected_status)
 
   expected_status.tweak('A/D/G/pi', writelocked=None)
 
   # Failing post-unlock doesn't stop lock being removed.
-  svntest.actions.run_and_verify_svn2(None, "'pi' unlocked",
-                                      expected_fail_err_re, 1,
-                                      'unlock', pi_path)
+  svntest.actions.run_and_verify_svn(None, "'pi' unlocked",
+                                     expected_unlock_err,
+                                     'unlock', pi_path)
   svntest.actions.run_and_verify_status(wc_dir, expected_status)
 
 @XFail()

Modified: subversion/branches/move-tracking-2/subversion/tests/cmdline/svnadmin_tests.py
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/tests/cmdline/svnadmin_tests.py?rev=1634609&r1=1634608&r2=1634609&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/tests/cmdline/svnadmin_tests.py (original)
+++ subversion/branches/move-tracking-2/subversion/tests/cmdline/svnadmin_tests.py Mon Oct 27 17:28:13 2014
@@ -86,12 +86,6 @@ def check_hotcopy_fsfs_fsx(src, dst):
                                 "source" % src_dirent)
       # Compare all files in this directory
       for src_file in src_files:
-        # Exclude temporary files
-        if src_file == 'rev-prop-atomics.shm':
-          continue
-        if src_file == 'rev-prop-atomics.mutex':
-          continue
-
         # Ignore auto-created empty lock files as they may or may not
         # be present and are neither required by nor do they harm to
         # the destination repository.
@@ -392,7 +386,9 @@ def set_changed_path_list(sbox, revision
     footer_length = ord(contents[length-1]);
     footer = contents[length - footer_length - 1:length-1]
     l2p_offset = long(footer.split(' ')[0])
-    p2l_offset = long(footer.split(' ')[1])
+    l2p_checksum = footer.split(' ')[1]
+    p2l_offset = long(footer.split(' ')[2])
+    p2l_checksum = footer.split(' ')[3]
 
     idx = FSFS_Index(sbox, revision)
     (offset, item_len, item_type) = idx.get_item(1)
@@ -405,7 +401,8 @@ def set_changed_path_list(sbox, revision
     file_len = body_len + len(changes) + 1
     p2l_offset += file_len - l2p_offset
 
-    header = str(file_len) + ' ' + str(p2l_offset)
+    header = str(file_len) + ' ' + l2p_checksum + ' ' \
+           + str(p2l_offset) + ' ' + p2l_checksum
     header += chr(len(header))
     header = '\n' + indexes + header
 
@@ -2928,6 +2925,20 @@ def freeze_same_uuid(sbox):
                                           sys.executable, '-c', 'True')
 
 
+@Skip(svntest.main.is_fs_type_fsx)
+def upgrade(sbox):
+  "upgrade --compatible-version=1.3"
+
+  sbox.build(create_wc=False, minor_version=3)
+  svntest.actions.run_and_verify_svnadmin(None, None, [], "upgrade",
+                                          sbox.repo_dir)
+  # Does the repository work after upgrade?
+  svntest.actions.run_and_verify_svn(None, ['Committing transaction...\n',
+                                     'Committed revision 2.\n'], [], 'mkdir',
+                                     '-m', svntest.main.make_log_msg(),
+                                     sbox.repo_url + '/dir')
+
+
 ########################################################################
 # Run the tests
 
@@ -2980,6 +2991,7 @@ test_list = [ None,
               fsfs_hotcopy_progress_with_revprop_changes,
               fsfs_hotcopy_progress_old,
               freeze_same_uuid,
+              upgrade,
              ]
 
 if __name__ == '__main__':

Modified: subversion/branches/move-tracking-2/subversion/tests/cmdline/switch_tests.py
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/tests/cmdline/switch_tests.py?rev=1634609&r1=1634608&r2=1634609&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/tests/cmdline/switch_tests.py (original)
+++ subversion/branches/move-tracking-2/subversion/tests/cmdline/switch_tests.py Mon Oct 27 17:28:13 2014
@@ -2860,6 +2860,49 @@ def switch_keywords(sbox):
                                         None, expected_disk, expected_status,
                                         None, None, None, None, None)
 
+@Issue(4524)
+def switch_moves(sbox):
+  "switch moves on wc checkpoint"
+
+  sbox.build()
+
+  sbox.simple_move('A/B', 'B')
+  sbox.simple_rm('A')
+
+  branch_url = sbox.repo_url + '/branch'
+
+  svntest.actions.run_and_verify_svn(None, None, [],
+                                     'cp', sbox.wc_dir, branch_url,
+                                     '-m', '')
+
+  expected_disk = svntest.wc.State('', {
+    'B/E/alpha' : Item(contents="This is the file 'alpha'.\n"),
+    'B/E/beta'  : Item(contents="This is the file 'beta'.\n"),
+    'B/lambda'  : Item(contents="This is the file 'lambda'.\n"),
+    'B/F'       : Item(),
+    'iota'      : Item(contents="This is the file 'iota'.\n"),
+  })
+
+  expected_status = svntest.wc.State(sbox.wc_dir, {
+    ''          : Item(status='  ', wc_rev='2'),
+    'B'         : Item(status='R ', copied='+', treeconflict='C', wc_rev='-'),
+    'B/lambda'  : Item(status='  ', copied='+', wc_rev='-'),
+    'B/F'       : Item(status='  ', copied='+', wc_rev='-'),
+    'B/E'       : Item(status='  ', copied='+', wc_rev='-'),
+    'B/E/beta'  : Item(status='  ', copied='+', wc_rev='-'),
+    'B/E/alpha' : Item(status='  ', copied='+', wc_rev='-'),
+    'A'         : Item(status='! ', treeconflict='C'),
+    'iota'      : Item(status='  ', wc_rev='2'),
+  })
+
+  # In Subversion 1.8 this scenario causes an Sqlite row not found error.
+  # It would be nice if we could handle the tree conflict more intelligent, as
+  # the working copy matches the incomming change.
+  svntest.actions.run_and_verify_switch(sbox.wc_dir, sbox.ospath(''), branch_url,
+                                        None, expected_disk, expected_status,
+                                        None, None, None, None, None)
+
+
 ########################################################################
 # Run the tests
 
@@ -2903,6 +2946,7 @@ test_list = [ None,
               switch_to_spaces,
               switch_across_replacement,
               switch_keywords,
+              switch_moves,
               ]
 
 if __name__ == '__main__':

Modified: subversion/branches/move-tracking-2/subversion/tests/libsvn_fs/fs-test.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/tests/libsvn_fs/fs-test.c?rev=1634609&r1=1634608&r2=1634609&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/tests/libsvn_fs/fs-test.c (original)
+++ subversion/branches/move-tracking-2/subversion/tests/libsvn_fs/fs-test.c Mon Oct 27 17:28:13 2014
@@ -41,6 +41,7 @@
 #include "svn_private_config.h"
 #include "private/svn_fs_util.h"
 #include "private/svn_fs_private.h"
+#include "private/svn_fspath.h"
 
 #include "../svn_test_fs.h"
 
@@ -207,24 +208,35 @@ reopen_trivial_transaction(const svn_tes
 {
   svn_fs_t *fs;
   svn_fs_txn_t *txn;
+  svn_fs_root_t *root;
   const char *txn_name;
   apr_pool_t *subpool = svn_pool_create(pool);
 
   SVN_ERR(svn_test__create_fs(&fs, "test-repo-reopen-trivial-txn",
                               opts, pool));
 
-  /* Begin a new transaction that is based on revision 0.  */
+  /* Create a first transaction - we don't want that one to reopen. */
+  SVN_ERR(svn_fs_begin_txn(&txn, fs, 0, subpool));
+
+  /* Begin a second transaction that is based on revision 0.  */
   SVN_ERR(svn_fs_begin_txn(&txn, fs, 0, subpool));
 
   /* Don't use the subpool, txn_name must persist beyond the current txn */
   SVN_ERR(svn_fs_txn_name(&txn_name, txn, pool));
 
+  /* Create a third transaction - we don't want that one to reopen. */
+  SVN_ERR(svn_fs_begin_txn(&txn, fs, 0, subpool));
+
   /* Close the transaction. */
   svn_pool_clear(subpool);
 
   /* Reopen the transaction by name */
   SVN_ERR(svn_fs_open_txn(&txn, fs, txn_name, subpool));
 
+  /* Does it have the same name? */
+  SVN_ERR(svn_fs_txn_root(&root, txn, subpool));
+  SVN_TEST_STRING_ASSERT(svn_fs_txn_root_name(root, subpool), txn_name);
+
   /* Close the transaction ... again. */
   svn_pool_destroy(subpool);
 
@@ -1126,6 +1138,8 @@ basic_commit(const svn_test_opts_t *opts
 
   /* Create the greek tree. */
   SVN_ERR(svn_test__create_greek_tree(txn_root, pool));
+  SVN_TEST_ASSERT(svn_fs_is_txn_root(txn_root));
+  SVN_TEST_ASSERT(!svn_fs_is_revision_root(txn_root));
 
   /* Commit it. */
   SVN_ERR(svn_fs_commit_txn(&conflict, &after_rev, txn, pool));
@@ -1139,6 +1153,8 @@ basic_commit(const svn_test_opts_t *opts
 
   /* Get root of the revision */
   SVN_ERR(svn_fs_revision_root(&revision_root, fs, after_rev, pool));
+  SVN_TEST_ASSERT(!svn_fs_is_txn_root(revision_root));
+  SVN_TEST_ASSERT(svn_fs_is_revision_root(revision_root));
 
   /* Check the tree. */
   SVN_ERR(svn_test__check_greek_tree(revision_root, pool));
@@ -4171,6 +4187,12 @@ check_related(const svn_test_opts_t *opt
       { "E", 7 }, { "E", 8 }, { "F", 9 }, { "F", 10 }
     };
 
+    /* Latest revision that touched the respective path. */
+    struct path_rev_t latest_changes[6] = {
+      { "A", 4 }, { "B", 6 }, { "C", 6 },
+      { "D", 7 }, { "E", 8 }, { "F", 10 }
+    };
+
     int related_matrix[16][16] = {
       /* A1 ... F10 across the top here*/
       { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0 }, /* A1 */
@@ -4200,14 +4222,16 @@ check_related(const svn_test_opts_t *opt
             struct path_rev_t pr2 = path_revs[j];
             const svn_fs_id_t *id1, *id2;
             int related = 0;
+            svn_fs_node_relation_t relation;
+            svn_fs_root_t *rev_root1, *rev_root2;
 
             /* Get the ID for the first path/revision combination. */
-            SVN_ERR(svn_fs_revision_root(&rev_root, fs, pr1.rev, subpool));
-            SVN_ERR(svn_fs_node_id(&id1, rev_root, pr1.path, subpool));
+            SVN_ERR(svn_fs_revision_root(&rev_root1, fs, pr1.rev, subpool));
+            SVN_ERR(svn_fs_node_id(&id1, rev_root1, pr1.path, subpool));
 
             /* Get the ID for the second path/revision combination. */
-            SVN_ERR(svn_fs_revision_root(&rev_root, fs, pr2.rev, subpool));
-            SVN_ERR(svn_fs_node_id(&id2, rev_root, pr2.path, subpool));
+            SVN_ERR(svn_fs_revision_root(&rev_root2, fs, pr2.rev, subpool));
+            SVN_ERR(svn_fs_node_id(&id2, rev_root2, pr2.path, subpool));
 
             /* <exciting> Now, run the relationship check! </exciting> */
             related = svn_fs_check_related(id1, id2) ? 1 : 0;
@@ -4230,9 +4254,74 @@ check_related(const svn_test_opts_t *opt
                    pr1.path, (int)pr1.rev, pr2.path, (int)pr2.rev);
               }
 
+            /* Asking directly, i.e. without involving the noderev IDs as
+             * an intermediate, should yield the same results. */
+            SVN_ERR(svn_fs_node_relation(&relation, rev_root1, pr1.path,
+                                         rev_root2, pr2.path, subpool));
+            if (i == j)
+              {
+                /* Identical note. */
+                if (!related || relation != svn_fs_node_same)
+                  {
+                    return svn_error_createf
+                      (SVN_ERR_TEST_FAILED, NULL,
+                      "expected '%s:%d' to be the same as '%s:%d';"
+                      " it was not",
+                      pr1.path, (int)pr1.rev, pr2.path, (int)pr2.rev);
+                  }
+              }
+            else if (related && relation != svn_fs_node_common_ancestor)
+              {
+                return svn_error_createf
+                  (SVN_ERR_TEST_FAILED, NULL,
+                   "expected '%s:%d' to have a common ancestor with '%s:%d';"
+                   " it had not",
+                   pr1.path, (int)pr1.rev, pr2.path, (int)pr2.rev);
+              }
+            else if (!related && relation != svn_fs_node_unrelated)
+              {
+                return svn_error_createf
+                  (SVN_ERR_TEST_FAILED, NULL,
+                   "expected '%s:%d' to not be related to '%s:%d'; it was",
+                   pr1.path, (int)pr1.rev, pr2.path, (int)pr2.rev);
+              }
+
             svn_pool_clear(subpool);
           } /* for ... */
       } /* for ... */
+
+    /* Verify that the noderevs stay the same after their last change. */
+    for (i = 0; i < 6; ++i)
+      {
+        const char *path = latest_changes[i].path;
+        svn_revnum_t latest = latest_changes[i].rev;
+        svn_fs_root_t *latest_root;
+        svn_revnum_t rev;
+        svn_fs_node_relation_t relation;
+
+        /* FS root of the latest change. */
+        svn_pool_clear(subpool);
+        SVN_ERR(svn_fs_revision_root(&latest_root, fs, latest, subpool));
+
+        /* All future revisions. */
+        for (rev = latest + 1; rev <= 10; ++rev)
+          {
+            /* Query their noderev relationship to the latest change. */
+            SVN_ERR(svn_fs_revision_root(&rev_root, fs, rev, subpool));
+            SVN_ERR(svn_fs_node_relation(&relation, latest_root, path,
+                                         rev_root, path, subpool));
+
+            /* They shall use the same noderevs */
+            if (relation != svn_fs_node_same)
+              {
+                return svn_error_createf
+                  (SVN_ERR_TEST_FAILED, NULL,
+                  "expected '%s:%d' to be the same as '%s:%d';"
+                  " it was not",
+                  path, (int)latest, path, (int)rev);
+              }
+          } /* for ... */
+      } /* for ... */
   }
 
   /* Destroy the subpool. */
@@ -4320,22 +4409,49 @@ branch_test(const svn_test_opts_t *opts,
 }
 
 
+/* Verify that file FILENAME under ROOT has the same contents checksum
+ * as CONTENTS when comparing the checksums of the given TYPE.
+ * Use POOL for temporary allocations. */
+static svn_error_t *
+verify_file_checksum(svn_stringbuf_t *contents,
+                     svn_fs_root_t *root,
+                     const char *filename,
+                     svn_checksum_kind_t type,
+                     apr_pool_t *pool)
+{
+  svn_checksum_t *expected_checksum, *actual_checksum;
+
+  /* Write a file, compare the repository's idea of its checksum
+     against our idea of its checksum.  They should be the same. */
+  SVN_ERR(svn_checksum(&expected_checksum, type, contents->data,
+                       contents->len, pool));
+  SVN_ERR(svn_fs_file_checksum(&actual_checksum, type, root, filename, TRUE,
+                               pool));
+  if (!svn_checksum_match(expected_checksum, actual_checksum))
+    return svn_error_createf
+      (SVN_ERR_FS_GENERAL, NULL,
+       "verify-checksum: checksum mismatch:\n"
+       "   expected:  %s\n"
+       "     actual:  %s\n",
+       svn_checksum_to_cstring(expected_checksum, pool),
+       svn_checksum_to_cstring(actual_checksum, pool));
+
+  return SVN_NO_ERROR;
+}
+
 static svn_error_t *
 verify_checksum(const svn_test_opts_t *opts,
                 apr_pool_t *pool)
 {
   svn_fs_t *fs;
   svn_fs_txn_t *txn;
-  svn_fs_root_t *txn_root;
+  svn_fs_root_t *txn_root, *rev_root;
   svn_stringbuf_t *str;
-  svn_checksum_t *expected_checksum, *actual_checksum;
+  svn_revnum_t rev;
 
   /* Write a file, compare the repository's idea of its checksum
      against our idea of its checksum.  They should be the same. */
-
   str = svn_stringbuf_create("My text editor charges me rent.", pool);
-  SVN_ERR(svn_checksum(&expected_checksum, svn_checksum_md5, str->data,
-                       str->len, pool));
 
   SVN_ERR(svn_test__create_fs(&fs, "test-repo-verify-checksum",
                               opts, pool));
@@ -4343,17 +4459,20 @@ verify_checksum(const svn_test_opts_t *o
   SVN_ERR(svn_fs_txn_root(&txn_root, txn, pool));
   SVN_ERR(svn_fs_make_file(txn_root, "fact", pool));
   SVN_ERR(svn_test__set_file_contents(txn_root, "fact", str->data, pool));
-  SVN_ERR(svn_fs_file_checksum(&actual_checksum, svn_checksum_md5, txn_root,
-                               "fact", TRUE, pool));
 
-  if (!svn_checksum_match(expected_checksum, actual_checksum))
-    return svn_error_createf
-      (SVN_ERR_FS_GENERAL, NULL,
-       "verify-checksum: checksum mismatch:\n"
-       "   expected:  %s\n"
-       "     actual:  %s\n",
-       svn_checksum_to_cstring(expected_checksum, pool),
-       svn_checksum_to_cstring(actual_checksum, pool));
+  /* Do it for the txn. */
+  SVN_ERR(verify_file_checksum(str, txn_root, "fact", svn_checksum_md5,
+                               pool));
+  SVN_ERR(verify_file_checksum(str, txn_root, "fact", svn_checksum_sha1,
+                               pool));
+
+  /* Do it again - this time for the revision. */
+  SVN_ERR(svn_fs_commit_txn(NULL, &rev, txn, pool));
+  SVN_ERR(svn_fs_revision_root(&rev_root, fs, rev, pool));
+  SVN_ERR(verify_file_checksum(str, rev_root, "fact", svn_checksum_md5,
+                               pool));
+  SVN_ERR(verify_file_checksum(str, rev_root, "fact", svn_checksum_sha1,
+                               pool));
 
   return SVN_NO_ERROR;
 }
@@ -5403,6 +5522,346 @@ reopen_modify(const svn_test_opts_t *opt
 #endif
 }
 
+static svn_error_t *
+upgrade_while_committing(const svn_test_opts_t *opts,
+                         apr_pool_t *pool)
+{
+  svn_fs_t *fs;
+  svn_revnum_t head_rev = 0;
+  svn_fs_root_t *root;
+  svn_fs_txn_t *txn1, *txn2;
+  const char *fs_path;
+  apr_hash_t *fs_config = apr_hash_make(pool);
+
+  /* Bail (with success) on known-untestable scenarios */
+  if (strcmp(opts->fs_type, "fsfs") != 0)
+    return svn_error_create(SVN_ERR_TEST_SKIPPED, NULL,
+                            "this will test FSFS repositories only");
+
+  if (opts->server_minor_version && (opts->server_minor_version < 6))
+    return svn_error_create(SVN_ERR_TEST_SKIPPED, NULL,
+                            "pre-1.6 SVN doesn't support FSFS packing");
+
+  /* Create test repository with greek tree. */
+  fs_path = "test-upgrade-while-committing";
+
+  svn_hash_sets(fs_config, SVN_FS_CONFIG_COMPATIBLE_VERSION, "1.7");
+  svn_hash_sets(fs_config, SVN_FS_CONFIG_FSFS_SHARD_SIZE, "2");
+  SVN_ERR(svn_test__create_fs2(&fs, fs_path, opts, fs_config, pool));
+
+  SVN_ERR(svn_fs_begin_txn(&txn1, fs, head_rev, pool));
+  SVN_ERR(svn_fs_txn_root(&root, txn1, pool));
+  SVN_ERR(svn_test__create_greek_tree(root, pool));
+  SVN_ERR(test_commit_txn(&head_rev, txn1, NULL, pool));
+
+  /* Create txn with changes. */
+  SVN_ERR(svn_fs_begin_txn(&txn1, fs, head_rev, pool));
+  SVN_ERR(svn_fs_txn_root(&root, txn1, pool));
+  SVN_ERR(svn_fs_make_dir(root, "/foo", pool));
+
+  /* Upgrade filesystem, but keep existing svn_fs_t object. */
+  SVN_ERR(svn_fs_upgrade(fs_path, pool));
+
+  /* Creating a new txn for the old svn_fs_t object shall fail. */
+  SVN_TEST_ASSERT_ANY_ERROR(svn_fs_begin_txn(&txn2, fs, head_rev, pool));
+
+  /* Committing the already existing txn shall fail as well. */
+  SVN_TEST_ASSERT_ANY_ERROR(test_commit_txn(&head_rev, txn1, NULL, pool));
+
+  /* Verify filesystem content. */
+  SVN_ERR(svn_fs_verify(fs_path, NULL, 0, SVN_INVALID_REVNUM, NULL, NULL,
+                        NULL, NULL, pool));
+
+  return SVN_NO_ERROR;
+}
+
+/* Utility method for test_paths_changed. Verify that REV in FS changes
+ * exactly one path and that that change is a property change.  Expect
+ * the MERGEINFO_MOD flag of the change to have the given value.
+ */
+static svn_error_t *
+verify_root_prop_change(svn_fs_t *fs,
+                        svn_revnum_t rev,
+                        svn_tristate_t mergeinfo_mod,
+                        apr_pool_t *pool)
+{
+  svn_fs_path_change2_t *change;
+  svn_fs_root_t *root;
+  apr_hash_t *changes;
+
+  SVN_ERR(svn_fs_revision_root(&root, fs, rev, pool));
+  SVN_ERR(svn_fs_paths_changed2(&changes, root, pool));
+  SVN_TEST_ASSERT(apr_hash_count(changes) == 1);
+  change = svn_hash_gets(changes, "/");
+
+  SVN_TEST_ASSERT(change->node_rev_id);
+  SVN_TEST_ASSERT(change->change_kind == svn_fs_path_change_modify);
+  SVN_TEST_ASSERT(   change->node_kind == svn_node_dir
+                  || change->node_kind == svn_node_unknown);
+  SVN_TEST_ASSERT(change->text_mod == FALSE);
+  SVN_TEST_ASSERT(change->prop_mod == TRUE);
+
+  if (change->copyfrom_known)
+    {
+      SVN_TEST_ASSERT(change->copyfrom_rev == SVN_INVALID_REVNUM);
+      SVN_TEST_ASSERT(change->copyfrom_path == NULL);
+    }
+
+  SVN_TEST_ASSERT(change->mergeinfo_mod == mergeinfo_mod);
+
+  return SVN_NO_ERROR;
+}
+
+static svn_error_t *
+test_paths_changed(const svn_test_opts_t *opts,
+                   apr_pool_t *pool)
+{
+  svn_fs_t *fs;
+  svn_revnum_t head_rev = 0;
+  svn_fs_root_t *root;
+  svn_fs_txn_t *txn;
+  const char *fs_path;
+  apr_hash_t *changes;
+  svn_boolean_t has_mergeinfo_mod = FALSE;
+  apr_hash_index_t *hi;
+  int i;
+
+  /* The "mergeinfo_mod flag will say "unknown" until recently. */
+  if (   strcmp(opts->fs_type, "bdb") != 0
+      && (!opts->server_minor_version || (opts->server_minor_version >= 9)))
+    has_mergeinfo_mod = TRUE;
+
+  /* Create test repository with greek tree. */
+  fs_path = "test-paths-changed";
+
+  SVN_ERR(svn_test__create_fs2(&fs, fs_path, opts, NULL, pool));
+
+  SVN_ERR(svn_fs_begin_txn(&txn, fs, head_rev, pool));
+  SVN_ERR(svn_fs_txn_root(&root, txn, pool));
+  SVN_ERR(svn_test__create_greek_tree(root, pool));
+  SVN_ERR(test_commit_txn(&head_rev, txn, NULL, pool));
+
+  /* Create txns with various prop changes. */
+  SVN_ERR(svn_fs_begin_txn(&txn, fs, head_rev, pool));
+  SVN_ERR(svn_fs_txn_root(&root, txn, pool));
+  SVN_ERR(svn_fs_change_node_prop(root, "/", "propname",
+                                  svn_string_create("propval", pool), pool));
+  SVN_ERR(test_commit_txn(&head_rev, txn, NULL, pool));
+
+  SVN_ERR(svn_fs_begin_txn(&txn, fs, head_rev, pool));
+  SVN_ERR(svn_fs_txn_root(&root, txn, pool));
+  SVN_ERR(svn_fs_change_node_prop(root, "/", "svn:mergeinfo",
+                                  svn_string_create("/: 1\n", pool), pool));
+  SVN_ERR(test_commit_txn(&head_rev, txn, NULL, pool));
+
+  /* Verify changed path lists. */
+
+  /* Greek tree creation rev. */
+  SVN_ERR(svn_fs_revision_root(&root, fs, head_rev - 2, pool));
+  SVN_ERR(svn_fs_paths_changed2(&changes, root, pool));
+
+  /* Reports all paths? */
+  for (i = 0; svn_test__greek_tree_nodes[i].path; ++i)
+    {
+      const char *path
+        = svn_fspath__canonicalize(svn_test__greek_tree_nodes[i].path, pool);
+
+      SVN_TEST_ASSERT(svn_hash_gets(changes, path));
+    }
+
+  SVN_TEST_ASSERT(apr_hash_count(changes) == i);
+
+  /* Verify per-path info. */
+  for (hi = apr_hash_first(pool, changes); hi; hi = apr_hash_next(hi))
+    {
+      svn_fs_path_change2_t *change = apr_hash_this_val(hi);
+
+      SVN_TEST_ASSERT(change->node_rev_id);
+      SVN_TEST_ASSERT(change->change_kind == svn_fs_path_change_add);
+      SVN_TEST_ASSERT(   change->node_kind == svn_node_file
+                      || change->node_kind == svn_node_dir
+                      || change->node_kind == svn_node_unknown);
+
+      if (change->node_kind != svn_node_unknown)
+        SVN_TEST_ASSERT(change->text_mod == (   change->node_kind
+                                             == svn_node_file));
+
+      SVN_TEST_ASSERT(change->prop_mod == FALSE);
+
+      if (change->copyfrom_known)
+        {
+          SVN_TEST_ASSERT(change->copyfrom_rev == SVN_INVALID_REVNUM);
+          SVN_TEST_ASSERT(change->copyfrom_path == NULL);
+        }
+
+      if (has_mergeinfo_mod)
+        SVN_TEST_ASSERT(change->mergeinfo_mod == svn_tristate_false);
+      else
+        SVN_TEST_ASSERT(change->mergeinfo_mod == svn_tristate_unknown);
+    }
+
+  /* Propset rev. */
+  SVN_ERR(verify_root_prop_change(fs, head_rev - 1,
+                                  has_mergeinfo_mod ? svn_tristate_false
+                                                    : svn_tristate_unknown,
+                                  pool));
+
+  /* Mergeinfo set rev. */
+  SVN_ERR(verify_root_prop_change(fs, head_rev,
+                                  has_mergeinfo_mod ? svn_tristate_true
+                                                    : svn_tristate_unknown,
+                                  pool));
+
+  return SVN_NO_ERROR;
+}
+
+static svn_error_t *
+test_delete_replaced_paths_changed(const svn_test_opts_t *opts,
+                                   apr_pool_t *pool)
+{
+  svn_fs_t *fs;
+  svn_revnum_t head_rev = 0;
+  svn_fs_root_t *root;
+  svn_fs_txn_t *txn;
+  const char *fs_path;
+  apr_hash_t *changes;
+  svn_fs_path_change2_t *change;
+  const svn_fs_id_t *file_id;
+
+  /* Create test repository with greek tree. */
+  fs_path = "test-delete-replace-paths-changed";
+
+  SVN_ERR(svn_test__create_fs2(&fs, fs_path, opts, NULL, pool));
+
+  SVN_ERR(svn_fs_begin_txn(&txn, fs, head_rev, pool));
+  SVN_ERR(svn_fs_txn_root(&root, txn, pool));
+  SVN_ERR(svn_test__create_greek_tree(root, pool));
+  SVN_ERR(test_commit_txn(&head_rev, txn, NULL, pool));
+
+  /* Create that replaces a file with a folder and then deletes that
+   * replacement.  Start with the deletion. */
+  SVN_ERR(svn_fs_begin_txn(&txn, fs, head_rev, pool));
+  SVN_ERR(svn_fs_txn_root(&root, txn, pool));
+  SVN_ERR(svn_fs_delete(root, "/iota", pool));
+
+  /* The change list should now report a deleted file. */
+  SVN_ERR(svn_fs_paths_changed2(&changes, root, pool));
+  change = svn_hash_gets(changes, "/iota");
+  file_id = change->node_rev_id;
+  SVN_TEST_ASSERT(   change->node_kind == svn_node_file
+                  || change->node_kind == svn_node_unknown);
+  SVN_TEST_ASSERT(change->change_kind == svn_fs_path_change_delete);
+
+  /* Add a replacement. */
+  SVN_ERR(svn_fs_make_dir(root, "/iota", pool));
+
+  /* The change list now reports a replacement by a directory. */
+  SVN_ERR(svn_fs_paths_changed2(&changes, root, pool));
+  change = svn_hash_gets(changes, "/iota");
+  SVN_TEST_ASSERT(   change->node_kind == svn_node_dir
+                  || change->node_kind == svn_node_unknown);
+  SVN_TEST_ASSERT(change->change_kind == svn_fs_path_change_replace);
+  SVN_TEST_ASSERT(svn_fs_compare_ids(change->node_rev_id, file_id) != 0);
+
+  /* Delete the replacement again. */
+  SVN_ERR(svn_fs_delete(root, "/iota", pool));
+
+  /* The change list should now be reported as a deleted file again. */
+  SVN_ERR(svn_fs_paths_changed2(&changes, root, pool));
+  change = svn_hash_gets(changes, "/iota");
+  SVN_TEST_ASSERT(   change->node_kind == svn_node_file
+                  || change->node_kind == svn_node_unknown);
+  SVN_TEST_ASSERT(change->change_kind == svn_fs_path_change_delete);
+  SVN_TEST_ASSERT(svn_fs_compare_ids(change->node_rev_id, file_id) == 0);
+
+  /* Finally, commit the change. */
+  SVN_ERR(test_commit_txn(&head_rev, txn, NULL, pool));
+
+  /* The committed revision should still report the same change. */
+  SVN_ERR(svn_fs_revision_root(&root, fs, head_rev, pool));
+  SVN_ERR(svn_fs_paths_changed2(&changes, root, pool));
+  change = svn_hash_gets(changes, "/iota");
+  SVN_TEST_ASSERT(   change->node_kind == svn_node_file
+                  || change->node_kind == svn_node_unknown);
+  SVN_TEST_ASSERT(change->change_kind == svn_fs_path_change_delete);
+
+  return SVN_NO_ERROR;
+}
+
+/* Get rid of transaction NAME in FS.  This function deals with backend-
+ * specific behavior as permitted by the API. */
+static svn_error_t *
+cleanup_txn(svn_fs_t *fs,
+            const char *name,
+            apr_pool_t *scratch_pool)
+{
+  /* Get rid of the txns one at a time. */
+  svn_error_t *err = svn_fs_purge_txn(fs, name, scratch_pool);
+
+  /* Some backends (BDB) don't support purging transactions that have never
+   * seen an abort or commit attempt.   Simply abort those txns. */
+  if (err && err->apr_err == SVN_ERR_FS_TRANSACTION_NOT_DEAD)
+    {
+      svn_fs_txn_t *txn;
+      svn_error_clear(err);
+      err = SVN_NO_ERROR;
+
+      SVN_ERR(svn_fs_open_txn(&txn, fs, name, scratch_pool));
+      SVN_ERR(svn_fs_abort_txn(txn, scratch_pool));
+
+      /* Should be gone now ... */
+      SVN_TEST_ASSERT_ERROR(svn_fs_open_txn(&txn, fs, name, scratch_pool),
+                            SVN_ERR_FS_NO_SUCH_TRANSACTION);
+    }
+
+  return svn_error_trace(err);
+}
+
+/* Make sure we get txn lists correctly. */
+static svn_error_t *
+purge_txn_test(const svn_test_opts_t *opts,
+               apr_pool_t *pool)
+{
+  svn_fs_t *fs;
+  svn_fs_txn_t *txn;
+  const char *name1, *name2;
+  apr_array_header_t *txn_list;
+  apr_pool_t *subpool = svn_pool_create(pool);
+
+  SVN_ERR(svn_test__create_fs(&fs, "test-repo-purge-txn",
+                              opts, pool));
+
+  /* Begin a new transaction, get its name (in the top pool), close it.  */
+  SVN_ERR(svn_fs_begin_txn(&txn, fs, 0, subpool));
+  SVN_ERR(svn_fs_txn_name(&name1, txn, pool));
+
+  /* Begin *another* transaction, get its name (in the top pool), close it.  */
+  SVN_ERR(svn_fs_begin_txn(&txn, fs, 0, subpool));
+  SVN_ERR(svn_fs_txn_name(&name2, txn, pool));
+  svn_pool_clear(subpool);
+
+  /* Get rid of the txns one at a time. */
+  SVN_ERR(cleanup_txn(fs, name1, pool));
+
+  /* There should be exactly one left. */
+  SVN_ERR(svn_fs_list_transactions(&txn_list, fs, pool));
+
+  /* Check the list. It should have *exactly* one entry. */
+  SVN_TEST_ASSERT(   txn_list->nelts == 1
+                  && !strcmp(name2, APR_ARRAY_IDX(txn_list, 0, const char *)));
+
+  /* Get rid of the other txn as well. */
+  SVN_ERR(cleanup_txn(fs, name2, pool));
+
+  /* There should be exactly one left. */
+  SVN_ERR(svn_fs_list_transactions(&txn_list, fs, pool));
+
+  /* Check the list. It should have no entries. */
+  SVN_TEST_ASSERT(txn_list->nelts == 0);
+
+  return SVN_NO_ERROR;
+}
+
 
 /* ------------------------------------------------------------------------ */
 
@@ -5501,6 +5960,14 @@ static struct svn_test_descriptor_t test
     SVN_TEST_OPTS_WIMP(reopen_modify,
                        "test reopen and modify txn",
                        "txn_dir_cache fail in FSFS"),
+    SVN_TEST_OPTS_PASS(upgrade_while_committing,
+                       "upgrade while committing"),
+    SVN_TEST_OPTS_PASS(test_paths_changed,
+                       "test svn_fs_paths_changed"),
+    SVN_TEST_OPTS_PASS(test_delete_replaced_paths_changed,
+                       "test deletion after replace in changed paths list"),
+    SVN_TEST_OPTS_PASS(purge_txn_test,
+                       "test purging transactions"),
     SVN_TEST_NULL
   };
 

Propchange: subversion/branches/move-tracking-2/subversion/tests/libsvn_fs_fs/
------------------------------------------------------------------------------
--- svn:ignore (original)
+++ svn:ignore Mon Oct 27 17:28:13 2014
@@ -4,6 +4,7 @@ Release
 test-repo-*
 upgrade_*
 fs-pack-test
+fs-fs-fuzzy-test
 fs-fs-pack-test
 test-get-set-revprop-packed-fs
 get_set_multiple_huge_revprops_packed_fs

Modified: subversion/branches/move-tracking-2/subversion/tests/libsvn_fs_fs/fs-fs-pack-test.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/tests/libsvn_fs_fs/fs-fs-pack-test.c?rev=1634609&r1=1634608&r2=1634609&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/tests/libsvn_fs_fs/fs-fs-pack-test.c (original)
+++ subversion/branches/move-tracking-2/subversion/tests/libsvn_fs_fs/fs-fs-pack-test.c Mon Oct 27 17:28:13 2014
@@ -1,4 +1,4 @@
-/* fs-pack-test.c --- tests for the filesystem
+/* fs-fs-pack-test.c --- tests for the FSFS filesystem
  *
  * ====================================================================
  *    Licensed to the Apache Software Foundation (ASF) under one
@@ -33,7 +33,6 @@
 #include "svn_props.h"
 #include "svn_fs.h"
 #include "private/svn_string_private.h"
-#include "private/svn_string_private.h"
 
 #include "../svn_test_fs.h"
 
@@ -51,65 +50,6 @@ ignore_fs_warnings(void *baton, svn_erro
   return;
 }
 
-/* Write the format number and maximum number of files per directory
-   to a new format file in PATH, overwriting a previously existing
-   file.  Use POOL for temporary allocation.
-
-   (This implementation is largely stolen from libsvn_fs_fs/fs_fs.c.) */
-static svn_error_t *
-write_format(const char *path,
-             int format,
-             int max_files_per_dir,
-             apr_pool_t *pool)
-{
-  const char *contents;
-
-  path = svn_dirent_join(path, "format", pool);
-
-  if (format >= SVN_FS_FS__MIN_LAYOUT_FORMAT_OPTION_FORMAT)
-    {
-      if (format >= SVN_FS_FS__MIN_LOG_ADDRESSING_FORMAT)
-        {
-          if (max_files_per_dir)
-            contents = apr_psprintf(pool,
-                                    "%d\n"
-                                    "layout sharded %d\n"
-                                    "addressing logical 0\n",
-                                    format, max_files_per_dir);
-          else
-            /* linear layouts never use logical addressing */
-            contents = apr_psprintf(pool,
-                                    "%d\n"
-                                    "layout linear\n"
-                                    "addressing physical\n",
-                                    format);
-        }
-      else
-        {
-          if (max_files_per_dir)
-            contents = apr_psprintf(pool,
-                                    "%d\n"
-                                    "layout sharded %d\n",
-                                    format, max_files_per_dir);
-          else
-            contents = apr_psprintf(pool,
-                                    "%d\n"
-                                    "layout linear\n",
-                                    format);
-        }
-    }
-  else
-    {
-      contents = apr_psprintf(pool, "%d\n", format);
-    }
-
-  SVN_ERR(svn_io_write_atomic(path, contents, strlen(contents),
-                              NULL /* copy perms */, pool));
-
-  /* And set the perms to make it read only */
-  return svn_io_set_file_read_only(path, FALSE, pool);
-}
-
 /* Return the expected contents of "iota" in revision REV. */
 static const char *
 get_rev_contents(svn_revnum_t rev, apr_pool_t *pool)
@@ -178,7 +118,7 @@ create_packed_filesystem(const char *dir
   apr_pool_t *subpool = svn_pool_create(pool);
   struct pack_notify_baton pnb;
   apr_pool_t *iterpool;
-  int version;
+  apr_hash_t *fs_config;
 
   /* Bail (with success) on known-untestable scenarios */
   if (strcmp(opts->fs_type, "fsfs") != 0)
@@ -189,25 +129,12 @@ create_packed_filesystem(const char *dir
     return svn_error_create(SVN_ERR_TEST_SKIPPED, NULL,
                             "pre-1.6 SVN doesn't support FSFS packing");
 
-  /* Create a filesystem, then close it */
-  SVN_ERR(svn_test__create_fs(&fs, dir, opts, subpool));
-  svn_pool_destroy(subpool);
-
-  subpool = svn_pool_create(pool);
-
-  /* Rewrite the format file.  (The rest of this function is backend-agnostic,
-     so we just avoid adding the FSFS-specific format information if we run on
-     some other backend.) */
-  if ((strcmp(opts->fs_type, "fsfs") == 0))
-    {
-      SVN_ERR(svn_io_read_version_file(&version,
-                                       svn_dirent_join(dir, "format", subpool),
-                                       subpool));
-      SVN_ERR(write_format(dir, version, shard_size, subpool));
-    }
+  fs_config = apr_hash_make(pool);
+  svn_hash_sets(fs_config, SVN_FS_CONFIG_FSFS_SHARD_SIZE,
+                apr_itoa(pool, shard_size));
 
-  /* Reopen the filesystem */
-  SVN_ERR(svn_fs_open2(&fs, dir, NULL, subpool, subpool));
+  /* Create a filesystem. */
+  SVN_ERR(svn_test__create_fs2(&fs, dir, opts, fs_config, subpool));
 
   /* Revision 1: the Greek tree */
   SVN_ERR(svn_fs_begin_txn(&txn, fs, 0, subpool));
@@ -856,7 +783,7 @@ pack_shard_size_one(const svn_test_opts_
 #undef SHARD_SIZE
 #undef MAX_REV
 /* ------------------------------------------------------------------------ */
-#define REPO_NAME "get_set_multiple_huge_revprops_packed_fs"
+#define REPO_NAME "test-repo-get_set_multiple_huge_revprops_packed_fs"
 #define SHARD_SIZE 4
 #define MAX_REV 9
 static svn_error_t *
@@ -1091,7 +1018,7 @@ upgrade_txns_to_log_addressing(const svn
 }
 #undef SHARD_SIZE
 
-#define REPO_NAME "upgrade_new_txns_to_log_addressing"
+#define REPO_NAME "test-repo-upgrade_new_txns_to_log_addressing"
 #define MAX_REV 8
 static svn_error_t *
 upgrade_new_txns_to_log_addressing(const svn_test_opts_t *opts,
@@ -1106,7 +1033,7 @@ upgrade_new_txns_to_log_addressing(const
 #undef MAX_REV
 
 /* ------------------------------------------------------------------------ */
-#define REPO_NAME "upgrade_old_txns_to_log_addressing"
+#define REPO_NAME "test-repo-upgrade_old_txns_to_log_addressing"
 #define MAX_REV 8
 static svn_error_t *
 upgrade_old_txns_to_log_addressing(const svn_test_opts_t *opts,
@@ -1123,7 +1050,7 @@ upgrade_old_txns_to_log_addressing(const
 
 /* ------------------------------------------------------------------------ */
 
-#define REPO_NAME "metadata_checksumming"
+#define REPO_NAME "test-repo-metadata_checksumming"
 static svn_error_t *
 metadata_checksumming(const svn_test_opts_t *opts,
                   apr_pool_t *pool)
@@ -1179,7 +1106,7 @@ metadata_checksumming(const svn_test_opt
 
 /* ------------------------------------------------------------------------ */
 
-#define REPO_NAME "revprop_caching_on_off"
+#define REPO_NAME "test-repo-revprop_caching_on_off"
 static svn_error_t *
 revprop_caching_on_off(const svn_test_opts_t *opts,
                        apr_pool_t *pool)

Propchange: subversion/branches/move-tracking-2/subversion/tests/libsvn_fs_x/
------------------------------------------------------------------------------
  Merged /subversion/trunk/subversion/tests/libsvn_fs_x:r1619126-1634606

Modified: subversion/branches/move-tracking-2/subversion/tests/libsvn_fs_x/fs-x-pack-test.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/tests/libsvn_fs_x/fs-x-pack-test.c?rev=1634609&r1=1634608&r2=1634609&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/tests/libsvn_fs_x/fs-x-pack-test.c (original)
+++ subversion/branches/move-tracking-2/subversion/tests/libsvn_fs_x/fs-x-pack-test.c Mon Oct 27 17:28:13 2014
@@ -1,4 +1,4 @@
-/* fs-pack-test.c --- tests for the filesystem
+/* fs-x-pack-test.c --- tests for the FSX filesystem
  *
  * ====================================================================
  *    Licensed to the Apache Software Foundation (ASF) under one

Modified: subversion/branches/move-tracking-2/subversion/tests/libsvn_subr/io-test.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/tests/libsvn_subr/io-test.c?rev=1634609&r1=1634608&r2=1634609&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/tests/libsvn_subr/io-test.c (original)
+++ subversion/branches/move-tracking-2/subversion/tests/libsvn_subr/io-test.c Mon Oct 27 17:28:13 2014
@@ -561,7 +561,7 @@ aligned_seek(apr_file_t *file,
 
   /* we must be at the desired offset */
   current = 0;
-  SVN_ERR(svn_io_file_seek(file, SEEK_CUR, &current, pool));
+  SVN_ERR(svn_io_file_seek(file, APR_CUR, &current, pool));
   SVN_TEST_ASSERT(current == (apr_off_t)offset);
 
   return SVN_NO_ERROR;

Modified: subversion/branches/move-tracking-2/subversion/tests/libsvn_subr/skel-test.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/tests/libsvn_subr/skel-test.c?rev=1634609&r1=1634608&r2=1634609&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/tests/libsvn_subr/skel-test.c (original)
+++ subversion/branches/move-tracking-2/subversion/tests/libsvn_subr/skel-test.c Mon Oct 27 17:28:13 2014
@@ -59,7 +59,7 @@ get_empty_string(apr_pool_t *pool)
 {
   svn_pool_clear(pool);
 
-  return svn_stringbuf_ncreate(0, 0, pool);
+  return svn_stringbuf_create_empty(pool);
 }
 
 /* Parse a skeleton from a Subversion string.  */

Modified: subversion/branches/move-tracking-2/subversion/tests/libsvn_wc/wc-test.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/tests/libsvn_wc/wc-test.c?rev=1634609&r1=1634608&r2=1634609&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/tests/libsvn_wc/wc-test.c (original)
+++ subversion/branches/move-tracking-2/subversion/tests/libsvn_wc/wc-test.c Mon Oct 27 17:28:13 2014
@@ -23,6 +23,9 @@
 
 #include <apr_pools.h>
 #include <apr_general.h>
+#include <apr_md5.h>
+
+#define SVN_DEPRECATED
 
 #include "svn_types.h"
 #include "svn_io.h"
@@ -305,6 +308,132 @@ test_externals_parse_erratic(apr_pool_t 
   return SVN_NO_ERROR;
 }
 
+static svn_error_t *
+test_legacy_commit1(const svn_test_opts_t *opts, apr_pool_t *pool)
+{
+  svn_test__sandbox_t b;
+  svn_wc_adm_access_t *adm_access;
+  const char *lambda;
+
+  SVN_ERR(svn_test__sandbox_create(&b, "legacy_commit1", opts, pool));
+  SVN_ERR(sbox_add_and_commit_greek_tree(&b));
+
+  SVN_ERR(sbox_wc_copy(&b, "A", "A_copied"));
+
+  lambda = sbox_wc_path(&b, "A_copied/B/lambda");
+
+
+  SVN_ERR(svn_io_remove_file2(lambda, FALSE, pool));
+  SVN_ERR(svn_io_copy_file(sbox_wc_path(&b, "iota"), lambda, FALSE, pool));
+  SVN_ERR(svn_wc_adm_open3(&adm_access, NULL, b.wc_abspath, TRUE, -1,
+                           NULL, NULL, pool));
+
+  {
+    svn_wc_status2_t *status;
+
+    SVN_ERR(svn_wc_status2(&status, lambda, adm_access, pool));
+
+    SVN_TEST_ASSERT(status != NULL);
+    SVN_TEST_ASSERT(status->text_status == svn_wc_status_modified);
+    SVN_TEST_ASSERT(status->copied == TRUE);
+  }
+
+  /* Simulate a very old style svn ci . -m "QQQ" on the WC root */
+  SVN_ERR(svn_wc_process_committed4(sbox_wc_path(&b, "A_copied"), adm_access,
+                                    TRUE, 12, "2014-10-01T19:00:50.966679Z",
+                                    "me", NULL, TRUE, TRUE,
+                                    NULL, pool));
+
+  {
+    unsigned char digest[APR_MD5_DIGESTSIZE];
+
+    /* Use the fact that iota has the same checksum to ease committing */
+
+    SVN_ERR(svn_io_file_checksum (digest, lambda, pool));
+
+    SVN_ERR(svn_wc_process_committed4(lambda, adm_access,
+                                      TRUE, 12, "2014-10-01T19:00:50.966679Z",
+                                      "me", NULL, TRUE, TRUE,
+                                      digest, pool));
+  }
+
+  {
+    svn_wc_status2_t *status;
+
+    SVN_ERR(svn_wc_status2(&status, lambda, adm_access, pool));
+
+    /* Node is still modified, as we didn't change the text base! */
+    SVN_TEST_ASSERT(status != NULL);
+    SVN_TEST_ASSERT(status->text_status == svn_wc_status_normal);
+    SVN_TEST_ASSERT(status->copied == FALSE);
+  }
+
+  return SVN_NO_ERROR;
+}
+
+static svn_error_t *
+test_legacy_commit2(const svn_test_opts_t *opts, apr_pool_t *pool)
+{
+  svn_test__sandbox_t b;
+  svn_wc_adm_access_t *adm_access;
+  const char *lambda;
+  svn_wc_committed_queue_t *queue;
+
+  SVN_ERR(svn_test__sandbox_create(&b, "legacy_commit2", opts, pool));
+  SVN_ERR(sbox_add_and_commit_greek_tree(&b));
+
+  SVN_ERR(sbox_wc_copy(&b, "A", "A_copied"));
+
+  lambda = sbox_wc_path(&b, "A_copied/B/lambda");
+
+  SVN_ERR(svn_io_remove_file2(lambda, FALSE, pool));
+  SVN_ERR(svn_io_copy_file(sbox_wc_path(&b, "iota"), lambda, FALSE, pool));
+
+  SVN_ERR(svn_wc_adm_open3(&adm_access, NULL, b.wc_abspath, TRUE, -1,
+                           NULL, NULL, pool));
+
+  {
+    svn_wc_status2_t *status;
+
+    SVN_ERR(svn_wc_status2(&status, lambda, adm_access, pool));
+
+    SVN_TEST_ASSERT(status != NULL);
+    SVN_TEST_ASSERT(status->text_status == svn_wc_status_modified);
+    SVN_TEST_ASSERT(status->copied == TRUE);
+  }
+
+  /* Simulate an old style svn ci . -m "QQQ" on the WC root */
+  queue = svn_wc_committed_queue_create(pool);
+  SVN_ERR(svn_wc_queue_committed(&queue, sbox_wc_path(&b, "A_copied"), adm_access,
+                                 TRUE, NULL, FALSE, FALSE, NULL, pool));
+  {
+    unsigned char digest[APR_MD5_DIGESTSIZE];
+
+    /* Use the fact that iota has the same checksum to ease committing */
+
+    SVN_ERR(svn_io_file_checksum(digest, lambda, pool));
+
+    SVN_ERR(svn_wc_queue_committed(&queue, lambda, adm_access, FALSE, NULL,
+                                   FALSE, FALSE, digest, pool));
+  }
+
+  SVN_ERR(svn_wc_process_committed_queue(queue, adm_access,
+                                         12, "2014-10-01T19:00:50.966679Z",
+                                        "me", pool));
+
+  {
+    svn_wc_status2_t *status;
+
+    SVN_ERR(svn_wc_status2(&status, lambda, adm_access, pool));
+
+    /* Node is still modified, as we didn't change the text base! */
+    SVN_TEST_ASSERT(status != NULL);
+    SVN_TEST_ASSERT(status->text_status == svn_wc_status_normal);
+    SVN_TEST_ASSERT(status->copied == FALSE);
+  }
+
+  return SVN_NO_ERROR;
+}
 
 /* ---------------------------------------------------------------------- */
 /* The list of test functions */
@@ -322,6 +451,10 @@ static struct svn_test_descriptor_t test
                        "test svn_wc_parse_externals_description3"),
     SVN_TEST_PASS2(test_externals_parse_erratic,
                    "parse erratic externals definition"),
+    SVN_TEST_OPTS_PASS(test_legacy_commit1,
+                       "test legacy commit1"),
+    SVN_TEST_OPTS_PASS(test_legacy_commit2,
+                       "test legacy commit2"),
     SVN_TEST_NULL
   };
 

Modified: subversion/branches/move-tracking-2/subversion/tests/svn_test.h
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/tests/svn_test.h?rev=1634609&r1=1634608&r2=1634609&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/tests/svn_test.h (original)
+++ subversion/branches/move-tracking-2/subversion/tests/svn_test.h Mon Oct 27 17:28:13 2014
@@ -74,6 +74,23 @@ extern "C" {
     svn_error_clear(err__);                                               \
   } while (0)
 
+/** Handy macro for testing that an svn_error_t is returned.
+ * The result must be neither SVN_NO_ERROR nor SVN_ERR_ASSERTION_FAIL.
+ * The error returned by EXPR will be cleared.
+ */
+#define SVN_TEST_ASSERT_ANY_ERROR(expr)                                   \
+  do {                                                                    \
+    svn_error_t *err__ = (expr);                                          \
+    if (err__ == SVN_NO_ERROR || err__->apr_err == SVN_ERR_ASSERTION_FAIL)\
+      return err__ ? svn_error_createf(SVN_ERR_TEST_FAILED, err__,        \
+                                       "Expected error but got %s",       \
+                                       "SVN_ERR_ASSERTION_FAIL")          \
+                   : svn_error_createf(SVN_ERR_TEST_FAILED, err__,        \
+                                       "Expected error but got %s",       \
+                                       "SVN_NO_ERROR");                   \
+    svn_error_clear(err__);                                               \
+  } while (0)
+
 /** Handy macro for testing string equality.
  *
  * EXPR and/or EXPECTED_EXPR may be NULL which compares equal to NULL and



Mime
View raw message