提交 ace0d5d8 编写于 作者: D David S. Miller

Merge branch 'tipc'

Jon Maloy says:

====================
Some small and relatively straightforward patches. With exception of
the two first ones they are all unrelated and address minor issues.

v2: update of v1 (http://patchwork.ozlabs.org/patch/277404/)

-added commit to use memcpy_fromiovec on user data as per v1 feedback
-updated sparse fix commit to drop chunks covered by above commit
-added new commit that greatly simplifies the link lookup routine
====================
Signed-off-by: NDavid S. Miller <davem@davemloft.net>
......@@ -387,7 +387,7 @@ int tipc_enable_bearer(const char *name, u32 disc_domain, u32 priority)
b_ptr = &tipc_bearers[bearer_id];
strcpy(b_ptr->name, name);
res = m_ptr->enable_bearer(b_ptr);
res = m_ptr->enable_media(b_ptr);
if (res) {
pr_warn("Bearer <%s> rejected, enable failure (%d)\n",
name, -res);
......@@ -420,23 +420,15 @@ int tipc_enable_bearer(const char *name, u32 disc_domain, u32 priority)
}
/**
* tipc_block_bearer - Block the bearer with the given name, and reset all its links
* tipc_block_bearer - Block the bearer, and reset all its links
*/
int tipc_block_bearer(const char *name)
int tipc_block_bearer(struct tipc_bearer *b_ptr)
{
struct tipc_bearer *b_ptr = NULL;
struct tipc_link *l_ptr;
struct tipc_link *temp_l_ptr;
read_lock_bh(&tipc_net_lock);
b_ptr = tipc_bearer_find(name);
if (!b_ptr) {
pr_warn("Attempt to block unknown bearer <%s>\n", name);
read_unlock_bh(&tipc_net_lock);
return -EINVAL;
}
pr_info("Blocking bearer <%s>\n", name);
pr_info("Blocking bearer <%s>\n", b_ptr->name);
spin_lock_bh(&b_ptr->lock);
b_ptr->blocked = 1;
list_for_each_entry_safe(l_ptr, temp_l_ptr, &b_ptr->links, link_list) {
......@@ -465,7 +457,7 @@ static void bearer_disable(struct tipc_bearer *b_ptr)
pr_info("Disabling bearer <%s>\n", b_ptr->name);
spin_lock_bh(&b_ptr->lock);
b_ptr->blocked = 1;
b_ptr->media->disable_bearer(b_ptr);
b_ptr->media->disable_media(b_ptr);
list_for_each_entry_safe(l_ptr, temp_l_ptr, &b_ptr->links, link_list) {
tipc_link_delete(l_ptr);
}
......
......@@ -75,8 +75,8 @@ struct tipc_bearer;
/**
* struct tipc_media - TIPC media information available to internal users
* @send_msg: routine which handles buffer transmission
* @enable_bearer: routine which enables a bearer
* @disable_bearer: routine which disables a bearer
* @enable_media: routine which enables a media
* @disable_media: routine which disables a media
* @addr2str: routine which converts media address to string
* @addr2msg: routine which converts media address to protocol message area
* @msg2addr: routine which converts media address from protocol message area
......@@ -91,8 +91,8 @@ struct tipc_media {
int (*send_msg)(struct sk_buff *buf,
struct tipc_bearer *b_ptr,
struct tipc_media_addr *dest);
int (*enable_bearer)(struct tipc_bearer *b_ptr);
void (*disable_bearer)(struct tipc_bearer *b_ptr);
int (*enable_media)(struct tipc_bearer *b_ptr);
void (*disable_media)(struct tipc_bearer *b_ptr);
int (*addr2str)(struct tipc_media_addr *a, char *str_buf, int str_size);
int (*addr2msg)(struct tipc_media_addr *a, char *msg_area);
int (*msg2addr)(const struct tipc_bearer *b_ptr,
......@@ -163,7 +163,7 @@ int tipc_register_media(struct tipc_media *m_ptr);
void tipc_recv_msg(struct sk_buff *buf, struct tipc_bearer *tb_ptr);
int tipc_block_bearer(const char *name);
int tipc_block_bearer(struct tipc_bearer *b_ptr);
void tipc_continue(struct tipc_bearer *tb_ptr);
int tipc_enable_bearer(const char *bearer_name, u32 disc_domain, u32 priority);
......
......@@ -2,7 +2,7 @@
* net/tipc/eth_media.c: Ethernet bearer support for TIPC
*
* Copyright (c) 2001-2007, Ericsson AB
* Copyright (c) 2005-2008, 2011, Wind River Systems
* Copyright (c) 2005-2008, 2011-2013, Wind River Systems
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
......@@ -37,19 +37,19 @@
#include "core.h"
#include "bearer.h"
#define MAX_ETH_BEARERS MAX_BEARERS
#define MAX_ETH_MEDIA MAX_BEARERS
#define ETH_ADDR_OFFSET 4 /* message header offset of MAC address */
/**
* struct eth_bearer - Ethernet bearer data structure
* struct eth_media - Ethernet bearer data structure
* @bearer: ptr to associated "generic" bearer structure
* @dev: ptr to associated Ethernet network device
* @tipc_packet_type: used in binding TIPC to Ethernet driver
* @setup: work item used when enabling bearer
* @cleanup: work item used when disabling bearer
*/
struct eth_bearer {
struct eth_media {
struct tipc_bearer *bearer;
struct net_device *dev;
struct packet_type tipc_packet_type;
......@@ -58,7 +58,7 @@ struct eth_bearer {
};
static struct tipc_media eth_media_info;
static struct eth_bearer eth_bearers[MAX_ETH_BEARERS];
static struct eth_media eth_media_array[MAX_ETH_MEDIA];
static int eth_started;
static int recv_notification(struct notifier_block *nb, unsigned long evt,
......@@ -100,7 +100,7 @@ static int send_msg(struct sk_buff *buf, struct tipc_bearer *tb_ptr,
if (!clone)
return 0;
dev = ((struct eth_bearer *)(tb_ptr->usr_handle))->dev;
dev = ((struct eth_media *)(tb_ptr->usr_handle))->dev;
delta = dev->hard_header_len - skb_headroom(buf);
if ((delta > 0) &&
......@@ -128,43 +128,43 @@ static int send_msg(struct sk_buff *buf, struct tipc_bearer *tb_ptr,
static int recv_msg(struct sk_buff *buf, struct net_device *dev,
struct packet_type *pt, struct net_device *orig_dev)
{
struct eth_bearer *eb_ptr = (struct eth_bearer *)pt->af_packet_priv;
struct eth_media *eb_ptr = (struct eth_media *)pt->af_packet_priv;
if (!net_eq(dev_net(dev), &init_net)) {
kfree_skb(buf);
return 0;
return NET_RX_DROP;
}
if (likely(eb_ptr->bearer)) {
if (likely(buf->pkt_type <= PACKET_BROADCAST)) {
buf->next = NULL;
tipc_recv_msg(buf, eb_ptr->bearer);
return 0;
return NET_RX_SUCCESS;
}
}
kfree_skb(buf);
return 0;
return NET_RX_DROP;
}
/**
* setup_bearer - setup association between Ethernet bearer and interface
* setup_media - setup association between Ethernet bearer and interface
*/
static void setup_bearer(struct work_struct *work)
static void setup_media(struct work_struct *work)
{
struct eth_bearer *eb_ptr =
container_of(work, struct eth_bearer, setup);
struct eth_media *eb_ptr =
container_of(work, struct eth_media, setup);
dev_add_pack(&eb_ptr->tipc_packet_type);
}
/**
* enable_bearer - attach TIPC bearer to an Ethernet interface
* enable_media - attach TIPC bearer to an Ethernet interface
*/
static int enable_bearer(struct tipc_bearer *tb_ptr)
static int enable_media(struct tipc_bearer *tb_ptr)
{
struct net_device *dev;
struct eth_bearer *eb_ptr = &eth_bearers[0];
struct eth_bearer *stop = &eth_bearers[MAX_ETH_BEARERS];
struct eth_media *eb_ptr = &eth_media_array[0];
struct eth_media *stop = &eth_media_array[MAX_ETH_MEDIA];
char *driver_name = strchr((const char *)tb_ptr->name, ':') + 1;
int pending_dev = 0;
......@@ -188,7 +188,7 @@ static int enable_bearer(struct tipc_bearer *tb_ptr)
eb_ptr->tipc_packet_type.func = recv_msg;
eb_ptr->tipc_packet_type.af_packet_priv = eb_ptr;
INIT_LIST_HEAD(&(eb_ptr->tipc_packet_type.list));
INIT_WORK(&eb_ptr->setup, setup_bearer);
INIT_WORK(&eb_ptr->setup, setup_media);
schedule_work(&eb_ptr->setup);
/* Associate TIPC bearer with Ethernet bearer */
......@@ -205,14 +205,14 @@ static int enable_bearer(struct tipc_bearer *tb_ptr)
}
/**
* cleanup_bearer - break association between Ethernet bearer and interface
* cleanup_media - break association between Ethernet bearer and interface
*
* This routine must be invoked from a work queue because it can sleep.
*/
static void cleanup_bearer(struct work_struct *work)
static void cleanup_media(struct work_struct *work)
{
struct eth_bearer *eb_ptr =
container_of(work, struct eth_bearer, cleanup);
struct eth_media *eb_ptr =
container_of(work, struct eth_media, cleanup);
dev_remove_pack(&eb_ptr->tipc_packet_type);
dev_put(eb_ptr->dev);
......@@ -220,18 +220,18 @@ static void cleanup_bearer(struct work_struct *work)
}
/**
* disable_bearer - detach TIPC bearer from an Ethernet interface
* disable_media - detach TIPC bearer from an Ethernet interface
*
* Mark Ethernet bearer as inactive so that incoming buffers are thrown away,
* then get worker thread to complete bearer cleanup. (Can't do cleanup
* here because cleanup code needs to sleep and caller holds spinlocks.)
*/
static void disable_bearer(struct tipc_bearer *tb_ptr)
static void disable_media(struct tipc_bearer *tb_ptr)
{
struct eth_bearer *eb_ptr = (struct eth_bearer *)tb_ptr->usr_handle;
struct eth_media *eb_ptr = (struct eth_media *)tb_ptr->usr_handle;
eb_ptr->bearer = NULL;
INIT_WORK(&eb_ptr->cleanup, cleanup_bearer);
INIT_WORK(&eb_ptr->cleanup, cleanup_media);
schedule_work(&eb_ptr->cleanup);
}
......@@ -245,8 +245,8 @@ static int recv_notification(struct notifier_block *nb, unsigned long evt,
void *ptr)
{
struct net_device *dev = netdev_notifier_info_to_dev(ptr);
struct eth_bearer *eb_ptr = &eth_bearers[0];
struct eth_bearer *stop = &eth_bearers[MAX_ETH_BEARERS];
struct eth_media *eb_ptr = &eth_media_array[0];
struct eth_media *stop = &eth_media_array[MAX_ETH_MEDIA];
if (!net_eq(dev_net(dev), &init_net))
return NOTIFY_DONE;
......@@ -265,17 +265,17 @@ static int recv_notification(struct notifier_block *nb, unsigned long evt,
if (netif_carrier_ok(dev))
tipc_continue(eb_ptr->bearer);
else
tipc_block_bearer(eb_ptr->bearer->name);
tipc_block_bearer(eb_ptr->bearer);
break;
case NETDEV_UP:
tipc_continue(eb_ptr->bearer);
break;
case NETDEV_DOWN:
tipc_block_bearer(eb_ptr->bearer->name);
tipc_block_bearer(eb_ptr->bearer);
break;
case NETDEV_CHANGEMTU:
case NETDEV_CHANGEADDR:
tipc_block_bearer(eb_ptr->bearer->name);
tipc_block_bearer(eb_ptr->bearer);
tipc_continue(eb_ptr->bearer);
break;
case NETDEV_UNREGISTER:
......@@ -327,8 +327,8 @@ static int eth_msg2addr(const struct tipc_bearer *tb_ptr,
*/
static struct tipc_media eth_media_info = {
.send_msg = send_msg,
.enable_bearer = enable_bearer,
.disable_bearer = disable_bearer,
.enable_media = enable_media,
.disable_media = disable_media,
.addr2str = eth_addr2str,
.addr2msg = eth_addr2msg,
.msg2addr = eth_msg2addr,
......
......@@ -42,17 +42,17 @@
#include "core.h"
#include "bearer.h"
#define MAX_IB_BEARERS MAX_BEARERS
#define MAX_IB_MEDIA MAX_BEARERS
/**
* struct ib_bearer - Infiniband bearer data structure
* struct ib_media - Infiniband media data structure
* @bearer: ptr to associated "generic" bearer structure
* @dev: ptr to associated Infiniband network device
* @tipc_packet_type: used in binding TIPC to Infiniband driver
* @cleanup: work item used when disabling bearer
*/
struct ib_bearer {
struct ib_media {
struct tipc_bearer *bearer;
struct net_device *dev;
struct packet_type tipc_packet_type;
......@@ -61,7 +61,7 @@ struct ib_bearer {
};
static struct tipc_media ib_media_info;
static struct ib_bearer ib_bearers[MAX_IB_BEARERS];
static struct ib_media ib_media_array[MAX_IB_MEDIA];
static int ib_started;
/**
......@@ -93,7 +93,7 @@ static int send_msg(struct sk_buff *buf, struct tipc_bearer *tb_ptr,
if (!clone)
return 0;
dev = ((struct ib_bearer *)(tb_ptr->usr_handle))->dev;
dev = ((struct ib_media *)(tb_ptr->usr_handle))->dev;
delta = dev->hard_header_len - skb_headroom(buf);
if ((delta > 0) &&
......@@ -121,43 +121,43 @@ static int send_msg(struct sk_buff *buf, struct tipc_bearer *tb_ptr,
static int recv_msg(struct sk_buff *buf, struct net_device *dev,
struct packet_type *pt, struct net_device *orig_dev)
{
struct ib_bearer *ib_ptr = (struct ib_bearer *)pt->af_packet_priv;
struct ib_media *ib_ptr = (struct ib_media *)pt->af_packet_priv;
if (!net_eq(dev_net(dev), &init_net)) {
kfree_skb(buf);
return 0;
return NET_RX_DROP;
}
if (likely(ib_ptr->bearer)) {
if (likely(buf->pkt_type <= PACKET_BROADCAST)) {
buf->next = NULL;
tipc_recv_msg(buf, ib_ptr->bearer);
return 0;
return NET_RX_SUCCESS;
}
}
kfree_skb(buf);
return 0;
return NET_RX_DROP;
}
/**
* setup_bearer - setup association between InfiniBand bearer and interface
*/
static void setup_bearer(struct work_struct *work)
static void setup_media(struct work_struct *work)
{
struct ib_bearer *ib_ptr =
container_of(work, struct ib_bearer, setup);
struct ib_media *ib_ptr =
container_of(work, struct ib_media, setup);
dev_add_pack(&ib_ptr->tipc_packet_type);
}
/**
* enable_bearer - attach TIPC bearer to an InfiniBand interface
* enable_media - attach TIPC bearer to an InfiniBand interface
*/
static int enable_bearer(struct tipc_bearer *tb_ptr)
static int enable_media(struct tipc_bearer *tb_ptr)
{
struct net_device *dev;
struct ib_bearer *ib_ptr = &ib_bearers[0];
struct ib_bearer *stop = &ib_bearers[MAX_IB_BEARERS];
struct ib_media *ib_ptr = &ib_media_array[0];
struct ib_media *stop = &ib_media_array[MAX_IB_MEDIA];
char *driver_name = strchr((const char *)tb_ptr->name, ':') + 1;
int pending_dev = 0;
......@@ -181,7 +181,7 @@ static int enable_bearer(struct tipc_bearer *tb_ptr)
ib_ptr->tipc_packet_type.func = recv_msg;
ib_ptr->tipc_packet_type.af_packet_priv = ib_ptr;
INIT_LIST_HEAD(&(ib_ptr->tipc_packet_type.list));
INIT_WORK(&ib_ptr->setup, setup_bearer);
INIT_WORK(&ib_ptr->setup, setup_media);
schedule_work(&ib_ptr->setup);
/* Associate TIPC bearer with InfiniBand bearer */
......@@ -204,8 +204,8 @@ static int enable_bearer(struct tipc_bearer *tb_ptr)
*/
static void cleanup_bearer(struct work_struct *work)
{
struct ib_bearer *ib_ptr =
container_of(work, struct ib_bearer, cleanup);
struct ib_media *ib_ptr =
container_of(work, struct ib_media, cleanup);
dev_remove_pack(&ib_ptr->tipc_packet_type);
dev_put(ib_ptr->dev);
......@@ -213,15 +213,15 @@ static void cleanup_bearer(struct work_struct *work)
}
/**
* disable_bearer - detach TIPC bearer from an InfiniBand interface
* disable_media - detach TIPC bearer from an InfiniBand interface
*
* Mark InfiniBand bearer as inactive so that incoming buffers are thrown away,
* then get worker thread to complete bearer cleanup. (Can't do cleanup
* here because cleanup code needs to sleep and caller holds spinlocks.)
*/
static void disable_bearer(struct tipc_bearer *tb_ptr)
static void disable_media(struct tipc_bearer *tb_ptr)
{
struct ib_bearer *ib_ptr = (struct ib_bearer *)tb_ptr->usr_handle;
struct ib_media *ib_ptr = (struct ib_media *)tb_ptr->usr_handle;
ib_ptr->bearer = NULL;
INIT_WORK(&ib_ptr->cleanup, cleanup_bearer);
......@@ -238,8 +238,8 @@ static int recv_notification(struct notifier_block *nb, unsigned long evt,
void *ptr)
{
struct net_device *dev = netdev_notifier_info_to_dev(ptr);
struct ib_bearer *ib_ptr = &ib_bearers[0];
struct ib_bearer *stop = &ib_bearers[MAX_IB_BEARERS];
struct ib_media *ib_ptr = &ib_media_array[0];
struct ib_media *stop = &ib_media_array[MAX_IB_MEDIA];
if (!net_eq(dev_net(dev), &init_net))
return NOTIFY_DONE;
......@@ -258,17 +258,17 @@ static int recv_notification(struct notifier_block *nb, unsigned long evt,
if (netif_carrier_ok(dev))
tipc_continue(ib_ptr->bearer);
else
tipc_block_bearer(ib_ptr->bearer->name);
tipc_block_bearer(ib_ptr->bearer);
break;
case NETDEV_UP:
tipc_continue(ib_ptr->bearer);
break;
case NETDEV_DOWN:
tipc_block_bearer(ib_ptr->bearer->name);
tipc_block_bearer(ib_ptr->bearer);
break;
case NETDEV_CHANGEMTU:
case NETDEV_CHANGEADDR:
tipc_block_bearer(ib_ptr->bearer->name);
tipc_block_bearer(ib_ptr->bearer);
tipc_continue(ib_ptr->bearer);
break;
case NETDEV_UNREGISTER:
......@@ -323,8 +323,8 @@ static int ib_msg2addr(const struct tipc_bearer *tb_ptr,
*/
static struct tipc_media ib_media_info = {
.send_msg = send_msg,
.enable_bearer = enable_bearer,
.disable_bearer = disable_bearer,
.enable_media = enable_media,
.disable_media = disable_media,
.addr2str = ib_addr2str,
.addr2msg = ib_addr2msg,
.msg2addr = ib_msg2addr,
......
......@@ -75,20 +75,6 @@ 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);
......@@ -97,8 +83,7 @@ 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,
u32 num_sect, unsigned int total_len,
u32 destnode);
unsigned int 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);
......@@ -160,72 +145,6 @@ int tipc_link_is_active(struct tipc_link *l_ptr)
(l_ptr->owner->active_links[1] == 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
......@@ -1065,8 +984,7 @@ 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,
const u32 num_sect, unsigned int total_len,
u32 destaddr)
unsigned int len, u32 destaddr)
{
struct tipc_msg *hdr = &sender->phdr;
struct tipc_link *l_ptr;
......@@ -1080,8 +998,7 @@ int tipc_link_send_sections_fast(struct tipc_port *sender,
* Try building message using port's max_pkt hint.
* (Must not hold any locks while building message.)
*/
res = tipc_msg_build(hdr, msg_sect, num_sect, total_len,
sender->max_pkt, &buf);
res = tipc_msg_build(hdr, msg_sect, len, sender->max_pkt, &buf);
/* Exit if build request was invalid */
if (unlikely(res < 0))
return res;
......@@ -1121,8 +1038,7 @@ int tipc_link_send_sections_fast(struct tipc_port *sender,
if ((msg_hdr_sz(hdr) + res) <= sender->max_pkt)
goto again;
return link_send_sections_long(sender, msg_sect,
num_sect, total_len,
return link_send_sections_long(sender, msg_sect, len,
destaddr);
}
tipc_node_unlock(node);
......@@ -1133,8 +1049,8 @@ int tipc_link_send_sections_fast(struct tipc_port *sender,
if (buf)
return tipc_reject_msg(buf, TIPC_ERR_NO_NODE);
if (res >= 0)
return tipc_port_reject_sections(sender, hdr, msg_sect, num_sect,
total_len, TIPC_ERR_NO_NODE);
return tipc_port_reject_sections(sender, hdr, msg_sect,
len, TIPC_ERR_NO_NODE);
return res;
}
......@@ -1154,18 +1070,17 @@ int tipc_link_send_sections_fast(struct tipc_port *sender,
*/
static int link_send_sections_long(struct tipc_port *sender,
struct iovec const *msg_sect,
u32 num_sect, unsigned int total_len,
u32 destaddr)
unsigned int len, u32 destaddr)
{
struct tipc_link *l_ptr;
struct tipc_node *node;
struct tipc_msg *hdr = &sender->phdr;
u32 dsz = total_len;
u32 dsz = 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 *sect_crs;
const unchar __user *sect_crs;
int curr_sect;
u32 fragm_no;
int res = 0;
......@@ -1207,7 +1122,7 @@ static int link_send_sections_long(struct tipc_port *sender,
if (!sect_rest) {
sect_rest = msg_sect[++curr_sect].iov_len;
sect_crs = (const unchar *)msg_sect[curr_sect].iov_base;
sect_crs = msg_sect[curr_sect].iov_base;
}
if (sect_rest < fragm_rest)
......@@ -1283,8 +1198,8 @@ static int link_send_sections_long(struct tipc_port *sender,
buf = buf_chain->next;
kfree_skb(buf_chain);
}
return tipc_port_reject_sections(sender, hdr, msg_sect, num_sect,
total_len, TIPC_ERR_NO_NODE);
return tipc_port_reject_sections(sender, hdr, msg_sect,
len, TIPC_ERR_NO_NODE);
}
/* Append chain of fragments to send queue & send them */
......@@ -2585,25 +2500,21 @@ 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;
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;
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;
return l_ptr;
}
......@@ -2646,6 +2557,7 @@ 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) {
......@@ -2668,9 +2580,12 @@ 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 0;
return res;
}
b_ptr = tipc_bearer_find(name);
......@@ -2678,15 +2593,18 @@ 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;
return 0;
break;
case TIPC_CMD_SET_LINK_PRI:
b_ptr->priority = new_value;
return 0;
break;
case TIPC_CMD_SET_LINK_WINDOW:
b_ptr->window = new_value;
return 0;
break;
default:
res = -EINVAL;
break;
}
return -EINVAL;
return res;
}
m_ptr = tipc_media_find(name);
......@@ -2695,15 +2613,18 @@ 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;
return 0;
break;
case TIPC_CMD_SET_LINK_PRI:
m_ptr->priority = new_value;
return 0;
break;
case TIPC_CMD_SET_LINK_WINDOW:
m_ptr->window = new_value;
return 0;
break;
default:
res = -EINVAL;
break;
}
return -EINVAL;
return res;
}
struct sk_buff *tipc_link_cmd_config(const void *req_tlv_area, int req_tlv_space,
......
......@@ -227,9 +227,7 @@ int tipc_link_send_buf(struct tipc_link *l_ptr, struct sk_buff *buf);
u32 tipc_link_get_max_pkt(u32 dest, u32 selector);
int tipc_link_send_sections_fast(struct tipc_port *sender,
struct iovec const *msg_sect,
const u32 num_sect,
unsigned int total_len,
u32 destnode);
unsigned int len, u32 destnode);
void tipc_link_recv_bundle(struct sk_buff *buf);
int tipc_link_recv_fragment(struct sk_buff **pending,
struct sk_buff **fb,
......
......@@ -73,13 +73,13 @@ void tipc_msg_init(struct tipc_msg *m, u32 user, u32 type, u32 hsize,
* Returns message data size or errno
*/
int tipc_msg_build(struct tipc_msg *hdr, struct iovec const *msg_sect,
u32 num_sect, unsigned int total_len, int max_size,
struct sk_buff **buf)
unsigned int len, int max_size, struct sk_buff **buf)
{
int dsz, sz, hsz, pos, res, cnt;
int dsz, sz, hsz;
unsigned char *to;
dsz = total_len;
pos = hsz = msg_hdr_sz(hdr);
dsz = len;
hsz = msg_hdr_sz(hdr);
sz = hsz + dsz;
msg_set_size(hdr, sz);
if (unlikely(sz > max_size)) {
......@@ -91,16 +91,11 @@ int tipc_msg_build(struct tipc_msg *hdr, struct iovec const *msg_sect,
if (!(*buf))
return -ENOMEM;
skb_copy_to_linear_data(*buf, hdr, hsz);
for (res = 1, cnt = 0; res && (cnt < num_sect); cnt++) {
skb_copy_to_linear_data_offset(*buf, pos,
msg_sect[cnt].iov_base,
msg_sect[cnt].iov_len);
pos += msg_sect[cnt].iov_len;
to = (*buf)->data + hsz;
if (len && memcpy_fromiovecend(to, msg_sect, 0, dsz)) {
kfree_skb(*buf);
*buf = NULL;
return -EFAULT;
}
if (likely(res))
return dsz;
kfree_skb(*buf);
*buf = NULL;
return -EFAULT;
return dsz;
}
......@@ -722,6 +722,5 @@ u32 tipc_msg_tot_importance(struct tipc_msg *m);
void tipc_msg_init(struct tipc_msg *m, u32 user, u32 type, u32 hsize,
u32 destnode);
int tipc_msg_build(struct tipc_msg *hdr, struct iovec const *msg_sect,
u32 num_sect, unsigned int total_len, int max_size,
struct sk_buff **buf);
unsigned int len, int max_size, struct sk_buff **buf);
#endif
......@@ -90,8 +90,7 @@ int tipc_port_peer_msg(struct tipc_port *p_ptr, struct tipc_msg *msg)
* tipc_multicast - send a multicast message to local and remote destinations
*/
int tipc_multicast(u32 ref, struct tipc_name_seq const *seq,
u32 num_sect, struct iovec const *msg_sect,
unsigned int total_len)
struct iovec const *msg_sect, unsigned int len)
{
struct tipc_msg *hdr;
struct sk_buff *buf;
......@@ -114,8 +113,7 @@ int tipc_multicast(u32 ref, struct tipc_name_seq const *seq,
msg_set_namelower(hdr, seq->lower);
msg_set_nameupper(hdr, seq->upper);
msg_set_hdr_sz(hdr, MCAST_H_SIZE);
res = tipc_msg_build(hdr, msg_sect, num_sect, total_len, MAX_MSG_SIZE,
&buf);
res = tipc_msg_build(hdr, msg_sect, len, MAX_MSG_SIZE, &buf);
if (unlikely(!buf))
return res;
......@@ -436,14 +434,13 @@ int tipc_reject_msg(struct sk_buff *buf, u32 err)
}
int tipc_port_reject_sections(struct tipc_port *p_ptr, struct tipc_msg *hdr,
struct iovec const *msg_sect, u32 num_sect,
unsigned int total_len, int err)
struct iovec const *msg_sect, unsigned int len,
int err)
{
struct sk_buff *buf;
int res;
res = tipc_msg_build(hdr, msg_sect, num_sect, total_len, MAX_MSG_SIZE,
&buf);
res = tipc_msg_build(hdr, msg_sect, len, MAX_MSG_SIZE, &buf);
if (!buf)
return res;
......@@ -918,15 +915,14 @@ int tipc_port_recv_msg(struct sk_buff *buf)
* tipc_port_recv_sections(): Concatenate and deliver sectioned
* message for this node.
*/
static int tipc_port_recv_sections(struct tipc_port *sender, unsigned int num_sect,
static int tipc_port_recv_sections(struct tipc_port *sender,
struct iovec const *msg_sect,
unsigned int total_len)
unsigned int len)
{
struct sk_buff *buf;
int res;
res = tipc_msg_build(&sender->phdr, msg_sect, num_sect, total_len,
MAX_MSG_SIZE, &buf);
res = tipc_msg_build(&sender->phdr, msg_sect, len, MAX_MSG_SIZE, &buf);
if (likely(buf))
tipc_port_recv_msg(buf);
return res;
......@@ -935,8 +931,7 @@ static int tipc_port_recv_sections(struct tipc_port *sender, unsigned int num_se
/**
* tipc_send - send message sections on connection
*/
int tipc_send(u32 ref, unsigned int num_sect, struct iovec const *msg_sect,
unsigned int total_len)
int tipc_send(u32 ref, struct iovec const *msg_sect, unsigned int len)
{
struct tipc_port *p_ptr;
u32 destnode;
......@@ -950,11 +945,10 @@ int tipc_send(u32 ref, unsigned int num_sect, struct iovec const *msg_sect,
if (!tipc_port_congested(p_ptr)) {
destnode = port_peernode(p_ptr);
if (likely(!in_own_node(destnode)))
res = tipc_link_send_sections_fast(p_ptr, msg_sect, num_sect,
total_len, destnode);
res = tipc_link_send_sections_fast(p_ptr, msg_sect,
len, destnode);
else
res = tipc_port_recv_sections(p_ptr, num_sect, msg_sect,
total_len);
res = tipc_port_recv_sections(p_ptr, msg_sect, len);
if (likely(res != -ELINKCONG)) {
p_ptr->congested = 0;
......@@ -965,7 +959,7 @@ int tipc_send(u32 ref, unsigned int num_sect, struct iovec const *msg_sect,
}
if (port_unreliable(p_ptr)) {
p_ptr->congested = 0;
return total_len;
return len;
}
return -ELINKCONG;
}
......@@ -974,8 +968,7 @@ int tipc_send(u32 ref, unsigned int num_sect, struct iovec const *msg_sect,
* tipc_send2name - send message sections to port name
*/
int tipc_send2name(u32 ref, struct tipc_name const *name, unsigned int domain,
unsigned int num_sect, struct iovec const *msg_sect,
unsigned int total_len)
struct iovec const *msg_sect, unsigned int len)
{
struct tipc_port *p_ptr;
struct tipc_msg *msg;
......@@ -999,36 +992,32 @@ int tipc_send2name(u32 ref, struct tipc_name const *name, unsigned int domain,
if (likely(destport || destnode)) {
if (likely(in_own_node(destnode)))
res = tipc_port_recv_sections(p_ptr, num_sect,
msg_sect, total_len);
res = tipc_port_recv_sections(p_ptr, msg_sect, len);
else if (tipc_own_addr)
res = tipc_link_send_sections_fast(p_ptr, msg_sect,
num_sect, total_len,
destnode);
len, destnode);
else
res = tipc_port_reject_sections(p_ptr, msg, msg_sect,
num_sect, total_len,
TIPC_ERR_NO_NODE);
len, TIPC_ERR_NO_NODE);
if (likely(res != -ELINKCONG)) {
if (res > 0)
p_ptr->sent++;
return res;
}
if (port_unreliable(p_ptr)) {
return total_len;
return len;
}
return -ELINKCONG;
}
return tipc_port_reject_sections(p_ptr, msg, msg_sect, num_sect,
total_len, TIPC_ERR_NO_NAME);
return tipc_port_reject_sections(p_ptr, msg, msg_sect, len,
TIPC_ERR_NO_NAME);
}
/**
* tipc_send2port - send message sections to port identity
*/
int tipc_send2port(u32 ref, struct tipc_portid const *dest,
unsigned int num_sect, struct iovec const *msg_sect,
unsigned int total_len)
struct iovec const *msg_sect, unsigned int len)
{
struct tipc_port *p_ptr;
struct tipc_msg *msg;
......@@ -1046,21 +1035,20 @@ int tipc_send2port(u32 ref, struct tipc_portid const *dest,
msg_set_hdr_sz(msg, BASIC_H_SIZE);
if (in_own_node(dest->node))
res = tipc_port_recv_sections(p_ptr, num_sect, msg_sect,
total_len);
res = tipc_port_recv_sections(p_ptr, msg_sect, len);
else if (tipc_own_addr)
res = tipc_link_send_sections_fast(p_ptr, msg_sect, num_sect,
total_len, dest->node);
res = tipc_link_send_sections_fast(p_ptr, msg_sect, len,
dest->node);
else
res = tipc_port_reject_sections(p_ptr, msg, msg_sect, num_sect,
total_len, TIPC_ERR_NO_NODE);
res = tipc_port_reject_sections(p_ptr, msg, msg_sect, len,
TIPC_ERR_NO_NODE);
if (likely(res != -ELINKCONG)) {
if (res > 0)
p_ptr->sent++;
return res;
}
if (port_unreliable(p_ptr)) {
return total_len;
return len;
}
return -ELINKCONG;
}
......@@ -151,24 +151,20 @@ int tipc_port_peer_msg(struct tipc_port *p_ptr, struct tipc_msg *msg);
* TIPC messaging routines
*/
int tipc_port_recv_msg(struct sk_buff *buf);
int tipc_send(u32 portref, unsigned int num_sect, struct iovec const *msg_sect,
unsigned int total_len);
int tipc_send(u32 portref, struct iovec const *msg_sect, unsigned int len);
int tipc_send2name(u32 portref, struct tipc_name const *name, u32 domain,
unsigned int num_sect, struct iovec const *msg_sect,
unsigned int total_len);
struct iovec const *msg_sect, unsigned int len);
int tipc_send2port(u32 portref, struct tipc_portid const *dest,
unsigned int num_sect, struct iovec const *msg_sect,
unsigned int total_len);
struct iovec const *msg_sect, unsigned int len);
int tipc_multicast(u32 portref, struct tipc_name_seq const *seq,
unsigned int section_count, struct iovec const *msg,
unsigned int total_len);
struct iovec const *msg, unsigned int len);
int tipc_port_reject_sections(struct tipc_port *p_ptr, struct tipc_msg *hdr,
struct iovec const *msg_sect, u32 num_sect,
unsigned int total_len, int err);
struct iovec const *msg_sect, unsigned int len,
int err);
struct sk_buff *tipc_port_get_ports(void);
void tipc_port_recv_proto_msg(struct sk_buff *buf);
void tipc_port_recv_mcast(struct sk_buff *buf, struct tipc_port_list *dp);
......
......@@ -338,7 +338,7 @@ static int release(struct socket *sock)
buf = __skb_dequeue(&sk->sk_receive_queue);
if (buf == NULL)
break;
if (TIPC_SKB_CB(buf)->handle != 0)
if (TIPC_SKB_CB(buf)->handle != NULL)
kfree_skb(buf);
else {
if ((sock->state == SS_CONNECTING) ||
......@@ -622,13 +622,11 @@ static int send_msg(struct kiocb *iocb, struct socket *sock,
res = tipc_send2name(tport->ref,
&dest->addr.name.name,
dest->addr.name.domain,
m->msg_iovlen,
m->msg_iov,
total_len);
} else if (dest->addrtype == TIPC_ADDR_ID) {
res = tipc_send2port(tport->ref,
&dest->addr.id,
m->msg_iovlen,
m->msg_iov,
total_len);
} else if (dest->addrtype == TIPC_ADDR_MCAST) {
......@@ -641,7 +639,6 @@ static int send_msg(struct kiocb *iocb, struct socket *sock,
break;
res = tipc_multicast(tport->ref,
&dest->addr.nameseq,
m->msg_iovlen,
m->msg_iov,
total_len);
}
......@@ -707,8 +704,7 @@ static int send_packet(struct kiocb *iocb, struct socket *sock,
break;
}
res = tipc_send(tport->ref, m->msg_iovlen, m->msg_iov,
total_len);
res = tipc_send(tport->ref, m->msg_iov, total_len);
if (likely(res != -ELINKCONG))
break;
if (timeout_val <= 0L) {
......@@ -1368,7 +1364,7 @@ static u32 filter_rcv(struct sock *sk, struct sk_buff *buf)
return TIPC_ERR_OVERLOAD;
/* Enqueue message */
TIPC_SKB_CB(buf)->handle = 0;
TIPC_SKB_CB(buf)->handle = NULL;
__skb_queue_tail(&sk->sk_receive_queue, buf);
skb_set_owner_r(buf, sk);
......@@ -1691,7 +1687,7 @@ static int shutdown(struct socket *sock, int how)
/* Disconnect and send a 'FIN+' or 'FIN-' message to peer */
buf = __skb_dequeue(&sk->sk_receive_queue);
if (buf) {
if (TIPC_SKB_CB(buf)->handle != 0) {
if (TIPC_SKB_CB(buf)->handle != NULL) {
kfree_skb(buf);
goto restart;
}
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册