A simple web server that can be bound to either the EthernetInterface or the WiflyInterface.
Dependents: Smart-WiFly-WebServer WattEye X10Svr SSDP_Server
Diff: SW_HTTPServer.cpp
- Revision:
- 59:9a71ac02c782
- Parent:
- 58:5303e962f711
--- a/SW_HTTPServer.cpp Sun Nov 18 04:04:16 2018 +0000 +++ b/SW_HTTPServer.cpp Tue Feb 26 22:45:55 2019 +0000 @@ -13,7 +13,7 @@ #include "mbed.h" #include "SW_String.h" // Secure methods and others that were missing -#define DEBUG "HTTP" +//#define DEBUG "HTTP" #include <cstdio> #if (defined(DEBUG) && !defined(TARGET_LPC11U24)) #define DBG(x, ...) std::printf("[DBG %s %4d] "x"\r\n", DEBUG, __LINE__, ##__VA_ARGS__); @@ -27,8 +27,6 @@ #define INFO(x, ...) #endif -extern void ShowSignOfLife(int which); - #include "SW_HTTPServer.h" // define DEBUG before this #define CHUNK_SIZE 1500 // max size of a single chunk (probably limited by Ethernet to 1500) @@ -85,15 +83,16 @@ {NULL, 0} }; -#if 0 && defined(DEBUG) +#if 1 && defined(DEBUG) // Haven't learned anything from this in a long time, so disabled. // This uses standard library dynamic memory management, but for an // embedded system there are alternates that may make better sense - // search the web for embedded system malloc alternates. -void * HTTPServer::MyMalloc(int x, int y) +void * HTTPServer::MyMalloc(int Bytes, int LINE) { - pc->printf("[INF HTTP%4d] malloc(%d)\r\n", y, x); - return malloc(x); + void * pMem = malloc(Bytes); + pc->printf("[INF %s %4d] MyMalloc %p = malloc(%d)\r\n", DEBUG, LINE, pMem, Bytes); + return pMem; } char HTTPServer::toP(void * x) { @@ -103,9 +102,11 @@ else return '.'; } -#define mymalloc(x) MyMalloc(x, __LINE__) +#define mymalloc(Bytes) MyMalloc(Bytes, __LINE__) #define myfree(x) \ - pc->printf("[INF HTTP%4d] free(%02x %02x %02x %02x %02x ... %c%c%c%c%c)\r\n", __LINE__, \ + pc->printf("[INF %s %4d] MyMalloc %p = free(%02x %02x %02x %02x %02x ... %c%c%c%c%c)\r\n", \ + DEBUG, __LINE__, \ + x, \ *x, *(x+1), *(x+2), *(x+3), *(x+4), \ toP(x), toP(x+1), toP(x+2), toP(x+3), toP(x+4) ); \ free(x); @@ -147,13 +148,14 @@ postParamCount = 0; maxdynamicpages = _maxdynamicpages; handlers = (handler *)malloc(maxdynamicpages * sizeof(handler)); + handlercount = 0; + ndxActiveHandler = -1; headerbuffersize = _allocforheader; headerbuffer = (char *)malloc(headerbuffersize); pc = _pc; queryType = NULL; queryString = NULL; postQueryString = NULL; - handlercount = 0; maxheaderbytes = 0; server = new TCPSocketServer(); server->bind(port); @@ -200,6 +202,14 @@ } } +const char * HTTPServer::GetActiveHandlerPath(void) +{ + if (ndxActiveHandler >= 0) + return handlers[ndxActiveHandler].path; + else + return NULL; +} + // Poll() // // *OPEN*GET /x=1 HTTP/1.1 @@ -239,7 +249,6 @@ break; case Idle: - ShowSignOfLife(3); PerformanceTimer.reset(); t_ref = (unsigned int)PerformanceTimer.read_us(); bPtr = headerbuffer; @@ -256,6 +265,7 @@ case ReceivingHeader: n = client.receive(bPtr, headerbuffersize - (bPtr - headerbuffer)); INFO("client.receive() returned %d, from %s", n, client.get_address()); + INFO(" ReceivingHeader: %s", bPtr); if (n == -2) { // was hang here waiting ... op = Sending; which causes misses op = WaitingToClose; @@ -512,6 +522,12 @@ return NULL; } +int HTTPServer::ParsePostParameters(char * pPostString) +{ + return ParseParameters(postParams, &postParamCount, maxPostParams, pPostString); +} + + // this=that&who=what&more=stuff... // ^ ^ ^ int HTTPServer::ParseParameters(namevalue * qP, int * qpCount, int maxP, char * pName) @@ -679,11 +695,12 @@ bool regHandled = false; // If this queryString is in the list of registered handlers, call that - for (int i=0; i<handlercount; i++) { - if (strcmp(handlers[i].path, queryString) == 0) { - INFO("CheckDynamicHandlers - SEND_PAGE %s", handlers[i].path); - (*handlers[i].callback)(this, SEND_PAGE, queryString, queryParams, queryParamCount); + for (ndxActiveHandler=0; ndxActiveHandler<handlercount; ndxActiveHandler++) { + if (strcmp(handlers[ndxActiveHandler].path, queryString) == 0) { + INFO("CheckDynamicHandlers - SEND_PAGE %s", handlers[ndxActiveHandler].path); + (*handlers[ndxActiveHandler].callback)(this, SEND_PAGE, queryString, queryParams, queryParamCount); regHandled = true; + ndxActiveHandler = -1; break; // we only execute the first one } } @@ -727,6 +744,10 @@ INFO(" SendResponse complete at %8u us", (unsigned int)PerformanceTimer.read_us()); + if (postQueryString) { + myfree(postQueryString); + postQueryString = NULL; + } if (queryType) { myfree(queryType); queryType = NULL; @@ -735,10 +756,6 @@ myfree(queryString); queryString = NULL; } - if (postQueryString) { - myfree(postQueryString); - postQueryString = NULL; - } INFO(" SendResponse free at %8u us", (unsigned int)PerformanceTimer.read_us()); } @@ -890,7 +907,7 @@ dblCR += 4; // There may be some after the double CR that we need ttlCount = strlen(dblCR); strcpy_s(postQueryString, CHUNK_SIZE, dblCR); - //INFO(" {%s}", postQueryString); + INFO(" {%s}", postQueryString); while ((!postBytes || ttlCount < postBytes) && !escape) { INFO("ttlCount: %d < postBytes: %d, of max chunk alloc %d", ttlCount, postBytes, CHUNK_SIZE); len = client.receive(postQueryString + ttlCount, CHUNK_SIZE - ttlCount); @@ -913,13 +930,14 @@ break; } //postParamCount = 0; - //INFO("post: %s", postQueryString); + INFO("post: %s", postQueryString); //We're after the header, so there is "body" stuff which could be anything... //but probably html or xml stuff... //ParseParameters(postParams, &postParamCount, maxPostParams, postQueryString); acceptIt = (*handlers[ndxHandler].callback)(this, DATA_TRANSFER, postQueryString, NULL, ttlCount); - INFO("..processing exit"); + INFO("..processing exit [%d]", acceptIt); acceptIt = (*handlers[ndxHandler].callback)(this, DATA_TRANSFER_END, NULL, NULL, 0); + INFO("..transfer end[%d]", acceptIt); } else { ERR("attempt to allocate %d failed.", CHUNK_SIZE); }