aboutsummaryrefslogtreecommitdiff
path: root/src/interfaces/libpq/fe-secure-openssl.c
diff options
context:
space:
mode:
authorTom Lane <tgl@sss.pgh.pa.us>2022-03-02 11:57:02 -0500
committerTom Lane <tgl@sss.pgh.pa.us>2022-03-02 11:57:02 -0500
commit72918ea86cb9308dd4748b4e269e3a53917cbdca (patch)
tree930bec9935402eebab1f725e76f480a537253ce0 /src/interfaces/libpq/fe-secure-openssl.c
parent0f7b62f29d16c771486418f88473ce07b605bb92 (diff)
downloadpostgresql-72918ea86cb9308dd4748b4e269e3a53917cbdca.tar.gz
postgresql-72918ea86cb9308dd4748b4e269e3a53917cbdca.zip
Allow root-owned SSL private keys in libpq, not only the backend.
This change makes libpq apply the same private-key-file ownership and permissions checks that we have used in the backend since commit 9a83564c5. Namely, that the private key can be owned by either the current user or root (with different file permissions allowed in the two cases). This allows system-wide management of key files, which is just as sensible on the client side as the server, particularly when the client is itself some application daemon. Sync the comments about this between libpq and the backend, too. Back-patch of a59c79564 and 50f03473e into all supported branches. David Steele Discussion: https://postgr.es/m/f4b7bc55-97ac-9e69-7398-335e212f7743@pgmasters.net
Diffstat (limited to 'src/interfaces/libpq/fe-secure-openssl.c')
-rw-r--r--src/interfaces/libpq/fe-secure-openssl.c40
1 files changed, 37 insertions, 3 deletions
diff --git a/src/interfaces/libpq/fe-secure-openssl.c b/src/interfaces/libpq/fe-secure-openssl.c
index 80faceefa23..f5f9c5e7e7b 100644
--- a/src/interfaces/libpq/fe-secure-openssl.c
+++ b/src/interfaces/libpq/fe-secure-openssl.c
@@ -1121,11 +1121,45 @@ initialize_SSL(PGconn *conn)
fnbuf);
return -1;
}
-#ifndef WIN32
- if (!S_ISREG(buf.st_mode) || buf.st_mode & (S_IRWXG | S_IRWXO))
+
+ /* Key file must be a regular file */
+ if (!S_ISREG(buf.st_mode))
+ {
+ printfPQExpBuffer(&conn->errorMessage,
+ libpq_gettext("private key file \"%s\" is not a regular file"),
+ fnbuf);
+ return -1;
+ }
+
+ /*
+ * Refuse to load key files owned by users other than us or root, and
+ * require no public access to the key file. If the file is owned by
+ * us, require mode 0600 or less. If owned by root, require 0640 or
+ * less to allow read access through either our gid or a supplementary
+ * gid that allows us to read system-wide certificates.
+ *
+ * Note that similar checks are performed in
+ * src/backend/libpq/be-secure-common.c so any changes here may need
+ * to be made there as well.
+ *
+ * Ideally we would do similar permissions checks on Windows, but it
+ * is not clear how that would work since Unix-style permissions may
+ * not be available.
+ */
+#if !defined(WIN32) && !defined(__CYGWIN__)
+ if (buf.st_uid != geteuid() && buf.st_uid != 0)
+ {
+ printfPQExpBuffer(&conn->errorMessage,
+ libpq_gettext("private key file \"%s\" must be owned by the current user or root\n"),
+ fnbuf);
+ return -1;
+ }
+
+ if ((buf.st_uid == geteuid() && buf.st_mode & (S_IRWXG | S_IRWXO)) ||
+ (buf.st_uid == 0 && buf.st_mode & (S_IWGRP | S_IXGRP | S_IRWXO)))
{
printfPQExpBuffer(&conn->errorMessage,
- libpq_gettext("private key file \"%s\" has group or world access; permissions should be u=rw (0600) or less\n"),
+ libpq_gettext("private key file \"%s\" has group or world access; file must have permissions u=rw (0600) or less if owned by the current user, or permissions u=rw,g=r (0640) or less if owned by root\n"),
fnbuf);
return -1;
}