summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/backend/bootstrap/bootstrap.c9
-rw-r--r--src/backend/port/sysv_shmem.c89
-rw-r--r--src/backend/postmaster/postmaster.c12
-rw-r--r--src/backend/tcop/postgres.c12
-rw-r--r--src/include/storage/pg_shmem.h3
5 files changed, 78 insertions, 47 deletions
diff --git a/src/backend/bootstrap/bootstrap.c b/src/backend/bootstrap/bootstrap.c
index 215e165cf7..54b541a0d6 100644
--- a/src/backend/bootstrap/bootstrap.c
+++ b/src/backend/bootstrap/bootstrap.c
@@ -8,7 +8,7 @@
* Portions Copyright (c) 1994, Regents of the University of California
*
* IDENTIFICATION
- * $Header: /cvsroot/pgsql/src/backend/bootstrap/bootstrap.c,v 1.155 2003/05/06 23:34:55 momjian Exp $
+ * $Header: /cvsroot/pgsql/src/backend/bootstrap/bootstrap.c,v 1.156 2003/05/08 14:49:03 momjian Exp $
*
*-------------------------------------------------------------------------
*/
@@ -286,11 +286,14 @@ BootstrapMain(int argc, char *argv[])
case 'p':
{
/* indicates fork from postmaster */
- char *p;
#ifdef EXEC_BACKEND
- sscanf(optarg, "%d,", &UsedShmemSegID);
+ char *p;
+
+ sscanf(optarg, "%d,%p,", &UsedShmemSegID, &UsedShmemSegAddr);
p = strchr(optarg, ',');
if (p)
+ p = strchr(p+1, ',');
+ if (p)
dbname = strdup(p+1);
#else
dbname = strdup(optarg);
diff --git a/src/backend/port/sysv_shmem.c b/src/backend/port/sysv_shmem.c
index c98aff5231..9454c3e92c 100644
--- a/src/backend/port/sysv_shmem.c
+++ b/src/backend/port/sysv_shmem.c
@@ -10,7 +10,7 @@
* Portions Copyright (c) 1994, Regents of the University of California
*
* IDENTIFICATION
- * $Header: /cvsroot/pgsql/src/backend/port/sysv_shmem.c,v 1.8 2003/05/06 23:34:55 momjian Exp $
+ * $Header: /cvsroot/pgsql/src/backend/port/sysv_shmem.c,v 1.9 2003/05/08 14:49:03 momjian Exp $
*
*-------------------------------------------------------------------------
*/
@@ -39,9 +39,8 @@ typedef int IpcMemoryId; /* shared memory ID returned by shmget(2) */
#define IPCProtection (0600) /* access/modify by user only */
-#ifdef EXEC_BACKEND
IpcMemoryKey UsedShmemSegID = 0;
-#endif
+void *UsedShmemSegAddr = NULL;
static void *InternalIpcMemoryCreate(IpcMemoryKey memKey, uint32 size);
static void IpcMemoryDetach(int status, Datum shmaddr);
@@ -282,7 +281,7 @@ PrivateMemoryDelete(int status, Datum memaddr)
*
* Create a shared memory segment of the given size and initialize its
* standard header. Also, register an on_shmem_exit callback to release
- * the storage.
+ * the storage. For an exec'ed backend, it just attaches.
*
* Dead Postgres segments are recycled if found, but we do not fail upon
* collision with non-Postgres shmem segments. The idea here is to detect and
@@ -302,11 +301,9 @@ PGSharedMemoryCreate(uint32 size, bool makePrivate, int port)
/* Room for a header? */
Assert(size > MAXALIGN(sizeof(PGShmemHeader)));
-#ifdef EXEC_BACKEND
- if (UsedShmemSegID != 0)
+ if (ExecBackend && UsedShmemSegID != 0)
NextShmemSegID = UsedShmemSegID;
else
-#endif
NextShmemSegID = port * 1000 + 1;
for (;;NextShmemSegID++)
@@ -320,25 +317,39 @@ PGSharedMemoryCreate(uint32 size, bool makePrivate, int port)
break;
}
- /* Try to create new segment */
- memAddress = InternalIpcMemoryCreate(NextShmemSegID, size);
- if (memAddress)
- break; /* successful create and attach */
+ /* If attach to fixed address, only try once */
+ if (ExecBackend && UsedShmemSegAddr != NULL && NextShmemSegID != UsedShmemSegID)
+ {
+ fprintf(stderr, "Unable to attach to memory at fixed address: shmget(key=%d, addr=%p) failed: %s\n",
+ (int) UsedShmemSegID, UsedShmemSegAddr, strerror(errno));
+ proc_exit(1);
+ }
+
+ if (!ExecBackend || UsedShmemSegAddr == NULL)
+ {
+ /* Try to create new segment */
+ memAddress = InternalIpcMemoryCreate(NextShmemSegID, size);
+ if (memAddress)
+ break; /* successful create and attach */
+ }
/* See if it looks to be leftover from a dead Postgres process */
shmid = shmget(NextShmemSegID, sizeof(PGShmemHeader), 0);
if (shmid < 0)
continue; /* failed: must be some other app's */
-#if defined(solaris) && defined(__sparc__)
/* use intimate shared memory on SPARC Solaris */
- memAddress = shmat(shmid, 0, SHM_SHARE_MMU);
+ memAddress = shmat(shmid, UsedShmemSegAddr,
+#if defined(solaris) && defined(__sparc__)
+ SHM_SHARE_MMU
#else
- memAddress = shmat(shmid, 0, 0);
+ 0
#endif
+ );
if (memAddress == (void *) -1)
continue; /* failed: must be some other app's */
+
hdr = (PGShmemHeader *) memAddress;
if (hdr->magic != PGShmemMagic)
{
@@ -346,14 +357,19 @@ PGSharedMemoryCreate(uint32 size, bool makePrivate, int port)
continue; /* segment belongs to a non-Postgres app */
}
+ /* Successfully attached to shared memory, which is all we wanted */
+ if (ExecBackend && UsedShmemSegAddr != NULL)
+ break;
+
+ /* Check shared memory and possibly remove and recreate */
+
/*
- * If the creator PID is my own PID or does not belong to any
- * extant process, it's safe to zap it.
+ * If I am not the creator and it belongs to an extant process,
+ * continue.
*/
if (hdr->creatorPID != getpid())
{
- if (kill(hdr->creatorPID, 0) == 0 ||
- errno != ESRCH)
+ if (kill(hdr->creatorPID, 0) == 0 || errno != ESRCH)
{
shmdt(memAddress);
continue; /* segment belongs to a live process */
@@ -385,26 +401,31 @@ PGSharedMemoryCreate(uint32 size, bool makePrivate, int port)
*/
}
- /*
- * OK, we created a new segment. Mark it as created by this process.
- * The order of assignments here is critical so that another Postgres
- * process can't see the header as valid but belonging to an invalid
- * PID!
- */
hdr = (PGShmemHeader *) memAddress;
- hdr->creatorPID = getpid();
- hdr->magic = PGShmemMagic;
- /*
- * Initialize space allocation status for segment.
- */
- hdr->totalsize = size;
- hdr->freeoffset = MAXALIGN(sizeof(PGShmemHeader));
+ if (!ExecBackend || makePrivate || UsedShmemSegAddr == NULL)
+ {
+ /*
+ * OK, we created a new segment. Mark it as created by this process.
+ * The order of assignments here is critical so that another Postgres
+ * process can't see the header as valid but belonging to an invalid
+ * PID!
+ */
+ hdr->creatorPID = getpid();
+ hdr->magic = PGShmemMagic;
+
+ /*
+ * Initialize space allocation status for segment.
+ */
+ hdr->totalsize = size;
+ hdr->freeoffset = MAXALIGN(sizeof(PGShmemHeader));
+ }
-#ifdef EXEC_BACKEND
- if (!makePrivate && UsedShmemSegID == 0)
+ if (ExecBackend && !makePrivate && UsedShmemSegAddr == NULL)
+ {
+ UsedShmemSegAddr = memAddress;
UsedShmemSegID = NextShmemSegID;
-#endif
+ }
return hdr;
}
diff --git a/src/backend/postmaster/postmaster.c b/src/backend/postmaster/postmaster.c
index 23c948ce2b..211fc216f9 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.322 2003/05/06 23:34:55 momjian Exp $
+ * $Header: /cvsroot/pgsql/src/backend/postmaster/postmaster.c,v 1.323 2003/05/08 14:49:03 momjian Exp $
*
* NOTES
*
@@ -2439,9 +2439,10 @@ BackendFinalize(Port *port)
*/
av[ac++] = "-p";
#ifdef EXEC_BACKEND
- Assert(UsedShmemSegID != 0);
+ Assert(UsedShmemSegID != 0 && UsedShmemSegAddr != NULL);
/* database name at the end because it might contain commas */
- snprintf(pbuf, NAMEDATALEN + 256, "%d,%d,%s", port->sock, UsedShmemSegID, port->database_name);
+ snprintf(pbuf, NAMEDATALEN + 256, "%d,%d,%p,%s", port->sock,
+ UsedShmemSegID, UsedShmemSegAddr, port->database_name);
av[ac++] = pbuf;
#else
av[ac++] = port->database_name;
@@ -2776,9 +2777,10 @@ SSDataBase(int xlop)
av[ac++] = "-p";
#ifdef EXEC_BACKEND
- Assert(UsedShmemSegID != 0);
+ Assert(UsedShmemSegID != 0 && UsedShmemSegAddr != NULL);
/* database name at the end because it might contain commas */
- snprintf(pbuf, NAMEDATALEN + 256, "%d,%s", UsedShmemSegID, "template1");
+ snprintf(pbuf, NAMEDATALEN + 256, "%d,%p,%s", UsedShmemSegID,
+ UsedShmemSegAddr, "template1");
av[ac++] = pbuf;
#else
av[ac++] = "template1";
diff --git a/src/backend/tcop/postgres.c b/src/backend/tcop/postgres.c
index 78696cd077..8956455870 100644
--- a/src/backend/tcop/postgres.c
+++ b/src/backend/tcop/postgres.c
@@ -8,7 +8,7 @@
*
*
* IDENTIFICATION
- * $Header: /cvsroot/pgsql/src/backend/tcop/postgres.c,v 1.338 2003/05/06 23:34:55 momjian Exp $
+ * $Header: /cvsroot/pgsql/src/backend/tcop/postgres.c,v 1.339 2003/05/08 14:49:04 momjian Exp $
*
* NOTES
* this is the "main" module of the postgres backend and
@@ -2025,14 +2025,18 @@ PostgresMain(int argc, char *argv[], const char *username)
*/
if (secure)
{
- char *p;
#ifdef EXEC_BACKEND
- sscanf(optarg, "%d,%d,", &MyProcPort->sock, &UsedShmemSegID);
+ char *p;
+
+ sscanf(optarg, "%d,%d,%p,", &MyProcPort->sock,
+ &UsedShmemSegID, &UsedShmemSegAddr);
/* Grab dbname as last param */
p = strchr(optarg, ',');
if (p)
p = strchr(p+1, ',');
if (p)
+ p = strchr(p+1, ',');
+ if (p)
dbname = strdup(p+1);
#else
dbname = strdup(optarg);
@@ -2393,7 +2397,7 @@ PostgresMain(int argc, char *argv[], const char *username)
if (!IsUnderPostmaster)
{
puts("\nPOSTGRES backend interactive interface ");
- puts("$Revision: 1.338 $ $Date: 2003/05/06 23:34:55 $\n");
+ puts("$Revision: 1.339 $ $Date: 2003/05/08 14:49:04 $\n");
}
/*
diff --git a/src/include/storage/pg_shmem.h b/src/include/storage/pg_shmem.h
index 5f9df7602a..0c2b9cb299 100644
--- a/src/include/storage/pg_shmem.h
+++ b/src/include/storage/pg_shmem.h
@@ -17,7 +17,7 @@
* Portions Copyright (c) 1996-2002, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
- * $Id: pg_shmem.h,v 1.5 2003/05/06 23:34:56 momjian Exp $
+ * $Id: pg_shmem.h,v 1.6 2003/05/08 14:49:04 momjian Exp $
*
*-------------------------------------------------------------------------
*/
@@ -38,6 +38,7 @@ typedef struct PGShmemHeader /* standard header for all Postgres shmem */
#ifdef EXEC_BACKEND
extern IpcMemoryKey UsedShmemSegID;
+extern void *UsedShmemSegAddr;
#endif
extern PGShmemHeader *PGSharedMemoryCreate(uint32 size, bool makePrivate,