首页 > 解决方案 > Winsock2:select() 函数给出“无效的争论错误”(错误 10022)?

问题描述

运行 select() 函数(提供代码的第 13 行)返回错误 10022 (WSAEINVAL),这意味着我的超时变量为负数或所有 3 个其他变量为 NULL。但是我只有在通过外部循环的第一次迭代后才得到这个错误。

基本上我的设置是在基地发送一个大小为 N 的数据包窗口,然后通过检查我的套接字是否准备好从中读取来检查是否有任何确认已发送回我。对于数据包的第一个窗口,select() 调用工作得很好,返回 1。但是在完整循环的第一次迭代之后对 select() 的所有调用都会导致错误代码。我完全没有想法。

我看到一个线程说只是用另一个函数调用包装函数,它似乎并没有改变问题。我不知道为什么它会在第一个循环中起作用,但在那之后就完全没有了。

int Exit = 0;
int endRecv = 0;
int ready = 0;
//Sending Algorithm
int base = 0;
uint32_t confirmedPosition;



while (Exit == 0) {
    //Send data in an N sized Window.
    for (int i = 0; i < N; i++) {
        if (successfulPackets[i + base] != 1) {
            memcpy(&buffer_tx, &packets[i + base], BUFFERS_LEN);
            sendto(socketS, buffer_tx, BUFFERS_LEN, 0, (sockaddr*)& addrDest, sizeof(addrDest));
        }
    }
    endRecv = 0;
    //Receive Confirmations
    while (endRecv == 0) {
        //Poll to see if something is waiting
        ready = select(NULL, &readfds, NULL, NULL, &pollTime);
        if (ready == -1) {
            printf("Error with Code: %d", WSAGetLastError());
        } else if (ready == 1) {//If yes, log confirmation
            recvfrom(socketS, buffer_rx, BUFFERS_LEN, 0, (sockaddr *)&from, &fromlen);
            memcpy(&confirmedPosition, &buffer_rx, 4);
            successfulPackets[confirmedPosition] = 1;
            fileSize -= BUFFERS_LEN - 8;
        } else {//If no, end receiving and send
            endRecv = 1;
        }
    }
    //Apply Changes to Base
    for (int i = 0; i < N; i++) {
        if (successfulPackets[base] == 1) {
            base++;
        }
    }
    if (fileSize <= 0) {
        Exit = 1;
    }
}

标签: c++winsockwinsock2

解决方案


当 select 返回 0 时,结构 readfds 的内容也设置为零(select 修改它以指示哪个套接字已准备好)。

当外部循环再次执行时,readfds 结构不包含任何要检查的套接字,这会导致错误。您应该在 readfds 中再次设置套接字。


推荐阅读