]> granicus.if.org Git - postgresql/blob - src/backend/nodes/readfuncs.c
Add support for INSERT ... ON CONFLICT DO NOTHING/UPDATE.
[postgresql] / src / backend / nodes / readfuncs.c
1 /*-------------------------------------------------------------------------
2  *
3  * readfuncs.c
4  *        Reader functions for Postgres tree nodes.
5  *
6  * Portions Copyright (c) 1996-2015, PostgreSQL Global Development Group
7  * Portions Copyright (c) 1994, Regents of the University of California
8  *
9  *
10  * IDENTIFICATION
11  *        src/backend/nodes/readfuncs.c
12  *
13  * NOTES
14  *        Path and Plan nodes do not have any readfuncs support, because we
15  *        never have occasion to read them in.  (There was once code here that
16  *        claimed to read them, but it was broken as well as unused.)  We
17  *        never read executor state trees, either.
18  *
19  *        Parse location fields are written out by outfuncs.c, but only for
20  *        possible debugging use.  When reading a location field, we discard
21  *        the stored value and set the location field to -1 (ie, "unknown").
22  *        This is because nodes coming from a stored rule should not be thought
23  *        to have a known location in the current query's text.
24  *
25  *-------------------------------------------------------------------------
26  */
27 #include "postgres.h"
28
29 #include <math.h>
30
31 #include "nodes/parsenodes.h"
32 #include "nodes/readfuncs.h"
33
34
35 /*
36  * Macros to simplify reading of different kinds of fields.  Use these
37  * wherever possible to reduce the chance for silly typos.  Note that these
38  * hard-wire conventions about the names of the local variables in a Read
39  * routine.
40  */
41
42 /* Macros for declaring appropriate local variables */
43
44 /* A few guys need only local_node */
45 #define READ_LOCALS_NO_FIELDS(nodeTypeName) \
46         nodeTypeName *local_node = makeNode(nodeTypeName)
47
48 /* And a few guys need only the pg_strtok support fields */
49 #define READ_TEMP_LOCALS()      \
50         char       *token;              \
51         int                     length
52
53 /* ... but most need both */
54 #define READ_LOCALS(nodeTypeName)                       \
55         READ_LOCALS_NO_FIELDS(nodeTypeName);    \
56         READ_TEMP_LOCALS()
57
58 /* Read an integer field (anything written as ":fldname %d") */
59 #define READ_INT_FIELD(fldname) \
60         token = pg_strtok(&length);             /* skip :fldname */ \
61         token = pg_strtok(&length);             /* get field value */ \
62         local_node->fldname = atoi(token)
63
64 /* Read an unsigned integer field (anything written as ":fldname %u") */
65 #define READ_UINT_FIELD(fldname) \
66         token = pg_strtok(&length);             /* skip :fldname */ \
67         token = pg_strtok(&length);             /* get field value */ \
68         local_node->fldname = atoui(token)
69
70 /* Read an OID field (don't hard-wire assumption that OID is same as uint) */
71 #define READ_OID_FIELD(fldname) \
72         token = pg_strtok(&length);             /* skip :fldname */ \
73         token = pg_strtok(&length);             /* get field value */ \
74         local_node->fldname = atooid(token)
75
76 /* Read a char field (ie, one ascii character) */
77 #define READ_CHAR_FIELD(fldname) \
78         token = pg_strtok(&length);             /* skip :fldname */ \
79         token = pg_strtok(&length);             /* get field value */ \
80         local_node->fldname = token[0]
81
82 /* Read an enumerated-type field that was written as an integer code */
83 #define READ_ENUM_FIELD(fldname, enumtype) \
84         token = pg_strtok(&length);             /* skip :fldname */ \
85         token = pg_strtok(&length);             /* get field value */ \
86         local_node->fldname = (enumtype) atoi(token)
87
88 /* Read a float field */
89 #define READ_FLOAT_FIELD(fldname) \
90         token = pg_strtok(&length);             /* skip :fldname */ \
91         token = pg_strtok(&length);             /* get field value */ \
92         local_node->fldname = atof(token)
93
94 /* Read a boolean field */
95 #define READ_BOOL_FIELD(fldname) \
96         token = pg_strtok(&length);             /* skip :fldname */ \
97         token = pg_strtok(&length);             /* get field value */ \
98         local_node->fldname = strtobool(token)
99
100 /* Read a character-string field */
101 #define READ_STRING_FIELD(fldname) \
102         token = pg_strtok(&length);             /* skip :fldname */ \
103         token = pg_strtok(&length);             /* get field value */ \
104         local_node->fldname = nullable_string(token, length)
105
106 /* Read a parse location field (and throw away the value, per notes above) */
107 #define READ_LOCATION_FIELD(fldname) \
108         token = pg_strtok(&length);             /* skip :fldname */ \
109         token = pg_strtok(&length);             /* get field value */ \
110         (void) token;                           /* in case not used elsewhere */ \
111         local_node->fldname = -1        /* set field to "unknown" */
112
113 /* Read a Node field */
114 #define READ_NODE_FIELD(fldname) \
115         token = pg_strtok(&length);             /* skip :fldname */ \
116         (void) token;                           /* in case not used elsewhere */ \
117         local_node->fldname = nodeRead(NULL, 0)
118
119 /* Read a bitmapset field */
120 #define READ_BITMAPSET_FIELD(fldname) \
121         token = pg_strtok(&length);             /* skip :fldname */ \
122         (void) token;                           /* in case not used elsewhere */ \
123         local_node->fldname = _readBitmapset()
124
125 /* Routine exit */
126 #define READ_DONE() \
127         return local_node
128
129
130 /*
131  * NOTE: use atoi() to read values written with %d, or atoui() to read
132  * values written with %u in outfuncs.c.  An exception is OID values,
133  * for which use atooid().  (As of 7.1, outfuncs.c writes OIDs as %u,
134  * but this will probably change in the future.)
135  */
136 #define atoui(x)  ((unsigned int) strtoul((x), NULL, 10))
137
138 #define atooid(x)  ((Oid) strtoul((x), NULL, 10))
139
140 #define strtobool(x)  ((*(x) == 't') ? true : false)
141
142 #define nullable_string(token,length)  \
143         ((length) == 0 ? NULL : debackslash(token, length))
144
145
146 static Datum readDatum(bool typbyval);
147
148 /*
149  * _readBitmapset
150  */
151 static Bitmapset *
152 _readBitmapset(void)
153 {
154         Bitmapset  *result = NULL;
155
156         READ_TEMP_LOCALS();
157
158         token = pg_strtok(&length);
159         if (token == NULL)
160                 elog(ERROR, "incomplete Bitmapset structure");
161         if (length != 1 || token[0] != '(')
162                 elog(ERROR, "unrecognized token: \"%.*s\"", length, token);
163
164         token = pg_strtok(&length);
165         if (token == NULL)
166                 elog(ERROR, "incomplete Bitmapset structure");
167         if (length != 1 || token[0] != 'b')
168                 elog(ERROR, "unrecognized token: \"%.*s\"", length, token);
169
170         for (;;)
171         {
172                 int                     val;
173                 char       *endptr;
174
175                 token = pg_strtok(&length);
176                 if (token == NULL)
177                         elog(ERROR, "unterminated Bitmapset structure");
178                 if (length == 1 && token[0] == ')')
179                         break;
180                 val = (int) strtol(token, &endptr, 10);
181                 if (endptr != token + length)
182                         elog(ERROR, "unrecognized integer: \"%.*s\"", length, token);
183                 result = bms_add_member(result, val);
184         }
185
186         return result;
187 }
188
189
190 /*
191  * _readQuery
192  */
193 static Query *
194 _readQuery(void)
195 {
196         READ_LOCALS(Query);
197
198         READ_ENUM_FIELD(commandType, CmdType);
199         READ_ENUM_FIELD(querySource, QuerySource);
200         local_node->queryId = 0;        /* not saved in output format */
201         READ_BOOL_FIELD(canSetTag);
202         READ_NODE_FIELD(utilityStmt);
203         READ_INT_FIELD(resultRelation);
204         READ_BOOL_FIELD(hasAggs);
205         READ_BOOL_FIELD(hasWindowFuncs);
206         READ_BOOL_FIELD(hasSubLinks);
207         READ_BOOL_FIELD(hasDistinctOn);
208         READ_BOOL_FIELD(hasRecursive);
209         READ_BOOL_FIELD(hasModifyingCTE);
210         READ_BOOL_FIELD(hasForUpdate);
211         READ_BOOL_FIELD(hasRowSecurity);
212         READ_NODE_FIELD(cteList);
213         READ_NODE_FIELD(rtable);
214         READ_NODE_FIELD(jointree);
215         READ_NODE_FIELD(targetList);
216         READ_NODE_FIELD(withCheckOptions);
217         READ_NODE_FIELD(onConflict);
218         READ_NODE_FIELD(returningList);
219         READ_NODE_FIELD(groupClause);
220         READ_NODE_FIELD(havingQual);
221         READ_NODE_FIELD(windowClause);
222         READ_NODE_FIELD(distinctClause);
223         READ_NODE_FIELD(sortClause);
224         READ_NODE_FIELD(limitOffset);
225         READ_NODE_FIELD(limitCount);
226         READ_NODE_FIELD(rowMarks);
227         READ_NODE_FIELD(setOperations);
228         READ_NODE_FIELD(constraintDeps);
229
230         READ_DONE();
231 }
232
233 /*
234  * _readNotifyStmt
235  */
236 static NotifyStmt *
237 _readNotifyStmt(void)
238 {
239         READ_LOCALS(NotifyStmt);
240
241         READ_STRING_FIELD(conditionname);
242         READ_STRING_FIELD(payload);
243
244         READ_DONE();
245 }
246
247 /*
248  * _readDeclareCursorStmt
249  */
250 static DeclareCursorStmt *
251 _readDeclareCursorStmt(void)
252 {
253         READ_LOCALS(DeclareCursorStmt);
254
255         READ_STRING_FIELD(portalname);
256         READ_INT_FIELD(options);
257         READ_NODE_FIELD(query);
258
259         READ_DONE();
260 }
261
262 /*
263  * _readWithCheckOption
264  */
265 static WithCheckOption *
266 _readWithCheckOption(void)
267 {
268         READ_LOCALS(WithCheckOption);
269
270         READ_ENUM_FIELD(kind, WCOKind);
271         READ_STRING_FIELD(relname);
272         READ_NODE_FIELD(qual);
273         READ_BOOL_FIELD(cascaded);
274
275         READ_DONE();
276 }
277
278 /*
279  * _readSortGroupClause
280  */
281 static SortGroupClause *
282 _readSortGroupClause(void)
283 {
284         READ_LOCALS(SortGroupClause);
285
286         READ_UINT_FIELD(tleSortGroupRef);
287         READ_OID_FIELD(eqop);
288         READ_OID_FIELD(sortop);
289         READ_BOOL_FIELD(nulls_first);
290         READ_BOOL_FIELD(hashable);
291
292         READ_DONE();
293 }
294
295 /*
296  * _readWindowClause
297  */
298 static WindowClause *
299 _readWindowClause(void)
300 {
301         READ_LOCALS(WindowClause);
302
303         READ_STRING_FIELD(name);
304         READ_STRING_FIELD(refname);
305         READ_NODE_FIELD(partitionClause);
306         READ_NODE_FIELD(orderClause);
307         READ_INT_FIELD(frameOptions);
308         READ_NODE_FIELD(startOffset);
309         READ_NODE_FIELD(endOffset);
310         READ_UINT_FIELD(winref);
311         READ_BOOL_FIELD(copiedOrder);
312
313         READ_DONE();
314 }
315
316 /*
317  * _readRowMarkClause
318  */
319 static RowMarkClause *
320 _readRowMarkClause(void)
321 {
322         READ_LOCALS(RowMarkClause);
323
324         READ_UINT_FIELD(rti);
325         READ_ENUM_FIELD(strength, LockClauseStrength);
326         READ_ENUM_FIELD(waitPolicy, LockWaitPolicy);
327         READ_BOOL_FIELD(pushedDown);
328
329         READ_DONE();
330 }
331
332 /*
333  * _readCommonTableExpr
334  */
335 static CommonTableExpr *
336 _readCommonTableExpr(void)
337 {
338         READ_LOCALS(CommonTableExpr);
339
340         READ_STRING_FIELD(ctename);
341         READ_NODE_FIELD(aliascolnames);
342         READ_NODE_FIELD(ctequery);
343         READ_LOCATION_FIELD(location);
344         READ_BOOL_FIELD(cterecursive);
345         READ_INT_FIELD(cterefcount);
346         READ_NODE_FIELD(ctecolnames);
347         READ_NODE_FIELD(ctecoltypes);
348         READ_NODE_FIELD(ctecoltypmods);
349         READ_NODE_FIELD(ctecolcollations);
350
351         READ_DONE();
352 }
353
354 /*
355  * _readSetOperationStmt
356  */
357 static SetOperationStmt *
358 _readSetOperationStmt(void)
359 {
360         READ_LOCALS(SetOperationStmt);
361
362         READ_ENUM_FIELD(op, SetOperation);
363         READ_BOOL_FIELD(all);
364         READ_NODE_FIELD(larg);
365         READ_NODE_FIELD(rarg);
366         READ_NODE_FIELD(colTypes);
367         READ_NODE_FIELD(colTypmods);
368         READ_NODE_FIELD(colCollations);
369         READ_NODE_FIELD(groupClauses);
370
371         READ_DONE();
372 }
373
374
375 /*
376  *      Stuff from primnodes.h.
377  */
378
379 static Alias *
380 _readAlias(void)
381 {
382         READ_LOCALS(Alias);
383
384         READ_STRING_FIELD(aliasname);
385         READ_NODE_FIELD(colnames);
386
387         READ_DONE();
388 }
389
390 static RangeVar *
391 _readRangeVar(void)
392 {
393         READ_LOCALS(RangeVar);
394
395         local_node->catalogname = NULL;         /* not currently saved in output
396                                                                                  * format */
397
398         READ_STRING_FIELD(schemaname);
399         READ_STRING_FIELD(relname);
400         READ_ENUM_FIELD(inhOpt, InhOption);
401         READ_CHAR_FIELD(relpersistence);
402         READ_NODE_FIELD(alias);
403         READ_LOCATION_FIELD(location);
404
405         READ_DONE();
406 }
407
408 static IntoClause *
409 _readIntoClause(void)
410 {
411         READ_LOCALS(IntoClause);
412
413         READ_NODE_FIELD(rel);
414         READ_NODE_FIELD(colNames);
415         READ_NODE_FIELD(options);
416         READ_ENUM_FIELD(onCommit, OnCommitAction);
417         READ_STRING_FIELD(tableSpaceName);
418         READ_NODE_FIELD(viewQuery);
419         READ_BOOL_FIELD(skipData);
420
421         READ_DONE();
422 }
423
424 /*
425  * _readVar
426  */
427 static Var *
428 _readVar(void)
429 {
430         READ_LOCALS(Var);
431
432         READ_UINT_FIELD(varno);
433         READ_INT_FIELD(varattno);
434         READ_OID_FIELD(vartype);
435         READ_INT_FIELD(vartypmod);
436         READ_OID_FIELD(varcollid);
437         READ_UINT_FIELD(varlevelsup);
438         READ_UINT_FIELD(varnoold);
439         READ_INT_FIELD(varoattno);
440         READ_LOCATION_FIELD(location);
441
442         READ_DONE();
443 }
444
445 /*
446  * _readConst
447  */
448 static Const *
449 _readConst(void)
450 {
451         READ_LOCALS(Const);
452
453         READ_OID_FIELD(consttype);
454         READ_INT_FIELD(consttypmod);
455         READ_OID_FIELD(constcollid);
456         READ_INT_FIELD(constlen);
457         READ_BOOL_FIELD(constbyval);
458         READ_BOOL_FIELD(constisnull);
459         READ_LOCATION_FIELD(location);
460
461         token = pg_strtok(&length); /* skip :constvalue */
462         if (local_node->constisnull)
463                 token = pg_strtok(&length);             /* skip "<>" */
464         else
465                 local_node->constvalue = readDatum(local_node->constbyval);
466
467         READ_DONE();
468 }
469
470 /*
471  * _readParam
472  */
473 static Param *
474 _readParam(void)
475 {
476         READ_LOCALS(Param);
477
478         READ_ENUM_FIELD(paramkind, ParamKind);
479         READ_INT_FIELD(paramid);
480         READ_OID_FIELD(paramtype);
481         READ_INT_FIELD(paramtypmod);
482         READ_OID_FIELD(paramcollid);
483         READ_LOCATION_FIELD(location);
484
485         READ_DONE();
486 }
487
488 /*
489  * _readAggref
490  */
491 static Aggref *
492 _readAggref(void)
493 {
494         READ_LOCALS(Aggref);
495
496         READ_OID_FIELD(aggfnoid);
497         READ_OID_FIELD(aggtype);
498         READ_OID_FIELD(aggcollid);
499         READ_OID_FIELD(inputcollid);
500         READ_NODE_FIELD(aggdirectargs);
501         READ_NODE_FIELD(args);
502         READ_NODE_FIELD(aggorder);
503         READ_NODE_FIELD(aggdistinct);
504         READ_NODE_FIELD(aggfilter);
505         READ_BOOL_FIELD(aggstar);
506         READ_BOOL_FIELD(aggvariadic);
507         READ_CHAR_FIELD(aggkind);
508         READ_UINT_FIELD(agglevelsup);
509         READ_LOCATION_FIELD(location);
510
511         READ_DONE();
512 }
513
514 /*
515  * _readWindowFunc
516  */
517 static WindowFunc *
518 _readWindowFunc(void)
519 {
520         READ_LOCALS(WindowFunc);
521
522         READ_OID_FIELD(winfnoid);
523         READ_OID_FIELD(wintype);
524         READ_OID_FIELD(wincollid);
525         READ_OID_FIELD(inputcollid);
526         READ_NODE_FIELD(args);
527         READ_NODE_FIELD(aggfilter);
528         READ_UINT_FIELD(winref);
529         READ_BOOL_FIELD(winstar);
530         READ_BOOL_FIELD(winagg);
531         READ_LOCATION_FIELD(location);
532
533         READ_DONE();
534 }
535
536 /*
537  * _readArrayRef
538  */
539 static ArrayRef *
540 _readArrayRef(void)
541 {
542         READ_LOCALS(ArrayRef);
543
544         READ_OID_FIELD(refarraytype);
545         READ_OID_FIELD(refelemtype);
546         READ_INT_FIELD(reftypmod);
547         READ_OID_FIELD(refcollid);
548         READ_NODE_FIELD(refupperindexpr);
549         READ_NODE_FIELD(reflowerindexpr);
550         READ_NODE_FIELD(refexpr);
551         READ_NODE_FIELD(refassgnexpr);
552
553         READ_DONE();
554 }
555
556 /*
557  * _readFuncExpr
558  */
559 static FuncExpr *
560 _readFuncExpr(void)
561 {
562         READ_LOCALS(FuncExpr);
563
564         READ_OID_FIELD(funcid);
565         READ_OID_FIELD(funcresulttype);
566         READ_BOOL_FIELD(funcretset);
567         READ_BOOL_FIELD(funcvariadic);
568         READ_ENUM_FIELD(funcformat, CoercionForm);
569         READ_OID_FIELD(funccollid);
570         READ_OID_FIELD(inputcollid);
571         READ_NODE_FIELD(args);
572         READ_LOCATION_FIELD(location);
573
574         READ_DONE();
575 }
576
577 /*
578  * _readNamedArgExpr
579  */
580 static NamedArgExpr *
581 _readNamedArgExpr(void)
582 {
583         READ_LOCALS(NamedArgExpr);
584
585         READ_NODE_FIELD(arg);
586         READ_STRING_FIELD(name);
587         READ_INT_FIELD(argnumber);
588         READ_LOCATION_FIELD(location);
589
590         READ_DONE();
591 }
592
593 /*
594  * _readOpExpr
595  */
596 static OpExpr *
597 _readOpExpr(void)
598 {
599         READ_LOCALS(OpExpr);
600
601         READ_OID_FIELD(opno);
602         READ_OID_FIELD(opfuncid);
603
604         /*
605          * The opfuncid is stored in the textual format primarily for debugging
606          * and documentation reasons.  We want to always read it as zero to force
607          * it to be re-looked-up in the pg_operator entry.  This ensures that
608          * stored rules don't have hidden dependencies on operators' functions.
609          * (We don't currently support an ALTER OPERATOR command, but might
610          * someday.)
611          */
612         local_node->opfuncid = InvalidOid;
613
614         READ_OID_FIELD(opresulttype);
615         READ_BOOL_FIELD(opretset);
616         READ_OID_FIELD(opcollid);
617         READ_OID_FIELD(inputcollid);
618         READ_NODE_FIELD(args);
619         READ_LOCATION_FIELD(location);
620
621         READ_DONE();
622 }
623
624 /*
625  * _readDistinctExpr
626  */
627 static DistinctExpr *
628 _readDistinctExpr(void)
629 {
630         READ_LOCALS(DistinctExpr);
631
632         READ_OID_FIELD(opno);
633         READ_OID_FIELD(opfuncid);
634
635         /*
636          * The opfuncid is stored in the textual format primarily for debugging
637          * and documentation reasons.  We want to always read it as zero to force
638          * it to be re-looked-up in the pg_operator entry.  This ensures that
639          * stored rules don't have hidden dependencies on operators' functions.
640          * (We don't currently support an ALTER OPERATOR command, but might
641          * someday.)
642          */
643         local_node->opfuncid = InvalidOid;
644
645         READ_OID_FIELD(opresulttype);
646         READ_BOOL_FIELD(opretset);
647         READ_OID_FIELD(opcollid);
648         READ_OID_FIELD(inputcollid);
649         READ_NODE_FIELD(args);
650         READ_LOCATION_FIELD(location);
651
652         READ_DONE();
653 }
654
655 /*
656  * _readNullIfExpr
657  */
658 static NullIfExpr *
659 _readNullIfExpr(void)
660 {
661         READ_LOCALS(NullIfExpr);
662
663         READ_OID_FIELD(opno);
664         READ_OID_FIELD(opfuncid);
665
666         /*
667          * The opfuncid is stored in the textual format primarily for debugging
668          * and documentation reasons.  We want to always read it as zero to force
669          * it to be re-looked-up in the pg_operator entry.  This ensures that
670          * stored rules don't have hidden dependencies on operators' functions.
671          * (We don't currently support an ALTER OPERATOR command, but might
672          * someday.)
673          */
674         local_node->opfuncid = InvalidOid;
675
676         READ_OID_FIELD(opresulttype);
677         READ_BOOL_FIELD(opretset);
678         READ_OID_FIELD(opcollid);
679         READ_OID_FIELD(inputcollid);
680         READ_NODE_FIELD(args);
681         READ_LOCATION_FIELD(location);
682
683         READ_DONE();
684 }
685
686 /*
687  * _readScalarArrayOpExpr
688  */
689 static ScalarArrayOpExpr *
690 _readScalarArrayOpExpr(void)
691 {
692         READ_LOCALS(ScalarArrayOpExpr);
693
694         READ_OID_FIELD(opno);
695         READ_OID_FIELD(opfuncid);
696
697         /*
698          * The opfuncid is stored in the textual format primarily for debugging
699          * and documentation reasons.  We want to always read it as zero to force
700          * it to be re-looked-up in the pg_operator entry.  This ensures that
701          * stored rules don't have hidden dependencies on operators' functions.
702          * (We don't currently support an ALTER OPERATOR command, but might
703          * someday.)
704          */
705         local_node->opfuncid = InvalidOid;
706
707         READ_BOOL_FIELD(useOr);
708         READ_OID_FIELD(inputcollid);
709         READ_NODE_FIELD(args);
710         READ_LOCATION_FIELD(location);
711
712         READ_DONE();
713 }
714
715 /*
716  * _readBoolExpr
717  */
718 static BoolExpr *
719 _readBoolExpr(void)
720 {
721         READ_LOCALS(BoolExpr);
722
723         /* do-it-yourself enum representation */
724         token = pg_strtok(&length); /* skip :boolop */
725         token = pg_strtok(&length); /* get field value */
726         if (strncmp(token, "and", 3) == 0)
727                 local_node->boolop = AND_EXPR;
728         else if (strncmp(token, "or", 2) == 0)
729                 local_node->boolop = OR_EXPR;
730         else if (strncmp(token, "not", 3) == 0)
731                 local_node->boolop = NOT_EXPR;
732         else
733                 elog(ERROR, "unrecognized boolop \"%.*s\"", length, token);
734
735         READ_NODE_FIELD(args);
736         READ_LOCATION_FIELD(location);
737
738         READ_DONE();
739 }
740
741 /*
742  * _readSubLink
743  */
744 static SubLink *
745 _readSubLink(void)
746 {
747         READ_LOCALS(SubLink);
748
749         READ_ENUM_FIELD(subLinkType, SubLinkType);
750         READ_INT_FIELD(subLinkId);
751         READ_NODE_FIELD(testexpr);
752         READ_NODE_FIELD(operName);
753         READ_NODE_FIELD(subselect);
754         READ_LOCATION_FIELD(location);
755
756         READ_DONE();
757 }
758
759 /*
760  * _readSubPlan is not needed since it doesn't appear in stored rules.
761  */
762
763 /*
764  * _readFieldSelect
765  */
766 static FieldSelect *
767 _readFieldSelect(void)
768 {
769         READ_LOCALS(FieldSelect);
770
771         READ_NODE_FIELD(arg);
772         READ_INT_FIELD(fieldnum);
773         READ_OID_FIELD(resulttype);
774         READ_INT_FIELD(resulttypmod);
775         READ_OID_FIELD(resultcollid);
776
777         READ_DONE();
778 }
779
780 /*
781  * _readFieldStore
782  */
783 static FieldStore *
784 _readFieldStore(void)
785 {
786         READ_LOCALS(FieldStore);
787
788         READ_NODE_FIELD(arg);
789         READ_NODE_FIELD(newvals);
790         READ_NODE_FIELD(fieldnums);
791         READ_OID_FIELD(resulttype);
792
793         READ_DONE();
794 }
795
796 /*
797  * _readRelabelType
798  */
799 static RelabelType *
800 _readRelabelType(void)
801 {
802         READ_LOCALS(RelabelType);
803
804         READ_NODE_FIELD(arg);
805         READ_OID_FIELD(resulttype);
806         READ_INT_FIELD(resulttypmod);
807         READ_OID_FIELD(resultcollid);
808         READ_ENUM_FIELD(relabelformat, CoercionForm);
809         READ_LOCATION_FIELD(location);
810
811         READ_DONE();
812 }
813
814 /*
815  * _readCoerceViaIO
816  */
817 static CoerceViaIO *
818 _readCoerceViaIO(void)
819 {
820         READ_LOCALS(CoerceViaIO);
821
822         READ_NODE_FIELD(arg);
823         READ_OID_FIELD(resulttype);
824         READ_OID_FIELD(resultcollid);
825         READ_ENUM_FIELD(coerceformat, CoercionForm);
826         READ_LOCATION_FIELD(location);
827
828         READ_DONE();
829 }
830
831 /*
832  * _readArrayCoerceExpr
833  */
834 static ArrayCoerceExpr *
835 _readArrayCoerceExpr(void)
836 {
837         READ_LOCALS(ArrayCoerceExpr);
838
839         READ_NODE_FIELD(arg);
840         READ_OID_FIELD(elemfuncid);
841         READ_OID_FIELD(resulttype);
842         READ_INT_FIELD(resulttypmod);
843         READ_OID_FIELD(resultcollid);
844         READ_BOOL_FIELD(isExplicit);
845         READ_ENUM_FIELD(coerceformat, CoercionForm);
846         READ_LOCATION_FIELD(location);
847
848         READ_DONE();
849 }
850
851 /*
852  * _readConvertRowtypeExpr
853  */
854 static ConvertRowtypeExpr *
855 _readConvertRowtypeExpr(void)
856 {
857         READ_LOCALS(ConvertRowtypeExpr);
858
859         READ_NODE_FIELD(arg);
860         READ_OID_FIELD(resulttype);
861         READ_ENUM_FIELD(convertformat, CoercionForm);
862         READ_LOCATION_FIELD(location);
863
864         READ_DONE();
865 }
866
867 /*
868  * _readCollateExpr
869  */
870 static CollateExpr *
871 _readCollateExpr(void)
872 {
873         READ_LOCALS(CollateExpr);
874
875         READ_NODE_FIELD(arg);
876         READ_OID_FIELD(collOid);
877         READ_LOCATION_FIELD(location);
878
879         READ_DONE();
880 }
881
882 /*
883  * _readCaseExpr
884  */
885 static CaseExpr *
886 _readCaseExpr(void)
887 {
888         READ_LOCALS(CaseExpr);
889
890         READ_OID_FIELD(casetype);
891         READ_OID_FIELD(casecollid);
892         READ_NODE_FIELD(arg);
893         READ_NODE_FIELD(args);
894         READ_NODE_FIELD(defresult);
895         READ_LOCATION_FIELD(location);
896
897         READ_DONE();
898 }
899
900 /*
901  * _readCaseWhen
902  */
903 static CaseWhen *
904 _readCaseWhen(void)
905 {
906         READ_LOCALS(CaseWhen);
907
908         READ_NODE_FIELD(expr);
909         READ_NODE_FIELD(result);
910         READ_LOCATION_FIELD(location);
911
912         READ_DONE();
913 }
914
915 /*
916  * _readCaseTestExpr
917  */
918 static CaseTestExpr *
919 _readCaseTestExpr(void)
920 {
921         READ_LOCALS(CaseTestExpr);
922
923         READ_OID_FIELD(typeId);
924         READ_INT_FIELD(typeMod);
925         READ_OID_FIELD(collation);
926
927         READ_DONE();
928 }
929
930 /*
931  * _readArrayExpr
932  */
933 static ArrayExpr *
934 _readArrayExpr(void)
935 {
936         READ_LOCALS(ArrayExpr);
937
938         READ_OID_FIELD(array_typeid);
939         READ_OID_FIELD(array_collid);
940         READ_OID_FIELD(element_typeid);
941         READ_NODE_FIELD(elements);
942         READ_BOOL_FIELD(multidims);
943         READ_LOCATION_FIELD(location);
944
945         READ_DONE();
946 }
947
948 /*
949  * _readRowExpr
950  */
951 static RowExpr *
952 _readRowExpr(void)
953 {
954         READ_LOCALS(RowExpr);
955
956         READ_NODE_FIELD(args);
957         READ_OID_FIELD(row_typeid);
958         READ_ENUM_FIELD(row_format, CoercionForm);
959         READ_NODE_FIELD(colnames);
960         READ_LOCATION_FIELD(location);
961
962         READ_DONE();
963 }
964
965 /*
966  * _readRowCompareExpr
967  */
968 static RowCompareExpr *
969 _readRowCompareExpr(void)
970 {
971         READ_LOCALS(RowCompareExpr);
972
973         READ_ENUM_FIELD(rctype, RowCompareType);
974         READ_NODE_FIELD(opnos);
975         READ_NODE_FIELD(opfamilies);
976         READ_NODE_FIELD(inputcollids);
977         READ_NODE_FIELD(largs);
978         READ_NODE_FIELD(rargs);
979
980         READ_DONE();
981 }
982
983 /*
984  * _readCoalesceExpr
985  */
986 static CoalesceExpr *
987 _readCoalesceExpr(void)
988 {
989         READ_LOCALS(CoalesceExpr);
990
991         READ_OID_FIELD(coalescetype);
992         READ_OID_FIELD(coalescecollid);
993         READ_NODE_FIELD(args);
994         READ_LOCATION_FIELD(location);
995
996         READ_DONE();
997 }
998
999 /*
1000  * _readMinMaxExpr
1001  */
1002 static MinMaxExpr *
1003 _readMinMaxExpr(void)
1004 {
1005         READ_LOCALS(MinMaxExpr);
1006
1007         READ_OID_FIELD(minmaxtype);
1008         READ_OID_FIELD(minmaxcollid);
1009         READ_OID_FIELD(inputcollid);
1010         READ_ENUM_FIELD(op, MinMaxOp);
1011         READ_NODE_FIELD(args);
1012         READ_LOCATION_FIELD(location);
1013
1014         READ_DONE();
1015 }
1016
1017 /*
1018  * _readXmlExpr
1019  */
1020 static XmlExpr *
1021 _readXmlExpr(void)
1022 {
1023         READ_LOCALS(XmlExpr);
1024
1025         READ_ENUM_FIELD(op, XmlExprOp);
1026         READ_STRING_FIELD(name);
1027         READ_NODE_FIELD(named_args);
1028         READ_NODE_FIELD(arg_names);
1029         READ_NODE_FIELD(args);
1030         READ_ENUM_FIELD(xmloption, XmlOptionType);
1031         READ_OID_FIELD(type);
1032         READ_INT_FIELD(typmod);
1033         READ_LOCATION_FIELD(location);
1034
1035         READ_DONE();
1036 }
1037
1038 /*
1039  * _readNullTest
1040  */
1041 static NullTest *
1042 _readNullTest(void)
1043 {
1044         READ_LOCALS(NullTest);
1045
1046         READ_NODE_FIELD(arg);
1047         READ_ENUM_FIELD(nulltesttype, NullTestType);
1048         READ_BOOL_FIELD(argisrow);
1049         READ_LOCATION_FIELD(location);
1050
1051         READ_DONE();
1052 }
1053
1054 /*
1055  * _readBooleanTest
1056  */
1057 static BooleanTest *
1058 _readBooleanTest(void)
1059 {
1060         READ_LOCALS(BooleanTest);
1061
1062         READ_NODE_FIELD(arg);
1063         READ_ENUM_FIELD(booltesttype, BoolTestType);
1064         READ_LOCATION_FIELD(location);
1065
1066         READ_DONE();
1067 }
1068
1069 /*
1070  * _readCoerceToDomain
1071  */
1072 static CoerceToDomain *
1073 _readCoerceToDomain(void)
1074 {
1075         READ_LOCALS(CoerceToDomain);
1076
1077         READ_NODE_FIELD(arg);
1078         READ_OID_FIELD(resulttype);
1079         READ_INT_FIELD(resulttypmod);
1080         READ_OID_FIELD(resultcollid);
1081         READ_ENUM_FIELD(coercionformat, CoercionForm);
1082         READ_LOCATION_FIELD(location);
1083
1084         READ_DONE();
1085 }
1086
1087 /*
1088  * _readCoerceToDomainValue
1089  */
1090 static CoerceToDomainValue *
1091 _readCoerceToDomainValue(void)
1092 {
1093         READ_LOCALS(CoerceToDomainValue);
1094
1095         READ_OID_FIELD(typeId);
1096         READ_INT_FIELD(typeMod);
1097         READ_OID_FIELD(collation);
1098         READ_LOCATION_FIELD(location);
1099
1100         READ_DONE();
1101 }
1102
1103 /*
1104  * _readSetToDefault
1105  */
1106 static SetToDefault *
1107 _readSetToDefault(void)
1108 {
1109         READ_LOCALS(SetToDefault);
1110
1111         READ_OID_FIELD(typeId);
1112         READ_INT_FIELD(typeMod);
1113         READ_OID_FIELD(collation);
1114         READ_LOCATION_FIELD(location);
1115
1116         READ_DONE();
1117 }
1118
1119 /*
1120  * _readCurrentOfExpr
1121  */
1122 static CurrentOfExpr *
1123 _readCurrentOfExpr(void)
1124 {
1125         READ_LOCALS(CurrentOfExpr);
1126
1127         READ_UINT_FIELD(cvarno);
1128         READ_STRING_FIELD(cursor_name);
1129         READ_INT_FIELD(cursor_param);
1130
1131         READ_DONE();
1132 }
1133
1134 /*
1135  * _readInferenceElem
1136  */
1137 static InferenceElem *
1138 _readInferenceElem(void)
1139 {
1140         READ_LOCALS(InferenceElem);
1141
1142         READ_NODE_FIELD(expr);
1143         READ_OID_FIELD(infercollid);
1144         READ_OID_FIELD(inferopfamily);
1145         READ_OID_FIELD(inferopcinputtype);
1146
1147         READ_DONE();
1148 }
1149
1150 /*
1151  * _readTargetEntry
1152  */
1153 static TargetEntry *
1154 _readTargetEntry(void)
1155 {
1156         READ_LOCALS(TargetEntry);
1157
1158         READ_NODE_FIELD(expr);
1159         READ_INT_FIELD(resno);
1160         READ_STRING_FIELD(resname);
1161         READ_UINT_FIELD(ressortgroupref);
1162         READ_OID_FIELD(resorigtbl);
1163         READ_INT_FIELD(resorigcol);
1164         READ_BOOL_FIELD(resjunk);
1165
1166         READ_DONE();
1167 }
1168
1169 /*
1170  * _readRangeTblRef
1171  */
1172 static RangeTblRef *
1173 _readRangeTblRef(void)
1174 {
1175         READ_LOCALS(RangeTblRef);
1176
1177         READ_INT_FIELD(rtindex);
1178
1179         READ_DONE();
1180 }
1181
1182 /*
1183  * _readJoinExpr
1184  */
1185 static JoinExpr *
1186 _readJoinExpr(void)
1187 {
1188         READ_LOCALS(JoinExpr);
1189
1190         READ_ENUM_FIELD(jointype, JoinType);
1191         READ_BOOL_FIELD(isNatural);
1192         READ_NODE_FIELD(larg);
1193         READ_NODE_FIELD(rarg);
1194         READ_NODE_FIELD(usingClause);
1195         READ_NODE_FIELD(quals);
1196         READ_NODE_FIELD(alias);
1197         READ_INT_FIELD(rtindex);
1198
1199         READ_DONE();
1200 }
1201
1202 /*
1203  * _readFromExpr
1204  */
1205 static FromExpr *
1206 _readFromExpr(void)
1207 {
1208         READ_LOCALS(FromExpr);
1209
1210         READ_NODE_FIELD(fromlist);
1211         READ_NODE_FIELD(quals);
1212
1213         READ_DONE();
1214 }
1215
1216 /*
1217  * _readOnConflictExpr
1218  */
1219 static OnConflictExpr *
1220 _readOnConflictExpr(void)
1221 {
1222         READ_LOCALS(OnConflictExpr);
1223
1224         READ_ENUM_FIELD(action, OnConflictAction);
1225         READ_NODE_FIELD(arbiterElems);
1226         READ_NODE_FIELD(arbiterWhere);
1227         READ_NODE_FIELD(onConflictSet);
1228         READ_NODE_FIELD(onConflictWhere);
1229         READ_OID_FIELD(constraint);
1230         READ_INT_FIELD(exclRelIndex);
1231         READ_NODE_FIELD(exclRelTlist);
1232
1233         READ_DONE();
1234 }
1235
1236 /*
1237  *      Stuff from parsenodes.h.
1238  */
1239
1240 /*
1241  * _readRangeTblEntry
1242  */
1243 static RangeTblEntry *
1244 _readRangeTblEntry(void)
1245 {
1246         READ_LOCALS(RangeTblEntry);
1247
1248         /* put alias + eref first to make dump more legible */
1249         READ_NODE_FIELD(alias);
1250         READ_NODE_FIELD(eref);
1251         READ_ENUM_FIELD(rtekind, RTEKind);
1252
1253         switch (local_node->rtekind)
1254         {
1255                 case RTE_RELATION:
1256                         READ_OID_FIELD(relid);
1257                         READ_CHAR_FIELD(relkind);
1258                         break;
1259                 case RTE_SUBQUERY:
1260                         READ_NODE_FIELD(subquery);
1261                         READ_BOOL_FIELD(security_barrier);
1262                         break;
1263                 case RTE_JOIN:
1264                         READ_ENUM_FIELD(jointype, JoinType);
1265                         READ_NODE_FIELD(joinaliasvars);
1266                         break;
1267                 case RTE_FUNCTION:
1268                         READ_NODE_FIELD(functions);
1269                         READ_BOOL_FIELD(funcordinality);
1270                         break;
1271                 case RTE_VALUES:
1272                         READ_NODE_FIELD(values_lists);
1273                         READ_NODE_FIELD(values_collations);
1274                         break;
1275                 case RTE_CTE:
1276                         READ_STRING_FIELD(ctename);
1277                         READ_UINT_FIELD(ctelevelsup);
1278                         READ_BOOL_FIELD(self_reference);
1279                         READ_NODE_FIELD(ctecoltypes);
1280                         READ_NODE_FIELD(ctecoltypmods);
1281                         READ_NODE_FIELD(ctecolcollations);
1282                         break;
1283                 default:
1284                         elog(ERROR, "unrecognized RTE kind: %d",
1285                                  (int) local_node->rtekind);
1286                         break;
1287         }
1288
1289         READ_BOOL_FIELD(lateral);
1290         READ_BOOL_FIELD(inh);
1291         READ_BOOL_FIELD(inFromCl);
1292         READ_UINT_FIELD(requiredPerms);
1293         READ_OID_FIELD(checkAsUser);
1294         READ_BITMAPSET_FIELD(selectedCols);
1295         READ_BITMAPSET_FIELD(insertedCols);
1296         READ_BITMAPSET_FIELD(updatedCols);
1297         READ_NODE_FIELD(securityQuals);
1298
1299         READ_DONE();
1300 }
1301
1302 /*
1303  * _readRangeTblFunction
1304  */
1305 static RangeTblFunction *
1306 _readRangeTblFunction(void)
1307 {
1308         READ_LOCALS(RangeTblFunction);
1309
1310         READ_NODE_FIELD(funcexpr);
1311         READ_INT_FIELD(funccolcount);
1312         READ_NODE_FIELD(funccolnames);
1313         READ_NODE_FIELD(funccoltypes);
1314         READ_NODE_FIELD(funccoltypmods);
1315         READ_NODE_FIELD(funccolcollations);
1316         READ_BITMAPSET_FIELD(funcparams);
1317
1318         READ_DONE();
1319 }
1320
1321
1322 /*
1323  * parseNodeString
1324  *
1325  * Given a character string representing a node tree, parseNodeString creates
1326  * the internal node structure.
1327  *
1328  * The string to be read must already have been loaded into pg_strtok().
1329  */
1330 Node *
1331 parseNodeString(void)
1332 {
1333         void       *return_value;
1334
1335         READ_TEMP_LOCALS();
1336
1337         token = pg_strtok(&length);
1338
1339 #define MATCH(tokname, namelen) \
1340         (length == namelen && memcmp(token, tokname, namelen) == 0)
1341
1342         if (MATCH("QUERY", 5))
1343                 return_value = _readQuery();
1344         else if (MATCH("WITHCHECKOPTION", 15))
1345                 return_value = _readWithCheckOption();
1346         else if (MATCH("SORTGROUPCLAUSE", 15))
1347                 return_value = _readSortGroupClause();
1348         else if (MATCH("WINDOWCLAUSE", 12))
1349                 return_value = _readWindowClause();
1350         else if (MATCH("ROWMARKCLAUSE", 13))
1351                 return_value = _readRowMarkClause();
1352         else if (MATCH("COMMONTABLEEXPR", 15))
1353                 return_value = _readCommonTableExpr();
1354         else if (MATCH("SETOPERATIONSTMT", 16))
1355                 return_value = _readSetOperationStmt();
1356         else if (MATCH("ALIAS", 5))
1357                 return_value = _readAlias();
1358         else if (MATCH("RANGEVAR", 8))
1359                 return_value = _readRangeVar();
1360         else if (MATCH("INTOCLAUSE", 10))
1361                 return_value = _readIntoClause();
1362         else if (MATCH("VAR", 3))
1363                 return_value = _readVar();
1364         else if (MATCH("CONST", 5))
1365                 return_value = _readConst();
1366         else if (MATCH("PARAM", 5))
1367                 return_value = _readParam();
1368         else if (MATCH("AGGREF", 6))
1369                 return_value = _readAggref();
1370         else if (MATCH("WINDOWFUNC", 10))
1371                 return_value = _readWindowFunc();
1372         else if (MATCH("ARRAYREF", 8))
1373                 return_value = _readArrayRef();
1374         else if (MATCH("FUNCEXPR", 8))
1375                 return_value = _readFuncExpr();
1376         else if (MATCH("NAMEDARGEXPR", 12))
1377                 return_value = _readNamedArgExpr();
1378         else if (MATCH("OPEXPR", 6))
1379                 return_value = _readOpExpr();
1380         else if (MATCH("DISTINCTEXPR", 12))
1381                 return_value = _readDistinctExpr();
1382         else if (MATCH("NULLIFEXPR", 10))
1383                 return_value = _readNullIfExpr();
1384         else if (MATCH("SCALARARRAYOPEXPR", 17))
1385                 return_value = _readScalarArrayOpExpr();
1386         else if (MATCH("BOOLEXPR", 8))
1387                 return_value = _readBoolExpr();
1388         else if (MATCH("SUBLINK", 7))
1389                 return_value = _readSubLink();
1390         else if (MATCH("FIELDSELECT", 11))
1391                 return_value = _readFieldSelect();
1392         else if (MATCH("FIELDSTORE", 10))
1393                 return_value = _readFieldStore();
1394         else if (MATCH("RELABELTYPE", 11))
1395                 return_value = _readRelabelType();
1396         else if (MATCH("COERCEVIAIO", 11))
1397                 return_value = _readCoerceViaIO();
1398         else if (MATCH("ARRAYCOERCEEXPR", 15))
1399                 return_value = _readArrayCoerceExpr();
1400         else if (MATCH("CONVERTROWTYPEEXPR", 18))
1401                 return_value = _readConvertRowtypeExpr();
1402         else if (MATCH("COLLATE", 7))
1403                 return_value = _readCollateExpr();
1404         else if (MATCH("CASE", 4))
1405                 return_value = _readCaseExpr();
1406         else if (MATCH("WHEN", 4))
1407                 return_value = _readCaseWhen();
1408         else if (MATCH("CASETESTEXPR", 12))
1409                 return_value = _readCaseTestExpr();
1410         else if (MATCH("ARRAY", 5))
1411                 return_value = _readArrayExpr();
1412         else if (MATCH("ROW", 3))
1413                 return_value = _readRowExpr();
1414         else if (MATCH("ROWCOMPARE", 10))
1415                 return_value = _readRowCompareExpr();
1416         else if (MATCH("COALESCE", 8))
1417                 return_value = _readCoalesceExpr();
1418         else if (MATCH("MINMAX", 6))
1419                 return_value = _readMinMaxExpr();
1420         else if (MATCH("XMLEXPR", 7))
1421                 return_value = _readXmlExpr();
1422         else if (MATCH("NULLTEST", 8))
1423                 return_value = _readNullTest();
1424         else if (MATCH("BOOLEANTEST", 11))
1425                 return_value = _readBooleanTest();
1426         else if (MATCH("COERCETODOMAIN", 14))
1427                 return_value = _readCoerceToDomain();
1428         else if (MATCH("COERCETODOMAINVALUE", 19))
1429                 return_value = _readCoerceToDomainValue();
1430         else if (MATCH("SETTODEFAULT", 12))
1431                 return_value = _readSetToDefault();
1432         else if (MATCH("CURRENTOFEXPR", 13))
1433                 return_value = _readCurrentOfExpr();
1434         else if (MATCH("INFERENCEELEM", 13))
1435                 return_value = _readInferenceElem();
1436         else if (MATCH("TARGETENTRY", 11))
1437                 return_value = _readTargetEntry();
1438         else if (MATCH("RANGETBLREF", 11))
1439                 return_value = _readRangeTblRef();
1440         else if (MATCH("JOINEXPR", 8))
1441                 return_value = _readJoinExpr();
1442         else if (MATCH("FROMEXPR", 8))
1443                 return_value = _readFromExpr();
1444         else if (MATCH("ONCONFLICTEXPR", 14))
1445                 return_value = _readOnConflictExpr();
1446         else if (MATCH("RTE", 3))
1447                 return_value = _readRangeTblEntry();
1448         else if (MATCH("RANGETBLFUNCTION", 16))
1449                 return_value = _readRangeTblFunction();
1450         else if (MATCH("NOTIFY", 6))
1451                 return_value = _readNotifyStmt();
1452         else if (MATCH("DECLARECURSOR", 13))
1453                 return_value = _readDeclareCursorStmt();
1454         else
1455         {
1456                 elog(ERROR, "badly formatted node string \"%.32s\"...", token);
1457                 return_value = NULL;    /* keep compiler quiet */
1458         }
1459
1460         return (Node *) return_value;
1461 }
1462
1463
1464 /*
1465  * readDatum
1466  *
1467  * Given a string representation of a constant, recreate the appropriate
1468  * Datum.  The string representation embeds length info, but not byValue,
1469  * so we must be told that.
1470  */
1471 static Datum
1472 readDatum(bool typbyval)
1473 {
1474         Size            length,
1475                                 i;
1476         int                     tokenLength;
1477         char       *token;
1478         Datum           res;
1479         char       *s;
1480
1481         /*
1482          * read the actual length of the value
1483          */
1484         token = pg_strtok(&tokenLength);
1485         length = atoui(token);
1486
1487         token = pg_strtok(&tokenLength);        /* read the '[' */
1488         if (token == NULL || token[0] != '[')
1489                 elog(ERROR, "expected \"[\" to start datum, but got \"%s\"; length = %zu",
1490                          token ? (const char *) token : "[NULL]", length);
1491
1492         if (typbyval)
1493         {
1494                 if (length > (Size) sizeof(Datum))
1495                         elog(ERROR, "byval datum but length = %zu", length);
1496                 res = (Datum) 0;
1497                 s = (char *) (&res);
1498                 for (i = 0; i < (Size) sizeof(Datum); i++)
1499                 {
1500                         token = pg_strtok(&tokenLength);
1501                         s[i] = (char) atoi(token);
1502                 }
1503         }
1504         else if (length <= 0)
1505                 res = (Datum) NULL;
1506         else
1507         {
1508                 s = (char *) palloc(length);
1509                 for (i = 0; i < length; i++)
1510                 {
1511                         token = pg_strtok(&tokenLength);
1512                         s[i] = (char) atoi(token);
1513                 }
1514                 res = PointerGetDatum(s);
1515         }
1516
1517         token = pg_strtok(&tokenLength);        /* read the ']' */
1518         if (token == NULL || token[0] != ']')
1519                 elog(ERROR, "expected \"]\" to end datum, but got \"%s\"; length = %zu",
1520                          token ? (const char *) token : "[NULL]", length);
1521
1522         return res;
1523 }