diff --git a/client/controller.cpp b/client/controller.cpp index d470a2c2..e1812788 100644 --- a/client/controller.cpp +++ b/client/controller.cpp @@ -60,7 +60,10 @@ #include "common/aixlog.hpp" #include "common/message/client_info.hpp" #include "common/message/error.hpp" +#include "common/message/factory.hpp" #include "common/message/hello.hpp" +#include "common/message/message.hpp" +#include "common/message/server_settings.hpp" #include "common/message/time.hpp" #include "common/snap_exception.hpp" #include "time_provider.hpp" @@ -459,13 +462,15 @@ void Controller::worker() if (settings_.host_id.empty()) settings_.host_id = ::getHostId(macAddress); + // Start receiver loop + getNextMessage(); + // Say hello to the server std::optional auth; if (settings_.server.auth.has_value()) auth = msg::Hello::Auth{settings_.server.auth->scheme, settings_.server.auth->param}; auto hello = std::make_shared(macAddress, settings_.host_id, settings_.instance, auth); - clientConnection_->sendRequest( - hello, 2s, [this](const boost::system::error_code& ec, std::unique_ptr response) mutable + clientConnection_->sendRequest(hello, 2s, [this](const boost::system::error_code& ec, std::unique_ptr response) mutable { if (ec) { @@ -475,7 +480,22 @@ void Controller::worker() } else { - serverSettings_ = std::move(response); + if (response->type == message_type::kError) + { + auto error_msg = msg::message_cast(std::move(response)); + LOG(ERROR, LOG_TAG) << "Received error repsonse to hello request: " << error_msg->error << ", code: " << error_msg->code + << ", message: " << error_msg->message << "\n"; + // reconnect(); + return; + } + else if (response->type != message_type::kServerSettings) + { + LOG(ERROR, LOG_TAG) << "Received unexpected message type as repsonse to hello request: " << response->type << "\n"; + reconnect(); + return; + } + + serverSettings_ = msg::message_cast(std::move(response)); LOG(INFO, LOG_TAG) << "ServerSettings - buffer: " << serverSettings_->getBufferMs() << ", latency: " << serverSettings_->getLatency() << ", volume: " << serverSettings_->getVolume() << ", muted: " << serverSettings_->isMuted() << "\n"; @@ -483,9 +503,6 @@ void Controller::worker() sendTimeSyncMessage(50); } }); - - // Start receiver loop - getNextMessage(); } else { diff --git a/server/server.cpp b/server/server.cpp index 46fee9b8..55c92bdb 100644 --- a/server/server.cpp +++ b/server/server.cpp @@ -322,26 +322,26 @@ void Server::onMessageReceived(const std::shared_ptr& streamSessi if (auth.has_value()) ec = streamSession->authinfo.authenticate(auth->scheme, auth->param); + std::shared_ptr error_msg; if (!auth.has_value() || ec) { if (ec) LOG(ERROR, LOG_TAG) << "Authentication failed: " << ec.detailed_message() << "\n"; else LOG(ERROR, LOG_TAG) << "Authentication required\n"; - auto error_msg = make_shared(401, "Unauthorized", ec ? ec.detailed_message() : "Authentication required"); - streamSession->send(error_msg, [streamSession](boost::system::error_code ec, std::size_t length) - { - LOG(DEBUG, LOG_TAG) << "Sent result: " << ec << ", len: " << length << "\n"; - streamSession->stop(); - }); - return; + error_msg = make_shared(401, "Unauthorized", ec ? ec.detailed_message() : "Authentication required"); } if (!streamSession->authinfo.hasPermission("Streaming")) { std::string error = "Permission 'Streaming' missing"; LOG(ERROR, LOG_TAG) << error << "\n"; - auto error_msg = make_shared(403, "Forbidden", error); + error_msg = make_shared(403, "Forbidden", error); + } + + if (error_msg) + { + error_msg->refersTo = helloMsg.id; streamSession->send(error_msg, [streamSession](boost::system::error_code ec, std::size_t length) { LOG(DEBUG, LOG_TAG) << "Sent result: " << ec << ", len: " << length << "\n"; diff --git a/server/stream_session_ws.cpp b/server/stream_session_ws.cpp index c01b3c7d..2209da3e 100644 --- a/server/stream_session_ws.cpp +++ b/server/stream_session_ws.cpp @@ -66,19 +66,37 @@ void StreamSessionWebsocket::start() void StreamSessionWebsocket::stop() { + LOG(DEBUG, LOG_TAG) << "stop\n"; boost::beast::error_code ec; if (is_ssl_) { +#if 0 // this might not return if (ssl_ws_->is_open()) ssl_ws_->close(beast::websocket::close_code::normal, ec); +#endif + + if (ssl_ws_->next_layer().lowest_layer().is_open()) + { + ssl_ws_->next_layer().lowest_layer().shutdown(boost::asio::ip::tcp::socket::shutdown_both, ec); + ssl_ws_->next_layer().lowest_layer().close(ec); + } } else { +#if 0 // this might not return if (tcp_ws_->is_open()) tcp_ws_->close(beast::websocket::close_code::normal, ec); +#endif + + if (tcp_ws_->next_layer().is_open()) + { + tcp_ws_->next_layer().shutdown(boost::asio::ip::tcp::socket::shutdown_both, ec); + tcp_ws_->next_layer().close(ec); + } } if (ec) LOG(ERROR, LOG_TAG) << "Error in socket close: " << ec.message() << "\n"; + LOG(DEBUG, LOG_TAG) << "stopped\n"; }