You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@subversion.apache.org by br...@apache.org on 2012/08/16 12:18:03 UTC
svn commit: r1373783 [31/50] - in /subversion/branches/compressed-pristines:
./ build/ build/ac-macros/ build/generator/ build/generator/templates/
build/win32/ contrib/client-side/emacs/ contrib/client-side/svn-push/
contrib/client-side/svnmerge/ cont...
Modified: subversion/branches/compressed-pristines/subversion/libsvn_wc/update_editor.c
URL: http://svn.apache.org/viewvc/subversion/branches/compressed-pristines/subversion/libsvn_wc/update_editor.c?rev=1373783&r1=1373782&r2=1373783&view=diff
==============================================================================
--- subversion/branches/compressed-pristines/subversion/libsvn_wc/update_editor.c (original)
+++ subversion/branches/compressed-pristines/subversion/libsvn_wc/update_editor.c Thu Aug 16 10:17:48 2012
@@ -46,10 +46,12 @@
#include "wc.h"
#include "adm_files.h"
+#include "conflicts.h"
#include "entries.h"
#include "translate.h"
#include "workqueue.h"
+#include "private/svn_subr_private.h"
#include "private/svn_wc_private.h"
/* Checks whether a svn_wc__db_status_t indicates whether a node is
present in a working copy. Used by the editor implementation */
@@ -284,19 +286,15 @@ struct dir_baton
/* Absolute path of this directory */
const char *local_abspath;
- /* Absolute path to the new location of the directory if it was moved away,
- * and the op-root of the move operation.
- * This is set on the root of a move operation and all children.
- * If the directory was not moved away, this is NULL. */
- const char *moved_to_abspath;
- const char *moved_to_op_root_abspath;
-
/* The repository relative path this directory will correspond to. */
const char *new_relpath;
/* The revision of the directory before updating */
svn_revnum_t old_revision;
+ /* The repos_relpath before updating/switching */
+ const char *old_repos_relpath;
+
/* The global edit baton. */
struct edit_baton *edit_baton;
@@ -324,7 +322,7 @@ struct dir_baton
const char *changed_author;
/* If not NULL, contains a mapping of const char* basenames of children that
- have been deleted to their svn_wc_conflict_description2_t* tree conflicts.
+ have been deleted to their svn_skel_t* tree conflicts.
We store this hash to allow replacements to continue under a just
installed tree conflict.
@@ -354,7 +352,7 @@ struct dir_baton
svn_boolean_t edited;
/* The tree conflict to install once the node is really edited */
- svn_wc_conflict_description2_t *edit_conflict;
+ svn_skel_t *edit_conflict;
/* The bump information for this directory. */
struct bump_dir_info *bump_info;
@@ -625,8 +623,6 @@ make_dir_baton(struct dir_baton **d_p,
d->adding_dir = adding;
d->changed_rev = SVN_INVALID_REVNUM;
d->not_present_files = apr_hash_make(dir_pool);
- d->moved_to_abspath = NULL;
- d->moved_to_op_root_abspath = NULL;
/* Copy some flags from the parent baton */
if (pb)
@@ -709,16 +705,15 @@ struct file_baton
/* Absolute path to this file */
const char *local_abspath;
- /* Absolute path to the new location of the file if it was moved away.
- * If the file was not moved away, this is NULL. */
- const char *moved_to_abspath;
-
/* The repository relative path this file will correspond to. */
const char *new_relpath;
/* The revision of the file before updating */
svn_revnum_t old_revision;
+ /* The repos_relpath before updating/switching */
+ const char *old_repos_relpath;
+
/* The global edit baton. */
struct edit_baton *edit_baton;
@@ -773,7 +768,7 @@ struct file_baton
svn_boolean_t edited;
/* The tree conflict to install once the node is really edited */
- svn_wc_conflict_description2_t *edit_conflict;
+ svn_skel_t *edit_conflict;
};
@@ -849,6 +844,56 @@ make_file_baton(struct file_baton **f_p,
return SVN_NO_ERROR;
}
+/* Complete a conflict skel by describing the update.
+ *
+ * All temporary allocations are be made in SCRATCH_POOL, while allocations
+ * needed for the returned conflict struct are made in RESULT_POOL.
+ */
+static svn_error_t *
+complete_conflict(svn_skel_t *conflict,
+ const struct dir_baton *pb,
+ const char *local_abspath,
+ const char *old_repos_relpath,
+ svn_revnum_t old_revision,
+ svn_node_kind_t kind,
+ apr_pool_t *result_pool, apr_pool_t *scratch_pool)
+{
+ const struct edit_baton *eb = pb->edit_baton;
+ svn_wc_conflict_version_t *src_left_version;
+ svn_boolean_t is_complete;
+
+ if (!conflict)
+ return SVN_NO_ERROR; /* Not conflicted */
+
+ SVN_ERR(svn_wc__conflict_skel_is_complete(&is_complete, conflict));
+
+ if (is_complete)
+ return SVN_NO_ERROR; /* Already competed */
+
+ if (old_repos_relpath)
+ src_left_version = svn_wc_conflict_version_create2(eb->repos_root,
+ eb->repos_uuid,
+ old_repos_relpath,
+ old_revision,
+ kind,
+ result_pool);
+ else
+ src_left_version = NULL;
+
+
+ if (eb->switch_relpath)
+ SVN_ERR(svn_wc__conflict_skel_set_op_switch(conflict,
+ src_left_version,
+ result_pool, scratch_pool));
+ else
+ SVN_ERR(svn_wc__conflict_skel_set_op_update(conflict,
+ src_left_version,
+ result_pool, scratch_pool));
+
+ return SVN_NO_ERROR;
+}
+
+
/* Called when a directory is really edited, to avoid marking a
tree conflict on a node for a no-change edit */
static svn_error_t *
@@ -865,10 +910,15 @@ mark_directory_edited(struct dir_baton *
if (db->edit_conflict)
{
/* We have a (delayed) tree conflict to install */
- SVN_ERR(svn_wc__db_op_set_tree_conflict(db->edit_baton->db,
- db->local_abspath,
- db->edit_conflict,
- scratch_pool));
+
+ SVN_ERR(complete_conflict(db->edit_conflict, db->parent_baton,
+ db->local_abspath, db->old_repos_relpath,
+ db->old_revision, svn_node_dir,
+ db->pool, scratch_pool));
+ SVN_ERR(svn_wc__db_op_mark_conflict(db->edit_baton->db,
+ db->local_abspath,
+ db->edit_conflict, NULL,
+ scratch_pool));
do_notification(db->edit_baton, db->local_abspath, svn_node_dir,
svn_wc_notify_tree_conflict, scratch_pool);
@@ -893,10 +943,16 @@ mark_file_edited(struct file_baton *fb,
if (fb->edit_conflict)
{
/* We have a (delayed) tree conflict to install */
- SVN_ERR(svn_wc__db_op_set_tree_conflict(fb->edit_baton->db,
- fb->local_abspath,
- fb->edit_conflict,
- scratch_pool));
+
+ SVN_ERR(complete_conflict(fb->edit_conflict, fb->dir_baton,
+ fb->local_abspath, fb->old_repos_relpath,
+ fb->old_revision, svn_node_file,
+ fb->pool, scratch_pool));
+
+ SVN_ERR(svn_wc__db_op_mark_conflict(fb->edit_baton->db,
+ fb->local_abspath,
+ fb->edit_conflict, NULL,
+ scratch_pool));
do_notification(fb->edit_baton, fb->local_abspath, svn_node_file,
svn_wc_notify_tree_conflict, scratch_pool);
@@ -961,8 +1017,7 @@ window_handler(svn_txdelta_window_t *win
{
/* Tell the file baton about the new text base's checksums. */
fb->new_text_base_md5_checksum =
- svn_checksum__from_digest(hb->new_text_base_md5_digest,
- svn_checksum_md5, fb->pool);
+ svn_checksum__from_digest_md5(hb->new_text_base_md5_digest, fb->pool);
fb->new_text_base_sha1_checksum =
svn_checksum_dup(hb->new_text_base_sha1_checksum, fb->pool);
@@ -1131,7 +1186,8 @@ open_root(void *edit_baton,
/* For an update with a NULL target, this is equivalent to open_dir(): */
/* Read the depth from the entry. */
- SVN_ERR(svn_wc__db_base_get_info(&status, NULL, NULL, NULL, NULL, NULL,
+ SVN_ERR(svn_wc__db_base_get_info(&status, NULL, &db->old_revision,
+ &db->old_repos_relpath, NULL, NULL,
&db->changed_rev, &db->changed_date,
&db->changed_author, &db->ambient_depth,
NULL, NULL, NULL, NULL, NULL,
@@ -1146,25 +1202,6 @@ open_root(void *edit_baton,
pool));
}
- /* Check if this directory was moved away. */
- err = svn_wc__db_read_info(&status, NULL, NULL, NULL, NULL, NULL, NULL,
- NULL, NULL, NULL, NULL, NULL, NULL, NULL,
- NULL, NULL, NULL, NULL, NULL, NULL,
- NULL, NULL, NULL, NULL,
- NULL, NULL, NULL,
- eb->db, db->local_abspath, pool, pool);
- if (err)
- {
- if (err->apr_err == SVN_ERR_WC_PATH_NOT_FOUND)
- svn_error_clear(err);
- else
- return svn_error_trace(err);
- }
- else if (status == svn_wc__db_status_deleted)
- SVN_ERR(svn_wc__db_scan_deletion(NULL, &db->moved_to_abspath, NULL,
- &db->moved_to_op_root_abspath,
- eb->db, db->local_abspath, db->pool, pool));
-
return SVN_NO_ERROR;
}
@@ -1178,6 +1215,7 @@ typedef struct modcheck_baton_t {
svn_boolean_t found_mod; /* whether a modification has been found */
svn_boolean_t found_not_delete; /* Found a not-delete modification */
svn_boolean_t is_copy; /* check for post-copy modifications only */
+ const char *modcheck_root_abspath;
} modcheck_baton_t;
/* An implementation of svn_wc_status_func4_t. */
@@ -1207,10 +1245,19 @@ modcheck_callback(void *baton,
case svn_wc_status_obstructed:
if (status->prop_status != svn_wc_status_modified)
break;
- /* Fall through in the found modification case */
+
+ mb->found_mod = TRUE;
+ mb->found_not_delete = TRUE;
+ /* Exit from the status walker: We know what we want to know */
+ return svn_error_create(SVN_ERR_CEASE_INVOCATION, NULL, NULL);
case svn_wc_status_added:
- if (!mb->is_copy)
+ /* Ignore the copy status if we expect a copy, but don't ignore
+ other changes */
+ if (!mb->is_copy
+ || status->text_status == svn_wc_status_modified
+ || status->prop_status == svn_wc_status_modified
+ || strcmp(mb->modcheck_root_abspath, local_abspath) != 0)
{
mb->found_mod = TRUE;
mb->found_not_delete = TRUE;
@@ -1254,6 +1301,7 @@ node_has_local_mods(svn_boolean_t *modif
modcheck_baton.db = db;
modcheck_baton.is_copy = is_copy;
+ modcheck_baton.modcheck_root_abspath = local_abspath;
/* Walk the WC tree for status with depth infinity, looking for any local
* modifications. If it's a "sparse" directory, that's OK: there can be
@@ -1277,194 +1325,9 @@ node_has_local_mods(svn_boolean_t *modif
return SVN_NO_ERROR;
}
-
/* Indicates an unset svn_wc_conflict_reason_t. */
#define SVN_WC_CONFLICT_REASON_NONE (svn_wc_conflict_reason_t)(-1)
-/* Create a tree conflict struct.
- *
- * The REASON is stored directly in the tree conflict info.
- *
- * All temporary allocactions are be made in SCRATCH_POOL, while allocations
- * needed for the returned conflict struct are made in RESULT_POOL.
- *
- * All other parameters are identical to and described by
- * check_tree_conflict(), with the slight modification that this function
- * relies on the reason passed in REASON instead of actively looking for one. */
-static svn_error_t *
-create_tree_conflict(svn_wc_conflict_description2_t **pconflict,
- struct edit_baton *eb,
- const char *local_abspath,
- svn_wc_conflict_reason_t reason,
- svn_wc_conflict_action_t action,
- svn_node_kind_t their_node_kind,
- const char *their_relpath,
- apr_pool_t *result_pool, apr_pool_t *scratch_pool)
-{
- const char *repos_root_url = NULL;
- const char *left_repos_relpath;
- svn_revnum_t left_revision;
- svn_node_kind_t left_kind;
- const char *right_repos_relpath;
- const char *added_repos_relpath = NULL;
- svn_node_kind_t conflict_node_kind;
- svn_wc_conflict_version_t *src_left_version;
- svn_wc_conflict_version_t *src_right_version;
-
- *pconflict = NULL;
-
- SVN_ERR_ASSERT(reason != SVN_WC_CONFLICT_REASON_NONE);
- SVN_ERR_ASSERT(their_relpath != NULL);
-
- /* Get the source-left information, i.e. the local state of the node
- * before any changes were made to the working copy, i.e. the state the
- * node would have if it was reverted. */
- if (reason == svn_wc_conflict_reason_added ||
- reason == svn_wc_conflict_reason_moved_here)
- {
- svn_wc__db_status_t added_status;
-
- /* ###TODO: It would be nice to tell the user at which URL and
- * ### revision source-left was empty, which could be quite difficult
- * ### to code, and is a slight theoretical leap of the svn mind.
- * ### Update should show
- * ### URL: svn_wc__db_scan_addition( &repos_relpath )
- * ### REV: The base revision of the parent of before this update
- * ### started
- * ### ### BUT what if parent was updated/switched away with
- * ### ### depth=empty after this node was added?
- * ### Switch should show
- * ### URL: scan_addition URL of before this switch started
- * ### REV: same as above */
-
- /* In case of a local addition, source-left is non-existent / empty. */
- left_kind = svn_node_none;
- left_revision = SVN_INVALID_REVNUM;
- left_repos_relpath = NULL;
-
- /* Still get the repository root needed by both 'update' and 'switch',
- * and the would-be repos_relpath needed to construct the source-right
- * in case of an 'update'. Check sanity while we're at it. */
- SVN_ERR(svn_wc__db_scan_addition(&added_status, NULL,
- &added_repos_relpath,
- &repos_root_url,
- NULL, NULL, NULL, NULL, NULL, NULL,
- NULL, eb->db, local_abspath,
- result_pool, scratch_pool));
-
- /* This better really be an added status. */
- SVN_ERR_ASSERT(added_status == svn_wc__db_status_added
- || added_status == svn_wc__db_status_copied
- || added_status == svn_wc__db_status_moved_here);
- }
- else if (reason == svn_wc_conflict_reason_unversioned)
- {
- /* Obstructed by an unversioned node. Source-left is
- * non-existent/empty. */
- left_kind = svn_node_none;
- left_revision = SVN_INVALID_REVNUM;
- left_repos_relpath = NULL;
- repos_root_url = eb->repos_root;
- }
- else
- {
- /* A BASE node should exist. */
- svn_kind_t base_kind;
-
- /* If anything else shows up, then this assertion is probably naive
- * and that other case should also be handled. */
- SVN_ERR_ASSERT(reason == svn_wc_conflict_reason_edited
- || reason == svn_wc_conflict_reason_deleted
- || reason == svn_wc_conflict_reason_moved_away
- || reason == svn_wc_conflict_reason_moved_away_and_edited
- || reason == svn_wc_conflict_reason_replaced
- || reason == svn_wc_conflict_reason_obstructed);
-
- SVN_ERR(svn_wc__db_base_get_info(NULL, &base_kind,
- &left_revision,
- &left_repos_relpath,
- &repos_root_url,
- NULL, NULL, NULL, NULL, NULL, NULL,
- NULL, NULL, NULL, NULL,
- eb->db,
- local_abspath,
- result_pool,
- scratch_pool));
- /* Translate the node kind. */
- if (base_kind == svn_kind_file
- || base_kind == svn_kind_symlink)
- left_kind = svn_node_file;
- else if (base_kind == svn_kind_dir)
- left_kind = svn_node_dir;
- else
- SVN_ERR_MALFUNCTION();
- }
-
- SVN_ERR_ASSERT(strcmp(repos_root_url, eb->repos_root) == 0);
-
- /* Find the source-right information, i.e. the state in the repository
- * to which we would like to update. */
- if (eb->switch_relpath)
- {
- /* This is a 'switch' operation. */
- right_repos_relpath = their_relpath;
- }
- else
- {
- /* This is an 'update', so REPOS_RELPATH would be the same as for
- * source-left. However, we don't have a source-left for locally
- * added files. */
- right_repos_relpath = ((reason == svn_wc_conflict_reason_added ||
- reason == svn_wc_conflict_reason_moved_here) ?
- added_repos_relpath : left_repos_relpath);
- if (! right_repos_relpath)
- right_repos_relpath = their_relpath;
- }
-
- SVN_ERR_ASSERT(right_repos_relpath != NULL);
-
- /* Determine PCONFLICT's overall node kind, which is not allowed to be
- * svn_node_none. We give it the source-right revision (THEIR_NODE_KIND)
- * -- unless source-right is deleted and hence == svn_node_none, in which
- * case we take it from source-left, which has to be the node kind that
- * was deleted. */
- conflict_node_kind = (action == svn_wc_conflict_action_delete ?
- left_kind : their_node_kind);
- SVN_ERR_ASSERT(conflict_node_kind == svn_node_file
- || conflict_node_kind == svn_node_dir);
-
-
- /* Construct the tree conflict info structs. */
-
- if (left_repos_relpath == NULL)
- /* A locally added or unversioned path in conflict with an incoming add.
- * Send an 'empty' left revision. */
- src_left_version = NULL;
- else
- src_left_version = svn_wc_conflict_version_create(repos_root_url,
- left_repos_relpath,
- left_revision,
- left_kind,
- result_pool);
-
- src_right_version = svn_wc_conflict_version_create(repos_root_url,
- right_repos_relpath,
- *eb->target_revision,
- their_node_kind,
- result_pool);
-
- *pconflict = svn_wc_conflict_description_create_tree2(
- local_abspath, conflict_node_kind,
- eb->switch_relpath ?
- svn_wc_operation_switch : svn_wc_operation_update,
- src_left_version, src_right_version, result_pool);
- (*pconflict)->action = action;
- (*pconflict)->reason = reason;
-
- return SVN_NO_ERROR;
-}
-
-
/* Check whether the incoming change ACTION on FULL_PATH would conflict with
* LOCAL_ABSPATH's scheduled change. If so, then raise a tree conflict with
* LOCAL_ABSPATH as the victim.
@@ -1480,39 +1343,24 @@ create_tree_conflict(svn_wc_conflict_des
* tree conflict info is returned in *PCONFLICT. PCONFLICT must be non-NULL,
* while *PCONFLICT is always overwritten.
*
- * THEIR_NODE_KIND should be the node kind reflected by the incoming edit
- * function. E.g. dir_opened() should pass svn_node_dir, etc.
- * In some cases of delete, svn_node_none may be used here.
- *
- * THEIR_RELPATH should be the involved node's repository-relative path on the
- * source-right side, the side that the target should become after the update.
- * Simply put, that's the URL obtained from the node's dir_baton->new_relpath
- * or file_baton->new_relpath (but it's more complex for a delete).
- *
* The tree conflict is allocated in RESULT_POOL. Temporary allocations use
- * SCRACTH_POOl.
+ * SCRATCH_POOL.
*/
static svn_error_t *
-check_tree_conflict(svn_wc_conflict_description2_t **pconflict,
+check_tree_conflict(svn_skel_t **pconflict,
struct edit_baton *eb,
const char *local_abspath,
svn_wc__db_status_t working_status,
svn_kind_t working_kind,
svn_boolean_t exists_in_repos,
svn_wc_conflict_action_t action,
- svn_node_kind_t their_node_kind,
- const char *their_relpath,
- const char *moved_to_abspath,
apr_pool_t *result_pool,
apr_pool_t *scratch_pool)
{
svn_wc_conflict_reason_t reason = SVN_WC_CONFLICT_REASON_NONE;
- svn_boolean_t locally_replaced = FALSE;
svn_boolean_t modified = FALSE;
svn_boolean_t all_mods_are_deletes = FALSE;
- SVN_ERR_ASSERT(their_relpath != NULL);
-
*pconflict = NULL;
/* Find out if there are any local changes to this node that may
@@ -1522,21 +1370,7 @@ check_tree_conflict(svn_wc_conflict_desc
case svn_wc__db_status_added:
case svn_wc__db_status_moved_here:
case svn_wc__db_status_copied:
- /* Is it a replace? */
- if (exists_in_repos)
- {
- svn_wc__db_status_t base_status;
- SVN_ERR(svn_wc__db_base_get_info(&base_status, NULL, NULL,
- NULL, NULL, NULL, NULL, NULL,
- NULL, NULL, NULL, NULL, NULL,
- NULL, NULL,
- eb->db, local_abspath,
- scratch_pool, scratch_pool));
- if (base_status != svn_wc__db_status_not_present)
- locally_replaced = TRUE;
- }
-
- if (!locally_replaced)
+ if (!exists_in_repos)
{
/* The node is locally added, and it did not exist before. This
* is an 'update', so the local add can only conflict with an
@@ -1570,28 +1404,7 @@ check_tree_conflict(svn_wc_conflict_desc
case svn_wc__db_status_deleted:
- if (!moved_to_abspath)
- reason = svn_wc_conflict_reason_deleted;
- else if (action == svn_wc_conflict_action_delete)
- {
- svn_boolean_t all_edits_are_deletes = FALSE;
-
- /* The update wants to delete a node which was locally moved
- * away. We allow this only if the node wasn't modified post-move.
- * If the only post-move changes within a subtree are deletions,
- * allow the update to delete the entire subtree. */
- if (working_kind == svn_kind_dir)
- SVN_ERR(node_has_local_mods(&modified, &all_edits_are_deletes,
- TRUE, eb->db, moved_to_abspath,
- eb->cancel_func, eb->cancel_baton,
- scratch_pool));
- else
- SVN_ERR(svn_wc__internal_file_modified_p(&modified, eb->db,
- moved_to_abspath,
- FALSE, scratch_pool));
- if (modified && !all_edits_are_deletes)
- reason = svn_wc_conflict_reason_moved_away_and_edited;
- }
+ reason = svn_wc_conflict_reason_deleted;
break;
case svn_wc__db_status_incomplete:
@@ -1608,6 +1421,10 @@ check_tree_conflict(svn_wc_conflict_desc
* but we don't handle those here.) */
return SVN_NO_ERROR;
+ /* Replace is handled as delete and then specifically in
+ add_directory() and add_file(), so we only expect deletes here */
+ SVN_ERR_ASSERT(action == svn_wc_conflict_action_delete);
+
/* Check if the update wants to delete or replace a locally
* modified node. */
@@ -1672,12 +1489,16 @@ check_tree_conflict(svn_wc_conflict_desc
SVN_ERR_ASSERT(action == svn_wc_conflict_action_add);
- /* A conflict was detected. Append log commands to the log accumulator
- * to record it. */
- return svn_error_trace(create_tree_conflict(pconflict, eb, local_abspath,
- reason, action, their_node_kind,
- their_relpath,
- result_pool, scratch_pool));
+ /* A conflict was detected. Create a conflict skel to record it. */
+ *pconflict = svn_wc__conflict_skel_create(result_pool);
+
+ SVN_ERR(svn_wc__conflict_skel_add_tree_conflict(*pconflict,
+ eb->db, local_abspath,
+ reason,
+ action,
+ result_pool, scratch_pool));
+
+ return SVN_NO_ERROR;
}
@@ -1700,30 +1521,17 @@ already_in_a_tree_conflict(svn_boolean_t
while (TRUE)
{
- svn_boolean_t is_wc_root, has_conflict;
+ svn_boolean_t is_wc_root, tree_conflicted;
svn_pool_clear(iterpool);
- SVN_ERR(svn_wc__db_read_info(NULL, NULL, NULL, NULL, NULL, NULL, NULL,
- NULL, NULL, NULL, NULL, NULL, NULL, NULL,
- NULL, NULL, NULL, NULL, NULL, NULL,
- &has_conflict, NULL, NULL, NULL,
- NULL, NULL, NULL,
- db, ancestor_abspath, iterpool, iterpool));
+ SVN_ERR(svn_wc__internal_conflicted_p(NULL, NULL, &tree_conflicted,
+ db, ancestor_abspath, iterpool));
- if (has_conflict)
+ if (tree_conflicted)
{
- const svn_wc_conflict_description2_t *conflict;
-
- SVN_ERR(svn_wc__db_op_read_tree_conflict(&conflict, db,
- ancestor_abspath,
- iterpool, iterpool));
-
- if (conflict != NULL)
- {
- *conflicted = TRUE;
- break;
- }
+ *conflicted = TRUE;
+ break;
}
SVN_ERR(svn_wc__db_is_wcroot(&is_wc_root, db, ancestor_abspath,
@@ -1772,17 +1580,16 @@ delete_entry(const char *path,
const char *base = svn_relpath_basename(path, NULL);
const char *local_abspath;
const char *repos_relpath;
- const char *moved_to_abspath = NULL;
svn_kind_t kind, base_kind;
+ svn_revnum_t old_revision;
svn_boolean_t conflicted;
- svn_boolean_t have_base;
svn_boolean_t have_work;
- svn_wc_conflict_description2_t *tree_conflict = NULL;
- svn_skel_t *work_item = NULL;
+ svn_skel_t *tree_conflict = NULL;
svn_wc__db_status_t status;
svn_wc__db_status_t base_status;
apr_pool_t *scratch_pool;
svn_boolean_t deleting_target;
+ svn_boolean_t keep_as_working = FALSE;
if (pb->skip_this)
return SVN_NO_ERROR;
@@ -1816,11 +1623,11 @@ delete_entry(const char *path,
}
}
- SVN_ERR(svn_wc__db_read_info(&status, &kind, NULL, &repos_relpath, NULL, NULL,
+ SVN_ERR(svn_wc__db_read_info(&status, &kind, &old_revision, &repos_relpath,
NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
- NULL, NULL, NULL, NULL, NULL, NULL, &conflicted,
- NULL, NULL, NULL,
- &have_base, NULL, &have_work,
+ NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
+ &conflicted, NULL, NULL, NULL,
+ NULL, NULL, &have_work,
eb->db, local_abspath,
scratch_pool, scratch_pool));
@@ -1830,7 +1637,7 @@ delete_entry(const char *path,
base_kind = kind;
}
else
- SVN_ERR(svn_wc__db_base_get_info(&base_status, &base_kind, NULL,
+ SVN_ERR(svn_wc__db_base_get_info(&base_status, &base_kind, &old_revision,
&repos_relpath,
NULL, NULL, NULL, NULL, NULL, NULL, NULL,
NULL, NULL, NULL, NULL,
@@ -1862,7 +1669,10 @@ delete_entry(const char *path,
|| base_status == svn_wc__db_status_excluded
|| base_status == svn_wc__db_status_server_excluded)
{
- SVN_ERR(svn_wc__db_base_remove(eb->db, local_abspath, scratch_pool));
+ SVN_ERR(svn_wc__db_base_remove(eb->db, local_abspath,
+ FALSE, SVN_INVALID_REVNUM,
+ NULL, NULL,
+ scratch_pool));
if (deleting_target)
eb->target_deleted = TRUE;
@@ -1872,13 +1682,6 @@ delete_entry(const char *path,
return SVN_NO_ERROR;
}
- /* Has the to-be-deleted node been moved away? */
- if (status == svn_wc__db_status_deleted)
- SVN_ERR(svn_wc__db_scan_deletion(NULL, &moved_to_abspath, NULL,
- NULL, eb->db, local_abspath,
- pool, pool));
-
-
/* Is this path the victim of a newly-discovered tree conflict? If so,
* remember it and notify the client. Then (if it was existing and
* modified), re-schedule the node to be added back again, as a (modified)
@@ -1890,13 +1693,13 @@ delete_entry(const char *path,
{
SVN_ERR(check_tree_conflict(&tree_conflict, eb, local_abspath,
status, kind, TRUE,
- svn_wc_conflict_action_delete, svn_node_none,
- repos_relpath, moved_to_abspath,
+ svn_wc_conflict_action_delete,
pb->pool, scratch_pool));
}
if (tree_conflict != NULL)
{
+ svn_wc_conflict_reason_t reason;
/* When we raise a tree conflict on a node, we don't want to mark the
* node as skipped, to allow a replacement to continue doing at least
* a bit of its work (possibly adding a not present node, for the
@@ -1907,15 +1710,12 @@ delete_entry(const char *path,
apr_hash_set(pb->deletion_conflicts, apr_pstrdup(pb->pool, base),
APR_HASH_KEY_STRING, tree_conflict);
- SVN_ERR(svn_wc__db_op_set_tree_conflict(eb->db,
- local_abspath,
- tree_conflict,
- scratch_pool));
-
- do_notification(eb, local_abspath, svn_node_unknown,
- svn_wc_notify_tree_conflict, scratch_pool);
+ SVN_ERR(svn_wc__conflict_read_tree_conflict(&reason, NULL,
+ eb->db, local_abspath,
+ tree_conflict,
+ scratch_pool, scratch_pool));
- if (tree_conflict->reason == svn_wc_conflict_reason_edited)
+ if (reason == svn_wc_conflict_reason_edited)
{
/* The item exists locally and has some sort of local mod.
* It no longer exists in the repository at its target URL@REV.
@@ -1923,17 +1723,15 @@ delete_entry(const char *path,
* To prepare the "accept mine" resolution for the tree conflict,
* we must schedule the existing content for re-addition as a copy
* of what it was, but with its local modifications preserved. */
- SVN_ERR(svn_wc__db_temp_op_make_copy(eb->db, local_abspath,
- scratch_pool));
+ keep_as_working = TRUE;
/* Fall through to remove the BASE_NODEs properly, with potentially
keeping a not-present marker */
}
- else if (tree_conflict->reason == svn_wc_conflict_reason_deleted
- || tree_conflict->reason == svn_wc_conflict_reason_moved_away
- || tree_conflict->reason ==
- svn_wc_conflict_reason_moved_away_and_edited
- || tree_conflict->reason == svn_wc_conflict_reason_replaced)
+ else if (reason == svn_wc_conflict_reason_deleted
+ || reason == svn_wc_conflict_reason_moved_away
+ || reason == svn_wc_conflict_reason_moved_away_and_edited
+ || reason == svn_wc_conflict_reason_replaced)
{
/* The item does not exist locally because it was already shadowed.
* We must complete the deletion, leaving the tree conflict info
@@ -1944,23 +1742,13 @@ delete_entry(const char *path,
else
SVN_ERR_MALFUNCTION(); /* other reasons are not expected here */
}
- else if (moved_to_abspath)
- {
- /* No tree conflict was flagged, and the node was moved-away.
- * Automatically merge the incoming deletion with the local move
- * by deleting the node from the moved-away subtree. */
- /* ### This should probably use a work queue. */
- SVN_ERR(svn_wc__db_op_delete(eb->db, moved_to_abspath, NULL,
- NULL, NULL, /* notify below */
- eb->cancel_func, eb->cancel_baton,
- scratch_pool));
- if (kind == svn_kind_dir)
- SVN_ERR(svn_io_remove_dir2(moved_to_abspath, TRUE,
- eb->cancel_func, eb->cancel_baton,
- scratch_pool));
- else
- SVN_ERR(svn_io_remove_file2(moved_to_abspath, TRUE, scratch_pool));
- }
+
+ SVN_ERR(complete_conflict(tree_conflict, pb, local_abspath, repos_relpath,
+ old_revision,
+ (kind == svn_kind_dir)
+ ? svn_node_dir
+ : svn_node_file,
+ pb->pool, scratch_pool));
/* Issue a wq operation to delete the BASE_NODE data and to delete actual
nodes based on that from disk, but leave any WORKING_NODEs on disk.
@@ -1973,32 +1761,30 @@ delete_entry(const char *path,
if (! deleting_target)
{
/* Delete, and do not leave a not-present node. */
- SVN_ERR(svn_wc__wq_build_base_remove(&work_item,
- eb->db, local_abspath,
- SVN_INVALID_REVNUM,
- svn_kind_unknown,
- scratch_pool, scratch_pool));
+ SVN_ERR(svn_wc__db_base_remove(eb->db, local_abspath,
+ keep_as_working, SVN_INVALID_REVNUM,
+ tree_conflict, NULL,
+ scratch_pool));
}
else
{
/* Delete, leaving a not-present node. */
- SVN_ERR(svn_wc__wq_build_base_remove(&work_item,
- eb->db, local_abspath,
- *eb->target_revision,
- base_kind,
- scratch_pool, scratch_pool));
+ SVN_ERR(svn_wc__db_base_remove(eb->db, local_abspath,
+ keep_as_working, *eb->target_revision,
+ tree_conflict, NULL,
+ scratch_pool));
eb->target_deleted = TRUE;
}
- SVN_ERR(svn_wc__db_wq_add(eb->db, pb->local_abspath, work_item,
- scratch_pool));
-
SVN_ERR(svn_wc__wq_run(eb->db, pb->local_abspath,
eb->cancel_func, eb->cancel_baton,
scratch_pool));
- /* Notify. (If tree_conflict, we've already notified.) */
- if (tree_conflict == NULL)
+ /* Notify. */
+ if (tree_conflict)
+ do_notification(eb, local_abspath, svn_node_unknown,
+ svn_wc_notify_tree_conflict, scratch_pool);
+ else
{
svn_wc_notify_action_t action = svn_wc_notify_update_delete;
svn_node_kind_t node_kind;
@@ -2011,8 +1797,7 @@ delete_entry(const char *path,
else
node_kind = svn_node_file;
- do_notification(eb, moved_to_abspath ? moved_to_abspath : local_abspath,
- node_kind, action, scratch_pool);
+ do_notification(eb, local_abspath, node_kind, action, scratch_pool);
}
svn_pool_destroy(scratch_pool);
@@ -2037,7 +1822,7 @@ add_directory(const char *path,
svn_kind_t wc_kind;
svn_boolean_t conflicted;
svn_boolean_t versioned_locally_and_present;
- svn_wc_conflict_description2_t *tree_conflict = NULL;
+ svn_skel_t *tree_conflict = NULL;
svn_error_t *err;
SVN_ERR_ASSERT(! (copyfrom_path || SVN_IS_VALID_REVNUM(copyfrom_rev)));
@@ -2165,18 +1950,30 @@ add_directory(const char *path,
if (tree_conflict)
{
+ svn_wc_conflict_reason_t reason;
/* So this deletion wasn't just a deletion, it is actually a
- replacement. Luckily we still have the conflict so we can
- just update it. */
+ replacement. Let's install a better tree conflict. */
+
+ /* ### Should store the conflict in DB to allow reinstalling
+ ### with theoretically more data in close_directory() */
- /* ### What else should we update? */
- tree_conflict->action = svn_wc_conflict_action_replace;
+ SVN_ERR(svn_wc__conflict_read_tree_conflict(&reason, NULL,
+ eb->db,
+ db->local_abspath,
+ tree_conflict,
+ db->pool, db->pool));
- SVN_ERR(svn_wc__db_op_set_tree_conflict(eb->db, db->local_abspath,
- tree_conflict, pool));
+ tree_conflict = svn_wc__conflict_skel_create(db->pool);
+
+ SVN_ERR(svn_wc__conflict_skel_add_tree_conflict(
+ tree_conflict,
+ eb->db, db->local_abspath,
+ reason, svn_wc_conflict_action_replace,
+ db->pool, db->pool));
/* And now stop checking for conflicts here and just perform
a shadowed update */
+ db->edit_conflict = tree_conflict; /* Cache for close_directory */
tree_conflict = NULL; /* No direct notification */
db->shadowed = TRUE; /* Just continue */
conflicted = FALSE; /* No skip */
@@ -2269,8 +2066,7 @@ add_directory(const char *path,
db->local_abspath,
status, wc_kind, FALSE,
svn_wc_conflict_action_add,
- svn_node_dir, db->new_relpath,
- NULL, pool, pool));
+ pool, pool));
}
if (tree_conflict == NULL)
@@ -2291,66 +2087,46 @@ add_directory(const char *path,
db->shadowed = TRUE;
/* Mark a conflict */
- SVN_ERR(create_tree_conflict(&tree_conflict, eb,
- db->local_abspath,
- svn_wc_conflict_reason_unversioned,
- svn_wc_conflict_action_add,
- svn_node_dir,
- db->new_relpath, pool, pool));
- SVN_ERR_ASSERT(tree_conflict != NULL);
+ tree_conflict = svn_wc__conflict_skel_create(db->pool);
+
+ SVN_ERR(svn_wc__conflict_skel_add_tree_conflict(
+ tree_conflict,
+ eb->db, db->local_abspath,
+ svn_wc_conflict_reason_unversioned,
+ svn_wc_conflict_action_add,
+ db->pool, pool));
+ db->edit_conflict = tree_conflict;
}
}
- SVN_ERR(svn_wc__db_temp_op_set_new_dir_to_incomplete(eb->db,
- db->local_abspath,
- db->new_relpath,
- eb->repos_root,
- eb->repos_uuid,
- *eb->target_revision,
- db->ambient_depth,
- pool));
+ SVN_ERR(complete_conflict(tree_conflict, pb, db->local_abspath,
+ db->old_repos_relpath, db->old_revision,
+ svn_node_dir, db->pool, pool));
+
+ SVN_ERR(svn_wc__db_base_add_incomplete_directory(
+ eb->db, db->local_abspath,
+ db->new_relpath,
+ eb->repos_root,
+ eb->repos_uuid,
+ *eb->target_revision,
+ db->ambient_depth,
+ (db->shadowed && db->obstruction_found),
+ (! db->shadowed
+ && status == svn_wc__db_status_added),
+ tree_conflict, NULL,
+ pool));
/* Make sure there is a real directory at LOCAL_ABSPATH, unless we are just
- updating the DB or the parent was moved away. */
- if (!db->shadowed && !pb->moved_to_abspath)
+ updating the DB */
+ if (!db->shadowed)
SVN_ERR(svn_wc__ensure_directory(db->local_abspath, pool));
- if (!db->shadowed && status == svn_wc__db_status_added)
- /* If there is no conflict we take over any added directory */
- SVN_ERR(svn_wc__db_temp_op_remove_working(eb->db, db->local_abspath, pool));
-
- /* ### We can't record an unversioned obstruction yet, so
- ### we record a delete instead, which will allow resolving the conflict
- ### to theirs with 'svn revert'. */
- if (db->shadowed && db->obstruction_found)
- {
- SVN_ERR(svn_wc__db_op_delete(eb->db, db->local_abspath, NULL,
- NULL, NULL /* notification */,
- eb->cancel_func, eb->cancel_baton,
- pool));
- }
-
if (tree_conflict != NULL)
{
- SVN_ERR(svn_wc__db_op_set_tree_conflict(eb->db, db->local_abspath,
- tree_conflict, pool));
-
db->already_notified = TRUE;
-
do_notification(eb, db->local_abspath, svn_node_dir,
svn_wc_notify_tree_conflict, pool);
}
- else if (wc_kind == svn_kind_unknown &&
- versioned_locally_and_present == FALSE &&
- pb->moved_to_abspath)
- {
- /* The parent directory of the directory we're adding was moved.
- * Add the new directory at the new location. */
- db->moved_to_abspath = svn_dirent_join(pb->moved_to_abspath,
- db->name, db->pool);
- db->moved_to_op_root_abspath = pb->moved_to_op_root_abspath;
- }
-
/* If this add was obstructed by dir scheduled for addition without
@@ -2371,9 +2147,7 @@ add_directory(const char *path,
db->already_notified = TRUE;
- do_notification(eb, db->moved_to_abspath ? db->moved_to_abspath
- : db->local_abspath,
- svn_node_dir, action, pool);
+ do_notification(eb, db->local_abspath, svn_node_dir, action, pool);
}
return SVN_NO_ERROR;
@@ -2391,10 +2165,9 @@ open_directory(const char *path,
struct edit_baton *eb = pb->edit_baton;
svn_boolean_t have_work;
svn_boolean_t conflicted;
- svn_wc_conflict_description2_t *tree_conflict = NULL;
+ svn_skel_t *tree_conflict = NULL;
svn_wc__db_status_t status, base_status;
svn_kind_t wc_kind;
- svn_error_t *err;
SVN_ERR(make_dir_baton(&db, path, eb, pb, FALSE, pool));
*child_baton = db;
@@ -2426,8 +2199,9 @@ open_directory(const char *path,
/* We should have a write lock on every directory touched. */
SVN_ERR(svn_wc__write_check(eb->db, db->local_abspath, pool));
- SVN_ERR(svn_wc__db_read_info(&status, &wc_kind, &db->old_revision, NULL,
- NULL, NULL, &db->changed_rev, &db->changed_date,
+ SVN_ERR(svn_wc__db_read_info(&status, &wc_kind, &db->old_revision,
+ &db->old_repos_relpath, NULL, NULL,
+ &db->changed_rev, &db->changed_date,
&db->changed_author, &db->ambient_depth,
NULL, NULL, NULL, NULL,
NULL, NULL, NULL, NULL, NULL, NULL,
@@ -2440,10 +2214,10 @@ open_directory(const char *path,
base_status = status;
else
SVN_ERR(svn_wc__db_base_get_info(&base_status, NULL, &db->old_revision,
- NULL, NULL, NULL, &db->changed_rev,
- &db->changed_date, &db->changed_author,
- &db->ambient_depth, NULL, NULL, NULL,
- NULL, NULL,
+ &db->old_repos_relpath, NULL, NULL,
+ &db->changed_rev, &db->changed_date,
+ &db->changed_author, &db->ambient_depth,
+ NULL, NULL, NULL, NULL, NULL,
eb->db, db->local_abspath,
db->pool, pool));
@@ -2469,46 +2243,29 @@ open_directory(const char *path,
/* Is this path a fresh tree conflict victim? If so, skip the tree
with one notification. */
- /* Check if this directory was moved away. */
- err = svn_wc__db_read_info(&status, NULL, NULL, NULL, NULL, NULL, NULL,
- NULL, NULL, NULL, NULL, NULL, NULL, NULL,
- NULL, NULL, NULL, NULL, NULL, NULL,
- NULL, NULL, NULL, NULL,
- NULL, NULL, NULL,
- eb->db, db->local_abspath, pool, pool);
- if (err)
- {
- if (err->apr_err == SVN_ERR_WC_PATH_NOT_FOUND)
- svn_error_clear(err);
- else
- return svn_error_trace(err);
- }
- else if (status == svn_wc__db_status_deleted)
- SVN_ERR(svn_wc__db_scan_deletion(NULL, &db->moved_to_abspath, NULL,
- &db->moved_to_op_root_abspath,
- eb->db, db->local_abspath,
- db->pool, pool));
-
/* Check for conflicts only when we haven't already recorded
* a tree-conflict on a parent node. */
if (!db->shadowed)
SVN_ERR(check_tree_conflict(&tree_conflict, eb, db->local_abspath,
status, wc_kind, TRUE,
- svn_wc_conflict_action_edit, svn_node_dir,
- db->new_relpath, db->moved_to_abspath,
+ svn_wc_conflict_action_edit,
db->pool, pool));
/* Remember the roots of any locally deleted trees. */
if (tree_conflict != NULL)
{
+ svn_wc_conflict_reason_t reason;
db->edit_conflict = tree_conflict;
/* Other modifications wouldn't be a tree conflict */
- SVN_ERR_ASSERT(
- tree_conflict->reason == svn_wc_conflict_reason_deleted ||
- tree_conflict->reason == svn_wc_conflict_reason_moved_away ||
- tree_conflict->reason ==
- svn_wc_conflict_reason_moved_away_and_edited ||
- tree_conflict->reason == svn_wc_conflict_reason_replaced);
+
+ SVN_ERR(svn_wc__conflict_read_tree_conflict(&reason, NULL,
+ eb->db, db->local_abspath,
+ tree_conflict,
+ db->pool, db->pool));
+ SVN_ERR_ASSERT(reason == svn_wc_conflict_reason_deleted
+ || reason == svn_wc_conflict_reason_moved_away
+ || reason == svn_wc_conflict_reason_moved_away_and_edited
+ || reason == svn_wc_conflict_reason_replaced);
/* Continue updating BASE */
db->shadowed = TRUE;
@@ -2588,6 +2345,7 @@ close_directory(void *dir_baton,
const char *new_changed_author = NULL;
apr_pool_t *scratch_pool = db->pool;
svn_skel_t *all_work_items = NULL;
+ svn_skel_t *conflict_skel = NULL;
/* Skip if we're in a conflicted tree. */
if (db->skip_this)
@@ -2598,6 +2356,9 @@ close_directory(void *dir_baton,
return SVN_NO_ERROR;
}
+ if (db->edited)
+ conflict_skel = db->edit_conflict;
+
SVN_ERR(svn_categorize_props(db->propchanges, &entry_prop_changes,
&dav_prop_changes, ®ular_prop_changes, pool));
@@ -2670,8 +2431,6 @@ close_directory(void *dir_baton,
to deal with them. */
if (regular_prop_changes->nelts)
{
- svn_skel_t *work_item;
-
/* If recording traversal info, then see if the
SVN_PROP_EXTERNALS property on this directory changed,
and record before and after for the change. */
@@ -2719,23 +2478,19 @@ close_directory(void *dir_baton,
/* Merge pending properties into temporary files (ignoring
conflicts). */
- SVN_ERR_W(svn_wc__merge_props(&work_item,
+ SVN_ERR_W(svn_wc__merge_props(&conflict_skel,
&prop_state,
&new_base_props,
&new_actual_props,
eb->db,
db->local_abspath,
svn_kind_dir,
- NULL, /* left_version */
- NULL, /* right_version */
NULL /* use baseprops */,
base_props,
actual_props,
regular_prop_changes,
TRUE /* base_merge */,
FALSE /* dry_run */,
- eb->conflict_func,
- eb->conflict_baton,
eb->cancel_func,
eb->cancel_baton,
db->pool,
@@ -2743,8 +2498,6 @@ close_directory(void *dir_baton,
_("Couldn't do property merge"));
/* After a (not-dry-run) merge, we ALWAYS have props to save. */
SVN_ERR_ASSERT(new_base_props != NULL && new_actual_props != NULL);
- all_work_items = svn_wc__wq_merge(all_work_items, work_item,
- scratch_pool);
}
SVN_ERR(accumulate_last_change(&new_changed_rev, &new_changed_date,
@@ -2915,6 +2668,27 @@ close_directory(void *dir_baton,
if (props == NULL)
props = base_props;
+ if (conflict_skel)
+ {
+ svn_skel_t *work_item;
+
+ SVN_ERR(complete_conflict(conflict_skel,
+ db->parent_baton,
+ db->local_abspath,
+ db->old_repos_relpath,
+ db->old_revision,
+ svn_node_dir,
+ db->pool, scratch_pool));
+
+ SVN_ERR(svn_wc__conflict_create_markers(&work_item,
+ eb->db, db->local_abspath,
+ conflict_skel,
+ scratch_pool, scratch_pool));
+
+ all_work_items = svn_wc__wq_merge(all_work_items, work_item,
+ scratch_pool);
+ }
+
/* Update the BASE data for the directory and mark the directory
complete */
SVN_ERR(svn_wc__db_base_add_directory(
@@ -2930,46 +2704,11 @@ close_directory(void *dir_baton,
(dav_prop_changes->nelts > 0)
? svn_prop_array_to_hash(dav_prop_changes, pool)
: NULL,
- NULL /* conflict */,
+ conflict_skel,
(! db->shadowed) && new_base_props != NULL,
new_actual_props,
all_work_items,
scratch_pool));
-
- if (db->moved_to_abspath)
- {
- /* Perform another in-DB move of the directory to sync meta-data
- * of the moved-away node with the new BASE node. */
- apr_array_header_t *children = NULL;
- apr_hash_t *children_hash = apr_hash_get(eb->dir_dirents,
- db->new_relpath,
- APR_HASH_KEY_STRING);
- /* The op-root of the move needs to retain its moved-here flag.
- * Its children are normal copied children. */
- svn_boolean_t is_move = (strcmp(db->moved_to_op_root_abspath,
- db->moved_to_abspath) == 0);
-
- /* Add the new directory as a copy and create it on disk. */
- if (children_hash)
- SVN_ERR(svn_hash_keys(&children, children_hash, scratch_pool));
- SVN_ERR(svn_wc__db_op_copy_dir(eb->db, db->moved_to_abspath,
- new_actual_props ? new_actual_props
- : actual_props,
- db->changed_rev,
- db->changed_date,
- db->changed_author,
- db->new_relpath,
- eb->repos_root,
- eb->repos_uuid,
- *eb->target_revision,
- children,
- is_move,
- db->ambient_depth,
- NULL /* conflict */,
- NULL, /* no work, just modify DB */
- scratch_pool));
- SVN_ERR(svn_wc__ensure_directory(db->moved_to_abspath, pool));
- }
}
/* Process all of the queued work items for this directory. */
@@ -2977,6 +2716,14 @@ close_directory(void *dir_baton,
eb->cancel_func, eb->cancel_baton,
scratch_pool));
+ if (conflict_skel && eb->conflict_func)
+ SVN_ERR(svn_wc__conflict_invoke_resolver(eb->db, db->local_abspath,
+ conflict_skel,
+ NULL /* merge_options */,
+ eb->conflict_func,
+ eb->conflict_baton,
+ scratch_pool));
+
/* Notify of any prop changes on this directory -- but do nothing if
it's an added or skipped directory, because notification has already
happened in that case - unless the add was obstructed by a dir
@@ -3152,7 +2899,7 @@ add_file(const char *path,
apr_pool_t *scratch_pool;
svn_boolean_t conflicted = FALSE;
svn_boolean_t versioned_locally_and_present = FALSE;
- svn_wc_conflict_description2_t *tree_conflict = NULL;
+ svn_skel_t *tree_conflict = NULL;
svn_error_t *err = SVN_NO_ERROR;
SVN_ERR_ASSERT(! (copyfrom_path || SVN_IS_VALID_REVNUM(copyfrom_rev)));
@@ -3266,18 +3013,30 @@ add_file(const char *path,
if (tree_conflict)
{
+ svn_wc_conflict_reason_t reason;
/* So this deletion wasn't just a deletion, it is actually a
- replacement. Luckily we still have the conflict so we can
- just update it. */
+ replacement. Let's install a better tree conflict. */
+
+ /* ### Should store the conflict in DB to allow reinstalling
+ ### with theoretically more data in close_directory() */
- /* ### What else should we update? */
- tree_conflict->action = svn_wc_conflict_action_replace;
+ SVN_ERR(svn_wc__conflict_read_tree_conflict(&reason, NULL,
+ eb->db,
+ fb->local_abspath,
+ tree_conflict,
+ fb->pool, fb->pool));
- SVN_ERR(svn_wc__db_op_set_tree_conflict(eb->db, fb->local_abspath,
- tree_conflict, pool));
+ tree_conflict = svn_wc__conflict_skel_create(fb->pool);
+
+ SVN_ERR(svn_wc__conflict_skel_add_tree_conflict(
+ tree_conflict,
+ eb->db, fb->local_abspath,
+ reason, svn_wc_conflict_action_replace,
+ fb->pool, fb->pool));
/* And now stop checking for conflicts here and just perform
a shadowed update */
+ fb->edit_conflict = tree_conflict; /* Cache for close_file */
tree_conflict = NULL; /* No direct notification */
fb->shadowed = TRUE; /* Just continue */
conflicted = FALSE; /* No skip */
@@ -3366,7 +3125,6 @@ add_file(const char *path,
fb->local_abspath,
status, wc_kind, FALSE,
svn_wc_conflict_action_add,
- svn_node_file, fb->new_relpath, NULL,
scratch_pool, scratch_pool));
}
@@ -3389,14 +3147,14 @@ add_file(const char *path,
fb->shadowed = TRUE;
/* Mark a conflict */
- SVN_ERR(create_tree_conflict(&tree_conflict, eb,
- fb->local_abspath,
- svn_wc_conflict_reason_unversioned,
- svn_wc_conflict_action_add,
- svn_node_file,
- fb->new_relpath,
- scratch_pool, scratch_pool));
- SVN_ERR_ASSERT(tree_conflict != NULL);
+ tree_conflict = svn_wc__conflict_skel_create(fb->pool);
+
+ SVN_ERR(svn_wc__conflict_skel_add_tree_conflict(
+ tree_conflict,
+ eb->db, fb->local_abspath,
+ svn_wc_conflict_reason_unversioned,
+ svn_wc_conflict_action_add,
+ fb->pool, scratch_pool));
}
}
@@ -3413,24 +3171,23 @@ add_file(const char *path,
if (tree_conflict != NULL)
{
- SVN_ERR(svn_wc__db_op_set_tree_conflict(eb->db,
- fb->local_abspath,
- tree_conflict,
- scratch_pool));
+ SVN_ERR(complete_conflict(tree_conflict,
+ fb->dir_baton,
+ fb->local_abspath,
+ fb->old_repos_relpath,
+ fb->old_revision,
+ svn_node_file,
+ fb->pool, scratch_pool));
+
+ SVN_ERR(svn_wc__db_op_mark_conflict(eb->db,
+ fb->local_abspath,
+ tree_conflict, NULL,
+ scratch_pool));
fb->already_notified = TRUE;
do_notification(eb, fb->local_abspath, svn_node_file,
svn_wc_notify_tree_conflict, scratch_pool);
}
- else if (wc_kind == svn_kind_unknown &&
- versioned_locally_and_present == FALSE &&
- pb->moved_to_abspath)
- {
- /* The parent directory of the file we're adding was moved.
- * Add the new file at the new location. */
- fb->moved_to_abspath = svn_dirent_join(pb->moved_to_abspath,
- fb->name, fb->pool);
- }
svn_pool_destroy(scratch_pool);
@@ -3453,7 +3210,7 @@ open_file(const char *path,
svn_boolean_t have_work;
svn_wc__db_status_t status;
svn_kind_t wc_kind;
- svn_wc_conflict_description2_t *tree_conflict = NULL;
+ svn_skel_t *tree_conflict = NULL;
/* the file_pool can stick around for a *long* time, so we want to use
a subpool for any temporary allocations. */
@@ -3489,8 +3246,9 @@ open_file(const char *path,
/* Sanity check. */
/* If replacing, make sure the .svn entry already exists. */
- SVN_ERR(svn_wc__db_read_info(&status, &wc_kind, &fb->old_revision, NULL,
- NULL, NULL, &fb->changed_rev, &fb->changed_date,
+ SVN_ERR(svn_wc__db_read_info(&status, &wc_kind, &fb->old_revision,
+ &fb->old_repos_relpath, NULL, NULL,
+ &fb->changed_rev, &fb->changed_date,
&fb->changed_author, NULL,
&fb->original_checksum, NULL, NULL, NULL,
NULL, NULL, NULL, NULL, NULL, NULL,
@@ -3501,19 +3259,14 @@ open_file(const char *path,
if (have_work)
SVN_ERR(svn_wc__db_base_get_info(NULL, NULL, &fb->old_revision,
- NULL, NULL, NULL, &fb->changed_rev,
- &fb->changed_date, &fb->changed_author,
- NULL, &fb->original_checksum, NULL, NULL,
+ &fb->old_repos_relpath, NULL, NULL,
+ &fb->changed_rev, &fb->changed_date,
+ &fb->changed_author, NULL,
+ &fb->original_checksum, NULL, NULL,
NULL, NULL,
eb->db, fb->local_abspath,
fb->pool, scratch_pool));
- /* If the file has moved locally look up its new location. */
- if (status == svn_wc__db_status_deleted)
- SVN_ERR(svn_wc__db_scan_deletion(NULL, &fb->moved_to_abspath, NULL, NULL,
- eb->db, fb->local_abspath,
- fb->pool, scratch_pool));
-
/* Is this path a conflict victim? */
if (conflicted)
SVN_ERR(node_already_conflicted(&conflicted, eb->db,
@@ -3540,22 +3293,24 @@ open_file(const char *path,
if (!fb->shadowed)
SVN_ERR(check_tree_conflict(&tree_conflict, eb, fb->local_abspath,
status, wc_kind, TRUE,
- svn_wc_conflict_action_edit, svn_node_file,
- fb->new_relpath, fb->moved_to_abspath,
+ svn_wc_conflict_action_edit,
fb->pool, scratch_pool));
/* Is this path the victim of a newly-discovered tree conflict? */
if (tree_conflict != NULL)
{
+ svn_wc_conflict_reason_t reason;
fb->edit_conflict = tree_conflict;
-
/* Other modifications wouldn't be a tree conflict */
- SVN_ERR_ASSERT(
- tree_conflict->reason == svn_wc_conflict_reason_deleted ||
- tree_conflict->reason == svn_wc_conflict_reason_moved_away ||
- tree_conflict->reason ==
- svn_wc_conflict_reason_moved_away_and_edited ||
- tree_conflict->reason == svn_wc_conflict_reason_replaced);
+
+ SVN_ERR(svn_wc__conflict_read_tree_conflict(&reason, NULL,
+ eb->db, fb->local_abspath,
+ tree_conflict,
+ fb->pool, fb->pool));
+ SVN_ERR_ASSERT(reason == svn_wc_conflict_reason_deleted
+ || reason == svn_wc_conflict_reason_moved_away
+ || reason == svn_wc_conflict_reason_moved_away_and_edited
+ || reason == svn_wc_conflict_reason_replaced);
/* Continue updating BASE */
fb->shadowed = TRUE;
@@ -3742,6 +3497,7 @@ change_file_prop(void *file_baton,
*/
svn_error_t *
svn_wc__perform_file_merge(svn_skel_t **work_items,
+ svn_skel_t **conflict_skel,
enum svn_wc_merge_outcome_t *merge_outcome,
svn_wc__db_t *db,
const char *local_abspath,
@@ -3754,8 +3510,6 @@ svn_wc__perform_file_merge(svn_skel_t **
svn_revnum_t target_revision,
const apr_array_header_t *propchanges,
const char *diff3_cmd,
- svn_wc_conflict_resolver_func2_t conflict_func,
- void *conflict_baton,
svn_cancel_func_t cancel_func,
void *cancel_baton,
apr_pool_t *result_pool,
@@ -3821,19 +3575,18 @@ svn_wc__perform_file_merge(svn_skel_t **
/* Merge the changes from the old textbase to the new
textbase into the file we're updating.
Remember that this function wants full paths! */
- /* ### TODO: Pass version info here. */
SVN_ERR(svn_wc__internal_merge(&work_item,
+ conflict_skel,
merge_outcome,
db,
- merge_left, NULL,
- new_text_base_tmp_abspath, NULL,
+ merge_left,
+ new_text_base_tmp_abspath,
local_abspath,
wri_abspath,
oldrev_str, newrev_str, mine_str,
actual_props,
FALSE /* dry_run */,
diff3_cmd, NULL, propchanges,
- conflict_func, conflict_baton,
cancel_func, cancel_baton,
result_pool, scratch_pool));
@@ -3842,7 +3595,8 @@ svn_wc__perform_file_merge(svn_skel_t **
/* If we created a temporary left merge file, get rid of it. */
if (delete_left)
{
- SVN_ERR(svn_wc__wq_build_file_remove(&work_item, db, merge_left,
+ SVN_ERR(svn_wc__wq_build_file_remove(&work_item, db, wri_abspath,
+ merge_left,
result_pool, scratch_pool));
*work_items = svn_wc__wq_merge(*work_items, work_item, result_pool);
}
@@ -3875,6 +3629,7 @@ svn_wc__perform_file_merge(svn_skel_t **
*/
static svn_error_t *
merge_file(svn_skel_t **work_items,
+ svn_skel_t **conflict_skel,
svn_boolean_t *install_pristine,
const char **install_from,
svn_wc_notify_state_t *content_state,
@@ -3888,9 +3643,6 @@ merge_file(svn_skel_t **work_items,
struct dir_baton *pb = fb->dir_baton;
svn_boolean_t is_locally_modified;
enum svn_wc_merge_outcome_t merge_outcome = svn_wc_merge_unchanged;
- svn_skel_t *work_item;
- const char *working_abspath = fb->moved_to_abspath ? fb->moved_to_abspath
- : fb->local_abspath;
SVN_ERR_ASSERT(! fb->shadowed && !fb->obstruction_found);
@@ -3935,7 +3687,7 @@ merge_file(svn_skel_t **work_items,
files that do not exist and for directories. */
SVN_ERR(svn_wc__internal_file_modified_p(&is_locally_modified,
- eb->db, working_abspath,
+ eb->db, fb->local_abspath,
FALSE /* exact_comparison */,
scratch_pool));
}
@@ -3977,9 +3729,10 @@ merge_file(svn_skel_t **work_items,
Now we need to let loose svn_wc__merge_internal() to merge
the textual changes into the working file. */
SVN_ERR(svn_wc__perform_file_merge(work_items,
+ conflict_skel,
&merge_outcome,
eb->db,
- working_abspath,
+ fb->local_abspath,
pb->local_abspath,
fb->new_text_base_sha1_checksum,
fb->add_existed
@@ -3991,7 +3744,6 @@ merge_file(svn_skel_t **work_items,
*eb->target_revision,
fb->propchanges,
eb->diff3_cmd,
- eb->conflict_func, eb->conflict_baton,
eb->cancel_func, eb->cancel_baton,
result_pool, scratch_pool));
} /* end: working file exists and has mods */
@@ -4011,7 +3763,7 @@ merge_file(svn_skel_t **work_items,
SVN_ERR(svn_wc__get_translate_info(NULL, NULL,
&keywords,
NULL,
- eb->db, working_abspath,
+ eb->db, fb->local_abspath,
actual_props, TRUE,
scratch_pool, scratch_pool));
if (magic_props_changed || keywords)
@@ -4031,7 +3783,7 @@ merge_file(svn_skel_t **work_items,
/* Copy and DEtranslate the working file to a temp text-base.
Note that detranslation is done according to the old props. */
SVN_ERR(svn_wc__internal_translated_file(
- &tmptext, working_abspath, eb->db, working_abspath,
+ &tmptext, fb->local_abspath, eb->db, fb->local_abspath,
SVN_WC_TRANSLATE_TO_NF
| SVN_WC_TRANSLATE_NO_OUTPUT_CLEANUP,
eb->cancel_func, eb->cancel_baton,
@@ -4059,26 +3811,6 @@ merge_file(svn_skel_t **work_items,
}
}
- /* Installing from a pristine will handle timestamps and recording.
- However, if we are NOT creating a new working copy file, then create
- work items to handle the recording of the timestamp and working-size. */
- if (!*install_pristine
- && !is_locally_modified)
- {
- apr_time_t set_date = 0;
-
- if (eb->use_commit_times && last_changed_date != 0)
- {
- set_date = last_changed_date;
- }
-
- SVN_ERR(svn_wc__wq_build_record_fileinfo(&work_item,
- eb->db, working_abspath,
- set_date,
- result_pool, scratch_pool));
- *work_items = svn_wc__wq_merge(*work_items, work_item, result_pool);
- }
-
/* Set the returned content state. */
/* This is kind of interesting. Even if no new text was
@@ -4125,12 +3857,11 @@ close_file(void *file_baton,
apr_hash_t *current_actual_props = NULL;
apr_hash_t *local_actual_props = NULL;
svn_skel_t *all_work_items = NULL;
+ svn_skel_t *conflict_skel = NULL;
svn_skel_t *work_item;
apr_pool_t *scratch_pool = fb->pool; /* Destroyed at function exit */
svn_boolean_t keep_recorded_info = FALSE;
const svn_checksum_t *new_checksum;
- const char *working_abspath = fb->moved_to_abspath ? fb->moved_to_abspath
- : fb->local_abspath;
if (fb->skip_this)
{
@@ -4139,6 +3870,9 @@ close_file(void *file_baton,
return SVN_NO_ERROR;
}
+ if (fb->edited)
+ conflict_skel = fb->edit_conflict;
+
if (expected_md5_digest)
SVN_ERR(svn_checksum_parse_hex(&expected_md5_checksum, svn_checksum_md5,
expected_md5_digest, scratch_pool));
@@ -4221,7 +3955,7 @@ close_file(void *file_baton,
if ((!fb->adding_file || fb->add_existed)
&& !fb->shadowed)
SVN_ERR(svn_wc__get_actual_props(&local_actual_props,
- eb->db, working_abspath,
+ eb->db, fb->local_abspath,
scratch_pool, scratch_pool));
if (local_actual_props == NULL)
local_actual_props = apr_hash_make(scratch_pool);
@@ -4287,26 +4021,26 @@ close_file(void *file_baton,
if (local_is_link != incoming_is_link)
{
- svn_wc_conflict_description2_t *tree_conflict = NULL;
-
fb->shadowed = TRUE;
fb->obstruction_found = TRUE;
fb->add_existed = FALSE;
- SVN_ERR(create_tree_conflict(&tree_conflict, eb,
- fb->local_abspath,
+ if (!conflict_skel)
+ conflict_skel = svn_wc__conflict_skel_create(fb->pool);
+
+ SVN_ERR(svn_wc__conflict_skel_add_tree_conflict(
+ conflict_skel,
+ eb->db, fb->local_abspath,
svn_wc_conflict_reason_added,
svn_wc_conflict_action_add,
- svn_node_file, fb->new_relpath,
scratch_pool, scratch_pool));
- SVN_ERR(svn_wc__db_op_set_tree_conflict(eb->db,
- fb->local_abspath,
- tree_conflict,
- scratch_pool));
fb->already_notified = TRUE;
do_notification(eb, fb->local_abspath, svn_node_unknown,
svn_wc_notify_tree_conflict, scratch_pool);
+
+ /* The update will be applied to PRISTINE, but not to
+ the in-working copy node */
}
}
@@ -4321,35 +4055,31 @@ close_file(void *file_baton,
/* This will merge the old and new props into a new prop db, and
write <cp> commands to the logfile to install the merged
props. */
- SVN_ERR(svn_wc__merge_props(&work_item,
+ SVN_ERR(svn_wc__merge_props(&conflict_skel,
&prop_state,
&new_base_props,
&new_actual_props,
eb->db,
- working_abspath,
+ fb->local_abspath,
svn_kind_file,
- NULL /* left_version */,
- NULL /* right_version */,
NULL /* server_baseprops (update, not merge) */,
current_base_props,
current_actual_props,
regular_prop_changes, /* propchanges */
TRUE /* base_merge */,
FALSE /* dry_run */,
- eb->conflict_func, eb->conflict_baton,
eb->cancel_func, eb->cancel_baton,
scratch_pool,
scratch_pool));
/* We will ALWAYS have properties to save (after a not-dry-run merge). */
SVN_ERR_ASSERT(new_base_props != NULL && new_actual_props != NULL);
- all_work_items = svn_wc__wq_merge(all_work_items, work_item,
- scratch_pool);
/* Merge the text. This will queue some additional work. */
if (!fb->obstruction_found)
{
svn_error_t *err;
- err = merge_file(&work_item, &install_pristine, &install_from,
+ err = merge_file(&work_item, &conflict_skel,
+ &install_pristine, &install_from,
&content_state, fb, current_actual_props,
fb->changed_date, scratch_pool, scratch_pool);
@@ -4358,7 +4088,7 @@ close_file(void *file_baton,
if (eb->notify_func)
{
svn_wc_notify_t *notify =svn_wc_create_notify(
- working_abspath,
+ fb->local_abspath,
svn_wc_notify_update_skip_access_denied,
scratch_pool);
@@ -4405,7 +4135,7 @@ close_file(void *file_baton,
SVN_ERR(svn_wc__wq_build_file_install(&work_item,
eb->db,
- working_abspath,
+ fb->local_abspath,
install_from,
eb->use_commit_times,
record_fileinfo,
@@ -4421,7 +4151,7 @@ close_file(void *file_baton,
Note: this will also update the executable flag, but ... meh. */
SVN_ERR(svn_wc__wq_build_sync_file_flags(&work_item, eb->db,
- working_abspath,
+ fb->local_abspath,
scratch_pool, scratch_pool));
all_work_items = svn_wc__wq_merge(all_work_items, work_item,
scratch_pool);
@@ -4439,10 +4169,10 @@ close_file(void *file_baton,
/* Remove the INSTALL_FROM file, as long as it doesn't refer to the
working file. */
if (install_from != NULL
- && strcmp(install_from, working_abspath) != 0)
+ && strcmp(install_from, fb->local_abspath) != 0)
{
SVN_ERR(svn_wc__wq_build_file_remove(&work_item, eb->db,
- install_from,
+ fb->local_abspath, install_from,
scratch_pool, scratch_pool));
all_work_items = svn_wc__wq_merge(all_work_items, work_item,
scratch_pool);
@@ -4460,29 +4190,23 @@ close_file(void *file_baton,
/* Store the incoming props (sent as propchanges) in new_base_props
and create a set of new actual props to use for notifications */
- SVN_ERR(svn_wc__merge_props(&work_item,
+ SVN_ERR(svn_wc__merge_props(&conflict_skel,
&prop_state,
&new_base_props,
&new_actual_props,
eb->db,
fb->local_abspath,
svn_kind_file,
- NULL /* left_version */,
- NULL /* right_version */,
NULL /* server_baseprops (not merging) */,
current_base_props /* pristine_props */,
fake_actual_props /* actual_props */,
regular_prop_changes, /* propchanges */
TRUE /* base_merge */,
FALSE /* dry_run */,
- NULL, NULL, /* No conflict handling */
eb->cancel_func, eb->cancel_baton,
scratch_pool,
scratch_pool));
- all_work_items = svn_wc__wq_merge(all_work_items, work_item,
- scratch_pool);
-
if (fb->new_text_base_sha1_checksum)
content_state = svn_wc_notify_state_changed;
else
@@ -4501,6 +4225,25 @@ close_file(void *file_baton,
if (new_checksum == NULL)
new_checksum = fb->original_checksum;
+ if (conflict_skel)
+ {
+ SVN_ERR(complete_conflict(conflict_skel,
+ fb->dir_baton,
+ fb->local_abspath,
+ fb->old_repos_relpath,
+ fb->old_revision,
+ svn_node_file,
+ fb->pool, scratch_pool));
+
+ SVN_ERR(svn_wc__conflict_create_markers(&work_item,
+ eb->db, fb->local_abspath,
+ conflict_skel,
+ scratch_pool, scratch_pool));
+
+ all_work_items = svn_wc__wq_merge(all_work_items, work_item,
+ scratch_pool);
+ }
+
SVN_ERR(svn_wc__db_base_add_file(eb->db, fb->local_abspath,
eb->wcroot_abspath,
fb->new_relpath,
@@ -4516,73 +4259,62 @@ close_file(void *file_baton,
dav_prop_changes,
scratch_pool)
: NULL,
- NULL /* conflict */,
+ (fb->add_existed && fb->adding_file),
(! fb->shadowed) && new_base_props,
new_actual_props,
keep_recorded_info,
(fb->shadowed && fb->obstruction_found),
+ conflict_skel,
all_work_items,
scratch_pool));
- /* Deal with the WORKING tree, based on updates to the BASE tree. */
-
- if (fb->moved_to_abspath)
- {
- /* Perform another in-DB move of the file to sync meta-data
- * of the moved-away node with the new BASE node. */
- SVN_ERR(svn_wc__db_op_copy_file(eb->db, fb->moved_to_abspath,
- new_actual_props,
- fb->changed_rev,
- fb->changed_date,
- fb->changed_author,
- fb->new_relpath,
- eb->repos_root,
- eb->repos_uuid,
- *eb->target_revision,
- new_checksum,
- TRUE /* is_move */,
- NULL /* conflict */,
- NULL, /* no work, just modify DB */
- scratch_pool));
- }
+ if (conflict_skel && eb->conflict_func)
+ SVN_ERR(svn_wc__conflict_invoke_resolver(eb->db, fb->local_abspath,
+ conflict_skel,
+ NULL /* merge_options */,
+ eb->conflict_func,
+ eb->conflict_baton,
+ scratch_pool));
- /* If this file was locally-added and is now being added by the update, we
- can toss the local-add, turning this into a local-edit.
- If the local file is replaced, we don't want to touch ACTUAL. */
- if (fb->add_existed && fb->adding_file)
- {
- SVN_ERR(svn_wc__db_temp_op_remove_working(eb->db, fb->local_abspath,
- scratch_pool));
- }
+ /* Deal with the WORKING tree, based on updates to the BASE tree. */
apr_hash_set(fb->dir_baton->not_present_files, fb->name,
APR_HASH_KEY_STRING, NULL);
/* Send a notification to the callback function. (Skip notifications
about files which were already notified for another reason.) */
- if (eb->notify_func && !fb->already_notified && fb->edited)
+ if (eb->notify_func && !fb->already_notified
+ && (fb->edited || lock_state == svn_wc_notify_lock_state_unlocked))
{
svn_wc_notify_t *notify;
svn_wc_notify_action_t action = svn_wc_notify_update_update;
- if (fb->shadowed)
- action = fb->adding_file
- ? svn_wc_notify_update_shadowed_add
- : svn_wc_notify_update_shadowed_update;
- else if (fb->obstruction_found || fb->add_existed)
+ if (fb->edited)
{
- if (content_state != svn_wc_notify_state_conflicted)
- action = svn_wc_notify_exists;
+ if (fb->shadowed)
+ action = fb->adding_file
+ ? svn_wc_notify_update_shadowed_add
+ : svn_wc_notify_update_shadowed_update;
+ else if (fb->obstruction_found || fb->add_existed)
+ {
+ if (content_state != svn_wc_notify_state_conflicted)
+ action = svn_wc_notify_exists;
+ }
+ else if (fb->adding_file)
+ {
+ action = svn_wc_notify_update_add;
+ }
}
- else if (fb->adding_file)
+ else
{
- action = svn_wc_notify_update_add;
+ SVN_ERR_ASSERT(lock_state == svn_wc_notify_lock_state_unlocked);
+ action = svn_wc_notify_update_broken_lock;
}
/* If the file was moved-away, notify for the moved-away node.
* The original location only had its BASE info changed and
* we don't usually notify about such changes. */
- notify = svn_wc_create_notify(working_abspath, action, scratch_pool);
+ notify = svn_wc_create_notify(fb->local_abspath, action, scratch_pool);
notify->kind = svn_node_file;
notify->content_state = content_state;
notify->prop_state = prop_state;
@@ -4689,7 +4421,8 @@ close_edit(void *edit_baton,
If so, we should get rid of this excluded node now. */
SVN_ERR(svn_wc__db_base_remove(eb->db, eb->target_abspath,
- scratch_pool));
+ FALSE, SVN_INVALID_REVNUM,
+ NULL, NULL, scratch_pool));
}
}
}
@@ -5656,8 +5389,8 @@ svn_wc_add_repos_file4(svn_wc_context_t
it is a temporary file, which needs to be removed. */
if (source_abspath != NULL)
{
- SVN_ERR(svn_wc__wq_build_file_remove(&work_item,
- db, source_abspath,
+ SVN_ERR(svn_wc__wq_build_file_remove(&work_item, db, local_abspath,
+ source_abspath,
pool, pool));
all_work_items = svn_wc__wq_merge(all_work_items, work_item, pool);
}
@@ -5676,16 +5409,10 @@ svn_wc_add_repos_file4(svn_wc_context_t
original_uuid,
copyfrom_rev,
[... 17 lines stripped ...]