Subject: [Fwd: Re: [Lksctp-developers] Broken Pipe error when client disconnect abruptly]

From: "La Monte H.P. Yarroll" <[email-masked]>
Date: Wed, 02 Mar 2005 13:16:19 -0500

Randy, is this your server code?  I don't know if you want to handle
every error case going in reference code like this, but I thought
you might want to know about this bug report...

-------- Original Message --------
From: 	- Wed Mar 02 13:09:37 2005
exchange.timesys.com with Microsoft SMTPSVC(5.0.2195.6713); Wed, 2 Mar 
2005 13:06:51 -0500
Received: 	from projects.sourceforge.net (sc8-sf-list1-b.sourceforge.net 
[10.3.1.7]) by sc8-sf-spam2.sourceforge.net (Postfix) with ESMTP id 
A427912192; Wed, 2 Mar 2005 10:09:20 -0800 (PST)
Received: 	from sc8-sf-mx2-b.sourceforge.net ([10.3.1.12] 
helo=sc8-sf-mx2.sourceforge.net) by sc8-sf-list1.sourceforge.net with 
esmtp (Exim 4.30) id 1D6YHN-0001WE-LG for 
[email-masked]; Wed, 02 Mar 2005 10:09:01 -0800
Received: 	from e6.ny.us.ibm.com ([32.97.182.146]) by 
sc8-sf-mx2.sourceforge.net with esmtp (TLSv1:AES256-SHA:256) (Exim 4.41) 
id 1D6YHM-0008Kf-JX for [email-masked]; Wed, 02 
Mar 2005 10:09:01 -0800
Received: 	from d01relay02.pok.ibm.com (d01relay02.pok.ibm.com 
[9.56.227.234]) by e6.ny.us.ibm.com (8.12.11/8.12.11) with ESMTP id 
j22I8qpJ013141 for <[email-masked]>; Wed, 2 Mar 
2005 13:08:52 -0500
Received: 	from d01av02.pok.ibm.com (d01av02.pok.ibm.com [9.56.224.216]) 
by d01relay02.pok.ibm.com (8.12.10/NCO/VER6.6) with ESMTP id 
j22I8qLP044802 for <[email-masked]>; Wed, 2 Mar 
2005 13:08:52 -0500
Received: 	from d01av02.pok.ibm.com (loopback [127.0.0.1]) by 
d01av02.pok.ibm.com (8.12.11/8.12.11) with ESMTP id j22I8qRV025567 for 
<[email-masked]>; Wed, 2 Mar 2005 13:08:52 -0500
Received: 	from sig-9-65-50-149.mts.ibm.com (sig-9-65-50-149.mts.ibm.com 
[9.65.50.149]) by d01av02.pok.ibm.com (8.12.11/8.12.11) with ESMTP id 
j22I8lqw025292; Wed, 2 Mar 2005 13:08:49 -0500
From: 	Sridhar Samudrala <[email-masked]>
X-X-Sender: 	[email-masked]
To: 	Karthik <[email-masked]>
Cc: 	[email-masked]
Subject: 	Re: [Lksctp-developers] Broken Pipe error when client 
disconnect abruptly
http://spamassassin.org/tag/ for more details. Report problems to 
http://sf.net/tracker/?func=add&group_id=1&atid=200001 0.0 
SF_CHICKENPOX_PARATHESES_OPEN BODY: Text interparsed with ( 0.0 
SF_CHICKENPOX_PARATHESES_CLOSE BODY: Text interparsed with ) 0.0 
SF_CHICKENPOX_PERIOD BODY: Text interparsed with . 0.0 
SF_CHICKENPOX_SLASH BODY: Text interparsed with / 0.0 
SF_CHICKENPOX_MINUS BODY: Text interparsed with - 0.0 
SF_CHICKENPOX_BRACKET_OPEN BODY: Text interparsed with [ 0.0 
SF_CHICKENPOX_UNDERSCORE BODY: Text interparsed with _ 0.0 
SF_CHICKENPOX_EQUAL BODY: Text interparsed with = 0.0 
SF_CHICKENPOX_BACKSLASH BODY: Text interparsed with \ 0.0 
SF_CHICKENPOX_AT BODY: Text interparsed with @ -0.0 AWL AWL: From: 
address is in the auto white-list
Sender: 	[email-masked]
Date: 	Wed, 2 Mar 2005 23:38:46 +0530 (IST)
FILETIME=[9C2DE540:01C51F52]

Karthik,

The echo server is trying to echo the received message using sendmsg() and
noticing that the association is already closed by the client. So it correctly
returns EPIPE error to the user. 
You either need to handle EPIPE error on the server or let the client wait
for the echoed message before closing the association.

-Sridhar

On Tue, 1 Mar 2005, Karthik wrote:

> Hello!!
>
> I am using the echo server program provided in the
> socket extension draft
> (draft-ietf-tsvwg-sctpsocket-09.txt). The problem is
> when the echo client is connected to the server
> diconnects abruptly(i hit "ctrl + c" soon after
> sending a message and before receiving the message
> sent), the server gives a "Broken pipe" error(at the
> sendmsg() call as it fails) and aborts.
>
> How do i avoid this error, so that the server would
> again work normally and wait for a new connection.
>
> For reference i am attaching the code below :
>
>   #include <stdio.h>
>   #include <sys/types.h>
>   #include <sys/socket.h>
>   #include <netinet/in.h>
>   #include <arpa/inet.h>
>   #include <stdlib.h>
>   #include <unistd.h>
>   #include <netinet/sctp.h>
>   #include <sys/uio.h>
>
>   #define BUFLEN  100
>
>   static void
>   handle_event(void *buf)
>   {
>           struct sctp_assoc_change *sac;
>           struct sctp_send_failed *ssf;
>           struct sctp_paddr_change *spc;
>           struct sctp_remote_error *sre;
>           union sctp_notification *snp;
>           char addrbuf[INET6_ADDRSTRLEN];
>           const char *ap;
>           struct sockaddr_in *sin;
>           struct sockaddr_in6 *sin6;
>
>           snp = buf;
>
>           switch (snp->sn_header.sn_type) {
>           case SCTP_ASSOC_CHANGE:
>                   sac = &snp->sn_assoc_change;
>                   printf("^^^ assoc_change:
> state=%hu, error=%hu, instr=%hu "
>                       "outstr=%hu\n", sac->sac_state,
> sac->sac_error,
>                       sac->sac_inbound_streams,
> sac->sac_outbound_streams);
>                   break;
>           case SCTP_SEND_FAILED:
>                   ssf = &snp->sn_send_failed;
>                   printf("^^^ sendfailed: len=%hu
> err=%d\n", ssf->ssf_length,
>                       ssf->ssf_error);
>                   break;
>
>           case SCTP_PEER_ADDR_CHANGE:
>                   spc = &snp->sn_paddr_change;
>                   if (spc->spc_aaddr.ss_family ==
> AF_INET) {
>                     sin = (struct sockaddr_in
> *)&spc->spc_aaddr;
>                     ap = inet_ntop(AF_INET,
> &sin->sin_addr,
>                                    addrbuf,
> INET6_ADDRSTRLEN);
>                   } else {
>                     sin6 = (struct sockaddr_in6
> *)&spc->spc_aaddr;
>                     ap = inet_ntop(AF_INET6,
> &sin6->sin6_addr,
>                                    addrbuf,
> INET6_ADDRSTRLEN);
>                   }
>                   printf("^^^ intf_change: %s
> state=%d, error=%d\n", ap,
>                          spc->spc_state,
> spc->spc_error);
>                   break;
>           case SCTP_REMOTE_ERROR:
>                   sre = &snp->sn_remote_error;
>                   printf("^^^ remote_error: err=%hu
> len=%hu\n",
>                       ntohs(sre->sre_error),
> ntohs(sre->sre_length));
>                   break;
>           case SCTP_SHUTDOWN_EVENT:
>                   printf("^^^ shutdown event\n");
>                   break;
>           default:
>                   printf("unknown type: %hu\n",
> snp->sn_header.sn_type);
>                   break;
>           }
>   }
>
>   static void *
>   mysctp_recvmsg(int fd, struct msghdr *msg, void
> *buf, size_t *buflen,
>       ssize_t *nrp, size_t cmsglen)
>   {
>           ssize_t nr = 0, nnr = 0;
>           struct iovec iov[1];
>
>           *nrp = 0;
>           iov->iov_base = buf;
>           iov->iov_len = *buflen;
>           msg->msg_iov = iov;
>           msg->msg_iovlen = 1;
>
>
>           for (;;) {
>
>   #ifndef MSG_XPG4_2
>   #define MSG_XPG4_2 0
>   #endif
>                   msg->msg_flags = MSG_XPG4_2;
>                   msg->msg_controllen = cmsglen;
>
>                   nnr = recvmsg(fd, msg, 0);
>                   if (nnr <= 0) {
>                           /* EOF or error */
>                           *nrp = nr;
>                           return (NULL);
>                   }
>                   nr += nnr;
>
>                   if ((msg->msg_flags & MSG_EOR) !=
> 0) {
>                           *nrp = nr;
>                           return (buf);
>                   }
>
>                   /* Realloc the buffer? */
>                   if (*buflen == (size_t)nr) {
>                           buf = realloc(buf, *buflen
> * 2);
>                           if (buf == 0) {
>                                   fprintf(stderr,
> "out of memory\n");
>                                   exit(1);
>                           }
>                           *buflen *= 2;
>                   }
>
>                   /* Set the next read offset */
>                   iov->iov_base = (char *)buf + nr;
>                   iov->iov_len = *buflen - nr;
>
>           }
>   }
>
>   static void
>   echo(int fd, int socketModeone_to_many)
>   {
>           ssize_t nr;
>           struct sctp_sndrcvinfo *sri;
>           struct msghdr msg[1];
>           struct cmsghdr *cmsg;
>           char cbuf[sizeof (*cmsg) + sizeof (*sri)];
>           char *buf;
>           size_t buflen;
>           struct iovec iov[1];
>           size_t cmsglen = sizeof (*cmsg) + sizeof
> (*sri);
>
>           /* Allocate the initial data buffer */
>           buflen = BUFLEN;
>           if (!(buf = malloc(BUFLEN))) {
>                   fprintf(stderr, "out of memory\n");
>                   exit(1);
>           }
>
>           /* Set up the msghdr structure for
> receiving */
>           memset(msg, 0, sizeof (*msg));
>           msg->msg_control = cbuf;
>           msg->msg_controllen = cmsglen;
>           msg->msg_flags = 0;
>           cmsg = (struct cmsghdr *)cbuf;
>           sri = (struct sctp_sndrcvinfo *)(cmsg + 1);
>
>           /* Wait for something to echo */
>           while (buf = mysctp_recvmsg(fd, msg, buf,
> &buflen, &nr, cmsglen)) {
>
>                   /* Intercept notifications here */
>                   if (msg->msg_flags &
> MSG_NOTIFICATION) {
>                           handle_event(buf);
>                           continue;
>                   }
>
>                   iov->iov_base = buf;
>                   iov->iov_len = nr;
>                   msg->msg_iov = iov;
>                   msg->msg_iovlen = 1;
>
>                   printf("got %u bytes on stream
> %hu:\n", nr,
>                       sri->sinfo_stream);
>                   write(0, buf, nr);
>
>                   /* Echo it back */
>                   msg->msg_flags = MSG_XPG4_2;
>                   if (sendmsg(fd, msg, 0) < 0) {
>                           perror("sendmsg");
>                           exit(1);
>                   }
>           }
>
>           if (nr < 0) {
>                   perror("recvmsg");
>           }
>           if(socketModeone_to_many == 0)
>             close(fd);
>   }
>
>   int main()
>   {
>           struct sctp_event_subscribe event;
>           int lfd, cfd;
>           int onoff = 1;
>           struct sockaddr_in sin[1];
>
>           if ((lfd = socket(AF_INET, SOCK_STREAM,
> IPPROTO_SCTP)) == -1) {
>                   perror("socket");
>                   exit(1);
>           }
>
>           sin->sin_family = AF_INET;
>           sin->sin_port = htons(7);
>           sin->sin_addr.s_addr = INADDR_ANY;
>           if (bind(lfd, (struct sockaddr *)sin,
> sizeof (*sin)) == -1) {
>                   perror("bind");
>                   exit(1);
>           }
>
>           if (listen(lfd, 1) == -1) {
>                   perror("listen");
>                   exit(1);
>           }
>
>           /* Wait for new associations */
>           for (;;) {
>                   if ((cfd = accept(lfd, NULL, 0)) ==
> -1) {
>                           perror("accept");
>                           exit(1);
>                   }
>
>                   /* Enable all events */
>                   event.sctp_data_io_event = 1;
>                   event.sctp_association_event = 1;
>                   event.sctp_address_event = 1;
>                   event.sctp_send_failure_event = 1;
>                   event.sctp_peer_error_event = 1;
>                   event.sctp_shutdown_event = 1;
>                   event.sctp_partial_delivery_event =
> 1;
>                   event.sctp_adaption_layer_event =
> 1;
>                   if (setsockopt(cfd, IPPROTO_SCTP,
>                       SCTP_EVENTS, &event,
>                       sizeof(event)) != 0) {
>                       perror("setevent failed");
>                       exit(1);
>                   }
>                   /* Echo back any and all data */
>
>                   echo(cfd,0);
>           }
>   }
>
>
>
> Thanking you in advance
>
> Karthik
>
> __________________________________________________
> Do You Yahoo!?
> Tired of spam?  Yahoo! Mail has the best spam protection around
> http://mail.yahoo.com
>
>
> -------------------------------------------------------
> SF email is sponsored by - The IT Product Guide
> Read honest & candid reviews on hundreds of IT Products from real users.
> Discover which products truly live up to the hype. Start reading now.
> http://ads.osdn.com/?ad_id=6595&alloc_id=14396&op=click
> _______________________________________________
> Lksctp-developers mailing list
> [email-masked]
> https://lists.sourceforge.net/lists/listinfo/lksctp-developers
>

-- 

-------------------------------------------------------
SF email is sponsored by - The IT Product Guide
Read honest & candid reviews on hundreds of IT Products from real users.
Discover which products truly live up to the hype. Start reading now.
http://ads.osdn.com/?ad_id=6595&alloc_id=14396&op=click
_______________________________________________
Lksctp-developers mailing list
[email-masked]
https://lists.sourceforge.net/lists/listinfo/lksctp-developers

-- 
"Beware of bugs in the above code; I have only proven it correct,
not tried it."  -Donald Knuth