mirror of
https://github.com/FirebirdSQL/firebird.git
synced 2025-02-02 10:40:38 +01:00
Fixed bug GH-6843 : Crash when UDR is used by system attachment, for ex. Garbage Collector
This commit is contained in:
parent
fda403bfdd
commit
2b0dc05f52
@ -385,11 +385,7 @@ public:
|
||||
|
||||
JAttachment* getInterface() throw();
|
||||
|
||||
JProvider* getProvider()
|
||||
{
|
||||
fb_assert(att_provider);
|
||||
return att_provider;
|
||||
}
|
||||
JProvider* getProvider();
|
||||
|
||||
private:
|
||||
Attachment(MemoryPool* pool, Database* dbb, JProvider* provider);
|
||||
@ -461,6 +457,12 @@ inline bool Attachment::isUtility() const
|
||||
return (att_utility != UTIL_NONE);
|
||||
}
|
||||
|
||||
inline JProvider* Attachment::getProvider()
|
||||
{
|
||||
fb_assert(att_provider || (att_flags & ATT_system));
|
||||
return att_provider;
|
||||
}
|
||||
|
||||
// This class holds references to all attachments it contains
|
||||
|
||||
class AttachmentsRefHolder
|
||||
|
@ -603,8 +603,13 @@ ExtEngineManager::ExternalContextImpl::ExternalContextImpl(thread_db* tdbb,
|
||||
|
||||
internalAttachment->getStable()->addRef();
|
||||
|
||||
externalAttachment = MasterInterfacePtr()->registerAttachment
|
||||
(internalAttachment->getProvider(), internalAttachment->getInterface());
|
||||
Jrd::JProvider* jProv = internalAttachment->getProvider();
|
||||
Jrd::JAttachment* jAtt = internalAttachment->getInterface();
|
||||
|
||||
// System attachments (such as garbage collector) have no external interface
|
||||
// and should not be used by UDR's
|
||||
if (jProv && jAtt)
|
||||
externalAttachment = MasterInterfacePtr()->registerAttachment(jProv, jAtt);
|
||||
}
|
||||
|
||||
ExtEngineManager::ExternalContextImpl::~ExternalContextImpl()
|
||||
@ -616,6 +621,8 @@ ExtEngineManager::ExternalContextImpl::~ExternalContextImpl()
|
||||
externalAttachment->release();
|
||||
externalAttachment = NULL;
|
||||
}
|
||||
else
|
||||
internalAttachment->getStable()->release();
|
||||
}
|
||||
|
||||
void ExtEngineManager::ExternalContextImpl::releaseTransaction()
|
||||
@ -640,8 +647,11 @@ void ExtEngineManager::ExternalContextImpl::setTransaction(thread_db* tdbb)
|
||||
fb_assert(!externalTransaction && !internalTransaction);
|
||||
|
||||
if ((internalTransaction = newTransaction))
|
||||
{
|
||||
if (externalAttachment)
|
||||
externalTransaction = MasterInterfacePtr()->registerTransaction(externalAttachment, internalTransaction);
|
||||
}
|
||||
}
|
||||
|
||||
IMaster* ExtEngineManager::ExternalContextImpl::getMaster()
|
||||
{
|
||||
@ -657,6 +667,8 @@ IExternalEngine* ExtEngineManager::ExternalContextImpl::getEngine(CheckStatusWra
|
||||
Firebird::IAttachment* ExtEngineManager::ExternalContextImpl::getAttachment(
|
||||
CheckStatusWrapper* /*status*/)
|
||||
{
|
||||
checkExternalAttachment();
|
||||
|
||||
externalAttachment->addRef();
|
||||
return externalAttachment;
|
||||
}
|
||||
@ -664,6 +676,8 @@ Firebird::IAttachment* ExtEngineManager::ExternalContextImpl::getAttachment(
|
||||
Firebird::ITransaction* ExtEngineManager::ExternalContextImpl::getTransaction(
|
||||
CheckStatusWrapper* /*status*/)
|
||||
{
|
||||
checkExternalAttachment();
|
||||
|
||||
externalTransaction->addRef();
|
||||
return externalTransaction;
|
||||
}
|
||||
@ -703,6 +717,13 @@ void* ExtEngineManager::ExternalContextImpl::setInfo(int code, void* value)
|
||||
return oldValue;
|
||||
}
|
||||
|
||||
void ExtEngineManager::ExternalContextImpl::checkExternalAttachment()
|
||||
{
|
||||
if (!externalAttachment)
|
||||
{
|
||||
(Arg::Gds(isc_random) << Arg::Str("Use of system attachment in UDR is not allowed")).raise();
|
||||
}
|
||||
}
|
||||
|
||||
//---------------------
|
||||
|
||||
|
@ -167,6 +167,8 @@ private:
|
||||
void* setInfo(int code, void* value);
|
||||
|
||||
private:
|
||||
void checkExternalAttachment();
|
||||
|
||||
Firebird::IExternalEngine* engine;
|
||||
Attachment* internalAttachment;
|
||||
Firebird::ITransaction* internalTransaction;
|
||||
|
@ -5091,6 +5091,7 @@ void Database::garbage_collector(Database* dbb)
|
||||
TRA_commit(tdbb, transaction, false);
|
||||
|
||||
Monitoring::cleanupAttachment(tdbb);
|
||||
dbb->dbb_extManager.closeAttachment(tdbb, attachment);
|
||||
attachment->releaseLocks(tdbb);
|
||||
LCK_fini(tdbb, LCK_OWNER_attachment);
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user