|
@@ -382,7 +382,7 @@ static void sctp_insert_list(struct list_head *head, struct list_head *new)
|
|
/* Mark all the eligible packets on a transport for retransmission. */
|
|
/* Mark all the eligible packets on a transport for retransmission. */
|
|
void sctp_retransmit_mark(struct sctp_outq *q,
|
|
void sctp_retransmit_mark(struct sctp_outq *q,
|
|
struct sctp_transport *transport,
|
|
struct sctp_transport *transport,
|
|
- __u8 fast_retransmit)
|
|
|
|
|
|
+ __u8 reason)
|
|
{
|
|
{
|
|
struct list_head *lchunk, *ltemp;
|
|
struct list_head *lchunk, *ltemp;
|
|
struct sctp_chunk *chunk;
|
|
struct sctp_chunk *chunk;
|
|
@@ -412,20 +412,20 @@ void sctp_retransmit_mark(struct sctp_outq *q,
|
|
continue;
|
|
continue;
|
|
}
|
|
}
|
|
|
|
|
|
- /* If we are doing retransmission due to a fast retransmit,
|
|
|
|
- * only the chunk's that are marked for fast retransmit
|
|
|
|
- * should be added to the retransmit queue. If we are doing
|
|
|
|
- * retransmission due to a timeout or pmtu discovery, only the
|
|
|
|
- * chunks that are not yet acked should be added to the
|
|
|
|
- * retransmit queue.
|
|
|
|
|
|
+ /* If we are doing retransmission due to a timeout or pmtu
|
|
|
|
+ * discovery, only the chunks that are not yet acked should
|
|
|
|
+ * be added to the retransmit queue.
|
|
*/
|
|
*/
|
|
- if ((fast_retransmit && (chunk->fast_retransmit > 0)) ||
|
|
|
|
- (!fast_retransmit && !chunk->tsn_gap_acked)) {
|
|
|
|
|
|
+ if ((reason == SCTP_RTXR_FAST_RTX &&
|
|
|
|
+ (chunk->fast_retransmit > 0)) ||
|
|
|
|
+ (reason != SCTP_RTXR_FAST_RTX && !chunk->tsn_gap_acked)) {
|
|
/* If this chunk was sent less then 1 rto ago, do not
|
|
/* If this chunk was sent less then 1 rto ago, do not
|
|
* retransmit this chunk, but give the peer time
|
|
* retransmit this chunk, but give the peer time
|
|
- * to acknowlege it.
|
|
|
|
|
|
+ * to acknowlege it. Do this only when
|
|
|
|
+ * retransmitting due to T3 timeout.
|
|
*/
|
|
*/
|
|
- if ((jiffies - chunk->sent_at) < transport->rto)
|
|
|
|
|
|
+ if (reason == SCTP_RTXR_T3_RTX &&
|
|
|
|
+ (jiffies - chunk->sent_at) < transport->last_rto)
|
|
continue;
|
|
continue;
|
|
|
|
|
|
/* RFC 2960 6.2.1 Processing a Received SACK
|
|
/* RFC 2960 6.2.1 Processing a Received SACK
|
|
@@ -467,10 +467,10 @@ void sctp_retransmit_mark(struct sctp_outq *q,
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
|
|
- SCTP_DEBUG_PRINTK("%s: transport: %p, fast_retransmit: %d, "
|
|
|
|
|
|
+ SCTP_DEBUG_PRINTK("%s: transport: %p, reason: %d, "
|
|
"cwnd: %d, ssthresh: %d, flight_size: %d, "
|
|
"cwnd: %d, ssthresh: %d, flight_size: %d, "
|
|
"pba: %d\n", __FUNCTION__,
|
|
"pba: %d\n", __FUNCTION__,
|
|
- transport, fast_retransmit,
|
|
|
|
|
|
+ transport, reason,
|
|
transport->cwnd, transport->ssthresh,
|
|
transport->cwnd, transport->ssthresh,
|
|
transport->flight_size,
|
|
transport->flight_size,
|
|
transport->partial_bytes_acked);
|
|
transport->partial_bytes_acked);
|
|
@@ -484,7 +484,6 @@ void sctp_retransmit(struct sctp_outq *q, struct sctp_transport *transport,
|
|
sctp_retransmit_reason_t reason)
|
|
sctp_retransmit_reason_t reason)
|
|
{
|
|
{
|
|
int error = 0;
|
|
int error = 0;
|
|
- __u8 fast_retransmit = 0;
|
|
|
|
|
|
|
|
switch(reason) {
|
|
switch(reason) {
|
|
case SCTP_RTXR_T3_RTX:
|
|
case SCTP_RTXR_T3_RTX:
|
|
@@ -499,16 +498,18 @@ void sctp_retransmit(struct sctp_outq *q, struct sctp_transport *transport,
|
|
case SCTP_RTXR_FAST_RTX:
|
|
case SCTP_RTXR_FAST_RTX:
|
|
SCTP_INC_STATS(SCTP_MIB_FAST_RETRANSMITS);
|
|
SCTP_INC_STATS(SCTP_MIB_FAST_RETRANSMITS);
|
|
sctp_transport_lower_cwnd(transport, SCTP_LOWER_CWND_FAST_RTX);
|
|
sctp_transport_lower_cwnd(transport, SCTP_LOWER_CWND_FAST_RTX);
|
|
- fast_retransmit = 1;
|
|
|
|
break;
|
|
break;
|
|
case SCTP_RTXR_PMTUD:
|
|
case SCTP_RTXR_PMTUD:
|
|
SCTP_INC_STATS(SCTP_MIB_PMTUD_RETRANSMITS);
|
|
SCTP_INC_STATS(SCTP_MIB_PMTUD_RETRANSMITS);
|
|
break;
|
|
break;
|
|
|
|
+ case SCTP_RTXR_T1_RTX:
|
|
|
|
+ SCTP_INC_STATS(SCTP_MIB_T1_RETRANSMITS);
|
|
|
|
+ break;
|
|
default:
|
|
default:
|
|
BUG();
|
|
BUG();
|
|
}
|
|
}
|
|
|
|
|
|
- sctp_retransmit_mark(q, transport, fast_retransmit);
|
|
|
|
|
|
+ sctp_retransmit_mark(q, transport, reason);
|
|
|
|
|
|
/* PR-SCTP A5) Any time the T3-rtx timer expires, on any destination,
|
|
/* PR-SCTP A5) Any time the T3-rtx timer expires, on any destination,
|
|
* the sender SHOULD try to advance the "Advanced.Peer.Ack.Point" by
|
|
* the sender SHOULD try to advance the "Advanced.Peer.Ack.Point" by
|