Обсуждение: Client SSL validation using root.crt
Hello all, I see a strange behaviour using root.crt. PostgreSQL always waits a client certificate to check agains root.crt. But I set up a 'hostnossl' auth line un pg_hba.conf, PostgreSQL still wants a client certificate. Also fails if line is a 'host'. Better with an example: ---pg_hba.conf--- hostssl all all 192.168.0.1/32 md5 hostnossl all all 192.168.0.2/32 md5 ----------------- If I connect to PostgresSQL from 192.168.0.1, it fails if I don't provide a client certificate, it is ok. But if I connect from 192.168.0.2, it also fails becouse I don't send a certificate. But I declared a non-ssl connection from 192.168.0.2, it should let me connect to databases, isn'it? Removing root.crt works as expected. Client in 192.168.0.1 connect using a SSL connection, and client in 192.168.0.2 connect using a single connection. It this behaviour ok? I think not. I want to allow clients on my LAN access PostgreSQL server without a SSL connection , and require a client certificate and a SSL connection to clients from outside my LAN. I think it is not a strange configuration. So the configuration is: ---pg_hba.conf--- hostnossl all all <my-lan-range> md5 hostssl <user> <db> 0.0.0.0/0 md5 ----------------- This fails, because PostgreSQL expect that all clients provide a client certificate. Is there any config option to solve this? Is there any page or manual about PostgreSQL with SSL (more in-deep that http://www.postgresql.org/docs/8.0/interactive/ssl-tcp.html) ? Oh, I'm using PostgreSQL 8.0.8 on a Gentoo box. Maybe I have to upgrade to another version? Thans you in advance.
"Sergio" <sergio.cinos@gmail.com> writes: > I see a strange behaviour using root.crt. PostgreSQL always waits a > client certificate to check agains root.crt. But I set up a > 'hostnossl' auth line un pg_hba.conf, PostgreSQL still wants a client > certificate. No, not really. The problem is that in the default PGSSLMODE=prefer behavior, libpq tries an SSL connection first. It's prepared to retry with a non-SSL connection if it gets a rejection from the server ... but if OpenSSL fails to establish the connection, it just dies immediately. I got the behavior I think you want with the attached patch, which allows a retry for SSL setup errors as well as server rejections. The trouble with this is that it masks SSL setup errors. For example, if the server has "hostssl" to require SSL on localhost connections, and I don't have a client certificate: $ psql -l -h localhost psql: FATAL: no pg_hba.conf entry for host "127.0.0.1", user "tgl", database "postgres", SSL off The only way to get any info about what's wrong with the SSL setup is to select a nondefault SSLMODE: $ PGSSLMODE=require psql -l -h localhost psql: could not open certificate file "/home/tgl/.postgresql/postgresql.crt": No such file or directory I'm not sure there's anything much to be done about this --- in any given failure scenario, the user is probably only interested in one or the other of the SSL and non-SSL error messages, and libpq has no very good way to guess which one. (I thought for a bit about reporting both, but that seems pretty likely to confuse more often than it helps.) So I'm inclined to apply the patch, at least in HEAD (8.2), but wanted to see if anyone had any other ideas. Meanwhile, Sergio's best workaround is "export PGSSLMODE=allow". regards, tom lane Index: fe-connect.c =================================================================== RCS file: /cvsroot/pgsql/src/interfaces/libpq/fe-connect.c,v retrieving revision 1.338 diff -c -r1.338 fe-connect.c *** fe-connect.c 6 Oct 2006 17:14:00 -0000 1.338 --- fe-connect.c 21 Nov 2006 02:56:20 -0000 *************** *** 1400,1405 **** --- 1400,1424 ---- conn->status = CONNECTION_MADE; return PGRES_POLLING_WRITING; } + if (pollres == PGRES_POLLING_FAILED) + { + /* + * Failed ... if sslmode is "prefer" then do a non-SSL + * retry + */ + if (conn->sslmode[0] == 'p' /* "prefer" */ + && conn->allow_ssl_try /* redundant? */ + && !conn->wait_ssl_try) /* redundant? */ + { + /* only retry once */ + conn->allow_ssl_try = false; + /* Must drop the old connection */ + closesocket(conn->sock); + conn->sock = -1; + conn->status = CONNECTION_NEEDED; + goto keep_going; + } + } return pollres; #else /* !USE_SSL */ /* can't get here */
On Mon, Nov 20, 2006 at 10:30:31PM -0500, Tom Lane wrote: > "Sergio" <sergio.cinos@gmail.com> writes: > > I see a strange behaviour using root.crt. PostgreSQL always waits a > > client certificate to check agains root.crt. But I set up a > > 'hostnossl' auth line un pg_hba.conf, PostgreSQL still wants a client > > certificate. > > No, not really. The problem is that in the default PGSSLMODE=prefer > behavior, libpq tries an SSL connection first. It's prepared to retry > with a non-SSL connection if it gets a rejection from the server ... > but if OpenSSL fails to establish the connection, it just dies > immediately. It is possible to continue communicating after SSL negotiation failure. If SSL_accept/connect return 0, that means the negotiation failed cleanly and in theory libpq could continue in non-SSL mode. I think long term this would be the nicest solution (no double connections) but it's probably more complicated then looping around again after SSL failure. Have a nice day, -- Martijn van Oosterhout <kleptog@svana.org> http://svana.org/kleptog/ > From each according to his ability. To each according to his ability to litigate.
Вложения
Martijn van Oosterhout <kleptog@svana.org> writes: > It is possible to continue communicating after SSL negotiation failure. > If SSL_accept/connect return 0, that means the negotiation failed > cleanly and in theory libpq could continue in non-SSL mode. We'd have to change the backend too, though, because in existing releases it likewise will drop out on SSL negotiation failure. > I think long term this would be the nicest solution (no double > connections) but it's probably more complicated then looping around > again after SSL failure. I don't think it's that important. If the backend is configured with ssl = off then we already fall through without using an extra connection cycle. The double connection only occurs if both sides think they should use SSL but something goes wrong ... which is probably a situation that needs user attention anyway. regards, tom lane