aboutsummaryrefslogtreecommitdiff
path: root/src/backend
diff options
context:
space:
mode:
Diffstat (limited to 'src/backend')
-rw-r--r--src/backend/libpq/Makefile4
-rw-r--r--src/backend/libpq/auth.c9
-rw-r--r--src/backend/libpq/hba.c27
-rw-r--r--src/backend/libpq/pg_hba.conf.sample5
-rw-r--r--src/backend/libpq/pqcomm.c341
-rw-r--r--src/backend/postmaster/postmaster.c9
6 files changed, 226 insertions, 169 deletions
diff --git a/src/backend/libpq/Makefile b/src/backend/libpq/Makefile
index cc4f750a7d6..6e7c1561b4d 100644
--- a/src/backend/libpq/Makefile
+++ b/src/backend/libpq/Makefile
@@ -4,7 +4,7 @@
# Makefile for libpq subsystem (backend half of libpq interface)
#
# IDENTIFICATION
-# $Header: /cvsroot/pgsql/src/backend/libpq/Makefile,v 1.33 2002/06/14 04:23:17 momjian Exp $
+# $Header: /cvsroot/pgsql/src/backend/libpq/Makefile,v 1.34 2002/12/06 03:46:24 momjian Exp $
#
#-------------------------------------------------------------------------
@@ -15,7 +15,7 @@ include $(top_builddir)/src/Makefile.global
# be-fsstubs is here for historical reasons, probably belongs elsewhere
OBJS = be-fsstubs.o be-secure.o auth.o crypt.o hba.o md5.o pqcomm.o \
- pqformat.o pqsignal.o
+ pqformat.o pqsignal.o v6util.o
all: SUBSYS.o
diff --git a/src/backend/libpq/auth.c b/src/backend/libpq/auth.c
index 0e0b64555bc..dfd6d1e93f5 100644
--- a/src/backend/libpq/auth.c
+++ b/src/backend/libpq/auth.c
@@ -8,7 +8,7 @@
*
*
* IDENTIFICATION
- * $Header: /cvsroot/pgsql/src/backend/libpq/auth.c,v 1.92 2002/12/03 22:09:19 momjian Exp $
+ * $Header: /cvsroot/pgsql/src/backend/libpq/auth.c,v 1.93 2002/12/06 03:46:24 momjian Exp $
*
*-------------------------------------------------------------------------
*/
@@ -410,9 +410,12 @@ ClientAuthentication(Port *port)
*/
{
const char *hostinfo = "localhost";
+ char ip_hostinfo[INET6_ADDRSTRLEN];
+ if (isAF_INETx(&port->raddr.sa) ){
+ hostinfo = SockAddr_ntop(&port->raddr, ip_hostinfo,
+ INET6_ADDRSTRLEN, 1);
+ }
- if (port->raddr.sa.sa_family == AF_INET)
- hostinfo = inet_ntoa(port->raddr.in.sin_addr);
elog(FATAL,
"No pg_hba.conf entry for host %s, user %s, database %s",
hostinfo, port->user, port->database);
diff --git a/src/backend/libpq/hba.c b/src/backend/libpq/hba.c
index 396347945e3..5cdf60da96a 100644
--- a/src/backend/libpq/hba.c
+++ b/src/backend/libpq/hba.c
@@ -10,7 +10,7 @@
*
*
* IDENTIFICATION
- * $Header: /cvsroot/pgsql/src/backend/libpq/hba.c,v 1.88 2002/12/03 21:50:44 momjian Exp $
+ * $Header: /cvsroot/pgsql/src/backend/libpq/hba.c,v 1.89 2002/12/06 03:46:26 momjian Exp $
*
*-------------------------------------------------------------------------
*/
@@ -582,9 +582,8 @@ parse_hba(List *line, hbaPort *port, bool *found_p, bool *error_p)
}
else if (strcmp(token, "host") == 0 || strcmp(token, "hostssl") == 0)
{
- struct in_addr file_ip_addr,
- mask;
-
+ SockAddr file_ip_addr, mask;
+
if (strcmp(token, "hostssl") == 0)
{
#ifdef USE_SSL
@@ -619,16 +618,25 @@ parse_hba(List *line, hbaPort *port, bool *found_p, bool *error_p)
if (!line)
goto hba_syntax;
token = lfirst(line);
- if (!inet_aton(token, &file_ip_addr))
- goto hba_syntax;
+
+ if(SockAddr_pton(&file_ip_addr, token, strlen(token)) < 0){
+ goto hba_syntax;
+ }
/* Read the mask field. */
line = lnext(line);
if (!line)
goto hba_syntax;
token = lfirst(line);
- if (!inet_aton(token, &mask))
- goto hba_syntax;
+
+ if(SockAddr_pton(&mask, token, strlen(token)) < 0){
+ goto hba_syntax;
+ }
+
+
+ if(file_ip_addr.sa.sa_family != mask.sa.sa_family){
+ goto hba_syntax;
+ }
/* Read the rest of the line. */
line = lnext(line);
@@ -639,8 +647,7 @@ parse_hba(List *line, hbaPort *port, bool *found_p, bool *error_p)
goto hba_syntax;
/* Must meet network restrictions */
- if (port->raddr.sa.sa_family != AF_INET ||
- ((file_ip_addr.s_addr ^ port->raddr.in.sin_addr.s_addr) & mask.s_addr) != 0)
+ if (!isAF_INETx(&port->raddr) || !rangeSockAddr(&port->raddr, &file_ip_addr, &mask))
return;
}
else
diff --git a/src/backend/libpq/pg_hba.conf.sample b/src/backend/libpq/pg_hba.conf.sample
index 5338c79104b..4ff29977c62 100644
--- a/src/backend/libpq/pg_hba.conf.sample
+++ b/src/backend/libpq/pg_hba.conf.sample
@@ -44,5 +44,6 @@
# TYPE DATABASE USER IP-ADDRESS IP-MASK METHOD
-local all all trust
-host all all 127.0.0.1 255.255.255.255 trust
+local all all trust
+host all all 127.0.0.1 255.255.255.255 trust
+host all all ::1 ffff:ffff:ffff:fff:ffff:ffff:ffff trust
diff --git a/src/backend/libpq/pqcomm.c b/src/backend/libpq/pqcomm.c
index 62e8bd44cd5..757a8a72ce6 100644
--- a/src/backend/libpq/pqcomm.c
+++ b/src/backend/libpq/pqcomm.c
@@ -29,7 +29,7 @@
* Portions Copyright (c) 1996-2002, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
- * $Id: pqcomm.c,v 1.141 2002/09/04 23:31:34 tgl Exp $
+ * $Id: pqcomm.c,v 1.142 2002/12/06 03:46:28 momjian Exp $
*
*-------------------------------------------------------------------------
*/
@@ -85,6 +85,11 @@ extern ssize_t secure_read(Port *, void *, size_t);
extern ssize_t secure_write(Port *, const void *, size_t);
static void pq_close(void);
+#ifdef HAVE_UNIX_SOCKETS
+int StreamServerPortSubAFUNIX1(unsigned short portNumber,
+ char *unixSocketName );
+int StreamServerPortSubAFUNIX2(void);
+#endif /* HAVE_UNIX_SOCKETS */
/*
@@ -182,171 +187,199 @@ int
StreamServerPort(int family, char *hostName, unsigned short portNumber,
char *unixSocketName, int *fdP)
{
- SockAddr saddr;
- int fd,
- err;
- int maxconn;
- size_t len = 0;
- int one = 1;
+ int fd,
+ err;
+ int maxconn;
+ int one = 1;
- Assert(family == AF_INET || family == AF_UNIX);
+ int ret;
+ struct addrinfo* addrs = NULL;
+ struct addrinfo hint;
+ char portNumberStr[64];
+ char* service = portNumberStr;
+ char* hostn = (hostName[0] == '\0')? NULL : hostName;
- if ((fd = socket(family, SOCK_STREAM, 0)) < 0)
- {
- elog(LOG, "StreamServerPort: socket() failed: %m");
- return STATUS_ERROR;
- }
+ Assert(family == AF_INET6 || family == AF_INET || family == AF_UNIX);
- if (family == AF_INET)
- {
- if ((setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, (char *) &one,
- sizeof(one))) == -1)
- {
- elog(LOG, "StreamServerPort: setsockopt(SO_REUSEADDR) failed: %m");
- return STATUS_ERROR;
- }
- }
+ memset(&hint, 0, sizeof(hint));
+ hint.ai_family = family;
+ hint.ai_flags = AI_PASSIVE;
+ hint.ai_socktype = SOCK_STREAM;
- MemSet((char *) &saddr, 0, sizeof(saddr));
- saddr.sa.sa_family = family;
+ snprintf(portNumberStr, sizeof(portNumberStr)/sizeof(char),
+ "%d", portNumber);
#ifdef HAVE_UNIX_SOCKETS
- if (family == AF_UNIX)
- {
- UNIXSOCK_PATH(saddr.un, portNumber, unixSocketName);
- len = UNIXSOCK_LEN(saddr.un);
- strcpy(sock_path, saddr.un.sun_path);
-
- /*
- * Grab an interlock file associated with the socket file.
- */
- if (!CreateSocketLockFile(sock_path, true))
- return STATUS_ERROR;
-
- /*
- * Once we have the interlock, we can safely delete any
- * pre-existing socket file to avoid failure at bind() time.
- */
- unlink(sock_path);
- }
+ if (family == AF_UNIX) {
+ if(StreamServerPortSubAFUNIX1(portNumber, unixSocketName) != STATUS_OK){
+ return STATUS_ERROR;
+ }
+ service = sock_path;
+ }
#endif /* HAVE_UNIX_SOCKETS */
- if (family == AF_INET)
- {
- /* TCP/IP socket */
- if (hostName[0] == '\0')
- saddr.in.sin_addr.s_addr = htonl(INADDR_ANY);
- else
- {
- struct hostent *hp;
- hp = gethostbyname(hostName);
- if ((hp == NULL) || (hp->h_addrtype != AF_INET))
- {
- elog(LOG, "StreamServerPort: gethostbyname(%s) failed",
- hostName);
- return STATUS_ERROR;
- }
- memmove((char *) &(saddr.in.sin_addr), (char *) hp->h_addr,
- hp->h_length);
- }
- saddr.in.sin_port = htons(portNumber);
- len = sizeof(struct sockaddr_in);
- }
-
- err = bind(fd, (struct sockaddr *) & saddr.sa, len);
- if (err < 0)
- {
- if (family == AF_UNIX)
- elog(LOG, "StreamServerPort: bind() failed: %m\n"
- "\tIs another postmaster already running on port %d?\n"
- "\tIf not, remove socket node (%s) and retry.",
- (int) portNumber, sock_path);
- else
- elog(LOG, "StreamServerPort: bind() failed: %m\n"
- "\tIs another postmaster already running on port %d?\n"
- "\tIf not, wait a few seconds and retry.",
- (int) portNumber);
- return STATUS_ERROR;
- }
+ ret = getaddrinfo2(hostn, service, &hint, &addrs);
+ if(ret || addrs == NULL){
+ elog(LOG, "FATAL: StreamServerPort: getaddrinfo2() failed: %s\n",
+ gai_strerror(ret));
+ freeaddrinfo2(hint.ai_family, addrs);
+ return STATUS_ERROR;
+ }
+
+
+ /** YY DEBUG
+ if(addrs->ai_family == AF_UNIX){
+ printf("%s-%s-%s \n", "debug: AF_UNIX!", unixSocketName, hostName);
+ }
+ else {
+ printf("%s", "debug: NOT AF_UNIX!\n");
+ }
+ fflush(stdout);
+ **/
+
+ if( (fd = socket(addrs->ai_family, SOCK_STREAM, 0)) < 0){
+ elog(LOG, "FATAL: StreamServerPort: socket() failed: %s\n",
+ strerror(errno));
+ freeaddrinfo2(hint.ai_family, addrs);
+ return STATUS_ERROR;
+ }
+
+ if( isAF_INETx2(family) ){
+ if ((setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, (char*)&one,
+ sizeof(one) )) == -1 ){
+ elog(LOG, "FATAL: StreamServerPort: setsockopt(SO_REUSEADDR) failed: %s\n",
+ strerror(errno));
+ freeaddrinfo2(hint.ai_family, addrs);
+ return STATUS_ERROR;
+ }
+ }
+
+
+ err = bind(fd, addrs->ai_addr, addrs->ai_addrlen);
+ if(err < 0){
+ elog(LOG, "FATAL: StreamServerPort: bind() failed: %s\n"
+ "\tIs another postmaster already running on port %d?\n",
+ strerror(errno), (int) portNumber);
+ if (family == AF_UNIX)
+ elog(LOG, "\tIf not, remove socket node (%s) and retry.\n",
+ sock_path);
+ else
+ elog(LOG, "\tIf not, wait a few seconds and retry.\n");
+ freeaddrinfo2(hint.ai_family, addrs);
+ return STATUS_ERROR;
+ }
#ifdef HAVE_UNIX_SOCKETS
- if (family == AF_UNIX)
- {
- /* Arrange to unlink the socket file at exit */
- on_proc_exit(StreamDoUnlink, 0);
-
- /*
- * Fix socket ownership/permission if requested. Note we must do
- * this before we listen() to avoid a window where unwanted
- * connections could get accepted.
- */
- Assert(Unix_socket_group);
- if (Unix_socket_group[0] != '\0')
- {
- char *endptr;
- unsigned long int val;
- gid_t gid;
-
- val = strtoul(Unix_socket_group, &endptr, 10);
- if (*endptr == '\0')
- {
- /* numeric group id */
- gid = val;
- }
- else
- {
- /* convert group name to id */
- struct group *gr;
-
- gr = getgrnam(Unix_socket_group);
- if (!gr)
- {
- elog(LOG, "No such group as '%s'",
- Unix_socket_group);
- return STATUS_ERROR;
- }
- gid = gr->gr_gid;
- }
- if (chown(sock_path, -1, gid) == -1)
- {
- elog(LOG, "Could not set group of %s: %m",
- sock_path);
- return STATUS_ERROR;
- }
- }
+ if (family == AF_UNIX){
+ if(StreamServerPortSubAFUNIX2() != STATUS_OK){
+ freeaddrinfo2(hint.ai_family, addrs);
+ return STATUS_ERROR;
+ }
+ }
+#endif
- if (chmod(sock_path, Unix_socket_permissions) == -1)
- {
- elog(LOG, "Could not set permissions on %s: %m",
- sock_path);
- return STATUS_ERROR;
- }
- }
-#endif /* HAVE_UNIX_SOCKETS */
+ /*
+ * Select appropriate accept-queue length limit. PG_SOMAXCONN is only
+ * intended to provide a clamp on the request on platforms where an
+ * overly large request provokes a kernel error (are there any?).
+ */
+ maxconn = MaxBackends * 2;
+ if (maxconn > PG_SOMAXCONN)
+ maxconn = PG_SOMAXCONN;
+
+ err = listen(fd, maxconn);
+ if (err < 0) {
+ elog(LOG, "FATAL: StreamServerPort: listen() failed: %s\n",
+ strerror(errno));
+ freeaddrinfo2(hint.ai_family, addrs);
+ return STATUS_ERROR;
+ }
+
+ *fdP = fd;
+ freeaddrinfo2(hint.ai_family, addrs);
+ return STATUS_OK;
- /*
- * Select appropriate accept-queue length limit. PG_SOMAXCONN is only
- * intended to provide a clamp on the request on platforms where an
- * overly large request provokes a kernel error (are there any?).
- */
- maxconn = MaxBackends * 2;
- if (maxconn > PG_SOMAXCONN)
- maxconn = PG_SOMAXCONN;
+}
- err = listen(fd, maxconn);
- if (err < 0)
- {
- elog(LOG, "StreamServerPort: listen() failed: %m");
- return STATUS_ERROR;
- }
+#ifdef HAVE_UNIX_SOCKETS
+int StreamServerPortSubAFUNIX1(unsigned short portNumber,
+ char *unixSocketName )
+{
+ SockAddr saddr;
+ int len;
+
+ MemSet((char *) &saddr, 0, sizeof(saddr));
+
+ UNIXSOCK_PATH(saddr.un, portNumber, unixSocketName);
+ len = UNIXSOCK_LEN(saddr.un);
+ strcpy(sock_path, saddr.un.sun_path);
+
+ /*
+ * Grab an interlock file associated with the socket file.
+ */
+ if (!CreateSocketLockFile(sock_path, true))
+ return STATUS_ERROR;
+
+ /*
+ * Once we have the interlock, we can safely delete any
+ * pre-existing socket file to avoid failure at bind() time.
+ */
+ unlink(sock_path);
+
+ return STATUS_OK;
+}
- *fdP = fd;
- return STATUS_OK;
+int StreamServerPortSubAFUNIX2(void)
+{
+ /* Arrange to unlink the socket file at exit */
+ on_proc_exit(StreamDoUnlink, 0);
+
+ /*
+ * Fix socket ownership/permission if requested. Note we must do
+ * this before we listen() to avoid a window where unwanted
+ * connections could get accepted.
+ */
+ Assert(Unix_socket_group);
+ if (Unix_socket_group[0] != '\0') {
+ char *endptr;
+ unsigned long int val;
+ gid_t gid;
+
+ val = strtoul(Unix_socket_group, &endptr, 10);
+ if (*endptr == '\0'){ /* numeric group id */
+ gid = val;
+ }
+ else { /* convert group name to id */
+ struct group *gr;
+ gr = getgrnam(Unix_socket_group);
+ if (!gr) {
+ elog(LOG, "FATAL: no such group '%s'\n",
+ Unix_socket_group);
+ return STATUS_ERROR;
+ }
+ gid = gr->gr_gid;
+ }
+ if (chown(sock_path, -1, gid) == -1){
+ elog(LOG, "FATAL: could not set group of %s: %s\n",
+ sock_path, strerror(errno));
+ return STATUS_ERROR;
+ }
+ }
+
+ if (chmod(sock_path, Unix_socket_permissions) == -1){
+ elog(LOG, "FATAL: could not set permissions on %s: %s\n",
+ sock_path, strerror(errno));
+ return STATUS_ERROR;
+ }
+ return STATUS_OK;
}
+#endif /* HAVE_UNIX_SOCKETS */
+
+
/*
* StreamConnection -- create a new connection with client using
* server port.
@@ -391,8 +424,20 @@ StreamConnection(int server_fd, Port *port)
return STATUS_ERROR;
}
+ /* DEBUG YY
+ {
+ char l_hostinfo[INET6_ADDRSTRLEN];
+ char r_hostinfo[INET6_ADDRSTRLEN];
+ SockAddr_ntop(&port->laddr, l_hostinfo, INET6_ADDRSTRLEN, 1);
+ SockAddr_ntop(&port->raddr, r_hostinfo, INET6_ADDRSTRLEN, 1);
+ printf("StreamConnect() l: %s r: %s\n", l_hostinfo, r_hostinfo);
+ printf("StreamConnect() l: %d r: %d\n", port->laddr.sa.sa_family,
+ port->raddr.sa.sa_family);
+ }
+ */
+
/* select NODELAY and KEEPALIVE options if it's a TCP connection */
- if (port->laddr.sa.sa_family == AF_INET)
+ if ( isAF_INETx(&port->laddr) )
{
int on = 1;
diff --git a/src/backend/postmaster/postmaster.c b/src/backend/postmaster/postmaster.c
index 8f34a3fd2dc..07787844903 100644
--- a/src/backend/postmaster/postmaster.c
+++ b/src/backend/postmaster/postmaster.c
@@ -37,7 +37,7 @@
*
*
* IDENTIFICATION
- * $Header: /cvsroot/pgsql/src/backend/postmaster/postmaster.c,v 1.299 2002/11/21 06:36:08 tgl Exp $
+ * $Header: /cvsroot/pgsql/src/backend/postmaster/postmaster.c,v 1.300 2002/12/06 03:46:29 momjian Exp $
*
* NOTES
*
@@ -669,7 +669,7 @@ PostmasterMain(int argc, char *argv[])
*/
if (NetServer)
{
- status = StreamServerPort(AF_INET, VirtualHost,
+ status = StreamServerPort(AF_INET6, VirtualHost,
(unsigned short) PostPortNumber,
UnixSocketDir,
&ServerSock_INET);
@@ -2091,13 +2091,14 @@ DoBackend(Port *port)
/*
* Get the remote host name and port for logging and status display.
*/
- if (port->raddr.sa.sa_family == AF_INET)
+ if (isAF_INETx(&port->raddr))
{
unsigned short remote_port;
char *host_addr;
+ char ip_hostinfo[INET6_ADDRSTRLEN];
remote_port = ntohs(port->raddr.in.sin_port);
- host_addr = inet_ntoa(port->raddr.in.sin_addr);
+ host_addr = SockAddr_ntop(&port->raddr, ip_hostinfo, INET6_ADDRSTRLEN, 1);
remote_host = NULL;