From e5555e5c269c72177e20b5a4d1b20434dc4d70f0 Mon Sep 17 00:00:00 2001 From: matt Date: Tue, 7 May 2002 02:59:38 +0000 Subject: [PATCH] Change struct ipqe to use TAILQ's instead of LIST's (primarily for TCP's benefit currently). Rework tcp_reass code to optimize the 4 most likely causes of out-of-order packets: first OoO pkt, next OoO pkt in seq, OoO pkt is part of new chuck of OoO packets, and the OoO pkt fills the first hole. Add evcnts to instrument tcp_reass (enabled by the options TCP_REASS_COUNTERS). This is part 1/2 of tcp_reass changes. --- sys/netinet/ip_input.c | 34 +++++----- sys/netinet/ip_var.h | 11 ++-- sys/netinet/tcp_input.c | 135 +++++++++++++++++++++++++++++++++++----- sys/netinet/tcp_subr.c | 77 ++++++++++++++++++++--- 4 files changed, 211 insertions(+), 46 deletions(-) diff --git a/sys/netinet/ip_input.c b/sys/netinet/ip_input.c index d0c9984deebc..9ae029a5bc4e 100644 --- a/sys/netinet/ip_input.c +++ b/sys/netinet/ip_input.c @@ -1,4 +1,4 @@ -/* $NetBSD: ip_input.c,v 1.147 2002/04/18 22:33:21 matt Exp $ */ +/* $NetBSD: ip_input.c,v 1.148 2002/05/07 02:59:38 matt Exp $ */ /* * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project. @@ -102,7 +102,7 @@ */ #include -__KERNEL_RCSID(0, "$NetBSD: ip_input.c,v 1.147 2002/04/18 22:33:21 matt Exp $"); +__KERNEL_RCSID(0, "$NetBSD: ip_input.c,v 1.148 2002/05/07 02:59:38 matt Exp $"); #include "opt_gateway.h" #include "opt_pfil_hooks.h" @@ -858,7 +858,7 @@ ip_reass(ipqe, fp) fp->ipq_ttl = IPFRAGTTL; fp->ipq_p = ipqe->ipqe_ip->ip_p; fp->ipq_id = ipqe->ipqe_ip->ip_id; - LIST_INIT(&fp->ipq_fragq); + TAILQ_INIT(&fp->ipq_fragq); fp->ipq_src = ipqe->ipqe_ip->ip_src; fp->ipq_dst = ipqe->ipqe_ip->ip_dst; p = NULL; @@ -868,8 +868,8 @@ ip_reass(ipqe, fp) /* * Find a segment which begins after this one does. */ - for (p = NULL, q = LIST_FIRST(&fp->ipq_fragq); q != NULL; - p = q, q = LIST_NEXT(q, ipqe_q)) + for (p = NULL, q = TAILQ_FIRST(&fp->ipq_fragq); q != NULL; + p = q, q = TAILQ_NEXT(q, ipqe_q)) if (q->ipqe_ip->ip_off > ipqe->ipqe_ip->ip_off) break; @@ -904,9 +904,9 @@ ip_reass(ipqe, fp) m_adj(q->ipqe_m, i); break; } - nq = LIST_NEXT(q, ipqe_q); + nq = TAILQ_NEXT(q, ipqe_q); m_freem(q->ipqe_m); - LIST_REMOVE(q, ipqe_q); + TAILQ_REMOVE(&fp->ipq_fragq, q, ipqe_q); pool_put(&ipqent_pool, q); } @@ -916,13 +916,13 @@ insert: * check for complete reassembly. */ if (p == NULL) { - LIST_INSERT_HEAD(&fp->ipq_fragq, ipqe, ipqe_q); + TAILQ_INSERT_HEAD(&fp->ipq_fragq, ipqe, ipqe_q); } else { - LIST_INSERT_AFTER(p, ipqe, ipqe_q); + TAILQ_INSERT_AFTER(&fp->ipq_fragq, p, ipqe, ipqe_q); } next = 0; - for (p = NULL, q = LIST_FIRST(&fp->ipq_fragq); q != NULL; - p = q, q = LIST_NEXT(q, ipqe_q)) { + for (p = NULL, q = TAILQ_FIRST(&fp->ipq_fragq); q != NULL; + p = q, q = TAILQ_NEXT(q, ipqe_q)) { if (q->ipqe_ip->ip_off != next) return (0); next += q->ipqe_ip->ip_len; @@ -934,7 +934,7 @@ insert: * Reassembly is complete. Check for a bogus message size and * concatenate fragments. */ - q = LIST_FIRST(&fp->ipq_fragq); + q = TAILQ_FIRST(&fp->ipq_fragq); ip = q->ipqe_ip; if ((next + (ip->ip_hl << 2)) > IP_MAXPACKET) { ipstat.ips_toolong++; @@ -945,11 +945,11 @@ insert: t = m->m_next; m->m_next = 0; m_cat(m, t); - nq = LIST_NEXT(q, ipqe_q); + nq = TAILQ_NEXT(q, ipqe_q); pool_put(&ipqent_pool, q); for (q = nq; q != NULL; q = nq) { t = q->ipqe_m; - nq = LIST_NEXT(q, ipqe_q); + nq = TAILQ_NEXT(q, ipqe_q); pool_put(&ipqent_pool, q); m_cat(m, t); } @@ -996,10 +996,10 @@ ip_freef(fp) IPQ_LOCK_CHECK(); - for (q = LIST_FIRST(&fp->ipq_fragq); q != NULL; q = p) { - p = LIST_NEXT(q, ipqe_q); + for (q = TAILQ_FIRST(&fp->ipq_fragq); q != NULL; q = p) { + p = TAILQ_NEXT(q, ipqe_q); m_freem(q->ipqe_m); - LIST_REMOVE(q, ipqe_q); + TAILQ_REMOVE(&fp->ipq_fragq, q, ipqe_q); pool_put(&ipqent_pool, q); } LIST_REMOVE(fp, ipq_q); diff --git a/sys/netinet/ip_var.h b/sys/netinet/ip_var.h index e56ac337bbd9..78da28399bb8 100644 --- a/sys/netinet/ip_var.h +++ b/sys/netinet/ip_var.h @@ -1,4 +1,4 @@ -/* $NetBSD: ip_var.h,v 1.46 2001/12/21 02:51:47 itojun Exp $ */ +/* $NetBSD: ip_var.h,v 1.47 2002/05/07 02:59:38 matt Exp $ */ /* * Copyright (c) 1982, 1986, 1993 @@ -63,19 +63,20 @@ struct ipovly { * port numbers (which are no longer needed once we've located the * tcpcb) are overlayed with an mbuf pointer. */ -LIST_HEAD(ipqehead, ipqent); +TAILQ_HEAD(ipqehead, ipqent); struct ipqent { - LIST_ENTRY(ipqent) ipqe_q; + TAILQ_ENTRY(ipqent) ipqe_q; union { struct ip *_ip; struct tcpiphdr *_tcp; } _ipqe_u1; - struct mbuf *ipqe_m; /* mbuf contains packet */ + struct mbuf *ipqe_m; /* point to first mbuf */ + struct mbuf *ipre_mlast; /* point to last mbuf */ u_int8_t ipqe_mff; /* for IP fragmentation */ /* * The following are used in TCP reassembly */ - LIST_ENTRY(ipqent) ipqe_timeq; + TAILQ_ENTRY(ipqent) ipqe_timeq; u_int32_t ipqe_seq; u_int32_t ipqe_len; u_int32_t ipqe_flags; diff --git a/sys/netinet/tcp_input.c b/sys/netinet/tcp_input.c index 7c438aec2f3e..3b64b9f5cafa 100644 --- a/sys/netinet/tcp_input.c +++ b/sys/netinet/tcp_input.c @@ -1,4 +1,4 @@ -/* $NetBSD: tcp_input.c,v 1.140 2002/03/24 17:09:01 christos Exp $ */ +/* $NetBSD: tcp_input.c,v 1.141 2002/05/07 02:59:38 matt Exp $ */ /* * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project. @@ -152,7 +152,7 @@ */ #include -__KERNEL_RCSID(0, "$NetBSD: tcp_input.c,v 1.140 2002/03/24 17:09:01 christos Exp $"); +__KERNEL_RCSID(0, "$NetBSD: tcp_input.c,v 1.141 2002/05/07 02:59:38 matt Exp $"); #include "opt_inet.h" #include "opt_ipsec.h" @@ -292,6 +292,31 @@ extern struct evcnt tcp_swcsum; #endif /* TCP_CSUM_COUNTERS */ +#ifdef TCP_REASS_COUNTERS +#include + +extern struct evcnt tcp_reass_; +extern struct evcnt tcp_reass_empty; +extern struct evcnt tcp_reass_iteration[8]; +extern struct evcnt tcp_reass_prependfirst; +extern struct evcnt tcp_reass_prepend; +extern struct evcnt tcp_reass_insert; +extern struct evcnt tcp_reass_inserttail; +extern struct evcnt tcp_reass_append; +extern struct evcnt tcp_reass_appendtail; +extern struct evcnt tcp_reass_overlaptail; +extern struct evcnt tcp_reass_overlapfront; +extern struct evcnt tcp_reass_segdup; +extern struct evcnt tcp_reass_fragdup; + +#define TCP_REASS_COUNTER_INCR(ev) (ev)->ev_count++ + +#else + +#define TCP_REASS_COUNTER_INCR(ev) /* nothing */ + +#endif /* TCP_REASS_COUNTERS */ + int tcp_reass(tp, th, m, tlen) struct tcpcb *tp; @@ -306,6 +331,9 @@ tcp_reass(tp, th, m, tlen) unsigned pkt_len; u_long rcvpartdupbyte = 0; u_long rcvoobyte; +#ifdef TCP_REASS_COUNTERS + u_int count = 0; +#endif if (tp->t_inpcb) so = tp->t_inpcb->inp_socket; @@ -331,11 +359,64 @@ tcp_reass(tp, th, m, tlen) pkt_seq = th->th_seq; pkt_len = *tlen; pkt_flags = th->th_flags; + + TCP_REASS_COUNTER_INCR(&tcp_reass_); + + if ((p = TAILQ_LAST(&tp->segq, ipqehead)) != NULL) { + /* + * When we miss a packet, the vast majority of time we get + * packets that follow it in order. So optimize for that. + */ + if (pkt_seq == p->ipqe_seq + p->ipqe_len) { + p->ipqe_len += pkt_len; + p->ipqe_flags |= pkt_flags; + m_cat(p->ipqe_m, m); + tiqe = p; + TAILQ_REMOVE(&tp->timeq, p, ipqe_timeq); + TCP_REASS_COUNTER_INCR(&tcp_reass_appendtail); + goto skip_replacement; + } + /* + * While we're here, if the pkt is completely beyond + * anything we have, just insert it at the tail. + */ + if (SEQ_GT(pkt_seq, p->ipqe_seq + p->ipqe_len)) { + TCP_REASS_COUNTER_INCR(&tcp_reass_inserttail); + goto insert_it; + } + } + + q = TAILQ_FIRST(&tp->segq); + + if (q != NULL) { + /* + * If this segment immediately precedes the first out-of-order + * block, simply slap the segment in front of it and (mostly) + * skip the complicated logic. + */ + if (pkt_seq + pkt_len == q->ipqe_seq) { + q->ipqe_seq = pkt_seq; + q->ipqe_len += pkt_len; + q->ipqe_flags |= pkt_flags; + m_cat(m, q->ipqe_m); + q->ipqe_m = m; + tiqe = q; + TAILQ_REMOVE(&tp->timeq, q, ipqe_timeq); + TCP_REASS_COUNTER_INCR(&tcp_reass_prependfirst); + goto skip_replacement; + } + } else { + TCP_REASS_COUNTER_INCR(&tcp_reass_empty); + } + /* * Find a segment which begins after this one does. */ - for (p = NULL, q = LIST_FIRST(&tp->segq); q != NULL; q = nq) { - nq = LIST_NEXT(q, ipqe_q); + for (p = NULL; q != NULL; q = nq) { + nq = TAILQ_NEXT(q, ipqe_q); +#ifdef TCP_REASS_COUNTERS + count++; +#endif /* * If the received segment is just right after this * fragment, merge the two together and then check @@ -352,6 +433,7 @@ tcp_reass(tp, th, m, tlen) pkt_seq = q->ipqe_seq; m_cat(q->ipqe_m, m); m = q->ipqe_m; + TCP_REASS_COUNTER_INCR(&tcp_reass_append); goto free_ipqe; } /* @@ -366,8 +448,11 @@ tcp_reass(tp, th, m, tlen) * If the fragment is past the received segment, * it (or any following) can't be concatenated. */ - if (SEQ_GT(q->ipqe_seq, pkt_seq + pkt_len)) + if (SEQ_GT(q->ipqe_seq, pkt_seq + pkt_len)) { + TCP_REASS_COUNTER_INCR(&tcp_reass_insert); break; + } + /* * We've received all the data in this segment before. * mark it as a duplicate and return. @@ -379,6 +464,7 @@ tcp_reass(tp, th, m, tlen) m_freem(m); if (tiqe != NULL) pool_put(&ipqent_pool, tiqe); + TCP_REASS_COUNTER_INCR(&tcp_reass_segdup); return (0); } /* @@ -390,6 +476,7 @@ tcp_reass(tp, th, m, tlen) SEQ_LEQ(q->ipqe_seq + q->ipqe_len, pkt_seq + pkt_len)) { rcvpartdupbyte += q->ipqe_len; m_freem(q->ipqe_m); + TCP_REASS_COUNTER_INCR(&tcp_reass_fragdup); goto free_ipqe; } /* @@ -413,6 +500,7 @@ tcp_reass(tp, th, m, tlen) pkt_seq = q->ipqe_seq; pkt_len += q->ipqe_len - overlap; rcvoobyte -= overlap; + TCP_REASS_COUNTER_INCR(&tcp_reass_overlaptail); goto free_ipqe; } /* @@ -432,6 +520,7 @@ tcp_reass(tp, th, m, tlen) m_adj(m, -overlap); pkt_len -= overlap; rcvpartdupbyte += overlap; + TCP_REASS_COUNTER_INCR(&tcp_reass_overlapfront); rcvoobyte -= overlap; } /* @@ -448,13 +537,14 @@ tcp_reass(tp, th, m, tlen) pkt_len += q->ipqe_len; pkt_flags |= q->ipqe_flags; m_cat(m, q->ipqe_m); - LIST_REMOVE(q, ipqe_q); - LIST_REMOVE(q, ipqe_timeq); + TAILQ_REMOVE(&tp->segq, q, ipqe_q); + TAILQ_REMOVE(&tp->timeq, q, ipqe_timeq); if (tiqe == NULL) { tiqe = q; } else { pool_put(&ipqent_pool, q); } + TCP_REASS_COUNTER_INCR(&tcp_reass_prepend); break; } /* @@ -473,8 +563,8 @@ tcp_reass(tp, th, m, tlen) * to save doing a malloc/free in most instances. */ free_ipqe: - LIST_REMOVE(q, ipqe_q); - LIST_REMOVE(q, ipqe_timeq); + TAILQ_REMOVE(&tp->segq, q, ipqe_q); + TAILQ_REMOVE(&tp->timeq, q, ipqe_timeq); if (tiqe == NULL) { tiqe = q; } else { @@ -482,6 +572,15 @@ tcp_reass(tp, th, m, tlen) } } +#ifdef TCP_REASS_COUNTERS + if (count > 7) + TCP_REASS_COUNTER_INCR(&tcp_reass_iteration[0]); + else if (count > 0) + TCP_REASS_COUNTER_INCR(&tcp_reass_iteration[count]); +#endif + + insert_it: + /* * Allocate a new queue entry since the received segment did not * collapse onto any other out-of-order block; thus we are allocating @@ -516,14 +615,14 @@ tcp_reass(tp, th, m, tlen) tiqe->ipqe_len = pkt_len; tiqe->ipqe_flags = pkt_flags; if (p == NULL) { - LIST_INSERT_HEAD(&tp->segq, tiqe, ipqe_q); + TAILQ_INSERT_HEAD(&tp->segq, tiqe, ipqe_q); #ifdef TCPREASS_DEBUG if (tiqe->ipqe_seq != tp->rcv_nxt) printf("tcp_reass[%p]: insert %u:%u(%u) at front\n", tp, pkt_seq, pkt_seq + pkt_len, pkt_len); #endif } else { - LIST_INSERT_AFTER(p, tiqe, ipqe_q); + TAILQ_INSERT_AFTER(&tp->segq, p, tiqe, ipqe_q); #ifdef TCPREASS_DEBUG printf("tcp_reass[%p]: insert %u:%u(%u) after %u:%u(%u)\n", tp, pkt_seq, pkt_seq + pkt_len, pkt_len, @@ -531,7 +630,9 @@ tcp_reass(tp, th, m, tlen) #endif } - LIST_INSERT_HEAD(&tp->timeq, tiqe, ipqe_timeq); +skip_replacement: + + TAILQ_INSERT_HEAD(&tp->timeq, tiqe, ipqe_timeq); present: /* @@ -540,7 +641,7 @@ present: */ if (TCPS_HAVEESTABLISHED(tp->t_state) == 0) return (0); - q = LIST_FIRST(&tp->segq); + q = TAILQ_FIRST(&tp->segq); if (q == NULL || q->ipqe_seq != tp->rcv_nxt) return (0); if (tp->t_state == TCPS_SYN_RECEIVED && q->ipqe_len) @@ -550,8 +651,8 @@ present: pkt_flags = q->ipqe_flags & TH_FIN; ND6_HINT(tp); - LIST_REMOVE(q, ipqe_q); - LIST_REMOVE(q, ipqe_timeq); + TAILQ_REMOVE(&tp->segq, q, ipqe_q); + TAILQ_REMOVE(&tp->timeq, q, ipqe_timeq); if (so->so_state & SS_CANTRCVMORE) m_freem(q->ipqe_m); else @@ -1375,7 +1476,7 @@ after_listen: return; } } else if (th->th_ack == tp->snd_una && - LIST_FIRST(&tp->segq) == NULL && + TAILQ_FIRST(&tp->segq) == NULL && tlen <= sbspace(&so->so_rcv)) { /* * this is a pure, in-sequence data packet @@ -2122,7 +2223,7 @@ dodata: /* XXX */ /* NOTE: this was TCP_REASS() macro, but used only once */ TCP_REASS_LOCK(tp); if (th->th_seq == tp->rcv_nxt && - LIST_FIRST(&tp->segq) == NULL && + TAILQ_FIRST(&tp->segq) == NULL && tp->t_state == TCPS_ESTABLISHED) { TCP_SETUP_ACK(tp, th); tp->rcv_nxt += tlen; diff --git a/sys/netinet/tcp_subr.c b/sys/netinet/tcp_subr.c index e81329ffbda5..4280f6fb8a2e 100644 --- a/sys/netinet/tcp_subr.c +++ b/sys/netinet/tcp_subr.c @@ -1,4 +1,4 @@ -/* $NetBSD: tcp_subr.c,v 1.125 2002/04/27 01:47:58 thorpej Exp $ */ +/* $NetBSD: tcp_subr.c,v 1.126 2002/05/07 02:59:39 matt Exp $ */ /* * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project. @@ -102,7 +102,7 @@ */ #include -__KERNEL_RCSID(0, "$NetBSD: tcp_subr.c,v 1.125 2002/04/27 01:47:58 thorpej Exp $"); +__KERNEL_RCSID(0, "$NetBSD: tcp_subr.c,v 1.126 2002/05/07 02:59:39 matt Exp $"); #include "opt_inet.h" #include "opt_ipsec.h" @@ -240,6 +240,46 @@ struct evcnt tcp_output_refbig = EVCNT_INITIALIZER(EVCNT_TYPE_MISC, NULL, "tcp", "output reference big"); #endif /* TCP_OUTPUT_COUNTERS */ +#ifdef TCP_REASS_COUNTERS +#include + +struct evcnt tcp_reass_ = EVCNT_INITIALIZER(EVCNT_TYPE_MISC, + NULL, "tcp_reass", "calls"); +struct evcnt tcp_reass_empty = EVCNT_INITIALIZER(EVCNT_TYPE_MISC, + &tcp_reass_, "tcp_reass", "insert into empty queue"); +struct evcnt tcp_reass_iteration[8] = { + EVCNT_INITIALIZER(EVCNT_TYPE_MISC, &tcp_reass_, "tcp_reass", ">7 iterations"), + EVCNT_INITIALIZER(EVCNT_TYPE_MISC, &tcp_reass_, "tcp_reass", "1 iteration"), + EVCNT_INITIALIZER(EVCNT_TYPE_MISC, &tcp_reass_, "tcp_reass", "2 iterations"), + EVCNT_INITIALIZER(EVCNT_TYPE_MISC, &tcp_reass_, "tcp_reass", "3 iterations"), + EVCNT_INITIALIZER(EVCNT_TYPE_MISC, &tcp_reass_, "tcp_reass", "4 iterations"), + EVCNT_INITIALIZER(EVCNT_TYPE_MISC, &tcp_reass_, "tcp_reass", "5 iterations"), + EVCNT_INITIALIZER(EVCNT_TYPE_MISC, &tcp_reass_, "tcp_reass", "6 iterations"), + EVCNT_INITIALIZER(EVCNT_TYPE_MISC, &tcp_reass_, "tcp_reass", "7 iterations"), +}; +struct evcnt tcp_reass_prependfirst = EVCNT_INITIALIZER(EVCNT_TYPE_MISC, + &tcp_reass_, "tcp_reass", "prepend to first"); +struct evcnt tcp_reass_prepend = EVCNT_INITIALIZER(EVCNT_TYPE_MISC, + &tcp_reass_, "tcp_reass", "prepend"); +struct evcnt tcp_reass_insert = EVCNT_INITIALIZER(EVCNT_TYPE_MISC, + &tcp_reass_, "tcp_reass", "insert"); +struct evcnt tcp_reass_inserttail = EVCNT_INITIALIZER(EVCNT_TYPE_MISC, + &tcp_reass_, "tcp_reass", "insert at tail"); +struct evcnt tcp_reass_append = EVCNT_INITIALIZER(EVCNT_TYPE_MISC, + &tcp_reass_, "tcp_reass", "append"); +struct evcnt tcp_reass_appendtail = EVCNT_INITIALIZER(EVCNT_TYPE_MISC, + &tcp_reass_, "tcp_reass", "append to tail fragment"); +struct evcnt tcp_reass_overlaptail = EVCNT_INITIALIZER(EVCNT_TYPE_MISC, + &tcp_reass_, "tcp_reass", "overlap at end"); +struct evcnt tcp_reass_overlapfront = EVCNT_INITIALIZER(EVCNT_TYPE_MISC, + &tcp_reass_, "tcp_reass", "overlap at start"); +struct evcnt tcp_reass_segdup = EVCNT_INITIALIZER(EVCNT_TYPE_MISC, + &tcp_reass_, "tcp_reass", "duplicate segment"); +struct evcnt tcp_reass_fragdup = EVCNT_INITIALIZER(EVCNT_TYPE_MISC, + &tcp_reass_, "tcp_reass", "duplicate fragment"); + +#endif /* TCP_REASS_COUNTERS */ + /* * Tcp initialization */ @@ -291,6 +331,29 @@ tcp_init() evcnt_attach_static(&tcp_output_copybig); evcnt_attach_static(&tcp_output_refbig); #endif /* TCP_OUTPUT_COUNTERS */ + +#ifdef TCP_REASS_COUNTERS + evcnt_attach_static(&tcp_reass_); + evcnt_attach_static(&tcp_reass_empty); + evcnt_attach_static(&tcp_reass_iteration[0]); + evcnt_attach_static(&tcp_reass_iteration[1]); + evcnt_attach_static(&tcp_reass_iteration[2]); + evcnt_attach_static(&tcp_reass_iteration[3]); + evcnt_attach_static(&tcp_reass_iteration[4]); + evcnt_attach_static(&tcp_reass_iteration[5]); + evcnt_attach_static(&tcp_reass_iteration[6]); + evcnt_attach_static(&tcp_reass_iteration[7]); + evcnt_attach_static(&tcp_reass_prependfirst); + evcnt_attach_static(&tcp_reass_prepend); + evcnt_attach_static(&tcp_reass_insert); + evcnt_attach_static(&tcp_reass_inserttail); + evcnt_attach_static(&tcp_reass_append); + evcnt_attach_static(&tcp_reass_appendtail); + evcnt_attach_static(&tcp_reass_overlaptail); + evcnt_attach_static(&tcp_reass_overlapfront); + evcnt_attach_static(&tcp_reass_segdup); + evcnt_attach_static(&tcp_reass_fragdup); +#endif /* TCP_REASS_COUNTERS */ } /* @@ -823,8 +886,8 @@ tcp_newtcpcb(family, aux) if (tp == NULL) return (NULL); bzero((caddr_t)tp, sizeof(struct tcpcb)); - LIST_INIT(&tp->segq); - LIST_INIT(&tp->timeq); + TAILQ_INIT(&tp->segq); + TAILQ_INIT(&tp->timeq); tp->t_family = family; /* may be overridden later on */ tp->t_peermss = tcp_mssdflt; tp->t_ourmss = tcp_mssdflt; @@ -1080,14 +1143,14 @@ tcp_freeq(tp) TCP_REASS_LOCK_CHECK(tp); - while ((qe = LIST_FIRST(&tp->segq)) != NULL) { + while ((qe = TAILQ_FIRST(&tp->segq)) != NULL) { #ifdef TCPREASS_DEBUG printf("tcp_freeq[%p,%d]: %u:%u(%u) 0x%02x\n", tp, i++, qe->ipqe_seq, qe->ipqe_seq + qe->ipqe_len, qe->ipqe_len, qe->ipqe_flags & (TH_SYN|TH_FIN|TH_RST)); #endif - LIST_REMOVE(qe, ipqe_q); - LIST_REMOVE(qe, ipqe_timeq); + TAILQ_REMOVE(&tp->segq, qe, ipqe_q); + TAILQ_REMOVE(&tp->timeq, qe, ipqe_timeq); m_freem(qe->ipqe_m); pool_put(&ipqent_pool, qe); rv = 1;