(linenum→info "unix/slp.c:2238")

netbsdsrc/4.0/usr/src/usr.bin/tee/tee.c

    1: /*      $NetBSD: tee.c,v 1.7 2003/08/07 11:16:07 agc Exp $   */
    2: 
    3: /*
    4:  * Copyright (c) 1988, 1993
    5:  *      The Regents of the University of California.  All rights reserved.
    6:  *
    7:  * Redistribution and use in source and binary forms, with or without
    8:  * modification, are permitted provided that the following conditions
    9:  * are met:
   10:  * 1. Redistributions of source code must retain the above copyright
   11:  *    notice, this list of conditions and the following disclaimer.
   12:  * 2. Redistributions in binary form must reproduce the above copyright
   13:  *    notice, this list of conditions and the following disclaimer in the
   14:  *    documentation and/or other materials provided with the distribution.
   15:  * 3. Neither the name of the University nor the names of its contributors
   16:  *    may be used to endorse or promote products derived from this software
   17:  *    without specific prior written permission.
   18:  *
   19:  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
   20:  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
   21:  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
   22:  * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
   23:  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
   24:  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
   25:  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
   26:  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
   27:  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
   28:  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
   29:  * SUCH DAMAGE.
   30:  */
   31: 
   32: #include <sys/cdefs.h>
   33: #ifndef lint
   34: __COPYRIGHT("@(#) Copyright (c) 1988, 1993\n\
   35:         The Regents of the University of California.  All rights reserved.\n");
   36: #endif /* not lint */
   37: 
   38: #ifndef lint
   39: #if 0
   40: static char sccsid[] = "@(#)tee.c       8.1 (Berkeley) 6/6/93";
   41: #endif
   42: __RCSID("$NetBSD: tee.c,v 1.7 2003/08/07 11:16:07 agc Exp $");
   43: #endif
   44: 
   45: #include <sys/types.h>
   46: #include <sys/stat.h>
   47: #include <signal.h>
   48: #include <errno.h>
   49: #include <fcntl.h>
   50: #include <unistd.h>
   51: #include <stdio.h>
   52: #include <stdlib.h>
   53: #include <string.h>
   54: #include <locale.h>
   55: #include <err.h>
   56: 
   57: typedef struct _list {
   58:         struct _list *next;
   59:         int fd;
   60:         char *name;
   61: } LIST;
   62: LIST *head;
   63: 
   64: void    add __P((int, char *));
   65: int     main __P((int, char **));
   66: 
   67: int
   68: main(argc, argv)
   69:         int argc;
   70:         char *argv[];
   71: {
   72:         LIST *p;
   73:         int n, fd, rval, wval;
   74:         char *bp;
   75:         int append, ch, exitval;
   76:         char *buf;
   77: #define BSIZE (8 * 1024)
   78: 
   79:         setlocale(LC_ALL, "");
   80: 
   81:         append = 0;
   82:         while ((ch = getopt(argc, argv, "ai")) != -1)
   83:                 switch((char)ch) {
   84:                 case 'a':
   85:                         append = 1;
   86:                         break;
   87:                 case 'i':
   88:                         (void)signal(SIGINT, SIG_IGN);
   89:                         break;
   90:                 case '?':
   91:                 default:
   92:                         (void)fprintf(stderr, "usage: tee [-ai] [file ...]\n");
   93:                         exit(1);
   94:                 }
   95:         argv += optind;
   96:         argc -= optind;
   97: 
   98:         if ((buf = malloc((size_t)BSIZE)) == NULL)
   99:                 err(1, "malloc");
  100: 
  101:         add(STDOUT_FILENO, "stdout");
  102: 
  103:         for (exitval = 0; *argv; ++argv)
  104:                 if ((fd = open(*argv, append ? O_WRONLY|O_CREAT|O_APPEND :
  105:                     O_WRONLY|O_CREAT|O_TRUNC, DEFFILEMODE)) < 0) {
  106:                         warn("%s", *argv);
  107:                         exitval = 1;
  108:                 } else
  109:                         add(fd, *argv);
  110: 
  111:         while ((rval = read(STDIN_FILENO, buf, BSIZE)) > 0)
  112:                 for (p = head; p; p = p->next) {
  113:                         n = rval;
  114:                         bp = buf;
  115:                         do {
  116:                                 if ((wval = write(p->fd, bp, n)) == -1) {
  117:                                         warn("%s", p->name);
  118:                                         exitval = 1;
  119:                                         break;
  120:                                 }
  121:                                 bp += wval;
  122:                         } while (n -= wval);
  123:                 }
  124:         if (rval < 0) {
  125:                 warn("read");
  126:                 exitval = 1;
  127:         }
  128: 
  129:         for (p = head; p; p = p->next) {
  130:                 if (close(p->fd) == -1) {
  131:                         warn("%s", p->name);
  132:                         exitval = 1;
  133:                 }
  134:         }
  135: 
  136:         exit(exitval);
  137: }
  138: 
  139: void
  140: add(fd, name)
  141:         int fd;
  142:         char *name;
  143: {
  144:         LIST *p;
  145: 
  146:         if ((p = malloc((size_t)sizeof(LIST))) == NULL)
  147:                 err(1, "malloc");
  148:         p->fd = fd;
  149:         p->name = name;
  150:         p->next = head;
  151:         head = p;
  152: }
Syntax (Markdown)