77 *
88 *
99 * IDENTIFICATION
10- * $Header: /cvsroot/pgsql/src/backend/access/common/tupdesc.c,v 1.18 1997/08/21 14:33:05 momjian Exp $
10+ * $Header: /cvsroot/pgsql/src/backend/access/common/tupdesc.c,v 1.19 1997/08/22 02:55:39 vadim Exp $
1111 *
1212 * NOTES
1313 * some of the executor utility code such as "ExecTypeFromTL" should be
@@ -99,6 +99,7 @@ CreateTupleDesc(int natts, AttributeTupleForm* attrs)
9999 *This function creates a new TupleDesc by copying from an existing
100100 * TupleDesc
101101 *
102+ * !!! Constraints are not copied !!!
102103 * ----------------------------------------------------------------
103104 */
104105TupleDesc
@@ -117,15 +118,127 @@ CreateTupleDescCopy(TupleDesc tupdesc)
117118memmove (desc -> attrs [i ],
118119tupdesc -> attrs [i ],
119120ATTRIBUTE_TUPLE_SIZE );
121+ desc -> attrs [i ]-> attnotnull = false;
122+ desc -> attrs [i ]-> atthasdef = false;
120123 }
121- if (tupdesc -> constr ) {
122- desc -> constr = (TupleConstr * )palloc (sizeof (TupleConstr ));
123- memmove (desc -> constr ,tupdesc -> constr ,sizeof (TupleConstr ));
124- }else
125- desc -> constr = NULL ;
124+ desc -> constr = NULL ;
125+
126126return desc ;
127127}
128128
129+ /* ----------------------------------------------------------------
130+ *CreateTupleDescCopyConstr
131+ *
132+ *This function creates a new TupleDesc by copying from an existing
133+ * TupleDesc (with Constraints)
134+ *
135+ * ----------------------------------------------------------------
136+ */
137+ TupleDesc
138+ CreateTupleDescCopyConstr (TupleDesc tupdesc )
139+ {
140+ TupleDesc desc ;
141+ TupleConstr * constr = tupdesc -> constr ;
142+ int i ,size ;
143+
144+ desc = (TupleDesc )palloc (sizeof (struct tupleDesc ));
145+ desc -> natts = tupdesc -> natts ;
146+ size = desc -> natts * sizeof (AttributeTupleForm );
147+ desc -> attrs = (AttributeTupleForm * )palloc (size );
148+ for (i = 0 ;i < desc -> natts ;i ++ ) {
149+ desc -> attrs [i ]=
150+ (AttributeTupleForm )palloc (ATTRIBUTE_TUPLE_SIZE );
151+ memmove (desc -> attrs [i ],
152+ tupdesc -> attrs [i ],
153+ ATTRIBUTE_TUPLE_SIZE );
154+ }
155+ if (constr )
156+ {
157+ TupleConstr * cpy = (TupleConstr * )palloc (sizeof (TupleConstr ));
158+
159+ cpy -> has_not_null = constr -> has_not_null ;
160+
161+ if ( (cpy -> num_defval = constr -> num_defval )> 0 )
162+ {
163+ cpy -> defval = (AttrDefault * )palloc (cpy -> num_defval * sizeof (AttrDefault ));
164+ memcpy (cpy -> defval ,constr -> defval ,cpy -> num_defval * sizeof (AttrDefault ));
165+ for (i = cpy -> num_defval - 1 ;i >=0 ;i -- )
166+ {
167+ if (constr -> defval [i ].adbin )
168+ cpy -> defval [i ].adbin = pstrdup (constr -> defval [i ].adbin );
169+ if (constr -> defval [i ].adsrc )
170+ cpy -> defval [i ].adsrc = pstrdup (constr -> defval [i ].adsrc );
171+ }
172+ }
173+
174+ if ( (cpy -> num_check = constr -> num_check )> 0 )
175+ {
176+ cpy -> check = (ConstrCheck * )palloc (cpy -> num_check * sizeof (ConstrCheck ));
177+ memcpy (cpy -> check ,constr -> check ,cpy -> num_check * sizeof (ConstrCheck ));
178+ for (i = cpy -> num_check - 1 ;i >=0 ;i -- )
179+ {
180+ if (constr -> check [i ].ccname )
181+ cpy -> check [i ].ccname = pstrdup (constr -> check [i ].ccname );
182+ if (constr -> check [i ].ccbin )
183+ cpy -> check [i ].ccbin = pstrdup (constr -> check [i ].ccbin );
184+ if (constr -> check [i ].ccsrc )
185+ cpy -> check [i ].ccsrc = pstrdup (constr -> check [i ].ccsrc );
186+ }
187+ }
188+
189+ desc -> constr = cpy ;
190+ }
191+ else
192+ desc -> constr = NULL ;
193+
194+ return desc ;
195+ }
196+
197+ void
198+ FreeTupleDesc (TupleDesc tupdesc )
199+ {
200+ int i ;
201+
202+ for (i = 0 ;i < tupdesc -> natts ;i ++ )
203+ pfree (tupdesc -> attrs [i ]);
204+ pfree (tupdesc -> attrs );
205+ if (tupdesc -> constr )
206+ {
207+ if (tupdesc -> constr -> num_defval > 0 )
208+ {
209+ AttrDefault * attrdef = tupdesc -> constr -> defval ;
210+
211+ for (i = tupdesc -> constr -> num_defval - 1 ;i >=0 ;i -- )
212+ {
213+ if (attrdef [i ].adbin )
214+ pfree (attrdef [i ].adbin );
215+ if (attrdef [i ].adsrc )
216+ pfree (attrdef [i ].adsrc );
217+ }
218+ pfree (attrdef );
219+ }
220+ if (tupdesc -> constr -> num_check > 0 )
221+ {
222+ ConstrCheck * check = tupdesc -> constr -> check ;
223+
224+ for (i = tupdesc -> constr -> num_check - 1 ;i >=0 ;i -- )
225+ {
226+ if (check [i ].ccname )
227+ pfree (check [i ].ccname );
228+ if (check [i ].ccbin )
229+ pfree (check [i ].ccbin );
230+ if (check [i ].ccsrc )
231+ pfree (check [i ].ccsrc );
232+ }
233+ pfree (check );
234+ }
235+ pfree (tupdesc -> constr );
236+ }
237+
238+ pfree (tupdesc );
239+
240+ }
241+
129242/* ----------------------------------------------------------------
130243 *TupleDescInitEntry
131244 *
@@ -179,7 +292,7 @@ TupleDescInitEntry(TupleDesc desc,
179292memset (att -> attname .data ,0 ,NAMEDATALEN );
180293
181294
182- att -> attdisbursion = 0 ;/* dummy value */
295+ att -> attdisbursion = 0 ;/* dummy value */
183296att -> attcacheoff = -1 ;
184297
185298att -> attnum = attributeNumber ;
@@ -318,9 +431,12 @@ BuildDescForRelation(List *schema, char *relname)
318431AttrNumber attnum ;
319432List * p ;
320433TupleDesc desc ;
321- char * attname ;
322- char * typename ;
434+ AttrDefault * attrdef = NULL ;
435+ TupleConstr * constr = (TupleConstr * )palloc (sizeof (TupleConstr ));
436+ char * attname ;
437+ char * typename ;
323438int attdim ;
439+ int ndef = 0 ;
324440bool attisset ;
325441
326442/* ----------------
@@ -329,6 +445,7 @@ BuildDescForRelation(List *schema, char *relname)
329445 */
330446natts = length (schema );
331447desc = CreateTemplateTupleDesc (natts );
448+ constr -> has_not_null = false;
332449
333450attnum = 0 ;
334451
@@ -385,14 +502,44 @@ BuildDescForRelation(List *schema, char *relname)
385502}
386503
387504/* This is for constraints */
388- if (entry -> is_not_null ) {
389- if (!desc -> constr )
390- desc -> constr = (TupleConstr * )palloc (sizeof (TupleConstr ));
391- desc -> constr -> has_not_null = true;
392- }
505+ if (entry -> is_not_null )
506+ constr -> has_not_null = true;
393507desc -> attrs [attnum - 1 ]-> attnotnull = entry -> is_not_null ;
508+
509+ if (entry -> defval != NULL )
510+ {
511+ if (attrdef == NULL )
512+ attrdef = (AttrDefault * )palloc (natts * sizeof (AttrDefault ));
513+ attrdef [ndef ].adnum = attnum ;
514+ attrdef [ndef ].adbin = NULL ;
515+ attrdef [ndef ].adsrc = entry -> defval ;
516+ ndef ++ ;
517+ desc -> attrs [attnum - 1 ]-> atthasdef = true;
518+ }
394519
395520 }
521+ if (constr -> has_not_null || ndef > 0 )
522+ {
523+ desc -> constr = constr ;
524+
525+ if (ndef > 0 )/* DEFAULTs */
526+ {
527+ if (ndef < natts )
528+ constr -> defval = (AttrDefault * )
529+ repalloc (attrdef ,ndef * sizeof (AttrDefault ));
530+ else
531+ constr -> defval = attrdef ;
532+ constr -> num_defval = ndef ;
533+ }
534+ else
535+ constr -> num_defval = 0 ;
536+ constr -> num_check = 0 ;
537+ }
538+ else
539+ {
540+ pfree (constr );
541+ desc -> constr = NULL ;
542+ }
396543return desc ;
397544}
398545