Mbed library for ENC28J60 Ethernet modules. Full support for TCP/IP and UDP Server, Client and HTTP server (webserver). DHCP and DNS is included.

Dependents:   mBuino_ENC28_MQTT Nucleo_Web_ENC28J60 Nucleo_Web_ENC28J60_ADC Serial_over_Ethernet ... more

Library for ENC28J60 Ethernet modules.

/media/uploads/hudakz/enc28j60_module01.jpg

Ported to mbed from Norbert Truchsess's UIPEthernet library for Arduino. Thank you Norbert!

  • Full support for persistent (streaming) TCP/IP and UDP connections Client and Server each, ARP, ICMP, DHCP and DNS.
  • Works with both Mbed OS 2 and Mbed OS 5.

Usage:

  • Import the library into your project.
  • Add #include "UipEthernet.h" to main.cpp
  • Create one instance of the UipEthernet class initialized with the MAC address you'd like to use and SPI pins of the connected Mbed board.

Example programs:

Import programWebSwitch_ENC28J60

HTTP Server serving a simple webpage which enables to remotely turn a digital output on/off. Compile, download, run and type 'IP_address/secret/' (don't forget the last '/') into your web browser and hit ENTER.

Import programHTTPServer_Echo_ENC28J60

A simple HTTP server echoing received requests. Ethernet connection is over an ENC28J60 board. Usage: Type the server's IP address into you web browser and hit <ENTER>.

Import programTcpServer_ENC28J60

Simple TCP/IP Server using the UIPEthernet library for ENC28J60 Ethernet boards.

Import programTcpClient_ENC28J60

Simple TCP/IP Client using the UIPEthernet library for ENC28J60 Ethernet boards.

Import programUdpServer_ENC28J60

Simple UDP Server using the UIPEthernet library for ENC28J60 Ethernet boards.

Import programUdpClient_ENC28J60

Simple UDP Client using the UIPEthernet library for ENC28J60 Ethernet boards.

Import programMQTT_Hello_ENC28J60

MQTT Client example program. Ethernet connection is via an ENC28J60 module.

Committer:
hudakz
Date:
Fri Aug 30 08:11:40 2019 +0000
Revision:
11:647d53d146f1
Parent:
9:a156d3de5647
Child:
13:95c00132cd98
"set_network" method of Mbed style added.

Who changed what in which revision?

UserRevisionLine numberNew contents of line
hudakz 9:a156d3de5647 1 /*
hudakz 9:a156d3de5647 2 UIPEthernet.cpp - Arduino implementation of a UIP wrapper class.
hudakz 9:a156d3de5647 3 Copyright (c) 2013 Norbert Truchsess <norbert.truchsess@t-online.de>
hudakz 9:a156d3de5647 4 All rights reserved.
hudakz 9:a156d3de5647 5
hudakz 9:a156d3de5647 6 Modified (ported to mbed) by Zoltan Hudak <hudakz@inbox.com>
hudakz 9:a156d3de5647 7
hudakz 9:a156d3de5647 8 This program is free software: you can redistribute it and/or modify
hudakz 9:a156d3de5647 9 it under the terms of the GNU General Public License as published by
hudakz 9:a156d3de5647 10 the Free Software Foundation, either version 3 of the License, or
hudakz 9:a156d3de5647 11 (at your option) any later version.
hudakz 9:a156d3de5647 12
hudakz 9:a156d3de5647 13 This program is distributed in the hope that it will be useful,
hudakz 9:a156d3de5647 14 but WITHOUT ANY WARRANTY; without even the implied warranty of
hudakz 9:a156d3de5647 15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
hudakz 9:a156d3de5647 16 GNU General Public License for more details.
hudakz 9:a156d3de5647 17
hudakz 9:a156d3de5647 18 You should have received a copy of the GNU General Public License
hudakz 9:a156d3de5647 19 along with this program. If not, see <http://www.gnu.org/licenses/>.
hudakz 9:a156d3de5647 20 */
hudakz 9:a156d3de5647 21 #include "mbed.h"
hudakz 9:a156d3de5647 22 #include "UipEthernet.h"
hudakz 11:647d53d146f1 23 #include "utility/Enc28j60Eth.h"
hudakz 9:a156d3de5647 24 #include "UdpSocket.h"
hudakz 9:a156d3de5647 25
hudakz 9:a156d3de5647 26 extern "C"
hudakz 9:a156d3de5647 27 {
hudakz 9:a156d3de5647 28 #include "utility/uip-conf.h"
hudakz 9:a156d3de5647 29 #include "utility/uip.h"
hudakz 9:a156d3de5647 30 #include "utility/uip_arp.h"
hudakz 9:a156d3de5647 31 #include "utility/uip_timer.h"
hudakz 9:a156d3de5647 32 }
hudakz 9:a156d3de5647 33 #define ETH_HDR ((struct uip_eth_hdr*) &uip_buf[0])
hudakz 9:a156d3de5647 34
hudakz 9:a156d3de5647 35 UipEthernet* UipEthernet:: ethernet = NULL;
hudakz 9:a156d3de5647 36 memhandle UipEthernet:: inPacket(NOBLOCK);
hudakz 9:a156d3de5647 37 memhandle UipEthernet:: uipPacket(NOBLOCK);
hudakz 9:a156d3de5647 38 uint8_t UipEthernet:: uipHeaderLen(0);
hudakz 9:a156d3de5647 39 uint8_t UipEthernet:: packetState(0);
hudakz 9:a156d3de5647 40 IpAddress UipEthernet:: dnsServerAddress;
hudakz 9:a156d3de5647 41
hudakz 9:a156d3de5647 42 /**
hudakz 9:a156d3de5647 43 * @brief
hudakz 9:a156d3de5647 44 * @note
hudakz 9:a156d3de5647 45 * @param
hudakz 9:a156d3de5647 46 * @retval
hudakz 9:a156d3de5647 47 */
hudakz 9:a156d3de5647 48 void enc28j60_mempool_block_move_callback(memaddress dest, memaddress src, memaddress len)
hudakz 9:a156d3de5647 49 {
hudakz 11:647d53d146f1 50 //as ENC28J60 DMA is unable to copy single byte:
hudakz 9:a156d3de5647 51 if (len == 1) {
hudakz 11:647d53d146f1 52 UipEthernet::ethernet->enc28j60Eth.writeByte(dest, UipEthernet::ethernet->enc28j60Eth.readByte(src));
hudakz 9:a156d3de5647 53 }
hudakz 9:a156d3de5647 54 else {
hudakz 9:a156d3de5647 55 // calculate address of last byte
hudakz 9:a156d3de5647 56 len += src - 1;
hudakz 9:a156d3de5647 57
hudakz 9:a156d3de5647 58 /* 1. Appropriately program the EDMAST, EDMAND
hudakz 9:a156d3de5647 59 and EDMADST register pairs. The EDMAST
hudakz 9:a156d3de5647 60 registers should point to the first byte to copy
hudakz 9:a156d3de5647 61 from, the EDMAND registers should point to the
hudakz 9:a156d3de5647 62 last byte to copy and the EDMADST registers
hudakz 9:a156d3de5647 63 should point to the first byte in the destination
hudakz 9:a156d3de5647 64 range. The destination range will always be
hudakz 9:a156d3de5647 65 linear, never wrapping at any values except from
hudakz 9:a156d3de5647 66 8191 to 0 (the 8-Kbyte memory boundary).
hudakz 9:a156d3de5647 67 Extreme care should be taken when
hudakz 9:a156d3de5647 68 programming the start and end pointers to
hudakz 9:a156d3de5647 69 prevent a never ending DMA operation which
hudakz 9:a156d3de5647 70 would overwrite the entire 8-Kbyte buffer.
hudakz 9:a156d3de5647 71 */
hudakz 11:647d53d146f1 72 UipEthernet::ethernet->enc28j60Eth.writeRegPair(EDMASTL, src);
hudakz 11:647d53d146f1 73 UipEthernet::ethernet->enc28j60Eth.writeRegPair(EDMADSTL, dest);
hudakz 9:a156d3de5647 74
hudakz 11:647d53d146f1 75 if ((src <= RXEND_INIT) && (len > RXEND_INIT))
hudakz 11:647d53d146f1 76 len -= ((RXEND_INIT + 1) - RXSTART_INIT);
hudakz 11:647d53d146f1 77 UipEthernet::ethernet->enc28j60Eth.writeRegPair(EDMANDL, len);
hudakz 9:a156d3de5647 78
hudakz 9:a156d3de5647 79 /* 2. If an interrupt at the end of the copy process is
hudakz 9:a156d3de5647 80 desired, set EIE.DMAIE and EIE.INTIE and
hudakz 9:a156d3de5647 81 clear EIR.DMAIF.
hudakz 9:a156d3de5647 82
hudakz 9:a156d3de5647 83 3. Verify that ECON1.CSUMEN is clear. */
hudakz 11:647d53d146f1 84 UipEthernet::ethernet->enc28j60Eth.writeOp(ENC28J60_BIT_FIELD_CLR, ECON1, ECON1_CSUMEN);
hudakz 9:a156d3de5647 85
hudakz 9:a156d3de5647 86 /* 4. Start the DMA copy by setting ECON1.DMAST. */
hudakz 11:647d53d146f1 87 UipEthernet::ethernet->enc28j60Eth.writeOp(ENC28J60_BIT_FIELD_SET, ECON1, ECON1_DMAST);
hudakz 9:a156d3de5647 88
hudakz 9:a156d3de5647 89 // wait until runnig DMA is completed
hudakz 11:647d53d146f1 90 while (UipEthernet::ethernet->enc28j60Eth.readOp(ENC28J60_READ_CTRL_REG, ECON1) & ECON1_DMAST);
hudakz 9:a156d3de5647 91 }
hudakz 9:a156d3de5647 92 }
hudakz 9:a156d3de5647 93
hudakz 9:a156d3de5647 94 /*
hudakz 9:a156d3de5647 95 * Because UIP isn't encapsulated within a class we have to use global
hudakz 9:a156d3de5647 96 * variables, so we can only have one TCP/IP stack per program.
hudakz 9:a156d3de5647 97 */
hudakz 9:a156d3de5647 98 UipEthernet::UipEthernet(const uint8_t mac[6], PinName mosi, PinName miso, PinName sck, PinName cs) :
hudakz 11:647d53d146f1 99 enc28j60Eth(mosi, miso, sck, cs),
hudakz 9:a156d3de5647 100 _mac(new uint8_t[6]),
hudakz 9:a156d3de5647 101 _ip(),
hudakz 9:a156d3de5647 102 _dns(),
hudakz 9:a156d3de5647 103 _gateway(),
hudakz 9:a156d3de5647 104 _subnet()
hudakz 9:a156d3de5647 105 {
hudakz 9:a156d3de5647 106 for (uint8_t i = 0; i < 6; i++)
hudakz 9:a156d3de5647 107 _mac[i] = mac[i];
hudakz 9:a156d3de5647 108 }
hudakz 9:a156d3de5647 109
hudakz 9:a156d3de5647 110 /**
hudakz 9:a156d3de5647 111 * @brief
hudakz 9:a156d3de5647 112 * @note
hudakz 9:a156d3de5647 113 * @param
hudakz 9:a156d3de5647 114 * @retval
hudakz 9:a156d3de5647 115 */
hudakz 9:a156d3de5647 116 int UipEthernet::connect()
hudakz 9:a156d3de5647 117 {
hudakz 9:a156d3de5647 118 // Inicialize static pointer to the UIPEthernet instance
hudakz 9:a156d3de5647 119 ethernet = this;
hudakz 9:a156d3de5647 120
hudakz 9:a156d3de5647 121 // Initialise the basic info
hudakz 9:a156d3de5647 122 init(_mac);
hudakz 9:a156d3de5647 123
hudakz 9:a156d3de5647 124 // If no local IP address has been set ask DHCP server to provide one
hudakz 9:a156d3de5647 125 if (_ip == IpAddress()) {
hudakz 9:a156d3de5647 126 // Now try to get our config info from a DHCP server
hudakz 9:a156d3de5647 127 int ret = dhcpClient.begin((uint8_t*)_mac);
hudakz 9:a156d3de5647 128
hudakz 9:a156d3de5647 129 if (ret == 1) {
hudakz 9:a156d3de5647 130 // We've successfully found a DHCP server and got our configuration info, so set things
hudakz 9:a156d3de5647 131 // accordingly
hudakz 9:a156d3de5647 132 set_network
hudakz 9:a156d3de5647 133 (
hudakz 9:a156d3de5647 134 dhcpClient.getLocalIp(),
hudakz 9:a156d3de5647 135 dhcpClient.getDnsServerIp(),
hudakz 9:a156d3de5647 136 dhcpClient.getGatewayIp(),
hudakz 9:a156d3de5647 137 dhcpClient.getSubnetMask()
hudakz 9:a156d3de5647 138 );
hudakz 9:a156d3de5647 139 }
hudakz 9:a156d3de5647 140
hudakz 9:a156d3de5647 141 return ret;
hudakz 9:a156d3de5647 142 }
hudakz 9:a156d3de5647 143 else {
hudakz 9:a156d3de5647 144 return 1;
hudakz 9:a156d3de5647 145 }
hudakz 9:a156d3de5647 146 }
hudakz 11:647d53d146f1 147
hudakz 11:647d53d146f1 148 /**
hudakz 11:647d53d146f1 149 * @brief
hudakz 11:647d53d146f1 150 * @note
hudakz 11:647d53d146f1 151 * @param
hudakz 11:647d53d146f1 152 * @retval
hudakz 11:647d53d146f1 153 */
hudakz 11:647d53d146f1 154 void UipEthernet::set_network(const char *ip_address, const char *netmask, const char *gateway)
hudakz 11:647d53d146f1 155 {
hudakz 11:647d53d146f1 156 _ip = IpAddress(ip_address, strlen(ip_address));
hudakz 11:647d53d146f1 157 _dns = _ip;
hudakz 11:647d53d146f1 158 _dns[3] = 1;
hudakz 11:647d53d146f1 159 _gateway = IpAddress(gateway, strlen(gateway));
hudakz 11:647d53d146f1 160 _subnet = IpAddress(netmask, strlen(netmask));
hudakz 11:647d53d146f1 161 set_network(_ip, _dns, _gateway, _subnet);
hudakz 11:647d53d146f1 162 }
hudakz 9:a156d3de5647 163
hudakz 9:a156d3de5647 164 /**
hudakz 9:a156d3de5647 165 * @brief
hudakz 9:a156d3de5647 166 * @note
hudakz 9:a156d3de5647 167 * @param
hudakz 9:a156d3de5647 168 * @retval
hudakz 9:a156d3de5647 169 */
hudakz 9:a156d3de5647 170 void UipEthernet::set_network(uint8_t octet1, uint8_t octet2, uint8_t octet3, uint8_t octet4)
hudakz 9:a156d3de5647 171 {
hudakz 9:a156d3de5647 172 _ip = IpAddress(octet1, octet2, octet3, octet4);
hudakz 9:a156d3de5647 173 set_network(_ip);
hudakz 9:a156d3de5647 174 }
hudakz 9:a156d3de5647 175
hudakz 9:a156d3de5647 176 /**
hudakz 9:a156d3de5647 177 * @brief
hudakz 9:a156d3de5647 178 * @note
hudakz 9:a156d3de5647 179 * @param
hudakz 9:a156d3de5647 180 * @retval
hudakz 9:a156d3de5647 181 */
hudakz 9:a156d3de5647 182 void UipEthernet::set_network(IpAddress ip)
hudakz 9:a156d3de5647 183 {
hudakz 9:a156d3de5647 184 _ip = ip;
hudakz 9:a156d3de5647 185 _dns = ip;
hudakz 9:a156d3de5647 186 _dns[3] = 1;
hudakz 9:a156d3de5647 187 set_network(ip, dns);
hudakz 9:a156d3de5647 188 }
hudakz 9:a156d3de5647 189
hudakz 9:a156d3de5647 190 /**
hudakz 9:a156d3de5647 191 * @brief
hudakz 9:a156d3de5647 192 * @note
hudakz 9:a156d3de5647 193 * @param
hudakz 9:a156d3de5647 194 * @retval
hudakz 9:a156d3de5647 195 */
hudakz 9:a156d3de5647 196 void UipEthernet::set_network(IpAddress ip, IpAddress dns)
hudakz 9:a156d3de5647 197 {
hudakz 9:a156d3de5647 198 _ip = ip;
hudakz 9:a156d3de5647 199 _dns = dns;
hudakz 9:a156d3de5647 200 _gateway = ip;
hudakz 9:a156d3de5647 201 _gateway[3] = 1;
hudakz 9:a156d3de5647 202 set_network(ip, dns, _gateway);
hudakz 9:a156d3de5647 203 }
hudakz 9:a156d3de5647 204
hudakz 9:a156d3de5647 205 /**
hudakz 9:a156d3de5647 206 * @brief
hudakz 9:a156d3de5647 207 * @note
hudakz 9:a156d3de5647 208 * @param
hudakz 9:a156d3de5647 209 * @retval
hudakz 9:a156d3de5647 210 */
hudakz 9:a156d3de5647 211 void UipEthernet::set_network(IpAddress ip, IpAddress dns, IpAddress gateway)
hudakz 9:a156d3de5647 212 {
hudakz 9:a156d3de5647 213 _ip = ip;
hudakz 9:a156d3de5647 214 _dns = dns;
hudakz 9:a156d3de5647 215 _gateway = gateway;
hudakz 9:a156d3de5647 216 _subnet = IpAddress(255, 255, 255, 0);
hudakz 11:647d53d146f1 217 set_network(_ip, _dns, _gateway, _subnet);
hudakz 9:a156d3de5647 218 }
hudakz 9:a156d3de5647 219
hudakz 9:a156d3de5647 220 /**
hudakz 9:a156d3de5647 221 * @brief
hudakz 9:a156d3de5647 222 * @note
hudakz 9:a156d3de5647 223 * @param
hudakz 9:a156d3de5647 224 * @retval
hudakz 9:a156d3de5647 225 */
hudakz 9:a156d3de5647 226 void UipEthernet::set_network(IpAddress ip, IpAddress dns, IpAddress gateway, IpAddress subnet)
hudakz 9:a156d3de5647 227 {
hudakz 9:a156d3de5647 228 uip_ipaddr_t ipaddr;
hudakz 9:a156d3de5647 229
hudakz 9:a156d3de5647 230 uip_ip_addr(ipaddr, ip);
hudakz 9:a156d3de5647 231 uip_sethostaddr(ipaddr);
hudakz 9:a156d3de5647 232
hudakz 9:a156d3de5647 233 uip_ip_addr(ipaddr, gateway);
hudakz 9:a156d3de5647 234 uip_setdraddr(ipaddr);
hudakz 9:a156d3de5647 235
hudakz 9:a156d3de5647 236 uip_ip_addr(ipaddr, subnet);
hudakz 9:a156d3de5647 237 uip_setnetmask(ipaddr);
hudakz 9:a156d3de5647 238
hudakz 9:a156d3de5647 239 dnsServerAddress = dns;
hudakz 9:a156d3de5647 240 }
hudakz 9:a156d3de5647 241
hudakz 9:a156d3de5647 242 /**
hudakz 9:a156d3de5647 243 * @brief
hudakz 9:a156d3de5647 244 * @note
hudakz 9:a156d3de5647 245 * @param
hudakz 9:a156d3de5647 246 * @retval
hudakz 9:a156d3de5647 247 */
hudakz 9:a156d3de5647 248 IpAddress UipEthernet::localIP()
hudakz 9:a156d3de5647 249 {
hudakz 9:a156d3de5647 250 uip_ipaddr_t a;
hudakz 9:a156d3de5647 251
hudakz 9:a156d3de5647 252 uip_gethostaddr(a);
hudakz 9:a156d3de5647 253 return ip_addr_uip(a);
hudakz 9:a156d3de5647 254 }
hudakz 9:a156d3de5647 255
hudakz 9:a156d3de5647 256 /**
hudakz 9:a156d3de5647 257 * @brief
hudakz 9:a156d3de5647 258 * @note
hudakz 9:a156d3de5647 259 * @param
hudakz 9:a156d3de5647 260 * @retval
hudakz 9:a156d3de5647 261 */
hudakz 9:a156d3de5647 262 IpAddress UipEthernet::subnetMask()
hudakz 9:a156d3de5647 263 {
hudakz 9:a156d3de5647 264 uip_ipaddr_t a;
hudakz 9:a156d3de5647 265
hudakz 9:a156d3de5647 266 uip_getnetmask(a);
hudakz 9:a156d3de5647 267 return ip_addr_uip(a);
hudakz 9:a156d3de5647 268 }
hudakz 9:a156d3de5647 269
hudakz 9:a156d3de5647 270 /**
hudakz 9:a156d3de5647 271 * @brief
hudakz 9:a156d3de5647 272 * @note
hudakz 9:a156d3de5647 273 * @param
hudakz 9:a156d3de5647 274 * @retval
hudakz 9:a156d3de5647 275 */
hudakz 9:a156d3de5647 276 IpAddress UipEthernet::gatewayIP()
hudakz 9:a156d3de5647 277 {
hudakz 9:a156d3de5647 278 uip_ipaddr_t a;
hudakz 9:a156d3de5647 279
hudakz 9:a156d3de5647 280 uip_getdraddr(a);
hudakz 9:a156d3de5647 281 return ip_addr_uip(a);
hudakz 9:a156d3de5647 282 }
hudakz 9:a156d3de5647 283
hudakz 9:a156d3de5647 284 /**
hudakz 9:a156d3de5647 285 * @brief
hudakz 9:a156d3de5647 286 * @note
hudakz 9:a156d3de5647 287 * @param
hudakz 9:a156d3de5647 288 * @retval
hudakz 9:a156d3de5647 289 */
hudakz 9:a156d3de5647 290 IpAddress UipEthernet::dnsServerIP()
hudakz 9:a156d3de5647 291 {
hudakz 9:a156d3de5647 292 return dnsServerAddress;
hudakz 9:a156d3de5647 293 }
hudakz 9:a156d3de5647 294
hudakz 9:a156d3de5647 295 /**
hudakz 9:a156d3de5647 296 * @brief
hudakz 9:a156d3de5647 297 * @note
hudakz 9:a156d3de5647 298 * @param
hudakz 9:a156d3de5647 299 * @retval
hudakz 9:a156d3de5647 300 */
hudakz 9:a156d3de5647 301 const char* UipEthernet::get_ip_address()
hudakz 9:a156d3de5647 302 {
hudakz 9:a156d3de5647 303 static char buf[16];
hudakz 9:a156d3de5647 304 return localIP().toString(buf);
hudakz 9:a156d3de5647 305 }
hudakz 9:a156d3de5647 306
hudakz 9:a156d3de5647 307 /**
hudakz 9:a156d3de5647 308 * @brief
hudakz 9:a156d3de5647 309 * @note
hudakz 9:a156d3de5647 310 * @param
hudakz 9:a156d3de5647 311 * @retval
hudakz 9:a156d3de5647 312 */
hudakz 9:a156d3de5647 313 const char* UipEthernet::get_netmask()
hudakz 9:a156d3de5647 314 {
hudakz 9:a156d3de5647 315 static char buf[16];
hudakz 9:a156d3de5647 316 return subnetMask().toString(buf);
hudakz 9:a156d3de5647 317 }
hudakz 9:a156d3de5647 318
hudakz 9:a156d3de5647 319 /**
hudakz 9:a156d3de5647 320 * @brief
hudakz 9:a156d3de5647 321 * @note
hudakz 9:a156d3de5647 322 * @param
hudakz 9:a156d3de5647 323 * @retval
hudakz 9:a156d3de5647 324 */
hudakz 9:a156d3de5647 325 const char* UipEthernet::get_gateway()
hudakz 9:a156d3de5647 326 {
hudakz 9:a156d3de5647 327 static char buf[16];
hudakz 9:a156d3de5647 328 return gatewayIP().toString(buf);
hudakz 9:a156d3de5647 329 }
hudakz 9:a156d3de5647 330
hudakz 9:a156d3de5647 331 /**
hudakz 9:a156d3de5647 332 * @brief
hudakz 9:a156d3de5647 333 * @note
hudakz 9:a156d3de5647 334 * @param
hudakz 9:a156d3de5647 335 * @retval
hudakz 9:a156d3de5647 336 */
hudakz 9:a156d3de5647 337 void UipEthernet::tick()
hudakz 9:a156d3de5647 338 {
hudakz 9:a156d3de5647 339 if (inPacket == NOBLOCK) {
hudakz 11:647d53d146f1 340 inPacket = enc28j60Eth.receivePacket();
hudakz 9:a156d3de5647 341 #ifdef UIPETHERNET_DEBUG
hudakz 9:a156d3de5647 342 if (in_packet != NOBLOCK) {
hudakz 9:a156d3de5647 343 printf("--------------\r\nreceivePacket: %d\r\n", in_packet);
hudakz 9:a156d3de5647 344 }
hudakz 9:a156d3de5647 345 #endif
hudakz 9:a156d3de5647 346 }
hudakz 9:a156d3de5647 347
hudakz 9:a156d3de5647 348 if (inPacket != NOBLOCK) {
hudakz 9:a156d3de5647 349 packetState = UIPETHERNET_FREEPACKET;
hudakz 11:647d53d146f1 350 uip_len = enc28j60Eth.blockSize(inPacket);
hudakz 9:a156d3de5647 351 if (uip_len > 0) {
hudakz 11:647d53d146f1 352 enc28j60Eth.readPacket(inPacket, 0, (uint8_t*)uip_buf, UIP_BUFSIZE);
hudakz 9:a156d3de5647 353 if (ETH_HDR->type == HTONS(UIP_ETHTYPE_IP)) {
hudakz 9:a156d3de5647 354 uipPacket = inPacket; //required for upper_layer_checksum of in_packet!
hudakz 9:a156d3de5647 355 #ifdef UIPETHERNET_DEBUG
hudakz 9:a156d3de5647 356 printf("readPacket type IP, uip_len: %d\r\n", uip_len);
hudakz 9:a156d3de5647 357 #endif
hudakz 9:a156d3de5647 358 uip_arp_ipin();
hudakz 9:a156d3de5647 359 uip_input();
hudakz 9:a156d3de5647 360 if (uip_len > 0) {
hudakz 9:a156d3de5647 361 uip_arp_out();
hudakz 9:a156d3de5647 362 network_send();
hudakz 9:a156d3de5647 363 }
hudakz 9:a156d3de5647 364 }
hudakz 9:a156d3de5647 365 else
hudakz 9:a156d3de5647 366 if (ETH_HDR->type == HTONS(UIP_ETHTYPE_ARP))
hudakz 9:a156d3de5647 367 {
hudakz 9:a156d3de5647 368 #ifdef UIPETHERNET_DEBUG
hudakz 9:a156d3de5647 369 printf("readPacket type ARP, uip_len: %d\r\n", uip_len);
hudakz 9:a156d3de5647 370 #endif
hudakz 9:a156d3de5647 371 uip_arp_arpin();
hudakz 9:a156d3de5647 372 if (uip_len > 0) {
hudakz 9:a156d3de5647 373 network_send();
hudakz 9:a156d3de5647 374 }
hudakz 9:a156d3de5647 375 }
hudakz 9:a156d3de5647 376 }
hudakz 9:a156d3de5647 377
hudakz 9:a156d3de5647 378 if (inPacket != NOBLOCK && (packetState & UIPETHERNET_FREEPACKET))
hudakz 9:a156d3de5647 379 {
hudakz 9:a156d3de5647 380 #ifdef UIPETHERNET_DEBUG
hudakz 9:a156d3de5647 381 printf("freeing packet: %d\r\n", in_packet);
hudakz 9:a156d3de5647 382 #endif
hudakz 11:647d53d146f1 383 enc28j60Eth.freePacket();
hudakz 9:a156d3de5647 384 inPacket = NOBLOCK;
hudakz 9:a156d3de5647 385 }
hudakz 9:a156d3de5647 386 }
hudakz 9:a156d3de5647 387
hudakz 9:a156d3de5647 388 bool periodic = periodicTimer.read_ms() > UIP_PERIODIC_TIMEOUT;
hudakz 9:a156d3de5647 389
hudakz 9:a156d3de5647 390 for (int i = 0; i < UIP_CONNS; i++) {
hudakz 9:a156d3de5647 391 uip_conn = &uip_conns[i];
hudakz 9:a156d3de5647 392 if (periodic) {
hudakz 9:a156d3de5647 393 uip_process(UIP_TIMER);
hudakz 9:a156d3de5647 394 }
hudakz 9:a156d3de5647 395 else {
hudakz 9:a156d3de5647 396 uip_userdata_t* data = (uip_userdata_t*)uip_conn->appstate;
hudakz 9:a156d3de5647 397 if (data != NULL) {
hudakz 9:a156d3de5647 398 if (data->pollTimer.read_ms() >= UIP_CLIENT_TIMEOUT) {
hudakz 9:a156d3de5647 399 uip_process(UIP_POLL_REQUEST);
hudakz 9:a156d3de5647 400 data->pollTimer.stop();
hudakz 9:a156d3de5647 401 data->pollTimer.reset();
hudakz 9:a156d3de5647 402 }
hudakz 9:a156d3de5647 403 }
hudakz 9:a156d3de5647 404 else
hudakz 9:a156d3de5647 405 continue;
hudakz 9:a156d3de5647 406 }
hudakz 9:a156d3de5647 407
hudakz 9:a156d3de5647 408 // If the above function invocation resulted in data that
hudakz 9:a156d3de5647 409 // should be sent out on the Enc28J60Network, the global variable
hudakz 9:a156d3de5647 410 // uip_len is set to a value > 0.
hudakz 9:a156d3de5647 411 if (uip_len > 0) {
hudakz 9:a156d3de5647 412 uip_arp_out();
hudakz 9:a156d3de5647 413 network_send();
hudakz 9:a156d3de5647 414 }
hudakz 9:a156d3de5647 415 }
hudakz 9:a156d3de5647 416
hudakz 9:a156d3de5647 417 if (periodic) {
hudakz 9:a156d3de5647 418 periodicTimer.reset();
hudakz 9:a156d3de5647 419 #if UIP_UDP
hudakz 9:a156d3de5647 420 for (int i = 0; i < UIP_UDP_CONNS; i++) {
hudakz 9:a156d3de5647 421 uip_udp_periodic(i);
hudakz 9:a156d3de5647 422
hudakz 9:a156d3de5647 423 // If the above function invocation resulted in data that
hudakz 9:a156d3de5647 424 // should be sent out on the Enc28J60Network, the global variable
hudakz 9:a156d3de5647 425 // uip_len is set to a value > 0.
hudakz 9:a156d3de5647 426 if (uip_len > 0) {
hudakz 9:a156d3de5647 427 UdpSocket::_send((uip_udp_userdata_t *) (uip_udp_conns[i].appstate));
hudakz 9:a156d3de5647 428 }
hudakz 9:a156d3de5647 429 }
hudakz 9:a156d3de5647 430 #endif // UIP_UDP
hudakz 9:a156d3de5647 431 }
hudakz 9:a156d3de5647 432 }
hudakz 9:a156d3de5647 433
hudakz 9:a156d3de5647 434 /**
hudakz 9:a156d3de5647 435 * @brief
hudakz 9:a156d3de5647 436 * @note
hudakz 9:a156d3de5647 437 * @param
hudakz 9:a156d3de5647 438 * @retval
hudakz 9:a156d3de5647 439 */
hudakz 9:a156d3de5647 440 bool UipEthernet::network_send()
hudakz 9:a156d3de5647 441 {
hudakz 9:a156d3de5647 442 if (packetState & UIPETHERNET_SENDPACKET)
hudakz 9:a156d3de5647 443 {
hudakz 9:a156d3de5647 444 #ifdef UIPETHERNET_DEBUG
hudakz 9:a156d3de5647 445 printf("Enc28J60Network_send uip_packet: %d, hdrlen: %d\r\n", uip_packet, uip_hdrlen);
hudakz 9:a156d3de5647 446 #endif
hudakz 11:647d53d146f1 447 enc28j60Eth.writePacket(uipPacket, 0, uip_buf, uipHeaderLen);
hudakz 9:a156d3de5647 448 packetState &= ~UIPETHERNET_SENDPACKET;
hudakz 9:a156d3de5647 449 goto sendandfree;
hudakz 9:a156d3de5647 450 }
hudakz 9:a156d3de5647 451
hudakz 11:647d53d146f1 452 uipPacket = Enc28j60Eth::allocBlock(uip_len);
hudakz 9:a156d3de5647 453 if (uipPacket != NOBLOCK)
hudakz 9:a156d3de5647 454 {
hudakz 9:a156d3de5647 455 #ifdef UIPETHERNET_DEBUG
hudakz 9:a156d3de5647 456 printf("Enc28J60Network_send uip_buf (uip_len): %d, packet: %d\r\n", uip_len, uip_packet);
hudakz 9:a156d3de5647 457 #endif
hudakz 11:647d53d146f1 458 enc28j60Eth.writePacket(uipPacket, 0, uip_buf, uip_len);
hudakz 9:a156d3de5647 459 goto sendandfree;
hudakz 9:a156d3de5647 460 }
hudakz 9:a156d3de5647 461
hudakz 9:a156d3de5647 462 return false;
hudakz 9:a156d3de5647 463 sendandfree:
hudakz 11:647d53d146f1 464 enc28j60Eth.sendPacket(uipPacket);
hudakz 11:647d53d146f1 465 Enc28j60Eth::freeBlock(uipPacket);
hudakz 9:a156d3de5647 466 uipPacket = NOBLOCK;
hudakz 9:a156d3de5647 467 return true;
hudakz 9:a156d3de5647 468 }
hudakz 9:a156d3de5647 469
hudakz 9:a156d3de5647 470 /**
hudakz 9:a156d3de5647 471 * @brief
hudakz 9:a156d3de5647 472 * @note
hudakz 9:a156d3de5647 473 * @param
hudakz 9:a156d3de5647 474 * @retval
hudakz 9:a156d3de5647 475 */
hudakz 9:a156d3de5647 476 void UipEthernet::init(const uint8_t* mac)
hudakz 9:a156d3de5647 477 {
hudakz 9:a156d3de5647 478 periodicTimer.start();
hudakz 9:a156d3de5647 479
hudakz 11:647d53d146f1 480 enc28j60Eth.init((uint8_t*)mac);
hudakz 9:a156d3de5647 481 uip_seteth_addr(mac);
hudakz 9:a156d3de5647 482
hudakz 9:a156d3de5647 483 uip_init();
hudakz 9:a156d3de5647 484 uip_arp_init();
hudakz 9:a156d3de5647 485 }
hudakz 9:a156d3de5647 486
hudakz 9:a156d3de5647 487 /**
hudakz 9:a156d3de5647 488 * @brief
hudakz 9:a156d3de5647 489 * @note
hudakz 9:a156d3de5647 490 * @param
hudakz 9:a156d3de5647 491 * @retval
hudakz 9:a156d3de5647 492 */
hudakz 9:a156d3de5647 493 //void UIPEthernet::configure(IPAddress ip, IPAddress dns, IPAddress gateway, IPAddress subnet)
hudakz 9:a156d3de5647 494 //{
hudakz 9:a156d3de5647 495 // uip_ipaddr_t ipaddr;
hudakz 9:a156d3de5647 496 // uip_ip_addr(ipaddr, ip);
hudakz 9:a156d3de5647 497 // uip_sethostaddr(ipaddr);
hudakz 9:a156d3de5647 498 // uip_ip_addr(ipaddr, gateway);
hudakz 9:a156d3de5647 499 // uip_setdraddr(ipaddr);
hudakz 9:a156d3de5647 500 // uip_ip_addr(ipaddr, subnet);
hudakz 9:a156d3de5647 501 // uip_setnetmask(ipaddr);
hudakz 9:a156d3de5647 502 // dnsServerAddress = dns;
hudakz 9:a156d3de5647 503 //}
hudakz 9:a156d3de5647 504
hudakz 9:a156d3de5647 505 /**
hudakz 9:a156d3de5647 506 * @brief
hudakz 9:a156d3de5647 507 * @note
hudakz 9:a156d3de5647 508 * @param
hudakz 9:a156d3de5647 509 * @retval
hudakz 9:a156d3de5647 510 */
hudakz 9:a156d3de5647 511 uint16_t UipEthernet::chksum(uint16_t sum, const uint8_t* data, uint16_t len)
hudakz 9:a156d3de5647 512 {
hudakz 9:a156d3de5647 513 uint16_t t;
hudakz 9:a156d3de5647 514 const uint8_t* dataptr;
hudakz 9:a156d3de5647 515 const uint8_t* last_byte;
hudakz 9:a156d3de5647 516
hudakz 9:a156d3de5647 517 dataptr = data;
hudakz 9:a156d3de5647 518 last_byte = data + len - 1;
hudakz 9:a156d3de5647 519
hudakz 9:a156d3de5647 520 while (dataptr < last_byte) {
hudakz 9:a156d3de5647 521 /* At least two more bytes */
hudakz 9:a156d3de5647 522 t = (dataptr[0] << 8) + dataptr[1];
hudakz 9:a156d3de5647 523 sum += t;
hudakz 9:a156d3de5647 524 if (sum < t) {
hudakz 9:a156d3de5647 525 sum++; /* carry */
hudakz 9:a156d3de5647 526 }
hudakz 9:a156d3de5647 527
hudakz 9:a156d3de5647 528 dataptr += 2;
hudakz 9:a156d3de5647 529 }
hudakz 9:a156d3de5647 530
hudakz 9:a156d3de5647 531 if (dataptr == last_byte) {
hudakz 9:a156d3de5647 532 t = (dataptr[0] << 8) + 0;
hudakz 9:a156d3de5647 533 sum += t;
hudakz 9:a156d3de5647 534 if (sum < t) {
hudakz 9:a156d3de5647 535 sum++; /* carry */
hudakz 9:a156d3de5647 536 }
hudakz 9:a156d3de5647 537 }
hudakz 9:a156d3de5647 538
hudakz 9:a156d3de5647 539 /* Return sum in host byte order. */
hudakz 9:a156d3de5647 540 return sum;
hudakz 9:a156d3de5647 541 }
hudakz 9:a156d3de5647 542
hudakz 9:a156d3de5647 543 /**
hudakz 9:a156d3de5647 544 * @brief
hudakz 9:a156d3de5647 545 * @note
hudakz 9:a156d3de5647 546 * @param
hudakz 9:a156d3de5647 547 * @retval
hudakz 9:a156d3de5647 548 */
hudakz 9:a156d3de5647 549 uint16_t UipEthernet::ipchksum()
hudakz 9:a156d3de5647 550 {
hudakz 9:a156d3de5647 551 uint16_t sum;
hudakz 9:a156d3de5647 552
hudakz 9:a156d3de5647 553 sum = chksum(0, &uip_buf[UIP_LLH_LEN], UIP_IPH_LEN);
hudakz 9:a156d3de5647 554 return(sum == 0) ? 0xffff : htons(sum);
hudakz 9:a156d3de5647 555 }
hudakz 9:a156d3de5647 556
hudakz 9:a156d3de5647 557 uint16_t
hudakz 9:a156d3de5647 558 #if UIP_UDP
hudakz 9:a156d3de5647 559 UipEthernet::upper_layer_chksum(uint8_t proto)
hudakz 9:a156d3de5647 560 #else
hudakz 9:a156d3de5647 561 uip_tcpchksum()
hudakz 9:a156d3de5647 562 #endif
hudakz 9:a156d3de5647 563 {
hudakz 9:a156d3de5647 564 uint16_t upper_layer_len;
hudakz 9:a156d3de5647 565 uint16_t sum;
hudakz 9:a156d3de5647 566
hudakz 9:a156d3de5647 567 #if UIP_CONF_IPV6
hudakz 9:a156d3de5647 568 upper_layer_len = (((u16_t) (BUF->len[0]) << 8) + BUF->len[1]);
hudakz 9:a156d3de5647 569 #else /* UIP_CONF_IPV6 */
hudakz 9:a156d3de5647 570 upper_layer_len = (((u16_t) (BUF->len[0]) << 8) + BUF->len[1]) - UIP_IPH_LEN;
hudakz 9:a156d3de5647 571 #endif /* UIP_CONF_IPV6 */
hudakz 9:a156d3de5647 572
hudakz 9:a156d3de5647 573 /* First sum pseudoheader. */
hudakz 9:a156d3de5647 574
hudakz 9:a156d3de5647 575 /* IP protocol and length fields. This addition cannot carry. */
hudakz 9:a156d3de5647 576 #if UIP_UDP
hudakz 9:a156d3de5647 577 sum = upper_layer_len + proto;
hudakz 9:a156d3de5647 578 #else
hudakz 9:a156d3de5647 579 sum = upper_layer_len + UIP_PROTO_TCP;
hudakz 9:a156d3de5647 580 #endif
hudakz 9:a156d3de5647 581 /* Sum IP source and destination addresses. */
hudakz 9:a156d3de5647 582
hudakz 9:a156d3de5647 583 sum = UipEthernet::chksum(sum, (u8_t*) &BUF->srcipaddr[0], 2 * sizeof(uip_ipaddr_t));
hudakz 9:a156d3de5647 584
hudakz 9:a156d3de5647 585 uint8_t upper_layer_memlen;
hudakz 9:a156d3de5647 586 #if UIP_UDP
hudakz 9:a156d3de5647 587 switch (proto) {
hudakz 9:a156d3de5647 588 // case UIP_PROTO_ICMP:
hudakz 9:a156d3de5647 589 // case UIP_PROTO_ICMP6:
hudakz 9:a156d3de5647 590 // upper_layer_memlen = upper_layer_len;
hudakz 9:a156d3de5647 591 // break;
hudakz 9:a156d3de5647 592 case UIP_PROTO_UDP:
hudakz 9:a156d3de5647 593 upper_layer_memlen = UIP_UDPH_LEN;
hudakz 9:a156d3de5647 594 break;
hudakz 9:a156d3de5647 595
hudakz 9:a156d3de5647 596 default:
hudakz 9:a156d3de5647 597 // case UIP_PROTO_TCP:
hudakz 9:a156d3de5647 598 #endif
hudakz 9:a156d3de5647 599 upper_layer_memlen = (BUF->tcpoffset >> 4) << 2;
hudakz 9:a156d3de5647 600 #if UIP_UDP
hudakz 9:a156d3de5647 601 break;
hudakz 9:a156d3de5647 602 }
hudakz 9:a156d3de5647 603 #endif
hudakz 9:a156d3de5647 604 sum = UipEthernet::chksum(sum, &uip_buf[UIP_IPH_LEN + UIP_LLH_LEN], upper_layer_memlen);
hudakz 9:a156d3de5647 605 #ifdef UIPETHERNET_DEBUG_CHKSUM
hudakz 9:a156d3de5647 606 printf
hudakz 9:a156d3de5647 607 (
hudakz 9:a156d3de5647 608 "chksum uip_buf[%d-%d]: %d\r\n", UIP_IPH_LEN +
hudakz 9:a156d3de5647 609 UIP_LLH_LEN, UIP_IPH_LEN +
hudakz 9:a156d3de5647 610 UIP_LLH_LEN +
hudakz 9:a156d3de5647 611 upper_layer_memlen, htons(sum)
hudakz 9:a156d3de5647 612 );
hudakz 9:a156d3de5647 613 #endif
hudakz 9:a156d3de5647 614 if (upper_layer_memlen < upper_layer_len) {
hudakz 11:647d53d146f1 615 sum = enc28j60Eth.chksum
hudakz 9:a156d3de5647 616 (
hudakz 9:a156d3de5647 617 sum, UipEthernet::uipPacket, UIP_IPH_LEN +
hudakz 9:a156d3de5647 618 UIP_LLH_LEN +
hudakz 9:a156d3de5647 619 upper_layer_memlen, upper_layer_len -
hudakz 9:a156d3de5647 620 upper_layer_memlen
hudakz 9:a156d3de5647 621 );
hudakz 9:a156d3de5647 622 #ifdef UIPETHERNET_DEBUG_CHKSUM
hudakz 9:a156d3de5647 623 printf
hudakz 9:a156d3de5647 624 (
hudakz 9:a156d3de5647 625 "chksum uip_packet(%d)[%d-%d]: %d\r\n", uip_packet, UIP_IPH_LEN +
hudakz 9:a156d3de5647 626 UIP_LLH_LEN +
hudakz 9:a156d3de5647 627 upper_layer_memlen, UIP_IPH_LEN +
hudakz 9:a156d3de5647 628 UIP_LLH_LEN +
hudakz 9:a156d3de5647 629 upper_layer_len, htons(sum)
hudakz 9:a156d3de5647 630 );
hudakz 9:a156d3de5647 631 #endif
hudakz 9:a156d3de5647 632 }
hudakz 9:a156d3de5647 633 return(sum == 0) ? 0xffff : htons(sum);
hudakz 9:a156d3de5647 634 }
hudakz 9:a156d3de5647 635
hudakz 9:a156d3de5647 636 /**
hudakz 9:a156d3de5647 637 * @brief
hudakz 9:a156d3de5647 638 * @note
hudakz 9:a156d3de5647 639 * @param
hudakz 9:a156d3de5647 640 * @retval
hudakz 9:a156d3de5647 641 */
hudakz 9:a156d3de5647 642 uint16_t uip_ipchksum()
hudakz 9:a156d3de5647 643 {
hudakz 9:a156d3de5647 644 return UipEthernet::ethernet->ipchksum();
hudakz 9:a156d3de5647 645 }
hudakz 9:a156d3de5647 646
hudakz 9:a156d3de5647 647 #if UIP_UDP
hudakz 9:a156d3de5647 648
hudakz 9:a156d3de5647 649 /**
hudakz 9:a156d3de5647 650 * @brief
hudakz 9:a156d3de5647 651 * @note
hudakz 9:a156d3de5647 652 * @param
hudakz 9:a156d3de5647 653 * @retval
hudakz 9:a156d3de5647 654 */
hudakz 9:a156d3de5647 655 uint16_t uip_tcpchksum()
hudakz 9:a156d3de5647 656 {
hudakz 9:a156d3de5647 657 uint16_t sum = UipEthernet::ethernet->upper_layer_chksum(UIP_PROTO_TCP);
hudakz 9:a156d3de5647 658
hudakz 9:a156d3de5647 659 return sum;
hudakz 9:a156d3de5647 660 }
hudakz 9:a156d3de5647 661
hudakz 9:a156d3de5647 662 /**
hudakz 9:a156d3de5647 663 * @brief
hudakz 9:a156d3de5647 664 * @note
hudakz 9:a156d3de5647 665 * @param
hudakz 9:a156d3de5647 666 * @retval
hudakz 9:a156d3de5647 667 */
hudakz 9:a156d3de5647 668 uint16_t uip_udpchksum()
hudakz 9:a156d3de5647 669 {
hudakz 9:a156d3de5647 670 uint16_t sum = UipEthernet::ethernet->upper_layer_chksum(UIP_PROTO_UDP);
hudakz 9:a156d3de5647 671
hudakz 9:a156d3de5647 672 return sum;
hudakz 9:a156d3de5647 673 }
hudakz 11:647d53d146f1 674
hudakz 9:a156d3de5647 675 #endif