HTTP Server library for Mbed OS-5. A fork of Henry Leinen's [[https://os.mbed.com/users/leihen/code/HTTPServer/]] library.

Dependents:   STM32F407VET6_HTTPServer

Files at this revision

API Documentation at this revision

Comitter:
hudakz
Date:
Sun Oct 06 18:10:41 2019 +0000
Parent:
16:cc3f5c53d0d5
Commit message:
HTTP Server library for Mbed OS-5. A fork of Henry Leine's [[https://os.mbed.com/users/leihen/code/HTTPServer | HTTPServer]] library.

Changed in this revision

HTTPConnection.cpp Show annotated file Show diff for this revision Revisions of this file
HTTPConnection.h Show annotated file Show diff for this revision Revisions of this file
HTTPRequestHandler.cpp Show annotated file Show diff for this revision Revisions of this file
HTTPRequestHandler.h Show annotated file Show diff for this revision Revisions of this file
HTTPServer.cpp Show annotated file Show diff for this revision Revisions of this file
HTTPServer.h Show annotated file Show diff for this revision Revisions of this file
Handler/FsHandler.cpp Show annotated file Show diff for this revision Revisions of this file
Handler/FsHandler.h Show annotated file Show diff for this revision Revisions of this file
Handler/RpcHandler.cpp Show diff for this revision Revisions of this file
Handler/RpcHandler.h Show diff for this revision Revisions of this file
--- a/HTTPConnection.cpp	Sat Aug 17 16:17:55 2013 +0000
+++ b/HTTPConnection.cpp	Sun Oct 06 18:10:41 2019 +0000
@@ -27,7 +27,7 @@
 };
 
 
-HTTPConnection::HTTPConnection(TCPSocketConnection& clnt) : m_Tcp(clnt)
+HTTPConnection::HTTPConnection(TCPSocket* clnt) : m_Tcp(clnt)
 {
 }
 
@@ -40,14 +40,16 @@
 void HTTPConnection::close()
 {
     m_Msg.headers.clear();
+    m_Tcp->close();
 }
 
 int HTTPConnection::poll()
 {
     static char buffer[256] = {};
-
+    int rcvd= 0;
+    int ret = 0;
+    int attri_len = 0;
     
-    int rcvd= 0;
     INFO("Waiting for new data in connection");
     //  Try receiving request line
     rcvd = receiveLine(buffer, 255, 3000); 
@@ -63,9 +65,9 @@
     if (rcvd == -1) {
         //  Invalid content received, so close the connection
         INFO("Invalid message received, so sending negative response and closing connection !");
-        sprintf(buffer,"HTTP/1.1 400 BadRequest\n\rContent-Length: %d\n\rContent-Type: text\n\r\n\r\n\r",0);
-        m_Tcp.set_blocking(true, 1500);
-        m_Tcp.send(buffer,strlen(buffer));
+        //sprintf(buffer,"HTTP/1.1 400 BadRequest\n\rContent-Length: %d\n\rContent-Type: text\n\r\n\r\n\r",0);
+        m_Tcp->set_timeout(1500);
+        //m_Tcp->send(buffer,strlen(buffer));
         close();
         rcvd = -1;
         return -1;
@@ -82,13 +84,22 @@
         }
         else {
             //  add message body
-            if (parseHeader(buffer) == 0) {
+            ret = parseHeader(buffer);
+            if (ret == 0) {
+                
             }
             else {
-                WARN("Invalid message header received !");
+                attri_len = ret;
             }
         }
-    }             
+    }
+    
+    //Receive attribute data
+    if( attri_len != 0 )
+    {
+        m_Tcp->recv(m_Msg.attri, attri_len);
+    }
+      
     INFO("Leaving poll function!");
     return rcvd;
 }
@@ -99,27 +110,28 @@
         return -1;
     
     szLine[0] = 0;
-    m_Tcp.set_blocking(false);
+    m_Tcp->set_blocking(false);
     
-    if (!m_Tcp.is_connected()) {
-        error("NOT COnnected anymore");
-        return -1;
-    }
+//    if (!m_Tcp->is_connected()) {
+//        error("NOT COnnected anymore");
+//        return -1;
+//    }
+
     Timer tm;
     int i;
     
     //  Try to receive up to the max number of characters
     for (i = 0 ; i < nMaxLen-1 ; i++) {
         int c;
-        c = m_Tcp.receive( szLine + i, 1 );
+        c = m_Tcp->recv( szLine + i, 1 );
         //  Check that - if no character was currently received - the timeout period is reached.
         if ((c == 0) || (c==-1)) {
             //  no character was read, so check if operation timed out
-            if (tm.read_ms() > nTimeout) {
+            //if (tm.read_ms() > nTimeout) {
                 //  Operation timed out
-                INFO("Timeout occured in function 'receiveLine'.");
+                //INFO("Timeout occured in function 'receiveLine'.");
                 return -1;
-            }
+            //}
         }
         
         //  Check if line terminating character was received
@@ -128,6 +140,7 @@
             break;
         }
     }
+    
     //  Terminate with \0
     szLine[i] = 0;
 
@@ -161,6 +174,12 @@
     //  decompose string into a list of arguments
     char s = 0; // current starting char
     int nLen = strlen(buffer)+1;
+    
+    
+    //for(int i = 0; i < nLen; i++)
+        //printf("%d : %c\r\n", i, buffer[i]);
+    
+    
     for (int i = 0 ; i < nLen ; i++) {
         if ((buffer[i] == ' ') || (buffer[i] == '\n') || (buffer[i] == 0)) {
             // new arg found
@@ -198,9 +217,13 @@
     if ((strlen(buffer) <3) || (buffer == NULL))
         return -1;
         
-    //  decompose string into a touple of <field name> : <field value>
-    int value_start = 0;
-    int buflen = strlen(buffer)+1;
+    //Find Content length
+    if(strncmp(buffer, "Content-Length", 14) == 0)
+    {
+        m_Msg.attri_len = atoi(&buffer[16]);
+        return m_Msg.attri_len;
+    }
+    /*
     for (int i = 0 ; i < buflen ; i++) {
         if (buffer[i] == ':') {
             //  touple found
@@ -212,9 +235,10 @@
             return 0;
         }
     }
-    
-    ERR("Did not recieve a valid header : \"%s\".", buffer);
-    return -1;
+    */
+    return 0;
+    //ERR("Did not recieve a valid header : \"%s\".", buffer);
+    //return -1;
 }
 
 int HTTPConnection::parseUriArgs(char *buffer, map<string,string>&args)
@@ -260,5 +284,6 @@
         }
     }
     
+    
     return 0;
 }
--- a/HTTPConnection.h	Sat Aug 17 16:17:55 2013 +0000
+++ b/HTTPConnection.h	Sun Oct 06 18:10:41 2019 +0000
@@ -24,7 +24,7 @@
 #define __HTTPConnection_H__
 
 #include "mbed.h"
-#include "TCPSocketConnection.h"
+#include "TCPSocket.h"
 
 #include <string>
 #include <map>
@@ -70,12 +70,17 @@
             /** Map of arguments that came with the uri string
             */
             std::map<std::string, std::string>      args;
+            
+            //attribute data
+            char                                    attri[50];
+            //attribute length
+            uint32_t                                attri_len;
         } HTTPMessage;
         
         /** Public constructor for HTTPConnection objects.
          *
          */
-        HTTPConnection (TCPSocketConnection& clnt);
+        HTTPConnection(TCPSocket* clnt);
         
         /** Destructor for HTTPConnection objects.
         *
@@ -100,7 +105,7 @@
 
         friend class HTTPServer;
                         
-        TCPSocketConnection m_Tcp;
+        TCPSocket*  m_Tcp;
         HTTPMessage m_Msg;
 
         /** parse a HTTP request line from the content of the buffer. 
@@ -135,4 +140,4 @@
 
 };
 
-#endif // __HTTPConnection_H__
\ No newline at end of file
+#endif // __HTTPConnection_H__
--- a/HTTPRequestHandler.cpp	Sat Aug 17 16:17:55 2013 +0000
+++ b/HTTPRequestHandler.cpp	Sun Oct 06 18:10:41 2019 +0000
@@ -10,12 +10,12 @@
 
 
 const char hdrStandard[] = "DNT: 1\r\n"
-                            "MaxAge: 0\r\n"
-                            "Connection: Keep-Alive\r\n"
-                            "Content-Type: text/html\r\n"
-                            "Server: mbed embedded\r\n"
-                            "Accessible: 1\r\n"
-                            "\r\n";
+                           "MaxAge: 0\r\n"
+                           "Connection: Keep-Alive\r\n"
+                           "Content-Type: text/html\r\n"
+                           "Server: mbed embedded\r\n"
+                           "Accessible: 1\r\n"
+                           "\r\n";
 
 
 static int _stricmp(const char* a, const char* b)
@@ -34,7 +34,7 @@
     const char* key;
     const char* value;
 } fileTypeMapping[]  = {
-        {".gif", "Content-Type: image/gif\r\n"   },
+    {".gif", "Content-Type: image/gif\r\n"   },
     {".jpg", "Content-Type: image/jpeg\r\n"  },
     {".jpeg","Content-Type: image/jpeg\r\n"  },
     {".ico", "Content-Type: image/x-icon\r\n"},
@@ -49,12 +49,11 @@
     {".css", "Content-Type: text/css\r\n"    },
     {".js",  "Content-Type: text/javascript\r\n"}};
     
-HTTPRequestHandler::HTTPRequestHandler(HTTPConnection::HTTPMessage& Msg, TCPSocketConnection& Tcp)
+HTTPRequestHandler::HTTPRequestHandler(HTTPConnection::HTTPMessage& Msg, TCPSocket* Tcp)
     : msg(Msg), tcp(Tcp)
 {
     msg = Msg;
     tcp = Tcp;
-
 }
 
 HTTPRequestHandler::~HTTPRequestHandler()
@@ -117,48 +116,48 @@
 void HTTPRequestHandler::handleError(int errorCode, HTTPHeaders* header)
 {
     INFO("Handling error !");
-    tcp.set_blocking(false, 1500);
+    tcp->set_blocking(false);
     sprintf(buffer,"HTTP/1.1 %d Error\r\n", errorCode);
-    tcp.send(buffer, strlen(buffer));
+    tcp->send(buffer, strlen(buffer));
     sprintf(buffer, "Content-Length: %d\r\n", strlen(szErrorPage));
-    tcp.send(buffer, strlen(buffer));
+    tcp->send(buffer, strlen(buffer));
     if (header == NULL) {
         sprintf(buffer, "Content-Type: text/html\r\nServer: mbed embedded\r\n\n\r");
-        tcp.send(buffer, strlen(buffer));
+        tcp->send(buffer, strlen(buffer));
     }
     else {
         for ( map<const char*, const char*>::iterator cIter = header->begin() ; cIter != header->end() ; cIter ++) {
-            tcp.send((char*)cIter->first, strlen(cIter->first));
-            tcp.send(": ", 2);
-            tcp.send((char*)cIter->second, strlen(cIter->second));
-            tcp.send("\r\n",2);
+            tcp->send((char*)cIter->first, strlen(cIter->first));
+            tcp->send(": ", 2);
+            tcp->send((char*)cIter->second, strlen(cIter->second));
+            tcp->send("\r\n",2);
         }
-        tcp.send("\r\n",2);
+        tcp->send("\r\n",2);
     }
-    tcp.send((char*)szErrorPage, strlen(szErrorPage));
+    tcp->send((char*)szErrorPage, strlen(szErrorPage));
 }
 
 
 void HTTPRequestHandler::startResponse(int returnCode, long nLen, HTTPHeaders* header)
 {
     INFO("Starting response (%ld bytes in total)!", nLen);
-    tcp.set_blocking(false, 1500);
+    tcp->set_blocking(false);
     sprintf(buffer, "HTTP/1.1 %d OK\r\n", returnCode);
-    tcp.send(buffer, strlen(buffer));
+    tcp->send(buffer, strlen(buffer));
     sprintf(buffer, "Content-Length: %ld\r\n", nLen);    //  Add 2 chars for the terminating CR+LF
-    tcp.send(buffer, strlen(buffer));
+    tcp->send(buffer, strlen(buffer));
     INFO("Sending standard headers !");
     if (header == NULL) {
-        tcp.send_all((char*)hdrStandard, strlen(hdrStandard));
+        tcp->send((char*)hdrStandard, strlen(hdrStandard));
     }
     else {
         for ( map<const char*, const char*>::iterator cIter = header->begin() ; cIter != header->end() ; cIter ++) {
-            tcp.send_all((char*)cIter->first, strlen(cIter->first));
-            tcp.send_all(": ", 2);
-            tcp.send_all((char*)cIter->second, strlen(cIter->second));
-            tcp.send_all("\r\n\r\n",2);
+            tcp->send((char*)cIter->first, strlen(cIter->first));
+            tcp->send(": ", 2);
+            tcp->send((char*)cIter->second, strlen(cIter->second));
+            tcp->send("\r\n\r\n",2);
         }
-        tcp.send_all("\r\n", 2);
+        tcp->send("\r\n", 2);
     }
     INFO("Proceeding !");
     //  other content must be sent using the 'processResponse' function
@@ -167,7 +166,7 @@
 void HTTPRequestHandler::processResponse(int nLen, char* body)
 {
     INFO("Processing Response (%d bytes)!\n",nLen);
-    tcp.send_all(body, nLen);
+    tcp->send(body, nLen);
 }
 
 void HTTPRequestHandler::endResponse()
--- a/HTTPRequestHandler.h	Sat Aug 17 16:17:55 2013 +0000
+++ b/HTTPRequestHandler.h	Sun Oct 06 18:10:41 2019 +0000
@@ -80,12 +80,12 @@
 {
     protected:
         HTTPConnection::HTTPMessage& msg;
-        TCPSocketConnection& tcp;
+        TCPSocket* tcp;
         
     public:
         /** Constructor for HTTPRequestHandler objects.
          */
-        HTTPRequestHandler(HTTPConnection::HTTPMessage&, TCPSocketConnection&);
+        HTTPRequestHandler(HTTPConnection::HTTPMessage&, TCPSocket*);
         
         /** Destructor for HTTPRequestHandler objects.
         */
@@ -136,4 +136,4 @@
         void getStandardHeaders(HTTPHeaders& header, const char* fext = NULL);
 };
 
-#endif //   __HTTPREQUESTHANDLER_H__
\ No newline at end of file
+#endif //   __HTTPREQUESTHANDLER_H__
--- a/HTTPServer.cpp	Sat Aug 17 16:17:55 2013 +0000
+++ b/HTTPServer.cpp	Sun Oct 06 18:10:41 2019 +0000
@@ -23,13 +23,13 @@
 
 static const char* szStdErrorPage = "<HTML><HEAD><META content=\"text/html\" http-equiv=Content-Type></HEAD><BODY><h1>Error 404</h1><P>This resource is not available<P></BODY></HTML>\r\n\r\n";
 
-void HTTPServer::StdErrorHandler(HTTPConnection::HTTPMessage& msg, TCPSocketConnection& tcp)
+void HTTPServer::StdErrorHandler(HTTPConnection::HTTPMessage& msg, TCPSocket* tcp)
 {
     char echoHeader[256];
-    tcp.set_blocking(true, 1500);
+    tcp->set_blocking(false);
     sprintf(echoHeader,"HTTP/1.0 404 Fail\r\nConnection: close\r\nContent-Length: %d\r\nContent-Type: text/html\r\nServer: mbed embedded\r\n\n\r",strlen(szStdErrorPage));
-    tcp.send(echoHeader, strlen(echoHeader));
-    tcp.send((char*)szStdErrorPage, strlen(szStdErrorPage));
+    tcp->send(echoHeader, strlen(echoHeader));
+    tcp->send((char*)szStdErrorPage, strlen(szStdErrorPage));
 }
 
 
@@ -38,57 +38,42 @@
     //  If no ethernet interface is provided, instantiate own on the heap. This has to be deleted later in the destructor.
     //  If a valid pointer to an thernet interface is proveded, we can simply use it. 
     if (pEthernet == NULL) {
-        INFO("Creating EthernetInterface object\n");
-        m_pEthernet = new EthernetInterface();
-        
-        if (m_pEthernet == NULL) {
-            ERR("Out of memory, unable to instantiate an EthernetInterface object.");
-            return false;
-        }
-
-        //  Initiaize the network
-        INFO("Initializing network\n");
-        if (m_pEthernet->init() != 0) {
-            ERR("Failed to initialize the ethernet interface !");
-            delete m_pEthernet;
-            m_pEthernet = NULL;
-            return false;
-        }
-        
-        //  Connect to the network using DHCP
-        INFO("Connecting to the network using DHCP...");
-        if (m_pEthernet->connect() != 0) {
-            ERR("Failed to connect to the ethernet !");
-            delete m_pEthernet;
-            m_pEthernet = NULL;
-            return false;
-        }
-        
-        INFO("Connected IP %s", m_pEthernet->getIPAddress());
+        ERR("Socket is not opened!!\r\n");
         
     } else {
         //  In the case that the ethernet interface is provided, it is assumed that a connection has already been created.
-        INFO("Using connection IP %s", pEthernet->getIPAddress());
+        INFO("Using connection IP %s", pEthernet->get_ip_address());
     }
     
+    nsapi_error_t r;
+    const char* ip = pEthernet->get_ip_address();
+
+    /* Open the server on ethernet stack */
+    INFO("Opening server on the Ethernet stack ...");
+    r = m_Svr.open(pEthernet);
+    if (r != 0) {
+        INFO("Error! Opening server returned: %d\n", r);
+        error("Opening server");
+        return false;
+    }
+
     INFO("Binding to port %d...", port);
-    if (m_Svr.bind(port) < 0) {
+    if (m_Svr.bind(ip, port) < 0) {
         ERR("Failed to bind to port !\n");
         error("Binding");
         return false;
     }
 
-    INFO("Listening ...");
     if (m_Svr.listen(1) < 0) {
         ERR("Failed to listen !\n");
         error("Listening");
         return false;
     }
 
-    INFO("Connected !");
-    //  set into non blocking operation
-    m_Svr.set_blocking(false, 100);
-
+    INFO("Listening ...");
+    //  set into non blocking operation after timeout
+    m_Svr.set_timeout(1500);
+    
     return true;
 }
 
@@ -97,19 +82,28 @@
 {
     //  This thread basically checks if there is a new incoming connection.
     //  If so , a new HTTPConnection is created and the connection thread is started.
-    TCPSocketConnection Clnt;
-    if (m_Svr.accept(Clnt) < 0) {
+    nsapi_error_t   error;
+    SocketAddress   clntAddress;
+    TCPSocket*      clnt = m_Svr.accept(&error);
+    
+    if (clnt == NULL) {
         return -1;
     }
+    
+    if (error != 0) {
+        clnt->close();
+        return error;
+    }  
 
     //   a new connection was received
-    INFO("Client (IP=%s) is connected !\n", Clnt.get_address());
-    HTTPConnection con(Clnt);
+    clnt->getpeername(&clntAddress);
+    INFO("Client (IP=%s) is connected !\n", clntAddress.get_ip_address());
+    HTTPConnection con(clnt);
     int c = con.poll();
     if (c == 0) {
         //  Handle the request
         INFO("Handling request !");
-        HandleRequest(con.m_Msg, Clnt);
+        HandleRequest(con.m_Msg, clnt);
     }
     if (c == -1) {
 //        break;
@@ -119,10 +113,10 @@
     return 0;
 }
 
-void HTTPServer::HandleRequest(HTTPConnection::HTTPMessage& msg, TCPSocketConnection& tcp)
+void HTTPServer::HandleRequest(HTTPConnection::HTTPMessage& msg, TCPSocket* tcp)
 {
     std::string localPath;
-    std::map<std::string, HTTPRequestHandler*(*)(const char*, const char*, HTTPConnection::HTTPMessage&, TCPSocketConnection&), handlersComp>::const_iterator it;
+    std::map<std::string, HTTPRequestHandler*(*)(const char*, const char*, HTTPConnection::HTTPMessage&, TCPSocket*), handlersComp>::const_iterator it;
 
     //  Iterate through registered handlers and check if the handler's path is a subset of the requested uri.
     for (it = m_lpHandlers.begin() ; it != m_lpHandlers.end() ; it++) {
--- a/HTTPServer.h	Sat Aug 17 16:17:55 2013 +0000
+++ b/HTTPServer.h	Sun Oct 06 18:10:41 2019 +0000
@@ -32,12 +32,11 @@
 #include <string>
 using std::string;
 
-#include <TCPSocketConnection.h>
-#include <TCPSocketServer.h>
+#include <TCPSocket.h>
 
 /** Typedefinition for a handler function
 */
-typedef void (*HTTPRequestHandlerFunction)(HTTPConnection::HTTPMessage&, TCPSocketConnection&);
+typedef void (*HTTPRequestHandlerFunction)(HTTPConnection::HTTPMessage&, TCPSocket*);
 
 
 /** Class HTTPServer for use with <a href="http://mbed.org/users/samux/code/WiflyInterface/">WiflyInterface</a>.
@@ -116,7 +115,7 @@
 */
 class HTTPServer
 {
-        TCPSocketServer         m_Svr;
+        TCPSocket               m_Svr;
         bool                    m_bServerListening;
         EthernetInterface*      m_pEthernet;
        
@@ -188,7 +187,7 @@
         * @param msg : Request message data.
         * @param tcp : Socket to be used for responding.
         */
-        static void StdErrorHandler(HTTPConnection::HTTPMessage& msg, TCPSocketConnection& tcp);
+        static void StdErrorHandler(HTTPConnection::HTTPMessage& msg, TCPSocket* tcp);
         
         /** Internal function which processes a request and which will try to find the matching handler function
         * for the given request. Please note that the function will search through the list of handlers, iterating
@@ -197,14 +196,14 @@
         * @param msg : Request message data. Contains the requested logical \c uri. 
         * @param tcp : Socket to be used for communication with the client.
         */
-        void HandleRequest(HTTPConnection::HTTPMessage& msg, TCPSocketConnection& tcp);
+        void HandleRequest(HTTPConnection::HTTPMessage& msg, TCPSocket* tcp);
     
         /** Map of handler objects. Can be any object derived from \ref HTTPRequestHeader. Use the \ref addHandler function
         * to register new handler objects.
         */
-        map<string, HTTPRequestHandler* (*)(const char*, const char*, HTTPConnection::HTTPMessage&, TCPSocketConnection&), handlersComp>   m_lpHandlers;
+        map<string, HTTPRequestHandler* (*)(const char*, const char*, HTTPConnection::HTTPMessage&, TCPSocket*), handlersComp>   m_lpHandlers;
         HTTPRequestHandlerFunction m_pErrorHandler;
         
  };
  
- #endif //__HTTPSERVER_H__
\ No newline at end of file
+ #endif //__HTTPSERVER_H__
--- a/Handler/FsHandler.cpp	Sat Aug 17 16:17:55 2013 +0000
+++ b/Handler/FsHandler.cpp	Sun Oct 06 18:10:41 2019 +0000
@@ -4,7 +4,7 @@
 #define DEBUG
 #include "hl_debug.h"
 
-
+DigitalOut led1(LED1);
 
 static int matchstrings(const char* one, const char* two)
 {
@@ -19,9 +19,10 @@
 
 std::map<const char*, const char*> HTTPFsRequestHandler::m_fsMap;
  
-HTTPFsRequestHandler::HTTPFsRequestHandler(const char* rootPath, const char* localPath, HTTPConnection::HTTPMessage& Msg, TCPSocketConnection& Tcp)
+HTTPFsRequestHandler::HTTPFsRequestHandler(const char* rootPath, const char* localPath, HTTPConnection::HTTPMessage& Msg, TCPSocket* Tcp)
     : HTTPRequestHandler(Msg, Tcp)
 {
+    INFO("Request handler called.");
     m_rootPath = rootPath;
     m_localPath = localPath;
     
@@ -58,6 +59,7 @@
 int HTTPFsRequestHandler::handleGetRequest()
 {
     HTTPHeaders headers;
+    int retval = 0;   //success
     
     if (m_localPath.length() > 4) 
         getStandardHeaders(headers, m_localPath.substr(m_localPath.length()-4).c_str());
@@ -65,7 +67,7 @@
         getStandardHeaders(headers);
     
     INFO("Handling Get Request (root = %s, local = %s).", m_rootPath.c_str(), m_localPath.c_str());
-    int retval = 0;   //success
+    
     std::string reqPath;
 
     //  Check if we received a directory with the local bath
@@ -79,7 +81,9 @@
     INFO("Mapping \"%s\" to \"%s\"", msg.uri.c_str(), reqPath.c_str());
         
     FILE *fp = fopen(reqPath.c_str(), "r");
+    INFO("fopen(reqPath.c_str()");
     if (fp != NULL) {
+        INFO("fp != NULL");
         char * pBuffer = NULL;
         int sz = 8192;
         while( pBuffer == NULL) {
@@ -90,6 +94,7 @@
         }
         
         //  File was found and can be returned
+        INFO("File was found and can be returned");
     
         //  first determine the size
         fseek(fp, 0, SEEK_END);
@@ -116,11 +121,50 @@
 }
 
 int HTTPFsRequestHandler::handlePostRequest()
-{
-    return 404;
+{  
+    INFO("Handling Post Request (msg.uri = %s).", msg.uri.c_str());
+    
+    if( std::string::npos != msg.uri.find("/toggle") )
+    {
+        led1 = !led1;        
+        return 0;
+    }    
+    else
+    {
+        return 404;
+    }
 }
 
 int HTTPFsRequestHandler::handlePutRequest()
 {
     return 404;
-}
\ No newline at end of file
+}
+
+uint32_t HTTPFsRequestHandler::get_http_param_value(char* param_name)
+{
+    uint8_t * name = 0;
+    uint8_t * pos2;
+    uint16_t len = 0;
+    char value[10];
+    uint32_t ret = 0;
+    
+    //msg.attri
+    if((name = (uint8_t *)strstr(msg.attri, param_name)))
+    {
+        name += strlen(param_name) + 1;
+        pos2 = (uint8_t*)strstr((char*)name, "&");
+        if(!pos2)
+        {
+            pos2 = name + strlen((char*)name);
+        }
+        len = pos2 - name;
+        
+        if(len)
+        {
+            strncpy(value, (char*)name, len);
+            ret = atoi(value);
+        }
+    }
+    return ret;
+}
+
--- a/Handler/FsHandler.h	Sat Aug 17 16:17:55 2013 +0000
+++ b/Handler/FsHandler.h	Sun Oct 06 18:10:41 2019 +0000
@@ -44,7 +44,7 @@
         * @param Msg : Message request information that comes with the request.
         * @param Tcp : The socket connection for communicating with the client.
         */
-        HTTPFsRequestHandler(const char* rootPath, const char* localPath, HTTPConnection::HTTPMessage& Msg, TCPSocketConnection& Tcp);
+        HTTPFsRequestHandler(const char* rootPath, const char* localPath, HTTPConnection::HTTPMessage& Msg, TCPSocket* Tcp);
         
         /** Destructor 
         */
@@ -52,7 +52,7 @@
   
         /** static creation function for this object.
         */
-        static inline HTTPRequestHandler* create(const char* rootPath, const char* localPath, HTTPConnection::HTTPMessage& msg, TCPSocketConnection& tcp) { return new HTTPFsRequestHandler(rootPath, localPath, msg, tcp); }
+        static inline HTTPRequestHandler* create(const char* rootPath, const char* localPath, HTTPConnection::HTTPMessage& msg, TCPSocket* tcp) { return new HTTPFsRequestHandler(rootPath, localPath, msg, tcp); }
               
         /** Handler function to serve GET requests
         */
@@ -77,5 +77,7 @@
         /** Parse a uri string for uri file name and argument:value pairs
         */
         int parseUriArgs(string uri, map<string, string>& args);
+        
+        uint32_t get_http_param_value(char* param_name);
 };
-#endif // __FSHANDLER_H__
\ No newline at end of file
+#endif // __FSHANDLER_H__
--- a/Handler/RpcHandler.cpp	Sat Aug 17 16:17:55 2013 +0000
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,76 +0,0 @@
-/* FsHandler.cpp */
-#include "mbed.h"
-#include "RpcHandler.h"
-#include "mbed_rpc.h"
-
-
-#define DEBUG 1
-#include "hl_debug.h"
-
-RPC rpc("rpc");
-
-
-HTTPRpcRequestHandler::HTTPRpcRequestHandler(const char* rootPath, const char* localPath, HTTPConnection::HTTPMessage& Msg, TCPSocketConnection& Tcp)
-    : HTTPRequestHandler(Msg, Tcp)
-{
-    m_rootPath = rootPath;
-    m_localPath = localPath;
-    
-    handleRequest();
-}
-
-
-HTTPRpcRequestHandler::~HTTPRpcRequestHandler()
-{
-}
-
-
-int HTTPRpcRequestHandler::handleGetRequest()
-{
-    char outBuf[256] = {};
-    bool retval = false;
-    int err = 404;
-    string rpc_args("");
-    
-    INFO("Handling RPC Get Requesst.");
-    // This version of the RPC handler does only accept native RPC commands in the format
-    //  /<class>/<method> <argument1> [<argument2> [<argument3> ...]]
-    // So we can simply pass our local pathg to our rpc
-
-    //  Append missing slash if needed
-    if (m_localPath.c_str()[0] != '/') {
-        rpc_args = "/";
-    }
-    // replace the HTTP strings with ascii strings
-    for (int i = 0 ; i < m_localPath.length() ; i++) {
-        if (m_localPath.substr(i,3) == "%20") {
-            rpc_args += " ";
-            i+=2;
-        }
-        else {
-            rpc_args += m_localPath.substr(i,1);
-        }
-    }
-    INFO("RPC to %s", rpc_args.c_str());
-    retval = rpc.call(rpc_args.c_str(),outBuf);
-    INFO("RPC Request returned %d with args : %s", retval==true ? 1 : 0, outBuf);
-    if (retval) {
-        //  No error
-        startResponse(retval, strlen(outBuf));
-        processResponse(strlen(outBuf), outBuf);
-        endResponse();
-        err = 0;
-    }
-    
-    return err;
-}
-
-int HTTPRpcRequestHandler::handlePutRequest()
-{
-    return 404;
-}
-
-int HTTPRpcRequestHandler::handlePostRequest()
-{
-    return 404;
-}
\ No newline at end of file
--- a/Handler/RpcHandler.h	Sat Aug 17 16:17:55 2013 +0000
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,68 +0,0 @@
-/* RpcHandler.h */
-/*
-Copyright (c) 2013 Henry Leinen (henry[dot]leinen [at] online [dot] de)
- 
-Permission is hereby granted, 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.
-*/
-#ifndef __RPCHANDLER_H__
-#define __RPCHANDLER_H__
-
-#include "mbed.h"
-#include "HTTPRequestHandler.h"
-
-class HTTPRpcRequestHandler : public HTTPRequestHandler
-{
-        std::string m_rootPath;
-        std::string m_localPath;
-
-    public:
-        /** constructor for HTTPRpcRequestHandler object and stores the request related data locally. 
-        * the request handling will be initiated from within the constructor.
-        * @param rootPath : The path under which the handler was registered.
-        * @param localPath : The path which is relative to the registered file system root.
-        * @param Msg : Message request information that comes with the request.
-        * @param Tcp : The socket connection for communicating with the client.
-        */
-        HTTPRpcRequestHandler(const char* rootPath, const char* localPath, HTTPConnection::HTTPMessage& Msg, TCPSocketConnection& Tcp);
-        
-        /** Destructor 
-        */
-        virtual ~HTTPRpcRequestHandler();
-  
-        /** static creation function for this object.
-        */
-        static inline HTTPRequestHandler* create(const char* rootPath, const char* localPath, HTTPConnection::HTTPMessage& msg, TCPSocketConnection& tcp) { return new HTTPRpcRequestHandler(rootPath, localPath, msg, tcp); }
-              
-        /** Handler function to serve GET requests
-        */
-        virtual int handleGetRequest();
-        
-        /** Handler function to serve PUT requests
-        */
-        virtual int handlePutRequest();
-        
-        /** Handler function to serve POST requests
-        */
-        virtual int handlePostRequest();
-
-        /** Parse a uri string for uri file name and argument:value pairs
-        */
-//        int parseUriArgs(string uri, string map<string, string>& args);
-};
-#endif //   __RPCHANDLER_H__
\ No newline at end of file