void
pq_init(void)
{
+ Port *port = MyProcPort;
int socket_pos PG_USED_FOR_ASSERTS_ONLY;
int latch_pos PG_USED_FOR_ASSERTS_ONLY;
+ /* fill in the server (local) address */
+ port->laddr.salen = sizeof(port->laddr.addr);
+ if (getsockname(port->sock,
+ (struct sockaddr *) &port->laddr.addr,
+ &port->laddr.salen) < 0)
+ {
+ ereport(FATAL,
+ (errmsg("%s() failed: %m", "getsockname")));
+ }
+
+ /* select NODELAY and KEEPALIVE options if it's a TCP connection */
+ if (port->laddr.addr.ss_family != AF_UNIX)
+ {
+ int on;
+#ifdef WIN32
+ int oldopt;
+ int optlen;
+ int newopt;
+#endif
+
+#ifdef TCP_NODELAY
+ on = 1;
+ if (setsockopt(port->sock, IPPROTO_TCP, TCP_NODELAY,
+ (char *) &on, sizeof(on)) < 0)
+ {
+ ereport(FATAL,
+ (errmsg("%s(%s) failed: %m", "setsockopt", "TCP_NODELAY")));
+ }
+#endif
+ on = 1;
+ if (setsockopt(port->sock, SOL_SOCKET, SO_KEEPALIVE,
+ (char *) &on, sizeof(on)) < 0)
+ {
+ ereport(FATAL,
+ (errmsg("%s(%s) failed: %m", "setsockopt", "SO_KEEPALIVE")));
+ }
+
+#ifdef WIN32
+
+ /*
+ * This is a Win32 socket optimization. The OS send buffer should be
+ * large enough to send the whole Postgres send buffer in one go, or
+ * performance suffers. The Postgres send buffer can be enlarged if a
+ * very large message needs to be sent, but we won't attempt to
+ * enlarge the OS buffer if that happens, so somewhat arbitrarily
+ * ensure that the OS buffer is at least PQ_SEND_BUFFER_SIZE * 4.
+ * (That's 32kB with the current default).
+ *
+ * The default OS buffer size used to be 8kB in earlier Windows
+ * versions, but was raised to 64kB in Windows 2012. So it shouldn't
+ * be necessary to change it in later versions anymore. Changing it
+ * unnecessarily can even reduce performance, because setting
+ * SO_SNDBUF in the application disables the "dynamic send buffering"
+ * feature that was introduced in Windows 7. So before fiddling with
+ * SO_SNDBUF, check if the current buffer size is already large enough
+ * and only increase it if necessary.
+ *
+ * See https://support.microsoft.com/kb/823764/EN-US/ and
+ * https://msdn.microsoft.com/en-us/library/bb736549%28v=vs.85%29.aspx
+ */
+ optlen = sizeof(oldopt);
+ if (getsockopt(port->sock, SOL_SOCKET, SO_SNDBUF, (char *) &oldopt,
+ &optlen) < 0)
+ {
+ ereport(FATAL,
+ (errmsg("%s(%s) failed: %m", "getsockopt", "SO_SNDBUF")));
+ }
+ newopt = PQ_SEND_BUFFER_SIZE * 4;
+ if (oldopt < newopt)
+ {
+ if (setsockopt(port->sock, SOL_SOCKET, SO_SNDBUF, (char *) &newopt,
+ sizeof(newopt)) < 0)
+ {
+ ereport(FATAL,
+ (errmsg("%s(%s) failed: %m", "setsockopt", "SO_SNDBUF")));
+ }
+ }
+#endif
+
+ /*
+ * Also apply the current keepalive parameters. If we fail to set a
+ * parameter, don't error out, because these aren't universally
+ * supported. (Note: you might think we need to reset the GUC
+ * variables to 0 in such a case, but it's not necessary because the
+ * show hooks for these variables report the truth anyway.)
+ */
+ (void) pq_setkeepalivesidle(tcp_keepalives_idle, port);
+ (void) pq_setkeepalivesinterval(tcp_keepalives_interval, port);
+ (void) pq_setkeepalivescount(tcp_keepalives_count, port);
+ (void) pq_settcpusertimeout(tcp_user_timeout, port);
+ }
+
/* initialize state variables */
PqSendBufferSize = PQ_SEND_BUFFER_SIZE;
PqSendBuffer = MemoryContextAlloc(TopMemoryContext, PqSendBufferSize);
* writes.
*/
#ifndef WIN32
- if (!pg_set_noblock(MyProcPort->sock))
+ if (!pg_set_noblock(port->sock))
ereport(FATAL,
(errmsg("could not set socket to nonblocking mode: %m")));
#endif
#ifndef WIN32
/* Don't give the socket to any subprograms we execute. */
- if (fcntl(MyProcPort->sock, F_SETFD, FD_CLOEXEC) < 0)
+ if (fcntl(port->sock, F_SETFD, FD_CLOEXEC) < 0)
elog(FATAL, "fcntl(F_SETFD) failed on socket: %m");
#endif
FeBeWaitSet = CreateWaitEventSet(NULL, FeBeWaitSetNEvents);
socket_pos = AddWaitEventToSet(FeBeWaitSet, WL_SOCKET_WRITEABLE,
- MyProcPort->sock, NULL, NULL);
+ port->sock, NULL, NULL);
latch_pos = AddWaitEventToSet(FeBeWaitSet, WL_LATCH_SET, PGINVALID_SOCKET,
MyLatch, NULL);
AddWaitEventToSet(FeBeWaitSet, WL_POSTMASTER_DEATH, PGINVALID_SOCKET,
return STATUS_ERROR;
}
- /* fill in the server (local) address */
- port->laddr.salen = sizeof(port->laddr.addr);
- if (getsockname(port->sock,
- (struct sockaddr *) &port->laddr.addr,
- &port->laddr.salen) < 0)
- {
- ereport(LOG,
- (errmsg("%s() failed: %m", "getsockname")));
- return STATUS_ERROR;
- }
-
- /* select NODELAY and KEEPALIVE options if it's a TCP connection */
- if (port->laddr.addr.ss_family != AF_UNIX)
- {
- int on;
-#ifdef WIN32
- int oldopt;
- int optlen;
- int newopt;
-#endif
-
-#ifdef TCP_NODELAY
- on = 1;
- if (setsockopt(port->sock, IPPROTO_TCP, TCP_NODELAY,
- (char *) &on, sizeof(on)) < 0)
- {
- ereport(LOG,
- (errmsg("%s(%s) failed: %m", "setsockopt", "TCP_NODELAY")));
- return STATUS_ERROR;
- }
-#endif
- on = 1;
- if (setsockopt(port->sock, SOL_SOCKET, SO_KEEPALIVE,
- (char *) &on, sizeof(on)) < 0)
- {
- ereport(LOG,
- (errmsg("%s(%s) failed: %m", "setsockopt", "SO_KEEPALIVE")));
- return STATUS_ERROR;
- }
-
-#ifdef WIN32
-
- /*
- * This is a Win32 socket optimization. The OS send buffer should be
- * large enough to send the whole Postgres send buffer in one go, or
- * performance suffers. The Postgres send buffer can be enlarged if a
- * very large message needs to be sent, but we won't attempt to
- * enlarge the OS buffer if that happens, so somewhat arbitrarily
- * ensure that the OS buffer is at least PQ_SEND_BUFFER_SIZE * 4.
- * (That's 32kB with the current default).
- *
- * The default OS buffer size used to be 8kB in earlier Windows
- * versions, but was raised to 64kB in Windows 2012. So it shouldn't
- * be necessary to change it in later versions anymore. Changing it
- * unnecessarily can even reduce performance, because setting
- * SO_SNDBUF in the application disables the "dynamic send buffering"
- * feature that was introduced in Windows 7. So before fiddling with
- * SO_SNDBUF, check if the current buffer size is already large enough
- * and only increase it if necessary.
- *
- * See https://support.microsoft.com/kb/823764/EN-US/ and
- * https://msdn.microsoft.com/en-us/library/bb736549%28v=vs.85%29.aspx
- */
- optlen = sizeof(oldopt);
- if (getsockopt(port->sock, SOL_SOCKET, SO_SNDBUF, (char *) &oldopt,
- &optlen) < 0)
- {
- ereport(LOG,
- (errmsg("%s(%s) failed: %m", "getsockopt", "SO_SNDBUF")));
- return STATUS_ERROR;
- }
- newopt = PQ_SEND_BUFFER_SIZE * 4;
- if (oldopt < newopt)
- {
- if (setsockopt(port->sock, SOL_SOCKET, SO_SNDBUF, (char *) &newopt,
- sizeof(newopt)) < 0)
- {
- ereport(LOG,
- (errmsg("%s(%s) failed: %m", "setsockopt", "SO_SNDBUF")));
- return STATUS_ERROR;
- }
- }
-#endif
-
- /*
- * Also apply the current keepalive parameters. If we fail to set a
- * parameter, don't error out, because these aren't universally
- * supported. (Note: you might think we need to reset the GUC
- * variables to 0 in such a case, but it's not necessary because the
- * show hooks for these variables report the truth anyway.)
- */
- (void) pq_setkeepalivesidle(tcp_keepalives_idle, port);
- (void) pq_setkeepalivesinterval(tcp_keepalives_interval, port);
- (void) pq_setkeepalivescount(tcp_keepalives_count, port);
- (void) pq_settcpusertimeout(tcp_user_timeout, port);
- }
-
return STATUS_OK;
}