]> rtime.felk.cvut.cz Git - pes-rpp/rpp-lwip.git/blob - src/core/tcp_out.c
fixed bug #34587: TCP_BUILD_MSS_OPTION doesn't consider netif->mtu, causes slow network
[pes-rpp/rpp-lwip.git] / src / core / tcp_out.c
1 /**
2  * @file
3  * Transmission Control Protocol, outgoing traffic
4  *
5  * The output functions of TCP.
6  *
7  */
8
9 /*
10  * Copyright (c) 2001-2004 Swedish Institute of Computer Science.
11  * All rights reserved.
12  *
13  * Redistribution and use in source and binary forms, with or without modification,
14  * are permitted provided that the following conditions are met:
15  *
16  * 1. Redistributions of source code must retain the above copyright notice,
17  *    this list of conditions and the following disclaimer.
18  * 2. Redistributions in binary form must reproduce the above copyright notice,
19  *    this list of conditions and the following disclaimer in the documentation
20  *    and/or other materials provided with the distribution.
21  * 3. The name of the author may not be used to endorse or promote products
22  *    derived from this software without specific prior written permission.
23  *
24  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED
25  * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
26  * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
27  * SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
28  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT
29  * OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
30  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
31  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
32  * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY
33  * OF SUCH DAMAGE.
34  *
35  * This file is part of the lwIP TCP/IP stack.
36  *
37  * Author: Adam Dunkels <adam@sics.se>
38  *
39  */
40
41 #include "lwip/opt.h"
42
43 #if LWIP_TCP /* don't build if not configured for use in lwipopts.h */
44
45 #include "lwip/tcp_impl.h"
46 #include "lwip/def.h"
47 #include "lwip/mem.h"
48 #include "lwip/memp.h"
49 #include "lwip/ip_addr.h"
50 #include "lwip/netif.h"
51 #include "lwip/inet_chksum.h"
52 #include "lwip/stats.h"
53 #include "lwip/snmp.h"
54 #include "lwip/ip6.h"
55 #include "lwip/ip6_addr.h"
56 #include "lwip/inet_chksum.h"
57 #if LWIP_TCP_TIMESTAMPS
58 #include "lwip/sys.h"
59 #endif
60
61 #include <string.h>
62
63 /* Define some copy-macros for checksum-on-copy so that the code looks
64    nicer by preventing too many ifdef's. */
65 #if TCP_CHECKSUM_ON_COPY
66 #define TCP_DATA_COPY(dst, src, len, seg) do { \
67   tcp_seg_add_chksum(LWIP_CHKSUM_COPY(dst, src, len), \
68                      len, &seg->chksum, &seg->chksum_swapped); \
69   seg->flags |= TF_SEG_DATA_CHECKSUMMED; } while(0)
70 #define TCP_DATA_COPY2(dst, src, len, chksum, chksum_swapped)  \
71   tcp_seg_add_chksum(LWIP_CHKSUM_COPY(dst, src, len), len, chksum, chksum_swapped);
72 #else /* TCP_CHECKSUM_ON_COPY*/
73 #define TCP_DATA_COPY(dst, src, len, seg)                     MEMCPY(dst, src, len)
74 #define TCP_DATA_COPY2(dst, src, len, chksum, chksum_swapped) MEMCPY(dst, src, len)
75 #endif /* TCP_CHECKSUM_ON_COPY*/
76
77 /** Define this to 1 for an extra check that the output checksum is valid
78  * (usefule when the checksum is generated by the application, not the stack) */
79 #ifndef TCP_CHECKSUM_ON_COPY_SANITY_CHECK
80 #define TCP_CHECKSUM_ON_COPY_SANITY_CHECK   0
81 #endif
82
83 /* Forward declarations.*/
84 static void tcp_output_segment(struct tcp_seg *seg, struct tcp_pcb *pcb);
85
86 /** Allocate a pbuf and create a tcphdr at p->payload, used for output
87  * functions other than the default tcp_output -> tcp_output_segment
88  * (e.g. tcp_send_empty_ack, etc.)
89  *
90  * @param pcb tcp pcb for which to send a packet (used to initialize tcp_hdr)
91  * @param optlen length of header-options
92  * @param datalen length of tcp data to reserve in pbuf
93  * @param seqno_be seqno in network byte order (big-endian)
94  * @return pbuf with p->payload being the tcp_hdr
95  */
96 static struct pbuf *
97 tcp_output_alloc_header(struct tcp_pcb *pcb, u16_t optlen, u16_t datalen,
98                       u32_t seqno_be /* already in network byte order */)
99 {
100   struct tcp_hdr *tcphdr;
101   struct pbuf *p = pbuf_alloc(PBUF_IP, TCP_HLEN + optlen + datalen, PBUF_RAM);
102   if (p != NULL) {
103     LWIP_ASSERT("check that first pbuf can hold struct tcp_hdr",
104                  (p->len >= TCP_HLEN + optlen));
105     tcphdr = (struct tcp_hdr *)p->payload;
106     tcphdr->src = htons(pcb->local_port);
107     tcphdr->dest = htons(pcb->remote_port);
108     tcphdr->seqno = seqno_be;
109     tcphdr->ackno = htonl(pcb->rcv_nxt);
110     TCPH_HDRLEN_FLAGS_SET(tcphdr, (5 + optlen / 4), TCP_ACK);
111     tcphdr->wnd = htons(pcb->rcv_ann_wnd);
112     tcphdr->chksum = 0;
113     tcphdr->urgp = 0;
114
115     /* If we're sending a packet, update the announced right window edge */
116     pcb->rcv_ann_right_edge = pcb->rcv_nxt + pcb->rcv_ann_wnd;
117   }
118   return p;
119 }
120
121 /**
122  * Called by tcp_close() to send a segment including FIN flag but not data.
123  *
124  * @param pcb the tcp_pcb over which to send a segment
125  * @return ERR_OK if sent, another err_t otherwise
126  */
127 err_t
128 tcp_send_fin(struct tcp_pcb *pcb)
129 {
130   /* first, try to add the fin to the last unsent segment */
131   if (pcb->unsent != NULL) {
132     struct tcp_seg *last_unsent;
133     for (last_unsent = pcb->unsent; last_unsent->next != NULL;
134          last_unsent = last_unsent->next);
135
136     if ((TCPH_FLAGS(last_unsent->tcphdr) & (TCP_SYN | TCP_FIN | TCP_RST)) == 0) {
137       /* no SYN/FIN/RST flag in the header, we can add the FIN flag */
138       TCPH_SET_FLAG(last_unsent->tcphdr, TCP_FIN);
139       pcb->flags |= TF_FIN;
140       return ERR_OK;
141     }
142   }
143   /* no data, no length, flags, copy=1, no optdata */
144   return tcp_enqueue_flags(pcb, TCP_FIN);
145 }
146
147 /**
148  * Create a TCP segment with prefilled header.
149  *
150  * Called by tcp_write and tcp_enqueue_flags.
151  *
152  * @param pcb Protocol control block for the TCP connection.
153  * @param p pbuf that is used to hold the TCP header.
154  * @param flags TCP flags for header.
155  * @param seqno TCP sequence number of this packet
156  * @param optflags options to include in TCP header
157  * @return a new tcp_seg pointing to p, or NULL.
158  * The TCP header is filled in except ackno and wnd.
159  * p is freed on failure.
160  */
161 static struct tcp_seg *
162 tcp_create_segment(struct tcp_pcb *pcb, struct pbuf *p, u8_t flags, u32_t seqno, u8_t optflags)
163 {
164   struct tcp_seg *seg;
165   u8_t optlen = LWIP_TCP_OPT_LENGTH(optflags);
166
167   if ((seg = (struct tcp_seg *)memp_malloc(MEMP_TCP_SEG)) == NULL) {
168     LWIP_DEBUGF(TCP_OUTPUT_DEBUG | 2, ("tcp_create_segment: no memory.\n"));
169     pbuf_free(p);
170     return NULL;
171   }
172   seg->flags = optflags;
173   seg->next = NULL;
174   seg->p = p;
175   seg->len = p->tot_len - optlen;
176 #if TCP_OVERSIZE_DBGCHECK
177   seg->oversize_left = 0;
178 #endif /* TCP_OVERSIZE_DBGCHECK */
179 #if TCP_CHECKSUM_ON_COPY
180   seg->chksum = 0;
181   seg->chksum_swapped = 0;
182   /* check optflags */
183   LWIP_ASSERT("invalid optflags passed: TF_SEG_DATA_CHECKSUMMED",
184               (optflags & TF_SEG_DATA_CHECKSUMMED) == 0);
185 #endif /* TCP_CHECKSUM_ON_COPY */
186
187   /* build TCP header */
188   if (pbuf_header(p, TCP_HLEN)) {
189     LWIP_DEBUGF(TCP_OUTPUT_DEBUG | 2, ("tcp_create_segment: no room for TCP header in pbuf.\n"));
190     TCP_STATS_INC(tcp.err);
191     tcp_seg_free(seg);
192     return NULL;
193   }
194   seg->tcphdr = (struct tcp_hdr *)seg->p->payload;
195   seg->tcphdr->src = htons(pcb->local_port);
196   seg->tcphdr->dest = htons(pcb->remote_port);
197   seg->tcphdr->seqno = htonl(seqno);
198   /* ackno is set in tcp_output */
199   TCPH_HDRLEN_FLAGS_SET(seg->tcphdr, (5 + optlen / 4), flags);
200   /* wnd and chksum are set in tcp_output */
201   seg->tcphdr->urgp = 0;
202   return seg;
203
204
205 /**
206  * Allocate a PBUF_RAM pbuf, perhaps with extra space at the end.
207  *
208  * This function is like pbuf_alloc(layer, length, PBUF_RAM) except
209  * there may be extra bytes available at the end.
210  *
211  * @param layer flag to define header size.
212  * @param length size of the pbuf's payload.
213  * @param max_length maximum usable size of payload+oversize.
214  * @param oversize pointer to a u16_t that will receive the number of usable tail bytes.
215  * @param pcb The TCP connection that willo enqueue the pbuf.
216  * @param apiflags API flags given to tcp_write.
217  * @param first_seg true when this pbuf will be used in the first enqueued segment.
218  * @param 
219  */
220 #if TCP_OVERSIZE
221 static struct pbuf *
222 tcp_pbuf_prealloc(pbuf_layer layer, u16_t length, u16_t max_length,
223                   u16_t *oversize, struct tcp_pcb *pcb, u8_t apiflags,
224                   u8_t first_seg)
225 {
226   struct pbuf *p;
227   u16_t alloc = length;
228
229 #if LWIP_NETIF_TX_SINGLE_PBUF
230   LWIP_UNUSED_ARG(max_length);
231   LWIP_UNUSED_ARG(pcb);
232   LWIP_UNUSED_ARG(apiflags);
233   LWIP_UNUSED_ARG(first_seg);
234   /* always create MSS-sized pbufs */
235   alloc = pcb->mss;
236 #else /* LWIP_NETIF_TX_SINGLE_PBUF */
237   if (length < max_length) {
238     /* Should we allocate an oversized pbuf, or just the minimum
239      * length required? If tcp_write is going to be called again
240      * before this segment is transmitted, we want the oversized
241      * buffer. If the segment will be transmitted immediately, we can
242      * save memory by allocating only length. We use a simple
243      * heuristic based on the following information:
244      *
245      * Did the user set TCP_WRITE_FLAG_MORE?
246      *
247      * Will the Nagle algorithm defer transmission of this segment?
248      */
249     if ((apiflags & TCP_WRITE_FLAG_MORE) ||
250         (!(pcb->flags & TF_NODELAY) &&
251          (!first_seg ||
252           pcb->unsent != NULL ||
253           pcb->unacked != NULL))) {
254       alloc = LWIP_MIN(max_length, LWIP_MEM_ALIGN_SIZE(length + TCP_OVERSIZE));
255     }
256   }
257 #endif /* LWIP_NETIF_TX_SINGLE_PBUF */
258   p = pbuf_alloc(layer, alloc, PBUF_RAM);
259   if (p == NULL) {
260     return NULL;
261   }
262   LWIP_ASSERT("need unchained pbuf", p->next == NULL);
263   *oversize = p->len - length;
264   /* trim p->len to the currently used size */
265   p->len = p->tot_len = length;
266   return p;
267 }
268 #else /* TCP_OVERSIZE */
269 #define tcp_pbuf_prealloc(layer, length, mx, os, pcb, api, fst) pbuf_alloc((layer), (length), PBUF_RAM)
270 #endif /* TCP_OVERSIZE */
271
272 #if TCP_CHECKSUM_ON_COPY
273 /** Add a checksum of newly added data to the segment */
274 static void
275 tcp_seg_add_chksum(u16_t chksum, u16_t len, u16_t *seg_chksum,
276                    u8_t *seg_chksum_swapped)
277 {
278   u32_t helper;
279   /* add chksum to old chksum and fold to u16_t */
280   helper = chksum + *seg_chksum;
281   chksum = FOLD_U32T(helper);
282   if ((len & 1) != 0) {
283     *seg_chksum_swapped = 1 - *seg_chksum_swapped;
284     chksum = SWAP_BYTES_IN_WORD(chksum);
285   }
286   *seg_chksum = chksum;
287 }
288 #endif /* TCP_CHECKSUM_ON_COPY */
289
290 /** Checks if tcp_write is allowed or not (checks state, snd_buf and snd_queuelen).
291  *
292  * @param pcb the tcp pcb to check for
293  * @param len length of data to send (checked agains snd_buf)
294  * @return ERR_OK if tcp_write is allowed to proceed, another err_t otherwise
295  */
296 static err_t
297 tcp_write_checks(struct tcp_pcb *pcb, u16_t len)
298 {
299   /* connection is in invalid state for data transmission? */
300   if ((pcb->state != ESTABLISHED) &&
301       (pcb->state != CLOSE_WAIT) &&
302       (pcb->state != SYN_SENT) &&
303       (pcb->state != SYN_RCVD)) {
304     LWIP_DEBUGF(TCP_OUTPUT_DEBUG | LWIP_DBG_STATE | LWIP_DBG_LEVEL_SEVERE, ("tcp_write() called in invalid state\n"));
305     return ERR_CONN;
306   } else if (len == 0) {
307     return ERR_OK;
308   }
309
310   /* fail on too much data */
311   if (len > pcb->snd_buf) {
312     LWIP_DEBUGF(TCP_OUTPUT_DEBUG | 3, ("tcp_write: too much data (len=%"U16_F" > snd_buf=%"U16_F")\n",
313       len, pcb->snd_buf));
314     pcb->flags |= TF_NAGLEMEMERR;
315     return ERR_MEM;
316   }
317
318   LWIP_DEBUGF(TCP_QLEN_DEBUG, ("tcp_write: queuelen: %"U16_F"\n", (u16_t)pcb->snd_queuelen));
319
320   /* If total number of pbufs on the unsent/unacked queues exceeds the
321    * configured maximum, return an error */
322   /* check for configured max queuelen and possible overflow */
323   if ((pcb->snd_queuelen >= TCP_SND_QUEUELEN) || (pcb->snd_queuelen > TCP_SNDQUEUELEN_OVERFLOW)) {
324     LWIP_DEBUGF(TCP_OUTPUT_DEBUG | 3, ("tcp_write: too long queue %"U16_F" (max %"U16_F")\n",
325       pcb->snd_queuelen, TCP_SND_QUEUELEN));
326     TCP_STATS_INC(tcp.memerr);
327     pcb->flags |= TF_NAGLEMEMERR;
328     return ERR_MEM;
329   }
330   if (pcb->snd_queuelen != 0) {
331     LWIP_ASSERT("tcp_write: pbufs on queue => at least one queue non-empty",
332       pcb->unacked != NULL || pcb->unsent != NULL);
333   } else {
334     LWIP_ASSERT("tcp_write: no pbufs on queue => both queues empty",
335       pcb->unacked == NULL && pcb->unsent == NULL);
336   }
337   return ERR_OK;
338 }
339
340 /**
341  * Write data for sending (but does not send it immediately).
342  *
343  * It waits in the expectation of more data being sent soon (as
344  * it can send them more efficiently by combining them together).
345  * To prompt the system to send data now, call tcp_output() after
346  * calling tcp_write().
347  *
348  * @param pcb Protocol control block for the TCP connection to enqueue data for.
349  * @param arg Pointer to the data to be enqueued for sending.
350  * @param len Data length in bytes
351  * @param apiflags combination of following flags :
352  * - TCP_WRITE_FLAG_COPY (0x01) data will be copied into memory belonging to the stack
353  * - TCP_WRITE_FLAG_MORE (0x02) for TCP connection, PSH flag will be set on last segment sent,
354  * @return ERR_OK if enqueued, another err_t on error
355  */
356 err_t
357 tcp_write(struct tcp_pcb *pcb, const void *arg, u16_t len, u8_t apiflags)
358 {
359   struct pbuf *concat_p = NULL;
360   struct tcp_seg *last_unsent = NULL, *seg = NULL, *prev_seg = NULL, *queue = NULL;
361   u16_t pos = 0; /* position in 'arg' data */
362   u16_t queuelen;
363   u8_t optlen = 0;
364   u8_t optflags = 0;
365 #if TCP_OVERSIZE
366   u16_t oversize = 0;
367   u16_t oversize_used = 0;
368 #endif /* TCP_OVERSIZE */
369 #if TCP_CHECKSUM_ON_COPY
370   u16_t concat_chksum = 0;
371   u8_t concat_chksum_swapped = 0;
372   u16_t concat_chksummed = 0;
373 #endif /* TCP_CHECKSUM_ON_COPY */
374   err_t err;
375
376 #if LWIP_NETIF_TX_SINGLE_PBUF
377   /* Always copy to try to create single pbufs for TX */
378   apiflags |= TCP_WRITE_FLAG_COPY;
379 #endif /* LWIP_NETIF_TX_SINGLE_PBUF */
380
381   LWIP_DEBUGF(TCP_OUTPUT_DEBUG, ("tcp_write(pcb=%p, data=%p, len=%"U16_F", apiflags=%"U16_F")\n",
382     (void *)pcb, arg, len, (u16_t)apiflags));
383   LWIP_ERROR("tcp_write: arg == NULL (programmer violates API)", 
384              arg != NULL, return ERR_ARG;);
385
386   err = tcp_write_checks(pcb, len);
387   if (err != ERR_OK) {
388     return err;
389   }
390   queuelen = pcb->snd_queuelen;
391
392 #if LWIP_TCP_TIMESTAMPS
393   if ((pcb->flags & TF_TIMESTAMP)) {
394     optflags = TF_SEG_OPTS_TS;
395     optlen = LWIP_TCP_OPT_LENGTH(TF_SEG_OPTS_TS);
396   }
397 #endif /* LWIP_TCP_TIMESTAMPS */
398
399
400   /*
401    * TCP segmentation is done in three phases with increasing complexity:
402    *
403    * 1. Copy data directly into an oversized pbuf.
404    * 2. Chain a new pbuf to the end of pcb->unsent.
405    * 3. Create new segments.
406    *
407    * We may run out of memory at any point. In that case we must
408    * return ERR_MEM and not change anything in pcb. Therefore, all
409    * changes are recorded in local variables and committed at the end
410    * of the function. Some pcb fields are maintained in local copies:
411    *
412    * queuelen = pcb->snd_queuelen
413    * oversize = pcb->unsent_oversize
414    *
415    * These variables are set consistently by the phases:
416    *
417    * seg points to the last segment tampered with.
418    *
419    * pos records progress as data is segmented.
420    */
421
422   /* Find the tail of the unsent queue. */
423   if (pcb->unsent != NULL) {
424     u16_t space;
425     u16_t unsent_optlen;
426
427     /* @todo: this could be sped up by keeping last_unsent in the pcb */
428     for (last_unsent = pcb->unsent; last_unsent->next != NULL;
429          last_unsent = last_unsent->next);
430
431     /* Usable space at the end of the last unsent segment */
432     unsent_optlen = LWIP_TCP_OPT_LENGTH(last_unsent->flags);
433     space = pcb->mss - (last_unsent->len + unsent_optlen);
434
435     /*
436      * Phase 1: Copy data directly into an oversized pbuf.
437      *
438      * The number of bytes copied is recorded in the oversize_used
439      * variable. The actual copying is done at the bottom of the
440      * function.
441      */
442 #if TCP_OVERSIZE
443 #if TCP_OVERSIZE_DBGCHECK
444     /* check that pcb->unsent_oversize matches last_unsent->unsent_oversize */
445     LWIP_ASSERT("unsent_oversize mismatch (pcb vs. last_unsent)",
446                 pcb->unsent_oversize == last_unsent->oversize_left);
447 #endif /* TCP_OVERSIZE_DBGCHECK */
448     oversize = pcb->unsent_oversize;
449     if (oversize > 0) {
450       LWIP_ASSERT("inconsistent oversize vs. space", oversize_used <= space);
451       seg = last_unsent;
452       oversize_used = oversize < len ? oversize : len;
453       pos += oversize_used;
454       oversize -= oversize_used;
455       space -= oversize_used;
456     }
457     /* now we are either finished or oversize is zero */
458     LWIP_ASSERT("inconsistend oversize vs. len", (oversize == 0) || (pos == len));
459 #endif /* TCP_OVERSIZE */
460
461     /*
462      * Phase 2: Chain a new pbuf to the end of pcb->unsent.
463      *
464      * We don't extend segments containing SYN/FIN flags or options
465      * (len==0). The new pbuf is kept in concat_p and pbuf_cat'ed at
466      * the end.
467      */
468     if ((pos < len) && (space > 0) && (last_unsent->len > 0)) {
469       u16_t seglen = space < len - pos ? space : len - pos;
470       seg = last_unsent;
471
472       /* Create a pbuf with a copy or reference to seglen bytes. We
473        * can use PBUF_RAW here since the data appears in the middle of
474        * a segment. A header will never be prepended. */
475       if (apiflags & TCP_WRITE_FLAG_COPY) {
476         /* Data is copied */
477         if ((concat_p = tcp_pbuf_prealloc(PBUF_RAW, seglen, space, &oversize, pcb, apiflags, 1)) == NULL) {
478           LWIP_DEBUGF(TCP_OUTPUT_DEBUG | 2,
479                       ("tcp_write : could not allocate memory for pbuf copy size %"U16_F"\n",
480                        seglen));
481           goto memerr;
482         }
483 #if TCP_OVERSIZE_DBGCHECK
484         last_unsent->oversize_left = oversize;
485 #endif /* TCP_OVERSIZE_DBGCHECK */
486         TCP_DATA_COPY2(concat_p->payload, (u8_t*)arg + pos, seglen, &concat_chksum, &concat_chksum_swapped);
487 #if TCP_CHECKSUM_ON_COPY
488         concat_chksummed += seglen;
489 #endif /* TCP_CHECKSUM_ON_COPY */
490       } else {
491         /* Data is not copied */
492         if ((concat_p = pbuf_alloc(PBUF_RAW, seglen, PBUF_ROM)) == NULL) {
493           LWIP_DEBUGF(TCP_OUTPUT_DEBUG | 2,
494                       ("tcp_write: could not allocate memory for zero-copy pbuf\n"));
495           goto memerr;
496         }
497 #if TCP_CHECKSUM_ON_COPY
498         /* calculate the checksum of nocopy-data */
499         tcp_seg_add_chksum(~inet_chksum((u8_t*)arg + pos, seglen), seglen,
500           &concat_chksum, &concat_chksum_swapped);
501         concat_chksummed += seglen;
502 #endif /* TCP_CHECKSUM_ON_COPY */
503         /* reference the non-volatile payload data */
504         concat_p->payload = (u8_t*)arg + pos;
505       }
506
507       pos += seglen;
508       queuelen += pbuf_clen(concat_p);
509     }
510   } else {
511 #if TCP_OVERSIZE
512     LWIP_ASSERT("unsent_oversize mismatch (pcb->unsent is NULL)",
513                 pcb->unsent_oversize == 0);
514 #endif /* TCP_OVERSIZE */
515   }
516
517   /*
518    * Phase 3: Create new segments.
519    *
520    * The new segments are chained together in the local 'queue'
521    * variable, ready to be appended to pcb->unsent.
522    */
523   while (pos < len) {
524     struct pbuf *p;
525     u16_t left = len - pos;
526     u16_t max_len = pcb->mss - optlen;
527     u16_t seglen = left > max_len ? max_len : left;
528 #if TCP_CHECKSUM_ON_COPY
529     u16_t chksum = 0;
530     u8_t chksum_swapped = 0;
531 #endif /* TCP_CHECKSUM_ON_COPY */
532
533     if (apiflags & TCP_WRITE_FLAG_COPY) {
534       /* If copy is set, memory should be allocated and data copied
535        * into pbuf */
536       if ((p = tcp_pbuf_prealloc(PBUF_TRANSPORT, seglen + optlen, pcb->mss, &oversize, pcb, apiflags, queue == NULL)) == NULL) {
537         LWIP_DEBUGF(TCP_OUTPUT_DEBUG | 2, ("tcp_write : could not allocate memory for pbuf copy size %"U16_F"\n", seglen));
538         goto memerr;
539       }
540       LWIP_ASSERT("tcp_write: check that first pbuf can hold the complete seglen",
541                   (p->len >= seglen));
542       TCP_DATA_COPY2((char *)p->payload + optlen, (u8_t*)arg + pos, seglen, &chksum, &chksum_swapped);
543     } else {
544       /* Copy is not set: First allocate a pbuf for holding the data.
545        * Since the referenced data is available at least until it is
546        * sent out on the link (as it has to be ACKed by the remote
547        * party) we can safely use PBUF_ROM instead of PBUF_REF here.
548        */
549       struct pbuf *p2;
550 #if TCP_OVERSIZE
551       LWIP_ASSERT("oversize == 0", oversize == 0);
552 #endif /* TCP_OVERSIZE */
553       if ((p2 = pbuf_alloc(PBUF_TRANSPORT, seglen, PBUF_ROM)) == NULL) {
554         LWIP_DEBUGF(TCP_OUTPUT_DEBUG | 2, ("tcp_write: could not allocate memory for zero-copy pbuf\n"));
555         goto memerr;
556       }
557 #if TCP_CHECKSUM_ON_COPY
558       /* calculate the checksum of nocopy-data */
559       chksum = ~inet_chksum((u8_t*)arg + pos, seglen);
560 #endif /* TCP_CHECKSUM_ON_COPY */
561       /* reference the non-volatile payload data */
562       p2->payload = (u8_t*)arg + pos;
563
564       /* Second, allocate a pbuf for the headers. */
565       if ((p = pbuf_alloc(PBUF_TRANSPORT, optlen, PBUF_RAM)) == NULL) {
566         /* If allocation fails, we have to deallocate the data pbuf as
567          * well. */
568         pbuf_free(p2);
569         LWIP_DEBUGF(TCP_OUTPUT_DEBUG | 2, ("tcp_write: could not allocate memory for header pbuf\n"));
570         goto memerr;
571       }
572       /* Concatenate the headers and data pbufs together. */
573       pbuf_cat(p/*header*/, p2/*data*/);
574     }
575
576     queuelen += pbuf_clen(p);
577
578     /* Now that there are more segments queued, we check again if the
579      * length of the queue exceeds the configured maximum or
580      * overflows. */
581     if ((queuelen > TCP_SND_QUEUELEN) || (queuelen > TCP_SNDQUEUELEN_OVERFLOW)) {
582       LWIP_DEBUGF(TCP_OUTPUT_DEBUG | 2, ("tcp_write: queue too long %"U16_F" (%"U16_F")\n", queuelen, TCP_SND_QUEUELEN));
583       pbuf_free(p);
584       goto memerr;
585     }
586
587     if ((seg = tcp_create_segment(pcb, p, 0, pcb->snd_lbb + pos, optflags)) == NULL) {
588       goto memerr;
589     }
590 #if TCP_OVERSIZE_DBGCHECK
591     seg->oversize_left = oversize;
592 #endif /* TCP_OVERSIZE_DBGCHECK */
593 #if TCP_CHECKSUM_ON_COPY
594     seg->chksum = chksum;
595     seg->chksum_swapped = chksum_swapped;
596     seg->flags |= TF_SEG_DATA_CHECKSUMMED;
597 #endif /* TCP_CHECKSUM_ON_COPY */
598
599     /* first segment of to-be-queued data? */
600     if (queue == NULL) {
601       queue = seg;
602     } else {
603       /* Attach the segment to the end of the queued segments */
604       LWIP_ASSERT("prev_seg != NULL", prev_seg != NULL);
605       prev_seg->next = seg;
606     }
607     /* remember last segment of to-be-queued data for next iteration */
608     prev_seg = seg;
609
610     LWIP_DEBUGF(TCP_OUTPUT_DEBUG | LWIP_DBG_TRACE, ("tcp_write: queueing %"U32_F":%"U32_F"\n",
611       ntohl(seg->tcphdr->seqno),
612       ntohl(seg->tcphdr->seqno) + TCP_TCPLEN(seg)));
613
614     pos += seglen;
615   }
616
617   /*
618    * All three segmentation phases were successful. We can commit the
619    * transaction.
620    */
621
622   /*
623    * Phase 1: If data has been added to the preallocated tail of
624    * last_unsent, we update the length fields of the pbuf chain.
625    */
626 #if TCP_OVERSIZE
627   if (oversize_used > 0) {
628     struct pbuf *p;
629     /* Bump tot_len of whole chain, len of tail */
630     for (p = last_unsent->p; p; p = p->next) {
631       p->tot_len += oversize_used;
632       if (p->next == NULL) {
633         TCP_DATA_COPY((char *)p->payload + p->len, arg, oversize_used, last_unsent);
634         p->len += oversize_used;
635       }
636     }
637     last_unsent->len += oversize_used;
638 #if TCP_OVERSIZE_DBGCHECK
639     last_unsent->oversize_left -= oversize_used;
640 #endif /* TCP_OVERSIZE_DBGCHECK */
641   }
642   pcb->unsent_oversize = oversize;
643 #endif /* TCP_OVERSIZE */
644
645   /*
646    * Phase 2: concat_p can be concatenated onto last_unsent->p
647    */
648   if (concat_p != NULL) {
649     LWIP_ASSERT("tcp_write: cannot concatenate when pcb->unsent is empty",
650       (last_unsent != NULL));
651     pbuf_cat(last_unsent->p, concat_p);
652     last_unsent->len += concat_p->tot_len;
653 #if TCP_CHECKSUM_ON_COPY
654     if (concat_chksummed) {
655       tcp_seg_add_chksum(concat_chksum, concat_chksummed, &last_unsent->chksum,
656         &last_unsent->chksum_swapped);
657       last_unsent->flags |= TF_SEG_DATA_CHECKSUMMED;
658     }
659 #endif /* TCP_CHECKSUM_ON_COPY */
660   }
661
662   /*
663    * Phase 3: Append queue to pcb->unsent. Queue may be NULL, but that
664    * is harmless
665    */
666   if (last_unsent == NULL) {
667     pcb->unsent = queue;
668   } else {
669     last_unsent->next = queue;
670   }
671
672   /*
673    * Finally update the pcb state.
674    */
675   pcb->snd_lbb += len;
676   pcb->snd_buf -= len;
677   pcb->snd_queuelen = queuelen;
678
679   LWIP_DEBUGF(TCP_QLEN_DEBUG, ("tcp_write: %"S16_F" (after enqueued)\n",
680     pcb->snd_queuelen));
681   if (pcb->snd_queuelen != 0) {
682     LWIP_ASSERT("tcp_write: valid queue length",
683                 pcb->unacked != NULL || pcb->unsent != NULL);
684   }
685
686   /* Set the PSH flag in the last segment that we enqueued. */
687   if (seg != NULL && seg->tcphdr != NULL && ((apiflags & TCP_WRITE_FLAG_MORE)==0)) {
688     TCPH_SET_FLAG(seg->tcphdr, TCP_PSH);
689   }
690
691   return ERR_OK;
692 memerr:
693   pcb->flags |= TF_NAGLEMEMERR;
694   TCP_STATS_INC(tcp.memerr);
695
696   if (concat_p != NULL) {
697     pbuf_free(concat_p);
698   }
699   if (queue != NULL) {
700     tcp_segs_free(queue);
701   }
702   if (pcb->snd_queuelen != 0) {
703     LWIP_ASSERT("tcp_write: valid queue length", pcb->unacked != NULL ||
704       pcb->unsent != NULL);
705   }
706   LWIP_DEBUGF(TCP_QLEN_DEBUG | LWIP_DBG_STATE, ("tcp_write: %"S16_F" (with mem err)\n", pcb->snd_queuelen));
707   return ERR_MEM;
708 }
709
710 /**
711  * Enqueue TCP options for transmission.
712  *
713  * Called by tcp_connect(), tcp_listen_input(), and tcp_send_ctrl().
714  *
715  * @param pcb Protocol control block for the TCP connection.
716  * @param flags TCP header flags to set in the outgoing segment.
717  * @param optdata pointer to TCP options, or NULL.
718  * @param optlen length of TCP options in bytes.
719  */
720 err_t
721 tcp_enqueue_flags(struct tcp_pcb *pcb, u8_t flags)
722 {
723   struct pbuf *p;
724   struct tcp_seg *seg;
725   u8_t optflags = 0;
726   u8_t optlen = 0;
727
728   LWIP_DEBUGF(TCP_QLEN_DEBUG, ("tcp_enqueue_flags: queuelen: %"U16_F"\n", (u16_t)pcb->snd_queuelen));
729
730   LWIP_ASSERT("tcp_enqueue_flags: need either TCP_SYN or TCP_FIN in flags (programmer violates API)",
731               (flags & (TCP_SYN | TCP_FIN)) != 0);
732
733   /* check for configured max queuelen and possible overflow */
734   if ((pcb->snd_queuelen >= TCP_SND_QUEUELEN) || (pcb->snd_queuelen > TCP_SNDQUEUELEN_OVERFLOW)) {
735     LWIP_DEBUGF(TCP_OUTPUT_DEBUG | 3, ("tcp_enqueue_flags: too long queue %"U16_F" (max %"U16_F")\n",
736                                        pcb->snd_queuelen, TCP_SND_QUEUELEN));
737     TCP_STATS_INC(tcp.memerr);
738     pcb->flags |= TF_NAGLEMEMERR;
739     return ERR_MEM;
740   }
741
742   if (flags & TCP_SYN) {
743     optflags = TF_SEG_OPTS_MSS;
744   }
745 #if LWIP_TCP_TIMESTAMPS
746   if ((pcb->flags & TF_TIMESTAMP)) {
747     optflags |= TF_SEG_OPTS_TS;
748   }
749 #endif /* LWIP_TCP_TIMESTAMPS */
750   optlen = LWIP_TCP_OPT_LENGTH(optflags);
751
752   /* tcp_enqueue_flags is always called with either SYN or FIN in flags.
753    * We need one available snd_buf byte to do that.
754    * This means we can't send FIN while snd_buf==0. A better fix would be to
755    * not include SYN and FIN sequence numbers in the snd_buf count. */
756   if (pcb->snd_buf == 0) {
757     LWIP_DEBUGF(TCP_OUTPUT_DEBUG | 3, ("tcp_enqueue_flags: no send buffer available\n"));
758     TCP_STATS_INC(tcp.memerr);
759     return ERR_MEM;
760   }
761
762   /* Allocate pbuf with room for TCP header + options */
763   if ((p = pbuf_alloc(PBUF_TRANSPORT, optlen, PBUF_RAM)) == NULL) {
764     pcb->flags |= TF_NAGLEMEMERR;
765     TCP_STATS_INC(tcp.memerr);
766     return ERR_MEM;
767   }
768   LWIP_ASSERT("tcp_enqueue_flags: check that first pbuf can hold optlen",
769               (p->len >= optlen));
770
771   /* Allocate memory for tcp_seg, and fill in fields. */
772   if ((seg = tcp_create_segment(pcb, p, flags, pcb->snd_lbb, optflags)) == NULL) {
773     pcb->flags |= TF_NAGLEMEMERR;
774     TCP_STATS_INC(tcp.memerr);
775     return ERR_MEM;
776   }
777   LWIP_ASSERT("seg->tcphdr not aligned", ((mem_ptr_t)seg->tcphdr % MEM_ALIGNMENT) == 0);
778   LWIP_ASSERT("tcp_enqueue_flags: invalid segment length", seg->len == 0);
779
780   LWIP_DEBUGF(TCP_OUTPUT_DEBUG | LWIP_DBG_TRACE,
781               ("tcp_enqueue_flags: queueing %"U32_F":%"U32_F" (0x%"X16_F")\n",
782                ntohl(seg->tcphdr->seqno),
783                ntohl(seg->tcphdr->seqno) + TCP_TCPLEN(seg),
784                (u16_t)flags));
785
786   /* Now append seg to pcb->unsent queue */
787   if (pcb->unsent == NULL) {
788     pcb->unsent = seg;
789   } else {
790     struct tcp_seg *useg;
791     for (useg = pcb->unsent; useg->next != NULL; useg = useg->next);
792     useg->next = seg;
793   }
794 #if TCP_OVERSIZE
795   /* The new unsent tail has no space */
796   pcb->unsent_oversize = 0;
797 #endif /* TCP_OVERSIZE */
798
799   /* SYN and FIN bump the sequence number */
800   if ((flags & TCP_SYN) || (flags & TCP_FIN)) {
801     pcb->snd_lbb++;
802     /* optlen does not influence snd_buf */
803     pcb->snd_buf--;
804   }
805   if (flags & TCP_FIN) {
806     pcb->flags |= TF_FIN;
807   }
808
809   /* update number of segments on the queues */
810   pcb->snd_queuelen += pbuf_clen(seg->p);
811   LWIP_DEBUGF(TCP_QLEN_DEBUG, ("tcp_enqueue_flags: %"S16_F" (after enqueued)\n", pcb->snd_queuelen));
812   if (pcb->snd_queuelen != 0) {
813     LWIP_ASSERT("tcp_enqueue_flags: invalid queue length",
814       pcb->unacked != NULL || pcb->unsent != NULL);
815   }
816
817   return ERR_OK;
818 }
819
820 #if LWIP_TCP_TIMESTAMPS
821 /* Build a timestamp option (12 bytes long) at the specified options pointer)
822  *
823  * @param pcb tcp_pcb
824  * @param opts option pointer where to store the timestamp option
825  */
826 static void
827 tcp_build_timestamp_option(struct tcp_pcb *pcb, u32_t *opts)
828 {
829   /* Pad with two NOP options to make everything nicely aligned */
830   opts[0] = PP_HTONL(0x0101080A);
831   opts[1] = htonl(sys_now());
832   opts[2] = htonl(pcb->ts_recent);
833 }
834 #endif
835
836 /** Send an ACK without data.
837  *
838  * @param pcb Protocol control block for the TCP connection to send the ACK
839  */
840 err_t
841 tcp_send_empty_ack(struct tcp_pcb *pcb)
842 {
843   struct pbuf *p;
844   struct tcp_hdr *tcphdr;
845   u8_t optlen = 0;
846
847 #if LWIP_TCP_TIMESTAMPS
848   if (pcb->flags & TF_TIMESTAMP) {
849     optlen = LWIP_TCP_OPT_LENGTH(TF_SEG_OPTS_TS);
850   }
851 #endif
852
853   p = tcp_output_alloc_header(pcb, optlen, 0, htonl(pcb->snd_nxt));
854   if (p == NULL) {
855     LWIP_DEBUGF(TCP_OUTPUT_DEBUG, ("tcp_output: (ACK) could not allocate pbuf\n"));
856     return ERR_BUF;
857   }
858   tcphdr = (struct tcp_hdr *)p->payload;
859   LWIP_DEBUGF(TCP_OUTPUT_DEBUG, 
860               ("tcp_output: sending ACK for %"U32_F"\n", pcb->rcv_nxt));
861   /* remove ACK flags from the PCB, as we send an empty ACK now */
862   pcb->flags &= ~(TF_ACK_DELAY | TF_ACK_NOW);
863
864   /* NB. MSS option is only sent on SYNs, so ignore it here */
865 #if LWIP_TCP_TIMESTAMPS
866   pcb->ts_lastacksent = pcb->rcv_nxt;
867
868   if (pcb->flags & TF_TIMESTAMP) {
869     tcp_build_timestamp_option(pcb, (u32_t *)(tcphdr + 1));
870   }
871 #endif 
872
873 #if CHECKSUM_GEN_TCP
874   tcphdr->chksum = ipX_chksum_pseudo(PCB_ISIPV6(pcb), p, IP_PROTO_TCP, p->tot_len,
875     &pcb->local_ip, &pcb->remote_ip);
876 #endif
877 #if LWIP_NETIF_HWADDRHINT
878   ipX_output_hinted(PCB_ISIPV6(pcb), p, &pcb->local_ip, &pcb->remote_ip, pcb->ttl, pcb->tos,
879       IP_PROTO_TCP, &pcb->addr_hint);
880 #else /* LWIP_NETIF_HWADDRHINT*/
881   ipX_output(PCB_ISIPV6(pcb), p, &pcb->local_ip, &pcb->remote_ip, pcb->ttl, pcb->tos,
882       IP_PROTO_TCP);
883 #endif /* LWIP_NETIF_HWADDRHINT*/
884   pbuf_free(p);
885
886   return ERR_OK;
887 }
888
889 /**
890  * Find out what we can send and send it
891  *
892  * @param pcb Protocol control block for the TCP connection to send data
893  * @return ERR_OK if data has been sent or nothing to send
894  *         another err_t on error
895  */
896 err_t
897 tcp_output(struct tcp_pcb *pcb)
898 {
899   struct tcp_seg *seg, *useg;
900   u32_t wnd, snd_nxt;
901 #if TCP_CWND_DEBUG
902   s16_t i = 0;
903 #endif /* TCP_CWND_DEBUG */
904
905   /* pcb->state LISTEN not allowed here */
906   LWIP_ASSERT("don't call tcp_output for listen-pcbs",
907     pcb->state != LISTEN);
908
909   /* First, check if we are invoked by the TCP input processing
910      code. If so, we do not output anything. Instead, we rely on the
911      input processing code to call us when input processing is done
912      with. */
913   if (tcp_input_pcb == pcb) {
914     return ERR_OK;
915   }
916
917   wnd = LWIP_MIN(pcb->snd_wnd, pcb->cwnd);
918
919   seg = pcb->unsent;
920
921   /* If the TF_ACK_NOW flag is set and no data will be sent (either
922    * because the ->unsent queue is empty or because the window does
923    * not allow it), construct an empty ACK segment and send it.
924    *
925    * If data is to be sent, we will just piggyback the ACK (see below).
926    */
927   if (pcb->flags & TF_ACK_NOW &&
928      (seg == NULL ||
929       ntohl(seg->tcphdr->seqno) - pcb->lastack + seg->len > wnd)) {
930      return tcp_send_empty_ack(pcb);
931   }
932
933   /* useg should point to last segment on unacked queue */
934   useg = pcb->unacked;
935   if (useg != NULL) {
936     for (; useg->next != NULL; useg = useg->next);
937   }
938
939 #if TCP_OUTPUT_DEBUG
940   if (seg == NULL) {
941     LWIP_DEBUGF(TCP_OUTPUT_DEBUG, ("tcp_output: nothing to send (%p)\n",
942                                    (void*)pcb->unsent));
943   }
944 #endif /* TCP_OUTPUT_DEBUG */
945 #if TCP_CWND_DEBUG
946   if (seg == NULL) {
947     LWIP_DEBUGF(TCP_CWND_DEBUG, ("tcp_output: snd_wnd %"U16_F
948                                  ", cwnd %"U16_F", wnd %"U32_F
949                                  ", seg == NULL, ack %"U32_F"\n",
950                                  pcb->snd_wnd, pcb->cwnd, wnd, pcb->lastack));
951   } else {
952     LWIP_DEBUGF(TCP_CWND_DEBUG, 
953                 ("tcp_output: snd_wnd %"U16_F", cwnd %"U16_F", wnd %"U32_F
954                  ", effwnd %"U32_F", seq %"U32_F", ack %"U32_F"\n",
955                  pcb->snd_wnd, pcb->cwnd, wnd,
956                  ntohl(seg->tcphdr->seqno) - pcb->lastack + seg->len,
957                  ntohl(seg->tcphdr->seqno), pcb->lastack));
958   }
959 #endif /* TCP_CWND_DEBUG */
960   /* data available and window allows it to be sent? */
961   while (seg != NULL &&
962          ntohl(seg->tcphdr->seqno) - pcb->lastack + seg->len <= wnd) {
963     LWIP_ASSERT("RST not expected here!", 
964                 (TCPH_FLAGS(seg->tcphdr) & TCP_RST) == 0);
965     /* Stop sending if the nagle algorithm would prevent it
966      * Don't stop:
967      * - if tcp_write had a memory error before (prevent delayed ACK timeout) or
968      * - if FIN was already enqueued for this PCB (SYN is always alone in a segment -
969      *   either seg->next != NULL or pcb->unacked == NULL;
970      *   RST is no sent using tcp_write/tcp_output.
971      */
972     if((tcp_do_output_nagle(pcb) == 0) &&
973       ((pcb->flags & (TF_NAGLEMEMERR | TF_FIN)) == 0)){
974       break;
975     }
976 #if TCP_CWND_DEBUG
977     LWIP_DEBUGF(TCP_CWND_DEBUG, ("tcp_output: snd_wnd %"U16_F", cwnd %"U16_F", wnd %"U32_F", effwnd %"U32_F", seq %"U32_F", ack %"U32_F", i %"S16_F"\n",
978                             pcb->snd_wnd, pcb->cwnd, wnd,
979                             ntohl(seg->tcphdr->seqno) + seg->len -
980                             pcb->lastack,
981                             ntohl(seg->tcphdr->seqno), pcb->lastack, i));
982     ++i;
983 #endif /* TCP_CWND_DEBUG */
984
985     pcb->unsent = seg->next;
986
987     if (pcb->state != SYN_SENT) {
988       TCPH_SET_FLAG(seg->tcphdr, TCP_ACK);
989       pcb->flags &= ~(TF_ACK_DELAY | TF_ACK_NOW);
990     }
991
992     tcp_output_segment(seg, pcb);
993     snd_nxt = ntohl(seg->tcphdr->seqno) + TCP_TCPLEN(seg);
994     if (TCP_SEQ_LT(pcb->snd_nxt, snd_nxt)) {
995       pcb->snd_nxt = snd_nxt;
996     }
997     /* put segment on unacknowledged list if length > 0 */
998     if (TCP_TCPLEN(seg) > 0) {
999       seg->next = NULL;
1000       /* unacked list is empty? */
1001       if (pcb->unacked == NULL) {
1002         pcb->unacked = seg;
1003         useg = seg;
1004       /* unacked list is not empty? */
1005       } else {
1006         /* In the case of fast retransmit, the packet should not go to the tail
1007          * of the unacked queue, but rather somewhere before it. We need to check for
1008          * this case. -STJ Jul 27, 2004 */
1009         if (TCP_SEQ_LT(ntohl(seg->tcphdr->seqno), ntohl(useg->tcphdr->seqno))) {
1010           /* add segment to before tail of unacked list, keeping the list sorted */
1011           struct tcp_seg **cur_seg = &(pcb->unacked);
1012           while (*cur_seg &&
1013             TCP_SEQ_LT(ntohl((*cur_seg)->tcphdr->seqno), ntohl(seg->tcphdr->seqno))) {
1014               cur_seg = &((*cur_seg)->next );
1015           }
1016           seg->next = (*cur_seg);
1017           (*cur_seg) = seg;
1018         } else {
1019           /* add segment to tail of unacked list */
1020           useg->next = seg;
1021           useg = useg->next;
1022         }
1023       }
1024     /* do not queue empty segments on the unacked list */
1025     } else {
1026       tcp_seg_free(seg);
1027     }
1028     seg = pcb->unsent;
1029   }
1030 #if TCP_OVERSIZE
1031   if (pcb->unsent == NULL) {
1032     /* last unsent has been removed, reset unsent_oversize */
1033     pcb->unsent_oversize = 0;
1034   }
1035 #endif /* TCP_OVERSIZE */
1036
1037   pcb->flags &= ~TF_NAGLEMEMERR;
1038   return ERR_OK;
1039 }
1040
1041 /**
1042  * Called by tcp_output() to actually send a TCP segment over IP.
1043  *
1044  * @param seg the tcp_seg to send
1045  * @param pcb the tcp_pcb for the TCP connection used to send the segment
1046  */
1047 static void
1048 tcp_output_segment(struct tcp_seg *seg, struct tcp_pcb *pcb)
1049 {
1050   u16_t len;
1051   u32_t *opts;
1052
1053   /** @bug Exclude retransmitted segments from this count. */
1054   snmp_inc_tcpoutsegs();
1055
1056   /* The TCP header has already been constructed, but the ackno and
1057    wnd fields remain. */
1058   seg->tcphdr->ackno = htonl(pcb->rcv_nxt);
1059
1060   /* advertise our receive window size in this TCP segment */
1061   seg->tcphdr->wnd = htons(pcb->rcv_ann_wnd);
1062
1063   pcb->rcv_ann_right_edge = pcb->rcv_nxt + pcb->rcv_ann_wnd;
1064
1065   /* Add any requested options.  NB MSS option is only set on SYN
1066      packets, so ignore it here */
1067   //LWIP_ASSERT("seg->tcphdr not aligned", ((mem_ptr_t)seg->tcphdr % MEM_ALIGNMENT) == 0);
1068   opts = (u32_t *)(void *)(seg->tcphdr + 1);
1069   if (seg->flags & TF_SEG_OPTS_MSS) {
1070     *opts = TCP_BUILD_MSS_OPTION(pcb->mss);
1071     opts += 1;
1072   }
1073 #if LWIP_TCP_TIMESTAMPS
1074   pcb->ts_lastacksent = pcb->rcv_nxt;
1075
1076   if (seg->flags & TF_SEG_OPTS_TS) {
1077     tcp_build_timestamp_option(pcb, opts);
1078     opts += 3;
1079   }
1080 #endif
1081
1082   /* Set retransmission timer running if it is not currently enabled 
1083      This must be set before checking the route. */
1084   if (pcb->rtime == -1) {
1085     pcb->rtime = 0;
1086   }
1087
1088   /* If we don't have a local IP address, we get one by
1089      calling ip_route(). */
1090   if (ipX_addr_isany(PCB_ISIPV6(pcb), &pcb->local_ip)) {
1091     struct netif *netif;
1092     ipX_addr_t *local_ip;
1093     ipX_route_get_local_ipX(PCB_ISIPV6(pcb), &pcb->local_ip, &pcb->remote_ip, netif, local_ip);
1094     if ((netif == NULL) || (local_ip == NULL)) {
1095       return;
1096     }
1097     ipX_addr_copy(PCB_ISIPV6(pcb), pcb->local_ip, *local_ip);
1098   }
1099
1100   if (pcb->rttest == 0) {
1101     pcb->rttest = tcp_ticks;
1102     pcb->rtseq = ntohl(seg->tcphdr->seqno);
1103
1104     LWIP_DEBUGF(TCP_RTO_DEBUG, ("tcp_output_segment: rtseq %"U32_F"\n", pcb->rtseq));
1105   }
1106   LWIP_DEBUGF(TCP_OUTPUT_DEBUG, ("tcp_output_segment: %"U32_F":%"U32_F"\n",
1107           htonl(seg->tcphdr->seqno), htonl(seg->tcphdr->seqno) +
1108           seg->len));
1109
1110   len = (u16_t)((u8_t *)seg->tcphdr - (u8_t *)seg->p->payload);
1111
1112   seg->p->len -= len;
1113   seg->p->tot_len -= len;
1114
1115   seg->p->payload = seg->tcphdr;
1116
1117   seg->tcphdr->chksum = 0;
1118 #if TCP_CHECKSUM_ON_COPY
1119   {
1120     u32_t acc;
1121 #if TCP_CHECKSUM_ON_COPY_SANITY_CHECK
1122     u16_t chksum_slow = ipX_chksum_pseudo(PCB_ISIPV6(pcb), seg->p, IP_PROTO_TCP,
1123       seg->p->tot_len, &pcb->local_ip, &pcb->remote_ip);
1124 #endif /* TCP_CHECKSUM_ON_COPY_SANITY_CHECK */
1125     if ((seg->flags & TF_SEG_DATA_CHECKSUMMED) == 0) {
1126       LWIP_ASSERT("data included but not checksummed",
1127         seg->p->tot_len == (TCPH_HDRLEN(seg->tcphdr) * 4));
1128     }
1129
1130     /* rebuild TCP header checksum (TCP header changes for retransmissions!) */
1131     acc = ipX_chksum_pseudo_partial(PCB_ISIPV6(pcb), seg->p, IP_PROTO_TCP,
1132       seg->p->tot_len, TCPH_HDRLEN(seg->tcphdr) * 4, &pcb->local_ip, &pcb->remote_ip);
1133     /* add payload checksum */
1134     if (seg->chksum_swapped) {
1135       seg->chksum = SWAP_BYTES_IN_WORD(seg->chksum);
1136       seg->chksum_swapped = 0;
1137     }
1138     acc += (u16_t)~(seg->chksum);
1139     seg->tcphdr->chksum = FOLD_U32T(acc);
1140 #if TCP_CHECKSUM_ON_COPY_SANITY_CHECK
1141     if (chksum_slow != seg->tcphdr->chksum) {
1142       LWIP_DEBUGF(TCP_DEBUG | LWIP_DBG_LEVEL_WARNING,
1143                   ("tcp_output_segment: calculated checksum is %"X16_F" instead of %"X16_F"\n",
1144                   seg->tcphdr->chksum, chksum_slow));
1145       seg->tcphdr->chksum = chksum_slow;
1146     }
1147 #endif /* TCP_CHECKSUM_ON_COPY_SANITY_CHECK */
1148   }
1149 #else /* TCP_CHECKSUM_ON_COPY */
1150 #if CHECKSUM_GEN_TCP
1151   seg->tcphdr->chksum = ipX_chksum_pseudo(PCB_ISIPV6(pcb), seg->p, IP_PROTO_TCP,
1152     seg->p->tot_len, &pcb->local_ip, &pcb->remote_ip);
1153 #endif /* CHECKSUM_GEN_TCP */
1154 #endif /* TCP_CHECKSUM_ON_COPY */
1155   TCP_STATS_INC(tcp.xmit);
1156
1157 #if LWIP_NETIF_HWADDRHINT
1158   ipX_output_hinted(PCB_ISIPV6(pcb), seg->p, &pcb->local_ip, &pcb->remote_ip,
1159     pcb->ttl, pcb->tos, IP_PROTO_TCP, &pcb->addr_hint);
1160 #else /* LWIP_NETIF_HWADDRHINT*/
1161   ipX_output(PCB_ISIPV6(pcb), seg->p, &pcb->local_ip, &pcb->remote_ip, pcb->ttl,
1162     pcb->tos, IP_PROTO_TCP);
1163 #endif /* LWIP_NETIF_HWADDRHINT*/
1164 }
1165
1166 /**
1167  * Send a TCP RESET packet (empty segment with RST flag set) either to
1168  * abort a connection or to show that there is no matching local connection
1169  * for a received segment.
1170  *
1171  * Called by tcp_abort() (to abort a local connection), tcp_input() (if no
1172  * matching local pcb was found), tcp_listen_input() (if incoming segment
1173  * has ACK flag set) and tcp_process() (received segment in the wrong state)
1174  *
1175  * Since a RST segment is in most cases not sent for an active connection,
1176  * tcp_rst() has a number of arguments that are taken from a tcp_pcb for
1177  * most other segment output functions.
1178  *
1179  * @param seqno the sequence number to use for the outgoing segment
1180  * @param ackno the acknowledge number to use for the outgoing segment
1181  * @param local_ip the local IP address to send the segment from
1182  * @param remote_ip the remote IP address to send the segment to
1183  * @param local_port the local TCP port to send the segment from
1184  * @param remote_port the remote TCP port to send the segment to
1185  */
1186 void
1187 tcp_rst_impl(u32_t seqno, u32_t ackno,
1188   ipX_addr_t *local_ip, ipX_addr_t *remote_ip,
1189   u16_t local_port, u16_t remote_port
1190 #if LWIP_IPV6
1191   , u8_t isipv6
1192 #endif /* LWIP_IPV6 */
1193   )
1194 {
1195   struct pbuf *p;
1196   struct tcp_hdr *tcphdr;
1197   p = pbuf_alloc(PBUF_IP, TCP_HLEN, PBUF_RAM);
1198   if (p == NULL) {
1199       LWIP_DEBUGF(TCP_DEBUG, ("tcp_rst: could not allocate memory for pbuf\n"));
1200       return;
1201   }
1202   LWIP_ASSERT("check that first pbuf can hold struct tcp_hdr",
1203               (p->len >= sizeof(struct tcp_hdr)));
1204
1205   tcphdr = (struct tcp_hdr *)p->payload;
1206   tcphdr->src = htons(local_port);
1207   tcphdr->dest = htons(remote_port);
1208   tcphdr->seqno = htonl(seqno);
1209   tcphdr->ackno = htonl(ackno);
1210   TCPH_HDRLEN_FLAGS_SET(tcphdr, TCP_HLEN/4, TCP_RST | TCP_ACK);
1211   tcphdr->wnd = PP_HTONS(TCP_WND);
1212   tcphdr->chksum = 0;
1213   tcphdr->urgp = 0;
1214
1215   TCP_STATS_INC(tcp.xmit);
1216   snmp_inc_tcpoutrsts();
1217
1218 #if CHECKSUM_GEN_TCP
1219   tcphdr->chksum = ipX_chksum_pseudo(isipv6, p, IP_PROTO_TCP, p->tot_len,
1220                                      local_ip, remote_ip);
1221 #endif
1222   /* Send output with hardcoded TTL/HL since we have no access to the pcb */
1223   ipX_output(isipv6, p, local_ip, remote_ip, TCP_TTL, 0, IP_PROTO_TCP);
1224   pbuf_free(p);
1225   LWIP_DEBUGF(TCP_RST_DEBUG, ("tcp_rst: seqno %"U32_F" ackno %"U32_F".\n", seqno, ackno));
1226 }
1227
1228 /**
1229  * Requeue all unacked segments for retransmission
1230  *
1231  * Called by tcp_slowtmr() for slow retransmission.
1232  *
1233  * @param pcb the tcp_pcb for which to re-enqueue all unacked segments
1234  */
1235 void
1236 tcp_rexmit_rto(struct tcp_pcb *pcb)
1237 {
1238   struct tcp_seg *seg;
1239
1240   if (pcb->unacked == NULL) {
1241     return;
1242   }
1243
1244   /* Move all unacked segments to the head of the unsent queue */
1245   for (seg = pcb->unacked; seg->next != NULL; seg = seg->next);
1246   /* concatenate unsent queue after unacked queue */
1247   seg->next = pcb->unsent;
1248   /* unsent queue is the concatenated queue (of unacked, unsent) */
1249   pcb->unsent = pcb->unacked;
1250   /* unacked queue is now empty */
1251   pcb->unacked = NULL;
1252   /* last unsent hasn't changed, no need to reset unsent_oversize */
1253
1254   /* increment number of retransmissions */
1255   ++pcb->nrtx;
1256
1257   /* Don't take any RTT measurements after retransmitting. */
1258   pcb->rttest = 0;
1259
1260   /* Do the actual retransmission */
1261   tcp_output(pcb);
1262 }
1263
1264 /**
1265  * Requeue the first unacked segment for retransmission
1266  *
1267  * Called by tcp_receive() for fast retramsmit.
1268  *
1269  * @param pcb the tcp_pcb for which to retransmit the first unacked segment
1270  */
1271 void
1272 tcp_rexmit(struct tcp_pcb *pcb)
1273 {
1274   struct tcp_seg *seg;
1275   struct tcp_seg **cur_seg;
1276
1277   if (pcb->unacked == NULL) {
1278     return;
1279   }
1280
1281   /* Move the first unacked segment to the unsent queue */
1282   /* Keep the unsent queue sorted. */
1283   seg = pcb->unacked;
1284   pcb->unacked = seg->next;
1285
1286   cur_seg = &(pcb->unsent);
1287   while (*cur_seg &&
1288     TCP_SEQ_LT(ntohl((*cur_seg)->tcphdr->seqno), ntohl(seg->tcphdr->seqno))) {
1289       cur_seg = &((*cur_seg)->next );
1290   }
1291   seg->next = *cur_seg;
1292   *cur_seg = seg;
1293 #if TCP_OVERSIZE
1294   if (seg->next == NULL) {
1295     /* the retransmitted segment is last in unsent, so reset unsent_oversize */
1296     pcb->unsent_oversize = 0;
1297   }
1298 #endif /* TCP_OVERSIZE */
1299
1300   ++pcb->nrtx;
1301
1302   /* Don't take any rtt measurements after retransmitting. */
1303   pcb->rttest = 0;
1304
1305   /* Do the actual retransmission. */
1306   snmp_inc_tcpretranssegs();
1307   /* No need to call tcp_output: we are always called from tcp_input()
1308      and thus tcp_output directly returns. */
1309 }
1310
1311
1312 /**
1313  * Handle retransmission after three dupacks received
1314  *
1315  * @param pcb the tcp_pcb for which to retransmit the first unacked segment
1316  */
1317 void 
1318 tcp_rexmit_fast(struct tcp_pcb *pcb)
1319 {
1320   if (pcb->unacked != NULL && !(pcb->flags & TF_INFR)) {
1321     /* This is fast retransmit. Retransmit the first unacked segment. */
1322     LWIP_DEBUGF(TCP_FR_DEBUG, 
1323                 ("tcp_receive: dupacks %"U16_F" (%"U32_F
1324                  "), fast retransmit %"U32_F"\n",
1325                  (u16_t)pcb->dupacks, pcb->lastack,
1326                  ntohl(pcb->unacked->tcphdr->seqno)));
1327     tcp_rexmit(pcb);
1328
1329     /* Set ssthresh to half of the minimum of the current
1330      * cwnd and the advertised window */
1331     if (pcb->cwnd > pcb->snd_wnd) {
1332       pcb->ssthresh = pcb->snd_wnd / 2;
1333     } else {
1334       pcb->ssthresh = pcb->cwnd / 2;
1335     }
1336     
1337     /* The minimum value for ssthresh should be 2 MSS */
1338     if (pcb->ssthresh < 2*pcb->mss) {
1339       LWIP_DEBUGF(TCP_FR_DEBUG, 
1340                   ("tcp_receive: The minimum value for ssthresh %"U16_F
1341                    " should be min 2 mss %"U16_F"...\n",
1342                    pcb->ssthresh, 2*pcb->mss));
1343       pcb->ssthresh = 2*pcb->mss;
1344     }
1345     
1346     pcb->cwnd = pcb->ssthresh + 3 * pcb->mss;
1347     pcb->flags |= TF_INFR;
1348   } 
1349 }
1350
1351
1352 /**
1353  * Send keepalive packets to keep a connection active although
1354  * no data is sent over it.
1355  *
1356  * Called by tcp_slowtmr()
1357  *
1358  * @param pcb the tcp_pcb for which to send a keepalive packet
1359  */
1360 void
1361 tcp_keepalive(struct tcp_pcb *pcb)
1362 {
1363   struct pbuf *p;
1364   struct tcp_hdr *tcphdr;
1365
1366   LWIP_DEBUGF(TCP_DEBUG, ("tcp_keepalive: sending KEEPALIVE probe to "));
1367   ipX_addr_debug_print(PCB_ISIPV6(pcb), TCP_DEBUG, &pcb->remote_ip);
1368   LWIP_DEBUGF(TCP_DEBUG, ("\n"));
1369
1370   LWIP_DEBUGF(TCP_DEBUG, ("tcp_keepalive: tcp_ticks %"U32_F"   pcb->tmr %"U32_F" pcb->keep_cnt_sent %"U16_F"\n", 
1371                           tcp_ticks, pcb->tmr, pcb->keep_cnt_sent));
1372    
1373   p = tcp_output_alloc_header(pcb, 0, 0, htonl(pcb->snd_nxt - 1));
1374   if(p == NULL) {
1375     LWIP_DEBUGF(TCP_DEBUG, 
1376                 ("tcp_keepalive: could not allocate memory for pbuf\n"));
1377     return;
1378   }
1379   tcphdr = (struct tcp_hdr *)p->payload;
1380
1381   tcphdr->chksum = ipX_chksum_pseudo(PCB_ISIPV6(pcb), p, IP_PROTO_TCP, p->tot_len,
1382       &pcb->local_ip, &pcb->remote_ip);
1383   TCP_STATS_INC(tcp.xmit);
1384
1385   /* Send output to IP */
1386 #if LWIP_NETIF_HWADDRHINT
1387   ipX_output_hinted(PCB_ISIPV6(pcb), p, &pcb->local_ip, &pcb->remote_ip,
1388     pcb->ttl, 0, IP_PROTO_TCP, &pcb->addr_hint);
1389 #else /* LWIP_NETIF_HWADDRHINT*/
1390   ipX_output(PCB_ISIPV6(pcb), p, &pcb->local_ip, &pcb->remote_ip, pcb->ttl,
1391     0, IP_PROTO_TCP);
1392 #endif /* LWIP_NETIF_HWADDRHINT*/
1393
1394   pbuf_free(p);
1395
1396   LWIP_DEBUGF(TCP_DEBUG, ("tcp_keepalive: seqno %"U32_F" ackno %"U32_F".\n",
1397                           pcb->snd_nxt - 1, pcb->rcv_nxt));
1398 }
1399
1400
1401 /**
1402  * Send persist timer zero-window probes to keep a connection active
1403  * when a window update is lost.
1404  *
1405  * Called by tcp_slowtmr()
1406  *
1407  * @param pcb the tcp_pcb for which to send a zero-window probe packet
1408  */
1409 void
1410 tcp_zero_window_probe(struct tcp_pcb *pcb)
1411 {
1412   struct pbuf *p;
1413   struct tcp_hdr *tcphdr;
1414   struct tcp_seg *seg;
1415   u16_t len;
1416   u8_t is_fin;
1417
1418   LWIP_DEBUGF(TCP_DEBUG, ("tcp_zero_window_probe: sending ZERO WINDOW probe to "));
1419   ipX_addr_debug_print(PCB_ISIPV6(pcb), TCP_DEBUG, &pcb->remote_ip);
1420   LWIP_DEBUGF(TCP_DEBUG, ("\n"));
1421
1422   LWIP_DEBUGF(TCP_DEBUG, 
1423               ("tcp_zero_window_probe: tcp_ticks %"U32_F
1424                "   pcb->tmr %"U32_F" pcb->keep_cnt_sent %"U16_F"\n", 
1425                tcp_ticks, pcb->tmr, pcb->keep_cnt_sent));
1426
1427   seg = pcb->unacked;
1428
1429   if(seg == NULL) {
1430     seg = pcb->unsent;
1431   }
1432   if(seg == NULL) {
1433     return;
1434   }
1435
1436   is_fin = ((TCPH_FLAGS(seg->tcphdr) & TCP_FIN) != 0) && (seg->len == 0);
1437   /* we want to send one seqno: either FIN or data (no options) */
1438   len = is_fin ? 0 : 1;
1439
1440   p = tcp_output_alloc_header(pcb, 0, len, seg->tcphdr->seqno);
1441   if(p == NULL) {
1442     LWIP_DEBUGF(TCP_DEBUG, ("tcp_zero_window_probe: no memory for pbuf\n"));
1443     return;
1444   }
1445   tcphdr = (struct tcp_hdr *)p->payload;
1446
1447   if (is_fin) {
1448     /* FIN segment, no data */
1449     TCPH_FLAGS_SET(tcphdr, TCP_ACK | TCP_FIN);
1450   } else {
1451     /* Data segment, copy in one byte from the head of the unacked queue */
1452     char *d = ((char *)p->payload + TCP_HLEN);
1453     /* Depending on whether the segment has already been sent (unacked) or not
1454        (unsent), seg->p->payload points to the IP header or TCP header.
1455        Ensure we copy the first TCP data byte: */
1456     pbuf_copy_partial(seg->p, d, 1, seg->p->tot_len - seg->len);
1457   }
1458
1459 #if CHECKSUM_GEN_TCP
1460   tcphdr->chksum = ipX_chksum_pseudo(PCB_ISIPV6(pcb), p, IP_PROTO_TCP, p->tot_len,
1461       &pcb->local_ip, &pcb->remote_ip);
1462 #endif
1463   TCP_STATS_INC(tcp.xmit);
1464
1465   /* Send output to IP */
1466 #if LWIP_NETIF_HWADDRHINT
1467   ipX_output_hinted(PCB_ISIPV6(pcb), p, &pcb->local_ip, &pcb->remote_ip, pcb->ttl,
1468     0, IP_PROTO_TCP, &pcb->addr_hint);
1469 #else /* LWIP_NETIF_HWADDRHINT*/
1470   ipX_output(PCB_ISIPV6(pcb), p, &pcb->local_ip, &pcb->remote_ip, pcb->ttl, 0, IP_PROTO_TCP);
1471 #endif /* LWIP_NETIF_HWADDRHINT*/
1472
1473   pbuf_free(p);
1474
1475   LWIP_DEBUGF(TCP_DEBUG, ("tcp_zero_window_probe: seqno %"U32_F
1476                           " ackno %"U32_F".\n",
1477                           pcb->snd_nxt - 1, pcb->rcv_nxt));
1478 }
1479 #endif /* LWIP_TCP */