summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorCeara Chewning <ceara.k.chewning@intel.com>2012-09-12 15:05:54 -0700
committerPatrik Flykt <patrik.flykt@linux.intel.com>2012-09-14 16:32:00 +0300
commit800d3a8630992f400f2d0336a2e337db2456928f (patch)
tree4c446d9ede3d86abb40402008d219f88372f76fc
parentd00244b8e6afce2aa988c3c4a4cce7893c8d78b7 (diff)
downloadconnman-800d3a8630992f400f2d0336a2e337db2456928f.tar.gz
connman-800d3a8630992f400f2d0336a2e337db2456928f.tar.bz2
connman-800d3a8630992f400f2d0336a2e337db2456928f.zip
client: Event monitoring support for the command line client
The command line client is able to run as a monitor to ConnMan. When the client is started with the 'monitor' option, it will wait for any signals from ConnMan and display them. It is useful for realtime verbose output of ConnMan D-Bus events.
-rw-r--r--client/monitor.c248
-rw-r--r--client/monitor.h46
2 files changed, 294 insertions, 0 deletions
diff --git a/client/monitor.c b/client/monitor.c
new file mode 100644
index 00000000..3c3ca5cd
--- /dev/null
+++ b/client/monitor.c
@@ -0,0 +1,248 @@
+/*
+ *
+ * Connection Manager
+ *
+ * Copyright (C) 2012 Intel Corporation. All rights reserved.
+ *
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation.
+ *
+ * This program 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 General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
+ *
+ */
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <string.h>
+#include <stdint.h>
+
+#include <glib.h>
+
+#include <dbus/dbus.h>
+
+#include "client/monitor.h"
+#include "client/services.h"
+#include "client/technology.h"
+#include "client/data_manager.h"
+#include "src/connman.h"
+#include "gdbus/gdbus.h"
+
+static const char *get_service_name(DBusMessage *message, char *dbus_path)
+{
+ DBusMessageIter iter, array;
+
+ dbus_message_iter_init(message, &iter);
+ dbus_message_iter_recurse(&iter, &array);
+
+ while (dbus_message_iter_get_arg_type(&array) == DBUS_TYPE_STRUCT) {
+ DBusMessageIter entry, dict;
+ struct service_data service;
+ char *path;
+
+ dbus_message_iter_recurse(&array, &entry);
+ dbus_message_iter_get_basic(&entry, &path);
+
+ if (g_strcmp0(path, dbus_path) == 0) {
+ dbus_message_iter_next(&entry);
+ dbus_message_iter_recurse(&entry, &dict);
+ extract_service_name(&dict, &service);
+ return service.name;
+ } else {
+ dbus_message_iter_next(&array);
+ }
+ }
+ return NULL;
+}
+
+static void extract_tech_signal(DBusMessage *message)
+{
+ DBusMessageIter iter, dict;
+ char *path;
+
+ dbus_message_iter_init(message, &iter);
+
+ if (dbus_message_iter_get_arg_type(&iter) == DBUS_TYPE_OBJECT_PATH) {
+ dbus_message_iter_get_basic(&iter, &path);
+ printf(" { %s }\n", path);
+ }
+ dbus_message_iter_next(&iter);
+
+ if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_INVALID) {
+ dbus_message_iter_recurse(&iter, &dict);
+ extract_properties(&dict);
+ }
+}
+
+static void extract_signal_args(DBusMessage *message)
+{
+ DBusMessageIter iter, array, dict;
+ char *string, *value;
+ uint16_t key_int;
+ dbus_bool_t bvalue;
+
+ value = NULL;
+ key_int = 0;
+
+ dbus_message_iter_init(message, &iter);
+
+ while (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_INVALID) {
+ if (dbus_message_iter_get_arg_type(&iter) == DBUS_TYPE_STRING) {
+ dbus_message_iter_get_basic(&iter, &string);
+ printf("\n[%s] = ",
+ string);
+ }
+ dbus_message_iter_next(&iter);
+ if (dbus_message_iter_get_arg_type(&iter) !=
+ DBUS_TYPE_INVALID) {
+ dbus_message_iter_recurse(&iter, &array);
+ if (dbus_message_iter_get_arg_type(&array) ==
+ DBUS_TYPE_STRING) {
+ dbus_message_iter_get_basic(&array, &value);
+ printf("%s\n", value);
+ continue;
+ } else if (dbus_message_iter_get_arg_type(&array) ==
+ DBUS_TYPE_BOOLEAN) {
+ dbus_message_iter_get_basic(&array, &bvalue);
+ printf("%s\n", bvalue == TRUE ?
+ "True" : "False");
+ continue;
+ } else if (dbus_message_iter_get_arg_type(&array) ==
+ DBUS_TYPE_ARRAY)
+ dbus_message_iter_recurse(&array, &dict);
+ if (dbus_message_iter_get_arg_type(&dict) ==
+ DBUS_TYPE_DICT_ENTRY) {
+ iterate_dict(&dict, value, key_int);
+ printf("\n");
+ } else {
+ iterate_array(&array);
+ printf("\n");
+ }
+ dbus_message_iter_next(&iter);
+ }
+ }
+}
+
+int monitor_connman(DBusConnection *connection, char *interface,
+ char *signal_name)
+{
+ char *rule = g_strdup_printf("type='signal',interface='net.connman.%s',"
+ "member='%s'", interface, signal_name);
+ DBusError err;
+
+ dbus_error_init(&err);
+ g_dbus_setup_bus(DBUS_BUS_SYSTEM, NULL, &err);
+ if (dbus_error_is_set(&err)) {
+ fprintf(stderr, "Bus setup error:%s\n", err.message);
+ return -1;
+ }
+ dbus_bus_add_match(connection, rule, &err);
+
+ if (dbus_error_is_set(&err)) {
+ fprintf(stderr, "Match Error: %s\n", err.message);
+ return -1;
+ }
+ return 0;
+}
+
+DBusHandlerResult service_property_changed(DBusConnection *connection,
+ DBusMessage *message,
+ void *user_data)
+{
+ DBusMessage *service_message;
+ struct service_data service;
+
+ if (dbus_message_is_signal(message, "net.connman.Service",
+ "PropertyChanged")) {
+ service_message = get_message(connection, "GetServices");
+ service.name = get_service_name(service_message,
+ (char *) dbus_message_get_path(message));
+ printf("\n");
+ g_message("Path = %s, Interface = %s\nService = %s",
+ dbus_message_get_path(message),
+ dbus_message_get_interface(message),
+ service.name);
+ extract_signal_args(message);
+ }
+
+ return DBUS_HANDLER_RESULT_NOT_YET_HANDLED;
+}
+
+DBusHandlerResult tech_property_changed(DBusConnection *connection,
+ DBusMessage *message, void *user_data)
+{
+ if (dbus_message_is_signal(message, "net.connman.Technology",
+ "PropertyChanged")) {
+ printf("\n");
+ g_message("Path = %s, Interface = %s",
+ dbus_message_get_path(message),
+ dbus_message_get_interface(message));
+ extract_signal_args(message);
+ }
+ return DBUS_HANDLER_RESULT_NOT_YET_HANDLED;
+}
+
+DBusHandlerResult tech_added_removed(DBusConnection *connection,
+ DBusMessage *message, void *user_data)
+{
+ if (dbus_message_is_signal(message, "net.connman.Manager",
+ "TechnologyAdded")) {
+ printf("\n");
+ g_message("Path = %s, Interface = %s",
+ dbus_message_get_path(message),
+ dbus_message_get_interface(message));
+ printf("New technology added:\n");
+ extract_tech_signal(message);
+ } else if (dbus_message_is_signal(message, "net.connman.Manager",
+ "TechnologyRemoved")) {
+ printf("\n");
+ g_message("Path = %s, Interface = %s",
+ dbus_message_get_path(message),
+ dbus_message_get_interface(message));
+ printf("Technology was removed:\n");
+ extract_tech_signal(message);
+ }
+
+ return DBUS_HANDLER_RESULT_NOT_YET_HANDLED;
+}
+
+DBusHandlerResult manager_services_changed(DBusConnection *connection,
+ DBusMessage *message, void *user_data)
+{
+ if (dbus_message_is_signal(message, "net.connman.Manager",
+ "ServicesChanged")) {
+ printf("\n");
+ g_message("Path = %s, Interface = %s",
+ dbus_message_get_path(message),
+ dbus_message_get_interface(message));
+ printf("Services Changed, displaying updated "
+ "list of services:\n");
+ list_properties(connection, "GetServices", NULL);
+ }
+
+ return DBUS_HANDLER_RESULT_NOT_YET_HANDLED;
+}
+
+DBusHandlerResult manager_property_changed(DBusConnection *connection,
+ DBusMessage *message, void *user_data)
+{
+ if (dbus_message_is_signal(message, "net.connman.Manager",
+ "PropertyChanged")) {
+ printf("\n");
+ g_message("Path = %s, Interface = %s",
+ dbus_message_get_path(message),
+ dbus_message_get_interface(message));
+ extract_signal_args(message);
+ }
+
+ return DBUS_HANDLER_RESULT_NOT_YET_HANDLED;
+}
diff --git a/client/monitor.h b/client/monitor.h
new file mode 100644
index 00000000..12ccb909
--- /dev/null
+++ b/client/monitor.h
@@ -0,0 +1,46 @@
+/*
+ *
+ * Connection Manager
+ *
+ * Copyright (C) 2012 Intel Corporation. All rights reserved.
+ *
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation.
+ *
+ * This program 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 General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
+ *
+ */
+
+#ifndef __CLIENT_MONITOR_H
+#define __CLIENT_MONITOR_H
+
+#include <dbus/dbus.h>
+
+
+int monitor_connman(DBusConnection *connection, char *interface,
+ char *signal_name);
+
+DBusHandlerResult service_property_changed(DBusConnection *connection,
+ DBusMessage *message, void *user_data);
+
+DBusHandlerResult tech_property_changed(DBusConnection *connection,
+ DBusMessage *message, void *user_data);
+
+DBusHandlerResult tech_added_removed(DBusConnection *connection,
+ DBusMessage *message, void *user_data);
+
+DBusHandlerResult manager_property_changed(DBusConnection *connection,
+ DBusMessage *message, void *user_data);
+
+DBusHandlerResult manager_services_changed(DBusConnection *connection,
+ DBusMessage *message, void *user_data);
+#endif