Re: Bug plperl.c - Mailing list pgsql-bugs
From | Tom Lane |
---|---|
Subject | Re: Bug plperl.c |
Date | |
Msg-id | 2081576.1645825002@sss.pgh.pa.us Whole thread Raw |
In response to | Re: Bug plperl.c (Mark Murawski <markm-lists@intellasoft.net>) |
Responses |
Re: Bug plperl.c
|
List | pgsql-bugs |
Mark Murawski <markm-lists@intellasoft.net> writes: > Were you able to reproduce using the updated example? Sorry, this wasn't at the top of my to-do queue. It does reproduce for me, and I think what we need to do about it is the attached. In the normal code paths, this change will disallow usage of SPI until we have completed compile_plperl_function and have a valid "prodesc" to look at. I didn't care for your proposed workaround because (1) it'd allow execution of non-read-only code during compilation of a supposedly read-only function; (2) it didn't patch the dozen or so other places where plperl SPI functions could try to dereference prodesc; (3) allowing code execution during function validation is, if not an actual security hole, certainly on the hairy edge of being one. I'm somewhat comforted about (3) because it seems the problem is only reachable from plperlu not plperl. It's still pretty scary though. I realize that this solution might make your use-case rather awkward. As far as function validation goes, you can still create your functions by setting check_function_bodies = off. If you feel you need to have Perl code that executes during compilation otherwise, I'm not sure what to tell you, except that it doesn't seem like a great idea. I also noticed while looking at this that the relatively-recently-added plperl_spi_commit and plperl_spi_rollback functions neglected to do check_spi_usage_allowed(), so this fixes that too. regards, tom lane diff --git a/src/pl/plperl/plperl.c b/src/pl/plperl/plperl.c index 81d9c46e00..3f221ee01b 100644 --- a/src/pl/plperl/plperl.c +++ b/src/pl/plperl/plperl.c @@ -3097,6 +3097,21 @@ check_spi_usage_allowed(void) /* simple croak as we don't want to involve PostgreSQL code */ croak("SPI functions can not be used in END blocks"); } + + /* + * Disallow SPI usage if we're not executing a fully-compiled plperl + * function. It might seem impossible to get here in that case, but there + * are cases where Perl will try to execute code during compilation. If + * we proceed we are likely to crash trying to dereference the prodesc + * pointer. Working around that might be possible, but it seems unwise + * because it'd allow code execution to happen while validating a + * function, which is undesirable. + */ + if (current_call_data == NULL || current_call_data->prodesc == NULL) + { + /* simple croak as we don't want to involve PostgreSQL code */ + croak("SPI functions can not be used during function compilation"); + } } @@ -3961,6 +3976,8 @@ plperl_spi_commit(void) { MemoryContext oldcontext = CurrentMemoryContext; + check_spi_usage_allowed(); + PG_TRY(); { SPI_commit(); @@ -3986,6 +4003,8 @@ plperl_spi_rollback(void) { MemoryContext oldcontext = CurrentMemoryContext; + check_spi_usage_allowed(); + PG_TRY(); { SPI_rollback();
pgsql-bugs by date: