diff options
Diffstat (limited to 'net/sctp/outqueue.c')
-rw-r--r-- | net/sctp/outqueue.c | 34 |
1 files changed, 24 insertions, 10 deletions
diff --git a/net/sctp/outqueue.c b/net/sctp/outqueue.c index ace6770e9048..70ead8dc3485 100644 --- a/net/sctp/outqueue.c +++ b/net/sctp/outqueue.c | |||
@@ -702,6 +702,7 @@ int sctp_outq_uncork(struct sctp_outq *q) | |||
702 | return error; | 702 | return error; |
703 | } | 703 | } |
704 | 704 | ||
705 | |||
705 | /* | 706 | /* |
706 | * Try to flush an outqueue. | 707 | * Try to flush an outqueue. |
707 | * | 708 | * |
@@ -725,6 +726,7 @@ int sctp_outq_flush(struct sctp_outq *q, int rtx_timeout) | |||
725 | sctp_xmit_t status; | 726 | sctp_xmit_t status; |
726 | int error = 0; | 727 | int error = 0; |
727 | int start_timer = 0; | 728 | int start_timer = 0; |
729 | int one_packet = 0; | ||
728 | 730 | ||
729 | /* These transports have chunks to send. */ | 731 | /* These transports have chunks to send. */ |
730 | struct list_head transport_list; | 732 | struct list_head transport_list; |
@@ -830,20 +832,33 @@ int sctp_outq_flush(struct sctp_outq *q, int rtx_timeout) | |||
830 | if (sctp_test_T_bit(chunk)) { | 832 | if (sctp_test_T_bit(chunk)) { |
831 | packet->vtag = asoc->c.my_vtag; | 833 | packet->vtag = asoc->c.my_vtag; |
832 | } | 834 | } |
833 | case SCTP_CID_SACK: | 835 | /* The following chunks are "response" chunks, i.e. |
834 | case SCTP_CID_HEARTBEAT: | 836 | * they are generated in response to something we |
837 | * received. If we are sending these, then we can | ||
838 | * send only 1 packet containing these chunks. | ||
839 | */ | ||
835 | case SCTP_CID_HEARTBEAT_ACK: | 840 | case SCTP_CID_HEARTBEAT_ACK: |
836 | case SCTP_CID_SHUTDOWN: | ||
837 | case SCTP_CID_SHUTDOWN_ACK: | 841 | case SCTP_CID_SHUTDOWN_ACK: |
838 | case SCTP_CID_ERROR: | ||
839 | case SCTP_CID_COOKIE_ECHO: | ||
840 | case SCTP_CID_COOKIE_ACK: | 842 | case SCTP_CID_COOKIE_ACK: |
841 | case SCTP_CID_ECN_ECNE: | 843 | case SCTP_CID_COOKIE_ECHO: |
844 | case SCTP_CID_ERROR: | ||
842 | case SCTP_CID_ECN_CWR: | 845 | case SCTP_CID_ECN_CWR: |
843 | case SCTP_CID_ASCONF: | ||
844 | case SCTP_CID_ASCONF_ACK: | 846 | case SCTP_CID_ASCONF_ACK: |
847 | one_packet = 1; | ||
848 | /* Fall throught */ | ||
849 | |||
850 | case SCTP_CID_SACK: | ||
851 | case SCTP_CID_HEARTBEAT: | ||
852 | case SCTP_CID_SHUTDOWN: | ||
853 | case SCTP_CID_ECN_ECNE: | ||
854 | case SCTP_CID_ASCONF: | ||
845 | case SCTP_CID_FWD_TSN: | 855 | case SCTP_CID_FWD_TSN: |
846 | sctp_packet_transmit_chunk(packet, chunk); | 856 | status = sctp_packet_transmit_chunk(packet, chunk, |
857 | one_packet); | ||
858 | if (status != SCTP_XMIT_OK) { | ||
859 | /* put the chunk back */ | ||
860 | list_add(&chunk->list, &q->control_chunk_list); | ||
861 | } | ||
847 | break; | 862 | break; |
848 | 863 | ||
849 | default: | 864 | default: |
@@ -974,7 +989,7 @@ int sctp_outq_flush(struct sctp_outq *q, int rtx_timeout) | |||
974 | atomic_read(&chunk->skb->users) : -1); | 989 | atomic_read(&chunk->skb->users) : -1); |
975 | 990 | ||
976 | /* Add the chunk to the packet. */ | 991 | /* Add the chunk to the packet. */ |
977 | status = sctp_packet_transmit_chunk(packet, chunk); | 992 | status = sctp_packet_transmit_chunk(packet, chunk, 0); |
978 | 993 | ||
979 | switch (status) { | 994 | switch (status) { |
980 | case SCTP_XMIT_PMTU_FULL: | 995 | case SCTP_XMIT_PMTU_FULL: |
@@ -1239,7 +1254,6 @@ int sctp_outq_sack(struct sctp_outq *q, struct sctp_sackhdr *sack) | |||
1239 | * Make sure the empty queue handler will get run later. | 1254 | * Make sure the empty queue handler will get run later. |
1240 | */ | 1255 | */ |
1241 | q->empty = (list_empty(&q->out_chunk_list) && | 1256 | q->empty = (list_empty(&q->out_chunk_list) && |
1242 | list_empty(&q->control_chunk_list) && | ||
1243 | list_empty(&q->retransmit)); | 1257 | list_empty(&q->retransmit)); |
1244 | if (!q->empty) | 1258 | if (!q->empty) |
1245 | goto finish; | 1259 | goto finish; |