Compare commits
63 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
6a62f9c082 | ||
|
|
c5112ffa11 | ||
|
|
7b9fda4e81 | ||
|
|
278e531806 | ||
|
|
047de40642 | ||
|
|
4e671a1c21 | ||
|
|
f36c8ce280 | ||
|
|
e77f2c91d7 | ||
|
|
82b0d5ce5f | ||
|
|
6117035863 | ||
|
|
c86e31ad99 | ||
|
|
f506fe1c0e | ||
|
|
554dc06eda | ||
|
|
80e1dfd142 | ||
|
|
6db5cf60dc | ||
|
|
63d181a0ac | ||
|
|
73c4896cce | ||
|
|
5b1b5ab904 | ||
|
|
80a537bc4c | ||
|
|
2a8a1d3736 | ||
|
|
61fbfa0684 | ||
|
|
f06a6bfe7b | ||
|
|
587f81f511 | ||
|
|
435ca63d1b | ||
|
|
64bb660f44 | ||
|
|
8bf24de0b3 | ||
|
|
943ea633a4 | ||
|
|
b1d5f7d7e5 | ||
|
|
188b94ce19 | ||
|
|
515282abfe | ||
|
|
efbdb722e7 | ||
|
|
e980823294 | ||
|
|
3692f4fb3c | ||
|
|
3e645f3c79 | ||
|
|
6127763302 | ||
|
|
19a181b38f | ||
|
|
2818b0384c | ||
|
|
36faf8c2ea | ||
|
|
a208171250 | ||
|
|
b8a2b7cff6 | ||
|
|
2a08cbc1a0 | ||
|
|
62bc6c1fb1 | ||
|
|
1098650421 | ||
|
|
15d85c2f87 | ||
|
|
16fb3f0339 | ||
|
|
37f6dff065 | ||
|
|
baf8832fc9 | ||
|
|
b558e11ede | ||
|
|
103cdabff1 | ||
|
|
57e33c8f7d | ||
|
|
da0f65c2d3 | ||
|
|
6535c075f3 | ||
|
|
f3c0b9544c | ||
|
|
3609fd4745 | ||
|
|
622e140622 | ||
|
|
a4954c3825 | ||
|
|
b6e1b9c203 | ||
|
|
34a35c2658 | ||
|
|
90b7c9a17c | ||
|
|
c72297020b | ||
|
|
f07b601dce | ||
|
|
63c62a2aae | ||
|
|
6888a9d340 |
7
.hgtags
7
.hgtags
@@ -10,3 +10,10 @@ d70c5ad29163306f50979a95b5aebbe9a93cfe76 2.0-BETA
|
|||||||
2a289ff41e2ed3a0247877306c2db7b266f3b6b8 3.0.1
|
2a289ff41e2ed3a0247877306c2db7b266f3b6b8 3.0.1
|
||||||
58092712d092ee521d1e1c8fa596a67f7d113ee9 3.0.2
|
58092712d092ee521d1e1c8fa596a67f7d113ee9 3.0.2
|
||||||
40b681ffc5cd609320e3f8ffc8eb6aa3bfdfbf19 before_merge_changesAfter3_0_2
|
40b681ffc5cd609320e3f8ffc8eb6aa3bfdfbf19 before_merge_changesAfter3_0_2
|
||||||
|
260f35b9c6cad113f242c83c89be9cdac802f610 3.1.0
|
||||||
|
1348c22b125861ecb9da95b23f20314b167ee155 4.0.0
|
||||||
|
1348c22b125861ecb9da95b23f20314b167ee155 4.0.0
|
||||||
|
9c62aaa83b9db6ad69740a6bb46d6529e0e60b78 4.0.0
|
||||||
|
9c62aaa83b9db6ad69740a6bb46d6529e0e60b78 4.0.0
|
||||||
|
f9f187685032ebf4b108c759be196fda055c9e42 4.0.0
|
||||||
|
b0d39d12d743b82038066955db6bb957b1f2f767 4.0.1
|
||||||
|
|||||||
2
LICENSE
2
LICENSE
@@ -2,7 +2,7 @@
|
|||||||
Copyright (c) 2008 Martin R. Kraimer
|
Copyright (c) 2008 Martin R. Kraimer
|
||||||
Copyright (c) 2006 The University of Chicago, as Operator of Argonne
|
Copyright (c) 2006 The University of Chicago, as Operator of Argonne
|
||||||
National Laboratory.
|
National Laboratory.
|
||||||
Copyright (c) 2006 Deutsches Elektronen-Synchroton,
|
Copyright (c) 2006 Deutsches Elektronen-Synchrotron,
|
||||||
Member of the Helmholtz Association, (DESY), HAMBURG, GERMANY.
|
Member of the Helmholtz Association, (DESY), HAMBURG, GERMANY.
|
||||||
Copyright (c) 2007 Control System Laboratory,
|
Copyright (c) 2007 Control System Laboratory,
|
||||||
(COSYLAB) Ljubljana Slovenia
|
(COSYLAB) Ljubljana Slovenia
|
||||||
|
|||||||
@@ -580,7 +580,7 @@ WARN_LOGFILE =
|
|||||||
# directories like "/usr/src/myproject". Separate the files or directories
|
# directories like "/usr/src/myproject". Separate the files or directories
|
||||||
# with spaces.
|
# with spaces.
|
||||||
|
|
||||||
INPUT = ../pvDataApp
|
INPUT = ../include/pv
|
||||||
|
|
||||||
# This tag can be used to specify the character encoding of the source files
|
# This tag can be used to specify the character encoding of the source files
|
||||||
# that doxygen parses. Internally doxygen uses the UTF-8 encoding, which is
|
# that doxygen parses. Internally doxygen uses the UTF-8 encoding, which is
|
||||||
|
|||||||
58
documentation/RELEASE_NOTES.html
Normal file
58
documentation/RELEASE_NOTES.html
Normal file
@@ -0,0 +1,58 @@
|
|||||||
|
<h1>Release 4.0 IN DEVELOPMENT</h1>
|
||||||
|
<p>The main changes since release 3.0.2 are:</p>
|
||||||
|
<ul>
|
||||||
|
<li>array semantics now enforce Copy On Write.</li>
|
||||||
|
<li>String no longer defined.</li>
|
||||||
|
<li>timeStamp and valueAlarm name changes</li>
|
||||||
|
<li>toString replaced by stream I/O </li>
|
||||||
|
<li>union is new type.</li>
|
||||||
|
<li>copy is new.</li>
|
||||||
|
<li>monitorPlugin is new.</li>
|
||||||
|
</ul>
|
||||||
|
<h2>New Semantics for Arrays</h2>
|
||||||
|
<p>PVScalarArray, PVStructureArray, and PVUnionArray all enforce COW (Copy On Write) Semantics.
|
||||||
|
In order to limit memory usage the storage for raw data is managed via a new shared_vector facility.
|
||||||
|
This allows multiple instances of array data to use the shared raw data.
|
||||||
|
COW is implemented via shared_vectors of const data, i. e. data that can not be modified.</p>
|
||||||
|
<h2>String no longer defined</h2>
|
||||||
|
<p>This is replaced by std::string.</p>
|
||||||
|
<h2>timeStamp and valueAlarm name changes</h2>
|
||||||
|
<p>In timeStamp nanoSeconds is changed to nanoseconds.</p>
|
||||||
|
<p>In valueAlarm hystersis is changed to hysteresis</p>
|
||||||
|
<h2>toString replaced by stream I/O</h2>
|
||||||
|
<p>pvData.h and pvIntrospect no longer defines toString
|
||||||
|
Instead they have stream support.
|
||||||
|
pvIntrospect uses method dump and pvData uses dumpValue.
|
||||||
|
For example:</p>
|
||||||
|
<pre><code> PVDoublePtr pvValue;
|
||||||
|
String buffer;
|
||||||
|
pvValue->toString(&buffer);
|
||||||
|
cout << buffer << endl;
|
||||||
|
buffer.clear();
|
||||||
|
pvValue->getField()->toString(&buffer);
|
||||||
|
cout << buffer << evdl;
|
||||||
|
</code></pre>
|
||||||
|
<p>is replaced by</p>
|
||||||
|
<pre><code> PVDoublePtr pvValue;
|
||||||
|
cout << *pvValue << endl
|
||||||
|
cout << *pvValue->getField() << endl;
|
||||||
|
</code></pre>
|
||||||
|
<h2>union is a new basic type.</h2>
|
||||||
|
<p>There are two new basic types: union_t and unionArray.</p>
|
||||||
|
<p>A union is like a structure that has a single subfield.
|
||||||
|
There are two flavors:</p>
|
||||||
|
<ul>
|
||||||
|
<li><b>varient union</b> The field can have any type.</li>
|
||||||
|
<li><b>union</b> The field can any of specified set of types.</li>
|
||||||
|
</ul>
|
||||||
|
<p>The field type can be dynamically changed.</p>
|
||||||
|
<h2>copy</h2>
|
||||||
|
<p>This consists of createRequest and pvCopy.
|
||||||
|
createRequest was moved from pvAccess to here.
|
||||||
|
pvCopy is moved from pvDatabaseCPP and now depends
|
||||||
|
only on pvData, i. e. it no longer has any knowledge of PVRecord.</p>
|
||||||
|
<h2>monitorPlugin</h2>
|
||||||
|
<p>This is for is for use by code that implements pvAccess monitors.
|
||||||
|
This is prototype and is subject to debate.</p>
|
||||||
|
<h1>Release 3.0.2</h1>
|
||||||
|
<p>This was the starting point for RELEASE_NOTES</p>
|
||||||
@@ -1,9 +1,12 @@
|
|||||||
Release release/3.1 IN DEVELOPMENT
|
Release 4.0 IN DEVELOPMENT
|
||||||
===========
|
===========
|
||||||
|
|
||||||
The main changes since release 3.0.2 are:
|
The main changes since release 3.0.2 are:
|
||||||
|
|
||||||
* array semantics now enforce Copy On Write.
|
* array semantics now enforce Copy On Write.
|
||||||
|
* String no longer defined.
|
||||||
|
* timeStamp and valueAlarm name changes
|
||||||
|
* toString replaced by stream I/O
|
||||||
* union is new type.
|
* union is new type.
|
||||||
* copy is new.
|
* copy is new.
|
||||||
* monitorPlugin is new.
|
* monitorPlugin is new.
|
||||||
@@ -16,6 +19,44 @@ In order to limit memory usage the storage for raw data is managed via a new sha
|
|||||||
This allows multiple instances of array data to use the shared raw data.
|
This allows multiple instances of array data to use the shared raw data.
|
||||||
COW is implemented via shared_vectors of const data, i. e. data that can not be modified.
|
COW is implemented via shared_vectors of const data, i. e. data that can not be modified.
|
||||||
|
|
||||||
|
|
||||||
|
String no longer defined
|
||||||
|
---------
|
||||||
|
|
||||||
|
This is replaced by std::string.
|
||||||
|
|
||||||
|
|
||||||
|
timeStamp and valueAlarm name changes
|
||||||
|
--------------
|
||||||
|
|
||||||
|
In timeStamp nanoSeconds is changed to nanoseconds.
|
||||||
|
|
||||||
|
In valueAlarm hystersis is changed to hysteresis
|
||||||
|
|
||||||
|
|
||||||
|
toString replaced by stream I/O
|
||||||
|
---------
|
||||||
|
|
||||||
|
pvData.h and pvIntrospect no longer defines toString
|
||||||
|
Instead they have stream support.
|
||||||
|
pvIntrospect uses method dump and pvData uses dumpValue.
|
||||||
|
For example:
|
||||||
|
|
||||||
|
PVDoublePtr pvValue;
|
||||||
|
String buffer;
|
||||||
|
pvValue->toString(&buffer);
|
||||||
|
cout << buffer << endl;
|
||||||
|
buffer.clear();
|
||||||
|
pvValue->getField()->toString(&buffer);
|
||||||
|
cout << buffer << evdl;
|
||||||
|
|
||||||
|
is replaced by
|
||||||
|
|
||||||
|
PVDoublePtr pvValue;
|
||||||
|
cout << *pvValue << endl
|
||||||
|
cout << *pvValue->getField() << endl;
|
||||||
|
|
||||||
|
|
||||||
union is a new basic type.
|
union is a new basic type.
|
||||||
------------
|
------------
|
||||||
|
|
||||||
@@ -41,6 +82,7 @@ monitorPlugin
|
|||||||
-------------
|
-------------
|
||||||
|
|
||||||
This is for is for use by code that implements pvAccess monitors.
|
This is for is for use by code that implements pvAccess monitors.
|
||||||
|
This is prototype and is subject to debate.
|
||||||
|
|
||||||
Release 3.0.2
|
Release 3.0.2
|
||||||
==========
|
==========
|
||||||
|
|||||||
17
documentation/TODO.html
Normal file
17
documentation/TODO.html
Normal file
@@ -0,0 +1,17 @@
|
|||||||
|
<h1>TODO</h1>
|
||||||
|
<h2>printer</h2>
|
||||||
|
<p>pv/printer.h is not used.</p>
|
||||||
|
<h2>doxygen</h2>
|
||||||
|
<p>There is a lot of public code that does not have doxygen tags.</p>
|
||||||
|
<h2>postMonitor: PVUnion, PVUnionArray, and PVStructureArray</h2>
|
||||||
|
<p>PVUnion, PVUnionArray, and PVStructureArray all have elements
|
||||||
|
that are treated like a top level field.</p>
|
||||||
|
<p>Currently if a subField of any of these is changed postMonitor is not called for the field itself.</p>
|
||||||
|
<p>David asked if this could be changed so that it is called.
|
||||||
|
Marty thinks this may not be a good idea.</p>
|
||||||
|
<h2>valueAlarm</h2>
|
||||||
|
<p>normativeTypes.html describes valueAlarm only for a value field that has type
|
||||||
|
double.
|
||||||
|
The implementation also supports all the numeric scalar types.</p>
|
||||||
|
<h2>monitorPlugin</h2>
|
||||||
|
<p>A debate is on-going about what semantics should be.</p>
|
||||||
@@ -1,33 +1,10 @@
|
|||||||
TODO
|
TODO
|
||||||
===========
|
===========
|
||||||
|
|
||||||
toString, dumpValue, printer, and streams
|
printer
|
||||||
------------
|
------------
|
||||||
|
|
||||||
The way to print introspection and data instances is not consistent.
|
pv/printer.h is not used.
|
||||||
This needs work.
|
|
||||||
Some items that need work are:
|
|
||||||
|
|
||||||
* Introspection has no support for streams. Only for toString.
|
|
||||||
* data has problems. toString is implemented by calling Convert::getString.
|
|
||||||
It look like this was intended to use printer but that did nor properly indent fields of structures.
|
|
||||||
|
|
||||||
The current implementation is:
|
|
||||||
|
|
||||||
void Convert::getString(StringBuilder buf,PVField const *pvField,int /*indentLevel*/)
|
|
||||||
{
|
|
||||||
// TODO indextLevel ignored
|
|
||||||
std::ostringstream strm;
|
|
||||||
strm << pvField->dumpValue(strm) << std::endl;
|
|
||||||
// PrinterPlain p;
|
|
||||||
// p.setStream(strm);
|
|
||||||
// p.print(*pvField);
|
|
||||||
strm.str().swap(*buf);
|
|
||||||
}
|
|
||||||
|
|
||||||
Thus it just uses dumpValue.
|
|
||||||
What should it do?
|
|
||||||
If printer is used it must do proper indentation.
|
|
||||||
|
|
||||||
doxygen
|
doxygen
|
||||||
-------
|
-------
|
||||||
@@ -35,20 +12,27 @@ doxygen
|
|||||||
There is a lot of public code that does not have doxygen tags.
|
There is a lot of public code that does not have doxygen tags.
|
||||||
|
|
||||||
|
|
||||||
|
postMonitor: PVUnion, PVUnionArray, and PVStructureArray
|
||||||
|
--------
|
||||||
|
|
||||||
|
PVUnion, PVUnionArray, and PVStructureArray all have elements
|
||||||
|
that are treated like a top level field.
|
||||||
|
|
||||||
|
Currently if a subField of any of these is changed postMonitor is not called for the field itself.
|
||||||
|
|
||||||
|
David asked if this could be changed so that it is called.
|
||||||
|
Marty thinks this may not be a good idea.
|
||||||
|
|
||||||
|
|
||||||
|
valueAlarm
|
||||||
|
---------
|
||||||
|
|
||||||
|
normativeTypes.html describes valueAlarm only for a value field that has type
|
||||||
|
double.
|
||||||
|
The implementation also supports all the numeric scalar types.
|
||||||
|
|
||||||
monitorPlugin
|
monitorPlugin
|
||||||
-------------
|
-------------
|
||||||
|
|
||||||
A debate is on-going about what semantics should be.
|
A debate is on-going about what semantics should be.
|
||||||
|
|
||||||
PVFieldConstPtr etc
|
|
||||||
-------------------
|
|
||||||
|
|
||||||
In pvDataCPP.html look at the monoitorPlugin example.
|
|
||||||
It has a discussion of a possible need for shared pointers that can not be used to modify data.
|
|
||||||
This in addition to PVFieldPtr should PVFieldConstPtr exist.
|
|
||||||
But this means that all methods defined in pvDataCPP must be checked.
|
|
||||||
This is a BIG job.
|
|
||||||
|
|
||||||
Release 3.0.2
|
|
||||||
==========
|
|
||||||
This was the starting point for RELEASE_NOTES
|
|
||||||
|
|||||||
@@ -52,7 +52,7 @@ provides a language independent overview of <b>copy</b> and <b>monitor</b>.
|
|||||||
</p>
|
</p>
|
||||||
<p>
|
<p>
|
||||||
<b>NOTE:pvRequest.html</b> must be updated since it is based on an earlier version of pvCopy that
|
<b>NOTE:pvRequest.html</b> must be updated since it is based on an earlier version of pvCopy that
|
||||||
had knowlege of PVRecord. The C++ version was implemented in pvDatabaseCPP
|
had knowledge of PVRecord. The C++ version was implemented in pvDatabaseCPP
|
||||||
and the Java version on pvIOCJava.
|
and the Java version on pvIOCJava.
|
||||||
At present only the C++ version of the new API for pvCopy is implemented.
|
At present only the C++ version of the new API for pvCopy is implemented.
|
||||||
</p>
|
</p>
|
||||||
@@ -65,13 +65,13 @@ At present only the C++ version of the new API for pvCopy is implemented.
|
|||||||
Given an ascii string createRequest creates a PVStructure that provides
|
Given an ascii string createRequest creates a PVStructure that provides
|
||||||
a pvData representation of the information from the ascii string.
|
a pvData representation of the information from the ascii string.
|
||||||
It is this structure that can be passed to the channel create methods.<br />
|
It is this structure that can be passed to the channel create methods.<br />
|
||||||
The information in a pvRequest selects an arbitrarary subset of the
|
The information in a pvRequest selects an arbitrary subset of the
|
||||||
fields in a top level structure that resides in the server.
|
fields in a top level structure that resides in the server.
|
||||||
In addition options can be specified. Both global and field specific
|
In addition options can be specified. Both global and field specific
|
||||||
options can be specified.
|
options can be specified.
|
||||||
</dd>
|
</dd>
|
||||||
<dt>pvCopy</dt>
|
<dt>pvCopy</dt>
|
||||||
<dd>This is a faculity used by channel providers.
|
<dd>This is a facility used by channel providers.
|
||||||
It provides client specific code that manages a copy of an arbitrary
|
It provides client specific code that manages a copy of an arbitrary
|
||||||
subset of the fields in a top level structure that resides in the
|
subset of the fields in a top level structure that resides in the
|
||||||
provider. It also allows provider access to options specified
|
provider. It also allows provider access to options specified
|
||||||
@@ -185,7 +185,7 @@ where
|
|||||||
This is the method for creating a PVCopy instance.<br/>
|
This is the method for creating a PVCopy instance.<br/>
|
||||||
<dl>
|
<dl>
|
||||||
<dt>pvMaster</dt>
|
<dt>pvMaster</dt>
|
||||||
<dd>the top level sructure managed by the server.</dd>
|
<dd>the top level structure managed by the server.</dd>
|
||||||
<dt>pvRequest</dt>
|
<dt>pvRequest</dt>
|
||||||
<dd>selects the set of subfields desired
|
<dd>selects the set of subfields desired
|
||||||
and options for each field.</dd>
|
and options for each field.</dd>
|
||||||
@@ -241,12 +241,12 @@ where
|
|||||||
<dt>updateCopyFromBitSet</dt>
|
<dt>updateCopyFromBitSet</dt>
|
||||||
<dd>
|
<dd>
|
||||||
For each set bit in bitSet set the field in copyPVStructure to the value
|
For each set bit in bitSet set the field in copyPVStructure to the value
|
||||||
of the corrseponding field in pvMaster.
|
of the corresponding field in pvMaster.
|
||||||
</dd>
|
</dd>
|
||||||
<dt>updateMaster</dt>
|
<dt>updateMaster</dt>
|
||||||
<dd>
|
<dd>
|
||||||
For each set bit in bitSet set the field in pvMaster to the value
|
For each set bit in bitSet set the field in pvMaster to the value
|
||||||
of the corrseponding field in copyPVStructure.
|
of the corresponding field in copyPVStructure.
|
||||||
|
|
||||||
</dd>
|
</dd>
|
||||||
<dt>getOptions</dt>
|
<dt>getOptions</dt>
|
||||||
@@ -266,7 +266,7 @@ where
|
|||||||
<p>This consists of two components:
|
<p>This consists of two components:
|
||||||
<dl>
|
<dl>
|
||||||
<dt>monitor</dt>
|
<dt>monitor</dt>
|
||||||
<dd>Used by code that implements pvAccess montors.</dd>
|
<dd>Used by code that implements pvAccess monitors.</dd>
|
||||||
<dt>monitorPlugin</dt>
|
<dt>monitorPlugin</dt>
|
||||||
<dd>Code that provides special semantics for monitors.</dd>
|
<dd>Code that provides special semantics for monitors.</dd>
|
||||||
</dl>
|
</dl>
|
||||||
@@ -346,7 +346,7 @@ Note that each client has it's own queue that is not shared with other client.
|
|||||||
<dt>start</dt>
|
<dt>start</dt>
|
||||||
<dd>
|
<dd>
|
||||||
Start monitoring.
|
Start monitoring.
|
||||||
This will result in a an inital monitor that has the current value
|
This will result in a an initial monitor that has the current value
|
||||||
of all fields.
|
of all fields.
|
||||||
</dd>
|
</dd>
|
||||||
<dt>stop</dt>
|
<dt>stop</dt>
|
||||||
@@ -356,11 +356,11 @@ Note that each client has it's own queue that is not shared with other client.
|
|||||||
<dt>poll</dt>
|
<dt>poll</dt>
|
||||||
<dd>
|
<dd>
|
||||||
Called to get a monitor element.
|
Called to get a monitor element.
|
||||||
If no new elemants are available then a null pointer is returned.
|
If no new elements are available then a null pointer is returned.
|
||||||
</dd>
|
</dd>
|
||||||
<dt>release</dt>
|
<dt>release</dt>
|
||||||
<dd>
|
<dd>
|
||||||
Release the monotor element.
|
Release the monitor element.
|
||||||
The caller owns the monitor element between the calls to poll and release.
|
The caller owns the monitor element between the calls to poll and release.
|
||||||
</dd>
|
</dd>
|
||||||
<dl>
|
<dl>
|
||||||
@@ -488,7 +488,7 @@ It has methods:</p>
|
|||||||
<dd>
|
<dd>
|
||||||
MonitorPluginManager is a singleton.
|
MonitorPluginManager is a singleton.
|
||||||
The first call to get will create the single instance.
|
The first call to get will create the single instance.
|
||||||
Further calls will rerurn the single instance.
|
Further calls will return the single instance.
|
||||||
</dd>
|
</dd>
|
||||||
<dt>addPlugin</dt>
|
<dt>addPlugin</dt>
|
||||||
<dd>
|
<dd>
|
||||||
@@ -496,18 +496,18 @@ It has methods:</p>
|
|||||||
</dd>
|
</dd>
|
||||||
<dt>findPlugin</dt>
|
<dt>findPlugin</dt>
|
||||||
<dd>
|
<dd>
|
||||||
Find a plugin. A NULL shared pointer is reurned if it has not been added.
|
Find a plugin. A NULL shared pointer is returned if it has not been added.
|
||||||
</dd>
|
</dd>
|
||||||
<dt>showNames</dt>
|
<dt>showNames</dt>
|
||||||
<dd>
|
<dd>
|
||||||
Show the names of all puugins that have been added.
|
Show the names of all plugins that have been added.
|
||||||
</dd>
|
</dd>
|
||||||
</dl>
|
</dl>
|
||||||
<p><b>NOTE:</b>
|
<p><b>NOTE:</b>
|
||||||
Should the method <b>causeMonitor</b>
|
Should the method <b>causeMonitor</b>
|
||||||
have arguments <b>pvField</b> and <b>pvTop</b>
|
have arguments <b>pvField</b> and <b>pvTop</b>
|
||||||
be defined so that they can not be modfied.
|
be defined so that they can not be modified.
|
||||||
This would be posssible if the following was defined:
|
This would be possible if the following was defined:
|
||||||
<pre>
|
<pre>
|
||||||
typedef std::tr1::shared_ptr<const PVField> PVFieldConstPtr;
|
typedef std::tr1::shared_ptr<const PVField> PVFieldConstPtr;
|
||||||
typedef std::tr1::shared_ptr<const PVStructure> PVStructureConstPtr;
|
typedef std::tr1::shared_ptr<const PVStructure> PVStructureConstPtr;
|
||||||
@@ -519,7 +519,7 @@ virtual bool causeMonitor(
|
|||||||
PVStructureConstPtr const &pvTop,
|
PVStructureConstPtr const &pvTop,
|
||||||
MonitorElementPtr const &monitorElement) = 0;
|
MonitorElementPtr const &monitorElement) = 0;
|
||||||
</pre>
|
</pre>
|
||||||
But just adding these definitions is not sufficent.
|
But just adding these definitions is not sufficient.
|
||||||
In addition all methods defined in pvDataCPP must be checked.
|
In addition all methods defined in pvDataCPP must be checked.
|
||||||
In particular many of the methods in <b>Convert</b> must have
|
In particular many of the methods in <b>Convert</b> must have
|
||||||
their arguments modified.
|
their arguments modified.
|
||||||
@@ -545,15 +545,15 @@ structure powerSupply
|
|||||||
structure power
|
structure power
|
||||||
double value
|
double value
|
||||||
structure alarm
|
structure alarm
|
||||||
struvture display
|
structure display
|
||||||
structure voltage
|
structure voltage
|
||||||
double value
|
double value
|
||||||
structure alarm
|
structure alarm
|
||||||
struvture display
|
structure display
|
||||||
structure current
|
structure current
|
||||||
double value
|
double value
|
||||||
structure alarm
|
structure alarm
|
||||||
struvture display
|
structure display
|
||||||
</pre>
|
</pre>
|
||||||
<p>A pvAccess client wants to create a monitor on the powerSupply as follows:
|
<p>A pvAccess client wants to create a monitor on the powerSupply as follows:
|
||||||
The client wants a top level structure that looks like:
|
The client wants a top level structure that looks like:
|
||||||
@@ -578,7 +578,7 @@ client wants. It can be attached to any field via the following options:
|
|||||||
[plugin=onChange,raiseMonitor=value]
|
[plugin=onChange,raiseMonitor=value]
|
||||||
</pre>
|
</pre>
|
||||||
This plugin will trigger a monitor for the field only if the field changes
|
This plugin will trigger a monitor for the field only if the field changes
|
||||||
value. In addition <b>value</b> equals <b>false</b> means do not raise a monotor
|
value. In addition <b>value</b> equals <b>false</b> means do not raise a monitor
|
||||||
for changes to this field.
|
for changes to this field.
|
||||||
But if a change to another field does cause a monitor the change to this field
|
But if a change to another field does cause a monitor the change to this field
|
||||||
will be passed to the client.
|
will be passed to the client.
|
||||||
|
|||||||
Binary file not shown.
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@@ -28,11 +28,11 @@ StructureConstPtr enum_t =
|
|||||||
// create a structure (cntd.)
|
// create a structure (cntd.)
|
||||||
StructureConstPtr ntEnum =
|
StructureConstPtr ntEnum =
|
||||||
getFieldCreate()->createFieldBuilder()->
|
getFieldCreate()->createFieldBuilder()->
|
||||||
setId("uri:ev4:nt/2012/pwd/NTEnum")->
|
setId("epics:nt/NTEnum:1.0")->
|
||||||
add("value", enum_t)->
|
add("value", enum_t)->
|
||||||
addNestedStructure("timeStamp")->
|
addNestedStructure("timeStamp")->
|
||||||
setId("time_t")->
|
setId("time_t")->
|
||||||
add("secsPastEpoch", pvLong)->
|
add("secondsPastEpoch", pvLong)->
|
||||||
add("nanoseconds", pvInt)->
|
add("nanoseconds", pvInt)->
|
||||||
add("userTag", pvInt)->
|
add("userTag", pvInt)->
|
||||||
endNested()->
|
endNested()->
|
||||||
|
|||||||
5380
documentation/pvDataCPP_20140708.html
Normal file
5380
documentation/pvDataCPP_20140708.html
Normal file
File diff suppressed because it is too large
Load Diff
5392
documentation/pvDataCPP_20140723.html
Normal file
5392
documentation/pvDataCPP_20140723.html
Normal file
File diff suppressed because it is too large
Load Diff
5478
documentation/pvDataCPP_20141110.html
Normal file
5478
documentation/pvDataCPP_20141110.html
Normal file
File diff suppressed because it is too large
Load Diff
@@ -1,792 +0,0 @@
|
|||||||
<?xml version="1.0" encoding="iso-8859-1"?>
|
|
||||||
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
|
|
||||||
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
|
||||||
<html xmlns="http://www.w3.org/1999/xhtml">
|
|
||||||
<head>
|
|
||||||
<meta http-equiv="content-type" content="text/html; charset=iso-8859-1" />
|
|
||||||
<title>EPICS pvDataDiscussion</title>
|
|
||||||
<link rel="stylesheet" type="text/css"
|
|
||||||
href="http://epics-pvdata.sourceforge.net/base.css" />
|
|
||||||
<link rel="stylesheet" type="text/css"
|
|
||||||
href="http://epics-pvdata.sourceforge.net/epicsv4.css" />
|
|
||||||
<style type="text/css">
|
|
||||||
/*<![CDATA[*/
|
|
||||||
.about { margin-left: 3em; margin-right: 3em; font-size: .83em}
|
|
||||||
table { margin-left: auto; margin-right: auto }
|
|
||||||
.diagram { text-align: center; margin: 2.5em 0 }
|
|
||||||
span.opt { color: grey }
|
|
||||||
span.nterm { font-style:italic }
|
|
||||||
span.term { font-family:courier }
|
|
||||||
span.user { font-family:courier }
|
|
||||||
span.user:before { content:"<" }
|
|
||||||
span.user:after { content:">" }
|
|
||||||
.nonnorm { font-style:italic }
|
|
||||||
p.ed { color: #AA0000 }
|
|
||||||
span.ed { color: #AA0000 }
|
|
||||||
p.ed.priv { display: inline; }
|
|
||||||
span.ed.priv { display: inline; }
|
|
||||||
/*]]>*/</style>
|
|
||||||
<!-- Script that generates the Table of Contents -->
|
|
||||||
<script type="text/javascript"
|
|
||||||
src="http://epics-pvdata.sourceforge.net/script/tocgen.js">
|
|
||||||
</script>
|
|
||||||
</head>
|
|
||||||
<body>
|
|
||||||
|
|
||||||
<div class="head">
|
|
||||||
<h1>EPICS pvDataDiscussion</h1>
|
|
||||||
<!-- Maturity: Working Draft or Request for Comments, or Recommendation, and date. -->
|
|
||||||
|
|
||||||
<h2 class="nocount">EPICS v4 Working Group, Working Draft, 03-Jul-2013</h2>
|
|
||||||
|
|
||||||
<dl>
|
|
||||||
<dt>Latest version:</dt>
|
|
||||||
<dd><a
|
|
||||||
href="http://epics-pvdata.hg.sourceforge.net/hgweb/epics-pvdata/pvDataCPP/raw-file/tip/documentation/pvDataDiscussion.html">pvDataDiscussion.html</a>
|
|
||||||
</dd>
|
|
||||||
<dt>This version:</dt>
|
|
||||||
<dd>none</dd>
|
|
||||||
<dt>Previous version:</dt>
|
|
||||||
<dd>None</dd>
|
|
||||||
<dt>Editors:</dt>
|
|
||||||
<dd>Marty Kraimer, BNL<dd />
|
|
||||||
</dl>
|
|
||||||
|
|
||||||
<p class="copyright">This product is made available subject to acceptance of the <a
|
|
||||||
href="http://epics-pvdata.sourceforge.net/LICENSE.html">EPICS open source
|
|
||||||
license.</a></p>
|
|
||||||
<hr />
|
|
||||||
</div>
|
|
||||||
|
|
||||||
|
|
||||||
<div id="toc">
|
|
||||||
<h2 class="nocount" style="page-break-before: always">Table of Contents</h2>
|
|
||||||
</div>
|
|
||||||
<div id="contents" class="contents">
|
|
||||||
|
|
||||||
|
|
||||||
<h2>Introduction</h2>
|
|
||||||
<p>As pvDataCPP progressed PVField and derived classes accumulated
|
|
||||||
more and more member functions.
|
|
||||||
These member functions have nothing to do with the primary primary
|
|
||||||
purpose for pvData:
|
|
||||||
<blockquote>pvData (Process Variable Data) defines and implements an efficent
|
|
||||||
way to store, access, and communicate memory resident data structures.</blockquote>
|
|
||||||
This statement appears as the first sentence of pvDataJava.html.
|
|
||||||
A few sentances later the document makes it clear that communication
|
|
||||||
includes efficent network communication.
|
|
||||||
Thus pvData provides an interface for network accessible structured data.
|
|
||||||
The problem of adding member functions that have nothing to do with the primary purpose
|
|
||||||
started with the Java API.
|
|
||||||
It already had extra methods that solved problems that should have had a different solution.
|
|
||||||
This document removes the extra methods so that when new problems arise in the future
|
|
||||||
the solution will not involve adding new member functions to the introspection and data API.
|
|
||||||
</p>
|
|
||||||
<p>The introspection and data API for pvData should only encapuslate methods that support the primary purpose
|
|
||||||
stated above.
|
|
||||||
The interfaces for C++ and Java should be similar so that
|
|
||||||
someone who understands the interface in one of the languages
|
|
||||||
and knows both languages will quickly understand the interface of the other language.</p>
|
|
||||||
<p>There is another problem with the existing API. There are methods that allow the "structure"
|
|
||||||
to change after an pvData object is created. An example is PVField::renameField(std::string newName).
|
|
||||||
Such methods should not exist.</p>
|
|
||||||
<p>There are methods regarding immutability: setImmutable, isImmutablei, setCapacityMutable, and isCapacityMutable.
|
|
||||||
Should they exists? For now lets assume no.
|
|
||||||
</p>
|
|
||||||
<p>One last issue is the interface for array data. This document proposes a simplified
|
|
||||||
version of what currently exists. It requires that the implementation always provides storage for
|
|
||||||
the complete raw array. The existing APIs allow the implementation to provide the data in
|
|
||||||
"chunks". Giving up this requirement simplifies the array interfaces.
|
|
||||||
The existing C++ implementation of PVValueArray has serious problems.
|
|
||||||
The shared_vector that is implemented in pvDataCP-md provides the solution to fixing
|
|
||||||
the problems. This document describes an API that is very similar to the new Java API
|
|
||||||
except that raw arrays are replaced by shared_vector.</p>
|
|
||||||
<p>This document will first describe changes to the existing Java interfaces
|
|
||||||
and then the corresponding C++ API.</p>
|
|
||||||
<h2>Java API</h2>
|
|
||||||
<p>The following shows which methods will be removed from the existing interfaces
|
|
||||||
and what will be added.
|
|
||||||
The methods to be removed are in <font color = "red">red</font>
|
|
||||||
and methods to add are in <font color = "blue">blue</font>
|
|
||||||
Also the removed methods are at the end with a comment above.
|
|
||||||
The new methods also have a comment.
|
|
||||||
</p>
|
|
||||||
<h3>Introspection Interfaces</h3>
|
|
||||||
|
|
||||||
<pre>interface Field extends Serializable {
|
|
||||||
std::string getId();
|
|
||||||
Type getType();
|
|
||||||
// following will be removed
|
|
||||||
<font color = "red">void toString(StringBuilder buf);</font>
|
|
||||||
<font color = "red">void toString(StringBuilder buf,int indentLevel);</font>
|
|
||||||
<font color = "red">std::string toString();</font>
|
|
||||||
}
|
|
||||||
|
|
||||||
<font color = "blue">
|
|
||||||
// new interface
|
|
||||||
interface FieldTostd::string {
|
|
||||||
std::string toString(Field field);
|
|
||||||
}</font>
|
|
||||||
|
|
||||||
interface Scalar extends Field {
|
|
||||||
ScalarType getScalarType();
|
|
||||||
}
|
|
||||||
|
|
||||||
interface ScalarArray extends Field {
|
|
||||||
ScalarType getElementType();
|
|
||||||
}
|
|
||||||
|
|
||||||
interface Structure extends Field {
|
|
||||||
Field getField(std::string fieldName);
|
|
||||||
int getFieldIndex(std::string fieldName);
|
|
||||||
Field[] getFields();
|
|
||||||
Field getField(int fieldIndex);
|
|
||||||
std::string[] getFieldNames();
|
|
||||||
std::string getFieldName(int fieldIndex)
|
|
||||||
}
|
|
||||||
|
|
||||||
interface StructureArray extends Field {
|
|
||||||
Structure getStructure();
|
|
||||||
}
|
|
||||||
|
|
||||||
interface FieldCreate {
|
|
||||||
Scalar createScalar(ScalarType scalarType);
|
|
||||||
ScalarArray createScalarArray(ScalarType elementType);
|
|
||||||
StructureArray createStructureArray(Structure elementStructure);
|
|
||||||
Structure createStructure(std::string[] fieldNames, Field[] field);
|
|
||||||
Structure createStructure(std::string id,std::string[] fieldNames, Field[] field);
|
|
||||||
Structure createStructure(Structure structToClone);
|
|
||||||
Field deserialize(ByteBuffer buffer, DeserializableControl control);
|
|
||||||
// following will be removed
|
|
||||||
<font color = "red">Structure appendField(Structure structure,std::string fieldName, Field field);</font>
|
|
||||||
<font color = "red">Structure appendFields(Structure structure,std::string[] fieldNames, Field[] fields);</font>
|
|
||||||
}
|
|
||||||
</pre>
|
|
||||||
<h3>Data Interfaces</h3>
|
|
||||||
<pre>
|
|
||||||
interface PVField extends Requester, Serializable {
|
|
||||||
std::string getFieldName();
|
|
||||||
void setRequester(Requester requester);
|
|
||||||
int getFieldOffset();
|
|
||||||
int getNextFieldOffset();
|
|
||||||
int getNumberFields();
|
|
||||||
Field getField();
|
|
||||||
PVStructure getParent();
|
|
||||||
void postPut();
|
|
||||||
void setPostHandler(PostHandler postHandler);
|
|
||||||
// following will be removed
|
|
||||||
<font color = "red">PVAuxInfo getPVAuxInfo();</font>
|
|
||||||
<font color = "red">boolean isImmutable();</font>
|
|
||||||
<font color = "red">void setImmutable();</font>
|
|
||||||
<font color = "red">void renameField(std::string newName);</font>
|
|
||||||
<font color = "red">void toString(StringBuilder buf);</font>
|
|
||||||
<font color = "red">void toString(StringBuilder buf,int indentLevel);</font>
|
|
||||||
<font color = "red">std::string toString();</font>
|
|
||||||
}
|
|
||||||
|
|
||||||
<font color = "blue">
|
|
||||||
// The following is a new interface
|
|
||||||
interface PVFieldTostd::string {
|
|
||||||
std::string toString(PVField pvField);
|
|
||||||
void setMaxInitialArrayElements(int num);
|
|
||||||
void setMaxFinalArrayElements(int num);
|
|
||||||
int getMaxInitialArrayElements();
|
|
||||||
int getMaxFinalArrayElements();
|
|
||||||
}</font>
|
|
||||||
|
|
||||||
interface PVScalar extends PVField{
|
|
||||||
Scalar getScalar();
|
|
||||||
}
|
|
||||||
|
|
||||||
interface PVDouble extends PVScalar{
|
|
||||||
double get();
|
|
||||||
void put(double value);
|
|
||||||
}
|
|
||||||
// also PVBoolean, PVByte, PVShort, PVInt, PVLong, PVFloat, and PVString
|
|
||||||
|
|
||||||
interface PVArray extends PVField, SerializableArray {
|
|
||||||
int getLength();
|
|
||||||
void setLength(int length);
|
|
||||||
int getCapacity();
|
|
||||||
void setCapacity(int length);
|
|
||||||
// following will be removed
|
|
||||||
<font color = "red">boolean isCapacityMutable();</font>
|
|
||||||
<font color = "red">void setCapacityMutable(boolean isMutable);</font>
|
|
||||||
}
|
|
||||||
|
|
||||||
interface PVScalarArray extends PVArray {
|
|
||||||
ScalarArray getScalarArray();
|
|
||||||
}
|
|
||||||
|
|
||||||
<font color = "red">
|
|
||||||
//following will be removed
|
|
||||||
public class DoubleArrayData {
|
|
||||||
public double[] data;
|
|
||||||
public int offset;
|
|
||||||
}</font>
|
|
||||||
|
|
||||||
interface PVDoubleArray extends PVArray {
|
|
||||||
// following are new
|
|
||||||
<font color = "blue"> double[] get();</font>
|
|
||||||
<font color = "blue"> void swap(double[] value);</font>
|
|
||||||
//following will be removed
|
|
||||||
<font color = "red"> int get(int offset, int len, DoubleArrayData data);</font>
|
|
||||||
<font color = "red"> int put(int offset,int len, double[] from, int fromOffset)</font>;
|
|
||||||
<font color = "red"> void shareData(double[] from);</font>
|
|
||||||
}
|
|
||||||
|
|
||||||
// also PVBooleanArray, ..., PVStringArray
|
|
||||||
|
|
||||||
|
|
||||||
interface PVStructure extends PVField , BitSetSerializable{
|
|
||||||
Structure getStructure();
|
|
||||||
PVField[] getPVFields();
|
|
||||||
PVField getSubField(std::string fieldName);
|
|
||||||
PVField getSubField(int fieldOffset);
|
|
||||||
// The following are convenience methods
|
|
||||||
PVBoolean getBooleanField(std::string fieldName);
|
|
||||||
PVByte getByteField(std::string fieldName);
|
|
||||||
PVShort getShortField(std::string fieldName);
|
|
||||||
PVInt getIntField(std::string fieldName);
|
|
||||||
PVLong getLongField(std::string fieldName);
|
|
||||||
PVFloat getFloatField(std::string fieldName);
|
|
||||||
PVDouble getDoubleField(std::string fieldName);
|
|
||||||
PVString getStringField(std::string fieldName);
|
|
||||||
PVScalarArray getScalarArrayField(std::string fieldName);
|
|
||||||
PVStructureArray getStructureArrayField(std::string fieldName);
|
|
||||||
PVStructure getStructureField(std::string fieldName);
|
|
||||||
PVArray getArrayField(std::string fieldName,ScalarType elementType);
|
|
||||||
// following will be removed
|
|
||||||
<font color = "red"> void appendPVField(std::string fieldName,PVField pvField);</font>
|
|
||||||
<font color = "red"> void appendPVFields(std::string[] fieldNames,PVField[] pvFields);</font>
|
|
||||||
<font color = "red"> void removePVField(std::string fieldName);</font>
|
|
||||||
<font color = "red"> void replacePVField(PVField oldPVField,PVField newPVField);</font>
|
|
||||||
<font color = "red"> std::string getExtendsStructureName();</font>
|
|
||||||
<font color = "red"> boolean putExtendsStructureName(std::string extendsStructureName);</font>
|
|
||||||
<font color = "red"> public boolean checkValid();</font>
|
|
||||||
}
|
|
||||||
|
|
||||||
<font color = "red">
|
|
||||||
//following will be removed
|
|
||||||
public class StructureArrayData {
|
|
||||||
public PVStructure[] data;
|
|
||||||
public int offset;
|
|
||||||
}
|
|
||||||
</font>
|
|
||||||
|
|
||||||
interface PVStructureArray extends PVArray{
|
|
||||||
StructureArray getStructureArray();
|
|
||||||
// following are new
|
|
||||||
<font color = "blue"> PVStructure[] get();</font>
|
|
||||||
<font color = "blue"> void swap(PVStructure[] value);</font>
|
|
||||||
// following will be removed
|
|
||||||
<font color = "red"> int get(int offset, int length, StructureArrayData data);</font>
|
|
||||||
<font color = "red"> int put(int offset,int length, PVStructure[] from, int fromOffset);</font>
|
|
||||||
<font color = "red"> void shareData(PVStructure[] from);</font>
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
public interface PVDataCreate {
|
|
||||||
PVField createPVField(Field field);
|
|
||||||
PVField createPVField(PVField fieldToClone);
|
|
||||||
PVScalar createPVScalar(Scalar scalar);
|
|
||||||
PVScalar createPVScalar(ScalarType fieldType);
|
|
||||||
PVScalar createPVScalar(PVScalar scalarToClone);
|
|
||||||
PVScalarArray createPVScalarArray(ScalarArray array);
|
|
||||||
PVScalarArray createPVScalarArray(ScalarType elementType);
|
|
||||||
PVScalarArray createPVScalarArray(PVScalarArray arrayToClone;
|
|
||||||
PVStructureArray createPVStructureArray(StructureArray structureArray);
|
|
||||||
PVStructure createPVStructure(Structure structure);
|
|
||||||
PVStructure createPVStructure(std::string[] fieldNames,Field[] fields);
|
|
||||||
PVStructure createPVStructure(PVStructure structToClone);
|
|
||||||
// following will be removed
|
|
||||||
<font color = "red">PVField[] flattenPVStructure(PVStructure pvStructure);</font>
|
|
||||||
}
|
|
||||||
</pre>
|
|
||||||
<h3>PVFieldTostd::string</h3>
|
|
||||||
<p>In addition to toString this has methods to limit the number of array element to display.
|
|
||||||
The existing Java implementation of toString displayed all elements.
|
|
||||||
For large arrays this is not desirable.
|
|
||||||
The new methods provide a way for the client to limit the number of elements.
|
|
||||||
The default might be set to something like display up to 10 elements with 5 fron the beginning and 5 from the end.</p>
|
|
||||||
<p>For C++ this can be a replacement for dumpValue.</p>
|
|
||||||
<h3>PVBooleanArray, ..., PVStructureArray</h3>
|
|
||||||
<p>The old get and put are replaced by two new and simpler methods:
|
|
||||||
<dl>
|
|
||||||
<dt>get</dt>
|
|
||||||
<dd>Returns the raw array. If the client code modifies the elements in the array then
|
|
||||||
the client must call postPut. The client also has to realize that if the raw array held by the PVXXXArray changes
|
|
||||||
then the client is no longer sharing data
|
|
||||||
<dt>swap</dt>
|
|
||||||
<dd>This exchanges the old raw data with the new raw data.</dd>
|
|
||||||
</dl>
|
|
||||||
</p>
|
|
||||||
<p>
|
|
||||||
The method <b>setCapacity</b> will always create a new raw array and copy old data from the old to the new array.
|
|
||||||
This is not true now since the implementation does not create a new array if the old capacity is equal to the requested capacity.
|
|
||||||
</p>
|
|
||||||
<h2>C++ API</h2>
|
|
||||||
<p>The C++ class definitions are similar to the Java definitions with two main exceptions:
|
|
||||||
<dl>
|
|
||||||
<dt>toString</dt>
|
|
||||||
<dd>In c++ this is replaced by std::ostream.</dd>
|
|
||||||
<dt>raw array data</dt>
|
|
||||||
<dd>Java supports array data like <b>double[]</b>
|
|
||||||
The C++ replacement is shared_vector<double>, which is implemented
|
|
||||||
in pvDataCPP-md.</dd
|
|
||||||
</dl>
|
|
||||||
<h3>Introspection Interfaces</h3>
|
|
||||||
|
|
||||||
<pre>
|
|
||||||
class Field :
|
|
||||||
virtual public Serializable,
|
|
||||||
public std::tr1::enable_shared_from_this<Field>
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
POINTER_DEFINITIONS(Field);
|
|
||||||
virtual ~Field();
|
|
||||||
Type getType() const{return m_type;}
|
|
||||||
virtual std::string getID() const = 0;
|
|
||||||
<font color = "red">
|
|
||||||
// following will be removed
|
|
||||||
virtual void toString(StringBuilder buf) const{toString(buf,0);}
|
|
||||||
virtual void toString(StringBuilder buf,int indentLevel) const;
|
|
||||||
</font>
|
|
||||||
...
|
|
||||||
};
|
|
||||||
<font color = "blue">
|
|
||||||
// new function
|
|
||||||
std::ostream &toString(Field::const_reference field, std::ostream& o);
|
|
||||||
</font>
|
|
||||||
|
|
||||||
class Scalar : public Field{
|
|
||||||
public:
|
|
||||||
POINTER_DEFINITIONS(Scalar);
|
|
||||||
virtual ~Scalar();
|
|
||||||
typedef Scalar& reference;
|
|
||||||
typedef const Scalar& const_reference;
|
|
||||||
|
|
||||||
ScalarType getScalarType() const {return scalarType;}
|
|
||||||
virtual void serialize(ByteBuffer *buffer, SerializableControl *control) const;
|
|
||||||
virtual void deserialize(ByteBuffer *buffer, DeserializableContol *control);
|
|
||||||
<font color = "red">
|
|
||||||
// following will be removed
|
|
||||||
virtual void toString(StringBuilder buf) const{toString(buf,0);}
|
|
||||||
virtual void toString(StringBuilder buf,int indentLevel) const;
|
|
||||||
virtual std::string getID() const;
|
|
||||||
</font>
|
|
||||||
...
|
|
||||||
};
|
|
||||||
class ScalarArray : public Field{
|
|
||||||
public:
|
|
||||||
POINTER_DEFINITIONS(ScalarArray);
|
|
||||||
typedef ScalarArray& reference;
|
|
||||||
typedef const ScalarArray& const_reference;
|
|
||||||
|
|
||||||
ScalarArray(ScalarType scalarType);
|
|
||||||
ScalarType getElementType() const {return elementType;}
|
|
||||||
virtual void serialize(ByteBuffer *buffer, SerializableControl *control) const;
|
|
||||||
virtual void deserialize(ByteBuffer *buffer, DeserializableControl *control);
|
|
||||||
<font color = "red">
|
|
||||||
// following will be removed
|
|
||||||
virtual void toString(StringBuilder buf) const{toString(buf,0);}
|
|
||||||
virtual void toString(StringBuilder buf,int indentLevel) const;
|
|
||||||
virtual std::string getID() const;
|
|
||||||
</font>
|
|
||||||
...
|
|
||||||
};
|
|
||||||
|
|
||||||
class Structure : public Field {
|
|
||||||
public:
|
|
||||||
POINTER_DEFINITIONS(Structure);
|
|
||||||
typedef Structure& reference;
|
|
||||||
typedef const Structure& const_reference;
|
|
||||||
|
|
||||||
std::size_t getNumberFields() const {return numberFields;}
|
|
||||||
FieldConstPtr getField(std::string const & fieldName) const;
|
|
||||||
FieldConstPtr getField(std::size_t index) const;
|
|
||||||
std::size_t getFieldIndex(std::string const &fieldName) const;
|
|
||||||
FieldConstPtrArray const & getFields() const {return fields;}
|
|
||||||
StringArray const & getFieldNames() const;
|
|
||||||
std::string getFieldName(std::size_t fieldIndex);
|
|
||||||
virtual void serialize(ByteBuffer *buffer, SerializableControl *control) const;
|
|
||||||
virtual void deserialize(ByteBuffer *buffer, DeserializableControl *control);
|
|
||||||
<font color = "red">
|
|
||||||
// following will be removed
|
|
||||||
void renameField(std::size_t fieldIndex,std::string const &newName);
|
|
||||||
virtual void toString(StringBuilder buf,int indentLevel) const;
|
|
||||||
virtual std::string getID() const;
|
|
||||||
</font>
|
|
||||||
...
|
|
||||||
};
|
|
||||||
|
|
||||||
class StructureArray : public Field{
|
|
||||||
public:
|
|
||||||
POINTER_DEFINITIONS(StructureArray);
|
|
||||||
typedef StructureArray& reference;
|
|
||||||
typedef const StructureArray& const_reference;
|
|
||||||
|
|
||||||
StructureConstPtr getStructure() const {return pstructure;}
|
|
||||||
virtual void serialize(ByteBuffer *buffer, SerializableControl *control) const;
|
|
||||||
virtual void deserialize(ByteBuffer *buffer, DeserializableControl *control);
|
|
||||||
<font color = "red">
|
|
||||||
// following will be removed
|
|
||||||
virtual void toString(StringBuilder buf,int indentLevel=0) const;
|
|
||||||
virtual std::string getID() const;
|
|
||||||
</font>
|
|
||||||
...
|
|
||||||
};
|
|
||||||
|
|
||||||
class FieldCreate {
|
|
||||||
public:
|
|
||||||
static FieldCreatePtr getFieldCreate();
|
|
||||||
ScalarConstPtr createScalar(ScalarType scalarType) const
|
|
||||||
ScalarArrayConstPtr createScalarArray(ScalarType elementType) const;
|
|
||||||
StructureArrayConstPtr createStructureArray(StructureConstPtr const & structure) const;
|
|
||||||
StructureConstPtr createStructure (
|
|
||||||
StringArray const & fieldNames,
|
|
||||||
FieldConstPtrArray const & fields) const;
|
|
||||||
StructureConstPtr createStructure (
|
|
||||||
std::string const &id,
|
|
||||||
StringArray const & fieldNames,
|
|
||||||
FieldConstPtrArray const & fields) const;
|
|
||||||
FieldConstPtr deserialize(ByteBuffer* buffer, DeserializableControl* control) const;
|
|
||||||
<font color = "red">
|
|
||||||
// following will be removed
|
|
||||||
StructureConstPtr appendField(
|
|
||||||
StructureConstPtr const & structure,
|
|
||||||
std::string const &fieldName, FieldConstPtr const & field) const;
|
|
||||||
StructureConstPtr appendFields(
|
|
||||||
StructureConstPtr const & structure,
|
|
||||||
StringArray const & fieldNames,
|
|
||||||
FieldConstPtrArray const & fields) const;
|
|
||||||
</font>
|
|
||||||
...
|
|
||||||
};
|
|
||||||
|
|
||||||
extern FieldCreatePtr getFieldCreate();
|
|
||||||
</pre>
|
|
||||||
<h3>Data Interfaces</h3>
|
|
||||||
<pre>
|
|
||||||
class PVField
|
|
||||||
: virtual public Serializable,
|
|
||||||
public std::tr1::enable_shared_from_this<PVField>
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
POINTER_DEFINITIONS(PVField);
|
|
||||||
virtual ~PVField();
|
|
||||||
inline const std::string &getFieldName() const ;
|
|
||||||
virtual void setRequester(RequesterPtr const &prequester);
|
|
||||||
std::size_t getFieldOffset() const;
|
|
||||||
std::size_t getNextFieldOffset() const;
|
|
||||||
std::size_t getNumberFields() const;
|
|
||||||
const FieldConstPtr & getField() const ;
|
|
||||||
PVStructure * getParent() const
|
|
||||||
void postPut() ;
|
|
||||||
void setPostHandler(PostHandlerPtr const &postHandler);
|
|
||||||
// following will be removed
|
|
||||||
<font color = "red">
|
|
||||||
virtual void message(std::string message,MessageType messageType);
|
|
||||||
void replacePVField(const PVFieldPtr& newPVField);
|
|
||||||
std::string getFullName() const;
|
|
||||||
virtual bool equals(PVField &pv);
|
|
||||||
PVAuxInfoPtr & getPVAuxInfo()
|
|
||||||
bool isImmutable() const;
|
|
||||||
virtual void setImmutable();
|
|
||||||
void replacePVField(const PVFieldPtr& newPVField);
|
|
||||||
void renameField(std::string const &newName);
|
|
||||||
virtual void toString(StringBuilder buf) ;
|
|
||||||
virtual void toString(StringBuilder buf,int indentLevel);
|
|
||||||
std::ostream& dumpValue(std::ostream& o) const;
|
|
||||||
</font>
|
|
||||||
...
|
|
||||||
};
|
|
||||||
|
|
||||||
<font color = "blue">
|
|
||||||
// The following is a new class
|
|
||||||
class PVFieldTostd::string {
|
|
||||||
std::string toString(const PVFieldPtr &pvField);
|
|
||||||
void setMaxInitialArrayElements(size_t num);
|
|
||||||
void setMaxFinalArrayElements(size_t num);
|
|
||||||
size_t getMaxInitialArrayElements();
|
|
||||||
size_t getMaxFinalArrayElements();
|
|
||||||
...
|
|
||||||
}</font>
|
|
||||||
|
|
||||||
class PVScalar : public PVField {
|
|
||||||
public:
|
|
||||||
POINTER_DEFINITIONS(PVScalar);
|
|
||||||
virtual ~PVScalar();
|
|
||||||
typedef PVScalar &reference;
|
|
||||||
typedef const PVScalar& const_reference;
|
|
||||||
|
|
||||||
const ScalarConstPtr getScalar() const ;
|
|
||||||
...
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
template<typename T>
|
|
||||||
class PVScalarValue : public PVScalar {
|
|
||||||
public:
|
|
||||||
POINTER_DEFINITIONS(PVScalarValue);
|
|
||||||
typedef T value_type;
|
|
||||||
typedef T* pointer;
|
|
||||||
typedef const T* const_pointer;
|
|
||||||
|
|
||||||
virtual ~PVScalarValue() {}
|
|
||||||
virtual T get() const = 0;
|
|
||||||
virtual void put(T value) = 0;
|
|
||||||
<font color = "red">
|
|
||||||
// following will be removed
|
|
||||||
std::ostream& dumpValue(std::ostream& o)
|
|
||||||
void operator>>=(T& value) const;
|
|
||||||
void operator<<=(T value);
|
|
||||||
</font>
|
|
||||||
...
|
|
||||||
}
|
|
||||||
|
|
||||||
// PVString is special case, since it implements SerializableArray
|
|
||||||
class PVString : public PVScalarValue<std::string>, SerializableArray {
|
|
||||||
public:
|
|
||||||
virtual ~PVString() {}
|
|
||||||
...
|
|
||||||
}
|
|
||||||
class PVArray : public PVField, public SerializableArray {
|
|
||||||
public:
|
|
||||||
POINTER_DEFINITIONS(PVArray);
|
|
||||||
virtual ~PVArray();
|
|
||||||
std::size_t getLength() const;
|
|
||||||
virtual void setLength(std::size_t length);
|
|
||||||
std::size_t getCapacity() const;
|
|
||||||
virtual void setCapacity(std::size_t capacity) = 0;
|
|
||||||
<font color = "red">
|
|
||||||
// following will be removed
|
|
||||||
virtual void setImmutable();
|
|
||||||
bool isCapacityMutable() const;
|
|
||||||
void setCapacityMutable(bool isMutable);
|
|
||||||
virtual std::ostream& dumpValue(std::ostream& o, std::size_t index) const = 0;
|
|
||||||
</font>
|
|
||||||
...
|
|
||||||
};
|
|
||||||
|
|
||||||
class PVScalarArray : public PVArray {
|
|
||||||
public:
|
|
||||||
POINTER_DEFINITIONS(PVScalarArray);
|
|
||||||
virtual ~PVScalarArray();
|
|
||||||
typedef PVScalarArray &reference;
|
|
||||||
typedef const PVScalarArray& const_reference;
|
|
||||||
|
|
||||||
const ScalarArrayConstPtr getScalarArray() const ;
|
|
||||||
<font color = "red">
|
|
||||||
// following will be removed
|
|
||||||
virtual std::ostream& dumpValue(std::ostream& o, size_t index) const = 0;
|
|
||||||
</font>
|
|
||||||
...
|
|
||||||
}
|
|
||||||
|
|
||||||
<font color = "red">
|
|
||||||
// following will be removed
|
|
||||||
template<typename T>
|
|
||||||
class PVArrayData {
|
|
||||||
private:
|
|
||||||
std::vector<T> init;
|
|
||||||
public:
|
|
||||||
POINTER_DEFINITIONS(PVArrayData);
|
|
||||||
typedef T value_type;
|
|
||||||
typedef T* pointer;
|
|
||||||
typedef const T* const_pointer;
|
|
||||||
std::vector<T> & data;
|
|
||||||
std::size_t offset;
|
|
||||||
PVArrayData()
|
|
||||||
: data(init)
|
|
||||||
{}
|
|
||||||
};
|
|
||||||
</font>
|
|
||||||
|
|
||||||
template<typename T>
|
|
||||||
class PVValueArray : public PVScalarArray {
|
|
||||||
public:
|
|
||||||
POINTER_DEFINITIONS(PVValueArray);
|
|
||||||
typedef T value_type;
|
|
||||||
typedef T* pointer;
|
|
||||||
typedef const T* const_pointer;
|
|
||||||
// following are new typeDefs
|
|
||||||
<font color = "blue">typedef shared_vector<T> svector;</font>
|
|
||||||
<font color = "blue">typedef shared_vector<const T> const_svector; </font>
|
|
||||||
|
|
||||||
virtual ~PVValueArray() {}
|
|
||||||
// following are added
|
|
||||||
<font color = "blue">svector get();</font>
|
|
||||||
<font color = "blue">void swap(svector& value);</font>
|
|
||||||
<font color = "red">
|
|
||||||
// following are removed
|
|
||||||
typedef PVValueArray & reference;
|
|
||||||
typedef const PVValueArray & const_reference;
|
|
||||||
typedef PVArrayData<T> ArrayDataType;
|
|
||||||
typedef std::vector<T> vector;
|
|
||||||
typedef const std::vector<T> const_vector;
|
|
||||||
typedef std::tr1::shared_ptr<vector> shared_vector;
|
|
||||||
|
|
||||||
virtual std::size_t get(
|
|
||||||
std::size_t offset, std::size_t length, ArrayDataType &data) = 0;
|
|
||||||
virtual std::size_t put(std::size_t offset,
|
|
||||||
std::size_t length, const_pointer from, std::size_t fromOffset) = 0;
|
|
||||||
virtual std::size_t put(std::size_t offset,
|
|
||||||
std::size_t length, const_vector &from, std::size_t fromOffset);
|
|
||||||
virtual void shareData(
|
|
||||||
shared_vector const & value,
|
|
||||||
std::size_t capacity,
|
|
||||||
std::size_t length) = 0;
|
|
||||||
virtual pointer get() = 0;
|
|
||||||
virtual pointer get() const = 0;
|
|
||||||
virtual vector const & getVector() = 0;
|
|
||||||
virtual shared_vector const & getSharedVector() = 0;
|
|
||||||
std::ostream& dumpValue(std::ostream& o) const;
|
|
||||||
std::ostream& dumpValue(std::ostream& o, size_t index) const;
|
|
||||||
</font>
|
|
||||||
...
|
|
||||||
};
|
|
||||||
|
|
||||||
typedef PVValueArray<uint8> PVBooleanArray;
|
|
||||||
typedef std::tr1::shared_ptr<PVBooleanArray> PVBooleanArrayPtr;
|
|
||||||
...
|
|
||||||
typedef PVValueArray<std::string> PVStringArray;
|
|
||||||
typedef std::tr1::shared_ptr<PVStringArray> PVStringArrayPtr;
|
|
||||||
|
|
||||||
class PVStructure : public PVField,public BitSetSerializable {
|
|
||||||
public:
|
|
||||||
POINTER_DEFINITIONS(PVStructure);
|
|
||||||
virtual ~PVStructure();
|
|
||||||
typedef PVStructure & reference;
|
|
||||||
typedef const PVStructure & const_reference;
|
|
||||||
|
|
||||||
StructureConstPtr getStructure() const;
|
|
||||||
const PVFieldPtrArray & getPVFields() const;
|
|
||||||
PVFieldPtr getSubField(std::string const &fieldName) const;
|
|
||||||
PVFieldPtr getSubField(std::size_t fieldOffset) const;
|
|
||||||
PVBooleanPtr getBooleanField(std::string const &fieldName) ;
|
|
||||||
PVBytePtr getByteField(std::string const &fieldName) ;
|
|
||||||
PVShortPtr getShortField(std::string const &fieldName) ;
|
|
||||||
PVIntPtr getIntField(std::string const &fieldName) ;
|
|
||||||
PVLongPtr getLongField(std::string const &fieldName) ;
|
|
||||||
PVUBytePtr getUByteField(std::string const &fieldName) ;
|
|
||||||
PVUShortPtr getUShortField(std::string const &fieldName) ;
|
|
||||||
PVUIntPtr getUIntField(std::string const &fieldName) ;
|
|
||||||
PVULongPtr getULongField(std::string const &fieldName) ;
|
|
||||||
PVFloatPtr getFloatField(std::string const &fieldName) ;
|
|
||||||
PVDoublePtr getDoubleField(std::string const &fieldName) ;
|
|
||||||
PVStringPtr getStringField(std::string const &fieldName) ;
|
|
||||||
PVStructurePtr getStructureField(std::string const &fieldName) ;
|
|
||||||
PVScalarArrayPtr getScalarArrayField(
|
|
||||||
std::string const &fieldName,ScalarType elementType) ;
|
|
||||||
PVStructureArrayPtr getStructureArrayField(std::string const &fieldName) ;
|
|
||||||
virtual void serialize(
|
|
||||||
ByteBuffer *pbuffer,SerializableControl *pflusher) const ;
|
|
||||||
virtual void deserialize(
|
|
||||||
ByteBuffer *pbuffer,DeserializableControl *pflusher);
|
|
||||||
virtual void serialize(ByteBuffer *pbuffer,
|
|
||||||
SerializableControl *pflusher,BitSet *pbitSet) const;
|
|
||||||
virtual void deserialize(ByteBuffer *pbuffer,
|
|
||||||
DeserializableControl*pflusher,BitSet *pbitSet);
|
|
||||||
PVStructure(StructureConstPtr const & structure);
|
|
||||||
PVStructure(StructureConstPtr const & structure,PVFieldPtrArray const & pvFields);
|
|
||||||
<font color = "red">
|
|
||||||
// following are removed
|
|
||||||
void appendPVField(
|
|
||||||
std::string const &fieldName,
|
|
||||||
PVFieldPtr const & pvField);
|
|
||||||
void appendPVFields(
|
|
||||||
StringArray const & fieldNames,
|
|
||||||
PVFieldPtrArray const & pvFields);
|
|
||||||
void removePVField(std::string const &fieldName);
|
|
||||||
virtual void setImmutable();
|
|
||||||
std::string getExtendsStructureName() const;
|
|
||||||
bool putExtendsStructureName(
|
|
||||||
std::string const &extendsStructureName);
|
|
||||||
</font>
|
|
||||||
};
|
|
||||||
|
|
||||||
<font color = "red">
|
|
||||||
// following will be removed
|
|
||||||
typedef PVArrayData<PVStructurePtr> StructureArrayData;
|
|
||||||
</font>
|
|
||||||
|
|
||||||
class PVStructureArray : public PVArray
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
POINTER_DEFINITIONS(PVStructureArray);
|
|
||||||
typedef PVStructurePtr value_type;
|
|
||||||
typedef PVStructurePtr* pointer;
|
|
||||||
typedef const PVStructurePtr* const_pointer;
|
|
||||||
<font color = "blue">
|
|
||||||
// following are new typeDefs
|
|
||||||
typedef shared_vector<PVStructurePtr> svector;
|
|
||||||
typedef shared_vector<const PVStructurePtr> const_svector;
|
|
||||||
</font>
|
|
||||||
|
|
||||||
virtual ~PVStructureArray() {}
|
|
||||||
virtual void setCapacity(size_t capacity);
|
|
||||||
virtual void setLength(std::size_t length);
|
|
||||||
virtual StructureArrayConstPtr getStructureArray() const ;
|
|
||||||
virtual void serialize(ByteBuffer *pbuffer,
|
|
||||||
SerializableControl *pflusher) const;
|
|
||||||
virtual void deserialize(ByteBuffer *buffer,
|
|
||||||
virtual void serialize(ByteBuffer *pbuffer,
|
|
||||||
SerializableControl *pflusher, std::size_t offset, std::size_t count) const ;
|
|
||||||
// following are new
|
|
||||||
<font color = "blue"> svector get();</font>
|
|
||||||
<font color = "blue"> void swap(svector & value);</font>
|
|
||||||
<font color = "red">
|
|
||||||
// following are removed
|
|
||||||
typedef PVArrayData<PVStructurePtr> ArrayDataType;
|
|
||||||
typedef std::vector<PVStructurePtr> vector;
|
|
||||||
typedef const std::vector<PVStructurePtr> const_vector;
|
|
||||||
typedef std::tr1::shared_ptr<vector> shared_vector;
|
|
||||||
typedef PVStructureArray &reference;
|
|
||||||
typedef const PVStructureArray& const_reference;
|
|
||||||
|
|
||||||
virtual std::size_t append(std::size_t number);
|
|
||||||
virtual bool remove(std::size_t offset,std::size_t number);
|
|
||||||
virtual void compress();
|
|
||||||
virtual std::size_t get(std::size_t offset, std::size_t length,
|
|
||||||
StructureArrayData &data);
|
|
||||||
virtual std::size_t put(std::size_t offset,std::size_t length,
|
|
||||||
const_vector const & from, std::size_t fromOffset);
|
|
||||||
virtual void shareData(
|
|
||||||
shared_vector const & value,
|
|
||||||
std::size_t capacity,
|
|
||||||
std::size_t length);
|
|
||||||
virtual pointer get() { return &((*value.get())[0]); }
|
|
||||||
virtual pointer get() const { return &((*value.get())[0]); }
|
|
||||||
virtual vector const & getVector() {return *value;}
|
|
||||||
virtual shared_vector const & getSharedVector() {return value;}
|
|
||||||
</font>
|
|
||||||
...
|
|
||||||
};
|
|
||||||
|
|
||||||
class PVDataCreate {
|
|
||||||
public:
|
|
||||||
static PVDataCreatePtr getPVDataCreate();
|
|
||||||
PVFieldPtr createPVField(FieldConstPtr const & field);
|
|
||||||
PVFieldPtr createPVField(PVFieldPtr const & fieldToClone);
|
|
||||||
PVScalarPtr createPVScalar(ScalarConstPtr const & scalar);
|
|
||||||
PVScalarPtr createPVScalar(ScalarType scalarType);
|
|
||||||
PVScalarPtr createPVScalar(PVScalarPtr const & scalarToClone);
|
|
||||||
PVScalarArrayPtr createPVScalarArray(ScalarArrayConstPtr const & scalarArray);
|
|
||||||
PVScalarArrayPtr createPVScalarArray(ScalarType elementType);
|
|
||||||
PVScalarArrayPtr createPVScalarArray(PVScalarArrayPtr const & scalarArrayToClone);
|
|
||||||
PVStructureArrayPtr createPVStructureArray(StructureArrayConstPtr const & structureArray);
|
|
||||||
PVStructurePtr createPVStructure(StructureConstPtr const & structure);
|
|
||||||
PVStructurePtr createPVStructure(
|
|
||||||
StringArray const & fieldNames,PVFieldPtrArray const & pvFields);
|
|
||||||
PVStructurePtr createPVStructure(PVStructurePtr const & structToClone);
|
|
||||||
...
|
|
||||||
};
|
|
||||||
|
|
||||||
extern PVDataCreatePtr getPVDataCreate();
|
|
||||||
</pre>
|
|
||||||
|
|
||||||
|
|
||||||
</div>
|
|
||||||
</body>
|
|
||||||
</html>
|
|
||||||
464
pvDataCPP.files
464
pvDataCPP.files
@@ -62,42 +62,6 @@ pvDataApp/misc/timeFunction.h
|
|||||||
pvDataApp/misc/timer.cpp
|
pvDataApp/misc/timer.cpp
|
||||||
pvDataApp/misc/timer.h
|
pvDataApp/misc/timer.h
|
||||||
pvDataApp/monitor/monitor.h
|
pvDataApp/monitor/monitor.h
|
||||||
pvDataApp/O.linux-x86_64/alarm.d
|
|
||||||
pvDataApp/O.linux-x86_64/bitSet.d
|
|
||||||
pvDataApp/O.linux-x86_64/bitSetUtil.d
|
|
||||||
pvDataApp/O.linux-x86_64/byteBuffer.d
|
|
||||||
pvDataApp/O.linux-x86_64/Compare.d
|
|
||||||
pvDataApp/O.linux-x86_64/Convert.d
|
|
||||||
pvDataApp/O.linux-x86_64/epicsException.d
|
|
||||||
pvDataApp/O.linux-x86_64/event.d
|
|
||||||
pvDataApp/O.linux-x86_64/executor.d
|
|
||||||
pvDataApp/O.linux-x86_64/FieldCreateFactory.d
|
|
||||||
pvDataApp/O.linux-x86_64/libpvData.a
|
|
||||||
pvDataApp/O.linux-x86_64/libpvData.so
|
|
||||||
pvDataApp/O.linux-x86_64/localStaticLock.d
|
|
||||||
pvDataApp/O.linux-x86_64/messageQueue.d
|
|
||||||
pvDataApp/O.linux-x86_64/pvAlarm.d
|
|
||||||
pvDataApp/O.linux-x86_64/PVArray.d
|
|
||||||
pvDataApp/O.linux-x86_64/PVAuxInfoImpl.d
|
|
||||||
pvDataApp/O.linux-x86_64/pvControl.d
|
|
||||||
pvDataApp/O.linux-x86_64/PVDataCreateFactory.d
|
|
||||||
pvDataApp/O.linux-x86_64/pvDisplay.d
|
|
||||||
pvDataApp/O.linux-x86_64/pvEnumerated.d
|
|
||||||
pvDataApp/O.linux-x86_64/PVField.d
|
|
||||||
pvDataApp/O.linux-x86_64/PVScalar.d
|
|
||||||
pvDataApp/O.linux-x86_64/PVScalarArray.d
|
|
||||||
pvDataApp/O.linux-x86_64/PVStructure.d
|
|
||||||
pvDataApp/O.linux-x86_64/PVStructureArray.d
|
|
||||||
pvDataApp/O.linux-x86_64/pvTimeStamp.d
|
|
||||||
pvDataApp/O.linux-x86_64/requester.d
|
|
||||||
pvDataApp/O.linux-x86_64/serializeHelper.d
|
|
||||||
pvDataApp/O.linux-x86_64/StandardField.d
|
|
||||||
pvDataApp/O.linux-x86_64/StandardPVField.d
|
|
||||||
pvDataApp/O.linux-x86_64/status.d
|
|
||||||
pvDataApp/O.linux-x86_64/timeFunction.d
|
|
||||||
pvDataApp/O.linux-x86_64/timer.d
|
|
||||||
pvDataApp/O.linux-x86_64/timeStamp.d
|
|
||||||
pvDataApp/O.linux-x86_64/TypeFunc.d
|
|
||||||
pvDataApp/property/alarm.cpp
|
pvDataApp/property/alarm.cpp
|
||||||
pvDataApp/property/alarm.h
|
pvDataApp/property/alarm.h
|
||||||
pvDataApp/property/alarm.h.orig
|
pvDataApp/property/alarm.h.orig
|
||||||
@@ -117,45 +81,15 @@ pvDataApp/property/timeStamp.cpp
|
|||||||
pvDataApp/property/timeStamp.h
|
pvDataApp/property/timeStamp.h
|
||||||
pvDataApp/property/timeStamp.h.orig
|
pvDataApp/property/timeStamp.h.orig
|
||||||
pvDataApp/pv/convert.h
|
pvDataApp/pv/convert.h
|
||||||
pvDataApp/pv/convert.h.orig
|
|
||||||
pvDataApp/pv/pvData.h
|
pvDataApp/pv/pvData.h
|
||||||
pvDataApp/pv/pvData.h.orig
|
|
||||||
pvDataApp/pv/pvIntrospect.h
|
pvDataApp/pv/pvIntrospect.h
|
||||||
pvDataApp/pv/pvIntrospect.h.orig
|
|
||||||
pvDataApp/pv/pvType.h
|
pvDataApp/pv/pvType.h
|
||||||
pvDataApp/pv/standardField.h
|
pvDataApp/pv/standardField.h
|
||||||
pvDataApp/pv/standardField.h.orig
|
|
||||||
pvDataApp/pv/standardPVField.h
|
pvDataApp/pv/standardPVField.h
|
||||||
pvDataApp/pv/standardPVField.h.orig
|
|
||||||
pvDataApp/pvMisc/bitSetUtil.cpp
|
pvDataApp/pvMisc/bitSetUtil.cpp
|
||||||
pvDataApp/pvMisc/bitSetUtil.h
|
pvDataApp/pvMisc/bitSetUtil.h
|
||||||
testApp/capi/O.linux-x86_64/libtestc.a
|
|
||||||
testApp/capi/O.linux-x86_64/libtestc.so
|
|
||||||
testApp/capi/O.linux-x86_64/testc.d
|
|
||||||
testApp/capi/testc.cpp
|
testApp/capi/testc.cpp
|
||||||
testApp/capi/testc.py
|
testApp/capi/testc.py
|
||||||
testApp/mb/O.linux-x86_64/mb_test
|
|
||||||
testApp/mb/O.linux-x86_64/mb_test.d
|
|
||||||
testApp/misc/O.linux-x86_64/testBaseException
|
|
||||||
testApp/misc/O.linux-x86_64/testBaseException.d
|
|
||||||
testApp/misc/O.linux-x86_64/testBitSet
|
|
||||||
testApp/misc/O.linux-x86_64/testBitSet.d
|
|
||||||
testApp/misc/O.linux-x86_64/testByteBuffer
|
|
||||||
testApp/misc/O.linux-x86_64/testByteBuffer.d
|
|
||||||
testApp/misc/O.linux-x86_64/testByteOrder
|
|
||||||
testApp/misc/O.linux-x86_64/testByteOrder.d
|
|
||||||
testApp/misc/O.linux-x86_64/testMessageQueue
|
|
||||||
testApp/misc/O.linux-x86_64/testMessageQueue.d
|
|
||||||
testApp/misc/O.linux-x86_64/testQueue
|
|
||||||
testApp/misc/O.linux-x86_64/testQueue.d
|
|
||||||
testApp/misc/O.linux-x86_64/testSerialization
|
|
||||||
testApp/misc/O.linux-x86_64/testSerialization.d
|
|
||||||
testApp/misc/O.linux-x86_64/testThread
|
|
||||||
testApp/misc/O.linux-x86_64/testThread.d
|
|
||||||
testApp/misc/O.linux-x86_64/testTimer
|
|
||||||
testApp/misc/O.linux-x86_64/testTimer.d
|
|
||||||
testApp/misc/O.linux-x86_64/testTimeStamp
|
|
||||||
testApp/misc/O.linux-x86_64/testTimeStamp.d
|
|
||||||
testApp/misc/testBaseException.cpp
|
testApp/misc/testBaseException.cpp
|
||||||
testApp/misc/testBitSet.cpp
|
testApp/misc/testBitSet.cpp
|
||||||
testApp/misc/testByteBuffer.cpp
|
testApp/misc/testByteBuffer.cpp
|
||||||
@@ -166,34 +100,8 @@ testApp/misc/testSerialization.cpp
|
|||||||
testApp/misc/testThread.cpp
|
testApp/misc/testThread.cpp
|
||||||
testApp/misc/testTimer.cpp
|
testApp/misc/testTimer.cpp
|
||||||
testApp/misc/testTimeStamp.cpp
|
testApp/misc/testTimeStamp.cpp
|
||||||
testApp/monitor/O.linux-x86_64/testMonitor
|
|
||||||
testApp/monitor/O.linux-x86_64/testMonitor.d
|
|
||||||
testApp/monitor/testMonitor.cpp
|
testApp/monitor/testMonitor.cpp
|
||||||
testApp/property/O.linux-x86_64/testProperty
|
|
||||||
testApp/property/O.linux-x86_64/testProperty.d
|
|
||||||
testApp/property/testProperty.cpp
|
testApp/property/testProperty.cpp
|
||||||
testApp/pv/O.linux-x86_64/testConvert
|
|
||||||
testApp/pv/O.linux-x86_64/testConvert.d
|
|
||||||
testApp/pv/O.linux-x86_64/testIntrospect
|
|
||||||
testApp/pv/O.linux-x86_64/testIntrospect.d
|
|
||||||
testApp/pv/O.linux-x86_64/testOperators
|
|
||||||
testApp/pv/O.linux-x86_64/testOperators.d
|
|
||||||
testApp/pv/O.linux-x86_64/testPVAppend
|
|
||||||
testApp/pv/O.linux-x86_64/testPVAppend.d
|
|
||||||
testApp/pv/O.linux-x86_64/testPVAuxInfo
|
|
||||||
testApp/pv/O.linux-x86_64/testPVAuxInfo.d
|
|
||||||
testApp/pv/O.linux-x86_64/testPVData
|
|
||||||
testApp/pv/O.linux-x86_64/testPVData.d
|
|
||||||
testApp/pv/O.linux-x86_64/testPVScalarArray
|
|
||||||
testApp/pv/O.linux-x86_64/testPVScalarArray.d
|
|
||||||
testApp/pv/O.linux-x86_64/testPVStructureArray
|
|
||||||
testApp/pv/O.linux-x86_64/testPVStructureArray.d
|
|
||||||
testApp/pv/O.linux-x86_64/testPVType
|
|
||||||
testApp/pv/O.linux-x86_64/testPVType.d
|
|
||||||
testApp/pv/O.linux-x86_64/testStandardField
|
|
||||||
testApp/pv/O.linux-x86_64/testStandardField.d
|
|
||||||
testApp/pv/O.linux-x86_64/testStandardPVField
|
|
||||||
testApp/pv/O.linux-x86_64/testStandardPVField.d
|
|
||||||
testApp/pv/testConvert.cpp
|
testApp/pv/testConvert.cpp
|
||||||
testApp/pv/testIntrospect.cpp
|
testApp/pv/testIntrospect.cpp
|
||||||
testApp/pv/testOperators.cpp
|
testApp/pv/testOperators.cpp
|
||||||
@@ -209,3 +117,375 @@ COPYRIGHT
|
|||||||
Doxyfile
|
Doxyfile
|
||||||
LICENSE
|
LICENSE
|
||||||
README.html
|
README.html
|
||||||
|
src/copy/createRequest.cpp
|
||||||
|
src/copy/createRequest.h
|
||||||
|
src/copy/pvCopy.cpp
|
||||||
|
src/copy/pvCopy.h
|
||||||
|
src/factory/Compare.cpp
|
||||||
|
src/factory/Convert.cpp
|
||||||
|
src/factory/factory.h
|
||||||
|
src/factory/FieldCreateFactory.cpp
|
||||||
|
src/factory/printer.cpp
|
||||||
|
src/factory/PVArray.cpp
|
||||||
|
src/factory/PVDataCreateFactory.cpp
|
||||||
|
src/factory/PVField.cpp
|
||||||
|
src/factory/PVScalar.cpp
|
||||||
|
src/factory/PVScalarArray.cpp
|
||||||
|
src/factory/PVStructure.cpp
|
||||||
|
src/factory/PVStructureArray.cpp
|
||||||
|
src/factory/pvSubArrayCopy.cpp
|
||||||
|
src/factory/PVUnion.cpp
|
||||||
|
src/factory/PVUnionArray.cpp
|
||||||
|
src/factory/StandardField.cpp
|
||||||
|
src/factory/StandardPVField.cpp
|
||||||
|
src/factory/TypeFunc.cpp
|
||||||
|
src/misc/bitSet.cpp
|
||||||
|
src/misc/bitSet.h
|
||||||
|
src/misc/byteBuffer.cpp
|
||||||
|
src/misc/byteBuffer.h
|
||||||
|
src/misc/current_function.h
|
||||||
|
src/misc/destroyable.h
|
||||||
|
src/misc/epicsException.cpp
|
||||||
|
src/misc/epicsException.h
|
||||||
|
src/misc/event.cpp
|
||||||
|
src/misc/event.h
|
||||||
|
src/misc/executor.cpp
|
||||||
|
src/misc/executor.h
|
||||||
|
src/misc/localStaticLock.cpp
|
||||||
|
src/misc/localStaticLock.h
|
||||||
|
src/misc/lock.h
|
||||||
|
src/misc/messageQueue.cpp
|
||||||
|
src/misc/messageQueue.h
|
||||||
|
src/misc/noDefaultMethods.h
|
||||||
|
src/misc/parseToPOD.cpp
|
||||||
|
src/misc/queue.h
|
||||||
|
src/misc/requester.cpp
|
||||||
|
src/misc/requester.h
|
||||||
|
src/misc/serialize.h
|
||||||
|
src/misc/serializeHelper.cpp
|
||||||
|
src/misc/serializeHelper.h
|
||||||
|
src/misc/sharedPtr.h
|
||||||
|
src/misc/sharedVector.h
|
||||||
|
src/misc/status.cpp
|
||||||
|
src/misc/status.h
|
||||||
|
src/misc/templateMeta.h
|
||||||
|
src/misc/thread.h
|
||||||
|
src/misc/timeFunction.cpp
|
||||||
|
src/misc/timeFunction.h
|
||||||
|
src/misc/timer.cpp
|
||||||
|
src/misc/timer.h
|
||||||
|
src/misc/typeCast.cpp
|
||||||
|
src/misc/typeCast.h
|
||||||
|
src/monitor/monitor.cpp
|
||||||
|
src/monitor/monitor.h
|
||||||
|
src/monitor/monitorPlugin.cpp
|
||||||
|
src/monitor/monitorPlugin.h
|
||||||
|
src/property/alarm.cpp
|
||||||
|
src/property/alarm.h
|
||||||
|
src/property/control.h
|
||||||
|
src/property/display.h
|
||||||
|
src/property/pvAlarm.cpp
|
||||||
|
src/property/pvAlarm.h
|
||||||
|
src/property/pvControl.cpp
|
||||||
|
src/property/pvControl.h
|
||||||
|
src/property/pvDisplay.cpp
|
||||||
|
src/property/pvDisplay.h
|
||||||
|
src/property/pvEnumerated.cpp
|
||||||
|
src/property/pvEnumerated.h
|
||||||
|
src/property/pvTimeStamp.cpp
|
||||||
|
src/property/pvTimeStamp.h
|
||||||
|
src/property/timeStamp.cpp
|
||||||
|
src/property/timeStamp.h
|
||||||
|
src/pv/convert.h
|
||||||
|
src/pv/printer.h
|
||||||
|
src/pv/pvData.h
|
||||||
|
src/pv/pvIntrospect.h
|
||||||
|
src/pv/pvSubArrayCopy.h
|
||||||
|
src/pv/pvType.h
|
||||||
|
src/pv/standardField.h
|
||||||
|
src/pv/standardPVField.h
|
||||||
|
src/pvMisc/bitSetUtil.cpp
|
||||||
|
src/pvMisc/bitSetUtil.h
|
||||||
|
testApp/copy/testCreateRequest.cpp
|
||||||
|
testApp/copy/testPVCopy.cpp
|
||||||
|
testApp/misc/testBaseException.cpp
|
||||||
|
testApp/misc/testBitSet.cpp
|
||||||
|
testApp/misc/testByteBuffer.cpp
|
||||||
|
testApp/misc/testByteOrder.cpp
|
||||||
|
testApp/misc/testMessageQueue.cpp
|
||||||
|
testApp/misc/testOverrunBitSet.cpp
|
||||||
|
testApp/misc/testQueue.cpp
|
||||||
|
testApp/misc/testSerialization.cpp
|
||||||
|
testApp/misc/testSharedVector.cpp
|
||||||
|
testApp/misc/testThread.cpp
|
||||||
|
testApp/misc/testTimer.cpp
|
||||||
|
testApp/misc/testTimeStamp.cpp
|
||||||
|
testApp/misc/testTypeCast.cpp
|
||||||
|
testApp/property/testProperty.cpp
|
||||||
|
testApp/pv/testBitSetUtil.cpp
|
||||||
|
testApp/pv/testConvert.cpp
|
||||||
|
testApp/pv/testFieldBuilder.cpp
|
||||||
|
testApp/pv/testIntrospect.cpp
|
||||||
|
testApp/pv/testOperators.cpp
|
||||||
|
testApp/pv/testPVData.cpp
|
||||||
|
testApp/pv/testPVScalarArray.cpp
|
||||||
|
testApp/pv/testPVStructureArray.cpp
|
||||||
|
testApp/pv/testPVType.cpp
|
||||||
|
testApp/pv/testStandardField.cpp
|
||||||
|
testApp/pv/testStandardPVField.cpp
|
||||||
|
src/factory/printer.cpp
|
||||||
|
configure/O.darwin-x86/Makefile
|
||||||
|
configure/Makefile
|
||||||
|
include/pv/alarm.h
|
||||||
|
include/pv/bitSet.h
|
||||||
|
include/pv/bitSetUtil.h
|
||||||
|
include/pv/byteBuffer.h
|
||||||
|
include/pv/control.h
|
||||||
|
include/pv/convert.h
|
||||||
|
include/pv/createRequest.h
|
||||||
|
include/pv/current_function.h
|
||||||
|
include/pv/destroyable.h
|
||||||
|
include/pv/display.h
|
||||||
|
include/pv/epicsException.h
|
||||||
|
include/pv/event.h
|
||||||
|
include/pv/executor.h
|
||||||
|
include/pv/factory.h
|
||||||
|
include/pv/localStaticLock.h
|
||||||
|
include/pv/lock.h
|
||||||
|
include/pv/messageQueue.h
|
||||||
|
include/pv/monitor.h
|
||||||
|
include/pv/monitorPlugin.h
|
||||||
|
include/pv/noDefaultMethods.h
|
||||||
|
include/pv/printer.h
|
||||||
|
include/pv/pvAlarm.h
|
||||||
|
include/pv/pvControl.h
|
||||||
|
include/pv/pvCopy.h
|
||||||
|
include/pv/pvData.h
|
||||||
|
include/pv/pvDisplay.h
|
||||||
|
include/pv/pvEnumerated.h
|
||||||
|
include/pv/pvIntrospect.h
|
||||||
|
include/pv/pvSubArrayCopy.h
|
||||||
|
include/pv/pvTimeStamp.h
|
||||||
|
include/pv/pvType.h
|
||||||
|
include/pv/queue.h
|
||||||
|
include/pv/requester.h
|
||||||
|
include/pv/serialize.h
|
||||||
|
include/pv/serializeHelper.h
|
||||||
|
include/pv/sharedPtr.h
|
||||||
|
include/pv/sharedVector.h
|
||||||
|
include/pv/standardField.h
|
||||||
|
include/pv/standardPVField.h
|
||||||
|
include/pv/status.h
|
||||||
|
include/pv/templateMeta.h
|
||||||
|
include/pv/thread.h
|
||||||
|
include/pv/timeFunction.h
|
||||||
|
include/pv/timer.h
|
||||||
|
include/pv/timeStamp.h
|
||||||
|
include/pv/typeCast.h
|
||||||
|
src/copy/createRequest.cpp
|
||||||
|
src/copy/createRequest.h
|
||||||
|
src/copy/Makefile
|
||||||
|
src/copy/pvCopy.cpp
|
||||||
|
src/copy/pvCopy.h
|
||||||
|
src/factory/Compare.cpp
|
||||||
|
src/factory/Convert.cpp
|
||||||
|
src/factory/factory.h
|
||||||
|
src/factory/FieldCreateFactory.cpp
|
||||||
|
src/factory/Makefile
|
||||||
|
src/factory/printer.cpp
|
||||||
|
src/factory/PVArray.cpp
|
||||||
|
src/factory/PVDataCreateFactory.cpp
|
||||||
|
src/factory/PVField.cpp
|
||||||
|
src/factory/PVScalar.cpp
|
||||||
|
src/factory/PVScalarArray.cpp
|
||||||
|
src/factory/PVStructure.cpp
|
||||||
|
src/factory/PVStructureArray.cpp
|
||||||
|
src/factory/pvSubArrayCopy.cpp
|
||||||
|
src/factory/PVUnion.cpp
|
||||||
|
src/factory/PVUnionArray.cpp
|
||||||
|
src/factory/StandardField.cpp
|
||||||
|
src/factory/StandardPVField.cpp
|
||||||
|
src/factory/TypeFunc.cpp
|
||||||
|
src/misc/bitSet.cpp
|
||||||
|
src/misc/bitSet.h
|
||||||
|
src/misc/byteBuffer.cpp
|
||||||
|
src/misc/byteBuffer.h
|
||||||
|
src/misc/current_function.h
|
||||||
|
src/misc/destroyable.h
|
||||||
|
src/misc/epicsException.cpp
|
||||||
|
src/misc/epicsException.h
|
||||||
|
src/misc/event.cpp
|
||||||
|
src/misc/event.h
|
||||||
|
src/misc/executor.cpp
|
||||||
|
src/misc/executor.h
|
||||||
|
src/misc/localStaticLock.cpp
|
||||||
|
src/misc/localStaticLock.h
|
||||||
|
src/misc/lock.h
|
||||||
|
src/misc/Makefile
|
||||||
|
src/misc/messageQueue.cpp
|
||||||
|
src/misc/messageQueue.h
|
||||||
|
src/misc/noDefaultMethods.h
|
||||||
|
src/misc/parseToPOD.cpp
|
||||||
|
src/misc/queue.h
|
||||||
|
src/misc/requester.cpp
|
||||||
|
src/misc/requester.h
|
||||||
|
src/misc/serialize.h
|
||||||
|
src/misc/serializeHelper.cpp
|
||||||
|
src/misc/serializeHelper.h
|
||||||
|
src/misc/sharedPtr.h
|
||||||
|
src/misc/sharedVector.h
|
||||||
|
src/misc/status.cpp
|
||||||
|
src/misc/status.h
|
||||||
|
src/misc/templateMeta.h
|
||||||
|
src/misc/thread.h
|
||||||
|
src/misc/timeFunction.cpp
|
||||||
|
src/misc/timeFunction.h
|
||||||
|
src/misc/timer.cpp
|
||||||
|
src/misc/timer.h
|
||||||
|
src/misc/typeCast.cpp
|
||||||
|
src/misc/typeCast.h
|
||||||
|
src/monitor/Makefile
|
||||||
|
src/monitor/monitor.cpp
|
||||||
|
src/monitor/monitor.h
|
||||||
|
src/monitor/monitorPlugin.cpp
|
||||||
|
src/monitor/monitorPlugin.h
|
||||||
|
src/O.darwin-x86/Makefile
|
||||||
|
src/property/alarm.cpp
|
||||||
|
src/property/alarm.h
|
||||||
|
src/property/control.h
|
||||||
|
src/property/display.h
|
||||||
|
src/property/Makefile
|
||||||
|
src/property/pvAlarm.cpp
|
||||||
|
src/property/pvAlarm.h
|
||||||
|
src/property/pvControl.cpp
|
||||||
|
src/property/pvControl.h
|
||||||
|
src/property/pvDisplay.cpp
|
||||||
|
src/property/pvDisplay.h
|
||||||
|
src/property/pvEnumerated.cpp
|
||||||
|
src/property/pvEnumerated.h
|
||||||
|
src/property/pvTimeStamp.cpp
|
||||||
|
src/property/pvTimeStamp.h
|
||||||
|
src/property/timeStamp.cpp
|
||||||
|
src/property/timeStamp.h
|
||||||
|
src/pv/convert.h
|
||||||
|
src/pv/Makefile
|
||||||
|
src/pv/printer.h
|
||||||
|
src/pv/pvData.h
|
||||||
|
src/pv/pvIntrospect.h
|
||||||
|
src/pv/pvSubArrayCopy.h
|
||||||
|
src/pv/pvType.h
|
||||||
|
src/pv/standardField.h
|
||||||
|
src/pv/standardPVField.h
|
||||||
|
src/pvMisc/bitSetUtil.cpp
|
||||||
|
src/pvMisc/bitSetUtil.h
|
||||||
|
src/pvMisc/Makefile
|
||||||
|
src/Makefile
|
||||||
|
testApp/copy/epicsRunPVDataTests.c
|
||||||
|
testApp/copy/Makefile
|
||||||
|
testApp/copy/testCreateRequest.cpp
|
||||||
|
testApp/copy/testPVCopy.cpp
|
||||||
|
testApp/misc/epicsRunPVDataTests.c
|
||||||
|
testApp/misc/Makefile
|
||||||
|
testApp/misc/testBaseException.cpp
|
||||||
|
testApp/misc/testBitSet.cpp
|
||||||
|
testApp/misc/testByteBuffer.cpp
|
||||||
|
testApp/misc/testByteOrder.cpp
|
||||||
|
testApp/misc/testMessageQueue.cpp
|
||||||
|
testApp/misc/testOverrunBitSet.cpp
|
||||||
|
testApp/misc/testQueue.cpp
|
||||||
|
testApp/misc/testSerialization.cpp
|
||||||
|
testApp/misc/testSharedVector.cpp
|
||||||
|
testApp/misc/testThread.cpp
|
||||||
|
testApp/misc/testTimer.cpp
|
||||||
|
testApp/misc/testTimeStamp.cpp
|
||||||
|
testApp/misc/testTypeCast.cpp
|
||||||
|
testApp/property/epicsRunPVDataTests.c
|
||||||
|
testApp/property/Makefile
|
||||||
|
testApp/property/testProperty.cpp
|
||||||
|
testApp/pv/epicsRunPVDataTests.c
|
||||||
|
testApp/pv/Makefile
|
||||||
|
testApp/pv/testBitSetUtil.cpp
|
||||||
|
testApp/pv/testConvert.cpp
|
||||||
|
testApp/pv/testFieldBuilder.cpp
|
||||||
|
testApp/pv/testIntrospect.cpp
|
||||||
|
testApp/pv/testOperators.cpp
|
||||||
|
testApp/pv/testPVData.cpp
|
||||||
|
testApp/pv/testPVScalarArray.cpp
|
||||||
|
testApp/pv/testPVStructureArray.cpp
|
||||||
|
testApp/pv/testPVType.cpp
|
||||||
|
testApp/pv/testPVUnion.cpp
|
||||||
|
testApp/pv/testStandardField.cpp
|
||||||
|
testApp/pv/testStandardPVField.cpp
|
||||||
|
testApp/Makefile
|
||||||
|
Makefile
|
||||||
|
testApp/copy/epicsRunPVDataTests.c
|
||||||
|
testApp/copy/Makefile
|
||||||
|
testApp/copy/testCreateRequest.cpp
|
||||||
|
testApp/copy/testPVCopy.cpp
|
||||||
|
testApp/misc/epicsRunPVDataTests.c
|
||||||
|
testApp/misc/Makefile
|
||||||
|
testApp/misc/testBaseException.cpp
|
||||||
|
testApp/misc/testBitSet.cpp
|
||||||
|
testApp/misc/testByteBuffer.cpp
|
||||||
|
testApp/misc/testByteOrder.cpp
|
||||||
|
testApp/misc/testMessageQueue.cpp
|
||||||
|
testApp/misc/testOverrunBitSet.cpp
|
||||||
|
testApp/misc/testQueue.cpp
|
||||||
|
testApp/misc/testSerialization.cpp
|
||||||
|
testApp/misc/testSharedVector.cpp
|
||||||
|
testApp/misc/testThread.cpp
|
||||||
|
testApp/misc/testTimer.cpp
|
||||||
|
testApp/misc/testTimeStamp.cpp
|
||||||
|
testApp/misc/testTypeCast.cpp
|
||||||
|
testApp/O.darwin-x86/Makefile
|
||||||
|
testApp/property/epicsRunPVDataTests.c
|
||||||
|
testApp/property/Makefile
|
||||||
|
testApp/property/testProperty.cpp
|
||||||
|
testApp/pv/epicsRunPVDataTests.c
|
||||||
|
testApp/pv/Makefile
|
||||||
|
testApp/pv/testBitSetUtil.cpp
|
||||||
|
testApp/pv/testConvert.cpp
|
||||||
|
testApp/pv/testFieldBuilder.cpp
|
||||||
|
testApp/pv/testIntrospect.cpp
|
||||||
|
testApp/pv/testOperators.cpp
|
||||||
|
testApp/pv/testPVData.cpp
|
||||||
|
testApp/pv/testPVScalarArray.cpp
|
||||||
|
testApp/pv/testPVStructureArray.cpp
|
||||||
|
testApp/pv/testPVType.cpp
|
||||||
|
testApp/pv/testPVUnion.cpp
|
||||||
|
testApp/pv/testStandardField.cpp
|
||||||
|
testApp/pv/testStandardPVField.cpp
|
||||||
|
testApp/Makefile
|
||||||
|
testApp/pvDataAllTests.c
|
||||||
|
testApp/copy/testCreateRequest.cpp
|
||||||
|
testApp/copy/testPVCopy.cpp
|
||||||
|
testApp/misc/testBaseException.cpp
|
||||||
|
testApp/misc/testBitSet.cpp
|
||||||
|
testApp/misc/testByteBuffer.cpp
|
||||||
|
testApp/misc/testByteOrder.cpp
|
||||||
|
testApp/misc/testMessageQueue.cpp
|
||||||
|
testApp/misc/testOverrunBitSet.cpp
|
||||||
|
testApp/misc/testQueue.cpp
|
||||||
|
testApp/misc/testSerialization.cpp
|
||||||
|
testApp/misc/testSharedVector.cpp
|
||||||
|
testApp/misc/testThread.cpp
|
||||||
|
testApp/misc/testTimer.cpp
|
||||||
|
testApp/misc/testTimeStamp.cpp
|
||||||
|
testApp/misc/testTypeCast.cpp
|
||||||
|
testApp/property/testProperty.cpp
|
||||||
|
testApp/pv/testBitSetUtil.cpp
|
||||||
|
testApp/pv/testConvert.cpp
|
||||||
|
testApp/pv/testFieldBuilder.cpp
|
||||||
|
testApp/pv/testIntrospect.cpp
|
||||||
|
testApp/pv/testOperators.cpp
|
||||||
|
testApp/pv/testPVData.cpp
|
||||||
|
testApp/pv/testPVScalarArray.cpp
|
||||||
|
testApp/pv/testPVStructureArray.cpp
|
||||||
|
testApp/pv/testPVType.cpp
|
||||||
|
testApp/pv/testPVUnion.cpp
|
||||||
|
testApp/pv/testStandardField.cpp
|
||||||
|
testApp/pv/testStandardPVField.cpp
|
||||||
|
testApp/pvDataAllTests.c
|
||||||
|
testApp/rtemsConfig.c
|
||||||
|
testApp/rtemsNetworking.h
|
||||||
|
testApp/rtemsTestHarness.c
|
||||||
|
|||||||
@@ -4,3 +4,8 @@
|
|||||||
/home/msekoranja/epicsV4/pvDataCPP/pvDataApp/property
|
/home/msekoranja/epicsV4/pvDataCPP/pvDataApp/property
|
||||||
/home/msekoranja/epicsV4/pvDataCPP/pvDataApp/pv
|
/home/msekoranja/epicsV4/pvDataCPP/pvDataApp/pv
|
||||||
/home/msekoranja/epicsV4/pvDataCPP/pvDataApp/pvMisc
|
/home/msekoranja/epicsV4/pvDataCPP/pvDataApp/pvMisc
|
||||||
|
testApp/pv
|
||||||
|
testApp/copy
|
||||||
|
testApp/misc
|
||||||
|
testApp
|
||||||
|
testApp/property
|
||||||
|
|||||||
@@ -14,10 +14,12 @@
|
|||||||
#include <pv/createRequest.h>
|
#include <pv/createRequest.h>
|
||||||
|
|
||||||
using namespace epics::pvData;
|
using namespace epics::pvData;
|
||||||
|
using std::ostringstream;
|
||||||
using std::tr1::static_pointer_cast;
|
using std::tr1::static_pointer_cast;
|
||||||
using std::cout;
|
using std::cout;
|
||||||
using std::endl;
|
using std::endl;
|
||||||
using std::string;
|
using std::string;
|
||||||
|
using std::vector;
|
||||||
|
|
||||||
namespace epics { namespace pvData {
|
namespace epics { namespace pvData {
|
||||||
|
|
||||||
@@ -27,6 +29,38 @@ static FieldCreatePtr fieldCreate = getFieldCreate();
|
|||||||
class CreateRequestImpl : public CreateRequest {
|
class CreateRequestImpl : public CreateRequest {
|
||||||
private:
|
private:
|
||||||
|
|
||||||
|
struct Node
|
||||||
|
{
|
||||||
|
string name;
|
||||||
|
vector<Node> nodes;
|
||||||
|
Node(string name)
|
||||||
|
: name(name)
|
||||||
|
{}
|
||||||
|
};
|
||||||
|
|
||||||
|
struct OptionPair
|
||||||
|
{
|
||||||
|
string name;
|
||||||
|
string value;
|
||||||
|
OptionPair(string name,string value)
|
||||||
|
: name(name),
|
||||||
|
value(value)
|
||||||
|
{}
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
vector<OptionPair> optionList;
|
||||||
|
string fullFieldName;
|
||||||
|
|
||||||
|
|
||||||
|
public:
|
||||||
|
CreateRequestImpl()
|
||||||
|
{
|
||||||
|
fullFieldName = "";
|
||||||
|
}
|
||||||
|
private:
|
||||||
|
|
||||||
|
|
||||||
void removeBlanks(string& str)
|
void removeBlanks(string& str)
|
||||||
{
|
{
|
||||||
while(true) {
|
while(true) {
|
||||||
@@ -40,8 +74,8 @@ private:
|
|||||||
size_t openBrace = request.find('{', index+1);
|
size_t openBrace = request.find('{', index+1);
|
||||||
size_t closeBrace = request.find('}', index+1);
|
size_t closeBrace = request.find('}', index+1);
|
||||||
if(openBrace == string::npos && closeBrace == string::npos){
|
if(openBrace == string::npos && closeBrace == string::npos){
|
||||||
message = request + " missing }";
|
message = request + " mismatched {}";
|
||||||
return string::npos;
|
throw std::logic_error("message");
|
||||||
}
|
}
|
||||||
if (openBrace != string::npos && openBrace!=0) {
|
if (openBrace != string::npos && openBrace!=0) {
|
||||||
if(openBrace<closeBrace) return findMatchingBrace(request,openBrace,numOpen+1);
|
if(openBrace<closeBrace) return findMatchingBrace(request,openBrace,numOpen+1);
|
||||||
@@ -56,14 +90,14 @@ private:
|
|||||||
for(size_t i=index+1; i< request.size(); ++i) {
|
for(size_t i=index+1; i< request.size(); ++i) {
|
||||||
if(request[i] == ']') {
|
if(request[i] == ']') {
|
||||||
if(i==index+1) {
|
if(i==index+1) {
|
||||||
message = request + " illegal []";
|
message = request + " mismatched []";
|
||||||
return string::npos;
|
throw std::logic_error("message");
|
||||||
}
|
}
|
||||||
return i;
|
return i;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
message = request + " missing ]";
|
message = request + " missing ]";
|
||||||
return string::npos;
|
throw std::logic_error("message");
|
||||||
}
|
}
|
||||||
|
|
||||||
size_t findEndField(string& request) {
|
size_t findEndField(string& request) {
|
||||||
@@ -84,13 +118,17 @@ private:
|
|||||||
ind = closeBrace;
|
ind = closeBrace;
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
if(request[ind]=='.') {
|
||||||
|
++ind;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
if(ind>=maxind) break;
|
if(ind>=maxind) break;
|
||||||
++ind;
|
++ind;
|
||||||
}
|
}
|
||||||
return request.size();
|
return request.size();
|
||||||
}
|
}
|
||||||
|
|
||||||
std::vector<string> split(string const & commaSeparatedList) {
|
vector<string> split(string const & commaSeparatedList) {
|
||||||
string::size_type numValues = 1;
|
string::size_type numValues = 1;
|
||||||
string::size_type index=0;
|
string::size_type index=0;
|
||||||
while(true) {
|
while(true) {
|
||||||
@@ -99,7 +137,7 @@ private:
|
|||||||
numValues++;
|
numValues++;
|
||||||
index = pos +1;
|
index = pos +1;
|
||||||
}
|
}
|
||||||
std::vector<string> valueList(numValues,"");
|
vector<string> valueList(numValues,"");
|
||||||
index=0;
|
index=0;
|
||||||
for(size_t i=0; i<numValues; i++) {
|
for(size_t i=0; i<numValues; i++) {
|
||||||
size_t pos = commaSeparatedList.find(',',index);
|
size_t pos = commaSeparatedList.find(',',index);
|
||||||
@@ -110,417 +148,329 @@ private:
|
|||||||
return valueList;
|
return valueList;
|
||||||
}
|
}
|
||||||
|
|
||||||
StructureConstPtr createRequestOptions(
|
Node createRequestOptions(
|
||||||
string request)
|
string const & request)
|
||||||
{
|
{
|
||||||
if(request.length()<=1) return StructureConstPtr();
|
if(request.length()<=1) {
|
||||||
std::vector<string> items = split(request);
|
throw std::logic_error("logic error empty options");
|
||||||
|
}
|
||||||
|
vector<Node> top;
|
||||||
|
vector<string> items = split(request);
|
||||||
|
|
||||||
size_t nitems = items.size();
|
size_t nitems = items.size();
|
||||||
StringArray fieldNames(nitems);
|
|
||||||
FieldConstPtrArray fields(nitems);
|
|
||||||
for(size_t j=0; j<nitems; j++) {
|
for(size_t j=0; j<nitems; j++) {
|
||||||
string item = items[j];
|
string item = items[j];
|
||||||
size_t equals = item.find('=');
|
size_t equals = item.find('=');
|
||||||
if(equals==string::npos || equals==0) {
|
if(equals==string::npos || equals==0) {
|
||||||
message = item + " illegal option";
|
message = item + " illegal option " + request;
|
||||||
StructureConstPtr xxx;
|
throw std::logic_error("message");
|
||||||
return xxx;
|
|
||||||
}
|
}
|
||||||
fieldNames[j] = item.substr(0,equals);
|
top.push_back(Node(item.substr(0,equals)));
|
||||||
fields[j] = fieldCreate->createScalar(pvString);
|
string name = fullFieldName + "._options." + item.substr(0,equals);
|
||||||
}
|
|
||||||
return fieldCreate->createStructure(fieldNames,fields);
|
|
||||||
}
|
|
||||||
|
|
||||||
void initRequestOptions(
|
|
||||||
PVStructurePtr const & pvParent,
|
|
||||||
string request)
|
|
||||||
{
|
|
||||||
if(request.length()<=1) return;
|
|
||||||
std::vector<string> items = split(request);
|
|
||||||
size_t nitems = items.size();
|
|
||||||
for(size_t j=0; j<nitems; j++) {
|
|
||||||
string item = items[j];
|
|
||||||
size_t equals = item.find('=');
|
|
||||||
string name = item.substr(0,equals);
|
|
||||||
string value = item.substr(equals+1);
|
string value = item.substr(equals+1);
|
||||||
PVStringPtr pvValue = pvParent->getSubField<PVString>(name);
|
optionList.push_back(OptionPair(name,value));
|
||||||
pvValue->put(value);
|
|
||||||
}
|
}
|
||||||
}
|
Node node("_options");
|
||||||
|
node.nodes = top;
|
||||||
StructureConstPtr createSubFieldRequest(
|
return node;
|
||||||
StructureConstPtr parent,
|
|
||||||
string request)
|
|
||||||
{
|
|
||||||
if(request.length()<=0) return parent;
|
|
||||||
size_t period = request.find('.');
|
|
||||||
size_t openBracket = request.find('[');
|
|
||||||
size_t openBrace = request.find('{');
|
|
||||||
|
|
||||||
// name only
|
|
||||||
if(period==string::npos
|
|
||||||
&& openBracket==string::npos
|
|
||||||
&& openBrace==string::npos)
|
|
||||||
{
|
|
||||||
StructureConstPtr subField = fieldCreate->createStructure();
|
|
||||||
parent = fieldCreate->appendField(parent,request,subField);
|
|
||||||
return parent;
|
|
||||||
}
|
|
||||||
|
|
||||||
// period is first
|
|
||||||
if(period!=string::npos
|
|
||||||
&& (openBracket==string::npos || period<openBracket)
|
|
||||||
&& (openBrace==string::npos || period<openBrace) )
|
|
||||||
{
|
|
||||||
string fieldName = request.substr(0,period);
|
|
||||||
StructureConstPtr subField = fieldCreate->createStructure();
|
|
||||||
subField = createSubFieldRequest(subField,request.substr(period+1));
|
|
||||||
if(subField==NULL) return subField;
|
|
||||||
parent = fieldCreate->appendField(parent,fieldName,subField);
|
|
||||||
return parent;
|
|
||||||
}
|
|
||||||
|
|
||||||
// brace before [ or .
|
|
||||||
if(openBrace!=string::npos
|
|
||||||
&& (openBracket==string::npos || openBrace<openBracket) )
|
|
||||||
{
|
|
||||||
string fieldName = request.substr(0,openBrace);
|
|
||||||
size_t closeBrace = findMatchingBrace(request,openBrace,1);
|
|
||||||
if(closeBrace==string::npos) return StructureConstPtr();
|
|
||||||
size_t nextChar = closeBrace+1;
|
|
||||||
if(nextChar>= request.size()) nextChar = string::npos;
|
|
||||||
if(nextChar!=string::npos) {
|
|
||||||
message = request + " syntax error " + request[nextChar] + " after } illegal";
|
|
||||||
return StructureConstPtr();
|
|
||||||
}
|
|
||||||
StructureConstPtr subField = fieldCreate->createStructure();
|
|
||||||
string subRequest = request.substr(openBrace+1,closeBrace-openBrace-1);
|
|
||||||
subField = createFieldRequest(subField,subRequest);
|
|
||||||
if(subField==NULL) return subField;
|
|
||||||
parent = fieldCreate->appendField(parent,fieldName,subField);
|
|
||||||
return parent;
|
|
||||||
}
|
|
||||||
|
|
||||||
// [ is before brace or .
|
|
||||||
if(openBracket!=string::npos
|
|
||||||
&& (openBrace==string::npos || openBracket<openBrace) )
|
|
||||||
{
|
|
||||||
string fieldName = request.substr(0,openBracket);
|
|
||||||
size_t closeBracket = findMatchingBracket(request,openBracket);
|
|
||||||
if(closeBracket==string::npos) return StructureConstPtr();
|
|
||||||
size_t nextChar = closeBracket+1;
|
|
||||||
if(nextChar>= request.size()) nextChar = string::npos;
|
|
||||||
if(nextChar==string::npos) {
|
|
||||||
StringArray fieldNames(1);
|
|
||||||
FieldConstPtrArray fields(1);
|
|
||||||
fieldNames[0] = "_options";
|
|
||||||
fields[0] = createRequestOptions(
|
|
||||||
request.substr(openBracket+1,closeBracket-openBracket-1));
|
|
||||||
StructureConstPtr subField = fieldCreate->createStructure(fieldNames,fields);
|
|
||||||
parent = fieldCreate->appendField(parent,fieldName,subField);
|
|
||||||
return parent;
|
|
||||||
}
|
|
||||||
if(request[nextChar]=='.') {
|
|
||||||
StructureConstPtr subField = fieldCreate->createStructure();
|
|
||||||
subField = createSubFieldRequest(subField,request.substr(nextChar+1));
|
|
||||||
if(subField==NULL) return StructureConstPtr();
|
|
||||||
if(subField->getNumberFields()!=1) {
|
|
||||||
message = request + " logic error createSubFieldRequest openBracket subField";
|
|
||||||
return StructureConstPtr();
|
|
||||||
}
|
|
||||||
StringArray fieldNames(2);
|
|
||||||
FieldConstPtrArray fields(2);
|
|
||||||
fieldNames[0] = "_options";
|
|
||||||
fields[0] = createRequestOptions(
|
|
||||||
request.substr(openBracket+1,closeBracket-openBracket-1));
|
|
||||||
fieldNames[1] = subField->getFieldNames()[0];
|
|
||||||
fields[1] = subField;
|
|
||||||
subField = fieldCreate->createStructure(fieldNames,fields);
|
|
||||||
parent = fieldCreate->appendField(parent,fieldName,subField);
|
|
||||||
return parent;
|
|
||||||
}
|
|
||||||
if(request[nextChar]=='{') {
|
|
||||||
size_t closeBrace = findMatchingBrace(request,openBrace,1);
|
|
||||||
if(closeBrace==string::npos) return StructureConstPtr();
|
|
||||||
StructureConstPtr subField = fieldCreate->createStructure();
|
|
||||||
string subRequest = request.substr(openBrace+1,closeBrace-openBrace-1);
|
|
||||||
subField = createFieldRequest(subField,subRequest);
|
|
||||||
if(subField==NULL) return subField;
|
|
||||||
size_t numSub = subField->getNumberFields();
|
|
||||||
StringArray fieldNames(numSub + 1);
|
|
||||||
FieldConstPtrArray fields(numSub+1);
|
|
||||||
fieldNames[0] = "_options";
|
|
||||||
fields[0] = createRequestOptions(
|
|
||||||
request.substr(openBracket+1,closeBracket-openBracket-1));
|
|
||||||
StringArray subNames = subField->getFieldNames();
|
|
||||||
FieldConstPtrArray subFields = subField->getFields();
|
|
||||||
for(size_t i=0; i<numSub; ++i) {
|
|
||||||
fieldNames[i+1] = subNames[i];
|
|
||||||
fields[i+1] = subFields[i];
|
|
||||||
}
|
|
||||||
subField = fieldCreate->appendFields(parent,fieldNames,fields);
|
|
||||||
parent = fieldCreate->appendField(parent,fieldName,subField);
|
|
||||||
return parent;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
message = request + " logic error createSubFieldRequest";
|
|
||||||
return StructureConstPtr();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
StructureConstPtr createFieldRequest(
|
void createSubNode(Node &node,string const & crequest)
|
||||||
StructureConstPtr parent,
|
|
||||||
string request)
|
|
||||||
{
|
{
|
||||||
size_t length = request.length();
|
string request = crequest;
|
||||||
if(length<=0) return parent;
|
size_t end = 0;
|
||||||
size_t end = findEndField(request);
|
for(size_t i=0; i<request.size(); ++i) {
|
||||||
if(end==string::npos) return StructureConstPtr();
|
if(request[i]=='[') { end = i; break;}
|
||||||
StringArray fieldNames;
|
if(request[i]=='.') { end = i; break;}
|
||||||
FieldConstPtrArray fields;
|
if(request[i]=='{') { end = i; break;}
|
||||||
StructureConstPtr subField = fieldCreate->createStructure();
|
if(request[i]==',') { end = i; break;}
|
||||||
subField = createSubFieldRequest(subField,request.substr(0,end));
|
|
||||||
if(subField==NULL) return subField;
|
|
||||||
fieldNames.push_back(subField->getFieldNames()[0]);
|
|
||||||
fields.push_back(subField->getFields()[0]);
|
|
||||||
if(end!=length) {
|
|
||||||
if(request[end]!=',') {
|
|
||||||
message = request;
|
|
||||||
message += " expected char ";
|
|
||||||
message += length;
|
|
||||||
message += " to be ,";
|
|
||||||
return StructureConstPtr();
|
|
||||||
}
|
|
||||||
StructureConstPtr nextSubField = fieldCreate->createStructure();
|
|
||||||
nextSubField = createFieldRequest(nextSubField,request.substr(end+1));
|
|
||||||
if(nextSubField==NULL) return nextSubField;
|
|
||||||
size_t numFields = nextSubField->getNumberFields();
|
|
||||||
StringArray subNames = nextSubField->getFieldNames();
|
|
||||||
FieldConstPtrArray subFields = nextSubField->getFields();
|
|
||||||
for(size_t i=0; i<numFields; ++i) {
|
|
||||||
fieldNames.push_back(subNames[i]);
|
|
||||||
fields.push_back(subFields[i]);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
parent = fieldCreate->appendFields(parent,fieldNames,fields);
|
char chr = request[end];
|
||||||
return parent;
|
Node optionNode("");
|
||||||
}
|
if(chr=='[') {
|
||||||
|
string saveFullName = fullFieldName;
|
||||||
void initSubFieldOptions(
|
fullFieldName += "." + request.substr(0,end);
|
||||||
PVStructurePtr const & pvParent,
|
size_t endBracket = findMatchingBracket(request,end);
|
||||||
string request)
|
string options = request.substr(end+1,endBracket -end -1);
|
||||||
{
|
optionNode = createRequestOptions(options);
|
||||||
if(request.length()<=0) return;
|
fullFieldName = saveFullName;
|
||||||
size_t period = request.find('.');
|
size_t next = endBracket+1;
|
||||||
size_t openBracket = request.find('[');
|
if(next<request.size()) {
|
||||||
size_t openBrace = request.find('{');
|
request = request.substr(0, end) + request.substr(endBracket+1);
|
||||||
// name only
|
} else {
|
||||||
if(period==string::npos
|
request = request.substr(0, end);
|
||||||
&& openBracket==string::npos
|
}
|
||||||
&& openBrace==string::npos)
|
end = 0;
|
||||||
{
|
for(size_t i=0; i<request.size(); ++i) {
|
||||||
return;
|
if(request[i]=='.') { end = i; break;}
|
||||||
|
if(request[i]=='{') { end = i; break;}
|
||||||
|
if(request[i]==',') { end = i; break;}
|
||||||
|
}
|
||||||
|
chr = request[end];
|
||||||
}
|
}
|
||||||
|
if(end==0) end = request.size();
|
||||||
// period is first
|
string name = request.substr(0,end);
|
||||||
if(period!=string::npos
|
if(name.size()<1) {
|
||||||
&& (openBracket==string::npos || period<openBracket)
|
throw std::logic_error("null field name " + request);
|
||||||
&& (openBrace==string::npos || period<openBrace) )
|
}
|
||||||
{
|
string saveFullName = fullFieldName;
|
||||||
PVStructurePtr pvSubField = static_pointer_cast<PVStructure>(pvParent->getPVFields()[0]);
|
fullFieldName += "." + name;
|
||||||
initSubFieldOptions(pvSubField,request.substr(period+1));
|
if(end==request.size()) {
|
||||||
|
Node subNode(name);
|
||||||
|
if(optionNode.name.size()>0) subNode.nodes.push_back(optionNode);
|
||||||
|
node.nodes.push_back(subNode);
|
||||||
|
fullFieldName = saveFullName;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
if(chr==',') {
|
||||||
// brace before [ or .
|
Node subNode(name);
|
||||||
if(openBrace!=string::npos
|
if(optionNode.name.size()>0) subNode.nodes.push_back(optionNode);
|
||||||
&& (openBracket==string::npos || openBrace<openBracket) )
|
node.nodes.push_back(subNode);
|
||||||
{
|
string rest = request.substr(end+1);
|
||||||
PVStructurePtr pvSubField = static_pointer_cast<PVStructure>(pvParent->getPVFields()[0]);
|
fullFieldName = saveFullName;
|
||||||
size_t closeBrace = findMatchingBrace(request,openBrace,1);
|
createSubNode(node,rest);
|
||||||
string subRequest = request.substr(openBrace+1,closeBrace-openBrace-1);
|
|
||||||
initFieldOptions(pvSubField,subRequest);
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
PVStructurePtr pvOptions = pvParent->getSubField<PVStructure>("_options");
|
if(chr=='.') {
|
||||||
if(pvOptions==NULL) throw std::logic_error("initSubFieldOptions pvOptions NULL");
|
request = request.substr(end+1);
|
||||||
size_t closeBracket = findMatchingBracket(request,openBracket);
|
if(request.size()==string::npos || request.size()<1) {
|
||||||
initRequestOptions(pvOptions,request.substr(openBracket+1,closeBracket-openBracket-1));
|
throw std::logic_error("null field name " + request);
|
||||||
size_t nextChar = closeBracket+1;
|
}
|
||||||
if(nextChar>= request.size()) nextChar = string::npos;
|
Node subNode(name);
|
||||||
if(nextChar==string::npos) return;
|
if(optionNode.name.size()>0) subNode.nodes.push_back(optionNode);
|
||||||
if(request[nextChar]=='.') {
|
size_t endField = findEndField(request);
|
||||||
PVStructurePtr pvSubField = static_pointer_cast<PVStructure>(pvParent->getPVFields()[1]);
|
string subRequest = request.substr(0, endField);
|
||||||
initSubFieldOptions(pvSubField,request.substr(nextChar+1));
|
createSubNode(subNode,subRequest);
|
||||||
|
node.nodes.push_back(subNode);
|
||||||
|
size_t next = endField+1;
|
||||||
|
if(next>=request.size()) {
|
||||||
|
fullFieldName = saveFullName;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
request = request.substr(next);
|
||||||
|
fullFieldName = saveFullName;
|
||||||
|
createSubNode(node,request);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if(request[nextChar]!='{') throw std::logic_error("initSubFieldOptions request[nextChar]!='{'");
|
if(chr=='{') {
|
||||||
size_t closeBrace = findMatchingBrace(request,openBrace,1);
|
size_t endBrace = findEndField(request);
|
||||||
const PVFieldPtrArray &pvFields = pvParent->getPVFields();
|
if((end+1)>=(endBrace-1)) {
|
||||||
string subRequest = request.substr(openBrace+1,closeBrace-openBrace-1);
|
throw std::logic_error("illegal syntax " + request);
|
||||||
for(size_t i=1; i<pvFields.size(); ++i) {
|
}
|
||||||
PVStructurePtr pvSubField = static_pointer_cast<PVStructure>(pvFields[i]);
|
string subRequest = request.substr(end+1,endBrace-1 -end -1);
|
||||||
size_t comma = subRequest.find(',');
|
if(subRequest.size()<1) {
|
||||||
initSubFieldOptions(pvSubField, subRequest.substr(0,comma-1));
|
throw std::logic_error("empty {} " + request);
|
||||||
subRequest = subRequest.substr(comma+1);
|
}
|
||||||
|
Node subNode(name);
|
||||||
|
if(optionNode.name.size()>0) subNode.nodes.push_back(optionNode);
|
||||||
|
createSubNode(subNode,subRequest);
|
||||||
|
node.nodes.push_back(subNode);
|
||||||
|
size_t next = endBrace + 1;
|
||||||
|
if(next>=request.size()) {
|
||||||
|
fullFieldName = saveFullName;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
request = request.substr(next);
|
||||||
|
fullFieldName = saveFullName;
|
||||||
|
createSubNode(node,request);
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
|
throw std::logic_error("logic error");
|
||||||
}
|
}
|
||||||
|
|
||||||
void initFieldOptions(
|
FieldConstPtr createSubStructure(vector<Node> & nodes)
|
||||||
PVStructurePtr const & pvParent,
|
|
||||||
string request)
|
|
||||||
{
|
{
|
||||||
if(request.find('[')==string::npos) return;
|
size_t num = nodes.size();
|
||||||
size_t num = pvParent->getStructure()->getNumberFields();
|
StringArray names(num);
|
||||||
if(num==0) return;
|
FieldConstPtrArray fields(num);
|
||||||
if(num==1) {
|
|
||||||
initSubFieldOptions(pvParent,request);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
size_t end = findEndField(request);
|
|
||||||
size_t start = 0;
|
|
||||||
for(size_t i=0; i<num; ++i) {
|
for(size_t i=0; i<num; ++i) {
|
||||||
PVStructurePtr pvSub = static_pointer_cast<PVStructure>(pvParent->getPVFields()[i]);
|
Node node = nodes[i];
|
||||||
string subRequest = request.substr(start, end - start);
|
names[i] = node.name;
|
||||||
initSubFieldOptions(pvSub,subRequest);
|
if(node.name.compare("_options")==0) {
|
||||||
if(i==num-1) break;
|
fields[i] = createOptions(node.nodes);
|
||||||
start = end +1;
|
} else {
|
||||||
string xxx = request.substr(start);
|
vector<Node> subNode = node.nodes;
|
||||||
end += findEndField(xxx) + 1;
|
if(subNode.empty()) {
|
||||||
|
fields[i] = fieldCreate->createStructure();
|
||||||
|
} else {
|
||||||
|
fields[i] = createSubStructure(subNode);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
StructureConstPtr structure = fieldCreate->createStructure(
|
||||||
|
names, fields);
|
||||||
|
return structure;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
StructureConstPtr createOptions(vector<Node> &nodes)
|
||||||
|
{
|
||||||
|
size_t num = nodes.size();
|
||||||
|
StringArray names(num);
|
||||||
|
FieldConstPtrArray fields(num);
|
||||||
|
for(size_t i=0; i<num; ++i) {
|
||||||
|
Node node = nodes[i];
|
||||||
|
names[i] = node.name;
|
||||||
|
fields[i] = fieldCreate->createScalar(pvString);
|
||||||
|
}
|
||||||
|
StructureConstPtr structure = fieldCreate->createStructure(names, fields);
|
||||||
|
return structure;
|
||||||
|
}
|
||||||
|
|
||||||
public:
|
public:
|
||||||
|
|
||||||
virtual PVStructure::shared_pointer createRequest(
|
virtual PVStructurePtr createRequest(
|
||||||
string const & crequest)
|
string const & crequest)
|
||||||
{
|
{
|
||||||
string request = crequest;
|
try {
|
||||||
StructureConstPtr topStructure = fieldCreate->createStructure();
|
string request = crequest;
|
||||||
|
if (!request.empty()) removeBlanks(request);
|
||||||
if (!request.empty()) removeBlanks(request);
|
if (request.empty())
|
||||||
if (request.empty())
|
|
||||||
{
|
|
||||||
PVFieldPtrArray pvFields;
|
|
||||||
StringArray fieldNames;
|
|
||||||
return pvDataCreate->createPVStructure(fieldNames,pvFields);
|
|
||||||
}
|
|
||||||
size_t offsetRecord = request.find("record[");
|
|
||||||
size_t offsetField = request.find("field(");
|
|
||||||
size_t offsetPutField = request.find("putField(");
|
|
||||||
size_t offsetGetField = request.find("getField(");
|
|
||||||
if(offsetRecord==string::npos
|
|
||||||
&& offsetField==string::npos
|
|
||||||
&& offsetPutField==string::npos
|
|
||||||
&& offsetGetField==string::npos)
|
|
||||||
{
|
|
||||||
request = "field(" + crequest + ")";
|
|
||||||
offsetField = request.find("field(");
|
|
||||||
}
|
|
||||||
if (offsetRecord != string::npos) {
|
|
||||||
size_t openBracket = request.find('[', offsetRecord);
|
|
||||||
size_t closeBracket = request.find(']', openBracket);
|
|
||||||
if(closeBracket == string::npos) {
|
|
||||||
message = request.substr(offsetRecord)
|
|
||||||
+ " record[ does not have matching ]";
|
|
||||||
return PVStructurePtr();
|
|
||||||
}
|
|
||||||
StructureConstPtr structure = createRequestOptions(
|
|
||||||
request.substr(openBracket+1,closeBracket-openBracket-1));
|
|
||||||
if(structure==NULL)
|
|
||||||
{
|
{
|
||||||
return PVStructurePtr();
|
return pvDataCreate->createPVStructure(fieldCreate->createStructure());
|
||||||
}
|
}
|
||||||
topStructure = fieldCreate->appendField(topStructure,"record",structure);
|
size_t offsetRecord = request.find("record[");
|
||||||
}
|
size_t offsetField = request.find("field(");
|
||||||
if (offsetField != string::npos) {
|
size_t offsetPutField = request.find("putField(");
|
||||||
size_t openBrace = request.find('(', offsetField);
|
size_t offsetGetField = request.find("getField(");
|
||||||
size_t closeBrace = request.find(')', openBrace);
|
if(offsetRecord==string::npos
|
||||||
if(closeBrace == string::npos) {
|
&& offsetField==string::npos
|
||||||
message = request.substr(offsetField)
|
&& offsetPutField==string::npos
|
||||||
+ " field( does not have matching )";
|
&& offsetGetField==string::npos)
|
||||||
return PVStructurePtr();
|
|
||||||
}
|
|
||||||
StructureConstPtr structure = fieldCreate->createStructure();
|
|
||||||
structure = createFieldRequest(structure,request.substr(openBrace+1,closeBrace-openBrace-1));
|
|
||||||
if(structure==NULL)
|
|
||||||
{
|
{
|
||||||
|
request = "field(" + request + ")";
|
||||||
|
offsetField = request.find("field(");
|
||||||
|
}
|
||||||
|
int numParan = 0;
|
||||||
|
int numBrace = 0;
|
||||||
|
int numBracket = 0;
|
||||||
|
for(size_t i=0; i< request.length() ; ++i) {
|
||||||
|
char chr = request[i];
|
||||||
|
if(chr=='(') numParan++;
|
||||||
|
if(chr==')') numParan--;
|
||||||
|
if(chr=='{') numBrace++;
|
||||||
|
if(chr=='}') numBrace--;
|
||||||
|
if(chr=='[') numBracket++;
|
||||||
|
if(chr==']') numBracket--;
|
||||||
|
}
|
||||||
|
if(numParan!=0) {
|
||||||
|
ostringstream oss;
|
||||||
|
oss << "mismatched () " << numParan;
|
||||||
|
message = oss.str();
|
||||||
return PVStructurePtr();
|
return PVStructurePtr();
|
||||||
}
|
}
|
||||||
topStructure = fieldCreate->appendField(topStructure,"field",structure);
|
if(numBrace!=0) {
|
||||||
}
|
ostringstream oss;
|
||||||
if (offsetPutField != string::npos) {
|
oss << "mismatched {} " << numBrace;
|
||||||
size_t openBrace = request.find('(', offsetPutField);
|
message = oss.str();
|
||||||
size_t closeBrace = request.find(')', openBrace);
|
|
||||||
if(closeBrace == string::npos) {
|
|
||||||
message = request.substr(offsetField)
|
|
||||||
+ " putField( does not have matching )";
|
|
||||||
return PVStructurePtr();
|
return PVStructurePtr();
|
||||||
}
|
}
|
||||||
StructureConstPtr structure = fieldCreate->createStructure();
|
if(numBracket!=0) {
|
||||||
structure = createFieldRequest(structure,request.substr(openBrace+1,closeBrace-openBrace-1));
|
ostringstream oss;
|
||||||
if(structure==NULL)
|
oss << "mismatched [] " << numBracket;
|
||||||
{
|
message = oss.str();
|
||||||
return PVStructurePtr();
|
return PVStructurePtr();
|
||||||
}
|
}
|
||||||
topStructure = fieldCreate->appendField(topStructure,"putField",structure);
|
vector<Node> top;
|
||||||
}
|
try {
|
||||||
if (offsetGetField != string::npos) {
|
if(offsetRecord!=string::npos) {
|
||||||
size_t openBrace = request.find('(', offsetGetField);
|
fullFieldName = "record";
|
||||||
size_t closeBrace = request.find(')', openBrace);
|
size_t openBracket = request.find('[', offsetRecord);
|
||||||
if(closeBrace == string::npos) {
|
size_t closeBracket = request.find(']', openBracket);
|
||||||
message = request.substr(offsetField)
|
if(closeBracket==string::npos) {
|
||||||
+ " getField( does not have matching )";
|
message = request.substr(offsetRecord) +
|
||||||
|
"record[ does not have matching ]";
|
||||||
|
return PVStructurePtr();
|
||||||
|
}
|
||||||
|
if(closeBracket-openBracket > 3) {
|
||||||
|
Node node("record");
|
||||||
|
Node optNode = createRequestOptions(
|
||||||
|
request.substr(openBracket+1,closeBracket-openBracket-1));
|
||||||
|
node.nodes.push_back(optNode);
|
||||||
|
top.push_back(node);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if(offsetField!=string::npos) {
|
||||||
|
fullFieldName = "field";
|
||||||
|
Node node("field");
|
||||||
|
size_t openParan = request.find('(', offsetField);
|
||||||
|
size_t closeParan = request.find(')', openParan);
|
||||||
|
if(closeParan==string::npos) {
|
||||||
|
message = request.substr(offsetField)
|
||||||
|
+ " field( does not have matching )";
|
||||||
|
return PVStructurePtr();
|
||||||
|
}
|
||||||
|
if(closeParan>openParan+1) {
|
||||||
|
createSubNode(node,request.substr(openParan+1,closeParan-openParan-1));
|
||||||
|
}
|
||||||
|
top.push_back(node);
|
||||||
|
}
|
||||||
|
if(offsetGetField!=string::npos) {
|
||||||
|
fullFieldName = "getField";
|
||||||
|
Node node("getField");
|
||||||
|
size_t openParan = request.find('(', offsetGetField);
|
||||||
|
size_t closeParan = request.find(')', openParan);
|
||||||
|
if(closeParan==string::npos) {
|
||||||
|
message = request.substr(offsetField)
|
||||||
|
+ " getField( does not have matching )";
|
||||||
|
return PVStructurePtr();
|
||||||
|
}
|
||||||
|
if(closeParan>openParan+1) {
|
||||||
|
createSubNode(node,request.substr(openParan+1,closeParan-openParan-1));
|
||||||
|
}
|
||||||
|
top.push_back(node);
|
||||||
|
}
|
||||||
|
if(offsetPutField!=string::npos) {
|
||||||
|
fullFieldName = "putField";
|
||||||
|
Node node("putField");
|
||||||
|
size_t openParan = request.find('(', offsetPutField);
|
||||||
|
size_t closeParan = request.find(')', openParan);
|
||||||
|
if(closeParan==string::npos) {
|
||||||
|
message = request.substr(offsetField)
|
||||||
|
+ " putField( does not have matching )";
|
||||||
|
return PVStructurePtr();
|
||||||
|
}
|
||||||
|
if(closeParan>openParan+1) {
|
||||||
|
createSubNode(node,request.substr(openParan+1,closeParan-openParan-1));
|
||||||
|
}
|
||||||
|
top.push_back(node);
|
||||||
|
}
|
||||||
|
} catch (std::exception &e) {
|
||||||
|
string xxx = e.what();
|
||||||
|
message = "while creating Structure exception " + xxx;
|
||||||
return PVStructurePtr();
|
return PVStructurePtr();
|
||||||
}
|
}
|
||||||
StructureConstPtr structure = fieldCreate->createStructure();
|
size_t num = top.size();
|
||||||
structure = createFieldRequest(structure,request.substr(openBrace+1,closeBrace-openBrace-1));
|
StringArray names(num);
|
||||||
if(structure==NULL)
|
FieldConstPtrArray fields(num);
|
||||||
{
|
for(size_t i=0; i<num; ++i) {
|
||||||
return PVStructurePtr();
|
Node node = top[i];
|
||||||
|
names[i] = node.name;
|
||||||
|
vector<Node> subNode = node.nodes;
|
||||||
|
if(subNode.empty()) {
|
||||||
|
fields[i] = fieldCreate->createStructure();
|
||||||
|
} else {
|
||||||
|
fields[i] = createSubStructure(subNode);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
topStructure = fieldCreate->appendField(topStructure,"getField",structure);
|
StructureConstPtr structure = fieldCreate->createStructure(names, fields);
|
||||||
}
|
PVStructurePtr pvStructure = pvDataCreate->createPVStructure(structure);
|
||||||
PVStructurePtr pvStructure = pvDataCreate->createPVStructure(topStructure);
|
for(size_t i=0; i<optionList.size(); ++i) {
|
||||||
if (offsetRecord != string::npos) {
|
OptionPair pair = optionList[i];
|
||||||
size_t openBracket = request.find('[', offsetRecord);
|
string name = pair.name;
|
||||||
size_t closeBracket = request.find(']', openBracket);
|
string value = pair.value;
|
||||||
initRequestOptions(
|
PVStringPtr pvField = pvStructure->getSubField<PVString>(name);
|
||||||
pvStructure->getSubField<PVStructure>("record"),
|
pvField->put(value);
|
||||||
request.substr(openBracket+1,closeBracket-openBracket-1));
|
|
||||||
}
|
|
||||||
if (offsetField != string::npos) {
|
|
||||||
size_t openParam = request.find('(', offsetField);
|
|
||||||
size_t closeParam = request.find(')', openParam);
|
|
||||||
PVStructurePtr pvSub = pvStructure->getSubField<PVStructure>("field");
|
|
||||||
if(pvSub->getStructure()->getNumberFields()==1) {
|
|
||||||
pvSub = static_pointer_cast<PVStructure>(pvSub->getPVFields()[0]);
|
|
||||||
}
|
}
|
||||||
if(pvSub!=NULL) initFieldOptions(pvSub,request.substr(openParam+1,closeParam-openParam-1));
|
optionList.clear();
|
||||||
|
return pvStructure;
|
||||||
|
} catch (std::exception &e) {
|
||||||
|
message = e.what();
|
||||||
|
return PVStructurePtr();
|
||||||
}
|
}
|
||||||
if (offsetPutField != string::npos) {
|
|
||||||
size_t openParam = request.find('(', offsetPutField);
|
|
||||||
size_t closeParam = request.find(')', openParam);
|
|
||||||
PVStructurePtr pvSub = pvStructure->getSubField<PVStructure>("putField");
|
|
||||||
if(pvSub->getStructure()->getNumberFields()==1) {
|
|
||||||
pvSub = static_pointer_cast<PVStructure>(pvSub->getPVFields()[0]);
|
|
||||||
}
|
|
||||||
if(pvSub!=NULL) initFieldOptions(pvSub,request.substr(openParam+1,closeParam-openParam-1));
|
|
||||||
}
|
|
||||||
if (offsetGetField != string::npos) {
|
|
||||||
size_t openParam = request.find('(', offsetGetField);
|
|
||||||
size_t closeParam = request.find(')', openParam);
|
|
||||||
PVStructurePtr pvSub = pvStructure->getSubField<PVStructure>("getField");
|
|
||||||
if(pvSub->getStructure()->getNumberFields()==1) {
|
|
||||||
pvSub = static_pointer_cast<PVStructure>(pvSub->getPVFields()[0]);
|
|
||||||
}
|
|
||||||
if(pvSub!=NULL) initFieldOptions(pvSub,request.substr(openParam+1,closeParam-openParam-1));
|
|
||||||
}
|
|
||||||
return pvStructure;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
CreateRequest::shared_pointer CreateRequest::create()
|
CreateRequest::shared_pointer CreateRequest::create()
|
||||||
|
|||||||
@@ -68,9 +68,9 @@ PVCopyPtr PVCopy::create(
|
|||||||
if(structureName.size()>0) {
|
if(structureName.size()>0) {
|
||||||
if(pvRequest->getStructure()->getNumberFields()>0) {
|
if(pvRequest->getStructure()->getNumberFields()>0) {
|
||||||
pvStructure = pvRequest->getStructureField(structureName);
|
pvStructure = pvRequest->getStructureField(structureName);
|
||||||
if(pvStructure.get()==NULL) return NULLPVCopy;
|
if(!pvStructure) return NULLPVCopy;
|
||||||
}
|
}
|
||||||
} else if(pvStructure->getSubField("field")!=NULL) {
|
} else if(pvStructure->getSubField("field")) {
|
||||||
pvStructure = pvRequest->getStructureField("field");
|
pvStructure = pvRequest->getStructureField("field");
|
||||||
}
|
}
|
||||||
PVCopyPtr pvCopy = PVCopyPtr(new PVCopy(pvMaster));
|
PVCopyPtr pvCopy = PVCopyPtr(new PVCopy(pvMaster));
|
||||||
@@ -118,7 +118,7 @@ StructureConstPtr PVCopy::getStructure()
|
|||||||
|
|
||||||
PVStructurePtr PVCopy::createPVStructure()
|
PVStructurePtr PVCopy::createPVStructure()
|
||||||
{
|
{
|
||||||
if(cacheInitStructure.get()!=NULL) {
|
if(cacheInitStructure) {
|
||||||
PVStructurePtr save = cacheInitStructure;
|
PVStructurePtr save = cacheInitStructure;
|
||||||
cacheInitStructure.reset();
|
cacheInitStructure.reset();
|
||||||
return save;
|
return save;
|
||||||
@@ -174,7 +174,7 @@ size_t PVCopy::getCopyOffset(PVFieldPtr const &masterPVField)
|
|||||||
}
|
}
|
||||||
CopyStructureNodePtr node = static_pointer_cast<CopyStructureNode>(headNode);
|
CopyStructureNodePtr node = static_pointer_cast<CopyStructureNode>(headNode);
|
||||||
CopyMasterNodePtr masterNode = getCopyOffset(node,masterPVField);
|
CopyMasterNodePtr masterNode = getCopyOffset(node,masterPVField);
|
||||||
if(masterNode.get()!=NULL) return masterNode->structureOffset;
|
if(masterNode) return masterNode->structureOffset;
|
||||||
return string::npos;
|
return string::npos;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -190,7 +190,7 @@ size_t PVCopy::getCopyOffset(
|
|||||||
CopyStructureNodePtr node = static_pointer_cast<CopyStructureNode>(headNode);
|
CopyStructureNodePtr node = static_pointer_cast<CopyStructureNode>(headNode);
|
||||||
masterNode = getCopyOffset(node,masterPVField);
|
masterNode = getCopyOffset(node,masterPVField);
|
||||||
}
|
}
|
||||||
if(masterNode.get()==NULL) return string::npos;
|
if(!masterNode) return string::npos;
|
||||||
size_t diff = masterPVField->getFieldOffset()
|
size_t diff = masterPVField->getFieldOffset()
|
||||||
- masterPVStructure->getFieldOffset();
|
- masterPVStructure->getFieldOffset();
|
||||||
return masterNode->structureOffset + diff;
|
return masterNode->structureOffset + diff;
|
||||||
@@ -205,7 +205,7 @@ PVFieldPtr PVCopy::getMasterPVField(size_t structureOffset)
|
|||||||
CopyStructureNodePtr node = static_pointer_cast<CopyStructureNode>(headNode);
|
CopyStructureNodePtr node = static_pointer_cast<CopyStructureNode>(headNode);
|
||||||
masterNode = getMasterNode(node,structureOffset);
|
masterNode = getMasterNode(node,structureOffset);
|
||||||
}
|
}
|
||||||
if(masterNode.get()==NULL) {
|
if(!masterNode) {
|
||||||
throw std::invalid_argument(
|
throw std::invalid_argument(
|
||||||
"PVCopy::getMasterPVField: setstructureOffset not valid");
|
"PVCopy::getMasterPVField: setstructureOffset not valid");
|
||||||
}
|
}
|
||||||
@@ -299,7 +299,7 @@ void PVCopy::dump(string *builder,CopyNodePtr const &node,int indentLevel)
|
|||||||
ss << " nfields " << node->nfields;
|
ss << " nfields " << node->nfields;
|
||||||
*builder += ss.str();
|
*builder += ss.str();
|
||||||
PVStructurePtr options = node->options;
|
PVStructurePtr options = node->options;
|
||||||
if(options.get()!=NULL) {
|
if(options) {
|
||||||
getConvert()->newLine(builder,indentLevel +1);
|
getConvert()->newLine(builder,indentLevel +1);
|
||||||
|
|
||||||
// TODO !!! ugly
|
// TODO !!! ugly
|
||||||
@@ -338,7 +338,7 @@ bool PVCopy::init(epics::pvData::PVStructurePtr const &pvRequest)
|
|||||||
if(len==string::npos) entireMaster = true;
|
if(len==string::npos) entireMaster = true;
|
||||||
if(len==0) entireMaster = true;
|
if(len==0) entireMaster = true;
|
||||||
PVStructurePtr pvOptions;
|
PVStructurePtr pvOptions;
|
||||||
if(len==1 && pvRequest->getSubField("_options")!=NULL) {
|
if(len==1 && pvRequest->getSubField("_options")) {
|
||||||
pvOptions = pvRequest->getStructureField("_options");
|
pvOptions = pvRequest->getStructureField("_options");
|
||||||
}
|
}
|
||||||
if(entireMaster) {
|
if(entireMaster) {
|
||||||
@@ -353,7 +353,7 @@ bool PVCopy::init(epics::pvData::PVStructurePtr const &pvRequest)
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
structure = createStructure(pvMasterStructure,pvRequest);
|
structure = createStructure(pvMasterStructure,pvRequest);
|
||||||
if(structure==NULL) return false;
|
if(!structure) return false;
|
||||||
cacheInitStructure = createPVStructure();
|
cacheInitStructure = createPVStructure();
|
||||||
headNode = createStructureNodes(
|
headNode = createStructureNodes(
|
||||||
pvMaster,
|
pvMaster,
|
||||||
@@ -387,7 +387,7 @@ StructureConstPtr PVCopy::createStructure(
|
|||||||
for(size_t i=0; i<length; ++i) {
|
for(size_t i=0; i<length; ++i) {
|
||||||
string const &fieldName = fromRequestFieldNames[i];
|
string const &fieldName = fromRequestFieldNames[i];
|
||||||
PVFieldPtr pvMasterField = pvMaster->getSubField(fieldName);
|
PVFieldPtr pvMasterField = pvMaster->getSubField(fieldName);
|
||||||
if(pvMasterField==NULL) continue;
|
if(!pvMasterField) continue;
|
||||||
FieldConstPtr field = pvMasterField->getField();
|
FieldConstPtr field = pvMasterField->getField();
|
||||||
if(field->getType()==epics::pvData::structure) {
|
if(field->getType()==epics::pvData::structure) {
|
||||||
PVStructurePtr pvRequestStructure = static_pointer_cast<PVStructure>(
|
PVStructurePtr pvRequestStructure = static_pointer_cast<PVStructure>(
|
||||||
@@ -423,7 +423,7 @@ CopyNodePtr PVCopy::createStructureNodes(
|
|||||||
PVFieldPtrArray const & copyPVFields = pvFromCopy->getPVFields();
|
PVFieldPtrArray const & copyPVFields = pvFromCopy->getPVFields();
|
||||||
PVStructurePtr pvOptions;
|
PVStructurePtr pvOptions;
|
||||||
PVFieldPtr pvField = pvFromRequest->getSubField("_options");
|
PVFieldPtr pvField = pvFromRequest->getSubField("_options");
|
||||||
if(pvField!=NULL) pvOptions = static_pointer_cast<PVStructure>(pvField);
|
if(pvField) pvOptions = static_pointer_cast<PVStructure>(pvField);
|
||||||
size_t number = copyPVFields.size();
|
size_t number = copyPVFields.size();
|
||||||
CopyNodePtrArrayPtr nodes(new CopyNodePtrArray());
|
CopyNodePtrArrayPtr nodes(new CopyNodePtrArray());
|
||||||
nodes->reserve(number);
|
nodes->reserve(number);
|
||||||
@@ -435,7 +435,7 @@ CopyNodePtr PVCopy::createStructureNodes(
|
|||||||
pvFromRequest->getSubField(fieldName));
|
pvFromRequest->getSubField(fieldName));
|
||||||
PVStructurePtr pvSubFieldOptions;
|
PVStructurePtr pvSubFieldOptions;
|
||||||
PVFieldPtr pvField = requestPVStructure->getSubField("_options");
|
PVFieldPtr pvField = requestPVStructure->getSubField("_options");
|
||||||
if(pvField!=NULL) pvSubFieldOptions = static_pointer_cast<PVStructure>(pvField);
|
if(pvField) pvSubFieldOptions = static_pointer_cast<PVStructure>(pvField);
|
||||||
PVFieldPtr pvMasterField;
|
PVFieldPtr pvMasterField;
|
||||||
PVFieldPtrArray const & pvMasterFields = pvMasterStructure->getPVFields();
|
PVFieldPtrArray const & pvMasterFields = pvMasterStructure->getPVFields();
|
||||||
for(size_t j=0; i<pvMasterFields.size(); j++ ) {
|
for(size_t j=0; i<pvMasterFields.size(); j++ ) {
|
||||||
@@ -445,7 +445,7 @@ CopyNodePtr PVCopy::createStructureNodes(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
size_t numberRequest = requestPVStructure->getPVFields().size();
|
size_t numberRequest = requestPVStructure->getPVFields().size();
|
||||||
if(pvSubFieldOptions!=NULL) numberRequest--;
|
if(pvSubFieldOptions) numberRequest--;
|
||||||
if(numberRequest>0) {
|
if(numberRequest>0) {
|
||||||
nodes->push_back(createStructureNodes(
|
nodes->push_back(createStructureNodes(
|
||||||
static_pointer_cast<PVStructure>(pvMasterField),
|
static_pointer_cast<PVStructure>(pvMasterField),
|
||||||
@@ -621,7 +621,7 @@ CopyMasterNodePtr PVCopy::getCopyOffset(
|
|||||||
static_pointer_cast<CopyStructureNode>(node);
|
static_pointer_cast<CopyStructureNode>(node);
|
||||||
CopyMasterNodePtr masterNode =
|
CopyMasterNodePtr masterNode =
|
||||||
getCopyOffset(subNode,masterPVField);
|
getCopyOffset(subNode,masterPVField);
|
||||||
if(masterNode.get()!=NULL) return masterNode;
|
if(masterNode) return masterNode;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return NULLCopyMasterNode;
|
return NULLCopyMasterNode;
|
||||||
|
|||||||
@@ -134,6 +134,13 @@ bool operator==(const UnionArray& a, const UnionArray& b)
|
|||||||
return *(a.getUnion().get())==*(b.getUnion().get());
|
return *(a.getUnion().get())==*(b.getUnion().get());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool operator==(const BoundedString& a, const BoundedString& b)
|
||||||
|
{
|
||||||
|
if(&a==&b)
|
||||||
|
return true;
|
||||||
|
return a.getMaximumLength()==b.getMaximumLength();
|
||||||
|
}
|
||||||
|
|
||||||
// PVXXX object comparison
|
// PVXXX object comparison
|
||||||
|
|
||||||
namespace {
|
namespace {
|
||||||
@@ -244,7 +251,13 @@ bool compareField(const PVStructureArray* left, const PVStructureArray* right)
|
|||||||
lit!=lend;
|
lit!=lend;
|
||||||
++lit, ++rit)
|
++lit, ++rit)
|
||||||
{
|
{
|
||||||
if(**lit != **rit)
|
// element can be null
|
||||||
|
if (!(*lit) || !(*rit))
|
||||||
|
{
|
||||||
|
if (*lit || *rit)
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
else if (**lit != **rit)
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
@@ -297,7 +310,13 @@ bool compareField(const PVUnionArray* left, const PVUnionArray* right)
|
|||||||
lit!=lend;
|
lit!=lend;
|
||||||
++lit, ++rit)
|
++lit, ++rit)
|
||||||
{
|
{
|
||||||
if(**lit != **rit)
|
// element can be null
|
||||||
|
if (!(*lit) || !(*rit))
|
||||||
|
{
|
||||||
|
if (*lit || *rit)
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
else if (**lit != **rit)
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
|
|||||||
@@ -18,7 +18,6 @@
|
|||||||
#include <pv/pvIntrospect.h>
|
#include <pv/pvIntrospect.h>
|
||||||
#include <pv/pvData.h>
|
#include <pv/pvData.h>
|
||||||
#include <pv/convert.h>
|
#include <pv/convert.h>
|
||||||
#include <pv/printer.h>
|
|
||||||
|
|
||||||
using std::tr1::static_pointer_cast;
|
using std::tr1::static_pointer_cast;
|
||||||
using std::size_t;
|
using std::size_t;
|
||||||
@@ -51,7 +50,8 @@ void Convert::getString(string *buf,PVField const *pvField,int /*indentLevel*/)
|
|||||||
{
|
{
|
||||||
// TODO indextLevel ignored
|
// TODO indextLevel ignored
|
||||||
std::ostringstream strm;
|
std::ostringstream strm;
|
||||||
strm << pvField->dumpValue(strm) << std::endl;
|
pvField->dumpValue(strm);
|
||||||
|
strm << std::endl;
|
||||||
// PrinterPlain p;
|
// PrinterPlain p;
|
||||||
// p.setStream(strm);
|
// p.setStream(strm);
|
||||||
// p.print(*pvField);
|
// p.print(*pvField);
|
||||||
@@ -462,17 +462,14 @@ void Convert::copyUnion(PVUnionPtr const & from, PVUnionPtr const & to)
|
|||||||
PVFieldPtr fromValue = from->get();
|
PVFieldPtr fromValue = from->get();
|
||||||
if (from->getUnion()->isVariant())
|
if (from->getUnion()->isVariant())
|
||||||
{
|
{
|
||||||
if (fromValue.get() == 0)
|
to->set(from->get());
|
||||||
to->set(PVFieldPtr());
|
|
||||||
else
|
|
||||||
to->set(getPVDataCreate()->createPVField(fromValue)); // clone value // TODO cache getPVDataCreate()
|
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
if (fromValue.get() == 0)
|
if (fromValue.get() == 0)
|
||||||
to->select(PVUnion::UNDEFINED_INDEX);
|
to->select(PVUnion::UNDEFINED_INDEX);
|
||||||
else
|
else
|
||||||
to->set(from->getSelectedFieldName(),from->get());
|
to->set(from->getSelectedIndex(),from->get());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -17,6 +17,7 @@
|
|||||||
#include <string>
|
#include <string>
|
||||||
#include <cstdio>
|
#include <cstdio>
|
||||||
#include <stdexcept>
|
#include <stdexcept>
|
||||||
|
#include <sstream>
|
||||||
|
|
||||||
#define epicsExportSharedSymbols
|
#define epicsExportSharedSymbols
|
||||||
#include <pv/lock.h>
|
#include <pv/lock.h>
|
||||||
@@ -80,7 +81,7 @@ string Scalar::getID() const
|
|||||||
return idScalarLUT[scalarType];
|
return idScalarLUT[scalarType];
|
||||||
}
|
}
|
||||||
|
|
||||||
int8 Scalar::getTypeCodeLUT() const
|
int8 Scalar::getTypeCodeLUT(ScalarType scalarType)
|
||||||
{
|
{
|
||||||
static const int8 typeCodeLUT[] = {
|
static const int8 typeCodeLUT[] = {
|
||||||
0x00, // pvBoolean
|
0x00, // pvBoolean
|
||||||
@@ -88,10 +89,10 @@ int8 Scalar::getTypeCodeLUT() const
|
|||||||
0x21, // pvShort
|
0x21, // pvShort
|
||||||
0x22, // pvInt
|
0x22, // pvInt
|
||||||
0x23, // pvLong
|
0x23, // pvLong
|
||||||
0x28, // pvUByte
|
0x24, // pvUByte
|
||||||
0x29, // pvUShort
|
0x25, // pvUShort
|
||||||
0x2A, // pvUInt
|
0x26, // pvUInt
|
||||||
0x2B, // pvULong
|
0x27, // pvULong
|
||||||
0x42, // pvFloat
|
0x42, // pvFloat
|
||||||
0x43, // pvDouble
|
0x43, // pvDouble
|
||||||
0x60 // pvString
|
0x60 // pvString
|
||||||
@@ -102,7 +103,7 @@ int8 Scalar::getTypeCodeLUT() const
|
|||||||
|
|
||||||
void Scalar::serialize(ByteBuffer *buffer, SerializableControl *control) const {
|
void Scalar::serialize(ByteBuffer *buffer, SerializableControl *control) const {
|
||||||
control->ensureBuffer(1);
|
control->ensureBuffer(1);
|
||||||
buffer->putByte(getTypeCodeLUT());
|
buffer->putByte(getTypeCodeLUT(scalarType));
|
||||||
}
|
}
|
||||||
|
|
||||||
void Scalar::deserialize(ByteBuffer* /*buffer*/, DeserializableControl* /*control*/) {
|
void Scalar::deserialize(ByteBuffer* /*buffer*/, DeserializableControl* /*control*/) {
|
||||||
@@ -110,6 +111,38 @@ void Scalar::deserialize(ByteBuffer* /*buffer*/, DeserializableControl* /*contro
|
|||||||
throw std::runtime_error("not valid operation, use FieldCreate::deserialize instead");
|
throw std::runtime_error("not valid operation, use FieldCreate::deserialize instead");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
std::string BoundedString::getID() const
|
||||||
|
{
|
||||||
|
std::ostringstream id;
|
||||||
|
id << Scalar::getID() << '(' << maxLength << ')';
|
||||||
|
return id.str();
|
||||||
|
}
|
||||||
|
|
||||||
|
void BoundedString::serialize(ByteBuffer *buffer, SerializableControl *control) const
|
||||||
|
{
|
||||||
|
control->ensureBuffer(1);
|
||||||
|
buffer->putByte(0x83);
|
||||||
|
SerializeHelper::writeSize(maxLength, buffer, control);
|
||||||
|
}
|
||||||
|
|
||||||
|
std::size_t BoundedString::getMaximumLength() const
|
||||||
|
{
|
||||||
|
return maxLength;
|
||||||
|
}
|
||||||
|
|
||||||
|
BoundedString::BoundedString(std::size_t maxStringLength) :
|
||||||
|
Scalar(pvString), maxLength(maxStringLength)
|
||||||
|
{
|
||||||
|
if (maxLength == 0)
|
||||||
|
throw std::invalid_argument("maxLength == 0");
|
||||||
|
}
|
||||||
|
|
||||||
|
BoundedString::~BoundedString() {}
|
||||||
|
|
||||||
|
|
||||||
static string emptyStringtring;
|
static string emptyStringtring;
|
||||||
|
|
||||||
static void serializeStructureField(const Structure* structure, ByteBuffer* buffer, SerializableControl* control)
|
static void serializeStructureField(const Structure* structure, ByteBuffer* buffer, SerializableControl* control)
|
||||||
@@ -198,7 +231,8 @@ Array::Array(Type type)
|
|||||||
Array::~Array() {}
|
Array::~Array() {}
|
||||||
|
|
||||||
ScalarArray::ScalarArray(ScalarType elementType)
|
ScalarArray::ScalarArray(ScalarType elementType)
|
||||||
: Array(scalarArray),elementType(elementType)
|
: Array(scalarArray),
|
||||||
|
elementType(elementType)
|
||||||
{
|
{
|
||||||
if(elementType<0 || elementType>MAX_SCALAR_TYPE)
|
if(elementType<0 || elementType>MAX_SCALAR_TYPE)
|
||||||
throw std::invalid_argument("Can't construct ScalarArray from invalid ScalarType");
|
throw std::invalid_argument("Can't construct ScalarArray from invalid ScalarType");
|
||||||
@@ -206,31 +240,12 @@ ScalarArray::ScalarArray(ScalarType elementType)
|
|||||||
|
|
||||||
ScalarArray::~ScalarArray() {}
|
ScalarArray::~ScalarArray() {}
|
||||||
|
|
||||||
int8 ScalarArray::getTypeCodeLUT() const
|
|
||||||
{
|
|
||||||
static const int8 typeCodeLUT[] = {
|
|
||||||
0x00, // pvBoolean
|
|
||||||
0x20, // pvByte
|
|
||||||
0x21, // pvShort
|
|
||||||
0x22, // pvInt
|
|
||||||
0x23, // pvLong
|
|
||||||
0x28, // pvUByte
|
|
||||||
0x29, // pvUShort
|
|
||||||
0x2A, // pvUInt
|
|
||||||
0x2B, // pvULong
|
|
||||||
0x42, // pvFloat
|
|
||||||
0x43, // pvDouble
|
|
||||||
0x60 // pvString
|
|
||||||
};
|
|
||||||
return typeCodeLUT[elementType];
|
|
||||||
}
|
|
||||||
|
|
||||||
const string ScalarArray::getIDScalarArrayLUT() const
|
const string ScalarArray::getIDScalarArrayLUT() const
|
||||||
{
|
{
|
||||||
static const string idScalarArrayLUT[] = {
|
static const string idScalarArrayLUT[] = {
|
||||||
"boolean[]", // pvBoolean
|
"boolean[]", // pvBoolean
|
||||||
"byte[]", // pvByte
|
"byte[]", // pvByte
|
||||||
"short[]", // pvShort
|
"short[]", // pvShort
|
||||||
"int[]", // pvInt
|
"int[]", // pvInt
|
||||||
"long[]", // pvLong
|
"long[]", // pvLong
|
||||||
"ubyte[]", // pvUByte
|
"ubyte[]", // pvUByte
|
||||||
@@ -256,13 +271,59 @@ std::ostream& ScalarArray::dump(std::ostream& o) const
|
|||||||
|
|
||||||
void ScalarArray::serialize(ByteBuffer *buffer, SerializableControl *control) const {
|
void ScalarArray::serialize(ByteBuffer *buffer, SerializableControl *control) const {
|
||||||
control->ensureBuffer(1);
|
control->ensureBuffer(1);
|
||||||
buffer->putByte((int8)0x10 | getTypeCodeLUT());
|
buffer->putByte((int8)0x08 | Scalar::getTypeCodeLUT(elementType));
|
||||||
}
|
}
|
||||||
|
|
||||||
void ScalarArray::deserialize(ByteBuffer* /*buffer*/, DeserializableControl* /*control*/) {
|
void ScalarArray::deserialize(ByteBuffer* /*buffer*/, DeserializableControl* /*control*/) {
|
||||||
throw std::runtime_error("not valid operation, use FieldCreate::deserialize instead");
|
throw std::runtime_error("not valid operation, use FieldCreate::deserialize instead");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
BoundedScalarArray::~BoundedScalarArray() {}
|
||||||
|
|
||||||
|
BoundedScalarArray::BoundedScalarArray(ScalarType elementType, size_t size)
|
||||||
|
: ScalarArray(elementType),
|
||||||
|
size(size)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
string BoundedScalarArray::getID() const
|
||||||
|
{
|
||||||
|
char buffer[32];
|
||||||
|
sprintf(buffer, "%s<%zu>", ScalarTypeFunc::name(getElementType()), size);
|
||||||
|
return string(buffer);
|
||||||
|
}
|
||||||
|
|
||||||
|
void BoundedScalarArray::serialize(ByteBuffer *buffer, SerializableControl *control) const {
|
||||||
|
control->ensureBuffer(1);
|
||||||
|
buffer->putByte((int8)0x10 | Scalar::getTypeCodeLUT(getElementType()));
|
||||||
|
SerializeHelper::writeSize(size, buffer, control);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
FixedScalarArray::~FixedScalarArray() {}
|
||||||
|
|
||||||
|
FixedScalarArray::FixedScalarArray(ScalarType elementType, size_t size)
|
||||||
|
: ScalarArray(elementType),
|
||||||
|
size(size)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
string FixedScalarArray::getID() const
|
||||||
|
{
|
||||||
|
char buffer[32];
|
||||||
|
sprintf(buffer, "%s[%zu]", ScalarTypeFunc::name(getElementType()), size);
|
||||||
|
return string(buffer);
|
||||||
|
}
|
||||||
|
|
||||||
|
void FixedScalarArray::serialize(ByteBuffer *buffer, SerializableControl *control) const {
|
||||||
|
control->ensureBuffer(1);
|
||||||
|
buffer->putByte((int8)0x18 | Scalar::getTypeCodeLUT(getElementType()));
|
||||||
|
SerializeHelper::writeSize(size, buffer, control);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
StructureArray::StructureArray(StructureConstPtr const & structure)
|
StructureArray::StructureArray(StructureConstPtr const & structure)
|
||||||
: Array(structureArray),pstructure(structure)
|
: Array(structureArray),pstructure(structure)
|
||||||
{
|
{
|
||||||
@@ -289,7 +350,7 @@ std::ostream& StructureArray::dump(std::ostream& o) const
|
|||||||
|
|
||||||
void StructureArray::serialize(ByteBuffer *buffer, SerializableControl *control) const {
|
void StructureArray::serialize(ByteBuffer *buffer, SerializableControl *control) const {
|
||||||
control->ensureBuffer(1);
|
control->ensureBuffer(1);
|
||||||
buffer->putByte((int8)0x90);
|
buffer->putByte((int8)0x88);
|
||||||
control->cachedSerialize(pstructure, buffer);
|
control->cachedSerialize(pstructure, buffer);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -326,11 +387,11 @@ void UnionArray::serialize(ByteBuffer *buffer, SerializableControl *control) con
|
|||||||
if (punion->isVariant())
|
if (punion->isVariant())
|
||||||
{
|
{
|
||||||
// unrestricted/variant union
|
// unrestricted/variant union
|
||||||
buffer->putByte((int8)0x92);
|
buffer->putByte((int8)0x8A);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
buffer->putByte((int8)0x91);
|
buffer->putByte((int8)0x89);
|
||||||
control->cachedSerialize(punion, buffer);
|
control->cachedSerialize(punion, buffer);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -552,7 +613,7 @@ size_t Union::getFieldIndex(string const &fieldName) const {
|
|||||||
|
|
||||||
std::ostream& Union::dump(std::ostream& o) const
|
std::ostream& Union::dump(std::ostream& o) const
|
||||||
{
|
{
|
||||||
o << getID() << std::endl;
|
o << format::indent() << getID() << std::endl;
|
||||||
{
|
{
|
||||||
format::indent_scope s(o);
|
format::indent_scope s(o);
|
||||||
dumpFields(o);
|
dumpFields(o);
|
||||||
@@ -655,6 +716,12 @@ FieldBuilderPtr FieldBuilder::add(string const & name, ScalarType scalarType)
|
|||||||
return shared_from_this();
|
return shared_from_this();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
FieldBuilderPtr FieldBuilder::addBoundedString(std::string const & name, std::size_t maxLength)
|
||||||
|
{
|
||||||
|
fields.push_back(fieldCreate->createBoundedString(maxLength)); fieldNames.push_back(name);
|
||||||
|
return shared_from_this();
|
||||||
|
}
|
||||||
|
|
||||||
FieldBuilderPtr FieldBuilder::add(string const & name, FieldConstPtr const & field)
|
FieldBuilderPtr FieldBuilder::add(string const & name, FieldConstPtr const & field)
|
||||||
{
|
{
|
||||||
fields.push_back(field); fieldNames.push_back(name);
|
fields.push_back(field); fieldNames.push_back(name);
|
||||||
@@ -667,6 +734,18 @@ FieldBuilderPtr FieldBuilder::addArray(string const & name, ScalarType scalarTyp
|
|||||||
return shared_from_this();
|
return shared_from_this();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
FieldBuilderPtr FieldBuilder::addFixedArray(string const & name, ScalarType scalarType, size_t size)
|
||||||
|
{
|
||||||
|
fields.push_back(fieldCreate->createFixedScalarArray(scalarType, size)); fieldNames.push_back(name);
|
||||||
|
return shared_from_this();
|
||||||
|
}
|
||||||
|
|
||||||
|
FieldBuilderPtr FieldBuilder::addBoundedArray(string const & name, ScalarType scalarType, size_t size)
|
||||||
|
{
|
||||||
|
fields.push_back(fieldCreate->createBoundedScalarArray(scalarType, size)); fieldNames.push_back(name);
|
||||||
|
return shared_from_this();
|
||||||
|
}
|
||||||
|
|
||||||
FieldBuilderPtr FieldBuilder::addArray(string const & name, FieldConstPtr const & element)
|
FieldBuilderPtr FieldBuilder::addArray(string const & name, FieldConstPtr const & element)
|
||||||
{
|
{
|
||||||
switch (element->getType())
|
switch (element->getType())
|
||||||
@@ -678,10 +757,17 @@ FieldBuilderPtr FieldBuilder::addArray(string const & name, FieldConstPtr const
|
|||||||
fields.push_back(fieldCreate->createUnionArray(static_pointer_cast<const Union>(element)));
|
fields.push_back(fieldCreate->createUnionArray(static_pointer_cast<const Union>(element)));
|
||||||
break;
|
break;
|
||||||
case scalar:
|
case scalar:
|
||||||
|
|
||||||
|
if (std::tr1::dynamic_pointer_cast<const BoundedString>(element).get())
|
||||||
|
throw std::invalid_argument("bounded string arrays are not supported");
|
||||||
|
|
||||||
fields.push_back(fieldCreate->createScalarArray(static_pointer_cast<const Scalar>(element)->getScalarType()));
|
fields.push_back(fieldCreate->createScalarArray(static_pointer_cast<const Scalar>(element)->getScalarType()));
|
||||||
break;
|
break;
|
||||||
|
// scalarArray?
|
||||||
default:
|
default:
|
||||||
throw std::invalid_argument("unsupported array element type:" + element->getType());
|
std::ostringstream msg("unsupported array element type: ");
|
||||||
|
msg << element->getType();
|
||||||
|
throw std::invalid_argument(msg.str());
|
||||||
}
|
}
|
||||||
|
|
||||||
fieldNames.push_back(name);
|
fieldNames.push_back(name);
|
||||||
@@ -707,7 +793,11 @@ FieldConstPtr FieldBuilder::createFieldInternal(Type type)
|
|||||||
fieldCreate->createUnion(fieldNames, fields);
|
fieldCreate->createUnion(fieldNames, fields);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
throw std::invalid_argument("unsupported type: " + type);
|
{
|
||||||
|
std::ostringstream msg("unsupported type: ");
|
||||||
|
msg << type;
|
||||||
|
throw std::invalid_argument(msg.str());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -781,6 +871,14 @@ ScalarConstPtr FieldCreate::createScalar(ScalarType scalarType) const
|
|||||||
return scalars[scalarType];
|
return scalars[scalarType];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
BoundedStringConstPtr FieldCreate::createBoundedString(std::size_t maxLength) const
|
||||||
|
{
|
||||||
|
// TODO use std::make_shared
|
||||||
|
std::tr1::shared_ptr<BoundedString> s(new BoundedString(maxLength), Field::Deleter());
|
||||||
|
BoundedStringConstPtr sa = s;
|
||||||
|
return sa;
|
||||||
|
}
|
||||||
|
|
||||||
ScalarArrayConstPtr FieldCreate::createScalarArray(ScalarType elementType) const
|
ScalarArrayConstPtr FieldCreate::createScalarArray(ScalarType elementType) const
|
||||||
{
|
{
|
||||||
if(elementType<0 || elementType>MAX_SCALAR_TYPE)
|
if(elementType<0 || elementType>MAX_SCALAR_TYPE)
|
||||||
@@ -789,6 +887,28 @@ ScalarArrayConstPtr FieldCreate::createScalarArray(ScalarType elementType) const
|
|||||||
return scalarArrays[elementType];
|
return scalarArrays[elementType];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
ScalarArrayConstPtr FieldCreate::createFixedScalarArray(ScalarType elementType, size_t size) const
|
||||||
|
{
|
||||||
|
if(elementType<0 || elementType>MAX_SCALAR_TYPE)
|
||||||
|
throw std::invalid_argument("Can't construct ScalarArray from invalid ScalarType");
|
||||||
|
|
||||||
|
// TODO use std::make_shared
|
||||||
|
std::tr1::shared_ptr<ScalarArray> s(new FixedScalarArray(elementType, size), Field::Deleter());
|
||||||
|
ScalarArrayConstPtr sa = s;
|
||||||
|
return sa;
|
||||||
|
}
|
||||||
|
|
||||||
|
ScalarArrayConstPtr FieldCreate::createBoundedScalarArray(ScalarType elementType, size_t size) const
|
||||||
|
{
|
||||||
|
if(elementType<0 || elementType>MAX_SCALAR_TYPE)
|
||||||
|
throw std::invalid_argument("Can't construct ScalarArray from invalid ScalarType");
|
||||||
|
|
||||||
|
// TODO use std::make_shared
|
||||||
|
std::tr1::shared_ptr<ScalarArray> s(new BoundedScalarArray(elementType, size), Field::Deleter());
|
||||||
|
ScalarArrayConstPtr sa = s;
|
||||||
|
return sa;
|
||||||
|
}
|
||||||
|
|
||||||
StructureConstPtr FieldCreate::createStructure () const
|
StructureConstPtr FieldCreate::createStructure () const
|
||||||
{
|
{
|
||||||
StringArray fieldNames;
|
StringArray fieldNames;
|
||||||
@@ -799,8 +919,9 @@ StructureConstPtr FieldCreate::createStructure () const
|
|||||||
StructureConstPtr FieldCreate::createStructure (
|
StructureConstPtr FieldCreate::createStructure (
|
||||||
StringArray const & fieldNames,FieldConstPtrArray const & fields) const
|
StringArray const & fieldNames,FieldConstPtrArray const & fields) const
|
||||||
{
|
{
|
||||||
StructureConstPtr structure(
|
// TODO use std::make_shared
|
||||||
new Structure(fieldNames,fields), Field::Deleter());
|
std::tr1::shared_ptr<Structure> sp(new Structure(fieldNames,fields), Field::Deleter());
|
||||||
|
StructureConstPtr structure = sp;
|
||||||
return structure;
|
return structure;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -809,24 +930,27 @@ StructureConstPtr FieldCreate::createStructure (
|
|||||||
StringArray const & fieldNames,
|
StringArray const & fieldNames,
|
||||||
FieldConstPtrArray const & fields) const
|
FieldConstPtrArray const & fields) const
|
||||||
{
|
{
|
||||||
StructureConstPtr structure(
|
// TODO use std::make_shared
|
||||||
new Structure(fieldNames,fields,id), Field::Deleter());
|
std::tr1::shared_ptr<Structure> sp(new Structure(fieldNames,fields,id), Field::Deleter());
|
||||||
|
StructureConstPtr structure = sp;
|
||||||
return structure;
|
return structure;
|
||||||
}
|
}
|
||||||
|
|
||||||
StructureArrayConstPtr FieldCreate::createStructureArray(
|
StructureArrayConstPtr FieldCreate::createStructureArray(
|
||||||
StructureConstPtr const & structure) const
|
StructureConstPtr const & structure) const
|
||||||
{
|
{
|
||||||
StructureArrayConstPtr structureArray(
|
// TODO use std::make_shared
|
||||||
new StructureArray(structure), Field::Deleter());
|
std::tr1::shared_ptr<StructureArray> sp(new StructureArray(structure), Field::Deleter());
|
||||||
|
StructureArrayConstPtr structureArray = sp;
|
||||||
return structureArray;
|
return structureArray;
|
||||||
}
|
}
|
||||||
|
|
||||||
UnionConstPtr FieldCreate::createUnion (
|
UnionConstPtr FieldCreate::createUnion (
|
||||||
StringArray const & fieldNames,FieldConstPtrArray const & fields) const
|
StringArray const & fieldNames,FieldConstPtrArray const & fields) const
|
||||||
{
|
{
|
||||||
UnionConstPtr punion(
|
// TODO use std::make_shared
|
||||||
new Union(fieldNames,fields), Field::Deleter());
|
std::tr1::shared_ptr<Union> sp(new Union(fieldNames,fields), Field::Deleter());
|
||||||
|
UnionConstPtr punion = sp;
|
||||||
return punion;
|
return punion;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -835,8 +959,9 @@ UnionConstPtr FieldCreate::createUnion (
|
|||||||
StringArray const & fieldNames,
|
StringArray const & fieldNames,
|
||||||
FieldConstPtrArray const & fields) const
|
FieldConstPtrArray const & fields) const
|
||||||
{
|
{
|
||||||
UnionConstPtr punion(
|
// TODO use std::make_shared
|
||||||
new Union(fieldNames,fields,id), Field::Deleter());
|
std::tr1::shared_ptr<Union> sp(new Union(fieldNames,fields,id), Field::Deleter());
|
||||||
|
UnionConstPtr punion = sp;
|
||||||
return punion;
|
return punion;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -848,8 +973,9 @@ UnionConstPtr FieldCreate::createVariantUnion () const
|
|||||||
UnionArrayConstPtr FieldCreate::createUnionArray(
|
UnionArrayConstPtr FieldCreate::createUnionArray(
|
||||||
UnionConstPtr const & punion) const
|
UnionConstPtr const & punion) const
|
||||||
{
|
{
|
||||||
UnionArrayConstPtr unionArray(
|
// TODO use std::make_shared
|
||||||
new UnionArray(punion), Field::Deleter());
|
std::tr1::shared_ptr<UnionArray> sp(new UnionArray(punion), Field::Deleter());
|
||||||
|
UnionArrayConstPtr unionArray = sp;
|
||||||
return unionArray;
|
return unionArray;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -904,22 +1030,14 @@ static int decodeScalar(int8 code)
|
|||||||
{
|
{
|
||||||
static const int integerLUT[] =
|
static const int integerLUT[] =
|
||||||
{
|
{
|
||||||
pvByte, // 8-bits
|
pvByte, // 8-bits
|
||||||
pvShort, // 16-bits
|
pvShort, // 16-bits
|
||||||
pvInt, // 32-bits
|
pvInt, // 32-bits
|
||||||
pvLong, // 64-bits
|
pvLong, // 64-bits
|
||||||
-1,
|
|
||||||
-1,
|
|
||||||
-1,
|
|
||||||
-1,
|
|
||||||
pvUByte, // unsigned 8-bits
|
pvUByte, // unsigned 8-bits
|
||||||
pvUShort, // unsigned 16-bits
|
pvUShort, // unsigned 16-bits
|
||||||
pvUInt, // unsigned 32-bits
|
pvUInt, // unsigned 32-bits
|
||||||
pvULong, // unsigned 64-bits
|
pvULong // unsigned 64-bits
|
||||||
-1,
|
|
||||||
-1,
|
|
||||||
-1,
|
|
||||||
-1
|
|
||||||
};
|
};
|
||||||
|
|
||||||
static const int floatLUT[] =
|
static const int floatLUT[] =
|
||||||
@@ -931,22 +1049,14 @@ static int decodeScalar(int8 code)
|
|||||||
-1,
|
-1,
|
||||||
-1,
|
-1,
|
||||||
-1,
|
-1,
|
||||||
-1,
|
|
||||||
-1,
|
|
||||||
-1,
|
|
||||||
-1,
|
|
||||||
-1,
|
|
||||||
-1,
|
|
||||||
-1,
|
|
||||||
-1,
|
|
||||||
-1
|
-1
|
||||||
};
|
};
|
||||||
// bits 7-5
|
// bits 7-5
|
||||||
switch (code >> 5)
|
switch (code >> 5)
|
||||||
{
|
{
|
||||||
case 0: return pvBoolean;
|
case 0: return pvBoolean;
|
||||||
case 1: return integerLUT[code & 0x0F];
|
case 1: return integerLUT[code & 0x07];
|
||||||
case 2: return floatLUT[code & 0x0F];
|
case 2: return floatLUT[code & 0x07];
|
||||||
case 3: return pvString;
|
case 3: return pvString;
|
||||||
default: return -1;
|
default: return -1;
|
||||||
}
|
}
|
||||||
@@ -959,8 +1069,9 @@ FieldConstPtr FieldCreate::deserialize(ByteBuffer* buffer, DeserializableControl
|
|||||||
if (code == -1)
|
if (code == -1)
|
||||||
return FieldConstPtr();
|
return FieldConstPtr();
|
||||||
|
|
||||||
int typeCode = code & 0xEF;
|
int typeCode = code & 0xE7;
|
||||||
bool notArray = ((code & 0x10) == 0);
|
int scalarOrArray = code & 0x18;
|
||||||
|
bool notArray = (scalarOrArray == 0);
|
||||||
if (notArray)
|
if (notArray)
|
||||||
{
|
{
|
||||||
if (typeCode < 0x80)
|
if (typeCode < 0x80)
|
||||||
@@ -986,33 +1097,90 @@ FieldConstPtr FieldCreate::deserialize(ByteBuffer* buffer, DeserializableControl
|
|||||||
// Type type = Type.union; variant union (aka any type)
|
// Type type = Type.union; variant union (aka any type)
|
||||||
return variantUnion;
|
return variantUnion;
|
||||||
}
|
}
|
||||||
|
else if (typeCode == 0x83)
|
||||||
|
{
|
||||||
|
// TODO cache?
|
||||||
|
// bounded string
|
||||||
|
|
||||||
|
size_t size = SerializeHelper::readSize(buffer, control);
|
||||||
|
|
||||||
|
// TODO use std::make_shared
|
||||||
|
std::tr1::shared_ptr<Field> sp(
|
||||||
|
new BoundedString(size),
|
||||||
|
Field::Deleter());
|
||||||
|
FieldConstPtr p = sp;
|
||||||
|
return p;
|
||||||
|
}
|
||||||
else
|
else
|
||||||
throw std::invalid_argument("invalid type encoding");
|
throw std::invalid_argument("invalid type encoding");
|
||||||
}
|
}
|
||||||
else // array
|
else // array
|
||||||
{
|
{
|
||||||
|
bool isVariable = (scalarOrArray == 0x08);
|
||||||
|
// bounded == 0x10;
|
||||||
|
bool isFixed = (scalarOrArray == 0x18);
|
||||||
|
|
||||||
|
size_t size = (isVariable ? 0 : SerializeHelper::readSize(buffer, control));
|
||||||
|
|
||||||
if (typeCode < 0x80)
|
if (typeCode < 0x80)
|
||||||
{
|
{
|
||||||
// Type type = Type.scalarArray;
|
// Type type = Type.scalarArray;
|
||||||
int scalarType = decodeScalar(code);
|
int scalarType = decodeScalar(code);
|
||||||
if (scalarType == -1)
|
if (scalarType == -1)
|
||||||
throw std::invalid_argument("invalid scalarArray type encoding");
|
throw std::invalid_argument("invalid scalarArray type encoding");
|
||||||
return scalarArrays[scalarType];
|
if (isVariable)
|
||||||
|
return scalarArrays[scalarType];
|
||||||
|
else if (isFixed)
|
||||||
|
{
|
||||||
|
// TODO use std::make_shared
|
||||||
|
std::tr1::shared_ptr<Field> sp(
|
||||||
|
new FixedScalarArray(static_cast<epics::pvData::ScalarType>(scalarType), size),
|
||||||
|
Field::Deleter());
|
||||||
|
FieldConstPtr p = sp;
|
||||||
|
return p;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
// TODO use std::make_shared
|
||||||
|
std::tr1::shared_ptr<Field> sp(
|
||||||
|
new BoundedScalarArray(static_cast<epics::pvData::ScalarType>(scalarType), size),
|
||||||
|
Field::Deleter());
|
||||||
|
FieldConstPtr p = sp;
|
||||||
|
return p;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
else if (typeCode == 0x80)
|
else if (typeCode == 0x80)
|
||||||
{
|
{
|
||||||
|
// TODO fixed and bounded array support
|
||||||
|
if (!isVariable)
|
||||||
|
throw std::invalid_argument("fixed and bounded structure array not supported");
|
||||||
|
|
||||||
// Type type = Type.structureArray;
|
// Type type = Type.structureArray;
|
||||||
StructureConstPtr elementStructure = std::tr1::static_pointer_cast<const Structure>(control->cachedDeserialize(buffer));
|
StructureConstPtr elementStructure = std::tr1::static_pointer_cast<const Structure>(control->cachedDeserialize(buffer));
|
||||||
return FieldConstPtr(new StructureArray(elementStructure), Field::Deleter());
|
// TODO use std::make_shared
|
||||||
|
std::tr1::shared_ptr<Field> sp(new StructureArray(elementStructure), Field::Deleter());
|
||||||
|
FieldConstPtr p = sp;
|
||||||
|
return p;
|
||||||
}
|
}
|
||||||
else if (typeCode == 0x81)
|
else if (typeCode == 0x81)
|
||||||
{
|
{
|
||||||
|
// TODO fixed and bounded array support
|
||||||
|
if (!isVariable)
|
||||||
|
throw std::invalid_argument("fixed and bounded structure array not supported");
|
||||||
|
|
||||||
// Type type = Type.unionArray;
|
// Type type = Type.unionArray;
|
||||||
UnionConstPtr elementUnion = std::tr1::static_pointer_cast<const Union>(control->cachedDeserialize(buffer));
|
UnionConstPtr elementUnion = std::tr1::static_pointer_cast<const Union>(control->cachedDeserialize(buffer));
|
||||||
return FieldConstPtr(new UnionArray(elementUnion), Field::Deleter());
|
// TODO use std::make_shared
|
||||||
|
std::tr1::shared_ptr<Field> sp(new UnionArray(elementUnion), Field::Deleter());
|
||||||
|
FieldConstPtr p = sp;
|
||||||
|
return p;
|
||||||
}
|
}
|
||||||
else if (typeCode == 0x82)
|
else if (typeCode == 0x82)
|
||||||
{
|
{
|
||||||
|
// TODO fixed and bounded array support
|
||||||
|
if (!isVariable)
|
||||||
|
throw std::invalid_argument("fixed and bounded structure array not supported");
|
||||||
|
|
||||||
// Type type = Type.unionArray; variant union (aka any type)
|
// Type type = Type.unionArray; variant union (aka any type)
|
||||||
return variantUnionArray;
|
return variantUnionArray;
|
||||||
}
|
}
|
||||||
@@ -1037,11 +1205,24 @@ FieldCreate::FieldCreate()
|
|||||||
{
|
{
|
||||||
for (int i = 0; i <= MAX_SCALAR_TYPE; i++)
|
for (int i = 0; i <= MAX_SCALAR_TYPE; i++)
|
||||||
{
|
{
|
||||||
scalars.push_back(ScalarConstPtr(new Scalar(static_cast<ScalarType>(i)), Field::Deleter()));
|
// TODO use std::make_shared
|
||||||
scalarArrays.push_back(ScalarArrayConstPtr(new ScalarArray(static_cast<ScalarType>(i)), Field::Deleter()));
|
std::tr1::shared_ptr<Scalar> sp(new Scalar(static_cast<ScalarType>(i)), Field::Deleter());
|
||||||
|
ScalarConstPtr p = sp;
|
||||||
|
scalars.push_back(p);
|
||||||
|
|
||||||
|
// TODO use std::make_shared
|
||||||
|
std::tr1::shared_ptr<ScalarArray> spa(new ScalarArray(static_cast<ScalarType>(i)), Field::Deleter());
|
||||||
|
ScalarArrayConstPtr pa = spa;
|
||||||
|
scalarArrays.push_back(spa);
|
||||||
}
|
}
|
||||||
variantUnion = UnionConstPtr(new Union(), Field::Deleter());
|
|
||||||
variantUnionArray = UnionArrayConstPtr(new UnionArray(variantUnion), Field::Deleter());
|
// TODO use std::make_shared
|
||||||
|
std::tr1::shared_ptr<Union> su(new Union(), Field::Deleter());
|
||||||
|
variantUnion = su;
|
||||||
|
|
||||||
|
// TODO use std::make_shared
|
||||||
|
std::tr1::shared_ptr<UnionArray> sua(new UnionArray(variantUnion), Field::Deleter());
|
||||||
|
variantUnionArray = sua;
|
||||||
}
|
}
|
||||||
|
|
||||||
FieldCreatePtr getFieldCreate() {
|
FieldCreatePtr getFieldCreate() {
|
||||||
|
|||||||
@@ -145,11 +145,18 @@ public:
|
|||||||
SerializableControl *pflusher, size_t offset, size_t count) const;
|
SerializableControl *pflusher, size_t offset, size_t count) const;
|
||||||
private:
|
private:
|
||||||
string value;
|
string value;
|
||||||
|
std::size_t maxLength;
|
||||||
};
|
};
|
||||||
|
|
||||||
BasePVString::BasePVString(ScalarConstPtr const & scalar)
|
BasePVString::BasePVString(ScalarConstPtr const & scalar)
|
||||||
: PVString(scalar),value()
|
: PVString(scalar),value()
|
||||||
{}
|
{
|
||||||
|
BoundedStringConstPtr boundedString = std::tr1::dynamic_pointer_cast<const BoundedString>(scalar);
|
||||||
|
if (boundedString.get())
|
||||||
|
maxLength = boundedString->getMaximumLength();
|
||||||
|
else
|
||||||
|
maxLength = 0;
|
||||||
|
}
|
||||||
|
|
||||||
BasePVString::~BasePVString() {}
|
BasePVString::~BasePVString() {}
|
||||||
|
|
||||||
@@ -157,6 +164,9 @@ string BasePVString::get() const { return value;}
|
|||||||
|
|
||||||
void BasePVString::put(string val)
|
void BasePVString::put(string val)
|
||||||
{
|
{
|
||||||
|
if (maxLength > 0 && val.length() > maxLength)
|
||||||
|
throw std::overflow_error("string too long");
|
||||||
|
|
||||||
value = val;
|
value = val;
|
||||||
postPut();
|
postPut();
|
||||||
}
|
}
|
||||||
@@ -190,6 +200,19 @@ void BasePVString::serialize(ByteBuffer *pbuffer,
|
|||||||
SerializeHelper::serializeSubstring(value, offset, count, pbuffer, pflusher);
|
SerializeHelper::serializeSubstring(value, offset, count, pbuffer, pflusher);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void PVArray::checkLength(size_t len)
|
||||||
|
{
|
||||||
|
Array::ArraySizeType type = getArray()->getArraySizeType();
|
||||||
|
if (type != Array::variable)
|
||||||
|
{
|
||||||
|
size_t size = getArray()->getMaximumCapacity();
|
||||||
|
if (type == Array::fixed && len != size)
|
||||||
|
throw std::invalid_argument("invalid length for a fixed size array");
|
||||||
|
else if (type == Array::bounded && len > size)
|
||||||
|
throw std::invalid_argument("new array capacity too large for a bounded size array");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/** Default storage for arrays
|
/** Default storage for arrays
|
||||||
*/
|
*/
|
||||||
template<typename T>
|
template<typename T>
|
||||||
@@ -231,7 +254,14 @@ DefaultPVArray<T>::DefaultPVArray(ScalarArrayConstPtr const & scalarArray)
|
|||||||
: PVValueArray<T>(scalarArray),
|
: PVValueArray<T>(scalarArray),
|
||||||
value()
|
value()
|
||||||
|
|
||||||
{ }
|
{
|
||||||
|
ArrayConstPtr array = this->getArray();
|
||||||
|
if (array->getArraySizeType() == Array::fixed)
|
||||||
|
{
|
||||||
|
// this->setLength(array->getMaximumCapacity());
|
||||||
|
this->setCapacityMutable(false);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
template<typename T>
|
template<typename T>
|
||||||
DefaultPVArray<T>::~DefaultPVArray()
|
DefaultPVArray<T>::~DefaultPVArray()
|
||||||
@@ -240,18 +270,25 @@ template<typename T>
|
|||||||
void DefaultPVArray<T>::setCapacity(size_t capacity)
|
void DefaultPVArray<T>::setCapacity(size_t capacity)
|
||||||
{
|
{
|
||||||
if(this->isCapacityMutable()) {
|
if(this->isCapacityMutable()) {
|
||||||
|
this->checkLength(capacity);
|
||||||
value.reserve(capacity);
|
value.reserve(capacity);
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
THROW_EXCEPTION2(std::logic_error, "capacity immutable");
|
||||||
}
|
}
|
||||||
|
|
||||||
template<typename T>
|
template<typename T>
|
||||||
void DefaultPVArray<T>::setLength(size_t length)
|
void DefaultPVArray<T>::setLength(size_t length)
|
||||||
{
|
{
|
||||||
if(this->isImmutable())
|
if(this->isImmutable())
|
||||||
THROW_EXCEPTION2(std::logic_error,"Immutable");
|
THROW_EXCEPTION2(std::logic_error, "immutable");
|
||||||
if(length == value.size())
|
|
||||||
|
if (length == value.size())
|
||||||
return;
|
return;
|
||||||
else if(length < value.size())
|
|
||||||
|
this->checkLength(length);
|
||||||
|
|
||||||
|
if (length < value.size())
|
||||||
value.slice(0, length);
|
value.slice(0, length);
|
||||||
else
|
else
|
||||||
value.resize(length);
|
value.resize(length);
|
||||||
@@ -260,6 +297,8 @@ void DefaultPVArray<T>::setLength(size_t length)
|
|||||||
template<typename T>
|
template<typename T>
|
||||||
void DefaultPVArray<T>::replace(const const_svector& next)
|
void DefaultPVArray<T>::replace(const const_svector& next)
|
||||||
{
|
{
|
||||||
|
this->checkLength(next.size());
|
||||||
|
|
||||||
value = next;
|
value = next;
|
||||||
this->postPut();
|
this->postPut();
|
||||||
}
|
}
|
||||||
@@ -267,8 +306,10 @@ void DefaultPVArray<T>::replace(const const_svector& next)
|
|||||||
template<typename T>
|
template<typename T>
|
||||||
void DefaultPVArray<T>::swap(const_svector &other)
|
void DefaultPVArray<T>::swap(const_svector &other)
|
||||||
{
|
{
|
||||||
if(this->isImmutable())
|
if (this->isImmutable())
|
||||||
THROW_EXCEPTION2(std::logic_error,"Immutable");
|
THROW_EXCEPTION2(std::logic_error, "immutable");
|
||||||
|
|
||||||
|
// no checkLength call here
|
||||||
|
|
||||||
value.swap(other);
|
value.swap(other);
|
||||||
}
|
}
|
||||||
@@ -283,7 +324,10 @@ void DefaultPVArray<T>::serialize(ByteBuffer *pbuffer,
|
|||||||
template<typename T>
|
template<typename T>
|
||||||
void DefaultPVArray<T>::deserialize(ByteBuffer *pbuffer,
|
void DefaultPVArray<T>::deserialize(ByteBuffer *pbuffer,
|
||||||
DeserializableControl *pcontrol) {
|
DeserializableControl *pcontrol) {
|
||||||
size_t size = SerializeHelper::readSize(pbuffer, pcontrol);
|
|
||||||
|
size_t size = this->getArray()->getArraySizeType() == Array::fixed ?
|
||||||
|
this->getArray()->getMaximumCapacity() :
|
||||||
|
SerializeHelper::readSize(pbuffer, pcontrol);
|
||||||
|
|
||||||
svector nextvalue(thaw(value));
|
svector nextvalue(thaw(value));
|
||||||
nextvalue.resize(size); // TODO: avoid copy of stuff we will then overwrite
|
nextvalue.resize(size); // TODO: avoid copy of stuff we will then overwrite
|
||||||
@@ -321,6 +365,7 @@ void DefaultPVArray<T>::deserialize(ByteBuffer *pbuffer,
|
|||||||
remaining -= n2read;
|
remaining -= n2read;
|
||||||
}
|
}
|
||||||
value = freeze(nextvalue);
|
value = freeze(nextvalue);
|
||||||
|
// TODO !!!
|
||||||
// inform about the change?
|
// inform about the change?
|
||||||
PVField::postPut();
|
PVField::postPut();
|
||||||
}
|
}
|
||||||
@@ -334,7 +379,11 @@ void DefaultPVArray<T>::serialize(ByteBuffer *pbuffer,
|
|||||||
temp.slice(offset, count);
|
temp.slice(offset, count);
|
||||||
count = temp.size();
|
count = temp.size();
|
||||||
|
|
||||||
SerializeHelper::writeSize(temp.size(), pbuffer, pflusher);
|
ArrayConstPtr array = this->getArray();
|
||||||
|
if (array->getArraySizeType() != Array::fixed)
|
||||||
|
SerializeHelper::writeSize(count, pbuffer, pflusher);
|
||||||
|
else if (count != array->getMaximumCapacity())
|
||||||
|
throw std::length_error("fixed array cannot be partially serialized");
|
||||||
|
|
||||||
const T* cur = temp.data();
|
const T* cur = temp.data();
|
||||||
|
|
||||||
@@ -368,7 +417,10 @@ void DefaultPVArray<T>::serialize(ByteBuffer *pbuffer,
|
|||||||
template<>
|
template<>
|
||||||
void DefaultPVArray<string>::deserialize(ByteBuffer *pbuffer,
|
void DefaultPVArray<string>::deserialize(ByteBuffer *pbuffer,
|
||||||
DeserializableControl *pcontrol) {
|
DeserializableControl *pcontrol) {
|
||||||
size_t size = SerializeHelper::readSize(pbuffer, pcontrol);
|
|
||||||
|
size_t size = this->getArray()->getArraySizeType() == Array::fixed ?
|
||||||
|
this->getArray()->getMaximumCapacity() :
|
||||||
|
SerializeHelper::readSize(pbuffer, pcontrol);
|
||||||
|
|
||||||
svector nextvalue(thaw(value));
|
svector nextvalue(thaw(value));
|
||||||
|
|
||||||
@@ -396,7 +448,9 @@ void DefaultPVArray<string>::serialize(ByteBuffer *pbuffer,
|
|||||||
const_svector temp(value);
|
const_svector temp(value);
|
||||||
temp.slice(offset, count);
|
temp.slice(offset, count);
|
||||||
|
|
||||||
SerializeHelper::writeSize(temp.size(), pbuffer, pflusher);
|
// TODO if fixed count == getArray()->getMaximumCapacity()
|
||||||
|
if (this->getArray()->getArraySizeType() != Array::fixed)
|
||||||
|
SerializeHelper::writeSize(temp.size(), pbuffer, pflusher);
|
||||||
|
|
||||||
const string * pvalue = temp.data();
|
const string * pvalue = temp.data();
|
||||||
for(size_t i = 0; i<temp.size(); i++) {
|
for(size_t i = 0; i<temp.size(); i++) {
|
||||||
@@ -649,7 +703,7 @@ PVStructurePtr PVDataCreate::createPVStructure(
|
|||||||
PVStructurePtr PVDataCreate::createPVStructure(PVStructurePtr const & structToClone)
|
PVStructurePtr PVDataCreate::createPVStructure(PVStructurePtr const & structToClone)
|
||||||
{
|
{
|
||||||
FieldConstPtrArray field;
|
FieldConstPtrArray field;
|
||||||
if(structToClone==0) {
|
if(!structToClone) {
|
||||||
// is this correct?!
|
// is this correct?!
|
||||||
FieldConstPtrArray fields(0);
|
FieldConstPtrArray fields(0);
|
||||||
StringArray fieldNames(0);
|
StringArray fieldNames(0);
|
||||||
|
|||||||
@@ -33,7 +33,7 @@ namespace epics { namespace pvData {
|
|||||||
template<>
|
template<>
|
||||||
std::ostream& PVScalarValue<int8>::dumpValue(std::ostream& o) const
|
std::ostream& PVScalarValue<int8>::dumpValue(std::ostream& o) const
|
||||||
{
|
{
|
||||||
return o << static_cast<int>(get());
|
return o << static_cast<int>(get());
|
||||||
}
|
}
|
||||||
|
|
||||||
template<>
|
template<>
|
||||||
@@ -41,4 +41,10 @@ namespace epics { namespace pvData {
|
|||||||
{
|
{
|
||||||
return o << static_cast<unsigned int>(get());
|
return o << static_cast<unsigned int>(get());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<>
|
||||||
|
std::ostream& PVScalarValue<boolean>::dumpValue(std::ostream& o) const
|
||||||
|
{
|
||||||
|
return o << std::boolalpha << static_cast<bool>(get());
|
||||||
|
}
|
||||||
}}
|
}}
|
||||||
|
|||||||
@@ -25,6 +25,8 @@ namespace epics { namespace pvData {
|
|||||||
|
|
||||||
size_t PVStructureArray::append(size_t number)
|
size_t PVStructureArray::append(size_t number)
|
||||||
{
|
{
|
||||||
|
checkLength(value.size()+number);
|
||||||
|
|
||||||
svector data(reuse());
|
svector data(reuse());
|
||||||
data.resize(data.size()+number);
|
data.resize(data.size()+number);
|
||||||
|
|
||||||
@@ -44,9 +46,11 @@ size_t PVStructureArray::append(size_t number)
|
|||||||
|
|
||||||
bool PVStructureArray::remove(size_t offset,size_t number)
|
bool PVStructureArray::remove(size_t offset,size_t number)
|
||||||
{
|
{
|
||||||
if(number==0)
|
if (number==0)
|
||||||
return true;
|
return true;
|
||||||
else if(offset+number>getLength())
|
else if (offset+number>getLength())
|
||||||
|
return false;
|
||||||
|
else if (getArray()->getArraySizeType() == Array::fixed)
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
svector vec(reuse());
|
svector vec(reuse());
|
||||||
@@ -65,6 +69,9 @@ bool PVStructureArray::remove(size_t offset,size_t number)
|
|||||||
}
|
}
|
||||||
|
|
||||||
void PVStructureArray::compress() {
|
void PVStructureArray::compress() {
|
||||||
|
if (getArray()->getArraySizeType() == Array::fixed)
|
||||||
|
return;
|
||||||
|
|
||||||
svector vec(reuse()); // TODO: check for first NULL before realloc
|
svector vec(reuse()); // TODO: check for first NULL before realloc
|
||||||
|
|
||||||
size_t length = vec.size();
|
size_t length = vec.size();
|
||||||
@@ -99,7 +106,8 @@ void PVStructureArray::compress() {
|
|||||||
|
|
||||||
void PVStructureArray::setCapacity(size_t capacity)
|
void PVStructureArray::setCapacity(size_t capacity)
|
||||||
{
|
{
|
||||||
if(this->isCapacityMutable()) {
|
if (this->isCapacityMutable()) {
|
||||||
|
checkLength(capacity);
|
||||||
const_svector value;
|
const_svector value;
|
||||||
swap(value);
|
swap(value);
|
||||||
if(value.capacity()<capacity) {
|
if(value.capacity()<capacity) {
|
||||||
@@ -109,17 +117,23 @@ void PVStructureArray::setCapacity(size_t capacity)
|
|||||||
}
|
}
|
||||||
swap(value);
|
swap(value);
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
THROW_EXCEPTION2(std::logic_error, "capacity immutable");
|
||||||
}
|
}
|
||||||
|
|
||||||
void PVStructureArray::setLength(size_t length)
|
void PVStructureArray::setLength(size_t length)
|
||||||
{
|
{
|
||||||
if(this->isImmutable())
|
if(this->isImmutable())
|
||||||
THROW_EXCEPTION2(std::logic_error,"Immutable");
|
THROW_EXCEPTION2(std::logic_error, "immutable");
|
||||||
const_svector value;
|
const_svector value;
|
||||||
swap(value);
|
swap(value);
|
||||||
if(length == value.size()) {
|
|
||||||
// nothing
|
if (length == value.size())
|
||||||
} else if(length < value.size()) {
|
return;
|
||||||
|
|
||||||
|
checkLength(length);
|
||||||
|
|
||||||
|
if (length < value.size()) {
|
||||||
value.slice(0, length);
|
value.slice(0, length);
|
||||||
} else {
|
} else {
|
||||||
svector mvalue(thaw(value));
|
svector mvalue(thaw(value));
|
||||||
@@ -131,8 +145,10 @@ void PVStructureArray::setLength(size_t length)
|
|||||||
|
|
||||||
void PVStructureArray::swap(const_svector &other)
|
void PVStructureArray::swap(const_svector &other)
|
||||||
{
|
{
|
||||||
if(this->isImmutable())
|
if (this->isImmutable())
|
||||||
THROW_EXCEPTION2(std::logic_error,"Immutable");
|
THROW_EXCEPTION2(std::logic_error, "immutable");
|
||||||
|
|
||||||
|
// no checkLength call here
|
||||||
|
|
||||||
value.swap(other);
|
value.swap(other);
|
||||||
}
|
}
|
||||||
@@ -146,7 +162,10 @@ void PVStructureArray::deserialize(ByteBuffer *pbuffer,
|
|||||||
DeserializableControl *pcontrol) {
|
DeserializableControl *pcontrol) {
|
||||||
svector data(reuse());
|
svector data(reuse());
|
||||||
|
|
||||||
size_t size = SerializeHelper::readSize(pbuffer, pcontrol);
|
size_t size = this->getArray()->getArraySizeType() == Array::fixed ?
|
||||||
|
this->getArray()->getMaximumCapacity() :
|
||||||
|
SerializeHelper::readSize(pbuffer, pcontrol);
|
||||||
|
|
||||||
data.resize(size);
|
data.resize(size);
|
||||||
|
|
||||||
StructureConstPtr structure = structureArray->getStructure();
|
StructureConstPtr structure = structureArray->getStructure();
|
||||||
@@ -175,7 +194,11 @@ void PVStructureArray::serialize(ByteBuffer *pbuffer,
|
|||||||
const_svector temp(view());
|
const_svector temp(view());
|
||||||
temp.slice(offset, count);
|
temp.slice(offset, count);
|
||||||
|
|
||||||
SerializeHelper::writeSize(temp.size(), pbuffer, pflusher);
|
ArrayConstPtr array = this->getArray();
|
||||||
|
if (array->getArraySizeType() != Array::fixed)
|
||||||
|
SerializeHelper::writeSize(temp.size(), pbuffer, pflusher);
|
||||||
|
else if (count != array->getMaximumCapacity())
|
||||||
|
throw std::length_error("fixed array cannot be partially serialized");
|
||||||
|
|
||||||
for(size_t i = 0; i<count; i++) {
|
for(size_t i = 0; i<count; i++) {
|
||||||
if(pbuffer->getRemaining()<1)
|
if(pbuffer->getRemaining()<1)
|
||||||
@@ -209,8 +232,13 @@ std::ostream& PVStructureArray::dumpValue(std::ostream& o) const
|
|||||||
std::ostream& PVStructureArray::dumpValue(std::ostream& o, std::size_t index) const
|
std::ostream& PVStructureArray::dumpValue(std::ostream& o, std::size_t index) const
|
||||||
{
|
{
|
||||||
const_svector temp(view());
|
const_svector temp(view());
|
||||||
if(index<temp.size())
|
if (index<temp.size())
|
||||||
o << *temp[index];
|
{
|
||||||
|
if (temp[index])
|
||||||
|
o << *temp[index];
|
||||||
|
else
|
||||||
|
o << format::indent() << "(none)" << std::endl;
|
||||||
|
}
|
||||||
return o;
|
return o;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -169,7 +169,9 @@ void PVUnion::deserialize(ByteBuffer *pbuffer, DeserializableControl *pcontrol)
|
|||||||
FieldConstPtr field = pcontrol->cachedDeserialize(pbuffer);
|
FieldConstPtr field = pcontrol->cachedDeserialize(pbuffer);
|
||||||
if (field.get())
|
if (field.get())
|
||||||
{
|
{
|
||||||
value = getPVDataCreate()->createPVField(field);
|
// try to reuse existing field instance
|
||||||
|
if (!value.get() || *value->getField() != *field)
|
||||||
|
value = getPVDataCreate()->createPVField(field);
|
||||||
value->deserialize(pbuffer, pcontrol);
|
value->deserialize(pbuffer, pcontrol);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
@@ -177,11 +179,17 @@ void PVUnion::deserialize(ByteBuffer *pbuffer, DeserializableControl *pcontrol)
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
int32 previousSelector = selector;
|
||||||
selector = static_cast<int32>(SerializeHelper::readSize(pbuffer, pcontrol));
|
selector = static_cast<int32>(SerializeHelper::readSize(pbuffer, pcontrol));
|
||||||
if (selector != UNDEFINED_INDEX)
|
if (selector != UNDEFINED_INDEX)
|
||||||
{
|
{
|
||||||
FieldConstPtr field = unionPtr->getField(selector);
|
if (selector != previousSelector)
|
||||||
value = getPVDataCreate()->createPVField(field);
|
{
|
||||||
|
FieldConstPtr field = unionPtr->getField(selector);
|
||||||
|
// try to reuse existing field instance
|
||||||
|
if (!value.get() || *value->getField() != *field)
|
||||||
|
value = getPVDataCreate()->createPVField(field);
|
||||||
|
}
|
||||||
value->deserialize(pbuffer, pcontrol);
|
value->deserialize(pbuffer, pcontrol);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
|
|||||||
@@ -25,6 +25,8 @@ namespace epics { namespace pvData {
|
|||||||
|
|
||||||
size_t PVUnionArray::append(size_t number)
|
size_t PVUnionArray::append(size_t number)
|
||||||
{
|
{
|
||||||
|
checkLength(value.size()+number);
|
||||||
|
|
||||||
svector data(reuse());
|
svector data(reuse());
|
||||||
data.resize(data.size()+number);
|
data.resize(data.size()+number);
|
||||||
|
|
||||||
@@ -44,9 +46,11 @@ size_t PVUnionArray::append(size_t number)
|
|||||||
|
|
||||||
bool PVUnionArray::remove(size_t offset,size_t number)
|
bool PVUnionArray::remove(size_t offset,size_t number)
|
||||||
{
|
{
|
||||||
if(number==0)
|
if (number==0)
|
||||||
return true;
|
return true;
|
||||||
else if(offset+number>getLength())
|
else if (offset+number>getLength())
|
||||||
|
return false;
|
||||||
|
else if (getArray()->getArraySizeType() == Array::fixed)
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
svector vec(reuse());
|
svector vec(reuse());
|
||||||
@@ -65,6 +69,9 @@ bool PVUnionArray::remove(size_t offset,size_t number)
|
|||||||
}
|
}
|
||||||
|
|
||||||
void PVUnionArray::compress() {
|
void PVUnionArray::compress() {
|
||||||
|
if (getArray()->getArraySizeType() == Array::fixed)
|
||||||
|
return;
|
||||||
|
|
||||||
svector vec(reuse()); // TODO: check for first NULL before realloc
|
svector vec(reuse()); // TODO: check for first NULL before realloc
|
||||||
|
|
||||||
size_t length = vec.size();
|
size_t length = vec.size();
|
||||||
@@ -100,6 +107,7 @@ void PVUnionArray::compress() {
|
|||||||
void PVUnionArray::setCapacity(size_t capacity)
|
void PVUnionArray::setCapacity(size_t capacity)
|
||||||
{
|
{
|
||||||
if(this->isCapacityMutable()) {
|
if(this->isCapacityMutable()) {
|
||||||
|
checkLength(capacity);
|
||||||
const_svector value;
|
const_svector value;
|
||||||
swap(value);
|
swap(value);
|
||||||
if(value.capacity()<capacity) {
|
if(value.capacity()<capacity) {
|
||||||
@@ -109,17 +117,22 @@ void PVUnionArray::setCapacity(size_t capacity)
|
|||||||
}
|
}
|
||||||
swap(value);
|
swap(value);
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
THROW_EXCEPTION2(std::logic_error, "capacity immutable");
|
||||||
}
|
}
|
||||||
|
|
||||||
void PVUnionArray::setLength(size_t length)
|
void PVUnionArray::setLength(size_t length)
|
||||||
{
|
{
|
||||||
if(this->isImmutable())
|
if(this->isImmutable())
|
||||||
THROW_EXCEPTION2(std::logic_error,"Immutable");
|
THROW_EXCEPTION2(std::logic_error, "immutable");
|
||||||
const_svector value;
|
const_svector value;
|
||||||
swap(value);
|
swap(value);
|
||||||
if(length == value.size()) {
|
if (length == value.size())
|
||||||
// nothing
|
return;
|
||||||
} else if(length < value.size()) {
|
|
||||||
|
checkLength(length);
|
||||||
|
|
||||||
|
if (length < value.size()) {
|
||||||
value.slice(0, length);
|
value.slice(0, length);
|
||||||
} else {
|
} else {
|
||||||
svector mvalue(thaw(value));
|
svector mvalue(thaw(value));
|
||||||
@@ -134,6 +147,8 @@ void PVUnionArray::swap(const_svector &other)
|
|||||||
if(this->isImmutable())
|
if(this->isImmutable())
|
||||||
THROW_EXCEPTION2(std::logic_error,"Immutable");
|
THROW_EXCEPTION2(std::logic_error,"Immutable");
|
||||||
|
|
||||||
|
// no checkLength call here
|
||||||
|
|
||||||
value.swap(other);
|
value.swap(other);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -146,7 +161,10 @@ void PVUnionArray::deserialize(ByteBuffer *pbuffer,
|
|||||||
DeserializableControl *pcontrol) {
|
DeserializableControl *pcontrol) {
|
||||||
svector data(reuse());
|
svector data(reuse());
|
||||||
|
|
||||||
size_t size = SerializeHelper::readSize(pbuffer, pcontrol);
|
size_t size = this->getArray()->getArraySizeType() == Array::fixed ?
|
||||||
|
this->getArray()->getMaximumCapacity() :
|
||||||
|
SerializeHelper::readSize(pbuffer, pcontrol);
|
||||||
|
|
||||||
data.resize(size);
|
data.resize(size);
|
||||||
|
|
||||||
UnionConstPtr punion = unionArray->getUnion();
|
UnionConstPtr punion = unionArray->getUnion();
|
||||||
@@ -175,7 +193,11 @@ void PVUnionArray::serialize(ByteBuffer *pbuffer,
|
|||||||
const_svector temp(view());
|
const_svector temp(view());
|
||||||
temp.slice(offset, count);
|
temp.slice(offset, count);
|
||||||
|
|
||||||
SerializeHelper::writeSize(temp.size(), pbuffer, pflusher);
|
ArrayConstPtr array = this->getArray();
|
||||||
|
if (array->getArraySizeType() != Array::fixed)
|
||||||
|
SerializeHelper::writeSize(temp.size(), pbuffer, pflusher);
|
||||||
|
else if (count != array->getMaximumCapacity())
|
||||||
|
throw std::length_error("fixed array cannot be partially serialized");
|
||||||
|
|
||||||
for(size_t i = 0; i<count; i++) {
|
for(size_t i = 0; i<count; i++) {
|
||||||
if(pbuffer->getRemaining()<1)
|
if(pbuffer->getRemaining()<1)
|
||||||
@@ -209,8 +231,13 @@ std::ostream& PVUnionArray::dumpValue(std::ostream& o) const
|
|||||||
std::ostream& PVUnionArray::dumpValue(std::ostream& o, std::size_t index) const
|
std::ostream& PVUnionArray::dumpValue(std::ostream& o, std::size_t index) const
|
||||||
{
|
{
|
||||||
const_svector temp(view());
|
const_svector temp(view());
|
||||||
if(index<temp.size())
|
if (index<temp.size())
|
||||||
o << *temp[index];
|
{
|
||||||
|
if (temp[index])
|
||||||
|
o << *temp[index];
|
||||||
|
else
|
||||||
|
o << format::indent() << "(none)" << std::endl;
|
||||||
|
}
|
||||||
return o;
|
return o;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -162,7 +162,7 @@ void StandardField::createTimeStamp() {
|
|||||||
FieldConstPtrArray fields(num);
|
FieldConstPtrArray fields(num);
|
||||||
StringArray names(num);
|
StringArray names(num);
|
||||||
names[0] = "secondsPastEpoch";
|
names[0] = "secondsPastEpoch";
|
||||||
names[1] = "nanoSeconds";
|
names[1] = "nanoseconds";
|
||||||
names[2] = "userTag";
|
names[2] = "userTag";
|
||||||
fields[0] = fieldCreate->createScalar(pvLong);
|
fields[0] = fieldCreate->createScalar(pvLong);
|
||||||
fields[1] = fieldCreate->createScalar(pvInt);
|
fields[1] = fieldCreate->createScalar(pvInt);
|
||||||
@@ -228,7 +228,7 @@ void StandardField::createByteAlarm() {
|
|||||||
names[6] = "lowWarningSeverity";
|
names[6] = "lowWarningSeverity";
|
||||||
names[7] = "highWarningSeverity";
|
names[7] = "highWarningSeverity";
|
||||||
names[8] = "highAlarmSeverity";
|
names[8] = "highAlarmSeverity";
|
||||||
names[9] = "hystersis";
|
names[9] = "hysteresis";
|
||||||
fields[0] = fieldCreate->createScalar(pvBoolean);
|
fields[0] = fieldCreate->createScalar(pvBoolean);
|
||||||
fields[1] = fieldCreate->createScalar(pvByte);
|
fields[1] = fieldCreate->createScalar(pvByte);
|
||||||
fields[2] = fieldCreate->createScalar(pvByte);
|
fields[2] = fieldCreate->createScalar(pvByte);
|
||||||
@@ -255,7 +255,7 @@ void StandardField::createShortAlarm() {
|
|||||||
names[6] = "lowWarningSeverity";
|
names[6] = "lowWarningSeverity";
|
||||||
names[7] = "highWarningSeverity";
|
names[7] = "highWarningSeverity";
|
||||||
names[8] = "highAlarmSeverity";
|
names[8] = "highAlarmSeverity";
|
||||||
names[9] = "hystersis";
|
names[9] = "hysteresis";
|
||||||
fields[0] = fieldCreate->createScalar(pvBoolean);
|
fields[0] = fieldCreate->createScalar(pvBoolean);
|
||||||
fields[1] = fieldCreate->createScalar(pvShort);
|
fields[1] = fieldCreate->createScalar(pvShort);
|
||||||
fields[2] = fieldCreate->createScalar(pvShort);
|
fields[2] = fieldCreate->createScalar(pvShort);
|
||||||
@@ -282,7 +282,7 @@ void StandardField::createIntAlarm() {
|
|||||||
names[6] = "lowWarningSeverity";
|
names[6] = "lowWarningSeverity";
|
||||||
names[7] = "highWarningSeverity";
|
names[7] = "highWarningSeverity";
|
||||||
names[8] = "highAlarmSeverity";
|
names[8] = "highAlarmSeverity";
|
||||||
names[9] = "hystersis";
|
names[9] = "hysteresis";
|
||||||
fields[0] = fieldCreate->createScalar(pvBoolean);
|
fields[0] = fieldCreate->createScalar(pvBoolean);
|
||||||
fields[1] = fieldCreate->createScalar(pvInt);
|
fields[1] = fieldCreate->createScalar(pvInt);
|
||||||
fields[2] = fieldCreate->createScalar(pvInt);
|
fields[2] = fieldCreate->createScalar(pvInt);
|
||||||
@@ -309,7 +309,7 @@ void StandardField::createLongAlarm() {
|
|||||||
names[6] = "lowWarningSeverity";
|
names[6] = "lowWarningSeverity";
|
||||||
names[7] = "highWarningSeverity";
|
names[7] = "highWarningSeverity";
|
||||||
names[8] = "highAlarmSeverity";
|
names[8] = "highAlarmSeverity";
|
||||||
names[9] = "hystersis";
|
names[9] = "hysteresis";
|
||||||
fields[0] = fieldCreate->createScalar(pvBoolean);
|
fields[0] = fieldCreate->createScalar(pvBoolean);
|
||||||
fields[1] = fieldCreate->createScalar(pvLong);
|
fields[1] = fieldCreate->createScalar(pvLong);
|
||||||
fields[2] = fieldCreate->createScalar(pvLong);
|
fields[2] = fieldCreate->createScalar(pvLong);
|
||||||
@@ -336,7 +336,7 @@ void StandardField::createUByteAlarm() {
|
|||||||
names[6] = "lowWarningSeverity";
|
names[6] = "lowWarningSeverity";
|
||||||
names[7] = "highWarningSeverity";
|
names[7] = "highWarningSeverity";
|
||||||
names[8] = "highAlarmSeverity";
|
names[8] = "highAlarmSeverity";
|
||||||
names[9] = "hystersis";
|
names[9] = "hysteresis";
|
||||||
fields[0] = fieldCreate->createScalar(pvBoolean);
|
fields[0] = fieldCreate->createScalar(pvBoolean);
|
||||||
fields[1] = fieldCreate->createScalar(pvUByte);
|
fields[1] = fieldCreate->createScalar(pvUByte);
|
||||||
fields[2] = fieldCreate->createScalar(pvUByte);
|
fields[2] = fieldCreate->createScalar(pvUByte);
|
||||||
@@ -363,7 +363,7 @@ void StandardField::createUShortAlarm() {
|
|||||||
names[6] = "lowWarningSeverity";
|
names[6] = "lowWarningSeverity";
|
||||||
names[7] = "highWarningSeverity";
|
names[7] = "highWarningSeverity";
|
||||||
names[8] = "highAlarmSeverity";
|
names[8] = "highAlarmSeverity";
|
||||||
names[9] = "hystersis";
|
names[9] = "hysteresis";
|
||||||
fields[0] = fieldCreate->createScalar(pvBoolean);
|
fields[0] = fieldCreate->createScalar(pvBoolean);
|
||||||
fields[1] = fieldCreate->createScalar(pvUShort);
|
fields[1] = fieldCreate->createScalar(pvUShort);
|
||||||
fields[2] = fieldCreate->createScalar(pvUShort);
|
fields[2] = fieldCreate->createScalar(pvUShort);
|
||||||
@@ -390,7 +390,7 @@ void StandardField::createUIntAlarm() {
|
|||||||
names[6] = "lowWarningSeverity";
|
names[6] = "lowWarningSeverity";
|
||||||
names[7] = "highWarningSeverity";
|
names[7] = "highWarningSeverity";
|
||||||
names[8] = "highAlarmSeverity";
|
names[8] = "highAlarmSeverity";
|
||||||
names[9] = "hystersis";
|
names[9] = "hysteresis";
|
||||||
fields[0] = fieldCreate->createScalar(pvBoolean);
|
fields[0] = fieldCreate->createScalar(pvBoolean);
|
||||||
fields[1] = fieldCreate->createScalar(pvUInt);
|
fields[1] = fieldCreate->createScalar(pvUInt);
|
||||||
fields[2] = fieldCreate->createScalar(pvUInt);
|
fields[2] = fieldCreate->createScalar(pvUInt);
|
||||||
@@ -417,7 +417,7 @@ void StandardField::createULongAlarm() {
|
|||||||
names[6] = "lowWarningSeverity";
|
names[6] = "lowWarningSeverity";
|
||||||
names[7] = "highWarningSeverity";
|
names[7] = "highWarningSeverity";
|
||||||
names[8] = "highAlarmSeverity";
|
names[8] = "highAlarmSeverity";
|
||||||
names[9] = "hystersis";
|
names[9] = "hysteresis";
|
||||||
fields[0] = fieldCreate->createScalar(pvBoolean);
|
fields[0] = fieldCreate->createScalar(pvBoolean);
|
||||||
fields[1] = fieldCreate->createScalar(pvULong);
|
fields[1] = fieldCreate->createScalar(pvULong);
|
||||||
fields[2] = fieldCreate->createScalar(pvULong);
|
fields[2] = fieldCreate->createScalar(pvULong);
|
||||||
@@ -444,7 +444,7 @@ void StandardField::createFloatAlarm() {
|
|||||||
names[6] = "lowWarningSeverity";
|
names[6] = "lowWarningSeverity";
|
||||||
names[7] = "highWarningSeverity";
|
names[7] = "highWarningSeverity";
|
||||||
names[8] = "highAlarmSeverity";
|
names[8] = "highAlarmSeverity";
|
||||||
names[9] = "hystersis";
|
names[9] = "hysteresis";
|
||||||
fields[0] = fieldCreate->createScalar(pvBoolean);
|
fields[0] = fieldCreate->createScalar(pvBoolean);
|
||||||
fields[1] = fieldCreate->createScalar(pvFloat);
|
fields[1] = fieldCreate->createScalar(pvFloat);
|
||||||
fields[2] = fieldCreate->createScalar(pvFloat);
|
fields[2] = fieldCreate->createScalar(pvFloat);
|
||||||
@@ -471,7 +471,7 @@ void StandardField::createDoubleAlarm() {
|
|||||||
names[6] = "lowWarningSeverity";
|
names[6] = "lowWarningSeverity";
|
||||||
names[7] = "highWarningSeverity";
|
names[7] = "highWarningSeverity";
|
||||||
names[8] = "highAlarmSeverity";
|
names[8] = "highAlarmSeverity";
|
||||||
names[9] = "hystersis";
|
names[9] = "hysteresis";
|
||||||
fields[0] = fieldCreate->createScalar(pvBoolean);
|
fields[0] = fieldCreate->createScalar(pvBoolean);
|
||||||
fields[1] = fieldCreate->createScalar(pvDouble);
|
fields[1] = fieldCreate->createScalar(pvDouble);
|
||||||
fields[2] = fieldCreate->createScalar(pvDouble);
|
fields[2] = fieldCreate->createScalar(pvDouble);
|
||||||
@@ -503,28 +503,28 @@ StructureConstPtr StandardField::scalar(
|
|||||||
ScalarType type,string const &properties)
|
ScalarType type,string const &properties)
|
||||||
{
|
{
|
||||||
ScalarConstPtr field = fieldCreate->createScalar(type); // scalar_t
|
ScalarConstPtr field = fieldCreate->createScalar(type); // scalar_t
|
||||||
return createProperties("uri:ev4:nt/2012/pwd:NTScalar",field,properties);
|
return createProperties("epics:nt/NTScalar:1.0",field,properties);
|
||||||
}
|
}
|
||||||
|
|
||||||
StructureConstPtr StandardField::regUnion(
|
StructureConstPtr StandardField::regUnion(
|
||||||
UnionConstPtr const &field,
|
UnionConstPtr const &field,
|
||||||
string const & properties)
|
string const & properties)
|
||||||
{
|
{
|
||||||
return createProperties("uri:ev4:nt/2012/pwd:NTUnion",field,properties);
|
return createProperties("epics:nt/NTUnion:1.0",field,properties);
|
||||||
}
|
}
|
||||||
|
|
||||||
StructureConstPtr StandardField::variantUnion(
|
StructureConstPtr StandardField::variantUnion(
|
||||||
string const & properties)
|
string const & properties)
|
||||||
{
|
{
|
||||||
UnionConstPtr field = fieldCreate->createVariantUnion();
|
UnionConstPtr field = fieldCreate->createVariantUnion();
|
||||||
return createProperties("uri:ev4:nt/2012/pwd:NTUnion",field,properties);
|
return createProperties("epics:nt/NTUnion:1.0",field,properties);
|
||||||
}
|
}
|
||||||
|
|
||||||
StructureConstPtr StandardField::scalarArray(
|
StructureConstPtr StandardField::scalarArray(
|
||||||
ScalarType elementType, string const &properties)
|
ScalarType elementType, string const &properties)
|
||||||
{
|
{
|
||||||
ScalarArrayConstPtr field = fieldCreate->createScalarArray(elementType); // scalar_t[]
|
ScalarArrayConstPtr field = fieldCreate->createScalarArray(elementType); // scalar_t[]
|
||||||
return createProperties("uri:ev4:nt/2012/pwd:NTScalarArray",field,properties);
|
return createProperties("epics:nt/NTScalarArray:1.0",field,properties);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -533,7 +533,7 @@ StructureConstPtr StandardField::structureArray(
|
|||||||
{
|
{
|
||||||
StructureArrayConstPtr field = fieldCreate->createStructureArray(
|
StructureArrayConstPtr field = fieldCreate->createStructureArray(
|
||||||
structure);
|
structure);
|
||||||
return createProperties("uri:ev4:nt/2012/pwd:NTStructureArray",field,properties);
|
return createProperties("epics:nt/NTStructureArray:1.0",field,properties);
|
||||||
}
|
}
|
||||||
|
|
||||||
StructureConstPtr StandardField::unionArray(
|
StructureConstPtr StandardField::unionArray(
|
||||||
@@ -541,7 +541,7 @@ StructureConstPtr StandardField::unionArray(
|
|||||||
{
|
{
|
||||||
UnionArrayConstPtr field = fieldCreate->createUnionArray(
|
UnionArrayConstPtr field = fieldCreate->createUnionArray(
|
||||||
punion);
|
punion);
|
||||||
return createProperties("uri:ev4:nt/2012/pwd:NTUnionArray",field,properties);
|
return createProperties("epics:nt/NTUnionArray:1.0",field,properties);
|
||||||
}
|
}
|
||||||
|
|
||||||
StructureConstPtr StandardField::enumerated()
|
StructureConstPtr StandardField::enumerated()
|
||||||
@@ -560,7 +560,7 @@ StructureConstPtr StandardField::enumerated()
|
|||||||
StructureConstPtr StandardField::enumerated(string const &properties)
|
StructureConstPtr StandardField::enumerated(string const &properties)
|
||||||
{
|
{
|
||||||
StructureConstPtr field = enumerated(); // enum_t
|
StructureConstPtr field = enumerated(); // enum_t
|
||||||
return createProperties("uri:ev4:nt/2012/pwd:NTEnum",field,properties);
|
return createProperties("epics:nt/NTEnum:1.0",field,properties);
|
||||||
}
|
}
|
||||||
|
|
||||||
StructureConstPtr StandardField::alarm()
|
StructureConstPtr StandardField::alarm()
|
||||||
|
|||||||
@@ -26,7 +26,14 @@ namespace epics { namespace pvData {
|
|||||||
|
|
||||||
namespace format
|
namespace format
|
||||||
{
|
{
|
||||||
std::ostream& operator<<(std::ostream& os, indent_level const& indent)
|
static int indent_index = std::ios_base::xalloc();
|
||||||
|
|
||||||
|
long& indent_value(std::ios_base& ios)
|
||||||
|
{
|
||||||
|
return ios.iword(indent_index);
|
||||||
|
}
|
||||||
|
|
||||||
|
std::ostream& operator<<(std::ostream& os, indent_level const& indent)
|
||||||
{
|
{
|
||||||
indent_value(os) = indent.level;
|
indent_value(os) = indent.level;
|
||||||
return os;
|
return os;
|
||||||
|
|||||||
@@ -54,14 +54,14 @@ void Executor::run()
|
|||||||
{
|
{
|
||||||
Lock xx(mutex);
|
Lock xx(mutex);
|
||||||
while(true) {
|
while(true) {
|
||||||
while(head.get()==NULL) {
|
while(!head.get()) {
|
||||||
xx.unlock();
|
xx.unlock();
|
||||||
moreWork.wait();
|
moreWork.wait();
|
||||||
xx.lock();
|
xx.lock();
|
||||||
}
|
}
|
||||||
CommandPtr command = head;
|
CommandPtr command = head;
|
||||||
head = command->next;
|
head = command->next;
|
||||||
if(command.get()==NULL) continue;
|
if(!command.get()) continue;
|
||||||
if(command.get()==shutdown.get()) break;
|
if(command.get()==shutdown.get()) break;
|
||||||
xx.unlock();
|
xx.unlock();
|
||||||
try {
|
try {
|
||||||
@@ -82,13 +82,13 @@ void Executor::execute(CommandPtr const & command)
|
|||||||
{
|
{
|
||||||
Lock xx(mutex);
|
Lock xx(mutex);
|
||||||
command->next.reset();
|
command->next.reset();
|
||||||
if(head.get()==NULL) {
|
if(!head.get()) {
|
||||||
head = command;
|
head = command;
|
||||||
moreWork.signal();
|
moreWork.signal();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
CommandPtr tail = head;
|
CommandPtr tail = head;
|
||||||
while(tail->next!=NULL) tail = tail->next;
|
while(tail->next) tail = tail->next;
|
||||||
tail->next = command;
|
tail->next = command;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -17,7 +17,7 @@
|
|||||||
using std::string;
|
using std::string;
|
||||||
|
|
||||||
// need to use "long long" when sizeof(int)==sizeof(long)
|
// need to use "long long" when sizeof(int)==sizeof(long)
|
||||||
#if (ULONG_MAX == 0xfffffffful) || defined(_WIN32) || defined(__rtems__)
|
#if (ULONG_MAX == 0xfffffffful) || defined(_WIN32) || defined(__rtems__) || defined(__APPLE__)
|
||||||
#define NEED_LONGLONG
|
#define NEED_LONGLONG
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@@ -27,7 +27,7 @@ using std::string;
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if EPICS_VERSION_INT < VERSION_INT(3,15,0,1)
|
#if EPICS_VERSION_INT < VERSION_INT(3,15,0,1)
|
||||||
/* integer conversion primatives added to epicsStdlib.c in 3.15.0.1 */
|
/* integer conversion primitives added to epicsStdlib.c in 3.15.0.1 */
|
||||||
|
|
||||||
#define S_stdlib_noConversion 1 /* No digits to convert */
|
#define S_stdlib_noConversion 1 /* No digits to convert */
|
||||||
#define S_stdlib_extraneous 2 /* Extraneous characters */
|
#define S_stdlib_extraneous 2 /* Extraneous characters */
|
||||||
@@ -249,7 +249,18 @@ epicsParseFloat(const char *str, float *to, char **units)
|
|||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if defined(NEED_LONGLONG) && (defined(__vxworks) || defined (_WIN32))
|
// MS Visual Studio 2013 defines strtoll, etc.
|
||||||
|
#if defined(_WIN32)
|
||||||
|
# if (_MSC_VER >= 1800)
|
||||||
|
# define WIN_NEEDS_OLL_FUNC 0
|
||||||
|
# else
|
||||||
|
# define WIN_NEEDS_OLL_FUNC 1
|
||||||
|
# endif
|
||||||
|
#else
|
||||||
|
# define WIN_NEEDS_OLL_FUNC 0
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if defined(NEED_LONGLONG) && (defined(__vxworks) || WIN_NEEDS_OLL_FUNC)
|
||||||
static
|
static
|
||||||
long long strtoll(const char *ptr, char ** endp, int base)
|
long long strtoll(const char *ptr, char ** endp, int base)
|
||||||
{
|
{
|
||||||
@@ -297,6 +308,71 @@ noconvert:
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#if defined(__vxworks)
|
||||||
|
/* vxworks version of std::istringstream >>uint64_t is buggy, we use out own implementation */
|
||||||
|
static
|
||||||
|
unsigned long long strtoull(const char *nptr, char **endptr, int base)
|
||||||
|
{
|
||||||
|
const char *s = nptr;
|
||||||
|
unsigned long long acc;
|
||||||
|
int c;
|
||||||
|
unsigned long long cutoff;
|
||||||
|
int neg = 0, any, cutlim;
|
||||||
|
|
||||||
|
do
|
||||||
|
c = *s++;
|
||||||
|
while (isspace(c));
|
||||||
|
if (c == '-')
|
||||||
|
{
|
||||||
|
neg = 1;
|
||||||
|
c = *s++;
|
||||||
|
}
|
||||||
|
else if (c == '+')
|
||||||
|
c = *s++;
|
||||||
|
if ((base == 0 || base == 16) &&
|
||||||
|
c == '0' && (*s == 'x' || *s == 'X'))
|
||||||
|
{
|
||||||
|
c = s[1];
|
||||||
|
s += 2;
|
||||||
|
base = 16;
|
||||||
|
}
|
||||||
|
if (base == 0)
|
||||||
|
base = c == '0' ? 8 : 10;
|
||||||
|
|
||||||
|
cutoff = (unsigned long long) UINT64_MAX / (unsigned long long) base;
|
||||||
|
cutlim = (unsigned long long) UINT64_MAX % (unsigned long long) base;
|
||||||
|
|
||||||
|
for (acc = 0, any = 0;; c = *s++)
|
||||||
|
{
|
||||||
|
if (isdigit(c))
|
||||||
|
c -= '0';
|
||||||
|
else if (isalpha(c))
|
||||||
|
c -= isupper(c) ? 'A' - 10 : 'a' - 10;
|
||||||
|
else
|
||||||
|
break;
|
||||||
|
if (c >= base)
|
||||||
|
break;
|
||||||
|
if (any < 0 || acc > cutoff || (acc == cutoff && c > cutlim))
|
||||||
|
any = -1;
|
||||||
|
else
|
||||||
|
{
|
||||||
|
any = 1;
|
||||||
|
acc *= base;
|
||||||
|
acc += c;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (any < 0)
|
||||||
|
{
|
||||||
|
acc = UINT64_MAX;
|
||||||
|
errno = ERANGE;
|
||||||
|
}
|
||||||
|
else if (neg)
|
||||||
|
acc = -acc;
|
||||||
|
if (endptr != 0)
|
||||||
|
*endptr = any ? (char *) s - 1 : (char *) nptr;
|
||||||
|
return (acc);
|
||||||
|
}
|
||||||
|
#else
|
||||||
static
|
static
|
||||||
unsigned long long strtoull(const char *ptr, char ** endp, int base)
|
unsigned long long strtoull(const char *ptr, char ** endp, int base)
|
||||||
{
|
{
|
||||||
@@ -339,7 +415,7 @@ noconvert:
|
|||||||
*endp = (char*)ptr;
|
*endp = (char*)ptr;
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/* do we need long long? */
|
/* do we need long long? */
|
||||||
@@ -475,6 +551,26 @@ void parseToPOD(const string& in, float *out) {
|
|||||||
void parseToPOD(const string& in, double *out) {
|
void parseToPOD(const string& in, double *out) {
|
||||||
int err = epicsParseDouble(in.c_str(), out, NULL);
|
int err = epicsParseDouble(in.c_str(), out, NULL);
|
||||||
if(err) handleParseError(err);
|
if(err) handleParseError(err);
|
||||||
|
#if defined(__vxworks)
|
||||||
|
/* vxWorks strtod returns [-]epicsINF when it should return ERANGE error
|
||||||
|
* if [-]epicsINF is returned and first char is a digit then translate this into ERANGE error
|
||||||
|
*/
|
||||||
|
else if (*out == epicsINF || *out == -epicsINF) {
|
||||||
|
const char* s = in.c_str();
|
||||||
|
int c;
|
||||||
|
|
||||||
|
/* skip spaces and the sign */
|
||||||
|
do {
|
||||||
|
c = *s++;
|
||||||
|
} while (isspace(c));
|
||||||
|
|
||||||
|
if (c == '-' || c == '+')
|
||||||
|
c = *s++;
|
||||||
|
|
||||||
|
if (isdigit(c))
|
||||||
|
handleParseError(S_stdlib_overflow);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
}}}
|
}}}
|
||||||
|
|||||||
@@ -65,9 +65,10 @@ namespace epics { namespace pvData {
|
|||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
class epicsShareClass SerializableArray : virtual public Serializable {
|
class epicsShareClass SerializableArray : public virtual Serializable {
|
||||||
public:
|
public:
|
||||||
virtual ~SerializableArray(){}
|
virtual ~SerializableArray(){}
|
||||||
|
using Serializable::serialize;
|
||||||
virtual void serialize(ByteBuffer *buffer,
|
virtual void serialize(ByteBuffer *buffer,
|
||||||
SerializableControl *flusher, std::size_t offset, std::size_t count) const = 0;
|
SerializableControl *flusher, std::size_t offset, std::size_t count) const = 0;
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -44,6 +44,25 @@
|
|||||||
# undef SHARED_FROM_TR1
|
# undef SHARED_FROM_TR1
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#if defined(__clang__)
|
||||||
|
# undef SHARED_FROM_BOOST
|
||||||
|
# undef SHARED_FROM_TR1
|
||||||
|
|
||||||
|
#include <memory>
|
||||||
|
|
||||||
|
// import std classes into std::tr1
|
||||||
|
namespace std {
|
||||||
|
namespace tr1 {
|
||||||
|
using std::shared_ptr;
|
||||||
|
using std::weak_ptr;
|
||||||
|
using std::static_pointer_cast;
|
||||||
|
using std::dynamic_pointer_cast;
|
||||||
|
using std::const_pointer_cast;
|
||||||
|
using std::enable_shared_from_this;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
// go and get it
|
// go and get it
|
||||||
|
|
||||||
#if defined(SHARED_FROM_TR1)
|
#if defined(SHARED_FROM_TR1)
|
||||||
|
|||||||
@@ -23,7 +23,7 @@ MonitorPluginManagerPtr MonitorPluginManager::get()
|
|||||||
static MonitorPluginManagerPtr pluginManager;
|
static MonitorPluginManagerPtr pluginManager;
|
||||||
static Mutex mutex;
|
static Mutex mutex;
|
||||||
Lock xx(mutex);
|
Lock xx(mutex);
|
||||||
if(pluginManager==NULL) {
|
if(!pluginManager) {
|
||||||
pluginManager = MonitorPluginManagerPtr(new MonitorPluginManager());
|
pluginManager = MonitorPluginManagerPtr(new MonitorPluginManager());
|
||||||
}
|
}
|
||||||
return pluginManager;
|
return pluginManager;
|
||||||
|
|||||||
@@ -16,7 +16,7 @@ namespace epics { namespace pvData {
|
|||||||
|
|
||||||
class epicsShareClass Control {
|
class epicsShareClass Control {
|
||||||
public:
|
public:
|
||||||
Control() : low(0.0), high(0.0) {}
|
Control() : low(0.0), high(0.0), minStep(0.0) {}
|
||||||
//default constructors and destructor are OK
|
//default constructors and destructor are OK
|
||||||
double getLow() const {return low;}
|
double getLow() const {return low;}
|
||||||
double getHigh() const {return high;}
|
double getHigh() const {return high;}
|
||||||
|
|||||||
@@ -30,11 +30,17 @@ bool PVControl::attach(PVFieldPtr const & pvField)
|
|||||||
PVStructurePtr pvStructure = static_pointer_cast<PVStructure>(pvField);
|
PVStructurePtr pvStructure = static_pointer_cast<PVStructure>(pvField);
|
||||||
pvLow = pvStructure->getDoubleField("limitLow");
|
pvLow = pvStructure->getDoubleField("limitLow");
|
||||||
if(pvLow.get()==NULL) return false;
|
if(pvLow.get()==NULL) return false;
|
||||||
pvHigh = pvStructure->getDoubleField(string("limitHigh"));
|
pvHigh = pvStructure->getDoubleField("limitHigh");
|
||||||
if(pvHigh.get()==NULL) {
|
if(pvHigh.get()==NULL) {
|
||||||
pvLow.reset();
|
pvLow.reset();
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
pvMinStep = pvStructure->getDoubleField("minStep");
|
||||||
|
if(pvMinStep.get()==NULL) {
|
||||||
|
pvLow.reset();
|
||||||
|
pvHigh.reset();
|
||||||
|
return false;
|
||||||
|
}
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -56,6 +62,7 @@ void PVControl::get(Control &control) const
|
|||||||
}
|
}
|
||||||
control.setLow(pvLow->get());
|
control.setLow(pvLow->get());
|
||||||
control.setHigh(pvHigh->get());
|
control.setHigh(pvHigh->get());
|
||||||
|
control.setMinStep(pvMinStep->get());
|
||||||
}
|
}
|
||||||
|
|
||||||
bool PVControl::set(Control const & control)
|
bool PVControl::set(Control const & control)
|
||||||
@@ -63,9 +70,10 @@ bool PVControl::set(Control const & control)
|
|||||||
if(pvLow.get()==NULL) {
|
if(pvLow.get()==NULL) {
|
||||||
throw std::logic_error(notAttached);
|
throw std::logic_error(notAttached);
|
||||||
}
|
}
|
||||||
if(pvLow->isImmutable() || pvHigh->isImmutable()) return false;
|
if(pvLow->isImmutable() || pvHigh->isImmutable() || pvMinStep->isImmutable()) return false;
|
||||||
pvLow->put(control.getLow());
|
pvLow->put(control.getLow());
|
||||||
pvHigh->put(control.getHigh());
|
pvHigh->put(control.getHigh());
|
||||||
|
pvMinStep->put(control.getMinStep());
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -33,6 +33,7 @@ public:
|
|||||||
private:
|
private:
|
||||||
PVDoublePtr pvLow;
|
PVDoublePtr pvLow;
|
||||||
PVDoublePtr pvHigh;
|
PVDoublePtr pvHigh;
|
||||||
|
PVDoublePtr pvMinStep;
|
||||||
static std::string noControlFound;
|
static std::string noControlFound;
|
||||||
static std::string notAttached;
|
static std::string notAttached;
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -33,7 +33,7 @@ bool PVTimeStamp::attach(PVFieldPtr const & pvField)
|
|||||||
PVLongPtr pvLong = pvStructure->getLongField("secondsPastEpoch");
|
PVLongPtr pvLong = pvStructure->getLongField("secondsPastEpoch");
|
||||||
if(pvLong.get()!=NULL) {
|
if(pvLong.get()!=NULL) {
|
||||||
pvSecs = pvLong;
|
pvSecs = pvLong;
|
||||||
pvNano = pvStructure->getIntField("nanoSeconds");
|
pvNano = pvStructure->getIntField("nanoseconds");
|
||||||
pvUserTag = pvStructure->getIntField("userTag");
|
pvUserTag = pvStructure->getIntField("userTag");
|
||||||
}
|
}
|
||||||
if(pvSecs.get()!=NULL
|
if(pvSecs.get()!=NULL
|
||||||
@@ -76,7 +76,7 @@ bool PVTimeStamp::set(TimeStamp const & timeStamp)
|
|||||||
if(pvSecs->isImmutable() || pvNano->isImmutable()) return false;
|
if(pvSecs->isImmutable() || pvNano->isImmutable()) return false;
|
||||||
pvSecs->put(timeStamp.getSecondsPastEpoch());
|
pvSecs->put(timeStamp.getSecondsPastEpoch());
|
||||||
pvUserTag->put(timeStamp.getUserTag());
|
pvUserTag->put(timeStamp.getUserTag());
|
||||||
pvNano->put(timeStamp.getNanoSeconds());
|
pvNano->put(timeStamp.getNanoseconds());
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -27,21 +27,21 @@ int32 microSecPerSec = milliSecPerSec*milliSecPerSec;
|
|||||||
int32 nanoSecPerSec = milliSecPerSec*microSecPerSec;
|
int32 nanoSecPerSec = milliSecPerSec*microSecPerSec;
|
||||||
int64 posixEpochAtEpicsEpoch = POSIX_TIME_AT_EPICS_EPOCH;
|
int64 posixEpochAtEpicsEpoch = POSIX_TIME_AT_EPICS_EPOCH;
|
||||||
|
|
||||||
TimeStamp::TimeStamp(int64 secondsPastEpoch,int32 nanoSeconds,int32 userTag)
|
TimeStamp::TimeStamp(int64 secondsPastEpoch,int32 nanoseconds,int32 userTag)
|
||||||
: secondsPastEpoch(secondsPastEpoch),nanoSeconds(nanoSeconds),userTag(userTag)
|
: secondsPastEpoch(secondsPastEpoch),nanoseconds(nanoseconds),userTag(userTag)
|
||||||
{
|
{
|
||||||
normalize();
|
normalize();
|
||||||
}
|
}
|
||||||
|
|
||||||
void TimeStamp::normalize()
|
void TimeStamp::normalize()
|
||||||
{
|
{
|
||||||
if(nanoSeconds>=0 && nanoSeconds<nanoSecPerSec) return;
|
if(nanoseconds>=0 && nanoseconds<nanoSecPerSec) return;
|
||||||
while(nanoSeconds>=nanoSecPerSec) {
|
while(nanoseconds>=nanoSecPerSec) {
|
||||||
nanoSeconds -= nanoSecPerSec;
|
nanoseconds -= nanoSecPerSec;
|
||||||
secondsPastEpoch++;
|
secondsPastEpoch++;
|
||||||
}
|
}
|
||||||
while(nanoSeconds<0) {
|
while(nanoseconds<0) {
|
||||||
nanoSeconds += nanoSecPerSec;
|
nanoseconds += nanoSecPerSec;
|
||||||
secondsPastEpoch--;
|
secondsPastEpoch--;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -51,21 +51,21 @@ void TimeStamp::fromTime_t(const time_t & tt)
|
|||||||
epicsTimeStamp epicsTime;
|
epicsTimeStamp epicsTime;
|
||||||
epicsTimeFromTime_t(&epicsTime,tt);
|
epicsTimeFromTime_t(&epicsTime,tt);
|
||||||
secondsPastEpoch = epicsTime.secPastEpoch + posixEpochAtEpicsEpoch;
|
secondsPastEpoch = epicsTime.secPastEpoch + posixEpochAtEpicsEpoch;
|
||||||
nanoSeconds = epicsTime.nsec;
|
nanoseconds = epicsTime.nsec;
|
||||||
}
|
}
|
||||||
|
|
||||||
void TimeStamp::toTime_t(time_t &tt) const
|
void TimeStamp::toTime_t(time_t &tt) const
|
||||||
{
|
{
|
||||||
epicsTimeStamp epicsTime;
|
epicsTimeStamp epicsTime;
|
||||||
epicsTime.secPastEpoch = static_cast<epicsUInt32>(secondsPastEpoch-posixEpochAtEpicsEpoch);
|
epicsTime.secPastEpoch = static_cast<epicsUInt32>(secondsPastEpoch-posixEpochAtEpicsEpoch);
|
||||||
epicsTime.nsec = nanoSeconds;
|
epicsTime.nsec = nanoseconds;
|
||||||
epicsTimeToTime_t(&tt,&epicsTime);
|
epicsTimeToTime_t(&tt,&epicsTime);
|
||||||
}
|
}
|
||||||
|
|
||||||
void TimeStamp::put(int64 milliseconds)
|
void TimeStamp::put(int64 milliseconds)
|
||||||
{
|
{
|
||||||
secondsPastEpoch = milliseconds/1000;
|
secondsPastEpoch = milliseconds/1000;
|
||||||
nanoSeconds = (milliseconds%1000)*1000000;
|
nanoseconds = (milliseconds%1000)*1000000;
|
||||||
}
|
}
|
||||||
|
|
||||||
void TimeStamp::getCurrent()
|
void TimeStamp::getCurrent()
|
||||||
@@ -74,13 +74,13 @@ void TimeStamp::getCurrent()
|
|||||||
epicsTimeGetCurrent(&epicsTime);
|
epicsTimeGetCurrent(&epicsTime);
|
||||||
secondsPastEpoch = epicsTime.secPastEpoch;
|
secondsPastEpoch = epicsTime.secPastEpoch;
|
||||||
secondsPastEpoch += posixEpochAtEpicsEpoch;
|
secondsPastEpoch += posixEpochAtEpicsEpoch;
|
||||||
nanoSeconds = epicsTime.nsec;
|
nanoseconds = epicsTime.nsec;
|
||||||
}
|
}
|
||||||
|
|
||||||
double TimeStamp::toSeconds() const
|
double TimeStamp::toSeconds() const
|
||||||
{
|
{
|
||||||
double value = static_cast<double>(secondsPastEpoch);
|
double value = static_cast<double>(secondsPastEpoch);
|
||||||
double nano = nanoSeconds;
|
double nano = nanoseconds;
|
||||||
value += nano/1e9;
|
value += nano/1e9;
|
||||||
return value;
|
return value;
|
||||||
}
|
}
|
||||||
@@ -88,9 +88,9 @@ double TimeStamp::toSeconds() const
|
|||||||
int64 TimeStamp::diffInt(TimeStamp const & left,TimeStamp const&right )
|
int64 TimeStamp::diffInt(TimeStamp const & left,TimeStamp const&right )
|
||||||
{
|
{
|
||||||
int64 sl = left.secondsPastEpoch;
|
int64 sl = left.secondsPastEpoch;
|
||||||
int32 nl = left.nanoSeconds;
|
int32 nl = left.nanoseconds;
|
||||||
int64 sr = right.secondsPastEpoch;
|
int64 sr = right.secondsPastEpoch;
|
||||||
int32 nr = right.nanoSeconds;
|
int32 nr = right.nanoseconds;
|
||||||
int64 sdiff = sl - sr;
|
int64 sdiff = sl - sr;
|
||||||
sdiff *= nanoSecPerSec;
|
sdiff *= nanoSecPerSec;
|
||||||
sdiff += nl - nr;
|
sdiff += nl - nr;
|
||||||
@@ -142,7 +142,7 @@ bool TimeStamp::operator>(TimeStamp const &right) const
|
|||||||
double TimeStamp::diff(TimeStamp const & a,TimeStamp const & b)
|
double TimeStamp::diff(TimeStamp const & a,TimeStamp const & b)
|
||||||
{
|
{
|
||||||
double result = static_cast<double>(a.secondsPastEpoch - b.secondsPastEpoch);
|
double result = static_cast<double>(a.secondsPastEpoch - b.secondsPastEpoch);
|
||||||
result += (a.nanoSeconds - b.nanoSeconds)/1e9;
|
result += (a.nanoseconds - b.nanoseconds)/1e9;
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -163,12 +163,12 @@ TimeStamp & TimeStamp::operator+=(double seconds)
|
|||||||
{
|
{
|
||||||
int64 secs = static_cast<int64>(seconds);
|
int64 secs = static_cast<int64>(seconds);
|
||||||
int64 nano = static_cast<int64>((seconds - secs)*1e9);
|
int64 nano = static_cast<int64>((seconds - secs)*1e9);
|
||||||
nanoSeconds += static_cast<int32>(nano);
|
nanoseconds += static_cast<int32>(nano);
|
||||||
if(nanoSeconds>nanoSecPerSec) {
|
if(nanoseconds>nanoSecPerSec) {
|
||||||
nanoSeconds -= nanoSecPerSec;
|
nanoseconds -= nanoSecPerSec;
|
||||||
secondsPastEpoch += 1;
|
secondsPastEpoch += 1;
|
||||||
} else if(nanoSeconds<-nanoSecPerSec) {
|
} else if(nanoseconds<-nanoSecPerSec) {
|
||||||
nanoSeconds += -nanoSecPerSec;
|
nanoseconds += -nanoSecPerSec;
|
||||||
secondsPastEpoch -= 1;
|
secondsPastEpoch -= 1;
|
||||||
}
|
}
|
||||||
secondsPastEpoch += secs;
|
secondsPastEpoch += secs;
|
||||||
@@ -182,7 +182,7 @@ TimeStamp & TimeStamp::operator-=(double seconds)
|
|||||||
|
|
||||||
int64 TimeStamp::getMilliseconds()
|
int64 TimeStamp::getMilliseconds()
|
||||||
{
|
{
|
||||||
return secondsPastEpoch*1000 + nanoSeconds/1000000;
|
return secondsPastEpoch*1000 + nanoseconds/1000000;
|
||||||
}
|
}
|
||||||
|
|
||||||
}}
|
}}
|
||||||
|
|||||||
@@ -38,8 +38,8 @@ epicsShareExtern int64 posixEpochAtEpicsEpoch;
|
|||||||
class epicsShareClass TimeStamp {
|
class epicsShareClass TimeStamp {
|
||||||
public:
|
public:
|
||||||
TimeStamp()
|
TimeStamp()
|
||||||
:secondsPastEpoch(0), nanoSeconds(0), userTag(0) {}
|
:secondsPastEpoch(0), nanoseconds(0), userTag(0) {}
|
||||||
TimeStamp(int64 secondsPastEpoch,int32 nanoSeconds = 0,int32 userTag = 0);
|
TimeStamp(int64 secondsPastEpoch,int32 nanoseconds = 0,int32 userTag = 0);
|
||||||
//default constructors and destructor are OK
|
//default constructors and destructor are OK
|
||||||
//This class should not be extended
|
//This class should not be extended
|
||||||
void normalize();
|
void normalize();
|
||||||
@@ -49,12 +49,12 @@ public:
|
|||||||
int64 getEpicsSecondsPastEpoch() const {
|
int64 getEpicsSecondsPastEpoch() const {
|
||||||
return secondsPastEpoch - posixEpochAtEpicsEpoch;
|
return secondsPastEpoch - posixEpochAtEpicsEpoch;
|
||||||
}
|
}
|
||||||
int32 getNanoSeconds() const {return nanoSeconds;}
|
int32 getNanoseconds() const {return nanoseconds;}
|
||||||
int32 getUserTag() const {return userTag;}
|
int32 getUserTag() const {return userTag;}
|
||||||
void setUserTag(int userTag) {this->userTag = userTag;}
|
void setUserTag(int userTag) {this->userTag = userTag;}
|
||||||
void put(int64 secondsPastEpoch,int32 nanoSeconds = 0) {
|
void put(int64 secondsPastEpoch,int32 nanoseconds = 0) {
|
||||||
this->secondsPastEpoch = secondsPastEpoch;
|
this->secondsPastEpoch = secondsPastEpoch;
|
||||||
this->nanoSeconds = nanoSeconds;
|
this->nanoseconds = nanoseconds;
|
||||||
normalize();
|
normalize();
|
||||||
}
|
}
|
||||||
void put(int64 milliseconds);
|
void put(int64 milliseconds);
|
||||||
@@ -75,7 +75,7 @@ public:
|
|||||||
private:
|
private:
|
||||||
static int64 diffInt(TimeStamp const &left,TimeStamp const &right );
|
static int64 diffInt(TimeStamp const &left,TimeStamp const &right );
|
||||||
int64 secondsPastEpoch;
|
int64 secondsPastEpoch;
|
||||||
int32 nanoSeconds;
|
int32 nanoseconds;
|
||||||
int32 userTag;
|
int32 userTag;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|||||||
@@ -35,6 +35,7 @@ bool epicsShareExtern operator==(const Structure&, const Structure&);
|
|||||||
bool epicsShareExtern operator==(const StructureArray&, const StructureArray&);
|
bool epicsShareExtern operator==(const StructureArray&, const StructureArray&);
|
||||||
bool epicsShareExtern operator==(const Union&, const Union&);
|
bool epicsShareExtern operator==(const Union&, const Union&);
|
||||||
bool epicsShareExtern operator==(const UnionArray&, const UnionArray&);
|
bool epicsShareExtern operator==(const UnionArray&, const UnionArray&);
|
||||||
|
bool epicsShareExtern operator==(const BoundedString&, const BoundedString&);
|
||||||
|
|
||||||
static inline bool operator!=(const Field& a, const Field& b)
|
static inline bool operator!=(const Field& a, const Field& b)
|
||||||
{return !(a==b);}
|
{return !(a==b);}
|
||||||
@@ -50,6 +51,8 @@ static inline bool operator!=(const Union& a, const Union& b)
|
|||||||
{return !(a==b);}
|
{return !(a==b);}
|
||||||
static inline bool operator!=(const UnionArray& a, const UnionArray& b)
|
static inline bool operator!=(const UnionArray& a, const UnionArray& b)
|
||||||
{return !(a==b);}
|
{return !(a==b);}
|
||||||
|
static inline bool operator!=(const BoundedString& a, const BoundedString& b)
|
||||||
|
{return !(a==b);}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -63,9 +66,7 @@ static inline bool operator!=(const UnionArray& a, const UnionArray& b)
|
|||||||
* pvUByte, pvUShort, pvUInt, pvULong,
|
* pvUByte, pvUShort, pvUInt, pvULong,
|
||||||
* pvFloat, or pvDouble.</p>
|
* pvFloat, or pvDouble.</p>
|
||||||
*
|
*
|
||||||
* <p>getString converts any supported type to a std::string.
|
* <p>getString converts any supported type to a std::string.</p>
|
||||||
* Code that implements a PVField interface should implement
|
|
||||||
* method toString by calling this method.</p>
|
|
||||||
*
|
*
|
||||||
* <p>fromString converts a std::string to a scalar.
|
* <p>fromString converts a std::string to a scalar.
|
||||||
* fromStringArray converts an array of std::strings
|
* fromStringArray converts an array of std::strings
|
||||||
@@ -478,7 +479,7 @@ public:
|
|||||||
inline void fromDouble(PVScalarPtr const & pv, double from) { pv->putFrom<double>(from); }
|
inline void fromDouble(PVScalarPtr const & pv, double from) { pv->putFrom<double>(from); }
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Convenience method for implementing toString.
|
* Convenience method for implementing dump.
|
||||||
* It generates a newline and inserts blanks at the beginning of the newline.
|
* It generates a newline and inserts blanks at the beginning of the newline.
|
||||||
* @param builder The std::string * being constructed.
|
* @param builder The std::string * being constructed.
|
||||||
* @param indentLevel Indent level, Each level is four spaces.
|
* @param indentLevel Indent level, Each level is four spaces.
|
||||||
|
|||||||
@@ -507,10 +507,12 @@ public:
|
|||||||
*/
|
*/
|
||||||
virtual void setCapacity(std::size_t capacity) = 0;
|
virtual void setCapacity(std::size_t capacity) = 0;
|
||||||
|
|
||||||
|
using PVField::dumpValue;
|
||||||
virtual std::ostream& dumpValue(std::ostream& o, std::size_t index) const = 0;
|
virtual std::ostream& dumpValue(std::ostream& o, std::size_t index) const = 0;
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
PVArray(FieldConstPtr const & field);
|
PVArray(FieldConstPtr const & field);
|
||||||
|
void checkLength(size_t length);
|
||||||
private:
|
private:
|
||||||
bool capacityMutable;
|
bool capacityMutable;
|
||||||
friend class PVDataCreate;
|
friend class PVDataCreate;
|
||||||
@@ -979,7 +981,6 @@ public:
|
|||||||
|
|
||||||
private:
|
private:
|
||||||
friend class PVDataCreate;
|
friend class PVDataCreate;
|
||||||
|
|
||||||
UnionConstPtr unionPtr;
|
UnionConstPtr unionPtr;
|
||||||
|
|
||||||
int32 selector;
|
int32 selector;
|
||||||
@@ -1195,6 +1196,7 @@ public:
|
|||||||
virtual const_svector view() const { return value; }
|
virtual const_svector view() const { return value; }
|
||||||
virtual void swap(const_svector &other);
|
virtual void swap(const_svector &other);
|
||||||
virtual void replace(const const_svector &other) {
|
virtual void replace(const const_svector &other) {
|
||||||
|
checkLength(other.size());
|
||||||
value = other;
|
value = other;
|
||||||
PVField::postPut();
|
PVField::postPut();
|
||||||
}
|
}
|
||||||
@@ -1290,6 +1292,7 @@ public:
|
|||||||
virtual const_svector view() const { return value; }
|
virtual const_svector view() const { return value; }
|
||||||
virtual void swap(const_svector &other);
|
virtual void swap(const_svector &other);
|
||||||
virtual void replace(const const_svector &other) {
|
virtual void replace(const const_svector &other) {
|
||||||
|
checkLength(other.size());
|
||||||
value = other;
|
value = other;
|
||||||
PVField::postPut();
|
PVField::postPut();
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -32,11 +32,7 @@ struct indent_level
|
|||||||
indent_level(long l) : level(l) {}
|
indent_level(long l) : level(l) {}
|
||||||
};
|
};
|
||||||
|
|
||||||
inline long& indent_value(std::ios_base& ios)
|
epicsShareExtern long& indent_value(std::ios_base& ios);
|
||||||
{
|
|
||||||
static int indent_index = std::ios_base::xalloc();
|
|
||||||
return ios.iword(indent_index);
|
|
||||||
}
|
|
||||||
|
|
||||||
epicsShareExtern std::ostream& operator<<(std::ostream& os, indent_level const& indent);
|
epicsShareExtern std::ostream& operator<<(std::ostream& os, indent_level const& indent);
|
||||||
|
|
||||||
@@ -93,6 +89,8 @@ class StructureArray;
|
|||||||
class Union;
|
class Union;
|
||||||
class UnionArray;
|
class UnionArray;
|
||||||
|
|
||||||
|
class BoundedString;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* typedef for a shared pointer to an immutable Field.
|
* typedef for a shared pointer to an immutable Field.
|
||||||
*/
|
*/
|
||||||
@@ -129,6 +127,10 @@ typedef std::tr1::shared_ptr<const Union> UnionConstPtr;
|
|||||||
* typedef for a shared pointer to an immutable UnionArray.
|
* typedef for a shared pointer to an immutable UnionArray.
|
||||||
*/
|
*/
|
||||||
typedef std::tr1::shared_ptr<const UnionArray> UnionArrayConstPtr;
|
typedef std::tr1::shared_ptr<const UnionArray> UnionArrayConstPtr;
|
||||||
|
/**
|
||||||
|
* typedef for a shared pointer to an immutable BoundedString.
|
||||||
|
*/
|
||||||
|
typedef std::tr1::shared_ptr<const BoundedString> BoundedStringConstPtr;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Definition of support field types.
|
* Definition of support field types.
|
||||||
@@ -360,9 +362,39 @@ public:
|
|||||||
protected:
|
protected:
|
||||||
Scalar(ScalarType scalarType);
|
Scalar(ScalarType scalarType);
|
||||||
private:
|
private:
|
||||||
int8 getTypeCodeLUT() const;
|
static int8 getTypeCodeLUT(ScalarType scalarType);
|
||||||
ScalarType scalarType;
|
ScalarType scalarType;
|
||||||
friend class FieldCreate;
|
friend class FieldCreate;
|
||||||
|
friend class ScalarArray;
|
||||||
|
friend class BoundedScalarArray;
|
||||||
|
friend class FixedScalarArray;
|
||||||
|
friend class BoundedString;
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This class implements introspection object for BoundedString.
|
||||||
|
*/
|
||||||
|
class epicsShareClass BoundedString : public Scalar{
|
||||||
|
public:
|
||||||
|
POINTER_DEFINITIONS(BoundedString);
|
||||||
|
/**
|
||||||
|
* Destructor.
|
||||||
|
*/
|
||||||
|
virtual ~BoundedString();
|
||||||
|
typedef BoundedString& reference;
|
||||||
|
typedef const BoundedString& const_reference;
|
||||||
|
|
||||||
|
virtual std::string getID() const;
|
||||||
|
|
||||||
|
virtual void serialize(ByteBuffer *buffer, SerializableControl *control) const;
|
||||||
|
|
||||||
|
std::size_t getMaximumLength() const;
|
||||||
|
|
||||||
|
protected:
|
||||||
|
BoundedString(std::size_t maxStringLength);
|
||||||
|
private:
|
||||||
|
std::size_t maxLength;
|
||||||
|
friend class FieldCreate;
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -378,13 +410,20 @@ public:
|
|||||||
typedef Array& reference;
|
typedef Array& reference;
|
||||||
typedef const Array& const_reference;
|
typedef const Array& const_reference;
|
||||||
|
|
||||||
/* fixed-size array support
|
enum ArraySizeType { variable, fixed, bounded };
|
||||||
// 0 not valid value, means undefined
|
|
||||||
std::size_t getMaximumCapacity() const;
|
/**
|
||||||
|
* Get array size type (i.e. variable/fixed/bounded size array).
|
||||||
|
* @return array size type enum.
|
||||||
|
*/
|
||||||
|
virtual ArraySizeType getArraySizeType() const = 0;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get maximum capacity of the array.
|
||||||
|
* @return maximum capacity of the array, 0 indicates variable size array.
|
||||||
|
*/
|
||||||
|
virtual std::size_t getMaximumCapacity() const = 0;
|
||||||
|
|
||||||
// 0 not valid value, means undefined
|
|
||||||
std::size_t getFixedLength() const;
|
|
||||||
*/
|
|
||||||
protected:
|
protected:
|
||||||
/**
|
/**
|
||||||
* Constructor
|
* Constructor
|
||||||
@@ -394,8 +433,14 @@ protected:
|
|||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* This class implements introspection object for field.
|
* This class implements introspection object for scalar array.
|
||||||
*/
|
*/
|
||||||
class epicsShareClass ScalarArray : public Array{
|
class epicsShareClass ScalarArray : public Array{
|
||||||
public:
|
public:
|
||||||
@@ -414,6 +459,10 @@ public:
|
|||||||
*/
|
*/
|
||||||
ScalarType getElementType() const {return elementType;}
|
ScalarType getElementType() const {return elementType;}
|
||||||
|
|
||||||
|
virtual ArraySizeType getArraySizeType() const {return Array::variable;}
|
||||||
|
|
||||||
|
virtual std::size_t getMaximumCapacity() const {return 0;}
|
||||||
|
|
||||||
virtual std::string getID() const;
|
virtual std::string getID() const;
|
||||||
|
|
||||||
virtual std::ostream& dump(std::ostream& o) const;
|
virtual std::ostream& dump(std::ostream& o) const;
|
||||||
@@ -427,12 +476,85 @@ protected:
|
|||||||
*/
|
*/
|
||||||
virtual ~ScalarArray();
|
virtual ~ScalarArray();
|
||||||
private:
|
private:
|
||||||
int8 getTypeCodeLUT() const;
|
|
||||||
const std::string getIDScalarArrayLUT() const;
|
const std::string getIDScalarArrayLUT() const;
|
||||||
ScalarType elementType;
|
ScalarType elementType;
|
||||||
friend class FieldCreate;
|
friend class FieldCreate;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This class implements introspection object for bounded scalar array.
|
||||||
|
*/
|
||||||
|
class epicsShareClass BoundedScalarArray : public ScalarArray{
|
||||||
|
public:
|
||||||
|
POINTER_DEFINITIONS(BoundedScalarArray);
|
||||||
|
typedef BoundedScalarArray& reference;
|
||||||
|
typedef const BoundedScalarArray& const_reference;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Constructor
|
||||||
|
* @param scalarType The scalarType for the field.
|
||||||
|
* @param size maximum (bound) capacity.
|
||||||
|
*/
|
||||||
|
BoundedScalarArray(ScalarType scalarType, std::size_t size);
|
||||||
|
|
||||||
|
virtual ArraySizeType getArraySizeType() const {return Array::bounded;}
|
||||||
|
|
||||||
|
virtual std::size_t getMaximumCapacity() const {return size;}
|
||||||
|
|
||||||
|
virtual std::string getID() const;
|
||||||
|
|
||||||
|
virtual void serialize(ByteBuffer *buffer, SerializableControl *control) const;
|
||||||
|
|
||||||
|
protected:
|
||||||
|
/**
|
||||||
|
* Destructor.
|
||||||
|
*/
|
||||||
|
virtual ~BoundedScalarArray();
|
||||||
|
private:
|
||||||
|
std::size_t size;
|
||||||
|
friend class FieldCreate;
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This class implements introspection object for bounded scalar array.
|
||||||
|
*/
|
||||||
|
class epicsShareClass FixedScalarArray : public ScalarArray{
|
||||||
|
public:
|
||||||
|
POINTER_DEFINITIONS(FixedScalarArray);
|
||||||
|
typedef FixedScalarArray& reference;
|
||||||
|
typedef const FixedScalarArray& const_reference;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Constructor
|
||||||
|
* @param scalarType The scalarType for the field.
|
||||||
|
* @param size maximum (bound) capacity.
|
||||||
|
*/
|
||||||
|
FixedScalarArray(ScalarType scalarType, std::size_t size);
|
||||||
|
|
||||||
|
virtual ArraySizeType getArraySizeType() const {return Array::fixed;}
|
||||||
|
|
||||||
|
virtual std::size_t getMaximumCapacity() const {return size;}
|
||||||
|
|
||||||
|
virtual std::string getID() const;
|
||||||
|
|
||||||
|
virtual void serialize(ByteBuffer *buffer, SerializableControl *control) const;
|
||||||
|
|
||||||
|
protected:
|
||||||
|
/**
|
||||||
|
* Destructor.
|
||||||
|
*/
|
||||||
|
virtual ~FixedScalarArray();
|
||||||
|
private:
|
||||||
|
std::size_t size;
|
||||||
|
friend class FieldCreate;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* This class implements introspection object for a structureArray
|
* This class implements introspection object for a structureArray
|
||||||
*/
|
*/
|
||||||
@@ -448,6 +570,10 @@ public:
|
|||||||
*/
|
*/
|
||||||
StructureConstPtr getStructure() const {return pstructure;}
|
StructureConstPtr getStructure() const {return pstructure;}
|
||||||
|
|
||||||
|
virtual ArraySizeType getArraySizeType() const {return Array::variable;}
|
||||||
|
|
||||||
|
virtual std::size_t getMaximumCapacity() const {return 0;}
|
||||||
|
|
||||||
virtual std::string getID() const;
|
virtual std::string getID() const;
|
||||||
|
|
||||||
virtual std::ostream& dump(std::ostream& o) const;
|
virtual std::ostream& dump(std::ostream& o) const;
|
||||||
@@ -485,6 +611,10 @@ public:
|
|||||||
*/
|
*/
|
||||||
UnionConstPtr getUnion() const {return punion;}
|
UnionConstPtr getUnion() const {return punion;}
|
||||||
|
|
||||||
|
virtual ArraySizeType getArraySizeType() const {return Array::variable;}
|
||||||
|
|
||||||
|
virtual std::size_t getMaximumCapacity() const {return 0;}
|
||||||
|
|
||||||
virtual std::string getID() const;
|
virtual std::string getID() const;
|
||||||
|
|
||||||
virtual std::ostream& dump(std::ostream& o) const;
|
virtual std::ostream& dump(std::ostream& o) const;
|
||||||
@@ -711,6 +841,14 @@ public:
|
|||||||
*/
|
*/
|
||||||
FieldBuilderPtr add(std::string const & name, ScalarType scalarType);
|
FieldBuilderPtr add(std::string const & name, ScalarType scalarType);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Add a {@code BoundedString}.
|
||||||
|
* @param name name of the array.
|
||||||
|
* @param maxLength a string maximum length.
|
||||||
|
* @return this instance of a {@code FieldBuilder}.
|
||||||
|
*/
|
||||||
|
FieldBuilderPtr addBoundedString(std::string const & name, std::size_t maxLength);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Add a {@code Field} (e.g. {@code Structure}, {@code Union}).
|
* Add a {@code Field} (e.g. {@code Structure}, {@code Union}).
|
||||||
* @param name name of the array.
|
* @param name name of the array.
|
||||||
@@ -720,13 +858,31 @@ public:
|
|||||||
FieldBuilderPtr add(std::string const & name, FieldConstPtr const & field);
|
FieldBuilderPtr add(std::string const & name, FieldConstPtr const & field);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Add array of {@code Scalar} elements.
|
* Add variable size array of {@code Scalar} elements.
|
||||||
* @param name name of the array.
|
* @param name name of the array.
|
||||||
* @param scalarType type of a scalar element.
|
* @param scalarType type of a scalar element.
|
||||||
* @return this instance of a {@code FieldBuilder}.
|
* @return this instance of a {@code FieldBuilder}.
|
||||||
*/
|
*/
|
||||||
FieldBuilderPtr addArray(std::string const & name, ScalarType scalarType);
|
FieldBuilderPtr addArray(std::string const & name, ScalarType scalarType);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Add fixed-size array of {@code Scalar} elements.
|
||||||
|
* @param name name of the array.
|
||||||
|
* @param scalarType type of a scalar element.
|
||||||
|
* @param size Array fixed size.
|
||||||
|
* @return this instance of a {@code FieldBuilder}.
|
||||||
|
*/
|
||||||
|
FieldBuilderPtr addFixedArray(std::string const & name, ScalarType scalarType, std::size_t size);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Add bounded-size array of {@code Scalar} elements.
|
||||||
|
* @param name name of the array.
|
||||||
|
* @param scalarType type of a scalar element.
|
||||||
|
* @param bound Array maximum capacity (size).
|
||||||
|
* @return this instance of a {@code FieldBuilder}.
|
||||||
|
*/
|
||||||
|
FieldBuilderPtr addBoundedArray(std::string const & name, ScalarType scalarType, std::size_t bound);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Add array of {@code Field} elements.
|
* Add array of {@code Field} elements.
|
||||||
* @param name name of the array.
|
* @param name name of the array.
|
||||||
@@ -843,11 +999,32 @@ public:
|
|||||||
*/
|
*/
|
||||||
ScalarConstPtr createScalar(ScalarType scalarType) const;
|
ScalarConstPtr createScalar(ScalarType scalarType) const;
|
||||||
/**
|
/**
|
||||||
* Create an {@code Array} field.
|
* Create a {@code BoundedString}.
|
||||||
|
* @param maxLength a string maximum length.
|
||||||
|
* @return a {@code BoundedString} interface for the newly created object.
|
||||||
|
* @throws An {@code IllegalArgumentException} if maxLength == 0.
|
||||||
|
*/
|
||||||
|
BoundedStringConstPtr createBoundedString(std::size_t maxLength) const;
|
||||||
|
/**
|
||||||
|
* Create an {@code Array} field, variable size array.
|
||||||
* @param elementType The {@code scalarType} for array elements
|
* @param elementType The {@code scalarType} for array elements
|
||||||
* @return An {@code Array} Interface for the newly created object.
|
* @return An {@code Array} Interface for the newly created object.
|
||||||
*/
|
*/
|
||||||
ScalarArrayConstPtr createScalarArray(ScalarType elementType) const;
|
ScalarArrayConstPtr createScalarArray(ScalarType elementType) const;
|
||||||
|
/*
|
||||||
|
* Create an {@code Array} field, fixed size array.
|
||||||
|
* @param elementType The {@code scalarType} for array elements
|
||||||
|
* @param size Fixed array size.
|
||||||
|
* @return An {@code Array} Interface for the newly created object.
|
||||||
|
*/
|
||||||
|
ScalarArrayConstPtr createFixedScalarArray(ScalarType elementType, std::size_t size) const;
|
||||||
|
/**
|
||||||
|
* Create an {@code Array} field, bounded size array.
|
||||||
|
* @param elementType The {@code scalarType} for array elements
|
||||||
|
* @param size Array maximum capacity (bound).
|
||||||
|
* @return An {@code Array} Interface for the newly created object.
|
||||||
|
*/
|
||||||
|
ScalarArrayConstPtr createBoundedScalarArray(ScalarType elementType, std::size_t bound) const;
|
||||||
/**
|
/**
|
||||||
* Create an {@code Array} field that is has element type <i>Structure</i>
|
* Create an {@code Array} field that is has element type <i>Structure</i>
|
||||||
* @param fieldName The field name
|
* @param fieldName The field name
|
||||||
@@ -972,7 +1149,7 @@ epicsShareExtern FieldCreatePtr getFieldCreate();
|
|||||||
* value (eg -1).
|
* value (eg -1).
|
||||||
*/
|
*/
|
||||||
template<typename T>
|
template<typename T>
|
||||||
struct ScalarTypeID { enum {value=-1}; };
|
struct ScalarTypeID {};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Static mapping from ScalarType enum to value type.
|
* Static mapping from ScalarType enum to value type.
|
||||||
|
|||||||
@@ -29,7 +29,7 @@ typedef int intptr_t;
|
|||||||
typedef unsigned int uintptr_t;
|
typedef unsigned int uintptr_t;
|
||||||
#ifndef INT64_MAX
|
#ifndef INT64_MAX
|
||||||
#define INT64_MAX (0x7fffffffffffffffLL)
|
#define INT64_MAX (0x7fffffffffffffffLL)
|
||||||
#define UINT64_MAX (0xffffffffffffffffLL)
|
#define UINT64_MAX (0xffffffffffffffffULL)
|
||||||
#endif
|
#endif
|
||||||
#else
|
#else
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
|
|||||||
@@ -51,7 +51,7 @@ typedef std::tr1::shared_ptr<StandardField> StandardFieldPtr;
|
|||||||
string message
|
string message
|
||||||
structure timeStamp
|
structure timeStamp
|
||||||
long secondsPastEpoch
|
long secondsPastEpoch
|
||||||
int nanoSeconds
|
int nanoseconds
|
||||||
int userTag
|
int userTag
|
||||||
* }
|
* }
|
||||||
* In addition there are methods that create each of the property structures,
|
* In addition there are methods that create each of the property structures,
|
||||||
@@ -122,7 +122,7 @@ public:
|
|||||||
*/
|
*/
|
||||||
StructureConstPtr enumerated();
|
StructureConstPtr enumerated();
|
||||||
/** Create a structure that has an enumerated structure value field
|
/** Create a structure that has an enumerated structure value field
|
||||||
* The id for the structure is "uri:ev4:nt/2012/pwd:NTEnum".
|
* The id for the structure is "epics:nt/NTEnum:1.0".
|
||||||
* @param properties A comma separated list of properties.
|
* @param properties A comma separated list of properties.
|
||||||
* This is some combination of "alarm,timeStamp,display,control,valueAlarm".
|
* This is some combination of "alarm,timeStamp,display,control,valueAlarm".
|
||||||
* @return The const shared pointer to the structure.
|
* @return The const shared pointer to the structure.
|
||||||
|
|||||||
@@ -84,7 +84,7 @@ public:
|
|||||||
PVStructurePtr enumerated(StringArray const &choices);
|
PVStructurePtr enumerated(StringArray const &choices);
|
||||||
/**
|
/**
|
||||||
* Create a structure that has an enumerated structure value field.
|
* Create a structure that has an enumerated structure value field.
|
||||||
* The id for the structure is "uri:ev4:nt/2012/pwd:NTEnum".
|
* The id for the structure is "epics:nt/NTEnum:1.0".
|
||||||
* @param choices This is a StringArray of choices.
|
* @param choices This is a StringArray of choices.
|
||||||
* @param properties A comma separated list of properties.
|
* @param properties A comma separated list of properties.
|
||||||
* @return The const shared pointer to the structure.
|
* @return The const shared pointer to the structure.
|
||||||
|
|||||||
@@ -1,8 +1,31 @@
|
|||||||
|
# Makefile for the pvData tests
|
||||||
|
|
||||||
TOP = ..
|
TOP = ..
|
||||||
include $(TOP)/configure/CONFIG
|
include $(TOP)/configure/CONFIG
|
||||||
DIRS += misc
|
|
||||||
DIRS += pv
|
PVDATA_TEST = $(TOP)/testApp
|
||||||
DIRS += property
|
|
||||||
DIRS += copy
|
PROD_LIBS += pvData Com
|
||||||
include $(TOP)/configure/RULES_DIRS
|
|
||||||
|
include $(PVDATA_TEST)/misc/Makefile
|
||||||
|
include $(PVDATA_TEST)/pv/Makefile
|
||||||
|
include $(PVDATA_TEST)/property/Makefile
|
||||||
|
include $(PVDATA_TEST)/copy/Makefile
|
||||||
|
|
||||||
|
# The testHarness runs all the test programs in a known working order.
|
||||||
|
testHarness_SRCS += pvDataAllTests.c
|
||||||
|
|
||||||
|
PROD_vxWorks = vxTestHarness
|
||||||
|
vxTestHarness_SRCS += $(testHarness_SRCS)
|
||||||
|
TESTSPEC_vxWorks = vxTestHarness.$(MUNCH_SUFFIX); pvDataAllTests
|
||||||
|
|
||||||
|
PROD_RTEMS += rtemsTestHarness
|
||||||
|
rtemsTestHarness_SRCS += rtemsTestHarness.c rtemsConfig.c
|
||||||
|
rtemsTestHarness_SRCS += $(testHarness_SRCS)
|
||||||
|
TESTSPEC_RTEMS = rtemsTestHarness.$(MUNCH_SUFFIX); pvDataAllTests
|
||||||
|
|
||||||
|
TESTSCRIPTS_HOST += $(TESTS:%=%.t)
|
||||||
|
|
||||||
|
include $(TOP)/configure/RULES
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -1,22 +1,13 @@
|
|||||||
TOP=../..
|
# This is a Makefile fragment, see ../Makefile
|
||||||
|
|
||||||
include $(TOP)/configure/CONFIG
|
SRC_DIRS += $(PVDATA_TEST)/copy
|
||||||
|
|
||||||
PROD_HOST += testCreateRequest
|
TESTPROD_HOST += testCreateRequest
|
||||||
testCreateRequest_SRCS = testCreateRequest.cpp
|
testCreateRequest_SRCS = testCreateRequest.cpp
|
||||||
testCreateRequest_LIBS = pvData Com
|
testHarness_SRCS += testCreateRequest.cpp
|
||||||
TESTS += testCreateRequest
|
TESTS += testCreateRequest
|
||||||
|
|
||||||
PROD_HOST += testPVCopy
|
TESTPROD_HOST += testPVCopy
|
||||||
testPVCopy_SRCS += testPVCopy.cpp
|
testPVCopy_SRCS += testPVCopy.cpp
|
||||||
testPVCopy_LIBS += pvData Com
|
testHarness_SRCS += testPVCopy.cpp
|
||||||
TESTS += testPVCopy
|
TESTS += testPVCopy
|
||||||
|
|
||||||
TESTSCRIPTS_HOST += $(TESTS:%=%.t)
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
include $(TOP)/configure/RULES
|
|
||||||
#----------------------------------------
|
|
||||||
# ADD RULES AFTER THIS LINE
|
|
||||||
|
|
||||||
|
|||||||
@@ -20,101 +20,102 @@ using std::endl;
|
|||||||
|
|
||||||
static bool debug = false;
|
static bool debug = false;
|
||||||
|
|
||||||
void testCreateRequest() {
|
static void testCreateRequestInternal() {
|
||||||
printf("testCreateRequest... \n");
|
printf("testCreateRequest... \n");
|
||||||
CreateRequest::shared_pointer createRequest = CreateRequest::create();
|
CreateRequest::shared_pointer createRequest = CreateRequest::create();
|
||||||
|
PVStringPtr pvString;
|
||||||
|
string sval;
|
||||||
|
|
||||||
string out;
|
string out;
|
||||||
string request = "";
|
string request = "";
|
||||||
if(debug) { cout << "request " << request <<endl;}
|
if(debug) { cout << "request " << request <<endl;}
|
||||||
PVStructurePtr pvRequest = createRequest->createRequest(request);
|
PVStructurePtr pvRequest = createRequest->createRequest(request);
|
||||||
if(debug) { cout<< createRequest->getMessage() << endl;}
|
if(!pvRequest) { cout<< createRequest->getMessage() << endl;}
|
||||||
testOk1(pvRequest!=NULL);
|
if(debug) { cout << *pvRequest << endl;}
|
||||||
if(debug) { cout << pvRequest->dumpValue(cout) << endl;}
|
testOk1(pvRequest.get()!=NULL);
|
||||||
testOk1(pvRequest->getStructure()->getNumberFields()==0);
|
testOk1(pvRequest->getStructure()->getNumberFields()==0);
|
||||||
testPass("request %s",request.c_str());
|
testPass("request %s",request.c_str());
|
||||||
|
|
||||||
|
request = "record[]field()getField()putField()";
|
||||||
|
if(debug) { cout << "request " << request <<endl;}
|
||||||
|
pvRequest = createRequest->createRequest(request);
|
||||||
|
if(!pvRequest) { cout<< createRequest->getMessage() << endl;}
|
||||||
|
if(debug) { cout << *pvRequest << endl;}
|
||||||
|
testOk1(pvRequest.get()!=NULL);
|
||||||
|
testOk1(pvRequest->getSubField("field").get()!=NULL);
|
||||||
|
testOk1(pvRequest->getSubField("putField").get()!=NULL);
|
||||||
|
testOk1(pvRequest->getSubField("getField").get()!=NULL);
|
||||||
|
testPass("request %s",request.c_str());
|
||||||
|
|
||||||
request = "record[a=b,x=y]field(a) putField(a),getField(a)";
|
request = "record[a=b,x=y]field(a) putField(a),getField(a)";
|
||||||
pvRequest = createRequest->createRequest(request);
|
|
||||||
if(pvRequest==NULL) {
|
|
||||||
cout << createRequest->getMessage() << endl;
|
|
||||||
}
|
|
||||||
if(debug) { cout << "request " << request <<endl;}
|
if(debug) { cout << "request " << request <<endl;}
|
||||||
testOk1(pvRequest!=NULL);
|
pvRequest = createRequest->createRequest(request);
|
||||||
if(debug) { cout << pvRequest->dumpValue(cout) << endl;}
|
if(!pvRequest) { cout<< createRequest->getMessage() << endl;}
|
||||||
PVStringPtr pvString = pvRequest->getSubField<PVString>("record.a");
|
if(debug) { cout << *pvRequest << endl;}
|
||||||
string sval = pvString->get();
|
testOk1(pvRequest.get()!=NULL);
|
||||||
|
pvString = pvRequest->getSubField<PVString>("record._options.a");
|
||||||
|
sval = pvString->get();
|
||||||
testOk(sval.compare("b")==0,"record.a = b");
|
testOk(sval.compare("b")==0,"record.a = b");
|
||||||
pvString = pvRequest->getSubField<PVString>("record.x");
|
pvString = pvRequest->getSubField<PVString>("record._options.x");
|
||||||
sval = pvString->get();
|
sval = pvString->get();
|
||||||
testOk(sval.compare("y")==0,"record.x = y");
|
testOk(sval.compare("y")==0,"record.x = y");
|
||||||
testOk1(pvRequest->getSubField("field.a")!=NULL);
|
testOk1(pvRequest->getSubField("field.a").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("putField.a")!=NULL);
|
testOk1(pvRequest->getSubField("putField.a").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.a")!=NULL);
|
testOk1(pvRequest->getSubField("getField.a").get()!=NULL);
|
||||||
testPass("request %s",request.c_str());
|
testPass("request %s",request.c_str());
|
||||||
|
|
||||||
request = "field(a.b[x=y])";
|
request = "field(a.b[x=y])";
|
||||||
pvRequest = createRequest->createRequest(request);
|
|
||||||
if(pvRequest==NULL) {
|
|
||||||
cout << createRequest->getMessage() << endl;
|
|
||||||
}
|
|
||||||
if(debug) { cout << "request " << request <<endl;}
|
if(debug) { cout << "request " << request <<endl;}
|
||||||
testOk1(pvRequest!=NULL);
|
pvRequest = createRequest->createRequest(request);
|
||||||
if(debug) { cout << pvRequest->dumpValue(cout) << endl;}
|
if(!pvRequest) { cout<< createRequest->getMessage() << endl;}
|
||||||
|
if(debug) { cout << *pvRequest << endl;}
|
||||||
|
testOk1(pvRequest.get()!=NULL);
|
||||||
pvString = pvRequest->getSubField<PVString>("field.a.b._options.x");
|
pvString = pvRequest->getSubField<PVString>("field.a.b._options.x");
|
||||||
sval = pvString->get();
|
sval = pvString->get();
|
||||||
testOk(sval.compare("y")==0,"field.a.b._options.x = y");
|
testOk(sval.compare("y")==0,"field.a.b._options.x = y");
|
||||||
testPass("request %s",request.c_str());
|
testPass("request %s",request.c_str());
|
||||||
|
|
||||||
request = "field(a.b{c.d})";
|
request = "field(a.b{c.d})";
|
||||||
pvRequest = createRequest->createRequest(request);
|
|
||||||
if(debug) { cout << "request " << request <<endl;}
|
if(debug) { cout << "request " << request <<endl;}
|
||||||
if(pvRequest==NULL) {
|
pvRequest = createRequest->createRequest(request);
|
||||||
cout << createRequest->getMessage() << endl;
|
if(!pvRequest) { cout<< createRequest->getMessage() << endl;}
|
||||||
}
|
if(debug) { cout << *pvRequest << endl;}
|
||||||
testOk1(pvRequest!=NULL);
|
testOk1(pvRequest.get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("field.a.b.c.d")!=NULL);
|
testOk1(pvRequest->getSubField("field.a.b.c.d").get()!=NULL);
|
||||||
if(debug) { cout << pvRequest->dumpValue(cout) << endl;}
|
|
||||||
testPass("request %s",request.c_str());
|
testPass("request %s",request.c_str());
|
||||||
|
|
||||||
request = "field(a.b[x=y]{c.d})";
|
request = "field(a.b[x=y]{c.d})";
|
||||||
pvRequest = createRequest->createRequest(request);
|
|
||||||
if(debug) { cout << "request " << request <<endl;}
|
if(debug) { cout << "request " << request <<endl;}
|
||||||
if(pvRequest==NULL) {
|
pvRequest = createRequest->createRequest(request);
|
||||||
cout << createRequest->getMessage() << endl;
|
if(!pvRequest) { cout<< createRequest->getMessage() << endl;}
|
||||||
}
|
if(debug) { cout << *pvRequest << endl;}
|
||||||
testOk1(pvRequest!=NULL);
|
testOk1(pvRequest.get()!=NULL);
|
||||||
pvString = pvRequest->getSubField<PVString>("field.a.b._options.x");
|
pvString = pvRequest->getSubField<PVString>("field.a.b._options.x");
|
||||||
sval = pvString->get();
|
sval = pvString->get();
|
||||||
testOk(sval.compare("y")==0,"field.a.b._options.x = y");
|
testOk(sval.compare("y")==0,"field.a.b._options.x = y");
|
||||||
testOk1(pvRequest->getSubField("field.a.b.c.d")!=NULL);
|
testOk1(pvRequest->getSubField("field.a.b.c.d").get()!=NULL);
|
||||||
if(debug) { cout << pvRequest->dumpValue(cout) << endl;}
|
|
||||||
testPass("request %s",request.c_str());
|
testPass("request %s",request.c_str());
|
||||||
|
|
||||||
request = "field(a.b[x=y]{c.d[x=y]})";
|
request = "field(a.b[x=y]{c.d[x=y]})";
|
||||||
pvRequest = createRequest->createRequest(request);
|
|
||||||
if(debug) { cout << "request " << request <<endl;}
|
if(debug) { cout << "request " << request <<endl;}
|
||||||
if(pvRequest==NULL) {
|
pvRequest = createRequest->createRequest(request);
|
||||||
cout << createRequest->getMessage() << endl;
|
if(!pvRequest) { cout<< createRequest->getMessage() << endl;}
|
||||||
}
|
if(debug) { cout << *pvRequest << endl;}
|
||||||
testOk1(pvRequest!=NULL);
|
testOk1(pvRequest.get()!=NULL);
|
||||||
pvString = pvRequest->getSubField<PVString>("field.a.b._options.x");
|
pvString = pvRequest->getSubField<PVString>("field.a.b._options.x");
|
||||||
sval = pvString->get();
|
sval = pvString->get();
|
||||||
testOk(sval.compare("y")==0,"field.a.b._options.x = y");
|
testOk(sval.compare("y")==0,"field.a.b._options.x = y");
|
||||||
pvString = pvRequest->getSubField<PVString>("field.a.b.c.d._options.x");
|
pvString = pvRequest->getSubField<PVString>("field.a.b.c.d._options.x");
|
||||||
sval = pvString->get();
|
sval = pvString->get();
|
||||||
testOk(sval.compare("y")==0,"field.a.b.c.d._options.x = y");
|
testOk(sval.compare("y")==0,"field.a.b.c.d._options.x = y");
|
||||||
if(debug) { cout << pvRequest->dumpValue(cout) << endl;}
|
|
||||||
testPass("request %s",request.c_str());
|
testPass("request %s",request.c_str());
|
||||||
|
|
||||||
request = "record[a=b,c=d] field(a.a[a=b]{a.a[a=b]},b.a[a=b]{a,b})";
|
request = "record[a=b,c=d] field(a.a[a=b]{a.a[a=b]},b.a[a=b]{a,b})";
|
||||||
pvRequest = createRequest->createRequest(request);
|
|
||||||
if(debug) { cout << "request " << request <<endl;}
|
if(debug) { cout << "request " << request <<endl;}
|
||||||
if(pvRequest==NULL) {
|
pvRequest = createRequest->createRequest(request);
|
||||||
cout << createRequest->getMessage() << endl;
|
if(!pvRequest) { cout<< createRequest->getMessage() << endl;}
|
||||||
}
|
if(debug) { cout << *pvRequest << endl;}
|
||||||
testOk1(pvRequest!=NULL);
|
testOk1(pvRequest.get()!=NULL);
|
||||||
pvString = pvRequest->getSubField<PVString>("field.a.a._options.a");
|
pvString = pvRequest->getSubField<PVString>("field.a.a._options.a");
|
||||||
sval = pvString->get();
|
sval = pvString->get();
|
||||||
testOk(sval.compare("b")==0,"field.a.a._options.a = b");
|
testOk(sval.compare("b")==0,"field.a.a._options.a = b");
|
||||||
@@ -124,126 +125,113 @@ void testCreateRequest() {
|
|||||||
pvString = pvRequest->getSubField<PVString>("field.b.a._options.a");
|
pvString = pvRequest->getSubField<PVString>("field.b.a._options.a");
|
||||||
sval = pvString->get();
|
sval = pvString->get();
|
||||||
testOk(sval.compare("b")==0,"field.b.a._options.a = b");
|
testOk(sval.compare("b")==0,"field.b.a._options.a = b");
|
||||||
testOk1(pvRequest->getSubField("field.b.a.a")!=NULL);
|
testOk1(pvRequest->getSubField("field.b.a.a").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("field.b.a.b")!=NULL);
|
testOk1(pvRequest->getSubField("field.b.a.b").get()!=NULL);
|
||||||
if(debug) { cout << pvRequest->dumpValue(cout) << endl;}
|
|
||||||
testPass("request %s",request.c_str());
|
testPass("request %s",request.c_str());
|
||||||
|
|
||||||
|
|
||||||
request = "alarm,timeStamp,power.value";
|
request = "alarm,timeStamp,power.value";
|
||||||
|
if(debug) { cout << "request " << request <<endl;}
|
||||||
pvRequest = createRequest->createRequest(request);
|
pvRequest = createRequest->createRequest(request);
|
||||||
if(debug) { cout << endl << string("request") <<endl << request <<endl;}
|
if(!pvRequest) { cout<< createRequest->getMessage() << endl;}
|
||||||
if(pvRequest==NULL) {
|
if(debug) { cout << *pvRequest << endl;}
|
||||||
cout << "reason " << createRequest->getMessage() << endl;
|
testOk1(pvRequest.get()!=NULL);
|
||||||
}
|
testOk1(pvRequest->getSubField("field.alarm").get()!=NULL);
|
||||||
testOk1(pvRequest!=NULL);
|
testOk1(pvRequest->getSubField("field.timeStamp").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("field.alarm")!=NULL);
|
testOk1(pvRequest->getSubField("field.power.value").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("field.timeStamp")!=NULL);
|
|
||||||
testOk1(pvRequest->getSubField("field.power.value")!=NULL);
|
|
||||||
if(debug) { cout << pvRequest->dumpValue(cout) << endl;}
|
|
||||||
testPass("request %s",request.c_str());
|
testPass("request %s",request.c_str());
|
||||||
|
|
||||||
request = "record[process=true]field(alarm,timeStamp,power.value)";
|
request = "record[process=true]field(alarm,timeStamp,power.value)";
|
||||||
|
if(debug) { cout << "request " << request <<endl;}
|
||||||
pvRequest = createRequest->createRequest(request);
|
pvRequest = createRequest->createRequest(request);
|
||||||
if(debug) { cout << endl << string("request") <<endl << request <<endl;}
|
if(!pvRequest) { cout<< createRequest->getMessage() << endl;}
|
||||||
if(pvRequest==NULL) {
|
if(debug) { cout << *pvRequest << endl;}
|
||||||
cout << "reason " << createRequest->getMessage() << endl;
|
testOk1(pvRequest.get()!=NULL);
|
||||||
}
|
pvString = pvRequest->getSubField<PVString>("record._options.process");
|
||||||
testOk1(pvRequest!=NULL);
|
|
||||||
pvString = pvRequest->getSubField<PVString>("record.process");
|
|
||||||
sval = pvString->get();
|
sval = pvString->get();
|
||||||
testOk(sval.compare("true")==0,"record.process = true");
|
testOk(sval.compare("true")==0,"record._options.process = true");
|
||||||
testOk1(pvRequest->getSubField("field.alarm")!=NULL);
|
testOk1(pvRequest->getSubField("field.alarm").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("field.timeStamp")!=NULL);
|
testOk1(pvRequest->getSubField("field.timeStamp").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("field.power.value")!=NULL);
|
testOk1(pvRequest->getSubField("field.power.value").get()!=NULL);
|
||||||
if(debug) {cout << pvRequest->dumpValue(cout) << endl;}
|
|
||||||
testPass("request %s",request.c_str());
|
testPass("request %s",request.c_str());
|
||||||
|
|
||||||
request = "record[process=true]field(alarm,timeStamp[algorithm=onChange,causeMonitor=false],power{value,alarm})";
|
request = "record[process=true]field(alarm,timeStamp[algorithm=onChange,causeMonitor=false],power{value,alarm})";
|
||||||
|
if(debug) { cout << "request " << request <<endl;}
|
||||||
pvRequest = createRequest->createRequest(request);
|
pvRequest = createRequest->createRequest(request);
|
||||||
if(debug) { cout << string("request") <<endl << request <<endl;}
|
if(!pvRequest) { cout<< createRequest->getMessage() << endl;}
|
||||||
if(pvRequest==NULL) {
|
if(debug) { cout << *pvRequest << endl;}
|
||||||
cout << "reason " << createRequest->getMessage() << endl;
|
testOk1(pvRequest.get()!=NULL);
|
||||||
}
|
pvString = pvRequest->getSubField<PVString>("record._options.process");
|
||||||
testOk1(pvRequest!=NULL);
|
|
||||||
pvString = pvRequest->getSubField<PVString>("record.process");
|
|
||||||
sval = pvString->get();
|
sval = pvString->get();
|
||||||
testOk(sval.compare("true")==0,"record.process = true");
|
testOk(sval.compare("true")==0,"record._options.process = true");
|
||||||
testOk1(pvRequest->getSubField("field.alarm")!=NULL);
|
testOk1(pvRequest->getSubField("field.alarm").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("field.timeStamp")!=NULL);
|
testOk1(pvRequest->getSubField("field.timeStamp").get()!=NULL);
|
||||||
pvString = pvRequest->getSubField<PVString>("field.timeStamp._options.algorithm");
|
pvString = pvRequest->getSubField<PVString>("field.timeStamp._options.algorithm");
|
||||||
sval = pvString->get();
|
sval = pvString->get();
|
||||||
testOk(sval.compare("onChange")==0,"field.timeStamp._options.algorithm = onChange");
|
testOk(sval.compare("onChange")==0,"field.timeStamp._options.algorithm = onChange");
|
||||||
pvString = pvRequest->getSubField<PVString>("field.timeStamp._options.causeMonitor");
|
pvString = pvRequest->getSubField<PVString>("field.timeStamp._options.causeMonitor");
|
||||||
sval = pvString->get();
|
sval = pvString->get();
|
||||||
testOk(sval.compare("false")==0,"field.timeStamp._options.causeMonitor = false");
|
testOk(sval.compare("false")==0,"field.timeStamp._options.causeMonitor = false");
|
||||||
testOk1(pvRequest->getSubField("field.power.value")!=NULL);
|
testOk1(pvRequest->getSubField("field.power.value").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("field.power.alarm")!=NULL);
|
testOk1(pvRequest->getSubField("field.power.alarm").get()!=NULL);
|
||||||
if(debug) {cout << pvRequest->dumpValue(cout) << endl;}
|
|
||||||
testPass("request %s",request.c_str());
|
testPass("request %s",request.c_str());
|
||||||
|
|
||||||
request = "record[int=2,float=3.14159]field(alarm,timeStamp[shareData=true],power.value)";
|
request = "record[int=2,float=3.14159]field(alarm,timeStamp[shareData=true],power.value)";
|
||||||
|
if(debug) { cout << "request " << request <<endl;}
|
||||||
pvRequest = createRequest->createRequest(request);
|
pvRequest = createRequest->createRequest(request);
|
||||||
if(debug) { cout << string("request") <<endl << request <<endl;}
|
if(!pvRequest) { cout<< createRequest->getMessage() << endl;}
|
||||||
if(pvRequest==NULL) {
|
if(debug) { cout << *pvRequest << endl;}
|
||||||
cout << "reason " << createRequest->getMessage() << endl;
|
testOk1(pvRequest.get()!=NULL);
|
||||||
}
|
pvString = pvRequest->getSubField<PVString>("record._options.int");
|
||||||
testOk1(pvRequest!=NULL);
|
|
||||||
pvString = pvRequest->getSubField<PVString>("record.int");
|
|
||||||
sval = pvString->get();
|
sval = pvString->get();
|
||||||
testOk(sval.compare("2")==0,"record.int = 2");
|
testOk(sval.compare("2")==0,"record._options.int = 2");
|
||||||
pvString = pvRequest->getSubField<PVString>("record.float");
|
pvString = pvRequest->getSubField<PVString>("record._options.float");
|
||||||
sval = pvString->get();
|
sval = pvString->get();
|
||||||
testOk(sval.compare("3.14159")==0,"record.float = 3.14159");
|
testOk(sval.compare("3.14159")==0,"record._options.float = 3.14159");
|
||||||
testOk1(pvRequest->getSubField("field.alarm")!=NULL);
|
testOk1(pvRequest->getSubField("field.alarm").get()!=NULL);
|
||||||
pvString = pvRequest->getSubField<PVString>("field.timeStamp._options.shareData");
|
pvString = pvRequest->getSubField<PVString>("field.timeStamp._options.shareData");
|
||||||
sval = pvString->get();
|
sval = pvString->get();
|
||||||
testOk(sval.compare("true")==0,"field.timeStamp._options.shareData = true");
|
testOk(sval.compare("true")==0,"field.timeStamp._options.shareData = true");
|
||||||
testOk1(pvRequest->getSubField("field.power.value")!=NULL);
|
testOk1(pvRequest->getSubField("field.power.value").get()!=NULL);
|
||||||
if(debug) {cout << pvRequest->dumpValue(cout) << endl;}
|
|
||||||
testPass("request %s",request.c_str());
|
testPass("request %s",request.c_str());
|
||||||
|
|
||||||
request = string("record[process=true,xxx=yyy]")
|
request = string("record[process=true,xxx=yyy]")
|
||||||
+ "putField(power.value)"
|
+ "putField(power.value)"
|
||||||
+ "getField(alarm,timeStamp,power{value,alarm},"
|
+ "getField(alarm,timeStamp,power{value,alarm},"
|
||||||
+ "current{value,alarm},voltage{value,alarm})";
|
+ "current{value,alarm},voltage{value,alarm})";
|
||||||
|
if(debug) { cout << "request " << request <<endl;}
|
||||||
pvRequest = createRequest->createRequest(request);
|
pvRequest = createRequest->createRequest(request);
|
||||||
if(debug) { cout << string("request") <<endl << request <<endl;}
|
if(!pvRequest) { cout<< createRequest->getMessage() << endl;}
|
||||||
if(pvRequest==NULL) {
|
if(debug) { cout << *pvRequest << endl;}
|
||||||
cout << "reason " << createRequest->getMessage() << endl;
|
testOk1(pvRequest.get()!=NULL);
|
||||||
}
|
testOk1(pvRequest->getSubField("putField.power.value").get()!=NULL);
|
||||||
testOk1(pvRequest!=NULL);
|
testOk1(pvRequest->getSubField("getField.alarm").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("putField.power.value")!=NULL);
|
testOk1(pvRequest->getSubField("getField.timeStamp").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.alarm")!=NULL);
|
testOk1(pvRequest->getSubField("getField.power.value").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.timeStamp")!=NULL);
|
testOk1(pvRequest->getSubField("getField.power.alarm").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.power.value")!=NULL);
|
testOk1(pvRequest->getSubField("getField.current.value").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.power.alarm")!=NULL);
|
testOk1(pvRequest->getSubField("getField.current.alarm").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.current.value")!=NULL);
|
testOk1(pvRequest->getSubField("getField.voltage.value").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.current.alarm")!=NULL);
|
testOk1(pvRequest->getSubField("getField.voltage.alarm").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.voltage.value")!=NULL);
|
|
||||||
testOk1(pvRequest->getSubField("getField.voltage.alarm")!=NULL);
|
|
||||||
if(debug) {cout << pvRequest->dumpValue(cout) << endl;}
|
|
||||||
testPass("request %s",request.c_str());
|
testPass("request %s",request.c_str());
|
||||||
|
|
||||||
request = string("field(alarm,timeStamp,supply{")
|
request = string("field(alarm,timeStamp,supply{")
|
||||||
+ "0{voltage.value,current.value,power.value},"
|
+ "0{voltage.value,current.value,power.value},"
|
||||||
+ "1{voltage.value,current.value,power.value}"
|
+ "1{voltage.value,current.value,power.value}"
|
||||||
+ "})";
|
+ "})";
|
||||||
|
if(debug) { cout << "request " << request <<endl;}
|
||||||
pvRequest = createRequest->createRequest(request);
|
pvRequest = createRequest->createRequest(request);
|
||||||
if(debug) { cout << string("request") <<endl << request <<endl;}
|
if(!pvRequest) { cout<< createRequest->getMessage() << endl;}
|
||||||
if(pvRequest==NULL) {
|
if(debug) { cout << *pvRequest << endl;}
|
||||||
cout << "reason " << createRequest->getMessage() << endl;
|
testOk1(pvRequest.get()!=NULL);
|
||||||
}
|
testOk1(pvRequest->getSubField("field.alarm").get()!=NULL);
|
||||||
testOk1(pvRequest!=NULL);
|
testOk1(pvRequest->getSubField("field.timeStamp").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("field.alarm")!=NULL);
|
testOk1(pvRequest->getSubField("field.supply.0.voltage.value").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("field.timeStamp")!=NULL);
|
testOk1(pvRequest->getSubField("field.supply.0.current.value").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("field.supply.0.voltage.value")!=NULL);
|
testOk1(pvRequest->getSubField("field.supply.0.power.value").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("field.supply.0.current.value")!=NULL);
|
testOk1(pvRequest->getSubField("field.supply.1.voltage.value").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("field.supply.0.power.value")!=NULL);
|
testOk1(pvRequest->getSubField("field.supply.1.current.value").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("field.supply.1.voltage.value")!=NULL);
|
testOk1(pvRequest->getSubField("field.supply.1.power.value").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("field.supply.1.current.value")!=NULL);
|
|
||||||
testOk1(pvRequest->getSubField("field.supply.1.power.value")!=NULL);
|
|
||||||
if(debug) {cout << pvRequest->dumpValue(cout) << endl;}
|
|
||||||
testPass("request %s",request.c_str());
|
testPass("request %s",request.c_str());
|
||||||
|
|
||||||
request = string("record[process=true,xxx=yyy]")
|
request = string("record[process=true,xxx=yyy]")
|
||||||
@@ -253,46 +241,45 @@ void testCreateRequest() {
|
|||||||
+ "ps0{alarm,timeStamp,power{value,alarm},current{value,alarm},voltage{value,alarm}},"
|
+ "ps0{alarm,timeStamp,power{value,alarm},current{value,alarm},voltage{value,alarm}},"
|
||||||
+ "ps1{alarm,timeStamp,power{value,alarm},current{value,alarm},voltage{value,alarm}}"
|
+ "ps1{alarm,timeStamp,power{value,alarm},current{value,alarm},voltage{value,alarm}}"
|
||||||
+ ")";
|
+ ")";
|
||||||
|
if(debug) { cout << "request " << request <<endl;}
|
||||||
pvRequest = createRequest->createRequest(request);
|
pvRequest = createRequest->createRequest(request);
|
||||||
if(debug) { cout << string("request") <<endl << request <<endl;}
|
if(!pvRequest) { cout<< createRequest->getMessage() << endl;}
|
||||||
if(pvRequest==NULL) {
|
if(debug) { cout << *pvRequest << endl;}
|
||||||
cout << "reason " << createRequest->getMessage() << endl;
|
testOk1(pvRequest.get()!=NULL);
|
||||||
}
|
testOk1(pvRequest->getSubField("putField.power.value").get()!=NULL);
|
||||||
testOk1(pvRequest!=NULL);
|
testOk1(pvRequest->getSubField("getField.alarm").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("putField.power.value")!=NULL);
|
testOk1(pvRequest->getSubField("getField.timeStamp").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.alarm")!=NULL);
|
testOk1(pvRequest->getSubField("getField.power.value").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.timeStamp")!=NULL);
|
testOk1(pvRequest->getSubField("getField.power.alarm").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.power.value")!=NULL);
|
testOk1(pvRequest->getSubField("getField.current.value").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.power.alarm")!=NULL);
|
testOk1(pvRequest->getSubField("getField.current.alarm").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.current.value")!=NULL);
|
testOk1(pvRequest->getSubField("getField.voltage.value").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.current.alarm")!=NULL);
|
testOk1(pvRequest->getSubField("getField.voltage.alarm").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.voltage.value")!=NULL);
|
testOk1(pvRequest->getSubField("getField.ps0.alarm").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.voltage.alarm")!=NULL);
|
testOk1(pvRequest->getSubField("getField.ps0.timeStamp").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.ps0.alarm")!=NULL);
|
testOk1(pvRequest->getSubField("getField.ps0.power.value").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.ps0.timeStamp")!=NULL);
|
testOk1(pvRequest->getSubField("getField.ps0.power.alarm").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.ps0.power.value")!=NULL);
|
testOk1(pvRequest->getSubField("getField.ps0.current.value").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.ps0.power.alarm")!=NULL);
|
testOk1(pvRequest->getSubField("getField.ps0.current.alarm").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.ps0.current.value")!=NULL);
|
testOk1(pvRequest->getSubField("getField.ps0.voltage.value").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.ps0.current.alarm")!=NULL);
|
testOk1(pvRequest->getSubField("getField.ps0.voltage.alarm").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.ps0.voltage.value")!=NULL);
|
testOk1(pvRequest->getSubField("getField.ps1.alarm").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.ps0.voltage.alarm")!=NULL);
|
testOk1(pvRequest->getSubField("getField.ps1.timeStamp").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.ps1.alarm")!=NULL);
|
testOk1(pvRequest->getSubField("getField.ps1.power.value").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.ps1.timeStamp")!=NULL);
|
testOk1(pvRequest->getSubField("getField.ps1.power.alarm").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.ps1.power.value")!=NULL);
|
testOk1(pvRequest->getSubField("getField.ps1.current.value").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.ps1.power.alarm")!=NULL);
|
testOk1(pvRequest->getSubField("getField.ps1.current.alarm").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.ps1.current.value")!=NULL);
|
testOk1(pvRequest->getSubField("getField.ps1.voltage.value").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.ps1.current.alarm")!=NULL);
|
testOk1(pvRequest->getSubField("getField.ps1.voltage.alarm").get()!=NULL);
|
||||||
testOk1(pvRequest->getSubField("getField.ps1.voltage.value")!=NULL);
|
|
||||||
testOk1(pvRequest->getSubField("getField.ps1.voltage.alarm")!=NULL);
|
|
||||||
if(debug) {cout << pvRequest->dumpValue(cout) << endl;}
|
|
||||||
testPass("request %s",request.c_str());
|
testPass("request %s",request.c_str());
|
||||||
|
|
||||||
request = "a{b{c{d}}}";
|
request = "a{b{c{d}}}";
|
||||||
|
if(debug) { cout << "request " << request <<endl;}
|
||||||
pvRequest = createRequest->createRequest(request);
|
pvRequest = createRequest->createRequest(request);
|
||||||
if(debug) { cout << string("request") <<endl << request <<endl;}
|
if(!pvRequest) { cout<< createRequest->getMessage() << endl;}
|
||||||
testOk1(pvRequest!=NULL);
|
if(debug) { cout << *pvRequest << endl;}
|
||||||
testOk1(pvRequest->getSubField("field.a.b.c.d")!=NULL);
|
testOk1(pvRequest.get()!=NULL);
|
||||||
if(debug) {cout << pvRequest->dumpValue(cout) << endl;}
|
testOk1(pvRequest->getSubField("field.a.b.c.d").get()!=NULL);
|
||||||
testPass("request %s",request.c_str());
|
testPass("request %s",request.c_str());
|
||||||
|
|
||||||
request = string("record[process=true,xxx=yyy]")
|
request = string("record[process=true,xxx=yyy]")
|
||||||
@@ -302,26 +289,33 @@ void testCreateRequest() {
|
|||||||
+ "ps0{alarm,timeStamp,power{value,alarm},current{value,alarm},voltage{value,alarm}},"
|
+ "ps0{alarm,timeStamp,power{value,alarm},current{value,alarm},voltage{value,alarm}},"
|
||||||
+ "ps1{alarm,timeStamp,power{value,alarm},current{value,alarm},voltage{value,alarm}"
|
+ "ps1{alarm,timeStamp,power{value,alarm},current{value,alarm},voltage{value,alarm}"
|
||||||
+ ")";
|
+ ")";
|
||||||
if(debug) { cout << endl << "Error Expected for next call!!" << endl;}
|
if(debug) { cout << "request " << request <<endl;}
|
||||||
if(debug) { cout << string("request") <<endl << request <<endl;}
|
cout << endl << "Error Expected for next call!!" << endl;
|
||||||
pvRequest = createRequest->createRequest(request);
|
pvRequest = createRequest->createRequest(request);
|
||||||
assert(pvRequest.get()==NULL);
|
cout << "reason " << createRequest->getMessage() << endl;
|
||||||
if(debug) {cout << "reason " << createRequest->getMessage() << endl;}
|
|
||||||
testPass("request %s",request.c_str());
|
testPass("request %s",request.c_str());
|
||||||
|
|
||||||
request = "record[process=true,power.value";
|
request = "record[process=true,power.value";
|
||||||
if(debug) { cout << string("request") <<endl << request <<endl;}
|
if(debug) { cout << "request " << request <<endl;}
|
||||||
if(debug) { cout << endl << "Error Expected for next call!!" << endl;}
|
cout << endl << "Error Expected for next call!!" << endl;
|
||||||
pvRequest = createRequest->createRequest(request);
|
pvRequest = createRequest->createRequest(request);
|
||||||
assert(pvRequest.get()==NULL);
|
cout << "reason " << createRequest->getMessage() << endl;
|
||||||
if(debug) { cout << "reason " << createRequest->getMessage() << endl;}
|
testOk1(pvRequest.get()==NULL);
|
||||||
|
testPass("request %s",request.c_str());
|
||||||
|
|
||||||
|
request = "field(alarm.status,alarm.severity)";
|
||||||
|
if(debug) { cout << "request " << request <<endl;}
|
||||||
|
cout << endl << "Error Expected for next call!!" << endl;
|
||||||
|
pvRequest = createRequest->createRequest(request);
|
||||||
|
cout << "reason " << createRequest->getMessage() << endl;
|
||||||
|
testOk1(pvRequest.get()==NULL);
|
||||||
testPass("request %s",request.c_str());
|
testPass("request %s",request.c_str());
|
||||||
}
|
}
|
||||||
|
|
||||||
MAIN(testCreateRequest)
|
MAIN(testCreateRequest)
|
||||||
{
|
{
|
||||||
testPlan(111);
|
testPlan(119);
|
||||||
testCreateRequest();
|
testCreateRequestInternal();
|
||||||
return testDone();
|
return testDone();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -214,7 +214,7 @@ static void scalarTest()
|
|||||||
CreateRequest::shared_pointer createRequest = CreateRequest::create();
|
CreateRequest::shared_pointer createRequest = CreateRequest::create();
|
||||||
pvRequest = createRequest->createRequest(request);
|
pvRequest = createRequest->createRequest(request);
|
||||||
if(debug) { cout << "request " << request << endl; }
|
if(debug) { cout << "request " << request << endl; }
|
||||||
if(debug) { cout << "pvRequest\n" << pvRequest->dumpValue(cout) << endl; }
|
if(debug) { cout << "pvRequest\n" << *pvRequest << endl; }
|
||||||
pvCopy = PVCopy::create(pvMaster,pvRequest,"");
|
pvCopy = PVCopy::create(pvMaster,pvRequest,"");
|
||||||
valueNameCopy = "value";
|
valueNameCopy = "value";
|
||||||
testPVScalar(valueNameMaster,valueNameCopy,pvMaster,pvCopy);
|
testPVScalar(valueNameMaster,valueNameCopy,pvMaster,pvCopy);
|
||||||
@@ -222,7 +222,7 @@ static void scalarTest()
|
|||||||
valueNameMaster = "value";
|
valueNameMaster = "value";
|
||||||
pvRequest = createRequest->createRequest(request);
|
pvRequest = createRequest->createRequest(request);
|
||||||
if(debug) { cout << "request " << request << endl; }
|
if(debug) { cout << "request " << request << endl; }
|
||||||
if(debug) { cout << "pvRequest\n" << pvRequest->dumpValue(cout) << endl; }
|
if(debug) { cout << "pvRequest\n" << *pvRequest << endl; }
|
||||||
pvCopy = PVCopy::create(pvMaster,pvRequest,"");
|
pvCopy = PVCopy::create(pvMaster,pvRequest,"");
|
||||||
valueNameCopy = "value";
|
valueNameCopy = "value";
|
||||||
testPVScalar(valueNameMaster,valueNameCopy,pvMaster,pvCopy);
|
testPVScalar(valueNameMaster,valueNameCopy,pvMaster,pvCopy);
|
||||||
@@ -230,7 +230,7 @@ static void scalarTest()
|
|||||||
valueNameMaster = "value";
|
valueNameMaster = "value";
|
||||||
pvRequest = createRequest->createRequest(request);
|
pvRequest = createRequest->createRequest(request);
|
||||||
if(debug) { cout << "request " << request << endl; }
|
if(debug) { cout << "request " << request << endl; }
|
||||||
if(debug) { cout << "pvRequest\n" << pvRequest->dumpValue(cout) << endl; }
|
if(debug) { cout << "pvRequest\n" << *pvRequest << endl; }
|
||||||
pvCopy = PVCopy::create(pvMaster,pvRequest,"");
|
pvCopy = PVCopy::create(pvMaster,pvRequest,"");
|
||||||
valueNameCopy = "value";
|
valueNameCopy = "value";
|
||||||
testPVScalar(valueNameMaster,valueNameCopy,pvMaster,pvCopy);
|
testPVScalar(valueNameMaster,valueNameCopy,pvMaster,pvCopy);
|
||||||
@@ -253,7 +253,7 @@ static void arrayTest()
|
|||||||
valueNameMaster = request = "value";
|
valueNameMaster = request = "value";
|
||||||
pvRequest = createRequest->createRequest(request);
|
pvRequest = createRequest->createRequest(request);
|
||||||
if(debug) { cout << "request " << request << endl; }
|
if(debug) { cout << "request " << request << endl; }
|
||||||
if(debug) { cout << "pvRequest\n" << pvRequest->dumpValue(cout) << endl; }
|
if(debug) { cout << "pvRequest\n" << *pvRequest << endl; }
|
||||||
pvCopy = PVCopy::create(pvMaster,pvRequest,"");
|
pvCopy = PVCopy::create(pvMaster,pvRequest,"");
|
||||||
valueNameCopy = "value";
|
valueNameCopy = "value";
|
||||||
testPVScalarArray(pvDouble,valueNameMaster,valueNameCopy,pvMaster,pvCopy);
|
testPVScalarArray(pvDouble,valueNameMaster,valueNameCopy,pvMaster,pvCopy);
|
||||||
@@ -261,7 +261,7 @@ static void arrayTest()
|
|||||||
valueNameMaster = "value";
|
valueNameMaster = "value";
|
||||||
pvRequest = createRequest->createRequest(request);
|
pvRequest = createRequest->createRequest(request);
|
||||||
if(debug) { cout << "request " << request << endl; }
|
if(debug) { cout << "request " << request << endl; }
|
||||||
if(debug) { cout << "pvRequest\n" << pvRequest->dumpValue(cout) << endl; }
|
if(debug) { cout << "pvRequest\n" << *pvRequest << endl; }
|
||||||
pvCopy = PVCopy::create(pvMaster,pvRequest,"");
|
pvCopy = PVCopy::create(pvMaster,pvRequest,"");
|
||||||
valueNameCopy = "value";
|
valueNameCopy = "value";
|
||||||
testPVScalarArray(pvDouble,valueNameMaster,valueNameCopy,pvMaster,pvCopy);
|
testPVScalarArray(pvDouble,valueNameMaster,valueNameCopy,pvMaster,pvCopy);
|
||||||
@@ -269,7 +269,7 @@ static void arrayTest()
|
|||||||
valueNameMaster = "value";
|
valueNameMaster = "value";
|
||||||
pvRequest = createRequest->createRequest(request);
|
pvRequest = createRequest->createRequest(request);
|
||||||
if(debug) { cout << "request " << request << endl; }
|
if(debug) { cout << "request " << request << endl; }
|
||||||
if(debug) { cout << "pvRequest\n" << pvRequest->dumpValue(cout) << endl; }
|
if(debug) { cout << "pvRequest\n" << *pvRequest << endl; }
|
||||||
pvCopy = PVCopy::create(pvMaster,pvRequest,"");
|
pvCopy = PVCopy::create(pvMaster,pvRequest,"");
|
||||||
valueNameCopy = "value";
|
valueNameCopy = "value";
|
||||||
testPVScalarArray(pvDouble,valueNameMaster,valueNameCopy,pvMaster,pvCopy);
|
testPVScalarArray(pvDouble,valueNameMaster,valueNameCopy,pvMaster,pvCopy);
|
||||||
@@ -320,7 +320,7 @@ static void powerSupplyTest()
|
|||||||
valueNameMaster = request = "power.value";
|
valueNameMaster = request = "power.value";
|
||||||
pvRequest = createRequest->createRequest(request);
|
pvRequest = createRequest->createRequest(request);
|
||||||
if(debug) { cout << "request " << request << endl; }
|
if(debug) { cout << "request " << request << endl; }
|
||||||
if(debug) { cout << "pvRequest\n" << pvRequest->dumpValue(cout) << endl; }
|
if(debug) { cout << "pvRequest\n" << *pvRequest << endl; }
|
||||||
pvCopy = PVCopy::create(pvMaster,pvRequest,"");
|
pvCopy = PVCopy::create(pvMaster,pvRequest,"");
|
||||||
valueNameCopy = "power.value";
|
valueNameCopy = "power.value";
|
||||||
testPVScalar(valueNameMaster,valueNameCopy,pvMaster,pvCopy);
|
testPVScalar(valueNameMaster,valueNameCopy,pvMaster,pvCopy);
|
||||||
@@ -328,7 +328,7 @@ static void powerSupplyTest()
|
|||||||
valueNameMaster = "power.value";
|
valueNameMaster = "power.value";
|
||||||
pvRequest = createRequest->createRequest(request);
|
pvRequest = createRequest->createRequest(request);
|
||||||
if(debug) { cout << "request " << request << endl; }
|
if(debug) { cout << "request " << request << endl; }
|
||||||
if(debug) { cout << "pvRequest\n" << pvRequest->dumpValue(cout) << endl; }
|
if(debug) { cout << "pvRequest\n" << *pvRequest << endl; }
|
||||||
pvCopy = PVCopy::create(pvMaster,pvRequest,"");
|
pvCopy = PVCopy::create(pvMaster,pvRequest,"");
|
||||||
valueNameCopy = "power.value";
|
valueNameCopy = "power.value";
|
||||||
testPVScalar(valueNameMaster,valueNameCopy,pvMaster,pvCopy);
|
testPVScalar(valueNameMaster,valueNameCopy,pvMaster,pvCopy);
|
||||||
@@ -336,7 +336,7 @@ static void powerSupplyTest()
|
|||||||
valueNameMaster = "power.value";
|
valueNameMaster = "power.value";
|
||||||
pvRequest = createRequest->createRequest(request);
|
pvRequest = createRequest->createRequest(request);
|
||||||
if(debug) { cout << "request " << request << endl; }
|
if(debug) { cout << "request " << request << endl; }
|
||||||
if(debug) { cout << "pvRequest\n" << pvRequest->dumpValue(cout) << endl; }
|
if(debug) { cout << "pvRequest\n" << *pvRequest << endl; }
|
||||||
pvCopy = PVCopy::create(pvMaster,pvRequest,"");
|
pvCopy = PVCopy::create(pvMaster,pvRequest,"");
|
||||||
valueNameCopy = "power.value";
|
valueNameCopy = "power.value";
|
||||||
testPVScalar(valueNameMaster,valueNameCopy,pvMaster,pvCopy);
|
testPVScalar(valueNameMaster,valueNameCopy,pvMaster,pvCopy);
|
||||||
@@ -344,7 +344,7 @@ static void powerSupplyTest()
|
|||||||
valueNameMaster = "power.value";
|
valueNameMaster = "power.value";
|
||||||
pvRequest = createRequest->createRequest(request);
|
pvRequest = createRequest->createRequest(request);
|
||||||
if(debug) { cout << "request " << request << endl; }
|
if(debug) { cout << "request " << request << endl; }
|
||||||
if(debug) { cout << "pvRequest\n" << pvRequest->dumpValue(cout) << endl; }
|
if(debug) { cout << "pvRequest\n" << *pvRequest << endl; }
|
||||||
pvCopy = PVCopy::create(pvMaster,pvRequest,"");
|
pvCopy = PVCopy::create(pvMaster,pvRequest,"");
|
||||||
valueNameCopy = "power.value";
|
valueNameCopy = "power.value";
|
||||||
testPVScalar(valueNameMaster,valueNameCopy,pvMaster,pvCopy);
|
testPVScalar(valueNameMaster,valueNameCopy,pvMaster,pvCopy);
|
||||||
|
|||||||
@@ -1,63 +1,66 @@
|
|||||||
TOP=../..
|
# This is a Makefile fragment, see ../Makefile
|
||||||
|
|
||||||
include $(TOP)/configure/CONFIG
|
SRC_DIRS += $(PVDATA_TEST)/misc
|
||||||
|
|
||||||
PROD_LIBS += pvData Com
|
TESTPROD_HOST += testThread
|
||||||
|
|
||||||
PROD_HOST += testThread
|
|
||||||
testThread_SRCS += testThread.cpp
|
testThread_SRCS += testThread.cpp
|
||||||
|
testHarness_SRCS += testThread.cpp
|
||||||
TESTS += testThread
|
TESTS += testThread
|
||||||
|
|
||||||
PROD_HOST += testTimer
|
TESTPROD_HOST += testTimer
|
||||||
testTimer_SRCS += testTimer.cpp
|
testTimer_SRCS += testTimer.cpp
|
||||||
|
testHarness_SRCS += testTimer.cpp
|
||||||
TESTS += testTimer
|
TESTS += testTimer
|
||||||
|
|
||||||
PROD_HOST += testBitSet
|
TESTPROD_HOST += testBitSet
|
||||||
testBitSet_SRCS += testBitSet.cpp
|
testBitSet_SRCS += testBitSet.cpp
|
||||||
|
testHarness_SRCS += testBitSet.cpp
|
||||||
TESTS += testBitSet
|
TESTS += testBitSet
|
||||||
|
|
||||||
PROD_HOST += testOverrunBitSet
|
TESTPROD_HOST += testOverrunBitSet
|
||||||
testOverrunBitSet_SRCS += testOverrunBitSet.cpp
|
testOverrunBitSet_SRCS += testOverrunBitSet.cpp
|
||||||
|
testHarness_SRCS += testOverrunBitSet.cpp
|
||||||
TESTS += testOverrunBitSet
|
TESTS += testOverrunBitSet
|
||||||
|
|
||||||
PROD_HOST += testByteOrder
|
TESTPROD_HOST += testByteOrder
|
||||||
testByteOrder_SRCS += testByteOrder.cpp
|
testByteOrder_SRCS += testByteOrder.cpp
|
||||||
|
|
||||||
PROD_HOST += testByteBuffer
|
TESTPROD_HOST += testByteBuffer
|
||||||
testByteBuffer_SRCS += testByteBuffer.cpp
|
testByteBuffer_SRCS += testByteBuffer.cpp
|
||||||
|
testHarness_SRCS += testByteBuffer.cpp
|
||||||
TESTS += testByteBuffer
|
TESTS += testByteBuffer
|
||||||
|
|
||||||
PROD_HOST += testBaseException
|
TESTPROD_HOST += testBaseException
|
||||||
testBaseException_SRCS += testBaseException.cpp
|
testBaseException_SRCS += testBaseException.cpp
|
||||||
|
testHarness_SRCS += testBaseException.cpp
|
||||||
TESTS += testBaseException
|
TESTS += testBaseException
|
||||||
|
|
||||||
PROD_HOST += testSharedVector
|
TESTPROD_HOST += testSharedVector
|
||||||
testSharedVector_SRCS += testSharedVector.cpp
|
testSharedVector_SRCS += testSharedVector.cpp
|
||||||
|
testHarness_SRCS += testSharedVector.cpp
|
||||||
TESTS += testSharedVector
|
TESTS += testSharedVector
|
||||||
|
|
||||||
PROD_HOST += testSerialization
|
TESTPROD_HOST += testSerialization
|
||||||
testSerialization_SRCS += testSerialization.cpp
|
testSerialization_SRCS += testSerialization.cpp
|
||||||
|
testHarness_SRCS += testSerialization.cpp
|
||||||
TESTS += testSerialization
|
TESTS += testSerialization
|
||||||
|
|
||||||
PROD_HOST += testTimeStamp
|
TESTPROD_HOST += testTimeStamp
|
||||||
testTimeStamp_SRCS += testTimeStamp.cpp
|
testTimeStamp_SRCS += testTimeStamp.cpp
|
||||||
|
testHarness_SRCS += testTimeStamp.cpp
|
||||||
TESTS += testTimeStamp
|
TESTS += testTimeStamp
|
||||||
|
|
||||||
PROD_HOST += testQueue
|
TESTPROD_HOST += testQueue
|
||||||
testQueue_SRCS += testQueue.cpp
|
testQueue_SRCS += testQueue.cpp
|
||||||
|
testHarness_SRCS += testQueue.cpp
|
||||||
TESTS += testQueue
|
TESTS += testQueue
|
||||||
|
|
||||||
PROD_HOST += testMessageQueue
|
TESTPROD_HOST += testMessageQueue
|
||||||
testMessageQueue_SRCS += testMessageQueue.cpp
|
testMessageQueue_SRCS += testMessageQueue.cpp
|
||||||
|
testHarness_SRCS += testMessageQueue.cpp
|
||||||
TESTS += testMessageQueue
|
TESTS += testMessageQueue
|
||||||
|
|
||||||
PROD_HOST += testTypeCast
|
TESTPROD_HOST += testTypeCast
|
||||||
testTypeCast_SRCS += testTypeCast.cpp
|
testTypeCast_SRCS += testTypeCast.cpp
|
||||||
|
testHarness_SRCS += testTypeCast.cpp
|
||||||
TESTS += testTypeCast
|
TESTS += testTypeCast
|
||||||
|
|
||||||
TESTSCRIPTS_HOST += $(TESTS:%=%.t)
|
|
||||||
|
|
||||||
include $(TOP)/configure/RULES
|
|
||||||
#----------------------------------------
|
|
||||||
# ADD RULES AFTER THIS LINE
|
|
||||||
|
|
||||||
|
|||||||
@@ -42,7 +42,7 @@ void internalTestBaseException(int /*unused*/ = 0)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void testBaseException() {
|
void testBaseExceptionTest() {
|
||||||
printf("testBaseException... ");
|
printf("testBaseException... ");
|
||||||
|
|
||||||
try {
|
try {
|
||||||
@@ -86,7 +86,7 @@ MAIN(testBaseException)
|
|||||||
testPlan(2);
|
testPlan(2);
|
||||||
testDiag("Tests base exception");
|
testDiag("Tests base exception");
|
||||||
testLogicException();
|
testLogicException();
|
||||||
testBaseException();
|
testBaseExceptionTest();
|
||||||
return testDone();
|
return testDone();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,7 +1,8 @@
|
|||||||
|
#include <testMain.h>
|
||||||
#include <epicsEndian.h>
|
#include <epicsEndian.h>
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
|
|
||||||
int main()
|
MAIN(testByteOrder)
|
||||||
{
|
{
|
||||||
printf("EPICS_BYTE_ORDER: %s\n", (EPICS_BYTE_ORDER == EPICS_ENDIAN_LITTLE) ? "little" : "big");
|
printf("EPICS_BYTE_ORDER: %s\n", (EPICS_BYTE_ORDER == EPICS_ENDIAN_LITTLE) ? "little" : "big");
|
||||||
printf("EPICS_FLOAT_WORD_ORDER: %s\n", (EPICS_FLOAT_WORD_ORDER == EPICS_ENDIAN_LITTLE) ? "little" : "big");
|
printf("EPICS_FLOAT_WORD_ORDER: %s\n", (EPICS_FLOAT_WORD_ORDER == EPICS_ENDIAN_LITTLE) ? "little" : "big");
|
||||||
|
|||||||
@@ -41,11 +41,11 @@ void test()
|
|||||||
uint32 messageOffset = (uint32) pvMessage->getFieldOffset();
|
uint32 messageOffset = (uint32) pvMessage->getFieldOffset();
|
||||||
PVStructurePtr pvTimeStamp = pvStructure->getStructureField("timeStamp");
|
PVStructurePtr pvTimeStamp = pvStructure->getStructureField("timeStamp");
|
||||||
PVLongPtr pvSeconds = pvTimeStamp->getLongField("secondsPastEpoch");
|
PVLongPtr pvSeconds = pvTimeStamp->getLongField("secondsPastEpoch");
|
||||||
PVIntPtr pvNanoSeconds = pvTimeStamp->getIntField("nanoSeconds");
|
PVIntPtr pvNanoseconds = pvTimeStamp->getIntField("nanoseconds");
|
||||||
PVIntPtr pvUserTag = pvTimeStamp->getIntField("userTag");
|
PVIntPtr pvUserTag = pvTimeStamp->getIntField("userTag");
|
||||||
uint32 timeStampOffset = (uint32) pvTimeStamp->getFieldOffset();
|
uint32 timeStampOffset = (uint32) pvTimeStamp->getFieldOffset();
|
||||||
uint32 secondsOffset = (uint32) pvSeconds->getFieldOffset();
|
uint32 secondsOffset = (uint32) pvSeconds->getFieldOffset();
|
||||||
uint32 nanoSecondsOffset = (uint32) pvNanoSeconds->getFieldOffset();
|
uint32 nanosecondsOffset = (uint32) pvNanoseconds->getFieldOffset();
|
||||||
uint32 userTagOffset = (uint32) pvUserTag->getFieldOffset();
|
uint32 userTagOffset = (uint32) pvUserTag->getFieldOffset();
|
||||||
uint32 nfields = (uint32) pvStructure->getNumberFields();
|
uint32 nfields = (uint32) pvStructure->getNumberFields();
|
||||||
BitSetPtr changeBitSet = BitSet::create(nfields);
|
BitSetPtr changeBitSet = BitSet::create(nfields);
|
||||||
@@ -55,7 +55,7 @@ void test()
|
|||||||
pvSeverity->put(2); changeBitSet->set(severityOffset);
|
pvSeverity->put(2); changeBitSet->set(severityOffset);
|
||||||
pvMessage->put("error"); changeBitSet->set(messageOffset);
|
pvMessage->put("error"); changeBitSet->set(messageOffset);
|
||||||
pvSeconds->put(1); changeBitSet->set(secondsOffset);
|
pvSeconds->put(1); changeBitSet->set(secondsOffset);
|
||||||
pvNanoSeconds->put(1000000); changeBitSet->set(nanoSecondsOffset);
|
pvNanoseconds->put(1000000); changeBitSet->set(nanosecondsOffset);
|
||||||
pvUserTag->put(1); changeBitSet->set(userTagOffset);
|
pvUserTag->put(1); changeBitSet->set(userTagOffset);
|
||||||
userOverrunBitSet->or_and(*changeBitSet.get(),*userChangeBitSet.get());
|
userOverrunBitSet->or_and(*changeBitSet.get(),*userChangeBitSet.get());
|
||||||
(*userChangeBitSet)|=(*changeBitSet.get());
|
(*userChangeBitSet)|=(*changeBitSet.get());
|
||||||
@@ -64,7 +64,7 @@ void test()
|
|||||||
pvSeverity->put(0); changeBitSet->set(severityOffset);
|
pvSeverity->put(0); changeBitSet->set(severityOffset);
|
||||||
pvMessage->put(""); changeBitSet->set(messageOffset);
|
pvMessage->put(""); changeBitSet->set(messageOffset);
|
||||||
pvSeconds->put(2); changeBitSet->set(secondsOffset);
|
pvSeconds->put(2); changeBitSet->set(secondsOffset);
|
||||||
pvNanoSeconds->put(0); changeBitSet->set(nanoSecondsOffset);
|
pvNanoseconds->put(0); changeBitSet->set(nanosecondsOffset);
|
||||||
pvUserTag->put(0); changeBitSet->set(userTagOffset);
|
pvUserTag->put(0); changeBitSet->set(userTagOffset);
|
||||||
userOverrunBitSet->or_and(*changeBitSet.get(),*userChangeBitSet.get());
|
userOverrunBitSet->or_and(*changeBitSet.get(),*userChangeBitSet.get());
|
||||||
(*userChangeBitSet)|=(*changeBitSet.get());
|
(*userChangeBitSet)|=(*changeBitSet.get());
|
||||||
@@ -73,14 +73,14 @@ void test()
|
|||||||
testOk1(userChangeBitSet->get(severityOffset));
|
testOk1(userChangeBitSet->get(severityOffset));
|
||||||
testOk1(userChangeBitSet->get(messageOffset));
|
testOk1(userChangeBitSet->get(messageOffset));
|
||||||
testOk1(userChangeBitSet->get(secondsOffset));
|
testOk1(userChangeBitSet->get(secondsOffset));
|
||||||
testOk1(userChangeBitSet->get(nanoSecondsOffset));
|
testOk1(userChangeBitSet->get(nanosecondsOffset));
|
||||||
testOk1(userChangeBitSet->get(userTagOffset));
|
testOk1(userChangeBitSet->get(userTagOffset));
|
||||||
testOk1(userOverrunBitSet->cardinality()==6);
|
testOk1(userOverrunBitSet->cardinality()==6);
|
||||||
testOk1(userOverrunBitSet->get(valueOffset));
|
testOk1(userOverrunBitSet->get(valueOffset));
|
||||||
testOk1(userOverrunBitSet->get(severityOffset));
|
testOk1(userOverrunBitSet->get(severityOffset));
|
||||||
testOk1(userOverrunBitSet->get(messageOffset));
|
testOk1(userOverrunBitSet->get(messageOffset));
|
||||||
testOk1(userOverrunBitSet->get(secondsOffset));
|
testOk1(userOverrunBitSet->get(secondsOffset));
|
||||||
testOk1(userOverrunBitSet->get(nanoSecondsOffset));
|
testOk1(userOverrunBitSet->get(nanosecondsOffset));
|
||||||
testOk1(userOverrunBitSet->get(userTagOffset));
|
testOk1(userOverrunBitSet->get(userTagOffset));
|
||||||
|
|
||||||
BitSetUtil::compress(userChangeBitSet,pvStructure);
|
BitSetUtil::compress(userChangeBitSet,pvStructure);
|
||||||
@@ -101,13 +101,13 @@ void test()
|
|||||||
userOverrunBitSet->clear();
|
userOverrunBitSet->clear();
|
||||||
pvValue->put(1.0); changeBitSet->set(valueOffset);
|
pvValue->put(1.0); changeBitSet->set(valueOffset);
|
||||||
pvSeconds->put(3); changeBitSet->set(secondsOffset);
|
pvSeconds->put(3); changeBitSet->set(secondsOffset);
|
||||||
pvNanoSeconds->put(0); changeBitSet->set(nanoSecondsOffset);
|
pvNanoseconds->put(0); changeBitSet->set(nanosecondsOffset);
|
||||||
userOverrunBitSet->or_and(*changeBitSet.get(),*userChangeBitSet.get());
|
userOverrunBitSet->or_and(*changeBitSet.get(),*userChangeBitSet.get());
|
||||||
(*userChangeBitSet)|=(*changeBitSet.get());
|
(*userChangeBitSet)|=(*changeBitSet.get());
|
||||||
testOk1(userChangeBitSet->cardinality()==3);
|
testOk1(userChangeBitSet->cardinality()==3);
|
||||||
testOk1(userChangeBitSet->get(valueOffset));
|
testOk1(userChangeBitSet->get(valueOffset));
|
||||||
testOk1(userChangeBitSet->get(secondsOffset));
|
testOk1(userChangeBitSet->get(secondsOffset));
|
||||||
testOk1(userChangeBitSet->get(nanoSecondsOffset));
|
testOk1(userChangeBitSet->get(nanosecondsOffset));
|
||||||
testOk1(userOverrunBitSet->cardinality()==0);
|
testOk1(userOverrunBitSet->cardinality()==0);
|
||||||
|
|
||||||
changeBitSet->clear();
|
changeBitSet->clear();
|
||||||
@@ -117,7 +117,7 @@ void test()
|
|||||||
testOk1(userChangeBitSet->cardinality()==3);
|
testOk1(userChangeBitSet->cardinality()==3);
|
||||||
testOk1(userChangeBitSet->get(valueOffset));
|
testOk1(userChangeBitSet->get(valueOffset));
|
||||||
testOk1(userChangeBitSet->get(secondsOffset));
|
testOk1(userChangeBitSet->get(secondsOffset));
|
||||||
testOk1(userChangeBitSet->get(nanoSecondsOffset));
|
testOk1(userChangeBitSet->get(nanosecondsOffset));
|
||||||
testOk1(userOverrunBitSet->cardinality()==1);
|
testOk1(userOverrunBitSet->cardinality()==1);
|
||||||
testOk1(userOverrunBitSet->get(valueOffset));
|
testOk1(userOverrunBitSet->get(valueOffset));
|
||||||
|
|
||||||
@@ -126,13 +126,13 @@ void test()
|
|||||||
testOk1(userChangeBitSet->cardinality()==3);
|
testOk1(userChangeBitSet->cardinality()==3);
|
||||||
testOk1(userChangeBitSet->get(valueOffset));
|
testOk1(userChangeBitSet->get(valueOffset));
|
||||||
testOk1(userChangeBitSet->get(secondsOffset));
|
testOk1(userChangeBitSet->get(secondsOffset));
|
||||||
testOk1(userChangeBitSet->get(nanoSecondsOffset));
|
testOk1(userChangeBitSet->get(nanosecondsOffset));
|
||||||
testOk1(userOverrunBitSet->cardinality()==1);
|
testOk1(userOverrunBitSet->cardinality()==1);
|
||||||
testOk1(userOverrunBitSet->get(valueOffset));
|
testOk1(userOverrunBitSet->get(valueOffset));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
MAIN(testOverrunBitSet`)
|
MAIN(testOverrunBitSet)
|
||||||
{
|
{
|
||||||
testPlan(41);
|
testPlan(41);
|
||||||
testDiag("Tests for changeBitSet and overrunBitSet");
|
testDiag("Tests for changeBitSet and overrunBitSet");
|
||||||
|
|||||||
@@ -386,7 +386,7 @@ void testStructure() {
|
|||||||
testDiag("\tSimple structure serialization");
|
testDiag("\tSimple structure serialization");
|
||||||
PVStructurePtr pvStructure = factory->createPVStructure(getStandardField()->timeStamp());
|
PVStructurePtr pvStructure = factory->createPVStructure(getStandardField()->timeStamp());
|
||||||
pvStructure->getLongField("secondsPastEpoch")->put(123);
|
pvStructure->getLongField("secondsPastEpoch")->put(123);
|
||||||
pvStructure->getIntField("nanoSeconds")->put(456);
|
pvStructure->getIntField("nanoseconds")->put(456);
|
||||||
pvStructure->getIntField("userTag")->put(789);
|
pvStructure->getIntField("userTag")->put(789);
|
||||||
|
|
||||||
serializationTest(pvStructure);
|
serializationTest(pvStructure);
|
||||||
@@ -625,13 +625,13 @@ void testStructureId() {
|
|||||||
testOk1(structureWithNoId!=structure1);
|
testOk1(structureWithNoId!=structure1);
|
||||||
testOk1(structure1!=structure2);
|
testOk1(structure1!=structure2);
|
||||||
|
|
||||||
//serializationTest(structure1);
|
//serializationFieldTest(structure1);
|
||||||
|
|
||||||
PVStructurePtr pvStructure = getPVDataCreate()->createPVStructure(structure1);
|
PVStructurePtr pvStructure = getPVDataCreate()->createPVStructure(structure1);
|
||||||
serializationTest(pvStructure);
|
serializationTest(pvStructure);
|
||||||
}
|
}
|
||||||
|
|
||||||
void serializatioTest(FieldConstPtr const & field)
|
void serializationFieldTest(FieldConstPtr const & field)
|
||||||
{
|
{
|
||||||
buffer->clear();
|
buffer->clear();
|
||||||
|
|
||||||
@@ -660,27 +660,27 @@ void testIntrospectionSerialization()
|
|||||||
ScalarType scalarType = static_cast<ScalarType>(i);
|
ScalarType scalarType = static_cast<ScalarType>(i);
|
||||||
|
|
||||||
ScalarConstPtr scalar = factory->createScalar(scalarType);
|
ScalarConstPtr scalar = factory->createScalar(scalarType);
|
||||||
serializatioTest(scalar);
|
serializationFieldTest(scalar);
|
||||||
|
|
||||||
ScalarArrayConstPtr array = factory->createScalarArray(scalarType);
|
ScalarArrayConstPtr array = factory->createScalarArray(scalarType);
|
||||||
serializatioTest(array);
|
serializationFieldTest(array);
|
||||||
}
|
}
|
||||||
|
|
||||||
// and a structure
|
// and a structure
|
||||||
StructureConstPtr structure = getStandardField()->timeStamp();
|
StructureConstPtr structure = getStandardField()->timeStamp();
|
||||||
serializatioTest(structure);
|
serializationFieldTest(structure);
|
||||||
|
|
||||||
// and a structure array
|
// and a structure array
|
||||||
StructureArrayConstPtr structureArray = factory->createStructureArray(structure);
|
StructureArrayConstPtr structureArray = factory->createStructureArray(structure);
|
||||||
serializatioTest(structureArray);
|
serializationFieldTest(structureArray);
|
||||||
|
|
||||||
// variant union
|
// variant union
|
||||||
UnionConstPtr variant = factory->createVariantUnion();
|
UnionConstPtr variant = factory->createVariantUnion();
|
||||||
serializatioTest(variant);
|
serializationFieldTest(variant);
|
||||||
|
|
||||||
// variant array union
|
// variant array union
|
||||||
UnionArrayConstPtr variantArray = factory->createVariantUnionArray();
|
UnionArrayConstPtr variantArray = factory->createVariantUnionArray();
|
||||||
serializatioTest(variantArray);
|
serializationFieldTest(variantArray);
|
||||||
|
|
||||||
// union
|
// union
|
||||||
UnionConstPtr punion = factory->createFieldBuilder()->
|
UnionConstPtr punion = factory->createFieldBuilder()->
|
||||||
@@ -692,11 +692,66 @@ void testIntrospectionSerialization()
|
|||||||
endNested()->
|
endNested()->
|
||||||
addArray("intArray", pvInt)->
|
addArray("intArray", pvInt)->
|
||||||
createUnion();
|
createUnion();
|
||||||
serializatioTest(punion);
|
serializationFieldTest(punion);
|
||||||
|
|
||||||
// union array
|
// union array
|
||||||
UnionArrayConstPtr punionArray = factory->createUnionArray(punion);
|
UnionArrayConstPtr punionArray = factory->createUnionArray(punion);
|
||||||
serializatioTest(punionArray);
|
serializationFieldTest(punionArray);
|
||||||
|
}
|
||||||
|
|
||||||
|
void testArraySizeType() {
|
||||||
|
testDiag("Testing array size types...");
|
||||||
|
|
||||||
|
FieldCreatePtr fieldCreate = getFieldCreate();
|
||||||
|
|
||||||
|
StructureConstPtr s = fieldCreate->createFieldBuilder()->
|
||||||
|
addArray("variableArray", pvDouble)->
|
||||||
|
addFixedArray("fixedArray", pvDouble, 10)->
|
||||||
|
addBoundedArray("boundedArray", pvDouble, 1024)->
|
||||||
|
createStructure();
|
||||||
|
testOk1(s.get() != 0);
|
||||||
|
testOk1(Structure::DEFAULT_ID == s->getID());
|
||||||
|
testOk1(3 == s->getFields().size());
|
||||||
|
|
||||||
|
serializationFieldTest(s);
|
||||||
|
|
||||||
|
PVStructurePtr pvs = getPVDataCreate()->createPVStructure(s);
|
||||||
|
PVDoubleArray::shared_pointer pvDA = pvs->getSubField<PVDoubleArray>("fixedArray");
|
||||||
|
PVDoubleArray::svector vec(10, 42);
|
||||||
|
pvDA->replace(freeze(vec));
|
||||||
|
serializationTest(pvs);
|
||||||
|
}
|
||||||
|
|
||||||
|
void testBoundedString() {
|
||||||
|
testDiag("Testing bounded string...");
|
||||||
|
|
||||||
|
FieldCreatePtr fieldCreate = getFieldCreate();
|
||||||
|
|
||||||
|
StructureConstPtr s = fieldCreate->createFieldBuilder()->
|
||||||
|
add("str", pvString)->
|
||||||
|
addBoundedString("boundedStr", 8)->
|
||||||
|
add("scalar", pvDouble)->
|
||||||
|
createStructure();
|
||||||
|
testOk1(s.get() != 0);
|
||||||
|
testOk1(Structure::DEFAULT_ID == s->getID());
|
||||||
|
testOk1(3 == s->getFields().size());
|
||||||
|
|
||||||
|
serializationFieldTest(s);
|
||||||
|
PVStructurePtr pvs = getPVDataCreate()->createPVStructure(s);
|
||||||
|
serializationTest(pvs);
|
||||||
|
|
||||||
|
PVStringPtr pvStr = pvs->getSubField<PVString>("boundedStr");
|
||||||
|
pvStr->put("");
|
||||||
|
pvStr->put("small");
|
||||||
|
pvStr->put("exact123");
|
||||||
|
|
||||||
|
try {
|
||||||
|
pvStr->put("tooLargeString");
|
||||||
|
testFail("too large string accepted");
|
||||||
|
} catch (std::overflow_error oe) {
|
||||||
|
// OK
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void testStringCopy() {
|
void testStringCopy() {
|
||||||
@@ -710,7 +765,7 @@ void testStringCopy() {
|
|||||||
|
|
||||||
MAIN(testSerialization) {
|
MAIN(testSerialization) {
|
||||||
|
|
||||||
testPlan(213);
|
testPlan(226);
|
||||||
|
|
||||||
flusher = new SerializableControlImpl();
|
flusher = new SerializableControlImpl();
|
||||||
control = new DeserializableControlImpl();
|
control = new DeserializableControlImpl();
|
||||||
@@ -724,16 +779,19 @@ MAIN(testSerialization) {
|
|||||||
testScalar();
|
testScalar();
|
||||||
testArray();
|
testArray();
|
||||||
testStructure();
|
testStructure();
|
||||||
|
testStructureId();
|
||||||
testStructureArray();
|
testStructureArray();
|
||||||
|
|
||||||
testUnion();
|
testUnion();
|
||||||
|
|
||||||
|
testArraySizeType();
|
||||||
|
testBoundedString();
|
||||||
|
|
||||||
|
|
||||||
delete buffer;
|
delete buffer;
|
||||||
delete control;
|
delete control;
|
||||||
delete flusher;
|
delete flusher;
|
||||||
|
|
||||||
epicsExitCallAtExits();
|
|
||||||
return testDone();
|
return testDone();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -19,11 +19,12 @@
|
|||||||
#include "pv/sharedVector.h"
|
#include "pv/sharedVector.h"
|
||||||
|
|
||||||
using std::string;
|
using std::string;
|
||||||
|
using namespace epics::pvData;
|
||||||
|
|
||||||
static void testEmpty()
|
static void testEmpty()
|
||||||
{
|
{
|
||||||
testDiag("Test empty vector");
|
testDiag("Test empty vector");
|
||||||
epics::pvData::shared_vector<int> empty, empty2;
|
epics::pvData::shared_vector<int32> empty, empty2;
|
||||||
|
|
||||||
testOk1(empty.size()==0);
|
testOk1(empty.size()==0);
|
||||||
testOk1(empty.empty());
|
testOk1(empty.empty());
|
||||||
@@ -42,7 +43,7 @@ static void testInternalAlloc()
|
|||||||
{
|
{
|
||||||
testDiag("Test vector alloc w/ new[]");
|
testDiag("Test vector alloc w/ new[]");
|
||||||
|
|
||||||
epics::pvData::shared_vector<int> internal(5);
|
epics::pvData::shared_vector<int32> internal(5);
|
||||||
|
|
||||||
testOk1(internal.size()==5);
|
testOk1(internal.size()==5);
|
||||||
testOk1(!internal.empty());
|
testOk1(!internal.empty());
|
||||||
@@ -57,7 +58,7 @@ static void testInternalAlloc()
|
|||||||
internal[2] = 42;
|
internal[2] = 42;
|
||||||
testOk1(internal[2]==42);
|
testOk1(internal[2]==42);
|
||||||
|
|
||||||
epics::pvData::shared_vector<int> internal2(15, 500);
|
epics::pvData::shared_vector<int32> internal2(15, 500);
|
||||||
|
|
||||||
testOk1(internal2.size()==15);
|
testOk1(internal2.size()==15);
|
||||||
testOk1(internal2[1]==500);
|
testOk1(internal2[1]==500);
|
||||||
@@ -79,8 +80,8 @@ namespace {
|
|||||||
//Note: STL shared_ptr requires that deletors be copy constructable
|
//Note: STL shared_ptr requires that deletors be copy constructable
|
||||||
template<typename E>
|
template<typename E>
|
||||||
struct callCounter {
|
struct callCounter {
|
||||||
std::tr1::shared_ptr<int> count;
|
std::tr1::shared_ptr<int32> count;
|
||||||
callCounter():count(new int){*count=0;}
|
callCounter():count(new int32){*count=0;}
|
||||||
callCounter(const callCounter& o):count(o.count) {};
|
callCounter(const callCounter& o):count(o.count) {};
|
||||||
callCounter& operator=(const callCounter& o){count=o.count;}
|
callCounter& operator=(const callCounter& o){count=o.count;}
|
||||||
void operator()(E){*count=1;}
|
void operator()(E){*count=1;}
|
||||||
@@ -92,8 +93,8 @@ static void testExternalAlloc()
|
|||||||
testDiag("Test vector external alloc");
|
testDiag("Test vector external alloc");
|
||||||
|
|
||||||
// Simulate a failed malloc() or similar
|
// Simulate a failed malloc() or similar
|
||||||
int *oops=0;
|
int32 *oops=0;
|
||||||
epics::pvData::shared_vector<int> nullPtr(oops, 42, 100);
|
epics::pvData::shared_vector<int32> nullPtr(oops, 42, 100);
|
||||||
|
|
||||||
testOk1(nullPtr.size()==0);
|
testOk1(nullPtr.size()==0);
|
||||||
testOk1(nullPtr.empty());
|
testOk1(nullPtr.empty());
|
||||||
@@ -102,8 +103,8 @@ static void testExternalAlloc()
|
|||||||
|
|
||||||
testOk1(nullPtr.data()==NULL);
|
testOk1(nullPtr.data()==NULL);
|
||||||
|
|
||||||
int *raw=new int[5];
|
int32 *raw=new int32[5];
|
||||||
epics::pvData::shared_vector<int> newData(raw, 1, 4);
|
epics::pvData::shared_vector<int32> newData(raw, 1, 4);
|
||||||
|
|
||||||
testOk1(newData.size()==4);
|
testOk1(newData.size()==4);
|
||||||
testOk1(!newData.empty());
|
testOk1(!newData.empty());
|
||||||
@@ -113,11 +114,11 @@ static void testExternalAlloc()
|
|||||||
testOk1(newData[0]==14);
|
testOk1(newData[0]==14);
|
||||||
|
|
||||||
// Check use of custom deleter
|
// Check use of custom deleter
|
||||||
int localVar[4] = {1,2,3,4};
|
int32 localVar[4] = {1,2,3,4};
|
||||||
callCounter<int*> tracker;
|
callCounter<int32*> tracker;
|
||||||
testOk1(*tracker.count==0);
|
testOk1(*tracker.count==0);
|
||||||
|
|
||||||
epics::pvData::shared_vector<int> locvar(localVar,
|
epics::pvData::shared_vector<int32> locvar(localVar,
|
||||||
tracker,
|
tracker,
|
||||||
0, 4);
|
0, 4);
|
||||||
|
|
||||||
@@ -137,8 +138,8 @@ static void testShare()
|
|||||||
{
|
{
|
||||||
testDiag("Test vector Sharing");
|
testDiag("Test vector Sharing");
|
||||||
|
|
||||||
epics::pvData::shared_vector<int> one, two(15);
|
epics::pvData::shared_vector<int32> one, two(15);
|
||||||
epics::pvData::shared_vector<int> three(two);
|
epics::pvData::shared_vector<int32> three(two);
|
||||||
|
|
||||||
testOk1(one.unique());
|
testOk1(one.unique());
|
||||||
testOk1(!two.unique());
|
testOk1(!two.unique());
|
||||||
@@ -199,22 +200,22 @@ static void testConst()
|
|||||||
{
|
{
|
||||||
testDiag("Test constant vector");
|
testDiag("Test constant vector");
|
||||||
|
|
||||||
epics::pvData::shared_vector<int> writable(15, 100);
|
epics::pvData::shared_vector<int32> writable(15, 100);
|
||||||
|
|
||||||
epics::pvData::shared_vector<int>::reference wr = writable[0];
|
epics::pvData::shared_vector<int32>::reference wr = writable[0];
|
||||||
epics::pvData::shared_vector<int>::const_reference ror = writable[0];
|
epics::pvData::shared_vector<int32>::const_reference ror = writable[0];
|
||||||
|
|
||||||
testOk1(wr==ror);
|
testOk1(wr==ror);
|
||||||
|
|
||||||
int *compare = writable.data();
|
int32 *compare = writable.data();
|
||||||
|
|
||||||
testOk1(writable.unique());
|
testOk1(writable.unique());
|
||||||
|
|
||||||
// can re-target container, but data is R/O
|
// can re-target container, but data is R/O
|
||||||
epics::pvData::shared_vector<const int> rodata(freeze(writable));
|
epics::pvData::shared_vector<const int32> rodata(freeze(writable));
|
||||||
|
|
||||||
epics::pvData::shared_vector<const int>::reference wcr = rodata[0];
|
epics::pvData::shared_vector<const int32>::reference wcr = rodata[0];
|
||||||
epics::pvData::shared_vector<const int>::const_reference rocr = rodata[0];
|
epics::pvData::shared_vector<const int32>::const_reference rocr = rodata[0];
|
||||||
|
|
||||||
testOk1(wcr==rocr);
|
testOk1(wcr==rocr);
|
||||||
|
|
||||||
@@ -227,7 +228,7 @@ static void testConst()
|
|||||||
|
|
||||||
testOk1(rodata.data()==compare);
|
testOk1(rodata.data()==compare);
|
||||||
|
|
||||||
epics::pvData::shared_vector<const int> rodata2(rodata);
|
epics::pvData::shared_vector<const int32> rodata2(rodata);
|
||||||
|
|
||||||
testOk1(rodata.data()==rodata2.data());
|
testOk1(rodata.data()==rodata2.data());
|
||||||
|
|
||||||
@@ -240,9 +241,9 @@ static void testSlice()
|
|||||||
{
|
{
|
||||||
testDiag("Test vector slicing");
|
testDiag("Test vector slicing");
|
||||||
|
|
||||||
epics::pvData::shared_vector<int> original(10, 100);
|
epics::pvData::shared_vector<int32> original(10, 100);
|
||||||
|
|
||||||
epics::pvData::shared_vector<int> half1(original), half2(original), half2a(original);
|
epics::pvData::shared_vector<int32> half1(original), half2(original), half2a(original);
|
||||||
|
|
||||||
half1.slice(0, 5);
|
half1.slice(0, 5);
|
||||||
half2.slice(5, 5);
|
half2.slice(5, 5);
|
||||||
@@ -290,9 +291,9 @@ static void testCapacity()
|
|||||||
{
|
{
|
||||||
testDiag("Test vector capacity");
|
testDiag("Test vector capacity");
|
||||||
|
|
||||||
epics::pvData::shared_vector<int> vect(10, 100);
|
epics::pvData::shared_vector<int32> vect(10, 100);
|
||||||
|
|
||||||
int *peek = vect.dataPtr().get();
|
int32 *peek = vect.dataPtr().get();
|
||||||
|
|
||||||
vect.slice(0, 5);
|
vect.slice(0, 5);
|
||||||
|
|
||||||
@@ -330,7 +331,7 @@ static void testCapacity()
|
|||||||
|
|
||||||
static void testPush()
|
static void testPush()
|
||||||
{
|
{
|
||||||
epics::pvData::shared_vector<int> vect;
|
epics::pvData::shared_vector<int32> vect;
|
||||||
|
|
||||||
testDiag("Test push_back optimizations");
|
testDiag("Test push_back optimizations");
|
||||||
|
|
||||||
@@ -357,7 +358,7 @@ static void testVoid()
|
|||||||
{
|
{
|
||||||
testDiag("Test vecter cast to/from void");
|
testDiag("Test vecter cast to/from void");
|
||||||
|
|
||||||
epics::pvData::shared_vector<int> typed(4);
|
epics::pvData::shared_vector<int32> typed(4);
|
||||||
|
|
||||||
epics::pvData::shared_vector<void> untyped2(epics::pvData::static_shared_vector_cast<void>(typed));
|
epics::pvData::shared_vector<void> untyped2(epics::pvData::static_shared_vector_cast<void>(typed));
|
||||||
|
|
||||||
@@ -366,7 +367,7 @@ static void testVoid()
|
|||||||
|
|
||||||
untyped2.slice(sizeof(int), 2*sizeof(int));
|
untyped2.slice(sizeof(int), 2*sizeof(int));
|
||||||
|
|
||||||
typed = epics::pvData::static_shared_vector_cast<int>(untyped2);
|
typed = epics::pvData::static_shared_vector_cast<int32>(untyped2);
|
||||||
|
|
||||||
testOk1(typed.dataOffset()==1);
|
testOk1(typed.dataOffset()==1);
|
||||||
testOk1(typed.size()==2);
|
testOk1(typed.size()==2);
|
||||||
@@ -406,7 +407,7 @@ static void testVectorConvert()
|
|||||||
{
|
{
|
||||||
testDiag("Test shared_vector_convert");
|
testDiag("Test shared_vector_convert");
|
||||||
|
|
||||||
epics::pvData::shared_vector<int> ints(6, 42), moreints;
|
epics::pvData::shared_vector<int32> ints(6, 42), moreints;
|
||||||
epics::pvData::shared_vector<float> floats;
|
epics::pvData::shared_vector<float> floats;
|
||||||
epics::pvData::shared_vector<string> strings;
|
epics::pvData::shared_vector<string> strings;
|
||||||
epics::pvData::shared_vector<void> voids;
|
epics::pvData::shared_vector<void> voids;
|
||||||
@@ -414,7 +415,7 @@ static void testVectorConvert()
|
|||||||
testOk1(ints.unique());
|
testOk1(ints.unique());
|
||||||
|
|
||||||
// no-op convert. Just returns another reference
|
// no-op convert. Just returns another reference
|
||||||
moreints = epics::pvData::shared_vector_convert<int>(ints);
|
moreints = epics::pvData::shared_vector_convert<int32>(ints);
|
||||||
|
|
||||||
testOk1(!ints.unique());
|
testOk1(!ints.unique());
|
||||||
moreints.clear();
|
moreints.clear();
|
||||||
@@ -432,11 +433,12 @@ static void testVectorConvert()
|
|||||||
voids = epics::pvData::shared_vector_convert<void>(ints);
|
voids = epics::pvData::shared_vector_convert<void>(ints);
|
||||||
|
|
||||||
testOk1(!ints.unique());
|
testOk1(!ints.unique());
|
||||||
testOk1(voids.size()==ints.size()*sizeof(int));
|
testOk1(voids.size()==ints.size()*sizeof(int32));
|
||||||
|
|
||||||
// convert from void uses shared_vector<void>::original_type()
|
// convert from void uses shared_vector<void>::original_type()
|
||||||
// to find that the actual type is 'int'.
|
// to find that the actual type is 'int32'.
|
||||||
// returns a new vector
|
// returns a new vector
|
||||||
|
testOk1(voids.original_type()==epics::pvData::pvInt);
|
||||||
strings = epics::pvData::shared_vector_convert<string>(voids);
|
strings = epics::pvData::shared_vector_convert<string>(voids);
|
||||||
|
|
||||||
voids.clear();
|
voids.clear();
|
||||||
@@ -450,11 +452,11 @@ static void testWeak()
|
|||||||
{
|
{
|
||||||
testDiag("Test weak_ptr counting");
|
testDiag("Test weak_ptr counting");
|
||||||
|
|
||||||
epics::pvData::shared_vector<int> data(6);
|
epics::pvData::shared_vector<int32> data(6);
|
||||||
|
|
||||||
testOk1(data.unique());
|
testOk1(data.unique());
|
||||||
|
|
||||||
std::tr1::shared_ptr<int> pdata(data.dataPtr());
|
std::tr1::shared_ptr<int32> pdata(data.dataPtr());
|
||||||
|
|
||||||
testOk1(!data.unique());
|
testOk1(!data.unique());
|
||||||
|
|
||||||
@@ -462,7 +464,7 @@ static void testWeak()
|
|||||||
|
|
||||||
testOk1(data.unique());
|
testOk1(data.unique());
|
||||||
|
|
||||||
std::tr1::weak_ptr<int> wdata(data.dataPtr());
|
std::tr1::weak_ptr<int32> wdata(data.dataPtr());
|
||||||
|
|
||||||
testOk1(data.unique()); // True, but I wish it wasn't!!!
|
testOk1(data.unique()); // True, but I wish it wasn't!!!
|
||||||
|
|
||||||
@@ -475,10 +477,10 @@ static void testICE()
|
|||||||
{
|
{
|
||||||
testDiag("Test freeze and thaw");
|
testDiag("Test freeze and thaw");
|
||||||
|
|
||||||
epics::pvData::shared_vector<int> A(6, 42), C;
|
epics::pvData::shared_vector<int32> A(6, 42), C;
|
||||||
epics::pvData::shared_vector<const int> B, D;
|
epics::pvData::shared_vector<const int32> B, D;
|
||||||
|
|
||||||
int *check = A.data();
|
int32 *check = A.data();
|
||||||
|
|
||||||
// check freeze w/ unique reference
|
// check freeze w/ unique reference
|
||||||
|
|
||||||
@@ -537,11 +539,11 @@ static void testICE()
|
|||||||
|
|
||||||
MAIN(testSharedVector)
|
MAIN(testSharedVector)
|
||||||
{
|
{
|
||||||
testPlan(162);
|
testPlan(163);
|
||||||
testDiag("Tests for shared_vector");
|
testDiag("Tests for shared_vector");
|
||||||
|
|
||||||
testDiag("sizeof(shared_vector<int>)=%lu",
|
testDiag("sizeof(shared_vector<int32>)=%lu",
|
||||||
(unsigned long)sizeof(epics::pvData::shared_vector<int>));
|
(unsigned long)sizeof(epics::pvData::shared_vector<int32>));
|
||||||
|
|
||||||
testEmpty();
|
testEmpty();
|
||||||
testInternalAlloc();
|
testInternalAlloc();
|
||||||
|
|||||||
@@ -28,14 +28,14 @@ using namespace epics::pvData;
|
|||||||
|
|
||||||
static bool debug = false;
|
static bool debug = false;
|
||||||
|
|
||||||
void testTimeStamp()
|
void testTimeStampInternal()
|
||||||
{
|
{
|
||||||
testOk1(nanoSecPerSec==1000000000);
|
testOk1(nanoSecPerSec==1000000000);
|
||||||
TimeStamp current;
|
TimeStamp current;
|
||||||
current.getCurrent();
|
current.getCurrent();
|
||||||
printf("current %lli %i milliSec %lli\n",
|
printf("current %lli %i milliSec %lli\n",
|
||||||
(long long)current.getSecondsPastEpoch(),
|
(long long)current.getSecondsPastEpoch(),
|
||||||
current.getNanoSeconds(),
|
current.getNanoseconds(),
|
||||||
(long long)current.getMilliseconds());
|
(long long)current.getMilliseconds());
|
||||||
time_t tt;
|
time_t tt;
|
||||||
current.toTime_t(tt);
|
current.toTime_t(tt);
|
||||||
@@ -45,13 +45,13 @@ void testTimeStamp()
|
|||||||
"%4.4d.%2.2d.%2.2d %2.2d:%2.2d:%2.2d %d isDst %s\n",
|
"%4.4d.%2.2d.%2.2d %2.2d:%2.2d:%2.2d %d isDst %s\n",
|
||||||
ctm.tm_year+1900,ctm.tm_mon + 1,ctm.tm_mday,
|
ctm.tm_year+1900,ctm.tm_mon + 1,ctm.tm_mday,
|
||||||
ctm.tm_hour,ctm.tm_min,ctm.tm_sec,
|
ctm.tm_hour,ctm.tm_min,ctm.tm_sec,
|
||||||
current.getNanoSeconds(),
|
current.getNanoseconds(),
|
||||||
(ctm.tm_isdst==0) ? "false" : "true");
|
(ctm.tm_isdst==0) ? "false" : "true");
|
||||||
tt = time(&tt);
|
tt = time(&tt);
|
||||||
current.fromTime_t(tt);
|
current.fromTime_t(tt);
|
||||||
printf("fromTime_t\ncurrent %lli %i milliSec %lli\n",
|
printf("fromTime_t\ncurrent %lli %i milliSec %lli\n",
|
||||||
(long long)current.getSecondsPastEpoch(),
|
(long long)current.getSecondsPastEpoch(),
|
||||||
current.getNanoSeconds(),
|
current.getNanoseconds(),
|
||||||
(long long)current.getMilliseconds());
|
(long long)current.getMilliseconds());
|
||||||
current.toTime_t(tt);
|
current.toTime_t(tt);
|
||||||
memcpy(&ctm,localtime(&tt),sizeof(struct tm));
|
memcpy(&ctm,localtime(&tt),sizeof(struct tm));
|
||||||
@@ -59,12 +59,12 @@ void testTimeStamp()
|
|||||||
"%4.4d.%2.2d.%2.2d %2.2d:%2.2d:%2.2d %d isDst %s\n",
|
"%4.4d.%2.2d.%2.2d %2.2d:%2.2d:%2.2d %d isDst %s\n",
|
||||||
ctm.tm_year+1900,ctm.tm_mon + 1,ctm.tm_mday,
|
ctm.tm_year+1900,ctm.tm_mon + 1,ctm.tm_mday,
|
||||||
ctm.tm_hour,ctm.tm_min,ctm.tm_sec,
|
ctm.tm_hour,ctm.tm_min,ctm.tm_sec,
|
||||||
current.getNanoSeconds(),
|
current.getNanoseconds(),
|
||||||
(ctm.tm_isdst==0) ? "false" : "true");
|
(ctm.tm_isdst==0) ? "false" : "true");
|
||||||
TimeStamp right;
|
TimeStamp right;
|
||||||
TimeStamp left;
|
TimeStamp left;
|
||||||
right.put(current.getSecondsPastEpoch(),current.getNanoSeconds());
|
right.put(current.getSecondsPastEpoch(),current.getNanoseconds());
|
||||||
left.put(current.getSecondsPastEpoch(),current.getNanoSeconds());
|
left.put(current.getSecondsPastEpoch(),current.getNanoseconds());
|
||||||
double diff;
|
double diff;
|
||||||
diff = TimeStamp::diff(left,right);
|
diff = TimeStamp::diff(left,right);
|
||||||
if(debug) printf("diff %e\n",diff);
|
if(debug) printf("diff %e\n",diff);
|
||||||
@@ -75,7 +75,7 @@ void testTimeStamp()
|
|||||||
testOk1(!(left<right));
|
testOk1(!(left<right));
|
||||||
testOk1((left>=right));
|
testOk1((left>=right));
|
||||||
testOk1(!(left>right));
|
testOk1(!(left>right));
|
||||||
left.put(current.getSecondsPastEpoch()+1,current.getNanoSeconds());
|
left.put(current.getSecondsPastEpoch()+1,current.getNanoseconds());
|
||||||
diff = TimeStamp::diff(left,right);
|
diff = TimeStamp::diff(left,right);
|
||||||
if(debug) printf("diff %e\n",diff);
|
if(debug) printf("diff %e\n",diff);
|
||||||
testOk1(diff==1.0);
|
testOk1(diff==1.0);
|
||||||
@@ -85,7 +85,7 @@ void testTimeStamp()
|
|||||||
testOk1(!(left<right));
|
testOk1(!(left<right));
|
||||||
testOk1((left>=right));
|
testOk1((left>=right));
|
||||||
testOk1((left>right));
|
testOk1((left>right));
|
||||||
left.put(current.getSecondsPastEpoch()-1,current.getNanoSeconds());
|
left.put(current.getSecondsPastEpoch()-1,current.getNanoseconds());
|
||||||
diff = TimeStamp::diff(left,right);
|
diff = TimeStamp::diff(left,right);
|
||||||
if(debug) printf("diff %e\n",diff);
|
if(debug) printf("diff %e\n",diff);
|
||||||
testOk1(diff==-1.0);
|
testOk1(diff==-1.0);
|
||||||
@@ -95,7 +95,7 @@ void testTimeStamp()
|
|||||||
testOk1((left<right));
|
testOk1((left<right));
|
||||||
testOk1(!(left>=right));
|
testOk1(!(left>=right));
|
||||||
testOk1(!(left>right));
|
testOk1(!(left>right));
|
||||||
left.put(current.getSecondsPastEpoch(),current.getNanoSeconds()-nanoSecPerSec);
|
left.put(current.getSecondsPastEpoch(),current.getNanoseconds()-nanoSecPerSec);
|
||||||
diff = TimeStamp::diff(left,right);
|
diff = TimeStamp::diff(left,right);
|
||||||
if(debug) printf("diff %e\n",diff);
|
if(debug) printf("diff %e\n",diff);
|
||||||
testOk1(diff==-1.0);
|
testOk1(diff==-1.0);
|
||||||
@@ -105,7 +105,7 @@ void testTimeStamp()
|
|||||||
testOk1((left<right));
|
testOk1((left<right));
|
||||||
testOk1(!(left>=right));
|
testOk1(!(left>=right));
|
||||||
testOk1(!(left>right));
|
testOk1(!(left>right));
|
||||||
left.put(current.getSecondsPastEpoch(),current.getNanoSeconds()-1);
|
left.put(current.getSecondsPastEpoch(),current.getNanoseconds()-1);
|
||||||
diff = TimeStamp::diff(left,right);
|
diff = TimeStamp::diff(left,right);
|
||||||
if(debug) printf("diff %e\n",diff);
|
if(debug) printf("diff %e\n",diff);
|
||||||
testOk1(diff<0.0);
|
testOk1(diff<0.0);
|
||||||
@@ -115,11 +115,11 @@ void testTimeStamp()
|
|||||||
testOk1((left<right));
|
testOk1((left<right));
|
||||||
testOk1(!(left>=right));
|
testOk1(!(left>=right));
|
||||||
testOk1(!(left>right));
|
testOk1(!(left>right));
|
||||||
left.put(current.getSecondsPastEpoch(),current.getNanoSeconds());
|
left.put(current.getSecondsPastEpoch(),current.getNanoseconds());
|
||||||
left += .1;
|
left += .1;
|
||||||
diff = TimeStamp::diff(left,right);
|
diff = TimeStamp::diff(left,right);
|
||||||
if(debug) printf("diff %e\n",diff);
|
if(debug) printf("diff %e\n",diff);
|
||||||
left.put(current.getSecondsPastEpoch(),current.getNanoSeconds());
|
left.put(current.getSecondsPastEpoch(),current.getNanoseconds());
|
||||||
int64 inc = -1;
|
int64 inc = -1;
|
||||||
left += inc;
|
left += inc;
|
||||||
diff = TimeStamp::diff(left,right);
|
diff = TimeStamp::diff(left,right);
|
||||||
@@ -131,6 +131,6 @@ MAIN(testTimeStamp)
|
|||||||
{
|
{
|
||||||
testPlan(37);
|
testPlan(37);
|
||||||
testDiag("Tests timeStamp");
|
testDiag("Tests timeStamp");
|
||||||
testTimeStamp();
|
testTimeStampInternal();
|
||||||
return testDone();
|
return testDone();
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -37,11 +37,11 @@ namespace {
|
|||||||
};
|
};
|
||||||
template<>
|
template<>
|
||||||
struct testequal<double> {
|
struct testequal<double> {
|
||||||
static bool op(double A, double B) {return fabs(A-B)<1e-300; }
|
static bool op(double A, double B) {return fabs(A-B)<1e-15; }
|
||||||
};
|
};
|
||||||
template<>
|
template<>
|
||||||
struct testequal<float> {
|
struct testequal<float> {
|
||||||
static bool op(float A, float B) {return fabs(A-B)<1e-30; }
|
static bool op(float A, float B) {return fabs(A-B)<1e-7; }
|
||||||
};
|
};
|
||||||
|
|
||||||
template<typename TO, typename FROM>
|
template<typename TO, typename FROM>
|
||||||
@@ -117,7 +117,7 @@ namespace {
|
|||||||
|
|
||||||
MAIN(testTypeCast)
|
MAIN(testTypeCast)
|
||||||
{
|
{
|
||||||
testPlan(122);
|
testPlan(123);
|
||||||
|
|
||||||
try {
|
try {
|
||||||
|
|
||||||
@@ -387,7 +387,8 @@ try {
|
|||||||
FAIL(int8_t, string, "1000");
|
FAIL(int8_t, string, "1000");
|
||||||
FAIL(int8_t, string, "-1000");
|
FAIL(int8_t, string, "-1000");
|
||||||
|
|
||||||
FAIL(double, string, "1e+10000000");
|
FAIL(double, string, "1e+1000");
|
||||||
|
FAIL(double, string, "-1e+1000");
|
||||||
|
|
||||||
FAIL(epics::pvData::boolean, string, "hello");
|
FAIL(epics::pvData::boolean, string, "hello");
|
||||||
FAIL(epics::pvData::boolean, string, "1");
|
FAIL(epics::pvData::boolean, string, "1");
|
||||||
|
|||||||
@@ -1,16 +1,8 @@
|
|||||||
TOP=../..
|
# This is a Makefile fragment, see ../Makefile
|
||||||
|
|
||||||
include $(TOP)/configure/CONFIG
|
SRC_DIRS += $(PVDATA_TEST)/property
|
||||||
|
|
||||||
TESTPROD_HOST += testProperty
|
TESTPROD_HOST += testProperty
|
||||||
testProperty_SRCS += testProperty.cpp
|
testProperty_SRCS += testProperty.cpp
|
||||||
|
testHarness_SRCS += testProperty.cpp
|
||||||
TESTS += testProperty
|
TESTS += testProperty
|
||||||
|
|
||||||
testProperty_LIBS += pvData Com
|
|
||||||
|
|
||||||
TESTSCRIPTS_HOST += $(TESTS:%=%.t)
|
|
||||||
|
|
||||||
include $(TOP)/configure/RULES
|
|
||||||
#----------------------------------------
|
|
||||||
# ADD RULES AFTER THIS LINE
|
|
||||||
|
|
||||||
|
|||||||
@@ -48,11 +48,15 @@ static string allProperties("alarm,timeStamp,display,control");
|
|||||||
static PVStructurePtr doubleRecord;
|
static PVStructurePtr doubleRecord;
|
||||||
static PVStructurePtr enumeratedRecord;
|
static PVStructurePtr enumeratedRecord;
|
||||||
|
|
||||||
|
static void printRecords()
|
||||||
|
{
|
||||||
|
std::cout << "doubleRecord" << std::endl << *doubleRecord << std::endl;
|
||||||
|
std::cout << "enumeratedRecord" << std::endl << *enumeratedRecord << std::endl;
|
||||||
|
}
|
||||||
|
|
||||||
static void createRecords()
|
static void createRecords()
|
||||||
{
|
{
|
||||||
doubleRecord = standardPVField->scalar(pvDouble,allProperties);
|
doubleRecord = standardPVField->scalar(pvDouble,allProperties);
|
||||||
if(debug)
|
|
||||||
std::cout << "doubleRecord" << std::endl << *doubleRecord << std::endl;
|
|
||||||
StringArray choices;
|
StringArray choices;
|
||||||
choices.reserve(4);
|
choices.reserve(4);
|
||||||
choices.push_back("1");
|
choices.push_back("1");
|
||||||
@@ -60,14 +64,7 @@ static void createRecords()
|
|||||||
choices.push_back("3");
|
choices.push_back("3");
|
||||||
choices.push_back("4");
|
choices.push_back("4");
|
||||||
enumeratedRecord = standardPVField->enumerated(choices,alarmTimeStamp);
|
enumeratedRecord = standardPVField->enumerated(choices,alarmTimeStamp);
|
||||||
if(debug)
|
if(debug) printRecords();
|
||||||
std::cout << "enumeratedRecord" << std::endl << *doubleRecord << std::endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
static void printRecords()
|
|
||||||
{
|
|
||||||
std::cout << "doubleRecord" << std::endl << *doubleRecord << std::endl;
|
|
||||||
std::cout << "enumeratedRecord" << std::endl << *doubleRecord << std::endl;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static void testAlarm()
|
static void testAlarm()
|
||||||
@@ -123,7 +120,7 @@ static void testTimeStamp()
|
|||||||
testOk1(result);
|
testOk1(result);
|
||||||
pvTimeStamp.get(timeStamp);
|
pvTimeStamp.get(timeStamp);
|
||||||
testOk1(ts.getSecondsPastEpoch()==timeStamp.getSecondsPastEpoch());
|
testOk1(ts.getSecondsPastEpoch()==timeStamp.getSecondsPastEpoch());
|
||||||
testOk1(ts.getNanoSeconds()==timeStamp.getNanoSeconds());
|
testOk1(ts.getNanoseconds()==timeStamp.getNanoseconds());
|
||||||
testOk1(ts.getUserTag()==timeStamp.getUserTag());
|
testOk1(ts.getUserTag()==timeStamp.getUserTag());
|
||||||
time_t tt;
|
time_t tt;
|
||||||
timeStamp.toTime_t(tt);
|
timeStamp.toTime_t(tt);
|
||||||
@@ -131,10 +128,10 @@ static void testTimeStamp()
|
|||||||
memcpy(&ctm,localtime(&tt),sizeof(struct tm));
|
memcpy(&ctm,localtime(&tt),sizeof(struct tm));
|
||||||
if(debug) {
|
if(debug) {
|
||||||
printf(
|
printf(
|
||||||
"%4.4d.%2.2d.%2.2d %2.2d:%2.2d:%2.2d %d nanoSeconds isDst %s userTag %d\n",
|
"%4.4d.%2.2d.%2.2d %2.2d:%2.2d:%2.2d %d nanoseconds isDst %s userTag %d\n",
|
||||||
ctm.tm_year+1900,ctm.tm_mon + 1,ctm.tm_mday,
|
ctm.tm_year+1900,ctm.tm_mon + 1,ctm.tm_mday,
|
||||||
ctm.tm_hour,ctm.tm_min,ctm.tm_sec,
|
ctm.tm_hour,ctm.tm_min,ctm.tm_sec,
|
||||||
timeStamp.getNanoSeconds(),
|
timeStamp.getNanoseconds(),
|
||||||
(ctm.tm_isdst==0) ? "false" : "true",
|
(ctm.tm_isdst==0) ? "false" : "true",
|
||||||
timeStamp.getUserTag());
|
timeStamp.getUserTag());
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,65 +1,63 @@
|
|||||||
TOP=../..
|
# This is a Makefile fragment, see ../Makefile
|
||||||
|
|
||||||
include $(TOP)/configure/CONFIG
|
SRC_DIRS += $(PVDATA_TEST)/pv
|
||||||
|
|
||||||
PROD_HOST += testBitSetUtil
|
TESTPROD_HOST += testBitSetUtil
|
||||||
testBitSetUtil_SRCS += testBitSetUtil.cpp
|
testBitSetUtil_SRCS += testBitSetUtil.cpp
|
||||||
testBitSetUtil_LIBS += pvData Com
|
testHarness_SRCS += testBitSetUtil.cpp
|
||||||
TESTS += testBitSetUtil
|
TESTS += testBitSetUtil
|
||||||
|
|
||||||
PROD_HOST += testIntrospect
|
TESTPROD_HOST += testIntrospect
|
||||||
testIntrospect_SRCS += testIntrospect.cpp
|
testIntrospect_SRCS += testIntrospect.cpp
|
||||||
testIntrospect_LIBS += pvData Com
|
testHarness_SRCS += testIntrospect.cpp
|
||||||
TESTS += testIntrospect
|
TESTS += testIntrospect
|
||||||
|
|
||||||
PROD_HOST += testPVType
|
TESTPROD_HOST += testPVType
|
||||||
testPVType_SRCS += testPVType.cpp
|
testPVType_SRCS += testPVType.cpp
|
||||||
testPVType_LIBS += pvData Com
|
testHarness_SRCS += testPVType.cpp
|
||||||
TESTS += testPVType
|
TESTS += testPVType
|
||||||
|
|
||||||
PROD_HOST += testStandardField
|
TESTPROD_HOST += testStandardField
|
||||||
testStandardField_SRCS += testStandardField.cpp
|
testStandardField_SRCS += testStandardField.cpp
|
||||||
testStandardField_LIBS += pvData Com
|
testHarness_SRCS += testStandardField.cpp
|
||||||
TESTS += testStandardField
|
TESTS += testStandardField
|
||||||
|
|
||||||
PROD_HOST += testStandardPVField
|
TESTPROD_HOST += testStandardPVField
|
||||||
testStandardPVField_SRCS += testStandardPVField.cpp
|
testStandardPVField_SRCS += testStandardPVField.cpp
|
||||||
testStandardPVField_LIBS += pvData Com
|
testHarness_SRCS += testStandardPVField.cpp
|
||||||
TESTS += testStandardPVField
|
TESTS += testStandardPVField
|
||||||
|
|
||||||
PROD_HOST += testPVData
|
TESTPROD_HOST += testPVData
|
||||||
testPVData_SRCS += testPVData.cpp
|
testPVData_SRCS += testPVData.cpp
|
||||||
testPVData_LIBS += pvData Com
|
testHarness_SRCS += testPVData.cpp
|
||||||
TESTS += testPVData
|
TESTS += testPVData
|
||||||
|
|
||||||
PROD_HOST += testConvert
|
TESTPROD_HOST += testPVUnion
|
||||||
|
testPVUnion_SRCS += testPVUnion.cpp
|
||||||
|
testHarness_SRCS += testPVUnion.cpp
|
||||||
|
TESTS += testPVUnion
|
||||||
|
|
||||||
|
TESTPROD_HOST += testConvert
|
||||||
testConvert_SRCS += testConvert.cpp
|
testConvert_SRCS += testConvert.cpp
|
||||||
testConvert_LIBS += pvData Com
|
testHarness_SRCS += testConvert.cpp
|
||||||
TESTS += testConvert
|
TESTS += testConvert
|
||||||
|
|
||||||
PROD_HOST += testPVScalarArray
|
TESTPROD_HOST += testPVScalarArray
|
||||||
testPVScalarArray_SRCS += testPVScalarArray.cpp
|
testPVScalarArray_SRCS += testPVScalarArray.cpp
|
||||||
testPVScalarArray_LIBS += pvData Com
|
testHarness_SRCS += testPVScalarArray.cpp
|
||||||
TESTS += testPVScalarArray
|
TESTS += testPVScalarArray
|
||||||
|
|
||||||
PROD_HOST += testPVStructureArray
|
TESTPROD_HOST += testPVStructureArray
|
||||||
testPVStructureArray_SRCS += testPVStructureArray.cpp
|
testPVStructureArray_SRCS += testPVStructureArray.cpp
|
||||||
testPVStructureArray_LIBS += pvData Com
|
testHarness_SRCS += testPVStructureArray.cpp
|
||||||
TESTS += testPVStructureArray
|
TESTS += testPVStructureArray
|
||||||
|
|
||||||
PROD_HOST += testOperators
|
TESTPROD_HOST += testOperators
|
||||||
testOperators_SRCS += testOperators.cpp
|
testOperators_SRCS += testOperators.cpp
|
||||||
testOperators_LIBS += pvData Com
|
testHarness_SRCS += testOperators.cpp
|
||||||
TESTS += testOperators
|
TESTS += testOperators
|
||||||
|
|
||||||
PROD_HOST += testFieldBuilder
|
TESTPROD_HOST += testFieldBuilder
|
||||||
testFieldBuilder_SRCS += testFieldBuilder.cpp
|
testFieldBuilder_SRCS += testFieldBuilder.cpp
|
||||||
testFieldBuilder_LIBS += pvData Com
|
testHarness_SRCS += testFieldBuilder.cpp
|
||||||
TESTS += testFieldBuilder
|
TESTS += testFieldBuilder
|
||||||
|
|
||||||
TESTSCRIPTS_HOST += $(TESTS:%=%.t)
|
|
||||||
|
|
||||||
include $(TOP)/configure/RULES
|
|
||||||
#----------------------------------------
|
|
||||||
# ADD RULES AFTER THIS LINE
|
|
||||||
|
|
||||||
|
|||||||
@@ -90,7 +90,7 @@ static void test()
|
|||||||
int32 offsetTimeStamp = (int32)pvField->getFieldOffset();
|
int32 offsetTimeStamp = (int32)pvField->getFieldOffset();
|
||||||
pvField = pvs->getSubField("timeStamp.secondsPastEpoch");
|
pvField = pvs->getSubField("timeStamp.secondsPastEpoch");
|
||||||
int32 offsetSeconds = (int32)pvField->getFieldOffset();
|
int32 offsetSeconds = (int32)pvField->getFieldOffset();
|
||||||
pvField = pvs->getSubField("timeStamp.nanoSeconds");
|
pvField = pvs->getSubField("timeStamp.nanoseconds");
|
||||||
int32 offsetNano = (int32)pvField->getFieldOffset();
|
int32 offsetNano = (int32)pvField->getFieldOffset();
|
||||||
pvField = pvs->getSubField("timeStamp.userTag");
|
pvField = pvs->getSubField("timeStamp.userTag");
|
||||||
int32 offsetUserTag = (int32)pvField->getFieldOffset();
|
int32 offsetUserTag = (int32)pvField->getFieldOffset();
|
||||||
|
|||||||
@@ -60,7 +60,7 @@ void test_structure()
|
|||||||
StructureConstPtr s2 = fb->add("s", s)->
|
StructureConstPtr s2 = fb->add("s", s)->
|
||||||
addArray("sArray", s)->
|
addArray("sArray", s)->
|
||||||
createStructure();
|
createStructure();
|
||||||
testOk1(s2 != 0);
|
testOk1(s2.get()!=0);
|
||||||
testOk1(Structure::DEFAULT_ID == s2->getID());
|
testOk1(Structure::DEFAULT_ID == s2->getID());
|
||||||
testOk1(2 == s2->getFields().size());
|
testOk1(2 == s2->getFields().size());
|
||||||
|
|
||||||
@@ -110,6 +110,23 @@ void test_invalid()
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void test_arraySizeTypes()
|
||||||
|
{
|
||||||
|
testDiag("Test test_arraySizeTypes()");
|
||||||
|
|
||||||
|
FieldCreatePtr fieldCreate = getFieldCreate();
|
||||||
|
|
||||||
|
StructureConstPtr s = fieldCreate->createFieldBuilder()->
|
||||||
|
addArray("variableArray", pvDouble)->
|
||||||
|
addFixedArray("fixedArray", pvDouble, 10)->
|
||||||
|
addBoundedArray("boundedArray", pvDouble, 1024)->
|
||||||
|
createStructure();
|
||||||
|
testOk1(s.get() != 0);
|
||||||
|
testOk1(Structure::DEFAULT_ID == s->getID());
|
||||||
|
testOk1(3 == s->getFields().size());
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
void test_nestedStructure()
|
void test_nestedStructure()
|
||||||
{
|
{
|
||||||
testDiag("Test test_nestedStructure()");
|
testDiag("Test test_nestedStructure()");
|
||||||
@@ -224,11 +241,12 @@ void test_nestedStructureArray()
|
|||||||
|
|
||||||
MAIN(testFieldBuilder)
|
MAIN(testFieldBuilder)
|
||||||
{
|
{
|
||||||
testPlan(65);
|
testPlan(68);
|
||||||
testDiag("Tests for FieldBuilder");
|
testDiag("Tests for FieldBuilder");
|
||||||
|
|
||||||
test_factory();
|
test_factory();
|
||||||
test_structure();
|
test_structure();
|
||||||
|
test_arraySizeTypes();
|
||||||
test_nestedStructure();
|
test_nestedStructure();
|
||||||
test_nestedStructureArray();
|
test_nestedStructureArray();
|
||||||
|
|
||||||
|
|||||||
@@ -59,9 +59,26 @@ static void testScalar() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
static void testScalarArrayCommon(ScalarType stype,
|
static void testScalarArrayCommon(ScalarType stype,
|
||||||
bool isInteger,bool isNumeric,bool isPrimitive)
|
bool isInteger,bool isNumeric,bool isPrimitive,
|
||||||
|
Array::ArraySizeType sizeType = Array::variable, size_t size = 0)
|
||||||
{
|
{
|
||||||
ScalarArrayConstPtr pscalar = fieldCreate->createScalarArray(stype);
|
ScalarArrayConstPtr pscalar;
|
||||||
|
switch (sizeType)
|
||||||
|
{
|
||||||
|
case Array::variable:
|
||||||
|
pscalar = fieldCreate->createScalarArray(stype);
|
||||||
|
size = 0;
|
||||||
|
break;
|
||||||
|
case Array::bounded:
|
||||||
|
pscalar = fieldCreate->createBoundedScalarArray(stype, size);
|
||||||
|
break;
|
||||||
|
case Array::fixed:
|
||||||
|
pscalar = fieldCreate->createFixedScalarArray(stype, size);
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
throw std::invalid_argument("unsupported array size type");
|
||||||
|
}
|
||||||
|
|
||||||
Type type = pscalar->getType();
|
Type type = pscalar->getType();
|
||||||
testOk1(type==scalarArray);
|
testOk1(type==scalarArray);
|
||||||
|
|
||||||
@@ -69,6 +86,9 @@ static void testScalarArrayCommon(ScalarType stype,
|
|||||||
oss << type;
|
oss << type;
|
||||||
testOk1(oss.str().compare("scalarArray")==0);
|
testOk1(oss.str().compare("scalarArray")==0);
|
||||||
|
|
||||||
|
testOk1(pscalar->getArraySizeType()==sizeType);
|
||||||
|
testOk1(pscalar->getMaximumCapacity()==size);
|
||||||
|
|
||||||
ScalarType scalarType = pscalar->getElementType();
|
ScalarType scalarType = pscalar->getElementType();
|
||||||
testOk1(scalarType==stype);
|
testOk1(scalarType==stype);
|
||||||
testOk1(ScalarTypeFunc::isInteger(scalarType)==isInteger);
|
testOk1(ScalarTypeFunc::isInteger(scalarType)==isInteger);
|
||||||
@@ -86,6 +106,24 @@ static void testScalarArray() {
|
|||||||
testScalarArrayCommon(pvFloat,false,true,true);
|
testScalarArrayCommon(pvFloat,false,true,true);
|
||||||
testScalarArrayCommon(pvDouble,false,true,true);
|
testScalarArrayCommon(pvDouble,false,true,true);
|
||||||
testScalarArrayCommon(pvString,false,false,false);
|
testScalarArrayCommon(pvString,false,false,false);
|
||||||
|
|
||||||
|
testScalarArrayCommon(pvBoolean,false,false,true,Array::bounded,10);
|
||||||
|
testScalarArrayCommon(pvByte,true,true,true,Array::bounded,10);
|
||||||
|
testScalarArrayCommon(pvShort,true,true,true,Array::bounded,10);
|
||||||
|
testScalarArrayCommon(pvInt,true,true,true,Array::bounded,10);
|
||||||
|
testScalarArrayCommon(pvLong,true,true,true,Array::bounded,10);
|
||||||
|
testScalarArrayCommon(pvFloat,false,true,true,Array::bounded,10);
|
||||||
|
testScalarArrayCommon(pvDouble,false,true,true,Array::bounded,10);
|
||||||
|
testScalarArrayCommon(pvString,false,false,false,Array::bounded,10);
|
||||||
|
|
||||||
|
testScalarArrayCommon(pvBoolean,false,false,true,Array::fixed,16);
|
||||||
|
testScalarArrayCommon(pvByte,true,true,true,Array::fixed,16);
|
||||||
|
testScalarArrayCommon(pvShort,true,true,true,Array::fixed,16);
|
||||||
|
testScalarArrayCommon(pvInt,true,true,true,Array::fixed,16);
|
||||||
|
testScalarArrayCommon(pvLong,true,true,true,Array::fixed,16);
|
||||||
|
testScalarArrayCommon(pvFloat,false,true,true,Array::fixed,16);
|
||||||
|
testScalarArrayCommon(pvDouble,false,true,true,Array::fixed,16);
|
||||||
|
testScalarArrayCommon(pvString,false,false,false,Array::fixed,16);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void testStructure()
|
static void testStructure()
|
||||||
@@ -187,6 +225,21 @@ static void testUnion()
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void testBoundedString()
|
||||||
|
{
|
||||||
|
testDiag("testBoundedString");
|
||||||
|
|
||||||
|
BoundedStringConstPtr bs = fieldCreate->createBoundedString(8);
|
||||||
|
|
||||||
|
Type type = bs->getType();
|
||||||
|
testOk1(type==scalar);
|
||||||
|
|
||||||
|
ScalarType scalarType = bs->getScalarType();
|
||||||
|
testOk1(scalarType==pvString);
|
||||||
|
|
||||||
|
testOk1(bs->getMaximumLength()==8);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
#define testExcept(EXCEPT, CMD) try{ CMD; testFail( "No exception from: " #CMD); } \
|
#define testExcept(EXCEPT, CMD) try{ CMD; testFail( "No exception from: " #CMD); } \
|
||||||
catch(EXCEPT& e) {testPass("Got expected exception from: " #CMD);} \
|
catch(EXCEPT& e) {testPass("Got expected exception from: " #CMD);} \
|
||||||
@@ -236,6 +289,9 @@ static void testError()
|
|||||||
static void testMapping()
|
static void testMapping()
|
||||||
{
|
{
|
||||||
#define OP(TYPE, ENUM) \
|
#define OP(TYPE, ENUM) \
|
||||||
|
printf(#TYPE ": sizeof %u typeid '%s' ScalarTypeID %d\n",\
|
||||||
|
(unsigned)sizeof(TYPE), typeid(TYPE).name(),\
|
||||||
|
epics::pvData::ScalarTypeID<TYPE>::value);\
|
||||||
testOk1(typeid(ScalarTypeTraits<ENUM>::type)==typeid(TYPE)); \
|
testOk1(typeid(ScalarTypeTraits<ENUM>::type)==typeid(TYPE)); \
|
||||||
testOk1(ENUM==(ScalarType)ScalarTypeID<TYPE>::value); \
|
testOk1(ENUM==(ScalarType)ScalarTypeID<TYPE>::value); \
|
||||||
testOk1(ENUM==(ScalarType)ScalarTypeID<const TYPE>::value);
|
testOk1(ENUM==(ScalarType)ScalarTypeID<const TYPE>::value);
|
||||||
@@ -253,12 +309,11 @@ static void testMapping()
|
|||||||
OP(string, pvString)
|
OP(string, pvString)
|
||||||
#undef OP
|
#undef OP
|
||||||
|
|
||||||
testOk1((ScalarType)ScalarTypeID<PVField>::value==(ScalarType)-1);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
MAIN(testIntrospect)
|
MAIN(testIntrospect)
|
||||||
{
|
{
|
||||||
testPlan(180);
|
testPlan(326);
|
||||||
fieldCreate = getFieldCreate();
|
fieldCreate = getFieldCreate();
|
||||||
pvDataCreate = getPVDataCreate();
|
pvDataCreate = getPVDataCreate();
|
||||||
standardField = getStandardField();
|
standardField = getStandardField();
|
||||||
@@ -266,6 +321,7 @@ MAIN(testIntrospect)
|
|||||||
testScalarArray();
|
testScalarArray();
|
||||||
testStructure();
|
testStructure();
|
||||||
testUnion();
|
testUnion();
|
||||||
|
testBoundedString();
|
||||||
testError();
|
testError();
|
||||||
testMapping();
|
testMapping();
|
||||||
return testDone();
|
return testDone();
|
||||||
|
|||||||
@@ -197,45 +197,45 @@ static void testPVScalarWithProperties(
|
|||||||
}
|
}
|
||||||
PVLongPtr seconds = pvStructure->getLongField(
|
PVLongPtr seconds = pvStructure->getLongField(
|
||||||
string("timeStamp.secondsPastEpoch"));
|
string("timeStamp.secondsPastEpoch"));
|
||||||
testOk1(seconds!=0);
|
testOk1(seconds.get()!=0);
|
||||||
seconds->put(123456789);
|
seconds->put(123456789);
|
||||||
PVIntPtr nano = pvStructure->getIntField(string("timeStamp.nanoSeconds"));
|
PVIntPtr nano = pvStructure->getIntField(string("timeStamp.nanoseconds"));
|
||||||
testOk1(nano!=0);
|
testOk1(nano.get()!=0);
|
||||||
nano->put(1000000);
|
nano->put(1000000);
|
||||||
PVIntPtr severity = pvStructure->getIntField(string("alarm.severity"));
|
PVIntPtr severity = pvStructure->getIntField(string("alarm.severity"));
|
||||||
testOk1(severity!=0);
|
testOk1(severity.get()!=0);
|
||||||
severity->put(2);
|
severity->put(2);
|
||||||
PVStringPtr message = pvStructure->getStringField(string("alarm.message"));
|
PVStringPtr message = pvStructure->getStringField(string("alarm.message"));
|
||||||
testOk1(message!=0);
|
testOk1(message.get()!=0);
|
||||||
message->put(string("messageForAlarm"));
|
message->put(string("messageForAlarm"));
|
||||||
if(hasDisplayControl) {
|
if(hasDisplayControl) {
|
||||||
PVStringPtr desc = pvStructure->getStringField(
|
PVStringPtr desc = pvStructure->getStringField(
|
||||||
string("display.description"));
|
string("display.description"));
|
||||||
testOk1(desc!=0);
|
testOk1(desc.get()!=0);
|
||||||
desc->put(string("this is a description"));
|
desc->put(string("this is a description"));
|
||||||
PVStringPtr format = pvStructure->getStringField(
|
PVStringPtr format = pvStructure->getStringField(
|
||||||
string("display.format"));
|
string("display.format"));
|
||||||
testOk1(format!=0);
|
testOk1(format.get()!=0);
|
||||||
format->put(string("f10.2"));
|
format->put(string("f10.2"));
|
||||||
PVStringPtr units = pvStructure->getStringField(
|
PVStringPtr units = pvStructure->getStringField(
|
||||||
string("display.units"));
|
string("display.units"));
|
||||||
testOk1(units!=0);
|
testOk1(units.get()!=0);
|
||||||
units->put(string("SomeUnits"));
|
units->put(string("SomeUnits"));
|
||||||
PVDoublePtr limit = pvStructure->getDoubleField(
|
PVDoublePtr limit = pvStructure->getDoubleField(
|
||||||
string("display.limitLow"));
|
string("display.limitLow"));
|
||||||
testOk1(limit!=0);
|
testOk1(limit.get()!=0);
|
||||||
limit->put(0.0);
|
limit->put(0.0);
|
||||||
limit = pvStructure->getDoubleField(
|
limit = pvStructure->getDoubleField(
|
||||||
string("display.limitHigh"));
|
string("display.limitHigh"));
|
||||||
testOk1(limit!=0);
|
testOk1(limit.get()!=0);
|
||||||
limit->put(10.0);
|
limit->put(10.0);
|
||||||
limit = pvStructure->getDoubleField(
|
limit = pvStructure->getDoubleField(
|
||||||
string("control.limitLow"));
|
string("control.limitLow"));
|
||||||
testOk1(limit!=0);
|
testOk1(limit.get()!=0);
|
||||||
limit->put(1.0);
|
limit->put(1.0);
|
||||||
limit = pvStructure->getDoubleField(
|
limit = pvStructure->getDoubleField(
|
||||||
string("control.limitHigh"));
|
string("control.limitHigh"));
|
||||||
testOk1(limit!=0);
|
testOk1(limit.get()!=0);
|
||||||
limit->put(9.0);
|
limit->put(9.0);
|
||||||
}
|
}
|
||||||
if(hasValueAlarm) {
|
if(hasValueAlarm) {
|
||||||
@@ -255,15 +255,15 @@ static void testPVScalarWithProperties(
|
|||||||
convert->fromDouble(pvtemp,9.0);
|
convert->fromDouble(pvtemp,9.0);
|
||||||
severity = pvStructure->getIntField(
|
severity = pvStructure->getIntField(
|
||||||
string("valueAlarm.lowAlarmSeverity"));
|
string("valueAlarm.lowAlarmSeverity"));
|
||||||
testOk1(severity!=0);
|
testOk1(severity.get()!=0);
|
||||||
severity->put(2);
|
severity->put(2);
|
||||||
severity = pvStructure->getIntField(
|
severity = pvStructure->getIntField(
|
||||||
string("valueAlarm.highAlarmSeverity"));
|
string("valueAlarm.highAlarmSeverity"));
|
||||||
testOk1(severity!=0);
|
testOk1(severity.get()!=0);
|
||||||
severity->put(2);
|
severity->put(2);
|
||||||
PVBooleanPtr active = pvStructure->getBooleanField(
|
PVBooleanPtr active = pvStructure->getBooleanField(
|
||||||
string("valueAlarm.active"));
|
string("valueAlarm.active"));
|
||||||
testOk1(active!=0);
|
testOk1(active.get()!=0);
|
||||||
active->put(true);
|
active->put(true);
|
||||||
}
|
}
|
||||||
if(hasBooleanAlarm) {
|
if(hasBooleanAlarm) {
|
||||||
@@ -273,15 +273,15 @@ static void testPVScalarWithProperties(
|
|||||||
pvBoolean->put(true);
|
pvBoolean->put(true);
|
||||||
severity = pvStructure->getIntField(
|
severity = pvStructure->getIntField(
|
||||||
string("valueAlarm.falseSeverity"));
|
string("valueAlarm.falseSeverity"));
|
||||||
testOk1(severity!=0);
|
testOk1(severity.get()!=0);
|
||||||
severity->put(0);
|
severity->put(0);
|
||||||
severity = pvStructure->getIntField(
|
severity = pvStructure->getIntField(
|
||||||
string("valueAlarm.trueSeverity"));
|
string("valueAlarm.trueSeverity"));
|
||||||
testOk1(severity!=0);
|
testOk1(severity.get()!=0);
|
||||||
severity->put(2);
|
severity->put(2);
|
||||||
severity = pvStructure->getIntField(
|
severity = pvStructure->getIntField(
|
||||||
string("valueAlarm.changeStateSeverity"));
|
string("valueAlarm.changeStateSeverity"));
|
||||||
testOk1(severity!=0);
|
testOk1(severity.get()!=0);
|
||||||
severity->put(1);
|
severity->put(1);
|
||||||
}
|
}
|
||||||
if(debug)
|
if(debug)
|
||||||
@@ -345,7 +345,7 @@ static void testScalarArrayCommon(string /*fieldName*/,ScalarType stype)
|
|||||||
if(debug)
|
if(debug)
|
||||||
std::cout << *pvStructure << std::endl;
|
std::cout << *pvStructure << std::endl;
|
||||||
PVFieldPtr pvField = pvStructure->getSubField("alarm.status");
|
PVFieldPtr pvField = pvStructure->getSubField("alarm.status");
|
||||||
testOk1(pvField!=NULL);
|
testOk1(pvField.get()!=0);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void testScalarArray()
|
static void testScalarArray()
|
||||||
|
|||||||
@@ -108,7 +108,7 @@ static void testBasic()
|
|||||||
|
|
||||||
{
|
{
|
||||||
typename PVT::const_svector avoid;
|
typename PVT::const_svector avoid;
|
||||||
arr1->PVScalarArray::getAs<typename PVT::value_type>(avoid);
|
arr1->PVScalarArray::template getAs<typename PVT::value_type>(avoid);
|
||||||
testOk1(avoid.data()==cdata.data());
|
testOk1(avoid.data()==cdata.data());
|
||||||
testOk1(avoid.data()==arr1->view().data());
|
testOk1(avoid.data()==arr1->view().data());
|
||||||
}
|
}
|
||||||
@@ -133,7 +133,7 @@ static void testBasic()
|
|||||||
testOk1(cdata.size()==arr1->getLength());
|
testOk1(cdata.size()==arr1->getLength());
|
||||||
|
|
||||||
PVIntArray::const_svector idata;
|
PVIntArray::const_svector idata;
|
||||||
arr1->PVScalarArray::getAs<int32>(idata);
|
arr1->PVScalarArray::template getAs<int32>(idata);
|
||||||
|
|
||||||
testOk1(idata.at(1)==10);
|
testOk1(idata.at(1)==10);
|
||||||
|
|
||||||
@@ -143,7 +143,7 @@ static void testBasic()
|
|||||||
|
|
||||||
idata = freeze(wdata);
|
idata = freeze(wdata);
|
||||||
|
|
||||||
arr1->PVScalarArray::putFrom<int32>(idata);
|
arr1->PVScalarArray::template putFrom<int32>(idata);
|
||||||
|
|
||||||
testOk1(castUnsafe<PVIntArray::value_type>(arr1->view()[1])==42);
|
testOk1(castUnsafe<PVIntArray::value_type>(arr1->view()[1])==42);
|
||||||
}
|
}
|
||||||
|
|||||||
125
testApp/pv/testPVUnion.cpp
Normal file
125
testApp/pv/testPVUnion.cpp
Normal file
@@ -0,0 +1,125 @@
|
|||||||
|
/* testPVUnion.cpp */
|
||||||
|
/**
|
||||||
|
* Copyright - See the COPYRIGHT that is included with this distribution.
|
||||||
|
* EPICS pvData is distributed subject to a Software License Agreement found
|
||||||
|
* in file LICENSE that is included with this distribution.
|
||||||
|
*/
|
||||||
|
/* Author: Marty Kraimer Date: 2014.07 */
|
||||||
|
|
||||||
|
#include <cstddef>
|
||||||
|
#include <cstdlib>
|
||||||
|
#include <cstddef>
|
||||||
|
#include <string>
|
||||||
|
#include <cstdio>
|
||||||
|
|
||||||
|
#include <epicsUnitTest.h>
|
||||||
|
#include <testMain.h>
|
||||||
|
|
||||||
|
#include <pv/pvIntrospect.h>
|
||||||
|
#include <pv/pvData.h>
|
||||||
|
#include <pv/convert.h>
|
||||||
|
#include <pv/standardField.h>
|
||||||
|
#include <pv/standardPVField.h>
|
||||||
|
#include <pv/timeStamp.h>
|
||||||
|
#include <pv/pvTimeStamp.h>
|
||||||
|
|
||||||
|
using namespace epics::pvData;
|
||||||
|
using std::tr1::static_pointer_cast;
|
||||||
|
using std::string;
|
||||||
|
using std::cout;
|
||||||
|
using std::endl;
|
||||||
|
|
||||||
|
static bool debug = false;
|
||||||
|
|
||||||
|
static FieldCreatePtr fieldCreate = getFieldCreate();
|
||||||
|
static PVDataCreatePtr pvDataCreate = getPVDataCreate();
|
||||||
|
static StandardFieldPtr standardField = getStandardField();
|
||||||
|
static StandardPVFieldPtr standardPVField = getStandardPVField();
|
||||||
|
static ConvertPtr convert = getConvert();
|
||||||
|
|
||||||
|
static void testPVUnionType()
|
||||||
|
{
|
||||||
|
if(debug)
|
||||||
|
std::cout << std::endl << "testPVUnion" << std::endl;
|
||||||
|
PVStructurePtr pvStructure = pvDataCreate->createPVStructure(
|
||||||
|
standardField->regUnion(
|
||||||
|
fieldCreate->createFieldBuilder()->
|
||||||
|
add("doubleValue", pvDouble)->
|
||||||
|
add("intValue", pvInt)->
|
||||||
|
add("timeStamp",standardField->timeStamp())->
|
||||||
|
createUnion(),
|
||||||
|
"alarm,timeStamp"));
|
||||||
|
PVUnionPtr pvValue = pvStructure->getSubField<PVUnion>("value");
|
||||||
|
PVStructurePtr pvTime= pvValue->select<PVStructure>(2);
|
||||||
|
TimeStamp timeStamp;
|
||||||
|
timeStamp.getCurrent();
|
||||||
|
PVTimeStamp pvTimeStamp;
|
||||||
|
pvTimeStamp.attach(pvTime);
|
||||||
|
pvTimeStamp.set(timeStamp);
|
||||||
|
testOk1(
|
||||||
|
pvTime->getSubField<PVLong>("secondsPastEpoch")->get()
|
||||||
|
==
|
||||||
|
pvValue->get<PVStructure>()->getSubField<PVLong>("secondsPastEpoch")->get()
|
||||||
|
);
|
||||||
|
PVDoublePtr pvDouble = pvValue->select<PVDouble>("doubleValue");
|
||||||
|
pvDouble->put(1e5);
|
||||||
|
testOk1(pvDouble->get()==pvValue->get<PVDouble>()->get());
|
||||||
|
PVIntPtr pvInt = pvValue->select<PVInt>("intValue");
|
||||||
|
pvInt->put(15);
|
||||||
|
testOk1(pvInt->get()==pvValue->get<PVInt>()->get());
|
||||||
|
std::cout << "testPVUnion PASSED" << std::endl;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void testPVUnionArray()
|
||||||
|
{
|
||||||
|
if(debug)
|
||||||
|
std::cout << std::endl << "testPVUnion" << std::endl;
|
||||||
|
PVStructurePtr pvStructure = pvDataCreate->createPVStructure(
|
||||||
|
standardField->unionArray(
|
||||||
|
fieldCreate->createFieldBuilder()->
|
||||||
|
add("doubleValue", pvDouble)->
|
||||||
|
add("intValue", pvInt)->
|
||||||
|
add("timeStamp",standardField->timeStamp())->
|
||||||
|
createUnion(),
|
||||||
|
"alarm,timeStamp"));
|
||||||
|
PVUnionArrayPtr pvValue = pvStructure->getSubField<PVUnionArray>("value");
|
||||||
|
size_t num = 3;
|
||||||
|
shared_vector<PVUnionPtr> unions(3);
|
||||||
|
for(size_t i=0; i<num; ++i)
|
||||||
|
{
|
||||||
|
unions[i] = pvDataCreate->createPVUnion(pvValue->getUnionArray()->getUnion());
|
||||||
|
}
|
||||||
|
unions[0]->select("doubleValue");
|
||||||
|
unions[1]->select("intValue");
|
||||||
|
unions[2]->select("timeStamp");
|
||||||
|
PVDoublePtr pvDouble = unions[0]->get<PVDouble>();
|
||||||
|
pvDouble->put(1.235);
|
||||||
|
PVIntPtr pvInt = unions[1]->get<PVInt>();
|
||||||
|
pvInt->put(5);
|
||||||
|
PVStructurePtr pvTime = unions[2]->get<PVStructure>();
|
||||||
|
TimeStamp timeStamp;
|
||||||
|
timeStamp.getCurrent();
|
||||||
|
PVTimeStamp pvTimeStamp;
|
||||||
|
pvTimeStamp.attach(pvTime);
|
||||||
|
pvTimeStamp.set(timeStamp);
|
||||||
|
pvValue->replace(freeze(unions));
|
||||||
|
shared_vector<const PVUnionPtr> sharedUnions = pvValue->view();
|
||||||
|
testOk1(pvDouble->get()==sharedUnions[0]->get<PVDouble>()->get());
|
||||||
|
testOk1(pvInt->get()==sharedUnions[1]->get<PVInt>()->get());
|
||||||
|
testOk1(
|
||||||
|
pvTime->getSubField<PVLong>("secondsPastEpoch")->get()
|
||||||
|
==
|
||||||
|
sharedUnions[2]->get<PVStructure>()->getSubField<PVLong>("secondsPastEpoch")->get()
|
||||||
|
);
|
||||||
|
std::cout << "testPVUnionArray PASSED" << std::endl;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
MAIN(testPVUnion)
|
||||||
|
{
|
||||||
|
testPlan(6);
|
||||||
|
testPVUnionType();
|
||||||
|
testPVUnionArray();
|
||||||
|
return testDone();
|
||||||
|
}
|
||||||
|
|
||||||
86
testApp/pvDataAllTests.c
Normal file
86
testApp/pvDataAllTests.c
Normal file
@@ -0,0 +1,86 @@
|
|||||||
|
/*
|
||||||
|
* Run pvData tests as a batch.
|
||||||
|
*
|
||||||
|
* Do *not* include performance measurements here, they don't help to
|
||||||
|
* prove functionality (which is the point of this convenience routine).
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <epicsThread.h>
|
||||||
|
#include <epicsUnitTest.h>
|
||||||
|
|
||||||
|
/* copy */
|
||||||
|
int testCreateRequest(void);
|
||||||
|
int testPVCopy(void);
|
||||||
|
|
||||||
|
/* misc */
|
||||||
|
int testBaseException(void);
|
||||||
|
int testBitSet(void);
|
||||||
|
int testByteBuffer(void);
|
||||||
|
int testMessageQueue(void);
|
||||||
|
int testOverrunBitSet(void);
|
||||||
|
int testQueue(void);
|
||||||
|
int testSerialization(void);
|
||||||
|
int testSharedVector(void);
|
||||||
|
int testThread(void);
|
||||||
|
int testTimeStamp(void);
|
||||||
|
int testTimer(void);
|
||||||
|
int testTypeCast(void);
|
||||||
|
|
||||||
|
/* property */
|
||||||
|
int testCreateRequest(void);
|
||||||
|
|
||||||
|
/* pv */
|
||||||
|
int testBitSetUtil(void);
|
||||||
|
int testConvert(void);
|
||||||
|
int testFieldBuilder(void);
|
||||||
|
int testIntrospect(void);
|
||||||
|
int testOperators(void);
|
||||||
|
int testPVData(void);
|
||||||
|
int testPVScalarArray(void);
|
||||||
|
int testPVStructureArray(void);
|
||||||
|
int testPVType(void);
|
||||||
|
int testPVUnion(void);
|
||||||
|
int testStandardField(void);
|
||||||
|
int testStandardPVField(void);
|
||||||
|
|
||||||
|
void pvDataAllTests(void)
|
||||||
|
{
|
||||||
|
testHarness();
|
||||||
|
|
||||||
|
/* pv */
|
||||||
|
runTest(testBitSetUtil);
|
||||||
|
runTest(testConvert);
|
||||||
|
runTest(testFieldBuilder);
|
||||||
|
runTest(testIntrospect);
|
||||||
|
runTest(testOperators);
|
||||||
|
runTest(testPVData);
|
||||||
|
runTest(testPVScalarArray);
|
||||||
|
runTest(testPVStructureArray);
|
||||||
|
runTest(testPVType);
|
||||||
|
runTest(testPVUnion);
|
||||||
|
runTest(testStandardField);
|
||||||
|
runTest(testStandardPVField);
|
||||||
|
|
||||||
|
/* misc */
|
||||||
|
runTest(testBaseException);
|
||||||
|
runTest(testBitSet);
|
||||||
|
runTest(testByteBuffer);
|
||||||
|
runTest(testMessageQueue);
|
||||||
|
runTest(testOverrunBitSet);
|
||||||
|
runTest(testQueue);
|
||||||
|
runTest(testSerialization);
|
||||||
|
runTest(testSharedVector);
|
||||||
|
runTest(testThread);
|
||||||
|
runTest(testTimeStamp);
|
||||||
|
runTest(testTimer);
|
||||||
|
runTest(testTypeCast);
|
||||||
|
|
||||||
|
/* copy */
|
||||||
|
runTest(testCreateRequest);
|
||||||
|
runTest(testPVCopy);
|
||||||
|
|
||||||
|
/* property */
|
||||||
|
runTest(testCreateRequest);
|
||||||
|
}
|
||||||
|
|
||||||
1
testApp/qemuRunTest.sh
Executable file
1
testApp/qemuRunTest.sh
Executable file
@@ -0,0 +1 @@
|
|||||||
|
qemu-system-i386 --kernel O.RTEMS-pc386/rtemsTestHarness -netdev user,id=mynet0 -device ne2k_isa,netdev=mynet0 -redir tcp:5075::5075 -redir udp:5076::5076 -m 1024 --no-reboot -curses
|
||||||
72
testApp/rtemsConfig.c
Normal file
72
testApp/rtemsConfig.c
Normal file
@@ -0,0 +1,72 @@
|
|||||||
|
/*************************************************************************\
|
||||||
|
* Copyright (c) 2002 The University of Saskatchewan
|
||||||
|
* EPICS BASE Versions 3.13.7
|
||||||
|
* and higher are distributed subject to a Software License Agreement found
|
||||||
|
* in file LICENSE that is included with this distribution.
|
||||||
|
\*************************************************************************/
|
||||||
|
/*
|
||||||
|
* RTEMS configuration for EPICS
|
||||||
|
* Revision-Id: anj@aps.anl.gov-20101005192737-disfz3vs0f3fiixd
|
||||||
|
* Author: W. Eric Norum
|
||||||
|
* norume@aps.anl.gov
|
||||||
|
* (630) 252-4793
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <rtems.h>
|
||||||
|
|
||||||
|
/*
|
||||||
|
***********************************************************************
|
||||||
|
* RTEMS CONFIGURATION *
|
||||||
|
***********************************************************************
|
||||||
|
*/
|
||||||
|
#define CONFIGURE_RTEMS_INIT_TASKS_TABLE
|
||||||
|
|
||||||
|
#if __RTEMS_MAJOR__>4 || (__RTEMS_MAJOR__==4 && __RTEMS_MINOR__>9) || (__RTEMS_MAJOR__==4 && __RTEMS_MINOR__==9 && __RTEMS_REVISION__==99)
|
||||||
|
# define CONFIGURE_UNIFIED_WORK_AREAS
|
||||||
|
#else
|
||||||
|
# define CONFIGURE_EXECUTIVE_RAM_SIZE (2000*1024)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#define CONFIGURE_MAXIMUM_TASKS rtems_resource_unlimited(30)
|
||||||
|
#define CONFIGURE_MAXIMUM_SEMAPHORES rtems_resource_unlimited(500)
|
||||||
|
#define CONFIGURE_MAXIMUM_TIMERS rtems_resource_unlimited(20)
|
||||||
|
#define CONFIGURE_MAXIMUM_MESSAGE_QUEUES rtems_resource_unlimited(5)
|
||||||
|
#define CONFIGURE_MAXIMUM_USER_EXTENSIONS 1
|
||||||
|
|
||||||
|
#define CONFIGURE_LIBIO_MAXIMUM_FILE_DESCRIPTORS 150
|
||||||
|
#define CONFIGURE_USE_IMFS_AS_BASE_FILESYSTEM
|
||||||
|
#define CONFIGURE_MAXIMUM_DRIVERS 8
|
||||||
|
|
||||||
|
#define CONFIGURE_MICROSECONDS_PER_TICK 20000
|
||||||
|
|
||||||
|
#define CONFIGURE_INIT_TASK_PRIORITY 80
|
||||||
|
|
||||||
|
#define CONFIGURE_MALLOC_STATISTICS 1
|
||||||
|
|
||||||
|
#define CONFIGURE_INIT
|
||||||
|
#define CONFIGURE_INIT_TASK_INITIAL_MODES (RTEMS_PREEMPT | \
|
||||||
|
RTEMS_NO_TIMESLICE | \
|
||||||
|
RTEMS_NO_ASR | \
|
||||||
|
RTEMS_INTERRUPT_LEVEL(0))
|
||||||
|
#define CONFIGURE_INIT_TASK_ATTRIBUTES (RTEMS_FLOATING_POINT | RTEMS_LOCAL)
|
||||||
|
#define CONFIGURE_INIT_TASK_STACK_SIZE (16*1024)
|
||||||
|
rtems_task Init (rtems_task_argument argument);
|
||||||
|
|
||||||
|
#define CONFIGURE_APPLICATION_NEEDS_CONSOLE_DRIVER
|
||||||
|
#define CONFIGURE_APPLICATION_NEEDS_CLOCK_DRIVER
|
||||||
|
|
||||||
|
#define CONFIGURE_FILESYSTEM_NFS
|
||||||
|
#define CONFIGURE_FILESYSTEM_IMFS
|
||||||
|
|
||||||
|
/*
|
||||||
|
* This should be made BSP dependent, not CPU dependent but I know of no
|
||||||
|
* appropriate conditionals to use.
|
||||||
|
* The new general time support makes including the RTC driverr less important.
|
||||||
|
*/
|
||||||
|
#if !defined(mpc604) && !defined(__mc68040__) && !defined(__mcf5200__) && !defined(mpc7455) && !defined(__arm__) /* don't have RTC code */
|
||||||
|
#define CONFIGURE_APPLICATION_NEEDS_RTC_DRIVER
|
||||||
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
#include <bsp.h>
|
||||||
|
#include <rtems/confdefs.h>
|
||||||
294
testApp/rtemsNetworking.h
Normal file
294
testApp/rtemsNetworking.h
Normal file
@@ -0,0 +1,294 @@
|
|||||||
|
/*
|
||||||
|
* Network configuration -- QEMU NOT using DHCP
|
||||||
|
*
|
||||||
|
************************************************************
|
||||||
|
* EDIT THIS FILE TO REFLECT YOUR NETWORK CONFIGURATION *
|
||||||
|
* BEFORE RUNNING ANY RTEMS PROGRAMS WHICH USE THE NETWORK! *
|
||||||
|
************************************************************
|
||||||
|
*
|
||||||
|
* The dynamic probing is based upon the EPICS network
|
||||||
|
* configuration file written by:
|
||||||
|
* W. Eric Norum
|
||||||
|
* eric.norum@usask.ca
|
||||||
|
* (306) 966-5394
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef _RTEMS_NETWORKCONFIG_H_
|
||||||
|
#define _RTEMS_NETWORKCONFIG_H_
|
||||||
|
|
||||||
|
/* #define USE_LIBBSDPORT */
|
||||||
|
|
||||||
|
#if defined(USE_LIBBSDPORT)
|
||||||
|
#include <bsp/libbsdport_api.h>
|
||||||
|
#define CONFIGURE_MAXIMUM_TIMERS 10
|
||||||
|
#endif
|
||||||
|
/*
|
||||||
|
* For TFTP test application
|
||||||
|
*/
|
||||||
|
#if (defined (RTEMS_USE_BOOTP))
|
||||||
|
#define RTEMS_TFTP_TEST_HOST_NAME "BOOTP_HOST"
|
||||||
|
#define RTEMS_TFTP_TEST_FILE_NAME "BOOTP_FILE"
|
||||||
|
#else
|
||||||
|
#define RTEMS_TFTP_TEST_HOST_NAME "XXX.YYY.ZZZ.XYZ"
|
||||||
|
#define RTEMS_TFTP_TEST_FILE_NAME "tftptest"
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/*
|
||||||
|
* For NFS test application
|
||||||
|
*
|
||||||
|
* NFS mount and a directory to ls once mounted
|
||||||
|
*/
|
||||||
|
#define RTEMS_NFS_SERVER "192.168.1.210"
|
||||||
|
#define RTEMS_NFS_SERVER_PATH "/home"
|
||||||
|
#define RTEMS_NFS_LS_PATH "/mnt/nfstest"
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
* This file can be copied to an application source dirctory
|
||||||
|
* and modified to override the values shown below.
|
||||||
|
*
|
||||||
|
* The following CPP symbols may be passed from the Makefile:
|
||||||
|
*
|
||||||
|
* symbol default description
|
||||||
|
*
|
||||||
|
* NETWORK_TASK_PRIORITY 150 can be read by app from public
|
||||||
|
* var 'gesysNetworkTaskPriority'
|
||||||
|
* FIXED_IP_ADDR <undefined> hardcoded IP address (e.g.,
|
||||||
|
* "192.168.0.10"); disables BOOTP;
|
||||||
|
* must also define FIXED_NETMASK
|
||||||
|
* FIXED_NETMASK <undefined> IP netmask string
|
||||||
|
* (e.g. "255.255.255.0")
|
||||||
|
* MULTI_NETDRIVER <undefined> ugly hack; if defined try to probe
|
||||||
|
* a variety of PCI and ISA drivers
|
||||||
|
* (i386 ONLY) use is discouraged!
|
||||||
|
* NIC_NAME <undefined> Ethernet driver name (e.g. "pcn1");
|
||||||
|
* must also define NIC_ATTACH
|
||||||
|
* NIC_ATTACH <undefined> Ethernet driver attach function
|
||||||
|
* (e.g., rtems_fxp_attach).
|
||||||
|
* If these are undefined then
|
||||||
|
* a) MULTI_NETDRIVER is used
|
||||||
|
* (if defined)
|
||||||
|
* b) RTEMS_BSP_NETWORK_DRIVER_NAME/
|
||||||
|
* RTEMS_BSP_NETWORK_DRIVER_ATTACH
|
||||||
|
* are tried
|
||||||
|
* MEMORY_CUSTOM <undefined> Allocate the defined amount of
|
||||||
|
* memory for mbufs and mbuf clusters,
|
||||||
|
* respectively. Define to a comma ','
|
||||||
|
* separated pair of two numerical
|
||||||
|
* values, e.g: 100*1024,200*1024
|
||||||
|
* MEMORY_SCARCE <undefined> Allocate few memory for mbufs
|
||||||
|
* (hint for how much memory the
|
||||||
|
* board has)
|
||||||
|
* MEMORY_HUGE <undefined> Allocate a lot of memory for mbufs
|
||||||
|
* (hint for how much memory the
|
||||||
|
* board has)
|
||||||
|
* If none of MEMORY_CUSTOM/
|
||||||
|
* MEMORY_SCARCE/MEMORY_HUGE are
|
||||||
|
* defined then a medium amount of
|
||||||
|
* memory is allocated for mbufs.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <rtems/bspIo.h>
|
||||||
|
#include <bsp.h>
|
||||||
|
#include <rtems/rtems_bsdnet.h>
|
||||||
|
|
||||||
|
#if 0
|
||||||
|
#ifdef HAVE_CONFIG_H
|
||||||
|
#include <config.h>
|
||||||
|
#else
|
||||||
|
#include "verscheck.h"
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
|
|
||||||
|
//#define MULTI_NETDRIVER
|
||||||
|
//#define RTEMS_BSP_NETWORK_DRIVER_NAME 1
|
||||||
|
|
||||||
|
#define FIXED_IP_ADDR "192.168.1.249"
|
||||||
|
#define FIXED_NETMASK "255.255.255.0"
|
||||||
|
|
||||||
|
#ifndef NETWORK_TASK_PRIORITY
|
||||||
|
#define NETWORK_TASK_PRIORITY 150 /* within EPICS' range */
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/* make publicily available for startup scripts... */
|
||||||
|
const int gesysNetworkTaskPriority = NETWORK_TASK_PRIORITY;
|
||||||
|
|
||||||
|
#ifdef FIXED_IP_ADDR
|
||||||
|
#define RTEMS_DO_BOOTP 0
|
||||||
|
#else
|
||||||
|
#define RTEMS_DO_BOOTP rtems_bsdnet_do_bootp
|
||||||
|
#define FIXED_IP_ADDR 0
|
||||||
|
#undef FIXED_NETMASK
|
||||||
|
#define FIXED_NETMASK 0
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if !defined(NIC_NAME)
|
||||||
|
|
||||||
|
#ifdef MULTI_NETDRIVER
|
||||||
|
|
||||||
|
#if 0
|
||||||
|
#if RTEMS_VERSION_ATLEAST(4,6,99)
|
||||||
|
#define pcib_init pci_initialize
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
|
|
||||||
|
extern int rtems_3c509_driver_attach (struct rtems_bsdnet_ifconfig *, int);
|
||||||
|
extern int rtems_fxp_attach (struct rtems_bsdnet_ifconfig *, int);
|
||||||
|
extern int rtems_elnk_driver_attach (struct rtems_bsdnet_ifconfig *, int);
|
||||||
|
extern int rtems_dec21140_driver_attach (struct rtems_bsdnet_ifconfig *, int);
|
||||||
|
|
||||||
|
/* these don't probe and will be used even if there's no device :-( */
|
||||||
|
extern int rtems_ne_driver_attach (struct rtems_bsdnet_ifconfig *, int);
|
||||||
|
extern int rtems_wd_driver_attach (struct rtems_bsdnet_ifconfig *, int);
|
||||||
|
|
||||||
|
static struct rtems_bsdnet_ifconfig isa_netdriver_config[] = {
|
||||||
|
{
|
||||||
|
"ep0", rtems_3c509_driver_attach, isa_netdriver_config + 1,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"ne1", rtems_ne_driver_attach, 0, irno: 9 /* qemu cannot configure irq-no :-(; has it hardwired to 9 */
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|
||||||
|
static struct rtems_bsdnet_ifconfig pci_netdriver_config[]={
|
||||||
|
{
|
||||||
|
"dc1", rtems_dec21140_driver_attach, pci_netdriver_config+1,
|
||||||
|
},
|
||||||
|
#if !defined(USE_LIBBSDPORT)
|
||||||
|
{
|
||||||
|
"fxp1", rtems_fxp_attach, pci_netdriver_config+2,
|
||||||
|
},
|
||||||
|
#else
|
||||||
|
{
|
||||||
|
"", libbsdport_netdriver_attach, pci_netdriver_config+2,
|
||||||
|
},
|
||||||
|
#endif
|
||||||
|
{
|
||||||
|
"elnk1", rtems_elnk_driver_attach, isa_netdriver_config,
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|
||||||
|
static int pci_check(struct rtems_bsdnet_ifconfig *ocfg, int attaching)
|
||||||
|
{
|
||||||
|
struct rtems_bsdnet_ifconfig *cfg;
|
||||||
|
int if_index_pre;
|
||||||
|
extern int if_index;
|
||||||
|
if ( attaching ) {
|
||||||
|
cfg = pci_initialize() ?
|
||||||
|
isa_netdriver_config : pci_netdriver_config;
|
||||||
|
}
|
||||||
|
while ( cfg ) {
|
||||||
|
printk("Probing '%s'", cfg->name);
|
||||||
|
/* unfortunately, the return value is unreliable - some drivers report
|
||||||
|
* success even if they fail.
|
||||||
|
* Check if they chained an interface (ifnet) structure instead
|
||||||
|
*/
|
||||||
|
if_index_pre = if_index;
|
||||||
|
cfg->attach(cfg, attaching);
|
||||||
|
if ( if_index > if_index_pre ) {
|
||||||
|
/* assume success */
|
||||||
|
printk(" .. seemed to work\n");
|
||||||
|
ocfg->name = cfg->name;
|
||||||
|
ocfg->attach = cfg->attach;
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
printk(" .. failed\n");
|
||||||
|
cfg = cfg->next;
|
||||||
|
}
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
#define NIC_NAME "dummy"
|
||||||
|
#define NIC_ATTACH pci_check
|
||||||
|
|
||||||
|
#else
|
||||||
|
|
||||||
|
#if defined(RTEMS_BSP_NETWORK_DRIVER_NAME) /* Use NIC provided by BSP */
|
||||||
|
|
||||||
|
/* force ne2k_isa on i386 for qemu */
|
||||||
|
#if defined(__i386__)
|
||||||
|
# define NIC_NAME BSP_NE2000_NETWORK_DRIVER_NAME
|
||||||
|
# define NIC_ATTACH BSP_NE2000_NETWORK_DRIVER_ATTACH
|
||||||
|
|
||||||
|
#else
|
||||||
|
|
||||||
|
# define NIC_NAME RTEMS_BSP_NETWORK_DRIVER_NAME
|
||||||
|
# define NIC_ATTACH RTEMS_BSP_NETWORK_DRIVER_ATTACH
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#endif /* ifdef MULTI_NETDRIVER */
|
||||||
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
#ifdef NIC_NAME
|
||||||
|
|
||||||
|
extern int NIC_ATTACH();
|
||||||
|
|
||||||
|
#if RTEMS_BSP_NETWORK_DRIVER_ATTACH == BSP_NE2000_NETWORK_DRIVER_ATTACH
|
||||||
|
static char ethernet_address[6] = { 0x00, 0xab, 0xcd, 0xef, 0x12, 0x34 };
|
||||||
|
#endif
|
||||||
|
|
||||||
|
static struct rtems_bsdnet_ifconfig netdriver_config[1] = {{
|
||||||
|
NIC_NAME, /* name */
|
||||||
|
(int (*)(struct rtems_bsdnet_ifconfig*,int))NIC_ATTACH, /* attach function */
|
||||||
|
0, /* link to next interface */
|
||||||
|
FIXED_IP_ADDR,
|
||||||
|
FIXED_NETMASK
|
||||||
|
#if RTEMS_BSP_NETWORK_DRIVER_ATTACH == BSP_NE2000_NETWORK_DRIVER_ATTACH
|
||||||
|
,
|
||||||
|
ethernet_address,
|
||||||
|
irno:9,
|
||||||
|
port:0xc100
|
||||||
|
#endif
|
||||||
|
}};
|
||||||
|
#else
|
||||||
|
#warning "NO KNOWN NETWORK DRIVER FOR THIS BSP -- YOU MAY HAVE TO EDIT networkconfig.h"
|
||||||
|
#endif
|
||||||
|
|
||||||
|
struct rtems_bsdnet_config rtems_bsdnet_config = {
|
||||||
|
#ifdef NIC_NAME
|
||||||
|
netdriver_config, /* link to next interface */
|
||||||
|
RTEMS_DO_BOOTP, /* Use BOOTP to get network configuration */
|
||||||
|
#else
|
||||||
|
0,
|
||||||
|
0,
|
||||||
|
#endif
|
||||||
|
NETWORK_TASK_PRIORITY, /* Network task priority */
|
||||||
|
#if defined(MEMORY_CUSTOM)
|
||||||
|
MEMORY_CUSTOM,
|
||||||
|
#elif defined(MEMORY_SCARCE)
|
||||||
|
100*1024, /* MBUF space */
|
||||||
|
200*1024, /* MBUF cluster space */
|
||||||
|
#elif defined(MEMORY_HUGE)
|
||||||
|
2*1024*1024, /* MBUF space */
|
||||||
|
5*1024*1024, /* MBUF cluster space */
|
||||||
|
#else
|
||||||
|
180*1024, /* MBUF space */
|
||||||
|
350*1024, /* MBUF cluster space */
|
||||||
|
#endif
|
||||||
|
#if (!defined (RTEMS_USE_BOOTP)) && defined(ON_RTEMS_LAB_WINSYSTEMS)
|
||||||
|
"rtems", /* Host name */
|
||||||
|
"nodomain.com", /* Domain name */
|
||||||
|
"192.168.1.14", /* Gateway */
|
||||||
|
"192.168.1.1", /* Log host */
|
||||||
|
{"89.212.75.6" }, /* Name server(s) */
|
||||||
|
{"192.168.1.1" }, /* NTP server(s) */
|
||||||
|
#else
|
||||||
|
NULL, /* Host name */
|
||||||
|
NULL, /* Domain name */
|
||||||
|
NULL, /* Gateway */
|
||||||
|
NULL, /* Log host */
|
||||||
|
{ NULL }, /* Name server(s) */
|
||||||
|
{ NULL }, /* NTP server(s) */
|
||||||
|
#endif /* !RTEMS_USE_BOOTP */
|
||||||
|
0, /* efficiency */
|
||||||
|
0, /* udp TX buffer */
|
||||||
|
0, /* udp RX buffer */
|
||||||
|
0, /* tcp TX buffer */
|
||||||
|
0, /* tcp RX buffer */
|
||||||
|
};
|
||||||
|
#endif /* _RTEMS_NETWORKCONFIG_H_ */
|
||||||
37
testApp/rtemsTestHarness.c
Normal file
37
testApp/rtemsTestHarness.c
Normal file
@@ -0,0 +1,37 @@
|
|||||||
|
#include <stdio.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <rtems/rtems_bsdnet.h>
|
||||||
|
#include <rtems/error.h>
|
||||||
|
|
||||||
|
#include "rtemsNetworking.h"
|
||||||
|
|
||||||
|
#include <epicsExit.h>
|
||||||
|
#include <osdTime.h>
|
||||||
|
|
||||||
|
rtems_task
|
||||||
|
Init (rtems_task_argument ignored)
|
||||||
|
{
|
||||||
|
rtems_bsdnet_initialize_network ();
|
||||||
|
//rtems_bsdnet_show_if_stats ();
|
||||||
|
|
||||||
|
rtems_time_of_day timeOfDay;
|
||||||
|
if (rtems_clock_get(RTEMS_CLOCK_GET_TOD,&timeOfDay) != RTEMS_SUCCESSFUL) {
|
||||||
|
timeOfDay.year = 2014;
|
||||||
|
timeOfDay.month = 1;
|
||||||
|
timeOfDay.day = 1;
|
||||||
|
timeOfDay.hour = 0;
|
||||||
|
timeOfDay.minute = 0;
|
||||||
|
timeOfDay.second = 0;
|
||||||
|
timeOfDay.ticks = 0;
|
||||||
|
|
||||||
|
rtems_status_code ret = rtems_clock_set(&timeOfDay);
|
||||||
|
if (ret != RTEMS_SUCCESSFUL) {
|
||||||
|
printf("**** Can't set time %s\n", rtems_status_text(ret));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
osdTimeRegister();
|
||||||
|
|
||||||
|
extern void pvDataAllTests(void);
|
||||||
|
pvDataAllTests();
|
||||||
|
epicsExit(0);
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user