[BACK]Return to atomicio.c CVS log [TXT][DIR] Up to [local] / src / usr.bin / ssh

Diff for /src/usr.bin/ssh/atomicio.c between version 1.14.2.1 and 1.15

version 1.14.2.1, 2006/09/30 04:06:50 version 1.15, 2006/03/19 18:51:18
Line 1 
Line 1 
 /* $OpenBSD$ */  
 /*  /*
  * Copyright (c) 2006 Damien Miller. All rights reserved.  
  * Copyright (c) 2005 Anil Madhavapeddy. All rights reserved.   * Copyright (c) 2005 Anil Madhavapeddy. All rights reserved.
  * Copyright (c) 1995,1999 Theo de Raadt.  All rights reserved.   * Copyright (c) 1995,1999 Theo de Raadt.  All rights reserved.
  * All rights reserved.   * All rights reserved.
Line 26 
Line 24 
  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.   * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  */   */
   
 #include <sys/param.h>  #include "includes.h"
 #include <sys/uio.h>  
   
 #include <errno.h>  
 #include <string.h>  
   
 #include "atomicio.h"  #include "atomicio.h"
   
 /*  /*
  * ensure all of data on socket comes through. f==read || f==vwrite   * ensure all of data on socket comes through. f==read || f==vwrite
  */   */
 size_t  size_t
 atomicio(ssize_t (*f) (int, void *, size_t), int fd, void *_s, size_t n)  atomicio(f, fd, _s, n)
           ssize_t (*f) (int, void *, size_t);
           int fd;
           void *_s;
           size_t n;
 {  {
         char *s = _s;          char *s = _s;
         size_t pos = 0;          size_t pos = 0;
Line 59 
Line 57 
                 }                  }
         }          }
         return (pos);          return (pos);
 }  
   
 /*  
  * ensure all of data on socket comes through. f==readv || f==writev  
  */  
 size_t  
 atomiciov(ssize_t (*f) (int, const struct iovec *, int), int fd,  
     const struct iovec *_iov, int iovcnt)  
 {  
         size_t pos = 0, rem;  
         ssize_t res;  
         struct iovec iov_array[IOV_MAX], *iov = iov_array;  
   
         if (iovcnt > IOV_MAX) {  
                 errno = EINVAL;  
                 return 0;  
         }  
         /* Make a copy of the iov array because we may modify it below */  
         memcpy(iov, _iov, iovcnt * sizeof(*_iov));  
   
         for (; iovcnt > 0 && iov[0].iov_len > 0;) {  
                 res = (f) (fd, iov, iovcnt);  
                 switch (res) {  
                 case -1:  
                         if (errno == EINTR || errno == EAGAIN)  
                                 continue;  
                         return 0;  
                 case 0:  
                         errno = EPIPE;  
                         return pos;  
                 default:  
                         rem = (size_t)res;  
                         pos += rem;  
                         /* skip completed iov entries */  
                         while (iovcnt > 0 && rem >= iov[0].iov_len) {  
                                 rem -= iov[0].iov_len;  
                                 iov++;  
                                 iovcnt--;  
                         }  
                         /* This shouldn't happen... */  
                         if (rem > 0 && (iovcnt <= 0 || rem > iov[0].iov_len)) {  
                                 errno = EFAULT;  
                                 return 0;  
                         }  
                         if (iovcnt == 0)  
                                 break;  
                         /* update pointer in partially complete iov */  
                         iov[0].iov_base = ((char *)iov[0].iov_base) + rem;  
                         iov[0].iov_len -= rem;  
                 }  
         }  
         return pos;  
 }  }

Legend:
Removed from v.1.14.2.1  
changed lines
  Added in v.1.15