/* * ESPRSSIF MIT License * * Copyright (c) 2015 * * Permission is hereby granted for use on ESPRESSIF SYSTEMS ESP8266 only, in which case, * it is free of charge, to any person obtaining a copy of this software and associated * documentation files (the "Software"), to deal in the Software without restriction, including * without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, * and/or sell copies of the Software, and to permit persons to whom the Software is furnished * to do so, subject to the following conditions: * * The above copyright notice and this permission notice shall be included in all copies or * substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS * FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR * COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER * IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. * */ #include "esp_common.h" #include "espconn.h" #include "freertos/FreeRTOS.h" #include "freertos/task.h" #include "freertos/queue.h" #include "soft_ap.h" #include "log.h" #include "user_main.h" #include "sniffer.h" #include "cfg.h" static int g_isNetReady = FALSE; #if 0 #define DEMO_AP_SSID "WT_TEST" #define DEMO_AP_PASSWORD "1234567abc" #define SOFT_AP_SSID "DEMO_AP" #define SOFT_AP_PASSWORD "12345678" void wifi_handle_event_cb(System_Event_t *evt) { printf("event %x\n", evt->event_id); switch (evt->event_id) { case EVENT_STAMODE_CONNECTED: printf("connect to ssid %s, channel %d\n", evt->event_info.connected.ssid, evt->event_info.connected.channel); break; case EVENT_STAMODE_DISCONNECTED: printf("disconnect from ssid %s, reason %d\n", evt->event_info.disconnected.ssid, evt->event_info.disconnected.reason); break; case EVENT_STAMODE_AUTHMODE_CHANGE: printf("mode: %d -> %d\n", evt->event_info.auth_change.old_mode, evt->event_info.auth_change.new_mode); break; case EVENT_STAMODE_GOT_IP: printf("ip:" IPSTR ",mask:" IPSTR ",gw:" IPSTR, IP2STR(&evt->event_info.got_ip.ip), IP2STR(&evt->event_info.got_ip.mask), IP2STR(&evt->event_info.got_ip.gw)); printf("\n"); break; case EVENT_SOFTAPMODE_STACONNECTED: printf("station: " MACSTR "join, AID = %d\n", MAC2STR(evt->event_info.sta_connected.mac), evt->event_info.sta_connected.aid); break; case EVENT_SOFTAPMODE_STADISCONNECTED: printf("station: " MACSTR "leave, AID = %d\n", MAC2STR(evt->event_info.sta_disconnected.mac), evt->event_info.sta_disconnected.aid); break; default: break; } } void conn_ap_init(void) { wifi_set_opmode(STATIONAP_MODE); struct station_config config; memset(&config,0,sizeof(config)); //set value of config from address of &config to width of size to be value '0' sprintf(config.ssid, DEMO_AP_SSID); sprintf(config.password, DEMO_AP_PASSWORD); wifi_station_set_config(&config); wifi_set_event_handler_cb(wifi_handle_event_cb); wifi_station_connect(); } #endif void wifi_event_handler_cb(System_Event_t *evt) { if (evt == NULL) { return; } //LOG_EX(LOG_Debug, "WIFI event = %d\n", evt->event_id); switch (evt->event_id) { case EVENT_STAMODE_CONNECTED: LOG_EX(LOG_Debug, "connect to ssid %s, channel %d\n", evt->event_info.connected.ssid, evt->event_info.connected.channel); break; case EVENT_STAMODE_DISCONNECTED: LOG_EX(LOG_Debug, "disconnect from ssid %s, reason %d\n", evt->event_info.disconnected.ssid, evt->event_info.disconnected.reason); g_isNetReady = FALSE; wifi_station_connect(); break; case EVENT_STAMODE_AUTHMODE_CHANGE: LOG_EX(LOG_Debug, "mode: %d -> %d\n", evt->event_info.auth_change.old_mode, evt->event_info.auth_change.new_mode); break; case EVENT_STAMODE_GOT_IP: LOG_EX(LOG_Debug, "ip:" IPSTR ",mask:" IPSTR ",gw:" IPSTR, IP2STR(&evt->event_info.got_ip.ip), IP2STR(&evt->event_info.got_ip.mask), IP2STR(&evt->event_info.got_ip.gw)); //init_sntp(); g_isNetReady = TRUE; break; case EVENT_SOFTAPMODE_STACONNECTED: LOG_EX(LOG_Debug, "station: " MACSTR "join, AID = %d\n", MAC2STR(evt->event_info.sta_connected.mac), evt->event_info.sta_connected.aid); break; case EVENT_SOFTAPMODE_STADISCONNECTED: LOG_EX(LOG_Debug, "station: " MACSTR "leave, AID = %d\n", MAC2STR(evt->event_info.sta_disconnected.mac), evt->event_info.sta_disconnected.aid); break; default: break; } } os_timer_t channel_timer; uint8 current_channel; uint16 channel_bits; os_timer_t check_sniffer; os_timer_t check_sniffer_2; SLIST_HEAD(router_info_head, router_info) router_list; void ICACHE_FLASH_ATTR sniffer_wifi_promiscuous_rx(uint8 *buf, uint16 buf_len) { uint8 *data; uint16 i; uint16 len; uint16 cnt = 0; if (buf_len == sizeof(struct RxControl)) { struct RxControl * rxCtrl = (struct RxControl *) buf; os_printf("[%sM%d%s] rssi%d, len%d\n", rxCtrl->CWB ? "H4" : "H2", rxCtrl->MCS, rxCtrl->FEC_CODING ? "L " : "", rxCtrl->rssi, rxCtrl->HT_length); return; } else if (buf_len == sizeof(struct sniffer_buf2)) { return; //manage pack } else { struct router_info *info = NULL; struct sniffer_buf * sniffer = (struct sniffer_buf *) buf; data = buf + sizeof(struct RxControl); SLIST_FOREACH(info, &router_list, next) { if ((data[1] & 0x01) == 0x01) { // just toDS if (memcmp(info->bssid, data + 4, 6) == 0) { if (current_channel - 1 != info->channel) { // check channel return; } else { break; } } } } if (info == NULL) { return; } struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) data; if (sniffer->cnt == 1) { len = sniffer->ampdu_info[0].length; //get ieee80211_hdr/data len to do user task os_printf("[len] %d, rssi %d\n", len, sniffer->rx_ctrl.rssi); } else { int i; os_printf("rx ampdu %d\n", sniffer->cnt); for (i = 0; i < sniffer->cnt; i++) { hdr->seq_ctrl = sniffer->ampdu_info[i].seq; memcpy(&hdr->addr3, sniffer->ampdu_info[i].address3, 6); len = sniffer->ampdu_info[i].length; //get ieee80211_hdr/data len to do user task os_printf("[LEN] %d, RSSI %d\n", len, sniffer->rx_ctrl.rssi); } } } } void ICACHE_FLASH_ATTR sniffer_channel_timer_cb(void *arg) { uint8 i; for (i = current_channel; i < 14; i++) { if ((channel_bits & (1 << i)) != 0) { current_channel = i + 1; wifi_set_channel(i); os_printf("current channel %d--------------------------------------------%d\n", i, system_get_time()); os_timer_arm(&channel_timer, 1000, 0); break; } } if (i == 14) { current_channel = 1; for (i = current_channel; i < 14; i++) { if ((channel_bits & (1 << i)) != 0) { current_channel = i + 1; wifi_set_channel(i); os_printf("current channel %d--------------------------------------------%d\n", i, system_get_time()); os_timer_arm(&channel_timer, 1000, 0); break; } } } } void ICACHE_FLASH_ATTR sniffer_wifi_scan_done(void *arg, STATUS status) { uint8 ssid[33]; channel_bits = 0; current_channel = 1; struct router_info *info = NULL; os_printf("%s(%d)\n", __FUNCTION__, __LINE__); while ((info = SLIST_FIRST(&router_list)) != NULL) { SLIST_REMOVE_HEAD(&router_list, next); free(info); } os_printf("%s(%d)\n", __FUNCTION__, __LINE__); if (status == OK) { uint8 i; struct bss_info *bss = (struct bss_info *) arg; while (bss != NULL) { if (bss->channel != 0) { struct router_info *info = NULL; os_printf("ssid %s, channel %d, authmode %d, rssi %d\n", bss->ssid, bss->channel, bss->authmode, bss->rssi); IHW_LOG_BUF(LOG_Debug, "***AP", bss->ssid, strlen(bss->ssid)); channel_bits |= 1 << (bss->channel); info = (struct router_info *) malloc(sizeof(struct router_info)); info->authmode = bss->authmode; info->channel = bss->channel; memcpy(info->bssid, bss->bssid, 6); SLIST_INSERT_HEAD(&router_list, info, next); } bss = STAILQ_NEXT(bss, next); } for (i = current_channel; i < 14; i++) { if ((channel_bits & (1 << i)) != 0) { current_channel = i + 1; wifi_set_channel(i); os_printf("current channel1 %d--------------------------------------------%d\n", i, system_get_time()); break; } } wifi_set_channel(1); wifi_promiscuous_enable(0); wifi_set_promiscuous_rx_cb(sniffer_wifi_promiscuous_rx); wifi_promiscuous_enable(1); os_timer_disarm(&channel_timer); os_timer_setfn(&channel_timer, sniffer_channel_timer_cb, NULL); os_timer_arm(&channel_timer, 1000, 0); } else { os_printf("err, scan status %d\n", status); } os_printf("%s(%d)\n", __FUNCTION__, __LINE__); } void wifi_connect_ap(const char* pSSID, int lenSSID, const char* pPasswd, int lenPasswd) { char buf[24]; #if 0 wifi_set_opmode(STATION_MODE); SLIST_INIT(&router_list); if(wifi_station_scan(NULL,sniffer_wifi_scan_done)){ os_printf("wifi_station_scan ok\n"); } return; #endif memset(buf, 0x3f, 24); wifi_set_opmode(STATION_MODE); wifi_set_event_handler_cb(wifi_event_handler_cb); wifi_station_set_auto_connect(1); if (pSSID && lenSSID > 0 && lenSSID < 32) { struct station_config config; //wifi_station_get_config(&config); bzero(&config, sizeof(struct station_config)); memcpy(config.ssid, pSSID, lenSSID); if (pPasswd && lenPasswd > 0 && lenPasswd < 64) { memcpy(config.password, pPasswd, lenPasswd); } wifi_station_set_config(&config); LOG_EX(LOG_Debug, "WIFI Conect: AP = [%s], Password = [%s]\n", pSSID, pPasswd); IHW_LOG_BUF(LOG_Debug, "AP", (char*)pSSID, strlen(pSSID)); IHW_LOG_BUF(LOG_Debug, "PD", (char*)pPasswd, strlen(pPasswd)); wifi_station_connect(); } else { LOG_EX(LOG_Debug, "WIFI Reconect......\n"); wifi_station_connect(); } } int soft_ap_network_ready(void) { return g_isNetReady; } void soft_ap_init(void) { u8_t mac[6]; wifi_set_event_handler_cb(NULL); wifi_set_opmode(STATIONAP_MODE); struct softap_config *config = (struct softap_config *) zalloc(sizeof(struct softap_config)); // initialization wifi_get_macaddr(SOFTAP_IF, mac); wifi_softap_get_config(config); // Get soft-AP config first. sprintf(config->ssid, USR_CFG_SOFTAP(SoftAPFormat), mac[4], mac[5]); //sprintf(config->password, SOFT_AP_PASSWORD); //config->authmode = AUTH_WPA_WPA2_PSK; config->authmode = AUTH_OPEN; config->ssid_len = 0; // or its actual SSID length config->max_connection = 4; wifi_softap_set_config(config); // Set ESP8266 soft-AP config LOG_EX(LOG_Info, "SSID: [%s], AUTH = NONE\n", config->ssid); free(config); struct station_info * station = wifi_softap_get_station_info(); while (station) { LOG_EX(LOG_Info, "bssid : MACSTR, ip : IPSTR/n", MAC2STR(station->bssid), IP2STR(&station->ip)); station = STAILQ_NEXT(station, next); } wifi_softap_free_station_info(); // Free it by calling functionss wifi_softap_dhcps_stop(); // disable soft-AP DHCP server struct ip_info info; info.ip.addr = ipaddr_addr(USR_CFG_SOFTAP_DHCP(IPAddr)); info.gw.addr = ipaddr_addr(USR_CFG_SOFTAP_DHCP(Gatway)); info.netmask.addr = ipaddr_addr(USR_CFG_SOFTAP_DHCP(Netmask)); // IP4_ADDR(&info.ip, 192, 168, 5, 1); // set IP // IP4_ADDR(&info.gw, 192, 168, 5, 1); // set gateway // IP4_ADDR(&info.netmask, 255, 255, 255, 0); // set netmask wifi_set_ip_info(SOFTAP_IF, &info); struct dhcps_lease dhcp_lease; dhcp_lease.start_ip.addr = ipaddr_addr(USR_CFG_SOFTAP_DHCP(DHCPStartIP)); dhcp_lease.end_ip.addr = ipaddr_addr(USR_CFG_SOFTAP_DHCP(DHCPEndIP)); // IP4_ADDR(&dhcp_lease.start_ip, 192, 168, 5, 100); // IP4_ADDR(&dhcp_lease.end_ip, 192, 168, 5, 105); wifi_softap_set_dhcps_lease(&dhcp_lease); wifi_softap_dhcps_start(); // enable soft-AP DHCP server }