subversion-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From stef...@apache.org
Subject svn commit: r1614080 - in /subversion/branches/authzperf: BRANCH-README subversion/libsvn_repos/authz.c subversion/libsvn_subr/config.c subversion/libsvn_subr/config_impl.h
Date Mon, 28 Jul 2014 17:19:48 GMT
Author: stefan2
Date: Mon Jul 28 17:19:47 2014
New Revision: 1614080

URL: http://svn.apache.org/r1614080
Log:
On the authzperf branch: Implement the notion of path rule ordering
by making svn_config_t iterate through sections in declaration order.
This is done using a simple linked list because we can't remove
sections but only add them.

Without support for wildcards or other patterns, the config struct
will only contain a single section for each path.  With wildcards,
there may be more than one.  All three of the follwing path rules
are equally applicable:

  [/foo/*.doc]
  * = r

  [/foo/bar.*]
  * = rw

  [/foo/bar.doc]
  jrandom =

To make conflicts managable, always pick the last path rule.  That
means users should specify general rules first, followed by exceptions
and finally (and optionally) critical rules that deny certain access,
potentially globally.

Right now, this functionality is a mere preparation for wildcard
support (soon to be added).

* BRANCH-README
  (TODO, DONE): One more down.

* subversion/libsvn_subr/config_impl.h
  (svn_config_t): Add pointers to the first and last section.

* subversion/libsvn_subr/config.c
  (cfg_section_t): Add link to next section in the list.
  (svn_config_create2): Update constructor.
  (for_each_option): Iterate following the section creation order
                     instead of the hash order.
  (svn_config_addsection): Append new sections properly to the list. 
  (svn_config_enumerate_sections,
   svn_config_enumerate_sections2): Iterate sections in creation order.

* subversion/libsvn_repos/authz.c
  (access_t): Add SEQUENCE_NUMBER as criterion for later use.
  (NO_SEQUENCE_NUMBER): Yet another "not a value" constant.
  (process_path_rule_baton_t): Add counter such that all access_t
                               get a unique sequence number.
  (process_path_rule): Assign and bump the sequence number.
  (create_user_authz): Initialize sequence numbers and the numbering
                       process.

Modified:
    subversion/branches/authzperf/BRANCH-README
    subversion/branches/authzperf/subversion/libsvn_repos/authz.c
    subversion/branches/authzperf/subversion/libsvn_subr/config.c
    subversion/branches/authzperf/subversion/libsvn_subr/config_impl.h

Modified: subversion/branches/authzperf/BRANCH-README
URL: http://svn.apache.org/viewvc/subversion/branches/authzperf/BRANCH-README?rev=1614080&r1=1614079&r2=1614080&view=diff
==============================================================================
--- subversion/branches/authzperf/BRANCH-README (original)
+++ subversion/branches/authzperf/BRANCH-README Mon Jul 28 17:19:47 2014
@@ -4,7 +4,6 @@ allows much faster authz resolving and a
 
 TODO:
 
-* implement precedence rules
 * add support for full-segment wildcards ("/*/")
 * add support for variable length full-segment wildcards ("/**/")
 * add support for prefix segment patterns ("/foo*/")
@@ -18,3 +17,4 @@ DONE:
 * pre-calculate rule sets for the given user
 * implement recursive tree checks
 * implement evaluation shortcuts
+* implement precedence rules

Modified: subversion/branches/authzperf/subversion/libsvn_repos/authz.c
URL: http://svn.apache.org/viewvc/subversion/branches/authzperf/subversion/libsvn_repos/authz.c?rev=1614080&r1=1614079&r2=1614080&view=diff
==============================================================================
--- subversion/branches/authzperf/subversion/libsvn_repos/authz.c (original)
+++ subversion/branches/authzperf/subversion/libsvn_repos/authz.c Mon Jul 28 17:19:47 2014
@@ -266,13 +266,27 @@ get_memberships(svn_config_t *config,
 /* This structure describes the access rights given to a specific user by
  * a path rule (actually the rule set specified for a path).  I.e. there is
  * one instance of this per path rule.
- * Later commits will add more fields.
  */
 typedef struct access_t
 {
+  /* Sequence number of the path rule that this struct was derived from.
+   * If multiple rules apply to the same path (only possible with wildcard
+   * matching), the one with the highest SEQUENCE_ID wins, i.e. the latest
+   * one defined in the authz file.
+   *
+   * A value of 0 denotes the default rule at the repository root denying
+   * access to everybody.  User-defined path rules start with ID 1.
+   */
+  apr_int64_t sequence_number;
+
+  /* Access rights of the respective user as defined by the rule set. */
   svn_repos_authz_access_t rights;
 } access_t;
 
+/* Use this to indicate that no sequence ID has been assigned.
+ * It will automatically be inferior to (less than) any other sequence ID. */
+#define NO_SEQUENCE_NUMBER (-1)
+
 /* The pattern tree.  All relevant path rules are being folded into this
  * prefix tree, with a single, whole segment stored at each node.  The whole
  * tree applies to a single user only.
@@ -448,6 +462,9 @@ typedef struct process_path_rule_baton_t
      a member of. */
   apr_hash_t *memberships;
 
+  /* Next sequence number.  Basically a counter. */
+  apr_int64_t sequence_number;
+
   /* Root node of the result tree. Never NULL. */
   node_t *root;
 
@@ -494,6 +511,7 @@ process_path_rule(const char *name,
 
   /* Access rights to assign. */
   access = apr_pcalloc(baton->pool, sizeof(*access));
+  access->sequence_number = baton->sequence_number++;
   access->rights = rights;
 
   /* Insert the path rule into the filtered tree. */
@@ -557,6 +575,7 @@ create_user_authz(svn_config_t *config,
   baton.repository.data = repository;
   baton.repository.len = strlen(repository);
   baton.pool = result_pool;
+  baton.sequence_number = 1;
 
   /* Determine the user's aliases, group memberships etc. */
   baton.memberships = get_memberships(config, user, scratch_pool, subpool);
@@ -567,10 +586,11 @@ create_user_authz(svn_config_t *config,
   svn_config_enumerate_sections2(config, process_path_rule, &baton, subpool);
 
   /* If there is no relevant rule at the root node, the "no access" default
-   * applies. */
+   * applies. Give it a SEQUENCE_ID that will never overrule others. */
   if (!baton.root->access)
     {
       baton.root->access = apr_pcalloc(result_pool, sizeof(access_t));
+      baton.root->access->sequence_number = 0;
       baton.root->access->rights = svn_authz_none;
     }
 

Modified: subversion/branches/authzperf/subversion/libsvn_subr/config.c
URL: http://svn.apache.org/viewvc/subversion/branches/authzperf/subversion/libsvn_subr/config.c?rev=1614080&r1=1614079&r2=1614080&view=diff
==============================================================================
--- subversion/branches/authzperf/subversion/libsvn_subr/config.c (original)
+++ subversion/branches/authzperf/subversion/libsvn_subr/config.c Mon Jul 28 17:19:47 2014
@@ -52,6 +52,9 @@ struct cfg_section_t
 
   /* Table of cfg_option_t's. */
   apr_hash_t *options;
+
+  /* Section added immediately after this one. NULL for the last section. */
+  cfg_section_t *next;
 };
 
 
@@ -88,6 +91,8 @@ svn_config_create2(svn_config_t **cfgp,
   svn_config_t *cfg = apr_palloc(result_pool, sizeof(*cfg));
 
   cfg->sections = apr_hash_make(result_pool);
+  cfg->first_section = NULL;
+  cfg->last_section = NULL;
   cfg->pool = result_pool;
   cfg->x_pool = svn_pool_create(result_pool);
   cfg->x_values = FALSE;
@@ -333,18 +338,11 @@ for_each_option(svn_config_t *cfg, void 
                                        cfg_section_t *section,
                                        cfg_option_t *option))
 {
-  apr_hash_index_t *sec_ndx;
-  for (sec_ndx = apr_hash_first(pool, cfg->sections);
-       sec_ndx != NULL;
-       sec_ndx = apr_hash_next(sec_ndx))
+  cfg_section_t *sec;
+  for (sec = cfg->first_section; sec != NULL; sec = sec->next)
     {
-      void *sec_ptr;
-      cfg_section_t *sec;
       apr_hash_index_t *opt_ndx;
 
-      apr_hash_this(sec_ndx, NULL, NULL, &sec_ptr);
-      sec = sec_ptr;
-
       for (opt_ndx = apr_hash_first(pool, sec->options);
            opt_ndx != NULL;
            opt_ndx = apr_hash_next(opt_ndx))
@@ -640,6 +638,14 @@ svn_config_addsection(svn_config_t *cfg,
   else
     hash_key = make_hash_key(apr_pstrdup(cfg->pool, section));
   s->options = apr_hash_make(cfg->pool);
+
+  s->next = NULL;
+  if (cfg->last_section)
+    cfg->last_section->next = s;
+  else
+    cfg->first_section = s;
+  cfg->last_section = s;
+
   svn_hash_sets(cfg->sections, hash_key, s);
 
   return s;
@@ -927,25 +933,15 @@ svn_config_enumerate_sections(svn_config
                               svn_config_section_enumerator_t callback,
                               void *baton)
 {
-  apr_hash_index_t *sec_ndx;
   int count = 0;
-  apr_pool_t *subpool = svn_pool_create(cfg->x_pool);
-
-  for (sec_ndx = apr_hash_first(subpool, cfg->sections);
-       sec_ndx != NULL;
-       sec_ndx = apr_hash_next(sec_ndx))
+  cfg_section_t *sec;
+  for (sec = cfg->first_section; sec != NULL; sec = sec->next)
     {
-      void *sec_ptr;
-      cfg_section_t *sec;
-
-      apr_hash_this(sec_ndx, NULL, NULL, &sec_ptr);
-      sec = sec_ptr;
       ++count;
       if (!callback(sec->name, baton))
         break;
     }
 
-  svn_pool_destroy(subpool);
   return count;
 }
 
@@ -955,20 +951,13 @@ svn_config_enumerate_sections2(svn_confi
                                svn_config_section_enumerator2_t callback,
                                void *baton, apr_pool_t *pool)
 {
-  apr_hash_index_t *sec_ndx;
+  cfg_section_t *sec;
   apr_pool_t *iteration_pool;
   int count = 0;
 
   iteration_pool = svn_pool_create(pool);
-  for (sec_ndx = apr_hash_first(pool, cfg->sections);
-       sec_ndx != NULL;
-       sec_ndx = apr_hash_next(sec_ndx))
+  for (sec = cfg->first_section; sec != NULL; sec = sec->next)
     {
-      void *sec_ptr;
-      cfg_section_t *sec;
-
-      apr_hash_this(sec_ndx, NULL, NULL, &sec_ptr);
-      sec = sec_ptr;
       ++count;
       svn_pool_clear(iteration_pool);
       if (!callback(sec->name, baton, iteration_pool))

Modified: subversion/branches/authzperf/subversion/libsvn_subr/config_impl.h
URL: http://svn.apache.org/viewvc/subversion/branches/authzperf/subversion/libsvn_subr/config_impl.h?rev=1614080&r1=1614079&r2=1614080&view=diff
==============================================================================
--- subversion/branches/authzperf/subversion/libsvn_subr/config_impl.h (original)
+++ subversion/branches/authzperf/subversion/libsvn_subr/config_impl.h Mon Jul 28 17:19:47
2014
@@ -46,6 +46,12 @@ struct svn_config_t
   /* Table of cfg_section_t's. */
   apr_hash_t *sections;
 
+  /* First section added to this configuration.  NULL if SECTIONS is empty. */
+  struct cfg_section_t *first_section;
+
+  /* Last section added to this configuration.  NULL if SECTIONS is empty. */
+  struct cfg_section_t *last_section;
+
   /* Pool for hash tables, table entries and unexpanded values.
      Also, parent pool for temporary pools. */
   apr_pool_t *pool;



Mime
View raw message