summaryrefslogtreecommitdiff
path: root/src/bus-proxyd/proxy.c
diff options
context:
space:
mode:
authorDavid Herrmann <dh.herrmann@gmail.com>2015-01-17 18:07:58 +0100
committerDavid Herrmann <dh.herrmann@gmail.com>2015-01-17 18:27:23 +0100
commitc4bc1a8434f2a34840ea6f63064fa998ecfae738 (patch)
treec10ae7cfd3864cc74fc83c997baaf45e81215b48 /src/bus-proxyd/proxy.c
parentb58d857136496ee463223cd90af46512e9eef152 (diff)
bus-proxy: share policy between threads
This implements a shared policy cache with read-write locks. We no longer parse the XML policy in each thread. This will allow us to easily implement ReloadConfig().
Diffstat (limited to 'src/bus-proxyd/proxy.c')
-rw-r--r--src/bus-proxyd/proxy.c50
1 files changed, 37 insertions, 13 deletions
diff --git a/src/bus-proxyd/proxy.c b/src/bus-proxyd/proxy.c
index 744b11da5c..ab164474fa 100644
--- a/src/bus-proxyd/proxy.c
+++ b/src/bus-proxyd/proxy.c
@@ -255,16 +255,27 @@ Proxy *proxy_free(Proxy *p) {
return NULL;
}
-int proxy_load_policy(Proxy *p, char **configuration) {
+int proxy_set_policy(Proxy *p, SharedPolicy *sp, char **configuration) {
_cleanup_strv_free_ char **strv = NULL;
+ Policy *policy;
int r;
assert(p);
+ assert(sp);
/* no need to load legacy policy if destination is not kdbus */
if (!p->dest_bus->is_kernel)
return 0;
+ p->policy = sp;
+
+ policy = shared_policy_acquire(sp);
+ if (policy) {
+ /* policy already pre-loaded */
+ shared_policy_release(sp, policy);
+ return 0;
+ }
+
if (!configuration) {
const char *scope;
@@ -291,30 +302,30 @@ int proxy_load_policy(Proxy *p, char **configuration) {
configuration = strv;
}
- r = policy_load(&p->policy_buffer, configuration);
- if (r < 0)
- return log_error_errno(r, "Failed to load policy: %m");
-
- p->policy = &p->policy_buffer;
- /* policy_dump(p->policy); */
-
- return 0;
+ return shared_policy_preload(sp, configuration);
}
int proxy_hello_policy(Proxy *p, uid_t original_uid) {
+ Policy *policy;
+ int r = 0;
+
assert(p);
if (!p->policy)
return 0;
+ policy = shared_policy_acquire(p->policy);
+
if (p->local_creds.uid == original_uid)
log_debug("Permitting access, since bus owner matches bus client.");
- else if (policy_check_hello(p->policy, p->local_creds.uid, p->local_creds.gid))
+ else if (policy_check_hello(policy, p->local_creds.uid, p->local_creds.gid))
log_debug("Permitting access due to XML policy.");
else
- return log_error_errno(EPERM, "Policy denied connection.");
+ r = log_error_errno(EPERM, "Policy denied connection.");
- return 0;
+ shared_policy_release(p->policy, policy);
+
+ return r;
}
static int proxy_wait(Proxy *p) {
@@ -384,7 +395,7 @@ static int handle_policy_error(sd_bus_message *m, int r) {
return r;
}
-static int process_policy(sd_bus *from, sd_bus *to, sd_bus_message *m, Policy *policy, const struct ucred *our_ucred, Set *owned_names) {
+static int process_policy_unlocked(sd_bus *from, sd_bus *to, sd_bus_message *m, Policy *policy, const struct ucred *our_ucred, Set *owned_names) {
int r;
assert(from);
@@ -584,6 +595,19 @@ static int process_policy(sd_bus *from, sd_bus *to, sd_bus_message *m, Policy *p
return 0;
}
+static int process_policy(sd_bus *from, sd_bus *to, sd_bus_message *m, SharedPolicy *sp, const struct ucred *our_ucred, Set *owned_names) {
+ Policy *policy;
+ int r;
+
+ assert(sp);
+
+ policy = shared_policy_acquire(sp);
+ r = process_policy_unlocked(from, to, m, policy, our_ucred, owned_names);
+ shared_policy_release(sp, policy);
+
+ return r;
+}
+
static int process_hello(Proxy *p, sd_bus_message *m) {
_cleanup_bus_message_unref_ sd_bus_message *n = NULL;
bool is_hello;