Support non-builtin commands

* Support executing commands in the path
 * This makes 'ostree-pull' work as 'ostree pull'
This commit is contained in:
Stef Walter 2012-08-10 15:55:26 +02:00
parent 179fc65947
commit 66c8a1d3f6
3 changed files with 92 additions and 18 deletions

View File

@ -24,6 +24,7 @@
#include <gio/gio.h>
#include <errno.h>
#include <string.h>
#include "ot-main.h"
@ -52,9 +53,62 @@ static OstreeBuiltin builtins[] = {
{ NULL }
};
static int
exec_external (int argc,
char **argv,
GError **error)
{
gchar *command;
gchar *tmp;
int errn;
command = g_strdup_printf ("ostree-%s", argv[1]);
tmp = argv[1];
argv[1] = command;
execvp (command, argv + 1);
errn = errno;
argv[1] = tmp;
g_free (command);
if (errn == ENOENT)
{
g_set_error (error, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED,
"Unknown command: '%s'", argv[1]);
}
else
{
g_set_error (error, G_FILE_ERROR, g_file_error_from_errno (errn),
"Failed to execute command: %s", g_strerror (errn));
}
return 1;
}
int
main (int argc,
char **argv)
{
return ostree_main (argc, argv, builtins);
GError *error = NULL;
int ret;
ret = ostree_run (argc, argv, builtins, &error);
if (g_error_matches (error, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED))
{
g_clear_error (&error);
ret = exec_external (argc, argv, &error);
}
if (g_error_matches (error, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED))
ostree_usage (argv, builtins, TRUE);
if (error != NULL)
{
g_printerr ("%s\n", error->message);
g_error_free (error);
}
return ret;
}

View File

@ -29,8 +29,8 @@
#include "ot-main.h"
#include "otutil.h"
static int
usage (char **argv, OstreeBuiltin *builtins, gboolean is_error)
int
ostree_usage (char **argv, OstreeBuiltin *builtins, gboolean is_error)
{
OstreeBuiltin *builtin = builtins;
void (*print_func) (const gchar *format, ...);
@ -72,17 +72,11 @@ prep_builtin_argv (const char *builtin,
*out_argv = cmd_argv;
}
static void
set_error_print_usage (GError **error, OstreeBuiltin *builtins, const char *msg, char **argv)
{
g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_FAILED, msg);
usage (argv, builtins, TRUE);
}
int
ostree_main (int argc,
char **argv,
OstreeBuiltin *builtins)
ostree_run (int argc,
char **argv,
OstreeBuiltin *builtins,
GError **res_error)
{
OstreeBuiltin *builtin;
GError *error = NULL;
@ -105,7 +99,7 @@ ostree_main (int argc,
g_set_prgname (argv[0]);
if (argc < 2)
return usage (argv, builtins, 1);
return ostree_usage (argv, builtins, 1);
am_root = getuid () == 0;
have_repo_arg = g_str_has_prefix (argv[1], "--repo=");
@ -157,13 +151,15 @@ ostree_main (int argc,
if (!builtin->name)
{
ot_lfree char *msg = g_strdup_printf ("Unknown command '%s'", cmd);
set_error_print_usage (&error, builtins, msg, argv);
g_set_error_literal (&error, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED, msg);
goto out;
}
if (repo == NULL && !(builtin->flags & OSTREE_BUILTIN_FLAG_NO_REPO))
{
set_error_print_usage (&error, builtins, "Command requires a --repo argument", argv);
g_set_error_literal (&error, G_IO_ERROR, G_IO_ERROR_FAILED,
"Command requires a --repo argument");
ostree_usage (argv, builtins, TRUE);
goto out;
}
@ -177,9 +173,30 @@ ostree_main (int argc,
g_clear_object (&repo_file);
if (error)
{
g_printerr ("%s\n", error->message);
g_clear_error (&error);
g_propagate_error (res_error, error);
return 1;
}
return 0;
}
int
ostree_main (int argc,
char **argv,
OstreeBuiltin *builtins)
{
GError *error = NULL;
int ret;
ret = ostree_run (argc, argv, builtins, &error);
if (g_error_matches (error, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED))
ostree_usage (argv, builtins, TRUE);
if (error)
{
g_printerr ("%s\n", error->message);
g_error_free (error);
}
return ret;
}

View File

@ -35,3 +35,6 @@ typedef struct {
int ostree_main (int argc, char **argv, OstreeBuiltin *builtins);
int ostree_run (int argc, char **argv, OstreeBuiltin *builtins, GError **error);
int ostree_usage (char **argv, OstreeBuiltin *builtins, gboolean is_error);