diff --git a/src/test/regress/expected/plpgsql.out b/src/test/regress/expected/plpgsql.out
index 268626ea0eba25b3757ff25c6b9469d39513cf23..5e742797d1d956a68a1302cee2cc60ed1ff4c954 100644
--- a/src/test/regress/expected/plpgsql.out
+++ b/src/test/regress/expected/plpgsql.out
@@ -2011,7 +2011,7 @@ NOTICE:  caught numeric_value_out_of_range or cardinality_violation
 (1 row)
 
 create temp table foo (f1 int);
-create function blockme() returns int as $$
+create function subxact_rollback_semantics() returns int as $$
 declare x int;
 begin
   x := 1;
@@ -2019,28 +2019,20 @@ begin
   begin
     x := x + 1;
     insert into foo values(x);
-    -- we assume this will take longer than 2 seconds:
-    select count(*) into x from tenk1 a, tenk1 b, tenk1 c;
+    raise exception 'inner';
   exception
     when others then
-      raise notice 'caught others?';
-      return -1;
-    when query_canceled then
-      raise notice 'nyeah nyeah, can''t stop me';
       x := x * 10;
   end;
   insert into foo values(x);
   return x;
 end$$ language plpgsql;
-set statement_timeout to 2000;
-select blockme();
-NOTICE:  nyeah nyeah, can't stop me
- blockme 
----------
-      20
+select subxact_rollback_semantics();
+ subxact_rollback_semantics 
+----------------------------
+                         20
 (1 row)
 
-reset statement_timeout;
 select * from foo;
  f1 
 ----
@@ -2049,6 +2041,29 @@ select * from foo;
 (2 rows)
 
 drop table foo;
+create function trap_timeout() returns void as $$
+begin
+  declare x int;
+  begin
+    -- we assume this will take longer than 2 seconds:
+    select count(*) into x from tenk1 a, tenk1 b, tenk1 c;
+  exception
+    when others then
+      raise notice 'caught others?';
+    when query_canceled then
+      raise notice 'nyeah nyeah, can''t stop me';
+  end;
+  -- Abort transaction to abandon the statement_timeout setting.  Otherwise,
+  -- the next top-level statement would be vulnerable to the timeout.
+  raise exception 'end of function';
+end$$ language plpgsql;
+begin;
+set statement_timeout to 2000;
+select trap_timeout();
+NOTICE:  nyeah nyeah, can't stop me
+ERROR:  end of function
+CONTEXT:  PL/pgSQL function trap_timeout() line 15 at RAISE
+rollback;
 -- Test for pass-by-ref values being stored in proper context
 create function test_variable_storage() returns text as $$
 declare x text;
diff --git a/src/test/regress/expected/prepared_xacts.out b/src/test/regress/expected/prepared_xacts.out
index c0b08649e8d8b4543e47384a2a2975f590151ec7..ef7034b588487628e2b3181da402a5ec7d4fbd7a 100644
--- a/src/test/regress/expected/prepared_xacts.out
+++ b/src/test/regress/expected/prepared_xacts.out
@@ -194,10 +194,11 @@ SELECT gid FROM pg_prepared_xacts;
 (2 rows)
 
 -- pxtest3 should be locked because of the pending DROP
+begin;
 set statement_timeout to 2000;
 SELECT * FROM pxtest3;
 ERROR:  canceling statement due to statement timeout
-reset statement_timeout;
+rollback;
 -- Disconnect, we will continue testing in a different backend
 \c -
 -- There should still be two prepared transactions
@@ -209,10 +210,11 @@ SELECT gid FROM pg_prepared_xacts;
 (2 rows)
 
 -- pxtest3 should still be locked because of the pending DROP
+begin;
 set statement_timeout to 2000;
 SELECT * FROM pxtest3;
 ERROR:  canceling statement due to statement timeout
-reset statement_timeout;
+rollback;
 -- Commit table creation
 COMMIT PREPARED 'regress-one';
 \d pxtest2
diff --git a/src/test/regress/expected/prepared_xacts_1.out b/src/test/regress/expected/prepared_xacts_1.out
index 898f278c11ed8aab20ea1a6bc45a2fcabda04dbc..5078bf6ba987785a21ca4631c83b3c292b253c0f 100644
--- a/src/test/regress/expected/prepared_xacts_1.out
+++ b/src/test/regress/expected/prepared_xacts_1.out
@@ -198,13 +198,14 @@ SELECT gid FROM pg_prepared_xacts;
 (0 rows)
 
 -- pxtest3 should be locked because of the pending DROP
+begin;
 set statement_timeout to 2000;
 SELECT * FROM pxtest3;
  fff 
 -----
 (0 rows)
 
-reset statement_timeout;
+rollback;
 -- Disconnect, we will continue testing in a different backend
 \c -
 -- There should still be two prepared transactions
@@ -214,13 +215,14 @@ SELECT gid FROM pg_prepared_xacts;
 (0 rows)
 
 -- pxtest3 should still be locked because of the pending DROP
+begin;
 set statement_timeout to 2000;
 SELECT * FROM pxtest3;
  fff 
 -----
 (0 rows)
 
-reset statement_timeout;
+rollback;
 -- Commit table creation
 COMMIT PREPARED 'regress-one';
 ERROR:  prepared transaction with identifier "regress-one" does not exist
diff --git a/src/test/regress/sql/plpgsql.sql b/src/test/regress/sql/plpgsql.sql
index d76004424e570a4672d935397387afd5fc7d93c7..4f27e02227b7fc6bc331c6af2b7a0b3ef9a17213 100644
--- a/src/test/regress/sql/plpgsql.sql
+++ b/src/test/regress/sql/plpgsql.sql
@@ -1745,7 +1745,7 @@ select trap_matching_test(1);
 
 create temp table foo (f1 int);
 
-create function blockme() returns int as $$
+create function subxact_rollback_semantics() returns int as $$
 declare x int;
 begin
   x := 1;
@@ -1753,29 +1753,40 @@ begin
   begin
     x := x + 1;
     insert into foo values(x);
+    raise exception 'inner';
+  exception
+    when others then
+      x := x * 10;
+  end;
+  insert into foo values(x);
+  return x;
+end$$ language plpgsql;
+
+select subxact_rollback_semantics();
+select * from foo;
+drop table foo;
+
+create function trap_timeout() returns void as $$
+begin
+  declare x int;
+  begin
     -- we assume this will take longer than 2 seconds:
     select count(*) into x from tenk1 a, tenk1 b, tenk1 c;
   exception
     when others then
       raise notice 'caught others?';
-      return -1;
     when query_canceled then
       raise notice 'nyeah nyeah, can''t stop me';
-      x := x * 10;
   end;
-  insert into foo values(x);
-  return x;
+  -- Abort transaction to abandon the statement_timeout setting.  Otherwise,
+  -- the next top-level statement would be vulnerable to the timeout.
+  raise exception 'end of function';
 end$$ language plpgsql;
 
+begin;
 set statement_timeout to 2000;
-
-select blockme();
-
-reset statement_timeout;
-
-select * from foo;
-
-drop table foo;
+select trap_timeout();
+rollback;
 
 -- Test for pass-by-ref values being stored in proper context
 create function test_variable_storage() returns text as $$
diff --git a/src/test/regress/sql/prepared_xacts.sql b/src/test/regress/sql/prepared_xacts.sql
index 7902152775c70751ff8ceaf67114559f5736ac04..dfb20a18e7c972367e82e33536c3a2e988cb7788 100644
--- a/src/test/regress/sql/prepared_xacts.sql
+++ b/src/test/regress/sql/prepared_xacts.sql
@@ -122,9 +122,10 @@ SELECT * FROM pxtest2;
 SELECT gid FROM pg_prepared_xacts;
 
 -- pxtest3 should be locked because of the pending DROP
+begin;
 set statement_timeout to 2000;
 SELECT * FROM pxtest3;
-reset statement_timeout;
+rollback;
 
 -- Disconnect, we will continue testing in a different backend
 \c -
@@ -133,9 +134,10 @@ reset statement_timeout;
 SELECT gid FROM pg_prepared_xacts;
 
 -- pxtest3 should still be locked because of the pending DROP
+begin;
 set statement_timeout to 2000;
 SELECT * FROM pxtest3;
-reset statement_timeout;
+rollback;
 
 -- Commit table creation
 COMMIT PREPARED 'regress-one';