terom@185: terom@186: #include "UDP.hh" terom@378: #include "../Engine.hh" terom@185: terom@185: #include terom@185: #include terom@185: terom@185: NetworkUDP::NetworkUDP (void) : terom@378: socket(AF_UNSPEC, SOCK_DGRAM) terom@378: { terom@185: // do not bind terom@185: terom@185: // connect signal terom@378: slots.connect(socket.sig_read(), this, &NetworkUDP::on_recv); terom@185: terom@185: // nonblocking terom@185: socket.set_nonblocking(true); terom@380: terom@380: // activate polling terom@380: socket.set_poll_read(true); terom@185: } terom@185: terom@185: NetworkUDP::NetworkUDP (const NetworkAddress &bind_addr) : terom@378: socket(AF_UNSPEC, SOCK_DGRAM) { terom@185: terom@185: // bind socket terom@185: socket.bind(bind_addr); terom@185: terom@185: // connect signal terom@378: slots.connect(socket.sig_read(), this, &NetworkUDP::on_recv); terom@185: terom@185: // nonblocking terom@185: socket.set_nonblocking(true); terom@380: terom@380: // activate polling terom@380: socket.set_poll_read(true); terom@185: } terom@185: terom@185: void NetworkUDP::on_recv (void) { terom@378: size_t ret; terom@185: NetworkPacket pkt; terom@185: NetworkAddress src; terom@185: terom@185: // receieve as many packets as possible terom@185: do { terom@185: // attempt to recv a packet terom@378: ret = socket.recv(pkt.get_buf(), pkt.get_buf_size(), &src); terom@378: terom@378: // no more packets? terom@378: if (ret == 0) terom@378: return; terom@185: terom@185: // set packet data size terom@185: pkt.set_data_size(ret); terom@185: terom@185: // handle packet terom@185: _sig_packet(pkt, src); terom@185: terom@185: } while (true); terom@185: } terom@185: terom@202: bool NetworkUDP::sendto (const NetworkPacketBuffer &packet, const NetworkAddress &dst) { terom@378: size_t ret; terom@185: terom@185: try { terom@378: // try and send terom@378: ret = socket.send(packet.get_buf(), packet.get_data_size(), &dst); terom@185: terom@378: } catch (NetworkSocketError &e) { terom@378: // catch and log errors terom@378: Engine::log(WARN, "udp.sendto") << "socket->send raised error: " << e.what(); terom@185: return false; terom@185: } terom@185: terom@378: // weird packet size? terom@378: if (ret != packet.get_data_size()) { terom@378: Engine::log(ERROR, "udp.sendto") << "socket->send returned weird length: " << ret << ", packet was " << packet.get_data_size(); terom@378: return false; terom@378: terom@378: } else { terom@378: // sent terom@378: return true; terom@378: } terom@185: } terom@185: