subversion-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From s...@apache.org
Subject svn commit: r1041580 [10/35] - in /subversion/branches/gpg-agent-password-store: ./ build/ build/ac-macros/ build/generator/ build/generator/templates/ build/win32/ contrib/hook-scripts/ contrib/server-side/ notes/http-and-webdav/ notes/wc-ng/ subversi...
Date Thu, 02 Dec 2010 20:55:18 GMT
Modified: subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/conflicts.c
URL: http://svn.apache.org/viewvc/subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/conflicts.c?rev=1041580&r1=1041579&r2=1041580&view=diff
==============================================================================
--- subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/conflicts.c (original)
+++ subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/conflicts.c Thu Dec  2 20:55:08 2010
@@ -50,152 +50,6 @@
 
 #include "svn_private_config.h"
 
-struct svn_wc_conflict_t
-{
-  /* ### kind + property name are the primary keys of a conflict */
-  /* The kind of conflict recorded */
-  svn_wc_conflict_kind_t kind;
-
-  /* When describing a property conflict the property name
-     or "" when no property name is available. (Upgrade from old WC or
-     raised via compatibility apis). */
-  const char *property_name;
-
-  /* ### TODO: Add more fields */
-};
-
-/* */
-static svn_error_t *
-conflict_alloc(svn_wc_conflict_t **conflict, apr_pool_t *result_pool)
-{
-  svn_wc_conflict_t *c = apr_pcalloc(result_pool, sizeof(*c));
-
-  *conflict = c;
-
-  return SVN_NO_ERROR;
-}
-
-svn_error_t *
-svn_wc_conflict_dup(svn_wc_conflict_t **duplicate,
-                    const svn_wc_conflict_t *base,
-                    apr_pool_t *result_pool)
-{
-  svn_wc_conflict_t *c;
-
-  SVN_ERR(conflict_alloc(&c, result_pool));
-
-  c->kind = base->kind;
-  c->property_name = base->property_name
-                          ? apr_pstrdup(result_pool, base->property_name)
-                          : NULL;
-
-  *duplicate = c;
-  return SVN_NO_ERROR;
-}
-
-svn_error_t *
-svn_wc_create_property_conflict(svn_wc_conflict_t **conflict,
-                                const char *property_name,
-                                const svn_wc_conflict_version_t *older_version,
-                                const svn_wc_conflict_version_t *left_version,
-                                const svn_wc_conflict_version_t *right_version,
-                                const svn_string_t *older_value,
-                                const svn_string_t *left_value,
-                                const svn_string_t *right_value,
-                                const char *marker_abspath,
-                                svn_wc_operation_t operation,
-                                apr_pool_t *result_pool,
-                                apr_pool_t *scratch_pool)
-{
-  SVN_ERR_MALFUNCTION(); /* ### Not implemented yet */
-}
-
-svn_error_t *
-svn_wc_create_text_conflict(svn_wc_conflict_t **conflict,
-                            const svn_wc_conflict_version_t *older_version,
-                            const svn_wc_conflict_version_t *left_version,
-                            const svn_wc_conflict_version_t *right_version,
-                            const char *older_abspath,
-                            const char *left_abspath,
-                            const char *right_abspath,
-                            svn_wc_operation_t operation,
-                            apr_pool_t *result_pool,
-                            apr_pool_t *scratch_pool)
-{
-  SVN_ERR_MALFUNCTION(); /* ### Not implemented yet */
-}
-
-svn_error_t *
-svn_wc_create_tree_conflict(svn_wc_conflict_t **conflict,
-                            const svn_wc_conflict_version_t *older_version,
-                            const svn_wc_conflict_version_t *left_version,
-                            const svn_wc_conflict_version_t *right_version,
-                            svn_wc_conflict_action_t action,
-                            svn_wc_conflict_reason_t reason,
-                            svn_wc_operation_t operation,
-                            apr_pool_t *result_pool,
-                            apr_pool_t *scratch_pool)
-{
-  SVN_ERR_MALFUNCTION(); /* ### Not implemented yet */
-}
-
-svn_error_t *
-svn_wc_get_conflict_info(svn_wc_conflict_kind_t *kind,
-                         const char **property_name,
-                         svn_wc_conflict_action_t *action,
-                         svn_wc_conflict_reason_t *reason,
-                         svn_wc_operation_t *operation,
-                         svn_boolean_t *conflict_resolved,
-                         svn_wc_context_t *wc_ctx,
-                         const char *local_abspath,
-                         svn_wc_conflict_t *conflict,
-                         apr_pool_t *result_pool,
-                         apr_pool_t *scratch_pool)
-{
-  SVN_ERR_MALFUNCTION(); /* ### Not implemented yet */
-}
-
-
-svn_error_t *
-svn_wc_get_conflict_marker_files(const char **older_abspath,
-                                 const char **left_abspath,
-                                 const char **right_abspath,
-                                 svn_wc_context_t *wc_ctx,
-                                 const char *local_abspath,
-                                 svn_wc_conflict_t *conflict,
-                                 apr_pool_t *result_pool,
-                                 apr_pool_t *scratch_pool)
-{
-  SVN_ERR_MALFUNCTION(); /* ### Not implemented yet */
-}
-
-svn_error_t *
-svn_wc_get_conflict_sources(const svn_wc_conflict_version_t **older_version,
-                            const svn_wc_conflict_version_t **left_version,
-                            const svn_wc_conflict_version_t **right_version,
-                            svn_wc_context_t *wc_ctx,
-                            const char *local_abspath,
-                            svn_wc_conflict_t *conflict,
-                            apr_pool_t *result_pool,
-                            apr_pool_t *scratch_pool)
-{
-  SVN_ERR_MALFUNCTION(); /* ### Not implemented yet */
-}
-
-svn_error_t *
-svn_wc_get_property_conflict_data(const svn_string_t **older_value,
-                                  const svn_string_t **left_value,
-                                  const svn_string_t **right_value,
-                                  svn_wc_context_t *wc_ctx,
-                                  const char *local_abspath,
-                                  svn_wc_conflict_t *conflict,
-                                  apr_pool_t *result_pool,
-                                  apr_pool_t *scratch_pool)
-{
-  SVN_ERR_MALFUNCTION(); /* ### Not implemented yet */
-}
-
-
 svn_skel_t *
 svn_wc__conflict_skel_new(apr_pool_t *result_pool)
 {
@@ -312,6 +166,8 @@ attempt_deletion(const char *parent_dir,
    ### leave, for example, one of the conflict artifact files deleted but
    ### the entry still referring to it and trying to use it for the next
    ### attempt at resolving.
+
+   ### Does this still apply in the world of WC-NG?  -hkw
 */
 static svn_error_t *
 resolve_conflict_on_node(svn_wc__db_t *db,
@@ -334,11 +190,7 @@ resolve_conflict_on_node(svn_wc__db_t *d
 
   *did_resolve = FALSE;
 
-  SVN_ERR(svn_wc__db_read_info(NULL, &kind, NULL, NULL, NULL, NULL, NULL,
-                               NULL, NULL, NULL, NULL, NULL, NULL, NULL,
-                               NULL, NULL, NULL, NULL, NULL, NULL, NULL,
-                               NULL, NULL, NULL,
-                               db, local_abspath, pool, pool));
+  SVN_ERR(svn_wc__db_read_kind(&kind, db, local_abspath, TRUE, pool));
   SVN_ERR(svn_wc__db_read_conflicts(&conflicts, db, local_abspath,
                                     pool, pool));
 
@@ -366,6 +218,7 @@ resolve_conflict_on_node(svn_wc__db_t *d
 
   if (resolve_text)
     {
+      svn_stream_t *tmp_stream = NULL;
       const char *auto_resolve_src;
 
       /* Handle automatic conflict resolution before the temporary files are
@@ -390,7 +243,6 @@ resolve_conflict_on_node(svn_wc__db_t *d
             if (conflict_old && conflict_working && conflict_new)
               {
                 const char *temp_dir;
-                svn_stream_t *tmp_stream;
                 svn_diff_t *diff;
                 svn_diff_conflict_display_style_t style =
                   conflict_choice == svn_wc_conflict_choose_theirs_conflict
@@ -402,7 +254,8 @@ resolve_conflict_on_node(svn_wc__db_t *d
                                                        pool, pool));
                 SVN_ERR(svn_stream_open_unique(&tmp_stream,
                                                &auto_resolve_src,
-                                               temp_dir, svn_io_file_del_none,
+                                               temp_dir,
+                                               svn_io_file_del_on_close,
                                                pool, pool));
 
                 /* ### If any of these paths isn't absolute, treat it
@@ -436,7 +289,6 @@ resolve_conflict_on_node(svn_wc__db_t *d
                                                     NULL, NULL, NULL, NULL,
                                                     style,
                                                     pool));
-                SVN_ERR(svn_stream_close(tmp_stream));
               }
             else
               auto_resolve_src = NULL;
@@ -451,6 +303,9 @@ resolve_conflict_on_node(svn_wc__db_t *d
         SVN_ERR(svn_io_copy_file(
           svn_dirent_join(conflict_dir_abspath, auto_resolve_src, pool),
           local_abspath, TRUE, pool));
+
+      if (tmp_stream)
+        SVN_ERR(svn_stream_close(tmp_stream));
     }
 
   /* Records whether we found any of the conflict files.  */

Modified: subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/copy.c
URL: http://svn.apache.org/viewvc/subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/copy.c?rev=1041580&r1=1041579&r2=1041580&view=diff
==============================================================================
--- subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/copy.c (original)
+++ subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/copy.c Thu Dec  2 20:55:08 2010
@@ -197,17 +197,13 @@ copy_pristine_text_if_necessary(svn_wc__
    otherwise copy both the versioned metadata and the filesystem node (even
    if it is the wrong kind, and recursively if it is a dir).
 
-   A replacement for both copy_file_administratively and
-   copy_added_file_administratively.
-
-   ### Not yet fully working.  Relies on in-db-props.
-
    This also works for versioned symlinks that are stored in the db as
    svn_wc__db_kind_file with svn:special set. */
 static svn_error_t *
 copy_versioned_file(svn_wc__db_t *db,
                     const char *src_abspath,
                     const char *dst_abspath,
+                    const char *dst_op_root_abspath,
                     svn_boolean_t metadata_only,
                     svn_cancel_func_t cancel_func,
                     void *cancel_baton,
@@ -218,8 +214,6 @@ copy_versioned_file(svn_wc__db_t *db,
   svn_skel_t *work_items = NULL;
   const char *dir_abspath = svn_dirent_dirname(dst_abspath, scratch_pool);
   const char *tmpdir_abspath;
-  const char *tmp_dst_abspath;
-  svn_node_kind_t kind;
 
   SVN_ERR(svn_wc__db_temp_wcroot_tempdir(&tmpdir_abspath, db, dst_abspath,
                                          scratch_pool, scratch_pool));
@@ -234,14 +228,29 @@ copy_versioned_file(svn_wc__db_t *db,
      copy recursively if it's a dir. */
   if (!metadata_only)
     {
-      SVN_ERR(copy_to_tmpdir(&tmp_dst_abspath, &kind, src_abspath,
+      const char *tmp_dst_abspath;
+      svn_node_kind_t disk_kind;
+
+      SVN_ERR(copy_to_tmpdir(&tmp_dst_abspath, &disk_kind, src_abspath,
                              tmpdir_abspath,
                              TRUE, /* recursive */
                              cancel_func, cancel_baton, scratch_pool));
+
       if (tmp_dst_abspath)
         {
           svn_skel_t *work_item;
 
+          /* Remove 'read-only' from the destination file; it's a local add. */
+            {
+              const svn_string_t *needs_lock;
+              SVN_ERR(svn_wc__internal_propget(&needs_lock, db, src_abspath,
+                                               SVN_PROP_NEEDS_LOCK,
+                                               scratch_pool, scratch_pool));
+              if (needs_lock)
+                SVN_ERR(svn_io_set_file_read_write(tmp_dst_abspath,
+                                                   FALSE, scratch_pool));
+            }
+
           SVN_ERR(svn_wc__wq_build_file_move(&work_item, db,
                                              tmp_dst_abspath, dst_abspath,
                                              scratch_pool, scratch_pool));
@@ -251,7 +260,7 @@ copy_versioned_file(svn_wc__db_t *db,
 
   /* Copy the (single) node's metadata, and move the new filesystem node
      into place. */
-  SVN_ERR(svn_wc__db_op_copy(db, src_abspath, dst_abspath,
+  SVN_ERR(svn_wc__db_op_copy(db, src_abspath, dst_abspath, dst_op_root_abspath,
                              work_items, scratch_pool));
   SVN_ERR(svn_wc__wq_run(db, dir_abspath,
                          cancel_func, cancel_baton, scratch_pool));
@@ -275,6 +284,7 @@ static svn_error_t *
 copy_versioned_dir(svn_wc__db_t *db,
                    const char *src_abspath,
                    const char *dst_abspath,
+                   const char *dst_op_root_abspath,
                    svn_boolean_t metadata_only,
                    svn_cancel_func_t cancel_func,
                    void *cancel_baton,
@@ -285,21 +295,22 @@ copy_versioned_dir(svn_wc__db_t *db,
   svn_skel_t *work_items = NULL;
   const char *dir_abspath = svn_dirent_dirname(dst_abspath, scratch_pool);
   const char *tmpdir_abspath;
-  const char *tmp_dst_abspath;
   const apr_array_header_t *versioned_children;
-  apr_hash_t *children;
-  svn_node_kind_t kind;
+  apr_hash_t *disk_children;
+  svn_node_kind_t disk_kind;
   apr_pool_t *iterpool;
   int i;
 
   /* Prepare a temp copy of the single filesystem node (usually a dir). */
   if (!metadata_only)
     {
+      const char *tmp_dst_abspath;
+
       SVN_ERR(svn_wc__db_temp_wcroot_tempdir(&tmpdir_abspath, db,
                                              dst_abspath,
                                              scratch_pool, scratch_pool));
 
-      SVN_ERR(copy_to_tmpdir(&tmp_dst_abspath, &kind, src_abspath,
+      SVN_ERR(copy_to_tmpdir(&tmp_dst_abspath, &disk_kind, src_abspath,
                              tmpdir_abspath, FALSE, /* recursive */
                              cancel_func, cancel_baton, scratch_pool));
       if (tmp_dst_abspath)
@@ -315,7 +326,7 @@ copy_versioned_dir(svn_wc__db_t *db,
 
   /* Copy the (single) node's metadata, and move the new filesystem node
      into place. */
-  SVN_ERR(svn_wc__db_op_copy(db, src_abspath, dst_abspath,
+  SVN_ERR(svn_wc__db_op_copy(db, src_abspath, dst_abspath, dst_op_root_abspath,
                              work_items, scratch_pool));
   SVN_ERR(svn_wc__wq_run(db, dir_abspath,
                          cancel_func, cancel_baton, scratch_pool));
@@ -329,12 +340,14 @@ copy_versioned_dir(svn_wc__db_t *db,
       (*notify_func)(notify_baton, notify, scratch_pool);
     }
 
-  if (!metadata_only && kind == svn_node_dir)
+  if (!metadata_only && disk_kind == svn_node_dir)
     /* All filesystem children, versioned and unversioned.  We're only
        interested in their names, so we can pass TRUE as the only_check_type
        param. */
-    SVN_ERR(svn_io_get_dirents3(&children, src_abspath, TRUE,
+    SVN_ERR(svn_io_get_dirents3(&disk_children, src_abspath, TRUE,
                                 scratch_pool, scratch_pool));
+  else
+    disk_children = NULL;
 
   /* Copy all the versioned children */
   SVN_ERR(svn_wc__db_read_children(&versioned_children, db, src_abspath,
@@ -359,12 +372,14 @@ copy_versioned_dir(svn_wc__db_t *db,
       if (child_kind == svn_wc__db_kind_file)
         SVN_ERR(copy_versioned_file(db,
                                     child_src_abspath, child_dst_abspath,
+                                    dst_op_root_abspath,
                                     metadata_only,
                                     cancel_func, cancel_baton, NULL, NULL,
                                     iterpool));
       else if (child_kind == svn_wc__db_kind_dir)
         SVN_ERR(copy_versioned_dir(db,
                                    child_src_abspath, child_dst_abspath,
+                                   dst_op_root_abspath,
                                    metadata_only,
                                    cancel_func, cancel_baton, NULL, NULL,
                                    iterpool));
@@ -374,21 +389,22 @@ copy_versioned_dir(svn_wc__db_t *db,
                                  svn_dirent_local_style(child_src_abspath,
                                                         scratch_pool));
 
-      if (!metadata_only && kind == svn_node_dir)
+      if (disk_children)
         /* Remove versioned child as it has been handled */
-        apr_hash_set(children, child_name, APR_HASH_KEY_STRING, NULL);
+        apr_hash_set(disk_children, child_name, APR_HASH_KEY_STRING, NULL);
     }
 
   /* Copy all the remaining filesystem children, which are unversioned. */
-  if (!metadata_only && kind == svn_node_dir)
+  if (disk_children)
     {
       apr_hash_index_t *hi;
 
-      for (hi = apr_hash_first(scratch_pool, children); hi;
+      for (hi = apr_hash_first(scratch_pool, disk_children); hi;
            hi = apr_hash_next(hi))
         {
           const char *name = svn__apr_hash_index_key(hi);
           const char *unver_src_abspath, *unver_dst_abspath;
+          const char *tmp_dst_abspath;
 
           if (svn_wc_is_adm_dir(name, iterpool))
             continue;
@@ -400,8 +416,8 @@ copy_versioned_dir(svn_wc__db_t *db,
           unver_src_abspath = svn_dirent_join(src_abspath, name, iterpool);
           unver_dst_abspath = svn_dirent_join(dst_abspath, name, iterpool);
 
-          SVN_ERR(copy_to_tmpdir(&tmp_dst_abspath, &kind, unver_src_abspath,
-                                 tmpdir_abspath,
+          SVN_ERR(copy_to_tmpdir(&tmp_dst_abspath, &disk_kind,
+                                 unver_src_abspath, tmpdir_abspath,
                                  TRUE, /* recursive */
                                  cancel_func, cancel_baton, iterpool));
           if (tmp_dst_abspath)
@@ -426,7 +442,6 @@ copy_versioned_dir(svn_wc__db_t *db,
 }
 
 
-
 /* Public Interface */
 
 svn_error_t *
@@ -443,7 +458,7 @@ svn_wc_copy3(svn_wc_context_t *wc_ctx,
   svn_wc__db_t *db = wc_ctx->db;
   svn_wc__db_kind_t src_db_kind;
   const char *dstdir_abspath;
-  
+
   SVN_ERR_ASSERT(svn_dirent_is_absolute(src_abspath));
   SVN_ERR_ASSERT(svn_dirent_is_absolute(dst_abspath));
   
@@ -597,14 +612,16 @@ svn_wc_copy3(svn_wc_context_t *wc_ctx,
   if (src_db_kind == svn_wc__db_kind_file
       || src_db_kind == svn_wc__db_kind_symlink)
     {
-      SVN_ERR(copy_versioned_file(db, src_abspath, dst_abspath, metadata_only,
+      SVN_ERR(copy_versioned_file(db, src_abspath, dst_abspath, dst_abspath,
+                                  metadata_only,
                                   cancel_func, cancel_baton,
                                   notify_func, notify_baton,
                                   scratch_pool));
     }
   else
     {
-      SVN_ERR(copy_versioned_dir(db, src_abspath, dst_abspath, metadata_only,
+      SVN_ERR(copy_versioned_dir(db, src_abspath, dst_abspath, dst_abspath,
+                                 metadata_only,
                                  cancel_func, cancel_baton,
                                  notify_func, notify_baton,
                                  scratch_pool));

Modified: subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/deprecated.c
URL: http://svn.apache.org/viewvc/subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/deprecated.c?rev=1041580&r1=1041579&r2=1041580&view=diff
==============================================================================
--- subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/deprecated.c (original)
+++ subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/deprecated.c Thu Dec  2 20:55:08 2010
@@ -2729,7 +2729,6 @@ svn_wc_add_repos_file3(const char *dst_p
                                  copyfrom_url,
                                  copyfrom_rev,
                                  cancel_func, cancel_baton,
-                                 notify_func, notify_baton,
                                  pool));
 
   return svn_error_return(svn_wc_context_destroy(wc_ctx));

Modified: subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/entries.c
URL: http://svn.apache.org/viewvc/subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/entries.c?rev=1041580&r1=1041579&r2=1041580&view=diff
==============================================================================
--- subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/entries.c (original)
+++ subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/entries.c Thu Dec  2 20:55:08 2010
@@ -74,6 +74,7 @@ typedef struct {
 typedef struct {
   apr_int64_t wc_id;
   const char *local_relpath;
+  apr_int64_t op_depth;
   const char *parent_relpath;
   svn_wc__db_status_t presence;
   svn_node_kind_t kind;  /* ### should switch to svn_wc__db_kind_t */
@@ -471,6 +472,42 @@ get_base_info_for_deleted(svn_wc_entry_t
 }
 
 
+/*
+ * Encode tree conflict descriptions into a single string.
+ *
+ * Set *CONFLICT_DATA to a string, allocated in POOL, that encodes the tree
+ * conflicts in CONFLICTS in a form suitable for storage in a single string
+ * field in a WC entry. CONFLICTS is a hash of zero or more pointers to
+ * svn_wc_conflict_description2_t objects, index by their basenames. All of the
+ * conflict victim paths must be siblings.
+ *
+ * Do all allocations in POOL.
+ *
+ * @see svn_wc__read_tree_conflicts()
+ */
+static svn_error_t *
+write_tree_conflicts(const char **conflict_data,
+                     apr_hash_t *conflicts,
+                     apr_pool_t *pool)
+{
+  svn_skel_t *skel = svn_skel__make_empty_list(pool);
+  apr_hash_index_t *hi;
+
+  for (hi = apr_hash_first(pool, conflicts); hi; hi = apr_hash_next(hi))
+    {
+      svn_skel_t *c_skel;
+
+      SVN_ERR(svn_wc__serialize_conflict(&c_skel, svn__apr_hash_index_val(hi),
+                                         pool, pool));
+      svn_skel__prepend(c_skel, skel);
+    }
+
+  *conflict_data = svn_skel__unparse(skel, pool)->data;
+
+  return SVN_NO_ERROR;
+}
+
+
 /* Read one entry from wc_db. It will be allocated in RESULT_POOL and
    returned in *NEW_ENTRY.
 
@@ -487,7 +524,7 @@ get_base_info_for_deleted(svn_wc_entry_t
 static svn_error_t *
 read_one_entry(const svn_wc_entry_t **new_entry,
                svn_wc__db_t *db,
-               apr_uint64_t wc_id,
+               apr_int64_t wc_id,
                const char *dir_abspath,
                const char *name,
                const svn_wc_entry_t *parent_entry,
@@ -586,9 +623,8 @@ read_one_entry(const svn_wc_entry_t **ne
 
       if (tree_conflicts)
         {
-          SVN_ERR(svn_wc__write_tree_conflicts(&entry->tree_conflict_data,
-                                               tree_conflicts,
-                                               result_pool));
+          SVN_ERR(write_tree_conflicts(&entry->tree_conflict_data,
+                                       tree_conflicts, result_pool));
         }
     }
 
@@ -601,40 +637,24 @@ read_one_entry(const svn_wc_entry_t **ne
          a subdirectory "over" a not-present directory. The read_info()
          will return information out of the wc.db in the subdir. We
          need to detect this situation and create a DELETED entry
-         instead.  */
+         instead.
+
+         ### Does this still happen?  The regression tests passed when
+             the NODES query was erroneously accessing BASE_NODE. */
       if (kind == svn_wc__db_kind_dir)
         {
           svn_sqlite__db_t *sdb;
           svn_sqlite__stmt_t *stmt;
-#ifdef SVN_WC__NODES
-          svn_sqlite__stmt_t *stmt_nodes;
-          svn_boolean_t have_nodes_row;
-#endif
 
           SVN_ERR(svn_wc__db_temp_borrow_sdb(
                     &sdb, db, dir_abspath,
                     svn_wc__db_openmode_readonly,
                     scratch_pool));
 
-#ifndef SVN_WC__NODES_ONLY
           SVN_ERR(svn_sqlite__get_statement(&stmt, sdb,
                                             STMT_SELECT_NOT_PRESENT));
           SVN_ERR(svn_sqlite__bindf(stmt, "is", wc_id, entry->name));
           SVN_ERR(svn_sqlite__step(&have_row, stmt));
-#endif
-#ifdef SVN_WC__NODES
-          SVN_ERR(svn_sqlite__get_statement(&stmt_nodes, sdb,
-                                            STMT_SELECT_NOT_PRESENT));
-          SVN_ERR(svn_sqlite__bindf(stmt_nodes, "is", wc_id, entry->name));
-          SVN_ERR(svn_sqlite__step(&have_nodes_row, stmt_nodes));
-#ifndef SVN_WC__NODES_ONLY
-          SVN_ERR_ASSERT(have_row == have_nodes_row);
-          SVN_ERR(svn_sqlite__reset(stmt_nodes));
-#else
-          stmt = stmt_nodes;
-          have_row = have_nodes_row;
-#endif
-#endif
           SVN_ERR(svn_sqlite__reset(stmt));
         }
 
@@ -1084,7 +1104,7 @@ read_entries_new(apr_hash_t **result_ent
   apr_pool_t *iterpool = svn_pool_create(scratch_pool);
   int i;
   const svn_wc_entry_t *parent_entry;
-  apr_uint64_t wc_id = 1;  /* ### hacky. should remove.  */
+  apr_int64_t wc_id = 1;  /* ### hacky. should remove.  */
 
   entries = apr_hash_make(result_pool);
 
@@ -1139,7 +1159,7 @@ read_entry_pair(const svn_wc_entry_t **p
                 apr_pool_t *result_pool,
                 apr_pool_t *scratch_pool)
 {
-  apr_uint64_t wc_id = 1;  /* ### hacky. should remove.  */
+  apr_int64_t wc_id = 1;  /* ### hacky. should remove.  */
 
   SVN_ERR(read_one_entry(parent_entry, db, wc_id, dir_abspath,
                          "" /* name */,
@@ -1532,77 +1552,9 @@ insert_base_node(svn_sqlite__db_t *sdb,
 {
   svn_sqlite__stmt_t *stmt;
 
-#ifndef SVN_WC__NODES_ONLY
-  /* ### NODE_DATA when switching to NODE_DATA, replace the
-     query below with STMT_INSERT_BASE_NODE_DATA_FOR_ENTRY_1
-     and adjust the parameters bound. Can't do that yet. */
   SVN_ERR(svn_sqlite__get_statement(&stmt, sdb,
                                     STMT_INSERT_BASE_NODE_FOR_ENTRY));
 
-  SVN_ERR(svn_sqlite__bind_int64(stmt, 1, base_node->wc_id));
-  SVN_ERR(svn_sqlite__bind_text(stmt, 2, base_node->local_relpath));
-
-  if (base_node->repos_id)
-    {
-      SVN_ERR(svn_sqlite__bind_int64(stmt, 3, base_node->repos_id));
-      SVN_ERR(svn_sqlite__bind_text(stmt, 4, base_node->repos_relpath));
-    }
-
-  if (base_node->parent_relpath)
-    SVN_ERR(svn_sqlite__bind_text(stmt, 5, base_node->parent_relpath));
-
-  if (base_node->presence == svn_wc__db_status_not_present)
-    SVN_ERR(svn_sqlite__bind_text(stmt, 6, "not-present"));
-  else if (base_node->presence == svn_wc__db_status_normal)
-    SVN_ERR(svn_sqlite__bind_text(stmt, 6, "normal"));
-  else if (base_node->presence == svn_wc__db_status_absent)
-    SVN_ERR(svn_sqlite__bind_text(stmt, 6, "absent"));
-  else if (base_node->presence == svn_wc__db_status_incomplete)
-    SVN_ERR(svn_sqlite__bind_text(stmt, 6, "incomplete"));
-  else if (base_node->presence == svn_wc__db_status_excluded)
-    SVN_ERR(svn_sqlite__bind_text(stmt, 6, "excluded"));
-
-  SVN_ERR(svn_sqlite__bind_int64(stmt, 7, base_node->revision));
-
-  /* ### kind might be "symlink" or "unknown" */
-  if (base_node->kind == svn_node_none)
-    SVN_ERR(svn_sqlite__bind_text(stmt, 5, "unknown"));
-  else
-    SVN_ERR(svn_sqlite__bind_text(stmt, 8,
-                                  svn_node_kind_to_word(base_node->kind)));
-
-  if (base_node->checksum)
-    SVN_ERR(svn_sqlite__bind_checksum(stmt, 9, base_node->checksum,
-                                      scratch_pool));
-
-  if (base_node->translated_size != SVN_INVALID_FILESIZE)
-    SVN_ERR(svn_sqlite__bind_int64(stmt, 10, base_node->translated_size));
-
-  /* ### strictly speaking, changed_rev should be valid for present nodes. */
-  if (SVN_IS_VALID_REVNUM(base_node->changed_rev))
-    SVN_ERR(svn_sqlite__bind_int64(stmt, 11, base_node->changed_rev));
-  if (base_node->changed_date)
-    SVN_ERR(svn_sqlite__bind_int64(stmt, 12, base_node->changed_date));
-  if (base_node->changed_author)
-    SVN_ERR(svn_sqlite__bind_text(stmt, 13, base_node->changed_author));
-
-  SVN_ERR(svn_sqlite__bind_text(stmt, 14, svn_depth_to_word(base_node->depth)));
-
-  SVN_ERR(svn_sqlite__bind_int64(stmt, 15, base_node->last_mod_time));
-
-  if (base_node->properties)
-    SVN_ERR(svn_sqlite__bind_properties(stmt, 16, base_node->properties,
-                                        scratch_pool));
-
-  /* Execute and reset the insert clause. */
-  SVN_ERR(svn_sqlite__insert(NULL, stmt));
-
-#endif
-#ifdef SVN_WC__NODES
-
-  SVN_ERR(svn_sqlite__get_statement(&stmt, sdb,
-                                    STMT_INSERT_BASE_NODE_FOR_ENTRY_1));
-
   SVN_ERR(svn_sqlite__bindf(stmt, "issisr",
                             base_node->wc_id,
                             base_node->local_relpath,
@@ -1655,8 +1607,6 @@ insert_base_node(svn_sqlite__db_t *sdb,
   /* Execute and reset the insert clause. */
   SVN_ERR(svn_sqlite__insert(NULL, stmt));
 
-
-#endif
   return SVN_NO_ERROR;
 }
 
@@ -1668,86 +1618,10 @@ insert_working_node(svn_sqlite__db_t *sd
 {
   svn_sqlite__stmt_t *stmt;
 
-#ifndef SVN_WC__NODES_ONLY
-  /* ### NODE_DATA when switching to NODE_DATA, replace the
-     query below with STMT_INSERT_WORKING_NODE_DATA_2
-     and adjust the parameters bound. Can't do that yet. */
-  SVN_ERR(svn_sqlite__get_statement(&stmt, sdb, STMT_INSERT_WORKING_NODE));
-
-  SVN_ERR(svn_sqlite__bind_int64(stmt, 1, working_node->wc_id));
-  SVN_ERR(svn_sqlite__bind_text(stmt, 2, working_node->local_relpath));
-  SVN_ERR(svn_sqlite__bind_text(stmt, 3, working_node->parent_relpath));
-
-  /* ### need rest of values */
-  if (working_node->presence == svn_wc__db_status_normal)
-    SVN_ERR(svn_sqlite__bind_text(stmt, 4, "normal"));
-  else if (working_node->presence == svn_wc__db_status_not_present)
-    SVN_ERR(svn_sqlite__bind_text(stmt, 4, "not-present"));
-  else if (working_node->presence == svn_wc__db_status_base_deleted)
-    SVN_ERR(svn_sqlite__bind_text(stmt, 4, "base-deleted"));
-  else if (working_node->presence == svn_wc__db_status_incomplete)
-    SVN_ERR(svn_sqlite__bind_text(stmt, 4, "incomplete"));
-  else if (working_node->presence == svn_wc__db_status_excluded)
-    SVN_ERR(svn_sqlite__bind_text(stmt, 4, "excluded"));
-
-  if (working_node->kind == svn_node_none)
-    SVN_ERR(svn_sqlite__bind_text(stmt, 5, "unknown"));
-  else
-    SVN_ERR(svn_sqlite__bind_text(stmt, 5,
-                                  svn_node_kind_to_word(working_node->kind)));
-
-  if (working_node->copyfrom_repos_path)
-    {
-      SVN_ERR(svn_sqlite__bind_int64(stmt, 6,
-                                     working_node->copyfrom_repos_id));
-      SVN_ERR(svn_sqlite__bind_text(stmt, 7,
-                                    working_node->copyfrom_repos_path));
-      SVN_ERR(svn_sqlite__bind_int64(stmt, 8, working_node->copyfrom_revnum));
-    }
-
-  if (working_node->moved_here)
-    SVN_ERR(svn_sqlite__bind_int(stmt, 9, working_node->moved_here));
-
-  if (working_node->moved_to)
-    SVN_ERR(svn_sqlite__bind_text(stmt, 10, working_node->moved_to));
-
-  if (working_node->checksum)
-    SVN_ERR(svn_sqlite__bind_checksum(stmt, 11, working_node->checksum,
-                                      scratch_pool));
-
-  if (working_node->translated_size != SVN_INVALID_FILESIZE)
-    SVN_ERR(svn_sqlite__bind_int64(stmt, 12, working_node->translated_size));
-
-  if (SVN_IS_VALID_REVNUM(working_node->changed_rev))
-    SVN_ERR(svn_sqlite__bind_int64(stmt, 13, working_node->changed_rev));
-  if (working_node->changed_date)
-    SVN_ERR(svn_sqlite__bind_int64(stmt, 14, working_node->changed_date));
-  if (working_node->changed_author)
-    SVN_ERR(svn_sqlite__bind_text(stmt, 15, working_node->changed_author));
-
-  SVN_ERR(svn_sqlite__bind_text(stmt, 16,
-                                svn_depth_to_word(working_node->depth)));
-
-  SVN_ERR(svn_sqlite__bind_int64(stmt, 17, working_node->last_mod_time));
-
-  if (working_node->properties)
-    SVN_ERR(svn_sqlite__bind_properties(stmt, 18, working_node->properties,
-                                        scratch_pool));
-
-  SVN_ERR(svn_sqlite__bind_int64(stmt, 19, working_node->keep_local));
-
-  /* ### we should bind 'symlink_target' (20) as appropriate.  */
-
-  /* Execute and reset the insert clause. */
-  SVN_ERR(svn_sqlite__insert(NULL, stmt));
-#endif
-
-#ifdef SVN_WC__NODES
   SVN_ERR(svn_sqlite__get_statement(&stmt, sdb, STMT_INSERT_NODE));
   SVN_ERR(svn_sqlite__bindf(stmt, "isisnnnnsnrisnnni",
                             working_node->wc_id, working_node->local_relpath,
-                            (working_node->parent_relpath == NULL
-                             ? (apr_int64_t)1 : (apr_int64_t)2),
+                            working_node->op_depth,
                             working_node->parent_relpath,
                             /* Setting depth for files? */
                             svn_depth_to_word(working_node->depth),
@@ -1786,7 +1660,7 @@ insert_working_node(svn_sqlite__db_t *sd
     SVN_ERR(svn_sqlite__bind_checksum(stmt, 14, working_node->checksum,
                                       scratch_pool));
 
-  if (working_node->properties)
+  if (working_node->properties) /* ### Never set, props done later */
     SVN_ERR(svn_sqlite__bind_properties(stmt, 15, working_node->properties,
                                         scratch_pool));
 
@@ -1794,7 +1668,6 @@ insert_working_node(svn_sqlite__db_t *sd
     SVN_ERR(svn_sqlite__bind_int64(stmt, 16, working_node->translated_size));
 
   SVN_ERR(svn_sqlite__insert(NULL, stmt));
-#endif
 
   return SVN_NO_ERROR;
 }
@@ -1839,23 +1712,29 @@ insert_actual_node(svn_sqlite__db_t *sdb
   return svn_error_return(svn_sqlite__insert(NULL, stmt));
 }
 
+struct write_baton {
+  db_base_node_t *base;
+  db_working_node_t *work;
+};
+
 
 /* Write the information for ENTRY to WC_DB.  The WC_ID, REPOS_ID and
    REPOS_ROOT will all be used for writing ENTRY.
    ### transitioning from straight sql to using the wc_db APIs.  For the
    ### time being, we'll need both parameters. */
 static svn_error_t *
-write_entry(svn_wc__db_t *db,
+write_entry(struct write_baton **entry_node,
+            struct write_baton *parent_node,
+            svn_wc__db_t *db,
             svn_sqlite__db_t *sdb,
             apr_int64_t wc_id,
             apr_int64_t repos_id,
-            const char *repos_root,
             const svn_wc_entry_t *entry,
             const char *local_relpath,
             const char *entry_abspath,
             const svn_wc_entry_t *this_dir,
-            svn_boolean_t always_create_actual,
             svn_boolean_t create_locks,
+            apr_pool_t *result_pool,
             apr_pool_t *scratch_pool)
 {
   db_base_node_t *base_node = NULL;
@@ -1868,34 +1747,118 @@ write_entry(svn_wc__db_t *db,
   else
     parent_relpath = svn_relpath_dirname(local_relpath, scratch_pool);
 
+  /* This is how it should work, it doesn't work like this yet because
+     we need proper op_depth to layer the working nodes.
+
+     Using "svn add", "svn rm", "svn cp" only files can be replaced
+     pre-wcng; directories can only be normal, deleted or added.
+     Files cannot be replaced within a deleted directory, so replaced
+     files can only exist in a normal directory, or a directory that
+     is added+copied.  In a normal directory a replaced file needs a
+     base node and a working node, in an added+copied directory a
+     replaced file needs two working nodes at different op-depths.
+
+     With just the above operations the conversion for files and
+     directories is straightforward:
+
+           pre-wcng                             wcng
+     parent         child                 parent     child
+
+     normal         normal                base       base
+     add+copied     normal+copied         work       work
+     normal+copied  normal+copied         work       work
+     normal         delete                base       base+work
+     delete         delete                base+work  base+work
+     add+copied     delete                work       work
+     normal         add                   base       work
+     add            add                   work       work
+     add+copied     add                   work       work
+     normal         add+copied            base       work
+     add            add+copied            work       work
+     add+copied     add+copied            work       work
+     normal         replace               base       base+work
+     add+copied     replace               work       work+work
+     normal         replace+copied        base       base+work
+     add+copied     replace+copied        work       work+work
+
+     However "svn merge" make this more complicated.  The pre-wcng
+     "svn merge" is capable of replacing a directory, that is it can
+     mark the whole tree deleted, and then copy another tree on top.
+     The entries then represent the replacing tree overlayed on the
+     deleted tree.
+
+       original       replace          schedule in
+       tree           tree             combined tree
+
+       A              A                replace+copied
+       A/f                             delete+copied
+       A/g            A/g              replace+copied
+                      A/h              add+copied
+       A/B            A/B              replace+copied
+       A/B/f                           delete+copied
+       A/B/g          A/B/g            replace+copied
+                      A/B/h            add+copied
+       A/C                             delete+copied
+       A/C/f                           delete+copied
+                      A/D              add+copied
+                      A/D/f            add+copied
+
+     The original tree could be normal tree, or an add+copied tree.
+     Committing such a merge generally worked, but making further tree
+     modifications before commit sometimes failed.
+
+     The root of the replace is handled like the file replace:
+
+           pre-wcng                             wcng
+     parent         child                 parent     child
+
+     normal         replace+copied        base       base+work
+     add+copied     replace+copied        work       work+work
+
+     although obviously the node is a directory rather then a file.
+     There are then more conversion states where the parent is
+     replaced.
+
+           pre-wcng                                wcng
+     parent           child              parent            child
+
+     replace+copied   add                [base|work]+work  work
+     replace+copied   add+copied         [base|work]+work  work
+     replace+copied   delete+copied      [base|work]+work  [base|work]+work
+     delete+copied    delete+copied      [base|work]+work  [base|work]+work
+     replace+copied   replace+copied     [base|work]+work  [base|work]+work
+  */
+
   switch (entry->schedule)
     {
       case svn_wc_schedule_normal:
         if (entry->copied)
-          working_node = MAYBE_ALLOC(working_node, scratch_pool);
+          working_node = MAYBE_ALLOC(working_node, result_pool);
         else
-          base_node = MAYBE_ALLOC(base_node, scratch_pool);
+          base_node = MAYBE_ALLOC(base_node, result_pool);
         break;
 
       case svn_wc_schedule_add:
-        working_node = MAYBE_ALLOC(working_node, scratch_pool);
+        working_node = MAYBE_ALLOC(working_node, result_pool);
         break;
 
       case svn_wc_schedule_delete:
-        working_node = MAYBE_ALLOC(working_node, scratch_pool);
+        working_node = MAYBE_ALLOC(working_node, result_pool);
         /* If the entry is part of a REPLACED (not COPIED) subtree,
            then it needs a BASE node. */
-       if (! (entry->copied
-               || (this_dir->copied
-                   && (this_dir->schedule == svn_wc_schedule_add ||
-                       this_dir->schedule == svn_wc_schedule_delete ||
-                       this_dir->schedule == svn_wc_schedule_replace))))
-          base_node = MAYBE_ALLOC(base_node, scratch_pool);
+        if (parent_node->base
+            && (! (entry->copied
+                   || (this_dir->copied
+                       && (this_dir->schedule == svn_wc_schedule_add ||
+                           this_dir->schedule == svn_wc_schedule_delete ||
+                           this_dir->schedule == svn_wc_schedule_replace)))))
+          base_node = MAYBE_ALLOC(base_node, result_pool);
         break;
 
       case svn_wc_schedule_replace:
-        working_node = MAYBE_ALLOC(working_node, scratch_pool);
-        base_node = MAYBE_ALLOC(base_node, scratch_pool);
+        working_node = MAYBE_ALLOC(working_node, result_pool);
+        if (parent_node->base)
+          base_node = MAYBE_ALLOC(base_node, result_pool);
         break;
     }
 
@@ -1903,21 +1866,21 @@ write_entry(svn_wc__db_t *db,
      BASE node to indicate the not-present node.  */
   if (entry->deleted)
     {
-      base_node = MAYBE_ALLOC(base_node, scratch_pool);
+      base_node = MAYBE_ALLOC(base_node, result_pool);
     }
 
   if (entry->copied)
     {
       /* Make sure we get a WORKING_NODE inserted. The copyfrom information
          will occur here or on a parent, as appropriate.  */
-      working_node = MAYBE_ALLOC(working_node, scratch_pool);
+      working_node = MAYBE_ALLOC(working_node, result_pool);
 
       if (entry->copyfrom_url)
         {
           const char *relative_url;
 
           working_node->copyfrom_repos_id = repos_id;
-          relative_url = svn_uri_is_child(repos_root, entry->copyfrom_url,
+          relative_url = svn_uri_is_child(this_dir->repos, entry->copyfrom_url,
                                           NULL);
           if (relative_url == NULL)
             working_node->copyfrom_repos_path = "";
@@ -1925,60 +1888,31 @@ write_entry(svn_wc__db_t *db,
             {
               /* copyfrom_repos_path is NOT a URI. decode into repos path.  */
               working_node->copyfrom_repos_path =
-                svn_path_uri_decode(relative_url, scratch_pool);
+                svn_path_uri_decode(relative_url, result_pool);
             }
           working_node->copyfrom_revnum = entry->copyfrom_rev;
+#ifdef SVN_WC__OP_DEPTH
+          working_node->op_depth
+            = svn_wc__db_op_depth_for_upgrade(local_relpath);
+#else
+          working_node->op_depth = 2; /* ### temporary op_depth */
+#endif
         }
-      else
+      else if (parent_node->work && parent_node->work->copyfrom_repos_path)
         {
-          const char *parent_abspath = svn_dirent_dirname(entry_abspath,
-                                                          scratch_pool);
-          const char *op_root_abspath;
-          const char *original_repos_relpath;
-          svn_revnum_t original_revision;
-          svn_error_t *err;
-
-          /* The parent will *always* have info in the WORKING tree, since
-             we've been designated as COPIED but do not have our own
-             COPYFROM information. Therefore, our parent or a more distant
-             ancestor has that information. Grab the data.  */
-          err = svn_wc__db_scan_addition(
-                    NULL,
-                    &op_root_abspath,
-                    NULL, NULL, NULL,
-                    &original_repos_relpath, NULL, NULL, &original_revision,
-                    db,
-                    parent_abspath,
-                    scratch_pool, scratch_pool);
-
-          /* We could be reading the entries while in a transitional state
-             during an add/copy operation. The scan_addition *does* throw
-             errors sometimes. So clear anything that may come out of it,
-             and perform the copyfrom construction only when it looks like
-             we have a good/real set of return values.  */
-          svn_error_clear(err);
-
-          /* We may have been copied from a mixed-rev working copy. We need
-             to simulate additional copies around revision changes. The old
-             code could separately store the revision, but NG needs to create
-             copies at each change.  */
-          if (err == NULL
-              && op_root_abspath != NULL
-              && original_repos_relpath != NULL
-              && SVN_IS_VALID_REVNUM(original_revision)
-              /* above is valid result testing. below is the key test.  */
-              && original_revision != entry->revision)
-            {
-              const char *relpath_to_entry = svn_dirent_is_child(
-                op_root_abspath, entry_abspath, NULL);
-              const char *new_copyfrom_relpath = svn_relpath_join(
-                original_repos_relpath, relpath_to_entry, scratch_pool);
-
-              working_node->copyfrom_repos_id = repos_id;
-              working_node->copyfrom_repos_path = new_copyfrom_relpath;
-              working_node->copyfrom_revnum = entry->revision;
-            }
+          working_node->copyfrom_repos_id = repos_id;
+          working_node->copyfrom_repos_path
+            = svn_relpath_join(parent_node->work->copyfrom_repos_path,
+                               svn_relpath_basename(local_relpath, NULL),
+                               result_pool);
+          working_node->copyfrom_revnum = parent_node->work->copyfrom_revnum;
+          working_node->op_depth = parent_node->work->op_depth;
         }
+      else
+        return svn_error_createf(SVN_ERR_ENTRY_MISSING_URL, NULL,
+                                 _("No copyfrom URL for '%s'"),
+                                 svn_dirent_local_style(local_relpath,
+                                                        scratch_pool));
     }
 
   if (entry->keep_local)
@@ -2025,9 +1959,10 @@ write_entry(svn_wc__db_t *db,
 
   if (entry->file_external_path != NULL)
     {
-      base_node = MAYBE_ALLOC(base_node, scratch_pool);
+      base_node = MAYBE_ALLOC(base_node, result_pool);
     }
 
+
   /* Insert the base node. */
   if (base_node)
     {
@@ -2083,16 +2018,16 @@ write_entry(svn_wc__db_t *db,
         base_node->checksum = NULL;
       else
         SVN_ERR(svn_checksum_parse_hex(&base_node->checksum, svn_checksum_md5,
-                                       entry->checksum, scratch_pool));
+                                       entry->checksum, result_pool));
 
-      if (repos_root)
+      if (this_dir->repos)
         {
           base_node->repos_id = repos_id;
 
           /* repos_relpath is NOT a URI. decode as appropriate.  */
           if (entry->url != NULL)
             {
-              const char *relative_url = svn_uri_is_child(repos_root,
+              const char *relative_url = svn_uri_is_child(this_dir->repos,
                                                           entry->url,
                                                           scratch_pool);
 
@@ -2100,11 +2035,11 @@ write_entry(svn_wc__db_t *db,
                 base_node->repos_relpath = "";
               else
                 base_node->repos_relpath = svn_path_uri_decode(relative_url,
-                                                               scratch_pool);
+                                                               result_pool);
             }
           else
             {
-              const char *base_path = svn_uri_is_child(repos_root,
+              const char *base_path = svn_uri_is_child(this_dir->repos,
                                                        this_dir->url,
                                                        scratch_pool);
               if (base_path == NULL)
@@ -2113,7 +2048,7 @@ write_entry(svn_wc__db_t *db,
                 base_node->repos_relpath =
                   svn_dirent_join(svn_path_uri_decode(base_path, scratch_pool),
                                   entry->name,
-                                  scratch_pool);
+                                  result_pool);
             }
         }
 
@@ -2157,24 +2092,13 @@ write_entry(svn_wc__db_t *db,
                                                   &entry->file_external_rev,
                                                   scratch_pool));
 
-#ifndef SVN_WC__NODES_ONLY
           SVN_ERR(svn_sqlite__get_statement(&stmt, sdb,
                                             STMT_UPDATE_FILE_EXTERNAL));
           SVN_ERR(svn_sqlite__bindf(stmt, "iss",
-                                    (apr_uint64_t)1 /* wc_id */,
+                                    (apr_int64_t)1 /* wc_id */,
                                     entry->name,
                                     str));
           SVN_ERR(svn_sqlite__step_done(stmt));
-#endif
-#ifdef SVN_WC__NODES
-          SVN_ERR(svn_sqlite__get_statement(&stmt, sdb,
-                                            STMT_UPDATE_FILE_EXTERNAL_1));
-          SVN_ERR(svn_sqlite__bindf(stmt, "iss",
-                                    (apr_uint64_t)1 /* wc_id */,
-                                    entry->name,
-                                    str));
-          SVN_ERR(svn_sqlite__step_done(stmt));
-#endif
         }
     }
 
@@ -2201,7 +2125,7 @@ write_entry(svn_wc__db_t *db,
       else
         SVN_ERR(svn_checksum_parse_hex(&working_node->checksum,
                                        svn_checksum_md5,
-                                       entry->checksum, scratch_pool));
+                                       entry->checksum, result_pool));
 
       /* All subdirs start of incomplete, and stop being incomplete
          when the entries file in the subdir is upgraded. */
@@ -2227,7 +2151,8 @@ write_entry(svn_wc__db_t *db,
               /* If the entry is part of a COPIED (not REPLACED) subtree,
                  then the deletion is referring to the WORKING node, not
                  the BASE node. */
-              if (entry->copied
+              if (!base_node
+                  || entry->copied
                   || (this_dir->copied
                       && this_dir->schedule == svn_wc_schedule_add))
                 working_node->presence = svn_wc__db_status_not_present;
@@ -2262,11 +2187,24 @@ write_entry(svn_wc__db_t *db,
       working_node->changed_date = entry->cmt_date;
       working_node->changed_author = entry->cmt_author;
 
+      if (!entry->copied)
+        {
+          if (parent_node->work)
+            working_node->op_depth = parent_node->work->op_depth;
+          else
+#ifdef SVN_WC__OP_DEPTH
+            working_node->op_depth
+              = svn_wc__db_op_depth_for_upgrade(local_relpath);
+#else
+            working_node->op_depth = 2; /* ### temporary op_depth */
+#endif
+        }
+
       SVN_ERR(insert_working_node(sdb, working_node, scratch_pool));
     }
 
   /* Insert the actual node. */
-  if (actual_node || always_create_actual)
+  if (actual_node)
     {
       actual_node = MAYBE_ALLOC(actual_node, scratch_pool);
 
@@ -2277,6 +2215,13 @@ write_entry(svn_wc__db_t *db,
       SVN_ERR(insert_actual_node(sdb, actual_node, scratch_pool));
     }
 
+  if (entry_node)
+    {
+      *entry_node = apr_palloc(result_pool, sizeof(*entry_node));
+      (*entry_node)->base = base_node;
+      (*entry_node)->work = working_node;
+    }
+
   return SVN_NO_ERROR;
 }
 
@@ -2288,6 +2233,9 @@ struct entries_write_baton
   const char *dir_abspath;
   const char *new_root_abspath;
   apr_hash_t *entries;
+  struct write_baton *parent_node;
+  struct write_baton *dir_node;
+  apr_pool_t *result_pool;
 };
 
 /* Writes entries inside a sqlite transaction
@@ -2304,7 +2252,7 @@ entries_write_new_cb(void *baton,
   const svn_wc_entry_t *this_dir;
   apr_hash_index_t *hi;
   apr_pool_t *iterpool = svn_pool_create(scratch_pool);
-  const char *repos_root, *old_root_abspath, *dir_relpath;
+  const char *old_root_abspath, *dir_relpath;
 
   /* Get a copy of the "this dir" entry for comparison purposes. */
   this_dir = apr_hash_get(ewb->entries, SVN_WC_ENTRY_THIS_DIR,
@@ -2316,8 +2264,6 @@ entries_write_new_cb(void *baton,
                              _("No default entry in directory '%s'"),
                              svn_dirent_local_style(dir_abspath,
                                                     iterpool));
-  repos_root = this_dir->repos;
-
   old_root_abspath = svn_dirent_get_longest_ancestor(dir_abspath,
                                                      new_root_abspath,
                                                      scratch_pool);
@@ -2327,12 +2273,11 @@ entries_write_new_cb(void *baton,
   dir_relpath = svn_dirent_skip_ancestor(old_root_abspath, dir_abspath);
 
   /* Write out "this dir" */
-  SVN_ERR(write_entry(db, sdb, ewb->wc_id, ewb->repos_id, repos_root,
-                      this_dir,
-                      dir_relpath,
+  SVN_ERR(write_entry(&ewb->dir_node, ewb->parent_node, db, sdb,
+                      ewb->wc_id, ewb->repos_id, this_dir, dir_relpath,
                       svn_dirent_join(new_root_abspath, dir_relpath,
                                       scratch_pool),
-                      this_dir, FALSE, FALSE, iterpool));
+                      this_dir, FALSE, ewb->result_pool, iterpool));
 
   for (hi = apr_hash_first(scratch_pool, ewb->entries); hi;
        hi = apr_hash_next(hi))
@@ -2351,14 +2296,12 @@ entries_write_new_cb(void *baton,
          use this function for upgrading old working copies. */
       child_abspath = svn_dirent_join(dir_abspath, name, iterpool);
       child_relpath = svn_dirent_skip_ancestor(old_root_abspath, child_abspath);
-      SVN_ERR(write_entry(db, sdb, ewb->wc_id, ewb->repos_id, repos_root,
-                          this_entry,
-                          child_relpath,
+      SVN_ERR(write_entry(NULL, ewb->dir_node, db, sdb,
+                          ewb->wc_id, ewb->repos_id,
+                          this_entry, child_relpath,
                           svn_dirent_join(new_root_abspath, child_relpath,
                                           scratch_pool),
-                          this_dir,
-                          FALSE, TRUE,
-                          iterpool));
+                          this_dir, TRUE, iterpool, iterpool));
     }
 
   svn_pool_destroy(iterpool);
@@ -2367,13 +2310,16 @@ entries_write_new_cb(void *baton,
 
 
 svn_error_t *
-svn_wc__write_upgraded_entries(svn_wc__db_t *db,
+svn_wc__write_upgraded_entries(void **dir_baton,
+                               void *parent_baton,
+                               svn_wc__db_t *db,
                                svn_sqlite__db_t *sdb,
                                apr_int64_t repos_id,
                                apr_int64_t wc_id,
                                const char *dir_abspath,
                                const char *new_root_abspath,
                                apr_hash_t *entries,
+                               apr_pool_t *result_pool,
                                apr_pool_t *scratch_pool)
 {
   struct entries_write_baton ewb;
@@ -2384,12 +2330,17 @@ svn_wc__write_upgraded_entries(svn_wc__d
   ewb.dir_abspath = dir_abspath;
   ewb.new_root_abspath = new_root_abspath;
   ewb.entries = entries;
+  ewb.parent_node = parent_baton;
+  ewb.result_pool = result_pool;
 
   /* Run this operation in a transaction to speed up SQLite.
      See http://www.sqlite.org/faq.html#q19 for more details */
-  return svn_error_return(
-      svn_sqlite__with_transaction(sdb, entries_write_new_cb, &ewb,
-                                   scratch_pool));
+  SVN_ERR(svn_sqlite__with_transaction(sdb, entries_write_new_cb, &ewb,
+                                       scratch_pool));
+
+  *dir_baton = ewb.dir_node;
+
+  return SVN_NO_ERROR;
 }
 
 

Modified: subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/entries.h
URL: http://svn.apache.org/viewvc/subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/entries.h?rev=1041580&r1=1041579&r2=1041580&view=diff
==============================================================================
--- subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/entries.h (original)
+++ subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/entries.h Thu Dec  2 20:55:08 2010
@@ -87,15 +87,21 @@ svn_wc__read_entries_old(apr_hash_t **en
                          apr_pool_t *result_pool,
                          apr_pool_t *scratch_pool);
 
-/* For internal use by upgrade.c to write entries in the wc-ng format.  */
+/* For internal use by upgrade.c to write entries in the wc-ng format.
+   Return in DIR_BATON the baton to be passed as PARENT_BATON when
+   upgrading child directories. Pass a NULL PARENT_BATON when upgrading
+   the root directory. */
 svn_error_t *
-svn_wc__write_upgraded_entries(svn_wc__db_t *db,
+svn_wc__write_upgraded_entries(void **dir_baton,
+                               void *parent_baton,
+                               svn_wc__db_t *db,
                                svn_sqlite__db_t *sdb,
                                apr_int64_t repos_id,
                                apr_int64_t wc_id,
                                const char *dir_abspath,
                                const char *new_root_abspath,
                                apr_hash_t *entries,
+                               apr_pool_t *result_pool,
                                apr_pool_t *scratch_pool);
 
 /* Parse a file external specification in the NULL terminated STR and

Modified: subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/node.c
URL: http://svn.apache.org/viewvc/subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/node.c?rev=1041580&r1=1041579&r2=1041580&view=diff
==============================================================================
--- subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/node.c (original)
+++ subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/node.c Thu Dec  2 20:55:08 2010
@@ -1122,14 +1122,22 @@ svn_wc__node_get_lock_info(const char **
                            apr_pool_t *scratch_pool)
 {
   svn_wc__db_lock_t *lock;
+  svn_error_t *err;
 
-  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, NULL, NULL,
-                               NULL, &lock,
-                               wc_ctx->db, local_abspath,
-                               result_pool, scratch_pool));
+  err = svn_wc__db_base_get_info(NULL, NULL, NULL, NULL, NULL, NULL, NULL,
+                                 NULL, NULL, NULL, NULL, NULL, NULL, NULL,
+                                 &lock,
+                                 wc_ctx->db, local_abspath,
+                                 result_pool, scratch_pool);
+
+  if (err)
+    {
+      if (err->apr_err != SVN_ERR_WC_PATH_NOT_FOUND)
+        return svn_error_return(err);
+
+      svn_error_clear(err);
+      lock = NULL;
+    }
   if (lock_token)
     *lock_token = lock ? lock->token : NULL;
   if (lock_owner)

Modified: subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/props.c
URL: http://svn.apache.org/viewvc/subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/props.c?rev=1041580&r1=1041579&r2=1041580&view=diff
==============================================================================
--- subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/props.c (original)
+++ subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/props.c Thu Dec  2 20:55:08 2010
@@ -139,30 +139,9 @@ svn_wc__get_prejfile_abspath(const char 
 static svn_error_t *
 immediate_install_props(svn_wc__db_t *db,
                         const char *local_abspath,
-                        svn_wc__db_kind_t kind,
                         apr_hash_t *working_props,
                         apr_pool_t *scratch_pool)
 {
-  apr_hash_t *base_props;
-
-  /* ### no pristines should be okay.  */
-  SVN_ERR_W(svn_wc__db_read_pristine_props(&base_props, db, local_abspath,
-                                           scratch_pool, scratch_pool),
-            _("Failed to load pristine properties"));
-
-  /* Check if the props are modified. If no changes, then wipe out
-     the ACTUAL props. No pristines defined means that any ACTUAL
-     props are okay, so go ahead and set them.  */
-  if (base_props != NULL)
-    {
-      apr_array_header_t *prop_diffs;
-
-      SVN_ERR(svn_prop_diffs(&prop_diffs, working_props, base_props,
-                             scratch_pool));
-      if (prop_diffs->nelts == 0)
-        working_props = NULL;
-    }
-
   SVN_ERR(svn_wc__db_op_set_props(db, local_abspath,
                                   working_props,
                                   NULL /* conflict */,
@@ -350,7 +329,6 @@ svn_wc__perform_props_merge(svn_wc_notif
       {
         svn_wc__db_status_t status;
         svn_boolean_t have_base;
-        apr_array_header_t *prop_diffs;
 
         SVN_ERR(svn_wc__db_read_info(&status, NULL, NULL, NULL, NULL, NULL,
                                      NULL, NULL, NULL, NULL, NULL, NULL, NULL,
@@ -365,41 +343,18 @@ svn_wc__perform_props_merge(svn_wc_notif
           SVN_ERR(svn_wc__db_temp_base_set_props(db, local_abspath,
                                                  new_base_props, pool));
 
-        /* Check if the props are modified. */
-        SVN_ERR(svn_prop_diffs(&prop_diffs, actual_props, new_base_props, pool));
-
-        /* Save the actual properties file if it differs from base. */
-        if (prop_diffs->nelts == 0)
-          SVN_ERR(svn_wc__db_op_set_props(db, local_abspath, NULL, NULL, NULL,
-                                          pool));
-        else
-          SVN_ERR(svn_wc__db_op_set_props(db, local_abspath, actual_props,
-                                          NULL, NULL, pool));
+        SVN_ERR(svn_wc__db_op_set_props(db, local_abspath, actual_props,
+                                        NULL, NULL, pool));
       }
 #else
       if (base_merge)
         return svn_error_create(SVN_ERR_UNSUPPORTED_FEATURE, NULL,
                                 U_("base_merge=TRUE is no longer supported"));
 
-      {
-        apr_array_header_t *prop_diffs;
-
-        SVN_ERR(svn_prop_diffs(&prop_diffs, new_actual_props, new_base_props,
-                               pool));
-
-        /* Save the actual properties file if it differs from base. */
-        if (prop_diffs->nelts == 0)
-          new_actual_props = NULL; /* Remove actual properties*/
-
-        /* For the old school: write the properties into the "working"
-           (aka ACTUAL) location. Note that PROPS may be NULL, indicating
-           a removal of the props file.  */
-
-        SVN_ERR(svn_wc__db_op_set_props(db, local_abspath, new_actual_props,
-                                        NULL /* conflict */,
-                                        NULL /* work_item */,
-                                        pool));
-      }
+      SVN_ERR(svn_wc__db_op_set_props(db, local_abspath, new_actual_props,
+                                      NULL /* conflict */,
+                                      NULL /* work_item */,
+                                      pool));
 #endif
 
       SVN_ERR(svn_wc__wq_run(db, local_abspath,
@@ -1622,7 +1577,8 @@ svn_wc__merge_props(svn_wc_notify_state_
         SVN_ERR(svn_wc__wq_tmp_build_set_property_conflict_marker(
                                           &work_item,
                                           db, local_abspath,
-                                          svn_dirent_basename(reject_path, NULL),
+                                          svn_dirent_basename(reject_path,
+                                                              NULL),
                                           scratch_pool, scratch_pool));
 
         SVN_ERR(svn_wc__db_wq_add(db, local_abspath, work_item, scratch_pool));
@@ -2185,7 +2141,7 @@ svn_wc__internal_propset(svn_wc__db_t *d
 
   /* Drop it right onto the disk. We don't need loggy since we aren't
      coordinating this change with anything else.  */
-  SVN_ERR(immediate_install_props(db, local_abspath, kind, prophash,
+  SVN_ERR(immediate_install_props(db, local_abspath, prophash,
                                   scratch_pool));
 
   if (notify_func)

Modified: subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/relocate.c
URL: http://svn.apache.org/viewvc/subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/relocate.c?rev=1041580&r1=1041579&r2=1041580&view=diff
==============================================================================
--- subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/relocate.c (original)
+++ subversion/branches/gpg-agent-password-store/subversion/libsvn_wc/relocate.c Thu Dec  2 20:55:08 2010
@@ -82,9 +82,9 @@ svn_wc_relocate4(svn_wc_context_t *wc_ct
 {
   svn_wc__db_kind_t kind;
   const char *repos_relpath;
-  const char *old_repos_root;
-  const char *old_url;
-  const char *new_repos_root;
+  const char *old_repos_root, *old_url;
+  const char *new_repos_root, *new_url;
+  int from_len, old_url_len;
   const char *uuid;
   svn_boolean_t is_wc_root;
 
@@ -129,16 +129,28 @@ svn_wc_relocate4(svn_wc_context_t *wc_ct
                             _("Cannot relocate a single file"));
 
   old_url = svn_uri_join(old_repos_root, repos_relpath, scratch_pool);
-  if (strcmp(old_url, from) != 0)
-    return svn_error_create(SVN_ERR_WC_INVALID_RELOCATION, NULL,
-                            _("Given source URL invalid"));
+  old_url_len = strlen(old_url);
+  from_len = strlen(from);
+  if ((from_len > old_url_len) || (strncmp(old_url, from, strlen(from)) != 0))
+    return svn_error_createf(SVN_ERR_WC_INVALID_RELOCATION, NULL,
+                             _("Invalid source URL prefix: '%s' (does not "
+                               "overlap target's URL '%s')"),
+                             from, old_url);
+  
+  if (old_url_len == from_len)
+    new_url = to;
+  else
+    new_url = apr_pstrcat(scratch_pool, to, old_url + from_len, NULL);
+  if (! svn_path_is_url(new_url))
+    return svn_error_createf(SVN_ERR_WC_INVALID_RELOCATION, NULL,
+                             _("Invalid destination URL: '%s'"), new_url);
 
-  new_repos_root = uri_remove_components(to, repos_relpath, scratch_pool);
+  new_repos_root = uri_remove_components(new_url, repos_relpath, scratch_pool);
   if (!new_repos_root)
     return svn_error_createf(SVN_ERR_WC_INVALID_RELOCATION, NULL,
-                             _("Given destination URL invalid: '%s'"), to);
+                             _("Invalid destination URL: '%s'"), new_url);
 
-  SVN_ERR(validator(validator_baton, uuid, to, new_repos_root, scratch_pool));
+  SVN_ERR(validator(validator_baton, uuid, new_url, new_repos_root, scratch_pool));
 
   return svn_error_return(svn_wc__db_global_relocate(wc_ctx->db, local_abspath,
                                                      new_repos_root,



Mime
View raw message