aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/backend/commands/copy.c4
-rw-r--r--src/backend/commands/explain.c12
-rw-r--r--src/backend/commands/portalcmds.c4
-rw-r--r--src/backend/commands/prepare.c4
-rw-r--r--src/backend/executor/functions.c4
-rw-r--r--src/backend/executor/spi.c63
-rw-r--r--src/backend/optimizer/plan/planner.c9
-rw-r--r--src/backend/parser/gram.y17
-rw-r--r--src/backend/tcop/postgres.c21
-rw-r--r--src/backend/utils/cache/plancache.c9
-rw-r--r--src/include/executor/spi.h11
-rw-r--r--src/include/nodes/parsenodes.h13
-rw-r--r--src/include/optimizer/planner.h4
-rw-r--r--src/include/tcop/tcopprot.h9
14 files changed, 117 insertions, 67 deletions
diff --git a/src/backend/commands/copy.c b/src/backend/commands/copy.c
index 99d347f5907..42121f3fe45 100644
--- a/src/backend/commands/copy.c
+++ b/src/backend/commands/copy.c
@@ -8,7 +8,7 @@
*
*
* IDENTIFICATION
- * $PostgreSQL: pgsql/src/backend/commands/copy.c,v 1.279 2007/03/29 00:15:38 tgl Exp $
+ * $PostgreSQL: pgsql/src/backend/commands/copy.c,v 1.280 2007/04/16 01:14:55 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@@ -1023,7 +1023,7 @@ DoCopy(const CopyStmt *stmt, const char *queryString)
errmsg("COPY (SELECT INTO) is not supported")));
/* plan the query */
- plan = planner(query, false, 0, NULL);
+ plan = planner(query, 0, NULL);
/*
* Update snapshot command ID to ensure this query sees results of any
diff --git a/src/backend/commands/explain.c b/src/backend/commands/explain.c
index 1b2cfccce9f..bb7d4303598 100644
--- a/src/backend/commands/explain.c
+++ b/src/backend/commands/explain.c
@@ -7,7 +7,7 @@
* Portions Copyright (c) 1994-5, Regents of the University of California
*
* IDENTIFICATION
- * $PostgreSQL: pgsql/src/backend/commands/explain.c,v 1.160 2007/03/13 00:33:39 tgl Exp $
+ * $PostgreSQL: pgsql/src/backend/commands/explain.c,v 1.161 2007/04/16 01:14:55 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@@ -42,7 +42,7 @@ typedef struct ExplainState
List *rtable; /* range table */
} ExplainState;
-static void ExplainOneQuery(Query *query, bool isCursor, int cursorOptions,
+static void ExplainOneQuery(Query *query, int cursorOptions,
ExplainStmt *stmt, const char *queryString,
ParamListInfo params, TupOutputState *tstate);
static double elapsed_time(instr_time *starttime);
@@ -102,7 +102,7 @@ ExplainQuery(ExplainStmt *stmt, const char *queryString,
/* Explain every plan */
foreach(l, rewritten)
{
- ExplainOneQuery((Query *) lfirst(l), false, 0,
+ ExplainOneQuery((Query *) lfirst(l), 0,
stmt, queryString, params, tstate);
/* put a blank line between plans */
if (lnext(l) != NULL)
@@ -134,7 +134,7 @@ ExplainResultDesc(ExplainStmt *stmt)
* print out the execution plan for one Query
*/
static void
-ExplainOneQuery(Query *query, bool isCursor, int cursorOptions,
+ExplainOneQuery(Query *query, int cursorOptions,
ExplainStmt *stmt, const char *queryString,
ParamListInfo params, TupOutputState *tstate)
{
@@ -150,7 +150,7 @@ ExplainOneQuery(Query *query, bool isCursor, int cursorOptions,
}
/* plan the query */
- plan = planner(query, isCursor, cursorOptions, params);
+ plan = planner(query, cursorOptions, params);
/*
* Update snapshot command ID to ensure this query sees results of any
@@ -229,7 +229,7 @@ ExplainOneUtility(Node *utilityStmt, ExplainStmt *stmt,
/* do not actually execute the underlying query! */
memcpy(&newstmt, stmt, sizeof(ExplainStmt));
newstmt.analyze = false;
- ExplainOneQuery(query, true, dcstmt->options, &newstmt,
+ ExplainOneQuery(query, dcstmt->options, &newstmt,
queryString, params, tstate);
}
else if (IsA(utilityStmt, ExecuteStmt))
diff --git a/src/backend/commands/portalcmds.c b/src/backend/commands/portalcmds.c
index d759ed4ac2d..eb381ebb705 100644
--- a/src/backend/commands/portalcmds.c
+++ b/src/backend/commands/portalcmds.c
@@ -14,7 +14,7 @@
*
*
* IDENTIFICATION
- * $PostgreSQL: pgsql/src/backend/commands/portalcmds.c,v 1.63 2007/04/12 06:53:46 neilc Exp $
+ * $PostgreSQL: pgsql/src/backend/commands/portalcmds.c,v 1.64 2007/04/16 01:14:55 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@@ -111,7 +111,7 @@ PerformCursorOpen(DeclareCursorStmt *stmt, ParamListInfo params,
errdetail("Cursors must be READ ONLY.")));
/* plan the query */
- plan = planner(query, true, stmt->options, params);
+ plan = planner(query, stmt->options, params);
/*
* Create a portal and copy the plan into its memory context.
diff --git a/src/backend/commands/prepare.c b/src/backend/commands/prepare.c
index fe1a8532f07..9a4f88d1a0b 100644
--- a/src/backend/commands/prepare.c
+++ b/src/backend/commands/prepare.c
@@ -10,7 +10,7 @@
* Copyright (c) 2002-2007, PostgreSQL Global Development Group
*
* IDENTIFICATION
- * $PostgreSQL: pgsql/src/backend/commands/prepare.c,v 1.71 2007/04/12 06:53:46 neilc Exp $
+ * $PostgreSQL: pgsql/src/backend/commands/prepare.c,v 1.72 2007/04/16 01:14:55 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@@ -160,7 +160,7 @@ PrepareQuery(PrepareStmt *stmt, const char *queryString)
query_list = QueryRewrite(query);
/* Generate plans for queries. Snapshot is already set. */
- plan_list = pg_plan_queries(query_list, NULL, false);
+ plan_list = pg_plan_queries(query_list, 0, NULL, false);
/*
* Save the results.
diff --git a/src/backend/executor/functions.c b/src/backend/executor/functions.c
index 1e1d450be57..b59228b0c9e 100644
--- a/src/backend/executor/functions.c
+++ b/src/backend/executor/functions.c
@@ -8,7 +8,7 @@
*
*
* IDENTIFICATION
- * $PostgreSQL: pgsql/src/backend/executor/functions.c,v 1.114 2007/04/02 18:49:29 tgl Exp $
+ * $PostgreSQL: pgsql/src/backend/executor/functions.c,v 1.115 2007/04/16 01:14:56 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@@ -115,7 +115,7 @@ init_execution_state(List *queryTree_list, bool readonly_func)
if (queryTree->commandType == CMD_UTILITY)
stmt = queryTree->utilityStmt;
else
- stmt = (Node *) pg_plan_query(queryTree, NULL);
+ stmt = (Node *) pg_plan_query(queryTree, 0, NULL);
/* Precheck all commands for validity in a function */
if (IsA(stmt, TransactionStmt))
diff --git a/src/backend/executor/spi.c b/src/backend/executor/spi.c
index 655503cd708..bf3bbdbceb3 100644
--- a/src/backend/executor/spi.c
+++ b/src/backend/executor/spi.c
@@ -8,7 +8,7 @@
*
*
* IDENTIFICATION
- * $PostgreSQL: pgsql/src/backend/executor/spi.c,v 1.175 2007/03/25 23:42:43 tgl Exp $
+ * $PostgreSQL: pgsql/src/backend/executor/spi.c,v 1.176 2007/04/16 01:14:56 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@@ -34,7 +34,8 @@ static int _SPI_stack_depth = 0; /* allocated size of _SPI_stack */
static int _SPI_connected = -1;
static int _SPI_curid = -1;
-static void _SPI_prepare_plan(const char *src, SPIPlanPtr plan);
+static void _SPI_prepare_plan(const char *src, SPIPlanPtr plan,
+ int cursorOptions);
static int _SPI_execute_plan(SPIPlanPtr plan,
Datum *Values, const char *Nulls,
@@ -45,8 +46,9 @@ static int _SPI_pquery(QueryDesc *queryDesc, long tcount);
static void _SPI_error_callback(void *arg);
-static void _SPI_cursor_operation(Portal portal, bool forward, long count,
- DestReceiver *dest);
+static void _SPI_cursor_operation(Portal portal,
+ FetchDirection direction, long count,
+ DestReceiver *dest);
static SPIPlanPtr _SPI_copy_plan(SPIPlanPtr plan, MemoryContext parentcxt);
static SPIPlanPtr _SPI_save_plan(SPIPlanPtr plan);
@@ -310,7 +312,7 @@ SPI_execute(const char *src, bool read_only, long tcount)
memset(&plan, 0, sizeof(_SPI_plan));
plan.magic = _SPI_PLAN_MAGIC;
- _SPI_prepare_plan(src, &plan);
+ _SPI_prepare_plan(src, &plan, 0);
res = _SPI_execute_plan(&plan, NULL, NULL,
InvalidSnapshot, InvalidSnapshot,
@@ -399,6 +401,13 @@ SPI_execute_snapshot(SPIPlanPtr plan,
SPIPlanPtr
SPI_prepare(const char *src, int nargs, Oid *argtypes)
{
+ return SPI_prepare_cursor(src, nargs, argtypes, 0);
+}
+
+SPIPlanPtr
+SPI_prepare_cursor(const char *src, int nargs, Oid *argtypes,
+ int cursorOptions)
+{
_SPI_plan plan;
SPIPlanPtr result;
@@ -417,7 +426,7 @@ SPI_prepare(const char *src, int nargs, Oid *argtypes)
plan.nargs = nargs;
plan.argtypes = argtypes;
- _SPI_prepare_plan(src, &plan);
+ _SPI_prepare_plan(src, &plan, cursorOptions);
/* copy plan to procedure context */
result = _SPI_copy_plan(&plan, _SPI_current->procCxt);
@@ -1032,7 +1041,8 @@ SPI_cursor_find(const char *name)
void
SPI_cursor_fetch(Portal portal, bool forward, long count)
{
- _SPI_cursor_operation(portal, forward, count,
+ _SPI_cursor_operation(portal,
+ forward ? FETCH_FORWARD : FETCH_BACKWARD, count,
CreateDestReceiver(DestSPI, NULL));
/* we know that the DestSPI receiver doesn't need a destroy call */
}
@@ -1046,7 +1056,36 @@ SPI_cursor_fetch(Portal portal, bool forward, long count)
void
SPI_cursor_move(Portal portal, bool forward, long count)
{
- _SPI_cursor_operation(portal, forward, count, None_Receiver);
+ _SPI_cursor_operation(portal,
+ forward ? FETCH_FORWARD : FETCH_BACKWARD, count,
+ None_Receiver);
+}
+
+
+/*
+ * SPI_scroll_cursor_fetch()
+ *
+ * Fetch rows in a scrollable cursor
+ */
+void
+SPI_scroll_cursor_fetch(Portal portal, FetchDirection direction, long count)
+{
+ _SPI_cursor_operation(portal,
+ direction, count,
+ CreateDestReceiver(DestSPI, NULL));
+ /* we know that the DestSPI receiver doesn't need a destroy call */
+}
+
+
+/*
+ * SPI_scroll_cursor_move()
+ *
+ * Move in a scrollable cursor
+ */
+void
+SPI_scroll_cursor_move(Portal portal, FetchDirection direction, long count)
+{
+ _SPI_cursor_operation(portal, direction, count, None_Receiver);
}
@@ -1299,7 +1338,7 @@ spi_printtup(TupleTableSlot *slot, DestReceiver *self)
* and need to be copied somewhere to survive.
*/
static void
-_SPI_prepare_plan(const char *src, SPIPlanPtr plan)
+_SPI_prepare_plan(const char *src, SPIPlanPtr plan, int cursorOptions)
{
List *raw_parsetree_list;
List *plancache_list;
@@ -1345,7 +1384,7 @@ _SPI_prepare_plan(const char *src, SPIPlanPtr plan)
/* Need a copyObject here to keep parser from modifying raw tree */
stmt_list = pg_analyze_and_rewrite(copyObject(parsetree),
src, argtypes, nargs);
- stmt_list = pg_plan_queries(stmt_list, NULL, false);
+ stmt_list = pg_plan_queries(stmt_list, cursorOptions, NULL, false);
plansource = (CachedPlanSource *) palloc0(sizeof(CachedPlanSource));
cplan = (CachedPlan *) palloc0(sizeof(CachedPlan));
@@ -1739,7 +1778,7 @@ _SPI_error_callback(void *arg)
* Do a FETCH or MOVE in a cursor
*/
static void
-_SPI_cursor_operation(Portal portal, bool forward, long count,
+_SPI_cursor_operation(Portal portal, FetchDirection direction, long count,
DestReceiver *dest)
{
long nfetched;
@@ -1760,7 +1799,7 @@ _SPI_cursor_operation(Portal portal, bool forward, long count,
/* Run the cursor */
nfetched = PortalRunFetch(portal,
- forward ? FETCH_FORWARD : FETCH_BACKWARD,
+ direction,
count,
dest);
diff --git a/src/backend/optimizer/plan/planner.c b/src/backend/optimizer/plan/planner.c
index 9bf5516ca4c..5c65a78d6f7 100644
--- a/src/backend/optimizer/plan/planner.c
+++ b/src/backend/optimizer/plan/planner.c
@@ -8,7 +8,7 @@
*
*
* IDENTIFICATION
- * $PostgreSQL: pgsql/src/backend/optimizer/plan/planner.c,v 1.216 2007/02/27 01:11:25 tgl Exp $
+ * $PostgreSQL: pgsql/src/backend/optimizer/plan/planner.c,v 1.217 2007/04/16 01:14:56 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@@ -80,8 +80,7 @@ static List *postprocess_setop_tlist(List *new_tlist, List *orig_tlist);
*
*****************************************************************************/
PlannedStmt *
-planner(Query *parse, bool isCursor, int cursorOptions,
- ParamListInfo boundParams)
+planner(Query *parse, int cursorOptions, ParamListInfo boundParams)
{
PlannedStmt *result;
PlannerGlobal *glob;
@@ -107,7 +106,7 @@ planner(Query *parse, bool isCursor, int cursorOptions,
glob->finalrtable = NIL;
/* Determine what fraction of the plan is likely to be scanned */
- if (isCursor)
+ if (cursorOptions & CURSOR_OPT_FAST_PLAN)
{
/*
* We have no real idea how many tuples the user will ultimately FETCH
@@ -130,7 +129,7 @@ planner(Query *parse, bool isCursor, int cursorOptions,
* If creating a plan for a scrollable cursor, make sure it can run
* backwards on demand. Add a Material node at the top at need.
*/
- if (isCursor && (cursorOptions & CURSOR_OPT_SCROLL))
+ if (cursorOptions & CURSOR_OPT_SCROLL)
{
if (!ExecSupportsBackwardScan(top_plan))
top_plan = materialize_finished_plan(top_plan);
diff --git a/src/backend/parser/gram.y b/src/backend/parser/gram.y
index 6aa81eec3ef..b9728deaada 100644
--- a/src/backend/parser/gram.y
+++ b/src/backend/parser/gram.y
@@ -11,7 +11,7 @@
*
*
* IDENTIFICATION
- * $PostgreSQL: pgsql/src/backend/parser/gram.y,v 2.588 2007/04/12 06:53:46 neilc Exp $
+ * $PostgreSQL: pgsql/src/backend/parser/gram.y,v 2.589 2007/04/16 01:14:56 tgl Exp $
*
* HISTORY
* AUTHOR DATE MAJOR EVENT
@@ -279,9 +279,9 @@ static Node *makeXmlExpr(XmlExprOp op, char *name, List *named_args, List *args)
%type <boolean> opt_freeze opt_default opt_recheck
%type <defelt> opt_binary opt_oids copy_delimiter
-%type <boolean> copy_from opt_hold
+%type <boolean> copy_from
-%type <ival> opt_column event cursor_options
+%type <ival> opt_column event cursor_options opt_hold
%type <objtype> reindex_type drop_type comment_type
%type <node> fetch_direction select_limit_value select_offset_value
@@ -5821,10 +5821,9 @@ DeclareCursorStmt: DECLARE name cursor_options CURSOR opt_hold FOR SelectStmt
{
DeclareCursorStmt *n = makeNode(DeclareCursorStmt);
n->portalname = $2;
- n->options = $3;
+ /* currently we always set FAST_PLAN option */
+ n->options = $3 | $5 | CURSOR_OPT_FAST_PLAN;
n->query = $7;
- if ($5)
- n->options |= CURSOR_OPT_HOLD;
$$ = (Node *)n;
}
;
@@ -5836,9 +5835,9 @@ cursor_options: /*EMPTY*/ { $$ = 0; }
| cursor_options INSENSITIVE { $$ = $1 | CURSOR_OPT_INSENSITIVE; }
;
-opt_hold: /* EMPTY */ { $$ = FALSE; }
- | WITH HOLD { $$ = TRUE; }
- | WITHOUT HOLD { $$ = FALSE; }
+opt_hold: /* EMPTY */ { $$ = 0; }
+ | WITH HOLD { $$ = CURSOR_OPT_HOLD; }
+ | WITHOUT HOLD { $$ = 0; }
;
/*****************************************************************************
diff --git a/src/backend/tcop/postgres.c b/src/backend/tcop/postgres.c
index bfcc271996e..7722eddf347 100644
--- a/src/backend/tcop/postgres.c
+++ b/src/backend/tcop/postgres.c
@@ -8,7 +8,7 @@
*
*
* IDENTIFICATION
- * $PostgreSQL: pgsql/src/backend/tcop/postgres.c,v 1.530 2007/03/29 19:10:10 tgl Exp $
+ * $PostgreSQL: pgsql/src/backend/tcop/postgres.c,v 1.531 2007/04/16 01:14:57 tgl Exp $
*
* NOTES
* this is the "main" module of the postgres backend and
@@ -656,9 +656,12 @@ pg_rewrite_queries(List *querytree_list)
}
-/* Generate a plan for a single already-rewritten query. */
+/*
+ * Generate a plan for a single already-rewritten query.
+ * This is a thin wrapper around planner() and takes the same parameters.
+ */
PlannedStmt *
-pg_plan_query(Query *querytree, ParamListInfo boundParams)
+pg_plan_query(Query *querytree, int cursorOptions, ParamListInfo boundParams)
{
PlannedStmt *plan;
@@ -670,7 +673,7 @@ pg_plan_query(Query *querytree, ParamListInfo boundParams)
ResetUsage();
/* call the optimizer */
- plan = planner(querytree, false, 0, boundParams);
+ plan = planner(querytree, cursorOptions, boundParams);
if (log_planner_stats)
ShowUsage("PLANNER STATISTICS");
@@ -718,7 +721,7 @@ pg_plan_query(Query *querytree, ParamListInfo boundParams)
* list. Utility statements are simply represented by their statement nodes.
*/
List *
-pg_plan_queries(List *querytrees, ParamListInfo boundParams,
+pg_plan_queries(List *querytrees, int cursorOptions, ParamListInfo boundParams,
bool needSnapshot)
{
List *stmt_list = NIL;
@@ -741,7 +744,7 @@ pg_plan_queries(List *querytrees, ParamListInfo boundParams,
ActiveSnapshot = CopySnapshot(GetTransactionSnapshot());
needSnapshot = false;
}
- stmt = (Node *) pg_plan_query(query, boundParams);
+ stmt = (Node *) pg_plan_query(query, cursorOptions, boundParams);
}
stmt_list = lappend(stmt_list, stmt);
@@ -892,7 +895,7 @@ exec_simple_query(const char *query_string)
querytree_list = pg_analyze_and_rewrite(parsetree, query_string,
NULL, 0);
- plantree_list = pg_plan_queries(querytree_list, NULL, true);
+ plantree_list = pg_plan_queries(querytree_list, 0, NULL, true);
/* If we got a cancel signal in analysis or planning, quit */
CHECK_FOR_INTERRUPTS();
@@ -1207,7 +1210,7 @@ exec_parse_message(const char *query_string, /* string to execute */
}
else
{
- stmt_list = pg_plan_queries(querytree_list, NULL, true);
+ stmt_list = pg_plan_queries(querytree_list, 0, NULL, true);
fully_planned = true;
}
}
@@ -1621,7 +1624,7 @@ exec_bind_message(StringInfo input_message)
*/
oldContext = MemoryContextSwitchTo(PortalGetHeapMemory(portal));
query_list = copyObject(cplan->stmt_list);
- plan_list = pg_plan_queries(query_list, params, true);
+ plan_list = pg_plan_queries(query_list, 0, params, true);
MemoryContextSwitchTo(oldContext);
/* We no longer need the cached plan refcount ... */
diff --git a/src/backend/utils/cache/plancache.c b/src/backend/utils/cache/plancache.c
index 6165e59c6e6..28838eba09a 100644
--- a/src/backend/utils/cache/plancache.c
+++ b/src/backend/utils/cache/plancache.c
@@ -33,7 +33,7 @@
* Portions Copyright (c) 1994, Regents of the University of California
*
* IDENTIFICATION
- * $PostgreSQL: pgsql/src/backend/utils/cache/plancache.c,v 1.6 2007/04/12 06:53:47 neilc Exp $
+ * $PostgreSQL: pgsql/src/backend/utils/cache/plancache.c,v 1.7 2007/04/16 01:14:57 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@@ -458,10 +458,13 @@ RevalidateCachedPlan(CachedPlanSource *plansource, bool useResOwner)
if (plansource->fully_planned)
{
/*
- * Generate plans for queries. Assume snapshot is not set yet
+ * Generate plans for queries. We don't need any boundParams, and
+ * currently we don't need to worry about cursor options because
+ * cursor plans are never saved in the plancache (that might have
+ * to change someday). Also, assume snapshot is not set yet
* (XXX this may be wasteful, won't all callers have done that?)
*/
- slist = pg_plan_queries(slist, NULL, true);
+ slist = pg_plan_queries(slist, 0, NULL, true);
}
/*
diff --git a/src/include/executor/spi.h b/src/include/executor/spi.h
index 80c8993c7c3..c996f644c03 100644
--- a/src/include/executor/spi.h
+++ b/src/include/executor/spi.h
@@ -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.h,v 1.60 2007/03/25 23:27:59 tgl Exp $
+ * $PostgreSQL: pgsql/src/include/executor/spi.h,v 1.61 2007/04/16 01:14:57 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@@ -20,8 +20,8 @@
#include "postgres.h"
/*
- * These are not needed by this file, but used by other programs
- * using SPI
+ * Most of these are not needed by this file, but may be used by
+ * user-written code that uses SPI
*/
#include "access/heapam.h"
#include "access/xact.h"
@@ -32,6 +32,7 @@
#include "executor/executor.h"
#include "nodes/execnodes.h"
#include "nodes/params.h"
+#include "nodes/parsenodes.h"
#include "nodes/plannodes.h"
#include "nodes/primnodes.h"
#include "nodes/relation.h"
@@ -105,6 +106,8 @@ extern int SPI_execute_snapshot(SPIPlanPtr plan,
Snapshot crosscheck_snapshot,
bool read_only, long tcount);
extern SPIPlanPtr SPI_prepare(const char *src, int nargs, Oid *argtypes);
+extern SPIPlanPtr SPI_prepare_cursor(const char *src, int nargs, Oid *argtypes,
+ int cursorOptions);
extern SPIPlanPtr SPI_saveplan(SPIPlanPtr plan);
extern int SPI_freeplan(SPIPlanPtr plan);
@@ -136,6 +139,8 @@ extern Portal SPI_cursor_open(const char *name, SPIPlanPtr plan,
extern Portal SPI_cursor_find(const char *name);
extern void SPI_cursor_fetch(Portal portal, bool forward, long count);
extern void SPI_cursor_move(Portal portal, bool forward, long count);
+extern void SPI_scroll_cursor_fetch(Portal, FetchDirection direction, long count);
+extern void SPI_scroll_cursor_move(Portal, FetchDirection direction, long count);
extern void SPI_cursor_close(Portal portal);
extern void AtEOXact_SPI(bool isCommit);
diff --git a/src/include/nodes/parsenodes.h b/src/include/nodes/parsenodes.h
index bc421e265fc..dbc29642f06 100644
--- a/src/include/nodes/parsenodes.h
+++ b/src/include/nodes/parsenodes.h
@@ -7,7 +7,7 @@
* Portions Copyright (c) 1996-2007, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
- * $PostgreSQL: pgsql/src/include/nodes/parsenodes.h,v 1.345 2007/04/12 06:53:48 neilc Exp $
+ * $PostgreSQL: pgsql/src/include/nodes/parsenodes.h,v 1.346 2007/04/16 01:14:57 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@@ -1429,11 +1429,12 @@ typedef struct CommentStmt
* Declare Cursor Statement
* ----------------------
*/
-#define CURSOR_OPT_BINARY 0x0001
-#define CURSOR_OPT_SCROLL 0x0002
-#define CURSOR_OPT_NO_SCROLL 0x0004
-#define CURSOR_OPT_INSENSITIVE 0x0008
-#define CURSOR_OPT_HOLD 0x0010
+#define CURSOR_OPT_BINARY 0x0001 /* BINARY */
+#define CURSOR_OPT_SCROLL 0x0002 /* SCROLL explicitly given */
+#define CURSOR_OPT_NO_SCROLL 0x0004 /* NO SCROLL explicitly given */
+#define CURSOR_OPT_INSENSITIVE 0x0008 /* INSENSITIVE (unimplemented) */
+#define CURSOR_OPT_HOLD 0x0010 /* WITH HOLD */
+#define CURSOR_OPT_FAST_PLAN 0x0020 /* prefer fast-start plan */
typedef struct DeclareCursorStmt
{
diff --git a/src/include/optimizer/planner.h b/src/include/optimizer/planner.h
index c243cdbc356..b568a7dbe82 100644
--- a/src/include/optimizer/planner.h
+++ b/src/include/optimizer/planner.h
@@ -7,7 +7,7 @@
* Portions Copyright (c) 1996-2007, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
- * $PostgreSQL: pgsql/src/include/optimizer/planner.h,v 1.38 2007/02/20 17:32:17 tgl Exp $
+ * $PostgreSQL: pgsql/src/include/optimizer/planner.h,v 1.39 2007/04/16 01:14:58 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@@ -18,7 +18,7 @@
#include "nodes/relation.h"
-extern PlannedStmt *planner(Query *parse, bool isCursor, int cursorOptions,
+extern PlannedStmt *planner(Query *parse, int cursorOptions,
ParamListInfo boundParams);
extern Plan *subquery_planner(PlannerGlobal *glob, Query *parse,
Index level, double tuple_fraction,
diff --git a/src/include/tcop/tcopprot.h b/src/include/tcop/tcopprot.h
index 098cb1da1ed..613d9a99837 100644
--- a/src/include/tcop/tcopprot.h
+++ b/src/include/tcop/tcopprot.h
@@ -7,7 +7,7 @@
* Portions Copyright (c) 1996-2007, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
- * $PostgreSQL: pgsql/src/include/tcop/tcopprot.h,v 1.88 2007/03/07 13:35:03 alvherre Exp $
+ * $PostgreSQL: pgsql/src/include/tcop/tcopprot.h,v 1.89 2007/04/16 01:14:58 tgl Exp $
*
* OLD COMMENTS
* This file was created so that other c files could get the two
@@ -49,9 +49,10 @@ extern List *pg_parse_and_rewrite(const char *query_string,
extern List *pg_parse_query(const char *query_string);
extern List *pg_analyze_and_rewrite(Node *parsetree, const char *query_string,
Oid *paramTypes, int numParams);
-extern PlannedStmt *pg_plan_query(Query *querytree, ParamListInfo boundParams);
-extern List *pg_plan_queries(List *querytrees, ParamListInfo boundParams,
- bool needSnapshot);
+extern PlannedStmt *pg_plan_query(Query *querytree, int cursorOptions,
+ ParamListInfo boundParams);
+extern List *pg_plan_queries(List *querytrees, int cursorOptions,
+ ParamListInfo boundParams, bool needSnapshot);
extern bool assign_max_stack_depth(int newval, bool doit, GucSource source);