66 #include "utils/fmgroids.h"
115 static void movedb(
const char *
dbname,
const char *tblspcname);
118 Oid *dbIdP,
Oid *ownerIdP,
119 int *encodingP,
bool *dbIsTemplateP,
bool *dbAllowConnP,
121 Oid *dbTablespace,
char **dbCollate,
char **dbCtype,
char **dbIculocale,
124 char **dbCollversion);
132 Oid dbid,
char *srcpath,
140 Oid src_tsid,
Oid dst_tsid);
150 Oid src_tsid,
Oid dst_tsid)
154 List *rlocatorlist = NULL;
180 srcrelid.
dbId = src_dboid;
181 dstrelid.
dbId = dst_dboid;
184 foreach(cell, rlocatorlist)
195 if (srcrlocator.
spcOid == src_tsid)
196 dstrlocator.
spcOid = dst_tsid;
200 dstrlocator.
dbOid = dst_dboid;
271 relid.
relId = RelationRelationId;
276 rlocator.
dbOid = dbid;
295 for (blkno = 0; blkno < nblocks; blkno++)
312 srcpath, rlocatorlist,
330 char *srcpath,
List *rlocatorlist,
376 rlocatorlist =
lappend(rlocatorlist, relinfo);
412 if (classForm->reltablespace == GLOBALTABLESPACE_OID ||
413 !RELKIND_HAS_STORAGE(classForm->relkind) ||
414 classForm->relpersistence == RELPERSISTENCE_TEMP)
422 relfilenumber = classForm->relfilenode;
429 elog(
ERROR,
"relation with OID %u does not have a valid relfilenumber",
441 relinfo->
reloid = classForm->oid;
444 Assert(classForm->relpersistence != RELPERSISTENCE_TEMP);
446 (classForm->relpersistence == RELPERSISTENCE_PERMANENT) ?
true :
false;
471 nbytes = strlen(PG_MAJORVERSION) + 1;
498 if (errno != EEXIST || !isRedo)
501 errmsg(
"could not create directory \"%s\": %m", dbpath)));
509 snprintf(versionfile,
sizeof(versionfile),
"%s/%s", dbpath,
"PG_VERSION");
512 if (
fd < 0 && errno == EEXIST && isRedo)
518 errmsg(
"could not create file \"%s\": %m", versionfile)));
530 errmsg(
"could not write to file \"%s\": %m", versionfile)));
580 Oid srctablespace = spaceform->oid;
587 if (srctablespace == GLOBALTABLESPACE_OID)
600 if (srctablespace == src_tsid)
601 dsttablespace = dst_tsid;
603 dsttablespace = srctablespace;
618 xlrec.
db_id = dst_dboid;
675 int src_encoding = -1;
676 char *src_collate = NULL;
677 char *src_ctype = NULL;
678 char *src_iculocale = NULL;
679 char *src_icurules = NULL;
680 char src_locprovider =
'\0';
681 char *src_collversion = NULL;
686 Oid src_deftablespace;
687 volatile Oid dst_deftablespace;
690 Datum new_record[Natts_pg_database] = {0};
691 bool new_record_nulls[Natts_pg_database] = {0};
695 DefElem *dtablespacename = NULL;
706 DefElem *dallowconnections = NULL;
711 char *dbowner = NULL;
712 const char *dbtemplate = NULL;
713 char *dbcollate = NULL;
714 char *dbctype = NULL;
715 char *dbiculocale = NULL;
716 char *dbicurules = NULL;
717 char dblocprovider =
'\0';
720 bool dbistemplate =
false;
721 bool dballowconnections =
true;
723 char *dbcollversion = NULL;
734 if (strcmp(defel->
defname,
"tablespace") == 0)
738 dtablespacename = defel;
740 else if (strcmp(defel->
defname,
"owner") == 0)
746 else if (strcmp(defel->
defname,
"template") == 0)
752 else if (strcmp(defel->
defname,
"encoding") == 0)
758 else if (strcmp(defel->
defname,
"locale") == 0)
764 else if (strcmp(defel->
defname,
"lc_collate") == 0)
770 else if (strcmp(defel->
defname,
"lc_ctype") == 0)
776 else if (strcmp(defel->
defname,
"icu_locale") == 0)
782 else if (strcmp(defel->
defname,
"icu_rules") == 0)
788 else if (strcmp(defel->
defname,
"locale_provider") == 0)
792 dlocprovider = defel;
794 else if (strcmp(defel->
defname,
"is_template") == 0)
800 else if (strcmp(defel->
defname,
"allow_connections") == 0)
802 if (dallowconnections)
804 dallowconnections = defel;
806 else if (strcmp(defel->
defname,
"connection_limit") == 0)
812 else if (strcmp(defel->
defname,
"collation_version") == 0)
816 dcollversion = defel;
818 else if (strcmp(defel->
defname,
"location") == 0)
821 (
errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
822 errmsg(
"LOCATION is not supported anymore"),
823 errhint(
"Consider using tablespaces instead."),
826 else if (strcmp(defel->
defname,
"oid") == 0)
847 (
errcode(ERRCODE_INVALID_PARAMETER_VALUE)),
850 else if (strcmp(defel->
defname,
"strategy") == 0)
858 (
errcode(ERRCODE_SYNTAX_ERROR),
863 if (downer && downer->
arg)
865 if (dtemplate && dtemplate->
arg)
867 if (dencoding && dencoding->
arg)
869 const char *encoding_name;
875 if (strcmp(encoding_name,
"") == 0 ||
878 (
errcode(ERRCODE_UNDEFINED_OBJECT),
879 errmsg(
"%d is not a valid encoding code",
889 (
errcode(ERRCODE_UNDEFINED_OBJECT),
890 errmsg(
"%s is not a valid encoding name",
895 if (dlocale && dlocale->
arg)
900 if (dcollate && dcollate->
arg)
902 if (dctype && dctype->
arg)
904 if (diculocale && diculocale->
arg)
906 if (dicurules && dicurules->
arg)
908 if (dlocprovider && dlocprovider->
arg)
913 dblocprovider = COLLPROVIDER_ICU;
915 dblocprovider = COLLPROVIDER_LIBC;
918 (
errcode(ERRCODE_INVALID_OBJECT_DEFINITION),
919 errmsg(
"unrecognized locale provider: %s",
922 if (distemplate && distemplate->
arg)
924 if (dallowconnections && dallowconnections->
arg)
926 if (dconnlimit && dconnlimit->
arg)
931 (
errcode(ERRCODE_INVALID_PARAMETER_VALUE),
932 errmsg(
"invalid connection limit: %d", dbconnlimit)));
952 (
errcode(ERRCODE_INSUFFICIENT_PRIVILEGE),
953 errmsg(
"permission denied to create database")));
967 dbtemplate =
"template1";
970 &src_dboid, &src_owner, &src_encoding,
971 &src_istemplate, &src_allowconn,
972 &src_frozenxid, &src_minmxid, &src_deftablespace,
973 &src_collate, &src_ctype, &src_iculocale, &src_icurules, &src_locprovider,
976 (
errcode(ERRCODE_UNDEFINED_DATABASE),
977 errmsg(
"template database \"%s\" does not exist",
986 errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
987 errmsg(
"cannot use invalid database \"%s\" as template", dbtemplate),
988 errhint(
"Use DROP DATABASE to drop invalid databases."));
998 (
errcode(ERRCODE_INSUFFICIENT_PRIVILEGE),
999 errmsg(
"permission denied to copy database \"%s\"",
1004 if (dstrategy && dstrategy->
arg)
1009 if (strcmp(strategy,
"wal_log") == 0)
1011 else if (strcmp(strategy,
"file_copy") == 0)
1015 (
errcode(ERRCODE_INVALID_PARAMETER_VALUE),
1016 errmsg(
"invalid create database strategy \"%s\"", strategy),
1017 errhint(
"Valid strategies are \"wal_log\", and \"file_copy\".")));
1023 if (dbcollate == NULL)
1024 dbcollate = src_collate;
1025 if (dbctype == NULL)
1026 dbctype = src_ctype;
1027 if (dblocprovider ==
'\0')
1028 dblocprovider = src_locprovider;
1029 if (dbiculocale == NULL && dblocprovider == COLLPROVIDER_ICU)
1031 if (dlocale && dlocale->
arg)
1034 dbiculocale = src_iculocale;
1036 if (dbicurules == NULL && dblocprovider == COLLPROVIDER_ICU)
1037 dbicurules = src_icurules;
1042 (
errcode(ERRCODE_WRONG_OBJECT_TYPE),
1048 (
errcode(ERRCODE_WRONG_OBJECT_TYPE),
1049 errmsg(
"invalid LC_COLLATE locale name: \"%s\"", dbcollate),
1050 errhint(
"If the locale name is specific to ICU, use ICU_LOCALE.")));
1051 dbcollate = canonname;
1054 (
errcode(ERRCODE_WRONG_OBJECT_TYPE),
1055 errmsg(
"invalid LC_CTYPE locale name: \"%s\"", dbctype),
1056 errhint(
"If the locale name is specific to ICU, use ICU_LOCALE.")));
1057 dbctype = canonname;
1061 if (dblocprovider == COLLPROVIDER_ICU)
1065 (
errcode(ERRCODE_INVALID_PARAMETER_VALUE),
1066 errmsg(
"encoding \"%s\" is not supported with ICU provider",
1075 (
errcode(ERRCODE_INVALID_PARAMETER_VALUE),
1076 errmsg(
"LOCALE or ICU_LOCALE must be specified")));
1088 if (langtag && strcmp(dbiculocale, langtag) != 0)
1091 (
errmsg(
"using standard form \"%s\" for ICU locale \"%s\"",
1092 langtag, dbiculocale)));
1094 dbiculocale = langtag;
1104 (
errcode(ERRCODE_INVALID_OBJECT_DEFINITION),
1105 errmsg(
"ICU locale cannot be specified unless locale provider is ICU")));
1109 (
errcode(ERRCODE_INVALID_OBJECT_DEFINITION),
1110 errmsg(
"ICU rules cannot be specified unless locale provider is ICU")));
1123 if (strcmp(dbtemplate,
"template0") != 0)
1127 (
errcode(ERRCODE_INVALID_PARAMETER_VALUE),
1128 errmsg(
"new encoding (%s) is incompatible with the encoding of the template database (%s)",
1131 errhint(
"Use the same encoding as in the template database, or use template0 as template.")));
1133 if (strcmp(dbcollate, src_collate) != 0)
1135 (
errcode(ERRCODE_INVALID_PARAMETER_VALUE),
1136 errmsg(
"new collation (%s) is incompatible with the collation of the template database (%s)",
1137 dbcollate, src_collate),
1138 errhint(
"Use the same collation as in the template database, or use template0 as template.")));
1140 if (strcmp(dbctype, src_ctype) != 0)
1142 (
errcode(ERRCODE_INVALID_PARAMETER_VALUE),
1143 errmsg(
"new LC_CTYPE (%s) is incompatible with the LC_CTYPE of the template database (%s)",
1144 dbctype, src_ctype),
1145 errhint(
"Use the same LC_CTYPE as in the template database, or use template0 as template.")));
1147 if (dblocprovider != src_locprovider)
1149 (
errcode(ERRCODE_INVALID_PARAMETER_VALUE),
1150 errmsg(
"new locale provider (%s) does not match locale provider of the template database (%s)",
1151 collprovider_name(dblocprovider), collprovider_name(src_locprovider)),
1152 errhint(
"Use the same locale provider as in the template database, or use template0 as template.")));
1154 if (dblocprovider == COLLPROVIDER_ICU)
1161 if (strcmp(dbiculocale, src_iculocale) != 0)
1163 (
errcode(ERRCODE_INVALID_PARAMETER_VALUE),
1164 errmsg(
"new ICU locale (%s) is incompatible with the ICU locale of the template database (%s)",
1165 dbiculocale, src_iculocale),
1166 errhint(
"Use the same ICU locale as in the template database, or use template0 as template.")));
1171 val2 = src_icurules;
1174 if (strcmp(val1, val2) != 0)
1176 (
errcode(ERRCODE_INVALID_PARAMETER_VALUE),
1177 errmsg(
"new ICU collation rules (%s) are incompatible with the ICU collation rules of the template database (%s)",
1179 errhint(
"Use the same ICU collation rules as in the template database, or use template0 as template.")));
1195 if (src_collversion && !dcollversion)
1197 char *actual_versionstr;
1200 if (!actual_versionstr)
1202 (
errmsg(
"template database \"%s\" has a collation version, but no actual collation version could be determined",
1205 if (strcmp(actual_versionstr, src_collversion) != 0)
1207 (
errmsg(
"template database \"%s\" has a collation version mismatch",
1209 errdetail(
"The template database was created using collation version %s, "
1210 "but the operating system provides version %s.",
1211 src_collversion, actual_versionstr),
1212 errhint(
"Rebuild all objects in the template database that use the default collation and run "
1213 "ALTER DATABASE %s REFRESH COLLATION VERSION, "
1214 "or build PostgreSQL with the right library version.",
1218 if (dbcollversion == NULL)
1219 dbcollversion = src_collversion;
1226 if (dbcollversion == NULL)
1230 if (dtablespacename && dtablespacename->
arg)
1232 char *tablespacename;
1245 if (dst_deftablespace == GLOBALTABLESPACE_OID)
1247 (
errcode(ERRCODE_INVALID_PARAMETER_VALUE),
1248 errmsg(
"pg_global cannot be used as default tablespace")));
1262 if (dst_deftablespace != src_deftablespace)
1269 if (
stat(srcpath, &st) == 0 &&
1273 (
errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
1274 errmsg(
"cannot assign new default tablespace \"%s\"",
1276 errdetail(
"There is a conflict because database \"%s\" already has some tables in this tablespace.",
1284 dst_deftablespace = src_deftablespace;
1293 #ifdef ENFORCE_REGRESSION_TEST_NAME_RESTRICTIONS
1295 elog(
WARNING,
"databases created by regression test cases should have names including \"regression\"");
1305 (
errcode(ERRCODE_DUPLICATE_DATABASE),
1319 (
errcode(ERRCODE_OBJECT_IN_USE),
1320 errmsg(
"source database \"%s\" is being accessed by other users",
1339 if (existing_dbname != NULL)
1341 (
errcode(ERRCODE_INVALID_PARAMETER_VALUE)),
1342 errmsg(
"database OID %u is already in use by database \"%s\"",
1343 dboid, existing_dbname));
1347 (
errcode(ERRCODE_INVALID_PARAMETER_VALUE)),
1348 errmsg(
"data directory with the specified OID %u already exists", dboid));
1356 Anum_pg_database_oid);
1366 Assert((dblocprovider == COLLPROVIDER_ICU && dbiculocale) ||
1367 (dblocprovider != COLLPROVIDER_ICU && !dbiculocale));
1371 new_record[Anum_pg_database_datname - 1] =
1375 new_record[Anum_pg_database_datlocprovider - 1] =
CharGetDatum(dblocprovider);
1376 new_record[Anum_pg_database_datistemplate - 1] =
BoolGetDatum(dbistemplate);
1377 new_record[Anum_pg_database_datallowconn - 1] =
BoolGetDatum(dballowconnections);
1378 new_record[Anum_pg_database_datconnlimit - 1] =
Int32GetDatum(dbconnlimit);
1381 new_record[Anum_pg_database_dattablespace - 1] =
ObjectIdGetDatum(dst_deftablespace);
1387 new_record_nulls[Anum_pg_database_daticulocale - 1] =
true;
1391 new_record_nulls[Anum_pg_database_daticurules - 1] =
true;
1395 new_record_nulls[Anum_pg_database_datcollversion - 1] =
true;
1402 new_record_nulls[Anum_pg_database_datacl - 1] =
true;
1405 new_record, new_record_nulls);
1511 if (!(ctype_encoding ==
encoding ||
1513 ctype_encoding == -1 ||
1519 (
errcode(ERRCODE_INVALID_PARAMETER_VALUE),
1520 errmsg(
"encoding \"%s\" does not match locale \"%s\"",
1523 errdetail(
"The chosen LC_CTYPE setting requires encoding \"%s\".",
1526 if (!(collate_encoding ==
encoding ||
1528 collate_encoding == -1 ||
1534 (
errcode(ERRCODE_INVALID_PARAMETER_VALUE),
1535 errmsg(
"encoding \"%s\" does not match locale \"%s\"",
1538 errdetail(
"The chosen LC_COLLATE setting requires encoding \"%s\".",
1606 &db_istemplate, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL))
1611 (
errcode(ERRCODE_UNDEFINED_DATABASE),
1619 (
errmsg(
"database \"%s\" does not exist, skipping",
1642 (
errcode(ERRCODE_WRONG_OBJECT_TYPE),
1643 errmsg(
"cannot drop a template database")));
1648 (
errcode(ERRCODE_OBJECT_IN_USE),
1649 errmsg(
"cannot drop the currently open database")));
1661 (
errcode(ERRCODE_OBJECT_IN_USE),
1662 errmsg(
"database \"%s\" is used by an active logical replication slot",
1665 "There are %d active slots.",
1666 nslots_active, nslots_active)));
1677 (
errcode(ERRCODE_OBJECT_IN_USE),
1678 errmsg(
"database \"%s\" is being used by logical replication subscription",
1681 "There are %d subscriptions.",
1682 nsubscriptions, nsubscriptions)));
1700 (
errcode(ERRCODE_OBJECT_IN_USE),
1701 errmsg(
"database \"%s\" is being accessed by other users",
1728 elog(
ERROR,
"cache lookup failed for database %u", db_id);
1821 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL))
1823 (
errcode(ERRCODE_UNDEFINED_DATABASE),
1824 errmsg(
"database \"%s\" does not exist", oldname)));
1834 (
errcode(ERRCODE_INSUFFICIENT_PRIVILEGE),
1835 errmsg(
"permission denied to rename database")));
1841 #ifdef ENFORCE_REGRESSION_TEST_NAME_RESTRICTIONS
1842 if (strstr(newname,
"regression") == NULL)
1843 elog(
WARNING,
"databases created by regression test cases should have names including \"regression\"");
1852 (
errcode(ERRCODE_DUPLICATE_DATABASE),
1853 errmsg(
"database \"%s\" already exists", newname)));
1863 (
errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
1864 errmsg(
"current database cannot be renamed")));
1874 (
errcode(ERRCODE_OBJECT_IN_USE),
1875 errmsg(
"database \"%s\" is being accessed by other users",
1882 elog(
ERROR,
"cache lookup failed for database %u", db_id);
1931 NULL, NULL, NULL, NULL, &src_tblspcoid, NULL, NULL, NULL, NULL, NULL, NULL))
1933 (
errcode(ERRCODE_UNDEFINED_DATABASE),
1957 (
errcode(ERRCODE_OBJECT_IN_USE),
1958 errmsg(
"cannot change the tablespace of the currently open database")));
1977 if (dst_tblspcoid == GLOBALTABLESPACE_OID)
1979 (
errcode(ERRCODE_INVALID_PARAMETER_VALUE),
1980 errmsg(
"pg_global cannot be used as default tablespace")));
1985 if (src_tblspcoid == dst_tblspcoid)
2001 (
errcode(ERRCODE_OBJECT_IN_USE),
2002 errmsg(
"database \"%s\" is being accessed by other users",
2056 while ((xlde =
ReadDir(dstdir, dst_dbpath)) != NULL)
2058 if (strcmp(xlde->
d_name,
".") == 0 ||
2059 strcmp(xlde->
d_name,
"..") == 0)
2063 (
errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
2064 errmsg(
"some relations of database \"%s\" are already in tablespace \"%s\"",
2066 errhint(
"You must move them back to the database's default tablespace before using this command.")));
2075 if (rmdir(dst_dbpath) != 0)
2076 elog(
ERROR,
"could not remove directory \"%s\": %m",
2091 Datum new_record[Natts_pg_database] = {0};
2092 bool new_record_nulls[Natts_pg_database] = {0};
2093 bool new_record_repl[Natts_pg_database] = {0};
2098 copydir(src_dbpath, dst_dbpath,
false);
2106 xlrec.
db_id = db_id;
2123 Anum_pg_database_datname,
2131 (
errcode(ERRCODE_UNDEFINED_DATABASE),
2134 new_record[Anum_pg_database_dattablespace - 1] =
ObjectIdGetDatum(dst_tblspcoid);
2135 new_record_repl[Anum_pg_database_dattablespace - 1] =
true;
2139 new_record_nulls, new_record_repl);
2191 if (!
rmtree(src_dbpath,
true))
2193 (
errmsg(
"some useless files may be left behind in old database directory \"%s\"",
2202 xlrec.
db_id = db_id;
2245 foreach(lc,
stmt->options)
2249 if (strcmp(opt->
defname,
"force") == 0)
2253 (
errcode(ERRCODE_SYNTAX_ERROR),
2254 errmsg(
"unrecognized DROP DATABASE option \"%s\"", opt->
defname),
2275 bool dbistemplate =
false;
2276 bool dballowconnections =
true;
2279 DefElem *dallowconnections = NULL;
2282 Datum new_record[Natts_pg_database] = {0};
2283 bool new_record_nulls[Natts_pg_database] = {0};
2284 bool new_record_repl[Natts_pg_database] = {0};
2291 if (strcmp(defel->
defname,
"is_template") == 0)
2295 distemplate = defel;
2297 else if (strcmp(defel->
defname,
"allow_connections") == 0)
2299 if (dallowconnections)
2301 dallowconnections = defel;
2303 else if (strcmp(defel->
defname,
"connection_limit") == 0)
2309 else if (strcmp(defel->
defname,
"tablespace") == 0)
2313 dtablespace = defel;
2317 (
errcode(ERRCODE_SYNTAX_ERROR),
2331 (
errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
2332 errmsg(
"option \"%s\" cannot be specified with other options",
2341 if (distemplate && distemplate->
arg)
2343 if (dallowconnections && dallowconnections->
arg)
2345 if (dconnlimit && dconnlimit->
arg)
2350 (
errcode(ERRCODE_INVALID_PARAMETER_VALUE),
2351 errmsg(
"invalid connection limit: %d", dbconnlimit)));
2361 Anum_pg_database_datname,
2369 (
errcode(ERRCODE_UNDEFINED_DATABASE),
2370 errmsg(
"database \"%s\" does not exist",
stmt->dbname)));
2373 dboid = datform->oid;
2378 errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
2379 errmsg(
"cannot alter invalid database \"%s\"",
stmt->dbname),
2380 errhint(
"Use DROP DATABASE to drop invalid databases."));
2395 (
errcode(ERRCODE_INVALID_PARAMETER_VALUE),
2396 errmsg(
"cannot disallow connections for current database")));
2403 new_record[Anum_pg_database_datistemplate - 1] =
BoolGetDatum(dbistemplate);
2404 new_record_repl[Anum_pg_database_datistemplate - 1] =
true;
2406 if (dallowconnections)
2408 new_record[Anum_pg_database_datallowconn - 1] =
BoolGetDatum(dballowconnections);
2409 new_record_repl[Anum_pg_database_datallowconn - 1] =
true;
2413 new_record[Anum_pg_database_datconnlimit - 1] =
Int32GetDatum(dbconnlimit);
2414 new_record_repl[Anum_pg_database_datconnlimit - 1] =
true;
2418 new_record_nulls, new_record_repl);
2452 Anum_pg_database_datname,
2460 (
errcode(ERRCODE_UNDEFINED_DATABASE),
2461 errmsg(
"database \"%s\" does not exist",
stmt->dbname)));
2464 db_id = datForm->oid;
2473 datum =
heap_getattr(tuple, datForm->datlocprovider == COLLPROVIDER_ICU ? Anum_pg_database_daticulocale : Anum_pg_database_datcollate,
RelationGetDescr(rel), &isnull);
2475 elog(
ERROR,
"unexpected null in pg_database");
2479 if ((!oldversion && newversion) || (oldversion && !newversion))
2480 elog(
ERROR,
"invalid collation version change");
2481 else if (oldversion && newversion && strcmp(newversion, oldversion) != 0)
2483 bool nulls[Natts_pg_database] = {0};
2484 bool replaces[Natts_pg_database] = {0};
2488 (
errmsg(
"changing version from %s to %s",
2489 oldversion, newversion)));
2492 replaces[Anum_pg_database_datcollversion - 1] =
true;
2495 values, nulls, replaces);
2501 (
errmsg(
"version has not changed")));
2562 Anum_pg_database_datname,
2570 (
errcode(ERRCODE_UNDEFINED_DATABASE),
2574 db_id = datForm->oid;
2581 if (datForm->datdba != newOwnerId)
2583 Datum repl_val[Natts_pg_database];
2584 bool repl_null[Natts_pg_database] = {0};
2585 bool repl_repl[Natts_pg_database] = {0};
2610 (
errcode(ERRCODE_INSUFFICIENT_PRIVILEGE),
2611 errmsg(
"permission denied to change owner of database")));
2613 repl_repl[Anum_pg_database_datdba - 1] =
true;
2621 Anum_pg_database_datacl,
2627 datForm->datdba, newOwnerId);
2628 repl_repl[Anum_pg_database_datacl - 1] =
true;
2666 (
errcode(ERRCODE_UNDEFINED_OBJECT),
2667 errmsg(
"database with OID %u does not exist", dbid)));
2695 Oid *dbIdP,
Oid *ownerIdP,
2696 int *encodingP,
bool *dbIsTemplateP,
bool *dbAllowConnP,
2698 Oid *dbTablespace,
char **dbCollate,
char **dbCtype,
char **dbIculocale,
2700 char *dbLocProvider,
2701 char **dbCollversion)
2703 bool result =
false;
2728 Anum_pg_database_datname,
2774 *ownerIdP = dbform->datdba;
2777 *encodingP = dbform->encoding;
2780 *dbIsTemplateP = dbform->datistemplate;
2783 *dbAllowConnP = dbform->datallowconn;
2786 *dbFrozenXidP = dbform->datfrozenxid;
2789 *dbMinMultiP = dbform->datminmxid;
2792 *dbTablespace = dbform->dattablespace;
2795 *dbLocProvider = dbform->datlocprovider;
2810 *dbIculocale = NULL;
2826 *dbCollversion = NULL;
2851 bool result =
false;
2883 Oid *tablespace_ids;
2890 Oid dsttablespace = spcform->oid;
2895 if (dsttablespace == GLOBALTABLESPACE_OID)
2909 (
errmsg(
"some useless files may be left behind in old database directory \"%s\"",
2924 tablespace_ids = (
Oid *)
palloc(ntblspc *
sizeof(
Oid));
2926 foreach(cell, ltblspc)
2933 xlrec.
db_id = db_id;
2945 pfree(tablespace_ids);
2966 bool result =
false;
2976 Oid dsttablespace = spcform->oid;
2981 if (dsttablespace == GLOBALTABLESPACE_OID)
3009 if (notherbackends > 0 && npreparedxacts > 0)
3015 errdetail(
"There are %d other session(s) and %d prepared transaction(s) using the database.",
3016 notherbackends, npreparedxacts);
3017 else if (notherbackends > 0)
3019 "There are %d other sessions using the database.",
3024 "There are %d prepared transactions using the database.",
3051 Anum_pg_database_datname,
3070 (
errcode(ERRCODE_UNDEFINED_DATABASE),
3071 errmsg(
"database \"%s\" does not exist",
3126 elog(
ERROR,
"cache lookup failed for database %u", dboid);
3157 if (
stat(path, &st) == 0)
3160 if (only_tblspc && strstr(path,
"pg_tblspc/") == NULL)
3161 elog(
PANIC,
"requested to created invalid directory: %s", path);
3165 errmsg(
"missing directory \"%s\"", path));
3168 "creating missing directory: %s", path);
3172 errmsg(
"could not create missing directory \"%s\": %m", path));
3206 if (!
rmtree(dst_path,
true))
3209 (
errmsg(
"some useless files may be left behind in old database directory \"%s\"",
3217 parent_path =
pstrdup(dst_path);
3219 if (
stat(parent_path, &st) < 0)
3221 if (errno != ENOENT)
3223 errmsg(
"could not stat directory \"%s\": %m",
3237 if (
stat(src_path, &st) < 0 && errno == ENOENT)
3254 copydir(src_path, dst_path,
false);
3269 parent_path =
pstrdup(dbpath);
3320 if (!
rmtree(dst_path,
true))
3322 (
errmsg(
"some useless files may be left behind in old database directory \"%s\"",
3340 elog(
PANIC,
"dbase_redo: unknown op code %u", info);
Acl * aclnewowner(const Acl *old_acl, Oid oldOwnerId, Oid newOwnerId)
Oid get_role_oid(const char *rolname, bool missing_ok)
void check_can_set_role(Oid member, Oid role)
void aclcheck_error(AclResult aclerr, ObjectType objtype, const char *objectname)
AclResult object_aclcheck(Oid classid, Oid objectid, Oid roleid, AclMode mode)
bool object_ownercheck(Oid classid, Oid objectid, Oid roleid)
bool directory_is_empty(const char *path)
Oid get_tablespace_oid(const char *tablespacename, bool missing_ok)
bool allow_in_place_tablespaces
static Datum values[MAXATTR]
void DropDatabaseBuffers(Oid dbid)
BlockNumber BufferGetBlockNumber(Buffer buffer)
void CreateAndCopyRelationData(RelFileLocator src_rlocator, RelFileLocator dst_rlocator, bool permanent)
void UnlockReleaseBuffer(Buffer buffer)
void LockBuffer(Buffer buffer, int mode)
Buffer ReadBufferWithoutRelcache(RelFileLocator rlocator, ForkNumber forkNum, BlockNumber blockNum, ReadBufferMode mode, BufferAccessStrategy strategy, bool permanent)
void FlushDatabaseBuffers(Oid dbid)
#define BUFFER_LOCK_SHARE
static Page BufferGetPage(Buffer buffer)
static bool PageIsEmpty(Page page)
static Item PageGetItem(Page page, ItemId itemId)
static ItemId PageGetItemId(Page page, OffsetNumber offsetNumber)
static bool PageIsNew(Page page)
static OffsetNumber PageGetMaxOffsetNumber(Page page)
#define CStringGetTextDatum(s)
#define TextDatumGetCString(d)
TransactionId MultiXactId
#define OidIsValid(objectId)
Oid GetNewOidWithIndex(Relation relation, Oid indexId, AttrNumber oidcolumn)
void RequestCheckpoint(int flags)
void copydir(const char *fromdir, const char *todir, bool recurse)
static void remove_dbtablespaces(Oid db_id)
static void CreateDirAndVersionFile(char *dbpath, Oid dbid, Oid tsid, bool isRedo)
ObjectAddress AlterDatabaseRefreshColl(AlterDatabaseRefreshCollStmt *stmt)
bool have_createdb_privilege(void)
ObjectAddress RenameDatabase(const char *oldname, const char *newname)
char * get_database_name(Oid dbid)
Oid get_database_oid(const char *dbname, bool missing_ok)
static bool get_db_info(const char *name, LOCKMODE lockmode, Oid *dbIdP, Oid *ownerIdP, int *encodingP, bool *dbIsTemplateP, bool *dbAllowConnP, TransactionId *dbFrozenXidP, MultiXactId *dbMinMultiP, Oid *dbTablespace, char **dbCollate, char **dbCtype, char **dbIculocale, char **dbIcurules, char *dbLocProvider, char **dbCollversion)
static void movedb_failure_callback(int code, Datum arg)
static void CreateDatabaseUsingWalLog(Oid src_dboid, Oid dst_dboid, Oid src_tsid, Oid dst_tsid)
static List * ScanSourceDatabasePgClass(Oid tbid, Oid dbid, char *srcpath)
static void recovery_create_dbdir(char *path, bool only_tblspc)
ObjectAddress AlterDatabaseOwner(const char *dbname, Oid newOwnerId)
bool database_is_invalid_form(Form_pg_database datform)
Datum pg_database_collation_actual_version(PG_FUNCTION_ARGS)
static void movedb(const char *dbname, const char *tblspcname)
static List * ScanSourceDatabasePgClassPage(Page page, Buffer buf, Oid tbid, Oid dbid, char *srcpath, List *rlocatorlist, Snapshot snapshot)
void check_encoding_locale_matches(int encoding, const char *collate, const char *ctype)
Oid createdb(ParseState *pstate, const CreatedbStmt *stmt)
Oid AlterDatabase(ParseState *pstate, AlterDatabaseStmt *stmt, bool isTopLevel)
static int errdetail_busy_db(int notherbackends, int npreparedxacts)
static CreateDBRelInfo * ScanSourceDatabasePgClassTuple(HeapTupleData *tuple, Oid tbid, Oid dbid, char *srcpath)
static bool check_db_file_conflict(Oid db_id)
struct CreateDBRelInfo CreateDBRelInfo
void dbase_redo(XLogReaderState *record)
static void CreateDatabaseUsingFileCopy(Oid src_dboid, Oid dst_dboid, Oid src_tsid, Oid dst_tsid)
void DropDatabase(ParseState *pstate, DropdbStmt *stmt)
void dropdb(const char *dbname, bool missing_ok, bool force)
Oid AlterDatabaseSet(AlterDatabaseSetStmt *stmt)
static void createdb_failure_callback(int code, Datum arg)
bool database_is_invalid_oid(Oid dboid)
#define XLOG_DBASE_CREATE_WAL_LOG
#define MinSizeOfDbaseDropRec
#define XLOG_DBASE_CREATE_FILE_COPY
elog(ERROR, "%s: %s", p2, msg)
int32 defGetInt32(DefElem *def)
bool defGetBoolean(DefElem *def)
char * defGetString(DefElem *def)
void errorConflictingDefElem(DefElem *defel, ParseState *pstate)
Oid defGetObjectId(DefElem *def)
int errcode_for_file_access(void)
int errdetail(const char *fmt,...)
int errdetail_plural(const char *fmt_singular, const char *fmt_plural, unsigned long n,...)
int errhint(const char *fmt,...)
int errcode(int sqlerrcode)
int errmsg(const char *fmt,...)
#define ereport(elevel,...)
int pg_valid_server_encoding(const char *name)
bool is_encoding_supported_by_icu(int encoding)
const char * pg_encoding_to_char(int encoding)
struct dirent * ReadDir(DIR *dir, const char *dirname)
int MakePGDirectory(const char *directoryName)
int CloseTransientFile(int fd)
int OpenTransientFile(const char *fileName, int fileFlags)
DIR * AllocateDir(const char *dirname)
static char dstpath[MAXPGPATH]
#define DirectFunctionCall1(func, arg1)
#define PG_RETURN_TEXT_P(x)
BufferAccessStrategy GetAccessStrategy(BufferAccessStrategyType btype)
void systable_endscan(SysScanDesc sysscan)
HeapTuple systable_getnext(SysScanDesc sysscan)
SysScanDesc systable_beginscan(Relation heapRelation, Oid indexId, bool indexOK, Snapshot snapshot, int nkeys, ScanKey key)
bool allowSystemTableMods
void heap_inplace_update(Relation relation, HeapTuple tuple)
HeapTuple heap_getnext(TableScanDesc sscan, ScanDirection direction)
bool HeapTupleSatisfiesVisibility(HeapTuple htup, Snapshot snapshot, Buffer buffer)
HeapTuple heap_form_tuple(TupleDesc tupleDescriptor, Datum *values, bool *isnull)
HeapTuple heap_modify_tuple(HeapTuple tuple, TupleDesc tupleDesc, Datum *replValues, bool *replIsnull, bool *doReplace)
void heap_freetuple(HeapTuple htup)
HeapTupleHeaderData * HeapTupleHeader
#define HeapTupleIsValid(tuple)
static Datum heap_getattr(HeapTuple tup, int attnum, TupleDesc tupleDesc, bool *isnull)
void CatalogTupleUpdate(Relation heapRel, ItemPointer otid, HeapTuple tup)
void CatalogTupleInsert(Relation heapRel, HeapTuple tup)
void CatalogTupleDelete(Relation heapRel, ItemPointer tid)
#define PG_ENSURE_ERROR_CLEANUP(cleanup_function, arg)
#define PG_END_ENSURE_ERROR_CLEANUP(cleanup_function, arg)
invalidindex index d is invalid
#define ItemIdGetLength(itemId)
#define ItemIdIsNormal(itemId)
#define ItemIdIsDead(itemId)
#define ItemIdIsUsed(itemId)
#define ItemIdIsRedirected(itemId)
static void ItemPointerSet(ItemPointerData *pointer, BlockNumber blockNumber, OffsetNumber offNum)
Assert(fmt[strlen(fmt) - 1] !='\n')
List * lappend(List *list, void *datum)
List * lappend_oid(List *list, Oid datum)
void list_free(List *list)
void list_free_deep(List *list)
void LockSharedObject(Oid classid, Oid objid, uint16 objsubid, LOCKMODE lockmode)
void UnlockSharedObjectForSession(Oid classid, Oid objid, uint16 objsubid, LOCKMODE lockmode)
void UnlockRelationId(LockRelId *relid, LOCKMODE lockmode)
void UnlockSharedObject(Oid classid, Oid objid, uint16 objsubid, LOCKMODE lockmode)
void LockSharedObjectForSession(Oid classid, Oid objid, uint16 objsubid, LOCKMODE lockmode)
void LockRelationId(LockRelId *relid, LOCKMODE lockmode)
#define AccessExclusiveLock
char * pstrdup(const char *in)
void pfree(void *pointer)
void ForgetDatabaseSyncRequests(Oid dbid)
#define START_CRIT_SECTION()
#define CHECK_FOR_INTERRUPTS()
#define END_CRIT_SECTION()
#define InvalidMultiXactId
void namestrcpy(Name name, const char *str)
Datum namein(PG_FUNCTION_ARGS)
#define IsA(nodeptr, _type_)
#define InvokeObjectPostCreateHook(classId, objectId, subId)
#define InvokeObjectPostAlterHook(classId, objectId, subId)
#define InvokeObjectDropHook(classId, objectId, subId)
#define ObjectAddressSet(addr, class_id, object_id)
#define OffsetNumberNext(offsetNumber)
#define FirstOffsetNumber
int parser_errposition(ParseState *pstate, int location)
FormData_pg_authid * Form_pg_authid
FormData_pg_class * Form_pg_class
FormData_pg_database * Form_pg_database
#define DATCONNLIMIT_INVALID_DB
#define DATCONNLIMIT_UNLIMITED
void DropSetting(Oid databaseid, Oid roleid)
void AlterSetting(Oid databaseid, Oid roleid, VariableSetStmt *setstmt)
static int list_length(const List *l)
void icu_validate_locale(const char *loc_str)
char * get_collation_actual_version(char collprovider, const char *collcollate)
char * icu_language_tag(const char *loc_str, int elevel)
bool check_locale(int category, const char *locale, char **canonname)
void dropDatabaseDependencies(Oid databaseId)
void changeDependencyOnOwner(Oid classId, Oid objectId, Oid newOwnerId)
void copyTemplateDependencies(Oid templateDbId, Oid newDbId)
void recordDependencyOnOwner(Oid classId, Oid objectId, Oid owner)
void shdepLockAndCheckObject(Oid classId, Oid objectId)
int CountDBSubscriptions(Oid dbid)
FormData_pg_tablespace * Form_pg_tablespace
#define PG_VALID_BE_ENCODING(_enc)
void pgstat_drop_database(Oid databaseid)
int pg_mkdir_p(char *path, int omode)
int pg_strcasecmp(const char *s1, const char *s2)
void get_parent_directory(char *path)
int pg_get_encoding_from_locale(const char *ctype, bool write_message)
static Datum PointerGetDatum(const void *X)
static Datum TransactionIdGetDatum(TransactionId X)
static Datum BoolGetDatum(bool X)
static Datum ObjectIdGetDatum(Oid X)
static Pointer DatumGetPointer(Datum X)
static Datum CStringGetDatum(const char *X)
static Datum Int32GetDatum(int32 X)
static Datum CharGetDatum(char X)
static int fd(const char *x, int i)
void TerminateOtherDBBackends(Oid databaseId)
bool CountOtherDBBackends(Oid databaseId, int *nbackends, int *nprepared)
void WaitForProcSignalBarrier(uint64 generation)
uint64 EmitProcSignalBarrier(ProcSignalBarrierType type)
@ PROCSIGNAL_BARRIER_SMGRRELEASE
#define RelationGetDescr(relation)
RelFileNumber RelationMapOidToFilenumberForDatabase(char *dbpath, Oid relationId)
void RelationMapCopy(Oid dbid, Oid tsid, char *srcdbpath, char *dstdbpath)
char * GetDatabasePath(Oid dbOid, Oid spcOid)
#define InvalidRelFileNumber
#define RelFileNumberIsValid(relnumber)
bool rmtree(const char *path, bool rmtopdir)
const char * quote_identifier(const char *ident)
void ScanKeyInit(ScanKey entry, AttrNumber attributeNumber, StrategyNumber strategy, RegProcedure procedure, Datum argument)
void DeleteSharedSecurityLabel(Oid objectId, Oid classId)
bool ReplicationSlotsCountDBSlots(Oid dboid, int *nslots, int *nactive)
void ReplicationSlotsDropDBSlots(Oid dboid)
BlockNumber smgrnblocks(SMgrRelation reln, ForkNumber forknum)
void smgrclose(SMgrRelation reln)
SMgrRelation smgropen(RelFileLocator rlocator, BackendId backend)
Snapshot GetLatestSnapshot(void)
void PopActiveSnapshot(void)
void ResolveRecoveryConflictWithDatabase(Oid dbid)
#define BTEqualStrategyNumber
CreateDBStrategy strategy
Oid tablespace_ids[FLEXIBLE_ARRAY_MEMBER]
void ReleaseSysCache(HeapTuple tuple)
HeapTuple SearchSysCache1(int cacheId, Datum key1)
Datum SysCacheGetAttr(int cacheId, HeapTuple tup, AttrNumber attributeNumber, bool *isNull)
Datum SysCacheGetAttrNotNull(int cacheId, HeapTuple tup, AttrNumber attributeNumber)
#define SearchSysCacheCopy1(cacheId, key1)
void table_close(Relation relation, LOCKMODE lockmode)
Relation table_open(Oid relationId, LOCKMODE lockmode)
TableScanDesc table_beginscan_catalog(Relation relation, int nkeys, struct ScanKeyData *key)
static void table_endscan(TableScanDesc scan)
#define InvalidTransactionId
#define FirstNormalObjectId
text * cstring_to_text(const char *s)
static void pgstat_report_wait_start(uint32 wait_event_info)
static void pgstat_report_wait_end(void)
void PreventInTransactionBlock(bool isTopLevel, const char *stmtType)
void StartTransactionCommand(void)
void ForceSyncCommit(void)
void CommitTransactionCommand(void)
bool RecoveryInProgress(void)
XLogRecPtr XactLastRecEnd
void XLogFlush(XLogRecPtr record)
#define CHECKPOINT_FLUSH_ALL
#define CHECKPOINT_IMMEDIATE
void XLogRegisterData(char *data, uint32 len)
XLogRecPtr XLogInsert(RmgrId rmid, uint8 info)
void XLogBeginInsert(void)
#define XLogRecGetInfo(decoder)
#define XLogRecGetData(decoder)
#define XLogRecHasAnyBlockRefs(decoder)
#define XLR_SPECIAL_REL_UPDATE
void XLogDropDatabase(Oid dbid)