10 #include <pv/sharedPtr.h> 14 #define epicsExportSharedSymbols 22 namespace epics {
namespace nt {
26 static FieldCreatePtr fieldCreate = getFieldCreate();
27 static PVDataCreatePtr pvDataCreate = getPVDataCreate();
31 StructureConstPtr NTNDArrayBuilder::createStructure()
41 const size_t NUMBER_OF_INDICES = DISPLAY_INDEX+1;
42 const size_t NUMBER_OF_STRUCTURES = 1 << NUMBER_OF_INDICES;
46 static StructureConstPtr ntndarrayStruc[NUMBER_OF_STRUCTURES];
47 static UnionConstPtr valueType;
48 static StructureConstPtr codecStruc;
49 static StructureConstPtr dimensionStruc;
50 static StructureConstPtr attributeStruc;
52 StructureConstPtr returnedStruc;
55 if (descriptor) index |= 1 << DISCRIPTOR_INDEX;
56 if (timeStamp) index |= 1 << TIMESTAMP_INDEX;
57 if (alarm) index |= 1 << ALARM_INDEX;
58 if (display) index |= 1 << DISPLAY_INDEX;
60 bool isExtended = !extraFieldNames.empty();
62 if (isExtended || !ntndarrayStruc[index])
64 StandardFieldPtr standardField = getStandardField();
65 FieldBuilderPtr fb = fieldCreate->createFieldBuilder();
69 for (
int i = pvBoolean; i < pvString; ++i)
71 ScalarType st =
static_cast<ScalarType
>(i);
72 fb->addArray(std::string(ScalarTypeFunc::name(st)) +
"Value", st);
74 valueType = fb->createUnion();
79 codecStruc = fb->setId(
"codec_t")->
80 add(
"name", pvString)->
81 add(
"parameters", fieldCreate->createVariantUnion())->
87 dimensionStruc = fb->setId(
"dimension_t")->
89 add(
"offset", pvInt)->
90 add(
"fullSize", pvInt)->
91 add(
"binning", pvInt)->
92 add(
"reverse", pvBoolean)->
98 attributeStruc = NTNDArrayAttribute::createBuilder()->createStructure();
101 fb->setId(NTNDArray::URI)->
102 add(
"value", valueType)->
103 add(
"codec", codecStruc)->
104 add(
"compressedSize", pvLong)->
105 add(
"uncompressedSize", pvLong)->
106 addArray(
"dimension", dimensionStruc)->
107 add(
"uniqueId", pvInt)->
108 add(
"dataTimeStamp", standardField->timeStamp())->
109 addArray(
"attribute", attributeStruc);
112 fb->add(
"descriptor", pvString);
115 fb->add(
"alarm", standardField->alarm());
118 fb->add(
"timeStamp", standardField->timeStamp());
121 fb->add(
"display", standardField->display());
123 size_t extraCount = extraFieldNames.size();
124 for (
size_t i = 0; i< extraCount; i++)
125 fb->add(extraFieldNames[i], extraFields[i]);
127 returnedStruc = fb->createStructure();
130 ntndarrayStruc[index] = returnedStruc;
134 return ntndarrayStruc[index];
137 return returnedStruc;
140 NTNDArrayBuilder::shared_pointer NTNDArrayBuilder::addDescriptor()
143 return shared_from_this();
146 NTNDArrayBuilder::shared_pointer NTNDArrayBuilder::addAlarm()
149 return shared_from_this();
152 NTNDArrayBuilder::shared_pointer NTNDArrayBuilder::addTimeStamp()
155 return shared_from_this();
158 NTNDArrayBuilder::shared_pointer NTNDArrayBuilder::addDisplay()
161 return shared_from_this();
164 PVStructurePtr NTNDArrayBuilder::createPVStructure()
166 return getPVDataCreate()->createPVStructure(createStructure());
174 NTNDArrayBuilder::NTNDArrayBuilder()
179 void NTNDArrayBuilder::reset()
185 extraFieldNames.clear();
189 NTNDArrayBuilder::shared_pointer NTNDArrayBuilder::add(
string const & name, FieldConstPtr
const & field)
191 extraFields.push_back(field); extraFieldNames.push_back(name);
192 return shared_from_this();
197 const std::string NTNDArray::URI(
"epics:nt/NTNDArray:1.0");
198 const std::string
ntAttrStr(
"epics:nt/NTAttribute:1.0");
200 NTNDArray::shared_pointer NTNDArray::wrap(PVStructurePtr
const & pvStructure)
202 if(!isCompatible(pvStructure))
return shared_pointer();
203 return wrapUnsafe(pvStructure);
206 NTNDArray::shared_pointer NTNDArray::wrapUnsafe(PVStructurePtr
const & pvStructure)
208 return shared_pointer(
new NTNDArray(pvStructure));
211 bool NTNDArray::is_a(StructureConstPtr
const & structure)
213 return NTUtils::is_a(structure->getID(), URI);
216 bool NTNDArray::is_a(PVStructurePtr
const & pvStructure)
218 return is_a(pvStructure->getStructure());
224 result.
is<Union>(Union::defaultId());
226 for (
int i = pvBoolean; i < pvString; ++i) {
227 ScalarType type =
static_cast<ScalarType
>(i);
228 string name(ScalarTypeFunc::name(type));
229 result.
has<ScalarArray>(name +
"Value");
238 .
is<Structure>(
"codec_t")
240 .
has<Union>(
"parameters");
246 .
is<StructureArray>(
"dimension_t[]")
248 .
has<Scalar>(
"offset")
249 .has<Scalar>(
"fullSize")
250 .
has<Scalar>(
"binning")
251 .has<Scalar>(
"reverse");
255 bool NTNDArray::isCompatible(StructureConstPtr
const &structure)
264 .has<&isValue>(
"value")
265 .
has<&isCodec>(
"codec")
266 .has<Scalar>(
"compressedSize")
267 .
has<Scalar>(
"uncompressedSize")
268 .has<&isDimension>(
"dimension")
269 .
has<Scalar>(
"uniqueId")
270 .has<&NTField::isTimeStamp, Structure>(
"dataTimeStamp")
271 .
has<&NTNDArrayAttribute::isAttribute, StructureArray>(
"attribute")
272 .maybeHas<Scalar>(
"descriptor")
273 .
maybeHas<&NTField::isAlarm, Structure>(
"alarm")
274 .maybeHas<&NTField::isTimeStamp, Structure>(
"timeStamp")
275 .
maybeHas<&NTField::isDisplay, Structure>(
"display")
280 bool NTNDArray::isCompatible(PVStructurePtr
const & pvStructure)
282 if(!pvStructure.get())
return false;
284 return isCompatible(pvStructure->getStructure());
287 bool NTNDArray::isValid()
289 int64 valueSize = getValueSize();
290 int64 compressedSize = getCompressedDataSize()->get();
291 if (valueSize != compressedSize)
294 long expectedUncompressed = getExpectedUncompressedSize();
295 long uncompressedSize = getUncompressedDataSize()->get();
296 if (uncompressedSize != expectedUncompressed)
299 std::string codecName = getCodec()->getSubField<PVString>(
"name")->
get();
300 if (codecName ==
"" && valueSize < uncompressedSize)
306 int64 NTNDArray::getExpectedUncompressedSize()
309 PVStructureArrayPtr pvDim = getDimension();
311 if (pvDim->getLength() != 0)
313 PVStructureArray::const_svector data = pvDim->view();
314 size = getValueTypeSize();
315 for (PVStructureArray::const_svector::const_iterator it = data.begin();
316 it != data.end(); ++it )
318 PVStructurePtr dim = *it;
319 size *= dim->getSubField<PVInt>(
"size")->
get();
326 int64 NTNDArray::getValueSize()
329 PVScalarArrayPtr storedValue = getValue()->get<PVScalarArray>();
330 if (!storedValue.get())
332 size = storedValue->getLength()*getValueTypeSize();
337 int64 NTNDArray::getValueTypeSize()
340 PVScalarArrayPtr storedValue = getValue()->get<PVScalarArray>();
341 if (storedValue.get())
343 switch (storedValue->getScalarArray()->getElementType())
381 bool NTNDArray::attachTimeStamp(PVTimeStamp &pvTimeStamp)
const 383 PVStructurePtr ts = getTimeStamp();
385 return pvTimeStamp.attach(ts);
390 bool NTNDArray::attachDataTimeStamp(PVTimeStamp &pvTimeStamp)
const 392 PVStructurePtr ts = getDataTimeStamp();
394 return pvTimeStamp.attach(ts);
399 bool NTNDArray::attachAlarm(PVAlarm &pvAlarm)
const 401 PVStructurePtr al = getAlarm();
403 return pvAlarm.attach(al);
408 bool NTNDArray::attachDisplay(PVDisplay &pvDisplay)
const 410 PVStructurePtr dp = getDisplay();
412 return pvDisplay.attach(dp);
417 PVStructurePtr NTNDArray::getPVStructure()
const 422 PVUnionPtr NTNDArray::getValue()
const 424 return pvNTNDArray->getSubField<PVUnion>(
"value");
427 PVStructurePtr NTNDArray::getCodec()
const 429 return pvNTNDArray->getSubField<PVStructure>(
"codec");
432 PVLongPtr NTNDArray::getCompressedDataSize()
const 434 return pvNTNDArray->getSubField<PVLong>(
"compressedSize");
437 PVLongPtr NTNDArray::getUncompressedDataSize()
const 439 return pvNTNDArray->getSubField<PVLong>(
"uncompressedSize");
442 PVStructureArrayPtr NTNDArray::getDimension()
const 444 return pvNTNDArray->getSubField<PVStructureArray>(
"dimension");
447 PVIntPtr NTNDArray::getUniqueId()
const 449 return pvNTNDArray->getSubField<PVInt>(
"uniqueId");
452 PVStructurePtr NTNDArray::getDataTimeStamp()
const 454 return pvNTNDArray->getSubField<PVStructure>(
"dataTimeStamp");
457 PVStructureArrayPtr NTNDArray::getAttribute()
const 459 return pvNTNDArray->getSubField<PVStructureArray>(
"attribute");
462 PVStringPtr NTNDArray::getDescriptor()
const 464 return pvNTNDArray->getSubField<PVString>(
"descriptor");
467 PVStructurePtr NTNDArray::getTimeStamp()
const 469 return pvNTNDArray->getSubField<PVStructure>(
"timeStamp");
472 PVStructurePtr NTNDArray::getAlarm()
const 474 return pvNTNDArray->getSubField<PVStructure>(
"alarm");
477 PVStructurePtr NTNDArray::getDisplay()
const 479 return pvNTNDArray->getSubField<PVStructure>(
"display");
483 NTNDArray::NTNDArray(PVStructurePtr
const & pvStructure) :
484 pvNTNDArray(pvStructure)
std::tr1::shared_ptr< detail::NTNDArrayBuilder > NTNDArrayBuilderPtr
Result & maybeHas(const std::string &name)
Validation methods for NT types.
Interface for in-line creating of NTNDArray.
std::tr1::shared_ptr< NTNDArray > NTNDArrayPtr
Result & has(const std::string &name)
Convenience Class for NTNDArray.
const std::string ntAttrStr("epics:nt/NTAttribute:1.0")