Bredbandskollen CLI  1.2
Asynchronous network task engine
socket.h
1 // Copyright (c) 2018 IIS (The Internet Foundation in Sweden)
2 // Written by Göran Andersson <initgoran@gmail.com>
3 
4 #pragma once
5 
6 #ifdef _WIN32
7 #include <winsock2.h>
8 #endif
9 
10 #include "pollstate.h"
11 #include "logger.h"
12 
13 class Task;
14 
18 class Socket : public Logger {
19  friend class Engine;
20 public:
21  Socket(const std::string &label, Task *owner,
22  const std::string &hostname, uint16_t port);
23 
24  Socket(const std::string &label, Task *owner, int fd);
25 
27  Task *owner() const {
28  return _owner;
29  }
30 
32  std::string hostname() const {
33  return _hostname;
34  }
35 
37  uint16_t port() const {
38  return _port;
39  }
40 
43  PollState state() const {
44  return _state;
45  }
46 
47 #ifndef _WIN32
55  int getUnixDomainPeer() const {
56  return unix_domain_peer;
57  }
58 #endif
59 
60  virtual ~Socket();
61 
70  virtual std::string cacheLabel() {
71  return _hostname + std::to_string(_port);
72  }
73 
79  int id() const {
80  return _socket;
81  }
82 
84  virtual void setOwner(Task *t) {
85  _owner = t;
86  }
87 
94  void setExpiry(double s) {
95  expiry = timeAfter(s);
96  }
97 
99  bool hasExpired(const TimePoint &when) const {
100  return (expiry < when);
101  }
102 
104  const char *localIp() const {
105  const char *ip = getIp(socket(), nullptr, false);
106  return ip;
107  }
108 
113  static const char *getIp(int fd, uint16_t *port = nullptr,
114  bool peer = true);
115 
117  static const char *getIp(struct sockaddr *address, uint16_t *port=nullptr);
118 
120  static const char *getIp(struct addrinfo *address, uint16_t *port=nullptr);
121 
123  struct addrinfo *getAddressInfo(uint16_t iptype = 0);
124 protected:
126  static bool isTempError() {
127 #ifdef _WIN32
128  if (WSAGetLastError() == WSAEWOULDBLOCK ||
129  WSAGetLastError() == WSAEINPROGRESS ||
130  WSAGetLastError() == WSAENOTCONN ||
131  !WSAGetLastError())
132 #else
133  if (errno == EAGAIN || errno == EWOULDBLOCK || errno == EINPROGRESS
134  || errno == EINTR || !errno)
135 #endif
136  return true;
137  else
138  return false;
139  }
140 
142  virtual bool wantToSend() {
143  return false;
144  }
145 
155  }
156 
164  void setWantToSend() {
165  if (_state != PollState::CLOSE)
166  _state = PollState::READ_WRITE;
167  }
168 
170  int socket() const {
171  return _socket;
172  }
173 
175  static int closeSocket(int fd);
176 
178  void closeMe() {
179  _state = PollState::CLOSE;
180  }
181 
187  void createNonBlockingSocket(struct addrinfo *addressEntry,
188  struct addrinfo *localAddr=nullptr);
189 
191  bool setNonBlocking(int fd);
192 
194  static bool socketInError(int fd);
195 
197  bool inError() const {
198  if (!socketInError(_socket))
199  return false;
200  errno_log() << "failed socket " << _socket;
201  return true;
202  }
203 private:
204  void setState(PollState state) {
205  if (_state != PollState::CLOSE)
206  _state = state;
207  }
208 
209  // Return false on failure:
210  bool createServerSocket();
211 
212  static void clearCache();
213 
214  void killMe() {
215  _state = PollState::KILL;
216  }
217 
218  // Internal identifier used as key in dns_cache:
219  std::string _peer_label;
220 
221  void setSocket(int fd) {
222  _socket = fd;
223  }
224 
225  Socket(const Socket &);
226  Task *_owner;
227  int _socket;
228 #ifndef _WIN32
229  // If this is a Unix Domain socket, the peer socket descriptor will be
230  // stored here:
231  int unix_domain_peer = 0;
232 #endif
233  std::string _hostname;
234  uint16_t _port;
235  PollState _state;
236  TimePoint expiry = timeMax();
237 };
The network engine.
Definition: engine.h:33
A simple logger. All classes that want to write to the global log file should inherit from this class...
Definition: logger.h:86
std::string label() const
Return the object's log label.
Definition: logger.h:251
static TimePoint timeMax()
Return a very distant time.
Definition: logger.h:228
std::ostream & errno_log() const
Write a line of error log after a failed system call has set the global errno to a non-zero value.
Definition: logger.cpp:143
static TimePoint timeAfter(double s)
Return current time plus s seconds.
Definition: logger.h:223
This is a slave to the Engine class. You can't use it directly, only through its subclasses,...
Definition: socket.h:18
Task * owner() const
Return task owning the socket.
Definition: socket.h:27
static bool socketInError(int fd)
Return true if the file descriptor has encountered a fatal error.
Definition: socket.cpp:204
PollState state() const
Return current socket state.
Definition: socket.h:43
static int closeSocket(int fd)
Close a file descriptor.
Definition: socket.cpp:196
virtual void setOwner(Task *t)
Set the given task as owner of the socket.
Definition: socket.h:84
int getUnixDomainPeer() const
Return the peer socket descriptor.
Definition: socket.h:55
int id() const
Return unique connection ID if connected.
Definition: socket.h:79
bool inError() const
Return true if the socket has encountered a fatal error.
Definition: socket.h:197
std::string hostname() const
Return name of the host to which the socket is supposed to connect.
Definition: socket.h:32
void setWantToSend()
Notify intention of sending large amounts of data.
Definition: socket.h:164
static bool isTempError()
Return true unless last syscall encountered a fatal error.
Definition: socket.h:126
bool hasExpired(const TimePoint &when) const
Return true if the given TimePoint is after the socket's expiry.
Definition: socket.h:99
struct addrinfo * getAddressInfo(uint16_t iptype=0)
Perform DNS lookup of remote host.
Definition: socket.cpp:100
virtual std::string cacheLabel()
Return the socket's cache group, or an empty string.
Definition: socket.h:70
virtual PollState checkReadBlock()
This will be called regularly on READ_BLOCKED sockets to check if the block can be lifted.
Definition: socket.h:153
int socket() const
Return file descriptor.
Definition: socket.h:170
void createNonBlockingSocket(struct addrinfo *addressEntry, struct addrinfo *localAddr=nullptr)
Create socket and initiate the connection.
Definition: socket.cpp:162
uint16_t port() const
Return port number to which the socket is supposed to connect.
Definition: socket.h:37
bool setNonBlocking(int fd)
Set socket as non-blocking.
Definition: socket.cpp:219
const char * localIp() const
Return local IP address in static buffer.
Definition: socket.h:104
static const char * getIp(int fd, uint16_t *port=nullptr, bool peer=true)
Return IP address of connected socket in static buffer.
Definition: socket.cpp:283
void setExpiry(double s)
Set a time to live for the socket.
Definition: socket.h:94
virtual bool wantToSend()
Return true if socket is watched for writeability.
Definition: socket.h:142
void closeMe()
Tell the network engine that the connection should be closed.
Definition: socket.h:178
The purpose of a task is to manage socket connections, and/or to execute timers.
Definition: task.h:39
Measure elapsed time during execution, for example by timer events.
PollState
Definition: pollstate.h:11