summaryrefslogtreecommitdiff
path: root/src/backend/access/gist/gistscan.c
diff options
context:
space:
mode:
authorPavan Deolasee2015-06-05 13:35:08 +0000
committerPavan Deolasee2015-06-05 13:35:08 +0000
commitbbf2fec2f194a40b25561c2d2d62c432b49bdd1a (patch)
treeaef582c5cba2ab7b111c0e20e9ebf71dab32c91f /src/backend/access/gist/gistscan.c
parent633da80d8080348ae59dcdd1404a061abc8d0ead (diff)
parent38d500ac2e5d4d4f3468b505962fb85850c1ff4b (diff)
Merge remote-tracking branch 'remotes/PGSQL/master' into XL_NEW_MASTER
Conflicts: .gitignore contrib/Makefile src/backend/access/common/heaptuple.c src/backend/access/transam/rmgr.c src/backend/access/transam/xact.c src/backend/catalog/Makefile src/backend/catalog/catalog.c src/backend/catalog/genbki.pl src/backend/catalog/namespace.c src/backend/commands/sequence.c src/backend/executor/execMain.c src/backend/executor/functions.c src/backend/executor/nodeAgg.c src/backend/executor/nodeModifyTable.c src/backend/nodes/copyfuncs.c src/backend/nodes/outfuncs.c src/backend/nodes/readfuncs.c src/backend/optimizer/plan/createplan.c src/backend/optimizer/plan/planner.c src/backend/optimizer/plan/setrefs.c src/backend/optimizer/util/pathnode.c src/backend/parser/gram.y src/backend/parser/parse_agg.c src/backend/parser/parse_utilcmd.c src/backend/postmaster/postmaster.c src/backend/replication/logical/decode.c src/backend/storage/file/fd.c src/backend/storage/ipc/procsignal.c src/backend/tcop/utility.c src/backend/utils/adt/lockfuncs.c src/backend/utils/adt/ruleutils.c src/backend/utils/sort/tuplesort.c src/backend/utils/time/snapmgr.c src/include/access/rmgrlist.h src/include/catalog/pg_aggregate.h src/include/catalog/pg_proc.h src/include/nodes/execnodes.h src/include/nodes/plannodes.h src/include/nodes/primnodes.h src/include/nodes/relation.h src/include/storage/lwlock.h src/include/storage/procsignal.h src/include/utils/plancache.h src/include/utils/snapshot.h src/test/regress/expected/foreign_key.out src/test/regress/expected/triggers.out src/test/regress/expected/with.out src/test/regress/input/constraints.source src/test/regress/output/constraints.source src/test/regress/pg_regress.c src/test/regress/serial_schedule src/test/regress/sql/returning.sql
Diffstat (limited to 'src/backend/access/gist/gistscan.c')
-rw-r--r--src/backend/access/gist/gistscan.c29
1 files changed, 26 insertions, 3 deletions
diff --git a/src/backend/access/gist/gistscan.c b/src/backend/access/gist/gistscan.c
index 6f65398230..ad39294875 100644
--- a/src/backend/access/gist/gistscan.c
+++ b/src/backend/access/gist/gistscan.c
@@ -17,6 +17,7 @@
#include "access/gist_private.h"
#include "access/gistscan.h"
#include "access/relscan.h"
+#include "utils/lsyscache.h"
#include "utils/memutils.h"
#include "utils/rel.h"
@@ -85,6 +86,12 @@ gistbeginscan(PG_FUNCTION_ARGS)
/* workspaces with size dependent on numberOfOrderBys: */
so->distances = palloc(sizeof(double) * scan->numberOfOrderBys);
so->qual_ok = true; /* in case there are zero keys */
+ if (scan->numberOfOrderBys > 0)
+ {
+ scan->xs_orderbyvals = palloc0(sizeof(Datum) * scan->numberOfOrderBys);
+ scan->xs_orderbynulls = palloc(sizeof(bool) * scan->numberOfOrderBys);
+ memset(scan->xs_orderbynulls, true, sizeof(bool) * scan->numberOfOrderBys);
+ }
scan->opaque = so;
@@ -147,8 +154,8 @@ gistrescan(PG_FUNCTION_ARGS)
}
/*
- * If we're doing an index-only scan, on the first call, also initialize
- * a tuple descriptor to represent the returned index tuples and create a
+ * If we're doing an index-only scan, on the first call, also initialize a
+ * tuple descriptor to represent the returned index tuples and create a
* memory context to hold them during the scan.
*/
if (scan->xs_want_itup && !scan->xs_itupdesc)
@@ -162,7 +169,7 @@ gistrescan(PG_FUNCTION_ARGS)
* descriptor. Instead, construct a descriptor with the original data
* types.
*/
- natts = RelationGetNumberOfAttributes(scan->indexRelation);
+ natts = RelationGetNumberOfAttributes(scan->indexRelation);
so->giststate->fetchTupdesc = CreateTemplateTupleDesc(natts, false);
for (attno = 1; attno <= natts; attno++)
{
@@ -258,6 +265,8 @@ gistrescan(PG_FUNCTION_ARGS)
memmove(scan->orderByData, orderbys,
scan->numberOfOrderBys * sizeof(ScanKeyData));
+ so->orderByTypes = (Oid *) palloc(scan->numberOfOrderBys * sizeof(Oid));
+
/*
* Modify the order-by key so that the Distance method is called for
* all comparisons. The original operator is passed to the Distance
@@ -278,6 +287,20 @@ gistrescan(PG_FUNCTION_ARGS)
fmgr_info_copy(&(skey->sk_func), finfo, so->giststate->scanCxt);
+ /*
+ * Look up the datatype returned by the original ordering
+ * operator. GiST always uses a float8 for the distance function,
+ * but the ordering operator could be anything else.
+ *
+ * XXX: The distance function is only allowed to be lossy if the
+ * ordering operator's result type is float4 or float8. Otherwise
+ * we don't know how to return the distance to the executor. But
+ * we cannot check that here, as we won't know if the distance
+ * function is lossy until it returns *recheck = true for the
+ * first time.
+ */
+ so->orderByTypes[i] = get_func_rettype(skey->sk_func.fn_oid);
+
/* Restore prior fn_extra pointers, if not first time */
if (!first_time)
skey->sk_func.fn_extra = fn_extras[i];