From 4bb47c9bc8fc0772a60c6d349a5479bd88c8bccc Mon Sep 17 00:00:00 2001 From: Lars Ellenberg Date: Wed, 12 Feb 2025 11:11:27 +0100 Subject: [PATCH] drbd: TCP: use sk_set_memalloc and sk_allocation ATOMIC We used to "only" set NOIO. But we are a block device, we are in the write-out path, we may need to tap into the "reserves" to facilitate memory reclaim. If you expect to have serious memory pressure, we recommend to generously increase sysctl min_free_kbytes. --- drbd/drbd_transport_lb-tcp.c | 8 +++++++- drbd/drbd_transport_tcp.c | 10 ++++++++-- 2 files changed, 15 insertions(+), 3 deletions(-) diff --git a/drbd/drbd_transport_lb-tcp.c b/drbd/drbd_transport_lb-tcp.c index a5ed03b9c..b9f5a946d 100644 --- a/drbd/drbd_transport_lb-tcp.c +++ b/drbd/drbd_transport_lb-tcp.c @@ -1094,7 +1094,13 @@ static void dtl_setup_socket(struct dtl_transport *dtl_transport, struct socket long timeout = HZ; socket->sk->sk_reuse = SK_CAN_REUSE; /* SO_REUSEADDR */ - socket->sk->sk_allocation = GFP_NOIO; + /* We are a block device, we are in the write-out path, + * we may need memory to facilitate memory reclaim + */ + socket->sk->sk_use_task_frag = false; + socket->sk->sk_allocation = GFP_ATOMIC; + sk_set_memalloc(socket->sk); + socket->sk->sk_priority = use_for_data ? TC_PRIO_INTERACTIVE_BULK : TC_PRIO_INTERACTIVE; tcp_sock_set_nodelay(socket->sk); diff --git a/drbd/drbd_transport_tcp.c b/drbd/drbd_transport_tcp.c index ffbf5ed81..9714ef81d 100644 --- a/drbd/drbd_transport_tcp.c +++ b/drbd/drbd_transport_tcp.c @@ -1322,12 +1322,18 @@ static int dtt_connect(struct drbd_transport *transport) dsocket->sk->sk_reuse = SK_CAN_REUSE; /* SO_REUSEADDR */ csocket->sk->sk_reuse = SK_CAN_REUSE; /* SO_REUSEADDR */ - dsocket->sk->sk_allocation = GFP_NOIO; - csocket->sk->sk_allocation = GFP_NOIO; + /* We are a block device, we are in the write-out path, + * we may need memory to facilitate memory reclaim + */ + dsocket->sk->sk_allocation = GFP_ATOMIC; + csocket->sk->sk_allocation = GFP_ATOMIC; dsocket->sk->sk_use_task_frag = false; csocket->sk->sk_use_task_frag = false; + sk_set_memalloc(dsocket->sk); + sk_set_memalloc(csocket->sk); + dsocket->sk->sk_priority = TC_PRIO_INTERACTIVE_BULK; csocket->sk->sk_priority = TC_PRIO_INTERACTIVE;