static int generate_new_id128(void) { sd_id128_t id; int r; unsigned i; r = sd_id128_randomize(&id); if (r < 0) { log_error("Failed to generate ID: %s", strerror(-r)); return r; } printf("As string:\n" SD_ID128_FORMAT_STR "\n\n" "As UUID:\n" "%02x%02x%02x%02x-%02x%02x-%02x%02x-%02x%02x-%02x%02x%02x%02x%02x%02x\n\n" "As macro:\n" "#define MESSAGE_XYZ SD_ID128_MAKE(", SD_ID128_FORMAT_VAL(id), SD_ID128_FORMAT_VAL(id)); for (i = 0; i < 16; i++) printf("%02x%s", id.bytes[i], i != 15 ? "," : ""); fputs(")\n", stdout); return 0; }
static void *server(void *p) { struct context *c = p; sd_bus *bus = NULL; sd_id128_t id; int r; c->quit = false; assert_se(sd_id128_randomize(&id) >= 0); assert_se(sd_bus_new(&bus) >= 0); assert_se(sd_bus_set_fd(bus, c->fds[0], c->fds[0]) >= 0); assert_se(sd_bus_set_server(bus, 1, id) >= 0); assert_se(sd_bus_add_object_vtable(bus, NULL, "/foo", "org.freedesktop.systemd.test", vtable, c) >= 0); assert_se(sd_bus_add_object_vtable(bus, NULL, "/foo", "org.freedesktop.systemd.test2", vtable, c) >= 0); assert_se(sd_bus_add_fallback_vtable(bus, NULL, "/value", "org.freedesktop.systemd.ValueTest", vtable2, NULL, UINT_TO_PTR(20)) >= 0); assert_se(sd_bus_add_node_enumerator(bus, NULL, "/value", enumerator_callback, NULL) >= 0); assert_se(sd_bus_add_node_enumerator(bus, NULL, "/value/a", enumerator2_callback, NULL) >= 0); assert_se(sd_bus_add_object_manager(bus, NULL, "/value") >= 0); assert_se(sd_bus_add_object_manager(bus, NULL, "/value/a") >= 0); assert_se(sd_bus_start(bus) >= 0); log_error("Entering event loop on server"); while (!c->quit) { log_error("Loop!"); r = sd_bus_process(bus, NULL); if (r < 0) { log_error_errno(r, "Failed to process requests: %m"); goto fail; } if (r == 0) { r = sd_bus_wait(bus, (uint64_t) -1); if (r < 0) { log_error_errno(r, "Failed to wait: %m"); goto fail; } continue; } } r = 0; fail: if (bus) { sd_bus_flush(bus); sd_bus_unref(bus); } return INT_TO_PTR(r); }
static int stdout_stream_install(Server *s, int fd, StdoutStream **ret) { _cleanup_(stdout_stream_freep) StdoutStream *stream = NULL; sd_id128_t id; int r; assert(s); assert(fd >= 0); r = sd_id128_randomize(&id); if (r < 0) return log_error_errno(r, "Failed to generate stream ID: %m"); stream = new0(StdoutStream, 1); if (!stream) return log_oom(); stream->fd = -1; stream->priority = LOG_INFO; xsprintf(stream->id_field, "_STREAM_ID=" SD_ID128_FORMAT_STR, SD_ID128_FORMAT_VAL(id)); r = getpeercred(fd, &stream->ucred); if (r < 0) return log_error_errno(r, "Failed to determine peer credentials: %m"); if (mac_selinux_use()) { r = getpeersec(fd, &stream->label); if (r < 0 && r != -EOPNOTSUPP) (void) log_warning_errno(r, "Failed to determine peer security context: %m"); } (void) shutdown(fd, SHUT_WR); r = sd_event_add_io(s->event, &stream->event_source, fd, EPOLLIN, stdout_stream_process, stream); if (r < 0) return log_error_errno(r, "Failed to add stream to event loop: %m"); r = sd_event_source_set_priority(stream->event_source, SD_EVENT_PRIORITY_NORMAL+5); if (r < 0) return log_error_errno(r, "Failed to adjust stdout event source priority: %m"); stream->fd = fd; stream->server = s; LIST_PREPEND(stdout_stream, s->stdout_streams, stream); s->n_stdout_streams++; if (ret) *ret = stream; stream = NULL; return 0; }
int main(int argc, char *argv[]) { sd_id128_t id, id2; char t[33]; _cleanup_free_ char *b = NULL; assert_se(sd_id128_randomize(&id) == 0); printf("random: %s\n", sd_id128_to_string(id, t)); assert_se(sd_id128_from_string(t, &id2) == 0); assert_se(sd_id128_equal(id, id2)); if (sd_booted() > 0) { assert_se(sd_id128_get_machine(&id) == 0); printf("machine: %s\n", sd_id128_to_string(id, t)); assert_se(sd_id128_get_boot(&id) == 0); printf("boot: %s\n", sd_id128_to_string(id, t)); } printf("waldi: %s\n", sd_id128_to_string(ID128_WALDI, t)); assert_se(streq(t, STR_WALDI)); assert_se(asprintf(&b, SD_ID128_FORMAT_STR, SD_ID128_FORMAT_VAL(ID128_WALDI)) == 32); printf("waldi2: %s\n", b); assert_se(streq(t, b)); assert_se(sd_id128_from_string(UUID_WALDI, &id) >= 0); assert_se(sd_id128_equal(id, ID128_WALDI)); assert_se(sd_id128_from_string("", &id) < 0); assert_se(sd_id128_from_string("01020304-0506-0708-090a-0b0c0d0e0f101", &id) < 0); assert_se(sd_id128_from_string("01020304-0506-0708-090a-0b0c0d0e0f10-", &id) < 0); assert_se(sd_id128_from_string("01020304-0506-0708-090a0b0c0d0e0f10", &id) < 0); assert_se(sd_id128_from_string("010203040506-0708-090a-0b0c0d0e0f10", &id) < 0); assert_se(id128_is_valid(STR_WALDI)); assert_se(id128_is_valid(UUID_WALDI)); assert_se(!id128_is_valid("")); assert_se(!id128_is_valid("01020304-0506-0708-090a-0b0c0d0e0f101")); assert_se(!id128_is_valid("01020304-0506-0708-090a-0b0c0d0e0f10-")); assert_se(!id128_is_valid("01020304-0506-0708-090a0b0c0d0e0f10")); assert_se(!id128_is_valid("010203040506-0708-090a-0b0c0d0e0f10")); return 0; }
static int make_unit_name(sd_bus *bus, UnitType t, char **ret) { const char *unique, *id; char *p; int r; assert(bus); assert(t >= 0); assert(t < _UNIT_TYPE_MAX); r = sd_bus_get_unique_name(bus, &unique); if (r < 0) { sd_id128_t rnd; /* We couldn't get the unique name, which is a pretty * common case if we are connected to systemd * directly. In that case, just pick a random uuid as * name */ r = sd_id128_randomize(&rnd); if (r < 0) return log_error_errno(r, "Failed to generate random run unit name: %m"); if (asprintf(ret, "run-r" SD_ID128_FORMAT_STR ".%s", SD_ID128_FORMAT_VAL(rnd), unit_type_to_string(t)) < 0) return log_oom(); return 0; } /* We managed to get the unique name, then let's use that to * name our transient units. */ id = startswith(unique, ":1."); if (!id) { log_error("Unique name %s has unexpected format.", unique); return -EINVAL; } p = strjoin("run-u", id, ".", unit_type_to_string(t), NULL); if (!p) return log_oom(); *ret = p; return 0; }
static int parse_argv(int argc, char *argv[]) { enum { ARG_VERSION = 0x100, ARG_ROOT, ARG_LOCALE, ARG_LOCALE_MESSAGES, ARG_TIMEZONE, ARG_HOSTNAME, ARG_MACHINE_ID, ARG_ROOT_PASSWORD, ARG_ROOT_PASSWORD_FILE, ARG_PROMPT, ARG_PROMPT_LOCALE, ARG_PROMPT_TIMEZONE, ARG_PROMPT_HOSTNAME, ARG_PROMPT_ROOT_PASSWORD, ARG_COPY, ARG_COPY_LOCALE, ARG_COPY_TIMEZONE, ARG_COPY_ROOT_PASSWORD, ARG_SETUP_MACHINE_ID, }; static const struct option options[] = { { "help", no_argument, NULL, 'h' }, { "version", no_argument, NULL, ARG_VERSION }, { "root", required_argument, NULL, ARG_ROOT }, { "locale", required_argument, NULL, ARG_LOCALE }, { "locale-messages", required_argument, NULL, ARG_LOCALE_MESSAGES }, { "timezone", required_argument, NULL, ARG_TIMEZONE }, { "hostname", required_argument, NULL, ARG_HOSTNAME }, { "machine-id", required_argument, NULL, ARG_MACHINE_ID }, { "root-password", required_argument, NULL, ARG_ROOT_PASSWORD }, { "root-password-file", required_argument, NULL, ARG_ROOT_PASSWORD_FILE }, { "prompt", no_argument, NULL, ARG_PROMPT }, { "prompt-locale", no_argument, NULL, ARG_PROMPT_LOCALE }, { "prompt-timezone", no_argument, NULL, ARG_PROMPT_TIMEZONE }, { "prompt-hostname", no_argument, NULL, ARG_PROMPT_HOSTNAME }, { "prompt-root-password", no_argument, NULL, ARG_PROMPT_ROOT_PASSWORD }, { "copy", no_argument, NULL, ARG_COPY }, { "copy-locale", no_argument, NULL, ARG_COPY_LOCALE }, { "copy-timezone", no_argument, NULL, ARG_COPY_TIMEZONE }, { "copy-root-password", no_argument, NULL, ARG_COPY_ROOT_PASSWORD }, { "setup-machine-id", no_argument, NULL, ARG_SETUP_MACHINE_ID }, {} }; int r, c; assert(argc >= 0); assert(argv); while ((c = getopt_long(argc, argv, "h", options, NULL)) >= 0) switch (c) { case 'h': help(); return 0; case ARG_VERSION: return version(); case ARG_ROOT: free(arg_root); arg_root = path_make_absolute_cwd(optarg); if (!arg_root) return log_oom(); path_kill_slashes(arg_root); if (path_equal(arg_root, "/")) arg_root = mfree(arg_root); break; case ARG_LOCALE: if (!locale_is_valid(optarg)) { log_error("Locale %s is not valid.", optarg); return -EINVAL; } r = free_and_strdup(&arg_locale, optarg); if (r < 0) return log_oom(); break; case ARG_LOCALE_MESSAGES: if (!locale_is_valid(optarg)) { log_error("Locale %s is not valid.", optarg); return -EINVAL; } r = free_and_strdup(&arg_locale_messages, optarg); if (r < 0) return log_oom(); break; case ARG_TIMEZONE: if (!timezone_is_valid(optarg)) { log_error("Timezone %s is not valid.", optarg); return -EINVAL; } r = free_and_strdup(&arg_timezone, optarg); if (r < 0) return log_oom(); break; case ARG_ROOT_PASSWORD: r = free_and_strdup(&arg_root_password, optarg); if (r < 0) return log_oom(); break; case ARG_ROOT_PASSWORD_FILE: arg_root_password = mfree(arg_root_password); r = read_one_line_file(optarg, &arg_root_password); if (r < 0) return log_error_errno(r, "Failed to read %s: %m", optarg); break; case ARG_HOSTNAME: if (!hostname_is_valid(optarg, true)) { log_error("Host name %s is not valid.", optarg); return -EINVAL; } hostname_cleanup(optarg); r = free_and_strdup(&arg_hostname, optarg); if (r < 0) return log_oom(); break; case ARG_MACHINE_ID: if (sd_id128_from_string(optarg, &arg_machine_id) < 0) { log_error("Failed to parse machine id %s.", optarg); return -EINVAL; } break; case ARG_PROMPT: arg_prompt_locale = arg_prompt_timezone = arg_prompt_hostname = arg_prompt_root_password = true; break; case ARG_PROMPT_LOCALE: arg_prompt_locale = true; break; case ARG_PROMPT_TIMEZONE: arg_prompt_timezone = true; break; case ARG_PROMPT_HOSTNAME: arg_prompt_hostname = true; break; case ARG_PROMPT_ROOT_PASSWORD: arg_prompt_root_password = true; break; case ARG_COPY: arg_copy_locale = arg_copy_timezone = arg_copy_root_password = true; break; case ARG_COPY_LOCALE: arg_copy_locale = true; break; case ARG_COPY_TIMEZONE: arg_copy_timezone = true; break; case ARG_COPY_ROOT_PASSWORD: arg_copy_root_password = true; break; case ARG_SETUP_MACHINE_ID: r = sd_id128_randomize(&arg_machine_id); if (r < 0) return log_error_errno(r, "Failed to generate randomized machine ID: %m"); break; case '?': return -EINVAL; default: assert_not_reached("Unhandled option"); } return 1; }
static void *server(void *p) { struct context *c = p; sd_bus *bus = NULL; sd_id128_t id; bool quit = false; int r; assert_se(sd_id128_randomize(&id) >= 0); assert_se(sd_bus_new(&bus) >= 0); assert_se(sd_bus_set_fd(bus, c->fds[0], c->fds[0]) >= 0); assert_se(sd_bus_set_server(bus, 1, id) >= 0); assert_se(sd_bus_set_anonymous(bus, c->server_anonymous_auth) >= 0); assert_se(sd_bus_negotiate_fds(bus, c->server_negotiate_unix_fds) >= 0); assert_se(sd_bus_start(bus) >= 0); while (!quit) { _cleanup_bus_message_unref_ sd_bus_message *m = NULL, *reply = NULL; r = sd_bus_process(bus, &m); if (r < 0) { log_error("Failed to process requests: %s", strerror(-r)); goto fail; } if (r == 0) { r = sd_bus_wait(bus, (uint64_t) -1); if (r < 0) { log_error("Failed to wait: %s", strerror(-r)); goto fail; } continue; } if (!m) continue; log_info("Got message! member=%s", strna(sd_bus_message_get_member(m))); if (sd_bus_message_is_method_call(m, "org.freedesktop.systemd.test", "Exit")) { assert_se((sd_bus_can_send(bus, 'h') >= 1) == (c->server_negotiate_unix_fds && c->client_negotiate_unix_fds)); r = sd_bus_message_new_method_return(m, &reply); if (r < 0) { log_error("Failed to allocate return: %s", strerror(-r)); goto fail; } quit = true; } else if (sd_bus_message_is_method_call(m, NULL, NULL)) { r = sd_bus_message_new_method_error( m, &reply, &SD_BUS_ERROR_MAKE_CONST(SD_BUS_ERROR_UNKNOWN_METHOD, "Unknown method.")); if (r < 0) { log_error("Failed to allocate return: %s", strerror(-r)); goto fail; } } if (reply) { r = sd_bus_send(bus, reply, NULL); if (r < 0) { log_error("Failed to send reply: %s", strerror(-r)); goto fail; } } } r = 0; fail: if (bus) { sd_bus_flush(bus); sd_bus_unref(bus); } return INT_TO_PTR(r); }
static void test_non_empty(void) { dual_timestamp ts; JournalFile *f; struct iovec iovec; static const char test[] = "TEST1=1", test2[] = "TEST2=2"; Object *o; uint64_t p; sd_id128_t fake_boot_id; char t[] = "/tmp/journal-XXXXXX"; test_setup_logging(LOG_DEBUG); assert_se(mkdtemp(t)); assert_se(chdir(t) >= 0); assert_se(journal_file_open(-1, "test.journal", O_RDWR|O_CREAT, 0666, true, (uint64_t) -1, true, NULL, NULL, NULL, NULL, &f) == 0); assert_se(dual_timestamp_get(&ts)); assert_se(sd_id128_randomize(&fake_boot_id) == 0); iovec.iov_base = (void*) test; iovec.iov_len = strlen(test); assert_se(journal_file_append_entry(f, &ts, NULL, &iovec, 1, NULL, NULL, NULL) == 0); iovec.iov_base = (void*) test2; iovec.iov_len = strlen(test2); assert_se(journal_file_append_entry(f, &ts, NULL, &iovec, 1, NULL, NULL, NULL) == 0); iovec.iov_base = (void*) test; iovec.iov_len = strlen(test); assert_se(journal_file_append_entry(f, &ts, &fake_boot_id, &iovec, 1, NULL, NULL, NULL) == 0); #if HAVE_GCRYPT journal_file_append_tag(f); #endif journal_file_dump(f); assert_se(journal_file_next_entry(f, 0, DIRECTION_DOWN, &o, &p) == 1); assert_se(le64toh(o->entry.seqnum) == 1); assert_se(journal_file_next_entry(f, p, DIRECTION_DOWN, &o, &p) == 1); assert_se(le64toh(o->entry.seqnum) == 2); assert_se(journal_file_next_entry(f, p, DIRECTION_DOWN, &o, &p) == 1); assert_se(le64toh(o->entry.seqnum) == 3); assert_se(sd_id128_equal(o->entry.boot_id, fake_boot_id)); assert_se(journal_file_next_entry(f, p, DIRECTION_DOWN, &o, &p) == 0); assert_se(journal_file_next_entry(f, 0, DIRECTION_DOWN, &o, &p) == 1); assert_se(le64toh(o->entry.seqnum) == 1); assert_se(journal_file_find_data_object(f, test, strlen(test), NULL, &p) == 1); assert_se(journal_file_next_entry_for_data(f, NULL, 0, p, DIRECTION_DOWN, &o, NULL) == 1); assert_se(le64toh(o->entry.seqnum) == 1); assert_se(journal_file_next_entry_for_data(f, NULL, 0, p, DIRECTION_UP, &o, NULL) == 1); assert_se(le64toh(o->entry.seqnum) == 3); assert_se(journal_file_find_data_object(f, test2, strlen(test2), NULL, &p) == 1); assert_se(journal_file_next_entry_for_data(f, NULL, 0, p, DIRECTION_UP, &o, NULL) == 1); assert_se(le64toh(o->entry.seqnum) == 2); assert_se(journal_file_next_entry_for_data(f, NULL, 0, p, DIRECTION_DOWN, &o, NULL) == 1); assert_se(le64toh(o->entry.seqnum) == 2); assert_se(journal_file_find_data_object(f, "quux", 4, NULL, &p) == 0); assert_se(journal_file_move_to_entry_by_seqnum(f, 1, DIRECTION_DOWN, &o, NULL) == 1); assert_se(le64toh(o->entry.seqnum) == 1); assert_se(journal_file_move_to_entry_by_seqnum(f, 3, DIRECTION_DOWN, &o, NULL) == 1); assert_se(le64toh(o->entry.seqnum) == 3); assert_se(journal_file_move_to_entry_by_seqnum(f, 2, DIRECTION_DOWN, &o, NULL) == 1); assert_se(le64toh(o->entry.seqnum) == 2); assert_se(journal_file_move_to_entry_by_seqnum(f, 10, DIRECTION_DOWN, &o, NULL) == 0); journal_file_rotate(&f, true, (uint64_t) -1, true, NULL); journal_file_rotate(&f, true, (uint64_t) -1, true, NULL); (void) journal_file_close(f); log_info("Done..."); if (arg_keep) log_info("Not removing %s", t); else { journal_directory_vacuum(".", 3000000, 0, 0, NULL, true); assert_se(rm_rf(t, REMOVE_ROOT|REMOVE_PHYSICAL) >= 0); } puts("------------------------------------------------------------"); }
int main(int argc, char *argv[]) { sd_id128_t id, id2; char t[33], q[37]; _cleanup_free_ char *b = NULL; _cleanup_close_ int fd = -1; assert_se(sd_id128_randomize(&id) == 0); printf("random: %s\n", sd_id128_to_string(id, t)); assert_se(sd_id128_from_string(t, &id2) == 0); assert_se(sd_id128_equal(id, id2)); if (sd_booted() > 0) { assert_se(sd_id128_get_machine(&id) == 0); printf("machine: %s\n", sd_id128_to_string(id, t)); assert_se(sd_id128_get_boot(&id) == 0); printf("boot: %s\n", sd_id128_to_string(id, t)); } printf("waldi: %s\n", sd_id128_to_string(ID128_WALDI, t)); assert_se(streq(t, STR_WALDI)); assert_se(asprintf(&b, SD_ID128_FORMAT_STR, SD_ID128_FORMAT_VAL(ID128_WALDI)) == 32); printf("waldi2: %s\n", b); assert_se(streq(t, b)); printf("waldi3: %s\n", id128_to_uuid_string(ID128_WALDI, q)); assert_se(streq(q, UUID_WALDI)); b = mfree(b); assert_se(asprintf(&b, ID128_UUID_FORMAT_STR, SD_ID128_FORMAT_VAL(ID128_WALDI)) == 36); printf("waldi4: %s\n", b); assert_se(streq(q, b)); assert_se(sd_id128_from_string(STR_WALDI, &id) >= 0); assert_se(sd_id128_equal(id, ID128_WALDI)); assert_se(sd_id128_from_string(UUID_WALDI, &id) >= 0); assert_se(sd_id128_equal(id, ID128_WALDI)); assert_se(sd_id128_from_string("", &id) < 0); assert_se(sd_id128_from_string("01020304-0506-0708-090a-0b0c0d0e0f101", &id) < 0); assert_se(sd_id128_from_string("01020304-0506-0708-090a-0b0c0d0e0f10-", &id) < 0); assert_se(sd_id128_from_string("01020304-0506-0708-090a0b0c0d0e0f10", &id) < 0); assert_se(sd_id128_from_string("010203040506-0708-090a-0b0c0d0e0f10", &id) < 0); assert_se(id128_is_valid(STR_WALDI)); assert_se(id128_is_valid(UUID_WALDI)); assert_se(!id128_is_valid("")); assert_se(!id128_is_valid("01020304-0506-0708-090a-0b0c0d0e0f101")); assert_se(!id128_is_valid("01020304-0506-0708-090a-0b0c0d0e0f10-")); assert_se(!id128_is_valid("01020304-0506-0708-090a0b0c0d0e0f10")); assert_se(!id128_is_valid("010203040506-0708-090a-0b0c0d0e0f10")); fd = open_tmpfile_unlinkable(NULL, O_RDWR|O_CLOEXEC); assert_se(fd >= 0); /* First, write as UUID */ assert_se(sd_id128_randomize(&id) >= 0); assert_se(id128_write_fd(fd, ID128_UUID, id, false) >= 0); assert_se(lseek(fd, 0, SEEK_SET) == 0); assert_se(id128_read_fd(fd, ID128_PLAIN, &id2) == -EINVAL); assert_se(lseek(fd, 0, SEEK_SET) == 0); assert_se(id128_read_fd(fd, ID128_UUID, &id2) >= 0); assert_se(sd_id128_equal(id, id2)); assert_se(lseek(fd, 0, SEEK_SET) == 0); assert_se(id128_read_fd(fd, ID128_ANY, &id2) >= 0); assert_se(sd_id128_equal(id, id2)); /* Second, write as plain */ assert_se(lseek(fd, 0, SEEK_SET) == 0); assert_se(ftruncate(fd, 0) >= 0); assert_se(sd_id128_randomize(&id) >= 0); assert_se(id128_write_fd(fd, ID128_PLAIN, id, false) >= 0); assert_se(lseek(fd, 0, SEEK_SET) == 0); assert_se(id128_read_fd(fd, ID128_UUID, &id2) == -EINVAL); assert_se(lseek(fd, 0, SEEK_SET) == 0); assert_se(id128_read_fd(fd, ID128_PLAIN, &id2) >= 0); assert_se(sd_id128_equal(id, id2)); assert_se(lseek(fd, 0, SEEK_SET) == 0); assert_se(id128_read_fd(fd, ID128_ANY, &id2) >= 0); assert_se(sd_id128_equal(id, id2)); /* Third, write plain without trailing newline */ assert_se(lseek(fd, 0, SEEK_SET) == 0); assert_se(ftruncate(fd, 0) >= 0); assert_se(sd_id128_randomize(&id) >= 0); assert_se(write(fd, sd_id128_to_string(id, t), 32) == 32); assert_se(lseek(fd, 0, SEEK_SET) == 0); assert_se(id128_read_fd(fd, ID128_UUID, &id2) == -EINVAL); assert_se(lseek(fd, 0, SEEK_SET) == 0); assert_se(id128_read_fd(fd, ID128_PLAIN, &id2) >= 0); assert_se(sd_id128_equal(id, id2)); /* Third, write UUID without trailing newline */ assert_se(lseek(fd, 0, SEEK_SET) == 0); assert_se(ftruncate(fd, 0) >= 0); assert_se(sd_id128_randomize(&id) >= 0); assert_se(write(fd, id128_to_uuid_string(id, q), 36) == 36); assert_se(lseek(fd, 0, SEEK_SET) == 0); assert_se(id128_read_fd(fd, ID128_PLAIN, &id2) == -EINVAL); assert_se(lseek(fd, 0, SEEK_SET) == 0); assert_se(id128_read_fd(fd, ID128_UUID, &id2) >= 0); assert_se(sd_id128_equal(id, id2)); return 0; }
static int generate(char id[34]) { int fd, r; unsigned char *p; sd_id128_t buf; char *q; ssize_t k; const char *vm_id; assert(id); /* First, try reading the D-Bus machine id, unless it is a symlink */ fd = open("/var/lib/dbus/machine-id", O_RDONLY|O_CLOEXEC|O_NOCTTY|O_NOFOLLOW); if (fd >= 0) { k = loop_read(fd, id, 32, false); close_nointr_nofail(fd); if (k >= 32) { id[32] = '\n'; id[33] = 0; log_info("Initializing machine ID from D-Bus machine ID."); return 0; } } /* If that didn't work, see if we are running in qemu/kvm and a * machine ID was passed in via -uuid on the qemu/kvm command * line */ r = detect_vm(&vm_id); if (r > 0 && streq(vm_id, "kvm")) { char uuid[37]; fd = open("/sys/class/dmi/id/product_uuid", O_RDONLY|O_CLOEXEC|O_NOCTTY|O_NOFOLLOW); if (fd >= 0) { k = loop_read(fd, uuid, 36, false); close_nointr_nofail(fd); if (k >= 36) { r = shorten_uuid(id, uuid); if (r >= 0) { log_info("Initializing machine ID from KVM UUID."); return 0; } } } } /* If that didn't work either, see if we are running in a * container, and a machine ID was passed in via * $container_uuid the way libvirt/LXC does it */ r = detect_container(NULL); if (r > 0) { char *e; r = getenv_for_pid(1, "container_uuid", &e); if (r > 0) { if (strlen(e) >= 36) { r = shorten_uuid(id, e); if (r >= 0) { log_info("Initializing machine ID from container UUID."); free(e); return 0; } } free(e); } } /* If that didn't work, generate a random machine id */ r = sd_id128_randomize(&buf); if (r < 0) { log_error("Failed to open /dev/urandom: %s", strerror(-r)); return r; } for (p = buf.bytes, q = id; p < buf.bytes + sizeof(buf); p++, q += 2) { q[0] = hexchar(*p >> 4); q[1] = hexchar(*p & 15); } id[32] = '\n'; id[33] = 0; log_info("Initializing machine ID from random generator."); return 0; }