kern/77570: [PATCH] ipfw: Multiple rules may have the same number.
Wojciech A. Koszek
dunstan at freebsd.czest.pl
Tue Feb 15 12:00:47 PST 2005
>Number: 77570
>Category: kern
>Synopsis: [PATCH] ipfw: Multiple rules may have the same number.
>Confidential: no
>Severity: non-critical
>Priority: low
>Responsible: freebsd-bugs
>State: open
>Quarter:
>Keywords:
>Date-Required:
>Class: sw-bug
>Submitter-Id: current-users
>Arrival-Date: Tue Feb 15 20:00:46 GMT 2005
>Closed-Date:
>Last-Modified:
>Originator: Wojciech A. Koszek
>Release: FreeBSD 5.3-STABLE i386
>Organization:
>Environment:
System: FreeBSD dunstan.freebsd.czest.pl 5.3-STABLE FreeBSD 5.3-STABLE #0: Sat Feb 12 11:15:23 CET 2005 root at dunstan.freebsd.czest.pl:/usr/obj/usr/src/sys/HOME6 i386
This problem exists in either -STABLE or -CURRENT.
>Description:
There is a problem while inserting ipfw2 rule with specified rule number.
# ipfw add <num> <action>
While executing this command N times, it will add N rules with the same
number <num>. I don't really like this behaviour, since rule number has to
represent the unique rule.
>How-To-Repeat:
This problem may be easily reproduced:
# ipfw add 100 allow all from any to any
00100 allow ip from any to any
# ipfw add 100 allow all from any to any
00100 allow ip from any to any
# ipfw add 100 allow all from any to any
00100 allow ip from any to any
# ipfw show | grep 00100
00100 0 0 allow ip from any to any
00100 0 0 allow ip from any to any
00100 0 0 allow ip from any to any
>Fix:
Attached patch [diff.0.ipfw2] should correct this problem. It also adds predefinition of
remove_rule(), because after applying this patch, add_rule() requires it.
--- diff.0.ipfw2 begins here ---
Patch against FreeBSD 5.3-STABLE, kern.osreldate: 503102.
diff -upr /usr/src/sys/netinet/ip_fw2.c src/sys/netinet/ip_fw2.c
--- /usr/src/sys/netinet/ip_fw2.c Sat Feb 12 09:36:43 2005
+++ src/sys/netinet/ip_fw2.c Tue Feb 15 20:11:17 2005
@@ -104,6 +104,9 @@ static struct callout ipfw_timeout;
static uma_zone_t ipfw_dyn_rule_zone;
#define IPFW_DEFAULT_RULE 65535
+static struct ip_fw *
+remove_rule(struct ip_fw_chain *, struct ip_fw *, struct ip_fw *);
+
/*
* Data structure to cache our ucred related
* information. This structure only gets used if
@@ -2599,7 +2602,19 @@ add_rule(struct ip_fw_chain *chain, stru
* Now insert the new rule in the right place in the sorted list.
*/
for (prev = NULL, f = chain->rules; f; prev = f, f = f->next) {
- if (f->rulenum > rule->rulenum) { /* found the location */
+ if (f->rulenum == rule->rulenum) { /* exact match */
+ rule->next = f->next;
+ (void) remove_rule(chain, f, prev);
+ if (prev != NULL) {
+ prev->next = rule;
+ }
+ else { /* head insert */
+ rule->next = chain->rules;
+ chain->rules = rule;
+ }
+ break;
+ }
+ else if (f->rulenum > rule->rulenum) { /* found the location */
if (prev) {
rule->next = f;
prev->next = rule;
--- diff.0.ipfw2 ends here ---
>Release-Note:
>Audit-Trail:
>Unformatted:
More information about the freebsd-bugs
mailing list