标签: winsock2

使用非阻塞udp读取时缺少消息

在两个主机之间的udp中使用非阻塞读取时,我遇到了丢失消息的问题.发件人在linux上,读者在winxp上.python中的这个例子显示了这个问题.
以下是用于显示问题的三个脚本.
send.py:

import socket, sys
s = socket.socket(socket.AF_INET,socket.SOCK_DGRAM)
host = sys.argv[1]
s.sendto('A'*10,   (host,8888))
s.sendto('B'*9000, (host,8888))
s.sendto('C'*9000, (host,8888))
s.sendto('D'*10,   (host,8888))
s.sendto('E'*9000, (host,8888))
s.sendto('F'*9000, (host,8888))
s.sendto('G'*10,   (host,8888))
Run Code Online (Sandbox Code Playgroud)

read.py

import socket
s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
s.bind(('',8888))
while True:
    data,address = s.recvfrom(10000)
    print "recv:", data[0],"times",len(data) 
Run Code Online (Sandbox Code Playgroud)

read_nb.py

import socket
s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
s.bind(('',8888))
s.setblocking(0)
data =''
address = ''
while True:
    try:
        data,address = s.recvfrom(10000)
    except socket.error:
        pass
    else: 
        print "recv:", data[0],"times",len(data) 
Run Code Online (Sandbox Code Playgroud)

示例1(工作正常):

ubuntu> python send.py
winxp> read.py

从read.py得到这个ok结果:

recv:A次10次
recv:B次9000次
recv:C次9000次 …

python sockets udp nonblocking winsock2

6
推荐指数
2
解决办法
8566
查看次数

所有对getaddrinfo()的调用都返回11001

连接到网络上的设备时出现问题.每当我调用getaddrinfo()时它返回11001.我已经在IP_ADDRESS字符串(Global Var)中检查了许多不同的IP.我用nslookup检查了所有非工作号码,大多数存在于那里.

getaddrinfo-returns-always-11001-host-not-found 似乎在问一个类似的问题,但那里没有答案.

目前,我的代码甚至没有尝试连接到远程设备,只是尝试解析IP.一旦有效,我就可以继续处理更大更混乱的问题.

执行:

int connectToDevice(char *sendbuf, char *recvbuf, SOCKET ConnectSocket)
{
WSADATA wsaData;
    struct addrinfo *result = NULL,
                *ptr = NULL,
                hints;
struct timeval tval;

fd_set rset, wset;


int iResult;
u_long mode = -1;

//Initialize Winsock
iResult = WSAStartup(MAKEWORD(2,2), &wsaData);
if (iResult != 0) 
{
    printf("WSAStartup failed with error: %d\n", iResult);
    return 1;
}

ZeroMemory( &hints, sizeof(hints) );
hints.ai_family = AF_UNSPEC;
hints.ai_socktype = SOCK_STREAM;
hints.ai_protocol = IPPROTO_TCP;

//Resolve the server address and port
iResult = getaddrinfo(IP_ADDRESS, DEFAULT_PORT, …
Run Code Online (Sandbox Code Playgroud)

c c++ sockets windows winsock2

6
推荐指数
1
解决办法
1万
查看次数

为什么我的C程序中的ws2_32.dll会出现链接器错误?

我在Visual Studio 2010中编写程序.我无法链接ws2_32.dll以我的项目命名的文件.

谁能告诉我怎么做到这一点?

c winapi linker-errors winsock2 visual-studio

6
推荐指数
3
解决办法
1万
查看次数

为什么Windows上的套接字描述符得到这样的值?

无论如何,不​​确定这是否是正确的地方.
我正在用c ++编写一个简单的聊天,其中客户端获取套接字值作为开头的昵称.
在Linux套接字只是文件描述符,他们得到他们的3,4,5 ...跟随stdin,stdout,stderr.
但我注意到在Win上,第一个客户端套接字总是获得值192,而其他客户端套接字则相差20(几乎总是).
G
所以这就是我的问题,为什么套接字在win平台上获得这样的价值(我的是win7 x64)?小小的谷歌搜索没有帮助.
提前致谢

c++ sockets windows winsock2

6
推荐指数
1
解决办法
1801
查看次数

为什么WSAStringToAddress采用非const AddressString?

WSAStringToAddress的Windows文档指出:

INT WSAAPI WSAStringToAddress(
  _In_     LPTSTR             AddressString,
  _In_     INT                AddressFamily,
  _In_opt_ LPWSAPROTOCOL_INFO lpProtocolInfo,
  _Out_    LPSOCKADDR         lpAddress,
  _Inout_  LPINT              lpAddressLength
);
Run Code Online (Sandbox Code Playgroud)

AddressString一个_In_参数,而不是一个_Inout_参数.我不清楚为什么API采用非const指针,并导致编译失败,因为我有一个const char*.

我的第一个问题是,为什么WSAStringToAddress采用非常量指针?

我的第二个问题是,将常数抛弃是否安全?会WSAStringToAddress修改char*参数吗?


下面是更后面的故事的......我试图用WSAStringToAddressinet_addr更换由于在Visual Studio中的当代版本弃用警告.

这是PetarKorponaić提供答案问题中详述的相同问题.Korponaić遇到了同样的问题.它的额外副本的原因:

int inet_pton(int af, const char *src, void *dst)
{
  struct sockaddr_storage ss;
  int size = sizeof(ss);
  char src_copy[INET6_ADDRSTRLEN+1];

  ZeroMemory(&ss, sizeof(ss));
  /* stupid non-const API */
  strncpy (src_copy, src, INET6_ADDRSTRLEN+1);
  src_copy[INET6_ADDRSTRLEN] = …
Run Code Online (Sandbox Code Playgroud)

parameters winapi const winsock2

6
推荐指数
1
解决办法
136
查看次数

Windows 套接字:如何在非阻塞 connect() 上立即检测 TCP RST?

我们的软件(Nmap 端口扫描器)需要快速确定非阻塞 TCP 套接字的状态connect()。我们select()用来监控很多套接字,Windows 擅长在一个成功时通知我们。但是如果端口关闭并且目标发送 TCP RST,Windows 会在通知 之前继续尝试几次exceptfds,并且套接字错误WSAECONNREFUSED如预期。不过,我们的应用程序有自己的超时,并且通常会在 Windows 放弃之前将连接标记为超时。我们希望尽可能接近 Linux 的行为,即ECONNREFUSED在收到第一个 RST 后立即通知。

我们尝试使用TCP_MAXRT套接字选项,这可以立即select()向我们发出信号,但结果(对于关闭的端口)总是WSAETIMEDOUT,这使得无法区分关闭(RST)和过滤/防火墙(网络超时),这让我们回到原来的问题。确定这种区别是我们应用程序的核心功能。

那么在 Windows 上找出非阻塞套接字connect()是否已收到连接重置的最佳方法是什么?

编辑添加:这里的一个核心问题是微软关于SO_ERROR套接字选项的文档中的这一行:“这个每套接字错误代码并不总是立即设置。” 如果立即设置,我们可以在连接超时之前检查它。

windows select tcp winsock winsock2

6
推荐指数
0
解决办法
420
查看次数

C套接字:套接字关闭时避免垃圾

我正在使用非阻塞套接字(fd_setsselect函数)编写服务器和客户端,一旦服务器关闭或关闭客户端套接字,客户端就会开始接收大量垃圾直到它崩溃.我已经被警告过,当工作时用select()插座将成为可读当连接被终止,但我怎么能知道

if( FD_ISSET( socket, &read ) ) 
{
} 
Run Code Online (Sandbox Code Playgroud)

如果原因只是常规数据或连接已结束?

非常感谢!

c sockets networking select winsock2

5
推荐指数
1
解决办法
614
查看次数

如何使用 getaddrinfo()?

我正在尝试制作一个简单的程序,它接受一个像 www.google.com 这样的字符串并返回 IP 地址......

到目前为止我所拥有的:

char* hostname = new char[www.size()+1];
std::copy(www.begin(), www.end(), hostname);
hostname[www.size()] = '\0';

struct addrinfo new_addr, *res;

getaddrinfo(www.c_str(), SERVICE.c_str(), &new_addr, &res);



cout << new_addr.ai_addr;
Run Code Online (Sandbox Code Playgroud)

第 4 个参数中的第 3 个应该做什么?getaddrinfo 函数是否修改了 new_addr 结构或什么?我不太了解 msdn 文档。解析主机名后,我想将套接字连接到它。

winsock winsock2 getaddrinfo

5
推荐指数
1
解决办法
1万
查看次数

Winsock2 listen() 是如何阻塞的?

MSDN说:Listen() 是一个阻塞调用。我在其中使用过 listen() 的函数的代码片段如下所示:

sockaddr_in addr    = {0};
int     addrlen = sizeof(addr);
SOCKET  sock_listen;

if(-1 == (sock_listen = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP)))
{
    cout<<"error";
}   

addr.sin_family = AF_INET;
/* Network byte ordered address for loopback */
addr.sin_addr.s_addr= inet_addr("127.0.0.1");
/* Let service provider assign a unique port from dynamic client port range */  
addr.sin_port   = 0;                        

if(-1 == bind(sock_listen, (const sockaddr *)&addr, addrlen))       
{
    CloseHandle((HANDLE)sock_listen_fd);
    cout<<"error";
}

if(-1 == getsockname(sock_listen, (sockaddr *)&addr, &addrlen))
{     
    CloseHandle((HANDLE)sock_listen);
    cout<<"error";
}

u_long mode = 0; …
Run Code Online (Sandbox Code Playgroud)

sockets linux windows blocking winsock2

5
推荐指数
1
解决办法
744
查看次数

IO完成端口初始读取和双向数据

我有以下简化的 IO 完成端口服务器 C++ 代码:

int main(..)
{
    startCompletionPortThreadProc();

    // Await client connection

    sockaddr_in clientAddress;
    int clientAddressSize = sizeof( clientAddress );
    SOCKET acceptSocket = WSAAccept( serverSocket, (SOCKADDR*)&clientAddress, &clientAddressSize, NULL, NULL);  

    // Connected

    CreateIoCompletionPort( (HANDLE)acceptSocket, completionPort, 0, 0 );

    // Issue initial read
    read( acceptSocket );
}


DWORD WINAPI completionPortThreadProc( LPVOID param )
{
    DWORD bytesTransferred = 0;
    ULONG_PTR completionKey = NULL;
    LPPER_IO_DATA perIoData = NULL;

    while( GetQueuedCompletionStatus( completionPort, &bytesTransferred, &completionKey, (LPOVERLAPPED*)&perIoData, INFINITE ) )
    {
        if( WaitForSingleObject( exitEvent, 0 ) …
Run Code Online (Sandbox Code Playgroud)

c++ iocp winsock2

5
推荐指数
1
解决办法
600
查看次数