diff --git a/src/backend/access/spgist/spgscan.c b/src/backend/access/spgist/spgscan.c index 34983ee5a7..dbd68a3b24 100644 --- a/src/backend/access/spgist/spgscan.c +++ b/src/backend/access/spgist/spgscan.c @@ -451,10 +451,22 @@ spgNewHeapItem(SpGistScanOpaque so, int level, ItemPointer heapPtr, item->level = level; item->heapPtr = *heapPtr; - /* copy value to queue cxt out of tmp cxt */ - item->value = isnull ? (Datum) 0 : - datumCopy(leafValue, so->state.attLeafType.attbyval, - so->state.attLeafType.attlen); + + /* + * If we need the reconstructed value, copy it to queue cxt out of tmp + * cxt. Caution: the leaf_consistent method may not have supplied a value + * if we didn't ask it to, and mildly-broken methods might supply one of + * the wrong type. Also, while the correct leafValue type is attType not + * leafType, pre-v14 Postgres versions have historically used attLeafType + * here; let's not confuse matters even more by changing that in a minor + * release. + */ + if (so->want_itup) + item->value = isnull ? (Datum) 0 : + datumCopy(leafValue, so->state.attLeafType.attbyval, + so->state.attLeafType.attlen); + else + item->value = (Datum) 0; item->traversalValue = NULL; item->isLeaf = true; item->recheck = recheck; diff --git a/src/backend/utils/adt/geo_spgist.c b/src/backend/utils/adt/geo_spgist.c index 8e29770422..fb2e7b5720 100644 --- a/src/backend/utils/adt/geo_spgist.c +++ b/src/backend/utils/adt/geo_spgist.c @@ -749,8 +749,13 @@ spg_box_quad_leaf_consistent(PG_FUNCTION_ARGS) /* All tests are exact. */ out->recheck = false; - /* leafDatum is what it is... */ - out->leafValue = in->leafDatum; + /* + * Don't return leafValue unless told to; this is used for both box and + * polygon opclasses, and in the latter case the leaf datum is not even of + * the right type to return. + */ + if (in->returnData) + out->leafValue = leaf; /* Perform the required comparison(s) */ for (i = 0; i < in->nkeys; i++)