diff options
author | Markus Friedl <markus@cvs.openbsd.org> | 2005-08-02 11:05:45 +0000 |
---|---|---|
committer | Markus Friedl <markus@cvs.openbsd.org> | 2005-08-02 11:05:45 +0000 |
commit | b349f21820bdff22160c34fd6dc2a37bf5f6ed25 (patch) | |
tree | 083b34dbc662062db21f29e577fbc7c2b5573be8 /sys | |
parent | 9c9f4185c4024cbe9bd35802e910d7cc39fb0b55 (diff) |
change the TCP reass queue from LIST to TAILQ;
ok henning claudio fgsch krw
Diffstat (limited to 'sys')
-rw-r--r-- | sys/netinet/ip_var.h | 19 | ||||
-rw-r--r-- | sys/netinet/tcp_input.c | 62 | ||||
-rw-r--r-- | sys/netinet/tcp_subr.c | 14 | ||||
-rw-r--r-- | sys/netinet/tcp_var.h | 16 |
4 files changed, 53 insertions, 58 deletions
diff --git a/sys/netinet/ip_var.h b/sys/netinet/ip_var.h index 33b34eb54f8..3b63a9b8cdc 100644 --- a/sys/netinet/ip_var.h +++ b/sys/netinet/ip_var.h @@ -1,4 +1,4 @@ -/* $OpenBSD: ip_var.h,v 1.33 2005/05/27 04:55:28 mcbride Exp $ */ +/* $OpenBSD: ip_var.h,v 1.34 2005/08/02 11:05:44 markus Exp $ */ /* $NetBSD: ip_var.h,v 1.16 1996/02/13 23:43:20 christos Exp $ */ /* @@ -49,28 +49,15 @@ struct ipovly { }; /* - * Ip (reassembly or sequence) queue structures. - * - * XXX -- The following explains why the ipqe_m field is here, for TCP's use: - * We want to avoid doing m_pullup on incoming packets but that - * means avoiding dtom on the tcp reassembly code. That in turn means - * keeping an mbuf pointer in the reassembly queue (since we might - * have a cluster). As a quick hack, the source & destination - * port numbers (which are no longer needed once we've located the - * tcpcb) are overlayed with an mbuf pointer. + * Ip reassembly queue structures. */ LIST_HEAD(ipqehead, ipqent); struct ipqent { LIST_ENTRY(ipqent) ipqe_q; - union { - struct ip *_ip; - struct tcphdr *_tcp; - } _ipqe_u1; + struct ip *ipqe_ip; struct mbuf *ipqe_m; /* mbuf contains packet */ u_int8_t ipqe_mff; /* for IP fragmentation */ }; -#define ipqe_ip _ipqe_u1._ip -#define ipqe_tcp _ipqe_u1._tcp /* * Ip reassembly queue structure. Each fragment diff --git a/sys/netinet/tcp_input.c b/sys/netinet/tcp_input.c index 3c112d968a6..1e011cfd75a 100644 --- a/sys/netinet/tcp_input.c +++ b/sys/netinet/tcp_input.c @@ -1,4 +1,4 @@ -/* $OpenBSD: tcp_input.c,v 1.188 2005/06/30 08:51:31 markus Exp $ */ +/* $OpenBSD: tcp_input.c,v 1.189 2005/08/02 11:05:44 markus Exp $ */ /* $NetBSD: tcp_input.c,v 1.23 1996/02/13 23:43:44 christos Exp $ */ /* @@ -191,7 +191,7 @@ tcp_reass(tp, th, m, tlen) struct mbuf *m; int *tlen; { - struct ipqent *p, *q, *nq, *tiqe; + struct tcpqent *p, *q, *nq, *tiqe; struct socket *so = tp->t_inpcb->inp_socket; int flags; @@ -208,13 +208,11 @@ tcp_reass(tp, th, m, tlen) */ tiqe = pool_get(&tcpqe_pool, PR_NOWAIT); if (tiqe == NULL) { - tiqe = LIST_FIRST(&tp->segq); + tiqe = TAILQ_LAST(&tp->t_segq, tcpqehead); if (tiqe != NULL && th->th_seq == tp->rcv_nxt) { /* Reuse last entry since new segment fills a hole */ - while ((p = LIST_NEXT(tiqe, ipqe_q)) != NULL) - tiqe = p; - m_freem(tiqe->ipqe_m); - LIST_REMOVE(tiqe, ipqe_q); + m_freem(tiqe->tcpqe_m); + TAILQ_REMOVE(&tp->t_segq, tiqe, tcpqe_q); } if (tiqe == NULL || th->th_seq != tp->rcv_nxt) { /* Flush segment queue for this connection */ @@ -228,9 +226,9 @@ tcp_reass(tp, th, m, tlen) /* * Find a segment which begins after this one does. */ - for (p = NULL, q = tp->segq.lh_first; q != NULL; - p = q, q = q->ipqe_q.le_next) - if (SEQ_GT(q->ipqe_tcp->th_seq, th->th_seq)) + for (p = NULL, q = TAILQ_FIRST(&tp->t_segq); q != NULL; + p = q, q = TAILQ_NEXT(q, tcpqe_q)) + if (SEQ_GT(q->tcpqe_tcp->th_seq, th->th_seq)) break; /* @@ -239,7 +237,7 @@ tcp_reass(tp, th, m, tlen) * segment. If it provides all of our data, drop us. */ if (p != NULL) { - struct tcphdr *phdr = p->ipqe_tcp; + struct tcphdr *phdr = p->tcpqe_tcp; int i; /* conversion to int (in i) handles seq wraparound */ @@ -265,7 +263,7 @@ tcp_reass(tp, th, m, tlen) * if they are completely covered, dequeue them. */ for (; q != NULL; q = nq) { - struct tcphdr *qhdr = q->ipqe_tcp; + struct tcphdr *qhdr = q->tcpqe_tcp; int i = (th->th_seq + *tlen) - qhdr->th_seq; if (i <= 0) @@ -273,23 +271,23 @@ tcp_reass(tp, th, m, tlen) if (i < qhdr->th_reseqlen) { qhdr->th_seq += i; qhdr->th_reseqlen -= i; - m_adj(q->ipqe_m, i); + m_adj(q->tcpqe_m, i); break; } - nq = q->ipqe_q.le_next; - m_freem(q->ipqe_m); - LIST_REMOVE(q, ipqe_q); + nq = TAILQ_NEXT(q, tcpqe_q); + m_freem(q->tcpqe_m); + TAILQ_REMOVE(&tp->t_segq, q, tcpqe_q); pool_put(&tcpqe_pool, q); } /* Insert the new segment queue entry into place. */ - tiqe->ipqe_m = m; + tiqe->tcpqe_m = m; th->th_reseqlen = *tlen; - tiqe->ipqe_tcp = th; + tiqe->tcpqe_tcp = th; if (p == NULL) { - LIST_INSERT_HEAD(&tp->segq, tiqe, ipqe_q); + TAILQ_INSERT_HEAD(&tp->t_segq, tiqe, tcpqe_q); } else { - LIST_INSERT_AFTER(p, tiqe, ipqe_q); + TAILQ_INSERT_AFTER(&tp->t_segq, p, tiqe, tcpqe_q); } present: @@ -299,25 +297,25 @@ present: */ if (TCPS_HAVEESTABLISHED(tp->t_state) == 0) return (0); - q = tp->segq.lh_first; - if (q == NULL || q->ipqe_tcp->th_seq != tp->rcv_nxt) + q = TAILQ_FIRST(&tp->t_segq); + if (q == NULL || q->tcpqe_tcp->th_seq != tp->rcv_nxt) return (0); - if (tp->t_state == TCPS_SYN_RECEIVED && q->ipqe_tcp->th_reseqlen) + if (tp->t_state == TCPS_SYN_RECEIVED && q->tcpqe_tcp->th_reseqlen) return (0); do { - tp->rcv_nxt += q->ipqe_tcp->th_reseqlen; - flags = q->ipqe_tcp->th_flags & TH_FIN; + tp->rcv_nxt += q->tcpqe_tcp->th_reseqlen; + flags = q->tcpqe_tcp->th_flags & TH_FIN; - nq = q->ipqe_q.le_next; - LIST_REMOVE(q, ipqe_q); + nq = TAILQ_NEXT(q, tcpqe_q); + TAILQ_REMOVE(&tp->t_segq, q, tcpqe_q); ND6_HINT(tp); if (so->so_state & SS_CANTRCVMORE) - m_freem(q->ipqe_m); + m_freem(q->tcpqe_m); else - sbappendstream(&so->so_rcv, q->ipqe_m); + sbappendstream(&so->so_rcv, q->tcpqe_m); pool_put(&tcpqe_pool, q); q = nq; - } while (q != NULL && q->ipqe_tcp->th_seq == tp->rcv_nxt); + } while (q != NULL && q->tcpqe_tcp->th_seq == tp->rcv_nxt); sorwakeup(so); return (flags); } @@ -1067,7 +1065,7 @@ after_listen: return; } } else if (th->th_ack == tp->snd_una && - tp->segq.lh_first == NULL && + TAILQ_EMPTY(&tp->t_segq) && tlen <= sbspace(&so->so_rcv)) { /* * This is a pure, in-sequence data packet @@ -2020,7 +2018,7 @@ dodata: /* XXX */ if ((tlen || (tiflags & TH_FIN)) && TCPS_HAVERCVDFIN(tp->t_state) == 0) { tcp_reass_lock(tp); - if (th->th_seq == tp->rcv_nxt && tp->segq.lh_first == NULL && + if (th->th_seq == tp->rcv_nxt && TAILQ_EMPTY(&tp->t_segq) && tp->t_state == TCPS_ESTABLISHED) { tcp_reass_unlock(tp); TCP_SETUP_ACK(tp, tiflags); diff --git a/sys/netinet/tcp_subr.c b/sys/netinet/tcp_subr.c index b39678cc7fb..b8da6bb78b5 100644 --- a/sys/netinet/tcp_subr.c +++ b/sys/netinet/tcp_subr.c @@ -1,4 +1,4 @@ -/* $OpenBSD: tcp_subr.c,v 1.90 2005/06/30 08:51:31 markus Exp $ */ +/* $OpenBSD: tcp_subr.c,v 1.91 2005/08/02 11:05:44 markus Exp $ */ /* $NetBSD: tcp_subr.c,v 1.22 1996/02/13 23:44:00 christos Exp $ */ /* @@ -177,7 +177,7 @@ tcp_init() #endif /* TCP_COMPAT_42 */ pool_init(&tcpcb_pool, sizeof(struct tcpcb), 0, 0, 0, "tcpcbpl", NULL); - pool_init(&tcpqe_pool, sizeof(struct ipqent), 0, 0, 0, "tcpqepl", + pool_init(&tcpqe_pool, sizeof(struct tcpqent), 0, 0, 0, "tcpqepl", NULL); pool_sethardlimit(&tcpqe_pool, tcp_reass_limit, NULL, 0); #ifdef TCP_SACK @@ -492,7 +492,7 @@ tcp_newtcpcb(struct inpcb *inp) if (tp == NULL) return ((struct tcpcb *)0); bzero((char *) tp, sizeof(struct tcpcb)); - LIST_INIT(&tp->segq); + TAILQ_INIT(&tp->t_segq); tp->t_maxseg = tcp_mssdflt; tp->t_maxopd = 0; @@ -628,12 +628,12 @@ tcp_reaper(void *arg) int tcp_freeq(struct tcpcb *tp) { - struct ipqent *qe; + struct tcpqent *qe; int rv = 0; - while ((qe = LIST_FIRST(&tp->segq)) != NULL) { - LIST_REMOVE(qe, ipqe_q); - m_freem(qe->ipqe_m); + while ((qe = TAILQ_FIRST(&tp->t_segq)) != NULL) { + TAILQ_REMOVE(&tp->t_segq, qe, tcpqe_q); + m_freem(qe->tcpqe_m); pool_put(&tcpqe_pool, qe); rv = 1; } diff --git a/sys/netinet/tcp_var.h b/sys/netinet/tcp_var.h index 004cc4b2597..85117aa15f3 100644 --- a/sys/netinet/tcp_var.h +++ b/sys/netinet/tcp_var.h @@ -1,4 +1,4 @@ -/* $OpenBSD: tcp_var.h,v 1.76 2005/07/04 12:34:12 markus Exp $ */ +/* $OpenBSD: tcp_var.h,v 1.77 2005/08/02 11:05:44 markus Exp $ */ /* $NetBSD: tcp_var.h,v 1.17 1996/02/13 23:44:24 christos Exp $ */ /* @@ -35,6 +35,10 @@ #ifndef _NETINET_TCP_VAR_H_ #define _NETINET_TCP_VAR_H_ +/* + * Kernel variables for tcp. + */ + struct sackblk { tcp_seq start; /* start seq no. of sack block */ tcp_seq end; /* end seq no. */ @@ -49,14 +53,20 @@ struct sackhole { }; /* - * Kernel variables for tcp. + * TCP sequence queue structures. */ +TAILQ_HEAD(tcpqehead, tcpqent); +struct tcpqent { + TAILQ_ENTRY(tcpqent) tcpqe_q; + struct tcphdr *tcpqe_tcp; + struct mbuf *tcpqe_m; /* mbuf contains packet */ +}; /* * Tcp control block, one per tcp; fields: */ struct tcpcb { - struct ipqehead segq; /* sequencing queue */ + struct tcpqehead t_segq; /* sequencing queue */ struct timeout t_timer[TCPT_NTIMERS]; /* tcp timers */ short t_state; /* state of this connection */ short t_rxtshift; /* log(2) of rexmt exp. backoff */ |