summaryrefslogtreecommitdiff
path: root/sys/net/pf.c
diff options
context:
space:
mode:
Diffstat (limited to 'sys/net/pf.c')
-rw-r--r--sys/net/pf.c34
1 files changed, 29 insertions, 5 deletions
diff --git a/sys/net/pf.c b/sys/net/pf.c
index bbe4a72d276..02687cb2e9d 100644
--- a/sys/net/pf.c
+++ b/sys/net/pf.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: pf.c,v 1.347 2003/05/12 17:49:03 mcbride Exp $ */
+/* $OpenBSD: pf.c,v 1.348 2003/05/12 22:53:47 frantzen Exp $ */
/*
* Copyright (c) 2001 Daniel Hartmeier
@@ -2145,9 +2145,16 @@ pf_test_tcp(struct pf_rule **rm, struct pf_state **sm, int direction,
s->src.seqhi++;
s->src.wscale = pf_get_wscale(m, off, th->th_off, af);
}
+ s->src.max_win = MAX(ntohs(th->th_win), 1);
+ if (s->src.wscale & PF_WSCALE_MASK) {
+ /* Remove scale factor from initial window */
+ int win = s->src.max_win;
+ win += 1 << (s->src.wscale & PF_WSCALE_MASK);
+ s->src.max_win = (win - 1) >>
+ (s->src.wscale & PF_WSCALE_MASK);
+ }
if (th->th_flags & TH_FIN)
s->src.seqhi++;
- s->src.max_win = MAX(ntohs(th->th_win), 1);
s->dst.seqlo = 0; /* Haven't seen these yet */
s->dst.seqhi = 1;
s->dst.max_win = 1;
@@ -2989,7 +2996,24 @@ pf_test_state_tcp(struct pf_state **state, int direction, struct ifnet *ifp,
end = seq + pd->p_len;
if (th->th_flags & TH_SYN) {
end++;
- src->wscale = pf_get_wscale(m, off, th->th_off, pd->af);
+ if (dst->wscale & PF_WSCALE_FLAG) {
+ src->wscale = pf_get_wscale(m, off, th->th_off,
+ pd->af);
+ if (src->wscale & PF_WSCALE_FLAG) {
+ /* Remove scale factor from initial
+ * window */
+ sws = src->wscale & PF_WSCALE_MASK;
+ win = ((u_int32_t)win + (1 << sws) - 1)
+ >> sws;
+ dws = dst->wscale & PF_WSCALE_MASK;
+ } else {
+ /* fixup other window */
+ dst->max_win <<= dst->wscale &
+ PF_WSCALE_MASK;
+ /* in case of a retrans SYN|ACK */
+ dst->wscale = 0;
+ }
+ }
}
if (th->th_flags & TH_FIN)
end++;
@@ -3052,8 +3076,8 @@ pf_test_state_tcp(struct pf_state **state, int direction, struct ifnet *ifp,
SEQ_GEQ(seq, src->seqlo - (dst->max_win << dws)) &&
/* Retrans: not more than one window back */
(ackskew >= -MAXACKWINDOW) &&
- /* Acking not more than one window back */
- (ackskew <= MAXACKWINDOW)) {
+ /* Acking not more than one reassembled fragment backwards */
+ (ackskew <= (MAXACKWINDOW << dws))) {
/* Acking not more than one window forward */
(*state)->packets++;