write on closed connection doesn't generate si

2019-01-26 02:25发布

I've this problem with my server/client on C. If I close the server socket after a SIGINT, and then I try to write on this closed connection from the client, I've to do write two times before than client generates SIGPIPE. Shouldn't it generate it immediately? Is this a normal behaviour or something I need to fix? This is my code. I'm testing things on ubuntu, same PC, connecting via 127.0.0.1.

server.c

sigset_t set;
struct sigaction sign;
int sock_acc;
int sock;

void closeSig(){
    close(sock_acc);
    close(sock);
    exit(1);
}


int main(){
    sigemptyset(&set);
    sigaddset(&set, SIGINT);
    sig.sa_sigaction = &closeSig;
    sig.sa_flags = SA_SIGINFO;
    sig.sa_mask = set;
    sigaction(SIGINT, &sig, NULL);
    //other code to accept the connection from the client
    sigprocmask(SIG_UNBLOCK, &set, NULL);
    //write/read calls
}

client.c

void closeSigPipe(){
    close(ds_sock);
    printf("Stop...");
    exit(1);
}

int main(){
    sigpipe.sa_sigaction = &closeSigPipe;
    sigpipe.sa_flags = SA_SIGINFO;
    sigaction(SIGPIPE, &sigpipe, NULL);
    //other code to connect the server, and write/read calls
}

The problem is that when I close the server terminal with CTRL+C, the first write to the connection from the client works without any problem... perror("Error:"); prints "success"...

1条回答
Viruses.
2楼-- · 2019-01-26 02:52

The TCP protocol doesn't provide a way for the receiver to tell the sender that it's closing the connection. When it closes the connection, it sends a FIN segment, but this just means that it's done sending, not that it can no longer receive.

The way the sender detects that the connection has been closed is that it tries to send data, and the receiver sends back a RST segment in response. But writing to a socket doesn't wait for the response, it just queues the data and returns immediately. The signal occurs when the RST is received, which will be a short time later.

The reason you have to do two writes may be because of Nagle's Algorithm. To avoid excessive network overhead, TCP tries to combine short messages into a single segment. The Wikipedia page includes some workarounds for this.

查看更多
登录 后发表回答