diff --git a/contrib/pg_upgrade/check.c b/contrib/pg_upgrade/check.c
new file mode 100644
index fdec6e3..376d25a
*** a/contrib/pg_upgrade/check.c
--- b/contrib/pg_upgrade/check.c
*************** static void check_old_cluster_has_new_cl
*** 16,21 ****
--- 16,22 ----
  static void check_locale_and_encoding(ControlData *oldctrl,
  						  ControlData *newctrl);
  static void check_is_super_user(ClusterInfo *cluster);
+ static void check_for_prepared_transactions(ClusterInfo *cluster);
  static void check_for_isn_and_int8_passing_mismatch(ClusterInfo *cluster);
  static void check_for_reg_data_type_usage(ClusterInfo *cluster);
  
*************** check_old_cluster(bool live_check,
*** 65,70 ****
--- 66,72 ----
  	 * Check for various failure cases
  	 */
  	check_is_super_user(&old_cluster);
+ 	check_for_prepared_transactions(&old_cluster);
  	check_for_reg_data_type_usage(&old_cluster);
  	check_for_isn_and_int8_passing_mismatch(&old_cluster);
  
*************** check_new_cluster(void)
*** 117,122 ****
--- 119,125 ----
  	get_db_and_rel_infos(&new_cluster);
  
  	check_new_cluster_is_empty();
+ 	check_for_prepared_transactions(&new_cluster);
  	check_old_cluster_has_new_cluster_dbs();
  
  	check_loadable_libraries();
*************** check_is_super_user(ClusterInfo *cluster
*** 507,512 ****
--- 510,545 ----
  
  
  /*
+  *	check_for_prepared_transactions()
+  *
+  *	Make sure there are no prepared transactions because the storage format
+  *	might have changed.
+  */
+ static void
+ check_for_prepared_transactions(ClusterInfo *cluster)
+ {
+ 	PGresult   *res;
+ 	PGconn	   *conn = connectToServer(cluster, "template1");
+ 
+ 	prep_status("Checking for prepared transactions");
+ 
+ 	res = executeQueryOrDie(conn,
+ 							"SELECT * "
+ 							"FROM pg_catalog.pg_prepared_xact()");
+ 
+ 	if (PQntuples(res) != 0)
+ 		pg_log(PG_FATAL, "The %s cluster contains prepared transactions\n",
+ 			   CLUSTER_NAME(cluster));
+ 
+ 	PQclear(res);
+ 
+ 	PQfinish(conn);
+ 
+ 	check_ok();
+ }
+ 
+ 
+ /*
   *	check_for_isn_and_int8_passing_mismatch()
   *
   *	contrib/isn relies on data type int8, and in 8.4 int8 can now be passed
