A simple web server that can be bound to either the EthernetInterface or the WiflyInterface.

Dependents:   Smart-WiFly-WebServer WattEye X10Svr SSDP_Server

Committer:
WiredHome
Date:
Mon Jun 24 20:02:01 2013 +0000
Revision:
3:17928786bdb5
Parent:
2:a29c32190037
Child:
4:f34642902056
Revise so buffer allocations are alterable
; Refactor Poll() for maintenance
; Diagnostics:
; GetMaxHeaderSize() to size the buffer
; GetPerformanceData() Get Metrics
; ResetPerformanceData()

Who changed what in which revision?

UserRevisionLine numberNew contents of line
WiredHome 1:54353af0d20a 1
WiredHome 1:54353af0d20a 2 #ifndef SW_HTTPSERVER_H
WiredHome 1:54353af0d20a 3 #define SW_HTTPSERVER_H
WiredHome 1:54353af0d20a 4 #include "mbed.h"
WiredHome 1:54353af0d20a 5 //#include "MODSERIAL.h" // would like to hook in mod serial for higher performance, less blocking
WiredHome 1:54353af0d20a 6 #include "Wifly.h"
WiredHome 1:54353af0d20a 7 #include "TCPSocketServer.h"
WiredHome 1:54353af0d20a 8 #include "TCPSocketConnection.h"
WiredHome 1:54353af0d20a 9
WiredHome 1:54353af0d20a 10 #ifdef MODSERIAL_H
WiredHome 1:54353af0d20a 11 #define PC MODSERIAL
WiredHome 1:54353af0d20a 12 #else
WiredHome 1:54353af0d20a 13 #define PC Serial
WiredHome 1:54353af0d20a 14 #endif
WiredHome 1:54353af0d20a 15
WiredHome 3:17928786bdb5 16 /// This is the default buffer size used to send files. You might
WiredHome 3:17928786bdb5 17 /// size this to be a little less than the ethernet frame size
WiredHome 3:17928786bdb5 18 #define FILESEND_BUF_SIZE 1200
WiredHome 3:17928786bdb5 19
WiredHome 3:17928786bdb5 20
WiredHome 3:17928786bdb5 21 /// MAX_HEADER_SIZE is the default size to contain the largest header. This is
WiredHome 3:17928786bdb5 22 /// the size of the URL and query string, and also all the
WiredHome 3:17928786bdb5 23 /// other header information about the client. This can be
WiredHome 3:17928786bdb5 24 /// a couple of K, larger if you have big forms as it includes the
WiredHome 3:17928786bdb5 25 /// form data that is submitted.
WiredHome 3:17928786bdb5 26 #define MAX_HEADER_SIZE 1000
WiredHome 3:17928786bdb5 27
WiredHome 1:54353af0d20a 28 /// HTTPServer is a simple web server using the WiFly module.
WiredHome 0:729320f63c5c 29 ///
WiredHome 3:17928786bdb5 30 /// While simple, it is a capable, web server. The basic mode
WiredHome 3:17928786bdb5 31 /// of operation is for it to serve static web pages from an available
WiredHome 3:17928786bdb5 32 /// file system.
WiredHome 3:17928786bdb5 33 ///
WiredHome 3:17928786bdb5 34 /// The default page is index.htm (compile time defined)
WiredHome 3:17928786bdb5 35 /// standard support to serve a number of standard file types;
WiredHome 3:17928786bdb5 36 /// gif, jpg, jpeg, ico, png, zip, gz, tar, txt, pdf, htm, html
WiredHome 3:17928786bdb5 37 /// (this list is also compile time defined)
WiredHome 3:17928786bdb5 38 ///
WiredHome 3:17928786bdb5 39 /// It can also serve dynamically generated pages, and therefore
WiredHome 3:17928786bdb5 40 /// respond to form submission. Through the dynamic interface it is
WiredHome 3:17928786bdb5 41 /// then quite easy to interact with the hardware, reading the inputs
WiredHome 3:17928786bdb5 42 /// or signaling outputs.
WiredHome 3:17928786bdb5 43 ///
WiredHome 3:17928786bdb5 44 /// @code
WiredHome 3:17928786bdb5 45 /// HTTPServer svr(&wifly, HTTP_SERVER_PORT, "/local/", 30, 10, &pc);
WiredHome 3:17928786bdb5 46 /// svr.RegisterHandler("/dyn1", SimpleDynamicPage);
WiredHome 3:17928786bdb5 47 /// while (true)
WiredHome 3:17928786bdb5 48 /// {
WiredHome 3:17928786bdb5 49 /// svr.Poll(); // this is non blocking process, but variable execution
WiredHome 3:17928786bdb5 50 /// }
WiredHome 3:17928786bdb5 51 /// @endcode
WiredHome 3:17928786bdb5 52 ///
WiredHome 3:17928786bdb5 53 /// This web server used nweb as a starting point, but expanded well beyond there.
WiredHome 0:729320f63c5c 54 /// http://www.ibm.com/developerworks/systems/library/es-nweb/sidefile1.html
WiredHome 0:729320f63c5c 55 ///
WiredHome 3:17928786bdb5 56 /// @note This server uses a modified version of the mbed WiflyInterface - there
WiredHome 3:17928786bdb5 57 /// were a number of performance issues identified and resolved in the local version.
WiredHome 0:729320f63c5c 58 ///
WiredHome 3:17928786bdb5 59 /// Given: scheme://server:port/path?query_string#fragment_id
WiredHome 0:729320f63c5c 60 /// @li scheme is "http"
WiredHome 3:17928786bdb5 61 /// @li server is whatever IP the server has
WiredHome 0:729320f63c5c 62 /// @li port is the registered port
WiredHome 0:729320f63c5c 63 /// @li /path is the reference to the file (actual or logical) on the server
WiredHome 0:729320f63c5c 64 /// @li query_string is any combination of name=value pairs
WiredHome 0:729320f63c5c 65 /// @li fragment_id is a reference to an anchor on the page
WiredHome 0:729320f63c5c 66 ///
WiredHome 3:17928786bdb5 67 /// Features:
WiredHome 3:17928786bdb5 68 /// @li Serves static pages from a file system. Many normal filetypes are
WiredHome 3:17928786bdb5 69 /// supported.
WiredHome 3:17928786bdb5 70 /// @li Compile time configurable for the "default" file, typically index.htm.
WiredHome 3:17928786bdb5 71 /// @li Provides a registration interface for dynamically generated pages that
WiredHome 3:17928786bdb5 72 /// can then interact with other hardware.
WiredHome 3:17928786bdb5 73 /// @li Revised to be Non-blocking, however the execution time is variable
WiredHome 3:17928786bdb5 74 /// depending on the actions being performed.
WiredHome 3:17928786bdb5 75 ///
WiredHome 3:17928786bdb5 76 /// Limitations:
WiredHome 3:17928786bdb5 77 /// @li Supports only a single connection at a time.
WiredHome 3:17928786bdb5 78 /// @li Rapid requests for page objects (e.g. embedded images) are lost. Still
WiredHome 3:17928786bdb5 79 /// working to understand this issue.
WiredHome 3:17928786bdb5 80 ///
WiredHome 3:17928786bdb5 81 /// ToDo:
WiredHome 3:17928786bdb5 82 /// @li A web page with served objects (img src=...) is rarely served properly. It
WiredHome 3:17928786bdb5 83 /// might trace to forcing the connection to close, but not yet sure.
WiredHome 3:17928786bdb5 84 /// Explore "Set Uart Rx Data Buffer" in WiFly manual 2.3.65
WiredHome 3:17928786bdb5 85 /// @li hunt down lengthy operations - there seems to be a long timeout somewhere.
WiredHome 3:17928786bdb5 86 /// @li parse the header similar to the query string, and then make
WiredHome 2:a29c32190037 87 /// those parameters accessible - perhaps like environment vars.
WiredHome 3:17928786bdb5 88 /// @li move part of the POST method handler to the registered handler, so
WiredHome 0:729320f63c5c 89 /// it can decide if it should allocate the needed memory.
WiredHome 3:17928786bdb5 90 /// @li Add password capability to some web pages
WiredHome 3:17928786bdb5 91 /// @li transform the pc serial interface to a log interface, which might
WiredHome 0:729320f63c5c 92 /// be more useful.
WiredHome 3:17928786bdb5 93 /// @li Add ability to put WiFly in AP mode and then configuration pages
WiredHome 2:a29c32190037 94 /// to find and join a network.
WiredHome 3:17928786bdb5 95 /// @li Add ability to change/update SW in the WiFly module
WiredHome 3:17928786bdb5 96 /// @li Add ability to upload a new application to the mbed
WiredHome 2:a29c32190037 97 ///
WiredHome 2:a29c32190037 98 /// History:
WiredHome 2:a29c32190037 99 /// @li 20130530 Initial version
WiredHome 2:a29c32190037 100 /// @li 20130601 Renamed ip_process to Poll
WiredHome 3:17928786bdb5 101 /// @li 20130617 Cleaned up some of the documentation changes
WiredHome 3:17928786bdb5 102 /// @li 20130623 Make it non-blocking. "Poll" takes a variable amount
WiredHome 3:17928786bdb5 103 /// of time, based on whether it is idle, or how much it
WiredHome 3:17928786bdb5 104 /// has to do.
WiredHome 3:17928786bdb5 105 /// @li It now survives overnight and still responds, so the problem with
WiredHome 3:17928786bdb5 106 /// it going offline after long inactivity appears resolved.
WiredHome 0:729320f63c5c 107 ///
WiredHome 0:729320f63c5c 108 /// @note Copyright © 2013 by Smartware Computing, all rights reserved.
WiredHome 0:729320f63c5c 109 /// Individuals may use this application for evaluation or non-commercial
WiredHome 0:729320f63c5c 110 /// purposes. Within this restriction, changes may be made to this application
WiredHome 0:729320f63c5c 111 /// as long as this copyright notice is retained. The user shall make
WiredHome 0:729320f63c5c 112 /// clear that their work is a derived work, and not the original.
WiredHome 0:729320f63c5c 113 /// Users of this application and sources accept this application "as is" and
WiredHome 0:729320f63c5c 114 /// shall hold harmless Smartware Computing, for any undesired results while
WiredHome 0:729320f63c5c 115 /// using this application - whether real or imagined.
WiredHome 0:729320f63c5c 116 ///
WiredHome 0:729320f63c5c 117 /// @author David Smart, Smartware Computing
WiredHome 0:729320f63c5c 118 ///
WiredHome 0:729320f63c5c 119 class HTTPServer
WiredHome 0:729320f63c5c 120 {
WiredHome 0:729320f63c5c 121 public:
WiredHome 0:729320f63c5c 122 /**
WiredHome 3:17928786bdb5 123 * name-value pairs for parameters
WiredHome 0:729320f63c5c 124 */
WiredHome 3:17928786bdb5 125 typedef struct NAMEVALUE {
WiredHome 0:729320f63c5c 126 char * name;
WiredHome 0:729320f63c5c 127 char * value;
WiredHome 0:729320f63c5c 128 } namevalue;
WiredHome 2:a29c32190037 129
WiredHome 2:a29c32190037 130 /**
WiredHome 3:17928786bdb5 131 * Indicates the purpose of the Handler callback
WiredHome 3:17928786bdb5 132 *
WiredHome 3:17928786bdb5 133 * Application code in a dynamic page uses this to determine the state
WiredHome 3:17928786bdb5 134 * and therefore the needed operation to be performed.
WiredHome 3:17928786bdb5 135 *
WiredHome 3:17928786bdb5 136 * @code
WiredHome 3:17928786bdb5 137 * bool SimpleDynamicPage(HTTPServer *svr, HTTPServer::CallBackType type, const char * path, const HTTPServer::namevalue *params, int paramcount) {
WiredHome 3:17928786bdb5 138 * char buf[100];
WiredHome 3:17928786bdb5 139 * bool ret = false;
WiredHome 3:17928786bdb5 140 *
WiredHome 3:17928786bdb5 141 * switch (type) {
WiredHome 3:17928786bdb5 142 * case HTTPServer::SEND_PAGE:
WiredHome 3:17928786bdb5 143 * svr->header(200, "OK", "Content-Type: text/html\r\n");
WiredHome 3:17928786bdb5 144 * svr->send("<html><head><title>Dynamic Page</title></head>\r\n");
WiredHome 3:17928786bdb5 145 * svr->send("<body>\r\n");
WiredHome 3:17928786bdb5 146 * svr->send("This page was generated dynamically. Create your own name=value pairs on the URL "
WiredHome 3:17928786bdb5 147 * "which uses the GET method.<br/>\r\n");
WiredHome 3:17928786bdb5 148 * sprintf(buf, "%d parameters passed to {%s}:<br/>\r\n", paramcount, path);
WiredHome 3:17928786bdb5 149 * svr->send(buf);
WiredHome 3:17928786bdb5 150 * for (int i=0; i<paramcount; i++) {
WiredHome 3:17928786bdb5 151 * sprintf(buf, "%d: %s = %s<br/>\r\n", i, params[i].name, params[i].value);
WiredHome 3:17928786bdb5 152 * svr->send(buf);
WiredHome 3:17928786bdb5 153 * }
WiredHome 3:17928786bdb5 154 * svr->send("<br/><a href='/'>back to main</a></body></html>\r\n");
WiredHome 3:17928786bdb5 155 * ret = true;
WiredHome 3:17928786bdb5 156 * break;
WiredHome 3:17928786bdb5 157 * case HTTPServer::CONTENT_LENGTH_REQUEST:
WiredHome 3:17928786bdb5 158 * ret = true;
WiredHome 3:17928786bdb5 159 * break;
WiredHome 3:17928786bdb5 160 * case HTTPServer::DATA_TRANSFER:
WiredHome 3:17928786bdb5 161 * ret = true;
WiredHome 3:17928786bdb5 162 * break;
WiredHome 3:17928786bdb5 163 * default:
WiredHome 3:17928786bdb5 164 * ret = false;
WiredHome 3:17928786bdb5 165 * break;
WiredHome 3:17928786bdb5 166 * }
WiredHome 3:17928786bdb5 167 * return ret;
WiredHome 3:17928786bdb5 168 * }
WiredHome 3:17928786bdb5 169 * @endcode
WiredHome 2:a29c32190037 170 */
WiredHome 3:17928786bdb5 171 typedef enum CALLBACKTYPE {
WiredHome 3:17928786bdb5 172 CONTENT_LENGTH_REQUEST, ///< ask the client if they wish to accept the data
WiredHome 3:17928786bdb5 173 DATA_TRANSFER, ///< not currently used, may allow "chunking" the data to the client
WiredHome 3:17928786bdb5 174 SEND_PAGE, ///< the activated method should now send the page
WiredHome 2:a29c32190037 175 } CallBackType;
WiredHome 0:729320f63c5c 176
WiredHome 0:729320f63c5c 177 /**
WiredHome 3:17928786bdb5 178 * This is the prototype for custom handlers that are activated via a callback
WiredHome 0:729320f63c5c 179 *
WiredHome 3:17928786bdb5 180 * This callback gets overloaded for a few purposes, which can be identified by the \see CallBackType parameter
WiredHome 2:a29c32190037 181 * @li SEND_PAGE - the callback should now send the html page, using as many svr->send() as needed.
WiredHome 2:a29c32190037 182 * When the callback returns, it should always indicate true.
WiredHome 2:a29c32190037 183 * @li CONTENT_LENGTH_REQUEST - the server is asking the callback if it wants to receive the message,
WiredHome 2:a29c32190037 184 * which may require significant memory. If the request is accepted, true should be returned.
WiredHome 2:a29c32190037 185 * If the request is denied, false should be returned.
WiredHome 2:a29c32190037 186 *
WiredHome 0:729320f63c5c 187 * @param svr is a handle to this class, so the callback has access to member functions
WiredHome 0:729320f63c5c 188 * @param params is a pointer to an array of name value pairs
WiredHome 0:729320f63c5c 189 * @paramcount is the number of parameters.
WiredHome 2:a29c32190037 190 * @return true if command was accepted
WiredHome 0:729320f63c5c 191 */
WiredHome 2:a29c32190037 192 typedef bool (* Handler)(HTTPServer * svr, CallBackType type, const char *path, const namevalue *params, int paramcount);
WiredHome 0:729320f63c5c 193
WiredHome 0:729320f63c5c 194 /**
WiredHome 0:729320f63c5c 195 * Create the HTTPServer object.
WiredHome 0:729320f63c5c 196 *
WiredHome 0:729320f63c5c 197 * @param wifly is the serial port with the wifly interface.
WiredHome 0:729320f63c5c 198 * @param port is the optional parameter for the port number to use, default is 80.
WiredHome 0:729320f63c5c 199 * @param webroot is a file system path to the root folder for the web space.
WiredHome 0:729320f63c5c 200 * @param maxparams defines the maximum number of parameters to a dynamic function (and the memory to support them).
WiredHome 0:729320f63c5c 201 * @param maxdynamicpages defines the maximum number of dynamic pages that can be registered.
WiredHome 0:729320f63c5c 202 * @param pc is the serial port for debug information (I should transform this to a log interface)
WiredHome 3:17928786bdb5 203 * @param allocforheader is the memory allocation to support the largest expected header from a client
WiredHome 3:17928786bdb5 204 * @param allocforfile is the memory allocation to support sending a file to the client. This is typically sized to fit
WiredHome 3:17928786bdb5 205 * an ethernet frame.
WiredHome 0:729320f63c5c 206 */
WiredHome 3:17928786bdb5 207 HTTPServer(Wifly * wifly, int port = 80, const char * webroot = "/", int maxparams = 30, int maxdynamicpages = 10, PC * pc = NULL,
WiredHome 3:17928786bdb5 208 int _allocforheader = MAX_HEADER_SIZE, int _allocforfile = FILESEND_BUF_SIZE);
WiredHome 0:729320f63c5c 209
WiredHome 0:729320f63c5c 210 /**
WiredHome 3:17928786bdb5 211 * Destructor, which can clean up memory.
WiredHome 0:729320f63c5c 212 */
WiredHome 0:729320f63c5c 213 ~HTTPServer();
WiredHome 0:729320f63c5c 214
WiredHome 0:729320f63c5c 215 /**
WiredHome 3:17928786bdb5 216 * The process to call whenever there is free time, as this basically does
WiredHome 0:729320f63c5c 217 * all the work to monitor for connections and handle replies.
WiredHome 2:a29c32190037 218 *
WiredHome 2:a29c32190037 219 * 20130601 Renamed from ip_process to Poll
WiredHome 0:729320f63c5c 220 */
WiredHome 2:a29c32190037 221 void Poll();
WiredHome 0:729320f63c5c 222
WiredHome 0:729320f63c5c 223 /**
WiredHome 3:17928786bdb5 224 * Send typical header data, and some optional data back to the client.
WiredHome 3:17928786bdb5 225 *
WiredHome 3:17928786bdb5 226 * This forms and sends the typical header back to the client. It may also send
WiredHome 3:17928786bdb5 227 * optional data (which must end with "\r\n"). It then sends the second newline
WiredHome 3:17928786bdb5 228 * sequence that signals the end of the header.
WiredHome 0:729320f63c5c 229 *
WiredHome 0:729320f63c5c 230 * @param code is the optional return code; 200 = OK, if not provided then 404 = Not found is returned
WiredHome 0:729320f63c5c 231 * @param code_text is the text to align with the code (e.g. 404, "Not Found")
WiredHome 0:729320f63c5c 232 * @param content_type is a pointer to "Content-Type: text/html\r\n" (for example)
WiredHome 3:17928786bdb5 233 * @param optional_text is a pointer to any other text that is part of the header, which must
WiredHome 3:17928786bdb5 234 * have \r\n termination.
WiredHome 0:729320f63c5c 235 */
WiredHome 0:729320f63c5c 236 void header(int code = 404, const char * code_text = "Not Found", const char * content_type = NULL, const char * optional_text = NULL);
WiredHome 0:729320f63c5c 237
WiredHome 0:729320f63c5c 238 /**
WiredHome 0:729320f63c5c 239 * Send text to the client
WiredHome 0:729320f63c5c 240 *
WiredHome 3:17928786bdb5 241 * This sends the specified text to the client. If the number of bytes is not set,
WiredHome 3:17928786bdb5 242 * then it calculates the number of bytes as a string. For binary transfers, the
WiredHome 3:17928786bdb5 243 * number of bytes to send is required for proper operation.
WiredHome 3:17928786bdb5 244 *
WiredHome 0:729320f63c5c 245 * @param msg is the text string to send
WiredHome 0:729320f63c5c 246 * @param bytes is the number of bytes to send. If not set, then strlen is calculated.
WiredHome 0:729320f63c5c 247 */
WiredHome 0:729320f63c5c 248 void send(const char * msg, int bytes = -1);
WiredHome 0:729320f63c5c 249
WiredHome 0:729320f63c5c 250 /**
WiredHome 3:17928786bdb5 251 * Send a referenced file to the client, including the header
WiredHome 3:17928786bdb5 252 *
WiredHome 3:17928786bdb5 253 * This sends a file from the filesystem to the client. It must be of a supported type
WiredHome 3:17928786bdb5 254 * in order to properly create the header.
WiredHome 0:729320f63c5c 255 *
WiredHome 0:729320f63c5c 256 * @param filename is the fully qualified path and filename
WiredHome 3:17928786bdb5 257 * @param filetype is the header information (e.g. "Content-Type: application/pdf")
WiredHome 0:729320f63c5c 258 * @return true if it thinks it sent ok, false otherwise.
WiredHome 0:729320f63c5c 259 */
WiredHome 0:729320f63c5c 260 bool SendFile(const char * filename, const char * filetype);
WiredHome 0:729320f63c5c 261
WiredHome 0:729320f63c5c 262 /**
WiredHome 0:729320f63c5c 263 * register a handler for a specific URL.
WiredHome 0:729320f63c5c 264 *
WiredHome 3:17928786bdb5 265 * This api lets you register a dynamic handler in the web server. This is
WiredHome 3:17928786bdb5 266 * most useful for interactive web pages, rather than simply serving static
WiredHome 3:17928786bdb5 267 * pages.
WiredHome 3:17928786bdb5 268 *
WiredHome 3:17928786bdb5 269 * @code
WiredHome 3:17928786bdb5 270 *
WiredHome 3:17928786bdb5 271 * ...
WiredHome 3:17928786bdb5 272 * svr.RegisterHandler("/dyn1", SimpleDynamicPage);svr.RegisterHandler("/dyn1", SimpleDynamicPage);
WiredHome 3:17928786bdb5 273 * ...
WiredHome 3:17928786bdb5 274 *
WiredHome 3:17928786bdb5 275 * bool SimpleDynamicPage(HTTPServer *svr, HTTPServer::CallBackType type, const char * path, const HTTPServer::namevalue *params, int paramcount) {
WiredHome 3:17928786bdb5 276 * char buf[100];
WiredHome 3:17928786bdb5 277 * bool ret = false;
WiredHome 3:17928786bdb5 278 *
WiredHome 3:17928786bdb5 279 * switch (type) {
WiredHome 3:17928786bdb5 280 * case HTTPServer::SEND_PAGE:
WiredHome 3:17928786bdb5 281 * svr->header(200, "OK", "Content-Type: text/html\r\n");
WiredHome 3:17928786bdb5 282 * svr->send("<html><head><title>Dynamic Page</title></head>\r\n");
WiredHome 3:17928786bdb5 283 * svr->send("<body>\r\n");
WiredHome 3:17928786bdb5 284 * svr->send("This page was generated dynamically. Create your own name=value pairs on the URL "
WiredHome 3:17928786bdb5 285 * "which uses the GET method.<br/>\r\n");
WiredHome 3:17928786bdb5 286 * sprintf(buf, "%d parameters passed to {%s}:<br/>\r\n", paramcount, path);
WiredHome 3:17928786bdb5 287 * svr->send(buf);
WiredHome 3:17928786bdb5 288 * for (int i=0; i<paramcount; i++) {
WiredHome 3:17928786bdb5 289 * sprintf(buf, "%d: %s = %s<br/>\r\n", i, params[i].name, params[i].value);
WiredHome 3:17928786bdb5 290 * svr->send(buf);
WiredHome 3:17928786bdb5 291 * }
WiredHome 3:17928786bdb5 292 * svr->send("Stats:<br/>\r\n");
WiredHome 3:17928786bdb5 293 * sprintf(buf,"Free memory space: %d<br/>\r\n", Free());
WiredHome 3:17928786bdb5 294 * svr->send(buf);
WiredHome 3:17928786bdb5 295 * sprintf(buf,"Max Header size: %d<br/>\r\n", svr->GetMaxHeaderSize());
WiredHome 3:17928786bdb5 296 * svr->send(buf);
WiredHome 3:17928786bdb5 297 * svr->send("<br/><a href='/'>back to main</a></body></html>\r\n");
WiredHome 3:17928786bdb5 298 * ret = true;
WiredHome 3:17928786bdb5 299 * break;
WiredHome 3:17928786bdb5 300 * case HTTPServer::CONTENT_LENGTH_REQUEST:
WiredHome 3:17928786bdb5 301 * ret = true;
WiredHome 3:17928786bdb5 302 * break;
WiredHome 3:17928786bdb5 303 * case HTTPServer::DATA_TRANSFER:
WiredHome 3:17928786bdb5 304 * ret = true;
WiredHome 3:17928786bdb5 305 * break;
WiredHome 3:17928786bdb5 306 * default:
WiredHome 3:17928786bdb5 307 * ret = false;
WiredHome 3:17928786bdb5 308 * break;
WiredHome 3:17928786bdb5 309 * }
WiredHome 3:17928786bdb5 310 * return ret;
WiredHome 3:17928786bdb5 311 * }
WiredHome 3:17928786bdb5 312 * @endcode
WiredHome 3:17928786bdb5 313 *
WiredHome 0:729320f63c5c 314 * @param path to register
WiredHome 0:729320f63c5c 315 * @param callback of type Handler
WiredHome 0:729320f63c5c 316 * @return true if successfully registered
WiredHome 0:729320f63c5c 317 */
WiredHome 0:729320f63c5c 318 bool RegisterHandler(const char * path, Handler callback);
WiredHome 0:729320f63c5c 319
WiredHome 0:729320f63c5c 320 /**
WiredHome 0:729320f63c5c 321 * determine if the named file is a supported type (e.g. .htm, .jpg, ...)
WiredHome 0:729320f63c5c 322 *
WiredHome 3:17928786bdb5 323 * if you pass in a filename, it will attempt to extract the extension
WiredHome 3:17928786bdb5 324 * and compare that to the list of supported file types. If it finds a
WiredHome 3:17928786bdb5 325 * match, then it will return a pointer to the content-type string.
WiredHome 3:17928786bdb5 326 *
WiredHome 3:17928786bdb5 327 * @code
WiredHome 3:17928786bdb5 328 * fType = GetSupportedType("mypix.jpg");
WiredHome 3:17928786bdb5 329 * if (fType) {
WiredHome 3:17928786bdb5 330 * ...
WiredHome 3:17928786bdb5 331 * @endcode
WiredHome 3:17928786bdb5 332 *
WiredHome 0:729320f63c5c 333 * @param filename is the filename to test, based on the extension
WiredHome 0:729320f63c5c 334 * @return pointer to a Content-Type string if supported, or NULL if not.
WiredHome 0:729320f63c5c 335 */
WiredHome 0:729320f63c5c 336 const char * GetSupportedType(const char * filename);
WiredHome 0:729320f63c5c 337
WiredHome 0:729320f63c5c 338 /**
WiredHome 0:729320f63c5c 339 * search the available parameters for 'name' and if found, return the 'value'
WiredHome 0:729320f63c5c 340 *
WiredHome 3:17928786bdb5 341 * After the querystring is parsed, the server maintains an array of
WiredHome 3:17928786bdb5 342 * name=value pairs. This Get function will search for the passed in name
WiredHome 3:17928786bdb5 343 * and provide access to the value.
WiredHome 3:17928786bdb5 344 *
WiredHome 3:17928786bdb5 345 * @code
WiredHome 3:17928786bdb5 346 * BusOut leds(LED1,LED2,LED3,LED4);
WiredHome 3:17928786bdb5 347 * ...
WiredHome 3:17928786bdb5 348 * leds = atoi(svr->GetParameter("leds"));
WiredHome 3:17928786bdb5 349 * @endcode
WiredHome 3:17928786bdb5 350 *
WiredHome 0:729320f63c5c 351 * @param name is the name to search for
WiredHome 0:729320f63c5c 352 * @return pointer to the value, or NULL
WiredHome 0:729320f63c5c 353 */
WiredHome 0:729320f63c5c 354 const char * GetParameter(const char * name);
WiredHome 0:729320f63c5c 355
WiredHome 0:729320f63c5c 356 /**
WiredHome 3:17928786bdb5 357 * Parse the text string into name=value parameters.
WiredHome 3:17928786bdb5 358 *
WiredHome 3:17928786bdb5 359 * This will directly modify the referenced string. If there is a
WiredHome 3:17928786bdb5 360 * #fragment_id on the end of the string, it will be removed.
WiredHome 0:729320f63c5c 361 *
WiredHome 0:729320f63c5c 362 * @param pString is a pointer to the string.
WiredHome 0:729320f63c5c 363 */
WiredHome 0:729320f63c5c 364 void ParseParameters(char * pString);
WiredHome 0:729320f63c5c 365
WiredHome 0:729320f63c5c 366 /**
WiredHome 0:729320f63c5c 367 * Unescape string converts a coded string "in place" into a normal string
WiredHome 3:17928786bdb5 368 *
WiredHome 3:17928786bdb5 369 * A query string will have a number of characters replaced for communication
WiredHome 3:17928786bdb5 370 * which includes spaces, quotes, question marks and more. Most of them
WiredHome 3:17928786bdb5 371 * will be replaced with a %xx format, where xx is the hex code for the
WiredHome 3:17928786bdb5 372 * character. Since the string will only get shorter when this happens
WiredHome 3:17928786bdb5 373 * the operation is performed in place.
WiredHome 3:17928786bdb5 374 *
WiredHome 0:729320f63c5c 375 * this "This%20is%20a%20question%3F%20and%20an%20answer."
WiredHome 3:17928786bdb5 376 *
WiredHome 0:729320f63c5c 377 * becomes "This is a question? and an answer."
WiredHome 3:17928786bdb5 378 *
WiredHome 0:729320f63c5c 379 * @note '+' is another form of space, so is converted to a space before the %xx
WiredHome 0:729320f63c5c 380 *
WiredHome 0:729320f63c5c 381 * @param encoded string to be converted
WiredHome 0:729320f63c5c 382 */
WiredHome 0:729320f63c5c 383 void UnescapeString(char * encoded);
WiredHome 0:729320f63c5c 384
WiredHome 0:729320f63c5c 385 /**
WiredHome 0:729320f63c5c 386 * Get the IP address of the remote node to which we are connected.
WiredHome 3:17928786bdb5 387 *
WiredHome 3:17928786bdb5 388 * This will get the IP address of the remote node to which we are
WiredHome 3:17928786bdb5 389 * currently connected. This is written into the buffer in
WiredHome 3:17928786bdb5 390 * "192.168.100.234" format. If the buffer size is note >= 16 bytes,
WiredHome 3:17928786bdb5 391 * it will set the buffer to null.
WiredHome 3:17928786bdb5 392 *
WiredHome 3:17928786bdb5 393 * @note This switches the module into, and out of, command mode
WiredHome 3:17928786bdb5 394 * which has quite a time penalty.
WiredHome 3:17928786bdb5 395 *
WiredHome 3:17928786bdb5 396 * @param str is the string to write the address into, which should be at
WiredHome 3:17928786bdb5 397 * least as large as "192.168.100.203" (16-bytes).
WiredHome 3:17928786bdb5 398 * @param size of the str buffer must be >=16, so it will not buffer overrun.
WiredHome 0:729320f63c5c 399 */
WiredHome 0:729320f63c5c 400 void GetRemoteAddr(char * str, int size);
WiredHome 0:729320f63c5c 401
WiredHome 0:729320f63c5c 402 /**
WiredHome 3:17928786bdb5 403 * This is used to force a connection to close
WiredHome 3:17928786bdb5 404 *
WiredHome 3:17928786bdb5 405 * This switches the module into command mode, performs the close,
WiredHome 3:17928786bdb5 406 * then switches it back to data mode. So, this is a time-expensive
WiredHome 3:17928786bdb5 407 * command.
WiredHome 0:729320f63c5c 408 */
WiredHome 0:729320f63c5c 409 void close_connection();
WiredHome 3:17928786bdb5 410
WiredHome 3:17928786bdb5 411 /**
WiredHome 3:17928786bdb5 412 * Get the size of the largest header.
WiredHome 3:17928786bdb5 413 *
WiredHome 3:17928786bdb5 414 * This is a diagnostic function, so you can resize the allocated
WiredHome 3:17928786bdb5 415 * buffer for your application. With proper sizing, more of the
WiredHome 3:17928786bdb5 416 * system memory is available for your application.
WiredHome 3:17928786bdb5 417 *
WiredHome 3:17928786bdb5 418 * @code
WiredHome 3:17928786bdb5 419 * sprintf(buf,"Max Header size: %d<br/>\r\n", svr->GetMaxHeaderSize());
WiredHome 3:17928786bdb5 420 * svr->send(buf);
WiredHome 3:17928786bdb5 421 * @endcode
WiredHome 3:17928786bdb5 422 *
WiredHome 3:17928786bdb5 423 * @returns size in bytes of the larger header measured.
WiredHome 3:17928786bdb5 424 */
WiredHome 3:17928786bdb5 425 int GetMaxHeaderSize();
WiredHome 3:17928786bdb5 426
WiredHome 3:17928786bdb5 427
WiredHome 3:17928786bdb5 428 /**
WiredHome 3:17928786bdb5 429 * Performance parameter
WiredHome 3:17928786bdb5 430 */
WiredHome 3:17928786bdb5 431 typedef struct SW_PERFPARAM {
WiredHome 3:17928786bdb5 432 unsigned long long TotalTime_us;
WiredHome 3:17928786bdb5 433 unsigned long Samples;
WiredHome 3:17928786bdb5 434 unsigned long MaxTime_us;
WiredHome 3:17928786bdb5 435 } SW_PerformanceParam;
WiredHome 3:17928786bdb5 436
WiredHome 3:17928786bdb5 437 /**
WiredHome 3:17928786bdb5 438 * Performance metrics
WiredHome 3:17928786bdb5 439 */
WiredHome 3:17928786bdb5 440 typedef struct SW_PERFDATA {
WiredHome 3:17928786bdb5 441 SW_PerformanceParam Header;
WiredHome 3:17928786bdb5 442 SW_PerformanceParam SendData;
WiredHome 3:17928786bdb5 443 //SW_PerformanceParam SendFile;
WiredHome 3:17928786bdb5 444 } SW_PerformanceData;
WiredHome 3:17928786bdb5 445
WiredHome 3:17928786bdb5 446 /**
WiredHome 3:17928786bdb5 447 * Get performance metrics from the web server.
WiredHome 3:17928786bdb5 448 *
WiredHome 3:17928786bdb5 449 * This is a diagnostic function, and gathers data on the internal
WiredHome 3:17928786bdb5 450 * performance of the server, as it works various actions.
WiredHome 3:17928786bdb5 451 *
WiredHome 3:17928786bdb5 452 * @param p is a pointer to a SW_PerformanceData structure to be populated
WiredHome 3:17928786bdb5 453 */
WiredHome 3:17928786bdb5 454 void GetPerformanceData(SW_PerformanceData * p);
WiredHome 3:17928786bdb5 455
WiredHome 3:17928786bdb5 456 /**
WiredHome 3:17928786bdb5 457 * Reset performance metrics.
WiredHome 3:17928786bdb5 458 */
WiredHome 3:17928786bdb5 459 void ResetPerformanceData();
WiredHome 0:729320f63c5c 460
WiredHome 0:729320f63c5c 461 private:
WiredHome 0:729320f63c5c 462 Wifly * wifly;
WiredHome 0:729320f63c5c 463 char * webroot;
WiredHome 0:729320f63c5c 464 PC * pc;
WiredHome 0:729320f63c5c 465 TCPSocketServer * server;
WiredHome 0:729320f63c5c 466 TCPSocketConnection client;
WiredHome 0:729320f63c5c 467 char * rewriteWithDefaultFile(char * queryString);
WiredHome 0:729320f63c5c 468 char * rewritePrependWebroot(char * queryString);
WiredHome 0:729320f63c5c 469 int maxparams;
WiredHome 0:729320f63c5c 470 namevalue *params;
WiredHome 0:729320f63c5c 471 int paramcount;
WiredHome 3:17928786bdb5 472 int maxheaderbytes;
WiredHome 3:17928786bdb5 473 char * headerbuffer;
WiredHome 3:17928786bdb5 474 int headerbuffersize;
WiredHome 0:729320f63c5c 475
WiredHome 3:17928786bdb5 476 Timer timer; // for performance metrics gathering
WiredHome 3:17928786bdb5 477 /**
WiredHome 3:17928786bdb5 478 * Records performance data
WiredHome 3:17928786bdb5 479 *
WiredHome 3:17928786bdb5 480 * This will take a pointer to a SW_PerformanceParam, and it will
WiredHome 3:17928786bdb5 481 * take the time when the performance measurement started. It locally
WiredHome 3:17928786bdb5 482 * accesses the current time to measure the elapsed.
WiredHome 3:17928786bdb5 483 *
WiredHome 3:17928786bdb5 484 * @param param is the performance parameter to update
WiredHome 3:17928786bdb5 485 * @param value is the reference time.
WiredHome 3:17928786bdb5 486 * @returns the current time which may be used as the reference time
WiredHome 3:17928786bdb5 487 * for further measurements.
WiredHome 3:17928786bdb5 488 */
WiredHome 3:17928786bdb5 489 int RecordPerformanceData(SW_PerformanceParam * param, int value);
WiredHome 3:17928786bdb5 490 SW_PerformanceData perfData;
WiredHome 3:17928786bdb5 491
WiredHome 3:17928786bdb5 492 typedef struct HANDLER {
WiredHome 0:729320f63c5c 493 char * path;
WiredHome 0:729320f63c5c 494 Handler callback;
WiredHome 0:729320f63c5c 495 } handler;
WiredHome 0:729320f63c5c 496 int maxdynamicpages;
WiredHome 0:729320f63c5c 497 handler *handlers;
WiredHome 0:729320f63c5c 498 int handlercount;
WiredHome 3:17928786bdb5 499
WiredHome 3:17928786bdb5 500 char * queryType;
WiredHome 3:17928786bdb5 501 char * queryString;
WiredHome 3:17928786bdb5 502 char * hostString;
WiredHome 3:17928786bdb5 503 char * contentLength;
WiredHome 3:17928786bdb5 504 char * contentType;
WiredHome 3:17928786bdb5 505 char * postQueryString;
WiredHome 0:729320f63c5c 506
WiredHome 0:729320f63c5c 507 /**
WiredHome 0:729320f63c5c 508 * Extract the message from the record, by searching for the needle
WiredHome 0:729320f63c5c 509 * the string of interest follows the needle, and may be ' ' delimited
WiredHome 0:729320f63c5c 510 * Can damage haystack while processing it.
WiredHome 0:729320f63c5c 511 *
WiredHome 0:729320f63c5c 512 * @param haystack is the record to search
WiredHome 0:729320f63c5c 513 * @param needle is the text to search for, which precedes the text to return
WiredHome 0:729320f63c5c 514 * @param string is the text following the needle
WiredHome 0:729320f63c5c 515 * @return true if it extracted something successfully
WiredHome 0:729320f63c5c 516 */
WiredHome 0:729320f63c5c 517 bool Extract(char * rec, char * needle, char ** string);
WiredHome 0:729320f63c5c 518
WiredHome 3:17928786bdb5 519 void SendResponse();
WiredHome 3:17928786bdb5 520 bool ParseHeader(char * bPtr);
WiredHome 3:17928786bdb5 521 bool CheckDynamicHandlers();
WiredHome 3:17928786bdb5 522
WiredHome 0:729320f63c5c 523 int HexCharToInt(char c);
WiredHome 0:729320f63c5c 524 char HexPairToChar(char * p);
WiredHome 0:729320f63c5c 525 };
WiredHome 0:729320f63c5c 526 #endif //SW_HTTPSERVER_H