summaryrefslogtreecommitdiff
path: root/net/tipc/link.c
diff options
context:
space:
mode:
Diffstat (limited to 'net/tipc/link.c')
-rw-r--r--net/tipc/link.c493
1 files changed, 323 insertions, 170 deletions
diff --git a/net/tipc/link.c b/net/tipc/link.c
index 69cd9bf..0cc3d90 100644
--- a/net/tipc/link.c
+++ b/net/tipc/link.c
@@ -75,6 +75,20 @@ static const char *link_unk_evt = "Unknown link event ";
*/
#define START_CHANGEOVER 100000u
+/**
+ * struct tipc_link_name - deconstructed link name
+ * @addr_local: network address of node at this end
+ * @if_local: name of interface at this end
+ * @addr_peer: network address of node at far end
+ * @if_peer: name of interface at far end
+ */
+struct tipc_link_name {
+ u32 addr_local;
+ char if_local[TIPC_MAX_IF_NAME];
+ u32 addr_peer;
+ char if_peer[TIPC_MAX_IF_NAME];
+};
+
static void link_handle_out_of_seq_msg(struct tipc_link *l_ptr,
struct sk_buff *buf);
static void link_recv_proto_msg(struct tipc_link *l_ptr, struct sk_buff *buf);
@@ -83,7 +97,8 @@ static int link_recv_changeover_msg(struct tipc_link **l_ptr,
static void link_set_supervision_props(struct tipc_link *l_ptr, u32 tolerance);
static int link_send_sections_long(struct tipc_port *sender,
struct iovec const *msg_sect,
- unsigned int len, u32 destnode);
+ u32 num_sect, unsigned int total_len,
+ u32 destnode);
static void link_state_event(struct tipc_link *l_ptr, u32 event);
static void link_reset_statistics(struct tipc_link *l_ptr);
static void link_print(struct tipc_link *l_ptr, const char *str);
@@ -146,6 +161,72 @@ int tipc_link_is_active(struct tipc_link *l_ptr)
}
/**
+ * link_name_validate - validate & (optionally) deconstruct tipc_link name
+ * @name: ptr to link name string
+ * @name_parts: ptr to area for link name components (or NULL if not needed)
+ *
+ * Returns 1 if link name is valid, otherwise 0.
+ */
+static int link_name_validate(const char *name,
+ struct tipc_link_name *name_parts)
+{
+ char name_copy[TIPC_MAX_LINK_NAME];
+ char *addr_local;
+ char *if_local;
+ char *addr_peer;
+ char *if_peer;
+ char dummy;
+ u32 z_local, c_local, n_local;
+ u32 z_peer, c_peer, n_peer;
+ u32 if_local_len;
+ u32 if_peer_len;
+
+ /* copy link name & ensure length is OK */
+ name_copy[TIPC_MAX_LINK_NAME - 1] = 0;
+ /* need above in case non-Posix strncpy() doesn't pad with nulls */
+ strncpy(name_copy, name, TIPC_MAX_LINK_NAME);
+ if (name_copy[TIPC_MAX_LINK_NAME - 1] != 0)
+ return 0;
+
+ /* ensure all component parts of link name are present */
+ addr_local = name_copy;
+ if_local = strchr(addr_local, ':');
+ if (if_local == NULL)
+ return 0;
+ *(if_local++) = 0;
+ addr_peer = strchr(if_local, '-');
+ if (addr_peer == NULL)
+ return 0;
+ *(addr_peer++) = 0;
+ if_local_len = addr_peer - if_local;
+ if_peer = strchr(addr_peer, ':');
+ if (if_peer == NULL)
+ return 0;
+ *(if_peer++) = 0;
+ if_peer_len = strlen(if_peer) + 1;
+
+ /* validate component parts of link name */
+ if ((sscanf(addr_local, "%u.%u.%u%c",
+ &z_local, &c_local, &n_local, &dummy) != 3) ||
+ (sscanf(addr_peer, "%u.%u.%u%c",
+ &z_peer, &c_peer, &n_peer, &dummy) != 3) ||
+ (z_local > 255) || (c_local > 4095) || (n_local > 4095) ||
+ (z_peer > 255) || (c_peer > 4095) || (n_peer > 4095) ||
+ (if_local_len <= 1) || (if_local_len > TIPC_MAX_IF_NAME) ||
+ (if_peer_len <= 1) || (if_peer_len > TIPC_MAX_IF_NAME))
+ return 0;
+
+ /* return link name components, if necessary */
+ if (name_parts) {
+ name_parts->addr_local = tipc_addr(z_local, c_local, n_local);
+ strcpy(name_parts->if_local, if_local);
+ name_parts->addr_peer = tipc_addr(z_peer, c_peer, n_peer);
+ strcpy(name_parts->if_peer, if_peer);
+ }
+ return 1;
+}
+
+/**
* link_timeout - handle expiration of link timer
* @l_ptr: pointer to link
*
@@ -404,9 +485,15 @@ static void link_release_outqueue(struct tipc_link *l_ptr)
*/
void tipc_link_reset_fragments(struct tipc_link *l_ptr)
{
- kfree_skb(l_ptr->reasm_head);
- l_ptr->reasm_head = NULL;
- l_ptr->reasm_tail = NULL;
+ struct sk_buff *buf = l_ptr->defragm_buf;
+ struct sk_buff *next;
+
+ while (buf) {
+ next = buf->next;
+ kfree_skb(buf);
+ buf = next;
+ }
+ l_ptr->defragm_buf = NULL;
}
/**
@@ -978,7 +1065,8 @@ static int link_send_buf_fast(struct tipc_link *l_ptr, struct sk_buff *buf,
*/
int tipc_link_send_sections_fast(struct tipc_port *sender,
struct iovec const *msg_sect,
- unsigned int len, u32 destaddr)
+ const u32 num_sect, unsigned int total_len,
+ u32 destaddr)
{
struct tipc_msg *hdr = &sender->phdr;
struct tipc_link *l_ptr;
@@ -992,7 +1080,8 @@ again:
* Try building message using port's max_pkt hint.
* (Must not hold any locks while building message.)
*/
- res = tipc_msg_build(hdr, msg_sect, len, sender->max_pkt, &buf);
+ res = tipc_msg_build(hdr, msg_sect, num_sect, total_len,
+ sender->max_pkt, &buf);
/* Exit if build request was invalid */
if (unlikely(res < 0))
return res;
@@ -1032,7 +1121,8 @@ exit:
if ((msg_hdr_sz(hdr) + res) <= sender->max_pkt)
goto again;
- return link_send_sections_long(sender, msg_sect, len,
+ return link_send_sections_long(sender, msg_sect,
+ num_sect, total_len,
destaddr);
}
tipc_node_unlock(node);
@@ -1043,8 +1133,8 @@ exit:
if (buf)
return tipc_reject_msg(buf, TIPC_ERR_NO_NODE);
if (res >= 0)
- return tipc_port_reject_sections(sender, hdr, msg_sect,
- len, TIPC_ERR_NO_NODE);
+ return tipc_port_reject_sections(sender, hdr, msg_sect, num_sect,
+ total_len, TIPC_ERR_NO_NODE);
return res;
}
@@ -1064,17 +1154,18 @@ exit:
*/
static int link_send_sections_long(struct tipc_port *sender,
struct iovec const *msg_sect,
- unsigned int len, u32 destaddr)
+ u32 num_sect, unsigned int total_len,
+ u32 destaddr)
{
struct tipc_link *l_ptr;
struct tipc_node *node;
struct tipc_msg *hdr = &sender->phdr;
- u32 dsz = len;
+ u32 dsz = total_len;
u32 max_pkt, fragm_sz, rest;
struct tipc_msg fragm_hdr;
struct sk_buff *buf, *buf_chain, *prev;
u32 fragm_crs, fragm_rest, hsz, sect_rest;
- const unchar __user *sect_crs;
+ const unchar *sect_crs;
int curr_sect;
u32 fragm_no;
int res = 0;
@@ -1116,7 +1207,7 @@ again:
if (!sect_rest) {
sect_rest = msg_sect[++curr_sect].iov_len;
- sect_crs = msg_sect[curr_sect].iov_base;
+ sect_crs = (const unchar *)msg_sect[curr_sect].iov_base;
}
if (sect_rest < fragm_rest)
@@ -1192,8 +1283,8 @@ reject:
buf = buf_chain->next;
kfree_skb(buf_chain);
}
- return tipc_port_reject_sections(sender, hdr, msg_sect,
- len, TIPC_ERR_NO_NODE);
+ return tipc_port_reject_sections(sender, hdr, msg_sect, num_sect,
+ total_len, TIPC_ERR_NO_NODE);
}
/* Append chain of fragments to send queue & send them */
@@ -1501,15 +1592,15 @@ void tipc_recv_msg(struct sk_buff *head, struct tipc_bearer *b_ptr)
/* Ensure bearer is still enabled */
if (unlikely(!b_ptr->active))
- goto discard;
+ goto cont;
/* Ensure message is well-formed */
if (unlikely(!link_recv_buf_validate(buf)))
- goto discard;
+ goto cont;
/* Ensure message data is a single contiguous unit */
if (unlikely(skb_linearize(buf)))
- goto discard;
+ goto cont;
/* Handle arrival of a non-unicast link message */
msg = buf_msg(buf);
@@ -1525,18 +1616,20 @@ void tipc_recv_msg(struct sk_buff *head, struct tipc_bearer *b_ptr)
/* Discard unicast link messages destined for another node */
if (unlikely(!msg_short(msg) &&
(msg_destnode(msg) != tipc_own_addr)))
- goto discard;
+ goto cont;
/* Locate neighboring node that sent message */
n_ptr = tipc_node_find(msg_prevnode(msg));
if (unlikely(!n_ptr))
- goto discard;
+ goto cont;
tipc_node_lock(n_ptr);
/* Locate unicast link endpoint that should handle message */
l_ptr = n_ptr->links[b_ptr->identity];
- if (unlikely(!l_ptr))
- goto unlock_discard;
+ if (unlikely(!l_ptr)) {
+ tipc_node_unlock(n_ptr);
+ goto cont;
+ }
/* Verify that communication with node is currently allowed */
if ((n_ptr->block_setup & WAIT_PEER_DOWN) &&
@@ -1546,8 +1639,10 @@ void tipc_recv_msg(struct sk_buff *head, struct tipc_bearer *b_ptr)
!msg_redundant_link(msg))
n_ptr->block_setup &= ~WAIT_PEER_DOWN;
- if (n_ptr->block_setup)
- goto unlock_discard;
+ if (n_ptr->block_setup) {
+ tipc_node_unlock(n_ptr);
+ goto cont;
+ }
/* Validate message sequence number info */
seq_no = msg_seqno(msg);
@@ -1583,100 +1678,98 @@ void tipc_recv_msg(struct sk_buff *head, struct tipc_bearer *b_ptr)
/* Now (finally!) process the incoming message */
protocol_check:
- if (unlikely(!link_working_working(l_ptr))) {
- if (msg_user(msg) == LINK_PROTOCOL) {
- link_recv_proto_msg(l_ptr, buf);
- head = link_insert_deferred_queue(l_ptr, head);
- tipc_node_unlock(n_ptr);
- continue;
- }
-
- /* Traffic message. Conditionally activate link */
- link_state_event(l_ptr, TRAFFIC_MSG_EVT);
-
- if (link_working_working(l_ptr)) {
- /* Re-insert buffer in front of queue */
- buf->next = head;
- head = buf;
+ if (likely(link_working_working(l_ptr))) {
+ if (likely(seq_no == mod(l_ptr->next_in_no))) {
+ l_ptr->next_in_no++;
+ if (unlikely(l_ptr->oldest_deferred_in))
+ head = link_insert_deferred_queue(l_ptr,
+ head);
+deliver:
+ if (likely(msg_isdata(msg))) {
+ tipc_node_unlock(n_ptr);
+ tipc_port_recv_msg(buf);
+ continue;
+ }
+ switch (msg_user(msg)) {
+ int ret;
+ case MSG_BUNDLER:
+ l_ptr->stats.recv_bundles++;
+ l_ptr->stats.recv_bundled +=
+ msg_msgcnt(msg);
+ tipc_node_unlock(n_ptr);
+ tipc_link_recv_bundle(buf);
+ continue;
+ case NAME_DISTRIBUTOR:
+ n_ptr->bclink.recv_permitted = true;
+ tipc_node_unlock(n_ptr);
+ tipc_named_recv(buf);
+ continue;
+ case BCAST_PROTOCOL:
+ tipc_link_recv_sync(n_ptr, buf);
+ tipc_node_unlock(n_ptr);
+ continue;
+ case CONN_MANAGER:
+ tipc_node_unlock(n_ptr);
+ tipc_port_recv_proto_msg(buf);
+ continue;
+ case MSG_FRAGMENTER:
+ l_ptr->stats.recv_fragments++;
+ ret = tipc_link_recv_fragment(
+ &l_ptr->defragm_buf,
+ &buf, &msg);
+ if (ret == 1) {
+ l_ptr->stats.recv_fragmented++;
+ goto deliver;
+ }
+ if (ret == -1)
+ l_ptr->next_in_no--;
+ break;
+ case CHANGEOVER_PROTOCOL:
+ type = msg_type(msg);
+ if (link_recv_changeover_msg(&l_ptr,
+ &buf)) {
+ msg = buf_msg(buf);
+ seq_no = msg_seqno(msg);
+ if (type == ORIGINAL_MSG)
+ goto deliver;
+ goto protocol_check;
+ }
+ break;
+ default:
+ kfree_skb(buf);
+ buf = NULL;
+ break;
+ }
tipc_node_unlock(n_ptr);
+ tipc_net_route_msg(buf);
continue;
}
- goto unlock_discard;
- }
-
- /* Link is now in state WORKING_WORKING */
- if (unlikely(seq_no != mod(l_ptr->next_in_no))) {
link_handle_out_of_seq_msg(l_ptr, buf);
head = link_insert_deferred_queue(l_ptr, head);
tipc_node_unlock(n_ptr);
continue;
}
- l_ptr->next_in_no++;
- if (unlikely(l_ptr->oldest_deferred_in))
+
+ /* Link is not in state WORKING_WORKING */
+ if (msg_user(msg) == LINK_PROTOCOL) {
+ link_recv_proto_msg(l_ptr, buf);
head = link_insert_deferred_queue(l_ptr, head);
-deliver:
- if (likely(msg_isdata(msg))) {
tipc_node_unlock(n_ptr);
- tipc_port_recv_msg(buf);
continue;
}
- switch (msg_user(msg)) {
- int ret;
- case MSG_BUNDLER:
- l_ptr->stats.recv_bundles++;
- l_ptr->stats.recv_bundled += msg_msgcnt(msg);
- tipc_node_unlock(n_ptr);
- tipc_link_recv_bundle(buf);
- continue;
- case NAME_DISTRIBUTOR:
- n_ptr->bclink.recv_permitted = true;
- tipc_node_unlock(n_ptr);
- tipc_named_recv(buf);
- continue;
- case BCAST_PROTOCOL:
- tipc_link_recv_sync(n_ptr, buf);
- tipc_node_unlock(n_ptr);
- continue;
- case CONN_MANAGER:
- tipc_node_unlock(n_ptr);
- tipc_port_recv_proto_msg(buf);
- continue;
- case MSG_FRAGMENTER:
- l_ptr->stats.recv_fragments++;
- ret = tipc_link_recv_fragment(&l_ptr->reasm_head,
- &l_ptr->reasm_tail,
- &buf);
- if (ret == LINK_REASM_COMPLETE) {
- l_ptr->stats.recv_fragmented++;
- msg = buf_msg(buf);
- goto deliver;
- }
- if (ret == LINK_REASM_ERROR)
- tipc_link_reset(l_ptr);
+
+ /* Traffic message. Conditionally activate link */
+ link_state_event(l_ptr, TRAFFIC_MSG_EVT);
+
+ if (link_working_working(l_ptr)) {
+ /* Re-insert buffer in front of queue */
+ buf->next = head;
+ head = buf;
tipc_node_unlock(n_ptr);
continue;
- case CHANGEOVER_PROTOCOL:
- type = msg_type(msg);
- if (link_recv_changeover_msg(&l_ptr, &buf)) {
- msg = buf_msg(buf);
- seq_no = msg_seqno(msg);
- if (type == ORIGINAL_MSG)
- goto deliver;
- goto protocol_check;
- }
- break;
- default:
- kfree_skb(buf);
- buf = NULL;
- break;
}
tipc_node_unlock(n_ptr);
- tipc_net_route_msg(buf);
- continue;
-unlock_discard:
-
- tipc_node_unlock(n_ptr);
-discard:
+cont:
kfree_skb(buf);
}
read_unlock_bh(&tipc_net_lock);
@@ -2339,48 +2432,114 @@ static int link_send_long_buf(struct tipc_link *l_ptr, struct sk_buff *buf)
}
/*
+ * A pending message being re-assembled must store certain values
+ * to handle subsequent fragments correctly. The following functions
+ * help storing these values in unused, available fields in the
+ * pending message. This makes dynamic memory allocation unnecessary.
+ */
+static void set_long_msg_seqno(struct sk_buff *buf, u32 seqno)
+{
+ msg_set_seqno(buf_msg(buf), seqno);
+}
+
+static u32 get_fragm_size(struct sk_buff *buf)
+{
+ return msg_ack(buf_msg(buf));
+}
+
+static void set_fragm_size(struct sk_buff *buf, u32 sz)
+{
+ msg_set_ack(buf_msg(buf), sz);
+}
+
+static u32 get_expected_frags(struct sk_buff *buf)
+{
+ return msg_bcast_ack(buf_msg(buf));
+}
+
+static void set_expected_frags(struct sk_buff *buf, u32 exp)
+{
+ msg_set_bcast_ack(buf_msg(buf), exp);
+}
+
+/*
* tipc_link_recv_fragment(): Called with node lock on. Returns
* the reassembled buffer if message is complete.
*/
-int tipc_link_recv_fragment(struct sk_buff **head, struct sk_buff **tail,
- struct sk_buff **fbuf)
-{
- struct sk_buff *frag = *fbuf;
- struct tipc_msg *msg = buf_msg(frag);
- u32 fragid = msg_type(msg);
- bool headstolen;
- int delta;
-
- skb_pull(frag, msg_hdr_sz(msg));
- if (fragid == FIRST_FRAGMENT) {
- if (*head || skb_unclone(frag, GFP_ATOMIC))
- goto out_free;
- *head = frag;
- skb_frag_list_init(*head);
+int tipc_link_recv_fragment(struct sk_buff **pending, struct sk_buff **fb,
+ struct tipc_msg **m)
+{
+ struct sk_buff *prev = NULL;
+ struct sk_buff *fbuf = *fb;
+ struct tipc_msg *fragm = buf_msg(fbuf);
+ struct sk_buff *pbuf = *pending;
+ u32 long_msg_seq_no = msg_long_msgno(fragm);
+
+ *fb = NULL;
+
+ /* Is there an incomplete message waiting for this fragment? */
+ while (pbuf && ((buf_seqno(pbuf) != long_msg_seq_no) ||
+ (msg_orignode(fragm) != msg_orignode(buf_msg(pbuf))))) {
+ prev = pbuf;
+ pbuf = pbuf->next;
+ }
+
+ if (!pbuf && (msg_type(fragm) == FIRST_FRAGMENT)) {
+ struct tipc_msg *imsg = (struct tipc_msg *)msg_data(fragm);
+ u32 msg_sz = msg_size(imsg);
+ u32 fragm_sz = msg_data_sz(fragm);
+ u32 exp_fragm_cnt;
+ u32 max = TIPC_MAX_USER_MSG_SIZE + NAMED_H_SIZE;
+
+ if (msg_type(imsg) == TIPC_MCAST_MSG)
+ max = TIPC_MAX_USER_MSG_SIZE + MCAST_H_SIZE;
+ if (fragm_sz == 0 || msg_size(imsg) > max) {
+ kfree_skb(fbuf);
+ return 0;
+ }
+ exp_fragm_cnt = msg_sz / fragm_sz + !!(msg_sz % fragm_sz);
+ pbuf = tipc_buf_acquire(msg_size(imsg));
+ if (pbuf != NULL) {
+ pbuf->next = *pending;
+ *pending = pbuf;
+ skb_copy_to_linear_data(pbuf, imsg,
+ msg_data_sz(fragm));
+ /* Prepare buffer for subsequent fragments. */
+ set_long_msg_seqno(pbuf, long_msg_seq_no);
+ set_fragm_size(pbuf, fragm_sz);
+ set_expected_frags(pbuf, exp_fragm_cnt - 1);
+ } else {
+ pr_debug("Link unable to reassemble fragmented message\n");
+ kfree_skb(fbuf);
+ return -1;
+ }
+ kfree_skb(fbuf);
+ return 0;
+ } else if (pbuf && (msg_type(fragm) != FIRST_FRAGMENT)) {
+ u32 dsz = msg_data_sz(fragm);
+ u32 fsz = get_fragm_size(pbuf);
+ u32 crs = ((msg_fragm_no(fragm) - 1) * fsz);
+ u32 exp_frags = get_expected_frags(pbuf) - 1;
+ skb_copy_to_linear_data_offset(pbuf, crs,
+ msg_data(fragm), dsz);
+ kfree_skb(fbuf);
+
+ /* Is message complete? */
+ if (exp_frags == 0) {
+ if (prev)
+ prev->next = pbuf->next;
+ else
+ *pending = pbuf->next;
+ msg_reset_reroute_cnt(buf_msg(pbuf));
+ *fb = pbuf;
+ *m = buf_msg(pbuf);
+ return 1;
+ }
+ set_expected_frags(pbuf, exp_frags);
return 0;
- } else if (*head &&
- skb_try_coalesce(*head, frag, &headstolen, &delta)) {
- kfree_skb_partial(frag, headstolen);
- } else {
- if (!*head)
- goto out_free;
- if (!skb_has_frag_list(*head))
- skb_shinfo(*head)->frag_list = frag;
- else
- (*tail)->next = frag;
- *tail = frag;
- (*head)->truesize += frag->truesize;
- }
- if (fragid == LAST_FRAGMENT) {
- *fbuf = *head;
- *tail = *head = NULL;
- return LINK_REASM_COMPLETE;
}
+ kfree_skb(fbuf);
return 0;
-out_free:
- pr_warn_ratelimited("Link unable to reassemble fragmented message\n");
- kfree_skb(*fbuf);
- return LINK_REASM_ERROR;
}
static void link_set_supervision_props(struct tipc_link *l_ptr, u32 tolerance)
@@ -2426,21 +2585,25 @@ void tipc_link_set_queue_limits(struct tipc_link *l_ptr, u32 window)
static struct tipc_link *link_find_link(const char *name,
struct tipc_node **node)
{
+ struct tipc_link_name link_name_parts;
+ struct tipc_bearer *b_ptr;
struct tipc_link *l_ptr;
- struct tipc_node *n_ptr;
- int i;
- list_for_each_entry(n_ptr, &tipc_node_list, list) {
- for (i = 0; i < MAX_BEARERS; i++) {
- l_ptr = n_ptr->links[i];
- if (l_ptr && !strcmp(l_ptr->name, name))
- goto found;
- }
- }
- l_ptr = NULL;
- n_ptr = NULL;
-found:
- *node = n_ptr;
+ if (!link_name_validate(name, &link_name_parts))
+ return NULL;
+
+ b_ptr = tipc_bearer_find_interface(link_name_parts.if_local);
+ if (!b_ptr)
+ return NULL;
+
+ *node = tipc_node_find(link_name_parts.addr_peer);
+ if (!*node)
+ return NULL;
+
+ l_ptr = (*node)->links[b_ptr->identity];
+ if (!l_ptr || strcmp(l_ptr->name, name))
+ return NULL;
+
return l_ptr;
}
@@ -2483,7 +2646,6 @@ static int link_cmd_set_value(const char *name, u32 new_value, u16 cmd)
struct tipc_link *l_ptr;
struct tipc_bearer *b_ptr;
struct tipc_media *m_ptr;
- int res = 0;
l_ptr = link_find_link(name, &node);
if (l_ptr) {
@@ -2506,12 +2668,9 @@ static int link_cmd_set_value(const char *name, u32 new_value, u16 cmd)
case TIPC_CMD_SET_LINK_WINDOW:
tipc_link_set_queue_limits(l_ptr, new_value);
break;
- default:
- res = -EINVAL;
- break;
}
tipc_node_unlock(node);
- return res;
+ return 0;
}
b_ptr = tipc_bearer_find(name);
@@ -2519,18 +2678,15 @@ static int link_cmd_set_value(const char *name, u32 new_value, u16 cmd)
switch (cmd) {
case TIPC_CMD_SET_LINK_TOL:
b_ptr->tolerance = new_value;
- break;
+ return 0;
case TIPC_CMD_SET_LINK_PRI:
b_ptr->priority = new_value;
- break;
+ return 0;
case TIPC_CMD_SET_LINK_WINDOW:
b_ptr->window = new_value;
- break;
- default:
- res = -EINVAL;
- break;
+ return 0;
}
- return res;
+ return -EINVAL;
}
m_ptr = tipc_media_find(name);
@@ -2539,18 +2695,15 @@ static int link_cmd_set_value(const char *name, u32 new_value, u16 cmd)
switch (cmd) {
case TIPC_CMD_SET_LINK_TOL:
m_ptr->tolerance = new_value;
- break;
+ return 0;
case TIPC_CMD_SET_LINK_PRI:
m_ptr->priority = new_value;
- break;
+ return 0;
case TIPC_CMD_SET_LINK_WINDOW:
m_ptr->window = new_value;
- break;
- default:
- res = -EINVAL;
- break;
+ return 0;
}
- return res;
+ return -EINVAL;
}
struct sk_buff *tipc_link_cmd_config(const void *req_tlv_area, int req_tlv_space,