Skip to content

Commit e883d0b

Browse files
committed
Remove sslverify parameter again, replacing it with two new sslmode values:
"verify-ca" and "verify-full". Since "prefer" remains the default, this will make certificate validation off by default, which should lead to less upgrade issues.
1 parent 420ea68 commit e883d0b

File tree

5 files changed

+89
-102
lines changed

5 files changed

+89
-102
lines changed

doc/src/sgml/libpq.sgml

Lines changed: 68 additions & 58 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
<!-- $PostgreSQL: pgsql/doc/src/sgml/libpq.sgml,v 1.285 2009/04/15 13:03:11 momjian Exp $ -->
1+
<!-- $PostgreSQL: pgsql/doc/src/sgml/libpq.sgml,v 1.286 2009/04/24 09:43:09 mha Exp $ -->
22

33
<chapter id="libpq">
44
<title><application>libpq</application> - C Library</title>
@@ -292,7 +292,21 @@
292292
<entry><literal>require</></entry>
293293
<entry>only try an <acronym>SSL</> connection</entry>
294294
</row>
295-
295+
296+
<row>
297+
<entry><literal>verify-ca</></entry>
298+
<entry>only try an <acronym>SSL</> connection, and verify that
299+
the server certificate is issued by a trusted <acronym>CA</>.
300+
</entry>
301+
</row>
302+
303+
<row>
304+
<entry><literal>verify-full</></entry>
305+
<entry>only try an <acronym>SSL</> connection, verify that
306+
the server certificate is issued by a trusted <acronym>CA</> and
307+
that the server hostname matches that in the certificate.</entry>
308+
</row>
309+
296310
</tbody>
297311
</tgroup>
298312
</table>
@@ -311,43 +325,6 @@
311325
</listitem>
312326
</varlistentry>
313327

314-
<varlistentry id="libpq-connect-sslverify" xreflabel="sslverify">
315-
<term><literal>sslverify</literal></term>
316-
<listitem>
317-
<para>
318-
This option controls how libpq verifies the certificate on the
319-
server when performing an <acronym>SSL</> connection. There are
320-
three options: <literal>none</> disables verification completely
321-
(not recommended); <literal>cert</> enables verification that
322-
the server certificate chains to a known certificate
323-
authority (CA); <literal>cn</> will both verify that the
324-
certificate chains to a known CA and that the <literal>cn</>
325-
attribute of the server certificate matches the server's
326-
hostname (default).
327-
</para>
328-
329-
<para>
330-
It is always recommended to use the <literal>cn</> value for
331-
this parameter, since this is the only option that prevents
332-
man-in-the-middle attacks. Note that this requires the server
333-
name on the certificate to match exactly with the host name
334-
used for the connection, and therefore does not support connections
335-
to aliased names. It can be used with pure IP address connections
336-
only if the certificate also has just the IP address in the
337-
<literal>cn</> field.
338-
</para>
339-
340-
<para>
341-
If the <literal>cn</> attribute in the certificate sent by the
342-
server starts with an asterisk (<literal>*</>), it will be treated
343-
as a wildcard. This wildcard can only be present at the start of
344-
the value, and will match all characters <emphasis>except</> a
345-
dot (<literal>.</>). This means the certificate will not match
346-
subdomains.
347-
</para>
348-
</listitem>
349-
</varlistentry>
350-
351328
<varlistentry id="libpq-connect-requiressl" xreflabel="requiressl">
352329
<term><literal>requiressl</literal></term>
353330
<listitem>
@@ -5800,16 +5777,6 @@ myEventProc(PGEventId evtId, void *evtInfo, void *passThrough)
58005777
</para>
58015778
</listitem>
58025779

5803-
<listitem>
5804-
<para>
5805-
<indexterm>
5806-
<primary><envar>PGSSLVERIFY</envar></primary>
5807-
</indexterm>
5808-
<envar>PGSSLVERIFY</envar> behaves the same as <xref
5809-
linkend="libpq-connect-sslverify"> connection parameter.
5810-
</para>
5811-
</listitem>
5812-
58135780
<listitem>
58145781
<para>
58155782
<indexterm>
@@ -6162,25 +6129,60 @@ myEventProc(PGEventId evtId, void *evtInfo, void *passThrough)
61626129
file.
61636130
</para>
61646131

6132+
<sect2 id="libq-ssl-certificates">
6133+
<title>Certificate verification</title>
6134+
6135+
<para>
6136+
By default, <productname>PostgreSQL</> will not perform any validation of
6137+
the server certificate. This means that it is possible to spoof the server
6138+
identity (for example by modifying a DNS record or by taking over the server
6139+
IP address) without the client knowing. In order to prevent this,
6140+
<acronym>SSL</> certificate validation must be used.
6141+
</para>
6142+
6143+
<para>
6144+
If the parameter <literal>sslmode</> is set to <literal>verify-ca</>
6145+
libpq will verify that the server is trustworthy by checking the certificate
6146+
chain up to a trusted <acronym>CA</>. If <literal>sslmode</> is set to
6147+
<literal>verify-full</>, libpq will <emphasis>also</> verify that the server
6148+
hostname matches that of the certificate. The SSL connection will fail if
6149+
the server certificate cannot be verified. <literal>verify-full</> is
6150+
recommended in most security sensitive environments.
6151+
</para>
6152+
61656153
<para>
6166-
When the <literal>sslverify</> parameter is set to <literal>cn</> or
6167-
<literal>cert</>, libpq requires a trustworthy server certificate by
6168-
checking the certificate chain up to a <acronym>CA</>.
6169-
To allow verification, place the certificate of a trusted <acronym>CA</>
6170-
in the file <filename>~/.postgresql/root.crt</> in the user's home directory.
6171-
(On Microsoft Windows the file is named
6154+
In <literal>verify-full</> mode, the <literal>cn</> attribute of the
6155+
certificate is matched against the hostname. If the <literal>cn</>
6156+
attribute starts with an asterisk (<literal>*</>), it will be treated as
6157+
a wildcard, and will match all characters <emphasis>except</> a dot
6158+
(<literal>.</>). This means the certificate will not match subdomains.
6159+
If the connection is made using an IP address instead of a hostname, the
6160+
IP address will be matched (without doing any DNS lookups).
6161+
</para>
6162+
6163+
<para>
6164+
To allow verification, the certificate of a trusted <acronym>CA</> must be
6165+
placed in the file <filename>~/.postgresql/root.crt</> in the user's home
6166+
directory. (On Microsoft Windows the file is named
61726167
<filename>%APPDATA%\postgresql\root.crt</filename>.)
6173-
<application>libpq</application> will then verify that the server's
6174-
certificate is signed by one of the trusted certificate authorities.
6175-
The SSL connection will fail if the server certificate cannot be verified.
6168+
</para>
6169+
6170+
<para>
61766171
Certificate Revocation List (CRL) entries are also checked
61776172
if the file <filename>~/.postgresql/root.crl</filename> exists
61786173
(<filename>%APPDATA%\postgresql\root.crl</filename> on Microsoft
61796174
Windows).
6175+
</para>
6176+
6177+
<para>
61806178
The location of the root certificate store and the CRL can be overridden
61816179
by the connection parameters <literal>sslrootcert</> and <literal>sslcrl</>
61826180
or the environment variables <envar>PGSSLROOTCERT</> and <envar>PGSSLCRL</>.
61836181
</para>
6182+
</sect2>
6183+
6184+
<sect2 id="libpq-ssl-clientcert">
6185+
<title>Client certificates</title>
61846186

61856187
<para>
61866188
If the server requests a trusted client certificate,
@@ -6201,6 +6203,9 @@ myEventProc(PGEventId evtId, void *evtInfo, void *passThrough)
62016203
environment variables <envar>PGSSLCERT</> and <envar>PGSSLKEY</>.
62026204
</para>
62036205

6206+
</sect2>
6207+
<sect2 id="libpq-ssl-fileusage">
6208+
<title>SSL File Usage</title>
62046209
<table id="libpq-ssl-file-usage">
62056210
<title>Libpq/Client SSL File Usage</title>
62066211
<tgroup cols="3">
@@ -6243,6 +6248,10 @@ myEventProc(PGEventId evtId, void *evtInfo, void *passThrough)
62436248
</tbody>
62446249
</tgroup>
62456250
</table>
6251+
</sect2>
6252+
6253+
<sect2 id="libpq-ssl-initialize">
6254+
<title>SSL library initialization</title>
62466255

62476256
<para>
62486257
If your application initializes <literal>libssl</> and/or
@@ -6330,6 +6339,7 @@ myEventProc(PGEventId evtId, void *evtInfo, void *passThrough)
63306339
</varlistentry>
63316340
</variablelist>
63326341
</para>
6342+
</sect2>
63336343

63346344
</sect1>
63356345

doc/src/sgml/runtime.sgml

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
<!-- $PostgreSQL: pgsql/doc/src/sgml/runtime.sgml,v 1.425 2009/01/09 13:37:18 petere Exp $ -->
1+
<!-- $PostgreSQL: pgsql/doc/src/sgml/runtime.sgml,v 1.426 2009/04/24 09:43:09 mha Exp $ -->
22

33
<chapter Id="runtime">
44
<title>Server Setup and Operation</title>
@@ -1422,8 +1422,8 @@ $ <userinput>kill -INT `head -1 /usr/local/pgsql/data/postmaster.pid`</userinput
14221422
<filename>server.key</filename> (key) and
14231423
<filename>server.crt</filename> (certificate) files (<xref
14241424
linkend="ssl-tcp">). The TCP client must connect using
1425-
<literal>sslmode='require'</>, specify <literal>sslverify='cn'</>
1426-
or <literal>sslverify='cert'</> and have the required certificate
1425+
<literal>sslmode='verify-ca'</> or
1426+
<literal>'verify-full'</> and have the required certificate
14271427
files present (<xref linkend="libpq-connect">).
14281428
</para>
14291429
</sect1>

src/interfaces/libpq/fe-connect.c

Lines changed: 10 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@
88
*
99
*
1010
* IDENTIFICATION
11-
* $PostgreSQL: pgsql/src/interfaces/libpq/fe-connect.c,v 1.372 2009/01/01 17:24:03 momjian Exp $
11+
* $PostgreSQL: pgsql/src/interfaces/libpq/fe-connect.c,v 1.373 2009/04/24 09:43:10 mha Exp $
1212
*
1313
*-------------------------------------------------------------------------
1414
*/
@@ -91,11 +91,9 @@ static int ldapServiceLookup(const char *purl, PQconninfoOption *options,
9191
#define DefaultAuthtype ""
9292
#define DefaultPassword ""
9393
#ifdef USE_SSL
94-
#define DefaultSSLMode "prefer"
95-
#define DefaultSSLVerify "cn"
94+
#define DefaultSSLMode "prefer"
9695
#else
9796
#define DefaultSSLMode "disable"
98-
#define DefaultSSLVerify "none"
9997
#endif
10098

10199
/* ----------
@@ -185,9 +183,6 @@ static const PQconninfoOption PQconninfoOptions[] = {
185183
{"sslmode", "PGSSLMODE", DefaultSSLMode, NULL,
186184
"SSL-Mode", "", 8}, /* sizeof("disable") == 8 */
187185

188-
{"sslverify", "PGSSLVERIFY", DefaultSSLVerify, NULL,
189-
"SSL-Verify", "", 5}, /* sizeof("chain") == 5 */
190-
191186
{"sslcert", "PGSSLCERT", NULL, NULL,
192187
"SSL-Client-Cert", "", 64},
193188

@@ -431,8 +426,6 @@ connectOptions1(PGconn *conn, const char *conninfo)
431426
conn->connect_timeout = tmp ? strdup(tmp) : NULL;
432427
tmp = conninfo_getval(connOptions, "sslmode");
433428
conn->sslmode = tmp ? strdup(tmp) : NULL;
434-
tmp = conninfo_getval(connOptions, "sslverify");
435-
conn->sslverify = tmp ? strdup(tmp) : NULL;
436429
tmp = conninfo_getval(connOptions, "sslkey");
437430
conn->sslkey = tmp ? strdup(tmp) : NULL;
438431
tmp = conninfo_getval(connOptions, "sslcert");
@@ -522,7 +515,9 @@ connectOptions2(PGconn *conn)
522515
if (strcmp(conn->sslmode, "disable") != 0
523516
&& strcmp(conn->sslmode, "allow") != 0
524517
&& strcmp(conn->sslmode, "prefer") != 0
525-
&& strcmp(conn->sslmode, "require") != 0)
518+
&& strcmp(conn->sslmode, "require") != 0
519+
&& strcmp(conn->sslmode, "verify-ca") != 0
520+
&& strcmp(conn->sslmode, "verify-full") != 0)
526521
{
527522
conn->status = CONNECTION_BAD;
528523
printfPQExpBuffer(&conn->errorMessage,
@@ -544,6 +539,7 @@ connectOptions2(PGconn *conn)
544539
break;
545540

546541
case 'r': /* "require" */
542+
case 'v': /* "verify-ca" or "verify-full" */
547543
conn->status = CONNECTION_BAD;
548544
printfPQExpBuffer(&conn->errorMessage,
549545
libpq_gettext("sslmode value \"%s\" invalid when SSL support is not compiled in\n"),
@@ -555,24 +551,6 @@ connectOptions2(PGconn *conn)
555551
else
556552
conn->sslmode = strdup(DefaultSSLMode);
557553

558-
/*
559-
* Validate sslverify option
560-
*/
561-
if (conn->sslverify)
562-
{
563-
if (strcmp(conn->sslverify, "none") != 0
564-
&& strcmp(conn->sslverify, "cert") != 0
565-
&& strcmp(conn->sslverify, "cn") != 0)
566-
{
567-
conn->status = CONNECTION_BAD;
568-
printfPQExpBuffer(&conn->errorMessage,
569-
libpq_gettext("invalid sslverify value: \"%s\"\n"),
570-
conn->sslverify);
571-
return false;
572-
}
573-
}
574-
575-
576554
/*
577555
* Only if we get this far is it appropriate to try to connect. (We need a
578556
* state flag, rather than just the boolean result of this function, in
@@ -1428,7 +1406,8 @@ PQconnectPoll(PGconn *conn)
14281406
}
14291407
else if (SSLok == 'N')
14301408
{
1431-
if (conn->sslmode[0] == 'r') /* "require" */
1409+
if (conn->sslmode[0] == 'r' || /* "require" */
1410+
conn->sslmode[0] == 'v') /* "verify-ca" or "verify-full" */
14321411
{
14331412
/* Require SSL, but server does not want it */
14341413
appendPQExpBuffer(&conn->errorMessage,
@@ -1445,7 +1424,8 @@ PQconnectPoll(PGconn *conn)
14451424
/* Received error - probably protocol mismatch */
14461425
if (conn->Pfdebug)
14471426
fprintf(conn->Pfdebug, "received error from server, attempting fallback to pre-7.0\n");
1448-
if (conn->sslmode[0] == 'r') /* "require" */
1427+
if (conn->sslmode[0] == 'r' || /* "require" */
1428+
conn->sslmode[0] == 'v') /* "verify-ca" or "verify-full" */
14491429
{
14501430
/* Require SSL, but server is too old */
14511431
appendPQExpBuffer(&conn->errorMessage,
@@ -2052,8 +2032,6 @@ freePGconn(PGconn *conn)
20522032
free(conn->pgpass);
20532033
if (conn->sslmode)
20542034
free(conn->sslmode);
2055-
if (conn->sslverify)
2056-
free(conn->sslverify);
20572035
if (conn->sslcert)
20582036
free(conn->sslcert);
20592037
if (conn->sslkey)

src/interfaces/libpq/fe-secure.c

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@
1111
*
1212
*
1313
* IDENTIFICATION
14-
* $PostgreSQL: pgsql/src/interfaces/libpq/fe-secure.c,v 1.123 2009/04/14 17:30:16 momjian Exp $
14+
* $PostgreSQL: pgsql/src/interfaces/libpq/fe-secure.c,v 1.124 2009/04/24 09:43:10 mha Exp $
1515
*
1616
* NOTES
1717
*
@@ -523,7 +523,7 @@ verify_peer_name_matches_certificate(PGconn *conn)
523523
* If told not to verify the peer name, don't do it. Return
524524
* 0 indicating that the verification was successful.
525525
*/
526-
if(strcmp(conn->sslverify, "cn") != 0)
526+
if (strcmp(conn->sslmode, "verify-full") != 0)
527527
return true;
528528

529529
if (conn->pghostaddr)
@@ -987,9 +987,9 @@ initialize_SSL(PGconn *conn)
987987
return -1;
988988

989989
/*
990-
* If sslverify is set to anything other than "none", perform certificate
991-
* verification. If set to "cn" we will also do further verifications after
992-
* the connection has been completed.
990+
* If sslmode is set to one of the verify options, perform certificate
991+
* verification. If set to "verify-full" we will also do further
992+
* verification after the connection has been completed.
993993
*
994994
* If we are going to look for either root certificate or CRL in the home directory,
995995
* we need pqGetHomeDirectory() to succeed. In other cases, we don't need to
@@ -999,7 +999,7 @@ initialize_SSL(PGconn *conn)
999999
{
10001000
if (!pqGetHomeDirectory(homedir, sizeof(homedir)))
10011001
{
1002-
if (strcmp(conn->sslverify, "none") != 0)
1002+
if (conn->sslmode[0] == 'v') /* "verify-ca" or "verify-full" */
10031003
{
10041004
printfPQExpBuffer(&conn->errorMessage,
10051005
libpq_gettext("could not get home directory to locate root certificate file"));
@@ -1064,7 +1064,7 @@ initialize_SSL(PGconn *conn)
10641064
else
10651065
{
10661066
/* stat() failed; assume cert file doesn't exist */
1067-
if (strcmp(conn->sslverify, "none") != 0)
1067+
if (conn->sslmode[0] == 'v') /* "verify-ca" or "verify-full" */
10681068
{
10691069
printfPQExpBuffer(&conn->errorMessage,
10701070
libpq_gettext("root certificate file \"%s\" does not exist\n"

src/interfaces/libpq/libpq-int.h

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@
1212
* Portions Copyright (c) 1996-2009, PostgreSQL Global Development Group
1313
* Portions Copyright (c) 1994, Regents of the University of California
1414
*
15-
* $PostgreSQL: pgsql/src/interfaces/libpq/libpq-int.h,v 1.140 2009/04/19 22:37:13 tgl Exp $
15+
* $PostgreSQL: pgsql/src/interfaces/libpq/libpq-int.h,v 1.141 2009/04/24 09:43:10 mha Exp $
1616
*
1717
*-------------------------------------------------------------------------
1818
*/
@@ -294,7 +294,6 @@ struct pg_conn
294294
char *pguser; /* Postgres username and password, if any */
295295
char *pgpass;
296296
char *sslmode; /* SSL mode (require,prefer,allow,disable) */
297-
char *sslverify; /* Verify server SSL certificate (none,chain,cn) */
298297
char *sslkey; /* client key filename */
299298
char *sslcert; /* client certificate filename */
300299
char *sslrootcert; /* root certificate filename */

0 commit comments

Comments
 (0)