This is Unofficial EPICS BASE Doxygen Site
pvlist.cpp
Go to the documentation of this file.
1 /*
2  * Copyright information and license terms for this software can be
3  * found in the file LICENSE that is included with the distribution
4  */
5 
6 #include <stdio.h>
7 
8 #include <iostream>
9 #include <map>
10 #include <iterator>
11 #include <vector>
12 #include <string>
13 #include <istream>
14 #include <fstream>
15 #include <sstream>
16 
17 
18 #include <epicsStdlib.h>
19 #include <epicsGetopt.h>
20 #include <pv/logger.h>
21 
22 #include <epicsExit.h>
23 #include <osiSock.h>
24 
25 #include <pv/byteBuffer.h>
26 #include <pv/serializeHelper.h>
27 #include <pv/pvaConstants.h>
28 #include <pv/inetAddressUtil.h>
29 #include <pv/configuration.h>
30 #include <pv/remote.h>
31 #include <pv/rpcClient.h>
32 
33 #if defined(_WIN32) && !defined(_MINGW)
34 FILE *popen(const char *command, const char *mode) {
35  return _popen(command, mode);
36 }
37 int pclose(FILE *stream) {
38  return _pclose(stream);
39 }
40 #endif
41 
42 using namespace std;
43 
44 using namespace epics::pvData;
45 using namespace epics::pvAccess;
46 
47 namespace {
48 
50 static const char lookup[] = {
51  '0', '1', '2', '3', '4', '5', '6', '7',
52  '8', '9', 'A', 'B', 'C', 'D', 'E', 'F'
53 };
54 
56 string toHex(int8* ba, size_t len) {
57  string sb;
58 
59  for (size_t i = 0; i < len; i++)
60  {
61  int8 b = ba[i];
62 
63  int upper = (b>>4)&0x0F;
64  sb += lookup[upper];
65 
66  int lower = b&0x0F;
67  sb += lookup[lower];
68  }
69 
70  return sb;
71 }
72 
73 
74 std::size_t readSize(ByteBuffer* buffer) {
75  int8 b = buffer->getByte();
76  if(b==-1)
77  return -1;
78  else if(b==-2) {
79  int32 s = buffer->getInt();
80  if(s<0) THROW_BASE_EXCEPTION("negative size");
81  return s;
82  }
83  else
84  return (std::size_t)(b<0 ? b+256 : b);
85 }
86 
87 string deserializeString(ByteBuffer* buffer) {
88 
89  std::size_t size = /*SerializeHelper::*/readSize(buffer);
90  if(size!=(size_t)-1) // TODO null strings check, to be removed in the future
91  {
92  // entire string is in buffer, simply create a string out of it (copy)
93  std::size_t pos = buffer->getPosition();
94  string str(buffer->getBuffer()+pos, size);
95  buffer->setPosition(pos+size);
96  return str;
97  }
98  else
99  return std::string();
100 }
101 
102 struct ServerEntry {
103  string guid;
104  string protocol;
105  vector<osiSockAddr> addresses;
106  int8 version;
107 };
108 
109 
110 typedef map<string, ServerEntry> ServerMap;
111 static ServerMap serverMap;
112 
113 // return true if new server response is recevived
114 bool processSearchResponse(osiSockAddr const & responseFrom, ByteBuffer & receiveBuffer)
115 {
116  // first byte is PVA_MAGIC
117  int8 magic = receiveBuffer.getByte();
118  if(magic != PVA_MAGIC)
119  return false;
120 
121  // second byte version
122  int8 version = receiveBuffer.getByte();
123  if(version == 0) {
124  // 0 -> 1 included incompatible changes
125  return false;
126  }
127 
128  // only data for UDP
129  int8 flags = receiveBuffer.getByte();
130  if (flags < 0)
131  {
132  // 7-bit set
133  receiveBuffer.setEndianess(EPICS_ENDIAN_BIG);
134  }
135  else
136  {
137  receiveBuffer.setEndianess(EPICS_ENDIAN_LITTLE);
138  }
139 
140  // command ID and paylaod
141  int8 command = receiveBuffer.getByte();
142  if (command != (int8)0x04)
143  return false;
144 
145  size_t payloadSize = receiveBuffer.getInt();
146  if (payloadSize < (12+4+16+2))
147  return false;
148 
149 
151  receiveBuffer.get(guid.value, 0, sizeof(guid.value));
152 
153  /*int32 searchSequenceId = */receiveBuffer.getInt();
154 
155  osiSockAddr serverAddress;
156  memset(&serverAddress, 0, sizeof(serverAddress));
157  serverAddress.ia.sin_family = AF_INET;
158 
159  // 128-bit IPv6 address
160  if (!decodeAsIPv6Address(&receiveBuffer, &serverAddress))
161  return false;
162 
163  // accept given address if explicitly specified by sender
164  if (serverAddress.ia.sin_addr.s_addr == INADDR_ANY)
165  serverAddress.ia.sin_addr = responseFrom.ia.sin_addr;
166 
167  // NOTE: htons might be a macro (e.g. vxWorks)
168  int16 port = receiveBuffer.getShort();
169  serverAddress.ia.sin_port = htons(port);
170 
171  string protocol = /*SerializeHelper::*/deserializeString(&receiveBuffer);
172 
173  /*bool found =*/ receiveBuffer.getByte(); // != 0;
174 
175 
176  string guidString = toHex((int8*)guid.value, sizeof(guid.value));
177 
178  ServerMap::iterator iter = serverMap.find(guidString);
179  if (iter != serverMap.end())
180  {
181  bool found = false;
182  vector<osiSockAddr>& vec = iter->second.addresses;
183  for (vector<osiSockAddr>::const_iterator ai = vec.begin();
184  ai != vec.end();
185  ai++)
186  if (sockAddrAreIdentical(&(*ai), &serverAddress))
187  {
188  found = true;
189  break;
190  }
191 
192  if (!found)
193  {
194  vec.push_back(serverAddress);
195  return true;
196  }
197  else
198  return false;
199  }
200  else
201  {
202  ServerEntry serverEntry;
203  serverEntry.guid = guidString;
204  serverEntry.protocol = protocol;
205  serverEntry.addresses.push_back(serverAddress);
206  serverEntry.version = version;
207 
208  serverMap[guidString] = serverEntry;
209 
210  return true;
211  }
212 }
213 
214 bool discoverServers(double timeOut)
215 {
216  osiSockAttach();
217 
218  SOCKET socket = epicsSocketCreate(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
219  if (socket == INVALID_SOCKET)
220  {
221  char errStr[64];
222  epicsSocketConvertErrnoToString(errStr, sizeof(errStr));
223  fprintf(stderr, "Failed to create a socket: %s\n", errStr);
224  return false;
225  }
226 
227  //
228  // read config
229  //
230 
231  Configuration::shared_pointer configuration(new SystemConfigurationImpl());
232 
233  string addressList = configuration->getPropertyAsString("EPICS_PVA_ADDR_LIST", "");
234  bool autoAddressList = configuration->getPropertyAsBoolean("EPICS_PVA_AUTO_ADDR_LIST", true);
235  int broadcastPort = configuration->getPropertyAsInteger("EPICS_PVA_BROADCAST_PORT", PVA_BROADCAST_PORT);
236 
237  // quary broadcast addresses of all IFs
238  InetAddrVector broadcastAddresses;
239  {
240  IfaceNodeVector ifaces;
241  if(discoverInterfaces(ifaces, socket, 0)) {
242  fprintf(stderr, "Unable to populate interface list\n");
243  return false;
244  }
245 
246  for(IfaceNodeVector::const_iterator it(ifaces.begin()), end(ifaces.end()); it!=end; ++it)
247  {
248  if(it->validBcast && it->bcast.sa.sa_family == AF_INET) {
249  osiSockAddr bcast = it->bcast;
250  bcast.ia.sin_port = htons(broadcastPort);
251  broadcastAddresses.push_back(bcast);
252  }
253  }
254  }
255 
256  // set broadcast address list
257  if (!addressList.empty())
258  {
259  // if auto is true, add it to specified list
260  InetAddrVector* appendList = 0;
261  if (autoAddressList)
262  appendList = &broadcastAddresses;
263 
264  InetAddrVector list;
265  getSocketAddressList(list, addressList, broadcastPort, appendList);
266  if (!list.empty()) {
267  // delete old list and take ownership of a new one
268  broadcastAddresses = list;
269  }
270  }
271 
272  for (size_t i = 0; i < broadcastAddresses.size(); i++)
274  "Broadcast address #%zu: %s.", i, inetAddressToString(broadcastAddresses[i]).c_str());
275 
276  // ---
277 
278  int optval = 1;
279  int status = ::setsockopt(socket, SOL_SOCKET, SO_BROADCAST, (char *)&optval, sizeof(optval));
280  if (status)
281  {
282  char errStr[64];
283  epicsSocketConvertErrnoToString(errStr, sizeof(errStr));
284  fprintf(stderr, "Error setting SO_BROADCAST: %s\n", errStr);
285  epicsSocketDestroy (socket);
286  return false;
287  }
288 
289  osiSockAddr bindAddr;
290  memset(&bindAddr, 0, sizeof(bindAddr));
291  bindAddr.ia.sin_family = AF_INET;
292  bindAddr.ia.sin_port = htons(0);
293  bindAddr.ia.sin_addr.s_addr = htonl(INADDR_ANY);
294 
295  status = ::bind(socket, (sockaddr*)&(bindAddr.sa), sizeof(sockaddr));
296  if (status)
297  {
298  char errStr[64];
299  epicsSocketConvertErrnoToString(errStr, sizeof(errStr));
300  fprintf(stderr, "Failed to bind: %s\n", errStr);
301  epicsSocketDestroy(socket);
302  return false;
303  }
304 
305  // set timeout
306 #ifdef _WIN32
307  // ms
308  DWORD timeout = 250;
309 #else
310  struct timeval timeout;
311  memset(&timeout, 0, sizeof(struct timeval));
312  timeout.tv_sec = 0;
313  timeout.tv_usec = 250000;
314 #endif
315  status = ::setsockopt (socket, SOL_SOCKET, SO_RCVTIMEO,
316  (char*)&timeout, sizeof(timeout));
317  if (status)
318  {
319  char errStr[64];
320  epicsSocketConvertErrnoToString(errStr, sizeof(errStr));
321  fprintf(stderr, "Error setting SO_RCVTIMEO: %s\n", errStr);
322  return false;
323  }
324 
325  osiSockAddr responseAddress;
326  osiSocklen_t sockLen = sizeof(sockaddr);
327  // read the actual socket info
328  status = ::getsockname(socket, &responseAddress.sa, &sockLen);
329  if (status) {
330  char errStr[64];
331  epicsSocketConvertErrnoToString(errStr, sizeof(errStr));
332  fprintf(stderr, "Failed to get local socket address: %s.", errStr);
333  return false;
334  }
335 
336  char buffer[1024];
337  ByteBuffer sendBuffer(buffer, sizeof(buffer)/sizeof(char));
338 
339  sendBuffer.putByte(PVA_MAGIC);
340  sendBuffer.putByte(PVA_CLIENT_PROTOCOL_REVISION);
341  sendBuffer.putByte((EPICS_BYTE_ORDER == EPICS_ENDIAN_BIG) ? 0x80 : 0x00); // data + 7-bit endianess
342  sendBuffer.putByte((int8_t)CMD_SEARCH); // search
343  sendBuffer.putInt(4+1+3+16+2+1+2); // "zero" payload
344 
345  sendBuffer.putInt(0); // sequenceId
346  sendBuffer.putByte((int8_t)0x81); // reply required // TODO unicast vs multicast; for now we mark ourselves as unicast
347  sendBuffer.putByte((int8_t)0); // reserved
348  sendBuffer.putShort((int16_t)0); // reserved
349 
350  // NOTE: is it possible (very likely) that address is any local address ::ffff:0.0.0.0
351  encodeAsIPv6Address(&sendBuffer, &responseAddress);
352  sendBuffer.putShort((int16_t)ntohs(responseAddress.ia.sin_port));
353 
354  sendBuffer.putByte((int8_t)0x00); // protocol count
355  sendBuffer.putShort((int16_t)0); // name count
356 
357  bool oneOK = false;
358  for (size_t i = 0; i < broadcastAddresses.size(); i++)
359  {
361  char strBuffer[64];
362  sockAddrToDottedIP(&broadcastAddresses[i].sa, strBuffer, sizeof(strBuffer));
363  LOG(logLevelDebug, "UDP Tx (%zu) -> %s", sendBuffer.getPosition(), strBuffer);
364  }
365 
366  status = ::sendto(socket, sendBuffer.getBuffer(), sendBuffer.getPosition(), 0,
367  &broadcastAddresses[i].sa, sizeof(sockaddr));
368  if (status < 0)
369  {
370  char errStr[64];
371  epicsSocketConvertErrnoToString(errStr, sizeof(errStr));
372  fprintf(stderr, "Send error: %s\n", errStr);
373  }
374  else
375  oneOK = true;
376  }
377 
378  if (!oneOK)
379  return false;
380 
381 
382  char rxbuff[1024];
383  ByteBuffer receiveBuffer(rxbuff, sizeof(rxbuff)/sizeof(char));
384 
385  osiSockAddr fromAddress;
386  osiSocklen_t addrStructSize = sizeof(sockaddr);
387 
388  int sendCount = 0;
389 
390  while (true)
391  {
392  receiveBuffer.clear();
393 
394  // receive packet from socket
395  int bytesRead = ::recvfrom(socket, (char*)receiveBuffer.getBuffer(),
396  receiveBuffer.getRemaining(), 0,
397  (sockaddr*)&fromAddress, &addrStructSize);
398 
399  if (bytesRead > 0)
400  {
402  char strBuffer[64];
403  sockAddrToDottedIP(&fromAddress.sa, strBuffer, sizeof(strBuffer));
404  LOG(logLevelDebug, "UDP Rx (%d) <- %s", bytesRead, strBuffer);
405  }
406  receiveBuffer.setPosition(bytesRead);
407  receiveBuffer.flip();
408 
409  processSearchResponse(fromAddress, receiveBuffer);
410 
411  }
412  else
413  {
414  if (bytesRead == -1)
415  {
416  int socketError = SOCKERRNO;
417 
418  // interrupted or timeout
419  if (socketError == SOCK_EINTR ||
420  socketError == EAGAIN || // no alias in libCom
421  // windows times out with this
422  socketError == SOCK_ETIMEDOUT ||
423  socketError == SOCK_EWOULDBLOCK)
424  {
425  // OK
426  }
427  else if (socketError == SOCK_ECONNREFUSED || // avoid spurious ECONNREFUSED in Linux
428  socketError == SOCK_ECONNRESET) // or ECONNRESET in Windows
429  {
430  // OK
431  }
432  else
433  {
434  // unexpected error
435  char errStr[64];
436  epicsSocketConvertErrnoToString(errStr, sizeof(errStr));
437  fprintf(stderr, "Socket recv error: %s\n", errStr);
438  break;
439  }
440 
441  }
442 
443  if (++sendCount < 3)
444  {
445  // TODO duplicate code
446  bool oneOK = false;
447  for (size_t i = 0; i < broadcastAddresses.size(); i++)
448  {
449  // send the packet
450  status = ::sendto(socket, sendBuffer.getBuffer(), sendBuffer.getPosition(), 0,
451  &broadcastAddresses[i].sa, sizeof(sockaddr));
452  if (status < 0)
453  {
454  char errStr[64];
455  epicsSocketConvertErrnoToString(errStr, sizeof(errStr));
456  fprintf(stderr, "Send error: %s\n", errStr);
457  }
458  else
459  oneOK = true;
460  }
461 
462  if (!oneOK)
463  return false;
464 
465  }
466  else
467  break;
468  }
469 
470  }
471 
472  // TODO shutdown sockets?
473  // TODO this resouce is not released on failure
474  epicsSocketDestroy(socket);
475 
476  return true;
477 }
478 
479 
480 #define DEFAULT_TIMEOUT 3.0
481 
482 void usage (void)
483 {
484  fprintf (stderr, "\nUsage: pvlist [options] [<server address or GUID starting with '0x'>]...\n\n"
485  "\noptions:\n"
486  " -h: Help: Print this message\n"
487  " -V: Print version and exit\n"
488  " -i Print server info (when server address list/GUID is given)\n"
489  " -w <sec>: Wait time, specifies timeout, default is %f second(s)\n"
490  " -q: Quiet mode, print only error messages\n"
491  " -d: Enable debug output\n"
492 // " -F <ofs>: Use <ofs> as an alternate output field separator\n"
493 // " -f <input file>: Use <input file> as an input that provides a list input parameters(s) to be read, use '-' for stdin\n"
494  "\nexamples:\n"
495  "\tpvlist\n"
496  "\tpvlist ioc0001\n"
497  "\tpvlist 10.5.1.205:10000\n"
498  "\tpvlist 0x83DE3C540000000000BF351F\n\n"
499  , DEFAULT_TIMEOUT);
500 }
501 
502 }//namespace
503 
504 /*+**************************************************************************
505  *
506  * Function: main
507  *
508  * Description: pvlist main()
509  * Evaluate command line options, ...
510  *
511  * Arg(s) In: [options] [<server>]...
512  *
513  * Arg(s) Out: none
514  *
515  * Return(s): Standard return code (0=success, 1=error)
516  *
517  **************************************************************************-*/
518 
519 int main (int argc, char *argv[])
520 {
521  int opt; /* getopt() current option */
522  bool debug = false;
523  double timeOut = DEFAULT_TIMEOUT;
524  bool printInfo = false;
525 
526  /*
527  istream* inputStream = 0;
528  ifstream ifs;
529  bool fromStream = false;
530  */
531  setvbuf(stdout,NULL,_IOLBF,BUFSIZ); /* Set stdout to line buffering */
532 
533  while ((opt = getopt(argc, argv, ":hVw:qdF:f:i")) != -1) {
534  switch (opt) {
535  case 'h': /* Print usage */
536  usage();
537  return 0;
538  case 'V': /* Print version */
539  {
540  fprintf(stdout, "pvAccess %u.%u.%u%s\n",
541  EPICS_PVA_MAJOR_VERSION,
542  EPICS_PVA_MINOR_VERSION,
543  EPICS_PVA_MAINTENANCE_VERSION,
544  (EPICS_PVA_DEVELOPMENT_FLAG)?"-SNAPSHOT":"");
545  fprintf(stdout, "pvData %u.%u.%u%s\n",
546  EPICS_PVD_MAJOR_VERSION,
547  EPICS_PVD_MINOR_VERSION,
548  EPICS_PVD_MAINTENANCE_VERSION,
549  (EPICS_PVD_DEVELOPMENT_FLAG)?"-SNAPSHOT":"");
550  fprintf(stdout, "Base %s\n", EPICS_VERSION_FULL);
551  return 0;
552  }
553  case 'w': /* Set PVA timeout value */
554  if((epicsScanDouble(optarg, &timeOut)) != 1 || timeOut <= 0.0)
555  {
556  fprintf(stderr, "'%s' is not a valid timeout value "
557  "- ignored. ('pvlist -h' for help.)\n", optarg);
558  timeOut = DEFAULT_TIMEOUT;
559  }
560  break;
561  case 'q': /* Quiet mode */
562  break;
563  case 'd': /* Debug log level */
564  debug = true;
565  break;
566  case 'i': /* Print server info */
567  printInfo = true;
568  break;
569  case '?':
570  fprintf(stderr,
571  "Unrecognized option: '-%c'. ('pvlist -h' for help.)\n",
572  optopt);
573  return 1;
574  case ':':
575  fprintf(stderr,
576  "Option '-%c' requires an argument. ('pvlist -h' for help.)\n",
577  optopt);
578  return 1;
579  default :
580  usage();
581  return 1;
582  }
583  }
584 
586 
587  bool noArgs = (optind == argc);
588 
589  bool byGUIDSearch = false;
590  for (int i = optind; i < argc; i++)
591  {
592  string serverAddress = argv[i];
593 
594  // by GUID search
595  if (serverAddress.length() == 26 &&
596  serverAddress[0] == '0' &&
597  serverAddress[1] == 'x')
598  {
599  byGUIDSearch = true;
600  break;
601  }
602  }
603 
604  bool allOK = true;
605 
606  if (noArgs || byGUIDSearch)
607  discoverServers(timeOut);
608 
609  // just list all the discovered servers
610  if (noArgs)
611  {
612  for (ServerMap::const_iterator iter = serverMap.begin();
613  iter != serverMap.end();
614  iter++)
615  {
616  const ServerEntry& entry = iter->second;
617 
618  cout << "GUID 0x" << entry.guid << " version " << (int)entry.version << ": "
619  << entry.protocol << "@[ ";
620 
621  size_t count = entry.addresses.size();
622  for (size_t i = 0; i < count; i++)
623  {
624  cout << inetAddressToString(entry.addresses[i]);
625  if (i < (count-1))
626  cout << " ";
627  }
628  cout << " ]" << endl;
629  }
630  }
631  else
632  {
633  for (int i = optind; i < argc; i++)
634  {
635  string serverAddress = argv[i];
636 
637  // by GUID search
638  if (serverAddress.length() == 26 &&
639  serverAddress[0] == '0' &&
640  serverAddress[1] == 'x')
641  {
642  bool resolved = false;
643  for (ServerMap::const_iterator iter = serverMap.begin();
644  iter != serverMap.end();
645  iter++)
646  {
647  const ServerEntry& entry = iter->second;
648 
649  if (strncmp(entry.guid.c_str(), &(serverAddress[2]), 24) == 0)
650  {
651  // found match
652 
653  // TODO for now we take only first server address
654  serverAddress = inetAddressToString(entry.addresses[0]);
655  resolved = true;
656  break;
657  }
658  }
659 
660  if (!resolved)
661  {
662  fprintf(stderr, "Failed to resolve GUID '%s'!\n", serverAddress.c_str());
663  allOK = false;
664  continue;
665  }
666  }
667 
668  StructureConstPtr argstype(getFieldCreate()->createFieldBuilder()
669  ->setId("epics:nt/NTURI:1.0")
670  ->add("scheme", pvString)
671  ->add("path", pvString)
672  ->addNestedStructure("query")
673  ->add("op", pvString)
674  ->endNested()
675  ->createStructure());
676 
677  PVStructure::shared_pointer args(getPVDataCreate()->createPVStructure(argstype));
678 
679  args->getSubFieldT<PVString>("scheme")->put("pva");
680  args->getSubFieldT<PVString>("path")->put("server");
681  args->getSubFieldT<PVString>("query.op")->put(printInfo ? "info" : "channels");
682 
683  if(debug) {
684  std::cerr<<"Query to "<<serverAddress<<"\n"<<args<<"\n";
685  }
686 
687  PVStructure::shared_pointer ret;
688  try {
689  RPCClient rpc("server",
690  createRequest("field()"),
691  ChannelProvider::shared_pointer(),
692  serverAddress);
693 
694  if(debug)
695  std::cerr<<"Execute\n";
696  ret = rpc.request(args, timeOut, true);
697  } catch(std::exception& e) {
698  std::cerr<<"Error: "<<e.what()<<"\n";
699  return 1;
700  }
701 
702  if(!printInfo) {
703  PVStringArray::shared_pointer pvs(ret->getSubField<PVStringArray>("value"));
704 
705  PVStringArray::const_svector val(pvs->view());
706 
707  std::copy(val.begin(),
708  val.end(),
709  std::ostream_iterator<std::string>(std::cout, "\n"));
710  }
711  else {
712  std::cout<<ret<<"\n";
713  }
714  }
715  }
716 
717  return allOK ? 0 : 1;
718 }
int8_t int8
Definition: pvType.h:75
#define SOCK_ECONNREFUSED
Definition: osdSock.h:58
double timeout
Definition: pvutils.cpp:25
LIBCOM_API void epicsStdCall epicsSocketDestroy(SOCKET s)
Definition: osdSock.c:117
unsigned epicsStdCall sockAddrToDottedIP(const struct sockaddr *paddr, char *pBuf, unsigned bufSize)
Definition: osiSock.c:118
int getopt(int nargc, char *const *nargv, const char *ostr)
Definition: epicsGetopt.c:65
#define INVALID_SOCKET
Definition: osdSock.h:32
std::tr1::shared_ptr< detail::SharedPut > put
EPICS_ALWAYS_INLINE int8 getByte()
Definition: byteBuffer.h:617
pvd::Status status
int osiSocklen_t
Definition: osdSock.h:36
int i
Definition: scan.c:967
const char * getBuffer() const
Definition: byteBuffer.h:294
struct sockaddr sa
Definition: osiSock.h:158
int optind
Definition: epicsGetopt.c:50
const epics::pvData::int8 PVA_MAGIC
Definition: pvaConstants.h:29
const epics::pvData::int8 PVA_CLIENT_PROTOCOL_REVISION
Definition: pvaConstants.h:32
struct sockaddr_in ia
Definition: osiSock.h:157
#define SET_LOG_LEVEL(level)
Definition: logger.h:50
#define SOCK_ETIMEDOUT
Definition: osdSock.h:54
Definition: memory.hpp:41
int main(int argc, char *argv[])
Definition: pvlist.cpp:519
std::tr1::shared_ptr< const Structure > StructureConstPtr
Definition: pvIntrospect.h:162
#define NULL
Definition: catime.c:38
bucket * lookup(char *name)
Definition: symtab.c:66
#define DEFAULT_TIMEOUT
Definition: pvlist.cpp:480
#define str(v)
std::size_t getPosition() const
Definition: byteBuffer.h:346
#define epicsScanDouble(str, to)
Definition: epicsStdlib.h:78
PVStructure::shared_pointer createRequest(std::string const &request)
void copy(PVValueArray< T > &pvFrom, size_t fromOffset, size_t fromStride, PVValueArray< T > &pvTo, size_t toOffset, size_t toStride, size_t count)
Copy a subarray from one scalar array to another.
void epicsSocketConvertErrnoToString(char *pBuf, unsigned bufSize)
EPICS_ALWAYS_INLINE int32 getInt()
Definition: byteBuffer.h:629
int optopt
Definition: epicsGetopt.c:50
#define SOCK_ECONNRESET
Definition: osdSock.h:53
LIBCOM_API SOCKET epicsStdCall epicsSocketCreate(int domain, int type, int protocol)
Definition: osdSock.c:71
Holds all PVA related.
Definition: pvif.h:34
PVString is special case, since it implements SerializableArray.
Definition: pvData.h:521
#define LOG(level, format,...)
Definition: logger.h:48
void setPosition(std::size_t pos)
Definition: byteBuffer.h:357
epics::pvData::PVStructure::shared_pointer request(epics::pvData::PVStructure::shared_pointer const &pvArgument, double timeout=RPCCLIENT_DEFAULT_TIMEOUT, bool lastRequest=false)
Definition: rpcClient.cpp:187
pvData
Definition: monitor.h:428
std::vector< osiSockAddr > InetAddrVector
template class for all extensions of PVArray.
Definition: pvData.h:55
void encodeAsIPv6Address(ByteBuffer *buffer, const osiSockAddr *address)
#define EPICS_ENDIAN_BIG
Definition: epicsEndian.h:16
std::vector< ifaceNode > IfaceNodeVector
const epics::pvData::int32 PVA_BROADCAST_PORT
Definition: pvaConstants.h:44
This class implements a Bytebuffer that is like the java.nio.ByteBuffer.
Definition: byteBuffer.h:233
BSD and SRV5 Unix timestamp.
Definition: epicsTime.h:52
Extended replacement for the Posix exit and atexit routines.
int SOCKET
Definition: osdSock.h:31
EPICS_ALWAYS_INLINE int16 getShort()
Definition: byteBuffer.h:623
std::size_t getRemaining() const
Definition: byteBuffer.h:391
#define stdout
Definition: epicsStdio.h:30
FORCE_INLINE const FieldCreatePtr & getFieldCreate()
bool decodeAsIPv6Address(ByteBuffer *buffer, osiSockAddr *address)
#define SOCKERRNO
Definition: osdSock.h:33
#define THROW_BASE_EXCEPTION(msg)
void getSocketAddressList(InetAddrVector &ret, const std::string &list, int defaultPort, const InetAddrVector *appendList)
#define SOCK_EINTR
Definition: osdSock.h:64
void setEndianess(int byteOrder)
Definition: byteBuffer.h:285
ConfigurationEnviron SystemConfigurationImpl
bool pvAccessIsLoggable(pvAccessLogLevel level)
Definition: logger.cpp:64
int osiSockAttach()
Definition: osdSock.c:54
int16_t int16
Definition: pvType.h:79
#define stderr
Definition: epicsStdio.h:32
#define EPICS_BYTE_ORDER
Definition: osdWireConfig.h:16
char * optarg
Definition: epicsGetopt.c:55
int epicsStdCall sockAddrAreIdentical(const osiSockAddr *plhs, const osiSockAddr *prhs)
Definition: osiSock.c:35
string inetAddressToString(const osiSockAddr &addr, bool displayPort, bool displayHex)
int discoverInterfaces(IfaceNodeVector &list, SOCKET socket, const osiSockAddr *pMatchAddr)
void usage(void)
Definition: cainfo.c:36
int32_t int32
Definition: pvType.h:83
FORCE_INLINE const PVDataCreatePtr & getPVDataCreate()
Definition: pvData.h:1648
#define SOCK_EWOULDBLOCK
Definition: osdSock.h:51
#define EPICS_ENDIAN_LITTLE
Definition: epicsEndian.h:15