gsimpleactiongroup.h \
gaction.h \
gsimpleaction.h \
+ gapplicationcommandline.h \
gapplication.h
application_sources = \
gsimpleactiongroup.c \
gaction.c \
gsimpleaction.c \
+ gapplicationcommandline.c \
gapplicationimpl-dbus.c \
gapplication.c
/* Prologue {{{1 */
#include "gapplication.h"
+#include "gapplicationcommandline.h"
#include "gapplicationimpl.h"
#include "gioenumtypes.h"
}
}
+static int
+g_application_real_command_line (GApplication *application,
+ GApplicationCommandLine *cmdline)
+{
+ static gboolean warned;
+
+ if (warned)
+ return 1;
+
+ g_warning ("Your application claims to support custom command line "
+ "handling but does not implement g_application_command_line() "
+ "and has no handlers connected to the 'command-line' signal.");
+
+ warned = TRUE;
+
+ return 1;
+}
+
static gboolean
g_application_real_local_command_line (GApplication *application,
GVariant **arguments,
int *exit_status)
{
- if (0)
+ if (application->priv->flags & G_APPLICATION_HANDLES_COMMAND_LINE)
return FALSE;
else
n_args = g_variant_n_children (*arguments);
- if (application->priv->flags & G_APPLICATION_FLAGS_IS_SERVICE)
+ if (application->priv->flags & G_APPLICATION_IS_SERVICE)
{
if (n_args > 1)
{
g_printerr ("GApplication service mode takes no arguments.\n");
- application->priv->flags &= ~G_APPLICATION_FLAGS_IS_SERVICE;
+ application->priv->flags &= ~G_APPLICATION_IS_SERVICE;
}
return TRUE;
else
{
- if (~application->priv->flags & G_APPLICATION_FLAGS_HANDLES_OPEN)
+ if (~application->priv->flags & G_APPLICATION_HANDLES_OPEN)
{
g_critical ("This application can not open files.");
*exit_status = 1;
GApplicationPrivate);
}
+static gboolean
+first_wins_accumulator (GSignalInvocationHint *ihint,
+ GValue *return_accu,
+ const GValue *handler_return,
+ gpointer data)
+{
+ g_value_copy (handler_return, return_accu);
+
+ return FALSE;
+}
+
static void
g_application_class_init (GApplicationClass *class)
{
class->startup = g_application_real_startup;
class->activate = g_application_real_activate;
class->open = g_application_real_open;
+ class->command_line = g_application_real_command_line;
class->local_command_line = g_application_real_local_command_line;
class->add_platform_data = g_application_real_add_platform_data;
class->quit_mainloop = g_application_real_quit_mainloop;
NULL, NULL, _gio_marshal_VOID__POINTER_INT_STRING,
G_TYPE_NONE, 3, G_TYPE_POINTER, G_TYPE_INT, G_TYPE_STRING);
+ g_application_signals[SIGNAL_COMMAND_LINE] =
+ g_signal_new ("command-line", G_TYPE_APPLICATION, G_SIGNAL_RUN_LAST,
+ G_STRUCT_OFFSET (GApplicationClass, command_line),
+ first_wins_accumulator, NULL, _gio_marshal_INT__OBJECT,
+ G_TYPE_INT, 1, G_TYPE_APPLICATION_COMMAND_LINE);
+
g_type_class_add_private (class, sizeof (GApplicationPrivate));
}
gboolean try;
/* don't try to be the primary instance if
- * G_APPLICATION_FLAGS_IS_LAUNCHER was specified.
+ * G_APPLICATION_IS_LAUNCHER was specified.
*/
- try = !(application->priv->flags & G_APPLICATION_FLAGS_IS_LAUNCHER);
+ try = !(application->priv->flags & G_APPLICATION_IS_LAUNCHER);
application->priv->impl =
g_application_impl_register (application, application->priv->id,
* for this functionality, you should use "".
*
* The application must be registered before calling this function and
- * it must have the %G_APPLICATION_FLAGS_CAN_OPEN flag set. The open()
+ * it must have the %G_APPLICATION_CAN_OPEN flag set. The open()
* virtual function should also be implemented in order for anything
* meaningful to happen.
*
{
g_return_if_fail (G_IS_APPLICATION (application));
g_return_if_fail (application->priv->flags &
- G_APPLICATION_FLAGS_HANDLES_OPEN);
+ G_APPLICATION_HANDLES_OPEN);
g_return_if_fail (application->priv->is_registered);
if (application->priv->is_remote)
* virtual function is invoked in the primary instance (which may or may
* not be this instance).
*
- * If the application has the %G_APPLICATION_FLAGS_REMOTE_COMMAND_LINE
+ * If the application has the %G_APPLICATION_REMOTE_COMMAND_LINE
* flag set then the default implementation of handle_command_line()
* always returns %FALSE immediately, resulting in the commandline
* always being handled in the primary instance.
* to register the application. If that works, then the command line
* arguments are inspected. If no commandline arguments are given, then
* g_application_activate() is called. If commandline arguments are
- * given and the %G_APPLICATION_FLAGS_CAN_OPEN flags is set then they
+ * given and the %G_APPLICATION_CAN_OPEN flags is set then they
* are assumed to be filenames and g_application_open() is called.
*
* If you are interested in doing more complicated local handling of the
if (!G_APPLICATION_GET_CLASS (application)
->local_command_line (application, &arguments, &status))
{
- g_assert_not_reached ();
+ GError *error = NULL;
+
+ if (!g_application_register (application, NULL, &error))
+ {
+ g_printerr ("%s", error->message);
+ g_error_free (error);
+ return 1;
+ }
+
+ if (application->priv->is_remote)
+ {
+ GVariant *platform_data;
+
+ platform_data = get_platform_data (application);
+ status = g_application_impl_command_line (application->priv->impl,
+ arguments, platform_data);
+ }
+ else
+ {
+ GApplicationCommandLine *cmdline;
+
+ cmdline = g_object_new (G_TYPE_APPLICATION_COMMAND_LINE,
+ "arguments", arguments, NULL);
+ g_signal_emit (application,
+ g_application_signals[SIGNAL_COMMAND_LINE],
+ 0, cmdline, &status);
+ g_object_unref (cmdline);
+ }
}
g_variant_unref (arguments);
- if (application->priv->flags & G_APPLICATION_FLAGS_IS_SERVICE &&
+ if (application->priv->flags & G_APPLICATION_IS_SERVICE &&
!application->priv->use_count &&
!application->priv->inactivity_timeout_id)
{
gint n_files,
const gchar *hint);
- gpointer _reserved_1;
+ int (* command_line) (GApplication *application,
+ GApplicationCommandLine *command_line);
/* vfuncs */
gboolean (* local_command_line) (GApplication *application,
GVariant **arguments,
int *exit_status);
- gpointer _reserved_2;
-
void (* before_emit) (GApplication *application,
GVariant *platform_data);
void (* after_emit) (GApplication *application,
--- /dev/null
+#include "gapplicationcommandline.h"
+
+#include <string.h>
+#include <stdio.h>
+
+G_DEFINE_TYPE (GApplicationCommandLine, g_application_command_line, G_TYPE_OBJECT)
+
+enum
+{
+ PROP_NONE,
+ PROP_ARGUMENTS,
+ PROP_PLATFORM_DATA,
+ PROP_IS_REMOTE
+};
+
+struct _GApplicationCommandLinePrivate
+{
+ GVariant *platform_data;
+ GVariant *arguments;
+ GVariant *cwd;
+ gint exit_status;
+};
+
+#define IS_REMOTE(cmdline) ((cmdline)->priv->platform_data != NULL)
+
+void
+g_application_command_line_get_argc_argv (GApplicationCommandLine *cmdline,
+ int *argc,
+ char ***argv)
+{
+ gsize len;
+
+ g_return_if_fail (G_IS_APPLICATION_COMMAND_LINE (cmdline));
+ g_return_if_fail (argc != NULL && argv != NULL);
+
+ *argv = g_variant_dup_bytestring_array (cmdline->priv->arguments, &len);
+ *argc = len;
+}
+
+GVariant *
+g_application_command_line_get_arguments (GApplicationCommandLine *cmdline)
+{
+ return g_variant_ref (cmdline->priv->arguments);
+}
+
+const gchar *
+g_application_command_line_get_cwd (GApplicationCommandLine *cmdline)
+{
+ if (cmdline->priv->cwd)
+ return g_variant_get_bytestring (cmdline->priv->cwd);
+ else
+ return NULL;
+}
+
+GVariant *
+g_application_command_line_get_cwd_variant (GApplicationCommandLine *cmdline)
+{
+ if (cmdline->priv->cwd)
+ return g_variant_ref (cmdline->priv->cwd);
+ else
+ return NULL;
+}
+
+gboolean
+g_application_command_line_get_is_remote (GApplicationCommandLine *cmdline)
+{
+ return IS_REMOTE (cmdline);
+}
+
+static void
+g_application_command_line_real_print_literal (GApplicationCommandLine *cmdline,
+ const gchar *message)
+{
+ g_print ("%s\n", message);
+}
+
+static void
+g_application_command_line_real_printerr_literal (GApplicationCommandLine *cmdline,
+ const gchar *message)
+{
+ g_printerr ("%s\n", message);
+}
+
+void
+g_application_command_line_print (GApplicationCommandLine *cmdline,
+ const gchar *format,
+ ...)
+{
+ gchar *message;
+ va_list ap;
+
+ g_return_if_fail (G_IS_APPLICATION_COMMAND_LINE (cmdline));
+ g_return_if_fail (format != NULL);
+
+ va_start (ap, format);
+ message = g_strdup_vprintf (format, ap);
+ va_end (ap);
+
+ G_APPLICATION_COMMAND_LINE_GET_CLASS (cmdline)
+ ->print_literal (cmdline, message);
+ g_free (message);
+}
+
+void
+g_application_command_line_printerr (GApplicationCommandLine *cmdline,
+ const gchar *format,
+ ...)
+{
+ gchar *message;
+ va_list ap;
+
+ g_return_if_fail (G_IS_APPLICATION_COMMAND_LINE (cmdline));
+ g_return_if_fail (format != NULL);
+
+ va_start (ap, format);
+ message = g_strdup_vprintf (format, ap);
+ va_end (ap);
+
+ G_APPLICATION_COMMAND_LINE_GET_CLASS (cmdline)
+ ->printerr_literal (cmdline, message);
+ g_free (message);
+}
+
+void
+g_application_command_line_set_exit_status (GApplicationCommandLine *cmdline,
+ int exit_status)
+{
+ g_return_if_fail (G_IS_APPLICATION_COMMAND_LINE (cmdline));
+
+ cmdline->priv->exit_status = exit_status;
+}
+
+int
+g_application_command_line_get_exit_status (GApplicationCommandLine *cmdline)
+{
+ g_return_val_if_fail (G_IS_APPLICATION_COMMAND_LINE (cmdline), -1);
+
+ return cmdline->priv->exit_status;
+}
+
+static void
+grok_platform_data (GApplicationCommandLine *cmdline)
+{
+ GVariantIter iter;
+ const gchar *key;
+ GVariant *value;
+
+ g_variant_iter_init (&iter, cmdline->priv->platform_data);
+
+ while (g_variant_iter_loop (&iter, "{&sv}", &key, &value))
+ if (strcmp (key, "cwd") == 0)
+ {
+ if (!cmdline->priv->cwd)
+ cmdline->priv->cwd = g_variant_ref (value);
+ }
+}
+
+static void
+g_application_command_line_get_property (GObject *object, guint prop_id,
+ GValue *value, GParamSpec *pspec)
+{
+ GApplicationCommandLine *cmdline = G_APPLICATION_COMMAND_LINE (object);
+
+ switch (prop_id)
+ {
+ case PROP_ARGUMENTS:
+ g_value_set_variant (value, cmdline->priv->arguments);
+ break;
+
+ case PROP_PLATFORM_DATA:
+ g_value_set_variant (value, cmdline->priv->platform_data);
+ break;
+
+ case PROP_IS_REMOTE:
+ g_value_set_boolean (value, IS_REMOTE (cmdline));
+ break;
+
+ default:
+ g_assert_not_reached ();
+ }
+}
+
+static void
+g_application_command_line_set_property (GObject *object, guint prop_id,
+ const GValue *value, GParamSpec *pspec)
+{
+ GApplicationCommandLine *cmdline = G_APPLICATION_COMMAND_LINE (object);
+
+ switch (prop_id)
+ {
+ case PROP_ARGUMENTS:
+ g_assert (cmdline->priv->arguments == NULL);
+ cmdline->priv->arguments = g_value_dup_variant (value);
+ break;
+
+ case PROP_PLATFORM_DATA:
+ g_assert (cmdline->priv->platform_data == NULL);
+ cmdline->priv->platform_data = g_value_dup_variant (value);
+ if (cmdline->priv->platform_data != NULL)
+ grok_platform_data (cmdline);
+ break;
+
+ default:
+ g_assert_not_reached ();
+ }
+}
+
+static void
+g_application_command_line_finalize (GObject *object)
+{
+ GApplicationCommandLine *cmdline = G_APPLICATION_COMMAND_LINE (object);
+
+ if (cmdline->priv->platform_data)
+ g_variant_unref (cmdline->priv->platform_data);
+ if (cmdline->priv->arguments)
+ g_variant_unref (cmdline->priv->arguments);
+ if (cmdline->priv->cwd)
+ g_variant_unref (cmdline->priv->cwd);
+
+ G_OBJECT_CLASS (g_application_command_line_parent_class)
+ ->finalize (object);
+}
+
+static void
+g_application_command_line_init (GApplicationCommandLine *cmdline)
+{
+ cmdline->priv =
+ G_TYPE_INSTANCE_GET_PRIVATE (cmdline,
+ G_TYPE_APPLICATION_COMMAND_LINE,
+ GApplicationCommandLinePrivate);
+}
+
+static void
+g_application_command_line_class_init (GApplicationCommandLineClass *class)
+{
+ GObjectClass *object_class = G_OBJECT_CLASS (class);
+
+ object_class->get_property = g_application_command_line_get_property;
+ object_class->set_property = g_application_command_line_set_property;
+ object_class->finalize = g_application_command_line_finalize;
+ class->printerr_literal = g_application_command_line_real_printerr_literal;
+ class->print_literal = g_application_command_line_real_print_literal;
+
+ g_object_class_install_property (object_class, PROP_ARGUMENTS,
+ g_param_spec_variant ("arguments", "commandline arguments",
+ "the commandline that caused this cmdline",
+ G_VARIANT_TYPE_BYTESTRING_ARRAY, NULL,
+ G_PARAM_WRITABLE | G_PARAM_CONSTRUCT_ONLY |
+ G_PARAM_STATIC_STRINGS));
+
+ g_object_class_install_property (object_class, PROP_PLATFORM_DATA,
+ g_param_spec_variant ("platform-data", "platform data",
+ "platform-specific data for the cmdline",
+ G_VARIANT_TYPE ("a{sv}"), NULL,
+ G_PARAM_WRITABLE | G_PARAM_CONSTRUCT_ONLY |
+ G_PARAM_STATIC_STRINGS));
+
+ g_object_class_install_property (object_class, PROP_IS_REMOTE,
+ g_param_spec_boolean ("is-remote", "is remote",
+ "TRUE if this is a remote cmdline", FALSE,
+ G_PARAM_READABLE | G_PARAM_STATIC_STRINGS));
+
+ g_type_class_add_private (class, sizeof (GApplicationCommandLinePrivate));
+}
+
+GVariant *
+g_application_command_line_get_platform_data (GApplicationCommandLine *cmdline)
+{
+ g_return_val_if_fail (G_IS_APPLICATION_COMMAND_LINE (cmdline), NULL);
+ g_return_val_if_fail (IS_REMOTE (cmdline), NULL);
+
+ return g_variant_ref (cmdline->priv->platform_data);
+}
--- /dev/null
+/* GIO - GLib Input, Output and Streaming Library
+ *
+ * Copyright © 2010 Codethink Limited
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License as published
+ * by the Free Software Foundation; either version 2 of the licence or (at
+ * your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General
+ * Public License along with this library; if not, write to the
+ * Free Software Foundation, Inc., 59 Temple Place, Suite 330,
+ * Boston, MA 02111-1307, USA.
+ *
+ * Authors: Ryan Lortie <desrt@desrt.ca>
+ */
+
+#if !defined (__GIO_GIO_H_INSIDE__) && !defined (GIO_COMPILATION)
+#error "Only <gio/gio.h> can be included directly."
+#endif
+
+#ifndef __G_APPLICATION_COMMAND_LINE_H__
+#define __G_APPLICATION_COMMAND_LINE_H__
+
+#include <gio/giotypes.h>
+
+G_BEGIN_DECLS
+
+#define G_TYPE_APPLICATION_COMMAND_LINE (g_application_command_line_get_type ())
+#define G_APPLICATION_COMMAND_LINE(inst) (G_TYPE_CHECK_INSTANCE_CAST ((inst), \
+ G_TYPE_APPLICATION_COMMAND_LINE, \
+ GApplicationCommandLine))
+#define G_APPLICATION_COMMAND_LINE_CLASS(class) (G_TYPE_CHECK_CLASS_CAST ((class), \
+ G_TYPE_APPLICATION_COMMAND_LINE, \
+ GApplicationCommandLineClass))
+#define G_IS_APPLICATION_COMMAND_LINE(inst) (G_TYPE_CHECK_INSTANCE_TYPE ((inst), \
+ G_TYPE_APPLICATION_COMMAND_LINE))
+#define G_IS_APPLICATION_COMMAND_LINE_CLASS(class) (G_TYPE_CHECK_CLASS_TYPE ((class), \
+ G_TYPE_APPLICATION_COMMAND_LINE))
+#define G_APPLICATION_COMMAND_LINE_GET_CLASS(inst) (G_TYPE_INSTANCE_GET_CLASS ((inst), \
+ G_TYPE_APPLICATION_COMMAND_LINE, \
+ GApplicationCommandLineClass))
+
+typedef struct _GApplicationCommandLinePrivate GApplicationCommandLinePrivate;
+typedef struct _GApplicationCommandLineClass GApplicationCommandLineClass;
+
+/**
+ * GApplicationCommandLine:
+ *
+ * The <structname>GApplicationCommandLine</structname> structure contains private
+ * data and should only be accessed using the provided API
+ *
+ * Since: 2.26
+ */
+struct _GApplicationCommandLine
+{
+ /*< private >*/
+ GObject parent_instance;
+
+ GApplicationCommandLinePrivate *priv;
+};
+
+/**
+ * GApplicationCommandLineClass:
+ *
+ * The <structname>GApplicationCommandLineClass</structname> structure contains
+ * private data only
+ *
+ * Since: 2.26
+ */
+struct _GApplicationCommandLineClass
+{
+ /*< private >*/
+ GObjectClass parent_class;
+
+ void (* print_literal) (GApplicationCommandLine *command_line,
+ const gchar *message);
+ void (* printerr_literal) (GApplicationCommandLine *command_line,
+ const gchar *message);
+
+ gpointer padding[12];
+};
+
+GType g_application_command_line_get_type (void) G_GNUC_CONST;
+
+void g_application_command_line_get_argc_argv (GApplicationCommandLine *command_line,
+ int *argc,
+ char ***argv);
+GVariant * g_application_command_line_get_arguments (GApplicationCommandLine *command_line);
+
+const gchar * g_application_command_line_get_cwd (GApplicationCommandLine *command_line);
+GVariant * g_application_command_line_get_cwd_variant (GApplicationCommandLine *command_line);
+
+gboolean g_application_command_line_get_is_remote (GApplicationCommandLine *command_line);
+
+void g_application_command_line_output (GApplicationCommandLine *command_line,
+ gint fd,
+ gconstpointer buffer,
+ gssize length);
+void g_application_command_line_print (GApplicationCommandLine *command_line,
+ const gchar *format,
+ ...);
+void g_application_command_line_printerr (GApplicationCommandLine *command_line,
+ const gchar *format,
+ ...);
+
+int g_application_command_line_get_exit_status (GApplicationCommandLine *command_line);
+void g_application_command_line_set_exit_status (GApplicationCommandLine *command_line,
+ int exit_status);
+
+GVariant * g_application_command_line_get_platform_data (GApplicationCommandLine *command_line);
+
+G_END_DECLS
+
+#endif /* __G_APPLICATION_COMMAND_LINE_H__ */
static const GDBusArgInfo *open_in[] = { &open_uris_arg, &open_hint_arg, &platform_data_arg, NULL };
static const GDBusArgInfo *open_out[] = { NULL };
+static const GDBusArgInfo *cmdline_in[] = { &cmdline_path_arg, &cmdline_arguments_arg, &platform_data_arg, NULL };
+static const GDBusArgInfo *cmdline_out[] = { &cmdline_exit_status_arg, NULL };
+
static const GDBusMethodInfo activate_method = {
-1, (gchar *) "Activate",
(GDBusArgInfo **) activate_in,
(GDBusArgInfo **) open_out
};
+static const GDBusMethodInfo command_line_method = {
+ -1, (gchar *) "CommandLine",
+ (GDBusArgInfo **) cmdline_in,
+ (GDBusArgInfo **) cmdline_out
+};
+
static const GDBusMethodInfo *application_methods[] = {
- &activate_method, &open_method, NULL
+ &activate_method, &open_method, &command_line_method, NULL
};
const GDBusInterfaceInfo org_gtk_Application = {
-1, (gchar *) "org.gtk.Application",
(GDBusMethodInfo **) application_methods
};
+
+static const GDBusArgInfo message_arg = { -1, (gchar *) "message", (gchar *) "s" };
+static const GDBusArgInfo *print_in[] = { &message_arg, NULL };
+static const GDBusArgInfo *print_out[] = { NULL };
+
+static const GDBusMethodInfo stdout_method = {
+ -1, (gchar *) "Print",
+ (GDBusArgInfo **) print_in,
+ (GDBusArgInfo **) print_out
+};
+
+static const GDBusMethodInfo stderr_method = {
+ -1, (gchar *) "PrintError",
+ (GDBusArgInfo **) print_in,
+ (GDBusArgInfo **) print_out
+};
+
+static const GDBusMethodInfo *cmdline_methods[] = {
+ &stdout_method, &stderr_method, NULL
+};
+
+const GDBusInterfaceInfo org_gtk_private_Cmdline = {
+ -1, (gchar *) "org.gtk.private.CommandLine",
+ (GDBusMethodInfo **) cmdline_methods
+};
#include "gdbuserror.h"
#include <string.h>
-
+#include <stdio.h>
#include "gapplicationimpl-dbus-interface.c"
+#include "gapplicationcommandline.h"
+#include "gdbusmethodinvocation.h"
struct _GApplicationImpl
{
gchar *object_path;
guint object_id;
gpointer app;
-
- GMainLoop *cmdline_mainloop;
};
+
+static GApplicationCommandLine *
+g_dbus_command_line_new (GDBusMethodInvocation *invocation);
+
+
static void
g_application_impl_method_call (GDBusConnection *connection,
const gchar *sender,
g_free (files);
}
+ else if (strcmp (method_name, "CommandLine") == 0)
+ {
+ GApplicationCommandLine *cmdline;
+ GVariant *platform_data;
+ int status;
+
+ cmdline = g_dbus_command_line_new (invocation);
+ platform_data = g_variant_get_child_value (parameters, 2);
+ class->before_emit (impl->app, platform_data);
+ g_signal_emit_by_name (impl->app, "command-line", cmdline, &status);
+ g_application_command_line_set_exit_status (cmdline, status);
+ class->after_emit (impl->app, platform_data);
+ g_variant_unref (platform_data);
+ g_object_unref (cmdline);
+ }
+
else
g_assert_not_reached ();
}
impl->object_path = application_path_from_appid (appid);
- if (flags & G_APPLICATION_FLAGS_IS_LAUNCHER)
+ if (flags & G_APPLICATION_IS_LAUNCHER)
{
impl->object_id = 0;
*is_remote = TRUE;
impl->object_id);
impl->object_id = 0;
- if (flags & G_APPLICATION_FLAGS_IS_SERVICE)
+ if (flags & G_APPLICATION_IS_SERVICE)
{
g_set_error (error, G_DBUS_ERROR, G_DBUS_ERROR_FAILED,
"Unable to acquire bus name `%s'", appid);
NULL, 0, -1, NULL, NULL, NULL);
}
+static void
+g_application_impl_cmdline_method_call (GDBusConnection *connection,
+ const gchar *sender,
+ const gchar *object_path,
+ const gchar *interface_name,
+ const gchar *method_name,
+ GVariant *parameters,
+ GDBusMethodInvocation *invocation,
+ gpointer user_data)
+{
+ const gchar *message;
+
+ g_variant_get_child (parameters, 0, "&s", &message);
+
+ if (strcmp (method_name, "Print") == 0)
+ g_print ("%s", message);
+ else if (strcmp (method_name, "PrintError") == 0)
+ g_printerr ("%s", message);
+ else
+ g_assert_not_reached ();
+
+ g_dbus_method_invocation_return_value (invocation, NULL);
+}
+
+typedef struct
+{
+ GMainLoop *loop;
+ int status;
+} CommandLineData;
+
+static void
+g_application_impl_cmdline_done (GObject *source,
+ GAsyncResult *result,
+ gpointer user_data)
+{
+ CommandLineData *data = user_data;
+ GError *error = NULL;
+ GVariant *reply;
+
+ reply = g_dbus_connection_call_finish (G_DBUS_CONNECTION (source),
+ result, &error);
+
+ if (reply != NULL)
+ {
+ g_variant_get (reply, "(i)", &data->status);
+ g_variant_unref (reply);
+ }
+
+ else
+ {
+ g_printerr ("%s\n", error->message);
+ g_error_free (error);
+ data->status = 1;
+ }
+
+ g_main_loop_quit (data->loop);
+}
+
+int
+g_application_impl_command_line (GApplicationImpl *impl,
+ GVariant *arguments,
+ GVariant *platform_data)
+{
+ const static GDBusInterfaceVTable vtable = {
+ g_application_impl_cmdline_method_call
+ };
+ const gchar *object_path = "/org/gtk/Application/CommandLine";
+ GMainContext *context;
+ CommandLineData data;
+ guint object_id;
+
+ context = g_main_context_new ();
+ data.loop = g_main_loop_new (context, FALSE);
+ g_main_context_push_thread_default (context);
+
+ object_id = g_dbus_connection_register_object (impl->session_bus,
+ object_path,
+ (GDBusInterfaceInfo *)
+ &org_gtk_private_Cmdline,
+ &vtable, &data, NULL, NULL);
+ /* In theory we should try other paths... */
+ g_assert (object_id != 0);
+
+ g_dbus_connection_call (impl->session_bus,
+ impl->bus_name,
+ impl->object_path,
+ "org.gtk.Application",
+ "CommandLine",
+ g_variant_new ("(o@aay@a{sv})", object_path,
+ arguments, platform_data),
+ G_VARIANT_TYPE ("(i)"), 0, -1, NULL,
+ g_application_impl_cmdline_done, &data);
+
+ g_main_loop_run (data.loop);
+
+ g_main_context_pop_thread_default (context);
+ g_main_context_unref (context);
+ g_main_loop_unref (data.loop);
+
+ return data.status;
+}
+
void
g_application_impl_flush (GApplicationImpl *impl)
{
g_dbus_connection_flush_sync (impl->session_bus, NULL, NULL);
}
+
+
+
+
+
+typedef GApplicationCommandLineClass GDBusCommandLineClass;
+static GType g_dbus_command_line_get_type (void);
+typedef struct
+{
+ GApplicationCommandLine parent_instance;
+ GDBusMethodInvocation *invocation;
+
+ GDBusConnection *connection;
+ const gchar *bus_name;
+ const gchar *object_path;
+} GDBusCommandLine;
+
+
+G_DEFINE_TYPE (GDBusCommandLine,
+ g_dbus_command_line,
+ G_TYPE_APPLICATION_COMMAND_LINE)
+
+static void
+g_dbus_command_line_print_literal (GApplicationCommandLine *cmdline,
+ const gchar *message)
+{
+ GDBusCommandLine *gdbcl = (GDBusCommandLine *) cmdline;
+
+ g_dbus_connection_call (gdbcl->connection,
+ gdbcl->bus_name,
+ gdbcl->object_path,
+ "org.gtk.private.CommandLine", "Print",
+ g_variant_new ("(s)", message),
+ NULL, 0, -1, NULL, NULL, NULL);
+}
+
+static void
+g_dbus_command_line_printerr_literal (GApplicationCommandLine *cmdline,
+ const gchar *message)
+{
+ GDBusCommandLine *gdbcl = (GDBusCommandLine *) cmdline;
+
+ g_dbus_connection_call (gdbcl->connection,
+ gdbcl->bus_name,
+ gdbcl->object_path,
+ "org.gtk.private.CommandLine", "PrintError",
+ g_variant_new ("(s)", message),
+ NULL, 0, -1, NULL, NULL, NULL);
+}
+
+static void
+g_dbus_command_line_finalize (GObject *object)
+{
+ GApplicationCommandLine *cmdline = G_APPLICATION_COMMAND_LINE (object);
+ GDBusCommandLine *gdbcl = (GDBusCommandLine *) object;
+ gint status;
+
+ status = g_application_command_line_get_exit_status (cmdline);
+
+ g_dbus_method_invocation_return_value (gdbcl->invocation,
+ g_variant_new ("(i)", status));
+ g_object_unref (gdbcl->invocation);
+
+ G_OBJECT_CLASS (g_dbus_command_line_parent_class)
+ ->finalize (object);
+}
+
+static void
+g_dbus_command_line_init (GDBusCommandLine *gdbcl)
+{
+}
+
+static void
+g_dbus_command_line_class_init (GApplicationCommandLineClass *class)
+{
+ GObjectClass *object_class = G_OBJECT_CLASS (class);
+
+ object_class->finalize = g_dbus_command_line_finalize;
+ class->printerr_literal = g_dbus_command_line_printerr_literal;
+ class->print_literal = g_dbus_command_line_print_literal;
+}
+
+static GApplicationCommandLine *
+g_dbus_command_line_new (GDBusMethodInvocation *invocation)
+{
+ GDBusCommandLine *gdbcl;
+ GVariant *args;
+
+ args = g_dbus_method_invocation_get_parameters (invocation);
+
+ gdbcl = g_object_new (g_dbus_command_line_get_type (),
+ "arguments", g_variant_get_child_value (args, 1),
+ "platform-data", g_variant_get_child_value (args, 2),
+ NULL);
+ gdbcl->connection = g_dbus_method_invocation_get_connection (invocation);
+ gdbcl->bus_name = g_dbus_method_invocation_get_sender (invocation);
+ g_variant_get_child (args, 0, "&o", &gdbcl->object_path);
+ gdbcl->invocation = g_object_ref (invocation);
+
+ return G_APPLICATION_COMMAND_LINE (gdbcl);
+}
const gchar *hint,
GVariant *platform_data);
+G_GNUC_INTERNAL
+int g_application_impl_command_line (GApplicationImpl *impl,
+ GVariant *arguments,
+ GVariant *platform_data);
+
G_GNUC_INTERNAL
void g_application_impl_flush (GApplicationImpl *impl);
VOID:STRING,BOOLEAN
VOID:POINTER,INT,STRING
BOOLEAN:OBJECT
+INT:OBJECT
#include <gio/gactiongroup.h>
#include <gio/gsimpleactiongroup.h>
#include <gio/gapplication.h>
+#include <gio/gapplicationcommandline.h>
#include <gio/gasyncinitable.h>
#include <gio/gasyncresult.h>
#include <gio/gbufferedinputstream.h>
typedef enum
{
G_APPLICATION_FLAGS_NONE,
- G_APPLICATION_FLAGS_IS_SERVICE = (1 << 0),
- G_APPLICATION_FLAGS_IS_LAUNCHER = (1 << 1),
+ G_APPLICATION_IS_SERVICE = (1 << 0),
+ G_APPLICATION_IS_LAUNCHER = (1 << 1),
- G_APPLICATION_FLAGS_HANDLES_OPEN = (1 << 2)
+ G_APPLICATION_HANDLES_OPEN = (1 << 2),
+ G_APPLICATION_HANDLES_COMMAND_LINE = (1 << 3)
} GApplicationFlags;
G_END_DECLS