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 2019/01/30 21:55:09 UTC
svn commit: r1852559 - in /subversion/trunk/subversion:
include/private/svn_client_private.h libsvn_client/copy.c
libsvn_client/shelf.c libsvn_client/wc_editor.c
Author: julianfoad
Date: Wed Jan 30 21:55:08 2019
New Revision: 1852559
URL: http://svn.apache.org/viewvc?rev=1852559&view=rev
Log:
Teach the WC editor to acquire and release a WC write lock.
* subversion/include/private/svn_client_private.h
(svn_client__wc_editor): Document that it manages the write lock.
(svn_client__wc_editor_internal): Add an option flag to manage the write lock.
* subversion/libsvn_client/copy.c
(copy_foreign_dir,
svn_client__repos_to_wc_copy_by_editor): Ask the WC editor not to manage
the write lock for us here, as the caller does it.
* subversion/libsvn_client/shelf.c
(svn_client__shelf_apply): Don't aquire and release the write lock here:
let the WC editor do it.
* subversion/libsvn_client/wc_editor.c
(edit_baton_t): Add fields to manage the write lock.
(release_write_lock,
pool_cleanup_handler): New.
(edit_open): If requested, acquire the write lock and arrange for it to be
released on pool clean-up.
(edit_close): If acquired, release the write lock.
(svn_client__wc_editor_internal): Add the option flag to manage the write
lock. Initialize the 'abort_edit' method so that it will release the
write lock, the same as 'close_edit'.
(svn_client__wc_editor): Ask for the write lock to be managed.
Modified:
subversion/trunk/subversion/include/private/svn_client_private.h
subversion/trunk/subversion/libsvn_client/copy.c
subversion/trunk/subversion/libsvn_client/shelf.c
subversion/trunk/subversion/libsvn_client/wc_editor.c
Modified: subversion/trunk/subversion/include/private/svn_client_private.h
URL: http://svn.apache.org/viewvc/subversion/trunk/subversion/include/private/svn_client_private.h?rev=1852559&r1=1852558&r2=1852559&view=diff
==============================================================================
--- subversion/trunk/subversion/include/private/svn_client_private.h (original)
+++ subversion/trunk/subversion/include/private/svn_client_private.h Wed Jan 30 21:55:08 2019
@@ -447,6 +447,9 @@ svn_client__repos_to_wc_copy_by_editor(s
* RA_SESSION is used to fetch the original content for copies.
*
* Ignore changes to non-regular property (entry-props, DAV/WC-props).
+ *
+ * Acquire the WC write lock in 'open_root' and release it in
+ * 'close_edit', in 'abort_edit', or when @a result_pool is cleared.
*/
svn_error_t *
svn_client__wc_editor(const svn_delta_editor_t **editor_p,
@@ -468,6 +471,10 @@ svn_client__wc_editor(const svn_delta_ed
*
* If @a ignore_mergeinfo_changes is true, ignore any incoming changes
* to the 'svn:mergeinfo' property.
+ *
+ * If @a manage_wc_write_lock is true, acquire the WC write lock in
+ * 'open_root' and release it in 'close_edit', in 'abort_edit', or
+ * when @a result_pool is cleared.
*/
svn_error_t *
svn_client__wc_editor_internal(const svn_delta_editor_t **editor_p,
@@ -475,6 +482,7 @@ svn_client__wc_editor_internal(const svn
const char *dst_abspath,
svn_boolean_t root_dir_add,
svn_boolean_t ignore_mergeinfo_changes,
+ svn_boolean_t manage_wc_write_lock,
svn_wc_notify_func2_t notify_func,
void *notify_baton,
svn_ra_session_t *ra_session,
Modified: subversion/trunk/subversion/libsvn_client/copy.c
URL: http://svn.apache.org/viewvc/subversion/trunk/subversion/libsvn_client/copy.c?rev=1852559&r1=1852558&r2=1852559&view=diff
==============================================================================
--- subversion/trunk/subversion/libsvn_client/copy.c (original)
+++ subversion/trunk/subversion/libsvn_client/copy.c Wed Jan 30 21:55:08 2019
@@ -2384,6 +2384,7 @@ copy_foreign_dir(svn_ra_session_t *ra_se
dst_abspath,
TRUE /*root_dir_add*/,
TRUE /*ignore_mergeinfo_changes*/,
+ FALSE /*manage_wc_write_lock*/,
notify_func, notify_baton,
NULL /*ra_session*/,
ctx, scratch_pool));
@@ -2652,11 +2653,15 @@ svn_client__repos_to_wc_copy_by_editor(s
SVN_ERR(svn_ra_reparent(ra_session, src_anchor, scratch_pool));
- SVN_ERR(svn_client__wc_editor(&editor, &eb,
- svn_dirent_dirname(dst_abspath, scratch_pool),
- ctx->notify_func2, ctx->notify_baton2,
- ra_session,
- ctx, scratch_pool));
+ SVN_ERR(svn_client__wc_editor_internal(
+ &editor, &eb,
+ svn_dirent_dirname(dst_abspath, scratch_pool),
+ FALSE /*root_dir_add*/,
+ FALSE /*ignore_mergeinfo_changes*/,
+ FALSE /*manage_wc_write_lock*/,
+ ctx->notify_func2, ctx->notify_baton2,
+ ra_session,
+ ctx, scratch_pool));
SVN_ERR(editor->open_root(eb, SVN_INVALID_REVNUM, scratch_pool, &rb));
if (kind == svn_node_dir)
Modified: subversion/trunk/subversion/libsvn_client/shelf.c
URL: http://svn.apache.org/viewvc/subversion/trunk/subversion/libsvn_client/shelf.c?rev=1852559&r1=1852558&r2=1852559&view=diff
==============================================================================
--- subversion/trunk/subversion/libsvn_client/shelf.c (original)
+++ subversion/trunk/subversion/libsvn_client/shelf.c Wed Jan 30 21:55:08 2019
@@ -1961,12 +1961,9 @@ svn_client__shelf_apply(svn_client__shel
shelf->wc_root_abspath,
shelf->ctx, scratch_pool));
- SVN_WC__CALL_WITH_WRITE_LOCK(
- svn_client__shelf_replay(shelf_version, "",
- editor, edit_baton,
- scratch_pool),
- shelf->ctx->wc_ctx, shelf->wc_root_abspath,
- FALSE /*lock_anchor*/, scratch_pool);
+ SVN_ERR(svn_client__shelf_replay(shelf_version, "",
+ editor, edit_baton,
+ scratch_pool));
svn_io_sleep_for_timestamps(shelf->wc_root_abspath,
scratch_pool);
Modified: subversion/trunk/subversion/libsvn_client/wc_editor.c
URL: http://svn.apache.org/viewvc/subversion/trunk/subversion/libsvn_client/wc_editor.c?rev=1852559&r1=1852558&r2=1852559&view=diff
==============================================================================
--- subversion/trunk/subversion/libsvn_client/wc_editor.c (original)
+++ subversion/trunk/subversion/libsvn_client/wc_editor.c Wed Jan 30 21:55:08 2019
@@ -74,6 +74,8 @@
struct edit_baton_t
{
const char *anchor_abspath;
+ svn_boolean_t manage_wc_write_lock;
+ const char *lock_root_abspath; /* the path locked, when locked */
/* True => 'open_root' method will act as 'add_directory' */
svn_boolean_t root_dir_add;
@@ -163,6 +165,31 @@ dir_open_or_add(struct dir_baton_t **chi
return SVN_NO_ERROR;
}
+/* */
+static svn_error_t *
+release_write_lock(struct edit_baton_t *eb,
+ apr_pool_t *scratch_pool)
+{
+ if (eb->lock_root_abspath)
+ {
+ SVN_ERR(svn_wc__release_write_lock(
+ eb->ctx->wc_ctx, eb->lock_root_abspath, scratch_pool));
+ eb->lock_root_abspath = NULL;
+ }
+ return SVN_NO_ERROR;
+}
+
+/* */
+static apr_status_t
+pool_cleanup_handler(void *root_baton)
+{
+ struct dir_baton_t *db = root_baton;
+ struct edit_baton_t *eb = db->eb;
+
+ svn_error_clear(release_write_lock(eb, db->pool));
+ return APR_SUCCESS;
+}
+
/* svn_delta_editor_t function */
static svn_error_t *
edit_open(void *edit_baton,
@@ -175,6 +202,19 @@ edit_open(void *edit_baton,
SVN_ERR(dir_open_or_add(&db, "", NULL, eb, result_pool));
+ /* Acquire a WC write lock */
+ if (eb->manage_wc_write_lock)
+ {
+ apr_pool_cleanup_register(db->pool, db,
+ pool_cleanup_handler,
+ apr_pool_cleanup_null);
+ SVN_ERR(svn_wc__acquire_write_lock(&eb->lock_root_abspath,
+ eb->ctx->wc_ctx,
+ eb->anchor_abspath,
+ FALSE /*lock_anchor*/,
+ db->pool, db->pool));
+ }
+
if (eb->root_dir_add)
{
SVN_ERR(mkdir(db->local_abspath, eb, result_pool));
@@ -186,9 +226,10 @@ edit_open(void *edit_baton,
/* svn_delta_editor_t function */
static svn_error_t *
-edit_close(void *edit_baton,
- apr_pool_t *scratch_pool)
+edit_close_or_abort(void *edit_baton,
+ apr_pool_t *scratch_pool)
{
+ SVN_ERR(release_write_lock(edit_baton, scratch_pool));
return SVN_NO_ERROR;
}
@@ -509,6 +550,7 @@ svn_client__wc_editor_internal(const svn
const char *dst_abspath,
svn_boolean_t root_dir_add,
svn_boolean_t ignore_mergeinfo_changes,
+ svn_boolean_t manage_wc_write_lock,
svn_wc_notify_func2_t notify_func,
void *notify_baton,
svn_ra_session_t *ra_session,
@@ -519,6 +561,8 @@ svn_client__wc_editor_internal(const svn
struct edit_baton_t *eb = apr_pcalloc(result_pool, sizeof(*eb));
eb->anchor_abspath = apr_pstrdup(result_pool, dst_abspath);
+ eb->manage_wc_write_lock = manage_wc_write_lock;
+ eb->lock_root_abspath = NULL;
eb->root_dir_add = root_dir_add;
eb->ignore_mergeinfo_changes = ignore_mergeinfo_changes;
@@ -529,7 +573,8 @@ svn_client__wc_editor_internal(const svn
eb->notify_baton = notify_baton;
editor->open_root = edit_open;
- editor->close_edit = edit_close;
+ editor->close_edit = edit_close_or_abort;
+ editor->abort_edit = edit_close_or_abort;
editor->delete_entry = delete_entry;
@@ -563,6 +608,7 @@ svn_client__wc_editor(const svn_delta_ed
dst_abspath,
FALSE /*root_dir_add*/,
FALSE /*ignore_mergeinfo_changes*/,
+ TRUE /*manage_wc_write_lock*/,
notify_func, notify_baton,
ra_session,
ctx, result_pool));