Skip to content

Commit 1d617b2

Browse files
committed
some daily fix on 1.7 branch
1 parent 9305c5c commit 1d617b2

File tree

4 files changed

+74
-8
lines changed

4 files changed

+74
-8
lines changed

expected/plpgsql_check_active.out

Lines changed: 35 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -3666,9 +3666,10 @@ select * from plpgsql_check_function('dyn_sql_1', security_warnings := true, fat
36663666
Detail: The EXECUTE expression is SQL injection vulnerable.
36673667
Hint: Use quote_ident, quote_literal or format function to secure variable.
36683668
warning:00000:13:EXECUTE:values passed to EXECUTE statement by USING clause was not used
3669-
error:XX000:14:EXECUTE:there is no parameter $1
3670-
Context: SQL statement "select $1"
3671-
(13 rows)
3669+
error:42P02:14:EXECUTE:there is no parameter $1
3670+
Query: select $1
3671+
-- ^
3672+
(14 rows)
36723673

36733674
drop function dyn_sql_1();
36743675
create type tp as (a int, b int);
@@ -3700,3 +3701,34 @@ select * from plpgsql_check_function('dyn_sql_2', security_warnings := true);
37003701

37013702
drop function dyn_sql_2();
37023703
drop type tp;
3704+
/*
3705+
* Should not to work
3706+
*/
3707+
create or replace function dyn_sql_2()
3708+
returns void as $$
3709+
declare
3710+
r record;
3711+
result int;
3712+
begin
3713+
select 10 a, 20 b into r;
3714+
raise notice '%', r.a;
3715+
execute 'select $1.a + $1.b' into result using r;
3716+
raise notice '%', result;
3717+
end;
3718+
$$ language plpgsql;
3719+
select dyn_sql_2(); --should to fail
3720+
NOTICE: 10
3721+
ERROR: could not identify column "a" in record data type
3722+
LINE 1: select $1.a + $1.b
3723+
^
3724+
QUERY: select $1.a + $1.b
3725+
CONTEXT: PL/pgSQL function dyn_sql_2() line 8 at EXECUTE
3726+
select * from plpgsql_check_function('dyn_sql_2', security_warnings := true);
3727+
plpgsql_check_function
3728+
-------------------------------------------------------------------------
3729+
error:42703:8:EXECUTE:could not identify column "a" in record data type
3730+
Query: select $1.a + $1.b
3731+
-- ^
3732+
(3 rows)
3733+
3734+
drop function dyn_sql_2();

sql/plpgsql_check_active.sql

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2693,3 +2693,24 @@ select * from plpgsql_check_function('dyn_sql_2', security_warnings := true);
26932693
drop function dyn_sql_2();
26942694

26952695
drop type tp;
2696+
2697+
/*
2698+
* Should not to work
2699+
*/
2700+
create or replace function dyn_sql_2()
2701+
returns void as $$
2702+
declare
2703+
r record;
2704+
result int;
2705+
begin
2706+
select 10 a, 20 b into r;
2707+
raise notice '%', r.a;
2708+
execute 'select $1.a + $1.b' into result using r;
2709+
raise notice '%', result;
2710+
end;
2711+
$$ language plpgsql;
2712+
2713+
select dyn_sql_2(); --should to fail
2714+
select * from plpgsql_check_function('dyn_sql_2', security_warnings := true);
2715+
2716+
drop function dyn_sql_2();

src/check_expr.c

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -462,9 +462,14 @@ plpgsql_check_expr_get_string(PLpgSQL_checkstate *cstate, PLpgSQL_expr *expr, bo
462462
Const *c;
463463

464464
c = expr_get_const(cstate, expr);
465-
*isnull = c && c->constisnull;
465+
if (c)
466+
{
467+
*isnull = c->constisnull;
468+
469+
return plpgsql_check_const_to_string(c);
470+
}
466471

467-
return plpgsql_check_const_to_string(c);
472+
return NULL;
468473
}
469474

470475
static void

src/stmtwalk.c

Lines changed: 11 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@
1212
#include "plpgsql_check.h"
1313

1414
#include "access/tupconvert.h"
15+
#include "catalog/pg_collation.h"
1516
#include "catalog/pg_type.h"
1617

1718
#include "nodes/nodeFuncs.h"
@@ -55,7 +56,10 @@ dynsql_param_ref(ParseState *pstate, ParamRef *pref)
5556
TupleDesc tupdesc;
5657

5758
if (pref->number < 1 || pref->number > nargs)
58-
elog(ERROR, "there is no parameter $%d", pref->number);
59+
ereport(ERROR,
60+
(errcode(ERRCODE_UNDEFINED_PARAMETER),
61+
errmsg("there is no parameter $%d", pref->number),
62+
parser_errposition(pstate, pref->location)));
5963

6064
expr = (PLpgSQL_expr *) list_nth(args, pref->number - 1);
6165

@@ -72,8 +76,12 @@ dynsql_param_ref(ParseState *pstate, ParamRef *pref)
7276
param->paramkind = PARAM_EXTERN;
7377
param->paramid = pref->number;
7478
param->paramtype = TupleDescAttr(tupdesc, 0)->atttypid;
75-
param->paramtypmod = TupleDescAttr(tupdesc, 0)->atttypmod;
76-
param->paramcollid = TupleDescAttr(tupdesc, 0)->attcollation;
79+
80+
/*
81+
* SPI_execute_with_args doesn't allow pass typmod.
82+
*/
83+
param->paramtypmod = -1;
84+
param->paramcollid = DEFAULT_COLLATION_OID;
7785

7886
ReleaseTupleDesc(tupdesc);
7987
}

0 commit comments

Comments
 (0)