diff --git a/src/pl/plpgsql/src/pl_exec.c b/src/pl/plpgsql/src/pl_exec.c
index d09c9fc234270af3eaf652b04970d538eb15e666..04403fa5640b01d4d98aa52d0b4a14c059094b6d 100644
--- a/src/pl/plpgsql/src/pl_exec.c
+++ b/src/pl/plpgsql/src/pl_exec.c
@@ -3,7 +3,7 @@
  *			  procedural language
  *
  * IDENTIFICATION
- *	  $PostgreSQL: pgsql/src/pl/plpgsql/src/pl_exec.c,v 1.145 2005/06/20 20:44:44 tgl Exp $
+ *	  $PostgreSQL: pgsql/src/pl/plpgsql/src/pl_exec.c,v 1.146 2005/06/20 22:51:29 tgl Exp $
  *
  *	  This software is copyrighted by Jan Wieck - Hamburg.
  *
@@ -2012,11 +2012,30 @@ plpgsql_estate_setup(PLpgSQL_execstate *estate,
 	estate->eval_tuptable = NULL;
 	estate->eval_processed = 0;
 	estate->eval_lastoid = InvalidOid;
-	estate->eval_econtext = NULL;
 
 	estate->err_func = func;
 	estate->err_stmt = NULL;
 	estate->err_text = NULL;
+
+	/*
+	 * Create an EState for evaluation of simple expressions, if there's
+	 * not one already in the current transaction.	The EState is made a
+	 * child of TopTransactionContext so it will have the right lifespan.
+	 */
+	if (simple_eval_estate == NULL)
+	{
+		MemoryContext oldcontext;
+
+		oldcontext = MemoryContextSwitchTo(TopTransactionContext);
+		simple_eval_estate = CreateExecutorState();
+		MemoryContextSwitchTo(oldcontext);
+	}
+
+	/*
+	 * Create an expression context for simple expressions.
+	 * This must be a child of simple_eval_estate.
+	 */
+	estate->eval_econtext = CreateExprContext(simple_eval_estate);
 }
 
 /* ----------
@@ -3264,6 +3283,8 @@ exec_eval_datum(PLpgSQL_execstate *estate,
 				Datum *value,
 				bool *isnull)
 {
+	MemoryContext oldcontext;
+
 	switch (datum->dtype)
 	{
 		case PLPGSQL_DTYPE_VAR:
@@ -3290,9 +3311,11 @@ exec_eval_datum(PLpgSQL_execstate *estate,
 					elog(ERROR, "row variable has no tupdesc");
 				/* Make sure we have a valid type/typmod setting */
 				BlessTupleDesc(row->rowtupdesc);
+				oldcontext = MemoryContextSwitchTo(estate->eval_econtext->ecxt_per_tuple_memory);
 				tup = make_tuple_from_row(estate, row, row->rowtupdesc);
 				if (tup == NULL)	/* should not happen */
 					elog(ERROR, "row not compatible with its own tupdesc");
+				MemoryContextSwitchTo(oldcontext);
 				*typeid = row->rowtupdesc->tdtypeid;
 				*value = HeapTupleGetDatum(tup);
 				*isnull = false;
@@ -3325,10 +3348,12 @@ exec_eval_datum(PLpgSQL_execstate *estate,
 				 * fields. Copy the tuple body and insert the right
 				 * values.
 				 */
+				oldcontext = MemoryContextSwitchTo(estate->eval_econtext->ecxt_per_tuple_memory);
 				heap_copytuple_with_tuple(rec->tup, &worktup);
 				HeapTupleHeaderSetDatumLength(worktup.t_data, worktup.t_len);
 				HeapTupleHeaderSetTypeId(worktup.t_data, rec->tupdesc->tdtypeid);
 				HeapTupleHeaderSetTypMod(worktup.t_data, rec->tupdesc->tdtypmod);
+				MemoryContextSwitchTo(oldcontext);
 				*typeid = rec->tupdesc->tdtypeid;
 				*value = HeapTupleGetDatum(&worktup);
 				*isnull = false;
@@ -3605,7 +3630,7 @@ exec_eval_simple_expr(PLpgSQL_execstate *estate,
 					  Oid *rettype)
 {
 	Datum		retval;
-	ExprContext * volatile econtext;
+	ExprContext *econtext = estate->eval_econtext;
 	ParamListInfo paramLI;
 	int			i;
 	Snapshot	saveActiveSnapshot;
@@ -3615,20 +3640,6 @@ exec_eval_simple_expr(PLpgSQL_execstate *estate,
 	 */
 	*rettype = expr->expr_simple_type;
 
-	/*
-	 * Create an EState for evaluation of simple expressions, if there's
-	 * not one already in the current transaction.	The EState is made a
-	 * child of TopTransactionContext so it will have the right lifespan.
-	 */
-	if (simple_eval_estate == NULL)
-	{
-		MemoryContext oldcontext;
-
-		oldcontext = MemoryContextSwitchTo(TopTransactionContext);
-		simple_eval_estate = CreateExecutorState();
-		MemoryContextSwitchTo(oldcontext);
-	}
-
 	/*
 	 * Prepare the expression for execution, if it's not been done already
 	 * in the current transaction.
@@ -3642,18 +3653,6 @@ exec_eval_simple_expr(PLpgSQL_execstate *estate,
 		active_simple_exprs = expr;
 	}
 
-	/*
-	 * Create an expression context for simple expressions, if there's not
-	 * one already in the current function call.  This must be a child of
-	 * simple_eval_estate.
-	 */
-	econtext = estate->eval_econtext;
-	if (econtext == NULL)
-	{
-		econtext = CreateExprContext(simple_eval_estate);
-		estate->eval_econtext = econtext;
-	}
-
 	/*
 	 * Param list can live in econtext's temporary memory context.
 	 *