]> granicus.if.org Git - postgresql/blob - src/backend/nodes/equalfuncs.c
First phase of SCHEMA changes, concentrating on fixing the grammar and
[postgresql] / src / backend / nodes / equalfuncs.c
1 /*-------------------------------------------------------------------------
2  *
3  * equalfuncs.c
4  *        Equality functions to compare node trees.
5  *
6  * NOTE: a general convention when copying or comparing plan nodes is
7  * that we ignore the executor state subnode.  We do not need to look
8  * at it because no current uses of copyObject() or equal() need to
9  * deal with already-executing plan trees.      By leaving the state subnodes
10  * out, we avoid needing to write copy/compare routines for all the
11  * different executor state node types.
12  *
13  * Currently, in fact, equal() doesn't know how to compare Plan nodes
14  * at all, let alone their executor-state subnodes.  This will probably
15  * need to be fixed someday, but presently there is no need to compare
16  * plan trees.
17  *
18  *
19  * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
20  * Portions Copyright (c) 1994, Regents of the University of California
21  *
22  * IDENTIFICATION
23  *        $Header: /cvsroot/pgsql/src/backend/nodes/equalfuncs.c,v 1.120 2002/03/21 16:00:39 tgl Exp $
24  *
25  *-------------------------------------------------------------------------
26  */
27
28 #include "postgres.h"
29
30 #include "nodes/plannodes.h"
31 #include "nodes/relation.h"
32 #include "utils/datum.h"
33
34
35 /* Macro for comparing string fields that might be NULL */
36 #define equalstr(a, b)  \
37         (((a) != NULL && (b) != NULL) ? (strcmp(a, b) == 0) : (a) == (b))
38
39
40 /*
41  *      Stuff from primnodes.h
42  */
43
44 static bool
45 _equalResdom(Resdom *a, Resdom *b)
46 {
47         if (a->resno != b->resno)
48                 return false;
49         if (a->restype != b->restype)
50                 return false;
51         if (a->restypmod != b->restypmod)
52                 return false;
53         if (!equalstr(a->resname, b->resname))
54                 return false;
55         if (a->ressortgroupref != b->ressortgroupref)
56                 return false;
57         if (a->reskey != b->reskey)
58                 return false;
59         if (a->reskeyop != b->reskeyop)
60                 return false;
61         /* we ignore resjunk flag ... is this correct? */
62
63         return true;
64 }
65
66 static bool
67 _equalFjoin(Fjoin *a, Fjoin *b)
68 {
69         int                     nNodes;
70
71         if (a->fj_initialized != b->fj_initialized)
72                 return false;
73         if (a->fj_nNodes != b->fj_nNodes)
74                 return false;
75         if (!equal(a->fj_innerNode, b->fj_innerNode))
76                 return false;
77
78         nNodes = a->fj_nNodes;
79         if (memcmp(a->fj_results, b->fj_results, nNodes * sizeof(Datum)) != 0)
80                 return false;
81         if (memcmp(a->fj_alwaysDone, b->fj_alwaysDone, nNodes * sizeof(bool)) != 0)
82                 return false;
83
84         return true;
85 }
86
87 static bool
88 _equalExpr(Expr *a, Expr *b)
89 {
90         /*
91          * We do not examine typeOid, since the optimizer often doesn't bother
92          * to set it in created nodes, and it is logically a derivative of the
93          * oper field anyway.
94          */
95         if (a->opType != b->opType)
96                 return false;
97         if (!equal(a->oper, b->oper))
98                 return false;
99         if (!equal(a->args, b->args))
100                 return false;
101
102         return true;
103 }
104
105 static bool
106 _equalVar(Var *a, Var *b)
107 {
108         if (a->varno != b->varno)
109                 return false;
110         if (a->varattno != b->varattno)
111                 return false;
112         if (a->vartype != b->vartype)
113                 return false;
114         if (a->vartypmod != b->vartypmod)
115                 return false;
116         if (a->varlevelsup != b->varlevelsup)
117                 return false;
118         if (a->varnoold != b->varnoold)
119                 return false;
120         if (a->varoattno != b->varoattno)
121                 return false;
122
123         return true;
124 }
125
126 static bool
127 _equalOper(Oper *a, Oper *b)
128 {
129         if (a->opno != b->opno)
130                 return false;
131         if (a->opresulttype != b->opresulttype)
132                 return false;
133
134         /*
135          * We do not examine opid or op_fcache, since these are logically
136          * derived from opno, and they may not be set yet depending on how far
137          * along the node is in the parse/plan pipeline.
138          *
139          * (Besides, op_fcache is executor state, which we don't check --- see
140          * notes at head of file.)
141          *
142          * It's probably not really necessary to check opresulttype either...
143          */
144
145         return true;
146 }
147
148 static bool
149 _equalConst(Const *a, Const *b)
150 {
151         if (a->consttype != b->consttype)
152                 return false;
153         if (a->constlen != b->constlen)
154                 return false;
155         if (a->constisnull != b->constisnull)
156                 return false;
157         if (a->constbyval != b->constbyval)
158                 return false;
159         /* XXX What about constisset and constiscast? */
160
161         /*
162          * We treat all NULL constants of the same type as equal. Someday this
163          * might need to change?  But datumIsEqual doesn't work on nulls,
164          * so...
165          */
166         if (a->constisnull)
167                 return true;
168         return datumIsEqual(a->constvalue, b->constvalue,
169                                                 a->constbyval, a->constlen);
170 }
171
172 static bool
173 _equalParam(Param *a, Param *b)
174 {
175         if (a->paramkind != b->paramkind)
176                 return false;
177         if (a->paramtype != b->paramtype)
178                 return false;
179
180         switch (a->paramkind)
181         {
182                 case PARAM_NAMED:
183                 case PARAM_NEW:
184                 case PARAM_OLD:
185                         if (strcmp(a->paramname, b->paramname) != 0)
186                                 return false;
187                         break;
188                 case PARAM_NUM:
189                 case PARAM_EXEC:
190                         if (a->paramid != b->paramid)
191                                 return false;
192                         break;
193                 case PARAM_INVALID:
194
195                         /*
196                          * XXX: Hmmm... What are we supposed to return in this case ??
197                          */
198                         return true;
199                         break;
200                 default:
201                         elog(ERROR, "_equalParam: Invalid paramkind value: %d",
202                                  a->paramkind);
203         }
204
205         return true;
206 }
207
208 static bool
209 _equalFunc(Func *a, Func *b)
210 {
211         if (a->funcid != b->funcid)
212                 return false;
213         if (a->functype != b->functype)
214                 return false;
215         /* Note we do not look at func_fcache; see notes for _equalOper */
216
217         return true;
218 }
219
220 static bool
221 _equalAggref(Aggref *a, Aggref *b)
222 {
223         if (strcmp(a->aggname, b->aggname) != 0)
224                 return false;
225         if (a->basetype != b->basetype)
226                 return false;
227         if (a->aggtype != b->aggtype)
228                 return false;
229         if (!equal(a->target, b->target))
230                 return false;
231         if (a->aggstar != b->aggstar)
232                 return false;
233         if (a->aggdistinct != b->aggdistinct)
234                 return false;
235         /* ignore aggno, which is only a private field for the executor */
236         return true;
237 }
238
239 static bool
240 _equalSubLink(SubLink *a, SubLink *b)
241 {
242         if (a->subLinkType != b->subLinkType)
243                 return false;
244         if (a->useor != b->useor)
245                 return false;
246         if (!equal(a->lefthand, b->lefthand))
247                 return false;
248         if (!equal(a->oper, b->oper))
249                 return false;
250         if (!equal(a->subselect, b->subselect))
251                 return false;
252         return true;
253 }
254
255 static bool
256 _equalArrayRef(ArrayRef *a, ArrayRef *b)
257 {
258         if (a->refelemtype != b->refelemtype)
259                 return false;
260         if (a->refattrlength != b->refattrlength)
261                 return false;
262         if (a->refelemlength != b->refelemlength)
263                 return false;
264         if (a->refelembyval != b->refelembyval)
265                 return false;
266         if (!equal(a->refupperindexpr, b->refupperindexpr))
267                 return false;
268         if (!equal(a->reflowerindexpr, b->reflowerindexpr))
269                 return false;
270         if (!equal(a->refexpr, b->refexpr))
271                 return false;
272         return equal(a->refassgnexpr, b->refassgnexpr);
273 }
274
275 static bool
276 _equalFieldSelect(FieldSelect *a, FieldSelect *b)
277 {
278         if (!equal(a->arg, b->arg))
279                 return false;
280         if (a->fieldnum != b->fieldnum)
281                 return false;
282         if (a->resulttype != b->resulttype)
283                 return false;
284         if (a->resulttypmod != b->resulttypmod)
285                 return false;
286         return true;
287 }
288
289 static bool
290 _equalRelabelType(RelabelType *a, RelabelType *b)
291 {
292         if (!equal(a->arg, b->arg))
293                 return false;
294         if (a->resulttype != b->resulttype)
295                 return false;
296         if (a->resulttypmod != b->resulttypmod)
297                 return false;
298         return true;
299 }
300
301 static bool
302 _equalRangeTblRef(RangeTblRef *a, RangeTblRef *b)
303 {
304         if (a->rtindex != b->rtindex)
305                 return false;
306
307         return true;
308 }
309
310 static bool
311 _equalFromExpr(FromExpr *a, FromExpr *b)
312 {
313         if (!equal(a->fromlist, b->fromlist))
314                 return false;
315         if (!equal(a->quals, b->quals))
316                 return false;
317
318         return true;
319 }
320
321 static bool
322 _equalJoinExpr(JoinExpr *a, JoinExpr *b)
323 {
324         if (a->jointype != b->jointype)
325                 return false;
326         if (a->isNatural != b->isNatural)
327                 return false;
328         if (!equal(a->larg, b->larg))
329                 return false;
330         if (!equal(a->rarg, b->rarg))
331                 return false;
332         if (!equal(a->using, b->using))
333                 return false;
334         if (!equal(a->quals, b->quals))
335                 return false;
336         if (!equal(a->alias, b->alias))
337                 return false;
338         if (a->rtindex != b->rtindex)
339                 return false;
340
341         return true;
342 }
343
344 /*
345  * Stuff from relation.h
346  */
347
348 static bool
349 _equalRelOptInfo(RelOptInfo *a, RelOptInfo *b)
350 {
351         /*
352          * We treat RelOptInfos as equal if they refer to the same base rels
353          * joined in the same order.  Is this appropriate/sufficient?
354          */
355         return equali(a->relids, b->relids);
356 }
357
358 static bool
359 _equalIndexOptInfo(IndexOptInfo *a, IndexOptInfo *b)
360 {
361         /*
362          * We treat IndexOptInfos as equal if they refer to the same index. Is
363          * this sufficient?
364          */
365         if (a->indexoid != b->indexoid)
366                 return false;
367         return true;
368 }
369
370 static bool
371 _equalPathKeyItem(PathKeyItem *a, PathKeyItem *b)
372 {
373         if (a->sortop != b->sortop)
374                 return false;
375         if (!equal(a->key, b->key))
376                 return false;
377         return true;
378 }
379
380 static bool
381 _equalPath(Path *a, Path *b)
382 {
383         if (a->pathtype != b->pathtype)
384                 return false;
385         if (!equal(a->parent, b->parent))
386                 return false;
387
388         /*
389          * do not check path costs, since they may not be set yet, and being
390          * float values there are roundoff error issues anyway...
391          */
392         if (!equal(a->pathkeys, b->pathkeys))
393                 return false;
394         return true;
395 }
396
397 static bool
398 _equalIndexPath(IndexPath *a, IndexPath *b)
399 {
400         if (!_equalPath((Path *) a, (Path *) b))
401                 return false;
402         if (!equal(a->indexinfo, b->indexinfo))
403                 return false;
404         if (!equal(a->indexqual, b->indexqual))
405                 return false;
406         if (a->indexscandir != b->indexscandir)
407                 return false;
408         if (!equali(a->joinrelids, b->joinrelids))
409                 return false;
410         if (a->alljoinquals != b->alljoinquals)
411                 return false;
412
413         /*
414          * Skip 'rows' because of possibility of floating-point roundoff
415          * error. It should be derivable from the other fields anyway.
416          */
417         return true;
418 }
419
420 static bool
421 _equalTidPath(TidPath *a, TidPath *b)
422 {
423         if (!_equalPath((Path *) a, (Path *) b))
424                 return false;
425         if (!equal(a->tideval, b->tideval))
426                 return false;
427         if (!equali(a->unjoined_relids, b->unjoined_relids))
428                 return false;
429         return true;
430 }
431
432 static bool
433 _equalAppendPath(AppendPath *a, AppendPath *b)
434 {
435         if (!_equalPath((Path *) a, (Path *) b))
436                 return false;
437         if (!equal(a->subpaths, b->subpaths))
438                 return false;
439         return true;
440 }
441
442 static bool
443 _equalJoinPath(JoinPath *a, JoinPath *b)
444 {
445         if (!_equalPath((Path *) a, (Path *) b))
446                 return false;
447         if (a->jointype != b->jointype)
448                 return false;
449         if (!equal(a->outerjoinpath, b->outerjoinpath))
450                 return false;
451         if (!equal(a->innerjoinpath, b->innerjoinpath))
452                 return false;
453         if (!equal(a->joinrestrictinfo, b->joinrestrictinfo))
454                 return false;
455         return true;
456 }
457
458 static bool
459 _equalNestPath(NestPath *a, NestPath *b)
460 {
461         if (!_equalJoinPath((JoinPath *) a, (JoinPath *) b))
462                 return false;
463         return true;
464 }
465
466 static bool
467 _equalMergePath(MergePath *a, MergePath *b)
468 {
469         if (!_equalJoinPath((JoinPath *) a, (JoinPath *) b))
470                 return false;
471         if (!equal(a->path_mergeclauses, b->path_mergeclauses))
472                 return false;
473         if (!equal(a->outersortkeys, b->outersortkeys))
474                 return false;
475         if (!equal(a->innersortkeys, b->innersortkeys))
476                 return false;
477         return true;
478 }
479
480 static bool
481 _equalHashPath(HashPath *a, HashPath *b)
482 {
483         if (!_equalJoinPath((JoinPath *) a, (JoinPath *) b))
484                 return false;
485         if (!equal(a->path_hashclauses, b->path_hashclauses))
486                 return false;
487         return true;
488 }
489
490 static bool
491 _equalSubPlan(SubPlan *a, SubPlan *b)
492 {
493         /* should compare plans, but have to settle for comparing plan IDs */
494         if (a->plan_id != b->plan_id)
495                 return false;
496
497         if (!equal(a->rtable, b->rtable))
498                 return false;
499
500         if (!equal(a->sublink, b->sublink))
501                 return false;
502
503         return true;
504 }
505
506 static bool
507 _equalRestrictInfo(RestrictInfo *a, RestrictInfo *b)
508 {
509         if (!equal(a->clause, b->clause))
510                 return false;
511         if (a->ispusheddown != b->ispusheddown)
512                 return false;
513
514         /*
515          * We ignore eval_cost, this_selec, left/right_pathkey, and
516          * left/right_bucketsize, since they may not be set yet, and should be
517          * derivable from the clause anyway.  Probably it's not really
518          * necessary to compare any of these remaining fields ...
519          */
520         if (!equal(a->subclauseindices, b->subclauseindices))
521                 return false;
522         if (a->mergejoinoperator != b->mergejoinoperator)
523                 return false;
524         if (a->left_sortop != b->left_sortop)
525                 return false;
526         if (a->right_sortop != b->right_sortop)
527                 return false;
528         if (a->hashjoinoperator != b->hashjoinoperator)
529                 return false;
530         return true;
531 }
532
533 static bool
534 _equalJoinInfo(JoinInfo *a, JoinInfo *b)
535 {
536         if (!equali(a->unjoined_relids, b->unjoined_relids))
537                 return false;
538         if (!equal(a->jinfo_restrictinfo, b->jinfo_restrictinfo))
539                 return false;
540         return true;
541 }
542
543 static bool
544 _equalIter(Iter *a, Iter *b)
545 {
546         return equal(a->iterexpr, b->iterexpr);
547 }
548
549 static bool
550 _equalStream(Stream *a, Stream *b)
551 {
552         if (a->clausetype != b->clausetype)
553                 return false;
554         if (a->groupup != b->groupup)
555                 return false;
556         if (a->groupcost != b->groupcost)
557                 return false;
558         if (a->groupsel != b->groupsel)
559                 return false;
560         if (!equal(a->pathptr, b->pathptr))
561                 return false;
562         if (!equal(a->cinfo, b->cinfo))
563                 return false;
564         if (!equal(a->upstream, b->upstream))
565                 return false;
566         return equal(a->downstream, b->downstream);
567 }
568
569 /*
570  * Stuff from parsenodes.h
571  */
572
573 static bool
574 _equalQuery(Query *a, Query *b)
575 {
576         if (a->commandType != b->commandType)
577                 return false;
578         if (!equal(a->utilityStmt, b->utilityStmt))
579                 return false;
580         if (a->resultRelation != b->resultRelation)
581                 return false;
582         if (!equal(a->into, b->into))
583                 return false;
584         if (a->isPortal != b->isPortal)
585                 return false;
586         if (a->isBinary != b->isBinary)
587                 return false;
588         if (a->hasAggs != b->hasAggs)
589                 return false;
590         if (a->hasSubLinks != b->hasSubLinks)
591                 return false;
592         /* we deliberately ignore originalQuery */
593         if (!equal(a->rtable, b->rtable))
594                 return false;
595         if (!equal(a->jointree, b->jointree))
596                 return false;
597         if (!equali(a->rowMarks, b->rowMarks))
598                 return false;
599         if (!equal(a->targetList, b->targetList))
600                 return false;
601         if (!equal(a->groupClause, b->groupClause))
602                 return false;
603         if (!equal(a->havingQual, b->havingQual))
604                 return false;
605         if (!equal(a->distinctClause, b->distinctClause))
606                 return false;
607         if (!equal(a->sortClause, b->sortClause))
608                 return false;
609         if (!equal(a->limitOffset, b->limitOffset))
610                 return false;
611         if (!equal(a->limitCount, b->limitCount))
612                 return false;
613         if (!equal(a->setOperations, b->setOperations))
614                 return false;
615         if (!equali(a->resultRelations, b->resultRelations))
616                 return false;
617
618         /*
619          * We do not check the internal-to-the-planner fields: base_rel_list,
620          * other_rel_list, join_rel_list, equi_key_list, query_pathkeys. They
621          * might not be set yet, and in any case they should be derivable from
622          * the other fields.
623          */
624         return true;
625 }
626
627 static bool
628 _equalInsertStmt(InsertStmt *a, InsertStmt *b)
629 {
630         if (!equal(a->relation, b->relation))
631                 return false;
632         if (!equal(a->cols, b->cols))
633                 return false;
634         if (!equal(a->targetList, b->targetList))
635                 return false;
636         if (!equal(a->selectStmt, b->selectStmt))
637                 return false;
638
639         return true;
640 }
641
642 static bool
643 _equalDeleteStmt(DeleteStmt *a, DeleteStmt *b)
644 {
645         if (!equal(a->relation, b->relation))
646                 return false;
647         if (!equal(a->whereClause, b->whereClause))
648                 return false;
649
650         return true;
651 }
652
653 static bool
654 _equalUpdateStmt(UpdateStmt *a, UpdateStmt *b)
655 {
656         if (!equal(a->relation, b->relation))
657                 return false;
658         if (!equal(a->targetList, b->targetList))
659                 return false;
660         if (!equal(a->whereClause, b->whereClause))
661                 return false;
662         if (!equal(a->fromClause, b->fromClause))
663                 return false;
664
665         return true;
666 }
667
668 static bool
669 _equalSelectStmt(SelectStmt *a, SelectStmt *b)
670 {
671         if (!equal(a->distinctClause, b->distinctClause))
672                 return false;
673         if (!equal(a->into, b->into))
674                 return false;
675         if (!equal(a->intoColNames, b->intoColNames))
676                 return false;
677         if (!equal(a->targetList, b->targetList))
678                 return false;
679         if (!equal(a->fromClause, b->fromClause))
680                 return false;
681         if (!equal(a->whereClause, b->whereClause))
682                 return false;
683         if (!equal(a->groupClause, b->groupClause))
684                 return false;
685         if (!equal(a->havingClause, b->havingClause))
686                 return false;
687         if (!equal(a->sortClause, b->sortClause))
688                 return false;
689         if (!equalstr(a->portalname, b->portalname))
690                 return false;
691         if (a->binary != b->binary)
692                 return false;
693         if (!equal(a->limitOffset, b->limitOffset))
694                 return false;
695         if (!equal(a->limitCount, b->limitCount))
696                 return false;
697         if (!equal(a->forUpdate, b->forUpdate))
698                 return false;
699         if (a->op != b->op)
700                 return false;
701         if (a->all != b->all)
702                 return false;
703         if (!equal(a->larg, b->larg))
704                 return false;
705         if (!equal(a->rarg, b->rarg))
706                 return false;
707
708         return true;
709 }
710
711 static bool
712 _equalSetOperationStmt(SetOperationStmt *a, SetOperationStmt *b)
713 {
714         if (a->op != b->op)
715                 return false;
716         if (a->all != b->all)
717                 return false;
718         if (!equal(a->larg, b->larg))
719                 return false;
720         if (!equal(a->rarg, b->rarg))
721                 return false;
722         if (!equali(a->colTypes, b->colTypes))
723                 return false;
724
725         return true;
726 }
727
728 static bool
729 _equalAlterTableStmt(AlterTableStmt *a, AlterTableStmt *b)
730 {
731         if (a->subtype != b->subtype)
732                 return false;
733         if (!equal(a->relation, b->relation))
734                 return false;
735         if (!equalstr(a->name, b->name))
736                 return false;
737         if (!equal(a->def, b->def))
738                 return false;
739         if (a->behavior != b->behavior)
740                 return false;
741
742         return true;
743 }
744
745 static bool
746 _equalGrantStmt(GrantStmt *a, GrantStmt *b)
747 {
748         if (a->is_grant != b->is_grant)
749                 return false;
750         if (a->objtype != b->objtype)
751                 return false;
752         if (!equal(a->objects, b->objects))
753                 return false;
754         if (!equali(a->privileges, b->privileges))
755                 return false;
756         if (!equal(a->grantees, b->grantees))
757                 return false;
758
759         return true;
760 }
761
762 static bool
763 _equalPrivGrantee(PrivGrantee *a, PrivGrantee *b)
764 {
765         return equalstr(a->username, b->username)
766                 && equalstr(a->groupname, b->groupname);
767 }
768
769 static bool
770 _equalFuncWithArgs(FuncWithArgs *a, FuncWithArgs *b)
771 {
772         return equalstr(a->funcname, b->funcname)
773                 && equal(a->funcargs, b->funcargs);
774 }
775
776 static bool
777 _equalClosePortalStmt(ClosePortalStmt *a, ClosePortalStmt *b)
778 {
779         if (!equalstr(a->portalname, b->portalname))
780                 return false;
781
782         return true;
783 }
784
785 static bool
786 _equalClusterStmt(ClusterStmt *a, ClusterStmt *b)
787 {
788         if (!equal(a->relation, b->relation))
789                 return false;
790         if (!equalstr(a->indexname, b->indexname))
791                 return false;
792
793         return true;
794 }
795
796 static bool
797 _equalCopyStmt(CopyStmt *a, CopyStmt *b)
798 {
799         if (a->binary != b->binary)
800                 return false;
801         if (!equal(a->relation, b->relation))
802                 return false;
803         if (a->oids != b->oids)
804                 return false;
805         if (a->direction != b->direction)
806                 return false;
807         if (!equalstr(a->filename, b->filename))
808                 return false;
809         if (!equalstr(a->delimiter, b->delimiter))
810                 return false;
811         if (!equalstr(a->null_print, b->null_print))
812                 return false;
813
814         return true;
815 }
816
817 static bool
818 _equalCreateStmt(CreateStmt *a, CreateStmt *b)
819 {
820         if (!equal(a->relation, b->relation))
821                 return false;
822         if (!equal(a->tableElts, b->tableElts))
823                 return false;
824         if (!equal(a->inhRelations, b->inhRelations))
825                 return false;
826         if (!equal(a->constraints, b->constraints))
827                 return false;
828         if (a->hasoids != b->hasoids)
829                 return false;
830
831         return true;
832 }
833
834 static bool
835 _equalVersionStmt(VersionStmt *a, VersionStmt *b)
836 {
837         if (!equalstr(a->relname, b->relname))
838                 return false;
839         if (a->direction != b->direction)
840                 return false;
841         if (!equalstr(a->fromRelname, b->fromRelname))
842                 return false;
843         if (!equalstr(a->date, b->date))
844                 return false;
845
846         return true;
847 }
848
849 static bool
850 _equalDefineStmt(DefineStmt *a, DefineStmt *b)
851 {
852         if (a->defType != b->defType)
853                 return false;
854         if (!equalstr(a->defname, b->defname))
855                 return false;
856         if (!equal(a->definition, b->definition))
857                 return false;
858
859         return true;
860 }
861
862 static bool
863 _equalDropStmt(DropStmt *a, DropStmt *b)
864 {
865         if (!equal(a->objects, b->objects))
866                 return false;
867         if (a->removeType != b->removeType)
868                 return false;
869         if (a->behavior != b->behavior)
870                 return false;
871
872         return true;
873 }
874
875 static bool
876 _equalTruncateStmt(TruncateStmt *a, TruncateStmt *b)
877 {
878         if (!equal(a->relation, b->relation))
879                 return false;
880
881         return true;
882 }
883
884 static bool
885 _equalCommentStmt(CommentStmt *a, CommentStmt *b)
886 {
887         if (a->objtype != b->objtype)
888                 return false;
889         if (!equalstr(a->objname, b->objname))
890                 return false;
891         if (!equalstr(a->objschema, b->objschema))
892                 return false;
893         if (!equalstr(a->objproperty, b->objproperty))
894                 return false;
895         if (!equal(a->objlist, b->objlist))
896                 return false;
897         if (!equalstr(a->comment, b->comment))
898                 return false;
899
900         return true;
901 }
902
903 static bool
904 _equalFetchStmt(FetchStmt *a, FetchStmt *b)
905 {
906         if (a->direction != b->direction)
907                 return false;
908         if (a->howMany != b->howMany)
909                 return false;
910         if (!equalstr(a->portalname, b->portalname))
911                 return false;
912         if (a->ismove != b->ismove)
913                 return false;
914
915         return true;
916 }
917
918 static bool
919 _equalIndexStmt(IndexStmt *a, IndexStmt *b)
920 {
921         if (!equalstr(a->idxname, b->idxname))
922                 return false;
923         if (!equal(a->relation, b->relation))
924                 return false;
925         if (!equalstr(a->accessMethod, b->accessMethod))
926                 return false;
927         if (!equal(a->indexParams, b->indexParams))
928                 return false;
929         if (!equal(a->whereClause, b->whereClause))
930                 return false;
931         if (!equal(a->rangetable, b->rangetable))
932                 return false;
933         if (a->unique != b->unique)
934                 return false;
935         if (a->primary != b->primary)
936                 return false;
937
938         return true;
939 }
940
941 static bool
942 _equalProcedureStmt(ProcedureStmt *a, ProcedureStmt *b)
943 {
944         if (a->replace != b->replace)
945                 return false;
946         if (!equalstr(a->funcname, b->funcname))
947                 return false;
948         if (!equal(a->argTypes, b->argTypes))
949                 return false;
950         if (!equal(a->returnType, b->returnType))
951                 return false;
952         if (!equal(a->withClause, b->withClause))
953                 return false;
954         if (!equal(a->as, b->as))
955                 return false;
956         if (!equalstr(a->language, b->language))
957                 return false;
958
959         return true;
960 }
961
962 static bool
963 _equalRemoveAggrStmt(RemoveAggrStmt *a, RemoveAggrStmt *b)
964 {
965         if (!equalstr(a->aggname, b->aggname))
966                 return false;
967         if (!equal(a->aggtype, b->aggtype))
968                 return false;
969
970         return true;
971 }
972
973 static bool
974 _equalRemoveFuncStmt(RemoveFuncStmt *a, RemoveFuncStmt *b)
975 {
976         if (!equalstr(a->funcname, b->funcname))
977                 return false;
978         if (!equal(a->args, b->args))
979                 return false;
980
981         return true;
982 }
983
984 static bool
985 _equalRemoveOperStmt(RemoveOperStmt *a, RemoveOperStmt *b)
986 {
987         if (!equalstr(a->opname, b->opname))
988                 return false;
989         if (!equal(a->args, b->args))
990                 return false;
991
992         return true;
993 }
994
995
996 static bool
997 _equalRenameStmt(RenameStmt *a, RenameStmt *b)
998 {
999         if (!equal(a->relation, b->relation))
1000                 return false;
1001         if (!equalstr(a->column, b->column))
1002                 return false;
1003         if (!equalstr(a->newname, b->newname))
1004                 return false;
1005
1006         return true;
1007 }
1008
1009 static bool
1010 _equalRuleStmt(RuleStmt *a, RuleStmt *b)
1011 {
1012         if (!equal(a->relation, b->relation))
1013                 return false;
1014         if (!equalstr(a->rulename, b->rulename))
1015                 return false;
1016         if (!equal(a->whereClause, b->whereClause))
1017                 return false;
1018         if (a->event != b->event)
1019                 return false;
1020         if (a->instead != b->instead)
1021                 return false;
1022         if (!equal(a->actions, b->actions))
1023                 return false;
1024
1025         return true;
1026 }
1027
1028 static bool
1029 _equalNotifyStmt(NotifyStmt *a, NotifyStmt *b)
1030 {
1031         if (!equal(a->relation, b->relation))
1032                 return false;
1033
1034         return true;
1035 }
1036
1037 static bool
1038 _equalListenStmt(ListenStmt *a, ListenStmt *b)
1039 {
1040         if (!equal(a->relation, b->relation))
1041                 return false;
1042
1043         return true;
1044 }
1045
1046 static bool
1047 _equalUnlistenStmt(UnlistenStmt *a, UnlistenStmt *b)
1048 {
1049         if (!equal(a->relation, b->relation))
1050                 return false;
1051
1052         return true;
1053 }
1054
1055 static bool
1056 _equalTransactionStmt(TransactionStmt *a, TransactionStmt *b)
1057 {
1058         if (a->command != b->command)
1059                 return false;
1060
1061         return true;
1062 }
1063
1064 static bool
1065 _equalViewStmt(ViewStmt *a, ViewStmt *b)
1066 {
1067         if (!equal(a->view, b->view))
1068                 return false;
1069         if (!equal(a->aliases, b->aliases))
1070                 return false;
1071         if (!equal(a->query, b->query))
1072                 return false;
1073
1074         return true;
1075 }
1076
1077 static bool
1078 _equalLoadStmt(LoadStmt *a, LoadStmt *b)
1079 {
1080         if (!equalstr(a->filename, b->filename))
1081                 return false;
1082
1083         return true;
1084 }
1085
1086 static bool
1087 _equalCreateDomainStmt(CreateDomainStmt *a, CreateDomainStmt *b)
1088 {
1089         if (!equalstr(a->domainname, b->domainname))
1090                 return false;
1091         if (!equal(a->typename, b->typename))
1092                 return false;
1093         if (!equal(a->constraints, b->constraints))
1094                 return false;
1095
1096         return true;
1097 }
1098
1099 static bool
1100 _equalCreatedbStmt(CreatedbStmt *a, CreatedbStmt *b)
1101 {
1102         if (!equalstr(a->dbname, b->dbname))
1103                 return false;
1104         if (!equalstr(a->dbowner, b->dbowner))
1105                 return false;
1106         if (!equalstr(a->dbpath, b->dbpath))
1107                 return false;
1108         if (!equalstr(a->dbtemplate, b->dbtemplate))
1109                 return false;
1110         if (a->encoding != b->encoding)
1111                 return false;
1112
1113         return true;
1114 }
1115
1116 static bool
1117 _equalAlterDatabaseSetStmt(AlterDatabaseSetStmt *a, AlterDatabaseSetStmt *b)
1118 {
1119         if (!equalstr(a->dbname, b->dbname))
1120                 return false;
1121         if (!equalstr(a->variable, b->variable))
1122                 return false;
1123         if (!equal(a->value, b->value))
1124                 return false;
1125
1126         return true;
1127 }
1128
1129 static bool
1130 _equalDropdbStmt(DropdbStmt *a, DropdbStmt *b)
1131 {
1132         if (!equalstr(a->dbname, b->dbname))
1133                 return false;
1134
1135         return true;
1136 }
1137
1138 static bool
1139 _equalVacuumStmt(VacuumStmt *a, VacuumStmt *b)
1140 {
1141         if (a->vacuum != b->vacuum)
1142                 return false;
1143         if (a->full != b->full)
1144                 return false;
1145         if (a->analyze != b->analyze)
1146                 return false;
1147         if (a->freeze != b->freeze)
1148                 return false;
1149         if (a->verbose != b->verbose)
1150                 return false;
1151         if (!equal(a->relation, b->relation))
1152                 return false;
1153         if (!equal(a->va_cols, b->va_cols))
1154                 return false;
1155
1156         return true;
1157 }
1158
1159 static bool
1160 _equalExplainStmt(ExplainStmt *a, ExplainStmt *b)
1161 {
1162         if (!equal(a->query, b->query))
1163                 return false;
1164         if (a->verbose != b->verbose)
1165                 return false;
1166         if (a->analyze != b->analyze)
1167                 return false;
1168
1169         return true;
1170 }
1171
1172 static bool
1173 _equalCreateSeqStmt(CreateSeqStmt *a, CreateSeqStmt *b)
1174 {
1175         if (!equal(a->sequence, b->sequence))
1176                 return false;
1177         if (!equal(a->options, b->options))
1178                 return false;
1179
1180         return true;
1181 }
1182
1183 static bool
1184 _equalVariableSetStmt(VariableSetStmt *a, VariableSetStmt *b)
1185 {
1186         if (!equalstr(a->name, b->name))
1187                 return false;
1188         if (!equal(a->args, b->args))
1189                 return false;
1190
1191         return true;
1192 }
1193
1194 static bool
1195 _equalVariableShowStmt(VariableShowStmt *a, VariableShowStmt *b)
1196 {
1197         if (!equalstr(a->name, b->name))
1198                 return false;
1199
1200         return true;
1201 }
1202
1203 static bool
1204 _equalVariableResetStmt(VariableResetStmt *a, VariableResetStmt *b)
1205 {
1206         if (!equalstr(a->name, b->name))
1207                 return false;
1208
1209         return true;
1210 }
1211
1212 static bool
1213 _equalCreateTrigStmt(CreateTrigStmt *a, CreateTrigStmt *b)
1214 {
1215         if (!equalstr(a->trigname, b->trigname))
1216                 return false;
1217         if (!equal(a->relation, b->relation))
1218                 return false;
1219         if (!equalstr(a->funcname, b->funcname))
1220                 return false;
1221         if (!equal(a->args, b->args))
1222                 return false;
1223         if (a->before != b->before)
1224                 return false;
1225         if (a->row != b->row)
1226                 return false;
1227         if (strcmp(a->actions, b->actions) != 0)
1228                 return false;
1229         if (!equalstr(a->lang, b->lang))
1230                 return false;
1231         if (!equalstr(a->text, b->text))
1232                 return false;
1233         if (!equal(a->attr, b->attr))
1234                 return false;
1235         if (!equalstr(a->when, b->when))
1236                 return false;
1237         if (a->isconstraint != b->isconstraint)
1238                 return false;
1239         if (a->deferrable != b->deferrable)
1240                 return false;
1241         if (a->initdeferred != b->initdeferred)
1242                 return false;
1243         if (!equal(a->constrrel, b->constrrel))
1244                 return false;
1245
1246         return true;
1247 }
1248
1249 static bool
1250 _equalDropTrigStmt(DropTrigStmt *a, DropTrigStmt *b)
1251 {
1252         if (!equalstr(a->trigname, b->trigname))
1253                 return false;
1254         if (!equal(a->relation, b->relation))
1255                 return false;
1256
1257         return true;
1258 }
1259
1260 static bool
1261 _equalCreatePLangStmt(CreatePLangStmt *a, CreatePLangStmt *b)
1262 {
1263         if (!equalstr(a->plname, b->plname))
1264                 return false;
1265         if (!equalstr(a->plhandler, b->plhandler))
1266                 return false;
1267         if (!equalstr(a->plcompiler, b->plcompiler))
1268                 return false;
1269         if (a->pltrusted != b->pltrusted)
1270                 return false;
1271
1272         return true;
1273 }
1274
1275 static bool
1276 _equalDropPLangStmt(DropPLangStmt *a, DropPLangStmt *b)
1277 {
1278         if (!equalstr(a->plname, b->plname))
1279                 return false;
1280
1281         return true;
1282 }
1283
1284 static bool
1285 _equalCreateUserStmt(CreateUserStmt *a, CreateUserStmt *b)
1286 {
1287         if (!equalstr(a->user, b->user))
1288                 return false;
1289         if (!equal(a->options, b->options))
1290                 return false;
1291
1292         return true;
1293 }
1294
1295 static bool
1296 _equalAlterUserStmt(AlterUserStmt *a, AlterUserStmt *b)
1297 {
1298         if (!equalstr(a->user, b->user))
1299                 return false;
1300         if (!equal(a->options, b->options))
1301                 return false;
1302
1303         return true;
1304 }
1305
1306 static bool
1307 _equalAlterUserSetStmt(AlterUserSetStmt *a, AlterUserSetStmt *b)
1308 {
1309         if (!equalstr(a->user, b->user))
1310                 return false;
1311         if (!equalstr(a->variable, b->variable))
1312                 return false;
1313         if (!equal(a->value, b->value))
1314                 return false;
1315
1316         return true;
1317 }
1318
1319 static bool
1320 _equalDropUserStmt(DropUserStmt *a, DropUserStmt *b)
1321 {
1322         if (!equal(a->users, b->users))
1323                 return false;
1324
1325         return true;
1326 }
1327
1328 static bool
1329 _equalLockStmt(LockStmt *a, LockStmt *b)
1330 {
1331         if (!equal(a->relations, b->relations))
1332                 return false;
1333         if (a->mode != b->mode)
1334                 return false;
1335
1336         return true;
1337 }
1338
1339 static bool
1340 _equalConstraintsSetStmt(ConstraintsSetStmt *a, ConstraintsSetStmt *b)
1341 {
1342         if (!equal(a->constraints, b->constraints))
1343                 return false;
1344         if (a->deferred != b->deferred)
1345                 return false;
1346
1347         return true;
1348 }
1349
1350 static bool
1351 _equalCreateGroupStmt(CreateGroupStmt *a, CreateGroupStmt *b)
1352 {
1353         if (!equalstr(a->name, b->name))
1354                 return false;
1355         if (!equal(a->options, b->options))
1356                 return false;
1357
1358         return true;
1359 }
1360
1361 static bool
1362 _equalAlterGroupStmt(AlterGroupStmt *a, AlterGroupStmt *b)
1363 {
1364         if (!equalstr(a->name, b->name))
1365                 return false;
1366         if (a->action != b->action)
1367                 return false;
1368         if (!equal(a->listUsers, b->listUsers))
1369                 return false;
1370
1371         return true;
1372 }
1373
1374 static bool
1375 _equalDropGroupStmt(DropGroupStmt *a, DropGroupStmt *b)
1376 {
1377         if (!equalstr(a->name, b->name))
1378                 return false;
1379
1380         return true;
1381 }
1382
1383 static bool
1384 _equalReindexStmt(ReindexStmt *a, ReindexStmt *b)
1385 {
1386         if (a->reindexType != b->reindexType)
1387                 return false;
1388         if (!equal(a->relation, b->relation))
1389                 return false;
1390         if (!equalstr(a->name, b->name))
1391                 return false;
1392         if (a->force != b->force)
1393                 return false;
1394         if (a->all != b->all)
1395                 return false;
1396
1397         return true;
1398 }
1399
1400 static bool
1401 _equalCreateSchemaStmt(CreateSchemaStmt *a, CreateSchemaStmt *b)
1402 {
1403         if (!equalstr(a->schemaname, b->schemaname))
1404                 return false;
1405         if (!equalstr(a->authid, b->authid))
1406                 return false;
1407         if (!equal(a->schemaElts, b->schemaElts))
1408                 return false;
1409
1410         return true;
1411 }
1412
1413 static bool
1414 _equalAExpr(A_Expr *a, A_Expr *b)
1415 {
1416         if (a->oper != b->oper)
1417                 return false;
1418         if (!equalstr(a->opname, b->opname))
1419                 return false;
1420         if (!equal(a->lexpr, b->lexpr))
1421                 return false;
1422         if (!equal(a->rexpr, b->rexpr))
1423                 return false;
1424
1425         return true;
1426 }
1427
1428 static bool
1429 _equalColumnRef(ColumnRef *a, ColumnRef *b)
1430 {
1431         if (!equal(a->fields, b->fields))
1432                 return false;
1433         if (!equal(a->indirection, b->indirection))
1434                 return false;
1435
1436         return true;
1437 }
1438
1439 static bool
1440 _equalParamRef(ParamRef *a, ParamRef *b)
1441 {
1442         if (a->number != b->number)
1443                 return false;
1444         if (!equal(a->fields, b->fields))
1445                 return false;
1446         if (!equal(a->indirection, b->indirection))
1447                 return false;
1448
1449         return true;
1450 }
1451
1452 static bool
1453 _equalAConst(A_Const *a, A_Const *b)
1454 {
1455         if (!equal(&a->val, &b->val))
1456                 return false;
1457         if (!equal(a->typename, b->typename))
1458                 return false;
1459
1460         return true;
1461 }
1462
1463 static bool
1464 _equalIdent(Ident *a, Ident *b)
1465 {
1466         if (!equalstr(a->name, b->name))
1467                 return false;
1468
1469         return true;
1470 }
1471
1472 static bool
1473 _equalFuncCall(FuncCall *a, FuncCall *b)
1474 {
1475         if (!equalstr(a->funcname, b->funcname))
1476                 return false;
1477         if (!equal(a->args, b->args))
1478                 return false;
1479         if (a->agg_star != b->agg_star)
1480                 return false;
1481         if (a->agg_distinct != b->agg_distinct)
1482                 return false;
1483
1484         return true;
1485 }
1486
1487 static bool
1488 _equalAIndices(A_Indices *a, A_Indices *b)
1489 {
1490         if (!equal(a->lidx, b->lidx))
1491                 return false;
1492         if (!equal(a->uidx, b->uidx))
1493                 return false;
1494
1495         return true;
1496 }
1497
1498 static bool
1499 _equalExprFieldSelect(ExprFieldSelect *a, ExprFieldSelect *b)
1500 {
1501         if (!equal(a->arg, b->arg))
1502                 return false;
1503         if (!equal(a->fields, b->fields))
1504                 return false;
1505         if (!equal(a->indirection, b->indirection))
1506                 return false;
1507
1508         return true;
1509 }
1510
1511 static bool
1512 _equalResTarget(ResTarget *a, ResTarget *b)
1513 {
1514         if (!equalstr(a->name, b->name))
1515                 return false;
1516         if (!equal(a->indirection, b->indirection))
1517                 return false;
1518         if (!equal(a->val, b->val))
1519                 return false;
1520
1521         return true;
1522 }
1523
1524 static bool
1525 _equalTypeCast(TypeCast *a, TypeCast *b)
1526 {
1527         if (!equal(a->arg, b->arg))
1528                 return false;
1529         if (!equal(a->typename, b->typename))
1530                 return false;
1531
1532         return true;
1533 }
1534
1535 static bool
1536 _equalSortGroupBy(SortGroupBy *a, SortGroupBy *b)
1537 {
1538         if (!equalstr(a->useOp, b->useOp))
1539                 return false;
1540         if (!equal(a->node, b->node))
1541                 return false;
1542
1543         return true;
1544 }
1545
1546 static bool
1547 _equalAlias(Alias *a, Alias *b)
1548 {
1549         if (!equalstr(a->aliasname, b->aliasname))
1550                 return false;
1551         if (!equal(a->colnames, b->colnames))
1552                 return false;
1553
1554         return true;
1555 }
1556
1557 static bool
1558 _equalRangeVar(RangeVar *a, RangeVar *b)
1559 {
1560         if (!equalstr(a->catalogname, b->catalogname))
1561                 return false;
1562         if (!equalstr(a->schemaname, b->schemaname))
1563                 return false;
1564         if (!equalstr(a->relname, b->relname))
1565                 return false;
1566         if (a->inhOpt != b->inhOpt)
1567                 return false;
1568         if (a->istemp != b->istemp)
1569                 return false;
1570         if (!equal(a->alias, b->alias))
1571                 return false;
1572
1573         return true;
1574 }
1575
1576 static bool
1577 _equalRangeSubselect(RangeSubselect *a, RangeSubselect *b)
1578 {
1579         if (!equal(a->subquery, b->subquery))
1580                 return false;
1581         if (!equal(a->alias, b->alias))
1582                 return false;
1583
1584         return true;
1585 }
1586
1587 static bool
1588 _equalTypeName(TypeName *a, TypeName *b)
1589 {
1590         if (!equalstr(a->name, b->name))
1591                 return false;
1592         if (a->timezone != b->timezone)
1593                 return false;
1594         if (a->setof != b->setof)
1595                 return false;
1596         if (a->typmod != b->typmod)
1597                 return false;
1598         if (!equal(a->arrayBounds, b->arrayBounds))
1599                 return false;
1600
1601         return true;
1602 }
1603
1604 static bool
1605 _equalIndexElem(IndexElem *a, IndexElem *b)
1606 {
1607         if (!equalstr(a->name, b->name))
1608                 return false;
1609         if (!equal(a->args, b->args))
1610                 return false;
1611         if (!equalstr(a->class, b->class))
1612                 return false;
1613
1614         return true;
1615 }
1616
1617 static bool
1618 _equalColumnDef(ColumnDef *a, ColumnDef *b)
1619 {
1620         if (!equalstr(a->colname, b->colname))
1621                 return false;
1622         if (!equal(a->typename, b->typename))
1623                 return false;
1624         if (a->is_not_null != b->is_not_null)
1625                 return false;
1626         if (!equal(a->raw_default, b->raw_default))
1627                 return false;
1628         if (!equalstr(a->cooked_default, b->cooked_default))
1629                 return false;
1630         if (!equal(a->constraints, b->constraints))
1631                 return false;
1632
1633         return true;
1634 }
1635
1636 static bool
1637 _equalConstraint(Constraint *a, Constraint *b)
1638 {
1639         if (a->contype != b->contype)
1640                 return false;
1641         if (!equalstr(a->name, b->name))
1642                 return false;
1643         if (!equal(a->raw_expr, b->raw_expr))
1644                 return false;
1645         if (!equalstr(a->cooked_expr, b->cooked_expr))
1646                 return false;
1647         if (!equal(a->keys, b->keys))
1648                 return false;
1649
1650         return true;
1651 }
1652
1653 static bool
1654 _equalDefElem(DefElem *a, DefElem *b)
1655 {
1656         if (!equalstr(a->defname, b->defname))
1657                 return false;
1658         if (!equal(a->arg, b->arg))
1659                 return false;
1660
1661         return true;
1662 }
1663
1664 static bool
1665 _equalTargetEntry(TargetEntry *a, TargetEntry *b)
1666 {
1667         if (!equal(a->resdom, b->resdom))
1668                 return false;
1669         if (!equal(a->fjoin, b->fjoin))
1670                 return false;
1671         if (!equal(a->expr, b->expr))
1672                 return false;
1673
1674         return true;
1675 }
1676
1677 static bool
1678 _equalRangeTblEntry(RangeTblEntry *a, RangeTblEntry *b)
1679 {
1680         if (a->rtekind != b->rtekind)
1681                 return false;
1682         if (!equalstr(a->relname, b->relname))
1683                 return false;
1684         if (a->relid != b->relid)
1685                 return false;
1686         if (!equal(a->subquery, b->subquery))
1687                 return false;
1688         if (a->jointype != b->jointype)
1689                 return false;
1690         if (!equali(a->joincoltypes, b->joincoltypes))
1691                 return false;
1692         if (!equali(a->joincoltypmods, b->joincoltypmods))
1693                 return false;
1694         if (!equali(a->joinleftcols, b->joinleftcols))
1695                 return false;
1696         if (!equali(a->joinrightcols, b->joinrightcols))
1697                 return false;
1698         if (!equal(a->alias, b->alias))
1699                 return false;
1700         if (!equal(a->eref, b->eref))
1701                 return false;
1702         if (a->inh != b->inh)
1703                 return false;
1704         if (a->inFromCl != b->inFromCl)
1705                 return false;
1706         if (a->checkForRead != b->checkForRead)
1707                 return false;
1708         if (a->checkForWrite != b->checkForWrite)
1709                 return false;
1710         if (a->checkAsUser != b->checkAsUser)
1711                 return false;
1712
1713         return true;
1714 }
1715
1716 static bool
1717 _equalSortClause(SortClause *a, SortClause *b)
1718 {
1719         if (a->tleSortGroupRef != b->tleSortGroupRef)
1720                 return false;
1721         if (a->sortop != b->sortop)
1722                 return false;
1723
1724         return true;
1725 }
1726
1727 static bool
1728 _equalFkConstraint(FkConstraint *a, FkConstraint *b)
1729 {
1730         if (!equalstr(a->constr_name, b->constr_name))
1731                 return false;
1732         if (!equal(a->pktable, b->pktable))
1733                 return false;
1734         if (!equal(a->fk_attrs, b->fk_attrs))
1735                 return false;
1736         if (!equal(a->pk_attrs, b->pk_attrs))
1737                 return false;
1738         if (!equalstr(a->match_type, b->match_type))
1739                 return false;
1740         if (a->actions != b->actions)
1741                 return false;
1742         if (a->deferrable != b->deferrable)
1743                 return false;
1744         if (a->initdeferred != b->initdeferred)
1745                 return false;
1746
1747         return true;
1748 }
1749
1750 static bool
1751 _equalCaseExpr(CaseExpr *a, CaseExpr *b)
1752 {
1753         if (a->casetype != b->casetype)
1754                 return false;
1755         if (!equal(a->arg, b->arg))
1756                 return false;
1757         if (!equal(a->args, b->args))
1758                 return false;
1759         if (!equal(a->defresult, b->defresult))
1760                 return false;
1761
1762         return true;
1763 }
1764
1765 static bool
1766 _equalCaseWhen(CaseWhen *a, CaseWhen *b)
1767 {
1768         if (!equal(a->expr, b->expr))
1769                 return false;
1770         if (!equal(a->result, b->result))
1771                 return false;
1772
1773         return true;
1774 }
1775
1776 static bool
1777 _equalNullTest(NullTest *a, NullTest *b)
1778 {
1779         if (!equal(a->arg, b->arg))
1780                 return false;
1781         if (a->nulltesttype != b->nulltesttype)
1782                 return false;
1783         return true;
1784 }
1785
1786 static bool
1787 _equalBooleanTest(BooleanTest *a, BooleanTest *b)
1788 {
1789         if (!equal(a->arg, b->arg))
1790                 return false;
1791         if (a->booltesttype != b->booltesttype)
1792                 return false;
1793         return true;
1794 }
1795
1796 /*
1797  * Stuff from pg_list.h
1798  */
1799
1800 static bool
1801 _equalValue(Value *a, Value *b)
1802 {
1803         if (a->type != b->type)
1804                 return false;
1805
1806         switch (a->type)
1807         {
1808                 case T_Integer:
1809                         return a->val.ival == b->val.ival;
1810                 case T_Float:
1811                 case T_String:
1812                 case T_BitString:
1813                         return strcmp(a->val.str, b->val.str) == 0;
1814                 default:
1815                         break;
1816         }
1817
1818         return true;
1819 }
1820
1821 /*
1822  * equal
1823  *        returns whether two nodes are equal
1824  */
1825 bool
1826 equal(void *a, void *b)
1827 {
1828         bool            retval = false;
1829
1830         if (a == b)
1831                 return true;
1832
1833         /*
1834          * note that a!=b, so only one of them can be NULL
1835          */
1836         if (a == NULL || b == NULL)
1837                 return false;
1838
1839         /*
1840          * are they the same type of nodes?
1841          */
1842         if (nodeTag(a) != nodeTag(b))
1843                 return false;
1844
1845         switch (nodeTag(a))
1846         {
1847                 case T_SubPlan:
1848                         retval = _equalSubPlan(a, b);
1849                         break;
1850
1851                 case T_Resdom:
1852                         retval = _equalResdom(a, b);
1853                         break;
1854                 case T_Fjoin:
1855                         retval = _equalFjoin(a, b);
1856                         break;
1857                 case T_Expr:
1858                         retval = _equalExpr(a, b);
1859                         break;
1860                 case T_Var:
1861                         retval = _equalVar(a, b);
1862                         break;
1863                 case T_Oper:
1864                         retval = _equalOper(a, b);
1865                         break;
1866                 case T_Const:
1867                         retval = _equalConst(a, b);
1868                         break;
1869                 case T_Param:
1870                         retval = _equalParam(a, b);
1871                         break;
1872                 case T_Aggref:
1873                         retval = _equalAggref(a, b);
1874                         break;
1875                 case T_SubLink:
1876                         retval = _equalSubLink(a, b);
1877                         break;
1878                 case T_Func:
1879                         retval = _equalFunc(a, b);
1880                         break;
1881                 case T_FieldSelect:
1882                         retval = _equalFieldSelect(a, b);
1883                         break;
1884                 case T_ArrayRef:
1885                         retval = _equalArrayRef(a, b);
1886                         break;
1887                 case T_Iter:
1888                         retval = _equalIter(a, b);
1889                         break;
1890                 case T_RelabelType:
1891                         retval = _equalRelabelType(a, b);
1892                         break;
1893                 case T_RangeTblRef:
1894                         retval = _equalRangeTblRef(a, b);
1895                         break;
1896                 case T_FromExpr:
1897                         retval = _equalFromExpr(a, b);
1898                         break;
1899                 case T_JoinExpr:
1900                         retval = _equalJoinExpr(a, b);
1901                         break;
1902
1903                 case T_RelOptInfo:
1904                         retval = _equalRelOptInfo(a, b);
1905                         break;
1906                 case T_Path:
1907                         retval = _equalPath(a, b);
1908                         break;
1909                 case T_IndexPath:
1910                         retval = _equalIndexPath(a, b);
1911                         break;
1912                 case T_NestPath:
1913                         retval = _equalNestPath(a, b);
1914                         break;
1915                 case T_MergePath:
1916                         retval = _equalMergePath(a, b);
1917                         break;
1918                 case T_HashPath:
1919                         retval = _equalHashPath(a, b);
1920                         break;
1921                 case T_PathKeyItem:
1922                         retval = _equalPathKeyItem(a, b);
1923                         break;
1924                 case T_RestrictInfo:
1925                         retval = _equalRestrictInfo(a, b);
1926                         break;
1927                 case T_JoinInfo:
1928                         retval = _equalJoinInfo(a, b);
1929                         break;
1930                 case T_Stream:
1931                         retval = _equalStream(a, b);
1932                         break;
1933                 case T_TidPath:
1934                         retval = _equalTidPath(a, b);
1935                         break;
1936                 case T_AppendPath:
1937                         retval = _equalAppendPath(a, b);
1938                         break;
1939                 case T_IndexOptInfo:
1940                         retval = _equalIndexOptInfo(a, b);
1941                         break;
1942
1943                 case T_List:
1944                         {
1945                                 List       *la = (List *) a;
1946                                 List       *lb = (List *) b;
1947                                 List       *l;
1948
1949                                 /*
1950                                  * Try to reject by length check before we grovel through
1951                                  * all the elements...
1952                                  */
1953                                 if (length(la) != length(lb))
1954                                         return false;
1955                                 foreach(l, la)
1956                                 {
1957                                         if (!equal(lfirst(l), lfirst(lb)))
1958                                                 return false;
1959                                         lb = lnext(lb);
1960                                 }
1961                                 retval = true;
1962                         }
1963                         break;
1964                 case T_Integer:
1965                 case T_Float:
1966                 case T_String:
1967                 case T_BitString:
1968                         retval = _equalValue(a, b);
1969                         break;
1970
1971                 case T_Query:
1972                         retval = _equalQuery(a, b);
1973                         break;
1974                 case T_InsertStmt:
1975                         retval = _equalInsertStmt(a, b);
1976                         break;
1977                 case T_DeleteStmt:
1978                         retval = _equalDeleteStmt(a, b);
1979                         break;
1980                 case T_UpdateStmt:
1981                         retval = _equalUpdateStmt(a, b);
1982                         break;
1983                 case T_SelectStmt:
1984                         retval = _equalSelectStmt(a, b);
1985                         break;
1986                 case T_SetOperationStmt:
1987                         retval = _equalSetOperationStmt(a, b);
1988                         break;
1989                 case T_AlterTableStmt:
1990                         retval = _equalAlterTableStmt(a, b);
1991                         break;
1992                 case T_GrantStmt:
1993                         retval = _equalGrantStmt(a, b);
1994                         break;
1995                 case T_ClosePortalStmt:
1996                         retval = _equalClosePortalStmt(a, b);
1997                         break;
1998                 case T_ClusterStmt:
1999                         retval = _equalClusterStmt(a, b);
2000                         break;
2001                 case T_CopyStmt:
2002                         retval = _equalCopyStmt(a, b);
2003                         break;
2004                 case T_CreateStmt:
2005                         retval = _equalCreateStmt(a, b);
2006                         break;
2007                 case T_VersionStmt:
2008                         retval = _equalVersionStmt(a, b);
2009                         break;
2010                 case T_DefineStmt:
2011                         retval = _equalDefineStmt(a, b);
2012                         break;
2013                 case T_DropStmt:
2014                         retval = _equalDropStmt(a, b);
2015                         break;
2016                 case T_TruncateStmt:
2017                         retval = _equalTruncateStmt(a, b);
2018                         break;
2019                 case T_CommentStmt:
2020                         retval = _equalCommentStmt(a, b);
2021                         break;
2022                 case T_FetchStmt:
2023                         retval = _equalFetchStmt(a, b);
2024                         break;
2025                 case T_IndexStmt:
2026                         retval = _equalIndexStmt(a, b);
2027                         break;
2028                 case T_ProcedureStmt:
2029                         retval = _equalProcedureStmt(a, b);
2030                         break;
2031                 case T_RemoveAggrStmt:
2032                         retval = _equalRemoveAggrStmt(a, b);
2033                         break;
2034                 case T_RemoveFuncStmt:
2035                         retval = _equalRemoveFuncStmt(a, b);
2036                         break;
2037                 case T_RemoveOperStmt:
2038                         retval = _equalRemoveOperStmt(a, b);
2039                         break;
2040                 case T_RenameStmt:
2041                         retval = _equalRenameStmt(a, b);
2042                         break;
2043                 case T_RuleStmt:
2044                         retval = _equalRuleStmt(a, b);
2045                         break;
2046                 case T_NotifyStmt:
2047                         retval = _equalNotifyStmt(a, b);
2048                         break;
2049                 case T_ListenStmt:
2050                         retval = _equalListenStmt(a, b);
2051                         break;
2052                 case T_UnlistenStmt:
2053                         retval = _equalUnlistenStmt(a, b);
2054                         break;
2055                 case T_TransactionStmt:
2056                         retval = _equalTransactionStmt(a, b);
2057                         break;
2058                 case T_ViewStmt:
2059                         retval = _equalViewStmt(a, b);
2060                         break;
2061                 case T_LoadStmt:
2062                         retval = _equalLoadStmt(a, b);
2063                         break;
2064                 case T_CreateDomainStmt:
2065                         retval = _equalCreateDomainStmt(a, b);
2066                         break;
2067                 case T_CreatedbStmt:
2068                         retval = _equalCreatedbStmt(a, b);
2069                         break;
2070                 case T_AlterDatabaseSetStmt:
2071                         retval = _equalAlterDatabaseSetStmt(a, b);
2072                         break;
2073                 case T_DropdbStmt:
2074                         retval = _equalDropdbStmt(a, b);
2075                         break;
2076                 case T_VacuumStmt:
2077                         retval = _equalVacuumStmt(a, b);
2078                         break;
2079                 case T_ExplainStmt:
2080                         retval = _equalExplainStmt(a, b);
2081                         break;
2082                 case T_CreateSeqStmt:
2083                         retval = _equalCreateSeqStmt(a, b);
2084                         break;
2085                 case T_VariableSetStmt:
2086                         retval = _equalVariableSetStmt(a, b);
2087                         break;
2088                 case T_VariableShowStmt:
2089                         retval = _equalVariableShowStmt(a, b);
2090                         break;
2091                 case T_VariableResetStmt:
2092                         retval = _equalVariableResetStmt(a, b);
2093                         break;
2094                 case T_CreateTrigStmt:
2095                         retval = _equalCreateTrigStmt(a, b);
2096                         break;
2097                 case T_DropTrigStmt:
2098                         retval = _equalDropTrigStmt(a, b);
2099                         break;
2100                 case T_CreatePLangStmt:
2101                         retval = _equalCreatePLangStmt(a, b);
2102                         break;
2103                 case T_DropPLangStmt:
2104                         retval = _equalDropPLangStmt(a, b);
2105                         break;
2106                 case T_CreateUserStmt:
2107                         retval = _equalCreateUserStmt(a, b);
2108                         break;
2109                 case T_AlterUserStmt:
2110                         retval = _equalAlterUserStmt(a, b);
2111                         break;
2112                 case T_AlterUserSetStmt:
2113                         retval = _equalAlterUserSetStmt(a, b);
2114                         break;
2115                 case T_DropUserStmt:
2116                         retval = _equalDropUserStmt(a, b);
2117                         break;
2118                 case T_LockStmt:
2119                         retval = _equalLockStmt(a, b);
2120                         break;
2121                 case T_ConstraintsSetStmt:
2122                         retval = _equalConstraintsSetStmt(a, b);
2123                         break;
2124                 case T_CreateGroupStmt:
2125                         retval = _equalCreateGroupStmt(a, b);
2126                         break;
2127                 case T_AlterGroupStmt:
2128                         retval = _equalAlterGroupStmt(a, b);
2129                         break;
2130                 case T_DropGroupStmt:
2131                         retval = _equalDropGroupStmt(a, b);
2132                         break;
2133                 case T_ReindexStmt:
2134                         retval = _equalReindexStmt(a, b);
2135                         break;
2136                 case T_CheckPointStmt:
2137                         retval = true;
2138                         break;
2139                 case T_CreateSchemaStmt:
2140                         retval = _equalCreateSchemaStmt(a, b);
2141                         break;
2142
2143                 case T_A_Expr:
2144                         retval = _equalAExpr(a, b);
2145                         break;
2146                 case T_ColumnRef:
2147                         retval = _equalColumnRef(a, b);
2148                         break;
2149                 case T_ParamRef:
2150                         retval = _equalParamRef(a, b);
2151                         break;
2152                 case T_A_Const:
2153                         retval = _equalAConst(a, b);
2154                         break;
2155                 case T_Ident:
2156                         retval = _equalIdent(a, b);
2157                         break;
2158                 case T_FuncCall:
2159                         retval = _equalFuncCall(a, b);
2160                         break;
2161                 case T_A_Indices:
2162                         retval = _equalAIndices(a, b);
2163                         break;
2164                 case T_ExprFieldSelect:
2165                         retval = _equalExprFieldSelect(a, b);
2166                         break;
2167                 case T_ResTarget:
2168                         retval = _equalResTarget(a, b);
2169                         break;
2170                 case T_TypeCast:
2171                         retval = _equalTypeCast(a, b);
2172                         break;
2173                 case T_SortGroupBy:
2174                         retval = _equalSortGroupBy(a, b);
2175                         break;
2176                 case T_Alias:
2177                         retval = _equalAlias(a, b);
2178                         break;
2179                 case T_RangeVar:
2180                         retval = _equalRangeVar(a, b);
2181                         break;
2182                 case T_RangeSubselect:
2183                         retval = _equalRangeSubselect(a, b);
2184                         break;
2185                 case T_TypeName:
2186                         retval = _equalTypeName(a, b);
2187                         break;
2188                 case T_IndexElem:
2189                         retval = _equalIndexElem(a, b);
2190                         break;
2191                 case T_ColumnDef:
2192                         retval = _equalColumnDef(a, b);
2193                         break;
2194                 case T_Constraint:
2195                         retval = _equalConstraint(a, b);
2196                         break;
2197                 case T_DefElem:
2198                         retval = _equalDefElem(a, b);
2199                         break;
2200                 case T_TargetEntry:
2201                         retval = _equalTargetEntry(a, b);
2202                         break;
2203                 case T_RangeTblEntry:
2204                         retval = _equalRangeTblEntry(a, b);
2205                         break;
2206                 case T_SortClause:
2207                         retval = _equalSortClause(a, b);
2208                         break;
2209                 case T_GroupClause:
2210                         /* GroupClause is equivalent to SortClause */
2211                         retval = _equalSortClause(a, b);
2212                         break;
2213                 case T_CaseExpr:
2214                         retval = _equalCaseExpr(a, b);
2215                         break;
2216                 case T_CaseWhen:
2217                         retval = _equalCaseWhen(a, b);
2218                         break;
2219                 case T_NullTest:
2220                         retval = _equalNullTest(a, b);
2221                         break;
2222                 case T_BooleanTest:
2223                         retval = _equalBooleanTest(a, b);
2224                         break;
2225                 case T_FkConstraint:
2226                         retval = _equalFkConstraint(a, b);
2227                         break;
2228                 case T_PrivGrantee:
2229                         retval = _equalPrivGrantee(a, b);
2230                         break;
2231                 case T_FuncWithArgs:
2232                         retval = _equalFuncWithArgs(a, b);
2233                         break;
2234
2235                 default:
2236                         elog(WARNING, "equal: don't know whether nodes of type %d are equal",
2237                                  nodeTag(a));
2238                         break;
2239         }
2240
2241         return retval;
2242 }