Amalgamate delay acks
diff --git a/include/trace/events/rxrpc.h b/include/trace/events/rxrpc.h
index d8fd57a..5ae06b2 100644
--- a/include/trace/events/rxrpc.h
+++ b/include/trace/events/rxrpc.h
@@ -1277,6 +1277,35 @@ TRACE_EVENT(rxrpc_send_ack,
__entry->serial)
);
+TRACE_EVENT(rxrpc_drop_ack,
+ TP_PROTO(struct rxrpc_call *call, enum rxrpc_propose_ack_trace why,
+ u8 ack_reason, rxrpc_serial_t serial, bool nobuf),
+
+ TP_ARGS(call, why, ack_reason, serial, nobuf),
+
+ TP_STRUCT__entry(
+ __field(unsigned int, call )
+ __field(enum rxrpc_propose_ack_trace, why )
+ __field(rxrpc_serial_t, serial )
+ __field(u8, ack_reason )
+ __field(bool, nobuf )
+ ),
+
+ TP_fast_assign(
+ __entry->call = call->debug_id;
+ __entry->why = why;
+ __entry->serial = serial;
+ __entry->ack_reason = ack_reason;
+ __entry->nobuf = nobuf;
+ ),
+
+ TP_printk("c=%08x %s %s r=%08x nbf=%u",
+ __entry->call,
+ __print_symbolic(__entry->why, rxrpc_propose_ack_traces),
+ __print_symbolic(__entry->ack_reason, rxrpc_ack_names),
+ __entry->serial, __entry->nobuf)
+ );
+
TRACE_EVENT(rxrpc_retransmit,
TP_PROTO(struct rxrpc_call *call, rxrpc_seq_t seq, u8 annotation,
s64 expiry),
diff --git a/net/rxrpc/ar-internal.h b/net/rxrpc/ar-internal.h
index 8ced6dc..a4bd51f 100644
--- a/net/rxrpc/ar-internal.h
+++ b/net/rxrpc/ar-internal.h
@@ -499,6 +499,7 @@ enum rxrpc_call_flag {
RXRPC_CALL_RX_UNDERRUN, /* Got data underrun */
RXRPC_CALL_IS_INTR, /* The call is interruptible */
RXRPC_CALL_DISCONNECTED, /* The call has been disconnected */
+ RXRPC_CALL_DELAY_ACK_PENDING, /* DELAY ACK generation is pending */
};
/*
diff --git a/net/rxrpc/call_event.c b/net/rxrpc/call_event.c
index 47eda13..e754459 100644
--- a/net/rxrpc/call_event.c
+++ b/net/rxrpc/call_event.c
@@ -132,6 +132,11 @@ void rxrpc_send_ACK(struct rxrpc_call *call, u8 ack_reason,
if (test_bit(RXRPC_CALL_DISCONNECTED, &call->flags))
return;
+ if (ack_reason == RXRPC_ACK_DELAY &&
+ test_and_set_bit(RXRPC_CALL_DELAY_ACK_PENDING, &call->flags)) {
+ trace_rxrpc_drop_ack(call, why, ack_reason, serial, false);
+ return;
+ }
spin_lock_bh(&local->ack_tx_lock);
head = local->ack_tx_head;
diff --git a/net/rxrpc/output.c b/net/rxrpc/output.c
index 56c4df3..db7d7fe 100644
--- a/net/rxrpc/output.c
+++ b/net/rxrpc/output.c
@@ -162,6 +162,9 @@ static int rxrpc_send_ack_packet(struct rxrpc_local *local, struct rxrpc_ack *ac
if (ack->ack_reason == RXRPC_ACK_PING)
pkt->whdr.flags |= RXRPC_REQUEST_ACK;
+ if (ack->ack_reason == RXRPC_ACK_DELAY)
+ clear_bit(RXRPC_CALL_DELAY_ACK_PENDING, &call->flags);
+
spin_lock_bh(&call->lock);
n = rxrpc_fill_out_ack(conn, call, ack, pkt, &hard_ack, &top);
spin_unlock_bh(&call->lock);