From 8edbd93e24130ccc1726cbf6a514cd4a9040e874 Mon Sep 17 00:00:00 2001 From: Heikki Linnakangas Date: Thu, 14 Aug 2025 13:45:44 +0300 Subject: [PATCH v4 1/3] libpq: Don't hang on out-of-memory If an allocation failed while handling an async notification, we returned EOF, which stopped processing any further data until more data was received from the server. If more data never arrives, e.g. because the connection was used just to wait for the notification, or because the next ReadyForQuery was already received and buffered, it would get stuck forever. Instead, silently ignore the notification. Silently ignoring the notification is not a great way to handle the situation, but at least the connection doesn't get stuck, and it's consistent with how the malloc() later in the function is handled, and with e.g. how pqSaveParameterStatus() handles allocation failures. Fix the same issue with OOM on receiving BackendKeyData message. That one is new in v18. Discussion: https://www.postgresql.org/message-id/df892f9f-5923-4046-9d6f-8c48d8980b50@iki.fi --- src/interfaces/libpq/fe-protocol3.c | 16 ++++++++++------ 1 file changed, 10 insertions(+), 6 deletions(-) diff --git a/src/interfaces/libpq/fe-protocol3.c b/src/interfaces/libpq/fe-protocol3.c index 1599de757d1..5683229e32e 100644 --- a/src/interfaces/libpq/fe-protocol3.c +++ b/src/interfaces/libpq/fe-protocol3.c @@ -1550,9 +1550,8 @@ getBackendKeyData(PGconn *conn, int msgLength) conn->be_cancel_key = malloc(cancel_key_len); if (conn->be_cancel_key == NULL) { - libpq_append_conn_error(conn, "out of memory"); - /* discard the message */ - return EOF; + /* continue without cancel key */ + return 0; } if (pqGetnchar(conn->be_cancel_key, cancel_key_len, conn)) { @@ -1588,14 +1587,19 @@ getNotify(PGconn *conn) return EOF; /* must save name while getting extra string */ svname = strdup(conn->workBuffer.data); - if (!svname) - return EOF; if (pqGets(&conn->workBuffer, conn)) { - free(svname); + if (svname) + free(svname); return EOF; } + if (!svname) + { + /* out of memory; silently ignore the notification */ + return 0; + } + /* * Store the strings right after the PGnotify structure so it can all be * freed at once. We don't use NAMEDATALEN because we don't want to tie -- 2.39.5