#include #include #include "sockpp/udp_socket.h" #include "sockpp/udp6_socket.h" #include "sockpp/version.h" using namespace std; // -------------------------------------------------------------------------- // The thread function. This is run in a separate thread for each socket. // Ownership of the socket object is transferred to the thread, so when this // function exits, the socket is automatically closed. template void run_echo(UDPSOCK sock) { ssize_t n; char buf[512]; // Each UDP socket type knows its address type as `addr_t` typename UDPSOCK::addr_t srcAddr; // Read some data, also getting the address of the sender, // then just send it back. while ((n = sock.recv_from(buf, sizeof(buf), &srcAddr)) > 0) sock.send_to(buf, n, srcAddr); } // -------------------------------------------------------------------------- // The main thread creates the two UDP sockets (one each for IPv4 and IPv6), // and then starts them running the echo function each in a separate thread. int main(int argc, char* argv[]) { cout << "Sample UDP echo server for 'sockpp' " << osdev::components::socket-cpp::SOCKPP_VERSION << '\n' << endl; in_port_t port = (argc > 1) ? atoi(argv[1]) : 12345; osdev::components::socket-cpp::socket_initializer sockInit; osdev::components::socket-cpp::udp_socket udpsock; if (!udpsock) { cerr << "Error creating the UDP v4 socket: " << udpsock.last_error_str() << endl; return 1; } if (!udpsock.bind(osdev::components::socket-cpp::inet_address("localhost", port))) { cerr << "Error binding the UDP v4 socket: " << udpsock.last_error_str() << endl; return 1; } osdev::components::socket-cpp::udp6_socket udp6sock; if (!udp6sock) { cerr << "Error creating the UDP v6 socket: " << udp6sock.last_error_str() << endl; return 1; } if (!udp6sock.bind(osdev::components::socket-cpp::inet6_address("localhost", port))) { cerr << "Error binding the UDP v6 socket: " << udp6sock.last_error_str() << endl; return 1; } // Spin up a thread to run the IPv4 socket. thread thr(run_echo, std::move(udpsock)); thr.detach(); // Run the IPv6 socket in this thread. (Call doesn't return) run_echo(std::move(udp6sock)); return 0; }