diff options
author | Tom Lane <tgl@sss.pgh.pa.us> | 2006-12-30 21:21:56 +0000 |
---|---|---|
committer | Tom Lane <tgl@sss.pgh.pa.us> | 2006-12-30 21:21:56 +0000 |
commit | 5725b9d9afc8c3ba24e94cbc7020889fe8ad7ef9 (patch) | |
tree | e1c8a77dbb660fa0de36528f19dc4f3cb81829d2 /src/backend/utils/adt/varchar.c | |
parent | 24b1f14eae0b83ef5d6b269ebf1ecae2f3acbb8c (diff) | |
download | postgresql-5725b9d9afc8c3ba24e94cbc7020889fe8ad7ef9.tar.gz postgresql-5725b9d9afc8c3ba24e94cbc7020889fe8ad7ef9.zip |
Support type modifiers for user-defined types, and pull most knowledge
about typmod representation for standard types out into type-specific
typmod I/O functions. Teodor Sigaev, with some editorialization by
Tom Lane.
Diffstat (limited to 'src/backend/utils/adt/varchar.c')
-rw-r--r-- | src/backend/utils/adt/varchar.c | 89 |
1 files changed, 88 insertions, 1 deletions
diff --git a/src/backend/utils/adt/varchar.c b/src/backend/utils/adt/varchar.c index 937cf96ebef..9cc2f5e34e3 100644 --- a/src/backend/utils/adt/varchar.c +++ b/src/backend/utils/adt/varchar.c @@ -8,7 +8,7 @@ * * * IDENTIFICATION - * $PostgreSQL: pgsql/src/backend/utils/adt/varchar.c,v 1.119 2006/10/04 00:30:00 momjian Exp $ + * $PostgreSQL: pgsql/src/backend/utils/adt/varchar.c,v 1.120 2006/12/30 21:21:54 tgl Exp $ * *------------------------------------------------------------------------- */ @@ -17,10 +17,65 @@ #include "access/hash.h" #include "libpq/pqformat.h" +#include "utils/array.h" #include "utils/builtins.h" #include "mb/pg_wchar.h" +/* common code for bpchartypmodin and varchartypmodin */ +static int32 +anychar_typmodin(ArrayType *ta, const char *typename) +{ + int32 typmod; + int32 *tl; + int n; + + tl = ArrayGetTypmods(ta, &n); + + /* + * we're not too tense about good error message here because grammar + * shouldn't allow wrong number of modifiers for CHAR + */ + if (n != 1) + ereport(ERROR, + (errcode(ERRCODE_INVALID_PARAMETER_VALUE), + errmsg("invalid type modifier"))); + + if (*tl < 1) + ereport(ERROR, + (errcode(ERRCODE_INVALID_PARAMETER_VALUE), + errmsg("length for type %s must be at least 1", typename))); + if (*tl > MaxAttrSize) + ereport(ERROR, + (errcode(ERRCODE_INVALID_PARAMETER_VALUE), + errmsg("length for type %s cannot exceed %d", + typename, MaxAttrSize))); + + /* + * For largely historical reasons, the typmod is VARHDRSZ plus the + * number of characters; there is enough client-side code that knows + * about that that we'd better not change it. + */ + typmod = VARHDRSZ + *tl; + + return typmod; +} + +/* common code for bpchartypmodout and varchartypmodout */ +static char * +anychar_typmodout(int32 typmod) +{ + char *res = (char *) palloc(64); + + if (typmod > VARHDRSZ) + snprintf(res, 64, "(%d)", (int) (typmod - VARHDRSZ)); + else + *res = '\0'; + + return res; +} + + /* * CHAR() and VARCHAR() types are part of the ANSI SQL standard. CHAR() * is for blank-padded string whose length is specified in CREATE TABLE. @@ -359,6 +414,22 @@ name_bpchar(PG_FUNCTION_ARGS) PG_RETURN_BPCHAR_P(result); } +Datum +bpchartypmodin(PG_FUNCTION_ARGS) +{ + ArrayType *ta = PG_GETARG_ARRAYTYPE_P(0); + + PG_RETURN_INT32(anychar_typmodin(ta, "char")); +} + +Datum +bpchartypmodout(PG_FUNCTION_ARGS) +{ + int32 typmod = PG_GETARG_INT32(0); + + PG_RETURN_CSTRING(anychar_typmodout(typmod)); +} + /***************************************************************************** * varchar - varchar(n) @@ -536,6 +607,22 @@ varchar(PG_FUNCTION_ARGS) PG_RETURN_VARCHAR_P(result); } +Datum +varchartypmodin(PG_FUNCTION_ARGS) +{ + ArrayType *ta = PG_GETARG_ARRAYTYPE_P(0); + + PG_RETURN_INT32(anychar_typmodin(ta, "varchar")); +} + +Datum +varchartypmodout(PG_FUNCTION_ARGS) +{ + int32 typmod = PG_GETARG_INT32(0); + + PG_RETURN_CSTRING(anychar_typmodout(typmod)); +} + /***************************************************************************** * Exported functions |