Host library for controlling a WiConnect enabled Wi-Fi module.
Dependents: wiconnect-ota_example wiconnect-web_setup_example wiconnect-test-console wiconnect-tcp_server_example ... more
Diff: internal/network/NetworkInterface.cpp
- Revision:
- 0:ea85c4bb5e1f
- Child:
- 1:6ec9998427ad
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/internal/network/NetworkInterface.cpp Mon Aug 11 09:58:24 2014 +0000 @@ -0,0 +1,493 @@ +/* + * Copyright 2014, ACKme Networks + * All Rights Reserved. + * + * This is UNPUBLISHED PROPRIETARY SOURCE CODE of ACKme Networks; + * the contents of this file may not be disclosed to third parties, copied + * or duplicated in any form, in whole or in part, without the prior + * written permission of ACKme Networks. + */ + + +#include "Wiconnect.h" +#include "internal/common.h" +#include "StringUtil.h" + + +#define IPV4_FORMAT "%d.%d.%d.%d" +#define IPV4_ARGS(ip) \ + (int)( (ip) & 0xff), \ + (int)(((ip) >> 8) & 0xff), \ + (int)(((ip) >> 16) & 0xff), \ + (int)(((ip) >> 24) & 0xff) + + + +/*************************************************************************************************/ +NetworkInterface::NetworkInterface(Wiconnect *wiconnect_) +{ + wiconnect = wiconnect_; +} + +/*************************************************************************************************/ +WiconnectResult NetworkInterface::ping(const char *domain, uint32_t *timeMsPtr) +{ + WiconnectResult result; + + CHECK_OTHER_COMMAND_EXECUTING(); + + if(WICONNECT_SUCCEEDED(result, wiconnect->sendCommand(completeHandler, "ping %s", (domain == NULL) ? "-g" : domain)) && + timeMsPtr != NULL) + { + if(sscanf(wiconnect->internalBuffer, "Ping reply in %ums", timeMsPtr) != 1) + { + result = WICONNECT_RESPONSE_PARSE_ERROR; + } + } + + CHECK_CLEANUP_COMMAND(); + + return result; +} + +/*************************************************************************************************/ +WiconnectResult NetworkInterface::lookup(const char *domain, uint32_t *ipAddressPtr) +{ + WiconnectResult result; + + CHECK_OTHER_COMMAND_EXECUTING(); + + if(WICONNECT_SUCCEEDED(result, wiconnect->sendCommand("nlo %s", domain))) + { + if(!NetworkInterface::strToIp(wiconnect->internalBuffer, ipAddressPtr)) + { + result = WICONNECT_RESPONSE_PARSE_ERROR; + } + } + + CHECK_CLEANUP_COMMAND(); + + return result; +} + +/*************************************************************************************************/ +WiconnectResult NetworkInterface::setDhcpEnabled(bool enabled) +{ + WiconnectResult result; + + CHECK_OTHER_COMMAND_EXECUTING(); + + result = wiconnect->sendCommand(CMD_SET_NETWORK_DHCP, enabled); + + CHECK_CLEANUP_COMMAND(); + + return result; +} + +/*************************************************************************************************/ +WiconnectResult NetworkInterface::getDhcpEnabled(bool *enabledPtr) +{ + WiconnectResult result; + + CHECK_OTHER_COMMAND_EXECUTING(); + + if(WICONNECT_SUCCEEDED(result, wiconnect->sendCommand("get network.dhcp"))) + { + int32_t enabled; + if(WICONNECT_SUCCEEDED(result, wiconnect->responseToInt32(&enabled))) + { + *enabledPtr = (bool)enabled; + } + } + + CHECK_CLEANUP_COMMAND(); + + return result; +} + +/*************************************************************************************************/ +WiconnectResult NetworkInterface::setIpSettings(uint32_t ip, uint32_t netmask, uint32_t gateway) +{ + WiconnectResult result; + + enum + { + FS_SET_IP, + FS_SET_NETMASK, + FS_SET_GATEWAY + }; + + CHECK_OTHER_COMMAND_EXECUTING(); + + if(wiconnect->internalProcessingState == FS_SET_IP) + { + if(WICONNECT_SUCCEEDED(result, wiconnect->sendCommand(CMD_SET_STATIC_IP, IPV4_ARGS(ip)))) + { + wiconnect->internalProcessingState = FS_SET_NETMASK; + } + } + + if(wiconnect->internalProcessingState == FS_SET_NETMASK) + { + if(WICONNECT_SUCCEEDED(result, wiconnect->sendCommand(CMD_SET_STATIC_NETMASK, IPV4_ARGS(netmask)))) + { + wiconnect->internalProcessingState = FS_SET_GATEWAY; + } + } + + if(wiconnect->internalProcessingState == FS_SET_GATEWAY) + { + if(WICONNECT_SUCCEEDED(result, wiconnect->sendCommand(CMD_SET_STATIC_GATEWAY, IPV4_ARGS(gateway)))) + { + } + } + + CHECK_CLEANUP_COMMAND(); + + return result; +} + +/*************************************************************************************************/ +WiconnectResult NetworkInterface::setIpSettings(const char* ipStr, const char* netmaskStr, const char* gatewayStr) +{ + uint32_t ip, nm, gw; + + if( !NetworkInterface::strToIp(ipStr, &ip) || + !NetworkInterface::strToIp(netmaskStr, &nm) || + !NetworkInterface::strToIp(gatewayStr, &gw)) + { + return WICONNECT_ERROR; + } + return setIpSettings(ip, nm, gw); +} + +/*************************************************************************************************/ +WiconnectResult NetworkInterface::getIpSettings(uint32_t *ip, uint32_t *netmask, uint32_t *gateway) +{ + WiconnectResult result; + + enum + { + FS_GET_IP, + FS_GET_NETMASK, + FS_GET_GATEWAY + }; + + CHECK_OTHER_COMMAND_EXECUTING(); + + if(wiconnect->internalProcessingState == FS_GET_IP) + { + if(WICONNECT_SUCCEEDED(result, wiconnect->sendCommand("get network.ip"))) + { + if(!NetworkInterface::strToIp(wiconnect->internalBuffer, ip)) + { + result = WICONNECT_RESPONSE_PARSE_ERROR; + wiconnect->internalProcessingState = FS_GET_NETMASK; + } + } + } + + if(wiconnect->internalProcessingState == FS_GET_NETMASK) + { + if(WICONNECT_SUCCEEDED(result, wiconnect->sendCommand("get network.netmask"))) + { + if(!NetworkInterface::strToIp(wiconnect->internalBuffer, netmask)) + { + result = WICONNECT_RESPONSE_PARSE_ERROR; + wiconnect->internalProcessingState = FS_GET_GATEWAY; + } + } + } + + if(wiconnect->internalProcessingState == FS_GET_GATEWAY) + { + if(WICONNECT_SUCCEEDED(result, wiconnect->sendCommand("get network.gateway"))) + { + if(!NetworkInterface::strToIp(wiconnect->internalBuffer, gateway)) + { + result = WICONNECT_RESPONSE_PARSE_ERROR; + } + } + } + + CHECK_CLEANUP_COMMAND(); + + return result; +} +/*************************************************************************************************/ +WiconnectResult NetworkInterface::getSignalStrength(NetworkSignalStrength *signalStrengthPtr) +{ + WiconnectResult result; + int32_t rssi_dbm; + + CHECK_OTHER_COMMAND_EXECUTING(); + + if(WICONNECT_SUCCEEDED(result, wiconnect->sendCommand("rssi"))) + { + if(!WICONNECT_FAILED(result, wiconnect->responseToInt32(&rssi_dbm))) + { + *signalStrengthPtr = NetworkInterface::rssiToSignalStrength(rssi_dbm); + } + } + + if(result == WICONNECT_CMD_RESPONSE_ERROR) + { + *signalStrengthPtr = NETWORK_RSSI_UNKNOWN; + result = WICONNECT_SUCCESS; + } + + CHECK_CLEANUP_COMMAND(); + + return result; +} + + +//----------------------------------------------------------------------------------------------- + + +/*************************************************************************************************/ +bool NetworkInterface::strToIp(const char *str, uint32_t *intPtr) +{ + if (!intPtr) + { + return false; + } + int temp[4]; + + if(sscanf(str, "%d.%d.%d.%d", &temp[0], &temp[1], &temp[2], &temp[3] ) != 4) + { + return false; + } + else if(temp[0] > 255 || temp[1] > 255 || temp[2] > 255 || temp[3] > 255) + { + return false; + } + *intPtr = (uint32_t)temp[3] << 24 | temp[2] << 16 | temp[1] << 8 | temp[0]; + + return true; +} + +/*************************************************************************************************/ +const char* NetworkInterface::ipToStr(uint32_t ip, char *ipStrBuffer) +{ + SET_STR_BUFFER(ipStrBuffer, 16); + sprintf(ptr, IPV4_FORMAT, IPV4_ARGS(ip)); + return ptr; +} + +/*************************************************************************************************/ +const char* NetworkInterface::networkStatusToStr(NetworkStatus status) +{ + switch(status) + { + case NETWORK_STATUS_DOWN: + return "Down"; + case NETWORK_STATUS_WIFI_ONLY: + return "WiFi Only"; + case NETWORK_STATUS_UP: + return "Up"; + default: + return "Unknown"; + } +} + +/*************************************************************************************************/ +const char* NetworkInterface::signalStrengthToStr(NetworkSignalStrength signalStrenth) +{ + switch(signalStrenth) + { + case NETWORK_RSSI_EXCELLENT: + return "Excellent"; + case NETWORK_RSSI_VERY_GOOD: + return "Very Good"; + case NETWORK_RSSI_GOOD: + return "Good"; + case NETWORK_RSSI_POOR: + return "Poor"; + case NETWORK_RSSI_VERY_POOR: + return "Very Poor"; + case NETWORK_RSSI_UNKNOWN: + default: + return "Unknown"; + } +} + +/*************************************************************************************************/ +NetworkSignalStrength NetworkInterface::rssiToSignalStrength(int rssi_dbm) +{ + if(rssi_dbm > -20) + { + return NETWORK_RSSI_EXCELLENT; + } + else if(rssi_dbm > -35) + { + return NETWORK_RSSI_VERY_GOOD; + } + else if(rssi_dbm > -50) + { + return NETWORK_RSSI_GOOD; + } + else if(rssi_dbm > -70) + { + return NETWORK_RSSI_POOR; + } + else + { + return NETWORK_RSSI_VERY_POOR; + } +} + + +typedef struct +{ + const char* key; + NetworkSecurity value; +} NetworkSecurityTableEntry; + +static const NetworkSecurityTableEntry networkSecurityTable[] = { + {"Auto", NETWORK_SECURITY_UNKNOWN}, + {"Open", NETWORK_SECURITY_OPEN}, + {"Unknown", NETWORK_SECURITY_UNKNOWN}, + {"WEP", NETWORK_SECURITY_WEP_PSK}, + {"WPA-AES", NETWORK_SECURITY_WPA_AES_PSK}, + {"WPA-TKIP", NETWORK_SECURITY_WPA_TKIP_PSK}, + {"WPA2-AES", NETWORK_SECURITY_WPA2_AES_PSK}, + {"WPA2-Mixed", NETWORK_SECURITY_WPA2_MIXED_PSK}, + {"WPA2-TKIP", NETWORK_SECURITY_WPA2_TKIP_PSK}, +}; + + +/*************************************************************************************************/ +NetworkSecurity NetworkInterface::strToNetworkSecurity(const char *str) +{ + const NetworkSecurityTableEntry *end = &networkSecurityTable[ARRAY_COUNT(networkSecurityTable)]; + + for(const NetworkSecurityTableEntry *e = networkSecurityTable; e < end; ++e) + { + if(StringUtil::strcasecmp(e->key, str) == 0) + { + return e->value; + } + } + return NETWORK_SECURITY_UNKNOWN; +} + +/*************************************************************************************************/ +const char* NetworkInterface::networkSecurityToStr(NetworkSecurity security) +{ + const NetworkSecurityTableEntry *end = &networkSecurityTable[ARRAY_COUNT(networkSecurityTable)]; + + for(const NetworkSecurityTableEntry *e = networkSecurityTable; e < end; ++e) + { + if(e->value == security) + { + return e->key; + } + } + return "Unknown"; +} + +/*************************************************************************************************/ +bool NetworkInterface::strToSsid(const char *str, Ssid *ssid) +{ +#define ESCAPE_CHARACTER_DELIMITER '\\' +#define HEX_ESCAPE_CHARACTER 'x' + int c; + uint8_t *ssidPtr = ssid->val; + int ssidLen = 0; + + while((c = (int)(*str++)) != 0) + { + if(c == ESCAPE_CHARACTER_DELIMITER) + { + if(*str == HEX_ESCAPE_CHARACTER) + { + c = StringUtil::hexToInt(str+1); + if(c == -1) + return false; + str += 3; + } + else + { + return false; + } + } + if(ssidLen >= sizeof(ssid->val)) + return false; + ++ssidLen; + *ssidPtr++ = (uint8_t)c; + } + + ssid->len = ssidLen; + + return true; +} + +/*************************************************************************************************/ +const char* NetworkInterface::ssidToStr(const Ssid *ssid, char *ssidStrBuffer) +{ + SET_STR_BUFFER(ssidStrBuffer, sizeof(SsidStrBuffer)); + const char *src = (const char*)ssid->val; + int len = ssid->len; + + while(len--) + { + if(*src >= 0x20 && *src <= 0x7E) + { + *ptr++ = *src; + } + else + { + ptr += sprintf(ptr, "\\x%02X", (*src) & 0xff); + } + ++src; + } + *ptr = 0; + return buf; +} + +/*************************************************************************************************/ +bool NetworkInterface::strToMacAddress(const char *str, MacAddress *macAddress) +{ + const char* strPtr = str; + uint8_t *macPtr = (uint8_t*)macAddress->octet; + + for(int count = 0; count < 6; ++count) + { + if(count < 5) + { + const char *idx = strchr(strPtr, ':'); + if(idx == NULL) + { + return false; + } + } + int num = StringUtil::hexToInt(strPtr); + if(num == -1) + { + return false; + } + *macPtr++ = (uint8_t)num; + strPtr += 3; + } + + return true; +} + +/*************************************************************************************************/ +const char* NetworkInterface::macAddressToStr(const MacAddress *macAddress, char *macStrBuffer) +{ + SET_STR_BUFFER(macStrBuffer, sizeof(MacAddressStrBuffer)); + const uint8_t *mac = macAddress->octet; + + sprintf(ptr, "%02X:%02X:%02X:%02X:%02X:%02X", + (unsigned int)mac[0], + (unsigned int)mac[1], + (unsigned int)mac[2], + (unsigned int)mac[3], + (unsigned int)mac[4], + (unsigned int)mac[5]); + + return ptr; +} +