X-Git-Url: http://git.rot13.org/?a=blobdiff_plain;f=net%2Fsctp%2Foutqueue.c;h=992f361084b741115f3e14006bb00bb0772a4fcf;hb=3ff50b7997fe06cd5d276b229967bb52d6b3b6c1;hp=5c2ddd10db065629139d0544cc439ffa42e10687;hpb=5a84d159061d914c8dd4aa372ac6e9529c2be453;p=powerpc.git diff --git a/net/sctp/outqueue.c b/net/sctp/outqueue.c index 5c2ddd10db..992f361084 100644 --- a/net/sctp/outqueue.c +++ b/net/sctp/outqueue.c @@ -338,7 +338,7 @@ int sctp_outq_tail(struct sctp_outq *q, struct sctp_chunk *chunk) SCTP_INC_STATS(SCTP_MIB_OUTORDERCHUNKS); q->empty = 0; break; - }; + } } else { list_add_tail(&chunk->list, &q->control_chunk_list); SCTP_INC_STATS(SCTP_MIB_OUTCTRLCHUNKS); @@ -396,6 +396,19 @@ void sctp_retransmit_mark(struct sctp_outq *q, if (sctp_chunk_abandoned(chunk)) { list_del_init(lchunk); sctp_insert_list(&q->abandoned, lchunk); + + /* If this chunk has not been previousely acked, + * stop considering it 'outstanding'. Our peer + * will most likely never see it since it will + * not be retransmitted + */ + if (!chunk->tsn_gap_acked) { + chunk->transport->flight_size -= + sctp_data_size(chunk); + q->outstanding_bytes -= sctp_data_size(chunk); + q->asoc->peer.rwnd += (sctp_data_size(chunk) + + sizeof(struct sk_buff)); + } continue; } @@ -617,7 +630,7 @@ static int sctp_outq_flush_rtx(struct sctp_outq *q, struct sctp_packet *pkt, /* Retrieve a new chunk to bundle. */ lchunk = sctp_list_dequeue(lqueue); break; - }; + } /* If we are here due to a retransmit timeout or a fast * retransmit and if there are any chunks left in the retransmit @@ -766,7 +779,7 @@ int sctp_outq_flush(struct sctp_outq *q, int rtx_timeout) default: /* We built a chunk with an illegal type! */ BUG(); - }; + } } /* Is it OK to send data chunks? */ @@ -1244,6 +1257,15 @@ static void sctp_check_transmitted(struct sctp_outq *q, if (sctp_chunk_abandoned(tchunk)) { /* Move the chunk to abandoned list. */ sctp_insert_list(&q->abandoned, lchunk); + + /* If this chunk has not been acked, stop + * considering it as 'outstanding'. + */ + if (!tchunk->tsn_gap_acked) { + tchunk->transport->flight_size -= + sctp_data_size(tchunk); + q->outstanding_bytes -= sctp_data_size(tchunk); + } continue; } @@ -1375,7 +1397,7 @@ static void sctp_check_transmitted(struct sctp_outq *q, SCTP_DEBUG_PRINTK("ACKed: %08x", tsn); dbg_prt_state = 0; dbg_ack_tsn = tsn; - }; + } dbg_last_ack_tsn = tsn; #endif /* SCTP_DEBUG */ @@ -1430,7 +1452,7 @@ static void sctp_check_transmitted(struct sctp_outq *q, SCTP_DEBUG_PRINTK("KEPT: %08x",tsn); dbg_prt_state = 1; dbg_kept_tsn = tsn; - }; + } dbg_last_kept_tsn = tsn; #endif /* SCTP_DEBUG */ @@ -1454,7 +1476,7 @@ static void sctp_check_transmitted(struct sctp_outq *q, } else { SCTP_DEBUG_PRINTK("\n"); } - }; + } #endif /* SCTP_DEBUG */ if (transport) { if (bytes_acked) { @@ -1695,11 +1717,6 @@ static void sctp_generate_fwdtsn(struct sctp_outq *q, __u32 ctsn) */ if (TSN_lte(tsn, ctsn)) { list_del_init(lchunk); - if (!chunk->tsn_gap_acked) { - chunk->transport->flight_size -= - sctp_data_size(chunk); - q->outstanding_bytes -= sctp_data_size(chunk); - } sctp_chunk_free(chunk); } else { if (TSN_lte(tsn, asoc->adv_peer_ack_point+1)) {