66 * Portions Copyright (c) 1996-2009, PostgreSQL Global Development Group 
77 * 
88 * IDENTIFICATION 
9-  *	  $PostgreSQL: pgsql/src/backend/port/win32_shmem.c,v 1.8  2009/05/04 08:36:40  mha Exp $ 
9+  *	  $PostgreSQL: pgsql/src/backend/port/win32_shmem.c,v 1.9  2009/05/05 09:48:51  mha Exp $ 
1010 * 
1111 *------------------------------------------------------------------------- 
1212 */ 
@@ -123,6 +123,7 @@ PGSharedMemoryCreate(Size size, bool makePrivate, int port)
123123	HANDLE 		hmap ,
124124				hmap2 ;
125125	char 	   * szShareMem ;
126+ 	int 			i ;
126127
127128	/* Room for a header? */ 
128129	Assert (size  >  MAXALIGN (sizeof (PGShmemHeader )));
@@ -131,54 +132,53 @@ PGSharedMemoryCreate(Size size, bool makePrivate, int port)
131132
132133	UsedShmemSegAddr  =  NULL ;
133134
134- 	/* In case CreateFileMapping() doesn't set the error code to 0 on success */ 
135- 	SetLastError (0 );
136- 
137- 	hmap  =  CreateFileMapping ((HANDLE ) 0xFFFFFFFF ,		/* Use the pagefile */ 
138- 							 NULL ,		/* Default security attrs */ 
139- 							 PAGE_READWRITE ,	/* Memory is Read/Write */ 
140- 							 0L ,	/* Size Upper 32 Bits	*/ 
141- 							 (DWORD ) size ,		/* Size Lower 32 bits */ 
142- 							 szShareMem );
143- 
144- 	if  (!hmap )
145- 		ereport (FATAL ,
146- 				(errmsg ("could not create shared memory segment: %lu" , GetLastError ()),
147- 				 errdetail ("Failed system call was CreateFileMapping(size=%lu, name=%s)." ,
148- 						   (unsigned long ) size , szShareMem )));
149- 
150135	/* 
151- 	 * If the segment already existed, CreateFileMapping() will return a 
152- 	 * handle to the existing one. 
136+ 	 * When recycling a shared memory segment, it may take a short while 
137+ 	 * before it gets dropped from the global namespace. So re-try after 
138+ 	 * sleeping for a second, and continue retrying 10 times. 
139+ 	 * (both the 1 second time and the 10 retries are completely arbitrary) 
153140	 */ 
154- 	if  ( GetLastError ()  ==   ERROR_ALREADY_EXISTS )
141+ 	for  ( i   =   0 ;  i   <   10 ;  i ++ )
155142	{
156- 		/* 
157- 		 * When recycling a shared memory segment, it may take a short while 
158- 		 * before it gets dropped from the global namespace. So re-try after 
159- 		 * sleeping for a second. 
160- 		 */ 
161- 		CloseHandle (hmap );		/* Close the old handle, since we got a valid 
162- 								 * one to the previous segment. */ 
163- 
164- 		Sleep (1000 );
165- 
166143		/* In case CreateFileMapping() doesn't set the error code to 0 on success */ 
167144		SetLastError (0 );
168145
169- 		hmap  =  CreateFileMapping ((HANDLE ) 0xFFFFFFFF , NULL , PAGE_READWRITE , 0L , (DWORD ) size , szShareMem );
146+ 		hmap  =  CreateFileMapping ((HANDLE ) 0xFFFFFFFF ,		/* Use the pagefile */ 
147+ 								 NULL ,		/* Default security attrs */ 
148+ 								 PAGE_READWRITE ,	/* Memory is Read/Write */ 
149+ 								 0L ,	/* Size Upper 32 Bits	*/ 
150+ 								 (DWORD ) size ,		/* Size Lower 32 bits */ 
151+ 								 szShareMem );
152+ 
170153		if  (!hmap )
171154			ereport (FATAL ,
172155					(errmsg ("could not create shared memory segment: %lu" , GetLastError ()),
173156					 errdetail ("Failed system call was CreateFileMapping(size=%lu, name=%s)." ,
174157							   (unsigned long ) size , szShareMem )));
175158
159+ 		/* 
160+ 		 * If the segment already existed, CreateFileMapping() will return a 
161+ 		 * handle to the existing one. 
162+ 		 */ 
176163		if  (GetLastError () ==  ERROR_ALREADY_EXISTS )
177- 			ereport (FATAL ,
178- 				 (errmsg ("pre-existing shared memory block is still in use" ),
179- 				  errhint ("Check if there are any old server processes still running, and terminate them." )));
164+ 		{
165+ 			CloseHandle (hmap );		/* Close the old handle, since we got a valid 
166+ 									 * one to the previous segment. */ 
167+ 			Sleep (1000 );
168+ 			continue ;
169+ 		}
170+ 		break ;
180171	}
181172
173+ 	/* 
174+ 	 * If the last call in the loop still returned ERROR_ALREADY_EXISTS, this shared memory 
175+ 	 * segment exists and we assume it belongs to somebody else. 
176+ 	 */ 
177+ 	if  (GetLastError () ==  ERROR_ALREADY_EXISTS )
178+ 		ereport (FATAL ,
179+ 			 (errmsg ("pre-existing shared memory block is still in use" ),
180+ 			  errhint ("Check if there are any old server processes still running, and terminate them." )));
181+ 
182182	free (szShareMem );
183183
184184	/* 
0 commit comments