tesseract 5.2.0
Loading...
Searching...
No Matches
tesseract::SVNetwork Class Reference

#include <svutil.h>

Public Member Functions

 SVNetwork (const char *hostname, int port)
 Set up a connection to hostname on port.
 
 ~SVNetwork ()
 Destructor.
 
void Send (const char *msg)
 Put a message in the messagebuffer to the server and try to send it.
 
char * Receive ()
 
void Close ()
 Close the connection to the server.
 
void Flush ()
 Flush the buffer.
 

Detailed Description

The SVNetwork class takes care of the remote connection for ScrollView This means setting up and maintaining a remote connection, sending and receiving messages and closing the connection. It is designed to work on both Linux and Windows.

Definition at line 71 of file svutil.h.

Constructor & Destructor Documentation

◆ SVNetwork()

tesseract::SVNetwork::SVNetwork ( const char *  hostname,
int  port 
)

Set up a connection to hostname on port.

Definition at line 275 of file svutil.cpp.

275 {
276 msg_buffer_in_ = new char[kMaxMsgSize + 1];
277 msg_buffer_in_[0] = '\0';
278
279 buffer_ptr_ = nullptr;
280
281 struct addrinfo *addr_info = nullptr;
282 auto port_string = std::to_string(port);
283# ifdef _WIN32
284 // Initialize Winsock
285 WSADATA wsaData;
286 int iResult = WSAStartup(MAKEWORD(2, 2), &wsaData);
287 if (iResult != 0) {
288 std::cerr << "WSAStartup failed: " << iResult << std::endl;
289 }
290# endif // _WIN32
291
292 if (getaddrinfo(hostname, port_string.c_str(), nullptr, &addr_info) != 0) {
293 std::cerr << "Error resolving name for ScrollView host "
294 << std::string(hostname) << ":" << port << std::endl;
295# ifdef _WIN32
296 WSACleanup();
297# endif // _WIN32
298 }
299
300 stream_ = socket(addr_info->ai_family, addr_info->ai_socktype,
301 addr_info->ai_protocol);
302
303 if (stream_ < 0) {
304 std::cerr << "Failed to open socket" << std::endl;
305 } else if (connect(stream_, addr_info->ai_addr, addr_info->ai_addrlen) < 0) {
306 // If server is not there, we will start a new server as local child
307 // process.
308 const char *scrollview_path = getenv("SCROLLVIEW_PATH");
309 if (scrollview_path == nullptr) {
310# ifdef SCROLLVIEW_PATH
311# define _STR(a) # a
312# define _XSTR(a) _STR(a)
313 scrollview_path = _XSTR(SCROLLVIEW_PATH);
314# undef _XSTR
315# undef _STR
316# else
317 scrollview_path = ".";
318# endif
319 }
320 const char *prog = ScrollViewProg();
321 std::string command = ScrollViewCommand(scrollview_path);
322 SVSync::StartProcess(prog, command.c_str());
323
324 // Wait for server to show up.
325 // Note: There is no exception handling in case the server never turns up.
326
327 Close();
328 for (;;) {
329 stream_ = socket(addr_info->ai_family, addr_info->ai_socktype,
330 addr_info->ai_protocol);
331 if (stream_ >= 0) {
332 if (connect(stream_, addr_info->ai_addr, addr_info->ai_addrlen) == 0) {
333 break;
334 }
335
336 Close();
337
338 std::cout << "ScrollView: Waiting for server...\n";
339 std::this_thread::sleep_for(std::chrono::seconds(1));
340 }
341 }
342 }
343# ifdef _WIN32
344 // WSACleanup(); // This cause ScrollView windows is not displayed
345# endif // _WIN32
346 freeaddrinfo(addr_info);
347}
const int kMaxMsgSize
Definition: scrollview.cpp:46
static void StartProcess(const char *executable, const char *args)
Starts a new process.
Definition: svutil.cpp:67
void Close()
Close the connection to the server.
Definition: svutil.cpp:225

◆ ~SVNetwork()

tesseract::SVNetwork::~SVNetwork ( )

Destructor.

Definition at line 349 of file svutil.cpp.

349 {
350 Close();
351 delete[] msg_buffer_in_;
352}

Member Function Documentation

◆ Close()

void tesseract::SVNetwork::Close ( )

Close the connection to the server.

Definition at line 225 of file svutil.cpp.

225 {
226# ifdef _WIN32
227 closesocket(stream_);
228# else
229 close(stream_);
230# endif
231 // Mark stream_ as invalid.
232 stream_ = -1;
233}

◆ Flush()

void tesseract::SVNetwork::Flush ( )

Flush the buffer.

Definition at line 170 of file svutil.cpp.

170 {
171 std::lock_guard<std::mutex> guard(mutex_send_);
172 while (!msg_buffer_out_.empty()) {
173 int i = send(stream_, msg_buffer_out_.c_str(), msg_buffer_out_.length(), 0);
174 msg_buffer_out_.erase(0, i);
175 }
176}

◆ Receive()

char * tesseract::SVNetwork::Receive ( )

Receive a message from the server. This will always return one line of char* (denoted by \n).

Definition at line 180 of file svutil.cpp.

180 {
181 char *result = nullptr;
182 if (buffer_ptr_ != nullptr) {
183 result = strtok_r(nullptr, "\n", &buffer_ptr_);
184 }
185
186 // This means there is something left in the buffer and we return it.
187 if (result != nullptr) {
188 return result;
189 // Otherwise, we read from the stream_.
190 } else {
191 buffer_ptr_ = nullptr;
192
193 // The timeout length is not really important since we are looping anyway
194 // until a new message is delivered.
195 struct timeval tv;
196 tv.tv_sec = 10;
197 tv.tv_usec = 0;
198
199 // Set the flags to return when the stream_ is ready to be read.
200 fd_set readfds;
201 FD_ZERO(&readfds);
202 FD_SET(stream_, &readfds);
203
204 int i = select(stream_ + 1, &readfds, nullptr, nullptr, &tv);
205
206 // The stream_ died.
207 if (i == 0) {
208 return nullptr;
209 }
210
211 // Read the message buffer.
212 i = recv(stream_, msg_buffer_in_, kMaxMsgSize, 0);
213
214 // Server quit (0) or error (-1).
215 if (i <= 0) {
216 return nullptr;
217 }
218 msg_buffer_in_[i] = '\0';
219 // Setup a new string tokenizer.
220 return strtok_r(msg_buffer_in_, "\n", &buffer_ptr_);
221 }
222}

◆ Send()

void tesseract::SVNetwork::Send ( const char *  msg)

Put a message in the messagebuffer to the server and try to send it.

Definition at line 164 of file svutil.cpp.

164 {
165 std::lock_guard<std::mutex> guard(mutex_send_);
166 msg_buffer_out_.append(msg);
167}

The documentation for this class was generated from the following files: