summaryrefslogtreecommitdiffstats
path: root/net
diff options
context:
space:
mode:
Diffstat (limited to 'net')
-rw-r--r--net/8021q/vlan.c4
-rw-r--r--net/8021q/vlan_dev.c3
-rw-r--r--net/atm/mpc.c7
-rw-r--r--net/ax25/ax25_in.c2
-rw-r--r--net/ax25/ax25_subr.c2
-rw-r--r--net/bluetooth/hci_conn.c10
-rw-r--r--net/bluetooth/hci_sysfs.c1
-rw-r--r--net/bridge/br.c4
-rw-r--r--net/bridge/br_device.c3
-rw-r--r--net/bridge/br_fdb.c2
-rw-r--r--net/bridge/br_input.c7
-rw-r--r--net/bridge/netfilter/ebt_among.c2
-rw-r--r--net/bridge/netfilter/ebtable_broute.c4
-rw-r--r--net/compat.c2
-rw-r--r--net/core/dev.c16
-rw-r--r--net/core/pktgen.c2
-rw-r--r--net/core/scm.c2
-rw-r--r--net/core/skbuff.c42
-rw-r--r--net/dccp/ackvec.h2
-rw-r--r--net/dccp/ccids/ccid3.c2
-rw-r--r--net/dccp/ccids/lib/loss_interval.c2
-rw-r--r--net/decnet/dn_dev.c4
-rw-r--r--net/ieee80211/ieee80211_crypt_ccmp.c2
-rw-r--r--net/ieee80211/ieee80211_crypt_tkip.c4
-rw-r--r--net/ieee80211/ieee80211_tx.c3
-rw-r--r--net/ipv4/arp.c25
-rw-r--r--net/ipv4/devinet.c5
-rw-r--r--net/ipv4/esp4.c5
-rw-r--r--net/ipv4/fib_frontend.c9
-rw-r--r--net/ipv4/inet_diag.c69
-rw-r--r--net/ipv4/inet_lro.c19
-rw-r--r--net/ipv4/ip_gre.c2
-rw-r--r--net/ipv4/ipconfig.c47
-rw-r--r--net/ipv4/ipvs/ip_vs_core.c2
-rw-r--r--net/ipv4/ipvs/ip_vs_ctl.c24
-rw-r--r--net/ipv4/ipvs/ip_vs_lblc.c9
-rw-r--r--net/ipv4/ipvs/ip_vs_lblcr.c9
-rw-r--r--net/ipv4/ipvs/ip_vs_proto.c2
-rw-r--r--net/ipv4/ipvs/ip_vs_sched.c27
-rw-r--r--net/ipv4/netfilter/ip_tables.c57
-rw-r--r--net/ipv4/netfilter/iptable_raw.c2
-rw-r--r--net/ipv4/netfilter/nf_conntrack_l3proto_ipv4.c3
-rw-r--r--net/ipv4/netfilter/nf_nat_core.c5
-rw-r--r--net/ipv4/netfilter/nf_nat_sip.c2
-rw-r--r--net/ipv4/raw.c4
-rw-r--r--net/ipv4/route.c21
-rw-r--r--net/ipv4/sysctl_net_ipv4.c2
-rw-r--r--net/ipv4/tcp_illinois.c2
-rw-r--r--net/ipv4/tcp_input.c38
-rw-r--r--net/ipv4/tcp_ipv4.c11
-rw-r--r--net/ipv4/tcp_output.c24
-rw-r--r--net/ipv6/addrconf.c13
-rw-r--r--net/ipv6/datagram.c6
-rw-r--r--net/ipv6/esp6.c6
-rw-r--r--net/ipv6/ip6_output.c2
-rw-r--r--net/ipv6/ipv6_sockglue.c12
-rw-r--r--net/ipv6/ndisc.c2
-rw-r--r--net/ipv6/tcp_ipv6.c11
-rw-r--r--net/ipv6/xfrm6_policy.c2
-rw-r--r--net/irda/af_irda.c2
-rw-r--r--net/irda/ircomm/ircomm_param.c2
-rw-r--r--net/irda/ircomm/ircomm_tty.c2
-rw-r--r--net/irda/iriap.c2
-rw-r--r--net/irda/irlan/irlan_eth.c4
-rw-r--r--net/irda/irlap_frame.c2
-rw-r--r--net/irda/irlmp.c1
-rw-r--r--net/irda/parameters.c18
-rw-r--r--net/irda/wrapper.c2
-rw-r--r--net/iucv/iucv.c107
-rw-r--r--net/key/af_key.c18
-rw-r--r--net/mac80211/ieee80211.c38
-rw-r--r--net/mac80211/ieee80211_ioctl.c6
-rw-r--r--net/mac80211/ieee80211_rate.c3
-rw-r--r--net/mac80211/ieee80211_sta.c10
-rw-r--r--net/mac80211/rx.c15
-rw-r--r--net/mac80211/sta_info.c7
-rw-r--r--net/mac80211/wep.c3
-rw-r--r--net/netfilter/nf_conntrack_core.c5
-rw-r--r--net/netfilter/nf_conntrack_netlink.c4
-rw-r--r--net/netfilter/nf_conntrack_sip.c4
-rw-r--r--net/netfilter/x_tables.c8
-rw-r--r--net/netfilter/xt_CONNMARK.c10
-rw-r--r--net/netfilter/xt_CONNSECMARK.c10
-rw-r--r--net/netfilter/xt_TCPMSS.c4
-rw-r--r--net/netfilter/xt_hashlimit.c2
-rw-r--r--net/netlabel/netlabel_mgmt.c2
-rw-r--r--net/netrom/nr_dev.c2
-rw-r--r--net/rfkill/rfkill.c14
-rw-r--r--net/rose/rose_dev.c2
-rw-r--r--net/rxrpc/Kconfig1
-rw-r--r--net/rxrpc/rxkad.c1
-rw-r--r--net/sched/sch_hfsc.c2
-rw-r--r--net/sctp/Kconfig6
-rw-r--r--net/sctp/auth.c4
-rw-r--r--net/sctp/bind_addr.c26
-rw-r--r--net/sctp/sm_make_chunk.c33
-rw-r--r--net/sctp/sm_statefuns.c26
-rw-r--r--net/sctp/socket.c18
-rw-r--r--net/sctp/ulpevent.c2
-rw-r--r--net/sctp/ulpqueue.c33
-rw-r--r--net/sunrpc/auth_gss/auth_gss.c6
-rw-r--r--net/sunrpc/auth_gss/gss_krb5_mech.c8
-rw-r--r--net/sunrpc/auth_gss/gss_krb5_seal.c1
-rw-r--r--net/sunrpc/rpc_pipe.c2
-rw-r--r--net/sunrpc/xprt.c2
-rw-r--r--net/sunrpc/xprtrdma/rpc_rdma.c9
-rw-r--r--net/sunrpc/xprtrdma/transport.c10
-rw-r--r--net/sunrpc/xprtsock.c4
-rw-r--r--net/tipc/socket.c2
-rw-r--r--net/unix/af_unix.c9
-rw-r--r--net/wireless/wext.c2
-rw-r--r--net/x25/x25_forward.c5
-rw-r--r--net/xfrm/xfrm_policy.c14
-rw-r--r--net/xfrm/xfrm_state.c18
-rw-r--r--net/xfrm/xfrm_user.c19
115 files changed, 636 insertions, 549 deletions
diff --git a/net/8021q/vlan.c b/net/8021q/vlan.c
index 6567213959c..4add9bd4bc8 100644
--- a/net/8021q/vlan.c
+++ b/net/8021q/vlan.c
@@ -124,8 +124,8 @@ static void __exit vlan_cleanup_module(void)
{
int i;
- vlan_netlink_fini();
vlan_ioctl_set(NULL);
+ vlan_netlink_fini();
/* Un-register us from receiving netdevice events */
unregister_netdevice_notifier(&vlan_notifier_block);
@@ -776,7 +776,7 @@ static int vlan_ioctl_handler(struct net *net, void __user *arg)
case SET_VLAN_NAME_TYPE_CMD:
err = -EPERM;
if (!capable(CAP_NET_ADMIN))
- return -EPERM;
+ break;
if ((args.u.name_type >= 0) &&
(args.u.name_type < VLAN_NAME_TYPE_HIGHEST)) {
vlan_name_type = args.u.name_type;
diff --git a/net/8021q/vlan_dev.c b/net/8021q/vlan_dev.c
index 7a36878241d..4f99bb86af5 100644
--- a/net/8021q/vlan_dev.c
+++ b/net/8021q/vlan_dev.c
@@ -462,7 +462,8 @@ int vlan_dev_hard_start_xmit(struct sk_buff *skb, struct net_device *dev)
* OTHER THINGS LIKE FDDI/TokenRing/802.3 SNAPs...
*/
- if (veth->h_vlan_proto != htons(ETH_P_8021Q)) {
+ if (veth->h_vlan_proto != htons(ETH_P_8021Q) ||
+ VLAN_DEV_INFO(dev)->flags & VLAN_FLAG_REORDER_HDR) {
int orig_headroom = skb_headroom(skb);
unsigned short veth_TCI;
diff --git a/net/atm/mpc.c b/net/atm/mpc.c
index 2086396de17..9c7f712fc7e 100644
--- a/net/atm/mpc.c
+++ b/net/atm/mpc.c
@@ -542,6 +542,13 @@ static int mpc_send_packet(struct sk_buff *skb, struct net_device *dev)
if (eth->h_proto != htons(ETH_P_IP))
goto non_ip; /* Multi-Protocol Over ATM :-) */
+ /* Weed out funny packets (e.g., AF_PACKET or raw). */
+ if (skb->len < ETH_HLEN + sizeof(struct iphdr))
+ goto non_ip;
+ skb_set_network_header(skb, ETH_HLEN);
+ if (skb->len < ETH_HLEN + ip_hdr(skb)->ihl * 4 || ip_hdr(skb)->ihl < 5)
+ goto non_ip;
+
while (i < mpc->number_of_mps_macs) {
if (!compare_ether_addr(eth->h_dest, (mpc->mps_macs + i*ETH_ALEN)))
if ( send_via_shortcut(skb, mpc) == 0 ) /* try shortcut */
diff --git a/net/ax25/ax25_in.c b/net/ax25/ax25_in.c
index 3b7d1720c2e..d1be080dcb2 100644
--- a/net/ax25/ax25_in.c
+++ b/net/ax25/ax25_in.c
@@ -124,7 +124,7 @@ int ax25_rx_iframe(ax25_cb *ax25, struct sk_buff *skb)
}
skb_pull(skb, 1); /* Remove PID */
- skb_reset_mac_header(skb);
+ skb->mac_header = skb->network_header;
skb_reset_network_header(skb);
skb->dev = ax25->ax25_dev->dev;
skb->pkt_type = PACKET_HOST;
diff --git a/net/ax25/ax25_subr.c b/net/ax25/ax25_subr.c
index 5fe9b2a6697..d8f21573317 100644
--- a/net/ax25/ax25_subr.c
+++ b/net/ax25/ax25_subr.c
@@ -279,6 +279,7 @@ void ax25_disconnect(ax25_cb *ax25, int reason)
ax25_link_failed(ax25, reason);
if (ax25->sk != NULL) {
+ local_bh_disable();
bh_lock_sock(ax25->sk);
ax25->sk->sk_state = TCP_CLOSE;
ax25->sk->sk_err = reason;
@@ -288,5 +289,6 @@ void ax25_disconnect(ax25_cb *ax25, int reason)
sock_set_flag(ax25->sk, SOCK_DEAD);
}
bh_unlock_sock(ax25->sk);
+ local_bh_enable();
}
}
diff --git a/net/bluetooth/hci_conn.c b/net/bluetooth/hci_conn.c
index 9483320f6da..34d1a3c822b 100644
--- a/net/bluetooth/hci_conn.c
+++ b/net/bluetooth/hci_conn.c
@@ -259,22 +259,14 @@ int hci_conn_del(struct hci_conn *conn)
}
tasklet_disable(&hdev->tx_task);
-
- hci_conn_del_sysfs(conn);
-
hci_conn_hash_del(hdev, conn);
if (hdev->notify)
hdev->notify(hdev, HCI_NOTIFY_CONN_DEL);
-
tasklet_enable(&hdev->tx_task);
-
skb_queue_purge(&conn->data_q);
-
+ hci_conn_del_sysfs(conn);
hci_dev_put(hdev);
- /* will free via device release */
- put_device(&conn->dev);
-
return 0;
}
diff --git a/net/bluetooth/hci_sysfs.c b/net/bluetooth/hci_sysfs.c
index cef1e3e1881..cad510309dc 100644
--- a/net/bluetooth/hci_sysfs.c
+++ b/net/bluetooth/hci_sysfs.c
@@ -320,6 +320,7 @@ static void del_conn(struct work_struct *work)
{
struct hci_conn *conn = container_of(work, struct hci_conn, work);
device_del(&conn->dev);
+ put_device(&conn->dev);
}
void hci_conn_del_sysfs(struct hci_conn *conn)
diff --git a/net/bridge/br.c b/net/bridge/br.c
index 93867bb6cc9..a9018287312 100644
--- a/net/bridge/br.c
+++ b/net/bridge/br.c
@@ -39,7 +39,7 @@ static int __init br_init(void)
err = br_fdb_init();
if (err)
- goto err_out1;
+ goto err_out;
err = br_netfilter_init();
if (err)
@@ -65,6 +65,8 @@ err_out3:
err_out2:
br_netfilter_fini();
err_out1:
+ br_fdb_fini();
+err_out:
llc_sap_put(br_stp_sap);
return err;
}
diff --git a/net/bridge/br_device.c b/net/bridge/br_device.c
index c07bac5e3e1..bf7787395fe 100644
--- a/net/bridge/br_device.c
+++ b/net/bridge/br_device.c
@@ -157,8 +157,7 @@ static struct ethtool_ops br_ethtool_ops = {
void br_dev_setup(struct net_device *dev)
{
- memset(dev->dev_addr, 0, ETH_ALEN);
-
+ random_ether_addr(dev->dev_addr);
ether_setup(dev);
dev->do_ioctl = br_dev_ioctl;
diff --git a/net/bridge/br_fdb.c b/net/bridge/br_fdb.c
index eb57502bb26..bc40377136a 100644
--- a/net/bridge/br_fdb.c
+++ b/net/bridge/br_fdb.c
@@ -44,7 +44,7 @@ int __init br_fdb_init(void)
return 0;
}
-void __exit br_fdb_fini(void)
+void br_fdb_fini(void)
{
kmem_cache_destroy(br_fdb_cache);
}
diff --git a/net/bridge/br_input.c b/net/bridge/br_input.c
index 3cedd4eeeed..0ee79a726d9 100644
--- a/net/bridge/br_input.c
+++ b/net/bridge/br_input.c
@@ -122,6 +122,7 @@ static inline int is_link_local(const unsigned char *dest)
struct sk_buff *br_handle_frame(struct net_bridge_port *p, struct sk_buff *skb)
{
const unsigned char *dest = eth_hdr(skb)->h_dest;
+ int (*rhook)(struct sk_buff *skb);
if (!is_valid_ether_addr(eth_hdr(skb)->h_source))
goto drop;
@@ -147,9 +148,9 @@ struct sk_buff *br_handle_frame(struct net_bridge_port *p, struct sk_buff *skb)
switch (p->state) {
case BR_STATE_FORWARDING:
-
- if (br_should_route_hook) {
- if (br_should_route_hook(skb))
+ rhook = rcu_dereference(br_should_route_hook);
+ if (rhook != NULL) {
+ if (rhook(skb))
return skb;
dest = eth_hdr(skb)->h_dest;
}
diff --git a/net/bridge/netfilter/ebt_among.c b/net/bridge/netfilter/ebt_among.c
index 392d877040d..6436d30a550 100644
--- a/net/bridge/netfilter/ebt_among.c
+++ b/net/bridge/netfilter/ebt_among.c
@@ -187,7 +187,7 @@ static int ebt_among_check(const char *tablename, unsigned int hookmask,
if (datalen != EBT_ALIGN(expected_length)) {
printk(KERN_WARNING
- "ebtables: among: wrong size: %d"
+ "ebtables: among: wrong size: %d "
"against expected %d, rounded to %Zd\n",
datalen, expected_length,
EBT_ALIGN(expected_length));
diff --git a/net/bridge/netfilter/ebtable_broute.c b/net/bridge/netfilter/ebtable_broute.c
index e44519ebf1d..be6f1868105 100644
--- a/net/bridge/netfilter/ebtable_broute.c
+++ b/net/bridge/netfilter/ebtable_broute.c
@@ -70,13 +70,13 @@ static int __init ebtable_broute_init(void)
if (ret < 0)
return ret;
/* see br_input.c */
- br_should_route_hook = ebt_broute;
+ rcu_assign_pointer(br_should_route_hook, ebt_broute);
return ret;
}
static void __exit ebtable_broute_fini(void)
{
- br_should_route_hook = NULL;
+ rcu_assign_pointer(br_should_route_hook, NULL);
synchronize_net();
ebt_unregister_table(&broute_table);
}
diff --git a/net/compat.c b/net/compat.c
index d74d82155d7..377e560ab5c 100644
--- a/net/compat.c
+++ b/net/compat.c
@@ -254,6 +254,8 @@ int put_cmsg_compat(struct msghdr *kmsg, int level, int type, int len, void *dat
if (copy_to_user(CMSG_COMPAT_DATA(cm), data, cmlen - sizeof(struct compat_cmsghdr)))
return -EFAULT;
cmlen = CMSG_COMPAT_SPACE(len);
+ if (kmsg->msg_controllen < cmlen)
+ cmlen = kmsg->msg_controllen;
kmsg->msg_control += cmlen;
kmsg->msg_controllen -= cmlen;
return 0;
diff --git a/net/core/dev.c b/net/core/dev.c
index 86d62611f2f..0879f52115e 100644
--- a/net/core/dev.c
+++ b/net/core/dev.c
@@ -2207,8 +2207,12 @@ static void net_rx_action(struct softirq_action *h)
* still "owns" the NAPI instance and therefore can
* move the instance around on the list at-will.
*/
- if (unlikely(work == weight))
- list_move_tail(&n->poll_list, list);
+ if (unlikely(work == weight)) {
+ if (unlikely(napi_disable_pending(n)))
+ __napi_complete(n);
+ else
+ list_move_tail(&n->poll_list, list);
+ }
netpoll_poll_unlock(have);
}
@@ -2819,7 +2823,7 @@ void dev_set_allmulti(struct net_device *dev, int inc)
/*
* Upload unicast and multicast address lists to device and
* configure RX filtering. When the device doesn't support unicast
- * filtering it is put in promiscous mode while unicast addresses
+ * filtering it is put in promiscuous mode while unicast addresses
* are present.
*/
void __dev_set_rx_mode(struct net_device *dev)
@@ -3972,8 +3976,7 @@ void synchronize_net(void)
* @dev: device
*
* This function shuts down a device interface and removes it
- * from the kernel tables. On success 0 is returned, on a failure
- * a negative errno code is returned.
+ * from the kernel tables.
*
* Callers must hold the rtnl semaphore. You may want
* unregister_netdev() instead of this.
@@ -3991,8 +3994,7 @@ void unregister_netdevice(struct net_device *dev)
* @dev: device
*
* This function shuts down a device interface and removes it
- * from the kernel tables. On success 0 is returned, on a failure
- * a negative errno code is returned.
+ * from the kernel tables.
*
* This is just a wrapper for unregister_netdevice that takes
* the rtnl semaphore. In general you want to use this and not
diff --git a/net/core/pktgen.c b/net/core/pktgen.c
index de33f36947e..285ec3ed9b3 100644
--- a/net/core/pktgen.c
+++ b/net/core/pktgen.c
@@ -2463,8 +2463,6 @@ static int pktgen_output_ipsec(struct sk_buff *skb, struct pktgen_dev *pkt_dev)
x->curlft.bytes +=skb->len;
x->curlft.packets++;
- spin_unlock(&x->lock);
-
error:
spin_unlock(&x->lock);
return err;
diff --git a/net/core/scm.c b/net/core/scm.c
index 100ba6d9d47..10f5c65f6a4 100644
--- a/net/core/scm.c
+++ b/net/core/scm.c
@@ -196,6 +196,8 @@ int put_cmsg(struct msghdr * msg, int level, int type, int len, void *data)
if (copy_to_user(CMSG_DATA(cm), data, cmlen - sizeof(struct cmsghdr)))
goto out;
cmlen = CMSG_SPACE(len);
+ if (msg->msg_controllen < cmlen)
+ cmlen = msg->msg_controllen;
msg->msg_control += cmlen;
msg->msg_controllen -= cmlen;
err = 0;
diff --git a/net/core/skbuff.c b/net/core/skbuff.c
index 32d5826b717..b6283779e93 100644
--- a/net/core/skbuff.c
+++ b/net/core/skbuff.c
@@ -275,12 +275,11 @@ static void skb_release_data(struct sk_buff *skb)
/*
* Free an skbuff by memory without cleaning the state.
*/
-void kfree_skbmem(struct sk_buff *skb)
+static void kfree_skbmem(struct sk_buff *skb)
{
struct sk_buff *other;
atomic_t *fclone_ref;
- skb_release_data(skb);
switch (skb->fclone) {
case SKB_FCLONE_UNAVAILABLE:
kmem_cache_free(skbuff_head_cache, skb);
@@ -307,16 +306,8 @@ void kfree_skbmem(struct sk_buff *skb)
}
}
-/**
- * __kfree_skb - private function
- * @skb: buffer
- *
- * Free an sk_buff. Release anything attached to the buffer.
- * Clean the state. This is an internal helper function. Users should
- * always call kfree_skb
- */
-
-void __kfree_skb(struct sk_buff *skb)
+/* Free everything but the sk_buff shell. */
+static void skb_release_all(struct sk_buff *skb)
{
dst_release(skb->dst);
#ifdef CONFIG_XFRM
@@ -340,7 +331,21 @@ void __kfree_skb(struct sk_buff *skb)
skb->tc_verd = 0;
#endif
#endif
+ skb_release_data(skb);
+}
+
+/**
+ * __kfree_skb - private function
+ * @skb: buffer
+ *
+ * Free an sk_buff. Release anything attached to the buffer.
+ * Clean the state. This is an internal helper function. Users should
+ * always call kfree_skb
+ */
+void __kfree_skb(struct sk_buff *skb)
+{
+ skb_release_all(skb);
kfree_skbmem(skb);
}
@@ -411,16 +416,17 @@ static struct sk_buff *__skb_clone(struct sk_buff *n, struct sk_buff *skb)
C(len);
C(data_len);
C(mac_len);
- n->cloned = 1;
n->hdr_len = skb->nohdr ? skb_headroom(skb) : skb->hdr_len;
+ n->cloned = 1;
n->nohdr = 0;
n->destructor = NULL;
- C(truesize);
- atomic_set(&n->users, 1);
- C(head);
- C(data);
+ C(iif);
C(tail);
C(end);
+ C(head);
+ C(data);
+ C(truesize);
+ atomic_set(&n->users, 1);
atomic_inc(&(skb_shinfo(skb)->dataref));
skb->cloned = 1;
@@ -441,7 +447,7 @@ static struct sk_buff *__skb_clone(struct sk_buff *n, struct sk_buff *skb)
*/
struct sk_buff *skb_morph(struct sk_buff *dst, struct sk_buff *src)
{
- skb_release_data(dst);
+ skb_release_all(dst);
return __skb_clone(dst, src);
}
EXPORT_SYMBOL_GPL(skb_morph);
diff --git a/net/dccp/ackvec.h b/net/dccp/ackvec.h
index 9ef0737043e..9671ecd17e0 100644
--- a/net/dccp/ackvec.h
+++ b/net/dccp/ackvec.h
@@ -71,7 +71,7 @@ struct dccp_ackvec {
* @dccpavr_ack_ackno - sequence number being acknowledged
* @dccpavr_ack_ptr - pointer into dccpav_buf where this record starts
* @dccpavr_ack_nonce - dccpav_ack_nonce at the time this record was sent
- * @dccpavr_sent_len - lenght of the record in dccpav_buf
+ * @dccpavr_sent_len - length of the record in dccpav_buf
*/
struct dccp_ackvec_record {
struct list_head dccpavr_node;
diff --git a/net/dccp/ccids/ccid3.c b/net/dccp/ccids/ccid3.c
index 19b33586333..d133416d397 100644
--- a/net/dccp/ccids/ccid3.c
+++ b/net/dccp/ccids/ccid3.c
@@ -239,7 +239,7 @@ static void ccid3_hc_tx_no_feedback_timer(unsigned long data)
ccid3_tx_state_name(hctx->ccid3hctx_state),
(unsigned)(hctx->ccid3hctx_x >> 6));
/* The value of R is still undefined and so we can not recompute
- * the timout value. Keep initial value as per [RFC 4342, 5]. */
+ * the timeout value. Keep initial value as per [RFC 4342, 5]. */
t_nfb = TFRC_INITIAL_TIMEOUT;
ccid3_update_send_interval(hctx);
break;
diff --git a/net/dccp/ccids/lib/loss_interval.c b/net/dccp/ccids/lib/loss_interval.c
index 40ad428a27f..d26b88dbbb4 100644
--- a/net/dccp/ccids/lib/loss_interval.c
+++ b/net/dccp/ccids/lib/loss_interval.c
@@ -166,7 +166,7 @@ static u32 dccp_li_calc_first_li(struct sock *sk,
}
if (unlikely(interval == 0)) {
- DCCP_WARN("%s(%p), Could not find a win_count interval > 0."
+ DCCP_WARN("%s(%p), Could not find a win_count interval > 0. "
"Defaulting to 1\n", dccp_role(sk), sk);
interval = 1;
}
diff --git a/net/decnet/dn_dev.c b/net/decnet/dn_dev.c
index 66e266fb590..3bc82dc83b3 100644
--- a/net/decnet/dn_dev.c
+++ b/net/decnet/dn_dev.c
@@ -651,16 +651,18 @@ static int dn_nl_deladdr(struct sk_buff *skb, struct nlmsghdr *nlh, void *arg)
struct dn_dev *dn_db;
struct ifaddrmsg *ifm;
struct dn_ifaddr *ifa, **ifap;
- int err = -EADDRNOTAVAIL;
+ int err;
err = nlmsg_parse(nlh, sizeof(*ifm), tb, IFA_MAX, dn_ifa_policy);
if (err < 0)
goto errout;
+ err = -ENODEV;
ifm = nlmsg_data(nlh);
if ((dn_db = dn_dev_by_index(ifm->ifa_index)) == NULL)
goto errout;
+ err = -EADDRNOTAVAIL;
for (ifap = &dn_db->ifa_list; (ifa = *ifap); ifap = &ifa->ifa_next) {
if (tb[IFA_LOCAL] &&
nla_memcmp(tb[IFA_LOCAL], &ifa->ifa_local, 2))
diff --git a/net/ieee80211/ieee80211_crypt_ccmp.c b/net/ieee80211/ieee80211_crypt_ccmp.c
index c6d760d9fbb..208bf35b554 100644
--- a/net/ieee80211/ieee80211_crypt_ccmp.c
+++ b/net/ieee80211/ieee80211_crypt_ccmp.c
@@ -338,7 +338,7 @@ static int ieee80211_ccmp_decrypt(struct sk_buff *skb, int hdr_len, void *priv)
pos += 8;
if (ccmp_replay_check(pn, key->rx_pn)) {
- if (net_ratelimit()) {
+ if (ieee80211_ratelimit_debug(IEEE80211_DL_DROP)) {
IEEE80211_DEBUG_DROP("CCMP: replay detected: STA=%s "
"previous PN %02x%02x%02x%02x%02x%02x "
"received PN %02x%02x%02x%02x%02x%02x\n",
diff --git a/net/ieee80211/ieee80211_crypt_tkip.c b/net/ieee80211/ieee80211_crypt_tkip.c
index 58b22619ab1..8e146949fc6 100644
--- a/net/ieee80211/ieee80211_crypt_tkip.c
+++ b/net/ieee80211/ieee80211_crypt_tkip.c
@@ -464,7 +464,7 @@ static int ieee80211_tkip_decrypt(struct sk_buff *skb, int hdr_len, void *priv)
pos += 8;
if (tkip_replay_check(iv32, iv16, tkey->rx_iv32, tkey->rx_iv16)) {
- if (net_ratelimit()) {
+ if (ieee80211_ratelimit_debug(IEEE80211_DL_DROP)) {
IEEE80211_DEBUG_DROP("TKIP: replay detected: STA=%s"
" previous TSC %08x%04x received TSC "
"%08x%04x\n", print_mac(mac, hdr->addr2),
@@ -504,7 +504,7 @@ static int ieee80211_tkip_decrypt(struct sk_buff *skb, int hdr_len, void *priv)
* it needs to be recalculated for the next packet. */
tkey->rx_phase1_done = 0;
}
- if (net_ratelimit()) {
+ if (ieee80211_ratelimit_debug(IEEE80211_DL_DROP)) {
IEEE80211_DEBUG_DROP("TKIP: ICV error detected: STA="
"%s\n", print_mac(mac, hdr->addr2));
}
diff --git a/net/ieee80211/ieee80211_tx.c b/net/ieee80211/ieee80211_tx.c
index a4c3c51140a..6d06f1385e2 100644
--- a/net/ieee80211/ieee80211_tx.c
+++ b/net/ieee80211/ieee80211_tx.c
@@ -144,7 +144,8 @@ static int ieee80211_copy_snap(u8 * data, u16 h_proto)
snap->oui[1] = oui[1];
snap->oui[2] = oui[2];
- *(u16 *) (data + SNAP_SIZE) = htons(h_proto);
+ h_proto = htons(h_proto);
+ memcpy(data + SNAP_SIZE, &h_proto, sizeof(u16));
return SNAP_SIZE + sizeof(u16);
}
diff --git a/net/ipv4/arp.c b/net/ipv4/arp.c
index 36d6798947b..08174a2aa87 100644
--- a/net/ipv4/arp.c
+++ b/net/ipv4/arp.c
@@ -111,12 +111,8 @@
#include <net/tcp.h>
#include <net/sock.h>
#include <net/arp.h>
-#if defined(CONFIG_AX25) || defined(CONFIG_AX25_MODULE)
#include <net/ax25.h>
-#if defined(CONFIG_NETROM) || defined(CONFIG_NETROM_MODULE)
#include <net/netrom.h>
-#endif
-#endif
#if defined(CONFIG_ATM_CLIP) || defined(CONFIG_ATM_CLIP_MODULE)
#include <net/atmclip.h>
struct neigh_table *clip_tbl_hook;
@@ -710,7 +706,7 @@ static int arp_process(struct sk_buff *skb)
struct arphdr *arp;
unsigned char *arp_ptr;
struct rtable *rt;
- unsigned char *sha, *tha;
+ unsigned char *sha;
__be32 sip, tip;
u16 dev_type = dev->type;
int addr_type;
@@ -731,20 +727,10 @@ static int arp_process(struct sk_buff *skb)
htons(dev_type) != arp->ar_hrd)
goto out;
break;
-#ifdef CONFIG_NET_ETHERNET
case ARPHRD_ETHER:
-#endif
-#ifdef CONFIG_TR
case ARPHRD_IEEE802_TR:
-#endif
-#ifdef CONFIG_FDDI
case ARPHRD_FDDI:
-#endif
-#ifdef CONFIG_NET_FC
case ARPHRD_IEEE802:
-#endif
-#if defined(CONFIG_NET_ETHERNET) || defined(CONFIG_TR) || \
- defined(CONFIG_FDDI) || defined(CONFIG_NET_FC)
/*
* ETHERNET, Token Ring and Fibre Channel (which are IEEE 802
* devices, according to RFC 2625) devices will accept ARP
@@ -759,21 +745,16 @@ static int arp_process(struct sk_buff *skb)
arp->ar_pro != htons(ETH_P_IP))
goto out;
break;
-#endif
-#if defined(CONFIG_AX25) || defined(CONFIG_AX25_MODULE)
case ARPHRD_AX25:
if (arp->ar_pro != htons(AX25_P_IP) ||
arp->ar_hrd != htons(ARPHRD_AX25))
goto out;
break;
-#if defined(CONFIG_NETROM) || defined(CONFIG_NETROM_MODULE)
case ARPHRD_NETROM:
if (arp->ar_pro != htons(AX25_P_IP) ||
arp->ar_hrd != htons(ARPHRD_NETROM))
goto out;
break;
-#endif
-#endif
}
/* Understand only these message types */
@@ -790,7 +771,6 @@ static int arp_process(struct sk_buff *skb)
arp_ptr += dev->addr_len;
memcpy(&sip, arp_ptr, 4);
arp_ptr += 4;
- tha = arp_ptr;
arp_ptr += dev->addr_len;
memcpy(&tip, arp_ptr, 4);
/*
@@ -828,7 +808,8 @@ static int arp_process(struct sk_buff *skb)
if (arp->ar_op == htons(ARPOP_REQUEST) &&
inet_addr_type(tip) == RTN_LOCAL &&
!arp_ignore(in_dev,dev,sip,tip))
- arp_send(ARPOP_REPLY,ETH_P_ARP,tip,dev,tip,sha,dev->dev_addr,dev->dev_addr);
+ arp_send(ARPOP_REPLY, ETH_P_ARP, sip, dev, tip, sha,
+ dev->dev_addr, sha);
goto out;
}
diff --git a/net/ipv4/devinet.c b/net/ipv4/devinet.c
index 55d199e4ae2..b42f74617ba 100644
--- a/net/ipv4/devinet.c
+++ b/net/ipv4/devinet.c
@@ -516,8 +516,6 @@ static struct in_ifaddr *rtm_to_ifaddr(struct nlmsghdr *nlh)
goto errout;
}
- ipv4_devconf_setall(in_dev);
-
ifa = inet_alloc_ifa();
if (ifa == NULL) {
/*
@@ -528,6 +526,7 @@ static struct in_ifaddr *rtm_to_ifaddr(struct nlmsghdr *nlh)
goto errout;
}
+ ipv4_devconf_setall(in_dev);
in_dev_hold(in_dev);
if (tb[IFA_ADDRESS] == NULL)
@@ -1028,7 +1027,7 @@ static void inetdev_changename(struct net_device *dev, struct in_device *in_dev)
memcpy(ifa->ifa_label, dev->name, IFNAMSIZ);
if (named++ == 0)
continue;
- dot = strchr(ifa->ifa_label, ':');
+ dot = strchr(old, ':');
if (dot == NULL) {
sprintf(old, ":%d", named);
dot = old;
diff --git a/net/ipv4/esp4.c b/net/ipv4/esp4.c
index c31bccb9b52..1738113268b 100644
--- a/net/ipv4/esp4.c
+++ b/net/ipv4/esp4.c
@@ -9,6 +9,7 @@
#include <linux/pfkeyv2.h>
#include <linux/random.h>
#include <linux/spinlock.h>
+#include <linux/in6.h>
#include <net/icmp.h>
#include <net/protocol.h>
#include <net/udp.h>
@@ -224,6 +225,10 @@ static int esp_input(struct xfrm_state *x, struct sk_buff *skb)
/* ... check padding bits here. Silly. :-) */
+ /* RFC4303: Drop dummy packets without any error */
+ if (nexthdr[1] == IPPROTO_NONE)
+ goto out;
+
iph = ip_hdr(skb);
ihl = iph->ihl * 4;
diff --git a/net/ipv4/fib_frontend.c b/net/ipv4/fib_frontend.c
index 732d8f088b1..97abf934d18 100644
--- a/net/ipv4/fib_frontend.c
+++ b/net/ipv4/fib_frontend.c
@@ -804,10 +804,13 @@ static void nl_fib_input(struct sk_buff *skb)
nlh = nlmsg_hdr(skb);
if (skb->len < NLMSG_SPACE(0) || skb->len < nlh->nlmsg_len ||
- nlh->nlmsg_len < NLMSG_LENGTH(sizeof(*frn))) {
- kfree_skb(skb);
+ nlh->nlmsg_len < NLMSG_LENGTH(sizeof(*frn)))
return;
- }
+
+ skb = skb_clone(skb, GFP_KERNEL);
+ if (skb == NULL)
+ return;
+ nlh = nlmsg_hdr(skb);
frn = (struct fib_result_nl *) NLMSG_DATA(nlh);
tb = fib_get_table(frn->tb_id_in);
diff --git a/net/ipv4/inet_diag.c b/net/ipv4/inet_diag.c
index b0170732b5e..e468e7a7aac 100644
--- a/net/ipv4/inet_diag.c
+++ b/net/ipv4/inet_diag.c
@@ -51,6 +51,29 @@ static struct sock *idiagnl;
#define INET_DIAG_PUT(skb, attrtype, attrlen) \
RTA_DATA(__RTA_PUT(skb, attrtype, attrlen))
+static DEFINE_MUTEX(inet_diag_table_mutex);
+
+static const struct inet_diag_handler *inet_diag_lock_handler(int type)
+{
+#ifdef CONFIG_KMOD
+ if (!inet_diag_table[type])
+ request_module("net-pf-%d-proto-%d-type-%d", PF_NETLINK,
+ NETLINK_INET_DIAG, type);
+#endif
+
+ mutex_lock(&inet_diag_table_mutex);
+ if (!inet_diag_table[type])
+ return ERR_PTR(-ENOENT);
+
+ return inet_diag_table[type];
+}
+
+static inline void inet_diag_unlock_handler(
+ const struct inet_diag_handler *handler)
+{
+ mutex_unlock(&inet_diag_table_mutex);
+}
+
static int inet_csk_diag_fill(struct sock *sk,
struct sk_buff *skb,
int ext, u32 pid, u32 seq, u16 nlmsg_flags,
@@ -235,9 +258,12 @@ static int inet_diag_get_exact(struct sk_buff *in_skb,
struct inet_hashinfo *hashinfo;
const struct inet_diag_handler *handler;
- handler = inet_diag_table[nlh->nlmsg_type];
- BUG_ON(handler == NULL);
+ handler = inet_diag_lock_handler(nlh->nlmsg_type);
+ if (!handler)
+ return -ENOENT;
+
hashinfo = handler->idiag_hashinfo;
+ err = -EINVAL;
if (req->idiag_family == AF_INET) {
sk = inet_lookup(hashinfo, req->id.idiag_dst[0],
@@ -255,11 +281,12 @@ static int inet_diag_get_exact(struct sk_buff *in_skb,
}
#endif
else {
- return -EINVAL;
+ goto unlock;
}
+ err = -ENOENT;
if (sk == NULL)
- return -ENOENT;
+ goto unlock;
err = -ESTALE;
if ((req->id.idiag_cookie[0] != INET_DIAG_NOCOOKIE ||
@@ -296,6 +323,8 @@ out:
else
sock_put(sk);
}
+unlock:
+ inet_diag_unlock_handler(handler);
return err;
}
@@ -678,8 +707,10 @@ static int inet_diag_dump(struct sk_buff *skb, struct netlink_callback *cb)
const struct inet_diag_handler *handler;
struct inet_hashinfo *hashinfo;
- handler = inet_diag_table[cb->nlh->nlmsg_type];
- BUG_ON(handler == NULL);
+ handler = inet_diag_lock_handler(cb->nlh->nlmsg_type);
+ if (!handler)
+ goto no_handler;
+
hashinfo = handler->idiag_hashinfo;
s_i = cb->args[1];
@@ -743,7 +774,7 @@ skip_listen_ht:
}
if (!(r->idiag_states & ~(TCPF_LISTEN | TCPF_SYN_RECV)))
- return skb->len;
+ goto unlock;
for (i = s_i; i < hashinfo->ehash_size; i++) {
struct inet_ehash_bucket *head = &hashinfo->ehash[i];
@@ -805,6 +836,9 @@ next_dying:
done:
cb->args[1] = i;
cb->args[2] = num;
+unlock:
+ inet_diag_unlock_handler(handler);
+no_handler:
return skb->len;
}
@@ -816,15 +850,6 @@ static int inet_diag_rcv_msg(struct sk_buff *skb, struct nlmsghdr *nlh)
nlmsg_len(nlh) < hdrlen)
return -EINVAL;
-#ifdef CONFIG_KMOD
- if (inet_diag_table[nlh->nlmsg_type] == NULL)
- request_module("net-pf-%d-proto-%d-type-%d", PF_NETLINK,
- NETLINK_INET_DIAG, nlh->nlmsg_type);
-#endif
-
- if (inet_diag_table[nlh->nlmsg_type] == NULL)
- return -ENOENT;
-
if (nlh->nlmsg_flags & NLM_F_DUMP) {
if (nlmsg_attrlen(nlh, hdrlen)) {
struct nlattr *attr;
@@ -853,8 +878,6 @@ static void inet_diag_rcv(struct sk_buff *skb)
mutex_unlock(&inet_diag_mutex);
}
-static DEFINE_SPINLOCK(inet_diag_register_lock);
-
int inet_diag_register(const struct inet_diag_handler *h)
{
const __u16 type = h->idiag_type;
@@ -863,13 +886,13 @@ int inet_diag_register(const struct inet_diag_handler *h)
if (type >= INET_DIAG_GETSOCK_MAX)
goto out;
- spin_lock(&inet_diag_register_lock);
+ mutex_lock(&inet_diag_table_mutex);
err = -EEXIST;
if (inet_diag_table[type] == NULL) {
inet_diag_table[type] = h;
err = 0;
}
- spin_unlock(&inet_diag_register_lock);
+ mutex_unlock(&inet_diag_table_mutex);
out:
return err;
}
@@ -882,11 +905,9 @@ void inet_diag_unregister(const struct inet_diag_handler *h)
if (type >= INET_DIAG_GETSOCK_MAX)
return;
- spin_lock(&inet_diag_register_lock);
+ mutex_lock(&inet_diag_table_mutex);
inet_diag_table[type] = NULL;
- spin_unlock(&inet_diag_register_lock);
-
- synchronize_rcu();
+ mutex_unlock(&inet_diag_table_mutex);
}
EXPORT_SYMBOL_GPL(inet_diag_unregister);
diff --git a/net/ipv4/inet_lro.c b/net/ipv4/inet_lro.c
index ac3b1d3dba2..4a4d49fca1f 100644
--- a/net/ipv4/inet_lro.c
+++ b/net/ipv4/inet_lro.c
@@ -310,7 +310,7 @@ static void lro_flush(struct net_lro_mgr *lro_mgr,
skb_shinfo(lro_desc->parent)->gso_size = lro_desc->mss;
if (lro_desc->vgrp) {
- if (test_bit(LRO_F_NAPI, &lro_mgr->features))
+ if (lro_mgr->features & LRO_F_NAPI)
vlan_hwaccel_receive_skb(lro_desc->parent,
lro_desc->vgrp,
lro_desc->vlan_tag);
@@ -320,7 +320,7 @@ static void lro_flush(struct net_lro_mgr *lro_mgr,
lro_desc->vlan_tag);
} else {
- if (test_bit(LRO_F_NAPI, &lro_mgr->features))
+ if (lro_mgr->features & LRO_F_NAPI)
netif_receive_skb(lro_desc->parent);
else
netif_rx(lro_desc->parent);
@@ -352,7 +352,7 @@ static int __lro_proc_skb(struct net_lro_mgr *lro_mgr, struct sk_buff *skb,
goto out;
if ((skb->protocol == htons(ETH_P_8021Q))
- && !test_bit(LRO_F_EXTRACT_VLAN_ID, &lro_mgr->features))
+ && !(lro_mgr->features & LRO_F_EXTRACT_VLAN_ID))
vlan_hdr_len = VLAN_HLEN;
if (!lro_desc->active) { /* start new lro session */
@@ -401,10 +401,11 @@ static struct sk_buff *lro_gen_skb(struct net_lro_mgr *lro_mgr,
int data_len = len;
int hdr_len = min(len, hlen);
- skb = netdev_alloc_skb(lro_mgr->dev, hlen);
+ skb = netdev_alloc_skb(lro_mgr->dev, hlen + lro_mgr->frag_align_pad);
if (!skb)
return NULL;
+ skb_reserve(skb, lro_mgr->frag_align_pad);
skb->len = len;
skb->data_len = len - hdr_len;
skb->truesize += true_size;
@@ -473,7 +474,7 @@ static struct sk_buff *__lro_proc_segment(struct net_lro_mgr *lro_mgr,
goto out;
if ((skb->protocol == htons(ETH_P_8021Q))
- && !test_bit(LRO_F_EXTRACT_VLAN_ID, &lro_mgr->features))
+ && !(lro_mgr->features & LRO_F_EXTRACT_VLAN_ID))
vlan_hdr_len = VLAN_HLEN;
iph = (void *)(skb->data + vlan_hdr_len);
@@ -515,7 +516,7 @@ void lro_receive_skb(struct net_lro_mgr *lro_mgr,
void *priv)
{
if (__lro_proc_skb(lro_mgr, skb, NULL, 0, priv)) {
- if (test_bit(LRO_F_NAPI, &lro_mgr->features))
+ if (lro_mgr->features & LRO_F_NAPI)
netif_receive_skb(skb);
else
netif_rx(skb);
@@ -530,7 +531,7 @@ void lro_vlan_hwaccel_receive_skb(struct net_lro_mgr *lro_mgr,
void *priv)
{
if (__lro_proc_skb(lro_mgr, skb, vgrp, vlan_tag, priv)) {
- if (test_bit(LRO_F_NAPI, &lro_mgr->features))
+ if (lro_mgr->features & LRO_F_NAPI)
vlan_hwaccel_receive_skb(skb, vgrp, vlan_tag);
else
vlan_hwaccel_rx(skb, vgrp, vlan_tag);
@@ -549,7 +550,7 @@ void lro_receive_frags(struct net_lro_mgr *lro_mgr,
if (!skb)
return;
- if (test_bit(LRO_F_NAPI, &lro_mgr->features))
+ if (lro_mgr->features & LRO_F_NAPI)
netif_receive_skb(skb);
else
netif_rx(skb);
@@ -569,7 +570,7 @@ void lro_vlan_hwaccel_receive_frags(struct net_lro_mgr *lro_mgr,
if (!skb)
return;
- if (test_bit(LRO_F_NAPI, &lro_mgr->features))
+ if (lro_mgr->features & LRO_F_NAPI)
vlan_hwaccel_receive_skb(skb, vgrp, vlan_tag);
else
vlan_hwaccel_rx(skb, vgrp, vlan_tag);
diff --git a/net/ipv4/ip_gre.c b/net/ipv4/ip_gre.c
index 02b02a8d681..4b93f32de10 100644
--- a/net/ipv4/ip_gre.c
+++ b/net/ipv4/ip_gre.c
@@ -613,7 +613,7 @@ static int ipgre_rcv(struct sk_buff *skb)
offset += 4;
}
- skb_reset_mac_header(skb);
+ skb->mac_header = skb->network_header;
__pskb_pull(skb, offset);
skb_reset_network_header(skb);
skb_postpull_rcsum(skb, skb_transport_header(skb), offset);
diff --git a/net/ipv4/ipconfig.c b/net/ipv4/ipconfig.c
index c5c107a0182..b8f7763b226 100644
--- a/net/ipv4/ipconfig.c
+++ b/net/ipv4/ipconfig.c
@@ -1396,31 +1396,16 @@ late_initcall(ip_auto_config);
/*
* Decode any IP configuration options in the "ip=" or "nfsaddrs=" kernel
- * command line parameter. It consists of option fields separated by colons in
- * the following order:
- *
- * <client-ip>:<server-ip>:<gw-ip>:<netmask>:<host name>:<device>:<PROTO>
- *
- * Any of the fields can be empty which means to use a default value:
- * <client-ip> - address given by BOOTP or RARP
- * <server-ip> - address of host returning BOOTP or RARP packet
- * <gw-ip> - none, or the address returned by BOOTP
- * <netmask> - automatically determined from <client-ip>, or the
- * one returned by BOOTP
- * <host name> - <client-ip> in ASCII notation, or the name returned
- * by BOOTP
- * <device> - use all available devices
- * <PROTO>:
- * off|none - don't do autoconfig at all (DEFAULT)
- * on|any - use any configured protocol
- * dhcp|bootp|rarp - use only the specified protocol
- * both - use both BOOTP and RARP (not DHCP)
+ * command line parameter. See Documentation/nfsroot.txt.
*/
static int __init ic_proto_name(char *name)
{
if (!strcmp(name, "on") || !strcmp(name, "any")) {
return 1;
}
+ if (!strcmp(name, "off") || !strcmp(name, "none")) {
+ return 0;
+ }
#ifdef CONFIG_IP_PNP_DHCP
else if (!strcmp(name, "dhcp")) {
ic_proto_enabled &= ~IC_RARP;
@@ -1454,17 +1439,24 @@ static int __init ip_auto_config_setup(char *addrs)
int num = 0;
ic_set_manually = 1;
+ ic_enable = 1;
- ic_enable = (*addrs &&
- (strcmp(addrs, "off") != 0) &&
- (strcmp(addrs, "none") != 0));
- if (!ic_enable)
+ /*
+ * If any dhcp, bootp etc options are set, leave autoconfig on
+ * and skip the below static IP processing.
+ */
+ if (ic_proto_name(addrs))
return 1;
- if (ic_proto_name(addrs))
+ /* If no static IP is given, turn off autoconfig and bail. */
+ if (*addrs == 0 ||
+ strcmp(addrs, "off") == 0 ||
+ strcmp(addrs, "none") == 0) {
+ ic_enable = 0;
return 1;
+ }
- /* Parse the whole string */
+ /* Parse string for static IP assignment. */
ip = addrs;
while (ip && *ip) {
if ((cp = strchr(ip, ':')))
@@ -1502,7 +1494,10 @@ static int __init ip_auto_config_setup(char *addrs)
strlcpy(user_dev_name, ip, sizeof(user_dev_name));
break;
case 6:
- ic_proto_name(ip);
+ if (ic_proto_name(ip) == 0 &&
+ ic_myaddr == NONE) {
+ ic_enable = 0;
+ }
break;
}
}
diff --git a/net/ipv4/ipvs/ip_vs_core.c b/net/ipv4/ipvs/ip_vs_core.c
index 20c884a5772..8fba20256f5 100644
--- a/net/ipv4/ipvs/ip_vs_core.c
+++ b/net/ipv4/ipvs/ip_vs_core.c
@@ -637,7 +637,7 @@ static int ip_vs_out_icmp(struct sk_buff *skb, int *related)
verdict = NF_DROP;
if (IP_VS_FWD_METHOD(cp) != 0) {
- IP_VS_ERR("shouldn't reach here, because the box is on the"
+ IP_VS_ERR("shouldn't reach here, because the box is on the "
"half connection in the tun/dr module.\n");
}
diff --git a/net/ipv4/ipvs/ip_vs_ctl.c b/net/ipv4/ipvs/ip_vs_ctl.c
index b64cf45a9ea..693d92490c1 100644
--- a/net/ipv4/ipvs/ip_vs_ctl.c
+++ b/net/ipv4/ipvs/ip_vs_ctl.c
@@ -1424,7 +1424,6 @@ proc_do_sync_threshold(ctl_table *table, int write, struct file *filp,
static struct ctl_table vs_vars[] = {
{
- .ctl_name = NET_IPV4_VS_AMEMTHRESH,
.procname = "amemthresh",
.data = &sysctl_ip_vs_amemthresh,
.maxlen = sizeof(int),
@@ -1433,7 +1432,6 @@ static struct ctl_table vs_vars[] = {
},
#ifdef CONFIG_IP_VS_DEBUG
{
- .ctl_name = NET_IPV4_VS_DEBUG_LEVEL,
.procname = "debug_level",
.data = &sysctl_ip_vs_debug_level,
.maxlen = sizeof(int),
@@ -1442,7 +1440,6 @@ static struct ctl_table vs_vars[] = {
},
#endif
{
- .ctl_name = NET_IPV4_VS_AMDROPRATE,
.procname = "am_droprate",
.data = &sysctl_ip_vs_am_droprate,
.maxlen = sizeof(int),
@@ -1450,7 +1447,6 @@ static struct ctl_table vs_vars[] = {
.proc_handler = &proc_dointvec,
},
{
- .ctl_name = NET_IPV4_VS_DROP_ENTRY,
.procname = "drop_entry",
.data = &sysctl_ip_vs_drop_entry,
.maxlen = sizeof(int),
@@ -1458,7 +1454,6 @@ static struct ctl_table vs_vars[] = {
.proc_handler = &proc_do_defense_mode,
},
{
- .ctl_name = NET_IPV4_VS_DROP_PACKET,
.procname = "drop_packet",
.data = &sysctl_ip_vs_drop_packet,
.maxlen = sizeof(int),
@@ -1466,7 +1461,6 @@ static struct ctl_table vs_vars[] = {
.proc_handler = &proc_do_defense_mode,
},
{
- .ctl_name = NET_IPV4_VS_SECURE_TCP,
.procname = "secure_tcp",
.data = &sysctl_ip_vs_secure_tcp,
.maxlen = sizeof(int),
@@ -1475,7 +1469,6 @@ static struct ctl_table vs_vars[] = {
},
#if 0
{
- .ctl_name = NET_IPV4_VS_TO_ES,
.procname = "timeout_established",
.data = &vs_timeout_table_dos.timeout[IP_VS_S_ESTABLISHED],
.maxlen = sizeof(int),
@@ -1483,7 +1476,6 @@ static struct ctl_table vs_vars[] = {
.proc_handler = &proc_dointvec_jiffies,
},
{
- .ctl_name = NET_IPV4_VS_TO_SS,
.procname = "timeout_synsent",
.data = &vs_timeout_table_dos.timeout[IP_VS_S_SYN_SENT],
.maxlen = sizeof(int),
@@ -1491,7 +1483,6 @@ static struct ctl_table vs_vars[] = {
.proc_handler = &proc_dointvec_jiffies,
},
{
- .ctl_name = NET_IPV4_VS_TO_SR,
.procname = "timeout_synrecv",
.data = &vs_timeout_table_dos.timeout[IP_VS_S_SYN_RECV],
.maxlen = sizeof(int),
@@ -1499,7 +1490,6 @@ static struct ctl_table vs_vars[] = {
.proc_handler = &proc_dointvec_jiffies,
},
{
- .ctl_name = NET_IPV4_VS_TO_FW,
.procname = "timeout_finwait",
.data = &vs_timeout_table_dos.timeout[IP_VS_S_FIN_WAIT],
.maxlen = sizeof(int),
@@ -1507,7 +1497,6 @@ static struct ctl_table vs_vars[] = {
.proc_handler = &proc_dointvec_jiffies,
},
{
- .ctl_name = NET_IPV4_VS_TO_TW,
.procname = "timeout_timewait",
.data = &vs_timeout_table_dos.timeout[IP_VS_S_TIME_WAIT],
.maxlen = sizeof(int),
@@ -1515,7 +1504,6 @@ static struct ctl_table vs_vars[] = {
.proc_handler = &proc_dointvec_jiffies,
},
{
- .ctl_name = NET_IPV4_VS_TO_CL,
.procname = "timeout_close",
.data = &vs_timeout_table_dos.timeout[IP_VS_S_CLOSE],
.maxlen = sizeof(int),
@@ -1523,7 +1511,6 @@ static struct ctl_table vs_vars[] = {
.proc_handler = &proc_dointvec_jiffies,
},
{
- .ctl_name = NET_IPV4_VS_TO_CW,
.procname = "timeout_closewait",
.data = &vs_timeout_table_dos.timeout[IP_VS_S_CLOSE_WAIT],
.maxlen = sizeof(int),
@@ -1531,7 +1518,6 @@ static struct ctl_table vs_vars[] = {
.proc_handler = &proc_dointvec_jiffies,
},
{
- .ctl_name = NET_IPV4_VS_TO_LA,
.procname = "timeout_lastack",
.data = &vs_timeout_table_dos.timeout[IP_VS_S_LAST_ACK],
.maxlen = sizeof(int),
@@ -1539,7 +1525,6 @@ static struct ctl_table vs_vars[] = {
.proc_handler = &proc_dointvec_jiffies,
},
{
- .ctl_name = NET_IPV4_VS_TO_LI,
.procname = "timeout_listen",
.data = &vs_timeout_table_dos.timeout[IP_VS_S_LISTEN],
.maxlen = sizeof(int),
@@ -1547,7 +1532,6 @@ static struct ctl_table vs_vars[] = {
.proc_handler = &proc_dointvec_jiffies,
},
{
- .ctl_name = NET_IPV4_VS_TO_SA,
.procname = "timeout_synack",
.data = &vs_timeout_table_dos.timeout[IP_VS_S_SYNACK],
.maxlen = sizeof(int),
@@ -1555,7 +1539,6 @@ static struct ctl_table vs_vars[] = {
.proc_handler = &proc_dointvec_jiffies,
},
{
- .ctl_name = NET_IPV4_VS_TO_UDP,
.procname = "timeout_udp",
.data = &vs_timeout_table_dos.timeout[IP_VS_S_UDP],
.maxlen = sizeof(int),
@@ -1563,7 +1546,6 @@ static struct ctl_table vs_vars[] = {
.proc_handler = &proc_dointvec_jiffies,
},
{
- .ctl_name = NET_IPV4_VS_TO_ICMP,
.procname = "timeout_icmp",
.data = &vs_timeout_table_dos.timeout[IP_VS_S_ICMP],
.maxlen = sizeof(int),
@@ -1572,7 +1554,6 @@ static struct ctl_table vs_vars[] = {
},
#endif
{
- .ctl_name = NET_IPV4_VS_CACHE_BYPASS,
.procname = "cache_bypass",
.data = &sysctl_ip_vs_cache_bypass,
.maxlen = sizeof(int),
@@ -1580,7 +1561,6 @@ static struct ctl_table vs_vars[] = {
.proc_handler = &proc_dointvec,
},
{
- .ctl_name = NET_IPV4_VS_EXPIRE_NODEST_CONN,
.procname = "expire_nodest_conn",
.data = &sysctl_ip_vs_expire_nodest_conn,
.maxlen = sizeof(int),
@@ -1588,7 +1568,6 @@ static struct ctl_table vs_vars[] = {
.proc_handler = &proc_dointvec,
},
{
- .ctl_name = NET_IPV4_VS_EXPIRE_QUIESCENT_TEMPLATE,
.procname = "expire_quiescent_template",
.data = &sysctl_ip_vs_expire_quiescent_template,
.maxlen = sizeof(int),
@@ -1596,7 +1575,6 @@ static struct ctl_table vs_vars[] = {
.proc_handler = &proc_dointvec,
},
{
- .ctl_name = NET_IPV4_VS_SYNC_THRESHOLD,
.procname = "sync_threshold",
.data = &sysctl_ip_vs_sync_threshold,
.maxlen = sizeof(sysctl_ip_vs_sync_threshold),
@@ -1604,7 +1582,6 @@ static struct ctl_table vs_vars[] = {
.proc_handler = &proc_do_sync_threshold,
},
{
- .ctl_name = NET_IPV4_VS_NAT_ICMP_SEND,
.procname = "nat_icmp_send",
.data = &sysctl_ip_vs_nat_icmp_send,
.maxlen = sizeof(int),
@@ -1616,7 +1593,6 @@ static struct ctl_table vs_vars[] = {
static ctl_table vs_table[] = {
{
- .ctl_name = NET_IPV4_VS,
.procname = "vs",
.mode = 0555,
.child = vs_vars
diff --git a/net/ipv4/ipvs/ip_vs_lblc.c b/net/ipv4/ipvs/ip_vs_lblc.c
index 052f4ed5917..ad89644ef5d 100644
--- a/net/ipv4/ipvs/ip_vs_lblc.c
+++ b/net/ipv4/ipvs/ip_vs_lblc.c
@@ -114,7 +114,6 @@ struct ip_vs_lblc_table {
static ctl_table vs_vars_table[] = {
{
- .ctl_name = NET_IPV4_VS_LBLC_EXPIRE,
.procname = "lblc_expiration",
.data = &sysctl_ip_vs_lblc_expiration,
.maxlen = sizeof(int),
@@ -126,7 +125,6 @@ static ctl_table vs_vars_table[] = {
static ctl_table vs_table[] = {
{
- .ctl_name = NET_IPV4_VS,
.procname = "vs",
.mode = 0555,
.child = vs_vars_table
@@ -582,9 +580,14 @@ static struct ip_vs_scheduler ip_vs_lblc_scheduler =
static int __init ip_vs_lblc_init(void)
{
+ int ret;
+
INIT_LIST_HEAD(&ip_vs_lblc_scheduler.n_list);
sysctl_header = register_sysctl_table(lblc_root_table);
- return register_ip_vs_scheduler(&ip_vs_lblc_scheduler);
+ ret = register_ip_vs_scheduler(&ip_vs_lblc_scheduler);
+ if (ret)
+ unregister_sysctl_table(sysctl_header);
+ return ret;
}
diff --git a/net/ipv4/ipvs/ip_vs_lblcr.c b/net/ipv4/ipvs/ip_vs_lblcr.c
index 427b593c106..2a5ed85a335 100644
--- a/net/ipv4/ipvs/ip_vs_lblcr.c
+++ b/net/ipv4/ipvs/ip_vs_lblcr.c
@@ -302,7 +302,6 @@ struct ip_vs_lblcr_table {
static ctl_table vs_vars_table[] = {
{
- .ctl_name = NET_IPV4_VS_LBLCR_EXPIRE,
.procname = "lblcr_expiration",
.data = &sysctl_ip_vs_lblcr_expiration,
.maxlen = sizeof(int),
@@ -314,7 +313,6 @@ static ctl_table vs_vars_table[] = {
static ctl_table vs_table[] = {
{
- .ctl_name = NET_IPV4_VS,
.procname = "vs",
.mode = 0555,
.child = vs_vars_table
@@ -771,9 +769,14 @@ static struct ip_vs_scheduler ip_vs_lblcr_scheduler =
static int __init ip_vs_lblcr_init(void)
{
+ int ret;
+
INIT_LIST_HEAD(&ip_vs_lblcr_scheduler.n_list);
sysctl_header = register_sysctl_table(lblcr_root_table);
- return register_ip_vs_scheduler(&ip_vs_lblcr_scheduler);
+ ret = register_ip_vs_scheduler(&ip_vs_lblcr_scheduler);
+ if (ret)
+ unregister_sysctl_table(sysctl_header);
+ return ret;
}
diff --git a/net/ipv4/ipvs/ip_vs_proto.c b/net/ipv4/ipvs/ip_vs_proto.c
index e844ddb82b9..c0e11ec8f0f 100644
--- a/net/ipv4/ipvs/ip_vs_proto.c
+++ b/net/ipv4/ipvs/ip_vs_proto.c
@@ -45,7 +45,7 @@ static struct ip_vs_protocol *ip_vs_proto_table[IP_VS_PROTO_TAB_SIZE];
/*
* register an ipvs protocol
*/
-static int register_ip_vs_protocol(struct ip_vs_protocol *pp)
+static int __used register_ip_vs_protocol(struct ip_vs_protocol *pp)
{
unsigned hash = IP_VS_PROTO_HASH(pp->protocol);
diff --git a/net/ipv4/ipvs/ip_vs_sched.c b/net/ipv4/ipvs/ip_vs_sched.c
index 1602304abbf..43223586190 100644
--- a/net/ipv4/ipvs/ip_vs_sched.c
+++ b/net/ipv4/ipvs/ip_vs_sched.c
@@ -183,19 +183,6 @@ int register_ip_vs_scheduler(struct ip_vs_scheduler *scheduler)
/* increase the module use count */
ip_vs_use_count_inc();
- /*
- * Make sure that the scheduler with this name doesn't exist
- * in the scheduler list.
- */
- sched = ip_vs_sched_getbyname(scheduler->name);
- if (sched) {
- ip_vs_scheduler_put(sched);
- ip_vs_use_count_dec();
- IP_VS_ERR("register_ip_vs_scheduler(): [%s] scheduler "
- "already existed in the system\n", scheduler->name);
- return -EINVAL;
- }
-
write_lock_bh(&__ip_vs_sched_lock);
if (scheduler->n_list.next != &scheduler->n_list) {
@@ -207,6 +194,20 @@ int register_ip_vs_scheduler(struct ip_vs_scheduler *scheduler)
}
/*
+ * Make sure that the scheduler with this name doesn't exist
+ * in the scheduler list.
+ */
+ list_for_each_entry(sched, &ip_vs_schedulers, n_list) {
+ if (strcmp(scheduler->name, sched->name) == 0) {
+ write_unlock_bh(&__ip_vs_sched_lock);
+ ip_vs_use_count_dec();
+ IP_VS_ERR("register_ip_vs_scheduler(): [%s] scheduler "
+ "already existed in the system\n",
+ scheduler->name);
+ return -EINVAL;
+ }
+ }
+ /*
* Add it into the d-linked scheduler list
*/
list_add(&scheduler->n_list, &ip_vs_schedulers);
diff --git a/net/ipv4/netfilter/ip_tables.c b/net/ipv4/netfilter/ip_tables.c
index 4b10b98640a..b9b189c2620 100644
--- a/net/ipv4/netfilter/ip_tables.c
+++ b/net/ipv4/netfilter/ip_tables.c
@@ -1492,8 +1492,10 @@ static inline int compat_copy_match_to_user(struct ipt_entry_match *m,
return xt_compat_match_to_user(m, dstptr, size);
}
-static int compat_copy_entry_to_user(struct ipt_entry *e,
- void __user **dstptr, compat_uint_t *size)
+static int
+compat_copy_entry_to_user(struct ipt_entry *e, void __user **dstptr,
+ compat_uint_t *size, struct xt_counters *counters,
+ unsigned int *i)
{
struct ipt_entry_target *t;
struct compat_ipt_entry __user *ce;
@@ -1507,6 +1509,9 @@ static int compat_copy_entry_to_user(struct ipt_entry *e,
if (copy_to_user(ce, e, sizeof(struct ipt_entry)))
goto out;
+ if (copy_to_user(&ce->counters, &counters[*i], sizeof(counters[*i])))
+ goto out;
+
*dstptr += sizeof(struct compat_ipt_entry);
ret = IPT_MATCH_ITERATE(e, compat_copy_match_to_user, dstptr, size);
target_offset = e->target_offset - (origsize - *size);
@@ -1522,6 +1527,8 @@ static int compat_copy_entry_to_user(struct ipt_entry *e,
goto out;
if (put_user(next_offset, &ce->next_offset))
goto out;
+
+ (*i)++;
return 0;
out:
return ret;
@@ -1937,14 +1944,13 @@ struct compat_ipt_get_entries
static int compat_copy_entries_to_user(unsigned int total_size,
struct xt_table *table, void __user *userptr)
{
- unsigned int off, num;
- struct compat_ipt_entry e;
struct xt_counters *counters;
struct xt_table_info *private = table->private;
void __user *pos;
unsigned int size;
int ret = 0;
void *loc_cpu_entry;
+ unsigned int i = 0;
counters = alloc_counters(table);
if (IS_ERR(counters))
@@ -1958,48 +1964,9 @@ static int compat_copy_entries_to_user(unsigned int total_size,
pos = userptr;
size = total_size;
ret = IPT_ENTRY_ITERATE(loc_cpu_entry, total_size,
- compat_copy_entry_to_user, &pos, &size);
- if (ret)
- goto free_counters;
-
- /* ... then go back and fix counters and names */
- for (off = 0, num = 0; off < size; off += e.next_offset, num++) {
- unsigned int i;
- struct ipt_entry_match m;
- struct ipt_entry_target t;
+ compat_copy_entry_to_user,
+ &pos, &size, counters, &i);
- ret = -EFAULT;
- if (copy_from_user(&e, userptr + off,
- sizeof(struct compat_ipt_entry)))
- goto free_counters;
- if (copy_to_user(userptr + off +
- offsetof(struct compat_ipt_entry, counters),
- &counters[num], sizeof(counters[num])))
- goto free_counters;
-
- for (i = sizeof(struct compat_ipt_entry);
- i < e.target_offset; i += m.u.match_size) {
- if (copy_from_user(&m, userptr + off + i,
- sizeof(struct ipt_entry_match)))
- goto free_counters;
- if (copy_to_user(userptr + off + i +
- offsetof(struct ipt_entry_match, u.user.name),
- m.u.kernel.match->name,
- strlen(m.u.kernel.match->name) + 1))
- goto free_counters;
- }
-
- if (copy_from_user(&t, userptr + off + e.target_offset,
- sizeof(struct ipt_entry_target)))
- goto free_counters;
- if (copy_to_user(userptr + off + e.target_offset +
- offsetof(struct ipt_entry_target, u.user.name),
- t.u.kernel.target->name,
- strlen(t.u.kernel.target->name) + 1))
- goto free_counters;
- }
- ret = 0;
-free_counters:
vfree(counters);
return ret;
}
diff --git a/net/ipv4/netfilter/iptable_raw.c b/net/ipv4/netfilter/iptable_raw.c
index 5de6e57ac55..f8678651250 100644
--- a/net/ipv4/netfilter/iptable_raw.c
+++ b/net/ipv4/netfilter/iptable_raw.c
@@ -66,7 +66,7 @@ ipt_local_hook(unsigned int hook,
if (skb->len < sizeof(struct iphdr) ||
ip_hdrlen(skb) < sizeof(struct iphdr)) {
if (net_ratelimit())
- printk("iptable_raw: ignoring short SOCK_RAW"
+ printk("iptable_raw: ignoring short SOCK_RAW "
"packet.\n");
return NF_ACCEPT;
}
diff --git a/net/ipv4/netfilter/nf_conntrack_l3proto_ipv4.c b/net/ipv4/netfilter/nf_conntrack_l3proto_ipv4.c
index 831e9b29806..910dae732a0 100644
--- a/net/ipv4/netfilter/nf_conntrack_l3proto_ipv4.c
+++ b/net/ipv4/netfilter/nf_conntrack_l3proto_ipv4.c
@@ -419,6 +419,9 @@ struct nf_conntrack_l3proto nf_conntrack_l3proto_ipv4 __read_mostly = {
.me = THIS_MODULE,
};
+module_param_call(hashsize, nf_conntrack_set_hashsize, param_get_uint,
+ &nf_conntrack_htable_size, 0600);
+
MODULE_ALIAS("nf_conntrack-" __stringify(AF_INET));
MODULE_ALIAS("ip_conntrack");
MODULE_LICENSE("GPL");
diff --git a/net/ipv4/netfilter/nf_nat_core.c b/net/ipv4/netfilter/nf_nat_core.c
index 70e7997ea28..86b465b176b 100644
--- a/net/ipv4/netfilter/nf_nat_core.c
+++ b/net/ipv4/netfilter/nf_nat_core.c
@@ -607,13 +607,10 @@ static void nf_nat_move_storage(struct nf_conn *conntrack, void *old)
struct nf_conn_nat *new_nat = nf_ct_ext_find(conntrack, NF_CT_EXT_NAT);
struct nf_conn_nat *old_nat = (struct nf_conn_nat *)old;
struct nf_conn *ct = old_nat->ct;
- unsigned int srchash;
- if (!(ct->status & IPS_NAT_DONE_MASK))
+ if (!ct || !(ct->status & IPS_NAT_DONE_MASK))
return;
- srchash = hash_by_src(&ct->tuplehash[IP_CT_DIR_ORIGINAL].tuple);
-
write_lock_bh(&nf_nat_lock);
hlist_replace_rcu(&old_nat->bysource, &new_nat->bysource);
new_nat->ct = ct;
diff --git a/net/ipv4/netfilter/nf_nat_sip.c b/net/ipv4/netfilter/nf_nat_sip.c
index 3ca98971a1e..8996ccb757d 100644
--- a/net/ipv4/netfilter/nf_nat_sip.c
+++ b/net/ipv4/netfilter/nf_nat_sip.c
@@ -165,7 +165,7 @@ static int mangle_content_len(struct sk_buff *skb,
dataoff = ip_hdrlen(skb) + sizeof(struct udphdr);
- /* Get actual SDP lenght */
+ /* Get actual SDP length */
if (ct_sip_get_info(ct, dptr, skb->len - dataoff, &matchoff,
&matchlen, POS_SDP_HEADER) > 0) {
diff --git a/net/ipv4/raw.c b/net/ipv4/raw.c
index 66b42f547bf..e7050f8eabe 100644
--- a/net/ipv4/raw.c
+++ b/net/ipv4/raw.c
@@ -271,6 +271,7 @@ static int raw_send_hdrinc(struct sock *sk, void *from, size_t length,
int hh_len;
struct iphdr *iph;
struct sk_buff *skb;
+ unsigned int iphlen;
int err;
if (length > rt->u.dst.dev->mtu) {
@@ -304,7 +305,8 @@ static int raw_send_hdrinc(struct sock *sk, void *from, size_t length,
goto error_fault;
/* We don't modify invalid header */
- if (length >= sizeof(*iph) && iph->ihl * 4U <= length) {
+ iphlen = iph->ihl * 4;
+ if (iphlen >= sizeof(*iph) && iphlen <= length) {
if (!iph->saddr)
iph->saddr = rt->rt_src;
iph->check = 0;
diff --git a/net/ipv4/route.c b/net/ipv4/route.c
index 1bff9ed349f..d3377069ce0 100644
--- a/net/ipv4/route.c
+++ b/net/ipv4/route.c
@@ -1161,7 +1161,7 @@ static struct dst_entry *ipv4_negative_advice(struct dst_entry *dst)
unsigned hash = rt_hash(rt->fl.fl4_dst, rt->fl.fl4_src,
rt->fl.oif);
#if RT_CACHE_DEBUG >= 1
- printk(KERN_DEBUG "ip_rt_advice: redirect to "
+ printk(KERN_DEBUG "ipv4_negative_advice: redirect to "
"%u.%u.%u.%u/%02x dropped\n",
NIPQUAD(rt->rt_dst), rt->fl.fl4_tos);
#endif
@@ -1252,6 +1252,7 @@ static int ip_error(struct sk_buff *skb)
break;
case ENETUNREACH:
code = ICMP_NET_UNREACH;
+ IP_INC_STATS_BH(IPSTATS_MIB_INNOROUTES);
break;
case EACCES:
code = ICMP_PKT_FILTERED;
@@ -1881,6 +1882,8 @@ no_route:
RT_CACHE_STAT_INC(in_no_route);
spec_dst = inet_select_addr(dev, 0, RT_SCOPE_UNIVERSE);
res.type = RTN_UNREACHABLE;
+ if (err == -ESRCH)
+ err = -ENETUNREACH;
goto local_input;
/*
@@ -2623,11 +2626,10 @@ int ip_rt_dump(struct sk_buff *skb, struct netlink_callback *cb)
int idx, s_idx;
s_h = cb->args[0];
+ if (s_h < 0)
+ s_h = 0;
s_idx = idx = cb->args[1];
- for (h = 0; h <= rt_hash_mask; h++) {
- if (h < s_h) continue;
- if (h > s_h)
- s_idx = 0;
+ for (h = s_h; h <= rt_hash_mask; h++) {
rcu_read_lock_bh();
for (rt = rcu_dereference(rt_hash_table[h].chain), idx = 0; rt;
rt = rcu_dereference(rt->u.dst.rt_next), idx++) {
@@ -2644,6 +2646,7 @@ int ip_rt_dump(struct sk_buff *skb, struct netlink_callback *cb)
dst_release(xchg(&skb->dst, NULL));
}
rcu_read_unlock_bh();
+ s_idx = 0;
}
done:
@@ -2888,18 +2891,14 @@ static int ip_rt_acct_read(char *buffer, char **start, off_t offset,
offset /= sizeof(u32);
if (length > 0) {
- u32 *src = ((u32 *) IP_RT_ACCT_CPU(0)) + offset;
u32 *dst = (u32 *) buffer;
- /* Copy first cpu. */
*start = buffer;
- memcpy(dst, src, length);
+ memset(dst, 0, length);
- /* Add the other cpus in, one int at a time */
for_each_possible_cpu(i) {
unsigned int j;
-
- src = ((u32 *) IP_RT_ACCT_CPU(i)) + offset;
+ u32 *src = ((u32 *) IP_RT_ACCT_CPU(i)) + offset;
for (j = 0; j < length/4; j++)
dst[j] += src[j];
diff --git a/net/ipv4/sysctl_net_ipv4.c b/net/ipv4/sysctl_net_ipv4.c
index ffddd2b4535..bec6fe88065 100644
--- a/net/ipv4/sysctl_net_ipv4.c
+++ b/net/ipv4/sysctl_net_ipv4.c
@@ -191,7 +191,7 @@ static int sysctl_tcp_congestion_control(ctl_table *table, int __user *name,
tcp_get_default_congestion_control(val);
ret = sysctl_string(&tbl, name, nlen, oldval, oldlenp, newval, newlen);
- if (ret == 0 && newval && newlen)
+ if (ret == 1 && newval && newlen)
ret = tcp_set_default_congestion_control(val);
return ret;
}
diff --git a/net/ipv4/tcp_illinois.c b/net/ipv4/tcp_illinois.c
index 64f1cbaf96e..5aa5f5496d6 100644
--- a/net/ipv4/tcp_illinois.c
+++ b/net/ipv4/tcp_illinois.c
@@ -298,7 +298,7 @@ static u32 tcp_illinois_ssthresh(struct sock *sk)
struct illinois *ca = inet_csk_ca(sk);
/* Multiplicative decrease */
- return max((tp->snd_cwnd * ca->beta) >> BETA_SHIFT, 2U);
+ return max(tp->snd_cwnd - ((tp->snd_cwnd * ca->beta) >> BETA_SHIFT), 2U);
}
diff --git a/net/ipv4/tcp_input.c b/net/ipv4/tcp_input.c
index 0f0c1c9829a..b39f0d86e44 100644
--- a/net/ipv4/tcp_input.c
+++ b/net/ipv4/tcp_input.c
@@ -923,7 +923,7 @@ static void tcp_init_metrics(struct sock *sk)
}
if (dst_metric(dst, RTAX_RTTVAR) > tp->mdev) {
tp->mdev = dst_metric(dst, RTAX_RTTVAR);
- tp->mdev_max = tp->rttvar = max(tp->mdev, TCP_RTO_MIN);
+ tp->mdev_max = tp->rttvar = max(tp->mdev, tcp_rto_min(sk));
}
tcp_set_rto(sk);
tcp_bound_rto(sk);
@@ -2651,6 +2651,7 @@ static int tcp_clean_rtx_queue(struct sock *sk, s32 *seq_rtt_p,
u32 cnt = 0;
u32 reord = tp->packets_out;
s32 seq_rtt = -1;
+ s32 ca_seq_rtt = -1;
ktime_t last_ackt = net_invalid_timestamp();
while ((skb = tcp_write_queue_head(sk)) && skb != tcp_send_head(sk)) {
@@ -2659,6 +2660,7 @@ static int tcp_clean_rtx_queue(struct sock *sk, s32 *seq_rtt_p,
u32 packets_acked;
u8 sacked = scb->sacked;
+ /* Determine how many packets and what bytes were acked, tso and else */
if (after(scb->end_seq, tp->snd_una)) {
if (tcp_skb_pcount(skb) == 1 ||
!after(tp->snd_una, scb->seq))
@@ -2686,15 +2688,16 @@ static int tcp_clean_rtx_queue(struct sock *sk, s32 *seq_rtt_p,
if (sacked & TCPCB_SACKED_RETRANS)
tp->retrans_out -= packets_acked;
flag |= FLAG_RETRANS_DATA_ACKED;
+ ca_seq_rtt = -1;
seq_rtt = -1;
if ((flag & FLAG_DATA_ACKED) ||
(packets_acked > 1))
flag |= FLAG_NONHEAD_RETRANS_ACKED;
} else {
+ ca_seq_rtt = now - scb->when;
+ last_ackt = skb->tstamp;
if (seq_rtt < 0) {
- seq_rtt = now - scb->when;
- if (fully_acked)
- last_ackt = skb->tstamp;
+ seq_rtt = ca_seq_rtt;
}
if (!(sacked & TCPCB_SACKED_ACKED))
reord = min(cnt, reord);
@@ -2709,10 +2712,10 @@ static int tcp_clean_rtx_queue(struct sock *sk, s32 *seq_rtt_p,
!before(end_seq, tp->snd_up))
tp->urg_mode = 0;
} else {
+ ca_seq_rtt = now - scb->when;
+ last_ackt = skb->tstamp;
if (seq_rtt < 0) {
- seq_rtt = now - scb->when;
- if (fully_acked)
- last_ackt = skb->tstamp;
+ seq_rtt = ca_seq_rtt;
}
reord = min(cnt, reord);
}
@@ -2772,8 +2775,8 @@ static int tcp_clean_rtx_queue(struct sock *sk, s32 *seq_rtt_p,
net_invalid_timestamp()))
rtt_us = ktime_us_delta(ktime_get_real(),
last_ackt);
- else if (seq_rtt > 0)
- rtt_us = jiffies_to_usecs(seq_rtt);
+ else if (ca_seq_rtt > 0)
+ rtt_us = jiffies_to_usecs(ca_seq_rtt);
}
ca_ops->pkts_acked(sk, pkts_acked, rtt_us);
@@ -3003,17 +3006,13 @@ static int tcp_process_frto(struct sock *sk, int flag)
}
if (tp->frto_counter == 1) {
- /* Sending of the next skb must be allowed or no F-RTO */
- if (!tcp_send_head(sk) ||
- after(TCP_SKB_CB(tcp_send_head(sk))->end_seq,
- tp->snd_una + tp->snd_wnd)) {
- tcp_enter_frto_loss(sk, (tp->frto_counter == 1 ? 2 : 3),
- flag);
- return 1;
- }
-
+ /* tcp_may_send_now needs to see updated state */
tp->snd_cwnd = tcp_packets_in_flight(tp) + 2;
tp->frto_counter = 2;
+
+ if (!tcp_may_send_now(sk))
+ tcp_enter_frto_loss(sk, 2, flag);
+
return 1;
} else {
switch (sysctl_tcp_frto_response) {
@@ -3069,6 +3068,7 @@ static int tcp_ack(struct sock *sk, struct sk_buff *skb, int flag)
}
prior_fackets = tp->fackets_out;
+ prior_in_flight = tcp_packets_in_flight(tp);
if (!(flag&FLAG_SLOWPATH) && after(ack, prior_snd_una)) {
/* Window is constant, pure forward advance.
@@ -3108,8 +3108,6 @@ static int tcp_ack(struct sock *sk, struct sk_buff *skb, int flag)
if (!prior_packets)
goto no_queue;
- prior_in_flight = tcp_packets_in_flight(tp);
-
/* See if we can take anything off of the retransmit queue. */
flag |= tcp_clean_rtx_queue(sk, &seq_rtt, prior_fackets);
diff --git a/net/ipv4/tcp_ipv4.c b/net/ipv4/tcp_ipv4.c
index e566f3c6767..652c32368cc 100644
--- a/net/ipv4/tcp_ipv4.c
+++ b/net/ipv4/tcp_ipv4.c
@@ -900,8 +900,7 @@ int tcp_v4_md5_do_add(struct sock *sk, __be32 addr,
sizeof(*keys) * md5sig->entries4);
/* Free old key list, and reference new one */
- if (md5sig->keys4)
- kfree(md5sig->keys4);
+ kfree(md5sig->keys4);
md5sig->keys4 = keys;
md5sig->alloced4++;
}
@@ -939,10 +938,10 @@ int tcp_v4_md5_do_del(struct sock *sk, __be32 addr)
tp->md5sig_info->alloced4 = 0;
} else if (tp->md5sig_info->entries4 != i) {
/* Need to do some manipulation */
- memcpy(&tp->md5sig_info->keys4[i],
- &tp->md5sig_info->keys4[i+1],
- (tp->md5sig_info->entries4 - i) *
- sizeof(struct tcp4_md5sig_key));
+ memmove(&tp->md5sig_info->keys4[i],
+ &tp->md5sig_info->keys4[i+1],
+ (tp->md5sig_info->entries4 - i) *
+ sizeof(struct tcp4_md5sig_key));
}
tcp_free_md5sig_pool();
return 0;
diff --git a/net/ipv4/tcp_output.c b/net/ipv4/tcp_output.c
index 324b4207254..f4c1eef89af 100644
--- a/net/ipv4/tcp_output.c
+++ b/net/ipv4/tcp_output.c
@@ -1162,8 +1162,7 @@ int tcp_may_send_now(struct sock *sk)
return (skb &&
tcp_snd_test(sk, skb, tcp_current_mss(sk, 1),
(tcp_skb_is_last(sk, skb) ?
- TCP_NAGLE_PUSH :
- tp->nonagle)));
+ tp->nonagle : TCP_NAGLE_PUSH)));
}
/* Trim TSO SKB to LEN bytes, put the remaining data into a new packet
@@ -1295,6 +1294,7 @@ static int tcp_mtu_probe(struct sock *sk)
struct sk_buff *skb, *nskb, *next;
int len;
int probe_size;
+ int size_needed;
unsigned int pif;
int copy;
int mss_now;
@@ -1313,27 +1313,20 @@ static int tcp_mtu_probe(struct sock *sk)
/* Very simple search strategy: just double the MSS. */
mss_now = tcp_current_mss(sk, 0);
probe_size = 2*tp->mss_cache;
+ size_needed = probe_size + (tp->reordering + 1) * tp->mss_cache;
if (probe_size > tcp_mtu_to_mss(sk, icsk->icsk_mtup.search_high)) {
/* TODO: set timer for probe_converge_event */
return -1;
}
/* Have enough data in the send queue to probe? */
- len = 0;
- if ((skb = tcp_send_head(sk)) == NULL)
- return -1;
- while ((len += skb->len) < probe_size && !tcp_skb_is_last(sk, skb))
- skb = tcp_write_queue_next(sk, skb);
- if (len < probe_size)
+ if (tp->write_seq - tp->snd_nxt < size_needed)
return -1;
- /* Receive window check. */
- if (after(TCP_SKB_CB(skb)->seq + probe_size, tp->snd_una + tp->snd_wnd)) {
- if (tp->snd_wnd < probe_size)
- return -1;
- else
- return 0;
- }
+ if (tp->snd_wnd < size_needed)
+ return -1;
+ if (after(tp->snd_nxt + size_needed, tp->snd_una + tp->snd_wnd))
+ return 0;
/* Do we need to wait to drain cwnd? */
pif = tcp_packets_in_flight(tp);
@@ -1352,7 +1345,6 @@ static int tcp_mtu_probe(struct sock *sk)
skb = tcp_send_head(sk);
tcp_insert_write_queue_before(nskb, skb, sk);
- tcp_advance_send_head(sk, skb);
TCP_SKB_CB(nskb)->seq = TCP_SKB_CB(skb)->seq;
TCP_SKB_CB(nskb)->end_seq = TCP_SKB_CB(skb)->seq + probe_size;
diff --git a/net/ipv6/addrconf.c b/net/ipv6/addrconf.c
index 1bd8d818f8e..e8c347579da 100644
--- a/net/ipv6/addrconf.c
+++ b/net/ipv6/addrconf.c
@@ -967,7 +967,7 @@ int ipv6_dev_get_saddr(struct net_device *daddr_dev,
if (unlikely(score.addr_type == IPV6_ADDR_ANY ||
score.addr_type & IPV6_ADDR_MULTICAST)) {
LIMIT_NETDEBUG(KERN_DEBUG
- "ADDRCONF: unspecified / multicast address"
+ "ADDRCONF: unspecified / multicast address "
"assigned as unicast address on %s",
dev->name);
continue;
@@ -2293,6 +2293,9 @@ static int addrconf_notify(struct notifier_block *this, unsigned long event,
break;
}
+ if (!idev && dev->mtu >= IPV6_MIN_MTU)
+ idev = ipv6_add_dev(dev);
+
if (idev)
idev->if_flags |= IF_READY;
} else {
@@ -2357,12 +2360,18 @@ static int addrconf_notify(struct notifier_block *this, unsigned long event,
break;
case NETDEV_CHANGEMTU:
- if ( idev && dev->mtu >= IPV6_MIN_MTU) {
+ if (idev && dev->mtu >= IPV6_MIN_MTU) {
rt6_mtu_change(dev, dev->mtu);
idev->cnf.mtu6 = dev->mtu;
break;
}
+ if (!idev && dev->mtu >= IPV6_MIN_MTU) {
+ idev = ipv6_add_dev(dev);
+ if (idev)
+ break;
+ }
+
/* MTU falled under IPV6_MIN_MTU. Stop IPv6 on this interface. */
case NETDEV_DOWN:
diff --git a/net/ipv6/datagram.c b/net/ipv6/datagram.c
index 2ed689ac449..5d4245ab418 100644
--- a/net/ipv6/datagram.c
+++ b/net/ipv6/datagram.c
@@ -123,11 +123,11 @@ ipv4_connected:
goto out;
}
sk->sk_bound_dev_if = usin->sin6_scope_id;
- if (!sk->sk_bound_dev_if &&
- (addr_type & IPV6_ADDR_MULTICAST))
- fl.oif = np->mcast_oif;
}
+ if (!sk->sk_bound_dev_if && (addr_type & IPV6_ADDR_MULTICAST))
+ sk->sk_bound_dev_if = np->mcast_oif;
+
/* Connect to link-local address requires an interface */
if (!sk->sk_bound_dev_if) {
err = -EINVAL;
diff --git a/net/ipv6/esp6.c b/net/ipv6/esp6.c
index 7db66f10e00..44405325467 100644
--- a/net/ipv6/esp6.c
+++ b/net/ipv6/esp6.c
@@ -230,6 +230,12 @@ static int esp6_input(struct xfrm_state *x, struct sk_buff *skb)
}
/* ... check padding bits here. Silly. :-) */
+ /* RFC4303: Drop dummy packets without any error */
+ if (nexthdr[1] == IPPROTO_NONE) {
+ ret = -EINVAL;
+ goto out;
+ }
+
pskb_trim(skb, skb->len - alen - padlen - 2);
ret = nexthdr[1];
}
diff --git a/net/ipv6/ip6_output.c b/net/ipv6/ip6_output.c
index 86e1835ce4e..6338a9c1aa1 100644
--- a/net/ipv6/ip6_output.c
+++ b/net/ipv6/ip6_output.c
@@ -933,6 +933,8 @@ static int ip6_dst_lookup_tail(struct sock *sk,
return 0;
out_err_release:
+ if (err == -ENETUNREACH)
+ IP6_INC_STATS_BH(NULL, IPSTATS_MIB_OUTNOROUTES);
dst_release(*dst);
*dst = NULL;
return err;
diff --git a/net/ipv6/ipv6_sockglue.c b/net/ipv6/ipv6_sockglue.c
index 1334fc174bc..8c5f80fd03a 100644
--- a/net/ipv6/ipv6_sockglue.c
+++ b/net/ipv6/ipv6_sockglue.c
@@ -1046,7 +1046,7 @@ static int do_ipv6_getsockopt(struct sock *sk, int level, int optname,
break;
default:
- return -EINVAL;
+ return -ENOPROTOOPT;
}
len = min_t(unsigned int, sizeof(int), len);
if(put_user(len, optlen))
@@ -1069,9 +1069,8 @@ int ipv6_getsockopt(struct sock *sk, int level, int optname,
err = do_ipv6_getsockopt(sk, level, optname, optval, optlen);
#ifdef CONFIG_NETFILTER
- /* we need to exclude all possible EINVALs except default case */
- if (err == -EINVAL && optname != IPV6_ADDRFORM &&
- optname != MCAST_MSFILTER) {
+ /* we need to exclude all possible ENOPROTOOPTs except default case */
+ if (err == -ENOPROTOOPT && optname != IPV6_2292PKTOPTIONS) {
int len;
if (get_user(len, optlen))
@@ -1108,9 +1107,8 @@ int compat_ipv6_getsockopt(struct sock *sk, int level, int optname,
err = do_ipv6_getsockopt(sk, level, optname, optval, optlen);
#ifdef CONFIG_NETFILTER
- /* we need to exclude all possible EINVALs except default case */
- if (err == -EINVAL && optname != IPV6_ADDRFORM &&
- optname != MCAST_MSFILTER) {
+ /* we need to exclude all possible ENOPROTOOPTs except default case */
+ if (err == -ENOPROTOOPT && optname != IPV6_2292PKTOPTIONS) {
int len;
if (get_user(len, optlen))
diff --git a/net/ipv6/ndisc.c b/net/ipv6/ndisc.c
index 67997a74ddc..777ed733b2d 100644
--- a/net/ipv6/ndisc.c
+++ b/net/ipv6/ndisc.c
@@ -612,7 +612,7 @@ void ndisc_send_rs(struct net_device *dev, struct in6_addr *saddr,
* optimistic addresses, but we may send the solicitation
* if we don't include the sllao. So here we check
* if our address is optimistic, and if so, we
- * supress the inclusion of the sllao.
+ * suppress the inclusion of the sllao.
*/
if (send_sllao) {
struct inet6_ifaddr *ifp = ipv6_get_ifaddr(saddr, dev, 1);
diff --git a/net/ipv6/tcp_ipv6.c b/net/ipv6/tcp_ipv6.c
index 3aad861975a..93980c3b83e 100644
--- a/net/ipv6/tcp_ipv6.c
+++ b/net/ipv6/tcp_ipv6.c
@@ -581,7 +581,10 @@ static int tcp_v6_md5_do_add(struct sock *sk, struct in6_addr *peer,
}
sk->sk_route_caps &= ~NETIF_F_GSO_MASK;
}
- tcp_alloc_md5sig_pool();
+ if (tcp_alloc_md5sig_pool() == NULL) {
+ kfree(newkey);
+ return -ENOMEM;
+ }
if (tp->md5sig_info->alloced6 == tp->md5sig_info->entries6) {
keys = kmalloc((sizeof (tp->md5sig_info->keys6[0]) *
(tp->md5sig_info->entries6 + 1)), GFP_ATOMIC);
@@ -634,10 +637,6 @@ static int tcp_v6_md5_do_del(struct sock *sk, struct in6_addr *peer)
kfree(tp->md5sig_info->keys6);
tp->md5sig_info->keys6 = NULL;
tp->md5sig_info->alloced6 = 0;
-
- tcp_free_md5sig_pool();
-
- return 0;
} else {
/* shrink the database */
if (tp->md5sig_info->entries6 != i)
@@ -646,6 +645,8 @@ static int tcp_v6_md5_do_del(struct sock *sk, struct in6_addr *peer)
(tp->md5sig_info->entries6 - i)
* sizeof (tp->md5sig_info->keys6[0]));
}
+ tcp_free_md5sig_pool();
+ return 0;
}
}
return -ENOENT;
diff --git a/net/ipv6/xfrm6_policy.c b/net/ipv6/xfrm6_policy.c
index 82e27b80d07..b8e9eb445d7 100644
--- a/net/ipv6/xfrm6_policy.c
+++ b/net/ipv6/xfrm6_policy.c
@@ -233,7 +233,7 @@ __xfrm6_bundle_create(struct xfrm_policy *policy, struct xfrm_state **xfrm, int
dst_prev->output = dst_prev->xfrm->outer_mode->afinfo->output;
/* Sheit... I remember I did this right. Apparently,
* it was magically lost, so this code needs audit */
- x->u.rt6.rt6i_flags = rt0->rt6i_flags&(RTCF_BROADCAST|RTCF_MULTICAST|RTCF_LOCAL);
+ x->u.rt6.rt6i_flags = rt0->rt6i_flags&(RTF_ANYCAST|RTF_LOCAL);
x->u.rt6.rt6i_metric = rt0->rt6i_metric;
x->u.rt6.rt6i_node = rt0->rt6i_node;
x->u.rt6.rt6i_gateway = rt0->rt6i_gateway;
diff --git a/net/irda/af_irda.c b/net/irda/af_irda.c
index 48ce59a6e02..d5e4dd75200 100644
--- a/net/irda/af_irda.c
+++ b/net/irda/af_irda.c
@@ -1118,8 +1118,6 @@ static int irda_create(struct net *net, struct socket *sock, int protocol)
self->max_sdu_size_rx = TTP_SAR_UNBOUND;
break;
default:
- IRDA_ERROR("%s: protocol not supported!\n",
- __FUNCTION__);
return -ESOCKTNOSUPPORT;
}
break;
diff --git a/net/irda/ircomm/ircomm_param.c b/net/irda/ircomm/ircomm_param.c
index e5e4792a031..598dcbe4a50 100644
--- a/net/irda/ircomm/ircomm_param.c
+++ b/net/irda/ircomm/ircomm_param.c
@@ -496,7 +496,7 @@ static int ircomm_param_poll(void *instance, irda_param_t *param, int get)
IRDA_ASSERT(self != NULL, return -1;);
IRDA_ASSERT(self->magic == IRCOMM_TTY_MAGIC, return -1;);
- /* Poll parameters are always of lenght 0 (just a signal) */
+ /* Poll parameters are always of length 0 (just a signal) */
if (!get) {
/* Respond with DTE line settings */
ircomm_param_request(self, IRCOMM_DTE, TRUE);
diff --git a/net/irda/ircomm/ircomm_tty.c b/net/irda/ircomm/ircomm_tty.c
index 1120b150e21..be627e1f04d 100644
--- a/net/irda/ircomm/ircomm_tty.c
+++ b/net/irda/ircomm/ircomm_tty.c
@@ -1245,6 +1245,7 @@ static void ircomm_tty_flow_indication(void *instance, void *sap,
self->flow = cmd;
}
+#ifdef CONFIG_PROC_FS
static int ircomm_tty_line_info(struct ircomm_tty_cb *self, char *buf)
{
int ret=0;
@@ -1354,7 +1355,6 @@ static int ircomm_tty_line_info(struct ircomm_tty_cb *self, char *buf)
*
*
*/
-#ifdef CONFIG_PROC_FS
static int ircomm_tty_read_proc(char *buf, char **start, off_t offset, int len,
int *eof, void *unused)
{
diff --git a/net/irda/iriap.c b/net/irda/iriap.c
index dc5e34a0162..a86a5d83786 100644
--- a/net/irda/iriap.c
+++ b/net/irda/iriap.c
@@ -928,7 +928,7 @@ void iriap_call_indication(struct iriap_cb *self, struct sk_buff *skb)
opcode = fp[0];
if (~opcode & 0x80) {
- IRDA_WARNING("%s: IrIAS multiframe commands or results"
+ IRDA_WARNING("%s: IrIAS multiframe commands or results "
"is not implemented yet!\n", __FUNCTION__);
return;
}
diff --git a/net/irda/irlan/irlan_eth.c b/net/irda/irlan/irlan_eth.c
index 7f9c8542e5f..1ab91f787cc 100644
--- a/net/irda/irlan/irlan_eth.c
+++ b/net/irda/irlan/irlan_eth.c
@@ -296,6 +296,7 @@ void irlan_eth_flow_indication(void *instance, void *sap, LOCAL_FLOW flow)
*/
void irlan_eth_send_gratuitous_arp(struct net_device *dev)
{
+#ifdef CONFIG_INET
struct in_device *in_dev;
/*
@@ -303,7 +304,6 @@ void irlan_eth_send_gratuitous_arp(struct net_device *dev)
* is useful if we have changed access points on the same
* subnet.
*/
-#ifdef CONFIG_INET
IRDA_DEBUG(4, "IrLAN: Sending gratuitous ARP\n");
rcu_read_lock();
in_dev = __in_dev_get_rcu(dev);
@@ -342,7 +342,7 @@ static void irlan_eth_set_multicast_list(struct net_device *dev)
if (dev->flags & IFF_PROMISC) {
/* Enable promiscuous mode */
- IRDA_WARNING("Promiscous mode not implemented by IrLAN!\n");
+ IRDA_WARNING("Promiscuous mode not implemented by IrLAN!\n");
}
else if ((dev->flags & IFF_ALLMULTI) || dev->mc_count > HW_MAX_ADDRS) {
/* Disable promiscuous mode, use normal mode. */
diff --git a/net/irda/irlap_frame.c b/net/irda/irlap_frame.c
index 4f3764546b2..7c132d6342a 100644
--- a/net/irda/irlap_frame.c
+++ b/net/irda/irlap_frame.c
@@ -144,7 +144,7 @@ void irlap_send_snrm_frame(struct irlap_cb *self, struct qos_info *qos)
frame->control = SNRM_CMD | PF_BIT;
/*
- * If we are establishing a connection then insert QoS paramerters
+ * If we are establishing a connection then insert QoS parameters
*/
if (qos) {
skb_put(tx_skb, 9); /* 25 left */
diff --git a/net/irda/irlmp.c b/net/irda/irlmp.c
index cedff8068fb..f24cb755908 100644
--- a/net/irda/irlmp.c
+++ b/net/irda/irlmp.c
@@ -353,6 +353,7 @@ void irlmp_unregister_link(__u32 saddr)
/* Final cleanup */
del_timer(&link->idle_timer);
link->magic = 0;
+ hashbin_delete(link->lsaps, (FREE_FUNC) __irlmp_close_lsap);
kfree(link);
}
}
diff --git a/net/irda/parameters.c b/net/irda/parameters.c
index 2627dad7cd8..722bbe044d9 100644
--- a/net/irda/parameters.c
+++ b/net/irda/parameters.c
@@ -133,7 +133,7 @@ static int irda_insert_integer(void *self, __u8 *buf, int len, __u8 pi,
int err;
p.pi = pi; /* In case handler needs to know */
- p.pl = type & PV_MASK; /* The integer type codes the lenght as well */
+ p.pl = type & PV_MASK; /* The integer type codes the length as well */
p.pv.i = 0; /* Clear value */
/* Call handler for this parameter */
@@ -142,7 +142,7 @@ static int irda_insert_integer(void *self, __u8 *buf, int len, __u8 pi,
return err;
/*
- * If parameter lenght is still 0, then (1) this is an any length
+ * If parameter length is still 0, then (1) this is an any length
* integer, and (2) the handler function does not care which length
* we choose to use, so we pick the one the gives the fewest bytes.
*/
@@ -206,11 +206,11 @@ static int irda_extract_integer(void *self, __u8 *buf, int len, __u8 pi,
{
irda_param_t p;
int n = 0;
- int extract_len; /* Real lenght we extract */
+ int extract_len; /* Real length we extract */
int err;
p.pi = pi; /* In case handler needs to know */
- p.pl = buf[1]; /* Extract lenght of value */
+ p.pl = buf[1]; /* Extract length of value */
p.pv.i = 0; /* Clear value */
extract_len = p.pl; /* Default : extract all */
@@ -297,7 +297,7 @@ static int irda_extract_string(void *self, __u8 *buf, int len, __u8 pi,
IRDA_DEBUG(2, "%s()\n", __FUNCTION__);
p.pi = pi; /* In case handler needs to know */
- p.pl = buf[1]; /* Extract lenght of value */
+ p.pl = buf[1]; /* Extract length of value */
IRDA_DEBUG(2, "%s(), pi=%#x, pl=%d\n", __FUNCTION__,
p.pi, p.pl);
@@ -339,7 +339,7 @@ static int irda_extract_octseq(void *self, __u8 *buf, int len, __u8 pi,
irda_param_t p;
p.pi = pi; /* In case handler needs to know */
- p.pl = buf[1]; /* Extract lenght of value */
+ p.pl = buf[1]; /* Extract length of value */
/* Check if buffer is long enough for parsing */
if (len < (2+p.pl)) {
@@ -463,7 +463,7 @@ int irda_param_insert(void *self, __u8 pi, __u8 *buf, int len,
int n = 0;
IRDA_ASSERT(buf != NULL, return ret;);
- IRDA_ASSERT(info != 0, return ret;);
+ IRDA_ASSERT(info != NULL, return ret;);
pi_minor = pi & info->pi_mask;
pi_major = pi >> info->pi_major_offset;
@@ -517,7 +517,7 @@ static int irda_param_extract(void *self, __u8 *buf, int len,
int n = 0;
IRDA_ASSERT(buf != NULL, return ret;);
- IRDA_ASSERT(info != 0, return ret;);
+ IRDA_ASSERT(info != NULL, return ret;);
pi_minor = buf[n] & info->pi_mask;
pi_major = buf[n] >> info->pi_major_offset;
@@ -570,7 +570,7 @@ int irda_param_extract_all(void *self, __u8 *buf, int len,
int n = 0;
IRDA_ASSERT(buf != NULL, return ret;);
- IRDA_ASSERT(info != 0, return ret;);
+ IRDA_ASSERT(info != NULL, return ret;);
/*
* Parse all parameters. Each parameter must be at least two bytes
diff --git a/net/irda/wrapper.c b/net/irda/wrapper.c
index e71286768a4..c246983308b 100644
--- a/net/irda/wrapper.c
+++ b/net/irda/wrapper.c
@@ -238,7 +238,7 @@ async_bump(struct net_device *dev,
skb_reserve(newskb, 1);
if(docopy) {
- /* Copy data without CRC (lenght already checked) */
+ /* Copy data without CRC (length already checked) */
skb_copy_to_linear_data(newskb, rx_buff->data,
rx_buff->len - 2);
/* Deliver this skb */
diff --git a/net/iucv/iucv.c b/net/iucv/iucv.c
index a2f5a6ea389..7698f6c459d 100644
--- a/net/iucv/iucv.c
+++ b/net/iucv/iucv.c
@@ -97,7 +97,7 @@ struct iucv_irq_list {
struct iucv_irq_data data;
};
-static struct iucv_irq_data *iucv_irq_data;
+static struct iucv_irq_data *iucv_irq_data[NR_CPUS];
static cpumask_t iucv_buffer_cpumask = CPU_MASK_NONE;
static cpumask_t iucv_irq_cpumask = CPU_MASK_NONE;
@@ -277,7 +277,7 @@ union iucv_param {
/*
* Anchor for per-cpu IUCV command parameter block.
*/
-static union iucv_param *iucv_param;
+static union iucv_param *iucv_param[NR_CPUS];
/**
* iucv_call_b2f0
@@ -356,7 +356,7 @@ static void iucv_allow_cpu(void *data)
* 0x10 - Flag to allow priority message completion interrupts
* 0x08 - Flag to allow IUCV control interrupts
*/
- parm = percpu_ptr(iucv_param, smp_processor_id());
+ parm = iucv_param[cpu];
memset(parm, 0, sizeof(union iucv_param));
parm->set_mask.ipmask = 0xf8;
iucv_call_b2f0(IUCV_SETMASK, parm);
@@ -377,7 +377,7 @@ static void iucv_block_cpu(void *data)
union iucv_param *parm;
/* Disable all iucv interrupts. */
- parm = percpu_ptr(iucv_param, smp_processor_id());
+ parm = iucv_param[cpu];
memset(parm, 0, sizeof(union iucv_param));
iucv_call_b2f0(IUCV_SETMASK, parm);
@@ -401,9 +401,9 @@ static void iucv_declare_cpu(void *data)
return;
/* Declare interrupt buffer. */
- parm = percpu_ptr(iucv_param, cpu);
+ parm = iucv_param[cpu];
memset(parm, 0, sizeof(union iucv_param));
- parm->db.ipbfadr1 = virt_to_phys(percpu_ptr(iucv_irq_data, cpu));
+ parm->db.ipbfadr1 = virt_to_phys(iucv_irq_data[cpu]);
rc = iucv_call_b2f0(IUCV_DECLARE_BUFFER, parm);
if (rc) {
char *err = "Unknown";
@@ -458,7 +458,7 @@ static void iucv_retrieve_cpu(void *data)
iucv_block_cpu(NULL);
/* Retrieve interrupt buffer. */
- parm = percpu_ptr(iucv_param, cpu);
+ parm = iucv_param[cpu];
iucv_call_b2f0(IUCV_RETRIEVE_BUFFER, parm);
/* Clear indication that an iucv buffer exists for this cpu. */
@@ -558,22 +558,23 @@ static int __cpuinit iucv_cpu_notify(struct notifier_block *self,
switch (action) {
case CPU_UP_PREPARE:
case CPU_UP_PREPARE_FROZEN:
- if (!percpu_populate(iucv_irq_data,
- sizeof(struct iucv_irq_data),
- GFP_KERNEL|GFP_DMA, cpu))
+ iucv_irq_data[cpu] = kmalloc_node(sizeof(struct iucv_irq_data),
+ GFP_KERNEL|GFP_DMA, cpu_to_node(cpu));
+ if (!iucv_irq_data[cpu])
return NOTIFY_BAD;
- if (!percpu_populate(iucv_param, sizeof(union iucv_param),
- GFP_KERNEL|GFP_DMA, cpu)) {
- percpu_depopulate(iucv_irq_data, cpu);
+ iucv_param[cpu] = kmalloc_node(sizeof(union iucv_param),
+ GFP_KERNEL|GFP_DMA, cpu_to_node(cpu));
+ if (!iucv_param[cpu])
return NOTIFY_BAD;
- }
break;
case CPU_UP_CANCELED:
case CPU_UP_CANCELED_FROZEN:
case CPU_DEAD:
case CPU_DEAD_FROZEN:
- percpu_depopulate(iucv_param, cpu);
- percpu_depopulate(iucv_irq_data, cpu);
+ kfree(iucv_param[cpu]);
+ iucv_param[cpu] = NULL;
+ kfree(iucv_irq_data[cpu]);
+ iucv_irq_data[cpu] = NULL;
break;
case CPU_ONLINE:
case CPU_ONLINE_FROZEN:
@@ -612,7 +613,7 @@ static int iucv_sever_pathid(u16 pathid, u8 userdata[16])
{
union iucv_param *parm;
- parm = percpu_ptr(iucv_param, smp_processor_id());
+ parm = iucv_param[smp_processor_id()];
memset(parm, 0, sizeof(union iucv_param));
if (userdata)
memcpy(parm->ctrl.ipuser, userdata, sizeof(parm->ctrl.ipuser));
@@ -755,7 +756,7 @@ int iucv_path_accept(struct iucv_path *path, struct iucv_handler *handler,
local_bh_disable();
/* Prepare parameter block. */
- parm = percpu_ptr(iucv_param, smp_processor_id());
+ parm = iucv_param[smp_processor_id()];
memset(parm, 0, sizeof(union iucv_param));
parm->ctrl.ippathid = path->pathid;
parm->ctrl.ipmsglim = path->msglim;
@@ -799,7 +800,7 @@ int iucv_path_connect(struct iucv_path *path, struct iucv_handler *handler,
BUG_ON(in_atomic());
spin_lock_bh(&iucv_table_lock);
iucv_cleanup_queue();
- parm = percpu_ptr(iucv_param, smp_processor_id());
+ parm = iucv_param[smp_processor_id()];
memset(parm, 0, sizeof(union iucv_param));
parm->ctrl.ipmsglim = path->msglim;
parm->ctrl.ipflags1 = path->flags;
@@ -854,7 +855,7 @@ int iucv_path_quiesce(struct iucv_path *path, u8 userdata[16])
int rc;
local_bh_disable();
- parm = percpu_ptr(iucv_param, smp_processor_id());
+ parm = iucv_param[smp_processor_id()];
memset(parm, 0, sizeof(union iucv_param));
if (userdata)
memcpy(parm->ctrl.ipuser, userdata, sizeof(parm->ctrl.ipuser));
@@ -881,7 +882,7 @@ int iucv_path_resume(struct iucv_path *path, u8 userdata[16])
int rc;
local_bh_disable();
- parm = percpu_ptr(iucv_param, smp_processor_id());
+ parm = iucv_param[smp_processor_id()];
memset(parm, 0, sizeof(union iucv_param));
if (userdata)
memcpy(parm->ctrl.ipuser, userdata, sizeof(parm->ctrl.ipuser));
@@ -936,7 +937,7 @@ int iucv_message_purge(struct iucv_path *path, struct iucv_message *msg,
int rc;
local_bh_disable();
- parm = percpu_ptr(iucv_param, smp_processor_id());
+ parm = iucv_param[smp_processor_id()];
memset(parm, 0, sizeof(union iucv_param));
parm->purge.ippathid = path->pathid;
parm->purge.ipmsgid = msg->id;
@@ -1003,7 +1004,7 @@ int iucv_message_receive(struct iucv_path *path, struct iucv_message *msg,
}
local_bh_disable();
- parm = percpu_ptr(iucv_param, smp_processor_id());
+ parm = iucv_param[smp_processor_id()];
memset(parm, 0, sizeof(union iucv_param));
parm->db.ipbfadr1 = (u32)(addr_t) buffer;
parm->db.ipbfln1f = (u32) size;
@@ -1040,7 +1041,7 @@ int iucv_message_reject(struct iucv_path *path, struct iucv_message *msg)
int rc;
local_bh_disable();
- parm = percpu_ptr(iucv_param, smp_processor_id());
+ parm = iucv_param[smp_processor_id()];
memset(parm, 0, sizeof(union iucv_param));
parm->db.ippathid = path->pathid;
parm->db.ipmsgid = msg->id;
@@ -1074,7 +1075,7 @@ int iucv_message_reply(struct iucv_path *path, struct iucv_message *msg,
int rc;
local_bh_disable();
- parm = percpu_ptr(iucv_param, smp_processor_id());
+ parm = iucv_param[smp_processor_id()];
memset(parm, 0, sizeof(union iucv_param));
if (flags & IUCV_IPRMDATA) {
parm->dpl.ippathid = path->pathid;
@@ -1118,7 +1119,7 @@ int iucv_message_send(struct iucv_path *path, struct iucv_message *msg,
int rc;
local_bh_disable();
- parm = percpu_ptr(iucv_param, smp_processor_id());
+ parm = iucv_param[smp_processor_id()];
memset(parm, 0, sizeof(union iucv_param));
if (flags & IUCV_IPRMDATA) {
/* Message of 8 bytes can be placed into the parameter list. */
@@ -1172,7 +1173,7 @@ int iucv_message_send2way(struct iucv_path *path, struct iucv_message *msg,
int rc;
local_bh_disable();
- parm = percpu_ptr(iucv_param, smp_processor_id());
+ parm = iucv_param[smp_processor_id()];
memset(parm, 0, sizeof(union iucv_param));
if (flags & IUCV_IPRMDATA) {
parm->dpl.ippathid = path->pathid;
@@ -1559,7 +1560,7 @@ static void iucv_external_interrupt(u16 code)
struct iucv_irq_data *p;
struct iucv_irq_list *work;
- p = percpu_ptr(iucv_irq_data, smp_processor_id());
+ p = iucv_irq_data[smp_processor_id()];
if (p->ippathid >= iucv_max_pathid) {
printk(KERN_WARNING "iucv_do_int: Got interrupt with "
"pathid %d > max_connections (%ld)\n",
@@ -1598,6 +1599,7 @@ static void iucv_external_interrupt(u16 code)
static int __init iucv_init(void)
{
int rc;
+ int cpu;
if (!MACHINE_IS_VM) {
rc = -EPROTONOSUPPORT;
@@ -1617,19 +1619,23 @@ static int __init iucv_init(void)
rc = PTR_ERR(iucv_root);
goto out_bus;
}
- /* Note: GFP_DMA used to get memory below 2G */
- iucv_irq_data = percpu_alloc(sizeof(struct iucv_irq_data),
- GFP_KERNEL|GFP_DMA);
- if (!iucv_irq_data) {
- rc = -ENOMEM;
- goto out_root;
- }
- /* Allocate parameter blocks. */
- iucv_param = percpu_alloc(sizeof(union iucv_param),
- GFP_KERNEL|GFP_DMA);
- if (!iucv_param) {
- rc = -ENOMEM;
- goto out_extint;
+
+ for_each_online_cpu(cpu) {
+ /* Note: GFP_DMA used to get memory below 2G */
+ iucv_irq_data[cpu] = kmalloc_node(sizeof(struct iucv_irq_data),
+ GFP_KERNEL|GFP_DMA, cpu_to_node(cpu));
+ if (!iucv_irq_data[cpu]) {
+ rc = -ENOMEM;
+ goto out_free;
+ }
+
+ /* Allocate parameter blocks. */
+ iucv_param[cpu] = kmalloc_node(sizeof(union iucv_param),
+ GFP_KERNEL|GFP_DMA, cpu_to_node(cpu));
+ if (!iucv_param[cpu]) {
+ rc = -ENOMEM;
+ goto out_free;
+ }
}
register_hotcpu_notifier(&iucv_cpu_notifier);
ASCEBC(iucv_error_no_listener, 16);
@@ -1638,9 +1644,13 @@ static int __init iucv_init(void)
iucv_available = 1;
return 0;
-out_extint:
- percpu_free(iucv_irq_data);
-out_root:
+out_free:
+ for_each_possible_cpu(cpu) {
+ kfree(iucv_param[cpu]);
+ iucv_param[cpu] = NULL;
+ kfree(iucv_irq_data[cpu]);
+ iucv_irq_data[cpu] = NULL;
+ }
s390_root_dev_unregister(iucv_root);
out_bus:
bus_unregister(&iucv_bus);
@@ -1658,6 +1668,7 @@ out:
static void __exit iucv_exit(void)
{
struct iucv_irq_list *p, *n;
+ int cpu;
spin_lock_irq(&iucv_queue_lock);
list_for_each_entry_safe(p, n, &iucv_task_queue, list)
@@ -1666,8 +1677,12 @@ static void __exit iucv_exit(void)
kfree(p);
spin_unlock_irq(&iucv_queue_lock);
unregister_hotcpu_notifier(&iucv_cpu_notifier);
- percpu_free(iucv_param);
- percpu_free(iucv_irq_data);
+ for_each_possible_cpu(cpu) {
+ kfree(iucv_param[cpu]);
+ iucv_param[cpu] = NULL;
+ kfree(iucv_irq_data[cpu]);
+ iucv_irq_data[cpu] = NULL;
+ }
s390_root_dev_unregister(iucv_root);
bus_unregister(&iucv_bus);
unregister_external_interrupt(0x4000, iucv_external_interrupt);
diff --git a/net/key/af_key.c b/net/key/af_key.c
index 10c89d47f68..26d5e63c4cc 100644
--- a/net/key/af_key.c
+++ b/net/key/af_key.c
@@ -1015,9 +1015,7 @@ static inline struct sk_buff *pfkey_xfrm_state2msg(struct xfrm_state *x)
{
struct sk_buff *skb;
- spin_lock_bh(&x->lock);
skb = __pfkey_xfrm_state2msg(x, 1, 3);
- spin_unlock_bh(&x->lock);
return skb;
}
@@ -1552,7 +1550,7 @@ static int pfkey_get(struct sock *sk, struct sk_buff *skb, struct sadb_msg *hdr,
out_hdr = (struct sadb_msg *) out_skb->data;
out_hdr->sadb_msg_version = hdr->sadb_msg_version;
- out_hdr->sadb_msg_type = SADB_DUMP;
+ out_hdr->sadb_msg_type = SADB_GET;
out_hdr->sadb_msg_satype = pfkey_proto2satype(proto);
out_hdr->sadb_msg_errno = 0;
out_hdr->sadb_msg_reserved = 0;
@@ -2786,12 +2784,22 @@ static struct sadb_msg *pfkey_get_base_msg(struct sk_buff *skb, int *errp)
static inline int aalg_tmpl_set(struct xfrm_tmpl *t, struct xfrm_algo_desc *d)
{
- return t->aalgos & (1 << d->desc.sadb_alg_id);
+ unsigned int id = d->desc.sadb_alg_id;
+
+ if (id >= sizeof(t->aalgos) * 8)
+ return 0;
+
+ return (t->aalgos >> id) & 1;
}
static inline int ealg_tmpl_set(struct xfrm_tmpl *t, struct xfrm_algo_desc *d)
{
- return t->ealgos & (1 << d->desc.sadb_alg_id);
+ unsigned int id = d->desc.sadb_alg_id;
+
+ if (id >= sizeof(t->ealgos) * 8)
+ return 0;
+
+ return (t->ealgos >> id) & 1;
}
static int count_ah_combs(struct xfrm_tmpl *t)
diff --git a/net/mac80211/ieee80211.c b/net/mac80211/ieee80211.c
index e0ee65a969b..6378850d858 100644
--- a/net/mac80211/ieee80211.c
+++ b/net/mac80211/ieee80211.c
@@ -216,6 +216,7 @@ static int ieee80211_open(struct net_device *dev)
res = local->ops->start(local_to_hw(local));
if (res)
return res;
+ ieee80211_hw_config(local);
}
switch (sdata->type) {
@@ -232,7 +233,6 @@ static int ieee80211_open(struct net_device *dev)
netif_tx_unlock_bh(local->mdev);
local->hw.conf.flags |= IEEE80211_CONF_RADIOTAP;
- ieee80211_hw_config(local);
}
break;
case IEEE80211_IF_TYPE_STA:
@@ -267,6 +267,17 @@ static int ieee80211_open(struct net_device *dev)
tasklet_enable(&local->tasklet);
}
+ /*
+ * set_multicast_list will be invoked by the networking core
+ * which will check whether any increments here were done in
+ * error and sync them down to the hardware as filter flags.
+ */
+ if (sdata->flags & IEEE80211_SDATA_ALLMULTI)
+ atomic_inc(&local->iff_allmultis);
+
+ if (sdata->flags & IEEE80211_SDATA_PROMISC)
+ atomic_inc(&local->iff_promiscs);
+
local->open_count++;
netif_start_queue(dev);
@@ -284,6 +295,18 @@ static int ieee80211_stop(struct net_device *dev)
netif_stop_queue(dev);
+ /*
+ * Don't count this interface for promisc/allmulti while it
+ * is down. dev_mc_unsync() will invoke set_multicast_list
+ * on the master interface which will sync these down to the
+ * hardware as filter flags.
+ */
+ if (sdata->flags & IEEE80211_SDATA_ALLMULTI)
+ atomic_dec(&local->iff_allmultis);
+
+ if (sdata->flags & IEEE80211_SDATA_PROMISC)
+ atomic_dec(&local->iff_promiscs);
+
dev_mc_unsync(local->mdev, dev);
/* down all dependent devices, that is VLANs */
@@ -311,8 +334,7 @@ static int ieee80211_stop(struct net_device *dev)
ieee80211_configure_filter(local);
netif_tx_unlock_bh(local->mdev);
- local->hw.conf.flags |= IEEE80211_CONF_RADIOTAP;
- ieee80211_hw_config(local);
+ local->hw.conf.flags &= ~IEEE80211_CONF_RADIOTAP;
}
break;
case IEEE80211_IF_TYPE_STA:
@@ -334,6 +356,11 @@ static int ieee80211_stop(struct net_device *dev)
cancel_delayed_work(&local->scan_work);
}
flush_workqueue(local->hw.workqueue);
+
+ sdata->u.sta.flags &= ~IEEE80211_STA_PRIVACY_INVOKED;
+ kfree(sdata->u.sta.extra_ie);
+ sdata->u.sta.extra_ie = NULL;
+ sdata->u.sta.extra_ie_len = 0;
/* fall through */
default:
conf.if_id = dev->ifindex;
@@ -366,8 +393,8 @@ static void ieee80211_set_multicast_list(struct net_device *dev)
allmulti = !!(dev->flags & IFF_ALLMULTI);
promisc = !!(dev->flags & IFF_PROMISC);
- sdata_allmulti = sdata->flags & IEEE80211_SDATA_ALLMULTI;
- sdata_promisc = sdata->flags & IEEE80211_SDATA_PROMISC;
+ sdata_allmulti = !!(sdata->flags & IEEE80211_SDATA_ALLMULTI);
+ sdata_promisc = !!(sdata->flags & IEEE80211_SDATA_PROMISC);
if (allmulti != sdata_allmulti) {
if (dev->flags & IFF_ALLMULTI)
@@ -400,7 +427,6 @@ static const struct header_ops ieee80211_header_ops = {
void ieee80211_if_setup(struct net_device *dev)
{
ether_setup(dev);
- dev->header_ops = &ieee80211_header_ops;
dev->hard_start_xmit = ieee80211_subif_start_xmit;
dev->wireless_handlers = &ieee80211_iw_handler_def;
dev->set_multicast_list = ieee80211_set_multicast_list;
diff --git a/net/mac80211/ieee80211_ioctl.c b/net/mac80211/ieee80211_ioctl.c
index 7027eed4d4a..308bbe4a133 100644
--- a/net/mac80211/ieee80211_ioctl.c
+++ b/net/mac80211/ieee80211_ioctl.c
@@ -591,7 +591,7 @@ static int ieee80211_ioctl_siwrate(struct net_device *dev,
sdata->bss->force_unicast_rateidx = -1;
if (rate->value < 0)
return 0;
- for (i=0; i< mode->num_rates; i++) {
+ for (i=0; i < mode->num_rates; i++) {
struct ieee80211_rate *rates = &mode->rates[i];
int this_rate = rates->rate;
@@ -599,10 +599,10 @@ static int ieee80211_ioctl_siwrate(struct net_device *dev,
sdata->bss->max_ratectrl_rateidx = i;
if (rate->fixed)
sdata->bss->force_unicast_rateidx = i;
- break;
+ return 0;
}
}
- return 0;
+ return -EINVAL;
}
static int ieee80211_ioctl_giwrate(struct net_device *dev,
diff --git a/net/mac80211/ieee80211_rate.c b/net/mac80211/ieee80211_rate.c
index 7254bd60983..c3f27839374 100644
--- a/net/mac80211/ieee80211_rate.c
+++ b/net/mac80211/ieee80211_rate.c
@@ -33,6 +33,7 @@ int ieee80211_rate_control_register(struct rate_control_ops *ops)
if (!strcmp(alg->ops->name, ops->name)) {
/* don't register an algorithm twice */
WARN_ON(1);
+ mutex_unlock(&rate_ctrl_mutex);
return -EALREADY;
}
}
@@ -59,11 +60,11 @@ void ieee80211_rate_control_unregister(struct rate_control_ops *ops)
list_for_each_entry(alg, &rate_ctrl_algs, list) {
if (alg->ops == ops) {
list_del(&alg->list);
+ kfree(alg);
break;
}
}
mutex_unlock(&rate_ctrl_mutex);
- kfree(alg);
}
EXPORT_SYMBOL(ieee80211_rate_control_unregister);
diff --git a/net/mac80211/ieee80211_sta.c b/net/mac80211/ieee80211_sta.c
index 015b3f879aa..bee8080f224 100644
--- a/net/mac80211/ieee80211_sta.c
+++ b/net/mac80211/ieee80211_sta.c
@@ -808,12 +808,8 @@ static void ieee80211_associated(struct net_device *dev,
sta_info_put(sta);
}
if (disassoc) {
- union iwreq_data wrqu;
- memset(wrqu.ap_addr.sa_data, 0, ETH_ALEN);
- wrqu.ap_addr.sa_family = ARPHRD_ETHER;
- wireless_send_event(dev, SIOCGIWAP, &wrqu, NULL);
- mod_timer(&ifsta->timer, jiffies +
- IEEE80211_MONITORING_INTERVAL + 30 * HZ);
+ ifsta->state = IEEE80211_DISABLED;
+ ieee80211_set_associated(dev, ifsta, 0);
} else {
mod_timer(&ifsta->timer, jiffies +
IEEE80211_MONITORING_INTERVAL);
@@ -2647,7 +2643,7 @@ void ieee80211_scan_completed(struct ieee80211_hw *hw)
local->sta_scanning = 0;
if (ieee80211_hw_config(local))
- printk(KERN_DEBUG "%s: failed to restore operational"
+ printk(KERN_DEBUG "%s: failed to restore operational "
"channel after scan\n", dev->name);
diff --git a/net/mac80211/rx.c b/net/mac80211/rx.c
index 428a9fcf57d..a7263fc476b 100644
--- a/net/mac80211/rx.c
+++ b/net/mac80211/rx.c
@@ -997,7 +997,7 @@ ieee80211_rx_h_drop_unencrypted(struct ieee80211_txrx_data *rx)
if (unlikely(!(rx->fc & IEEE80211_FCTL_PROTECTED) &&
(rx->fc & IEEE80211_FCTL_FTYPE) == IEEE80211_FTYPE_DATA &&
(rx->fc & IEEE80211_FCTL_STYPE) != IEEE80211_STYPE_NULLFUNC &&
- rx->sdata->drop_unencrypted &&
+ (rx->key || rx->sdata->drop_unencrypted) &&
(rx->sdata->eapol == 0 || !ieee80211_is_eapol(rx->skb)))) {
if (net_ratelimit())
printk(KERN_DEBUG "%s: RX non-WEP frame, but expected "
@@ -1443,6 +1443,7 @@ void __ieee80211_rx(struct ieee80211_hw *hw, struct sk_buff *skb,
struct ieee80211_sub_if_data *prev = NULL;
struct sk_buff *skb_new;
u8 *bssid;
+ int hdrlen;
/*
* key references and virtual interfaces are protected using RCU
@@ -1472,6 +1473,18 @@ void __ieee80211_rx(struct ieee80211_hw *hw, struct sk_buff *skb,
rx.fc = le16_to_cpu(hdr->frame_control);
type = rx.fc & IEEE80211_FCTL_FTYPE;
+ /*
+ * Drivers are required to align the payload data to a four-byte
+ * boundary, so the last two bits of the address where it starts
+ * may not be set. The header is required to be directly before
+ * the payload data, padding like atheros hardware adds which is
+ * inbetween the 802.11 header and the payload is not supported,
+ * the driver is required to move the 802.11 header further back
+ * in that case.
+ */
+ hdrlen = ieee80211_get_hdrlen(rx.fc);
+ WARN_ON_ONCE(((unsigned long)(skb->data + hdrlen)) & 3);
+
if (type == IEEE80211_FTYPE_DATA || type == IEEE80211_FTYPE_MGMT)
local->dot11ReceivedFragmentCount++;
diff --git a/net/mac80211/sta_info.c b/net/mac80211/sta_info.c
index e8491554a5d..cfd8ee9adad 100644
--- a/net/mac80211/sta_info.c
+++ b/net/mac80211/sta_info.c
@@ -14,6 +14,7 @@
#include <linux/slab.h>
#include <linux/skbuff.h>
#include <linux/if_arp.h>
+#include <linux/timer.h>
#include <net/mac80211.h>
#include "ieee80211_i.h"
@@ -306,7 +307,8 @@ static void sta_info_cleanup(unsigned long data)
}
read_unlock_bh(&local->sta_lock);
- local->sta_cleanup.expires = jiffies + STA_INFO_CLEANUP_INTERVAL;
+ local->sta_cleanup.expires =
+ round_jiffies(jiffies + STA_INFO_CLEANUP_INTERVAL);
add_timer(&local->sta_cleanup);
}
@@ -345,7 +347,8 @@ void sta_info_init(struct ieee80211_local *local)
INIT_LIST_HEAD(&local->sta_list);
init_timer(&local->sta_cleanup);
- local->sta_cleanup.expires = jiffies + STA_INFO_CLEANUP_INTERVAL;
+ local->sta_cleanup.expires =
+ round_jiffies(jiffies + STA_INFO_CLEANUP_INTERVAL);
local->sta_cleanup.data = (unsigned long) local;
local->sta_cleanup.function = sta_info_cleanup;
diff --git a/net/mac80211/wep.c b/net/mac80211/wep.c
index 9bf0e1cc530..b5f3413403b 100644
--- a/net/mac80211/wep.c
+++ b/net/mac80211/wep.c
@@ -265,7 +265,8 @@ int ieee80211_wep_decrypt(struct ieee80211_local *local, struct sk_buff *skb,
if (ieee80211_wep_decrypt_data(local->wep_rx_tfm, rc4key, klen,
skb->data + hdrlen + WEP_IV_LEN,
len)) {
- printk(KERN_DEBUG "WEP decrypt failed (ICV)\n");
+ if (net_ratelimit())
+ printk(KERN_DEBUG "WEP decrypt failed (ICV)\n");
ret = -1;
}
diff --git a/net/netfilter/nf_conntrack_core.c b/net/netfilter/nf_conntrack_core.c
index 000c2fb462d..a4d5cdeb011 100644
--- a/net/netfilter/nf_conntrack_core.c
+++ b/net/netfilter/nf_conntrack_core.c
@@ -1016,7 +1016,7 @@ struct hlist_head *nf_ct_alloc_hashtable(int *sizep, int *vmalloced)
}
EXPORT_SYMBOL_GPL(nf_ct_alloc_hashtable);
-int set_hashsize(const char *val, struct kernel_param *kp)
+int nf_conntrack_set_hashsize(const char *val, struct kernel_param *kp)
{
int i, bucket, hashsize, vmalloced;
int old_vmalloced, old_size;
@@ -1063,8 +1063,9 @@ int set_hashsize(const char *val, struct kernel_param *kp)
nf_ct_free_hashtable(old_hash, old_vmalloced, old_size);
return 0;
}
+EXPORT_SYMBOL_GPL(nf_conntrack_set_hashsize);
-module_param_call(hashsize, set_hashsize, param_get_uint,
+module_param_call(hashsize, nf_conntrack_set_hashsize, param_get_uint,
&nf_conntrack_htable_size, 0600);
int __init nf_conntrack_init(void)
diff --git a/net/netfilter/nf_conntrack_netlink.c b/net/netfilter/nf_conntrack_netlink.c
index 9be1826e6cd..7d231243754 100644
--- a/net/netfilter/nf_conntrack_netlink.c
+++ b/net/netfilter/nf_conntrack_netlink.c
@@ -1024,8 +1024,10 @@ ctnetlink_create_conntrack(struct nlattr *cda[],
}
/* setup master conntrack: this is a confirmed expectation */
- if (master_ct)
+ if (master_ct) {
+ __set_bit(IPS_EXPECTED_BIT, &ct->status);
ct->master = master_ct;
+ }
add_timer(&ct->timeout);
nf_conntrack_hash_insert(ct);
diff --git a/net/netfilter/nf_conntrack_sip.c b/net/netfilter/nf_conntrack_sip.c
index 8f8b5a48df3..515abffc4a0 100644
--- a/net/netfilter/nf_conntrack_sip.c
+++ b/net/netfilter/nf_conntrack_sip.c
@@ -187,7 +187,7 @@ static const struct sip_header_nfo ct_sip_hdrs[] = {
}
};
-/* get line lenght until first CR or LF seen. */
+/* get line length until first CR or LF seen. */
int ct_sip_lnlen(const char *line, const char *limit)
{
const char *k = line;
@@ -236,7 +236,7 @@ static int digits_len(struct nf_conn *ct, const char *dptr,
return len;
}
-/* get digits lenght, skiping blank spaces. */
+/* get digits length, skipping blank spaces. */
static int skp_digits_len(struct nf_conn *ct, const char *dptr,
const char *limit, int *shift)
{
diff --git a/net/netfilter/x_tables.c b/net/netfilter/x_tables.c
index d9a3bded0d0..b6160e41eb1 100644
--- a/net/netfilter/x_tables.c
+++ b/net/netfilter/x_tables.c
@@ -377,7 +377,9 @@ int xt_compat_match_to_user(struct xt_entry_match *m, void __user **dstptr,
u_int16_t msize = m->u.user.match_size - off;
if (copy_to_user(cm, m, sizeof(*cm)) ||
- put_user(msize, &cm->u.user.match_size))
+ put_user(msize, &cm->u.user.match_size) ||
+ copy_to_user(cm->u.user.name, m->u.kernel.match->name,
+ strlen(m->u.kernel.match->name) + 1))
return -EFAULT;
if (match->compat_to_user) {
@@ -468,7 +470,9 @@ int xt_compat_target_to_user(struct xt_entry_target *t, void __user **dstptr,
u_int16_t tsize = t->u.user.target_size - off;
if (copy_to_user(ct, t, sizeof(*ct)) ||
- put_user(tsize, &ct->u.user.target_size))
+ put_user(tsize, &ct->u.user.target_size) ||
+ copy_to_user(ct->u.user.name, t->u.kernel.target->name,
+ strlen(t->u.kernel.target->name) + 1))
return -EFAULT;
if (target->compat_to_user) {
diff --git a/net/netfilter/xt_CONNMARK.c b/net/netfilter/xt_CONNMARK.c
index 856793e8db7..0621ca7de3b 100644
--- a/net/netfilter/xt_CONNMARK.c
+++ b/net/netfilter/xt_CONNMARK.c
@@ -86,11 +86,6 @@ checkentry(const char *tablename,
{
const struct xt_connmark_target_info *matchinfo = targinfo;
- if (nf_ct_l3proto_try_module_get(target->family) < 0) {
- printk(KERN_WARNING "can't load conntrack support for "
- "proto=%d\n", target->family);
- return false;
- }
if (matchinfo->mode == XT_CONNMARK_RESTORE) {
if (strcmp(tablename, "mangle") != 0) {
printk(KERN_WARNING "CONNMARK: restore can only be "
@@ -103,6 +98,11 @@ checkentry(const char *tablename,
printk(KERN_WARNING "CONNMARK: Only supports 32bit mark\n");
return false;
}
+ if (nf_ct_l3proto_try_module_get(target->family) < 0) {
+ printk(KERN_WARNING "can't load conntrack support for "
+ "proto=%d\n", target->family);
+ return false;
+ }
return true;
}
diff --git a/net/netfilter/xt_CONNSECMARK.c b/net/netfilter/xt_CONNSECMARK.c
index 021b5c8d20e..d8feba9bdb4 100644
--- a/net/netfilter/xt_CONNSECMARK.c
+++ b/net/netfilter/xt_CONNSECMARK.c
@@ -90,11 +90,6 @@ static bool checkentry(const char *tablename, const void *entry,
{
const struct xt_connsecmark_target_info *info = targinfo;
- if (nf_ct_l3proto_try_module_get(target->family) < 0) {
- printk(KERN_WARNING "can't load conntrack support for "
- "proto=%d\n", target->family);
- return false;
- }
switch (info->mode) {
case CONNSECMARK_SAVE:
case CONNSECMARK_RESTORE:
@@ -105,6 +100,11 @@ static bool checkentry(const char *tablename, const void *entry,
return false;
}
+ if (nf_ct_l3proto_try_module_get(target->family) < 0) {
+ printk(KERN_WARNING "can't load conntrack support for "
+ "proto=%d\n", target->family);
+ return false;
+ }
return true;
}
diff --git a/net/netfilter/xt_TCPMSS.c b/net/netfilter/xt_TCPMSS.c
index 07435a602b1..8e76d1f52fb 100644
--- a/net/netfilter/xt_TCPMSS.c
+++ b/net/netfilter/xt_TCPMSS.c
@@ -174,10 +174,8 @@ xt_tcpmss_target6(struct sk_buff *skb,
nexthdr = ipv6h->nexthdr;
tcphoff = ipv6_skip_exthdr(skb, sizeof(*ipv6h), &nexthdr);
- if (tcphoff < 0) {
- WARN_ON(1);
+ if (tcphoff < 0)
return NF_DROP;
- }
ret = tcpmss_mangle_packet(skb, targinfo, tcphoff,
sizeof(*ipv6h) + sizeof(struct tcphdr));
if (ret < 0)
diff --git a/net/netfilter/xt_hashlimit.c b/net/netfilter/xt_hashlimit.c
index 19103678bf2..2ef44d8560c 100644
--- a/net/netfilter/xt_hashlimit.c
+++ b/net/netfilter/xt_hashlimit.c
@@ -240,7 +240,7 @@ static bool select_all(const struct xt_hashlimit_htable *ht,
static bool select_gc(const struct xt_hashlimit_htable *ht,
const struct dsthash_ent *he)
{
- return jiffies >= he->expires;
+ return time_after_eq(jiffies, he->expires);
}
static void htable_selective_cleanup(struct xt_hashlimit_htable *ht,
diff --git a/net/netlabel/netlabel_mgmt.c b/net/netlabel/netlabel_mgmt.c
index 56483377997..9c41464d58d 100644
--- a/net/netlabel/netlabel_mgmt.c
+++ b/net/netlabel/netlabel_mgmt.c
@@ -71,7 +71,7 @@ static const struct nla_policy netlbl_mgmt_genl_policy[NLBL_MGMT_A_MAX + 1] = {
};
/*
- * NetLabel Misc Managment Functions
+ * NetLabel Misc Management Functions
*/
/**
diff --git a/net/netrom/nr_dev.c b/net/netrom/nr_dev.c
index 8c68da5ef0a..6caf459665f 100644
--- a/net/netrom/nr_dev.c
+++ b/net/netrom/nr_dev.c
@@ -56,7 +56,7 @@ int nr_rx_ip(struct sk_buff *skb, struct net_device *dev)
/* Spoof incoming device */
skb->dev = dev;
- skb_reset_mac_header(skb);
+ skb->mac_header = skb->network_header;
skb_reset_network_header(skb);
skb->pkt_type = PACKET_HOST;
diff --git a/net/rfkill/rfkill.c b/net/rfkill/rfkill.c
index 73d60a30712..4469a7be006 100644
--- a/net/rfkill/rfkill.c
+++ b/net/rfkill/rfkill.c
@@ -60,11 +60,7 @@ static void rfkill_led_trigger(struct rfkill *rfkill,
static int rfkill_toggle_radio(struct rfkill *rfkill,
enum rfkill_state state)
{
- int retval;
-
- retval = mutex_lock_interruptible(&rfkill->mutex);
- if (retval)
- return retval;
+ int retval = 0;
if (state != rfkill->state) {
retval = rfkill->toggle_radio(rfkill->data, state);
@@ -74,7 +70,6 @@ static int rfkill_toggle_radio(struct rfkill *rfkill,
}
}
- mutex_unlock(&rfkill->mutex);
return retval;
}
@@ -158,12 +153,13 @@ static ssize_t rfkill_state_store(struct device *dev,
if (!capable(CAP_NET_ADMIN))
return -EPERM;
+ if (mutex_lock_interruptible(&rfkill->mutex))
+ return -ERESTARTSYS;
error = rfkill_toggle_radio(rfkill,
state ? RFKILL_STATE_ON : RFKILL_STATE_OFF);
- if (error)
- return error;
+ mutex_unlock(&rfkill->mutex);
- return count;
+ return error ? error : count;
}
static ssize_t rfkill_claim_show(struct device *dev,
diff --git a/net/rose/rose_dev.c b/net/rose/rose_dev.c
index 1b6741f1d74..12cfcf09556 100644
--- a/net/rose/rose_dev.c
+++ b/net/rose/rose_dev.c
@@ -55,13 +55,13 @@ static int rose_header(struct sk_buff *skb, struct net_device *dev,
static int rose_rebuild_header(struct sk_buff *skb)
{
+#ifdef CONFIG_INET
struct net_device *dev = skb->dev;
struct net_device_stats *stats = netdev_priv(dev);
unsigned char *bp = (unsigned char *)skb->data;
struct sk_buff *skbn;
unsigned int len;
-#ifdef CONFIG_INET
if (arp_find(bp + 7, skb)) {
return 1;
}
diff --git a/net/rxrpc/Kconfig b/net/rxrpc/Kconfig
index e662f1d0766..0d3103c4f11 100644
--- a/net/rxrpc/Kconfig
+++ b/net/rxrpc/Kconfig
@@ -5,6 +5,7 @@
config AF_RXRPC
tristate "RxRPC session sockets"
depends on INET && EXPERIMENTAL
+ select CRYPTO
select KEYS
help
Say Y or M here to include support for RxRPC session sockets (just
diff --git a/net/rxrpc/rxkad.c b/net/rxrpc/rxkad.c
index e09a95aa68f..8e69d699383 100644
--- a/net/rxrpc/rxkad.c
+++ b/net/rxrpc/rxkad.c
@@ -1021,6 +1021,7 @@ static int rxkad_verify_response(struct rxrpc_connection *conn,
abort_code = RXKADINCONSISTENCY;
if (version != RXKAD_VERSION)
+ goto protocol_error;
abort_code = RXKADTICKETLEN;
if (ticket_len < 4 || ticket_len > MAXKRB5TICKETLEN)
diff --git a/net/sched/sch_hfsc.c b/net/sched/sch_hfsc.c
index 55e7e4530f4..a6ad491e434 100644
--- a/net/sched/sch_hfsc.c
+++ b/net/sched/sch_hfsc.c
@@ -160,7 +160,7 @@ struct hfsc_class
u64 cl_vtoff; /* inter-period cumulative vt offset */
u64 cl_cvtmax; /* max child's vt in the last period */
u64 cl_cvtoff; /* cumulative cvtmax of all periods */
- u64 cl_pcvtoff; /* parent's cvtoff at initalization
+ u64 cl_pcvtoff; /* parent's cvtoff at initialization
time */
struct internal_sc cl_rsc; /* internal real-time service curve */
diff --git a/net/sctp/Kconfig b/net/sctp/Kconfig
index 8210f549c49..5390bc79215 100644
--- a/net/sctp/Kconfig
+++ b/net/sctp/Kconfig
@@ -6,9 +6,9 @@ menuconfig IP_SCTP
tristate "The SCTP Protocol (EXPERIMENTAL)"
depends on INET && EXPERIMENTAL
depends on IPV6 || IPV6=n
- select CRYPTO if SCTP_HMAC_SHA1 || SCTP_HMAC_MD5
- select CRYPTO_HMAC if SCTP_HMAC_SHA1 || SCTP_HMAC_MD5
- select CRYPTO_SHA1 if SCTP_HMAC_SHA1
+ select CRYPTO
+ select CRYPTO_HMAC
+ select CRYPTO_SHA1
select CRYPTO_MD5 if SCTP_HMAC_MD5
---help---
Stream Control Transmission Protocol
diff --git a/net/sctp/auth.c b/net/sctp/auth.c
index 6d5fa6bb371..97e6ebd1450 100644
--- a/net/sctp/auth.c
+++ b/net/sctp/auth.c
@@ -54,11 +54,13 @@ static struct sctp_hmac sctp_hmac_list[SCTP_AUTH_NUM_HMACS] = {
/* id 2 is reserved as well */
.hmac_id = SCTP_AUTH_HMAC_ID_RESERVED_2,
},
+#if defined (CONFIG_CRYPTO_SHA256) || defined (CONFIG_CRYPTO_SHA256_MODULE)
{
.hmac_id = SCTP_AUTH_HMAC_ID_SHA256,
.hmac_name="hmac(sha256)",
.hmac_len = SCTP_SHA256_SIG_SIZE,
}
+#endif
};
@@ -631,7 +633,7 @@ static int __sctp_auth_cid(sctp_cid_t chunk, struct sctp_chunks_param *param)
int found = 0;
int i;
- if (!param)
+ if (!param || param->param_hdr.length == 0)
return 0;
len = ntohs(param->param_hdr.length) - sizeof(sctp_paramhdr_t);
diff --git a/net/sctp/bind_addr.c b/net/sctp/bind_addr.c
index cae95af9a8c..6a7d01091f0 100644
--- a/net/sctp/bind_addr.c
+++ b/net/sctp/bind_addr.c
@@ -105,6 +105,32 @@ out:
return error;
}
+/* Exactly duplicate the address lists. This is necessary when doing
+ * peer-offs and accepts. We don't want to put all the current system
+ * addresses into the endpoint. That's useless. But we do want duplicat
+ * the list of bound addresses that the older endpoint used.
+ */
+int sctp_bind_addr_dup(struct sctp_bind_addr *dest,
+ const struct sctp_bind_addr *src,
+ gfp_t gfp)
+{
+ struct sctp_sockaddr_entry *addr;
+ struct list_head *pos;
+ int error = 0;
+
+ /* All addresses share the same port. */
+ dest->port = src->port;
+
+ list_for_each(pos, &src->address_list) {
+ addr = list_entry(pos, struct sctp_sockaddr_entry, list);
+ error = sctp_add_bind_addr(dest, &addr->a, 1, gfp);
+ if (error < 0)
+ break;
+ }
+
+ return error;
+}
+
/* Initialize the SCTP_bind_addr structure for either an endpoint or
* an association.
*/
diff --git a/net/sctp/sm_make_chunk.c b/net/sctp/sm_make_chunk.c
index 5a9783c38de..3cc629d3c9f 100644
--- a/net/sctp/sm_make_chunk.c
+++ b/net/sctp/sm_make_chunk.c
@@ -77,6 +77,8 @@ static int sctp_process_param(struct sctp_association *asoc,
union sctp_params param,
const union sctp_addr *peer_addr,
gfp_t gfp);
+static void *sctp_addto_param(struct sctp_chunk *chunk, int len,
+ const void *data);
/* What was the inbound interface for this chunk? */
int sctp_chunk_iif(const struct sctp_chunk *chunk)
@@ -207,11 +209,10 @@ struct sctp_chunk *sctp_make_init(const struct sctp_association *asoc,
chunksize = sizeof(init) + addrs_len + SCTP_SAT_LEN(num_types);
chunksize += sizeof(ecap_param);
- if (sctp_prsctp_enable) {
+
+ if (sctp_prsctp_enable)
chunksize += sizeof(prsctp_param);
- extensions[num_ext] = SCTP_CID_FWD_TSN;
- num_ext += 1;
- }
+
/* ADDIP: Section 4.2.7:
* An implementation supporting this extension [ADDIP] MUST list
* the ASCONF,the ASCONF-ACK, and the AUTH chunks in its INIT and
@@ -243,7 +244,7 @@ struct sctp_chunk *sctp_make_init(const struct sctp_association *asoc,
if (auth_chunks->length)
chunksize += ntohs(auth_chunks->length);
else
- auth_hmacs = NULL;
+ auth_chunks = NULL;
extensions[num_ext] = SCTP_CID_AUTH;
num_ext += 1;
@@ -288,7 +289,7 @@ struct sctp_chunk *sctp_make_init(const struct sctp_association *asoc,
sctp_addto_chunk(retval, sizeof(ecap_param), &ecap_param);
- /* Add the supported extensions paramter. Be nice and add this
+ /* Add the supported extensions parameter. Be nice and add this
* fist before addiding the parameters for the extensions themselves
*/
if (num_ext) {
@@ -297,7 +298,7 @@ struct sctp_chunk *sctp_make_init(const struct sctp_association *asoc,
htons(sizeof(sctp_supported_ext_param_t) + num_ext);
sctp_addto_chunk(retval, sizeof(sctp_supported_ext_param_t),
&ext_param);
- sctp_addto_chunk(retval, num_ext, extensions);
+ sctp_addto_param(retval, num_ext, extensions);
}
if (sctp_prsctp_enable)
@@ -371,12 +372,8 @@ struct sctp_chunk *sctp_make_init_ack(const struct sctp_association *asoc,
if (asoc->peer.ecn_capable)
chunksize += sizeof(ecap_param);
- /* Tell peer that we'll do PR-SCTP only if peer advertised. */
- if (asoc->peer.prsctp_capable) {
+ if (sctp_prsctp_enable)
chunksize += sizeof(prsctp_param);
- extensions[num_ext] = SCTP_CID_FWD_TSN;
- num_ext += 1;
- }
if (sctp_addip_enable) {
extensions[num_ext] = SCTP_CID_ASCONF;
@@ -384,7 +381,6 @@ struct sctp_chunk *sctp_make_init_ack(const struct sctp_association *asoc,
num_ext += 2;
}
- chunksize += sizeof(ext_param) + num_ext;
chunksize += sizeof(aiparam);
if (asoc->peer.auth_capable) {
@@ -407,6 +403,9 @@ struct sctp_chunk *sctp_make_init_ack(const struct sctp_association *asoc,
num_ext += 1;
}
+ if (num_ext)
+ chunksize += sizeof(sctp_supported_ext_param_t) + num_ext;
+
/* Now allocate and fill out the chunk. */
retval = sctp_make_chunk(asoc, SCTP_CID_INIT_ACK, 0, chunksize);
if (!retval)
@@ -428,7 +427,7 @@ struct sctp_chunk *sctp_make_init_ack(const struct sctp_association *asoc,
htons(sizeof(sctp_supported_ext_param_t) + num_ext);
sctp_addto_chunk(retval, sizeof(sctp_supported_ext_param_t),
&ext_param);
- sctp_addto_chunk(retval, num_ext, extensions);
+ sctp_addto_param(retval, num_ext, extensions);
}
if (asoc->peer.prsctp_capable)
sctp_addto_chunk(retval, sizeof(prsctp_param), &prsctp_param);
@@ -2866,7 +2865,7 @@ struct sctp_chunk *sctp_process_asconf(struct sctp_association *asoc,
chunk_len -= length;
/* Skip the address parameter and store a pointer to the first
- * asconf paramter.
+ * asconf parameter.
*/
length = ntohs(addr_param->v4.param_hdr.length);
asconf_param = (sctp_addip_param_t *)((void *)addr_param + length);
@@ -2875,7 +2874,7 @@ struct sctp_chunk *sctp_process_asconf(struct sctp_association *asoc,
/* create an ASCONF_ACK chunk.
* Based on the definitions of parameters, we know that the size of
* ASCONF_ACK parameters are less than or equal to the twice of ASCONF
- * paramters.
+ * parameters.
*/
asconf_ack = sctp_make_asconf_ack(asoc, serial, chunk_len * 2);
if (!asconf_ack)
@@ -3069,7 +3068,7 @@ int sctp_process_asconf_ack(struct sctp_association *asoc,
asconf_len -= length;
/* Skip the address parameter in the last asconf sent and store a
- * pointer to the first asconf paramter.
+ * pointer to the first asconf parameter.
*/
length = ntohs(addr_param->v4.param_hdr.length);
asconf_param = (sctp_addip_param_t *)((void *)addr_param + length);
diff --git a/net/sctp/sm_statefuns.c b/net/sctp/sm_statefuns.c
index 5ebbe808d80..d247ed4ee42 100644
--- a/net/sctp/sm_statefuns.c
+++ b/net/sctp/sm_statefuns.c
@@ -959,7 +959,7 @@ sctp_disposition_t sctp_sf_sendbeat_8_3(const struct sctp_endpoint *ep,
{
struct sctp_transport *transport = (struct sctp_transport *) arg;
- if (asoc->overall_error_count >= asoc->max_retrans) {
+ if (asoc->overall_error_count > asoc->max_retrans) {
sctp_add_cmd_sf(commands, SCTP_CMD_SET_SK_ERR,
SCTP_ERROR(ETIMEDOUT));
/* CMD_ASSOC_FAILED calls CMD_DELETE_TCB. */
@@ -1146,7 +1146,7 @@ sctp_disposition_t sctp_sf_backbeat_8_3(const struct sctp_endpoint *ep,
/* Check if the timestamp looks valid. */
if (time_after(hbinfo->sent_at, jiffies) ||
time_after(jiffies, hbinfo->sent_at + max_interval)) {
- SCTP_DEBUG_PRINTK("%s: HEARTBEAT ACK with invalid timestamp"
+ SCTP_DEBUG_PRINTK("%s: HEARTBEAT ACK with invalid timestamp "
"received for transport: %p\n",
__FUNCTION__, link);
return SCTP_DISPOSITION_DISCARD;
@@ -1309,26 +1309,6 @@ static void sctp_tietags_populate(struct sctp_association *new_asoc,
new_asoc->c.initial_tsn = asoc->c.initial_tsn;
}
-static void sctp_auth_params_populate(struct sctp_association *new_asoc,
- const struct sctp_association *asoc)
-{
- /* Only perform this if AUTH extension is enabled */
- if (!sctp_auth_enable)
- return;
-
- /* We need to provide the same parameter information as
- * was in the original INIT. This means that we need to copy
- * the HMACS, CHUNKS, and RANDOM parameter from the original
- * assocaition.
- */
- memcpy(new_asoc->c.auth_random, asoc->c.auth_random,
- sizeof(asoc->c.auth_random));
- memcpy(new_asoc->c.auth_hmacs, asoc->c.auth_hmacs,
- sizeof(asoc->c.auth_hmacs));
- memcpy(new_asoc->c.auth_chunks, asoc->c.auth_chunks,
- sizeof(asoc->c.auth_chunks));
-}
-
/*
* Compare vtag/tietag values to determine unexpected COOKIE-ECHO
* handling action.
@@ -1486,8 +1466,6 @@ static sctp_disposition_t sctp_sf_do_unexpected_init(
sctp_tietags_populate(new_asoc, asoc);
- sctp_auth_params_populate(new_asoc, asoc);
-
/* B) "Z" shall respond immediately with an INIT ACK chunk. */
/* If there are errors need to be reported for unknown parameters,
diff --git a/net/sctp/socket.c b/net/sctp/socket.c
index ff8bc95670e..ea9649ca0b2 100644
--- a/net/sctp/socket.c
+++ b/net/sctp/socket.c
@@ -6325,7 +6325,7 @@ static void sctp_sock_migrate(struct sock *oldsk, struct sock *newsk,
struct sctp_endpoint *newep = newsp->ep;
struct sk_buff *skb, *tmp;
struct sctp_ulpevent *event;
- int flags = 0;
+ struct sctp_bind_hashbucket *head;
/* Migrate socket buffer sizes and all the socket level options to the
* new socket.
@@ -6342,23 +6342,21 @@ static void sctp_sock_migrate(struct sock *oldsk, struct sock *newsk,
newsp->hmac = NULL;
/* Hook this new socket in to the bind_hash list. */
+ head = &sctp_port_hashtable[sctp_phashfn(inet_sk(oldsk)->num)];
+ sctp_local_bh_disable();
+ sctp_spin_lock(&head->lock);
pp = sctp_sk(oldsk)->bind_hash;
sk_add_bind_node(newsk, &pp->owner);
sctp_sk(newsk)->bind_hash = pp;
inet_sk(newsk)->num = inet_sk(oldsk)->num;
+ sctp_spin_unlock(&head->lock);
+ sctp_local_bh_enable();
/* Copy the bind_addr list from the original endpoint to the new
* endpoint so that we can handle restarts properly
*/
- if (PF_INET6 == assoc->base.sk->sk_family)
- flags = SCTP_ADDR6_ALLOWED;
- if (assoc->peer.ipv4_address)
- flags |= SCTP_ADDR4_PEERSUPP;
- if (assoc->peer.ipv6_address)
- flags |= SCTP_ADDR6_PEERSUPP;
- sctp_bind_addr_copy(&newsp->ep->base.bind_addr,
- &oldsp->ep->base.bind_addr,
- SCTP_SCOPE_GLOBAL, GFP_KERNEL, flags);
+ sctp_bind_addr_dup(&newsp->ep->base.bind_addr,
+ &oldsp->ep->base.bind_addr, GFP_KERNEL);
/* Move any messages in the old socket's receive queue that are for the
* peeled off association to the new socket's receive queue.
diff --git a/net/sctp/ulpevent.c b/net/sctp/ulpevent.c
index 2c17c7efad4..307314356e1 100644
--- a/net/sctp/ulpevent.c
+++ b/net/sctp/ulpevent.c
@@ -830,7 +830,7 @@ struct sctp_ulpevent *sctp_ulpevent_make_authkey(
ak = (struct sctp_authkey_event *)
skb_put(skb, sizeof(struct sctp_authkey_event));
- ak->auth_type = SCTP_AUTHENTICATION_EVENT;
+ ak->auth_type = SCTP_AUTHENTICATION_INDICATION;
ak->auth_flags = 0;
ak->auth_length = sizeof(struct sctp_authkey_event);
diff --git a/net/sctp/ulpqueue.c b/net/sctp/ulpqueue.c
index 4908041ffb3..1733fa29a50 100644
--- a/net/sctp/ulpqueue.c
+++ b/net/sctp/ulpqueue.c
@@ -53,6 +53,7 @@ static struct sctp_ulpevent * sctp_ulpq_reasm(struct sctp_ulpq *ulpq,
struct sctp_ulpevent *);
static struct sctp_ulpevent * sctp_ulpq_order(struct sctp_ulpq *,
struct sctp_ulpevent *);
+static void sctp_ulpq_reasm_drain(struct sctp_ulpq *ulpq);
/* 1st Level Abstractions */
@@ -190,6 +191,7 @@ static void sctp_ulpq_set_pd(struct sctp_ulpq *ulpq)
static int sctp_ulpq_clear_pd(struct sctp_ulpq *ulpq)
{
ulpq->pd_mode = 0;
+ sctp_ulpq_reasm_drain(ulpq);
return sctp_clear_pd(ulpq->asoc->base.sk, ulpq->asoc);
}
@@ -699,6 +701,37 @@ void sctp_ulpq_reasm_flushtsn(struct sctp_ulpq *ulpq, __u32 fwd_tsn)
}
}
+/*
+ * Drain the reassembly queue. If we just cleared parted delivery, it
+ * is possible that the reassembly queue will contain already reassembled
+ * messages. Retrieve any such messages and give them to the user.
+ */
+static void sctp_ulpq_reasm_drain(struct sctp_ulpq *ulpq)
+{
+ struct sctp_ulpevent *event = NULL;
+ struct sk_buff_head temp;
+
+ if (skb_queue_empty(&ulpq->reasm))
+ return;
+
+ while ((event = sctp_ulpq_retrieve_reassembled(ulpq)) != NULL) {
+ /* Do ordering if needed. */
+ if ((event) && (event->msg_flags & MSG_EOR)){
+ skb_queue_head_init(&temp);
+ __skb_queue_tail(&temp, sctp_event2skb(event));
+
+ event = sctp_ulpq_order(ulpq, event);
+ }
+
+ /* Send event to the ULP. 'event' is the
+ * sctp_ulpevent for very first SKB on the temp' list.
+ */
+ if (event)
+ sctp_ulpq_tail_event(ulpq, event);
+ }
+}
+
+
/* Helper function to gather skbs that have possibly become
* ordered by an an incoming chunk.
*/
diff --git a/net/sunrpc/auth_gss/auth_gss.c b/net/sunrpc/auth_gss/auth_gss.c
index 53995af9ca4..1f2d85e869c 100644
--- a/net/sunrpc/auth_gss/auth_gss.c
+++ b/net/sunrpc/auth_gss/auth_gss.c
@@ -540,7 +540,7 @@ gss_pipe_downcall(struct file *filp, const char __user *src, size_t mlen)
p = gss_fill_context(p, end, ctx, gss_msg->auth->mech);
if (IS_ERR(p)) {
err = PTR_ERR(p);
- gss_msg->msg.errno = (err == -EACCES) ? -EACCES : -EAGAIN;
+ gss_msg->msg.errno = (err == -EAGAIN) ? -EAGAIN : -EACCES;
goto err_release_msg;
}
gss_msg->ctx = gss_get_ctx(ctx);
@@ -625,7 +625,7 @@ gss_create(struct rpc_clnt *clnt, rpc_authflavor_t flavor)
err = -EINVAL;
gss_auth->mech = gss_mech_get_by_pseudoflavor(flavor);
if (!gss_auth->mech) {
- printk(KERN_WARNING "%s: Pseudoflavor %d not found!",
+ printk(KERN_WARNING "%s: Pseudoflavor %d not found!\n",
__FUNCTION__, flavor);
goto err_free;
}
@@ -967,7 +967,7 @@ gss_validate(struct rpc_task *task, __be32 *p)
if (maj_stat == GSS_S_CONTEXT_EXPIRED)
clear_bit(RPCAUTH_CRED_UPTODATE, &cred->cr_flags);
if (maj_stat) {
- dprintk("RPC: %5u gss_validate: gss_verify_mic returned"
+ dprintk("RPC: %5u gss_validate: gss_verify_mic returned "
"error 0x%08x\n", task->tk_pid, maj_stat);
goto out_bad;
}
diff --git a/net/sunrpc/auth_gss/gss_krb5_mech.c b/net/sunrpc/auth_gss/gss_krb5_mech.c
index 9843eacef11..60c3dba545d 100644
--- a/net/sunrpc/auth_gss/gss_krb5_mech.c
+++ b/net/sunrpc/auth_gss/gss_krb5_mech.c
@@ -147,13 +147,17 @@ gss_import_sec_context_kerberos(const void *p,
p = simple_get_bytes(p, end, &tmp, sizeof(tmp));
if (IS_ERR(p))
goto out_err_free_ctx;
- if (tmp != SGN_ALG_DES_MAC_MD5)
+ if (tmp != SGN_ALG_DES_MAC_MD5) {
+ p = ERR_PTR(-ENOSYS);
goto out_err_free_ctx;
+ }
p = simple_get_bytes(p, end, &tmp, sizeof(tmp));
if (IS_ERR(p))
goto out_err_free_ctx;
- if (tmp != SEAL_ALG_DES)
+ if (tmp != SEAL_ALG_DES) {
+ p = ERR_PTR(-ENOSYS);
goto out_err_free_ctx;
+ }
p = simple_get_bytes(p, end, &ctx->endtime, sizeof(ctx->endtime));
if (IS_ERR(p))
goto out_err_free_ctx;
diff --git a/net/sunrpc/auth_gss/gss_krb5_seal.c b/net/sunrpc/auth_gss/gss_krb5_seal.c
index 1c6eda5077c..dedcbd6108f 100644
--- a/net/sunrpc/auth_gss/gss_krb5_seal.c
+++ b/net/sunrpc/auth_gss/gss_krb5_seal.c
@@ -83,6 +83,7 @@ gss_get_mic_kerberos(struct gss_ctx *gss_ctx, struct xdr_buf *text,
u32 seq_send;
dprintk("RPC: gss_krb5_seal\n");
+ BUG_ON(ctx == NULL);
now = get_seconds();
diff --git a/net/sunrpc/rpc_pipe.c b/net/sunrpc/rpc_pipe.c
index 18f0a8dcc09..c59f3ca2b41 100644
--- a/net/sunrpc/rpc_pipe.c
+++ b/net/sunrpc/rpc_pipe.c
@@ -280,7 +280,7 @@ rpc_pipe_poll(struct file *filp, struct poll_table_struct *wait)
mask = POLLOUT | POLLWRNORM;
if (rpci->ops == NULL)
mask |= POLLERR | POLLHUP;
- if (!list_empty(&rpci->pipe))
+ if (filp->private_data || !list_empty(&rpci->pipe))
mask |= POLLIN | POLLRDNORM;
return mask;
}
diff --git a/net/sunrpc/xprt.c b/net/sunrpc/xprt.c
index 282a9a2ec90..cd641c8634f 100644
--- a/net/sunrpc/xprt.c
+++ b/net/sunrpc/xprt.c
@@ -62,7 +62,7 @@ static inline void do_xprt_reserve(struct rpc_task *);
static void xprt_connect_status(struct rpc_task *task);
static int __xprt_get_cong(struct rpc_xprt *, struct rpc_task *);
-static spinlock_t xprt_list_lock = SPIN_LOCK_UNLOCKED;
+static DEFINE_SPINLOCK(xprt_list_lock);
static LIST_HEAD(xprt_list);
/*
diff --git a/net/sunrpc/xprtrdma/rpc_rdma.c b/net/sunrpc/xprtrdma/rpc_rdma.c
index 9e11ce71595..ee8de7af2a5 100644
--- a/net/sunrpc/xprtrdma/rpc_rdma.c
+++ b/net/sunrpc/xprtrdma/rpc_rdma.c
@@ -92,7 +92,6 @@ rpcrdma_convert_iovs(struct xdr_buf *xdrbuf, int pos,
seg[n].mr_page = NULL;
seg[n].mr_offset = xdrbuf->head[0].iov_base;
seg[n].mr_len = xdrbuf->head[0].iov_len;
- pos += xdrbuf->head[0].iov_len;
++n;
}
@@ -104,7 +103,6 @@ rpcrdma_convert_iovs(struct xdr_buf *xdrbuf, int pos,
seg[n].mr_len = min_t(u32,
PAGE_SIZE - xdrbuf->page_base, xdrbuf->page_len);
len = xdrbuf->page_len - seg[n].mr_len;
- pos += len;
++n;
p = 1;
while (len > 0) {
@@ -119,20 +117,15 @@ rpcrdma_convert_iovs(struct xdr_buf *xdrbuf, int pos,
}
}
- if (pos < xdrbuf->len && xdrbuf->tail[0].iov_len) {
+ if (xdrbuf->tail[0].iov_len) {
if (n == nsegs)
return 0;
seg[n].mr_page = NULL;
seg[n].mr_offset = xdrbuf->tail[0].iov_base;
seg[n].mr_len = xdrbuf->tail[0].iov_len;
- pos += xdrbuf->tail[0].iov_len;
++n;
}
- if (pos < xdrbuf->len)
- dprintk("RPC: %s: marshaled only %d of %d\n",
- __func__, pos, xdrbuf->len);
-
return n;
}
diff --git a/net/sunrpc/xprtrdma/transport.c b/net/sunrpc/xprtrdma/transport.c
index 1afeb3eb8e4..6f2112dd9f7 100644
--- a/net/sunrpc/xprtrdma/transport.c
+++ b/net/sunrpc/xprtrdma/transport.c
@@ -89,7 +89,7 @@ static struct ctl_table_header *sunrpc_table_header;
static ctl_table xr_tunables_table[] = {
{
- .ctl_name = CTL_SLOTTABLE_RDMA,
+ .ctl_name = CTL_UNNUMBERED,
.procname = "rdma_slot_table_entries",
.data = &xprt_rdma_slot_table_entries,
.maxlen = sizeof(unsigned int),
@@ -100,7 +100,7 @@ static ctl_table xr_tunables_table[] = {
.extra2 = &max_slot_table_size
},
{
- .ctl_name = CTL_RDMA_MAXINLINEREAD,
+ .ctl_name = CTL_UNNUMBERED,
.procname = "rdma_max_inline_read",
.data = &xprt_rdma_max_inline_read,
.maxlen = sizeof(unsigned int),
@@ -109,7 +109,7 @@ static ctl_table xr_tunables_table[] = {
.strategy = &sysctl_intvec,
},
{
- .ctl_name = CTL_RDMA_MAXINLINEWRITE,
+ .ctl_name = CTL_UNNUMBERED,
.procname = "rdma_max_inline_write",
.data = &xprt_rdma_max_inline_write,
.maxlen = sizeof(unsigned int),
@@ -118,7 +118,7 @@ static ctl_table xr_tunables_table[] = {
.strategy = &sysctl_intvec,
},
{
- .ctl_name = CTL_RDMA_WRITEPADDING,
+ .ctl_name = CTL_UNNUMBERED,
.procname = "rdma_inline_write_padding",
.data = &xprt_rdma_inline_write_padding,
.maxlen = sizeof(unsigned int),
@@ -129,7 +129,7 @@ static ctl_table xr_tunables_table[] = {
.extra2 = &max_padding,
},
{
- .ctl_name = CTL_RDMA_MEMREG,
+ .ctl_name = CTL_UNNUMBERED,
.procname = "rdma_memreg_strategy",
.data = &xprt_rdma_memreg_strategy,
.maxlen = sizeof(unsigned int),
diff --git a/net/sunrpc/xprtsock.c b/net/sunrpc/xprtsock.c
index 02298f529da..2f630a512ab 100644
--- a/net/sunrpc/xprtsock.c
+++ b/net/sunrpc/xprtsock.c
@@ -1828,7 +1828,7 @@ static struct rpc_xprt *xs_setup_xprt(struct xprt_create *args,
* @args: rpc transport creation arguments
*
*/
-struct rpc_xprt *xs_setup_udp(struct xprt_create *args)
+static struct rpc_xprt *xs_setup_udp(struct xprt_create *args)
{
struct sockaddr *addr = args->dstaddr;
struct rpc_xprt *xprt;
@@ -1894,7 +1894,7 @@ struct rpc_xprt *xs_setup_udp(struct xprt_create *args)
* @args: rpc transport creation arguments
*
*/
-struct rpc_xprt *xs_setup_tcp(struct xprt_create *args)
+static struct rpc_xprt *xs_setup_tcp(struct xprt_create *args)
{
struct sockaddr *addr = args->dstaddr;
struct rpc_xprt *xprt;
diff --git a/net/tipc/socket.c b/net/tipc/socket.c
index 6b792265dc0..24ddfd2ca38 100644
--- a/net/tipc/socket.c
+++ b/net/tipc/socket.c
@@ -253,7 +253,7 @@ static int release(struct socket *sock)
dbg("sock_delete: %x\n",tsock);
if (!tsock)
return 0;
- down_interruptible(&tsock->sem);
+ down(&tsock->sem);
if (!sock->sk) {
up(&tsock->sem);
return 0;
diff --git a/net/unix/af_unix.c b/net/unix/af_unix.c
index e835da8fc09..060bba4567d 100644
--- a/net/unix/af_unix.c
+++ b/net/unix/af_unix.c
@@ -1637,8 +1637,15 @@ static int unix_dgram_recvmsg(struct kiocb *iocb, struct socket *sock,
mutex_lock(&u->readlock);
skb = skb_recv_datagram(sk, flags, noblock, &err);
- if (!skb)
+ if (!skb) {
+ unix_state_lock(sk);
+ /* Signal EOF on disconnected non-blocking SEQPACKET socket. */
+ if (sk->sk_type == SOCK_SEQPACKET && err == -EAGAIN &&
+ (sk->sk_shutdown & RCV_SHUTDOWN))
+ err = 0;
+ unix_state_unlock(sk);
goto out_unlock;
+ }
wake_up_interruptible_sync(&u->peer_wait);
diff --git a/net/wireless/wext.c b/net/wireless/wext.c
index 85e5f9dd0d8..47e80cc2077 100644
--- a/net/wireless/wext.c
+++ b/net/wireless/wext.c
@@ -1094,7 +1094,7 @@ int wext_handle_ioctl(struct net *net, struct ifreq *ifr, unsigned int cmd,
rtnl_lock();
ret = wireless_process_ioctl(net, ifr, cmd);
rtnl_unlock();
- if (IW_IS_GET(cmd) && copy_to_user(arg, ifr, sizeof(struct ifreq)))
+ if (IW_IS_GET(cmd) && copy_to_user(arg, ifr, sizeof(struct iwreq)))
return -EFAULT;
return ret;
}
diff --git a/net/x25/x25_forward.c b/net/x25/x25_forward.c
index 8738ec7ce69..34478035e05 100644
--- a/net/x25/x25_forward.c
+++ b/net/x25/x25_forward.c
@@ -118,13 +118,14 @@ int x25_forward_data(int lci, struct x25_neigh *from, struct sk_buff *skb) {
goto out;
if ( (skbn = pskb_copy(skb, GFP_ATOMIC)) == NULL){
- goto out;
+ goto output;
}
x25_transmit_link(skbn, nb);
- x25_neigh_put(nb);
rc = 1;
+output:
+ x25_neigh_put(nb);
out:
return rc;
}
diff --git a/net/xfrm/xfrm_policy.c b/net/xfrm/xfrm_policy.c
index b702bd8a389..26b846e11bf 100644
--- a/net/xfrm/xfrm_policy.c
+++ b/net/xfrm/xfrm_policy.c
@@ -1318,8 +1318,9 @@ restart:
if (sk && sk->sk_policy[XFRM_POLICY_OUT]) {
policy = xfrm_sk_policy_lookup(sk, XFRM_POLICY_OUT, fl);
+ err = PTR_ERR(policy);
if (IS_ERR(policy))
- return PTR_ERR(policy);
+ goto dropdst;
}
if (!policy) {
@@ -1330,8 +1331,9 @@ restart:
policy = flow_cache_lookup(fl, dst_orig->ops->family,
dir, xfrm_policy_lookup);
+ err = PTR_ERR(policy);
if (IS_ERR(policy))
- return PTR_ERR(policy);
+ goto dropdst;
}
if (!policy)
@@ -1344,6 +1346,7 @@ restart:
xfrm_nr += pols[0]->xfrm_nr;
switch (policy->action) {
+ default:
case XFRM_POLICY_BLOCK:
/* Prohibit the flow */
err = -EPERM;
@@ -1500,8 +1503,9 @@ restart:
return 0;
error:
- dst_release(dst_orig);
xfrm_pols_put(pols, npols);
+dropdst:
+ dst_release(dst_orig);
*dst_p = NULL;
return err;
}
@@ -2158,7 +2162,7 @@ xfrm_audit_policy_add(struct xfrm_policy *xp, int result, u32 auid, u32 sid)
if (audit_enabled == 0)
return;
- audit_buf = xfrm_audit_start(sid, auid);
+ audit_buf = xfrm_audit_start(auid, sid);
if (audit_buf == NULL)
return;
audit_log_format(audit_buf, " op=SPD-add res=%u", result);
@@ -2175,7 +2179,7 @@ xfrm_audit_policy_delete(struct xfrm_policy *xp, int result, u32 auid, u32 sid)
if (audit_enabled == 0)
return;
- audit_buf = xfrm_audit_start(sid, auid);
+ audit_buf = xfrm_audit_start(auid, sid);
if (audit_buf == NULL)
return;
audit_log_format(audit_buf, " op=SPD-delete res=%u", result);
diff --git a/net/xfrm/xfrm_state.c b/net/xfrm/xfrm_state.c
index 224b44e31a0..f26aaaca1fa 100644
--- a/net/xfrm/xfrm_state.c
+++ b/net/xfrm/xfrm_state.c
@@ -552,7 +552,7 @@ int __xfrm_state_delete(struct xfrm_state *x)
* The xfrm_state_alloc call gives a reference, and that
* is what we are dropping here.
*/
- __xfrm_state_put(x);
+ xfrm_state_put(x);
err = 0;
}
@@ -1749,6 +1749,7 @@ void km_policy_expired(struct xfrm_policy *pol, int dir, int hard, u32 pid)
}
EXPORT_SYMBOL(km_policy_expired);
+#ifdef CONFIG_XFRM_MIGRATE
int km_migrate(struct xfrm_selector *sel, u8 dir, u8 type,
struct xfrm_migrate *m, int num_migrate)
{
@@ -1768,6 +1769,7 @@ int km_migrate(struct xfrm_selector *sel, u8 dir, u8 type,
return err;
}
EXPORT_SYMBOL(km_migrate);
+#endif
int km_report(u8 proto, struct xfrm_selector *sel, xfrm_address_t *addr)
{
@@ -2028,17 +2030,18 @@ void
xfrm_audit_state_add(struct xfrm_state *x, int result, u32 auid, u32 sid)
{
struct audit_buffer *audit_buf;
+ u32 spi;
extern int audit_enabled;
if (audit_enabled == 0)
return;
- audit_buf = xfrm_audit_start(sid, auid);
+ audit_buf = xfrm_audit_start(auid, sid);
if (audit_buf == NULL)
return;
audit_log_format(audit_buf, " op=SAD-add res=%u",result);
xfrm_audit_common_stateinfo(x, audit_buf);
- audit_log_format(audit_buf, " spi=%lu(0x%lx)",
- (unsigned long)x->id.spi, (unsigned long)x->id.spi);
+ spi = ntohl(x->id.spi);
+ audit_log_format(audit_buf, " spi=%u(0x%x)", spi, spi);
audit_log_end(audit_buf);
}
EXPORT_SYMBOL_GPL(xfrm_audit_state_add);
@@ -2047,17 +2050,18 @@ void
xfrm_audit_state_delete(struct xfrm_state *x, int result, u32 auid, u32 sid)
{
struct audit_buffer *audit_buf;
+ u32 spi;
extern int audit_enabled;
if (audit_enabled == 0)
return;
- audit_buf = xfrm_audit_start(sid, auid);
+ audit_buf = xfrm_audit_start(auid, sid);
if (audit_buf == NULL)
return;
audit_log_format(audit_buf, " op=SAD-delete res=%u",result);
xfrm_audit_common_stateinfo(x, audit_buf);
- audit_log_format(audit_buf, " spi=%lu(0x%lx)",
- (unsigned long)x->id.spi, (unsigned long)x->id.spi);
+ spi = ntohl(x->id.spi);
+ audit_log_format(audit_buf, " spi=%u(0x%x)", spi, spi);
audit_log_end(audit_buf);
}
EXPORT_SYMBOL_GPL(xfrm_audit_state_delete);
diff --git a/net/xfrm/xfrm_user.c b/net/xfrm/xfrm_user.c
index d41588d101d..c4f6419b176 100644
--- a/net/xfrm/xfrm_user.c
+++ b/net/xfrm/xfrm_user.c
@@ -31,11 +31,6 @@
#include <linux/in6.h>
#endif
-static inline int alg_len(struct xfrm_algo *alg)
-{
- return sizeof(*alg) + ((alg->alg_key_len + 7) / 8);
-}
-
static int verify_one_alg(struct nlattr **attrs, enum xfrm_attr_type_t type)
{
struct nlattr *rt = attrs[type];
@@ -45,7 +40,7 @@ static int verify_one_alg(struct nlattr **attrs, enum xfrm_attr_type_t type)
return 0;
algp = nla_data(rt);
- if (nla_len(rt) < alg_len(algp))
+ if (nla_len(rt) < xfrm_alg_len(algp))
return -EINVAL;
switch (type) {
@@ -204,7 +199,7 @@ static int attach_one_algo(struct xfrm_algo **algpp, u8 *props,
return -ENOSYS;
*props = algo->desc.sadb_alg_id;
- p = kmemdup(ualg, alg_len(ualg), GFP_KERNEL);
+ p = kmemdup(ualg, xfrm_alg_len(ualg), GFP_KERNEL);
if (!p)
return -ENOMEM;
@@ -507,7 +502,6 @@ static int copy_to_user_state_extra(struct xfrm_state *x,
struct xfrm_usersa_info *p,
struct sk_buff *skb)
{
- spin_lock_bh(&x->lock);
copy_to_user_state(x, p);
if (x->coaddr)
@@ -515,12 +509,11 @@ static int copy_to_user_state_extra(struct xfrm_state *x,
if (x->lastused)
NLA_PUT_U64(skb, XFRMA_LASTUSED, x->lastused);
- spin_unlock_bh(&x->lock);
if (x->aalg)
- NLA_PUT(skb, XFRMA_ALG_AUTH, alg_len(x->aalg), x->aalg);
+ NLA_PUT(skb, XFRMA_ALG_AUTH, xfrm_alg_len(x->aalg), x->aalg);
if (x->ealg)
- NLA_PUT(skb, XFRMA_ALG_CRYPT, alg_len(x->ealg), x->ealg);
+ NLA_PUT(skb, XFRMA_ALG_CRYPT, xfrm_alg_len(x->ealg), x->ealg);
if (x->calg)
NLA_PUT(skb, XFRMA_ALG_COMP, sizeof(*(x->calg)), x->calg);
@@ -1980,9 +1973,9 @@ static inline size_t xfrm_sa_len(struct xfrm_state *x)
{
size_t l = 0;
if (x->aalg)
- l += nla_total_size(alg_len(x->aalg));
+ l += nla_total_size(xfrm_alg_len(x->aalg));
if (x->ealg)
- l += nla_total_size(alg_len(x->ealg));
+ l += nla_total_size(xfrm_alg_len(x->ealg));
if (x->calg)
l += nla_total_size(sizeof(*x->calg));
if (x->encap)