The lib with which to make LPC1768 a simple HTTP server. This have not yet implemented. fopen() DOESN'T WORK after EthernetInterface::connect() is called as using mbed-os 5.4~. See also https://os.mbed.com/questions/80658/HardFault-occurs-when-fopen-is-called-af/ or https://github.com/ARMmbed/mbed-os/issues/6578 and https://github.com/ARMmbed/mbed-os/issues/6624

Fork of HTTP_SERVER by Akifumi Takahashi

Committer:
aktk
Date:
Sat Nov 26 18:22:42 2016 +0000
Revision:
3:59884bc0a238
Parent:
2:33714d7c0f45
Child:
4:b551799053c6
fix the library to be compilable

Who changed what in which revision?

UserRevisionLine numberNew contents of line
aktk 0:cc483bea4fe3 1 #include "HTTP_SERVER.h"
aktk 1:3a1fe94c6e42 2 #include "string"
aktk 0:cc483bea4fe3 3 #define DEBUG
aktk 1:3a1fe94c6e42 4
aktk 1:3a1fe94c6e42 5 void DEBUG_PRINT_LINE(const char* arg_line)
aktk 1:3a1fe94c6e42 6 {
aktk 1:3a1fe94c6e42 7 #ifdef DEBUG
aktk 1:3a1fe94c6e42 8 printf("%s",arg_line);
aktk 1:3a1fe94c6e42 9 #endif
aktk 1:3a1fe94c6e42 10 }
aktk 1:3a1fe94c6e42 11
aktk 0:cc483bea4fe3 12 HttpServer::HttpServer()
aktk 0:cc483bea4fe3 13 {
aktk 0:cc483bea4fe3 14 keep_alive = (false);
aktk 0:cc483bea4fe3 15 listening_flag = (false);
aktk 0:cc483bea4fe3 16 req_buf[0] = '\0';
aktk 0:cc483bea4fe3 17 }
aktk 0:cc483bea4fe3 18
aktk 0:cc483bea4fe3 19 HttpServer::~HttpServer()
aktk 0:cc483bea4fe3 20 {
aktk 0:cc483bea4fe3 21 }
aktk 0:cc483bea4fe3 22
aktk 0:cc483bea4fe3 23 bool HttpServer::init()
aktk 0:cc483bea4fe3 24 {
aktk 0:cc483bea4fe3 25
aktk 0:cc483bea4fe3 26 // Ethernet Initialization
aktk 0:cc483bea4fe3 27 if(eth.init()) {
aktk 1:3a1fe94c6e42 28 printf("(HTTP_SERVER) Error!@EthernetInterface::init()\r\n");
aktk 0:cc483bea4fe3 29 return false;
aktk 0:cc483bea4fe3 30 }
aktk 0:cc483bea4fe3 31 // Ethernet Connecting setup
aktk 0:cc483bea4fe3 32 if(eth.connect()) {
aktk 1:3a1fe94c6e42 33 printf("(HTTP_SERVER) Error!@EthernetInterface::connect()\r\n");
aktk 0:cc483bea4fe3 34 return false;
aktk 0:cc483bea4fe3 35 } else {
aktk 1:3a1fe94c6e42 36 printf("(HTTP_SERVER) IP Address is %s\r\n", eth.getIPAddress());
aktk 0:cc483bea4fe3 37 }
aktk 0:cc483bea4fe3 38 // TCP Socket setup
aktk 0:cc483bea4fe3 39 // To open Server-side PORT
aktk 0:cc483bea4fe3 40 if(tcpsvr.bind(TCP_PORT)< 0) {
aktk 1:3a1fe94c6e42 41 printf("(HTTP_SERVER) Error!@TCPSocketServer::bind()\r\n");
aktk 0:cc483bea4fe3 42 return false;
aktk 0:cc483bea4fe3 43 } else {
aktk 1:3a1fe94c6e42 44 printf("(HTTP_SERVER) TCP Server has bounden!\r\n");
aktk 0:cc483bea4fe3 45 }
aktk 0:cc483bea4fe3 46 // Server start listening Request from a web browser.
aktk 0:cc483bea4fe3 47 if(tcpsvr.listen(1) < 0) {
aktk 1:3a1fe94c6e42 48 printf("(HTTP_SERVER) tcp server listen failed.\r\n");
aktk 0:cc483bea4fe3 49 return false;
aktk 0:cc483bea4fe3 50 } else {
aktk 0:cc483bea4fe3 51 listening_flag = true;
aktk 1:3a1fe94c6e42 52 printf("(HTTP_SERVER) tcp server is listening...\r\n");
aktk 0:cc483bea4fe3 53 }
aktk 0:cc483bea4fe3 54
aktk 0:cc483bea4fe3 55 return true;
aktk 0:cc483bea4fe3 56 }
aktk 0:cc483bea4fe3 57
aktk 0:cc483bea4fe3 58 bool HttpServer::run()
aktk 0:cc483bea4fe3 59 {
aktk 0:cc483bea4fe3 60 DigitalOut led1(LED1);
aktk 0:cc483bea4fe3 61 DigitalOut led2(LED1);
aktk 0:cc483bea4fe3 62
aktk 0:cc483bea4fe3 63 while (listening_flag) {
aktk 0:cc483bea4fe3 64 led1 = true;
aktk 0:cc483bea4fe3 65 // blocking mode (never timeout)
aktk 0:cc483bea4fe3 66 // waiting client connection
aktk 1:3a1fe94c6e42 67 printf("(HTTP_SERVER) waiting connection\r\n");
aktk 0:cc483bea4fe3 68 if(tcpsvr.accept(tcpcon) < 0) {
aktk 1:3a1fe94c6e42 69 printf("(HTTP_SERVER) failed to accept connection.\r\n");
aktk 0:cc483bea4fe3 70 return -1;
aktk 0:cc483bea4fe3 71 } else {
aktk 1:3a1fe94c6e42 72 printf("(HTTP_SERVER) connection success!\r\nIP: %s\r\n",tcpcon.get_address());
aktk 0:cc483bea4fe3 73 led2 = true;
aktk 0:cc483bea4fe3 74 }
aktk 1:3a1fe94c6e42 75 // When conected
aktk 0:cc483bea4fe3 76 while(tcpcon.is_connected()) {
aktk 1:3a1fe94c6e42 77 DEBUG_PRINT_LINE("(HTTP_SERVER) connected\r\n");
aktk 1:3a1fe94c6e42 78
aktk 0:cc483bea4fe3 79 char buffer[1024] = {0};
aktk 0:cc483bea4fe3 80 char* httpmethod = NULL;
aktk 0:cc483bea4fe3 81 char* filepath = NULL;
aktk 0:cc483bea4fe3 82 char* http_ver = NULL;
aktk 0:cc483bea4fe3 83 char* header_field_name = NULL;
aktk 0:cc483bea4fe3 84 char* header_field_val = NULL;
aktk 1:3a1fe94c6e42 85
aktk 0:cc483bea4fe3 86 //
aktk 0:cc483bea4fe3 87 // Request Analysis
aktk 0:cc483bea4fe3 88 //
aktk 1:3a1fe94c6e42 89 DEBUG_PRINT_LINE("(HTTP_SERVER) DEBUG MODE\r\n");
aktk 0:cc483bea4fe3 90 switch(tcpcon.receive(buffer, 1023)) {
aktk 0:cc483bea4fe3 91 case 0:
aktk 1:3a1fe94c6e42 92 printf("(HTTP_SERVER) recieved buffer is empty.\r\n");
aktk 0:cc483bea4fe3 93 msger.setStatusLine(400, "No Request");
aktk 0:cc483bea4fe3 94 httpmethod = NULL;
aktk 0:cc483bea4fe3 95 filepath = NULL;
aktk 0:cc483bea4fe3 96 http_ver = NULL;
aktk 0:cc483bea4fe3 97 break;
aktk 0:cc483bea4fe3 98 case -1:
aktk 1:3a1fe94c6e42 99 printf("(HTTP_SERVER) failed to read data from client.\r\n");
aktk 0:cc483bea4fe3 100 msger.setStatusLine(500, "Internal Server Error");
aktk 0:cc483bea4fe3 101 httpmethod = NULL;
aktk 0:cc483bea4fe3 102 filepath = NULL;
aktk 0:cc483bea4fe3 103 http_ver = NULL;
aktk 0:cc483bea4fe3 104 break;
aktk 0:cc483bea4fe3 105 default:
aktk 1:3a1fe94c6e42 106 printf("(HTTP_SERVER) Recieved Data: %d\r\n-->\r\n%.*s[End of Request]\r\n",strlen(buffer),strlen(buffer),buffer);
aktk 0:cc483bea4fe3 107 // get HTTP method
aktk 0:cc483bea4fe3 108 httpmethod = strtok(buffer," ");
aktk 0:cc483bea4fe3 109 // get File path
aktk 0:cc483bea4fe3 110 filepath = strtok(NULL, " ");
aktk 0:cc483bea4fe3 111 // get HTTP version
aktk 0:cc483bea4fe3 112 http_ver = strtok(NULL, "\r\n");
aktk 0:cc483bea4fe3 113 #ifdef DEBUG
aktk 1:3a1fe94c6e42 114 printf("(HTTP_SERVER) httpmethod: %s\r\n", httpmethod);
aktk 1:3a1fe94c6e42 115 printf("(HTTP_SERVER) file path: %s\r\n", filepath);
aktk 1:3a1fe94c6e42 116 printf("(HTTP_SERVER) http ver : %s\r\n", http_ver);
aktk 0:cc483bea4fe3 117 #endif
aktk 0:cc483bea4fe3 118 break;
aktk 0:cc483bea4fe3 119 }
aktk 1:3a1fe94c6e42 120 DEBUG_PRINT_LINE("\r\n"
aktk 1:3a1fe94c6e42 121 "(HTTP_SERVER) debug before response\r\n");
aktk 1:3a1fe94c6e42 122
aktk 0:cc483bea4fe3 123 //
aktk 0:cc483bea4fe3 124 // Response
aktk 0:cc483bea4fe3 125 //
aktk 0:cc483bea4fe3 126 if (strcmp(httpmethod,"GET") == 0 ) {
aktk 1:3a1fe94c6e42 127 printf("(HTTP_SERVER) GET request incomming.\r\n");
aktk 0:cc483bea4fe3 128
aktk 0:cc483bea4fe3 129 // file calibration
aktk 1:3a1fe94c6e42 130 DEBUG_PRINT_LINE("(HTTP_SERVER) file opening\r\n");
aktk 0:cc483bea4fe3 131 fhandl.open(filepath,"rb");
aktk 0:cc483bea4fe3 132 if(fhandl.arrival()) {
aktk 0:cc483bea4fe3 133 msger.setStatusLine(200, "OK");
aktk 0:cc483bea4fe3 134 if(msger.setHeaderField("Content-Length", fhandl.getFileSize()))printf("buffer over flow");
aktk 0:cc483bea4fe3 135 if(msger.setHeaderField("Connection", "keep-alive"))printf("buffer over flow");
aktk 0:cc483bea4fe3 136 } else {
aktk 0:cc483bea4fe3 137 if(msger.setStatusLine(404, "NOT FOUND"))printf("buffer over flow");
aktk 0:cc483bea4fe3 138 if(msger.setHeaderField("Connection", "close"))printf("buffer over flow");
aktk 1:3a1fe94c6e42 139 DEBUG_PRINT_LINE("(HTTP_SERVER) NOT FOUND\r\n");
aktk 0:cc483bea4fe3 140 }
aktk 1:3a1fe94c6e42 141 if( strcmp(fhandl.getSuffix(), "htm" ) ||
aktk 1:3a1fe94c6e42 142 strcmp(fhandl.getSuffix(), "HTM" ) ||
aktk 1:3a1fe94c6e42 143 strcmp(fhandl.getSuffix(), "html") ||
aktk 1:3a1fe94c6e42 144 strcmp(fhandl.getSuffix(), "HTML")) {
aktk 0:cc483bea4fe3 145 if(msger.setHeaderField("Content-Type", "text/html"))printf("buffer over flow");
aktk 1:3a1fe94c6e42 146 } else if (strcmp(fhandl.getSuffix(), "ico" ) ) {
aktk 0:cc483bea4fe3 147 if(msger.setHeaderField("Content-Type", "image/png"))printf("buffer over flow");
aktk 0:cc483bea4fe3 148 } else {
aktk 0:cc483bea4fe3 149 msger.setStatusLine(406, "not acceptable");
aktk 0:cc483bea4fe3 150 }
aktk 0:cc483bea4fe3 151
aktk 0:cc483bea4fe3 152 // Connection timeout field
aktk 0:cc483bea4fe3 153 if(msger.setHeaderField("Keep-Alive", "timeouit=15"))printf("buffer over flow");
aktk 1:3a1fe94c6e42 154
aktk 1:3a1fe94c6e42 155 // Define behaviour of server according to Request Header lines
aktk 2:33714d7c0f45 156 // Apply request header field to response header field
aktk 3:59884bc0a238 157 char* field_Connection = NULL;
aktk 3:59884bc0a238 158 char* field_Upgrade = NULL;
aktk 3:59884bc0a238 159 char* field_Sec_WebSocket_Key = NULL;
aktk 3:59884bc0a238 160 char* field_Sec_WebSocket_Version = NULL;
aktk 3:59884bc0a238 161 char* field_Origin = NULL;
aktk 0:cc483bea4fe3 162 do {
aktk 2:33714d7c0f45 163 //Analyze the header feilds
aktk 0:cc483bea4fe3 164 header_field_name = strtok(NULL, ":");
aktk 0:cc483bea4fe3 165 header_field_name++;
aktk 0:cc483bea4fe3 166 header_field_val = strtok(NULL, "\r\n");
aktk 0:cc483bea4fe3 167 header_field_val++;
aktk 2:33714d7c0f45 168
aktk 2:33714d7c0f45 169 if(header_field_name != NULL) {
aktk 3:59884bc0a238 170 if(!strcmp(header_field_name, "Connection")) {
aktk 3:59884bc0a238 171 field_Connection = header_field_val;
aktk 3:59884bc0a238 172 } else if(!strcmp(header_field_name, "Upgrade")) {
aktk 3:59884bc0a238 173 field_Upgrade = header_field_val;
aktk 3:59884bc0a238 174 } else if(!strcmp(header_field_name, "Sec-WebSocket-Key") ) {
aktk 3:59884bc0a238 175 field_Sec_WebSocket_Key = header_field_val;
aktk 3:59884bc0a238 176 } else if(!strcmp(header_field_name, "Sec-WebSocket-Version") ) {
aktk 3:59884bc0a238 177 field_Sec_WebSocket_Version = header_field_val;
aktk 3:59884bc0a238 178 } else if(!strcmp(header_field_name, "Origin") ) {
aktk 3:59884bc0a238 179 field_Origin = header_field_val;
aktk 2:33714d7c0f45 180 }
aktk 3:59884bc0a238 181 } else break;
aktk 0:cc483bea4fe3 182 #ifdef DEBUG
aktk 1:3a1fe94c6e42 183 printf("(HTTP_SERVER) *header_field_name adr: %d %s\r\n", header_field_name - 1, header_field_name);
aktk 1:3a1fe94c6e42 184 printf("(HTTP_SERVER) header_field_val adr: %d %s\r\n", header_field_val - 1, header_field_val);
aktk 0:cc483bea4fe3 185 #endif
aktk 2:33714d7c0f45 186 } while(1);
aktk 2:33714d7c0f45 187
aktk 2:33714d7c0f45 188 // if the request is to switching to the WebSocket Server
aktk 3:59884bc0a238 189 if( !strcmp(field_Connection, "Upgrade") &&
aktk 2:33714d7c0f45 190 !strcmp(field_Upgrade, "websocket") &&
aktk 2:33714d7c0f45 191 field_Sec_WebSocket_Key != NULL &&
aktk 2:33714d7c0f45 192 !strcmp(field_Sec_WebSocket_Version, "13") &&
aktk 2:33714d7c0f45 193 field_Origin != NULL) {
aktk 2:33714d7c0f45 194 DEBUG_PRINT_LINE("(HTTP_SERVER) Communication Protocol will be Upgraded to Websocket! \r\n");
aktk 2:33714d7c0f45 195 /*
aktk 2:33714d7c0f45 196 if(ws.isValid()){
aktk 3:59884bc0a238 197 ...//calcurate the key
aktk 2:33714d7c0f45 198 msger.resetHeader();
aktk 2:33714d7c0f45 199 msger.setStatusLine(101, "Switching Protocols");
aktk 2:33714d7c0f45 200 if(msger.msger.setHeaderField("Connection", "Upgrade")) printf("(HTTP_SERVER)buffer over flow@ResposeMessenger");
aktk 2:33714d7c0f45 201 if(msger.msger.setHeaderField("Upgrade", "websocket")) printf("(HTTP_SERVER)buffer over flow@ResposeMessenger");
aktk 2:33714d7c0f45 202 if(msger.msger.setHeaderField("Sec-WebSocket-Accept", ...)) printf("(HTTP_SERVER)buffer over flow@ResposeMessenger");
aktk 2:33714d7c0f45 203 if(msger.msger.setHeaderField("Access-Control-Allow-Origin", "*")) printf("(HTTP_SERVER)buffer over flow@ResposeMessenger");
aktk 0:cc483bea4fe3 204 }
aktk 3:59884bc0a238 205 else goto AAA;
aktk 2:33714d7c0f45 206 */
aktk 2:33714d7c0f45 207 } else {
aktk 3:59884bc0a238 208 //AAA:
aktk 2:33714d7c0f45 209 DEBUG_PRINT_LINE("(HTTP_SERVER) Communication Protocol won't be Upgraded.\r\n");
aktk 2:33714d7c0f45 210 msger.setStatusLine(426, "Upgrade Required");
aktk 2:33714d7c0f45 211 if(msger.setHeaderField("Connection", "Close"))printf("buffer over flow");
aktk 2:33714d7c0f45 212 }
aktk 2:33714d7c0f45 213
aktk 1:3a1fe94c6e42 214
aktk 0:cc483bea4fe3 215 #ifdef DEBUG
aktk 0:cc483bea4fe3 216 //printf("status code : %d\r\n", status_code);
aktk 0:cc483bea4fe3 217 //printf("content type: %s\r\n", content_type);
aktk 0:cc483bea4fe3 218 #endif
aktk 0:cc483bea4fe3 219
aktk 0:cc483bea4fe3 220 // send response
aktk 0:cc483bea4fe3 221 msger.sendHTTPResponse(tcpcon, fhandl);
aktk 0:cc483bea4fe3 222
aktk 0:cc483bea4fe3 223 //file close
aktk 0:cc483bea4fe3 224 #ifdef DEBUG
aktk 0:cc483bea4fe3 225 if(
aktk 0:cc483bea4fe3 226 #endif
aktk 0:cc483bea4fe3 227 fhandl.close()
aktk 0:cc483bea4fe3 228 #ifndef DEBUG
aktk 0:cc483bea4fe3 229 ;
aktk 0:cc483bea4fe3 230 #endif
aktk 0:cc483bea4fe3 231 #ifdef DEBUG
aktk 0:cc483bea4fe3 232 == 0)
aktk 1:3a1fe94c6e42 233 printf("(HTTP_SERVER) file has closed\r\n");
aktk 0:cc483bea4fe3 234 else if(EOF)
aktk 1:3a1fe94c6e42 235 printf("(HTTP_SERVER) failed to close the file\r\n");
aktk 0:cc483bea4fe3 236 #endif
aktk 0:cc483bea4fe3 237 msger.resetHeader();
aktk 1:3a1fe94c6e42 238 printf("(HTTP_SERVER) echo back done.\r\n");
aktk 0:cc483bea4fe3 239 }
aktk 1:3a1fe94c6e42 240 printf("(HTTP_SERVER) Response to Request has done\r\n");
aktk 0:cc483bea4fe3 241 }
aktk 1:3a1fe94c6e42 242 printf("(HTTP_SERVER) close connection.\r\ntcp server is listening...\r\n");
aktk 0:cc483bea4fe3 243 tcpcon.close();
aktk 1:3a1fe94c6e42 244 //tcpsvr.close();
aktk 0:cc483bea4fe3 245 led2 = false;
aktk 0:cc483bea4fe3 246 }
aktk 0:cc483bea4fe3 247 led1 = false;
aktk 0:cc483bea4fe3 248 return 0;
aktk 0:cc483bea4fe3 249 }