@@ -1978,8 +1978,6 @@ CopyFrom(CopyState cstate)
19781978 * ROLLBACK TO save;
19791979 * COPY ...
19801980 *
1981- * However this is OK since at worst we will fail to make the optimization.
1982- *
19831981 * Also, if the target file is new-in-transaction, we assume that checking
19841982 * FSM for free space is a waste of time, even if we must use WAL because
19851983 * of archiving. This could possibly be wrong, but it's unlikely.
@@ -1991,6 +1989,7 @@ CopyFrom(CopyState cstate)
19911989 * no additional work to enforce that.
19921990 *----------
19931991 */
1992+ /* createSubid is creation check, newRelfilenodeSubid is truncation check */
19941993 if (cstate -> rel -> rd_createSubid != InvalidSubTransactionId ||
19951994 cstate -> rel -> rd_newRelfilenodeSubid != InvalidSubTransactionId )
19961995 {
@@ -2006,18 +2005,27 @@ CopyFrom(CopyState cstate)
20062005 * after xact cleanup. Note that the stronger test of exactly
20072006 * which subtransaction created it is crucial for correctness
20082007 * of this optimisation.
2009- *
2010- * As noted above rd_newRelfilenodeSubid is not set in all cases
2011- * where we can apply the optimization, so in those rare cases
2012- * where we cannot honour the request we do so silently.
20132008 */
2014- if (cstate -> freeze &&
2015- ThereAreNoPriorRegisteredSnapshots () &&
2016- ThereAreNoReadyPortals () &&
2017- (cstate -> rel -> rd_newRelfilenodeSubid == GetCurrentSubTransactionId () ||
2018- cstate -> rel -> rd_createSubid == GetCurrentSubTransactionId ()))
2019- hi_options |= HEAP_INSERT_FROZEN ;
2009+ if (cstate -> freeze )
2010+ {
2011+ if (!ThereAreNoPriorRegisteredSnapshots () || !ThereAreNoReadyPortals ())
2012+ ereport (ERROR ,
2013+ (ERRCODE_INVALID_TRANSACTION_STATE ,
2014+ errmsg ("cannot perform FREEZE because of prior transaction activity" )));
2015+
2016+ if (cstate -> rel -> rd_createSubid == GetCurrentSubTransactionId () ||
2017+ cstate -> rel -> rd_newRelfilenodeSubid == GetCurrentSubTransactionId ())
2018+ hi_options |= HEAP_INSERT_FROZEN ;
2019+ else
2020+ ereport (ERROR ,
2021+ (ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE ,
2022+ errmsg ("cannot perform FREEZE because of transaction activity after table creation or truncation" )));
2023+ }
20202024 }
2025+ else if (cstate -> freeze )
2026+ ereport (ERROR ,
2027+ (ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE ,
2028+ errmsg ("cannot perform FREEZE because the table was not created or truncated in the current transaction" )));
20212029
20222030 /*
20232031 * We need a ResultRelInfo so we can use the regular executor's
0 commit comments