]> git.ipfire.org Git - thirdparty/systemd.git/commitdiff
hostname: expose product UUID on bus
authorYu Watanabe <watanabe.yu+github@gmail.com>
Mon, 25 Jun 2018 07:20:18 +0000 (16:20 +0900)
committerYu Watanabe <watanabe.yu+github@gmail.com>
Wed, 8 Aug 2018 01:15:00 +0000 (10:15 +0900)
src/hostname/hostnamed.c
src/hostname/org.freedesktop.hostname1.policy
src/libsystemd/sd-bus/bus-common-errors.c
src/libsystemd/sd-bus/bus-common-errors.h

index b98f962ad298f0c2b157ba6f5ec06840bd9abf80..d8074e6f5fb454ffba993e4ec9238e53cef2eb18 100644 (file)
@@ -6,11 +6,13 @@
 #include <unistd.h>
 
 #include "alloc-util.h"
+#include "bus-common-errors.h"
 #include "bus-util.h"
 #include "def.h"
 #include "env-util.h"
 #include "fileio-label.h"
 #include "hostname-util.h"
+#include "id128-util.h"
 #include "os-util.h"
 #include "parse-util.h"
 #include "path-util.h"
@@ -43,6 +45,8 @@ enum {
 typedef struct Context {
         char *data[_PROP_MAX];
         Hashmap *polkit_registry;
+        sd_id128_t uuid;
+        bool has_uuid;
 } Context;
 
 static void context_reset(Context *c) {
@@ -103,6 +107,11 @@ static int context_read_data(Context *c) {
         if (r < 0 && r != -ENOENT)
                 return r;
 
+        r = id128_read("/sys/class/dmi/id/product_uuid", ID128_UUID, &c->uuid);
+        if (r < 0)
+                log_info_errno(r, "Failed to read product UUID, ignoring: %m");
+        c->has_uuid = (r >= 0);
+
         return 0;
 }
 
@@ -598,6 +607,46 @@ static int method_set_location(sd_bus_message *m, void *userdata, sd_bus_error *
         return set_machine_info(userdata, m, PROP_LOCATION, method_set_location, error);
 }
 
+static int method_get_product_uuid(sd_bus_message *m, void *userdata, sd_bus_error *error) {
+        _cleanup_(sd_bus_message_unrefp) sd_bus_message *reply = NULL;
+        Context *c = userdata;
+        int interactive, r;
+
+        assert(m);
+        assert(c);
+
+        if (!c->has_uuid)
+                return sd_bus_error_set(error, BUS_ERROR_NO_PRODUCT_UUID, "Failed to read product UUID from /sys/class/dmi/id/product_uuid");
+
+        r = sd_bus_message_read(m, "b", &interactive);
+        if (r < 0)
+                return r;
+
+        r = bus_verify_polkit_async(
+                        m,
+                        CAP_SYS_ADMIN,
+                        "org.freedesktop.hostname1.get-product-uuid",
+                        NULL,
+                        interactive,
+                        UID_INVALID,
+                        &c->polkit_registry,
+                        error);
+        if (r < 0)
+                return r;
+        if (r == 0)
+                return 1; /* No authorization for now, but the async polkit stuff will call us again when it has it */
+
+        r = sd_bus_message_new_method_return(m, &reply);
+        if (r < 0)
+                return r;
+
+        r = sd_bus_message_append_array(reply, 'y', &c->uuid, sizeof(c->uuid));
+        if (r < 0)
+                return r;
+
+        return sd_bus_send(NULL, reply, NULL);
+}
+
 static const sd_bus_vtable hostname_vtable[] = {
         SD_BUS_VTABLE_START(0),
         SD_BUS_PROPERTY("Hostname", "s", NULL, offsetof(Context, data) + sizeof(char*) * PROP_HOSTNAME, SD_BUS_VTABLE_PROPERTY_EMITS_CHANGE),
@@ -620,6 +669,7 @@ static const sd_bus_vtable hostname_vtable[] = {
         SD_BUS_METHOD("SetChassis", "sb", NULL, method_set_chassis, SD_BUS_VTABLE_UNPRIVILEGED),
         SD_BUS_METHOD("SetDeployment", "sb", NULL, method_set_deployment, SD_BUS_VTABLE_UNPRIVILEGED),
         SD_BUS_METHOD("SetLocation", "sb", NULL, method_set_location, SD_BUS_VTABLE_UNPRIVILEGED),
+        SD_BUS_METHOD("GetProductUUID", "b", "ay", method_get_product_uuid, SD_BUS_VTABLE_UNPRIVILEGED),
         SD_BUS_VTABLE_END,
 };
 
index e1519ce86be24a6367ae84ec0f1b5ac072db0cd2..5bedc0b6942a37d4f06ac40ff21e8cd824b3aef9 100644 (file)
                 </defaults>
         </action>
 
+        <action id="org.freedesktop.hostname1.get-product-uuid">
+                <description gettext-domain="systemd">Get product UUID</description>
+                <message gettext-domain="systemd">Authentication is required to get product UUID.</message>
+                <defaults>
+                        <allow_any>auth_admin_keep</allow_any>
+                        <allow_inactive>auth_admin_keep</allow_inactive>
+                        <allow_active>auth_admin_keep</allow_active>
+                </defaults>
+        </action>
+
 </policyconfig>
index ff0790bf5a566dca457034719d5729872aa492ac..b6e40ee8a92e271f08c3db87a9c6b75a041ba7b0 100644 (file)
@@ -94,5 +94,7 @@ BUS_ERROR_MAP_ELF_REGISTER const sd_bus_error_map bus_common_errors[] = {
         SD_BUS_ERROR_MAP(BUS_ERROR_NO_SUCH_TRANSFER,             ENXIO),
         SD_BUS_ERROR_MAP(BUS_ERROR_TRANSFER_IN_PROGRESS,         EBUSY),
 
+        SD_BUS_ERROR_MAP(BUS_ERROR_NO_PRODUCT_UUID,              EOPNOTSUPP),
+
         SD_BUS_ERROR_MAP_END
 };
index daf7cdae6734ae017fb3da1d657809965c235a07..a76a93644caeccb2de0d5f5545579cc6835330c4 100644 (file)
@@ -75,4 +75,6 @@
 #define BUS_ERROR_NO_SUCH_TRANSFER "org.freedesktop.import1.NoSuchTransfer"
 #define BUS_ERROR_TRANSFER_IN_PROGRESS "org.freedesktop.import1.TransferInProgress"
 
+#define BUS_ERROR_NO_PRODUCT_UUID "org.freedesktop.hostname1.NoProductUUID"
+
 BUS_ERROR_MAP_ELF_USE(bus_common_errors);