1 /*-------------------------------------------------------------------------
4 * functions related to setting up a secure connection to the backend.
5 * Secure connections are expected to provide confidentiality,
6 * message integrity and endpoint authentication.
9 * Portions Copyright (c) 1996-2008, PostgreSQL Global Development Group
10 * Portions Copyright (c) 1994, Regents of the University of California
14 * $PostgreSQL: pgsql/src/interfaces/libpq/fe-secure.c,v 1.106 2008/10/24 12:29:11 mha Exp $
18 * We don't provide informational callbacks here (like
19 * info_cb() in be-secure.c), since there's mechanism to
20 * display that information to the client.
22 *-------------------------------------------------------------------------
25 #include "postgres_fe.h"
38 #include <sys/socket.h>
41 #include <netinet/in.h>
42 #ifdef HAVE_NETINET_TCP_H
43 #include <netinet/tcp.h>
45 #include <arpa/inet.h>
49 #ifdef ENABLE_THREAD_SAFETY
51 #include "pthread-win32.h"
58 #include <openssl/ssl.h>
59 #include <openssl/bio.h>
60 #if (SSLEAY_VERSION_NUMBER >= 0x00907000L)
61 #include <openssl/conf.h>
63 #if (SSLEAY_VERSION_NUMBER >= 0x00907000L) && !defined(OPENSSL_NO_ENGINE)
64 #include <openssl/engine.h>
72 #define USER_CERT_FILE ".postgresql/postgresql.crt"
73 #define USER_KEY_FILE ".postgresql/postgresql.key"
74 #define ROOT_CERT_FILE ".postgresql/root.crt"
75 #define ROOT_CRL_FILE ".postgresql/root.crl"
77 /* On Windows, the "home" directory is already PostgreSQL-specific */
78 #define USER_CERT_FILE "postgresql.crt"
79 #define USER_KEY_FILE "postgresql.key"
80 #define ROOT_CERT_FILE "root.crt"
81 #define ROOT_CRL_FILE "root.crl"
84 #ifndef HAVE_ERR_SET_MARK
85 /* These don't exist in OpenSSL before 0.9.8 */
86 #define ERR_set_mark() ((void) 0)
87 #define ERR_pop_to_mark() ((void) 0)
91 static int verify_peer_name_matches_certificate(PGconn *);
93 static int verify_cb(int ok, X509_STORE_CTX *ctx);
94 static int client_cert_cb(SSL *, X509 **, EVP_PKEY **);
95 static int init_ssl_system(PGconn *conn);
96 static int initialize_SSL(PGconn *);
97 static void destroy_SSL(void);
98 static PostgresPollingStatusType open_client_SSL(PGconn *);
99 static void close_SSL(PGconn *);
100 static char *SSLerrmessage(void);
101 static void SSLerrfree(char *buf);
105 static bool pq_initssllib = true;
107 static SSL_CTX *SSL_context = NULL;
111 * Macros to handle disabling and then restoring the state of SIGPIPE handling.
112 * Note that DISABLE_SIGPIPE() must appear at the start of a block.
116 #ifdef ENABLE_THREAD_SAFETY
118 #define DISABLE_SIGPIPE(failaction) \
120 bool sigpipe_pending; \
121 bool got_epipe = false; \
123 if (pq_block_sigpipe(&osigmask, &sigpipe_pending) < 0) \
126 #define REMEMBER_EPIPE(cond) \
132 #define RESTORE_SIGPIPE() \
133 pq_reset_sigpipe(&osigmask, sigpipe_pending, got_epipe)
135 #else /* !ENABLE_THREAD_SAFETY */
137 #define DISABLE_SIGPIPE(failaction) \
138 pqsigfunc oldsighandler = pqsignal(SIGPIPE, SIG_IGN)
140 #define REMEMBER_EPIPE(cond)
142 #define RESTORE_SIGPIPE() \
143 pqsignal(SIGPIPE, oldsighandler)
145 #endif /* ENABLE_THREAD_SAFETY */
148 #define DISABLE_SIGPIPE(failaction)
149 #define REMEMBER_EPIPE(cond)
150 #define RESTORE_SIGPIPE()
154 /* ------------------------------------------------------------ */
155 /* Procedures common to all secure sessions */
156 /* ------------------------------------------------------------ */
160 * Exported function to allow application to tell us it's already
161 * initialized OpenSSL.
164 PQinitSSL(int do_init)
167 pq_initssllib = do_init;
172 * Initialize global context
175 pqsecure_initialize(PGconn *conn)
180 r = initialize_SSL(conn);
187 * Destroy global context
190 pqsecure_destroy(void)
198 * Attempt to negotiate secure session.
200 PostgresPollingStatusType
201 pqsecure_open_client(PGconn *conn)
204 /* First time through? */
205 if (conn->ssl == NULL)
207 if (!(conn->ssl = SSL_new(SSL_context)) ||
208 !SSL_set_app_data(conn->ssl, conn) ||
209 !SSL_set_fd(conn->ssl, conn->sock))
211 char *err = SSLerrmessage();
213 printfPQExpBuffer(&conn->errorMessage,
214 libpq_gettext("could not establish SSL connection: %s\n"),
218 return PGRES_POLLING_FAILED;
222 * Initialize errorMessage to empty. This allows open_client_SSL() to
223 * detect whether client_cert_cb() has stored a message.
225 resetPQExpBuffer(&conn->errorMessage);
227 /* Begin or continue the actual handshake */
228 return open_client_SSL(conn);
230 /* shouldn't get here */
231 return PGRES_POLLING_FAILED;
236 * Close secure session.
239 pqsecure_close(PGconn *conn)
248 * Read data from a secure connection.
251 pqsecure_read(PGconn *conn, void *ptr, size_t len)
260 /* SSL_read can write to the socket, so we need to disable SIGPIPE */
261 DISABLE_SIGPIPE(return -1);
264 n = SSL_read(conn->ssl, ptr, len);
265 err = SSL_get_error(conn->ssl, n);
270 case SSL_ERROR_WANT_READ:
273 case SSL_ERROR_WANT_WRITE:
276 * Returning 0 here would cause caller to wait for read-ready,
277 * which is not correct since what SSL wants is wait for
278 * write-ready. The former could get us stuck in an infinite
279 * wait, so don't risk it; busy-loop instead.
282 case SSL_ERROR_SYSCALL:
288 REMEMBER_EPIPE(SOCK_ERRNO == EPIPE);
289 printfPQExpBuffer(&conn->errorMessage,
290 libpq_gettext("SSL SYSCALL error: %s\n"),
291 SOCK_STRERROR(SOCK_ERRNO, sebuf, sizeof(sebuf)));
295 printfPQExpBuffer(&conn->errorMessage,
296 libpq_gettext("SSL SYSCALL error: EOF detected\n"));
298 SOCK_ERRNO_SET(ECONNRESET);
305 char *err = SSLerrmessage();
307 printfPQExpBuffer(&conn->errorMessage,
308 libpq_gettext("SSL error: %s\n"), err);
312 case SSL_ERROR_ZERO_RETURN:
313 SOCK_ERRNO_SET(ECONNRESET);
317 printfPQExpBuffer(&conn->errorMessage,
318 libpq_gettext("unrecognized SSL error code: %d\n"),
328 n = recv(conn->sock, ptr, len, 0);
334 * Write data to a secure connection.
337 pqsecure_write(PGconn *conn, const void *ptr, size_t len)
341 DISABLE_SIGPIPE(return -1);
348 n = SSL_write(conn->ssl, ptr, len);
349 err = SSL_get_error(conn->ssl, n);
354 case SSL_ERROR_WANT_READ:
357 * Returning 0 here causes caller to wait for write-ready,
358 * which is not really the right thing, but it's the best we
363 case SSL_ERROR_WANT_WRITE:
366 case SSL_ERROR_SYSCALL:
372 REMEMBER_EPIPE(SOCK_ERRNO == EPIPE);
373 printfPQExpBuffer(&conn->errorMessage,
374 libpq_gettext("SSL SYSCALL error: %s\n"),
375 SOCK_STRERROR(SOCK_ERRNO, sebuf, sizeof(sebuf)));
379 printfPQExpBuffer(&conn->errorMessage,
380 libpq_gettext("SSL SYSCALL error: EOF detected\n"));
381 SOCK_ERRNO_SET(ECONNRESET);
388 char *err = SSLerrmessage();
390 printfPQExpBuffer(&conn->errorMessage,
391 libpq_gettext("SSL error: %s\n"), err);
395 case SSL_ERROR_ZERO_RETURN:
396 SOCK_ERRNO_SET(ECONNRESET);
400 printfPQExpBuffer(&conn->errorMessage,
401 libpq_gettext("unrecognized SSL error code: %d\n"),
410 n = send(conn->sock, ptr, len, 0);
411 REMEMBER_EPIPE(n < 0 && SOCK_ERRNO == EPIPE);
419 /* ------------------------------------------------------------ */
420 /* SSL specific code */
421 /* ------------------------------------------------------------ */
425 * Certificate verification callback
427 * This callback allows us to log intermediate problems during
428 * verification, but there doesn't seem to be a clean way to get
429 * our PGconn * structure. So we can't log anything!
431 * This callback also allows us to override the default acceptance
432 * criteria (e.g., accepting self-signed or expired certs), but
433 * for now we accept the default checks.
436 verify_cb(int ok, X509_STORE_CTX *ctx)
443 * Verify that common name resolves to peer.
446 verify_peer_name_matches_certificate(PGconn *conn)
448 struct hostent *cn_hostentry = NULL;
449 struct sockaddr server_addr;
450 struct sockaddr_in *sin (struct sockaddr_in *) &server_addr;
451 ACCEPT_TYPE_ARG3 len;
455 /* Get the address on the other side of the socket. */
456 len = sizeof(server_addr);
457 if (getpeername(conn->sock, &server_addr, &len) == -1)
461 printfPQExpBuffer(&conn->errorMessage,
462 libpq_gettext("error querying socket: %s\n"),
463 SOCK_STRERROR(SOCK_ERRNO, sebuf, sizeof(sebuf)));
467 if (server_addr.sa_family != AF_INET)
469 printfPQExpBuffer(&conn->errorMessage,
470 libpq_gettext("unsupported protocol\n"));
474 /* Get the IP addresses of the certificate's common name (CN) */
476 struct hostent hpstr;
481 * Currently, pqGethostbyname() is used only on platforms that don't
482 * have getaddrinfo(). If you enable this function, you should
483 * convert the pqGethostbyname() function call to use getaddrinfo().
485 pqGethostbyname(conn->peer_cn, &hpstr, buf, sizeof(buf),
486 &cn_hostentry, &herrno);
489 /* Did we get an IP address? */
490 if (cn_hostentry == NULL)
492 printfPQExpBuffer(&conn->errorMessage,
493 libpq_gettext("could not get information about host \"%s\": %s\n"),
494 conn->peer_cn, hstrerror(h_errno));
498 /* Does one of the CN's IP addresses match the server's IP address? */
499 for (s = cn_hostentry->h_addr_list; *s != NULL; s++)
500 if (!memcmp(&sin->sin_addr.s_addr, *s, cn_hostentry->h_length))
503 l = ntohl(sin->sin_addr.s_addr);
504 printfPQExpBuffer(&conn->errorMessage,
506 "server common name \"%s\" does not resolve to %ld.%ld.%ld.%ld\n"),
507 conn->peer_cn, (l >> 24) % 0x100, (l >> 16) % 0x100,
508 (l >> 8) % 0x100, l % 0x100);
511 #endif /* NOT_USED */
514 * Callback used by SSL to load client cert and key.
515 * This callback is only called when the server wants a
518 * Since BIO functions can set OpenSSL error codes, we must
519 * reset the OpenSSL error stack on *every* exit from this
520 * function once we've started using BIO.
522 * Must return 1 on success, 0 on no data or error.
525 client_cert_cb(SSL *ssl, X509 **x509, EVP_PKEY **pkey)
527 char homedir[MAXPGPATH];
534 char fnbuf[MAXPGPATH];
536 PGconn *conn = (PGconn *) SSL_get_app_data(ssl);
539 if (!pqGetHomeDirectory(homedir, sizeof(homedir)))
541 printfPQExpBuffer(&conn->errorMessage,
542 libpq_gettext("could not get user information\n"));
546 /* read the user certificate */
547 snprintf(fnbuf, sizeof(fnbuf), "%s/%s", homedir, USER_CERT_FILE);
550 * OpenSSL <= 0.9.8 lacks error stack handling, which means it's likely to
551 * report wrong error messages if access to the cert file fails. Do our
552 * own check for the readability of the file to catch the majority of such
553 * problems before OpenSSL gets involved.
555 #ifndef HAVE_ERR_SET_MARK
559 if ((fp2 = fopen(fnbuf, "r")) == NULL)
561 printfPQExpBuffer(&conn->errorMessage,
562 libpq_gettext("could not open certificate file \"%s\": %s\n"),
563 fnbuf, pqStrerror(errno, sebuf, sizeof(sebuf)));
570 /* save OpenSSL error stack */
573 if ((bio = BIO_new_file(fnbuf, "r")) == NULL)
575 printfPQExpBuffer(&conn->errorMessage,
576 libpq_gettext("could not open certificate file \"%s\": %s\n"),
577 fnbuf, pqStrerror(errno, sebuf, sizeof(sebuf)));
582 if (PEM_read_bio_X509(bio, x509, NULL, NULL) == NULL)
584 char *err = SSLerrmessage();
586 printfPQExpBuffer(&conn->errorMessage,
587 libpq_gettext("could not read certificate file \"%s\": %s\n"),
597 #if (SSLEAY_VERSION_NUMBER >= 0x00907000L) && !defined(OPENSSL_NO_ENGINE)
598 if (getenv("PGSSLKEY"))
600 /* read the user key from engine */
601 char *engine_env = getenv("PGSSLKEY");
602 char *engine_colon = strchr(engine_env, ':');
608 printfPQExpBuffer(&conn->errorMessage,
609 libpq_gettext("invalid value of PGSSLKEY environment variable\n"));
614 engine_str = malloc(engine_colon - engine_env + 1);
615 strlcpy(engine_str, engine_env, engine_colon - engine_env + 1);
616 engine_ptr = ENGINE_by_id(engine_str);
617 if (engine_ptr == NULL)
619 char *err = SSLerrmessage();
621 printfPQExpBuffer(&conn->errorMessage,
622 libpq_gettext("could not load SSL engine \"%s\": %s\n"),
630 *pkey = ENGINE_load_private_key(engine_ptr, engine_colon + 1,
634 char *err = SSLerrmessage();
636 printfPQExpBuffer(&conn->errorMessage,
637 libpq_gettext("could not read private SSL key \"%s\" from engine \"%s\": %s\n"),
638 engine_colon + 1, engine_str, err);
647 #endif /* use PGSSLKEY */
649 /* read the user key from file */
650 snprintf(fnbuf, sizeof(fnbuf), "%s/%s", homedir, USER_KEY_FILE);
651 if (stat(fnbuf, &buf) != 0)
653 printfPQExpBuffer(&conn->errorMessage,
654 libpq_gettext("certificate present, but not private key file \"%s\"\n"),
660 if (!S_ISREG(buf.st_mode) || buf.st_mode & (S_IRWXG | S_IRWXO))
662 printfPQExpBuffer(&conn->errorMessage,
663 libpq_gettext("private key file \"%s\" has group or world access; permissions should be u=rw (0600) or less\n"),
670 if ((bio = BIO_new_file(fnbuf, "r")) == NULL)
672 printfPQExpBuffer(&conn->errorMessage,
673 libpq_gettext("could not open private key file \"%s\": %s\n"),
674 fnbuf, pqStrerror(errno, sebuf, sizeof(sebuf)));
679 BIO_get_fp(bio, &fp);
680 if (fstat(fileno(fp), &buf2) == -1 ||
681 buf.st_dev != buf2.st_dev || buf.st_ino != buf2.st_ino)
683 printfPQExpBuffer(&conn->errorMessage,
684 libpq_gettext("private key file \"%s\" changed during execution\n"), fnbuf);
690 if (PEM_read_bio_PrivateKey(bio, pkey, NULL, NULL) == NULL)
692 char *err = SSLerrmessage();
694 printfPQExpBuffer(&conn->errorMessage,
695 libpq_gettext("could not read private key file \"%s\": %s\n"),
707 /* verify that the cert and key go together */
708 if (!X509_check_private_key(*x509, *pkey))
710 char *err = SSLerrmessage();
712 printfPQExpBuffer(&conn->errorMessage,
713 libpq_gettext("certificate does not match private key file \"%s\": %s\n"),
725 #ifdef ENABLE_THREAD_SAFETY
728 pq_threadidcallback(void)
731 * This is not standards-compliant. pthread_self() returns pthread_t, and
732 * shouldn't be cast to unsigned long, but CRYPTO_set_id_callback requires
733 * it, so we have to do it.
735 return (unsigned long) pthread_self();
738 static pthread_mutex_t *pq_lockarray;
741 pq_lockingcallback(int mode, int n, const char *file, int line)
743 if (mode & CRYPTO_LOCK)
745 if (pthread_mutex_lock(&pq_lockarray[n]))
746 PGTHREAD_ERROR("failed to lock mutex");
750 if (pthread_mutex_unlock(&pq_lockarray[n]))
751 PGTHREAD_ERROR("failed to unlock mutex");
754 #endif /* ENABLE_THREAD_SAFETY */
757 * Also see similar code in fe-connect.c, default_threadlock()
760 init_ssl_system(PGconn *conn)
762 #ifdef ENABLE_THREAD_SAFETY
764 static pthread_mutex_t init_mutex = PTHREAD_MUTEX_INITIALIZER;
766 static pthread_mutex_t init_mutex = NULL;
767 static long mutex_initlock = 0;
769 if (init_mutex == NULL)
771 while (InterlockedExchange(&mutex_initlock, 1) == 1)
772 /* loop, another thread own the lock */ ;
773 if (init_mutex == NULL)
775 if (pthread_mutex_init(&init_mutex, NULL))
778 InterlockedExchange(&mutex_initlock, 0);
781 if (pthread_mutex_lock(&init_mutex))
784 if (pq_initssllib && pq_lockarray == NULL)
788 CRYPTO_set_id_callback(pq_threadidcallback);
790 pq_lockarray = malloc(sizeof(pthread_mutex_t) * CRYPTO_num_locks());
793 pthread_mutex_unlock(&init_mutex);
796 for (i = 0; i < CRYPTO_num_locks(); i++)
798 if (pthread_mutex_init(&pq_lockarray[i], NULL))
802 CRYPTO_set_locking_callback(pq_lockingcallback);
809 #if SSLEAY_VERSION_NUMBER >= 0x00907000L
810 OPENSSL_config(NULL);
813 SSL_load_error_strings();
815 SSL_context = SSL_CTX_new(TLSv1_method());
818 char *err = SSLerrmessage();
820 printfPQExpBuffer(&conn->errorMessage,
821 libpq_gettext("could not create SSL context: %s\n"),
824 #ifdef ENABLE_THREAD_SAFETY
825 pthread_mutex_unlock(&init_mutex);
830 #ifdef ENABLE_THREAD_SAFETY
831 pthread_mutex_unlock(&init_mutex);
837 * Initialize global SSL context.
840 initialize_SSL(PGconn *conn)
843 char homedir[MAXPGPATH];
844 char fnbuf[MAXPGPATH];
846 if (init_ssl_system(conn))
849 /* Set up to verify server cert, if root.crt is present */
850 if (pqGetHomeDirectory(homedir, sizeof(homedir)))
852 snprintf(fnbuf, sizeof(fnbuf), "%s/%s", homedir, ROOT_CERT_FILE);
853 if (stat(fnbuf, &buf) == 0)
857 if (!SSL_CTX_load_verify_locations(SSL_context, fnbuf, NULL))
859 char *err = SSLerrmessage();
861 printfPQExpBuffer(&conn->errorMessage,
862 libpq_gettext("could not read root certificate file \"%s\": %s\n"),
868 if ((cvstore = SSL_CTX_get_cert_store(SSL_context)) != NULL)
870 /* setting the flags to check against the complete CRL chain */
871 if (X509_STORE_load_locations(cvstore, ROOT_CRL_FILE, NULL) != 0)
872 /* OpenSSL 0.96 does not support X509_V_FLAG_CRL_CHECK */
873 #ifdef X509_V_FLAG_CRL_CHECK
874 X509_STORE_set_flags(cvstore,
875 X509_V_FLAG_CRL_CHECK | X509_V_FLAG_CRL_CHECK_ALL);
876 /* if not found, silently ignore; we do not require CRL */
879 char *err = SSLerrmessage();
881 printfPQExpBuffer(&conn->errorMessage,
882 libpq_gettext("SSL library does not support CRL certificates (file \"%s\")\n"),
890 SSL_CTX_set_verify(SSL_context, SSL_VERIFY_PEER, verify_cb);
894 /* set up mechanism to provide client certificate, if available */
895 SSL_CTX_set_client_cert_cb(SSL_context, client_cert_cb);
901 * Destroy global SSL context.
908 SSL_CTX_free(SSL_context);
914 * Attempt to negotiate SSL connection.
916 static PostgresPollingStatusType
917 open_client_SSL(PGconn *conn)
921 r = SSL_connect(conn->ssl);
924 int err = SSL_get_error(conn->ssl, r);
928 case SSL_ERROR_WANT_READ:
929 return PGRES_POLLING_READING;
931 case SSL_ERROR_WANT_WRITE:
932 return PGRES_POLLING_WRITING;
934 case SSL_ERROR_SYSCALL:
939 printfPQExpBuffer(&conn->errorMessage,
940 libpq_gettext("SSL SYSCALL error: %s\n"),
941 SOCK_STRERROR(SOCK_ERRNO, sebuf, sizeof(sebuf)));
943 printfPQExpBuffer(&conn->errorMessage,
944 libpq_gettext("SSL SYSCALL error: EOF detected\n"));
946 return PGRES_POLLING_FAILED;
951 * If there are problems with the local certificate files,
952 * these will be detected by client_cert_cb() which is
953 * called from SSL_connect(). We want to return that
954 * error message and not the rather unhelpful error that
955 * OpenSSL itself returns. So check to see if an error
956 * message was already stored.
958 if (conn->errorMessage.len == 0)
960 char *err = SSLerrmessage();
962 printfPQExpBuffer(&conn->errorMessage,
963 libpq_gettext("SSL error: %s\n"),
968 return PGRES_POLLING_FAILED;
972 printfPQExpBuffer(&conn->errorMessage,
973 libpq_gettext("unrecognized SSL error code: %d\n"),
976 return PGRES_POLLING_FAILED;
981 * We already checked the server certificate in initialize_SSL()
982 * using SSL_CTX_set_verify() if root.crt exists.
985 /* pull out server distinguished and common names */
986 conn->peer = SSL_get_peer_certificate(conn->ssl);
987 if (conn->peer == NULL)
989 char *err = SSLerrmessage();
991 printfPQExpBuffer(&conn->errorMessage,
992 libpq_gettext("certificate could not be obtained: %s\n"),
996 return PGRES_POLLING_FAILED;
999 X509_NAME_oneline(X509_get_subject_name(conn->peer),
1000 conn->peer_dn, sizeof(conn->peer_dn));
1001 conn->peer_dn[sizeof(conn->peer_dn) - 1] = '\0';
1003 X509_NAME_get_text_by_NID(X509_get_subject_name(conn->peer),
1004 NID_commonName, conn->peer_cn, SM_USER);
1005 conn->peer_cn[SM_USER] = '\0';
1008 if (verify_peer_name_matches_certificate(conn) == -1)
1011 return PGRES_POLLING_FAILED;
1015 /* SSL handshake is complete */
1016 return PGRES_POLLING_OK;
1020 * Close SSL connection.
1023 close_SSL(PGconn *conn)
1027 DISABLE_SIGPIPE((void) 0);
1028 SSL_shutdown(conn->ssl);
1029 SSL_free(conn->ssl);
1031 /* We have to assume we got EPIPE */
1032 REMEMBER_EPIPE(true);
1038 X509_free(conn->peer);
1044 * Obtain reason string for last SSL error
1046 * Some caution is needed here since ERR_reason_error_string will
1047 * return NULL if it doesn't recognize the error code. We don't
1048 * want to return NULL ever.
1050 static char ssl_nomem[] = "out of memory allocating error description";
1052 #define SSL_ERR_LEN 128
1057 unsigned long errcode;
1058 const char *errreason;
1061 errbuf = malloc(SSL_ERR_LEN);
1064 errcode = ERR_get_error();
1067 snprintf(errbuf, SSL_ERR_LEN, libpq_gettext("no SSL error reported"));
1070 errreason = ERR_reason_error_string(errcode);
1071 if (errreason != NULL)
1073 strlcpy(errbuf, errreason, SSL_ERR_LEN);
1076 snprintf(errbuf, SSL_ERR_LEN, libpq_gettext("SSL error code %lu"), errcode);
1081 SSLerrfree(char *buf)
1083 if (buf != ssl_nomem)
1088 * Return pointer to OpenSSL object.
1091 PQgetssl(PGconn *conn)
1097 #else /* !USE_SSL */
1100 PQgetssl(PGconn *conn)
1104 #endif /* USE_SSL */
1107 #if defined(ENABLE_THREAD_SAFETY) && !defined(WIN32)
1110 * Block SIGPIPE for this thread. This prevents send()/write() from exiting
1114 pq_block_sigpipe(sigset_t *osigset, bool *sigpipe_pending)
1116 sigset_t sigpipe_sigset;
1119 sigemptyset(&sigpipe_sigset);
1120 sigaddset(&sigpipe_sigset, SIGPIPE);
1122 /* Block SIGPIPE and save previous mask for later reset */
1123 SOCK_ERRNO_SET(pthread_sigmask(SIG_BLOCK, &sigpipe_sigset, osigset));
1127 /* We can have a pending SIGPIPE only if it was blocked before */
1128 if (sigismember(osigset, SIGPIPE))
1130 /* Is there a pending SIGPIPE? */
1131 if (sigpending(&sigset) != 0)
1134 if (sigismember(&sigset, SIGPIPE))
1135 *sigpipe_pending = true;
1137 *sigpipe_pending = false;
1140 *sigpipe_pending = false;
1146 * Discard any pending SIGPIPE and reset the signal mask.
1148 * Note: we are effectively assuming here that the C library doesn't queue
1149 * up multiple SIGPIPE events. If it did, then we'd accidentally leave
1150 * ours in the queue when an event was already pending and we got another.
1151 * As long as it doesn't queue multiple events, we're OK because the caller
1152 * can't tell the difference.
1154 * The caller should say got_epipe = FALSE if it is certain that it
1155 * didn't get an EPIPE error; in that case we'll skip the clear operation
1156 * and things are definitely OK, queuing or no. If it got one or might have
1157 * gotten one, pass got_epipe = TRUE.
1159 * We do not want this to change errno, since if it did that could lose
1160 * the error code from a preceding send(). We essentially assume that if
1161 * we were able to do pq_block_sigpipe(), this can't fail.
1164 pq_reset_sigpipe(sigset_t *osigset, bool sigpipe_pending, bool got_epipe)
1166 int save_errno = SOCK_ERRNO;
1170 /* Clear SIGPIPE only if none was pending */
1171 if (got_epipe && !sigpipe_pending)
1173 if (sigpending(&sigset) == 0 &&
1174 sigismember(&sigset, SIGPIPE))
1176 sigset_t sigpipe_sigset;
1178 sigemptyset(&sigpipe_sigset);
1179 sigaddset(&sigpipe_sigset, SIGPIPE);
1181 sigwait(&sigpipe_sigset, &signo);
1185 /* Restore saved block mask */
1186 pthread_sigmask(SIG_SETMASK, osigset, NULL);
1188 SOCK_ERRNO_SET(save_errno);
1191 #endif /* ENABLE_THREAD_SAFETY && !WIN32 */