2

IPv6とUDPを使用してCでクライアント/サーバープログラムを作成しようとしています。プログラムがソケットをバインドすると、WSAError 10049が返されます。これがアドレス名の問題であることはわかっていますが、何が問題なのかわかりません。誰かが助けてくれることを願っています。

struct sockaddr_in6 server, client;
SOCKET sock;
char buffer[BUFFERSIZE];
LPTSTR recvBuff[1024];
DWORD recvBuffLen = 1024UL;
int len = sizeof(client);

WORD wVersionRequested;
WSADATA wsaData;
wVersionRequested = MAKEWORD(1,1);
WSAStartup(wVersionRequested, &wsaData);

sock = socket(AF_INET6, SOCK_DGRAM, 0);
if (sock < 0)
    error("Fehler beim Anlegen des Sockets");

server.sin6_family = AF_INET6;
server.sin6_port = htons(6000);
server.sin6_addr = in6addr_any;

if (bind(sock, (struct sockaddr *) &server, sizeof(server)) == -1)
    error("Fehler beim binden des Sockets");
4

4 に答える 4

5

これは通常、ローカルコンピューターで無効なアドレスにバインドしようとしたことが原因です。

PF_INETの代わりにここを使用する必要がありAF_INETます。AFこれらの値は同じですが、ここではアドレスファミリを指定しているのではなく、プロトコルファミリを指定していますPF。これは単なるスタイルの推奨事項です。

memset以下の配列、構造をゼロにすることをお勧めします。

struct sockaddr_in6 server, client;
SOCKET sock;
char buffer[BUFFERSIZE];
LPTSTR recvBuff[1024];
于 2013-01-16T19:49:15.543 に答える
5

sockaddr_in6構造体を使用する前にmemset、ゼロにする必要があります。

  memset(server, 0, sizeof(struct sockaddr_in6));

その理由は、struct sockaddr_in6構造に初期化していない他のフィールド(などsin6_scope_id)が含まれていて、ガベージが含まれている可能性があるためです。

于 2013-01-16T19:46:42.647 に答える
2

私は同じエラーに直面しました。

@askMishの答えは正解です。そもそも理解できませんでしたが、やがてわかりました。

これは通常、ローカルコンピューターで無効なアドレスにバインドしようとしたことが原因です。

通常、コンピュータはゲートウェイの下にあります。

実行ipconfigすると、IPアドレスは192.168.somethingであることがわかります。

これが、コードでバインドするために使用できるIPです。

他の人はパブリックIPに接続する必要がありますが(インターネットをサーフィンできる場合は確かに1つあります)、47.93。と同じLANにある場合は何か。

あなたはあなたのゲートウェイ(おそらくあなたの家族のルート)でそのIPを見つける必要があります。

于 2017-04-18T07:43:42.690 に答える
1

bind()Windowsで呼び出すと、同じエラーコードが発生しました。

私の場合の理由は最初の投稿者のコードと同じではありませんでしたが、他の人が私とまったく同じ間違いを犯したと思います:

-functionを使用して、サーバーをローカルにバインドするローカルアドレスを生成しましたinet_addr()。この結果を次のようにローカルアドレス構造に割り当てましたstruct sockaddr_in localaddr

localaddr.sin_addr.s_addr = htonl(inaddr);

しかし、inet_addr()すでにbyte-network-orderでアドレスを返しているので、htonl(inaddr)私のコードでは呼び出しが間違っていて、エラー10049が発生しました。

SOCKET tcpsock_bindlisten(unsigned short port, const char* bindaddr)
{
    SOCKET srvsock = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP);

    unsigned long inaddr = bindaddr ? inet_addr(bindaddr) : INADDR_ANY;

    struct sockaddr_in localaddr;
    memset(&localaddr, 0, sizeof(struct sockaddr_in));
    localaddr.sin_family        = AF_INET;
    localaddr.sin_port          = htons(port);  

    // ERROR HERE! address returned from inet_addr is already in network-byte-order!
    localaddr.sin_addr.s_addr   = htonl(inaddr); 

    // CORRECT THIS WAY:
    localaddr.sin_addr.s_addr   = inaddr;   

    if (bind(srvsock, (struct sockaddr *) &localaddr, sizeof(localaddr)) != 0)
    {
        print_socketerror("tcpsock bind()");
        return INVALID_SOCKET;
    }

    if (listen(srvsock, SVRSOCK_BACKLOG) != 0)
    {
        print_socketerror("tcpsock listen()");
        return INVALID_SOCKET;
    }

    return srvsock;
}

bind()「すべてのローカルインターフェイス」()を使用して呼び出すとINADDR_ANY、この偶然の一致のために機能しましたINADDR_ANY == htonl(INADDR_ANY)

int main()
{
    ...
    // this works for this special case:
    SOCKET svrsock1 = tcpsock_bindlisten(4444, NULL); 

    // did not work!
    SOCKET svrsock2 = tcpsock_bindlisten(5555, "192.168.0.123"); 
}
于 2015-06-09T13:33:33.453 に答える