diff options
author | Robert Olsson <robert.olsson@its.uu.se> | 2005-10-04 16:01:58 -0400 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2005-10-04 16:01:58 -0400 |
commit | e6308be85afee685347fa3440bed10faaa5d6c1a (patch) | |
tree | 9cb766b5b66f700528722b2e92745a2a6dcc3288 | |
parent | 87bf9c97b4b3af8dec7b2b79cdfe7bfc0a0a03b2 (diff) |
[IPV4]: fib_trie root-node expansion
The patch below introduces special thresholds to keep root node in the trie
large. This gives a flatter tree at the cost of a modest memory increase.
Overall it seems to be gain and this was also proposed by one the authors
of the paper in recent a seminar.
Main table after loading 123 k routes.
Aver depth: 3.30
Max depth: 9
Root-node size 12 bits
Total size: 4044 kB
With the patch:
Aver depth: 2.78
Max depth: 8
Root-node size 15 bits
Total size: 4150 kB
An increase of 8-10% was seen in forwading performance for an rDoS attack.
Signed-off-by: Robert Olsson <robert.olsson@its.uu.se>
Signed-off-by: David S. Miller <davem@davemloft.net>
-rw-r--r-- | net/ipv4/fib_trie.c | 23 |
1 files changed, 21 insertions, 2 deletions
diff --git a/net/ipv4/fib_trie.c b/net/ipv4/fib_trie.c index 50c0519cd70d..0093ea08c7f5 100644 --- a/net/ipv4/fib_trie.c +++ b/net/ipv4/fib_trie.c | |||
@@ -286,6 +286,8 @@ static inline void check_tnode(const struct tnode *tn) | |||
286 | 286 | ||
287 | static int halve_threshold = 25; | 287 | static int halve_threshold = 25; |
288 | static int inflate_threshold = 50; | 288 | static int inflate_threshold = 50; |
289 | static int halve_threshold_root = 15; | ||
290 | static int inflate_threshold_root = 25; | ||
289 | 291 | ||
290 | 292 | ||
291 | static void __alias_free_mem(struct rcu_head *head) | 293 | static void __alias_free_mem(struct rcu_head *head) |
@@ -449,6 +451,8 @@ static struct node *resize(struct trie *t, struct tnode *tn) | |||
449 | int i; | 451 | int i; |
450 | int err = 0; | 452 | int err = 0; |
451 | struct tnode *old_tn; | 453 | struct tnode *old_tn; |
454 | int inflate_threshold_use; | ||
455 | int halve_threshold_use; | ||
452 | 456 | ||
453 | if (!tn) | 457 | if (!tn) |
454 | return NULL; | 458 | return NULL; |
@@ -541,10 +545,17 @@ static struct node *resize(struct trie *t, struct tnode *tn) | |||
541 | 545 | ||
542 | check_tnode(tn); | 546 | check_tnode(tn); |
543 | 547 | ||
548 | /* Keep root node larger */ | ||
549 | |||
550 | if(!tn->parent) | ||
551 | inflate_threshold_use = inflate_threshold_root; | ||
552 | else | ||
553 | inflate_threshold_use = inflate_threshold; | ||
554 | |||
544 | err = 0; | 555 | err = 0; |
545 | while ((tn->full_children > 0 && | 556 | while ((tn->full_children > 0 && |
546 | 50 * (tn->full_children + tnode_child_length(tn) - tn->empty_children) >= | 557 | 50 * (tn->full_children + tnode_child_length(tn) - tn->empty_children) >= |
547 | inflate_threshold * tnode_child_length(tn))) { | 558 | inflate_threshold_use * tnode_child_length(tn))) { |
548 | 559 | ||
549 | old_tn = tn; | 560 | old_tn = tn; |
550 | tn = inflate(t, tn); | 561 | tn = inflate(t, tn); |
@@ -564,10 +575,18 @@ static struct node *resize(struct trie *t, struct tnode *tn) | |||
564 | * node is above threshold. | 575 | * node is above threshold. |
565 | */ | 576 | */ |
566 | 577 | ||
578 | |||
579 | /* Keep root node larger */ | ||
580 | |||
581 | if(!tn->parent) | ||
582 | halve_threshold_use = halve_threshold_root; | ||
583 | else | ||
584 | halve_threshold_use = halve_threshold; | ||
585 | |||
567 | err = 0; | 586 | err = 0; |
568 | while (tn->bits > 1 && | 587 | while (tn->bits > 1 && |
569 | 100 * (tnode_child_length(tn) - tn->empty_children) < | 588 | 100 * (tnode_child_length(tn) - tn->empty_children) < |
570 | halve_threshold * tnode_child_length(tn)) { | 589 | halve_threshold_use * tnode_child_length(tn)) { |
571 | 590 | ||
572 | old_tn = tn; | 591 | old_tn = tn; |
573 | tn = halve(t, tn); | 592 | tn = halve(t, tn); |