]> git.unchartedbackwaters.co.uk Git - francis/winuae.git/commitdiff
SLIRP 64-bit patch (from qemu).
authorToni Wilen <twilen@winuae.net>
Mon, 22 Sep 2014 17:19:32 +0000 (20:19 +0300)
committerToni Wilen <twilen@winuae.net>
Mon, 22 Sep 2014 17:19:32 +0000 (20:19 +0300)
slirp/ip.h
slirp/ip_input.cpp
slirp/misc.cpp
slirp/slirp.cpp
slirp/slirp.h
slirp/tcp_input.cpp
slirp/tcp_subr.cpp
slirp/tcp_var.h
slirp/tcpip.h
slirp/udp.cpp
slirp/udp.h

index 0bc111fc22acc1e8db36dc2728a972b0abc8e908..5af91b5010cad5d49976c5839cc523c98f314061 100644 (file)
@@ -183,30 +183,26 @@ struct    ip_timestamp {
 
 #define        IP_MSS          576             /* default maximum segment size */
 
-#ifdef HAVE_SYS_TYPES32_H  /* Overcome some Solaris 2.x junk */
-#include <sys/types32.h>
-#else
 #if SIZEOF_CHAR_P == 4
-typedef caddr_t caddr32_t;
-#else
-typedef u_int32_t caddr32_t;
-#endif
-#endif
-
-#if SIZEOF_CHAR_P == 4
-typedef struct ipq *ipqp_32;
-typedef struct ipasfrag *ipasfragp_32;
+struct mbuf_ptr {
+       struct mbuf *mptr;
+       uint32_t dummy;
+};
 #else
-typedef caddr32_t ipqp_32;
-typedef caddr32_t ipasfragp_32;
+struct mbuf_ptr {
+       struct mbuf *mptr;
+};
 #endif
-
+struct qlink {
+       void *next, *prev;
+};
 /*
  * Overlay for ip header used by other protocols (tcp, udp).
  */
 #include "packed.h"
 struct ipovly {
-       caddr32_t       ih_next, ih_prev;       /* for protocol sequence q's */
+       struct mbuf_ptr ih_mbuf;        /* backpointer to mbuf */
        u_int8_t        ih_x1;                  /* (unused) */
        u_int8_t        ih_pr;                  /* protocol */
        u_int16_t       ih_len;                 /* protocol length */
@@ -223,44 +219,30 @@ struct ipovly {
  * size 28 bytes
  */
 struct ipq {
-       ipqp_32 next,prev;      /* to other reass headers */
+       struct qlink frag_link;         /* to ip headers of fragments */
+       struct qlink ip_link;           /* to other reass headers */
        u_int8_t        ipq_ttl;                /* time for reass q to live */
        u_int8_t        ipq_p;                  /* protocol of this fragment */
        u_int16_t       ipq_id;                 /* sequence id for reassembly */
-       ipasfragp_32 ipq_next,ipq_prev;
-                                       /* to ip headers of fragments */
        struct  in_addr ipq_src,ipq_dst;
 };
 
 /*
  * Ip header, when holding a fragment.
  *
- * Note: ipf_next must be at same offset as ipq_next above
+ * Note: ipf_link must be at same offset as frag_link above
  */
 struct ipasfrag {
-#ifdef WORDS_BIGENDIAN
-       u_char  ip_v:4,
-               ip_hl:4;
-#else
-       u_char  ip_hl:4,
-               ip_v:4;
-#endif
-                                        /* BUG : u_int changed to u_int8_t.
-                                         * sizeof(u_int)==4 on linux 2.0
-                                        */
-        u_int8_t ipf_mff;              /* XXX overlays ip_tos: use low bit
-                                        * to avoid destroying tos (PPPDTRuu);
-                                        * copied from (ip_off&IP_MF) */
-       u_int16_t       ip_len;
-       u_int16_t       ip_id;
-       u_int16_t       ip_off;
-       u_int8_t        ip_ttl;
-       u_int8_t        ip_p;
-       u_int16_t       ip_sum;
-       ipasfragp_32 ipf_next;          /* next fragment */
-       ipasfragp_32 ipf_prev;          /* previous fragment */
+       struct qlink ipf_link;
+       struct ip ipf_ip;
 };
 
+#define ipf_off                ipf_ip.ip_off
+#define ipf_tos                ipf_ip.ip_tos
+#define ipf_len                ipf_ip.ip_len
+#define ipf_next       ipf_link.next
+#define ipf_prev       ipf_link.prev 
+
 /*
  * Structure stored in mbuf in inpcb.ip_options
  * and passed to ip_output when ip options are in use.
index 9105166c566c2343fe7e723af429e68bb119e1d1..c594556aa2d0507adf6f18b8c364c952607b8584 100644 (file)
@@ -51,7 +51,7 @@ struct ipq ipq;
  */
 void ip_init(void)
 {
-       ipq.next = ipq.prev = (ipqp_32)&ipq;
+       ipq.ip_link.next = ipq.ip_link.prev = &ipq.ip_link;
        ip_id = tt.tv_sec & 0xffff;
        udp_init();
        tcp_init();
@@ -159,19 +159,21 @@ void ip_input(struct mbuf *m)
         * XXX This should fail, don't fragment yet
         */
        if (ip->ip_off &~ IP_DF) {
-         register struct ipq *fp;
+         struct ipq *fp;
+         struct qlink *l;
                /*
                 * Look for queue of fragments
                 * of this datagram.
                 */
-               for (fp = (struct ipq *) ipq.next; fp != &ipq;
-                    fp = (struct ipq *) fp->next)
-                 if (ip->ip_id == fp->ipq_id &&
-                     ip->ip_src.s_addr == fp->ipq_src.s_addr &&
-                     ip->ip_dst.s_addr == fp->ipq_dst.s_addr &&
-                     ip->ip_p == fp->ipq_p)
+        for (l = (struct qlink*)(ipq.ip_link.next); l != &ipq.ip_link; l = (struct qlink*)(l->next)) {
+            fp = container_of(l, struct ipq, ip_link);
+            if (ip->ip_id == fp->ipq_id &&
+                    ip->ip_src.s_addr == fp->ipq_src.s_addr &&
+                    ip->ip_dst.s_addr == fp->ipq_dst.s_addr &&
+                    ip->ip_p == fp->ipq_p)
                    goto found;
-               fp = 0;
+               }
+               fp = NULL;
        found:
 
                /*
@@ -181,9 +183,9 @@ void ip_input(struct mbuf *m)
                 */
                ip->ip_len -= hlen;
                if (ip->ip_off & IP_MF)
-                 ((struct ipasfrag *)ip)->ipf_mff |= 1;
+                  ip->ip_tos |= 1;
                else 
-                 ((struct ipasfrag *)ip)->ipf_mff &= ~1;
+                  ip->ip_tos &= ~1;
 
                ip->ip_off <<= 3;
 
@@ -192,9 +194,9 @@ void ip_input(struct mbuf *m)
                 * or if this is not the first fragment,
                 * attempt reassembly; if it succeeds, proceed.
                 */
-               if (((struct ipasfrag *)ip)->ipf_mff & 1 || ip->ip_off) {
+               if ((ip->ip_tos & 1) || ip->ip_off) {
                        ipstat.ips_fragments++;
-                       ip = ip_reass((struct ipasfrag *)ip, fp);
+                       ip = ip_reass(ip, fp);
                        if (ip == 0)
                                return;
                        ipstat.ips_reassembled++;
@@ -230,13 +232,16 @@ bad:
        return;
 }
 
+#define iptofrag(P) ((struct ipasfrag *)(((char*)(P)) - sizeof(struct qlink)))
+#define fragtoip(P) ((struct ip*)(((char*)(P)) + sizeof(struct qlink)))
+
 /*
  * Take incoming datagram fragment and try to
  * reassemble it into whole datagram.  If a chain for
  * reassembly of this datagram already exists, then it
  * is given as fp; otherwise have to make a chain.
  */
-struct ip *ip_reass(struct ipasfrag *ip, struct ipq *fp)
+struct ip *ip_reass(struct ip *ip, struct ipq *fp)
 {
        struct mbuf *m = dtom(ip);
        struct ipasfrag *q;
@@ -263,13 +268,13 @@ struct ip *ip_reass(struct ipasfrag *ip, struct ipq *fp)
          struct mbuf *t;
          if ((t = m_get()) == NULL) goto dropfrag;
          fp = mtod(t, struct ipq *);
-         insque_32(fp, &ipq);
+         insque(&fp->ip_link, &ipq.ip_link);
          fp->ipq_ttl = IPFRAGTTL;
          fp->ipq_p = ip->ip_p;
          fp->ipq_id = ip->ip_id;
-         fp->ipq_next = fp->ipq_prev = (ipasfragp_32)fp;
-         fp->ipq_src = ((struct ip *)ip)->ip_src;
-         fp->ipq_dst = ((struct ip *)ip)->ip_dst;
+         fp->frag_link.next = fp->frag_link.prev = &fp->frag_link;
+         fp->ipq_src = ip->ip_src;
+         fp->ipq_dst = ip->ip_dst;
          q = (struct ipasfrag *)fp;
          goto insert;
        }
@@ -277,19 +282,19 @@ struct ip *ip_reass(struct ipasfrag *ip, struct ipq *fp)
        /*
         * Find a segment which begins after this one does.
         */
-       for (q = (struct ipasfrag *)fp->ipq_next; q != (struct ipasfrag *)fp;
-           q = (struct ipasfrag *)q->ipf_next)
-               if (q->ip_off > ip->ip_off)
+       for (q = (struct ipasfrag*)fp->frag_link.next; q != (struct ipasfrag *)&fp->frag_link; q = (struct ipasfrag*)(q->ipf_next)) {
+               if (q->ipf_off > ip->ip_off)
                        break;
+       }
 
        /*
         * If there is a preceding segment, it may provide some of
         * our data already.  If so, drop the data from the incoming
         * segment.  If it provides all of our data, drop us.
         */
-       if (q->ipf_prev != (ipasfragp_32)fp) {
-               i = ((struct ipasfrag *)(q->ipf_prev))->ip_off +
-                 ((struct ipasfrag *)(q->ipf_prev))->ip_len - ip->ip_off;
+       if (q->ipf_prev != &fp->frag_link) {
+               struct ipasfrag *pq = (struct ipasfrag*)(q->ipf_prev);
+               i = pq->ipf_off + pq->ipf_len - ip->ip_off;
                if (i > 0) {
                        if (i >= ip->ip_len)
                                goto dropfrag;
@@ -303,17 +308,18 @@ struct ip *ip_reass(struct ipasfrag *ip, struct ipq *fp)
         * While we overlap succeeding segments trim them or,
         * if they are completely covered, dequeue them.
         */
-       while (q != (struct ipasfrag *)fp && ip->ip_off + ip->ip_len > q->ip_off) {
-               i = (ip->ip_off + ip->ip_len) - q->ip_off;
-               if (i < q->ip_len) {
-                       q->ip_len -= i;
-                       q->ip_off += i;
+       while (q != (struct ipasfrag*)&fp->frag_link &&
+               ip->ip_off + ip->ip_len > q->ipf_off) {
+               i = (ip->ip_off + ip->ip_len) - q->ipf_off;
+               if (i < q->ipf_len) {
+                       q->ipf_len -= i;
+                       q->ipf_off += i;
                        m_adj(dtom(q), i);
                        break;
                }
-               q = (struct ipasfrag *) q->ipf_next;
-               m_freem(dtom((struct ipasfrag *) q->ipf_prev));
-               ip_deq((struct ipasfrag *) q->ipf_prev);
+               q = (struct ipasfrag*)(q->ipf_next);
+               m_freem(dtom(q->ipf_prev));
+               ip_deq((struct ipasfrag*)(q->ipf_prev));
        }
 
 insert:
@@ -321,29 +327,27 @@ insert:
         * Stick new segment in its place;
         * check for complete reassembly.
         */
-       ip_enq(ip, (struct ipasfrag *) q->ipf_prev);
+       ip_enq(iptofrag(ip), (struct ipasfrag*)(q->ipf_prev));
        next = 0;
-       for (q = (struct ipasfrag *) fp->ipq_next; q != (struct ipasfrag *)fp;
-            q = (struct ipasfrag *) q->ipf_next) {
-               if (q->ip_off != next)
-                       return (0);
-               next += q->ip_len;
+       for (q = (struct ipasfrag*)(fp->frag_link.next); q != (struct ipasfrag*)&fp->frag_link; q = (struct ipasfrag*)(q->ipf_next)) {
+               if (q->ipf_off != next)
+                       return 0;
+               next += q->ipf_len;
        }
-       if (((struct ipasfrag *)(q->ipf_prev))->ipf_mff & 1)
+       if (((struct ipasfrag *)(q->ipf_prev))->ipf_tos & 1)
                return (0);
 
        /*
         * Reassembly is complete; concatenate fragments.
         */
-       q = (struct ipasfrag *) fp->ipq_next;
+       q = (struct ipasfrag*)(fp->frag_link.next);
        m = dtom(q);
 
        q = (struct ipasfrag *) q->ipf_next;
-       while (q != (struct ipasfrag *)fp) {
-         struct mbuf *t;
-         t = dtom(q);
-         q = (struct ipasfrag *) q->ipf_next;
-         m_cat(m, t);
+       while (q != (struct ipasfrag*)&fp->frag_link) {
+               struct mbuf *t = dtom(q);
+               q = (struct ipasfrag *) q->ipf_next;
+               m_cat(m, t);
        }
 
        /*
@@ -352,7 +356,7 @@ insert:
         * dequeue and discard fragment reassembly header.
         * Make header visible.
         */
-       ip = (struct ipasfrag *) fp->ipq_next;
+       q = (struct ipasfrag*)(fp->frag_link.next);
 
        /*
         * If the fragments concatenated to an mbuf that's
@@ -364,23 +368,23 @@ insert:
        if (m->m_flags & M_EXT) {
          int delta;
          delta = (char *)ip - m->m_dat;
-         ip = (struct ipasfrag *)(m->m_ext + delta);
+         q = (struct ipasfrag *)(m->m_ext + delta);
        }
 
        /* DEBUG_ARG("ip = %lx", (long)ip); 
         * ip=(struct ipasfrag *)m->m_data; */
 
+       ip = fragtoip(q);
        ip->ip_len = next;
-       ip->ipf_mff &= ~1;
-       ((struct ip *)ip)->ip_src = fp->ipq_src;
-       ((struct ip *)ip)->ip_dst = fp->ipq_dst;
-       remque_32(fp);
+       ip->ip_tos &= ~1;
+       ip->ip_src = fp->ipq_src;
+       ip->ip_dst = fp->ipq_dst;
+       remque(&fp->ip_link);
        (void) m_free(dtom(fp));
-       m = dtom(ip);
        m->m_len += (ip->ip_hl << 2);
        m->m_data -= (ip->ip_hl << 2);
 
-       return ((struct ip *)ip);
+       return ip;
 
 dropfrag:
        ipstat.ips_fragdropped++;
@@ -396,13 +400,12 @@ void ip_freef(struct ipq *fp)
 {
        struct ipasfrag *q, *p;
 
-       for (q = (struct ipasfrag *) fp->ipq_next; q != (struct ipasfrag *)fp;
-           q = p) {
-               p = (struct ipasfrag *) q->ipf_next;
+       for (q = (struct ipasfrag*)(fp->frag_link.next); q != (struct ipasfrag*)&fp->frag_link; q = p) {
+               p = (struct ipasfrag*)(q->ipf_next);
                ip_deq(q);
                m_freem(dtom(q));
        }
-       remque_32(fp);
+       remque(&fp->ip_link);
        (void) m_free(dtom(fp));
 }
 
@@ -414,10 +417,10 @@ void ip_enq(struct ipasfrag *p, struct ipasfrag *prev)
 {
        DEBUG_CALL("ip_enq");
        DEBUG_ARG("prev = %lx", (long)prev);
-       p->ipf_prev = (ipasfragp_32) prev;
+       p->ipf_prev =  prev;
        p->ipf_next = prev->ipf_next;
-       ((struct ipasfrag *)(prev->ipf_next))->ipf_prev = (ipasfragp_32) p;
-       prev->ipf_next = (ipasfragp_32) p;
+       ((struct ipasfrag *)(prev->ipf_next))->ipf_prev = p;
+       prev->ipf_next = p;
 }
 
 /*
@@ -436,20 +439,21 @@ void ip_deq(struct ipasfrag *p)
  */
 void ip_slowtimo(void)
 {
-       struct ipq *fp;
+       struct qlink *l;
        
        DEBUG_CALL("ip_slowtimo");
        
-       fp = (struct ipq *) ipq.next;
-       if (fp == 0)
-          return;
-
-       while (fp != &ipq) {
-               --fp->ipq_ttl;
-               fp = (struct ipq *) fp->next;
-               if (((struct ipq *)(fp->prev))->ipq_ttl == 0) {
+       l = (struct qlink*)(ipq.ip_link.next);
+
+       if (l == 0)
+               return;
+
+       while (l != &ipq.ip_link) {
+               struct ipq *fp = container_of(l, struct ipq, ip_link);
+               l = (struct qlink*)(l->next);
+               if (--fp->ipq_ttl == 0) {
                        ipstat.ips_fragtimeout++;
-                       ip_freef((struct ipq *) fp->prev);
+                       ip_freef(fp);
                }
        }
 }
index 574e2ba02e1df7f714f5411c76a9131cbb851b29..249aba417b078e767b42da77ee50eb259c80e08e 100644 (file)
@@ -97,35 +97,6 @@ getouraddr(void)
             our_addr.s_addr = loopback_addr.s_addr;
 }
 
-#if SIZEOF_CHAR_P == 8
-
-struct quehead_32 {
-       u_int32_t qh_link;
-       u_int32_t qh_rlink;
-};
-
-inline void
-insque_32(void *a, void *b)
-{
-       register struct quehead_32 *element = (struct quehead_32 *) a;
-       register struct quehead_32 *head = (struct quehead_32 *) b;
-       element->qh_link = head->qh_link;
-       head->qh_link = (u_int32_t)element;
-       element->qh_rlink = (u_int32_t)head;
-       ((struct quehead_32 *)(element->qh_link))->qh_rlink
-       = (u_int32_t)element;
-}
-
-inline void
-remque_32(void *a)
-{
-       register struct quehead_32 *element = (struct quehead_32 *) a;
-       ((struct quehead_32 *)(element->qh_link))->qh_rlink = element->qh_rlink;
-       ((struct quehead_32 *)(element->qh_rlink))->qh_link = element->qh_link;
-       element->qh_rlink = 0;
-}
-
-#endif /* SIZEOF_CHAR_P == 8 */
 
 struct quehead {
        struct quehead *qh_link;
index 09481c636a2ee96bea62b1286fe2122cf56cc257..3416cd8865fb74ba9ae7445a1df1a9897d6b55af 100644 (file)
@@ -213,8 +213,7 @@ int slirp_select_fill(SOCKET *pnfds,
                 * *_slowtimo needs calling if there are IP fragments
                 * in the fragment queue, or there are TCP connections active
                 */
-               do_slowtimo = ((tcb.so_next != &tcb) ||
-                              ((struct ipasfrag *)&ipq != (struct ipasfrag *)ipq.next));
+               do_slowtimo = ((tcb.so_next != &tcb) || (&ipq.ip_link != ipq.ip_link.next));
                
                for (so = tcb.so_next; so != &tcb; so = so_next) {
                        so_next = so->so_next;
index 7736339093d6dac9bca637e7d553cf674cb7c698..4d0d67016e925ed2bb3f31a3e1bbd15827588eb0 100644 (file)
 #ifdef _WIN32
 # include <inttypes.h>
 
+#ifdef _MSC_VER
+#define container_of(address, type, field) ((type *)( \
+        (PCHAR)(address) - \
+        (ULONG_PTR)(&((type *)0)->field)))
+#endif
+
 typedef char *caddr_t;
 typedef int socklen_t;
 typedef unsigned long ioctlsockopt_t;
@@ -295,16 +301,6 @@ void if_start _P((struct ttys *));
 
 void lprint _P((const char *, ...));
 
-extern int do_echo;
-
-#if SIZEOF_CHAR_P == 4
-# define insque_32 insque
-# define remque_32 remque
-#else
- extern inline void insque_32 _P((void *, void *));
- extern inline void remque_32 _P((void *));
-#endif
-
 #ifndef _WIN32
 #include <netdb.h>
 #endif
@@ -322,7 +318,7 @@ void if_output _P((struct socket *, struct mbuf *));
 void ip_init _P((void));
 void ip_cleanup _P((void));
 void ip_input _P((struct mbuf *));
-struct ip * ip_reass _P((register struct ipasfrag *, register struct ipq *));
+struct ip * ip_reass _P((struct ip *, struct ipq *));
 void ip_freef _P((struct ipq *));
 void ip_enq _P((register struct ipasfrag *, register struct ipasfrag *));
 void ip_deq _P((register struct ipasfrag *));
index a7a405f7526ba9a96ab0e48073b388f012f2ddce..4a0e1179812cda11ad5d4299954d177807bf0cc4 100644 (file)
@@ -68,7 +68,7 @@ tcp_seq tcp_iss;                /* tcp initial send seq # */
 #ifdef TCP_ACK_HACK
 #define TCP_REASS(tp, ti, m, so, flags) {\
        if ((ti)->ti_seq == (tp)->rcv_nxt && \
-           (tp)->seg_next == (tcpiphdrp_32)(tp) && \
+           tcpfrag_list_empty(tp) && \
            (tp)->t_state == TCPS_ESTABLISHED) {\
                if (ti->ti_flags & TH_PUSH) \
                        tp->t_flags |= TF_ACKNOW; \
@@ -91,7 +91,7 @@ tcp_seq tcp_iss;                /* tcp initial send seq # */
 #else
 #define        TCP_REASS(tp, ti, m, so, flags) { \
        if ((ti)->ti_seq == (tp)->rcv_nxt && \
-           (tp)->seg_next == (tcpiphdrp_32)(tp) && \
+           tcpfrag_list_empty(tp) && \
            (tp)->t_state == TCPS_ESTABLISHED) { \
                tp->t_flags |= TF_DELACK; \
                (tp)->rcv_nxt += (ti)->ti_len; \
@@ -127,8 +127,8 @@ tcp_reass(struct tcpcb *tp, struct tcpiphdr *ti, struct mbuf *m)
        /*
         * Find a segment which begins after this one does.
         */
-       for (q = (struct tcpiphdr *)tp->seg_next; q != (struct tcpiphdr *)tp;
-           q = (struct tcpiphdr *)q->ti_next)
+       for (q = tcpfrag_list_first(tp); !tcpfrag_list_end(q, tp);
+               q = tcpiphdr_next(q))
                if (SEQ_GT(q->ti_seq, ti->ti_seq))
                        break;
 
@@ -137,9 +137,9 @@ tcp_reass(struct tcpcb *tp, struct tcpiphdr *ti, struct mbuf *m)
         * our data already.  If so, drop the data from the incoming
         * segment.  If it provides all of our data, drop us.
         */
-       if ((struct tcpiphdr *)q->ti_prev != (struct tcpiphdr *)tp) {
-               register int i;
-               q = (struct tcpiphdr *)q->ti_prev;
+       if (!tcpfrag_list_end(tcpiphdr_prev(q), tp)) {
+               int i;
+               q = tcpiphdr_prev(q);
                /* conversion to int (in i) handles seq wraparound */
                i = q->ti_seq + q->ti_len - ti->ti_seq;
                if (i > 0) {
@@ -159,36 +159,36 @@ tcp_reass(struct tcpcb *tp, struct tcpiphdr *ti, struct mbuf *m)
                        ti->ti_len -= i;
                        ti->ti_seq += i;
                }
-               q = (struct tcpiphdr *)(q->ti_next);
+               q = tcpiphdr_next(q);
        }
        tcpstat.tcps_rcvoopack++;
        tcpstat.tcps_rcvoobyte += ti->ti_len;
-       REASS_MBUF(ti) = (mbufp_32) m;          /* XXX */
+       ti->ti_mbuf = m;
 
        /*
         * While we overlap succeeding segments trim them or,
         * if they are completely covered, dequeue them.
         */
-       while (q != (struct tcpiphdr *)tp) {
+       while (!tcpfrag_list_end(q, tp)) {
                register int i = (ti->ti_seq + ti->ti_len) - q->ti_seq;
                if (i <= 0)
                        break;
                if (i < q->ti_len) {
                        q->ti_seq += i;
                        q->ti_len -= i;
-                       m_adj((struct mbuf *) REASS_MBUF(q), i);
+                       m_adj(q->ti_mbuf, i);
                        break;
                }
-               q = (struct tcpiphdr *)q->ti_next;
-               m = (struct mbuf *) REASS_MBUF((struct tcpiphdr *)q->ti_prev);
-               remque_32((void *)(q->ti_prev));
+               q = tcpiphdr_next(q);
+               m = tcpiphdr_prev(q)->ti_mbuf;
+               remque(tcpiphdr2qlink(tcpiphdr_prev(q)));
                m_freem(m);
        }
 
        /*
         * Stick new segment in its place.
         */
-       insque_32(ti, (void *)(q->ti_prev));
+       insque(tcpiphdr2qlink(ti), tcpiphdr2qlink(tcpiphdr_prev(q)));
 
 present:
        /*
@@ -197,17 +197,17 @@ present:
         */
        if (!TCPS_HAVEESTABLISHED(tp->t_state))
                return (0);
-       ti = (struct tcpiphdr *) tp->seg_next;
-       if (ti == (struct tcpiphdr *)tp || ti->ti_seq != tp->rcv_nxt)
+       ti = tcpfrag_list_first(tp);
+       if (tcpfrag_list_end(ti, tp) || ti->ti_seq != tp->rcv_nxt)
                return (0);
        if (tp->t_state == TCPS_SYN_RECEIVED && ti->ti_len)
                return (0);
        do {
                tp->rcv_nxt += ti->ti_len;
                flags = ti->ti_flags & TH_FIN;
-               remque_32(ti);
-               m = (struct mbuf *) REASS_MBUF(ti); /* XXX */
-               ti = (struct tcpiphdr *)ti->ti_next;
+               remque(tcpiphdr2qlink(ti));
+               m = ti->ti_mbuf;
+               ti = tcpiphdr_next(ti);
 /*             if (so->so_state & SS_FCANTRCVMORE) */
                if (so->so_state & SS_FCANTSENDMORE)
                        m_freem(m);
@@ -290,7 +290,8 @@ void tcp_input(struct mbuf *m, int iphlen, struct socket *inso)
         * Checksum extended TCP header and data.
         */
        tlen = ((struct ip *)ti)->ip_len;
-       ti->ti_next = ti->ti_prev = 0;
+       tcpiphdr2qlink(ti)->next = tcpiphdr2qlink(ti)->prev = 0;
+       memset(&ti->ti_i.ih_mbuf, 0 , sizeof(struct mbuf_ptr));
        ti->ti_x1 = 0;
        ti->ti_len = htons((u_int16_t)tlen);
        len = sizeof(struct ip ) + tlen;
@@ -539,8 +540,8 @@ findso:
                                return;
                        }
                } else if (ti->ti_ack == tp->snd_una &&
-                   tp->seg_next == (tcpiphdrp_32)tp &&
-                   ti->ti_len <= sbspace(&so->so_rcv)) {
+                       tcpfrag_list_empty(tp) &&
+                       ti->ti_len <= sbspace(&so->so_rcv)) {
                        /*
                         * this is a pure, in-sequence data packet
                         * with nothing on the reassembly queue and
index 238925171e54c878d61dfde0afb0977e5e6860cc..554601fcf753de0563a8b530d5ac76fa8ed5c284 100644 (file)
@@ -86,7 +86,7 @@ void tcp_template(struct tcpcb *tp)
        struct socket *so = tp->t_socket;
        struct tcpiphdr *n = &tp->t_template;
 
-       n->ti_next = n->ti_prev = 0;
+       n->ti_mbuf = NULL;
        n->ti_x1 = 0;
        n->ti_pr = IPPROTO_TCP;
        n->ti_len = htons(sizeof (struct tcpiphdr) - sizeof (struct ip));
@@ -163,7 +163,7 @@ void tcp_respond(struct tcpcb *tp, struct tcpiphdr *ti, struct mbuf *m, tcp_seq
        tlen += sizeof (struct tcpiphdr);
        m->m_len = tlen;
 
-       ti->ti_next = ti->ti_prev = 0;
+       ti->ti_mbuf = 0;
        ti->ti_x1 = 0;
        ti->ti_seq = htonl(seq);
        ti->ti_ack = htonl(ack);
@@ -201,7 +201,7 @@ struct tcpcb *tcp_newtcpcb(struct socket *so)
                return ((struct tcpcb *)0);
        
        memset((char *) tp, 0, sizeof(struct tcpcb));
-       tp->seg_next = tp->seg_prev = (tcpiphdrp_32)tp;
+       tp->seg_next = tp->seg_prev = (struct tcpiphdr*)tp;
        tp->t_maxseg = tcp_mssdflt;
        
        tp->t_flags = tcp_do_rfc1323 ? (TF_REQ_SCALE|TF_REQ_TSTMP) : 0;
@@ -275,11 +275,11 @@ struct tcpcb *tcp_close(struct tcpcb *tp)
        DEBUG_ARG("tp = %lx", (long )tp);
        
        /* free the reassembly queue, if any */
-       t = (struct tcpiphdr *) tp->seg_next;
-       while (t != (struct tcpiphdr *)tp) {
-               t = (struct tcpiphdr *)t->ti_next;
-               m = (struct mbuf *) REASS_MBUF((struct tcpiphdr *)t->ti_prev);
-               remque_32((struct tcpiphdr *) t->ti_prev);
+       t = tcpfrag_list_first(tp);
+       while (!tcpfrag_list_end(t, tp)) {
+               t = tcpiphdr_next(t);
+               m = tcpiphdr_prev(t)->ti_mbuf;
+               remque(tcpiphdr2qlink(tcpiphdr_prev(t)));
                m_freem(m);
        }
        /* It's static */
index c8e99ae0307276abad7737552cc552998a05a2c0..064ac69a1fb46532f10764f2ddddab4152a5fd91 100644 (file)
 #include "tcpip.h"
 #include "tcp_timer.h"
 
-#if SIZEOF_CHAR_P == 4
- typedef struct tcpiphdr *tcpiphdrp_32;
-#else
- typedef u_int32_t tcpiphdrp_32;
-#endif
-
 /*
  * Tcp control block, one per tcp; fields:
  */
 struct tcpcb {
-       tcpiphdrp_32 seg_next;  /* sequencing queue */
-       tcpiphdrp_32 seg_prev;
+       struct tcpiphdr *seg_next;      /* sequencing queue */
+       struct tcpiphdr *seg_prev;
        short   t_state;                /* state of this connection */
        short   t_timer[TCPT_NTIMERS];  /* tcp timers */
        short   t_rxtshift;             /* log(2) of rexmt exp. backoff */
@@ -166,21 +160,6 @@ struct tcpcb {
 #define        TCP_REXMTVAL(tp) \
        (((tp)->t_srtt >> TCP_RTT_SHIFT) + (tp)->t_rttvar)
 
-/* XXX
- * 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.
- */
-#if SIZEOF_CHAR_P == 4
-typedef struct mbuf *mbufp_32;
-#else
-typedef u_int32_t mbufp_32;
-#endif
-#define REASS_MBUF(ti) (*(mbufp_32 *)&((ti)->ti_t))
-
 /*
  * TCP statistics.
  * Many of these should be kept per connection,
index dff5a3c961ed287a1b8904b79c6636b6458781af..7974ce3d52efb7ad78409ab9e46752c05ebbe7ae 100644 (file)
@@ -40,8 +40,7 @@ struct tcpiphdr {
        struct  ipovly ti_i;            /* overlaid ip structure */
        struct  tcphdr ti_t;            /* tcp header */
 };
-#define        ti_next         ti_i.ih_next
-#define        ti_prev         ti_i.ih_prev
+#define        ti_mbuf         ti_i.ih_mbuf.mptr
 #define        ti_x1           ti_i.ih_x1
 #define        ti_pr           ti_i.ih_pr
 #define        ti_len          ti_i.ih_len
@@ -58,6 +57,14 @@ struct tcpiphdr {
 #define        ti_sum          ti_t.th_sum
 #define        ti_urp          ti_t.th_urp
 
+#define tcpiphdr2qlink(T) ((struct qlink*)(((char*)(T)) - sizeof(struct qlink)))
+#define qlink2tcpiphdr(Q) ((struct tcpiphdr*)(((char*)(Q)) + sizeof(struct qlink)))
+#define tcpiphdr_next(T) qlink2tcpiphdr(tcpiphdr2qlink(T)->next)
+#define tcpiphdr_prev(T) qlink2tcpiphdr(tcpiphdr2qlink(T)->prev)
+#define tcpfrag_list_first(T) qlink2tcpiphdr((T)->seg_next)
+#define tcpfrag_list_end(F, T) (tcpiphdr2qlink(F) == (struct qlink*)(T))
+#define tcpfrag_list_empty(T) ((T)->seg_next == (struct tcpiphdr*)(T))
+
 /*
  * Just a clean way to get to the first byte
  * of the packet
index bb2949a23ebc0468b9d17ffc9ba1ce089f7e7465..d04d6106a0adec2f0dbfdba7f81829b6d005e45b 100644 (file)
@@ -132,8 +132,7 @@ void udp_input(struct mbuf *m, int iphlen)
         * Checksum extended UDP header and data.
         */
        if (udpcksum && uh->uh_sum) {
-         ((struct ipovly *)ip)->ih_next = 0;
-         ((struct ipovly *)ip)->ih_prev = 0;
+         memset(&((struct ipovly *)ip)->ih_mbuf, 0, sizeof(struct mbuf_ptr));
          ((struct ipovly *)ip)->ih_x1 = 0;
          ((struct ipovly *)ip)->ih_len = uh->uh_ulen;
          /* keep uh_sum for ICMP reply
@@ -276,7 +275,7 @@ int udp_output2(struct socket *so, struct mbuf *m,
         * and addresses and length put into network format.
         */
        ui = mtod(m, struct udpiphdr *);
-       ui->ui_next = ui->ui_prev = 0;
+       memset(&ui->ui_i.ih_mbuf, 0 , sizeof(struct mbuf_ptr));
        ui->ui_x1 = 0;
        ui->ui_pr = IPPROTO_UDP;
        ui->ui_len = htons(m->m_len - sizeof(struct ip)); /* + sizeof (struct udphdr)); */
index 73120086b5a99ba28571663cad6fc2cd41c074ac..6bdf8fd5bfade4e3454864d5e5e5ef72066e87b6 100644 (file)
@@ -58,8 +58,7 @@ struct udpiphdr {
                struct  ipovly ui_i;            /* overlaid ip structure */
                struct  udphdr ui_u;            /* udp header */
 };
-#define ui_next         ui_i.ih_next
-#define ui_prev         ui_i.ih_prev
+#define ui_mbuf         ui_i.ih_mbuf.mptr
 #define ui_x1           ui_i.ih_x1
 #define ui_pr           ui_i.ih_pr
 #define ui_len          ui_i.ih_len