📄 driver_test.c
字号:
struct wpa_driver_test_data *drv; drv = os_zalloc(sizeof(*drv)); if (drv == NULL) return NULL; drv->ctx = ctx; drv->test_socket = -1; /* Set dummy BSSID and SSID for testing. */ drv->bssid[0] = 0x02; drv->bssid[1] = 0x00; drv->bssid[2] = 0x00; drv->bssid[3] = 0x00; drv->bssid[4] = 0x00; drv->bssid[5] = 0x01; os_memcpy(drv->ssid, "test", 5); drv->ssid_len = 4; /* Generate a MAC address to help testing with multiple STAs */ drv->own_addr[0] = 0x02; /* locally administered */ sha1_prf((const u8 *) ifname, os_strlen(ifname), "wpa_supplicant test mac addr generation", NULL, 0, drv->own_addr + 1, ETH_ALEN - 1); return drv;}static void wpa_driver_test_close_test_socket(struct wpa_driver_test_data *drv){ if (drv->test_socket >= 0) { eloop_unregister_read_sock(drv->test_socket); close(drv->test_socket); drv->test_socket = -1; } if (drv->own_socket_path) { unlink(drv->own_socket_path); os_free(drv->own_socket_path); drv->own_socket_path = NULL; }}static void wpa_driver_test_deinit(void *priv){ struct wpa_driver_test_data *drv = priv; wpa_driver_test_close_test_socket(drv); eloop_cancel_timeout(wpa_driver_test_scan_timeout, drv, drv->ctx); os_free(drv->test_dir); os_free(drv);}static int wpa_driver_test_attach(struct wpa_driver_test_data *drv, const char *dir){ static unsigned int counter = 0; struct sockaddr_un addr; size_t len; os_free(drv->own_socket_path); if (dir) { len = os_strlen(dir) + 30; drv->own_socket_path = os_malloc(len); if (drv->own_socket_path == NULL) return -1; os_snprintf(drv->own_socket_path, len, "%s/STA-" MACSTR, dir, MAC2STR(drv->own_addr)); } else { drv->own_socket_path = os_malloc(100); if (drv->own_socket_path == NULL) return -1; os_snprintf(drv->own_socket_path, 100, "/tmp/wpa_supplicant_test-%d-%d", getpid(), counter++); } drv->test_socket = socket(PF_UNIX, SOCK_DGRAM, 0); if (drv->test_socket < 0) { perror("socket(PF_UNIX)"); os_free(drv->own_socket_path); drv->own_socket_path = NULL; return -1; } os_memset(&addr, 0, sizeof(addr)); addr.sun_family = AF_UNIX; os_strncpy(addr.sun_path, drv->own_socket_path, sizeof(addr.sun_path)); if (bind(drv->test_socket, (struct sockaddr *) &addr, sizeof(addr)) < 0) { perror("bind(PF_UNIX)"); close(drv->test_socket); unlink(drv->own_socket_path); os_free(drv->own_socket_path); drv->own_socket_path = NULL; return -1; } eloop_register_read_sock(drv->test_socket, wpa_driver_test_receive_unix, drv, NULL); return 0;}static int wpa_driver_test_set_param(void *priv, const char *param){ struct wpa_driver_test_data *drv = priv; const char *pos, *pos2; size_t len; wpa_printf(MSG_DEBUG, "%s: param='%s'", __func__, param); if (param == NULL) return 0; wpa_driver_test_close_test_socket(drv); pos = os_strstr(param, "test_socket="); if (pos) { pos += 12; pos2 = os_strchr(pos, ' '); if (pos2) len = pos2 - pos; else len = os_strlen(pos); if (len > sizeof(drv->hostapd_addr.sun_path)) return -1; os_memset(&drv->hostapd_addr, 0, sizeof(drv->hostapd_addr)); drv->hostapd_addr.sun_family = AF_UNIX; os_memcpy(drv->hostapd_addr.sun_path, pos, len); drv->hostapd_addr_set = 1; } pos = os_strstr(param, "test_dir="); if (pos) { char *end; os_free(drv->test_dir); drv->test_dir = os_strdup(pos + 9); if (drv->test_dir == NULL) return -1; end = os_strchr(drv->test_dir, ' '); if (end) *end = '\0'; wpa_driver_test_attach(drv, drv->test_dir); } else wpa_driver_test_attach(drv, NULL); if (os_strstr(param, "use_associnfo=1")) { wpa_printf(MSG_DEBUG, "test_driver: Use AssocInfo events"); drv->use_associnfo = 1; }#ifdef CONFIG_CLIENT_MLME if (os_strstr(param, "use_mlme=1")) { wpa_printf(MSG_DEBUG, "test_driver: Use internal MLME"); drv->use_mlme = 1; }#endif /* CONFIG_CLIENT_MLME */ return 0;}static const u8 * wpa_driver_test_get_mac_addr(void *priv){ struct wpa_driver_test_data *drv = priv; wpa_printf(MSG_DEBUG, "%s", __func__); return drv->own_addr;}static int wpa_driver_test_send_eapol(void *priv, const u8 *dest, u16 proto, const u8 *data, size_t data_len){ struct wpa_driver_test_data *drv = priv; struct msghdr msg; struct iovec io[3]; struct l2_ethhdr eth; struct sockaddr_un addr; wpa_hexdump(MSG_MSGDUMP, "test_send_eapol TX frame", data, data_len); os_memset(ð, 0, sizeof(eth)); os_memcpy(eth.h_dest, dest, ETH_ALEN); os_memcpy(eth.h_source, drv->own_addr, ETH_ALEN); eth.h_proto = host_to_be16(proto); io[0].iov_base = "EAPOL "; io[0].iov_len = 6; io[1].iov_base = (u8 *) ð io[1].iov_len = sizeof(eth); io[2].iov_base = (u8 *) data; io[2].iov_len = data_len; os_memset(&msg, 0, sizeof(msg)); msg.msg_iov = io; msg.msg_iovlen = 3; if (os_memcmp(dest, drv->bssid, ETH_ALEN) == 0 || drv->test_dir == NULL) { msg.msg_name = &drv->hostapd_addr; msg.msg_namelen = sizeof(drv->hostapd_addr); } else { struct stat st; os_memset(&addr, 0, sizeof(addr)); addr.sun_family = AF_UNIX; os_snprintf(addr.sun_path, sizeof(addr.sun_path), "%s/STA-" MACSTR, drv->test_dir, MAC2STR(dest)); if (stat(addr.sun_path, &st) < 0) { os_snprintf(addr.sun_path, sizeof(addr.sun_path), "%s/AP-" MACSTR, drv->test_dir, MAC2STR(dest)); } msg.msg_name = &addr; msg.msg_namelen = sizeof(addr); } if (sendmsg(drv->test_socket, &msg, 0) < 0) { perror("sendmsg(test_socket)"); return -1; } return 0;}static int wpa_driver_test_get_capa(void *priv, struct wpa_driver_capa *capa){ struct wpa_driver_test_data *drv = priv; os_memset(capa, 0, sizeof(*capa)); capa->key_mgmt = WPA_DRIVER_CAPA_KEY_MGMT_WPA | WPA_DRIVER_CAPA_KEY_MGMT_WPA2 | WPA_DRIVER_CAPA_KEY_MGMT_WPA_PSK | WPA_DRIVER_CAPA_KEY_MGMT_WPA2_PSK | WPA_DRIVER_CAPA_KEY_MGMT_WPA_NONE; capa->enc = WPA_DRIVER_CAPA_ENC_WEP40 | WPA_DRIVER_CAPA_ENC_WEP104 | WPA_DRIVER_CAPA_ENC_TKIP | WPA_DRIVER_CAPA_ENC_CCMP; capa->auth = WPA_DRIVER_AUTH_OPEN | WPA_DRIVER_AUTH_SHARED | WPA_DRIVER_AUTH_LEAP; if (drv->use_mlme) capa->flags |= WPA_DRIVER_FLAGS_USER_SPACE_MLME; return 0;}static int wpa_driver_test_mlme_setprotection(void *priv, const u8 *addr, int protect_type, int key_type){ wpa_printf(MSG_DEBUG, "%s: protect_type=%d key_type=%d", __func__, protect_type, key_type); if (addr) { wpa_printf(MSG_DEBUG, "%s: addr=" MACSTR, __func__, MAC2STR(addr)); } return 0;}#ifdef CONFIG_CLIENT_MLMEstatic struct wpa_hw_modes *wpa_driver_test_get_hw_feature_data(void *priv, u16 *num_modes, u16 *flags){ struct wpa_hw_modes *modes; *num_modes = 1; *flags = 0; modes = os_zalloc(*num_modes * sizeof(struct wpa_hw_modes)); if (modes == NULL) return NULL; modes[0].mode = WPA_MODE_IEEE80211G; modes[0].num_channels = 1; modes[0].num_rates = 1; modes[0].channels = os_zalloc(sizeof(struct wpa_channel_data)); modes[0].rates = os_zalloc(sizeof(struct wpa_rate_data)); if (modes[0].channels == NULL || modes[0].rates == NULL) { ieee80211_sta_free_hw_features(modes, *num_modes); return NULL; } modes[0].channels[0].chan = 1; modes[0].channels[0].freq = 2412; modes[0].channels[0].flag = WPA_CHAN_W_SCAN | WPA_CHAN_W_ACTIVE_SCAN; modes[0].rates[0].rate = 10; modes[0].rates[0].flags = WPA_RATE_BASIC | WPA_RATE_SUPPORTED | WPA_RATE_CCK | WPA_RATE_MANDATORY; return modes;}int wpa_driver_test_set_channel(void *priv, wpa_hw_mode phymode, int chan, int freq){ wpa_printf(MSG_DEBUG, "%s: phymode=%d chan=%d freq=%d", __func__, phymode, chan, freq); return 0;}static int wpa_driver_test_send_mlme(void *priv, const u8 *data, size_t data_len){ struct wpa_driver_test_data *drv = priv; struct msghdr msg; struct iovec io[2]; struct sockaddr_un addr; const u8 *dest; struct dirent *dent; DIR *dir; wpa_hexdump(MSG_MSGDUMP, "test_send_mlme", data, data_len); if (data_len < 10) return -1; dest = data + 4; io[0].iov_base = "MLME "; io[0].iov_len = 5; io[1].iov_base = (u8 *) data; io[1].iov_len = data_len; os_memset(&msg, 0, sizeof(msg)); msg.msg_iov = io; msg.msg_iovlen = 2; if (os_memcmp(dest, drv->bssid, ETH_ALEN) == 0 || drv->test_dir == NULL) { msg.msg_name = &drv->hostapd_addr; msg.msg_namelen = sizeof(drv->hostapd_addr); } else if (os_memcmp(dest, "\xff\xff\xff\xff\xff\xff", ETH_ALEN) == 0) { dir = opendir(drv->test_dir); if (dir == NULL) return -1; while ((dent = readdir(dir))) {#ifdef _DIRENT_HAVE_D_TYPE /* Skip the file if it is not a socket. * Also accept DT_UNKNOWN (0) in case * the C library or underlying file * system does not support d_type. */ if (dent->d_type != DT_SOCK && dent->d_type != DT_UNKNOWN) continue;#endif /* _DIRENT_HAVE_D_TYPE */ if (os_strcmp(dent->d_name, ".") == 0 || os_strcmp(dent->d_name, "..") == 0) continue; wpa_printf(MSG_DEBUG, "%s: Send broadcast MLME to %s", __func__, dent->d_name); os_memset(&addr, 0, sizeof(addr)); addr.sun_family = AF_UNIX; os_snprintf(addr.sun_path, sizeof(addr.sun_path), "%s/%s", drv->test_dir, dent->d_name); msg.msg_name = &addr; msg.msg_namelen = sizeof(addr); if (sendmsg(drv->test_socket, &msg, 0) < 0) perror("sendmsg(test_socket)"); } closedir(dir); return 0; } else { struct stat st; os_memset(&addr, 0, sizeof(addr)); addr.sun_family = AF_UNIX; os_snprintf(addr.sun_path, sizeof(addr.sun_path), "%s/AP-" MACSTR, drv->test_dir, MAC2STR(dest)); if (stat(addr.sun_path, &st) < 0) { os_snprintf(addr.sun_path, sizeof(addr.sun_path), "%s/STA-" MACSTR, drv->test_dir, MAC2STR(dest)); } msg.msg_name = &addr; msg.msg_namelen = sizeof(addr); } if (sendmsg(drv->test_socket, &msg, 0) < 0) { perror("sendmsg(test_socket)"); return -1; } return 0;}static int wpa_driver_test_mlme_add_sta(void *priv, const u8 *addr, const u8 *supp_rates, size_t supp_rates_len){ wpa_printf(MSG_DEBUG, "%s: addr=" MACSTR, __func__, MAC2STR(addr)); return 0;}static int wpa_driver_test_mlme_remove_sta(void *priv, const u8 *addr){ wpa_printf(MSG_DEBUG, "%s: addr=" MACSTR, __func__, MAC2STR(addr)); return 0;}int wpa_driver_test_set_ssid(void *priv, const u8 *ssid, size_t ssid_len){ wpa_printf(MSG_DEBUG, "%s", __func__); return 0;}int wpa_driver_test_set_bssid(void *priv, const u8 *bssid){ wpa_printf(MSG_DEBUG, "%s: bssid=" MACSTR, __func__, MAC2STR(bssid)); return 0;}#endif /* CONFIG_CLIENT_MLME */const struct wpa_driver_ops wpa_driver_test_ops = { "test", "wpa_supplicant test driver", wpa_driver_test_get_bssid, wpa_driver_test_get_ssid, wpa_driver_test_set_wpa, wpa_driver_test_set_key, wpa_driver_test_init, wpa_driver_test_deinit, wpa_driver_test_set_param, NULL /* set_countermeasures */, NULL /* set_drop_unencrypted */, wpa_driver_test_scan, wpa_driver_test_get_scan_results, wpa_driver_test_deauthenticate, wpa_driver_test_disassociate, wpa_driver_test_associate, NULL /* set_auth_alg */, NULL /* add_pmkid */, NULL /* remove_pmkid */, NULL /* flush_pmkid */, wpa_driver_test_get_capa, NULL /* poll */, NULL /* get_ifname */, wpa_driver_test_get_mac_addr, wpa_driver_test_send_eapol, NULL /* set_operstate */, wpa_driver_test_mlme_setprotection,#ifdef CONFIG_CLIENT_MLME wpa_driver_test_get_hw_feature_data, wpa_driver_test_set_channel, wpa_driver_test_set_ssid, wpa_driver_test_set_bssid, wpa_driver_test_send_mlme, wpa_driver_test_mlme_add_sta, wpa_driver_test_mlme_remove_sta#else /* CONFIG_CLIENT_MLME */ NULL /* get_hw_feature_data */, NULL /* set_channel */, NULL /* set_ssid */, NULL /* set_bssid */, NULL /* send_mlme */, NULL /* mlme_add_sta */, NULL /* mlme_remove_sta */#endif /* CONFIG_CLIENT_MLME */};
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -