@@ -59,7 +59,7 @@ static void BootstrapModeMain(void);
5959static void bootstrap_signals (void );
6060static void ShutdownAuxiliaryProcess (int code , Datum arg );
6161static Form_pg_attribute AllocateAttribute (void );
62- static void populate_typ_array (void );
62+ static void populate_typ_list (void );
6363static Oid gettype (char * type );
6464static void cleanup (void );
6565
@@ -160,7 +160,7 @@ struct typmap
160160 FormData_pg_type am_typ ;
161161};
162162
163- static struct typmap * * Typ = NULL ;
163+ static List * Typ = NIL ; /* List of struct typmap* */
164164static struct typmap * Ap = NULL ;
165165
166166static Datum values [MAXATTR ]; /* current row's attribute values */
@@ -598,10 +598,10 @@ boot_openrel(char *relname)
598598
599599 /*
600600 * pg_type must be filled before any OPEN command is executed, hence we
601- * can now populate the Typ array if we haven't yet.
601+ * can now populate Typ if we haven't yet.
602602 */
603- if (Typ == NULL )
604- populate_typ_array ();
603+ if (Typ == NIL )
604+ populate_typ_list ();
605605
606606 if (boot_reldesc != NULL )
607607 closerel (NULL );
@@ -691,7 +691,7 @@ DefineAttr(char *name, char *type, int attnum, int nullness)
691691
692692 typeoid = gettype (type );
693693
694- if (Typ != NULL )
694+ if (Typ != NIL )
695695 {
696696 attrtypes [attnum ]-> atttypid = Ap -> am_oid ;
697697 attrtypes [attnum ]-> attlen = Ap -> am_typ .typlen ;
@@ -873,47 +873,36 @@ cleanup(void)
873873}
874874
875875/* ----------------
876- * populate_typ_array
876+ * populate_typ_list
877877 *
878- * Load the Typ array by reading pg_type.
878+ * Load the Typ list by reading pg_type.
879879 * ----------------
880880 */
881881static void
882- populate_typ_array (void )
882+ populate_typ_list (void )
883883{
884884 Relation rel ;
885885 TableScanDesc scan ;
886886 HeapTuple tup ;
887- int nalloc ;
888- int i ;
889-
890- Assert (Typ == NULL );
887+ MemoryContext old ;
891888
892- nalloc = 512 ;
893- Typ = (struct typmap * * )
894- MemoryContextAlloc (TopMemoryContext , nalloc * sizeof (struct typmap * ));
889+ Assert (Typ == NIL );
895890
896891 rel = table_open (TypeRelationId , NoLock );
897892 scan = table_beginscan_catalog (rel , 0 , NULL );
898- i = 0 ;
893+ old = MemoryContextSwitchTo ( TopMemoryContext ) ;
899894 while ((tup = heap_getnext (scan , ForwardScanDirection )) != NULL )
900895 {
901896 Form_pg_type typForm = (Form_pg_type ) GETSTRUCT (tup );
897+ struct typmap * newtyp ;
902898
903- /* make sure there will be room for a trailing NULL pointer */
904- if (i >= nalloc - 1 )
905- {
906- nalloc *= 2 ;
907- Typ = (struct typmap * * )
908- repalloc (Typ , nalloc * sizeof (struct typmap * ));
909- }
910- Typ [i ] = (struct typmap * )
911- MemoryContextAlloc (TopMemoryContext , sizeof (struct typmap ));
912- Typ [i ]-> am_oid = typForm -> oid ;
913- memcpy (& (Typ [i ]-> am_typ ), typForm , sizeof (Typ [i ]-> am_typ ));
914- i ++ ;
899+ newtyp = (struct typmap * ) palloc (sizeof (struct typmap ));
900+ Typ = lappend (Typ , newtyp );
901+
902+ newtyp -> am_oid = typForm -> oid ;
903+ memcpy (& newtyp -> am_typ , typForm , sizeof (newtyp -> am_typ ));
915904 }
916- Typ [ i ] = NULL ; /* Fill trailing NULL pointer */
905+ MemoryContextSwitchTo ( old );
917906 table_endscan (scan );
918907 table_close (rel , NoLock );
919908}
@@ -923,25 +912,26 @@ populate_typ_array(void)
923912 *
924913 * NB: this is really ugly; it will return an integer index into TypInfo[],
925914 * and not an OID at all, until the first reference to a type not known in
926- * TypInfo[]. At that point it will read and cache pg_type in the Typ array ,
915+ * TypInfo[]. At that point it will read and cache pg_type in Typ,
927916 * and subsequently return a real OID (and set the global pointer Ap to
928917 * point at the found row in Typ). So caller must check whether Typ is
929- * still NULL to determine what the return value is!
918+ * still NIL to determine what the return value is!
930919 * ----------------
931920 */
932921static Oid
933922gettype (char * type )
934923{
935- if (Typ != NULL )
924+ if (Typ != NIL )
936925 {
937- struct typmap * * app ;
926+ ListCell * lc ;
938927
939- for ( app = Typ ; * app != NULL ; app ++ )
928+ foreach ( lc , Typ )
940929 {
941- if (strncmp (NameStr ((* app )-> am_typ .typname ), type , NAMEDATALEN ) == 0 )
930+ struct typmap * app = lfirst (lc );
931+ if (strncmp (NameStr (app -> am_typ .typname ), type , NAMEDATALEN ) == 0 )
942932 {
943- Ap = * app ;
944- return ( * app ) -> am_oid ;
933+ Ap = app ;
934+ return app -> am_oid ;
945935 }
946936 }
947937 }
@@ -956,7 +946,7 @@ gettype(char *type)
956946 }
957947 /* Not in TypInfo, so we'd better be able to read pg_type now */
958948 elog (DEBUG4 , "external type: %s" , type );
959- populate_typ_array ();
949+ populate_typ_list ();
960950 return gettype (type );
961951 }
962952 elog (ERROR , "unrecognized type \"%s\"" , type );
@@ -984,17 +974,20 @@ boot_get_type_io_data(Oid typid,
984974 Oid * typinput ,
985975 Oid * typoutput )
986976{
987- if (Typ != NULL )
977+ if (Typ != NIL )
988978 {
989979 /* We have the boot-time contents of pg_type, so use it */
990- struct typmap * * app ;
991- struct typmap * ap ;
992-
993- app = Typ ;
994- while (* app && (* app )-> am_oid != typid )
995- ++ app ;
996- ap = * app ;
997- if (ap == NULL )
980+ struct typmap * ap = NULL ;
981+ ListCell * lc ;
982+
983+ foreach (lc , Typ )
984+ {
985+ ap = lfirst (lc );
986+ if (ap -> am_oid == typid )
987+ break ;
988+ }
989+
990+ if (!ap || ap -> am_oid != typid )
998991 elog (ERROR , "type OID %u not found in Typ list" , typid );
999992
1000993 * typlen = ap -> am_typ .typlen ;
0 commit comments