10 #include <sys/timeb.h> 13 # include <winsock2.h> 14 static int poll(
struct pollfd *pfd,
int nfds,
int timeout)
25 for (
int i = 0; i < nfds; ++i)
27 if (pfd[i].events & POLLOUT)
29 FD_SET(pfd[i].fd, &writable);
30 FD_SET(pfd[i].fd, &error);
34 int connectionError = 0;
35 if (writable.fd_count > 0)
37 int result = select(0,
nullptr, &writable, &error,
nullptr);
38 if (SOCKET_ERROR == result)
45 for (
int i = 0; i < nfds; ++i)
47 if ((pfd[i].events & POLLOUT) &&
48 (FD_ISSET(pfd[i].fd, &error)))
56 if (connectionError == nfds)
63 return WSAPoll(pfd, nfds, timeout);
68 # if defined(_MSC_VER) 70 # define ftime _ftime_s 73 # include <sys/poll.h> 74 # include <sys/time.h> 106 if (it->getSource() == source)
119 if (it->getSource() == source)
121 it->getMask() = eventMask;
134 const unsigned POLLIN_REQ = POLLIN;
135 const unsigned POLLIN_CHK = (POLLIN | POLLHUP | POLLERR);
136 const unsigned POLLOUT_REQ = POLLOUT;
137 const unsigned POLLOUT_CHK = (POLLOUT | POLLERR);
138 #if !defined(_WINDOWS) 139 const unsigned POLLEX_REQ = POLLPRI;
140 const unsigned POLLEX_CHK = (POLLPRI | POLLNVAL);
142 const unsigned POLLEX_REQ = POLLRDBAND;
143 const unsigned POLLEX_CHK = (POLLRDBAND | POLLNVAL);
150 int timeout_ms =
static_cast<int>(floor(timeout * 1000.));
156 const unsigned source_cnt =
_sources.size();
157 std::vector<pollfd> fds(source_cnt);
158 std::vector<XmlRpcSource *> sources(source_cnt);
160 SourceList::iterator it;
163 sources[i] = it->getSource();
164 fds[i].fd = sources[i]->getfd();
167 if (it->getMask() &
ReadableEvent) fds[i].events |= POLLIN_REQ;
168 if (it->getMask() &
WritableEvent) fds[i].events |= POLLOUT_REQ;
169 if (it->getMask() &
Exception) fds[i].events |= POLLEX_REQ;
173 int nEvents = poll(&fds[0], source_cnt, (timeout_ms < 0) ? -1 : timeout_ms);
177 #if defined(_WINDOWS) 178 XmlRpcUtil::error(
"Error in XmlRpcDispatch::work: error in poll (%d).", WSAGetLastError());
181 XmlRpcUtil::error(
"Error in XmlRpcDispatch::work: error in poll (%d).", nEvents);
188 for (i=0; i < source_cnt; ++i)
191 pollfd & pfd = fds[i];
192 unsigned newMask = (unsigned) -1;
194 bool readable = (pfd.events & POLLIN_REQ) == POLLIN_REQ;
195 bool writable = (pfd.events & POLLOUT_REQ) == POLLOUT_REQ;
196 bool oob = (pfd.events & POLLEX_REQ) == POLLEX_REQ;
197 if (readable && (pfd.revents & POLLIN_CHK))
199 if (writable && (pfd.revents & POLLOUT_CHK))
201 if (oob && (pfd.revents & POLLEX_CHK))
207 SourceList::iterator thisIt;
210 if(thisIt->getSource() == src)
215 XmlRpcUtil::error(
"Error in XmlRpcDispatch::work: couldn't find source iterator");
223 }
else if (newMask != (
unsigned) -1) {
224 thisIt->getMask() = newMask;
233 for (SourceList::iterator it=closeList.begin(); it!=closeList.end(); ++it) {
268 for (SourceList::iterator it=closeList.begin(); it!=closeList.end(); ++it)
269 it->getSource()->close();
281 return ((
double) tbuff.time + ((
double)tbuff.millitm / 1000.0) +
282 ((
double) tbuff.timezone * 60));
287 return ((
double)sec + (
double)nsec / 1e9);
connected/data can be written without blocking
ROSTIME_DECL void ros_steadytime(uint32_t &sec, uint32_t &nsec)
void removeSource(XmlRpcSource *source)
static void error(const char *fmt,...)
Dump error messages somewhere.
void clear()
Clear all sources from the monitored sources list. Sources are closed.
virtual void close()
Close the owned fd. If deleteOnClose was specified at construction, the object is deleted...
XmlRpcDispatch()
Constructor.
An RPC source represents a file descriptor to monitor.
void setSourceEvents(XmlRpcSource *source, unsigned eventMask)
Modify the types of events to watch for on this source.
void addSource(XmlRpcSource *source, unsigned eventMask)
bool getKeepOpen() const
Return whether the file descriptor should be kept open if it is no longer monitored.
out-of-band data has arrived
std::list< MonitoredSource > SourceList
void exit()
Exit from work routine.
virtual unsigned handleEvent(unsigned eventType)=0
Return true to continue monitoring this source.