0
votes

Currently I'm success fully make server and client using TIdTCPServer and TIdTCPClient Indy components, but I got a trouble when two client connect to the server at the same time. I have two networks 192.168.10.23 and localhost, when client connect using localhost it's fine and the second client try connect to 192.168.10.23 there still waiting for first client disconnect.

can anyone please give me advice how to handle multiple client using Indy10.

Added:

This my code:

void __fastcall TfrmServer::TCPServerConnect(TIdContext *AContext)
{
    TList *list = TCPServer->Contexts->LockList();
    try
    {
        for (int j=0; j < list->Count; j++)
        {
            TIdContext *myContext = static_cast<TIdContext*>(list->Items[j]);
            CLIENT_AUTH(myContext);

            INFO_CLIENT *br = ((INFO_CLIENT*)brb);
            br->ClientIP    = myContext->Binding()->IP;
            br->ClientPort  = myContext->Binding()->Port;
            br->peerIp      = myContext->Binding()->PeerIP;
            br->peerPort    = myContext->Binding()->PeerPort;

            if (myContext->Connection->Connected())
            {
                for (int i=0; i < list->Count; i++)
                {
                    ListIt = ListClient->Items->Add();
                    ListIt->Caption = String(i+1); // number
                    ListIt->SubItems->Add(br->UserName); // Name
                    ListIt->SubItems->Add(br->ClientIP); // Ip
                    ListIt->SubItems->Add(br->peerIp); // Peer Ip
                    ListIt->SubItems->Add(br->ClientPort); // port
                    ListIt->SubItems->Add(br->peerPort); // port
                    ListIt->SubItems->Add("Connected"); // Status
                }
            }
        }
    }
    __finally
    {
        TCPServer->Contexts->UnlockList();
    }
}

Did this code have supports for multiple client ?

1
The code you have shown is COMPLETELY wrong. You need to get rid of it. While the TIdTCPServer::Contexts list is locked (which you should not be doing at all), no additional clients can connect to the server. And you are manipulating the UI from outside the context of the main thread, which can cause crashes and deadlocks. You need to re-write this code. - Remy Lebeau

1 Answers

3
votes

TIdTCPServer supports multiple simultaneous connections on multiple networks and that works just fine. If your clients are serializing with each other, then the problem has to be in your own code or networking setup. Indy does not prevent multiple clients from connecting to the same server at the same time.

Update: try this:

class TAddToListSync : public TIdSync
{
protected:
    TIdContext *FContext;

    void __fastcall DoSynchronize()
    {
        TListItem *ListIt = frmServer->ListClient->Items->Add();
        ListIt->Caption = String(ListIt->Index+1); // number
        ListIt->SubItems->Add(...); // Name
        ListIt->SubItems->Add(FContext->Binding()->IP); // Ip
        ListIt->SubItems->Add(FContext->Binding()->PeerIP); // Peer Ip
        ListIt->SubItems->Add(FContext->Binding()->Port); // port
        ListIt->SubItems->Add(FContext->Binding()->PeerPort); // port
        ListIt->SubItems->Add("Connected"); // Status
    }

public:
    __fastcall TAddToListSync(TIdContext *AContext)
        : TIdSync(), FContext(AContext)
    {
    }

    static void Add(TIdContext *AContext)
    {
        TAddToListSync *sync = new TAddToListSync(AContext);
        sync->Synchronize();
        delete sync;
    }
};

void __fastcall TfrmServer::TCPServerConnect(TIdContext *AContext) {
{
    CLIENT_AUTH(AContext);
    TAddToListSync::Add(AContext);
}