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 2016/11/18 18:14:40 UTC
svn commit: r1770418 - in /subversion/branches/authzperf/subversion:
include/svn_repos.h libsvn_repos/authz.c mod_dav_svn/mod_dav_svn.c
svnserve/svnserve.c
Author: stefan2
Date: Fri Nov 18 18:14:40 2016
New Revision: 1770418
URL: http://svn.apache.org/viewvc?rev=1770418&view=rev
Log:
On the authzperf branch:
Add caching support to our authz parsers.
There is only one authz parser function anymore and we simply need to add
a global object cache to be used by that function. However, the cache /
object pool needs to be created early on to guarantee pool lifetimes. To
this end, the cache is optional and we add a public *_initialize function.
* subversion/include/svn_repos.h
(svn_repos_authz_initialize): New API.
* subversion/libsvn_repos/authz.c
(authz_pool,
authz_pool_initialized,
synchronized_authz_initialize,
svn_repos_authz_initialize): Adds the authz object cache and the
initialization infrastructure.
(construct_key): New utility function.
(authz_read): Add cache lookup and insertion code.
* subversion/mod_dav_svn/mod_dav_svn.c
(init): Initialize the authz caching.
* subversion/svnserve/svnserve.c
(sub_main): Same.
Modified:
subversion/branches/authzperf/subversion/include/svn_repos.h
subversion/branches/authzperf/subversion/libsvn_repos/authz.c
subversion/branches/authzperf/subversion/mod_dav_svn/mod_dav_svn.c
subversion/branches/authzperf/subversion/svnserve/svnserve.c
Modified: subversion/branches/authzperf/subversion/include/svn_repos.h
URL: http://svn.apache.org/viewvc/subversion/branches/authzperf/subversion/include/svn_repos.h?rev=1770418&r1=1770417&r2=1770418&view=diff
==============================================================================
--- subversion/branches/authzperf/subversion/include/svn_repos.h (original)
+++ subversion/branches/authzperf/subversion/include/svn_repos.h Fri Nov 18 18:14:40 2016
@@ -3889,6 +3889,17 @@ svn_repos_get_fs_build_parser(const svn_
typedef struct svn_authz_t svn_authz_t;
/**
+ * This should be called before any other authz function.
+ *
+ * @a pool must support multi-threaded access if the application will use
+ * authz from multiple threads.
+ *
+ * @since New in 1.10.
+ */
+svn_error_t *
+svn_repos_authz_initialize(apr_pool_t *pool);
+
+/**
* Read authz configuration data from @a path (a dirent, an absolute file url
* or a registry path) into @a *authz_p, allocated in @a pool.
*
Modified: subversion/branches/authzperf/subversion/libsvn_repos/authz.c
URL: http://svn.apache.org/viewvc/subversion/branches/authzperf/subversion/libsvn_repos/authz.c?rev=1770418&r1=1770417&r2=1770418&view=diff
==============================================================================
--- subversion/branches/authzperf/subversion/libsvn_repos/authz.c (original)
+++ subversion/branches/authzperf/subversion/libsvn_repos/authz.c Fri Nov 18 18:14:40 2016
@@ -35,6 +35,7 @@
#include "svn_repos.h"
#include "svn_config.h"
#include "svn_ctype.h"
+#include "private/svn_atomic.h"
#include "private/svn_fspath.h"
#include "private/svn_repos_private.h"
#include "private/svn_sorts_private.h"
@@ -1353,6 +1354,67 @@ get_filtered_tree(svn_authz_t *authz,
return authz->user_rules[i];
}
+
+
+/*** Authz cache access. ***/
+
+/* All authz instances currently in use will be cached here.
+ * Will be instantiated at most once. */
+svn_object_pool__t *authz_pool = NULL;
+static svn_atomic_t authz_pool_initialized = FALSE;
+
+/* Implements svn_atomic__err_init_func_t. */
+static svn_error_t *
+synchronized_authz_initialize(void *baton, apr_pool_t *pool)
+{
+ svn_boolean_t multi_threaded
+ = apr_allocator_mutex_get(apr_pool_allocator_get(pool)) != NULL;
+
+ return svn_error_trace(svn_object_pool__create(&authz_pool, multi_threaded,
+ pool));
+}
+
+svn_error_t *
+svn_repos_authz_initialize(apr_pool_t *pool)
+{
+ /* Protect against multiple calls. */
+ return svn_error_trace(svn_atomic__init_once(&authz_pool_initialized,
+ synchronized_authz_initialize,
+ NULL, pool));
+}
+
+/* Return a combination of AUTHZ_KEY and GROUPS_KEY, allocated in RESULT_POOL.
+ * GROUPS_KEY may be NULL.
+ */
+static svn_membuf_t *
+construct_key(const svn_checksum_t *authz_key,
+ const svn_checksum_t *groups_key,
+ apr_pool_t *result_pool)
+{
+ svn_membuf_t *result = apr_pcalloc(result_pool, sizeof(*result));
+ if (groups_key)
+ {
+ apr_size_t authz_size = svn_checksum_size(authz_key);
+ apr_size_t groups_size = svn_checksum_size(groups_key);
+
+ svn_membuf__create(result, authz_size + groups_size, result_pool);
+ result->size = authz_size + groups_size; /* exact length is required! */
+
+ memcpy(result->data, authz_key->digest, authz_size);
+ memcpy((char *)result->data + authz_size,
+ groups_key->digest, groups_size);
+ }
+ else
+ {
+ apr_size_t size = svn_checksum_size(authz_key);
+ svn_membuf__create(result, size, result_pool);
+ result->size = size; /* exact length is required! */
+ memcpy(result->data, authz_key->digest, size);
+ }
+
+ return result;
+}
+
/* Read authz configuration data from PATH into *AUTHZ_P, allocated in
RESULT_POOL. If GROUPS_PATH is set, use the global groups parsed from it.
@@ -1379,6 +1441,7 @@ authz_read(authz_full_t **authz_p,
svn_stream_t *groups_stream = NULL;
svn_checksum_t *rules_checksum = NULL;
svn_checksum_t *groups_checksum = NULL;
+ svn_membuf_t *key;
config_access_t *access = svn_repos__create_config_access(repos_hint,
scratch_pool);
@@ -1392,12 +1455,52 @@ authz_read(authz_full_t **authz_p,
SVN_ERR(svn_repos__get_config(&groups_stream, &groups_checksum, access,
groups_path, must_exist, scratch_pool));
- /* Parse the configuration(s) and construct the full authz model from it. */
- err = svn_error_quick_wrapf(svn_authz__parse(authz_p, rules_stream,
- groups_stream,
- result_pool, scratch_pool),
- "Error while parsing authz file: '%s':",
- path);
+ /* The authz cache is optional. */
+ if (authz_pool)
+ {
+ /* Cache lookup. */
+ key = construct_key(rules_checksum, groups_checksum, scratch_pool);
+ SVN_ERR(svn_object_pool__lookup((void **)authz_p, authz_pool, key,
+ result_pool));
+
+ /* If not found, parse and add to cache. */
+ if (!*authz_p)
+ {
+ apr_pool_t *item_pool = svn_object_pool__new_item_pool(authz_pool);
+
+ /* Parse the configuration(s) and construct the full authz model
+ * from it. */
+ err = svn_authz__parse(authz_p, rules_stream, groups_stream,
+ item_pool, scratch_pool);
+ if (err != SVN_NO_ERROR)
+ {
+ /* That pool would otherwise never get destroyed. */
+ svn_pool_destroy(item_pool);
+
+ /* Add the URL / file name to the error stack since the parser
+ * doesn't have it. */
+ err = svn_error_quick_wrapf(err,
+ "Error while parsing config file: '%s':",
+ path);
+ }
+ else
+ {
+ SVN_ERR(svn_object_pool__insert((void **)authz_p, authz_pool,
+ key, *authz_p,
+ item_pool, result_pool));
+ }
+ }
+ }
+ else
+ {
+ /* Parse the configuration(s) and construct the full authz model from
+ * it. */
+ err = svn_error_quick_wrapf(svn_authz__parse(authz_p, rules_stream,
+ groups_stream,
+ result_pool, scratch_pool),
+ "Error while parsing authz file: '%s':",
+ path);
+ }
svn_repos__destroy_config_access(access);
Modified: subversion/branches/authzperf/subversion/mod_dav_svn/mod_dav_svn.c
URL: http://svn.apache.org/viewvc/subversion/branches/authzperf/subversion/mod_dav_svn/mod_dav_svn.c?rev=1770418&r1=1770417&r2=1770418&view=diff
==============================================================================
--- subversion/branches/authzperf/subversion/mod_dav_svn/mod_dav_svn.c (original)
+++ subversion/branches/authzperf/subversion/mod_dav_svn/mod_dav_svn.c Fri Nov 18 18:14:40 2016
@@ -137,6 +137,15 @@ init(apr_pool_t *p, apr_pool_t *plog, ap
return HTTP_INTERNAL_SERVER_ERROR;
}
+ serr = svn_repos_authz_initialize(p);
+ if (serr)
+ {
+ ap_log_perror(APLOG_MARK, APLOG_ERR, serr->apr_err, p,
+ "mod_dav_svn: error calling svn_repos_authz_initialize: '%s'",
+ serr->message ? serr->message : "(no more info)");
+ return HTTP_INTERNAL_SERVER_ERROR;
+ }
+
/* This returns void, so we can't check for error. */
conf = ap_get_module_config(s->module_config, &dav_svn_module);
svn_utf_initialize2(conf->use_utf8, p);
Modified: subversion/branches/authzperf/subversion/svnserve/svnserve.c
URL: http://svn.apache.org/viewvc/subversion/branches/authzperf/subversion/svnserve/svnserve.c?rev=1770418&r1=1770417&r2=1770418&view=diff
==============================================================================
--- subversion/branches/authzperf/subversion/svnserve/svnserve.c (original)
+++ subversion/branches/authzperf/subversion/svnserve/svnserve.c Fri Nov 18 18:14:40 2016
@@ -752,6 +752,9 @@ sub_main(int *exit_code, int argc, const
/* Initialize the FS library. */
SVN_ERR(svn_fs_initialize(pool));
+ /* Initialize the efficient Authz support. */
+ SVN_ERR(svn_repos_authz_initialize(pool));
+
SVN_ERR(svn_cmdline__getopt_init(&os, argc, argv, pool));
params.root = "/";