aboutsummaryrefslogtreecommitdiffstats
path: root/agent.c
diff options
context:
space:
mode:
Diffstat (limited to 'agent.c')
-rwxr-xr-xagent.c262
1 files changed, 262 insertions, 0 deletions
diff --git a/agent.c b/agent.c
new file mode 100755
index 0000000..a22dc31
--- /dev/null
+++ b/agent.c
@@ -0,0 +1,262 @@
+/* Copyright 2016 ALPS ELECTRIC CO., LTD.
+*
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+
+#include <stdio.h>
+#include <errno.h>
+
+#include <gio/gio.h>
+#include "wifi-connman.h"
+
+static GMainLoop *loop = NULL;
+
+static GDBusNodeInfo *introspection_data = NULL;
+
+GDBusMethodInvocation *invocation_passkey = NULL;
+
+/* Introspection data for the agent service */
+static const gchar introspection_xml[] = "<node>"
+ " <interface name='net.connman.Agent'>"
+ " <method name='RequestInput'>"
+ " <arg type='o' name='service' direction='in'/>"
+ " <arg type='a{sv}' name='fields' direction='in'/>"
+ " <arg type='a{sv}' name='fields' direction='out'/>"
+ " </method>"
+ " <method name='ReportError'>"
+ " <arg type='o' name='service' direction='in'/>"
+ " <arg type='s' name='error' direction='in'/>"
+ " </method>"
+ " </interface>"
+ "</node>";
+
+callback password_callback;
+
+static void handle_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) {
+ //MyObject *myobj = user_data;
+
+ if (g_strcmp0(method_name, "RequestInput") == 0) {
+ printf("Input requested\n");
+
+ invocation_passkey = invocation;
+
+ //TODO: send the name of the network to callback
+
+ (*password_callback)(0);
+
+ GVariantIter *array;
+ gchar * object_path;
+ g_variant_get(parameters, "(oa{sv})", &object_path, &array);
+ //TODO: get only object path for now, complete parameters are
+
+ /*
+ object path "/net/connman/service/wifi_d85d4c880b1a_4c656e6f766f204b3520506c7573_managed_psk"
+ array [
+ dict entry(
+ string "Passphrase"
+ variant array [
+ dict entry(
+ string "Type"
+ variant string "psk"
+ )
+ dict entry(
+ string "Requirement"
+ variant string "mandatory"
+ )
+ ]
+ )
+ ]
+ */
+ printf("Passphrase requested for network : %s\n", object_path);
+
+ }
+
+ if (g_strcmp0(method_name, "ReportError") == 0) {
+ printf("Error reported\n");
+
+ gchar *error_string; // = NULL;
+
+ gchar * object_path;
+ g_variant_get(parameters, "(os)", &object_path, &error_string);
+
+ printf("Error %s for %s\n", error_string, object_path);
+
+ if (g_strcmp0(error_string, "invalid-key") == 0) {
+
+ printf("Passkey is not correct.\n");
+ (*password_callback)(1);
+
+ }
+
+ }
+}
+
+GError* sendPasskey(gchar *passkey) {
+
+ GVariantBuilder *builder;
+ GVariant *value = NULL;
+
+ printf("Passkey to send: %s\n", passkey);
+
+ builder = g_variant_builder_new(G_VARIANT_TYPE("a{sv}"));
+
+ g_variant_builder_add(builder, "{sv}", "Passphrase",
+ g_variant_new_string(passkey));
+
+ value = g_variant_new("(a{sv})", builder);
+
+ g_dbus_method_invocation_return_value(invocation_passkey, value);
+
+ return NULL;
+
+}
+
+static const GDBusInterfaceVTable interface_vtable = { handle_method_call, NULL,
+ NULL };
+
+static void on_bus_acquired(GDBusConnection *connection, const gchar *name,
+ gpointer user_data) {
+ //MyObject *myobj = user_data;
+ guint registration_id;
+
+ registration_id = g_dbus_connection_register_object(connection,
+ "/net/connman/Agent", introspection_data->interfaces[0],
+ &interface_vtable, NULL, NULL, /* user_data_free_func */
+ NULL); /* GError** */
+ //TODO: make some proper error message rather than exiting
+ //g_assert(registration_id > 0);
+
+ return NULL;
+}
+
+void* register_agent(void *data) {
+
+ //printf("Loop start\n");
+
+ guint owner_id;
+ //MyObject *myobj;
+
+ introspection_data = g_dbus_node_info_new_for_xml(introspection_xml, NULL);
+ g_assert(introspection_data != NULL);
+
+ //myobj = g_object_new(my_object_get_type(), NULL);
+
+// owner_id = g_bus_own_name(G_BUS_TYPE_SYSTEM, "org.agent",
+// G_BUS_NAME_OWNER_FLAGS_NONE, on_bus_acquired, on_name_acquired,
+// on_name_lost, myobj,
+// NULL);
+
+//FIXME: ALLOW_REPLACEMENT for now, make proper deinitialization
+ owner_id = g_bus_own_name(G_BUS_TYPE_SYSTEM, AGENT_SERVICE,
+ G_BUS_NAME_OWNER_FLAGS_REPLACE, on_bus_acquired, NULL, NULL, NULL,
+ NULL);
+ //G_BUS_NAME_OWNER_FLAGS_NONE G_BUS_NAME_OWNER_FLAGS_ALLOW_REPLACEMENT
+
+ loop = g_main_loop_new(NULL, FALSE);
+
+ //sleep(10);
+ g_main_loop_run(loop);
+
+ printf("Loop running\n");
+
+ g_bus_unown_name(owner_id);
+
+ g_dbus_node_info_unref(introspection_data);
+
+ //g_object_unref(myobj);
+
+ //printf("Loop end\n");
+
+ return NULL;
+
+}
+
+GError* create_agent(GDBusConnection *connection) {
+
+ int err = -1;
+ pthread_t tid[1];
+
+ //struct callbackData *threadData;
+
+ err = pthread_create((&tid[0]), NULL, register_agent, NULL);
+
+ if (err != 0) {
+ printf("\ncan't create thread :[%d]", err);
+ printf("Fatal error!\n\n");
+ return NULL;
+ }
+
+ GVariant *message = NULL;
+ GError *error = NULL;
+
+ GVariant *params = NULL;
+
+ char *agent_path = AGENT_PATH;
+
+ params = g_variant_new("(o)", agent_path);
+
+ message = g_dbus_connection_call_sync(connection, CONNMAN_SERVICE,
+ CONNMAN_MANAGER_PATH, CONNMAN_MANAGER_INTERFACE, "RegisterAgent", params,
+ NULL, G_DBUS_CALL_FLAGS_NONE,
+ DBUS_REPLY_TIMEOUT, NULL, &error);
+
+ if (error) {
+ printf("error: %d:%s\n", error->code, error->message);
+
+ return error;
+
+ } else {
+ printf("Agent registered\n");
+ return NULL;
+ }
+
+}
+
+GError* stop_agent(GDBusConnection *connection) {
+
+ GVariant *message = NULL;
+ GError *error = NULL;
+
+
+ GVariant *params = NULL;
+
+ char *agent_path = AGENT_PATH;
+
+
+ params = g_variant_new("(o)", agent_path);
+
+ message = g_dbus_connection_call_sync(connection, CONNMAN_SERVICE,
+ CONNMAN_MANAGER_PATH, CONNMAN_MANAGER_INTERFACE, "UnregisterAgent", params,
+ NULL, G_DBUS_CALL_FLAGS_NONE,
+ DBUS_REPLY_TIMEOUT, NULL, &error);
+
+ if (error) {
+ printf("error: %d:%s\n", error->code, error->message);
+ return error;
+
+ } else {
+ printf("Agent unregistered\n");
+ return NULL;
+ }
+
+}
+
+void register_callback(callback callback_function) {
+
+ password_callback = callback_function;
+
+}
+