X-Git-Url: http://www.chiark.greenend.org.uk/ucgi/~ianmdlvl/git?a=blobdiff_plain;f=src%2Fbus-proxyd%2Fbus-proxyd.c;h=2f26f81a366ba3136e169d469ee55e9b504448bb;hb=f0a4c7391c7c682b658974b82390d332197740e2;hp=8c1b6a5ad6281bfce44e27a271f332c529c6789f;hpb=96343c3039020d55ee64fb4746abee483e05fc29;p=elogind.git diff --git a/src/bus-proxyd/bus-proxyd.c b/src/bus-proxyd/bus-proxyd.c index 8c1b6a5ad..2f26f81a3 100644 --- a/src/bus-proxyd/bus-proxyd.c +++ b/src/bus-proxyd/bus-proxyd.c @@ -51,6 +51,8 @@ static char *arg_command_line_buffer = NULL; static bool arg_drop_privileges = false; static char **arg_configuration = NULL; +static Hashmap *names_hash = NULL; + static int help(void) { printf("%s [OPTIONS...]\n\n" @@ -507,7 +509,7 @@ static int peer_is_privileged(sd_bus *bus, sd_bus_message *m) { return false; } -static int process_driver(sd_bus *a, sd_bus *b, sd_bus_message *m) { +static int process_driver(sd_bus *a, sd_bus *b, sd_bus_message *m, Policy *policy, const struct ucred *ucred) { int r; assert(a); @@ -676,7 +678,7 @@ static int process_driver(sd_bus *a, sd_bus *b, sd_bus_message *m) { sd_id128_t server_id; char buf[SD_ID128_STRING_MAX]; - r = sd_bus_get_server_id(a, &server_id); + r = sd_bus_get_owner_id(a, &server_id); if (r < 0) return synthetic_reply_method_errno(m, r, NULL); @@ -768,8 +770,8 @@ static int process_driver(sd_bus *a, sd_bus *b, sd_bus_message *m) { char *n; KDBUS_ITEM_FOREACH(item, name, items) - if (item->type == KDBUS_ITEM_NAME) - entry_name = item->str; + if (item->type == KDBUS_ITEM_OWNED_NAME) + entry_name = item->name.name; if (!streq_ptr(entry_name, arg0)) continue; @@ -837,6 +839,8 @@ static int process_driver(sd_bus *a, sd_bus *b, sd_bus_message *m) { return synthetic_reply_method_errno(m, r, NULL); } + hashmap_remove(names_hash, name); + return synthetic_reply_method_return(m, "u", BUS_NAME_RELEASED); } else if (sd_bus_message_is_method_call(m, "org.freedesktop.DBus", "ReloadConfig")) { @@ -849,11 +853,15 @@ static int process_driver(sd_bus *a, sd_bus *b, sd_bus_message *m) { } else if (sd_bus_message_is_method_call(m, "org.freedesktop.DBus", "RequestName")) { const char *name; uint32_t flags, param; + bool in_queue; r = sd_bus_message_read(m, "su", &name, &flags); if (r < 0) return synthetic_reply_method_errno(m, r, NULL); + if (!policy_check_own(policy, ucred, name)) + return synthetic_reply_method_errno(m, -EPERM, NULL); + if (!service_name_is_valid(name)) return synthetic_reply_method_errno(m, -EINVAL, NULL); if ((flags & ~(BUS_NAME_ALLOW_REPLACEMENT|BUS_NAME_REPLACE_EXISTING|BUS_NAME_DO_NOT_QUEUE)) != 0) @@ -876,7 +884,13 @@ static int process_driver(sd_bus *a, sd_bus *b, sd_bus_message *m) { return synthetic_reply_method_errno(m, r, NULL); } - if (r == 0) + in_queue = (r == 0); + + r = hashmap_put(names_hash, name, NULL); + if (r < 0) + return synthetic_reply_method_errno(m, r, NULL); + + if (in_queue) return synthetic_reply_method_return(m, "u", BUS_NAME_IN_QUEUE); return synthetic_reply_method_return(m, "u", BUS_NAME_PRIMARY_OWNER); @@ -986,7 +1000,7 @@ static int process_driver(sd_bus *a, sd_bus *b, sd_bus_message *m) { } } -static int process_hello(sd_bus *a, sd_bus *b, sd_bus_message *m, bool *got_hello) { +static int process_hello(sd_bus *a, sd_bus *b, sd_bus_message *m, Policy *policy, const struct ucred *ucred, bool *got_hello) { _cleanup_bus_message_unref_ sd_bus_message *n = NULL; bool is_hello; int r; @@ -1018,6 +1032,11 @@ static int process_hello(sd_bus *a, sd_bus *b, sd_bus_message *m, bool *got_hell return -EIO; } + if (!policy_check_hello(policy, ucred)) { + log_error("Policy denied HELLO"); + return -EPERM; + } + *got_hello = true; if (!a->is_kernel) @@ -1186,13 +1205,19 @@ int main(int argc, char *argv[]) { goto finish; } + names_hash = hashmap_new(&string_hash_ops); + if (!names_hash) { + log_oom(); + goto finish; + } + r = sd_bus_new(&a); if (r < 0) { log_error("Failed to allocate bus: %s", strerror(-r)); goto finish; } - r = sd_bus_set_name(a, "sd-proxy"); + r = sd_bus_set_description(a, "sd-proxy"); if (r < 0) { log_error("Failed to set bus name: %s", strerror(-r)); goto finish; @@ -1230,7 +1255,7 @@ int main(int argc, char *argv[]) { goto finish; } - r = sd_bus_get_server_id(a, &server_id); + r = sd_bus_get_owner_id(a, &server_id); if (r < 0) { log_error("Failed to get server ID: %s", strerror(-r)); goto finish; @@ -1401,7 +1426,7 @@ int main(int argc, char *argv[]) { goto finish; } - k = process_hello(a, b, m, &got_hello); + k = process_hello(a, b, m, &policy, &ucred, &got_hello); if (k < 0) { r = k; log_error("Failed to process HELLO: %s", strerror(-r)); @@ -1418,7 +1443,7 @@ int main(int argc, char *argv[]) { goto finish; } - k = process_driver(a, b, m); + k = process_driver(a, b, m, &policy, &ucred); if (k < 0) { r = k; log_error("Failed to process driver calls: %s", strerror(-r)); @@ -1514,6 +1539,7 @@ finish: policy_free(&policy); strv_free(arg_configuration); + hashmap_free(names_hash); free(arg_address); return r < 0 ? EXIT_FAILURE : EXIT_SUCCESS;