summaryrefslogtreecommitdiffstats
path: root/include/net
diff options
context:
space:
mode:
authorRalf Baechle <ralf@linux-mips.org>1997-06-01 03:16:17 +0000
committerRalf Baechle <ralf@linux-mips.org>1997-06-01 03:16:17 +0000
commitd8d9b8f76f22b7a16a83e261e64f89ee611f49df (patch)
tree3067bc130b80d52808e6390c9fc7fc087ec1e33c /include/net
parent19c9bba94152148523ba0f7ef7cffe3d45656b11 (diff)
Initial revision
Diffstat (limited to 'include/net')
-rw-r--r--include/net/ip.h30
-rw-r--r--include/net/sock.h1
-rw-r--r--include/net/tcp.h68
3 files changed, 65 insertions, 34 deletions
diff --git a/include/net/ip.h b/include/net/ip.h
index c0e600a37..e5d59dd33 100644
--- a/include/net/ip.h
+++ b/include/net/ip.h
@@ -65,36 +65,6 @@ extern void ip_mc_dropsocket(struct sock *);
extern void ip_mc_dropdevice(struct device *dev);
extern int ip_mc_procinfo(char *, char **, off_t, int, int);
-/* Describe an IP fragment. */
-struct ipfrag
-{
- int offset; /* offset of fragment in IP datagram */
- int end; /* last byte of data in datagram */
- int len; /* length of this fragment */
- struct sk_buff *skb; /* complete received fragment */
- unsigned char *ptr; /* pointer into real fragment data */
- struct ipfrag *next; /* linked list pointers */
- struct ipfrag *prev;
-};
-
-/*
- * Describe an entry in the "incomplete datagrams" queue.
- */
-
-struct ipq
-{
- unsigned char *mac; /* pointer to MAC header */
- struct iphdr *iph; /* pointer to IP header */
- int len; /* total length of original datagram */
- short ihlen; /* length of the IP header */
- short maclen; /* length of the MAC header */
- struct timer_list timer; /* when will this queue expire? */
- struct ipfrag *fragments; /* linked list of received fragments */
- struct ipq *next; /* linked list pointers */
- struct ipq *prev;
- struct device *dev; /* Device - for icmp replies */
-};
-
/*
* Functions provided by ip.c
*/
diff --git a/include/net/sock.h b/include/net/sock.h
index 61936854f..354d8dae5 100644
--- a/include/net/sock.h
+++ b/include/net/sock.h
@@ -216,6 +216,7 @@ struct tcp_opt
* Options received (usually on last packet, some only on SYN packets).
*/
char tstamp_ok, /* TIMESTAMP seen on SYN packet */
+ wscale_ok, /* Wscale seen on SYN packet */
sack_ok; /* SACK_PERM seen on SYN packet */
char saw_tstamp; /* Saw TIMESTAMP on last packet */
__u16 in_mss; /* MSS option received from sender */
diff --git a/include/net/tcp.h b/include/net/tcp.h
index 3822b461f..cedc7f3b1 100644
--- a/include/net/tcp.h
+++ b/include/net/tcp.h
@@ -43,6 +43,17 @@ extern struct sock *tcp_established_hash[TCP_HTABLE_SIZE];
extern struct sock *tcp_listening_hash[TCP_LHTABLE_SIZE];
extern struct sock *tcp_bound_hash[TCP_BHTABLE_SIZE];
+/* tcp_ipv4.c: These sysctl variables need to be shared between v4 and v6
+ * because the v6 tcp code to intialize a connection needs to interoperate
+ * with the v4 code using the same variables.
+ * FIXME: It would be better to rewrite the connection code to be
+ * address family independent and just leave one copy in the ipv4 section.
+ * This would also clean up some code duplication. -- erics
+ */
+extern int sysctl_tcp_sack;
+extern int sysctl_tcp_timestamps;
+extern int sysctl_tcp_window_scaling;
+
/* These are AF independant. */
static __inline__ int tcp_bhashfn(__u16 lport)
{
@@ -224,8 +235,12 @@ struct open_request {
__u16 rmt_port;
__u16 mss;
__u8 snd_wscale;
+ __u8 rcv_wscale;
char sack_ok;
char tstamp_ok;
+ char wscale_ok;
+ __u32 window_clamp; /* window clamp at creation time */
+ __u32 rcv_wnd; /* rcv_wnd offered first time */
__u32 ts_recent;
unsigned long expires;
int retrans;
@@ -452,6 +467,10 @@ struct tcp_sl_timer {
extern struct tcp_sl_timer tcp_slt_array[TCP_SLT_MAX];
+/*
+ * FIXME: this method of choosing when to send a window update
+ * does not seem correct to me. -- erics
+ */
static __inline__ unsigned short tcp_raise_window(struct sock *sk)
{
struct tcp_opt *tp = &sk->tp_pinfo.af_tcp;
@@ -553,9 +572,9 @@ static __inline__ void tcp_set_state(struct sock *sk, int state)
* It would be especially magical to compute the checksum for this
* stuff on the fly here.
*/
-extern __inline__ int tcp_syn_build_options(struct sk_buff *skb, int mss, int sack, int ts, int wscale)
+extern __inline__ int tcp_syn_build_options(struct sk_buff *skb, int mss, int sack, int ts, int offer_wscale, int wscale)
{
- int count = 4 + (wscale ? 4 : 0) + ((ts || sack) ? 4 : 0) + (ts ? 8 : 0);
+ int count = 4 + (offer_wscale ? 4 : 0) + ((ts || sack) ? 4 : 0) + (ts ? 8 : 0);
unsigned char *optr = skb_put(skb,count);
__u32 *ptr = (__u32 *)optr;
@@ -579,12 +598,53 @@ extern __inline__ int tcp_syn_build_options(struct sk_buff *skb, int mss, int sa
*ptr++ = htonl((TCPOPT_SACK_PERM << 24) | (TCPOLEN_SACK_PERM << 16)
| (TCPOPT_NOP << 8) | TCPOPT_NOP);
}
- if (wscale)
- *ptr++ = htonl((TCPOPT_WINDOW << 24) | (TCPOLEN_WINDOW << 16) | wscale);
+ if (offer_wscale)
+ *ptr++ = htonl((TCPOPT_WINDOW << 24) | (TCPOLEN_WINDOW << 16) | (wscale << 8));
skb->csum = csum_partial(optr, count, 0);
return count;
}
+/* Determine a window scaling and initial window to offer.
+ * Based on the assumption that the given amount of space
+ * will be offered. Store the results in the tp structure.
+ * NOTE: for smooth operation initial space offering should
+ * be a multiple of mss if possible. We assume here that mss >= 1.
+ * This MUST be enforced by all callers.
+ */
+extern __inline__ void tcp_select_initial_window(__u32 space, __u16 mss,
+ __u32 *rcv_wnd,
+ __u32 *window_clamp,
+ int wscale_ok,
+ __u8 *rcv_wscale)
+{
+ /* If no clamp set the clamp to the max possible scaled window */
+ if (*window_clamp == 0)
+ (*window_clamp) = (65535<<14);
+ space = min(*window_clamp,space);
+
+ /* Quantize space offering to a multiple of mss if possible. */
+ if (space > mss)
+ space = (space/mss)*mss;
+
+ /* NOTE: offering an initial window larger than 32767
+ * will break some buggy TCP stacks. We try to be nice.
+ * If we are not window scaling, then this truncates
+ * our initial window offering to 32k. There should also
+ * be a sysctl option to stop being nice.
+ */
+ (*rcv_wnd) = min(space,32767);
+ (*rcv_wscale) = 0;
+ if (wscale_ok) {
+ /* See RFC1323 for an explanation of the limit to 14 */
+ while (space > 65535 && (*rcv_wscale) < 14) {
+ space >>= 1;
+ (*rcv_wscale)++;
+ }
+ }
+ /* Set the clamp no higher than max representable value */
+ (*window_clamp) = min(65535<<(*rcv_wscale),*window_clamp);
+}
+
extern __inline__ void tcp_synq_unlink(struct tcp_opt *tp, struct open_request *req)
{
if(req->dl_next)