You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@subversion.apache.org by st...@apache.org on 2010/08/09 20:14:02 UTC
svn commit: r983760 - in
/subversion/branches/performance/subversion/libsvn_fs_fs: caching.c fs.h
fs_fs.c
Author: stefan2
Date: Mon Aug 9 18:14:01 2010
New Revision: 983760
URL: http://svn.apache.org/viewvc?rev=983760&view=rev
Log:
* subversion/libsvn_fs_fs/fs.h
(fs_fs_data_t): add node_revision_cache member
* subversion/libsvn_fs_fs/fs_fs.c
(get_noderev_cache_key, get_cached_node_revision_body,
set_cached_node_revision_body): new functions to get / set noderevs from / to cache
(get_node_revision_body): speed up using the noderev cache
* subversion/libsvn_fs_fs/caching.c
(svn_fs_fs__initialize_caches): initialize the revnode cache; fix a comment
Modified:
subversion/branches/performance/subversion/libsvn_fs_fs/caching.c
subversion/branches/performance/subversion/libsvn_fs_fs/fs.h
subversion/branches/performance/subversion/libsvn_fs_fs/fs_fs.c
Modified: subversion/branches/performance/subversion/libsvn_fs_fs/caching.c
URL: http://svn.apache.org/viewvc/subversion/branches/performance/subversion/libsvn_fs_fs/caching.c?rev=983760&r1=983759&r2=983760&view=diff
==============================================================================
--- subversion/branches/performance/subversion/libsvn_fs_fs/caching.c (original)
+++ subversion/branches/performance/subversion/libsvn_fs_fs/caching.c Mon Aug 9 18:14:01 2010
@@ -300,7 +300,7 @@ svn_fs_fs__initialize_caches(svn_fs_t *f
/* initialize file handle cache as configured */
ffd->file_handle_cache = get_global_file_handle_cache();
- /* if enabled, enable the txdelta window cache */
+ /* initialize txdelta window cache, if that has been enabled */
if (get_global_membuffer_cache() &&
svn_fs_fs__get_cache_config()->cache_txdeltas)
{
@@ -322,5 +322,28 @@ svn_fs_fs__initialize_caches(svn_fs_t *f
SVN_ERR(svn_cache__set_error_handler(ffd->txdelta_window_cache,
warn_on_cache_errors, fs, pool));
+ /* initialize node revision cache, if caching has been enabled */
+ if (get_global_membuffer_cache())
+ {
+ SVN_ERR(svn_cache__create_membuffer_cache(&(ffd->node_revision_cache),
+ get_global_membuffer_cache(),
+ svn_fs_fs__serialize_node_revision,
+ svn_fs_fs__deserialize_node_revision,
+ APR_HASH_KEY_STRING,
+ apr_pstrcat(pool,
+ prefix,
+ "NODEREVS",
+ NULL),
+ fs->pool));
+ }
+ else
+ {
+ ffd->node_revision_cache = NULL;
+ }
+
+ if (ffd->node_revision_cache && ! no_handler)
+ SVN_ERR(svn_cache__set_error_handler(ffd->node_revision_cache,
+ warn_on_cache_errors, fs, pool));
+
return SVN_NO_ERROR;
}
Modified: subversion/branches/performance/subversion/libsvn_fs_fs/fs.h
URL: http://svn.apache.org/viewvc/subversion/branches/performance/subversion/libsvn_fs_fs/fs.h?rev=983760&r1=983759&r2=983760&view=diff
==============================================================================
--- subversion/branches/performance/subversion/libsvn_fs_fs/fs.h (original)
+++ subversion/branches/performance/subversion/libsvn_fs_fs/fs.h Mon Aug 9 18:14:01 2010
@@ -247,6 +247,9 @@ typedef struct
/* Cache for txdelta_window_t objects; the key is (revFilePath, offset) */
svn_cache__t *txdelta_window_cache;
+ /* Cache for node_revision_t objects; the key is (revision, id offset) */
+ svn_cache__t *node_revision_cache;
+
/* Data shared between all svn_fs_t objects for a given filesystem. */
fs_fs_shared_data_t *shared;
Modified: subversion/branches/performance/subversion/libsvn_fs_fs/fs_fs.c
URL: http://svn.apache.org/viewvc/subversion/branches/performance/subversion/libsvn_fs_fs/fs_fs.c?rev=983760&r1=983759&r2=983760&view=diff
==============================================================================
--- subversion/branches/performance/subversion/libsvn_fs_fs/fs_fs.c (original)
+++ subversion/branches/performance/subversion/libsvn_fs_fs/fs_fs.c Mon Aug 9 18:14:01 2010
@@ -2079,6 +2079,66 @@ read_rep_offsets(representation_t **rep_
return SVN_NO_ERROR;
}
+/* Combine the revision and offset of the ID to a string that will
+ * be used as a cache key. Allocations will be made from POOL.
+ */
+static const char *
+get_noderev_cache_key(const svn_fs_id_t *id, apr_pool_t *pool)
+{
+ return svn_fs_fs__combine_two_numbers(svn_fs_fs__id_rev(id),
+ svn_fs_fs__id_offset(id),
+ pool);
+}
+
+/* Look up the NODEREV_P for ID in FS' node revsion cache. If noderev
+ * caching has been enabled and the data can be found, IS_CACHED will
+ * be set to TRUE. The noderev will be allocated from POOL.
+ *
+ * Non-permanent ids (e.g. ids within a TXN) will not be cached.
+ */
+static svn_error_t *
+get_cached_node_revision_body(node_revision_t **noderev_p,
+ svn_fs_t *fs,
+ const svn_fs_id_t *id,
+ svn_boolean_t *is_cached,
+ apr_pool_t *pool)
+{
+ fs_fs_data_t *ffd = fs->fsap_data;
+ if (! ffd->node_revision_cache || svn_fs_fs__id_txn_id(id))
+ *is_cached = FALSE;
+ else
+ SVN_ERR(svn_cache__get((void **) noderev_p,
+ is_cached,
+ ffd->node_revision_cache,
+ get_noderev_cache_key(id, pool),
+ pool));
+
+ return SVN_NO_ERROR;
+}
+
+/* If noderev caching has been enabled, store the NODEREV_P for the given ID
+ * in FS' node revsion cache. SCRATCH_POOL is used for temporary allcations.
+ *
+ * Non-permanent ids (e.g. ids within a TXN) will not be cached.
+ */
+static svn_error_t *
+set_cached_node_revision_body(node_revision_t *noderev_p,
+ svn_fs_t *fs,
+ const svn_fs_id_t *id,
+ apr_pool_t *scratch_pool)
+{
+ fs_fs_data_t *ffd = fs->fsap_data;
+
+ if (ffd->node_revision_cache && !svn_fs_fs__id_txn_id(id))
+ return svn_cache__set(ffd->node_revision_cache,
+ get_noderev_cache_key(id, scratch_pool),
+ noderev_p,
+ scratch_pool);
+
+ return SVN_NO_ERROR;
+}
+
+
/* Get the node-revision for the node ID in FS.
Set *NODEREV_P to the new node-revision structure, allocated in POOL.
See svn_fs_fs__get_node_revision, which wraps this and adds another
@@ -2091,6 +2151,12 @@ get_node_revision_body(node_revision_t *
{
svn_file_handle_cache__handle_t *revision_file;
svn_error_t *err;
+ svn_boolean_t is_cached = FALSE;
+
+ /* First, try a cache lookup. If that succeeds, we are done here. */
+ SVN_ERR(get_cached_node_revision_body(noderev_p, fs, id, &is_cached, pool));
+ if (is_cached)
+ return SVN_NO_ERROR;
if (svn_fs_fs__id_txn_id(id))
{
@@ -2126,12 +2192,15 @@ get_node_revision_body(node_revision_t *
return svn_error_return(err);
}
- return svn_fs_fs__read_noderev(noderev_p,
- svn_stream__from_cached_file_handle
- (revision_file,
+ SVN_ERR(svn_fs_fs__read_noderev(noderev_p,
+ svn_stream__from_cached_file_handle
+ (revision_file,
FALSE,
pool),
- pool);
+ pool));
+
+ /* The noderev is not in cache, yet. Add it, if caching has been enabled. */
+ return set_cached_node_revision_body(*noderev_p, fs, id, pool);
}
svn_error_t *