我有一个使用mpi的C ++程序,它遵循典型的客户端服务器模型。客户端的每个mpi实例都连接到服务器的相应mpi实例。这已经相当不错了,直到我不得不做一些延迟增加的测试(精确增加延迟1秒)。
问题: 有时,其中一个服务器进程不认为客户端已连接但客户端认为已连接。即使用gdb后,服务器正在accept()处等待,但客户端已经继续执行connect()。因此,当服务器认为它没有连接时,客户端认为它已连接。
我最好的猜测是我需要在某处设置一个sock-option,但是与其他程序员交谈并使用Google搜索并没有产生任何有用的结果。
编辑: 有两组MPI进程(因此对mpirun进行两次不同的调用),accept()和connect()调用用于套接字,它们位于两组MPI进程之间。这是openmpi。
代码(实际上来自其他人的代码)[减少]:
客户端(连接代码):( m_socket是实际的套接字)
if (-1 == m_socket)
{
perror("cannot create socket");
exit(EXIT_FAILURE);
}
memset(&addr, 0, sizeof(addr));
addr.sin_family = AF_INET;
addr.sin_port = htons(port);
res = inet_pton(AF_INET, host_ip, &addr.sin_addr);
if (0 > res)
{
perror("error: first parameter is not a valid address family");
close(m_socket);
exit(EXIT_FAILURE);
}
else if (0 == res)
{
perror("error: second parameter does not contain valid IP address");
close(m_socket);
exit(EXIT_FAILURE);
}
//backoff
for (int sec = 1; sec < 20000; sec++ )
{
int ret;
if (0 == (ret = connect(m_socket, (struct sockaddr *)&addr, sizeof(addr))))
{
return;
}
sleep(1);
close(m_socket);
m_socket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
}
perror("connect failed");
close(m_socket);
exit(EXIT_FAILURE);
服务器:( m_socket是实际的套接字)
int socket = ::accept(m_socket, NULL, NULL);
if(socket < 0)
{
fprintf(stderr, "accept() failed: %s\n", strerror(errno));
close(m_socket);
exit(EXIT_FAILURE);
}
答案 0 :(得分:0)
看起来您正在尝试手动连接/接受,而不是使用MPI。如果您尝试使用MPI进行连接,可以查看Deino(http://mpi.deino.net/mpi_functions/MPI_Comm_accept.html)上的示例。
或者,您可能只需要查看MPI的更一般的教程(这里有一些:http://www.mcs.anl.gov/research/projects/mpi/tutorial/)来了解通信的工作原理。大多数时候和应用程序不使用Connect / Accept进行通信,而是使用MPI Communicator在进程之间建立通信机制。这是一个不同的模型(SPMD而不是MPMD)。