#include "configServer.h" char arg_networkNameStr[100]; char arg_passphraseStr[100]; char arg_securityTypeStr[100]; char arg_radUserStr[100]; char arg_radPassStr[100]; char arg_geoLocalizationStr[100]; wismart_timer_t rebootTimer; /* This is the array that stores the http resources */ wismart_server_resource_t configServerResources[22]; /*void create_keys(void) { libwismart_RegistryCreateKey }*/ void configServer_start(uint8_t enableApScan) { //create_keys(); configServer_buildResources(); libwismart_server_start(80, "WismartServer", configServer_dynamicCb, chHeapFree, configServerResources); } void configServer_connect() { libwismart_server_connect(); } void configServer_reboot() { libwismart_TimerSet(&rebootTimer, 5000, configServer_rebootTimerHandler, NULL); } void configServer_rebootTimerHandler(void *arg) { libwismart_Reboot(); } void configServer_setClientParameters() { char asciiBuf[20]; libwismart_server_GET("networkName", arg_networkNameStr, sizeof(arg_networkNameStr)); libwismart_server_GET("passphrase", arg_passphraseStr, sizeof(arg_passphraseStr)); libwismart_server_GET("securityType", arg_securityTypeStr, sizeof(arg_securityTypeStr)); libwismart_server_GET("radUser", arg_radUserStr, sizeof(arg_radUserStr)); libwismart_server_GET("radPass", arg_radPassStr, sizeof(arg_radPassStr)); libwismart_server_GET("geoloc", arg_geoLocalizationStr, sizeof(arg_geoLocalizationStr)); CONFIG_SERVER_DBG("The following client settings where retrieved:\r\n"); CONFIG_SERVER_DBG("networkName : %s\r\n",arg_networkNameStr); CONFIG_SERVER_DBG("securityType : %s\r\n",arg_securityTypeStr); CONFIG_SERVER_DBG("passphrase : %s\r\n",arg_passphraseStr); CONFIG_SERVER_DBG("radUser : %s\r\n",arg_radUserStr); CONFIG_SERVER_DBG("radPass : %s\r\n",arg_radPassStr); CONFIG_SERVER_DBG("geoloc : %s\r\n",arg_geoLocalizationStr); config_params_t config; strcpy(config.user,arg_radUserStr); strcpy(config.password,arg_radPassStr); strcpy(config.localization,arg_geoLocalizationStr); strcpy(config.ssid,arg_networkNameStr); strcpy(config.wepkey,arg_passphraseStr); strcpy(config.passphrase,arg_passphraseStr); /* Value validation */ if((strlen((char*)arg_networkNameStr) > 32) || (strlen((char*)arg_networkNameStr) == 0)) { CONFIG_SERVER_DBG_WARNING("Invalid network name![%s]\r\n",(char*)arg_networkNameStr); strcpy(config.ssid,"modularsense"); } if(strcmp((char*)arg_securityTypeStr, SECURITY_TYPE_OPEN) == 0) { /* OPEN ----------------------------------------------------------- */ config.security = (uint16_t) PROFILE_SECURITY_OPEN; } else if(strcmp((char*)arg_securityTypeStr, SECURITY_TYPE_WPA) == 0) { /* WPA ------------------------------------------------------------- */ if((strlen((char*)arg_passphraseStr) < 8) || (strlen((char*)arg_passphraseStr) > 64)) { CONFIG_SERVER_DBG_WARNING("Invalid passphrase length![%s]\r\n", arg_passphraseStr); strcpy((char*)arg_passphraseStr,""); } config.security = (uint16_t) PROFILE_SECURITY_WPA_WPA2; } else { /* WEP ------------------------------------------------------------- */ if(strlen((char*)arg_passphraseStr) == 5) { config.security = PROFILE_SECURITY_WEP40; } else if(strlen((char*)arg_passphraseStr) == 13) { config.security = PROFILE_SECURITY_WEP104; } else if(strlen((char*)arg_passphraseStr) == 10) { config.security = PROFILE_SECURITY_WEP104; CONFIG_SERVER_DBG("WEP hex2ascii conversion for '%s' ...\r\n",arg_passphraseStr); int ret; ret = configServer_hex2bin((char*)arg_passphraseStr, (char*)asciiBuf, 5); if(ret == 0) { //successful conversion memset(arg_passphraseStr, 0, sizeof(arg_passphraseStr)); memcpy(arg_passphraseStr, asciiBuf, 5); } else { //failed conversion memset(arg_passphraseStr, 0, sizeof(arg_passphraseStr)); CONFIG_SERVER_DBG_WARNING("WEP hex2ascii conversion failed!\r\n"); } CONFIG_SERVER_DBG("WEP hex2ascii conversion result is '%s'\r\n",arg_passphraseStr); } else if(strlen((char*)arg_passphraseStr) == 26) { config.security = PROFILE_SECURITY_WEP104; CONFIG_SERVER_DBG("WEP hex2ascii conversion for '%s' ...\r\n",arg_passphraseStr); int ret; ret = configServer_hex2bin((char*)arg_passphraseStr, (char*)asciiBuf, 13); if(ret == 0) { memset(arg_passphraseStr, 0, sizeof(arg_passphraseStr)); memcpy(arg_passphraseStr, asciiBuf, 13); } else { memset(arg_passphraseStr, 0, sizeof(arg_passphraseStr)); CONFIG_SERVER_DBG_WARNING("WEP hex2ascii conversion failed!\r\n"); } CONFIG_SERVER_DBG("WEP hex2ascii conversion result is '%s'\r\n",arg_passphraseStr); } else { CONFIG_SERVER_DBG_WARNING("Invalid WEP key length![%s]\r\n",(char*)arg_passphraseStr); config.security = PROFILE_SECURITY_WEP104; strcpy((char*)arg_passphraseStr,""); } strcpy(config.passphrase, (char*)arg_passphraseStr); strcpy(config.wepkey, (char*)arg_passphraseStr); } libwismart_RegistrySet(&geo,&config); } /*---------------------------------------------------------------------------------------------------------------------------------------------- // DYNAMIC CONTENT -----------------------------------------------------------------------------------------------------------------------------------------------*/ /* * This callback function is called everytime the browser requests a page with the 'hasDynamicContent' * field equal to 1. The user must return only the following values, depending the case: * - WISMART_SERVER_ERR_MEM : if program is out of memory. This will tell the server to not drop the * http request, and ask in ~200ms again for the value of the variable. * After ~5 seconds of failed rerties, the http request will be dropped by the server. * - WISMART_SERVER_ERR_OK : The program filled the 'varValue' and 'varAllocType' fields, * and server can use them for the reply. * */ uint32_t configServer_dynamicCb(char* varName, char** varValue, uint8_t* varAllocType) { char* value; uint16_t profile_enabled; CONFIG_SERVER_DBG("Quering configuration server for variable '%s'", varName); libwismart_ProfileGet_Int("profile_enabled", &profile_enabled); if(strcmp((char*)varName,"WIFI_SECURITY") == 0){ uint16_t security; /* Alocate space for the value */ value = chHeapAlloc(NULL, 100); if(value == NULL){ return WISMART_SERVER_ERR_MEM; } libwismart_ProfileGet_Int("security", &security); if(security == PROFILE_SECURITY_OPEN) { strcpy(value,"Open"); } else if(security == PROFILE_SECURITY_WPA_WPA2) { strcpy(value,"WPA/WPA2"); } else { strcpy(value,"WEP"); } /* * Instruct server to automatically free the memory by calling the * appropriate free() function when the request is replied. */ *varAllocType = WISMART_SERVER_ALLOC_DYNAMIC; (*varValue) = value; return WISMART_SERVER_ERR_OK; } if(strcmp((char*)varName,"WIFI_SSID") == 0){ /* Alocate space for the value */ value = chHeapAlloc(NULL, 100); if(value == NULL){ return WISMART_SERVER_ERR_MEM; } libwismart_ProfileGet_Str("ssid", (char*)value); /* * Instruct server to automatically free the memory by calling the * appropriate free() function when the request is replied. */ *varAllocType = WISMART_SERVER_ALLOC_DYNAMIC; (*varValue) = value; return WISMART_SERVER_ERR_OK; } if(strcmp((char*)varName,"WIFI_PASSPHRASE") == 0){ /* Alocate space for the value */ value = chHeapAlloc(NULL, 100); if(value == NULL){ return WISMART_SERVER_ERR_MEM; } if(profile_enabled == PROFILE_ENABLED) { libwismart_ProfileGet_Str("passphrase", (char*)value); }else{ strcpy((char*)value, "N/A"); } /* Display only visible characters */ uint32_t index; char* ascci = (char*)value; for(index = 0; index < strlen(ascci); index++){ if((ascci[index] < 32) || (ascci[index] > 126)){ ascci[index] = '?'; } } /* * Instruct server to automatically free the memory by calling the * appropriate free() function when the request is replied. */ *varAllocType = WISMART_SERVER_ALLOC_DYNAMIC; (*varValue) = value; return WISMART_SERVER_ERR_OK; } if(strcmp((char*)varName,"WIFI_RADUSER") == 0){ /* Alocate space for the value */ value = chHeapAlloc(NULL, 100); if(value == NULL){ return WISMART_SERVER_ERR_MEM; } libwismart_ProfileGet_Str("gateway", (char*)value); /* * Instruct server to automatically free the memory by calling the * appropriate free() function when the request is replied. */ *varAllocType = WISMART_SERVER_ALLOC_DYNAMIC; (*varValue) = value; return WISMART_SERVER_ERR_OK; } if(strcmp((char*)varName,"WIFI_RADPASS") == 0){ /* Alocate space for the value */ value = chHeapAlloc(NULL, 100); if(value == NULL){ return WISMART_SERVER_ERR_MEM; } libwismart_ProfileGet_Str("netmask", (char*)value); /* * Instruct server to automatically free the memory by calling the * appropriate free() function when the request is replied. */ *varAllocType = WISMART_SERVER_ALLOC_DYNAMIC; (*varValue) = value; return WISMART_SERVER_ERR_OK; } if(strcmp((char*)varName,"WIFI_GEOLOC") == 0){ /* Alocate space for the value */ value = chHeapAlloc(NULL, 100); char geoloc[32]; if(value == NULL){ return WISMART_SERVER_ERR_MEM; } libwismart_RegistryGet(&geo,&geoloc); strcpy(value,geoloc); /* * Instruct server to automatically free the memory by calling the * appropriate free() function when the request is replied. */ *varAllocType = WISMART_SERVER_ALLOC_DYNAMIC; (*varValue) = value; return WISMART_SERVER_ERR_OK; } /* We should never reach here */ CONFIG_SERVER_DBG_WARNING("Unknown dynamic content asked!!"); return WISMART_SERVER_ERR_MEM; } /*---------------------------------------------------------------------------------------------------------------------------------------------- HEX2BIN conversion -----------------------------------------------------------------------------------------------------------------------------------------------*/ /* * This function converts a string in hex format to a string of ascii format. for * example it will convert the string "313131" (byte array [3][1][3][1][3][1]) * into "111" (byte array [49][49][49]). This is needed because WEP keys can be * givent either as HEX strigs or as ASCII strings. */ int configServer_hex2bin(char *hex, char *buf, size_t hexLen){ size_t i; char *ipos = hex; char *opos = buf; if( (hexLen%2) != 0){ return -1; } for (i = 0; i < hexLen; i += 2) { *opos++ = (ipos[i] << 4) | (ipos[i + 1]); } return 0; } /*---------------------------------------------------------------------------------------------------------------------------------------------- HTTP RESOURCES -----------------------------------------------------------------------------------------------------------------------------------------------*/ /* * This function builds a list of all the files of our http server. The next-to-last * entry must have the 'name' field point to NULL so the server can understand * that this was the last entry into the array. */ void configServer_buildResources() { uint32_t index; /* --------------------------------------------------------------------------------------------- */ // STATIC FILES /* --------------------------------------------------------------------------------------------- */ index = 0; /* The root html file can be queried as '/' or as '/en_index.html' */ configServerResources[index].name = "/"; configServerResources[index].mimeType = CONFIG_SERVER_MIME_TYPE_HTML; configServerResources[index].dataPtr = (uint8_t*)data_en_index_html; configServerResources[index].dataSize = sizeof(data_en_index_html); configServerResources[index].hasDynamicContent = 1; /* This page has dynamic content ( $_DYNAMIC[XYZ] code inside the html ) */ configServerResources[index].canBeCached = 0; configServerResources[index].scriptCb = NULL; index++; configServerResources[index].name = "/en_index.html"; configServerResources[index].mimeType = CONFIG_SERVER_MIME_TYPE_HTML; configServerResources[index].dataPtr = (uint8_t*)data_en_index_html; configServerResources[index].dataSize = sizeof(data_en_index_html); configServerResources[index].hasDynamicContent = 1; /* This page has dynamic content ( $_DYNAMIC[XYZ] code inside the html ) */ configServerResources[index].canBeCached = 0; configServerResources[index].scriptCb = NULL; /* --------------------------------------------------------------------------------------------- */ index++; configServerResources[index].name = "/en_client.html"; configServerResources[index].mimeType = CONFIG_SERVER_MIME_TYPE_HTML; configServerResources[index].dataPtr = (uint8_t*)data_en_client_html; configServerResources[index].dataSize = sizeof(data_en_client_html); configServerResources[index].hasDynamicContent = 0; configServerResources[index].canBeCached = 0; configServerResources[index].scriptCb = NULL; /* --------------------------------------------------------------------------------------------- */ index++; configServerResources[index].name = "/en_reboot.html"; configServerResources[index].mimeType = CONFIG_SERVER_MIME_TYPE_HTML; configServerResources[index].dataPtr = (uint8_t*)data_en_reboot_html; configServerResources[index].dataSize = sizeof(data_en_reboot_html); configServerResources[index].hasDynamicContent = 0; configServerResources[index].canBeCached = 0; configServerResources[index].scriptCb = NULL; /* --------------------------------------------------------------------------------------------- */ index++; configServerResources[index].name = "/css.css"; configServerResources[index].mimeType = CONFIG_SERVER_MIME_TYPE_CSS; configServerResources[index].dataPtr = (uint8_t*)data_css_css; configServerResources[index].dataSize = sizeof(data_css_css); configServerResources[index].hasDynamicContent = 0; configServerResources[index].canBeCached = 0; configServerResources[index].scriptCb = NULL; /* --------------------------------------------------------------------------------------------- */ index++; configServerResources[index].name = "/logo.png"; configServerResources[index].mimeType = CONFIG_SERVER_MIME_TYPE_PNG; configServerResources[index].dataPtr = (uint8_t*)data_logo_png; configServerResources[index].dataSize = sizeof(data_logo_png); configServerResources[index].hasDynamicContent = 0; configServerResources[index].canBeCached = 0; configServerResources[index].scriptCb = NULL; /* --------------------------------------------------------------------------------------------- */ // SCRIPTS /* --------------------------------------------------------------------------------------------- */ index++; configServerResources[index].name = "/en_clientParams"; configServerResources[index].mimeType = CONFIG_SERVER_MIME_TYPE_HTML; configServerResources[index].dataPtr = (uint8_t*)data_en_reboot_html; configServerResources[index].dataSize = sizeof(data_en_reboot_html); configServerResources[index].hasDynamicContent = 0; configServerResources[index].canBeCached = 0; configServerResources[index].scriptCb = configServer_setClientParameters; /* Function to be called when Server receives request for this script */ /* --------------------------------------------------------------------------------------------- */ index++; configServerResources[index].name = "/en_reboot"; configServerResources[index].mimeType = CONFIG_SERVER_MIME_TYPE_HTML; configServerResources[index].dataPtr = (uint8_t*)data_en_rebooting_html; configServerResources[index].dataSize = sizeof(data_en_rebooting_html); configServerResources[index].hasDynamicContent = 0; configServerResources[index].canBeCached = 0; configServerResources[index].scriptCb = configServer_reboot; /* Function to be called when Server receives request for this script */ /* --------------------------------------------------------------------------------------------- */ // END OF LIST INDICATOR /* --------------------------------------------------------------------------------------------- */ index++; configServerResources[index].name = NULL; /* --------------------------------------------------------------------------------------------- */ // RESOURCE NUMBER CHECK /* --------------------------------------------------------------------------------------------- */ if(index + 1 > sizeof(configServerResources)/sizeof(wismart_server_resource_t)){ CONFIG_SERVER_DBG_WARNING("configServerResources[] size is too small! [%u/%u]",index + 1, sizeof(configServerResources)/sizeof(wismart_server_resource_t)); while(1){} } }