8
0
mirror of https://github.com/FirebirdSQL/firebird.git synced 2025-01-22 23:23:02 +01:00

Objects are not allowed to live on the stack if you want to ask a pool of their type.

This commit is contained in:
tamlin 2002-01-04 19:03:49 +00:00
parent 8921cd2368
commit f3eb5e8233

View File

@ -40,6 +40,7 @@
#include "../jrd/thd_proto.h" #include "../jrd/thd_proto.h"
#include "../jrd/tpc_proto.h" #include "../jrd/tpc_proto.h"
#include "../jrd/tra_proto.h" #include "../jrd/tra_proto.h"
#include <memory>
static TPC allocate_tpc(TDBB, ULONG); static TPC allocate_tpc(TDBB, ULONG);
static void cache_transactions(TDBB, TPC *, ULONG); static void cache_transactions(TDBB, TPC *, ULONG);
@ -197,67 +198,74 @@ int TPC_snapshot_state(TDBB tdbb, SLONG number)
* further checking to see if it really is. * further checking to see if it really is.
* *
**************************************/ **************************************/
DBB dbb;
TPC tip_cache;
USHORT state;
SET_TDBB(tdbb); SET_TDBB(tdbb);
dbb = tdbb->tdbb_database; DBB dbb = tdbb->tdbb_database;
CHECK_DBB(dbb); CHECK_DBB(dbb);
if (!(tip_cache = dbb->dbb_tip_cache)) { TPC tip_cache = dbb->dbb_tip_cache;
if (!tip_cache) {
cache_transactions(tdbb, (TPC *) 0, (ULONG) 0); cache_transactions(tdbb, (TPC *) 0, (ULONG) 0);
tip_cache = dbb->dbb_tip_cache; tip_cache = dbb->dbb_tip_cache;
} }
if (number && dbb->dbb_pc_transactions) if (number && dbb->dbb_pc_transactions) {
if (TRA_precommited(tdbb, number, number)) if (TRA_precommited(tdbb, number, number)) {
return tra_precommitted; return tra_precommitted;
}
}
/* if the transaction is older than the oldest /* if the transaction is older than the oldest
transaction in our tip cache, it must be committed */ transaction in our tip cache, it must be committed */
if (number < tip_cache->tpc_base) if (number < tip_cache->tpc_base) {
return tra_committed; return tra_committed;
}
/* locate the specific TIP cache block for the transaction */ /* locate the specific TIP cache block for the transaction */
for (; tip_cache; tip_cache = tip_cache->tpc_next) for (; tip_cache; tip_cache = tip_cache->tpc_next)
if (number < tip_cache->tpc_base + dbb->dbb_pcontrol->pgc_tpt) { {
struct lck temp_lock; if (number < tip_cache->tpc_base + dbb->dbb_pcontrol->pgc_tpt)
{
state = const USHORT state =
TRA_state(tip_cache->tpc_transactions, tip_cache->tpc_base, TRA_state( tip_cache->tpc_transactions,
tip_cache->tpc_base,
number); number);
/* committed or dead transactions always stay that /* committed or dead transactions always stay that
way, so no need to check their current state */ way, so no need to check their current state */
if (state == tra_committed || state == tra_dead) if (state == tra_committed || state == tra_dead) {
return state; return state;
}
/* see if we can get a lock on the transaction; if we can't // see if we can get a lock on the transaction; if we can't
then we know it is still active */ // then we know it is still active
// We need to create this one in a pool since the
// receiver of this (ptr) checks its type.
// Please review this. This lock has _nothing_ to do in the
// permamnent pool!
std::auto_ptr<lck> temp_lock(new(*dbb->dbb_permanent, 0) lck);
MOVE_CLEAR(&temp_lock, sizeof(struct lck));
//temp_lock.blk_type = type_lck; //temp_lock.blk_type = type_lck;
temp_lock.lck_dbb = dbb; temp_lock->lck_dbb = dbb;
temp_lock.lck_type = LCK_tra; temp_lock->lck_type = LCK_tra;
temp_lock.lck_owner_handle = temp_lock->lck_owner_handle =
LCK_get_owner_handle(tdbb, temp_lock.lck_type); LCK_get_owner_handle(tdbb, temp_lock->lck_type);
temp_lock.lck_parent = dbb->dbb_lock; temp_lock->lck_parent = dbb->dbb_lock;
temp_lock.lck_length = sizeof(SLONG); temp_lock->lck_length = sizeof(SLONG);
temp_lock.lck_key.lck_long = number; temp_lock->lck_key.lck_long = number;
/* If we can't get a lock on the transaction, it must be active. */ /* If we can't get a lock on the transaction, it must be active. */
if (!LCK_lock_non_blocking(tdbb, &temp_lock, LCK_read, FALSE)) { if (!LCK_lock_non_blocking(tdbb, temp_lock.get(), LCK_read, FALSE)) {
INIT_STATUS(tdbb->tdbb_status_vector); INIT_STATUS(tdbb->tdbb_status_vector);
return tra_active; return tra_active;
} }
INIT_STATUS(tdbb->tdbb_status_vector); INIT_STATUS(tdbb->tdbb_status_vector);
LCK_release(tdbb, &temp_lock); LCK_release(tdbb, temp_lock.get());
/* as a last resort we must look at the TIP page to see /* as a last resort we must look at the TIP page to see
whether the transaction is committed or dead; to minimize whether the transaction is committed or dead; to minimize
@ -266,6 +274,7 @@ int TPC_snapshot_state(TDBB tdbb, SLONG number)
return TRA_fetch_state(tdbb, number); return TRA_fetch_state(tdbb, number);
} }
}
/* if the transaction has been started since we /* if the transaction has been started since we
last looked, extend the cache upward */ last looked, extend the cache upward */