1

UDP(WinSocks / C ++)の単純なサーバーとクライアントがあります。

sendto経由でデータグラムクライアント->サーバーを送信し、recvfrom関数から取得したIPとポートを使用してサーバーからクライアントに応答します。

私はそれを見出した:

  1. クライアントからのすべてのsendtoは異なるポートから送信されています
  2. サーバーから応答しようとすると、WindowsはWSAECONNRESETを返します(これは、ポートが閉じていることを意味します-http ://support.microsoft.com/kb/263823

サーバーからクライアントに適切に応答するにはどうすればよいですか(つまり、sendtoを使用して送信するときにクライアントにポートバインディングを強制しますか?)

編集:いくつかのソースコードを追加します:

bool InitClient()
{
    internal->sock = socket(PF_INET, SOCK_DGRAM, 0);
    char8 yes = 1;
    setsockopt(internal->sock, SOL_SOCKET, SO_REUSEADDR, &yes, sizeof(int32));
    return internal->sock != -1;
}
void Send(const IpAddress & target, const uint16 port, const char8 * data, int32 size )
{
    sockaddr_in trgt;
    memset(&trgt, 0, sizeof(trgt));
    trgt.sin_family = AF_INET;
    trgt.sin_port = htons(port);
    trgt.sin_addr.s_addr = target.GetRaw();

    if(sendto(internal->sock, (const char8 *)data, size, 0, (PSOCKADDR)&trgt, sizeof(trgt)) == SOCKET_ERROR)
    {
        LOG("Network sending error: %d", WSAGetLastError());
    }
}
4

1 に答える 1

4

「bind」関数を呼び出して、送信元のローカルポートを指定します。以下のポート4567の使用例。bindからの戻り値を必ず確認してください。ソケットを作成したら、このコードを呼び出してください。

sockaddr_in local = {};
local.family = AF_INET;
local.port = htons(4567);
local.addr = INADDR_ANY;

bind(internal->sock,(sockaddr*)&local, sizeof(local));

4567ではなくポート0にバインドすると、OSはランダムなポートを選択し、それ以降のすべての送受信に使用します。Getsocknameを呼び出すと、bindを呼び出した後にOSが選択したポートを見つけることができます。

于 2011-12-15T22:39:58.100 に答える