You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@subversion.apache.org by ju...@apache.org on 2015/03/09 10:53:09 UTC
svn commit: r1665166 [2/5] - in /subversion/branches/move-tracking-2: ./
subversion/ subversion/bindings/javahl/native/
subversion/bindings/javahl/native/jniwrapper/
subversion/bindings/javahl/tests/org/apache/subversion/javahl/
subversion/bindings/swi...
Modified: subversion/branches/move-tracking-2/subversion/libsvn_fs/fs-loader.h
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_fs/fs-loader.h?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_fs/fs-loader.h (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_fs/fs-loader.h Mon Mar 9 09:53:06 2015
@@ -446,7 +446,7 @@ typedef struct id_vtable_t
/*** Definitions of the abstract FS object types ***/
/* These are transaction properties that correspond to the bitfields
- in the 'flags' argument to svn_fs_lock(). */
+ in the 'flags' argument to svn_fs_begin_txn2(). */
#define SVN_FS__PROP_TXN_CHECK_LOCKS SVN_PROP_PREFIX "check-locks"
#define SVN_FS__PROP_TXN_CHECK_OOD SVN_PROP_PREFIX "check-ood"
/* Set to "0" at the start of the txn, to "1" when svn:date changes. */
Modified: subversion/branches/move-tracking-2/subversion/libsvn_fs_base/revs-txns.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_fs_base/revs-txns.c?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_fs_base/revs-txns.c (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_fs_base/revs-txns.c Mon Mar 9 09:53:06 2015
@@ -711,6 +711,23 @@ txn_body_begin_txn(void *baton, trail_t
SVN_ERR(txn_body_change_txn_prop(&cpargs, trail));
}
+ /* Put a datestamp on the newly created txn, so we always know
+ exactly how old it is. (This will help sysadmins identify
+ long-abandoned txns that may need to be manually removed.) Do
+ this before setting CLIENT_DATE so that it is not recorded as an
+ explicit setting. */
+ {
+ struct change_txn_prop_args cpargs;
+ svn_string_t date;
+ cpargs.fs = trail->fs;
+ cpargs.id = txn_id;
+ cpargs.name = SVN_PROP_REVISION_DATE;
+ date.data = svn_time_to_cstring(apr_time_now(), trail->pool);
+ date.len = strlen(date.data);
+ cpargs.value = &date;
+ SVN_ERR(txn_body_change_txn_prop(&cpargs, trail));
+ }
+
if (args->flags & SVN_FS_TXN_CLIENT_DATE)
{
struct change_txn_prop_args cpargs;
@@ -737,7 +754,6 @@ svn_fs_base__begin_txn(svn_fs_txn_t **tx
{
svn_fs_txn_t *txn;
struct begin_txn_args args;
- svn_string_t date;
SVN_ERR(svn_fs__check_fs(fs, TRUE));
@@ -748,15 +764,7 @@ svn_fs_base__begin_txn(svn_fs_txn_t **tx
*txn_p = txn;
- /* Put a datestamp on the newly created txn, so we always know
- exactly how old it is. (This will help sysadmins identify
- long-abandoned txns that may need to be manually removed.) When
- a txn is promoted to a revision, this property will be
- automatically overwritten with a revision datestamp. */
- date.data = svn_time_to_cstring(apr_time_now(), pool);
- date.len = strlen(date.data);
- return svn_fs_base__change_txn_prop(txn, SVN_PROP_REVISION_DATE,
- &date, pool);
+ return SVN_NO_ERROR;
}
Modified: subversion/branches/move-tracking-2/subversion/libsvn_ra/ra_loader.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_ra/ra_loader.c?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_ra/ra_loader.c (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_ra/ra_loader.c Mon Mar 9 09:53:06 2015
@@ -269,6 +269,7 @@ svn_error_t *svn_ra_open4(svn_ra_session
apr_pool_t *pool)
{
apr_pool_t *sesspool = svn_pool_create(pool);
+ apr_pool_t *scratch_pool = svn_pool_create(sesspool);
svn_ra_session_t *session;
const struct ra_lib_defn *defn;
const svn_ra__vtable_t *vtable = NULL;
@@ -278,6 +279,7 @@ svn_error_t *svn_ra_open4(svn_ra_session
#ifdef CHOOSABLE_DAV_MODULE
const char *http_library = DEFAULT_HTTP_LIBRARY;
#endif
+ svn_auth_baton_t *auth_baton;
/* Initialize the return variable. */
*session_p = NULL;
@@ -293,8 +295,12 @@ svn_error_t *svn_ra_open4(svn_ra_session
repos_URL);
if (callbacks->auth_baton)
- SVN_ERR(svn_auth__apply_config_for_server(callbacks->auth_baton, config,
- repos_URI.hostname, sesspool));
+ SVN_ERR(svn_auth__make_session_auth(&auth_baton,
+ callbacks->auth_baton, config,
+ repos_URI.hostname,
+ sesspool, scratch_pool));
+ else
+ auth_baton = NULL;
#ifdef CHOOSABLE_DAV_MODULE
if (config)
@@ -347,16 +353,16 @@ svn_error_t *svn_ra_open4(svn_ra_session
if (! initfunc)
SVN_ERR(load_ra_module(&initfunc, NULL, defn->ra_name,
- sesspool));
+ scratch_pool));
if (! initfunc)
/* Library not found. */
continue;
- SVN_ERR(initfunc(svn_ra_version(), &vtable, sesspool));
+ SVN_ERR(initfunc(svn_ra_version(), &vtable, scratch_pool));
SVN_ERR(check_ra_version(vtable->get_version(), scheme));
- if (! has_scheme_of(vtable->get_schemes(sesspool), repos_URL))
+ if (! has_scheme_of(vtable->get_schemes(scratch_pool), repos_URL))
/* Library doesn't support the scheme at runtime. */
continue;
@@ -380,10 +386,12 @@ svn_error_t *svn_ra_open4(svn_ra_session
/* Ask the library to open the session. */
err = vtable->open_session(session, corrected_url_p,
repos_URL,
- callbacks, callback_baton, config, sesspool);
+ callbacks, callback_baton, auth_baton,
+ config, sesspool, scratch_pool);
if (err)
{
+ svn_pool_destroy(sesspool); /* Includes scratch_pool */
if (err->apr_err == SVN_ERR_RA_SESSION_URL_MISMATCH)
return svn_error_trace(err);
@@ -401,7 +409,7 @@ svn_error_t *svn_ra_open4(svn_ra_session
{
/* *session_p = NULL; */
*corrected_url_p = apr_pstrdup(pool, *corrected_url_p);
- svn_pool_destroy(sesspool);
+ svn_pool_destroy(sesspool); /* Includes scratch_pool */
return SVN_NO_ERROR;
}
@@ -415,7 +423,7 @@ svn_error_t *svn_ra_open4(svn_ra_session
{
/* Duplicate the uuid as it is allocated in sesspool */
repository_uuid = apr_pstrdup(pool, repository_uuid);
- svn_pool_destroy(sesspool);
+ svn_pool_destroy(sesspool); /* includes scratch_pool */
return svn_error_createf(SVN_ERR_RA_UUID_MISMATCH, NULL,
_("Repository UUID '%s' doesn't match "
"expected UUID '%s'"),
@@ -423,6 +431,7 @@ svn_error_t *svn_ra_open4(svn_ra_session
}
}
+ svn_pool_destroy(scratch_pool);
*session_p = session;
return SVN_NO_ERROR;
}
Modified: subversion/branches/move-tracking-2/subversion/libsvn_ra/ra_loader.h
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_ra/ra_loader.h?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_ra/ra_loader.h (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_ra/ra_loader.h Mon Mar 9 09:53:06 2015
@@ -61,8 +61,10 @@ typedef struct svn_ra__vtable_t {
const char *session_URL,
const svn_ra_callbacks2_t *callbacks,
void *callback_baton,
+ svn_auth_baton_t *auth_baton,
apr_hash_t *config,
- apr_pool_t *pool);
+ apr_pool_t *result_pool,
+ apr_pool_t *scratch_pool);
/* Backs svn_ra_dup_session */
svn_error_t * (*dup_session)(svn_ra_session_t *new_session,
svn_ra_session_t *old_session,
Modified: subversion/branches/move-tracking-2/subversion/libsvn_ra/wrapper_template.h
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_ra/wrapper_template.h?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_ra/wrapper_template.h (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_ra/wrapper_template.h Mon Mar 9 09:53:06 2015
@@ -91,7 +91,9 @@ static svn_error_t *compat_open(void **s
callbacks2->progress_baton = NULL;
SVN_ERR(VTBL.open_session(sess, &session_url, repos_URL,
- callbacks2, callback_baton, config, sesspool));
+ callbacks2, callback_baton,
+ callbacks ? callbacks->auth_baton : NULL,
+ config, sesspool, sesspool));
if (strcmp(repos_URL, session_url) != 0)
{
Modified: subversion/branches/move-tracking-2/subversion/libsvn_ra_local/ra_local.h
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_ra_local/ra_local.h?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_ra_local/ra_local.h (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_ra_local/ra_local.h Mon Mar 9 09:53:06 2015
@@ -63,6 +63,9 @@ typedef struct svn_ra_local__session_bat
const svn_ra_callbacks2_t *callbacks;
void *callback_baton;
+ /* Slave auth baton */
+ svn_auth_baton_t *auth_baton;
+
const char *useragent;
} svn_ra_local__session_baton_t;
Modified: subversion/branches/move-tracking-2/subversion/libsvn_ra_local/ra_plugin.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_ra_local/ra_plugin.c?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_ra_local/ra_plugin.c (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_ra_local/ra_plugin.c Mon Mar 9 09:53:06 2015
@@ -86,7 +86,7 @@ get_username(svn_ra_session_t *session,
{
/* Get a username somehow, so we have some svn:author property to
attach to a commit. */
- if (sess->callbacks->auth_baton)
+ if (sess->auth_baton)
{
void *creds;
svn_auth_cred_username_t *username_creds;
@@ -95,7 +95,7 @@ get_username(svn_ra_session_t *session,
SVN_ERR(svn_auth_first_credentials(&creds, &iterstate,
SVN_AUTH_CRED_USERNAME,
sess->uuid, /* realmstring */
- sess->callbacks->auth_baton,
+ sess->auth_baton,
scratch_pool));
/* No point in calling next_creds(), since that assumes that the
@@ -551,13 +551,16 @@ svn_ra_local__open(svn_ra_session_t *ses
const char *repos_URL,
const svn_ra_callbacks2_t *callbacks,
void *callback_baton,
+ svn_auth_baton_t *auth_baton,
apr_hash_t *config,
- apr_pool_t *pool)
+ apr_pool_t *result_pool,
+ apr_pool_t *scratch_pool)
{
const char *client_string;
svn_ra_local__session_baton_t *sess;
const char *fs_path;
static volatile svn_atomic_t cache_init_state = 0;
+ apr_pool_t *pool = result_pool;
/* Initialise the FSFS memory cache size. We can only do this once
so one CONFIG will win the race and all others will be ignored
@@ -572,6 +575,7 @@ svn_ra_local__open(svn_ra_session_t *ses
sess = apr_pcalloc(pool, sizeof(*sess));
sess->callbacks = callbacks;
sess->callback_baton = callback_baton;
+ sess->auth_baton = auth_baton;
/* Look through the URL, figure out which part points to the
repository, and which part is the path *within* the
Modified: subversion/branches/move-tracking-2/subversion/libsvn_ra_serf/commit.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_ra_serf/commit.c?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_ra_serf/commit.c (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_ra_serf/commit.c Mon Mar 9 09:53:06 2015
@@ -101,6 +101,8 @@ typedef struct delete_context_t {
svn_revnum_t revision;
commit_context_t *commit_ctx;
+
+ svn_boolean_t non_recursive_if; /* Only create a non-recursive If header */
} delete_context_t;
/* Represents a directory. */
@@ -1101,8 +1103,15 @@ setup_delete_headers(serf_bucket_t *head
serf_bucket_headers_set(headers, SVN_DAV_VERSION_NAME_HEADER,
apr_ltoa(pool, del->revision));
- SVN_ERR(setup_if_header_recursive(&added, headers, del->commit_ctx,
- del->relpath, pool));
+ if (! del->non_recursive_if)
+ SVN_ERR(setup_if_header_recursive(&added, headers, del->commit_ctx,
+ del->relpath, pool));
+ else
+ {
+ SVN_ERR(maybe_set_lock_token_header(headers, del->commit_ctx,
+ del->relpath, pool));
+ added = TRUE;
+ }
if (added && del->commit_ctx->keep_locks)
serf_bucket_headers_setn(headers, SVN_DAV_OPTIONS_HEADER,
@@ -1402,6 +1411,28 @@ open_root(void *edit_baton,
return SVN_NO_ERROR;
}
+/* Implements svn_ra_serf__request_body_delegate_t */
+static svn_error_t *
+create_delete_body(serf_bucket_t **body_bkt,
+ void *baton,
+ serf_bucket_alloc_t *alloc,
+ apr_pool_t *pool /* request pool */,
+ apr_pool_t *scratch_pool)
+{
+ delete_context_t *ctx = baton;
+ serf_bucket_t *body;
+
+ body = serf_bucket_aggregate_create(alloc);
+
+ svn_ra_serf__add_xml_header_buckets(body, alloc);
+
+ svn_ra_serf__merge_lock_token_list(ctx->commit_ctx->lock_tokens,
+ ctx->relpath, body, alloc, pool);
+
+ *body_bkt = body;
+ return SVN_NO_ERROR;
+}
+
static svn_error_t *
delete_entry(const char *path,
svn_revnum_t revision,
@@ -1412,6 +1443,7 @@ delete_entry(const char *path,
delete_context_t *delete_ctx;
svn_ra_serf__handler_t *handler;
const char *delete_target;
+ svn_error_t *err;
if (USING_HTTPV2_COMMIT_SUPPORT(dir->commit_ctx))
{
@@ -1446,7 +1478,23 @@ delete_entry(const char *path,
handler->method = "DELETE";
handler->path = delete_target;
- SVN_ERR(svn_ra_serf__context_run_one(handler, pool));
+ err = svn_ra_serf__context_run_one(handler, pool);
+ if (err && err->apr_err == SVN_ERR_RA_DAV_REQUEST_FAILED
+ && handler->sline.code == 400)
+ {
+ svn_error_clear(err);
+
+ /* Try again with non-standard body to overcome Apache Httpd
+ header limit */
+ delete_ctx->non_recursive_if = TRUE;
+ handler->body_type = "text/xml";
+ handler->body_delegate = create_delete_body;
+ handler->body_delegate_baton = delete_ctx;
+
+ SVN_ERR(svn_ra_serf__context_run_one(handler, pool));
+ }
+ else
+ SVN_ERR(err);
/* 204 No Content: item successfully deleted */
if (handler->sline.code != 204)
@@ -1539,7 +1587,9 @@ add_directory(const char *path,
handler->header_delegate = setup_copy_dir_headers;
handler->header_delegate_baton = dir;
}
-
+ /* We have the same problem as with DELETE here: if there are too many
+ locks, the request fails. But in this case there is no way to retry
+ with a non-standard request. #### How to fix? */
SVN_ERR(svn_ra_serf__context_run_one(handler, dir->pool));
if (handler->sline.code != 201)
Modified: subversion/branches/move-tracking-2/subversion/libsvn_ra_serf/merge.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_ra_serf/merge.c?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_ra_serf/merge.c (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_ra_serf/merge.c Mon Mar 9 09:53:06 2015
@@ -285,12 +285,12 @@ setup_merge_headers(serf_bucket_t *heade
return SVN_NO_ERROR;
}
-static void
-merge_lock_token_list(apr_hash_t *lock_tokens,
- const char *parent,
- serf_bucket_t *body,
- serf_bucket_alloc_t *alloc,
- apr_pool_t *pool)
+void
+svn_ra_serf__merge_lock_token_list(apr_hash_t *lock_tokens,
+ const char *parent,
+ serf_bucket_t *body,
+ serf_bucket_alloc_t *alloc,
+ apr_pool_t *pool)
{
apr_hash_index_t *hi;
@@ -378,7 +378,8 @@ create_merge_body(serf_bucket_t **bkt,
"D:creator-displayname", SVN_VA_NULL);
svn_ra_serf__add_close_tag_buckets(body_bkt, alloc, "D:prop");
- merge_lock_token_list(ctx->lock_tokens, NULL, body_bkt, alloc, pool);
+ svn_ra_serf__merge_lock_token_list(ctx->lock_tokens, NULL, body_bkt,
+ alloc, pool);
svn_ra_serf__add_close_tag_buckets(body_bkt, alloc, "D:merge");
Modified: subversion/branches/move-tracking-2/subversion/libsvn_ra_serf/ra_serf.h
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_ra_serf/ra_serf.h?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_ra_serf/ra_serf.h (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_ra_serf/ra_serf.h Mon Mar 9 09:53:06 2015
@@ -154,6 +154,7 @@ struct svn_ra_serf__session_t {
/* Callback functions to get info from WC */
const svn_ra_callbacks2_t *wc_callbacks;
void *wc_callback_baton;
+ svn_auth_baton_t *auth_baton;
/* Callback function to send progress info to the client */
svn_ra_progress_notify_func_t progress_func;
@@ -1021,6 +1022,13 @@ svn_ra_serf__svnname_from_wirename(const
/** MERGE-related functions **/
+void
+svn_ra_serf__merge_lock_token_list(apr_hash_t *lock_tokens,
+ const char *parent,
+ serf_bucket_t *body,
+ serf_bucket_alloc_t *alloc,
+ apr_pool_t *pool);
+
/* Create an MERGE request aimed at the SESSION url, requesting the
merge of the resource identified by MERGE_RESOURCE_URL.
LOCK_TOKENS is a hash mapping paths to lock tokens owned by the
Modified: subversion/branches/move-tracking-2/subversion/libsvn_ra_serf/serf.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_ra_serf/serf.c?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_ra_serf/serf.c (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_ra_serf/serf.c Mon Mar 9 09:53:06 2015
@@ -180,17 +180,17 @@ load_config(svn_ra_serf__session_t *sess
svn_config_get(config, &timeout_str, SVN_CONFIG_SECTION_GLOBAL,
SVN_CONFIG_OPTION_HTTP_TIMEOUT, NULL);
- if (session->wc_callbacks->auth_baton)
+ if (session->auth_baton)
{
if (config_client)
{
- svn_auth_set_parameter(session->wc_callbacks->auth_baton,
+ svn_auth_set_parameter(session->auth_baton,
SVN_AUTH_PARAM_CONFIG_CATEGORY_CONFIG,
config_client);
}
if (config)
{
- svn_auth_set_parameter(session->wc_callbacks->auth_baton,
+ svn_auth_set_parameter(session->auth_baton,
SVN_AUTH_PARAM_CONFIG_CATEGORY_SERVERS,
config);
}
@@ -255,7 +255,7 @@ load_config(svn_ra_serf__session_t *sess
SERF_LOG_INFO));
#endif
- server_group = svn_auth_get_parameter(session->wc_callbacks->auth_baton,
+ server_group = svn_auth_get_parameter(session->auth_baton,
SVN_AUTH_PARAM_SERVER_GROUP);
if (server_group)
@@ -474,27 +474,29 @@ svn_ra_serf__open(svn_ra_session_t *sess
const char *session_URL,
const svn_ra_callbacks2_t *callbacks,
void *callback_baton,
+ svn_auth_baton_t *auth_baton,
apr_hash_t *config,
- apr_pool_t *pool)
+ apr_pool_t *result_pool,
+ apr_pool_t *scratch_pool)
{
apr_status_t status;
svn_ra_serf__session_t *serf_sess;
apr_uri_t url;
const char *client_string = NULL;
svn_error_t *err;
- apr_pool_t *subpool;
if (corrected_url)
*corrected_url = NULL;
- serf_sess = apr_pcalloc(pool, sizeof(*serf_sess));
- serf_sess->pool = svn_pool_create(pool);
+ serf_sess = apr_pcalloc(result_pool, sizeof(*serf_sess));
+ serf_sess->pool = result_pool;
if (config)
- SVN_ERR(svn_config_copy_config(&serf_sess->config, config, pool));
+ SVN_ERR(svn_config_copy_config(&serf_sess->config, config, result_pool));
else
serf_sess->config = NULL;
serf_sess->wc_callbacks = callbacks;
serf_sess->wc_callback_baton = callback_baton;
+ serf_sess->auth_baton = auth_baton;
serf_sess->progress_func = callbacks->progress_func;
serf_sess->progress_baton = callbacks->progress_baton;
serf_sess->cancel_func = callbacks->cancel_func;
@@ -551,13 +553,16 @@ svn_ra_serf__open(svn_ra_session_t *sess
/* create the user agent string */
if (callbacks->get_client_string)
- SVN_ERR(callbacks->get_client_string(callback_baton, &client_string, pool));
+ SVN_ERR(callbacks->get_client_string(callback_baton, &client_string,
+ scratch_pool));
if (client_string)
- serf_sess->useragent = apr_pstrcat(pool, get_user_agent_string(pool), " ",
+ serf_sess->useragent = apr_pstrcat(result_pool,
+ get_user_agent_string(scratch_pool),
+ " ",
client_string, SVN_VA_NULL);
else
- serf_sess->useragent = get_user_agent_string(pool);
+ serf_sess->useragent = get_user_agent_string(result_pool);
/* go ahead and tell serf about the connection. */
status =
@@ -578,24 +583,29 @@ svn_ra_serf__open(svn_ra_session_t *sess
session->priv = serf_sess;
- /* This subpool not only avoids having a lot of temporary state in the long
- living session pool, but it also works around a bug in serf
- <= r2319 / 1.3.4 where serf doesn't report the request as failed/cancelled
- when the authorization request handler fails to handle the request.
-
- In this specific case the serf connection is cleaned up by the pool
- handlers before our handler is cleaned up (via subpools). Using a
- subpool here cleans up our handler before the connection is cleaned. */
- subpool = svn_pool_create(pool);
+ /* The following code explicitly works around a bug in serf <= r2319 / 1.3.8
+ where serf doesn't report the request as failed/cancelled when the
+ authorization request handler fails to handle the request.
+
+ As long as we allocate the request in a subpool of the serf connection
+ pool, we know that the handler is always cleaned before the connection.
+
+ Luckily our caller now passes us two pools which handle this case.
+ */
+#if defined(SVN_DEBUG) && !SERF_VERSION_AT_LEAST(1,4,0)
+ /* Currently ensured by svn_ra_open4().
+ If failing causes segfault in basic_tests.py 48, "basic auth test" */
+ SVN_ERR_ASSERT((serf_sess->pool != scratch_pool)
+ && apr_pool_is_ancestor(serf_sess->pool, scratch_pool));
+#endif
err = svn_ra_serf__exchange_capabilities(serf_sess, corrected_url,
- pool, subpool);
+ result_pool, scratch_pool);
/* serf should produce a usable error code instead of APR_EGENERAL */
if (err && err->apr_err == APR_EGENERAL)
err = svn_error_createf(SVN_ERR_RA_DAV_REQUEST_FAILED, err,
_("Connection to '%s' failed"), session_URL);
- svn_pool_clear(subpool);
SVN_ERR(err);
/* We have set up a useful connection (that doesn't indication a redirect).
@@ -604,9 +614,7 @@ svn_ra_serf__open(svn_ra_session_t *sess
problems in any proxy. */
if ((corrected_url == NULL || *corrected_url == NULL)
&& serf_sess->detect_chunking && !serf_sess->http10)
- SVN_ERR(svn_ra_serf__probe_proxy(serf_sess, subpool));
-
- svn_pool_destroy(subpool);
+ SVN_ERR(svn_ra_serf__probe_proxy(serf_sess, scratch_pool));
return SVN_NO_ERROR;
}
Modified: subversion/branches/move-tracking-2/subversion/libsvn_ra_serf/util.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_ra_serf/util.c?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_ra_serf/util.c (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_ra_serf/util.c Mon Mar 9 09:53:06 2015
@@ -313,11 +313,11 @@ ssl_server_cert(void *baton, int failure
{
svn_error_t *err;
- svn_auth_set_parameter(conn->session->wc_callbacks->auth_baton,
+ svn_auth_set_parameter(conn->session->auth_baton,
SVN_AUTH_PARAM_SSL_SERVER_CERT_INFO,
&cert_info);
- svn_auth_set_parameter(conn->session->wc_callbacks->auth_baton,
+ svn_auth_set_parameter(conn->session->auth_baton,
SVN_AUTH_PARAM_SSL_SERVER_FAILURES,
&svn_failures);
@@ -327,13 +327,13 @@ ssl_server_cert(void *baton, int failure
err = svn_auth_first_credentials(&creds, &state,
SVN_AUTH_CRED_SSL_SERVER_AUTHORITY,
realmstring,
- conn->session->wc_callbacks->auth_baton,
+ conn->session->auth_baton,
scratch_pool);
- svn_auth_set_parameter(conn->session->wc_callbacks->auth_baton,
+ svn_auth_set_parameter(conn->session->auth_baton,
SVN_AUTH_PARAM_SSL_SERVER_CERT_INFO, NULL);
- svn_auth_set_parameter(conn->session->wc_callbacks->auth_baton,
+ svn_auth_set_parameter(conn->session->auth_baton,
SVN_AUTH_PARAM_SSL_SERVER_FAILURES, NULL);
if (err)
@@ -360,11 +360,11 @@ ssl_server_cert(void *baton, int failure
return APR_SUCCESS;
}
- svn_auth_set_parameter(conn->session->wc_callbacks->auth_baton,
+ svn_auth_set_parameter(conn->session->auth_baton,
SVN_AUTH_PARAM_SSL_SERVER_FAILURES,
&svn_failures);
- svn_auth_set_parameter(conn->session->wc_callbacks->auth_baton,
+ svn_auth_set_parameter(conn->session->auth_baton,
SVN_AUTH_PARAM_SSL_SERVER_CERT_INFO,
&cert_info);
@@ -373,7 +373,7 @@ ssl_server_cert(void *baton, int failure
SVN_ERR(svn_auth_first_credentials(&creds, &state,
SVN_AUTH_CRED_SSL_SERVER_TRUST,
realmstring,
- conn->session->wc_callbacks->auth_baton,
+ conn->session->auth_baton,
scratch_pool));
if (creds)
{
@@ -394,7 +394,7 @@ ssl_server_cert(void *baton, int failure
}
}
- svn_auth_set_parameter(conn->session->wc_callbacks->auth_baton,
+ svn_auth_set_parameter(conn->session->auth_baton,
SVN_AUTH_PARAM_SSL_SERVER_CERT_INFO, NULL);
/* Are there non accepted failures left? */
@@ -648,7 +648,7 @@ handle_client_cert(void *data,
&conn->ssl_client_auth_state,
SVN_AUTH_CRED_SSL_CLIENT_CERT,
realm,
- session->wc_callbacks->auth_baton,
+ session->auth_baton,
pool));
}
else
@@ -700,7 +700,7 @@ handle_client_cert_pw(void *data,
&conn->ssl_client_pw_auth_state,
SVN_AUTH_CRED_SSL_CLIENT_CERT_PW,
cert_path,
- session->wc_callbacks->auth_baton,
+ session->auth_baton,
pool));
}
else
@@ -1132,7 +1132,7 @@ svn_ra_serf__credentials_callback(char *
&session->auth_state,
SVN_AUTH_CRED_SIMPLE,
realm,
- session->wc_callbacks->auth_baton,
+ session->auth_baton,
session->pool);
}
else
Modified: subversion/branches/move-tracking-2/subversion/libsvn_ra_svn/client.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_ra_svn/client.c?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_ra_svn/client.c (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_ra_svn/client.c Mon Mar 9 09:53:06 2015
@@ -616,7 +616,9 @@ static svn_error_t *open_session(svn_ra_
apr_hash_t *config,
const svn_ra_callbacks2_t *callbacks,
void *callbacks_baton,
- apr_pool_t *pool)
+ svn_auth_baton_t *auth_baton,
+ apr_pool_t *result_pool,
+ apr_pool_t *scratch_pool)
{
svn_ra_svn__session_baton_t *sess;
svn_ra_svn_conn_t *conn;
@@ -624,6 +626,7 @@ static svn_error_t *open_session(svn_ra_
apr_uint64_t minver, maxver;
apr_array_header_t *mechlist, *server_caplist, *repos_caplist;
const char *client_string = NULL;
+ apr_pool_t *pool = result_pool;
sess = apr_palloc(pool, sizeof(*sess));
sess->pool = pool;
@@ -636,6 +639,7 @@ static svn_error_t *open_session(svn_ra_
sess->callbacks = callbacks;
sess->callbacks_baton = callbacks_baton;
sess->bytes_read = sess->bytes_written = 0;
+ sess->auth_baton = auth_baton;
if (config)
SVN_ERR(svn_config_copy_config(&sess->config, config, pool));
@@ -804,6 +808,7 @@ static svn_error_t *ra_svn_open(svn_ra_s
const char *url,
const svn_ra_callbacks2_t *callbacks,
void *callback_baton,
+ svn_auth_baton_t *auth_baton,
apr_hash_t *config,
apr_pool_t *result_pool,
apr_pool_t *scratch_pool)
@@ -839,32 +844,21 @@ static svn_error_t *ra_svn_open(svn_ra_s
? svn_hash_gets(config, SVN_CONFIG_CATEGORY_CONFIG)
: NULL;
cfg = config ? svn_hash_gets(config, SVN_CONFIG_CATEGORY_SERVERS) : NULL;
- svn_auth_set_parameter(callbacks->auth_baton,
+ svn_auth_set_parameter(auth_baton,
SVN_AUTH_PARAM_CONFIG_CATEGORY_CONFIG, cfg_client);
- svn_auth_set_parameter(callbacks->auth_baton,
+ svn_auth_set_parameter(auth_baton,
SVN_AUTH_PARAM_CONFIG_CATEGORY_SERVERS, cfg);
/* We open the session in a subpool so we can get rid of it if we
reparent with a server that doesn't support reparenting. */
SVN_ERR(open_session(&sess, url, &uri, tunnel, tunnel_argv, config,
- callbacks, callback_baton, sess_pool));
+ callbacks, callback_baton,
+ auth_baton, sess_pool, scratch_pool));
session->priv = sess;
return SVN_NO_ERROR;
}
-static svn_error_t *ra_svn_open_pool(svn_ra_session_t *session,
- const char **corrected_url,
- const char *url,
- const svn_ra_callbacks2_t *callbacks,
- void *callback_baton,
- apr_hash_t *config,
- apr_pool_t *pool)
-{
- return ra_svn_open(session, corrected_url, url, callbacks, callback_baton,
- config, pool, pool);
-}
-
static svn_error_t *ra_svn_dup_session(svn_ra_session_t *new_session,
svn_ra_session_t *old_session,
const char *new_session_url,
@@ -875,7 +869,7 @@ static svn_error_t *ra_svn_dup_session(s
SVN_ERR(ra_svn_open(new_session, NULL, new_session_url,
old_sess->callbacks, old_sess->callbacks_baton,
- old_sess->config,
+ old_sess->auth_baton, old_sess->config,
result_pool, scratch_pool));
return SVN_NO_ERROR;
@@ -912,7 +906,7 @@ static svn_error_t *ra_svn_reparent(svn_
if (! err)
err = open_session(&new_sess, url, &uri, sess->tunnel_name, sess->tunnel_argv,
sess->config, sess->callbacks, sess->callbacks_baton,
- sess_pool);
+ sess->auth_baton, sess_pool, sess_pool);
/* We destroy the new session pool on error, since it is allocated in
the main session pool. */
if (err)
@@ -2872,7 +2866,7 @@ static const svn_ra__vtable_t ra_svn_vta
svn_ra_svn_version,
ra_svn_get_description,
ra_svn_get_schemes,
- ra_svn_open_pool,
+ ra_svn_open,
ra_svn_dup_session,
ra_svn_reparent,
ra_svn_get_session_url,
Modified: subversion/branches/move-tracking-2/subversion/libsvn_ra_svn/cyrus_auth.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_ra_svn/cyrus_auth.c?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_ra_svn/cyrus_auth.c (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_ra_svn/cyrus_auth.c Mon Mar 9 09:53:06 2015
@@ -867,7 +867,7 @@ svn_ra_svn__do_cyrus_auth(svn_ra_svn__se
realmstring = apr_psprintf(pool, "%s %s", sess->realm_prefix, realm);
/* Initialize the credential baton. */
- cred_baton.auth_baton = sess->callbacks->auth_baton;
+ cred_baton.auth_baton = sess->auth_baton;
cred_baton.realmstring = realmstring;
cred_baton.pool = pool;
Modified: subversion/branches/move-tracking-2/subversion/libsvn_ra_svn/editorp.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_ra_svn/editorp.c?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_ra_svn/editorp.c (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_ra_svn/editorp.c Mon Mar 9 09:53:06 2015
@@ -633,7 +633,7 @@ static svn_error_t *ra_svn_handle_close_
/* Close the directory and destroy the baton. */
SVN_CMD_ERR(ds->editor->close_directory(entry->baton, pool));
- svn_hash_sets(ds->tokens, token, NULL);
+ apr_hash_set(ds->tokens, token->data, token->len, NULL);
svn_pool_destroy(entry->pool);
return SVN_NO_ERROR;
}
@@ -812,7 +812,7 @@ static svn_error_t *ra_svn_handle_close_
/* Close the file and destroy the baton. */
SVN_CMD_ERR(ds->editor->close_file(entry->baton, text_checksum, pool));
- svn_hash_sets(ds->tokens, token, NULL);
+ apr_hash_set(ds->tokens, token->data, token->len, NULL);
if (--ds->file_refs == 0)
svn_pool_clear(ds->file_pool);
return SVN_NO_ERROR;
Modified: subversion/branches/move-tracking-2/subversion/libsvn_ra_svn/internal_auth.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_ra_svn/internal_auth.c?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_ra_svn/internal_auth.c (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_ra_svn/internal_auth.c Mon Mar 9 09:53:06 2015
@@ -95,7 +95,7 @@ svn_ra_svn__do_internal_auth(svn_ra_svn_
{
SVN_ERR(svn_auth_first_credentials(&creds, &iterstate,
SVN_AUTH_CRED_SIMPLE, realmstring,
- sess->callbacks->auth_baton, pool));
+ sess->auth_baton, pool));
if (!creds)
return svn_error_create(SVN_ERR_RA_NOT_AUTHORIZED, NULL,
_("Can't get password"));
Modified: subversion/branches/move-tracking-2/subversion/libsvn_ra_svn/ra_svn.h
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_ra_svn/ra_svn.h?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_ra_svn/ra_svn.h (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_ra_svn/ra_svn.h Mon Mar 9 09:53:06 2015
@@ -123,6 +123,7 @@ struct svn_ra_svn__session_baton_t {
apr_pool_t *pool;
svn_ra_svn_conn_t *conn;
svn_boolean_t is_tunneled;
+ svn_auth_baton_t *auth_baton;
const char *url;
const char *user;
const char *hostname; /* The remote hostname. */
Modified: subversion/branches/move-tracking-2/subversion/libsvn_repos/commit.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_repos/commit.c?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_repos/commit.c (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_repos/commit.c Mon Mar 9 09:53:06 2015
@@ -124,6 +124,7 @@ struct dir_baton
svn_revnum_t base_rev; /* the revision I'm based on */
svn_boolean_t was_copied; /* was this directory added with history? */
apr_pool_t *pool; /* my personal pool, in which I am allocated. */
+ svn_boolean_t checked_write; /* TRUE after successfull write check */
};
@@ -131,6 +132,7 @@ struct file_baton
{
struct edit_baton *edit_baton;
const char *path; /* the -absolute- path to this file in the fs */
+ svn_boolean_t checked_write; /* TRUE after successfull write check */
};
@@ -171,6 +173,30 @@ out_of_date(const char *path, svn_node_k
path);
}
+/* Perform an out of date check for base_rev against created rev,
+ and a sanity check of base_rev. */
+static svn_error_t *
+check_out_of_date(struct edit_baton *eb,
+ const char *path,
+ svn_node_kind_t kind,
+ svn_revnum_t base_rev,
+ svn_revnum_t created_rev)
+{
+ if (base_rev < created_rev)
+ {
+ return out_of_date(path, kind);
+ }
+ else if (base_rev > created_rev)
+ {
+ if (base_rev > svn_fs_txn_base_revision(eb->txn))
+ return svn_error_createf(SVN_ERR_FS_NO_SUCH_REVISION, NULL,
+ _("No such revision %ld"),
+ base_rev);
+ }
+
+ return SVN_NO_ERROR;
+}
+
static svn_error_t *
invoke_commit_cb(svn_commit_callback2_t commit_cb,
@@ -364,14 +390,18 @@ add_file_or_directory(const char *path,
/* Build a new child baton. */
if (is_dir)
{
- *return_baton = make_dir_baton(eb, pb, full_path, was_copied,
- SVN_INVALID_REVNUM, pool);
+ struct dir_baton *new_db = make_dir_baton(eb, pb, full_path, was_copied,
+ SVN_INVALID_REVNUM, pool);
+
+ new_db->checked_write = TRUE; /* Just created */
+ *return_baton = new_db;
}
else
{
struct file_baton *new_fb = apr_pcalloc(pool, sizeof(*new_fb));
new_fb->edit_baton = eb;
new_fb->path = full_path;
+ new_fb->checked_write = TRUE; /* Just created */
*return_baton = new_fb;
}
@@ -392,11 +422,16 @@ open_root(void *edit_baton,
struct edit_baton *eb = edit_baton;
svn_revnum_t youngest;
- /* Ignore BASE_REVISION. We always build our transaction against
- HEAD. However, we will keep it in our dir baton for out of
- dateness checks. */
+ /* We always build our transaction against HEAD. However, we will
+ sanity-check BASE_REVISION and keep it in our dir baton for out
+ of dateness checks. */
SVN_ERR(svn_fs_youngest_rev(&youngest, eb->fs, eb->pool));
+ if (base_revision > youngest)
+ return svn_error_createf(SVN_ERR_FS_NO_SUCH_REVISION, NULL,
+ _("No such revision %ld (HEAD is %ld)"),
+ base_revision, youngest);
+
/* Unless we've been instructed to use a specific transaction, we'll
make our own. */
if (eb->txn_owner)
@@ -443,7 +478,6 @@ delete_entry(const char *path,
struct dir_baton *parent = parent_baton;
struct edit_baton *eb = parent->edit_baton;
svn_node_kind_t kind;
- svn_revnum_t cr_rev;
svn_repos_authz_access_t required = svn_authz_write;
const char *full_path;
@@ -468,14 +502,18 @@ delete_entry(const char *path,
/* Now, make sure we're deleting the node we *think* we're
deleting, else return an out-of-dateness error. */
- SVN_ERR(svn_fs_node_created_rev(&cr_rev, eb->txn_root, full_path, pool));
- if (SVN_IS_VALID_REVNUM(revision) && (revision < cr_rev))
- return svn_error_trace(out_of_date(full_path, kind));
+ if (SVN_IS_VALID_REVNUM(revision))
+ {
+ svn_revnum_t cr_rev;
+
+ SVN_ERR(svn_fs_node_created_rev(&cr_rev, eb->txn_root, full_path, pool));
+ SVN_ERR(check_out_of_date(eb, full_path, kind, revision, cr_rev));
+ }
/* This routine is a mindless wrapper. We call svn_fs_delete()
because that will delete files and recursively delete
directories. */
- return svn_fs_delete(eb->txn_root, full_path, pool);
+ return svn_error_trace(svn_fs_delete(eb->txn_root, full_path, pool));
}
@@ -530,18 +568,23 @@ apply_textdelta(void *file_baton,
void **handler_baton)
{
struct file_baton *fb = file_baton;
+ struct edit_baton *eb = fb->edit_baton;
- /* Check for write authorization. */
- SVN_ERR(check_authz(fb->edit_baton, fb->path,
- fb->edit_baton->txn_root,
- svn_authz_write, pool));
+ if (!fb->checked_write)
+ {
+ /* Check for write authorization. */
+ SVN_ERR(check_authz(eb, fb->path, eb->txn_root,
+ svn_authz_write, pool));
+ fb->checked_write = TRUE;
+ }
- return svn_fs_apply_textdelta(handler, handler_baton,
- fb->edit_baton->txn_root,
- fb->path,
- base_checksum,
- NULL,
- pool);
+ return svn_error_trace(
+ svn_fs_apply_textdelta(handler, handler_baton,
+ eb->txn_root,
+ fb->path,
+ base_checksum,
+ NULL,
+ pool));
}
@@ -585,8 +628,9 @@ open_file(const char *path,
/* If the node our caller has is an older revision number than the
one in our transaction, return an out-of-dateness error. */
- if (SVN_IS_VALID_REVNUM(base_revision) && (base_revision < cr_rev))
- return svn_error_trace(out_of_date(full_path, svn_node_file));
+ if (SVN_IS_VALID_REVNUM(base_revision))
+ SVN_ERR(check_out_of_date(eb, full_path, svn_node_file,
+ base_revision, cr_rev));
/* Build a new file baton */
new_fb = apr_pcalloc(pool, sizeof(*new_fb));
@@ -611,9 +655,13 @@ change_file_prop(void *file_baton,
struct file_baton *fb = file_baton;
struct edit_baton *eb = fb->edit_baton;
- /* Check for write authorization. */
- SVN_ERR(check_authz(eb, fb->path, eb->txn_root,
- svn_authz_write, pool));
+ if (!fb->checked_write)
+ {
+ /* Check for write authorization. */
+ SVN_ERR(check_authz(eb, fb->path, eb->txn_root,
+ svn_authz_write, pool));
+ fb->checked_write = TRUE;
+ }
return svn_repos_fs_change_node_prop(eb->txn_root, fb->path,
name, value, pool);
@@ -658,19 +706,24 @@ change_dir_prop(void *dir_baton,
struct edit_baton *eb = db->edit_baton;
/* Check for write authorization. */
- SVN_ERR(check_authz(eb, db->path, eb->txn_root,
- svn_authz_write, pool));
-
- if (SVN_IS_VALID_REVNUM(db->base_rev))
+ if (!db->checked_write)
{
- /* Subversion rule: propchanges can only happen on a directory
- which is up-to-date. */
- svn_revnum_t created_rev;
- SVN_ERR(svn_fs_node_created_rev(&created_rev,
- eb->txn_root, db->path, pool));
+ SVN_ERR(check_authz(eb, db->path, eb->txn_root,
+ svn_authz_write, pool));
+
+ if (SVN_IS_VALID_REVNUM(db->base_rev))
+ {
+ /* Subversion rule: propchanges can only happen on a directory
+ which is up-to-date. */
+ svn_revnum_t created_rev;
+ SVN_ERR(svn_fs_node_created_rev(&created_rev,
+ eb->txn_root, db->path, pool));
+
+ SVN_ERR(check_out_of_date(eb, db->path, svn_node_dir,
+ db->base_rev, created_rev));
+ }
- if (db->base_rev < created_rev)
- return svn_error_trace(out_of_date(db->path, svn_node_dir));
+ db->checked_write = TRUE; /* Skip on further prop changes */
}
return svn_repos_fs_change_node_prop(eb->txn_root, db->path,
Modified: subversion/branches/move-tracking-2/subversion/libsvn_repos/rev_hunt.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_repos/rev_hunt.c?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_repos/rev_hunt.c (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_repos/rev_hunt.c Mon Mar 9 09:53:06 2015
@@ -310,9 +310,8 @@ svn_repos_deleted_rev(svn_fs_t *fs,
svn_revnum_t *deleted,
apr_pool_t *pool)
{
- apr_pool_t *subpool;
- svn_fs_root_t *start_root, *root, *copy_root;
- const char *copy_path;
+ apr_pool_t *iterpool;
+ svn_fs_root_t *start_root, *root;
svn_revnum_t mid_rev;
svn_node_kind_t kind;
svn_fs_node_relation_t node_relation;
@@ -379,6 +378,8 @@ svn_repos_deleted_rev(svn_fs_t *fs,
root, path, pool));
if (node_relation != svn_fs_node_unrelated)
{
+ svn_fs_root_t *copy_root;
+ const char *copy_path;
SVN_ERR(svn_fs_closest_copy(©_root, ©_path, root,
path, pool));
if (!copy_root ||
@@ -432,15 +433,15 @@ svn_repos_deleted_rev(svn_fs_t *fs,
*/
mid_rev = (start + end) / 2;
- subpool = svn_pool_create(pool);
+ iterpool = svn_pool_create(pool);
while (1)
{
- svn_pool_clear(subpool);
+ svn_pool_clear(iterpool);
/* Get revision root and node id for mid_rev at that revision. */
- SVN_ERR(svn_fs_revision_root(&root, fs, mid_rev, subpool));
- SVN_ERR(svn_fs_check_path(&kind, root, path, pool));
+ SVN_ERR(svn_fs_revision_root(&root, fs, mid_rev, iterpool));
+ SVN_ERR(svn_fs_check_path(&kind, root, path, iterpool));
if (kind == svn_node_none)
{
/* Case D: Look lower in the range. */
@@ -449,13 +450,15 @@ svn_repos_deleted_rev(svn_fs_t *fs,
}
else
{
+ svn_fs_root_t *copy_root;
+ const char *copy_path;
/* Determine the relationship between the start node
and the current node. */
SVN_ERR(svn_fs_node_relation(&node_relation, start_root, path,
- root, path, pool));
+ root, path, iterpool));
if (node_relation != svn_fs_node_unrelated)
- SVN_ERR(svn_fs_closest_copy(©_root, ©_path, root,
- path, subpool));
+ SVN_ERR(svn_fs_closest_copy(©_root, ©_path, root,
+ path, iterpool));
if (node_relation == svn_fs_node_unrelated ||
(copy_root &&
(svn_fs_revision_root_revision(copy_root) > start)))
@@ -479,7 +482,7 @@ svn_repos_deleted_rev(svn_fs_t *fs,
}
}
- svn_pool_destroy(subpool);
+ svn_pool_destroy(iterpool);
return SVN_NO_ERROR;
}
@@ -666,8 +669,7 @@ svn_repos_trace_node_locations(svn_fs_t
/* First - let's sort the array of the revisions from the greatest revision
* downward, so it will be easier to search on. */
location_revisions = apr_array_copy(pool, location_revisions_orig);
- qsort(location_revisions->elts, location_revisions->nelts,
- sizeof(*revision_ptr), svn_sort_compare_revisions);
+ svn_sort__array(location_revisions, svn_sort_compare_revisions);
revision_ptr = (svn_revnum_t *)location_revisions->elts;
revision_ptr_end = revision_ptr + location_revisions->nelts;
Modified: subversion/branches/move-tracking-2/subversion/libsvn_subr/auth.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_subr/auth.c?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_subr/auth.c (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_subr/auth.c Mon Mar 9 09:53:06 2015
@@ -109,10 +109,10 @@ struct svn_auth_baton_t
/* run-time parameters needed by providers. */
apr_hash_t *parameters;
+ apr_hash_t *slave_parameters;
/* run-time credentials cache. */
apr_hash_t *creds_cache;
-
};
/* Abstracted iteration baton */
@@ -125,6 +125,7 @@ struct svn_auth_iterstate_t
const char *realmstring; /* The original realmstring passed in */
const char *cache_key; /* key to use in auth_baton's creds_cache */
svn_auth_baton_t *auth_baton; /* the original auth_baton. */
+ apr_hash_t *parameters;
};
@@ -142,6 +143,7 @@ svn_auth_open(svn_auth_baton_t **auth_ba
ab = apr_pcalloc(pool, sizeof(*ab));
ab->tables = apr_hash_make(pool);
ab->parameters = apr_hash_make(pool);
+ /* ab->slave_parameters = NULL; */
ab->creds_cache = apr_hash_make(pool);
ab->pool = pool;
@@ -170,7 +172,8 @@ svn_auth_open(svn_auth_baton_t **auth_ba
*auth_baton = ab;
}
-
+/* Magic pointer value to allow storing 'NULL' in an apr_hash_t */
+static const void *auth_NULL = NULL;
void
svn_auth_set_parameter(svn_auth_baton_t *auth_baton,
@@ -178,17 +181,36 @@ svn_auth_set_parameter(svn_auth_baton_t
const void *value)
{
if (auth_baton)
- svn_hash_sets(auth_baton->parameters, name, value);
+ {
+ if (auth_baton->slave_parameters)
+ {
+ if (!value)
+ value = &auth_NULL;
+
+ svn_hash_sets(auth_baton->slave_parameters, name, value);
+ }
+ else
+ svn_hash_sets(auth_baton->parameters, name, value);
+ }
}
const void *
svn_auth_get_parameter(svn_auth_baton_t *auth_baton,
const char *name)
{
- if (auth_baton)
- return svn_hash_gets(auth_baton->parameters, name);
- else
+ const void *value;
+ if (!auth_baton)
return NULL;
+ else if (!auth_baton->slave_parameters)
+ return svn_hash_gets(auth_baton->parameters, name);
+
+ value = svn_hash_gets(auth_baton->slave_parameters, name);
+
+ if (value)
+ return (value == &auth_NULL) ? NULL
+ : value;
+
+ return svn_hash_gets(auth_baton->parameters, name);
}
@@ -218,6 +240,7 @@ svn_auth_first_credentials(void **creden
svn_boolean_t got_first = FALSE;
svn_auth_iterstate_t *iterstate;
const char *cache_key;
+ apr_hash_t *parameters;
if (! auth_baton)
return svn_error_create(SVN_ERR_AUTHN_NO_PROVIDER, NULL,
@@ -230,6 +253,26 @@ svn_auth_first_credentials(void **creden
_("No provider registered for '%s' credentials"),
cred_kind);
+ if (auth_baton->slave_parameters)
+ {
+ apr_hash_index_t *hi;
+ parameters = apr_hash_copy(pool, auth_baton->parameters);
+
+ for (hi = apr_hash_first(pool, auth_baton->slave_parameters);
+ hi;
+ hi = apr_hash_next(hi))
+ {
+ const void *value = apr_hash_this_val(hi);
+
+ if (value == &auth_NULL)
+ value = NULL;
+
+ svn_hash_sets(parameters, apr_hash_this_key(hi), value);
+ }
+ }
+ else
+ parameters = auth_baton->parameters;
+
/* First, see if we have cached creds in the auth_baton. */
cache_key = make_cache_key(cred_kind, realmstring, pool);
creds = svn_hash_gets(auth_baton->creds_cache, cache_key);
@@ -247,7 +290,7 @@ svn_auth_first_credentials(void **creden
svn_auth_provider_object_t *);
SVN_ERR(provider->vtable->first_credentials(&creds, &iter_baton,
provider->provider_baton,
- auth_baton->parameters,
+ parameters,
realmstring,
auth_baton->pool));
@@ -274,6 +317,7 @@ svn_auth_first_credentials(void **creden
iterstate->realmstring = apr_pstrdup(pool, realmstring);
iterstate->cache_key = cache_key;
iterstate->auth_baton = auth_baton;
+ iterstate->parameters = parameters;
*state = iterstate;
/* Put the creds in the cache */
@@ -319,7 +363,7 @@ svn_auth_next_credentials(void **credent
SVN_ERR(provider->vtable->next_credentials(&creds,
state->provider_iter_baton,
provider->provider_baton,
- auth_baton->parameters,
+ state->parameters,
state->realmstring,
auth_baton->pool));
}
@@ -687,10 +731,12 @@ svn_auth_get_platform_specific_client_pr
}
svn_error_t *
-svn_auth__apply_config_for_server(svn_auth_baton_t *auth_baton,
- apr_hash_t *config,
- const char *server_name,
- apr_pool_t *scratch_pool)
+svn_auth__make_session_auth(svn_auth_baton_t **session_auth_baton,
+ const svn_auth_baton_t *auth_baton,
+ apr_hash_t *config,
+ const char *server_name,
+ apr_pool_t *result_pool,
+ apr_pool_t *scratch_pool)
{
svn_boolean_t store_passwords = SVN_CONFIG_DEFAULT_OPTION_STORE_PASSWORDS;
svn_boolean_t store_auth_creds = SVN_CONFIG_DEFAULT_OPTION_STORE_AUTH_CREDS;
@@ -702,6 +748,12 @@ svn_auth__apply_config_for_server(svn_au
svn_config_t *servers = NULL;
const char *server_group = NULL;
+ struct svn_auth_baton_t *ab;
+
+ ab = apr_pmemdup(result_pool, auth_baton, sizeof(*ab));
+
+ ab->slave_parameters = apr_hash_make(result_pool);
+
/* The 'store-passwords' and 'store-auth-creds' parameters used to
* live in SVN_CONFIG_CATEGORY_CONFIG. For backward compatibility,
* if values for these parameters have already been set by our
@@ -716,11 +768,11 @@ svn_auth__apply_config_for_server(svn_au
* "store-auth-creds = yes" -- they'll get the expected behaviour.
*/
- if (svn_auth_get_parameter(auth_baton,
+ if (svn_auth_get_parameter(ab,
SVN_AUTH_PARAM_DONT_STORE_PASSWORDS) != NULL)
store_passwords = FALSE;
- if (svn_auth_get_parameter(auth_baton,
+ if (svn_auth_get_parameter(ab,
SVN_AUTH_PARAM_NO_AUTH_CACHE) != NULL)
store_auth_creds = FALSE;
@@ -806,46 +858,32 @@ svn_auth__apply_config_for_server(svn_au
/* Save auth caching parameters in the auth parameter hash. */
if (! store_passwords)
- svn_auth_set_parameter(auth_baton,
+ svn_auth_set_parameter(ab,
SVN_AUTH_PARAM_DONT_STORE_PASSWORDS, "");
- svn_auth_set_parameter(auth_baton,
+ svn_auth_set_parameter(ab,
SVN_AUTH_PARAM_STORE_PLAINTEXT_PASSWORDS,
store_plaintext_passwords);
if (! store_pp)
- svn_auth_set_parameter(auth_baton,
+ svn_auth_set_parameter(ab,
SVN_AUTH_PARAM_DONT_STORE_SSL_CLIENT_CERT_PP,
"");
- svn_auth_set_parameter(auth_baton,
+ svn_auth_set_parameter(ab,
SVN_AUTH_PARAM_STORE_SSL_CLIENT_CERT_PP_PLAINTEXT,
store_pp_plaintext);
if (! store_auth_creds)
- svn_auth_set_parameter(auth_baton,
- SVN_AUTH_PARAM_NO_AUTH_CACHE, "");
+ svn_auth_set_parameter(ab,
+ SVN_AUTH_PARAM_NO_AUTH_CACHE, "");
- /* ### This setting may have huge side-effects when the auth baton is shared
- ### between different ra sessions, as it will change which server settings
- ### will be used for all future auth requests.
- ###
- ### E.g. when you connect using a ssl client cert that is specified in the
- ### config file, you might have it when you first connect... but if you
- ### then connect to another repository, you might not see the same
- ### settings when the SSL connection is built up again later on.
- ###
- ### Most current usages should probably have been keyed on the realm
- ### string instead of this magic flag that changes when multiple repositories
- ### are used.
- ###
- ### This especially affects long living ra sessions, such as those on the
- ### reuse-ra-session branch.
- */
if (server_group)
- svn_auth_set_parameter(auth_baton,
+ svn_auth_set_parameter(ab,
SVN_AUTH_PARAM_SERVER_GROUP,
- apr_pstrdup(auth_baton->pool, server_group));
+ apr_pstrdup(ab->pool, server_group));
+
+ *session_auth_baton = ab;
return SVN_NO_ERROR;
}
Modified: subversion/branches/move-tracking-2/subversion/libsvn_subr/config_win.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_subr/config_win.c?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_subr/config_win.c (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_subr/config_win.c Mon Mar 9 09:53:06 2015
@@ -197,15 +197,15 @@ svn_config__parse_registry(svn_config_t
&hkey);
if (err != ERROR_SUCCESS)
{
- const int is_enoent = APR_STATUS_IS_ENOENT(APR_FROM_OS_ERROR(err));
- if (!is_enoent)
- return svn_error_createf(SVN_ERR_BAD_FILENAME, NULL,
+ apr_status_t apr_err = APR_FROM_OS_ERROR(err);
+ svn_boolean_t is_enoent = APR_STATUS_IS_ENOENT(apr_err);
+
+ if (must_exist || !is_enoent)
+ return svn_error_createf(SVN_ERR_BAD_FILENAME,
+ is_enoent ? NULL
+ : svn_error_wrap_apr(apr_err, NULL),
_("Can't open registry key '%s'"),
svn_dirent_local_style(file, pool));
- else if (must_exist && is_enoent)
- return svn_error_createf(SVN_ERR_BAD_FILENAME, NULL,
- _("Can't find registry key '%s'"),
- svn_dirent_local_style(file, pool));
else
return SVN_NO_ERROR;
}
Modified: subversion/branches/move-tracking-2/subversion/libsvn_subr/error.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_subr/error.c?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_subr/error.c (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_subr/error.c Mon Mar 9 09:53:06 2015
@@ -28,6 +28,10 @@
#include <apr_pools.h>
#include <apr_strings.h>
+#if defined(SVN_DEBUG) && APR_HAS_THREADS
+#include <apr_thread_proc.h>
+#endif
+
#include <zlib.h>
#ifndef SVN_ERR__TRACING
@@ -38,12 +42,56 @@
#include "svn_pools.h"
#include "svn_utf.h"
+#include "private/svn_error_private.h"
+#include "svn_private_config.h"
+
+#if defined(SVN_DEBUG) && APR_HAS_THREADS
+#include "private/svn_atomic.h"
+#include "pools.h"
+#endif
+
+
#ifdef SVN_DEBUG
-/* XXX FIXME: These should be protected by a thread mutex.
- svn_error__locate and make_error_internal should cooperate
- in locking and unlocking it. */
+# if APR_HAS_THREADS
+static apr_threadkey_t *error_file_key = NULL;
+static apr_threadkey_t *error_line_key = NULL;
+
+/* No-op destructor for apr_threadkey_private_create(). */
+static void null_threadkey_dtor(void *stuff) {}
+
+/* Handler for svn_atomic__init_once used by svn_error__locate to
+ initialize the thread-local error location storage.
+ This function will never return an error. */
+static svn_error_t *
+locate_init_once(void *ignored_baton, apr_pool_t *ignored_pool)
+{
+ /* Strictly speaking, this is a memory leak, since we're creating an
+ unmanaged, top-level pool and never destroying it. We do this
+ because this pool controls the lifetime of the thread-local
+ storage for error locations, and that storage must always be
+ available. */
+ apr_pool_t *threadkey_pool = svn_pool__create_unmanaged(TRUE);
+ apr_status_t status;
+
+ status = apr_threadkey_private_create(&error_file_key,
+ null_threadkey_dtor,
+ threadkey_pool);
+ if (status == APR_SUCCESS)
+ status = apr_threadkey_private_create(&error_line_key,
+ null_threadkey_dtor,
+ threadkey_pool);
+
+ /* If anything went wrong with the creation of the thread-local
+ storage, we'll revert to the old, thread-agnostic behaviour */
+ if (status != APR_SUCCESS)
+ error_file_key = error_line_key = NULL;
+
+ return SVN_NO_ERROR;
+}
+# endif /* APR_HAS_THREADS */
-/* XXX TODO: Define mutex here #if APR_HAS_THREADS */
+/* These location variables will be used in no-threads mode or if
+ thread-local storage is not available. */
static const char * volatile error_file = NULL;
static long volatile error_line = -1;
@@ -51,9 +99,6 @@ static long volatile error_line = -1;
static const char SVN_FILE_LINE_UNDEFINED[] = "svn:<undefined>";
#endif /* SVN_DEBUG */
-#include "svn_private_config.h"
-#include "private/svn_error_private.h"
-
/*
* Undefine the helpers for creating errors.
@@ -76,11 +121,27 @@ static const char SVN_FILE_LINE_UNDEFINE
void
svn_error__locate(const char *file, long line)
{
-#if defined(SVN_DEBUG)
- /* XXX TODO: Lock mutex here */
+#ifdef SVN_DEBUG
+# if APR_HAS_THREADS
+ static volatile svn_atomic_t init_status = 0;
+ svn_error_clear(svn_atomic__init_once(&init_status,
+ locate_init_once,
+ NULL, NULL));
+
+ if (error_file_key && error_line_key)
+ {
+ apr_status_t status;
+ status = apr_threadkey_private_set((char*)file, error_file_key);
+ if (status == APR_SUCCESS)
+ status = apr_threadkey_private_set((void*)line, error_line_key);
+ if (status == APR_SUCCESS)
+ return;
+ }
+# endif /* APR_HAS_THREADS */
+
error_file = file;
error_line = line;
-#endif
+#endif /* SVN_DEBUG */
}
@@ -103,6 +164,9 @@ make_error_internal(apr_status_t apr_err
{
apr_pool_t *pool;
svn_error_t *new_error;
+#ifdef SVN_DEBUG
+ apr_status_t status = APR_ENOTIMPL;
+#endif
/* Reuse the child's pool, or create our own. */
if (child)
@@ -121,16 +185,34 @@ make_error_internal(apr_status_t apr_err
new_error->apr_err = apr_err;
new_error->child = child;
new_error->pool = pool;
-#if defined(SVN_DEBUG)
- new_error->file = error_file;
- new_error->line = error_line;
- /* XXX TODO: Unlock mutex here */
+
+#ifdef SVN_DEBUG
+#if APR_HAS_THREADS
+ if (error_file_key && error_line_key)
+ {
+ void *item;
+ status = apr_threadkey_private_get(&item, error_file_key);
+ if (status == APR_SUCCESS)
+ {
+ new_error->file = item;
+ status = apr_threadkey_private_get(&item, error_line_key);
+ if (status == APR_SUCCESS)
+ new_error->line = (long)item;
+ }
+ }
+# endif /* APR_HAS_THREADS */
+
+ if (status != APR_SUCCESS)
+ {
+ new_error->file = error_file;
+ new_error->line = error_line;
+ }
if (! child)
apr_pool_cleanup_register(pool, new_error,
err_abort,
apr_pool_cleanup_null);
-#endif
+#endif /* SVN_DEBUG */
return new_error;
}
Modified: subversion/branches/move-tracking-2/subversion/libsvn_subr/hash.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_subr/hash.c?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_subr/hash.c (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_subr/hash.c Mon Mar 9 09:53:06 2015
@@ -31,10 +31,14 @@
#include <apr_hash.h>
#include <apr_file_io.h>
+#ifndef SVN_HASH__GETS_SETS
+#define SVN_HASH__GETS_SETS
+#endif
+#include "svn_hash.h"
+
#include "svn_types.h"
#include "svn_string.h"
#include "svn_error.h"
-#include "svn_hash.h"
#include "svn_sorts.h"
#include "svn_io.h"
#include "svn_pools.h"
@@ -45,7 +49,6 @@
#include "svn_private_config.h"
-
/*
@@ -560,6 +563,20 @@ svn_hash_from_cstring_keys(apr_hash_t **
}
+void *
+svn_hash__gets(apr_hash_t *ht, const char *key)
+{
+ return apr_hash_get(ht, key, APR_HASH_KEY_STRING);
+}
+
+
+void
+svn_hash__sets(apr_hash_t *ht, const char *key, const void *val)
+{
+ apr_hash_set(ht, key, APR_HASH_KEY_STRING, val);
+}
+
+
/*** Specialized getter APIs ***/
Modified: subversion/branches/move-tracking-2/subversion/libsvn_subr/pool.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_subr/pool.c?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_subr/pool.c (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_subr/pool.c Mon Mar 9 09:53:06 2015
@@ -26,12 +26,15 @@
#include <stdlib.h>
#include <stdio.h>
+#include <apr.h>
+#include <apr_version.h>
#include <apr_general.h>
#include <apr_pools.h>
#include <apr_thread_mutex.h>
#include "svn_pools.h"
+#include "pools.h"
#if APR_POOL_DEBUG
/* file_line for the non-debug case. */
@@ -140,3 +143,24 @@ svn_pool_create_allocator(svn_boolean_t
return allocator;
}
+
+
+/*
+ * apr_pool_create_core_ex was introduced in APR 1.3.0, then
+ * deprecated and renamed to apr_pool_create_unmanaged_ex in 1.3.3.
+ * Since our minimum requirement is APR 1.3.0, one or the other of
+ * these functions will always be available.
+ */
+#if !APR_VERSION_AT_LEAST(1,3,3)
+#define apr_pool_create_unmanaged_ex apr_pool_create_core_ex
+#endif
+
+/* Private function that creates an unmanaged pool. */
+apr_pool_t *
+svn_pool__create_unmanaged(svn_boolean_t thread_safe)
+{
+ apr_pool_t *pool;
+ apr_pool_create_unmanaged_ex(&pool, abort_on_pool_failure,
+ svn_pool_create_allocator(thread_safe));
+ return pool;
+}
Modified: subversion/branches/move-tracking-2/subversion/libsvn_subr/sqlite.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_subr/sqlite.c?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_subr/sqlite.c (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_subr/sqlite.c Mon Mar 9 09:53:06 2015
@@ -1307,7 +1307,7 @@ svn_sqlite__finish_transaction(svn_sqlit
err2 = get_internal_statement(&stmt, db,
STMT_INTERNAL_ROLLBACK_TRANSACTION);
if (!err2)
- err2 = svn_sqlite__step_done(stmt);
+ err2 = svn_error_trace(svn_sqlite__step_done(stmt));
if (err2 && err2->apr_err == SVN_ERR_SQLITE_BUSY)
{
@@ -1330,14 +1330,14 @@ svn_sqlite__finish_transaction(svn_sqlit
help diagnosing the original error and help in finding where
a reset statement is missing. */
- err2 = reset_all_statements(db, err2);
+ err2 = svn_error_trace(reset_all_statements(db, err2));
err2 = svn_error_compose_create(
- svn_sqlite__step_done(stmt),
+ svn_error_trace(svn_sqlite__step_done(stmt)),
err2);
+
}
- return svn_error_compose_create(err,
- err2);
+ return svn_error_compose_create(err, err2);
}
SVN_ERR(get_internal_statement(&stmt, db, STMT_INTERNAL_COMMIT_TRANSACTION));
@@ -1358,7 +1358,7 @@ svn_sqlite__finish_savepoint(svn_sqlite_
STMT_INTERNAL_ROLLBACK_TO_SAVEPOINT_SVN);
if (!err2)
- err2 = svn_sqlite__step_done(stmt);
+ err2 = svn_error_trace(svn_sqlite__step_done(stmt));
if (err2 && err2->apr_err == SVN_ERR_SQLITE_BUSY)
{
@@ -1368,8 +1368,10 @@ svn_sqlite__finish_savepoint(svn_sqlite_
### See huge comment in svn_sqlite__finish_transaction for
further details */
- err2 = reset_all_statements(db, err2);
- err2 = svn_error_compose_create(svn_sqlite__step_done(stmt), err2);
+ err2 = svn_error_trace(reset_all_statements(db, err2));
+ err2 = svn_error_compose_create(
+ svn_error_trace(svn_sqlite__step_done(stmt)),
+ err2);
}
err = svn_error_compose_create(err, err2);
@@ -1377,9 +1379,9 @@ svn_sqlite__finish_savepoint(svn_sqlite_
STMT_INTERNAL_RELEASE_SAVEPOINT_SVN);
if (!err2)
- err2 = svn_sqlite__step_done(stmt);
+ err2 = svn_error_trace(svn_sqlite__step_done(stmt));
- return svn_error_trace(svn_error_compose_create(err, err2));
+ return svn_error_compose_create(err, err2);
}
SVN_ERR(get_internal_statement(&stmt, db,
Modified: subversion/branches/move-tracking-2/subversion/libsvn_wc/conflicts.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_wc/conflicts.c?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_wc/conflicts.c (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_wc/conflicts.c Mon Mar 9 09:53:06 2015
@@ -2338,7 +2338,7 @@ static svn_error_t *
resolve_prop_conflict_on_node(svn_boolean_t *did_resolve,
svn_wc__db_t *db,
const char *local_abspath,
- const svn_skel_t *conflicts,
+ svn_skel_t *conflicts,
const char *conflicted_propname,
svn_wc_conflict_choice_t conflict_choice,
const char *merged_file,
@@ -2357,6 +2357,8 @@ resolve_prop_conflict_on_node(svn_boolea
svn_skel_t *work_items = NULL;
svn_wc_operation_t operation;
svn_boolean_t prop_conflicted;
+ apr_hash_t *actual_props;
+ svn_boolean_t resolved_all, resolved_all_prop;
*did_resolve = FALSE;
@@ -2372,12 +2374,35 @@ resolve_prop_conflict_on_node(svn_boolea
db, local_abspath, conflicts,
scratch_pool, scratch_pool));
+ if (!conflicted_props)
+ {
+ /* We have a pre 1.8 property conflict. Just mark it resolved */
+
+ SVN_ERR(remove_artifact_file_if_exists(&work_items, did_resolve,
+ db, local_abspath, prop_reject_file,
+ scratch_pool, scratch_pool));
+ SVN_ERR(svn_wc__db_op_mark_resolved(db, local_abspath, FALSE, TRUE, FALSE,
+ work_items, scratch_pool));
+ SVN_ERR(svn_wc__wq_run(db, local_abspath, cancel_func, cancel_baton,
+ scratch_pool));
+ return SVN_NO_ERROR;
+ }
+
+ if (conflicted_propname[0] != '\0'
+ && !svn_hash_gets(conflicted_props, conflicted_propname))
+ {
+ return SVN_NO_ERROR; /* This property is not conflicted! */
+ }
+
if (operation == svn_wc_operation_merge)
SVN_ERR(svn_wc__db_read_pristine_props(&old_props, db, local_abspath,
scratch_pool, scratch_pool));
else
old_props = their_old_props;
+ SVN_ERR(svn_wc__db_read_props(&actual_props, db, local_abspath,
+ scratch_pool, scratch_pool));
+
/* We currently handle *_conflict as *_full as this argument is currently
always applied for all conflicts on a node at the same time. Giving
an error would break some tests that assumed that this would just
@@ -2405,11 +2430,7 @@ resolve_prop_conflict_on_node(svn_boolea
case svn_wc_conflict_choose_merged:
if ((merged_file || merged_value) && conflicted_propname[0] != '\0')
{
- apr_hash_t *actual_props;
-
- SVN_ERR(svn_wc__db_read_props(&actual_props, db, local_abspath,
- scratch_pool, scratch_pool));
- resolve_from = actual_props;
+ resolve_from = apr_hash_copy(scratch_pool, actual_props);
if (!merged_value)
{
@@ -2433,15 +2454,26 @@ resolve_prop_conflict_on_node(svn_boolea
_("Invalid 'conflict_result' argument"));
}
- if (conflicted_props && apr_hash_count(conflicted_props) && resolve_from)
+
+ if (resolve_from)
{
apr_hash_index_t *hi;
- apr_hash_t *actual_props;
+ apr_hash_t *apply_on_props;
- SVN_ERR(svn_wc__db_read_props(&actual_props, db, local_abspath,
- scratch_pool, scratch_pool));
+ if (conflicted_propname[0] == '\0')
+ {
+ /* Apply to all conflicted properties */
+ apply_on_props = conflicted_props;
+ }
+ else
+ {
+ /* Apply to a single property */
+ apply_on_props = apr_hash_make(scratch_pool);
+ svn_hash_sets(apply_on_props, conflicted_propname, "");
+ }
- for (hi = apr_hash_first(scratch_pool, conflicted_props);
+ /* Apply the selected changes */
+ for (hi = apr_hash_first(scratch_pool, apply_on_props);
hi;
hi = apr_hash_next(hi))
{
@@ -2452,28 +2484,67 @@ resolve_prop_conflict_on_node(svn_boolea
svn_hash_sets(actual_props, propname, new_value);
}
- SVN_ERR(svn_wc__db_op_set_props(db, local_abspath, actual_props,
- FALSE, NULL, NULL,
- scratch_pool));
}
+ /*else the user accepted the properties as-is */
- /* Legacy behavior: Only report property conflicts as resolved when the
- property reject file exists
+ /* This function handles conflicted_propname "" as resolving
+ all property conflicts... Just what we need here */
+ SVN_ERR(svn_wc__conflict_skel_resolve(&resolved_all, conflicts,
+ db, local_abspath,
+ FALSE, conflicted_propname,
+ FALSE,
+ scratch_pool, scratch_pool));
- If not the UI shows the conflict as already resolved
- (and in this case we just remove the in-db conflict) */
+ if (!resolved_all)
+ {
+ /* Are there still property conflicts left? (or only...) */
+ SVN_ERR(svn_wc__conflict_read_info(NULL, NULL, NULL, &prop_conflicted,
+ NULL, db, local_abspath, conflicts,
+ scratch_pool, scratch_pool));
- {
- svn_skel_t *work_item;
+ resolved_all_prop = (! prop_conflicted);
+ }
+ else
+ {
+ resolved_all_prop = TRUE;
+ conflicts = NULL;
+ }
- SVN_ERR(remove_artifact_file_if_exists(&work_item, did_resolve,
- db, local_abspath, prop_reject_file,
- scratch_pool, scratch_pool));
- work_items = svn_wc__wq_merge(work_items, work_item, scratch_pool);
- }
+ if (resolved_all_prop)
+ {
+ /* Legacy behavior: Only report property conflicts as resolved when the
+ property reject file exists
+
+ If not the UI shows the conflict as already resolved
+ (and in this case we just remove the in-db conflict) */
+ SVN_ERR(remove_artifact_file_if_exists(&work_items, did_resolve,
+ db, local_abspath,
+ prop_reject_file,
+ scratch_pool, scratch_pool));
+ }
+ else
+ {
+ /* Create a new prej file, based on the remaining conflicts */
+ SVN_ERR(svn_wc__wq_build_prej_install(&work_items,
+ db, local_abspath,
+ scratch_pool, scratch_pool));
+ *did_resolve = TRUE; /* We resolved a property conflict */
+ }
+
+ /* This installs the updated conflict skel */
+ SVN_ERR(svn_wc__db_op_set_props(db, local_abspath, actual_props,
+ FALSE, conflicts, work_items,
+ scratch_pool));
+
+ if (resolved_all)
+ {
+ /* Remove the whole conflict. Should probably be integrated
+ into the op_set_props() call */
+ SVN_ERR(svn_wc__db_op_mark_resolved(db, local_abspath,
+ FALSE, TRUE, FALSE,
+ NULL, scratch_pool));
+ }
- SVN_ERR(svn_wc__db_op_mark_resolved(db, local_abspath, FALSE, TRUE, FALSE,
- work_items, scratch_pool));
SVN_ERR(svn_wc__wq_run(db, local_abspath, cancel_func, cancel_baton,
scratch_pool));
@@ -2570,7 +2641,8 @@ resolve_tree_conflict_on_node(svn_boolea
const char *dup_abspath;
if (!resolve_later
- || err->apr_err != SVN_ERR_WC_OBSTRUCTED_UPDATE)
+ || (err->apr_err != SVN_ERR_WC_OBSTRUCTED_UPDATE
+ && err->apr_err != SVN_ERR_WC_FOUND_CONFLICT))
return svn_error_trace(err);
svn_error_clear(err);
@@ -2651,7 +2723,8 @@ resolve_tree_conflict_on_node(svn_boolea
const char *dup_abspath;
if (!resolve_later
- || err->apr_err != SVN_ERR_WC_OBSTRUCTED_UPDATE)
+ || (err->apr_err != SVN_ERR_WC_OBSTRUCTED_UPDATE
+ && err->apr_err != SVN_ERR_WC_FOUND_CONFLICT))
return svn_error_trace(err);
svn_error_clear(err);
@@ -3014,33 +3087,11 @@ svn_wc__resolve_conflicts(svn_wc_context
void *notify_baton,
apr_pool_t *scratch_pool)
{
- svn_node_kind_t kind;
- svn_boolean_t conflicted;
struct conflict_status_walker_baton cswb;
apr_pool_t *iterpool = NULL;
svn_error_t *err;
- /* ### the underlying code does NOT support resolving individual
- ### properties. bail out if the caller tries it. */
- if (resolve_prop != NULL && *resolve_prop != '\0')
- return svn_error_create(SVN_ERR_INCORRECT_PARAMS, NULL,
- U_("Resolving a single property is not (yet) "
- "supported."));
-
- /* ### Just a versioned check? */
- /* Conflicted is set to allow invoking on actual only nodes */
- SVN_ERR(svn_wc__db_read_info(NULL, &kind, NULL, NULL, NULL, NULL, NULL,
- NULL, NULL, NULL, NULL, NULL, NULL, NULL,
- NULL, NULL, NULL, NULL, NULL, NULL, &conflicted,
- NULL, NULL, NULL, NULL, NULL, NULL,
- wc_ctx->db, local_abspath,
- scratch_pool, scratch_pool));
-
- /* When the implementation still used the entry walker, depth
- unknown was translated to infinity. */
- if (kind != svn_node_dir)
- depth = svn_depth_empty;
- else if (depth == svn_depth_unknown)
+ if (depth == svn_depth_unknown)
depth = svn_depth_infinity;
cswb.db = wc_ctx->db;
Modified: subversion/branches/move-tracking-2/subversion/libsvn_wc/externals.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_wc/externals.c?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_wc/externals.c (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_wc/externals.c Mon Mar 9 09:53:06 2015
@@ -1496,8 +1496,8 @@ svn_wc__external_remove(svn_wc_context_t
else
{
SVN_ERR(svn_wc__db_base_remove(wc_ctx->db, local_abspath,
- FALSE, FALSE, FALSE,
- SVN_INVALID_REVNUM,
+ FALSE, TRUE, FALSE,
+ 0,
NULL, NULL, scratch_pool));
SVN_ERR(svn_wc__wq_run(wc_ctx->db, local_abspath,
cancel_func, cancel_baton,
Modified: subversion/branches/move-tracking-2/subversion/libsvn_wc/status.c
URL: http://svn.apache.org/viewvc/subversion/branches/move-tracking-2/subversion/libsvn_wc/status.c?rev=1665166&r1=1665165&r2=1665166&view=diff
==============================================================================
--- subversion/branches/move-tracking-2/subversion/libsvn_wc/status.c (original)
+++ subversion/branches/move-tracking-2/subversion/libsvn_wc/status.c Mon Mar 9 09:53:06 2015
@@ -69,6 +69,7 @@ typedef struct svn_wc__internal_status_t
svn_wc_status3_t s; /* First member; same pointer*/
svn_boolean_t has_descendants;
+ svn_boolean_t op_root;
/* Make sure to update hash_stash() when adding values here */
} svn_wc__internal_status_t;
@@ -587,7 +588,8 @@ assemble_status(svn_wc__internal_status_
This filter should match the filter in is_sendable_status() */
if (! get_all)
if (((node_status == svn_wc_status_none)
- || (node_status == svn_wc_status_normal))
+ || (node_status == svn_wc_status_normal)
+ || (node_status == svn_wc_status_deleted && !info->op_root))
&& (! switched_p)
&& (! info->locked)
@@ -606,6 +608,7 @@ assemble_status(svn_wc__internal_status_
inner_stat = apr_pcalloc(result_pool, sizeof(*inner_stat));
stat = &inner_stat->s;
inner_stat->has_descendants = info->has_descendants;
+ inner_stat->op_root = info->op_root;
switch (info->kind)
{
@@ -1484,6 +1487,7 @@ hash_stash(void *baton,
/* Copy the internal/private data. */
svn_wc__internal_status_t *is = new_status;
is->has_descendants = old_status->has_descendants;
+ is->op_root = old_status->op_root;
assert(! svn_hash_gets(stat_hash, path));
svn_hash_sets(stat_hash, apr_pstrdup(hash_pool, path), new_status);
@@ -1865,7 +1869,9 @@ is_sendable_status(const svn_wc__interna
/* If the text, property or tree state is interesting, send it. */
if ((status->node_status != svn_wc_status_none)
- && (status->node_status != svn_wc_status_normal))
+ && (status->node_status != svn_wc_status_normal)
+ && !(status->node_status == svn_wc_status_deleted
+ && !i_status->op_root))
return TRUE;
/* If it's switched, send it. */