aboutsummaryrefslogtreecommitdiffstats
path: root/net/sctp/associola.c
diff options
context:
space:
mode:
Diffstat (limited to 'net/sctp/associola.c')
-rw-r--r--net/sctp/associola.c16
1 files changed, 12 insertions, 4 deletions
diff --git a/net/sctp/associola.c b/net/sctp/associola.c
index b1ef3bc301a5..b45ed1f96921 100644
--- a/net/sctp/associola.c
+++ b/net/sctp/associola.c
@@ -321,6 +321,9 @@ static struct sctp_association *sctp_association_init(struct sctp_association *a
321 asoc->default_timetolive = sp->default_timetolive; 321 asoc->default_timetolive = sp->default_timetolive;
322 asoc->default_rcv_context = sp->default_rcv_context; 322 asoc->default_rcv_context = sp->default_rcv_context;
323 323
324 /* SCTP_GET_ASSOC_STATS COUNTERS */
325 memset(&asoc->stats, 0, sizeof(struct sctp_priv_assoc_stats));
326
324 /* AUTH related initializations */ 327 /* AUTH related initializations */
325 INIT_LIST_HEAD(&asoc->endpoint_shared_keys); 328 INIT_LIST_HEAD(&asoc->endpoint_shared_keys);
326 err = sctp_auth_asoc_copy_shkeys(ep, asoc, gfp); 329 err = sctp_auth_asoc_copy_shkeys(ep, asoc, gfp);
@@ -445,7 +448,7 @@ void sctp_association_free(struct sctp_association *asoc)
445 /* Release the transport structures. */ 448 /* Release the transport structures. */
446 list_for_each_safe(pos, temp, &asoc->peer.transport_addr_list) { 449 list_for_each_safe(pos, temp, &asoc->peer.transport_addr_list) {
447 transport = list_entry(pos, struct sctp_transport, transports); 450 transport = list_entry(pos, struct sctp_transport, transports);
448 list_del(pos); 451 list_del_rcu(pos);
449 sctp_transport_free(transport); 452 sctp_transport_free(transport);
450 } 453 }
451 454
@@ -565,7 +568,7 @@ void sctp_assoc_rm_peer(struct sctp_association *asoc,
565 sctp_assoc_update_retran_path(asoc); 568 sctp_assoc_update_retran_path(asoc);
566 569
567 /* Remove this peer from the list. */ 570 /* Remove this peer from the list. */
568 list_del(&peer->transports); 571 list_del_rcu(&peer->transports);
569 572
570 /* Get the first transport of asoc. */ 573 /* Get the first transport of asoc. */
571 pos = asoc->peer.transport_addr_list.next; 574 pos = asoc->peer.transport_addr_list.next;
@@ -760,12 +763,13 @@ struct sctp_transport *sctp_assoc_add_peer(struct sctp_association *asoc,
760 763
761 /* Set the transport's RTO.initial value */ 764 /* Set the transport's RTO.initial value */
762 peer->rto = asoc->rto_initial; 765 peer->rto = asoc->rto_initial;
766 sctp_max_rto(asoc, peer);
763 767
764 /* Set the peer's active state. */ 768 /* Set the peer's active state. */
765 peer->state = peer_state; 769 peer->state = peer_state;
766 770
767 /* Attach the remote transport to our asoc. */ 771 /* Attach the remote transport to our asoc. */
768 list_add_tail(&peer->transports, &asoc->peer.transport_addr_list); 772 list_add_tail_rcu(&peer->transports, &asoc->peer.transport_addr_list);
769 asoc->peer.transport_count++; 773 asoc->peer.transport_count++;
770 774
771 /* If we do not yet have a primary path, set one. */ 775 /* If we do not yet have a primary path, set one. */
@@ -1152,8 +1156,12 @@ static void sctp_assoc_bh_rcv(struct work_struct *work)
1152 */ 1156 */
1153 if (sctp_chunk_is_data(chunk)) 1157 if (sctp_chunk_is_data(chunk))
1154 asoc->peer.last_data_from = chunk->transport; 1158 asoc->peer.last_data_from = chunk->transport;
1155 else 1159 else {
1156 SCTP_INC_STATS(net, SCTP_MIB_INCTRLCHUNKS); 1160 SCTP_INC_STATS(net, SCTP_MIB_INCTRLCHUNKS);
1161 asoc->stats.ictrlchunks++;
1162 if (chunk->chunk_hdr->type == SCTP_CID_SACK)
1163 asoc->stats.isacks++;
1164 }
1157 1165
1158 if (chunk->transport) 1166 if (chunk->transport)
1159 chunk->transport->last_time_heard = jiffies; 1167 chunk->transport->last_time_heard = jiffies;