Header And Logo

PostgreSQL
| The world's most advanced open source database.

plancache.h

Go to the documentation of this file.
00001 /*-------------------------------------------------------------------------
00002  *
00003  * plancache.h
00004  *    Plan cache definitions.
00005  *
00006  * See plancache.c for comments.
00007  *
00008  * Portions Copyright (c) 1996-2013, PostgreSQL Global Development Group
00009  * Portions Copyright (c) 1994, Regents of the University of California
00010  *
00011  * src/include/utils/plancache.h
00012  *
00013  *-------------------------------------------------------------------------
00014  */
00015 #ifndef PLANCACHE_H
00016 #define PLANCACHE_H
00017 
00018 #include "access/tupdesc.h"
00019 #include "nodes/params.h"
00020 
00021 #define CACHEDPLANSOURCE_MAGIC      195726186
00022 #define CACHEDPLAN_MAGIC            953717834
00023 
00024 /*
00025  * CachedPlanSource (which might better have been called CachedQuery)
00026  * represents a SQL query that we expect to use multiple times.  It stores
00027  * the query source text, the raw parse tree, and the analyzed-and-rewritten
00028  * query tree, as well as adjunct data.  Cache invalidation can happen as a
00029  * result of DDL affecting objects used by the query.  In that case we discard
00030  * the analyzed-and-rewritten query tree, and rebuild it when next needed.
00031  *
00032  * An actual execution plan, represented by CachedPlan, is derived from the
00033  * CachedPlanSource when we need to execute the query.  The plan could be
00034  * either generic (usable with any set of plan parameters) or custom (for a
00035  * specific set of parameters).  plancache.c contains the logic that decides
00036  * which way to do it for any particular execution.  If we are using a generic
00037  * cached plan then it is meant to be re-used across multiple executions, so
00038  * callers must always treat CachedPlans as read-only.
00039  *
00040  * Once successfully built and "saved", CachedPlanSources typically live
00041  * for the life of the backend, although they can be dropped explicitly.
00042  * CachedPlans are reference-counted and go away automatically when the last
00043  * reference is dropped.  A CachedPlan can outlive the CachedPlanSource it
00044  * was created from.
00045  *
00046  * An "unsaved" CachedPlanSource can be used for generating plans, but it
00047  * lives in transient storage and will not be updated in response to sinval
00048  * events.
00049  *
00050  * CachedPlans made from saved CachedPlanSources are likewise in permanent
00051  * storage, so to avoid memory leaks, the reference-counted references to them
00052  * must be held in permanent data structures or ResourceOwners.  CachedPlans
00053  * made from unsaved CachedPlanSources are in children of the caller's
00054  * memory context, so references to them should not be longer-lived than
00055  * that context.  (Reference counting is somewhat pro forma in that case,
00056  * though it may be useful if the CachedPlan can be discarded early.)
00057  *
00058  * A CachedPlanSource has two associated memory contexts: one that holds the
00059  * struct itself, the query source text and the raw parse tree, and another
00060  * context that holds the rewritten query tree and associated data.  This
00061  * allows the query tree to be discarded easily when it is invalidated.
00062  *
00063  * Some callers wish to use the CachedPlan API even with one-shot queries
00064  * that have no reason to be saved at all.  We therefore support a "oneshot"
00065  * variant that does no data copying or invalidation checking.  In this case
00066  * there are no separate memory contexts: the CachedPlanSource struct and
00067  * all subsidiary data live in the caller's CurrentMemoryContext, and there
00068  * is no way to free memory short of clearing that entire context.  A oneshot
00069  * plan is always treated as unsaved.
00070  *
00071  * Note: the string referenced by commandTag is not subsidiary storage;
00072  * it is assumed to be a compile-time-constant string.  As with portals,
00073  * commandTag shall be NULL if and only if the original query string (before
00074  * rewriting) was an empty string.
00075  */
00076 typedef struct CachedPlanSource
00077 {
00078     int         magic;          /* should equal CACHEDPLANSOURCE_MAGIC */
00079     Node       *raw_parse_tree; /* output of raw_parser() */
00080     const char *query_string;   /* source text of query */
00081     const char *commandTag;     /* command tag (a constant!), or NULL */
00082     Oid        *param_types;    /* array of parameter type OIDs, or NULL */
00083     int         num_params;     /* length of param_types array */
00084     ParserSetupHook parserSetup;    /* alternative parameter spec method */
00085     void       *parserSetupArg;
00086     int         cursor_options; /* cursor options used for planning */
00087     bool        fixed_result;   /* disallow change in result tupdesc? */
00088     TupleDesc   resultDesc;     /* result type; NULL = doesn't return tuples */
00089     MemoryContext context;      /* memory context holding all above */
00090     /* These fields describe the current analyzed-and-rewritten query tree: */
00091     List       *query_list;     /* list of Query nodes, or NIL if not valid */
00092     List       *relationOids;   /* OIDs of relations the queries depend on */
00093     List       *invalItems;     /* other dependencies, as PlanInvalItems */
00094     struct OverrideSearchPath *search_path;     /* search_path used for
00095                                                  * parsing and planning */
00096     MemoryContext query_context;    /* context holding the above, or NULL */
00097     /* If we have a generic plan, this is a reference-counted link to it: */
00098     struct CachedPlan *gplan;   /* generic plan, or NULL if not valid */
00099     /* Some state flags: */
00100     bool        is_oneshot;     /* is it a "oneshot" plan? */
00101     bool        is_complete;    /* has CompleteCachedPlan been done? */
00102     bool        is_saved;       /* has CachedPlanSource been "saved"? */
00103     bool        is_valid;       /* is the query_list currently valid? */
00104     int         generation;     /* increments each time we create a plan */
00105     /* If CachedPlanSource has been saved, it is a member of a global list */
00106     struct CachedPlanSource *next_saved;        /* list link, if so */
00107     /* State kept to help decide whether to use custom or generic plans: */
00108     double      generic_cost;   /* cost of generic plan, or -1 if not known */
00109     double      total_custom_cost;      /* total cost of custom plans so far */
00110     int         num_custom_plans;       /* number of plans included in total */
00111 } CachedPlanSource;
00112 
00113 /*
00114  * CachedPlan represents an execution plan derived from a CachedPlanSource.
00115  * The reference count includes both the link from the parent CachedPlanSource
00116  * (if any), and any active plan executions, so the plan can be discarded
00117  * exactly when refcount goes to zero.  Both the struct itself and the
00118  * subsidiary data live in the context denoted by the context field.
00119  * This makes it easy to free a no-longer-needed cached plan.  (However,
00120  * if is_oneshot is true, the context does not belong solely to the CachedPlan
00121  * so no freeing is possible.)
00122  */
00123 typedef struct CachedPlan
00124 {
00125     int         magic;          /* should equal CACHEDPLAN_MAGIC */
00126     List       *stmt_list;      /* list of statement nodes (PlannedStmts and
00127                                  * bare utility statements) */
00128     bool        is_oneshot;     /* is it a "oneshot" plan? */
00129     bool        is_saved;       /* is CachedPlan in a long-lived context? */
00130     bool        is_valid;       /* is the stmt_list currently valid? */
00131     TransactionId saved_xmin;   /* if valid, replan when TransactionXmin
00132                                  * changes from this value */
00133     int         generation;     /* parent's generation number for this plan */
00134     int         refcount;       /* count of live references to this struct */
00135     MemoryContext context;      /* context containing this CachedPlan */
00136 } CachedPlan;
00137 
00138 
00139 extern void InitPlanCache(void);
00140 extern void ResetPlanCache(void);
00141 
00142 extern CachedPlanSource *CreateCachedPlan(Node *raw_parse_tree,
00143                  const char *query_string,
00144                  const char *commandTag);
00145 extern CachedPlanSource *CreateOneShotCachedPlan(Node *raw_parse_tree,
00146                  const char *query_string,
00147                  const char *commandTag);
00148 extern void CompleteCachedPlan(CachedPlanSource *plansource,
00149                    List *querytree_list,
00150                    MemoryContext querytree_context,
00151                    Oid *param_types,
00152                    int num_params,
00153                    ParserSetupHook parserSetup,
00154                    void *parserSetupArg,
00155                    int cursor_options,
00156                    bool fixed_result);
00157 
00158 extern void SaveCachedPlan(CachedPlanSource *plansource);
00159 extern void DropCachedPlan(CachedPlanSource *plansource);
00160 
00161 extern void CachedPlanSetParentContext(CachedPlanSource *plansource,
00162                            MemoryContext newcontext);
00163 
00164 extern CachedPlanSource *CopyCachedPlan(CachedPlanSource *plansource);
00165 
00166 extern bool CachedPlanIsValid(CachedPlanSource *plansource);
00167 
00168 extern List *CachedPlanGetTargetList(CachedPlanSource *plansource);
00169 
00170 extern CachedPlan *GetCachedPlan(CachedPlanSource *plansource,
00171               ParamListInfo boundParams,
00172               bool useResOwner);
00173 extern void ReleaseCachedPlan(CachedPlan *plan, bool useResOwner);
00174 
00175 #endif   /* PLANCACHE_H */