Support arrays of composite types, including the rowtypes of regular tables

and views (but not system catalogs, nor sequences or toast tables).  Get rid
of the hardwired convention that a type's array type is named exactly "_type",
instead using a new column pg_type.typarray to provide the linkage.  (It still
will be named "_type", though, except in odd corner cases such as
maximum-length type names.)

Along the way, make tracking of owner and schema dependencies for types more
uniform: a type directly created by the user has these dependencies, while a
table rowtype or auto-generated array type does not have them, but depends on
its parent object instead.

David Fetter, Andrew Dunstan, Tom Lane
This commit is contained in:
Tom Lane 2007-05-11 17:57:14 +00:00
parent b1110aaa8b
commit bc8036fc66
25 changed files with 698 additions and 407 deletions

View File

@ -1,4 +1,4 @@
<!-- $PostgreSQL: pgsql/doc/src/sgml/array.sgml,v 1.60 2007/04/06 19:22:38 tgl Exp $ --> <!-- $PostgreSQL: pgsql/doc/src/sgml/array.sgml,v 1.61 2007/05/11 17:57:11 tgl Exp $ -->
<sect1 id="arrays"> <sect1 id="arrays">
<title>Arrays</title> <title>Arrays</title>
@ -10,8 +10,9 @@
<para> <para>
<productname>PostgreSQL</productname> allows columns of a table to be <productname>PostgreSQL</productname> allows columns of a table to be
defined as variable-length multidimensional arrays. Arrays of any defined as variable-length multidimensional arrays. Arrays of any
built-in or user-defined base type or enum type can be created. built-in or user-defined base type, enum type, or composite type
(Arrays of composite types or domains are not yet supported, however.) can be created.
Arrays of domains are not yet supported.
</para> </para>
<sect2> <sect2>

View File

@ -1,4 +1,4 @@
<!-- $PostgreSQL: pgsql/doc/src/sgml/catalogs.sgml,v 2.150 2007/04/06 22:33:41 tgl Exp $ --> <!-- $PostgreSQL: pgsql/doc/src/sgml/catalogs.sgml,v 2.151 2007/05/11 17:57:11 tgl Exp $ -->
<!-- <!--
Documentation of the system catalogs, directed toward PostgreSQL developers Documentation of the system catalogs, directed toward PostgreSQL developers
--> -->
@ -4524,6 +4524,17 @@
</entry> </entry>
</row> </row>
<row>
<entry><structfield>typarray</structfield></entry>
<entry><type>oid</type></entry>
<entry><literal><link linkend="catalog-pg-type"><structname>pg_type</structname></link>.oid</literal></entry>
<entry>
If <structfield>typarray</structfield> is not 0 then it
identifies another row in <structname>pg_type</structname>, which
is the <quote>true</quote> array type having this type as element
</entry>
</row>
<row> <row>
<entry><structfield>typinput</structfield></entry> <entry><structfield>typinput</structfield></entry>
<entry><type>regproc</type></entry> <entry><type>regproc</type></entry>
@ -4686,9 +4697,10 @@
<entry></entry> <entry></entry>
<entry><para> <entry><para>
<structfield>typndims</structfield> is the number of array dimensions <structfield>typndims</structfield> is the number of array dimensions
for a domain that is an array (that is, <structfield>typbasetype</> is an array type; for a domain that is an array (that is, <structfield>typbasetype</> is
the domain's <structfield>typelem</> will match the base type's <structfield>typelem</structfield>). an array type; the domain's <structfield>typelem</> will match the base
Zero for types other than array domains type's <structfield>typelem</structfield>).
Zero for types other than domains over array types
</para></entry> </para></entry>
</row> </row>

View File

@ -1,5 +1,5 @@
<!-- <!--
$PostgreSQL: pgsql/doc/src/sgml/ref/create_type.sgml,v 1.69 2007/04/02 03:49:37 tgl Exp $ $PostgreSQL: pgsql/doc/src/sgml/ref/create_type.sgml,v 1.70 2007/05/11 17:57:11 tgl Exp $
PostgreSQL documentation PostgreSQL documentation
--> -->
@ -312,15 +312,17 @@ CREATE TYPE <replaceable class="parameter">name</replaceable>
<title>Array Types</title> <title>Array Types</title>
<para> <para>
Whenever a user-defined base or enum data type is created, Whenever a user-defined type is created,
<productname>PostgreSQL</productname> automatically creates an <productname>PostgreSQL</productname> automatically creates an
associated array type, whose name consists of the base type's associated array type, whose name consists of the base type's
name prepended with an underscore. The parser understands this name prepended with an underscore, and truncated if necessary to keep
naming convention, and translates requests for columns of type it less than <symbol>NAMEDATALEN</symbol> bytes long. (If the name
<literal>foo[]</> into requests for type <literal>_foo</>. so generated collides with an existing type name, the process is
The implicitly-created array type is variable length and uses the repeated until a non-colliding name is found.)
This implicitly-created array type is variable length and uses the
built-in input and output functions <literal>array_in</> and built-in input and output functions <literal>array_in</> and
<literal>array_out</>. <literal>array_out</>. The array type tracks any changes in its
element type's owner or schema, and is dropped if the element type is.
</para> </para>
<para> <para>
@ -330,10 +332,9 @@ CREATE TYPE <replaceable class="parameter">name</replaceable>
making a fixed-length type that happens to be internally an array of a number of making a fixed-length type that happens to be internally an array of a number of
identical things, and you want to allow these things to be accessed identical things, and you want to allow these things to be accessed
directly by subscripting, in addition to whatever operations you plan directly by subscripting, in addition to whatever operations you plan
to provide for the type as a whole. For example, type <type>name</> to provide for the type as a whole. For example, type <type>point</>
allows its constituent <type>char</> elements to be accessed this way. is represented as just two floating-point numbers, which it allows to be
A 2-D <type>point</> type could allow its two component numbers to be accessed as <literal>point[0]</> and <literal>point[1]</>.
accessed like <literal>point[0]</> and <literal>point[1]</>.
Note that Note that
this facility only works for fixed-length types whose internal form this facility only works for fixed-length types whose internal form
is exactly a sequence of identical fixed-length fields. A subscriptable is exactly a sequence of identical fixed-length fields. A subscriptable
@ -529,12 +530,15 @@ CREATE TYPE <replaceable class="parameter">name</replaceable>
<title>Notes</title> <title>Notes</title>
<para> <para>
User-defined type names should not begin with the underscore character It is best to avoid using type names that begin with the underscore
(<literal>_</literal>) and should only be 62 characters character (<literal>_</literal>). <productname>PostgreSQL</productname>
long (or in general <symbol>NAMEDATALEN</symbol> - 2, rather than forms the name of an array type by prepending one or more underscores
the <symbol>NAMEDATALEN</symbol> - 1 characters allowed for other to the element type's name, and these names may collide with user-defined
names). Type names beginning with underscore are reserved for type names that begin with underscore. While the system will modify
internally-created array type names. generated array type names to avoid collisions, this does not help if the
conflicting array type already exists when you try to create your type.
Also, various old client software may assume that names beginning with
underscores always represent arrays.
</para> </para>
<para> <para>

View File

@ -1,4 +1,4 @@
<!-- $PostgreSQL: pgsql/doc/src/sgml/syntax.sgml,v 1.117 2007/02/20 14:04:50 momjian Exp $ --> <!-- $PostgreSQL: pgsql/doc/src/sgml/syntax.sgml,v 1.118 2007/05/11 17:57:11 tgl Exp $ -->
<chapter id="sql-syntax"> <chapter id="sql-syntax">
<title>SQL Syntax</title> <title>SQL Syntax</title>
@ -131,10 +131,10 @@ INSERT INTO MY_TABLE VALUES (3, 'hi there');
<para> <para>
<indexterm><primary>identifier</primary><secondary>length</secondary></indexterm> <indexterm><primary>identifier</primary><secondary>length</secondary></indexterm>
The system uses no more than <symbol>NAMEDATALEN</symbol>-1 The system uses no more than <symbol>NAMEDATALEN</symbol>-1
characters of an identifier; longer names can be written in bytes of an identifier; longer names can be written in
commands, but they will be truncated. By default, commands, but they will be truncated. By default,
<symbol>NAMEDATALEN</symbol> is 64 so the maximum identifier <symbol>NAMEDATALEN</symbol> is 64 so the maximum identifier
length is 63. If this limit is problematic, it can be raised by length is 63 bytes. If this limit is problematic, it can be raised by
changing the <symbol>NAMEDATALEN</symbol> constant in changing the <symbol>NAMEDATALEN</symbol> constant in
<filename>src/include/pg_config_manual.h</filename>. <filename>src/include/pg_config_manual.h</filename>.
</para> </para>

View File

@ -1,4 +1,4 @@
$PostgreSQL: pgsql/src/backend/catalog/README,v 1.10 2006/07/31 01:16:36 tgl Exp $ $PostgreSQL: pgsql/src/backend/catalog/README,v 1.11 2007/05/11 17:57:11 tgl Exp $
This directory contains .c files that manipulate the system catalogs; This directory contains .c files that manipulate the system catalogs;
src/include/catalog contains the .h files that define the structure src/include/catalog contains the .h files that define the structure
@ -86,9 +86,9 @@ general) assumes that the fixed-length portions of all system catalog
tuples are in fact present, because it maps C struct declarations onto tuples are in fact present, because it maps C struct declarations onto
them. Thus, the variable-length fields must all be at the end, and them. Thus, the variable-length fields must all be at the end, and
only the variable-length fields of a catalog tuple are permitted to be only the variable-length fields of a catalog tuple are permitted to be
NULL. For example, if you set pg_type.typdelim to be NULL, a NULL. For example, if you set pg_type.typrelid to be NULL, a
piece of code will likely perform "typetup->typdelim" (or, worse, piece of code will likely perform "typetup->typrelid" (or, worse,
"typetyp->typelem", which follows typdelim). This will result in "typetyp->typelem", which follows typrelid). This will result in
random errors or even segmentation violations. Hence, do NOT insert random errors or even segmentation violations. Hence, do NOT insert
catalog tuples that contain NULL attributes except in their catalog tuples that contain NULL attributes except in their
variable-length portions! (The bootstrapping code is fairly good about variable-length portions! (The bootstrapping code is fairly good about

View File

@ -8,7 +8,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $PostgreSQL: pgsql/src/backend/catalog/heap.c,v 1.318 2007/04/02 03:49:37 tgl Exp $ * $PostgreSQL: pgsql/src/backend/catalog/heap.c,v 1.319 2007/05/11 17:57:11 tgl Exp $
* *
* *
* INTERFACE ROUTINES * INTERFACE ROUTINES
@ -45,6 +45,7 @@
#include "catalog/pg_statistic.h" #include "catalog/pg_statistic.h"
#include "catalog/pg_type.h" #include "catalog/pg_type.h"
#include "commands/tablecmds.h" #include "commands/tablecmds.h"
#include "commands/typecmds.h"
#include "miscadmin.h" #include "miscadmin.h"
#include "optimizer/clauses.h" #include "optimizer/clauses.h"
#include "optimizer/var.h" #include "optimizer/var.h"
@ -69,7 +70,8 @@ static void AddNewRelationTuple(Relation pg_class_desc,
static Oid AddNewRelationType(const char *typeName, static Oid AddNewRelationType(const char *typeName,
Oid typeNamespace, Oid typeNamespace,
Oid new_rel_oid, Oid new_rel_oid,
char new_rel_kind); char new_rel_kind,
Oid new_array_type);
static void RelationRemoveInheritance(Oid relid); static void RelationRemoveInheritance(Oid relid);
static void StoreRelCheck(Relation rel, char *ccname, char *ccbin); static void StoreRelCheck(Relation rel, char *ccname, char *ccbin);
static void StoreConstraints(Relation rel, TupleDesc tupdesc); static void StoreConstraints(Relation rel, TupleDesc tupdesc);
@ -401,26 +403,55 @@ CheckAttributeType(const char *attname, Oid atttypid)
{ {
char att_typtype = get_typtype(atttypid); char att_typtype = get_typtype(atttypid);
/*
* Warn user, but don't fail, if column to be created has UNKNOWN type
* (usually as a result of a 'retrieve into' - jolly)
*
* Refuse any attempt to create a pseudo-type column.
*/
if (atttypid == UNKNOWNOID) if (atttypid == UNKNOWNOID)
{
/*
* Warn user, but don't fail, if column to be created has UNKNOWN type
* (usually as a result of a 'retrieve into' - jolly)
*/
ereport(WARNING, ereport(WARNING,
(errcode(ERRCODE_INVALID_TABLE_DEFINITION), (errcode(ERRCODE_INVALID_TABLE_DEFINITION),
errmsg("column \"%s\" has type \"unknown\"", attname), errmsg("column \"%s\" has type \"unknown\"", attname),
errdetail("Proceeding with relation creation anyway."))); errdetail("Proceeding with relation creation anyway.")));
}
else if (att_typtype == TYPTYPE_PSEUDO) else if (att_typtype == TYPTYPE_PSEUDO)
{ {
/* Special hack for pg_statistic: allow ANYARRAY during initdb */ /*
* Refuse any attempt to create a pseudo-type column, except for
* a special hack for pg_statistic: allow ANYARRAY during initdb
*/
if (atttypid != ANYARRAYOID || IsUnderPostmaster) if (atttypid != ANYARRAYOID || IsUnderPostmaster)
ereport(ERROR, ereport(ERROR,
(errcode(ERRCODE_INVALID_TABLE_DEFINITION), (errcode(ERRCODE_INVALID_TABLE_DEFINITION),
errmsg("column \"%s\" has pseudo-type %s", errmsg("column \"%s\" has pseudo-type %s",
attname, format_type_be(atttypid)))); attname, format_type_be(atttypid))));
} }
else if (att_typtype == TYPTYPE_COMPOSITE)
{
/*
* For a composite type, recurse into its attributes. You might
* think this isn't necessary, but since we allow system catalogs
* to break the rule, we have to guard against the case.
*/
Relation relation;
TupleDesc tupdesc;
int i;
relation = relation_open(get_typ_typrelid(atttypid), AccessShareLock);
tupdesc = RelationGetDescr(relation);
for (i = 0; i < tupdesc->natts; i++)
{
Form_pg_attribute attr = tupdesc->attrs[i];
if (attr->attisdropped)
continue;
CheckAttributeType(NameStr(attr->attname), attr->atttypid);
}
relation_close(relation, AccessShareLock);
}
} }
/* -------------------------------- /* --------------------------------
@ -710,16 +741,18 @@ static Oid
AddNewRelationType(const char *typeName, AddNewRelationType(const char *typeName,
Oid typeNamespace, Oid typeNamespace,
Oid new_rel_oid, Oid new_rel_oid,
char new_rel_kind) char new_rel_kind,
Oid new_array_type)
{ {
return return
TypeCreate(typeName, /* type name */ TypeCreate(InvalidOid, /* no predetermined OID */
typeName, /* type name */
typeNamespace, /* type namespace */ typeNamespace, /* type namespace */
new_rel_oid, /* relation oid */ new_rel_oid, /* relation oid */
new_rel_kind, /* relation kind */ new_rel_kind, /* relation kind */
-1, /* internal size (varlena) */ -1, /* internal size (varlena) */
TYPTYPE_COMPOSITE, /* type-type (composite) */ TYPTYPE_COMPOSITE, /* type-type (composite) */
',', /* default array delimiter */ DEFAULT_TYPDELIM, /* default array delimiter */
F_RECORD_IN, /* input procedure */ F_RECORD_IN, /* input procedure */
F_RECORD_OUT, /* output procedure */ F_RECORD_OUT, /* output procedure */
F_RECORD_RECV, /* receive procedure */ F_RECORD_RECV, /* receive procedure */
@ -728,6 +761,8 @@ AddNewRelationType(const char *typeName,
InvalidOid, /* typmodout procedure - none */ InvalidOid, /* typmodout procedure - none */
InvalidOid, /* analyze procedure - default */ InvalidOid, /* analyze procedure - default */
InvalidOid, /* array element type - irrelevant */ InvalidOid, /* array element type - irrelevant */
false, /* this is not an array type */
new_array_type, /* array type if any */
InvalidOid, /* domain base type - irrelevant */ InvalidOid, /* domain base type - irrelevant */
NULL, /* default value - none */ NULL, /* default value - none */
NULL, /* default binary representation */ NULL, /* default binary representation */
@ -763,6 +798,7 @@ heap_create_with_catalog(const char *relname,
Relation pg_class_desc; Relation pg_class_desc;
Relation new_rel_desc; Relation new_rel_desc;
Oid new_type_oid; Oid new_type_oid;
Oid new_array_oid = InvalidOid;
pg_class_desc = heap_open(RelationRelationId, RowExclusiveLock); pg_class_desc = heap_open(RelationRelationId, RowExclusiveLock);
@ -805,7 +841,24 @@ heap_create_with_catalog(const char *relname,
Assert(relid == RelationGetRelid(new_rel_desc)); Assert(relid == RelationGetRelid(new_rel_desc));
/* /*
* since defining a relation also defines a complex type, we add a new * Decide whether to create an array type over the relation's rowtype.
* We do not create any array types for system catalogs (ie, those made
* during initdb). We create array types for regular relations, views,
* and composite types ... but not, eg, for toast tables or sequences.
*/
if (IsUnderPostmaster && (relkind == RELKIND_RELATION ||
relkind == RELKIND_VIEW ||
relkind == RELKIND_COMPOSITE_TYPE))
{
/* OK, so pre-assign a type OID for the array type */
Relation pg_type = heap_open(TypeRelationId, AccessShareLock);
new_array_oid = GetNewOid(pg_type);
heap_close(pg_type, AccessShareLock);
}
/*
* Since defining a relation also defines a complex type, we add a new
* system type corresponding to the new relation. * system type corresponding to the new relation.
* *
* NOTE: we could get a unique-index failure here, in case the same name * NOTE: we could get a unique-index failure here, in case the same name
@ -814,7 +867,47 @@ heap_create_with_catalog(const char *relname,
new_type_oid = AddNewRelationType(relname, new_type_oid = AddNewRelationType(relname,
relnamespace, relnamespace,
relid, relid,
relkind); relkind,
new_array_oid);
/*
* Now make the array type if wanted.
*/
if (OidIsValid(new_array_oid))
{
char *relarrayname;
relarrayname = makeArrayTypeName(relname, relnamespace);
TypeCreate(new_array_oid, /* force the type's OID to this */
relarrayname, /* Array type name */
relnamespace, /* Same namespace as parent */
InvalidOid, /* Not composite, no relationOid */
0, /* relkind, also N/A here */
-1, /* Internal size (varlena) */
TYPTYPE_BASE, /* Not composite - typelem is */
DEFAULT_TYPDELIM, /* default array delimiter */
F_ARRAY_IN, /* array input proc */
F_ARRAY_OUT, /* array output proc */
F_ARRAY_RECV, /* array recv (bin) proc */
F_ARRAY_SEND, /* array send (bin) proc */
InvalidOid, /* typmodin procedure - none */
InvalidOid, /* typmodout procedure - none */
InvalidOid, /* analyze procedure - default */
new_type_oid, /* array element type - the rowtype */
true, /* yes, this is an array type */
InvalidOid, /* this has no array type */
InvalidOid, /* domain base type - irrelevant */
NULL, /* default value - none */
NULL, /* default binary representation */
false, /* passed by reference */
'd', /* alignment - must be the largest! */
'x', /* fully TOASTable */
-1, /* typmod */
0, /* array dimensions for typBaseType */
false); /* Type NOT NULL */
pfree(relarrayname);
}
/* /*
* now create an entry in pg_class for the relation. * now create an entry in pg_class for the relation.
@ -838,13 +931,15 @@ heap_create_with_catalog(const char *relname,
oidislocal, oidinhcount); oidislocal, oidinhcount);
/* /*
* make a dependency link to force the relation to be deleted if its * Make a dependency link to force the relation to be deleted if its
* namespace is. Skip this in bootstrap mode, since we don't make * namespace is. Also make a dependency link to its owner.
* dependencies while bootstrapping.
* *
* Also make a dependency link to its owner. * For composite types, these dependencies are tracked for the pg_type
* entry, so we needn't record them here. Also, skip this in bootstrap
* mode, since we don't make dependencies while bootstrapping.
*/ */
if (!IsBootstrapProcessingMode()) if (relkind != RELKIND_COMPOSITE_TYPE &&
!IsBootstrapProcessingMode())
{ {
ObjectAddress myself, ObjectAddress myself,
referenced; referenced;
@ -857,13 +952,7 @@ heap_create_with_catalog(const char *relname,
referenced.objectSubId = 0; referenced.objectSubId = 0;
recordDependencyOn(&myself, &referenced, DEPENDENCY_NORMAL); recordDependencyOn(&myself, &referenced, DEPENDENCY_NORMAL);
/* recordDependencyOnOwner(RelationRelationId, relid, ownerid);
* For composite types, the dependency on owner is tracked for the
* pg_type entry, so don't record it here. All other relkinds need
* their ownership tracked.
*/
if (relkind != RELKIND_COMPOSITE_TYPE)
recordDependencyOnOwner(RelationRelationId, relid, ownerid);
} }
/* /*

View File

@ -8,7 +8,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $PostgreSQL: pgsql/src/backend/catalog/pg_shdepend.c,v 1.17 2007/03/03 19:32:54 neilc Exp $ * $PostgreSQL: pgsql/src/backend/catalog/pg_shdepend.c,v 1.18 2007/05/11 17:57:12 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
@ -1254,7 +1254,7 @@ shdepReassignOwned(List *roleids, Oid newrole)
break; break;
case TypeRelationId: case TypeRelationId:
AlterTypeOwnerInternal(sdepForm->objid, newrole); AlterTypeOwnerInternal(sdepForm->objid, newrole, true);
break; break;
case OperatorRelationId: case OperatorRelationId:

View File

@ -8,7 +8,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $PostgreSQL: pgsql/src/backend/catalog/pg_type.c,v 1.111 2007/04/02 03:49:37 tgl Exp $ * $PostgreSQL: pgsql/src/backend/catalog/pg_type.c,v 1.112 2007/05/11 17:57:12 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
@ -22,6 +22,7 @@
#include "catalog/pg_type.h" #include "catalog/pg_type.h"
#include "commands/typecmds.h" #include "commands/typecmds.h"
#include "miscadmin.h" #include "miscadmin.h"
#include "parser/scansup.h"
#include "utils/acl.h" #include "utils/acl.h"
#include "utils/builtins.h" #include "utils/builtins.h"
#include "utils/fmgroids.h" #include "utils/fmgroids.h"
@ -90,6 +91,7 @@ TypeShellMake(const char *typeName, Oid typeNamespace)
values[i++] = CharGetDatum(DEFAULT_TYPDELIM); /* typdelim */ values[i++] = CharGetDatum(DEFAULT_TYPDELIM); /* typdelim */
values[i++] = ObjectIdGetDatum(InvalidOid); /* typrelid */ values[i++] = ObjectIdGetDatum(InvalidOid); /* typrelid */
values[i++] = ObjectIdGetDatum(InvalidOid); /* typelem */ values[i++] = ObjectIdGetDatum(InvalidOid); /* typelem */
values[i++] = ObjectIdGetDatum(InvalidOid); /* typarray */
values[i++] = ObjectIdGetDatum(F_SHELL_IN); /* typinput */ values[i++] = ObjectIdGetDatum(F_SHELL_IN); /* typinput */
values[i++] = ObjectIdGetDatum(F_SHELL_OUT); /* typoutput */ values[i++] = ObjectIdGetDatum(F_SHELL_OUT); /* typoutput */
values[i++] = ObjectIdGetDatum(InvalidOid); /* typreceive */ values[i++] = ObjectIdGetDatum(InvalidOid); /* typreceive */
@ -135,6 +137,7 @@ TypeShellMake(const char *typeName, Oid typeNamespace)
InvalidOid, InvalidOid,
InvalidOid, InvalidOid,
InvalidOid, InvalidOid,
false,
InvalidOid, InvalidOid,
NULL, NULL,
false); false);
@ -153,13 +156,16 @@ TypeShellMake(const char *typeName, Oid typeNamespace)
* *
* This does all the necessary work needed to define a new type. * This does all the necessary work needed to define a new type.
* *
* Returns the OID assigned to the new type. * Returns the OID assigned to the new type. If newTypeOid is
* zero (the normal case), a new OID is created; otherwise we
* use exactly that OID.
* ---------------------------------------------------------------- * ----------------------------------------------------------------
*/ */
Oid Oid
TypeCreate(const char *typeName, TypeCreate(Oid newTypeOid,
const char *typeName,
Oid typeNamespace, Oid typeNamespace,
Oid relationOid, /* only for composite types */ Oid relationOid, /* only for relation rowtypes */
char relationKind, /* ditto */ char relationKind, /* ditto */
int16 internalSize, int16 internalSize,
char typeType, char typeType,
@ -172,6 +178,8 @@ TypeCreate(const char *typeName,
Oid typmodoutProcedure, Oid typmodoutProcedure,
Oid analyzeProcedure, Oid analyzeProcedure,
Oid elementType, Oid elementType,
bool isImplicitArray,
Oid arrayType,
Oid baseType, Oid baseType,
const char *defaultTypeValue, /* human readable rep */ const char *defaultTypeValue, /* human readable rep */
char *defaultTypeBin, /* cooked rep */ char *defaultTypeBin, /* cooked rep */
@ -243,9 +251,9 @@ TypeCreate(const char *typeName,
values[i++] = CharGetDatum(typeType); /* typtype */ values[i++] = CharGetDatum(typeType); /* typtype */
values[i++] = BoolGetDatum(true); /* typisdefined */ values[i++] = BoolGetDatum(true); /* typisdefined */
values[i++] = CharGetDatum(typDelim); /* typdelim */ values[i++] = CharGetDatum(typDelim); /* typdelim */
values[i++] = ObjectIdGetDatum(typeType == TYPTYPE_COMPOSITE ? values[i++] = ObjectIdGetDatum(relationOid); /* typrelid */
relationOid : InvalidOid); /* typrelid */
values[i++] = ObjectIdGetDatum(elementType); /* typelem */ values[i++] = ObjectIdGetDatum(elementType); /* typelem */
values[i++] = ObjectIdGetDatum(arrayType); /* typarray */
values[i++] = ObjectIdGetDatum(inputProcedure); /* typinput */ values[i++] = ObjectIdGetDatum(inputProcedure); /* typinput */
values[i++] = ObjectIdGetDatum(outputProcedure); /* typoutput */ values[i++] = ObjectIdGetDatum(outputProcedure); /* typoutput */
values[i++] = ObjectIdGetDatum(receiveProcedure); /* typreceive */ values[i++] = ObjectIdGetDatum(receiveProcedure); /* typreceive */
@ -310,6 +318,10 @@ TypeCreate(const char *typeName,
if (((Form_pg_type) GETSTRUCT(tup))->typowner != GetUserId()) if (((Form_pg_type) GETSTRUCT(tup))->typowner != GetUserId())
aclcheck_error(ACLCHECK_NOT_OWNER, ACL_KIND_TYPE, typeName); aclcheck_error(ACLCHECK_NOT_OWNER, ACL_KIND_TYPE, typeName);
/* trouble if caller wanted to force the OID */
if (OidIsValid(newTypeOid))
elog(ERROR, "cannot assign new OID to existing shell type");
/* /*
* Okay to update existing shell type tuple * Okay to update existing shell type tuple
*/ */
@ -331,6 +343,10 @@ TypeCreate(const char *typeName,
values, values,
nulls); nulls);
/* Force the OID if requested by caller, else heap_insert does it */
if (OidIsValid(newTypeOid))
HeapTupleSetOid(tup, newTypeOid);
typeObjectId = simple_heap_insert(pg_type_desc, tup); typeObjectId = simple_heap_insert(pg_type_desc, tup);
} }
@ -354,6 +370,7 @@ TypeCreate(const char *typeName,
typmodoutProcedure, typmodoutProcedure,
analyzeProcedure, analyzeProcedure,
elementType, elementType,
isImplicitArray,
baseType, baseType,
(defaultTypeBin ? (defaultTypeBin ?
stringToNode(defaultTypeBin) : stringToNode(defaultTypeBin) :
@ -378,8 +395,8 @@ TypeCreate(const char *typeName,
void void
GenerateTypeDependencies(Oid typeNamespace, GenerateTypeDependencies(Oid typeNamespace,
Oid typeObjectId, Oid typeObjectId,
Oid relationOid, /* only for composite types */ Oid relationOid, /* only for relation rowtypes */
char relationKind, /* ditto */ char relationKind, /* ditto */
Oid owner, Oid owner,
Oid inputProcedure, Oid inputProcedure,
Oid outputProcedure, Oid outputProcedure,
@ -389,6 +406,7 @@ GenerateTypeDependencies(Oid typeNamespace,
Oid typmodoutProcedure, Oid typmodoutProcedure,
Oid analyzeProcedure, Oid analyzeProcedure,
Oid elementType, Oid elementType,
bool isImplicitArray,
Oid baseType, Oid baseType,
Node *defaultExpr, Node *defaultExpr,
bool rebuild) bool rebuild)
@ -406,14 +424,23 @@ GenerateTypeDependencies(Oid typeNamespace,
myself.objectId = typeObjectId; myself.objectId = typeObjectId;
myself.objectSubId = 0; myself.objectSubId = 0;
/* dependency on namespace */ /*
/* skip for relation rowtype, since we have indirect dependency */ * Make dependency on namespace and shared dependency on owner.
if (!OidIsValid(relationOid)) *
* For a relation rowtype (that's not a composite type), we should skip
* these because we'll depend on them indirectly through the pg_class
* entry. Likewise, skip for implicit arrays since we'll depend on them
* through the element type.
*/
if ((!OidIsValid(relationOid) || relationKind == RELKIND_COMPOSITE_TYPE) &&
!isImplicitArray)
{ {
referenced.classId = NamespaceRelationId; referenced.classId = NamespaceRelationId;
referenced.objectId = typeNamespace; referenced.objectId = typeNamespace;
referenced.objectSubId = 0; referenced.objectSubId = 0;
recordDependencyOn(&myself, &referenced, DEPENDENCY_NORMAL); recordDependencyOn(&myself, &referenced, DEPENDENCY_NORMAL);
recordDependencyOnOwner(TypeRelationId, typeObjectId, owner);
} }
/* Normal dependencies on the I/O functions */ /* Normal dependencies on the I/O functions */
@ -495,17 +522,17 @@ GenerateTypeDependencies(Oid typeNamespace,
} }
/* /*
* If the type is an array type, mark it auto-dependent on the base type. * If the type is an implicitly-created array type, mark it as internally
* (This is a compromise between the typical case where the array type is * dependent on the element type. Otherwise, if it has an element type,
* automatically generated and the case where it is manually created: we'd * the dependency is a normal one.
* prefer INTERNAL for the former case and NORMAL for the latter.)
*/ */
if (OidIsValid(elementType)) if (OidIsValid(elementType))
{ {
referenced.classId = TypeRelationId; referenced.classId = TypeRelationId;
referenced.objectId = elementType; referenced.objectId = elementType;
referenced.objectSubId = 0; referenced.objectSubId = 0;
recordDependencyOn(&myself, &referenced, DEPENDENCY_AUTO); recordDependencyOn(&myself, &referenced,
isImplicitArray ? DEPENDENCY_INTERNAL : DEPENDENCY_NORMAL);
} }
/* Normal dependency from a domain to its base type. */ /* Normal dependency from a domain to its base type. */
@ -520,9 +547,6 @@ GenerateTypeDependencies(Oid typeNamespace,
/* Normal dependency on the default expression. */ /* Normal dependency on the default expression. */
if (defaultExpr) if (defaultExpr)
recordDependencyOnExpr(&myself, defaultExpr, NIL, DEPENDENCY_NORMAL); recordDependencyOnExpr(&myself, defaultExpr, NIL, DEPENDENCY_NORMAL);
/* Shared dependency on owner. */
recordDependencyOnOwner(TypeRelationId, typeObjectId, owner);
} }
/* /*
@ -570,21 +594,47 @@ TypeRename(const char *oldTypeName, Oid typeNamespace,
heap_close(pg_type_desc, RowExclusiveLock); heap_close(pg_type_desc, RowExclusiveLock);
} }
/* /*
* makeArrayTypeName(typeName); * makeArrayTypeName(typeName)
* - given a base type name, make an array of type name out of it * - given a base type name, make an array type name for it
* *
* the caller is responsible for pfreeing the result * the caller is responsible for pfreeing the result
*/ */
char * char *
makeArrayTypeName(const char *typeName) makeArrayTypeName(const char *typeName, Oid typeNamespace)
{ {
char *arr; char *arr;
int i;
Relation pg_type_desc;
if (!typeName) /*
return NULL; * The idea is to prepend underscores as needed until we make a name
* that doesn't collide with anything...
*/
arr = palloc(NAMEDATALEN); arr = palloc(NAMEDATALEN);
snprintf(arr, NAMEDATALEN,
"_%.*s", NAMEDATALEN - 2, typeName); pg_type_desc = heap_open(TypeRelationId, AccessShareLock);
for (i = 1; i < NAMEDATALEN - 1; i++)
{
arr[i - 1] = '_';
strlcpy(arr + i, typeName, NAMEDATALEN - i);
truncate_identifier(arr, strlen(arr), false);
if (!SearchSysCacheExists(TYPENAMENSP,
CStringGetDatum(arr),
ObjectIdGetDatum(typeNamespace),
0, 0))
break;
}
heap_close(pg_type_desc, AccessShareLock);
if (i >= NAMEDATALEN-1)
ereport(ERROR,
(errcode(ERRCODE_DUPLICATE_OBJECT),
errmsg("could not form array type name for type \"%s\"",
typeName)));
return arr; return arr;
} }

View File

@ -8,7 +8,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $PostgreSQL: pgsql/src/backend/commands/tablecmds.c,v 1.219 2007/04/08 01:26:32 tgl Exp $ * $PostgreSQL: pgsql/src/backend/commands/tablecmds.c,v 1.220 2007/05/11 17:57:12 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
@ -2827,6 +2827,7 @@ find_composite_type_dependencies(Oid typeOid, const char *origTblName)
ScanKeyData key[2]; ScanKeyData key[2];
SysScanDesc depScan; SysScanDesc depScan;
HeapTuple depTup; HeapTuple depTup;
Oid arrayOid;
/* /*
* We scan pg_depend to find those things that depend on the rowtype. (We * We scan pg_depend to find those things that depend on the rowtype. (We
@ -2886,6 +2887,14 @@ find_composite_type_dependencies(Oid typeOid, const char *origTblName)
systable_endscan(depScan); systable_endscan(depScan);
relation_close(depRel, AccessShareLock); relation_close(depRel, AccessShareLock);
/*
* If there's an array type for the rowtype, must check for uses of it,
* too.
*/
arrayOid = get_array_type(typeOid);
if (OidIsValid(arrayOid))
find_composite_type_dependencies(arrayOid, origTblName);
} }
@ -5299,6 +5308,9 @@ ATPostAlterTypeParse(char *cmd, List **wqueue)
* be changed separately from the parent table. Also, we can skip permission * be changed separately from the parent table. Also, we can skip permission
* checks (this is necessary not just an optimization, else we'd fail to * checks (this is necessary not just an optimization, else we'd fail to
* handle toast tables properly). * handle toast tables properly).
*
* recursing is also true if ALTER TYPE OWNER is calling us to fix up a
* free-standing composite type.
*/ */
void void
ATExecChangeOwner(Oid relationOid, Oid newOwnerId, bool recursing) ATExecChangeOwner(Oid relationOid, Oid newOwnerId, bool recursing)
@ -5370,6 +5382,7 @@ ATExecChangeOwner(Oid relationOid, Oid newOwnerId, bool recursing)
} }
break; break;
case RELKIND_TOASTVALUE: case RELKIND_TOASTVALUE:
case RELKIND_COMPOSITE_TYPE:
if (recursing) if (recursing)
break; break;
/* FALL THRU */ /* FALL THRU */
@ -5448,14 +5461,22 @@ ATExecChangeOwner(Oid relationOid, Oid newOwnerId, bool recursing)
heap_freetuple(newtuple); heap_freetuple(newtuple);
/* Update owner dependency reference */ /*
changeDependencyOnOwner(RelationRelationId, relationOid, newOwnerId); * Update owner dependency reference, if any. A composite type has
* none, because it's tracked for the pg_type entry instead of here;
* indexes don't have their own entries either.
*/
if (tuple_class->relkind != RELKIND_COMPOSITE_TYPE &&
tuple_class->relkind != RELKIND_INDEX)
changeDependencyOnOwner(RelationRelationId, relationOid,
newOwnerId);
/* /*
* Also change the ownership of the table's rowtype, if it has one * Also change the ownership of the table's rowtype, if it has one
*/ */
if (tuple_class->relkind != RELKIND_INDEX) if (tuple_class->relkind != RELKIND_INDEX)
AlterTypeOwnerInternal(tuple_class->reltype, newOwnerId); AlterTypeOwnerInternal(tuple_class->reltype, newOwnerId,
tuple_class->relkind == RELKIND_COMPOSITE_TYPE);
/* /*
* If we are operating on a table, also change the ownership of any * If we are operating on a table, also change the ownership of any
@ -6462,7 +6483,7 @@ AlterTableNamespace(RangeVar *relation, const char *newschema)
AlterRelationNamespaceInternal(classRel, relid, oldNspOid, nspOid, true); AlterRelationNamespaceInternal(classRel, relid, oldNspOid, nspOid, true);
/* Fix the table's rowtype too */ /* Fix the table's rowtype too */
AlterTypeNamespaceInternal(rel->rd_rel->reltype, nspOid, false); AlterTypeNamespaceInternal(rel->rd_rel->reltype, nspOid, false, false);
/* Fix other dependent stuff */ /* Fix other dependent stuff */
if (rel->rd_rel->relkind == RELKIND_RELATION) if (rel->rd_rel->relkind == RELKIND_RELATION)
@ -6625,7 +6646,7 @@ AlterSeqNamespaces(Relation classRel, Relation rel,
* them to the new namespace, too. * them to the new namespace, too.
*/ */
AlterTypeNamespaceInternal(RelationGetForm(seqRel)->reltype, AlterTypeNamespaceInternal(RelationGetForm(seqRel)->reltype,
newNspOid, false); newNspOid, false, false);
/* Now we can close it. Keep the lock till end of transaction. */ /* Now we can close it. Keep the lock till end of transaction. */
relation_close(seqRel, NoLock); relation_close(seqRel, NoLock);

View File

@ -8,7 +8,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $PostgreSQL: pgsql/src/backend/commands/typecmds.c,v 1.101 2007/04/02 03:49:38 tgl Exp $ * $PostgreSQL: pgsql/src/backend/commands/typecmds.c,v 1.102 2007/05/11 17:57:12 tgl Exp $
* *
* DESCRIPTION * DESCRIPTION
* The "DefineFoo" routines take the parse tree and pick out the * The "DefineFoo" routines take the parse tree and pick out the
@ -34,6 +34,7 @@
#include "access/genam.h" #include "access/genam.h"
#include "access/heapam.h" #include "access/heapam.h"
#include "access/xact.h" #include "access/xact.h"
#include "catalog/catalog.h"
#include "catalog/dependency.h" #include "catalog/dependency.h"
#include "catalog/heap.h" #include "catalog/heap.h"
#include "catalog/indexing.h" #include "catalog/indexing.h"
@ -118,10 +119,12 @@ DefineType(List *names, List *parameters)
Oid typmodinOid = InvalidOid; Oid typmodinOid = InvalidOid;
Oid typmodoutOid = InvalidOid; Oid typmodoutOid = InvalidOid;
Oid analyzeOid = InvalidOid; Oid analyzeOid = InvalidOid;
char *shadow_type; char *array_type;
Oid array_oid;
ListCell *pl; ListCell *pl;
Oid typoid; Oid typoid;
Oid resulttype; Oid resulttype;
Relation pg_type;
/* Convert list of names to a name and namespace */ /* Convert list of names to a name and namespace */
typeNamespace = QualifiedNameGetCreationNamespace(names, &typeName); typeNamespace = QualifiedNameGetCreationNamespace(names, &typeName);
@ -132,16 +135,6 @@ DefineType(List *names, List *parameters)
aclcheck_error(aclresult, ACL_KIND_NAMESPACE, aclcheck_error(aclresult, ACL_KIND_NAMESPACE,
get_namespace_name(typeNamespace)); get_namespace_name(typeNamespace));
/*
* Type names must be one character shorter than other names, allowing
* room to create the corresponding array type name with prepended "_".
*/
if (strlen(typeName) > (NAMEDATALEN - 2))
ereport(ERROR,
(errcode(ERRCODE_INVALID_NAME),
errmsg("type names must be %d characters or less",
NAMEDATALEN - 2)));
/* /*
* Look to see if type already exists (presumably as a shell; if not, * Look to see if type already exists (presumably as a shell; if not,
* TypeCreate will complain). If it doesn't, create it as a shell, so * TypeCreate will complain). If it doesn't, create it as a shell, so
@ -396,11 +389,17 @@ DefineType(List *names, List *parameters)
aclcheck_error(ACLCHECK_NOT_OWNER, ACL_KIND_PROC, aclcheck_error(ACLCHECK_NOT_OWNER, ACL_KIND_PROC,
NameListToString(analyzeName)); NameListToString(analyzeName));
/* Preassign array type OID so we can insert it in pg_type.typarray */
pg_type = heap_open(TypeRelationId, AccessShareLock);
array_oid = GetNewOid(pg_type);
heap_close(pg_type, AccessShareLock);
/* /*
* now have TypeCreate do all the real work. * now have TypeCreate do all the real work.
*/ */
typoid = typoid =
TypeCreate(typeName, /* type name */ TypeCreate(InvalidOid, /* no predetermined type OID */
typeName, /* type name */
typeNamespace, /* namespace */ typeNamespace, /* namespace */
InvalidOid, /* relation oid (n/a here) */ InvalidOid, /* relation oid (n/a here) */
0, /* relation kind (ditto) */ 0, /* relation kind (ditto) */
@ -415,6 +414,8 @@ DefineType(List *names, List *parameters)
typmodoutOid,/* typmodout procedure */ typmodoutOid,/* typmodout procedure */
analyzeOid, /* analyze procedure */ analyzeOid, /* analyze procedure */
elemType, /* element type ID */ elemType, /* element type ID */
false, /* this is not an array type */
array_oid, /* array type we are about to create */
InvalidOid, /* base type ID (only for domains) */ InvalidOid, /* base type ID (only for domains) */
defaultValue, /* default type value */ defaultValue, /* default type value */
NULL, /* no binary form available */ NULL, /* no binary form available */
@ -426,19 +427,19 @@ DefineType(List *names, List *parameters)
false); /* Type NOT NULL */ false); /* Type NOT NULL */
/* /*
* When we create a base type (as opposed to a complex type) we need to * Create the array type that goes with it.
* have an array entry for it in pg_type as well.
*/ */
shadow_type = makeArrayTypeName(typeName); array_type = makeArrayTypeName(typeName, typeNamespace);
/* alignment must be 'i' or 'd' for arrays */ /* alignment must be 'i' or 'd' for arrays */
alignment = (alignment == 'd') ? 'd' : 'i'; alignment = (alignment == 'd') ? 'd' : 'i';
TypeCreate(shadow_type, /* type name */ TypeCreate(array_oid, /* force assignment of this type OID */
array_type, /* type name */
typeNamespace, /* namespace */ typeNamespace, /* namespace */
InvalidOid, /* relation oid (n/a here) */ InvalidOid, /* relation oid (n/a here) */
0, /* relation kind (ditto) */ 0, /* relation kind (ditto) */
-1, /* internal size */ -1, /* internal size (always varlena) */
TYPTYPE_BASE, /* type-type (base type) */ TYPTYPE_BASE, /* type-type (base type) */
DEFAULT_TYPDELIM, /* array element delimiter */ DEFAULT_TYPDELIM, /* array element delimiter */
F_ARRAY_IN, /* input procedure */ F_ARRAY_IN, /* input procedure */
@ -449,6 +450,8 @@ DefineType(List *names, List *parameters)
typmodoutOid, /* typmodout procedure */ typmodoutOid, /* typmodout procedure */
InvalidOid, /* analyze procedure - default */ InvalidOid, /* analyze procedure - default */
typoid, /* element type ID */ typoid, /* element type ID */
true, /* yes this is an array type */
InvalidOid, /* no further array type */
InvalidOid, /* base type ID */ InvalidOid, /* base type ID */
NULL, /* never a default type value */ NULL, /* never a default type value */
NULL, /* binary default isn't sent either */ NULL, /* binary default isn't sent either */
@ -459,7 +462,7 @@ DefineType(List *names, List *parameters)
0, /* Array dimensions of typbasetype */ 0, /* Array dimensions of typbasetype */
false); /* Type NOT NULL */ false); /* Type NOT NULL */
pfree(shadow_type); pfree(array_type);
} }
@ -474,6 +477,7 @@ RemoveType(List *names, DropBehavior behavior, bool missing_ok)
Oid typeoid; Oid typeoid;
HeapTuple tup; HeapTuple tup;
ObjectAddress object; ObjectAddress object;
Form_pg_type typ;
/* Make a TypeName so we can use standard type lookup machinery */ /* Make a TypeName so we can use standard type lookup machinery */
typename = makeTypeNameFromNameList(names); typename = makeTypeNameFromNameList(names);
@ -504,14 +508,19 @@ RemoveType(List *names, DropBehavior behavior, bool missing_ok)
0, 0, 0); 0, 0, 0);
if (!HeapTupleIsValid(tup)) if (!HeapTupleIsValid(tup))
elog(ERROR, "cache lookup failed for type %u", typeoid); elog(ERROR, "cache lookup failed for type %u", typeoid);
typ = (Form_pg_type) GETSTRUCT(tup);
/* Permission check: must own type or its namespace */ /* Permission check: must own type or its namespace */
if (!pg_type_ownercheck(typeoid, GetUserId()) && if (!pg_type_ownercheck(typeoid, GetUserId()) &&
!pg_namespace_ownercheck(((Form_pg_type) GETSTRUCT(tup))->typnamespace, !pg_namespace_ownercheck(typ->typnamespace, GetUserId()))
GetUserId()))
aclcheck_error(ACLCHECK_NOT_OWNER, ACL_KIND_TYPE, aclcheck_error(ACLCHECK_NOT_OWNER, ACL_KIND_TYPE,
TypeNameToString(typename)); TypeNameToString(typename));
/*
* Note: we need no special check for array types here, as the normal
* treatment of internal dependencies handles it just fine
*/
ReleaseSysCache(tup); ReleaseSysCache(tup);
/* /*
@ -607,19 +616,6 @@ DefineDomain(CreateDomainStmt *stmt)
aclcheck_error(aclresult, ACL_KIND_NAMESPACE, aclcheck_error(aclresult, ACL_KIND_NAMESPACE,
get_namespace_name(domainNamespace)); get_namespace_name(domainNamespace));
/*
* Domainnames, unlike typenames don't need to account for the '_' prefix.
* So they can be one character longer. (This test is presently useless
* since the parser will have truncated the name to fit. But leave it
* here since we may someday support arrays of domains, in which case
* we'll be back to needing to enforce NAMEDATALEN-2.)
*/
if (strlen(domainName) > (NAMEDATALEN - 1))
ereport(ERROR,
(errcode(ERRCODE_INVALID_NAME),
errmsg("domain names must be %d characters or less",
NAMEDATALEN - 1)));
/* /*
* Look up the base type. * Look up the base type.
*/ */
@ -805,7 +801,8 @@ DefineDomain(CreateDomainStmt *stmt)
* Have TypeCreate do all the real work. * Have TypeCreate do all the real work.
*/ */
domainoid = domainoid =
TypeCreate(domainName, /* type name */ TypeCreate(InvalidOid, /* no predetermined type OID */
domainName, /* type name */
domainNamespace, /* namespace */ domainNamespace, /* namespace */
InvalidOid, /* relation oid (n/a here) */ InvalidOid, /* relation oid (n/a here) */
0, /* relation kind (ditto) */ 0, /* relation kind (ditto) */
@ -820,6 +817,8 @@ DefineDomain(CreateDomainStmt *stmt)
InvalidOid, /* typmodout procedure - none */ InvalidOid, /* typmodout procedure - none */
analyzeProcedure, /* analyze procedure */ analyzeProcedure, /* analyze procedure */
typelem, /* element type ID */ typelem, /* element type ID */
false, /* this isn't an array */
InvalidOid, /* no arrays for domains (yet) */
basetypeoid, /* base type ID */ basetypeoid, /* base type ID */
defaultValue, /* default type value (text) */ defaultValue, /* default type value (text) */
defaultValueBin, /* default type value (binary) */ defaultValueBin, /* default type value (binary) */
@ -949,6 +948,8 @@ DefineEnum(CreateEnumStmt *stmt)
Oid enumNamespace; Oid enumNamespace;
Oid enumTypeOid; Oid enumTypeOid;
AclResult aclresult; AclResult aclresult;
Oid enumArrayOid;
Relation pg_type;
/* Convert list of names to a name and namespace */ /* Convert list of names to a name and namespace */
enumNamespace = QualifiedNameGetCreationNamespace(stmt->typename, enumNamespace = QualifiedNameGetCreationNamespace(stmt->typename,
@ -960,19 +961,15 @@ DefineEnum(CreateEnumStmt *stmt)
aclcheck_error(aclresult, ACL_KIND_NAMESPACE, aclcheck_error(aclresult, ACL_KIND_NAMESPACE,
get_namespace_name(enumNamespace)); get_namespace_name(enumNamespace));
/* /* Preassign array type OID so we can insert it in pg_type.typarray */
* Type names must be one character shorter than other names, allowing pg_type = heap_open(TypeRelationId, AccessShareLock);
* room to create the corresponding array type name with prepended "_". enumArrayOid = GetNewOid(pg_type);
*/ heap_close(pg_type, AccessShareLock);
if (strlen(enumName) > (NAMEDATALEN - 2))
ereport(ERROR,
(errcode(ERRCODE_INVALID_NAME),
errmsg("type names must be %d characters or less",
NAMEDATALEN - 2)));
/* Create the pg_type entry */ /* Create the pg_type entry */
enumTypeOid = enumTypeOid =
TypeCreate(enumName, /* type name */ TypeCreate(InvalidOid, /* no predetermined type OID */
enumName, /* type name */
enumNamespace, /* namespace */ enumNamespace, /* namespace */
InvalidOid, /* relation oid (n/a here) */ InvalidOid, /* relation oid (n/a here) */
0, /* relation kind (ditto) */ 0, /* relation kind (ditto) */
@ -987,6 +984,8 @@ DefineEnum(CreateEnumStmt *stmt)
InvalidOid, /* typmodout procedure - none */ InvalidOid, /* typmodout procedure - none */
InvalidOid, /* analyze procedure - default */ InvalidOid, /* analyze procedure - default */
InvalidOid, /* element type ID */ InvalidOid, /* element type ID */
false, /* this is not an array type */
enumArrayOid, /* array type we are about to create */
InvalidOid, /* base type ID (only for domains) */ InvalidOid, /* base type ID (only for domains) */
NULL, /* never a default type value */ NULL, /* never a default type value */
NULL, /* binary default isn't sent either */ NULL, /* binary default isn't sent either */
@ -1000,14 +999,17 @@ DefineEnum(CreateEnumStmt *stmt)
/* Enter the enum's values into pg_enum */ /* Enter the enum's values into pg_enum */
EnumValuesCreate(enumTypeOid, stmt->vals); EnumValuesCreate(enumTypeOid, stmt->vals);
/* Create array type for enum */ /*
enumArrayName = makeArrayTypeName(enumName); * Create the array type that goes with it.
*/
enumArrayName = makeArrayTypeName(enumName, enumNamespace);
TypeCreate(enumArrayName, /* type name */ TypeCreate(enumArrayOid, /* force assignment of this type OID */
enumArrayName, /* type name */
enumNamespace, /* namespace */ enumNamespace, /* namespace */
InvalidOid, /* relation oid (n/a here) */ InvalidOid, /* relation oid (n/a here) */
0, /* relation kind (ditto) */ 0, /* relation kind (ditto) */
-1, /* internal size */ -1, /* internal size (always varlena) */
TYPTYPE_BASE, /* type-type (base type) */ TYPTYPE_BASE, /* type-type (base type) */
DEFAULT_TYPDELIM, /* array element delimiter */ DEFAULT_TYPDELIM, /* array element delimiter */
F_ARRAY_IN, /* input procedure */ F_ARRAY_IN, /* input procedure */
@ -1018,6 +1020,8 @@ DefineEnum(CreateEnumStmt *stmt)
InvalidOid, /* typmodout procedure - none */ InvalidOid, /* typmodout procedure - none */
InvalidOid, /* analyze procedure - default */ InvalidOid, /* analyze procedure - default */
enumTypeOid, /* element type ID */ enumTypeOid, /* element type ID */
true, /* yes this is an array type */
InvalidOid, /* no further array type */
InvalidOid, /* base type ID */ InvalidOid, /* base type ID */
NULL, /* never a default type value */ NULL, /* never a default type value */
NULL, /* binary default isn't sent either */ NULL, /* binary default isn't sent either */
@ -1026,7 +1030,7 @@ DefineEnum(CreateEnumStmt *stmt)
'x', /* ARRAY is always toastable */ 'x', /* ARRAY is always toastable */
-1, /* typMod (Domains only) */ -1, /* typMod (Domains only) */
0, /* Array dimensions of typbasetype */ 0, /* Array dimensions of typbasetype */
false); /* Type NOT NULL */ false); /* Type NOT NULL */
pfree(enumArrayName); pfree(enumArrayName);
} }
@ -1435,7 +1439,7 @@ AlterDomainDefault(List *names, Node *defaultRaw)
/* Rebuild dependencies */ /* Rebuild dependencies */
GenerateTypeDependencies(typTup->typnamespace, GenerateTypeDependencies(typTup->typnamespace,
domainoid, domainoid,
typTup->typrelid, InvalidOid, /* typrelid is n/a */
0, /* relation kind is n/a */ 0, /* relation kind is n/a */
typTup->typowner, typTup->typowner,
typTup->typinput, typTup->typinput,
@ -1446,6 +1450,7 @@ AlterDomainDefault(List *names, Node *defaultRaw)
typTup->typmodout, typTup->typmodout,
typTup->typanalyze, typTup->typanalyze,
typTup->typelem, typTup->typelem,
false, /* a domain isn't an implicit array */
typTup->typbasetype, typTup->typbasetype,
defaultExpr, defaultExpr,
true); /* Rebuild is true */ true); /* Rebuild is true */
@ -2251,7 +2256,7 @@ AlterTypeOwner(List *names, Oid newOwnerId)
/* /*
* If it's a composite type, we need to check that it really is a * If it's a composite type, we need to check that it really is a
* free-standing composite type, and not a table's underlying type. We * free-standing composite type, and not a table's rowtype. We
* want people to use ALTER TABLE not ALTER TYPE for that case. * want people to use ALTER TABLE not ALTER TYPE for that case.
*/ */
if (typTup->typtype == TYPTYPE_COMPOSITE && if (typTup->typtype == TYPTYPE_COMPOSITE &&
@ -2261,6 +2266,16 @@ AlterTypeOwner(List *names, Oid newOwnerId)
errmsg("\"%s\" is a table's row type", errmsg("\"%s\" is a table's row type",
TypeNameToString(typename)))); TypeNameToString(typename))));
/* don't allow direct alteration of array types, either */
if (OidIsValid(typTup->typelem) &&
get_array_type(typTup->typelem) == typeOid)
ereport(ERROR,
(errcode(ERRCODE_WRONG_OBJECT_TYPE),
errmsg("cannot alter array type %s",
format_type_be(typeOid)),
errhint("You can alter type %s, which will alter the array type as well.",
format_type_be(typTup->typelem))));
/* /*
* If the new owner is the same as the existing owner, consider the * If the new owner is the same as the existing owner, consider the
* command to have succeeded. This is for dump restoration purposes. * command to have succeeded. This is for dump restoration purposes.
@ -2288,16 +2303,32 @@ AlterTypeOwner(List *names, Oid newOwnerId)
} }
/* /*
* Modify the owner --- okay to scribble on typTup because it's a copy * If it's a composite type, invoke ATExecChangeOwner so that we
* fix up the pg_class entry properly. That will call back to
* AlterTypeOwnerInternal to take care of the pg_type entry(s).
*/ */
typTup->typowner = newOwnerId; if (typTup->typtype == TYPTYPE_COMPOSITE)
ATExecChangeOwner(typTup->typrelid, newOwnerId, true);
else
{
/*
* We can just apply the modification directly.
*
* okay to scribble on typTup because it's a copy
*/
typTup->typowner = newOwnerId;
simple_heap_update(rel, &tup->t_self, tup); simple_heap_update(rel, &tup->t_self, tup);
CatalogUpdateIndexes(rel, tup); CatalogUpdateIndexes(rel, tup);
/* Update owner dependency reference */ /* Update owner dependency reference */
changeDependencyOnOwner(TypeRelationId, typeOid, newOwnerId); changeDependencyOnOwner(TypeRelationId, typeOid, newOwnerId);
/* If it has an array type, update that too */
if (OidIsValid(typTup->typarray))
AlterTypeOwnerInternal(typTup->typarray, newOwnerId, false);
}
} }
/* Clean up */ /* Clean up */
@ -2307,12 +2338,17 @@ AlterTypeOwner(List *names, Oid newOwnerId)
/* /*
* AlterTypeOwnerInternal - change type owner unconditionally * AlterTypeOwnerInternal - change type owner unconditionally
* *
* This is currently only used to propagate ALTER TABLE OWNER to the * This is currently only used to propagate ALTER TABLE/TYPE OWNER to a
* table's rowtype, and to implement REASSIGN OWNED BY. It assumes the * table's rowtype or an array type, and to implement REASSIGN OWNED BY.
* caller has done all needed checks. * It assumes the caller has done all needed checks. The function will
* automatically recurse to an array type if the type has one.
*
* hasDependEntry should be TRUE if type is expected to have a pg_shdepend
* entry (ie, it's not a table rowtype nor an array type).
*/ */
void void
AlterTypeOwnerInternal(Oid typeOid, Oid newOwnerId) AlterTypeOwnerInternal(Oid typeOid, Oid newOwnerId,
bool hasDependEntry)
{ {
Relation rel; Relation rel;
HeapTuple tup; HeapTuple tup;
@ -2336,8 +2372,13 @@ AlterTypeOwnerInternal(Oid typeOid, Oid newOwnerId)
CatalogUpdateIndexes(rel, tup); CatalogUpdateIndexes(rel, tup);
/* Update owner dependency reference */ /* Update owner dependency reference, if it has one */
changeDependencyOnOwner(TypeRelationId, typeOid, newOwnerId); if (hasDependEntry)
changeDependencyOnOwner(TypeRelationId, typeOid, newOwnerId);
/* If it has an array type, update that too */
if (OidIsValid(typTup->typarray))
AlterTypeOwnerInternal(typTup->typarray, newOwnerId, false);
/* Clean up */ /* Clean up */
heap_close(rel, RowExclusiveLock); heap_close(rel, RowExclusiveLock);
@ -2352,6 +2393,7 @@ AlterTypeNamespace(List *names, const char *newschema)
TypeName *typename; TypeName *typename;
Oid typeOid; Oid typeOid;
Oid nspOid; Oid nspOid;
Oid elemOid;
/* Make a TypeName so we can use standard type lookup machinery */ /* Make a TypeName so we can use standard type lookup machinery */
typename = makeTypeNameFromNameList(names); typename = makeTypeNameFromNameList(names);
@ -2365,8 +2407,18 @@ AlterTypeNamespace(List *names, const char *newschema)
/* get schema OID and check its permissions */ /* get schema OID and check its permissions */
nspOid = LookupCreationNamespace(newschema); nspOid = LookupCreationNamespace(newschema);
/* don't allow direct alteration of array types */
elemOid = get_element_type(typeOid);
if (OidIsValid(elemOid) && get_array_type(elemOid) == typeOid)
ereport(ERROR,
(errcode(ERRCODE_WRONG_OBJECT_TYPE),
errmsg("cannot alter array type %s",
format_type_be(typeOid)),
errhint("You can alter type %s, which will alter the array type as well.",
format_type_be(elemOid))));
/* and do the work */ /* and do the work */
AlterTypeNamespaceInternal(typeOid, nspOid, true); AlterTypeNamespaceInternal(typeOid, nspOid, false, true);
} }
/* /*
@ -2374,18 +2426,24 @@ AlterTypeNamespace(List *names, const char *newschema)
* *
* Caller must have already checked privileges. * Caller must have already checked privileges.
* *
* The function automatically recurses to process the type's array type,
* if any. isImplicitArray should be TRUE only when doing this internal
* recursion (outside callers must never try to move an array type directly).
*
* If errorOnTableType is TRUE, the function errors out if the type is * If errorOnTableType is TRUE, the function errors out if the type is
* a table type. ALTER TABLE has to be used to move a table to a new * a table type. ALTER TABLE has to be used to move a table to a new
* namespace. * namespace.
*/ */
void void
AlterTypeNamespaceInternal(Oid typeOid, Oid nspOid, AlterTypeNamespaceInternal(Oid typeOid, Oid nspOid,
bool isImplicitArray,
bool errorOnTableType) bool errorOnTableType)
{ {
Relation rel; Relation rel;
HeapTuple tup; HeapTuple tup;
Form_pg_type typform; Form_pg_type typform;
Oid oldNspOid; Oid oldNspOid;
Oid arrayOid;
bool isCompositeType; bool isCompositeType;
rel = heap_open(TypeRelationId, RowExclusiveLock); rel = heap_open(TypeRelationId, RowExclusiveLock);
@ -2398,6 +2456,7 @@ AlterTypeNamespaceInternal(Oid typeOid, Oid nspOid,
typform = (Form_pg_type) GETSTRUCT(tup); typform = (Form_pg_type) GETSTRUCT(tup);
oldNspOid = typform->typnamespace; oldNspOid = typform->typnamespace;
arrayOid = typform->typarray;
if (oldNspOid == nspOid) if (oldNspOid == nspOid)
ereport(ERROR, ereport(ERROR,
@ -2463,13 +2522,9 @@ AlterTypeNamespaceInternal(Oid typeOid, Oid nspOid,
classRel = heap_open(RelationRelationId, RowExclusiveLock); classRel = heap_open(RelationRelationId, RowExclusiveLock);
/*
* The dependency on the schema is listed under the pg_class entry, so
* tell AlterRelationNamespaceInternal to fix it.
*/
AlterRelationNamespaceInternal(classRel, typform->typrelid, AlterRelationNamespaceInternal(classRel, typform->typrelid,
oldNspOid, nspOid, oldNspOid, nspOid,
true); false);
heap_close(classRel, RowExclusiveLock); heap_close(classRel, RowExclusiveLock);
@ -2485,19 +2540,24 @@ AlterTypeNamespaceInternal(Oid typeOid, Oid nspOid,
/* If it's a domain, it might have constraints */ /* If it's a domain, it might have constraints */
if (typform->typtype == TYPTYPE_DOMAIN) if (typform->typtype == TYPTYPE_DOMAIN)
AlterConstraintNamespaces(typeOid, oldNspOid, nspOid, true); AlterConstraintNamespaces(typeOid, oldNspOid, nspOid, true);
/*
* Update dependency on schema, if any --- a table rowtype has not got
* one.
*/
if (typform->typtype != TYPTYPE_COMPOSITE)
if (changeDependencyFor(TypeRelationId, typeOid,
NamespaceRelationId, oldNspOid, nspOid) != 1)
elog(ERROR, "failed to change schema dependency for type %s",
format_type_be(typeOid));
} }
/*
* Update dependency on schema, if any --- a table rowtype has not got
* one, and neither does an implicit array.
*/
if ((isCompositeType || typform->typtype != TYPTYPE_COMPOSITE) &&
!isImplicitArray)
if (changeDependencyFor(TypeRelationId, typeOid,
NamespaceRelationId, oldNspOid, nspOid) != 1)
elog(ERROR, "failed to change schema dependency for type %s",
format_type_be(typeOid));
heap_freetuple(tup); heap_freetuple(tup);
heap_close(rel, RowExclusiveLock); heap_close(rel, RowExclusiveLock);
/* Recursively alter the associated array type, if any */
if (OidIsValid(arrayOid))
AlterTypeNamespaceInternal(arrayOid, nspOid, true, true);
} }

View File

@ -8,7 +8,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $PostgreSQL: pgsql/src/backend/parser/parse_type.c,v 1.89 2007/04/27 22:05:48 tgl Exp $ * $PostgreSQL: pgsql/src/backend/parser/parse_type.c,v 1.90 2007/05/11 17:57:12 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
@ -116,10 +116,6 @@ LookupTypeName(ParseState *pstate, const TypeName *typename)
/* deconstruct the name list */ /* deconstruct the name list */
DeconstructQualifiedName(typename->names, &schemaname, &typname); DeconstructQualifiedName(typename->names, &schemaname, &typname);
/* If an array reference, look up the array type instead */
if (typename->arrayBounds != NIL)
typname = makeArrayTypeName(typname);
if (schemaname) if (schemaname)
{ {
/* Look in specific schema only */ /* Look in specific schema only */
@ -136,6 +132,10 @@ LookupTypeName(ParseState *pstate, const TypeName *typename)
/* Unqualified type name, so search the search path */ /* Unqualified type name, so search the search path */
restype = TypenameGetTypid(typname); restype = TypenameGetTypid(typname);
} }
/* If an array reference, return the array type instead */
if (typename->arrayBounds != NIL)
restype = get_array_type(restype);
} }
return restype; return restype;

View File

@ -7,7 +7,7 @@
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* IDENTIFICATION * IDENTIFICATION
* $PostgreSQL: pgsql/src/backend/utils/cache/lsyscache.c,v 1.151 2007/04/02 03:49:39 tgl Exp $ * $PostgreSQL: pgsql/src/backend/utils/cache/lsyscache.c,v 1.152 2007/05/11 17:57:12 tgl Exp $
* *
* NOTES * NOTES
* Eventually, the index information should go through here, too. * Eventually, the index information should go through here, too.
@ -2203,50 +2203,24 @@ get_element_type(Oid typid)
/* /*
* get_array_type * get_array_type
* *
* Given the type OID, get the corresponding array type. * Given the type OID, get the corresponding "true" array type.
* Returns InvalidOid if no array type can be found. * Returns InvalidOid if no array type can be found.
*
* NB: this only considers varlena arrays to be true arrays.
*/ */
Oid Oid
get_array_type(Oid typid) get_array_type(Oid typid)
{ {
HeapTuple tp; HeapTuple tp;
Oid result = InvalidOid;
tp = SearchSysCache(TYPEOID, tp = SearchSysCache(TYPEOID,
ObjectIdGetDatum(typid), ObjectIdGetDatum(typid),
0, 0, 0); 0, 0, 0);
if (HeapTupleIsValid(tp)) if (HeapTupleIsValid(tp))
{ {
Form_pg_type typtup = (Form_pg_type) GETSTRUCT(tp); result = ((Form_pg_type) GETSTRUCT(tp))->typarray;
char *array_typename;
Oid namespaceId;
array_typename = makeArrayTypeName(NameStr(typtup->typname));
namespaceId = typtup->typnamespace;
ReleaseSysCache(tp); ReleaseSysCache(tp);
tp = SearchSysCache(TYPENAMENSP,
PointerGetDatum(array_typename),
ObjectIdGetDatum(namespaceId),
0, 0);
pfree(array_typename);
if (HeapTupleIsValid(tp))
{
Oid result;
typtup = (Form_pg_type) GETSTRUCT(tp);
if (typtup->typlen == -1 && typtup->typelem == typid)
result = HeapTupleGetOid(tp);
else
result = InvalidOid;
ReleaseSysCache(tp);
return result;
}
} }
return InvalidOid; return result;
} }
/* /*

View File

@ -12,7 +12,7 @@
* by PostgreSQL * by PostgreSQL
* *
* IDENTIFICATION * IDENTIFICATION
* $PostgreSQL: pgsql/src/bin/pg_dump/pg_dump.c,v 1.467 2007/04/16 18:42:10 tgl Exp $ * $PostgreSQL: pgsql/src/bin/pg_dump/pg_dump.c,v 1.468 2007/05/11 17:57:12 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
@ -963,9 +963,8 @@ selectDumpableType(TypeInfo *tinfo)
else if (!tinfo->isDefined) else if (!tinfo->isDefined)
tinfo->dobj.dump = false; tinfo->dobj.dump = false;
/* skip all array types that start w/ underscore */ /* skip auto-generated array types */
else if ((tinfo->dobj.name[0] == '_') && else if (tinfo->isArray)
OidIsValid(tinfo->typelem))
tinfo->dobj.dump = false; tinfo->dobj.dump = false;
else else
@ -1963,6 +1962,7 @@ getTypes(int *numTypes)
int i_typrelkind; int i_typrelkind;
int i_typtype; int i_typtype;
int i_typisdefined; int i_typisdefined;
int i_isarray;
/* /*
* we include even the built-in types because those may be used as array * we include even the built-in types because those may be used as array
@ -1970,13 +1970,20 @@ getTypes(int *numTypes)
* *
* we filter out the built-in types when we dump out the types * we filter out the built-in types when we dump out the types
* *
* same approach for undefined (shell) types * same approach for undefined (shell) types and array types
*
* Note: as of 8.3 we can reliably detect whether a type is an
* auto-generated array type by checking the element type's typarray.
* (Before that the test is capable of generating false positives.)
* We still check for name beginning with '_', though, so as to avoid
* the cost of the subselect probe for all standard types. This would
* have to be revisited if the backend ever allows renaming of array types.
*/ */
/* Make sure we are in proper schema */ /* Make sure we are in proper schema */
selectSourceSchema("pg_catalog"); selectSourceSchema("pg_catalog");
if (g_fout->remoteVersion >= 70300) if (g_fout->remoteVersion >= 80300)
{ {
appendPQExpBuffer(query, "SELECT tableoid, oid, typname, " appendPQExpBuffer(query, "SELECT tableoid, oid, typname, "
"typnamespace, " "typnamespace, "
@ -1985,7 +1992,23 @@ getTypes(int *numTypes)
"typoutput::oid as typoutput, typelem, typrelid, " "typoutput::oid as typoutput, typelem, typrelid, "
"CASE WHEN typrelid = 0 THEN ' '::\"char\" " "CASE WHEN typrelid = 0 THEN ' '::\"char\" "
"ELSE (SELECT relkind FROM pg_class WHERE oid = typrelid) END as typrelkind, " "ELSE (SELECT relkind FROM pg_class WHERE oid = typrelid) END as typrelkind, "
"typtype, typisdefined " "typtype, typisdefined, "
"typname[0] = '_' AND typelem != 0 AND "
"(SELECT typarray FROM pg_type te WHERE oid = pg_type.typelem) = oid AS isarray "
"FROM pg_type",
username_subquery);
}
else if (g_fout->remoteVersion >= 70300)
{
appendPQExpBuffer(query, "SELECT tableoid, oid, typname, "
"typnamespace, "
"(%s typowner) as rolname, "
"typinput::oid as typinput, "
"typoutput::oid as typoutput, typelem, typrelid, "
"CASE WHEN typrelid = 0 THEN ' '::\"char\" "
"ELSE (SELECT relkind FROM pg_class WHERE oid = typrelid) END as typrelkind, "
"typtype, typisdefined, "
"typname[0] = '_' AND typelem != 0 AS isarray "
"FROM pg_type", "FROM pg_type",
username_subquery); username_subquery);
} }
@ -1998,7 +2021,8 @@ getTypes(int *numTypes)
"typoutput::oid as typoutput, typelem, typrelid, " "typoutput::oid as typoutput, typelem, typrelid, "
"CASE WHEN typrelid = 0 THEN ' '::\"char\" " "CASE WHEN typrelid = 0 THEN ' '::\"char\" "
"ELSE (SELECT relkind FROM pg_class WHERE oid = typrelid) END as typrelkind, " "ELSE (SELECT relkind FROM pg_class WHERE oid = typrelid) END as typrelkind, "
"typtype, typisdefined " "typtype, typisdefined, "
"typname[0] = '_' AND typelem != 0 AS isarray "
"FROM pg_type", "FROM pg_type",
username_subquery); username_subquery);
} }
@ -2013,7 +2037,8 @@ getTypes(int *numTypes)
"typoutput::oid as typoutput, typelem, typrelid, " "typoutput::oid as typoutput, typelem, typrelid, "
"CASE WHEN typrelid = 0 THEN ' '::\"char\" " "CASE WHEN typrelid = 0 THEN ' '::\"char\" "
"ELSE (SELECT relkind FROM pg_class WHERE oid = typrelid) END as typrelkind, " "ELSE (SELECT relkind FROM pg_class WHERE oid = typrelid) END as typrelkind, "
"typtype, typisdefined " "typtype, typisdefined, "
"typname[0] = '_' AND typelem != 0 AS isarray "
"FROM pg_type", "FROM pg_type",
username_subquery); username_subquery);
} }
@ -2037,6 +2062,7 @@ getTypes(int *numTypes)
i_typrelkind = PQfnumber(res, "typrelkind"); i_typrelkind = PQfnumber(res, "typrelkind");
i_typtype = PQfnumber(res, "typtype"); i_typtype = PQfnumber(res, "typtype");
i_typisdefined = PQfnumber(res, "typisdefined"); i_typisdefined = PQfnumber(res, "typisdefined");
i_isarray = PQfnumber(res, "isarray");
for (i = 0; i < ntups; i++) for (i = 0; i < ntups; i++)
{ {
@ -2064,20 +2090,16 @@ getTypes(int *numTypes)
tinfo[i].typrelkind != RELKIND_COMPOSITE_TYPE) tinfo[i].typrelkind != RELKIND_COMPOSITE_TYPE)
tinfo[i].dobj.objType = DO_TABLE_TYPE; tinfo[i].dobj.objType = DO_TABLE_TYPE;
/*
* check for user-defined array types, omit system generated ones
*/
if (OidIsValid(tinfo[i].typelem) &&
tinfo[i].dobj.name[0] != '_')
tinfo[i].isArray = true;
else
tinfo[i].isArray = false;
if (strcmp(PQgetvalue(res, i, i_typisdefined), "t") == 0) if (strcmp(PQgetvalue(res, i, i_typisdefined), "t") == 0)
tinfo[i].isDefined = true; tinfo[i].isDefined = true;
else else
tinfo[i].isDefined = false; tinfo[i].isDefined = false;
if (strcmp(PQgetvalue(res, i, i_isarray), "t") == 0)
tinfo[i].isArray = true;
else
tinfo[i].isArray = false;
/* Decide whether we want to dump it */ /* Decide whether we want to dump it */
selectDumpableType(&tinfo[i]); selectDumpableType(&tinfo[i]);
@ -3894,7 +3916,7 @@ getTriggers(TableInfo tblinfo[], int numTables)
else if (g_fout->remoteVersion >= 70100) else if (g_fout->remoteVersion >= 70100)
{ {
appendPQExpBuffer(query, appendPQExpBuffer(query,
"SELECT tgname, tgfoid::pg_catalog.regproc as tgfname, " "SELECT tgname, tgfoid::regproc as tgfname, "
"tgtype, tgnargs, tgargs, tgenabled, " "tgtype, tgnargs, tgargs, tgenabled, "
"tgisconstraint, tgconstrname, tgdeferrable, " "tgisconstraint, tgconstrname, tgdeferrable, "
"tgconstrrelid, tginitdeferred, tableoid, oid, " "tgconstrrelid, tginitdeferred, tableoid, oid, "
@ -3907,7 +3929,7 @@ getTriggers(TableInfo tblinfo[], int numTables)
else else
{ {
appendPQExpBuffer(query, appendPQExpBuffer(query,
"SELECT tgname, tgfoid::pg_catalog.regproc as tgfname, " "SELECT tgname, tgfoid::regproc as tgfname, "
"tgtype, tgnargs, tgargs, tgenabled, " "tgtype, tgnargs, tgargs, tgenabled, "
"tgisconstraint, tgconstrname, tgdeferrable, " "tgisconstraint, tgconstrname, tgdeferrable, "
"tgconstrrelid, tginitdeferred, " "tgconstrrelid, tginitdeferred, "
@ -5473,7 +5495,7 @@ dumpBaseType(Archive *fout, TypeInfo *tinfo)
appendPQExpBufferStr(q, typdefault); appendPQExpBufferStr(q, typdefault);
} }
if (tinfo->isArray) if (OidIsValid(tinfo->typelem))
{ {
char *elemType; char *elemType;

View File

@ -6,7 +6,7 @@
* Portions Copyright (c) 1996-2007, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2007, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* $PostgreSQL: pgsql/src/bin/pg_dump/pg_dump.h,v 1.134 2007/03/19 23:38:30 wieck Exp $ * $PostgreSQL: pgsql/src/bin/pg_dump/pg_dump.h,v 1.135 2007/05/11 17:57:13 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
@ -164,7 +164,7 @@ typedef struct _typeInfo
Oid typrelid; Oid typrelid;
char typrelkind; /* 'r', 'v', 'c', etc */ char typrelkind; /* 'r', 'v', 'c', etc */
char typtype; /* 'b', 'c', etc */ char typtype; /* 'b', 'c', etc */
bool isArray; /* true if user-defined array type */ bool isArray; /* true if auto-generated array type */
bool isDefined; /* true if typisdefined */ bool isDefined; /* true if typisdefined */
/* If it's a dumpable base type, we create a "shell type" entry for it */ /* If it's a dumpable base type, we create a "shell type" entry for it */
struct _shellTypeInfo *shellType; /* shell-type entry, or NULL */ struct _shellTypeInfo *shellType; /* shell-type entry, or NULL */

View File

@ -37,7 +37,7 @@
* Portions Copyright (c) 1996-2007, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2007, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* $PostgreSQL: pgsql/src/include/catalog/catversion.h,v 1.405 2007/05/08 18:56:47 neilc Exp $ * $PostgreSQL: pgsql/src/include/catalog/catversion.h,v 1.406 2007/05/11 17:57:13 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
@ -53,6 +53,6 @@
*/ */
/* yyyymmddN */ /* yyyymmddN */
#define CATALOG_VERSION_NO 200705081 #define CATALOG_VERSION_NO 200705111
#endif #endif

View File

@ -8,7 +8,7 @@
* Portions Copyright (c) 1996-2007, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2007, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* $PostgreSQL: pgsql/src/include/catalog/pg_attribute.h,v 1.130 2007/01/22 01:35:21 tgl Exp $ * $PostgreSQL: pgsql/src/include/catalog/pg_attribute.h,v 1.131 2007/05/11 17:57:13 tgl Exp $
* *
* NOTES * NOTES
* the genbki.sh script reads this file and generates .bki * the genbki.sh script reads this file and generates .bki
@ -232,21 +232,22 @@ typedef FormData_pg_attribute *Form_pg_attribute;
{ 1247, {"typdelim"}, 18, -1, 1, 8, 0, -1, -1, true, 'p', 'c', true, false, false, true, 0 }, \ { 1247, {"typdelim"}, 18, -1, 1, 8, 0, -1, -1, true, 'p', 'c', true, false, false, true, 0 }, \
{ 1247, {"typrelid"}, 26, -1, 4, 9, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \ { 1247, {"typrelid"}, 26, -1, 4, 9, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \
{ 1247, {"typelem"}, 26, -1, 4, 10, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \ { 1247, {"typelem"}, 26, -1, 4, 10, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \
{ 1247, {"typinput"}, 24, -1, 4, 11, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \ { 1247, {"typarray"}, 26, -1, 4, 11, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \
{ 1247, {"typoutput"}, 24, -1, 4, 12, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \ { 1247, {"typinput"}, 24, -1, 4, 12, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \
{ 1247, {"typreceive"}, 24, -1, 4, 13, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \ { 1247, {"typoutput"}, 24, -1, 4, 13, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \
{ 1247, {"typsend"}, 24, -1, 4, 14, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \ { 1247, {"typreceive"}, 24, -1, 4, 14, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \
{ 1247, {"typmodin"}, 24, -1, 4, 15, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \ { 1247, {"typsend"}, 24, -1, 4, 15, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \
{ 1247, {"typmodout"}, 24, -1, 4, 16, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \ { 1247, {"typmodin"}, 24, -1, 4, 16, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \
{ 1247, {"typanalyze"}, 24, -1, 4, 17, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \ { 1247, {"typmodout"}, 24, -1, 4, 17, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \
{ 1247, {"typalign"}, 18, -1, 1, 18, 0, -1, -1, true, 'p', 'c', true, false, false, true, 0 }, \ { 1247, {"typanalyze"}, 24, -1, 4, 18, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \
{ 1247, {"typstorage"}, 18, -1, 1, 19, 0, -1, -1, true, 'p', 'c', true, false, false, true, 0 }, \ { 1247, {"typalign"}, 18, -1, 1, 19, 0, -1, -1, true, 'p', 'c', true, false, false, true, 0 }, \
{ 1247, {"typnotnull"}, 16, -1, 1, 20, 0, -1, -1, true, 'p', 'c', true, false, false, true, 0 }, \ { 1247, {"typstorage"}, 18, -1, 1, 20, 0, -1, -1, true, 'p', 'c', true, false, false, true, 0 }, \
{ 1247, {"typbasetype"}, 26, -1, 4, 21, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \ { 1247, {"typnotnull"}, 16, -1, 1, 21, 0, -1, -1, true, 'p', 'c', true, false, false, true, 0 }, \
{ 1247, {"typtypmod"}, 23, -1, 4, 22, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \ { 1247, {"typbasetype"}, 26, -1, 4, 22, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \
{ 1247, {"typndims"}, 23, -1, 4, 23, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \ { 1247, {"typtypmod"}, 23, -1, 4, 23, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \
{ 1247, {"typdefaultbin"}, 25, -1, -1, 24, 0, -1, -1, false, 'x', 'i', false, false, false, true, 0 }, \ { 1247, {"typndims"}, 23, -1, 4, 24, 0, -1, -1, true, 'p', 'i', true, false, false, true, 0 }, \
{ 1247, {"typdefault"}, 25, -1, -1, 25, 0, -1, -1, false, 'x', 'i', false, false, false, true, 0 } { 1247, {"typdefaultbin"}, 25, -1, -1, 25, 0, -1, -1, false, 'x', 'i', false, false, false, true, 0 }, \
{ 1247, {"typdefault"}, 25, -1, -1, 26, 0, -1, -1, false, 'x', 'i', false, false, false, true, 0 }
DATA(insert ( 1247 typname 19 -1 NAMEDATALEN 1 0 -1 -1 f p i t f f t 0)); DATA(insert ( 1247 typname 19 -1 NAMEDATALEN 1 0 -1 -1 f p i t f f t 0));
DATA(insert ( 1247 typnamespace 26 -1 4 2 0 -1 -1 t p i t f f t 0)); DATA(insert ( 1247 typnamespace 26 -1 4 2 0 -1 -1 t p i t f f t 0));
@ -258,21 +259,22 @@ DATA(insert ( 1247 typisdefined 16 -1 1 7 0 -1 -1 t p c t f f t 0));
DATA(insert ( 1247 typdelim 18 -1 1 8 0 -1 -1 t p c t f f t 0)); DATA(insert ( 1247 typdelim 18 -1 1 8 0 -1 -1 t p c t f f t 0));
DATA(insert ( 1247 typrelid 26 -1 4 9 0 -1 -1 t p i t f f t 0)); DATA(insert ( 1247 typrelid 26 -1 4 9 0 -1 -1 t p i t f f t 0));
DATA(insert ( 1247 typelem 26 -1 4 10 0 -1 -1 t p i t f f t 0)); DATA(insert ( 1247 typelem 26 -1 4 10 0 -1 -1 t p i t f f t 0));
DATA(insert ( 1247 typinput 24 -1 4 11 0 -1 -1 t p i t f f t 0)); DATA(insert ( 1247 typarray 26 -1 4 11 0 -1 -1 t p i t f f t 0));
DATA(insert ( 1247 typoutput 24 -1 4 12 0 -1 -1 t p i t f f t 0)); DATA(insert ( 1247 typinput 24 -1 4 12 0 -1 -1 t p i t f f t 0));
DATA(insert ( 1247 typreceive 24 -1 4 13 0 -1 -1 t p i t f f t 0)); DATA(insert ( 1247 typoutput 24 -1 4 13 0 -1 -1 t p i t f f t 0));
DATA(insert ( 1247 typsend 24 -1 4 14 0 -1 -1 t p i t f f t 0)); DATA(insert ( 1247 typreceive 24 -1 4 14 0 -1 -1 t p i t f f t 0));
DATA(insert ( 1247 typmodin 24 -1 4 15 0 -1 -1 t p i t f f t 0)); DATA(insert ( 1247 typsend 24 -1 4 15 0 -1 -1 t p i t f f t 0));
DATA(insert ( 1247 typmodout 24 -1 4 16 0 -1 -1 t p i t f f t 0)); DATA(insert ( 1247 typmodin 24 -1 4 16 0 -1 -1 t p i t f f t 0));
DATA(insert ( 1247 typanalyze 24 -1 4 17 0 -1 -1 t p i t f f t 0)); DATA(insert ( 1247 typmodout 24 -1 4 17 0 -1 -1 t p i t f f t 0));
DATA(insert ( 1247 typalign 18 -1 1 18 0 -1 -1 t p c t f f t 0)); DATA(insert ( 1247 typanalyze 24 -1 4 18 0 -1 -1 t p i t f f t 0));
DATA(insert ( 1247 typstorage 18 -1 1 19 0 -1 -1 t p c t f f t 0)); DATA(insert ( 1247 typalign 18 -1 1 19 0 -1 -1 t p c t f f t 0));
DATA(insert ( 1247 typnotnull 16 -1 1 20 0 -1 -1 t p c t f f t 0)); DATA(insert ( 1247 typstorage 18 -1 1 20 0 -1 -1 t p c t f f t 0));
DATA(insert ( 1247 typbasetype 26 -1 4 21 0 -1 -1 t p i t f f t 0)); DATA(insert ( 1247 typnotnull 16 -1 1 21 0 -1 -1 t p c t f f t 0));
DATA(insert ( 1247 typtypmod 23 -1 4 22 0 -1 -1 t p i t f f t 0)); DATA(insert ( 1247 typbasetype 26 -1 4 22 0 -1 -1 t p i t f f t 0));
DATA(insert ( 1247 typndims 23 -1 4 23 0 -1 -1 t p i t f f t 0)); DATA(insert ( 1247 typtypmod 23 -1 4 23 0 -1 -1 t p i t f f t 0));
DATA(insert ( 1247 typdefaultbin 25 -1 -1 24 0 -1 -1 f x i f f f t 0)); DATA(insert ( 1247 typndims 23 -1 4 24 0 -1 -1 t p i t f f t 0));
DATA(insert ( 1247 typdefault 25 -1 -1 25 0 -1 -1 f x i f f f t 0)); DATA(insert ( 1247 typdefaultbin 25 -1 -1 25 0 -1 -1 f x i f f f t 0));
DATA(insert ( 1247 typdefault 25 -1 -1 26 0 -1 -1 f x i f f f t 0));
DATA(insert ( 1247 ctid 27 0 6 -1 0 -1 -1 f p s t f f t 0)); DATA(insert ( 1247 ctid 27 0 6 -1 0 -1 -1 f p s t f f t 0));
DATA(insert ( 1247 oid 26 0 4 -2 0 -1 -1 t p i t f f t 0)); DATA(insert ( 1247 oid 26 0 4 -2 0 -1 -1 t p i t f f t 0));
DATA(insert ( 1247 xmin 28 0 4 -3 0 -1 -1 t p i t f f t 0)); DATA(insert ( 1247 xmin 28 0 4 -3 0 -1 -1 t p i t f f t 0));

View File

@ -8,7 +8,7 @@
* Portions Copyright (c) 1996-2007, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2007, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* $PostgreSQL: pgsql/src/include/catalog/pg_class.h,v 1.100 2007/01/22 01:35:22 tgl Exp $ * $PostgreSQL: pgsql/src/include/catalog/pg_class.h,v 1.101 2007/05/11 17:57:13 tgl Exp $
* *
* NOTES * NOTES
* the genbki.sh script reads this file and generates .bki * the genbki.sh script reads this file and generates .bki
@ -132,7 +132,7 @@ typedef FormData_pg_class *Form_pg_class;
*/ */
/* Note: "3" in the relfrozenxid column stands for FirstNormalTransactionId */ /* Note: "3" in the relfrozenxid column stands for FirstNormalTransactionId */
DATA(insert OID = 1247 ( pg_type PGNSP 71 PGUID 0 1247 0 0 0 0 0 f f r 25 0 0 0 0 0 t f f f 3 _null_ _null_ )); DATA(insert OID = 1247 ( pg_type PGNSP 71 PGUID 0 1247 0 0 0 0 0 f f r 26 0 0 0 0 0 t f f f 3 _null_ _null_ ));
DESCR(""); 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_ )); 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(""); DESCR("");

View File

@ -8,7 +8,7 @@
* Portions Copyright (c) 1996-2007, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2007, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* $PostgreSQL: pgsql/src/include/catalog/pg_type.h,v 1.182 2007/04/06 04:21:43 tgl Exp $ * $PostgreSQL: pgsql/src/include/catalog/pg_type.h,v 1.183 2007/05/11 17:57:13 tgl Exp $
* *
* NOTES * NOTES
* the genbki.sh script reads this file and generates .bki * the genbki.sh script reads this file and generates .bki
@ -97,6 +97,12 @@ CATALOG(pg_type,1247) BKI_BOOTSTRAP
*/ */
Oid typelem; Oid typelem;
/*
* If there is a "true" array type having this type as element type,
* typarray links to it. Zero if no associated "true" array type.
*/
Oid typarray;
/* /*
* I/O conversion procedures for the datatype. * I/O conversion procedures for the datatype.
*/ */
@ -214,7 +220,7 @@ typedef FormData_pg_type *Form_pg_type;
* compiler constants for pg_type * compiler constants for pg_type
* ---------------- * ----------------
*/ */
#define Natts_pg_type 25 #define Natts_pg_type 26
#define Anum_pg_type_typname 1 #define Anum_pg_type_typname 1
#define Anum_pg_type_typnamespace 2 #define Anum_pg_type_typnamespace 2
#define Anum_pg_type_typowner 3 #define Anum_pg_type_typowner 3
@ -225,21 +231,22 @@ typedef FormData_pg_type *Form_pg_type;
#define Anum_pg_type_typdelim 8 #define Anum_pg_type_typdelim 8
#define Anum_pg_type_typrelid 9 #define Anum_pg_type_typrelid 9
#define Anum_pg_type_typelem 10 #define Anum_pg_type_typelem 10
#define Anum_pg_type_typinput 11 #define Anum_pg_type_typarray 11
#define Anum_pg_type_typoutput 12 #define Anum_pg_type_typinput 12
#define Anum_pg_type_typreceive 13 #define Anum_pg_type_typoutput 13
#define Anum_pg_type_typsend 14 #define Anum_pg_type_typreceive 14
#define Anum_pg_type_typmodin 15 #define Anum_pg_type_typsend 15
#define Anum_pg_type_typmodout 16 #define Anum_pg_type_typmodin 16
#define Anum_pg_type_typanalyze 17 #define Anum_pg_type_typmodout 17
#define Anum_pg_type_typalign 18 #define Anum_pg_type_typanalyze 18
#define Anum_pg_type_typstorage 19 #define Anum_pg_type_typalign 19
#define Anum_pg_type_typnotnull 20 #define Anum_pg_type_typstorage 20
#define Anum_pg_type_typbasetype 21 #define Anum_pg_type_typnotnull 21
#define Anum_pg_type_typtypmod 22 #define Anum_pg_type_typbasetype 22
#define Anum_pg_type_typndims 23 #define Anum_pg_type_typtypmod 23
#define Anum_pg_type_typdefaultbin 24 #define Anum_pg_type_typndims 24
#define Anum_pg_type_typdefault 25 #define Anum_pg_type_typdefaultbin 25
#define Anum_pg_type_typdefault 26
/* ---------------- /* ----------------
@ -255,86 +262,86 @@ typedef FormData_pg_type *Form_pg_type;
*/ */
/* OIDS 1 - 99 */ /* OIDS 1 - 99 */
DATA(insert OID = 16 ( bool PGNSP PGUID 1 t b t \054 0 0 boolin boolout boolrecv boolsend - - - c p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 16 ( bool PGNSP PGUID 1 t b t \054 0 0 1000 boolin boolout boolrecv boolsend - - - c p f 0 -1 0 _null_ _null_ ));
DESCR("boolean, 'true'/'false'"); DESCR("boolean, 'true'/'false'");
#define BOOLOID 16 #define BOOLOID 16
DATA(insert OID = 17 ( bytea PGNSP PGUID -1 f b t \054 0 0 byteain byteaout bytearecv byteasend - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 17 ( bytea PGNSP PGUID -1 f b t \054 0 0 1001 byteain byteaout bytearecv byteasend - - - i x f 0 -1 0 _null_ _null_ ));
DESCR("variable-length string, binary values escaped"); DESCR("variable-length string, binary values escaped");
#define BYTEAOID 17 #define BYTEAOID 17
DATA(insert OID = 18 ( char PGNSP PGUID 1 t b t \054 0 0 charin charout charrecv charsend - - - c p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 18 ( char PGNSP PGUID 1 t b t \054 0 0 1002 charin charout charrecv charsend - - - c p f 0 -1 0 _null_ _null_ ));
DESCR("single character"); DESCR("single character");
#define CHAROID 18 #define CHAROID 18
DATA(insert OID = 19 ( name PGNSP PGUID NAMEDATALEN f b t \054 0 18 namein nameout namerecv namesend - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 19 ( name PGNSP PGUID NAMEDATALEN f b t \054 0 18 1003 namein nameout namerecv namesend - - - i p f 0 -1 0 _null_ _null_ ));
DESCR("63-character type for storing system identifiers"); DESCR("63-character type for storing system identifiers");
#define NAMEOID 19 #define NAMEOID 19
DATA(insert OID = 20 ( int8 PGNSP PGUID 8 f b t \054 0 0 int8in int8out int8recv int8send - - - d p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 20 ( int8 PGNSP PGUID 8 f b t \054 0 0 1016 int8in int8out int8recv int8send - - - d p f 0 -1 0 _null_ _null_ ));
DESCR("~18 digit integer, 8-byte storage"); DESCR("~18 digit integer, 8-byte storage");
#define INT8OID 20 #define INT8OID 20
DATA(insert OID = 21 ( int2 PGNSP PGUID 2 t b t \054 0 0 int2in int2out int2recv int2send - - - s p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 21 ( int2 PGNSP PGUID 2 t b t \054 0 0 1005 int2in int2out int2recv int2send - - - s p f 0 -1 0 _null_ _null_ ));
DESCR("-32 thousand to 32 thousand, 2-byte storage"); DESCR("-32 thousand to 32 thousand, 2-byte storage");
#define INT2OID 21 #define INT2OID 21
DATA(insert OID = 22 ( int2vector PGNSP PGUID -1 f b t \054 0 21 int2vectorin int2vectorout int2vectorrecv int2vectorsend - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 22 ( int2vector PGNSP PGUID -1 f b t \054 0 21 1006 int2vectorin int2vectorout int2vectorrecv int2vectorsend - - - i p f 0 -1 0 _null_ _null_ ));
DESCR("array of int2, used in system tables"); DESCR("array of int2, used in system tables");
#define INT2VECTOROID 22 #define INT2VECTOROID 22
DATA(insert OID = 23 ( int4 PGNSP PGUID 4 t b t \054 0 0 int4in int4out int4recv int4send - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 23 ( int4 PGNSP PGUID 4 t b t \054 0 0 1007 int4in int4out int4recv int4send - - - i p f 0 -1 0 _null_ _null_ ));
DESCR("-2 billion to 2 billion integer, 4-byte storage"); DESCR("-2 billion to 2 billion integer, 4-byte storage");
#define INT4OID 23 #define INT4OID 23
DATA(insert OID = 24 ( regproc PGNSP PGUID 4 t b t \054 0 0 regprocin regprocout regprocrecv regprocsend - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 24 ( regproc PGNSP PGUID 4 t b t \054 0 0 1008 regprocin regprocout regprocrecv regprocsend - - - i p f 0 -1 0 _null_ _null_ ));
DESCR("registered procedure"); DESCR("registered procedure");
#define REGPROCOID 24 #define REGPROCOID 24
DATA(insert OID = 25 ( text PGNSP PGUID -1 f b t \054 0 0 textin textout textrecv textsend - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 25 ( text PGNSP PGUID -1 f b t \054 0 0 1009 textin textout textrecv textsend - - - i x f 0 -1 0 _null_ _null_ ));
DESCR("variable-length string, no limit specified"); DESCR("variable-length string, no limit specified");
#define TEXTOID 25 #define TEXTOID 25
DATA(insert OID = 26 ( oid PGNSP PGUID 4 t b t \054 0 0 oidin oidout oidrecv oidsend - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 26 ( oid PGNSP PGUID 4 t b t \054 0 0 1028 oidin oidout oidrecv oidsend - - - i p f 0 -1 0 _null_ _null_ ));
DESCR("object identifier(oid), maximum 4 billion"); DESCR("object identifier(oid), maximum 4 billion");
#define OIDOID 26 #define OIDOID 26
DATA(insert OID = 27 ( tid PGNSP PGUID 6 f b t \054 0 0 tidin tidout tidrecv tidsend - - - s p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 27 ( tid PGNSP PGUID 6 f b t \054 0 0 1010 tidin tidout tidrecv tidsend - - - s p f 0 -1 0 _null_ _null_ ));
DESCR("(Block, offset), physical location of tuple"); DESCR("(Block, offset), physical location of tuple");
#define TIDOID 27 #define TIDOID 27
DATA(insert OID = 28 ( xid PGNSP PGUID 4 t b t \054 0 0 xidin xidout xidrecv xidsend - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 28 ( xid PGNSP PGUID 4 t b t \054 0 0 1011 xidin xidout xidrecv xidsend - - - i p f 0 -1 0 _null_ _null_ ));
DESCR("transaction id"); DESCR("transaction id");
#define XIDOID 28 #define XIDOID 28
DATA(insert OID = 29 ( cid PGNSP PGUID 4 t b t \054 0 0 cidin cidout cidrecv cidsend - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 29 ( cid PGNSP PGUID 4 t b t \054 0 0 1012 cidin cidout cidrecv cidsend - - - i p f 0 -1 0 _null_ _null_ ));
DESCR("command identifier type, sequence in transaction id"); DESCR("command identifier type, sequence in transaction id");
#define CIDOID 29 #define CIDOID 29
DATA(insert OID = 30 ( oidvector PGNSP PGUID -1 f b t \054 0 26 oidvectorin oidvectorout oidvectorrecv oidvectorsend - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 30 ( oidvector PGNSP PGUID -1 f b t \054 0 26 1013 oidvectorin oidvectorout oidvectorrecv oidvectorsend - - - i p f 0 -1 0 _null_ _null_ ));
DESCR("array of oids, used in system tables"); DESCR("array of oids, used in system tables");
#define OIDVECTOROID 30 #define OIDVECTOROID 30
/* hand-built rowtype entries for bootstrapped catalogs: */ /* hand-built rowtype entries for bootstrapped catalogs: */
DATA(insert OID = 71 ( pg_type PGNSP PGUID -1 f c t \054 1247 0 record_in record_out record_recv record_send - - - d x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 71 ( pg_type PGNSP PGUID -1 f c t \054 1247 0 0 record_in record_out record_recv record_send - - - d x f 0 -1 0 _null_ _null_ ));
#define PG_TYPE_RELTYPE_OID 71 #define PG_TYPE_RELTYPE_OID 71
DATA(insert OID = 75 ( pg_attribute PGNSP PGUID -1 f c t \054 1249 0 record_in record_out record_recv record_send - - - d x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 75 ( pg_attribute PGNSP PGUID -1 f c t \054 1249 0 0 record_in record_out record_recv record_send - - - d x f 0 -1 0 _null_ _null_ ));
#define PG_ATTRIBUTE_RELTYPE_OID 75 #define PG_ATTRIBUTE_RELTYPE_OID 75
DATA(insert OID = 81 ( pg_proc PGNSP PGUID -1 f c t \054 1255 0 record_in record_out record_recv record_send - - - d x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 81 ( pg_proc PGNSP PGUID -1 f c t \054 1255 0 0 record_in record_out record_recv record_send - - - d x f 0 -1 0 _null_ _null_ ));
#define PG_PROC_RELTYPE_OID 81 #define PG_PROC_RELTYPE_OID 81
DATA(insert OID = 83 ( pg_class PGNSP PGUID -1 f c t \054 1259 0 record_in record_out record_recv record_send - - - d x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 83 ( pg_class PGNSP PGUID -1 f c t \054 1259 0 0 record_in record_out record_recv record_send - - - d x f 0 -1 0 _null_ _null_ ));
#define PG_CLASS_RELTYPE_OID 83 #define PG_CLASS_RELTYPE_OID 83
/* OIDS 100 - 199 */ /* OIDS 100 - 199 */
DATA(insert OID = 142 ( xml PGNSP PGUID -1 f b t \054 0 0 xml_in xml_out xml_recv xml_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 142 ( xml PGNSP PGUID -1 f b t \054 0 0 143 xml_in xml_out xml_recv xml_send - - - i x f 0 -1 0 _null_ _null_ ));
DESCR("XML content"); DESCR("XML content");
#define XMLOID 142 #define XMLOID 142
DATA(insert OID = 143 ( _xml PGNSP PGUID -1 f b t \054 0 142 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 143 ( _xml PGNSP PGUID -1 f b t \054 0 142 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
/* OIDS 200 - 299 */ /* OIDS 200 - 299 */
DATA(insert OID = 210 ( smgr PGNSP PGUID 2 t b t \054 0 0 smgrin smgrout - - - - - s p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 210 ( smgr PGNSP PGUID 2 t b t \054 0 0 0 smgrin smgrout - - - - - s p f 0 -1 0 _null_ _null_ ));
DESCR("storage manager"); DESCR("storage manager");
/* OIDS 300 - 399 */ /* OIDS 300 - 399 */
@ -344,200 +351,200 @@ DESCR("storage manager");
/* OIDS 500 - 599 */ /* OIDS 500 - 599 */
/* OIDS 600 - 699 */ /* OIDS 600 - 699 */
DATA(insert OID = 600 ( point PGNSP PGUID 16 f b t \054 0 701 point_in point_out point_recv point_send - - - d p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 600 ( point PGNSP PGUID 16 f b t \054 0 701 1017 point_in point_out point_recv point_send - - - d p f 0 -1 0 _null_ _null_ ));
DESCR("geometric point '(x, y)'"); DESCR("geometric point '(x, y)'");
#define POINTOID 600 #define POINTOID 600
DATA(insert OID = 601 ( lseg PGNSP PGUID 32 f b t \054 0 600 lseg_in lseg_out lseg_recv lseg_send - - - d p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 601 ( lseg PGNSP PGUID 32 f b t \054 0 600 1018 lseg_in lseg_out lseg_recv lseg_send - - - d p f 0 -1 0 _null_ _null_ ));
DESCR("geometric line segment '(pt1,pt2)'"); DESCR("geometric line segment '(pt1,pt2)'");
#define LSEGOID 601 #define LSEGOID 601
DATA(insert OID = 602 ( path PGNSP PGUID -1 f b t \054 0 0 path_in path_out path_recv path_send - - - d x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 602 ( path PGNSP PGUID -1 f b t \054 0 0 1019 path_in path_out path_recv path_send - - - d x f 0 -1 0 _null_ _null_ ));
DESCR("geometric path '(pt1,...)'"); DESCR("geometric path '(pt1,...)'");
#define PATHOID 602 #define PATHOID 602
DATA(insert OID = 603 ( box PGNSP PGUID 32 f b t \073 0 600 box_in box_out box_recv box_send - - - d p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 603 ( box PGNSP PGUID 32 f b t \073 0 600 1020 box_in box_out box_recv box_send - - - d p f 0 -1 0 _null_ _null_ ));
DESCR("geometric box '(lower left,upper right)'"); DESCR("geometric box '(lower left,upper right)'");
#define BOXOID 603 #define BOXOID 603
DATA(insert OID = 604 ( polygon PGNSP PGUID -1 f b t \054 0 0 poly_in poly_out poly_recv poly_send - - - d x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 604 ( polygon PGNSP PGUID -1 f b t \054 0 0 1027 poly_in poly_out poly_recv poly_send - - - d x f 0 -1 0 _null_ _null_ ));
DESCR("geometric polygon '(pt1,...)'"); DESCR("geometric polygon '(pt1,...)'");
#define POLYGONOID 604 #define POLYGONOID 604
DATA(insert OID = 628 ( line PGNSP PGUID 32 f b t \054 0 701 line_in line_out line_recv line_send - - - d p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 628 ( line PGNSP PGUID 32 f b t \054 0 701 629 line_in line_out line_recv line_send - - - d p f 0 -1 0 _null_ _null_ ));
DESCR("geometric line (not implemented)'"); DESCR("geometric line (not implemented)'");
#define LINEOID 628 #define LINEOID 628
DATA(insert OID = 629 ( _line PGNSP PGUID -1 f b t \054 0 628 array_in array_out array_recv array_send - - - d x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 629 ( _line PGNSP PGUID -1 f b t \054 0 628 0 array_in array_out array_recv array_send - - - d x f 0 -1 0 _null_ _null_ ));
DESCR(""); DESCR("");
/* OIDS 700 - 799 */ /* OIDS 700 - 799 */
DATA(insert OID = 700 ( float4 PGNSP PGUID 4 f b t \054 0 0 float4in float4out float4recv float4send - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 700 ( float4 PGNSP PGUID 4 f b t \054 0 0 1021 float4in float4out float4recv float4send - - - i p f 0 -1 0 _null_ _null_ ));
DESCR("single-precision floating point number, 4-byte storage"); DESCR("single-precision floating point number, 4-byte storage");
#define FLOAT4OID 700 #define FLOAT4OID 700
DATA(insert OID = 701 ( float8 PGNSP PGUID 8 f b t \054 0 0 float8in float8out float8recv float8send - - - d p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 701 ( float8 PGNSP PGUID 8 f b t \054 0 0 1022 float8in float8out float8recv float8send - - - d p f 0 -1 0 _null_ _null_ ));
DESCR("double-precision floating point number, 8-byte storage"); DESCR("double-precision floating point number, 8-byte storage");
#define FLOAT8OID 701 #define FLOAT8OID 701
DATA(insert OID = 702 ( abstime PGNSP PGUID 4 t b t \054 0 0 abstimein abstimeout abstimerecv abstimesend - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 702 ( abstime PGNSP PGUID 4 t b t \054 0 0 1023 abstimein abstimeout abstimerecv abstimesend - - - i p f 0 -1 0 _null_ _null_ ));
DESCR("absolute, limited-range date and time (Unix system time)"); DESCR("absolute, limited-range date and time (Unix system time)");
#define ABSTIMEOID 702 #define ABSTIMEOID 702
DATA(insert OID = 703 ( reltime PGNSP PGUID 4 t b t \054 0 0 reltimein reltimeout reltimerecv reltimesend - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 703 ( reltime PGNSP PGUID 4 t b t \054 0 0 1024 reltimein reltimeout reltimerecv reltimesend - - - i p f 0 -1 0 _null_ _null_ ));
DESCR("relative, limited-range time interval (Unix delta time)"); DESCR("relative, limited-range time interval (Unix delta time)");
#define RELTIMEOID 703 #define RELTIMEOID 703
DATA(insert OID = 704 ( tinterval PGNSP PGUID 12 f b t \054 0 0 tintervalin tintervalout tintervalrecv tintervalsend - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 704 ( tinterval PGNSP PGUID 12 f b t \054 0 0 1025 tintervalin tintervalout tintervalrecv tintervalsend - - - i p f 0 -1 0 _null_ _null_ ));
DESCR("(abstime,abstime), time interval"); DESCR("(abstime,abstime), time interval");
#define TINTERVALOID 704 #define TINTERVALOID 704
DATA(insert OID = 705 ( unknown PGNSP PGUID -2 f b t \054 0 0 unknownin unknownout unknownrecv unknownsend - - - c p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 705 ( unknown PGNSP PGUID -2 f b t \054 0 0 0 unknownin unknownout unknownrecv unknownsend - - - c p f 0 -1 0 _null_ _null_ ));
DESCR(""); DESCR("");
#define UNKNOWNOID 705 #define UNKNOWNOID 705
DATA(insert OID = 718 ( circle PGNSP PGUID 24 f b t \054 0 0 circle_in circle_out circle_recv circle_send - - - d p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 718 ( circle PGNSP PGUID 24 f b t \054 0 0 719 circle_in circle_out circle_recv circle_send - - - d p f 0 -1 0 _null_ _null_ ));
DESCR("geometric circle '(center,radius)'"); DESCR("geometric circle '(center,radius)'");
#define CIRCLEOID 718 #define CIRCLEOID 718
DATA(insert OID = 719 ( _circle PGNSP PGUID -1 f b t \054 0 718 array_in array_out array_recv array_send - - - d x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 719 ( _circle PGNSP PGUID -1 f b t \054 0 718 0 array_in array_out array_recv array_send - - - d x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 790 ( money PGNSP PGUID 8 f b t \054 0 0 cash_in cash_out cash_recv cash_send - - - d p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 790 ( money PGNSP PGUID 8 f b t \054 0 0 791 cash_in cash_out cash_recv cash_send - - - d p f 0 -1 0 _null_ _null_ ));
DESCR("monetary amounts, $d,ddd.cc"); DESCR("monetary amounts, $d,ddd.cc");
#define CASHOID 790 #define CASHOID 790
DATA(insert OID = 791 ( _money PGNSP PGUID -1 f b t \054 0 790 array_in array_out array_recv array_send - - - d x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 791 ( _money PGNSP PGUID -1 f b t \054 0 790 0 array_in array_out array_recv array_send - - - d x f 0 -1 0 _null_ _null_ ));
/* OIDS 800 - 899 */ /* OIDS 800 - 899 */
DATA(insert OID = 829 ( macaddr PGNSP PGUID 6 f b t \054 0 0 macaddr_in macaddr_out macaddr_recv macaddr_send - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 829 ( macaddr PGNSP PGUID 6 f b t \054 0 0 1040 macaddr_in macaddr_out macaddr_recv macaddr_send - - - i p f 0 -1 0 _null_ _null_ ));
DESCR("XX:XX:XX:XX:XX:XX, MAC address"); DESCR("XX:XX:XX:XX:XX:XX, MAC address");
#define MACADDROID 829 #define MACADDROID 829
DATA(insert OID = 869 ( inet PGNSP PGUID -1 f b t \054 0 0 inet_in inet_out inet_recv inet_send - - - i m f 0 -1 0 _null_ _null_ )); DATA(insert OID = 869 ( inet PGNSP PGUID -1 f b t \054 0 0 1041 inet_in inet_out inet_recv inet_send - - - i m f 0 -1 0 _null_ _null_ ));
DESCR("IP address/netmask, host address, netmask optional"); DESCR("IP address/netmask, host address, netmask optional");
#define INETOID 869 #define INETOID 869
DATA(insert OID = 650 ( cidr PGNSP PGUID -1 f b t \054 0 0 cidr_in cidr_out cidr_recv cidr_send - - - i m f 0 -1 0 _null_ _null_ )); DATA(insert OID = 650 ( cidr PGNSP PGUID -1 f b t \054 0 0 651 cidr_in cidr_out cidr_recv cidr_send - - - i m f 0 -1 0 _null_ _null_ ));
DESCR("network IP address/netmask, network address"); DESCR("network IP address/netmask, network address");
#define CIDROID 650 #define CIDROID 650
/* OIDS 900 - 999 */ /* OIDS 900 - 999 */
/* OIDS 1000 - 1099 */ /* OIDS 1000 - 1099 */
DATA(insert OID = 1000 ( _bool PGNSP PGUID -1 f b t \054 0 16 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1000 ( _bool PGNSP PGUID -1 f b t \054 0 16 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1001 ( _bytea PGNSP PGUID -1 f b t \054 0 17 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1001 ( _bytea PGNSP PGUID -1 f b t \054 0 17 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1002 ( _char PGNSP PGUID -1 f b t \054 0 18 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1002 ( _char PGNSP PGUID -1 f b t \054 0 18 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1003 ( _name PGNSP PGUID -1 f b t \054 0 19 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1003 ( _name PGNSP PGUID -1 f b t \054 0 19 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1005 ( _int2 PGNSP PGUID -1 f b t \054 0 21 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1005 ( _int2 PGNSP PGUID -1 f b t \054 0 21 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1006 ( _int2vector PGNSP PGUID -1 f b t \054 0 22 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1006 ( _int2vector PGNSP PGUID -1 f b t \054 0 22 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1007 ( _int4 PGNSP PGUID -1 f b t \054 0 23 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1007 ( _int4 PGNSP PGUID -1 f b t \054 0 23 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
#define INT4ARRAYOID 1007 #define INT4ARRAYOID 1007
DATA(insert OID = 1008 ( _regproc PGNSP PGUID -1 f b t \054 0 24 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1008 ( _regproc PGNSP PGUID -1 f b t \054 0 24 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1009 ( _text PGNSP PGUID -1 f b t \054 0 25 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1009 ( _text PGNSP PGUID -1 f b t \054 0 25 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1028 ( _oid PGNSP PGUID -1 f b t \054 0 26 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1028 ( _oid PGNSP PGUID -1 f b t \054 0 26 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1010 ( _tid PGNSP PGUID -1 f b t \054 0 27 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1010 ( _tid PGNSP PGUID -1 f b t \054 0 27 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1011 ( _xid PGNSP PGUID -1 f b t \054 0 28 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1011 ( _xid PGNSP PGUID -1 f b t \054 0 28 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1012 ( _cid PGNSP PGUID -1 f b t \054 0 29 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1012 ( _cid PGNSP PGUID -1 f b t \054 0 29 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1013 ( _oidvector PGNSP PGUID -1 f b t \054 0 30 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1013 ( _oidvector PGNSP PGUID -1 f b t \054 0 30 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1014 ( _bpchar PGNSP PGUID -1 f b t \054 0 1042 array_in array_out array_recv array_send bpchartypmodin bpchartypmodout - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1014 ( _bpchar PGNSP PGUID -1 f b t \054 0 1042 0 array_in array_out array_recv array_send bpchartypmodin bpchartypmodout - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1015 ( _varchar PGNSP PGUID -1 f b t \054 0 1043 array_in array_out array_recv array_send varchartypmodin varchartypmodout - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1015 ( _varchar PGNSP PGUID -1 f b t \054 0 1043 0 array_in array_out array_recv array_send varchartypmodin varchartypmodout - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1016 ( _int8 PGNSP PGUID -1 f b t \054 0 20 array_in array_out array_recv array_send - - - d x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1016 ( _int8 PGNSP PGUID -1 f b t \054 0 20 0 array_in array_out array_recv array_send - - - d x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1017 ( _point PGNSP PGUID -1 f b t \054 0 600 array_in array_out array_recv array_send - - - d x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1017 ( _point PGNSP PGUID -1 f b t \054 0 600 0 array_in array_out array_recv array_send - - - d x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1018 ( _lseg PGNSP PGUID -1 f b t \054 0 601 array_in array_out array_recv array_send - - - d x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1018 ( _lseg PGNSP PGUID -1 f b t \054 0 601 0 array_in array_out array_recv array_send - - - d x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1019 ( _path PGNSP PGUID -1 f b t \054 0 602 array_in array_out array_recv array_send - - - d x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1019 ( _path PGNSP PGUID -1 f b t \054 0 602 0 array_in array_out array_recv array_send - - - d x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1020 ( _box PGNSP PGUID -1 f b t \073 0 603 array_in array_out array_recv array_send - - - d x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1020 ( _box PGNSP PGUID -1 f b t \073 0 603 0 array_in array_out array_recv array_send - - - d x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1021 ( _float4 PGNSP PGUID -1 f b t \054 0 700 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1021 ( _float4 PGNSP PGUID -1 f b t \054 0 700 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
#define FLOAT4ARRAYOID 1021 #define FLOAT4ARRAYOID 1021
DATA(insert OID = 1022 ( _float8 PGNSP PGUID -1 f b t \054 0 701 array_in array_out array_recv array_send - - - d x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1022 ( _float8 PGNSP PGUID -1 f b t \054 0 701 0 array_in array_out array_recv array_send - - - d x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1023 ( _abstime PGNSP PGUID -1 f b t \054 0 702 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1023 ( _abstime PGNSP PGUID -1 f b t \054 0 702 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1024 ( _reltime PGNSP PGUID -1 f b t \054 0 703 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1024 ( _reltime PGNSP PGUID -1 f b t \054 0 703 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1025 ( _tinterval PGNSP PGUID -1 f b t \054 0 704 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1025 ( _tinterval PGNSP PGUID -1 f b t \054 0 704 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1027 ( _polygon PGNSP PGUID -1 f b t \054 0 604 array_in array_out array_recv array_send - - - d x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1027 ( _polygon PGNSP PGUID -1 f b t \054 0 604 0 array_in array_out array_recv array_send - - - d x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1033 ( aclitem PGNSP PGUID 12 f b t \054 0 0 aclitemin aclitemout - - - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1033 ( aclitem PGNSP PGUID 12 f b t \054 0 0 1034 aclitemin aclitemout - - - - - i p f 0 -1 0 _null_ _null_ ));
DESCR("access control list"); DESCR("access control list");
#define ACLITEMOID 1033 #define ACLITEMOID 1033
DATA(insert OID = 1034 ( _aclitem PGNSP PGUID -1 f b t \054 0 1033 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1034 ( _aclitem PGNSP PGUID -1 f b t \054 0 1033 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1040 ( _macaddr PGNSP PGUID -1 f b t \054 0 829 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1040 ( _macaddr PGNSP PGUID -1 f b t \054 0 829 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1041 ( _inet PGNSP PGUID -1 f b t \054 0 869 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1041 ( _inet PGNSP PGUID -1 f b t \054 0 869 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 651 ( _cidr PGNSP PGUID -1 f b t \054 0 650 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 651 ( _cidr PGNSP PGUID -1 f b t \054 0 650 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1042 ( bpchar PGNSP PGUID -1 f b t \054 0 0 bpcharin bpcharout bpcharrecv bpcharsend bpchartypmodin bpchartypmodout - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1042 ( bpchar PGNSP PGUID -1 f b t \054 0 0 1014 bpcharin bpcharout bpcharrecv bpcharsend bpchartypmodin bpchartypmodout - i x f 0 -1 0 _null_ _null_ ));
DESCR("char(length), blank-padded string, fixed storage length"); DESCR("char(length), blank-padded string, fixed storage length");
#define BPCHAROID 1042 #define BPCHAROID 1042
DATA(insert OID = 1043 ( varchar PGNSP PGUID -1 f b t \054 0 0 varcharin varcharout varcharrecv varcharsend varchartypmodin varchartypmodout - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1043 ( varchar PGNSP PGUID -1 f b t \054 0 0 1015 varcharin varcharout varcharrecv varcharsend varchartypmodin varchartypmodout - i x f 0 -1 0 _null_ _null_ ));
DESCR("varchar(length), non-blank-padded string, variable storage length"); DESCR("varchar(length), non-blank-padded string, variable storage length");
#define VARCHAROID 1043 #define VARCHAROID 1043
DATA(insert OID = 1082 ( date PGNSP PGUID 4 t b t \054 0 0 date_in date_out date_recv date_send - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1082 ( date PGNSP PGUID 4 t b t \054 0 0 1182 date_in date_out date_recv date_send - - - i p f 0 -1 0 _null_ _null_ ));
DESCR("ANSI SQL date"); DESCR("ANSI SQL date");
#define DATEOID 1082 #define DATEOID 1082
DATA(insert OID = 1083 ( time PGNSP PGUID 8 f b t \054 0 0 time_in time_out time_recv time_send timetypmodin timetypmodout - d p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1083 ( time PGNSP PGUID 8 f b t \054 0 0 1183 time_in time_out time_recv time_send timetypmodin timetypmodout - d p f 0 -1 0 _null_ _null_ ));
DESCR("hh:mm:ss, ANSI SQL time"); DESCR("hh:mm:ss, ANSI SQL time");
#define TIMEOID 1083 #define TIMEOID 1083
/* OIDS 1100 - 1199 */ /* OIDS 1100 - 1199 */
DATA(insert OID = 1114 ( timestamp PGNSP PGUID 8 f b t \054 0 0 timestamp_in timestamp_out timestamp_recv timestamp_send timestamptypmodin timestamptypmodout - d p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1114 ( timestamp PGNSP PGUID 8 f b t \054 0 0 1115 timestamp_in timestamp_out timestamp_recv timestamp_send timestamptypmodin timestamptypmodout - d p f 0 -1 0 _null_ _null_ ));
DESCR("date and time"); DESCR("date and time");
#define TIMESTAMPOID 1114 #define TIMESTAMPOID 1114
DATA(insert OID = 1115 ( _timestamp PGNSP PGUID -1 f b t \054 0 1114 array_in array_out array_recv array_send timestamptypmodin timestamptypmodout - d x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1115 ( _timestamp PGNSP PGUID -1 f b t \054 0 1114 0 array_in array_out array_recv array_send timestamptypmodin timestamptypmodout - d x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1182 ( _date PGNSP PGUID -1 f b t \054 0 1082 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1182 ( _date PGNSP PGUID -1 f b t \054 0 1082 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1183 ( _time PGNSP PGUID -1 f b t \054 0 1083 array_in array_out array_recv array_send timetypmodin timetypmodout - d x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1183 ( _time PGNSP PGUID -1 f b t \054 0 1083 0 array_in array_out array_recv array_send timetypmodin timetypmodout - d x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1184 ( timestamptz PGNSP PGUID 8 f b t \054 0 0 timestamptz_in timestamptz_out timestamptz_recv timestamptz_send timestamptztypmodin timestamptztypmodout - d p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1184 ( timestamptz PGNSP PGUID 8 f b t \054 0 0 1185 timestamptz_in timestamptz_out timestamptz_recv timestamptz_send timestamptztypmodin timestamptztypmodout - d p f 0 -1 0 _null_ _null_ ));
DESCR("date and time with time zone"); DESCR("date and time with time zone");
#define TIMESTAMPTZOID 1184 #define TIMESTAMPTZOID 1184
DATA(insert OID = 1185 ( _timestamptz PGNSP PGUID -1 f b t \054 0 1184 array_in array_out array_recv array_send timestamptztypmodin timestamptztypmodout - d x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1185 ( _timestamptz PGNSP PGUID -1 f b t \054 0 1184 0 array_in array_out array_recv array_send timestamptztypmodin timestamptztypmodout - d x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1186 ( interval PGNSP PGUID 16 f b t \054 0 0 interval_in interval_out interval_recv interval_send intervaltypmodin intervaltypmodout - d p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1186 ( interval PGNSP PGUID 16 f b t \054 0 0 1187 interval_in interval_out interval_recv interval_send intervaltypmodin intervaltypmodout - d p f 0 -1 0 _null_ _null_ ));
DESCR("@ <number> <units>, time interval"); DESCR("@ <number> <units>, time interval");
#define INTERVALOID 1186 #define INTERVALOID 1186
DATA(insert OID = 1187 ( _interval PGNSP PGUID -1 f b t \054 0 1186 array_in array_out array_recv array_send intervaltypmodin intervaltypmodout - d x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1187 ( _interval PGNSP PGUID -1 f b t \054 0 1186 0 array_in array_out array_recv array_send intervaltypmodin intervaltypmodout - d x f 0 -1 0 _null_ _null_ ));
/* OIDS 1200 - 1299 */ /* OIDS 1200 - 1299 */
DATA(insert OID = 1231 ( _numeric PGNSP PGUID -1 f b t \054 0 1700 array_in array_out array_recv array_send numerictypmodin numerictypmodout - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1231 ( _numeric PGNSP PGUID -1 f b t \054 0 1700 0 array_in array_out array_recv array_send numerictypmodin numerictypmodout - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1266 ( timetz PGNSP PGUID 12 f b t \054 0 0 timetz_in timetz_out timetz_recv timetz_send timetztypmodin timetztypmodout - d p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1266 ( timetz PGNSP PGUID 12 f b t \054 0 0 1270 timetz_in timetz_out timetz_recv timetz_send timetztypmodin timetztypmodout - d p f 0 -1 0 _null_ _null_ ));
DESCR("hh:mm:ss, ANSI SQL time"); DESCR("hh:mm:ss, ANSI SQL time");
#define TIMETZOID 1266 #define TIMETZOID 1266
DATA(insert OID = 1270 ( _timetz PGNSP PGUID -1 f b t \054 0 1266 array_in array_out array_recv array_send timetztypmodin timetztypmodout - d x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1270 ( _timetz PGNSP PGUID -1 f b t \054 0 1266 0 array_in array_out array_recv array_send timetztypmodin timetztypmodout - d x f 0 -1 0 _null_ _null_ ));
/* OIDS 1500 - 1599 */ /* OIDS 1500 - 1599 */
DATA(insert OID = 1560 ( bit PGNSP PGUID -1 f b t \054 0 0 bit_in bit_out bit_recv bit_send bittypmodin bittypmodout - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1560 ( bit PGNSP PGUID -1 f b t \054 0 0 1561 bit_in bit_out bit_recv bit_send bittypmodin bittypmodout - i x f 0 -1 0 _null_ _null_ ));
DESCR("fixed-length bit string"); DESCR("fixed-length bit string");
#define BITOID 1560 #define BITOID 1560
DATA(insert OID = 1561 ( _bit PGNSP PGUID -1 f b t \054 0 1560 array_in array_out array_recv array_send bittypmodin bittypmodout - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1561 ( _bit PGNSP PGUID -1 f b t \054 0 1560 0 array_in array_out array_recv array_send bittypmodin bittypmodout - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 1562 ( varbit PGNSP PGUID -1 f b t \054 0 0 varbit_in varbit_out varbit_recv varbit_send varbittypmodin varbittypmodout - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1562 ( varbit PGNSP PGUID -1 f b t \054 0 0 1563 varbit_in varbit_out varbit_recv varbit_send varbittypmodin varbittypmodout - i x f 0 -1 0 _null_ _null_ ));
DESCR("variable-length bit string"); DESCR("variable-length bit string");
#define VARBITOID 1562 #define VARBITOID 1562
DATA(insert OID = 1563 ( _varbit PGNSP PGUID -1 f b t \054 0 1562 array_in array_out array_recv array_send varbittypmodin varbittypmodout - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1563 ( _varbit PGNSP PGUID -1 f b t \054 0 1562 0 array_in array_out array_recv array_send varbittypmodin varbittypmodout - i x f 0 -1 0 _null_ _null_ ));
/* OIDS 1600 - 1699 */ /* OIDS 1600 - 1699 */
/* OIDS 1700 - 1799 */ /* OIDS 1700 - 1799 */
DATA(insert OID = 1700 ( numeric PGNSP PGUID -1 f b t \054 0 0 numeric_in numeric_out numeric_recv numeric_send numerictypmodin numerictypmodout - i m f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1700 ( numeric PGNSP PGUID -1 f b t \054 0 0 1231 numeric_in numeric_out numeric_recv numeric_send numerictypmodin numerictypmodout - i m f 0 -1 0 _null_ _null_ ));
DESCR("numeric(precision, decimal), arbitrary precision number"); DESCR("numeric(precision, decimal), arbitrary precision number");
#define NUMERICOID 1700 #define NUMERICOID 1700
DATA(insert OID = 1790 ( refcursor PGNSP PGUID -1 f b t \054 0 0 textin textout textrecv textsend - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 1790 ( refcursor PGNSP PGUID -1 f b t \054 0 0 2201 textin textout textrecv textsend - - - i x f 0 -1 0 _null_ _null_ ));
DESCR("reference cursor (portal name)"); DESCR("reference cursor (portal name)");
#define REFCURSOROID 1790 #define REFCURSOROID 1790
/* OIDS 2200 - 2299 */ /* OIDS 2200 - 2299 */
DATA(insert OID = 2201 ( _refcursor PGNSP PGUID -1 f b t \054 0 1790 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 2201 ( _refcursor PGNSP PGUID -1 f b t \054 0 1790 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 2202 ( regprocedure PGNSP PGUID 4 t b t \054 0 0 regprocedurein regprocedureout regprocedurerecv regproceduresend - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 2202 ( regprocedure PGNSP PGUID 4 t b t \054 0 0 2207 regprocedurein regprocedureout regprocedurerecv regproceduresend - - - i p f 0 -1 0 _null_ _null_ ));
DESCR("registered procedure (with args)"); DESCR("registered procedure (with args)");
#define REGPROCEDUREOID 2202 #define REGPROCEDUREOID 2202
DATA(insert OID = 2203 ( regoper PGNSP PGUID 4 t b t \054 0 0 regoperin regoperout regoperrecv regopersend - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 2203 ( regoper PGNSP PGUID 4 t b t \054 0 0 2208 regoperin regoperout regoperrecv regopersend - - - i p f 0 -1 0 _null_ _null_ ));
DESCR("registered operator"); DESCR("registered operator");
#define REGOPEROID 2203 #define REGOPEROID 2203
DATA(insert OID = 2204 ( regoperator PGNSP PGUID 4 t b t \054 0 0 regoperatorin regoperatorout regoperatorrecv regoperatorsend - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 2204 ( regoperator PGNSP PGUID 4 t b t \054 0 0 2209 regoperatorin regoperatorout regoperatorrecv regoperatorsend - - - i p f 0 -1 0 _null_ _null_ ));
DESCR("registered operator (with args)"); DESCR("registered operator (with args)");
#define REGOPERATOROID 2204 #define REGOPERATOROID 2204
DATA(insert OID = 2205 ( regclass PGNSP PGUID 4 t b t \054 0 0 regclassin regclassout regclassrecv regclasssend - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 2205 ( regclass PGNSP PGUID 4 t b t \054 0 0 2210 regclassin regclassout regclassrecv regclasssend - - - i p f 0 -1 0 _null_ _null_ ));
DESCR("registered class"); DESCR("registered class");
#define REGCLASSOID 2205 #define REGCLASSOID 2205
DATA(insert OID = 2206 ( regtype PGNSP PGUID 4 t b t \054 0 0 regtypein regtypeout regtyperecv regtypesend - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 2206 ( regtype PGNSP PGUID 4 t b t \054 0 0 2211 regtypein regtypeout regtyperecv regtypesend - - - i p f 0 -1 0 _null_ _null_ ));
DESCR("registered type"); DESCR("registered type");
#define REGTYPEOID 2206 #define REGTYPEOID 2206
DATA(insert OID = 2207 ( _regprocedure PGNSP PGUID -1 f b t \054 0 2202 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 2207 ( _regprocedure PGNSP PGUID -1 f b t \054 0 2202 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 2208 ( _regoper PGNSP PGUID -1 f b t \054 0 2203 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 2208 ( _regoper PGNSP PGUID -1 f b t \054 0 2203 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 2209 ( _regoperator PGNSP PGUID -1 f b t \054 0 2204 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 2209 ( _regoperator PGNSP PGUID -1 f b t \054 0 2204 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 2210 ( _regclass PGNSP PGUID -1 f b t \054 0 2205 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 2210 ( _regclass PGNSP PGUID -1 f b t \054 0 2205 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
DATA(insert OID = 2211 ( _regtype PGNSP PGUID -1 f b t \054 0 2206 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 2211 ( _regtype PGNSP PGUID -1 f b t \054 0 2206 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
#define REGTYPEARRAYOID 2211 #define REGTYPEARRAYOID 2211
/* uuid */ /* uuid */
DATA(insert OID = 2950 ( uuid PGNSP PGUID 16 f b t \054 0 0 uuid_in uuid_out uuid_recv uuid_send - - - c p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 2950 ( uuid PGNSP PGUID 16 f b t \054 0 0 2951 uuid_in uuid_out uuid_recv uuid_send - - - c p f 0 -1 0 _null_ _null_ ));
DESCR("UUID datatype"); DESCR("UUID datatype");
DATA(insert OID = 2951 ( _uuid PGNSP PGUID -1 f b t \054 0 2950 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 2951 ( _uuid PGNSP PGUID -1 f b t \054 0 2950 0 array_in array_out array_recv array_send - - - i x f 0 -1 0 _null_ _null_ ));
/* /*
* pseudo-types * pseudo-types
@ -548,27 +555,27 @@ DATA(insert OID = 2951 ( _uuid PGNSP PGUID -1 f b t \054 0 2950 array_in array
* argument and result types (if supported by the function's implementation * argument and result types (if supported by the function's implementation
* language). * language).
*/ */
DATA(insert OID = 2249 ( record PGNSP PGUID -1 f p t \054 0 0 record_in record_out record_recv record_send - - - d x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 2249 ( record PGNSP PGUID -1 f p t \054 0 0 0 record_in record_out record_recv record_send - - - d x f 0 -1 0 _null_ _null_ ));
#define RECORDOID 2249 #define RECORDOID 2249
DATA(insert OID = 2275 ( cstring PGNSP PGUID -2 f p t \054 0 0 cstring_in cstring_out cstring_recv cstring_send - - - c p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 2275 ( cstring PGNSP PGUID -2 f p t \054 0 0 0 cstring_in cstring_out cstring_recv cstring_send - - - c p f 0 -1 0 _null_ _null_ ));
#define CSTRINGOID 2275 #define CSTRINGOID 2275
DATA(insert OID = 2276 ( any PGNSP PGUID 4 t p t \054 0 0 any_in any_out - - - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 2276 ( any PGNSP PGUID 4 t p t \054 0 0 0 any_in any_out - - - - - i p f 0 -1 0 _null_ _null_ ));
#define ANYOID 2276 #define ANYOID 2276
DATA(insert OID = 2277 ( anyarray PGNSP PGUID -1 f p t \054 0 0 anyarray_in anyarray_out anyarray_recv anyarray_send - - - d x f 0 -1 0 _null_ _null_ )); DATA(insert OID = 2277 ( anyarray PGNSP PGUID -1 f p t \054 0 0 0 anyarray_in anyarray_out anyarray_recv anyarray_send - - - d x f 0 -1 0 _null_ _null_ ));
#define ANYARRAYOID 2277 #define ANYARRAYOID 2277
DATA(insert OID = 2278 ( void PGNSP PGUID 4 t p t \054 0 0 void_in void_out - - - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 2278 ( void PGNSP PGUID 4 t p t \054 0 0 0 void_in void_out - - - - - i p f 0 -1 0 _null_ _null_ ));
#define VOIDOID 2278 #define VOIDOID 2278
DATA(insert OID = 2279 ( trigger PGNSP PGUID 4 t p t \054 0 0 trigger_in trigger_out - - - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 2279 ( trigger PGNSP PGUID 4 t p t \054 0 0 0 trigger_in trigger_out - - - - - i p f 0 -1 0 _null_ _null_ ));
#define TRIGGEROID 2279 #define TRIGGEROID 2279
DATA(insert OID = 2280 ( language_handler PGNSP PGUID 4 t p t \054 0 0 language_handler_in language_handler_out - - - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 2280 ( language_handler PGNSP PGUID 4 t p t \054 0 0 0 language_handler_in language_handler_out - - - - - i p f 0 -1 0 _null_ _null_ ));
#define LANGUAGE_HANDLEROID 2280 #define LANGUAGE_HANDLEROID 2280
DATA(insert OID = 2281 ( internal PGNSP PGUID 4 t p t \054 0 0 internal_in internal_out - - - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 2281 ( internal PGNSP PGUID 4 t p t \054 0 0 0 internal_in internal_out - - - - - i p f 0 -1 0 _null_ _null_ ));
#define INTERNALOID 2281 #define INTERNALOID 2281
DATA(insert OID = 2282 ( opaque PGNSP PGUID 4 t p t \054 0 0 opaque_in opaque_out - - - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 2282 ( opaque PGNSP PGUID 4 t p t \054 0 0 0 opaque_in opaque_out - - - - - i p f 0 -1 0 _null_ _null_ ));
#define OPAQUEOID 2282 #define OPAQUEOID 2282
DATA(insert OID = 2283 ( anyelement PGNSP PGUID 4 t p t \054 0 0 anyelement_in anyelement_out - - - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 2283 ( anyelement PGNSP PGUID 4 t p t \054 0 0 0 anyelement_in anyelement_out - - - - - i p f 0 -1 0 _null_ _null_ ));
#define ANYELEMENTOID 2283 #define ANYELEMENTOID 2283
DATA(insert OID = 3500 ( anyenum PGNSP PGUID 4 t p t \054 0 0 anyenum_in anyenum_out - - - - - i p f 0 -1 0 _null_ _null_ )); DATA(insert OID = 3500 ( anyenum PGNSP PGUID 4 t p t \054 0 0 0 anyenum_in anyenum_out - - - - - i p f 0 -1 0 _null_ _null_ ));
#define ANYENUMOID 3500 #define ANYENUMOID 3500
@ -592,7 +599,8 @@ DATA(insert OID = 3500 ( anyenum PGNSP PGUID 4 t p t \054 0 0 anyenum_in anyen
*/ */
extern Oid TypeShellMake(const char *typeName, Oid typeNamespace); extern Oid TypeShellMake(const char *typeName, Oid typeNamespace);
extern Oid TypeCreate(const char *typeName, extern Oid TypeCreate(Oid newTypeOid,
const char *typeName,
Oid typeNamespace, Oid typeNamespace,
Oid relationOid, Oid relationOid,
char relationKind, char relationKind,
@ -607,6 +615,8 @@ extern Oid TypeCreate(const char *typeName,
Oid typmodoutProcedure, Oid typmodoutProcedure,
Oid analyzeProcedure, Oid analyzeProcedure,
Oid elementType, Oid elementType,
bool isImplicitArray,
Oid arrayType,
Oid baseType, Oid baseType,
const char *defaultTypeValue, const char *defaultTypeValue,
char *defaultTypeBin, char *defaultTypeBin,
@ -630,6 +640,7 @@ extern void GenerateTypeDependencies(Oid typeNamespace,
Oid typmodoutProcedure, Oid typmodoutProcedure,
Oid analyzeProcedure, Oid analyzeProcedure,
Oid elementType, Oid elementType,
bool isImplicitArray,
Oid baseType, Oid baseType,
Node *defaultExpr, Node *defaultExpr,
bool rebuild); bool rebuild);
@ -637,6 +648,6 @@ extern void GenerateTypeDependencies(Oid typeNamespace,
extern void TypeRename(const char *oldTypeName, Oid typeNamespace, extern void TypeRename(const char *oldTypeName, Oid typeNamespace,
const char *newTypeName); const char *newTypeName);
extern char *makeArrayTypeName(const char *typeName); extern char *makeArrayTypeName(const char *typeName, Oid typeNamespace);
#endif /* PG_TYPE_H */ #endif /* PG_TYPE_H */

View File

@ -7,7 +7,7 @@
* Portions Copyright (c) 1996-2007, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2007, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* $PostgreSQL: pgsql/src/include/commands/typecmds.h,v 1.18 2007/04/02 03:49:41 tgl Exp $ * $PostgreSQL: pgsql/src/include/commands/typecmds.h,v 1.19 2007/05/11 17:57:14 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
@ -36,9 +36,11 @@ extern void AlterDomainDropConstraint(List *names, const char *constrName,
extern List *GetDomainConstraints(Oid typeOid); extern List *GetDomainConstraints(Oid typeOid);
extern void AlterTypeOwner(List *names, Oid newOwnerId); extern void AlterTypeOwner(List *names, Oid newOwnerId);
extern void AlterTypeOwnerInternal(Oid typeOid, Oid newOwnerId); extern void AlterTypeOwnerInternal(Oid typeOid, Oid newOwnerId,
bool hasDependEntry);
extern void AlterTypeNamespace(List *names, const char *newschema); extern void AlterTypeNamespace(List *names, const char *newschema);
extern void AlterTypeNamespaceInternal(Oid typeOid, Oid nspOid, extern void AlterTypeNamespaceInternal(Oid typeOid, Oid nspOid,
bool errorOnTableType); bool isImplicitArray,
bool errorOnTableType);
#endif /* TYPECMDS_H */ #endif /* TYPECMDS_H */

View File

@ -1456,7 +1456,6 @@ select alter2.plus1(41);
-- clean up -- clean up
drop schema alter2 cascade; drop schema alter2 cascade;
NOTICE: drop cascades to composite type alter2.ctype
NOTICE: drop cascades to type alter2.ctype NOTICE: drop cascades to type alter2.ctype
NOTICE: drop cascades to type alter2.posint NOTICE: drop cascades to type alter2.posint
NOTICE: drop cascades to function alter2.plus1(integer) NOTICE: drop cascades to function alter2.plus1(integer)

View File

@ -409,6 +409,14 @@ WHERE indrelid != 0 AND
------+---------- ------+----------
(0 rows) (0 rows)
SELECT ctid, lanowner
FROM pg_catalog.pg_language fk
WHERE lanowner != 0 AND
NOT EXISTS(SELECT 1 FROM pg_catalog.pg_authid pk WHERE pk.oid = fk.lanowner);
ctid | lanowner
------+----------
(0 rows)
SELECT ctid, lanvalidator SELECT ctid, lanvalidator
FROM pg_catalog.pg_language fk FROM pg_catalog.pg_language fk
WHERE lanvalidator != 0 AND WHERE lanvalidator != 0 AND
@ -721,6 +729,14 @@ WHERE typelem != 0 AND
------+--------- ------+---------
(0 rows) (0 rows)
SELECT ctid, typarray
FROM pg_catalog.pg_type fk
WHERE typarray != 0 AND
NOT EXISTS(SELECT 1 FROM pg_catalog.pg_type pk WHERE pk.oid = fk.typarray);
ctid | typarray
------+----------
(0 rows)
SELECT ctid, typinput SELECT ctid, typinput
FROM pg_catalog.pg_type fk FROM pg_catalog.pg_type fk
WHERE typinput != 0 AND WHERE typinput != 0 AND

View File

@ -69,6 +69,16 @@ WHERE p1.typtype in ('b','e') AND p1.typname NOT LIKE E'\\_%' AND NOT EXISTS
705 | unknown 705 | unknown
(2 rows) (2 rows)
-- Make sure typarray points to a varlena array type of our own base
SELECT p1.oid, p1.typname as basetype, p2.typname as arraytype,
p2.typelem, p2.typlen
FROM pg_type p1 LEFT JOIN pg_type p2 ON (p1.typarray = p2.oid)
WHERE p1.typarray <> 0 AND
(p2.oid IS NULL OR p2.typelem <> p1.oid OR p2.typlen <> -1);
oid | basetype | arraytype | typelem | typlen
-----+----------+-----------+---------+--------
(0 rows)
-- Text conversion routines must be provided. -- Text conversion routines must be provided.
SELECT p1.oid, p1.typname SELECT p1.oid, p1.typname
FROM pg_type as p1 FROM pg_type as p1

View File

@ -205,6 +205,10 @@ SELECT ctid, indrelid
FROM pg_catalog.pg_index fk FROM pg_catalog.pg_index fk
WHERE indrelid != 0 AND WHERE indrelid != 0 AND
NOT EXISTS(SELECT 1 FROM pg_catalog.pg_class pk WHERE pk.oid = fk.indrelid); NOT EXISTS(SELECT 1 FROM pg_catalog.pg_class pk WHERE pk.oid = fk.indrelid);
SELECT ctid, lanowner
FROM pg_catalog.pg_language fk
WHERE lanowner != 0 AND
NOT EXISTS(SELECT 1 FROM pg_catalog.pg_authid pk WHERE pk.oid = fk.lanowner);
SELECT ctid, lanvalidator SELECT ctid, lanvalidator
FROM pg_catalog.pg_language fk FROM pg_catalog.pg_language fk
WHERE lanvalidator != 0 AND WHERE lanvalidator != 0 AND
@ -361,6 +365,10 @@ SELECT ctid, typelem
FROM pg_catalog.pg_type fk FROM pg_catalog.pg_type fk
WHERE typelem != 0 AND WHERE typelem != 0 AND
NOT EXISTS(SELECT 1 FROM pg_catalog.pg_type pk WHERE pk.oid = fk.typelem); NOT EXISTS(SELECT 1 FROM pg_catalog.pg_type pk WHERE pk.oid = fk.typelem);
SELECT ctid, typarray
FROM pg_catalog.pg_type fk
WHERE typarray != 0 AND
NOT EXISTS(SELECT 1 FROM pg_catalog.pg_type pk WHERE pk.oid = fk.typarray);
SELECT ctid, typinput SELECT ctid, typinput
FROM pg_catalog.pg_type fk FROM pg_catalog.pg_type fk
WHERE typinput != 0 AND WHERE typinput != 0 AND

View File

@ -59,6 +59,13 @@ WHERE p1.typtype in ('b','e') AND p1.typname NOT LIKE E'\\_%' AND NOT EXISTS
WHERE p2.typname = ('_' || p1.typname)::name AND WHERE p2.typname = ('_' || p1.typname)::name AND
p2.typelem = p1.oid); p2.typelem = p1.oid);
-- Make sure typarray points to a varlena array type of our own base
SELECT p1.oid, p1.typname as basetype, p2.typname as arraytype,
p2.typelem, p2.typlen
FROM pg_type p1 LEFT JOIN pg_type p2 ON (p1.typarray = p2.oid)
WHERE p1.typarray <> 0 AND
(p2.oid IS NULL OR p2.typelem <> p1.oid OR p2.typlen <> -1);
-- Text conversion routines must be provided. -- Text conversion routines must be provided.
SELECT p1.oid, p1.typname SELECT p1.oid, p1.typname

View File

@ -1,3 +1,4 @@
$PostgreSQL: pgsql/src/tools/findoidjoins/README,v 1.4 2007/05/11 17:57:14 tgl Exp $
findoidjoins findoidjoins
@ -87,6 +88,7 @@ Join pg_catalog.pg_depend.refclassid => pg_catalog.pg_class.oid
Join pg_catalog.pg_description.classoid => pg_catalog.pg_class.oid Join pg_catalog.pg_description.classoid => pg_catalog.pg_class.oid
Join pg_catalog.pg_index.indexrelid => pg_catalog.pg_class.oid Join pg_catalog.pg_index.indexrelid => pg_catalog.pg_class.oid
Join pg_catalog.pg_index.indrelid => pg_catalog.pg_class.oid Join pg_catalog.pg_index.indrelid => pg_catalog.pg_class.oid
Join pg_catalog.pg_language.lanowner => pg_catalog.pg_authid.oid
Join pg_catalog.pg_language.lanvalidator => pg_catalog.pg_proc.oid Join pg_catalog.pg_language.lanvalidator => pg_catalog.pg_proc.oid
Join pg_catalog.pg_namespace.nspowner => pg_catalog.pg_authid.oid Join pg_catalog.pg_namespace.nspowner => pg_catalog.pg_authid.oid
Join pg_catalog.pg_opclass.opcmethod => pg_catalog.pg_am.oid Join pg_catalog.pg_opclass.opcmethod => pg_catalog.pg_am.oid
@ -126,6 +128,7 @@ Join pg_catalog.pg_type.typnamespace => pg_catalog.pg_namespace.oid
Join pg_catalog.pg_type.typowner => pg_catalog.pg_authid.oid Join pg_catalog.pg_type.typowner => pg_catalog.pg_authid.oid
Join pg_catalog.pg_type.typrelid => pg_catalog.pg_class.oid Join pg_catalog.pg_type.typrelid => pg_catalog.pg_class.oid
Join pg_catalog.pg_type.typelem => pg_catalog.pg_type.oid Join pg_catalog.pg_type.typelem => pg_catalog.pg_type.oid
Join pg_catalog.pg_type.typarray => pg_catalog.pg_type.oid
Join pg_catalog.pg_type.typinput => pg_catalog.pg_proc.oid Join pg_catalog.pg_type.typinput => pg_catalog.pg_proc.oid
Join pg_catalog.pg_type.typoutput => pg_catalog.pg_proc.oid Join pg_catalog.pg_type.typoutput => pg_catalog.pg_proc.oid
Join pg_catalog.pg_type.typreceive => pg_catalog.pg_proc.oid Join pg_catalog.pg_type.typreceive => pg_catalog.pg_proc.oid