[svn.haxx.se] · SVN Dev · SVN Users · SVN Org · TSVN Dev · TSVN Users · Subclipse Dev · Subclipse Users · this month's index

Re: [PATCH] notification callbacks for network data transfers (V6)

From: Stefan Küng <tortoisesvn_at_gmail.com>
Date: 2005-08-28 13:28:40 CEST

Branko ÄŒibej wrote:

> You don't have to rev the svn_ra__vtable_t::open callback. The
> svn_ra__vtable_t type is private to libsvn_ra*, so you can change the
> signature of the open() callback instead of revving it. It's not a
> public API. :)
>
> Otherwise, it looks fine. Please change the svn_ra__vtable_t thing and
> update the log message, and I'll test and commit.

Patch attached.

Stefan

-- 
        ___
   oo  // \\      "De Chelonian Mobile"
  (_,\/ \_/ \     TortoiseSVN
    \ \_/_\_/>    The coolest Interface to (Sub)Version Control
    /_/   \_\     http://tortoisesvn.tigris.org

[[[
Implement a reduced version of issue #901 for DAV connections.

Patch by: Stefan Küng <tortoisesvn@gmail.com>
          brane

* subversion/include/svn_client.h: Explicitly include svn_ra.h.
  (svn_client_ctx_t): Extend the client context structure with the
   callback function and baton.
* subversion/include/svn_ra.h
  (svn_ra_progress_notify_func_t): New. Notification callback function type.
  (svn_ra_callbacks_t): Deprecate the structure.
  (svn_ra_callbacks2_t): Same as svn_ra_callbacks_t, but with new
   progress notification callback and baton.
* subversion/libsvn_ra/ra_loader.h
  (svn_ra__vtable_t): Use the new open2() function instead of the
  deprecated open() function.
* subversion/libsvn_ra/ra_loader.c
  (svn_ra_open): Deprecate function, calls svn_ra_open2().
  (svn_ra_open2): New function which takes an svn_ra_callbacks2_t
   instead of an svn_ra_callback_t.
* subversion/libsvn_client/ra.c (svn_client__open_ra_session_internal):
   Set the progress notification callback and baton.
* subversion/libsvn_ra_dav/session.c
  (ra_dav_neonprogress): New function. The callback function neon calls
   during network data transfers.
  (svn_ra_dav__open): Set the neon callback function for the session.
* subversion/libsvn_ra_dav/ra_dav.h
  (svn_ra_dav__session_t): Use new svn_ra_callbacks2_t.
* subversion/libsvn_ra/wrapper_template.h
  (compat_open): Pass a svn_ra_callbacks2_t to the open() function.
* subversion/libsvn_ra_local/ra_local.h (svn_ra_local__session_baton_t)
  subversion/libsvn_ra_local/ra_plugin.c (svn_ra_local__open)
  subversion/libsvn_ra_svn/client.c (ra_svn_open):
  Use new svn_ra_callbacks2_t.
* subversion/libsvn_client/copy.c (repos_to_repos_copy): Correct comment.
]]]
Index: subversion/libsvn_ra/wrapper_template.h
===================================================================
--- subversion/libsvn_ra/wrapper_template.h (Revision 15946)
+++ subversion/libsvn_ra/wrapper_template.h (Arbeitskopie)
@@ -45,9 +45,20 @@
                                  apr_pool_t *pool)
 {
   svn_ra_session_t *sess = apr_pcalloc (pool, sizeof (svn_ra_session_t));
+ svn_ra_callbacks2_t callbacks2;
   sess->vtable = &VTBL;
   sess->pool = pool;
- SVN_ERR (VTBL.open (sess, repos_URL, callbacks, callback_baton,
+
+ callbacks2.open_tmp_file = callbacks->open_tmp_file;
+ callbacks2.auth_baton = callbacks->auth_baton;
+ callbacks2.get_wc_prop = callbacks->get_wc_prop;
+ callbacks2.set_wc_prop = callbacks->set_wc_prop;
+ callbacks2.push_wc_prop = callbacks->push_wc_prop;
+ callbacks2.invalidate_wc_props = callbacks->invalidate_wc_props;
+ callbacks2.progress_func = NULL;
+ callbacks2.progress_baton = NULL;
+
+ SVN_ERR (VTBL.open (sess, repos_URL, &callbacks2, callback_baton,
                       config, pool));
   *session_baton = sess;
   return SVN_NO_ERROR;
Index: subversion/libsvn_ra/ra_loader.c
===================================================================
--- subversion/libsvn_ra/ra_loader.c (Revision 15946)
+++ subversion/libsvn_ra/ra_loader.c (Arbeitskopie)
@@ -230,12 +230,12 @@
   return SVN_NO_ERROR;
 }
 
-svn_error_t *svn_ra_open (svn_ra_session_t **session_p,
- const char *repos_URL,
- const svn_ra_callbacks_t *callbacks,
- void *callback_baton,
- apr_hash_t *config,
- apr_pool_t *pool)
+svn_error_t *svn_ra_open2 (svn_ra_session_t **session_p,
+ const char *repos_URL,
+ const svn_ra_callbacks2_t *callbacks,
+ void *callback_baton,
+ apr_hash_t *config,
+ apr_pool_t *pool)
 {
   svn_ra_session_t *session;
   const struct ra_lib_defn *defn;
@@ -281,6 +281,29 @@
   return SVN_NO_ERROR;
 }
 
+svn_error_t *svn_ra_open (svn_ra_session_t **session_p,
+ const char *repos_URL,
+ const svn_ra_callbacks_t *callbacks,
+ void *callback_baton,
+ apr_hash_t *config,
+ apr_pool_t *pool)
+{
+ /* Ddeprecated function. Copy the contents of the svn_ra_callbacks_t
+ to a new svn_ra_callbacks2_t and call svn_ra_open2(). */
+ svn_ra_callbacks2_t callbacks2;
+ callbacks2.open_tmp_file = callbacks->open_tmp_file;
+ callbacks2.auth_baton = callbacks->auth_baton;
+ callbacks2.get_wc_prop = callbacks->get_wc_prop;
+ callbacks2.set_wc_prop = callbacks->set_wc_prop;
+ callbacks2.push_wc_prop = callbacks->push_wc_prop;
+ callbacks2.invalidate_wc_props = callbacks->invalidate_wc_props;
+ callbacks2.progress_func = NULL;
+ callbacks2.progress_baton = NULL;
+ return svn_ra_open2 (session_p, repos_URL,
+ &callbacks2, callback_baton,
+ config, pool);
+}
+
 svn_error_t *svn_ra_get_latest_revnum (svn_ra_session_t *session,
                                        svn_revnum_t *latest_revnum,
                                        apr_pool_t *pool)
Index: subversion/libsvn_ra/ra_loader.h
===================================================================
--- subversion/libsvn_ra/ra_loader.h (Revision 15946)
+++ subversion/libsvn_ra/ra_loader.h (Arbeitskopie)
@@ -50,7 +50,7 @@
      time this is called. SESSION->priv may be set by this function. */
   svn_error_t *(*open) (svn_ra_session_t *session,
                         const char *repos_URL,
- const svn_ra_callbacks_t *callbacks,
+ const svn_ra_callbacks2_t *callbacks,
                         void *callback_baton,
                         apr_hash_t *config,
                         apr_pool_t *pool);
Index: subversion/include/svn_client.h
===================================================================
--- subversion/include/svn_client.h (Revision 15946)
+++ subversion/include/svn_client.h (Arbeitskopie)
@@ -40,6 +40,7 @@
 #include "svn_error.h"
 #include "svn_opt.h"
 #include "svn_version.h"
+#include "svn_ra.h"
 
 
 #ifdef __cplusplus
@@ -533,6 +534,14 @@
   /** callback baton for log_msg_func2
    * @since New in 1.3. */
   void *log_msg_baton2;
+
+ /** Notification callback for network progress information.
+ * @since New in 1.3. */
+ svn_ra_progress_notify_func_t progress_func;
+
+ /** Callback baton for progress_func.
+ * @since New in 1.3. */
+ void *progress_baton;
 } svn_client_ctx_t;
 
 
@@ -2374,7 +2383,7 @@
  *
  * @since New in 1.3.
  *
- * @note This function is similar to svn_ra_open(), but the caller avoids
+ * @note This function is similar to svn_ra_open2(), but the caller avoids
  * having to providing its own callback functions.
  */
 svn_error_t *
Index: subversion/include/svn_ra.h
===================================================================
--- subversion/include/svn_ra.h (Revision 15946)
+++ subversion/include/svn_ra.h (Arbeitskopie)
@@ -169,6 +169,22 @@
                                                 svn_error_t *ra_err,
                                                 apr_pool_t *pool);
 
+/**
+ * Callback function type for progress notification.
+ *
+ * @a progress is the amount of bytes already transferred.
+ *
+ * @a total is the total amount of bytes to transfer or -1 if it's not
+ * known.
+ *
+ * @a baton is the callback baton. If not used, must be NULL.
+ *
+ * @since New in 1.3.
+ */
+typedef void (*svn_ra_progress_notify_func_t) (apr_off_t progress,
+ apr_off_t total,
+ void * baton);
+
 
 /**
  * The update Reporter.
@@ -308,7 +324,64 @@
  *
  * Each routine takes a @a callback_baton originally provided with the
  * vtable.
+ *
+ * @since New in 1.3.
  */
+typedef struct svn_ra_callbacks2_t
+{
+ /** Open a unique temporary file for writing in the working copy.
+ * This file will be automatically deleted when @a fp is closed.
+ */
+ svn_error_t *(*open_tmp_file) (apr_file_t **fp,
+ void *callback_baton,
+ apr_pool_t *pool);
+
+ /** An authentication baton, created by the application, which is
+ * capable of retrieving all known types of credentials.
+ */
+ svn_auth_baton_t *auth_baton;
+
+ /*** The following items may be set to NULL to disallow the RA layer
+ to perform the respective operations of the vtable functions.
+ Perhaps WC props are not defined or are in invalid for this
+ session, or perhaps the commit operation this RA session will
+ perform is a server-side only one that shouldn't do post-commit
+ processing on a working copy path. ***/
+
+ /** Fetch working copy properties.
+ *
+ *<pre> ### we might have a problem if the RA layer ever wants a property
+ * ### that corresponds to a different revision of the file than
+ * ### what is in the WC. we'll cross that bridge one day...</pre>
+ */
+ svn_ra_get_wc_prop_func_t get_wc_prop;
+
+ /** Immediately set new values for working copy properties. */
+ svn_ra_set_wc_prop_func_t set_wc_prop;
+
+ /** Schedule new values for working copy properties. */
+ svn_ra_push_wc_prop_func_t push_wc_prop;
+
+ /** Invalidate working copy properties. */
+ svn_ra_invalidate_wc_props_func_t invalidate_wc_props;
+
+ /** Notification callback used for progress information. */
+ svn_ra_progress_notify_func_t progress_func;
+
+ /** Notification callback baton, used with progress_func. */
+ void *progress_baton;
+} svn_ra_callbacks2_t;
+
+/** A collection of callbacks implemented by libsvn_client which allows
+ * an RA layer to "pull" information from the client application, or
+ * possibly store information. libsvn_client passes this vtable to
+ * @c RA->open().
+ *
+ * Each routine takes a @a callback_baton originally provided with the
+ * vtable.
+ *
+ * @deprecated Provided for backward compatibility with the 1.2 API.
+ */
 typedef struct svn_ra_callbacks_t
 {
   /** Open a unique temporary file for writing in the working copy.
@@ -380,7 +453,7 @@
  * representing this session in @a *session_p, allocated in @a pool.
  *
  * @a callbacks/@a callback_baton is a table of callbacks provided by the
- * client; see @c svn_ra_callbacks_t.
+ * client; see @c svn_ra_callbacks2_t.
  *
  * @a config is a hash mapping <tt>const char *</tt> keys to
  * @c svn_config_t * values. For example, the @c svn_config_t for the
@@ -391,7 +464,19 @@
  *
  * @see svn_client_open_ra_session().
  *
+ * @since New in 1.3.
+ */
+svn_error_t *svn_ra_open2 (svn_ra_session_t **session_p,
+ const char *repos_URL,
+ const svn_ra_callbacks2_t *callbacks,
+ void *callback_baton,
+ apr_hash_t *config,
+ apr_pool_t *pool);
+
+/**
+ * @see svn_ra_open2().
  * @since New in 1.2.
+ * @deprecated Provided for backward compatibility with the 1.2 API.
  */
 svn_error_t *svn_ra_open (svn_ra_session_t **session_p,
                           const char *repos_URL,
Index: subversion/libsvn_ra_local/ra_plugin.c
===================================================================
--- subversion/libsvn_ra_local/ra_plugin.c (Revision 15946)
+++ subversion/libsvn_ra_local/ra_plugin.c (Arbeitskopie)
@@ -261,7 +261,7 @@
 static svn_error_t *
 svn_ra_local__open (svn_ra_session_t *session,
                     const char *repos_URL,
- const svn_ra_callbacks_t *callbacks,
+ const svn_ra_callbacks2_t *callbacks,
                     void *callback_baton,
                     apr_hash_t *config,
                     apr_pool_t *pool)
Index: subversion/libsvn_ra_local/ra_local.h
===================================================================
--- subversion/libsvn_ra_local/ra_local.h (Revision 15946)
+++ subversion/libsvn_ra_local/ra_local.h (Arbeitskopie)
@@ -58,7 +58,7 @@
   const char *uuid;
 
   /* Callbacks/baton passed to svn_ra_open. */
- const svn_ra_callbacks_t *callbacks;
+ const svn_ra_callbacks2_t *callbacks;
   void *callback_baton;
 } svn_ra_local__session_baton_t;
 
Index: subversion/libsvn_client/ra.c
===================================================================
--- subversion/libsvn_client/ra.c (Revision 15946)
+++ subversion/libsvn_client/ra.c (Arbeitskopie)
@@ -270,7 +270,7 @@
                                       svn_client_ctx_t *ctx,
                                       apr_pool_t *pool)
 {
- svn_ra_callbacks_t *cbtable = apr_pcalloc (pool, sizeof(*cbtable));
+ svn_ra_callbacks2_t *cbtable = apr_pcalloc (pool, sizeof(*cbtable));
   svn_client__callback_baton_t *cb = apr_pcalloc (pool, sizeof(*cb));
   
   cbtable->open_tmp_file = use_admin ? open_admin_tmp_file : open_tmp_file;
@@ -279,6 +279,8 @@
   cbtable->push_wc_prop = commit_items ? push_wc_prop : NULL;
   cbtable->invalidate_wc_props = read_only_wc ? NULL : invalidate_wc_props;
   cbtable->auth_baton = ctx->auth_baton; /* new-style */
+ cbtable->progress_func = ctx->progress_func;
+ cbtable->progress_baton = ctx->progress_baton;
 
   cb->base_dir = base_dir;
   cb->base_access = base_access;
@@ -286,7 +288,8 @@
   cb->commit_items = commit_items;
   cb->ctx = ctx;
 
- SVN_ERR (svn_ra_open (ra_session, base_url, cbtable, cb, ctx->config, pool));
+ SVN_ERR (svn_ra_open2 (ra_session, base_url, cbtable, cb,
+ ctx->config, pool));
 
   return SVN_NO_ERROR;
 }
Index: subversion/libsvn_client/copy.c
===================================================================
--- subversion/libsvn_client/copy.c (Revision 15946)
+++ subversion/libsvn_client/copy.c (Arbeitskopie)
@@ -334,7 +334,7 @@
                                               ctx, pool);
 
   /* If the two URLs appear not to be in the same repository, then
- top_url will be empty and the call to svn_ra_open()
+ top_url will be empty and the call to svn_ra_open2()
      above will have failed. Below we check for that, and propagate a
      descriptive error back to the user.
    
Index: subversion/libsvn_ra_svn/client.c
===================================================================
--- subversion/libsvn_ra_svn/client.c (Revision 15946)
+++ subversion/libsvn_ra_svn/client.c (Arbeitskopie)
@@ -605,7 +605,7 @@
 
 
 static svn_error_t *ra_svn_open(svn_ra_session_t *session, const char *url,
- const svn_ra_callbacks_t *callbacks,
+ const svn_ra_callbacks2_t *callbacks,
                                 void *callback_baton,
                                 apr_hash_t *config,
                                 apr_pool_t *pool)
Index: subversion/libsvn_ra_dav/ra_dav.h
===================================================================
--- subversion/libsvn_ra_dav/ra_dav.h (Revision 15946)
+++ subversion/libsvn_ra_dav/ra_dav.h (Arbeitskopie)
@@ -160,7 +160,7 @@
   ne_session *sess; /* HTTP session to server */
   ne_session *sess2;
 
- const svn_ra_callbacks_t *callbacks; /* callbacks to get auth data */
+ const svn_ra_callbacks2_t *callbacks; /* callbacks to get auth data */
   void *callback_baton;
  
   svn_auth_iterstate_t *auth_iterstate; /* state of authentication retries */
Index: subversion/libsvn_ra_dav/session.c
===================================================================
--- subversion/libsvn_ra_dav/session.c (Revision 15946)
+++ subversion/libsvn_ra_dav/session.c (Arbeitskopie)
@@ -561,6 +561,16 @@
 #endif /* if/else SVN_NEON_0_25 */
 }
 
+static void
+ra_dav_neonprogress(void * baton, off_t progress, off_t total)
+{
+ /* Important: don't change the svn_ra_callbacks2_t struct here! */
+ const svn_ra_callbacks2_t * callbacks = (svn_ra_callbacks2_t *)baton;
+ if (callbacks->progress_func)
+ {
+ callbacks->progress_func(progress, total, callbacks->progress_baton);
+ }
+}
 
 
 /* ### need an ne_session_dup to avoid the second gethostbyname
@@ -570,7 +580,7 @@
 static svn_error_t *
 svn_ra_dav__open (svn_ra_session_t *session,
                   const char *repos_URL,
- const svn_ra_callbacks_t *callbacks,
+ const svn_ra_callbacks2_t *callbacks,
                   void *callback_baton,
                   apr_hash_t *config,
                   apr_pool_t *pool)
@@ -793,6 +803,12 @@
         }
     }
 
+ /* Set the neon callback to make it call the svn_progress_notify_func_t
+ * Note that ne_set_progress() takes a non-const baton as the third param.
+ * Since we don't change the callback struct but only use the non-const
+ * notification callback items of that struct, it's safe to cast */
+ ne_set_progress(sess, ra_dav_neonprogress, (void*)callbacks);
+ ne_set_progress(sess2, ra_dav_neonprogress, (void*)callbacks);
   session->priv = ras;
 
   return SVN_NO_ERROR;

---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@subversion.tigris.org
For additional commands, e-mail: dev-help@subversion.tigris.org
Received on Sun Aug 28 13:30:45 2005

This is an archived mail posted to the Subversion Dev mailing list.

This site is subject to the Apache Privacy Policy and the Apache Public Forum Archive Policy.