Files
tdesktop/cmake/external/glib/cppgir/examples/gio.cpp
allhaileris afb81b8278
Some checks failed
Docker. / Ubuntu (push) Has been cancelled
User-agent updater. / User-agent (push) Failing after 15s
Lock Threads / lock (push) Failing after 10s
Waiting for answer. / waiting-for-answer (push) Failing after 22s
Close stale issues and PRs / stale (push) Successful in 13s
Needs user action. / needs-user-action (push) Failing after 8s
Can't reproduce. / cant-reproduce (push) Failing after 8s
init
2026-02-16 15:50:16 +03:00

99 lines
2.5 KiB
C++

#define GI_INLINE 1
#include <gio/gio.hpp>
#include <iostream>
namespace GLib = gi::repository::GLib;
namespace Gio = gi::repository::Gio;
const std::string localhost("127.0.0.1");
static GLib::MainLoop loop;
// many calls here support GError
// so typically will throw here instead
// (unless GError output is explicitly requested in call signature)
// NOTE abundancy of gi::expect not generally needed;
// only needed when using --dl and --expected
static bool
receive(Gio::Socket s, GLib::IOCondition /*cond*/)
{
guint8 buffer[1024] = {
0,
};
Gio::SocketAddress a;
int count = gi::expect(s.receive_from(&a, buffer, sizeof(buffer)));
if (count > 0) {
// let's see where it came from
std::string origin("someone");
auto ia = gi::object_cast<Gio::InetSocketAddress>(a);
if (ia) {
origin = gi::expect(gi::expect(ia.get_address()).to_string());
origin += ":";
origin += std::to_string(gi::expect(ia.get_port()));
}
std::cout << origin << " said " << (char *)buffer << std::endl;
// quit when idle
GLib::idle_add([]() {
loop.quit();
return GLib::SOURCE_REMOVE_;
});
}
return true;
}
Gio::Socket
open(bool listen)
{
auto socket = gi::expect(Gio::Socket::new_(Gio::SocketFamily::IPV4_,
Gio::SocketType::DATAGRAM_, Gio::SocketProtocol::DEFAULT_));
auto address =
gi::expect(Gio::InetSocketAddress::new_from_string(localhost, 0));
socket.bind(address, false);
socket.set_blocking(false);
if (listen) {
// runtime introspection has a hard time here,
// but with a bit of extra information, we can keep going
#if defined(GI_CALL_ARGS) && CALL_ARGS <= 1
// so we should have this signature for a function with 1 non-required
GLib::Source source =
gi::expect(socket.create_source({.condition = GLib::IOCondition::IN_}));
#else
GLib::Source source =
gi::expect(socket.create_source(GLib::IOCondition::IN_, nullptr));
#endif
source.set_callback<Gio::SocketSourceFunc>(receive);
source.attach();
}
return socket;
}
static void
die(const std::string &why)
{
std::cerr << why << std::endl;
exit(2);
}
int
main(int argc, char **argv)
{
if (argc < 2)
die("missing argument");
std::string msg = argv[1];
std::cout << "will send message " << msg << std::endl;
auto recv = open(true);
auto local = gi::expect(recv.get_local_address());
auto send = open(false);
send.send_to(local, (guint8 *)msg.data(), msg.size(), nullptr);
loop = gi::expect(GLib::MainLoop::new_());
loop.run();
}