X-Git-Url: http://review.tizen.org/git/?a=blobdiff_plain;f=src%2Fwifi-agent.c;h=f130d95c2e1eefb51db0c95f6e0f71fbf9339820;hb=6d12d1bb86181a1a52de76118627b8c6df3f7151;hp=ba7d3317590975f64a7aef852dd60dfde6dc0d4e;hpb=b90132819d751591cd362325f5f82df756138919;p=platform%2Fcore%2Fconnectivity%2Fnet-config.git diff --git a/src/wifi-agent.c b/src/wifi-agent.c old mode 100644 new mode 100755 index ba7d331..f130d95 --- a/src/wifi-agent.c +++ b/src/wifi-agent.c @@ -1,7 +1,7 @@ /* * Network Configuration Module * - * Copyright (c) 2012-2013 Samsung Electronics Co., Ltd. All rights reserved. + * Copyright (c) 2000 - 2012 Samsung Electronics Co., Ltd. All rights reserved. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -18,186 +18,762 @@ */ #include +#include +#include #include +#include -#include "wifi-agent.h" #include "log.h" +#include "util.h" #include "wifi.h" #include "netdbus.h" - +#include "wifi-agent.h" +#include "wifi-state.h" +#include "wifi-eap-config.h" +#include "network-state.h" +#include "network-accessibility.h" +#include "wifi-key-encryption.h" + +#define NETCONFIG_AGENT_FIELD_NAME "Name" +#define NETCONFIG_AGENT_FIELD_SSID "SSID" +#define NETCONFIG_AGENT_FIELD_IDENTITY "Identity" #define NETCONFIG_AGENT_FIELD_PASSPHRASE "Passphrase" #define NETCONFIG_AGENT_FIELD_WPS "WPS" #define NETCONFIG_AGENT_FIELD_WPS_PBC "WPS_PBC" #define NETCONFIG_AGENT_FIELD_WPS_PIN "WPS_PIN" - -struct netconfig_wifi_agent { +#if defined TIZEN_CAPTIVE_PORTAL +#define NETCONFIG_AGENT_FIELD_USERNAME "Username" +#define NETCONFIG_AGENT_FIELD_PASSWORD "Password" +#endif + +#define NETCONFIG_AGENT_ERR_CONNECT_FAILED "connect-failed" + +typedef struct { + char *interface_name; + GByteArray *ssid; + char *name; + char *identity; char *passphrase; char *wps_pin; +#if defined TIZEN_CAPTIVE_PORTAL + char *username; + char *password; +#endif gboolean wps_pbc; -}; +} netconfig_wifi_agent_s; -static struct netconfig_wifi_agent agent; +static GSList *g_agent_list = NULL; -static void __netconfig_agent_clear_fields(void) +static void __agent_clear_fields(netconfig_wifi_agent_s *agent) { - DBG("__netconfig_agent_clear_fields"); + if (!agent) + return; + + g_free(agent->interface_name); + if (agent->ssid) + g_byte_array_free(agent->ssid, TRUE); + g_free(agent->name); + g_free(agent->identity); + g_free(agent->passphrase); + g_free(agent->wps_pin); +#if defined TIZEN_CAPTIVE_PORTAL + g_free(agent->username); + g_free(agent->password); +#endif + + agent->interface_name = NULL; + agent->ssid = NULL; + agent->name = NULL; + agent->identity = NULL; + agent->passphrase = NULL; + agent->wps_pin = NULL; +#if defined TIZEN_CAPTIVE_PORTAL + agent->username = NULL; + agent->password = NULL; +#endif + agent->wps_pbc = FALSE; +} - g_free(agent.passphrase); - g_free(agent.wps_pin); +static void __agent_free_data(gpointer data) +{ + netconfig_wifi_agent_s *agent = data; - agent.passphrase = NULL; - agent.wps_pin = NULL; - agent.wps_pbc = FALSE; + __agent_clear_fields(agent); + g_free(agent); } -gboolean netconfig_agent_register(void) +static netconfig_wifi_agent_s *__agent_get_data(const char *interface_name) { - DBG("netconfig_agent_register"); + GSList *list = NULL; - DBusMessage *reply = NULL; - char param1[64] = ""; - char *param_array[] = {NULL, NULL}; + for (list = g_agent_list; list; list = list->next) { + netconfig_wifi_agent_s *wifi_agent = list->data; + if (g_strcmp0(wifi_agent->interface_name, interface_name) == 0) + return wifi_agent; + } - snprintf(param1, 64, "objpath:%s", NETCONFIG_WIFI_PATH); - param_array[0] = param1; + return NULL; +} + +int connman_register_agent(void) +{ + GVariant *reply = NULL; + GVariant *params = NULL; + params = g_variant_new("(o)", NETCONFIG_WIFI_PATH); reply = netconfig_invoke_dbus_method(CONNMAN_SERVICE, CONNMAN_MANAGER_PATH, CONNMAN_MANAGER_INTERFACE, - "RegisterAgent", param_array); + "RegisterAgent", params); if (reply == NULL) { - ERR("Error! Request failed"); - return FALSE; - } + ERR("Fail to register agent"); + return FALSE; + } else + g_variant_unref(reply); - dbus_message_unref(reply); + INFO("Registered to connman agent successfully"); return TRUE; } -gboolean netconfig_agent_unregister(void) +int connman_unregister_agent(void) { - DBG("netconfig_agent_unregister"); + gboolean reply = FALSE; + GVariant *param = NULL; + const char *path = NETCONFIG_WIFI_PATH; - DBusMessage *reply = NULL; - char param1[64] = ""; - char *param_array[] = {NULL, NULL}; + param = g_variant_new("(o)", path); - snprintf(param1, 64, "objpath:%s", NETCONFIG_WIFI_PATH); - param_array[0] = param1; + DBG("ConnMan agent unregister"); - reply = netconfig_invoke_dbus_method(CONNMAN_SERVICE, + reply = netconfig_invoke_dbus_method_nonblock(CONNMAN_SERVICE, CONNMAN_MANAGER_PATH, CONNMAN_MANAGER_INTERFACE, - "UnregisterAgent", param_array); + "UnregisterAgent", param, NULL, NULL); - if (reply == NULL) { - ERR("Error! Request failed"); + if (reply != TRUE) + ERR("Fail to unregister agent"); + + /* Clearing the agent fields */ + g_slist_free_full(g_agent_list, __agent_free_data); + + return reply; +} + +gboolean netconfig_wifi_set_agent_field_for_eap_network(const char *interface_name, + const char *name, const char *identity, const char *passphrase) +{ + int name_len; + netconfig_wifi_agent_s *wifi_agent = NULL; + + if (name == NULL) + return FALSE; + + wifi_agent = __agent_get_data(interface_name); + if (wifi_agent == NULL) return FALSE; - } - dbus_message_unref(reply); + __agent_clear_fields(wifi_agent); - /* Clearing the agent fields */ - __netconfig_agent_clear_fields(); + name_len = strlen(name); + wifi_agent->ssid = g_byte_array_sized_new(name_len); + wifi_agent->ssid->len = name_len; + memcpy(wifi_agent->ssid->data, name, name_len + 1); + + if (identity) + wifi_agent->identity = g_strdup(identity); + + if (passphrase) + wifi_agent->passphrase = g_strdup(passphrase); + + gchar *enc_data = NULL; + enc_data = _netconfig_encrypt_passphrase(wifi_agent->passphrase); + + if (!enc_data) { + ERR("Failed to encrypt the passphrase"); + } else { + g_free(wifi_agent->passphrase); + wifi_agent->passphrase = enc_data; + } + + DBG("Successfully configured for EAP network"); return TRUE; } -gboolean netconfig_iface_wifi_set_field(NetconfigWifi *wifi, - GHashTable *fields, GError **error) +gboolean handle_set_field(NetConnmanAgent *connman_agent, + GDBusMethodInvocation *context, const gchar *service, GVariant *fields) { - GHashTableIter iter; - gpointer field, value; + GError *error = NULL; + GVariantIter *iter; + gpointer field; + GVariant *value; + gboolean updated = FALSE; + gboolean reply = FALSE; + const char *interface_name = NULL; + netconfig_wifi_agent_s *wifi_agent = NULL; + + g_return_val_if_fail(connman_agent != NULL, TRUE); + + DBG("Set agent fields for %s", service); + + if (netconfig_is_wifi_profile(service) != TRUE) { + error = g_error_new(G_DBUS_ERROR, + G_DBUS_ERROR_AUTH_FAILED, + CONNMAN_ERROR_INTERFACE ".InvalidService"); + + g_dbus_method_invocation_return_gerror(context, error); + g_clear_error(&error); + + return TRUE; + } + + interface_name = netconfig_get_ifname(service); + if (interface_name == NULL) { + error = g_error_new(G_DBUS_ERROR, + G_DBUS_ERROR_AUTH_FAILED, + CONNMAN_ERROR_INTERFACE ".InvalidService"); + + g_dbus_method_invocation_return_gerror(context, error); + g_clear_error(&error); + + return TRUE; + } - DBG("Set agent fields"); + wifi_agent = __agent_get_data(interface_name); + if (wifi_agent == NULL) { + wifi_agent = g_try_malloc0(sizeof(netconfig_wifi_agent_s)); + if (wifi_agent == NULL) { + error = g_error_new(G_DBUS_ERROR, + G_DBUS_ERROR_AUTH_FAILED, + CONNMAN_ERROR_INTERFACE ".OutOfMemory"); - g_return_val_if_fail(wifi != NULL, FALSE); + g_dbus_method_invocation_return_gerror(context, error); + g_clear_error(&error); - __netconfig_agent_clear_fields(); + return TRUE; + } + + g_agent_list = g_slist_append(g_agent_list, wifi_agent); + } - g_hash_table_iter_init(&iter, fields); + __agent_clear_fields(wifi_agent); + wifi_agent->interface_name = g_strdup(interface_name); - while (g_hash_table_iter_next(&iter, &field, &value)) { - DBG("Field - [%s]", field); + g_variant_get(fields, "a{sv}", &iter); + while (g_variant_iter_loop(iter, "{sv}", &field, &value)) { if (g_strcmp0(field, NETCONFIG_AGENT_FIELD_PASSPHRASE) == 0) { - g_free(agent.passphrase); - agent.passphrase = g_strdup(value); + if (g_variant_is_of_type(value, G_VARIANT_TYPE_STRING)) { + wifi_agent->passphrase = g_strdup(g_variant_get_string(value, NULL)); + updated = TRUE; + + DBG("Field [%s] - []", (gchar *)field); + + if (wifi_agent->passphrase == NULL) + continue; + + if (netconfig_check_passphrase(service, wifi_agent->passphrase) == FALSE) { + ERR("Invalid passphrase"); - DBG("Field [%s] - []", field); + g_free(wifi_agent->passphrase); + wifi_agent->passphrase = NULL; + + updated = FALSE; + continue; + } + + gchar *enc_data = NULL; + enc_data = _netconfig_encrypt_passphrase(wifi_agent->passphrase); + + if (!enc_data) { + ERR("Failed to encrypt the passphrase"); + continue; + } + + g_free(wifi_agent->passphrase); + wifi_agent->passphrase = enc_data; + } } else if (g_strcmp0(field, NETCONFIG_AGENT_FIELD_WPS_PBC) == 0) { - agent.wps_pbc = FALSE; - if (g_strcmp0(value, "enable") == 0) - agent.wps_pbc = TRUE; + if (g_variant_is_of_type(value, G_VARIANT_TYPE_STRING) && + g_strcmp0(g_variant_get_string(value, NULL), "enable") == 0) { + wifi_agent->wps_pbc = TRUE; + updated = TRUE; - DBG("Field [%s] - [%d]", field, agent.wps_pbc); + DBG("Field [%s] - [%d]", (gchar *)field, wifi_agent->wps_pbc); + } } else if (g_strcmp0(field, NETCONFIG_AGENT_FIELD_WPS_PIN) == 0) { - g_free(agent.wps_pin); - agent.wps_pbc = FALSE; - agent.wps_pin = g_strdup(value); + if (g_variant_is_of_type(value, G_VARIANT_TYPE_STRING)) { + wifi_agent->wps_pin = g_strdup(g_variant_get_string(value, NULL)); + updated = TRUE; + + DBG("Field [%s] - [%s]", (gchar *)field, wifi_agent->wps_pin); + } + } else if (g_strcmp0(field, NETCONFIG_AGENT_FIELD_NAME) == 0) { + if (g_variant_is_of_type(value, G_VARIANT_TYPE_STRING)) { + wifi_agent->name = g_strdup(g_variant_get_string(value, NULL)); + updated = TRUE; + + DBG("Field [%s] - [%s]", (gchar *)field, wifi_agent->name); + } + } else if (g_strcmp0(field, NETCONFIG_AGENT_FIELD_SSID) == 0) { + if (wifi_agent->ssid != NULL) { + g_byte_array_free(wifi_agent->ssid, TRUE); + wifi_agent->ssid = NULL; + } + + if (g_variant_is_of_type(value, G_VARIANT_TYPE_BYTESTRING)) { + guint8 char_value; + GVariantIter *iter1; + GByteArray *array = g_byte_array_new(); + + g_variant_get(value, "ay", &iter1); + while (g_variant_iter_loop(iter1, "y", &char_value)) + g_byte_array_append(array, &char_value, 1); + g_variant_iter_free(iter1); + if (array != NULL && (array->len > 0)) { + wifi_agent->ssid = g_byte_array_sized_new(array->len); + wifi_agent->ssid->len = array->len; + memcpy(wifi_agent->ssid->data, array->data, array->len); + updated = TRUE; + + DBG("Field [%s] - []", (gchar *)field); + } + } + } else if (g_strcmp0(field, NETCONFIG_AGENT_FIELD_IDENTITY) == 0) { + if (g_variant_is_of_type(value, G_VARIANT_TYPE_STRING)) { + wifi_agent->identity = g_strdup(g_variant_get_string(value, NULL)); + updated = TRUE; + + DBG("Field [%s] - [%s]", (gchar *)field, wifi_agent->identity); + } +#if defined TIZEN_CAPTIVE_PORTAL + } else if (g_strcmp0(field, NETCONFIG_AGENT_FIELD_USERNAME) == 0) { + if (g_variant_is_of_type(value, G_VARIANT_TYPE_STRING)) { + wifi_agent->username = g_strdup(g_variant_get_string(value, NULL)); + updated = TRUE; - DBG("Field [%s] - []", field); + DBG("Field [%s] - [%s]", (gchar *)field, wifi_agent->username); + } + } else if (g_strcmp0(field, NETCONFIG_AGENT_FIELD_PASSWORD) == 0) { + if (g_variant_is_of_type(value, G_VARIANT_TYPE_STRING)) { + wifi_agent->password = g_strdup(g_variant_get_string(value, NULL)); + updated = TRUE; + + DBG("Field [%s] - [%s]", (gchar *)field, wifi_agent->password); + } +#endif } } + g_variant_iter_free(iter); + + if (updated == TRUE) { + reply = netconfig_invoke_dbus_method_nonblock(CONNMAN_SERVICE, + service, CONNMAN_SERVICE_INTERFACE, "Connect", + NULL, __netconfig_wifi_connect_reply, + g_strdup(interface_name)); + if (reply != TRUE) { + ERR("Fail to connect Wi-Fi"); + __agent_clear_fields(wifi_agent); + error = g_error_new(G_DBUS_ERROR, + G_DBUS_ERROR_AUTH_FAILED, + CONNMAN_ERROR_INTERFACE ".InvalidArguments"); + + g_dbus_method_invocation_return_gerror(context, error); + g_clear_error(&error); + return TRUE; + } + } else { + ERR("Fail to connect Wi-Fi"); + __agent_clear_fields(wifi_agent); + + error = g_error_new(G_DBUS_ERROR, + G_DBUS_ERROR_AUTH_FAILED, + CONNMAN_ERROR_INTERFACE ".InvalidArguments"); + + g_dbus_method_invocation_return_gerror(context, error); + g_clear_error(&error); + return TRUE; + } + + net_connman_agent_complete_set_field(connman_agent, context); return TRUE; } -gboolean netconfig_iface_wifi_request_input(NetconfigWifi *wifi, - gchar *service, GHashTable *fields, - DBusGMethodInvocation *context) +gboolean handle_request_input(NetConnmanAgent *connman_agent, + GDBusMethodInvocation *context, const gchar *service, GVariant *fields) { - GHashTableIter iter; - gpointer field, value; - GHashTable *out_table = NULL; - GValue *ret_value = NULL; - - g_return_val_if_fail(wifi != NULL, FALSE); + GVariantIter *iter; + gchar *field = NULL; + GVariant *r_value = NULL; + GVariant *out_table = NULL; + gboolean updated = FALSE; + GVariantBuilder *builder = NULL; + GError *error = NULL; + const char *interface_name = NULL; + netconfig_wifi_agent_s *wifi_agent = NULL; + + g_return_val_if_fail(connman_agent != NULL, TRUE); if (NULL == service) - return FALSE; + return TRUE; DBG("Agent fields requested for service: %s", service); - out_table = g_hash_table_new_full(g_str_hash, g_str_equal, g_free, g_free); - if (NULL == out_table) - return FALSE; + interface_name = netconfig_get_ifname(service); + if (interface_name == NULL) { + error = g_error_new(G_DBUS_ERROR, + G_DBUS_ERROR_AUTH_FAILED, + CONNMAN_ERROR_INTERFACE ".InvalidService"); - g_hash_table_iter_init(&iter, fields); + g_dbus_method_invocation_return_gerror(context, error); + g_clear_error(&error); - while (g_hash_table_iter_next(&iter, &field, &value)) { - if (g_strcmp0(field, NETCONFIG_AGENT_FIELD_PASSPHRASE) == 0 && - agent.passphrase != NULL) { - ret_value = g_slice_new0(GValue); + return TRUE; + } - g_value_init(ret_value, G_TYPE_STRING); - g_value_set_string(ret_value, agent.passphrase); - g_hash_table_insert(out_table, g_strdup(field), ret_value); + wifi_agent = __agent_get_data(interface_name); + if (wifi_agent == NULL) { + error = g_error_new(G_DBUS_ERROR, + G_DBUS_ERROR_AUTH_FAILED, + CONNMAN_ERROR_INTERFACE ".InvalidService"); - DBG("Setting [%s] - []", field); - } else if (g_strcmp0(field, NETCONFIG_AGENT_FIELD_WPS) == 0 && - (agent.wps_pbc == TRUE || agent.wps_pin != NULL)) { - ret_value = g_slice_new0(GValue); + g_dbus_method_invocation_return_gerror(context, error); + g_clear_error(&error); + + return TRUE; + } - g_value_init(ret_value, G_TYPE_STRING); + builder = g_variant_builder_new(G_VARIANT_TYPE("a{sv}")); - if (agent.wps_pbc == TRUE) { + g_variant_get(fields, "a{sv}", &iter); + while (g_variant_iter_loop(iter, "{sv}", &field, &r_value)) { + + if (g_strcmp0(field, NETCONFIG_AGENT_FIELD_PASSPHRASE) == 0 && + wifi_agent->passphrase != NULL) { + g_variant_builder_add(builder, "{sv}", NETCONFIG_AGENT_FIELD_PASSPHRASE, + g_variant_new_string(wifi_agent->passphrase)); + + updated = TRUE; + DBG("Setting [%s] - [%s]", field, wifi_agent->passphrase); + } else if (g_strcmp0(field, NETCONFIG_AGENT_FIELD_WPS) == 0 && + (wifi_agent->wps_pbc == TRUE || wifi_agent->wps_pin != NULL)) { + if (wifi_agent->wps_pbc == TRUE) { /* Sending empty string for WPS push button method */ - g_value_set_string(ret_value, ""); + g_variant_builder_add(builder, "{sv}", NETCONFIG_AGENT_FIELD_WPS, + g_variant_new_string("")); + updated = TRUE; DBG("Setting empty string for [%s]", field); - } else if (agent.wps_pin != NULL) { - g_value_set_string(ret_value, agent.wps_pin); + } else if (wifi_agent->wps_pin != NULL) { + g_variant_builder_add(builder, "{sv}", NETCONFIG_AGENT_FIELD_WPS, + g_variant_new_string(wifi_agent->wps_pin)); - DBG("Setting string [%s] - []", field); + updated = TRUE; + DBG("Setting string [%s] - [%s]", field, wifi_agent->wps_pin); } + } else if (g_strcmp0(field, NETCONFIG_AGENT_FIELD_NAME) == 0 && + wifi_agent->name != NULL) { + g_variant_builder_add(builder, "{sv}", NETCONFIG_AGENT_FIELD_NAME, + g_variant_new_string(wifi_agent->name)); + + updated = TRUE; + DBG("Settings [%s] - [%s]", field, wifi_agent->name); + } else if (g_strcmp0(field, NETCONFIG_AGENT_FIELD_SSID) == 0 && + wifi_agent->ssid != NULL) { + int i = 0; + GVariantBuilder *builder1 = NULL; + builder1 = g_variant_builder_new(G_VARIANT_TYPE("ay")); + + for (i = 0; i < (wifi_agent->ssid->len); i++) + g_variant_builder_add(builder1, "y", wifi_agent->ssid->data[i]); + + g_variant_builder_add(builder, "{sv}", NETCONFIG_AGENT_FIELD_SSID, + g_variant_builder_end(builder1)); + + g_variant_builder_unref(builder1); + + updated = TRUE; + DBG("Settings [%s] - []", field); + } else if (g_strcmp0(field, NETCONFIG_AGENT_FIELD_IDENTITY) == 0 && + wifi_agent->identity != NULL) { + g_variant_builder_add(builder, "{sv}", NETCONFIG_AGENT_FIELD_IDENTITY, + g_variant_new_string(wifi_agent->identity)); + + updated = TRUE; + DBG("Settings [%s] - [%s]", field, wifi_agent->identity); +#if defined TIZEN_CAPTIVE_PORTAL + } else if (g_strcmp0(field, NETCONFIG_AGENT_FIELD_USERNAME) == 0 && + wifi_agent->username != NULL) { + g_variant_builder_add(builder, "{sv}", NETCONFIG_AGENT_FIELD_USERNAME, + g_variant_new_string(wifi_agent->username)); + + updated = TRUE; + DBG("Settings [%s] - [%s]", field, wifi_agent->username); + } else if (g_strcmp0(field, NETCONFIG_AGENT_FIELD_PASSWORD) == 0 && + wifi_agent->password != NULL) { + g_variant_builder_add(builder, "{sv}", NETCONFIG_AGENT_FIELD_PASSWORD, + g_variant_new_string(wifi_agent->password)); + + updated = TRUE; + DBG("Settings [%s] - [%s]", field, wifi_agent->password); +#endif + } + } + + out_table = g_variant_new("(@a{sv})", g_variant_builder_end(builder)); + + g_variant_builder_unref(builder); + + g_variant_iter_free(iter); + + + if (NULL == out_table) { + net_connman_agent_complete_request_input(connman_agent, context, out_table); + + return TRUE; + } + + if (updated == TRUE) + g_dbus_method_invocation_return_value(context, out_table); + else { + GError *error = NULL; + error = g_error_new(G_DBUS_ERROR, + G_DBUS_ERROR_AUTH_FAILED, + "net.connman.Agent.Error.Canceled"); + + g_dbus_method_invocation_return_gerror(context, error); + g_clear_error(&error); + } + + __agent_clear_fields(wifi_agent); + + return TRUE; +} + + +gboolean handle_report_error(NetConnmanAgent *connman_agent, + GDBusMethodInvocation *context, const gchar *service, const gchar *error) +{ + g_return_val_if_fail(connman_agent != NULL, TRUE); + + net_connman_agent_complete_report_error(connman_agent, context); + DBG("Agent error for service[%s] - [%s]", service, error); + + /* Do something when it failed to make a connection */ + + return TRUE; +} + +#if defined TIZEN_CAPTIVE_PORTAL +#if defined TIZEN_WEARABLE +#define QUERY_FOR_INTERNET_INTERVAL 2 +#define TIMER_THRESHOLD 4 +#else +#define QUERY_FOR_INTERNET_INTERVAL 20 +#define TIMER_THRESHOLD 120 +#endif + +static gboolean is_monitor_notifier_registered = FALSE; + +#if defined TIZEN_WEARABLE +static gboolean is_portal_msg_shown = FALSE; +#endif + +struct poll_timer_data { + guint time_elapsed; + guint timer_id; + void* data; +}; + +static struct poll_timer_data timer_data = { + QUERY_FOR_INTERNET_INTERVAL, 0, NULL}; - g_hash_table_insert(out_table, g_strdup(field), ret_value); +static gboolean __check_ignore_portal_list(const char * ssid) +{ + char def_str[1024]; + int i = 0; + int ignore_ap_count = 0; + + if (ssid == NULL) + return FALSE; + + DBG("checking ssid [%s]", ssid); + + DBG("csc string [%s]", def_str); + gchar ** ignore_ap_list = g_strsplit(def_str, ",", 0); + ignore_ap_count = g_strv_length(ignore_ap_list); + for (i = 0; i < ignore_ap_count; i++) { + DBG("[%d] - [%s]", i, ignore_ap_list[i]); + if (strncmp(ignore_ap_list[i], ssid, strlen(ssid)) == 0) { + g_strfreev(ignore_ap_list); + return TRUE; } } - dbus_g_method_return(context, out_table); + g_strfreev(ignore_ap_list); + return FALSE; +} + +static void __wifi_state_monitor(wifi_state_notifier_s *notifier, + char *service, wifi_service_state_e state, void *user_data); + +static wifi_state_notifier_s wifi_state_monitor_notifier = { + .notifier = NULL, + .service = NULL, + .wifi_state_changed = __wifi_state_monitor, + .user_data = NULL, +}; + +static void __wifi_state_monitor(wifi_state_notifier_s *notifier, + char *service, wifi_service_state_e state, void *user_data) +{ + DBG("Wi-Fi state: %x", state); + + if (state == NETCONFIG_WIFI_CONNECTED) + return; + + if (is_monitor_notifier_registered == TRUE) { + wifi_state_notifier_unregister(&wifi_state_monitor_notifier); + is_monitor_notifier_registered = FALSE; + } + +#if defined TIZEN_WEARABLE + is_portal_msg_shown = FALSE; +#endif + + /* suspend if Internet check activity in progress */ + if (timer_data.timer_id == 0) + return; + + netconfig_stop_timer(&timer_data.timer_id); + netconfig_stop_internet_check(); + + DBG("Stopped Internet accessibility check"); +} + +static gboolean __netconfig_wifi_portal_login_timeout(gpointer data) +{ + char *service_profile = NULL; + GVariant *reply = NULL; + + DBG(""); + + struct poll_timer_data *timer = (struct poll_timer_data *)data; + if (timer == NULL) + return FALSE; + + if (TRUE == netconfig_get_internet_status()) { + if (is_monitor_notifier_registered == TRUE) { + wifi_state_notifier_unregister(&wifi_state_monitor_notifier); + is_monitor_notifier_registered = FALSE; + } + + DBG("Portal logged in successfully and update ConnMan state"); + return FALSE; /* to stop the timer */ + } else { + if (timer->time_elapsed >= TIMER_THRESHOLD) { + DBG("Login failed, update ConnMan"); + + if (is_monitor_notifier_registered == TRUE) { + wifi_state_notifier_unregister(&wifi_state_monitor_notifier); + is_monitor_notifier_registered = FALSE; + } + + /* Disconnect and forget the AP */ + service_profile = (char *)netconfig_get_default_profile(); + if (service_profile && netconfig_is_wifi_profile(service_profile)) { + /* Now forget the AP*/ + reply = netconfig_invoke_dbus_method(CONNMAN_SERVICE, + service_profile, CONNMAN_SERVICE_INTERFACE, "Remove", + NULL); + + if (reply != NULL) + g_variant_unref(reply); + else + ERR("Failed to forget the AP "); + } + } else { + if (wifi_state_get_service_state(netconfig_get_default_ifname()) + == NETCONFIG_WIFI_CONNECTED) { + /* check Internet availability by sending and receiving data*/ + netconfig_check_internet_accessibility(); + /* Returning TRUE itself is enough to restart the timer */ + timer->time_elapsed = timer->time_elapsed + + QUERY_FOR_INTERNET_INTERVAL; + return TRUE; + } + } + } + + return FALSE; +} + +static void __netconfig_wifi_portal_login_timer_start(struct poll_timer_data + *data) +{ + DBG("__netconfig_wifi_browser_start_timer...starting timer"); + + if (data == NULL) + return; + + netconfig_stop_timer(&(data->timer_id)); + + /* Timer logic: After successful launch of browser, we would check for + * Internet status for every 20s until a threshold of 120s + */ + + data->time_elapsed = QUERY_FOR_INTERNET_INTERVAL; + netconfig_start_timer_seconds(QUERY_FOR_INTERNET_INTERVAL, + __netconfig_wifi_portal_login_timeout, data, &(data->timer_id)); +} +#endif + +gboolean handle_request_browser(NetConnmanAgent *connman_agent, + GDBusMethodInvocation *context, const gchar *service, const gchar *url) +{ +#if defined TIZEN_CAPTIVE_PORTAL + gboolean ignore_portal = FALSE; + const char * ssid = NULL; + + g_return_val_if_fail(connman_agent != NULL, TRUE); + + DBG("service[%s] - url[%s]", service, url); + + ssid = netconfig_wifi_get_connected_essid(netconfig_get_default_profile()); + if (ssid == NULL) { + ERR("Connected AP name is NULL!!"); + net_connman_agent_complete_request_browser(connman_agent, context); + return TRUE; + } + + ignore_portal = __check_ignore_portal_list(ssid); + + if (ignore_portal == TRUE) { + net_connman_agent_complete_request_browser(connman_agent, context); + return TRUE; + } + /* Register for Wifi state change notifier*/ + if (is_monitor_notifier_registered == FALSE) { + wifi_state_notifier_register(&wifi_state_monitor_notifier); + is_monitor_notifier_registered = TRUE; + } + + netconfig_send_notification_to_net_popup(NETCONFIG_ADD_PORTAL_NOTI, ssid); + + timer_data.time_elapsed = 0; + __netconfig_wifi_portal_login_timer_start(&timer_data); + + net_connman_agent_complete_request_browser(connman_agent, context); + return TRUE; +#else + GError *error = NULL; + error = g_error_new(G_DBUS_ERROR, + G_DBUS_ERROR_AUTH_FAILED, + CONNMAN_ERROR_INTERFACE ".NotSupported"); - __netconfig_agent_clear_fields(); + g_dbus_method_invocation_return_gerror(context, error); + g_clear_error(&error); return TRUE; +#endif }