Signed-off-by: Jintao Lin <jintaolin@xxxxxxxxxxxx> BUG=b:254714993 TEST=on device, check the interface creation and removal by using dbus command, > gdbus call --system --dest fi.w1.wpa_supplicant1 --object-path /fi/w1/wpa_supplicant1 --method fi.w1.wpa_supplicant1.CreateInterface "{'Ifname':<'wlan1'>, 'Driver':<'nl80211'>, 'ConfigFile':<'/usr/lib64/shill/shims/wpa_supplicant.conf'>, 'Create':<true>, 'Type':<'ap'>}" > iwconfig wlan1 > gdbus call --system --dest fi.w1.wpa_supplicant1 --object-path /fi/w1/wpa_supplicant1 --method fi.w1.wpa_supplicant1.RemoveInterface '/fi/w1/wpa_supplicant1/Interfaces/1' > ifconfig -a Change-Id: Idc987db638cdc68fc13fe34d430e212f6ce37e13 --- doc/dbus.doxygen | 2 + wpa_supplicant/dbus/dbus_new_handlers.c | 63 ++++++++++++++++++++++++- 2 files changed, 63 insertions(+), 2 deletions(-) diff --git a/doc/dbus.doxygen b/doc/dbus.doxygen index 075c2d5bf..b2e267605 100644 --- a/doc/dbus.doxygen +++ b/doc/dbus.doxygen @@ -41,6 +41,8 @@ registered in the bus with fi.w1.wpa_supplicant1 name. <tr><td>BridgeIfname</td><td>s</td><td>Name of the bridge interface to control, e.g., br0</td><td>No</td> <tr><td>Driver</td><td>s</td><td>Driver name which the interface uses, e.g., nl80211</td><td>No</td> <tr><td>ConfigFile</td><td>s</td><td>Configuration file path</td><td>No</td> + <tr><td>Create</td><td>b</td><td>Whether to create a new interface in the kernel</td><td>No</td> + <tr><td>Type</td><td>s</td><td>Interface type to create</td><td>No</td> </table> </dd> </dl> diff --git a/wpa_supplicant/dbus/dbus_new_handlers.c b/wpa_supplicant/dbus/dbus_new_handlers.c index c1f147398..ed27d5d64 100644 --- a/wpa_supplicant/dbus/dbus_new_handlers.c +++ b/wpa_supplicant/dbus/dbus_new_handlers.c @@ -755,6 +755,10 @@ DBusMessage * wpas_dbus_handler_create_interface(DBusMessage *message, char *ifname = NULL; char *confname = NULL; char *bridge_ifname = NULL; + char *type = NULL; + bool create_iface = false; + enum wpa_driver_if_type if_type = WPA_IF_STATION; + u8 mac_addr[ETH_ALEN]; dbus_message_iter_init(message, &iter); @@ -791,6 +795,17 @@ DBusMessage * wpas_dbus_handler_create_interface(DBusMessage *message, wpa_dbus_dict_entry_clear(&entry); if (bridge_ifname == NULL) goto oom; + } else if (os_strcmp(entry.key, "Create") == 0 && + entry.type == DBUS_TYPE_BOOLEAN) { + create_iface = entry.bool_value; + wpa_dbus_dict_entry_clear(&entry); + } else if (os_strcmp(entry.key, "Type") == 0 && + entry.type == DBUS_TYPE_STRING) { + os_free(type); + type = os_strdup(entry.str_value); + wpa_dbus_dict_entry_clear(&entry); + if (type == NULL) + goto oom; } else { wpa_dbus_dict_entry_clear(&entry); goto error; @@ -800,6 +815,26 @@ DBusMessage * wpas_dbus_handler_create_interface(DBusMessage *message, if (ifname == NULL) goto error; /* Required Ifname argument missing */ + if (create_iface) { + if (os_strcmp(type, "sta") == 0) { + if_type = WPA_IF_STATION; + } else if (os_strcmp(type, "ap") == 0) { + if_type = WPA_IF_AP_BSS; + } else { + goto error; + } + + wpa_printf(MSG_DEBUG, "%s[dbus]: creating an interface '%s'", + __func__, ifname); + if (!global->ifaces || wpa_drv_if_add(global->ifaces, if_type, ifname, + NULL, NULL, NULL, mac_addr, NULL) < 0) { + reply = wpas_dbus_error_unknown_error( + message, + "interface creation failed."); + goto out; + } + } + /* * Try to get the wpa_supplicant record for this iface, return * an error if we already control it. @@ -808,6 +843,7 @@ DBusMessage * wpas_dbus_handler_create_interface(DBusMessage *message, reply = dbus_message_new_error( message, WPAS_DBUS_ERROR_IFACE_EXISTS, "wpa_supplicant already controls this interface."); + goto fail; } else { struct wpa_supplicant *wpa_s; struct wpa_interface iface; @@ -822,6 +858,7 @@ DBusMessage * wpas_dbus_handler_create_interface(DBusMessage *message, if (wpa_s && wpa_s->dbus_new_path) { const char *path = wpa_s->dbus_new_path; + wpa_s->added_vif = create_iface; reply = dbus_message_new_method_return(message); dbus_message_append_args(reply, DBUS_TYPE_OBJECT_PATH, &path, DBUS_TYPE_INVALID); @@ -829,6 +866,7 @@ DBusMessage * wpas_dbus_handler_create_interface(DBusMessage *message, reply = wpas_dbus_error_unknown_error( message, "wpa_supplicant couldn't grab this interface."); + goto fail; } } @@ -837,6 +875,7 @@ out: os_free(ifname); os_free(confname); os_free(bridge_ifname); + os_free(type); return reply; error: @@ -845,6 +884,10 @@ error: oom: reply = wpas_dbus_error_no_memory(message); goto out; +fail: + if (create_iface) + wpa_drv_if_remove(global->ifaces, WPA_IF_STATION, ifname); + goto out; } @@ -865,19 +908,35 @@ DBusMessage * wpas_dbus_handler_remove_interface(DBusMessage *message, struct wpa_supplicant *wpa_s; char *path; DBusMessage *reply = NULL; + unsigned int delete_iface; dbus_message_get_args(message, NULL, DBUS_TYPE_OBJECT_PATH, &path, DBUS_TYPE_INVALID); wpa_s = get_iface_by_dbus_path(global, path); - if (wpa_s == NULL) + if (wpa_s == NULL) { reply = wpas_dbus_error_iface_unknown(message); - else if (wpa_supplicant_remove_iface(global, wpa_s, 0)) { + goto out; + } + delete_iface = wpa_s->added_vif; + if (wpa_supplicant_remove_iface(global, wpa_s, 0)) { reply = wpas_dbus_error_unknown_error( message, "wpa_supplicant couldn't remove this interface."); + goto out; } + if (delete_iface) { + wpa_printf(MSG_DEBUG, "%s[dbus]: deleting the interface '%s'", + __func__, wpa_s->ifname); + if (wpa_drv_if_remove(global->ifaces, WPA_IF_STATION, wpa_s->ifname)) { + reply = wpas_dbus_error_unknown_error( + message, + "wpa_supplicant couldn't delete this interface."); + } + } + +out: return reply; } -- 2.38.1.273.g43a17bfeac-goog _______________________________________________ Hostap mailing list Hostap@xxxxxxxxxxxxxxxxxxx http://lists.infradead.org/mailman/listinfo/hostap