88 *
99 *
1010 * IDENTIFICATION
11- * $Header: /cvsroot/pgsql/src/backend/executor/spi.c,v 1.101 2003/08/04 02:39:59 momjian Exp $
11+ * $Header: /cvsroot/pgsql/src/backend/executor/spi.c,v 1.102 2003/08/08 19:18:21 tgl Exp $
1212 *
1313 *-------------------------------------------------------------------------
1414 */
@@ -1263,6 +1263,8 @@ static void
12631263_SPI_cursor_operation (Portal portal ,bool forward ,int count ,
12641264DestReceiver * dest )
12651265{
1266+ long nfetched ;
1267+
12661268/* Check that the portal is valid */
12671269if (!PortalIsValid (portal ))
12681270elog (ERROR ,"invalid portal in SPI cursor operation" );
@@ -1277,11 +1279,20 @@ _SPI_cursor_operation(Portal portal, bool forward, int count,
12771279_SPI_current -> tuptable = NULL ;
12781280
12791281/* Run the cursor */
1280- _SPI_current -> processed =
1281- PortalRunFetch (portal ,
1282- forward ?FETCH_FORWARD :FETCH_BACKWARD ,
1283- (long )count ,
1284- dest );
1282+ nfetched = PortalRunFetch (portal ,
1283+ forward ?FETCH_FORWARD :FETCH_BACKWARD ,
1284+ (long )count ,
1285+ dest );
1286+
1287+ /*
1288+ * Think not to combine this store with the preceding function call.
1289+ * If the portal contains calls to functions that use SPI, then
1290+ * SPI_stack is likely to move around while the portal runs. When
1291+ * control returns, _SPI_current will point to the correct stack entry...
1292+ * but the pointer may be different than it was beforehand. So we must
1293+ * be sure to re-fetch the pointer after the function call completes.
1294+ */
1295+ _SPI_current -> processed = nfetched ;
12851296
12861297if (dest -> mydest == SPI && _SPI_checktuples ())
12871298elog (ERROR ,"consistency check on SPI tuple count failed" );