aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/backend/catalog/pg_proc.c37
-rw-r--r--src/test/regress/output/create_function_1.source4
2 files changed, 40 insertions, 1 deletions
diff --git a/src/backend/catalog/pg_proc.c b/src/backend/catalog/pg_proc.c
index b9628734701..3ea2af44d3e 100644
--- a/src/backend/catalog/pg_proc.c
+++ b/src/backend/catalog/pg_proc.c
@@ -8,7 +8,7 @@
*
*
* IDENTIFICATION
- * $PostgreSQL: pgsql/src/backend/catalog/pg_proc.c,v 1.111 2004/01/06 23:55:18 tgl Exp $
+ * $PostgreSQL: pgsql/src/backend/catalog/pg_proc.c,v 1.112 2004/03/14 01:58:41 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@@ -44,6 +44,7 @@ Datum fmgr_sql_validator(PG_FUNCTION_ARGS);
static Datum create_parameternames_array(int parameterCount,
const char *parameterNames[]);
+static void sql_function_parse_error_callback(void *arg);
/* ----------------------------------------------------------------
@@ -708,6 +709,7 @@ fmgr_sql_validator(PG_FUNCTION_ARGS)
bool isnull;
Datum tmp;
char *prosrc;
+ ErrorContextCallback sqlerrcontext;
char functyptype;
bool haspolyarg;
int i;
@@ -761,6 +763,16 @@ fmgr_sql_validator(PG_FUNCTION_ARGS)
prosrc = DatumGetCString(DirectFunctionCall1(textout, tmp));
/*
+ * Setup error traceback support for ereport(). This is mostly
+ * so we can add context info that shows that a syntax-error
+ * location is inside the function body, not out in CREATE FUNCTION.
+ */
+ sqlerrcontext.callback = sql_function_parse_error_callback;
+ sqlerrcontext.arg = proc;
+ sqlerrcontext.previous = error_context_stack;
+ error_context_stack = &sqlerrcontext;
+
+ /*
* We can't do full prechecking of the function definition if there
* are any polymorphic input types, because actual datatypes of
* expression results will be unresolvable. The check will be done
@@ -778,9 +790,32 @@ fmgr_sql_validator(PG_FUNCTION_ARGS)
}
else
querytree_list = pg_parse_query(prosrc);
+
+ error_context_stack = sqlerrcontext.previous;
}
ReleaseSysCache(tuple);
PG_RETURN_VOID();
}
+
+/*
+ * error context callback to let us supply a context marker
+ */
+static void
+sql_function_parse_error_callback(void *arg)
+{
+ Form_pg_proc proc = (Form_pg_proc) arg;
+
+ /*
+ * XXX it'd be really nice to adjust the syntax error position to
+ * account for the offset from the start of the statement to the
+ * function body string, not to mention any quoting characters in
+ * the string, but I can't see any decent way to do that...
+ *
+ * In the meantime, put in a CONTEXT entry that can cue clients
+ * not to trust the syntax error position completely.
+ */
+ errcontext("SQL function \"%s\"",
+ NameStr(proc->proname));
+}
diff --git a/src/test/regress/output/create_function_1.source b/src/test/regress/output/create_function_1.source
index 44e74fb527e..e3886febaa9 100644
--- a/src/test/regress/output/create_function_1.source
+++ b/src/test/regress/output/create_function_1.source
@@ -52,16 +52,20 @@ CREATE FUNCTION test1 (int) RETURNS int LANGUAGE sql
AS 'SELECT ''not an integer'';';
ERROR: return type mismatch in function declared to return integer
DETAIL: Actual return type is "unknown".
+CONTEXT: SQL function "test1"
CREATE FUNCTION test1 (int) RETURNS int LANGUAGE sql
AS 'not even SQL';
ERROR: syntax error at or near "not" at character 1
+CONTEXT: SQL function "test1"
CREATE FUNCTION test1 (int) RETURNS int LANGUAGE sql
AS 'SELECT 1, 2, 3;';
ERROR: return type mismatch in function declared to return integer
DETAIL: Final SELECT must return exactly one column.
+CONTEXT: SQL function "test1"
CREATE FUNCTION test1 (int) RETURNS int LANGUAGE sql
AS 'SELECT $2;';
ERROR: there is no parameter $2
+CONTEXT: SQL function "test1"
CREATE FUNCTION test1 (int) RETURNS int LANGUAGE sql
AS 'a', 'b';
ERROR: only one AS item needed for language "sql"