mirror of
https://github.com/postgres/postgres.git
synced 2025-08-27 07:42:10 +03:00
Make use of plancache module for SPI plans. In particular, since plpgsql
uses SPI plans, this finally fixes the ancient gotcha that you can't drop and recreate a temp table used by a plpgsql function. Along the way, clean up SPI's API a little bit by declaring SPI plan pointers as "SPIPlanPtr" instead of "void *". This is cosmetic but helps to forestall simple programming mistakes. (I have changed some but not all of the callers to match; there are still some "void *"'s in contrib and the PL's. This is intentional so that we can see if anyone's compiler complains about it.)
This commit is contained in:
@@ -6,7 +6,7 @@
|
||||
* Portions Copyright (c) 1996-2007, PostgreSQL Global Development Group
|
||||
* Portions Copyright (c) 1994, Regents of the University of California
|
||||
*
|
||||
* $PostgreSQL: pgsql/src/include/executor/spi_priv.h,v 1.27 2007/02/20 17:32:17 tgl Exp $
|
||||
* $PostgreSQL: pgsql/src/include/executor/spi_priv.h,v 1.28 2007/03/15 23:12:07 tgl Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@@ -16,6 +16,8 @@
|
||||
#include "executor/spi.h"
|
||||
|
||||
|
||||
#define _SPI_PLAN_MAGIC 569278163
|
||||
|
||||
typedef struct
|
||||
{
|
||||
/* current results */
|
||||
@@ -25,29 +27,46 @@ typedef struct
|
||||
|
||||
MemoryContext procCxt; /* procedure context */
|
||||
MemoryContext execCxt; /* executor context */
|
||||
MemoryContext savedcxt;
|
||||
MemoryContext savedcxt; /* context of SPI_connect's caller */
|
||||
SubTransactionId connectSubid; /* ID of connecting subtransaction */
|
||||
} _SPI_connection;
|
||||
|
||||
typedef struct
|
||||
/*
|
||||
* SPI plans have two states: saved or unsaved.
|
||||
*
|
||||
* For an unsaved plan, the _SPI_plan struct and all its subsidiary data are in
|
||||
* a dedicated memory context identified by plancxt. An unsaved plan is good
|
||||
* at most for the current transaction, since the locks that protect it from
|
||||
* schema changes will be lost at end of transaction. Hence the plancxt is
|
||||
* always a transient one.
|
||||
*
|
||||
* For a saved plan, the _SPI_plan struct and the argument type array are in
|
||||
* the plancxt (which can be really small). All the other subsidiary state
|
||||
* is in plancache entries identified by plancache_list (note: the list cells
|
||||
* themselves are in plancxt). We rely on plancache.c to keep the cache
|
||||
* entries up-to-date as needed. The plancxt is a child of CacheMemoryContext
|
||||
* since it should persist until explicitly destroyed.
|
||||
*
|
||||
* To avoid redundant coding, the representation of unsaved plans matches
|
||||
* that of saved plans, ie, plancache_list is a list of CachedPlanSource
|
||||
* structs which in turn point to CachedPlan structs. However, in an unsaved
|
||||
* plan all these structs are just created by spi.c and are not known to
|
||||
* plancache.c. We don't try very hard to make all their fields valid,
|
||||
* only the ones spi.c actually uses.
|
||||
*
|
||||
* Note: if the original query string contained only whitespace and comments,
|
||||
* the plancache_list will be NIL and so there is no place to store the
|
||||
* query string. We don't care about that, but we do care about the
|
||||
* argument type array, which is why it's seemingly-redundantly stored.
|
||||
*/
|
||||
typedef struct _SPI_plan
|
||||
{
|
||||
/* Context containing _SPI_plan itself as well as subsidiary data */
|
||||
MemoryContext plancxt;
|
||||
/* Original query string (used for error reporting) */
|
||||
const char *query;
|
||||
/*
|
||||
* List of List of PlannedStmts and utility stmts; one sublist per
|
||||
* original parsetree
|
||||
*/
|
||||
List *stmt_list_list;
|
||||
/* Argument types, if a prepared plan */
|
||||
int nargs;
|
||||
Oid *argtypes;
|
||||
int magic; /* should equal _SPI_PLAN_MAGIC */
|
||||
bool saved; /* saved or unsaved plan? */
|
||||
List *plancache_list; /* one CachedPlanSource per parsetree */
|
||||
MemoryContext plancxt; /* Context containing _SPI_plan and data */
|
||||
int nargs; /* number of plan arguments */
|
||||
Oid *argtypes; /* Argument types (NULL if nargs is 0) */
|
||||
} _SPI_plan;
|
||||
|
||||
|
||||
#define _SPI_CPLAN_CURCXT 0
|
||||
#define _SPI_CPLAN_PROCXT 1
|
||||
#define _SPI_CPLAN_TOPCXT 2
|
||||
|
||||
#endif /* SPI_PRIV_H */
|
||||
|
Reference in New Issue
Block a user