50 #include "lwip/ip_addr.h"
62 static struct tcp_seg inseg;
63 static struct tcp_hdr *tcphdr;
64 static struct ip_hdr *iphdr;
65 static u32_t seqno, ackno;
69 static u8_t recv_flags;
70 static struct pbuf *recv_data;
72 struct tcp_pcb *tcp_input_pcb;
75 static err_t tcp_process(
struct tcp_pcb *pcb);
76 static void tcp_receive(
struct tcp_pcb *pcb);
77 static void tcp_parseopt(
struct tcp_pcb *pcb);
79 static err_t tcp_listen_input(
struct tcp_pcb_listen *pcb);
80 static err_t tcp_timewait_input(
struct tcp_pcb *pcb);
92 tcp_input(
struct pbuf *p,
struct netif *inp)
94 struct tcp_pcb *pcb, *prev;
95 struct tcp_pcb_listen *lpcb;
97 struct tcp_pcb *lpcb_prev =
NULL;
98 struct tcp_pcb_listen *lpcb_any =
NULL;
112 tcp_debug_print(tcphdr);
136 #if CHECKSUM_CHECK_TCP
144 tcp_debug_print(tcphdr);
156 hdrlen = TCPH_HDRLEN(tcphdr);
168 tcphdr->src =
ntohs(tcphdr->src);
169 tcphdr->dest =
ntohs(tcphdr->dest);
170 seqno = tcphdr->seqno =
ntohl(tcphdr->seqno);
171 ackno = tcphdr->ackno =
ntohl(tcphdr->ackno);
172 tcphdr->wnd =
ntohs(tcphdr->wnd);
174 flags = TCPH_FLAGS(tcphdr);
175 tcplen = p->
tot_len + ((flags & (TCP_FIN | TCP_SYN)) ? 1 : 0);
182 for(pcb = tcp_active_pcbs; pcb !=
NULL; pcb = pcb->next) {
183 LWIP_ASSERT(
"tcp_input: active pcb->state != CLOSED", pcb->state != CLOSED);
184 LWIP_ASSERT(
"tcp_input: active pcb->state != TIME-WAIT", pcb->state != TIME_WAIT);
185 LWIP_ASSERT(
"tcp_input: active pcb->state != LISTEN", pcb->state != LISTEN);
186 if (pcb->remote_port == tcphdr->src &&
187 pcb->local_port == tcphdr->dest &&
194 LWIP_ASSERT(
"tcp_input: pcb->next != pcb (before cache)", pcb->next != pcb);
196 prev->next = pcb->next;
197 pcb->next = tcp_active_pcbs;
198 tcp_active_pcbs = pcb;
200 LWIP_ASSERT(
"tcp_input: pcb->next != pcb (after cache)", pcb->next != pcb);
209 for(pcb = tcp_tw_pcbs; pcb !=
NULL; pcb = pcb->next) {
210 LWIP_ASSERT(
"tcp_input: TIME-WAIT pcb->state == TIME-WAIT", pcb->state == TIME_WAIT);
211 if (pcb->remote_port == tcphdr->src &&
212 pcb->local_port == tcphdr->dest &&
219 tcp_timewait_input(pcb);
228 for(lpcb = tcp_listen_pcbs.listen_pcbs; lpcb !=
NULL; lpcb = lpcb->next) {
229 if (lpcb->local_port == tcphdr->dest) {
247 prev = (
struct tcp_pcb *)lpcb;
262 ((
struct tcp_pcb_listen *)prev)->next = lpcb->next;
264 lpcb->next = tcp_listen_pcbs.listen_pcbs;
266 tcp_listen_pcbs.listen_pcbs = lpcb;
270 tcp_listen_input(lpcb);
278 tcp_debug_print_flags(TCPH_FLAGS(tcphdr));
287 tcp_debug_print_state(pcb->state);
296 inseg.tcphdr = tcphdr;
302 if (pcb->refused_data !=
NULL) {
305 TCP_EVENT_RECV(pcb, pcb->refused_data,
ERR_OK, err);
307 pcb->refused_data =
NULL;
308 }
else if ((err ==
ERR_ABRT) || (tcplen > 0)) {
320 err = tcp_process(pcb);
324 if (recv_flags & TF_RESET) {
329 TCP_EVENT_ERR(pcb->errf, pcb->callback_arg,
ERR_RST);
330 tcp_pcb_remove(&tcp_active_pcbs, pcb);
332 }
else if (recv_flags & TF_CLOSED) {
335 tcp_pcb_remove(&tcp_active_pcbs, pcb);
342 if (pcb->acked > 0) {
343 TCP_EVENT_SENT(pcb, pcb->acked, err);
349 if (recv_data !=
NULL) {
351 if (pcb->flags & TF_RXCLOSED) {
358 if (flags & TCP_PSH) {
363 TCP_EVENT_RECV(pcb, recv_data,
ERR_OK, err);
370 pcb->refused_data = recv_data;
377 if (recv_flags & TF_GOT_FIN) {
383 TCP_EVENT_CLOSED(pcb, err);
389 tcp_input_pcb =
NULL;
394 tcp_debug_print_state(pcb->state);
402 tcp_input_pcb =
NULL;
416 if (!(TCPH_FLAGS(tcphdr) & TCP_RST)) {
419 tcp_rst(ackno, seqno + tcplen,
421 tcphdr->dest, tcphdr->src);
426 LWIP_ASSERT(
"tcp_input: tcp_pcbs_sane()", tcp_pcbs_sane());
443 tcp_listen_input(
struct tcp_pcb_listen *pcb)
445 struct tcp_pcb *npcb;
450 if (flags & TCP_ACK) {
454 tcp_rst(ackno + 1, seqno + tcplen,
456 tcphdr->dest, tcphdr->src);
457 }
else if (flags & TCP_SYN) {
459 #if TCP_LISTEN_BACKLOG
460 if (pcb->accepts_pending >= pcb->backlog) {
465 npcb = tcp_alloc(pcb->prio);
474 #if TCP_LISTEN_BACKLOG
475 pcb->accepts_pending++;
479 npcb->local_port = pcb->local_port;
481 npcb->remote_port = tcphdr->src;
482 npcb->state = SYN_RCVD;
483 npcb->rcv_nxt = seqno + 1;
484 npcb->rcv_ann_right_edge = npcb->rcv_nxt;
485 npcb->snd_wnd = tcphdr->wnd;
486 npcb->ssthresh = npcb->snd_wnd;
487 npcb->snd_wl1 = seqno - 1;
488 npcb->callback_arg = pcb->callback_arg;
489 #if LWIP_CALLBACK_API
490 npcb->accept = pcb->accept;
496 TCP_REG(&tcp_active_pcbs, npcb);
500 #if TCP_CALCULATE_EFF_SEND_MSS
501 npcb->mss = tcp_eff_send_mss(npcb->mss, &(npcb->remote_ip));
507 rc = tcp_enqueue_flags(npcb, TCP_SYN | TCP_ACK);
509 tcp_abandon(npcb, 0);
512 return tcp_output(npcb);
527 tcp_timewait_input(
struct tcp_pcb *pcb)
534 if (flags & TCP_RST) {
538 if (flags & TCP_SYN) {
541 if (TCP_SEQ_BETWEEN(seqno, pcb->rcv_nxt, pcb->rcv_nxt+pcb->rcv_wnd)) {
544 tcphdr->dest, tcphdr->src);
547 }
else if (flags & TCP_FIN) {
550 pcb->tmr = tcp_ticks;
555 pcb->flags |= TF_ACK_NOW;
556 return tcp_output(pcb);
573 tcp_process(
struct tcp_pcb *pcb)
575 struct tcp_seg *rseg;
582 if (flags & TCP_RST) {
584 if (pcb->state == SYN_SENT) {
585 if (ackno == pcb->snd_nxt) {
589 if (TCP_SEQ_BETWEEN(seqno, pcb->rcv_nxt,
590 pcb->rcv_nxt+pcb->rcv_wnd)) {
597 LWIP_ASSERT(
"tcp_input: pcb->state != CLOSED", pcb->state != CLOSED);
598 recv_flags |= TF_RESET;
599 pcb->flags &= ~TF_ACK_DELAY;
603 seqno, pcb->rcv_nxt));
605 seqno, pcb->rcv_nxt));
610 if ((flags & TCP_SYN) && (pcb->state != SYN_SENT && pcb->state != SYN_RCVD)) {
616 if ((pcb->flags & TF_RXCLOSED) == 0) {
618 pcb->tmr = tcp_ticks;
620 pcb->keep_cnt_sent = 0;
625 switch (pcb->state) {
628 pcb->snd_nxt,
ntohl(pcb->unacked->tcphdr->seqno)));
630 if ((flags & TCP_ACK) && (flags & TCP_SYN)
631 && ackno ==
ntohl(pcb->unacked->tcphdr->seqno) + 1) {
633 pcb->rcv_nxt = seqno + 1;
634 pcb->rcv_ann_right_edge = pcb->rcv_nxt;
635 pcb->lastack = ackno;
636 pcb->snd_wnd = tcphdr->wnd;
637 pcb->snd_wl1 = seqno - 1;
638 pcb->state = ESTABLISHED;
640 #if TCP_CALCULATE_EFF_SEND_MSS
641 pcb->mss = tcp_eff_send_mss(pcb->mss, &(pcb->remote_ip));
646 pcb->ssthresh = pcb->mss * 10;
648 pcb->cwnd = ((pcb->cwnd == 1) ? (pcb->mss * 2) : pcb->mss);
649 LWIP_ASSERT(
"pcb->snd_queuelen > 0", (pcb->snd_queuelen > 0));
653 pcb->unacked = rseg->next;
657 if(pcb->unacked ==
NULL)
668 TCP_EVENT_CONNECTED(pcb,
ERR_OK, err);
675 else if (flags & TCP_ACK) {
678 tcphdr->dest, tcphdr->src);
682 if (flags & TCP_ACK) {
684 if (TCP_SEQ_BETWEEN(ackno, pcb->lastack+1, pcb->snd_nxt)) {
686 pcb->state = ESTABLISHED;
688 #if LWIP_CALLBACK_API
692 TCP_EVENT_ACCEPT(pcb,
ERR_OK, err);
702 old_cwnd = pcb->cwnd;
708 if (pcb->acked != 0) {
712 pcb->cwnd = ((old_cwnd == 1) ? (pcb->mss * 2) : pcb->mss);
714 if (recv_flags & TF_GOT_FIN) {
716 pcb->state = CLOSE_WAIT;
721 tcphdr->dest, tcphdr->src);
723 }
else if ((flags & TCP_SYN) && (seqno == pcb->rcv_nxt - 1)) {
732 if (recv_flags & TF_GOT_FIN) {
734 pcb->state = CLOSE_WAIT;
739 if (recv_flags & TF_GOT_FIN) {
740 if ((flags & TCP_ACK) && (ackno == pcb->snd_nxt)) {
742 (
"TCP connection closed: FIN_WAIT_1 %"U16_F" -> %"U16_F".\n", inseg.tcphdr->src, inseg.tcphdr->dest));
745 TCP_RMV(&tcp_active_pcbs, pcb);
746 pcb->state = TIME_WAIT;
747 TCP_REG(&tcp_tw_pcbs, pcb);
750 pcb->state = CLOSING;
752 }
else if ((flags & TCP_ACK) && (ackno == pcb->snd_nxt)) {
753 pcb->state = FIN_WAIT_2;
758 if (recv_flags & TF_GOT_FIN) {
762 TCP_RMV(&tcp_active_pcbs, pcb);
763 pcb->state = TIME_WAIT;
764 TCP_REG(&tcp_tw_pcbs, pcb);
769 if (flags & TCP_ACK && ackno == pcb->snd_nxt) {
772 TCP_RMV(&tcp_active_pcbs, pcb);
773 pcb->state = TIME_WAIT;
774 TCP_REG(&tcp_tw_pcbs, pcb);
779 if (flags & TCP_ACK && ackno == pcb->snd_nxt) {
782 recv_flags |= TF_CLOSED;
798 tcp_oos_insert_segment(
struct tcp_seg *cseg,
struct tcp_seg *next)
800 struct tcp_seg *old_seg;
802 if (TCPH_FLAGS(cseg->tcphdr) & TCP_FIN) {
811 TCP_SEQ_GEQ((seqno + cseg->len),
812 (next->tcphdr->seqno + next->len))) {
814 if (TCPH_FLAGS(next->tcphdr) & TCP_FIN) {
815 TCPH_SET_FLAG(cseg->tcphdr, TCP_FIN);
819 tcp_seg_free(old_seg);
822 TCP_SEQ_GT(seqno + cseg->len, next->tcphdr->seqno)) {
824 cseg->len = (
u16_t)(next->tcphdr->seqno - seqno);
845 tcp_receive(
struct tcp_pcb *pcb)
847 struct tcp_seg *next;
849 struct tcp_seg *prev, *cseg;
854 u32_t right_wnd_edge;
856 int found_dupack = 0;
858 if (
flags & TCP_ACK) {
859 right_wnd_edge = pcb->snd_wnd + pcb->snd_wl2;
862 if (TCP_SEQ_LT(pcb->snd_wl1, seqno) ||
863 (pcb->snd_wl1 == seqno && TCP_SEQ_LT(pcb->snd_wl2, ackno)) ||
864 (pcb->snd_wl2 == ackno && tcphdr->wnd > pcb->snd_wnd)) {
865 pcb->snd_wnd = tcphdr->wnd;
866 pcb->snd_wl1 = seqno;
867 pcb->snd_wl2 = ackno;
868 if (pcb->snd_wnd > 0 && pcb->persist_backoff > 0) {
869 pcb->persist_backoff = 0;
874 if (pcb->snd_wnd != tcphdr->wnd) {
876 (
"tcp_receive: no window update lastack %"U32_F
" ackno %"
877 U32_F
" wl1 %"U32_F
" seqno %"U32_F
" wl2 %"U32_F
"\n",
878 pcb->lastack, ackno, pcb->snd_wl1, seqno, pcb->snd_wl2));
904 if (TCP_SEQ_LEQ(ackno, pcb->lastack)) {
909 if (pcb->snd_wl2 + pcb->snd_wnd == right_wnd_edge){
911 if (pcb->rtime >= 0) {
913 if (pcb->lastack == ackno) {
915 if (pcb->dupacks + 1 > pcb->dupacks)
917 if (pcb->dupacks > 3) {
920 if ((
u16_t)(pcb->cwnd + pcb->mss) > pcb->cwnd) {
921 pcb->cwnd += pcb->mss;
923 }
else if (pcb->dupacks == 3) {
925 tcp_rexmit_fast(pcb);
936 }
else if (TCP_SEQ_BETWEEN(ackno, pcb->lastack+1, pcb->snd_nxt)){
942 if (pcb->flags & TF_INFR) {
943 pcb->flags &= ~TF_INFR;
944 pcb->cwnd = pcb->ssthresh;
951 pcb->rto = (pcb->sa >> 3) + pcb->sv;
954 pcb->acked = (
u16_t)(ackno - pcb->lastack);
956 pcb->snd_buf += pcb->acked;
960 pcb->lastack = ackno;
964 if (pcb->state >= ESTABLISHED) {
965 if (pcb->cwnd < pcb->ssthresh) {
966 if ((
u16_t)(pcb->cwnd + pcb->mss) > pcb->cwnd) {
967 pcb->cwnd += pcb->mss;
971 u16_t new_cwnd = (pcb->cwnd + pcb->mss * pcb->mss / pcb->cwnd);
972 if (new_cwnd > pcb->cwnd) {
973 pcb->cwnd = new_cwnd;
980 pcb->unacked !=
NULL?
981 ntohl(pcb->unacked->tcphdr->seqno): 0,
982 pcb->unacked !=
NULL?
983 ntohl(pcb->unacked->tcphdr->seqno) + TCP_TCPLEN(pcb->unacked): 0));
987 while (pcb->unacked !=
NULL &&
988 TCP_SEQ_LEQ(
ntohl(pcb->unacked->tcphdr->seqno) +
989 TCP_TCPLEN(pcb->unacked), ackno)) {
991 ntohl(pcb->unacked->tcphdr->seqno),
992 ntohl(pcb->unacked->tcphdr->seqno) +
993 TCP_TCPLEN(pcb->unacked)));
996 pcb->unacked = pcb->unacked->next;
999 LWIP_ASSERT(
"pcb->snd_queuelen >= pbuf_clen(next->p)", (pcb->snd_queuelen >=
pbuf_clen(next->p)));
1001 if ((pcb->acked != 0) && ((TCPH_FLAGS(next->tcphdr) & TCP_FIN) != 0)) {
1005 pcb->snd_queuelen -=
pbuf_clen(next->p);
1009 if (pcb->snd_queuelen != 0) {
1010 LWIP_ASSERT(
"tcp_receive: valid queue length", pcb->unacked !=
NULL ||
1011 pcb->unsent !=
NULL);
1017 if(pcb->unacked ==
NULL)
1034 while (pcb->unsent !=
NULL &&
1035 TCP_SEQ_BETWEEN(ackno,
ntohl(pcb->unsent->tcphdr->seqno) +
1036 TCP_TCPLEN(pcb->unsent), pcb->snd_nxt)) {
1038 ntohl(pcb->unsent->tcphdr->seqno),
ntohl(pcb->unsent->tcphdr->seqno) +
1039 TCP_TCPLEN(pcb->unsent)));
1042 pcb->unsent = pcb->unsent->next;
1044 LWIP_ASSERT(
"pcb->snd_queuelen >= pbuf_clen(next->p)", (pcb->snd_queuelen >=
pbuf_clen(next->p)));
1046 if ((pcb->acked != 0) && ((TCPH_FLAGS(next->tcphdr) & TCP_FIN) != 0)) {
1049 pcb->snd_queuelen -=
pbuf_clen(next->p);
1052 if (pcb->snd_queuelen != 0) {
1054 pcb->unacked !=
NULL || pcb->unsent !=
NULL);
1060 pcb->rttest, pcb->rtseq, ackno));
1065 if (pcb->rttest && TCP_SEQ_LT(pcb->rtseq, ackno)) {
1068 m = (
s16_t)(tcp_ticks - pcb->rttest);
1071 m, m * TCP_SLOW_INTERVAL));
1074 m = m - (pcb->sa >> 3);
1079 m = m - (pcb->sv >> 2);
1081 pcb->rto = (pcb->sa >> 3) + pcb->sv;
1084 pcb->rto, pcb->rto * TCP_SLOW_INTERVAL));
1123 if (TCP_SEQ_BETWEEN(pcb->rcv_nxt, seqno + 1, seqno + tcplen - 1)){
1144 off = pcb->rcv_nxt - seqno;
1148 if (inseg.p->len < off) {
1150 new_tot_len = (
u16_t)(inseg.p->tot_len - off);
1151 while (p->
len < off) {
1173 inseg.len -= (
u16_t)(pcb->rcv_nxt - seqno);
1174 inseg.tcphdr->seqno = seqno = pcb->rcv_nxt;
1177 if (TCP_SEQ_LT(seqno, pcb->rcv_nxt)){
1189 if (TCP_SEQ_BETWEEN(seqno, pcb->rcv_nxt,
1190 pcb->rcv_nxt + pcb->rcv_wnd - 1)){
1191 if (pcb->rcv_nxt == seqno) {
1195 tcplen = TCP_TCPLEN(&inseg);
1197 if (tcplen > pcb->rcv_wnd) {
1199 (
"tcp_receive: other end overran receive window"
1200 "seqno %"U32_F
" len %"U16_F" right edge %"U32_F
"\n",
1201 seqno, tcplen, pcb->rcv_nxt + pcb->rcv_wnd));
1202 if (TCPH_FLAGS(inseg.tcphdr) & TCP_FIN) {
1205 TCPH_FLAGS_SET(inseg.tcphdr, TCPH_FLAGS(inseg.tcphdr) &~ TCP_FIN);
1208 inseg.len = pcb->rcv_wnd;
1209 if (TCPH_FLAGS(inseg.tcphdr) & TCP_SYN) {
1213 tcplen = TCP_TCPLEN(&inseg);
1214 LWIP_ASSERT(
"tcp_receive: segment not trimmed correctly to rcv_wnd\n",
1215 (seqno + tcplen) == (pcb->rcv_nxt + pcb->rcv_wnd));
1221 if (pcb->ooseq !=
NULL) {
1222 if (TCPH_FLAGS(inseg.tcphdr) & TCP_FIN) {
1224 (
"tcp_receive: received in-order FIN, binning ooseq queue\n"));
1228 while (pcb->ooseq !=
NULL) {
1229 struct tcp_seg *old_ooseq = pcb->ooseq;
1230 pcb->ooseq = pcb->ooseq->next;
1231 tcp_seg_free(old_ooseq);
1239 TCP_SEQ_GEQ(seqno + tcplen,
1240 next->tcphdr->seqno + next->len)) {
1242 if (TCPH_FLAGS(next->tcphdr) & TCP_FIN &&
1243 (TCPH_FLAGS(inseg.tcphdr) & TCP_SYN) == 0) {
1244 TCPH_SET_FLAG(inseg.tcphdr, TCP_FIN);
1245 tcplen = TCP_TCPLEN(&inseg);
1254 TCP_SEQ_GT(seqno + tcplen,
1255 next->tcphdr->seqno)) {
1257 inseg.len = (
u16_t)(next->tcphdr->seqno - seqno);
1258 if (TCPH_FLAGS(inseg.tcphdr) & TCP_SYN) {
1262 tcplen = TCP_TCPLEN(&inseg);
1263 LWIP_ASSERT(
"tcp_receive: segment not trimmed correctly to ooseq queue\n",
1264 (seqno + tcplen) == next->tcphdr->seqno);
1271 pcb->rcv_nxt = seqno + tcplen;
1274 LWIP_ASSERT(
"tcp_receive: tcplen > rcv_wnd\n", pcb->rcv_wnd >= tcplen);
1275 pcb->rcv_wnd -= tcplen;
1277 tcp_update_rcv_ann_wnd(pcb);
1288 if (inseg.p->tot_len > 0) {
1289 recv_data = inseg.p;
1295 if (TCPH_FLAGS(inseg.tcphdr) & TCP_FIN) {
1297 recv_flags |= TF_GOT_FIN;
1303 while (pcb->ooseq !=
NULL &&
1304 pcb->ooseq->tcphdr->seqno == pcb->rcv_nxt) {
1307 seqno = pcb->ooseq->tcphdr->seqno;
1309 pcb->rcv_nxt += TCP_TCPLEN(cseg);
1310 LWIP_ASSERT(
"tcp_receive: ooseq tcplen > rcv_wnd\n",
1311 pcb->rcv_wnd >= TCP_TCPLEN(cseg));
1312 pcb->rcv_wnd -= TCP_TCPLEN(cseg);
1314 tcp_update_rcv_ann_wnd(pcb);
1316 if (cseg->p->tot_len > 0) {
1322 recv_data = cseg->p;
1326 if (TCPH_FLAGS(cseg->tcphdr) & TCP_FIN) {
1328 recv_flags |= TF_GOT_FIN;
1329 if (pcb->state == ESTABLISHED) {
1330 pcb->state = CLOSE_WAIT;
1334 pcb->ooseq = cseg->next;
1345 tcp_send_empty_ack(pcb);
1348 if (pcb->ooseq ==
NULL) {
1349 pcb->ooseq = tcp_seg_copy(&inseg);
1364 for(next = pcb->ooseq; next !=
NULL; next = next->next) {
1365 if (seqno == next->tcphdr->seqno) {
1370 if (inseg.len > next->len) {
1374 cseg = tcp_seg_copy(&inseg);
1381 tcp_oos_insert_segment(cseg, next);
1392 if (TCP_SEQ_LT(seqno, next->tcphdr->seqno)) {
1397 cseg = tcp_seg_copy(&inseg);
1400 tcp_oos_insert_segment(cseg, next);
1407 if (TCP_SEQ_BETWEEN(seqno, prev->tcphdr->seqno+1, next->tcphdr->seqno-1)) {
1413 cseg = tcp_seg_copy(&inseg);
1415 if (TCP_SEQ_GT(prev->tcphdr->seqno + prev->len, seqno)) {
1417 prev->len = (
u16_t)(seqno - prev->tcphdr->seqno);
1421 tcp_oos_insert_segment(cseg, next);
1429 if (next->next ==
NULL &&
1430 TCP_SEQ_GT(seqno, next->tcphdr->seqno)) {
1431 if (TCPH_FLAGS(next->tcphdr) & TCP_FIN) {
1435 next->next = tcp_seg_copy(&inseg);
1436 if (next->next !=
NULL) {
1437 if (TCP_SEQ_GT(next->tcphdr->seqno + next->len, seqno)) {
1439 next->len = (
u16_t)(seqno - next->tcphdr->seqno);
1443 if ((
u32_t)tcplen + seqno > pcb->rcv_nxt + (
u32_t)pcb->rcv_wnd) {
1445 (
"tcp_receive: other end overran receive window"
1446 "seqno %"U32_F
" len %"U16_F" right edge %"U32_F
"\n",
1447 seqno, tcplen, pcb->rcv_nxt + pcb->rcv_wnd));
1448 if (TCPH_FLAGS(next->next->tcphdr) & TCP_FIN) {
1451 TCPH_FLAGS_SET(next->next->tcphdr, TCPH_FLAGS(next->next->tcphdr) &~ TCP_FIN);
1454 next->next->len = pcb->rcv_nxt + pcb->rcv_wnd - seqno;
1456 tcplen = TCP_TCPLEN(next->next);
1457 LWIP_ASSERT(
"tcp_receive: segment not trimmed correctly to rcv_wnd\n",
1458 (seqno + tcplen) == (pcb->rcv_nxt + pcb->rcv_wnd));
1472 tcp_send_empty_ack(pcb);
1479 if(!TCP_SEQ_BETWEEN(seqno, pcb->rcv_nxt, pcb->rcv_nxt + pcb->rcv_wnd-1)){
1494 tcp_parseopt(
struct tcp_pcb *pcb)
1499 #if LWIP_TCP_TIMESTAMPS
1503 opts = (
u8_t *)tcphdr + TCP_HLEN;
1506 if(TCPH_HDRLEN(tcphdr) > 0x5) {
1507 max_c = (TCPH_HDRLEN(tcphdr) - 5) << 2;
1508 for (c = 0; c < max_c; ) {
1522 if (opts[c + 1] != 0x04 || c + 0x04 > max_c) {
1528 mss = (opts[c + 2] << 8) | opts[c + 3];
1534 #if LWIP_TCP_TIMESTAMPS
1537 if (opts[c + 1] != 0x0A || c + 0x0A > max_c) {
1543 tsval = (opts[c+2]) | (opts[c+3] << 8) |
1544 (opts[c+4] << 16) | (opts[c+5] << 24);
1545 if (flags & TCP_SYN) {
1546 pcb->ts_recent =
ntohl(tsval);
1547 pcb->flags |= TF_TIMESTAMP;
1548 }
else if (TCP_SEQ_BETWEEN(pcb->ts_lastacksent, seqno, seqno+tcplen)) {
1549 pcb->ts_recent =
ntohl(tsval);
1557 if (opts[c + 1] == 0) {