mirror of
https://github.com/BobTheBlinker/android_kernel_motorola_sm6375.git
synced 2026-10-30 11:41:38 -04:00
Merge git://git.kernel.org/pub/scm/linux/kernel/git/davem/net-2.6
* git://git.kernel.org/pub/scm/linux/kernel/git/davem/net-2.6: e100: Use pci_pme_active to clear PME_Status and disable PME# e1000: prevent corruption of EEPROM/NVM forcedeth: call restore mac addr in nv_shutdown path bnx2: Promote vector field in bnx2_irq structure from u16 to unsigned int sctp: Fix oops when INIT-ACK indicates that peer doesn't support AUTH sctp: do not enable peer features if we can't do them. sctp: set the skb->ip_summed correctly when sending over loopback. udp: Fix rcv socket locking
This commit is contained in:
commit
764527a1b3
8 changed files with 87 additions and 47 deletions
|
|
@ -951,6 +951,27 @@ int udp_disconnect(struct sock *sk, int flags)
|
|||
return 0;
|
||||
}
|
||||
|
||||
static int __udp_queue_rcv_skb(struct sock *sk, struct sk_buff *skb)
|
||||
{
|
||||
int is_udplite = IS_UDPLITE(sk);
|
||||
int rc;
|
||||
|
||||
if ((rc = sock_queue_rcv_skb(sk, skb)) < 0) {
|
||||
/* Note that an ENOMEM error is charged twice */
|
||||
if (rc == -ENOMEM)
|
||||
UDP_INC_STATS_BH(sock_net(sk), UDP_MIB_RCVBUFERRORS,
|
||||
is_udplite);
|
||||
goto drop;
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
||||
drop:
|
||||
UDP_INC_STATS_BH(sock_net(sk), UDP_MIB_INERRORS, is_udplite);
|
||||
kfree_skb(skb);
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* returns:
|
||||
* -1: error
|
||||
* 0: success
|
||||
|
|
@ -989,9 +1010,7 @@ int udp_queue_rcv_skb(struct sock * sk, struct sk_buff *skb)
|
|||
up->encap_rcv != NULL) {
|
||||
int ret;
|
||||
|
||||
bh_unlock_sock(sk);
|
||||
ret = (*up->encap_rcv)(sk, skb);
|
||||
bh_lock_sock(sk);
|
||||
if (ret <= 0) {
|
||||
UDP_INC_STATS_BH(sock_net(sk),
|
||||
UDP_MIB_INDATAGRAMS,
|
||||
|
|
@ -1044,17 +1063,16 @@ int udp_queue_rcv_skb(struct sock * sk, struct sk_buff *skb)
|
|||
goto drop;
|
||||
}
|
||||
|
||||
if ((rc = sock_queue_rcv_skb(sk,skb)) < 0) {
|
||||
/* Note that an ENOMEM error is charged twice */
|
||||
if (rc == -ENOMEM) {
|
||||
UDP_INC_STATS_BH(sock_net(sk),
|
||||
UDP_MIB_RCVBUFERRORS, is_udplite);
|
||||
atomic_inc(&sk->sk_drops);
|
||||
}
|
||||
goto drop;
|
||||
}
|
||||
rc = 0;
|
||||
|
||||
return 0;
|
||||
bh_lock_sock(sk);
|
||||
if (!sock_owned_by_user(sk))
|
||||
rc = __udp_queue_rcv_skb(sk, skb);
|
||||
else
|
||||
sk_add_backlog(sk, skb);
|
||||
bh_unlock_sock(sk);
|
||||
|
||||
return rc;
|
||||
|
||||
drop:
|
||||
UDP_INC_STATS_BH(sock_net(sk), UDP_MIB_INERRORS, is_udplite);
|
||||
|
|
@ -1092,15 +1110,7 @@ static int __udp4_lib_mcast_deliver(struct net *net, struct sk_buff *skb,
|
|||
skb1 = skb_clone(skb, GFP_ATOMIC);
|
||||
|
||||
if (skb1) {
|
||||
int ret = 0;
|
||||
|
||||
bh_lock_sock(sk);
|
||||
if (!sock_owned_by_user(sk))
|
||||
ret = udp_queue_rcv_skb(sk, skb1);
|
||||
else
|
||||
sk_add_backlog(sk, skb1);
|
||||
bh_unlock_sock(sk);
|
||||
|
||||
int ret = udp_queue_rcv_skb(sk, skb1);
|
||||
if (ret > 0)
|
||||
/* we should probably re-process instead
|
||||
* of dropping packets here. */
|
||||
|
|
@ -1195,13 +1205,7 @@ int __udp4_lib_rcv(struct sk_buff *skb, struct hlist_head udptable[],
|
|||
uh->dest, inet_iif(skb), udptable);
|
||||
|
||||
if (sk != NULL) {
|
||||
int ret = 0;
|
||||
bh_lock_sock(sk);
|
||||
if (!sock_owned_by_user(sk))
|
||||
ret = udp_queue_rcv_skb(sk, skb);
|
||||
else
|
||||
sk_add_backlog(sk, skb);
|
||||
bh_unlock_sock(sk);
|
||||
int ret = udp_queue_rcv_skb(sk, skb);
|
||||
sock_put(sk);
|
||||
|
||||
/* a return value > 0 means to resubmit the input, but
|
||||
|
|
@ -1494,7 +1498,7 @@ struct proto udp_prot = {
|
|||
.sendmsg = udp_sendmsg,
|
||||
.recvmsg = udp_recvmsg,
|
||||
.sendpage = udp_sendpage,
|
||||
.backlog_rcv = udp_queue_rcv_skb,
|
||||
.backlog_rcv = __udp_queue_rcv_skb,
|
||||
.hash = udp_lib_hash,
|
||||
.unhash = udp_lib_unhash,
|
||||
.get_port = udp_v4_get_port,
|
||||
|
|
|
|||
|
|
@ -599,11 +599,12 @@ struct sctp_transport *sctp_assoc_add_peer(struct sctp_association *asoc,
|
|||
/* Check to see if this is a duplicate. */
|
||||
peer = sctp_assoc_lookup_paddr(asoc, addr);
|
||||
if (peer) {
|
||||
/* An UNKNOWN state is only set on transports added by
|
||||
* user in sctp_connectx() call. Such transports should be
|
||||
* considered CONFIRMED per RFC 4960, Section 5.4.
|
||||
*/
|
||||
if (peer->state == SCTP_UNKNOWN) {
|
||||
if (peer_state == SCTP_ACTIVE)
|
||||
peer->state = SCTP_ACTIVE;
|
||||
if (peer_state == SCTP_UNCONFIRMED)
|
||||
peer->state = SCTP_UNCONFIRMED;
|
||||
peer->state = SCTP_ACTIVE;
|
||||
}
|
||||
return peer;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -533,7 +533,8 @@ int sctp_packet_transmit(struct sctp_packet *packet)
|
|||
if (!(dst->dev->features & NETIF_F_NO_CSUM)) {
|
||||
crc32 = sctp_start_cksum((__u8 *)sh, cksum_buf_len);
|
||||
crc32 = sctp_end_cksum(crc32);
|
||||
}
|
||||
} else
|
||||
nskb->ip_summed = CHECKSUM_UNNECESSARY;
|
||||
|
||||
/* 3) Put the resultant value into the checksum field in the
|
||||
* common header, and leave the rest of the bits unchanged.
|
||||
|
|
|
|||
|
|
@ -1886,11 +1886,13 @@ static void sctp_process_ext_param(struct sctp_association *asoc,
|
|||
/* if the peer reports AUTH, assume that he
|
||||
* supports AUTH.
|
||||
*/
|
||||
asoc->peer.auth_capable = 1;
|
||||
if (sctp_auth_enable)
|
||||
asoc->peer.auth_capable = 1;
|
||||
break;
|
||||
case SCTP_CID_ASCONF:
|
||||
case SCTP_CID_ASCONF_ACK:
|
||||
asoc->peer.asconf_capable = 1;
|
||||
if (sctp_addip_enable)
|
||||
asoc->peer.asconf_capable = 1;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
|
|
@ -2319,12 +2321,10 @@ clean_up:
|
|||
/* Release the transport structures. */
|
||||
list_for_each_safe(pos, temp, &asoc->peer.transport_addr_list) {
|
||||
transport = list_entry(pos, struct sctp_transport, transports);
|
||||
list_del_init(pos);
|
||||
sctp_transport_free(transport);
|
||||
if (transport->state != SCTP_ACTIVE)
|
||||
sctp_assoc_rm_peer(asoc, transport);
|
||||
}
|
||||
|
||||
asoc->peer.transport_count = 0;
|
||||
|
||||
nomem:
|
||||
return 0;
|
||||
}
|
||||
|
|
@ -2460,6 +2460,9 @@ do_addr_param:
|
|||
break;
|
||||
|
||||
case SCTP_PARAM_SET_PRIMARY:
|
||||
if (!sctp_addip_enable)
|
||||
goto fall_through;
|
||||
|
||||
addr_param = param.v + sizeof(sctp_addip_param_t);
|
||||
|
||||
af = sctp_get_af_specific(param_type2af(param.p->type));
|
||||
|
|
|
|||
Loading…
Reference in a new issue