libreoffice-online/net/ServerSocket.hpp
Ashod Nakashian 2444e28059 wsd: reduce noisy logs
This reduces some logs from debug to trace,
especially in Socket where the amount of
activity is high, but the logs in question
don't add value in debug level.

Also supressed an error when superfluous.

This makes debug-level logs much more readable
and relevant to the main events.

Change-Id: Ie2698b56f320d15a09060cf2877477d9da0e1582
Signed-off-by: Ashod Nakashian <ashod.nakashian@collabora.co.uk>
2022-02-04 10:26:49 -05:00

150 lines
4.2 KiB
C++

/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4; fill-column: 100 -*- */
/*
* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
*/
#pragma once
#include "memory"
#include "Socket.hpp"
#include "Log.hpp"
#include <Poco/Net/SocketAddress.h>
class SocketFactory
{
public:
virtual std::shared_ptr<Socket> create(const int fd) = 0;
};
/// A non-blocking, streaming socket.
class ServerSocket : public Socket
{
public:
ServerSocket(Socket::Type type, SocketPoll& clientPoller, std::shared_ptr<SocketFactory> sockFactory) :
Socket(type),
#if !MOBILEAPP
_type(type),
#endif
_clientPoller(clientPoller),
_sockFactory(std::move(sockFactory))
{
}
/// Control access to a bound TCP socket
enum Type { Local, Public };
/// Create a new server socket - accepted sockets will be added
/// to the @clientSockets' poll when created with @factory.
static std::shared_ptr<ServerSocket> create(ServerSocket::Type type, int port,
Socket::Type socketType, SocketPoll& clientSocket,
std::shared_ptr<SocketFactory> factory)
{
auto serverSocket = std::make_shared<ServerSocket>(socketType, clientSocket, std::move(factory));
if (serverSocket && serverSocket->bind(type, port) && serverSocket->listen())
return serverSocket;
return nullptr;
}
/// Binds to a local address (Servers only).
/// Does not retry on error.
/// Returns true only on success.
virtual bool bind(Type type, int port);
/// Listen to incoming connections (Servers only).
/// Does not retry on error.
/// Returns true on success only.
bool listen(const int backlog = 64)
{
#if !MOBILEAPP
const int rc = ::listen(getFD(), backlog);
#else
const int rc = fakeSocketListen(getFD());
#endif
if (rc)
LOG_SYS('#' << getFD() << " Failed to listen");
else
LOG_TRC('#' << getFD() << " Listening");
return rc == 0;
}
/// Accepts an incoming connection (Servers only).
/// Does not retry on error.
/// Returns a valid Socket shared_ptr on success only.
virtual std::shared_ptr<Socket> accept();
int getPollEvents(std::chrono::steady_clock::time_point /* now */,
int64_t & /* timeoutMaxMicroS */) override
{
return POLLIN;
}
void dumpState(std::ostream& os) override;
void handlePoll(SocketDisposition &,
std::chrono::steady_clock::time_point /* now */,
int events) override
{
if (events & POLLIN)
{
std::shared_ptr<Socket> clientSocket = accept();
if (!clientSocket)
{
const std::string msg = "Failed to accept. (errno: ";
throw std::runtime_error(msg + std::strerror(errno) + ')');
}
LOG_TRC("Accepted client #" << clientSocket->getFD());
_clientPoller.insertNewSocket(clientSocket);
}
}
protected:
/// Create a Socket instance from the accepted socket FD.
std::shared_ptr<Socket> createSocketFromAccept(int fd) const
{
return _sockFactory->create(fd);
}
private:
#if !MOBILEAPP
Socket::Type _type;
#endif
SocketPoll& _clientPoller;
std::shared_ptr<SocketFactory> _sockFactory;
};
#if !MOBILEAPP
/// A non-blocking, streaming Unix Domain Socket for local use
class LocalServerSocket : public ServerSocket
{
public:
LocalServerSocket(SocketPoll& clientPoller, std::shared_ptr<SocketFactory> sockFactory) :
ServerSocket(Socket::Type::Unix, clientPoller, std::move(sockFactory))
{
}
~LocalServerSocket();
virtual bool bind(Type, int) override { assert(false); return false; }
virtual std::shared_ptr<Socket> accept() override;
std::string bind();
#ifndef HAVE_ABSTRACT_UNIX_SOCKETS
bool link(std::string to);
#endif
private:
std::string _name;
#ifndef HAVE_ABSTRACT_UNIX_SOCKETS
std::string _linkName;
#endif
};
#endif
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */