diff --git a/src/backend/utils/adt/arrayfuncs.c b/src/backend/utils/adt/arrayfuncs.c index bfb6065..d1028be 100644 --- a/src/backend/utils/adt/arrayfuncs.c +++ b/src/backend/utils/adt/arrayfuncs.c @@ -86,7 +86,7 @@ static void ReadArrayBinary(StringInfo buf, int nitems, FmgrInfo *receiveproc, Oid typioparam, int32 typmod, int typlen, bool typbyval, char typalign, Datum *values, bool *nulls, - bool *hasnulls, int32 *nbytes); + bool *hasnulls, int32 *nbytes, bool fixedlen); static void CopyArrayEls(ArrayType *array, Datum *values, bool *nulls, int nitems, int typlen, bool typbyval, char typalign, @@ -1242,7 +1242,7 @@ array_recv(PG_FUNCTION_ARGS) ndim, MAXDIM))); flags = pq_getmsgint(buf, 4); - if (flags != 0 && flags != 1) + if ((flags & ~3) != 0) ereport(ERROR, (errcode(ERRCODE_INVALID_BINARY_REPRESENTATION), errmsg("invalid array flags"))); @@ -1327,7 +1327,7 @@ array_recv(PG_FUNCTION_ARGS) &my_extra->proc, typioparam, typmod, typlen, typbyval, typalign, dataPtr, nullsPtr, - &hasnulls, &nbytes); + &hasnulls, &nbytes, (flags & 2) != 0); if (hasnulls) { dataoffset = ARR_OVERHEAD_WITHNULLS(ndim, nitems); @@ -1390,7 +1390,8 @@ ReadArrayBinary(StringInfo buf, Datum *values, bool *nulls, bool *hasnulls, - int32 *nbytes) + int32 *nbytes, + bool fixedlen) { int i; bool hasnull; @@ -1403,7 +1404,7 @@ ReadArrayBinary(StringInfo buf, char csave; /* Get and check the item length */ - itemlen = pq_getmsgint(buf, 4); + itemlen = fixedlen ? typlen : pq_getmsgint(buf, 4); if (itemlen < -1 || itemlen > (buf->len - buf->cursor)) ereport(ERROR, (errcode(ERRCODE_INVALID_BINARY_REPRESENTATION), @@ -1496,6 +1497,7 @@ array_send(PG_FUNCTION_ARGS) int bitmask; int nitems, i; + int flags; int ndim, *dim; StringInfoData buf; @@ -1535,6 +1537,10 @@ array_send(PG_FUNCTION_ARGS) typbyval = my_extra->typbyval; typalign = my_extra->typalign; + flags = ARR_HASNULL(v) ? 1 : 0; + if (binary_minor >= 1 && flags == 0 && typlen > 0) + flags |= 2; + ndim = ARR_NDIM(v); dim = ARR_DIMS(v); nitems = ArrayGetNItems(ndim, dim); @@ -1543,7 +1549,7 @@ array_send(PG_FUNCTION_ARGS) /* Send the array header information */ pq_sendint(&buf, ndim, 4); - pq_sendint(&buf, ARR_HASNULL(v) ? 1 : 0, 4); + pq_sendint(&buf, flags, 4); pq_sendint(&buf, element_type, sizeof(Oid)); for (i = 0; i < ndim; i++) { @@ -1571,7 +1577,8 @@ array_send(PG_FUNCTION_ARGS) itemvalue = fetch_att(p, typbyval, typlen); outputbytes = SendFunctionCall(&my_extra->proc, itemvalue); - pq_sendint(&buf, VARSIZE(outputbytes) - VARHDRSZ, 4); + if ((flags & 2) == 0) + pq_sendint(&buf, VARSIZE(outputbytes) - VARHDRSZ, 4); pq_sendbytes(&buf, VARDATA(outputbytes), VARSIZE(outputbytes) - VARHDRSZ); pfree(outputbytes);