33 #include "utils/fmgroids.h"
50 #define AARR_FREE_IF_COPY(array,n) \
52 if (!VARATT_IS_EXPANDED_HEADER(array)) \
53 PG_FREE_IF_COPY(array, n); \
92 int *dim,
int *lBound,
93 const char *origStr,
Node *escontext);
95 const char *origStr,
Node *escontext);
99 int typlen,
bool typbyval,
char typalign,
100 int *ndim_p,
int *dim,
102 Datum **values_p,
bool **nulls_p,
103 const char *origStr,
Node *escontext);
105 const char *origStr,
Node *escontext);
108 int typlen,
bool typbyval,
char typalign,
110 bool *hasnulls,
int32 *nbytes);
112 int nSubscripts,
int *indx,
114 int elmlen,
bool elmbyval,
char elmalign,
117 int nSubscripts,
int *indx,
118 Datum dataValue,
bool isNull,
120 int elmlen,
bool elmbyval,
char elmalign);
125 int typlen,
bool typbyval,
char typalign,
128 int typlen,
bool typbyval,
char typalign);
132 char *srcptr,
int offset,
bits8 *nullbitmap,
133 int typlen,
bool typbyval,
char typalign);
135 int ndim,
int *dim,
int *lb,
137 int typlen,
bool typbyval,
char typalign);
139 int ndim,
int *dim,
int *lb,
140 char *arraydataptr,
bits8 *arraynullsptr,
142 int typlen,
bool typbyval,
char typalign);
145 int ndim,
int *dim,
int *lb,
147 int typlen,
bool typbyval,
char typalign);
150 Oid elmtype,
int dataoffset);
155 Datum search,
bool search_isnull,
156 Datum replace,
bool replace_isnull,
157 bool remove,
Oid collation,
185 Node *escontext = fcinfo->context;
210 if (my_extra == NULL)
231 typlen = my_extra->
typlen;
263 (
errcode(ERRCODE_INVALID_TEXT_REPRESENTATION),
264 errmsg(
"malformed array literal: \"%s\"",
string),
265 errdetail(
"Array value must start with \"{\" or dimension information.")));
272 (
errcode(ERRCODE_INVALID_TEXT_REPRESENTATION),
273 errmsg(
"malformed array literal: \"%s\"",
string),
274 errdetail(
"Missing \"%s\" after array dimensions.",
283 (
errcode(ERRCODE_INVALID_TEXT_REPRESENTATION),
284 errmsg(
"malformed array literal: \"%s\"",
string),
285 errdetail(
"Array contents must start with \"{\".")));
290 &my_extra->
proc, typioparam, typmod,
306 (
errcode(ERRCODE_INVALID_TEXT_REPRESENTATION),
307 errmsg(
"malformed array literal: \"%s\"",
string),
308 errdetail(
"Junk after closing right brace.")));
334 (
errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
335 errmsg(
"array size exceeds the maximum allowed (%d)",
342 nbytes += dataoffset;
364 memcpy(
ARR_DIMS(retval), dim, ndim *
sizeof(
int));
365 memcpy(
ARR_LBOUND(retval), lBound, ndim *
sizeof(
int));
403 const char *origStr,
Node *escontext)
430 (
errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
431 errmsg(
"number of array dimensions exceeds the maximum allowed (%d)",
439 (
errcode(ERRCODE_INVALID_TEXT_REPRESENTATION),
440 errmsg(
"malformed array literal: \"%s\"", origStr),
441 errdetail(
"\"[\" must introduce explicitly-specified array dimensions.")));
453 (
errcode(ERRCODE_INVALID_TEXT_REPRESENTATION),
454 errmsg(
"malformed array literal: \"%s\"", origStr),
455 errdetail(
"Missing array dimension value.")));
465 (
errcode(ERRCODE_INVALID_TEXT_REPRESENTATION),
466 errmsg(
"malformed array literal: \"%s\"", origStr),
467 errdetail(
"Missing \"%s\" after array dimensions.",
478 if (ub < lBound[ndim])
480 (
errcode(ERRCODE_ARRAY_SUBSCRIPT_ERROR),
481 errmsg(
"upper bound cannot be less than lower bound")));
486 (
errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
487 errmsg(
"array upper bound is too large: %d", ub)));
493 (
errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
494 errmsg(
"array size exceeds the maximum allowed (%d)",
520 const char *origStr,
Node *escontext)
526 if (!isdigit((
unsigned char) *p) && *p !=
'-' && *p !=
'+')
533 l = strtol(p, srcptr, 10);
537 (
errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
538 errmsg(
"array bound is out of integer range")));
596 bool dimensions_specified = (ndim != 0);
621 ndim_frozen = dimensions_specified;
622 expect_delim =
false;
627 tok =
ReadArrayToken(srcptr, &elembuf, typdelim, origStr, escontext);
635 (
errcode(ERRCODE_INVALID_TEXT_REPRESENTATION),
636 errmsg(
"malformed array literal: \"%s\"", origStr),
637 errdetail(
"Unexpected \"%c\" character.",
'{')));
642 (
errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
643 errmsg(
"number of array dimensions exceeds the maximum allowed (%d)",
646 nelems[nest_level] = 0;
648 if (nest_level > ndim)
652 goto dimension_error;
665 if (nelems[nest_level - 1] > 0 && !expect_delim)
667 (
errcode(ERRCODE_INVALID_TEXT_REPRESENTATION),
668 errmsg(
"malformed array literal: \"%s\"", origStr),
669 errdetail(
"Unexpected \"%c\" character.",
674 nelems[nest_level - 1]++;
681 if (dim[nest_level] < 0)
684 dim[nest_level] = nelems[nest_level];
686 else if (nelems[nest_level] != dim[nest_level])
689 goto dimension_error;
702 (
errcode(ERRCODE_INVALID_TEXT_REPRESENTATION),
703 errmsg(
"malformed array literal: \"%s\"", origStr),
704 errdetail(
"Unexpected \"%c\" character.",
706 expect_delim =
false;
717 (
errcode(ERRCODE_INVALID_TEXT_REPRESENTATION),
718 errmsg(
"malformed array literal: \"%s\"", origStr),
719 errdetail(
"Unexpected array element.")));
726 (
errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
727 errmsg(
"array size exceeds the maximum allowed (%d)",
750 if (nest_level != ndim)
751 goto dimension_error;
753 nelems[nest_level - 1]++;
762 }
while (nest_level > 0);
774 if (dimensions_specified)
776 (
errcode(ERRCODE_INVALID_TEXT_REPRESENTATION),
777 errmsg(
"malformed array literal: \"%s\"", origStr),
778 errdetail(
"Specified array dimensions do not match array contents.")));
781 (
errcode(ERRCODE_INVALID_TEXT_REPRESENTATION),
782 errmsg(
"malformed array literal: \"%s\"", origStr),
783 errdetail(
"Multidimensional arrays must have sub-arrays with matching dimensions.")));
797 const char *origStr,
Node *escontext)
832 goto unquoted_element;
860 while (*(++p) !=
'\0')
862 if (*p == typdelim || *p ==
'}' || *p ==
'{')
869 (
errcode(ERRCODE_INVALID_TEXT_REPRESENTATION),
870 errmsg(
"malformed array literal: \"%s\"", origStr),
871 errdetail(
"Incorrectly quoted array element.")));
896 (
errcode(ERRCODE_INVALID_TEXT_REPRESENTATION),
897 errmsg(
"malformed array literal: \"%s\"", origStr),
898 errdetail(
"Unexpected \"%c\" character.",
903 (
errcode(ERRCODE_INVALID_TEXT_REPRESENTATION),
904 errmsg(
"malformed array literal: \"%s\"", origStr),
905 errdetail(
"Incorrectly quoted array element.")));
912 dstlen = elembuf->
len;
917 if (*p == typdelim || *p ==
'}')
920 elembuf->
data[dstlen] =
'\0';
921 elembuf->
len = dstlen;
932 dstlen = elembuf->
len;
940 (
errcode(ERRCODE_INVALID_TEXT_REPRESENTATION),
941 errmsg(
"malformed array literal: \"%s\"", origStr),
981 if (nulls && nulls[
i])
984 elog(
ERROR,
"null array element where not supported");
997 if (bitmask == 0x100)
1006 if (bitmap && bitmask != 1)
1028 dims_str[(
MAXDIM * 33) + 2];
1037 size_t overall_length;
1055 if (my_extra == NULL)
1076 typlen = my_extra->
typlen;
1096 for (
i = 0;
i < ndim;
i++)
1129 overall_length += 4;
1144 for (tmp =
values[
i]; *tmp !=
'\0'; tmp++)
1148 overall_length += 1;
1149 if (ch ==
'"' || ch ==
'\\')
1152 overall_length += 1;
1154 else if (ch ==
'{' || ch ==
'}' || ch == typdelim ||
1160 needquotes[
i] = needquote;
1164 overall_length += 2;
1166 overall_length += 1;
1175 for (
i =
j = 0, k = 1;
i < ndim;
i++)
1177 j += k, k *= dims[
i];
1179 overall_length += 2 *
j;
1185 char *ptr = dims_str;
1187 for (
i = 0;
i < ndim;
i++)
1189 sprintf(ptr,
"[%d:%d]", lb[
i], lb[
i] + dims[
i] - 1);
1194 overall_length += ptr - dims_str;
1198 retval = (
char *)
palloc(overall_length);
1201 #define APPENDSTR(str) (strcpy(p, (str)), p += strlen(p))
1202 #define APPENDCHAR(ch) (*p++ = (ch), *p = '\0')
1207 for (
i = 0;
i < ndim;
i++)
1213 for (
i =
j;
i < ndim - 1;
i++)
1219 for (tmp =
values[k]; *tmp; tmp++)
1223 if (ch ==
'"' || ch ==
'\\')
1234 for (
i = ndim - 1;
i >= 0;
i--)
1236 if (++(indx[
i]) < dims[
i])
1254 Assert(overall_length == (p - retval + 1));
1300 (
errcode(ERRCODE_INVALID_BINARY_REPRESENTATION),
1301 errmsg(
"invalid number of dimensions: %d", ndim)));
1304 (
errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
1305 errmsg(
"number of array dimensions (%d) exceeds the maximum allowed (%d)",
1309 if (flags != 0 && flags != 1)
1311 (
errcode(ERRCODE_INVALID_BINARY_REPRESENTATION),
1312 errmsg(
"invalid array flags")));
1328 if (element_type != spec_element_type)
1333 (
errcode(ERRCODE_DATATYPE_MISMATCH),
1334 errmsg(
"binary data has array element type %u (%s) instead of expected %u (%s)",
1341 element_type = spec_element_type;
1344 for (
i = 0;
i < ndim;
i++)
1360 if (my_extra == NULL)
1377 (
errcode(ERRCODE_UNDEFINED_FUNCTION),
1378 errmsg(
"no binary input function available for type %s",
1391 typlen = my_extra->
typlen;
1399 &my_extra->
proc, typioparam, typmod,
1402 &hasnulls, &nbytes);
1406 nbytes += dataoffset;
1415 retval->
ndim = ndim;
1418 memcpy(
ARR_DIMS(retval), dim, ndim *
sizeof(
int));
1419 memcpy(
ARR_LBOUND(retval), lBound, ndim *
sizeof(
int));
1422 dataPtr, nullsPtr,
nitems,
1478 if (itemlen < -1 || itemlen > (
buf->len -
buf->cursor))
1480 (
errcode(ERRCODE_INVALID_BINARY_REPRESENTATION),
1481 errmsg(
"insufficient data left in message")));
1487 typioparam, typmod);
1498 buf->cursor += itemlen;
1502 typioparam, typmod);
1506 if (elem_buf.
cursor != itemlen)
1508 (
errcode(ERRCODE_INVALID_BINARY_REPRESENTATION),
1509 errmsg(
"improper binary format in array element %d",
1532 (
errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
1533 errmsg(
"array size exceeds the maximum allowed (%d)",
1537 *hasnulls = hasnull;
1570 if (my_extra == NULL)
1587 (
errcode(ERRCODE_UNDEFINED_FUNCTION),
1588 errmsg(
"no binary output function available for type %s",
1594 typlen = my_extra->
typlen;
1609 for (
i = 0;
i < ndim;
i++)
1693 sprintf(p,
"[%d:%d]", lb[
i], dimv[
i] + lb[
i] - 1);
1718 if (reqdim <= 0 || reqdim >
AARR_NDIM(v))
1722 result = lb[reqdim - 1];
1746 if (reqdim <= 0 || reqdim >
AARR_NDIM(v))
1752 result = dimv[reqdim - 1] + lb[reqdim - 1] - 1;
1775 if (reqdim <= 0 || reqdim >
AARR_NDIM(v))
1780 result = dimv[reqdim - 1];
1838 bits8 *arraynullsptr;
1840 if (arraytyplen > 0)
1846 fixedDim[0] = arraytyplen / elmlen;
1851 arraynullsptr = NULL;
1880 if (ndim != nSubscripts || ndim <= 0 || ndim >
MAXDIM)
1885 for (
i = 0;
i < ndim;
i++)
1887 if (indx[
i] < lb[
i] || indx[
i] >= (dim[
i] + lb[
i]))
1912 retptr =
array_seek(arraydataptr, 0, arraynullsptr, offset,
1913 elmlen, elmbyval, elmalign);
1914 return ArrayCast(retptr, elmbyval, elmlen);
1922 int nSubscripts,
int *indx,
1924 int elmlen,
bool elmbyval,
char elmalign,
1940 Assert(arraytyplen == -1);
1952 if (ndim != nSubscripts || ndim <= 0 || ndim >
MAXDIM)
1957 for (
i = 0;
i < ndim;
i++)
1959 if (indx[
i] < lb[
i] || indx[
i] >= (dim[
i] + lb[
i]))
1983 if (dnulls && dnulls[offset])
1996 return dvalues[offset];
2034 bool *upperProvided,
2035 bool *lowerProvided,
2052 bits8 *arraynullsptr;
2057 if (arraytyplen > 0)
2066 (
errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
2067 errmsg(
"slices of fixed-length arrays not implemented")));
2075 fixedDim[0] = arraytyplen / elmlen;
2081 arraynullsptr = NULL;
2101 if (ndim < nSubscripts || ndim <= 0 || ndim >
MAXDIM)
2104 for (
i = 0;
i < nSubscripts;
i++)
2106 if (!lowerProvided[
i] || lowerIndx[
i] < lb[
i])
2107 lowerIndx[
i] = lb[
i];
2108 if (!upperProvided[
i] || upperIndx[
i] >= (dim[
i] + lb[
i]))
2109 upperIndx[
i] = dim[
i] + lb[
i] - 1;
2110 if (lowerIndx[
i] > upperIndx[
i])
2114 for (;
i < ndim;
i++)
2116 lowerIndx[
i] = lb[
i];
2117 upperIndx[
i] = dim[
i] + lb[
i] - 1;
2118 if (lowerIndx[
i] > upperIndx[
i])
2126 lowerIndx, upperIndx,
2127 elmlen, elmbyval, elmalign);
2136 bytes += dataoffset;
2146 newarray->
ndim = ndim;
2149 memcpy(
ARR_DIMS(newarray), span, ndim *
sizeof(
int));
2156 for (
i = 0;
i < ndim;
i++)
2161 arraydataptr, arraynullsptr,
2162 lowerIndx, upperIndx,
2163 elmlen, elmbyval, elmalign);
2220 bits8 *oldnullbitmap;
2234 if (arraytyplen > 0)
2242 if (nSubscripts != 1)
2244 (
errcode(ERRCODE_ARRAY_SUBSCRIPT_ERROR),
2245 errmsg(
"wrong number of array subscripts")));
2247 if (indx[0] < 0 || indx[0] >= arraytyplen / elmlen)
2249 (
errcode(ERRCODE_ARRAY_SUBSCRIPT_ERROR),
2250 errmsg(
"array subscript out of range")));
2254 (
errcode(ERRCODE_NULL_VALUE_NOT_ALLOWED),
2255 errmsg(
"cannot assign null value to an element of a fixed-length array")));
2257 resultarray = (
char *)
palloc(arraytyplen);
2259 elt_ptr = (
char *) resultarray + indx[0] * elmlen;
2264 if (nSubscripts <= 0 || nSubscripts >
MAXDIM)
2266 (
errcode(ERRCODE_ARRAY_SUBSCRIPT_ERROR),
2267 errmsg(
"wrong number of array subscripts")));
2270 if (elmlen == -1 && !isNull)
2301 for (
i = 0;
i < nSubscripts;
i++)
2308 nSubscripts, dim, lb,
2310 elmlen, elmbyval, elmalign));
2313 if (ndim != nSubscripts)
2315 (
errcode(ERRCODE_ARRAY_SUBSCRIPT_ERROR),
2316 errmsg(
"wrong number of array subscripts")));
2319 memcpy(dim,
ARR_DIMS(array), ndim *
sizeof(
int));
2320 memcpy(lb,
ARR_LBOUND(array), ndim *
sizeof(
int));
2323 addedbefore = addedafter = 0;
2333 if (indx[0] < lb[0])
2340 (
errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
2341 errmsg(
"array size exceeds the maximum allowed (%d)",
2344 if (addedbefore > 1)
2347 if (indx[0] >= (dim[0] + lb[0]))
2355 (
errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
2356 errmsg(
"array size exceeds the maximum allowed (%d)",
2368 for (
i = 0;
i < ndim;
i++)
2370 if (indx[
i] < lb[
i] ||
2371 indx[
i] >= (dim[
i] + lb[
i]))
2373 (
errcode(ERRCODE_ARRAY_SUBSCRIPT_ERROR),
2374 errmsg(
"array subscript out of range")));
2392 olddatasize =
ARR_SIZE(array) - oldoverheadlen;
2398 lenafter = olddatasize;
2400 else if (addedafter)
2403 lenbefore = olddatasize;
2411 elmlen, elmbyval, elmalign);
2420 lenafter = (int) (olddatasize - lenbefore - olditemlen);
2431 newsize = overheadlen + lenbefore + newitemlen + lenafter;
2438 newarray->
ndim = ndim;
2439 newarray->
dataoffset = newhasnulls ? overheadlen : 0;
2441 memcpy(
ARR_DIMS(newarray), dim, ndim *
sizeof(
int));
2442 memcpy(
ARR_LBOUND(newarray), lb, ndim *
sizeof(
int));
2447 memcpy((
char *) newarray + overheadlen,
2448 (
char *) array + oldoverheadlen,
2452 (
char *) newarray + overheadlen + lenbefore);
2453 memcpy((
char *) newarray + overheadlen + lenbefore + newitemlen,
2454 (
char *) array + oldoverheadlen + lenbefore + olditemlen,
2483 if (addedafter == 0)
2485 oldnullbitmap, offset + 1,
2486 oldnitems - offset - 1);
2502 int nSubscripts,
int *indx,
2503 Datum dataValue,
bool isNull,
2505 int elmlen,
bool elmbyval,
char elmalign)
2525 Assert(arraytyplen == -1);
2537 memcpy(dim, eah->
dims, ndim *
sizeof(
int));
2538 memcpy(lb, eah->
lbound, ndim *
sizeof(
int));
2539 dimschanged =
false;
2554 nSubscripts *
sizeof(
int));
2556 nSubscripts *
sizeof(
int));
2560 for (
i = 0;
i < nSubscripts;
i++)
2567 else if (ndim != nSubscripts)
2569 (
errcode(ERRCODE_ARRAY_SUBSCRIPT_ERROR),
2570 errmsg(
"wrong number of array subscripts")));
2599 newhasnulls = ((dnulls != NULL) || isNull);
2600 addedbefore = addedafter = 0;
2610 if (indx[0] < lb[0])
2617 (
errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
2618 errmsg(
"array size exceeds the maximum allowed (%d)",
2622 if (addedbefore > 1)
2625 if (indx[0] >= (dim[0] + lb[0]))
2633 (
errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
2634 errmsg(
"array size exceeds the maximum allowed (%d)",
2647 for (
i = 0;
i < ndim;
i++)
2649 if (indx[
i] < lb[
i] ||
2650 indx[
i] >= (dim[
i] + lb[
i]))
2652 (
errcode(ERRCODE_ARRAY_SUBSCRIPT_ERROR),
2653 errmsg(
"array subscript out of range")));
2671 int newlen = dim[0] + dim[0] / 8;
2673 newlen =
Max(newlen, dim[0]);
2677 eah->
dnulls = dnulls = (
bool *)
2678 repalloc(dnulls, newlen *
sizeof(
bool));
2686 if (newhasnulls && dnulls == NULL)
2687 eah->
dnulls = dnulls = (
bool *)
2705 memcpy(eah->
dims, dim, ndim *
sizeof(
int));
2706 memcpy(eah->
lbound, lb, ndim *
sizeof(
int));
2710 if (addedbefore > 0)
2712 memmove(dvalues + addedbefore, dvalues, eah->
nelems *
sizeof(
Datum));
2713 for (
i = 0;
i < addedbefore;
i++)
2717 memmove(dnulls + addedbefore, dnulls, eah->
nelems *
sizeof(
bool));
2718 for (
i = 0;
i < addedbefore;
i++)
2721 eah->
nelems += addedbefore;
2727 for (
i = 0;
i < addedafter;
i++)
2731 for (
i = 0;
i < addedafter;
i++)
2732 dnulls[eah->
nelems +
i] =
true;
2734 eah->
nelems += addedafter;
2738 if (!eah->
typbyval && (dnulls == NULL || !dnulls[offset]))
2744 dvalues[offset] = dataValue;
2746 dnulls[offset] = isNull;
2756 if (oldValue < eah->fstartptr || oldValue >= eah->
fendptr)
2810 bool *upperProvided,
2811 bool *lowerProvided,
2812 Datum srcArrayDatum,
2848 if (arraytyplen > 0)
2854 (
errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
2855 errmsg(
"updates on slices of fixed-length arrays not implemented")));
2879 &dvalues, &dnulls, &nelems);
2881 for (
i = 0;
i < nSubscripts;
i++)
2883 if (!upperProvided[
i] || !lowerProvided[
i])
2885 (
errcode(ERRCODE_ARRAY_SUBSCRIPT_ERROR),
2886 errmsg(
"array slice subscript must provide both boundaries"),
2887 errdetail(
"When assigning to a slice of an empty array value,"
2888 " slice boundaries must be fully specified.")));
2894 (
errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
2895 errmsg(
"array size exceeds the maximum allowed (%d)",
2898 lb[
i] = lowerIndx[
i];
2904 (
errcode(ERRCODE_ARRAY_SUBSCRIPT_ERROR),
2905 errmsg(
"source array too small")));
2909 elmlen, elmbyval, elmalign));
2912 if (ndim < nSubscripts || ndim <= 0 || ndim >
MAXDIM)
2914 (
errcode(ERRCODE_ARRAY_SUBSCRIPT_ERROR),
2915 errmsg(
"wrong number of array subscripts")));
2918 memcpy(dim,
ARR_DIMS(array), ndim *
sizeof(
int));
2919 memcpy(lb,
ARR_LBOUND(array), ndim *
sizeof(
int));
2922 addedbefore = addedafter = 0;
2932 Assert(nSubscripts == 1);
2933 if (!lowerProvided[0])
2934 lowerIndx[0] = lb[0];
2935 if (!upperProvided[0])
2936 upperIndx[0] = dim[0] + lb[0] - 1;
2937 if (lowerIndx[0] > upperIndx[0])
2939 (
errcode(ERRCODE_ARRAY_SUBSCRIPT_ERROR),
2940 errmsg(
"upper bound cannot be less than lower bound")));
2941 if (lowerIndx[0] < lb[0])
2948 (
errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
2949 errmsg(
"array size exceeds the maximum allowed (%d)",
2951 lb[0] = lowerIndx[0];
2952 if (addedbefore > 1)
2955 if (upperIndx[0] >= (dim[0] + lb[0]))
2963 (
errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
2964 errmsg(
"array size exceeds the maximum allowed (%d)",
2976 for (
i = 0;
i < nSubscripts;
i++)
2978 if (!lowerProvided[
i])
2979 lowerIndx[
i] = lb[
i];
2980 if (!upperProvided[
i])
2981 upperIndx[
i] = dim[
i] + lb[
i] - 1;
2982 if (lowerIndx[
i] > upperIndx[
i])
2984 (
errcode(ERRCODE_ARRAY_SUBSCRIPT_ERROR),
2985 errmsg(
"upper bound cannot be less than lower bound")));
2986 if (lowerIndx[
i] < lb[
i] ||
2987 upperIndx[
i] >= (dim[
i] + lb[
i]))
2989 (
errcode(ERRCODE_ARRAY_SUBSCRIPT_ERROR),
2990 errmsg(
"array subscript out of range")));
2993 for (;
i < ndim;
i++)
2995 lowerIndx[
i] = lb[
i];
2996 upperIndx[
i] = dim[
i] + lb[
i] - 1;
2997 if (lowerIndx[
i] > upperIndx[
i])
2999 (
errcode(ERRCODE_ARRAY_SUBSCRIPT_ERROR),
3000 errmsg(
"upper bound cannot be less than lower bound")));
3016 (
errcode(ERRCODE_ARRAY_SUBSCRIPT_ERROR),
3017 errmsg(
"source array too small")));
3029 elmlen, elmbyval, elmalign);
3031 olddatasize =
ARR_SIZE(array) - oldoverheadlen;
3041 lowerIndx, upperIndx,
3042 elmlen, elmbyval, elmalign);
3043 lenbefore = lenafter = 0;
3044 itemsbefore = itemsafter = nolditems = 0;
3053 int oldub = oldlb +
ARR_DIMS(array)[0] - 1;
3054 int slicelb =
Max(oldlb, lowerIndx[0]);
3055 int sliceub =
Min(oldub, upperIndx[0]);
3060 itemsbefore =
Min(slicelb, oldub + 1) - oldlb;
3063 elmlen, elmbyval, elmalign);
3065 if (slicelb > sliceub)
3072 nolditems = sliceub - slicelb + 1;
3074 itemsbefore, oldarraybitmap,
3076 elmlen, elmbyval, elmalign);
3079 itemsafter = oldub + 1 -
Max(sliceub + 1, oldlb);
3080 lenafter = olddatasize - lenbefore - olditemsize;
3083 newsize = overheadlen + olddatasize - olditemsize + newitemsize;
3087 newarray->
ndim = ndim;
3088 newarray->
dataoffset = newhasnulls ? overheadlen : 0;
3090 memcpy(
ARR_DIMS(newarray), dim, ndim *
sizeof(
int));
3091 memcpy(
ARR_LBOUND(newarray), lb, ndim *
sizeof(
int));
3101 lowerIndx, upperIndx,
3102 elmlen, elmbyval, elmalign);
3107 memcpy((
char *) newarray + overheadlen,
3108 (
char *) array + oldoverheadlen,
3110 memcpy((
char *) newarray + overheadlen + lenbefore,
3113 memcpy((
char *) newarray + overheadlen + lenbefore + newitemsize,
3114 (
char *) array + oldoverheadlen + lenbefore + olditemsize,
3130 oldnullbitmap, itemsbefore + nolditems,
3147 int arraytyplen,
int elmlen,
bool elmbyval,
char elmalign,
3151 arraytyplen, elmlen, elmbyval, elmalign,
3164 Datum dataValue,
bool isNull,
3165 int arraytyplen,
int elmlen,
bool elmbyval,
char elmalign)
3171 elmlen, elmbyval, elmalign));
3257 inp_typlen = inp_extra->
typlen;
3258 inp_typbyval = inp_extra->
typbyval;
3259 inp_typalign = inp_extra->
typalign;
3269 typlen = ret_extra->
typlen;
3286 inp_typlen, inp_typbyval, inp_typalign);
3304 (
errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
3305 errmsg(
"array size exceeds the maximum allowed (%d)",
3314 nbytes += dataoffset;
3323 result->
ndim = ndim;
3363 int elmlen,
bool elmbyval,
char elmalign)
3372 elmtype, elmlen, elmbyval, elmalign);
3392 elmalign = TYPALIGN_CHAR;
3398 elmalign = TYPALIGN_CHAR;
3404 elmalign = TYPALIGN_INT;
3408 elmlen =
sizeof(
int16);
3410 elmalign = TYPALIGN_SHORT;
3414 elmlen =
sizeof(
int32);
3416 elmalign = TYPALIGN_INT;
3420 elmlen =
sizeof(int64);
3422 elmalign = TYPALIGN_DOUBLE;
3428 elmalign = TYPALIGN_CHAR;
3433 elmlen =
sizeof(
Oid);
3435 elmalign = TYPALIGN_INT;
3441 elmalign = TYPALIGN_INT;
3447 elmalign = TYPALIGN_SHORT;
3451 elog(
ERROR,
"type %u not supported by construct_array_builtin()", elmtype);
3458 return construct_array(elems, nelems, elmtype, elmlen, elmbyval, elmalign);
3487 Oid elmtype,
int elmlen,
bool elmbyval,
char elmalign)
3498 (
errcode(ERRCODE_INVALID_PARAMETER_VALUE),
3499 errmsg(
"invalid number of dimensions: %d", ndims)));
3502 (
errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
3503 errmsg(
"number of array dimensions (%d) exceeds the maximum allowed (%d)",
3517 for (
i = 0;
i < nelems;
i++)
3519 if (nulls && nulls[
i])
3532 (
errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
3533 errmsg(
"array size exceeds the maximum allowed (%d)",
3541 nbytes += dataoffset;
3550 result->
ndim = ndims;
3553 memcpy(
ARR_DIMS(result), dims, ndims *
sizeof(
int));
3554 memcpy(
ARR_LBOUND(result), lbs, ndims *
sizeof(
int));
3557 elems, nulls, nelems,
3558 elmlen, elmbyval, elmalign,
3621 int elmlen,
bool elmbyval,
char elmalign,
3622 Datum **elemsp,
bool **nullsp,
int *nelemsp)
3637 *nullsp = nulls = (
bool *)
palloc0(nelems *
sizeof(
bool));
3646 for (
i = 0;
i < nelems;
i++)
3649 if (bitmap && (*bitmap & bitmask) == 0)
3656 (
errcode(ERRCODE_NULL_VALUE_NOT_ALLOWED),
3657 errmsg(
"null array element not allowed in this context")));
3670 if (bitmask == 0x100)
3687 Datum **elemsp,
bool **nullsp,
int *nelemsp)
3698 elmalign = TYPALIGN_CHAR;
3704 elmalign = TYPALIGN_CHAR;
3710 elmalign = TYPALIGN_DOUBLE;
3714 elmlen =
sizeof(
int16);
3716 elmalign = TYPALIGN_SHORT;
3720 elmlen =
sizeof(
Oid);
3722 elmalign = TYPALIGN_INT;
3728 elmalign = TYPALIGN_INT;
3734 elmalign = TYPALIGN_SHORT;
3738 elog(
ERROR,
"type %u not supported by deconstruct_array_builtin()", elmtype);
3745 deconstruct_array(array, elmtype, elmlen, elmbyval, elmalign, elemsp, nullsp, nelemsp);
3772 if (*bitmap != 0xFF)
3782 if ((*bitmap & bitmask) == 0)
3827 (
errcode(ERRCODE_DATATYPE_MISMATCH),
3828 errmsg(
"cannot compare arrays of different element types")));
3831 if (ndims1 != ndims2 ||
3832 memcmp(dims1, dims2, ndims1 *
sizeof(
int)) != 0 ||
3833 memcmp(lbs1, lbs2, ndims1 *
sizeof(
int)) != 0)
3844 if (typentry == NULL ||
3845 typentry->
type_id != element_type)
3851 (
errcode(ERRCODE_UNDEFINED_FUNCTION),
3852 errmsg(
"could not identify an equality operator for type %s",
3854 fcinfo->flinfo->fn_extra = (
void *) typentry;
3856 typlen = typentry->
typlen;
3864 collation, NULL, NULL);
3888 if (isnull1 && isnull2)
3890 if (isnull1 || isnull2)
3899 locfcinfo->args[0].value = elt1;
3900 locfcinfo->args[0].isnull =
false;
3901 locfcinfo->args[1].value = elt2;
3902 locfcinfo->args[1].isnull =
false;
3903 locfcinfo->isnull =
false;
3905 if (locfcinfo->isnull || !oprresult)
3998 (
errcode(ERRCODE_DATATYPE_MISMATCH),
3999 errmsg(
"cannot compare arrays of different element types")));
4008 if (typentry == NULL ||
4009 typentry->
type_id != element_type)
4015 (
errcode(ERRCODE_UNDEFINED_FUNCTION),
4016 errmsg(
"could not identify a comparison function for type %s",
4020 typlen = typentry->
typlen;
4028 collation, NULL, NULL);
4031 min_nitems =
Min(nitems1, nitems2);
4035 for (
i = 0;
i < min_nitems;
i++)
4050 if (isnull1 && isnull2)
4066 locfcinfo->args[0].value = elt1;
4067 locfcinfo->args[0].isnull =
false;
4068 locfcinfo->args[1].value = elt2;
4069 locfcinfo->args[1].isnull =
false;
4073 Assert(!locfcinfo->isnull);
4100 if (nitems1 != nitems2)
4101 result = (nitems1 < nitems2) ? -1 : 1;
4102 else if (ndims1 != ndims2)
4103 result = (ndims1 < ndims2) ? -1 : 1;
4106 for (
i = 0;
i < ndims1;
i++)
4108 if (dims1[
i] != dims2[
i])
4110 result = (dims1[
i] < dims2[
i]) ? -1 : 1;
4119 for (
i = 0;
i < ndims1;
i++)
4121 if (lbound1[
i] != lbound2[
i])
4123 result = (lbound1[
i] < lbound2[
i]) ? -1 : 1;
4169 if (typentry == NULL ||
4170 typentry->
type_id != element_type)
4176 (
errcode(ERRCODE_UNDEFINED_FUNCTION),
4177 errmsg(
"could not identify a hash function for type %s",
4187 if (element_type == RECORDOID)
4199 record_typentry =
palloc0(
sizeof(*record_typentry));
4200 record_typentry->
type_id = element_type;
4210 typentry = record_typentry;
4213 fcinfo->flinfo->fn_extra = (
void *) typentry;
4216 typlen = typentry->
typlen;
4247 locfcinfo->args[0].value = elt;
4248 locfcinfo->args[0].isnull =
false;
4251 Assert(!locfcinfo->isnull);
4265 result = (result << 5) - result + elthash;
4297 if (typentry == NULL ||
4298 typentry->
type_id != element_type)
4304 (
errcode(ERRCODE_UNDEFINED_FUNCTION),
4305 errmsg(
"could not identify an extended hash function for type %s",
4307 fcinfo->flinfo->fn_extra = (
void *) typentry;
4309 typlen = typentry->
typlen;
4336 locfcinfo->args[0].value = elt;
4337 locfcinfo->args[0].isnull =
false;
4339 locfcinfo->args[1].isnull =
false;
4342 Assert(!locfcinfo->isnull);
4345 result = (result << 5) - result + elthash;
4370 bool matchall,
void **fn_extra)
4373 bool result = matchall;
4389 (
errcode(ERRCODE_DATATYPE_MISMATCH),
4390 errmsg(
"cannot compare arrays of different element types")));
4399 if (typentry == NULL ||
4400 typentry->
type_id != element_type)
4406 (
errcode(ERRCODE_UNDEFINED_FUNCTION),
4407 errmsg(
"could not identify an equality operator for type %s",
4409 *fn_extra = (
void *) typentry;
4411 typlen = typentry->
typlen;
4430 element_type, typlen, typbyval,
typalign,
4431 &values2, &nulls2, &nelems2);
4437 collation, NULL, NULL);
4443 for (
i = 0;
i < nelems1;
i++)
4466 for (
j = 0;
j < nelems2;
j++)
4469 bool isnull2 = nulls2 ? nulls2[
j] :
false;
4478 locfcinfo->args[0].value = elt1;
4479 locfcinfo->args[0].isnull =
false;
4480 locfcinfo->args[1].value = elt2;
4481 locfcinfo->args[1].isnull =
false;
4482 locfcinfo->isnull =
false;
4484 if (!locfcinfo->isnull && oprresult)
4520 &fcinfo->flinfo->fn_extra);
4538 &fcinfo->flinfo->fn_extra);
4556 &fcinfo->flinfo->fn_extra);
4593 if (slice_ndim < 0 || slice_ndim >
ARR_NDIM(arr))
4594 elog(
ERROR,
"invalid arguments to array_create_iterator");
4599 iterator->
arr = arr;
4771 if (nullbitmap == NULL)
4773 if (nullbitmap[offset / 8] & (1 << (offset % 8)))
4790 nullbitmap += offset / 8;
4791 bitmask = 1 << (offset % 8);
4793 *nullbitmap &= ~bitmask;
4795 *nullbitmap |= bitmask;
4855 int typlen,
bool typbyval,
char typalign)
4861 if (typlen > 0 && !nullbitmap)
4867 nullbitmap += offset / 8;
4868 bitmask = 1 << (offset % 8);
4872 if (*nullbitmap & bitmask)
4878 if (bitmask == 0x100)
4903 int typlen,
bool typbyval,
char typalign)
4925 char *srcptr,
int offset,
bits8 *nullbitmap,
4926 int typlen,
bool typbyval,
char typalign)
4932 memcpy(destptr, srcptr, numbytes);
4955 const bits8 *srcbitmap,
int srcoffset,
4966 destbitmap += destoffset / 8;
4967 destbitmask = 1 << (destoffset % 8);
4968 destbitval = *destbitmap;
4971 srcbitmap += srcoffset / 8;
4972 srcbitmask = 1 << (srcoffset % 8);
4973 srcbitval = *srcbitmap;
4976 if (srcbitval & srcbitmask)
4977 destbitval |= destbitmask;
4979 destbitval &= ~destbitmask;
4981 if (destbitmask == 0x100)
4983 *destbitmap++ = destbitval;
4986 destbitval = *destbitmap;
4989 if (srcbitmask == 0x100)
4994 srcbitval = *srcbitmap;
4997 if (destbitmask != 1)
4998 *destbitmap = destbitval;
5004 destbitval |= destbitmask;
5006 if (destbitmask == 0x100)
5008 *destbitmap++ = destbitval;
5011 destbitval = *destbitmap;
5014 if (destbitmask != 1)
5015 *destbitmap = destbitval;
5026 int ndim,
int *dim,
int *lb,
5028 int typlen,
bool typbyval,
char typalign)
5044 if (typlen > 0 && !arraynullsptr)
5049 ptr =
array_seek(arraydataptr, 0, arraynullsptr, src_offset,
5053 for (
i = 0;
i < ndim;
i++)
5060 ptr =
array_seek(ptr, src_offset, arraynullsptr, dist[
j],
5062 src_offset += dist[
j];
5090 bits8 *arraynullsptr,
5111 srcdataptr =
array_seek(arraydataptr, 0, arraynullsptr, src_offset,
5116 for (
i = 0;
i < ndim;
i++)
5125 srcdataptr =
array_seek(srcdataptr, src_offset, arraynullsptr,
5128 src_offset += dist[
j];
5131 srcdataptr, src_offset, arraynullsptr,
5135 arraynullsptr, src_offset,
5192 origPtr, 0, origBitmap,
5198 orig_offset = dest_offset;
5202 for (
i = 0;
i < ndim;
i++)
5212 origPtr, orig_offset, origBitmap,
5218 origBitmap, orig_offset,
5220 dest_offset += dist[
j];
5221 orig_offset += dist[
j];
5225 srcPtr, src_offset, srcBitmap,
5229 srcBitmap, src_offset,
5236 origPtr =
array_seek(origPtr, orig_offset, origBitmap, 1,
5242 array_copy(destPtr, orignitems - orig_offset,
5243 origPtr, orig_offset, origBitmap,
5247 origBitmap, orig_offset,
5248 orignitems - orig_offset);
5289 subcontext ? 64 : 8);
5299 bool subcontext,
int initsize)
5314 astate->
alen = initsize;
5317 astate->
dnulls = (
bool *)
5339 Datum dvalue,
bool disnull,
5364 (
errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
5365 errmsg(
"array size exceeds the maximum allowed (%d)",
5369 astate->
dnulls = (
bool *)
5383 if (astate->
typlen == -1)
5416 ndims = (astate->
nelems > 0) ? 1 : 0;
5417 dims[0] = astate->
nelems;
5505 (
errcode(ERRCODE_DATATYPE_MISMATCH),
5506 errmsg(
"data type %s is not an array type",
5513 "accumArrayResultArr",
5539 Datum dvalue,
bool disnull,
5560 (
errcode(ERRCODE_NULL_VALUE_NOT_ALLOWED),
5561 errmsg(
"cannot accumulate null arrays")));
5581 if (astate->
ndims == 0)
5588 (
errcode(ERRCODE_ARRAY_SUBSCRIPT_ERROR),
5589 errmsg(
"cannot accumulate empty arrays")));
5592 (
errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
5593 errmsg(
"number of array dimensions (%d) exceeds the maximum allowed (%d)",
5600 astate->
ndims = ndims + 1;
5601 astate->
dims[0] = 0;
5602 memcpy(&astate->
dims[1], dims, ndims *
sizeof(
int));
5604 memcpy(&astate->
lbs[1], lbs, ndims *
sizeof(
int));
5613 if (astate->
ndims != ndims + 1)
5615 (
errcode(ERRCODE_ARRAY_SUBSCRIPT_ERROR),
5616 errmsg(
"cannot accumulate arrays of different dimensionality")));
5617 for (
i = 0;
i < ndims;
i++)
5619 if (astate->
dims[
i + 1] != dims[
i] || astate->
lbs[
i + 1] != lbs[
i])
5621 (
errcode(ERRCODE_ARRAY_SUBSCRIPT_ERROR),
5622 errmsg(
"cannot accumulate arrays of different dimensionality")));
5629 astate->
nbytes + ndatabytes);
5641 astate->
nbytes += ndatabytes;
5660 else if (newnitems > astate->
aitems)
5672 astate->
dims[0] += 1;
5701 if (astate->
ndims == 0)
5720 nbytes += dataoffset;
5816 Datum dvalue,
bool disnull,
5826 input_type, rcontext);
5830 input_type, rcontext);
5925 if (reqdim <= 0 || reqdim >
AARR_NDIM(v))
5937 fctx->
lower = lb[reqdim - 1];
5938 fctx->
upper = dimv[reqdim - 1] + lb[reqdim - 1] - 1;
5989 (
errcode(ERRCODE_NULL_VALUE_NOT_ALLOWED),
5990 errmsg(
"dimension array or low bound array cannot be null")));
6008 elog(
ERROR,
"could not determine data type of input");
6029 (
errcode(ERRCODE_NULL_VALUE_NOT_ALLOWED),
6030 errmsg(
"dimension array or low bound array cannot be null")));
6047 elog(
ERROR,
"could not determine data type of input");
6055 Oid elmtype,
int dataoffset)
6061 result->
ndim = ndims;
6064 memcpy(
ARR_DIMS(result), dimv, ndims *
sizeof(
int));
6065 memcpy(
ARR_LBOUND(result), lbsv, ndims *
sizeof(
int));
6091 (
errcode(ERRCODE_ARRAY_SUBSCRIPT_ERROR),
6092 errmsg(
"wrong number of array subscripts"),
6093 errdetail(
"Dimension array must be one dimensional.")));
6097 (
errcode(ERRCODE_NULL_VALUE_NOT_ALLOWED),
6098 errmsg(
"dimension values cannot be null")));
6105 (
errcode(ERRCODE_INVALID_PARAMETER_VALUE),
6106 errmsg(
"invalid number of dimensions: %d", ndims)));
6109 (
errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
6110 errmsg(
"number of array dimensions (%d) exceeds the maximum allowed (%d)",
6117 (
errcode(ERRCODE_ARRAY_SUBSCRIPT_ERROR),
6118 errmsg(
"wrong number of array subscripts"),
6119 errdetail(
"Dimension array must be one dimensional.")));
6123 (
errcode(ERRCODE_NULL_VALUE_NOT_ALLOWED),
6124 errmsg(
"dimension values cannot be null")));
6128 (
errcode(ERRCODE_ARRAY_SUBSCRIPT_ERROR),
6129 errmsg(
"wrong number of array subscripts"),
6130 errdetail(
"Low bound array has different size than dimensions array.")));
6157 if (my_extra == NULL)
6175 elmlen = my_extra->
typlen;
6195 totbytes = nbytes *
nitems;
6198 if (totbytes / nbytes !=
nitems ||
6201 (
errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
6202 errmsg(
"array size exceeds the maximum allowed (%d)",
6224 nbytes = dataoffset;
6227 elmtype, dataoffset);
6250 } array_unnest_fctx;
6253 array_unnest_fctx *fctx;
6279 fctx = (array_unnest_fctx *)
palloc(
sizeof(array_unnest_fctx));
6307 if (fctx->nextelem < fctx->numelems)
6309 int offset = fctx->nextelem++;
6313 fctx->elmlen, fctx->elmbyval, fctx->elmalign);
6368 Datum search,
bool search_isnull,
6369 Datum replace,
bool replace_isnull,
6370 bool remove,
Oid collation,
6392 bool changed =
false;
6408 if (remove && ndim > 1)
6410 (
errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
6411 errmsg(
"removing elements from multidimensional arrays is not supported")));
6418 if (typentry == NULL ||
6419 typentry->
type_id != element_type)
6425 (
errcode(ERRCODE_UNDEFINED_FUNCTION),
6426 errmsg(
"could not identify an equality operator for type %s",
6430 typlen = typentry->
typlen;
6443 if (!replace_isnull)
6449 collation, NULL, NULL);
6470 if (bitmap && (*bitmap & bitmask) == 0)
6481 else if (!replace_isnull)
6483 values[nresult] = replace;
6492 elt =
fetch_att(arraydataptr, typbyval, typlen);
6506 locfcinfo->args[0].value = elt;
6507 locfcinfo->args[0].isnull =
false;
6508 locfcinfo->args[1].value = search;
6509 locfcinfo->args[1].isnull =
false;
6510 locfcinfo->isnull =
false;
6512 if (locfcinfo->isnull || !oprresult)
6525 values[nresult] = replace;
6526 isNull = replace_isnull;
6534 nulls[nresult] = isNull;
6545 (
errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
6546 errmsg(
"array size exceeds the maximum allowed (%d)",
6556 if (bitmask == 0x100)
6586 nbytes += dataoffset;
6595 result->
ndim = ndim;
6636 search, search_isnull,
6660 search, search_isnull,
6661 replace, replace_isnull,
6687 (
errcode(ERRCODE_ARRAY_SUBSCRIPT_ERROR),
6688 errmsg(
"thresholds must be one-dimensional array")));
6692 (
errcode(ERRCODE_NULL_VALUE_NOT_ALLOWED),
6693 errmsg(
"thresholds array must not contain NULLs")));
6696 if (element_type == FLOAT8OID)
6704 if (typentry == NULL ||
6705 typentry->
type_id != element_type)
6711 (
errcode(ERRCODE_UNDEFINED_FUNCTION),
6712 errmsg(
"could not identify a comparison function for type %s",
6714 fcinfo->flinfo->fn_extra = (
void *) typentry;
6721 if (typentry->
typlen > 0)
6723 collation, typentry);
6726 collation, typentry);
6766 while (left < right)
6768 int mid = (left + right) / 2;
6770 if (isnan(thresholds_data[mid]) || op < thresholds_data[mid])
6789 char *thresholds_data;
6790 int typlen = typentry->
typlen;
6791 bool typbyval = typentry->
typbyval;
6802 collation, NULL, NULL);
6807 while (left < right)
6809 int mid = (left + right) / 2;
6813 ptr = thresholds_data + mid * typlen;
6815 locfcinfo->args[0].value = operand;
6816 locfcinfo->args[0].isnull =
false;
6817 locfcinfo->args[1].value =
fetch_att(ptr, typbyval, typlen);
6818 locfcinfo->args[1].isnull =
false;
6823 Assert(!locfcinfo->isnull);
6844 char *thresholds_data;
6845 int typlen = typentry->
typlen;
6846 bool typbyval = typentry->
typbyval;
6854 collation, NULL, NULL);
6859 while (left < right)
6861 int mid = (left + right) / 2;
6867 ptr = thresholds_data;
6868 for (
i = left;
i < mid;
i++)
6874 locfcinfo->args[0].value = operand;
6875 locfcinfo->args[0].isnull =
false;
6876 locfcinfo->args[1].value =
fetch_att(ptr, typbyval, typlen);
6877 locfcinfo->args[1].isnull =
false;
6882 Assert(!locfcinfo->isnull);
6918 bool lowerProvided[
MAXDIM];
6919 bool upperProvided[
MAXDIM];
6925 (
errcode(ERRCODE_ARRAY_ELEMENT_ERROR),
6926 errmsg(
"number of elements to trim must be between 0 and %d",
6930 memset(lowerProvided,
false,
sizeof(lowerProvided));
6931 memset(upperProvided,
false,
sizeof(upperProvided));
6935 upperProvided[0] =
true;
6944 -1, elmlen, elmbyval, elmalign);
#define PG_GETARG_ANY_ARRAY_P(n)
#define PG_GETARG_ARRAYTYPE_P(n)
#define ARR_NULLBITMAP(a)
#define ARR_OVERHEAD_WITHNULLS(ndims, nitems)
#define DatumGetArrayTypeP(X)
#define PG_RETURN_ARRAYTYPE_P(x)
#define ARR_OVERHEAD_NONULLS(ndims)
#define ARR_DATA_OFFSET(a)
ExpandedArrayHeader * DatumGetExpandedArray(Datum d)
Datum expand_array(Datum arraydatum, MemoryContext parentcontext, ArrayMetaState *metacache)
AnyArrayType * DatumGetAnyArrayP(Datum d)
void deconstruct_expanded_array(ExpandedArrayHeader *eah)
static Datum array_iter_next(array_iter *it, bool *isnull, int i, int elmlen, bool elmbyval, char elmalign)
static void array_iter_setup(array_iter *it, AnyArrayType *a)
Datum array_eq(PG_FUNCTION_ARGS)
Datum arraycontained(PG_FUNCTION_ARGS)
Datum array_lt(PG_FUNCTION_ARGS)
static bool ReadArrayStr(char **srcptr, FmgrInfo *inputproc, Oid typioparam, int32 typmod, char typdelim, int typlen, bool typbyval, char typalign, int *ndim_p, int *dim, int *nitems_p, Datum **values_p, bool **nulls_p, const char *origStr, Node *escontext)
Datum array_fill(PG_FUNCTION_ARGS)
bool array_contains_nulls(ArrayType *array)
Datum array_replace(PG_FUNCTION_ARGS)
static ArrayType * array_replace_internal(ArrayType *array, Datum search, bool search_isnull, Datum replace, bool replace_isnull, bool remove, Oid collation, FunctionCallInfo fcinfo)
Datum array_smaller(PG_FUNCTION_ARGS)
ArrayBuildState * accumArrayResult(ArrayBuildState *astate, Datum dvalue, bool disnull, Oid element_type, MemoryContext rcontext)
static bool ReadArrayDimensions(char **srcptr, int *ndim_p, int *dim, int *lBound, const char *origStr, Node *escontext)
ArrayBuildState * initArrayResult(Oid element_type, MemoryContext rcontext, bool subcontext)
Datum array_cardinality(PG_FUNCTION_ARGS)
ArrayType * construct_array_builtin(Datum *elems, int nelems, Oid elmtype)
bool array_iterate(ArrayIterator iterator, Datum *value, bool *isnull)
static Datum array_set_element_expanded(Datum arraydatum, int nSubscripts, int *indx, Datum dataValue, bool isNull, int arraytyplen, int elmlen, bool elmbyval, char elmalign)
ArrayBuildState * initArrayResultWithSize(Oid element_type, MemoryContext rcontext, bool subcontext, int initsize)
void array_free_iterator(ArrayIterator iterator)
Datum array_recv(PG_FUNCTION_ARGS)
ArrayBuildStateArr * initArrayResultArr(Oid array_type, Oid element_type, MemoryContext rcontext, bool subcontext)
Datum generate_subscripts_nodir(PG_FUNCTION_ARGS)
Datum hash_array(PG_FUNCTION_ARGS)
static int width_bucket_array_float8(Datum operand, ArrayType *thresholds)
ArrayBuildStateAny * initArrayResultAny(Oid input_type, MemoryContext rcontext, bool subcontext)
ArrayBuildStateAny * accumArrayResultAny(ArrayBuildStateAny *astate, Datum dvalue, bool disnull, Oid input_type, MemoryContext rcontext)
void CopyArrayEls(ArrayType *array, Datum *values, bool *nulls, int nitems, int typlen, bool typbyval, char typalign, bool freedata)
Datum array_dims(PG_FUNCTION_ARGS)
ArrayType * array_set(ArrayType *array, int nSubscripts, int *indx, Datum dataValue, bool isNull, int arraytyplen, int elmlen, bool elmbyval, char elmalign)
static ArrayToken ReadArrayToken(char **srcptr, StringInfo elembuf, char typdelim, const char *origStr, Node *escontext)
Datum arraycontains(PG_FUNCTION_ARGS)
static int array_slice_size(char *arraydataptr, bits8 *arraynullsptr, int ndim, int *dim, int *lb, int *st, int *endp, int typlen, bool typbyval, char typalign)
static bool array_get_isnull(const bits8 *nullbitmap, int offset)
Datum makeArrayResultArr(ArrayBuildStateArr *astate, MemoryContext rcontext, bool release)
#define AARR_FREE_IF_COPY(array, n)
Datum array_upper(PG_FUNCTION_ARGS)
Datum makeArrayResultAny(ArrayBuildStateAny *astate, MemoryContext rcontext, bool release)
static ArrayType * array_fill_internal(ArrayType *dims, ArrayType *lbs, Datum value, bool isnull, Oid elmtype, FunctionCallInfo fcinfo)
Datum array_map(Datum arrayd, ExprState *exprstate, ExprContext *econtext, Oid retType, ArrayMapState *amstate)
Datum array_set_element(Datum arraydatum, int nSubscripts, int *indx, Datum dataValue, bool isNull, int arraytyplen, int elmlen, bool elmbyval, char elmalign)
Datum makeMdArrayResult(ArrayBuildState *astate, int ndims, int *dims, int *lbs, MemoryContext rcontext, bool release)
struct ArrayIteratorData ArrayIteratorData
static bool ReadDimensionInt(char **srcptr, int *result, const char *origStr, Node *escontext)
static bool array_contain_compare(AnyArrayType *array1, AnyArrayType *array2, Oid collation, bool matchall, void **fn_extra)
Datum array_lower(PG_FUNCTION_ARGS)
static int width_bucket_array_fixed(Datum operand, ArrayType *thresholds, Oid collation, TypeCacheEntry *typentry)
static int array_cmp(FunctionCallInfo fcinfo)
ArrayIterator array_create_iterator(ArrayType *arr, int slice_ndim, ArrayMetaState *mstate)
Datum btarraycmp(PG_FUNCTION_ARGS)
ArrayType * construct_empty_array(Oid elmtype)
ArrayType * construct_array(Datum *elems, int nelems, Oid elmtype, int elmlen, bool elmbyval, char elmalign)
Datum array_ref(ArrayType *array, int nSubscripts, int *indx, int arraytyplen, int elmlen, bool elmbyval, char elmalign, bool *isNull)
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)
static Datum array_get_element_expanded(Datum arraydatum, int nSubscripts, int *indx, int arraytyplen, int elmlen, bool elmbyval, char elmalign, bool *isNull)
void deconstruct_array(ArrayType *array, Oid elmtype, int elmlen, bool elmbyval, char elmalign, Datum **elemsp, bool **nullsp, int *nelemsp)
Datum hash_array_extended(PG_FUNCTION_ARGS)
void deconstruct_array_builtin(ArrayType *array, Oid elmtype, Datum **elemsp, bool **nullsp, int *nelemsp)
Datum generate_subscripts(PG_FUNCTION_ARGS)
static void array_insert_slice(ArrayType *destArray, ArrayType *origArray, ArrayType *srcArray, int ndim, int *dim, int *lb, int *st, int *endp, int typlen, bool typbyval, char typalign)
Datum array_send(PG_FUNCTION_ARGS)
Datum array_le(PG_FUNCTION_ARGS)
static int array_copy(char *destptr, int nitems, char *srcptr, int offset, bits8 *nullbitmap, int typlen, bool typbyval, char typalign)
Datum array_gt(PG_FUNCTION_ARGS)
Datum array_unnest(PG_FUNCTION_ARGS)
static ArrayType * create_array_envelope(int ndims, int *dimv, int *lbsv, int nbytes, Oid elmtype, int dataoffset)
Datum array_remove(PG_FUNCTION_ARGS)
Datum array_ne(PG_FUNCTION_ARGS)
ArrayBuildStateArr * accumArrayResultArr(ArrayBuildStateArr *astate, Datum dvalue, bool disnull, Oid array_type, MemoryContext rcontext)
Datum array_larger(PG_FUNCTION_ARGS)
Datum array_in(PG_FUNCTION_ARGS)
static void array_extract_slice(ArrayType *newarray, int ndim, int *dim, int *lb, char *arraydataptr, bits8 *arraynullsptr, int *st, int *endp, int typlen, bool typbyval, char typalign)
static int width_bucket_array_variable(Datum operand, ArrayType *thresholds, Oid collation, TypeCacheEntry *typentry)
Datum array_length(PG_FUNCTION_ARGS)
Datum makeArrayResult(ArrayBuildState *astate, MemoryContext rcontext)
static int array_nelems_size(char *ptr, int offset, bits8 *nullbitmap, int nitems, int typlen, bool typbyval, char typalign)
static void array_set_isnull(bits8 *nullbitmap, int offset, bool isNull)
ArrayType * construct_md_array(Datum *elems, bool *nulls, int ndims, int *dims, int *lbs, Oid elmtype, int elmlen, bool elmbyval, char elmalign)
void array_bitmap_copy(bits8 *destbitmap, int destoffset, const bits8 *srcbitmap, int srcoffset, int nitems)
static int ArrayCastAndSet(Datum src, int typlen, bool typbyval, char typalign, char *dest)
static Datum ArrayCast(char *value, bool byval, int len)
Datum array_get_element(Datum arraydatum, int nSubscripts, int *indx, int arraytyplen, int elmlen, bool elmbyval, char elmalign, bool *isNull)
Datum array_out(PG_FUNCTION_ARGS)
Datum array_fill_with_lower_bounds(PG_FUNCTION_ARGS)
Datum array_ndims(PG_FUNCTION_ARGS)
static char * array_seek(char *ptr, int offset, bits8 *nullbitmap, int nitems, int typlen, bool typbyval, char typalign)
Datum array_get_slice(Datum arraydatum, int nSubscripts, int *upperIndx, int *lowerIndx, bool *upperProvided, bool *lowerProvided, int arraytyplen, int elmlen, bool elmbyval, char elmalign)
Datum array_ge(PG_FUNCTION_ARGS)
Datum width_bucket_array(PG_FUNCTION_ARGS)
Datum arrayoverlap(PG_FUNCTION_ARGS)
ExpandedArrayHeader * construct_empty_expanded_array(Oid element_type, MemoryContext parentcontext, ArrayMetaState *metacache)
Datum array_set_slice(Datum arraydatum, int nSubscripts, int *upperIndx, int *lowerIndx, bool *upperProvided, bool *lowerProvided, Datum srcArrayDatum, bool isNull, int arraytyplen, int elmlen, bool elmbyval, char elmalign)
Datum trim_array(PG_FUNCTION_ARGS)
Datum array_unnest_support(PG_FUNCTION_ARGS)
struct generate_subscripts_fctx generate_subscripts_fctx
void mda_get_offset_values(int n, int *dist, const int *prod, const int *span)
int ArrayGetOffset(int n, const int *dim, const int *lb, const int *indx)
void mda_get_range(int n, int *span, const int *st, const int *endp)
int ArrayGetNItems(int ndim, const int *dims)
void mda_get_prod(int n, const int *range, int *prod)
void ArrayCheckBounds(int ndim, const int *dims, const int *lb)
int mda_next_tuple(int n, int *curr, const int *span)
static Datum values[MAXATTR]
#define FORMAT_TYPE_ALLOW_INVALID
#define Assert(condition)
#define PointerIsValid(pointer)
#define OidIsValid(objectId)
Node * estimate_expression_value(PlannerInfo *root, Node *node)
Datum datumCopy(Datum value, bool typByVal, int typLen)
int errdetail(const char *fmt,...)
int errcode(int sqlerrcode)
int errmsg(const char *fmt,...)
#define ereturn(context, dummy_value,...)
#define ereport(elevel,...)
static Datum ExecEvalExpr(ExprState *state, ExprContext *econtext, bool *isNull)
ExpandedObjectHeader * DatumGetEOHP(Datum d)
#define VARATT_IS_EXPANDED_HEADER(PTR)
static Datum EOHPGetRWDatum(const struct ExpandedObjectHeader *eohptr)
#define repalloc_array(pointer, type, count)
#define palloc_array(type, count)
void fmgr_info(Oid functionId, FmgrInfo *finfo)
void fmgr_info_cxt(Oid functionId, FmgrInfo *finfo, MemoryContext mcxt)
Datum Int64GetDatum(int64 X)
bool InputFunctionCallSafe(FmgrInfo *flinfo, char *str, Oid typioparam, int32 typmod, fmNodePtr escontext, Datum *result)
Oid get_fn_expr_argtype(FmgrInfo *flinfo, int argnum)
bytea * SendFunctionCall(FmgrInfo *flinfo, Datum val)
char * OutputFunctionCall(FmgrInfo *flinfo, Datum val)
Datum ReceiveFunctionCall(FmgrInfo *flinfo, StringInfo buf, Oid typioparam, int32 typmod)
#define PG_FREE_IF_COPY(ptr, n)
#define PG_RETURN_UINT32(x)
#define PG_RETURN_BYTEA_P(x)
#define PG_DETOAST_DATUM_COPY(datum)
#define PG_GETARG_POINTER(n)
#define InitFunctionCallInfoData(Fcinfo, Flinfo, Nargs, Collation, Context, Resultinfo)
#define PG_RETURN_CSTRING(x)
#define PG_GETARG_DATUM(n)
#define LOCAL_FCINFO(name, nargs)
#define PG_GETARG_CSTRING(n)
#define PG_GETARG_INT64(n)
#define PG_RETURN_UINT64(x)
#define PG_DETOAST_DATUM(datum)
#define FunctionCallInvoke(fcinfo)
#define PG_RETURN_TEXT_P(x)
#define PG_RETURN_INT32(x)
#define PG_GETARG_INT32(n)
#define PG_GETARG_BOOL(n)
#define PG_RETURN_DATUM(x)
#define PG_RETURN_POINTER(x)
#define PG_GET_COLLATION()
#define PG_RETURN_BOOL(x)
#define SRF_IS_FIRSTCALL()
#define SRF_PERCALL_SETUP()
#define SRF_RETURN_NEXT(_funcctx, _result)
#define SRF_FIRSTCALL_INIT()
#define SRF_RETURN_DONE(_funcctx)
static bool pg_sub_s32_overflow(int32 a, int32 b, int32 *result)
static bool pg_add_s32_overflow(int32 a, int32 b, int32 *result)
if(TABLE==NULL||TABLE_index==NULL)
struct ItemPointerData ItemPointerData
Oid get_element_type(Oid typid)
void get_typlenbyvalalign(Oid typid, int16 *typlen, bool *typbyval, char *typalign)
void get_type_io_data(Oid typid, IOFuncSelector which_func, int16 *typlen, bool *typbyval, char *typalign, char *typdelim, Oid *typioparam, Oid *func)
Oid get_array_type(Oid typid)
char * pstrdup(const char *in)
void pfree(void *pointer)
void * palloc0(Size size)
void * MemoryContextAllocZero(MemoryContext context, Size size)
void * repalloc(void *pointer, Size size)
void * MemoryContextAlloc(MemoryContext context, Size size)
void MemoryContextDelete(MemoryContext context)
#define AllocSetContextCreate
#define ALLOCSET_DEFAULT_SIZES
#define AllocSizeIsValid(size)
static bool is_funcclause(const void *clause)
#define IsA(nodeptr, _type_)
Datum lower(PG_FUNCTION_ARGS)
Datum upper(PG_FUNCTION_ARGS)
static uint32 pg_nextpower2_32(uint32 num)
static const struct exclude_list_item skip[]
int pg_strcasecmp(const char *s1, const char *s2)
static uint32 DatumGetUInt32(Datum X)
static uint64 DatumGetUInt64(Datum X)
static bool DatumGetBool(Datum X)
static Datum PointerGetDatum(const void *X)
static float8 DatumGetFloat8(Datum X)
static Pointer DatumGetPointer(Datum X)
static Datum Int32GetDatum(int32 X)
static int32 DatumGetInt32(Datum X)
MemoryContextSwitchTo(old_ctx)
bool scanner_isspace(char ch)
double estimate_array_length(PlannerInfo *root, Node *arrayexpr)
void resetStringInfo(StringInfo str)
void appendStringInfoChar(StringInfo str, char ch)
void initStringInfo(StringInfo str)
StringInfoData * StringInfo
static void initReadOnlyStringInfo(StringInfo str, char *data, int len)
ArrayBuildStateArr * arraystate
ArrayBuildState * scalarstate
MemoryContext eoh_context
bool * innermost_casenull
Datum * innermost_caseval
MemoryContext multi_call_memory_ctx
struct PlannerInfo * root
FmgrInfo hash_extended_proc_finfo
#define FirstGenbkiObjectId
#define att_align_nominal(cur_offset, attalign)
#define att_addlength_pointer(cur_offset, attlen, attptr)
static Datum fetch_att(const void *T, bool attbyval, int attlen)
#define att_addlength_datum(cur_offset, attlen, attdatum)
static void store_att_byval(void *T, Datum newdatum, int attlen)
TypeCacheEntry * lookup_type_cache(Oid type_id, int flags)
#define TYPECACHE_HASH_PROC_FINFO
#define TYPECACHE_EQ_OPR_FINFO
#define TYPECACHE_HASH_EXTENDED_PROC_FINFO
#define TYPECACHE_CMP_PROC_FINFO
#define VARATT_IS_EXTERNAL_EXPANDED(PTR)
#define SET_VARSIZE(PTR, len)
text * cstring_to_text(const char *s)