You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@subversion.apache.org by rh...@apache.org on 2012/07/04 18:27:48 UTC
svn commit: r1357333 - in /subversion/trunk/subversion/libsvn_wc:
conflicts.c conflicts.h wc_db.c
Author: rhuijben
Date: Wed Jul 4 16:27:47 2012
New Revision: 1357333
URL: http://svn.apache.org/viewvc?rev=1357333&view=rev
Log:
Add support for resolving specific conflicts when using the currently still
disabled conflict-skel storage.
* subversion/libsvn_wc/conflicts.c
(svn_wc__conflict_skel_resolve): New function.
* subversion/libsvn_wc/conflicts.h
(svn_wc__conflict_skel_resolve): New function.
* subversion/libsvn_wc/wc_db.c
(op_mark_resolved_baton): Add db.
(db_op_mark_resolved): Add implementation for conflict skel storage. Return
an error when operating on non-existing paths.
Modified:
subversion/trunk/subversion/libsvn_wc/conflicts.c
subversion/trunk/subversion/libsvn_wc/conflicts.h
subversion/trunk/subversion/libsvn_wc/wc_db.c
Modified: subversion/trunk/subversion/libsvn_wc/conflicts.c
URL: http://svn.apache.org/viewvc/subversion/trunk/subversion/libsvn_wc/conflicts.c?rev=1357333&r1=1357332&r2=1357333&view=diff
==============================================================================
--- subversion/trunk/subversion/libsvn_wc/conflicts.c (original)
+++ subversion/trunk/subversion/libsvn_wc/conflicts.c Wed Jul 4 16:27:47 2012
@@ -566,6 +566,91 @@ svn_wc__conflict_skel_add_tree_conflict(
return SVN_NO_ERROR;
}
+svn_error_t *
+svn_wc__conflict_skel_resolve(svn_boolean_t *completely_resolved,
+ svn_skel_t *conflict_skel,
+ svn_wc__db_t *db,
+ const char *wri_abspath,
+ svn_boolean_t resolve_text,
+ const char *resolve_prop,
+ svn_boolean_t resolve_tree,
+ apr_pool_t *result_pool,
+ apr_pool_t *scratch_pool)
+{
+ svn_skel_t *op;
+ svn_skel_t **pconflict;
+ SVN_ERR(conflict__get_operation(&op, conflict_skel));
+
+ if (!op)
+ return svn_error_create(SVN_ERR_INCOMPLETE_DATA, NULL,
+ _("Not a completed conflict skel"));
+
+ /* We are going to drop items from a linked list. Instead of keeping
+ a pointer to the item we want to drop we store a pointer to the
+ pointer of what we may drop, to allow setting it to the next item. */
+
+ pconflict = &(conflict_skel->children->next->children);
+ while (*pconflict)
+ {
+ svn_skel_t *c = (*pconflict)->children;
+
+ if (resolve_text
+ && svn_skel__matches_atom(c, SVN_WC__CONFLICT_KIND_TEXT))
+ {
+ /* Remove the text conflict from the linked list */
+ *pconflict = (*pconflict)->next;
+ continue;
+ }
+ else if (resolve_prop
+ && svn_skel__matches_atom(c, SVN_WC__CONFLICT_KIND_PROP))
+ {
+ svn_skel_t **ppropnames = &(c->next->next->children);
+
+ if (resolve_prop[0] == '\0')
+ *ppropnames = NULL; /* remove all conflicted property names */
+ else
+ while (*ppropnames)
+ {
+ if (svn_skel__matches_atom(*ppropnames, resolve_prop))
+ {
+ *ppropnames = (*ppropnames)->next;
+ break;
+ }
+ ppropnames = &((*ppropnames)->next);
+ }
+
+ /* If no conflicted property names left */
+ if (!c->next->next->children)
+ {
+ /* Remove the propery conflict skel from the linked list */
+ *pconflict = (*pconflict)->next;
+ continue;
+ }
+ }
+ else if (resolve_tree
+ && svn_skel__matches_atom(c, SVN_WC__CONFLICT_KIND_TREE))
+ {
+ /* Remove the tree conflict from the linked list */
+ *pconflict = (*pconflict)->next;
+ continue;
+ }
+
+ pconflict = &((*pconflict)->next);
+ }
+
+ if (completely_resolved)
+ {
+ /* Nice, we can just call the complete function */
+ svn_boolean_t complete_conflict;
+ SVN_ERR(svn_wc__conflict_skel_is_complete(&complete_conflict,
+ conflict_skel));
+
+ *completely_resolved = !complete_conflict;
+ }
+ return SVN_NO_ERROR;
+}
+
+
/* A map for svn_wc_operation_t values. */
static const svn_token_map_t operation_map[] =
{
Modified: subversion/trunk/subversion/libsvn_wc/conflicts.h
URL: http://svn.apache.org/viewvc/subversion/trunk/subversion/libsvn_wc/conflicts.h?rev=1357333&r1=1357332&r2=1357333&view=diff
==============================================================================
--- subversion/trunk/subversion/libsvn_wc/conflicts.h (original)
+++ subversion/trunk/subversion/libsvn_wc/conflicts.h Wed Jul 4 16:27:47 2012
@@ -212,6 +212,42 @@ svn_wc__conflict_skel_add_tree_conflict(
apr_pool_t *result_pool,
apr_pool_t *scratch_pool);
+/* Allows resolving specific conflicts stored in CONFLICT_SKEL.
+
+ When RESOLVE_TEXT is TRUE and CONFLICT_SKEL contains a text conflict,
+ resolve/remove the text conflict in CONFLICT_SKEL.
+
+ When RESOLVE_PROP is "" and CONFLICT_SKEL contains a property conflict,
+ resolve/remove all property conflicts in CONFLICT_SKEL.
+
+ When RESOLVE_PROP is not NULL and not "", remove the property conflict on
+ the property RESOLVE_PROP in CONFLICT_SKEL. When RESOLVE_PROP was the last
+ property in CONFLICT_SKEL remove the property conflict info from
+ CONFLICT_SKEL.
+
+ When RESOLVE_TREE is TRUE and CONFLICT_SKEL contains a tree conflict,
+ resolve/remove the tree conflict in CONFLICT_SKEL.
+
+ If COMPLETELY_RESOLVED is not NULL, then set *COMPLETELY_RESOLVED to TRUE,
+ when no conflict registration is left in CONFLICT_SKEL after editting,
+ otherwise to FALSE.
+
+ Allocate data stored in the skel in RESULT_POOL.
+
+ This functions edits CONFLICT_SKEL. New skels might be created in
+ RESULT_POOL. Temporary allocations will use SCRATCH_POOL.
+ */
+/* ### db, wri_abspath is currently unused. Remove? */
+svn_error_t *
+svn_wc__conflict_skel_resolve(svn_boolean_t *completely_resolved,
+ svn_skel_t *conflict_skel,
+ svn_wc__db_t *db,
+ const char *wri_abspath,
+ svn_boolean_t resolve_text,
+ const char *resolve_prop,
+ svn_boolean_t resolve_tree,
+ apr_pool_t *result_pool,
+ apr_pool_t *scratch_pool);
/*
* -----------------------------------------------------------
Modified: subversion/trunk/subversion/libsvn_wc/wc_db.c
URL: http://svn.apache.org/viewvc/subversion/trunk/subversion/libsvn_wc/wc_db.c?rev=1357333&r1=1357332&r2=1357333&view=diff
==============================================================================
--- subversion/trunk/subversion/libsvn_wc/wc_db.c (original)
+++ subversion/trunk/subversion/libsvn_wc/wc_db.c Wed Jul 4 16:27:47 2012
@@ -5483,6 +5483,9 @@ struct op_mark_resolved_baton
svn_boolean_t resolved_props;
svn_boolean_t resolved_tree;
const svn_skel_t *work_items;
+#if SVN_WC__VERSION >= SVN_WC__USES_CONFLICT_SKELS
+ svn_wc__db_t *db;
+#endif
};
/* Helper for svn_wc__db_op_mark_resolved */
@@ -5494,9 +5497,48 @@ db_op_mark_resolved(void *baton,
{
struct op_mark_resolved_baton *rb = baton;
svn_sqlite__stmt_t *stmt;
- int affected_rows;
+ svn_boolean_t have_row;
int total_affected_rows = 0;
+#if SVN_WC__VERSION < SVN_WC__USES_CONFLICT_SKELS
+ int affected_rows;
+#else
+ svn_boolean_t have_conflict;
+ apr_size_t conflict_len;
+ const void *conflict_data;
+ svn_skel_t *conflicts;
+#endif
+
+ /* Check if we have a conflict in ACTUAL */
+ SVN_ERR(svn_sqlite__get_statement(&stmt, wcroot->sdb,
+ STMT_SELECT_ACTUAL_NODE));
+ SVN_ERR(svn_sqlite__bindf(stmt, "is", wcroot->wc_id, local_relpath));
+
+ SVN_ERR(svn_sqlite__step(&have_row, stmt));
+
+ if (! have_row)
+ {
+ SVN_ERR(svn_sqlite__reset(stmt));
+
+ SVN_ERR(svn_sqlite__get_statement(&stmt, wcroot->sdb,
+ STMT_SELECT_NODE_INFO));
+ SVN_ERR(svn_sqlite__bindf(stmt, "is", wcroot->wc_id, local_relpath));
+
+ SVN_ERR(svn_sqlite__step(&have_row, stmt));
+ SVN_ERR(svn_sqlite__reset(stmt));
+
+ if (have_row)
+ return SVN_NO_ERROR;
+
+ return svn_error_createf(SVN_ERR_WC_PATH_NOT_FOUND, NULL,
+ _("The node '%s' was not found."),
+ path_for_error_message(wcroot,
+ local_relpath,
+ scratch_pool));
+ }
+
+#if SVN_WC__VERSION < SVN_WC__USES_CONFLICT_SKELS
+ SVN_ERR(svn_sqlite__reset(stmt));
if (rb->resolved_text)
{
SVN_ERR(svn_sqlite__get_statement(&stmt, wcroot->sdb,
@@ -5521,6 +5563,32 @@ db_op_mark_resolved(void *baton,
SVN_ERR(svn_sqlite__update(&affected_rows, stmt));
total_affected_rows += affected_rows;
}
+#else
+ conflict_data = svn_sqlite__column_blob(stmt, 2, &conflict_len,
+ scratch_pool);
+ conflicts = svn_skel__parse(conflict_data, conflict_len, scratch_pool);
+ SVN_ERR(svn_sqlite__reset(stmt));
+
+ SVN_ERR(svn_wc__conflict_skel_resolve(&have_conflict, conflicts,
+ rb->db, wcroot->abspath,
+ rb->resolved_text,
+ rb->resolved_props ? "" : NULL,
+ rb->resolved_tree,
+ scratch_pool, scratch_pool));
+
+ SVN_ERR(svn_sqlite__get_statement(&stmt, wcroot->sdb,
+ STMT_UPDATE_ACTUAL_CONFLICT));
+ SVN_ERR(svn_sqlite__bindf(stmt, "is", wcroot->wc_id, local_relpath));
+
+ if (have_conflict)
+ {
+ svn_stringbuf_t *sb = svn_skel__unparse(conflicts, scratch_pool);
+
+ SVN_ERR(svn_sqlite__bind_blob(stmt, 3, sb->data, sb->len));
+ }
+
+ SVN_ERR(svn_sqlite__update(&total_affected_rows, stmt));
+#endif
/* Now, remove the actual node if it doesn't have any more useful
information. We only need to do this if we've remove data ourselves. */
@@ -5560,6 +5628,9 @@ svn_wc__db_op_mark_resolved(svn_wc__db_t
rb.resolved_text = resolved_text;
rb.resolved_tree = resolved_tree;
rb.work_items = work_items;
+#if SVN_WC__VERSION >= SVN_WC__USES_CONFLICT_SKELS
+ rb.db = db;
+#endif
SVN_ERR(svn_wc__db_with_txn(wcroot, local_relpath, db_op_mark_resolved,
&rb, scratch_pool));
@@ -11624,22 +11695,25 @@ get_conflict_marker_files(void *baton, s
{
apr_size_t len;
const void *data = svn_sqlite__column_blob(stmt, 2, &len, scratch_pool);
- svn_skel_t *conflicts;
+
const apr_array_header_t *markers;
int i;
- conflicts = svn_skel__parse(data, len, scratch_pool);
+ if (data)
+ {
+ svn_skel_t *conflicts;
+ conflicts = svn_skel__parse(data, len, scratch_pool);
- /* ### ADD markers to *marker_files */
- SVN_ERR(svn_wc__conflict_read_markers(&markers, mfb->db, wcroot->abspath,
- conflicts,
- result_pool, scratch_pool));
+ SVN_ERR(svn_wc__conflict_read_markers(&markers, mfb->db, wcroot->abspath,
+ conflicts,
+ result_pool, scratch_pool));
- for (i = 0; markers && (i < markers->nelts); i++)
- {
- const char *marker_abspath = APR_ARRAY_IDX(markers, i, const char*);
+ for (i = 0; markers && (i < markers->nelts); i++)
+ {
+ const char *marker_abspath = APR_ARRAY_IDX(markers, i, const char*);
- apr_hash_set(marker_files, marker_abspath, APR_HASH_KEY_STRING, "");
+ apr_hash_set(marker_files, marker_abspath, APR_HASH_KEY_STRING, "");
+ }
}
SVN_ERR(svn_sqlite__step(&have_row, stmt));