pvaClientCPP  4.8.1-dev
pvaClientMultiMonitorDouble.cpp
Go to the documentation of this file.
1 /* pvaClientMultiMonitorDouble.cpp */
12 #include <epicsThread.h>
13 #include <epicsMath.h>
14 
15 #define epicsExportSharedSymbols
16 
18 
19 using namespace epics::pvData;
20 using namespace epics::pvAccess;
21 using namespace epics::nt;
22 using namespace std;
23 
24 namespace epics { namespace pvaClient {
25 
26 
27 PvaClientMultiMonitorDoublePtr PvaClientMultiMonitorDouble::create(
28  PvaClientMultiChannelPtr const &pvaMultiChannel,
29  PvaClientChannelArray const &pvaClientChannelArray)
30 {
31  PvaClientMultiMonitorDoublePtr pvaClientMultiMonitorDouble(
32  new PvaClientMultiMonitorDouble(pvaMultiChannel,pvaClientChannelArray));
33  return pvaClientMultiMonitorDouble;
34 }
35 
36 PvaClientMultiMonitorDouble::PvaClientMultiMonitorDouble(
37  PvaClientMultiChannelPtr const &pvaClientMultiChannel,
38  PvaClientChannelArray const &pvaClientChannelArray)
39 : pvaClientMultiChannel(pvaClientMultiChannel),
40  pvaClientChannelArray(pvaClientChannelArray),
41  nchannel(pvaClientChannelArray.size()),
42  doubleValue(shared_vector<double>(nchannel,epicsNAN)),
43  pvaClientMonitor(std::vector<PvaClientMonitorPtr>(nchannel,PvaClientMonitorPtr())),
44  isMonitorConnected(false)
45 {
46  if(PvaClient::getDebug()) cout<< "PvaClientMultiMonitorDouble::PvaClientMultiMonitorDouble()\n";
47 }
48 
49 PvaClientMultiMonitorDouble::~PvaClientMultiMonitorDouble()
50 {
51  if(PvaClient::getDebug()) cout<< "PvaClientMultiMonitorDouble::~PvaClientMultiMonitorDouble()\n";
52 }
53 
54 void PvaClientMultiMonitorDouble::connect()
55 {
56  shared_vector<epics::pvData::boolean> isConnected = pvaClientMultiChannel->getIsConnected();
57  string request = "value";
58  for(size_t i=0; i<nchannel; ++i)
59  {
60  if(isConnected[i]) {
61  pvaClientMonitor[i] = pvaClientChannelArray[i]->createMonitor(request);
62  pvaClientMonitor[i]->issueConnect();
63  }
64  }
65  for(size_t i=0; i<nchannel; ++i)
66  {
67  if(isConnected[i]) {
68  Status status = pvaClientMonitor[i]->waitConnect();
69  if(status.isOK()) continue;
70  string message = string("channel ") + pvaClientChannelArray[i]->getChannelName()
71  + " PvaChannelMonitor::waitConnect " + status.getMessage();
72  throw std::runtime_error(message);
73  }
74  }
75  for(size_t i=0; i<nchannel; ++i)
76  {
77  if(isConnected[i]) pvaClientMonitor[i]->start();
78  }
79  isMonitorConnected = true;
80 }
81 
82 bool PvaClientMultiMonitorDouble::poll()
83 {
84  if(!isMonitorConnected){
85  connect();
86  epicsThreadSleep(.1);
87  }
88  bool result = false;
89  shared_vector<epics::pvData::boolean> isConnected = pvaClientMultiChannel->getIsConnected();
90  for(size_t i=0; i<nchannel; ++i)
91  {
92  if(isConnected[i]) {
93  if(!pvaClientMonitor[i]){
94  pvaClientMonitor[i] = pvaClientChannelArray[i]->createMonitor("value");
95  pvaClientMonitor[i]->issueConnect();
96  Status status = pvaClientMonitor[i]->waitConnect();
97  if(!status.isOK()) {
98  string message = string("channel ") + pvaClientChannelArray[i]->getChannelName()
99  + " PvaChannelMonitor::waitConnect " + status.getMessage();
100  throw std::runtime_error(message);
101  }
102  pvaClientMonitor[i]->start();
103  }
104  if(pvaClientMonitor[i]->poll()) {
105  doubleValue[i] = pvaClientMonitor[i]->getData()->getDouble();
106  pvaClientMonitor[i]->releaseEvent();
107  result = true;
108  }
109  }
110  }
111  return result;
112 }
113 
114 bool PvaClientMultiMonitorDouble::waitEvent(double waitForEvent)
115 {
116  if(poll()) return true;
117  TimeStamp start;
118  start.getCurrent();
119  TimeStamp now;
120  while(true) {
121  epicsThreadSleep(.1);
122  if(poll()) return true;
123  now.getCurrent();
124  double diff = TimeStamp::diff(now,start);
125  if(diff>=waitForEvent) break;
126  }
127  return false;
128 }
129 
130 shared_vector<double> PvaClientMultiMonitorDouble::get()
131 {
132  return doubleValue;
133 }
134 
135 
136 }}
epics::pvData::shared_vector< PvaClientChannelPtr > PvaClientChannelArray
STL namespace.
std::tr1::shared_ptr< PvaClientMultiMonitorDouble > PvaClientMultiMonitorDoublePtr
Provides a monitor to multiple channels where each channel has a numeric scalar value field...
std::tr1::shared_ptr< PvaClientMultiChannel > PvaClientMultiChannelPtr
std::tr1::shared_ptr< PvaClientMonitor > PvaClientMonitorPtr
Definition: pvaClient.h:81