You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@subversion.apache.org by hw...@apache.org on 2010/08/11 00:07:31 UTC

svn commit: r984234 [11/20] - in /subversion/branches/ignore-mergeinfo: ./ build/ build/ac-macros/ build/generator/ notes/ notes/api-errata/ notes/obliterate/ notes/obliterate/fspec-cc1/ notes/rename-tracking/ notes/svnpatch/ notes/tree-conflicts/ note...

Modified: subversion/branches/ignore-mergeinfo/subversion/libsvn_wc/node.c
URL: http://svn.apache.org/viewvc/subversion/branches/ignore-mergeinfo/subversion/libsvn_wc/node.c?rev=984234&r1=984233&r2=984234&view=diff
==============================================================================
--- subversion/branches/ignore-mergeinfo/subversion/libsvn_wc/node.c (original)
+++ subversion/branches/ignore-mergeinfo/subversion/libsvn_wc/node.c Tue Aug 10 22:07:24 2010
@@ -45,10 +45,9 @@
 #include "svn_types.h"
 
 #include "wc.h"
-#include "lock.h"
 #include "props.h"
-#include "log.h"
 #include "entries.h"
+#include "log.h"
 #include "wc_db.h"
 
 #include "svn_private_config.h"
@@ -329,29 +328,18 @@ svn_wc__internal_node_get_url(const char
   svn_wc__db_status_t status;
   const char *repos_relpath;
   const char *repos_root_url;
-  svn_boolean_t base_shadowed;
+  svn_boolean_t have_base;
 
   SVN_ERR(svn_wc__db_read_info(&status, NULL, NULL, &repos_relpath,
                                &repos_root_url,
                                NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
-                               NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
-                               &base_shadowed, NULL, NULL,
+                               NULL, NULL, NULL, NULL, NULL, NULL, NULL,
+                               &have_base, NULL, NULL, NULL,
                                db, local_abspath,
                                scratch_pool, scratch_pool));
   if (repos_relpath == NULL)
     {
-      if (status == svn_wc__db_status_normal
-          || status == svn_wc__db_status_incomplete
-          || (base_shadowed
-              && (status == svn_wc__db_status_deleted
-                  || status == svn_wc__db_status_obstructed_delete)))
-        {
-          SVN_ERR(svn_wc__db_scan_base_repos(&repos_relpath, &repos_root_url,
-                                             NULL,
-                                             db, local_abspath,
-                                             scratch_pool, scratch_pool));
-        }
-      else if (status == svn_wc__db_status_added)
+      if (status == svn_wc__db_status_added)
         {
           SVN_ERR(svn_wc__db_scan_addition(NULL, NULL, &repos_relpath,
                                            &repos_root_url, NULL, NULL, NULL,
@@ -359,16 +347,27 @@ svn_wc__internal_node_get_url(const char
                                            db, local_abspath,
                                            scratch_pool, scratch_pool));
         }
+      else if (have_base)
+        {
+          SVN_ERR(svn_wc__db_scan_base_repos(&repos_relpath, &repos_root_url,
+                                             NULL,
+                                             db, local_abspath,
+                                             scratch_pool, scratch_pool));
+        }
       else if (status == svn_wc__db_status_absent
                || status == svn_wc__db_status_excluded
                || status == svn_wc__db_status_not_present
-               || (!base_shadowed
+               || (!have_base
                    && (status == svn_wc__db_status_deleted
                        || status == svn_wc__db_status_obstructed_delete)))
         {
           const char *parent_abspath;
 
-          svn_dirent_split(local_abspath, &parent_abspath, &repos_relpath,
+          /* Set 'repos_root_url' to the *full URL* of the parent WC dir,
+           * and 'repos_relpath' to the *single path component* that is the
+           * basename of this WC directory, so that joining them will result
+           * in the correct full URL. */
+          svn_dirent_split(&parent_abspath, &repos_relpath, local_abspath,
                            scratch_pool);
           SVN_ERR(svn_wc__internal_node_get_url(&repos_root_url, db,
                                                 parent_abspath,
@@ -402,8 +401,75 @@ svn_wc__node_get_url(const char **url,
                             result_pool, scratch_pool));
 }
 
+/* ### This is essentially a copy-paste of svn_wc__internal_get_url(). 
+ * ### If we decide to keep this one, then it should be rewritten to avoid
+ * ### code duplication.*/
+svn_error_t *
+svn_wc__node_get_repos_relpath(const char **repos_relpath,
+                               svn_wc_context_t *wc_ctx,
+                               const char *local_abspath,
+                               apr_pool_t *result_pool,
+                               apr_pool_t *scratch_pool)
+{
+  svn_wc__db_status_t status;
+  svn_boolean_t have_base;
+
+  SVN_ERR(svn_wc__db_read_info(&status, NULL, NULL, repos_relpath,
+                               NULL, NULL, NULL, NULL, NULL, NULL, NULL,
+                               NULL, NULL, NULL, NULL, NULL, NULL, NULL,
+                               NULL, NULL, &have_base, NULL, NULL, NULL,
+                               wc_ctx->db, local_abspath,
+                               result_pool, scratch_pool));
+  if (*repos_relpath == NULL)
+    {
+      if (status == svn_wc__db_status_added)
+        {
+          SVN_ERR(svn_wc__db_scan_addition(NULL, NULL, repos_relpath,
+                                           NULL, NULL, NULL, NULL,
+                                           NULL, NULL,
+                                           wc_ctx->db, local_abspath,
+                                           result_pool, scratch_pool));
+        }
+      else if (have_base)
+        {
+          SVN_ERR(svn_wc__db_scan_base_repos(repos_relpath, NULL,
+                                             NULL,
+                                             wc_ctx->db, local_abspath,
+                                             result_pool, scratch_pool));
+        }
+      else if (status == svn_wc__db_status_excluded
+               || (!have_base
+                   && (status == svn_wc__db_status_deleted
+                       || status == svn_wc__db_status_obstructed_delete)))
+        {
+          const char *parent_abspath, *basename, *parent_relpath;
+
+          svn_dirent_split(&parent_abspath, &basename, local_abspath,
+                           scratch_pool);
+          SVN_ERR(svn_wc__node_get_repos_relpath(&parent_relpath, wc_ctx,
+                                                 parent_abspath,
+                                                 scratch_pool,
+                                                 scratch_pool));
+
+          if (parent_relpath)
+            *repos_relpath = svn_relpath_join(parent_relpath, basename,
+                                              result_pool);
+        }
+      else
+        {
+          /* Status: obstructed, obstructed_add */
+          *repos_relpath = NULL;
+          return SVN_NO_ERROR;
+        }
+    }
+
+  return SVN_NO_ERROR;
+}
+
 svn_error_t *
-svn_wc__node_get_copyfrom_info(const char **copyfrom_url,
+svn_wc__node_get_copyfrom_info(const char **copyfrom_root_url,
+                               const char **copyfrom_repos_relpath,
+                               const char **copyfrom_url,
                                svn_revnum_t *copyfrom_rev,
                                svn_boolean_t *is_copy_target,
                                svn_wc_context_t *wc_ctx,
@@ -417,6 +483,10 @@ svn_wc__node_get_copyfrom_info(const cha
   svn_revnum_t original_revision;
   svn_wc__db_status_t status;
 
+  if (copyfrom_root_url)
+    *copyfrom_root_url = NULL;
+  if (copyfrom_repos_relpath)
+    *copyfrom_repos_relpath = NULL;
   if (copyfrom_url)
     *copyfrom_url = NULL;
   if (copyfrom_rev)
@@ -429,7 +499,7 @@ svn_wc__node_get_copyfrom_info(const cha
                                NULL, &original_repos_relpath,
                                &original_root_url, NULL, &original_revision,
                                NULL, NULL, NULL, NULL, NULL, db,
-                               local_abspath, scratch_pool, scratch_pool));
+                               local_abspath, result_pool, scratch_pool));
   if (original_root_url && original_repos_relpath)
     {
       /* If this was the root of the copy then the URL is immediately
@@ -441,6 +511,10 @@ svn_wc__node_get_copyfrom_info(const cha
                                                       original_repos_relpath,
                                                       result_pool);
 
+      if (copyfrom_root_url)
+        *copyfrom_root_url = original_root_url;
+      if (copyfrom_repos_relpath)
+        *copyfrom_repos_relpath = original_repos_relpath;
       if (copyfrom_url)
         *copyfrom_url = my_copyfrom_url;
 
@@ -465,12 +539,13 @@ svn_wc__node_get_copyfrom_info(const cha
           const char *base_name;
           const char *parent_copyfrom_url;
 
-          svn_dirent_split(local_abspath, &parent_abspath, &base_name,
+          svn_dirent_split(&parent_abspath, &base_name, local_abspath,
                            scratch_pool);
 
           /* This is a copied node, so we should never fall off the top of a
            * working copy here. */
-          SVN_ERR(svn_wc__node_get_copyfrom_info(&parent_copyfrom_url,
+          SVN_ERR(svn_wc__node_get_copyfrom_info(NULL, NULL,
+                                                 &parent_copyfrom_url,
                                                  NULL, NULL,
                                                  wc_ctx, parent_abspath,
                                                  scratch_pool, scratch_pool));
@@ -487,7 +562,8 @@ svn_wc__node_get_copyfrom_info(const cha
     }
   else if ((status == svn_wc__db_status_added
             || status == svn_wc__db_status_obstructed_add)
-           && (copyfrom_rev || copyfrom_url))
+           && (copyfrom_rev || copyfrom_url || copyfrom_root_url
+               || copyfrom_repos_relpath))
     {
       /* ...But if this is merely the descendant of an explicitly
          copied/moved directory, we need to do a bit more work to
@@ -498,7 +574,7 @@ svn_wc__node_get_copyfrom_info(const cha
                                        NULL, &original_repos_relpath,
                                        &original_root_url, NULL,
                                        &original_revision, db, local_abspath,
-                                       scratch_pool, scratch_pool));
+                                       result_pool, scratch_pool));
       if (status == svn_wc__db_status_copied ||
           status == svn_wc__db_status_moved_here)
         {
@@ -512,6 +588,12 @@ svn_wc__node_get_copyfrom_info(const cha
                                             scratch_pool);
           if (src_relpath)
             {
+              if (copyfrom_root_url)
+                *copyfrom_root_url = original_root_url;
+              if (copyfrom_repos_relpath)
+                *copyfrom_repos_relpath = svn_relpath_join(
+                                            original_repos_relpath,
+                                            src_relpath, result_pool);
               if (copyfrom_url)
                 *copyfrom_url = svn_path_url_add_component2(src_parent_url,
                                                             src_relpath,
@@ -623,26 +705,28 @@ svn_wc__internal_walk_children(svn_wc__d
                                apr_pool_t *scratch_pool)
 {
   svn_wc__db_kind_t kind;
-  svn_depth_t depth;
+  svn_wc__db_status_t status;
+
+  SVN_ERR_ASSERT(walk_depth >= svn_depth_empty
+                 && walk_depth <= svn_depth_infinity);
 
-  SVN_ERR(svn_wc__db_read_info(NULL, &kind, NULL, NULL, NULL, NULL,
-                               NULL, NULL, NULL, NULL, &depth, NULL,
+  /* Check if the node exists before the first callback */
+  SVN_ERR(svn_wc__db_read_info(&status, &kind, NULL, NULL, NULL, NULL,
+                               NULL, NULL, NULL, NULL, NULL, NULL,
                                NULL, NULL, NULL, NULL, NULL, NULL, NULL,
                                NULL, NULL, NULL, NULL, NULL,
                                db, local_abspath, scratch_pool, scratch_pool));
 
-  if (kind == svn_wc__db_kind_file || depth == svn_depth_exclude)
-    {
-      return svn_error_return(
-        walk_callback(local_abspath, walk_baton, scratch_pool));
-    }
+  SVN_ERR(walk_callback(local_abspath, walk_baton, scratch_pool));
+
+  if (kind == svn_wc__db_kind_file
+      || status == svn_wc__db_status_not_present
+      || status == svn_wc__db_status_excluded
+      || status == svn_wc__db_status_absent)
+    return SVN_NO_ERROR;
 
   if (kind == svn_wc__db_kind_dir)
     {
-      /* Return the directory first, before starting recursion, since it
-         won't get returned as part of the recursion. */
-      SVN_ERR(walk_callback(local_abspath, walk_baton, scratch_pool));
-
       return svn_error_return(
         walker_helper(db, local_abspath, show_hidden, walk_callback, walk_baton,
                       walk_depth, cancel_func, cancel_baton, scratch_pool));
@@ -786,7 +870,7 @@ svn_wc__internal_is_replaced(svn_boolean
                              apr_pool_t *scratch_pool)
 {
   svn_wc__db_status_t status;
-  svn_boolean_t base_shadowed;
+  svn_boolean_t have_base;
   svn_wc__db_status_t base_status;
 
   SVN_ERR(svn_wc__db_read_info(
@@ -794,11 +878,11 @@ svn_wc__internal_is_replaced(svn_boolean
             NULL, NULL, NULL, NULL, NULL, NULL,
             NULL, NULL, NULL, NULL, NULL, NULL,
             NULL, NULL, NULL, NULL,
-            NULL, NULL, &base_shadowed,
+            NULL, &have_base, NULL,
             NULL, NULL,
             db, local_abspath,
             scratch_pool, scratch_pool));
-  if (base_shadowed)
+  if (have_base)
     SVN_ERR(svn_wc__db_base_get_info(&base_status, NULL, NULL,
                                      NULL, NULL, NULL,
                                      NULL, NULL, NULL,
@@ -809,7 +893,7 @@ svn_wc__internal_is_replaced(svn_boolean
 
   *replaced = ((status == svn_wc__db_status_added
                 || status == svn_wc__db_status_obstructed_add)
-               && base_shadowed
+               && have_base
                && base_status != svn_wc__db_status_not_present);
 
   return SVN_NO_ERROR;
@@ -835,13 +919,13 @@ svn_wc__node_get_base_rev(svn_revnum_t *
                           apr_pool_t *scratch_pool)
 {
   svn_wc__db_status_t status;
-  svn_boolean_t base_shadowed;
+  svn_boolean_t have_base;
 
   SVN_ERR(svn_wc__db_read_info(&status,
                                NULL, base_revision,
                                NULL, NULL, NULL, NULL, NULL, NULL, NULL,
                                NULL, NULL, NULL, NULL, NULL, NULL, NULL,
-                               NULL, NULL, NULL, NULL, &base_shadowed,
+                               NULL, NULL, NULL, &have_base, NULL,
                                NULL, NULL,
                                wc_ctx->db, local_abspath,
                                scratch_pool, scratch_pool));
@@ -849,7 +933,7 @@ svn_wc__node_get_base_rev(svn_revnum_t *
   if (SVN_IS_VALID_REVNUM(*base_revision))
     return SVN_NO_ERROR;
 
-  if (base_shadowed)
+  if (have_base)
     {
       /* The node was replaced with something else. Look at the base.  */
       SVN_ERR(svn_wc__db_base_get_info(NULL, NULL, base_revision,
@@ -875,15 +959,18 @@ svn_wc__node_get_working_rev_info(svn_re
                                   apr_pool_t *result_pool)
 {
   svn_wc__db_status_t status;
-  svn_boolean_t base_shadowed;
+  svn_boolean_t have_base;
 
   SVN_ERR(svn_wc__db_read_info(&status, NULL, revision, NULL, NULL, NULL,
                                changed_rev, changed_date, changed_author,
                                NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
-                               NULL, NULL, NULL, NULL, &base_shadowed, NULL,
+                               NULL, NULL, NULL, &have_base, NULL, NULL,
                                NULL, wc_ctx->db, local_abspath, result_pool,
                                scratch_pool));
 
+  if (SVN_IS_VALID_REVNUM(*changed_rev) && SVN_IS_VALID_REVNUM(*revision))
+    return SVN_NO_ERROR; /* We got everything we need */
+
   if (status == svn_wc__db_status_deleted)
     {
       const char *work_del_abspath = NULL;
@@ -899,7 +986,7 @@ svn_wc__node_get_working_rev_info(svn_re
                                        NULL, changed_rev, changed_date,
                                        changed_author, NULL, NULL, NULL,
                                        NULL, NULL, NULL, NULL, NULL, NULL,
-                                       NULL, NULL, NULL, &base_shadowed,
+                                       NULL, NULL, NULL, NULL, 
                                        NULL, NULL, wc_ctx->db, work_del_abspath,
                                        result_pool, scratch_pool));
         }
@@ -914,13 +1001,23 @@ svn_wc__node_get_working_rev_info(svn_re
                                            scratch_pool));
         }
     }
-  else if (base_shadowed)
+  else if (have_base)
     {
-      SVN_ERR(svn_wc__db_base_get_info(NULL, NULL, revision, NULL, NULL,
+      svn_wc__db_status_t base_status;
+      svn_revnum_t base_rev;
+      SVN_ERR(svn_wc__db_base_get_info(&base_status, NULL, &base_rev, NULL, NULL,
                                        NULL, changed_rev, changed_date,
                                        changed_author, NULL, NULL, NULL,
                                        NULL, NULL, NULL, wc_ctx->db, local_abspath,
                                        result_pool, scratch_pool));
+
+      if (revision && !SVN_IS_VALID_REVNUM(*revision)
+          && base_status != svn_wc__db_status_not_present)
+        {
+          /* When we used entries we reset the revision to 0 when we added a new
+             node over an existing not present node */
+          *revision = base_rev;
+        }
     }
   return SVN_NO_ERROR;
 }
@@ -933,13 +1030,13 @@ svn_wc__node_get_commit_base_rev(svn_rev
                                  apr_pool_t *scratch_pool)
 {
   svn_wc__db_status_t status;
-  svn_boolean_t base_shadowed;
+  svn_boolean_t have_base;
 
   SVN_ERR(svn_wc__db_read_info(&status, NULL,
                                commit_base_revision,
                                NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
                                NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
-                               NULL, NULL, &base_shadowed, NULL, NULL,
+                               NULL, &have_base, NULL, NULL, NULL,
                                wc_ctx->db, local_abspath, scratch_pool,
                                scratch_pool));
 
@@ -958,7 +1055,7 @@ svn_wc__node_get_commit_base_rev(svn_rev
                                        wc_ctx->db, local_abspath,
                                        scratch_pool, scratch_pool));
 
-      if (! SVN_IS_VALID_REVNUM(*commit_base_revision) && base_shadowed)
+      if (! SVN_IS_VALID_REVNUM(*commit_base_revision) && have_base)
         /* It is a replace that does not feature a copy/move-here.
            Return the revert-base revision. */
         return svn_error_return(
@@ -1123,3 +1220,263 @@ svn_wc__temp_get_keep_local(svn_boolean_
 
   return SVN_NO_ERROR;
 }
+
+svn_error_t *
+svn_wc__internal_node_get_schedule(svn_wc_schedule_t *schedule,
+                                   svn_boolean_t *copied,
+                                   svn_wc__db_t *db,
+                                   const char *local_abspath,
+                                   apr_pool_t *scratch_pool)
+{
+  svn_wc__db_status_t status;
+  svn_boolean_t has_base;
+  const char *copyfrom_relpath;
+
+  if (schedule)
+    *schedule = svn_wc_schedule_normal;
+  if (copied)
+    *copied = FALSE;
+
+  SVN_ERR(svn_wc__db_read_info(&status, NULL, NULL, NULL, NULL, NULL, NULL,
+                               NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
+                               &copyfrom_relpath, NULL, NULL, NULL, NULL,
+                               &has_base, NULL, NULL, NULL,
+                               db, local_abspath, scratch_pool, scratch_pool));
+
+  switch (status)
+    {
+      case svn_wc__db_status_not_present:
+      case svn_wc__db_status_absent:
+      case svn_wc__db_status_excluded:
+        return svn_error_createf(SVN_ERR_ENTRY_NOT_FOUND, NULL,
+                                 _("'%s' is not under version control"),
+                                 svn_dirent_local_style(local_abspath,
+                                                        scratch_pool));
+
+      case svn_wc__db_status_normal:
+      case svn_wc__db_status_incomplete:
+      case svn_wc__db_status_obstructed:
+        break;
+
+      case svn_wc__db_status_deleted:
+      case svn_wc__db_status_obstructed_delete:
+        {
+          const char *work_del_abspath;
+
+          if (schedule)
+            *schedule = svn_wc_schedule_delete;
+
+          if (!copied)
+            break;
+
+          /* Find out details of our deletion.  */
+          SVN_ERR(svn_wc__db_scan_deletion(NULL,
+                                           NULL,
+                                           NULL,
+                                           &work_del_abspath,
+                                           db, local_abspath,
+                                           scratch_pool, scratch_pool));
+
+          if (!work_del_abspath)
+            break; /* Base deletion */
+
+          /* We miss the 4th tree to properly find out if this is
+             the root of a working-delete. Only in that case
+             should copied be set to true. See entries.c for details. */
+
+          *copied = FALSE; /* Until we can fix this test */
+          break;
+        }
+      case svn_wc__db_status_added:
+      case svn_wc__db_status_obstructed_add:
+        {
+          const char *op_root_abspath;
+          const char *parent_abspath;
+          const char *parent_copyfrom_relpath;
+          const char *child_name;
+
+          if (schedule)
+            *schedule = svn_wc_schedule_add;
+
+          if (copyfrom_relpath != NULL)
+            {
+              status = svn_wc__db_status_copied; /* Or moved */
+              op_root_abspath = local_abspath;
+            }
+          else
+            SVN_ERR(svn_wc__db_scan_addition(&status,
+                                             &op_root_abspath,
+                                             NULL, NULL, NULL,
+                                             &copyfrom_relpath,
+                                             NULL, NULL, NULL,
+                                             db, local_abspath,
+                                             scratch_pool, scratch_pool));
+
+          if (copied && status != svn_wc__db_status_added)
+            *copied = TRUE;
+
+          if (!schedule)
+            break;
+
+          if (has_base)
+            {
+              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,
+                                               db, local_abspath,
+                                               scratch_pool, scratch_pool));
+
+              if (base_status != svn_wc__db_status_not_present)
+                *schedule = svn_wc_schedule_replace;
+            }
+
+          if (status == svn_wc__db_status_added)
+            break; /* Local addition */
+
+          /* Determine the parent status to check if we should show the
+             schedule of a child of a copy as normal. */
+          if (strcmp(op_root_abspath, local_abspath) != 0)
+            {
+              *schedule = svn_wc_schedule_normal;
+              break; /* Part of parent copy */
+            }
+
+          /* When we used entries we didn't see just a different revision
+             as a new operational root, so we have to check if the parent
+             is from the same copy origin */
+          parent_abspath = svn_dirent_dirname(local_abspath, scratch_pool);
+
+          SVN_ERR(svn_wc__db_read_info(&status, NULL, NULL, NULL, NULL, NULL,
+                                       NULL, NULL, NULL, NULL, NULL, NULL,
+                                       NULL, NULL, NULL,
+                                       &parent_copyfrom_relpath, NULL, NULL,
+                                       NULL, NULL, NULL, NULL, NULL, NULL,
+                                       db, parent_abspath,
+                                       scratch_pool, scratch_pool));
+
+          if (status != svn_wc__db_status_added)
+            break; /* Parent was not added */
+
+          if (!parent_copyfrom_relpath)
+            {
+              SVN_ERR(svn_wc__db_scan_addition(&status, &op_root_abspath, NULL,
+                                               NULL, NULL,
+                                               &parent_copyfrom_relpath, NULL,
+                                               NULL, NULL,
+                                               db, parent_abspath,
+                                               scratch_pool, scratch_pool));
+
+              if (!parent_copyfrom_relpath)
+                break; /* Parent is a local addition */
+
+              parent_copyfrom_relpath = svn_relpath_join(
+                                           parent_copyfrom_relpath,
+                                           svn_dirent_is_child(op_root_abspath,
+                                                               parent_abspath,
+                                                               NULL),
+                                           scratch_pool);
+            }
+
+
+          child_name = svn_relpath_is_child(parent_copyfrom_relpath,
+                                            copyfrom_relpath, NULL);
+
+          if (!child_name
+              || strcmp(child_name, svn_dirent_basename(local_abspath, NULL)))
+            break; /* Different operation */
+
+          *schedule = svn_wc_schedule_normal;
+          break;
+        }
+      default:
+        SVN_ERR_MALFUNCTION();
+    }
+
+  return SVN_NO_ERROR;
+}
+
+svn_error_t *
+svn_wc__node_get_schedule(svn_wc_schedule_t *schedule,
+                          svn_boolean_t *copied,
+                          svn_wc_context_t *wc_ctx,
+                          const char *local_abspath,
+                          apr_pool_t *scratch_pool)
+{
+  return svn_error_return(
+           svn_wc__internal_node_get_schedule(schedule,
+                                              copied,
+                                              wc_ctx->db,
+                                              local_abspath,
+                                              scratch_pool));
+}
+
+svn_error_t *
+svn_wc__node_get_info_bits(apr_time_t *text_time,
+                           const char **conflict_old,
+                           const char **conflict_new,
+                           const char **conflict_wrk,
+                           const char **prejfile,
+                           svn_wc_context_t *wc_ctx,
+                           const char *local_abspath,
+                           apr_pool_t *result_pool,
+                           apr_pool_t *scratch_pool)
+{
+  svn_boolean_t conflicted;
+
+  SVN_ERR(svn_wc__db_read_info(NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
+                               NULL, text_time, NULL, NULL, NULL, NULL, NULL,
+                               NULL, NULL, NULL, NULL, NULL, NULL, NULL,
+                               &conflicted, NULL,
+                               wc_ctx->db, local_abspath,
+                               scratch_pool, scratch_pool));
+
+  if (conflict_old)
+    *conflict_old = NULL;
+  if (conflict_new)
+    *conflict_new = NULL;
+  if (conflict_wrk)
+    *conflict_wrk = NULL;
+  if (prejfile)
+    *prejfile = NULL;
+
+  if (conflicted
+      && (conflict_old || conflict_new || conflict_wrk || prejfile))
+    {
+      const apr_array_header_t *conflicts;
+      int j;
+      SVN_ERR(svn_wc__db_read_conflicts(&conflicts, wc_ctx->db, local_abspath,
+                                        scratch_pool, scratch_pool));
+
+      for (j = 0; j < conflicts->nelts; j++)
+        {
+          const svn_wc_conflict_description2_t *cd;
+          cd = APR_ARRAY_IDX(conflicts, j,
+                             const svn_wc_conflict_description2_t *);
+
+          switch (cd->kind)
+            {
+            case svn_wc_conflict_kind_text:
+              if (conflict_old)
+                *conflict_old = apr_pstrdup(result_pool, cd->base_file);
+
+              if (conflict_new)
+                *conflict_new = apr_pstrdup(result_pool, cd->their_file);
+
+              if (conflict_wrk)
+                *conflict_wrk = apr_pstrdup(result_pool, cd->my_file);
+              break;
+
+            case svn_wc_conflict_kind_property:
+              if (prejfile)
+                *prejfile = apr_pstrdup(result_pool, cd->their_file);
+              break;
+            case svn_wc_conflict_kind_tree:
+              break;
+            }
+        }
+    }
+
+  return SVN_NO_ERROR;
+}

Modified: subversion/branches/ignore-mergeinfo/subversion/libsvn_wc/old-and-busted.c
URL: http://svn.apache.org/viewvc/subversion/branches/ignore-mergeinfo/subversion/libsvn_wc/old-and-busted.c?rev=984234&r1=984233&r2=984234&view=diff
==============================================================================
--- subversion/branches/ignore-mergeinfo/subversion/libsvn_wc/old-and-busted.c (original)
+++ subversion/branches/ignore-mergeinfo/subversion/libsvn_wc/old-and-busted.c Tue Aug 10 22:07:24 2010
@@ -75,6 +75,10 @@
 #define ENTRIES_ATTR_CHECKSUM           "checksum"
 #define ENTRIES_ATTR_WORKING_SIZE       "working-size"
 #define ENTRIES_ATTR_TEXT_TIME          "text-time"
+#define ENTRIES_ATTR_CONFLICT_OLD       "conflict-old" /* saved old file */
+#define ENTRIES_ATTR_CONFLICT_NEW       "conflict-new" /* saved new file */
+#define ENTRIES_ATTR_CONFLICT_WRK       "conflict-wrk" /* saved wrk file */
+#define ENTRIES_ATTR_PREJFILE           "prop-reject-file"
 
 /* Attribute values used in our old XML entries file.  */
 #define ENTRIES_VALUE_FILE     "file"
@@ -748,10 +752,8 @@ extract_string(apr_hash_t *atts,
 
 /* Like extract_string(), but normalizes empty strings to NULL.  */
 static const char *
-extract_string_normalize(int *modify_flags,
-                         apr_hash_t *atts,
+extract_string_normalize(apr_hash_t *atts,
                          const char *att_name,
-                         int flag,
                          apr_pool_t *result_pool)
 {
   const char *value = apr_hash_get(atts, att_name, APR_HASH_KEY_STRING);
@@ -759,9 +761,6 @@ extract_string_normalize(int *modify_fla
   if (value == NULL)
     return NULL;
 
-  if (modify_flags)
-    *modify_flags |= flag;
-
   if (*value == '\0')
     return NULL;
 
@@ -769,8 +768,8 @@ extract_string_normalize(int *modify_fla
 }
 
 
-/* NOTE: this is used for running old logs, and for upgrading old XML-based
-   entries file. Be wary of removing items.
+/* NOTE: this is used for upgrading old XML-based entries file. Be wary of
+         removing items.
 
    ### many attributes are no longer used within the old-style log files.
    ### These attrs need to be recognized for old entries, however. For these
@@ -778,18 +777,18 @@ extract_string_normalize(int *modify_fla
    ### for that particular field. MODIFY_FLAGS is *only* used by the
    ### log-based entry modification system, and will go way once we
    ### completely move away from loggy.
-*/
-svn_error_t *
-svn_wc__atts_to_entry(svn_wc_entry_t **new_entry,
-                      int *modify_flags,
-                      apr_hash_t *atts,
-                      apr_pool_t *pool)
+
+   Set *NEW_ENTRY to a new entry, taking attributes from ATTS, whose
+   keys and values are both char *.  Allocate the entry and copy
+   attributes into POOL as needed. */
+static svn_error_t *
+atts_to_entry(svn_wc_entry_t **new_entry,
+              apr_hash_t *atts,
+              apr_pool_t *pool)
 {
   svn_wc_entry_t *entry = alloc_entry(pool);
   const char *name;
 
-  *modify_flags = 0;
-
   /* Find the name and set up the entry under that name. */
   name = apr_hash_get(atts, ENTRIES_ATTR_NAME, APR_HASH_KEY_STRING);
   entry->name = name ? apr_pstrdup(pool, name) : SVN_WC_ENTRY_THIS_DIR;
@@ -871,26 +870,18 @@ svn_wc__atts_to_entry(svn_wc_entry_t **n
   }
 
   /* Is this entry in a state of mental torment (conflict)? */
-  entry->prejfile = extract_string_normalize(
-                      modify_flags, atts,
-                      SVN_WC__ENTRY_ATTR_PREJFILE,
-                      SVN_WC__ENTRY_MODIFY_PREJFILE,
-                      pool);
-  entry->conflict_old = extract_string_normalize(
-                          modify_flags, atts,
-                          SVN_WC__ENTRY_ATTR_CONFLICT_OLD,
-                          SVN_WC__ENTRY_MODIFY_CONFLICT_OLD,
-                          pool);
-  entry->conflict_new = extract_string_normalize(
-                          modify_flags, atts,
-                          SVN_WC__ENTRY_ATTR_CONFLICT_NEW,
-                          SVN_WC__ENTRY_MODIFY_CONFLICT_NEW,
-                          pool);
-  entry->conflict_wrk = extract_string_normalize(
-                          modify_flags, atts,
-                          SVN_WC__ENTRY_ATTR_CONFLICT_WRK,
-                          SVN_WC__ENTRY_MODIFY_CONFLICT_WRK,
-                          pool);
+  entry->prejfile = extract_string_normalize(atts,
+                                             ENTRIES_ATTR_PREJFILE,
+                                             pool);
+  entry->conflict_old = extract_string_normalize(atts,
+                                                 ENTRIES_ATTR_CONFLICT_OLD,
+                                                 pool);
+  entry->conflict_new = extract_string_normalize(atts,
+                                                 ENTRIES_ATTR_CONFLICT_NEW,
+                                                 pool);
+  entry->conflict_wrk = extract_string_normalize(atts,
+                                                 ENTRIES_ATTR_CONFLICT_WRK,
+                                                 pool);
 
   /* Is this entry copied? */
   /* ### not used by loggy; no need to set MODIFY_FLAGS  */
@@ -1035,7 +1026,6 @@ handle_start_tag(void *userData, const c
   apr_hash_t *attributes;
   svn_wc_entry_t *entry;
   svn_error_t *err;
-  int modify_flags = 0;
 
   /* We only care about the `entry' tag; all other tags, such as `xml'
      and `wc-entries', are ignored. */
@@ -1045,7 +1035,7 @@ handle_start_tag(void *userData, const c
   svn_pool_clear(accum->scratch_pool);
   /* Make an entry from the attributes. */
   attributes = svn_xml_make_att_hash(atts, accum->scratch_pool);
-  err = svn_wc__atts_to_entry(&entry, &modify_flags, attributes, accum->pool);
+  err = atts_to_entry(&entry, attributes, accum->pool);
   if (err)
     {
       svn_xml_signal_bailout(err, accum->parser);
@@ -1317,7 +1307,7 @@ svn_wc_entry(const svn_wc_entry_t **entr
 
       const char *dir_abspath;
 
-      svn_dirent_split(local_abspath, &dir_abspath, &entry_name, pool);
+      svn_dirent_split(&dir_abspath, &entry_name, local_abspath, pool);
 
       dir_access = svn_wc__adm_retrieve_internal2(db, dir_abspath, pool);
     }

Modified: subversion/branches/ignore-mergeinfo/subversion/libsvn_wc/props.c
URL: http://svn.apache.org/viewvc/subversion/branches/ignore-mergeinfo/subversion/libsvn_wc/props.c?rev=984234&r1=984233&r2=984234&view=diff
==============================================================================
--- subversion/branches/ignore-mergeinfo/subversion/libsvn_wc/props.c (original)
+++ subversion/branches/ignore-mergeinfo/subversion/libsvn_wc/props.c Tue Aug 10 22:07:24 2010
@@ -54,7 +54,6 @@
 #include "wc.h"
 #include "log.h"
 #include "adm_files.h"
-#include "entries.h"
 #include "props.h"
 #include "translate.h"
 #include "lock.h"  /* for svn_wc__write_check()  */
@@ -852,34 +851,51 @@ generate_conflict_message(const char *pr
       /* Attempting to delete the value INCOMING_BASE.  */
       SVN_ERR_ASSERT_NO_RETURN(incoming_base != NULL);
 
+      /* Are we trying to delete a local addition? */
+      if (original == NULL && mine != NULL)
+        return svn_string_createf(result_pool,
+                                  _("Trying to delete property '%s' with "
+                                    "value '%s',\nbut property has been "
+                                    "locally added with value '%s'."),
+                                  propname, incoming_base->data,
+                                  mine->data);
+
       /* A conflict can only occur if we originally had the property;
          otherwise, we would have merged the property-delete into the
          non-existent property.  */
       SVN_ERR_ASSERT_NO_RETURN(original != NULL);
 
-      if (mine && svn_string_compare(original, incoming_base))
+      if (svn_string_compare(original, incoming_base))
+        {
+          if (mine)
+            /* We were trying to delete the correct property, but an edit
+               caused the conflict.  */
+            return svn_string_createf(result_pool,
+                                      _("Trying to delete property '%s' with "
+                                        "value '%s',\nbut it has been modified "
+                                        "from '%s' to '%s'."),
+                                      propname, incoming_base->data,
+                                      original->data, mine->data);
+        }
+      else if (mine == NULL)
         {
-          /* We were trying to delete the correct property, but an edit
-             caused the conflict.  */
+          /* We were trying to delete the property, but we have locally
+             deleted the same property, but with a different value. */
           return svn_string_createf(result_pool,
                                     _("Trying to delete property '%s' with "
-                                      "value '%s'\nbut it has been modified "
-                                      "from '%s' to '%s'."),
+                                      "value '%s',\nbut property with value "
+                                      "'%s' is locally deleted."),
                                     propname, incoming_base->data,
-                                    original->data, mine->data);
+                                    original->data);          
         }
 
       /* We were trying to delete INCOMING_BASE but our ORIGINAL is
          something else entirely.  */
       SVN_ERR_ASSERT_NO_RETURN(!svn_string_compare(original, incoming_base));
 
-      /* ### wait. what if we had a different property and locally
-         ### deleted it? the statement below is gonna blow up.
-         ### we could have: local-add, local-edit, local-del, or just
-         ### something different (and unchanged).  */
       return svn_string_createf(result_pool,
                                 _("Trying to delete property '%s' with "
-                                  "value '%s'\nbut the local value is "
+                                  "value '%s',\nbut the local value is "
                                   "'%s'."),
                                 propname, incoming_base->data, mine->data);
     }
@@ -1466,12 +1482,27 @@ apply_single_prop_delete(svn_wc_notify_s
 
   if (! base_val)
     {
-      /* ### what about working_val? what if we locally-added?  */
-
-      apr_hash_set(working_props, propname, APR_HASH_KEY_STRING, NULL);
-      if (old_val)
-        /* This is a merge, merging a delete into non-existent */
-        set_prop_merge_state(state, svn_wc_notify_state_merged);
+      if (working_val
+          && !svn_string_compare(working_val, old_val))
+        {
+          /* We are trying to delete a locally-added prop. */
+          SVN_ERR(maybe_generate_propconflict(conflict_remains,
+                                              db, local_abspath,
+                                              left_version, right_version,
+                                              is_dir, propname,
+                                              working_props, old_val, NULL,
+                                              base_val, working_val,
+                                              conflict_func, conflict_baton,
+                                              dry_run, scratch_pool));
+        }
+      else
+        {
+          apr_hash_set(working_props, propname, APR_HASH_KEY_STRING, NULL);
+          if (old_val)
+            /* This is a merge, merging a delete into non-existent
+               property or a local addition of same prop value. */
+            set_prop_merge_state(state, svn_wc_notify_state_merged);
+        }
     }
 
   else if (svn_string_compare(base_val, old_val))
@@ -1496,7 +1527,8 @@ apply_single_prop_delete(svn_wc_notify_s
              }
          }
        else
-         /* The property is locally deleted, so it's a merge */
+         /* The property is locally deleted from the same value, so it's
+            a merge */
          set_prop_merge_state(state, svn_wc_notify_state_merged);
     }
 
@@ -1785,7 +1817,6 @@ svn_wc__merge_props(svn_wc_notify_state_
   apr_pool_t *iterpool;
   int i;
   svn_boolean_t is_dir;
-  const char *adm_abspath;
   svn_skel_t *conflict_skel = NULL;
 
   SVN_ERR_ASSERT(base_props != NULL);
@@ -1796,11 +1827,6 @@ svn_wc__merge_props(svn_wc_notify_state_
 
   is_dir = (kind == svn_wc__db_kind_dir);
 
-  if (is_dir)
-    adm_abspath = local_abspath;
-  else
-    adm_abspath = svn_dirent_dirname(local_abspath, scratch_pool);
-
   if (!server_baseprops)
     server_baseprops = base_props;
 
@@ -1935,7 +1961,7 @@ svn_wc__merge_props(svn_wc_notify_state_
               reject_filename = SVN_WC__THIS_DIR_PREJ;
             }
           else
-            svn_dirent_split(local_abspath, &reject_dirpath, &reject_filename,
+            svn_dirent_split(&reject_dirpath, &reject_filename, local_abspath,
                              scratch_pool);
 
           SVN_ERR(svn_io_open_uniquely_named(NULL, &reject_path,
@@ -1952,14 +1978,14 @@ svn_wc__merge_props(svn_wc_notify_state_
 
       /* Mark entry as "conflicted" with a particular .prej file. */
       {
-        svn_wc_entry_t entry;
         svn_skel_t *work_item;
 
-        entry.prejfile = svn_dirent_is_child(adm_abspath, reject_path, NULL);
-        SVN_ERR(svn_wc__loggy_entry_modify(&work_item, db, adm_abspath,
-                                           local_abspath, &entry,
-                                           SVN_WC__ENTRY_MODIFY_PREJFILE,
-                                           scratch_pool));
+        SVN_ERR(svn_wc__wq_tmp_build_set_property_conflict_marker(
+                                          &work_item,
+                                          db, local_abspath,
+                                          svn_dirent_basename(reject_path, NULL),
+                                          scratch_pool, scratch_pool));
+
         SVN_ERR(svn_wc__db_wq_add(db, local_abspath, work_item, scratch_pool));
       }
 

Modified: subversion/branches/ignore-mergeinfo/subversion/libsvn_wc/relocate.c
URL: http://svn.apache.org/viewvc/subversion/branches/ignore-mergeinfo/subversion/libsvn_wc/relocate.c?rev=984234&r1=984233&r2=984234&view=diff
==============================================================================
--- subversion/branches/ignore-mergeinfo/subversion/libsvn_wc/relocate.c (original)
+++ subversion/branches/ignore-mergeinfo/subversion/libsvn_wc/relocate.c Tue Aug 10 22:07:24 2010
@@ -30,8 +30,6 @@
 #include "svn_path.h"
 
 #include "wc.h"
-#include "entries.h"
-#include "lock.h"
 #include "props.h"
 
 #include "svn_private_config.h"