summaryrefslogtreecommitdiff
path: root/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols
diff options
context:
space:
mode:
authorJun Wako <wakojun@gmail.com>2015-04-24 16:26:14 +0900
committerJun Wako <wakojun@gmail.com>2015-04-24 16:26:14 +0900
commita3d96d3aa96318d339a67de1085e0ae495d57c84 (patch)
treedb85c16d03b52399d6c109eda7ea0341a0de0b1d /tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols
parent1d5bac21dc6f1425b8ef4bbe7935330c37c3a93e (diff)
parent1fe4406f374291ab2e86e95a97341fd9c475fcb8 (diff)
Merge commit '1fe4406f374291ab2e86e95a97341fd9c475fcb8'
Diffstat (limited to 'tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols')
-rw-r--r--tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/HTTPClient.cpp621
-rw-r--r--tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/HTTPClient.h138
-rw-r--r--tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/IHTTPData.h86
-rw-r--r--tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/data/HTTPMap.cpp196
-rw-r--r--tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/data/HTTPMap.h69
-rw-r--r--tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/data/HTTPText.cpp94
-rw-r--r--tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/data/HTTPText.h68
-rw-r--r--tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/main.cpp67
-rw-r--r--tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/NTPClient_HelloWorld/NTPClient/NTPClient.cpp163
-rw-r--r--tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/NTPClient_HelloWorld/NTPClient/NTPClient.h101
-rw-r--r--tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/NTPClient_HelloWorld/main.cpp39
11 files changed, 1642 insertions, 0 deletions
diff --git a/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/HTTPClient.cpp b/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/HTTPClient.cpp
new file mode 100644
index 0000000000..263c928949
--- /dev/null
+++ b/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/HTTPClient.cpp
@@ -0,0 +1,621 @@
+/* HTTPClient.cpp */
+/* Copyright (C) 2012 mbed.org, MIT License
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy of this software
+ * and associated documentation files (the "Software"), to deal in the Software without restriction,
+ * including without limitation the rights to use, copy, modify, merge, publish, distribute,
+ * sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all copies or
+ * substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+ * BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
+ * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ */
+
+//Debug is disabled by default
+#if 1
+//Enable debug
+#include <cstdio>
+//#define DBG(x, ...) std::printf("[HTTPClient : DBG]"x"\r\n", ##__VA_ARGS__);
+#define DBG(x, ...)
+#define WARN(x, ...) std::printf("[HTTPClient : WARN]"x"\r\n", ##__VA_ARGS__);
+#define ERR(x, ...) std::printf("[HTTPClient : ERR]"x"\r\n", ##__VA_ARGS__);
+
+#else
+//Disable debug
+#define DBG(x, ...)
+#define WARN(x, ...)
+#define ERR(x, ...)
+
+#endif
+
+#define HTTP_PORT 80
+
+#define OK 0
+
+#define MIN(x,y) (((x)<(y))?(x):(y))
+#define MAX(x,y) (((x)>(y))?(x):(y))
+
+#define CHUNK_SIZE 256
+
+#include <cstring>
+
+#include "HTTPClient.h"
+
+HTTPClient::HTTPClient() :
+m_sock(), m_basicAuthUser(NULL), m_basicAuthPassword(NULL), m_httpResponseCode(0)
+{
+
+}
+
+HTTPClient::~HTTPClient()
+{
+
+}
+
+#if 0
+void HTTPClient::basicAuth(const char* user, const char* password) //Basic Authentification
+{
+ m_basicAuthUser = user;
+ m_basicAuthPassword = password;
+}
+#endif
+
+HTTPResult HTTPClient::get(const char* url, IHTTPDataIn* pDataIn, int timeout /*= HTTP_CLIENT_DEFAULT_TIMEOUT*/) //Blocking
+{
+ return connect(url, HTTP_GET, NULL, pDataIn, timeout);
+}
+
+HTTPResult HTTPClient::get(const char* url, char* result, size_t maxResultLen, int timeout /*= HTTP_CLIENT_DEFAULT_TIMEOUT*/) //Blocking
+{
+ HTTPText str(result, maxResultLen);
+ return get(url, &str, timeout);
+}
+
+HTTPResult HTTPClient::post(const char* url, const IHTTPDataOut& dataOut, IHTTPDataIn* pDataIn, int timeout /*= HTTP_CLIENT_DEFAULT_TIMEOUT*/) //Blocking
+{
+ return connect(url, HTTP_POST, (IHTTPDataOut*)&dataOut, pDataIn, timeout);
+}
+
+int HTTPClient::getHTTPResponseCode()
+{
+ return m_httpResponseCode;
+}
+
+#define CHECK_CONN_ERR(ret) \
+ do{ \
+ if(ret) { \
+ m_sock.close(); \
+ ERR("Connection error (%d)", ret); \
+ return HTTP_CONN; \
+ } \
+ } while(0)
+
+#define PRTCL_ERR() \
+ do{ \
+ m_sock.close(); \
+ ERR("Protocol error"); \
+ return HTTP_PRTCL; \
+ } while(0)
+
+HTTPResult HTTPClient::connect(const char* url, HTTP_METH method, IHTTPDataOut* pDataOut, IHTTPDataIn* pDataIn, int timeout) //Execute request
+{
+ m_httpResponseCode = 0; //Invalidate code
+ m_timeout = timeout;
+
+ char scheme[8];
+ uint16_t port;
+ char host[32];
+ char path[64];
+ //First we need to parse the url (http[s]://host[:port][/[path]]) -- HTTPS not supported (yet?)
+ HTTPResult res = parseURL(url, scheme, sizeof(scheme), host, sizeof(host), &port, path, sizeof(path));
+ if(res != HTTP_OK)
+ {
+ ERR("parseURL returned %d", res);
+ return res;
+ }
+
+ if(port == 0) //TODO do handle HTTPS->443
+ {
+ port = 80;
+ }
+
+ DBG("Scheme: %s", scheme);
+ DBG("Host: %s", host);
+ DBG("Port: %d", port);
+ DBG("Path: %s", path);
+
+ //Connect
+ DBG("Connecting socket to server");
+ int ret = m_sock.connect(host, port);
+ if (ret < 0)
+ {
+ m_sock.close();
+ ERR("Could not connect");
+ return HTTP_CONN;
+ }
+
+ //Send request
+ DBG("Sending request");
+ char buf[CHUNK_SIZE];
+ const char* meth = (method==HTTP_GET)?"GET":(method==HTTP_POST)?"POST":"";
+ snprintf(buf, sizeof(buf), "%s %s HTTP/1.1\r\nHost: %s\r\n", meth, path, host); //Write request
+ ret = send(buf);
+ if(ret)
+ {
+ m_sock.close();
+ ERR("Could not write request");
+ return HTTP_CONN;
+ }
+
+ //Send all headers
+
+ //Send default headers
+ DBG("Sending headers");
+ if( (method == HTTP_POST) && (pDataOut != NULL) )
+ {
+ if( pDataOut->getIsChunked() )
+ {
+ ret = send("Transfer-Encoding: chunked\r\n");
+ CHECK_CONN_ERR(ret);
+ }
+ else
+ {
+ snprintf(buf, sizeof(buf), "Content-Length: %d\r\n", pDataOut->getDataLen());
+ ret = send(buf);
+ CHECK_CONN_ERR(ret);
+ }
+ char type[48];
+ if( pDataOut->getDataType(type, 48) == HTTP_OK )
+ {
+ snprintf(buf, sizeof(buf), "Content-Type: %s\r\n", type);
+ ret = send(buf);
+ CHECK_CONN_ERR(ret);
+ }
+ }
+
+ //Close headers
+ DBG("Headers sent");
+ ret = send("\r\n");
+ CHECK_CONN_ERR(ret);
+
+ size_t trfLen;
+
+ //Send data (if POST)
+ if( (method == HTTP_POST) && (pDataOut != NULL) )
+ {
+ DBG("Sending data");
+ while(true)
+ {
+ size_t writtenLen = 0;
+ pDataOut->read(buf, CHUNK_SIZE, &trfLen);
+ if( pDataOut->getIsChunked() )
+ {
+ //Write chunk header
+ char chunkHeader[16];
+ snprintf(chunkHeader, sizeof(chunkHeader), "%X\r\n", trfLen); //In hex encoding
+ ret = send(chunkHeader);
+ CHECK_CONN_ERR(ret);
+ }
+ else if( trfLen == 0 )
+ {
+ break;
+ }
+ if( trfLen != 0 )
+ {
+ ret = send(buf, trfLen);
+ CHECK_CONN_ERR(ret);
+ }
+
+ if( pDataOut->getIsChunked() )
+ {
+ ret = send("\r\n"); //Chunk-terminating CRLF
+ CHECK_CONN_ERR(ret);
+ }
+ else
+ {
+ writtenLen += trfLen;
+ if( writtenLen >= pDataOut->getDataLen() )
+ {
+ break;
+ }
+ }
+
+ if( trfLen == 0 )
+ {
+ break;
+ }
+ }
+
+ }
+
+ //Receive response
+ DBG("Receiving response");
+ ret = recv(buf, CHUNK_SIZE - 1, CHUNK_SIZE - 1, &trfLen); //Read n bytes
+ CHECK_CONN_ERR(ret);
+
+ buf[trfLen] = '\0';
+
+ char* crlfPtr = strstr(buf, "\r\n");
+ if(crlfPtr == NULL)
+ {
+ PRTCL_ERR();
+ }
+
+ int crlfPos = crlfPtr - buf;
+ buf[crlfPos] = '\0';
+
+ //Parse HTTP response
+ if( sscanf(buf, "HTTP/%*d.%*d %d %*[^\r\n]", &m_httpResponseCode) != 1 )
+ {
+ //Cannot match string, error
+ ERR("Not a correct HTTP answer : %s\n", buf);
+ PRTCL_ERR();
+ }
+
+ if(m_httpResponseCode != 200)
+ {
+ //Cannot match string, error
+ WARN("Response code %d", m_httpResponseCode);
+ PRTCL_ERR();
+ }
+
+ DBG("Reading headers");
+
+ memmove(buf, &buf[crlfPos+2], trfLen - (crlfPos + 2) + 1); //Be sure to move NULL-terminating char as well
+ trfLen -= (crlfPos + 2);
+
+ size_t recvContentLength = 0;
+ bool recvChunked = false;
+ //Now get headers
+ while( true )
+ {
+ crlfPtr = strstr(buf, "\r\n");
+ if(crlfPtr == NULL)
+ {
+ if( trfLen < CHUNK_SIZE - 1 )
+ {
+ size_t newTrfLen;
+ ret = recv(buf + trfLen, 1, CHUNK_SIZE - trfLen - 1, &newTrfLen);
+ trfLen += newTrfLen;
+ buf[trfLen] = '\0';
+ DBG("Read %d chars; In buf: [%s]", newTrfLen, buf);
+ CHECK_CONN_ERR(ret);
+ continue;
+ }
+ else
+ {
+ PRTCL_ERR();
+ }
+ }
+
+ crlfPos = crlfPtr - buf;
+
+ if(crlfPos == 0) //End of headers
+ {
+ DBG("Headers read");
+ memmove(buf, &buf[2], trfLen - 2 + 1); //Be sure to move NULL-terminating char as well
+ trfLen -= 2;
+ break;
+ }
+
+ buf[crlfPos] = '\0';
+
+ char key[64] = {0};
+ char value[32] = {0};
+
+ int n = sscanf(buf, "%63[^:]: %31[^\r\n]", key, value);
+
+ if ( n == 2 )
+ {
+ DBG("Read header : %s: %s\n", key, value);
+ if( !strcmp(key, "Content-Length") )
+ {
+ sscanf(value, "%d", &recvContentLength);
+ pDataIn->setDataLen(recvContentLength);
+ }
+ else if( !strcmp(key, "Transfer-Encoding") )
+ {
+ if( !strcmp(value, "Chunked") || !strcmp(value, "chunked") )
+ {
+ recvChunked = true;
+ pDataIn->setIsChunked(true);
+ }
+ }
+ else if( !strcmp(key, "Content-Type") )
+ {
+ pDataIn->setDataType(value);
+ }
+
+ memmove(buf, &buf[crlfPos+2], trfLen - (crlfPos + 2) + 1); //Be sure to move NULL-terminating char as well
+ trfLen -= (crlfPos + 2);
+
+ }
+ else
+ {
+ ERR("Could not parse header");
+ PRTCL_ERR();
+ }
+
+ }
+
+ //Receive data
+ DBG("Receiving data");
+ while(true)
+ {
+ size_t readLen = 0;
+
+ if( recvChunked )
+ {
+ //Read chunk header
+ crlfPos=0;
+ for(crlfPos++; crlfPos < trfLen - 2; crlfPos++)
+ {
+ if( buf[crlfPos] == '\r' && buf[crlfPos + 1] == '\n' )
+ {
+ break;
+ }
+ }
+ if(crlfPos >= trfLen - 2) //Try to read more
+ {
+ if( trfLen < CHUNK_SIZE )
+ {
+ size_t newTrfLen;
+ ret = recv(buf + trfLen, 0, CHUNK_SIZE - trfLen - 1, &newTrfLen);
+ trfLen += newTrfLen;
+ CHECK_CONN_ERR(ret);
+ continue;
+ }
+ else
+ {
+ PRTCL_ERR();
+ }
+ }
+ buf[crlfPos] = '\0';
+ int n = sscanf(buf, "%x", &readLen);
+ if(n!=1)
+ {
+ ERR("Could not read chunk length");
+ PRTCL_ERR();
+ }
+
+ memmove(buf, &buf[crlfPos+2], trfLen - (crlfPos + 2)); //Not need to move NULL-terminating char any more
+ trfLen -= (crlfPos + 2);
+
+ if( readLen == 0 )
+ {
+ //Last chunk
+ break;
+ }
+ }
+ else
+ {
+ readLen = recvContentLength;
+ }
+
+ DBG("Retrieving %d bytes", readLen);
+
+ do
+ {
+ pDataIn->write(buf, MIN(trfLen, readLen));
+ if( trfLen > readLen )
+ {
+ memmove(buf, &buf[readLen], trfLen - readLen);
+ trfLen -= readLen;
+ readLen = 0;
+ }
+ else
+ {
+ readLen -= trfLen;
+ }
+
+ if(readLen)
+ {
+ ret = recv(buf, 1, CHUNK_SIZE - trfLen - 1, &trfLen);
+ CHECK_CONN_ERR(ret);
+ }
+ } while(readLen);
+
+ if( recvChunked )
+ {
+ if(trfLen < 2)
+ {
+ size_t newTrfLen;
+ //Read missing chars to find end of chunk
+ ret = recv(buf, 2 - trfLen, CHUNK_SIZE, &newTrfLen);
+ CHECK_CONN_ERR(ret);
+ trfLen += newTrfLen;
+ }
+ if( (buf[0] != '\r') || (buf[1] != '\n') )
+ {
+ ERR("Format error");
+ PRTCL_ERR();
+ }
+ memmove(buf, &buf[2], trfLen - 2);
+ trfLen -= 2;
+ }
+ else
+ {
+ break;
+ }
+
+ }
+
+ m_sock.close();
+ DBG("Completed HTTP transaction");
+
+ return HTTP_OK;
+}
+
+HTTPResult HTTPClient::recv(char* buf, size_t minLen, size_t maxLen, size_t* pReadLen) //0 on success, err code on failure
+{
+ DBG("Trying to read between %d and %d bytes", minLen, maxLen);
+ size_t readLen = 0;
+
+ if(!m_sock.is_connected())
+ {
+ WARN("Connection was closed by server");
+ return HTTP_CLOSED; //Connection was closed by server
+ }
+
+ int ret;
+ while(readLen < maxLen)
+ {
+ if(readLen < minLen)
+ {
+ DBG("Trying to read at most %d bytes [Blocking]", minLen - readLen);
+ m_sock.set_blocking(false, m_timeout);
+ ret = m_sock.receive_all(buf + readLen, minLen - readLen);
+ }
+ else
+ {
+ DBG("Trying to read at most %d bytes [Not blocking]", maxLen - readLen);
+ m_sock.set_blocking(false, 0);
+ ret = m_sock.receive(buf + readLen, maxLen - readLen);
+ }
+
+ if( ret > 0)
+ {
+ readLen += ret;
+ }
+ else if( ret == 0 )
+ {
+ break;
+ }
+ else
+ {
+ if(!m_sock.is_connected())
+ {
+ ERR("Connection error (recv returned %d)", ret);
+ *pReadLen = readLen;
+ return HTTP_CONN;
+ }
+ else
+ {
+ break;
+ }
+ }
+
+ if(!m_sock.is_connected())
+ {
+ break;
+ }
+ }
+ DBG("Read %d bytes", readLen);
+ *pReadLen = readLen;
+ return HTTP_OK;
+}
+
+HTTPResult HTTPClient::send(char* buf, size_t len) //0 on success, err code on failure
+{
+ if(len == 0)
+ {
+ len = strlen(buf);
+ }
+ DBG("Trying to write %d bytes", len);
+ size_t writtenLen = 0;
+
+ if(!m_sock.is_connected())
+ {
+ WARN("Connection was closed by server");
+ return HTTP_CLOSED; //Connection was closed by server
+ }
+
+ m_sock.set_blocking(false, m_timeout);
+ int ret = m_sock.send_all(buf, len);
+ if(ret > 0)
+ {
+ writtenLen += ret;
+ }
+ else if( ret == 0 )
+ {
+ WARN("Connection was closed by server");
+ return HTTP_CLOSED; //Connection was closed by server
+ }
+ else
+ {
+ ERR("Connection error (send returned %d)", ret);
+ return HTTP_CONN;
+ }
+
+ DBG("Written %d bytes", writtenLen);
+ return HTTP_OK;
+}
+
+HTTPResult HTTPClient::parseURL(const char* url, char* scheme, size_t maxSchemeLen, char* host, size_t maxHostLen, uint16_t* port, char* path, size_t maxPathLen) //Parse URL
+{
+ char* schemePtr = (char*) url;
+ char* hostPtr = (char*) strstr(url, "://");
+ if(hostPtr == NULL)
+ {
+ WARN("Could not find host");
+ return HTTP_PARSE; //URL is invalid
+ }
+
+ if( maxSchemeLen < hostPtr - schemePtr + 1 ) //including NULL-terminating char
+ {
+ WARN("Scheme str is too small (%d >= %d)", maxSchemeLen, hostPtr - schemePtr + 1);
+ return HTTP_PARSE;
+ }
+ memcpy(scheme, schemePtr, hostPtr - schemePtr);
+ scheme[hostPtr - schemePtr] = '\0';
+
+ hostPtr+=3;
+
+ size_t hostLen = 0;
+
+ char* portPtr = strchr(hostPtr, ':');
+ if( portPtr != NULL )
+ {
+ hostLen = portPtr - hostPtr;
+ portPtr++;
+ if( sscanf(portPtr, "%hu", port) != 1)
+ {
+ WARN("Could not find port");
+ return HTTP_PARSE;
+ }
+ }
+ else
+ {
+ *port=0;
+ }
+ char* pathPtr = strchr(hostPtr, '/');
+ if( hostLen == 0 )
+ {
+ hostLen = pathPtr - hostPtr;
+ }
+
+ if( maxHostLen < hostLen + 1 ) //including NULL-terminating char
+ {
+ WARN("Host str is too small (%d >= %d)", maxHostLen, hostLen + 1);
+ return HTTP_PARSE;
+ }
+ memcpy(host, hostPtr, hostLen);
+ host[hostLen] = '\0';
+
+ size_t pathLen;
+ char* fragmentPtr = strchr(hostPtr, '#');
+ if(fragmentPtr != NULL)
+ {
+ pathLen = fragmentPtr - pathPtr;
+ }
+ else
+ {
+ pathLen = strlen(pathPtr);
+ }
+
+ if( maxPathLen < pathLen + 1 ) //including NULL-terminating char
+ {
+ WARN("Path str is too small (%d >= %d)", maxPathLen, pathLen + 1);
+ return HTTP_PARSE;
+ }
+ memcpy(path, pathPtr, pathLen);
+ path[pathLen] = '\0';
+
+ return HTTP_OK;
+}
diff --git a/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/HTTPClient.h b/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/HTTPClient.h
new file mode 100644
index 0000000000..e9ac860cab
--- /dev/null
+++ b/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/HTTPClient.h
@@ -0,0 +1,138 @@
+/* HTTPClient.h */
+/* Copyright (C) 2012 mbed.org, MIT License
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy of this software
+ * and associated documentation files (the "Software"), to deal in the Software without restriction,
+ * including without limitation the rights to use, copy, modify, merge, publish, distribute,
+ * sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all copies or
+ * substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+ * BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
+ * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ */
+
+/** \file
+HTTP Client header file
+*/
+
+#ifndef HTTP_CLIENT_H
+#define HTTP_CLIENT_H
+
+#include "TCPSocketConnection.h"
+
+#define HTTP_CLIENT_DEFAULT_TIMEOUT 15000
+
+class HTTPData;
+
+#include "IHTTPData.h"
+#include "mbed.h"
+
+///HTTP client results
+enum HTTPResult
+{
+ HTTP_PROCESSING, ///<Processing
+ HTTP_PARSE, ///<url Parse error
+ HTTP_DNS, ///<Could not resolve name
+ HTTP_PRTCL, ///<Protocol error
+ HTTP_NOTFOUND, ///<HTTP 404 Error
+ HTTP_REFUSED, ///<HTTP 403 Error
+ HTTP_ERROR, ///<HTTP xxx error
+ HTTP_TIMEOUT, ///<Connection timeout
+ HTTP_CONN, ///<Connection error
+ HTTP_CLOSED, ///<Connection was closed by remote host
+ HTTP_OK = 0, ///<Success
+};
+
+/**A simple HTTP Client
+The HTTPClient is composed of:
+- The actual client (HTTPClient)
+- Classes that act as a data repository, each of which deriving from the HTTPData class (HTTPText for short text content, HTTPFile for file I/O, HTTPMap for key/value pairs, and HTTPStream for streaming purposes)
+*/
+class HTTPClient
+{
+public:
+ ///Instantiate the HTTP client
+ HTTPClient();
+ ~HTTPClient();
+
+#if 0 //TODO add header handlers
+ /**
+ Provides a basic authentification feature (Base64 encoded username and password)
+ Pass two NULL pointers to switch back to no authentication
+ @param user username to use for authentication, must remain valid durlng the whole HTTP session
+ @param user password to use for authentication, must remain valid durlng the whole HTTP session
+ */
+ void basicAuth(const char* user, const char* password); //Basic Authentification
+#endif
+
+ //High Level setup functions
+ /** Execute a GET request on the url
+ Blocks until completion
+ @param url : url on which to execute the request
+ @param pDataIn : pointer to an IHTTPDataIn instance that will collect the data returned by the request, can be NULL
+ @param timeout waiting timeout in ms (osWaitForever for blocking function, not recommended)
+ @return 0 on success, HTTP error (<0) on failure
+ */
+ HTTPResult get(const char* url, IHTTPDataIn* pDataIn, int timeout = HTTP_CLIENT_DEFAULT_TIMEOUT); //Blocking
+
+ /** Execute a GET request on the url
+ Blocks until completion
+ This is a helper to directly get a piece of text from a HTTP result
+ @param url : url on which to execute the request
+ @param result : pointer to a char array in which the result will be stored
+ @param maxResultLen : length of the char array (including space for the NULL-terminating char)
+ @param timeout waiting timeout in ms (osWaitForever for blocking function, not recommended)
+ @return 0 on success, HTTP error (<0) on failure
+ */
+ HTTPResult get(const char* url, char* result, size_t maxResultLen, int timeout = HTTP_CLIENT_DEFAULT_TIMEOUT); //Blocking
+
+ /** Execute a POST request on the url
+ Blocks until completion
+ @param url : url on which to execute the request
+ @param dataOut : a IHTTPDataOut instance that contains the data that will be posted
+ @param pDataIn : pointer to an IHTTPDataIn instance that will collect the data returned by the request, can be NULL
+ @param timeout waiting timeout in ms (osWaitForever for blocking function, not recommended)
+ @return 0 on success, HTTP error (<0) on failure
+ */
+ HTTPResult post(const char* url, const IHTTPDataOut& dataOut, IHTTPDataIn* pDataIn, int timeout = HTTP_CLIENT_DEFAULT_TIMEOUT); //Blocking
+
+ /** Get last request's HTTP response code
+ @return The HTTP response code of the last request
+ */
+ int getHTTPResponseCode();
+
+private:
+ enum HTTP_METH
+ {
+ HTTP_GET,
+ HTTP_POST,
+ HTTP_HEAD
+ };
+
+ HTTPResult connect(const char* url, HTTP_METH method, IHTTPDataOut* pDataOut, IHTTPDataIn* pDataIn, int timeout); //Execute request
+ HTTPResult recv(char* buf, size_t minLen, size_t maxLen, size_t* pReadLen); //0 on success, err code on failure
+ HTTPResult send(char* buf, size_t len = 0); //0 on success, err code on failure
+ HTTPResult parseURL(const char* url, char* scheme, size_t maxSchemeLen, char* host, size_t maxHostLen, uint16_t* port, char* path, size_t maxPathLen); //Parse URL
+
+ //Parameters
+ TCPSocketConnection m_sock;
+
+ int m_timeout;
+
+ const char* m_basicAuthUser;
+ const char* m_basicAuthPassword;
+ int m_httpResponseCode;
+
+};
+
+//Including data containers here for more convenience
+#include "data/HTTPText.h"
+#include "data/HTTPMap.h"
+
+#endif
diff --git a/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/IHTTPData.h b/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/IHTTPData.h
new file mode 100644
index 0000000000..2eead464f1
--- /dev/null
+++ b/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/IHTTPData.h
@@ -0,0 +1,86 @@
+/* IHTTPData.h */
+/* Copyright (C) 2012 mbed.org, MIT License
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy of this software
+ * and associated documentation files (the "Software"), to deal in the Software without restriction,
+ * including without limitation the rights to use, copy, modify, merge, publish, distribute,
+ * sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all copies or
+ * substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+ * BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
+ * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef IHTTPDATA_H
+#define IHTTPDATA_H
+
+#include <cstring>
+
+using std::size_t;
+
+///This is a simple interface for HTTP data storage (impl examples are Key/Value Pairs, File, etc...)
+class IHTTPDataOut
+{
+protected:
+ friend class HTTPClient;
+
+ /** Read a piece of data to be transmitted
+ * @param buf Pointer to the buffer on which to copy the data
+ * @param len Length of the buffer
+ * @param pReadLen Pointer to the variable on which the actual copied data length will be stored
+ */
+ virtual int read(char* buf, size_t len, size_t* pReadLen) = 0;
+
+ /** Get MIME type
+ * @param type Internet media type from Content-Type header
+ */
+ virtual int getDataType(char* type, size_t maxTypeLen) = 0; //Internet media type for Content-Type header
+
+ /** Determine whether the HTTP client should chunk the data
+ * Used for Transfer-Encoding header
+ */
+ virtual bool getIsChunked() = 0;
+
+ /** If the data is not chunked, get its size
+ * Used for Content-Length header
+ */
+ virtual size_t getDataLen() = 0;
+
+};
+
+///This is a simple interface for HTTP data storage (impl examples are Key/Value Pairs, File, etc...)
+class IHTTPDataIn
+{
+protected:
+ friend class HTTPClient;
+
+ /** Write a piece of data transmitted by the server
+ * @param buf Pointer to the buffer from which to copy the data
+ * @param len Length of the buffer
+ */
+ virtual int write(const char* buf, size_t len) = 0;
+
+ /** Set MIME type
+ * @param type Internet media type from Content-Type header
+ */
+ virtual void setDataType(const char* type) = 0;
+
+ /** Determine whether the data is chunked
+ * Recovered from Transfer-Encoding header
+ */
+ virtual void setIsChunked(bool chunked) = 0;
+
+ /** If the data is not chunked, set its size
+ * From Content-Length header
+ */
+ virtual void setDataLen(size_t len) = 0;
+
+};
+
+#endif
diff --git a/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/data/HTTPMap.cpp b/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/data/HTTPMap.cpp
new file mode 100644
index 0000000000..75ffd970e9
--- /dev/null
+++ b/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/data/HTTPMap.cpp
@@ -0,0 +1,196 @@
+/* HTTPMap.cpp */
+/* Copyright (C) 2012 mbed.org, MIT License
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy of this software
+ * and associated documentation files (the "Software"), to deal in the Software without restriction,
+ * including without limitation the rights to use, copy, modify, merge, publish, distribute,
+ * sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all copies or
+ * substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+ * BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
+ * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ */
+
+#include "HTTPMap.h"
+
+#include <cstring>
+
+#include <cctype>
+
+#define OK 0
+
+using std::strncpy;
+
+HTTPMap::HTTPMap() : m_pos(0), m_count(0)
+{
+
+}
+
+void HTTPMap::put(const char* key, const char* value)
+{
+ if(m_count >= HTTPMAP_TABLE_SIZE)
+ {
+ return;
+ }
+ m_keys[m_count] = key;
+ m_values[m_count] = value;
+ m_count++;
+}
+
+void HTTPMap::clear()
+{
+ m_count = 0;
+ m_pos = 0;
+}
+
+
+/*virtual*/ int HTTPMap::read(char* buf, size_t len, size_t* pReadLen)
+{
+ if(m_pos >= m_count)
+ {
+ *pReadLen = 0;
+ m_pos = 0;
+ return OK;
+ }
+
+ //URL encode
+ char* out = buf;
+ const char* in = m_keys[m_pos];
+ if( (m_pos != 0) && (out - buf < len - 1) )
+ {
+ *out='&';
+ out++;
+ }
+
+ while( (*in != '\0') && (out - buf < len - 3) )
+ {
+ if (std::isalnum(*in) || *in == '-' || *in == '_' || *in == '.' || *in == '~')
+ {
+ *out = *in;
+ out++;
+ }
+ else if( *in == ' ' )
+ {
+ *out='+';
+ out++;
+ }
+ else
+ {
+ char hex[] = "0123456789abcdef";
+ *out='%';
+ out++;
+ *out=hex[(*in>>4)&0xf];
+ out++;
+ *out=hex[(*in)&0xf];
+ out++;
+ }
+ in++;
+ }
+
+ if( out - buf < len - 1 )
+ {
+ *out='=';
+ out++;
+ }
+
+ in = m_values[m_pos];
+ while( (*in != '\0') && (out - buf < len - 3) )
+ {
+ if (std::isalnum(*in) || *in == '-' || *in == '_' || *in == '.' || *in == '~')
+ {
+ *out = *in;
+ out++;
+ }
+ else if( *in == ' ' )
+ {
+ *out='+';
+ out++;
+ }
+ else
+ {
+ char hex[] = "0123456789abcdef";
+ *out='%';
+ out++;
+ *out=hex[(*in>>4)&0xf];
+ out++;
+ *out=hex[(*in)&0xf];
+ out++;
+ }
+ in++;
+ }
+
+ *pReadLen = out - buf;
+
+ m_pos++;
+ return OK;
+}
+
+/*virtual*/ int HTTPMap::getDataType(char* type, size_t maxTypeLen) //Internet media type for Content-Type header
+{
+ strncpy(type, "application/x-www-form-urlencoded", maxTypeLen-1);
+ type[maxTypeLen-1] = '\0';
+ return OK;
+}
+
+/*virtual*/ bool HTTPMap::getIsChunked() //For Transfer-Encoding header
+{
+ return false; ////Data is computed one key/value pair at a time
+}
+
+/*virtual*/ size_t HTTPMap::getDataLen() //For Content-Length header
+{
+ size_t count = 0;
+ for(size_t i = 0; i< m_count; i++)
+ {
+ //URL encode
+ const char* in = m_keys[i];
+ if( i != 0 )
+ {
+ count++;
+ }
+
+ while( (*in != '\0') )
+ {
+ if (std::isalnum(*in) || *in == '-' || *in == '_' || *in == '.' || *in == '~')
+ {
+ count++;
+ }
+ else if( *in == ' ' )
+ {
+ count++;
+ }
+ else
+ {
+ count+=3;
+ }
+ in++;
+ }
+
+ count ++;
+
+ in = m_values[i];
+ while( (*in != '\0') )
+ {
+ if (std::isalnum(*in) || *in == '-' || *in == '_' || *in == '.' || *in == '~')
+ {
+ count++;
+ }
+ else if( *in == ' ' )
+ {
+ count++;
+ }
+ else
+ {
+ count+=3;
+ }
+ in++;
+ }
+ }
+ return count;
+}
diff --git a/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/data/HTTPMap.h b/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/data/HTTPMap.h
new file mode 100644
index 0000000000..ad02211e9a
--- /dev/null
+++ b/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/data/HTTPMap.h
@@ -0,0 +1,69 @@
+/* HTTPMap.h */
+/* Copyright (C) 2012 mbed.org, MIT License
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy of this software
+ * and associated documentation files (the "Software"), to deal in the Software without restriction,
+ * including without limitation the rights to use, copy, modify, merge, publish, distribute,
+ * sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all copies or
+ * substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+ * BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
+ * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ */
+
+
+#ifndef HTTPMAP_H_
+#define HTTPMAP_H_
+
+#include "../IHTTPData.h"
+
+#define HTTPMAP_TABLE_SIZE 32
+
+/** Map of key/value pairs
+ * Used to transmit POST data using the application/x-www-form-urlencoded encoding
+ */
+class HTTPMap: public IHTTPDataOut
+{
+public:
+ /**
+ Instantiates HTTPMap
+ It supports at most 32 key/values pairs
+ */
+ HTTPMap();
+
+ /** Put Key/Value pair
+ The references to the parameters must remain valid as long as the clear() function is not called
+ @param key The key to use
+ @param value The corresponding value
+ */
+ void put(const char* key, const char* value);
+
+ /** Clear table
+ */
+ void clear();
+
+protected:
+ //IHTTPDataIn
+ virtual int read(char* buf, size_t len, size_t* pReadLen);
+
+ virtual int getDataType(char* type, size_t maxTypeLen); //Internet media type for Content-Type header
+
+ virtual bool getIsChunked(); //For Transfer-Encoding header
+
+ virtual size_t getDataLen(); //For Content-Length header
+
+private:
+ const char* m_keys[HTTPMAP_TABLE_SIZE];
+ const char* m_values[HTTPMAP_TABLE_SIZE];
+
+ size_t m_pos;
+ size_t m_count;
+};
+
+#endif /* HTTPMAP_H_ */
diff --git a/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/data/HTTPText.cpp b/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/data/HTTPText.cpp
new file mode 100644
index 0000000000..800532b0e2
--- /dev/null
+++ b/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/data/HTTPText.cpp
@@ -0,0 +1,94 @@
+/* HTTPText.cpp */
+/* Copyright (C) 2012 mbed.org, MIT License
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy of this software
+ * and associated documentation files (the "Software"), to deal in the Software without restriction,
+ * including without limitation the rights to use, copy, modify, merge, publish, distribute,
+ * sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all copies or
+ * substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+ * BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
+ * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ */
+
+#include "HTTPText.h"
+
+#include <cstring>
+
+#define OK 0
+
+using std::memcpy;
+using std::strncpy;
+using std::strlen;
+
+#define MIN(x,y) (((x)<(y))?(x):(y))
+
+HTTPText::HTTPText(char* str) : m_str(str), m_pos(0)
+{
+ m_size = strlen(str) + 1;
+}
+
+HTTPText::HTTPText(char* str, size_t size) : m_str(str), m_size(size), m_pos(0)
+{
+
+}
+
+//IHTTPDataIn
+/*virtual*/ int HTTPText::read(char* buf, size_t len, size_t* pReadLen)
+{
+ *pReadLen = MIN(len, m_size - 1 - m_pos);
+ memcpy(buf, m_str + m_pos, *pReadLen);
+ m_pos += *pReadLen;
+ return OK;
+}
+
+/*virtual*/ int HTTPText::getDataType(char* type, size_t maxTypeLen) //Internet media type for Content-Type header
+{
+ strncpy(type, "text/plain", maxTypeLen-1);
+ type[maxTypeLen-1] = '\0';
+ return OK;
+}
+
+/*virtual*/ bool HTTPText::getIsChunked() //For Transfer-Encoding header
+{
+ return false;
+}
+
+/*virtual*/ size_t HTTPText::getDataLen() //For Content-Length header
+{
+ return m_size - 1;
+}
+
+//IHTTPDataOut
+/*virtual*/ int HTTPText::write(const char* buf, size_t len)
+{
+ size_t writeLen = MIN(len, m_size - 1 - m_pos);
+ memcpy(m_str + m_pos, buf, writeLen);
+ m_pos += writeLen;
+ m_str[m_pos] = '\0';
+ return OK;
+}
+
+/*virtual*/ void HTTPText::setDataType(const char* type) //Internet media type from Content-Type header
+{
+
+}
+
+/*virtual*/ void HTTPText::setIsChunked(bool chunked) //From Transfer-Encoding header
+{
+
+}
+
+/*virtual*/ void HTTPText::setDataLen(size_t len) //From Content-Length header, or if the transfer is chunked, next chunk length
+{
+
+}
+
+
+
diff --git a/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/data/HTTPText.h b/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/data/HTTPText.h
new file mode 100644
index 0000000000..224a957878
--- /dev/null
+++ b/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/HTTPClient/data/HTTPText.h
@@ -0,0 +1,68 @@
+/* HTTPText.h */
+/* Copyright (C) 2012 mbed.org, MIT License
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy of this software
+ * and associated documentation files (the "Software"), to deal in the Software without restriction,
+ * including without limitation the rights to use, copy, modify, merge, publish, distribute,
+ * sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all copies or
+ * substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+ * BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
+ * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ */
+
+
+#ifndef HTTPTEXT_H_
+#define HTTPTEXT_H_
+
+#include "../IHTTPData.h"
+
+/** A data endpoint to store text
+*/
+class HTTPText : public IHTTPDataIn, public IHTTPDataOut
+{
+public:
+ /** Create an HTTPText instance for output
+ * @param str String to be transmitted
+ */
+ HTTPText(char* str);
+
+ /** Create an HTTPText instance for input
+ * @param str Buffer to store the incoming string
+ * @param size Size of the buffer
+ */
+ HTTPText(char* str, size_t size);
+
+protected:
+ //IHTTPDataIn
+ virtual int read(char* buf, size_t len, size_t* pReadLen);
+
+ virtual int getDataType(char* type, size_t maxTypeLen); //Internet media type for Content-Type header
+
+ virtual bool getIsChunked(); //For Transfer-Encoding header
+
+ virtual size_t getDataLen(); //For Content-Length header
+
+ //IHTTPDataOut
+ virtual int write(const char* buf, size_t len);
+
+ virtual void setDataType(const char* type); //Internet media type from Content-Type header
+
+ virtual void setIsChunked(bool chunked); //From Transfer-Encoding header
+
+ virtual void setDataLen(size_t len); //From Content-Length header, or if the transfer is chunked, next chunk length
+
+private:
+ char* m_str;
+ size_t m_size;
+
+ size_t m_pos;
+};
+
+#endif /* HTTPTEXT_H_ */
diff --git a/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/main.cpp b/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/main.cpp
new file mode 100644
index 0000000000..5ab616ea95
--- /dev/null
+++ b/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/HTTPClient_HelloWorld/main.cpp
@@ -0,0 +1,67 @@
+#include "mbed.h"
+#include "test_env.h"
+#include "EthernetInterface.h"
+#include "HTTPClient.h"
+
+
+namespace {
+ const int BUFFER_SIZE = 512;
+}
+
+int main() {
+ MBED_HOSTTEST_TIMEOUT(15);
+ MBED_HOSTTEST_SELECT(default_auto);
+ MBED_HOSTTEST_DESCRIPTION(HTTP client hello world);
+ MBED_HOSTTEST_START("NET_7");
+
+ char http_request_buffer[BUFFER_SIZE + 1] = {0};
+ HTTPClient http;
+ EthernetInterface eth;
+ eth.init(); //Use DHCP
+ eth.connect();
+
+ //GET data
+ {
+ bool result = true;
+ const char *url_hello_txt = "http://developer.mbed.org/media/uploads/donatien/hello.txt";
+ printf("HTTP_GET: Trying to fetch page '%s'...\r\n", url_hello_txt);
+ HTTPResult ret = http.get(url_hello_txt, http_request_buffer, BUFFER_SIZE);
+ if (ret == HTTP_OK) {
+ printf("HTTP_GET: Read %d chars: '%s' ... [OK]\r\n", strlen(http_request_buffer), http_request_buffer);
+ } else {
+ printf("HTTP_GET: Error(%d). HTTP error(%d) ... [FAIL]\r\n", ret, http.getHTTPResponseCode());
+ result = false;
+ }
+
+ if (result == false) {
+ eth.disconnect();
+ MBED_HOSTTEST_RESULT(false);
+ }
+ }
+
+ //POST data
+ {
+ bool result = true;
+ const char *url_httpbin_post = "http://httpbin.org/post";
+ HTTPText text(http_request_buffer, BUFFER_SIZE);
+ HTTPMap map;
+ map.put("Hello", "World");
+ map.put("test", "1234");
+ printf("HTTP_POST: Trying to post data to '%s' ...\r\n", url_httpbin_post);
+ HTTPResult ret = http.post(url_httpbin_post, map, &text);
+ if (ret == HTTP_OK) {
+ printf("HTTP_POST: Read %d chars ... [OK]\r\n", strlen(http_request_buffer));
+ printf("HTTP_POST: %s\r\n", http_request_buffer);
+ } else {
+ printf("HTTP_GET: Error(%d). HTTP error(%d) ... [FAIL]\r\n", ret, http.getHTTPResponseCode());
+ result = false;
+ }
+
+ if (result == false) {
+ eth.disconnect();
+ MBED_HOSTTEST_RESULT(false);
+ }
+ }
+ eth.disconnect();
+ MBED_HOSTTEST_RESULT(true);
+}
diff --git a/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/NTPClient_HelloWorld/NTPClient/NTPClient.cpp b/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/NTPClient_HelloWorld/NTPClient/NTPClient.cpp
new file mode 100644
index 0000000000..b049d30036
--- /dev/null
+++ b/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/NTPClient_HelloWorld/NTPClient/NTPClient.cpp
@@ -0,0 +1,163 @@
+/* NTPClient.cpp */
+/* Copyright (C) 2012 mbed.org, MIT License
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy of this software
+ * and associated documentation files (the "Software"), to deal in the Software without restriction,
+ * including without limitation the rights to use, copy, modify, merge, publish, distribute,
+ * sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all copies or
+ * substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+ * BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
+ * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ */
+
+//Debug is disabled by default
+#if 0
+//Enable debug
+#define __DEBUG__
+#include <cstdio>
+#define DBG(x, ...) std::printf("[NTPClient : DBG]"x"\r\n", ##__VA_ARGS__);
+#define WARN(x, ...) std::printf("[NTPClient : WARN]"x"\r\n", ##__VA_ARGS__);
+#define ERR(x, ...) std::printf("[NTPClient : ERR]"x"\r\n", ##__VA_ARGS__);
+
+#else
+//Disable debug
+#define DBG(x, ...)
+#define WARN(x, ...)
+#define ERR(x, ...)
+
+#endif
+
+#include "NTPClient.h"
+
+#include "UDPSocket.h"
+
+#include "mbed.h" //time() and set_time()
+
+#define NTP_PORT 123
+#define NTP_CLIENT_PORT 0 //Random port
+#define NTP_TIMESTAMP_DELTA 2208988800ull //Diff btw a UNIX timestamp (Starting Jan, 1st 1970) and a NTP timestamp (Starting Jan, 1st 1900)
+
+NTPClient::NTPClient() : m_sock()
+{
+
+
+}
+
+NTPResult NTPClient::setTime(const char* host, uint16_t port, uint32_t timeout)
+{
+#ifdef __DEBUG__
+ time_t ctTime;
+ ctTime = time(NULL);
+ DBG("Time is set to (UTC): %s", ctime(&ctTime));
+#endif
+
+ //Create & bind socket
+ DBG("Binding socket");
+ m_sock.bind(0); //Bind to a random port
+
+ m_sock.set_blocking(false, timeout); //Set not blocking
+
+ struct NTPPacket pkt;
+
+ //Now ping the server and wait for response
+ DBG("Ping");
+ //Prepare NTP Packet:
+ pkt.li = 0; //Leap Indicator : No warning
+ pkt.vn = 4; //Version Number : 4
+ pkt.mode = 3; //Client mode
+ pkt.stratum = 0; //Not relevant here
+ pkt.poll = 0; //Not significant as well
+ pkt.precision = 0; //Neither this one is
+
+ pkt.rootDelay = 0; //Or this one
+ pkt.rootDispersion = 0; //Or that one
+ pkt.refId = 0; //...
+
+ pkt.refTm_s = 0;
+ pkt.origTm_s = 0;
+ pkt.rxTm_s = 0;
+ pkt.txTm_s = htonl( NTP_TIMESTAMP_DELTA + time(NULL) ); //WARN: We are in LE format, network byte order is BE
+
+ pkt.refTm_f = pkt.origTm_f = pkt.rxTm_f = pkt.txTm_f = 0;
+
+ Endpoint outEndpoint;
+
+ if( outEndpoint.set_address(host, port) < 0)
+ {
+ m_sock.close();
+ return NTP_DNS;
+ }
+
+ //Set timeout, non-blocking and wait using select
+ int ret = m_sock.sendTo( outEndpoint, (char*)&pkt, sizeof(NTPPacket) );
+ if (ret < 0 )
+ {
+ ERR("Could not send packet");
+ m_sock.close();
+ return NTP_CONN;
+ }
+
+ //Read response
+ Endpoint inEndpoint;
+
+ DBG("Pong");
+ do
+ {
+ ret = m_sock.receiveFrom( inEndpoint, (char*)&pkt, sizeof(NTPPacket) ); //FIXME need a DNS Resolver to actually compare the incoming address with the DNS name
+ if(ret < 0)
+ {
+ ERR("Could not receive packet");
+ m_sock.close();
+ return NTP_CONN;
+ }
+ } while( strcmp(outEndpoint.get_address(), inEndpoint.get_address()) != 0 );
+
+ if(ret < sizeof(NTPPacket)) //TODO: Accept chunks
+ {
+ ERR("Receive packet size does not match");
+ m_sock.close();
+ return NTP_PRTCL;
+ }
+
+ if( pkt.stratum == 0) //Kiss of death message : Not good !
+ {
+ ERR("Kissed to death!");
+ m_sock.close();
+ return NTP_PRTCL;
+ }
+
+ //Correct Endianness
+ pkt.refTm_s = ntohl( pkt.refTm_s );
+ pkt.refTm_f = ntohl( pkt.refTm_f );
+ pkt.origTm_s = ntohl( pkt.origTm_s );
+ pkt.origTm_f = ntohl( pkt.origTm_f );
+ pkt.rxTm_s = ntohl( pkt.rxTm_s );
+ pkt.rxTm_f = ntohl( pkt.rxTm_f );
+ pkt.txTm_s = ntohl( pkt.txTm_s );
+ pkt.txTm_f = ntohl( pkt.txTm_f );
+
+ //Compute offset, see RFC 4330 p.13
+ uint32_t destTm_s = (NTP_TIMESTAMP_DELTA + time(NULL));
+ int64_t offset = ( (int64_t)( pkt.rxTm_s - pkt.origTm_s ) + (int64_t) ( pkt.txTm_s - destTm_s ) ) / 2; //Avoid overflow
+ DBG("Sent @%ul", pkt.txTm_s);
+ DBG("Offset: %lld", offset);
+ //Set time accordingly
+ set_time( time(NULL) + offset );
+
+#ifdef __DEBUG__
+ ctTime = time(NULL);
+ DBG("Time is now (UTC): %s", ctime(&ctTime));
+#endif
+
+ m_sock.close();
+
+ return NTP_OK;
+}
+
diff --git a/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/NTPClient_HelloWorld/NTPClient/NTPClient.h b/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/NTPClient_HelloWorld/NTPClient/NTPClient.h
new file mode 100644
index 0000000000..b7cf6ff127
--- /dev/null
+++ b/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/NTPClient_HelloWorld/NTPClient/NTPClient.h
@@ -0,0 +1,101 @@
+/* NTPClient.h */
+/* Copyright (C) 2012 mbed.org, MIT License
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy of this software
+ * and associated documentation files (the "Software"), to deal in the Software without restriction,
+ * including without limitation the rights to use, copy, modify, merge, publish, distribute,
+ * sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all copies or
+ * substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+ * BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
+ * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ */
+
+/** \file
+NTP Client header file
+*/
+
+#ifndef NTPCLIENT_H_
+#define NTPCLIENT_H_
+
+#include "UDPSocket.h"
+
+#define NTP_DEFAULT_PORT 123
+#define NTP_DEFAULT_TIMEOUT 4000
+
+///NTP client results
+enum NTPResult
+{
+ NTP_DNS, ///<Could not resolve name
+ NTP_PRTCL, ///<Protocol error
+ NTP_TIMEOUT, ///<Connection timeout
+ NTP_CONN, ///<Connection error
+ NTP_OK = 0, ///<Success
+};
+
+/** NTP Client to update the mbed's RTC using a remote time server
+*
+*/
+class NTPClient
+{
+public:
+ /**
+ Instantiate the NTP client
+ */
+ NTPClient();
+
+ /**Get current time (blocking)
+ Update the time using the server host
+ Blocks until completion
+ @param host NTP server IPv4 address or hostname (will be resolved via DNS)
+ @param port port to use; defaults to 123
+ @param timeout waiting timeout in ms (osWaitForever for blocking function, not recommended)
+ @return 0 on success, NTP error code (<0) on failure
+ */
+ NTPResult setTime(const char* host, uint16_t port = NTP_DEFAULT_PORT, uint32_t timeout = NTP_DEFAULT_TIMEOUT); //Blocking
+
+private:
+#if defined (__ICCARM__)
+ #pragma pack()
+#endif
+ struct NTPPacket //See RFC 4330 for Simple NTP
+ {
+ //WARN: We are in LE! Network is BE!
+ //LSb first
+ unsigned mode : 3;
+ unsigned vn : 3;
+ unsigned li : 2;
+
+ uint8_t stratum;
+ uint8_t poll;
+ uint8_t precision;
+ //32 bits header
+
+ uint32_t rootDelay;
+ uint32_t rootDispersion;
+ uint32_t refId;
+
+ uint32_t refTm_s;
+ uint32_t refTm_f;
+ uint32_t origTm_s;
+ uint32_t origTm_f;
+ uint32_t rxTm_s;
+ uint32_t rxTm_f;
+ uint32_t txTm_s;
+ uint32_t txTm_f;
+#if defined (__ICCARM__)
+ };
+#else
+ } __attribute__ ((packed));
+#endif
+
+ UDPSocket m_sock;
+};
+
+#endif /* NTPCLIENT_H_ */
diff --git a/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/NTPClient_HelloWorld/main.cpp b/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/NTPClient_HelloWorld/main.cpp
new file mode 100644
index 0000000000..fa71656b01
--- /dev/null
+++ b/tmk_core/tool/mbed/mbed-sdk/libraries/tests/net/protocols/NTPClient_HelloWorld/main.cpp
@@ -0,0 +1,39 @@
+#include "mbed.h"
+#include "test_env.h"
+#include "EthernetInterface.h"
+#include "NTPClient.h"
+
+int main() {
+ MBED_HOSTTEST_TIMEOUT(15);
+ MBED_HOSTTEST_SELECT(default_auto);
+ MBED_HOSTTEST_DESCRIPTION(NTP client);
+ MBED_HOSTTEST_START("NET_8");
+
+ EthernetInterface eth;
+ NTPClient ntp;
+ eth.init(); //Use DHCP
+ eth.connect();
+
+ // NTP set time
+ {
+ bool result = true;
+ const char *url_ntp_server = "0.pool.ntp.org";
+ printf("NTP_SETTIME: Trying to update time... \r\n");
+ const int ret = ntp.setTime(url_ntp_server);
+ if (ret == 0) {
+ time_t ctTime = time(NULL);
+ printf("NTP_SETTIME: UTC Time read successfully ... [OK]\r\n");
+ printf("NTP_SETTIME: %s\r\n", ctime(&ctTime));
+ }
+ else {
+ printf("NTP_SETTIME: Error(%d) ... [FAIL]\r\n", ret);
+ result = false;
+ }
+
+ if (result == false) {
+ MBED_HOSTTEST_RESULT(false);
+ }
+ }
+ eth.disconnect();
+ MBED_HOSTTEST_RESULT(true);
+}