ChannelProviderFactory, eget support for it
This commit is contained in:
@@ -16,35 +16,85 @@ using namespace epics::pvData;
|
||||
using namespace epics::pvAccess;
|
||||
|
||||
// TODO global static variable (de/initialization order not guaranteed)
|
||||
static Mutex m_mutex;
|
||||
static ClientContextImpl::shared_pointer m_context;
|
||||
static Mutex mutex;
|
||||
static ClientContextImpl::shared_pointer context;
|
||||
|
||||
class ChannelProviderFactoryImpl : public ChannelProviderFactory
|
||||
{
|
||||
public:
|
||||
POINTER_DEFINITIONS(ChannelProviderFactoryImpl);
|
||||
|
||||
virtual epics::pvData::String getFactoryName()
|
||||
{
|
||||
return ClientContextImpl::PROVIDER_NAME;
|
||||
}
|
||||
|
||||
virtual ChannelProvider::shared_pointer sharedInstance()
|
||||
{
|
||||
Lock guard(mutex);
|
||||
if (!context.get())
|
||||
{
|
||||
try {
|
||||
ClientContextImpl::shared_pointer lcontext = createClientContextImpl();
|
||||
lcontext->initialize();
|
||||
context = lcontext;
|
||||
} catch (std::exception &e) {
|
||||
LOG(logLevelError, "Unhandled exception caught at %s:%d: %s", __FILE__, __LINE__, e.what());
|
||||
} catch (...) {
|
||||
LOG(logLevelError, "Unhandled exception caught at %s:%d.", __FILE__, __LINE__);
|
||||
}
|
||||
}
|
||||
return context->getProvider();
|
||||
}
|
||||
|
||||
virtual ChannelProvider::shared_pointer newInstance()
|
||||
{
|
||||
Lock guard(mutex);
|
||||
try {
|
||||
ClientContextImpl::shared_pointer lcontext = createClientContextImpl();
|
||||
lcontext->initialize();
|
||||
return lcontext->getProvider();
|
||||
} catch (std::exception &e) {
|
||||
LOG(logLevelError, "Unhandled exception caught at %s:%d: %s", __FILE__, __LINE__, e.what());
|
||||
return ChannelProvider::shared_pointer();
|
||||
} catch (...) {
|
||||
LOG(logLevelError, "Unhandled exception caught at %s:%d.", __FILE__, __LINE__);
|
||||
return ChannelProvider::shared_pointer();
|
||||
}
|
||||
}
|
||||
|
||||
void destroySharedInstance()
|
||||
{
|
||||
Lock guard(mutex);
|
||||
if (context.get())
|
||||
{
|
||||
context->dispose();
|
||||
context.reset();
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
static ChannelProviderFactoryImpl::shared_pointer factory;
|
||||
|
||||
void ClientFactory::start()
|
||||
{
|
||||
epicsSignalInstallSigAlarmIgnore();
|
||||
epicsSignalInstallSigPipeIgnore();
|
||||
|
||||
Lock guard(m_mutex);
|
||||
if (m_context.get()) return;
|
||||
|
||||
try {
|
||||
m_context = createClientContextImpl();
|
||||
m_context->initialize();
|
||||
registerChannelProvider(m_context->getProvider());
|
||||
} catch (std::exception &e) {
|
||||
LOG(logLevelError, "Unhandled exception caught at %s:%d: %s", __FILE__, __LINE__, e.what());
|
||||
} catch (...) {
|
||||
LOG(logLevelError, "Unhandled exception caught at %s:%d.", __FILE__, __LINE__);
|
||||
}
|
||||
Lock guard(mutex);
|
||||
if (!factory.get())
|
||||
factory.reset(new ChannelProviderFactoryImpl());
|
||||
|
||||
registerChannelProviderFactory(factory);
|
||||
}
|
||||
|
||||
void ClientFactory::stop()
|
||||
{
|
||||
Lock guard(m_mutex);
|
||||
if (!m_context.get()) return;
|
||||
Lock guard(mutex);
|
||||
|
||||
unregisterChannelProvider(m_context->getProvider());
|
||||
|
||||
m_context->dispose();
|
||||
m_context.reset();
|
||||
if (factory.get())
|
||||
{
|
||||
unregisterChannelProviderFactory(factory);
|
||||
factory->destroySharedInstance();
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user