[gnome-battery-bench] Rework command line client



commit f179b22a32ba89fddff7488d99f45b69a4ee3cb3
Author: Owen W. Taylor <otaylor fishsoup net>
Date:   Fri Jan 2 13:53:21 2015 -0500

    Rework command line client
    
    Rewrite the command parsing using GOptionContext. Use a
    
     gbb <subcommand>
    
    syntax. Rename 'test' to 'monitor'.

 src/commandline.c |  230 +++++++++++++++++++++++++++++++++--------------------
 1 files changed, 142 insertions(+), 88 deletions(-)
---
diff --git a/src/commandline.c b/src/commandline.c
index db6bdd2..36e7919 100644
--- a/src/commandline.c
+++ b/src/commandline.c
@@ -20,27 +20,60 @@
 #include "xinput-wait.h"
 #include "util.h"
 
-void usage(void)
-    __attribute__ ((noreturn));
+static GbbPowerState *start_state;
 
-void
-usage(void)
+static void
+on_power_monitor_changed(GbbPowerMonitor *monitor)
 {
-    die("Usage: gbb [--record|--playback|--remote-playback|--test]");
+    if (start_state == NULL) {
+        start_state = gbb_power_state_copy(gbb_power_monitor_get_state(monitor));
+        return;
+    }
+
+    const GbbPowerState *state = gbb_power_monitor_get_state(monitor);
+    GbbPowerStatistics *statistics = gbb_power_statistics_compute(start_state, state);
+
+    if (statistics->power >= 0)
+        g_print("Power: %.2f W\n", statistics->power);
+    if (statistics->current >= 0)
+        g_print("Current: %.2f A\n", statistics->current);
+    if (statistics->battery_life >= 0) {
+        int h, m, s;
+        break_time(statistics->battery_life, &h, &m, &s);
+        g_print("Predicted battery life: %.0fs (%d:%02d:%02d)\n",
+                statistics->battery_life, h, m, s);
+    }
+    if (statistics->battery_life_design >= 0) {
+        int h, m, s;
+        break_time(statistics->battery_life_design, &h, &m, &s);
+        g_print("Predicted battery life (design): %.0fs (%d:%02d:%02d)\n",
+                statistics->battery_life_design, h, m, s);
+    }
+
+    gbb_power_statistics_free(statistics);
+
 }
 
-static void
-record(void)
+static GOptionEntry monitor_options[] =
 {
-    GbbEventRecorder *recorder;
+    { NULL }
+};
 
-    Display *display = XOpenDisplay(NULL);
-    if (!display)
-        die("Can't open X display %s", XDisplayName(NULL));
+static int
+monitor(int argc, char **argv)
+{
+    GbbPowerMonitor *monitor;
+    GMainLoop *loop;
 
-    recorder = gbb_event_recorder_new(display, NULL);
-    gbb_event_recorder_record(recorder);
-    gbb_event_recorder_free(recorder);
+    monitor = gbb_power_monitor_new();
+
+    g_signal_connect(monitor, "changed",
+                     G_CALLBACK(on_power_monitor_changed), NULL);
+
+    loop = g_main_loop_new (NULL, FALSE);
+    g_main_loop_run (loop);
+
+    return 0;
 }
 
 static void
@@ -67,9 +100,10 @@ on_player_ready(GObject      *source_object,
     g_main_loop_quit(loop);
 }
 
-static void
-do_playback(GbbEventPlayer *player,
-            const char     *filename)
+static int
+do_play(GbbEventPlayer *player,
+        int             argc,
+        char          **argv)
 {
     GMainLoop *loop = g_main_loop_new (NULL, FALSE);
 
@@ -79,102 +113,122 @@ do_playback(GbbEventPlayer *player,
 
     g_signal_connect(player, "finished",
                      G_CALLBACK(on_player_finished), loop);
-    gbb_event_player_play_file(player, filename);
+    gbb_event_player_play_file(player, argv[1]);
     g_main_loop_run (loop);
+
+    return 0;
 }
 
-static void
-playback(const char *filename)
+static GOptionEntry play_options[] =
 {
-    GbbEventPlayer *player = GBB_EVENT_PLAYER(gbb_evdev_player_new("Gnome Battery Bench Test"));
-    do_playback(player, filename);
-}
+    { NULL }
+};
 
-static void
-remote_playback(const char *filename)
+static int
+play(int argc, char **argv)
 {
     GbbEventPlayer *player = GBB_EVENT_PLAYER(gbb_remote_player_new("Gnome Battery Bench Test"));
-    do_playback(player, filename);
+    return do_play(player, argc, argv);
 }
 
-static GbbPowerState *start_state;
+static int
+play_local(int argc, char **argv)
+{
+    GbbEventPlayer *player = GBB_EVENT_PLAYER(gbb_evdev_player_new("Gnome Battery Bench Test"));
+    return do_play(player, argc, argv);
+}
 
-static void
-on_power_monitor_changed(GbbPowerMonitor *monitor)
+static char *record_output;
+
+static GOptionEntry record_options[] =
 {
-    if (start_state == NULL) {
-        start_state = gbb_power_state_copy(gbb_power_monitor_get_state(monitor));
-        return;
-    }
+    { "output", 'o', 0, G_OPTION_ARG_FILENAME, &record_output, "Output file", "FILENAME" },
+    { NULL }
+};
 
-    const GbbPowerState *state = gbb_power_monitor_get_state(monitor);
-    GbbPowerStatistics *statistics = gbb_power_statistics_compute(start_state, state);
+static int
+record(int argc, char **argv)
+{
+    GbbEventRecorder *recorder;
 
-    if (statistics->power >= 0)
-        g_print("Power: %.2f W\n", statistics->power);
-    if (statistics->current >= 0)
-        g_print("Current: %.2f A\n", statistics->current);
-    if (statistics->battery_life >= 0) {
-        int h, m, s;
-        break_time(statistics->battery_life, &h, &m, &s);
-        g_print("Predicted battery life: %.0fs (%d:%02d:%02d)\n",
-                statistics->battery_life, h, m, s);
-    }
-    if (statistics->battery_life_design >= 0) {
-        int h, m, s;
-        break_time(statistics->battery_life_design, &h, &m, &s);
-        g_print("Predicted battery life (design): %.0fs (%d:%02d:%02d)\n",
-                statistics->battery_life_design, h, m, s);
-    }
+    Display *display = XOpenDisplay(NULL);
+    if (!display)
+        die("Can't open X display %s", XDisplayName(NULL));
 
-    gbb_power_statistics_free(statistics);
+    recorder = gbb_event_recorder_new(display, record_output);
+    gbb_event_recorder_record(recorder);
+    gbb_event_recorder_free(recorder);
 
+    return 0;
 }
 
+typedef struct {
+    const char *command;
+    const GOptionEntry *options;
+    int (*run) (int argc, char **argv);
+    int min_args;
+    int max_args;
+    const char *param_string;
+} Subcommand;
+
+Subcommand subcommands[] = {
+    { "monitor",      monitor_options, monitor, 0, 0 },
+    { "play",         play_options, play, 1, 1, "FILENAME" },
+    { "play-local",   play_options, play_local, 1, 1, "FILENAME" },
+    { "record",       record_options, record, 0, 0 },
+    { NULL }
+};
+
+static void global_usage(void) G_GNUC_NORETURN;
+
 static void
-test(void)
+global_usage(void)
 {
-    GbbPowerMonitor *monitor;
-    GMainLoop *loop;
-
-    monitor = gbb_power_monitor_new();
-
-    g_signal_connect(monitor, "changed",
-                     G_CALLBACK(on_power_monitor_changed), NULL);
-
-    loop = g_main_loop_new (NULL, FALSE);
-    g_main_loop_run (loop);
+    int i;
+    fprintf(stderr, "Usage: [");
+    for (i = 0; subcommands[i].command; i++) {
+        fprintf(stderr,
+                "%s%s", i == 0 ? "" : "|",
+                subcommands[i].command);
+    }
+    fprintf(stderr, "]\n");
+    exit(1);
 }
 
 int
 main(int argc, char **argv)
 {
+    int i;
+
     if (argc < 2)
-        usage();
-
-    if (strcmp(argv[1], "--record") == 0) {
-        if (argc != 2)
-            usage();
-
-        record();
-    } else if (strcmp(argv[1], "--playback") == 0) {
-        if (argc != 3)
-            usage();
-
-        playback(argv[2]);
-    } else if (strcmp(argv[1], "--remote-playback") == 0) {
-        if (argc != 3)
-            usage();
-
-        remote_playback(argv[2]);
-    } else if (strcmp(argv[1], "--test") == 0) {
-        if (argc != 2)
-            usage();
-
-        test();
-    } else {
-        usage();
+        global_usage();
+
+    for (i = 0; subcommands[i].command; i++) {
+        Subcommand *subcommand = &subcommands[i];
+
+        if (strcmp(subcommand->command, argv[1]) == 0) {
+            char *command = g_strconcat("gbb ", subcommand->command, NULL);
+            argv[1] = command;
+            argv += 1;
+            argc -= 1;
+
+            GOptionContext *context = g_option_context_new(subcommand->param_string);
+            GError *error = NULL;
+
+            g_option_context_add_main_entries(context, subcommand->options, NULL);
+            if (!g_option_context_parse (context, &argc, &argv, &error))
+                die("option parsing failed: %s", error->message);
+
+            if (argc < 1 + subcommand->min_args ||
+                argc > 1 + subcommand->max_args) {
+                char *help = g_option_context_get_help (context, TRUE, NULL);
+                fprintf(stderr, "%s", help);
+                exit(1);
+            }
+
+            return subcommand->run(argc, argv);
+        }
     }
 
-    return 0;
+    global_usage();
 }


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]