0001-WIP-extend-TLS-read-pending-concept-to-GSS-too.patch
application/octet-stream
Filename: 0001-WIP-extend-TLS-read-pending-concept-to-GSS-too.patch
Type: application/octet-stream
Part: 0
Patch
Same data as JSON:
GET /api/v1/attachments/:id/patch
the parsed metadata as JSON — format, series position, per-file stats; never the diff bytes.
API reference →
Format: format-patch
Series: patch 0001
Subject: WIP: extend "TLS read pending" concept to GSS too
| File | + | − |
|---|---|---|
| src/interfaces/libpq/fe-misc.c | 2 | 4 |
| src/interfaces/libpq/fe-secure.c | 19 | 0 |
| src/interfaces/libpq/fe-secure-gssapi.c | 6 | 0 |
| src/interfaces/libpq/fe-secure-openssl.c | 1 | 1 |
| src/interfaces/libpq/libpq-int.h | 3 | 1 |
From 5b459b24696419c8747c506c26a813288ef899f5 Mon Sep 17 00:00:00 2001
From: Jacob Champion <jacob.champion@enterprisedb.com>
Date: Fri, 18 Jul 2025 10:06:13 -0700
Subject: [PATCH 1/2] WIP: extend "TLS read pending" concept to GSS too
pgtls_read_pending() is renamed to pgtls_read_is_pending(), to avoid
conflation with the forthcoming pgtls_drain_pending().
---
src/interfaces/libpq/fe-misc.c | 6 ++----
src/interfaces/libpq/fe-secure-gssapi.c | 6 ++++++
src/interfaces/libpq/fe-secure-openssl.c | 2 +-
src/interfaces/libpq/fe-secure.c | 19 +++++++++++++++++++
src/interfaces/libpq/libpq-int.h | 4 +++-
5 files changed, 31 insertions(+), 6 deletions(-)
diff --git a/src/interfaces/libpq/fe-misc.c b/src/interfaces/libpq/fe-misc.c
index dca44fdc5d2..434216ff89f 100644
--- a/src/interfaces/libpq/fe-misc.c
+++ b/src/interfaces/libpq/fe-misc.c
@@ -1099,14 +1099,12 @@ pqSocketCheck(PGconn *conn, int forRead, int forWrite, pg_usec_time_t end_time)
return -1;
}
-#ifdef USE_SSL
- /* Check for SSL library buffering read bytes */
- if (forRead && conn->ssl_in_use && pgtls_read_pending(conn))
+ /* Check for SSL/GSS library buffering read bytes */
+ if (forRead && pqsecure_read_is_pending(conn))
{
/* short-circuit the select */
return 1;
}
-#endif
}
/* We will retry as long as we get EINTR */
diff --git a/src/interfaces/libpq/fe-secure-gssapi.c b/src/interfaces/libpq/fe-secure-gssapi.c
index bc9e1ce06fa..7c88e64cfd2 100644
--- a/src/interfaces/libpq/fe-secure-gssapi.c
+++ b/src/interfaces/libpq/fe-secure-gssapi.c
@@ -469,6 +469,12 @@ gss_read(PGconn *conn, void *recv_buffer, size_t length, ssize_t *ret)
return PGRES_POLLING_OK;
}
+bool
+pg_GSS_read_is_pending(PGconn *conn)
+{
+ return PqGSSResultLength > PqGSSResultNext;
+}
+
/*
* Negotiate GSSAPI transport for a connection. When complete, returns
* PGRES_POLLING_OK. Will return PGRES_POLLING_READING or
diff --git a/src/interfaces/libpq/fe-secure-openssl.c b/src/interfaces/libpq/fe-secure-openssl.c
index 51dd7b9fec0..8f975561e51 100644
--- a/src/interfaces/libpq/fe-secure-openssl.c
+++ b/src/interfaces/libpq/fe-secure-openssl.c
@@ -231,7 +231,7 @@ rloop:
}
bool
-pgtls_read_pending(PGconn *conn)
+pgtls_read_is_pending(PGconn *conn)
{
return SSL_pending(conn->ssl) > 0;
}
diff --git a/src/interfaces/libpq/fe-secure.c b/src/interfaces/libpq/fe-secure.c
index e686681ba15..94c97ec26fb 100644
--- a/src/interfaces/libpq/fe-secure.c
+++ b/src/interfaces/libpq/fe-secure.c
@@ -243,6 +243,25 @@ pqsecure_raw_read(PGconn *conn, void *ptr, size_t len)
return n;
}
+/*
+ * Returns true if there are any bytes available in the transport buffer.
+ */
+bool
+pqsecure_read_is_pending(PGconn *conn)
+{
+#ifdef USE_SSL
+ if (conn->ssl_in_use)
+ return pgtls_read_is_pending(conn);
+#endif
+#ifdef ENABLE_GSS
+ if (conn->gssenc)
+ return pg_GSS_read_is_pending(conn);
+#endif
+
+ /* Plaintext connections have no transport buffer. */
+ return 0;
+}
+
/*
* Write data to a secure connection.
*
diff --git a/src/interfaces/libpq/libpq-int.h b/src/interfaces/libpq/libpq-int.h
index 70c28f2ffca..51bc2d3b740 100644
--- a/src/interfaces/libpq/libpq-int.h
+++ b/src/interfaces/libpq/libpq-int.h
@@ -809,6 +809,7 @@ extern int pqWriteReady(PGconn *conn);
extern PostgresPollingStatusType pqsecure_open_client(PGconn *);
extern void pqsecure_close(PGconn *);
extern ssize_t pqsecure_read(PGconn *, void *ptr, size_t len);
+extern bool pqsecure_read_is_pending(PGconn *);
extern ssize_t pqsecure_write(PGconn *, const void *ptr, size_t len);
extern ssize_t pqsecure_raw_read(PGconn *, void *ptr, size_t len);
extern ssize_t pqsecure_raw_write(PGconn *, const void *ptr, size_t len);
@@ -847,7 +848,7 @@ extern ssize_t pgtls_read(PGconn *conn, void *ptr, size_t len);
/*
* Is there unread data waiting in the SSL read buffer?
*/
-extern bool pgtls_read_pending(PGconn *conn);
+extern bool pgtls_read_is_pending(PGconn *conn);
/*
* Write data to a secure connection.
@@ -895,6 +896,7 @@ extern PostgresPollingStatusType pqsecure_open_gss(PGconn *conn);
*/
extern ssize_t pg_GSS_write(PGconn *conn, const void *ptr, size_t len);
extern ssize_t pg_GSS_read(PGconn *conn, void *ptr, size_t len);
+extern bool pg_GSS_read_is_pending(PGconn *conn);
#endif
/* === in fe-trace.c === */
--
2.34.1