From 251282d4b7bf7593cece7c4ce5669beb778604e3 Mon Sep 17 00:00:00 2001
From: Tom Lane <tgl@sss.pgh.pa.us>
Date: Wed, 20 Mar 2002 19:41:47 +0000
Subject: [PATCH] Tweak behavior of array slicing operations: seems like it
 ought to be okay to omit low-order dimensions when accessing an array slice.

---
 src/backend/utils/adt/arrayfuncs.c | 31 ++++++++++++++++++++++++------
 1 file changed, 25 insertions(+), 6 deletions(-)

diff --git a/src/backend/utils/adt/arrayfuncs.c b/src/backend/utils/adt/arrayfuncs.c
index 4458f71af78..f69f06359ba 100644
--- a/src/backend/utils/adt/arrayfuncs.c
+++ b/src/backend/utils/adt/arrayfuncs.c
@@ -8,7 +8,7 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/utils/adt/arrayfuncs.c,v 1.76 2002/03/16 22:47:13 tgl Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/utils/adt/arrayfuncs.c,v 1.77 2002/03/20 19:41:47 tgl Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -907,10 +907,10 @@ array_get_slice(ArrayType *array,
 	 * with an empty slice, return NULL (should it be an empty array
 	 * instead?)
 	 */
-	if (ndim != nSubscripts || ndim <= 0 || ndim > MAXDIM)
+	if (ndim < nSubscripts || ndim <= 0 || ndim > MAXDIM)
 		RETURN_NULL(ArrayType *);
 
-	for (i = 0; i < ndim; i++)
+	for (i = 0; i < nSubscripts; i++)
 	{
 		if (lowerIndx[i] < lb[i])
 			lowerIndx[i] = lb[i];
@@ -919,8 +919,16 @@ array_get_slice(ArrayType *array,
 		if (lowerIndx[i] > upperIndx[i])
 			RETURN_NULL(ArrayType *);
 	}
+	/* fill any missing subscript positions with full array range */
+	for (; i < ndim; i++)
+	{
+		lowerIndx[i] = lb[i];
+		upperIndx[i] = dim[i] + lb[i] - 1;
+		if (lowerIndx[i] > upperIndx[i])
+			RETURN_NULL(ArrayType *);
+	}
 
-	mda_get_range(nSubscripts, span, lowerIndx, upperIndx);
+	mda_get_range(ndim, span, lowerIndx, upperIndx);
 
 	bytes = array_slice_size(ndim, dim, lb, arraydataptr,
 							 elmlen, lowerIndx, upperIndx);
@@ -1120,6 +1128,9 @@ array_set(ArrayType *array,
  *		  A new array is returned, just like the old except for the
  *		  modified range.
  *
+ * NOTE: we assume it is OK to scribble on the provided index arrays
+ * lowerIndx[] and upperIndx[].  These are generally just temporaries.
+ *
  * NOTE: For assignments, we throw an error for silly subscripts etc,
  * rather than returning a NULL as the fetch operations do.  The reasoning
  * is that returning a NULL would cause the user's whole array to be replaced
@@ -1172,7 +1183,7 @@ array_set_slice(ArrayType *array,
 	/* note: we assume srcArray contains no toasted elements */
 
 	ndim = ARR_NDIM(array);
-	if (ndim != nSubscripts || ndim <= 0 || ndim > MAXDIM)
+	if (ndim < nSubscripts || ndim <= 0 || ndim > MAXDIM)
 		elog(ERROR, "Invalid array subscripts");
 
 	/* copy dim/lb since we may modify them */
@@ -1185,7 +1196,7 @@ array_set_slice(ArrayType *array,
 	 * extend the array as long as no hole is created. An empty slice is
 	 * an error, too.
 	 */
-	for (i = 0; i < ndim; i++)
+	for (i = 0; i < nSubscripts; i++)
 	{
 		if (lowerIndx[i] > upperIndx[i])
 			elog(ERROR, "Invalid array subscripts");
@@ -1207,6 +1218,14 @@ array_set_slice(ArrayType *array,
 				elog(ERROR, "Invalid array subscripts");
 		}
 	}
+	/* fill any missing subscript positions with full array range */
+	for (; i < ndim; i++)
+	{
+		lowerIndx[i] = lb[i];
+		upperIndx[i] = dim[i] + lb[i] - 1;
+		if (lowerIndx[i] > upperIndx[i])
+			elog(ERROR, "Invalid array subscripts");
+	}
 
 	/*
 	 * Make sure source array has enough entries.  Note we ignore the
-- 
GitLab