aboutsummaryrefslogtreecommitdiff
path: root/src/backend/parser/parse_target.c
diff options
context:
space:
mode:
authorTom Lane <tgl@sss.pgh.pa.us>2013-11-23 20:04:00 -0500
committerTom Lane <tgl@sss.pgh.pa.us>2013-11-23 20:04:00 -0500
commitc4d3cd3dc8514147cc8d30a648e4970a2a876ca8 (patch)
treeb024d5eb31d8b5275341bbf7d190c7467a09d811 /src/backend/parser/parse_target.c
parent69eb861695be52706217ec58830178d0a82d53ce (diff)
downloadpostgresql-c4d3cd3dc8514147cc8d30a648e4970a2a876ca8.tar.gz
postgresql-c4d3cd3dc8514147cc8d30a648e4970a2a876ca8.zip
Fix array slicing of int2vector and oidvector values.
The previous coding labeled expressions such as pg_index.indkey[1:3] as being of int2vector type; which is not right because the subscript bounds of such a result don't, in general, satisfy the restrictions of int2vector. To fix, implicitly promote the result of slicing int2vector to int2[], or oidvector to oid[]. This is similar to what we've done with domains over arrays, which is a good analogy because these types are very much like restricted domains of the corresponding regular-array types. A side-effect is that we now also forbid array-element updates on such columns, eg while "update pg_index set indkey[4] = 42" would have worked before if you were superuser (and corrupted your catalogs irretrievably, no doubt) it's now disallowed. This seems like a good thing since, again, some choices of subscripting would've led to results not satisfying the restrictions of int2vector. The case of an array-slice update was rejected before, though with a different error message than you get now. We could make these cases work in future if we added a cast from int2[] to int2vector (with a cast function checking the subscript restrictions) but it seems unlikely that there's any value in that. Per report from Ronan Dunklau. Back-patch to all supported branches because of the crash risks involved.
Diffstat (limited to 'src/backend/parser/parse_target.c')
-rw-r--r--src/backend/parser/parse_target.c8
1 files changed, 5 insertions, 3 deletions
diff --git a/src/backend/parser/parse_target.c b/src/backend/parser/parse_target.c
index 9c6c202c8e6..d56e00ffde6 100644
--- a/src/backend/parser/parse_target.c
+++ b/src/backend/parser/parse_target.c
@@ -839,18 +839,20 @@ transformAssignmentSubscripts(ParseState *pstate,
/* If target was a domain over array, need to coerce up to the domain */
if (arrayType != targetTypeId)
{
+ Oid resulttype = exprType(result);
+
result = coerce_to_target_type(pstate,
- result, exprType(result),
+ result, resulttype,
targetTypeId, targetTypMod,
COERCION_ASSIGNMENT,
COERCE_IMPLICIT_CAST,
-1);
- /* probably shouldn't fail, but check */
+ /* can fail if we had int2vector/oidvector, but not for true domains */
if (result == NULL)
ereport(ERROR,
(errcode(ERRCODE_CANNOT_COERCE),
errmsg("cannot cast type %s to %s",
- format_type_be(exprType(result)),
+ format_type_be(resulttype),
format_type_be(targetTypeId)),
parser_errposition(pstate, location)));
}