xapian-core  2.1.0
remoteconnection.h
Go to the documentation of this file.
1 
4 /* Copyright (C) 2006-2026 Olly Betts
5  *
6  * This program is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License as published by
8  * the Free Software Foundation; either version 2 of the License, or
9  * (at your option) any later version.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program; if not, see
18  * <https://www.gnu.org/licenses/>.
19  */
20 
21 #ifndef XAPIAN_INCLUDED_REMOTECONNECTION_H
22 #define XAPIAN_INCLUDED_REMOTECONNECTION_H
23 
24 #include <string>
25 
26 #include "remoteprotocol.h"
27 
28 #ifdef __WIN32__
29 # include "safewinsock2.h"
30 #else
31 # include "safesyssocket.h"
32 #endif
33 
43  void operator=(const RemoteConnection &);
44 
47 
53  int fdin;
54 
61  int fdout;
62 
63 #ifndef __WIN32__
64  // On Unix-like platforms we want to avoid generating SIGPIPE when writing
65  // to a socket when the other end has been closed since signals break the
66  // encapsulation of what we're doing inside the library - either user code
67  // would need to handle the SIGPIPE, or we set a signal handler for SIGPIPE
68  // but that would handle *any* SIGPIPE in the process, not just those we
69  // might trigger, and that could break user code which expects to trigger
70  // and handle SIGPIPE.
71  //
72  // We don't need SIGPIPE since we can check errno==EPIPE instead (which is
73  // actually simpler to do).
74  //
75  // We support using SO_NOSIGPIPE (not standardised) or MSG_NOSIGNAL
76  // (specified by POSIX but more awkward to use) which seems to cover all
77  // modern Unix-like platforms. For platforms without either we currently
78  // just set the SIGPIPE signal handler to SIG_IGN.
79 # if defined(SO_NOSIGPIPE) && !defined(__NetBSD__)
80  // Prefer using SO_NOSIGPIPE and write(), except on NetBSD where we seem to
81  // still get SIGPIPE despite using it.
82 # define USE_SO_NOSIGPIPE
83 # elif defined MSG_NOSIGNAL
84  // Use send(..., MSG_NOSIGNAL).
85  int send_flags = MSG_NOSIGNAL;
86 # define USE_MSG_NOSIGNAL
87 # endif
88 #endif
89 
91  std::string buffer;
92 
95 
108  bool read_at_least(size_t min_len, double end_time);
109 
110 #ifdef __WIN32__
117  WSAOVERLAPPED overlapped;
118 
123  DWORD calc_read_wait_msecs(double end_time);
124 #else
126  ssize_t send_or_write(const void* p, size_t n);
127 #endif
128 
129  protected:
134  std::string context;
135 
136  public:
138  RemoteConnection(int fdin_, int fdout_,
139  const std::string & context_ = std::string());
140 
141 #ifdef __WIN32__
143  ~RemoteConnection();
144 #endif
145 
147  int get_read_fd() const { return fdin; }
148 
165  int sniff_next_message_type(double end_time);
166 
176  int get_message(std::string &result, double end_time);
177 
193  int get_message_chunked(double end_time);
194 
215  int get_message_chunk(std::string &result, size_t at_least,
216  double end_time);
217 
228  int receive_file(const std::string &file, double end_time);
229 
238  void send_message(char type, std::string_view s, double end_time);
239 
248  void send_file(char type, int fd, double end_time);
249 
255  void shutdown();
256 
258  void do_close();
259 
261  const std::string& get_context() const { return context; }
262 };
263 
270  public:
272  OwnedRemoteConnection(int fdin_, int fdout_,
273  const std::string& context_ = std::string())
274  : RemoteConnection(fdin_, fdout_, context_) { }
275 
278  do_close();
279  }
280 };
281 
282 #endif // XAPIAN_INCLUDED_REMOTECONNECTION_H
RemoteConnection which owns its own fd(s).
OwnedRemoteConnection(int fdin_, int fdout_, const std::string &context_=std::string())
Constructor.
~OwnedRemoteConnection()
Destructor.
A RemoteConnection object provides a bidirectional connection to another RemoteConnection object on a...
void send_message(char type, std::string_view s, double end_time)
Send a message.
int fdin
The file descriptor used for reading.
std::string buffer
Buffer to hold unprocessed input.
const std::string & get_context() const
Return the context to report with errors.
RemoteConnection(const RemoteConnection &)
Don't allow copying.
int get_message_chunk(std::string &result, size_t at_least, double end_time)
Read a chunk of a message from fdin.
bool read_at_least(size_t min_len, double end_time)
Read until there are at least min_len bytes in buffer.
int fdout
The file descriptor used for writing.
int receive_file(const std::string &file, double end_time)
Save the contents of a message as a file.
void do_close()
Close the connection.
int get_read_fd() const
Return the underlying fd this remote connection reads from.
int get_message(std::string &result, double end_time)
Read one message from fdin.
size_t chunked_data_left
Remaining bytes of message data still to come over fdin for a chunked read.
void shutdown()
Shutdown the connection.
int sniff_next_message_type(double end_time)
Check what the next message type is.
int get_message_chunked(double end_time)
Prepare to read one message from fdin in chunks.
std::string context
The context to report with errors.
ssize_t send_or_write(const void *p, size_t n)
Helper which calls send() or write().
void operator=(const RemoteConnection &)
Don't allow assignment.
void send_file(char type, int fd, double end_time)
Send the contents of a file as a message.
PositionList * p
double end_time(double timeout)
Return the end time for a timeout in timeout seconds.
Definition: realtime.h:95
Remote protocol version and message numbers.
include <sys/socket.h> with portability workarounds.
include <winsock2.h> but working around problems.