xref: /nrf52832-nimble/rt-thread/components/net/uip/doc/uip-doc.txt (revision 104654410c56c573564690304ae786df310c91fc)
1
2
3/**
4\mainpage The uIP TCP/IP stack
5\author Adam Dunkels, http://www.sics.se/~adam/
6
7The uIP TCP/IP stack is intended to make it possible to communicate
8using the TCP/IP protocol suite even on small 8-bit
9micro-controllers. Despite being small and simple, uIP do not require
10their peers to have complex, full-size stacks, but can communicate
11with peers running a similarly light-weight stack. The code size is on
12the order of a few kilobytes and RAM usage can be configured to be as
13low as a few hundred bytes.
14
15uIP can be found at the uIP web page: http://www.sics.se/~adam/uip/
16
17\sa \ref apps "Application programs"
18\sa \ref uipopt "Compile-time configuration options"
19\sa \ref uipconffunc "Run-time configuration functions"
20\sa \ref uipinit "Initialization functions"
21\sa \ref uipdevfunc "Device driver interface" and
22    \ref uipdrivervars "variables used by device drivers"
23\sa \ref uipappfunc "uIP functions called from application programs"
24(see below) and the \ref psock "protosockets API" and their underlying
25\ref pt "protothreads"
26
27\section uIPIntroduction Introduction
28
29With the success of the Internet, the TCP/IP protocol suite has become
30a global standard for communication. TCP/IP is the underlying protocol
31used for web page transfers, e-mail transmissions, file transfers, and
32peer-to-peer networking over the Internet. For embedded systems, being
33able to run native TCP/IP makes it possible to connect the system
34directly to an intranet or even the global Internet. Embedded devices
35with full TCP/IP support will be first-class network citizens, thus
36being able to fully communicate with other hosts in the network.
37
38Traditional TCP/IP implementations have required far too much
39resources both in terms of code size and memory usage to be useful in
40small 8 or 16-bit systems. Code size of a few hundred kilobytes and
41RAM requirements of several hundreds of kilobytes have made it
42impossible to fit the full TCP/IP stack into systems with a few tens
43of kilobytes of RAM and room for less than 100 kilobytes of
44code.
45
46The uIP implementation is designed to have only the absolute minimal
47set of features needed for a full TCP/IP stack. It can only handle a
48single network interface and contains the IP, ICMP, UDP and TCP
49protocols. uIP is written in the C programming language.
50
51Many other TCP/IP implementations for small systems assume that the
52embedded device always will communicate with a full-scale TCP/IP
53implementation running on a workstation-class machine. Under this
54assumption, it is possible to remove certain TCP/IP mechanisms that
55are very rarely used in such situations. Many of those mechanisms are
56essential, however, if the embedded device is to communicate with
57another equally limited device, e.g., when running distributed
58peer-to-peer services and protocols. uIP is designed to be RFC
59compliant in order to let the embedded devices to act as first-class
60network citizens. The uIP TCP/IP implementation that is not tailored
61for any specific application.
62
63
64\section tcpip TCP/IP Communication
65
66The full TCP/IP suite consists of numerous protocols, ranging from low
67level protocols such as ARP which translates IP addresses to MAC
68addresses, to application level protocols such as SMTP that is used to
69transfer e-mail. The uIP is mostly concerned with the TCP and IP
70protocols and upper layer protocols will be referred to as "the
71application". Lower layer protocols are often implemented in hardware
72or firmware and will be referred to as "the network device" that are
73controlled by the network device driver.
74
75TCP provides a reliable byte stream to the upper layer protocols. It
76breaks the byte stream into appropriately sized segments and each
77segment is sent in its own IP packet. The IP packets are sent out on
78the network by the network device driver. If the destination is not on
79the physically connected network, the IP packet is forwarded onto
80another network by a router that is situated between the two
81networks. If the maximum packet size of the other network is smaller
82than the size of the IP packet, the packet is fragmented into smaller
83packets by the router. If possible, the size of the TCP segments are
84chosen so that fragmentation is minimized. The final recipient of the
85packet will have to reassemble any fragmented IP packets before they
86can be passed to higher layers.
87
88The formal requirements for the protocols in the TCP/IP stack is
89specified in a number of RFC documents published by the Internet
90Engineering Task Force, IETF. Each of the protocols in the stack is
91defined in one more RFC documents and RFC1122 collects
92all requirements and updates the previous RFCs.
93
94The RFC1122 requirements can be divided into two categories; those
95that deal with the host to host communication and those that deal with
96communication between the application and the networking stack. An
97example of the first kind is "A TCP MUST be able to receive a TCP
98option in any segment" and an example of the second kind is "There
99MUST be a mechanism for reporting soft TCP error conditions to the
100application." A TCP/IP implementation that violates requirements of
101the first kind may not be able to communicate with other TCP/IP
102implementations and may even lead to network failures. Violation of
103the second kind of requirements will only affect the communication
104within the system and will not affect host-to-host communication.
105
106In uIP, all RFC requirements that affect host-to-host communication
107are implemented. However, in order to reduce code size, we have
108removed certain mechanisms in the interface between the application
109and the stack, such as the soft error reporting mechanism and
110dynamically configurable type-of-service bits for TCP
111connections. Since there are only very few applications that make use
112of those features they can be removed without loss of generality.
113
114\section mainloop Main Control Loop
115
116The uIP stack can be run either as a task in a multitasking system, or
117as the main program in a singletasking system. In both cases, the main
118control loop does two things repeatedly:
119
120 - Check if a packet has arrived from the network.
121 - Check if a periodic timeout has occurred.
122
123If a packet has arrived, the input handler function, uip_input(),
124should be invoked by the main control loop. The input handler function
125will never block, but will return at once. When it returns, the stack
126or the application for which the incoming packet was intended may have
127produced one or more reply packets which should be sent out. If so,
128the network device driver should be called to send out these packets.
129
130Periodic timeouts are used to drive TCP mechanisms that depend on
131timers, such as delayed acknowledgments, retransmissions and
132round-trip time estimations. When the main control loop infers that
133the periodic timer should fire, it should invoke the timer handler
134function uip_periodic(). Because the TCP/IP stack may perform
135retransmissions when dealing with a timer event, the network device
136driver should called to send out the packets that may have been produced.
137
138\section arch Architecture Specific Functions
139
140uIP requires a few functions to be implemented specifically for the
141architecture on which uIP is intended to run. These functions should
142be hand-tuned for the particular architecture, but generic C
143implementations are given as part of the uIP distribution.
144
145\subsection checksums Checksum Calculation
146
147The TCP and IP protocols implement a checksum that covers the data and
148header portions of the TCP and IP packets. Since the calculation of
149this checksum is made over all bytes in every packet being sent and
150received it is important that the function that calculates the
151checksum is efficient. Most often, this means that the checksum
152calculation must be fine-tuned for the particular architecture on
153which the uIP stack runs.
154
155While uIP includes a generic checksum function, it also leaves it open
156for an architecture specific implementation of the two functions
157uip_ipchksum() and uip_tcpchksum(). The checksum calculations in those
158functions can be written in highly optimized assembler rather than
159generic C code.
160
161\subsection longarith 32-bit Arithmetic
162
163The TCP protocol uses 32-bit sequence numbers, and a TCP
164implementation will have to do a number of 32-bit additions as part of
165the normal protocol processing. Since 32-bit arithmetic is not
166natively available on many of the platforms for which uIP is intended,
167uIP leaves the 32-bit additions to be implemented by the architecture
168specific module and does not make use of any 32-bit arithmetic in the
169main code base.
170
171While uIP implements a generic 32-bit addition, there is support for
172having an architecture specific implementation of the uip_add32()
173function.
174
175
176\section memory Memory Management
177
178In the architectures for which uIP is intended, RAM is the most
179scarce resource. With only a few kilobytes of RAM available for the
180TCP/IP stack to use, mechanisms used in traditional TCP/IP cannot be
181directly applied.
182
183
184The uIP stack does not use explicit dynamic memory
185allocation. Instead, it uses a single global buffer for holding
186packets and has a fixed table for holding connection state. The global
187packet buffer is large enough to contain one packet of maximum
188size. When a packet arrives from the network, the device driver places
189it in the global buffer and calls the TCP/IP stack. If the packet
190contains data, the TCP/IP stack will notify the corresponding
191application. Because the data in the buffer will be overwritten by the
192next incoming packet, the application will either have to act
193immediately on the data or copy the data into a secondary buffer for
194later processing. The packet buffer will not be overwritten by new
195packets before the application has processed the data. Packets that
196arrive when the application is processing the data must be queued,
197either by the network device or by the device driver. Most single-chip
198Ethernet controllers have on-chip buffers that are large enough to
199contain at least 4 maximum sized Ethernet frames. Devices that are
200handled by the processor, such as RS-232 ports, can copy incoming
201bytes to a separate buffer during application processing. If the
202buffers are full, the incoming packet is dropped. This will cause
203performance degradation, but only when multiple connections are
204running in parallel. This is because uIP advertises a very small
205receiver window, which means that only a single TCP segment will be in
206the network per connection.
207
208In uIP, the same global packet buffer that is used for incoming
209packets is also used for the TCP/IP headers of outgoing data. If the
210application sends dynamic data, it may use the parts of the global
211packet buffer that are not used for headers as a temporary storage
212buffer. To send the data, the application passes a pointer to the data
213as well as the length of the data to the stack. The TCP/IP headers are
214written into the global buffer and once the headers have been
215produced, the device driver sends the headers and the application data
216out on the network. The data is not queued for
217retransmissions. Instead, the application will have to reproduce the
218data if a retransmission is necessary.
219
220The total amount of memory usage for uIP depends heavily on the
221applications of the particular device in which the implementations are
222to be run. The memory configuration determines both the amount of
223traffic the system should be able to handle and the maximum amount of
224simultaneous connections. A device that will be sending large e-mails
225while at the same time running a web server with highly dynamic web
226pages and multiple simultaneous clients, will require more RAM than a
227simple Telnet server. It is possible to run the uIP implementation
228with as little as 200 bytes of RAM, but such a configuration will
229provide extremely low throughput and will only allow a small number of
230simultaneous connections.
231
232\section api Application Program Interface (API)
233
234
235The Application Program Interface (API) defines the way the
236application program interacts with the TCP/IP stack. The most commonly
237used API for TCP/IP is the BSD socket API which is used in most Unix
238systems and has heavily influenced the Microsoft Windows WinSock
239API. Because the socket API uses stop-and-wait semantics, it requires
240support from an underlying multitasking operating system. Since the
241overhead of task management, context switching and allocation of stack
242space for the tasks might be too high in the intended uIP target
243architectures, the BSD socket interface is not suitable for our
244purposes.
245
246uIP provides two APIs to programmers: protosockets, a BSD socket-like
247API without the overhead of full multi-threading, and a "raw"
248event-based API that is nore low-level than protosockets but uses less
249memory.
250
251\sa \ref psock
252\sa \ref pt
253
254
255\subsection rawapi The uIP raw API
256
257The "raw" uIP API uses an event driven interface where the application is
258invoked in response to certain events. An application running on top
259of uIP is implemented as a C function that is called by uIP in
260response to certain events. uIP calls the application when data is
261received, when data has been successfully delivered to the other end
262of the connection, when a new connection has been set up, or when data
263has to be retransmitted. The application is also periodically polled
264for new data. The application program provides only one callback
265function; it is up to the application to deal with mapping different
266network services to different ports and connections. Because the
267application is able to act on incoming data and connection requests as
268soon as the TCP/IP stack receives the packet, low response times can
269be achieved even in low-end systems.
270
271uIP is different from other TCP/IP stacks in that it requires help
272from the application when doing retransmissions. Other TCP/IP stacks
273buffer the transmitted data in memory until the data is known to be
274successfully delivered to the remote end of the connection. If the
275data needs to be retransmitted, the stack takes care of the
276retransmission without notifying the application. With this approach,
277the data has to be buffered in memory while waiting for an
278acknowledgment even if the application might be able to quickly
279regenerate the data if a retransmission has to be made.
280
281In order to reduce memory usage, uIP utilizes the fact that the
282application may be able to regenerate sent data and lets the
283application take part in retransmissions. uIP does not keep track of
284packet contents after they have been sent by the device driver, and
285uIP requires that the application takes an active part in performing
286the retransmission. When uIP decides that a segment should be
287retransmitted, it calls the application with a flag set indicating
288that a retransmission is required. The application checks the
289retransmission flag and produces the same data that was previously
290sent. From the application's standpoint, performing a retransmission
291is not different from how the data originally was sent. Therefore the
292application can be written in such a way that the same code is used
293both for sending data and retransmitting data. Also, it is important
294to note that even though the actual retransmission operation is
295carried out by the application, it is the responsibility of the stack
296to know when the retransmission should be made. Thus the complexity of
297the application does not necessarily increase because it takes an
298active part in doing retransmissions.
299
300\subsubsection appevents Application Events
301
302The application must be implemented as a C function, UIP_APPCALL(),
303that uIP calls whenever an event occurs. Each event has a corresponding
304test function that is used to distinguish between different
305events. The functions are implemented as C macros that will evaluate
306to either zero or non-zero. Note that certain events can happen in
307conjunction with each other (i.e., new data can arrive at the same
308time as data is acknowledged).
309
310\subsubsection connstate The Connection Pointer
311
312When the application is called by uIP, the global variable uip_conn is
313set to point to the uip_conn structure for the connection that
314currently is handled, and is called the "current connection". The
315fields in the uip_conn structure for the current connection can be
316used, e.g., to distinguish between different services, or to check to
317which IP address the connection is connected. One typical use would be
318to inspect the uip_conn->lport (the local TCP port number) to decide
319which service the connection should provide. For instance, an
320application might decide to act as an HTTP server if the value of
321uip_conn->lport is equal to 80 and act as a TELNET server if the value
322is 23.
323
324\subsubsection recvdata Receiving Data
325
326If the uIP test function uip_newdata() is non-zero, the remote host of
327the connection has sent new data. The uip_appdata pointer point to the
328actual data. The size of the data is obtained through the uIP function
329uip_datalen(). The data is not buffered by uIP, but will be
330overwritten after the application function returns, and the
331application will therefor have to either act directly on the incoming
332data, or by itself copy the incoming data into a buffer for later
333processing.
334
335\subsubsection senddata Sending Data
336
337When sending data, uIP adjusts the length of the data sent by the
338application according to the available buffer space and the current
339TCP window advertised by the receiver. The amount of buffer space is
340dictated by the memory configuration. It is therefore possible that
341all data sent from the application does not arrive at the receiver,
342and the application may use the uip_mss() function to see how much
343data that actually will be sent by the stack.
344
345The application sends data by using the uIP function uip_send(). The
346uip_send() function takes two arguments; a pointer to the data to be
347sent and the length of the data. If the application needs RAM space
348for producing the actual data that should be sent, the packet buffer
349(pointed to by the uip_appdata pointer) can be used for this purpose.
350
351The application can send only one chunk of data at a time on a
352connection and it is not possible to call uip_send() more than once
353per application invocation; only the data from the last call will be
354sent.
355
356\subsubsection rexmitdata Retransmitting Data
357
358Retransmissions are driven by the periodic TCP timer. Every time the
359periodic timer is invoked, the retransmission timer for each
360connection is decremented. If the timer reaches zero, a retransmission
361should be made. As uIP does not keep track of packet contents after they have
362been sent by the device driver, uIP requires that the
363application takes an active part in performing the
364retransmission. When uIP decides that a segment should be
365retransmitted, the application function is called with the
366uip_rexmit() flag set, indicating that a retransmission is
367required.
368
369The application must check the uip_rexmit() flag and produce the same
370data that was previously sent. From the application's standpoint,
371performing a retransmission is not different from how the data
372originally was sent. Therefor, the application can be written in such
373a way that the same code is used both for sending data and
374retransmitting data. Also, it is important to note that even though
375the actual retransmission operation is carried out by the application,
376it is the responsibility of the stack to know when the retransmission
377should be made. Thus the complexity of the application does not
378necessarily increase because it takes an active part in doing
379retransmissions.
380
381\subsubsection closing Closing Connections
382
383The application closes the current connection by calling the
384uip_close() during an application call. This will cause the connection
385to be cleanly closed. In order to indicate a fatal error, the
386application might want to abort the connection and does so by calling
387the uip_abort() function.
388
389If the connection has been closed by the remote end, the test function
390uip_closed() is true. The application may then do any necessary
391cleanups.
392
393\subsubsection errors Reporting Errors
394
395There are two fatal errors that can happen to a connection, either
396that the connection was aborted by the remote host, or that the
397connection retransmitted the last data too many times and has been
398aborted. uIP reports this by calling the application function. The
399application can use the two test functions uip_aborted() and
400uip_timedout() to test for those error conditions.
401
402\subsubsection polling Polling
403
404When a connection is idle, uIP polls the application every time the
405periodic timer fires. The application uses the test function
406uip_poll() to check if it is being polled by uIP.
407
408The polling event has two purposes. The first is to let the
409application periodically know that a connection is idle, which allows
410the application to close connections that have been idle for too
411long. The other purpose is to let the application send new data that
412has been produced. The application can only send data when invoked by
413uIP, and therefore the poll event is the only way to send data on an
414otherwise idle connection.
415
416\subsubsection listen Listening Ports
417
418uIP maintains a list of listening TCP ports. A new port is opened for
419listening with the uip_listen() function. When a connection request
420arrives on a listening port, uIP creates a new connection and calls
421the application function. The test function uip_connected() is true if
422the application was invoked because a new connection was created.
423
424The application can check the lport field in the uip_conn structure to
425check to which port the new connection was connected.
426
427\subsubsection connect Opening Connections
428
429New connections can be opened from within
430uIP by the function uip_connect(). This function
431allocates a new connection and sets a flag in the connection state
432which will open a TCP connection to the specified IP address and port
433the next time the connection is polled by uIP. The uip_connect()
434function returns
435a pointer to the uip_conn structure for the new
436connection. If there are no free connection slots, the function
437returns NULL.
438
439The function uip_ipaddr() may be used to pack an IP address into the
440two element 16-bit array used by uIP to represent IP addresses.
441
442Two examples of usage are shown below. The first example shows how to
443open a connection to TCP port 8080 of the remote end of the current
444connection. If there are not enough TCP connection slots to allow a
445new connection to be opened, the uip_connect() function returns NULL
446and the current connection is aborted by uip_abort().
447
448\code
449void connect_example1_app(void) {
450   if(uip_connect(uip_conn->ripaddr, HTONS(8080)) == NULL) {
451      uip_abort();
452   }
453}
454\endcode
455
456The second example shows how to open a new connection to a specific IP
457address. No error checks are made in this example.
458
459\code
460void connect_example2(void) {
461   u16_t ipaddr[2];
462
463   uip_ipaddr(ipaddr, 192,168,0,1);
464   uip_connect(ipaddr, HTONS(8080));
465}
466\endcode
467
468\section examples Examples
469
470This section presents a number of very simple uIP applications. The
471uIP code distribution contains several more complex applications.
472
473\subsection example1 A Very Simple Application
474
475This first example shows a very simple application. The application
476listens for incoming connections on port 1234. When a connection has
477been established, the application replies to all data sent to it by
478saying "ok"
479
480The implementation of this application is shown below. The application
481is initialized with the function called example1_init() and the uIP
482callback function is called example1_app(). For this application, the
483configuration variable UIP_APPCALL should be defined to be
484example1_app().
485
486\code
487void example1_init(void) {
488   uip_listen(HTONS(1234));
489}
490
491void example1_app(void) {
492   if(uip_newdata() || uip_rexmit()) {
493      uip_send("ok\n", 3);
494   }
495}
496\endcode
497
498The initialization function calls the uIP function uip_listen() to
499register a listening port. The actual application function
500example1_app() uses the test functions uip_newdata() and uip_rexmit()
501to determine why it was called. If the application was called because
502the remote end has sent it data, it responds with an "ok". If the
503application function was called because data was lost in the network
504and has to be retransmitted, it also sends an "ok".  Note that this
505example actually shows a complete uIP application. It is not required
506for an application to deal with all types of events such as
507uip_connected() or uip_timedout().
508
509\subsection example2 A More Advanced Application
510
511This second example is slightly more advanced than the previous one,
512and shows how the application state field in the uip_conn structure is
513used.
514
515This application is similar to the first application in that it
516listens to a port for incoming connections and responds to data sent
517to it with a single "ok". The big difference is that this application
518prints out a welcoming "Welcome!" message when the connection has been
519established.
520
521This seemingly small change of operation makes a big difference in how
522the application is implemented. The reason for the increase in
523complexity is that if data should be lost in the network, the
524application must know what data to retransmit. If the "Welcome!"
525message was lost, the application must retransmit the welcome and if
526one of the "ok" messages is lost, the application must send a new
527"ok".
528
529The application knows that as long as the "Welcome!" message has not
530been acknowledged by the remote host, it might have been dropped in
531the network. But once the remote host has sent an acknowledgment
532back, the application can be sure that the welcome has been received
533and knows that any lost data must be an "ok" message. Thus the
534application can be in either of two states: either in the WELCOME-SENT
535state where the "Welcome!" has been sent but not acknowledged, or in
536the WELCOME-ACKED state where the "Welcome!" has been acknowledged.
537
538When a remote host connects to the application, the application sends
539the "Welcome!" message and sets it's state to WELCOME-SENT. When the
540welcome message is acknowledged, the application moves to the
541WELCOME-ACKED state. If the application receives any new data from the
542remote host, it responds by sending an "ok" back.
543
544If the application is requested to retransmit the last message, it
545looks at in which state the application is. If the application is in
546the WELCOME-SENT state, it sends a "Welcome!"  message since it
547knows that the previous welcome message hasn't been acknowledged. If
548the application is in the WELCOME-ACKED state, it knows that the last
549message was an "ok" message and sends such a message.
550
551The implementation of this application is seen below. This
552configuration settings for the application is follows after its
553implementation.
554
555\code
556struct example2_state {
557   enum {WELCOME_SENT, WELCOME_ACKED} state;
558};
559
560void example2_init(void) {
561   uip_listen(HTONS(2345));
562}
563
564void example2_app(void) {
565   struct example2_state *s;
566
567   s = (struct example2_state *)uip_conn->appstate;
568
569   if(uip_connected()) {
570      s->state = WELCOME_SENT;
571      uip_send("Welcome!\n", 9);
572      return;
573   }
574
575   if(uip_acked() && s->state == WELCOME_SENT) {
576      s->state = WELCOME_ACKED;
577   }
578
579   if(uip_newdata()) {
580      uip_send("ok\n", 3);
581   }
582
583   if(uip_rexmit()) {
584      switch(s->state) {
585      case WELCOME_SENT:
586         uip_send("Welcome!\n", 9);
587         break;
588      case WELCOME_ACKED:
589         uip_send("ok\n", 3);
590         break;
591      }
592   }
593}
594\endcode
595
596The configuration for the application:
597
598\code
599#define UIP_APPCALL       example2_app
600#define UIP_APPSTATE_SIZE sizeof(struct example2_state)
601\endcode
602
603\subsection example3 Differentiating Between Applications
604
605If the system should run multiple applications, one technique to
606differentiate between them is to use the TCP port number of either the
607remote end or the local end of the connection. The example below shows
608how the two examples above can be combined into one application.
609
610\code
611void example3_init(void) {
612   example1_init();
613   example2_init();
614}
615
616void example3_app(void) {
617   switch(uip_conn->lport) {
618   case HTONS(1234):
619      example1_app();
620      break;
621   case HTONS(2345):
622      example2_app();
623      break;
624   }
625}
626\endcode
627
628\subsection example4 Utilizing TCP Flow Control
629
630This example shows a simple application that connects to a host, sends
631an HTTP request for a file and downloads it to a slow device such a
632disk drive. This shows how to use the flow control functions of uIP.
633
634\code
635void example4_init(void) {
636   u16_t ipaddr[2];
637   uip_ipaddr(ipaddr, 192,168,0,1);
638   uip_connect(ipaddr, HTONS(80));
639}
640
641void example4_app(void) {
642   if(uip_connected() || uip_rexmit()) {
643      uip_send("GET /file HTTP/1.0\r\nServer:192.186.0.1\r\n\r\n",
644               48);
645      return;
646   }
647
648   if(uip_newdata()) {
649      device_enqueue(uip_appdata, uip_datalen());
650      if(device_queue_full()) {
651         uip_stop();
652      }
653   }
654
655   if(uip_poll() && uip_stopped()) {
656      if(!device_queue_full()) {
657         uip_restart();
658      }
659   }
660}
661\endcode
662
663When the connection has been established, an HTTP request is sent to
664the server. Since this is the only data that is sent, the application
665knows that if it needs to retransmit any data, it is that request that
666should be retransmitted. It is therefore possible to combine these two
667events as is done in the example.
668
669When the application receives new data from the remote host, it sends
670this data to the device by using the function device_enqueue(). It is
671important to note that this example assumes that this function copies
672the data into its own buffers. The data in the uip_appdata buffer will
673be overwritten by the next incoming packet.
674
675If the device's queue is full, the application stops the data from the
676remote host by calling the uIP function uip_stop(). The application
677can then be sure that it will not receive any new data until
678uip_restart() is called. The application polling event is used to
679check if the device's queue is no longer full and if so, the data flow
680is restarted with uip_restart().
681
682\subsection example5 A Simple Web Server
683
684This example shows a very simple file server application that listens
685to two ports and uses the port number to determine which file to
686send. If the files are properly formatted, this simple application can
687be used as a web server with static pages. The implementation follows.
688
689\code
690struct example5_state {
691   char *dataptr;
692   unsigned int dataleft;
693};
694
695void example5_init(void) {
696   uip_listen(HTONS(80));
697   uip_listen(HTONS(81));
698}
699
700void example5_app(void) {
701   struct example5_state *s;
702   s = (struct example5_state)uip_conn->appstate;
703
704   if(uip_connected()) {
705      switch(uip_conn->lport) {
706      case HTONS(80):
707         s->dataptr = data_port_80;
708         s->dataleft = datalen_port_80;
709         break;
710      case HTONS(81):
711         s->dataptr = data_port_81;
712         s->dataleft = datalen_port_81;
713         break;
714      }
715      uip_send(s->dataptr, s->dataleft);
716      return;
717   }
718
719   if(uip_acked()) {
720      if(s->dataleft < uip_mss()) {
721         uip_close();
722         return;
723      }
724      s->dataptr += uip_conn->len;
725      s->dataleft -= uip_conn->len;
726      uip_send(s->dataptr, s->dataleft);
727   }
728}
729\endcode
730
731The application state consists of a pointer to the data that should be
732sent and the size of the data that is left to send. When a remote host
733connects to the application, the local port number is used to
734determine which file to send. The first chunk of data is sent using
735uip_send(). uIP makes sure that no more than MSS bytes of data is
736actually sent, even though s->dataleft may be larger than the MSS.
737
738The application is driven by incoming acknowledgments. When data has
739been acknowledged, new data can be sent. If there is no more data to
740send, the connection is closed using uip_close().
741
742\subsection example6 Structured Application Program Design
743
744When writing larger programs using uIP it is useful to be able to
745utilize the uIP API in a structured way. The following example
746provides a structured design that has showed itself to be useful for
747writing larger protocol implementations than the previous examples
748showed here. The program is divided into an uIP event handler function
749that calls seven application handler functions that process new data,
750act on acknowledged data, send new data, deal with connection
751establishment or closure events and handle errors. The functions are
752called newdata(), acked(), senddata(), connected(), closed(),
753aborted(), and timedout(), and needs to be written specifically for
754the protocol that is being implemented.
755
756The uIP event handler function is shown below.
757
758\code
759void example6_app(void) {
760  if(uip_aborted()) {
761    aborted();
762  }
763  if(uip_timedout()) {
764    timedout();
765  }
766  if(uip_closed()) {
767    closed();
768  }
769  if(uip_connected()) {
770    connected();
771  }
772  if(uip_acked()) {
773    acked();
774  }
775  if(uip_newdata()) {
776    newdata();
777  }
778  if(uip_rexmit() ||
779     uip_newdata() ||
780     uip_acked() ||
781     uip_connected() ||
782     uip_poll()) {
783    senddata();
784  }
785}
786\endcode
787
788The function starts with dealing with any error conditions that might
789have happened by checking if uip_aborted() or uip_timedout() are
790true. If so, the appropriate error function is called. Also, if the
791connection has been closed, the closed() function is called to the it
792deal with the event.
793
794Next, the function checks if the connection has just been established
795by checking if uip_connected() is true. The connected() function is
796called and is supposed to do whatever needs to be done when the
797connection is established, such as intializing the application state
798for the connection. Since it may be the case that data should be sent
799out, the senddata() function is called to deal with the outgoing data.
800
801The following very simple application serves as an example of how the
802application handler functions might look. This application simply
803waits for any data to arrive on the connection, and responds to the
804data by sending out the message "Hello world!". To illustrate how to
805develop an application state machine, this message is sent in two
806parts, first the "Hello" part and then the "world!" part.
807
808\code
809#define STATE_WAITING 0
810#define STATE_HELLO   1
811#define STATE_WORLD   2
812
813struct example6_state {
814  u8_t state;
815  char *textptr;
816  int  textlen;
817};
818
819static void aborted(void) {}
820static void timedout(void) {}
821static void closed(void) {}
822
823static void connected(void) {
824  struct example6_state *s = (struct example6_state *)uip_conn->appstate;
825
826  s->state   = STATE_WAITING;
827  s->textlen = 0;
828}
829
830static void newdata(void) {
831  struct example6_state *s = (struct example6_state *)uip_conn->appstate;
832
833  if(s->state == STATE_WAITING) {
834    s->state   = STATE_HELLO;
835    s->textptr = "Hello ";
836    s->textlen = 6;
837  }
838}
839
840static void acked(void) {
841  struct example6_state *s = (struct example6_state *)uip_conn->appstate;
842
843  s->textlen -= uip_conn->len;
844  s->textptr += uip_conn->len;
845  if(s->textlen == 0) {
846    switch(s->state) {
847    case STATE_HELLO:
848      s->state   = STATE_WORLD;
849      s->textptr = "world!\n";
850      s->textlen = 7;
851      break;
852    case STATE_WORLD:
853      uip_close();
854      break;
855    }
856  }
857}
858
859static void senddata(void) {
860  struct example6_state *s = (struct example6_state *)uip_conn->appstate;
861
862  if(s->textlen > 0) {
863    uip_send(s->textptr, s->textlen);
864  }
865}
866\endcode
867
868The application state consists of a "state" variable, a "textptr"
869pointer to a text message and the "textlen" length of the text
870message. The "state" variable can be either "STATE_WAITING", meaning
871that the application is waiting for data to arrive from the network,
872"STATE_HELLO", in which the application is sending the "Hello" part of
873the message, or "STATE_WORLD", in which the application is sending the
874"world!" message.
875
876The application does not handle errors or connection closing events,
877and therefore the aborted(), timedout() and closed() functions are
878implemented as empty functions.
879
880The connected() function will be called when a connection has been
881established, and in this case sets the "state" variable to be
882"STATE_WAITING" and the "textlen" variable to be zero, indicating that
883there is no message to be sent out.
884
885When new data arrives from the network, the newdata() function will be
886called by the event handler function. The newdata() function will
887check if the connection is in the "STATE_WAITING" state, and if so
888switches to the "STATE_HELLO" state and registers a 6 byte long "Hello
889" message with the connection. This message will later be sent out by
890the senddata() function.
891
892The acked() function is called whenever data that previously was sent
893has been acknowleged by the receiving host. This acked() function
894first reduces the amount of data that is left to send, by subtracting
895the length of the previously sent data (obtained from "uip_conn->len")
896from the "textlen" variable, and also adjusts the "textptr" pointer
897accordingly. It then checks if the "textlen" variable now is zero,
898which indicates that all data now has been successfully received, and
899if so changes application state. If the application was in the
900"STATE_HELLO" state, it switches state to "STATE_WORLD" and sets up a
9017 byte "world!\n" message to be sent. If the application was in the
902"STATE_WORLD" state, it closes the connection.
903
904Finally, the senddata() function takes care of actually sending the
905data that is to be sent. It is called by the event handler function
906when new data has been received, when data has been acknowledged, when
907a new connection has been established, when the connection is polled
908because of inactivity, or when a retransmission should be made. The
909purpose of the senddata() function is to optionally format the data
910that is to be sent, and to call the uip_send() function to actually
911send out the data. In this particular example, the function simply
912calls uip_send() with the appropriate arguments if data is to be sent,
913after checking if data should be sent out or not as indicated by the
914"textlen" variable.
915
916It is important to note that the senddata() function never should
917affect the application state; this should only be done in the acked()
918and newdata() functions.
919
920\section protoimpl Protocol Implementations
921
922The protocols in the TCP/IP protocol suite are designed in a layered
923fashion where each protocol performs a specific function and the
924interactions between the protocol layers are strictly defined. While
925the layered approach is a good way to design protocols, it is not
926always the best way to implement them. In uIP, the protocol
927implementations are tightly coupled in order to save code space.
928
929This section gives detailed information on the specific protocol
930implementations in uIP.
931
932\subsection ip IP --- Internet Protocol
933
934When incoming packets are processed by uIP, the IP layer is the first
935protocol that examines the packet. The IP layer does a few simple
936checks such as if the destination IP address of the incoming packet
937matches any of the local IP address and verifies the IP header
938checksum. Since there are no IP options that are strictly required and
939because they are very uncommon, any IP options in received packets are
940dropped.
941
942\subsubsection ipreass IP Fragment Reassembly
943
944IP fragment reassembly is implemented using a separate buffer that
945holds the packet to be reassembled. An incoming fragment is copied
946into the right place in the buffer and a bit map is used to keep track
947of which fragments have been received. Because the first byte of an IP
948fragment is aligned on an 8-byte boundary, the bit map requires a
949small amount of memory. When all fragments have been reassembled, the
950resulting IP packet is passed to the transport layer. If all fragments
951have not been received within a specified time frame, the packet is
952dropped.
953
954The current implementation only has a single buffer for holding
955packets to be reassembled, and therefore does not support simultaneous
956reassembly of more than one packet. Since fragmented packets are
957uncommon, this ought to be a reasonable decision. Extending the
958implementation to support multiple buffers would be straightforward,
959however.
960
961\subsubsection ipbroadcast Broadcasts and Multicasts
962
963IP has the ability to broadcast and multicast packets on the local
964network. Such packets are addressed to special broadcast and multicast
965addresses. Broadcast is used heavily in many UDP based protocols such
966as the Microsoft Windows file-sharing SMB protocol. Multicast is
967primarily used in protocols used for multimedia distribution such as
968RTP. TCP is a point-to-point protocol and does not use broadcast or
969multicast packets. uIP current supports broadcast packets as well as
970sending multicast packets. Joining multicast groups (IGMP) and
971receiving non-local multicast packets is not currently supported.
972
973\subsection icmp ICMP --- Internet Control Message Protocol
974
975The ICMP protocol is used for reporting soft error conditions and for
976querying host parameters. Its main use is, however, the echo mechanism
977which is used by the "ping" program.
978
979The ICMP implementation in uIP is very simple as itis restricted to
980only implement ICMP echo messages. Replies to echo messages are
981constructed by simply swapping the source and destination IP addresses
982of incoming echo requests and rewriting the ICMP header with the
983Echo-Reply message type. The ICMP checksum is adjusted using standard
984techniques (see RFC1624).
985
986Since only the ICMP echo message is implemented, there is no support
987for Path MTU discovery or ICMP redirect messages. Neither of these is
988strictly required for interoperability; they are performance
989enhancement mechanisms.
990
991\subsection tcp TCP --- Transmission Control Protocol
992
993The TCP implementation in uIP is driven by incoming packets and timer
994events. Incoming packets are parsed by TCP and if the packet contains
995data that is to be delivered to the application, the application is
996invoked by the means of the application function call. If the incoming
997packet acknowledges previously sent data, the connection state is
998updated and the application is informed, allowing it to send out new
999data.
1000
1001\subsubsection listeb Listening Connections
1002
1003TCP allows a connection to listen for incoming connection requests. In
1004uIP, a listening connection is identified by the 16-bit port number
1005and incoming connection requests are checked against the list of
1006listening connections. This list of listening connections is dynamic
1007and can be altered by the applications in the system.
1008
1009\subsubsection slidingwindow Sliding Window
1010
1011Most TCP implementations use a sliding window mechanism for sending
1012data. Multiple data segments are sent in succession without waiting
1013for an acknowledgment for each segment.
1014
1015The sliding window algorithm uses a lot of 32-bit operations and
1016because 32-bit arithmetic is fairly expensive on most 8-bit CPUs, uIP
1017does not implement it. Also, uIP does not buffer sent packets and a
1018sliding window implementation that does not buffer sent packets will have
1019to be supported by a complex application layer. Instead, uIP allows
1020only a single TCP segment per connection to be unacknowledged at any
1021given time.
1022
1023It is important to note that even though most TCP implementations use
1024the sliding window algorithm, it is not required by the TCP
1025specifications. Removing the sliding window mechanism does not affect
1026interoperability in any way.
1027
1028\subsubsection rttest Round-Trip Time Estimation
1029
1030TCP continuously estimates the current Round-Trip Time (RTT) of every
1031active connection in order to find a suitable value for the
1032retransmission time-out.
1033
1034The RTT estimation in uIP is implemented using TCP's periodic
1035timer. Each time the periodic timer fires, it increments a counter for
1036each connection that has unacknowledged data in the network. When an
1037acknowledgment is received, the current value of the counter is used
1038as a sample of the RTT. The sample is used together with Van
1039Jacobson's standard TCP RTT estimation function to calculate an
1040estimate of the RTT. Karn's algorithm is used to ensure that
1041retransmissions do not skew the estimates.
1042
1043\subsubsection rexmit Retransmissions
1044
1045Retransmissions are driven by the periodic TCP timer. Every time the
1046periodic timer is invoked, the retransmission timer for each
1047connection is decremented. If the timer reaches zero, a retransmission
1048should be made.
1049
1050As uIP does not keep track of packet contents after they have
1051been sent by the device driver, uIP requires that the
1052application takes an active part in performing the
1053retransmission. When uIP decides that a segment should be
1054retransmitted, it calls the application with a flag set indicating
1055that a retransmission is required. The application checks the
1056retransmission flag and produces the same data that was previously
1057sent. From the application's standpoint, performing a retransmission
1058is not different from how the data originally was sent. Therefore the
1059application can be written in such a way that the same code is used
1060both for sending data and retransmitting data. Also, it is important
1061to note that even though the actual retransmission operation is
1062carried out by the application, it is the responsibility of the stack
1063to know when the retransmission should be made. Thus the complexity of
1064the application does not necessarily increase because it takes an
1065active part in doing retransmissions.
1066
1067\subsubsection flowcontrol Flow Control
1068
1069The purpose of TCP's flow control mechanisms is to allow communication
1070between hosts with wildly varying memory dimensions. In each TCP
1071segment, the sender of the segment indicates its available buffer
1072space. A TCP sender must not send more data than the buffer space
1073indicated by the receiver.
1074
1075In uIP, the application cannot send more data than the receiving host
1076can buffer. And application cannot send more data than the amount of
1077bytes it is allowed to send by the receiving host. If the remote host
1078cannot accept any data at all, the stack initiates the zero window
1079probing mechanism.
1080
1081\subsubsection congestioncontrol Congestion Control
1082
1083The congestion control mechanisms limit the number of simultaneous TCP
1084segments in the network. The algorithms used for congestion control
1085are designed to be simple to implement and require only a few lines of
1086code.
1087
1088Since uIP only handles one in-flight TCP segment per connection,
1089the amount of simultaneous segments cannot be further limited, thus
1090the congestion control mechanisms are not needed.
1091
1092\subsubsection urgdata Urgent Data
1093
1094TCP's urgent data mechanism provides an application-to-application
1095notification mechanism, which can be used by an application to mark
1096parts of the data stream as being more urgent than the normal
1097stream. It is up to the receiving application to interpret the meaning
1098of the urgent data.
1099
1100In many TCP implementations, including the BSD implementation, the
1101urgent data feature increases the complexity of the implementation
1102because it requires an asynchronous notification mechanism in an
1103otherwise synchronous API. As uIP already use an asynchronous event
1104based API, the implementation of the urgent data feature does not lead
1105to increased complexity.
1106
1107\section performance Performance
1108
1109In TCP/IP implementations for high-end systems, processing time is
1110dominated by the checksum calculation loop, the operation of copying
1111packet data and context switching. Operating systems for high-end
1112systems often have multiple protection domains for protecting kernel
1113data from user processes and user processes from each other. Because
1114the TCP/IP stack is run in the kernel, data has to be copied between
1115the kernel space and the address space of the user processes and a
1116context switch has to be performed once the data has been
1117copied. Performance can be enhanced by combining the copy operation
1118with the checksum calculation. Because high-end systems usually have
1119numerous active connections, packet demultiplexing is also an
1120expensive operation.
1121
1122A small embedded device does not have the necessary processing power
1123to have multiple protection domains and the power to run a
1124multitasking operating system. Therefore there is no need to copy
1125data between the TCP/IP stack and the application program. With an
1126event based API there is no context switch between the TCP/IP stack
1127and the applications.
1128
1129In such limited systems, the TCP/IP processing overhead is dominated
1130by the copying of packet data from the network device to host memory,
1131and checksum calculation. Apart from the checksum calculation and
1132copying, the TCP processing done for an incoming packet involves only
1133updating a few counters and flags before handing the data over to the
1134application. Thus an estimate of the CPU overhead of our TCP/IP
1135implementations can be obtained by calculating the amount of CPU
1136cycles needed for the checksum calculation and copying of a maximum
1137sized packet.
1138
1139\subsection delack The Impact of Delayed Acknowledgments
1140
1141Most TCP receivers implement the delayed acknowledgment algorithm for
1142reducing the number of pure acknowledgment packets sent. A TCP
1143receiver using this algorithm will only send acknowledgments for every
1144other received segment. If no segment is received within a specific
1145time-frame, an acknowledgment is sent. The time-frame can be as high
1146as 500 ms but typically is 200 ms.
1147
1148A TCP sender such as uIP that only handles a single outstanding TCP
1149segment will interact poorly with the delayed acknowledgment
1150algorithm. Because the receiver only receives a single segment at a
1151time, it will wait as much as 500 ms before an acknowledgment is
1152sent. This means that the maximum possible throughput is severely
1153limited by the 500 ms idle time.
1154
1155Thus the maximum throughput equation when sending data from uIP will
1156be $p = s / (t + t_d)$ where $s$ is the segment size and $t_d$ is the
1157delayed acknowledgment timeout, which typically is between 200 and
1158500 ms. With a segment size of 1000 bytes, a round-trip time of 40 ms
1159and a delayed acknowledgment timeout of 200 ms, the maximum
1160throughput will be 4166 bytes per second. With the delayed acknowledgment
1161algorithm disabled at the receiver, the maximum throughput would be
116225000 bytes per second.
1163
1164It should be noted, however, that since small systems running uIP are
1165not very likely to have large amounts of data to send, the delayed
1166acknowledgmen t throughput degradation of uIP need not be very
1167severe. Small amounts of data sent by such a system will not span more
1168than a single TCP segment, and would therefore not be affected by the
1169throughput degradation anyway.
1170
1171The maximum throughput when uIP acts as a receiver is not affected by
1172the delayed acknowledgment throughput degradation.
1173
1174
1175
1176*/
1177
1178
1179/** @} */
1180
1181