From: Tom Lane Date: Thu, 8 Feb 2007 18:38:28 +0000 (+0000) Subject: Rearrange use of plpgsql_add_initdatums() so that only the parsing of a X-Git-Tag: REL7_3_19~14 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=6eb61d578f3c9fc4fff78d69851b7558821668e3;p=thirdparty%2Fpostgresql.git Rearrange use of plpgsql_add_initdatums() so that only the parsing of a DECLARE section needs to know about it. Formerly, everyplace besides DECLARE that created variables needed to do "plpgsql_add_initdatums(NULL)" to prevent those variables from being sucked up as part of a subsequent DECLARE block. This is obviously error-prone, and in fact the SQLSTATE/SQLERRM patch had failed to do it for those two variables, leading to the bug recently exhibited by Asif Ali Rehman: a DECLARE within an exception handler tried to reinitialize SQLERRM. Although the SQLSTATE/SQLERRM patch isn't in any pre-8.1 branches, and so I can't point to a demonstrable failure there, it seems wise to back-patch this into the older branches anyway, just to keep the logic similar to HEAD. --- diff --git a/src/pl/plpgsql/src/gram.y b/src/pl/plpgsql/src/gram.y index 962fc59c4b8..d3775c46b9f 100644 --- a/src/pl/plpgsql/src/gram.y +++ b/src/pl/plpgsql/src/gram.y @@ -4,7 +4,7 @@ * procedural language * * IDENTIFICATION - * $Header: /cvsroot/pgsql/src/pl/plpgsql/src/gram.y,v 1.39.2.3 2006/05/21 19:56:41 momjian Exp $ + * $Header: /cvsroot/pgsql/src/pl/plpgsql/src/gram.y,v 1.39.2.4 2007/02/08 18:38:28 tgl Exp $ * * This software is copyrighted by Jan Wieck - Hamburg. * @@ -263,7 +263,6 @@ decl_sect : opt_label $$.label = $1; $$.n_initvars = 0; $$.initvarnos = NULL; - plpgsql_add_initdatums(NULL); } | opt_label decl_start { @@ -271,7 +270,6 @@ decl_sect : opt_label $$.label = $1; $$.n_initvars = 0; $$.initvarnos = NULL; - plpgsql_add_initdatums(NULL); } | opt_label decl_start decl_stmts { @@ -280,12 +278,16 @@ decl_sect : opt_label $$.label = $3; else $$.label = $1; + /* Remember variables declared in decl_stmts */ $$.n_initvars = plpgsql_add_initdatums(&($$.initvarnos)); } ; decl_start : K_DECLARE { + /* Forget any variables created before block */ + plpgsql_add_initdatums(NULL); + /* Make variable names be local to block */ plpgsql_ns_setlocal(true); } ; @@ -982,8 +984,6 @@ fori_var : fori_varname plpgsql_ns_additem(PLPGSQL_NSTYPE_VAR, new->varno, $1.name); - plpgsql_add_initdatums(NULL); - $$ = new; } ; diff --git a/src/pl/plpgsql/src/pl_comp.c b/src/pl/plpgsql/src/pl_comp.c index a2e116212bc..b92a69fb72a 100644 --- a/src/pl/plpgsql/src/pl_comp.c +++ b/src/pl/plpgsql/src/pl_comp.c @@ -3,7 +3,7 @@ * procedural language * * IDENTIFICATION - * $Header: /cvsroot/pgsql/src/pl/plpgsql/src/pl_comp.c,v 1.53.2.1 2003/01/31 00:32:00 tgl Exp $ + * $Header: /cvsroot/pgsql/src/pl/plpgsql/src/pl_comp.c,v 1.53.2.2 2007/02/08 18:38:28 tgl Exp $ * * This software is copyrighted by Jan Wieck - Hamburg. * @@ -504,12 +504,7 @@ plpgsql_compile(Oid fn_oid, int functype) function->found_varno = var->varno; /* - * Forget about the above created variables - */ - plpgsql_add_initdatums(NULL); - - /* - * Now parse the functions text + * Now parse the function's text */ parse_rc = plpgsql_yyparse(); if (parse_rc != 0) @@ -1477,11 +1472,17 @@ plpgsql_adddatum(PLpgSQL_datum * new) /* ---------- - * plpgsql_add_initdatums Put all datum entries created - * since the last call into the - * finishing code block so the - * block knows which variables to - * reinitialize when entered. + * plpgsql_add_initdatums Make an array of the datum numbers of + * all the simple VAR datums created since the last call + * to this function. + * + * If varnos is NULL, we just forget any datum entries created since the + * last call. + * + * This is used around a DECLARE section to create a list of the VARs + * that have to be initialized at block entry. Note that VARs can also + * be created elsewhere than DECLARE, eg by a FOR-loop, but it is then + * the responsibility of special-purpose code to initialize them. * ---------- */ int