Skip to content

Commit 02ec6ca

Browse files
Hoang Ledavem330
authored andcommitted
tipc: support broadcast/replicast configurable for bc-link
Currently, a multicast stream uses either broadcast or replicast as transmission method, based on the ratio between number of actual destinations nodes and cluster size. However, when an L2 interface (e.g., VXLAN) provides pseudo broadcast support, this becomes very inefficient, as it blindly replicates multicast packets to all cluster/subnet nodes, irrespective of whether they host actual target sockets or not. The TIPC multicast algorithm is able to distinguish real destination nodes from other nodes, and hence provides a smarter and more efficient method for transferring multicast messages than pseudo broadcast can do. Because of this, we now make it possible for users to force the broadcast link to permanently switch to using replicast, irrespective of which capabilities the bearer provides, or pretend to provide. Conversely, we also make it possible to force the broadcast link to always use true broadcast. While maybe less useful in deployed systems, this may at least be useful for testing the broadcast algorithm in small clusters. We retain the current AUTOSELECT ability, i.e., to let the broadcast link automatically select which algorithm to use, and to switch back and forth between broadcast and replicast as the ratio between destination node number and cluster size changes. This remains the default method. Furthermore, we make it possible to configure the threshold ratio for such switches. The default ratio is now set to 10%, down from 25% in the earlier implementation. Acked-by: Jon Maloy <[email protected]> Signed-off-by: Hoang Le <[email protected]> Signed-off-by: David S. Miller <[email protected]>
1 parent 310974f commit 02ec6ca

File tree

5 files changed

+120
-5
lines changed

5 files changed

+120
-5
lines changed

include/uapi/linux/tipc_netlink.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -281,6 +281,8 @@ enum {
281281
TIPC_NLA_PROP_TOL, /* u32 */
282282
TIPC_NLA_PROP_WIN, /* u32 */
283283
TIPC_NLA_PROP_MTU, /* u32 */
284+
TIPC_NLA_PROP_BROADCAST, /* u32 */
285+
TIPC_NLA_PROP_BROADCAST_RATIO, /* u32 */
284286

285287
__TIPC_NLA_PROP_MAX,
286288
TIPC_NLA_PROP_MAX = __TIPC_NLA_PROP_MAX - 1

net/tipc/bcast.c

Lines changed: 100 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -54,7 +54,9 @@ const char tipc_bclink_name[] = "broadcast-link";
5454
* @dests: array keeping number of reachable destinations per bearer
5555
* @primary_bearer: a bearer having links to all broadcast destinations, if any
5656
* @bcast_support: indicates if primary bearer, if any, supports broadcast
57+
* @force_bcast: forces broadcast for multicast traffic
5758
* @rcast_support: indicates if all peer nodes support replicast
59+
* @force_rcast: forces replicast for multicast traffic
5860
* @rc_ratio: dest count as percentage of cluster size where send method changes
5961
* @bc_threshold: calculated from rc_ratio; if dests > threshold use broadcast
6062
*/
@@ -64,7 +66,9 @@ struct tipc_bc_base {
6466
int dests[MAX_BEARERS];
6567
int primary_bearer;
6668
bool bcast_support;
69+
bool force_bcast;
6770
bool rcast_support;
71+
bool force_rcast;
6872
int rc_ratio;
6973
int bc_threshold;
7074
};
@@ -485,10 +489,63 @@ static int tipc_bc_link_set_queue_limits(struct net *net, u32 limit)
485489
return 0;
486490
}
487491

492+
static int tipc_bc_link_set_broadcast_mode(struct net *net, u32 bc_mode)
493+
{
494+
struct tipc_bc_base *bb = tipc_bc_base(net);
495+
496+
switch (bc_mode) {
497+
case BCLINK_MODE_BCAST:
498+
if (!bb->bcast_support)
499+
return -ENOPROTOOPT;
500+
501+
bb->force_bcast = true;
502+
bb->force_rcast = false;
503+
break;
504+
case BCLINK_MODE_RCAST:
505+
if (!bb->rcast_support)
506+
return -ENOPROTOOPT;
507+
508+
bb->force_bcast = false;
509+
bb->force_rcast = true;
510+
break;
511+
case BCLINK_MODE_SEL:
512+
if (!bb->bcast_support || !bb->rcast_support)
513+
return -ENOPROTOOPT;
514+
515+
bb->force_bcast = false;
516+
bb->force_rcast = false;
517+
break;
518+
default:
519+
return -EINVAL;
520+
}
521+
522+
return 0;
523+
}
524+
525+
static int tipc_bc_link_set_broadcast_ratio(struct net *net, u32 bc_ratio)
526+
{
527+
struct tipc_bc_base *bb = tipc_bc_base(net);
528+
529+
if (!bb->bcast_support || !bb->rcast_support)
530+
return -ENOPROTOOPT;
531+
532+
if (bc_ratio > 100 || bc_ratio <= 0)
533+
return -EINVAL;
534+
535+
bb->rc_ratio = bc_ratio;
536+
tipc_bcast_lock(net);
537+
tipc_bcbase_calc_bc_threshold(net);
538+
tipc_bcast_unlock(net);
539+
540+
return 0;
541+
}
542+
488543
int tipc_nl_bc_link_set(struct net *net, struct nlattr *attrs[])
489544
{
490545
int err;
491546
u32 win;
547+
u32 bc_mode;
548+
u32 bc_ratio;
492549
struct nlattr *props[TIPC_NLA_PROP_MAX + 1];
493550

494551
if (!attrs[TIPC_NLA_LINK_PROP])
@@ -498,12 +555,28 @@ int tipc_nl_bc_link_set(struct net *net, struct nlattr *attrs[])
498555
if (err)
499556
return err;
500557

501-
if (!props[TIPC_NLA_PROP_WIN])
558+
if (!props[TIPC_NLA_PROP_WIN] &&
559+
!props[TIPC_NLA_PROP_BROADCAST] &&
560+
!props[TIPC_NLA_PROP_BROADCAST_RATIO]) {
502561
return -EOPNOTSUPP;
562+
}
563+
564+
if (props[TIPC_NLA_PROP_BROADCAST]) {
565+
bc_mode = nla_get_u32(props[TIPC_NLA_PROP_BROADCAST]);
566+
err = tipc_bc_link_set_broadcast_mode(net, bc_mode);
567+
}
503568

504-
win = nla_get_u32(props[TIPC_NLA_PROP_WIN]);
569+
if (!err && props[TIPC_NLA_PROP_BROADCAST_RATIO]) {
570+
bc_ratio = nla_get_u32(props[TIPC_NLA_PROP_BROADCAST_RATIO]);
571+
err = tipc_bc_link_set_broadcast_ratio(net, bc_ratio);
572+
}
505573

506-
return tipc_bc_link_set_queue_limits(net, win);
574+
if (!err && props[TIPC_NLA_PROP_WIN]) {
575+
win = nla_get_u32(props[TIPC_NLA_PROP_WIN]);
576+
err = tipc_bc_link_set_queue_limits(net, win);
577+
}
578+
579+
return err;
507580
}
508581

509582
int tipc_bcast_init(struct net *net)
@@ -529,7 +602,7 @@ int tipc_bcast_init(struct net *net)
529602
goto enomem;
530603
bb->link = l;
531604
tn->bcl = l;
532-
bb->rc_ratio = 25;
605+
bb->rc_ratio = 10;
533606
bb->rcast_support = true;
534607
return 0;
535608
enomem:
@@ -576,3 +649,26 @@ void tipc_nlist_purge(struct tipc_nlist *nl)
576649
nl->remote = 0;
577650
nl->local = false;
578651
}
652+
653+
u32 tipc_bcast_get_broadcast_mode(struct net *net)
654+
{
655+
struct tipc_bc_base *bb = tipc_bc_base(net);
656+
657+
if (bb->force_bcast)
658+
return BCLINK_MODE_BCAST;
659+
660+
if (bb->force_rcast)
661+
return BCLINK_MODE_RCAST;
662+
663+
if (bb->bcast_support && bb->rcast_support)
664+
return BCLINK_MODE_SEL;
665+
666+
return 0;
667+
}
668+
669+
u32 tipc_bcast_get_broadcast_ratio(struct net *net)
670+
{
671+
struct tipc_bc_base *bb = tipc_bc_base(net);
672+
673+
return bb->rc_ratio;
674+
}

net/tipc/bcast.h

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -48,6 +48,10 @@ extern const char tipc_bclink_name[];
4848

4949
#define TIPC_METHOD_EXPIRE msecs_to_jiffies(5000)
5050

51+
#define BCLINK_MODE_BCAST 0x1
52+
#define BCLINK_MODE_RCAST 0x2
53+
#define BCLINK_MODE_SEL 0x4
54+
5155
struct tipc_nlist {
5256
struct list_head list;
5357
u32 self;
@@ -92,6 +96,9 @@ int tipc_nl_add_bc_link(struct net *net, struct tipc_nl_msg *msg);
9296
int tipc_nl_bc_link_set(struct net *net, struct nlattr *attrs[]);
9397
int tipc_bclink_reset_stats(struct net *net);
9498

99+
u32 tipc_bcast_get_broadcast_mode(struct net *net);
100+
u32 tipc_bcast_get_broadcast_ratio(struct net *net);
101+
95102
static inline void tipc_bcast_lock(struct net *net)
96103
{
97104
spin_lock_bh(&tipc_net(net)->bclock);

net/tipc/link.c

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2197,6 +2197,8 @@ int tipc_nl_add_bc_link(struct net *net, struct tipc_nl_msg *msg)
21972197
struct nlattr *attrs;
21982198
struct nlattr *prop;
21992199
struct tipc_net *tn = net_generic(net, tipc_net_id);
2200+
u32 bc_mode = tipc_bcast_get_broadcast_mode(net);
2201+
u32 bc_ratio = tipc_bcast_get_broadcast_ratio(net);
22002202
struct tipc_link *bcl = tn->bcl;
22012203

22022204
if (!bcl)
@@ -2233,6 +2235,12 @@ int tipc_nl_add_bc_link(struct net *net, struct tipc_nl_msg *msg)
22332235
goto attr_msg_full;
22342236
if (nla_put_u32(msg->skb, TIPC_NLA_PROP_WIN, bcl->window))
22352237
goto prop_msg_full;
2238+
if (nla_put_u32(msg->skb, TIPC_NLA_PROP_BROADCAST, bc_mode))
2239+
goto prop_msg_full;
2240+
if (bc_mode & BCLINK_MODE_SEL)
2241+
if (nla_put_u32(msg->skb, TIPC_NLA_PROP_BROADCAST_RATIO,
2242+
bc_ratio))
2243+
goto prop_msg_full;
22362244
nla_nest_end(msg->skb, prop);
22372245

22382246
err = __tipc_nl_add_bc_link_stat(msg->skb, &bcl->stats);

net/tipc/netlink.c

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -110,7 +110,9 @@ const struct nla_policy tipc_nl_prop_policy[TIPC_NLA_PROP_MAX + 1] = {
110110
[TIPC_NLA_PROP_UNSPEC] = { .type = NLA_UNSPEC },
111111
[TIPC_NLA_PROP_PRIO] = { .type = NLA_U32 },
112112
[TIPC_NLA_PROP_TOL] = { .type = NLA_U32 },
113-
[TIPC_NLA_PROP_WIN] = { .type = NLA_U32 }
113+
[TIPC_NLA_PROP_WIN] = { .type = NLA_U32 },
114+
[TIPC_NLA_PROP_BROADCAST] = { .type = NLA_U32 },
115+
[TIPC_NLA_PROP_BROADCAST_RATIO] = { .type = NLA_U32 }
114116
};
115117

116118
const struct nla_policy tipc_nl_bearer_policy[TIPC_NLA_BEARER_MAX + 1] = {

0 commit comments

Comments
 (0)