diff options
| -rw-r--r-- | net/ipv6/ip6_fib.c | 15 |
1 files changed, 11 insertions, 4 deletions
diff --git a/net/ipv6/ip6_fib.c b/net/ipv6/ip6_fib.c index 192dd1a0e188..5fc9c7a68d8d 100644 --- a/net/ipv6/ip6_fib.c +++ b/net/ipv6/ip6_fib.c | |||
| @@ -632,6 +632,12 @@ insert_above: | |||
| 632 | return ln; | 632 | return ln; |
| 633 | } | 633 | } |
| 634 | 634 | ||
| 635 | static inline bool rt6_qualify_for_ecmp(struct rt6_info *rt) | ||
| 636 | { | ||
| 637 | return (rt->rt6i_flags & (RTF_GATEWAY|RTF_ADDRCONF|RTF_DYNAMIC)) == | ||
| 638 | RTF_GATEWAY; | ||
| 639 | } | ||
| 640 | |||
| 635 | /* | 641 | /* |
| 636 | * Insert routing information in a node. | 642 | * Insert routing information in a node. |
| 637 | */ | 643 | */ |
| @@ -646,6 +652,7 @@ static int fib6_add_rt2node(struct fib6_node *fn, struct rt6_info *rt, | |||
| 646 | int add = (!info->nlh || | 652 | int add = (!info->nlh || |
| 647 | (info->nlh->nlmsg_flags & NLM_F_CREATE)); | 653 | (info->nlh->nlmsg_flags & NLM_F_CREATE)); |
| 648 | int found = 0; | 654 | int found = 0; |
| 655 | bool rt_can_ecmp = rt6_qualify_for_ecmp(rt); | ||
| 649 | 656 | ||
| 650 | ins = &fn->leaf; | 657 | ins = &fn->leaf; |
| 651 | 658 | ||
| @@ -691,9 +698,8 @@ static int fib6_add_rt2node(struct fib6_node *fn, struct rt6_info *rt, | |||
| 691 | * To avoid long list, we only had siblings if the | 698 | * To avoid long list, we only had siblings if the |
| 692 | * route have a gateway. | 699 | * route have a gateway. |
| 693 | */ | 700 | */ |
| 694 | if (rt->rt6i_flags & RTF_GATEWAY && | 701 | if (rt_can_ecmp && |
| 695 | !(rt->rt6i_flags & RTF_EXPIRES) && | 702 | rt6_qualify_for_ecmp(iter)) |
| 696 | !(iter->rt6i_flags & RTF_EXPIRES)) | ||
| 697 | rt->rt6i_nsiblings++; | 703 | rt->rt6i_nsiblings++; |
| 698 | } | 704 | } |
| 699 | 705 | ||
| @@ -715,7 +721,8 @@ static int fib6_add_rt2node(struct fib6_node *fn, struct rt6_info *rt, | |||
| 715 | /* Find the first route that have the same metric */ | 721 | /* Find the first route that have the same metric */ |
| 716 | sibling = fn->leaf; | 722 | sibling = fn->leaf; |
| 717 | while (sibling) { | 723 | while (sibling) { |
| 718 | if (sibling->rt6i_metric == rt->rt6i_metric) { | 724 | if (sibling->rt6i_metric == rt->rt6i_metric && |
| 725 | rt6_qualify_for_ecmp(sibling)) { | ||
| 719 | list_add_tail(&rt->rt6i_siblings, | 726 | list_add_tail(&rt->rt6i_siblings, |
| 720 | &sibling->rt6i_siblings); | 727 | &sibling->rt6i_siblings); |
| 721 | break; | 728 | break; |
