+ r = sd_bus_message_enter_container(m, SD_BUS_TYPE_ARRAY, "(st)");
+ if (r < 0)
+ return bus_log_parse_error(r);
+
+ while ((r = sd_bus_message_read(m, "(st)", &path, &weight)) > 0)
+ printf("%s=%s %" PRIu64 "\n", name, strna(path), weight);
+ if (r < 0)
+ return bus_log_parse_error(r);
+
+ r = sd_bus_message_exit_container(m);
+ if (r < 0)
+ return bus_log_parse_error(r);
+
+ return 0;
+
+ } else if (contents[1] == SD_BUS_TYPE_STRUCT_BEGIN && (streq(name, "BlockIOReadBandwidth") || streq(name, "BlockIOWriteBandwidth"))) {
+ const char *path;
+ uint64_t bandwidth;
+
+ r = sd_bus_message_enter_container(m, SD_BUS_TYPE_ARRAY, "(st)");
+ if (r < 0)
+ return bus_log_parse_error(r);
+
+ while ((r = sd_bus_message_read(m, "(st)", &path, &bandwidth)) > 0)
+ printf("%s=%s %" PRIu64 "\n", name, strna(path), bandwidth);
+ if (r < 0)
+ return bus_log_parse_error(r);
+
+ r = sd_bus_message_exit_container(m);
+ if (r < 0)
+ return bus_log_parse_error(r);
+
+ return 0;
+ }
+
+ break;
+ }
+
+ r = bus_print_property(name, m, arg_all);
+ if (r < 0)
+ return bus_log_parse_error(r);
+
+ if (r == 0) {
+ r = sd_bus_message_skip(m, contents);
+ if (r < 0)
+ return bus_log_parse_error(r);
+
+ if (arg_all)
+ printf("%s=[unprintable]\n", name);
+ }
+
+ return 0;
+}
+
+static int show_one(
+ const char *verb,
+ sd_bus *bus,
+ const char *path,
+ bool show_properties,
+ bool *new_line,
+ bool *ellipsized) {
+
+ _cleanup_bus_message_unref_ sd_bus_message *reply = NULL;
+ _cleanup_bus_error_free_ sd_bus_error error = SD_BUS_ERROR_NULL;
+ UnitStatusInfo info = {};
+ ExecStatusInfo *p;
+ int r;
+
+ assert(path);
+ assert(new_line);
+
+ r = sd_bus_call_method(
+ bus,
+ "org.freedesktop.systemd1",
+ path,
+ "org.freedesktop.DBus.Properties",
+ "GetAll",
+ &error,
+ &reply,
+ "s", "");
+ if (r < 0) {
+ log_error("Failed to get properties: %s", bus_error_message(&error, r));
+ return r;
+ }
+
+ r = sd_bus_message_enter_container(reply, SD_BUS_TYPE_ARRAY, "{sv}");
+ if (r < 0)
+ return bus_log_parse_error(r);
+
+ if (*new_line)
+ printf("\n");
+
+ *new_line = true;
+
+ while ((r = sd_bus_message_enter_container(reply, SD_BUS_TYPE_DICT_ENTRY, "sv")) > 0) {
+ const char *name, *contents;
+
+ r = sd_bus_message_read(reply, "s", &name);
+ if (r < 0)
+ return bus_log_parse_error(r);
+
+ r = sd_bus_message_peek_type(reply, NULL, &contents);
+ if (r < 0)
+ return bus_log_parse_error(r);
+
+ r = sd_bus_message_enter_container(reply, SD_BUS_TYPE_VARIANT, contents);
+ if (r < 0)
+ return bus_log_parse_error(r);
+
+ if (show_properties)
+ r = print_property(name, reply, contents);
+ else
+ r = status_property(name, reply, &info, contents);
+ if (r < 0)
+ return r;
+
+ r = sd_bus_message_exit_container(reply);
+ if (r < 0)
+ return bus_log_parse_error(r);
+
+ r = sd_bus_message_exit_container(reply);
+ if (r < 0)
+ return bus_log_parse_error(r);
+ }
+ if (r < 0)
+ return bus_log_parse_error(r);
+
+ r = sd_bus_message_exit_container(reply);
+ if (r < 0)
+ return bus_log_parse_error(r);
+
+ r = 0;
+
+ if (!show_properties) {
+ if (streq(verb, "help"))
+ show_unit_help(&info);
+ else
+ print_status_info(&info, ellipsized);
+ }
+
+ strv_free(info.documentation);
+ strv_free(info.dropin_paths);
+ strv_free(info.listen);
+
+ if (!streq_ptr(info.active_state, "active") &&
+ !streq_ptr(info.active_state, "reloading") &&
+ streq(verb, "status")) {
+ /* According to LSB: "program not running" */
+ /* 0: program is running or service is OK
+ * 1: program is dead and /var/run pid file exists
+ * 2: program is dead and /var/lock lock file exists
+ * 3: program is not running
+ * 4: program or service status is unknown
+ */
+ if (info.pid_file && access(info.pid_file, F_OK) == 0)
+ r = 1;
+ else
+ r = 3;
+ }
+
+ while ((p = info.exec)) {
+ LIST_REMOVE(exec, info.exec, p);
+ exec_status_info_free(p);
+ }
+
+ return r;
+}
+
+static int get_unit_dbus_path_by_pid(
+ sd_bus *bus,
+ uint32_t pid,
+ char **unit) {
+
+ _cleanup_bus_error_free_ sd_bus_error error = SD_BUS_ERROR_NULL;
+ _cleanup_bus_message_unref_ sd_bus_message *reply = NULL;
+ int r;
+
+ r = sd_bus_call_method(
+ bus,
+ "org.freedesktop.systemd1",
+ "/org/freedesktop/systemd1",
+ "org.freedesktop.systemd1.Manager",
+ "GetUnitByPID",
+ &error,
+ &reply,
+ "u", pid);
+ if (r < 0) {
+ log_error("Failed to get unit for PID %lu: %s", (unsigned long) pid, bus_error_message(&error, r));
+ return r;
+ }
+
+ r = sd_bus_message_read(reply, "o", unit);
+ if (r < 0)
+ return bus_log_parse_error(r);