mirror of
https://github.com/postgres/postgres.git
synced 2025-07-26 01:22:12 +03:00
tablefunc: Reject negative number of tuples passed to normal_rand()
The function converted the first argument i.e. the number of tuples to return into an unsigned integer which turns out to be huge number when a negative value is passed. This causes the function to take much longer time to execute. Instead, reject a negative value. (If someone really wants to generate many more result rows, they should consider adding a bigint or numeric variant.) While at it, improve SQL test to test the number of tuples returned by this function. Author: Ashutosh Bapat <ashutosh.bapat@2ndquadrant.com> Discussion: https://www.postgresql.org/message-id/CAG-ACPW3PUUmSnM6cLa9Rw4BEC5cEMKjX8Gogc8gvQcT3cYA1A@mail.gmail.com
This commit is contained in:
@ -3,12 +3,15 @@ CREATE EXTENSION tablefunc;
|
|||||||
-- normal_rand()
|
-- normal_rand()
|
||||||
-- no easy way to do this for regression testing
|
-- no easy way to do this for regression testing
|
||||||
--
|
--
|
||||||
SELECT avg(normal_rand)::int FROM normal_rand(100, 250, 0.2);
|
SELECT avg(normal_rand)::int, count(*) FROM normal_rand(100, 250, 0.2);
|
||||||
avg
|
avg | count
|
||||||
-----
|
-----+-------
|
||||||
250
|
250 | 100
|
||||||
(1 row)
|
(1 row)
|
||||||
|
|
||||||
|
-- negative number of tuples
|
||||||
|
SELECT avg(normal_rand)::int, count(*) FROM normal_rand(-1, 250, 0.2);
|
||||||
|
ERROR: number of rows cannot be negative
|
||||||
--
|
--
|
||||||
-- crosstab()
|
-- crosstab()
|
||||||
--
|
--
|
||||||
|
@ -4,7 +4,9 @@ CREATE EXTENSION tablefunc;
|
|||||||
-- normal_rand()
|
-- normal_rand()
|
||||||
-- no easy way to do this for regression testing
|
-- no easy way to do this for regression testing
|
||||||
--
|
--
|
||||||
SELECT avg(normal_rand)::int FROM normal_rand(100, 250, 0.2);
|
SELECT avg(normal_rand)::int, count(*) FROM normal_rand(100, 250, 0.2);
|
||||||
|
-- negative number of tuples
|
||||||
|
SELECT avg(normal_rand)::int, count(*) FROM normal_rand(-1, 250, 0.2);
|
||||||
|
|
||||||
--
|
--
|
||||||
-- crosstab()
|
-- crosstab()
|
||||||
|
@ -184,6 +184,8 @@ normal_rand(PG_FUNCTION_ARGS)
|
|||||||
/* stuff done only on the first call of the function */
|
/* stuff done only on the first call of the function */
|
||||||
if (SRF_IS_FIRSTCALL())
|
if (SRF_IS_FIRSTCALL())
|
||||||
{
|
{
|
||||||
|
int32 num_tuples;
|
||||||
|
|
||||||
/* create a function context for cross-call persistence */
|
/* create a function context for cross-call persistence */
|
||||||
funcctx = SRF_FIRSTCALL_INIT();
|
funcctx = SRF_FIRSTCALL_INIT();
|
||||||
|
|
||||||
@ -193,7 +195,12 @@ normal_rand(PG_FUNCTION_ARGS)
|
|||||||
oldcontext = MemoryContextSwitchTo(funcctx->multi_call_memory_ctx);
|
oldcontext = MemoryContextSwitchTo(funcctx->multi_call_memory_ctx);
|
||||||
|
|
||||||
/* total number of tuples to be returned */
|
/* total number of tuples to be returned */
|
||||||
funcctx->max_calls = PG_GETARG_UINT32(0);
|
num_tuples = PG_GETARG_INT32(0);
|
||||||
|
if (num_tuples < 0)
|
||||||
|
ereport(ERROR,
|
||||||
|
(errcode(ERRCODE_INVALID_PARAMETER_VALUE),
|
||||||
|
errmsg("number of rows cannot be negative")));
|
||||||
|
funcctx->max_calls = num_tuples;
|
||||||
|
|
||||||
/* allocate memory for user context */
|
/* allocate memory for user context */
|
||||||
fctx = (normal_rand_fctx *) palloc(sizeof(normal_rand_fctx));
|
fctx = (normal_rand_fctx *) palloc(sizeof(normal_rand_fctx));
|
||||||
|
Reference in New Issue
Block a user