use weak pointer for callbacks
This commit is contained in:
@@ -23,6 +23,7 @@ using namespace epics::pvData;
|
|||||||
using namespace epics::pvDatabase;
|
using namespace epics::pvDatabase;
|
||||||
using std::tr1::static_pointer_cast;
|
using std::tr1::static_pointer_cast;
|
||||||
using std::string;
|
using std::string;
|
||||||
|
using namespace std;
|
||||||
|
|
||||||
namespace epics { namespace exampleRPC {
|
namespace epics { namespace exampleRPC {
|
||||||
|
|
||||||
@@ -31,6 +32,7 @@ PVStructurePtr ExampleRPCService::request(
|
|||||||
PVStructure::shared_pointer const & args
|
PVStructure::shared_pointer const & args
|
||||||
) throw (epics::pvAccess::RPCRequestException)
|
) throw (epics::pvAccess::RPCRequestException)
|
||||||
{
|
{
|
||||||
|
|
||||||
bool haveControl = pvRecord->takeControl();
|
bool haveControl = pvRecord->takeControl();
|
||||||
if (!haveControl)
|
if (!haveControl)
|
||||||
throw pvAccess::RPCRequestException(Status::STATUSTYPE_ERROR,
|
throw pvAccess::RPCRequestException(Status::STATUSTYPE_ERROR,
|
||||||
@@ -40,22 +42,28 @@ PVStructurePtr ExampleRPCService::request(
|
|||||||
PVDataCreatePtr pvDataCreate = getPVDataCreate();
|
PVDataCreatePtr pvDataCreate = getPVDataCreate();
|
||||||
|
|
||||||
PVStructureArrayPtr valueField = args->getSubField<PVStructureArray>("value");
|
PVStructureArrayPtr valueField = args->getSubField<PVStructureArray>("value");
|
||||||
if (valueField.get() == 0)
|
if (valueField.get() == 0) {
|
||||||
|
pvRecord->releaseControl();
|
||||||
throw pvAccess::RPCRequestException(Status::STATUSTYPE_ERROR,
|
throw pvAccess::RPCRequestException(Status::STATUSTYPE_ERROR,
|
||||||
"No structure array value field");
|
"No structure array value field");
|
||||||
|
}
|
||||||
|
|
||||||
StructureConstPtr valueFieldStructure = valueField->
|
StructureConstPtr valueFieldStructure = valueField->
|
||||||
getStructureArray()->getStructure();
|
getStructureArray()->getStructure();
|
||||||
|
|
||||||
ScalarConstPtr xField = valueFieldStructure->getField<Scalar>("x");
|
ScalarConstPtr xField = valueFieldStructure->getField<Scalar>("x");
|
||||||
if (xField.get() == 0 || xField->getScalarType() != pvDouble)
|
if (xField.get() == 0 || xField->getScalarType() != pvDouble) {
|
||||||
|
pvRecord->releaseControl();
|
||||||
throw pvAccess::RPCRequestException(Status::STATUSTYPE_ERROR,
|
throw pvAccess::RPCRequestException(Status::STATUSTYPE_ERROR,
|
||||||
"value field's structure has no double field x");
|
"value field's structure has no double field x");
|
||||||
|
}
|
||||||
|
|
||||||
ScalarConstPtr yField = valueFieldStructure->getField<Scalar>("y");
|
ScalarConstPtr yField = valueFieldStructure->getField<Scalar>("y");
|
||||||
if (xField.get() == 0 || xField->getScalarType() != pvDouble)
|
if (xField.get() == 0 || xField->getScalarType() != pvDouble) {
|
||||||
|
pvRecord->releaseControl();
|
||||||
throw pvAccess::RPCRequestException(Status::STATUSTYPE_ERROR,
|
throw pvAccess::RPCRequestException(Status::STATUSTYPE_ERROR,
|
||||||
"value field's structure has no double field y");
|
"value field's structure has no double field y");
|
||||||
|
}
|
||||||
|
|
||||||
PVStructureArray::const_svector vals = valueField->view();
|
PVStructureArray::const_svector vals = valueField->view();
|
||||||
|
|
||||||
@@ -89,22 +97,28 @@ void ExampleRPCServiceAsync::request(
|
|||||||
PVDataCreatePtr pvDataCreate = getPVDataCreate();
|
PVDataCreatePtr pvDataCreate = getPVDataCreate();
|
||||||
|
|
||||||
PVStructureArrayPtr valueField = args->getSubField<PVStructureArray>("value");
|
PVStructureArrayPtr valueField = args->getSubField<PVStructureArray>("value");
|
||||||
if (valueField.get() == 0)
|
if (valueField.get() == 0) {
|
||||||
|
pvRecord->releaseControl();
|
||||||
throw pvAccess::RPCRequestException(Status::STATUSTYPE_ERROR,
|
throw pvAccess::RPCRequestException(Status::STATUSTYPE_ERROR,
|
||||||
"No structure array value field");
|
"No structure array value field");
|
||||||
|
}
|
||||||
|
|
||||||
StructureConstPtr valueFieldStructure = valueField->
|
StructureConstPtr valueFieldStructure = valueField->
|
||||||
getStructureArray()->getStructure();
|
getStructureArray()->getStructure();
|
||||||
|
|
||||||
ScalarConstPtr xField = valueFieldStructure->getField<Scalar>("x");
|
ScalarConstPtr xField = valueFieldStructure->getField<Scalar>("x");
|
||||||
if (xField.get() == 0 || xField->getScalarType() != pvDouble)
|
if (xField.get() == 0 || xField->getScalarType() != pvDouble) {
|
||||||
|
pvRecord->releaseControl();
|
||||||
throw pvAccess::RPCRequestException(Status::STATUSTYPE_ERROR,
|
throw pvAccess::RPCRequestException(Status::STATUSTYPE_ERROR,
|
||||||
"value field's structure has no double field x");
|
"value field's structure has no double field x");
|
||||||
|
}
|
||||||
|
|
||||||
ScalarConstPtr yField = valueFieldStructure->getField<Scalar>("y");
|
ScalarConstPtr yField = valueFieldStructure->getField<Scalar>("y");
|
||||||
if (yField.get() == 0 || yField->getScalarType() != pvDouble)
|
if (yField.get() == 0 || yField->getScalarType() != pvDouble) {
|
||||||
|
pvRecord->releaseControl();
|
||||||
throw pvAccess::RPCRequestException(Status::STATUSTYPE_ERROR,
|
throw pvAccess::RPCRequestException(Status::STATUSTYPE_ERROR,
|
||||||
"value field's structure has no double field y");
|
"value field's structure has no double field y");
|
||||||
|
}
|
||||||
|
|
||||||
PVStructureArray::const_svector vals = valueField->view();
|
PVStructureArray::const_svector vals = valueField->view();
|
||||||
|
|
||||||
|
|||||||
@@ -13,6 +13,7 @@
|
|||||||
#include <iostream>
|
#include <iostream>
|
||||||
|
|
||||||
using namespace epics::pvData;
|
using namespace epics::pvData;
|
||||||
|
using namespace std;
|
||||||
|
|
||||||
|
|
||||||
static StructureConstPtr makeDeviceStructure()
|
static StructureConstPtr makeDeviceStructure()
|
||||||
@@ -81,6 +82,14 @@ int main (int argc, char *argv[])
|
|||||||
usage();
|
usage();
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if(argc<2)
|
||||||
|
{
|
||||||
|
std::cerr << APP_NAME << " requires at least 2 arguments."
|
||||||
|
<< std::endl;
|
||||||
|
usage();
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
// Start the pvAccess client side.
|
// Start the pvAccess client side.
|
||||||
epics::pvAccess::ClientFactory::start();
|
epics::pvAccess::ClientFactory::start();
|
||||||
|
|
||||||
|
|||||||
@@ -49,9 +49,11 @@ typedef std::tr1::shared_ptr<PVRecordStructure> PVRecordStructurePtr;
|
|||||||
|
|
||||||
class PVRecordClient;
|
class PVRecordClient;
|
||||||
typedef std::tr1::shared_ptr<PVRecordClient> PVRecordClientPtr;
|
typedef std::tr1::shared_ptr<PVRecordClient> PVRecordClientPtr;
|
||||||
|
typedef std::tr1::weak_ptr<PVRecordClient> PVRecordClientWPtr;
|
||||||
|
|
||||||
class PVListener;
|
class PVListener;
|
||||||
typedef std::tr1::shared_ptr<PVListener> PVListenerPtr;
|
typedef std::tr1::shared_ptr<PVListener> PVListenerPtr;
|
||||||
|
typedef std::tr1::weak_ptr<PVListener> PVListenerWPtr;
|
||||||
|
|
||||||
class PVDatabase;
|
class PVDatabase;
|
||||||
typedef std::tr1::shared_ptr<PVDatabase> PVDatabasePtr;
|
typedef std::tr1::shared_ptr<PVDatabase> PVDatabasePtr;
|
||||||
@@ -249,8 +251,8 @@ private:
|
|||||||
std::string recordName;
|
std::string recordName;
|
||||||
epics::pvData::PVStructurePtr pvStructure;
|
epics::pvData::PVStructurePtr pvStructure;
|
||||||
PVRecordStructurePtr pvRecordStructure;
|
PVRecordStructurePtr pvRecordStructure;
|
||||||
std::list<PVListenerPtr> pvListenerList;
|
std::list<PVListenerWPtr> pvListenerList;
|
||||||
std::list<PVRecordClientPtr> pvRecordClientList;
|
std::list<PVRecordClientWPtr> pvRecordClientList;
|
||||||
epics::pvData::Mutex mutex;
|
epics::pvData::Mutex mutex;
|
||||||
std::size_t depthGroupPut;
|
std::size_t depthGroupPut;
|
||||||
int traceLevel;
|
int traceLevel;
|
||||||
@@ -261,7 +263,7 @@ private:
|
|||||||
|
|
||||||
// following only valid while addListener or removeListener is active.
|
// following only valid while addListener or removeListener is active.
|
||||||
bool isAddListener;
|
bool isAddListener;
|
||||||
PVListenerPtr pvListener;
|
PVListenerWPtr pvListener;
|
||||||
};
|
};
|
||||||
|
|
||||||
epicsShareExtern std::ostream& operator<<(std::ostream& o, const PVRecord& record);
|
epicsShareExtern std::ostream& operator<<(std::ostream& o, const PVRecord& record);
|
||||||
@@ -339,7 +341,7 @@ private:
|
|||||||
virtual void removeListener(PVListenerPtr const & pvListener);
|
virtual void removeListener(PVListenerPtr const & pvListener);
|
||||||
void callListener();
|
void callListener();
|
||||||
|
|
||||||
std::list<PVListenerPtr> pvListenerList;
|
std::list<PVListenerWPtr> pvListenerList;
|
||||||
epics::pvData::PVFieldPtr pvField;
|
epics::pvData::PVFieldPtr pvField;
|
||||||
bool isStructure;
|
bool isStructure;
|
||||||
PVRecordStructurePtr parent;
|
PVRecordStructurePtr parent;
|
||||||
|
|||||||
+63
-33
@@ -77,22 +77,28 @@ void PVRecord::destroy()
|
|||||||
isDestroyed = true;
|
isDestroyed = true;
|
||||||
pvTimeStamp.detach();
|
pvTimeStamp.detach();
|
||||||
|
|
||||||
std::list<PVRecordClientPtr>::iterator clientIter;
|
std::list<PVRecordClientWPtr>::iterator clientIter;
|
||||||
while(true) {
|
while(true) {
|
||||||
clientIter = pvRecordClientList.begin();
|
clientIter = pvRecordClientList.begin();
|
||||||
if(clientIter==pvRecordClientList.end()) break;
|
if(clientIter==pvRecordClientList.end()) break;
|
||||||
|
PVRecordClientPtr client = clientIter->lock();
|
||||||
|
if(client.get()) {
|
||||||
|
unlock();
|
||||||
|
client->detach(getPtrSelf());
|
||||||
|
lock();
|
||||||
|
}
|
||||||
pvRecordClientList.erase(clientIter);
|
pvRecordClientList.erase(clientIter);
|
||||||
unlock();
|
|
||||||
(*clientIter)->detach(getPtrSelf());
|
|
||||||
lock();
|
|
||||||
}
|
}
|
||||||
std::list<PVListenerPtr>::iterator listenerIter;
|
std::list<PVListenerWPtr>::iterator listenerIter;
|
||||||
while(true) {
|
while(true) {
|
||||||
listenerIter = pvListenerList.begin();
|
listenerIter = pvListenerList.begin();
|
||||||
if(listenerIter==pvListenerList.end()) break;
|
if(listenerIter==pvListenerList.end()) break;
|
||||||
unlock();
|
PVListenerPtr listener = listenerIter->lock();
|
||||||
(*listenerIter)->unlisten(getPtrSelf());
|
if(listener.get()) {
|
||||||
lock();
|
unlock();
|
||||||
|
listener->unlisten(getPtrSelf());
|
||||||
|
lock();
|
||||||
|
}
|
||||||
pvListenerList.erase(listenerIter);
|
pvListenerList.erase(listenerIter);
|
||||||
|
|
||||||
}
|
}
|
||||||
@@ -200,12 +206,14 @@ bool PVRecord::addPVRecordClient(PVRecordClientPtr const & pvRecordClient)
|
|||||||
unlock();
|
unlock();
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
std::list<PVRecordClientPtr>::iterator iter;
|
std::list<PVRecordClientWPtr>::iterator iter;
|
||||||
for (iter = pvRecordClientList.begin();
|
for (iter = pvRecordClientList.begin();
|
||||||
iter!=pvRecordClientList.end();
|
iter!=pvRecordClientList.end();
|
||||||
iter++ )
|
iter++ )
|
||||||
{
|
{
|
||||||
if((*iter).get()==pvRecordClient.get()) {
|
PVRecordClientPtr client = iter->lock();
|
||||||
|
if(!client.get()) continue;
|
||||||
|
if(client.get()==pvRecordClient.get()) {
|
||||||
unlock();
|
unlock();
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@@ -230,12 +238,14 @@ bool PVRecord::removePVRecordClient(PVRecordClientPtr const & pvRecordClient)
|
|||||||
unlock();
|
unlock();
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
std::list<PVRecordClientPtr>::iterator iter;
|
std::list<PVRecordClientWPtr>::iterator iter;
|
||||||
for (iter = pvRecordClientList.begin();
|
for (iter = pvRecordClientList.begin();
|
||||||
iter!=pvRecordClientList.end();
|
iter!=pvRecordClientList.end();
|
||||||
iter++ )
|
iter++ )
|
||||||
{
|
{
|
||||||
if((*iter).get()==pvRecordClient.get()) {
|
PVRecordClientPtr client = iter->lock();
|
||||||
|
if(!client.get()) continue;
|
||||||
|
if(client.get()==pvRecordClient.get()) {
|
||||||
pvRecordClientList.erase(iter);
|
pvRecordClientList.erase(iter);
|
||||||
unlock();
|
unlock();
|
||||||
return true;
|
return true;
|
||||||
@@ -260,13 +270,15 @@ void PVRecord::detachClients()
|
|||||||
unlock();
|
unlock();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
std::list<PVRecordClientPtr>::iterator iter;
|
std::list<PVRecordClientWPtr>::iterator iter;
|
||||||
for (iter = pvRecordClientList.begin();
|
for (iter = pvRecordClientList.begin();
|
||||||
iter!=pvRecordClientList.end();
|
iter!=pvRecordClientList.end();
|
||||||
iter++ )
|
iter++ )
|
||||||
{
|
{
|
||||||
|
PVRecordClientPtr client = iter->lock();
|
||||||
|
if(!client.get()) continue;
|
||||||
unlock();
|
unlock();
|
||||||
(*iter)->detach(getPtrSelf());
|
client->detach(getPtrSelf());
|
||||||
lock();
|
lock();
|
||||||
}
|
}
|
||||||
pvRecordClientList.clear();
|
pvRecordClientList.clear();
|
||||||
@@ -290,10 +302,12 @@ bool PVRecord::addListener(
|
|||||||
unlock();
|
unlock();
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
std::list<PVListenerPtr>::iterator iter;
|
std::list<PVListenerWPtr>::iterator iter;
|
||||||
for (iter = pvListenerList.begin(); iter!=pvListenerList.end(); iter++ )
|
for (iter = pvListenerList.begin(); iter!=pvListenerList.end(); iter++ )
|
||||||
{
|
{
|
||||||
if((*iter).get()==pvListener.get()) {
|
PVListenerPtr listener = iter->lock();
|
||||||
|
if(!listener.get()) continue;
|
||||||
|
if(listener.get()==pvListener.get()) {
|
||||||
unlock();
|
unlock();
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@@ -314,10 +328,12 @@ bool PVRecord::addListener(
|
|||||||
void PVRecord::nextMasterPVField(PVFieldPtr const & pvField)
|
void PVRecord::nextMasterPVField(PVFieldPtr const & pvField)
|
||||||
{
|
{
|
||||||
PVRecordFieldPtr pvRecordField = findPVRecordField(pvField);
|
PVRecordFieldPtr pvRecordField = findPVRecordField(pvField);
|
||||||
|
PVListenerPtr listener = pvListener.lock();
|
||||||
|
if(!listener.get()) return;
|
||||||
if(isAddListener) {
|
if(isAddListener) {
|
||||||
pvRecordField->addListener(pvListener);
|
pvRecordField->addListener(listener);
|
||||||
} else {
|
} else {
|
||||||
pvRecordField->removeListener(pvListener);
|
pvRecordField->removeListener(listener);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -334,15 +350,17 @@ bool PVRecord::removeListener(
|
|||||||
unlock();
|
unlock();
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
std::list<PVListenerPtr>::iterator iter;
|
std::list<PVListenerWPtr>::iterator iter;
|
||||||
for (iter = pvListenerList.begin(); iter!=pvListenerList.end(); iter++ )
|
for (iter = pvListenerList.begin(); iter!=pvListenerList.end(); iter++ )
|
||||||
{
|
{
|
||||||
if((*iter).get()==pvListener.get()) {
|
PVListenerPtr listener = iter->lock();
|
||||||
|
if(!listener.get()) continue;
|
||||||
|
if(listener.get()==pvListener.get()) {
|
||||||
pvListenerList.erase(iter);
|
pvListenerList.erase(iter);
|
||||||
this->pvListener = pvListener;
|
this->pvListener = pvListener;
|
||||||
isAddListener = false;
|
isAddListener = false;
|
||||||
pvCopy->traverseMaster(getPtrSelf());
|
pvCopy->traverseMaster(getPtrSelf());
|
||||||
this->pvListener = PVListenerPtr();;
|
this->pvListener = PVListenerPtr();
|
||||||
unlock();
|
unlock();
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@@ -361,10 +379,12 @@ void PVRecord::beginGroupPut()
|
|||||||
if(traceLevel>2) {
|
if(traceLevel>2) {
|
||||||
cout << "PVRecord::beginGroupPut() " << recordName << endl;
|
cout << "PVRecord::beginGroupPut() " << recordName << endl;
|
||||||
}
|
}
|
||||||
std::list<PVListenerPtr>::iterator iter;
|
std::list<PVListenerWPtr>::iterator iter;
|
||||||
for (iter = pvListenerList.begin(); iter!=pvListenerList.end(); iter++)
|
for (iter = pvListenerList.begin(); iter!=pvListenerList.end(); iter++)
|
||||||
{
|
{
|
||||||
(*iter).get()->beginGroupPut(getPtrSelf());
|
PVListenerPtr listener = iter->lock();
|
||||||
|
if(!listener.get()) continue;
|
||||||
|
listener->beginGroupPut(getPtrSelf());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -374,10 +394,12 @@ void PVRecord::endGroupPut()
|
|||||||
if(traceLevel>2) {
|
if(traceLevel>2) {
|
||||||
cout << "PVRecord::endGroupPut() " << recordName << endl;
|
cout << "PVRecord::endGroupPut() " << recordName << endl;
|
||||||
}
|
}
|
||||||
std::list<PVListenerPtr>::iterator iter;
|
std::list<PVListenerWPtr>::iterator iter;
|
||||||
for (iter = pvListenerList.begin(); iter!=pvListenerList.end(); iter++)
|
for (iter = pvListenerList.begin(); iter!=pvListenerList.end(); iter++)
|
||||||
{
|
{
|
||||||
(*iter).get()->endGroupPut(getPtrSelf());
|
PVListenerPtr listener = iter->lock();
|
||||||
|
if(!listener.get()) continue;
|
||||||
|
listener->endGroupPut(getPtrSelf());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -449,9 +471,11 @@ bool PVRecordField::addListener(PVListenerPtr const & pvListener)
|
|||||||
if(pvRecord->getTraceLevel()>1) {
|
if(pvRecord->getTraceLevel()>1) {
|
||||||
cout << "PVRecordField::addListener() " << getFullName() << endl;
|
cout << "PVRecordField::addListener() " << getFullName() << endl;
|
||||||
}
|
}
|
||||||
std::list<PVListenerPtr>::iterator iter;
|
std::list<PVListenerWPtr>::iterator iter;
|
||||||
for (iter = pvListenerList.begin(); iter!=pvListenerList.end(); iter++ ) {
|
for (iter = pvListenerList.begin(); iter!=pvListenerList.end(); iter++ ) {
|
||||||
if((*iter).get()==pvListener.get()) {
|
PVListenerPtr listener = iter->lock();
|
||||||
|
if(!listener.get()) continue;
|
||||||
|
if(listener.get()==pvListener.get()) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -464,9 +488,11 @@ void PVRecordField::removeListener(PVListenerPtr const & pvListener)
|
|||||||
if(pvRecord->getTraceLevel()>1) {
|
if(pvRecord->getTraceLevel()>1) {
|
||||||
cout << "PVRecordField::removeListener() " << getFullName() << endl;
|
cout << "PVRecordField::removeListener() " << getFullName() << endl;
|
||||||
}
|
}
|
||||||
std::list<PVListenerPtr>::iterator iter;
|
std::list<PVListenerWPtr>::iterator iter;
|
||||||
for (iter = pvListenerList.begin(); iter!=pvListenerList.end(); iter++ ) {
|
for (iter = pvListenerList.begin(); iter!=pvListenerList.end(); iter++ ) {
|
||||||
if((*iter).get()==pvListener.get()) {
|
PVListenerPtr listener = iter->lock();
|
||||||
|
if(!listener.get()) continue;
|
||||||
|
if(listener.get()==pvListener.get()) {
|
||||||
pvListenerList.erase(iter);
|
pvListenerList.erase(iter);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -484,10 +510,12 @@ void PVRecordField::postPut()
|
|||||||
void PVRecordField::postParent(PVRecordFieldPtr const & subField)
|
void PVRecordField::postParent(PVRecordFieldPtr const & subField)
|
||||||
{
|
{
|
||||||
PVRecordStructurePtr pvrs = static_pointer_cast<PVRecordStructure>(getPtrSelf());
|
PVRecordStructurePtr pvrs = static_pointer_cast<PVRecordStructure>(getPtrSelf());
|
||||||
std::list<PVListenerPtr>::iterator iter;
|
std::list<PVListenerWPtr>::iterator iter;
|
||||||
for(iter = pvListenerList.begin(); iter != pvListenerList.end(); ++iter)
|
for(iter = pvListenerList.begin(); iter != pvListenerList.end(); ++iter)
|
||||||
{
|
{
|
||||||
(*iter)->dataPut(pvrs,subField);
|
PVListenerPtr listener = iter->lock();
|
||||||
|
if(!listener.get()) continue;
|
||||||
|
listener->dataPut(pvrs,subField);
|
||||||
}
|
}
|
||||||
if(parent) parent->postParent(subField);
|
if(parent) parent->postParent(subField);
|
||||||
}
|
}
|
||||||
@@ -507,9 +535,11 @@ void PVRecordField::postSubField()
|
|||||||
|
|
||||||
void PVRecordField::callListener()
|
void PVRecordField::callListener()
|
||||||
{
|
{
|
||||||
std::list<PVListenerPtr>::iterator iter;
|
std::list<PVListenerWPtr>::iterator iter;
|
||||||
for (iter = pvListenerList.begin(); iter!=pvListenerList.end(); iter++ ) {
|
for (iter = pvListenerList.begin(); iter!=pvListenerList.end(); iter++ ) {
|
||||||
(*iter)->dataPut(getPtrSelf());
|
PVListenerPtr listener = iter->lock();
|
||||||
|
if(!listener.get()) continue;
|
||||||
|
listener->dataPut(getPtrSelf());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -129,7 +129,7 @@ private:
|
|||||||
}
|
}
|
||||||
bool isDestroyed;
|
bool isDestroyed;
|
||||||
ChannelLocalPtr channelLocal;
|
ChannelLocalPtr channelLocal;
|
||||||
ChannelProcessRequester::shared_pointer channelProcessRequester;
|
ChannelProcessRequester::weak_pointer channelProcessRequester;
|
||||||
PVRecordPtr pvRecord;
|
PVRecordPtr pvRecord;
|
||||||
int nProcess;
|
int nProcess;
|
||||||
Mutex mutex;
|
Mutex mutex;
|
||||||
@@ -192,8 +192,10 @@ void ChannelProcessLocal::destroy()
|
|||||||
|
|
||||||
void ChannelProcessLocal::process()
|
void ChannelProcessLocal::process()
|
||||||
{
|
{
|
||||||
|
ChannelProcessRequester::shared_pointer requester = channelProcessRequester.lock();
|
||||||
|
if(!requester.get()) return;
|
||||||
if(isDestroyed) {
|
if(isDestroyed) {
|
||||||
channelProcessRequester->processDone(channelDestroyedStatus,getPtrSelf());
|
requester->processDone(channelDestroyedStatus,getPtrSelf());
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if(pvRecord->getTraceLevel()>1)
|
if(pvRecord->getTraceLevel()>1)
|
||||||
@@ -213,7 +215,7 @@ void ChannelProcessLocal::process()
|
|||||||
}
|
}
|
||||||
pvRecord->unlock();
|
pvRecord->unlock();
|
||||||
}
|
}
|
||||||
channelProcessRequester->processDone(Status::Ok,getPtrSelf());
|
requester->processDone(Status::Ok,getPtrSelf());
|
||||||
}
|
}
|
||||||
|
|
||||||
class ChannelGetLocal :
|
class ChannelGetLocal :
|
||||||
@@ -271,7 +273,7 @@ private:
|
|||||||
bool isDestroyed;
|
bool isDestroyed;
|
||||||
bool callProcess;
|
bool callProcess;
|
||||||
ChannelLocalPtr channelLocal;
|
ChannelLocalPtr channelLocal;
|
||||||
ChannelGetRequester::shared_pointer channelGetRequester;
|
ChannelGetRequester::weak_pointer channelGetRequester;
|
||||||
PVCopyPtr pvCopy;
|
PVCopyPtr pvCopy;
|
||||||
PVStructurePtr pvStructure;
|
PVStructurePtr pvStructure;
|
||||||
BitSetPtr bitSet;
|
BitSetPtr bitSet;
|
||||||
@@ -339,8 +341,10 @@ void ChannelGetLocal::destroy()
|
|||||||
|
|
||||||
void ChannelGetLocal::get()
|
void ChannelGetLocal::get()
|
||||||
{
|
{
|
||||||
|
ChannelGetRequester::shared_pointer requester = channelGetRequester.lock();
|
||||||
|
if(!requester.get()) return;
|
||||||
if(isDestroyed) {
|
if(isDestroyed) {
|
||||||
channelGetRequester->getDone(
|
requester->getDone(
|
||||||
channelDestroyedStatus,getPtrSelf(),nullPVStructure,nullBitSet);
|
channelDestroyedStatus,getPtrSelf(),nullPVStructure,nullBitSet);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -363,7 +367,7 @@ void ChannelGetLocal::get()
|
|||||||
bitSet->set(0);
|
bitSet->set(0);
|
||||||
firstTime = false;
|
firstTime = false;
|
||||||
}
|
}
|
||||||
channelGetRequester->getDone(
|
requester->getDone(
|
||||||
Status::Ok,
|
Status::Ok,
|
||||||
getPtrSelf(),
|
getPtrSelf(),
|
||||||
pvStructure,
|
pvStructure,
|
||||||
@@ -424,7 +428,7 @@ private:
|
|||||||
bool isDestroyed;
|
bool isDestroyed;
|
||||||
bool callProcess;
|
bool callProcess;
|
||||||
ChannelLocalPtr channelLocal;
|
ChannelLocalPtr channelLocal;
|
||||||
ChannelPutRequester::shared_pointer channelPutRequester;
|
ChannelPutRequester::weak_pointer channelPutRequester;
|
||||||
PVCopyPtr pvCopy;
|
PVCopyPtr pvCopy;
|
||||||
PVRecordPtr pvRecord;
|
PVRecordPtr pvRecord;
|
||||||
Mutex mutex;
|
Mutex mutex;
|
||||||
@@ -487,8 +491,10 @@ void ChannelPutLocal::destroy()
|
|||||||
|
|
||||||
void ChannelPutLocal::get()
|
void ChannelPutLocal::get()
|
||||||
{
|
{
|
||||||
|
ChannelPutRequester::shared_pointer requester = channelPutRequester.lock();
|
||||||
|
if(!requester.get()) return;
|
||||||
if(isDestroyed) {
|
if(isDestroyed) {
|
||||||
channelPutRequester->getDone(
|
requester->getDone(
|
||||||
channelDestroyedStatus,getPtrSelf(),nullPVStructure,nullBitSet);
|
channelDestroyedStatus,getPtrSelf(),nullPVStructure,nullBitSet);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -504,7 +510,7 @@ void ChannelPutLocal::get()
|
|||||||
throw;
|
throw;
|
||||||
}
|
}
|
||||||
pvRecord->unlock();
|
pvRecord->unlock();
|
||||||
channelPutRequester->getDone(
|
requester->getDone(
|
||||||
Status::Ok,getPtrSelf(),pvStructure,bitSet);
|
Status::Ok,getPtrSelf(),pvStructure,bitSet);
|
||||||
if(pvRecord->getTraceLevel()>1)
|
if(pvRecord->getTraceLevel()>1)
|
||||||
{
|
{
|
||||||
@@ -515,8 +521,10 @@ void ChannelPutLocal::get()
|
|||||||
void ChannelPutLocal::put(
|
void ChannelPutLocal::put(
|
||||||
PVStructurePtr const &pvStructure,BitSetPtr const &bitSet)
|
PVStructurePtr const &pvStructure,BitSetPtr const &bitSet)
|
||||||
{
|
{
|
||||||
|
ChannelPutRequester::shared_pointer requester = channelPutRequester.lock();
|
||||||
|
if(!requester.get()) return;
|
||||||
if(isDestroyed) {
|
if(isDestroyed) {
|
||||||
channelPutRequester->putDone(channelDestroyedStatus,getPtrSelf());
|
requester->putDone(channelDestroyedStatus,getPtrSelf());
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
pvRecord->lock();
|
pvRecord->lock();
|
||||||
@@ -532,7 +540,7 @@ void ChannelPutLocal::put(
|
|||||||
throw;
|
throw;
|
||||||
}
|
}
|
||||||
pvRecord->unlock();
|
pvRecord->unlock();
|
||||||
channelPutRequester->putDone(Status::Ok,getPtrSelf());
|
requester->putDone(Status::Ok,getPtrSelf());
|
||||||
if(pvRecord->getTraceLevel()>1)
|
if(pvRecord->getTraceLevel()>1)
|
||||||
{
|
{
|
||||||
cout << "ChannelPutLocal::put" << endl;
|
cout << "ChannelPutLocal::put" << endl;
|
||||||
@@ -578,7 +586,7 @@ private:
|
|||||||
ChannelPutGetLocal(
|
ChannelPutGetLocal(
|
||||||
bool callProcess,
|
bool callProcess,
|
||||||
ChannelLocalPtr const &channelLocal,
|
ChannelLocalPtr const &channelLocal,
|
||||||
ChannelPutGetRequester::shared_pointer const & channelPutGetRequester,
|
ChannelPutGetRequester::weak_pointer const & channelPutGetRequester,
|
||||||
PVCopyPtr const &pvPutCopy,
|
PVCopyPtr const &pvPutCopy,
|
||||||
PVCopyPtr const &pvGetCopy,
|
PVCopyPtr const &pvGetCopy,
|
||||||
PVStructurePtr const&pvGetStructure,
|
PVStructurePtr const&pvGetStructure,
|
||||||
@@ -599,7 +607,7 @@ private:
|
|||||||
bool isDestroyed;
|
bool isDestroyed;
|
||||||
bool callProcess;
|
bool callProcess;
|
||||||
ChannelLocalPtr channelLocal;
|
ChannelLocalPtr channelLocal;
|
||||||
ChannelPutGetRequester::shared_pointer channelPutGetRequester;
|
ChannelPutGetRequester::weak_pointer channelPutGetRequester;
|
||||||
PVCopyPtr pvPutCopy;
|
PVCopyPtr pvPutCopy;
|
||||||
PVCopyPtr pvGetCopy;
|
PVCopyPtr pvGetCopy;
|
||||||
PVStructurePtr pvGetStructure;
|
PVStructurePtr pvGetStructure;
|
||||||
@@ -675,8 +683,10 @@ void ChannelPutGetLocal::destroy()
|
|||||||
void ChannelPutGetLocal::putGet(
|
void ChannelPutGetLocal::putGet(
|
||||||
PVStructurePtr const &pvPutStructure,BitSetPtr const &putBitSet)
|
PVStructurePtr const &pvPutStructure,BitSetPtr const &putBitSet)
|
||||||
{
|
{
|
||||||
|
ChannelPutGetRequester::shared_pointer requester = channelPutGetRequester.lock();
|
||||||
|
if(!requester.get()) return;
|
||||||
if(isDestroyed) {
|
if(isDestroyed) {
|
||||||
channelPutGetRequester->putGetDone(
|
requester->putGetDone(
|
||||||
channelDestroyedStatus,getPtrSelf(),nullPVStructure,nullBitSet);
|
channelDestroyedStatus,getPtrSelf(),nullPVStructure,nullBitSet);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -693,7 +703,7 @@ void ChannelPutGetLocal::putGet(
|
|||||||
throw;
|
throw;
|
||||||
}
|
}
|
||||||
pvRecord->unlock();
|
pvRecord->unlock();
|
||||||
channelPutGetRequester->putGetDone(
|
requester->putGetDone(
|
||||||
Status::Ok,getPtrSelf(),pvGetStructure,getBitSet);
|
Status::Ok,getPtrSelf(),pvGetStructure,getBitSet);
|
||||||
if(pvRecord->getTraceLevel()>1)
|
if(pvRecord->getTraceLevel()>1)
|
||||||
{
|
{
|
||||||
@@ -703,8 +713,10 @@ void ChannelPutGetLocal::putGet(
|
|||||||
|
|
||||||
void ChannelPutGetLocal::getPut()
|
void ChannelPutGetLocal::getPut()
|
||||||
{
|
{
|
||||||
|
ChannelPutGetRequester::shared_pointer requester = channelPutGetRequester.lock();
|
||||||
|
if(!requester.get()) return;
|
||||||
if(isDestroyed) {
|
if(isDestroyed) {
|
||||||
channelPutGetRequester->getPutDone(
|
requester->getPutDone(
|
||||||
channelDestroyedStatus,getPtrSelf(),nullPVStructure,nullBitSet);
|
channelDestroyedStatus,getPtrSelf(),nullPVStructure,nullBitSet);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -718,7 +730,7 @@ void ChannelPutGetLocal::getPut()
|
|||||||
throw;
|
throw;
|
||||||
}
|
}
|
||||||
pvRecord->unlock();
|
pvRecord->unlock();
|
||||||
channelPutGetRequester->getPutDone(
|
requester->getPutDone(
|
||||||
Status::Ok,getPtrSelf(),pvPutStructure,putBitSet);
|
Status::Ok,getPtrSelf(),pvPutStructure,putBitSet);
|
||||||
if(pvRecord->getTraceLevel()>1)
|
if(pvRecord->getTraceLevel()>1)
|
||||||
{
|
{
|
||||||
@@ -728,8 +740,10 @@ void ChannelPutGetLocal::getPut()
|
|||||||
|
|
||||||
void ChannelPutGetLocal::getGet()
|
void ChannelPutGetLocal::getGet()
|
||||||
{
|
{
|
||||||
|
ChannelPutGetRequester::shared_pointer requester = channelPutGetRequester.lock();
|
||||||
|
if(!requester.get()) return;
|
||||||
if(isDestroyed) {
|
if(isDestroyed) {
|
||||||
channelPutGetRequester->getGetDone(
|
requester->getGetDone(
|
||||||
channelDestroyedStatus,getPtrSelf(),nullPVStructure,nullBitSet);
|
channelDestroyedStatus,getPtrSelf(),nullPVStructure,nullBitSet);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -742,7 +756,7 @@ void ChannelPutGetLocal::getGet()
|
|||||||
throw;
|
throw;
|
||||||
}
|
}
|
||||||
pvRecord->unlock();
|
pvRecord->unlock();
|
||||||
channelPutGetRequester->getGetDone(
|
requester->getGetDone(
|
||||||
Status::Ok,getPtrSelf(),pvGetStructure,getBitSet);
|
Status::Ok,getPtrSelf(),pvGetStructure,getBitSet);
|
||||||
if(pvRecord->getTraceLevel()>1)
|
if(pvRecord->getTraceLevel()>1)
|
||||||
{
|
{
|
||||||
@@ -793,7 +807,9 @@ public:
|
|||||||
virtual void requestDone(Status const & status,
|
virtual void requestDone(Status const & status,
|
||||||
PVStructurePtr const & result)
|
PVStructurePtr const & result)
|
||||||
{
|
{
|
||||||
channelRPCRequester->requestDone(status, getPtrSelf(), result);
|
ChannelRPCRequester::shared_pointer requester = channelRPCRequester.lock();
|
||||||
|
if(!requester.get()) return;
|
||||||
|
requester->requestDone(status, getPtrSelf(), result);
|
||||||
|
|
||||||
if (isLastRequest.get())
|
if (isLastRequest.get())
|
||||||
destroy();
|
destroy();
|
||||||
@@ -831,7 +847,7 @@ private:
|
|||||||
|
|
||||||
AtomicBoolean isDestroyed;
|
AtomicBoolean isDestroyed;
|
||||||
ChannelLocalPtr channelLocal;
|
ChannelLocalPtr channelLocal;
|
||||||
ChannelRPCRequester::shared_pointer channelRPCRequester;
|
ChannelRPCRequester::weak_pointer channelRPCRequester;
|
||||||
Service::shared_pointer service;
|
Service::shared_pointer service;
|
||||||
PVRecordPtr pvRecord;
|
PVRecordPtr pvRecord;
|
||||||
AtomicBoolean isLastRequest;
|
AtomicBoolean isLastRequest;
|
||||||
@@ -901,8 +917,8 @@ void ChannelRPCLocal::processRequest(
|
|||||||
{
|
{
|
||||||
status = Status(Status::STATUSTYPE_FATAL, "RPCService.request(PVStructure) returned null.");
|
status = Status(Status::STATUSTYPE_FATAL, "RPCService.request(PVStructure) returned null.");
|
||||||
}
|
}
|
||||||
|
ChannelRPCRequester::shared_pointer requester = channelRPCRequester.lock();
|
||||||
channelRPCRequester->requestDone(status, getPtrSelf(), result);
|
if(requester.get()) requester->requestDone(status, getPtrSelf(), result);
|
||||||
|
|
||||||
if (isLastRequest.get())
|
if (isLastRequest.get())
|
||||||
destroy();
|
destroy();
|
||||||
@@ -920,9 +936,8 @@ void ChannelRPCLocal::processRequest(
|
|||||||
{
|
{
|
||||||
// handle user unexpected errors
|
// handle user unexpected errors
|
||||||
Status errorStatus(Status::STATUSTYPE_FATAL, ex.what());
|
Status errorStatus(Status::STATUSTYPE_FATAL, ex.what());
|
||||||
|
ChannelRPCRequester::shared_pointer requester = channelRPCRequester.lock();
|
||||||
channelRPCRequester->requestDone(errorStatus, getPtrSelf(), PVStructurePtr());
|
if(requester.get()) requester->requestDone(errorStatus, getPtrSelf(), PVStructurePtr());
|
||||||
|
|
||||||
if (isLastRequest.get())
|
if (isLastRequest.get())
|
||||||
destroy();
|
destroy();
|
||||||
}
|
}
|
||||||
@@ -931,8 +946,8 @@ void ChannelRPCLocal::processRequest(
|
|||||||
// handle user unexpected errors
|
// handle user unexpected errors
|
||||||
Status errorStatus(Status::STATUSTYPE_FATAL,
|
Status errorStatus(Status::STATUSTYPE_FATAL,
|
||||||
"Unexpected exception caught while calling RPCServiceAsync.request(PVStructure, RPCResponseCallback).");
|
"Unexpected exception caught while calling RPCServiceAsync.request(PVStructure, RPCResponseCallback).");
|
||||||
|
ChannelRPCRequester::shared_pointer requester = channelRPCRequester.lock();
|
||||||
channelRPCRequester->requestDone(errorStatus, shared_from_this(), PVStructurePtr());
|
if(requester.get()) requester->requestDone(errorStatus, shared_from_this(), PVStructurePtr());
|
||||||
|
|
||||||
if (isLastRequest.get())
|
if (isLastRequest.get())
|
||||||
destroy();
|
destroy();
|
||||||
@@ -1032,7 +1047,7 @@ private:
|
|||||||
}
|
}
|
||||||
bool isDestroyed;
|
bool isDestroyed;
|
||||||
ChannelLocalPtr channelLocal;
|
ChannelLocalPtr channelLocal;
|
||||||
ChannelArrayRequester::shared_pointer channelArrayRequester;
|
ChannelArrayRequester::weak_pointer channelArrayRequester;
|
||||||
PVArrayPtr pvArray;
|
PVArrayPtr pvArray;
|
||||||
PVArrayPtr pvCopy;
|
PVArrayPtr pvCopy;
|
||||||
PVRecordPtr pvRecord;
|
PVRecordPtr pvRecord;
|
||||||
@@ -1141,8 +1156,10 @@ void ChannelArrayLocal::destroy()
|
|||||||
|
|
||||||
void ChannelArrayLocal::getArray(size_t offset, size_t count, size_t stride)
|
void ChannelArrayLocal::getArray(size_t offset, size_t count, size_t stride)
|
||||||
{
|
{
|
||||||
|
ChannelArrayRequester::shared_pointer requester = channelArrayRequester.lock();
|
||||||
|
if(!requester.get()) return;
|
||||||
if(isDestroyed) {
|
if(isDestroyed) {
|
||||||
channelArrayRequester->getArrayDone(channelDestroyedStatus,getPtrSelf(),pvCopy);
|
requester->getArrayDone(channelDestroyedStatus,getPtrSelf(),pvCopy);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if(pvRecord->getTraceLevel()>1)
|
if(pvRecord->getTraceLevel()>1)
|
||||||
@@ -1150,11 +1167,11 @@ void ChannelArrayLocal::getArray(size_t offset, size_t count, size_t stride)
|
|||||||
cout << "ChannelArrayLocal::getArray" << endl;
|
cout << "ChannelArrayLocal::getArray" << endl;
|
||||||
}
|
}
|
||||||
if(offset<0) {
|
if(offset<0) {
|
||||||
channelArrayRequester->getArrayDone(illegalOffsetStatus,getPtrSelf(),pvCopy);
|
requester->getArrayDone(illegalOffsetStatus,getPtrSelf(),pvCopy);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if(stride<0) {
|
if(stride<0) {
|
||||||
channelArrayRequester->getArrayDone(illegalStrideStatus,getPtrSelf(),pvCopy);
|
requester->getArrayDone(illegalStrideStatus,getPtrSelf(),pvCopy);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const char *exceptionMessage = NULL;
|
const char *exceptionMessage = NULL;
|
||||||
@@ -1186,14 +1203,16 @@ void ChannelArrayLocal::getArray(size_t offset, size_t count, size_t stride)
|
|||||||
if(exceptionMessage!=NULL) {
|
if(exceptionMessage!=NULL) {
|
||||||
status = Status(Status::STATUSTYPE_ERROR,exceptionMessage);
|
status = Status(Status::STATUSTYPE_ERROR,exceptionMessage);
|
||||||
}
|
}
|
||||||
channelArrayRequester->getArrayDone(status,getPtrSelf(),pvCopy);
|
requester->getArrayDone(status,getPtrSelf(),pvCopy);
|
||||||
}
|
}
|
||||||
|
|
||||||
void ChannelArrayLocal::putArray(
|
void ChannelArrayLocal::putArray(
|
||||||
PVArrayPtr const & pvArray, size_t offset, size_t count, size_t stride)
|
PVArrayPtr const & pvArray, size_t offset, size_t count, size_t stride)
|
||||||
{
|
{
|
||||||
|
ChannelArrayRequester::shared_pointer requester = channelArrayRequester.lock();
|
||||||
|
if(!requester.get()) return;
|
||||||
if(isDestroyed) {
|
if(isDestroyed) {
|
||||||
channelArrayRequester->putArrayDone(channelDestroyedStatus,getPtrSelf());
|
requester->putArrayDone(channelDestroyedStatus,getPtrSelf());
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if(pvRecord->getTraceLevel()>1)
|
if(pvRecord->getTraceLevel()>1)
|
||||||
@@ -1201,15 +1220,15 @@ void ChannelArrayLocal::putArray(
|
|||||||
cout << "ChannelArrayLocal::putArray" << endl;
|
cout << "ChannelArrayLocal::putArray" << endl;
|
||||||
}
|
}
|
||||||
if(offset<0) {
|
if(offset<0) {
|
||||||
channelArrayRequester->putArrayDone(illegalOffsetStatus,getPtrSelf());
|
requester->putArrayDone(illegalOffsetStatus,getPtrSelf());
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if(count<0) {
|
if(count<0) {
|
||||||
channelArrayRequester->putArrayDone(illegalCountStatus,getPtrSelf());
|
requester->putArrayDone(illegalCountStatus,getPtrSelf());
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if(stride<0) {
|
if(stride<0) {
|
||||||
channelArrayRequester->putArrayDone(illegalStrideStatus,getPtrSelf());
|
requester->putArrayDone(illegalStrideStatus,getPtrSelf());
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
size_t newLength = offset + count*stride;
|
size_t newLength = offset + count*stride;
|
||||||
@@ -1226,11 +1245,13 @@ void ChannelArrayLocal::putArray(
|
|||||||
if(exceptionMessage!=NULL) {
|
if(exceptionMessage!=NULL) {
|
||||||
status = Status(Status::STATUSTYPE_ERROR,exceptionMessage);
|
status = Status(Status::STATUSTYPE_ERROR,exceptionMessage);
|
||||||
}
|
}
|
||||||
channelArrayRequester->putArrayDone(status,getPtrSelf());
|
requester->putArrayDone(status,getPtrSelf());
|
||||||
}
|
}
|
||||||
|
|
||||||
void ChannelArrayLocal::getLength()
|
void ChannelArrayLocal::getLength()
|
||||||
{
|
{
|
||||||
|
ChannelArrayRequester::shared_pointer requester = channelArrayRequester.lock();
|
||||||
|
if(!requester.get()) return;
|
||||||
size_t length = 0;
|
size_t length = 0;
|
||||||
const char *exceptionMessage = NULL;
|
const char *exceptionMessage = NULL;
|
||||||
pvRecord->lock();
|
pvRecord->lock();
|
||||||
@@ -1244,13 +1265,15 @@ void ChannelArrayLocal::getLength()
|
|||||||
if(exceptionMessage!=NULL) {
|
if(exceptionMessage!=NULL) {
|
||||||
status = Status(Status::STATUSTYPE_ERROR,exceptionMessage);
|
status = Status(Status::STATUSTYPE_ERROR,exceptionMessage);
|
||||||
}
|
}
|
||||||
channelArrayRequester->getLengthDone(status,getPtrSelf(),length);
|
requester->getLengthDone(status,getPtrSelf(),length);
|
||||||
}
|
}
|
||||||
|
|
||||||
void ChannelArrayLocal::setLength(size_t length)
|
void ChannelArrayLocal::setLength(size_t length)
|
||||||
{
|
{
|
||||||
|
ChannelArrayRequester::shared_pointer requester = channelArrayRequester.lock();
|
||||||
|
if(!requester.get()) return;
|
||||||
if(isDestroyed) {
|
if(isDestroyed) {
|
||||||
channelArrayRequester->setLengthDone(channelDestroyedStatus,getPtrSelf());
|
requester->setLengthDone(channelDestroyedStatus,getPtrSelf());
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if(pvRecord->getTraceLevel()>1)
|
if(pvRecord->getTraceLevel()>1)
|
||||||
@@ -1267,7 +1290,7 @@ void ChannelArrayLocal::setLength(size_t length)
|
|||||||
throw;
|
throw;
|
||||||
}
|
}
|
||||||
pvRecord->unlock();
|
pvRecord->unlock();
|
||||||
channelArrayRequester->setLengthDone(Status::Ok,getPtrSelf());
|
requester->setLengthDone(Status::Ok,getPtrSelf());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -1315,14 +1338,18 @@ void ChannelLocal::detach(PVRecordPtr const & pvRecord)
|
|||||||
|
|
||||||
string ChannelLocal::getRequesterName()
|
string ChannelLocal::getRequesterName()
|
||||||
{
|
{
|
||||||
return requester->getRequesterName();
|
ChannelRequester::shared_pointer req = requester.lock();
|
||||||
|
if(!req.get()) return string();
|
||||||
|
return req->getRequesterName();
|
||||||
}
|
}
|
||||||
|
|
||||||
void ChannelLocal::message(
|
void ChannelLocal::message(
|
||||||
string const &message,
|
string const &message,
|
||||||
MessageType messageType)
|
MessageType messageType)
|
||||||
{
|
{
|
||||||
requester->message(message,messageType);
|
ChannelRequester::shared_pointer req = requester.lock();
|
||||||
|
if(!req.get()) return;
|
||||||
|
req->message(message,messageType);
|
||||||
}
|
}
|
||||||
|
|
||||||
string ChannelLocal::getRemoteAddress()
|
string ChannelLocal::getRemoteAddress()
|
||||||
@@ -1344,7 +1371,7 @@ string ChannelLocal::getChannelName()
|
|||||||
|
|
||||||
ChannelRequester::shared_pointer ChannelLocal::getChannelRequester()
|
ChannelRequester::shared_pointer ChannelLocal::getChannelRequester()
|
||||||
{
|
{
|
||||||
return requester;
|
return requester.lock();
|
||||||
}
|
}
|
||||||
|
|
||||||
bool ChannelLocal::isConnected()
|
bool ChannelLocal::isConnected()
|
||||||
|
|||||||
@@ -394,7 +394,7 @@ protected:
|
|||||||
}
|
}
|
||||||
private:
|
private:
|
||||||
ChannelProviderLocalPtr provider;
|
ChannelProviderLocalPtr provider;
|
||||||
epics::pvAccess::ChannelRequester::shared_pointer requester;
|
epics::pvAccess::ChannelRequester::weak_pointer requester;
|
||||||
PVRecordPtr pvRecord;
|
PVRecordPtr pvRecord;
|
||||||
bool beingDestroyed;
|
bool beingDestroyed;
|
||||||
epics::pvData::Mutex mutex;
|
epics::pvData::Mutex mutex;
|
||||||
|
|||||||
@@ -41,6 +41,7 @@ static Status notStartedStatus(Status::STATUSTYPE_ERROR,"not started");
|
|||||||
|
|
||||||
typedef Queue<MonitorElement> MonitorElementQueue;
|
typedef Queue<MonitorElement> MonitorElementQueue;
|
||||||
typedef std::tr1::shared_ptr<MonitorElementQueue> MonitorElementQueuePtr;
|
typedef std::tr1::shared_ptr<MonitorElementQueue> MonitorElementQueuePtr;
|
||||||
|
typedef std::tr1::shared_ptr<MonitorRequester> MonitorRequesterPtr;
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
@@ -78,7 +79,7 @@ private:
|
|||||||
{
|
{
|
||||||
return shared_from_this();
|
return shared_from_this();
|
||||||
}
|
}
|
||||||
MonitorRequester::shared_pointer monitorRequester;
|
MonitorRequester::weak_pointer monitorRequester;
|
||||||
PVRecordPtr pvRecord;
|
PVRecordPtr pvRecord;
|
||||||
MonitorState state;
|
MonitorState state;
|
||||||
PVCopyPtr pvCopy;
|
PVCopyPtr pvCopy;
|
||||||
@@ -221,7 +222,9 @@ void MonitorLocal::releaseActiveElement()
|
|||||||
activeElement->changedBitSet->clear();
|
activeElement->changedBitSet->clear();
|
||||||
activeElement->overrunBitSet->clear();
|
activeElement->overrunBitSet->clear();
|
||||||
}
|
}
|
||||||
monitorRequester->monitorEvent(getPtrSelf());
|
MonitorRequesterPtr requester = monitorRequester.lock();
|
||||||
|
if(!requester.get()) return;
|
||||||
|
requester->monitorEvent(getPtrSelf());
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -323,6 +326,8 @@ bool MonitorLocal::init(PVStructurePtr const & pvRequest)
|
|||||||
PVFieldPtr pvField;
|
PVFieldPtr pvField;
|
||||||
size_t queueSize = 2;
|
size_t queueSize = 2;
|
||||||
PVStructurePtr pvOptions = pvRequest->getSubField<PVStructure>("record._options");
|
PVStructurePtr pvOptions = pvRequest->getSubField<PVStructure>("record._options");
|
||||||
|
MonitorRequesterPtr requester = monitorRequester.lock();
|
||||||
|
if(!requester.get()) return false;
|
||||||
if(pvOptions) {
|
if(pvOptions) {
|
||||||
PVStringPtr pvString = pvOptions->getSubField<PVString>("queueSize");
|
PVStringPtr pvString = pvOptions->getSubField<PVString>("queueSize");
|
||||||
if(pvString) {
|
if(pvString) {
|
||||||
@@ -333,7 +338,7 @@ bool MonitorLocal::init(PVStructurePtr const & pvRequest)
|
|||||||
ss >> size;
|
ss >> size;
|
||||||
queueSize = size;
|
queueSize = size;
|
||||||
} catch (...) {
|
} catch (...) {
|
||||||
monitorRequester->message("queueSize " +pvString->get() + " illegal",errorMessage);
|
requester->message("queueSize " +pvString->get() + " illegal",errorMessage);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -344,19 +349,19 @@ bool MonitorLocal::init(PVStructurePtr const & pvRequest)
|
|||||||
pvRecord->getPVRecordStructure()->getPVStructure(),
|
pvRecord->getPVRecordStructure()->getPVStructure(),
|
||||||
pvRequest,"");
|
pvRequest,"");
|
||||||
if(!pvCopy) {
|
if(!pvCopy) {
|
||||||
monitorRequester->message("illegal pvRequest",errorMessage);
|
requester->message("illegal pvRequest",errorMessage);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
if(pvField->getField()->getType()!=structure) {
|
if(pvField->getField()->getType()!=structure) {
|
||||||
monitorRequester->message("illegal pvRequest",errorMessage);
|
requester->message("illegal pvRequest",errorMessage);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
pvCopy = PVCopy::create(
|
pvCopy = PVCopy::create(
|
||||||
pvRecord->getPVRecordStructure()->getPVStructure(),
|
pvRecord->getPVRecordStructure()->getPVStructure(),
|
||||||
pvRequest,"field");
|
pvRequest,"field");
|
||||||
if(!pvCopy) {
|
if(!pvCopy) {
|
||||||
monitorRequester->message("illegal pvRequest",errorMessage);
|
requester->message("illegal pvRequest",errorMessage);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -370,7 +375,7 @@ bool MonitorLocal::init(PVStructurePtr const & pvRequest)
|
|||||||
monitorElementArray.push_back(monitorElement);
|
monitorElementArray.push_back(monitorElement);
|
||||||
}
|
}
|
||||||
queue = MonitorElementQueuePtr(new MonitorElementQueue(monitorElementArray));
|
queue = MonitorElementQueuePtr(new MonitorElementQueue(monitorElementArray));
|
||||||
monitorRequester->monitorConnect(
|
requester->monitorConnect(
|
||||||
Status::Ok,
|
Status::Ok,
|
||||||
getPtrSelf(),
|
getPtrSelf(),
|
||||||
pvCopy->getStructure());
|
pvCopy->getStructure());
|
||||||
|
|||||||
@@ -26,6 +26,7 @@
|
|||||||
#include <epicsThread.h>
|
#include <epicsThread.h>
|
||||||
#include <iocsh.h>
|
#include <iocsh.h>
|
||||||
#include <shareLib.h>
|
#include <shareLib.h>
|
||||||
|
#include <epicsExit.h>
|
||||||
|
|
||||||
#include <pv/pvAccess.h>
|
#include <pv/pvAccess.h>
|
||||||
#include <pv/serverContext.h>
|
#include <pv/serverContext.h>
|
||||||
@@ -52,6 +53,9 @@ extern "C" void pvdbl(const iocshArgBuf *args)
|
|||||||
for(size_t i=0; i<xxx.size(); ++i) cout<< xxx[i] << endl;
|
for(size_t i=0; i<xxx.size(); ++i) cout<< xxx[i] << endl;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void channelProviderLocalExitHandler(void* /*pPrivate*/) {
|
||||||
|
getChannelProviderLocal()->destroy();
|
||||||
|
}
|
||||||
|
|
||||||
static void registerChannelProviderLocal(void)
|
static void registerChannelProviderLocal(void)
|
||||||
{
|
{
|
||||||
@@ -60,6 +64,7 @@ static void registerChannelProviderLocal(void)
|
|||||||
firstTime = 0;
|
firstTime = 0;
|
||||||
iocshRegister(&pvdblFuncDef, pvdbl);
|
iocshRegister(&pvdblFuncDef, pvdbl);
|
||||||
getChannelProviderLocal();
|
getChannelProviderLocal();
|
||||||
|
epicsAtExit(channelProviderLocalExitHandler, NULL);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user