Socket interface for ESP8266. Implements the NetworkSocketAPI. Requires device to use the Espressif Firmware.

Dependencies:   ESP8266

Dependents:   ESP8266InterfaceTests HelloESP8266Interface

Fork of ESP8266Interface by NetworkSocketAPI

Note

This library assumes your ESP8266 is running the Espressif Firmware. For instructions on how to update your ESP8266 to use the correct firmware see the Firmware Update Wiki Page.

Currently the ESP8266Interface LIbrary has the following Abilities:

Working

  • TCP Client
  • UDP Client
  • Transparent mode (single connection of 1 type at a time)
  • Station Mode (connects to AP)

To be implimented

  • TCP Server
  • UDP Server
  • Multi Connection Mode (able to have up to 5 sockets at a time)
  • AP Mode (Make ESP Chip act like access point)
  • DNS Support (currently websites must be looked up by IP)
  • Error Recovery

Nice but not necessary

  • colorized text for ESP AT Commands in Command line (easier to differentiate from other text)
Committer:
Christopher Haster
Date:
Tue May 10 14:31:58 2016 -0500
Revision:
57:2ad35ade7a83
Parent:
56:34829ec3a3da
Minor documentation changes

Who changed what in which revision?

UserRevisionLine numberNew contents of line
geky 49:750ed1b67483 1 /* ESP8266 implementation of NetworkInterfaceAPI
sam_grove 11:288c15b80a26 2 * Copyright (c) 2015 ARM Limited
sam_grove 11:288c15b80a26 3 *
sam_grove 11:288c15b80a26 4 * Licensed under the Apache License, Version 2.0 (the "License");
sam_grove 11:288c15b80a26 5 * you may not use this file except in compliance with the License.
sam_grove 11:288c15b80a26 6 * You may obtain a copy of the License at
sam_grove 11:288c15b80a26 7 *
sam_grove 11:288c15b80a26 8 * http://www.apache.org/licenses/LICENSE-2.0
sam_grove 11:288c15b80a26 9 *
sam_grove 11:288c15b80a26 10 * Unless required by applicable law or agreed to in writing, software
sam_grove 11:288c15b80a26 11 * distributed under the License is distributed on an "AS IS" BASIS,
sam_grove 11:288c15b80a26 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
sam_grove 11:288c15b80a26 13 * See the License for the specific language governing permissions and
sam_grove 11:288c15b80a26 14 * limitations under the License.
sam_grove 11:288c15b80a26 15 */
Christopher Haster 57:2ad35ade7a83 16
sam_grove 24:37504440f296 17
sarahmarshy 18:9fc7976c7b27 18 #include "ESP8266Interface.h"
sam_grove 11:288c15b80a26 19
Christopher Haster 45:538e5ce2f0d3 20 // Various timeouts for different ESP8266 operations
Christopher Haster 45:538e5ce2f0d3 21 #define ESP8266_CONNECT_TIMEOUT 15000
Christopher Haster 45:538e5ce2f0d3 22 #define ESP8266_SEND_TIMEOUT 500
Christopher Haster 45:538e5ce2f0d3 23 #define ESP8266_RECV_TIMEOUT 0
Christopher Haster 47:60a4b49e8b83 24 #define ESP8266_MISC_TIMEOUT 500
Christopher Haster 45:538e5ce2f0d3 25
Christopher Haster 42:4bf09cadf328 26
Christopher Haster 40:83c6b4129468 27 // ESP8266Interface implementation
Christopher Haster 34:9c26a3dcdc1f 28 ESP8266Interface::ESP8266Interface(PinName tx, PinName rx, bool debug)
Christopher Haster 34:9c26a3dcdc1f 29 : _esp(tx, rx, debug)
sam_grove 24:37504440f296 30 {
Christopher Haster 34:9c26a3dcdc1f 31 memset(_ids, 0, sizeof(_ids));
sam_grove 11:288c15b80a26 32 }
sam_grove 11:288c15b80a26 33
Christopher Haster 56:34829ec3a3da 34 int ESP8266Interface::connect(
Christopher Haster 57:2ad35ade7a83 35 const char *ssid,
Christopher Haster 57:2ad35ade7a83 36 const char *pass,
Christopher Haster 57:2ad35ade7a83 37 nsapi_security_t security)
sam_grove 11:288c15b80a26 38 {
Christopher Haster 45:538e5ce2f0d3 39 _esp.setTimeout(ESP8266_CONNECT_TIMEOUT);
Christopher Haster 45:538e5ce2f0d3 40
Christopher Haster 41:3f4d5f4862d2 41 if (!_esp.startup(3)) {
Christopher Haster 56:34829ec3a3da 42 return NSAPI_ERROR_DEVICE_ERROR;
Christopher Haster 41:3f4d5f4862d2 43 }
Christopher Haster 41:3f4d5f4862d2 44
Christopher Haster 41:3f4d5f4862d2 45 if (!_esp.dhcp(true, 1)) {
Christopher Haster 56:34829ec3a3da 46 return NSAPI_ERROR_DHCP_FAILURE;
Christopher Haster 41:3f4d5f4862d2 47 }
Christopher Haster 41:3f4d5f4862d2 48
Christopher Haster 57:2ad35ade7a83 49 if (!_esp.connect(ssid, pass)) {
Christopher Haster 56:34829ec3a3da 50 return NSAPI_ERROR_NO_CONNECTION;
Christopher Haster 41:3f4d5f4862d2 51 }
Christopher Haster 34:9c26a3dcdc1f 52
Christopher Haster 46:6b1bd1268074 53 if (!_esp.getIPAddress()) {
Christopher Haster 56:34829ec3a3da 54 return NSAPI_ERROR_DHCP_FAILURE;
Christopher Haster 41:3f4d5f4862d2 55 }
Christopher Haster 34:9c26a3dcdc1f 56
sam_grove 24:37504440f296 57 return 0;
sam_grove 11:288c15b80a26 58 }
sam_grove 11:288c15b80a26 59
Christopher Haster 56:34829ec3a3da 60 int ESP8266Interface::disconnect()
sam_grove 11:288c15b80a26 61 {
Christopher Haster 45:538e5ce2f0d3 62 _esp.setTimeout(ESP8266_MISC_TIMEOUT);
Christopher Haster 45:538e5ce2f0d3 63
Christopher Haster 41:3f4d5f4862d2 64 if (!_esp.disconnect()) {
Christopher Haster 56:34829ec3a3da 65 return NSAPI_ERROR_DEVICE_ERROR;
Christopher Haster 41:3f4d5f4862d2 66 }
Christopher Haster 34:9c26a3dcdc1f 67
sarahmarshy 22:312453862371 68 return 0;
sam_grove 11:288c15b80a26 69 }
sam_grove 11:288c15b80a26 70
Christopher Haster 56:34829ec3a3da 71 const char *ESP8266Interface::get_ip_address()
sarahmarshy 18:9fc7976c7b27 72 {
Christopher Haster 46:6b1bd1268074 73 return _esp.getIPAddress();
sarahmarshy 18:9fc7976c7b27 74 }
sarahmarshy 18:9fc7976c7b27 75
Christopher Haster 56:34829ec3a3da 76 const char *ESP8266Interface::get_mac_address()
sam_grove 11:288c15b80a26 77 {
Christopher Haster 46:6b1bd1268074 78 return _esp.getMACAddress();
sam_grove 11:288c15b80a26 79 }
sam_grove 11:288c15b80a26 80
Christopher Haster 56:34829ec3a3da 81 struct esp8266_socket {
Christopher Haster 56:34829ec3a3da 82 int id;
Christopher Haster 56:34829ec3a3da 83 nsapi_protocol_t proto;
Christopher Haster 56:34829ec3a3da 84 bool connected;
Christopher Haster 56:34829ec3a3da 85 };
Christopher Haster 56:34829ec3a3da 86
Christopher Haster 56:34829ec3a3da 87 int ESP8266Interface::socket_open(void **handle, nsapi_protocol_t proto)
sam_grove 11:288c15b80a26 88 {
Christopher Haster 34:9c26a3dcdc1f 89 // Look for an unused socket
sarahmarshy 18:9fc7976c7b27 90 int id = -1;
Christopher Haster 57:2ad35ade7a83 91
Christopher Haster 34:9c26a3dcdc1f 92 for (int i = 0; i < ESP8266_SOCKET_COUNT; i++) {
Christopher Haster 34:9c26a3dcdc1f 93 if (!_ids[i]) {
sam_grove 24:37504440f296 94 id = i;
Christopher Haster 34:9c26a3dcdc1f 95 _ids[i] = true;
sarahmarshy 18:9fc7976c7b27 96 break;
sarahmarshy 18:9fc7976c7b27 97 }
sarahmarshy 18:9fc7976c7b27 98 }
Christopher Haster 57:2ad35ade7a83 99
sam_grove 24:37504440f296 100 if (id == -1) {
Christopher Haster 56:34829ec3a3da 101 return NSAPI_ERROR_NO_SOCKET;
sarahmarshy 22:312453862371 102 }
Christopher Haster 57:2ad35ade7a83 103
Christopher Haster 56:34829ec3a3da 104 struct esp8266_socket *socket = new struct esp8266_socket;
Christopher Haster 56:34829ec3a3da 105 if (!socket) {
Christopher Haster 56:34829ec3a3da 106 return NSAPI_ERROR_NO_SOCKET;
Christopher Haster 40:83c6b4129468 107 }
Christopher Haster 57:2ad35ade7a83 108
Christopher Haster 56:34829ec3a3da 109 socket->id = id;
Christopher Haster 56:34829ec3a3da 110 socket->proto = proto;
Christopher Haster 56:34829ec3a3da 111 socket->connected = false;
Christopher Haster 56:34829ec3a3da 112 *handle = socket;
Christopher Haster 40:83c6b4129468 113 return 0;
Christopher Haster 40:83c6b4129468 114 }
Christopher Haster 40:83c6b4129468 115
Christopher Haster 56:34829ec3a3da 116 int ESP8266Interface::socket_close(void *handle)
Christopher Haster 40:83c6b4129468 117 {
Christopher Haster 56:34829ec3a3da 118 struct esp8266_socket *socket = (struct esp8266_socket *)handle;
Christopher Haster 56:34829ec3a3da 119 int err = 0;
Christopher Haster 56:34829ec3a3da 120 _esp.setTimeout(ESP8266_MISC_TIMEOUT);
Christopher Haster 56:34829ec3a3da 121
Christopher Haster 56:34829ec3a3da 122 if (!_esp.close(socket->id)) {
Christopher Haster 56:34829ec3a3da 123 err = NSAPI_ERROR_DEVICE_ERROR;
Christopher Haster 40:83c6b4129468 124 }
Christopher Haster 40:83c6b4129468 125
Christopher Haster 56:34829ec3a3da 126 _ids[socket->id] = false;
Christopher Haster 56:34829ec3a3da 127 delete socket;
Christopher Haster 56:34829ec3a3da 128 return err;
Christopher Haster 56:34829ec3a3da 129 }
Christopher Haster 56:34829ec3a3da 130
Christopher Haster 56:34829ec3a3da 131 int ESP8266Interface::socket_bind(void *handle, const SocketAddress &address)
Christopher Haster 56:34829ec3a3da 132 {
Christopher Haster 56:34829ec3a3da 133 return NSAPI_ERROR_UNSUPPORTED;
Christopher Haster 56:34829ec3a3da 134 }
Christopher Haster 56:34829ec3a3da 135
Christopher Haster 56:34829ec3a3da 136 int ESP8266Interface::socket_listen(void *handle, int backlog)
Christopher Haster 56:34829ec3a3da 137 {
Christopher Haster 56:34829ec3a3da 138 return NSAPI_ERROR_UNSUPPORTED;
Christopher Haster 56:34829ec3a3da 139 }
Christopher Haster 56:34829ec3a3da 140
Christopher Haster 56:34829ec3a3da 141 int ESP8266Interface::socket_connect(void *handle, const SocketAddress &addr)
Christopher Haster 56:34829ec3a3da 142 {
Christopher Haster 56:34829ec3a3da 143 struct esp8266_socket *socket = (struct esp8266_socket *)handle;
Christopher Haster 56:34829ec3a3da 144 _esp.setTimeout(ESP8266_MISC_TIMEOUT);
Christopher Haster 56:34829ec3a3da 145
Christopher Haster 56:34829ec3a3da 146 const char *proto = (socket->proto == NSAPI_UDP) ? "UDP" : "TCP";
Christopher Haster 56:34829ec3a3da 147 if (!_esp.open(proto, socket->id, addr.get_ip_address(), addr.get_port())) {
Christopher Haster 56:34829ec3a3da 148 return NSAPI_ERROR_DEVICE_ERROR;
Christopher Haster 56:34829ec3a3da 149 }
Christopher Haster 56:34829ec3a3da 150
Christopher Haster 56:34829ec3a3da 151 socket->connected = true;
Christopher Haster 40:83c6b4129468 152 return 0;
Christopher Haster 40:83c6b4129468 153 }
Christopher Haster 56:34829ec3a3da 154
Christopher Haster 56:34829ec3a3da 155 int ESP8266Interface::socket_accept(void **handle, void *server)
Christopher Haster 40:83c6b4129468 156 {
Christopher Haster 56:34829ec3a3da 157 return NSAPI_ERROR_UNSUPPORTED;
Christopher Haster 56:34829ec3a3da 158 }
Christopher Haster 45:538e5ce2f0d3 159
Christopher Haster 56:34829ec3a3da 160 int ESP8266Interface::socket_send(void *handle, const void *data, unsigned size)
Christopher Haster 56:34829ec3a3da 161 {
Christopher Haster 56:34829ec3a3da 162 struct esp8266_socket *socket = (struct esp8266_socket *)handle;
Christopher Haster 56:34829ec3a3da 163 _esp.setTimeout(ESP8266_SEND_TIMEOUT);
Christopher Haster 56:34829ec3a3da 164
Christopher Haster 56:34829ec3a3da 165 if (!_esp.send(socket->id, data, size)) {
Christopher Haster 56:34829ec3a3da 166 return NSAPI_ERROR_DEVICE_ERROR;
Christopher Haster 40:83c6b4129468 167 }
Christopher Haster 56:34829ec3a3da 168
geky 54:e78fad32cfff 169 return size;
Christopher Haster 40:83c6b4129468 170 }
Christopher Haster 40:83c6b4129468 171
Christopher Haster 56:34829ec3a3da 172 int ESP8266Interface::socket_recv(void *handle, void *data, unsigned size)
Christopher Haster 40:83c6b4129468 173 {
Christopher Haster 56:34829ec3a3da 174 struct esp8266_socket *socket = (struct esp8266_socket *)handle;
Christopher Haster 56:34829ec3a3da 175 _esp.setTimeout(ESP8266_RECV_TIMEOUT);
Christopher Haster 56:34829ec3a3da 176
Christopher Haster 56:34829ec3a3da 177 int32_t recv = _esp.recv(socket->id, data, size);
Christopher Haster 44:7ac7eb406603 178 if (recv < 0) {
Christopher Haster 56:34829ec3a3da 179 return NSAPI_ERROR_WOULD_BLOCK;
Christopher Haster 43:7c010b1db697 180 }
Christopher Haster 56:34829ec3a3da 181
Christopher Haster 44:7ac7eb406603 182 return recv;
Christopher Haster 40:83c6b4129468 183 }
Christopher Haster 40:83c6b4129468 184
Christopher Haster 56:34829ec3a3da 185 int ESP8266Interface::socket_sendto(void *handle, const SocketAddress &addr, const void *data, unsigned size)
Christopher Haster 56:34829ec3a3da 186 {
Christopher Haster 56:34829ec3a3da 187 struct esp8266_socket *socket = (struct esp8266_socket *)handle;
Christopher Haster 56:34829ec3a3da 188 if (!socket->connected) {
Christopher Haster 56:34829ec3a3da 189 int err = socket_connect(socket, addr);
Christopher Haster 56:34829ec3a3da 190 if (err < 0) {
Christopher Haster 56:34829ec3a3da 191 return err;
Christopher Haster 56:34829ec3a3da 192 }
Christopher Haster 56:34829ec3a3da 193 }
Christopher Haster 56:34829ec3a3da 194
Christopher Haster 56:34829ec3a3da 195 return socket_send(socket, data, size);
Christopher Haster 56:34829ec3a3da 196 }
Christopher Haster 56:34829ec3a3da 197
Christopher Haster 56:34829ec3a3da 198 int ESP8266Interface::socket_recvfrom(void *handle, SocketAddress *addr, void *data, unsigned size)
Christopher Haster 56:34829ec3a3da 199 {
Christopher Haster 56:34829ec3a3da 200 struct esp8266_socket *socket = (struct esp8266_socket *)handle;
Christopher Haster 56:34829ec3a3da 201 return socket_recv(socket, data, size);
Christopher Haster 56:34829ec3a3da 202 }
Christopher Haster 56:34829ec3a3da 203
Christopher Haster 56:34829ec3a3da 204 void ESP8266Interface::socket_attach(void *handle, void (*callback)(void *), void *data)
Christopher Haster 56:34829ec3a3da 205 {
Christopher Haster 56:34829ec3a3da 206 }