Example #1
0
void
CTCPSocket::connect(const CNetworkAddress& addr)
{
	{
		CLock lock(&m_mutex);

		// fail on attempts to reconnect
		if (m_socket == NULL || m_connected) {
			sendConnectionFailedEvent("busy");
			return;
		}

		try {
			if (ARCH->connectSocket(m_socket, addr.getAddress())) {
				sendEvent(getConnectedEvent());
				onConnected();
			}
			else {
				// connection is in progress
				m_writable = true;
			}
		}
		catch (XArchNetwork& e) {
			throw XSocketConnect(e.what());
		}
	}
	setJob(newJob());
}
Example #2
0
void
CClientListener::handleUnknownClient(const CEvent&, void* vclient)
{
    CClientProxyUnknown* unknownClient =
        reinterpret_cast<CClientProxyUnknown*>(vclient);

    // we should have the client in our new client list
    assert(m_newClients.count(unknownClient) == 1);

    // get the real client proxy and install it
    CClientProxy* client = unknownClient->orphanClientProxy();
    if (client != NULL) {
        // handshake was successful
        m_waitingClients.push_back(client);
        EVENTQUEUE->addEvent(CEvent(getConnectedEvent(), this));

        // watch for client to disconnect while it's in our queue
        EVENTQUEUE->adoptHandler(CClientProxy::getDisconnectedEvent(), client,
                                 new TMethodEventJob<CClientListener>(this,
                                         &CClientListener::handleClientDisconnected,
                                         client));
    }

    // now finished with unknown client
    EVENTQUEUE->removeHandler(CClientProxyUnknown::getSuccessEvent(), client);
    EVENTQUEUE->removeHandler(CClientProxyUnknown::getFailureEvent(), client);
    m_newClients.erase(unknownClient);
    delete unknownClient;
}
Example #3
0
void
CClient::handshakeComplete()
{
	m_ready = true;
	m_screen->enable();
	sendEvent(getConnectedEvent(), NULL);
}
Example #4
0
void
CIpcClient::handleConnected(const CEvent&, void*)
{
	EVENTQUEUE->addEvent(CEvent(
		getConnectedEvent(), this, m_server, CEvent::kDontFreeData));

	CIpcHelloMessage message(kIpcClientNode);
	send(message);
}
Example #5
0
ISocketMultiplexerJob*
CTCPSocket::serviceConnecting(ISocketMultiplexerJob* job,
				bool, bool write, bool error)
{
	CLock lock(&m_mutex);

	// should only check for errors if error is true but checking a new
	// socket (and a socket that's connecting should be new) for errors
	// should be safe and Mac OS X appears to have a bug where a
	// non-blocking stream socket that fails to connect immediately is
	// reported by select as being writable (i.e. connected) even when
	// the connection has failed.  this is easily demonstrated on OS X
	// 10.3.4 by starting a synergy client and telling to connect to
	// another system that's not running a synergy server.  it will
	// claim to have connected then quickly disconnect (i guess because
	// read returns 0 bytes).  unfortunately, synergy attempts to
	// reconnect immediately, the process repeats and we end up
	// spinning the CPU.  luckily, OS X does set SO_ERROR on the
	// socket correctly when the connection has failed so checking for
	// errors works.  (curiously, sometimes OS X doesn't report
	// connection refused.  when that happens it at least doesn't
	// report the socket as being writable so synergy is able to time
	// out the attempt.)
	if (error || true) {
		try {
			// connection may have failed or succeeded
			ARCH->throwErrorOnSocket(m_socket);
		}
		catch (XArchNetwork& e) {
			sendConnectionFailedEvent(e.what().c_str());
			onDisconnected();
			return newJob();
		}
	}

	if (write) {
		sendEvent(getConnectedEvent());
		onConnected();
		return newJob();
	}

	return job;
}