rlpx/rlpx_session.hpp
Namespaces
Classes
Types
|
Name |
| using std::function< void(const protocol::Message &)> |
MessageHandler |
| using std::function< void(const protocol::HelloMessage &)> |
HelloHandler |
| using std::function< void(const protocol::DisconnectMessage &)> |
DisconnectHandler |
| using std::function< void(const protocol::PingMessage &)> |
PingHandler |
| using std::function< void(const protocol::PongMessage &)> |
PongHandler |
Types Documentation
using MessageHandler
using rlpx::MessageHandler = std::function<void(const protocol::Message&)>;
using HelloHandler
using rlpx::HelloHandler = std::function<void(const protocol::HelloMessage&)>;
using DisconnectHandler
using rlpx::DisconnectHandler = std::function<void(const protocol::DisconnectMessage&)>;
using PingHandler
using rlpx::PingHandler = std::function<void(const protocol::PingMessage&)>;
using PongHandler
using rlpx::PongHandler = std::function<void(const protocol::PongMessage&)>;
Source code
// Copyright 2025 GeniusVentures
// SPDX-License-Identifier: Apache-2.0
#pragma once
#include "rlpx_types.hpp"
#include "rlpx_error.hpp"
#include "framing/message_stream.hpp"
#include "protocol/messages.hpp"
#include <boost/asio/spawn.hpp>
#include <atomic>
#include <memory>
#include <functional>
namespace rlpx {
// Message handler callback types
using MessageHandler = std::function<void(const protocol::Message&)>;
using HelloHandler = std::function<void(const protocol::HelloMessage&)>;
using DisconnectHandler = std::function<void(const protocol::DisconnectMessage&)>;
using PingHandler = std::function<void(const protocol::PingMessage&)>;
using PongHandler = std::function<void(const protocol::PongMessage&)>;
// Session creation parameters for outbound connections
struct SessionConnectParams {
std::string_view remote_host;
uint16_t remote_port;
gsl::span<const uint8_t, kPublicKeySize> local_public_key;
gsl::span<const uint8_t, kPrivateKeySize> local_private_key;
PublicKey peer_public_key;
std::string_view client_id;
uint16_t listen_port;
};
// Session creation parameters for inbound connections
struct SessionAcceptParams {
gsl::span<const uint8_t, kPublicKeySize> local_public_key;
gsl::span<const uint8_t, kPrivateKeySize> local_private_key;
std::string_view client_id;
uint16_t listen_port;
// Socket passed separately via executor context
};
// Peer information (grouped values stored as member)
struct PeerInfo {
PublicKey public_key;
std::string client_id;
uint16_t listen_port;
std::string remote_address;
uint16_t remote_port;
};
class RlpxSession : public std::enable_shared_from_this<RlpxSession> {
public:
[[nodiscard]] static Result<std::shared_ptr<RlpxSession>>
connect(const SessionConnectParams& params, boost::asio::yield_context yield) noexcept;
[[nodiscard]] static Result<std::shared_ptr<RlpxSession>>
accept(const SessionAcceptParams& params, boost::asio::yield_context yield) noexcept;
~RlpxSession();
// Non-copyable, moveable
RlpxSession(const RlpxSession&) = delete;
RlpxSession& operator=(const RlpxSession&) = delete;
RlpxSession(RlpxSession&&) noexcept;
RlpxSession& operator=(RlpxSession&&) noexcept;
[[nodiscard]] VoidResult
post_message(framing::Message message) noexcept;
[[nodiscard]] Result<framing::Message>
receive_message(boost::asio::yield_context yield) noexcept;
[[nodiscard]] VoidResult
disconnect(DisconnectReason reason) noexcept;
[[nodiscard]] VoidResult
disconnect(DisconnectReason reason, boost::asio::yield_context yield) noexcept;
// Message handler registration
void set_hello_handler(HelloHandler handler) noexcept {
hello_handler_ = std::move(handler);
}
void set_disconnect_handler(DisconnectHandler handler) noexcept {
disconnect_handler_ = std::move(handler);
}
void set_ping_handler(PingHandler handler) noexcept {
ping_handler_ = std::move(handler);
}
void set_pong_handler(PongHandler handler) noexcept {
pong_handler_ = std::move(handler);
}
void set_generic_handler(MessageHandler handler) noexcept {
generic_handler_ = std::move(handler);
}
// State queries
[[nodiscard]] SessionState state() const noexcept {
return state_.load(std::memory_order_acquire);
}
[[nodiscard]] bool is_active() const noexcept {
return state() == SessionState::kActive;
}
// Return const reference to grouped peer info
[[nodiscard]] const PeerInfo& peer_info() const noexcept {
return peer_info_;
}
[[nodiscard]] uint8_t negotiated_eth_version() const noexcept
{
return negotiated_eth_version_;
}
// Access to cipher secrets if needed (grouped values)
[[nodiscard]] const auth::FrameSecrets& cipher_secrets() const noexcept;
private:
// Private constructor - use factories
RlpxSession(
std::unique_ptr<framing::MessageStream> stream,
PeerInfo peer_info,
bool is_initiator
) noexcept;
// Internal coroutine loops
[[nodiscard]] VoidResult run_send_loop(boost::asio::yield_context yield) noexcept;
[[nodiscard]] VoidResult run_receive_loop(boost::asio::yield_context yield) noexcept;
// Message routing
void route_message(const protocol::Message& msg) noexcept;
// State transition helpers
[[nodiscard]] bool try_transition_state(SessionState from, SessionState to) noexcept;
[[nodiscard]] bool is_terminal_state(SessionState state) const noexcept;
void force_error_state() noexcept;
// State management
std::atomic<SessionState> state_{SessionState::kUninitialized};
// Message stream (owns cipher and socket abstraction)
std::unique_ptr<framing::MessageStream> stream_;
// Peer metadata - stored as member for const reference access
PeerInfo peer_info_;
uint8_t negotiated_eth_version_{0U};
bool is_initiator_;
// Message channels (lock-free, hidden Boost types)
class MessageChannel;
std::unique_ptr<MessageChannel> send_channel_;
std::unique_ptr<MessageChannel> recv_channel_;
// Message handlers
HelloHandler hello_handler_;
DisconnectHandler disconnect_handler_;
PingHandler ping_handler_;
PongHandler pong_handler_;
MessageHandler generic_handler_;
};
} // namespace rlpx
Updated on 2026-04-13 at 23:22:46 -0700