LCOV - code coverage report
Current view: top level - asio/sockets - unix_socket.cpp (source / functions) Coverage Total Hit
Test: coverage_filtered.info Lines: 90.3 % 62 56
Test Date: 2026-02-20 15:38:22 Functions: 87.5 % 24 21

            Line data    Source code
       1              : #include "unix_socket.hpp"
       2              : #include "../../util/logger.hpp"
       3              : #include <boost/asio/read.hpp>
       4              : #include <boost/asio/write.hpp>
       5              : #include <boost/asio/read_until.hpp>
       6              : 
       7              : namespace thinger::asio {
       8              : 
       9           66 : unix_socket::unix_socket(const std::string &context, boost::asio::io_context &io_context)
      10           66 :     : socket(context, io_context), socket_(io_context) {
      11           66 : }
      12              : 
      13           66 : unix_socket::unix_socket(const std::string &context, boost::asio::local::stream_protocol::socket&& sock)
      14           66 :     : socket(context, static_cast<boost::asio::io_context&>(sock.get_executor().context()))
      15          132 :     , socket_(std::move(sock)) {
      16           66 : }
      17              : 
      18          132 : unix_socket::~unix_socket() {
      19          132 :     unix_socket::close();
      20          132 : }
      21              : 
      22          198 : void unix_socket::close() {
      23          198 :     if (socket_.is_open()) {
      24          132 :         boost::system::error_code ec;
      25          132 :         socket_.close(ec);
      26              :     }
      27          198 : }
      28              : 
      29            3 : void unix_socket::cancel() {
      30            3 :     socket_.cancel();
      31            3 : }
      32              : 
      33           66 : awaitable<boost::system::error_code> unix_socket::connect(const std::string &path, std::chrono::seconds timeout) {
      34              :     close();
      35              : 
      36              :     // Setup timeout timer
      37              :     boost::asio::steady_timer timer(io_context_);
      38              :     timer.expires_after(timeout);
      39              : 
      40              :     bool timed_out = false;
      41              :     boost::system::error_code connect_ec;
      42              : 
      43              :     // Start timeout
      44           66 :     auto timeout_coro = [&]() -> awaitable<void> {
      45              :         auto [ec] = co_await timer.async_wait(use_nothrow_awaitable);
      46              :         if (!ec) {
      47              :             timed_out = true;
      48              :             socket_.cancel();
      49              :         }
      50          132 :     };
      51              : 
      52              :     // Start connect
      53           66 :     auto connect_coro = [&]() -> awaitable<void> {
      54              :         auto [ec] = co_await socket_.async_connect(
      55              :             boost::asio::local::stream_protocol::endpoint(path),
      56              :             use_nothrow_awaitable);
      57              :         timer.cancel();
      58              :         if (ec) {
      59              :             connect_ec = timed_out ? boost::asio::error::timed_out : ec;
      60              :         }
      61          132 :     };
      62              : 
      63              :     co_spawn(io_context_, timeout_coro(), detached);
      64              :     co_await connect_coro();
      65              : 
      66              :     co_return connect_ec;
      67          132 : }
      68              : 
      69            0 : awaitable<boost::system::error_code> unix_socket::connect(
      70              :     const std::string &host,
      71              :     const std::string &port,
      72              :     std::chrono::seconds timeout)
      73              : {
      74              :     LOG_WARNING("calling connect to a unix socket over host/port");
      75              :     co_return co_await connect(host, timeout);
      76            0 : }
      77              : 
      78            3 : std::string unix_socket::get_remote_ip() const {
      79            3 :     boost::system::error_code ec;
      80            3 :     auto remote_ep = socket_.remote_endpoint(ec);
      81            3 :     if (!ec) {
      82            3 :         return remote_ep.path();
      83              :     }
      84            0 :     return "";
      85              : }
      86              : 
      87            3 : std::string unix_socket::get_local_port() const {
      88            6 :     return "0";
      89              : }
      90              : 
      91            3 : std::string unix_socket::get_remote_port() const {
      92            6 :     return "0";
      93              : }
      94              : 
      95          263 : awaitable<size_t> unix_socket::read_some(uint8_t buffer[], size_t max_size) {
      96              :     auto [ec, bytes] = co_await socket_.async_read_some(
      97              :         boost::asio::buffer(buffer, max_size),
      98              :         use_nothrow_awaitable);
      99              :     if (ec) co_return 0;
     100              :     co_return bytes;
     101          526 : }
     102              : 
     103            3 : awaitable<size_t> unix_socket::read(uint8_t buffer[], size_t size) {
     104              :     auto [ec, bytes] = co_await boost::asio::async_read(
     105              :         socket_,
     106              :         boost::asio::buffer(buffer, size),
     107              :         boost::asio::transfer_exactly(size),
     108              :         use_nothrow_awaitable);
     109              :     if (ec) co_return 0;
     110              :     co_return bytes;
     111            6 : }
     112              : 
     113            0 : awaitable<size_t> unix_socket::read(boost::asio::streambuf& buffer, size_t size) {
     114              :     auto [ec, bytes] = co_await boost::asio::async_read(
     115              :         socket_,
     116              :         buffer,
     117              :         boost::asio::transfer_exactly(size),
     118              :         use_nothrow_awaitable);
     119              :     if (ec) co_return 0;
     120              :     co_return bytes;
     121            0 : }
     122              : 
     123            3 : awaitable<size_t> unix_socket::read_until(boost::asio::streambuf& buffer, std::string_view delim) {
     124              :     auto [ec, bytes] = co_await boost::asio::async_read_until(
     125              :         socket_,
     126              :         buffer,
     127              :         std::string(delim),
     128              :         use_nothrow_awaitable);
     129              :     if (ec) co_return 0;
     130              :     co_return bytes;
     131            6 : }
     132              : 
     133           15 : awaitable<size_t> unix_socket::write(const uint8_t buffer[], size_t size) {
     134              :     auto [ec, bytes] = co_await boost::asio::async_write(
     135              :         socket_,
     136              :         boost::asio::buffer(buffer, size),
     137              :         use_nothrow_awaitable);
     138              :     if (ec) co_return 0;
     139              :     co_return bytes;
     140           30 : }
     141              : 
     142            9 : awaitable<size_t> unix_socket::write(std::string_view str) {
     143              :     auto [ec, bytes] = co_await boost::asio::async_write(
     144              :         socket_,
     145              :         boost::asio::buffer(str.data(), str.size()),
     146              :         use_nothrow_awaitable);
     147              :     if (ec) co_return 0;
     148              :     co_return bytes;
     149           18 : }
     150              : 
     151           96 : awaitable<size_t> unix_socket::write(const std::vector<boost::asio::const_buffer>& buffers) {
     152              :     auto [ec, bytes] = co_await boost::asio::async_write(
     153              :         socket_,
     154              :         buffers,
     155              :         use_nothrow_awaitable);
     156              :     if (ec) co_return 0;
     157              :     co_return bytes;
     158          192 : }
     159              : 
     160            3 : awaitable<boost::system::error_code> unix_socket::wait(boost::asio::socket_base::wait_type type) {
     161              :     auto [ec] = co_await socket_.async_wait(type, use_nothrow_awaitable);
     162              :     co_return ec;
     163            6 : }
     164              : 
     165          302 : bool unix_socket::is_open() const {
     166          302 :     return socket_.is_open();
     167              : }
     168              : 
     169           51 : bool unix_socket::is_secure() const {
     170           51 :     return false;
     171              : }
     172              : 
     173            3 : size_t unix_socket::available() const {
     174            3 :     boost::system::error_code ec;
     175            3 :     auto size = socket_.available(ec);
     176            3 :     if (ec) {
     177            0 :         LOG_ERROR("error while getting socket available bytes ({}): {}", size, ec.message());
     178              :     }
     179            3 :     return size;
     180              : }
     181              : 
     182              : }
        

Generated by: LCOV version 2.0-1