我正在编写一个客户端 - 服务器C项目,其中服务器处理来自客户端的消息,并将它们复制到备份服务器。它运作良好,但项目的一个要点(它的大学项目)是为错误做好准备,在这种情况下 - 备份服务器死亡。
我在复制功能上有这个:
int table_skel_replicate(struct message_t *msg, int sockSecundario){
char *msg_buf;
int buf_size_net = 0;
int buf_size=0;
int okk;
struct sockaddr_in server;
msg->opcode--;
buf_size = message_to_buffer ( msg, &msg_buf );
buf_size_net = htonl(buf_size);
okk = write( sockSecundario, &buf_size_net, sizeof(int) );
if(okk == -1 || okk == 0) {
msg->opcode++;
return okk;
}
okk = write_all ( sockSecundario, msg_buf, buf_size );
if(okk == -1) {
msg->opcode++;
return okk;
}
okk = read ( sockSecundario, &buf_size_net, sizeof(int) );
if(okk == -1 || okk == 0) {
msg->opcode++;
return okk;
}
buf_size = ntohl(buf_size_net);
msg_buf = malloc ( buf_size );
okk = read_all( sockSecundario, msg_buf, buf_size );
msg->opcode++;
return okk;
}
一旦备份服务器死亡,它应该在第一个write()
失败。但它没有。
相反,它会对write_all()
函数进行处理(对于长传输,它基本上是write()
内的while
)并在那里的第一个write()
处死。我尝试使用checksockopt()
函数,但它返回状态为ok ...
主要应用程序只是关闭。任何帮助表示赞赏...
答案 0 :(得分:0)
您对write()
电话的检查可能无效,因为程序因SIGPIPE而终止。 man 2 write:
fd 连接到读取结束的管道或套接字 关闭。当发生这种情况时,写作过程也会收到一个 SIGPIPE 信号。 (因此,只有在写入返回值时才会看到 程序捕获,阻止或忽略此信号。)
为了轻松避免这种情况,请更换每个
write( sockSecundario, …, … )
通过
send(sockSecundario, …, …, MSG_NOSIGNAL)