在Windows Phone平台上选择返回-1的函数

时间:2015-07-29 13:31:11

标签: c++ sockets winapi network-programming winsock2

我正在努力选择功能。如果我只传递readfds和exceptfds参数,该函数工作正常,但是当我传递writefds参数时,select函数返回-1并且WSAGetLastError返回错误代码10022,其中指出:"提供了一些无效参数"。

此功能用于多平台项目中的功能,唯一出现此问题的平台是Windows Phone平台。在其余平台上,没有关于此功能的问题。

int result = 0;


fd_set rset;
fd_set wset;
fd_set eset;

FD_ZERO(&rset);
FD_ZERO(&wset);
FD_ZERO(&eset);

for(int i = 0; i<events.size(); i++){
    if(read){
         FD_SET(events[i]->rfd, &rset);
         FD_SET(event[i]->rfd, &eset);
    }

    if(write){
         FD_SET(events[i]->rfd, &wset);
        FD_SET(event[i]->rfd, &eset);
    }
}

int number = event.size();
fd_set rset_copy = rset;
fd_set wset_copy = wset;
fd_set eset_copy = eset;
timeval t;
t.tv_sec = 0;
t.tv_usec = 0;

result = select(number, &rset_copy,&wset_copy,&eset_copy,&t);

编辑

更正了&#34; tv&#34;的传递时间值的名称。到&#34; t&#34;。

2 个答案:

答案 0 :(得分:1)

您的timeval变量名为t,但您将另一个名为tv的变量传递给select()的最后一个参数。根据{{​​3}}:

  

WSAEINVAL
  超时值无效,或者所有三个描述符参数均为空。

此外,如果readwrite为假,请勿将相应的fd_set传递给select(),而是传递NULL。

旁注:

  1. 在Windows平台上忽略select()的第一个参数(其他平台确实使用它),因此只需将其设置为0.无论如何都不会将正确的值传递给它。

  2. 不需要复制fd_set结构,因为它们是开始的局部变量。

  3. write为真时,您确定->rfd是要存储在wset中的正确套接字吗?什么是event[i]被确切地声明?是否有->wfd字段?

  4. 请改为尝试:

    if ((!events.empty()) && (read || write))
    {
        int result = 0;
    
        fd_set rset, *prset = NULL;
        fd_set wset, *pwset = NULL;
        fd_set eset;
    
        FD_ZERO(&rset);
        FD_ZERO(&wset);
        FD_ZERO(&eset);
    
        for(int i = 0; i < events.size(); i++)
        {
            if (read) FD_SET(events[i]->rfd, &rset);
            if (write) FD_SET(events[i]->rfd, &wset);
            FD_SET(event[i]->rfd, &eset);
        }
    
        if (read) prset = &rset;
        if (write) pwset = &wset;
    
        timeval t;
        t.tv_sec = 0;
        t.tv_usec = 0;
    
        result = select(0, prset, pwset, &eset, &t);
        //...
    }
    

答案 1 :(得分:0)

假设这只是整个代码的一部分。我不知道在visual c和Windows Phone中它是否会有所不同,但这可能有所帮助。

result = select(number, &rset_copy,&wset_copy,&eset_copy,&tv);

当你宣布时间t时,你正在传递&amp; tv。这是编译时错误。我假设你的代码不同。

  • 检查读取或写入是否大于0
  • 您确定所有事件[i] - &gt; rfd绝对是套接字的有效文件描述符吗?
  • 你是否包括Winsock2.h?
  • 尝试使用null而不是&amp; t(或tv)来阻止选择:

result = select(number, &rset_copy,&wset_copy,&eset_copy,null);