diff options
-rw-r--r-- | mdk-stage1/NEWS | 2 | ||||
-rw-r--r-- | mdk-stage1/wireless.c | 161 |
2 files changed, 82 insertions, 81 deletions
diff --git a/mdk-stage1/NEWS b/mdk-stage1/NEWS index c278f1c5a..ad6352209 100644 --- a/mdk-stage1/NEWS +++ b/mdk-stage1/NEWS @@ -1,3 +1,5 @@ +- add support for WPA/WPA2 (mga#9541) + 2.49 - sync with kernel 5.9 diff --git a/mdk-stage1/wireless.c b/mdk-stage1/wireless.c index c9e363048..42039ef7a 100644 --- a/mdk-stage1/wireless.c +++ b/mdk-stage1/wireless.c @@ -1,7 +1,9 @@ /* * Olivier Blin (oblin) + * Martin Whitaker (martinw) * * Copyright 2005 Mandriva + * Copyright 2020 Mageia * * This software may be freely redistributed under the terms of the GNU * public license. @@ -16,7 +18,9 @@ #include <sys/types.h> #include <sys/socket.h> #include <errno.h> +#include <signal.h> #include <stdio.h> +#include <stdlib.h> #include <string.h> #include <unistd.h> #include <linux/types.h> @@ -29,11 +33,10 @@ #include "utils.h" #include "wireless.h" -static int wireless_ioctl(int socket, const char *ifname, int request, struct iwreq *wrq); -static int wireless_set_mode_managed(int socket, const char *ifname); -static int wireless_disable_key(int socket, const char *ifname); -static int wireless_set_restricted_key(int socket, const char *ifname, const char *key); -static int wireless_set_essid(int socket, const char *ifname, const char *essid); +#define WPA_SUPPLICANT_CONF "/etc/wpa_supplicant.conf" +#define WPA_SUPPLICANT_CTRL "/var/run/wpa_supplicant" +#define WPA_SUPPLICANT_LOG "/var/log/wpa_supplicant.log" +#define WPA_SUPPLICANT_PID "/var/run/wpa_supplicant.pid" int wireless_open_socket() { @@ -57,104 +60,100 @@ int wireless_is_aware(int socket, const char *ifname) return wireless_ioctl(socket, ifname, SIOCGIWNAME, &wrq) == 0; } -static int wireless_set_mode_managed(int socket, const char *ifname) -{ - struct iwreq wrq; - - wrq.u.mode = IW_MODE_INFRA; /* managed */ - - return wireless_ioctl(socket, ifname, SIOCSIWMODE, &wrq) == 0; -} - -static int wireless_set_essid(int socket, const char *ifname, const char *essid) -{ - struct iwreq wrq; - - wrq.u.essid.flags = 1; - wrq.u.essid.pointer = (void *) essid; - wrq.u.essid.length = strlen(essid) + 1; - - return wireless_ioctl(socket, ifname, SIOCSIWESSID, &wrq) == 0; -} - -static int wireless_disable_key(int socket, const char *ifname) -{ - struct iwreq wrq; - - wrq.u.data.flags = IW_ENCODE_DISABLED; - wrq.u.data.pointer = NULL; - wrq.u.data.length = 0; - - return wireless_ioctl(socket, ifname, SIOCSIWENCODE, &wrq) == 0; -} - -static int wireless_set_restricted_key(int socket, const char *ifname, const char *key) -{ - struct iwreq wrq; - char real_key[IW_ENCODING_TOKEN_MAX]; - int key_len = 0; - unsigned int tmp; - - while (sscanf(key + 2*key_len, "%2X", &tmp) == 1) - real_key[key_len++] = (char) tmp; - - wrq.u.data.flags = IW_ENCODE_RESTRICTED; - wrq.u.data.pointer = (char *) real_key; - wrq.u.data.length = key_len; - - return wireless_ioctl(socket, ifname, SIOCSIWENCODE, &wrq) == 0; -} - enum return_type configure_wireless(const char *ifname) { enum return_type results; - char * questions[] = { "ESSID", "WEP key", NULL }; - char * questions_auto[] = { "essid", "wep_key" }; + char * security[] = { "No security", "WEP", "WPA/WPA2 Personal", NULL }; + char * security_auto[] = { "none", "wep", "wpa_psk", NULL }; + char * choice = NULL; + char * message = NULL; + char * questions[] = { "ESSID", "", NULL }; + char * questions_auto[] = { "essid", "" }; + char * key_mgmt = NULL; static char ** answers = NULL; - int wsock = wireless_open_socket(); + FILE * fd; + char cmd[256]; + int status; + int wsock = wireless_open_socket(); if (!wireless_is_aware(wsock, ifname)) { log_message("interface %s doesn't support wireless", ifname); wireless_close_socket(wsock); return RETURN_OK; } + wireless_close_socket(wsock); - results = ask_from_entries_auto("Please enter your wireless settings. " - "The ESSID is your wireless network identifier. " - "The WEP key must be entered in hexadecimal, without any separator.", - questions, &answers, 32, questions_auto, NULL); + results = ask_from_list_auto("Please select your wireless security mode.", + security, &choice, "wireless_security", security_auto); if (results != RETURN_OK) { - wireless_close_socket(wsock); return RETURN_BACK; } - if (!wireless_set_mode_managed(wsock, ifname)) { - stg1_error_message("unable to set mode Managed on device \"%s\": %s", ifname, strerror(errno)); - wireless_close_socket(wsock); - return RETURN_ERROR; + if (streq(choice, security[2])) { + message = "Please enter your wireless settings. " + "The ESSID is your wireless network identifier. " + "The passphrase must be a string of 8 to 63 ASCII characters."; + questions[1] = "passphrase"; + questions_auto[1] = "wpa_psk"; + key_mgmt = "WPA-PSK"; + } else if (streq(choice, security[1])) { + message = "Please enter your wireless settings. " + "The ESSID is your wireless network identifier. " + "The WEP key must be a string of 10 or 26 hexadecimal digits, without any separators."; + questions[1] = "WEP key"; + questions_auto[1] = "wep_key"; + key_mgmt = "NONE"; + } else { + message = "Please enter your wireless settings. " + "The ESSID is your wireless network identifier."; + questions[1] = NULL; + questions_auto[1] = NULL; + key_mgmt = "NONE"; + } + results = ask_from_entries_auto(message, questions, &answers, 32, questions_auto, NULL); + if (results != RETURN_OK) { + return RETURN_BACK; } - if (answers[1] && !streq(answers[1], "")) { - log_message("setting WEP key \"%s\" on device \"%s\"", answers[1], ifname); - if (!wireless_set_restricted_key(wsock, ifname, answers[1])) { - stg1_error_message("unable to set WEP key \"%s\" on device \"%s\": %s", answers[1], ifname, strerror(errno)); - return RETURN_ERROR; - } - } else { - log_message("disabling WEP key on device \"%s\"", ifname); - if (!wireless_disable_key(wsock, ifname)) { - stg1_error_message("unable to disable WEP key on device \"%s\": %s", ifname, strerror(errno)); - return RETURN_ERROR; + fd = fopen(WPA_SUPPLICANT_PID, "r"); + if (fd) { + unsigned pid = 0; + unsigned count = fscanf(fd, "%u", &pid); + fclose(fd); + if (count == 1 && pid > 1) { + log_message("terminating wpa_supplicant (pid %u)", pid); + kill(pid, SIGQUIT); + sleep(1); } } - /* most devices perform discovery when ESSID is set, it needs to be last */ - log_message("setting ESSID \"%s\" on device \"%s\"", answers[0], ifname); - if (!wireless_set_essid(wsock, ifname, answers[0])) { - stg1_error_message("unable to set ESSID \"%s\" on device \"%s\": %s", answers[0], ifname, strerror(errno)); + fd = fopen(WPA_SUPPLICANT_CONF, "w"); + if (fd == NULL) { + stg1_error_message("unable to create " WPA_SUPPLICANT_CONF ": %s", strerror(errno)); + return RETURN_ERROR; + } + fprintf(fd, "ctrl_interface=" WPA_SUPPLICANT_CTRL "\n"); + fprintf(fd, "ap_scan=1\n"); + fprintf(fd, "network={\n"); + fprintf(fd, " key_mgmt=%s\n", key_mgmt); + fprintf(fd, " scan_ssid=1\n"); + fprintf(fd, " ssid=\"%s\"\n", answers[0]); + if (streq(choice, security[2])) { + fprintf(fd, " psk=\"%s\"\n", answers[1]); + } else if (streq(choice, security[1])) { + fprintf(fd, " wep_key0=%s\n", answers[1]); + } + fprintf(fd, "}\n"); + fclose(fd); + + snprintf(cmd, sizeof(cmd), "/usr/sbin/wpa_supplicant -B -i %s -c %s -f %s -P %s", + ifname, WPA_SUPPLICANT_CONF, WPA_SUPPLICANT_LOG, WPA_SUPPLICANT_PID); + log_message("running %s", cmd); + status = system(cmd); + if (status != 0) { + stg1_error_message("unable to start wpa_supplicant daemon for interface \"%s\": %d", ifname, status); return RETURN_ERROR; } - wireless_close_socket(wsock); return RETURN_OK; } |