An example HTTP Server library using new Ethernet Interface
HTTPServer.h@0:8e1971a883be, 2014-12-23 (annotated)
- Committer:
- mkilivan
- Date:
- Tue Dec 23 18:49:25 2014 +0000
- Revision:
- 0:8e1971a883be
forked from http://developer.mbed.org/users/yueee_yt/code/giken9_HTMLServer_Sample/
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
mkilivan | 0:8e1971a883be | 1 | //#define _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 2 | |
mkilivan | 0:8e1971a883be | 3 | #ifndef HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 4 | #define HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 5 | |
mkilivan | 0:8e1971a883be | 6 | #define HELLO_PAGE "/hello" |
mkilivan | 0:8e1971a883be | 7 | #define RPC_PAGE "/rpc" |
mkilivan | 0:8e1971a883be | 8 | //#define IEEE1888WSDL_PAGE "/IEEE1888?wsdl" |
mkilivan | 0:8e1971a883be | 9 | //#define IEEE1888_PAGE "/IEEE1888" |
mkilivan | 0:8e1971a883be | 10 | #define FS_PAGE "/" |
mkilivan | 0:8e1971a883be | 11 | |
mkilivan | 0:8e1971a883be | 12 | #include <string> |
mkilivan | 0:8e1971a883be | 13 | using std::string; |
mkilivan | 0:8e1971a883be | 14 | |
mkilivan | 0:8e1971a883be | 15 | #include <map> |
mkilivan | 0:8e1971a883be | 16 | using std::map; |
mkilivan | 0:8e1971a883be | 17 | |
mkilivan | 0:8e1971a883be | 18 | #include "HTTPRequestHandler.h" |
mkilivan | 0:8e1971a883be | 19 | #include "rtos.h" |
mkilivan | 0:8e1971a883be | 20 | #include "mbed.h" |
mkilivan | 0:8e1971a883be | 21 | #include "EthernetInterface.h" |
mkilivan | 0:8e1971a883be | 22 | |
mkilivan | 0:8e1971a883be | 23 | #include "Handler/RPCHandler.h" |
mkilivan | 0:8e1971a883be | 24 | #include "Handler/FSHandler.h" |
mkilivan | 0:8e1971a883be | 25 | #include "Handler/SimpleHandler.h" |
mkilivan | 0:8e1971a883be | 26 | |
mkilivan | 0:8e1971a883be | 27 | #define THREAD_MAX 3 |
mkilivan | 0:8e1971a883be | 28 | Thread *threads[THREAD_MAX]; |
mkilivan | 0:8e1971a883be | 29 | Thread *xthread; |
mkilivan | 0:8e1971a883be | 30 | |
mkilivan | 0:8e1971a883be | 31 | /* |
mkilivan | 0:8e1971a883be | 32 | struct handlersComp { //Used to order handlers in the right way |
mkilivan | 0:8e1971a883be | 33 | bool operator() (const string& handler1, const string& handler2) const { |
mkilivan | 0:8e1971a883be | 34 | //The first handler is longer than the second one |
mkilivan | 0:8e1971a883be | 35 | if (handler1.length() > handler2.length()) |
mkilivan | 0:8e1971a883be | 36 | return true; //Returns true if handler1 is to appear before handler2 |
mkilivan | 0:8e1971a883be | 37 | else if (handler1.length() < handler2.length()) |
mkilivan | 0:8e1971a883be | 38 | return false; |
mkilivan | 0:8e1971a883be | 39 | else //To avoid the == case, sort now by address |
mkilivan | 0:8e1971a883be | 40 | return ((&handler1)>(&handler2)); |
mkilivan | 0:8e1971a883be | 41 | } |
mkilivan | 0:8e1971a883be | 42 | }; |
mkilivan | 0:8e1971a883be | 43 | |
mkilivan | 0:8e1971a883be | 44 | map< string, HTTPRequestHandler*(*)(const char*, const char* , TCPSocketConnection* ), handlersComp > m_lpHandlers; |
mkilivan | 0:8e1971a883be | 45 | template<typename T> |
mkilivan | 0:8e1971a883be | 46 | void HTTPServerAddHandler(const char* path) //Template decl in header |
mkilivan | 0:8e1971a883be | 47 | { |
mkilivan | 0:8e1971a883be | 48 | m_lpHandlers[path] = &T::inst; |
mkilivan | 0:8e1971a883be | 49 | } |
mkilivan | 0:8e1971a883be | 50 | */ |
mkilivan | 0:8e1971a883be | 51 | |
mkilivan | 0:8e1971a883be | 52 | void ListenThread(void const *args); |
mkilivan | 0:8e1971a883be | 53 | enum HTTP_METH { |
mkilivan | 0:8e1971a883be | 54 | HTTP_GET, |
mkilivan | 0:8e1971a883be | 55 | HTTP_POST, |
mkilivan | 0:8e1971a883be | 56 | HTTP_HEAD |
mkilivan | 0:8e1971a883be | 57 | }; |
mkilivan | 0:8e1971a883be | 58 | |
mkilivan | 0:8e1971a883be | 59 | bool getRequest(TCPSocketConnection* client,string* path, string* meth) |
mkilivan | 0:8e1971a883be | 60 | { |
mkilivan | 0:8e1971a883be | 61 | char req[128]; |
mkilivan | 0:8e1971a883be | 62 | char c_path[128]; |
mkilivan | 0:8e1971a883be | 63 | char c_meth[128]; |
mkilivan | 0:8e1971a883be | 64 | const int maxLen = 128; |
mkilivan | 0:8e1971a883be | 65 | char* p = req; |
mkilivan | 0:8e1971a883be | 66 | //Read Line |
mkilivan | 0:8e1971a883be | 67 | int ret; |
mkilivan | 0:8e1971a883be | 68 | int len = 0; |
mkilivan | 0:8e1971a883be | 69 | for(int i = 0; i < maxLen - 1; i++) { |
mkilivan | 0:8e1971a883be | 70 | ret = client->receive(p, 1); |
mkilivan | 0:8e1971a883be | 71 | if(!ret) { |
mkilivan | 0:8e1971a883be | 72 | break; |
mkilivan | 0:8e1971a883be | 73 | } |
mkilivan | 0:8e1971a883be | 74 | if( (len > 1) && *(p-1)=='\r' && *p=='\n' ) { |
mkilivan | 0:8e1971a883be | 75 | p--; |
mkilivan | 0:8e1971a883be | 76 | len-=2; |
mkilivan | 0:8e1971a883be | 77 | break; |
mkilivan | 0:8e1971a883be | 78 | } else if( *p=='\n' ) { |
mkilivan | 0:8e1971a883be | 79 | len--; |
mkilivan | 0:8e1971a883be | 80 | break; |
mkilivan | 0:8e1971a883be | 81 | } |
mkilivan | 0:8e1971a883be | 82 | p++; |
mkilivan | 0:8e1971a883be | 83 | len++; |
mkilivan | 0:8e1971a883be | 84 | } |
mkilivan | 0:8e1971a883be | 85 | *p = 0; |
mkilivan | 0:8e1971a883be | 86 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 87 | printf("Parsing request : %s\r\n", req); |
mkilivan | 0:8e1971a883be | 88 | #endif |
mkilivan | 0:8e1971a883be | 89 | ret = sscanf(req, "%s %s HTTP/%*d.%*d", c_meth, c_path); |
mkilivan | 0:8e1971a883be | 90 | if(ret !=2) return false; |
mkilivan | 0:8e1971a883be | 91 | *meth = string(c_meth); |
mkilivan | 0:8e1971a883be | 92 | *path = string(c_path); |
mkilivan | 0:8e1971a883be | 93 | return true; |
mkilivan | 0:8e1971a883be | 94 | } |
mkilivan | 0:8e1971a883be | 95 | |
mkilivan | 0:8e1971a883be | 96 | void dispatchRequest(TCPSocketConnection* client) |
mkilivan | 0:8e1971a883be | 97 | { |
mkilivan | 0:8e1971a883be | 98 | string path; |
mkilivan | 0:8e1971a883be | 99 | string meth; |
mkilivan | 0:8e1971a883be | 100 | HTTP_METH methCode; |
mkilivan | 0:8e1971a883be | 101 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 102 | printf("Dispatching req\r\n"); |
mkilivan | 0:8e1971a883be | 103 | #endif |
mkilivan | 0:8e1971a883be | 104 | if( !getRequest(client,&path, &meth ) ) { |
mkilivan | 0:8e1971a883be | 105 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 106 | printf("dispatchRequest Invalid request\r\n"); |
mkilivan | 0:8e1971a883be | 107 | #endif |
mkilivan | 0:8e1971a883be | 108 | //close(); |
mkilivan | 0:8e1971a883be | 109 | return; //Invalid request |
mkilivan | 0:8e1971a883be | 110 | } |
mkilivan | 0:8e1971a883be | 111 | if( !meth.compare("GET") ) { |
mkilivan | 0:8e1971a883be | 112 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 113 | printf("dispatchRequest HTTP_GET\r\n"); |
mkilivan | 0:8e1971a883be | 114 | #endif |
mkilivan | 0:8e1971a883be | 115 | methCode = HTTP_GET; |
mkilivan | 0:8e1971a883be | 116 | } else if( !meth.compare("POST") ) { |
mkilivan | 0:8e1971a883be | 117 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 118 | printf("dispatchRequest HTTP_POST\r\n"); |
mkilivan | 0:8e1971a883be | 119 | #endif |
mkilivan | 0:8e1971a883be | 120 | methCode = HTTP_POST; |
mkilivan | 0:8e1971a883be | 121 | } else if( !meth.compare("HEAD") ) { |
mkilivan | 0:8e1971a883be | 122 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 123 | printf("dispatchRequest HTTP_HEAD\r\n"); |
mkilivan | 0:8e1971a883be | 124 | #endif |
mkilivan | 0:8e1971a883be | 125 | methCode = HTTP_HEAD; |
mkilivan | 0:8e1971a883be | 126 | } else { |
mkilivan | 0:8e1971a883be | 127 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 128 | printf("dispatchRequest() Parse error\r\n"); |
mkilivan | 0:8e1971a883be | 129 | #endif |
mkilivan | 0:8e1971a883be | 130 | //close(); //Parse error |
mkilivan | 0:8e1971a883be | 131 | return; |
mkilivan | 0:8e1971a883be | 132 | } |
mkilivan | 0:8e1971a883be | 133 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 134 | printf("Looking for a handler\r\n"); |
mkilivan | 0:8e1971a883be | 135 | #endif |
mkilivan | 0:8e1971a883be | 136 | /* |
mkilivan | 0:8e1971a883be | 137 | map< string, HTTPRequestHandler*(*)(const char*, const char*, TCPSocketConnection*) >::iterator it; |
mkilivan | 0:8e1971a883be | 138 | int root_len = 0; |
mkilivan | 0:8e1971a883be | 139 | for (it = m_lpHandlers.begin(); it != m_lpHandlers.end(); it++) { |
mkilivan | 0:8e1971a883be | 140 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 141 | printf("Checking %s...\r\n", (*it).first.c_str()); |
mkilivan | 0:8e1971a883be | 142 | #endif |
mkilivan | 0:8e1971a883be | 143 | root_len = (*it).first.length(); |
mkilivan | 0:8e1971a883be | 144 | if ( root_len && |
mkilivan | 0:8e1971a883be | 145 | !path.compare( 0, root_len, (*it).first ) && |
mkilivan | 0:8e1971a883be | 146 | (path[root_len] == '/' || path[root_len] == '\0')) { |
mkilivan | 0:8e1971a883be | 147 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 148 | printf("Found (%s)\r\n", (*it).first.c_str()); |
mkilivan | 0:8e1971a883be | 149 | #endif |
mkilivan | 0:8e1971a883be | 150 | // Found! |
mkilivan | 0:8e1971a883be | 151 | break; // for |
mkilivan | 0:8e1971a883be | 152 | } |
mkilivan | 0:8e1971a883be | 153 | } |
mkilivan | 0:8e1971a883be | 154 | if((it == m_lpHandlers.end()) && !(m_lpHandlers.empty())) { |
mkilivan | 0:8e1971a883be | 155 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 156 | printf("Using default handler\r\n"); |
mkilivan | 0:8e1971a883be | 157 | #endif |
mkilivan | 0:8e1971a883be | 158 | it = m_lpHandlers.end(); |
mkilivan | 0:8e1971a883be | 159 | it--; //Get the last element |
mkilivan | 0:8e1971a883be | 160 | if( ! (((*it).first.length() == 0) || !(*it).first.compare("/")) ) //This is not the default handler |
mkilivan | 0:8e1971a883be | 161 | it = m_lpHandlers.end(); |
mkilivan | 0:8e1971a883be | 162 | root_len = 0; |
mkilivan | 0:8e1971a883be | 163 | } |
mkilivan | 0:8e1971a883be | 164 | if(it == m_lpHandlers.end()) { |
mkilivan | 0:8e1971a883be | 165 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 166 | printf("No handler found\r\n"); |
mkilivan | 0:8e1971a883be | 167 | #endif |
mkilivan | 0:8e1971a883be | 168 | return; |
mkilivan | 0:8e1971a883be | 169 | } |
mkilivan | 0:8e1971a883be | 170 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 171 | printf("Handler found.\r\n"); |
mkilivan | 0:8e1971a883be | 172 | #endif |
mkilivan | 0:8e1971a883be | 173 | HTTPRequestHandler* pHdlr = (*it).second((*it).first.c_str(), path.c_str() + root_len, client); |
mkilivan | 0:8e1971a883be | 174 | */ |
mkilivan | 0:8e1971a883be | 175 | HTTPRequestHandler* pHdlr; |
mkilivan | 0:8e1971a883be | 176 | if (!path.compare(0,strlen(HELLO_PAGE),HELLO_PAGE)) { |
mkilivan | 0:8e1971a883be | 177 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 178 | printf("HELLO PAGE CREATE. PATH %s: %s \r\n",HELLO_PAGE, path.c_str() + strlen(HELLO_PAGE)); |
mkilivan | 0:8e1971a883be | 179 | #endif |
mkilivan | 0:8e1971a883be | 180 | pHdlr = new SimpleHandler(HELLO_PAGE, path.c_str() + strlen(HELLO_PAGE), client); |
mkilivan | 0:8e1971a883be | 181 | } |
mkilivan | 0:8e1971a883be | 182 | |
mkilivan | 0:8e1971a883be | 183 | #ifdef RPC_PAGE |
mkilivan | 0:8e1971a883be | 184 | else if (!path.compare(0,strlen(RPC_PAGE),RPC_PAGE)) { |
mkilivan | 0:8e1971a883be | 185 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 186 | printf("RPC PAGE CREATE. PATH %s: %s \r\n",RPC_PAGE, path.c_str() + strlen(RPC_PAGE)); |
mkilivan | 0:8e1971a883be | 187 | #endif |
mkilivan | 0:8e1971a883be | 188 | pHdlr = new RPCHandler(RPC_PAGE, path.c_str() + strlen(RPC_PAGE), client); |
mkilivan | 0:8e1971a883be | 189 | } |
mkilivan | 0:8e1971a883be | 190 | #endif |
mkilivan | 0:8e1971a883be | 191 | |
mkilivan | 0:8e1971a883be | 192 | #ifdef IEEE1888WSDL_PAGE |
mkilivan | 0:8e1971a883be | 193 | else if (!path.compare(0,strlen(IEEE1888WSDL_PAGE),IEEE1888WSDL_PAGE)) { |
mkilivan | 0:8e1971a883be | 194 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 195 | printf("IEEE1888WSDL_PAGE CREATE. PATH %s: %s \r\n",IEEE1888WSDL_PAGE, path.c_str() + strlen(IEEE1888WSDL_PAGE)); |
mkilivan | 0:8e1971a883be | 196 | #endif |
mkilivan | 0:8e1971a883be | 197 | pHdlr = new IEEE1888WSDLHandler(IEEE1888WSDL_PAGE, path.c_str() + strlen(IEEE1888WSDL_PAGE)-1, client); |
mkilivan | 0:8e1971a883be | 198 | } |
mkilivan | 0:8e1971a883be | 199 | #endif |
mkilivan | 0:8e1971a883be | 200 | |
mkilivan | 0:8e1971a883be | 201 | #ifdef IEEE1888_PAGE |
mkilivan | 0:8e1971a883be | 202 | else if (!path.compare(0,strlen(IEEE1888_PAGE),IEEE1888_PAGE)) { |
mkilivan | 0:8e1971a883be | 203 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 204 | printf("IEEE1888_PAGE CREATE. PATH %s: %s \r\n",IEEE1888_PAGE, path.c_str() + strlen(IEEE1888_PAGE)); |
mkilivan | 0:8e1971a883be | 205 | #endif |
mkilivan | 0:8e1971a883be | 206 | pHdlr = new IEEE1888Handler(IEEE1888_PAGE, path.c_str() + strlen(IEEE1888_PAGE)-1, client); |
mkilivan | 0:8e1971a883be | 207 | } |
mkilivan | 0:8e1971a883be | 208 | #endif |
mkilivan | 0:8e1971a883be | 209 | |
mkilivan | 0:8e1971a883be | 210 | #ifdef FS_PAGE |
mkilivan | 0:8e1971a883be | 211 | else if (!path.compare(0,strlen(FS_PAGE),FS_PAGE)) { |
mkilivan | 0:8e1971a883be | 212 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 213 | printf("FS_PAGE CREATE. PATH %s: %s \r\n",FS_PAGE, path.c_str() + strlen(FS_PAGE)); |
mkilivan | 0:8e1971a883be | 214 | #endif |
mkilivan | 0:8e1971a883be | 215 | pHdlr = new FSHandler(FS_PAGE, path.c_str() + strlen(FS_PAGE)-1, client); |
mkilivan | 0:8e1971a883be | 216 | } |
mkilivan | 0:8e1971a883be | 217 | #endif |
mkilivan | 0:8e1971a883be | 218 | |
mkilivan | 0:8e1971a883be | 219 | else { |
mkilivan | 0:8e1971a883be | 220 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 221 | printf("No handler found\r\n"); |
mkilivan | 0:8e1971a883be | 222 | #endif |
mkilivan | 0:8e1971a883be | 223 | pHdlr = new SimpleHandler(HELLO_PAGE, path.c_str() + strlen(HELLO_PAGE), client); |
mkilivan | 0:8e1971a883be | 224 | return; |
mkilivan | 0:8e1971a883be | 225 | } |
mkilivan | 0:8e1971a883be | 226 | //**** client = NULL; //We don't own it anymore |
mkilivan | 0:8e1971a883be | 227 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 228 | printf("Handler Created.\r\n"); |
mkilivan | 0:8e1971a883be | 229 | #endif |
mkilivan | 0:8e1971a883be | 230 | switch(methCode) { |
mkilivan | 0:8e1971a883be | 231 | case HTTP_GET: |
mkilivan | 0:8e1971a883be | 232 | pHdlr->doGet(); |
mkilivan | 0:8e1971a883be | 233 | break; |
mkilivan | 0:8e1971a883be | 234 | case HTTP_POST: |
mkilivan | 0:8e1971a883be | 235 | pHdlr->doPost(); |
mkilivan | 0:8e1971a883be | 236 | break; |
mkilivan | 0:8e1971a883be | 237 | case HTTP_HEAD: |
mkilivan | 0:8e1971a883be | 238 | pHdlr->doHead(); |
mkilivan | 0:8e1971a883be | 239 | break; |
mkilivan | 0:8e1971a883be | 240 | } |
mkilivan | 0:8e1971a883be | 241 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 242 | printf("Handler Delete.\r\n"); |
mkilivan | 0:8e1971a883be | 243 | #endif |
mkilivan | 0:8e1971a883be | 244 | delete pHdlr; |
mkilivan | 0:8e1971a883be | 245 | // delete client; |
mkilivan | 0:8e1971a883be | 246 | //delete pTCPSocketConnection; |
mkilivan | 0:8e1971a883be | 247 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 248 | printf("(dispatcherRequest)return\r\n"); |
mkilivan | 0:8e1971a883be | 249 | #endif |
mkilivan | 0:8e1971a883be | 250 | return ; |
mkilivan | 0:8e1971a883be | 251 | } |
mkilivan | 0:8e1971a883be | 252 | |
mkilivan | 0:8e1971a883be | 253 | void HTTPServerChild (void const *arg) |
mkilivan | 0:8e1971a883be | 254 | { |
mkilivan | 0:8e1971a883be | 255 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 256 | printf("HTTPServerChiled Start......\r\n"); |
mkilivan | 0:8e1971a883be | 257 | #endif |
mkilivan | 0:8e1971a883be | 258 | TCPSocketConnection* client = (TCPSocketConnection*)arg; |
mkilivan | 0:8e1971a883be | 259 | |
mkilivan | 0:8e1971a883be | 260 | for (;;) { |
mkilivan | 0:8e1971a883be | 261 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 262 | printf("(HTTPServer.h<HTTPServerChild>)Connection from %s\r\n", client->get_address()); |
mkilivan | 0:8e1971a883be | 263 | #endif |
mkilivan | 0:8e1971a883be | 264 | dispatchRequest(client); |
mkilivan | 0:8e1971a883be | 265 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 266 | printf("(HTTPServer.h<HTTPServerChild>)Client->Close %s\r\n", client->get_address()); |
mkilivan | 0:8e1971a883be | 267 | #endif |
mkilivan | 0:8e1971a883be | 268 | client->close(); |
mkilivan | 0:8e1971a883be | 269 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 270 | // printf("(HTTPServer.h<HTTPServerChild>)Client->reset\r\n"); |
mkilivan | 0:8e1971a883be | 271 | #endif |
mkilivan | 0:8e1971a883be | 272 | // client->reset_address(); |
mkilivan | 0:8e1971a883be | 273 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 274 | printf("(HTTPServer.h<HTTPServerChild>)Thread::signal_wait(1)\r\n"); |
mkilivan | 0:8e1971a883be | 275 | #endif //delete client; |
mkilivan | 0:8e1971a883be | 276 | Thread::signal_wait(1); |
mkilivan | 0:8e1971a883be | 277 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 278 | printf("(HTTPServer.h<HTTPServerChild>)Return \r\n"); |
mkilivan | 0:8e1971a883be | 279 | #endif |
mkilivan | 0:8e1971a883be | 280 | } |
mkilivan | 0:8e1971a883be | 281 | } |
mkilivan | 0:8e1971a883be | 282 | |
mkilivan | 0:8e1971a883be | 283 | void HTTPServerCloser (void const *arg) |
mkilivan | 0:8e1971a883be | 284 | { |
mkilivan | 0:8e1971a883be | 285 | TCPSocketConnection *client = (TCPSocketConnection*)arg; |
mkilivan | 0:8e1971a883be | 286 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 287 | printf("HTTPCloser start%s\r\n", client->get_address()); |
mkilivan | 0:8e1971a883be | 288 | #endif |
mkilivan | 0:8e1971a883be | 289 | |
mkilivan | 0:8e1971a883be | 290 | for (;;) { |
mkilivan | 0:8e1971a883be | 291 | client->close(); |
mkilivan | 0:8e1971a883be | 292 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 293 | printf("Close %s\r\n", client->get_address()); |
mkilivan | 0:8e1971a883be | 294 | #endif |
mkilivan | 0:8e1971a883be | 295 | Thread::signal_wait(1); |
mkilivan | 0:8e1971a883be | 296 | } |
mkilivan | 0:8e1971a883be | 297 | } |
mkilivan | 0:8e1971a883be | 298 | |
mkilivan | 0:8e1971a883be | 299 | void HTTPServerStart(int port = 80) |
mkilivan | 0:8e1971a883be | 300 | { |
mkilivan | 0:8e1971a883be | 301 | int i, t = 0; |
mkilivan | 0:8e1971a883be | 302 | TCPSocketConnection clients[THREAD_MAX]; |
mkilivan | 0:8e1971a883be | 303 | TCPSocketConnection xclient; |
mkilivan | 0:8e1971a883be | 304 | |
mkilivan | 0:8e1971a883be | 305 | for (i = 0; i < THREAD_MAX; i ++) { |
mkilivan | 0:8e1971a883be | 306 | threads[i] = NULL; |
mkilivan | 0:8e1971a883be | 307 | } |
mkilivan | 0:8e1971a883be | 308 | xthread = NULL; |
mkilivan | 0:8e1971a883be | 309 | |
mkilivan | 0:8e1971a883be | 310 | TCPSocketServer server; |
mkilivan | 0:8e1971a883be | 311 | server.bind(port); |
mkilivan | 0:8e1971a883be | 312 | server.listen(); |
mkilivan | 0:8e1971a883be | 313 | // server.set_blocking(false); |
mkilivan | 0:8e1971a883be | 314 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 315 | printf("Wait for new connection...\r\n"); |
mkilivan | 0:8e1971a883be | 316 | #endif |
mkilivan | 0:8e1971a883be | 317 | for (;;) { |
mkilivan | 0:8e1971a883be | 318 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 319 | printf("**Start Loop** \r\n"); |
mkilivan | 0:8e1971a883be | 320 | #endif |
mkilivan | 0:8e1971a883be | 321 | if (t >= 0) { |
mkilivan | 0:8e1971a883be | 322 | if(server.accept(clients[t])==0) { |
mkilivan | 0:8e1971a883be | 323 | // fork child process |
mkilivan | 0:8e1971a883be | 324 | if (threads[t]) { |
mkilivan | 0:8e1971a883be | 325 | threads[t]->signal_set(1); |
mkilivan | 0:8e1971a883be | 326 | } else { |
mkilivan | 0:8e1971a883be | 327 | threads[t] = new Thread(HTTPServerChild, (void*)&clients[t]); |
mkilivan | 0:8e1971a883be | 328 | } |
mkilivan | 0:8e1971a883be | 329 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 330 | printf("Forked %d\r\n", t); |
mkilivan | 0:8e1971a883be | 331 | #endif |
mkilivan | 0:8e1971a883be | 332 | } |
mkilivan | 0:8e1971a883be | 333 | } else { |
mkilivan | 0:8e1971a883be | 334 | if(server.accept(xclient)==0) { |
mkilivan | 0:8e1971a883be | 335 | // closer process |
mkilivan | 0:8e1971a883be | 336 | if (xthread) { |
mkilivan | 0:8e1971a883be | 337 | xthread->signal_set(1); |
mkilivan | 0:8e1971a883be | 338 | } else { |
mkilivan | 0:8e1971a883be | 339 | xthread = new Thread(HTTPServerCloser, (void*)&xclient); |
mkilivan | 0:8e1971a883be | 340 | } |
mkilivan | 0:8e1971a883be | 341 | #ifdef _DEBUG_HTTP_SERVER_H |
mkilivan | 0:8e1971a883be | 342 | printf("Connection full\r\n"); |
mkilivan | 0:8e1971a883be | 343 | #endif |
mkilivan | 0:8e1971a883be | 344 | } |
mkilivan | 0:8e1971a883be | 345 | } |
mkilivan | 0:8e1971a883be | 346 | |
mkilivan | 0:8e1971a883be | 347 | t = -1; |
mkilivan | 0:8e1971a883be | 348 | for (i = 0; i < THREAD_MAX; i ++) { |
mkilivan | 0:8e1971a883be | 349 | if (threads[i] == NULL || threads[i]->get_state() == Thread::WaitingAnd) { |
mkilivan | 0:8e1971a883be | 350 | if (t < 0) t = i; // next empty thread |
mkilivan | 0:8e1971a883be | 351 | } |
mkilivan | 0:8e1971a883be | 352 | } |
mkilivan | 0:8e1971a883be | 353 | // Thread::wait(100); |
mkilivan | 0:8e1971a883be | 354 | } |
mkilivan | 0:8e1971a883be | 355 | } |
mkilivan | 0:8e1971a883be | 356 | |
mkilivan | 0:8e1971a883be | 357 | |
mkilivan | 0:8e1971a883be | 358 | #endif |
mkilivan | 0:8e1971a883be | 359 | |
mkilivan | 0:8e1971a883be | 360 |