--- src/analyze/systemd-analyze.c | 119 +++++++++++++++++++++++------------------ 1 files changed, 66 insertions(+), 53 deletions(-)
diff --git a/src/analyze/systemd-analyze.c b/src/analyze/systemd-analyze.c index 01bf55e..3dcde30 100644 --- a/src/analyze/systemd-analyze.c +++ b/src/analyze/systemd-analyze.c @@ -70,7 +70,7 @@ struct boot_times { usec_t userspace_time; usec_t finish_time; }; -struct unit_times { +struct unit_stat { char *name; usec_t ixt; usec_t iet; @@ -116,14 +116,44 @@ static int bus_get_uint64_property(DBusConnection *bus, const char *path, const return 0; } +static int aquire_time_data (DBusConnection *bus, struct unit_info *u, struct unit_stat *t) { + if (bus_get_uint64_property(bus, u->unit_path, + "org.freedesktop.systemd1.Unit", + "InactiveExitTimestampMonotonic", + &t->ixt) < 0 || + bus_get_uint64_property(bus, u->unit_path, + "org.freedesktop.systemd1.Unit", + "ActiveEnterTimestampMonotonic", + &t->aet) < 0 || + bus_get_uint64_property(bus, u->unit_path, + "org.freedesktop.systemd1.Unit", + "ActiveExitTimestampMonotonic", + &t->axt) < 0 || + bus_get_uint64_property(bus, u->unit_path, + "org.freedesktop.systemd1.Unit", + "InactiveEnterTimestampMonotonic", + &t->iet) < 0) { + return -EIO; + } + + if (t->aet >= t->ixt) + t->time = t->aet - t->ixt; + else if (t->iet >= t->ixt) + t->time = t->iet - t->ixt; + else + t->time = 0; + + return 0; +} + static int compare_unit_time(const void *a, const void *b) { - return compare(((struct unit_times *)b)->time, - ((struct unit_times *)a)->time); + return compare(((struct unit_stat *)b)->time, + ((struct unit_stat *)a)->time); } static int compare_unit_start(const void *a, const void *b) { - return compare(((struct unit_times *)a)->ixt, - ((struct unit_times *)b)->ixt); + return compare(((struct unit_stat *)a)->ixt, + ((struct unit_stat *)b)->ixt); } static int get_os_name(char **_n) { @@ -141,8 +171,8 @@ static int get_os_name(char **_n) { return 0; } -static void free_unit_times(struct unit_times *t, unsigned n) { - struct unit_times *p; +static void free_unit_stats(struct unit_stat *t, unsigned n) { + struct unit_stat *p; for (p = t; p < t + n; p++) free(p->name); @@ -150,11 +180,11 @@ static void free_unit_times(struct unit_times *t, unsigned n) { free(t); } -static int acquire_time_data(DBusConnection *bus, struct unit_times **out) { +static int acquire_stat_data(DBusConnection *bus, struct unit_stat **out) { _cleanup_dbus_message_unref_ DBusMessage *reply = NULL; DBusMessageIter iter, sub; int r, c = 0, n_units = 0; - struct unit_times *unit_times = NULL; + struct unit_stat *unit_stat = NULL; r = bus_method_call_with_reply( bus, @@ -180,7 +210,7 @@ static int acquire_time_data(DBusConnection *bus, struct unit_times **out) { dbus_message_iter_get_arg_type(&sub) != DBUS_TYPE_INVALID; dbus_message_iter_next(&sub)) { struct unit_info u; - struct unit_times *t; + struct unit_stat *t; if (dbus_message_iter_get_arg_type(&sub) != DBUS_TYPE_STRUCT) { log_error("Failed to parse reply."); @@ -189,19 +219,19 @@ static int acquire_time_data(DBusConnection *bus, struct unit_times **out) { } if (c >= n_units) { - struct unit_times *w; + struct unit_stat *w; n_units = MAX(2*c, 16); - w = realloc(unit_times, sizeof(struct unit_times) * n_units); + w = realloc(unit_stat, sizeof(struct unit_stat) * n_units); if (!w) { r = log_oom(); goto fail; } - unit_times = w; + unit_stat = w; } - t = unit_times+c; + t = unit_stat+c; t->name = NULL; r = bus_parse_unit_info(&sub, &u); @@ -210,35 +240,9 @@ static int acquire_time_data(DBusConnection *bus, struct unit_times **out) { assert_cc(sizeof(usec_t) == sizeof(uint64_t)); - if (bus_get_uint64_property(bus, u.unit_path, - "org.freedesktop.systemd1.Unit", - "InactiveExitTimestampMonotonic", - &t->ixt) < 0 || - bus_get_uint64_property(bus, u.unit_path, - "org.freedesktop.systemd1.Unit", - "ActiveEnterTimestampMonotonic", - &t->aet) < 0 || - bus_get_uint64_property(bus, u.unit_path, - "org.freedesktop.systemd1.Unit", - "ActiveExitTimestampMonotonic", - &t->axt) < 0 || - bus_get_uint64_property(bus, u.unit_path, - "org.freedesktop.systemd1.Unit", - "InactiveEnterTimestampMonotonic", - &t->iet) < 0) { - r = -EIO; + r = aquire_time_data (bus, &u, t); + if (r < 0) goto fail; - } - - if (t->aet >= t->ixt) - t->time = t->aet - t->ixt; - else if (t->iet >= t->ixt) - t->time = t->iet - t->ixt; - else - t->time = 0; - - if (t->ixt == 0) - continue; t->name = strdup(u.id); if (t->name == NULL) { @@ -248,11 +252,11 @@ static int acquire_time_data(DBusConnection *bus, struct unit_times **out) { c++; } - *out = unit_times; + *out = unit_stat; return c; fail: - free_unit_times(unit_times, (unsigned) c); + free_unit_stats(unit_stat, (unsigned) c); return r; } @@ -377,13 +381,13 @@ static void svg_graph_box(double height, double begin, double end) { } static int analyze_plot(DBusConnection *bus) { - struct unit_times *times; + struct unit_stat *times; struct boot_times *boot; struct utsname name; int n, m = 1, y=0; double width; _cleanup_free_ char *pretty_times = NULL, *osname = NULL; - struct unit_times *u; + struct unit_stat *u; n = acquire_boot_times(bus, &boot); if (n < 0) @@ -396,11 +400,11 @@ static int analyze_plot(DBusConnection *bus) { get_os_name(&osname); assert_se(uname(&name) >= 0); - n = acquire_time_data(bus, ×); + n = acquire_stat_data(bus, ×); if (n <= 0) return n; - qsort(times, n, sizeof(struct unit_times), compare_unit_start); + qsort(times, n, sizeof(struct unit_stat), compare_unit_start); width = SCALE_X * (boot->firmware_time + boot->finish_time); if (width < 800.0) @@ -421,6 +425,9 @@ static int analyze_plot(DBusConnection *bus) { for (u = times; u < times + n; u++) { double len; + if (u->ixt == 0) + continue; + if (u->ixt < boot->userspace_time || u->ixt > boot->finish_time) { free(u->name); @@ -520,6 +527,9 @@ static int analyze_plot(DBusConnection *bus) { char ts[FORMAT_TIMESPAN_MAX]; bool b; + if (u->ixt == 0) + continue; + if (!u->name) continue; @@ -539,30 +549,33 @@ static int analyze_plot(DBusConnection *bus) { svg("</svg>"); - free_unit_times(times, (unsigned) n); + free_unit_stats(times, (unsigned) n); return 0; } static int analyze_blame(DBusConnection *bus) { - struct unit_times *times; + struct unit_stat *times; unsigned i; int n; - n = acquire_time_data(bus, ×); + n = acquire_stat_data(bus, ×); if (n <= 0) return n; - qsort(times, n, sizeof(struct unit_times), compare_unit_time); + qsort(times, n, sizeof(struct unit_stat), compare_unit_time); for (i = 0; i < (unsigned) n; i++) { char ts[FORMAT_TIMESPAN_MAX]; + if (times[i].ixt == 0) + continue; + if (times[i].time > 0) printf("%16s %s\n", format_timespan(ts, sizeof(ts), times[i].time), times[i].name); } - free_unit_times(times, (unsigned) n); + free_unit_stats(times, (unsigned) n); return 0; } -- 1.7.2.5 _______________________________________________ systemd-devel mailing list systemd-devel@lists.freedesktop.org http://lists.freedesktop.org/mailman/listinfo/systemd-devel