aboutsummaryrefslogtreecommitdiffstats
path: root/net/sctp/outqueue.c
diff options
context:
space:
mode:
Diffstat (limited to 'net/sctp/outqueue.c')
-rw-r--r--net/sctp/outqueue.c96
1 files changed, 41 insertions, 55 deletions
diff --git a/net/sctp/outqueue.c b/net/sctp/outqueue.c
index abfc0b8dee74..c04b2eb59186 100644
--- a/net/sctp/outqueue.c
+++ b/net/sctp/outqueue.c
@@ -62,7 +62,7 @@ static void sctp_check_transmitted(struct sctp_outq *q,
62 struct list_head *transmitted_queue, 62 struct list_head *transmitted_queue,
63 struct sctp_transport *transport, 63 struct sctp_transport *transport,
64 struct sctp_sackhdr *sack, 64 struct sctp_sackhdr *sack,
65 __u32 highest_new_tsn); 65 __u32 *highest_new_tsn);
66 66
67static void sctp_mark_missing(struct sctp_outq *q, 67static void sctp_mark_missing(struct sctp_outq *q,
68 struct list_head *transmitted_queue, 68 struct list_head *transmitted_queue,
@@ -80,7 +80,6 @@ static inline void sctp_outq_head_data(struct sctp_outq *q,
80{ 80{
81 list_add(&ch->list, &q->out_chunk_list); 81 list_add(&ch->list, &q->out_chunk_list);
82 q->out_qlen += ch->skb->len; 82 q->out_qlen += ch->skb->len;
83 return;
84} 83}
85 84
86/* Take data from the front of the queue. */ 85/* Take data from the front of the queue. */
@@ -103,7 +102,6 @@ static inline void sctp_outq_tail_data(struct sctp_outq *q,
103{ 102{
104 list_add_tail(&ch->list, &q->out_chunk_list); 103 list_add_tail(&ch->list, &q->out_chunk_list);
105 q->out_qlen += ch->skb->len; 104 q->out_qlen += ch->skb->len;
106 return;
107} 105}
108 106
109/* 107/*
@@ -308,7 +306,7 @@ int sctp_outq_tail(struct sctp_outq *q, struct sctp_chunk *chunk)
308 /* If it is data, queue it up, otherwise, send it 306 /* If it is data, queue it up, otherwise, send it
309 * immediately. 307 * immediately.
310 */ 308 */
311 if (SCTP_CID_DATA == chunk->chunk_hdr->type) { 309 if (sctp_chunk_is_data(chunk)) {
312 /* Is it OK to queue data chunks? */ 310 /* Is it OK to queue data chunks? */
313 /* From 9. Termination of Association 311 /* From 9. Termination of Association
314 * 312 *
@@ -598,11 +596,23 @@ static int sctp_outq_flush_rtx(struct sctp_outq *q, struct sctp_packet *pkt,
598 if (fast_rtx && !chunk->fast_retransmit) 596 if (fast_rtx && !chunk->fast_retransmit)
599 continue; 597 continue;
600 598
599redo:
601 /* Attempt to append this chunk to the packet. */ 600 /* Attempt to append this chunk to the packet. */
602 status = sctp_packet_append_chunk(pkt, chunk); 601 status = sctp_packet_append_chunk(pkt, chunk);
603 602
604 switch (status) { 603 switch (status) {
605 case SCTP_XMIT_PMTU_FULL: 604 case SCTP_XMIT_PMTU_FULL:
605 if (!pkt->has_data && !pkt->has_cookie_echo) {
606 /* If this packet did not contain DATA then
607 * retransmission did not happen, so do it
608 * again. We'll ignore the error here since
609 * control chunks are already freed so there
610 * is nothing we can do.
611 */
612 sctp_packet_transmit(pkt);
613 goto redo;
614 }
615
606 /* Send this packet. */ 616 /* Send this packet. */
607 error = sctp_packet_transmit(pkt); 617 error = sctp_packet_transmit(pkt);
608 618
@@ -647,14 +657,6 @@ static int sctp_outq_flush_rtx(struct sctp_outq *q, struct sctp_packet *pkt,
647 if (chunk->fast_retransmit == SCTP_NEED_FRTX) 657 if (chunk->fast_retransmit == SCTP_NEED_FRTX)
648 chunk->fast_retransmit = SCTP_DONT_FRTX; 658 chunk->fast_retransmit = SCTP_DONT_FRTX;
649 659
650 /* Force start T3-rtx timer when fast retransmitting
651 * the earliest outstanding TSN
652 */
653 if (!timer && fast_rtx &&
654 ntohl(chunk->subh.data_hdr->tsn) ==
655 asoc->ctsn_ack_point + 1)
656 timer = 2;
657
658 q->empty = 0; 660 q->empty = 0;
659 break; 661 break;
660 } 662 }
@@ -854,6 +856,12 @@ static int sctp_outq_flush(struct sctp_outq *q, int rtx_timeout)
854 if (status != SCTP_XMIT_OK) { 856 if (status != SCTP_XMIT_OK) {
855 /* put the chunk back */ 857 /* put the chunk back */
856 list_add(&chunk->list, &q->control_chunk_list); 858 list_add(&chunk->list, &q->control_chunk_list);
859 } else if (chunk->chunk_hdr->type == SCTP_CID_FWD_TSN) {
860 /* PR-SCTP C5) If a FORWARD TSN is sent, the
861 * sender MUST assure that at least one T3-rtx
862 * timer is running.
863 */
864 sctp_transport_reset_timers(transport);
857 } 865 }
858 break; 866 break;
859 867
@@ -906,8 +914,7 @@ static int sctp_outq_flush(struct sctp_outq *q, int rtx_timeout)
906 rtx_timeout, &start_timer); 914 rtx_timeout, &start_timer);
907 915
908 if (start_timer) 916 if (start_timer)
909 sctp_transport_reset_timers(transport, 917 sctp_transport_reset_timers(transport);
910 start_timer-1);
911 918
912 /* This can happen on COOKIE-ECHO resend. Only 919 /* This can happen on COOKIE-ECHO resend. Only
913 * one chunk can get bundled with a COOKIE-ECHO. 920 * one chunk can get bundled with a COOKIE-ECHO.
@@ -1040,7 +1047,7 @@ static int sctp_outq_flush(struct sctp_outq *q, int rtx_timeout)
1040 list_add_tail(&chunk->transmitted_list, 1047 list_add_tail(&chunk->transmitted_list,
1041 &transport->transmitted); 1048 &transport->transmitted);
1042 1049
1043 sctp_transport_reset_timers(transport, 0); 1050 sctp_transport_reset_timers(transport);
1044 1051
1045 q->empty = 0; 1052 q->empty = 0;
1046 1053
@@ -1100,32 +1107,6 @@ static void sctp_sack_update_unack_data(struct sctp_association *assoc,
1100 assoc->unack_data = unack_data; 1107 assoc->unack_data = unack_data;
1101} 1108}
1102 1109
1103/* Return the highest new tsn that is acknowledged by the given SACK chunk. */
1104static __u32 sctp_highest_new_tsn(struct sctp_sackhdr *sack,
1105 struct sctp_association *asoc)
1106{
1107 struct sctp_transport *transport;
1108 struct sctp_chunk *chunk;
1109 __u32 highest_new_tsn, tsn;
1110 struct list_head *transport_list = &asoc->peer.transport_addr_list;
1111
1112 highest_new_tsn = ntohl(sack->cum_tsn_ack);
1113
1114 list_for_each_entry(transport, transport_list, transports) {
1115 list_for_each_entry(chunk, &transport->transmitted,
1116 transmitted_list) {
1117 tsn = ntohl(chunk->subh.data_hdr->tsn);
1118
1119 if (!chunk->tsn_gap_acked &&
1120 TSN_lt(highest_new_tsn, tsn) &&
1121 sctp_acked(sack, tsn))
1122 highest_new_tsn = tsn;
1123 }
1124 }
1125
1126 return highest_new_tsn;
1127}
1128
1129/* This is where we REALLY process a SACK. 1110/* This is where we REALLY process a SACK.
1130 * 1111 *
1131 * Process the SACK against the outqueue. Mostly, this just frees 1112 * Process the SACK against the outqueue. Mostly, this just frees
@@ -1145,6 +1126,7 @@ int sctp_outq_sack(struct sctp_outq *q, struct sctp_sackhdr *sack)
1145 struct sctp_transport *primary = asoc->peer.primary_path; 1126 struct sctp_transport *primary = asoc->peer.primary_path;
1146 int count_of_newacks = 0; 1127 int count_of_newacks = 0;
1147 int gap_ack_blocks; 1128 int gap_ack_blocks;
1129 u8 accum_moved = 0;
1148 1130
1149 /* Grab the association's destination address list. */ 1131 /* Grab the association's destination address list. */
1150 transport_list = &asoc->peer.transport_addr_list; 1132 transport_list = &asoc->peer.transport_addr_list;
@@ -1193,18 +1175,15 @@ int sctp_outq_sack(struct sctp_outq *q, struct sctp_sackhdr *sack)
1193 if (gap_ack_blocks) 1175 if (gap_ack_blocks)
1194 highest_tsn += ntohs(frags[gap_ack_blocks - 1].gab.end); 1176 highest_tsn += ntohs(frags[gap_ack_blocks - 1].gab.end);
1195 1177
1196 if (TSN_lt(asoc->highest_sacked, highest_tsn)) { 1178 if (TSN_lt(asoc->highest_sacked, highest_tsn))
1197 highest_new_tsn = highest_tsn;
1198 asoc->highest_sacked = highest_tsn; 1179 asoc->highest_sacked = highest_tsn;
1199 } else {
1200 highest_new_tsn = sctp_highest_new_tsn(sack, asoc);
1201 }
1202 1180
1181 highest_new_tsn = sack_ctsn;
1203 1182
1204 /* Run through the retransmit queue. Credit bytes received 1183 /* Run through the retransmit queue. Credit bytes received
1205 * and free those chunks that we can. 1184 * and free those chunks that we can.
1206 */ 1185 */
1207 sctp_check_transmitted(q, &q->retransmit, NULL, sack, highest_new_tsn); 1186 sctp_check_transmitted(q, &q->retransmit, NULL, sack, &highest_new_tsn);
1208 1187
1209 /* Run through the transmitted queue. 1188 /* Run through the transmitted queue.
1210 * Credit bytes received and free those chunks which we can. 1189 * Credit bytes received and free those chunks which we can.
@@ -1213,7 +1192,7 @@ int sctp_outq_sack(struct sctp_outq *q, struct sctp_sackhdr *sack)
1213 */ 1192 */
1214 list_for_each_entry(transport, transport_list, transports) { 1193 list_for_each_entry(transport, transport_list, transports) {
1215 sctp_check_transmitted(q, &transport->transmitted, 1194 sctp_check_transmitted(q, &transport->transmitted,
1216 transport, sack, highest_new_tsn); 1195 transport, sack, &highest_new_tsn);
1217 /* 1196 /*
1218 * SFR-CACC algorithm: 1197 * SFR-CACC algorithm:
1219 * C) Let count_of_newacks be the number of 1198 * C) Let count_of_newacks be the number of
@@ -1223,16 +1202,22 @@ int sctp_outq_sack(struct sctp_outq *q, struct sctp_sackhdr *sack)
1223 count_of_newacks ++; 1202 count_of_newacks ++;
1224 } 1203 }
1225 1204
1205 /* Move the Cumulative TSN Ack Point if appropriate. */
1206 if (TSN_lt(asoc->ctsn_ack_point, sack_ctsn)) {
1207 asoc->ctsn_ack_point = sack_ctsn;
1208 accum_moved = 1;
1209 }
1210
1226 if (gap_ack_blocks) { 1211 if (gap_ack_blocks) {
1212
1213 if (asoc->fast_recovery && accum_moved)
1214 highest_new_tsn = highest_tsn;
1215
1227 list_for_each_entry(transport, transport_list, transports) 1216 list_for_each_entry(transport, transport_list, transports)
1228 sctp_mark_missing(q, &transport->transmitted, transport, 1217 sctp_mark_missing(q, &transport->transmitted, transport,
1229 highest_new_tsn, count_of_newacks); 1218 highest_new_tsn, count_of_newacks);
1230 } 1219 }
1231 1220
1232 /* Move the Cumulative TSN Ack Point if appropriate. */
1233 if (TSN_lt(asoc->ctsn_ack_point, sack_ctsn))
1234 asoc->ctsn_ack_point = sack_ctsn;
1235
1236 /* Update unack_data field in the assoc. */ 1221 /* Update unack_data field in the assoc. */
1237 sctp_sack_update_unack_data(asoc, sack); 1222 sctp_sack_update_unack_data(asoc, sack);
1238 1223
@@ -1315,7 +1300,7 @@ static void sctp_check_transmitted(struct sctp_outq *q,
1315 struct list_head *transmitted_queue, 1300 struct list_head *transmitted_queue,
1316 struct sctp_transport *transport, 1301 struct sctp_transport *transport,
1317 struct sctp_sackhdr *sack, 1302 struct sctp_sackhdr *sack,
1318 __u32 highest_new_tsn_in_sack) 1303 __u32 *highest_new_tsn_in_sack)
1319{ 1304{
1320 struct list_head *lchunk; 1305 struct list_head *lchunk;
1321 struct sctp_chunk *tchunk; 1306 struct sctp_chunk *tchunk;
@@ -1387,7 +1372,6 @@ static void sctp_check_transmitted(struct sctp_outq *q,
1387 * instance). 1372 * instance).
1388 */ 1373 */
1389 if (!tchunk->tsn_gap_acked && 1374 if (!tchunk->tsn_gap_acked &&
1390 !tchunk->resent &&
1391 tchunk->rtt_in_progress) { 1375 tchunk->rtt_in_progress) {
1392 tchunk->rtt_in_progress = 0; 1376 tchunk->rtt_in_progress = 0;
1393 rtt = jiffies - tchunk->sent_at; 1377 rtt = jiffies - tchunk->sent_at;
@@ -1404,6 +1388,7 @@ static void sctp_check_transmitted(struct sctp_outq *q,
1404 */ 1388 */
1405 if (!tchunk->tsn_gap_acked) { 1389 if (!tchunk->tsn_gap_acked) {
1406 tchunk->tsn_gap_acked = 1; 1390 tchunk->tsn_gap_acked = 1;
1391 *highest_new_tsn_in_sack = tsn;
1407 bytes_acked += sctp_data_size(tchunk); 1392 bytes_acked += sctp_data_size(tchunk);
1408 if (!tchunk->transport) 1393 if (!tchunk->transport)
1409 migrate_bytes += sctp_data_size(tchunk); 1394 migrate_bytes += sctp_data_size(tchunk);
@@ -1677,7 +1662,8 @@ static void sctp_mark_missing(struct sctp_outq *q,
1677 struct sctp_chunk *chunk; 1662 struct sctp_chunk *chunk;
1678 __u32 tsn; 1663 __u32 tsn;
1679 char do_fast_retransmit = 0; 1664 char do_fast_retransmit = 0;
1680 struct sctp_transport *primary = q->asoc->peer.primary_path; 1665 struct sctp_association *asoc = q->asoc;
1666 struct sctp_transport *primary = asoc->peer.primary_path;
1681 1667
1682 list_for_each_entry(chunk, transmitted_queue, transmitted_list) { 1668 list_for_each_entry(chunk, transmitted_queue, transmitted_list) {
1683 1669