* ALTER TABLE ALTER COLUMN SET STORAGE * * Return value is the address of the modified column */
| 10140 | * Return value is the address of the modified column |
| 10141 | */ |
| 10142 | static ObjectAddress |
| 10143 | ATExecSetStorage(Relation rel, const char *colName, Node *newValue, LOCKMODE lockmode) |
| 10144 | { |
| 10145 | char *storagemode; |
| 10146 | char newstorage; |
| 10147 | Relation attrelation; |
| 10148 | HeapTuple tuple; |
| 10149 | Form_pg_attribute attrtuple; |
| 10150 | AttrNumber attnum; |
| 10151 | ObjectAddress address; |
| 10152 | |
| 10153 | Assert(IsA(newValue, String)); |
| 10154 | storagemode = strVal(newValue); |
| 10155 | |
| 10156 | if (pg_strcasecmp(storagemode, "plain") == 0) |
| 10157 | newstorage = TYPSTORAGE_PLAIN; |
| 10158 | else if (pg_strcasecmp(storagemode, "external") == 0) |
| 10159 | newstorage = TYPSTORAGE_EXTERNAL; |
| 10160 | else if (pg_strcasecmp(storagemode, "extended") == 0) |
| 10161 | newstorage = TYPSTORAGE_EXTENDED; |
| 10162 | else if (pg_strcasecmp(storagemode, "main") == 0) |
| 10163 | newstorage = TYPSTORAGE_MAIN; |
| 10164 | else |
| 10165 | { |
| 10166 | ereport(ERROR, |
| 10167 | (errcode(ERRCODE_INVALID_PARAMETER_VALUE), |
| 10168 | errmsg("invalid storage type \"%s\"", |
| 10169 | storagemode))); |
| 10170 | newstorage = 0; /* keep compiler quiet */ |
| 10171 | } |
| 10172 | |
| 10173 | attrelation = table_open(AttributeRelationId, RowExclusiveLock); |
| 10174 | |
| 10175 | tuple = SearchSysCacheCopyAttName(RelationGetRelid(rel), colName); |
| 10176 | |
| 10177 | if (!HeapTupleIsValid(tuple)) |
| 10178 | ereport(ERROR, |
| 10179 | (errcode(ERRCODE_UNDEFINED_COLUMN), |
| 10180 | errmsg("column \"%s\" of relation \"%s\" does not exist", |
| 10181 | colName, RelationGetRelationName(rel)))); |
| 10182 | attrtuple = (Form_pg_attribute) GETSTRUCT(tuple); |
| 10183 | |
| 10184 | attnum = attrtuple->attnum; |
| 10185 | if (attnum <= 0) |
| 10186 | ereport(ERROR, |
| 10187 | (errcode(ERRCODE_FEATURE_NOT_SUPPORTED), |
| 10188 | errmsg("cannot alter system column \"%s\"", |
| 10189 | colName))); |
| 10190 | |
| 10191 | /* |
| 10192 | * safety check: do not allow toasted storage modes unless column datatype |
| 10193 | * is TOAST-aware. |
| 10194 | */ |
| 10195 | if (newstorage == TYPSTORAGE_PLAIN || TypeIsToastable(attrtuple->atttypid)) |
| 10196 | attrtuple->attstorage = newstorage; |
| 10197 | else |
| 10198 | ereport(ERROR, |
| 10199 | (errcode(ERRCODE_FEATURE_NOT_SUPPORTED), |
no test coverage detected