Free (GPLv2) TCP/IP stack developed by TASS Belgium

Dependents:   lpc1768-picotcp-demo ZeroMQ_PicoTCP_Publisher_demo TCPSocket_HelloWorld_PicoTCP Pico_TCP_UDP_Test ... more

PicoTCP. Copyright (c) 2013 TASS Belgium NV.

Released under the GNU General Public License, version 2.

Different licensing models may exist, at the sole discretion of the Copyright holders.

Official homepage: http://www.picotcp.com

Bug tracker: https://github.com/tass-belgium/picotcp/issues

Development steps:

  • initial integration with mbed RTOS
  • generic mbed Ethernet driver
  • high performance NXP LPC1768 specific Ethernet driver
  • Multi-threading support for mbed RTOS
  • Berkeley sockets and integration with the New Socket API
  • Fork of the apps running on top of the New Socket API
  • Scheduling optimizations
  • Debugging/benchmarking/testing

Demo application (measuring TCP sender performance):

Import programlpc1768-picotcp-demo

A PicoTCP demo app testing the ethernet throughput on the lpc1768 mbed board.

Committer:
tass picotcp@tass.be
Date:
Wed Apr 09 14:31:41 2014 +0200
Revision:
149:5f4cb161cec3
Parent:
138:0a7a449980e6
Child:
150:551effcf6a39
Update from git masterbranch

Who changed what in which revision?

UserRevisionLine numberNew contents of line
tass 68:0847e35d08a6 1 /*********************************************************************
TASS Belgium NV 131:4758606c9316 2 PicoTCP. Copyright (c) 2012 TASS Belgium NV. Some rights reserved.
TASS Belgium NV 131:4758606c9316 3 See LICENSE and COPYING for usage.
tass 68:0847e35d08a6 4
TASS Belgium NV 131:4758606c9316 5 .
tass 68:0847e35d08a6 6
TASS Belgium NV 131:4758606c9316 7 Authors: Daniele Lacamera
TASS Belgium NV 131:4758606c9316 8 *********************************************************************/
tass 68:0847e35d08a6 9
tass 68:0847e35d08a6 10
tass 68:0847e35d08a6 11 #include "pico_config.h"
tass 68:0847e35d08a6 12 #include "pico_frame.h"
tass 68:0847e35d08a6 13 #include "pico_device.h"
tass 68:0847e35d08a6 14 #include "pico_protocol.h"
tass 68:0847e35d08a6 15 #include "pico_stack.h"
tass 68:0847e35d08a6 16 #include "pico_addressing.h"
tass 68:0847e35d08a6 17 #include "pico_dns_client.h"
tass 68:0847e35d08a6 18
tass 68:0847e35d08a6 19 #include "pico_eth.h"
tass 68:0847e35d08a6 20 #include "pico_arp.h"
tass 68:0847e35d08a6 21 #include "pico_ipv4.h"
tass 68:0847e35d08a6 22 #include "pico_ipv6.h"
tass 68:0847e35d08a6 23 #include "pico_icmp4.h"
tass picotcp@tass.be 149:5f4cb161cec3 24 #include "pico_icmp6.h"
tass 68:0847e35d08a6 25 #include "pico_igmp.h"
tass 68:0847e35d08a6 26 #include "pico_udp.h"
tass 68:0847e35d08a6 27 #include "pico_tcp.h"
tass 68:0847e35d08a6 28 #include "pico_socket.h"
tass 68:0847e35d08a6 29 #include "heap.h"
tass 68:0847e35d08a6 30
TASS Belgium NV 131:4758606c9316 31 #define IS_LIMITED_BCAST(f) (((struct pico_ipv4_hdr *) f->net_hdr)->dst.addr == PICO_IP4_BCAST)
tass 68:0847e35d08a6 32
tass picotcp@tass.be 149:5f4cb161cec3 33 const uint8_t PICO_ETHADDR_ALL[6] = {
tass picotcp@tass.be 149:5f4cb161cec3 34 0xff, 0xff, 0xff, 0xff, 0xff, 0xff
tass picotcp@tass.be 149:5f4cb161cec3 35 };
tass picotcp@tass.be 149:5f4cb161cec3 36
tass 68:0847e35d08a6 37 # define PICO_SIZE_MCAST 3
TASS Belgium NV 131:4758606c9316 38 const uint8_t PICO_ETHADDR_MCAST[6] = {
TASS Belgium NV 131:4758606c9316 39 0x01, 0x00, 0x5e, 0x00, 0x00, 0x00
TASS Belgium NV 131:4758606c9316 40 };
tass 68:0847e35d08a6 41
tass picotcp@tass.be 149:5f4cb161cec3 42 #ifdef PICO_SUPPORT_IPV6
tass picotcp@tass.be 149:5f4cb161cec3 43 # define PICO_SIZE_MCAST6 2
tass picotcp@tass.be 149:5f4cb161cec3 44 const uint8_t PICO_ETHADDR_MCAST6[6] = {
tass picotcp@tass.be 149:5f4cb161cec3 45 0x33, 0x33, 0x00, 0x00, 0x00, 0x00
tass picotcp@tass.be 149:5f4cb161cec3 46 };
tass picotcp@tass.be 149:5f4cb161cec3 47 #endif
tass picotcp@tass.be 149:5f4cb161cec3 48
tass picotcp@tass.be 149:5f4cb161cec3 49
tass 128:ae39e6e81531 50 volatile pico_time pico_tick;
tass 68:0847e35d08a6 51 volatile pico_err_t pico_err;
tass 68:0847e35d08a6 52
tass 68:0847e35d08a6 53 static uint32_t _rand_seed;
tass 68:0847e35d08a6 54
tass 68:0847e35d08a6 55 void pico_rand_feed(uint32_t feed)
tass 68:0847e35d08a6 56 {
TASS Belgium NV 131:4758606c9316 57 if (!feed)
TASS Belgium NV 131:4758606c9316 58 return;
TASS Belgium NV 131:4758606c9316 59
TASS Belgium NV 131:4758606c9316 60 _rand_seed *= 1664525;
TASS Belgium NV 131:4758606c9316 61 _rand_seed += 1013904223;
TASS Belgium NV 131:4758606c9316 62 _rand_seed ^= ~(feed);
tass 68:0847e35d08a6 63 }
tass 68:0847e35d08a6 64
tass 68:0847e35d08a6 65 uint32_t pico_rand(void)
tass 68:0847e35d08a6 66 {
TASS Belgium NV 131:4758606c9316 67 pico_rand_feed((uint32_t)pico_tick);
TASS Belgium NV 131:4758606c9316 68 return _rand_seed;
tass 68:0847e35d08a6 69 }
tass 68:0847e35d08a6 70
tass 68:0847e35d08a6 71 /* NOTIFICATIONS: distributed notifications for stack internal errors.
tass 68:0847e35d08a6 72 */
tass 68:0847e35d08a6 73
tass 68:0847e35d08a6 74 int pico_notify_socket_unreachable(struct pico_frame *f)
tass 68:0847e35d08a6 75 {
TASS Belgium NV 131:4758606c9316 76 if (0) {}
TASS Belgium NV 131:4758606c9316 77
TASS Belgium NV 131:4758606c9316 78 #ifdef PICO_SUPPORT_ICMP4
TASS Belgium NV 131:4758606c9316 79 else if (IS_IPV4(f)) {
TASS Belgium NV 131:4758606c9316 80 pico_icmp4_port_unreachable(f);
TASS Belgium NV 131:4758606c9316 81 }
tass 68:0847e35d08a6 82 #endif
TASS Belgium NV 131:4758606c9316 83 #ifdef PICO_SUPPORT_ICMP6
TASS Belgium NV 131:4758606c9316 84 else if (IS_IPV6(f)) {
TASS Belgium NV 131:4758606c9316 85 pico_icmp6_port_unreachable(f);
TASS Belgium NV 131:4758606c9316 86 }
tass 68:0847e35d08a6 87 #endif
tass 68:0847e35d08a6 88
TASS Belgium NV 131:4758606c9316 89 return 0;
tass 68:0847e35d08a6 90 }
tass 68:0847e35d08a6 91
tass 68:0847e35d08a6 92 int pico_notify_proto_unreachable(struct pico_frame *f)
tass 68:0847e35d08a6 93 {
TASS Belgium NV 131:4758606c9316 94 if (0) {}
TASS Belgium NV 131:4758606c9316 95
TASS Belgium NV 131:4758606c9316 96 #ifdef PICO_SUPPORT_ICMP4
TASS Belgium NV 131:4758606c9316 97 else if (IS_IPV4(f)) {
TASS Belgium NV 131:4758606c9316 98 pico_icmp4_proto_unreachable(f);
TASS Belgium NV 131:4758606c9316 99 }
tass 68:0847e35d08a6 100 #endif
TASS Belgium NV 131:4758606c9316 101 #ifdef PICO_SUPPORT_ICMP6
TASS Belgium NV 131:4758606c9316 102 else if (IS_IPV6(f)) {
TASS Belgium NV 131:4758606c9316 103 pico_icmp6_proto_unreachable(f);
TASS Belgium NV 131:4758606c9316 104 }
tass 68:0847e35d08a6 105 #endif
TASS Belgium NV 131:4758606c9316 106 return 0;
tass 68:0847e35d08a6 107 }
tass 68:0847e35d08a6 108
tass 68:0847e35d08a6 109 int pico_notify_dest_unreachable(struct pico_frame *f)
tass 68:0847e35d08a6 110 {
TASS Belgium NV 131:4758606c9316 111 if (0) {}
TASS Belgium NV 131:4758606c9316 112
TASS Belgium NV 131:4758606c9316 113 #ifdef PICO_SUPPORT_ICMP4
TASS Belgium NV 131:4758606c9316 114 else if (IS_IPV4(f)) {
TASS Belgium NV 131:4758606c9316 115 pico_icmp4_dest_unreachable(f);
TASS Belgium NV 131:4758606c9316 116 }
tass 68:0847e35d08a6 117 #endif
TASS Belgium NV 131:4758606c9316 118 #ifdef PICO_SUPPORT_ICMP6
TASS Belgium NV 131:4758606c9316 119 else if (IS_IPV6(f)) {
TASS Belgium NV 131:4758606c9316 120 pico_icmp6_dest_unreachable(f);
TASS Belgium NV 131:4758606c9316 121 }
tass 68:0847e35d08a6 122 #endif
TASS Belgium NV 131:4758606c9316 123 return 0;
tass 68:0847e35d08a6 124 }
tass 68:0847e35d08a6 125
tass 68:0847e35d08a6 126 int pico_notify_ttl_expired(struct pico_frame *f)
tass 68:0847e35d08a6 127 {
TASS Belgium NV 131:4758606c9316 128 if (0) {}
TASS Belgium NV 131:4758606c9316 129
TASS Belgium NV 131:4758606c9316 130 #ifdef PICO_SUPPORT_ICMP4
TASS Belgium NV 131:4758606c9316 131 else if (IS_IPV4(f)) {
TASS Belgium NV 131:4758606c9316 132 pico_icmp4_ttl_expired(f);
TASS Belgium NV 131:4758606c9316 133 }
tass 68:0847e35d08a6 134 #endif
TASS Belgium NV 131:4758606c9316 135 #ifdef PICO_SUPPORT_ICMP6
TASS Belgium NV 131:4758606c9316 136 else if (IS_IPV6(f)) {
TASS Belgium NV 131:4758606c9316 137 pico_icmp6_ttl_expired(f);
TASS Belgium NV 131:4758606c9316 138 }
tass 68:0847e35d08a6 139 #endif
TASS Belgium NV 131:4758606c9316 140 return 0;
tass 68:0847e35d08a6 141 }
tass 68:0847e35d08a6 142
tass 68:0847e35d08a6 143
tass 68:0847e35d08a6 144 /* Transport layer */
tass 70:cd218dd180e5 145 int32_t pico_transport_receive(struct pico_frame *f, uint8_t proto)
tass 68:0847e35d08a6 146 {
TASS Belgium NV 131:4758606c9316 147 int32_t ret = -1;
TASS Belgium NV 131:4758606c9316 148 switch (proto) {
tass 68:0847e35d08a6 149
tass 68:0847e35d08a6 150 #ifdef PICO_SUPPORT_ICMP4
TASS Belgium NV 131:4758606c9316 151 case PICO_PROTO_ICMP4:
TASS Belgium NV 131:4758606c9316 152 ret = pico_enqueue(pico_proto_icmp4.q_in, f);
TASS Belgium NV 131:4758606c9316 153 break;
tass 68:0847e35d08a6 154 #endif
tass 68:0847e35d08a6 155
tass picotcp@tass.be 149:5f4cb161cec3 156 #ifdef PICO_SUPPORT_ICMP6
tass picotcp@tass.be 149:5f4cb161cec3 157 case PICO_PROTO_ICMP6:
tass picotcp@tass.be 149:5f4cb161cec3 158 ret = pico_enqueue(pico_proto_icmp6.q_in, f);
tass picotcp@tass.be 149:5f4cb161cec3 159 break;
tass picotcp@tass.be 149:5f4cb161cec3 160 #endif
tass picotcp@tass.be 149:5f4cb161cec3 161
tass picotcp@tass.be 149:5f4cb161cec3 162
tass 68:0847e35d08a6 163 #ifdef PICO_SUPPORT_IGMP
TASS Belgium NV 131:4758606c9316 164 case PICO_PROTO_IGMP:
TASS Belgium NV 131:4758606c9316 165 ret = pico_enqueue(pico_proto_igmp.q_in, f);
TASS Belgium NV 131:4758606c9316 166 break;
tass 68:0847e35d08a6 167 #endif
tass 68:0847e35d08a6 168
tass 68:0847e35d08a6 169 #ifdef PICO_SUPPORT_UDP
TASS Belgium NV 131:4758606c9316 170 case PICO_PROTO_UDP:
TASS Belgium NV 131:4758606c9316 171 ret = pico_enqueue(pico_proto_udp.q_in, f);
TASS Belgium NV 131:4758606c9316 172 break;
tass 68:0847e35d08a6 173 #endif
tass 68:0847e35d08a6 174
tass 68:0847e35d08a6 175 #ifdef PICO_SUPPORT_TCP
TASS Belgium NV 131:4758606c9316 176 case PICO_PROTO_TCP:
TASS Belgium NV 131:4758606c9316 177 ret = pico_enqueue(pico_proto_tcp.q_in, f);
TASS Belgium NV 131:4758606c9316 178 break;
tass 68:0847e35d08a6 179 #endif
tass 68:0847e35d08a6 180
TASS Belgium NV 131:4758606c9316 181 default:
TASS Belgium NV 131:4758606c9316 182 /* Protocol not available */
TASS Belgium NV 131:4758606c9316 183 dbg("pkt: no such protocol (%d)\n", proto);
TASS Belgium NV 131:4758606c9316 184 pico_notify_proto_unreachable(f);
TASS Belgium NV 131:4758606c9316 185 pico_frame_discard(f);
TASS Belgium NV 131:4758606c9316 186 ret = -1;
TASS Belgium NV 131:4758606c9316 187 }
TASS Belgium NV 131:4758606c9316 188 return ret;
tass 68:0847e35d08a6 189 }
tass 68:0847e35d08a6 190
tass 70:cd218dd180e5 191 int32_t pico_network_receive(struct pico_frame *f)
tass 68:0847e35d08a6 192 {
TASS Belgium NV 131:4758606c9316 193 if (0) {}
TASS Belgium NV 131:4758606c9316 194
tass 68:0847e35d08a6 195 #ifdef PICO_SUPPORT_IPV4
TASS Belgium NV 131:4758606c9316 196 else if (IS_IPV4(f)) {
TASS Belgium NV 131:4758606c9316 197 pico_enqueue(pico_proto_ipv4.q_in, f);
TASS Belgium NV 131:4758606c9316 198 }
tass 68:0847e35d08a6 199 #endif
tass 68:0847e35d08a6 200 #ifdef PICO_SUPPORT_IPV6
TASS Belgium NV 131:4758606c9316 201 else if (IS_IPV6(f)) {
TASS Belgium NV 131:4758606c9316 202 pico_enqueue(pico_proto_ipv6.q_in, f);
TASS Belgium NV 131:4758606c9316 203 }
tass 68:0847e35d08a6 204 #endif
TASS Belgium NV 131:4758606c9316 205 else {
TASS Belgium NV 131:4758606c9316 206 dbg("Network not found.\n");
TASS Belgium NV 131:4758606c9316 207 pico_frame_discard(f);
TASS Belgium NV 131:4758606c9316 208 return -1;
TASS Belgium NV 131:4758606c9316 209 }
TASS Belgium NV 131:4758606c9316 210 return (int32_t)f->buffer_len;
tass 68:0847e35d08a6 211 }
tass 68:0847e35d08a6 212
tass 68:0847e35d08a6 213
tass 68:0847e35d08a6 214 /* Network layer: interface towards socket for frame sending */
tass 88:0e827d0d8017 215 int32_t pico_network_send(struct pico_frame *f)
tass 68:0847e35d08a6 216 {
TASS Belgium NV 131:4758606c9316 217 if (!f || !f->sock || !f->sock->net) {
TASS Belgium NV 131:4758606c9316 218 pico_frame_discard(f);
TASS Belgium NV 131:4758606c9316 219 return -1;
TASS Belgium NV 131:4758606c9316 220 }
TASS Belgium NV 131:4758606c9316 221
TASS Belgium NV 131:4758606c9316 222 return f->sock->net->push(f->sock->net, f);
tass 68:0847e35d08a6 223 }
tass 68:0847e35d08a6 224
tass 68:0847e35d08a6 225 int pico_source_is_local(struct pico_frame *f)
tass 68:0847e35d08a6 226 {
TASS Belgium NV 131:4758606c9316 227 if (0) { }
TASS Belgium NV 131:4758606c9316 228
tass 68:0847e35d08a6 229 #ifdef PICO_SUPPORT_IPV4
TASS Belgium NV 131:4758606c9316 230 else if (IS_IPV4(f)) {
TASS Belgium NV 131:4758606c9316 231 struct pico_ipv4_hdr *hdr = (struct pico_ipv4_hdr *)f->net_hdr;
TASS Belgium NV 131:4758606c9316 232 if (hdr->src.addr == PICO_IPV4_INADDR_ANY)
TASS Belgium NV 131:4758606c9316 233 return 1;
TASS Belgium NV 131:4758606c9316 234
TASS Belgium NV 131:4758606c9316 235 if (pico_ipv4_link_find(&hdr->src))
TASS Belgium NV 131:4758606c9316 236 return 1;
TASS Belgium NV 131:4758606c9316 237 }
tass 68:0847e35d08a6 238 #endif
tass 68:0847e35d08a6 239 #ifdef PICO_SUPPORT_IPV6
TASS Belgium NV 131:4758606c9316 240 else if (IS_IPV6(f)) {
TASS Belgium NV 131:4758606c9316 241 /* XXX */
TASS Belgium NV 131:4758606c9316 242 }
tass 68:0847e35d08a6 243 #endif
TASS Belgium NV 131:4758606c9316 244 return 0;
tass 68:0847e35d08a6 245
tass 68:0847e35d08a6 246
tass 68:0847e35d08a6 247 }
tass 68:0847e35d08a6 248
tass 68:0847e35d08a6 249
tass 68:0847e35d08a6 250 /* DATALINK LEVEL: interface from network to the device
tass 68:0847e35d08a6 251 * and vice versa.
tass 68:0847e35d08a6 252 */
tass 68:0847e35d08a6 253
TASS Belgium NV 131:4758606c9316 254 /* The pico_ethernet_receive() function is used by
TASS Belgium NV 131:4758606c9316 255 * those devices supporting ETH in order to push packets up
TASS Belgium NV 131:4758606c9316 256 * into the stack.
tass 68:0847e35d08a6 257 */
tass picotcp@tass.be 137:a1c8bfa9d691 258
tass picotcp@tass.be 137:a1c8bfa9d691 259 static int32_t pico_ll_receive(struct pico_frame *f)
tass picotcp@tass.be 137:a1c8bfa9d691 260 {
tass picotcp@tass.be 137:a1c8bfa9d691 261 struct pico_eth_hdr *hdr = (struct pico_eth_hdr *) f->datalink_hdr;
tass picotcp@tass.be 137:a1c8bfa9d691 262 f->net_hdr = f->datalink_hdr + sizeof(struct pico_eth_hdr);
tass picotcp@tass.be 149:5f4cb161cec3 263 if (0) { }
tass picotcp@tass.be 149:5f4cb161cec3 264
tass picotcp@tass.be 149:5f4cb161cec3 265 #if (defined PICO_SUPPORT_IPV4) && (defined PICO_SUPPORT_ETH)
tass picotcp@tass.be 149:5f4cb161cec3 266 else if (hdr->proto == PICO_IDETH_ARP)
tass picotcp@tass.be 137:a1c8bfa9d691 267 return pico_arp_receive(f);
tass picotcp@tass.be 149:5f4cb161cec3 268 #endif
tass picotcp@tass.be 149:5f4cb161cec3 269 #if defined (PICO_SUPPORT_IPV4) || defined (PICO_SUPPORT_IPV6)
tass picotcp@tass.be 137:a1c8bfa9d691 270 else if ((hdr->proto == PICO_IDETH_IPV4) || (hdr->proto == PICO_IDETH_IPV6))
tass picotcp@tass.be 137:a1c8bfa9d691 271 return pico_network_receive(f);
tass picotcp@tass.be 149:5f4cb161cec3 272 #endif
tass picotcp@tass.be 137:a1c8bfa9d691 273 else {
tass picotcp@tass.be 137:a1c8bfa9d691 274 pico_frame_discard(f);
tass picotcp@tass.be 137:a1c8bfa9d691 275 return -1;
tass picotcp@tass.be 137:a1c8bfa9d691 276 }
tass picotcp@tass.be 137:a1c8bfa9d691 277 }
tass picotcp@tass.be 137:a1c8bfa9d691 278
tass picotcp@tass.be 137:a1c8bfa9d691 279 static void pico_ll_check_bcast(struct pico_frame *f)
tass picotcp@tass.be 137:a1c8bfa9d691 280 {
tass picotcp@tass.be 137:a1c8bfa9d691 281 struct pico_eth_hdr *hdr = (struct pico_eth_hdr *) f->datalink_hdr;
tass picotcp@tass.be 137:a1c8bfa9d691 282 /* Indicate a link layer broadcast packet */
tass picotcp@tass.be 137:a1c8bfa9d691 283 if (memcmp(hdr->daddr, PICO_ETHADDR_ALL, PICO_SIZE_ETH) == 0)
tass picotcp@tass.be 137:a1c8bfa9d691 284 f->flags |= PICO_FRAME_FLAG_BCAST;
tass picotcp@tass.be 137:a1c8bfa9d691 285 }
tass picotcp@tass.be 137:a1c8bfa9d691 286
tass 70:cd218dd180e5 287 int32_t pico_ethernet_receive(struct pico_frame *f)
tass 68:0847e35d08a6 288 {
TASS Belgium NV 131:4758606c9316 289 struct pico_eth_hdr *hdr;
TASS Belgium NV 131:4758606c9316 290 if (!f || !f->dev || !f->datalink_hdr)
tass picotcp@tass.be 137:a1c8bfa9d691 291 {
tass picotcp@tass.be 137:a1c8bfa9d691 292 pico_frame_discard(f);
tass picotcp@tass.be 137:a1c8bfa9d691 293 return -1;
tass picotcp@tass.be 137:a1c8bfa9d691 294 }
TASS Belgium NV 131:4758606c9316 295
TASS Belgium NV 131:4758606c9316 296 hdr = (struct pico_eth_hdr *) f->datalink_hdr;
TASS Belgium NV 131:4758606c9316 297 if ((memcmp(hdr->daddr, f->dev->eth->mac.addr, PICO_SIZE_ETH) != 0) &&
TASS Belgium NV 131:4758606c9316 298 (memcmp(hdr->daddr, PICO_ETHADDR_MCAST, PICO_SIZE_MCAST) != 0) &&
tass picotcp@tass.be 149:5f4cb161cec3 299 #ifdef PICO_SUPPORT_IPV6
tass picotcp@tass.be 149:5f4cb161cec3 300 (memcmp(hdr->daddr, PICO_ETHADDR_MCAST6, PICO_SIZE_MCAST6) != 0) &&
tass picotcp@tass.be 149:5f4cb161cec3 301 #endif
TASS Belgium NV 131:4758606c9316 302 (memcmp(hdr->daddr, PICO_ETHADDR_ALL, PICO_SIZE_ETH) != 0))
tass picotcp@tass.be 137:a1c8bfa9d691 303 {
tass picotcp@tass.be 137:a1c8bfa9d691 304 pico_frame_discard(f);
tass picotcp@tass.be 137:a1c8bfa9d691 305 return -1;
tass picotcp@tass.be 137:a1c8bfa9d691 306 }
TASS Belgium NV 131:4758606c9316 307
tass picotcp@tass.be 137:a1c8bfa9d691 308 pico_ll_check_bcast(f);
tass 68:0847e35d08a6 309
tass picotcp@tass.be 137:a1c8bfa9d691 310 return pico_ll_receive(f);
tass 68:0847e35d08a6 311 }
tass 68:0847e35d08a6 312
tass 68:0847e35d08a6 313 static int destination_is_bcast(struct pico_frame *f)
tass 68:0847e35d08a6 314 {
TASS Belgium NV 131:4758606c9316 315 if (!f)
TASS Belgium NV 131:4758606c9316 316 return 0;
tass 68:0847e35d08a6 317
TASS Belgium NV 131:4758606c9316 318 if (IS_IPV6(f))
TASS Belgium NV 131:4758606c9316 319 return 0;
TASS Belgium NV 131:4758606c9316 320
tass 68:0847e35d08a6 321 #ifdef PICO_SUPPORT_IPV4
TASS Belgium NV 131:4758606c9316 322 else {
TASS Belgium NV 131:4758606c9316 323 struct pico_ipv4_hdr *hdr = (struct pico_ipv4_hdr *) f->net_hdr;
TASS Belgium NV 131:4758606c9316 324 return pico_ipv4_is_broadcast(hdr->dst.addr);
TASS Belgium NV 131:4758606c9316 325 }
tass picotcp@tass.be 134:cc4e6d2654d9 326 #else
tass picotcp@tass.be 134:cc4e6d2654d9 327 return 0;
tass 68:0847e35d08a6 328 #endif
tass 68:0847e35d08a6 329 }
tass 68:0847e35d08a6 330
tass 68:0847e35d08a6 331 static int destination_is_mcast(struct pico_frame *f)
tass 68:0847e35d08a6 332 {
tass picotcp@tass.be 149:5f4cb161cec3 333 int ret = 0;
TASS Belgium NV 131:4758606c9316 334 if (!f)
TASS Belgium NV 131:4758606c9316 335 return 0;
tass 68:0847e35d08a6 336
tass picotcp@tass.be 149:5f4cb161cec3 337 #ifdef PICO_SUPPORT_IPV6
tass picotcp@tass.be 149:5f4cb161cec3 338 if (IS_IPV6(f)) {
tass picotcp@tass.be 149:5f4cb161cec3 339 struct pico_ipv6_hdr *hdr = (struct pico_ipv6_hdr *) f->net_hdr;
tass picotcp@tass.be 149:5f4cb161cec3 340 ret = pico_ipv6_is_multicast(hdr->dst.addr);
tass picotcp@tass.be 149:5f4cb161cec3 341 }
TASS Belgium NV 131:4758606c9316 342
tass picotcp@tass.be 149:5f4cb161cec3 343 #endif
tass 68:0847e35d08a6 344 #ifdef PICO_SUPPORT_IPV4
TASS Belgium NV 131:4758606c9316 345 else {
TASS Belgium NV 131:4758606c9316 346 struct pico_ipv4_hdr *hdr = (struct pico_ipv4_hdr *) f->net_hdr;
tass picotcp@tass.be 149:5f4cb161cec3 347 ret = pico_ipv4_is_multicast(hdr->dst.addr);
TASS Belgium NV 131:4758606c9316 348 }
tass 68:0847e35d08a6 349 #endif
tass picotcp@tass.be 149:5f4cb161cec3 350
tass picotcp@tass.be 149:5f4cb161cec3 351 return ret;
tass 68:0847e35d08a6 352 }
tass 68:0847e35d08a6 353
tass 68:0847e35d08a6 354 static struct pico_eth *pico_ethernet_mcast_translate(struct pico_frame *f, uint8_t *pico_mcast_mac)
tass 68:0847e35d08a6 355 {
TASS Belgium NV 131:4758606c9316 356 struct pico_ipv4_hdr *hdr = (struct pico_ipv4_hdr *) f->net_hdr;
tass 68:0847e35d08a6 357
TASS Belgium NV 131:4758606c9316 358 /* place 23 lower bits of IP in lower 23 bits of MAC */
tass picotcp@tass.be 149:5f4cb161cec3 359 pico_mcast_mac[5] = (long_be(hdr->dst.addr) & 0x000000FFu);
tass picotcp@tass.be 149:5f4cb161cec3 360 pico_mcast_mac[4] = (uint8_t)((long_be(hdr->dst.addr) & 0x0000FF00u) >> 8u);
tass picotcp@tass.be 149:5f4cb161cec3 361 pico_mcast_mac[3] = (uint8_t)((long_be(hdr->dst.addr) & 0x007F0000u) >> 16u);
tass 68:0847e35d08a6 362
TASS Belgium NV 131:4758606c9316 363 return (struct pico_eth *)pico_mcast_mac;
tass 68:0847e35d08a6 364 }
tass 68:0847e35d08a6 365
tass 68:0847e35d08a6 366
tass picotcp@tass.be 149:5f4cb161cec3 367 #ifdef PICO_SUPPORT_IPV6
tass picotcp@tass.be 149:5f4cb161cec3 368 static struct pico_eth *pico_ethernet_mcast6_translate(struct pico_frame *f, uint8_t *pico_mcast6_mac)
tass picotcp@tass.be 149:5f4cb161cec3 369 {
tass picotcp@tass.be 149:5f4cb161cec3 370 struct pico_ipv6_hdr *hdr = (struct pico_ipv6_hdr *)f->net_hdr;
tass picotcp@tass.be 137:a1c8bfa9d691 371
tass picotcp@tass.be 149:5f4cb161cec3 372 /* first 2 octets are 0x33, last four are the last four of dst */
tass picotcp@tass.be 149:5f4cb161cec3 373 pico_mcast6_mac[5] = hdr->dst.addr[PICO_SIZE_IP6 - 1];
tass picotcp@tass.be 149:5f4cb161cec3 374 pico_mcast6_mac[4] = hdr->dst.addr[PICO_SIZE_IP6 - 2];
tass picotcp@tass.be 149:5f4cb161cec3 375 pico_mcast6_mac[3] = hdr->dst.addr[PICO_SIZE_IP6 - 3];
tass picotcp@tass.be 149:5f4cb161cec3 376 pico_mcast6_mac[2] = hdr->dst.addr[PICO_SIZE_IP6 - 4];
tass picotcp@tass.be 149:5f4cb161cec3 377
tass picotcp@tass.be 149:5f4cb161cec3 378 return (struct pico_eth *)pico_mcast6_mac;
tass picotcp@tass.be 149:5f4cb161cec3 379 }
tass picotcp@tass.be 149:5f4cb161cec3 380 #endif
tass picotcp@tass.be 149:5f4cb161cec3 381
tass picotcp@tass.be 149:5f4cb161cec3 382 struct pico_eth *pico_ethernet_ipv6_dst(struct pico_frame *f)
tass picotcp@tass.be 137:a1c8bfa9d691 383 {
tass picotcp@tass.be 149:5f4cb161cec3 384 struct pico_eth *dstmac = NULL;
tass picotcp@tass.be 149:5f4cb161cec3 385 #ifdef PICO_SUPPORT_IPV6
tass picotcp@tass.be 149:5f4cb161cec3 386 if (destination_is_mcast(f)) {
tass picotcp@tass.be 149:5f4cb161cec3 387 uint8_t pico_mcast6_mac[6] = {
tass picotcp@tass.be 149:5f4cb161cec3 388 0x33, 0x33, 0x00, 0x00, 0x00, 0x00
tass picotcp@tass.be 149:5f4cb161cec3 389 };
tass picotcp@tass.be 149:5f4cb161cec3 390 dstmac = pico_ethernet_mcast6_translate(f, pico_mcast6_mac);
tass picotcp@tass.be 149:5f4cb161cec3 391 } else {
tass picotcp@tass.be 149:5f4cb161cec3 392 dstmac = pico_nd_get(f);
tass picotcp@tass.be 149:5f4cb161cec3 393 }
tass picotcp@tass.be 149:5f4cb161cec3 394
tass picotcp@tass.be 149:5f4cb161cec3 395 #else
tass picotcp@tass.be 137:a1c8bfa9d691 396 (void)f;
tass picotcp@tass.be 149:5f4cb161cec3 397 pico_err = PICO_ERR_EPROTONOSUPPORT;
tass picotcp@tass.be 149:5f4cb161cec3 398 #endif
tass picotcp@tass.be 149:5f4cb161cec3 399 return dstmac;
tass picotcp@tass.be 137:a1c8bfa9d691 400 }
tass picotcp@tass.be 137:a1c8bfa9d691 401
tass picotcp@tass.be 137:a1c8bfa9d691 402
tass 68:0847e35d08a6 403
tass 68:0847e35d08a6 404 /* This is called by dev loop in order to ensure correct ethernet addressing.
tass 68:0847e35d08a6 405 * Returns 0 if the destination is unknown, and -1 if the packet is not deliverable
TASS Belgium NV 131:4758606c9316 406 * due to ethernet addressing (i.e., no arp association was possible.
tass 68:0847e35d08a6 407 *
tass 68:0847e35d08a6 408 * Only IP packets must pass by this. ARP will always use direct dev->send() function, so
tass 68:0847e35d08a6 409 * we assume IP is used.
tass 68:0847e35d08a6 410 */
tass picotcp@tass.be 137:a1c8bfa9d691 411
tass picotcp@tass.be 137:a1c8bfa9d691 412 static int32_t pico_ethsend_local(struct pico_frame *f, struct pico_eth_hdr *hdr, int *ret)
tass picotcp@tass.be 137:a1c8bfa9d691 413 {
tass picotcp@tass.be 137:a1c8bfa9d691 414 /* Check own mac */
tass picotcp@tass.be 137:a1c8bfa9d691 415 if(!memcmp(hdr->daddr, hdr->saddr, PICO_SIZE_ETH)) {
tass picotcp@tass.be 137:a1c8bfa9d691 416 dbg("sending out packet destined for our own mac\n");
tass picotcp@tass.be 137:a1c8bfa9d691 417 *ret = (int32_t)pico_ethernet_receive(f);
tass picotcp@tass.be 137:a1c8bfa9d691 418 return 1;
tass picotcp@tass.be 137:a1c8bfa9d691 419 }
tass picotcp@tass.be 137:a1c8bfa9d691 420
tass picotcp@tass.be 137:a1c8bfa9d691 421 return 0;
tass picotcp@tass.be 137:a1c8bfa9d691 422 }
tass picotcp@tass.be 137:a1c8bfa9d691 423
tass picotcp@tass.be 137:a1c8bfa9d691 424 static int32_t pico_ethsend_bcast(struct pico_frame *f, int *ret)
tass picotcp@tass.be 137:a1c8bfa9d691 425 {
tass picotcp@tass.be 137:a1c8bfa9d691 426 if (IS_LIMITED_BCAST(f)) {
tass picotcp@tass.be 137:a1c8bfa9d691 427 *ret = pico_device_broadcast(f);
tass picotcp@tass.be 137:a1c8bfa9d691 428 return 1;
tass picotcp@tass.be 137:a1c8bfa9d691 429 }
tass picotcp@tass.be 137:a1c8bfa9d691 430
tass picotcp@tass.be 137:a1c8bfa9d691 431 return 0;
tass picotcp@tass.be 137:a1c8bfa9d691 432 }
tass picotcp@tass.be 137:a1c8bfa9d691 433
tass picotcp@tass.be 137:a1c8bfa9d691 434 static int32_t pico_ethsend_dispatch(struct pico_frame *f, int *ret)
tass picotcp@tass.be 137:a1c8bfa9d691 435 {
tass picotcp@tass.be 137:a1c8bfa9d691 436 *ret = f->dev->send(f->dev, f->start, (int) f->len);
tass picotcp@tass.be 137:a1c8bfa9d691 437 if (*ret <= 0)
tass picotcp@tass.be 137:a1c8bfa9d691 438 return 0;
tass picotcp@tass.be 137:a1c8bfa9d691 439 else {
tass picotcp@tass.be 137:a1c8bfa9d691 440 pico_frame_discard(f);
tass picotcp@tass.be 137:a1c8bfa9d691 441 return 1;
tass picotcp@tass.be 137:a1c8bfa9d691 442 }
tass picotcp@tass.be 137:a1c8bfa9d691 443 }
tass picotcp@tass.be 137:a1c8bfa9d691 444
tass 70:cd218dd180e5 445 int32_t pico_ethernet_send(struct pico_frame *f)
tass 68:0847e35d08a6 446 {
TASS Belgium NV 131:4758606c9316 447 const struct pico_eth *dstmac = NULL;
TASS Belgium NV 131:4758606c9316 448 int32_t ret = -1;
tass picotcp@tass.be 149:5f4cb161cec3 449 uint16_t proto = PICO_IDETH_IPV4;
tass 68:0847e35d08a6 450
tass picotcp@tass.be 149:5f4cb161cec3 451 if (IS_IPV6(f)) {
tass picotcp@tass.be 149:5f4cb161cec3 452 dstmac = pico_ethernet_ipv6_dst(f);
tass picotcp@tass.be 149:5f4cb161cec3 453 if (!dstmac)
tass picotcp@tass.be 149:5f4cb161cec3 454 return 0;
tass picotcp@tass.be 137:a1c8bfa9d691 455
tass picotcp@tass.be 149:5f4cb161cec3 456 proto = PICO_IDETH_IPV6;
tass picotcp@tass.be 149:5f4cb161cec3 457 }
tass picotcp@tass.be 149:5f4cb161cec3 458
tass picotcp@tass.be 149:5f4cb161cec3 459 else if (IS_BCAST(f) || destination_is_bcast(f))
tass picotcp@tass.be 137:a1c8bfa9d691 460 dstmac = (const struct pico_eth *) PICO_ETHADDR_ALL;
tass picotcp@tass.be 137:a1c8bfa9d691 461
tass picotcp@tass.be 137:a1c8bfa9d691 462 else if (destination_is_mcast(f)) {
tass picotcp@tass.be 137:a1c8bfa9d691 463 uint8_t pico_mcast_mac[6] = {
tass picotcp@tass.be 137:a1c8bfa9d691 464 0x01, 0x00, 0x5e, 0x00, 0x00, 0x00
tass picotcp@tass.be 137:a1c8bfa9d691 465 };
tass picotcp@tass.be 137:a1c8bfa9d691 466 dstmac = pico_ethernet_mcast_translate(f, pico_mcast_mac);
tass picotcp@tass.be 137:a1c8bfa9d691 467 }
tass picotcp@tass.be 137:a1c8bfa9d691 468 else {
tass picotcp@tass.be 149:5f4cb161cec3 469 #if (defined PICO_SUPPORT_IPV4) && (defined PICO_SUPPORT_ETH)
tass picotcp@tass.be 137:a1c8bfa9d691 470 dstmac = pico_arp_get(f);
tass picotcp@tass.be 137:a1c8bfa9d691 471 if (!dstmac)
tass picotcp@tass.be 149:5f4cb161cec3 472 #endif
tass picotcp@tass.be 149:5f4cb161cec3 473 return 0;
tass 68:0847e35d08a6 474 }
TASS Belgium NV 131:4758606c9316 475
tass picotcp@tass.be 137:a1c8bfa9d691 476 /* This sets destination and source address, then pushes the packet to the device. */
tass picotcp@tass.be 137:a1c8bfa9d691 477 if (dstmac && (f->start > f->buffer) && ((f->start - f->buffer) >= PICO_SIZE_ETHHDR)) {
tass picotcp@tass.be 137:a1c8bfa9d691 478 struct pico_eth_hdr *hdr;
tass picotcp@tass.be 137:a1c8bfa9d691 479 f->start -= PICO_SIZE_ETHHDR;
tass picotcp@tass.be 137:a1c8bfa9d691 480 f->len += PICO_SIZE_ETHHDR;
tass picotcp@tass.be 137:a1c8bfa9d691 481 f->datalink_hdr = f->start;
tass picotcp@tass.be 137:a1c8bfa9d691 482 hdr = (struct pico_eth_hdr *) f->datalink_hdr;
tass picotcp@tass.be 137:a1c8bfa9d691 483 memcpy(hdr->saddr, f->dev->eth->mac.addr, PICO_SIZE_ETH);
tass picotcp@tass.be 137:a1c8bfa9d691 484 memcpy(hdr->daddr, dstmac, PICO_SIZE_ETH);
tass picotcp@tass.be 149:5f4cb161cec3 485 hdr->proto = proto;
tass 68:0847e35d08a6 486
tass picotcp@tass.be 137:a1c8bfa9d691 487 if (pico_ethsend_local(f, hdr, &ret) || pico_ethsend_bcast(f, &ret) || pico_ethsend_dispatch(f, &ret)) {
TASS Belgium NV 131:4758606c9316 488 return ret;
TASS Belgium NV 131:4758606c9316 489 } else {
TASS Belgium NV 131:4758606c9316 490 return -1;
TASS Belgium NV 131:4758606c9316 491 }
tass picotcp@tass.be 137:a1c8bfa9d691 492 }
TASS Belgium NV 131:4758606c9316 493
TASS Belgium NV 131:4758606c9316 494 return -1;
tass 68:0847e35d08a6 495 }
tass 68:0847e35d08a6 496
tass 68:0847e35d08a6 497 void pico_store_network_origin(void *src, struct pico_frame *f)
tass 68:0847e35d08a6 498 {
tass 68:0847e35d08a6 499 #ifdef PICO_SUPPORT_IPV4
TASS Belgium NV 131:4758606c9316 500 struct pico_ip4 *ip4;
tass 68:0847e35d08a6 501 #endif
tass 68:0847e35d08a6 502
tass 68:0847e35d08a6 503 #ifdef PICO_SUPPORT_IPV6
TASS Belgium NV 131:4758606c9316 504 struct pico_ip6 *ip6;
tass 68:0847e35d08a6 505 #endif
tass 68:0847e35d08a6 506
tass 68:0847e35d08a6 507 #ifdef PICO_SUPPORT_IPV4
TASS Belgium NV 131:4758606c9316 508 if (IS_IPV4(f)) {
TASS Belgium NV 131:4758606c9316 509 struct pico_ipv4_hdr *hdr;
TASS Belgium NV 131:4758606c9316 510 hdr = (struct pico_ipv4_hdr *) f->net_hdr;
TASS Belgium NV 131:4758606c9316 511 ip4 = (struct pico_ip4 *) src;
TASS Belgium NV 131:4758606c9316 512 ip4->addr = hdr->src.addr;
TASS Belgium NV 131:4758606c9316 513 }
TASS Belgium NV 131:4758606c9316 514
tass 68:0847e35d08a6 515 #endif
tass 68:0847e35d08a6 516 #ifdef PICO_SUPPORT_IPV6
TASS Belgium NV 131:4758606c9316 517 if (IS_IPV6(f)) {
TASS Belgium NV 131:4758606c9316 518 struct pico_ipv6_hdr *hdr;
TASS Belgium NV 131:4758606c9316 519 hdr = (struct pico_ipv6_hdr *) f->net_hdr;
TASS Belgium NV 131:4758606c9316 520 ip6 = (struct pico_ip6 *) src;
TASS Belgium NV 131:4758606c9316 521 memcpy(ip6->addr, hdr->src.addr, PICO_SIZE_IP6);
TASS Belgium NV 131:4758606c9316 522 }
TASS Belgium NV 131:4758606c9316 523
tass 68:0847e35d08a6 524 #endif
tass 68:0847e35d08a6 525 }
tass 68:0847e35d08a6 526
tass 68:0847e35d08a6 527
tass 68:0847e35d08a6 528 /* LOWEST LEVEL: interface towards devices. */
tass 68:0847e35d08a6 529 /* Device driver will call this function which returns immediately.
tass 68:0847e35d08a6 530 * Incoming packet will be processed later on in the dev loop.
tass 68:0847e35d08a6 531 */
tass 70:cd218dd180e5 532 int32_t pico_stack_recv(struct pico_device *dev, uint8_t *buffer, uint32_t len)
tass 68:0847e35d08a6 533 {
TASS Belgium NV 131:4758606c9316 534 struct pico_frame *f;
TASS Belgium NV 131:4758606c9316 535 int32_t ret;
TASS Belgium NV 131:4758606c9316 536 if (len <= 0)
TASS Belgium NV 131:4758606c9316 537 return -1;
tass 68:0847e35d08a6 538
TASS Belgium NV 131:4758606c9316 539 f = pico_frame_alloc(len);
TASS Belgium NV 131:4758606c9316 540 if (!f)
tass picotcp@tass.be 137:a1c8bfa9d691 541 {
tass picotcp@tass.be 137:a1c8bfa9d691 542 dbg("Cannot alloc incoming frame!\n");
TASS Belgium NV 131:4758606c9316 543 return -1;
tass picotcp@tass.be 137:a1c8bfa9d691 544 }
TASS Belgium NV 131:4758606c9316 545
TASS Belgium NV 131:4758606c9316 546 /* Association to the device that just received the frame. */
TASS Belgium NV 131:4758606c9316 547 f->dev = dev;
tass 68:0847e35d08a6 548
tass picotcp@tass.be 137:a1c8bfa9d691 549 /* Setup the start pointer, length. */
TASS Belgium NV 131:4758606c9316 550 f->start = f->buffer;
TASS Belgium NV 131:4758606c9316 551 f->len = f->buffer_len;
TASS Belgium NV 131:4758606c9316 552 if (f->len > 8) {
TASS Belgium NV 131:4758606c9316 553 uint32_t mid_frame = (f->buffer_len >> 2) << 1;
TASS Belgium NV 131:4758606c9316 554 mid_frame -= (mid_frame % 4);
TASS Belgium NV 131:4758606c9316 555 pico_rand_feed(*(uint32_t*)(f->buffer + mid_frame));
TASS Belgium NV 131:4758606c9316 556 }
TASS Belgium NV 131:4758606c9316 557
TASS Belgium NV 131:4758606c9316 558 memcpy(f->buffer, buffer, len);
TASS Belgium NV 131:4758606c9316 559 ret = pico_enqueue(dev->q_in, f);
TASS Belgium NV 131:4758606c9316 560 if (ret <= 0) {
TASS Belgium NV 131:4758606c9316 561 pico_frame_discard(f);
TASS Belgium NV 131:4758606c9316 562 }
TASS Belgium NV 131:4758606c9316 563
TASS Belgium NV 131:4758606c9316 564 return ret;
tass 68:0847e35d08a6 565 }
tass 68:0847e35d08a6 566
tass picotcp@tass.be 149:5f4cb161cec3 567 int32_t pico_stack_recv_zerocopy(struct pico_device *dev, uint8_t *buffer, uint32_t len)
tass picotcp@tass.be 149:5f4cb161cec3 568 {
tass picotcp@tass.be 149:5f4cb161cec3 569 struct pico_frame *f;
tass picotcp@tass.be 149:5f4cb161cec3 570 int ret;
tass picotcp@tass.be 149:5f4cb161cec3 571 if (len <= 0)
tass picotcp@tass.be 149:5f4cb161cec3 572 return -1;
tass picotcp@tass.be 149:5f4cb161cec3 573
tass picotcp@tass.be 149:5f4cb161cec3 574 f = pico_frame_alloc_skeleton(len);
tass picotcp@tass.be 149:5f4cb161cec3 575 if (!f)
tass picotcp@tass.be 149:5f4cb161cec3 576 {
tass picotcp@tass.be 149:5f4cb161cec3 577 dbg("Cannot alloc incoming frame!\n");
tass picotcp@tass.be 149:5f4cb161cec3 578 return -1;
tass picotcp@tass.be 149:5f4cb161cec3 579 }
tass picotcp@tass.be 149:5f4cb161cec3 580
tass picotcp@tass.be 149:5f4cb161cec3 581 if (pico_frame_skeleton_set_buffer(f, buffer) < 0)
tass picotcp@tass.be 149:5f4cb161cec3 582 {
tass picotcp@tass.be 149:5f4cb161cec3 583 dbg("Invalid zero-copy buffer!\n");
tass picotcp@tass.be 149:5f4cb161cec3 584 PICO_FREE(f->usage_count);
tass picotcp@tass.be 149:5f4cb161cec3 585 PICO_FREE(f);
tass picotcp@tass.be 149:5f4cb161cec3 586 return -1;
tass picotcp@tass.be 149:5f4cb161cec3 587 }
tass picotcp@tass.be 149:5f4cb161cec3 588
tass picotcp@tass.be 149:5f4cb161cec3 589 f->dev = dev;
tass picotcp@tass.be 149:5f4cb161cec3 590 ret = pico_enqueue(dev->q_in, f);
tass picotcp@tass.be 149:5f4cb161cec3 591 if (ret <= 0) {
tass picotcp@tass.be 149:5f4cb161cec3 592 pico_frame_discard(f);
tass picotcp@tass.be 149:5f4cb161cec3 593 }
tass picotcp@tass.be 149:5f4cb161cec3 594
tass picotcp@tass.be 149:5f4cb161cec3 595 return ret;
tass picotcp@tass.be 149:5f4cb161cec3 596 }
tass picotcp@tass.be 149:5f4cb161cec3 597
tass 70:cd218dd180e5 598 int32_t pico_sendto_dev(struct pico_frame *f)
tass 68:0847e35d08a6 599 {
TASS Belgium NV 131:4758606c9316 600 if (!f->dev) {
TASS Belgium NV 131:4758606c9316 601 pico_frame_discard(f);
TASS Belgium NV 131:4758606c9316 602 return -1;
TASS Belgium NV 131:4758606c9316 603 } else {
TASS Belgium NV 131:4758606c9316 604 if (f->len > 8) {
TASS Belgium NV 131:4758606c9316 605 uint32_t mid_frame = (f->buffer_len >> 2) << 1;
TASS Belgium NV 131:4758606c9316 606 mid_frame -= (mid_frame % 4);
TASS Belgium NV 131:4758606c9316 607 pico_rand_feed(*(uint32_t*)(f->buffer + mid_frame));
TASS Belgium NV 131:4758606c9316 608 }
TASS Belgium NV 131:4758606c9316 609
TASS Belgium NV 131:4758606c9316 610 return pico_enqueue(f->dev->q_out, f);
tass 68:0847e35d08a6 611 }
tass 68:0847e35d08a6 612 }
tass 68:0847e35d08a6 613
tass 68:0847e35d08a6 614 struct pico_timer
tass 68:0847e35d08a6 615 {
TASS Belgium NV 131:4758606c9316 616 void *arg;
TASS Belgium NV 131:4758606c9316 617 void (*timer)(pico_time timestamp, void *arg);
tass 68:0847e35d08a6 618 };
tass 68:0847e35d08a6 619
tass 70:cd218dd180e5 620 struct pico_timer_ref
tass 70:cd218dd180e5 621 {
TASS Belgium NV 131:4758606c9316 622 pico_time expire;
TASS Belgium NV 131:4758606c9316 623 struct pico_timer *tmr;
tass 70:cd218dd180e5 624 };
tass 68:0847e35d08a6 625
tass 70:cd218dd180e5 626 typedef struct pico_timer_ref pico_timer_ref;
tass 68:0847e35d08a6 627
tass 70:cd218dd180e5 628 DECLARE_HEAP(pico_timer_ref, expire);
tass 70:cd218dd180e5 629
tass 70:cd218dd180e5 630 static heap_pico_timer_ref *Timers;
tass 68:0847e35d08a6 631
tass 68:0847e35d08a6 632 void pico_check_timers(void)
tass 68:0847e35d08a6 633 {
TASS Belgium NV 131:4758606c9316 634 struct pico_timer *t;
TASS Belgium NV 131:4758606c9316 635 struct pico_timer_ref tref_unused, *tref = heap_first(Timers);
TASS Belgium NV 131:4758606c9316 636 pico_tick = PICO_TIME_MS();
TASS Belgium NV 131:4758606c9316 637 while((tref) && (tref->expire < pico_tick)) {
TASS Belgium NV 131:4758606c9316 638 t = tref->tmr;
TASS Belgium NV 131:4758606c9316 639 if (t && t->timer)
TASS Belgium NV 131:4758606c9316 640 t->timer(pico_tick, t->arg);
TASS Belgium NV 131:4758606c9316 641
TASS Belgium NV 131:4758606c9316 642 if (t)
tass picotcp@tass.be 149:5f4cb161cec3 643 PICO_FREE(t);
TASS Belgium NV 131:4758606c9316 644
TASS Belgium NV 131:4758606c9316 645 t = NULL;
TASS Belgium NV 131:4758606c9316 646 heap_peek(Timers, &tref_unused);
TASS Belgium NV 131:4758606c9316 647 tref = heap_first(Timers);
TASS Belgium NV 131:4758606c9316 648 }
tass 70:cd218dd180e5 649 }
tass 70:cd218dd180e5 650
tass 70:cd218dd180e5 651 void pico_timer_cancel(struct pico_timer *t)
tass 70:cd218dd180e5 652 {
TASS Belgium NV 131:4758606c9316 653 uint32_t i;
TASS Belgium NV 131:4758606c9316 654 struct pico_timer_ref *tref = Timers->top;
TASS Belgium NV 131:4758606c9316 655 if (!t)
TASS Belgium NV 131:4758606c9316 656 return;
TASS Belgium NV 131:4758606c9316 657
TASS Belgium NV 131:4758606c9316 658 for (i = 1; i <= Timers->n; i++) {
TASS Belgium NV 131:4758606c9316 659 if (tref[i].tmr == t) {
TASS Belgium NV 131:4758606c9316 660 Timers->top[i].tmr = NULL;
tass picotcp@tass.be 149:5f4cb161cec3 661 PICO_FREE(t);
TASS Belgium NV 131:4758606c9316 662 break;
TASS Belgium NV 131:4758606c9316 663 }
tass 70:cd218dd180e5 664 }
tass 68:0847e35d08a6 665 }
tass 68:0847e35d08a6 666
tass 68:0847e35d08a6 667 #define PROTO_DEF_NR 11
tass 68:0847e35d08a6 668 #define PROTO_DEF_AVG_NR 4
tass 68:0847e35d08a6 669 #define PROTO_DEF_SCORE 32
tass 68:0847e35d08a6 670 #define PROTO_MIN_SCORE 32
tass 68:0847e35d08a6 671 #define PROTO_MAX_SCORE 128
tass 68:0847e35d08a6 672 #define PROTO_LAT_IND 3 /* latecy indication 0-3 (lower is better latency performance), x1, x2, x4, x8 */
TASS Belgium NV 131:4758606c9316 673 #define PROTO_MAX_LOOP (PROTO_MAX_SCORE << PROTO_LAT_IND) /* max global loop score, so per tick */
tass 68:0847e35d08a6 674
tass 68:0847e35d08a6 675 static int calc_score(int *score, int *index, int avg[][PROTO_DEF_AVG_NR], int *ret)
tass 68:0847e35d08a6 676 {
TASS Belgium NV 131:4758606c9316 677 int temp, i, j, sum;
TASS Belgium NV 131:4758606c9316 678 int max_total = PROTO_MAX_LOOP, total = 0;
tass 68:0847e35d08a6 679
TASS Belgium NV 131:4758606c9316 680 /* dbg("USED SCORES> "); */
tass 68:0847e35d08a6 681
TASS Belgium NV 131:4758606c9316 682 for (i = 0; i < PROTO_DEF_NR; i++) {
tass 68:0847e35d08a6 683
TASS Belgium NV 131:4758606c9316 684 /* if used looped score */
TASS Belgium NV 131:4758606c9316 685 if (ret[i] < score[i]) {
TASS Belgium NV 131:4758606c9316 686 temp = score[i] - ret[i]; /* remaining loop score */
TASS Belgium NV 131:4758606c9316 687
TASS Belgium NV 131:4758606c9316 688 /* dbg("%3d - ",temp); */
tass 68:0847e35d08a6 689
TASS Belgium NV 131:4758606c9316 690 if (index[i] >= PROTO_DEF_AVG_NR)
TASS Belgium NV 131:4758606c9316 691 index[i] = 0; /* reset index */
TASS Belgium NV 131:4758606c9316 692
TASS Belgium NV 131:4758606c9316 693 j = index[i];
TASS Belgium NV 131:4758606c9316 694 avg[i][j] = temp;
tass 68:0847e35d08a6 695
TASS Belgium NV 131:4758606c9316 696 index[i]++;
tass 68:0847e35d08a6 697
tass picotcp@tass.be 149:5f4cb161cec3 698 if (ret[i] == 0 && ((score[i] * 2) <= PROTO_MAX_SCORE) && ((total + (score[i] * 2)) < max_total)) { /* used all loop score -> increase next score directly */
tass picotcp@tass.be 149:5f4cb161cec3 699 score[i] *= 2;
TASS Belgium NV 131:4758606c9316 700 total += score[i];
TASS Belgium NV 131:4758606c9316 701 continue;
TASS Belgium NV 131:4758606c9316 702 }
tass 68:0847e35d08a6 703
TASS Belgium NV 131:4758606c9316 704 sum = 0;
TASS Belgium NV 131:4758606c9316 705 for (j = 0; j < PROTO_DEF_AVG_NR; j++)
TASS Belgium NV 131:4758606c9316 706 sum += avg[i][j]; /* calculate sum */
tass 68:0847e35d08a6 707
tass picotcp@tass.be 149:5f4cb161cec3 708 sum /= 4; /* divide by 4 to get average used score */
tass 68:0847e35d08a6 709
TASS Belgium NV 131:4758606c9316 710 /* criterion to increase next loop score */
tass picotcp@tass.be 149:5f4cb161cec3 711 if (sum > (score[i] - (score[i] / 4)) && ((score[i] * 2) <= PROTO_MAX_SCORE) && ((total + (score[i] / 2)) < max_total)) { /* > 3/4 */
tass picotcp@tass.be 149:5f4cb161cec3 712 score[i] *= 2; /* double loop score */
TASS Belgium NV 131:4758606c9316 713 total += score[i];
TASS Belgium NV 131:4758606c9316 714 continue;
TASS Belgium NV 131:4758606c9316 715 }
tass 68:0847e35d08a6 716
TASS Belgium NV 131:4758606c9316 717 /* criterion to decrease next loop score */
tass picotcp@tass.be 149:5f4cb161cec3 718 if ((sum < (score[i] / 4)) && ((score[i] / 2) >= PROTO_MIN_SCORE)) { /* < 1/4 */
tass picotcp@tass.be 149:5f4cb161cec3 719 score[i] /= 2; /* half loop score */
TASS Belgium NV 131:4758606c9316 720 total += score[i];
TASS Belgium NV 131:4758606c9316 721 continue;
TASS Belgium NV 131:4758606c9316 722 }
tass 68:0847e35d08a6 723
TASS Belgium NV 131:4758606c9316 724 /* also add non-changed scores */
TASS Belgium NV 131:4758606c9316 725 total += score[i];
TASS Belgium NV 131:4758606c9316 726 }
TASS Belgium NV 131:4758606c9316 727 else if (ret[i] == score[i]) {
TASS Belgium NV 131:4758606c9316 728 /* no used loop score - gradually decrease */
tass 68:0847e35d08a6 729
TASS Belgium NV 131:4758606c9316 730 /* dbg("%3d - ",0); */
TASS Belgium NV 131:4758606c9316 731
TASS Belgium NV 131:4758606c9316 732 if (index[i] >= PROTO_DEF_AVG_NR)
TASS Belgium NV 131:4758606c9316 733 index[i] = 0; /* reset index */
TASS Belgium NV 131:4758606c9316 734
TASS Belgium NV 131:4758606c9316 735 j = index[i];
TASS Belgium NV 131:4758606c9316 736 avg[i][j] = 0;
tass 68:0847e35d08a6 737
TASS Belgium NV 131:4758606c9316 738 index[i]++;
tass 68:0847e35d08a6 739
TASS Belgium NV 131:4758606c9316 740 sum = 0;
TASS Belgium NV 131:4758606c9316 741 for (j = 0; j < PROTO_DEF_AVG_NR; j++)
TASS Belgium NV 131:4758606c9316 742 sum += avg[i][j]; /* calculate sum */
tass 68:0847e35d08a6 743
tass picotcp@tass.be 149:5f4cb161cec3 744 sum /= 2; /* divide by 4 to get average used score */
tass 68:0847e35d08a6 745
tass picotcp@tass.be 149:5f4cb161cec3 746 if ((sum == 0) && ((score[i] / 2) >= PROTO_MIN_SCORE)) {
tass picotcp@tass.be 149:5f4cb161cec3 747 score[i] /= 2; /* half loop score */
TASS Belgium NV 131:4758606c9316 748 total += score[i];
TASS Belgium NV 131:4758606c9316 749 for (j = 0; j < PROTO_DEF_AVG_NR; j++)
TASS Belgium NV 131:4758606c9316 750 avg[i][j] = score[i];
TASS Belgium NV 131:4758606c9316 751 }
TASS Belgium NV 131:4758606c9316 752
TASS Belgium NV 131:4758606c9316 753 }
tass 68:0847e35d08a6 754 }
TASS Belgium NV 131:4758606c9316 755 /* dbg("\n"); */
tass 68:0847e35d08a6 756
TASS Belgium NV 131:4758606c9316 757 return 0;
tass 68:0847e35d08a6 758 }
tass 68:0847e35d08a6 759
tass 68:0847e35d08a6 760
tass 68:0847e35d08a6 761
TASS Belgium NV 131:4758606c9316 762 /*
tass 68:0847e35d08a6 763
TASS Belgium NV 131:4758606c9316 764 .
TASS Belgium NV 131:4758606c9316 765 .vS.
TASS Belgium NV 131:4758606c9316 766 <aoSo.
TASS Belgium NV 131:4758606c9316 767 .XoS22.
TASS Belgium NV 131:4758606c9316 768 .S2S22. ._... ...... ..._.
TASS Belgium NV 131:4758606c9316 769 :=|2S2X2|=++; <vSX2XX2z+ |vSSSXSSs>. :iXXZUZXXe=
TASS Belgium NV 131:4758606c9316 770 )2SS2SS2S2S2I =oS2S2S2S2X22;. _vuXS22S2S2S22i ._wZZXZZZXZZXZX=
TASS Belgium NV 131:4758606c9316 771 )22S2S2S2S2Sl |S2S2S22S2SSSXc: .S2SS2S2S22S2SS= .]#XZZZXZXZZZZZZ:
TASS Belgium NV 131:4758606c9316 772 )oSS2SS2S2Sol |2}!"""!32S22S(. uS2S2Se**12oS2e ]dXZZXX2?YYXXXZ*
TASS Belgium NV 131:4758606c9316 773 .:2S2So:..-. . :]S2S2e;=X2SS2o .)oc ]XZZXZ( =nX:
TASS Belgium NV 131:4758606c9316 774 .S2S22. ___s_i,.)oS2So(;2SS2So, ` 3XZZZZc, -
TASS Belgium NV 131:4758606c9316 775 .S2SSo. =oXXXSSS2XoS2S2o( XS2S2XSos;. ]ZZZZXXXX|=
TASS Belgium NV 131:4758606c9316 776 .S2S22. .)S2S2S22S2S2S2S2o( "X2SS2S2S2Sus,, +3XZZZZZXZZoos_
TASS Belgium NV 131:4758606c9316 777 .S2S22. .]2S2SS22S222S2SS2o( ]S22S2S2S222So :3XXZZZZZZZZXXv
TASS Belgium NV 131:4758606c9316 778 .S2S22. =u2SS2e"~---"{2S2So( -"12S2S2SSS2Su. "?SXXXZXZZZZXo
TASS Belgium NV 131:4758606c9316 779 .S2SSo. )SS22z; :S2S2o( ={vS2S2S22v .<vXZZZZZZZ;
TASS Belgium NV 131:4758606c9316 780 .S2S2S: ]oSS2c; =22S2o( -"S2SS2n ~4XXZXZ(
TASS Belgium NV 131:4758606c9316 781 .2S2S2i )2S2S2[. .)XS2So( <;. .2S2S2o :<. ]XZZZX(
TASS Belgium NV 131:4758606c9316 782 nX2S2S,,_s_=3oSS2SoaasuXXS2S2o( .oXoasi_aioSSS22l.]dZoaas_aadXZZXZ'
TASS Belgium NV 131:4758606c9316 783 vS2SSSXXX2; )S2S2S2SoS2S2S2S2o( iS2S222XSoSS22So.)nXZZXXXZZXXZZXZo
TASS Belgium NV 131:4758606c9316 784 x32S22S2Sn -+S2S2S2S2So22S2So( 12S2SS2S2SS22S}- )SXXZZZZZZZZZXX!-
TASS Belgium NV 131:4758606c9316 785 .)S22222i .i2S2S2o>;:S2S2o( .<vSoSoSo2S(; :nXXXXXZXXX(
TASS Belgium NV 131:4758606c9316 786 .-~~~~- --- . - - --~~~-- --^^~~-
TASS Belgium NV 131:4758606c9316 787 .
tass 68:0847e35d08a6 788
tass 68:0847e35d08a6 789
TASS Belgium NV 131:4758606c9316 790 ... curious about our source code? We are hiring! mailto:<recruiting@tass.be>
TASS Belgium NV 131:4758606c9316 791
TASS Belgium NV 131:4758606c9316 792
TASS Belgium NV 131:4758606c9316 793 */
tass 68:0847e35d08a6 794
tass 68:0847e35d08a6 795 void pico_stack_tick(void)
tass 68:0847e35d08a6 796 {
TASS Belgium NV 131:4758606c9316 797 static int score[PROTO_DEF_NR] = {
TASS Belgium NV 131:4758606c9316 798 PROTO_DEF_SCORE, PROTO_DEF_SCORE, PROTO_DEF_SCORE, PROTO_DEF_SCORE, PROTO_DEF_SCORE, PROTO_DEF_SCORE, PROTO_DEF_SCORE, PROTO_DEF_SCORE, PROTO_DEF_SCORE, PROTO_DEF_SCORE, PROTO_DEF_SCORE
TASS Belgium NV 131:4758606c9316 799 };
TASS Belgium NV 131:4758606c9316 800 static int index[PROTO_DEF_NR] = {
TASS Belgium NV 131:4758606c9316 801 0, 0, 0, 0, 0, 0
TASS Belgium NV 131:4758606c9316 802 };
tass 68:0847e35d08a6 803 static int avg[PROTO_DEF_NR][PROTO_DEF_AVG_NR];
TASS Belgium NV 131:4758606c9316 804 static int ret[PROTO_DEF_NR] = {
TASS Belgium NV 131:4758606c9316 805 0
TASS Belgium NV 131:4758606c9316 806 };
tass 68:0847e35d08a6 807
tass 68:0847e35d08a6 808 pico_check_timers();
tass 68:0847e35d08a6 809
TASS Belgium NV 131:4758606c9316 810 /* dbg("LOOP_SCORES> %3d - %3d - %3d - %3d - %3d - %3d - %3d - %3d - %3d - %3d - %3d\n",score[0],score[1],score[2],score[3],score[4],score[5],score[6],score[7],score[8],score[9],score[10]); */
tass 68:0847e35d08a6 811
TASS Belgium NV 131:4758606c9316 812 /* score = pico_protocols_loop(100); */
tass 68:0847e35d08a6 813
TASS Belgium NV 131:4758606c9316 814 ret[0] = pico_devices_loop(score[0], PICO_LOOP_DIR_IN);
tass 70:cd218dd180e5 815 pico_rand_feed((uint32_t)ret[0]);
tass 68:0847e35d08a6 816
tass 68:0847e35d08a6 817 ret[1] = pico_protocol_datalink_loop(score[1], PICO_LOOP_DIR_IN);
tass 70:cd218dd180e5 818 pico_rand_feed((uint32_t)ret[1]);
tass 68:0847e35d08a6 819
tass 68:0847e35d08a6 820 ret[2] = pico_protocol_network_loop(score[2], PICO_LOOP_DIR_IN);
tass 70:cd218dd180e5 821 pico_rand_feed((uint32_t)ret[2]);
tass 68:0847e35d08a6 822
tass 68:0847e35d08a6 823 ret[3] = pico_protocol_transport_loop(score[3], PICO_LOOP_DIR_IN);
tass 70:cd218dd180e5 824 pico_rand_feed((uint32_t)ret[3]);
tass 68:0847e35d08a6 825
tass 68:0847e35d08a6 826
tass 68:0847e35d08a6 827 ret[5] = score[5];
tass 68:0847e35d08a6 828 #if defined (PICO_SUPPORT_IPV4) || defined (PICO_SUPPORT_IPV6)
tass 68:0847e35d08a6 829 #if defined (PICO_SUPPORT_TCP) || defined (PICO_SUPPORT_UDP)
TASS Belgium NV 131:4758606c9316 830 ret[5] = pico_sockets_loop(score[5]); /* swapped */
tass 70:cd218dd180e5 831 pico_rand_feed((uint32_t)ret[5]);
tass 68:0847e35d08a6 832 #endif
tass 68:0847e35d08a6 833 #endif
tass 68:0847e35d08a6 834
tass 68:0847e35d08a6 835 ret[4] = pico_protocol_socket_loop(score[4], PICO_LOOP_DIR_IN);
tass 70:cd218dd180e5 836 pico_rand_feed((uint32_t)ret[4]);
tass 68:0847e35d08a6 837
tass 68:0847e35d08a6 838
tass 68:0847e35d08a6 839 ret[6] = pico_protocol_socket_loop(score[6], PICO_LOOP_DIR_OUT);
tass 70:cd218dd180e5 840 pico_rand_feed((uint32_t)ret[6]);
tass 68:0847e35d08a6 841
tass 68:0847e35d08a6 842 ret[7] = pico_protocol_transport_loop(score[7], PICO_LOOP_DIR_OUT);
tass 70:cd218dd180e5 843 pico_rand_feed((uint32_t)ret[7]);
tass 68:0847e35d08a6 844
tass 68:0847e35d08a6 845 ret[8] = pico_protocol_network_loop(score[8], PICO_LOOP_DIR_OUT);
tass 70:cd218dd180e5 846 pico_rand_feed((uint32_t)ret[8]);
tass 68:0847e35d08a6 847
tass 68:0847e35d08a6 848 ret[9] = pico_protocol_datalink_loop(score[9], PICO_LOOP_DIR_OUT);
tass 70:cd218dd180e5 849 pico_rand_feed((uint32_t)ret[9]);
tass 68:0847e35d08a6 850
TASS Belgium NV 131:4758606c9316 851 ret[10] = pico_devices_loop(score[10], PICO_LOOP_DIR_OUT);
tass 70:cd218dd180e5 852 pico_rand_feed((uint32_t)ret[10]);
tass 68:0847e35d08a6 853
tass 68:0847e35d08a6 854 /* calculate new loop scores for next iteration */
TASS Belgium NV 131:4758606c9316 855 calc_score(score, index, (int (*)[])avg, ret);
tass 68:0847e35d08a6 856 }
tass 68:0847e35d08a6 857
tass 68:0847e35d08a6 858 void pico_stack_loop(void)
tass 68:0847e35d08a6 859 {
TASS Belgium NV 131:4758606c9316 860 while(1) {
TASS Belgium NV 131:4758606c9316 861 pico_stack_tick();
TASS Belgium NV 131:4758606c9316 862 PICO_IDLE();
TASS Belgium NV 131:4758606c9316 863 }
tass 68:0847e35d08a6 864 }
tass 68:0847e35d08a6 865
tass 128:ae39e6e81531 866 struct pico_timer *pico_timer_add(pico_time expire, void (*timer)(pico_time, void *), void *arg)
tass 68:0847e35d08a6 867 {
tass picotcp@tass.be 149:5f4cb161cec3 868 struct pico_timer *t = PICO_ZALLOC(sizeof(struct pico_timer));
TASS Belgium NV 131:4758606c9316 869 struct pico_timer_ref tref;
TASS Belgium NV 131:4758606c9316 870 if (!t) {
TASS Belgium NV 131:4758606c9316 871 pico_err = PICO_ERR_ENOMEM;
TASS Belgium NV 131:4758606c9316 872 return NULL;
TASS Belgium NV 131:4758606c9316 873 }
TASS Belgium NV 131:4758606c9316 874
TASS Belgium NV 131:4758606c9316 875 tref.expire = PICO_TIME_MS() + expire;
TASS Belgium NV 131:4758606c9316 876 t->arg = arg;
TASS Belgium NV 131:4758606c9316 877 t->timer = timer;
TASS Belgium NV 131:4758606c9316 878 tref.tmr = t;
tass picotcp@tass.be 138:0a7a449980e6 879 heap_insert(Timers, &tref);
TASS Belgium NV 131:4758606c9316 880 if (Timers->n > PICO_MAX_TIMERS) {
tass picotcp@tass.be 149:5f4cb161cec3 881 dbg("Warning: I have %d timers\n", Timers->n);
TASS Belgium NV 131:4758606c9316 882 }
TASS Belgium NV 131:4758606c9316 883
TASS Belgium NV 131:4758606c9316 884 return t;
tass 68:0847e35d08a6 885 }
tass 68:0847e35d08a6 886
tass picotcp@tass.be 149:5f4cb161cec3 887 int pico_stack_init(void)
tass 68:0847e35d08a6 888 {
tass 68:0847e35d08a6 889
tass 68:0847e35d08a6 890 #ifdef PICO_SUPPORT_IPV4
TASS Belgium NV 131:4758606c9316 891 pico_protocol_init(&pico_proto_ipv4);
tass 68:0847e35d08a6 892 #endif
tass 68:0847e35d08a6 893
tass 68:0847e35d08a6 894 #ifdef PICO_SUPPORT_IPV6
TASS Belgium NV 131:4758606c9316 895 pico_protocol_init(&pico_proto_ipv6);
tass 68:0847e35d08a6 896 #endif
tass 68:0847e35d08a6 897
tass 68:0847e35d08a6 898 #ifdef PICO_SUPPORT_ICMP4
TASS Belgium NV 131:4758606c9316 899 pico_protocol_init(&pico_proto_icmp4);
tass 68:0847e35d08a6 900 #endif
tass 68:0847e35d08a6 901
tass picotcp@tass.be 149:5f4cb161cec3 902 #ifdef PICO_SUPPORT_ICMP6
tass picotcp@tass.be 149:5f4cb161cec3 903 pico_protocol_init(&pico_proto_icmp6);
tass picotcp@tass.be 149:5f4cb161cec3 904 #endif
tass picotcp@tass.be 149:5f4cb161cec3 905
tass 68:0847e35d08a6 906 #ifdef PICO_SUPPORT_IGMP
TASS Belgium NV 131:4758606c9316 907 pico_protocol_init(&pico_proto_igmp);
tass 68:0847e35d08a6 908 #endif
tass 68:0847e35d08a6 909
tass 68:0847e35d08a6 910 #ifdef PICO_SUPPORT_UDP
TASS Belgium NV 131:4758606c9316 911 pico_protocol_init(&pico_proto_udp);
tass 68:0847e35d08a6 912 #endif
tass 68:0847e35d08a6 913
tass 68:0847e35d08a6 914 #ifdef PICO_SUPPORT_TCP
TASS Belgium NV 131:4758606c9316 915 pico_protocol_init(&pico_proto_tcp);
tass 68:0847e35d08a6 916 #endif
tass 68:0847e35d08a6 917
tass 68:0847e35d08a6 918 #ifdef PICO_SUPPORT_DNS_CLIENT
TASS Belgium NV 131:4758606c9316 919 pico_dns_client_init();
tass 68:0847e35d08a6 920 #endif
tass 68:0847e35d08a6 921
TASS Belgium NV 131:4758606c9316 922 pico_rand_feed(123456);
tass 68:0847e35d08a6 923
TASS Belgium NV 131:4758606c9316 924 /* Initialize timer heap */
TASS Belgium NV 131:4758606c9316 925 Timers = heap_init();
tass picotcp@tass.be 149:5f4cb161cec3 926 if (!Timers)
tass picotcp@tass.be 149:5f4cb161cec3 927 return -1;
tass picotcp@tass.be 149:5f4cb161cec3 928
tass picotcp@tass.be 149:5f4cb161cec3 929 #if ((defined PICO_SUPPORT_IPV4) && (defined PICO_SUPPORT_ETH))
tass picotcp@tass.be 149:5f4cb161cec3 930 /* Initialize ARP module */
tass picotcp@tass.be 133:5b075f5e141a 931 pico_arp_init();
tass picotcp@tass.be 149:5f4cb161cec3 932 #endif
tass picotcp@tass.be 149:5f4cb161cec3 933
tass picotcp@tass.be 149:5f4cb161cec3 934 #ifdef PICO_SUPPORT_IPV6
tass picotcp@tass.be 149:5f4cb161cec3 935 /* Initialize Neighbor discovery module */
tass picotcp@tass.be 149:5f4cb161cec3 936 pico_ipv6_nd_init();
tass picotcp@tass.be 149:5f4cb161cec3 937 #endif
TASS Belgium NV 131:4758606c9316 938 pico_stack_tick();
TASS Belgium NV 131:4758606c9316 939 pico_stack_tick();
TASS Belgium NV 131:4758606c9316 940 pico_stack_tick();
tass picotcp@tass.be 149:5f4cb161cec3 941 return 0;
tass 68:0847e35d08a6 942 }
tass 68:0847e35d08a6 943