linux - TCP recv error! Connection reset by peer? -
why? didn't on other peer!
i using massive threads data server. when thread count small, it's ok. when thread count large, recv()
return -1 , errno
indicates "connection reset peer".
here example reproduce issue:
server.cc
#include <arpa/inet.h> #include <assert.h> #include <netinet/in.h> #include <pthread.h> #include <unistd.h> char buffer[4096]; inline int send_all(int socket_fd, const char* data, size_t size, int flags) { int result; const char* pos = data; while (size > 0) { result = send(socket_fd, pos, size, flags); assert(result > 0); pos += result; size -= result; } return 0; } inline int recv_all(int socket_fd, void* data, size_t size, int flags) { int result = recv(socket_fd, data, size, flags | msg_waitall); assert(((size_t) result) == size); return 0; } void* server_thread(void* arg) { int socket_fd = (int) ((long) arg); // recv info first recv_all(socket_fd, buffer, 1, 0); // simulate computation (int = 0; < 0xffff; ++) (int j = 0; j < 0xffff; j ++); // send data (int = 0; < 4096; ++) send_all(socket_fd, buffer, sizeof(buffer), 0); // peer closed, return 0 recv(socket_fd, buffer, 1, msg_waitall); close(socket_fd); pthread_detach(pthread_self()); return null; } int main(void) { int listen_socket = socket(af_inet, sock_stream, 0); assert(listen_socket != -1); struct sockaddr_in listen_address; listen_address.sin_family = af_inet; listen_address.sin_port = htons(11282); listen_address.sin_addr.s_addr = inaddr_any; int result = bind(listen_socket, (struct sockaddr*) &listen_address, sizeof(listen_address)); assert(result != -1); result = listen(listen_socket, 5); assert(result != -1); while (true) { int server_socket = accept(listen_socket, null, null); assert(server_socket != -1); pthread_t tid; result = pthread_create(&tid, null, server_thread, (void *) ((long) server_socket)); assert(result != -1); } return 0; }
client.cc
#include <arpa/inet.h> #include <assert.h> #include <netinet/in.h> #include <pthread.h> #include <stdlib.h> #include <unistd.h> pthread_t threads[4096]; char buffer[4096]; inline int send_all(int socket_fd, const char* data, size_t size, int flags) { int result; const char* pos = data; while (size > 0) { result = send(socket_fd, pos, size, flags); assert(result > 0); pos += result; size -= result; } return 0; } inline int recv_all(int socket_fd, void* data, size_t size, int flags) { int result = recv(socket_fd, data, size, flags | msg_waitall); assert(((size_t) result) == size); return 0; } void* client_thread(void* arg) { int socket_fd = socket(af_inet, sock_stream, 0); assert(socket_fd != -1); struct sockaddr_in server_address; server_address.sin_family = af_inet; server_address.sin_port = htons(11282); server_address.sin_addr.s_addr = inet_addr("127.0.0.1"); int result = connect(socket_fd, (struct sockaddr *) &server_address, sizeof(server_address)); assert(result != -1); // send info first send_all(socket_fd, buffer, 1, 0); // recv reply data (int = 0; < 4096; ++) recv_all(socket_fd, buffer, sizeof(buffer), 0); close(socket_fd); return null; } int main(int argc, char* argv[]) { assert(argc == 2); // client thread count int thread_count = atoi(argv[1]); assert(thread_count <= 4096); (int = 0; < thread_count; ++) { int result = pthread_create(&threads[i], null, client_thread, null); assert(result != -1); } (int = 0; < thread_count; ++) pthread_join(threads[i], null); return 0; }
usage:
./server ./client [thread_count]
i using 480 thread_count, sometime reproduce issue.
Comments
Post a Comment