svn_error_t * svn_wc_copy3(svn_wc_context_t *wc_ctx, const char *src_abspath, const char *dst_abspath, svn_boolean_t metadata_only, svn_cancel_func_t cancel_func, void *cancel_baton, svn_wc_notify_func2_t notify_func, void *notify_baton, apr_pool_t *scratch_pool) { /* Verify that we have the required write lock. */ SVN_ERR(svn_wc__write_check(wc_ctx->db, svn_dirent_dirname(dst_abspath, scratch_pool), scratch_pool)); return svn_error_trace(copy_or_move(NULL, wc_ctx, src_abspath, dst_abspath, metadata_only, FALSE /* is_move */, TRUE /* allow_mixed_revisions */, cancel_func, cancel_baton, notify_func, notify_baton, scratch_pool)); }
int ne_move(ne_session *sess, int overwrite, const char *src, const char *dest) { return copy_or_move(sess, 1, overwrite, 0, src, dest); }
int ne_copy(ne_session *sess, int overwrite, int depth, const char *src, const char *dest) { return copy_or_move(sess, 0, overwrite, depth, src, dest); }
svn_error_t * svn_wc__move2(svn_wc_context_t *wc_ctx, const char *src_abspath, const char *dst_abspath, svn_boolean_t metadata_only, svn_boolean_t allow_mixed_revisions, svn_cancel_func_t cancel_func, void *cancel_baton, svn_wc_notify_func2_t notify_func, void *notify_baton, apr_pool_t *scratch_pool) { svn_wc__db_t *db = wc_ctx->db; svn_boolean_t move_degraded_to_copy = FALSE; svn_node_kind_t kind; svn_boolean_t conflicted; /* Verify that we have the required write locks. */ SVN_ERR(svn_wc__write_check(wc_ctx->db, svn_dirent_dirname(src_abspath, scratch_pool), scratch_pool)); SVN_ERR(svn_wc__write_check(wc_ctx->db, svn_dirent_dirname(dst_abspath, scratch_pool), scratch_pool)); SVN_ERR(copy_or_move(&move_degraded_to_copy, wc_ctx, src_abspath, dst_abspath, TRUE /* metadata_only */, TRUE /* is_move */, allow_mixed_revisions, cancel_func, cancel_baton, notify_func, notify_baton, scratch_pool)); /* An interrupt at this point will leave the new copy marked as moved-here but the source has not yet been deleted or marked as moved-to. */ /* Should we be using a workqueue for this move? It's not clear. What should happen if the copy above is interrupted? The user may want to abort the move and a workqueue might interfere with that. BH: On Windows it is not unlikely to encounter an access denied on this line. Installing the move in the workqueue via the copy_or_move might make it hard to recover from that situation, while the DB is still in a valid state. So be careful when switching this over to the workqueue. */ if (!metadata_only) SVN_ERR(svn_io_file_rename(src_abspath, dst_abspath, scratch_pool)); 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, &conflicted, NULL, NULL, NULL, NULL, NULL, NULL, db, src_abspath, scratch_pool, scratch_pool)); if (kind == svn_node_dir) SVN_ERR(remove_all_conflict_markers(db, src_abspath, dst_abspath, scratch_pool)); if (conflicted) SVN_ERR(remove_node_conflict_markers(db, src_abspath, dst_abspath, scratch_pool)); SVN_ERR(svn_wc__db_op_delete(db, src_abspath, move_degraded_to_copy ? NULL : dst_abspath, TRUE /* delete_dir_externals */, NULL /* conflict */, NULL /* work_items */, cancel_func, cancel_baton, notify_func, notify_baton, scratch_pool)); return SVN_NO_ERROR; }