1
0
mirror of https://github.com/postgres/postgres.git synced 2025-11-29 23:43:17 +03:00

Support enum data types. Along the way, use macros for the values of

pg_type.typtype whereever practical.  Tom Dunstan, with some kibitzing
from Tom Lane.
This commit is contained in:
Tom Lane
2007-04-02 03:49:42 +00:00
parent a482a3e58b
commit 57690c6803
74 changed files with 2398 additions and 332 deletions

View File

@@ -7,7 +7,7 @@
* Copyright (c) 2002-2007, PostgreSQL Global Development Group
*
* IDENTIFICATION
* $PostgreSQL: pgsql/src/backend/utils/fmgr/funcapi.c,v 1.33 2007/02/01 19:10:28 momjian Exp $
* $PostgreSQL: pgsql/src/backend/utils/fmgr/funcapi.c,v 1.34 2007/04/02 03:49:39 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@@ -193,8 +193,8 @@ shutdown_MultiFuncCall(Datum arg)
* only when we couldn't resolve the actual rowtype for lack of information.
*
* The other hard case that this handles is resolution of polymorphism.
* We will never return ANYELEMENT or ANYARRAY, either as a scalar result
* type or as a component of a rowtype.
* We will never return ANYELEMENT, ANYARRAY or ANYENUM, either as a scalar
* result type or as a component of a rowtype.
*
* This function is relatively expensive --- in a function returning set,
* try to call it only the first time through.
@@ -338,7 +338,7 @@ internal_get_result_type(Oid funcid,
/*
* If scalar polymorphic result, try to resolve it.
*/
if (rettype == ANYARRAYOID || rettype == ANYELEMENTOID)
if (IsPolymorphicType(rettype))
{
Oid newrettype = exprType(call_expr);
@@ -389,8 +389,8 @@ internal_get_result_type(Oid funcid,
/*
* Given the result tuple descriptor for a function with OUT parameters,
* replace any polymorphic columns (ANYELEMENT/ANYARRAY) with correct data
* types deduced from the input arguments. Returns TRUE if able to deduce
* replace any polymorphic columns (ANYELEMENT/ANYARRAY/ANYENUM) with correct
* data types deduced from the input arguments. Returns TRUE if able to deduce
* all types, FALSE if not.
*/
static bool
@@ -401,6 +401,7 @@ resolve_polymorphic_tupdesc(TupleDesc tupdesc, oidvector *declared_args,
int nargs = declared_args->dim1;
bool have_anyelement_result = false;
bool have_anyarray_result = false;
bool have_anyenum = false;
Oid anyelement_type = InvalidOid;
Oid anyarray_type = InvalidOid;
int i;
@@ -416,6 +417,10 @@ resolve_polymorphic_tupdesc(TupleDesc tupdesc, oidvector *declared_args,
case ANYARRAYOID:
have_anyarray_result = true;
break;
case ANYENUMOID:
have_anyelement_result = true;
have_anyenum = true;
break;
default:
break;
}
@@ -435,6 +440,7 @@ resolve_polymorphic_tupdesc(TupleDesc tupdesc, oidvector *declared_args,
switch (declared_args->values[i])
{
case ANYELEMENTOID:
case ANYENUMOID:
if (!OidIsValid(anyelement_type))
anyelement_type = get_call_expr_argtype(call_expr, i);
break;
@@ -461,12 +467,17 @@ resolve_polymorphic_tupdesc(TupleDesc tupdesc, oidvector *declared_args,
anyelement_type,
ANYELEMENTOID);
/* Check for enum if needed */
if (have_anyenum && !type_is_enum(anyelement_type))
return false;
/* And finally replace the tuple column types as needed */
for (i = 0; i < natts; i++)
{
switch (tupdesc->attrs[i]->atttypid)
{
case ANYELEMENTOID:
case ANYENUMOID:
TupleDescInitEntry(tupdesc, i + 1,
NameStr(tupdesc->attrs[i]->attname),
anyelement_type,
@@ -490,8 +501,8 @@ resolve_polymorphic_tupdesc(TupleDesc tupdesc, oidvector *declared_args,
/*
* Given the declared argument types and modes for a function,
* replace any polymorphic types (ANYELEMENT/ANYARRAY) with correct data
* types deduced from the input arguments. Returns TRUE if able to deduce
* replace any polymorphic types (ANYELEMENT/ANYARRAY/ANYENUM) with correct
* data types deduced from the input arguments. Returns TRUE if able to deduce
* all types, FALSE if not. This is the same logic as
* resolve_polymorphic_tupdesc, but with a different argument representation.
*
@@ -517,6 +528,7 @@ resolve_polymorphic_argtypes(int numargs, Oid *argtypes, char *argmodes,
switch (argtypes[i])
{
case ANYELEMENTOID:
case ANYENUMOID:
if (argmode == PROARGMODE_OUT)
have_anyelement_result = true;
else
@@ -571,12 +583,15 @@ resolve_polymorphic_argtypes(int numargs, Oid *argtypes, char *argmodes,
anyelement_type,
ANYELEMENTOID);
/* XXX do we need to enforce ANYENUM here? I think not */
/* And finally replace the output column types as needed */
for (i = 0; i < numargs; i++)
{
switch (argtypes[i])
{
case ANYELEMENTOID:
case ANYENUMOID:
argtypes[i] = anyelement_type;
break;
case ANYARRAYOID:
@@ -603,12 +618,13 @@ get_type_func_class(Oid typid)
{
switch (get_typtype(typid))
{
case 'c':
case TYPTYPE_COMPOSITE:
return TYPEFUNC_COMPOSITE;
case 'b':
case 'd':
case TYPTYPE_BASE:
case TYPTYPE_DOMAIN:
case TYPTYPE_ENUM:
return TYPEFUNC_SCALAR;
case 'p':
case TYPTYPE_PSEUDO:
if (typid == RECORDOID)
return TYPEFUNC_RECORD;
@@ -840,7 +856,7 @@ get_func_result_name(Oid functionId)
* Given a pg_proc row for a function, return a tuple descriptor for the
* result rowtype, or NULL if the function does not have OUT parameters.
*
* Note that this does not handle resolution of ANYELEMENT/ANYARRAY types;
* Note that this does not handle resolution of polymorphic types;
* that is deliberate.
*/
TupleDesc