/* ex:ts=4:sw=4:sts=4:et */ /* -*- tab-width: 4; c-basic-offset: 4; indent-tabs-mode: nil -*- */ /** * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 as * published by the Free Software Foundation. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License along * with this program; if not, write to the Free Software Foundation, Inc., * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. * * AUTHORS * Maciek Borzecki */ class Discovery : GLib.Object { private Socket socket = null; public signal void device_found(Device dev); public Discovery() { } ~Discovery() { debug("cleaning up discovery..."); if (this.socket != null) { this.socket.close(); } } public void listen() throws Error { this.socket = new Socket(SocketFamily.IPV4, SocketType.DATAGRAM, SocketProtocol.UDP); var sa = new InetSocketAddress(new InetAddress.any(SocketFamily.IPV4), 1714); debug("start listening for new devices at: %s:%u", sa.address.to_string(), sa.port); try { socket.bind(sa, false); } catch (Error e) { this.socket.close(); this.socket = null; throw e; } var source = socket.create_source(IOCondition.IN); source.set_callback((s, c) => { this.incomingPacket(); return true; }); source.attach(MainContext.default()); } private void incomingPacket() { debug("incoming packet"); uint8 buffer[4096]; SocketAddress sa; InetSocketAddress isa; try { ssize_t read = this.socket.receive_from(out sa, buffer); isa = (InetSocketAddress)sa; debug("got %zd bytes from: %s:%u", read, isa.address.to_string(), isa.port); } catch (Error e) { message("failed to receive packet: %s", e.message); return; } debug("message data: %s", (string)buffer); this.parsePacketFromHost((string) buffer, isa.address); } private void parsePacketFromHost(string data, InetAddress host) { // expecing an identity packet var pkt = Packet.new_from_data(data); if (pkt.pkt_type != Packet.IDENTITY) { message("unexpected packet type %s from device %s", pkt.pkt_type, host.to_string()); return; } var dev = new Device.from_identity(pkt, host); message("connection from device: \'%s\', responds at: %s:%u", dev.device_name, host.to_string(), dev.tcp_port); device_found(dev); } }