PostgreSQL Source Code: src/backend/access/common/reloptions.c Source File (original) (raw)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
17
19
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
95{
96 {
97 {
98 "autosummarize",
99 "Enables automatic summarization on this BRIN index",
102 },
103 false
104 },
105 {
106 {
107 "autovacuum_enabled",
108 "Enables autovacuum in this relation",
111 },
112 true
113 },
114 {
115 {
116 "user_catalog_table",
117 "Declare a table as an additional catalog table, e.g. for the purpose of logical replication",
120 },
121 false
122 },
123 {
124 {
125 "fastupdate",
126 "Enables \"fast update\" feature for this GIN index",
129 },
130 true
131 },
132 {
133 {
134 "security_barrier",
135 "View acts as a row security barrier",
138 },
139 false
140 },
141 {
142 {
143 "security_invoker",
144 "Privileges on underlying relations are checked as the invoking user, not the view owner",
147 },
148 false
149 },
150 {
151 {
152 "vacuum_truncate",
153 "Enables vacuum to truncate empty pages at the end of this table",
156 },
157 true
158 },
159 {
160 {
161 "deduplicate_items",
162 "Enables \"deduplicate items\" feature for this btree index",
165
166 },
167 true
168 },
169
170 {{NULL}}
171};
172
174{
175 {
176 {
177 "fillfactor",
178 "Packs table pages only to this percentage",
181
182 },
184 },
185 {
186 {
187 "fillfactor",
188 "Packs btree index pages only to this percentage",
191
192 },
194 },
195 {
196 {
197 "fillfactor",
198 "Packs hash index pages only to this percentage",
201
202 },
204 },
205 {
206 {
207 "fillfactor",
208 "Packs gist index pages only to this percentage",
211
212 },
214 },
215 {
216 {
217 "fillfactor",
218 "Packs spgist index pages only to this percentage",
221
222 },
224 },
225 {
226 {
227 "autovacuum_vacuum_threshold",
228 "Minimum number of tuple updates or deletes prior to vacuum",
231 },
232 -1, 0, INT_MAX
233 },
234 {
235 {
236 "autovacuum_vacuum_max_threshold",
237 "Maximum number of tuple updates or deletes prior to vacuum",
240 },
241 -2, -1, INT_MAX
242 },
243 {
244 {
245 "autovacuum_vacuum_insert_threshold",
246 "Minimum number of tuple inserts prior to vacuum, or -1 to disable insert vacuums",
249 },
250 -2, -1, INT_MAX
251 },
252 {
253 {
254 "autovacuum_analyze_threshold",
255 "Minimum number of tuple inserts, updates or deletes prior to analyze",
258 },
259 -1, 0, INT_MAX
260 },
261 {
262 {
263 "autovacuum_vacuum_cost_limit",
264 "Vacuum cost amount available before napping, for autovacuum",
267 },
268 -1, 1, 10000
269 },
270 {
271 {
272 "autovacuum_freeze_min_age",
273 "Minimum age at which VACUUM should freeze a table row, for autovacuum",
276 },
277 -1, 0, 1000000000
278 },
279 {
280 {
281 "autovacuum_multixact_freeze_min_age",
282 "Minimum multixact age at which VACUUM should freeze a row multixact's, for autovacuum",
285 },
286 -1, 0, 1000000000
287 },
288 {
289 {
290 "autovacuum_freeze_max_age",
291 "Age at which to autovacuum a table to prevent transaction ID wraparound",
294 },
295 -1, 100000, 2000000000
296 },
297 {
298 {
299 "autovacuum_multixact_freeze_max_age",
300 "Multixact age at which to autovacuum a table to prevent multixact wraparound",
303 },
304 -1, 10000, 2000000000
305 },
306 {
307 {
308 "autovacuum_freeze_table_age",
309 "Age at which VACUUM should perform a full table sweep to freeze row versions",
312 }, -1, 0, 2000000000
313 },
314 {
315 {
316 "autovacuum_multixact_freeze_table_age",
317 "Age of multixact at which VACUUM should perform a full table sweep to freeze row versions",
320 }, -1, 0, 2000000000
321 },
322 {
323 {
324 "log_autovacuum_min_duration",
325 "Sets the minimum execution time above which vacuum actions by autovacuum will be logged",
328 },
329 -1, -1, INT_MAX
330 },
331 {
332 {
333 "log_autoanalyze_min_duration",
334 "Sets the minimum execution time above which analyze actions by autovacuum will be logged",
337 },
338 -1, -1, INT_MAX
339 },
340 {
341 {
342 "toast_tuple_target",
343 "Sets the target tuple length at which external columns will be toasted",
346 },
348 },
349 {
350 {
351 "pages_per_range",
352 "Number of pages that each page range covers in a BRIN index",
355 }, 128, 1, 131072
356 },
357 {
358 {
359 "gin_pending_list_limit",
360 "Maximum size of the pending list for this GIN index, in kilobytes.",
363 },
365 },
366 {
367 {
368 "effective_io_concurrency",
369 "Number of simultaneous requests that can be handled efficiently by the disk subsystem.",
372 },
374 },
375 {
376 {
377 "maintenance_io_concurrency",
378 "Number of simultaneous requests that can be handled efficiently by the disk subsystem for maintenance work.",
381 },
383 },
384 {
385 {
386 "parallel_workers",
387 "Number of parallel processes that can be used per executor node for this relation.",
390 },
391 -1, 0, 1024
392 },
393
394
395 {{NULL}}
396};
397
399{
400 {
401 {
402 "autovacuum_vacuum_cost_delay",
403 "Vacuum cost delay in milliseconds, for autovacuum",
406 },
407 -1, 0.0, 100.0
408 },
409 {
410 {
411 "autovacuum_vacuum_scale_factor",
412 "Number of tuple updates or deletes prior to vacuum as a fraction of reltuples",
415 },
416 -1, 0.0, 100.0
417 },
418 {
419 {
420 "autovacuum_vacuum_insert_scale_factor",
421 "Number of tuple inserts prior to vacuum as a fraction of reltuples",
424 },
425 -1, 0.0, 100.0
426 },
427 {
428 {
429 "autovacuum_analyze_scale_factor",
430 "Number of tuple inserts, updates or deletes prior to analyze as a fraction of reltuples",
433 },
434 -1, 0.0, 100.0
435 },
436 {
437 {
438 "vacuum_max_eager_freeze_failure_rate",
439 "Fraction of pages in a relation vacuum can scan and fail to freeze before disabling eager scanning.",
442 },
443 -1, 0.0, 1.0
444 },
445
446 {
447 {
448 "seq_page_cost",
449 "Sets the planner's estimate of the cost of a sequentially fetched disk page.",
452 },
453 -1, 0.0, DBL_MAX
454 },
455 {
456 {
457 "random_page_cost",
458 "Sets the planner's estimate of the cost of a nonsequentially fetched disk page.",
461 },
462 -1, 0.0, DBL_MAX
463 },
464 {
465 {
466 "n_distinct",
467 "Sets the planner's estimate of the number of distinct values appearing in a column (excluding child relations).",
470 },
471 0, -1.0, DBL_MAX
472 },
473 {
474 {
475 "n_distinct_inherited",
476 "Sets the planner's estimate of the number of distinct values appearing in a column (including child relations).",
479 },
480 0, -1.0, DBL_MAX
481 },
482 {
483 {
484 "vacuum_cleanup_index_scale_factor",
485 "Deprecated B-Tree parameter.",
488 },
489 -1, 0.0, 1e10
490 },
491
492 {{NULL}}
493};
494
495
497{
507 {(const char *) NULL}
508};
509
510
512{
516 {(const char *) NULL}
517};
518
519
521{
522
525 {(const char *) NULL}
526};
527
529{
530 {
531 {
532 "vacuum_index_cleanup",
533 "Controls index vacuuming and index cleanup",
536 },
539 gettext_noop("Valid values are \"on\", \"off\", and \"auto\".")
540 },
541 {
542 {
543 "buffering",
544 "Enables buffering build for this GiST index",
547 },
550 gettext_noop("Valid values are \"on\", \"off\", and \"auto\".")
551 },
552 {
553 {
554 "check_option",
555 "View has WITH CHECK OPTION defined (local or cascaded).",
558 },
561 gettext_noop("Valid values are \"local\" and \"cascaded\".")
562 },
563
564 {{NULL}}
565};
566
568{
569
570 {{NULL}}
571};
572
575
579
582 int text_len, bool validate);
583
584
585
586
587
588
589#define GET_STRING_RELOPTION_LEN(option) \
590 ((option).isset ? strlen((option).values.string_val) : \
591 ((relopt_string *) (option).gen)->default_len)
592
593
594
595
596
597
598
599static void
601{
602 int i;
603 int j;
604
605 j = 0;
607 {
610 j++;
611 }
613 {
616 j++;
617 }
619 {
622 j++;
623 }
625 {
628 j++;
629 }
631 {
634 j++;
635 }
637
642
643 j = 0;
645 {
649 j++;
650 }
651
653 {
657 j++;
658 }
659
661 {
665 j++;
666 }
667
669 {
673 j++;
674 }
675
677 {
681 j++;
682 }
683
685 {
687 j++;
688 }
689
690
692
693
695}
696
697
698
699
700
701
704{
705
708 (errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
709 errmsg("user-defined relation parameter types limit exceeded")));
712}
713
714
715
716
717
718
719static void
721{
722 static int max_custom_options = 0;
723
725 {
727
729
730 if (max_custom_options == 0)
731 {
732 max_custom_options = 8;
734 }
735 else
736 {
737 max_custom_options *= 2;
739 max_custom_options * sizeof(relopt_gen *));
740 }
742 }
744
746}
747
748
749
750
751
752
753void
755{
759}
760
761
762
763
764
765
766void
768{
770}
771
772
773
774
775
776static void
778{
780
781 Assert(offset < relopts->relopt_struct_size);
782
783 opt->option = newoption;
784 opt->offset = offset;
785
787}
788
789
790
791
792
793
797{
799 size_t size;
801
804 else
805 oldcxt = NULL;
806
807 switch (type)
808 {
811 break;
814 break;
817 break;
820 break;
823 break;
824 default:
825 elog(ERROR, "unsupported reloption type %d", type);
826 return NULL;
827 }
828
829 newoption = palloc(size);
830
832 if (desc)
834 else
835 newoption->desc = NULL;
836 newoption->kinds = kinds;
839 newoption->lockmode = lockmode;
840
841 if (oldcxt != NULL)
843
844 return newoption;
845}
846
847
848
849
850
853 bool default_val, LOCKMODE lockmode)
854{
856
858 name, desc, lockmode);
860
861 return newoption;
862}
863
864
865
866
867
868void
870 bool default_val, LOCKMODE lockmode)
871{
873 default_val, lockmode);
874
876}
877
878
879
880
881
882
883
884void
886 const char *desc, bool default_val, int offset)
887{
890 default_val, 0);
891
893}
894
895
896
897
898
899
902 int default_val, int min_val, int max_val,
904{
906
908 name, desc, lockmode);
910 newoption->min = min_val;
912
913 return newoption;
914}
915
916
917
918
919
920void
923{
925 default_val, min_val,
927
929}
930
931
932
933
934
935
936
937void
939 const char *desc, int default_val, int min_val,
941{
943 name, desc, default_val,
945
947}
948
949
950
951
952
955 double default_val, double min_val, double max_val,
957{
959
961 name, desc, lockmode);
963 newoption->min = min_val;
965
966 return newoption;
967}
968
969
970
971
972
973void
975 double default_val, double min_val, double max_val,
977{
979 default_val, min_val,
981
983}
984
985
986
987
988
989
990
991void
993 const char *desc, double default_val,
994 double min_val, double max_val, int offset)
995{
998 default_val, min_val,
1000
1002}
1003
1004
1005
1006
1007
1011 const char *detailmsg, LOCKMODE lockmode)
1012{
1014
1016 name, desc, lockmode);
1017 newoption->members = members;
1019 newoption->detailmsg = detailmsg;
1020
1021 return newoption;
1022}
1023
1024
1025
1026
1027
1028
1029
1030
1031
1032
1033
1034
1035
1036
1037void
1040 const char *detailmsg, LOCKMODE lockmode)
1041{
1043 members, default_val,
1044 detailmsg, lockmode);
1045
1047}
1048
1049
1050
1051
1052
1053
1054
1055void
1058 int default_val, const char *detailmsg, int offset)
1059{
1062 members, default_val,
1063 detailmsg, 0);
1064
1066}
1067
1068
1069
1070
1071
1074 const char *default_val,
1078{
1080
1081
1082 if (validator)
1083 (validator) (default_val);
1084
1086 name, desc, lockmode);
1088 newoption->fill_cb = filler;
1089 if (default_val)
1090 {
1092 newoption->default_val = strdup(default_val);
1093 else
1095 newoption->default_len = strlen(default_val);
1097 }
1098 else
1099 {
1103 }
1104
1105 return newoption;
1106}
1107
1108
1109
1110
1111
1112
1113
1114
1115
1116
1117void
1121{
1123 default_val,
1124 validator, NULL,
1125 lockmode);
1126
1128}
1129
1130
1131
1132
1133
1134
1135
1136
1137void
1139 const char *desc, const char *default_val,
1142{
1145 default_val,
1146 validator, filler,
1147 0);
1148
1150}
1151
1152
1153
1154
1155
1156
1157
1158
1159
1160
1161
1162
1163
1164
1165
1166
1167
1168
1169
1170
1171
1172
1173
1174
1177 const char *const validnsps[], bool acceptOidsOff, bool isReset)
1178{
1182
1183
1184 if (defList == NIL)
1185 return oldOptions;
1186
1187
1188 astate = NULL;
1189
1190
1192 {
1194 Datum *oldoptions;
1195 int noldoptions;
1196 int i;
1197
1199
1200 for (i = 0; i < noldoptions; i++)
1201 {
1204
1205
1206 foreach(cell, defList)
1207 {
1209 int kw_len;
1210
1211
1212 if (nameSpace == NULL)
1213 {
1215 continue;
1216 }
1218 continue;
1219 else if (strcmp(def->defnamespace, nameSpace) != 0)
1220 continue;
1221
1222 kw_len = strlen(def->defname);
1223 if (text_len > kw_len && text_str[kw_len] == '=' &&
1224 strncmp(text_str, def->defname, kw_len) == 0)
1225 break;
1226 }
1227 if (!cell)
1228 {
1229
1231 false, TEXTOID,
1233 }
1234 }
1235 }
1236
1237
1238
1239
1240
1241
1242 foreach(cell, defList)
1243 {
1245
1246 if (isReset)
1247 {
1248 if (def->arg != NULL)
1250 (errcode(ERRCODE_SYNTAX_ERROR),
1251 errmsg("RESET must not include values for parameters")));
1252 }
1253 else
1254 {
1255 const char *name;
1256 const char *value;
1259
1260
1261
1262
1263
1265 {
1266 bool valid = false;
1267 int i;
1268
1269 if (validnsps)
1270 {
1271 for (i = 0; validnsps[i]; i++)
1272 {
1273 if (strcmp(def->defnamespace, validnsps[i]) == 0)
1274 {
1275 valid = true;
1276 break;
1277 }
1278 }
1279 }
1280
1281 if (!valid)
1283 (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
1284 errmsg("unrecognized parameter namespace \"%s\"",
1286 }
1287
1288
1289 if (nameSpace == NULL)
1290 {
1292 continue;
1293 }
1295 continue;
1296 else if (strcmp(def->defnamespace, nameSpace) != 0)
1297 continue;
1298
1299
1300
1301
1302
1303
1305 if (def->arg != NULL)
1307 else
1309
1310
1311 if (strchr(name, '=') != NULL)
1313 (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
1314 errmsg("invalid option name \"%s\": must not contain \"=\"",
1316
1317
1318
1319
1320
1321
1322
1323 if (acceptOidsOff && def->defnamespace == NULL &&
1324 strcmp(name, "oids") == 0)
1325 {
1328 (errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
1329 errmsg("tables declared WITH OIDS are not supported")));
1330
1331 continue;
1332 }
1333
1335
1339
1341 false, TEXTOID,
1343 }
1344 }
1345
1346 if (astate)
1348 else
1349 result = (Datum) 0;
1350
1351 return result;
1352}
1353
1354
1355
1356
1357
1358
1361{
1364 Datum *optiondatums;
1366 int i;
1367
1368
1370 return result;
1371
1373
1375
1377 {
1378 char *s;
1379 char *p;
1381
1383 p = strchr(s, '=');
1384 if (p)
1385 {
1386 *p++ = '\0';
1388 }
1390 }
1391
1392 return result;
1393}
1394
1395
1396
1397
1398
1399
1400
1401
1402
1403
1404
1405
1406
1410{
1412 bool isnull;
1415
1417 Anum_pg_class_reloptions,
1418 tupdesc,
1419 &isnull);
1420 if (isnull)
1421 return NULL;
1422
1424
1425
1426 switch (classForm->relkind)
1427 {
1428 case RELKIND_RELATION:
1429 case RELKIND_TOASTVALUE:
1430 case RELKIND_MATVIEW:
1432 break;
1433 case RELKIND_PARTITIONED_TABLE:
1435 break;
1436 case RELKIND_VIEW:
1438 break;
1439 case RELKIND_INDEX:
1440 case RELKIND_PARTITIONED_INDEX:
1442 break;
1443 case RELKIND_FOREIGN_TABLE:
1445 break;
1446 default:
1447 Assert(false);
1448 options = NULL;
1449 break;
1450 }
1451
1453}
1454
1455static void
1458{
1460 Datum *optiondatums;
1462 int i;
1463
1465
1467 {
1470 int j;
1471
1472
1473 for (j = 0; j < numoptions; j++)
1474 {
1475 int kw_len = reloptions[j].gen->namelen;
1476
1477 if (text_len > kw_len && text_str[kw_len] == '=' &&
1478 strncmp(text_str, reloptions[j].gen->name, kw_len) == 0)
1479 {
1482 break;
1483 }
1484 }
1485
1486 if (j >= numoptions && validate)
1487 {
1488 char *s;
1489 char *p;
1490
1492 p = strchr(s, '=');
1493 if (p)
1494 *p = '\0';
1496 (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
1497 errmsg("unrecognized parameter \"%s\"", s)));
1498 }
1499 }
1500
1501
1502 pfree(optiondatums);
1503
1506}
1507
1508
1509
1510
1511
1512
1513
1514
1515
1516
1517
1518
1519
1520
1521
1522
1523
1524
1525
1526
1529 int *numrelopts)
1530{
1532 int numoptions = 0;
1533 int i;
1534 int j;
1535
1538
1539
1540
1542 if (relOpts[i]->kinds & kind)
1543 numoptions++;
1544
1545 if (numoptions > 0)
1546 {
1548
1550 {
1551 if (relOpts[i]->kinds & kind)
1552 {
1554 reloptions[j].isset = false;
1555 j++;
1556 }
1557 }
1558 }
1559
1560
1563
1564 *numrelopts = numoptions;
1565 return reloptions;
1566}
1567
1568
1571{
1575 int i = 0;
1576
1577 foreach(lc, relopts->options)
1578 {
1580
1583
1584 i++;
1585 }
1586
1589
1591}
1592
1593
1594
1595
1596
1597static void
1600{
1602 int value_len;
1603 bool parsed;
1604 bool nofree = false;
1605
1608 (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
1609 errmsg("parameter \"%s\" specified more than once",
1611
1612 value_len = text_len - option->gen->namelen - 1;
1614 memcpy(value, text_str + option->gen->namelen + 1, value_len);
1615 value[value_len] = '\0';
1616
1617 switch (option->gen->type)
1618 {
1620 {
1624 (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
1625 errmsg("invalid value for boolean option \"%s\": %s",
1627 }
1628 break;
1630 {
1632
1636 (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
1637 errmsg("invalid value for integer option \"%s\": %s",
1640 option->values.int_val > optint->max))
1642 (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
1643 errmsg("value %s out of bounds for option \"%s\"",
1645 errdetail("Valid values are between \"%d\" and \"%d\".",
1646 optint->min, optint->max)));
1647 }
1648 break;
1650 {
1652
1656 (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
1657 errmsg("invalid value for floating point option \"%s\": %s",
1660 option->values.real_val > optreal->max))
1662 (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
1663 errmsg("value %s out of bounds for option \"%s\"",
1665 errdetail("Valid values are between \"%f\" and \"%f\".",
1666 optreal->min, optreal->max)));
1667 }
1668 break;
1670 {
1673
1674 parsed = false;
1676 {
1678 {
1679 option->values.enum_val = elt->symbol_val;
1680 parsed = true;
1681 break;
1682 }
1683 }
1686 (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
1687 errmsg("invalid value for enum option \"%s\": %s",
1691
1692
1693
1694
1695
1696 if (!parsed)
1698 }
1699 break;
1701 {
1703
1705 nofree = true;
1708 parsed = true;
1709 }
1710 break;
1711 default:
1712 elog(ERROR, "unsupported reloption type %d", option->gen->type);
1713 parsed = true;
1714 break;
1715 }
1716
1717 if (parsed)
1718 option->isset = true;
1719 if (!nofree)
1721}
1722
1723
1724
1725
1726
1727
1728
1729
1730static void *
1732{
1733 Size size = base;
1734 int i;
1735
1736 for (i = 0; i < numoptions; i++)
1737 {
1739
1741 {
1743
1745 {
1748
1750 }
1751 else
1753 }
1754 }
1755
1757}
1758
1759
1760
1761
1762
1763
1764
1765
1766
1767
1768
1769
1770static void
1775{
1776 int i;
1777 int offset = basesize;
1778
1779 for (i = 0; i < numoptions; i++)
1780 {
1781 int j;
1782 bool found = false;
1783
1784 for (j = 0; j < numelems; j++)
1785 {
1787 {
1789 char *itempos = ((char *) rdopts) + elems[j].offset;
1790 char *string_val;
1791
1792
1793
1794
1795
1796 if (elems[j].isset_offset > 0)
1797 {
1798 char *setpos = ((char *) rdopts) + elems[j].isset_offset;
1799
1800 *(bool *) setpos = options[i].isset;
1801 }
1802
1803 switch (options[i].gen->type)
1804 {
1806 *(bool *) itempos = options[i].isset ?
1809 break;
1811 *(int *) itempos = options[i].isset ?
1814 break;
1816 *(double *) itempos = options[i].isset ?
1819 break;
1821 *(int *) itempos = options[i].isset ?
1824 break;
1828 string_val = options[i].values.string_val;
1831 else
1832 string_val = NULL;
1833
1835 {
1837 optstring->fill_cb(string_val,
1838 (char *) rdopts + offset);
1839
1840 if (size)
1841 {
1842 *(int *) itempos = offset;
1843 offset += size;
1844 }
1845 else
1846 *(int *) itempos = 0;
1847 }
1848 else if (string_val == NULL)
1849 *(int *) itempos = 0;
1850 else
1851 {
1852 strcpy((char *) rdopts + offset, string_val);
1853 *(int *) itempos = offset;
1854 offset += strlen(string_val) + 1;
1855 }
1856 break;
1857 default:
1858 elog(ERROR, "unsupported reloption type %d",
1860 break;
1861 }
1862 found = true;
1863 break;
1864 }
1865 }
1867 elog(ERROR, "reloption \"%s\" not found in parse table",
1869 }
1871}
1872
1873
1874
1875
1876
1879{
1900 {"autovacuum_multixact_freeze_min_age", RELOPT_TYPE_INT,
1902 {"autovacuum_multixact_freeze_max_age", RELOPT_TYPE_INT,
1904 {"autovacuum_multixact_freeze_table_age", RELOPT_TYPE_INT,
1905 offsetof(StdRdOptions, autovacuum) + offsetof(AutoVacOpts, multixact_freeze_table_age)},
1911 offsetof(StdRdOptions, toast_tuple_target)},
1921 offsetof(StdRdOptions, user_catalog_table)},
1925 offsetof(StdRdOptions, vacuum_index_cleanup)},
1930 };
1931
1935}
1936
1937
1938
1939
1940
1941
1942
1943
1944
1945
1946
1947
1948
1949
1950
1951
1952
1953void *
1956 Size relopt_struct_size,
1958 int num_relopt_elems)
1959{
1960 int numoptions;
1962 void *rdopts;
1963
1964
1966 Assert(numoptions <= num_relopt_elems);
1967
1968
1969 if (numoptions == 0)
1970 {
1972 return NULL;
1973 }
1974
1975
1978 validate, relopt_elems, num_relopt_elems);
1979
1981
1982 return rdopts;
1983}
1984
1985
1986
1987
1988
1989
1990void *
1992{
1997 int i = 0;
1999
2000 foreach(lc, relopts->options)
2001 {
2003
2007 elems[i].isset_offset = 0;
2008
2009 i++;
2010 }
2011
2016
2020
2021 if (elems)
2023
2024 return opts;
2025}
2026
2027
2028
2029
2032{
2035 errcode(ERRCODE_WRONG_OBJECT_TYPE),
2036 errmsg("cannot specify storage parameters for a partitioned table"),
2037 errhint("Specify storage parameters for its leaf partitions instead."));
2038 return NULL;
2039}
2040
2041
2042
2043
2046{
2049 offsetof(ViewOptions, security_barrier)},
2051 offsetof(ViewOptions, security_invoker)},
2054 };
2055
2060}
2061
2062
2063
2064
2067{
2069
2070 switch (relkind)
2071 {
2072 case RELKIND_TOASTVALUE:
2075 if (rdopts != NULL)
2076 {
2077
2081 }
2082 return (bytea *) rdopts;
2083 case RELKIND_RELATION:
2084 case RELKIND_MATVIEW:
2086 default:
2087
2088 return NULL;
2089 }
2090}
2091
2092
2093
2094
2095
2096
2097
2098
2099
2102{
2103 Assert(amoptions != NULL);
2104
2105
2107 return NULL;
2108
2109 return amoptions(reloptions, validate);
2110}
2111
2112
2113
2114
2117{
2121 };
2122
2127}
2128
2129
2130
2131
2134{
2140 };
2141
2146}
2147
2148
2149
2150
2151
2152
2153
2156{
2159
2160 if (defList == NIL)
2162
2165
2166 foreach(cell, defList)
2167 {
2169 int i;
2170
2172 {
2176 {
2177 if (lockmode < relOpts[i]->lockmode)
2179 }
2180 }
2181 }
2182
2183 return lockmode;
2184}
bytea *(* amoptions_function)(Datum reloptions, bool validate)
#define DatumGetArrayTypeP(X)
ArrayBuildState * accumArrayResult(ArrayBuildState *astate, Datum dvalue, bool disnull, Oid element_type, MemoryContext rcontext)
void deconstruct_array_builtin(const ArrayType *array, Oid elmtype, Datum **elemsp, bool **nullsp, int *nelemsp)
Datum makeArrayResult(ArrayBuildState *astate, MemoryContext rcontext)
static bool validate(Port *port, const char *auth)
bool parse_bool(const char *value, bool *result)
static Datum values[MAXATTR]
int maintenance_io_concurrency
int effective_io_concurrency
#define MAX_IO_CONCURRENCY
#define TextDatumGetCString(d)
char * defGetString(DefElem *def)
bool defGetBoolean(DefElem *def)
int errdetail_internal(const char *fmt,...)
int errdetail(const char *fmt,...)
int errhint(const char *fmt,...)
int errcode(int sqlerrcode)
int errmsg(const char *fmt,...)
#define ereport(elevel,...)
#define palloc_object(type)
#define palloc_array(type, count)
@ GIST_OPTION_BUFFERING_OFF
@ GIST_OPTION_BUFFERING_AUTO
@ GIST_OPTION_BUFFERING_ON
#define GIST_MIN_FILLFACTOR
#define GIST_DEFAULT_FILLFACTOR
bool parse_int(const char *value, int *result, int flags, const char **hintmsg)
bool parse_real(const char *value, double *result, int flags, const char **hintmsg)
#define HASH_DEFAULT_FILLFACTOR
#define HASH_MIN_FILLFACTOR
Assert(PointerIsAligned(start, uint64))
#define TOAST_TUPLE_TARGET
#define TOAST_TUPLE_TARGET_MAIN
static void * GETSTRUCT(const HeapTupleData *tuple)
static Datum fastgetattr(HeapTuple tup, int attnum, TupleDesc tupleDesc, bool *isnull)
if(TABLE==NULL||TABLE_index==NULL)
List * lappend(List *list, void *datum)
bool DoLockModesConflict(LOCKMODE mode1, LOCKMODE mode2)
#define AccessExclusiveLock
#define ShareUpdateExclusiveLock
DefElem * makeDefElem(char *name, Node *arg, int location)
char * MemoryContextStrdup(MemoryContext context, const char *string)
void * MemoryContextAlloc(MemoryContext context, Size size)
char * pstrdup(const char *in)
void * repalloc(void *pointer, Size size)
void pfree(void *pointer)
void * palloc0(Size size)
MemoryContext TopMemoryContext
MemoryContext CurrentMemoryContext
#define BTREE_MIN_FILLFACTOR
#define BTREE_DEFAULT_FILLFACTOR
static MemoryContext MemoryContextSwitchTo(MemoryContext context)
static AmcheckOptions opts
FormData_pg_class * Form_pg_class
static int list_length(const List *l)
int pg_strcasecmp(const char *s1, const char *s2)
static Datum PointerGetDatum(const void *X)
static Pointer DatumGetPointer(Datum X)
#define HEAP_MIN_FILLFACTOR
@ VIEW_OPTION_CHECK_OPTION_NOT_SET
@ VIEW_OPTION_CHECK_OPTION_LOCAL
@ VIEW_OPTION_CHECK_OPTION_CASCADED
#define HEAP_DEFAULT_FILLFACTOR
@ STDRD_OPTION_VACUUM_INDEX_CLEANUP_AUTO
@ STDRD_OPTION_VACUUM_INDEX_CLEANUP_OFF
@ STDRD_OPTION_VACUUM_INDEX_CLEANUP_ON
static relopt_string * init_string_reloption(bits32 kinds, const char *name, const char *desc, const char *default_val, validate_string_relopt validator, fill_string_relopt filler, LOCKMODE lockmode)
static int num_custom_options
void add_local_string_reloption(local_relopts *relopts, const char *name, const char *desc, const char *default_val, validate_string_relopt validator, fill_string_relopt filler, int offset)
static relopt_real realRelOpts[]
void add_int_reloption(bits32 kinds, const char *name, const char *desc, int default_val, int min_val, int max_val, LOCKMODE lockmode)
static relopt_enum_elt_def gistBufferingOptValues[]
bytea * default_reloptions(Datum reloptions, bool validate, relopt_kind kind)
static relopt_value * parseLocalRelOptions(local_relopts *relopts, Datum options, bool validate)
bytea * tablespace_reloptions(Datum reloptions, bool validate)
static relopt_enum_elt_def StdRdOptIndexCleanupValues[]
#define GET_STRING_RELOPTION_LEN(option)
void add_string_reloption(bits32 kinds, const char *name, const char *desc, const char *default_val, validate_string_relopt validator, LOCKMODE lockmode)
List * untransformRelOptions(Datum options)
static relopt_int intRelOpts[]
static relopt_enum enumRelOpts[]
static void parse_one_reloption(relopt_value *option, char *text_str, int text_len, bool validate)
static relopt_string stringRelOpts[]
bytea * view_reloptions(Datum reloptions, bool validate)
static relopt_int * init_int_reloption(bits32 kinds, const char *name, const char *desc, int default_val, int min_val, int max_val, LOCKMODE lockmode)
bytea * index_reloptions(amoptions_function amoptions, Datum reloptions, bool validate)
void add_enum_reloption(bits32 kinds, const char *name, const char *desc, relopt_enum_elt_def *members, int default_val, const char *detailmsg, LOCKMODE lockmode)
void * build_reloptions(Datum reloptions, bool validate, relopt_kind kind, Size relopt_struct_size, const relopt_parse_elt *relopt_elems, int num_relopt_elems)
bytea * partitioned_table_reloptions(Datum reloptions, bool validate)
void add_real_reloption(bits32 kinds, const char *name, const char *desc, double default_val, double min_val, double max_val, LOCKMODE lockmode)
void add_local_bool_reloption(local_relopts *relopts, const char *name, const char *desc, bool default_val, int offset)
void init_local_reloptions(local_relopts *relopts, Size relopt_struct_size)
static relopt_enum_elt_def viewCheckOptValues[]
void add_local_real_reloption(local_relopts *relopts, const char *name, const char *desc, double default_val, double min_val, double max_val, int offset)
static void add_reloption(relopt_gen *newoption)
static void add_local_reloption(local_relopts *relopts, relopt_gen *newoption, int offset)
void add_bool_reloption(bits32 kinds, const char *name, const char *desc, bool default_val, LOCKMODE lockmode)
Datum transformRelOptions(Datum oldOptions, List *defList, const char *nameSpace, const char *const validnsps[], bool acceptOidsOff, bool isReset)
void add_local_enum_reloption(local_relopts *relopts, const char *name, const char *desc, relopt_enum_elt_def *members, int default_val, const char *detailmsg, int offset)
bytea * extractRelOptions(HeapTuple tuple, TupleDesc tupdesc, amoptions_function amoptions)
static void parseRelOptionsInternal(Datum options, bool validate, relopt_value *reloptions, int numoptions)
static void fillRelOptions(void *rdopts, Size basesize, relopt_value *options, int numoptions, bool validate, const relopt_parse_elt *elems, int numelems)
static relopt_enum * init_enum_reloption(bits32 kinds, const char *name, const char *desc, relopt_enum_elt_def *members, int default_val, const char *detailmsg, LOCKMODE lockmode)
static void initialize_reloptions(void)
relopt_kind add_reloption_kind(void)
void * build_local_reloptions(local_relopts *relopts, Datum options, bool validate)
void register_reloptions_validator(local_relopts *relopts, relopts_validator validator)
static bool need_initialization
static relopt_value * parseRelOptions(Datum options, bool validate, relopt_kind kind, int *numrelopts)
static relopt_bool * init_bool_reloption(bits32 kinds, const char *name, const char *desc, bool default_val, LOCKMODE lockmode)
static relopt_gen ** relOpts
static relopt_gen ** custom_options
LOCKMODE AlterTableGetRelOptionsLockLevel(List *defList)
static relopt_real * init_real_reloption(bits32 kinds, const char *name, const char *desc, double default_val, double min_val, double max_val, LOCKMODE lockmode)
bytea * attribute_reloptions(Datum reloptions, bool validate)
static relopt_gen * allocate_reloption(bits32 kinds, int type, const char *name, const char *desc, LOCKMODE lockmode)
static relopt_bool boolRelOpts[]
void add_local_int_reloption(local_relopts *relopts, const char *name, const char *desc, int default_val, int min_val, int max_val, int offset)
static void * allocateReloptStruct(Size base, relopt_value *options, int numoptions)
static bits32 last_assigned_kind
bytea * heap_reloptions(char relkind, Datum reloptions, bool validate)
struct relopt_real relopt_real
Size(* fill_string_relopt)(const char *value, void *ptr)
struct relopt_bool relopt_bool
@ RELOPT_KIND_LAST_DEFAULT
struct relopt_string relopt_string
void(* validate_string_relopt)(const char *value)
struct relopt_enum relopt_enum
void(* relopts_validator)(void *parsed_options, relopt_value *vals, int nvals)
struct relopt_int relopt_int
#define SPGIST_DEFAULT_FILLFACTOR
#define SPGIST_MIN_FILLFACTOR
float8 analyze_scale_factor
relopt_enum_elt_def * members
validate_string_relopt validate_cb
fill_string_relopt fill_cb
union relopt_value::@52 values
double vacuum_max_eager_freeze_failure_rate
String * makeString(char *str)
static Size VARSIZE(const void *PTR)
static char * VARDATA(const void *PTR)
static void SET_VARSIZE(void *PTR, Size len)