📄 wpa_supplicant.c
字号:
struct wpa_ssid * wpa_supplicant_get_ssid(struct wpa_supplicant *wpa_s)
{
struct wpa_ssid *entry;
u8 ssid[MAX_SSID_LEN];
int res;
size_t ssid_len;
u8 bssid[ETH_ALEN];
int wired;
if (wpa_s->use_client_mlme) {
if (ieee80211_sta_get_ssid(wpa_s, ssid, &ssid_len)) {
wpa_printf(MSG_WARNING, "Could not read SSID from "
"MLME.");
return NULL;
}
} else {
res = wpa_drv_get_ssid(wpa_s, ssid);
if (res < 0) {
wpa_printf(MSG_WARNING, "Could not read SSID from "
"driver.");
return NULL;
}
ssid_len = res;
}
if (wpa_s->use_client_mlme)
os_memcpy(bssid, wpa_s->bssid, ETH_ALEN);
else if (wpa_drv_get_bssid(wpa_s, bssid) < 0) {
wpa_printf(MSG_WARNING, "Could not read BSSID from driver.");
return NULL;
}
wired = wpa_s->conf->ap_scan == 0 && wpa_s->driver &&
os_strcmp(wpa_s->driver->name, "wired") == 0;
entry = wpa_s->conf->ssid;
while (entry) {
if (!entry->disabled &&
((ssid_len == entry->ssid_len &&
os_memcmp(ssid, entry->ssid, ssid_len) == 0) || wired) &&
(!entry->bssid_set ||
os_memcmp(bssid, entry->bssid, ETH_ALEN) == 0))
return entry;
entry = entry->next;
}
return NULL;
}
#ifndef CONFIG_NO_WPA
static u8 * _wpa_alloc_eapol(void *wpa_s, u8 type,
const void *data, u16 data_len,
size_t *msg_len, void **data_pos)
{
return wpa_alloc_eapol(wpa_s, type, data, data_len, msg_len, data_pos);
}
static int _wpa_ether_send(void *wpa_s, const u8 *dest, u16 proto,
const u8 *buf, size_t len)
{
return wpa_ether_send(wpa_s, dest, proto, buf, len);
}
static void _wpa_supplicant_req_scan(void *wpa_s, int sec, int usec)
{
wpa_supplicant_req_scan(wpa_s, sec, usec);
}
static void _wpa_supplicant_cancel_auth_timeout(void *wpa_s)
{
wpa_supplicant_cancel_auth_timeout(wpa_s);
}
static void _wpa_supplicant_set_state(void *wpa_s, wpa_states state)
{
wpa_supplicant_set_state(wpa_s, state);
}
static wpa_states _wpa_supplicant_get_state(void *wpa_s)
{
return wpa_supplicant_get_state(wpa_s);
}
static void _wpa_supplicant_disassociate(void *wpa_s, int reason_code)
{
wpa_supplicant_disassociate(wpa_s, reason_code);
}
static void _wpa_supplicant_deauthenticate(void *wpa_s, int reason_code)
{
wpa_supplicant_deauthenticate(wpa_s, reason_code);
}
static struct wpa_ssid * _wpa_supplicant_get_ssid(void *wpa_s)
{
return wpa_supplicant_get_ssid(wpa_s);
}
static int wpa_supplicant_get_bssid(void *ctx, u8 *bssid)
{
struct wpa_supplicant *wpa_s = ctx;
if (wpa_s->use_client_mlme) {
os_memcpy(bssid, wpa_s->bssid, ETH_ALEN);
return 0;
}
return wpa_drv_get_bssid(wpa_s, bssid);
}
static int wpa_supplicant_set_key(void *wpa_s, wpa_alg alg,
const u8 *addr, int key_idx, int set_tx,
const u8 *seq, size_t seq_len,
const u8 *key, size_t key_len)
{
return wpa_drv_set_key(wpa_s, alg, addr, key_idx, set_tx, seq, seq_len,
key, key_len);
}
static int wpa_supplicant_mlme_setprotection(void *wpa_s, const u8 *addr,
int protection_type,
int key_type)
{
return wpa_drv_mlme_setprotection(wpa_s, addr, protection_type,
key_type);
}
static int wpa_supplicant_add_pmkid(void *wpa_s,
const u8 *bssid, const u8 *pmkid)
{
return wpa_drv_add_pmkid(wpa_s, bssid, pmkid);
}
static int wpa_supplicant_remove_pmkid(void *wpa_s,
const u8 *bssid, const u8 *pmkid)
{
return wpa_drv_remove_pmkid(wpa_s, bssid, pmkid);
}
#ifdef CONFIG_DRIVER_RALINK
static void wpa_supplicant_poll(void *wpa_s)
{
wpa_drv_poll(wpa_s);
}
#endif
#endif /* CONFIG_NO_WPA */
static int wpa_supplicant_set_driver(struct wpa_supplicant *wpa_s,
const char *name)
{
int i;
if (wpa_s == NULL)
return -1;
if (wpa_supplicant_drivers[0] == NULL) {
wpa_printf(MSG_ERROR, "No driver interfaces build into "
"wpa_supplicant.");
return -1;
}
if (name == NULL) {
/* default to first driver in the list */
wpa_s->driver = wpa_supplicant_drivers[0];
return 0;
}
for (i = 0; wpa_supplicant_drivers[i]; i++) {
if (os_strcmp(name, wpa_supplicant_drivers[i]->name) == 0) {
wpa_s->driver = wpa_supplicant_drivers[i];
return 0;
}
}
wpa_printf(MSG_ERROR, "Unsupported driver '%s'.\n", name);
return -1;
}
void wpa_supplicant_rx_eapol(void *ctx, const u8 *src_addr,
const u8 *buf, size_t len)
{
struct wpa_supplicant *wpa_s = ctx;
// if(wpa_s->wpa_state < WPA_ASSOCIATED) //<--carella modify
if((wpa_s->wpa->proto == WPA_PROTO_RSN && wpa_s->wpa->pmksa == NULL && wpa_s->wpa_state < WPA_ASSOCIATED) || //<--carella modify
(wpa_s->wpa->proto != WPA_PROTO_RSN && wpa_s->wpa_state < WPA_ASSOCIATED))
{
printf("wpa_supplicant_rx_eapol: wpa_s->wpa_state[%d] < WPA_ASSOCIATED\n", wpa_s->wpa_state);
return; //-->carella
}
wpa_printf(MSG_DEBUG, "RX EAPOL from " MACSTR, MAC2STR(src_addr));
wpa_hexdump(MSG_MSGDUMP, "RX EAPOL", buf, len);
if (wpa_s->key_mgmt == WPA_KEY_MGMT_NONE) {
wpa_printf(MSG_DEBUG, "Ignored received EAPOL frame since "
"no key management is configured");
return;
}
if (wpa_s->eapol_received == 0) {
/* Timeout for completing IEEE 802.1X and WPA authentication */
wpa_supplicant_req_auth_timeout(
wpa_s,
(wpa_s->key_mgmt == WPA_KEY_MGMT_IEEE8021X ||
wpa_s->key_mgmt == WPA_KEY_MGMT_IEEE8021X_NO_WPA) ?
70 : 10, 0);
}
wpa_s->eapol_received++;
if (wpa_s->countermeasures) {
wpa_printf(MSG_INFO, "WPA: Countermeasures - dropped EAPOL "
"packet");
return;
}
/* Source address of the incoming EAPOL frame could be compared to the
* current BSSID. However, it is possible that a centralized
* Authenticator could be using another MAC address than the BSSID of
* an AP, so just allow any address to be used for now. The replies are
* still sent to the current BSSID (if available), though. */
os_memcpy(wpa_s->last_eapol_src, src_addr, ETH_ALEN);
if (wpa_s->key_mgmt != WPA_KEY_MGMT_PSK &&
eapol_sm_rx_eapol(wpa_s->eapol, src_addr, buf, len) > 0)
return;
wpa_drv_poll(wpa_s);
wpa_sm_rx_eapol(wpa_s->wpa, src_addr, buf, len);
}
/**
* wpa_supplicant_driver_init - Initialize driver interface parameters
* @wpa_s: Pointer to wpa_supplicant data
* @wait_for_interface: 0 = do not wait for the interface (reports a failure if
* the interface is not present), 1 = wait until the interface is available
* Returns: 0 on success, -1 on failure
*
* This function is called to initialize driver interface parameters.
* wpa_drv_init() must have been called before this function to initialize the
* driver interface.
*/
int wpa_supplicant_driver_init(struct wpa_supplicant *wpa_s,
int wait_for_interface)
{
static int interface_count = 0;
for (;;) {
if (wpa_s->driver->send_eapol) {
const u8 *addr = wpa_drv_get_mac_addr(wpa_s);
if (addr)
os_memcpy(wpa_s->own_addr, addr, ETH_ALEN);
break;
}
wpa_s->l2 = l2_packet_init(wpa_s->ifname,
wpa_drv_get_mac_addr(wpa_s),
ETH_P_EAPOL,
wpa_supplicant_rx_eapol, wpa_s, 0);
if (wpa_s->l2)
break;
else if (!wait_for_interface)
return -1;
wpa_printf(MSG_DEBUG, "Waiting for interface..");
os_sleep(5, 0);
}
if (wpa_s->l2 && l2_packet_get_own_addr(wpa_s->l2, wpa_s->own_addr)) {
wpa_printf(MSG_ERROR, "Failed to get own L2 address");
return -1;
}
wpa_printf(MSG_DEBUG, "Own MAC address: " MACSTR,
MAC2STR(wpa_s->own_addr));
if (wpa_s->bridge_ifname[0]) {
wpa_printf(MSG_DEBUG, "Receiving packets from bridge interface"
" '%s'", wpa_s->bridge_ifname);
wpa_s->l2_br = l2_packet_init(wpa_s->bridge_ifname,
wpa_s->own_addr,
ETH_P_EAPOL,
wpa_supplicant_rx_eapol, wpa_s,
0);
if (wpa_s->l2_br == NULL) {
wpa_printf(MSG_ERROR, "Failed to open l2_packet "
"connection for the bridge interface '%s'",
wpa_s->bridge_ifname);
return -1;
}
}
/* Backwards compatibility call to set_wpa() handler. This is called
* only just after init and just before deinit, so these handler can be
* used to implement same functionality. */
if (wpa_drv_set_wpa(wpa_s, 1) < 0) {
struct wpa_driver_capa capa;
if (wpa_drv_get_capa(wpa_s, &capa) < 0 ||
!(capa.flags & (WPA_DRIVER_CAPA_KEY_MGMT_WPA |
WPA_DRIVER_CAPA_KEY_MGMT_WPA2))) {
wpa_printf(MSG_DEBUG, "Driver does not support WPA.");
/* Continue to allow non-WPA modes to be used. */
} else {
wpa_printf(MSG_ERROR, "Failed to enable WPA in the "
"driver.");
return -1;
}
}
wpa_clear_keys(wpa_s, NULL);
/* Make sure that TKIP countermeasures are not left enabled (could
* happen if wpa_supplicant is killed during countermeasures. */
wpa_drv_set_countermeasures(wpa_s, 0);
wpa_drv_set_drop_unencrypted(wpa_s, 1);
wpa_s->prev_scan_ssid = BROADCAST_SSID_SCAN;
wpa_supplicant_req_scan(wpa_s, interface_count, 100000);
interface_count++;
return 0;
}
static int wpa_supplicant_daemon(const char *pid_file)
{
wpa_printf(MSG_DEBUG, "Daemonize..");
return os_daemonize(pid_file);
}
static struct wpa_supplicant * wpa_supplicant_alloc(void)
{
struct wpa_supplicant *wpa_s;
wpa_s = os_zalloc(sizeof(*wpa_s));
if (wpa_s == NULL)
return NULL;
wpa_s->scan_req = 1;
return wpa_s;
}
static int wpa_supplicant_init_iface(struct wpa_supplicant *wpa_s,
struct wpa_interface *iface)
{
wpa_printf(MSG_DEBUG, "Initializing interface '%s' conf '%s' driver "
"'%s' ctrl_interface '%s' bridge '%s'", iface->ifname,
iface->confname ? iface->confname : "N/A",
iface->driver ? iface->driver : "default",
iface->ctrl_interface ? iface->ctrl_interface : "N/A",
iface->bridge_ifname ? iface->bridge_ifname : "N/A");
if (wpa_supplicant_set_driver(wpa_s, iface->driver) < 0) {
return -1;
}
if (iface->confname) {
#ifdef CONFIG_BACKEND_FILE
wpa_s->confname = os_rel2abs_path(iface->confname);
if (wpa_s->confname == NULL) {
wpa_printf(MSG_ERROR, "Failed to get absolute path "
"for configuration file '%s'.",
iface->confname);
return -1;
}
wpa_printf(MSG_DEBUG, "Configuration file '%s' -> '%s'",
iface->confname, wpa_s->confname);
#else /* CONFIG_BACKEND_FILE */
wpa_s->confname = os_strdup(iface->confname);
#endif /* CONFIG_BACKEND_FILE */
wpa_s->conf = wpa_config_read(wpa_s->confname);
if (wpa_s->conf == NULL) {
wpa_printf(MSG_ERROR, "Failed to read or parse "
"configuration '%s'.", wpa_s->confname);
return -1;
}
/*
* Override ctrl_interface and driver_param if set on command
* line.
*/
if (iface->ctrl_interface) {
os_free(wpa_s->conf->ctrl_interface);
wpa_s->conf->ctrl_interface =
os_strdup(iface->ctrl_interface);
}
if (iface->driver_param) {
os_free(wpa_s->conf->driver_param);
wpa_s->conf->driver_param =
os_strdup(iface->driver_param);
}
} else
wpa_s->conf = wpa_config_alloc_empty(iface->ctrl_interface,
iface->driver_param);
if (wpa_s->conf == NULL) {
wpa_printf(MSG_ERROR, "\nNo configuration found.");
return -1;
}
if (iface->ifname == NULL) {
wpa_printf(MSG_ERROR, "\nInterface name is required.");
return -1;
}
if (os_strlen(iface->ifname) >= sizeof(wpa_s->ifname)) {
wpa_printf(MSG_ERROR, "\nToo long interface name '%s'.",
iface->ifname);
return -1;
}
os_strncpy(wpa_s->ifname, iface->ifname, sizeof(wpa_s->ifname));
if (iface->bridge_ifname) {
if (os_strlen(iface->bridge_ifname) >=
sizeof(wpa_s->bridge_ifname)) {
wpa_printf(MSG_ERROR, "\nToo long bridge interface "
"name '%s'.", iface->bridge_ifname);
return -1;
}
os_strn
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -