A sample program demonstrating a small but powerful web server using the Wifly module. This uses several libraries from others, but has a custom version of the WiflyInterface library, with numerous improvement to the mbed standard library.

Dependencies:   SW_HTTPServer WiflyInterface mbed C12832 IniManager

Here's the code

But you also might want to check out the SmartBoard-WiFly project page.

Basic Web Server

  • Serves static files from the selected file system. This is a compile-time setting, and a typical configuration supports gif, jpg, jpeg, ico, png, zip, gz, tar, txt, pdf, htm, and html.
  • It is designed to be small, thereby better supporting the limited resources of an embedded environment.

Advanced Web Services

  • Serves dynamically generated pages, where your software registers for a path, and then everything to that path activates your handler. Your handler then defines the header and body response.
  • Dynamic handlers can process GET query parameters (e.g. /dyn1?sky=blue&grass=green).
  • Dynamic handlers can process POST query parameters, as delivered from submission of a form.
  • Dynamic handlers can protect a resource with user:password access.

Run-Time Configurations

  • File System Support - using either the "local" file system supported by the magic chip, or from either an SD-Card or a USB flash drive.
  • Configurable to the maximum number of dynamic handlers (minimize memory requirements).
  • Configurable to the maximum number of name=value pairs for dynamic handlers (minimize memory requirements).

Compile-Time Configurations

  • Default filename for URL ending in '/' - default is 'index.htm'.
  • Configurable buffer sizes permit minimizing RAM requirements.
  • Configurable header response information.
  • Configurable for which serial port is used to communicate to the WiFly module.
  • Improved security option - to disable telnet access.

Diagnostics

  • API to determine the largest header (to more efficiently size the buffers).
  • API to gather the run-time characteristics - header processing time and content delivery time.

Limitations / Constraints

Known Issues

These are known issues, not yet resolved.

  1. Occasionally fails to serve a page - one test will constantly reload a web page every 30 seconds. It may run for hours, or minutes, then fail to load. Behaviors then are:
    • Hit the reload button in the browser and away it goes.
    • Hit the reload and you'll see the Wifly LEDs energize from the request, but no response by the web server. It appears that the embedded code does not "accept()" the connection in the TCP Socket Server.
      • In this case, the Wifly module has gone through an internal watchdog reset and the configuration parameters are such that it does not gracefully recover. Microchip is aware of this issue, but has not solved it.

Wifly Limitations

  • Single thread - it doesn't respond to overlapping requests (e.g. an embedded image may be requested before the main page completes transfer - the request is lost and the image not shown).
  • Single client - goes along with the single thread, but it doesn't support more than one client at a time.

Smart-Wifly-WebServer

  • Dynamic memory allocation - it does use dynamic memory allocation, which would be discouraged/avoided in many embedded systems. Here it uses it in parsing a request and it releases those resources upon completion of that request. If there is no other dynamic allocation that persists beyond a transaction, it should not cause memory fragmentation. Note that with multi-threading (if this is implemented with an OS), you then have race conditions that could cause fragmentation.

Web Server

Here's the web server in action. A combination of static pages served from the file system and dynamically generated pages.

/media/uploads/WiredHome/swsvr_1.pngPart of the main demo page,
which basically has all the
specifications, configurations, and limitations.
/media/uploads/WiredHome/swsvr_2.pngA zoomed out view of the same page.
/media/uploads/WiredHome/swsvr_3.pngIt would be possible to configure
the server via the web.
/media/uploads/WiredHome/swsvr_4.pngOne of the dynamically generated pages.
This one has parsed the query parameters.
/media/uploads/WiredHome/swsvr_5.pngA simple form which has a dynamic handler on the back end.
Here it takes the value associated with "leds"
and uses that to set the 4 LEDs on the mbed module.
/media/uploads/WiredHome/swsvr_6.pngA dynamic handler can require authentication.
/media/uploads/WiredHome/swsvr_7.pngSuccess!

But I've now gone so far beyond that in the current version. Here's what this one can do:

  1. It serves static web pages from a file system. I've only tested with the local file system and an SD card, but should work for any, so long as you remember that the local file system can't read subdirectories.
  2. It can serve dynamically generated web pages. This lets you accept name=value pairs using the URL (using either a GET or POST method). It can also accept them from forms. The demo lets you control the 4 LEDs from a form.
  3. As safely as possible it retrieves your credentials to the Wi-Fi Access Point. After using them, it overwrites that ram so they can't be as easily extracted.
  4. I made a large number of changes to the Wifly driver. It had too short of a timeout and I found quite a number of optimizations for performance and robustness.
  5. I have the start on a security feature - you can configure a resource to require user credentials to access it. The browser typically provides a username and password dialog. Take care however, as it does not support a secure (https) connection, so the credentials are not as securely transferred as I would like.

Optimizations I'd like to do:

  1. speed it up - I'm running the mbed to wifly module interface at 230K, which is about the top speed w/o flow control. There are other places where some time delays remain - I have eliminated a number of them.
  2. make it non-blocking, so other work can happen.
  3. integrate it with the rtos
  4. When a web page has referenced resources (e.g. an image tag), it rarely loads the image on the first try. I think the request for the resource comes in while it is still in the WiflyInterface cleaning up from the last connection. The Wifly module supports only a single connection at a time. I worked around this with a small bit of javascript to load the images after the web page.

But all in all I think it is a good start.

Program prerequisite

Here's the link to the program, but when you open it up, note a few very important items.

  1. Port Numbers listed in the constructor match the SmartBoard Baseboard.
  2. I sped up the communication baud rate to the mbed from the default 9600. Match your terminal program accordingly.
  3. Download this zip. Place it and an unzipped copy into the mbed local file system. These are the demo files.
  4. The typical ssid and password are not shown. See below to set yours.

ssid and password

You need to create a simple text file on your mbed root folder named "config.ini". The easiest way perhaps is to create "config.txt", add the information shown below and then rename it. This will be read at startup to connect you to the network. Something quite simple, like this:

[Wifi]
ssid=your_ssid
pass=your_pass_code

The program

And the program.

Import programSmart-WiFly-WebServer

A sample program demonstrating a small but powerful web server using the Wifly module. This uses several libraries from others, but has a custom version of the WiflyInterface library, with numerous improvement to the mbed standard library.

Committer:
WiredHome
Date:
Mon Feb 02 03:03:08 2015 +0000
Revision:
38:962d71d6dd0e
Parent:
35:87d3577800dc
Refresh update, bug fix, mbed application board compatibility.

Who changed what in which revision?

UserRevisionLine numberNew contents of line
WiredHome 7:72b5df2fac93 1 /// Demonstration of dynamic page creation using the Smartware Web Server
WiredHome 11:183b3893eb7d 2 ///
WiredHome 11:183b3893eb7d 3 /// There are a few samples here of the dynamically generated web pages.
WiredHome 11:183b3893eb7d 4 /// Read the header above each one for more details.
WiredHome 11:183b3893eb7d 5 ///
WiredHome 3:b3e21f3306a1 6 #include "mbed.h"
WiredHome 3:b3e21f3306a1 7
WiredHome 3:b3e21f3306a1 8 #include "SW_HTTPServer.h"
WiredHome 3:b3e21f3306a1 9 #include "DynamicPages.h"
WiredHome 35:87d3577800dc 10
WiredHome 38:962d71d6dd0e 11 //#define DEBUG "dynP" /* define DEBUG before "Utility.h" to activate the INFO, WARN, ERR macros. */
WiredHome 3:b3e21f3306a1 12 #include "Utility.h"
WiredHome 15:1f2b62130ffb 13
WiredHome 3:b3e21f3306a1 14
WiredHome 11:183b3893eb7d 15 BusOut leds(LED4,LED3,LED2,LED1); // dynamic page "/dyn2" lets you control these
WiredHome 3:b3e21f3306a1 16
WiredHome 3:b3e21f3306a1 17
WiredHome 4:178df829d62b 18 /// SimplyDynamicPage1
WiredHome 4:178df829d62b 19 ///
WiredHome 14:85c805890454 20 /// This web page is generated dynamically as a kind of "bare minimum".
WiredHome 11:183b3893eb7d 21 /// It doesn't do much.
WiredHome 11:183b3893eb7d 22 ///
WiredHome 11:183b3893eb7d 23 /// You can see in main how this page was registered.
WiredHome 4:178df829d62b 24 ///
WiredHome 29:14c47d31a9dc 25 HTTPServer::CallBackResults SuperSimpleDynamicPage(HTTPServer *svr, HTTPServer::CallBackType type, const char * path, const HTTPServer::namevalue *params, int paramcount)
WiredHome 14:85c805890454 26 {
WiredHome 29:14c47d31a9dc 27 HTTPServer::CallBackResults ret = HTTPServer::ACCEPT_ERROR;
WiredHome 16:ab1867ffcf94 28 char contentlen[30];
WiredHome 16:ab1867ffcf94 29 char buf[250];
WiredHome 14:85c805890454 30
WiredHome 4:178df829d62b 31 switch (type) {
WiredHome 4:178df829d62b 32 case HTTPServer::SEND_PAGE:
WiredHome 16:ab1867ffcf94 33 // This sample drops it all into a local buffer, computes the length,
WiredHome 16:ab1867ffcf94 34 // and passes that along as well. This can help the other end with efficiency.
WiredHome 35:87d3577800dc 35 strcpy(buf, "<html><head><title>Home Page</title></head>\r\n");
WiredHome 16:ab1867ffcf94 36 strcat(buf, "<body>\r\n");
WiredHome 16:ab1867ffcf94 37 strcat(buf, "<h1>Smart WiFly Web Server</h1>\r\n");
WiredHome 16:ab1867ffcf94 38 strcat(buf, "This page was generated dynamically.<br/>\r\n");
WiredHome 35:87d3577800dc 39 strcat(buf, "<a href='/dyn'>To another dynamically generated page.</a><br/>\r\n");
WiredHome 35:87d3577800dc 40 strcat(buf, "<a href='/led'>A page to control the LEDs.</a><br/>\r\n");
WiredHome 35:87d3577800dc 41 strcat(buf, "</body></html>\r\n");
WiredHome 16:ab1867ffcf94 42 sprintf(contentlen, "Content-Length: %d\r\n", strlen(buf));
WiredHome 16:ab1867ffcf94 43 // Now the actual header response
WiredHome 16:ab1867ffcf94 44 svr->header(200, "OK", "Content-Type: text/html\r\n", contentlen);
WiredHome 16:ab1867ffcf94 45 // and data are sent
WiredHome 16:ab1867ffcf94 46 svr->send(buf);
WiredHome 29:14c47d31a9dc 47 ret = HTTPServer::ACCEPT_COMPLETE;
WiredHome 4:178df829d62b 48 break;
WiredHome 4:178df829d62b 49 case HTTPServer::CONTENT_LENGTH_REQUEST:
WiredHome 29:14c47d31a9dc 50 ret = HTTPServer::ACCEPT_COMPLETE;
WiredHome 4:178df829d62b 51 break;
WiredHome 4:178df829d62b 52 case HTTPServer::DATA_TRANSFER:
WiredHome 29:14c47d31a9dc 53 ret = HTTPServer::ACCEPT_COMPLETE;
WiredHome 4:178df829d62b 54 break;
WiredHome 4:178df829d62b 55 default:
WiredHome 29:14c47d31a9dc 56 ret = HTTPServer::ACCEPT_ERROR;
WiredHome 4:178df829d62b 57 break;
WiredHome 4:178df829d62b 58 }
WiredHome 4:178df829d62b 59 return ret;
WiredHome 4:178df829d62b 60 }
WiredHome 4:178df829d62b 61
WiredHome 4:178df829d62b 62
WiredHome 3:b3e21f3306a1 63 /// SimplyDynamicPage
WiredHome 3:b3e21f3306a1 64 ///
WiredHome 14:85c805890454 65 /// This web page is generated dynamically and fills in part of the information from
WiredHome 11:183b3893eb7d 66 /// data extracted from the URL as a query string. It also shows some additional
WiredHome 11:183b3893eb7d 67 /// information - memory stats, server stats and so forth.
WiredHome 3:b3e21f3306a1 68 ///
WiredHome 3:b3e21f3306a1 69 /// You can see in main how this page was registered.
WiredHome 3:b3e21f3306a1 70 ///
WiredHome 29:14c47d31a9dc 71 HTTPServer::CallBackResults SimpleDynamicPage(HTTPServer *svr, HTTPServer::CallBackType type, const char * path, const HTTPServer::namevalue *params, int paramcount)
WiredHome 14:85c805890454 72 {
WiredHome 31:c9136c0f4024 73 static unsigned int pageCounter = 0;
WiredHome 38:962d71d6dd0e 74 char buf[150];
WiredHome 29:14c47d31a9dc 75 HTTPServer::CallBackResults ret = HTTPServer::ACCEPT_ERROR;
WiredHome 4:178df829d62b 76 HTTPServer::SW_PerformanceData perfData;
WiredHome 35:87d3577800dc 77 //Wifly * w = svr->GetWifly()->getInstance();
WiredHome 14:85c805890454 78
WiredHome 3:b3e21f3306a1 79 switch (type) {
WiredHome 3:b3e21f3306a1 80 case HTTPServer::SEND_PAGE:
WiredHome 35:87d3577800dc 81 INFO("dt: %d, %s", type, path);
WiredHome 4:178df829d62b 82 if (strcmp("true", svr->GetParameter("Reset")) == 0)
WiredHome 4:178df829d62b 83 svr->ResetPerformanceData();
WiredHome 4:178df829d62b 84 // Send the header
WiredHome 3:b3e21f3306a1 85 svr->header(200, "OK", "Content-Type: text/html\r\n");
WiredHome 14:85c805890454 86
WiredHome 4:178df829d62b 87 // Send top of the page
WiredHome 16:ab1867ffcf94 88 svr->send(
WiredHome 31:c9136c0f4024 89 "<html><head><title>Dynamic Page</title><meta http-equiv='refresh' content='15'></head>\r\n"
WiredHome 16:ab1867ffcf94 90 "<body>\r\n"
WiredHome 16:ab1867ffcf94 91 "<h1>Smart WiFly Web Server</h1>\r\n"
WiredHome 16:ab1867ffcf94 92 "This page was generated dynamically. Create your own name=value pairs on the URL "
WiredHome 31:c9136c0f4024 93 "which uses the GET method.<br/>\r\n");
WiredHome 4:178df829d62b 94
WiredHome 31:c9136c0f4024 95 sprintf(buf, "This page has been accessed %d times.<br/>\r\n", ++pageCounter);
WiredHome 31:c9136c0f4024 96 svr->send(buf);
WiredHome 31:c9136c0f4024 97
WiredHome 4:178df829d62b 98 // Show Passed-in parameters
WiredHome 31:c9136c0f4024 99 svr->send("<h2>Query Parameters:</h2><blockquote>\r\n");
WiredHome 3:b3e21f3306a1 100 sprintf(buf, "%d parameters passed to {%s}:<br/>\r\n", paramcount, path);
WiredHome 3:b3e21f3306a1 101 svr->send(buf);
WiredHome 3:b3e21f3306a1 102 // show each of the parameters passed on the URL
WiredHome 3:b3e21f3306a1 103 for (int i=0; i<paramcount; i++) {
WiredHome 3:b3e21f3306a1 104 sprintf(buf, "%d: %s = %s<br/>\r\n", i, params[i].name, params[i].value);
WiredHome 3:b3e21f3306a1 105 svr->send(buf);
WiredHome 3:b3e21f3306a1 106 }
WiredHome 4:178df829d62b 107 svr->send("</blockquote>\r\n");
WiredHome 4:178df829d62b 108
WiredHome 4:178df829d62b 109 // Show Memory Stats
WiredHome 16:ab1867ffcf94 110 svr->send(
WiredHome 16:ab1867ffcf94 111 "<h2>System Statistics:</h2><blockquote>\r\n"
WiredHome 16:ab1867ffcf94 112 "<table border='1'><tr><td>Parameter</td><td>Description</td></tr>\r\n");
WiredHome 7:72b5df2fac93 113 sprintf(buf,"<tr><td align='right'>%d</td><td>Free memory</td></tr>\r\n", Free());
WiredHome 7:72b5df2fac93 114 svr->send(buf);
WiredHome 7:72b5df2fac93 115 sprintf(buf,"<tr><td align='right'>%d</td><td>Max Header size</td></tr>\r\n", svr->GetMaxHeaderSize());
WiredHome 4:178df829d62b 116 svr->send(buf);
WiredHome 35:87d3577800dc 117 //sprintf(buf,"<tr><td align='right'>%3.2f</td><td>Wifly SW version</td></tr>\r\n", w->getWiflyVersion());
WiredHome 35:87d3577800dc 118 //svr->send(buf);
WiredHome 35:87d3577800dc 119 //sprintf(buf,"<tr><td align='right'><font size='-1'>%s</font></td><td>Wifly Version Information</td></tr>\r\n", w->getWiflyVersionString());
WiredHome 35:87d3577800dc 120 //svr->send(buf);
WiredHome 7:72b5df2fac93 121 svr->send("</table>\r\n");
WiredHome 4:178df829d62b 122 svr->send("</blockquote>\r\n");
WiredHome 4:178df829d62b 123
WiredHome 7:72b5df2fac93 124 // Show Web Server Performance metrics
WiredHome 4:178df829d62b 125 svr->GetPerformanceData(&perfData);
WiredHome 7:72b5df2fac93 126 svr->send("<h2>Web Server Performance Metrics</h2><blockquote>\r\n");
WiredHome 4:178df829d62b 127 svr->send("<table border='1'><tr><td>avg time (uS)</td><td>samples</td><td>max time (uS)</td><td>description</td></tr>\r\n");
WiredHome 16:ab1867ffcf94 128
WiredHome 4:178df829d62b 129 sprintf(buf, "<tr><td align='right'>%d</td><td align='right'>%d</td><td align='right'>%d</td><td>%s</td></tr>\r\n",
WiredHome 16:ab1867ffcf94 130 (unsigned long)(perfData.ConnectionAccepted.TotalTime_us / perfData.ConnectionAccepted.Samples),
WiredHome 16:ab1867ffcf94 131 perfData.ConnectionAccepted.Samples,
WiredHome 16:ab1867ffcf94 132 (unsigned long)(perfData.ConnectionAccepted.MaxTime_us),
WiredHome 16:ab1867ffcf94 133 "Connection Accepted");
WiredHome 4:178df829d62b 134 svr->send(buf);
WiredHome 16:ab1867ffcf94 135
WiredHome 16:ab1867ffcf94 136 sprintf(buf, "<tr><td align='right'>%d</td><td align='right'>%d</td><td align='right'>%d</td><td>%s</td></tr>\r\n",
WiredHome 16:ab1867ffcf94 137 (unsigned long)(perfData.HeaderParsed.TotalTime_us / perfData.HeaderParsed.Samples),
WiredHome 16:ab1867ffcf94 138 perfData.HeaderParsed.Samples,
WiredHome 16:ab1867ffcf94 139 (unsigned long)(perfData.HeaderParsed.MaxTime_us),
WiredHome 16:ab1867ffcf94 140 "Header Parsed");
WiredHome 16:ab1867ffcf94 141 svr->send(buf);
WiredHome 16:ab1867ffcf94 142
WiredHome 4:178df829d62b 143 sprintf(buf, "<tr><td align='right'>%d</td><td align='right'>%d</td><td align='right'>%d</td><td>%s</td></tr>\r\n",
WiredHome 16:ab1867ffcf94 144 (unsigned long)(perfData.ResponseSent.TotalTime_us / perfData.ResponseSent.Samples),
WiredHome 16:ab1867ffcf94 145 perfData.ResponseSent.Samples,
WiredHome 16:ab1867ffcf94 146 (unsigned long)(perfData.ResponseSent.MaxTime_us),
WiredHome 16:ab1867ffcf94 147 "Response Sent");
WiredHome 4:178df829d62b 148 svr->send(buf);
WiredHome 16:ab1867ffcf94 149
WiredHome 16:ab1867ffcf94 150 sprintf(buf, "<tr><td align='right'>%d</td><td align='right'>%d</td><td align='right'>%d</td><td>%s</td></tr>\r\n",
WiredHome 16:ab1867ffcf94 151 (unsigned long)(perfData.ConnectionClosed.TotalTime_us / perfData.ConnectionClosed.Samples),
WiredHome 16:ab1867ffcf94 152 perfData.ConnectionClosed.Samples,
WiredHome 16:ab1867ffcf94 153 (unsigned long)(perfData.ConnectionClosed.MaxTime_us),
WiredHome 16:ab1867ffcf94 154 "Connection Closed");
WiredHome 16:ab1867ffcf94 155 svr->send(buf);
WiredHome 16:ab1867ffcf94 156
WiredHome 16:ab1867ffcf94 157 svr->send(
WiredHome 16:ab1867ffcf94 158 "<tr><td colspan='3'>&nbsp;</td><td><a href='?Reset=false'>Reload</a>"
WiredHome 16:ab1867ffcf94 159 " <a href='?Reset=true'>Reset Metrics</a></td></tr>\r\n"
WiredHome 16:ab1867ffcf94 160 "</table>\r\n"
WiredHome 16:ab1867ffcf94 161 "</blockquote>\r\n");
WiredHome 4:178df829d62b 162
WiredHome 4:178df829d62b 163 // Send bottom of the page
WiredHome 4:178df829d62b 164 svr->send("<br/><a href='/'>back to main</a></body></html>\r\n");
WiredHome 29:14c47d31a9dc 165 ret = HTTPServer::ACCEPT_COMPLETE;
WiredHome 3:b3e21f3306a1 166 break;
WiredHome 3:b3e21f3306a1 167 case HTTPServer::CONTENT_LENGTH_REQUEST:
WiredHome 35:87d3577800dc 168 INFO("dt: %d, %s", type, path);
WiredHome 29:14c47d31a9dc 169 ret = HTTPServer::ACCEPT_COMPLETE;
WiredHome 3:b3e21f3306a1 170 break;
WiredHome 3:b3e21f3306a1 171 case HTTPServer::DATA_TRANSFER:
WiredHome 35:87d3577800dc 172 INFO("dt: %d, %s", type, path);
WiredHome 29:14c47d31a9dc 173 ret = HTTPServer::ACCEPT_COMPLETE;
WiredHome 3:b3e21f3306a1 174 break;
WiredHome 3:b3e21f3306a1 175 default:
WiredHome 35:87d3577800dc 176 INFO("dt: %d, %s", type, path);
WiredHome 29:14c47d31a9dc 177 ret = HTTPServer::ACCEPT_ERROR;
WiredHome 3:b3e21f3306a1 178 break;
WiredHome 3:b3e21f3306a1 179 }
WiredHome 3:b3e21f3306a1 180 return ret;
WiredHome 3:b3e21f3306a1 181 }
WiredHome 3:b3e21f3306a1 182
WiredHome 3:b3e21f3306a1 183 /// SimplyDynamicForm
WiredHome 3:b3e21f3306a1 184 ///
WiredHome 14:85c805890454 185 /// This web page is generated dynamically and fills in part of the information from
WiredHome 3:b3e21f3306a1 186 /// data extracted from the URL. It also generates a web form, and allows you to
WiredHome 14:85c805890454 187 /// update the data in the form using the POST method. This one also updates the
WiredHome 11:183b3893eb7d 188 /// leds on the mbed module based on the form submission, so demonstrates a very
WiredHome 11:183b3893eb7d 189 /// simple interaction with the hardware.
WiredHome 3:b3e21f3306a1 190 ///
WiredHome 3:b3e21f3306a1 191 /// You can see in main how this page was registered.
WiredHome 3:b3e21f3306a1 192 ///
WiredHome 29:14c47d31a9dc 193 HTTPServer::CallBackResults SimpleDynamicForm(HTTPServer *svr, HTTPServer::CallBackType type, const char * path, const HTTPServer::namevalue *params, int paramcount)
WiredHome 14:85c805890454 194 {
WiredHome 38:962d71d6dd0e 195 char buf[150];
WiredHome 35:87d3577800dc 196 const char * p1, *p2;
WiredHome 29:14c47d31a9dc 197 HTTPServer::CallBackResults ret = HTTPServer::ACCEPT_ERROR;
WiredHome 14:85c805890454 198
WiredHome 3:b3e21f3306a1 199 switch (type) {
WiredHome 35:87d3577800dc 200 case HTTPServer::CONTENT_LENGTH_REQUEST:
WiredHome 35:87d3577800dc 201 INFO("dt: %d, %s", type, path);
WiredHome 35:87d3577800dc 202 // this callback asks this handler if it will accept a data transfer.
WiredHome 35:87d3577800dc 203 ret = HTTPServer::ACCEPT_COMPLETE;
WiredHome 35:87d3577800dc 204 break;
WiredHome 35:87d3577800dc 205
WiredHome 3:b3e21f3306a1 206 case HTTPServer::SEND_PAGE:
WiredHome 35:87d3577800dc 207 INFO("dt: %d, %s", type, path);
WiredHome 3:b3e21f3306a1 208 // set the LEDs based on a passed in parameter.
WiredHome 35:87d3577800dc 209 p1 = svr->GetParameter("leds");
WiredHome 35:87d3577800dc 210 p2 = svr->GetPostParameter("leds");
WiredHome 35:87d3577800dc 211 if (p1)
WiredHome 35:87d3577800dc 212 leds = atoi(p1);
WiredHome 35:87d3577800dc 213 else if (p2)
WiredHome 35:87d3577800dc 214 leds = atoi(p2);
WiredHome 35:87d3577800dc 215
WiredHome 3:b3e21f3306a1 216 // send the header
WiredHome 3:b3e21f3306a1 217 svr->header(200, "OK", svr->GetSupportedType(".htm")); //svr->header(200, "OK", "Content-Type: text/html\r\n");
WiredHome 3:b3e21f3306a1 218 // send some data
WiredHome 3:b3e21f3306a1 219 svr->send("<html><head><title>Dynamic Page</title></head>\r\n");
WiredHome 3:b3e21f3306a1 220 svr->send("<body>\r\n");
WiredHome 11:183b3893eb7d 221 svr->send("<h1>Smart WiFly Web Server</h1>\r\n");
WiredHome 3:b3e21f3306a1 222 svr->send("This form was generated dynamically. You can add name=value pairs on the URL "
WiredHome 3:b3e21f3306a1 223 "which will show up in the form, but the form is submitted using POST method.<br/>\r\n");
WiredHome 35:87d3577800dc 224 svr->send("Hint: <a href='/led?leds=7&sky=Blue&car=Jaguar'>leds=7&sky=Blue&car=Jaguar</a> turns on"
WiredHome 35:87d3577800dc 225 " 3 of the 4 blue leds on the mbed and passes a couple other parameters.<br/>\r\n");
WiredHome 3:b3e21f3306a1 226 sprintf(buf, "%d parameters passed to {%s}:<br/>\r\n", paramcount, path);
WiredHome 3:b3e21f3306a1 227 svr->send(buf);
WiredHome 35:87d3577800dc 228
WiredHome 3:b3e21f3306a1 229 // Create a user form for which they can post changes
WiredHome 35:87d3577800dc 230 sprintf(buf, "POST Form: <form method='post' action='%s'>\r\n", path);
WiredHome 35:87d3577800dc 231 //sprintf(buf, "<form method='post' enctype='multipart/form-data' action='%s'>\r\n", path); // not supported
WiredHome 35:87d3577800dc 232 svr->send(buf);
WiredHome 35:87d3577800dc 233 // show the parameters in a nice format
WiredHome 35:87d3577800dc 234 svr->send("<table>\r\n");
WiredHome 35:87d3577800dc 235
WiredHome 35:87d3577800dc 236 for (int i=0; i<svr->GetParameterCount(); i++) {
WiredHome 35:87d3577800dc 237 HTTPServer::namevalue * p = svr->GetParameter(i);
WiredHome 35:87d3577800dc 238 sprintf(buf, "<tr><td>%d</td><td>%s</td><td><input type='text' name='%s' value='%s'></td></tr>\r\n",
WiredHome 35:87d3577800dc 239 i, p->name, p->name, p->value);
WiredHome 35:87d3577800dc 240 svr->send(buf);
WiredHome 35:87d3577800dc 241 }
WiredHome 35:87d3577800dc 242 for (int i=0; i<svr->GetPostParameterCount(); i++) {
WiredHome 35:87d3577800dc 243 HTTPServer::namevalue * p = svr->GetPostParameter(i);
WiredHome 35:87d3577800dc 244 sprintf(buf, "<tr><td>%d</td><td>%s</td><td><input type='text' name='%s' value='%s'></td></tr>\r\n",
WiredHome 35:87d3577800dc 245 i, p->name, p->name, p->value);
WiredHome 35:87d3577800dc 246 svr->send(buf);
WiredHome 35:87d3577800dc 247 }
WiredHome 35:87d3577800dc 248
WiredHome 35:87d3577800dc 249 //svr->send("<tr><td>&nbsp;</td><td>File</td><td><input type='file' name='InFile' size='40'></td></tr>\r\n");
WiredHome 35:87d3577800dc 250 svr->send("<tr><td>&nbsp;</td><td colspan='2'><input type='submit' value='submit'><input type='reset' value='clear'></td></tr>\r\n");
WiredHome 35:87d3577800dc 251 svr->send("</table>\r\n");
WiredHome 35:87d3577800dc 252 svr->send("</form>\r\n");
WiredHome 35:87d3577800dc 253
WiredHome 35:87d3577800dc 254 // Create a user form for which they can post changes
WiredHome 35:87d3577800dc 255 sprintf(buf, "GET Form: <form method='get' action='%s'>\r\n", path);
WiredHome 3:b3e21f3306a1 256 //sprintf(buf, "<form method='post' enctype='multipart/form-data' action='%s'>\r\n", path); // not supported
WiredHome 3:b3e21f3306a1 257 svr->send(buf);
WiredHome 3:b3e21f3306a1 258 // show the parameters in a nice format
WiredHome 3:b3e21f3306a1 259 svr->send("<table>\r\n");
WiredHome 3:b3e21f3306a1 260 for (int i=0; i<paramcount; i++) {
WiredHome 35:87d3577800dc 261 sprintf(buf, "<tr><td>%d</td><td>%s</td><td><input type='text' name='%s' value='%s'></td></tr>\r\n",
WiredHome 35:87d3577800dc 262 i,
WiredHome 35:87d3577800dc 263 params[i].name, params[i].name, params[i].value);
WiredHome 3:b3e21f3306a1 264 svr->send(buf);
WiredHome 3:b3e21f3306a1 265 }
WiredHome 3:b3e21f3306a1 266 //svr->send("<tr><td>&nbsp;</td><td>File</td><td><input type='file' name='InFile' size='40'></td></tr>\r\n");
WiredHome 3:b3e21f3306a1 267 svr->send("<tr><td>&nbsp;</td><td colspan='2'><input type='submit' value='submit'><input type='reset' value='clear'></td></tr>\r\n");
WiredHome 3:b3e21f3306a1 268 svr->send("</table>\r\n");
WiredHome 3:b3e21f3306a1 269 svr->send("</form>\r\n");
WiredHome 35:87d3577800dc 270
WiredHome 4:178df829d62b 271 svr->send("<br/><a href='/'>Back to main</a></body></html>\r\n");
WiredHome 29:14c47d31a9dc 272 ret = HTTPServer::ACCEPT_COMPLETE;
WiredHome 3:b3e21f3306a1 273 break;
WiredHome 35:87d3577800dc 274
WiredHome 35:87d3577800dc 275 case HTTPServer::DATA_TRANSFER:
WiredHome 35:87d3577800dc 276 INFO("dt: %d, %s", type, path);
WiredHome 29:14c47d31a9dc 277 ret = HTTPServer::ACCEPT_COMPLETE;
WiredHome 3:b3e21f3306a1 278 break;
WiredHome 35:87d3577800dc 279
WiredHome 3:b3e21f3306a1 280 default:
WiredHome 35:87d3577800dc 281 INFO("dt: %d, %s", type, path);
WiredHome 29:14c47d31a9dc 282 ret = HTTPServer::ACCEPT_ERROR;
WiredHome 3:b3e21f3306a1 283 break;
WiredHome 3:b3e21f3306a1 284 }
WiredHome 3:b3e21f3306a1 285 return ret;
WiredHome 3:b3e21f3306a1 286 }
WiredHome 7:72b5df2fac93 287