SPI nesting in plperl

Started by Tom Laneover 17 years ago2 messageshackers
Jump to latest
#1Tom Lane
tgl@sss.pgh.pa.us

I tried fixing this
http://archives.postgresql.org/pgsql-general/2009-01/msg00030.php
by inserting SPI_push/SPI_pop calls around plperl's use of
InputFunctionCall and OutputFunctionCall. Unfortunately it soon
turned into a mess, because there are various control paths through
that code and some arrive at the I/O calls inside a SPI context
while others don't. We could probably fix it with a kluge or two
but it would be awfully fragile. The reason for the inconsistency
is that the call handlers exit the SPI context before preparing
their results:

/************************************************************
* Disconnect from SPI manager and then create the return
* values datum (if the input function does a palloc for it
* this must not be allocated in the SPI memory context
* because SPI_finish would free it).
************************************************************/
if (SPI_finish() != SPI_OK_FINISH)
elog(ERROR, "SPI_finish() failed");

It seems like a "clean" fix would involve moving the SPI_finish down
to the end and dealing with the problem mentioned in the comment by
paying an extra datumCopy cycle for pass-by-reference function results.
Which is annoying, though in the big scheme of things it's probably
not much compared to the overall overhead of a PL function.

I also thought about attacking the problem by having InputFunctionCall
and OutputFunctionCall automatically do SPI_push/SPI_pop if they are
called within an active SPI context. I don't like this approach too
much because it seems likely to mask bugs as often as fix them. (In
particular I'd be afraid to back-patch such a change.) It might be the
cleanest solution overall, though, particularly when you consider that
we've probably got similar issues in pltcl, plpython, and add-on PLs.

Anyone have comments or better ideas?

regards, tom lane

#2Tom Lane
tgl@sss.pgh.pa.us
In reply to: Tom Lane (#1)
Re: SPI nesting in plperl

I wrote:

I tried fixing this
http://archives.postgresql.org/pgsql-general/2009-01/msg00030.php
by inserting SPI_push/SPI_pop calls around plperl's use of
InputFunctionCall and OutputFunctionCall ...

I also thought about attacking the problem by having InputFunctionCall
and OutputFunctionCall automatically do SPI_push/SPI_pop if they are
called within an active SPI context. I don't like this approach too
much because it seems likely to mask bugs as often as fix them. (In
particular I'd be afraid to back-patch such a change.) It might be the
cleanest solution overall, though, particularly when you consider that
we've probably got similar issues in pltcl, plpython, and add-on PLs.

I've done a trial patch along the second line, and on the whole I think
it's probably far safer than sprinkling the system with SPI_push/SPI_pop
calls. Comments?

regards, tom lane