diff --git a/src/backend/access/common/indextuple.c b/src/backend/access/common/indextuple.c index 3065730bae..c0bad3cd95 100644 --- a/src/backend/access/common/indextuple.c +++ b/src/backend/access/common/indextuple.c @@ -33,20 +33,39 @@ * ---------------------------------------------------------------- */ + /* ---------------- + * index_form_tuple + * + * As index_form_tuple_context, but allocates the returned tuple in the + * CurrentMemoryContext. + * ---------------- + */ +IndexTuple +index_form_tuple(TupleDesc tupleDescriptor, + Datum *values, + bool *isnull) +{ + return index_form_tuple_context(tupleDescriptor, values, isnull, + CurrentMemoryContext); +} + /* ---------------- - * index_form_tuple + * index_form_tuple_context * * This shouldn't leak any memory; otherwise, callers such as * tuplesort_putindextuplevalues() will be very unhappy. * * This shouldn't perform external table access provided caller * does not pass values that are stored EXTERNAL. + * + * Allocates returned tuple in provided 'context'. * ---------------- */ IndexTuple -index_form_tuple(TupleDesc tupleDescriptor, - Datum *values, - bool *isnull) +index_form_tuple_context(TupleDesc tupleDescriptor, + Datum *values, + bool *isnull, + MemoryContext context) { char *tp; /* tuple pointer */ IndexTuple tuple; /* return tuple */ @@ -143,7 +162,7 @@ index_form_tuple(TupleDesc tupleDescriptor, size = hoff + data_size; size = MAXALIGN(size); /* be conservative */ - tp = (char *) palloc0(size); + tp = (char *) MemoryContextAllocZero(context, size); tuple = (IndexTuple) tp; heap_fill_tuple(tupleDescriptor, diff --git a/src/backend/utils/sort/tuplesort.c b/src/backend/utils/sort/tuplesort.c index 31554fd867..421afcf47d 100644 --- a/src/backend/utils/sort/tuplesort.c +++ b/src/backend/utils/sort/tuplesort.c @@ -1884,12 +1884,13 @@ tuplesort_putindextuplevalues(Tuplesortstate *state, Relation rel, ItemPointer self, Datum *values, bool *isnull) { - MemoryContext oldcontext = MemoryContextSwitchTo(state->tuplecontext); + MemoryContext oldcontext; SortTuple stup; Datum original; IndexTuple tuple; - stup.tuple = index_form_tuple(RelationGetDescr(rel), values, isnull); + stup.tuple = index_form_tuple_context(RelationGetDescr(rel), values, + isnull, state->tuplecontext); tuple = ((IndexTuple) stup.tuple); tuple->t_tid = *self; USEMEM(state, GetMemoryChunkSpace(stup.tuple)); @@ -1899,7 +1900,7 @@ tuplesort_putindextuplevalues(Tuplesortstate *state, Relation rel, RelationGetDescr(state->indexRel), &stup.isnull1); - MemoryContextSwitchTo(state->sortcontext); + oldcontext = MemoryContextSwitchTo(state->sortcontext); if (!state->sortKeys || !state->sortKeys->abbrev_converter || stup.isnull1) { diff --git a/src/include/access/itup.h b/src/include/access/itup.h index 2c8877e991..7458bc2fda 100644 --- a/src/include/access/itup.h +++ b/src/include/access/itup.h @@ -150,6 +150,9 @@ typedef IndexAttributeBitMapData * IndexAttributeBitMap; /* routines in indextuple.c */ extern IndexTuple index_form_tuple(TupleDesc tupleDescriptor, Datum *values, bool *isnull); +extern IndexTuple index_form_tuple_context(TupleDesc tupleDescriptor, + Datum *values, bool *isnull, + MemoryContext context); extern Datum nocache_index_getattr(IndexTuple tup, int attnum, TupleDesc tupleDesc); extern void index_deform_tuple(IndexTuple tup, TupleDesc tupleDescriptor,