mirror of
https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git
synced 2024-09-30 14:19:16 +00:00
Merge branch 'rxrpc-miscellaneous-fixes'
David Howells says: ==================== rxrpc: Miscellaneous fixes (part) Here some miscellaneous fixes for AF_RXRPC: (1) Fix the congestion control algorithm to start cwnd at 4 and to not cut ssthresh when the peer cuts its rwind size. (2) Only transmit a single ACK for all the DATA packets glued together into a jumbo packet to reduce the number of ACKs being generated. ==================== Link: https://lore.kernel.org/r/20240503150749.1001323-1-dhowells@redhat.com Signed-off-by: Jakub Kicinski <kuba@kernel.org>
This commit is contained in:
commit
02754103e1
3 changed files with 37 additions and 21 deletions
|
@ -697,7 +697,7 @@ struct rxrpc_call {
|
|||
* packets) rather than bytes.
|
||||
*/
|
||||
#define RXRPC_TX_SMSS RXRPC_JUMBO_DATALEN
|
||||
#define RXRPC_MIN_CWND (RXRPC_TX_SMSS > 2190 ? 2 : RXRPC_TX_SMSS > 1095 ? 3 : 4)
|
||||
#define RXRPC_MIN_CWND 4
|
||||
u8 cong_cwnd; /* Congestion window size */
|
||||
u8 cong_extra; /* Extra to send for congestion management */
|
||||
u8 cong_ssthresh; /* Slow-start threshold */
|
||||
|
|
|
@ -174,12 +174,7 @@ struct rxrpc_call *rxrpc_alloc_call(struct rxrpc_sock *rx, gfp_t gfp,
|
|||
call->rx_winsize = rxrpc_rx_window_size;
|
||||
call->tx_winsize = 16;
|
||||
|
||||
if (RXRPC_TX_SMSS > 2190)
|
||||
call->cong_cwnd = 2;
|
||||
else if (RXRPC_TX_SMSS > 1095)
|
||||
call->cong_cwnd = 3;
|
||||
else
|
||||
call->cong_cwnd = 4;
|
||||
call->cong_cwnd = RXRPC_MIN_CWND;
|
||||
call->cong_ssthresh = RXRPC_TX_MAX_WINDOW;
|
||||
|
||||
call->rxnet = rxnet;
|
||||
|
|
|
@ -9,6 +9,17 @@
|
|||
|
||||
#include "ar-internal.h"
|
||||
|
||||
/* Override priority when generating ACKs for received DATA */
|
||||
static const u8 rxrpc_ack_priority[RXRPC_ACK__INVALID] = {
|
||||
[RXRPC_ACK_IDLE] = 1,
|
||||
[RXRPC_ACK_DELAY] = 2,
|
||||
[RXRPC_ACK_REQUESTED] = 3,
|
||||
[RXRPC_ACK_DUPLICATE] = 4,
|
||||
[RXRPC_ACK_EXCEEDS_WINDOW] = 5,
|
||||
[RXRPC_ACK_NOSPACE] = 6,
|
||||
[RXRPC_ACK_OUT_OF_SEQUENCE] = 7,
|
||||
};
|
||||
|
||||
static void rxrpc_proto_abort(struct rxrpc_call *call, rxrpc_seq_t seq,
|
||||
enum rxrpc_abort_reason why)
|
||||
{
|
||||
|
@ -365,7 +376,7 @@ static void rxrpc_input_queue_data(struct rxrpc_call *call, struct sk_buff *skb,
|
|||
* Process a DATA packet.
|
||||
*/
|
||||
static void rxrpc_input_data_one(struct rxrpc_call *call, struct sk_buff *skb,
|
||||
bool *_notify)
|
||||
bool *_notify, rxrpc_serial_t *_ack_serial, int *_ack_reason)
|
||||
{
|
||||
struct rxrpc_skb_priv *sp = rxrpc_skb(skb);
|
||||
struct sk_buff *oos;
|
||||
|
@ -418,8 +429,6 @@ static void rxrpc_input_data_one(struct rxrpc_call *call, struct sk_buff *skb,
|
|||
/* Send an immediate ACK if we fill in a hole */
|
||||
else if (!skb_queue_empty(&call->rx_oos_queue))
|
||||
ack_reason = RXRPC_ACK_DELAY;
|
||||
else
|
||||
call->ackr_nr_unacked++;
|
||||
|
||||
window++;
|
||||
if (after(window, wtop)) {
|
||||
|
@ -497,12 +506,16 @@ static void rxrpc_input_data_one(struct rxrpc_call *call, struct sk_buff *skb,
|
|||
}
|
||||
|
||||
send_ack:
|
||||
if (ack_reason >= 0)
|
||||
rxrpc_send_ACK(call, ack_reason, serial,
|
||||
rxrpc_propose_ack_input_data);
|
||||
else
|
||||
rxrpc_propose_delay_ACK(call, serial,
|
||||
rxrpc_propose_ack_input_data);
|
||||
if (ack_reason >= 0) {
|
||||
if (rxrpc_ack_priority[ack_reason] > rxrpc_ack_priority[*_ack_reason]) {
|
||||
*_ack_serial = serial;
|
||||
*_ack_reason = ack_reason;
|
||||
} else if (rxrpc_ack_priority[ack_reason] == rxrpc_ack_priority[*_ack_reason] &&
|
||||
ack_reason == RXRPC_ACK_REQUESTED) {
|
||||
*_ack_serial = serial;
|
||||
*_ack_reason = ack_reason;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -513,9 +526,11 @@ static bool rxrpc_input_split_jumbo(struct rxrpc_call *call, struct sk_buff *skb
|
|||
struct rxrpc_jumbo_header jhdr;
|
||||
struct rxrpc_skb_priv *sp = rxrpc_skb(skb), *jsp;
|
||||
struct sk_buff *jskb;
|
||||
rxrpc_serial_t ack_serial = 0;
|
||||
unsigned int offset = sizeof(struct rxrpc_wire_header);
|
||||
unsigned int len = skb->len - offset;
|
||||
bool notify = false;
|
||||
int ack_reason = 0;
|
||||
|
||||
while (sp->hdr.flags & RXRPC_JUMBO_PACKET) {
|
||||
if (len < RXRPC_JUMBO_SUBPKTLEN)
|
||||
|
@ -535,7 +550,7 @@ static bool rxrpc_input_split_jumbo(struct rxrpc_call *call, struct sk_buff *skb
|
|||
jsp = rxrpc_skb(jskb);
|
||||
jsp->offset = offset;
|
||||
jsp->len = RXRPC_JUMBO_DATALEN;
|
||||
rxrpc_input_data_one(call, jskb, ¬ify);
|
||||
rxrpc_input_data_one(call, jskb, ¬ify, &ack_serial, &ack_reason);
|
||||
rxrpc_free_skb(jskb, rxrpc_skb_put_jumbo_subpacket);
|
||||
|
||||
sp->hdr.flags = jhdr.flags;
|
||||
|
@ -548,7 +563,16 @@ static bool rxrpc_input_split_jumbo(struct rxrpc_call *call, struct sk_buff *skb
|
|||
|
||||
sp->offset = offset;
|
||||
sp->len = len;
|
||||
rxrpc_input_data_one(call, skb, ¬ify);
|
||||
rxrpc_input_data_one(call, skb, ¬ify, &ack_serial, &ack_reason);
|
||||
|
||||
if (ack_reason > 0) {
|
||||
rxrpc_send_ACK(call, ack_reason, ack_serial,
|
||||
rxrpc_propose_ack_input_data);
|
||||
} else {
|
||||
call->ackr_nr_unacked++;
|
||||
rxrpc_propose_delay_ACK(call, sp->hdr.serial,
|
||||
rxrpc_propose_ack_input_data);
|
||||
}
|
||||
if (notify) {
|
||||
trace_rxrpc_notify_socket(call->debug_id, sp->hdr.serial);
|
||||
rxrpc_notify_socket(call);
|
||||
|
@ -685,9 +709,6 @@ static void rxrpc_input_ack_trailer(struct rxrpc_call *call, struct sk_buff *skb
|
|||
call->tx_winsize = rwind;
|
||||
}
|
||||
|
||||
if (call->cong_ssthresh > rwind)
|
||||
call->cong_ssthresh = rwind;
|
||||
|
||||
mtu = min(ntohl(trailer->maxMTU), ntohl(trailer->ifMTU));
|
||||
|
||||
peer = call->peer;
|
||||
|
|
Loading…
Reference in a new issue