tipc: introduce jumbo frame support for broadcast
authorJon Paul Maloy <jon.maloy@ericsson.com>
Thu, 22 Oct 2015 12:51:43 +0000 (08:51 -0400)
committerDavid S. Miller <davem@davemloft.net>
Sat, 24 Oct 2015 13:56:40 +0000 (06:56 -0700)
Until now, we have only been supporting a fix MTU size of 1500 bytes
for all broadcast media, irrespective of their actual capability.

We now make the broadcast MTU adaptable to the carrying media, i.e.,
we use the smallest MTU supported by any of the interfaces attached
to TIPC.

Signed-off-by: Jon Maloy <jon.maloy@ericsson.com>
Reviewed-by: Ying Xue <ying.xue@windriver.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
net/tipc/bcast.c
net/tipc/bcast.h
net/tipc/bearer.c
net/tipc/bearer.h
net/tipc/link.c
net/tipc/link.h
net/tipc/socket.c

index 74ee09ac430d03fd3556cffdcad55a92c5932d7a..d8c399d312883571686596a50913ad938020f7bd 100644 (file)
@@ -148,9 +148,9 @@ void tipc_bclink_input(struct net *net)
        tipc_sk_mcast_rcv(net, &tn->bcbase->arrvq, &tn->bcbase->inputq);
 }
 
-uint  tipc_bcast_get_mtu(void)
+int tipc_bcast_get_mtu(struct net *net)
 {
-       return MAX_PKT_DEFAULT_MCAST;
+       return tipc_link_mtu(tipc_bc_sndlink(net));
 }
 
 static u16 bcbuf_acks(struct sk_buff *skb)
@@ -175,7 +175,7 @@ static void tipc_bcbase_select_primary(struct net *net)
 {
        struct tipc_bc_base *bb = tipc_bc_base(net);
        int all_dests =  tipc_link_bc_peers(bb->link);
-       int i;
+       int i, mtu;
 
        bb->primary_bearer = INVALID_BEARER_ID;
 
@@ -183,6 +183,13 @@ static void tipc_bcbase_select_primary(struct net *net)
                return;
 
        for (i = 0; i < MAX_BEARERS; i++) {
+               if (!bb->dests[i])
+                       continue;
+
+               mtu = tipc_bearer_mtu(net, i);
+               if (mtu < tipc_link_mtu(bb->link))
+                       tipc_link_set_mtu(bb->link, mtu);
+
                if (bb->dests[i] < all_dests)
                        continue;
 
@@ -1220,7 +1227,7 @@ int tipc_bcast_init(struct net *net)
        bb->node.net = net;
 
        if (!tipc_link_bc_create(&bb->node, 0, 0,
-                                MAX_PKT_DEFAULT_MCAST,
+                                U16_MAX,
                                 BCLINK_WIN_DEFAULT,
                                 0,
                                 &bb->inputq,
index 76b747a73b0bf537d141fbc7b5efe2a6507f5598..0cc72200f1cdf3f07f7922cf6b8011fe5b5b167c 100644 (file)
@@ -63,7 +63,7 @@ void tipc_bcbearer_sort(struct net *net, struct tipc_node_map *nm_ptr,
                        u32 node, bool action);
 int  tipc_bclink_reset_stats(struct net *net);
 int  tipc_bclink_set_queue_limits(struct net *net, u32 limit);
-uint  tipc_bcast_get_mtu(void);
+int  tipc_bcast_get_mtu(struct net *net);
 int tipc_bcast_xmit(struct net *net, struct sk_buff_head *list);
 int tipc_bcast_rcv(struct net *net, struct tipc_link *l, struct sk_buff *skb);
 void tipc_bcast_ack_rcv(struct net *net, struct tipc_link *l, u32 acked);
index 62f47ecc6b847d1a2a9419d7b20d669292ede1d1..b39f631fd6d7c4ceb251af7e6109da4c1ecee545 100644 (file)
@@ -464,6 +464,19 @@ void tipc_bearer_send(struct net *net, u32 bearer_id, struct sk_buff *buf,
        rcu_read_unlock();
 }
 
+int tipc_bearer_mtu(struct net *net, u32 bearer_id)
+{
+       int mtu = 0;
+       struct tipc_bearer *b;
+
+       rcu_read_lock();
+       b = rcu_dereference_rtnl(tipc_net(net)->bearer_list[bearer_id]);
+       if (b)
+               mtu = b->mtu;
+       rcu_read_unlock();
+       return mtu;
+}
+
 /* tipc_bearer_xmit() -send buffer to destination over bearer
  */
 void tipc_bearer_xmit(struct net *net, u32 bearer_id,
index 9fc1e074f7c075b8915f0239627985f442a8035a..2ba8a7e274a5e85dd1241f80d10c81bed565e9c2 100644 (file)
@@ -218,6 +218,7 @@ void tipc_bearer_cleanup(void);
 void tipc_bearer_stop(struct net *net);
 void tipc_bearer_send(struct net *net, u32 bearer_id, struct sk_buff *buf,
                      struct tipc_media_addr *dest);
+int tipc_bearer_mtu(struct net *net, u32 bearer_id);
 void tipc_bearer_xmit(struct net *net, u32 bearer_id,
                      struct sk_buff_head *xmitq,
                      struct tipc_media_addr *dst);
index ff725c398914f4b23b8f104ee9fe0b1c25ff0f98..3b98f8e706267b60c9c287606c9c572025bdf15f 100644 (file)
@@ -212,6 +212,16 @@ int tipc_link_bc_peers(struct tipc_link *l)
        return l->ackers;
 }
 
+void tipc_link_set_mtu(struct tipc_link *l, int mtu)
+{
+       l->mtu = mtu;
+}
+
+int tipc_link_mtu(struct tipc_link *l)
+{
+       return l->mtu;
+}
+
 static u32 link_own_addr(struct tipc_link *l)
 {
        return msg_prevnode(l->pmsg);
index 28a6396b6d314008a0b65eebde95226d81d376e4..9b5198e90fdf60b8ca78be81b82abb6047f216b5 100644 (file)
@@ -281,6 +281,8 @@ void tipc_link_remove_bc_peer(struct tipc_link *snd_l,
                              struct tipc_link *rcv_l,
                              struct sk_buff_head *xmitq);
 int tipc_link_bc_peers(struct tipc_link *l);
+void tipc_link_set_mtu(struct tipc_link *l, int mtu);
+int tipc_link_mtu(struct tipc_link *l);
 void tipc_link_bc_ack_rcv(struct tipc_link *l, u16 acked,
                          struct sk_buff_head *xmitq);
 void tipc_link_build_bc_sync_msg(struct tipc_link *l,
index e2e35b7b1d09a3bc62aa7db4fcbe0342742e5dd6..552dbaba9cf386a07e6c4f499fda27ca1f8a8f4a 100644 (file)
@@ -689,7 +689,7 @@ static int tipc_sendmcast(struct  socket *sock, struct tipc_name_seq *seq,
        msg_set_hdr_sz(mhdr, MCAST_H_SIZE);
 
 new_mtu:
-       mtu = tipc_bcast_get_mtu();
+       mtu = tipc_bcast_get_mtu(net);
        rc = tipc_msg_build(mhdr, msg, 0, dsz, mtu, pktchain);
        if (unlikely(rc < 0))
                return rc;