SSL Tests for sslinfo extension

Started by Daniel Gustafssonover 4 years ago12 messages
#1Daniel Gustafsson
daniel@yesql.se
2 attachment(s)

While playing around with the recent SSL testharness changes I wrote a test
suite for sslinfo as a side effect, which seemed valuable in its own right as
we currently have no coverage of this code. The small change needed to the
testharness is to support installing modules, which is broken out into 0001 for
easier reading.

I'll park this in the next commitfest for now.

--
Daniel Gustafsson https://vmware.com/

Attachments:

0002-Add-tests-for-sslinfo.patchapplication/octet-stream; name=0002-Add-tests-for-sslinfo.patch; x-unix-mode=0644Download
From b6db06c01a010116d617aaf950fe35c6479d4c8f Mon Sep 17 00:00:00 2001
From: Daniel Gustafsson <daniel@yesql.se>
Date: Wed, 19 May 2021 15:04:37 +0200
Subject: [PATCH 2/2] Add tests for sslinfo

This adds rudimentary coverage of the sslinfo extension into the SSL
test harness. The output is validated by comparing with pg_stat_ssl
to provide some level of test stability should the underlying certs
be slightly altered.
---
 src/test/ssl/Makefile         |   2 +
 src/test/ssl/t/003_sslinfo.pl | 129 ++++++++++++++++++++++++++++++++++
 2 files changed, 131 insertions(+)
 create mode 100644 src/test/ssl/t/003_sslinfo.pl

diff --git a/src/test/ssl/Makefile b/src/test/ssl/Makefile
index a517756c94..3699b9fc78 100644
--- a/src/test/ssl/Makefile
+++ b/src/test/ssl/Makefile
@@ -9,6 +9,8 @@
 #
 #-------------------------------------------------------------------------
 
+EXTRA_INSTALL = contrib/sslinfo
+
 subdir = src/test/ssl
 top_builddir = ../../..
 include $(top_builddir)/src/Makefile.global
diff --git a/src/test/ssl/t/003_sslinfo.pl b/src/test/ssl/t/003_sslinfo.pl
new file mode 100644
index 0000000000..369da8f843
--- /dev/null
+++ b/src/test/ssl/t/003_sslinfo.pl
@@ -0,0 +1,129 @@
+
+# Copyright (c) 2021, PostgreSQL Global Development Group
+
+use strict;
+use warnings;
+use PostgresNode;
+use TestLib;
+use Test::More;
+
+use File::Copy;
+
+use FindBin;
+use lib $FindBin::RealBin;
+
+use SSLServer;
+
+if ($ENV{with_ssl} ne 'openssl')
+{
+	plan skip_all => 'OpenSSL not supported by this build';
+}
+else
+{
+	plan tests => 11;
+}
+
+#### Some configuration
+
+# This is the hostname used to connect to the server. This cannot be a
+# hostname, because the server certificate is always for the domain
+# postgresql-ssl-regression.test.
+my $SERVERHOSTADDR = '127.0.0.1';
+# This is the pattern to use in pg_hba.conf to match incoming connections.
+my $SERVERHOSTCIDR = '127.0.0.1/32';
+
+# Allocation of base connection string shared among multiple tests.
+my $common_connstr;
+
+# The client's private key must not be world-readable, so take a copy
+# of the key stored in the code tree and update its permissions.
+#
+# This changes ssl/client.key to ssl/client_tmp.key etc for the rest
+# of the tests.
+copy("ssl/client.key", "ssl/client_tmp.key")
+  or die "couldn't copy ssl/client.key to ssl/client_tmp.key for permissions change: $!";
+chmod 0600, "ssl/client_tmp.key"
+  or die "failed to change permissions on ssl/client_tmp.key: $!";
+
+#### Set up the server.
+
+note "setting up data directory";
+my $node = get_new_node('primary');
+$node->init;
+
+# PGHOST is enforced here to set up the node, subsequent connections
+# will use a dedicated connection string.
+$ENV{PGHOST} = $node->host;
+$ENV{PGPORT} = $node->port;
+$node->start;
+
+configure_test_server_for_ssl($node, $SERVERHOSTADDR, $SERVERHOSTCIDR,
+	'trust', extensions => 'sslinfo');
+
+# We aren't using any CRL's in this suite so we can keep using server-revoked
+# as server certificate for simple client.crt connection much like how the
+# 001 test does.
+switch_server_cert($node, 'server-revoked');
+
+$common_connstr =
+  "sslrootcert=ssl/root+server_ca.crt sslmode=require dbname=certdb hostaddr=$SERVERHOSTADDR " .
+  "user=ssltestuser sslcert=ssl/client.crt sslkey=ssl/client_tmp.key";
+
+# Make sure we can connect even though previous test suites have established this
+$node->connect_ok(
+	$common_connstr,
+	"certificate authorization succeeds with correct client cert in PEM format",
+);
+
+my $result;
+
+$result = $node->safe_psql("certdb", "SELECT ssl_is_used();",
+  connstr => $common_connstr);
+is($result, 't', "ssl_is_used() for TLS connection");
+
+$result = $node->safe_psql("certdb", "SELECT ssl_version();",
+  connstr => $common_connstr . " ssl_min_protocol_version=TLSv1.2 " .
+  "ssl_max_protocol_version=TLSv1.2");
+is($result, 'TLSv1.2', "ssl_version() correctly returning TLS protocol");
+
+$result = $node->safe_psql("certdb",
+  "SELECT ssl_cipher() = cipher FROM pg_stat_ssl WHERE pid = pg_backend_pid();",
+  connstr => $common_connstr);
+is($result, 't', "ssl_cipher() compared with pg_stat_ssl");
+
+$result = $node->safe_psql("certdb", "SELECT ssl_client_cert_present();",
+  connstr => $common_connstr);
+is($result, 't', "ssl_client_cert_present() for connection with cert");
+
+$result = $node->safe_psql("trustdb", "SELECT ssl_client_cert_present();",
+  connstr => "sslrootcert=ssl/root+server_ca.crt sslmode=require " .
+  "dbname=trustdb hostaddr=$SERVERHOSTADDR user=ssltestuser");
+is($result, 'f', "ssl_client_cert_present() for connection without cert");
+
+$result = $node->safe_psql("certdb",
+  "SELECT ssl_client_serial() = client_serial FROM pg_stat_ssl WHERE pid = pg_backend_pid();",
+  connstr => $common_connstr);
+is($result, 't', "ssl_client_serial() compared with pg_stat_ssl");
+
+# Must not use safe_psql since we expect an error here
+$result = $node->psql("certdb", "SELECT ssl_client_dn_field('invalid');",
+  connstr => $common_connstr);
+is($result, '3', "ssl_client_dn_field() for an invalid field");
+
+$result = $node->safe_psql("trustdb", "SELECT ssl_client_dn_field('commonName');",
+  connstr => "sslrootcert=ssl/root+server_ca.crt sslmode=require " .
+  "dbname=trustdb hostaddr=$SERVERHOSTADDR user=ssltestuser");
+is($result, '', "ssl_client_dn_field() for connection without cert");
+
+$result = $node->safe_psql("certdb",
+  "SELECT '/CN=' || ssl_client_dn_field('commonName') = client_dn FROM pg_stat_ssl WHERE pid = pg_backend_pid();",
+  connstr => $common_connstr);
+is($result, 't', "ssl_client_dn_field() for commonName");
+
+$result = $node->safe_psql("certdb",
+  "SELECT ssl_issuer_dn() = issuer_dn FROM pg_stat_ssl WHERE pid = pg_backend_pid();",
+  connstr => $common_connstr);
+is($result, 't', "ssl_issuer_dn() for connection with cert");
+
+# Clean up
+unlink("ssl/client_tmp.key");
-- 
2.30.1 (Apple Git-130)

0001-Extend-configure_test_server_for_ssl-to-add-extensio.patchapplication/octet-stream; name=0001-Extend-configure_test_server_for_ssl-to-add-extensio.patch; x-unix-mode=0644Download
From 023d81df78a3961258344d00c1e21e62792f55dc Mon Sep 17 00:00:00 2001
From: Daniel Gustafsson <daniel@yesql.se>
Date: Wed, 19 May 2021 14:49:20 +0200
Subject: [PATCH 1/2] Extend configure_test_server_for_ssl to add extensions

In order to be able to test extensions with SSL connections, allow
configure_test_server_for_ssl to create any extensions passed as
comma separated list. Each extension is created in all the test
databases which may or may not be useful.
---
 src/test/ssl/t/002_scram.pl |  2 +-
 src/test/ssl/t/SSLServer.pm | 29 ++++++++++++++++++++++-------
 2 files changed, 23 insertions(+), 8 deletions(-)

diff --git a/src/test/ssl/t/002_scram.pl b/src/test/ssl/t/002_scram.pl
index 9143fa515f..d8cd8a9976 100644
--- a/src/test/ssl/t/002_scram.pl
+++ b/src/test/ssl/t/002_scram.pl
@@ -49,7 +49,7 @@ $node->start;
 
 # Configure server for SSL connections, with password handling.
 configure_test_server_for_ssl($node, $SERVERHOSTADDR, $SERVERHOSTCIDR,
-	"scram-sha-256", "pass", "scram-sha-256");
+	"scram-sha-256", 'password' => "pass", 'password_enc' => "scram-sha-256");
 switch_server_cert($node, 'server-cn-only');
 $ENV{PGPASSWORD} = "pass";
 $common_connstr =
diff --git a/src/test/ssl/t/SSLServer.pm b/src/test/ssl/t/SSLServer.pm
index 804d008245..71cd6882b7 100644
--- a/src/test/ssl/t/SSLServer.pm
+++ b/src/test/ssl/t/SSLServer.pm
@@ -62,9 +62,7 @@ sub copy_files
 # servercidr: what to put in pg_hba.conf, e.g. '127.0.0.1/32'
 sub configure_test_server_for_ssl
 {
-	my ($node, $serverhost, $servercidr, $authmethod, $password,
-		$password_enc) = @_;
-
+	my ($node, $serverhost, $servercidr, $authmethod, %params) = @_;
 	my $pgdata = $node->data_dir;
 
 	# Create test users and databases
@@ -80,20 +78,37 @@ sub configure_test_server_for_ssl
 	$node->psql('postgres', "CREATE DATABASE verifydb");
 
 	# Update password of each user as needed.
-	if (defined($password))
+	if (defined($params{password}))
 	{
+		die "Password encoding must be specified when password is set"
+			unless defined($params{password_enc});
+
 		$node->psql('postgres',
-			"SET password_encryption='$password_enc'; ALTER USER ssltestuser PASSWORD '$password';"
+			"SET password_encryption='$params{password_enc}'; ALTER USER ssltestuser PASSWORD '$params{password}';"
 		);
 		# A special user that always has an md5-encrypted password
 		$node->psql('postgres',
-			"SET password_encryption='md5'; ALTER USER md5testuser PASSWORD '$password';"
+			"SET password_encryption='md5'; ALTER USER md5testuser PASSWORD '$params{password}';"
 		);
 		$node->psql('postgres',
-			"SET password_encryption='$password_enc'; ALTER USER anotheruser PASSWORD '$password';"
+			"SET password_encryption='$params{password_enc}'; ALTER USER anotheruser PASSWORD '$params{password}';"
 		);
 	}
 
+	# Create any extensions requested in the setup
+	if (defined($params{extensions}))
+	{
+		for my $extension (split(/,/,$params{extensions}))
+		{
+			$node->psql('trustdb', "CREATE EXTENSION $extension;");
+			$node->psql('certdb', "CREATE EXTENSION $extension;");
+			$node->psql('certdb_dn', "CREATE EXTENSION $extension;");
+			$node->psql('certdb_dn_re', "CREATE EXTENSION $extension;");
+			$node->psql('certdb_cn', "CREATE EXTENSION $extension;");
+			$node->psql('verifydb', "CREATE EXTENSION $extension;");
+		}
+	}
+
 	# enable logging etc.
 	open my $conf, '>>', "$pgdata/postgresql.conf";
 	print $conf "fsync=off\n";
-- 
2.30.1 (Apple Git-130)

#2Noname
ilmari@ilmari.org
In reply to: Daniel Gustafsson (#1)
Re: SSL Tests for sslinfo extension

Daniel Gustafsson <daniel@yesql.se> writes:

In order to be able to test extensions with SSL connections, allow
configure_test_server_for_ssl to create any extensions passed as
comma separated list. Each extension is created in all the test
databases which may or may not be useful.

Why the comma-separated string, rather than an array reference,
i.e. `extensions => [qw(foo bar baz)]`? Also, should it use `CREATE
EXTENSION .. CASCADE`, in case the specified extensions depend on
others?

- ilmari
--
"The surreality of the universe tends towards a maximum" -- Skud's Law
"Never formulate a law or axiom that you're not prepared to live with
the consequences of." -- Skud's Meta-Law

#3Andrew Dunstan
andrew@dunslane.net
In reply to: Noname (#2)
Re: SSL Tests for sslinfo extension

On 5/19/21 1:01 PM, Dagfinn Ilmari Mannsåker wrote:

Daniel Gustafsson <daniel@yesql.se> writes:

In order to be able to test extensions with SSL connections, allow
configure_test_server_for_ssl to create any extensions passed as
comma separated list. Each extension is created in all the test
databases which may or may not be useful.

Why the comma-separated string, rather than an array reference,
i.e. `extensions => [qw(foo bar baz)]`? Also, should it use `CREATE
EXTENSION .. CASCADE`, in case the specified extensions depend on
others?

Also, instead of one line per db there should be an inner loop over the
db  names.

cheers

andrew

--
Andrew Dunstan
EDB: https://www.enterprisedb.com

#4Daniel Gustafsson
daniel@yesql.se
In reply to: Andrew Dunstan (#3)
2 attachment(s)
Re: SSL Tests for sslinfo extension

On 19 May 2021, at 21:05, Andrew Dunstan <andrew@dunslane.net> wrote:

On 5/19/21 1:01 PM, Dagfinn Ilmari Mannsåker wrote:

Daniel Gustafsson <daniel@yesql.se> writes:

In order to be able to test extensions with SSL connections, allow
configure_test_server_for_ssl to create any extensions passed as
comma separated list. Each extension is created in all the test
databases which may or may not be useful.

Why the comma-separated string, rather than an array reference,
i.e. `extensions => [qw(foo bar baz)]`?

No real reason, I just haven't written Perl enough lately to "think in Perl".
Fixed in the attached.

Also, should it use `CREATE
EXTENSION .. CASCADE`, in case the specified extensions depend on
others?

Good point. Each extension will have to be in EXTRA_INSTALL as well of course,
but we should to CASCADE.

Also, instead of one line per db there should be an inner loop over the
db names.

Right, I was lazily using the same approach as for CREATE DATABASE but when the
list is used it two places it should be a proper list. Fixed in the attached.

--
Daniel Gustafsson https://vmware.com/

Attachments:

v2-0001-Extend-configure_test_server_for_ssl-to-add-exten.patchapplication/octet-stream; name=v2-0001-Extend-configure_test_server_for_ssl-to-add-exten.patch; x-unix-mode=0644Download
From 6d22ba70b0ea49da188e0e1c0f85d34de2b1ffd2 Mon Sep 17 00:00:00 2001
From: Daniel Gustafsson <daniel@yesql.se>
Date: Wed, 19 May 2021 14:49:20 +0200
Subject: [PATCH v2 1/2] Extend configure_test_server_for_ssl to add extensions

In order to be able to test extensions with SSL connections, allow
configure_test_server_for_ssl to create any extensions passed as
an array. Each extension is created in all the test databases which
may or may not be useful.
---
 src/test/ssl/t/002_scram.pl |  2 +-
 src/test/ssl/t/SSLServer.pm | 40 +++++++++++++++++++++++++------------
 2 files changed, 28 insertions(+), 14 deletions(-)

diff --git a/src/test/ssl/t/002_scram.pl b/src/test/ssl/t/002_scram.pl
index 9143fa515f..d8cd8a9976 100644
--- a/src/test/ssl/t/002_scram.pl
+++ b/src/test/ssl/t/002_scram.pl
@@ -49,7 +49,7 @@ $node->start;
 
 # Configure server for SSL connections, with password handling.
 configure_test_server_for_ssl($node, $SERVERHOSTADDR, $SERVERHOSTCIDR,
-	"scram-sha-256", "pass", "scram-sha-256");
+	"scram-sha-256", 'password' => "pass", 'password_enc' => "scram-sha-256");
 switch_server_cert($node, 'server-cn-only');
 $ENV{PGPASSWORD} = "pass";
 $common_connstr =
diff --git a/src/test/ssl/t/SSLServer.pm b/src/test/ssl/t/SSLServer.pm
index 804d008245..835f272470 100644
--- a/src/test/ssl/t/SSLServer.pm
+++ b/src/test/ssl/t/SSLServer.pm
@@ -62,38 +62,52 @@ sub copy_files
 # servercidr: what to put in pg_hba.conf, e.g. '127.0.0.1/32'
 sub configure_test_server_for_ssl
 {
-	my ($node, $serverhost, $servercidr, $authmethod, $password,
-		$password_enc) = @_;
-
+	my ($node, $serverhost, $servercidr, $authmethod, %params) = @_;
 	my $pgdata = $node->data_dir;
 
+	my @databases = ( 'trustdb', 'certdb', 'certdb_dn', 'certdb_dn_re', 'certdb_cn', 'verifydb' );
+
 	# Create test users and databases
 	$node->psql('postgres', "CREATE USER ssltestuser");
 	$node->psql('postgres', "CREATE USER md5testuser");
 	$node->psql('postgres', "CREATE USER anotheruser");
 	$node->psql('postgres', "CREATE USER yetanotheruser");
-	$node->psql('postgres', "CREATE DATABASE trustdb");
-	$node->psql('postgres', "CREATE DATABASE certdb");
-	$node->psql('postgres', "CREATE DATABASE certdb_dn");
-	$node->psql('postgres', "CREATE DATABASE certdb_dn_re");
-	$node->psql('postgres', "CREATE DATABASE certdb_cn");
-	$node->psql('postgres', "CREATE DATABASE verifydb");
+
+	foreach my $db (@databases)
+	{
+		$node->psql('postgres', "CREATE DATABASE $db");
+	}
 
 	# Update password of each user as needed.
-	if (defined($password))
+	if (defined($params{password}))
 	{
+		die "Password encoding must be specified when password is set"
+			unless defined($params{password_enc});
+
 		$node->psql('postgres',
-			"SET password_encryption='$password_enc'; ALTER USER ssltestuser PASSWORD '$password';"
+			"SET password_encryption='$params{password_enc}'; ALTER USER ssltestuser PASSWORD '$params{password}';"
 		);
 		# A special user that always has an md5-encrypted password
 		$node->psql('postgres',
-			"SET password_encryption='md5'; ALTER USER md5testuser PASSWORD '$password';"
+			"SET password_encryption='md5'; ALTER USER md5testuser PASSWORD '$params{password}';"
 		);
 		$node->psql('postgres',
-			"SET password_encryption='$password_enc'; ALTER USER anotheruser PASSWORD '$password';"
+			"SET password_encryption='$params{password_enc}'; ALTER USER anotheruser PASSWORD '$params{password}';"
 		);
 	}
 
+	# Create any extensions requested in the setup
+	if (defined($params{extensions}))
+	{
+		foreach my $extension (@{$params{extensions}})
+		{
+			foreach my $db (@databases)
+			{
+				$node->psql($db, "CREATE EXTENSION $extension CASCADE;");
+			}
+		}
+	}
+
 	# enable logging etc.
 	open my $conf, '>>', "$pgdata/postgresql.conf";
 	print $conf "fsync=off\n";
-- 
2.30.1 (Apple Git-130)

v2-0002-Add-tests-for-sslinfo.patchapplication/octet-stream; name=v2-0002-Add-tests-for-sslinfo.patch; x-unix-mode=0644Download
From 0e826d71930a09cb00e1b7ec55aeac92612bcd4f Mon Sep 17 00:00:00 2001
From: Daniel Gustafsson <daniel@yesql.se>
Date: Wed, 19 May 2021 15:04:37 +0200
Subject: [PATCH v2 2/2] Add tests for sslinfo

This adds rudimentary coverage of the sslinfo extension into the SSL
test harness. The output is validated by comparing with pg_stat_ssl
to provide some level of test stability should the underlying certs
be slightly altered.
---
 src/test/ssl/Makefile         |   2 +
 src/test/ssl/t/003_sslinfo.pl | 129 ++++++++++++++++++++++++++++++++++
 2 files changed, 131 insertions(+)
 create mode 100644 src/test/ssl/t/003_sslinfo.pl

diff --git a/src/test/ssl/Makefile b/src/test/ssl/Makefile
index a517756c94..3699b9fc78 100644
--- a/src/test/ssl/Makefile
+++ b/src/test/ssl/Makefile
@@ -9,6 +9,8 @@
 #
 #-------------------------------------------------------------------------
 
+EXTRA_INSTALL = contrib/sslinfo
+
 subdir = src/test/ssl
 top_builddir = ../../..
 include $(top_builddir)/src/Makefile.global
diff --git a/src/test/ssl/t/003_sslinfo.pl b/src/test/ssl/t/003_sslinfo.pl
new file mode 100644
index 0000000000..2c0f7d27fa
--- /dev/null
+++ b/src/test/ssl/t/003_sslinfo.pl
@@ -0,0 +1,129 @@
+
+# Copyright (c) 2021, PostgreSQL Global Development Group
+
+use strict;
+use warnings;
+use PostgresNode;
+use TestLib;
+use Test::More;
+
+use File::Copy;
+
+use FindBin;
+use lib $FindBin::RealBin;
+
+use SSLServer;
+
+if ($ENV{with_ssl} ne 'openssl')
+{
+	plan skip_all => 'OpenSSL not supported by this build';
+}
+else
+{
+	plan tests => 11;
+}
+
+#### Some configuration
+
+# This is the hostname used to connect to the server. This cannot be a
+# hostname, because the server certificate is always for the domain
+# postgresql-ssl-regression.test.
+my $SERVERHOSTADDR = '127.0.0.1';
+# This is the pattern to use in pg_hba.conf to match incoming connections.
+my $SERVERHOSTCIDR = '127.0.0.1/32';
+
+# Allocation of base connection string shared among multiple tests.
+my $common_connstr;
+
+# The client's private key must not be world-readable, so take a copy
+# of the key stored in the code tree and update its permissions.
+#
+# This changes ssl/client.key to ssl/client_tmp.key etc for the rest
+# of the tests.
+copy("ssl/client.key", "ssl/client_tmp.key")
+  or die "couldn't copy ssl/client.key to ssl/client_tmp.key for permissions change: $!";
+chmod 0600, "ssl/client_tmp.key"
+  or die "failed to change permissions on ssl/client_tmp.key: $!";
+
+#### Set up the server.
+
+note "setting up data directory";
+my $node = get_new_node('primary');
+$node->init;
+
+# PGHOST is enforced here to set up the node, subsequent connections
+# will use a dedicated connection string.
+$ENV{PGHOST} = $node->host;
+$ENV{PGPORT} = $node->port;
+$node->start;
+
+configure_test_server_for_ssl($node, $SERVERHOSTADDR, $SERVERHOSTCIDR,
+	'trust', extensions => [ qw(sslinfo) ]);
+
+# We aren't using any CRL's in this suite so we can keep using server-revoked
+# as server certificate for simple client.crt connection much like how the
+# 001 test does.
+switch_server_cert($node, 'server-revoked');
+
+$common_connstr =
+  "sslrootcert=ssl/root+server_ca.crt sslmode=require dbname=certdb hostaddr=$SERVERHOSTADDR " .
+  "user=ssltestuser sslcert=ssl/client.crt sslkey=ssl/client_tmp.key";
+
+# Make sure we can connect even though previous test suites have established this
+$node->connect_ok(
+	$common_connstr,
+	"certificate authorization succeeds with correct client cert in PEM format",
+);
+
+my $result;
+
+$result = $node->safe_psql("certdb", "SELECT ssl_is_used();",
+  connstr => $common_connstr);
+is($result, 't', "ssl_is_used() for TLS connection");
+
+$result = $node->safe_psql("certdb", "SELECT ssl_version();",
+  connstr => $common_connstr . " ssl_min_protocol_version=TLSv1.2 " .
+  "ssl_max_protocol_version=TLSv1.2");
+is($result, 'TLSv1.2', "ssl_version() correctly returning TLS protocol");
+
+$result = $node->safe_psql("certdb",
+  "SELECT ssl_cipher() = cipher FROM pg_stat_ssl WHERE pid = pg_backend_pid();",
+  connstr => $common_connstr);
+is($result, 't', "ssl_cipher() compared with pg_stat_ssl");
+
+$result = $node->safe_psql("certdb", "SELECT ssl_client_cert_present();",
+  connstr => $common_connstr);
+is($result, 't', "ssl_client_cert_present() for connection with cert");
+
+$result = $node->safe_psql("trustdb", "SELECT ssl_client_cert_present();",
+  connstr => "sslrootcert=ssl/root+server_ca.crt sslmode=require " .
+  "dbname=trustdb hostaddr=$SERVERHOSTADDR user=ssltestuser");
+is($result, 'f', "ssl_client_cert_present() for connection without cert");
+
+$result = $node->safe_psql("certdb",
+  "SELECT ssl_client_serial() = client_serial FROM pg_stat_ssl WHERE pid = pg_backend_pid();",
+  connstr => $common_connstr);
+is($result, 't', "ssl_client_serial() compared with pg_stat_ssl");
+
+# Must not use safe_psql since we expect an error here
+$result = $node->psql("certdb", "SELECT ssl_client_dn_field('invalid');",
+  connstr => $common_connstr);
+is($result, '3', "ssl_client_dn_field() for an invalid field");
+
+$result = $node->safe_psql("trustdb", "SELECT ssl_client_dn_field('commonName');",
+  connstr => "sslrootcert=ssl/root+server_ca.crt sslmode=require " .
+  "dbname=trustdb hostaddr=$SERVERHOSTADDR user=ssltestuser");
+is($result, '', "ssl_client_dn_field() for connection without cert");
+
+$result = $node->safe_psql("certdb",
+  "SELECT '/CN=' || ssl_client_dn_field('commonName') = client_dn FROM pg_stat_ssl WHERE pid = pg_backend_pid();",
+  connstr => $common_connstr);
+is($result, 't', "ssl_client_dn_field() for commonName");
+
+$result = $node->safe_psql("certdb",
+  "SELECT ssl_issuer_dn() = issuer_dn FROM pg_stat_ssl WHERE pid = pg_backend_pid();",
+  connstr => $common_connstr);
+is($result, 't', "ssl_issuer_dn() for connection with cert");
+
+# Clean up
+unlink("ssl/client_tmp.key");
-- 
2.30.1 (Apple Git-130)

#5Michael Paquier
michael@paquier.xyz
In reply to: Daniel Gustafsson (#4)
Re: SSL Tests for sslinfo extension

On Thu, May 20, 2021 at 08:40:48PM +0200, Daniel Gustafsson wrote:

On 19 May 2021, at 21:05, Andrew Dunstan <andrew@dunslane.net> wrote:

On 5/19/21 1:01 PM, Dagfinn Ilmari Mannsåker wrote:

Daniel Gustafsson <daniel@yesql.se> writes:

In order to be able to test extensions with SSL connections, allow
configure_test_server_for_ssl to create any extensions passed as
comma separated list. Each extension is created in all the test
databases which may or may not be useful.

Why the comma-separated string, rather than an array reference,
i.e. `extensions => [qw(foo bar baz)]`?

No real reason, I just haven't written Perl enough lately to "think in Perl".
Fixed in the attached.

Hmm. Adding internal dependencies between the tests should be avoided
if we can. What would it take to move those TAP tests to
contrib/sslinfo instead? This is while keeping in mind that there was
a patch aimed at refactoring the SSL test suite for NSS.
--
Michael

#6Daniel Gustafsson
daniel@yesql.se
In reply to: Michael Paquier (#5)
Re: SSL Tests for sslinfo extension

On 17 Jun 2021, at 09:29, Michael Paquier <michael@paquier.xyz> wrote:

On Thu, May 20, 2021 at 08:40:48PM +0200, Daniel Gustafsson wrote:

On 19 May 2021, at 21:05, Andrew Dunstan <andrew@dunslane.net> wrote:

On 5/19/21 1:01 PM, Dagfinn Ilmari Mannsåker wrote:

Daniel Gustafsson <daniel@yesql.se> writes:

In order to be able to test extensions with SSL connections, allow
configure_test_server_for_ssl to create any extensions passed as
comma separated list. Each extension is created in all the test
databases which may or may not be useful.

Why the comma-separated string, rather than an array reference,
i.e. `extensions => [qw(foo bar baz)]`?

No real reason, I just haven't written Perl enough lately to "think in Perl".
Fixed in the attached.

Hmm. Adding internal dependencies between the tests should be avoided
if we can. What would it take to move those TAP tests to
contrib/sslinfo instead? This is while keeping in mind that there was
a patch aimed at refactoring the SSL test suite for NSS.

It would be quite invasive as we currently don't provide the SSLServer test
harness outside of src/test/ssl, and given how tailored it is today I'm not
sure doing so without a rewrite would be a good idea.

A longer term solution would probably be to teach PostgresNode to provide an
instance set up for TLS in case the backend is compiled with TLS support, and
use that for things like sslinfo.

--
Daniel Gustafsson https://vmware.com/

#7Tom Lane
tgl@sss.pgh.pa.us
In reply to: Daniel Gustafsson (#6)
Re: SSL Tests for sslinfo extension

Daniel Gustafsson <daniel@yesql.se> writes:

On 17 Jun 2021, at 09:29, Michael Paquier <michael@paquier.xyz> wrote:

Hmm. Adding internal dependencies between the tests should be avoided
if we can. What would it take to move those TAP tests to
contrib/sslinfo instead? This is while keeping in mind that there was
a patch aimed at refactoring the SSL test suite for NSS.

It would be quite invasive as we currently don't provide the SSLServer test
harness outside of src/test/ssl, and given how tailored it is today I'm not
sure doing so without a rewrite would be a good idea.

I think testing sslinfo in src/test/ssl is fine, while putting its test
inside contrib/ would be dangerous, because then the test would be run
by default. src/test/ssl is not run by default because the server it
starts is potentially accessible by other local users, and AFAICS the
same has to be true for an sslinfo test.

So I don't have any problem with this structurally, but I do have a
few nitpicks:

* I think the error message added in 0001 should complain about
missing password "encryption" not "encoding", no?

* 0002 hasn't been updated for the great PostgresNode renaming.

* 0002 needs to extend src/test/ssl/README to mention that
"make installcheck" requires having installed contrib/sslinfo,
analogous to similar comments in (eg) src/test/recovery/README.

* 0002 writes a temporary file in the source tree. This is bad;
for one thing I bet it fails under VPATH, but in any case there
is no reason to risk it. Put it in the tmp_check directory instead
(cf temp kdc files in src/test/kerberos/t/001_auth.pl). That's
safer and you needn't worry about cleaning it up.

* Hmm ... now I notice that you borrowed the key-file-copying logic
from the 001 and 002 tests, but it's just as bad practice there.
We should fix them too.

* I ran a code-coverage check and it shows that this doesn't test
ssl_issuer_field() or any of the following functions in sslinfo.c.
I think at least ssl_extension_info() is complicated enough to
deserve a test.

regards, tom lane

#8Michael Paquier
michael@paquier.xyz
In reply to: Tom Lane (#7)
Re: SSL Tests for sslinfo extension

On Sat, Nov 27, 2021 at 02:27:19PM -0500, Tom Lane wrote:

I think testing sslinfo in src/test/ssl is fine, while putting its test
inside contrib/ would be dangerous, because then the test would be run
by default. src/test/ssl is not run by default because the server it
starts is potentially accessible by other local users, and AFAICS the
same has to be true for an sslinfo test.

Ah, indeed, good point. I completely forgot that we'd better control
this stuff with PG_TEST_EXTRA.
--
Michael

#9Daniel Gustafsson
daniel@yesql.se
In reply to: Tom Lane (#7)
3 attachment(s)
Re: SSL Tests for sslinfo extension

On 27 Nov 2021, at 20:27, Tom Lane <tgl@sss.pgh.pa.us> wrote:

I don't have any problem with this structurally, but I do have a
few nitpicks:

Thanks for reviewing!

* I think the error message added in 0001 should complain about
missing password "encryption" not "encoding", no?

Doh, of course.

* 0002 hasn't been updated for the great PostgresNode renaming.

Fixed.

* 0002 needs to extend src/test/ssl/README to mention that
"make installcheck" requires having installed contrib/sslinfo,
analogous to similar comments in (eg) src/test/recovery/README.

Good point, I copied over the wording from recovery/README and adapted for SSL
since I think it was well written as is. (Consistency is also a good benefit.)

* 0002 writes a temporary file in the source tree. This is bad;
for one thing I bet it fails under VPATH, but in any case there
is no reason to risk it. Put it in the tmp_check directory instead
(cf temp kdc files in src/test/kerberos/t/001_auth.pl). That's
safer and you needn't worry about cleaning it up.

Fixed, and see below.

* Hmm ... now I notice that you borrowed the key-file-copying logic
from the 001 and 002 tests, but it's just as bad practice there.
We should fix them too.

Well spotted, I hadn't thought about that but in hindsight it's quite obviously
bad. I've done this in a 0003 patch in this series which also comes with the
IMO benefit of a tighter coupling between the key filename used in the test
with what's in the repo by removing the _tmp suffix. To avoid concatenating
with the long tmp_check path variable everywhere, I went with a lookup HASH to
make it easier on the eye and harder to mess up should we change tmp path at
some point. There might be ways which are more like modern Perl, but I wasn't
able to think of one off the bat.

* I ran a code-coverage check and it shows that this doesn't test
ssl_issuer_field() or any of the following functions in sslinfo.c.
I think at least ssl_extension_info() is complicated enough to
deserve a test.

Agreed. The attached v3 covers the issuer and extension function to at least
some degree. In order to reliably test the extension I added a new cert with a
CA extension.

--
Daniel Gustafsson https://vmware.com/

Attachments:

v3-0001-Extend-configure_test_server_for_ssl-to-add-exten.patchapplication/octet-stream; name=v3-0001-Extend-configure_test_server_for_ssl-to-add-exten.patch; x-unix-mode=0644Download
From 5afa53382c4badc47fbfccd9268a8b9fc077faf5 Mon Sep 17 00:00:00 2001
From: Daniel Gustafsson <daniel@yesql.se>
Date: Wed, 19 May 2021 14:49:20 +0200
Subject: [PATCH v3 1/3] Extend configure_test_server_for_ssl to add extensions

In order to be able to test extensions with SSL connections, allow
configure_test_server_for_ssl to create any extensions passed as
an array. Each extension is created in all the test databases which
may or may not be useful.
---
 src/test/ssl/t/002_scram.pl |  2 +-
 src/test/ssl/t/SSLServer.pm | 40 +++++++++++++++++++++++++------------
 2 files changed, 28 insertions(+), 14 deletions(-)

diff --git a/src/test/ssl/t/002_scram.pl b/src/test/ssl/t/002_scram.pl
index 983554263f..88803ee5c5 100644
--- a/src/test/ssl/t/002_scram.pl
+++ b/src/test/ssl/t/002_scram.pl
@@ -49,7 +49,7 @@ $node->start;
 
 # Configure server for SSL connections, with password handling.
 configure_test_server_for_ssl($node, $SERVERHOSTADDR, $SERVERHOSTCIDR,
-	"scram-sha-256", "pass", "scram-sha-256");
+	"scram-sha-256", 'password' => "pass", 'password_enc' => "scram-sha-256");
 switch_server_cert($node, 'server-cn-only');
 $ENV{PGPASSWORD} = "pass";
 $common_connstr =
diff --git a/src/test/ssl/t/SSLServer.pm b/src/test/ssl/t/SSLServer.pm
index c5999e0b33..3d7ff40b97 100644
--- a/src/test/ssl/t/SSLServer.pm
+++ b/src/test/ssl/t/SSLServer.pm
@@ -62,38 +62,52 @@ sub copy_files
 # servercidr: what to put in pg_hba.conf, e.g. '127.0.0.1/32'
 sub configure_test_server_for_ssl
 {
-	my ($node, $serverhost, $servercidr, $authmethod, $password,
-		$password_enc) = @_;
-
+	my ($node, $serverhost, $servercidr, $authmethod, %params) = @_;
 	my $pgdata = $node->data_dir;
 
+	my @databases = ( 'trustdb', 'certdb', 'certdb_dn', 'certdb_dn_re', 'certdb_cn', 'verifydb' );
+
 	# Create test users and databases
 	$node->psql('postgres', "CREATE USER ssltestuser");
 	$node->psql('postgres', "CREATE USER md5testuser");
 	$node->psql('postgres', "CREATE USER anotheruser");
 	$node->psql('postgres', "CREATE USER yetanotheruser");
-	$node->psql('postgres', "CREATE DATABASE trustdb");
-	$node->psql('postgres', "CREATE DATABASE certdb");
-	$node->psql('postgres', "CREATE DATABASE certdb_dn");
-	$node->psql('postgres', "CREATE DATABASE certdb_dn_re");
-	$node->psql('postgres', "CREATE DATABASE certdb_cn");
-	$node->psql('postgres', "CREATE DATABASE verifydb");
+
+	foreach my $db (@databases)
+	{
+		$node->psql('postgres', "CREATE DATABASE $db");
+	}
 
 	# Update password of each user as needed.
-	if (defined($password))
+	if (defined($params{password}))
 	{
+		die "Password encryption must be specified when password is set"
+			unless defined($params{password_enc});
+
 		$node->psql('postgres',
-			"SET password_encryption='$password_enc'; ALTER USER ssltestuser PASSWORD '$password';"
+			"SET password_encryption='$params{password_enc}'; ALTER USER ssltestuser PASSWORD '$params{password}';"
 		);
 		# A special user that always has an md5-encrypted password
 		$node->psql('postgres',
-			"SET password_encryption='md5'; ALTER USER md5testuser PASSWORD '$password';"
+			"SET password_encryption='md5'; ALTER USER md5testuser PASSWORD '$params{password}';"
 		);
 		$node->psql('postgres',
-			"SET password_encryption='$password_enc'; ALTER USER anotheruser PASSWORD '$password';"
+			"SET password_encryption='$params{password_enc}'; ALTER USER anotheruser PASSWORD '$params{password}';"
 		);
 	}
 
+	# Create any extensions requested in the setup
+	if (defined($params{extensions}))
+	{
+		foreach my $extension (@{$params{extensions}})
+		{
+			foreach my $db (@databases)
+			{
+				$node->psql($db, "CREATE EXTENSION $extension CASCADE;");
+			}
+		}
+	}
+
 	# enable logging etc.
 	open my $conf, '>>', "$pgdata/postgresql.conf";
 	print $conf "fsync=off\n";
-- 
2.24.3 (Apple Git-128)

v3-0002-Add-tests-for-sslinfo.patchapplication/octet-stream; name=v3-0002-Add-tests-for-sslinfo.patch; x-unix-mode=0644Download
From 9ada8b2f4eac52b3b7e7ecec4fc8a60d6eb5dce5 Mon Sep 17 00:00:00 2001
From: Daniel Gustafsson <daniel@yesql.se>
Date: Wed, 19 May 2021 15:04:37 +0200
Subject: [PATCH v3 2/3] Add tests for sslinfo

This adds rudimentary coverage of the sslinfo extension into the SSL
test harness. The output is validated by comparing with pg_stat_ssl
to provide some level of test stability should the underlying certs
be slightly altered.
---
 src/test/ssl/Makefile               |   2 +
 src/test/ssl/README                 |   4 +
 src/test/ssl/conf/client_ext.config |  17 ++++
 src/test/ssl/ssl/client_ext.crt     |  21 +++++
 src/test/ssl/ssl/client_ext.key     |  28 ++++++
 src/test/ssl/sslfiles.mk            |   2 +-
 src/test/ssl/t/003_sslinfo.pl       | 137 ++++++++++++++++++++++++++++
 7 files changed, 210 insertions(+), 1 deletion(-)
 create mode 100644 src/test/ssl/conf/client_ext.config
 create mode 100644 src/test/ssl/ssl/client_ext.crt
 create mode 100644 src/test/ssl/ssl/client_ext.key
 create mode 100644 src/test/ssl/t/003_sslinfo.pl

diff --git a/src/test/ssl/Makefile b/src/test/ssl/Makefile
index cb24e31c6e..b749383348 100644
--- a/src/test/ssl/Makefile
+++ b/src/test/ssl/Makefile
@@ -9,6 +9,8 @@
 #
 #-------------------------------------------------------------------------
 
+EXTRA_INSTALL = contrib/sslinfo
+
 subdir = src/test/ssl
 top_builddir = ../../..
 include $(top_builddir)/src/Makefile.global
diff --git a/src/test/ssl/README b/src/test/ssl/README
index 9e2cedc0dd..ca30f9329a 100644
--- a/src/test/ssl/README
+++ b/src/test/ssl/README
@@ -12,6 +12,10 @@ TCP connections on localhost. Any user on the same host is able to
 log in to the test server while the tests are running. Do not run this
 suite on a multi-user system where you don't trust all local users!
 
+NOTE: You must have given the --enable-tap-tests argument to configure.
+Also, to use "make installcheck", you must have built and installed
+contrib/sslinfo in addition to the core code.
+
 Running the tests
 =================
 
diff --git a/src/test/ssl/conf/client_ext.config b/src/test/ssl/conf/client_ext.config
new file mode 100644
index 0000000000..05527b65a7
--- /dev/null
+++ b/src/test/ssl/conf/client_ext.config
@@ -0,0 +1,17 @@
+# An OpenSSL format CSR config file for creating a client certificate.
+#
+# The certificate is for user "ssltestuser" and intends to test client
+# certificate with extensions.
+
+[ req ]
+distinguished_name     = req_distinguished_name
+req_extensions         = client_ext
+prompt                 = no
+
+[ req_distinguished_name ]
+CN                     = ssltestuser
+
+[ client_ext ]
+basicConstraints         = critical,CA:false
+extendedKeyUsage         = clientAuth
+
diff --git a/src/test/ssl/ssl/client_ext.crt b/src/test/ssl/ssl/client_ext.crt
new file mode 100644
index 0000000000..9874ce49b9
--- /dev/null
+++ b/src/test/ssl/ssl/client_ext.crt
@@ -0,0 +1,21 @@
+-----BEGIN CERTIFICATE-----
+MIIDezCCAmOgAwIBAgIIICEREAQyQQAwDQYJKoZIhvcNAQELBQAwQjFAMD4GA1UE
+Aww3VGVzdCBDQSBmb3IgUG9zdGdyZVNRTCBTU0wgcmVncmVzc2lvbiB0ZXN0IGNs
+aWVudCBjZXJ0czAeFw0yMTExMTAwMzMyNDFaFw00OTAzMjgwMzMyNDFaMBYxFDAS
+BgNVBAMMC3NzbHRlc3R1c2VyMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKC
+AQEArCHikkEQLFITbn3ZfO8X2RW3fELeaImgy8W4Pkkc4LxdHCWjdCML/vtE/ZVu
+Op74qrQQWT0HKXFVUiZLbjAgV2PONS6VFHhc3sTFxuTaBnVdY+K98hoFnXskINt/
+wgwUhRcRZuKPcZvEHiqF6e3g3lQa99l1nVKPGPLOCvVhSgoV0Gwgxok0t7s25BCV
+ZmpMAwSTxpeviLF0e2MsttuyClQ4nuD92EHZX3BuG0WNPLxiwikV96uMffpMRGsx
+uiAHzD5ykYM7/b3eU0bjfi0J0qcfTSeytqFuRCNEukJpmtUmyYGqsFJ7HN7ejCY7
+ObAlBn8h+4bgwBRaeZDZLTMaYQIDAQABo4GgMIGdMAwGA1UdEwEB/wQCMAAwEwYD
+VR0lBAwwCgYIKwYBBQUHAwIwHQYDVR0OBBYEFPPv1n7k1Vd9BBC4eoGWPZwVz2Lx
+MFkGA1UdIwRSMFChRKRCMEAxPjA8BgNVBAMMNVRlc3Qgcm9vdCBDQSBmb3IgUG9z
+dGdyZVNRTCBTU0wgcmVncmVzc2lvbiB0ZXN0IHN1aXRlggggIQMDFBIHATANBgkq
+hkiG9w0BAQsFAAOCAQEAtqIeTmUhtHyCt5k2yx88F0dKshYq4Z+LQI+agyZ1fRE6
+Ux5p+SBGbzvc+NcUvc7yGG6w2G/nTVnGwSHN9NtQa2T2XbHJysJ/dwCfmRsachKz
+4kCp0zAHEDrEmZua0sy5BLwwVCk5WNBR0lZ35WmIEuRA+5G/2lCywtrb9W4YnbAM
+nH7BtZE8qPbK4OicB40I2NXz6KhG3755oKN03VC1IaX9JFQxf37ac7jVK5bsjfaF
+0xCAeuDN6wDiVHZj6q1GhhmNLzaF5zmU2e/cI1nTI5tfGKnygavlZIz2VvAlcypt
+YZdMDy69VbTWUa57UPCspghgvm5M2/Hjmz50CXGMvw==
+-----END CERTIFICATE-----
diff --git a/src/test/ssl/ssl/client_ext.key b/src/test/ssl/ssl/client_ext.key
new file mode 100644
index 0000000000..04e5930638
--- /dev/null
+++ b/src/test/ssl/ssl/client_ext.key
@@ -0,0 +1,28 @@
+-----BEGIN PRIVATE KEY-----
+MIIEvQIBADANBgkqhkiG9w0BAQEFAASCBKcwggSjAgEAAoIBAQCsIeKSQRAsUhNu
+fdl87xfZFbd8Qt5oiaDLxbg+SRzgvF0cJaN0Iwv++0T9lW46nviqtBBZPQcpcVVS
+JktuMCBXY841LpUUeFzexMXG5NoGdV1j4r3yGgWdeyQg23/CDBSFFxFm4o9xm8Qe
+KoXp7eDeVBr32XWdUo8Y8s4K9WFKChXQbCDGiTS3uzbkEJVmakwDBJPGl6+IsXR7
+Yyy227IKVDie4P3YQdlfcG4bRY08vGLCKRX3q4x9+kxEazG6IAfMPnKRgzv9vd5T
+RuN+LQnSpx9NJ7K2oW5EI0S6Qmma1SbJgaqwUnsc3t6MJjs5sCUGfyH7huDAFFp5
+kNktMxphAgMBAAECggEAQlVWkmUHXgUNHvXZo8chyhMP4A+G1QNAl3Zs73fObJ66
+RPgOOtmsrEjZh92XmnibvHDiofkeMu7NYfiG9gIO3I6GL0Fxyu8tXt22l9SmXnnJ
+EQ6Wg19azZrgS9c6ryVnnPhMSPlDLRVJaRSbAZCdqSABOoUvSX7AzWz4UQnJwbVp
+c9Le7DbXcD4IIhi+D2o6k46oGTm+P8kEAbw73tN7NmxBudwMhvGup3HlDNypbwPJ
+0aWR+nxZbaAVnmYiENX7L68R9rweqDES8AgV030L4YF022C8TAuBLeCjuEQucdp4
++ZcNUzAF2G1NN/VUpjBKK08+Pu0C0vV+fDrKWK+QnwKBgQC74THLylX/+7TJC24U
+LXu/z5BjkejUr4GLHTZG9edGgaoSiKikXdseCI/RiDVXvtQ7kstFYflOZ+XGuc4l
+GVAN52uRqg7uXw0R8F8bKpal08j4Rhe4rXKvH5h9hSeozOlxq7jrQ2xk96Guu3k7
+ujqkkVoPX+dnwUVN6elWrMIUpwKBgQDqiwqaKk7Pmkqc5et4WKvKFLKYuTU/qOO6
+fVEqGlgbLGNf+DVgKcTl5AVyhqtedh1hin0ij/dDHoYOmynmbe/zguSxF7kYUxdJ
+STwWpQt/ccaWMfqgrjxXpWsPc1fRWgmACAaum04GXmBeZ4z0rVT4blwAVddgoLL8
+q4lrSNbRtwKBgQClv4jnyaxPNecLCmtln66xzFMMlJe8ssztRqswtRYA7Ll2ultV
+DnwVpeYDK1AsBe1EVT/BCSshEaXzyM3lisxGR+htTIL5pp9oORAeblcTGqEM7wFU
+aqhneM9VxRf04jn8j0uHOicxeAmKllfg6m1768NxFuGWdjpG/1pcnfJmtwKBgAF8
+Nen6AJvB710E+7O8ZAIYlXTwH00y5ZZFuuDYX9x0MIDoEnZ0bUHDauFpxuYHO3Jl
+rRst7DPpmpG3G9HQumdBWe9hJhPoWsplA1NlYihBcS98S4j+8XTgoEftxA2YU10T
+L++lHh5eNKAEadkWy+Xy1PRPltiOy/NbprgeMvYLAoGAKpt7DHcK8B0JdOnEzTuz
+7mT6xRt2C9IASCiv92Fx1BPiPy4l9ukT4CJza/wpSpH3xyeB37afe0kQyU8lDrCF
+iMU3RNTzTftwqO8GgtgntgW8ZKe9fuqzm9VLMQFyL+zdqEfGG6ROS8ipYLx9pn6x
+FHc3UsmLmK0hfCr9B4Yo+C0=
+-----END PRIVATE KEY-----
diff --git a/src/test/ssl/sslfiles.mk b/src/test/ssl/sslfiles.mk
index 81c20aac9e..270f55a58f 100644
--- a/src/test/ssl/sslfiles.mk
+++ b/src/test/ssl/sslfiles.mk
@@ -27,7 +27,7 @@ SERVERS := server-cn-and-alt-names \
 	server-multiple-alt-names \
 	server-no-names \
 	server-revoked
-CLIENTS := client client-dn client-revoked
+CLIENTS := client client-dn client-revoked client_ext
 
 #
 # To add a new non-standard key, add it to SPECIAL_KEYS and then add a recipe
diff --git a/src/test/ssl/t/003_sslinfo.pl b/src/test/ssl/t/003_sslinfo.pl
new file mode 100644
index 0000000000..61b117e6c2
--- /dev/null
+++ b/src/test/ssl/t/003_sslinfo.pl
@@ -0,0 +1,137 @@
+
+# Copyright (c) 2021, PostgreSQL Global Development Group
+
+use strict;
+use warnings;
+use PostgreSQL::Test::Cluster;
+use PostgreSQL::Test::Utils;
+use Test::More;
+
+use File::Copy;
+
+use FindBin;
+use lib $FindBin::RealBin;
+
+use SSLServer;
+
+if ($ENV{with_ssl} ne 'openssl')
+{
+	plan skip_all => 'OpenSSL not supported by this build';
+}
+else
+{
+	plan tests => 13;
+}
+
+#### Some configuration
+
+# This is the hostname used to connect to the server. This cannot be a
+# hostname, because the server certificate is always for the domain
+# postgresql-ssl-regression.test.
+my $SERVERHOSTADDR = '127.0.0.1';
+# This is the pattern to use in pg_hba.conf to match incoming connections.
+my $SERVERHOSTCIDR = '127.0.0.1/32';
+
+# Allocation of base connection string shared among multiple tests.
+my $common_connstr;
+
+# The client's private key must not be world-readable, so take a copy
+# of the key stored in the code tree and update its permissions.
+#
+# This changes ssl/client.key to ssl/client_tmp.key etc for the rest
+# of the tests.
+my $client_tmp_key = "${PostgreSQL::Test::Utils::tmp_check}/client_ext.key";
+copy("ssl/client_ext.key", $client_tmp_key)
+  or die "couldn't copy ssl/client_ext.key to $client_tmp_key for permissions change: $!";
+chmod 0600, $client_tmp_key
+  or die "failed to change permissions on $client_tmp_key: $!";
+
+#### Set up the server.
+
+note "setting up data directory";
+my $node = PostgreSQL::Test::Cluster->new('primary');
+$node->init;
+
+# PGHOST is enforced here to set up the node, subsequent connections
+# will use a dedicated connection string.
+$ENV{PGHOST} = $node->host;
+$ENV{PGPORT} = $node->port;
+$node->start;
+
+configure_test_server_for_ssl($node, $SERVERHOSTADDR, $SERVERHOSTCIDR,
+	'trust', extensions => [ qw(sslinfo) ]);
+
+# We aren't using any CRL's in this suite so we can keep using server-revoked
+# as server certificate for simple client.crt connection much like how the
+# 001 test does.
+switch_server_cert($node, 'server-revoked');
+
+$common_connstr =
+  "sslrootcert=ssl/root+server_ca.crt sslmode=require dbname=certdb hostaddr=$SERVERHOSTADDR " .
+  "user=ssltestuser sslcert=ssl/client_ext.crt sslkey=$client_tmp_key";
+
+# Make sure we can connect even though previous test suites have established this
+$node->connect_ok(
+	$common_connstr,
+	"certificate authorization succeeds with correct client cert in PEM format",
+);
+
+my $result;
+
+$result = $node->safe_psql("certdb", "SELECT ssl_is_used();",
+  connstr => $common_connstr);
+is($result, 't', "ssl_is_used() for TLS connection");
+
+$result = $node->safe_psql("certdb", "SELECT ssl_version();",
+  connstr => $common_connstr . " ssl_min_protocol_version=TLSv1.2 " .
+  "ssl_max_protocol_version=TLSv1.2");
+is($result, 'TLSv1.2', "ssl_version() correctly returning TLS protocol");
+
+$result = $node->safe_psql("certdb",
+  "SELECT ssl_cipher() = cipher FROM pg_stat_ssl WHERE pid = pg_backend_pid();",
+  connstr => $common_connstr);
+is($result, 't', "ssl_cipher() compared with pg_stat_ssl");
+
+$result = $node->safe_psql("certdb", "SELECT ssl_client_cert_present();",
+  connstr => $common_connstr);
+is($result, 't', "ssl_client_cert_present() for connection with cert");
+
+$result = $node->safe_psql("trustdb", "SELECT ssl_client_cert_present();",
+  connstr => "sslrootcert=ssl/root+server_ca.crt sslmode=require " .
+  "dbname=trustdb hostaddr=$SERVERHOSTADDR user=ssltestuser");
+is($result, 'f', "ssl_client_cert_present() for connection without cert");
+
+$result = $node->safe_psql("certdb",
+  "SELECT ssl_client_serial() = client_serial FROM pg_stat_ssl WHERE pid = pg_backend_pid();",
+  connstr => $common_connstr);
+is($result, 't', "ssl_client_serial() compared with pg_stat_ssl");
+
+# Must not use safe_psql since we expect an error here
+$result = $node->psql("certdb", "SELECT ssl_client_dn_field('invalid');",
+  connstr => $common_connstr);
+is($result, '3', "ssl_client_dn_field() for an invalid field");
+
+$result = $node->safe_psql("trustdb", "SELECT ssl_client_dn_field('commonName');",
+  connstr => "sslrootcert=ssl/root+server_ca.crt sslmode=require " .
+  "dbname=trustdb hostaddr=$SERVERHOSTADDR user=ssltestuser");
+is($result, '', "ssl_client_dn_field() for connection without cert");
+
+$result = $node->safe_psql("certdb",
+  "SELECT '/CN=' || ssl_client_dn_field('commonName') = client_dn FROM pg_stat_ssl WHERE pid = pg_backend_pid();",
+  connstr => $common_connstr);
+is($result, 't', "ssl_client_dn_field() for commonName");
+
+$result = $node->safe_psql("certdb",
+  "SELECT ssl_issuer_dn() = issuer_dn FROM pg_stat_ssl WHERE pid = pg_backend_pid();",
+  connstr => $common_connstr);
+is($result, 't', "ssl_issuer_dn() for connection with cert");
+
+$result = $node->safe_psql("certdb",
+  "SELECT '/CN=' || ssl_issuer_field('commonName') = issuer_dn FROM pg_stat_ssl WHERE pid = pg_backend_pid();",
+  connstr => $common_connstr);
+is($result, 't', "ssl_issuer_field() for commonName");
+
+$result = $node->safe_psql("certdb",
+  "SELECT value, critical FROM ssl_extension_info() WHERE name = 'basicConstraints';",
+  connstr => $common_connstr);
+is($result, 'CA:FALSE|t', 'extract extension from cert');
-- 
2.24.3 (Apple Git-128)

v3-0003-Use-test-specific-temp-path-for-keys-during-SSL-t.patchapplication/octet-stream; name=v3-0003-Use-test-specific-temp-path-for-keys-during-SSL-t.patch; x-unix-mode=0644Download
From 31ea26479e83349680303b2cbb673ebbfdef381e Mon Sep 17 00:00:00 2001
From: Daniel Gustafsson <daniel@yesql.se>
Date: Mon, 29 Nov 2021 12:04:45 +0100
Subject: [PATCH v3 3/3] Use test-specific temp path for keys during SSL test

The SSL and SCRAM tests both use temporary copies of the supplied test
keys in order to ensure correct permissions. These were however copied
inside the tree using temporary filenames rather than a true temporary
folder. Fix by using tmp_check supplied by PostgreSQL::Test::Utils.

Spotted by Tom Lane during review of a related patch.
---
 src/test/ssl/ssl/.gitignore    |  1 -
 src/test/ssl/t/001_ssltests.pl | 85 ++++++++++++++++------------------
 src/test/ssl/t/002_scram.pl    |  5 +-
 3 files changed, 42 insertions(+), 49 deletions(-)

diff --git a/src/test/ssl/ssl/.gitignore b/src/test/ssl/ssl/.gitignore
index af753d4c7d..9d5fd27810 100644
--- a/src/test/ssl/ssl/.gitignore
+++ b/src/test/ssl/ssl/.gitignore
@@ -1,3 +1,2 @@
 /*.old
 /new_certs_dir/
-/client*_tmp.key
diff --git a/src/test/ssl/t/001_ssltests.pl b/src/test/ssl/t/001_ssltests.pl
index 2f30d11763..37ea9ee687 100644
--- a/src/test/ssl/t/001_ssltests.pl
+++ b/src/test/ssl/t/001_ssltests.pl
@@ -39,28 +39,31 @@ my $common_connstr;
 # The client's private key must not be world-readable, so take a copy
 # of the key stored in the code tree and update its permissions.
 #
-# This changes ssl/client.key to ssl/client_tmp.key etc for the rest
-# of the tests.
+# This changes to using keys stored in a temporary path for the rest of
+# the tests. To get the full path for inclusion in connection strings, the
+# %key hash can be interrogated.
+my %key;
 my @keys = (
-	"client",               "client-revoked",
-	"client-der",           "client-encrypted-pem",
-	"client-encrypted-der", "client-dn");
-foreach my $key (@keys)
+	"client.key",               "client-revoked.key",
+	"client-der.key",           "client-encrypted-pem.key",
+	"client-encrypted-der.key", "client-dn.key");
+foreach my $keyfile (@keys)
 {
-	copy("ssl/${key}.key", "ssl/${key}_tmp.key")
+	copy("ssl/${keyfile}", "${PostgreSQL::Test::Utils::tmp_check}/${keyfile}")
 	  or die
-	  "couldn't copy ssl/${key}.key to ssl/${key}_tmp.key for permissions change: $!";
-	chmod 0600, "ssl/${key}_tmp.key"
-	  or die "failed to change permissions on ssl/${key}_tmp.key: $!";
+	  "couldn't copy ssl/${keyfile} to ${PostgreSQL::Test::Utils::tmp_check}/${keyfile} for permissions change: $!";
+	chmod 0600, "${PostgreSQL::Test::Utils::tmp_check}/${keyfile}"
+	  or die "failed to change permissions on ${PostgreSQL::Test::Utils::tmp_check}/${keyfile}: $!";
+
+	$key{$keyfile} = "${PostgreSQL::Test::Utils::tmp_check}/$keyfile";
 }
 
 # Also make a copy of that explicitly world-readable.  We can't
 # necessarily rely on the file in the source tree having those
-# permissions.  Add it to @keys to include it in the final clean
-# up phase.
-copy("ssl/client.key", "ssl/client_wrongperms_tmp.key");
-chmod 0644, "ssl/client_wrongperms_tmp.key";
-push @keys, 'client_wrongperms';
+# permissions.
+copy("ssl/client.key", "${PostgreSQL::Test::Utils::tmp_check}/client_wrongperms.key");
+chmod 0644, "${PostgreSQL::Test::Utils::tmp_check}/client_wrongperms.key";
+$key{'client_wrongperms.key'} = "${PostgreSQL::Test::Utils::tmp_check}/client_wrongperms.key";
 
 #### Set up the server.
 
@@ -399,34 +402,34 @@ $node->connect_fails(
 
 # correct client cert in unencrypted PEM
 $node->connect_ok(
-	"$common_connstr user=ssltestuser sslcert=ssl/client.crt sslkey=ssl/client_tmp.key",
+	"$common_connstr user=ssltestuser sslcert=ssl/client.crt sslkey=$key{'client.key'}",
 	"certificate authorization succeeds with correct client cert in PEM format"
 );
 
 # correct client cert in unencrypted DER
 $node->connect_ok(
-	"$common_connstr user=ssltestuser sslcert=ssl/client.crt sslkey=ssl/client-der_tmp.key",
+	"$common_connstr user=ssltestuser sslcert=ssl/client.crt sslkey=$key{'client-der.key'}",
 	"certificate authorization succeeds with correct client cert in DER format"
 );
 
 # correct client cert in encrypted PEM
 $node->connect_ok(
-	"$common_connstr user=ssltestuser sslcert=ssl/client.crt sslkey=ssl/client-encrypted-pem_tmp.key sslpassword='dUmmyP^#+'",
+	"$common_connstr user=ssltestuser sslcert=ssl/client.crt sslkey=$key{'client-encrypted-pem.key'} sslpassword='dUmmyP^#+'",
 	"certificate authorization succeeds with correct client cert in encrypted PEM format"
 );
 
 # correct client cert in encrypted DER
 $node->connect_ok(
-	"$common_connstr user=ssltestuser sslcert=ssl/client.crt sslkey=ssl/client-encrypted-der_tmp.key sslpassword='dUmmyP^#+'",
+	"$common_connstr user=ssltestuser sslcert=ssl/client.crt sslkey=$key{'client-encrypted-der.key'} sslpassword='dUmmyP^#+'",
 	"certificate authorization succeeds with correct client cert in encrypted DER format"
 );
 
 # correct client cert in encrypted PEM with wrong password
 $node->connect_fails(
-	"$common_connstr user=ssltestuser sslcert=ssl/client.crt sslkey=ssl/client-encrypted-pem_tmp.key sslpassword='wrong'",
+	"$common_connstr user=ssltestuser sslcert=ssl/client.crt sslkey=$key{'client-encrypted-pem.key'} sslpassword='wrong'",
 	"certificate authorization fails with correct client cert and wrong password in encrypted PEM format",
 	expected_stderr =>
-	  qr!\Qprivate key file "ssl/client-encrypted-pem_tmp.key": bad decrypt\E!
+	  qr!\Qprivate key file "$key{'client-encrypted-pem.key'}": bad decrypt\E!
 );
 
 
@@ -434,7 +437,7 @@ $node->connect_fails(
 my $dn_connstr = "$common_connstr dbname=certdb_dn";
 
 $node->connect_ok(
-	"$dn_connstr user=ssltestuser sslcert=ssl/client-dn.crt sslkey=ssl/client-dn_tmp.key",
+	"$dn_connstr user=ssltestuser sslcert=ssl/client-dn.crt sslkey=$key{'client-dn.key'}",
 	"certificate authorization succeeds with DN mapping",
 	log_like => [
 		qr/connection authenticated: identity="CN=ssltestuser-dn,OU=Testing,OU=Engineering,O=PGDG" method=cert/
@@ -444,14 +447,14 @@ $node->connect_ok(
 $dn_connstr = "$common_connstr dbname=certdb_dn_re";
 
 $node->connect_ok(
-	"$dn_connstr user=ssltestuser sslcert=ssl/client-dn.crt sslkey=ssl/client-dn_tmp.key",
+	"$dn_connstr user=ssltestuser sslcert=ssl/client-dn.crt sslkey=$key{'client-dn.key'}",
 	"certificate authorization succeeds with DN regex mapping");
 
 # same thing but using explicit CN
 $dn_connstr = "$common_connstr dbname=certdb_cn";
 
 $node->connect_ok(
-	"$dn_connstr user=ssltestuser sslcert=ssl/client-dn.crt sslkey=ssl/client-dn_tmp.key",
+	"$dn_connstr user=ssltestuser sslcert=ssl/client-dn.crt sslkey=$key{'client-dn.key'}",
 	"certificate authorization succeeds with CN mapping",
 	# the full DN should still be used as the authenticated identity
 	log_like => [
@@ -469,18 +472,18 @@ TODO:
 
 	# correct client cert in encrypted PEM with empty password
 	$node->connect_fails(
-		"$common_connstr user=ssltestuser sslcert=ssl/client.crt sslkey=ssl/client-encrypted-pem_tmp.key sslpassword=''",
+		"$common_connstr user=ssltestuser sslcert=ssl/client.crt sslkey=$key{'client-encrypted-pem.key'} sslpassword=''",
 		"certificate authorization fails with correct client cert and empty password in encrypted PEM format",
 		expected_stderr =>
-		  qr!\Qprivate key file "ssl/client-encrypted-pem_tmp.key": processing error\E!
+		  qr!\Qprivate key file "$key{'client-encrypted-pem.key'}": processing error\E!
 	);
 
 	# correct client cert in encrypted PEM with no password
 	$node->connect_fails(
-		"$common_connstr user=ssltestuser sslcert=ssl/client.crt sslkey=ssl/client-encrypted-pem_tmp.key",
+		"$common_connstr user=ssltestuser sslcert=ssl/client.crt sslkey=$key{'client-encrypted-pem.key'}",
 		"certificate authorization fails with correct client cert and no password in encrypted PEM format",
 		expected_stderr =>
-		  qr!\Qprivate key file "ssl/client-encrypted-pem_tmp.key": processing error\E!
+		  qr!\Qprivate key file "$key{'client-encrypted-pem.key'}": processing error\E!
 	);
 
 }
@@ -522,7 +525,7 @@ command_like(
 		'-P',
 		'null=_null_',
 		'-d',
-		"$common_connstr user=ssltestuser sslcert=ssl/client.crt sslkey=ssl/client_tmp.key",
+		"$common_connstr user=ssltestuser sslcert=ssl/client.crt sslkey=$key{'client.key'}",
 		'-c',
 		"SELECT * FROM pg_stat_ssl WHERE pid = pg_backend_pid()"
 	],
@@ -536,16 +539,16 @@ SKIP:
 	skip "Permissions check not enforced on Windows", 2 if ($windows_os);
 
 	$node->connect_fails(
-		"$common_connstr user=ssltestuser sslcert=ssl/client.crt sslkey=ssl/client_wrongperms_tmp.key",
+		"$common_connstr user=ssltestuser sslcert=ssl/client.crt sslkey=$key{'client_wrongperms.key'}",
 		"certificate authorization fails because of file permissions",
 		expected_stderr =>
-		  qr!\Qprivate key file "ssl/client_wrongperms_tmp.key" has group or world access\E!
+		  qr!\Qprivate key file "$key{'client_wrongperms.key'}" has group or world access\E!
 	);
 }
 
 # client cert belonging to another user
 $node->connect_fails(
-	"$common_connstr user=anotheruser sslcert=ssl/client.crt sslkey=ssl/client_tmp.key",
+	"$common_connstr user=anotheruser sslcert=ssl/client.crt sslkey=$key{'client.key'}",
 	"certificate authorization fails with client cert belonging to another user",
 	expected_stderr =>
 	  qr/certificate authentication failed for user "anotheruser"/,
@@ -555,7 +558,7 @@ $node->connect_fails(
 
 # revoked client cert
 $node->connect_fails(
-	"$common_connstr user=ssltestuser sslcert=ssl/client-revoked.crt sslkey=ssl/client-revoked_tmp.key",
+	"$common_connstr user=ssltestuser sslcert=ssl/client-revoked.crt sslkey=$key{'client-revoked.key'}",
 	"certificate authorization fails with revoked client cert",
 	expected_stderr => qr/SSL error: sslv3 alert certificate revoked/,
 	# revoked certificates should not authenticate the user
@@ -568,13 +571,13 @@ $common_connstr =
   "sslrootcert=ssl/root+server_ca.crt sslmode=require dbname=verifydb hostaddr=$SERVERHOSTADDR";
 
 $node->connect_ok(
-	"$common_connstr user=ssltestuser sslcert=ssl/client.crt sslkey=ssl/client_tmp.key",
+	"$common_connstr user=ssltestuser sslcert=ssl/client.crt sslkey=$key{'client.key'}",
 	"auth_option clientcert=verify-full succeeds with matching username and Common Name",
 	# verify-full does not provide authentication
 	log_unlike => [qr/connection authenticated:/],);
 
 $node->connect_fails(
-	"$common_connstr user=anotheruser sslcert=ssl/client.crt sslkey=ssl/client_tmp.key",
+	"$common_connstr user=anotheruser sslcert=ssl/client.crt sslkey=$key{'client.key'}",
 	"auth_option clientcert=verify-full fails with mismatching username and Common Name",
 	expected_stderr =>
 	  qr/FATAL: .* "trust" authentication failed for user "anotheruser"/,
@@ -584,7 +587,7 @@ $node->connect_fails(
 # Check that connecting with auth-optionverify-ca in pg_hba :
 # works, when username doesn't match Common Name
 $node->connect_ok(
-	"$common_connstr user=yetanotheruser sslcert=ssl/client.crt sslkey=ssl/client_tmp.key",
+	"$common_connstr user=yetanotheruser sslcert=ssl/client.crt sslkey=$key{'client.key'}",
 	"auth_option clientcert=verify-ca succeeds with mismatching username and Common Name",
 	# verify-full does not provide authentication
 	log_unlike => [qr/connection authenticated:/],);
@@ -592,7 +595,7 @@ $node->connect_ok(
 # intermediate client_ca.crt is provided by client, and isn't in server's ssl_ca_file
 switch_server_cert($node, 'server-cn-only', 'root_ca');
 $common_connstr =
-  "user=ssltestuser dbname=certdb sslkey=ssl/client_tmp.key sslrootcert=ssl/root+server_ca.crt hostaddr=$SERVERHOSTADDR";
+  "user=ssltestuser dbname=certdb sslkey=$key{'client.key'} sslrootcert=ssl/root+server_ca.crt hostaddr=$SERVERHOSTADDR";
 
 $node->connect_ok(
 	"$common_connstr sslmode=require sslcert=ssl/client+client_ca.crt",
@@ -608,12 +611,6 @@ switch_server_cert($node, 'server-cn-only', undef, undef,
 
 # revoked client cert
 $node->connect_fails(
-	"$common_connstr user=ssltestuser sslcert=ssl/client-revoked.crt sslkey=ssl/client-revoked_tmp.key",
+	"$common_connstr user=ssltestuser sslcert=ssl/client-revoked.crt sslkey=$key{'client-revoked.key'}",
 	"certificate authorization fails with revoked client cert with server-side CRL directory",
 	expected_stderr => qr/SSL error: sslv3 alert certificate revoked/);
-
-# clean up
-foreach my $key (@keys)
-{
-	unlink("ssl/${key}_tmp.key");
-}
diff --git a/src/test/ssl/t/002_scram.pl b/src/test/ssl/t/002_scram.pl
index 88803ee5c5..e8831e5ee8 100644
--- a/src/test/ssl/t/002_scram.pl
+++ b/src/test/ssl/t/002_scram.pl
@@ -95,7 +95,7 @@ $node->connect_fails(
 # because channel binding is not performed.  Note that ssl/client.key may
 # be used in a different test, so the name of this temporary client key
 # is chosen here to be unique.
-my $client_tmp_key = "ssl/client_scram_tmp.key";
+my $client_tmp_key = "${PostgreSQL::Test::Utils::tmp_check}/client_scram.key";
 copy("ssl/client.key", $client_tmp_key);
 chmod 0600, $client_tmp_key;
 $node->connect_fails(
@@ -113,7 +113,4 @@ $node->connect_ok(
 		qr/connection authenticated: identity="ssltestuser" method=scram-sha-256/
 	]);
 
-# clean up
-unlink($client_tmp_key);
-
 done_testing($number_of_tests);
-- 
2.24.3 (Apple Git-128)

#10Tom Lane
tgl@sss.pgh.pa.us
In reply to: Daniel Gustafsson (#9)
1 attachment(s)
Re: SSL Tests for sslinfo extension

Daniel Gustafsson <daniel@yesql.se> writes:

Agreed. The attached v3 covers the issuer and extension function to at least
some degree. In order to reliably test the extension I added a new cert with a
CA extension.

I have two remaining trivial nitpicks, for which I attach an 0004
delta patch: the README change was fat-fingered slightly, and some
of the commentary about the key file seems now obsolete.

Otherwise I think it's good to go, so I marked it RFC.

regards, tom lane

Attachments:

v3-0004-nitpicks.patchtext/x-diff; charset=us-ascii; name=v3-0004-nitpicks.patchDownload
diff --git a/src/test/ssl/README b/src/test/ssl/README
index ca30f9329a..7e60700652 100644
--- a/src/test/ssl/README
+++ b/src/test/ssl/README
@@ -12,14 +12,12 @@ TCP connections on localhost. Any user on the same host is able to
 log in to the test server while the tests are running. Do not run this
 suite on a multi-user system where you don't trust all local users!
 
-NOTE: You must have given the --enable-tap-tests argument to configure.
-Also, to use "make installcheck", you must have built and installed
-contrib/sslinfo in addition to the core code.
-
 Running the tests
 =================
 
 NOTE: You must have given the --enable-tap-tests argument to configure.
+Also, to use "make installcheck", you must have built and installed
+contrib/sslinfo in addition to the core code.
 
 Run
     make check
diff --git a/src/test/ssl/t/003_sslinfo.pl b/src/test/ssl/t/003_sslinfo.pl
index 61b117e6c2..cf2e8dde0f 100644
--- a/src/test/ssl/t/003_sslinfo.pl
+++ b/src/test/ssl/t/003_sslinfo.pl
@@ -37,9 +37,6 @@ my $common_connstr;
 
 # The client's private key must not be world-readable, so take a copy
 # of the key stored in the code tree and update its permissions.
-#
-# This changes ssl/client.key to ssl/client_tmp.key etc for the rest
-# of the tests.
 my $client_tmp_key = "${PostgreSQL::Test::Utils::tmp_check}/client_ext.key";
 copy("ssl/client_ext.key", $client_tmp_key)
   or die "couldn't copy ssl/client_ext.key to $client_tmp_key for permissions change: $!";
#11Daniel Gustafsson
daniel@yesql.se
In reply to: Tom Lane (#10)
Re: SSL Tests for sslinfo extension

On 29 Nov 2021, at 23:50, Tom Lane <tgl@sss.pgh.pa.us> wrote:

Daniel Gustafsson <daniel@yesql.se> writes:

Agreed. The attached v3 covers the issuer and extension function to at least
some degree. In order to reliably test the extension I added a new cert with a
CA extension.

I have two remaining trivial nitpicks, for which I attach an 0004
delta patch: the README change was fat-fingered slightly, and some
of the commentary about the key file seems now obsolete.

Ah yes, thanks.

Otherwise I think it's good to go, so I marked it RFC.

Great! I'll take another look over it tomorrow and will go ahead with it then.

--
Daniel Gustafsson https://vmware.com/

#12Daniel Gustafsson
daniel@yesql.se
In reply to: Daniel Gustafsson (#11)
Re: SSL Tests for sslinfo extension

On 30 Nov 2021, at 00:16, Daniel Gustafsson <daniel@yesql.se> wrote:

On 29 Nov 2021, at 23:50, Tom Lane <tgl@sss.pgh.pa.us> wrote:

Otherwise I think it's good to go, so I marked it RFC.

Great! I'll take another look over it tomorrow and will go ahead with it then.

I applied your nitpick diff and took it for another spin in CI, and pushed it.
Thanks for review!

--
Daniel Gustafsson https://vmware.com/