On 12/02/2013 04:17 PM, Tom Lane wrote:
Bruce Momjian <br...@momjian.us> writes:
Sorry, I should have said:
        Tom is saying that for his openssl version, a client that passed
        an intermediate certificate had to supply a certificate _matching_
        something in the remote root.crt, not just signed by it.
At least I think that was the issue, rather than requiring the client to
supply a "root" certificate, meaning the client can supply an
intermediate or root certificicate, as long as it appears in the
root.crt file on the remote end.
As far as the server is concerned, anything listed in its root.crt *is* a
trusted root CA.  Doesn't matter if it's a child of some other CA.


But it does need to be signed by a trusted signatory. At least in my test script (pretty ugly, but shown below for completeness), the Intermediate CA cert is signed with the Root cert rather than being self-signed as the Root cert is, and so if the server doesn't have that root cert as a trusted cert the validation fails.

In case 1, we put the root CA cert on the server and append the intermediate CA cert to the client's cert. This succeeds. In case 2, we put the intermediate CA cert on the server without the root CA's cert, and use the bare client cert. This fails. In case 3, we put both the root and the intermediate certs in the server's root.crt, and use the bare client key, and as expected this succeeds.

So the idea that you can just plonk any Intermediate CA cert in root.crt and have all keys it signs validated is not true, AFAICT.

OpenSSL version 1.0.0j was used in these tests, on a Fedora 16 box.

cheers

andrew




SUBJ='/C=US/ST=Virginia/L=Herndon/O=testca/OU=eng'
ROOTPASS='rootyroot'
INTERMEDIATEPASS='branchybranch'
LEAFPASS='leafyleaf'
CLIENTLOGIN=andrew
SERVERHOST=emma
INSTALL='/home/andrew/pgl/inst.93.5709'
DATA="$INSTALL/testca"
PGPORT=5809; export PGPORT

rm -rf myCA ; rm -rf myCA
mkdir myCA
cd    myCA


# make root ca in its own directory

mkdir rootCA
cd rootCA
DIR=`pwd`

cp /etc/pki/tls/openssl.cnf .

sed -i -e "s,^dir.*,dir = $DIR," -e 's/#unique_subject/unique_subject/' openssl.cnf

mkdir certs private newcerts
chmod 700 .
echo 1000 > serial
touch index.txt
echo 01 > crlnumber

openssl req -passout pass:"$ROOTPASS" -new -x509 -days 3650 -extensions v3_ca -config openssl.cnf -subj "$SUBJ/CN=root CA" -keyout private/cakey.pem -out cacert.pem openssl rsa -passin pass:"$ROOTPASS" -in private/cakey.pem -out private/cakey.pem


# now intermediate CA

cd ..

cp /etc/pki/tls/openssl.cnf .

DIR=`pwd`

sed -i -e "s,^dir.*,dir = $DIR," -e 's/#unique_subject/unique_subject/' openssl.cnf

mkdir certs private newcerts
chmod 700 .
echo 1000 > serial
touch index.txt
echo 01 > crlnumber

openssl genrsa -passout pass:"$INTERMEDIATEPASS" -des3 -out private/rakey.pem 4096 openssl rsa -passin pass:"$INTERMEDIATEPASS" -in private/rakey.pem -out private/rakey.pem

openssl req -passin pass:INTERMEDIATEPASS -new -subj "$SUBJ/CN=intermediate" -sha1 -key private/rakey.pem -out ra.csr -config openssl.cnf
# sign using root CA
openssl ca -extensions v3_ca -days 365 -out ra.crt -in ra.csr -config rootCA/openssl.cnf -batch
rm ra.csr

cp rootCA/cacert.pem root.crt

#
# postgresql client
#
openssl req -passout pass:$LEAFPASS -subj "$SUBJ/CN=$CLIENTLOGIN" -config openssl.cnf -new -out postgresql.req -keyout postgresql.key
openssl rsa -passin pass:$LEAFPASS -in postgresql.key -out postgresql.key
openssl ca -config openssl.cnf -in postgresql.req -out postgresql.crt -cert ra.crt -keyfile private/rakey.pem -batch

chmod 600 postgresql.key
rm postgresql.req

#
# postgresql server
#
openssl req -passout pass:$LEAFPASS -config openssl.cnf -subj "$SUBJ/CN=$SERVERHOST" -new -out server.req -keyout server.key
openssl rsa -passin pass:$LEAFPASS -in server.key -out server.key
openssl ca -config openssl.cnf -in server.req -out server.crt -cert ra.crt -keyfile private/rakey.pem -batch

chmod 600 server.key
rm server.req

cat ra.crt >> server.crt
cat postgresql.crt ra.crt >> client.crt

# copy certs to server

cp root.crt $DATA/root.crt
cp server.crt $DATA
cp server.key $DATA
rm -f $DATA/root.crl

# restart the server

set -x

(cd $INSTALL && $INSTALL/bin/pg_ctl -D $DATA -l $DIR/logfile.tca -w restart)

# make sure certs work ok
$INSTALL/bin/psql "sslmode=verify-ca host=localhost sslrootcert=root.crt sslcert=client.crt sslkey=postgresql.key" -c 'select $$key 1 OK$$, ssl_client_dn(), ssl_client_serial(), ssl_issuer_dn()'

# copy intermediate cert to server's root and try again with bare client cert

cp  ra.crt  $DATA/root.crt

(cd $INSTALL && $INSTALL/bin/pg_ctl -D $DATA -l $DIR/logfile.tca -w restart)

$INSTALL/bin/psql "sslmode=verify-ca host=localhost sslrootcert=root.crt sslcert=postgresql.crt sslkey=postgresql.key" -c 'select $$key 1 OK$$, ssl_client_dn(), ssl_client_serial(), ssl_issuer_dn()'

# copy root cert to server's root after intermediate crt and try again with bare client cert

cat  root.crt >>  $DATA/root.crt

(cd $INSTALL && $INSTALL/bin/pg_ctl -D $DATA -l $DIR/logfile.tca -w restart)

$INSTALL/bin/psql "sslmode=verify-ca host=localhost sslrootcert=root.crt sslcert=postgresql.crt sslkey=postgresql.key" -c 'select $$key 1 OK$$, ssl_client_dn(), ssl_client_serial(), ssl_issuer_dn()'




--
Sent via pgsql-hackers mailing list (pgsql-hackers@postgresql.org)
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers

Reply via email to