diff --git a/daemon/device.cpp b/daemon/device.cpp index 40bede5d8..14e27a5aa 100644 --- a/daemon/device.cpp +++ b/daemon/device.cpp @@ -69,7 +69,7 @@ static bool lessThan(DeviceLink* p1, DeviceLink* p2) void Device::addLink(DeviceLink* link) { - qDebug() << "Adding link to " << id() << "via" << link->provider(); + qDebug() << "Adding link to" << id() << "via" << link->provider(); connect(link,SIGNAL(destroyed(QObject*)),this,SLOT(linkDestroyed(QObject*))); @@ -86,7 +86,6 @@ void Device::addLink(DeviceLink* link) void Device::linkDestroyed(QObject* o) { - qDebug() << "Link destroyed"; removeLink(static_cast(o)); } diff --git a/daemon/linkproviders/avahitcplinkprovider.cpp b/daemon/linkproviders/avahitcplinkprovider.cpp index 4cc58540f..f17333cc0 100644 --- a/daemon/linkproviders/avahitcplinkprovider.cpp +++ b/daemon/linkproviders/avahitcplinkprovider.cpp @@ -53,6 +53,8 @@ void AvahiTcpLinkProvider::onStop() } void AvahiTcpLinkProvider::onNetworkChange(QNetworkSession::State state) { + Q_UNUSED(state); + //Nothing to do, Avahi will handle it } diff --git a/daemon/linkproviders/broadcasttcplinkprovider.cpp b/daemon/linkproviders/broadcasttcplinkprovider.cpp index 1b5295900..780b82505 100644 --- a/daemon/linkproviders/broadcasttcplinkprovider.cpp +++ b/daemon/linkproviders/broadcasttcplinkprovider.cpp @@ -70,20 +70,20 @@ void BroadcastTcpLinkProvider::newUdpConnection() mUdpServer->readDatagram(datagram.data(), datagram.size(), &sender, &senderPort); - NetworkPackage np(""); - NetworkPackage::unserialize(datagram,&np); + NetworkPackage* np = new NetworkPackage(""); + NetworkPackage::unserialize(datagram,np); - if (np.version() > 0 && np.type() == PACKAGE_TYPE_IDENTITY) { + if (np->version() > 0 && np->type() == PACKAGE_TYPE_IDENTITY) { NetworkPackage np2(""); NetworkPackage::createIdentityPackage(&np2); - if (np.get("deviceId") == np2.get("deviceId")) { + if (np->get("deviceId") == np2.get("deviceId")) { qDebug() << "I can't fuck myself!"; return; } - const QString& id = np.get("deviceId"); + const QString& id = np->get("deviceId"); if (links.contains(id)) { //Delete old link if we already know it, probably it is down if this happens. qDebug() << "Destroying old link"; @@ -94,30 +94,70 @@ void BroadcastTcpLinkProvider::newUdpConnection() QTcpSocket* socket = new QTcpSocket(this); qDebug() << "Received Udp presentation from" << sender << "asking for a tcp connection..."; + + receivedIdentityPackages[socket] = np; + connect(socket, SIGNAL(connected()), this, SLOT(connected())); + connect(socket, SIGNAL(error(QAbstractSocket::SocketError)), this, SLOT(connectError())); socket->connectToHost(sender, port); - socket->waitForConnected(); - qDebug() << "Connected" << socket->isWritable(); - TcpDeviceLink* dl = new TcpDeviceLink(id, this, socket); - - connect(dl,SIGNAL(destroyed(QObject*)),this,SLOT(deviceLinkDestroyed(QObject*))); - - links[id] = dl; - bool success = dl->sendPackage(np2); - if (!success) { //FIXME: Why is this happening? - qDebug() << "Fallback, try reverse connection"; - QUdpSocket().writeDatagram(np2.serialize(),sender, port); - } - - qDebug() << "Handshaking done (i'm the existing device)"; - - emit onNewDeviceLink(np, dl); + } else { + delete np; } } } +void BroadcastTcpLinkProvider::connectError() +{ + QTcpSocket* socket = (QTcpSocket*)sender(); + + disconnect(socket, SIGNAL(error(QAbstractSocket::SocketError)), this, SLOT(connectError())); + disconnect(socket, SIGNAL(connected()), this, SLOT(connected())); + + qDebug() << "Fallback (1), try reverse connection"; + onNetworkChange(QNetworkSession::Connected); + +} + +void BroadcastTcpLinkProvider::connected() +{ + + QTcpSocket* socket = (QTcpSocket*)sender(); + + disconnect(socket, SIGNAL(connected()), this, SLOT(connected())); + disconnect(socket, SIGNAL(error(QAbstractSocket::SocketError)), this, SLOT(connectError())); + + NetworkPackage* np = receivedIdentityPackages[socket]; + const QString& id = np->get("deviceId"); + qDebug() << "Connected" << socket->isWritable(); + + TcpDeviceLink* dl = new TcpDeviceLink(id, this, socket); + + connect(dl,SIGNAL(destroyed(QObject*)),this,SLOT(deviceLinkDestroyed(QObject*))); + + links[id] = dl; + + NetworkPackage np2(""); + NetworkPackage::createIdentityPackage(&np2); + + bool success = dl->sendPackage(np2); + + if (success) { + qDebug() << "Handshaking done (i'm the existing device)"; + emit onNewDeviceLink(*np, dl); + } else { + //I think this will never happen + qDebug() << "Fallback (2), try reverse connection"; + onNetworkChange(QNetworkSession::Connected); + delete dl; + } + + receivedIdentityPackages.remove(socket); + delete np; + +} + //I'm the new device and this is the answer to my UDP introduction (no data received yet) void BroadcastTcpLinkProvider::newConnection() { diff --git a/daemon/linkproviders/broadcasttcplinkprovider.h b/daemon/linkproviders/broadcasttcplinkprovider.h index b4580fe02..437a2b773 100644 --- a/daemon/linkproviders/broadcasttcplinkprovider.h +++ b/daemon/linkproviders/broadcasttcplinkprovider.h @@ -45,6 +45,8 @@ public Q_SLOTS: virtual void onNetworkChange(QNetworkSession::State state); virtual void onStart(); virtual void onStop(); + void connected(); + void connectError(); private Q_SLOTS: void newUdpConnection(); @@ -58,6 +60,7 @@ private: const static quint16 port = 1714; QMap links; + QMap receivedIdentityPackages; }; diff --git a/daemon/networkpackage.cpp b/daemon/networkpackage.cpp index 4fea23074..21afcf3e8 100644 --- a/daemon/networkpackage.cpp +++ b/daemon/networkpackage.cpp @@ -33,7 +33,7 @@ const static int CURRENT_PACKAGE_VERSION = 1; -NetworkPackage::NetworkPackage(QString type) +NetworkPackage::NetworkPackage(const QString& type) { mId = time(NULL); mType = type; @@ -63,7 +63,7 @@ QByteArray NetworkPackage::serialize() const return json; } -void NetworkPackage::unserialize(QByteArray a, NetworkPackage* np) +void NetworkPackage::unserialize(const QByteArray& a, NetworkPackage* np) { qDebug() << "Unserialize:" << a; diff --git a/daemon/networkpackage.h b/daemon/networkpackage.h index 5ac0c382c..6b65cd16e 100644 --- a/daemon/networkpackage.h +++ b/daemon/networkpackage.h @@ -39,9 +39,9 @@ class NetworkPackage : public QObject public: - NetworkPackage(QString type); + NetworkPackage(const QString& type); - static void unserialize(QByteArray, NetworkPackage*); + static void unserialize(const QByteArray&, NetworkPackage*); QByteArray serialize() const; static void createIdentityPackage(NetworkPackage*);