subversion-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From prabh...@apache.org
Subject svn commit: r1489765 [12/22] - in /subversion/branches/verify-keep-going: ./ build/ build/ac-macros/ build/generator/ build/generator/templates/ contrib/hook-scripts/ contrib/server-side/fsfsfixer/ contrib/server-side/fsfsfixer/fixer/ notes/ subversion...
Date Wed, 05 Jun 2013 09:22:51 GMT
Modified: subversion/branches/verify-keep-going/subversion/libsvn_subr/cmdline.c
URL: http://svn.apache.org/viewvc/subversion/branches/verify-keep-going/subversion/libsvn_subr/cmdline.c?rev=1489765&r1=1489764&r2=1489765&view=diff
==============================================================================
--- subversion/branches/verify-keep-going/subversion/libsvn_subr/cmdline.c (original)
+++ subversion/branches/verify-keep-going/subversion/libsvn_subr/cmdline.c Wed Jun  5 09:22:43 2013
@@ -236,7 +236,7 @@ svn_cmdline_init(const char *progname, F
   /* Create a pool for use by the UTF-8 routines.  It will be cleaned
      up by APR at exit time. */
   pool = svn_pool_create(NULL);
-  svn_utf_initialize2(pool, FALSE);
+  svn_utf_initialize2(FALSE, pool);
 
   if ((err = svn_nls_init()))
     {
@@ -946,7 +946,7 @@ svn_cmdline__be_interactive(svn_boolean_
       return (isatty(STDIN_FILENO) != 0);
 #endif
     }
-  else if (force_interactive) 
+  else if (force_interactive)
     return TRUE;
 
   return !non_interactive;

Modified: subversion/branches/verify-keep-going/subversion/libsvn_subr/compat.c
URL: http://svn.apache.org/viewvc/subversion/branches/verify-keep-going/subversion/libsvn_subr/compat.c?rev=1489765&r1=1489764&r2=1489765&view=diff
==============================================================================
--- subversion/branches/verify-keep-going/subversion/libsvn_subr/compat.c (original)
+++ subversion/branches/verify-keep-going/subversion/libsvn_subr/compat.c Wed Jun  5 09:22:43 2013
@@ -95,23 +95,33 @@ svn_compat_log_revprops_in(apr_pool_t *p
 }
 
 void
-svn_compat_log_revprops_out(const char **author, const char **date,
-                            const char **message, apr_hash_t *revprops)
+svn_compat_log_revprops_out_string(const svn_string_t **author,
+                                   const svn_string_t **date,
+                                   const svn_string_t **message,
+                                   apr_hash_t *revprops)
 {
-  svn_string_t *author_s, *date_s,  *message_s;
-
   *author = *date = *message = NULL;
   if (revprops)
     {
-      if ((author_s = svn_hash_gets(revprops, SVN_PROP_REVISION_AUTHOR)))
-        *author = author_s->data;
-      if ((date_s = svn_hash_gets(revprops, SVN_PROP_REVISION_DATE)))
-        *date = date_s->data;
-      if ((message_s = svn_hash_gets(revprops, SVN_PROP_REVISION_LOG)))
-        *message = message_s->data;
+      *author = svn_hash_gets(revprops, SVN_PROP_REVISION_AUTHOR);
+      *date = svn_hash_gets(revprops, SVN_PROP_REVISION_DATE);
+      *message = svn_hash_gets(revprops, SVN_PROP_REVISION_LOG);
     }
 }
 
+void
+svn_compat_log_revprops_out(const char **author, const char **date,
+                            const char **message, apr_hash_t *revprops)
+{
+  const svn_string_t *author_s, *date_s,  *message_s;
+  svn_compat_log_revprops_out_string(&author_s, &date_s,  &message_s,
+                                     revprops);
+
+  *author = author_s ? author_s->data : NULL;
+  *date = date_s ? date_s->data : NULL;
+  *message = message_s ? message_s->data : NULL;
+}
+
 /* Baton for use with svn_compat_wrap_log_receiver */
 struct log_wrapper_baton {
   void *baton;

Modified: subversion/branches/verify-keep-going/subversion/libsvn_subr/config.c
URL: http://svn.apache.org/viewvc/subversion/branches/verify-keep-going/subversion/libsvn_subr/config.c?rev=1489765&r1=1489764&r2=1489765&view=diff
==============================================================================
--- subversion/branches/verify-keep-going/subversion/libsvn_subr/config.c (original)
+++ subversion/branches/verify-keep-going/subversion/libsvn_subr/config.c Wed Jun  5 09:22:43 2013
@@ -77,9 +77,10 @@ struct cfg_option_t
 
 
 svn_error_t *
-svn_config_create(svn_config_t **cfgp,
-                  svn_boolean_t section_names_case_sensitive,
-                  apr_pool_t *result_pool)
+svn_config_create2(svn_config_t **cfgp,
+                   svn_boolean_t section_names_case_sensitive,
+                   svn_boolean_t option_names_case_sensitive,
+                   apr_pool_t *result_pool)
 {
   svn_config_t *cfg = apr_palloc(result_pool, sizeof(*cfg));
 
@@ -90,21 +91,26 @@ svn_config_create(svn_config_t **cfgp,
   cfg->tmp_key = svn_stringbuf_create_empty(result_pool);
   cfg->tmp_value = svn_stringbuf_create_empty(result_pool);
   cfg->section_names_case_sensitive = section_names_case_sensitive;
+  cfg->option_names_case_sensitive = option_names_case_sensitive;
 
   *cfgp = cfg;
   return SVN_NO_ERROR;
 }
 
 svn_error_t *
-svn_config_read2(svn_config_t **cfgp, const char *file,
+svn_config_read3(svn_config_t **cfgp, const char *file,
                  svn_boolean_t must_exist,
                  svn_boolean_t section_names_case_sensitive,
-                 apr_pool_t *pool)
+                 svn_boolean_t option_names_case_sensitive,
+                 apr_pool_t *result_pool)
 {
   svn_config_t *cfg;
   svn_error_t *err;
 
-  SVN_ERR(svn_config_create(&cfg, section_names_case_sensitive, pool));
+  SVN_ERR(svn_config_create2(&cfg,
+                             section_names_case_sensitive,
+                             option_names_case_sensitive,
+                             result_pool));
 
   /* Yes, this is platform-specific code in Subversion, but there's no
      practical way to migrate it into APR, as it's simultaneously
@@ -114,10 +120,10 @@ svn_config_read2(svn_config_t **cfgp, co
 #ifdef WIN32
   if (0 == strncmp(file, SVN_REGISTRY_PREFIX, SVN_REGISTRY_PREFIX_LEN))
     err = svn_config__parse_registry(cfg, file + SVN_REGISTRY_PREFIX_LEN,
-                                     must_exist, pool);
+                                     must_exist, result_pool);
   else
 #endif /* WIN32 */
-    err = svn_config__parse_file(cfg, file, must_exist, pool);
+    err = svn_config__parse_file(cfg, file, must_exist, result_pool);
 
   if (err != SVN_NO_ERROR)
     return err;
@@ -130,13 +136,17 @@ svn_config_read2(svn_config_t **cfgp, co
 svn_error_t *
 svn_config_parse(svn_config_t **cfgp, svn_stream_t *stream,
                  svn_boolean_t section_names_case_sensitive,
+                 svn_boolean_t option_names_case_sensitive,
                  apr_pool_t *result_pool)
 {
   svn_config_t *cfg;
   svn_error_t *err;
   apr_pool_t *scratch_pool = svn_pool_create(result_pool);
 
-  err = svn_config_create(&cfg, section_names_case_sensitive, result_pool);
+  err = svn_config_create2(&cfg,
+                           section_names_case_sensitive,
+                           option_names_case_sensitive,
+                           result_pool);
 
   if (err == SVN_NO_ERROR)
     err = svn_config__parse_stream(cfg, stream, result_pool, scratch_pool);
@@ -178,7 +188,8 @@ read_all(svn_config_t **cfgp,
 #ifdef WIN32
   if (sys_registry_path)
     {
-      SVN_ERR(svn_config_read2(cfgp, sys_registry_path, FALSE, FALSE, pool));
+      SVN_ERR(svn_config_read3(cfgp, sys_registry_path, FALSE, FALSE, FALSE,
+                               pool));
       red_config = TRUE;
     }
 #endif /* WIN32 */
@@ -189,7 +200,8 @@ read_all(svn_config_t **cfgp,
         SVN_ERR(svn_config_merge(*cfgp, sys_file_path, FALSE));
       else
         {
-          SVN_ERR(svn_config_read2(cfgp, sys_file_path, FALSE, FALSE, pool));
+          SVN_ERR(svn_config_read3(cfgp, sys_file_path,
+                                   FALSE, FALSE, FALSE, pool));
           red_config = TRUE;
         }
     }
@@ -203,8 +215,8 @@ read_all(svn_config_t **cfgp,
         SVN_ERR(svn_config_merge(*cfgp, usr_registry_path, FALSE));
       else
         {
-          SVN_ERR(svn_config_read2(cfgp, usr_registry_path,
-                                   FALSE, FALSE, pool));
+          SVN_ERR(svn_config_read3(cfgp, usr_registry_path,
+                                   FALSE, FALSE, FALSE, pool));
           red_config = TRUE;
         }
     }
@@ -216,13 +228,14 @@ read_all(svn_config_t **cfgp,
         SVN_ERR(svn_config_merge(*cfgp, usr_file_path, FALSE));
       else
         {
-          SVN_ERR(svn_config_read2(cfgp, usr_file_path, FALSE, FALSE, pool));
+          SVN_ERR(svn_config_read3(cfgp, usr_file_path,
+                                   FALSE, FALSE, FALSE, pool));
           red_config = TRUE;
         }
     }
 
   if (! red_config)
-    SVN_ERR(svn_config_create(cfgp, FALSE, pool));
+    SVN_ERR(svn_config_create2(cfgp, FALSE, FALSE, pool));
 
   return SVN_NO_ERROR;
 }
@@ -352,7 +365,10 @@ svn_config_merge(svn_config_t *cfg, cons
      ### We could use a tmp subpool for this, since merge_cfg is going
      to be tossed afterwards.  Premature optimization, though? */
   svn_config_t *merge_cfg;
-  SVN_ERR(svn_config_read2(&merge_cfg, file, must_exist, FALSE, cfg->pool));
+  SVN_ERR(svn_config_read3(&merge_cfg, file, must_exist,
+                           cfg->section_names_case_sensitive,
+                           cfg->option_names_case_sensitive,
+                           cfg->pool));
 
   /* Now copy the new options into the original table. */
   for_each_option(merge_cfg, cfg, merge_cfg->pool, merge_callback);
@@ -427,7 +443,8 @@ find_option(svn_config_t *cfg, const cha
 
       /* Canonicalize the option key */
       svn_stringbuf_set(cfg->tmp_key, option);
-      make_hash_key(cfg->tmp_key->data);
+      if (! cfg->option_names_case_sensitive)
+        make_hash_key(cfg->tmp_key->data);
 
       opt = apr_hash_get(sec->options, cfg->tmp_key->data,
                          cfg->tmp_key->len);
@@ -464,7 +481,7 @@ make_string_from_option(const char **val
       /* before attempting to expand an option, check for the placeholder.
        * If none is there, there is no point in calling expand_option_value.
        */
-      if (strchr(opt->value, '%'))
+      if (opt->value && strchr(opt->value, '%'))
         {
           apr_pool_t *tmp_pool = (x_pool ? x_pool : svn_pool_create(cfg->x_pool));
 
@@ -586,7 +603,7 @@ expand_option_value(svn_config_t *cfg, c
 static cfg_section_t *
 svn_config_addsection(svn_config_t *cfg,
                       const char *section)
-{  
+{
   cfg_section_t *s;
   const char *hash_key;
 
@@ -606,18 +623,22 @@ static void
 svn_config_create_option(cfg_option_t **opt,
                          const char *option,
                          const char *value,
+                         svn_boolean_t option_names_case_sensitive,
                          apr_pool_t *pool)
 {
   cfg_option_t *o;
 
   o = apr_palloc(pool, sizeof(cfg_option_t));
   o->name = apr_pstrdup(pool, option);
-  o->hash_key = make_hash_key(apr_pstrdup(pool, option));
+  if(option_names_case_sensitive)
+    o->hash_key = o->name;
+  else
+    o->hash_key = make_hash_key(apr_pstrdup(pool, option));
 
   o->value = apr_pstrdup(pool, value);
   o->x_value = NULL;
   o->expanded = FALSE;
-  
+
   *opt = o;
 }
 
@@ -677,7 +698,9 @@ svn_config_set(svn_config_t *cfg,
     }
 
   /* Create a new option */
-  svn_config_create_option(&opt, option, value, cfg->pool);
+  svn_config_create_option(&opt, option, value,
+                           cfg->option_names_case_sensitive,
+                           cfg->pool);
 
   if (sec == NULL)
     {
@@ -1012,7 +1035,7 @@ const char *svn_config_find_group(svn_co
   gb.key = key;
   gb.match = NULL;
   gb.pool = pool;
-  svn_config_enumerate2(cfg, master_section, search_groups, &gb, pool);
+  (void) svn_config_enumerate2(cfg, master_section, search_groups, &gb, pool);
   return gb.match;
 }
 
@@ -1043,10 +1066,11 @@ svn_config_dup(svn_config_t **cfgp,
   apr_hash_index_t *optidx;
 
   *cfgp = 0;
-  SVN_ERR(svn_config_create(cfgp, FALSE, pool));
+  SVN_ERR(svn_config_create2(cfgp, FALSE, FALSE, pool));
 
   (*cfgp)->x_values = src->x_values;
   (*cfgp)->section_names_case_sensitive = src->section_names_case_sensitive;
+  (*cfgp)->option_names_case_sensitive = src->option_names_case_sensitive;
 
   for (sectidx = apr_hash_first(pool, src->sections);
        sectidx != NULL;
@@ -1076,7 +1100,9 @@ svn_config_dup(svn_config_t **cfgp,
       apr_hash_this(optidx, &optkey, &optkeyLength, &optval);
       srcopt = optval;
 
-      svn_config_create_option(&destopt, srcopt->name, srcopt->value, pool);
+      svn_config_create_option(&destopt, srcopt->name, srcopt->value,
+                               (*cfgp)->option_names_case_sensitive,
+                               pool);
 
       destopt->value = apr_pstrdup(pool, srcopt->value);
       destopt->x_value = apr_pstrdup(pool, srcopt->x_value);
@@ -1086,7 +1112,7 @@ svn_config_dup(svn_config_t **cfgp,
                    optkeyLength, destopt);
     }
   }
-  
+
   return SVN_NO_ERROR;
 }
 
@@ -1113,7 +1139,7 @@ svn_config_copy_config(apr_hash_t **cfg_
 
     SVN_ERR(svn_config_dup(&destconfig, srcconfig, pool));
 
-    apr_hash_set(*cfg_hash, 
+    apr_hash_set(*cfg_hash,
                  apr_pstrdup(pool, (const char*)ckey),
                  ckeyLength, destconfig);
   }

Modified: subversion/branches/verify-keep-going/subversion/libsvn_subr/config_auth.c
URL: http://svn.apache.org/viewvc/subversion/branches/verify-keep-going/subversion/libsvn_subr/config_auth.c?rev=1489765&r1=1489764&r2=1489765&view=diff
==============================================================================
--- subversion/branches/verify-keep-going/subversion/libsvn_subr/config_auth.c (original)
+++ subversion/branches/verify-keep-going/subversion/libsvn_subr/config_auth.c Wed Jun  5 09:22:43 2013
@@ -26,13 +26,15 @@
 #include "svn_dirent_uri.h"
 #include "svn_hash.h"
 #include "svn_io.h"
-
+#include "svn_pools.h"
 #include "config_impl.h"
 
 #include "auth.h"
 
 #include "svn_private_config.h"
 
+#include "private/svn_auth_private.h"
+
 /* Helper for svn_config_{read|write}_auth_data.  Return a path to a
    file within ~/.subversion/auth/ that holds CRED_KIND credentials
    within REALMSTRING.  If no path is available *PATH will be set to
@@ -150,3 +152,126 @@ svn_config_write_auth_data(apr_hash_t *h
 
   return SVN_NO_ERROR;
 }
+
+
+svn_error_t *
+svn_config_walk_auth_data(const char *config_dir,
+                          svn_config_auth_walk_func_t walk_func,
+                          void *walk_baton,
+                          apr_pool_t *scratch_pool)
+{
+  int i;
+  apr_pool_t *iterpool;
+  svn_boolean_t finished = FALSE;
+  const char *cred_kinds[] =
+    {
+      SVN_AUTH_CRED_SIMPLE,
+      SVN_AUTH_CRED_USERNAME,
+      SVN_AUTH_CRED_SSL_CLIENT_CERT,
+      SVN_AUTH_CRED_SSL_CLIENT_CERT_PW,
+      SVN_AUTH_CRED_SSL_SERVER_TRUST,
+      NULL
+    };
+
+  if (! config_dir)
+    {
+      /* Can't locate the cache to clear */
+      return SVN_NO_ERROR;
+    }
+
+  iterpool = svn_pool_create(scratch_pool);
+  for (i = 0; cred_kinds[i]; i++)
+    {
+      const char *item_path;
+      const char *dir_path;
+      apr_hash_t *nodes;
+      svn_error_t *err;
+      apr_pool_t *itempool;
+      apr_hash_index_t *hi;
+
+      svn_pool_clear(iterpool);
+
+      if (finished)
+        break;
+
+      SVN_ERR(svn_auth__file_path(&item_path, cred_kinds[i], "!", config_dir,
+                                  iterpool));
+
+      dir_path = svn_dirent_dirname(item_path, iterpool);
+
+      err = svn_io_get_dirents3(&nodes, dir_path, TRUE, iterpool, iterpool);
+      if (err)
+        {
+          if (!APR_STATUS_IS_ENOENT(err->apr_err)
+              && !SVN__APR_STATUS_IS_ENOTDIR(err->apr_err))
+            return svn_error_trace(err);
+
+          svn_error_clear(err);
+          continue;
+        }
+
+      itempool = svn_pool_create(iterpool);
+      for (hi = apr_hash_first(iterpool, nodes); hi; hi = apr_hash_next(hi))
+        {
+          svn_io_dirent2_t *dirent = svn__apr_hash_index_val(hi);
+          svn_stream_t *stream;
+          apr_hash_t *creds_hash;
+          const svn_string_t *realm;
+          svn_boolean_t delete_file = FALSE;
+
+          if (finished)
+            break;
+
+          if (dirent->kind != svn_node_file)
+            continue;
+
+          svn_pool_clear(itempool);
+
+          item_path = svn_dirent_join(dir_path, svn__apr_hash_index_key(hi),
+                                      itempool);
+
+          err = svn_stream_open_readonly(&stream, item_path,
+                                         itempool, itempool);
+          if (err)
+            {
+              /* Ignore this file. There are no credentials in it anyway */
+              svn_error_clear(err);
+              continue;
+            }
+
+          creds_hash = apr_hash_make(itempool);
+          err = svn_hash_read2(creds_hash, stream,
+                               SVN_HASH_TERMINATOR, itempool);
+          err = svn_error_compose_create(err, svn_stream_close(stream));
+          if (err)
+            {
+              /* Ignore this file. There are no credentials in it anyway */
+              svn_error_clear(err);
+              continue;
+            }
+
+          realm = svn_hash_gets(creds_hash, SVN_CONFIG_REALMSTRING_KEY);
+          if (! realm)
+            continue; /* Not an auth file */
+
+          err = walk_func(&delete_file, walk_baton, cred_kinds[i],
+                          realm->data, creds_hash, itempool);
+          if (err && err->apr_err == SVN_ERR_CEASE_INVOCATION)
+            {
+              svn_error_clear(err);
+              err = SVN_NO_ERROR;
+              finished = TRUE;
+            }
+          SVN_ERR(err);
+
+          if (delete_file)
+            {
+              /* Delete the file on disk */
+              SVN_ERR(svn_io_remove_file2(item_path, TRUE, itempool));
+            }
+        }
+    }
+
+  svn_pool_destroy(iterpool);
+  return SVN_NO_ERROR;
+}

Modified: subversion/branches/verify-keep-going/subversion/libsvn_subr/config_file.c
URL: http://svn.apache.org/viewvc/subversion/branches/verify-keep-going/subversion/libsvn_subr/config_file.c?rev=1489765&r1=1489764&r2=1489765&view=diff
==============================================================================
--- subversion/branches/verify-keep-going/subversion/libsvn_subr/config_file.c (original)
+++ subversion/branches/verify-keep-going/subversion/libsvn_subr/config_file.c Wed Jun  5 09:22:43 2013
@@ -401,10 +401,13 @@ svn_config__parse_file(svn_config_t *cfg
                        svn_boolean_t must_exist, apr_pool_t *result_pool)
 {
   svn_error_t *err = SVN_NO_ERROR;
+  apr_file_t *apr_file;
   svn_stream_t *stream;
   apr_pool_t *scratch_pool = svn_pool_create(result_pool);
 
-  err = svn_stream_open_readonly(&stream, file, scratch_pool, scratch_pool);
+  /* Use unbuffered IO since we use our own buffering. */
+  err = svn_io_file_open(&apr_file, file, APR_READ, APR_OS_DEFAULT,
+                         scratch_pool);
 
   if (! must_exist && err && APR_STATUS_IS_ENOENT(err->apr_err))
     {
@@ -415,9 +418,10 @@ svn_config__parse_file(svn_config_t *cfg
   else
     SVN_ERR(err);
 
+  stream = svn_stream_from_aprfile2(apr_file, FALSE, scratch_pool);
   err = svn_config__parse_stream(cfg, stream, result_pool, scratch_pool);
 
-  if (err != SVN_NO_ERROR) 
+  if (err != SVN_NO_ERROR)
     {
       /* Add the filename to the error stack. */
       err = svn_error_createf(err->apr_err, err,
@@ -1152,6 +1156,16 @@ svn_config_ensure(const char *config_dir
         "### ra_local (the file:// scheme). The value represents the number" NL
         "### of MB used by the cache."                                       NL
         "# memory-cache-size = 16"                                           NL
+        "### Set diff-ignore-content-type to 'yes' to cause 'svn diff' to"   NL
+        "### attempt to show differences of all modified files regardless"   NL
+        "### of their MIME content type.  By default, Subversion will only"  NL
+        "### attempt to show differences for files believed to have human-"  NL
+        "### readable (non-binary) content.  This option is especially"      NL
+        "### useful when Subversion is configured (via the 'diff-cmd'"       NL
+        "### option) to employ an external differencing tool which is able"  NL
+        "### to show meaningful differences for binary file formats.  [New"  NL
+        "### in 1.9]"                                                        NL
+        "# diff-ignore-content-type = no"                                    NL
         ""                                                                   NL
         "### Section for configuring automatic properties."                  NL
         "[auto-props]"                                                       NL

Modified: subversion/branches/verify-keep-going/subversion/libsvn_subr/config_impl.h
URL: http://svn.apache.org/viewvc/subversion/branches/verify-keep-going/subversion/libsvn_subr/config_impl.h?rev=1489765&r1=1489764&r2=1489765&view=diff
==============================================================================
--- subversion/branches/verify-keep-going/subversion/libsvn_subr/config_impl.h (original)
+++ subversion/branches/verify-keep-going/subversion/libsvn_subr/config_impl.h Wed Jun  5 09:22:43 2013
@@ -67,6 +67,9 @@ struct svn_config_t
 
   /* Specifies whether section names are populated case sensitively. */
   svn_boolean_t section_names_case_sensitive;
+
+  /* Specifies whether option names are populated case sensitively. */
+  svn_boolean_t option_names_case_sensitive;
 };
 
 

Modified: subversion/branches/verify-keep-going/subversion/libsvn_subr/deprecated.c
URL: http://svn.apache.org/viewvc/subversion/branches/verify-keep-going/subversion/libsvn_subr/deprecated.c?rev=1489765&r1=1489764&r2=1489765&view=diff
==============================================================================
--- subversion/branches/verify-keep-going/subversion/libsvn_subr/deprecated.c (original)
+++ subversion/branches/verify-keep-going/subversion/libsvn_subr/deprecated.c Wed Jun  5 09:22:43 2013
@@ -1176,16 +1176,39 @@ svn_mergeinfo_intersect(svn_mergeinfo_t 
 }
 
 /*** From config.c ***/
+svn_error_t *
+svn_config_create(svn_config_t **cfgp,
+                  svn_boolean_t section_names_case_sensitive,
+                  apr_pool_t *result_pool)
+{
+  return svn_error_trace(svn_config_create2(cfgp,
+                                            section_names_case_sensitive,
+                                            FALSE,
+                                            result_pool));
+}
+
+svn_error_t *
+svn_config_read2(svn_config_t **cfgp, const char *file,
+                 svn_boolean_t must_exist,
+                 svn_boolean_t section_names_case_sensitive,
+                 apr_pool_t *result_pool)
+{
+  return svn_error_trace(svn_config_read3(cfgp, file,
+                                          must_exist,
+                                          section_names_case_sensitive,
+                                          FALSE,
+                                          result_pool));
+}
 
 svn_error_t *
 svn_config_read(svn_config_t **cfgp, const char *file,
                 svn_boolean_t must_exist,
-                apr_pool_t *pool)
+                apr_pool_t *result_pool)
 {
-  return svn_error_trace(svn_config_read2(cfgp, file,
+  return svn_error_trace(svn_config_read3(cfgp, file,
                                           must_exist,
-                                          FALSE,
-                                          pool));
+                                          FALSE, FALSE,
+                                          result_pool));
 }
 
 #ifdef SVN_DISABLE_FULL_VERSION_MATCH
@@ -1232,5 +1255,50 @@ svn_xml_make_header(svn_stringbuf_t **st
 void
 svn_utf_initialize(apr_pool_t *pool)
 {
-  svn_utf_initialize2(pool, FALSE);
+  svn_utf_initialize2(FALSE, pool);
 }
+
+svn_error_t *
+svn_subst_build_keywords(svn_subst_keywords_t *kw,
+                         const char *keywords_val,
+                         const char *rev,
+                         const char *url,
+                         apr_time_t date,
+                         const char *author,
+                         apr_pool_t *pool)
+{
+  apr_hash_t *kwhash;
+  const svn_string_t *val;
+
+  SVN_ERR(svn_subst_build_keywords2(&kwhash, keywords_val, rev,
+                                    url, date, author, pool));
+
+  /* The behaviour of pre-1.3 svn_subst_build_keywords, which we are
+   * replicating here, is to write to a slot in the svn_subst_keywords_t
+   * only if the relevant keyword was present in keywords_val, otherwise
+   * leaving that slot untouched. */
+
+  val = svn_hash_gets(kwhash, SVN_KEYWORD_REVISION_LONG);
+  if (val)
+    kw->revision = val;
+
+  val = svn_hash_gets(kwhash, SVN_KEYWORD_DATE_LONG);
+  if (val)
+    kw->date = val;
+
+  val = svn_hash_gets(kwhash, SVN_KEYWORD_AUTHOR_LONG);
+  if (val)
+    kw->author = val;
+
+  val = svn_hash_gets(kwhash, SVN_KEYWORD_URL_LONG);
+  if (val)
+    kw->url = val;
+
+  val = svn_hash_gets(kwhash, SVN_KEYWORD_ID);
+  if (val)
+    kw->id = val;
+
+  return SVN_NO_ERROR;
+}
+
+

Modified: subversion/branches/verify-keep-going/subversion/libsvn_subr/dirent_uri.c
URL: http://svn.apache.org/viewvc/subversion/branches/verify-keep-going/subversion/libsvn_subr/dirent_uri.c?rev=1489765&r1=1489764&r2=1489765&view=diff
==============================================================================
--- subversion/branches/verify-keep-going/subversion/libsvn_subr/dirent_uri.c (original)
+++ subversion/branches/verify-keep-going/subversion/libsvn_subr/dirent_uri.c Wed Jun  5 09:22:43 2013
@@ -1688,7 +1688,8 @@ svn_dirent_is_canonical(const char *dire
 static svn_boolean_t
 relpath_is_canonical(const char *relpath)
 {
-  const char *ptr = relpath, *seg = relpath;
+  const char *ptr = relpath;
+  apr_size_t i, len;
 
   /* RELPATH is canonical if it has:
    *  - no '.' segments
@@ -1696,36 +1697,32 @@ relpath_is_canonical(const char *relpath
    *  - no '//'
    */
 
-  if (*relpath == '\0')
-    return TRUE;
-
+  /* invalid beginnings */
   if (*ptr == '/')
     return FALSE;
 
-  /* Now validate the rest of the path. */
-  while(1)
-    {
-      apr_size_t seglen = ptr - seg;
-
-      if (seglen == 1 && *seg == '.')
-        return FALSE;  /*  /./   */
-
-      if (*ptr == '/' && *(ptr+1) == '/')
-        return FALSE;  /*  //    */
-
-      if (! *ptr && *(ptr - 1) == '/')
-        return FALSE;  /* foo/  */
+  if (ptr[0] == '.' && (ptr[1] == '/' || ptr[1] == '\0'))
+    return FALSE;
 
-      if (! *ptr)
-        break;
+  /* valid special cases */
+  len = strlen(ptr);
+  if (len < 2)
+    return TRUE;
 
-      if (*ptr == '/')
-        ptr++;
-      seg = ptr;
+  /* invalid endings */
+  if (ptr[len-1] == '/' || (ptr[len-1] == '.' && ptr[len-2] == '/'))
+    return FALSE;
 
-      while (*ptr && (*ptr != '/'))
-        ptr++;
-    }
+  /* Now validate the rest of the path. */
+  for (i = 0; i < len - 1; ++i)
+    if (ptr[i] == '/' && ptr[i+1] <= '/') /* '.' and '/' have smaller UTF-8
+                                             codes than most other chars */
+      {
+        if (ptr[i+1] == '/')
+          return FALSE;  /*  //   */
+        if (ptr[i+1] == '.' && ptr[i+2] == '/')
+          return FALSE;  /*  /./  */
+      }
 
   return TRUE;
 }
@@ -1794,7 +1791,7 @@ svn_uri_is_canonical(const char *uri, ap
   if (*ptr == '[')
     {
       ptr++;
-      while (*ptr == ':' 
+      while (*ptr == ':'
              || (*ptr >= '0' && *ptr <= '9')
              || (*ptr >= 'a' && *ptr <= 'f'))
         {

Modified: subversion/branches/verify-keep-going/subversion/libsvn_subr/eol.c
URL: http://svn.apache.org/viewvc/subversion/branches/verify-keep-going/subversion/libsvn_subr/eol.c?rev=1489765&r1=1489764&r2=1489765&view=diff
==============================================================================
--- subversion/branches/verify-keep-going/subversion/libsvn_subr/eol.c (original)
+++ subversion/branches/verify-keep-going/subversion/libsvn_subr/eol.c Wed Jun  5 09:22:43 2013
@@ -30,14 +30,12 @@
 #include "private/svn_eol_private.h"
 #include "private/svn_dep_compat.h"
 
-/* Machine-word-sized masks used in svn_eol__find_eol_start.
- */
 char *
 svn_eol__find_eol_start(char *buf, apr_size_t len)
 {
 #if !SVN_UNALIGNED_ACCESS_IS_OK
 
-  /* On some systems, we need to make sure that buf is properly aligned
+  /* On some systems, we need to make sure that BUF is properly aligned
    * for chunky data access. This overhead is still justified because
    * only lines tend to be tens of chars long.
    */
@@ -62,8 +60,8 @@ svn_eol__find_eol_start(char *buf, apr_s
     apr_uintptr_t r_test = chunk ^ SVN__R_MASK;
     apr_uintptr_t n_test = chunk ^ SVN__N_MASK;
 
-    /* A byte in SVN__R_TEST can by < 0x80, iff it has been \0 before
-     * (i.e. \r in *BUF). Dito for SVN__N_TEST. */
+    /* A byte in SVN__R_TEST can only be < 0x80, iff it has been \0 before
+     * (i.e. \r in *BUF). Ditto for SVN__N_TEST. */
     r_test |= (r_test & SVN__LOWER_7BITS_SET) + SVN__LOWER_7BITS_SET;
     n_test |= (n_test & SVN__LOWER_7BITS_SET) + SVN__LOWER_7BITS_SET;
 

Modified: subversion/branches/verify-keep-going/subversion/libsvn_subr/error.c
URL: http://svn.apache.org/viewvc/subversion/branches/verify-keep-going/subversion/libsvn_subr/error.c?rev=1489765&r1=1489764&r2=1489765&view=diff
==============================================================================
--- subversion/branches/verify-keep-going/subversion/libsvn_subr/error.c (original)
+++ subversion/branches/verify-keep-going/subversion/libsvn_subr/error.c Wed Jun  5 09:22:43 2013
@@ -454,6 +454,8 @@ svn_error_purge_tracing(svn_error_t *err
 #endif /* SVN_ERR__TRACING */
 }
 
+/* ### The logic around omitting (sic) apr_err= in maintainer mode is tightly
+   ### coupled to the current sole caller.*/
 static void
 print_error(svn_error_t *err, FILE *stream, const char *prefix)
 {
@@ -482,8 +484,11 @@ print_error(svn_error_t *err, FILE *stre
     }
 
   {
-    const char *symbolic_name = svn_error_symbolic_name(err->apr_err);
-    if (symbolic_name)
+    const char *symbolic_name;
+    if (svn_error__is_tracing_link(err))
+      /* Skip it; the error code will be printed by the real link. */
+      svn_error_clear(svn_cmdline_fprintf(stream, err->pool, ",\n"));
+    else if ((symbolic_name = svn_error_symbolic_name(err->apr_err)))
       svn_error_clear(svn_cmdline_fprintf(stream, err->pool,
                                           ": (apr_err=%s)\n", symbolic_name));
     else
@@ -613,6 +618,16 @@ void
 svn_handle_warning2(FILE *stream, svn_error_t *err, const char *prefix)
 {
   char buf[256];
+#ifdef SVN_DEBUG
+  const char *symbolic_name = svn_error_symbolic_name(err->apr_err);
+#endif
+
+#ifdef SVN_DEBUG
+  if (symbolic_name)
+    svn_error_clear(
+      svn_cmdline_fprintf(stream, err->pool, "%swarning: apr_err=%s\n",
+                          prefix, symbolic_name));
+#endif
 
   svn_error_clear(svn_cmdline_fprintf
                   (stream, err->pool,
@@ -663,10 +678,18 @@ svn_strerror(apr_status_t statcode, char
   return apr_strerror(statcode, buf, bufsize);
 }
 
+#ifdef SVN_DEBUG
+/* Defines svn__errno and svn__apr_errno */
+#include "errorcode.inc"
+#endif
+
 const char *
 svn_error_symbolic_name(apr_status_t statcode)
 {
   const err_defn *defn;
+#ifdef SVN_DEBUG
+  int i;
+#endif /* SVN_DEBUG */
 
   for (defn = error_table; defn->errdesc != NULL; ++defn)
     if (defn->errcode == (svn_errno_t)statcode)
@@ -676,6 +699,22 @@ svn_error_symbolic_name(apr_status_t sta
   if (statcode == SVN_NO_ERROR)
     return "SVN_NO_ERROR";
 
+#ifdef SVN_DEBUG
+  /* Try errno.h symbols. */
+  /* Linear search through a sorted array */
+  for (i = 0; i < sizeof(svn__errno) / sizeof(svn__errno[0]); i++)
+    if (svn__errno[i].errcode == (int)statcode)
+      return svn__errno[i].errname;
+
+  /* Try APR errors. */
+  /* Linear search through a sorted array */
+  for (i = 0; i < sizeof(svn__apr_errno) / sizeof(svn__apr_errno[0]); i++)
+    if (svn__apr_errno[i].errcode == (int)statcode)
+      return svn__apr_errno[i].errname;
+#endif /* SVN_DEBUG */
+
+  /* ### TODO: do we need APR_* error macros?  What about APR_TO_OS_ERROR()? */
+
   return NULL;
 }
 
@@ -732,6 +771,12 @@ svn_error_set_malfunction_handler(svn_er
   return old_malfunction_handler;
 }
 
+svn_error_malfunction_handler_t
+svn_error_get_malfunction_handler(void)
+{
+  return malfunction_handler;
+}
+
 /* Note: Although this is a "__" function, it is in the public ABI, so
  * we can never remove it or change its signature. */
 svn_error_t *

Modified: subversion/branches/verify-keep-going/subversion/libsvn_subr/hash.c
URL: http://svn.apache.org/viewvc/subversion/branches/verify-keep-going/subversion/libsvn_subr/hash.c?rev=1489765&r1=1489764&r2=1489765&view=diff
==============================================================================
--- subversion/branches/verify-keep-going/subversion/libsvn_subr/hash.c (original)
+++ subversion/branches/verify-keep-going/subversion/libsvn_subr/hash.c Wed Jun  5 09:22:43 2013
@@ -576,20 +576,16 @@ svn_hash__get_bool(apr_hash_t *hash, con
 
 /*** Optimized hash function ***/
 
-/* Optimized version of apr_hashfunc_default in APR 1.4.5 and earlier.
- * It assumes that the CPU has 32-bit multiplications with high throughput
- * of at least 1 operation every 3 cycles. Latency is not an issue. Another
- * optimization is a mildly unrolled main loop and breaking the dependency
- * chain within the loop.
- *
- * Note that most CPUs including Intel Atom, VIA Nano, ARM feature the
- * assumed pipelined multiplication circuitry. They can do one MUL every
- * or every other cycle.
- *
- * The performance is ultimately limited by the fact that most CPUs can
- * do only one LOAD and only one BRANCH operation per cycle. The best we
- * can do is to process one character per cycle - provided the processor
- * is wide enough to do 1 LOAD, COMPARE, BRANCH, MUL and ADD per cycle.
+/* apr_hashfunc_t optimized for the key that we use in SVN: paths and 
+ * property names.  Its primary goal is speed for keys of known length.
+ * 
+ * Since strings tend to spawn large value spaces (usually differ in many
+ * bits with differences spanning a larger section of the key), we can be
+ * quite sloppy extracting a hash value.  The more keys there are in a
+ * hash container, the more bits of the value returned by this function
+ * will be used.  For a small number of string keys, choosing bits from any 
+ * any fix location close to the tail of those keys would usually be good
+ * enough to prevent high collision rates.
  */
 static unsigned int
 hashfunc_compatible(const char *char_key, apr_ssize_t *klen)
@@ -600,37 +596,29 @@ hashfunc_compatible(const char *char_key
     apr_ssize_t i;
 
     if (*klen == APR_HASH_KEY_STRING)
+      *klen = strlen(char_key);
+
+#if SVN_UNALIGNED_ACCESS_IS_OK
+    for (p = key, i = *klen; i >= 4; i-=4, p+=4)
       {
-        for (p = key; ; p+=4)
-          {
-            unsigned int new_hash = hash * 33 * 33 * 33 * 33;
-            if (!p[0]) break;
-            new_hash += p[0] * 33 * 33 * 33;
-            if (!p[1]) break;
-            new_hash += p[1] * 33 * 33;
-            if (!p[2]) break;
-            new_hash += p[2] * 33;
-            if (!p[3]) break;
-            hash = new_hash + p[3];
-          }
-        for (; *p; p++)
-            hash = hash * 33 + *p;
+        apr_uint32_t chunk = *(apr_uint32_t *)p;
 
-        *klen = p - key;
+        /* the ">> 17" part gives upper bits in the chunk a chance to make
+           some impact as well */
+        hash = hash * 33 * 33 * 33 * 33 + chunk + (chunk >> 17);
       }
-    else
+#else
+    for (p = key, i = *klen; i >= 4; i-=4, p+=4)
       {
-        for (p = key, i = *klen; i >= 4; i-=4, p+=4)
-          {
-            hash = hash * 33 * 33 * 33 * 33
-                 + p[0] * 33 * 33 * 33
-                 + p[1] * 33 * 33
-                 + p[2] * 33
-                 + p[3];
-          }
-        for (; i; i--, p++)
-            hash = hash * 33 + *p;
+        hash = hash * 33 * 33 * 33 * 33
+              + p[0] * 33 * 33 * 33
+              + p[1] * 33 * 33
+              + p[2] * 33
+              + p[3];
       }
+#endif
+    for (; i; i--, p++)
+        hash = hash * 33 + *p;
 
     return hash;
 }

Modified: subversion/branches/verify-keep-going/subversion/libsvn_subr/io.c
URL: http://svn.apache.org/viewvc/subversion/branches/verify-keep-going/subversion/libsvn_subr/io.c?rev=1489765&r1=1489764&r2=1489765&view=diff
==============================================================================
--- subversion/branches/verify-keep-going/subversion/libsvn_subr/io.c (original)
+++ subversion/branches/verify-keep-going/subversion/libsvn_subr/io.c Wed Jun  5 09:22:43 2013
@@ -51,6 +51,10 @@
 #include <arch/win32/apr_arch_file_io.h>
 #endif
 
+#if APR_HAVE_FCNTL_H
+#include <fcntl.h>
+#endif
+
 #include "svn_hash.h"
 #include "svn_types.h"
 #include "svn_dirent_uri.h"
@@ -2069,7 +2073,7 @@ svn_io_file_lock2(const char *lock_file,
 
   /* locktype is never read after this block, so we don't need to bother
      setting it.  If that were to ever change, uncomment the following
-     block. 
+     block.
   if (nonblocking)
     locktype |= APR_FLOCK_NONBLOCK;
   */
@@ -2091,11 +2095,12 @@ svn_error_t *svn_io_file_flush_to_disk(a
 {
   apr_os_file_t filehand;
 
+  /* ### In apr 1.4+ we could delegate most of this function to
+         apr_file_sync(). The only major difference is that this doesn't
+         contain the retry loop for EINTR on linux. */
+
   /* First make sure that any user-space buffered data is flushed. */
-  SVN_ERR(do_io_file_wrapper_cleanup(file, apr_file_flush(file),
-                                     N_("Can't flush file '%s'"),
-                                     N_("Can't flush stream"),
-                                     pool));
+  SVN_ERR(svn_io_file_flush(file, pool));
 
   apr_os_file_get(&filehand, file);
 
@@ -2112,7 +2117,11 @@ svn_error_t *svn_io_file_flush_to_disk(a
       int rv;
 
       do {
+#ifdef F_FULLFSYNC
+        rv = fcntl(filehand, F_FULLFSYNC, 0);
+#else
         rv = fsync(filehand);
+#endif
       } while (rv == -1 && APR_STATUS_IS_EINTR(apr_get_os_error()));
 
       /* If the file is in a memory filesystem, fsync() may return
@@ -2795,10 +2804,23 @@ svn_io_wait_for_cmd(apr_proc_t *cmd_proc
 
   if (exitwhy)
     *exitwhy = exitwhy_val;
+  else if (APR_PROC_CHECK_SIGNALED(exitwhy_val)
+           && APR_PROC_CHECK_CORE_DUMP(exitwhy_val))
+    return svn_error_createf
+      (SVN_ERR_EXTERNAL_PROGRAM, NULL,
+       _("Process '%s' failed (exitwhy %d, signal %d, core dumped)"),
+       cmd, exitwhy_val, exitcode_val);
+  else if (APR_PROC_CHECK_SIGNALED(exitwhy_val))
+    return svn_error_createf
+      (SVN_ERR_EXTERNAL_PROGRAM, NULL,
+       _("Process '%s' failed (exitwhy %d, signal %d)"),
+       cmd, exitwhy_val, exitcode_val);
   else if (! APR_PROC_CHECK_EXIT(exitwhy_val))
+    /* Don't really know what happened here. */
     return svn_error_createf
       (SVN_ERR_EXTERNAL_PROGRAM, NULL,
-       _("Process '%s' failed (exitwhy %d)"), cmd, exitwhy_val);
+       _("Process '%s' failed (exitwhy %d, exitcode %d)"),
+       cmd, exitwhy_val, exitcode_val);
 
   if (exitcode)
     *exitcode = exitcode_val;
@@ -3408,6 +3430,16 @@ svn_io_file_write(apr_file_t *file, cons
      pool));
 }
 
+svn_error_t *
+svn_io_file_flush(apr_file_t *file,
+                  apr_pool_t *scratch_pool)
+{
+  return svn_error_trace(do_io_file_wrapper_cleanup(
+     file, apr_file_flush(file),
+     N_("Can't flush file '%s'"),
+     N_("Can't flush stream"),
+     scratch_pool));
+}
 
 svn_error_t *
 svn_io_file_write_full(apr_file_t *file, const void *buf,
@@ -3472,23 +3504,76 @@ svn_io_write_unique(const char **tmp_pat
 
   err = svn_io_file_write_full(new_file, buf, nbytes, NULL, pool);
 
-  /* ### BH: Windows doesn't have the race condition between the write and the
-     ###     rename that other operating systems might have. So allow windows
-     ###     to decide when it wants to perform the disk synchronization using
-     ###     the normal file locking and journaling filesystem rules.
-
-     ### Note that this function doesn't handle the rename, so we aren't even
-     ### sure that we really have to sync. */
-#ifndef WIN32
-  if (!err && nbytes > 0)
-    err = svn_io_file_flush_to_disk(new_file, pool);
-#endif
+  if (!err)
+    {
+      /* svn_io_file_flush_to_disk() can be very expensive, so use the
+         cheaper standard flush if the file is created as temporary file
+         anyway */
+      if (delete_when == svn_io_file_del_none)
+        err = svn_io_file_flush_to_disk(new_file, pool);
+      else
+        err = svn_io_file_flush(new_file, pool);
+    }
 
   return svn_error_trace(
                   svn_error_compose_create(err,
                                            svn_io_file_close(new_file, pool)));
 }
 
+svn_error_t *
+svn_io_write_atomic(const char *final_path,
+                    const void *buf,
+                    apr_size_t nbytes,
+                    const char *copy_perms_path,
+                    apr_pool_t *scratch_pool)
+{
+  apr_file_t *tmp_file;
+  const char *tmp_path;
+  svn_error_t *err;
+  const char *dirname = svn_dirent_dirname(final_path, scratch_pool);
+
+  SVN_ERR(svn_io_open_unique_file3(&tmp_file, &tmp_path, dirname,
+                                   svn_io_file_del_none,
+                                   scratch_pool, scratch_pool));
+
+  err = svn_io_file_write_full(tmp_file, buf, nbytes, NULL, scratch_pool);
+
+  if (!err)
+    err = svn_io_file_flush_to_disk(tmp_file, scratch_pool);
+
+  err = svn_error_compose_create(err,
+                                 svn_io_file_close(tmp_file, scratch_pool));
+
+  if (!err && copy_perms_path)
+    err = svn_io_copy_perms(copy_perms_path, tmp_path, scratch_pool);
+
+  if (err)
+    {
+      return svn_error_compose_create(err,
+                                      svn_io_remove_file2(tmp_path, FALSE,
+                                                          scratch_pool));
+    }
+
+  SVN_ERR(svn_io_file_rename(tmp_path, final_path, scratch_pool));
+
+#ifdef __linux__
+  {
+    /* Linux has the unusual feature that fsync() on a file is not
+       enough to ensure that a file's directory entries have been
+       flushed to disk; you have to fsync the directory as well.
+       On other operating systems, we'd only be asking for trouble
+       by trying to open and fsync a directory. */
+    apr_file_t *file;
+
+    SVN_ERR(svn_io_file_open(&file, dirname, APR_READ, APR_OS_DEFAULT,
+                             scratch_pool));
+    SVN_ERR(svn_io_file_flush_to_disk(file, scratch_pool));
+    SVN_ERR(svn_io_file_close(file, scratch_pool));
+  }
+#endif
+
+  return SVN_NO_ERROR;
+}
 
 svn_error_t *
 svn_io_file_trunc(apr_file_t *file, apr_off_t offset, apr_pool_t *pool)
@@ -3539,7 +3624,7 @@ svn_io_read_length_line(apr_file_t *file
       if (eol)
         {
           apr_off_t offset = (eol + 1 - buf) - (apr_off_t)bytes_read;
-          
+
           *eol = 0;
           *limit = total_read + (eol - buf);
 

Modified: subversion/branches/verify-keep-going/subversion/libsvn_subr/mergeinfo.c
URL: http://svn.apache.org/viewvc/subversion/branches/verify-keep-going/subversion/libsvn_subr/mergeinfo.c?rev=1489765&r1=1489764&r2=1489765&view=diff
==============================================================================
--- subversion/branches/verify-keep-going/subversion/libsvn_subr/mergeinfo.c (original)
+++ subversion/branches/verify-keep-going/subversion/libsvn_subr/mergeinfo.c Wed Jun  5 09:22:43 2013
@@ -611,6 +611,23 @@ svn_rangelist__parse(svn_rangelist_t **r
   return SVN_NO_ERROR;
 }
 
+/* Return TRUE, if all ranges in RANGELIST are in ascending order and do
+ * not overlap.  If this returns FALSE, you probaly want to qsort() the
+ * ranges and then call svn_rangelist__combine_adjacent_ranges().
+ */
+static svn_boolean_t
+is_rangelist_normalized(svn_rangelist_t *rangelist)
+{
+  int i;
+  svn_merge_range_t **ranges = (svn_merge_range_t **)rangelist->elts;
+
+  for (i = 0; i < rangelist->nelts-1; ++i)
+    if (ranges[i]->end >= ranges[i+1]->start)
+      return FALSE;
+
+  return TRUE;
+}
+
 svn_error_t *
 svn_rangelist__combine_adjacent_ranges(svn_rangelist_t *rangelist,
                                        apr_pool_t *scratch_pool)
@@ -692,9 +709,11 @@ parse_revision_line(const char **input, 
   if (*input != end)
     *input = *input + 1;
 
-  /* Sort the rangelist, combine adjacent ranges into single ranges,
-     and make sure there are no overlapping ranges. */
-  if (rangelist->nelts > 1)
+  /* Sort the rangelist, combine adjacent ranges into single ranges, and
+     make sure there are no overlapping ranges.  Luckily, most data in
+     svn:mergeinfo will already be in normalized form and we can skip this.
+   */
+  if (! is_rangelist_normalized(rangelist))
     {
       qsort(rangelist->elts, rangelist->nelts, rangelist->elt_size,
             svn_sort_compare_ranges);
@@ -2223,16 +2242,19 @@ svn_rangelist_dup(const svn_rangelist_t 
 
   /* allocate target range buffer with a single operation */
   svn_merge_range_t *copy = apr_palloc(pool, sizeof(*copy) * rangelist->nelts);
+
+  /* for efficiency, directly address source and target reference buffers */
+  svn_merge_range_t **source = (svn_merge_range_t **)(rangelist->elts);
+  svn_merge_range_t **target = (svn_merge_range_t **)(new_rl->elts);
   int i;
 
-  /* fill it iteratively and link it into the range list */
+  /* copy ranges iteratively and link them into the target range list */
   for (i = 0; i < rangelist->nelts; i++)
     {
-      memcpy(copy + i,
-             APR_ARRAY_IDX(rangelist, i, svn_merge_range_t *),
-             sizeof(*copy));
-      APR_ARRAY_PUSH(new_rl, svn_merge_range_t *) = copy + i;
+      copy[i] = *source[i];
+      target[i] = &copy[i];
     }
+  new_rl->nelts = rangelist->nelts;
 
   return new_rl;
 }
@@ -2463,15 +2485,8 @@ svn_mergeinfo__adjust_mergeinfo_rangelis
 
               if (range->start + offset > 0 && range->end + offset > 0)
                 {
-                  if (range->start + offset < 0)
-                    range->start = 0;
-                  else
-                    range->start = range->start + offset;
-
-                  if (range->end + offset < 0)
-                    range->end = 0;
-                  else
-                    range->end = range->end + offset;
+                  range->start = range->start + offset;
+                  range->end = range->end + offset;
                   APR_ARRAY_PUSH(adjusted_rangelist, svn_merge_range_t *) =
                     range;
                 }

Modified: subversion/branches/verify-keep-going/subversion/libsvn_subr/nls.c
URL: http://svn.apache.org/viewvc/subversion/branches/verify-keep-going/subversion/libsvn_subr/nls.c?rev=1489765&r1=1489764&r2=1489765&view=diff
==============================================================================
--- subversion/branches/verify-keep-going/subversion/libsvn_subr/nls.c (original)
+++ subversion/branches/verify-keep-going/subversion/libsvn_subr/nls.c Wed Jun  5 09:22:43 2013
@@ -56,7 +56,6 @@ svn_nls_init(void)
       char* utf8_path;
       const char* internal_path;
       apr_pool_t* pool;
-      apr_status_t apr_err;
       apr_size_t inwords, outbytes, outlength;
 
       apr_pool_create(&pool, 0);
@@ -99,10 +98,10 @@ svn_nls_init(void)
 
           if (outbytes == 0)
             {
-              err = svn_error_createf(apr_err, NULL,
-                                      _("Can't convert module path "
-                                        "to UTF-8 from UCS-2: '%s'"),
-                                      ucs2_path);
+              err = svn_error_wrap_apr(apr_get_os_error(),
+                                       _("Can't convert module path "
+                                         "to UTF-8 from UCS-2: '%s'"),
+                                       ucs2_path);
             }
           else
             {

Modified: subversion/branches/verify-keep-going/subversion/libsvn_subr/path.c
URL: http://svn.apache.org/viewvc/subversion/branches/verify-keep-going/subversion/libsvn_subr/path.c?rev=1489765&r1=1489764&r2=1489765&view=diff
==============================================================================
--- subversion/branches/verify-keep-going/subversion/libsvn_subr/path.c (original)
+++ subversion/branches/verify-keep-going/subversion/libsvn_subr/path.c Wed Jun  5 09:22:43 2013
@@ -1164,11 +1164,8 @@ svn_path_cstring_to_utf8(const char **pa
 }
 
 
-/* Return a copy of PATH, allocated from POOL, for which control
-   characters have been escaped using the form \NNN (where NNN is the
-   octal representation of the byte's ordinal value).  */
-static const char *
-illegal_path_escape(const char *path, apr_pool_t *pool)
+const char *
+svn_path_illegal_path_escape(const char *path, apr_pool_t *pool)
 {
   svn_stringbuf_t *retstr;
   apr_size_t i, copied = 0;
@@ -1194,7 +1191,7 @@ illegal_path_escape(const char *path, ap
                                   i - copied);
 
       /* Make sure buffer is big enough for '\' 'N' 'N' 'N' (and NUL) */
-      svn_stringbuf_ensure(retstr, retstr->len + 4);
+      svn_stringbuf_ensure(retstr, retstr->len + 5);
       /*### The backslash separator doesn't work too great with Windows,
          but it's what we'll use for consistency with invalid utf8
          formatting (until someone has a better idea) */
@@ -1228,11 +1225,11 @@ svn_path_check_valid(const char *path, a
     {
       if (svn_ctype_iscntrl(*c))
         {
-          return svn_error_createf
-            (SVN_ERR_FS_PATH_SYNTAX, NULL,
+          return svn_error_createf(SVN_ERR_FS_PATH_SYNTAX, NULL,
              _("Invalid control character '0x%02x' in path '%s'"),
              (unsigned char)*c,
-             illegal_path_escape(svn_dirent_local_style(path, pool), pool));
+             svn_path_illegal_path_escape(svn_dirent_local_style(path, pool),
+                                          pool));
         }
     }
 

Modified: subversion/branches/verify-keep-going/subversion/libsvn_subr/prompt.c
URL: http://svn.apache.org/viewvc/subversion/branches/verify-keep-going/subversion/libsvn_subr/prompt.c?rev=1489765&r1=1489764&r2=1489765&view=diff
==============================================================================
--- subversion/branches/verify-keep-going/subversion/libsvn_subr/prompt.c (original)
+++ subversion/branches/verify-keep-going/subversion/libsvn_subr/prompt.c Wed Jun  5 09:22:43 2013
@@ -236,7 +236,6 @@ terminal_puts(const char *string, termin
               apr_pool_t *pool)
 {
   svn_error_t *err;
-  apr_status_t status;
   const char *converted;
 
   err = svn_cmdline_cstring_from_utf8(&converted, string, pool);
@@ -255,13 +254,10 @@ terminal_puts(const char *string, termin
     }
 #endif
 
-  status = apr_file_write_full(terminal->outfd, converted,
-                               strlen(converted), NULL);
-  if (!status)
-    status = apr_file_flush(terminal->outfd);
-  if (status)
-    return svn_error_wrap_apr(status, _("Can't write to terminal"));
-  return SVN_NO_ERROR;
+  SVN_ERR(svn_io_file_write_full(terminal->outfd, converted,
+                                 strlen(converted), NULL, pool));
+
+  return svn_error_trace(svn_io_file_flush(terminal->outfd, pool));
 }
 
 /* These codes can be returned from terminal_getc instead of a character. */
@@ -575,7 +571,7 @@ prompt(const char **result,
     {
       /* If terminal echo was turned off, make sure future output
          to the terminal starts on a new line, as expected. */
-      terminal_puts(APR_EOL_STR, terminal, pool);
+      SVN_ERR(terminal_puts(APR_EOL_STR, terminal, pool));
     }
   SVN_ERR(terminal_close(terminal));
 

Modified: subversion/branches/verify-keep-going/subversion/libsvn_subr/pseudo_md5.c
URL: http://svn.apache.org/viewvc/subversion/branches/verify-keep-going/subversion/libsvn_subr/pseudo_md5.c?rev=1489765&r1=1489764&r2=1489765&view=diff
==============================================================================
--- subversion/branches/verify-keep-going/subversion/libsvn_subr/pseudo_md5.c (original)
+++ subversion/branches/verify-keep-going/subversion/libsvn_subr/pseudo_md5.c Wed Jun  5 09:22:43 2013
@@ -125,11 +125,11 @@
   }
 
 /* The idea of the functions below is as follows:
- * 
+ *
  * - The core MD5 algorithm does not assume that the "important" data
  *   is at the begin of the encryption block, followed by e.g. 0.
  *   Instead, all bits are equally relevant.
- * 
+ *
  * - If some bytes in the input are known to be 0, we may hard-code them.
  *   With the previous property, it is safe to move them to the upper end
  *   of the encryption block to maximize the number of steps that can be
@@ -153,7 +153,7 @@
  * - Collisions between pseudo-MD5 and pseudo-MD5 as well as pseudo-MD5
  *   and standard MD5 are as likely as any other MD5 collision.
  */
-  
+
 void svn__pseudo_md5_15(apr_uint32_t digest[4],
                         const apr_uint32_t x[4])
 {
@@ -164,7 +164,7 @@ void svn__pseudo_md5_15(apr_uint32_t dig
 
     /* make sure byte 63 gets the marker independently of BE / LE */
     apr_uint32_t x3n = x[3] ^ 0xffffffff;
-    
+
     /* Round 1 */
     FF(a, b, c, d, 0,    S11, 0xd76aa478); /* 1 */
     FF(d, a, b, c, 0,    S12, 0xe8c7b756); /* 2 */
@@ -253,7 +253,7 @@ void svn__pseudo_md5_31(apr_uint32_t dig
 
     /* make sure byte 63 gets the marker independently of BE / LE */
     apr_uint32_t x7n = x[7] ^ 0xfefefefe;
-    
+
     /* Round 1 */
     FF(a, b, c, d, 0,    S11, 0xd76aa478); /* 1 */
     FF(d, a, b, c, 0,    S12, 0xe8c7b756); /* 2 */
@@ -342,7 +342,7 @@ void svn__pseudo_md5_63(apr_uint32_t dig
 
     /* make sure byte 63 gets the marker independently of BE / LE */
     apr_uint32_t x15n = x[15] ^ 0xfcfcfcfc;
-    
+
     /* Round 1 */
     FF(a, b, c, d, x[0],  S11, 0xd76aa478); /* 1 */
     FF(d, a, b, c, x[1],  S12, 0xe8c7b756); /* 2 */

Modified: subversion/branches/verify-keep-going/subversion/libsvn_subr/simple_providers.c
URL: http://svn.apache.org/viewvc/subversion/branches/verify-keep-going/subversion/libsvn_subr/simple_providers.c?rev=1489765&r1=1489764&r2=1489765&view=diff
==============================================================================
--- subversion/branches/verify-keep-going/subversion/libsvn_subr/simple_providers.c (original)
+++ subversion/branches/verify-keep-going/subversion/libsvn_subr/simple_providers.c Wed Jun  5 09:22:43 2013
@@ -511,162 +511,6 @@ simple_save_creds(svn_boolean_t *saved,
                                           pool);
 }
 
-svn_error_t *
-svn_auth__simple_cleanup_walk(svn_auth_baton_t *baton,
-                              svn_auth_cleanup_func_t cleanup_func,
-                              void *cleanup_baton,
-                              apr_hash_t *creds_cache,
-                              apr_pool_t *scratch_pool)
-{
-  const char *config_dir;
-  int i;
-  apr_pool_t *iterpool;
-
-  const char *cred_kinds[] =
-  {
-      SVN_AUTH_CRED_SIMPLE,
-      SVN_AUTH_CRED_USERNAME,
-      SVN_AUTH_CRED_SSL_CLIENT_CERT,
-      SVN_AUTH_CRED_SSL_CLIENT_CERT_PW,
-      SVN_AUTH_CRED_SSL_SERVER_TRUST,
-      NULL
-  };
-
-  config_dir = svn_auth_get_parameter(baton, SVN_AUTH_PARAM_CONFIG_DIR);
-  if (! config_dir)
-    {
-      /* Can't locate the cache to clear */
-      return SVN_NO_ERROR;
-    }
-
-
-  /* ### FIXME: This is just plain wrong.  This function has no
-     ### business iterating over any credential type except
-     ### SVN_AUTH_CRED_SIMPLE.  The side-effect of this overreach is
-     ### that today, someone can open an auth baton with just a single
-     ### svn.simple provider, and this function -- which claims to be
-     ### cleaning up creds as supported by the provider -- will
-     ### happily go about peeking into other credential types, too,
-     ### even those for which no provider has been registered.
-     ###
-     ### In my opinion, svn_auth_cleanup_auth() should iterate over
-     ### the registered providers, calling per-provider functions that
-     ### take care of their own cleanup, exactly as the rest of this
-     ### subsystem uses per-provider functions to handle credential
-     ### get/set.  Alternatively, svn_auth_cleanup_auth() should stop
-     ### masquerading as if the auth_baton (and its provider table) is
-     ### valuable at all, and just accept the 'config_dir' as input so
-     ### it can do it's tree crawl, file parsing, and file removal.
-     ###
-     ### --cmpilato
-  */
-
-  iterpool = svn_pool_create(scratch_pool);
-  for (i = 0; cred_kinds[i]; i++)
-    {
-      const char *item_path;
-      const char *dir_path;
-      apr_hash_t *nodes;
-      svn_error_t *err;
-      apr_pool_t *itempool;
-      apr_hash_index_t *hi;
-
-      svn_pool_clear(iterpool);
-
-      SVN_ERR(svn_auth__file_path(&item_path, cred_kinds[i], "!", config_dir,
-                                  iterpool));
-
-      dir_path = svn_dirent_dirname(item_path, iterpool);
-
-      err = svn_io_get_dirents3(&nodes, dir_path, TRUE, iterpool, iterpool);
-      if (err)
-        {
-          if (!APR_STATUS_IS_ENOENT(err->apr_err)
-              && !SVN__APR_STATUS_IS_ENOTDIR(err->apr_err))
-            return svn_error_trace(err);
-
-          svn_error_clear(err);
-          continue;
-        }
-
-      itempool = svn_pool_create(iterpool);
-      for (hi = apr_hash_first(iterpool, nodes); hi; hi = apr_hash_next(hi))
-        {
-          svn_io_dirent2_t *dirent = svn__apr_hash_index_val(hi);
-          svn_stream_t *stream;
-          apr_hash_t *creds_hash;
-          const svn_string_t *realm, *passtype;
-          svn_boolean_t delete_file = FALSE;
-
-          if (dirent->kind != svn_node_file)
-            continue;
-
-          svn_pool_clear(itempool);
-
-          item_path = svn_dirent_join(dir_path, svn__apr_hash_index_key(hi),
-                                      itempool);
-
-          err = svn_stream_open_readonly(&stream, item_path, itempool, itempool);
-          if (err)
-            {
-              /* Ignore this file. There are no credentials in it anyway */
-              svn_error_clear(err);
-              continue;
-            }
-
-          creds_hash = apr_hash_make(itempool);
-          err = svn_hash_read2(creds_hash, stream, SVN_HASH_TERMINATOR, itempool);
-          err = svn_error_compose_create(err, svn_stream_close(stream));
-          if (err)
-            {
-              /* Ignore this file. There are no credentials in it anyway */
-              svn_error_clear(err);
-              continue;
-            }
-
-          realm = svn_hash_gets(creds_hash, SVN_CONFIG_REALMSTRING_KEY);
-          if (! realm)
-            continue; /* Not an auth file */
-
-          /* With the exception of the "windows" and "simple" password
-             types, a non-empty "passtype" value means that this
-             record is just metadata for credentials cached elsewhere.
-             In order to avoid giving the impression that we're able
-             to clear cached data that we really aren't, we'll skip
-             such records. */
-          passtype = svn_hash_gets(creds_hash, AUTHN_PASSTYPE_KEY);
-          if (passtype && passtype->data
-              && (! ((strcmp(passtype->data,
-                             SVN_AUTH__WINCRYPT_PASSWORD_TYPE) == 0)
-                     || (strcmp(passtype->data,
-                                SVN_AUTH__SIMPLE_PASSWORD_TYPE) == 0))))
-            continue; 
-          
-          SVN_ERR(cleanup_func(&delete_file, cleanup_baton, cred_kinds[i],
-                               realm->data,
-                               passtype ? passtype->data 
-                                        : SVN_AUTH__SIMPLE_PASSWORD_TYPE,
-                               itempool));
-
-          if (delete_file)
-            {
-              /* Delete from the credential hash */
-              const char *cache_key = apr_pstrcat(itempool, cred_kinds[0], ":",
-                                                  realm->data, (char *)NULL);
-
-              svn_hash_sets(creds_cache, cache_key, NULL);
-              
-              /* And the file on disk */
-              SVN_ERR(svn_io_remove_file2(item_path, TRUE, itempool));
-            }
-        }
-    }
-
-  svn_pool_destroy(iterpool);
-  return SVN_NO_ERROR;
-}
-
-
 static const svn_auth_provider_t simple_provider = {
   SVN_AUTH_CRED_SIMPLE,
   simple_first_creds,

Modified: subversion/branches/verify-keep-going/subversion/libsvn_subr/sqlite.c
URL: http://svn.apache.org/viewvc/subversion/branches/verify-keep-going/subversion/libsvn_subr/sqlite.c?rev=1489765&r1=1489764&r2=1489765&view=diff
==============================================================================
--- subversion/branches/verify-keep-going/subversion/libsvn_subr/sqlite.c (original)
+++ subversion/branches/verify-keep-going/subversion/libsvn_subr/sqlite.c Wed Jun  5 09:22:43 2013
@@ -38,6 +38,11 @@
 #include "private/svn_skel.h"
 #include "private/svn_token.h"
 
+#ifdef SVN_UNICODE_NORMALIZATION_FIXES
+#include "private/svn_utf_private.h"
+#include "private/svn_string_private.h"
+#endif /* SVN_UNICODE_NORMALIZATION_FIXES */
+
 #ifdef SQLITE3_DEBUG
 #include "private/svn_debug.h"
 #endif
@@ -60,6 +65,13 @@ extern int (*const svn_sqlite3__api_conf
 #error SQLite is too old -- version 3.7.12 is the minimum required version
 #endif
 
+#ifdef SVN_UNICODE_NORMALIZATION_FIXES
+/* Limit the length of a GLOB or LIKE pattern. */
+#ifndef SQLITE_MAX_LIKE_PATTERN_LENGTH
+# define SQLITE_MAX_LIKE_PATTERN_LENGTH 50000
+#endif
+#endif /* SVN_UNICODE_NORMALIZATION_FIXES */
+
 const char *
 svn_sqlite__compiled_version(void)
 {
@@ -104,6 +116,13 @@ struct svn_sqlite__db_t
   int nbr_statements;
   svn_sqlite__stmt_t **prepared_stmts;
   apr_pool_t *state_pool;
+
+#ifdef SVN_UNICODE_NORMALIZATION_FIXES
+  /* Buffers for SQLite extensoins. */
+  svn_membuf_t sqlext_buf1;
+  svn_membuf_t sqlext_buf2;
+  svn_membuf_t sqlext_buf3;
+#endif /* SVN_UNICODE_NORMALIZATION_FIXES */
 };
 
 struct svn_sqlite__stmt_t
@@ -873,6 +892,99 @@ close_apr(void *data)
   return APR_SUCCESS;
 }
 
+#ifdef SVN_UNICODE_NORMALIZATION_FIXES
+/* Unicode normalizing collation for WC paths */
+static int
+collate_ucs_nfd(void *baton,
+                int len1, const void *key1,
+                int len2, const void *key2)
+{
+  svn_sqlite__db_t *db = baton;
+  int result;
+
+  if (svn_utf__normcmp(key1, len1, key2, len2,
+                       &db->sqlext_buf1, &db->sqlext_buf2, &result))
+    {
+      /* There is really nothing we can do here if an error occurs
+         during Unicode normalizetion, and attempting to recover could
+         result in the wc.db index being corrupted. Presumably this
+         can only happen if the index already contains invalid UTF-8
+         strings, which should never happen in any case ... */
+      SVN_ERR_MALFUNCTION_NO_RETURN();
+    }
+
+  return result;
+}
+
+static void
+glob_like_ucs_nfd_common(sqlite3_context *context,
+                         int argc, sqlite3_value **argv,
+                         svn_boolean_t sql_like)
+{
+  svn_sqlite__db_t *const db = sqlite3_user_data(context);
+
+  const char *const pattern = (void*)sqlite3_value_text(argv[0]);
+  const apr_size_t pattern_len = sqlite3_value_bytes(argv[0]);
+  const char *const string = (void*)sqlite3_value_text(argv[1]);
+  const apr_size_t string_len = sqlite3_value_bytes(argv[1]);
+
+  const char *escape = NULL;
+  apr_size_t escape_len = 0;
+
+  svn_boolean_t match;
+  svn_error_t *err;
+
+  if (pattern_len > SQLITE_MAX_LIKE_PATTERN_LENGTH)
+    {
+      sqlite3_result_error(context, "LIKE or GLOB pattern too complex", -1);
+      return;
+    }
+
+  if (argc == 3 && sql_like)
+    {
+      escape = (void*)sqlite3_value_text(argv[2]);
+      escape_len = sqlite3_value_bytes(argv[2]);
+    }
+
+  if (pattern && string)
+    {
+      err = svn_utf__glob(pattern, pattern_len, string, string_len,
+                          escape, escape_len, sql_like,
+                          &db->sqlext_buf1, &db->sqlext_buf2, &db->sqlext_buf3,
+                          &match);
+
+      if (err)
+        {
+          const char *errmsg;
+          svn_membuf__ensure(&db->sqlext_buf1, 512);
+          errmsg = svn_err_best_message(err,
+                                        db->sqlext_buf1.data,
+                                        db->sqlext_buf1.size - 1);
+          svn_error_clear(err);
+          sqlite3_result_error(context, errmsg, -1);
+          return;
+        }
+
+      sqlite3_result_int(context, match);
+    }
+}
+
+/* Unicode normalizing implementation of GLOB */
+static void
+glob_ucs_nfd(sqlite3_context *context,
+             int argc, sqlite3_value **argv)
+{
+  glob_like_ucs_nfd_common(context, argc, argv, FALSE);
+}
+
+/* Unicode normalizing implementation of LIKE */
+static void
+like_ucs_nfd(sqlite3_context *context,
+             int argc, sqlite3_value **argv)
+{
+  glob_like_ucs_nfd_common(context, argc, argv, TRUE);
+}
+#endif /* SVN_UNICODE_NORMALIZATION_FIXES */
 
 svn_error_t *
 svn_sqlite__open(svn_sqlite__db_t **db, const char *path,
@@ -887,6 +999,28 @@ svn_sqlite__open(svn_sqlite__db_t **db, 
 
   SVN_ERR(internal_open(&(*db)->db3, path, mode, scratch_pool));
 
+#ifdef SVN_UNICODE_NORMALIZATION_FIXES
+  /* Create extension buffers with space for 200 UCS-4 characters. */
+  svn_membuf__create(&(*db)->sqlext_buf1, 800, result_pool);
+  svn_membuf__create(&(*db)->sqlext_buf2, 800, result_pool);
+  svn_membuf__create(&(*db)->sqlext_buf3, 800, result_pool);
+
+  /* Register collation and LIKE and GLOB operator replacements. */
+  SQLITE_ERR(sqlite3_create_collation((*db)->db3,
+                                      "svn-ucs-nfd", SQLITE_UTF8,
+                                      *db, collate_ucs_nfd),
+             *db);
+  SQLITE_ERR(sqlite3_create_function((*db)->db3, "glob", 2, SQLITE_UTF8,
+                                     *db, glob_ucs_nfd, NULL, NULL),
+             *db);
+  SQLITE_ERR(sqlite3_create_function((*db)->db3, "like", 2, SQLITE_UTF8,
+                                     *db, like_ucs_nfd, NULL, NULL),
+             *db);
+  SQLITE_ERR(sqlite3_create_function((*db)->db3, "like", 3, SQLITE_UTF8,
+                                     *db, like_ucs_nfd, NULL, NULL),
+             *db);
+#endif /* SVN_UNICODE_NORMALIZATION_FIXES */
+
 #ifdef SQLITE3_DEBUG
   sqlite3_trace((*db)->db3, sqlite_tracer, (*db)->db3);
 #endif

Modified: subversion/branches/verify-keep-going/subversion/libsvn_subr/sqlite3wrapper.c
URL: http://svn.apache.org/viewvc/subversion/branches/verify-keep-going/subversion/libsvn_subr/sqlite3wrapper.c?rev=1489765&r1=1489764&r2=1489765&view=diff
==============================================================================
--- subversion/branches/verify-keep-going/subversion/libsvn_subr/sqlite3wrapper.c (original)
+++ subversion/branches/verify-keep-going/subversion/libsvn_subr/sqlite3wrapper.c Wed Jun  5 09:22:43 2013
@@ -39,6 +39,17 @@
 #      pragma GCC diagnostic ignored "-Wshorten-64-to-32"
 #    endif
 #  endif
+#  ifdef __APPLE__
+#    include <Availability.h>
+#    if __MAC_OS_X_VERSION_MIN_REQUIRED < 1060
+       /* <libkern/OSAtomic.h> is included on OS X by sqlite3.c, and
+          on old systems (Leopard or older), it cannot be compiled
+          with -std=c89 because it uses inline. This is a work-around. */
+#      define inline __inline__
+#      include <libkern/OSAtomic.h>
+#      undef inline
+#    endif
+#  endif
 #  include <sqlite3.c>
 #  if __GNUC__ > 4 || (__GNUC__ == 4 && (__GNUC_MINOR__ >= 6))
 #    pragma GCC diagnostic pop

Modified: subversion/branches/verify-keep-going/subversion/libsvn_subr/ssl_client_cert_providers.c
URL: http://svn.apache.org/viewvc/subversion/branches/verify-keep-going/subversion/libsvn_subr/ssl_client_cert_providers.c?rev=1489765&r1=1489764&r2=1489765&view=diff
==============================================================================
--- subversion/branches/verify-keep-going/subversion/libsvn_subr/ssl_client_cert_providers.c (original)
+++ subversion/branches/verify-keep-going/subversion/libsvn_subr/ssl_client_cert_providers.c Wed Jun  5 09:22:43 2013
@@ -79,13 +79,12 @@ ssl_client_cert_file_first_credentials(v
 }
 
 
-static const svn_auth_provider_t ssl_client_cert_file_provider =
-  {
-    SVN_AUTH_CRED_SSL_CLIENT_CERT,
-    ssl_client_cert_file_first_credentials,
-    NULL,
-    NULL
-  };
+static const svn_auth_provider_t ssl_client_cert_file_provider = {
+  SVN_AUTH_CRED_SSL_CLIENT_CERT,
+  ssl_client_cert_file_first_credentials,
+  NULL,
+  NULL
+};
 
 
 /*** Public API to SSL file providers. ***/

Modified: subversion/branches/verify-keep-going/subversion/libsvn_subr/ssl_server_trust_providers.c
URL: http://svn.apache.org/viewvc/subversion/branches/verify-keep-going/subversion/libsvn_subr/ssl_server_trust_providers.c?rev=1489765&r1=1489764&r2=1489765&view=diff
==============================================================================
--- subversion/branches/verify-keep-going/subversion/libsvn_subr/ssl_server_trust_providers.c (original)
+++ subversion/branches/verify-keep-going/subversion/libsvn_subr/ssl_server_trust_providers.c Wed Jun  5 09:22:43 2013
@@ -149,9 +149,9 @@ ssl_server_trust_file_save_credentials(s
 
 static const svn_auth_provider_t ssl_server_trust_file_provider = {
   SVN_AUTH_CRED_SSL_SERVER_TRUST,
-  &ssl_server_trust_file_first_credentials,
+  ssl_server_trust_file_first_credentials,
   NULL,
-  &ssl_server_trust_file_save_credentials,
+  ssl_server_trust_file_save_credentials,
 };
 
 

Modified: subversion/branches/verify-keep-going/subversion/libsvn_subr/stream.c
URL: http://svn.apache.org/viewvc/subversion/branches/verify-keep-going/subversion/libsvn_subr/stream.c?rev=1489765&r1=1489764&r2=1489765&view=diff
==============================================================================
--- subversion/branches/verify-keep-going/subversion/libsvn_subr/stream.c (original)
+++ subversion/branches/verify-keep-going/subversion/libsvn_subr/stream.c Wed Jun  5 09:22:43 2013
@@ -21,8 +21,6 @@
  * ====================================================================
  */
 
-#include "svn_private_config.h"
-
 #include <assert.h>
 #include <stdio.h>
 
@@ -42,6 +40,7 @@
 #include "svn_utf.h"
 #include "svn_checksum.h"
 #include "svn_path.h"
+#include "svn_private_config.h"
 #include "private/svn_error_private.h"
 #include "private/svn_eol_private.h"
 #include "private/svn_io_private.h"
@@ -1677,6 +1676,9 @@ typedef struct lazyopen_baton_t {
   svn_stream_t *real_stream;
   apr_pool_t *pool;
 
+  /* Whether to open the wrapped stream on a close call. */
+  svn_boolean_t open_on_close;
+
 } lazyopen_baton_t;
 
 
@@ -1748,7 +1750,9 @@ close_handler_lazyopen(void *baton)
 {
   lazyopen_baton_t *b = baton;
 
-  if (b->real_stream != NULL)
+  if (b->open_on_close)
+    SVN_ERR(lazyopen_if_unopened(b));
+  if (b->real_stream)
     SVN_ERR(svn_stream_close(b->real_stream));
 
   return SVN_NO_ERROR;
@@ -1797,6 +1801,7 @@ is_buffered_lazyopen(void *baton)
 svn_stream_t *
 svn_stream_lazyopen_create(svn_stream_lazyopen_func_t open_func,
                            void *open_baton,
+                           svn_boolean_t open_on_close,
                            apr_pool_t *result_pool)
 {
   lazyopen_baton_t *lob = apr_pcalloc(result_pool, sizeof(*lob));
@@ -1806,6 +1811,7 @@ svn_stream_lazyopen_create(svn_stream_la
   lob->open_baton = open_baton;
   lob->real_stream = NULL;
   lob->pool = result_pool;
+  lob->open_on_close = open_on_close;
 
   stream = svn_stream_create(lob, result_pool);
   svn_stream_set_read(stream, read_handler_lazyopen);
@@ -1815,6 +1821,6 @@ svn_stream_lazyopen_create(svn_stream_la
   svn_stream_set_mark(stream, mark_handler_lazyopen);
   svn_stream_set_seek(stream, seek_handler_lazyopen);
   svn_stream__set_is_buffered(stream, is_buffered_lazyopen);
-  
+
   return stream;
 }

Modified: subversion/branches/verify-keep-going/subversion/libsvn_subr/string.c
URL: http://svn.apache.org/viewvc/subversion/branches/verify-keep-going/subversion/libsvn_subr/string.c?rev=1489765&r1=1489764&r2=1489765&view=diff
==============================================================================
--- subversion/branches/verify-keep-going/subversion/libsvn_subr/string.c (original)
+++ subversion/branches/verify-keep-going/subversion/libsvn_subr/string.c Wed Jun  5 09:22:43 2013
@@ -1027,6 +1027,36 @@ svn__strtoff(apr_off_t *offset, const ch
 #endif
 }
 
+unsigned long
+svn__strtoul(const char *buffer, char **end)
+{
+  unsigned long result = 0;
+
+  /* this loop will execute in just 2 CPU cycles, confirmed by measurement:
+     7 macro-ops (max 4 / cycle => 2 cycles)
+       1 load (max 1 / cycle)
+       1 jumps (compare + conditional jump == 1 macro op; max 1 / cycle)
+       2 arithmetic ops (subtract, increment; max 3 / cycle)
+       2 scale-and-add AGU ops (max 3 / cycle)
+       1 compiler-generated move operation
+     dependency chain: temp = result * 4 + result; result = temp * 2 + c
+                       (2 ops with latency 1 => 2 cycles)
+   */
+  while (1)
+    {
+      unsigned long c = *buffer - '0';
+      if (c > 9)
+        break;
+
+      result = result * 10 + c;
+      ++buffer;
+    }
+
+  *end = (char *)buffer;
+  return result;
+}
+
+
 /* "Precalculated" itoa values for 2 places (including leading zeros).
  * For maximum performance, make sure all table entries are word-aligned.
  */
@@ -1242,7 +1272,7 @@ svn_string__similarity(const svn_string_
       /* Calculate LCS length of the remainder */
       for (pstr = stra; pstr < enda; ++pstr)
         {
-          int i;
+          apr_size_t i;
           for (i = 1; i <= slots; ++i)
             {
               if (*pstr == strb[i-1])

Modified: subversion/branches/verify-keep-going/subversion/libsvn_subr/subst.c
URL: http://svn.apache.org/viewvc/subversion/branches/verify-keep-going/subversion/libsvn_subr/subst.c?rev=1489765&r1=1489764&r2=1489765&view=diff
==============================================================================
--- subversion/branches/verify-keep-going/subversion/libsvn_subr/subst.c (original)
+++ subversion/branches/verify-keep-going/subversion/libsvn_subr/subst.c Wed Jun  5 09:22:43 2013
@@ -50,6 +50,7 @@
 #include "svn_private_config.h"
 
 #include "private/svn_string_private.h"
+#include "private/svn_eol_private.h"
 
 /**
  * The textual elements of a detranslated special file.  One of these
@@ -136,16 +137,24 @@ svn_subst_translation_required(svn_subst
  * %b basename of the URL of this file
  * %d short format of date of this revision
  * %D long format of date of this revision
+ * %P path relative to root of repos
  * %r number of this revision
+ * %R root url of repository
  * %u URL of this file
+ * %_ a space
  * %% a literal %
  *
+ * The following special format codes are also recognized:
+ *   %H is equivalent to %P%_%r%_%d%_%a
+ *   %I is equivalent to %b%_%r%_%d%_%a
+ *
  * All memory is allocated out of @a pool.
  */
 static svn_string_t *
 keyword_printf(const char *fmt,
                const char *rev,
                const char *url,
+               const char *repos_root_url,
                apr_time_t date,
                const char *author,
                apr_pool_t *pool)
@@ -204,6 +213,20 @@ keyword_printf(const char *fmt,
             svn_stringbuf_appendcstr(value,
                                      svn_time_to_human_cstring(date, pool));
           break;
+        case 'P': /* relative path of this file */
+          if (repos_root_url && *repos_root_url != '\0' && url && *url != '\0')
+            {
+              const char *repos_relpath;
+
+              repos_relpath = svn_uri_skip_ancestor(repos_root_url, url, pool);
+              if (repos_relpath)
+                svn_stringbuf_appendcstr(value, repos_relpath);
+            }
+          break;
+        case 'R': /* root of repos */
+          if (repos_root_url && *repos_root_url != '\0')
+            svn_stringbuf_appendcstr(value, repos_root_url);
+          break;
         case 'r': /* number of this revision */
           if (rev)
             svn_stringbuf_appendcstr(value, rev);
@@ -212,6 +235,9 @@ keyword_printf(const char *fmt,
           if (url)
             svn_stringbuf_appendcstr(value, url);
           break;
+        case '_': /* '%_' => a space */
+          svn_stringbuf_appendbyte(value, ' ');
+          break;
         case '%': /* '%%' => a literal % */
           svn_stringbuf_appendbyte(value, *cur);
           break;
@@ -223,6 +249,22 @@ keyword_printf(const char *fmt,
            * formatting random memory contents. */
           cur--;
           break;
+        case 'H':
+          {
+            svn_string_t *s = keyword_printf("%P%_%r%_%d%_%a", rev, url,
+                                             repos_root_url, date, author,
+                                             pool);
+            svn_stringbuf_appendcstr(value, s->data);
+          }
+          break;
+        case 'I':
+          {
+            svn_string_t *s = keyword_printf("%b%_%r%_%d%_%a", rev, url,
+                                             repos_root_url, date, author,
+                                             pool);
+            svn_stringbuf_appendcstr(value, s->data);
+          }
+          break;
         default: /* Unrecognized code, just print it literally. */
           svn_stringbuf_appendbytes(value, cur, 2);
           break;
@@ -235,57 +277,16 @@ keyword_printf(const char *fmt,
   return svn_stringbuf__morph_into_string(value);
 }
 
-svn_error_t *
-svn_subst_build_keywords(svn_subst_keywords_t *kw,
-                         const char *keywords_val,
-                         const char *rev,
-                         const char *url,
-                         apr_time_t date,
-                         const char *author,
-                         apr_pool_t *pool)
-{
-  apr_hash_t *kwhash;
-  const svn_string_t *val;
-
-  SVN_ERR(svn_subst_build_keywords2(&kwhash, keywords_val, rev,
-                                    url, date, author, pool));
-
-  /* The behaviour of pre-1.3 svn_subst_build_keywords, which we are
-   * replicating here, is to write to a slot in the svn_subst_keywords_t
-   * only if the relevant keyword was present in keywords_val, otherwise
-   * leaving that slot untouched. */
-
-  val = svn_hash_gets(kwhash, SVN_KEYWORD_REVISION_LONG);
-  if (val)
-    kw->revision = val;
-
-  val = svn_hash_gets(kwhash, SVN_KEYWORD_DATE_LONG);
-  if (val)
-    kw->date = val;
-
-  val = svn_hash_gets(kwhash, SVN_KEYWORD_AUTHOR_LONG);
-  if (val)
-    kw->author = val;
-
-  val = svn_hash_gets(kwhash, SVN_KEYWORD_URL_LONG);
-  if (val)
-    kw->url = val;
-
-  val = svn_hash_gets(kwhash, SVN_KEYWORD_ID);
-  if (val)
-    kw->id = val;
-
-  return SVN_NO_ERROR;
-}
-
-svn_error_t *
-svn_subst_build_keywords2(apr_hash_t **kw,
-                          const char *keywords_val,
-                          const char *rev,
-                          const char *url,
-                          apr_time_t date,
-                          const char *author,
-                          apr_pool_t *pool)
+static svn_error_t *
+build_keywords(apr_hash_t **kw,
+               svn_boolean_t expand_custom_keywords,
+               const char *keywords_val,
+               const char *rev,
+               const char *url,
+               const char *repos_root_url,
+               apr_time_t date,
+               const char *author,
+               apr_pool_t *pool)
 {
   apr_array_header_t *keyword_tokens;
   int i;
@@ -297,14 +298,42 @@ svn_subst_build_keywords2(apr_hash_t **k
   for (i = 0; i < keyword_tokens->nelts; ++i)
     {
       const char *keyword = APR_ARRAY_IDX(keyword_tokens, i, const char *);
+      const char *custom_fmt = NULL;
+
+      if (expand_custom_keywords)
+        {
+          char *sep;
+
+          /* Check if there is a custom keyword definition, started by '='. */
+          sep = strchr(keyword, '=');
+          if (sep)
+            {
+              *sep = '\0'; /* Split keyword's name from custom format. */
+              custom_fmt = sep + 1;
+            }
+        }
 
-      if ((! strcmp(keyword, SVN_KEYWORD_REVISION_LONG))
-          || (! strcmp(keyword, SVN_KEYWORD_REVISION_MEDIUM))
-          || (! svn_cstring_casecmp(keyword, SVN_KEYWORD_REVISION_SHORT)))
+      if (custom_fmt)
+        {
+          svn_string_t *custom_val;
+
+          /* Custom keywords must be allowed to match the name of an
+           * existing fixed keyword. This is for compatibility purposes,
+           * in case new fixed keywords are added to Subversion which
+           * happen to match a custom keyword defined somewhere.
+           * There is only one global namespace for keyword names. */
+          custom_val = keyword_printf(custom_fmt, rev, url, repos_root_url,
+                                      date, author, pool);
+          svn_hash_sets(*kw, keyword, custom_val);
+        }
+      else if ((! strcmp(keyword, SVN_KEYWORD_REVISION_LONG))
+               || (! strcmp(keyword, SVN_KEYWORD_REVISION_MEDIUM))
+               || (! svn_cstring_casecmp(keyword, SVN_KEYWORD_REVISION_SHORT)))
         {
           svn_string_t *revision_val;
 
-          revision_val = keyword_printf("%r", rev, url, date, author, pool);
+          revision_val = keyword_printf("%r", rev, url, repos_root_url,
+                                        date, author, pool);
           svn_hash_sets(*kw, SVN_KEYWORD_REVISION_LONG, revision_val);
           svn_hash_sets(*kw, SVN_KEYWORD_REVISION_MEDIUM, revision_val);
           svn_hash_sets(*kw, SVN_KEYWORD_REVISION_SHORT, revision_val);
@@ -314,7 +343,8 @@ svn_subst_build_keywords2(apr_hash_t **k
         {
           svn_string_t *date_val;
 
-          date_val = keyword_printf("%D", rev, url, date, author, pool);
+          date_val = keyword_printf("%D", rev, url, repos_root_url, date,
+                                    author, pool);
           svn_hash_sets(*kw, SVN_KEYWORD_DATE_LONG, date_val);
           svn_hash_sets(*kw, SVN_KEYWORD_DATE_SHORT, date_val);
         }
@@ -323,7 +353,8 @@ svn_subst_build_keywords2(apr_hash_t **k
         {
           svn_string_t *author_val;
 
-          author_val = keyword_printf("%a", rev, url, date, author, pool);
+          author_val = keyword_printf("%a", rev, url, repos_root_url, date,
+                                      author, pool);
           svn_hash_sets(*kw, SVN_KEYWORD_AUTHOR_LONG, author_val);
           svn_hash_sets(*kw, SVN_KEYWORD_AUTHOR_SHORT, author_val);
         }
@@ -332,7 +363,8 @@ svn_subst_build_keywords2(apr_hash_t **k
         {
           svn_string_t *url_val;
 
-          url_val = keyword_printf("%u", rev, url, date, author, pool);
+          url_val = keyword_printf("%u", rev, url, repos_root_url, date,
+                                   author, pool);
           svn_hash_sets(*kw, SVN_KEYWORD_URL_LONG, url_val);
           svn_hash_sets(*kw, SVN_KEYWORD_URL_SHORT, url_val);
         }
@@ -340,16 +372,16 @@ svn_subst_build_keywords2(apr_hash_t **k
         {
           svn_string_t *id_val;
 
-          id_val = keyword_printf("%b %r %d %a", rev, url, date, author,
-                                  pool);
+          id_val = keyword_printf("%b %r %d %a", rev, url, repos_root_url,
+                                  date, author, pool);
           svn_hash_sets(*kw, SVN_KEYWORD_ID, id_val);
         }
       else if ((! svn_cstring_casecmp(keyword, SVN_KEYWORD_HEADER)))
         {
           svn_string_t *header_val;
 
-          header_val = keyword_printf("%u %r %d %a", rev, url, date, author,
-                                      pool);
+          header_val = keyword_printf("%u %r %d %a", rev, url, repos_root_url,
+                                      date, author, pool);
           svn_hash_sets(*kw, SVN_KEYWORD_HEADER, header_val);
         }
     }
@@ -357,6 +389,35 @@ svn_subst_build_keywords2(apr_hash_t **k
   return SVN_NO_ERROR;
 }
 
+svn_error_t *
+svn_subst_build_keywords2(apr_hash_t **kw,
+                          const char *keywords_val,
+                          const char *rev,
+                          const char *url,
+                          apr_time_t date,
+                          const char *author,
+                          apr_pool_t *pool)
+{
+  return svn_error_trace(build_keywords(kw, FALSE, keywords_val, rev, url,
+                                        NULL, date, author, pool));
+}
+
+
+svn_error_t *
+svn_subst_build_keywords3(apr_hash_t **kw,
+                          const char *keywords_val,
+                          const char *rev,
+                          const char *url,
+                          const char *repos_root_url,
+                          apr_time_t date,
+                          const char *author,
+                          apr_pool_t *pool)
+{
+  return svn_error_trace(build_keywords(kw, TRUE, keywords_val,
+                                        rev, url, repos_root_url,
+                                        date, author, pool));
+}
+
 
 /*** Helpers for svn_subst_translate_stream2 ***/
 
@@ -396,6 +457,11 @@ translate_keyword_subst(char *buf,
   if (*len < keyword_len + 2)
     return FALSE;
 
+  /* Need at least space for two $'s, two spaces and a colon, and that
+     leaves zero space for the value itself. */
+  if (keyword_len > SVN_KEYWORD_MAX_LEN - 5)
+    return FALSE;
+
   /* The keyword needs to match what we're looking for. */
   if (strncmp(buf + 1, keyword, keyword_len))
     return FALSE;
@@ -508,8 +574,8 @@ translate_keyword_subst(char *buf,
               apr_size_t vallen = value->len;
 
               /* "$keyword: value $" */
-              if (vallen > (SVN_KEYWORD_MAX_LEN - 5))
-                vallen = SVN_KEYWORD_MAX_LEN - 5;
+              if (vallen > (SVN_KEYWORD_MAX_LEN - 5 - keyword_len))
+                vallen = SVN_KEYWORD_MAX_LEN - 5 - keyword_len;
               strncpy(buf_ptr + 2, value->data, vallen);
               buf_ptr[2 + vallen] = ' ';
               buf_ptr[2 + vallen + 1] = '$';
@@ -1057,28 +1123,42 @@ translate_chunk(svn_stream_t *dst,
               /* skip current EOL */
               len += b->eol_str_len;
 
-              /* Check 4 bytes at once to allow for efficient pipelining
-                 and to reduce loop condition overhead. */
-              while ((p + len + 4) <= end)
+              if (b->keywords)
                 {
-                  if (interesting[(unsigned char)p[len]]
-                      || interesting[(unsigned char)p[len+1]]
-                      || interesting[(unsigned char)p[len+2]]
-                      || interesting[(unsigned char)p[len+3]])
-                    break;
-
-                  len += 4;
+                  /* Check 4 bytes at once to allow for efficient pipelining
+                    and to reduce loop condition overhead. */
+                  while ((p + len + 4) <= end)
+                    {
+                      if (interesting[(unsigned char)p[len]]
+                          || interesting[(unsigned char)p[len+1]]
+                          || interesting[(unsigned char)p[len+2]]
+                          || interesting[(unsigned char)p[len+3]])
+                        break;
+
+                      len += 4;
+                    }
+
+                  /* Found an interesting char or EOF in the next 4 bytes.
+                     Find its exact position. */
+                  while ((p + len) < end
+                         && !interesting[(unsigned char)p[len]])
+                    ++len;
+                }
+              else
+                {
+                  /* use our optimized sub-routine to find the next EOL */
+                  const char *start = p + len;
+                  const char *eol
+                    = svn_eol__find_eol_start((char *)start, end - start);
+                  
+                  /* EOL will be NULL if we did not find a line ending */
+                  len += (eol ? eol : end) - start;
                 }
-
-               /* Found an interesting char or EOF in the next 4 bytes.
-                  Find its exact position. */
-               while ((p + len) < end && !interesting[(unsigned char)p[len]])
-                 ++len;
             }
           while (b->nl_translation_skippable ==
                    svn_tristate_true &&       /* can potentially skip EOLs */
                  p + len + 2 < end &&         /* not too close to EOF */
-                 eol_unchanged (b, p + len)); /* EOL format already ok */
+                 eol_unchanged(b, p + len));  /* EOL format already ok */
 
           while ((p + len) < end && !interesting[(unsigned char)p[len]])
             len++;
@@ -1642,7 +1722,7 @@ create_special_file_from_stream(svn_stre
                                 svn_io_file_del_none, pool));
 
   /* Do the atomic rename from our temporary location. */
-  return svn_io_file_rename(dst_tmp, dst, pool);
+  return svn_error_trace(svn_io_file_rename(dst_tmp, dst, pool));
 }
 
 
@@ -1690,8 +1770,9 @@ svn_subst_copy_and_translate4(const char
               SVN_ERR(svn_stream_open_readonly(&src_stream, src, pool, pool));
             }
 
-          return svn_error_trace(create_special_file_from_stream(src_stream,
-                                                                 dst, pool));
+          SVN_ERR(create_special_file_from_stream(src_stream, dst, pool));
+
+          return svn_error_trace(svn_stream_close(src_stream));
         }
       /* else !expand */
 



Mime
View raw message