Re: OpenSSL Applink - Mailing list pgsql-patches
From | Dave Page |
---|---|
Subject | Re: OpenSSL Applink |
Date | |
Msg-id | 46FD6289.6070806@postgresql.org Whole thread Raw |
In response to | Re: OpenSSL Applink (Dave Page <dpage@postgresql.org>) |
Responses |
Re: OpenSSL Applink
|
List | pgsql-patches |
Dave Page wrote: > Dave Page wrote: >> I did stumble across this text on a mailing list in response to someone >> with a similar problem in some JNI code. I know little of the OpenSSL >> API, but perhaps it rings bells with you before I spend my evening >> trying to figure it out? > > OK, I think I've figured out a fix. Working up a patch now... Patch attached. It appears to work fine except that if the client certificate is missing, instead of: could not open certificate file "C:\Documents and Settings\Dave\Application Data/postgresql/postgresql.crt": No such file or directory I get: Error connecting to the server: SSL SYSCALL error: Operation would block (0x00002733/10035) for reasons that are not clear to me. Any ideas? Regards, Dave Index: src/interfaces/libpq/fe-secure.c =================================================================== RCS file: /projects/cvsroot/pgsql/src/interfaces/libpq/fe-secure.c,v retrieving revision 1.94 diff -c -r1.94 fe-secure.c *** src/interfaces/libpq/fe-secure.c 16 Feb 2007 17:07:00 -0000 1.94 --- src/interfaces/libpq/fe-secure.c 28 Sep 2007 20:15:17 -0000 *************** *** 111,116 **** --- 111,119 ---- #ifdef USE_SSL #include <openssl/ssl.h> + #ifdef WIN32 + #include <openssl/bio.h> + #endif #if (SSLEAY_VERSION_NUMBER >= 0x00907000L) #include <openssl/conf.h> #endif *************** *** 567,572 **** --- 570,581 ---- * This callback is only called when the server wants a * client cert. * + * Note: On Windows we use OpenSSL's BIO functions to + * handle I/O to avoid issues passing FILE pointers to + * incompatible runtimes. We don't use them on other + * platforms because we couldn't then stat the keys to + * check for changes during execution. + * * Must return 1 on success, 0 on no data or error. */ static int *************** *** 579,585 **** --- 588,598 ---- struct stat buf2; #endif char fnbuf[MAXPGPATH]; + #ifndef WIN32 FILE *fp; + #else + BIO *bio; + #endif PGconn *conn = (PGconn *) SSL_get_app_data(ssl); char sebuf[256]; *************** *** 592,605 **** --- 605,626 ---- /* read the user certificate */ snprintf(fnbuf, sizeof(fnbuf), "%s/%s", homedir, USER_CERT_FILE); + #ifndef WIN32 if ((fp = fopen(fnbuf, "r")) == NULL) + #else + if ((bio = BIO_new_file(fnbuf, "r")) == NULL) + #endif { printfPQExpBuffer(&conn->errorMessage, libpq_gettext("could not open certificate file \"%s\": %s\n"), fnbuf, pqStrerror(errno, sebuf, sizeof(sebuf))); return 0; } + #ifndef WIN32 if (PEM_read_X509(fp, x509, NULL, NULL) == NULL) + #else + if (PEM_read_bio_X509(bio, x509, NULL, NULL) == NULL) + #endif { char *err = SSLerrmessage(); *************** *** 607,616 **** --- 628,645 ---- libpq_gettext("could not read certificate file \"%s\": %s\n"), fnbuf, err); SSLerrfree(err); + #ifndef WIN32 fclose(fp); + #else + BIO_free(bio); + #endif return 0; } + #ifndef WIN32 fclose(fp); + #else + BIO_free(bio); + #endif #if (SSLEAY_VERSION_NUMBER >= 0x00907000L) && !defined(OPENSSL_NO_ENGINE) if (getenv("PGSSLKEY")) *************** *** 641,647 **** SSLerrfree(err); free(engine_str); return 0; ! } *pkey = ENGINE_load_private_key(engine_ptr, engine_colon + 1, NULL, NULL); --- 670,676 ---- SSLerrfree(err); free(engine_str); return 0; ! } *pkey = ENGINE_load_private_key(engine_ptr, engine_colon + 1, NULL, NULL); *************** *** 655,661 **** SSLerrfree(err); free(engine_str); return 0; ! } free(engine_str); } else --- 684,690 ---- SSLerrfree(err); free(engine_str); return 0; ! } free(engine_str); } else *************** *** 679,686 **** fnbuf); return 0; } ! #endif if ((fp = fopen(fnbuf, "r")) == NULL) { printfPQExpBuffer(&conn->errorMessage, libpq_gettext("could not open private key file \"%s\": %s\n"), --- 708,718 ---- fnbuf); return 0; } ! if ((fp = fopen(fnbuf, "r")) == NULL) + #else + if ((bio = BIO_new_file(fnbuf, "r")) == NULL) + #endif { printfPQExpBuffer(&conn->errorMessage, libpq_gettext("could not open private key file \"%s\": %s\n"), *************** *** 695,702 **** libpq_gettext("private key file \"%s\" changed during execution\n"), fnbuf); return 0; } ! #endif if (PEM_read_PrivateKey(fp, pkey, NULL, NULL) == NULL) { char *err = SSLerrmessage(); --- 727,737 ---- libpq_gettext("private key file \"%s\" changed during execution\n"), fnbuf); return 0; } ! if (PEM_read_PrivateKey(fp, pkey, NULL, NULL) == NULL) + #else + if (PEM_read_bio_PrivateKey(bio, pkey, NULL, NULL) == NULL) + #endif { char *err = SSLerrmessage(); *************** *** 704,713 **** --- 739,756 ---- libpq_gettext("could not read private key file \"%s\": %s\n"), fnbuf, err); SSLerrfree(err); + #ifndef WIN32 fclose(fp); + #else + BIO_free(bio); + #endif return 0; } + #ifndef WIN32 fclose(fp); + #else + BIO_free(bio); + #endif } /* verify that the cert and key go together */
pgsql-patches by date: