[systemd-devel] [PATCH] cgtop: Add cpu time opt and become stdout sensitive
Umut Tezduyar
umut at tezduyar.com
Tue Apr 2 09:52:16 PDT 2013
---
src/cgtop/cgtop.c | 122 ++++++++++++++++++++++++++++++++++++++---------------
1 files changed, 88 insertions(+), 34 deletions(-)
diff --git a/src/cgtop/cgtop.c b/src/cgtop/cgtop.c
index eebebf0..f124826 100644
--- a/src/cgtop/cgtop.c
+++ b/src/cgtop/cgtop.c
@@ -19,9 +19,11 @@
along with systemd; If not, see <http://www.gnu.org/licenses/>.
***/
+#define __STDC_FORMAT_MACROS
#include <errno.h>
#include <string.h>
#include <stdlib.h>
+#include <stdint.h>
#include <unistd.h>
#include <alloca.h>
#include <getopt.h>
@@ -69,6 +71,11 @@ static enum {
ORDER_IO
} arg_order = ORDER_CPU;
+static enum {
+ CPU_PERCENT,
+ CPU_TIME,
+} arg_cpu_type = CPU_PERCENT;
+
static void group_free(Group *g) {
assert(g);
@@ -372,16 +379,22 @@ static int group_compare(const void*a, const void *b) {
return 1;
if (arg_order == ORDER_CPU) {
- if (x->cpu_valid && y->cpu_valid) {
-
- if (x->cpu_fraction > y->cpu_fraction)
+ if (arg_cpu_type == CPU_PERCENT) {
+ if (x->cpu_valid && y->cpu_valid) {
+ if (x->cpu_fraction > y->cpu_fraction)
+ return -1;
+ else if (x->cpu_fraction < y->cpu_fraction)
+ return 1;
+ } else if (x->cpu_valid)
return -1;
- else if (x->cpu_fraction < y->cpu_fraction)
+ else if (y->cpu_valid)
return 1;
- } else if (x->cpu_valid)
- return -1;
- else if (y->cpu_valid)
- return 1;
+ } else {
+ if (x->cpu_usage > y->cpu_usage)
+ return -1;
+ else if (x->cpu_usage < y->cpu_usage)
+ return 1;
+ }
}
if (arg_order == ORDER_TASKS) {
@@ -428,13 +441,18 @@ static int display(Hashmap *a) {
Iterator i;
Group *g;
Group **array;
- unsigned rows, path_columns, n = 0, j;
+ signed path_columns;
+ unsigned rows, n = 0, j, maxtcpu = 0, maxtpath = 0;
+ char cpu_title[21];
+ const char *on = on_tty() ? ANSI_HIGHLIGHT_ON : "";
+ const char *off = on_tty() ? ANSI_HIGHLIGHT_OFF : "";
assert(a);
/* Set cursor to top left corner and clear screen */
- fputs("\033[H"
- "\033[2J", stdout);
+ if (on_tty())
+ fputs("\033[H"
+ "\033[2J", stdout);
array = alloca(sizeof(Group*) * hashmap_size(a));
@@ -444,33 +462,51 @@ static int display(Hashmap *a) {
qsort(array, n, sizeof(Group*), group_compare);
+ /* Find the longest names in one run */
+ for (j = 0; j < n; j++) {
+ unsigned cputlen, pathtlen;
+ snprintf(cpu_title, sizeof(cpu_title), "%"PRIu64, array[j]->cpu_usage);
+ cputlen = strlen(cpu_title);
+ maxtcpu = MAX(maxtcpu, cputlen);
+ pathtlen = strlen(array[j]->path);
+ maxtpath = MAX(maxtpath, pathtlen);
+ }
+
+ if (arg_cpu_type == CPU_PERCENT)
+ snprintf(cpu_title, sizeof(cpu_title), "%6s", "%CPU");
+ else
+ snprintf(cpu_title, sizeof(cpu_title), "%*s", maxtcpu, "CPU Time");
+
rows = lines();
if (rows <= 10)
rows = 10;
- path_columns = columns() - 42;
- if (path_columns < 10)
- path_columns = 10;
-
- printf("%s%-*s%s %s%7s%s %s%6s%s %s%8s%s %s%8s%s %s%8s%s\n\n",
- arg_order == ORDER_PATH ? ANSI_HIGHLIGHT_ON : "", path_columns, "Path",
- arg_order == ORDER_PATH ? ANSI_HIGHLIGHT_OFF : "",
- arg_order == ORDER_TASKS ? ANSI_HIGHLIGHT_ON : "", "Tasks",
- arg_order == ORDER_TASKS ? ANSI_HIGHLIGHT_OFF : "",
- arg_order == ORDER_CPU ? ANSI_HIGHLIGHT_ON : "", "%CPU",
- arg_order == ORDER_CPU ? ANSI_HIGHLIGHT_OFF : "",
- arg_order == ORDER_MEMORY ? ANSI_HIGHLIGHT_ON : "", "Memory",
- arg_order == ORDER_MEMORY ? ANSI_HIGHLIGHT_OFF : "",
- arg_order == ORDER_IO ? ANSI_HIGHLIGHT_ON : "", "Input/s",
- arg_order == ORDER_IO ? ANSI_HIGHLIGHT_OFF : "",
- arg_order == ORDER_IO ? ANSI_HIGHLIGHT_ON : "", "Output/s",
- arg_order == ORDER_IO ? ANSI_HIGHLIGHT_OFF : "");
+ if (on_tty()) {
+ path_columns = columns() - 36 - strlen(cpu_title);
+ if (path_columns < 10)
+ path_columns = 10;
+ } else
+ path_columns = maxtpath;
+
+ printf("%s%-*s%s %s%7s%s %s%s%s %s%8s%s %s%8s%s %s%8s%s\n\n",
+ arg_order == ORDER_PATH ? on : "", path_columns, "Path",
+ arg_order == ORDER_PATH ? off : "",
+ arg_order == ORDER_TASKS ? on : "", "Tasks",
+ arg_order == ORDER_TASKS ? off : "",
+ arg_order == ORDER_CPU ? on : "", cpu_title,
+ arg_order == ORDER_CPU ? off : "",
+ arg_order == ORDER_MEMORY ? on : "", "Memory",
+ arg_order == ORDER_MEMORY ? off : "",
+ arg_order == ORDER_IO ? on : "", "Input/s",
+ arg_order == ORDER_IO ? off : "",
+ arg_order == ORDER_IO ? on : "", "Output/s",
+ arg_order == ORDER_IO ? off : "");
for (j = 0; j < n; j++) {
char *p;
char m[FORMAT_BYTES_MAX];
- if (j + 5 > rows)
+ if (on_tty() && j + 5 > rows)
break;
g = array[j];
@@ -484,10 +520,13 @@ static int display(Hashmap *a) {
else
fputs(" -", stdout);
- if (g->cpu_valid)
- printf(" %6.1f", g->cpu_fraction*100);
+ if (arg_cpu_type == CPU_PERCENT)
+ if (g->cpu_valid)
+ printf(" %6.1f", g->cpu_fraction*100);
+ else
+ fputs(" -", stdout);
else
- fputs(" -", stdout);
+ printf(" %*"PRIu64, maxtcpu, g->cpu_usage);
if (g->memory_valid)
printf(" %8s", format_bytes(m, sizeof(m), g->memory));
@@ -519,6 +558,7 @@ static void help(void) {
" -c Order by CPU load\n"
" -m Order by memory load\n"
" -i Order by IO load\n"
+ " --cpu=TYPE time or percentage (default) as CPU type\n"
" -d --delay=DELAY Specify delay\n"
" -n --iterations=N Run for N iterations before exiting\n"
" -b --batch Run in batch mode, accepting no input\n"
@@ -535,6 +575,7 @@ static int parse_argv(int argc, char *argv[]) {
enum {
ARG_VERSION = 0x100,
ARG_DEPTH,
+ ARG_CPU_TYPE
};
static const struct option options[] = {
@@ -544,6 +585,7 @@ static int parse_argv(int argc, char *argv[]) {
{ "iterations", required_argument, NULL, 'n' },
{ "batch", no_argument, NULL, 'b' },
{ "depth", required_argument, NULL, ARG_DEPTH },
+ { "cpu", optional_argument, NULL, ARG_CPU_TYPE},
{ NULL, 0, NULL, 0 }
};
@@ -565,6 +607,17 @@ static int parse_argv(int argc, char *argv[]) {
version();
return 0;
+ case ARG_CPU_TYPE:
+ if (optarg) {
+ if (strcmp(optarg, "time") == 0)
+ arg_cpu_type = CPU_TIME;
+ else if (strcmp(optarg, "percentage") == 0)
+ arg_cpu_type = CPU_PERCENT;
+ else
+ return -EINVAL;
+ }
+ break;
+
case ARG_DEPTH:
r = safe_atou(optarg, &arg_depth);
if (r < 0) {
@@ -656,6 +709,9 @@ int main(int argc, char *argv[]) {
signal(SIGWINCH, columns_lines_cache_reset);
+ if (!on_tty())
+ arg_iterations = 1;
+
while (!quit) {
Hashmap *c;
usec_t t;
@@ -777,8 +833,6 @@ int main(int argc, char *argv[]) {
}
}
- log_info("Exiting.");
-
r = 0;
finish:
--
1.7.2.5
More information about the systemd-devel
mailing list