Skip to content

Commit

Permalink
Merge pull request #75 from sveseli/master
Browse files Browse the repository at this point in the history
Support requests to apply a pvCopy filter plugin to a whole PVRecord structure by using a field name `_` in the pvRequest.
  • Loading branch information
anjohnson committed Dec 6, 2021
2 parents 0cf7065 + 182eee5 commit 05d54c6
Show file tree
Hide file tree
Showing 4 changed files with 60 additions and 6 deletions.
6 changes: 6 additions & 0 deletions documentation/RELEASE_NOTES.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,12 @@

This document summarizes the changes to the module between releases.

## Release 4.X.Y (EPICS 7.X.Y, MMM 20YY)

* Added support for the whole structure (master field) server side plugins. The whole structure
is identified as the `_` string, and the pvRequest string that applies a plugin to it
has the form `field(_[pluginXYZ=optionA:3;optionB:uniqueId])`.

## Release 4.6.0 (EPICS 7.0.6, Jul 2021)

* Access Security is now supported.
Expand Down
16 changes: 12 additions & 4 deletions src/copy/pvCopy.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -88,7 +88,6 @@ PVCopyPtr PVCopy::create(
bool result = pvCopy->init(pvStructure);
if(!result) return PVCopyPtr();
pvCopy->traverseMasterInitPlugin();
//cout << pvCopy->dump() << endl;
return pvCopy;
}

Expand Down Expand Up @@ -433,10 +432,19 @@ bool PVCopy::init(epics::pvData::PVStructurePtr const &pvRequest)
PVStructurePtr pvMasterStructure = pvMaster;
size_t len = pvRequest->getPVFields().size();
bool entireMaster = false;
if(len==0) entireMaster = true;
PVStructurePtr pvOptions;
if(len==1) {
pvOptions = pvRequest->getSubField<PVStructure>("_options");
if(len==0) {
entireMaster = true;
}
else {
// If "_" is in the request, but not in the master structure,
// then assume the top level PV structure is requested
PVStructurePtr masterFieldPtr = pvMaster->getSubField<PVStructure>("_");
PVStructurePtr requestFieldPtr = pvRequest->getSubField<PVStructure>("_");
if (!masterFieldPtr && requestFieldPtr) {
entireMaster = true;
pvOptions = requestFieldPtr->getSubField<PVStructure>("_options");
}
}
if(entireMaster) {
structure = pvMasterStructure->getStructure();
Expand Down
5 changes: 4 additions & 1 deletion src/database/pvRecord.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -418,7 +418,10 @@ void PVRecordField::postParent(PVRecordFieldPtr const & subField)
listener->dataPut(pvrs,subField);
}
PVRecordStructurePtr parent(this->parent.lock());
if(parent) parent->postParent(subField);
if(parent) {
parent->postParent(subField);
parent->callListener();
}
}

void PVRecordField::postSubField()
Expand Down
39 changes: 38 additions & 1 deletion test/src/testPVCopy.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -274,6 +274,33 @@ static void testPVScalarArray(
}
}

static void testMasterField(PVRecordPtr const& pvRecord)
{
CreateRequest::shared_pointer createRequest = CreateRequest::create();
PVStructurePtr pvRequest = createRequest->createRequest("field(_)");
if(debug) {
cout << "pvRequest" << *pvRequest << endl ;
}
PVStructurePtr pvStructureRecord = pvRecord->getPVRecordStructure()->getPVStructure();
PVCopyPtr pvCopy = PVCopy::create(pvStructureRecord,pvRequest,"");
PVStructurePtr pvMasterField = pvCopy->getPVMaster();
if(debug) {
cout << "PV structure from record" << endl << *pvStructureRecord << endl;
cout << "Master PV structure from copy" << endl << *pvMasterField << endl;
cout << "Master PV structure from copy offset " << pvMasterField->getFieldOffset() << endl;
}
testOk1(pvMasterField->getNumberFields() == pvStructureRecord->getNumberFields());
testOk1(pvMasterField->getFieldOffset() == 0);
PVStructurePtr pvStructureCopy = pvCopy->createPVStructure();
BitSetPtr bitSet = BitSetPtr(new BitSet(pvStructureCopy->getNumberFields()));
pvCopy->initCopy(pvStructureCopy, bitSet);
if(debug) {
cout << "PV structure from copy" << endl << *pvStructureCopy << endl;
cout << "PV structure from copy offset " << pvStructureCopy->getFieldOffset() << endl;
}
testOk1(pvMasterField->getNumberFields() == pvStructureCopy->getNumberFields());
}

static void scalarTest()
{
if(debug) {cout << endl << endl << "****scalarTest****" << endl;}
Expand Down Expand Up @@ -393,11 +420,21 @@ static void powerSupplyTest()
testPVScalar(valueNameRecord,valueNameCopy,pvRecord,pvCopy);
}

static void masterFieldTest()
{
if(debug) {
cout << endl << endl << "****masterFieldTest****" << endl;
}
PVRecordPtr pvRecord = createScalar("doubleRecord",pvDouble,"alarm,timeStamp,display");
testMasterField(pvRecord);
}

MAIN(testPVCopy)
{
testPlan(67);
testPlan(70);
scalarTest();
arrayTest();
powerSupplyTest();
masterFieldTest();
return 0;
}

0 comments on commit 05d54c6

Please sign in to comment.