Commit 6563e9e2 authored by Tom Lane's avatar Tom Lane

Add a "provariadic" column to pg_proc to eliminate the remarkably expensive

need to deconstruct proargmodes for each pg_proc entry inspected by
FuncnameGetCandidates().  Fixes function lookup performance regression
caused by yesterday's variadic-functions patch.

In passing, make pg_proc.probin be NULL, rather than a dummy value '-',
in cases where it is not actually used for the particular type of function.
This should buy back some of the space cost of the extra column.
parent 895a4bcc
<!-- $PostgreSQL: pgsql/doc/src/sgml/catalogs.sgml,v 2.169 2008/07/16 01:30:21 tgl Exp $ -->
<!-- $PostgreSQL: pgsql/doc/src/sgml/catalogs.sgml,v 2.170 2008/07/16 16:55:23 tgl Exp $ -->
<!--
Documentation of the system catalogs, directed toward PostgreSQL developers
-->
......@@ -3569,6 +3569,14 @@
<entry>Estimated number of result rows (zero if not <structfield>proretset</>)</entry>
</row>
<row>
<entry><structfield>provariadic</structfield></entry>
<entry><type>oid</type></entry>
<entry><literal><link linkend="catalog-pg-type"><structname>pg_type</structname></link>.oid</literal></entry>
<entry>Data type of the variadic array parameter's elements,
or zero if the function does not have a variadic parameter</entry>
</row>
<row>
<entry><structfield>proisagg</structfield></entry>
<entry><type>bool</type></entry>
......
......@@ -13,7 +13,7 @@
* Portions Copyright (c) 1994, Regents of the University of California
*
* IDENTIFICATION
* $PostgreSQL: pgsql/src/backend/catalog/namespace.c,v 1.108 2008/07/16 01:30:21 tgl Exp $
* $PostgreSQL: pgsql/src/backend/catalog/namespace.c,v 1.109 2008/07/16 16:55:23 tgl Exp $
*
*-------------------------------------------------------------------------
*/
......@@ -619,50 +619,23 @@ FuncnameGetCandidates(List *names, int nargs, bool expand_variadic)
int pronargs = procform->pronargs;
int effective_nargs;
int pathpos = 0;
bool variadic = false;
Oid va_elem_type = InvalidOid;
bool variadic;
Oid va_elem_type;
FuncCandidateList newResult;
/*
* Check if function is variadic, and get variadic element type if so.
* If expand_variadic is false, we can just ignore variadic-ness.
*
* XXX it's annoying to inject something as expensive as this even
* when there are no variadic functions involved. Find a better way.
* If expand_variadic is false, we should just ignore variadic-ness.
*/
if (expand_variadic)
{
Datum proargmodes;
bool isnull;
proargmodes = SysCacheGetAttr(PROCOID, proctup,
Anum_pg_proc_proargmodes, &isnull);
if (!isnull)
{
ArrayType *ar = DatumGetArrayTypeP(proargmodes);
char *argmodes;
int j;
argmodes = ARR_DATA_PTR(ar);
j = ARR_DIMS(ar)[0] - 1;
if (j >= 0 && argmodes[j] == PROARGMODE_VARIADIC)
{
variadic = any_variadic = true;
switch (procform->proargtypes.values[j])
{
case ANYOID:
va_elem_type = ANYOID;
break;
case ANYARRAYOID:
va_elem_type = ANYELEMENTOID;
break;
default:
va_elem_type = get_element_type(procform->proargtypes.values[j]);
Assert(OidIsValid(va_elem_type));
break;
}
}
}
va_elem_type = procform->provariadic;
variadic = OidIsValid(va_elem_type);
}
else
{
va_elem_type = InvalidOid;
variadic = false;
}
/* Ignore if it doesn't match requested argument count */
......
......@@ -8,7 +8,7 @@
*
*
* IDENTIFICATION
* $PostgreSQL: pgsql/src/backend/catalog/pg_aggregate.c,v 1.94 2008/07/16 01:30:22 tgl Exp $
* $PostgreSQL: pgsql/src/backend/catalog/pg_aggregate.c,v 1.95 2008/07/16 16:55:23 tgl Exp $
*
*-------------------------------------------------------------------------
*/
......@@ -202,7 +202,7 @@ AggregateCreate(const char *aggName,
INTERNALlanguageId, /* languageObjectId */
InvalidOid, /* no validator */
"aggregate_dummy", /* placeholder proc */
"-", /* probin */
NULL, /* probin */
true, /* isAgg */
false, /* security invoker (currently not
* definable for agg) */
......
......@@ -8,7 +8,7 @@
*
*
* IDENTIFICATION
* $PostgreSQL: pgsql/src/backend/catalog/pg_proc.c,v 1.151 2008/03/27 03:57:33 tgl Exp $
* $PostgreSQL: pgsql/src/backend/catalog/pg_proc.c,v 1.152 2008/07/16 16:55:23 tgl Exp $
*
*-------------------------------------------------------------------------
*/
......@@ -85,6 +85,7 @@ ProcedureCreate(const char *procedureName,
bool genericOutParam = false;
bool internalInParam = false;
bool internalOutParam = false;
Oid variadicType = InvalidOid;
Relation rel;
HeapTuple tup;
HeapTuple oldtup;
......@@ -103,7 +104,6 @@ ProcedureCreate(const char *procedureName,
* sanity checks
*/
Assert(PointerIsValid(prosrc));
Assert(PointerIsValid(probin));
parameterCount = parameterTypes->dim1;
if (parameterCount < 0 || parameterCount > FUNC_MAX_ARGS)
......@@ -211,6 +211,64 @@ ProcedureCreate(const char *procedureName,
procedureName,
format_type_be(parameterTypes->values[0]))));
if (parameterModes != PointerGetDatum(NULL))
{
/*
* We expect the array to be a 1-D CHAR array; verify that. We don't
* need to use deconstruct_array() since the array data is just going
* to look like a C array of char values.
*/
ArrayType *modesArray = (ArrayType *) DatumGetPointer(parameterModes);
char *modes;
if (ARR_NDIM(modesArray) != 1 ||
ARR_DIMS(modesArray)[0] != allParamCount ||
ARR_HASNULL(modesArray) ||
ARR_ELEMTYPE(modesArray) != CHAROID)
elog(ERROR, "parameterModes is not a 1-D char array");
modes = (char *) ARR_DATA_PTR(modesArray);
/*
* Only the last input parameter can be variadic; if it is, save
* its element type. Errors here are just elog since caller should
* have checked this already.
*/
for (i = 0; i < allParamCount; i++)
{
switch (modes[i])
{
case PROARGMODE_IN:
case PROARGMODE_INOUT:
if (OidIsValid(variadicType))
elog(ERROR, "variadic parameter must be last");
break;
case PROARGMODE_OUT:
/* okay */
break;
case PROARGMODE_VARIADIC:
if (OidIsValid(variadicType))
elog(ERROR, "variadic parameter must be last");
switch (allParams[i])
{
case ANYOID:
variadicType = ANYOID;
break;
case ANYARRAYOID:
variadicType = ANYELEMENTOID;
break;
default:
variadicType = get_element_type(allParams[i]);
if (!OidIsValid(variadicType))
elog(ERROR, "variadic parameter is not an array");
break;
}
break;
default:
elog(ERROR, "invalid parameter mode '%c'", modes[i]);
break;
}
}
}
/*
* All seems OK; prepare the data to be inserted into pg_proc.
*/
......@@ -229,6 +287,7 @@ ProcedureCreate(const char *procedureName,
values[Anum_pg_proc_prolang - 1] = ObjectIdGetDatum(languageObjectId);
values[Anum_pg_proc_procost - 1] = Float4GetDatum(procost);
values[Anum_pg_proc_prorows - 1] = Float4GetDatum(prorows);
values[Anum_pg_proc_provariadic - 1] = ObjectIdGetDatum(variadicType);
values[Anum_pg_proc_proisagg - 1] = BoolGetDatum(isAgg);
values[Anum_pg_proc_prosecdef - 1] = BoolGetDatum(security_definer);
values[Anum_pg_proc_proisstrict - 1] = BoolGetDatum(isStrict);
......@@ -250,7 +309,10 @@ ProcedureCreate(const char *procedureName,
else
nulls[Anum_pg_proc_proargnames - 1] = 'n';
values[Anum_pg_proc_prosrc - 1] = CStringGetTextDatum(prosrc);
values[Anum_pg_proc_probin - 1] = CStringGetTextDatum(probin);
if (probin)
values[Anum_pg_proc_probin - 1] = CStringGetTextDatum(probin);
else
nulls[Anum_pg_proc_probin - 1] = 'n';
if (proconfig != PointerGetDatum(NULL))
values[Anum_pg_proc_proconfig - 1] = proconfig;
else
......@@ -497,12 +559,12 @@ fmgr_c_validator(PG_FUNCTION_ARGS)
tmp = SysCacheGetAttr(PROCOID, tuple, Anum_pg_proc_prosrc, &isnull);
if (isnull)
elog(ERROR, "null prosrc");
elog(ERROR, "null prosrc for C function %u", funcoid);
prosrc = TextDatumGetCString(tmp);
tmp = SysCacheGetAttr(PROCOID, tuple, Anum_pg_proc_probin, &isnull);
if (isnull)
elog(ERROR, "null probin");
elog(ERROR, "null probin for C function %u", funcoid);
probin = TextDatumGetCString(tmp);
(void) load_external_function(probin, prosrc, true, &libraryhandle);
......
......@@ -10,7 +10,7 @@
*
*
* IDENTIFICATION
* $PostgreSQL: pgsql/src/backend/commands/functioncmds.c,v 1.96 2008/07/16 01:30:22 tgl Exp $
* $PostgreSQL: pgsql/src/backend/commands/functioncmds.c,v 1.97 2008/07/16 16:55:23 tgl Exp $
*
* DESCRIPTION
* These routines take the parse tree and pick out the
......@@ -590,7 +590,8 @@ compute_attributes_with_style(List *parameters, bool *isStrict_p, char *volatili
* AS <object reference, or sql code>
*/
static void
interpret_AS_clause(Oid languageOid, const char *languageName, List *as,
interpret_AS_clause(Oid languageOid, const char *languageName,
char *funcname, List *as,
char **prosrc_str_p, char **probin_str_p)
{
Assert(as != NIL);
......@@ -599,25 +600,47 @@ interpret_AS_clause(Oid languageOid, const char *languageName, List *as,
{
/*
* For "C" language, store the file name in probin and, when given,
* the link symbol name in prosrc.
* the link symbol name in prosrc. If link symbol is omitted,
* substitute procedure name. We also allow link symbol to be
* specified as "-", since that was the habit in PG versions before
* 8.4, and there might be dump files out there that don't translate
* that back to "omitted".
*/
*probin_str_p = strVal(linitial(as));
if (list_length(as) == 1)
*prosrc_str_p = "-";
*prosrc_str_p = funcname;
else
{
*prosrc_str_p = strVal(lsecond(as));
if (strcmp(*prosrc_str_p, "-") == 0)
*prosrc_str_p = funcname;
}
}
else
{
/* Everything else wants the given string in prosrc. */
*prosrc_str_p = strVal(linitial(as));
*probin_str_p = "-";
*probin_str_p = NULL;
if (list_length(as) != 1)
ereport(ERROR,
(errcode(ERRCODE_INVALID_FUNCTION_DEFINITION),
errmsg("only one AS item needed for language \"%s\"",
languageName)));
if (languageOid == INTERNALlanguageId)
{
/*
* In PostgreSQL versions before 6.5, the SQL name of the created
* function could not be different from the internal name, and
* "prosrc" wasn't used. So there is code out there that does
* CREATE FUNCTION xyz AS '' LANGUAGE internal. To preserve some
* modicum of backwards compatibility, accept an empty "prosrc"
* value as meaning the supplied SQL function name.
*/
if (strlen(*prosrc_str_p) == 0)
*prosrc_str_p = funcname;
}
}
}
......@@ -759,30 +782,9 @@ CreateFunction(CreateFunctionStmt *stmt)
compute_attributes_with_style(stmt->withClause, &isStrict, &volatility);
interpret_AS_clause(languageOid, languageName, as_clause,
interpret_AS_clause(languageOid, languageName, funcname, as_clause,
&prosrc_str, &probin_str);
if (languageOid == INTERNALlanguageId)
{
/*
* In PostgreSQL versions before 6.5, the SQL name of the created
* function could not be different from the internal name, and
* "prosrc" wasn't used. So there is code out there that does CREATE
* FUNCTION xyz AS '' LANGUAGE internal. To preserve some modicum of
* backwards compatibility, accept an empty "prosrc" value as meaning
* the supplied SQL function name.
*/
if (strlen(prosrc_str) == 0)
prosrc_str = funcname;
}
if (languageOid == ClanguageId)
{
/* If link symbol is specified as "-", substitute procedure name */
if (strcmp(prosrc_str, "-") == 0)
prosrc_str = funcname;
}
/*
* Set default values for COST and ROWS depending on other parameters;
* reject ROWS if it's not returnsSet. NB: pg_dump knows these default
......
......@@ -9,7 +9,7 @@
*
*
* IDENTIFICATION
* $PostgreSQL: pgsql/src/backend/utils/adt/ruleutils.c,v 1.276 2008/07/16 01:30:22 tgl Exp $
* $PostgreSQL: pgsql/src/backend/utils/adt/ruleutils.c,v 1.277 2008/07/16 16:55:23 tgl Exp $
*
*-------------------------------------------------------------------------
*/
......@@ -5389,29 +5389,12 @@ generate_function_name(Oid funcid, int nargs, Oid *argtypes,
/* Check variadic-ness if caller cares */
if (is_variadic)
{
/* XXX change this if we simplify code in FuncnameGetCandidates */
Datum proargmodes;
bool isnull;
*is_variadic = false;
proargmodes = SysCacheGetAttr(PROCOID, proctup,
Anum_pg_proc_proargmodes, &isnull);
if (!isnull)
{
ArrayType *ar = DatumGetArrayTypeP(proargmodes);
char *argmodes;
int j;
argmodes = ARR_DATA_PTR(ar);
j = ARR_DIMS(ar)[0] - 1;
if (j >= 0 && argmodes[j] == PROARGMODE_VARIADIC)
{
/* "any" variadics are not treated as variadics for listing */
if (procform->proargtypes.values[j] != ANYOID)
*is_variadic = true;
}
}
/* "any" variadics are not treated as variadics for listing */
if (OidIsValid(procform->provariadic) &&
procform->provariadic != ANYOID)
*is_variadic = true;
else
*is_variadic = false;
}
ReleaseSysCache(proctup);
......
......@@ -8,7 +8,7 @@
*
*
* IDENTIFICATION
* $PostgreSQL: pgsql/src/backend/utils/fmgr/fmgr.c,v 1.120 2008/06/06 22:35:22 alvherre Exp $
* $PostgreSQL: pgsql/src/backend/utils/fmgr/fmgr.c,v 1.121 2008/07/16 16:55:23 tgl Exp $
*
*-------------------------------------------------------------------------
*/
......@@ -324,18 +324,20 @@ fmgr_info_C_lang(Oid functionId, FmgrInfo *finfo, HeapTuple procedureTuple)
void *libraryhandle;
/*
* Get prosrc and probin strings (link symbol and library filename)
* Get prosrc and probin strings (link symbol and library filename).
* While in general these columns might be null, that's not allowed
* for C-language functions.
*/
prosrcattr = SysCacheGetAttr(PROCOID, procedureTuple,
Anum_pg_proc_prosrc, &isnull);
if (isnull)
elog(ERROR, "null prosrc for function %u", functionId);
elog(ERROR, "null prosrc for C function %u", functionId);
prosrcstring = TextDatumGetCString(prosrcattr);
probinattr = SysCacheGetAttr(PROCOID, procedureTuple,
Anum_pg_proc_probin, &isnull);
if (isnull)
elog(ERROR, "null probin for function %u", functionId);
elog(ERROR, "null probin for C function %u", functionId);
probinstring = TextDatumGetCString(probinattr);
/* Look up the function itself */
......
......@@ -12,7 +12,7 @@
* by PostgreSQL
*
* IDENTIFICATION
* $PostgreSQL: pgsql/src/bin/pg_dump/pg_dump.c,v 1.494 2008/07/16 01:30:22 tgl Exp $
* $PostgreSQL: pgsql/src/bin/pg_dump/pg_dump.c,v 1.495 2008/07/16 16:55:23 tgl Exp $
*
*-------------------------------------------------------------------------
*/
......@@ -6671,10 +6671,12 @@ dumpFunc(Archive *fout, FuncInfo *finfo)
lanname = PQgetvalue(res, 0, PQfnumber(res, "lanname"));
/*
* See backend/commands/define.c for details of how the 'AS' clause is
* used.
* See backend/commands/functioncmds.c for details of how the 'AS' clause
* is used. In 8.4 and up, an unused probin is NULL (here ""); previous
* versions would set it to "-". There are no known cases in which prosrc
* is unused, so the tests below for "-" are probably useless.
*/
if (strcmp(probin, "-") != 0)
if (probin[0] != '\0' && strcmp(probin, "-") != 0)
{
appendPQExpBuffer(asPart, "AS ");
appendStringLiteralAH(asPart, probin, fout);
......
......@@ -37,7 +37,7 @@
* Portions Copyright (c) 1996-2008, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
* $PostgreSQL: pgsql/src/include/catalog/catversion.h,v 1.469 2008/07/16 01:30:23 tgl Exp $
* $PostgreSQL: pgsql/src/include/catalog/catversion.h,v 1.470 2008/07/16 16:55:23 tgl Exp $
*
*-------------------------------------------------------------------------
*/
......@@ -53,6 +53,6 @@
*/
/* yyyymmddN */
#define CATALOG_VERSION_NO 200807152
#define CATALOG_VERSION_NO 200807161
#endif
......@@ -8,7 +8,7 @@
* Portions Copyright (c) 1996-2008, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
* $PostgreSQL: pgsql/src/include/catalog/pg_attribute.h,v 1.138 2008/06/24 17:58:27 tgl Exp $
* $PostgreSQL: pgsql/src/include/catalog/pg_attribute.h,v 1.139 2008/07/16 16:55:24 tgl Exp $
*
* NOTES
* the genbki.sh script reads this file and generates .bki
......@@ -289,21 +289,22 @@ DATA(insert ( 1247 tableoid 26 0 4 -7 0 -1 -1 t p i t f f t 0));
{ 1255, {"prolang"}, 26, -1, 4, 4, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \
{ 1255, {"procost"}, 700, -1, 4, 5, 0, -1, -1, FLOAT4PASSBYVAL, 'p', 'i', true, false, false, true, 0 }, \
{ 1255, {"prorows"}, 700, -1, 4, 6, 0, -1, -1, FLOAT4PASSBYVAL, 'p', 'i', true, false, false, true, 0 }, \
{ 1255, {"proisagg"}, 16, -1, 1, 7, 0, -1, -1, true, 'p', 'c', true, false, false, true, 0 }, \
{ 1255, {"prosecdef"}, 16, -1, 1, 8, 0, -1, -1, true, 'p', 'c', true, false, false, true, 0 }, \
{ 1255, {"proisstrict"}, 16, -1, 1, 9, 0, -1, -1, true, 'p', 'c', true, false, false, true, 0 }, \
{ 1255, {"proretset"}, 16, -1, 1, 10, 0, -1, -1, true, 'p', 'c', true, false, false, true, 0 }, \
{ 1255, {"provolatile"}, 18, -1, 1, 11, 0, -1, -1, true, 'p', 'c', true, false, false, true, 0 }, \
{ 1255, {"pronargs"}, 21, -1, 2, 12, 0, -1, -1, true, 'p', 's', true, false, false, true, 0 }, \
{ 1255, {"prorettype"}, 26, -1, 4, 13, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \
{ 1255, {"proargtypes"}, 30, -1, -1, 14, 1, -1, -1, false, 'p', 'i', true, false, false, true, 0 }, \
{ 1255, {"proallargtypes"}, 1028, -1, -1, 15, 1, -1, -1, false, 'x', 'i', false, false, false, true, 0 }, \
{ 1255, {"proargmodes"}, 1002, -1, -1, 16, 1, -1, -1, false, 'x', 'i', false, false, false, true, 0 }, \
{ 1255, {"proargnames"}, 1009, -1, -1, 17, 1, -1, -1, false, 'x', 'i', false, false, false, true, 0 }, \
{ 1255, {"prosrc"}, 25, -1, -1, 18, 0, -1, -1, false, 'x', 'i', false, false, false, true, 0 }, \
{ 1255, {"probin"}, 17, -1, -1, 19, 0, -1, -1, false, 'x', 'i', false, false, false, true, 0 }, \
{ 1255, {"proconfig"}, 1009, -1, -1, 20, 1, -1, -1, false, 'x', 'i', false, false, false, true, 0 }, \
{ 1255, {"proacl"}, 1034, -1, -1, 21, 1, -1, -1, false, 'x', 'i', false, false, false, true, 0 }
{ 1255, {"provariadic"}, 26, -1, 4, 7, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \
{ 1255, {"proisagg"}, 16, -1, 1, 8, 0, -1, -1, true, 'p', 'c', true, false, false, true, 0 }, \
{ 1255, {"prosecdef"}, 16, -1, 1, 9, 0, -1, -1, true, 'p', 'c', true, false, false, true, 0 }, \
{ 1255, {"proisstrict"}, 16, -1, 1, 10, 0, -1, -1, true, 'p', 'c', true, false, false, true, 0 }, \
{ 1255, {"proretset"}, 16, -1, 1, 11, 0, -1, -1, true, 'p', 'c', true, false, false, true, 0 }, \
{ 1255, {"provolatile"}, 18, -1, 1, 12, 0, -1, -1, true, 'p', 'c', true, false, false, true, 0 }, \
{ 1255, {"pronargs"}, 21, -1, 2, 13, 0, -1, -1, true, 'p', 's', true, false, false, true, 0 }, \
{ 1255, {"prorettype"}, 26, -1, 4, 14, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \
{ 1255, {"proargtypes"}, 30, -1, -1, 15, 1, -1, -1, false, 'p', 'i', true, false, false, true, 0 }, \
{ 1255, {"proallargtypes"}, 1028, -1, -1, 16, 1, -1, -1, false, 'x', 'i', false, false, false, true, 0 }, \
{ 1255, {"proargmodes"}, 1002, -1, -1, 17, 1, -1, -1, false, 'x', 'i', false, false, false, true, 0 }, \
{ 1255, {"proargnames"}, 1009, -1, -1, 18, 1, -1, -1, false, 'x', 'i', false, false, false, true, 0 }, \
{ 1255, {"prosrc"}, 25, -1, -1, 19, 0, -1, -1, false, 'x', 'i', false, false, false, true, 0 }, \
{ 1255, {"probin"}, 17, -1, -1, 20, 0, -1, -1, false, 'x', 'i', false, false, false, true, 0 }, \
{ 1255, {"proconfig"}, 1009, -1, -1, 21, 1, -1, -1, false, 'x', 'i', false, false, false, true, 0 }, \
{ 1255, {"proacl"}, 1034, -1, -1, 22, 1, -1, -1, false, 'x', 'i', false, false, false, true, 0 }
DATA(insert ( 1255 proname 19 -1 NAMEDATALEN 1 0 -1 -1 f p c t f f t 0));
DATA(insert ( 1255 pronamespace 26 -1 4 2 0 -1 -1 t p i t f f t 0));
......@@ -311,21 +312,22 @@ DATA(insert ( 1255 proowner 26 -1 4 3 0 -1 -1 t p i t f f t 0));
DATA(insert ( 1255 prolang 26 -1 4 4 0 -1 -1 t p i t f f t 0));
DATA(insert ( 1255 procost 700 -1 4 5 0 -1 -1 FLOAT4PASSBYVAL p i t f f t 0));
DATA(insert ( 1255 prorows 700 -1 4 6 0 -1 -1 FLOAT4PASSBYVAL p i t f f t 0));
DATA(insert ( 1255 proisagg 16 -1 1 7 0 -1 -1 t p c t f f t 0));
DATA(insert ( 1255 prosecdef 16 -1 1 8 0 -1 -1 t p c t f f t 0));
DATA(insert ( 1255 proisstrict 16 -1 1 9 0 -1 -1 t p c t f f t 0));
DATA(insert ( 1255 proretset 16 -1 1 10 0 -1 -1 t p c t f f t 0));
DATA(insert ( 1255 provolatile 18 -1 1 11 0 -1 -1 t p c t f f t 0));
DATA(insert ( 1255 pronargs 21 -1 2 12 0 -1 -1 t p s t f f t 0));
DATA(insert ( 1255 prorettype 26 -1 4 13 0 -1 -1 t p i t f f t 0));
DATA(insert ( 1255 proargtypes 30 -1 -1 14 1 -1 -1 f p i t f f t 0));
DATA(insert ( 1255 proallargtypes 1028 -1 -1 15 1 -1 -1 f x i f f f t 0));
DATA(insert ( 1255 proargmodes 1002 -1 -1 16 1 -1 -1 f x i f f f t 0));
DATA(insert ( 1255 proargnames 1009 -1 -1 17 1 -1 -1 f x i f f f t 0));
DATA(insert ( 1255 prosrc 25 -1 -1 18 0 -1 -1 f x i f f f t 0));
DATA(insert ( 1255 probin 17 -1 -1 19 0 -1 -1 f x i f f f t 0));
DATA(insert ( 1255 proconfig 1009 -1 -1 20 1 -1 -1 f x i f f f t 0));
DATA(insert ( 1255 proacl 1034 -1 -1 21 1 -1 -1 f x i f f f t 0));
DATA(insert ( 1255 provariadic 26 -1 4 7 0 -1 -1 t p i t f f t 0));
DATA(insert ( 1255 proisagg 16 -1 1 8 0 -1 -1 t p c t f f t 0));
DATA(insert ( 1255 prosecdef 16 -1 1 9 0 -1 -1 t p c t f f t 0));
DATA(insert ( 1255 proisstrict 16 -1 1 10 0 -1 -1 t p c t f f t 0));
DATA(insert ( 1255 proretset 16 -1 1 11 0 -1 -1 t p c t f f t 0));
DATA(insert ( 1255 provolatile 18 -1 1 12 0 -1 -1 t p c t f f t 0));
DATA(insert ( 1255 pronargs 21 -1 2 13 0 -1 -1 t p s t f f t 0));
DATA(insert ( 1255 prorettype 26 -1 4 14 0 -1 -1 t p i t f f t 0));
DATA(insert ( 1255 proargtypes 30 -1 -1 15 1 -1 -1 f p i t f f t 0));
DATA(insert ( 1255 proallargtypes 1028 -1 -1 16 1 -1 -1 f x i f f f t 0));
DATA(insert ( 1255 proargmodes 1002 -1 -1 17 1 -1 -1 f x i f f f t 0));
DATA(insert ( 1255 proargnames 1009 -1 -1 18 1 -1 -1 f x i f f f t 0));
DATA(insert ( 1255 prosrc 25 -1 -1 19 0 -1 -1 f x i f f f t 0));
DATA(insert ( 1255 probin 17 -1 -1 20 0 -1 -1 f x i f f f t 0));
DATA(insert ( 1255 proconfig 1009 -1 -1 21 1 -1 -1 f x i f f f t 0));
DATA(insert ( 1255 proacl 1034 -1 -1 22 1 -1 -1 f x i f f f t 0));
DATA(insert ( 1255 ctid 27 0 6 -1 0 -1 -1 f p s t f f t 0));
DATA(insert ( 1255 oid 26 0 4 -2 0 -1 -1 t p i t f f t 0));
DATA(insert ( 1255 xmin 28 0 4 -3 0 -1 -1 t p i t f f t 0));
......
......@@ -8,7 +8,7 @@
* Portions Copyright (c) 1996-2008, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
* $PostgreSQL: pgsql/src/include/catalog/pg_class.h,v 1.105 2008/03/27 03:57:34 tgl Exp $
* $PostgreSQL: pgsql/src/include/catalog/pg_class.h,v 1.106 2008/07/16 16:55:24 tgl Exp $
*
* NOTES
* the genbki.sh script reads this file and generates .bki
......@@ -131,7 +131,7 @@ DATA(insert OID = 1247 ( pg_type PGNSP 71 PGUID 0 1247 0 0 0 0 0 f f r 26 0 0
DESCR("");
DATA(insert OID = 1249 ( pg_attribute PGNSP 75 PGUID 0 1249 0 0 0 0 0 f f r 17 0 0 0 0 0 f f f f 3 _null_ _null_ ));
DESCR("");
DATA(insert OID = 1255 ( pg_proc PGNSP 81 PGUID 0 1255 0 0 0 0 0 f f r 21 0 0 0 0 0 t f f f 3 _null_ _null_ ));
DATA(insert OID = 1255 ( pg_proc PGNSP 81 PGUID 0 1255 0 0 0 0 0 f f r 22 0 0 0 0 0 t f f f 3 _null_ _null_ ));
DESCR("");
DATA(insert OID = 1259 ( pg_class PGNSP 83 PGUID 0 1259 0 0 0 0 0 f f r 27 0 0 0 0 0 t f f f 3 _null_ _null_ ));
DESCR("");
......
This diff is collapsed.
......@@ -53,6 +53,29 @@ WHERE p1.prolang = 0 OR p1.prorettype = 0 OR
-----+---------
(0 rows)
-- prosrc should never be null or empty
SELECT p1.oid, p1.proname
FROM pg_proc as p1
WHERE prosrc IS NULL OR prosrc = '' OR prosrc = '-';
oid | proname
-----+---------
(0 rows)
-- probin should be non-empty for C functions, null everywhere else
SELECT p1.oid, p1.proname
FROM pg_proc as p1
WHERE prolang = 13 AND (probin IS NULL OR probin = '' OR probin = '-');
oid | proname
-----+---------
(0 rows)
SELECT p1.oid, p1.proname
FROM pg_proc as p1
WHERE prolang != 13 AND probin IS NOT NULL;
oid | proname
-----+---------
(0 rows)
-- Look for conflicting proc definitions (same names and input datatypes).
-- (This test should be dead code now that we have the unique index
-- pg_proc_proname_args_nsp_index, but I'll leave it in anyway.)
......
......@@ -57,6 +57,20 @@ WHERE p1.prolang = 0 OR p1.prorettype = 0 OR
procost <= 0 OR
CASE WHEN proretset THEN prorows <= 0 ELSE prorows != 0 END;
-- prosrc should never be null or empty
SELECT p1.oid, p1.proname
FROM pg_proc as p1
WHERE prosrc IS NULL OR prosrc = '' OR prosrc = '-';
-- probin should be non-empty for C functions, null everywhere else
SELECT p1.oid, p1.proname
FROM pg_proc as p1
WHERE prolang = 13 AND (probin IS NULL OR probin = '' OR probin = '-');
SELECT p1.oid, p1.proname
FROM pg_proc as p1
WHERE prolang != 13 AND probin IS NOT NULL;
-- Look for conflicting proc definitions (same names and input datatypes).
-- (This test should be dead code now that we have the unique index
-- pg_proc_proname_args_nsp_index, but I'll leave it in anyway.)
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment