Maybe better to show some code (simplified). Expecting the free and release to 
have separate responsibilities I wrote initially (the variables with underscore 
are class fields). The Execute is called at some point and Free is called 
either after the IExternalFunctionImpl finished executing or in 
IExternalResultSetImpl::dispose (because that's the only place I'm aware of I 
know no more fetching will occur and the fetching might end up in the middle 
not reading all the results (otherwise I would know it because fetchNext would 
return != IStatus::RESULT_OK).

void Execute(const char* stmt)
{
        auto status = ThrowStatusWrapper(_context->getMaster()->getStatus());
        _attachment = _context->getAttachment(&status);
        _transaction = _context->getTransaction(&status);
        _statement = _attachment->prepare(&status, _transaction, 0, stmt, 
SQL_DIALECT_CURRENT, 0);
        _cursor = _statement->openCursor(&status, _transaction, nullptr, 
nullptr, outMetadata, 0);
        _msg = new unsigned char[outMetadata->getMessageLength(&status)];
        // other method does the fetchNext
}

void Free()
{
        _cursor->close(&status);
        _statement->free(&status);

        delete _msg;
        _msg = nullptr;
        _cursor->release();
        _cursor = nullptr;
        _statement->release();
        _statement = nullptr;
        _transaction->release();
        _transaction = nullptr;
        _attachment->release();
        _attachment = nullptr;
}

-- 
Mgr. Jiří Činčura
https://www.tabsoverspaces.com/



Firebird-Devel mailing list, web interface at 
https://lists.sourceforge.net/lists/listinfo/firebird-devel

Reply via email to