From: Niraj Kumar Goit Date: Tue, 25 Jul 2017 13:32:31 +0000 (+0530) Subject: [net-config]Added Dbus methods to Add, Get and Remove VSIE. X-Git-Tag: submit/tizen/20170803.074947~1^2 X-Git-Url: http://review.tizen.org/git/?p=platform%2Fcore%2Fconnectivity%2Fnet-config.git;a=commitdiff_plain;h=e9c8d09e55f577800288ccfd60ae189bfb51c417 [net-config]Added Dbus methods to Add, Get and Remove VSIE. Change-Id: I90958c730daa33238f9837f5d346a3cbeff73116 Signed-off-by: Niraj Kumar Goit --- diff --git a/include/wifi-config.h b/include/wifi-config.h index 891cd0d..d84f2f2 100755 --- a/include/wifi-config.h +++ b/include/wifi-config.h @@ -47,6 +47,18 @@ extern "C" { #define WIFI_CONFIG_EAP_AUTH_TYPE "EapAuthType" #define WIFI_CONFIG_EAP_SUBJECT_MATCH "SubjectMatch" +/** + * This enumeration is used in frame id value in vsie method calls + */ +typedef enum { + NETCONFIG_VSIE_FRAME_ASSOC_REQ = 13, + NETCONFIG_VSIE_FRAME_PROBE_REQ = 14, + NETCONFIG_VSIE_FRAME_REASSOC = 15, + NETCONFIG_VSIE_FRAME_AUTH_REQ = 16, + NETCONFIG_VSIE_FRAME_ACTION = 17, + NETCONFIG_VSIE_FRAME_MAX +} netconfig_vsie_frames_e; + gboolean wifi_config_get_config_id(const gchar *service_profile, gchar **config_id); gboolean wifi_config_remove_configuration(const gchar *config_id); @@ -59,6 +71,10 @@ gboolean handle_remove_configuration(Wifi *wifi, GDBusMethodInvocation *context, gboolean handle_set_config_field(Wifi *wifi, GDBusMethodInvocation *context, const gchar *config_id, const gchar *key, const gchar *value); gboolean handle_get_config_passphrase(Wifi *wifi, GDBusMethodInvocation *context, const gchar *config_id); +gboolean handle_add_vsie(Wifi *wifi, GDBusMethodInvocation *context, int frame_id, const gchar *vsie); +gboolean handle_get_vsie(Wifi *wifi, GDBusMethodInvocation *context, int frame_id); +gboolean handle_remove_vsie(Wifi *wifi, GDBusMethodInvocation *context, int frame_id, const gchar *vsie); + #ifdef __cplusplus } #endif diff --git a/interfaces/netconfig-iface-wifi.xml b/interfaces/netconfig-iface-wifi.xml index 4a253ec..85374c4 100755 --- a/interfaces/netconfig-iface-wifi.xml +++ b/interfaces/netconfig-iface-wifi.xml @@ -136,6 +136,18 @@ + + + + + + + + + + + + diff --git a/src/wifi-config.c b/src/wifi-config.c index c90e77c..84a64a6 100755 --- a/src/wifi-config.c +++ b/src/wifi-config.c @@ -32,6 +32,7 @@ #include "util.h" #include "neterror.h" #include "wifi-config.h" +#include "netsupplicant.h" #define CONNMAN_STORAGE "/var/lib/connman" @@ -593,6 +594,315 @@ gboolean wifi_config_remove_configuration(const gchar *config_id) return ret; } +static int __netconfig_hex_char_to_num(char c) +{ + if (c >= '0' && c <= '9') + return c - '0'; + + if (c >= 'a' && c <= 'f') + return c - 'a' + 10; + + if (c >= 'A' && c <= 'F') + return c - 'A' + 10; + + return -1; +} + +static int __netconfig_hex_to_byte(const char *hex) +{ + int a, b; + + a = __netconfig_hex_char_to_num(*hex++); + if (a < 0) + return -1; + + b = __netconfig_hex_char_to_num(*hex++); + if (b < 0) + return -1; + + return (a << 4) | b; +} + +static int __netconfig_hex_str_to_bin(const char *hex, unsigned char *buf, size_t len) +{ + size_t i; + int a; + const char *ipos = hex; + unsigned char *opos = buf; + + for (i = 0; i < len; i++) { + a = __netconfig_hex_to_byte(ipos); + if (a < 0) + return -1; + + *opos++ = a; + ipos += 2; + } + + return 0; +} + +static int __netconfig_byte_to_txt(const unsigned char *src, char **dst, int src_len) +{ + int dst_length = 0; + int i = 0; + char *buf = NULL; + + if (src_len <= 0) { + ERR("Invalid parameter."); + return -1; + } + + *dst = (char *) g_try_malloc0((2*src_len)+1); + if (!(*dst)) { + ERR("failed to allocate memory to buffer."); + return -1; + } + + buf = (*dst); + + for (i = 0; i < src_len; i++) { + snprintf(buf, 3, "%02x", src[i]); + buf += 2; + dst_length += 2; + } + + return dst_length; +} + +static int __netconfig_unpack_ay_malloc(unsigned char **dst, GVariantIter *iter) +{ + GVariantIter *iter_copy = NULL; + int length = 0; + char tmp = 0; + unsigned char *tmp_dst = NULL; + + if (!dst || *dst || !iter) { + ERR("Invalid parameter"); + return 0; + } + + iter_copy = g_variant_iter_copy(iter); + + while (g_variant_iter_loop(iter, "y", &tmp)) + length++; + g_variant_iter_free(iter); + + tmp_dst = (unsigned char *)g_try_malloc0(length + 1); + if (!tmp_dst) { + ERR("failed to allocate memory"); + return 0; + } + + length = 0; + while (g_variant_iter_loop(iter_copy, "y", &tmp_dst[length])) + length++; + g_variant_iter_free(iter_copy); + + if (length == 0) { + g_free(tmp_dst); + tmp_dst = NULL; + } else { + tmp_dst[length] = '\0'; + } + + *dst = tmp_dst; + DBG("Length [%d]", length); + return length; +} + +gboolean _add_vsie(int frame_id, const char* vsie) +{ + GVariant *params = NULL; + GVariant *message = NULL; + GVariantBuilder *bytearray_builder = NULL; + const char *if_path; + int i = 0; + size_t vsie_len = 0; + + unsigned char *bytearray = NULL; + size_t bytearray_len = 0; + + if (frame_id >= NETCONFIG_VSIE_FRAME_MAX) { + DBG("Invalid parameter, frame-id: %d", frame_id); + return FALSE; + } + + vsie_len = strlen(vsie); + if (vsie_len == 0) { + DBG("vsie length is zero"); + return FALSE; + } + + bytearray_len = (vsie_len % 2) ? ((vsie_len / 2) + 1) : (vsie_len / 2); + + bytearray = (unsigned char *) g_try_malloc0(bytearray_len); + if (bytearray == NULL) { + DBG("Failed to allocate memory to bytearray"); + return FALSE; + } + + if (__netconfig_hex_str_to_bin(vsie, bytearray, bytearray_len) < 0) { + DBG("invalid vsie string"); + g_free(bytearray); + return FALSE; + } + + bytearray_builder = g_variant_builder_new(G_VARIANT_TYPE("ay")); + for (i = 0; i < bytearray_len; i++) + g_variant_builder_add(bytearray_builder, "y", bytearray[i]); + + params = g_variant_new("(iay)", frame_id, bytearray_builder); + g_variant_builder_unref(bytearray_builder); + + if_path = netconfig_wifi_get_supplicant_interface(); + + if (if_path == NULL) { + ERR("Fail to get wpa_supplicant DBus path"); + g_free(bytearray); + return FALSE; + } + + message = netconfig_supplicant_invoke_dbus_method(SUPPLICANT_SERVICE, + if_path, SUPPLICANT_INTERFACE ".Interface", "VendorElemAdd", params); + + if (message == NULL) { + ERR("Failed to send command to wpa_supplicant"); + g_free(bytearray); + return FALSE; + } + + DBG("Succeeded to add vsie: Frame ID[%d], VSIE[%s]", frame_id, vsie); + + g_free(bytearray); + return TRUE; +} + +gboolean _get_vsie(int frame_id, char **vsie) +{ + GVariant *params = NULL; + GVariant *message = NULL; + const char *if_path; + + if (frame_id >= NETCONFIG_VSIE_FRAME_MAX) { + DBG("Invalid parameter, frame-id: %d", frame_id); + return FALSE; + } + + if_path = netconfig_wifi_get_supplicant_interface(); + if (if_path == NULL) { + ERR("Fail to get wpa_supplicant DBus path"); + return FALSE; + } + + params = g_variant_new("(i)", frame_id); + + message = netconfig_supplicant_invoke_dbus_method(SUPPLICANT_SERVICE, + if_path, SUPPLICANT_INTERFACE ".Interface", "VendorElemGet", params); + + if (message == NULL) { + ERR("Failed to send command to wpa_supplicant"); + return FALSE; + } else { + GVariantIter *iter = NULL; + unsigned char *vsie_bytes = NULL; + int vsie_len = 0; + int ret = 0; + + g_variant_get(message, "(ay)", &iter); + if (iter == NULL) { + ERR("vsie is not present"); + return FALSE; + } + + vsie_len = __netconfig_unpack_ay_malloc(&vsie_bytes, iter); + if (vsie_bytes == NULL) { + ERR("vsie_bytes not allocated"); + return FALSE; + } + + ret = __netconfig_byte_to_txt(vsie_bytes, vsie, vsie_len); + if (ret < 0) { + g_free(vsie_bytes); + ERR("vsie not allocated."); + return FALSE; + } + + g_free(vsie_bytes); + } + + ERR("Succeeded to get vsie: Frame ID[%d], VSIE[%s]", frame_id, *vsie); + + return TRUE; + +} + +gboolean _remove_vsie(int frame_id, const char *vsie) +{ + GVariant *params = NULL; + GVariant *message = NULL; + GVariantBuilder *bytearray_builder = NULL; + const char *if_path; + int i = 0; + size_t vsie_len = 0; + + unsigned char *bytearray = NULL; + size_t bytearray_len = 0; + + if (frame_id >= NETCONFIG_VSIE_FRAME_MAX) { + DBG("Invalid parameter, frame-id: %d", frame_id); + return FALSE; + } + + vsie_len = strlen(vsie); + if (vsie_len == 0) { + DBG("vsie length is zero"); + return FALSE; + } + + bytearray_len = (vsie_len % 2) ? ((vsie_len / 2) + 1) : (vsie_len / 2); + + bytearray = (unsigned char *) g_try_malloc0(bytearray_len); + if (bytearray == NULL) { + DBG("Failed to allocate memory to bytearray"); + return FALSE; + } + + if (__netconfig_hex_str_to_bin(vsie, bytearray, bytearray_len) < 0) { + DBG("invalid vsie string"); + g_free(bytearray); + return FALSE; + } + + bytearray_builder = g_variant_builder_new(G_VARIANT_TYPE("ay")); + for (i = 0; i < bytearray_len; i++) + g_variant_builder_add(bytearray_builder, "y", bytearray[i]); + + params = g_variant_new("(iay)", frame_id, bytearray_builder); + g_variant_builder_unref(bytearray_builder); + + if_path = netconfig_wifi_get_supplicant_interface(); + if (if_path == NULL) { + ERR("Fail to get wpa_supplicant DBus path"); + g_free(bytearray); + return FALSE; + } + + message = netconfig_supplicant_invoke_dbus_method(SUPPLICANT_SERVICE, + if_path, SUPPLICANT_INTERFACE ".Interface", "VendorElemRem", params); + + if (message == NULL) { + ERR("Failed to send command to wpa_supplicant"); + g_free(bytearray); + return FALSE; + } + + DBG("Succeeded to remove vsie: Frame ID[%d], VSIE[%s]", frame_id, vsie); + + g_free(bytearray); + return TRUE; +} + /* dbus method */ gboolean handle_get_config_ids(Wifi *wifi, GDBusMethodInvocation *context) { @@ -1201,3 +1511,68 @@ gboolean handle_get_config_passphrase(Wifi *wifi, GDBusMethodInvocation *context return ret; } + +gboolean handle_add_vsie(Wifi *wifi, GDBusMethodInvocation *context, + int frame_id, const gchar *vsie) +{ + DBG("Frame ID: [%d] VSIE: [%s]", frame_id, vsie); + + g_return_val_if_fail(wifi != NULL, FALSE); + g_return_val_if_fail(vsie != NULL, FALSE); + + gboolean ret = FALSE; + + ret = _add_vsie(frame_id, vsie); + if (!ret) { + DBG("Failed to add vsie: %s", vsie); + netconfig_error_dbus_method_return(context, NETCONFIG_ERROR_INTERNAL, "OperationFailed"); + return ret; + } + + wifi_complete_add_vsie(wifi, context); + return ret; +} + +gboolean handle_get_vsie(Wifi *wifi, GDBusMethodInvocation *context, + int frame_id) +{ + DBG("Frame ID: [%d]", frame_id); + + g_return_val_if_fail(wifi != NULL, FALSE); + + gboolean ret = FALSE; + gchar *vsie = NULL; + + ret = _get_vsie(frame_id, &vsie); + if (!ret) { + DBG("Failed to get vsie for frame:[%d]", frame_id); + netconfig_error_dbus_method_return(context, NETCONFIG_ERROR_INTERNAL, "OperationFailed"); + return ret; + } + + DBG("Received vsie: %s", vsie); + wifi_complete_get_vsie(wifi, context, vsie); + + return ret; +} + +gboolean handle_remove_vsie(Wifi *wifi, GDBusMethodInvocation *context, + int frame_id, const gchar *vsie) +{ + DBG("Frame ID: [%d] VSIE: [%s]", frame_id, vsie); + + g_return_val_if_fail(wifi != NULL, FALSE); + g_return_val_if_fail(vsie != NULL, FALSE); + + gboolean ret = FALSE; + + ret = _remove_vsie(frame_id, vsie); + if (!ret) { + DBG("Failed to remove vsie: %s", vsie); + netconfig_error_dbus_method_return(context, NETCONFIG_ERROR_INTERNAL, "OperationFailed"); + return ret; + } + + wifi_complete_remove_vsie(wifi, context); + return ret; +} diff --git a/src/wifi.c b/src/wifi.c index dd4dcc5..429a68c 100755 --- a/src/wifi.c +++ b/src/wifi.c @@ -181,6 +181,14 @@ void wifi_object_create_and_init(void) g_signal_connect(wifi_object, "handle-delete-eap-config", G_CALLBACK(handle_delete_eap_config), NULL); + /* VSIE methods */ + g_signal_connect(wifi_object, "handle-add-vsie", + G_CALLBACK(handle_add_vsie), NULL); + g_signal_connect(wifi_object, "handle-get-vsie", + G_CALLBACK(handle_get_vsie), NULL); + g_signal_connect(wifi_object, "handle-remove-vsie", + G_CALLBACK(handle_remove_vsie), NULL); + /* WIFI configuration */ g_signal_connect(wifi_object, "handle-save-configuration", G_CALLBACK(handle_save_configuration), NULL);