Skip site navigation (1)Skip section navigation (2)
Date:      Sun, 16 Jun 2019 22:33:58 +0200
From:      Peter <pmc@citylink.dinoex.sub.org>
To:        "Andrey V. Elsukov" <bu7cher@yandex.ru>
Cc:        freebsd-ipfw@freebsd.org
Subject:   Re: ipfw: switching sets does stall the machine
Message-ID:  <20190616203358.GA74004@gate.oper.dinoex.org>
In-Reply-To: <083acaaf-6262-f582-11ad-71623a88786b@yandex.ru>
References:  <20190614153302.GA4503@gate.oper.dinoex.org> <20190614172018.GJ1219@albert.catwhisker.org> <20190614201317.GA8840@gate.oper.dinoex.org> <083acaaf-6262-f582-11ad-71623a88786b@yandex.ru>

next in thread | previous in thread | raw e-mail | index | archive | help
On Sun, Jun 16, 2019 at 10:06:40PM +0300, Andrey V. Elsukov wrote:
! On 14.06.2019 23:13, Peter wrote:
! > 2. There are dynamic rules involved. These do not disappear on a
! >    "set disable". They stay and continue to function - somehow.
! >
! > 3. When a packet successfully matches a check-state, it does NOT
! >    continue to be processed at the rule following that check-state.
! >    Instead, it does continue to be processed at the place after
! >    the parent keep-state rule that was originally matched!
! > 
! >    But what if that keep-state rule is now disabled, and the new
! >    rules do not line up in their numbering in the exact same way?
! >    Then this packet appears at some arbitrary place in the rule
! >    list and may go to whereever.
! 
! Dynamic rules use only "action" part of parent rule, so when dynamic
! state is "applied" to a packet, it just executes action of parent rule
! without checking the set to which belongs the rule.

Yes, that I understand. And they only disappear when the parent rule
is deleted, not when it is disabled. Which actually is a good thing,
as there are these items sitting on a database connection, and they
tend to sit there forever:

> 00594     9839     1363578 (216s) STATE tcp 192.168.98.3 45596 <-> 192.168.97.9 5432 :f35
> 00594     9275    35395116 (36s) STATE tcp 192.168.98.3 32565 <-> 192.168.97.9 5432 :f35
> 00713      829     3029042 (292s) STATE tcp 192.168.98.2 34036 <-> 192.168.97.9 5432 :f25

Actually these shouldn't be dynamic rules - but if they happen to be,
things should still work.

! But then, if a packet processing is continued, the next rule checked
! from the beginning, and thus its set is checked.

Processing seems to continue right behind the original parent rule -
whatever tends to be there in some enabled set at that moment.

! You may try 11.3-BETA where new implementation of dyn_keep_states was
! committed. When you set net.inet.ip.fw.dyn_keep_states=1, the dynamic
! states aren't deleted with their parents rules.

It appeared to me that this would already work in 11.2 - but there are
a couple of other nice things appearing in 11.3, as it seems - e.g. a
better differenciation between the statefulness and the action of a
rule.

Anyway,dyn_keep_states seems to point the processing to rule #65535,
and that one does either allow or deny (without logging) - which is
not what I need. 

I went a different way now (which was actually easier than I thought):
I put all the stateful rules at the end of the list, so that it looks
like that:

...
65491        0           0 count tag 65534 tcp from ... to ... setup keep-state :f72
65492        0           0 return ip from any to any
65493        0           0 count tag 65534 tcp from ... to ... setup keep-state :f66
65494        0           0 return ip from any to any
65495        0           0 count tag 65534 tcp from ... to ... setup keep-state :f70
65496     4178      220618 return ip from any to any
65497        0           0 count tag 65534 tcp from ... to ... setup keep-state :f65
65498     4178      220618 return ip from any to any
...

Since this stucture will now always be at the end of the list, it does
not harm to switch sets - the dynamic rules need just a "return",
and will get one.

And when switching between staging and production, I move all the old
rules to an unused and disabled set, so that the ever-living dynamic
stuff does not get disconnected. I don't know how many rules the whole
thing can hold, but currently it seems to work that way.


My background for the whole effort is this: after 15 years of manually
maintaining a list of rules, I got very bored of it: this can be done
by a machine, and man should not do machine's work. So I wrote a
little engine that auto-generates the rules from the network diagram and
required services.
Now there can be an arbitrary number of NATs and forwards and anything
at any place, and it should create correct rules to handle it all.

But this requires a genuine approach to statefulness, where the
dynamic rule is de-coupled from it's action; because the specific
action can vary (e.g. when traversing a NAT in different directions).



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?20190616203358.GA74004>