openMSX
RS232Net.hh
Go to the documentation of this file.
1#ifndef RS232NET_HH
2#define RS232NET_HH
3
4#include "RS232Device.hh"
5
6#include "EventListener.hh"
7#include "StringSetting.hh"
8#include "BooleanSetting.hh"
9#include "Socket.hh"
10
11#include "Poller.hh"
12#include "circular_buffer.hh"
13
14#include <atomic>
15#include <mutex>
16#include <span>
17#include <thread>
18#include <cstdint>
19
20namespace openmsx {
21
22class EventDistributor;
23class Scheduler;
24class CommandController;
25
26class RS232Net final : public RS232Device, private EventListener
27{
28public:
29 // opaque structure describing an address for use with socket functions
31 int domain; // the address family (AF_INET, ...)
32 socklen_t len; // the length of the socket address
33 union {
34 struct sockaddr generic; // the generic type needed for calling the socket API
35 struct sockaddr_in ipv4; // an IPv4 socket address
36 struct sockaddr_in6 ipv6; // an IPv6 socket address
38 };
39
40public:
41 RS232Net(EventDistributor& eventDistributor, Scheduler& scheduler,
42 CommandController& commandController);
43 ~RS232Net() override;
44
45 // Pluggable
46 void plugHelper(Connector& connector, EmuTime::param time) override;
47 void unplugHelper(EmuTime::param time) override;
48 [[nodiscard]] std::string_view getName() const override;
49 [[nodiscard]] std::string_view getDescription() const override;
50
51 // input
52 void signal(EmuTime::param time) override;
53
54 // output
55 void recvByte(uint8_t value, EmuTime::param time) override;
56
57 [[nodiscard]] std::optional<bool> getDSR(EmuTime::param time) const override;
58 [[nodiscard]] std::optional<bool> getCTS(EmuTime::param time) const override;
59 [[nodiscard]] std::optional<bool> getDCD(EmuTime::param time) const override;
60 [[nodiscard]] std::optional<bool> getRI(EmuTime::param time) const override;
61 void setDTR(bool status, EmuTime::param time) override;
62 void setRTS(bool status, EmuTime::param time) override;
63
64 template<typename Archive>
65 void serialize(Archive& ar, unsigned version);
66
67private:
68 void run(); // loop of helper thread that reads from 'sockfd'
69
70 // EventListener
71 bool signalEvent(const Event& event) override;
72
73 bool net_put(std::span<const char> buf);
74 void open_socket(const NetworkSocketAddress& socket_address);
75
76private:
77 [[no_unique_address]] SocketActivator socketActivator;
78 EventDistributor& eventDistributor;
79 Scheduler& scheduler;
80
81 // The value of these settings only matters at the time this device gets plugged in.
82 // In other words: changing these settings only takes effect the next time the device gets plugged in.
83 StringSetting rs232NetAddressSetting;
84 BooleanSetting rs232NetUseIP232;
85
86 std::thread thread; // receiving thread (reads from 'sockfd')
87 std::mutex mutex; // to protect shared data between emulation and receiving thread
88 Poller poller; // safe to use from main and receiver thread without extra locking
89 cb_queue<char> queue; // read/written by both the main and the receiver thread. Must hold 'mutex' while doing so.
90 std::atomic<SOCKET> sockfd; // read/written by both threads (use std::atomic as an alternative for locking)
91
92 // These are written by the receiver thread and read by the main thread (use std::atomic as an alternative for locking)
93 std::atomic<bool> DCD; // Data Carrier Detect input status
94 std::atomic<bool> RI; // Ring Indicator input status TODO not yet used (write-only)
95
96 // These are only accessed by the main thread (no need for locking)
97 bool DTR; // Data Terminal Ready output status
98 bool RTS; // Request To Send output status
99
100 // This does not change while the receiving thread is running (no need for locking)
101 bool IP232; // snapshot of 'rs232NetUseIP232' at the moment of plugging
102};
103
104} // namespace openmsx
105
106#endif
This implements a queue on top of circular_buffer (not part of boost).
Represents something you can plug devices into.
Definition Connector.hh:21
Polls for events on a given file descriptor.
Definition Poller.hh:15
void serialize(Archive &ar, unsigned version)
Definition RS232Net.cc:381
void recvByte(uint8_t value, EmuTime::param time) override
Definition RS232Net.cc:293
void plugHelper(Connector &connector, EmuTime::param time) override
Definition RS232Net.cc:154
~RS232Net() override
Definition RS232Net.cc:57
void unplugHelper(EmuTime::param time) override
Definition RS232Net.cc:183
std::string_view getDescription() const override
Description for this pluggable.
Definition RS232Net.cc:204
void setRTS(bool status, EmuTime::param time) override
Definition RS232Net.cc:340
std::optional< bool > getRI(EmuTime::param time) const override
Definition RS232Net.cc:323
void signal(EmuTime::param time) override
Definition RS232Net.cc:262
std::optional< bool > getCTS(EmuTime::param time) const override
Definition RS232Net.cc:313
std::optional< bool > getDCD(EmuTime::param time) const override
Definition RS232Net.cc:318
void setDTR(bool status, EmuTime::param time) override
Definition RS232Net.cc:328
std::optional< bool > getDSR(EmuTime::param time) const override
Definition RS232Net.cc:308
std::string_view getName() const override
Name used to identify this pluggable.
Definition RS232Net.cc:199
This file implemented 3 utility functions:
Definition Autofire.cc:11
int socklen_t
Definition Socket.hh:26
std::variant< KeyUpEvent, KeyDownEvent, MouseMotionEvent, MouseButtonUpEvent, MouseButtonDownEvent, MouseWheelEvent, JoystickAxisMotionEvent, JoystickHatEvent, JoystickButtonUpEvent, JoystickButtonDownEvent, OsdControlReleaseEvent, OsdControlPressEvent, WindowEvent, TextEvent, FileDropEvent, QuitEvent, FinishFrameEvent, CliCommandEvent, GroupEvent, BootEvent, FrameDrawnEvent, BreakEvent, SwitchRendererEvent, TakeReverseSnapshotEvent, AfterTimedEvent, MachineLoadedEvent, MachineActivatedEvent, MachineDeactivatedEvent, MidiInReaderEvent, MidiInWindowsEvent, MidiInCoreMidiEvent, MidiInCoreMidiVirtualEvent, MidiInALSAEvent, Rs232TesterEvent, Rs232NetEvent, ImGuiDelayedActionEvent, ImGuiActiveEvent > Event
Definition Event.hh:445
union openmsx::RS232Net::NetworkSocketAddress::@6 address