Index: doc/src/sgml/config.sgml
===================================================================
RCS file: /projects/cvsroot/pgsql/doc/src/sgml/config.sgml,v
retrieving revision 1.122
diff -c -r1.122 config.sgml
*** doc/src/sgml/config.sgml	20 Apr 2007 02:37:37 -0000	1.122
--- doc/src/sgml/config.sgml	3 May 2007 06:12:31 -0000
***************
*** 3479,3484 ****
--- 3479,3513 ----
        </listitem>
       </varlistentry>
  
+      <varlistentry id="guc-temp-tablespaces" xreflabel="temp_tablespaces">
+       <term><varname>temp_tablespaces</varname> (<type>string</type>)</term>
+       <indexterm>
+        <primary><varname>temp_tablespaces</> configuration parameter</primary>
+       </indexterm>
+       <indexterm><primary>tablespace</><secondary>temp</></>
+       <listitem>
+        <para>
+         This variable specifies tablespaces in which to create temp
+         objects (temp tables and indexes on temp tables) when a 
+ 		<command>CREATE</> command does not explicitly specify a tablespace 
+ 		and temp files when necessary (eg. for sorting operations).
+        </para>
+ 
+        <para>
+         The value is either a list of names of tablespaces, or an empty 
+ 		string to specify using the default tablespace of the current database.
+         If the value does not match the name of any existing tablespace,
+         <productname>PostgreSQL</> will automatically use the default
+         tablespace of the current database.
+        </para>
+ 
+        <para>
+         For more information on tablespaces,
+         see <xref linkend="manage-ag-tablespaces">.
+        </para>
+       </listitem>
+      </varlistentry>
+ 
       <varlistentry id="guc-check-function-bodies" xreflabel="check_function_bodies">
        <term><varname>check_function_bodies</varname> (<type>boolean</type>)</term>
        <indexterm>
Index: src/backend/commands/indexcmds.c
===================================================================
RCS file: /projects/cvsroot/pgsql/src/backend/commands/indexcmds.c,v
retrieving revision 1.158
diff -c -r1.158 indexcmds.c
*** src/backend/commands/indexcmds.c	2 May 2007 21:08:45 -0000	1.158
--- src/backend/commands/indexcmds.c	3 May 2007 06:12:34 -0000
***************
*** 208,214 ****
  	}
  	else
  	{
! 		tablespaceId = GetDefaultTablespace();
  		/* note InvalidOid is OK in this case */
  	}
  
--- 208,220 ----
  	}
  	else
  	{
!  		/*
!  		 * if the target table is temporary then use a temp_tablespace
!  		 */
!  		if (!rel->rd_istemp)
! 			tablespaceId = GetDefaultTablespace();
!  		else
!  			tablespaceId = GetTempTablespace();
  		/* note InvalidOid is OK in this case */
  	}
  
Index: src/backend/commands/tablecmds.c
===================================================================
RCS file: /projects/cvsroot/pgsql/src/backend/commands/tablecmds.c,v
retrieving revision 1.219
diff -c -r1.219 tablecmds.c
*** src/backend/commands/tablecmds.c	8 Apr 2007 01:26:32 -0000	1.219
--- src/backend/commands/tablecmds.c	3 May 2007 06:12:45 -0000
***************
*** 333,338 ****
--- 333,342 ----
  					 errmsg("tablespace \"%s\" does not exist",
  							stmt->tablespacename)));
  	}
+ 	else if (stmt->relation->istemp)
+ 	{
+ 		tablespaceId = GetTempTablespace();
+ 	}
  	else
  	{
  		tablespaceId = GetDefaultTablespace();
Index: src/backend/commands/tablespace.c
===================================================================
RCS file: /projects/cvsroot/pgsql/src/backend/commands/tablespace.c,v
retrieving revision 1.45
diff -c -r1.45 tablespace.c
*** src/backend/commands/tablespace.c	22 Mar 2007 19:51:44 -0000	1.45
--- src/backend/commands/tablespace.c	3 May 2007 06:12:47 -0000
***************
*** 65,73 ****
  #include "utils/lsyscache.h"
  
  
! /* GUC variable */
  char	   *default_tablespace = NULL;
  
  
  static bool remove_tablespace_directories(Oid tablespaceoid, bool redo);
  static void set_short_version(const char *path);
--- 65,76 ----
  #include "utils/lsyscache.h"
  
  
! /* GUC variables */
  char	   *default_tablespace = NULL;
+ char       *temp_tablespaces = NULL;
  
+ int	   next_temp_tablespace;
+ int	   num_temp_tablespaces;
  
  static bool remove_tablespace_directories(Oid tablespaceoid, bool redo);
  static void set_short_version(const char *path);
***************
*** 935,940 ****
--- 938,1079 ----
  	return result;
  }
  
+ /*
+  * Routines for handling the GUC variable 'temp_tablespaces'.
+  */
+ 
+ /* assign_hook: validate new temp_tablespaces, do extra actions as needed */
+ const char *
+ assign_temp_tablespaces(const char *newval, bool doit, GucSource source)
+ {
+ 	char	   *rawname;
+ 	List	   *namelist;
+ 	ListCell   *l;
+ 
+ 	/* Need a modifiable copy of string */
+ 	rawname = pstrdup(newval);
+ 
+ 	/* Parse string into list of identifiers */
+ 	if (!SplitIdentifierString(rawname, ',', &namelist))
+ 	{
+ 		/* syntax error in name list */
+ 		pfree(rawname);
+ 		list_free(namelist);
+ 		return NULL;
+ 	}
+ 
+ 	num_temp_tablespaces = 0;
+ 	foreach(l, namelist)
+ 	{
+ 		char	   *curname = (char *) lfirst(l);
+ 
+ 		/*
+ 		 * If we aren't inside a transaction, we cannot do database access so
+ 		 * cannot verify the individual names.	Must accept the list on faith.
+ 		 */
+ 		if (source >= PGC_S_INTERACTIVE && IsTransactionState())
+ 		{
+ 			/*
+ 			 * Verify that all the names are valid tablspace names 
+ 			 * We do not check for USAGE rights should we?
+ 			 */
+ 			if (get_tablespace_oid(curname) == InvalidOid)
+ 				ereport((source == PGC_S_TEST) ? NOTICE : ERROR,
+ 						(errcode(ERRCODE_UNDEFINED_OBJECT),
+ 						errmsg("tablespace \"%s\" does not exist", curname)));
+ 		}
+ 		num_temp_tablespaces++;
+ 	}
+ 
+ 	/*
+ 	 * Select the first tablespace to use
+ 	 */
+ 	next_temp_tablespace = MyProcPid % num_temp_tablespaces;
+ 
+ 	pfree(rawname);
+ 	list_free(namelist);
+ 	return newval;
+ }
+ 
+ /*
+  * GetTempTablespace -- get the OID of the tablespace for temporary objects
+  *
+  * May return InvalidOid to indicate "use the database's default tablespace"
+  *
+  * This exists to hide the temp_tablespace GUC variable.
+  */
+ Oid
+ GetTempTablespace(void)
+ {
+ 	Oid			result;
+ 	char *curname = NULL;
+ 	char *rawname;
+ 	List *namelist;
+ 	ListCell *l;
+ 	int i = 0;
+ 	
+ 	if ( temp_tablespaces == NULL )
+ 		return InvalidOid;
+ 
+ 	/* Need a modifiable version of temp_tablespaces */
+ 	rawname = pstrdup(temp_tablespaces);
+ 
+ 	/* Parse string into list of identifiers */
+ 	if (!SplitIdentifierString(rawname, ',', &namelist))
+ 	{
+ 		/* syntax error in name list */
+ 		pfree(rawname);
+ 		list_free(namelist);
+ 		return InvalidOid;
+ 	}
+ 
+ 	/* 
+ 	 * Iterate through the list of namespaces until the one we need 
+ 	 * (next_temp_tablespace) 
+ 	 */
+ 	foreach(l, namelist)
+ 	{
+ 		curname = (char *) lfirst(l);
+ 		if ( i == next_temp_tablespace )
+ 			break;
+ 		i++;
+ 	}
+ 
+ 
+ 	/* Prepare for the next time the function is called */
+ 	next_temp_tablespace++;
+ 	if (next_temp_tablespace == num_temp_tablespaces)
+ 		next_temp_tablespace = 0;
+ 
+ 	/* Fast path for temp_tablespaces == "" */
+ 	if ( curname == NULL || curname[0] == '\0') {
+ 		list_free(namelist);
+ 		pfree(rawname);
+ 		return InvalidOid;
+ 	}
+ 
+ 	/*
+ 	 * It is tempting to cache this lookup for more speed, but then we would
+ 	 * fail to detect the case where the tablespace was dropped since the GUC
+ 	 * variable was set.  Note also that we don't complain if the value fails
+ 	 * to refer to an existing tablespace; we just silently return InvalidOid,
+ 	 * causing the new object to be created in the database's tablespace.
+ 	 */
+ 	result = get_tablespace_oid(curname);
+ 
+ 	/* We don't free rawname before because curname points to a part of it */
+ 	pfree(rawname);
+ 
+ 	/*
+ 	 * Allow explicit specification of database's default tablespace in
+ 	 * default_tablespace without triggering permissions checks.
+ 	 */
+ 	if (result == MyDatabaseTableSpace)
+ 		result = InvalidOid;
+ 	
+ 	list_free(namelist);
+ 	return result;
+ }
  
  /*
   * get_tablespace_oid - given a tablespace name, look up the OID
Index: src/backend/executor/execMain.c
===================================================================
RCS file: /projects/cvsroot/pgsql/src/backend/executor/execMain.c,v
retrieving revision 1.293
diff -c -r1.293 execMain.c
*** src/backend/executor/execMain.c	27 Apr 2007 22:05:47 -0000	1.293
--- src/backend/executor/execMain.c	3 May 2007 06:12:51 -0000
***************
*** 2442,2447 ****
--- 2442,2451 ----
  					 errmsg("tablespace \"%s\" does not exist",
  							into->tableSpaceName)));
  	}
+ 	else if (into->rel->istemp)
+ 	{
+ 		tablespaceId = GetTempTablespace();
+ 	}
  	else
  	{
  		tablespaceId = GetDefaultTablespace();
Index: src/backend/executor/nodeHashjoin.c
===================================================================
RCS file: /projects/cvsroot/pgsql/src/backend/executor/nodeHashjoin.c,v
retrieving revision 1.89
diff -c -r1.89 nodeHashjoin.c
*** src/backend/executor/nodeHashjoin.c	2 Feb 2007 00:07:03 -0000	1.89
--- src/backend/executor/nodeHashjoin.c	3 May 2007 06:12:53 -0000
***************
*** 15,27 ****
  
  #include "postgres.h"
  
  #include "executor/executor.h"
  #include "executor/hashjoin.h"
  #include "executor/nodeHash.h"
  #include "executor/nodeHashjoin.h"
  #include "utils/memutils.h"
  
- 
  static TupleTableSlot *ExecHashJoinOuterGetTuple(PlanState *outerNode,
  						  HashJoinState *hjstate,
  						  uint32 *hashvalue);
--- 15,27 ----
  
  #include "postgres.h"
  
+ #include "commands/tablespace.h"
  #include "executor/executor.h"
  #include "executor/hashjoin.h"
  #include "executor/nodeHash.h"
  #include "executor/nodeHashjoin.h"
  #include "utils/memutils.h"
  
  static TupleTableSlot *ExecHashJoinOuterGetTuple(PlanState *outerNode,
  						  HashJoinState *hjstate,
  						  uint32 *hashvalue);
***************
*** 763,769 ****
  	if (file == NULL)
  	{
  		/* First write to this batch file, so open it. */
! 		file = BufFileCreateTemp(false);
  		*fileptr = file;
  	}
  
--- 763,769 ----
  	if (file == NULL)
  	{
  		/* First write to this batch file, so open it. */
! 		file = BufFileCreateTemp(false, GetTempTablespace());
  		*fileptr = file;
  	}
  
Index: src/backend/storage/file/buffile.c
===================================================================
RCS file: /projects/cvsroot/pgsql/src/backend/storage/file/buffile.c,v
retrieving revision 1.25
diff -c -r1.25 buffile.c
*** src/backend/storage/file/buffile.c	5 Jan 2007 22:19:37 -0000	1.25
--- src/backend/storage/file/buffile.c	3 May 2007 06:12:54 -0000
***************
*** 63,68 ****
--- 63,69 ----
  
  	bool		isTemp;			/* can only add files if this is TRUE */
  	bool		isInterXact;	/* keep open over transactions? */
+ 	Oid			tblspcOid;		/* Tablespace Oid or InvalidOid */
  	bool		dirty;			/* does buffer need to be written? */
  
  	/*
***************
*** 98,103 ****
--- 99,105 ----
  	file->offsets = (long *) palloc(sizeof(long));
  	file->offsets[0] = 0L;
  	file->isTemp = false;
+ 	file->tblspcOid = InvalidOid;
  	file->dirty = false;
  	file->curFile = 0;
  	file->curOffset = 0L;
***************
*** 116,122 ****
  	File		pfile;
  
  	Assert(file->isTemp);
! 	pfile = OpenTemporaryFile(file->isInterXact);
  	Assert(pfile >= 0);
  
  	file->files = (File *) repalloc(file->files,
--- 118,124 ----
  	File		pfile;
  
  	Assert(file->isTemp);
! 	pfile = OpenTemporaryFile(file->isInterXact, file->tblspcOid);
  	Assert(pfile >= 0);
  
  	file->files = (File *) repalloc(file->files,
***************
*** 137,153 ****
   * memory context that will survive across transaction boundaries.
   */
  BufFile *
! BufFileCreateTemp(bool interXact)
  {
  	BufFile    *file;
  	File		pfile;
  
! 	pfile = OpenTemporaryFile(interXact);
  	Assert(pfile >= 0);
  
  	file = makeBufFile(pfile);
  	file->isTemp = true;
  	file->isInterXact = interXact;
  
  	return file;
  }
--- 139,156 ----
   * memory context that will survive across transaction boundaries.
   */
  BufFile *
! BufFileCreateTemp(bool interXact, Oid tblspcOid)
  {
  	BufFile    *file;
  	File		pfile;
  
! 	pfile = OpenTemporaryFile(interXact, tblspcOid);
  	Assert(pfile >= 0);
  
  	file = makeBufFile(pfile);
  	file->isTemp = true;
  	file->isInterXact = interXact;
+ 	file->tblspcOid = tblspcOid;
  
  	return file;
  }
Index: src/backend/storage/file/fd.c
===================================================================
RCS file: /projects/cvsroot/pgsql/src/backend/storage/file/fd.c,v
retrieving revision 1.137
diff -c -r1.137 fd.c
*** src/backend/storage/file/fd.c	6 Mar 2007 02:06:14 -0000	1.137
--- src/backend/storage/file/fd.c	3 May 2007 06:12:57 -0000
***************
*** 76,81 ****
--- 76,82 ----
   */
  #define FD_MINFREE				10
  
+ #define OIDCHARS        10                      /* max chars printed by %u */
  
  /*
   * A number of platforms allow individual processes to open many more files
***************
*** 874,924 ****
   * that created them, so this should be false -- but if you need
   * "somewhat" temporary storage, this might be useful. In either case,
   * the file is removed when the File is explicitly closed.
   */
  File
! OpenTemporaryFile(bool interXact)
  {
  	char		tempfilepath[MAXPGPATH];
  	File		file;
  
  	/*
! 	 * Generate a tempfile name that should be unique within the current
! 	 * database instance.
  	 */
! 	snprintf(tempfilepath, sizeof(tempfilepath),
! 			 "%s/%s%d.%ld", PG_TEMP_FILES_DIR, PG_TEMP_FILE_PREFIX,
! 			 MyProcPid, tempFileCounter++);
  
! 	/*
! 	 * Open the file.  Note: we don't use O_EXCL, in case there is an orphaned
! 	 * temp file that can be reused.
! 	 */
! 	file = FileNameOpenFile(tempfilepath,
  							O_RDWR | O_CREAT | O_TRUNC | PG_BINARY,
  							0600);
! 	if (file <= 0)
! 	{
! 		char	   *dirpath;
  
  		/*
! 		 * We might need to create the pg_tempfiles subdirectory, if no one
! 		 * has yet done so.
! 		 *
! 		 * Don't check for error from mkdir; it could fail if someone else
! 		 * just did the same thing.  If it doesn't work then we'll bomb out on
! 		 * the second create attempt, instead.
  		 */
! 		dirpath = make_database_relative(PG_TEMP_FILES_DIR);
! 		mkdir(dirpath, S_IRWXU);
! 		pfree(dirpath);
  
  		file = FileNameOpenFile(tempfilepath,
  								O_RDWR | O_CREAT | O_TRUNC | PG_BINARY,
  								0600);
! 		if (file <= 0)
! 			elog(ERROR, "could not create temporary file \"%s\": %m",
! 				 tempfilepath);
! 	}
  
  	/* Mark it for deletion at close */
  	VfdCache[file].fdstate |= FD_TEMPORARY;
--- 875,965 ----
   * that created them, so this should be false -- but if you need
   * "somewhat" temporary storage, this might be useful. In either case,
   * the file is removed when the File is explicitly closed.
+  *
+  * tblspcOid: the oid of the tablespace where the temp file will be created.
+  * if InvalidOid we use the default tablespace
   */
  File
! OpenTemporaryFile(bool interXact, Oid tblspcOid)
  {
  	char		tempfilepath[MAXPGPATH];
  	File		file;
+ 	char		*path;
+ 	int		pathlen;
  
  	/*
! 	 * Take a look what should be the path of the temporary file
  	 */
! 	if (tblspcOid != InvalidOid)
! 	{
! 		/*
! 		 * As we got a valid tablespace, try to create the
! 		 * file there
! 		 */
  
! 		pathlen = 10 + OIDCHARS + 1;
! 		path = (char *) palloc(pathlen);
! 		snprintf(path, pathlen, "pg_tblspc/%u", tblspcOid );
! 
! 		/*
! 		 * Generate a tempfile name that should be unique within the current
! 		 * database instance.
! 		 */
! 		snprintf(tempfilepath, sizeof(tempfilepath),
! 				 "%s/%s%d.%ld", path, PG_TEMP_FILE_PREFIX,
! 				 MyProcPid, tempFileCounter++);
! 		pfree(path);
! 		file = PathNameOpenFile(tempfilepath,
  							O_RDWR | O_CREAT | O_TRUNC | PG_BINARY,
  							0600);
! 	}
  
+ 	/*
+ 	 * Create a normal temporary file if no tablespace returned or
+ 	 * couldn't create the file in the tablespace "tblspcOid"
+ 	 */
+ 	if (tblspcOid == InvalidOid || file <= 0) 
+ 	{
+ 		path = PG_TEMP_FILES_DIR;
  		/*
! 		 * Generate a tempfile name that should be unique within the current
! 		 * database instance.
  		 */
! 		snprintf(tempfilepath, sizeof(tempfilepath),
! 				 "%s/%s%d.%ld", path, PG_TEMP_FILE_PREFIX,
! 			 MyProcPid, tempFileCounter++);
  
+ 		/*
+ 		 * Open the file.  Note: we don't use O_EXCL, in case there is an 
+ 		 * orphaned temp file that can be reused.
+ 		 */
  		file = FileNameOpenFile(tempfilepath,
+ 							O_RDWR | O_CREAT | O_TRUNC | PG_BINARY,
+ 							0600);
+ 		if (file <= 0)
+ 		{
+ 			char	   *dirpath;
+ 
+ 			/*
+ 			 * We might need to create the pg_tempfiles subdirectory, if no one
+ 			 * has yet done so.
+ 			 *
+ 			 * Don't check for error from mkdir; it could fail if someone else
+ 			 * just did the same thing.  If it doesn't work then we'll bomb 
+ 			 * out on the second create attempt, instead.
+ 			 */
+ 			dirpath = make_database_relative(PG_TEMP_FILES_DIR);
+ 			mkdir(dirpath, S_IRWXU);
+ 			pfree(dirpath);
+ 
+ 			file = FileNameOpenFile(tempfilepath,
  								O_RDWR | O_CREAT | O_TRUNC | PG_BINARY,
  								0600);
! 			if (file <= 0)
! 				elog(ERROR, "could not create temporary file \"%s\": %m",
! 					 tempfilepath);
! 		}
!  	}
  
  	/* Mark it for deletion at close */
  	VfdCache[file].fdstate |= FD_TEMPORARY;
***************
*** 1292,1297 ****
--- 1333,1352 ----
  		errno = save_errno;
  	}
  
+ 	/*
+ 	 * TEMPORARY hack to log the Windows error code on fopen failures, in
+ 	 * hopes of diagnosing some hard-to-reproduce problems.
+ 	 */
+ #ifdef WIN32
+ 	{
+ 		int			save_errno = errno;
+ 
+ 		elog(LOG, "Windows fopen(\"%s\",\"%s\") failed: code %lu, errno %d",
+ 			 name, mode, GetLastError(), save_errno);
+ 		errno = save_errno;
+ 	}
+ #endif
+ 
  	return NULL;
  }
  
Index: src/backend/utils/misc/guc.c
===================================================================
RCS file: /projects/cvsroot/pgsql/src/backend/utils/misc/guc.c,v
retrieving revision 1.389
diff -c -r1.389 guc.c
*** src/backend/utils/misc/guc.c	26 Apr 2007 16:13:12 -0000	1.389
--- src/backend/utils/misc/guc.c	3 May 2007 06:13:08 -0000
***************
*** 103,108 ****
--- 103,109 ----
  extern int	CommitDelay;
  extern int	CommitSiblings;
  extern char *default_tablespace;
+ extern char *temp_tablespaces;
  extern bool fullPageWrites;
  
  #ifdef TRACE_SORT
***************
*** 2370,2375 ****
--- 2371,2386 ----
  	},
  #endif /* USE_SSL */
  
+ 	{
+ 		{"temp_tablespaces", PGC_USERSET, PGC_S_FILE,
+ 			gettext_noop("Sets the tablespaces suitable for creating new objects and sort files."),
+ 			NULL,
+ 			GUC_LIST_INPUT | GUC_LIST_QUOTE 
+ 		},
+ 		&temp_tablespaces,
+ 		NULL, assign_temp_tablespaces, NULL
+ 	},
+ 
  	/* End-of-list marker */
  	{
  		{NULL, 0, 0, NULL, NULL}, NULL, NULL, NULL, NULL
Index: src/backend/utils/misc/postgresql.conf.sample
===================================================================
RCS file: /projects/cvsroot/pgsql/src/backend/utils/misc/postgresql.conf.sample,v
retrieving revision 1.215
diff -c -r1.215 postgresql.conf.sample
*** src/backend/utils/misc/postgresql.conf.sample	18 Apr 2007 16:44:18 -0000	1.215
--- src/backend/utils/misc/postgresql.conf.sample	3 May 2007 06:13:08 -0000
***************
*** 408,413 ****
--- 408,415 ----
  #search_path = '"$user",public'		# schema names
  #default_tablespace = ''		# a tablespace name, '' uses
  					# the default
+ #temp_tablespaces = ''		# a list of tablespace names, 
+ 							# '' uses default_tablespace
  #check_function_bodies = on
  #default_transaction_isolation = 'read committed'
  #default_transaction_read_only = off
Index: src/backend/utils/sort/logtape.c
===================================================================
RCS file: /projects/cvsroot/pgsql/src/backend/utils/sort/logtape.c,v
retrieving revision 1.23
diff -c -r1.23 logtape.c
*** src/backend/utils/sort/logtape.c	5 Jan 2007 22:19:47 -0000	1.23
--- src/backend/utils/sort/logtape.c	3 May 2007 06:13:10 -0000
***************
*** 77,82 ****
--- 77,83 ----
  
  #include "postgres.h"
  
+ #include "commands/tablespace.h"
  #include "storage/buffile.h"
  #include "utils/logtape.h"
  
***************
*** 528,534 ****
  	Assert(ntapes > 0);
  	lts = (LogicalTapeSet *) palloc(sizeof(LogicalTapeSet) +
  									(ntapes - 1) *sizeof(LogicalTape));
! 	lts->pfile = BufFileCreateTemp(false);
  	lts->nFileBlocks = 0L;
  	lts->forgetFreeSpace = false;
  	lts->blocksSorted = true;	/* a zero-length array is sorted ... */
--- 529,535 ----
  	Assert(ntapes > 0);
  	lts = (LogicalTapeSet *) palloc(sizeof(LogicalTapeSet) +
  									(ntapes - 1) *sizeof(LogicalTape));
! 	lts->pfile = BufFileCreateTemp(false, GetTempTablespace());
  	lts->nFileBlocks = 0L;
  	lts->forgetFreeSpace = false;
  	lts->blocksSorted = true;	/* a zero-length array is sorted ... */
Index: src/backend/utils/sort/tuplestore.c
===================================================================
RCS file: /projects/cvsroot/pgsql/src/backend/utils/sort/tuplestore.c,v
retrieving revision 1.30
diff -c -r1.30 tuplestore.c
*** src/backend/utils/sort/tuplestore.c	5 Jan 2007 22:19:47 -0000	1.30
--- src/backend/utils/sort/tuplestore.c	3 May 2007 06:13:16 -0000
***************
*** 44,49 ****
--- 44,50 ----
  #include "postgres.h"
  
  #include "access/heapam.h"
+ #include "commands/tablespace.h"
  #include "storage/buffile.h"
  #include "utils/memutils.h"
  #include "utils/tuplestore.h"
***************
*** 388,394 ****
  			/*
  			 * Nope; time to switch to tape-based operation.
  			 */
! 			state->myfile = BufFileCreateTemp(state->interXact);
  			state->status = TSS_WRITEFILE;
  			dumptuples(state);
  			break;
--- 389,396 ----
  			/*
  			 * Nope; time to switch to tape-based operation.
  			 */
! 			state->myfile = BufFileCreateTemp(state->interXact, 
! 											  GetTempTablespace());
  			state->status = TSS_WRITEFILE;
  			dumptuples(state);
  			break;
Index: src/include/commands/tablespace.h
===================================================================
RCS file: /projects/cvsroot/pgsql/src/include/commands/tablespace.h,v
retrieving revision 1.16
diff -c -r1.16 tablespace.h
*** src/include/commands/tablespace.h	6 Mar 2007 02:06:15 -0000	1.16
--- src/include/commands/tablespace.h	3 May 2007 06:13:18 -0000
***************
*** 41,46 ****
--- 41,47 ----
  extern void TablespaceCreateDbspace(Oid spcNode, Oid dbNode, bool isRedo);
  
  extern Oid	GetDefaultTablespace(void);
+ extern Oid	GetTempTablespace(void);
  
  extern Oid	get_tablespace_oid(const char *tablespacename);
  extern char *get_tablespace_name(Oid spc_oid);
Index: src/include/storage/buffile.h
===================================================================
RCS file: /projects/cvsroot/pgsql/src/include/storage/buffile.h,v
retrieving revision 1.20
diff -c -r1.20 buffile.h
*** src/include/storage/buffile.h	5 Jan 2007 22:19:57 -0000	1.20
--- src/include/storage/buffile.h	3 May 2007 06:13:18 -0000
***************
*** 34,40 ****
   * prototypes for functions in buffile.c
   */
  
! extern BufFile *BufFileCreateTemp(bool interXact);
  extern void BufFileClose(BufFile *file);
  extern size_t BufFileRead(BufFile *file, void *ptr, size_t size);
  extern size_t BufFileWrite(BufFile *file, void *ptr, size_t size);
--- 34,40 ----
   * prototypes for functions in buffile.c
   */
  
! extern BufFile *BufFileCreateTemp(bool interXact, Oid tblspcOid);
  extern void BufFileClose(BufFile *file);
  extern size_t BufFileRead(BufFile *file, void *ptr, size_t size);
  extern size_t BufFileWrite(BufFile *file, void *ptr, size_t size);
Index: src/include/storage/fd.h
===================================================================
RCS file: /projects/cvsroot/pgsql/src/include/storage/fd.h,v
retrieving revision 1.57
diff -c -r1.57 fd.h
*** src/include/storage/fd.h	5 Jan 2007 22:19:57 -0000	1.57
--- src/include/storage/fd.h	3 May 2007 06:13:18 -0000
***************
*** 61,67 ****
  /* Operations on virtual Files --- equivalent to Unix kernel file ops */
  extern File FileNameOpenFile(FileName fileName, int fileFlags, int fileMode);
  extern File PathNameOpenFile(FileName fileName, int fileFlags, int fileMode);
! extern File OpenTemporaryFile(bool interXact);
  extern void FileClose(File file);
  extern void FileUnlink(File file);
  extern int	FileRead(File file, char *buffer, int amount);
--- 61,67 ----
  /* Operations on virtual Files --- equivalent to Unix kernel file ops */
  extern File FileNameOpenFile(FileName fileName, int fileFlags, int fileMode);
  extern File PathNameOpenFile(FileName fileName, int fileFlags, int fileMode);
! extern File OpenTemporaryFile(bool interXact, Oid tblspcOid);
  extern void FileClose(File file);
  extern void FileUnlink(File file);
  extern int	FileRead(File file, char *buffer, int amount);
Index: src/include/utils/guc.h
===================================================================
RCS file: /projects/cvsroot/pgsql/src/include/utils/guc.h,v
retrieving revision 1.81
diff -c -r1.81 guc.h
*** src/include/utils/guc.h	12 Apr 2007 06:53:48 -0000	1.81
--- src/include/utils/guc.h	3 May 2007 06:13:19 -0000
***************
*** 238,241 ****
--- 238,245 ----
  extern const char *assign_xlog_sync_method(const char *method,
  						bool doit, GucSource source);
  
+ /* in commands/tablespace.c */
+ extern const char *assign_temp_tablespaces(const char *newval,
+ 						  bool doit, GucSource source);
+ 
  #endif   /* GUC_H */
